Select to view content in your preferred language

Render nested content in widget view

495
1
08-10-2020 10:33 AM
BenRomlein
Frequent Contributor

Using 4.X api and TypeScript to create a custom widget. I'm having trouble rendering nested lists. My render method renders a list of layer groups, and lists of layers within each group:

  render() {
    const groupList = this.viewModel.layerGroups.map((layerGroupLayerGroupi=> 
        <div key={i} data-layer={layerGroup} onclick={this._expand} id={layerGroup.group}> {layerGroup.group}
             <div id={layerGroup.group + "_container"} class={CSS.layerGroup + ' ' + CSS.layerGroup__hidden}>
               {layerGroup.layers.map(layer => <div data-layer = {layer} class={layer.status==="active" ? CSS.layerActiveCSS.layerInactive} onclick={this._toggle}>{layer.name}</div>)}
             </div>
        </div>);
    return (<div>{groupList}</div>);
  }

The problem I have is that this renders the layer containers as children of the group element. Because of this, any time a click event happens on a layer (to call _toggle), an event happens on the group (inadvertently calling _expand), since the layer is within the group. How can I add elements to my VDOM so that they are appended, rather than added as children?

In other words, with nested lists like:

groups = [ { name: group1, layers: [layer1, layer2, layer3] } { name: group2, layers: [layer4, layer5] } ... ],
how can I get a structure like this:

<div id='group'>{group name}</div>
<div id='container'>
  <div> Layer Item </div>

     ...
</div>

instead of what I'm currently getting:

<div id='group'> {group name}
   <div id='container'>

      <div> Layer Item </div>

         ...
   </div>

</div>

0 Kudos
1 Reply
BenRomlein
Frequent Contributor

I ended up breaking up my original render method into two functions, one to render the groups and one to render the layers. I added a renderable property (openGroup) to my viewModel, then changed the _expand method to set that property to whichever group was clicked. Then I added a condition to the render method that will call whichever function it needs (render groups, or render layers) depending on the value of the openGroup property.

0 Kudos