@you-agent-factory/components 0.0.0 → 0.0.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (182) hide show
  1. package/LICENSE.md +21 -0
  2. package/README.md +38 -7
  3. package/dist/category-paths.d.ts +3 -0
  4. package/dist/charts/chart-state-panel.d.ts +11 -0
  5. package/dist/charts/chart.d.ts +35 -0
  6. package/dist/charts/index.d.ts +5 -0
  7. package/dist/charts/index.js +287 -0
  8. package/dist/chunks/action-row.js +39 -0
  9. package/dist/chunks/alert-panel.js +182 -0
  10. package/dist/chunks/button.js +193 -0
  11. package/dist/chunks/cn.js +6 -0
  12. package/dist/chunks/factory-emulator-controls.js +123 -0
  13. package/dist/chunks/package-form-field.js +546 -0
  14. package/dist/chunks/scroll-area.js +261 -0
  15. package/dist/chunks/surface-panel.js +73 -0
  16. package/dist/chunks/table-layout.js +292 -0
  17. package/dist/chunks/typography-roles.js +26 -0
  18. package/dist/chunks/typography.js +129 -0
  19. package/dist/chunks/widget-frame.js +344 -0
  20. package/dist/data-display/code-panel.d.ts +12 -0
  21. package/dist/data-display/data-table.d.ts +27 -0
  22. package/dist/data-display/description-list.d.ts +4 -0
  23. package/{src/data-display/index.ts → dist/data-display/index.d.ts} +4 -26
  24. package/dist/data-display/index.js +20 -0
  25. package/dist/data-display/table-layout.d.ts +8 -0
  26. package/dist/data-display/table.d.ts +14 -0
  27. package/dist/factory-emulator/factory-emulator-controls.d.ts +23 -0
  28. package/dist/factory-emulator/index.d.ts +6 -0
  29. package/dist/factory-emulator/index.js +6 -0
  30. package/dist/feedback/alert-panel-semantics.d.ts +11 -0
  31. package/dist/feedback/alert-panel.d.ts +29 -0
  32. package/dist/feedback/index.d.ts +6 -0
  33. package/dist/feedback/index.js +10 -0
  34. package/dist/feedback/skeleton.d.ts +2 -0
  35. package/dist/forms/index.d.ts +19 -0
  36. package/dist/forms/index.js +37 -0
  37. package/dist/forms/package-checkbox.d.ts +3 -0
  38. package/dist/forms/package-enum-select.d.ts +42 -0
  39. package/dist/forms/package-file-input.d.ts +3 -0
  40. package/dist/forms/package-form-field.d.ts +49 -0
  41. package/dist/forms/package-input.d.ts +6 -0
  42. package/dist/forms/package-native-select.d.ts +3 -0
  43. package/dist/forms/package-select.d.ts +32 -0
  44. package/dist/forms/package-textarea.d.ts +10 -0
  45. package/dist/forms/select-icons.d.ts +3 -0
  46. package/dist/graphs/graph-edge-path.d.ts +18 -0
  47. package/dist/graphs/graph-edge.d.ts +15 -0
  48. package/dist/graphs/graph-node-button.d.ts +11 -0
  49. package/dist/graphs/graph-node-handle-badge.d.ts +5 -0
  50. package/dist/graphs/graph-node-handle.d.ts +18 -0
  51. package/dist/graphs/graph-node-shell.d.ts +13 -0
  52. package/dist/graphs/graph-node-state-indicator.d.ts +6 -0
  53. package/dist/graphs/graph-node-state.d.ts +23 -0
  54. package/dist/graphs/graph-viewport-surface.d.ts +5 -0
  55. package/dist/graphs/index.d.ts +13 -0
  56. package/dist/graphs/index.js +614 -0
  57. package/{src/icons/index.ts → dist/icons/index.d.ts} +1 -2
  58. package/dist/icons/index.js +4 -0
  59. package/dist/index.d.ts +26 -0
  60. package/dist/index.js +145 -0
  61. package/dist/layout/action-row.d.ts +8 -0
  62. package/{src/layout/index.ts → dist/layout/index.d.ts} +1 -3
  63. package/dist/layout/index.js +9 -0
  64. package/dist/layout/surface-panel.d.ts +15 -0
  65. package/{src/navigation/index.ts → dist/navigation/index.d.ts} +1 -2
  66. package/dist/navigation/index.js +4 -0
  67. package/dist/overlays/collapsible.d.ts +5 -0
  68. package/dist/overlays/dialog.d.ts +16 -0
  69. package/dist/overlays/index.d.ts +10 -0
  70. package/dist/overlays/index.js +27 -0
  71. package/dist/overlays/overlay-layout.d.ts +6 -0
  72. package/dist/overlays/popover.d.ts +6 -0
  73. package/dist/overlays/scroll-area.d.ts +9 -0
  74. package/dist/primitives/button-link.d.ts +5 -0
  75. package/dist/primitives/button.d.ts +9 -0
  76. package/dist/primitives/icon-button-shell.d.ts +10 -0
  77. package/{src/primitives/index.ts → dist/primitives/index.d.ts} +2 -19
  78. package/dist/primitives/index.js +49 -0
  79. package/dist/primitives/package-text.d.ts +6 -0
  80. package/dist/primitives/typography-roles.d.ts +12 -0
  81. package/dist/primitives/typography.d.ts +36 -0
  82. package/dist/recipes/index.d.ts +14 -0
  83. package/dist/recipes/index.js +32 -0
  84. package/dist/recipes/widget-frame-content.d.ts +24 -0
  85. package/dist/recipes/widget-frame-disclosure.d.ts +33 -0
  86. package/dist/recipes/widget-frame-layout.d.ts +12 -0
  87. package/dist/recipes/widget-frame-skeleton.d.ts +2 -0
  88. package/dist/recipes/widget-frame-states.d.ts +15 -0
  89. package/dist/recipes/widget-frame-typography.d.ts +10 -0
  90. package/dist/recipes/widget-frame.d.ts +12 -0
  91. package/{src → dist}/styles.css +36 -0
  92. package/dist/testing/index.d.ts +4 -0
  93. package/dist/testing/index.js +16 -0
  94. package/dist/testing/render.d.ts +5 -0
  95. package/{src/tokens/index.ts → dist/tokens/index.d.ts} +1 -2
  96. package/dist/tokens/index.js +4 -0
  97. package/dist/utilities/cn.d.ts +1 -0
  98. package/{src/utilities/index.ts → dist/utilities/index.d.ts} +1 -3
  99. package/dist/utilities/index.js +6 -0
  100. package/package.json +65 -64
  101. package/docs/README.md +0 -83
  102. package/docs/button.md +0 -119
  103. package/docs/charts.md +0 -325
  104. package/docs/data-display-code-panel.md +0 -120
  105. package/docs/feedback-alert-panel.md +0 -117
  106. package/docs/feedback-skeleton.md +0 -54
  107. package/docs/forms-form-field.md +0 -490
  108. package/docs/forms-input-primitives.md +0 -311
  109. package/docs/forms-select-primitives.md +0 -362
  110. package/docs/graphs.md +0 -250
  111. package/docs/layout-display-primitives.md +0 -211
  112. package/docs/overlays.md +0 -414
  113. package/docs/table-data-table.md +0 -331
  114. package/docs/typography-roles.md +0 -182
  115. package/docs/widget-frame-recipes.md +0 -273
  116. package/src/category-paths.ts +0 -20
  117. package/src/charts/chart-state-panel.tsx +0 -103
  118. package/src/charts/chart.tsx +0 -287
  119. package/src/charts/index.ts +0 -21
  120. package/src/data-display/code-panel.tsx +0 -67
  121. package/src/data-display/data-table.tsx +0 -180
  122. package/src/data-display/description-list.tsx +0 -24
  123. package/src/data-display/table-layout.ts +0 -12
  124. package/src/data-display/table.tsx +0 -131
  125. package/src/feedback/alert-panel-semantics.ts +0 -75
  126. package/src/feedback/alert-panel.tsx +0 -187
  127. package/src/feedback/index.ts +0 -21
  128. package/src/feedback/skeleton.tsx +0 -16
  129. package/src/forms/index.ts +0 -73
  130. package/src/forms/package-checkbox.tsx +0 -50
  131. package/src/forms/package-enum-select.tsx +0 -185
  132. package/src/forms/package-file-input.tsx +0 -25
  133. package/src/forms/package-form-field.tsx +0 -202
  134. package/src/forms/package-input.tsx +0 -25
  135. package/src/forms/package-native-select.tsx +0 -25
  136. package/src/forms/package-select.tsx +0 -209
  137. package/src/forms/package-textarea.tsx +0 -35
  138. package/src/forms/select-icons.tsx +0 -35
  139. package/src/graphs/graph-edge-path.ts +0 -241
  140. package/src/graphs/graph-edge.tsx +0 -130
  141. package/src/graphs/graph-interactive-example.tsx +0 -187
  142. package/src/graphs/graph-node-button.tsx +0 -51
  143. package/src/graphs/graph-node-handle-badge.tsx +0 -108
  144. package/src/graphs/graph-node-handle.ts +0 -28
  145. package/src/graphs/graph-node-shell.tsx +0 -111
  146. package/src/graphs/graph-node-state-indicator.tsx +0 -47
  147. package/src/graphs/graph-node-state.ts +0 -111
  148. package/src/graphs/graph-viewport-surface.tsx +0 -27
  149. package/src/graphs/index.ts +0 -41
  150. package/src/index.ts +0 -209
  151. package/src/layout/action-row.tsx +0 -53
  152. package/src/layout/surface-panel.tsx +0 -91
  153. package/src/overlays/collapsible.tsx +0 -22
  154. package/src/overlays/dialog.tsx +0 -148
  155. package/src/overlays/index.ts +0 -31
  156. package/src/overlays/overlay-layout.ts +0 -9
  157. package/src/overlays/popover.tsx +0 -29
  158. package/src/overlays/scroll-area.tsx +0 -78
  159. package/src/primitives/button-link.tsx +0 -22
  160. package/src/primitives/button.tsx +0 -258
  161. package/src/primitives/icon-button-shell.tsx +0 -49
  162. package/src/primitives/package-text.tsx +0 -29
  163. package/src/primitives/typography-roles.ts +0 -12
  164. package/src/primitives/typography.tsx +0 -165
  165. package/src/recipes/index.ts +0 -61
  166. package/src/recipes/widget-frame-content.tsx +0 -114
  167. package/src/recipes/widget-frame-disclosure.tsx +0 -161
  168. package/src/recipes/widget-frame-layout.ts +0 -40
  169. package/src/recipes/widget-frame-skeleton.tsx +0 -16
  170. package/src/recipes/widget-frame-states.tsx +0 -99
  171. package/src/recipes/widget-frame-typography.ts +0 -19
  172. package/src/recipes/widget-frame.tsx +0 -84
  173. package/src/testing/index.ts +0 -13
  174. package/src/testing/render.tsx +0 -16
  175. package/src/utilities/cn.ts +0 -5
  176. /package/{src → dist}/styles/color-palette-presets.css +0 -0
  177. /package/{src → dist}/styles/color-role-tokens.css +0 -0
  178. /package/{src → dist}/styles/layout-role-tokens.css +0 -0
  179. /package/{src → dist}/styles/text-color-role-tokens.css +0 -0
  180. /package/{src → dist}/styles/typography-role-tokens.css +0 -0
  181. /package/{src → dist}/styles/typography-role-utilities.css +0 -0
  182. /package/{src → dist}/styles/typography-roles.css +0 -0
