🐛 fix(parameterComponent): add missing import for Button component

✨ feat(parameterComponent): add functionality to set filter edge when handle is clicked
🐛 fix(parameterComponent): fix type error in renderTooltips function
🐛 fix(GenericNode): add missing import for Button component
✨ feat(GenericNode): add functionality to reset filter edge when node title is clicked
🐛 fix(typesContext): add missing setFilterEdge and getFilterEdge to initial value
🐛 fix(ExtraSidebar): add missing import for cloneDeep function
✨ feat(ExtraSidebar): add functionality to reset filter edge and search input when blur event occurs
✨ feat(ExtraSidebar): add functionality to filter data based on filter edge
🐛 fix(ExtraSidebar): fix handleSearchInput function to reset filter data when search input is empty
🐛 fix(ExtraSidebar): fix handleBlur function to reset filter data, filter edge, and search input when filter edge is empty
🐛 fix(ExtraSidebar): fix useEffect to reset filter data, filter edge, and search input when filter edge is empty
🐛 fix(ExtraSidebar): fix useEffect to filter data based on filter edge when filter edge is not empty
This commit is contained in:
Cristhian Zanforlin Lousa 2023-09-18 19:25:52 -03:00
commit 8dd9cb29b5
5 changed files with 113 additions and 28 deletions

View file

