Random behavour when using selectedData to apply crossfiltering

Hi, All

I have been trying to add cross-filtering to dynamic graphs that share a base data frame. I got it to work but there is some underlining behaviour that happens. When I go to lasso and the callback applies the selected points it selects more than what was actually selected.

@app.callback([Output({'type': 'cross_filter_select', 'index': MATCH}, 'data')],
              [Input({'type': 'graph-display', 'index': MATCH}, 'selectedData')],
              [State({'type': 'tile-link', 'index': ALL}, 'className')],
              prevent_initial_call=True)
def do_stuff(selected_data, link_state):
    changed_id = [p['prop_id'] for p in dash.callback_context.triggered][0]
    if changed_id == '.':
        raise PreventUpdate
    tile = int(search(r'\d+', changed_id).group())
    point = None
    trace = None
    if selected_data is not None:
        if link_state[tile] == 'fa fa-link' and len(selected_data['points']) != 0:
            point = [p['pointNumber'] for p in selected_data['points']]
            trace = [p['customdata'] for p in selected_data['points']]


    selected = [{'point': point}, {'trace': trace}]
    filter = selected

    return [filter]


for x in range(4):
    @app.callback([Output({'type': 'graph-display', 'index': x}, 'figure')],
                  [Input({'type': 'cross_filter_select', 'index': ALL}, 'data')],
                  [State({'type': 'graph-display', 'index': x}, 'figure')],
                  prevent_initial_call=True)
    def cross_filter(selected_data, fig):
        changed_id = [p['prop_id'] for p in dash.callback_context.triggered][0]

        # callback context hasnt changed
        if changed_id == '.':
            raise PreventUpdate
        tile = int(search(r'\d+', changed_id).group())

        if selected_data[tile][0]['point'] is not None:
            trace = []
            # assigns the selected point to the corresponding curve number to build the selected point lists
            for selected_points in selected_data[tile][1]['trace']:
                for index in range(len(fig['data'])):
                    if selected_points in fig['data'][index]['customdata']:
                        trace.append(index)
                        break

            select = []
            print(trace)
            # makes the traces opaque to be able to distinguish the points that are selected on te graph
            for index in range(len(fig['data'])):
                fig['data'][index]['selectedpoints'] = {}
                select.append([])
            for count, index in enumerate(trace):
                select[index].append(selected_data[tile][0]['point'][count])
                # if selected_data[tile][0]['point'] in index:
            # applies the selected points to the correct trace
            for count, index in enumerate(select):
                if len(index) != 0:
                    fig['data'][count]['selectedpoints'] = index
            print(select)


        else:
            for index in range(len(fig['data'])):
                fig['data'][index]['selectedpoints'] = None
        return [fig]

I use the customdata to check to see if the the data is the same in the other graph. It may have to do with the callbacks and the amount that I have.
Thanks

Hi @DerrickChow ! Why are you using a loop in the second callback instead os specifying 'index':MATCH or 'index':ALL?

Hi @celia,

The reasoning is that I am dynamically creating graphs, so sometimes I will have one graph but can have up to 4 graphs created at one time. This is the way I got around the dynamic callbacks without throwing an error when an id has not been created.