diff options
| author | Sam Nystrom <sam@samnystrom.dev> | 2024-03-08 08:09:18 +0000 |
|---|---|---|
| committer | Sam Nystrom <sam@samnystrom.dev> | 2024-03-09 02:05:58 -0500 |
| commit | 9fb6fa12590609a4cd25d2e212166c61e1c23580 (patch) | |
| tree | 94f494fb4a0a841a8d17b3215227b7a7d77a3685 /src | |
| parent | 5d06d2359e8ad50f7a61ecd1787a0ad558329964 (diff) | |
Add basic toolbar
Diffstat (limited to 'src')
| -rw-r--r-- | src/AddNodeMenu.tsx | 21 | ||||
| -rw-r--r-- | src/NodeEditor.tsx | 12 | ||||
| -rw-r--r-- | src/Toolbar.module.css | 76 | ||||
| -rw-r--r-- | src/Toolbar.tsx | 30 |
4 files changed, 116 insertions, 23 deletions
diff --git a/src/AddNodeMenu.tsx b/src/AddNodeMenu.tsx deleted file mode 100644 index 197f56d..0000000 --- a/src/AddNodeMenu.tsx +++ /dev/null @@ -1,21 +0,0 @@ -import { useId } from 'preact/hooks'; -import { NodeInfo } from './node.tsx'; - -export interface AddNodeMenuProps { - nodes: Record<string, NodeInfo>; - onClick?: (NodeInfo) => void; -} - -export const AddNodeMenu = ({ nodes, onClick = _ => {} }: AddNodeMenuProps) => { - const id = useId(); - return ( - <> - <menu id={id} popover> - {Object.entries(nodes).map(([name, node]) => ( - <li><button onClick={() => onClick(node)}>{name}</button></li> - ))} - </menu> - <button popoverTarget={id}>Add</button> - </> - ); -};
\ No newline at end of file diff --git a/src/NodeEditor.tsx b/src/NodeEditor.tsx index 0340a49..17e7c27 100644 --- a/src/NodeEditor.tsx +++ b/src/NodeEditor.tsx @@ -3,7 +3,7 @@ import { signal, computed, batch, useSignal, useComputed, Signal } from '@preact import { nodeRegistry } from './nodes'; import { SocketHandlers, SocketHandler, NodeInfo } from './node.tsx'; import { InputSocket } from './dataflow.ts'; -import { AddNodeMenu } from './AddNodeMenu.tsx'; +import { Toolbar } from './Toolbar.tsx'; import styles from './NodeEditor.module.css'; export const nodeFactory = () => { @@ -221,9 +221,16 @@ export const NodeEditor = () => { scale.value *= 1 + delta; }); + const onNodeAdded = (node: NodeInfo) => { + nodes.value = nodes.value.concat(instantiateNode(100, 100, node)); + }; + return ( <> - <AddNodeMenu nodes={nodeRegistry} onClick={node => nodes.value = nodes.value.concat(instantiateNode(100, 100, node))} /> + <header> + <Toolbar nodes={nodeRegistry} onNodeAdded={onNodeAdded} /> + </header> + <main> <svg width="100vw" height="100vh" ref={svgRef} onMouseDown={onBgMouseDown} onWheel={onBgWheel}> <pattern id="bg-grid-major" @@ -251,6 +258,7 @@ export const NodeEditor = () => { </SocketHandlers.Provider> </g> </svg> + </main> </> ); };
\ No newline at end of file diff --git a/src/Toolbar.module.css b/src/Toolbar.module.css new file mode 100644 index 0000000..edea713 --- /dev/null +++ b/src/Toolbar.module.css @@ -0,0 +1,76 @@ +.toolbar { + background-color: var(--surface); + border-bottom: 1px solid var(--overlay); + width: 100%; + margin: 0; + padding: 0; + display: flex; + flex-direction: row; + align-items: center; + justify-content: space-between; + + > * { + flex-grow: 1; + display: flex; + justify-content: center; + } + :first-child, :last-child { flex-basis: 0 } + :first-child { justify-content: flex-start } + :last-child { justify-content: flex-end } + + > menu { + margin: 0; + padding: 0; + list-style: none; + display: flex; + flex-direction: row; + } + + h1 { + font-size: 1.5rem; + font-weight: normal; + margin: 0; + } + + button { + background-color: transparent; + border: none; + outline: none; + padding: 1rem; + color: var(--text); + font-size: 1em; + :hover { background-color: var(--overlay) } + } + + path { + fill: var(--text); + } +} + +.addMenu:popover-open { + background-color: var(--surface); + list-style: none; + border: none; + position: absolute; + inset: unset; + width: auto; + height: auto; + left: 140px; + top: 52px; + margin: 0; + padding: 0; + display: flex; + flex-direction: column; + --shadow-color: 0deg 0% 0%; + box-shadow: + 0.1px 0.4px 0.6px hsl(var(--shadow-color) / 0.04), + 0.5px 3.3px 4.8px -0.2px hsl(var(--shadow-color) / 0.15), + 1.4px 10.2px 14.7px -0.5px hsl(var(--shadow-color) / 0.27); + + button { + padding: 4px; + width: 100%; + text-align: left; + &:hover { background-color: var(--overlay) } + } +}
\ No newline at end of file diff --git a/src/Toolbar.tsx b/src/Toolbar.tsx new file mode 100644 index 0000000..62c79fe --- /dev/null +++ b/src/Toolbar.tsx @@ -0,0 +1,30 @@ +import { useId } from 'preact/hooks'; +import { NodeInfo } from './node.tsx'; +import styles from './Toolbar.module.css'; + +export interface ToolbarProps { + nodes: Record<string, NodeInfo>; + onNodeAdded?: (NodeInfo) => void; +} + +export const Toolbar = ({ nodes, onNodeAdded = _ => {} }: ToolbarProps) => { + const id = useId(); + return ( + <div class={styles.toolbar}> + <menu> + <li><button>Edit</button></li> + <li><button>Select</button></li> + <li> + <menu id={id} class={styles.addMenu} popover="auto"> + {Object.entries(nodes).map(([name, node]) => ( + <li><button onClick={() => onNodeAdded(node)}>{name}</button></li> + ))} + </menu> + <button popoverTarget={id}>Add</button> + </li> + </menu> + <h1>My Project</h1> + <div></div> + </div> + ); +};
\ No newline at end of file |
