// Copyright 2024, Command Line Inc. // SPDX-License-Identifier: Apache-2.0 import type { Meta, StoryObj } from "@storybook/react"; import { TileLayout } from "./TileLayout.jsx"; import { atom } from "jotai"; import { useState } from "react"; import { newLayoutNode } from "./layoutNode.js"; import "./tilelayout.stories.less"; import { LayoutNode, LayoutTreeActionType, LayoutTreeInsertNodeAction, LayoutTreeState, NodeModel, WritableLayoutTreeStateAtom, } from "./types.js"; const renderTestData = (data: string) => <div>{data}</div>; function newLayoutTreeStateAtom(node: LayoutNode): WritableLayoutTreeStateAtom { return atom({ rootNode: node } as LayoutTreeState); } function renderContent(nodeModel: NodeModel) { return ( <div ref={nodeModel.dragHandleRef} className="test-content" style={{ width: "100%", height: "100%" }}> {renderTestData(nodeModel.blockId)} </div> ); } const meta = { title: "TileLayout", args: { layoutTreeStateAtom: newLayoutTreeStateAtom( newLayoutNode(undefined, undefined, undefined, { blockId: "Hello world!", }) ), contents: { renderContent, renderPreview: renderContent, tabId: "", }, }, component: TileLayout, // This component will have an automatically generated Autodocs entry: https://storybook.js.org/docs/writing-docs/autodocs tags: ["autodocs"], } satisfies Meta<typeof TileLayout>; export default meta; type Story = StoryObj<typeof meta>; export const Basic: Story = { args: { layoutTreeStateAtom: newLayoutTreeStateAtom( newLayoutNode(undefined, undefined, undefined, { blockId: "Hello world!" }) ), }, }; export const More: Story = { args: { layoutTreeStateAtom: newLayoutTreeStateAtom<TestData>( newLayoutNode(undefined, undefined, [ newLayoutNode(undefined, undefined, undefined, { name: "Hello world1!" }), newLayoutNode(undefined, undefined, undefined, { name: "Hello world2!" }), newLayoutNode(undefined, undefined, [ newLayoutNode(undefined, undefined, undefined, { name: "Hello world3!" }), newLayoutNode(undefined, undefined, undefined, { name: "Hello world4!" }), ]), ]) ), }, }; const evenMoreRootNode = newLayoutNode<TestData>(undefined, undefined, [ newLayoutNode(undefined, undefined, undefined, { name: "Hello world1!" }), newLayoutNode(undefined, undefined, [ newLayoutNode(undefined, undefined, undefined, { name: "Hello world2!" }), newLayoutNode(undefined, undefined, undefined, { name: "Hello world3!" }), ]), newLayoutNode(undefined, undefined, [ newLayoutNode(undefined, undefined, undefined, { name: "Hello world4!" }), newLayoutNode(undefined, undefined, undefined, { name: "Hello world5!" }), newLayoutNode(undefined, undefined, [ newLayoutNode(undefined, undefined, undefined, { name: "Hello world6!" }), newLayoutNode(undefined, undefined, undefined, { name: "Hello world7!" }), newLayoutNode(undefined, undefined, undefined, { name: "Hello world8!" }), ]), ]), ]); export const EvenMore: Story = { args: { layoutTreeStateAtom: newLayoutTreeStateAtom<TestData>(evenMoreRootNode), }, }; const addNodeAtom = newLayoutTreeStateAtom(evenMoreRootNode); export const AddNode: Story = { render: () => { const [, dispatch] = useLayoutTreeStateReducerAtom(addNodeAtom); const [numAddedNodes, setNumAddedNodes] = useState(0); const dispatchAddNode = () => { const newNode = newLayoutNode(undefined, undefined, undefined, { name: "New Node" + numAddedNodes, }); const insertNodeAction: LayoutTreeInsertNodeAction<TestData> = { type: LayoutTreeActionType.InsertNode, node: newNode, }; dispatch(insertNodeAction); setNumAddedNodes(numAddedNodes + 1); }; return ( <div style={{ display: "flex", flexDirection: "column", width: "100%", height: "100%" }}> <div> <button onClick={dispatchAddNode}>Add node</button> </div> <TileLayout layoutTreeStateAtom={addNodeAtom as WritableLayoutTreeStateAtom<TestData>} contents={meta.args.contents} /> </div> ); }, };