@ -19,6 +19,7 @@ import IntComponent from "../../../../components/intComponent";
import PromptAreaComponent from "../../../../components/promptComponent"; import PromptAreaComponent from "../../../../components/promptComponent";
import TextAreaComponent from "../../../../components/textAreaComponent"; import TextAreaComponent from "../../../../components/textAreaComponent";
import ToggleShadComponent from "../../../../components/toggleShadComponent"; import ToggleShadComponent from "../../../../components/toggleShadComponent";
import { Button } from "../../../../components/ui/button";
import { TOOLTIP_EMPTY } from "../../../../constants/constants"; import { TOOLTIP_EMPTY } from "../../../../constants/constants";
import { TabsContext } from "../../../../contexts/tabsContext"; import { TabsContext } from "../../../../contexts/tabsContext";
import { typesContext } from "../../../../contexts/typesContext"; import { typesContext } from "../../../../contexts/typesContext";
@ -67,7 +68,9 @@ export default function ParameterComponent({
updateNodeInternals(data.id); updateNodeInternals(data.id);
}, [data.id, position, updateNodeInternals]); }, [data.id, position, updateNodeInternals]);
const { reactFlowInstance } = useContext(typesContext); const groupedEdge = useRef(null);
const { reactFlowInstance, setFilterEdge } = useContext(typesContext);
let disabled = let disabled =
reactFlowInstance?.getEdges().some((edge) => edge.targetHandle === id) ?? reactFlowInstance?.getEdges().some((edge) => edge.targetHandle === id) ??
false; false;
@ -108,7 +111,8 @@ export default function ParameterComponent({
}, [info]); }, [info]);
function renderTooltips() { function renderTooltips() {
let groupedObj = groupByFamily(myData, tooltipTitle!, left, flow!); let groupedObj: any = groupByFamily(myData, tooltipTitle!, left, flow!);
groupedEdge.current = groupedObj;
if (groupedObj && groupedObj.length > 0) { if (groupedObj && groupedObj.length > 0) {
//@ts-ignore //@ts-ignore
@ -218,29 +222,37 @@ export default function ParameterComponent({
!optionalHandle ? ( !optionalHandle ? (
<></> <></>
) : ( ) : (
<ShadTooltip <Button className="h-7 truncate bg-muted p-0 text-sm font-normal text-black hover:bg-muted">
styleClasses={"tooltip-fixed-width custom-scroll nowheel"} <div className="flex">
delayDuration={0} <ShadTooltip
content={refHtml.current} styleClasses={"tooltip-fixed-width custom-scroll nowheel"}
side={left ? "left" : "right"} delayDuration={0}
> content={refHtml.current}
<Handle side={left ? "left" : "right"}
type={left ? "target" : "source"} >
position={left ? Position.Left : Position.Right} <Handle
id={id} type={left ? "target" : "source"}
isValidConnection={(connection) => position={left ? Position.Left : Position.Right}
isValidConnection(connection, reactFlowInstance!) id={id}
} isValidConnection={(connection) =>
className={classNames( isValidConnection(connection, reactFlowInstance!)
left ? "-ml-0.5 " : "-mr-0.5 ", }
"h-3 w-3 rounded-full border-2 bg-background" className={classNames(
)} left ? "-ml-0.5 " : "-mr-0.5 ",
style={{ "h-3 w-3 rounded-full border-2 bg-background"
borderColor: color, )}
top: position, style={{
}} borderColor: color,
></Handle> top: position,
</ShadTooltip> }}
onClick={() => {
setFilterEdge(groupedEdge.current);
}}
></Handle>
</ShadTooltip>
</div>
<span className="text-status-red">{required ? " *" : ""}</span>
</Button>
)} )}
{left === true && {left === true &&

View file

@ -25,7 +25,8 @@ export default function GenericNode({
const [data, setData] = useState(olddata); const [data, setData] = useState(olddata);
const { updateFlow, flows, tabId } = useContext(TabsContext); const { updateFlow, flows, tabId } = useContext(TabsContext);
const updateNodeInternals = useUpdateNodeInternals(); const updateNodeInternals = useUpdateNodeInternals();
const { types, deleteNode, reactFlowInstance } = useContext(typesContext); const { types, deleteNode, reactFlowInstance, setFilterEdge, getFilterEdge } =
useContext(typesContext);
const name = nodeIconsLucide[data.type] ? data.type : types[data.type]; const name = nodeIconsLucide[data.type] ? data.type : types[data.type];
const [validationStatus, setValidationStatus] = const [validationStatus, setValidationStatus] =
useState<validationStatusType | null>(null); useState<validationStatusType | null>(null);
@ -84,7 +85,12 @@ export default function GenericNode({
<div className="beta-badge-content">BETA</div> <div className="beta-badge-content">BETA</div>
</div> </div>
)} )}
<div className="generic-node-div-title"> <div
className="generic-node-div-title"
onClick={() => {
setFilterEdge([]);
}}
>
<div className="generic-node-title-arrangement"> <div className="generic-node-title-arrangement">
<IconComponent <IconComponent
name={name} name={name}

View file

@ -26,6 +26,8 @@ const initialValue: typesContextType = {
setData: () => {}, setData: () => {},
setFetchError: () => {}, setFetchError: () => {},
fetchError: false, fetchError: false,
setFilterEdge: (filter) => {},
getFilterEdge: [],
}; };
export const typesContext = createContext<typesContextType>(initialValue); export const typesContext = createContext<typesContextType>(initialValue);
@ -39,6 +41,7 @@ export function TypesProvider({ children }: { children: ReactNode }) {
const [fetchError, setFetchError] = useState(false); const [fetchError, setFetchError] = useState(false);
const { setLoading } = useContext(alertContext); const { setLoading } = useContext(alertContext);
const { getAuthentication } = useContext(AuthContext); const { getAuthentication } = useContext(AuthContext);
const [getFilterEdge, setFilterEdge] = useState([]);
useEffect(() => { useEffect(() => {
// If the user is authenticated, fetch the types. This code is important to check if the user is auth because of the execution order of the useEffect hooks. // If the user is authenticated, fetch the types. This code is important to check if the user is auth because of the execution order of the useEffect hooks.
@ -113,6 +116,8 @@ export function TypesProvider({ children }: { children: ReactNode }) {
setData, setData,
fetchError, fetchError,
setFetchError, setFetchError,
setFilterEdge,
getFilterEdge,
}} }}
> >
{children} {children}

View file

@ -1,3 +1,4 @@
import { cloneDeep } from "lodash";
import { useContext, useEffect, useState } from "react"; import { useContext, useEffect, useState } from "react";
import ShadTooltip from "../../../../components/ShadTooltipComponent"; import ShadTooltip from "../../../../components/ShadTooltipComponent";
import IconComponent from "../../../../components/genericIconComponent"; import IconComponent from "../../../../components/genericIconComponent";
@ -18,7 +19,8 @@ import { classNames } from "../../../../utils/utils";
import DisclosureComponent from "../DisclosureComponent"; import DisclosureComponent from "../DisclosureComponent";
export default function ExtraSidebar(): JSX.Element { export default function ExtraSidebar(): JSX.Element {
const { data, templates } = useContext(typesContext); const { data, templates, getFilterEdge, setFilterEdge } =
useContext(typesContext);
const { flows, tabId, uploadFlow, tabsState, saveFlow, isBuilt } = const { flows, tabId, uploadFlow, tabsState, saveFlow, isBuilt } =
useContext(TabsContext); useContext(TabsContext);
const { setSuccessData, setErrorData } = useContext(alertContext); const { setSuccessData, setErrorData } = useContext(alertContext);
@ -42,6 +44,10 @@ export default function ExtraSidebar(): JSX.Element {
// Handle showing components after use search input // Handle showing components after use search input
function handleSearchInput(e: string) { function handleSearchInput(e: string) {
if (e === "") {
setFilterData(data);
return;
}
setFilterData((_) => { setFilterData((_) => {
let ret = {}; let ret = {};
Object.keys(data).forEach((d: keyof APIObjectType, i) => { Object.keys(data).forEach((d: keyof APIObjectType, i) => {
@ -69,6 +75,59 @@ export default function ExtraSidebar(): JSX.Element {
setErrorData({ title: " Components with errors: ", list: errors }); setErrorData({ title: " Components with errors: ", list: errors });
}, []); }, []);
function handleBlur() {
if (getFilterEdge.length > 0) {
setFilterData(data);
setFilterEdge([]);
setSearch("");
}
}
useEffect(() => {
if (getFilterEdge.length === 0) {
setFilterData(data);
setFilterEdge([]);
setSearch("");
}
}, [getFilterEdge]);
useEffect(() => {
if (getFilterEdge?.length > 0) {
setFilterData((_) => {
let dataClone = cloneDeep(data);
let ret = {};
Object.keys(dataClone).forEach((d: keyof APIObjectType, i) => {
ret[d] = {};
if (getFilterEdge.some((x) => x.family === d)) {
ret[d] = dataClone[d];
const filtered = getFilterEdge
.filter((x) => x.family === d)
.pop()
.type.split(",");
for (let i = 0; i < filtered.length; i++) {
filtered[i] = filtered[i].trimStart();
}
if (filtered.some((x) => x !== "")) {
let keys = Object.keys(dataClone[d]).filter((nd) =>
filtered.includes(nd)
);
Object.keys(dataClone[d]).forEach((element) => {
if (!keys.includes(element)) {
delete ret[d][element];
}
});
}
}
});
setSearch("search");
return ret;
});
}
}, [getFilterEdge]);
return ( return (
<div className="side-bar-arrangement"> <div className="side-bar-arrangement">
<div className="side-bar-buttons-arrangement"> <div className="side-bar-buttons-arrangement">
@ -141,6 +200,7 @@ export default function ExtraSidebar(): JSX.Element {
<Separator /> <Separator />
<div className="side-bar-search-div-placement"> <div className="side-bar-search-div-placement">
<Input <Input
onFocusCapture={() => handleBlur()}
type="text" type="text"
name="search" name="search"
id="search" id="search"

View file

@ -18,6 +18,8 @@ export type typesContextType = {
setData: (newState: {}) => void; setData: (newState: {}) => void;
fetchError: boolean; fetchError: boolean;
setFetchError: (newState: boolean) => void; setFetchError: (newState: boolean) => void;
setFilterEdge: (newState) => void;
getFilterEdge: any[];
}; };
export type alertContextType = { export type alertContextType = {