Skip to content

Commit

Permalink
feat: add edge mouse event handlers for highlighting edges in the gra…
Browse files Browse the repository at this point in the history
…ph (#1301)
  • Loading branch information
AndrasEszes authored Nov 14, 2024
1 parent 20aa143 commit 0621d50
Show file tree
Hide file tree
Showing 3 changed files with 50 additions and 14 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -12,3 +12,4 @@ export const PLACEHOLDER_NODE_TYPE = 'placeholder';
export const DEFAULT_GRAPH_EDGE_ZINDEX = 0;
export const HIGHLIGHTED_GRAPH_EDGE_ZINDEX = 1;
export const SELECTED_GRAPH_EDGE_ZINDEX = 2;
export const DEFAULT_WORKFLOW_NODE_ZINDEX = 3;
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import { useCallback } from 'react';
import {
addEdge,
EdgeMouseHandler,
EdgeTypes,
Node,
NodeTypes,
Expand All @@ -24,7 +25,14 @@ import usePipelineWorkflows from './hooks/usePipelineWorkflows';
import transformWorkflowsToNodesAndEdges from './utils/transformWorkflowsToNodesAndEdges';
import autoLayoutingGraphNodes from './utils/autoLayoutingGraphNodes';
import PlaceholderNode from './components/WorkflowNode/PlaceholderWorkflowNode';
import { GRAPH_EDGE_TYPE, PLACEHOLDER_NODE_TYPE, WORKFLOW_NODE_TYPE } from './GraphPipelineCanvas.const';
import {
DEFAULT_GRAPH_EDGE_ZINDEX,
GRAPH_EDGE_TYPE,
HIGHLIGHTED_GRAPH_EDGE_ZINDEX,
PLACEHOLDER_NODE_TYPE,
SELECTED_GRAPH_EDGE_ZINDEX,
WORKFLOW_NODE_TYPE,
} from './GraphPipelineCanvas.const';
import validateConnection from './utils/validateConnection';

const nodeTypes: NodeTypes = {
Expand All @@ -37,21 +45,15 @@ const edgeTypes: EdgeTypes = {
};

const GraphPipelineCanvas = (props: ReactFlowProps) => {
const isGraphPipelineEnabled = useFeatureFlag('enable-dag-pipelines');

const { selectedPipeline } = usePipelineSelector();
const workflows = usePipelineWorkflows();

const { openDialog } = usePipelinesPageStore();
const { updateNode } = useReactFlow<Node<WorkflowNodeDataType>>();
const { nodes: initialNodes, edges: initialEdges } = transformWorkflowsToNodesAndEdges(
selectedPipeline,
workflows,
isGraphPipelineEnabled,
);
const { selectedPipeline } = usePipelineSelector();
const isGraphPipelineEnabled = useFeatureFlag('enable-dag-pipelines');
const { updateNode, updateEdge } = useReactFlow<Node<WorkflowNodeDataType>>();
const initial = transformWorkflowsToNodesAndEdges(selectedPipeline, workflows, isGraphPipelineEnabled);

const [edges, setEdges, onEdgesChange] = useEdgesState(initialEdges);
const [nodes, setNodes, onNodesChange] = useNodesState(autoLayoutingGraphNodes(initialNodes));
const [edges, setEdges, onEdgesChange] = useEdgesState(initial.edges);
const [nodes, setNodes, onNodesChange] = useNodesState(autoLayoutingGraphNodes(initial.nodes));

const { addPipelineWorkflowDependency, removeWorkflowFromPipeline, removePipelineWorkflowDependency } =
useBitriseYmlStore((s) => ({
Expand Down Expand Up @@ -108,6 +110,30 @@ const GraphPipelineCanvas = (props: ReactFlowProps) => {
[selectedPipeline, addPipelineWorkflowDependency, setEdges, updateNode],
);

const handleEdgeMouseEnter: EdgeMouseHandler = useCallback(
(_, { id, selected }) => {
const zIndex = selected ? SELECTED_GRAPH_EDGE_ZINDEX : HIGHLIGHTED_GRAPH_EDGE_ZINDEX;
updateEdge(id, { zIndex, data: { highlighted: true } });
},
[updateEdge],
);

const handleEdgeMouseLeave: EdgeMouseHandler = useCallback(
(_, { id, target, selected }) => {
const targetNodeSelected = nodes.some((node) => node.id === target && node.selected);

let zIndex = DEFAULT_GRAPH_EDGE_ZINDEX;
if (selected) {
zIndex = SELECTED_GRAPH_EDGE_ZINDEX;
} else if (targetNodeSelected) {
zIndex = HIGHLIGHTED_GRAPH_EDGE_ZINDEX;
}

updateEdge(id, { zIndex, data: { highlighted: targetNodeSelected } });
},
[updateEdge, nodes],
);

return (
<>
<ReactFlow
Expand All @@ -120,6 +146,9 @@ const GraphPipelineCanvas = (props: ReactFlowProps) => {
onEdgesDelete={handleEdgesDelete}
onNodesChange={handleNodesChanges}
onNodesDelete={handleNodesDelete}
onEdgeMouseMove={handleEdgeMouseEnter}
onEdgeMouseEnter={handleEdgeMouseEnter}
onEdgeMouseLeave={handleEdgeMouseLeave}
connectionLineComponent={ConnectionGraphEdge}
isValidConnection={validateConnection(nodes, edges)}
{...props}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,11 @@
import { Node } from '@xyflow/react';
import { PipelineWorkflow } from '@/core/models/Workflow';
import { WORKFLOW_NODE_HEIGHT, WORKFLOW_NODE_TYPE, WORKFLOW_NODE_WIDTH } from '../GraphPipelineCanvas.const';
import {
DEFAULT_WORKFLOW_NODE_ZINDEX,
WORKFLOW_NODE_HEIGHT,
WORKFLOW_NODE_TYPE,
WORKFLOW_NODE_WIDTH,
} from '../GraphPipelineCanvas.const';
import { WorkflowNodeDataType } from '../components/WorkflowNode/WorkflowNode';

export default function createNodeFromPipelineWorkflow(
Expand All @@ -20,5 +25,6 @@ export default function createNodeFromPipelineWorkflow(
height: WORKFLOW_NODE_HEIGHT,
position: { x: -9999, y: -9999 },
data: { ...workflow, pipelineId },
zIndex: DEFAULT_WORKFLOW_NODE_ZINDEX,
};
}

0 comments on commit 0621d50

Please sign in to comment.