Can lasso select work with a go.Scattermap in a go.FigureWidget?

Hello,

In a Shiny for Python app, I have a go.Scattermap wrapped in a go.FigureWidget, and with a function on_map_select() registered as callback to mapwidget.data[0]. There is only one trace in the figure.

The callback is being called OK for single point selections as well as box selections.
However, for lasso selections the callback is not invoked. No crash or error.

In the Shiny UI, both box and lasso selections appear to behave similarly, highlighting the markers within the selected area.

Bug or missing feature? Anyone experienced something similar?

Plotly 6.2.0, Python 3.12, Shiny 1.2.1, Windows 11.
Plotly 6.1.1 and ScatterMapBox also tried, same behaviour.
The map has around 140 markers (have seen posts where this number was relevant).

pseudo-code:

mapfigure = InitMap(CatchmentDF) (function returning a Figure)
mapwidget = go.FigureWidget(mapfigure)
mapwidget.data[0].on_selection(on_map_select)

def on_map_select(trace, points, selector): Non-reactive callback function

Update: The callback is actually called even for a Lasso select if only one point is selected, but not if two or more points are within the lasso.

Working minimal example:

from shiny import ui, App
from shinywidgets import render_plotly, output_widget
import plotly.graph_objects as go
import geopandas as gpd
import random

app_ui = ui.page_fluid(output_widget("MapPlot", height="600px"))    # Shiny UI with one item MapPlot

def server(input, output, session):
    
    @render_plotly
    def MapPlot():  # Function to render a Plotly map with random points
        points = gpd.points_from_xy(x=[random.uniform(5, 12) for _ in range(25)],
                                    y=[random.uniform(59, 63) for _ in range(25)])
        gdf = gpd.GeoDataFrame(geometry=points, crs=4326)
        mapfigure = go.Figure(go.Scattermap(lat = gdf.geometry.y, lon = gdf.geometry.x))
        mapfigure.update_geos(projection_type="mercator")
        mapfigure = mapfigure.update_layout(map_style="open-street-map", 
                                            clickmode='event+select',
                                            map_zoom = 3.9,
                                            map_center = {"lat": 61, "lon": 18})
        mapwidget = go.FigureWidget(mapfigure)
        mapwidget.data[0].on_selection(on_map_select)
        return mapwidget

    def on_map_select(trace, points, selector): # Callback responding to map selections
        if len(points.point_inds) == 1:
            print(f"on_map_select() detects a single selected point with index {points.point_inds[0]}")
        else:
            print(f"on_map_select() detects {len(points.point_inds)} selected points, selector is {selector}")

app = App(app_ui, server)

New update: It appears that the lasso selector works OK, and that the error is that str(selector) fails when selector is a plotly.callbacks.LassoSelector’. Within the Shiny framework, that error caused the callback to abort silently.
To reproduce the error (plotly 6.3.1):

(venv) PS C:\Devel\PyProj\PlotlyLassoTest> python
Python 3.12.0 (tags/v3.12.0:0fb18b0, Oct 2 2023, 13:03:39) [MSC v.1935 64 bit (AMD64)] on win32
Type “help”, “copyright”, “credits” or “license” for more information.
Ctrl click to launch VS Code Native REPL

from plotly import callbacks

box_selector = callbacks.BoxSelector()
type(box_selector)
<class ‘plotly.callbacks.BoxSelector’>box_selector
BoxSelector(xrange=None,
yrange=None)

lasso_selector = callbacks.LassoSelector()
type(lasso_selector)
<class ‘plotly.callbacks.LassoSelector’>
lasso_selector
Traceback (most recent call last):
File “”, line 1, in
File “c:\Users\sak\AppData\Roaming\Code\User\workspaceStorage\483d815d6720e46e72b3e1eba8bd7f7e\ms-python.python\pythonrc.py”, line 24, in my_displayhook
self.original_displayhook(value)
File “C:\Devel\PyProj\PlotlyLassoTest\venv\Lib\site-packages\plotly\callbacks.py”, line 257, in repr
xs=_list_repr_elided(self.xs, indent=len(“LassoSelector(xs=”)),
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File “C:\Devel\PyProj\PlotlyLassoTest\venv\Lib\site-packages\plotly\utils.py”, line 30, in _list_repr_elided
raise ValueError(“Invalid value of type: %s” % type(v))
ValueError: Invalid value of type: <class ‘NoneType’>

So, in the minimal working example in comment #1 above, it is the “selector is {selector}” in the last diagnostic print that causes on_map_select() to abort silently if the selector is a LassoSelector. It works as expected for a BoxSelector, or if selector is None, as it is for a single-click selection. The special case of Lasso when selecting only a single point was an artefact of not trying to print the selector when len(points.point_inds) == 1.