Compare commits
2 Commits
7e51cc5ea1
...
a1ea56093c
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
a1ea56093c
|
||
|
|
1850e21810
|
@@ -397,17 +397,17 @@ export class GraphManager extends EventEmitter<{
|
|||||||
}
|
}
|
||||||
|
|
||||||
createNodeId() {
|
createNodeId() {
|
||||||
const max = Math.max(0, ...this.nodes.keys());
|
return Math.max(0, ...this.nodes.keys()) + 1;
|
||||||
return max + 1;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
createGraph(nodes: Node[], edges: [number, number, number, string][]) {
|
createGraph(nodes: Node[], edges: [number, number, number, string][]) {
|
||||||
// map old ids to new ids
|
// map old ids to new ids
|
||||||
const idMap = new Map<number, number>();
|
const idMap = new Map<number, number>();
|
||||||
|
|
||||||
|
let startId = this.createNodeId()
|
||||||
|
|
||||||
nodes = nodes.map((node) => {
|
nodes = nodes.map((node) => {
|
||||||
const id = this.createNodeId();
|
const id = startId++;
|
||||||
idMap.set(node.id, id);
|
idMap.set(node.id, id);
|
||||||
const type = this.registry.getNode(node.type);
|
const type = this.registry.getNode(node.type);
|
||||||
if (!type) {
|
if (!type) {
|
||||||
|
|||||||
@@ -26,15 +26,16 @@ export class GraphState {
|
|||||||
|
|
||||||
constructor(private graph: GraphManager) { }
|
constructor(private graph: GraphManager) { }
|
||||||
|
|
||||||
cameraPosition: [number, number, number] = $state([0, 0, 4]);
|
width = $state(100);
|
||||||
wrapper = $state<HTMLDivElement>(null!);
|
height = $state(100);
|
||||||
|
|
||||||
|
wrapper = $state<HTMLDivElement>(null!);
|
||||||
rect: DOMRect = $derived(
|
rect: DOMRect = $derived(
|
||||||
this.wrapper ? this.wrapper.getBoundingClientRect() : new DOMRect(0, 0, 0, 0),
|
(this.wrapper && this.width && this.height) ? this.wrapper.getBoundingClientRect() : new DOMRect(0, 0, 0, 0),
|
||||||
);
|
);
|
||||||
width = $derived(this.rect?.width ?? 100);
|
|
||||||
height = $derived(this.rect?.height ?? 100);
|
|
||||||
camera = $state<OrthographicCamera>(null!);
|
camera = $state<OrthographicCamera>(null!);
|
||||||
|
cameraPosition: [number, number, number] = $state([0, 0, 4]);
|
||||||
|
|
||||||
clipboard: null | {
|
clipboard: null | {
|
||||||
nodes: Node[];
|
nodes: Node[];
|
||||||
@@ -192,43 +193,42 @@ export class GraphState {
|
|||||||
copyNodes() {
|
copyNodes() {
|
||||||
if (this.activeNodeId === -1 && !this.selectedNodes?.size)
|
if (this.activeNodeId === -1 && !this.selectedNodes?.size)
|
||||||
return;
|
return;
|
||||||
let _nodes = [
|
let nodes = [
|
||||||
this.activeNodeId,
|
this.activeNodeId,
|
||||||
...(this.selectedNodes?.values() || []),
|
...(this.selectedNodes?.values() || []),
|
||||||
]
|
]
|
||||||
.map((id) => this.graph.getNode(id))
|
.map((id) => this.graph.getNode(id))
|
||||||
.filter(Boolean) as Node[];
|
.filter(b => !!b);
|
||||||
|
|
||||||
const _edges = this.graph.getEdgesBetweenNodes(_nodes);
|
const edges = this.graph.getEdgesBetweenNodes(nodes);
|
||||||
_nodes = $state.snapshot(
|
nodes = nodes.map((node) => ({
|
||||||
_nodes.map((_node) => ({
|
...node,
|
||||||
..._node,
|
position: [
|
||||||
tmp: {
|
this.mousePosition[0] - node.position[0],
|
||||||
downX: this.mousePosition[0] - _node.position[0],
|
this.mousePosition[1] - node.position[1],
|
||||||
downY: this.mousePosition[1] - _node.position[1],
|
],
|
||||||
},
|
tmp: undefined,
|
||||||
})),
|
}));
|
||||||
);
|
|
||||||
|
|
||||||
this.clipboard = {
|
this.clipboard = {
|
||||||
nodes: _nodes,
|
nodes: nodes,
|
||||||
edges: _edges,
|
edges: edges,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
pasteNodes() {
|
pasteNodes() {
|
||||||
if (!this.clipboard) return;
|
if (!this.clipboard) return;
|
||||||
|
|
||||||
const _nodes = this.clipboard.nodes
|
const nodes = this.clipboard.nodes
|
||||||
.map((node) => {
|
.map((node) => {
|
||||||
node.tmp = node.tmp || {};
|
node.tmp = node.tmp || {};
|
||||||
node.position[0] = this.mousePosition[0] - (node?.tmp?.downX || 0);
|
node.position[0] = this.mousePosition[0] - node.position[0];
|
||||||
node.position[1] = this.mousePosition[1] - (node?.tmp?.downY || 0);
|
node.position[1] = this.mousePosition[1] - node.position[1];
|
||||||
return node;
|
return node;
|
||||||
})
|
})
|
||||||
.filter(Boolean) as Node[];
|
.filter(Boolean) as Node[];
|
||||||
|
|
||||||
const newNodes = this.graph.createGraph(_nodes, this.clipboard.edges);
|
const newNodes = this.graph.createGraph(nodes, this.clipboard.edges);
|
||||||
this.selectedNodes.clear();
|
this.selectedNodes.clear();
|
||||||
for (const node of newNodes) {
|
for (const node of newNodes) {
|
||||||
this.selectedNodes.add(node.id);
|
this.selectedNodes.add(node.id);
|
||||||
|
|||||||
@@ -37,14 +37,14 @@ export function setupKeymaps(keymap: Keymap, graph: GraphManager, graphState: Gr
|
|||||||
key: "c",
|
key: "c",
|
||||||
ctrl: true,
|
ctrl: true,
|
||||||
description: "Copy active nodes",
|
description: "Copy active nodes",
|
||||||
callback: graphState.copyNodes,
|
callback: () => graphState.copyNodes(),
|
||||||
});
|
});
|
||||||
|
|
||||||
keymap.addShortcut({
|
keymap.addShortcut({
|
||||||
key: "v",
|
key: "v",
|
||||||
ctrl: true,
|
ctrl: true,
|
||||||
description: "Paste nodes",
|
description: "Paste nodes",
|
||||||
callback: graphState.pasteNodes,
|
callback: () => graphState.pasteNodes(),
|
||||||
});
|
});
|
||||||
|
|
||||||
keymap.addShortcut({
|
keymap.addShortcut({
|
||||||
|
|||||||
Reference in New Issue
Block a user