# Sync react state with Vtk.js renderer / scene state

**URL:** https://discourse.vtk.org/t/sync-react-state-with-vtk-js-renderer-scene-state/7751
**Category:** Web
**Created:** [February 1, 2022, 5:06pm UTC](https://discourse.vtk.org/t/sync-react-state-with-vtk-js-renderer-scene-state/7751 "2022-02-01T17:06:12Z")
**Posts on this page:** 4
**Page:** 1

<div class="post-metadata">

### Author: ![Nicolas\_Schmidt](https://discourse.vtk.org/user_avatar/discourse.vtk.org/nicolas_schmidt/32/3681_2.png) [@Nicolas\_Schmidt](https://discourse.vtk.org/u/Nicolas_Schmidt)
#### Post date: [February 1, 2022, 5:06pm UTC](https://discourse.vtk.org/t/sync-react-state-with-vtk-js-renderer-scene-state/7751/1 "2022-02-01T17:06:12Z")

</div>

**What’s the right way to derive the state from the vtk.js renderer (or other source) so that it can be properly reflected in the frontend using React?**

I’m using vtk.js in React, and have created an app with controls that can adjust the camera and properties of actors.

I’m managing the state of the vtk.js scene with a custom object, but would prefer to derive the state directly from the vtk.js scene itself.

I see that a lot of objects including the `vtkRenderer` have a function `getState()` which seems appropriate. Unfortunately when I call `renderer.getState()` I get a `Maximum call stack size exceeded` error. Similarly when I call `actor.getState()` I get an error related to reading the `isA` property. I also tried calling `renderer.get()` / `actor.get()` prior to calling `getState()` to ‘reify’ some of those object values, but that didn’t help.

For a little more context, my custom state object is an array of `Actor` objects shown below.

 ![Screen Shot 2022-02-01 at 11.58.04 AM](https://discourse.vtk.org/uploads/default/original/2X/c/cca4ca1d06c7824d7e2a6c89e023a819f5c0545a.png)

I’m using [useReducer](https://reactjs.org/docs/hooks-reference.html#usereducer) (like redux) to manage the state, which provides an opportunity to change the state of the vtk.js scene and then call a function that will return the new state. That looks like this:

 ![Screen Shot 2022-02-01 at 12.05.12 PM](https://discourse.vtk.org/uploads/default/original/2X/6/651cbf5d84185dd680afdb014025a2f0eb216723.png)

Any advice anyone can provide would be greatly appreciated! Thanks in advance 🙏

---

<div class="post-metadata">

### Author: ![Sebastien\_Jourdain](https://discourse.vtk.org/user_avatar/discourse.vtk.org/sebastien_jourdain/32/100_2.png) [@Sebastien\_Jourdain](https://discourse.vtk.org/u/Sebastien_Jourdain)
#### Post date: [February 1, 2022, 5:21pm UTC](https://discourse.vtk.org/t/sync-react-state-with-vtk-js-renderer-scene-state/7751/2 "2022-02-01T17:21:24Z")

</div>

Normally `getState()` should work if you ask it on a non cyclic data structure. It is possible that a bug sneak in. Anyhow, the idea behind is the following which might not exactly match your need.

```auto
const serializableJSObj = objA.getState();
const objB = vtk(serializableJSObj);
// objB is technically a clone of objA 

```

You may need to create a object walker and pick which properties matter to you with something like that

```auto
const saveState = obj.get('propA', 'propB', ...)
// later
obj.set(saveState);

```

HTH

```auto

```

---

<div class="post-metadata">

### Author: ![Nicolas\_Schmidt](https://discourse.vtk.org/user_avatar/discourse.vtk.org/nicolas_schmidt/32/3681_2.png) [@Nicolas\_Schmidt](https://discourse.vtk.org/u/Nicolas_Schmidt)
#### Post date: [February 1, 2022, 6:16pm UTC](https://discourse.vtk.org/t/sync-react-state-with-vtk-js-renderer-scene-state/7751/3 "2022-02-01T18:16:52Z")

</div>

Thanks for the quick reply @Sebastien_Jourdain I’ll give it a try and let you know. If I can pin down a bug with `.getState()` I’ll open an issue.

---

<div class="post-metadata">

### Author: ![Nicolas\_Schmidt](https://discourse.vtk.org/user_avatar/discourse.vtk.org/nicolas_schmidt/32/3681_2.png) [@Nicolas\_Schmidt](https://discourse.vtk.org/u/Nicolas_Schmidt)
#### Post date: [February 7, 2022, 3:24pm UTC](https://discourse.vtk.org/t/sync-react-state-with-vtk-js-renderer-scene-state/7751/4 "2022-02-07T15:24:43Z")

</div>

@Sebastien_Jourdain I played with this a bit last week and it seems to be a good solution. I’ll post it here in case you can give any feedback or it will be useful to others.

This function should be able to take and vtk.js object and return a js object configured by the `fields` argument.

```auto
interface Field {
  key: string, // field name on return object
  path?: string, // override get field path if key is for display purposes
  fields?: Field[] // array of subfields
}

// recursive "object walker" configured by fields object
const deriveVTKState = (fields: Field[], object: any) => {
  if (!object) return

  return fields.reduce((p, f, i, arr) => {
    // can't do f.get(f.path) because some fields don't exist
    // until functions are called like object.getActors()
    let call = f.path ? `get${f.path.charAt(0).toUpperCase() + f.path.slice(1)}` : `get${f.key.charAt(0).toUpperCase() + f.key.slice(1)}`
    let subObject
    try {
      subObject = object[call]()
    } catch {
      return { ...p, [f.key]: undefined }
    }

    if (typeof subObject === undefined) return { ...p, [f.key]: undefined }

    if (f.fields) {
      // returns true if subObject.length === 0
      if (typeof subObject.length !== 'undefined') {
        return {
          ...p, [f.key]: subObject.map(val => {
            return deriveVTKState(f.fields, val)
          })
        }
      } else return { ...p, [f.key]: deriveVTKState(f.fields, subObject) }
    }
    return { ...p, [f.key]: subObject }
  }, {} as { [index: string]: any })
}

```
