holoviz / panel

Panel: The powerful data exploration & web app framework for Python
https://panel.holoviz.org
BSD 3-Clause "New" or "Revised" License
4.68k stars 508 forks source link

PathLayer in DeckGL pane does not render if all paths are of the same length. #3953

Open edwardransome opened 1 year ago

edwardransome commented 1 year ago

ALL software version info

Win10, Python 3.10.2, Firefox 104.0.2

panel 0.13.0a37 pandas 1.4.1 pydeck 0.7.1

Description of expected behavior and the observed behavior

Expected: Panel can wrap the pydeck deck and display it without issue. Observed: Wrapping a pydeck deck containing a PathLayer with all paths having the same number of points causes an assertion error. Adding a single point to the first path will remove the error.

Complete, minimal, self-contained example code that reproduces the issue

import pandas as pd
import pydeck as pdk
import panel as pn

data_dict = {
    'name':['a','b','c','d'],
    'coordinates':[
        [[6.1,46.1],[6.1,46.2],[6.2,46.2]],
        [[6.3,46.3],[6.3,46.4],[6.4,46.4]],
        [[6.01,46.01],[6.01,46.02],[6.02,46.02]],
        [[6.03,46.03],[6.03, 46.04],[6.04,46.04]]
    ]
}

df = pd.DataFrame(data_dict)

layer = pdk.Layer(
    type="PathLayer",
    data=df,
    width_scale=20,
    get_path='coordinates',
    get_width=5,
    width_min_pixels=2,
    visible=True
)

INITIAL_VIEW_STATE = pdk.ViewState(
    latitude=46.1,
    longitude=6.1,
    zoom=13,
    max_zoom=24,
    bearing=0,
)

deck = pdk.Deck(
            #map_provider="mapbox",
            map_style='mapbox://styles/mapbox/light-v10',
            initial_view_state=INITIAL_VIEW_STATE,
            api_keys={'mapbox':'pk.eyJ1IjoicGFuZWxvcmciLCJhIjoiY2s1enA3ejhyMWhmZjNobjM1NXhtbWRrMyJ9.B_frQsAVepGIe-HiOJeqvQ'},
            layers=[layer],
            tooltip=True
        )

# Visible lines when not using panel
deck.to_html('example.html')

# luma.gl assertion error seen in console, no lines
deck_pane = pn.pane.DeckGL(deck, sizing_mode='stretch_both', margin=0)
deck_pane.show()

Stack traceback and/or browser JavaScript console output

Error: initialization of PathLayer({id: '14551e20-79cd-4f1a-93d2-0c496e3a4bcf'}): luma.gl: assertion failed.
    r http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:1
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    e http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
dist.min.js:11:369955
    onError http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    value http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11
    e http://localhost:55021/static/extensions/panel/bundled/deckglplot/npm/deck.gl@8.6.7/dist.min.js:11

Screenshots or screencasts of the bug in action

philippjfr commented 1 year ago

Thanks for reporting, very odd indeed. I'll take a look.

edwardransome commented 1 year ago

An update, a similar problem also occurs when using an [R,G,B] array column to define colours.

import pydeck as pdk
import panel as pn

data_dict = {
    'name':['a','b','c','d'],
    'coordinates':[
        [[6.1,46.1],[6.2,46.2]],
        [[6.3,46.3],[6.3,46.4],[6.4,46.4]],
        [[6.01,46.01],[6.01,46.02],[6.02,46.02]],
        [[6.03,46.03],[6.03, 46.04],[6.04,46.04]]
    ]
}

df = pd.DataFrame(data_dict)
df['colour'] = [[250,8,8]]*len(df)

layer = pdk.Layer(
    type="PathLayer",
    data=df,
    width_scale=20,
    get_path='coordinates',
    get_width=5,
    get_color='colour',
    width_min_pixels=2,
    visible=True
)

INITIAL_VIEW_STATE = pdk.ViewState(
    latitude=46.1,
    longitude=6.1,
    zoom=13,
    max_zoom=24,
    bearing=0,
)

deck = pdk.Deck(
            #map_provider="mapbox",
            map_style='mapbox://styles/mapbox/light-v10',
            initial_view_state=INITIAL_VIEW_STATE,
            api_keys={'mapbox':'pk.eyJ1IjoicGFuZWxvcmciLCJhIjoiY2s1enA3ejhyMWhmZjNobjM1NXhtbWRrMyJ9.B_frQsAVepGIe-HiOJeqvQ'},
            layers=[layer],
            tooltip=True
        )

#Visible lines and colour
deck.to_html('example.html')

#Luma.gl assertion error, no lines
deck_pane = pn.pane.DeckGL(deck, sizing_mode='stretch_both', margin=0)
deck_pane.show()

The exported html will show red paths, but the pane displayed by Panel will show no lines. A workaround is to use one column per colour with

layer = pdk.Layer(
    type="PathLayer",
    data=df,
    width_scale=20,
    get_path='coordinates',
    get_width=5,
    get_color="[colourR, colourG, colourB]",
    width_min_pixels=2,
    visible=True
)
edwardransome commented 1 year ago
data_dict = {
    'name':['a','b','c','d'],
    'coordinates':[
        [[6.1,46.1],[6.2,46.2]],
        [[6.3,46.3],[6.3,46.4],[6.4,46.4]],
        [[6.01,46.01],[6.01,46.02],[6.02,46.02]],
        [[6.03,46.03],[6.03, 46.04],[6.04,46.04]]
    ],
    'colour':[[123,0,0],[123,0,0],[123,0,0],[123,0,0,255]]
}

Just like for coordinates, adding an alpha coordinate to one of the [R,G,B] arrays so that they are not all the same length fixes the Panel display