feat: add cmdk dependency and enhance canvas node creation with edge splitting functionality

- Introduced the cmdk package for improved command palette capabilities.
- Enhanced the canvas placement context to support creating nodes with edge splitting, allowing for more dynamic node interactions.
- Updated the canvas inner component to utilize optimistic updates for node creation, improving user experience during interactions.
- Refactored node handling logic to incorporate new mutation types and streamline data management.
This commit is contained in:
Matthias
2026-03-27 23:40:31 +01:00
parent 4e84e7f76f
commit 6e866f2df6
15 changed files with 1037 additions and 112 deletions

View File

@@ -0,0 +1,46 @@
export const CANVAS_NODE_TEMPLATES = [
{
type: "image",
label: "Bild",
width: 280,
height: 180,
defaultData: {},
},
{
type: "text",
label: "Text",
width: 256,
height: 120,
defaultData: { content: "" },
},
{
type: "prompt",
label: "Prompt",
width: 320,
height: 220,
defaultData: { prompt: "", model: "", aspectRatio: "1:1" },
},
{
type: "note",
label: "Notiz",
width: 220,
height: 120,
defaultData: { content: "" },
},
{
type: "frame",
label: "Frame",
width: 360,
height: 240,
defaultData: { label: "Untitled", exportWidth: 1080, exportHeight: 1080 },
},
{
type: "compare",
label: "Compare",
width: 500,
height: 380,
defaultData: {},
},
] as const;
export type CanvasNodeTemplate = (typeof CANVAS_NODE_TEMPLATES)[number];

View File

@@ -7,6 +7,46 @@ import type { Doc } from "@/convex/_generated/dataModel";
* Convex speichert positionX/positionY als separate Felder,
* React Flow erwartet position: { x, y }.
*/
/**
* Reichert Node-Dokumente mit `data.url` an (aus gebündelter Storage-URL-Map).
* Behält eine zuvor gemappte URL bei, solange die Batch-Query noch lädt.
*/
export function convexNodeDocWithMergedStorageUrl(
node: Doc<"nodes">,
urlByStorage: Record<string, string | undefined> | undefined,
previousDataByNodeId: Map<string, Record<string, unknown>>,
): Doc<"nodes"> {
const data = node.data as Record<string, unknown> | undefined;
const sid = data?.storageId;
if (typeof sid !== "string") {
return node;
}
if (urlByStorage) {
const fromBatch = urlByStorage[sid];
if (fromBatch !== undefined) {
return {
...node,
data: { ...data, url: fromBatch },
};
}
}
const prev = previousDataByNodeId.get(node._id);
if (
prev?.url !== undefined &&
typeof prev.storageId === "string" &&
prev.storageId === sid
) {
return {
...node,
data: { ...data, url: prev.url },
};
}
return node;
}
export function convexNodeToRF(node: Doc<"nodes">): RFNode {
return {
id: node._id,