diff --git a/src/components/admin/narrative-flow/BooleanNode.tsx b/src/components/admin/narrative-flow/BooleanNode.tsx
new file mode 100644
index 0000000..a8cd6b3
--- /dev/null
+++ b/src/components/admin/narrative-flow/BooleanNode.tsx
@@ -0,0 +1,24 @@
+"use client";
+
+import { Handle, Position, type NodeProps } from "@xyflow/react";
+import { CheckCircleIcon } from "lucide-react";
+
+export function BooleanNode({ data }: NodeProps) {
+ const d = data as { value?: boolean; description?: string };
+
+ return (
+
-
-
-
-
-
- {nodes.length} node{nodes.length !== 1 ? "s" : ""}, {edges.length} edge
- {edges.length !== 1 ? "s" : ""}
-
-
+ {toolbarButtons}
= ({
);
+ case "wait": {
+ const ticks = (nodeData.ticks as number) ?? 10;
+ return (
+
+ );
+ }
+
+ case "number": {
+ const value = (nodeData.value as number) ?? 0;
+ return (
+
+ );
+ }
+
+ case "string": {
+ const value = (nodeData.value as string) ?? "";
+ return (
+
+ );
+ }
+
+ case "random": {
+ const min = (nodeData.min as number) ?? 0;
+ const max = (nodeData.max as number) ?? 100;
+ return (
+
+ );
+ }
+
+ case "boolean": {
+ const value = (nodeData.value as boolean) ?? false;
+ return (
+
+
+
+
+
+
+
+
+
+
+ updateField("description", e.target.value)}
+ placeholder="What flag does this represent?"
+ className="dark:bg-zinc-800 dark:border-zinc-700 dark:text-zinc-100"
+ />
+
+
+ );
+ }
+
+ case "date": {
+ const value = (nodeData.value as string) ?? "";
+ return (
+
+ );
+ }
+
case "choice": {
const options = (nodeData.options as Array<{ id: string; label: string }>) ?? [];
return (
@@ -241,7 +435,19 @@ export const NodeEditDialog: FC
= ({
? "Choice"
: nodeType === "outcome"
? "Outcome"
- : "Node";
+ : nodeType === "wait"
+ ? "Wait"
+ : nodeType === "number"
+ ? "Number"
+ : nodeType === "string"
+ ? "String"
+ : nodeType === "random"
+ ? "Random"
+ : nodeType === "boolean"
+ ? "Boolean"
+ : nodeType === "date"
+ ? "Date"
+ : "Node";
return (