Skip to content

Commit

Permalink
refactor: use useImperativeHandle for SystemMapCanvas modes
Browse files Browse the repository at this point in the history
  • Loading branch information
cidhuang committed May 20, 2024
1 parent cf83be3 commit dd0a628
Show file tree
Hide file tree
Showing 6 changed files with 140 additions and 143 deletions.
86 changes: 57 additions & 29 deletions src/app/lib/useMode.ts
Original file line number Diff line number Diff line change
@@ -1,67 +1,95 @@
import { useState } from "react";
import { useState, MutableRefObject } from "react";
import { useTranslation } from "next-export-i18n";
import { ESystemMapCanvasMode } from "@/components/SystemMapCanvas/reducer/types";

export function useMode(): [
import { SystemMapCanvasRef } from "@/components/SystemMapCanvas/SystemMapCanvas";
import {
IStateCanvasModes,
ESystemMapCanvasModeDragFromVariableStock,
ESystemMapCanvasModeDoubleClickOnLink,
} from "@/components/SystemMapCanvas/reducer/types";

export function useMode(
canvasRef: MutableRefObject<SystemMapCanvasRef>,
canvasModes: IStateCanvasModes,
): [
string,
() => void,
string,
ESystemMapCanvasMode,
Array<{ label: string; mode: ESystemMapCanvasMode }>,
(mode: ESystemMapCanvasMode) => void,
Array<{
label: string;
mode: ESystemMapCanvasModeDragFromVariableStock;
handler: (mode: ESystemMapCanvasModeDragFromVariableStock) => void;
}>,
string,
boolean,
Array<{ label: string; mode: boolean }>,
(mode: boolean) => void,
Array<{
label: string;
mode: ESystemMapCanvasModeDoubleClickOnLink;
handler: (mode: ESystemMapCanvasModeDoubleClickOnLink) => void;
}>,
] {
const { t } = useTranslation();

const [modeDragFromVariable, setModeDragFromVariable] =
useState<ESystemMapCanvasMode>(ESystemMapCanvasMode.MoveVariableStock);
const [modeDoubleClickOnLink, setModeDoubleClickOnLink] =
useState<boolean>(false);
function handleDeleteItem(): void {
canvasRef.current?.setModes({
...canvasModes,
doubleClickToDeleteItem: !canvasModes.doubleClickToDeleteItem,
});
}

function handleModeDragFromVariableClick(mode1: ESystemMapCanvasMode) {
setModeDragFromVariable(mode1);
function handleModeDragFromVariableStockClick(
mode: ESystemMapCanvasModeDragFromVariableStock,
): void {
canvasRef.current?.setModes({
...canvasModes,
dragFromVariableStock: mode,
});
}
function handleModeDoubleClickOnLink(mode1: boolean) {
setModeDoubleClickOnLink(mode1);

function handleModeDoubleClickOnLink(
mode: ESystemMapCanvasModeDoubleClickOnLink,
): void {
canvasRef.current?.setModes({
...canvasModes,
doubleClickOnLink: mode,
});
}

const lableDeleteItem = t("Double click to delete Item");

const labelDragFromVariable = t("Drag from Variable");
const modesDragFromVariable = [
const labelDragFromVariableStock = t("Drag from Variable");
const modesDragFromVariableStock = [
{
label: t("Move Variable"),
mode: ESystemMapCanvasMode.MoveVariableStock,
mode: ESystemMapCanvasModeDragFromVariableStock.MoveVariableStock,
handler: handleModeDragFromVariableStockClick,
},
{
label: t("Add Link"),
mode: ESystemMapCanvasMode.AddLinkFlow,
mode: ESystemMapCanvasModeDragFromVariableStock.AddLinkFlow,
handler: handleModeDragFromVariableStockClick,
},
];

const labelDoubleClickOnLink = t("Double click on Link");
const modesDoubleClickOnLink = [
{
label: t("Toggle Relation"),
mode: false,
mode: ESystemMapCanvasModeDoubleClickOnLink.ToggleRelation,
handler: handleModeDoubleClickOnLink,
},
{
label: t("Toggle Direction"),
mode: true,
mode: ESystemMapCanvasModeDoubleClickOnLink.ToggleDirection,
handler: handleModeDoubleClickOnLink,
},
];

return [
lableDeleteItem,
labelDragFromVariable,
modeDragFromVariable,
modesDragFromVariable,
handleModeDragFromVariableClick,
handleDeleteItem,
labelDragFromVariableStock,
modesDragFromVariableStock,
labelDoubleClickOnLink,
modeDoubleClickOnLink,
modesDoubleClickOnLink,
handleModeDoubleClickOnLink,
];
}
50 changes: 28 additions & 22 deletions src/app/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,11 @@ import {
Flow,
IItems,
} from "@/components/SystemMapCanvas/lib/types";
import { IStateCanvasModes } from "@/components/SystemMapCanvas/reducer/types";
import {
ESystemMapCanvasModeDragFromVariableStock,
ESystemMapCanvasModeDoubleClickOnLink,
} from "@/components/SystemMapCanvas/reducer/types";

function HomeImp() {
const canvasRef = useRef<SystemMapCanvasRef>(null);
Expand All @@ -38,7 +43,12 @@ function HomeImp() {
flows: new Array<Flow>(),
});

const [deleteItem, setDeleteItem] = useState<boolean>(false);
const [canvasModes, setCanvasModes] = useState<IStateCanvasModes>({
dragFromVariableStock:
ESystemMapCanvasModeDragFromVariableStock.MoveVariableStock,
doubleClickOnLink: ESystemMapCanvasModeDoubleClickOnLink.ToggleRelation,
doubleClickToDeleteItem: false,
});

const [handlerCanUndoChanged, handlerCanRedoChanged, menus] = useMenu(
canvasRef,
Expand All @@ -48,22 +58,19 @@ function HomeImp() {

const [
lableDeleteItem,
labelDragFromVariable,
modeDragFromVariable,
modesDragFromVariable,
handleModeDragFromVariableClick,
handleDeleteItem,
labelDragFromVariableStock,
modesDragFromVariableStock,
labelDoubleClickOnLink,
modeDoubleClickOnLink,
modesDoubleClickOnLink,
handleModeDoubleClickOnLink,
] = useMode();
] = useMode(canvasRef, canvasModes);

function handleItemsChange(items: IItems): void {
setItems(items);
function handleModesChange(modes: IStateCanvasModes) {
setCanvasModes(modes);
}

function handleDeleteItem(): void {
setDeleteItem(!deleteItem);
function handleItemsChange(items: IItems): void {
setItems(items);
}

return (
Expand All @@ -73,19 +80,19 @@ function HomeImp() {
<div className="flex">
<Checkbox
label={lableDeleteItem}
checked={deleteItem}
checked={canvasModes.doubleClickToDeleteItem === true}
onChange={handleDeleteItem}
/>
<div className="flex border">
<label className="m-4">{labelDragFromVariable + ": "}</label>
{modesDragFromVariable.map((item, i) => {
<label className="m-4">{labelDragFromVariableStock + ": "}</label>
{modesDragFromVariableStock.map((item, i) => {
return (
<Radio
key={"mode-" + i}
label={item.label}
value={item.mode}
checked={modeDragFromVariable === item.mode}
onClick={handleModeDragFromVariableClick}
checked={canvasModes.dragFromVariableStock === item.mode}
onClick={() => item.handler(item.mode)}
/>
);
})}
Expand All @@ -98,8 +105,8 @@ function HomeImp() {
key={"mode-" + i}
label={item.label}
value={item.mode}
checked={modeDoubleClickOnLink === item.mode}
onClick={handleModeDoubleClickOnLink}
checked={canvasModes.doubleClickOnLink === item.mode}
onClick={() => item.handler(item.mode)}
/>
);
})}
Expand All @@ -108,9 +115,8 @@ function HomeImp() {
</Suspense>
<SystemMapCanvas
ref={canvasRef}
mode={modeDragFromVariable}
toggleLinkDirection={modeDoubleClickOnLink}
deleteItem={deleteItem}
modes={canvasModes}
onModesChange={handleModesChange}
onCanUndoChanged={handlerCanUndoChanged}
onCanRedoChanged={handlerCanRedoChanged}
items={items0}
Expand Down
40 changes: 15 additions & 25 deletions src/components/SystemMapCanvas/SystemMapCanvas.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import useUndo from "use-undo";

import { IItems, isVariable } from "@/components/SystemMapCanvas/lib/types";
import { reducer } from "./reducer/reducer";
import { EStateCanvas, ESystemMapCanvasMode } from "./reducer/types";
import { EStateCanvas, IStateCanvasModes } from "./reducer/types";
import { useInteraction } from "./hooks/useInteraction";

import { InputTextArea } from "./InputTextArea";
Expand All @@ -25,12 +25,12 @@ export type SystemMapCanvasRef = {
zoomOut: () => void;
undo: () => void;
redo: () => void;
setModes: (modes: IStateCanvasModes) => void;
} | null;

interface SystemMapCanvasProps {
mode: ESystemMapCanvasMode;
toggleLinkDirection: boolean;
deleteItem: boolean;
modes: IStateCanvasModes;
onModesChange: (modes: IStateCanvasModes) => void;
onCanUndoChanged: (canUndo: boolean) => void;
onCanRedoChanged: (canRedo: boolean) => void;
items: IItems;
Expand All @@ -42,9 +42,8 @@ export const SystemMapCanvas = forwardRef<
SystemMapCanvasProps
>(function SystemMapCanvas(
{
mode,
toggleLinkDirection,
deleteItem,
modes,
onModesChange,
onCanUndoChanged,
onCanRedoChanged,
items,
Expand All @@ -58,13 +57,11 @@ export const SystemMapCanvas = forwardRef<
const [editingText, setEditingText] = useState<string>("");

const [state, dispatch] = useReducer(reducer, {
mode: mode,
modes: modes,
state: EStateCanvas.Idle,
items: items,
cmdUndoAdd: 0,
cmdUndoReset: 0,
toggleLinkDirection: toggleLinkDirection,
deleteItem: deleteItem,
});

const [
Expand Down Expand Up @@ -115,10 +112,6 @@ export const SystemMapCanvas = forwardRef<
setInputVisible,
] = useInput(app, editingText, setEditingText);

useEffect(() => {
dispatch({ type: "Mode", mode: mode });
}, [mode]);

useImperativeHandle(
ref,
() => {
Expand All @@ -135,9 +128,12 @@ export const SystemMapCanvas = forwardRef<
redo() {
redoItems();
},
setModes(modes: IStateCanvasModes) {
dispatch({ type: "Modes", modes: modes });
},
};
},
[handleZoomIn, handleZoomOut, undoItems, redoItems],
[handleZoomIn, handleZoomOut, undoItems, redoItems, state.modes],
);

useEffect(() => {
Expand Down Expand Up @@ -166,22 +162,16 @@ export const SystemMapCanvas = forwardRef<
}, [state.cmdUndoAdd]);

useEffect(() => {
dispatch({ type: "ToggleLinkDirection", enabled: toggleLinkDirection });

// eslint-disable-next-line react-hooks/exhaustive-deps
}, [toggleLinkDirection]);

useEffect(() => {
dispatch({ type: "DeleteItem", enabled: deleteItem });
dispatch({ type: "NewMap", items: items });

// eslint-disable-next-line react-hooks/exhaustive-deps
}, [deleteItem]);
}, [items]);

useEffect(() => {
dispatch({ type: "NewMap", items: items });
onModesChange(state.modes);

// eslint-disable-next-line react-hooks/exhaustive-deps
}, [items]);
}, [state.modes]);

useEffect(() => {
resetItems(state.items);
Expand Down
Loading

0 comments on commit dd0a628

Please sign in to comment.