diff --git a/src/frontend/src/CustomNodes/GenericNode/components/parameterComponent/index.tsx b/src/frontend/src/CustomNodes/GenericNode/components/parameterComponent/index.tsx index a72190ded..88d9e41da 100644 --- a/src/frontend/src/CustomNodes/GenericNode/components/parameterComponent/index.tsx +++ b/src/frontend/src/CustomNodes/GenericNode/components/parameterComponent/index.tsx @@ -1,3 +1,4 @@ +import { cloneDeep } from "lodash"; import { Info } from "lucide-react"; import React, { useContext, useEffect, useRef, useState } from "react"; import { Handle, Position, useUpdateNodeInternals } from "reactflow"; @@ -31,6 +32,7 @@ export default function ParameterComponent({ left, id, data, + setData, tooltipTitle, title, color, @@ -62,10 +64,13 @@ export default function ParameterComponent({ const { reactFlowInstance } = useContext(typesContext); let disabled = reactFlowInstance?.getEdges().some((e) => e.targetHandle === id) ?? false; - const [myData, setMyData] = useState(useContext(typesContext).data); + + const { data: myData } = useContext(typesContext); const handleOnNewValue = (newValue: any) => { - data.node.template[name].value = newValue; + let newData = cloneDeep(data); + newData.node.template[name].value = newValue; + setData(newData); // Set state to pending setTabsState((prev) => { return { diff --git a/src/frontend/src/CustomNodes/GenericNode/index.tsx b/src/frontend/src/CustomNodes/GenericNode/index.tsx index ec1976ac7..c47b9f5c1 100644 --- a/src/frontend/src/CustomNodes/GenericNode/index.tsx +++ b/src/frontend/src/CustomNodes/GenericNode/index.tsx @@ -17,15 +17,16 @@ import { import ParameterComponent from "./components/parameterComponent"; export default function GenericNode({ - data, + data: olddata, selected, }: { data: NodeDataType; selected: boolean; }) { + const [data, setData] = useState(olddata); const { setErrorData } = useContext(alertContext); const showError = useRef(true); - const { types, deleteNode } = useContext(typesContext); + const { types, deleteNode, reactFlowInstance } = useContext(typesContext); // any to avoid type conflict const Icon: any = nodeIconsLucide[data.type] || nodeIconsLucide[types[data.type]]; @@ -33,6 +34,10 @@ export default function GenericNode({ // State for outline color const { sseData, isBuilding } = useSSE(); const refHtml = useRef(null); + useEffect(() => { + console.log("atualizou", data); + olddata = data; + }, [data, reactFlowInstance]); // useEffect(() => { // if (reactFlowInstance) { @@ -63,12 +68,12 @@ export default function GenericNode({ deleteNode(data.id); return; } - useEffect(() => {}, [data.node.template]); return ( <> @@ -184,6 +189,7 @@ export default function GenericNode({ !data.node.template[t].advanced ? ( */} 0 diff --git a/src/frontend/src/components/floatComponent/index.tsx b/src/frontend/src/components/floatComponent/index.tsx index d3b39f61a..d8c4302c2 100644 --- a/src/frontend/src/components/floatComponent/index.tsx +++ b/src/frontend/src/components/floatComponent/index.tsx @@ -1,4 +1,4 @@ -import { useContext, useEffect, useState } from "react"; +import { useContext, useEffect } from "react"; import { TabsContext } from "../../contexts/tabsContext"; import { FloatComponentType } from "../../types/components"; @@ -9,7 +9,6 @@ export default function FloatComponent({ disabled, editNode = false, }: FloatComponentType) { - const [myValue, setMyValue] = useState(value ?? ""); const { setDisableCopyPaste } = useContext(TabsContext); const step = 0.1; @@ -18,7 +17,6 @@ export default function FloatComponent({ useEffect(() => { if (disabled) { - setMyValue(""); onChange(""); } }, [disabled, onChange]); @@ -44,7 +42,7 @@ export default function FloatComponent({ } }} max={max} - value={myValue} + value={value ?? ""} className={ editNode ? "input-edit-node" @@ -54,7 +52,6 @@ export default function FloatComponent({ editNode ? "Number 0 to 1" : "Type a number from zero to one" } onChange={(e) => { - setMyValue(e.target.value); onChange(e.target.value); }} /> diff --git a/src/frontend/src/components/inputComponent/index.tsx b/src/frontend/src/components/inputComponent/index.tsx index fe982310e..dea121efb 100644 --- a/src/frontend/src/components/inputComponent/index.tsx +++ b/src/frontend/src/components/inputComponent/index.tsx @@ -11,13 +11,11 @@ export default function InputComponent({ password, editNode = false, }: InputComponentType) { - const [myValue, setMyValue] = useState(value ?? ""); const [pwdVisible, setPwdVisible] = useState(false); const { setDisableCopyPaste } = useContext(TabsContext); useEffect(() => { if (disabled) { - setMyValue(""); onChange(""); } }, [disabled, onChange]); @@ -25,7 +23,7 @@ export default function InputComponent({ return (
{ if (disableCopyPaste) setDisableCopyPaste(true); }} @@ -34,16 +32,13 @@ export default function InputComponent({ }} className={classNames( disabled ? " input-disable " : "", - password && !pwdVisible && myValue !== "" - ? " text-clip password " - : "", + password && !pwdVisible && value !== "" ? " text-clip password " : "", editNode ? " input-edit-node " : " input-primary ", password && editNode ? "pr-8" : "", password && !editNode ? "pr-10" : "" )} placeholder={password && editNode ? "Key" : "Type something..."} onChange={(e) => { - setMyValue(e.target.value); onChange(e.target.value); }} /> diff --git a/src/frontend/src/components/inputListComponent/index.tsx b/src/frontend/src/components/inputListComponent/index.tsx index d1e6a8fec..445822902 100644 --- a/src/frontend/src/components/inputListComponent/index.tsx +++ b/src/frontend/src/components/inputListComponent/index.tsx @@ -13,6 +13,12 @@ export default function InputListComponent({ }: InputListComponentType) { const [inputList, setInputList] = useState(value ?? [""]); + useEffect(() => { + if (value) { + setInputList(value); + } + }, [value]); + useEffect(() => { if (disabled) { setInputList([""]); diff --git a/src/frontend/src/components/intComponent/index.tsx b/src/frontend/src/components/intComponent/index.tsx index 92b9c6ee1..68daf8117 100644 --- a/src/frontend/src/components/intComponent/index.tsx +++ b/src/frontend/src/components/intComponent/index.tsx @@ -1,4 +1,4 @@ -import { useContext, useEffect, useState } from "react"; +import { useContext, useEffect } from "react"; import { TabsContext } from "../../contexts/tabsContext"; import { FloatComponentType } from "../../types/components"; @@ -9,13 +9,11 @@ export default function IntComponent({ disabled, editNode = false, }: FloatComponentType) { - const [myValue, setMyValue] = useState(value ?? ""); const { setDisableCopyPaste } = useContext(TabsContext); const min = 0; useEffect(() => { if (disabled) { - setMyValue(""); onChange(""); } }, [disabled, onChange]); @@ -60,7 +58,7 @@ export default function IntComponent({ e.target.value = min.toString(); } }} - value={myValue} + value={value ?? ""} className={ editNode ? " input-edit-node " @@ -68,7 +66,6 @@ export default function IntComponent({ } placeholder={editNode ? "Integer number" : "Type an integer number"} onChange={(e) => { - setMyValue(e.target.value); onChange(e.target.value); }} /> diff --git a/src/frontend/src/components/textAreaComponent/index.tsx b/src/frontend/src/components/textAreaComponent/index.tsx index 78f92c64a..10e725905 100644 --- a/src/frontend/src/components/textAreaComponent/index.tsx +++ b/src/frontend/src/components/textAreaComponent/index.tsx @@ -1,4 +1,4 @@ -import { useContext, useEffect, useState } from "react"; +import { useContext, useEffect } from "react"; import GenericModal from "../../modals/genericModal"; import { TextAreaComponentType } from "../../types/components"; @@ -11,12 +11,10 @@ export default function TextAreaComponent({ disabled, editNode = false, }: TextAreaComponentType) { - const [myValue, setMyValue] = useState(value); const { setDisableCopyPaste } = useContext(TabsContext); useEffect(() => { if (disabled) { - setMyValue(""); onChange(""); } }, [disabled, onChange]); @@ -25,7 +23,7 @@ export default function TextAreaComponent({
{ setDisableCopyPaste(true); }} @@ -40,7 +38,6 @@ export default function TextAreaComponent({ } placeholder={"Type something..."} onChange={(e) => { - setMyValue(e.target.value); onChange(e.target.value); }} /> @@ -49,9 +46,8 @@ export default function TextAreaComponent({ type={"text"} buttonText="Finishing Editing" modalTitle="Edit Text" - value={myValue} + value={value} setValue={(t: string) => { - setMyValue(t); onChange(t); }} > diff --git a/src/frontend/src/modals/EditNodeModal/index.tsx b/src/frontend/src/modals/EditNodeModal/index.tsx index 952a1ed1b..f5cf095c9 100644 --- a/src/frontend/src/modals/EditNodeModal/index.tsx +++ b/src/frontend/src/modals/EditNodeModal/index.tsx @@ -1,5 +1,6 @@ +import { cloneDeep } from "lodash"; import { Variable } from "lucide-react"; -import { ReactNode, forwardRef, useContext, useState } from "react"; +import { ReactNode, forwardRef, useContext, useEffect, useState } from "react"; import CodeAreaComponent from "../../components/codeAreaComponent"; import Dropdown from "../../components/dropdownComponent"; import FloatComponent from "../../components/floatComponent"; @@ -30,17 +31,19 @@ const EditNodeModal = forwardRef( ( { data, + setData, nodeLength, children, }: { data: NodeDataType; + setData: (data: NodeDataType) => void; nodeLength: number; children: ReactNode; }, ref ) => { const [modalOpen, setModalOpen] = useState(false); - const [nodeValue, setNodeValue] = useState(null); + const [myData, setMyData] = useState(data); const { setTabsState, tabId } = useContext(TabsContext); const { reactFlowInstance } = useContext(typesContext); @@ -49,30 +52,31 @@ const EditNodeModal = forwardRef( false; function changeAdvanced(n) { - data.node.template[n].advanced = !data.node.template[n].advanced; - setNodeValue(!nodeValue); + setMyData((old) => { + let newData = cloneDeep(old); + newData.node.template[n].advanced = !newData.node.template[n].advanced; + return newData; + }); } const handleOnNewValue = (newValue: any, name) => { - data.node.template[name].value = newValue; - // Set state to pending - setTabsState((prev) => { - return { - ...prev, - [tabId]: { - ...prev[tabId], - isPending: true, - }, - }; + setMyData((old) => { + let newData = cloneDeep(old); + newData.node.template[name].value = newValue; + return newData; }); }; + useEffect(() => { + setMyData(data); // reset data to what it is on node when opening modal + }, [modalOpen]); + return ( {children} - - {data.type} - ID: {data.id} + + {myData.type} + ID: {myData.id}
@@ -102,49 +106,51 @@ const EditNodeModal = forwardRef( - {Object.keys(data.node.template) + {Object.keys(myData.node.template) .filter( (t) => t.charAt(0) !== "_" && - data.node.template[t].show && - (data.node.template[t].type === "str" || - data.node.template[t].type === "bool" || - data.node.template[t].type === "float" || - data.node.template[t].type === "code" || - data.node.template[t].type === "prompt" || - data.node.template[t].type === "file" || - data.node.template[t].type === "int") + myData.node.template[t].show && + (myData.node.template[t].type === "str" || + myData.node.template[t].type === "bool" || + myData.node.template[t].type === "float" || + myData.node.template[t].type === "code" || + myData.node.template[t].type === "prompt" || + myData.node.template[t].type === "file" || + myData.node.template[t].type === "int") ) .map((n, i) => ( - {data.node.template[n].name - ? data.node.template[n].name - : data.node.template[n].display_name} + {myData.node.template[n].name + ? myData.node.template[n].name + : myData.node.template[n].display_name} - {data.node.template[n].type === "str" && - !data.node.template[n].options ? ( + {myData.node.template[n].type === "str" && + !myData.node.template[n].options ? (
- {data.node.template[n].list ? ( + {myData.node.template[n].list ? ( { handleOnNewValue(t, n); }} /> - ) : data.node.template[n].multiline ? ( + ) : myData.node.template[n].multiline ? ( { handleOnNewValue(t, n); }} @@ -154,107 +160,112 @@ const EditNodeModal = forwardRef( editNode={true} disabled={disabled} password={ - data.node.template[n].password ?? false + myData.node.template[n].password ?? + false + } + value={ + myData.node.template[n].value ?? "" } - value={data.node.template[n].value ?? ""} onChange={(t) => { handleOnNewValue(t, n); }} /> )}
- ) : data.node.template[n].type === "bool" ? ( + ) : myData.node.template[n].type === "bool" ? (
{" "} { handleOnNewValue(t, n); }} size="small" />
- ) : data.node.template[n].type === "float" ? ( + ) : myData.node.template[n].type === "float" ? (
{ handleOnNewValue(t, n); }} />
- ) : data.node.template[n].type === "str" && - data.node.template[n].options ? ( + ) : myData.node.template[n].type === "str" && + myData.node.template[n].options ? (
handleOnNewValue(t, n)} value={ - data.node.template[n].value ?? + myData.node.template[n].value ?? "Choose an option" } >
- ) : data.node.template[n].type === "int" ? ( + ) : myData.node.template[n].type === "int" ? (
{ handleOnNewValue(t, n); }} />
- ) : data.node.template[n].type === "file" ? ( + ) : myData.node.template[n].type === "file" ? (
{ handleOnNewValue(t, n); }} - fileTypes={data.node.template[n].fileTypes} - suffixes={data.node.template[n].suffixes} + fileTypes={ + myData.node.template[n].fileTypes + } + suffixes={myData.node.template[n].suffixes} onFileChange={(t: string) => { handleOnNewValue(t, n); }} >
- ) : data.node.template[n].type === "prompt" ? ( + ) : myData.node.template[n].type === "prompt" ? (
{ - data.node = nodeClass; + myData.node = nodeClass; }} - value={data.node.template[n].value ?? ""} + value={myData.node.template[n].value ?? ""} onChange={(t: string) => { handleOnNewValue(t, n); }} />
- ) : data.node.template[n].type === "code" ? ( + ) : myData.node.template[n].type === "code" ? (
{ handleOnNewValue(t, n); }} />
- ) : data.node.template[n].type === "Any" ? ( + ) : myData.node.template[n].type === "Any" ? ( "-" ) : (
@@ -263,7 +274,7 @@ const EditNodeModal = forwardRef(
changeAdvanced(n)} disabled={disabled} size="small" @@ -284,6 +295,16 @@ const EditNodeModal = forwardRef(