// Returns the connection color public static Color Drag( InteractionManager interaction, Vector2 mousePosition, NodeGUIData nodeGuiData, NodeConnectionOptions connectionOptions ) { dragData.Set(interaction.targetNode); int connectionIndex = connectionOptions.connectionMode == ConnectionMode.Dual ? DeGUIKey.Exclusive.ctrl && DeGUIKey.Extra.space ? 1 : 0 : interaction.targetNodeConnectorAreaIndex; Color color = GetConnectionColor( connectionIndex, interaction.targetNode.connectedNodesIds.Count, nodeGuiData, connectionOptions ); Vector2 attachP = interaction.targetNodeConnectorArea.center; // Pointers Rect pointerFrom = new Rect(attachP.x - 4, attachP.y - 4, 8, 8); Rect pointerTo = new Rect(mousePosition.x - 4, mousePosition.y - 4, 8, 8); using (new DeGUI.ColorScope(null, null, Color.black)) { GUI.DrawTexture(pointerFrom.Expand(4), DeStylePalette.circle); GUI.DrawTexture(pointerTo.Expand(4), DeStylePalette.circle); } using (new DeGUI.ColorScope(null, null, color)) { GUI.DrawTexture(pointerFrom, DeStylePalette.circle); GUI.DrawTexture(pointerTo, DeStylePalette.circle); } // Line Handles.DrawBezier(attachP, mousePosition, attachP, mousePosition, Color.black, null, _LineSize + 2); Handles.DrawBezier(attachP, mousePosition, attachP, mousePosition, color, null, _LineSize + 2); return(color); }
void RefreshMapTexture(Rect fullZeroBasedArea, Vector2 shift) { int w = _process.options.minimapResolution == ProcessOptions.MinimapResolution.Big ? 256 : _process.options.minimapResolution == ProcessOptions.MinimapResolution.Small ? 64 : 128; if (_texture == null || _texture.width != w) { _texture = new Texture2D(w, w, TextureFormat.ARGB32, true) { wrapMode = TextureWrapMode.Clamp, filterMode = FilterMode.Bilinear }; } Color32[] pixels = new Color32[w * w]; // Clear the texture int len = pixels.Length; for (int i = 0; i < len; ++i) { pixels[i] = new Color32(0, 0, 0, 0); } _texture.SetPixels32(pixels); // Draw the elements foreach (IEditorGUINode node in _process.nodes) { bool evidenceAsEndNode = false; if (_process.options.minimapEvidenceEndNodes) { foreach (string connId in node.connectedNodesIds) { if (!string.IsNullOrEmpty(connId)) { continue; } evidenceAsEndNode = true; break; } } NodeGUIData nodeGuiData = _process.nodeToGUIData[node]; Rect nodeRect = nodeGuiData.fullArea; int xMin = (int)((nodeRect.x + shift.x) * w / fullZeroBasedArea.width); int xMax = (int)((nodeRect.xMax + shift.x) * w / fullZeroBasedArea.width); int yMin = (int)((nodeRect.y + shift.y) * w / fullZeroBasedArea.height); int yMax = (int)((nodeRect.yMax + shift.y) * w / fullZeroBasedArea.height); for (int x = xMin; x < xMax; ++x) { for (int y = yMin; y < yMax; ++y) { _texture.SetPixel(x, w - y, evidenceAsEndNode ? Color.red : nodeGuiData.mainColor); } } } // Apply _texture.Apply(); }
/// <summary> /// Always connects from BottomOrRight side to TopOrLeft side. /// If ALT is pressed shows the delete connection button. /// Called during Repaint or MouseDown/Up. /// Returns TRUE if the connection was deleted using the delete connection button. /// </summary> public static bool Connect( NodeProcess process, int connectionIndex, int fromTotConnections, NodeConnectionOptions fromOptions, IEditorGUINode fromNode, IEditorGUINode toNode ) { _Styles.Init(); NodeGUIData fromGUIData = process.nodeToGUIData[fromNode]; NodeGUIData toGUIData = process.nodeToGUIData[toNode]; bool useSubFromAreas = fromOptions.connectionMode != ConnectionMode.Dual && fromGUIData.connectorAreas != null; Rect fromArea = useSubFromAreas ? fromGUIData.connectorAreas[connectionIndex] : fromGUIData.fullArea; AnchorsData anchorsData = GetAnchors(process, connectionIndex, fromNode, fromArea, toNode, toGUIData.fullArea, fromOptions, useSubFromAreas); Color color = GetConnectionColor(connectionIndex, fromTotConnections, fromGUIData, fromOptions); // Line (shadow + line) Handles.DrawBezier( anchorsData.fromLineP, anchorsData.toLineP, anchorsData.fromTangent, anchorsData.toTangent, _lineShadowColor, null, _LineSize + 2 ); Handles.DrawBezier(anchorsData.fromLineP, anchorsData.toLineP, anchorsData.fromTangent, anchorsData.toTangent, color, null, _LineSize); // Line start square Rect fromSquareR = anchorsData.fromIsSide ? new Rect(anchorsData.fromMarkP.x, anchorsData.fromMarkP.y - FromSquareHeight * 0.5f, FromSquareWidth, FromSquareHeight) : new Rect(anchorsData.fromMarkP.x - FromSquareHeight * 0.5f, anchorsData.fromMarkP.y, FromSquareHeight, FromSquareWidth); using (new DeGUI.ColorScope(null, null, color)) GUI.DrawTexture(fromSquareR, DeStylePalette.whiteSquare); // Arrow Rect arrowR = new Rect( anchorsData.toArrowP.x - DeStylePalette.ico_nodeArrow.width, anchorsData.toArrowP.y - DeStylePalette.ico_nodeArrow.height * 0.5f, DeStylePalette.ico_nodeArrow.width, DeStylePalette.ico_nodeArrow.height ); Matrix4x4 currGUIMatrix = GUI.matrix; if (anchorsData.arrowRequiresRotation) { GUIUtility.RotateAroundPivot(anchorsData.arrowRotationAngle, anchorsData.toArrowP * process.guiScale + process.guiScalePositionDiff); } using (new DeGUI.ColorScope(null, null, color)) GUI.DrawTexture(arrowR, DeStylePalette.ico_nodeArrow); GUI.matrix = currGUIMatrix; // Delete connection button (placed at center of line) if (DeGUIKey.Exclusive.alt) { Vector2 midP = anchorsData.fromTangent + (anchorsData.toTangent - anchorsData.fromTangent) * 0.5f; Vector2 midPAlt = anchorsData.fromLineP + (anchorsData.toLineP - anchorsData.fromLineP) * 0.5f; midP += (midPAlt - midP) * 0.25f; Rect btR = new Rect(midP.x - 5, midP.y - 5, 10, 10); using (new DeGUI.ColorScope(null, null, color)) GUI.DrawTexture(btR.Expand(2), DeStylePalette.circle); using (new DeGUI.ColorScope(null, null, DeGUI.colors.global.red)) { if (GUI.Button(btR, "", _Styles.btDelete)) { return(true); } } GUI.DrawTexture(btR.Contract(2), DeStylePalette.ico_delete); } return(false); }
void RefreshAnchorsData() { // Debug.Log("<color=#00ff00>REFRESH</color> " + Event.current.type); _nodeToAnchorsData.Clear(); for (int i = 0; i < _process.nodes.Count; ++i) { IEditorGUINode fromNode = _process.nodes[i]; NodeGUIData fromGUIData = _process.nodeToGUIData[fromNode]; NodeConnectionOptions fromOptions = _process.nodeToConnectionOptions[fromNode]; List <string> connections = fromNode.connectedNodesIds; int totConnections = fromNode.connectedNodesIds.Count; AnchorsData[] anchors = null; for (int c = totConnections - 1; c > -1; --c) { string connId = connections[c]; if (string.IsNullOrEmpty(connId)) { continue; // No connection } if (anchors == null) { anchors = new AnchorsData[totConnections]; } IEditorGUINode toNode = _process.idToNode[connId]; NodeGUIData toGUIData = _process.nodeToGUIData[toNode]; // Verify if area between nodes is visible if (!fromGUIData.isVisible && !toGUIData.isVisible) { Rect area = fromGUIData.fullArea.Add(toGUIData.fullArea); if (!_process.AreaIsVisible(area)) { continue; // No visible connection } } bool useSubFromAreas = fromOptions.connectionMode != ConnectionMode.Dual && fromGUIData.connectorAreas != null && (fromOptions.connectionMode != ConnectionMode.NormalPlus || c < totConnections - 1); Rect fromArea = useSubFromAreas ? fromGUIData.connectorAreas[c] : fromGUIData.fullArea; AnchorsData anchorsData = GetAnchorsAllSides( _process, c, fromNode, new RectCache(fromArea), toNode, new RectCache(toGUIData.fullArea), fromOptions, useSubFromAreas ); anchorsData.isSet = true; anchors[c] = anchorsData; } if (anchors != null) { _nodeToAnchorsData.Add(fromNode, anchors); } } }
// Returns the connection color public Color Drag( InteractionManager interaction, Vector2 mousePosition, NodeGUIData nodeGuiData, NodeConnectionOptions connectionOptions, float lineThickness ) { dragData.Set(interaction.targetNode); int connectionIndex; switch (connectionOptions.connectionMode) { case ConnectionMode.Dual: connectionIndex = DeGUIKey.Exclusive.ctrl && DeGUIKey.Extra.space ? 1 : 0; break; case ConnectionMode.NormalPlus: connectionIndex = DeGUIKey.Exclusive.ctrl && DeGUIKey.Extra.space ? interaction.targetNode.connectedNodesIds.Count - 1 : interaction.targetNodeConnectorAreaIndex; break; default: connectionIndex = interaction.targetNodeConnectorAreaIndex; break; } Color color = GetConnectionColor( connectionIndex, interaction.targetNode.connectedNodesIds.Count, nodeGuiData, connectionOptions ); Vector2 attachP = interaction.targetNodeConnectorArea.center; // Pointers Rect pointerFrom = new Rect(attachP.x - 4, attachP.y - 4, 8, 8); Rect pointerTo = new Rect(mousePosition.x - 4, mousePosition.y - 4, 8, 8); using (new DeGUI.ColorScope(null, null, Color.black)) { GUI.DrawTexture(pointerFrom.Expand(4), DeStylePalette.circle); GUI.DrawTexture(pointerTo.Expand(4), DeStylePalette.circle); } using (new DeGUI.ColorScope(null, null, color)) { GUI.DrawTexture(pointerFrom, DeStylePalette.circle); GUI.DrawTexture(pointerTo, DeStylePalette.circle); } // Line Handles.DrawBezier(attachP, mousePosition, attachP, mousePosition, Color.black, null, lineThickness + 2); Handles.DrawBezier(attachP, mousePosition, attachP, mousePosition, color, null, lineThickness); return(color); }
static Color GetConnectionColor(int connectionIndex, int totConnections, NodeGUIData nodeGuiData, NodeConnectionOptions connectionOptions) { if (connectionOptions.connectionMode == ConnectionMode.NormalPlus) { if (connectionIndex == totConnections - 1 || connectionOptions.gradientColor == null) { // PLUS connection return(connectionOptions.startColor == Color.clear ? nodeGuiData.mainColor : connectionOptions.startColor); } else { // Regular return(connectionOptions.gradientColor.Evaluate(connectionIndex / (float)(totConnections - 2))); } } return(totConnections < 2 || connectionOptions.gradientColor == null ? connectionOptions.startColor == Color.clear ? nodeGuiData.mainColor : connectionOptions.startColor : connectionOptions.gradientColor.Evaluate(connectionIndex / (float)(totConnections - 1))); }
public void EvaluateSnapping( IEditorGUINode forNode, Rect forArea, List <IEditorGUINode> allNodes, List <IEditorGUINode> excludedNodes, Dictionary <IEditorGUINode, NodeGUIData> nodeToGuiData, Rect processRelativeArea ) { hasSnapX = hasSnapY = showHorizontalGuide = showVerticalGuide = false; _topSnappingPs.Clear(); _bottomSnappingPs.Clear(); _leftSnappingPs.Clear(); _rightSnappingPs.Clear(); bool hasNearSnappingX = false; bool hasNearSnappingY = false; bool hasBorderSnapping = false; bool hasTopSnappingPs = false; bool hasBottomSnappingPs = false; bool hasLeftSnappingPs = false; bool hasRightSnappingPs = false; if (Event.current.alt || nodeToGuiData[forNode].disableSnapping) { return; // ALT pressed or snapping disabled - no snapping } // Find snapping points and store them int len = allNodes.Count; // Near snapping for (int i = 0; i < len; ++i) { IEditorGUINode node = allNodes[i]; if (node == forNode || excludedNodes.Contains(node)) { continue; } NodeGUIData nodeGUIData = nodeToGuiData[node]; if (nodeGUIData.disableSnapping) { continue; } Rect toArea = nodeGUIData.fullArea; if (!hasNearSnappingX && forArea.yMax > toArea.y && forArea.y < toArea.yMax) { // Within nearSnappingX range // Check rightToLeft then leftToRight if (forArea.xMax < toArea.x && toArea.x - forArea.xMax <= NodeProcess.SnapOffset) { hasSnapX = hasNearSnappingX = true; snapX = toArea.x - forArea.width - NodeProcess.SnapOffset; if (hasNearSnappingY) { break; } } else if (forArea.x > toArea.xMax && forArea.x - toArea.xMax <= NodeProcess.SnapOffset) { hasSnapX = hasNearSnappingX = true; snapX = toArea.xMax + NodeProcess.SnapOffset; if (hasNearSnappingY) { break; } } } if (!hasNearSnappingY && forArea.xMax >= toArea.x && forArea.x < toArea.xMax) { // Within nearSnappingY range // Check bottomToTop then topToBottom if (forArea.yMax < toArea.y && toArea.y - forArea.yMax <= NodeProcess.SnapOffset) { hasSnapY = hasNearSnappingY = true; snapY = toArea.y - forArea.height - NodeProcess.SnapOffset; if (hasNearSnappingX) { break; } } else if (forArea.y > toArea.yMax && forArea.y - toArea.yMax <= NodeProcess.SnapOffset) { hasSnapY = hasNearSnappingY = true; snapY = toArea.yMax + NodeProcess.SnapOffset; if (hasNearSnappingX) { break; } } } } if (!hasNearSnappingX || !hasNearSnappingY) { // Border snapping for (int i = 0; i < len; ++i) { IEditorGUINode node = allNodes[i]; if (node == forNode || excludedNodes.Contains(node)) { continue; } NodeGUIData nodeGUIData = nodeToGuiData[node]; if (nodeGUIData.disableSnapping) { continue; } Rect toArea = nodeGUIData.fullArea; if (!processRelativeArea.Overlaps(toArea)) { continue; } if (!hasNearSnappingX) { if (ValuesAreWithinBorderSnappingRange(forArea.x, toArea.x)) { _leftSnappingPs.Add(toArea.x); hasSnapX = showVerticalGuide = hasBorderSnapping = hasLeftSnappingPs = true; } else if (ValuesAreWithinBorderSnappingRange(forArea.x, toArea.xMax)) { _rightSnappingPs.Add(toArea.xMax); hasSnapX = showVerticalGuide = hasBorderSnapping = hasRightSnappingPs = true; } } if (!hasNearSnappingY) { if (ValuesAreWithinBorderSnappingRange(forArea.y, toArea.y)) { _topSnappingPs.Add(toArea.y); hasSnapY = showHorizontalGuide = hasBorderSnapping = hasTopSnappingPs = true; } else if (ValuesAreWithinBorderSnappingRange(forArea.y, toArea.yMax)) { _bottomSnappingPs.Add(toArea.yMax); hasSnapY = showHorizontalGuide = hasBorderSnapping = hasBottomSnappingPs = true; } } } // Find closes snapping point if (hasBorderSnapping) { if (hasLeftSnappingPs) { snapX = FindNearestValueTo(forArea.x, _leftSnappingPs); } else if (hasRightSnappingPs) { snapX = FindNearestValueTo(forArea.x, _rightSnappingPs); } if (hasTopSnappingPs) { snapY = FindNearestValueTo(forArea.y, _topSnappingPs); } else if (hasBottomSnappingPs) { snapY = FindNearestValueTo(forArea.y, _bottomSnappingPs); } } } }
/// <summary> /// Always connects from BottomOrRight side to TopOrLeft side. /// If ALT is pressed shows the delete connection button. /// Called during Repaint or MouseDown/Up. /// Returns TRUE if the connection was deleted using the delete connection button. /// </summary> public bool Connect( int connectionIndex, int fromTotConnections, NodeConnectionOptions fromOptions, IEditorGUINode fromNode ) { _Styles.Init(); if (_anchorsDataRefreshRequired) { _anchorsDataRefreshRequired = false; RefreshAnchorsData(); } NodeGUIData fromGUIData = _process.nodeToGUIData[fromNode]; if (!_nodeToAnchorsData.ContainsKey(fromNode)) { return(false); } AnchorsData anchorsData = _nodeToAnchorsData[fromNode][connectionIndex]; if (!anchorsData.isSet) { return(false); } // Color color = GetConnectionColor(connectionIndex, fromTotConnections, fromGUIData, fromOptions); // Line (shadow + line) if (_process.options.connectorsShadow) { Handles.DrawBezier( anchorsData.fromLineP, anchorsData.toLineP, anchorsData.fromTangent, anchorsData.toTangent, _LineShadowColor, null, _process.options.connectorsThickness + 2 ); } Handles.DrawBezier(anchorsData.fromLineP, anchorsData.toLineP, anchorsData.fromTangent, anchorsData.toTangent, color, null, _process.options.connectorsThickness); // Line start square Rect fromSquareR; switch (anchorsData.fromSide) { case ConnectionSide.Top: fromSquareR = new Rect(anchorsData.fromMarkP.x - _FromSquareHeight * 0.5f, anchorsData.fromMarkP.y - _FromSquareWidth, _FromSquareHeight, _FromSquareWidth); break; case ConnectionSide.Bottom: fromSquareR = new Rect(anchorsData.fromMarkP.x - _FromSquareHeight * 0.5f, anchorsData.fromMarkP.y, _FromSquareHeight, _FromSquareWidth); break; case ConnectionSide.Left: fromSquareR = new Rect(anchorsData.fromMarkP.x - _FromSquareWidth, anchorsData.fromMarkP.y - _FromSquareHeight * 0.5f, _FromSquareWidth, _FromSquareHeight); break; default: // Right fromSquareR = new Rect(anchorsData.fromMarkP.x, anchorsData.fromMarkP.y - _FromSquareHeight * 0.5f, _FromSquareWidth, _FromSquareHeight); break; } using (new DeGUI.ColorScope(null, null, color)) GUI.DrawTexture(fromSquareR, DeStylePalette.whiteSquare); // Arrow Rect arrowR = new Rect( anchorsData.toArrowP.x - DeStylePalette.ico_nodeArrow.width, anchorsData.toArrowP.y - DeStylePalette.ico_nodeArrow.height * 0.5f, DeStylePalette.ico_nodeArrow.width, DeStylePalette.ico_nodeArrow.height ); Matrix4x4 currGUIMatrix = GUI.matrix; if (anchorsData.arrowRequiresRotation) { GUIUtility.RotateAroundPivot(anchorsData.arrowRotationAngle, anchorsData.toArrowP * _process.guiScale + _process.guiScalePositionDiff); } using (new DeGUI.ColorScope(null, null, color)) GUI.DrawTexture(arrowR, DeStylePalette.ico_nodeArrow); GUI.matrix = currGUIMatrix; // Delete connection button (placed at center of line) if (DeGUIKey.Exclusive.alt) { Vector2 midP = anchorsData.fromTangent + (anchorsData.toTangent - anchorsData.fromTangent) * 0.5f; Vector2 midPAlt = anchorsData.fromLineP + (anchorsData.toLineP - anchorsData.fromLineP) * 0.5f; midP += (midPAlt - midP) * 0.25f; Rect btR = new Rect(midP.x - 5, midP.y - 5, 10, 10); using (new DeGUI.ColorScope(null, null, color)) GUI.DrawTexture(btR.Expand(2), DeStylePalette.circle); using (new DeGUI.ColorScope(null, null, DeGUI.colors.global.red)) { if (GUI.Button(btR, "", _Styles.btDelete)) { return(true); } } GUI.DrawTexture(btR.Contract(2), DeStylePalette.ico_delete); } return(false); }
static Color GetConnectionColor(int connectionIndex, int totConnections, NodeGUIData nodeGuiData, NodeConnectionOptions connectionOptions) { return(totConnections < 2 || connectionOptions.gradientColor == null ? connectionOptions.startColor == Color.clear ? nodeGuiData.mainColor : connectionOptions.startColor : connectionOptions.gradientColor.Evaluate(connectionIndex / (float)(totConnections - 1))); }