refactor: moved visualProgrammingUI into page folder
BREAKING: moved directory visualProgrammingUI and contents into VisProgPage ref: N25B-114
This commit is contained in:
@@ -0,0 +1,137 @@
|
||||
import { useDraggable } from '@neodrag/react';
|
||||
import {
|
||||
useReactFlow,
|
||||
type XYPosition
|
||||
} from '@xyflow/react';
|
||||
import {
|
||||
type ReactNode,
|
||||
useCallback,
|
||||
useRef,
|
||||
useState
|
||||
} from 'react';
|
||||
|
||||
|
||||
// improve later to create better automatic IDs
|
||||
let id = 0;
|
||||
const getId = () => `dndnode_${id++}`;
|
||||
|
||||
|
||||
interface DraggableNodeProps {
|
||||
className?: string;
|
||||
children: ReactNode;
|
||||
nodeType: string;
|
||||
onDrop: (nodeType: string, position: XYPosition) => void;
|
||||
}
|
||||
|
||||
function DraggableNode({ className, children, nodeType, onDrop }: DraggableNodeProps) {
|
||||
const draggableRef = useRef<HTMLDivElement>(null);
|
||||
const [position, setPosition] = useState<XYPosition>({ x: 0, y: 0 });
|
||||
|
||||
|
||||
// @ts-ignore
|
||||
useDraggable(draggableRef, {
|
||||
position: position,
|
||||
onDrag: ({ offsetX, offsetY }) => {
|
||||
// Calculate position relative to the viewport
|
||||
setPosition({
|
||||
x: offsetX,
|
||||
y: offsetY,
|
||||
});
|
||||
},
|
||||
onDragEnd: ({ event }) => {
|
||||
setPosition({ x: 0, y: 0 });
|
||||
onDrop(nodeType, {
|
||||
x: event.clientX,
|
||||
y: event.clientY,
|
||||
});
|
||||
},
|
||||
});
|
||||
|
||||
return (
|
||||
<div className={className === "default" ? "draggable-node" : "draggable-node" + "__" + className} ref={draggableRef}>
|
||||
{children}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
||||
export function Sidebar() {
|
||||
const { setNodes, screenToFlowPosition } = useReactFlow();
|
||||
|
||||
const handleNodeDrop = useCallback(
|
||||
(nodeType: string, screenPosition: XYPosition) => {
|
||||
const flow = document.querySelector('.react-flow');
|
||||
const flowRect = flow?.getBoundingClientRect();
|
||||
const isInFlow =
|
||||
flowRect &&
|
||||
screenPosition.x >= flowRect.left &&
|
||||
screenPosition.x <= flowRect.right &&
|
||||
screenPosition.y >= flowRect.top &&
|
||||
screenPosition.y <= flowRect.bottom;
|
||||
|
||||
// Create a new node and add it to the flow
|
||||
if (isInFlow) {
|
||||
const position = screenToFlowPosition(screenPosition);
|
||||
|
||||
const newNode = () => {
|
||||
switch (nodeType) {
|
||||
case "phase":
|
||||
return {
|
||||
id: getId(),
|
||||
type: nodeType,
|
||||
position,
|
||||
data: {label: `"new"`, number: (-1)},
|
||||
};
|
||||
case "start":
|
||||
return {
|
||||
id: getId(),
|
||||
type: nodeType,
|
||||
position,
|
||||
data: {label: `new start node`},
|
||||
};
|
||||
case "end":
|
||||
return {
|
||||
id: getId(),
|
||||
type: nodeType,
|
||||
position,
|
||||
data: {label: `new end node`},
|
||||
};
|
||||
case "norm":
|
||||
return {
|
||||
id: getId(),
|
||||
type: nodeType,
|
||||
position,
|
||||
data: {label: `new norm node`},
|
||||
};
|
||||
default: {
|
||||
return {
|
||||
id: getId(),
|
||||
type: nodeType,
|
||||
position,
|
||||
data: {label: `new default node`},
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
setNodes((nds) => nds.concat(newNode()));
|
||||
}
|
||||
},
|
||||
[setNodes, screenToFlowPosition],
|
||||
);
|
||||
|
||||
return (
|
||||
<aside style={{padding: '10px 10px',outline: '2.5pt solid black',borderRadius: '0pt 0pt 5pt 5pt', borderColor:'dimgrey', backgroundColor:'canvas', display:'flex', flexDirection: 'column', gap: '1rem'}}>
|
||||
<div className="description">
|
||||
You can drag these nodes to the pane to create new nodes.
|
||||
</div>
|
||||
<div className="DraggableNodeContainer" style={{backgroundColor:'canvas', display: 'flex', flexDirection: 'row', gap: '1rem', justifyContent: 'center'}}>
|
||||
<DraggableNode className="phase" nodeType="phase" onDrop={handleNodeDrop}>
|
||||
phase Node
|
||||
</DraggableNode>
|
||||
<DraggableNode className="norm" nodeType="norm" onDrop={handleNodeDrop}>
|
||||
norm Node
|
||||
</DraggableNode>
|
||||
</div>
|
||||
</aside>
|
||||
);
|
||||
}
|
||||
Reference in New Issue
Block a user