agile-ts / agile

🌌 Global State and Logic Library for JavaScript/Typescript applications

Home Page:https://agile-ts.org

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

Update Agile subscriptions to a UI-Component without unmounting the Component.

bennoinbeta opened this issue Β· comments

commented

πŸ› Bug report / Feature Request

πŸ€– Current Behavior

In some cases, we need to dynamically update the Agile subscriptions to a React-Component,
although the Component hasn't been unmounted.
This is the case in the below code example:

const Property = ({
  label,
  path,
  id,
}: {
  label: string;
  path: string;
  id: number | string;
}) => {
  const ELEMENT = core.ui.ELEMENTS.getItem(id);
  const element = useProxy(ELEMENT, { componentId: 'Property' });

   return (
    // doesn't matter
  );
};

The Property-Component does display some properties (e.g. width, height, x, y)
of the current selected Element (for example, a Box) in the Canvas.
The problem is now, when we select another Element in the Canvas, the prop id of the Property-Compoent
does update and thus the ELEMENT (Agile Sub Instance).
However, the Property-Component doesn't unmount and thus not remount.
-> The Agile Sub Instance subscriptions to the Property-Compoent doesn't get updated.
This is due to the fact that the subscriptions to the React-Component are made in a useEffect() with an empty deps array,
which is only called when the React-Component got mounted.

useEffect(() => {
 // Subscribe Agile Sub Instance to the React-Component
return () => {
   // Unsubscribing Agile Sub Instance from the React-Component
}
}, [])

🎯 Expected behavior

Is the expected behavior!

πŸ’‘ Suggested solution(s)

To solve this issue, we should provide a deps option in the configuration object of useAgile().
-> The user can manually define when the Agile Sub Instance subscriptions should be updated
although the React-Component hasn't unmounted.

So to fix the above issue in the Property-Component, we have to make the following changes:

const Property = ({
  label,
  path,
  id,
}: {
  label: string;
  path: string;
  id: number | string;
}) => {
  const ELEMENT = core.ui.ELEMENTS.getItem(id);
  const element = useProxy(ELEMENT, { componentId: 'Property', deps: [id] }); // <-

  return (
    // doesn't matter
  );
};

Now, the Agile Sub Instance subscriptions (ELEMENT) are updated whenever the id prop changes.

βž• Additional notes

https://reactjs.org/docs/hooks-reference.html#conditionally-firing-an-effect

πŸ’» Your environment

doesn't matter