@@ -1,187 +0,0 @@
1
- import "@xyflow/react/dist/style.css";
2
-
3
- import {
4
- Background,
5
- Controls,
6
- ReactFlow,
7
- ReactFlowProvider,
8
- type Edge,
9
- type Node,
10
- type NodeProps,
11
- } from "@xyflow/react";
12
- import { useCallback, useMemo, useState } from "react";
13
-
14
- import { GRAPH_EDGE_TYPES } from "./graph-edge";
15
- import {
16
- desktopInteractiveGraphNodes,
17
- type GraphInteractiveFixtureNode,
18
- } from "./graph-story-fixtures";
19
- import { GraphNodeButton } from "./graph-node-button";
20
- import { GraphNodeShell } from "./graph-node-shell";
21
- import type { GraphNodeState } from "./graph-node-state";
22
- import { GraphViewportSurface } from "./graph-viewport-surface";
23
-
24
- type GenericGraphFlowNodeData = GraphInteractiveFixtureNode & {
25
- graphState: GraphNodeState;
26
- onActivate?: () => void;
27
- shellState: GraphNodeState;
28
- };
29
-
30
- function GenericGraphFlowNode({ data }: NodeProps<Node<GenericGraphFlowNodeData>>) {
31
- return (
32
- <div className="w-44 max-w-full sm:w-52">
33
- <GraphNodeShell
34
- handles={data.handles}
35
- nodeKind={data.nodeKind}
36
- state={data.shellState}
37
- stateLabel={data.stateLabel}
38
- >
39
- <GraphNodeButton
40
- graphState={data.graphState}
41
- onClick={data.onActivate}
42
- stateLabel={data.stateLabel}
43
- >
44
- {data.label}
45
- </GraphNodeButton>
46
- </GraphNodeShell>
47
- </div>
48
- );
49
- }
50
-
51
- const GENERIC_GRAPH_NODE_TYPES = {
52
- genericGraph: GenericGraphFlowNode,
53
- };
54
-
55
- function buildFlowNodes(
56
- fixtureNodes: GraphInteractiveFixtureNode[],
57
- selectedNodeId: string | null,
58
- onSelectNode: (nodeId: string) => void,
59
- ): Node<GenericGraphFlowNodeData>[] {
60
- return fixtureNodes.map((fixtureNode) => {
61
- const isSelectable = fixtureNode.selectable === true;
62
- const isSelected = isSelectable && selectedNodeId === fixtureNode.id;
63
- const resolvedState =
64
- fixtureNode.fixedState ?? (isSelected ? "selected" : "default");
65
-
66
- return {
67
- data: {
68
- ...fixtureNode,
69
- graphState: resolvedState,
70
- onActivate: isSelectable
71
- ? () => {
72
- onSelectNode(fixtureNode.id);
73
- }
74
- : undefined,
75
- shellState: resolvedState,
76
- },
77
- draggable: false,
78
- id: fixtureNode.id,
79
- position: fixtureNode.position,
80
- selectable: false,
81
- type: "genericGraph",
82
- };
83
- });
84
- }
85
-
86
- function buildFlowEdges(
87
- fixtureNodes: GraphInteractiveFixtureNode[],
88
- selectedNodeId: string | null,
89
- ): Edge[] {
90
- const readyNode = fixtureNodes.find((node) => node.id === "ready-node");
91
- const targetNode = fixtureNodes.find((node) => node.id === "target-node");
92
-
93
- if (!readyNode || !targetNode) {
94
- return [];
95
- }
96
-
97
- return [
98
- {
99
- data: {
100
- alwaysShowLabel: true,
101
- label: "Example edge",
102
- waypoints:
103
- readyNode.position.y === targetNode.position.y
104
- ? undefined
105
- : [
106
- {
107
- x: (readyNode.position.x + targetNode.position.x) / 2 + 72,
108
- y: readyNode.position.y + 48,
109
- },
110
- {
111
- x: (readyNode.position.x + targetNode.position.x) / 2 + 72,
112
- y: targetNode.position.y + 48,
113
- },
114
- ],
115
- },
116
- id: "ready-to-target",
117
- selectable: false,
118
- source: readyNode.id,
119
- target: targetNode.id,
120
- type: "graphEdge",
121
- },
122
- ].map((edge) => ({
123
- ...edge,
124
- selected: selectedNodeId === edge.source || selectedNodeId === edge.target,
125
- }));
126
- }
127
-
128
- export type GraphInteractiveExampleProps = {
129
- "aria-label"?: string;
130
- className?: string;
131
- fixtureNodes?: GraphInteractiveFixtureNode[];
132
- initialSelectedNodeId?: string | null;
133
- viewportWidthClass?: string;
134
- };
135
-
136
- export function GraphInteractiveExample({
137
- "aria-label": ariaLabel = "Interactive graph example",
138
- className = "h-[28rem]",
139
- fixtureNodes = desktopInteractiveGraphNodes,
140
- initialSelectedNodeId = null,
141
- viewportWidthClass = "w-[48rem] max-w-full",
142
- }: GraphInteractiveExampleProps) {
143
- const [selectedNodeId, setSelectedNodeId] = useState<string | null>(
144
- initialSelectedNodeId,
145
- );
146
-
147
- const handleSelectNode = useCallback((nodeId: string) => {
148
- setSelectedNodeId(nodeId);
149
- }, []);
150
-
151
- const nodes = useMemo(
152
- () => buildFlowNodes(fixtureNodes, selectedNodeId, handleSelectNode),
153
- [fixtureNodes, handleSelectNode, selectedNodeId],
154
- );
155
- const edges = useMemo(
156
- () => buildFlowEdges(fixtureNodes, selectedNodeId),
157
- [fixtureNodes, selectedNodeId],
158
- );
159
-
160
- return (
161
- <ReactFlowProvider>
162
- <div className={viewportWidthClass}>
163
- <GraphViewportSurface aria-label={ariaLabel} className={className}>
164
- <ReactFlow
165
- defaultEdgeOptions={{ selectable: false }}
166
- edgeTypes={GRAPH_EDGE_TYPES}
167
- edges={edges}
168
- fitView
169
- fitViewOptions={{ padding: 0.2 }}
170
- maxZoom={1.25}
171
- minZoom={0.5}
172
- nodeTypes={GENERIC_GRAPH_NODE_TYPES}
173
- nodes={nodes}
174
- nodesConnectable={false}
175
- nodesDraggable={false}
176
- panOnDrag={true}
177
- proOptions={{ hideAttribution: true }}
178
- zoomOnScroll={true}
179
- >
180
- <Background gap={16} size={1} />
181
- <Controls showInteractive={false} />
182
- </ReactFlow>
183
- </GraphViewportSurface>
184
- </div>
185
- </ReactFlowProvider>
186
- );
187
- }
@@ -1,51 +0,0 @@
1
- import { type ButtonHTMLAttributes, forwardRef } from "react";
2
-
3
- import { cn } from "../utilities/cn";
4
- import {
5
- type GraphNodeState,
6
- graphNodeButtonIsDisabled,
7
- graphNodeButtonStateAttributes,
8
- graphNodeButtonStateClassName,
9
- } from "./graph-node-state";
10
-
11
- export type GraphNodeButtonProps = ButtonHTMLAttributes<HTMLButtonElement> & {
12
- graphState?: GraphNodeState;
13
- stateLabel?: string;
14
- };
15
-
16
- export const GRAPH_NODE_BUTTON_BASE_CLASS =
17
- "nodrag nopan cursor-pointer border-0 bg-transparent p-0 text-left text-inherit focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-af-focus-ring disabled:cursor-not-allowed disabled:opacity-100";
18
-
19
- export const GraphNodeButton = forwardRef<
20
- HTMLButtonElement,
21
- GraphNodeButtonProps
22
- >(function GraphNodeButton(
23
- {
24
- className,
25
- disabled,
26
- graphState = "default",
27
- onClick,
28
- stateLabel,
29
- type = "button",
30
- ...props
31
- },
32
- ref,
33
- ) {
34
- const isDisabled = graphNodeButtonIsDisabled(graphState, disabled);
35
-
36
- return (
37
- <button
38
- className={cn(
39
- GRAPH_NODE_BUTTON_BASE_CLASS,
40
- graphNodeButtonStateClassName(graphState),
41
- className,
42
- )}
43
- disabled={isDisabled}
44
- onClick={isDisabled ? undefined : onClick}
45
- ref={ref}
46
- type={type}
47
- {...graphNodeButtonStateAttributes(graphState, stateLabel)}
48
- {...props}
49
- />
50
- );
51
- });
@@ -1,108 +0,0 @@
1
- import { Handle, Position } from "@xyflow/react";
2
- import type { CSSProperties } from "react";
3
-
4
- import { cn } from "../utilities/cn";
5
- import type { GraphNodeHandle, GraphNodeHandleTone } from "./graph-node-handle";
6
-
7
- export interface GraphNodeHandleBadgeProps {
8
- handle: GraphNodeHandle;
9
- }
10
-
11
- export function GraphNodeHandleBadge({ handle }: GraphNodeHandleBadgeProps) {
12
- const position = handle.side === "left" ? Position.Left : Position.Right;
13
- const overlayHandleStyle = anchoredHandleStyle(handle.side);
14
-
15
- if (handle.hidden) {
16
- return (
17
- <Handle
18
- className="pointer-events-none !top-1/2 opacity-0"
19
- id={handle.id}
20
- isConnectable={handle.connectable ?? false}
21
- position={position}
22
- style={overlayHandleStyle}
23
- type={handle.type}
24
- />
25
- );
26
- }
27
-
28
- const tone = handle.tone ?? "default";
29
-
30
- return (
31
- <div
32
- className="pointer-events-none relative flex h-5 w-5 items-center justify-center"
33
- data-node-handle-badge={handle.id}
34
- data-node-handle-invalid={handle.validationError ? "true" : undefined}
35
- data-node-handle-tone={tone}
36
- >
37
- <Handle
38
- aria-invalid={handle.validationError ? true : undefined}
39
- aria-label={handle.buttonAriaLabel ?? handle.label}
40
- className={cn(
41
- "pointer-events-auto absolute !top-1/2 !h-5 !w-5 !border-0 !bg-transparent",
42
- "before:pointer-events-none before:absolute before:top-1/2 before:h-2.5 before:w-2.5 before:-translate-x-1/2 before:-translate-y-1/2 before:rounded-full before:border before:border-surface before:bg-[var(--node-handle-background)] before:shadow-sm before:transition before:content-['']",
43
- handle.side === "left" ? "before:left-0" : "before:left-full",
44
- handle.buttonPressed &&
45
- "before:scale-125 before:shadow-[0_0_0_3px_var(--color-primary-container)]",
46
- handle.variant === "valid-target" &&
47
- "before:scale-125 before:shadow-[0_0_0_3px_var(--color-success-container)]",
48
- handle.variant === "error" &&
49
- "before:border-af-danger-border before:shadow-[0_0_0_3px_var(--color-error-container)] motion-safe:before:animate-pulse",
50
- handle.validationError &&
51
- "before:ring-2 before:ring-af-danger-border motion-safe:before:animate-pulse",
52
- )}
53
- id={handle.id}
54
- isConnectable={handle.connectable ?? true}
55
- onClick={handle.onButtonClick}
56
- position={position}
57
- style={
58
- {
59
- ...overlayHandleStyle,
60
- "--node-handle-background": handleDotColor(tone),
61
- opacity: handle.buttonDisabled ? 0.45 : undefined,
62
- } as CSSProperties
63
- }
64
- title={handle.buttonTitle ?? handle.validationMessage}
65
- type={handle.type}
66
- />
67
- </div>
68
- );
69
- }
70
-
71
- function handleDotColor(tone: GraphNodeHandleTone): string {
72
- switch (tone) {
73
- case "assignment":
74
- return "var(--color-success)";
75
- case "continue":
76
- return "var(--color-secondary)";
77
- case "failure":
78
- return "var(--color-error)";
79
- case "input":
80
- return "var(--color-success)";
81
- case "output":
82
- return "var(--color-success)";
83
- case "rejection":
84
- return "var(--color-warning)";
85
- case "resource":
86
- return "var(--color-black)";
87
- case "worker":
88
- return "var(--color-purple-500)";
89
- default:
90
- return "var(--color-success)";
91
- }
92
- }
93
-
94
- function anchoredHandleStyle(
95
- side: GraphNodeHandle["side"],
96
- ): CSSProperties {
97
- return side === "left"
98
- ? {
99
- left: "50%",
100
- top: "50%",
101
- transform: "translateY(-50%)",
102
- }
103
- : {
104
- left: "50%",
105
- top: "50%",
106
- transform: "translate(-100%, -50%)",
107
- };
108
- }
@@ -1,28 +0,0 @@
1
- export type GraphNodeHandleTone =
2
- | "assignment"
3
- | "continue"
4
- | "default"
5
- | "failure"
6
- | "input"
7
- | "output"
8
- | "rejection"
9
- | "resource"
10
- | "worker";
11
-
12
- export interface GraphNodeHandle {
13
- buttonAriaLabel?: string;
14
- buttonDisabled?: boolean;
15
- buttonPressed?: boolean;
16
- buttonTitle?: string;
17
- connectable?: boolean;
18
- hidden?: boolean;
19
- id: string;
20
- label: string;
21
- onButtonClick?: () => void;
22
- side: "left" | "right";
23
- tone?: GraphNodeHandleTone;
24
- type: "source" | "target";
25
- validationError?: boolean;
26
- validationMessage?: string;
27
- variant?: "default" | "error" | "muted" | "selected" | "valid-target";
28
- }
@@ -1,111 +0,0 @@
1
- import type { HTMLAttributes, ReactNode } from "react";
2
-
3
- import { cn } from "../utilities/cn";
4
- import { GraphNodeHandleBadge } from "./graph-node-handle-badge";
5
- import type { GraphNodeHandle } from "./graph-node-handle";
6
- import { GraphNodeStateIndicator } from "./graph-node-state-indicator";
7
- import {
8
- GRAPH_NODE_CONTENT_MIN_HEIGHT_CLASS,
9
- type GraphNodeState,
10
- graphNodeShellStateAttributes,
11
- graphNodeShellStateClassName,
12
- } from "./graph-node-state";
13
-
14
- export interface GraphNodeShellProps
15
- extends Omit<HTMLAttributes<HTMLElement>, "children"> {
16
- children: ReactNode;
17
- className?: string;
18
- handles: GraphNodeHandle[];
19
- nodeKind?: string;
20
- showStateIndicator?: boolean;
21
- state?: GraphNodeState;
22
- stateLabel?: string;
23
- }
24
-
25
- export function GraphNodeShell({
26
- children,
27
- className = "",
28
- handles,
29
- nodeKind,
30
- showStateIndicator = true,
31
- state = "default",
32
- stateLabel,
33
- ...articleProps
34
- }: GraphNodeShellProps) {
35
- const leftHandles = handles.filter((handle) => handle.side === "left");
36
- const rightHandles = handles.filter((handle) => handle.side === "right");
37
-
38
- return (
39
- <article
40
- className={cn(
41
- "relative flex h-full min-w-0 w-full overflow-visible rounded-lg border border-outline bg-surface text-on-surface",
42
- graphNodeShellStateClassName(state),
43
- className,
44
- )}
45
- data-graph-node-kind={nodeKind}
46
- {...graphNodeShellStateAttributes(state, stateLabel)}
47
- {...articleProps}
48
- >
49
- <NodeHandleRail handles={leftHandles} side="left" />
50
- <NodeHandleRail handles={rightHandles} side="right" />
51
- <div
52
- className={cn(
53
- "flex h-full min-w-0 w-full flex-col gap-1 py-3",
54
- showStateIndicator && GRAPH_NODE_CONTENT_MIN_HEIGHT_CLASS,
55
- leftHandles.length > 0 ? "pl-6 pr-3" : "px-3",
56
- rightHandles.length > 0 && leftHandles.length > 0
57
- ? "pr-6"
58
- : rightHandles.length > 0
59
- ? "pl-3 pr-6"
60
- : null,
61
- )}
62
- >
63
- {showStateIndicator ? (
64
- <GraphNodeStateIndicator state={state} stateLabel={stateLabel} />
65
- ) : null}
66
- {children}
67
- </div>
68
- </article>
69
- );
70
- }
71
-
72
- function NodeHandleRail({
73
- handles,
74
- side,
75
- }: {
76
- handles: GraphNodeHandle[];
77
- side: "left" | "right";
78
- }) {
79
- if (handles.length === 0) {
80
- return null;
81
- }
82
-
83
- return (
84
- <div
85
- className={cn(
86
- "pointer-events-none absolute inset-y-0 z-20 w-6",
87
- side === "left" ? "left-0" : "right-0",
88
- )}
89
- data-node-handle-rail={side}
90
- >
91
- {handles.map((handle, index) => (
92
- <div
93
- className={cn(
94
- "absolute top-0 flex -translate-y-1/2",
95
- side === "left"
96
- ? "left-0 -translate-x-1/2"
97
- : "right-0 translate-x-1/2",
98
- )}
99
- key={handle.id}
100
- style={{ top: handlePosition(index, handles.length) }}
101
- >
102
- <GraphNodeHandleBadge handle={handle} />
103
- </div>
104
- ))}
105
- </div>
106
- );
107
- }
108
-
109
- function handlePosition(index: number, count: number): string {
110
- return `${((index + 1) * 100) / (count + 1)}%`;
111
- }
@@ -1,47 +0,0 @@
1
- import { cn } from "../utilities/cn";
2
- import {
3
- defaultGraphNodeStateLabel,
4
- GRAPH_NODE_STATE_INDICATOR_HEIGHT_CLASS,
5
- type GraphNodeState,
6
- } from "./graph-node-state";
7
-
8
- export interface GraphNodeStateIndicatorProps {
9
- state: GraphNodeState;
10
- stateLabel?: string;
11
- }
12
-
13
- export function GraphNodeStateIndicator({
14
- state,
15
- stateLabel,
16
- }: GraphNodeStateIndicatorProps) {
17
- const label = stateLabel ?? defaultGraphNodeStateLabel(state);
18
- const showIndicator = state === "loading" || state === "error";
19
-
20
- return (
21
- <div
22
- aria-hidden={showIndicator ? undefined : true}
23
- className={cn(
24
- GRAPH_NODE_STATE_INDICATOR_HEIGHT_CLASS,
25
- "flex items-center gap-2 text-[0.65rem] font-semibold uppercase tracking-[0.08em]",
26
- state === "error" ? "text-on-error-container" : "text-on-surface-variant",
27
- !showIndicator && "invisible",
28
- )}
29
- data-graph-node-state-indicator={showIndicator ? state : undefined}
30
- >
31
- {state === "loading" ? (
32
- <>
33
- <span
34
- aria-hidden="true"
35
- className="inline-block h-4 w-4 shrink-0 animate-spin rounded-full border-2 border-outline border-t-primary"
36
- data-graph-node-loading-spinner="true"
37
- />
38
- <span>{label ?? "Loading"}</span>
39
- </>
40
- ) : state === "error" ? (
41
- <span role="alert">{label ?? "Error"}</span>
42
- ) : (
43
- <span aria-hidden="true">&nbsp;</span>
44
- )}
45
- </div>
46
- );
47
- }
@@ -1,111 +0,0 @@
1
- import { cn } from "../utilities/cn";
2
-
3
- export type GraphNodeState =
4
- | "default"
5
- | "selected"
6
- | "disabled"
7
- | "loading"
8
- | "error";
9
-
10
- export const GRAPH_NODE_CONTENT_MIN_HEIGHT_CLASS = "min-h-12";
11
-
12
- export const GRAPH_NODE_STATE_INDICATOR_HEIGHT_CLASS = "min-h-5";
13
-
14
- export function graphNodeShellStateClassName(state: GraphNodeState): string {
15
- switch (state) {
16
- case "selected":
17
- return cn(
18
- "border-2 border-primary bg-primary-container",
19
- "shadow-[0_0_0_1px_rgb(from_var(--color-primary)_r_g_b_/_0.28),0_0_0_4px_rgb(from_var(--color-primary)_r_g_b_/_0.08)]",
20
- );
21
- case "error":
22
- return cn(
23
- "border-2 border-dashed border-error bg-error-container",
24
- "shadow-[0_0_0_3px_var(--color-error-container)]",
25
- );
26
- case "disabled":
27
- return "border-outline-variant bg-surface-container text-on-surface";
28
- case "loading":
29
- return "border-outline bg-surface";
30
- default:
31
- return "";
32
- }
33
- }
34
-
35
- export function graphNodeButtonStateClassName(state: GraphNodeState): string {
36
- switch (state) {
37
- case "selected":
38
- return "ring-2 ring-primary/30";
39
- case "error":
40
- return "ring-2 ring-error/40";
41
- case "disabled":
42
- case "loading":
43
- return "cursor-not-allowed";
44
- default:
45
- return "";
46
- }
47
- }
48
-
49
- export function graphNodeShellStateAttributes(
50
- state: GraphNodeState,
51
- stateLabel?: string,
52
- ): {
53
- "aria-busy"?: boolean;
54
- "aria-disabled"?: boolean;
55
- "aria-invalid"?: boolean;
56
- "aria-label"?: string;
57
- "aria-selected"?: boolean;
58
- "data-graph-node-state"?: GraphNodeState;
59
- } {
60
- return {
61
- "aria-busy": state === "loading" ? true : undefined,
62
- "aria-disabled": state === "disabled" ? true : undefined,
63
- "aria-invalid": state === "error" ? true : undefined,
64
- "aria-label": stateLabel,
65
- "aria-selected": state === "selected" ? true : undefined,
66
- "data-graph-node-state": state === "default" ? undefined : state,
67
- };
68
- }
69
-
70
- export function graphNodeButtonStateAttributes(
71
- state: GraphNodeState,
72
- stateLabel?: string,
73
- ): {
74
- "aria-busy"?: boolean;
75
- "aria-disabled"?: boolean;
76
- "aria-invalid"?: boolean;
77
- "aria-label"?: string;
78
- "aria-pressed"?: boolean;
79
- "data-graph-node-state"?: GraphNodeState;
80
- } {
81
- return {
82
- "aria-busy": state === "loading" ? true : undefined,
83
- "aria-disabled": state === "disabled" ? true : undefined,
84
- "aria-invalid": state === "error" ? true : undefined,
85
- "aria-label": stateLabel,
86
- "aria-pressed": state === "selected" ? true : undefined,
87
- "data-graph-node-state": state === "default" ? undefined : state,
88
- };
89
- }
90
-
91
- export function graphNodeButtonIsDisabled(
92
- state: GraphNodeState,
93
- disabled?: boolean,
94
- ): boolean {
95
- return disabled === true || state === "disabled" || state === "loading";
96
- }
97
-
98
- export function defaultGraphNodeStateLabel(state: GraphNodeState): string | undefined {
99
- switch (state) {
100
- case "selected":
101
- return "Selected node";
102
- case "disabled":
103
- return "Disabled node";
104
- case "loading":
105
- return "Loading node";
106
- case "error":
107
- return "Error node";
108
- default:
109
- return undefined;
110
- }
111
- }
@@ -1,27 +0,0 @@
1
- import { forwardRef, type HTMLAttributes, type ReactNode } from "react";
2
-
3
- import { cn } from "../utilities/cn";
4
-
5
- export interface GraphViewportSurfaceProps extends HTMLAttributes<HTMLElement> {
6
- children: ReactNode;
7
- }
8
-
9
- export const GraphViewportSurface = forwardRef<
10
- HTMLElement,
11
- GraphViewportSurfaceProps
12
- >(function GraphViewportSurface({ children, className, role, ...props }, ref) {
13
- return (
14
- <section
15
- className={cn(
16
- "relative min-h-0 overflow-hidden rounded-3xl border shadow-none transition-colors",
17
- className,
18
- )}
19
- data-graph-viewport-surface="true"
20
- ref={ref}
21
- role={role ?? "region"}
22
- {...props}
23
- >
24
- {children}
25
- </section>
26
- );
27
- });