Skip to content

Commit

Permalink
fix(ui): Navigation arrow logic node history added.
Browse files Browse the repository at this point in the history
  • Loading branch information
billcookie committed Dec 19, 2024
1 parent 5fd42be commit d4ebb12
Show file tree
Hide file tree
Showing 4 changed files with 128 additions and 11 deletions.
95 changes: 95 additions & 0 deletions ui/src/features/Editor/components/Canvas/useNodeHistory.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,95 @@
import { useState, useEffect, useCallback } from "react";

import { Node } from "@flow/types";

type HistoryState = {
nodes: Node[];
currentIndex: number;
};

type NavigateNodeHistoryProps = {
direction: "prev" | "next";
history: { nodes: Node[]; currentIndex: number };
setHistory: React.Dispatch<
React.SetStateAction<{ nodes: Node[]; currentIndex: number }>
>;
setSelectedNode: (node: Node) => void;
};

type Props = {
selected?: Node;
nodes: Node[];
};

const handleNavigateNodeHistory = ({
direction,
history,
setHistory,
setSelectedNode,
}: NavigateNodeHistoryProps) => {
const newIndex =
direction === "prev" ? history.currentIndex - 1 : history.currentIndex + 1;

if (newIndex >= 0 && newIndex < history.nodes.length) {
setHistory((prev) => ({
...prev,
currentIndex: newIndex,
}));
setSelectedNode(history.nodes[newIndex]);
}
};

export const useNodeHistory = ({ selected, nodes }: Props) => {
const [history, setHistory] = useState<HistoryState>({
nodes: [],
currentIndex: -1,
});
const [selectedNode, setSelectedNode] = useState<Node | undefined>(selected);

useEffect(() => {
if (selected) {
setHistory((prev) => {
// Clean the history to only include valid nodes that are in the current list
const validNodeIds = new Set(nodes.map((node) => node.id));
const validHistory = prev.nodes.filter((node) =>
validNodeIds.has(node.id),
);

// We only want to add if the node is different and not the same as the last one
if (validHistory[prev.currentIndex]?.id !== selected.id) {
const newNodes = [
...validHistory.slice(0, prev.currentIndex + 1),
selected,
];
return {
nodes: newNodes,
currentIndex: newNodes.length - 1,
};
}
return { ...prev, nodes: validHistory };
});
setSelectedNode(selected);
}
}, [selected, nodes]);

const memoizedNodeHistory = useCallback(
(direction: "prev" | "next") => {
handleNavigateNodeHistory({
direction,
history,
setHistory,
setSelectedNode,
});
},
[history],
);

return {
selectedNode,
handleNavigateNodeHistory: memoizedNodeHistory,
nodeHistoryPosition: {
canGoBack: history.currentIndex > 0,
canGoForward: history.currentIndex < history.nodes.length - 1,
},
};
};
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,11 @@ type Props = {
nodeType: string;
nodeParameters?: unknown; // TODO: define type
onSubmit: (nodeId: string, data: any) => void;
onNavigateNodeHistory: (direction: "prev" | "next") => void;
nodeHistoryPosition: {
canGoBack: boolean;
canGoForward: boolean;
};
};

const actionButtonClasses = "border h-[25px]";
Expand All @@ -22,13 +27,15 @@ const ParamEditor: React.FC<Props> = ({
// nodeType,
// nodeParameters = [{ id: "param1", name: "Param 1", value: "Value 1", type: "string"}],
onSubmit,
onNavigateNodeHistory,
nodeHistoryPosition,
}) => {
const t = useT();

const { useGetActionById } = useAction();
const { action } = useGetActionById(nodeMeta.officialName);

const handleSubmit = (data: any) => onSubmit(nodeId, data);

return (
<div>
<div className="mb-3 flex justify-between gap-4">
Expand All @@ -37,11 +44,15 @@ const ParamEditor: React.FC<Props> = ({
className={actionButtonClasses}
icon={<ArrowLeft />}
tooltipText="Previous selection"
onClick={() => onNavigateNodeHistory("prev")}
disabled={!nodeHistoryPosition.canGoBack}
/>
<IconButton
className={actionButtonClasses}
icon={<ArrowRight />}
tooltipText="Next selection"
onClick={() => onNavigateNodeHistory("next")}
disabled={!nodeHistoryPosition.canGoForward}
/>
</div>
</div>
Expand All @@ -52,7 +63,6 @@ const ParamEditor: React.FC<Props> = ({
{/* <TabsTrigger className="flex-1" value="data">
{t("Node data")}
</TabsTrigger> */}

<TabsContent value="params">
<div className="rounded border bg-card p-3">
{!action?.parameter && <p>{t("No Parameters Available")}</p>}
Expand Down
29 changes: 20 additions & 9 deletions ui/src/features/Editor/components/RightPanel/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -4,17 +4,26 @@ import { memo, useCallback } from "react";
import { IconButton } from "@flow/components";
import { Node } from "@flow/types";

import { useNodeHistory } from "../Canvas/useNodeHistory";

import { ParamEditor } from "./components";

type Props = {
selected?: Node;
onParamsSubmit: (nodeId: string, data: any) => void;
nodes: Node[];
};

const RightPanel: React.FC<Props> = ({ selected, onParamsSubmit }) => {
const RightPanel: React.FC<Props> = ({ selected, onParamsSubmit, nodes }) => {
const { selectedNode, handleNavigateNodeHistory, nodeHistoryPosition } =
useNodeHistory({
selected,
nodes,
});

// This is a little hacky, but it works. We need to dispatch a click event to the react-flow__pane
// to unlock the node when user wants to close the right panel. - @KaWaite
const handleClose = useCallback(() => {
const handlePanelClose = useCallback(() => {
// react-flow__pane is the classname of the div inside react-flow that has the click event
// https://github.com/xyflow/xyflow/blob/71db83761c245493d44e74311e10cc6465bf8387/packages/react/src/container/Pane/index.tsx#L249
const paneElement = document.getElementsByClassName("react-flow__pane")[0];
Expand All @@ -26,9 +35,9 @@ const RightPanel: React.FC<Props> = ({ selected, onParamsSubmit }) => {
const handleParamsSubmit = useCallback(
async (nodeId: string, data: any) => {
await Promise.resolve(onParamsSubmit(nodeId, data));
handleClose();
handlePanelClose();
},
[onParamsSubmit, handleClose],
[onParamsSubmit, handlePanelClose],
);

return (
Expand All @@ -45,7 +54,7 @@ const RightPanel: React.FC<Props> = ({ selected, onParamsSubmit }) => {
<IconButton
className="relative before:absolute before:inset-y-0 before:right-0 before:z-[-1] before:bg-success before:content-['']"
icon={<X className="size-[30px]" weight="thin" />}
onClick={handleClose}
onClick={handlePanelClose}
/>
</div>
</div>
Expand All @@ -59,12 +68,14 @@ const RightPanel: React.FC<Props> = ({ selected, onParamsSubmit }) => {
transitionTimingFunction: "cubic-bezier(0.4, 0, 0.2, 1)",
}}>
<div className="size-full py-4 pl-4 pr-2">
{selected && (
{selectedNode && (
<ParamEditor
nodeId={selected.id}
nodeMeta={selected.data}
nodeType={selected.type}
nodeId={selectedNode.id}
nodeMeta={selectedNode.data}
nodeType={selectedNode.type}
onSubmit={handleParamsSubmit}
onNavigateNodeHistory={handleNavigateNodeHistory}
nodeHistoryPosition={nodeHistoryPosition}
/>
)}
</div>
Expand Down
1 change: 1 addition & 0 deletions ui/src/features/Editor/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,7 @@ export default function Editor({
<RightPanel
selected={locallyLockedNode}
onParamsSubmit={handleNodeParamsUpdate}
nodes={nodes}
/>
</div>
</div>
Expand Down

0 comments on commit d4ebb12

Please sign in to comment.