I have bokeh embedded in a Quasar page.
It’s essentially a grid of two rows, with the top row having two columns. I’d like the two main rows to be the same height. And the two columns in the top row to be the same width. And I’d like it all to respond to browser resize changes.
The main problem I’m seeing is with the data tables. Vertically, the one in the bottom row will go beyond the limits of the container. Horizontally, the one in the top row (on the right) will go beyond the limits of the container. The data tables also do not resize vertically or horizontally as the window gets smaller.
I’ve read about the different sizing_mode values and I’ve tried to use them, but I’m obviously misunderstanding them…
MIN_WIDTH = 100
MIN_HEIGHT = 100
SIZING_MODE = "stretch_both"
DEFAULT_NUM_FORMATTER = NumberFormatter(format='0,0[.]00',text_align='right')
DEFAULT_PERC_FORMATTER = NumberFormatter(format='0.0%', text_align='right')
DEFAULT_DATE_FORMATTER = DateFormatter(format='%Y-%m-%d')
COLUMNS_AVAILABLE = {
"label": {
"label": "Label",
"formatter": None,
"definition": TableColumn(field="label", title="Label"),
"defaultColumn": True
},
"date": {
"label": "Date",
"formatter": DEFAULT_DATE_FORMATTER,
"definition": TableColumn(field="date", title="Date", formatter=DEFAULT_DATE_FORMATTER),
"defaultColumn": True
},
"totalChildren": {
"label" : "Children",
"formatter": None,
"definition": TableColumn(field="totalChildren", title="Children"),
"defaultColumn": True
},
"totalParents": {
"label": "Parents",
"formatter": None,
"definition": TableColumn(field="totalParents", title="Parents"),
"defaultColumn": True
},
"totalSiblings": {
"label": "Siblings",
"formatter": None,
"definition": TableColumn(field="totalSiblings", title="Siblings"),
"defaultColumn": True
},
}
COLUMNS_ORDER = ["label",
"date",
"totalChildren",
"totalParents",
"totalSiblings"]
def createMap(wData, fData, mapOptions=None):
x_range = (-12819494.949494913, -8470448.933782242)
y_range = (2720808.080808082, 6578832.772166105)
fig = figure(x_axis_type="mercator",
y_axis_type="mercator",
tools="pan,wheel_zoom,box_zoom,reset,tap,box_select,lasso_select",
active_scroll="wheel_zoom",
active_tap="tap",
x_range=x_range, y_range=y_range,
min_width=MIN_WIDTH,
min_height=MIN_HEIGHT,
sizing_mode=SIZING_MODE,)
hover = HoverTool(tooltips=[("W", "@label"),])
fig.add_tools(hover)
fig.legend.click_policy = "hide"
fig.legend.location = "top_left"
fig.toolbar.active_inspect = None
fig.toolbar.logo = None
return fig
def createSummary(sources, ctx, info):
figMap = createMap(sources['wData'], sources['fData'])
modelPanel = createModelPanel(sources['wData'], ctx)
fTable = createFTable(sources['fData'], ctx)
gbox = grid(children=[[figMap, modelPanel],
fTable])
return gbox
def createModelPanel(data, ctx):
selected_columns = []
dataTableCols = []
for key in COLUMNS_ORDER:
column_def = COLUMNS_AVAILABLE[key]
if "defaultColumn" in column_def.keys() and column_def["defaultColumn"] == True:
dataTableCols.append(column_def["definition"])
selected_columns.append(key)
modelTable = DataTable(source=data,
columns=dataTableCols,
sizing_mode=SIZING_MODE,
width_policy="max")
options = list()
for key in COLUMNS_AVAILABLE.keys():
option_tuple = (key, (COLUMNS_AVAILABLE[key])["label"])
options.append(option_tuple)
widget = MultiChoice(title="Select Columns",
value=selected_columns,
options=options,
delete_button=True,
height=100,
sizing_mode="stretch_width")
w_header = Div(text="""
W Summary
""",
sizing_mode=SIZING_MODE)
model_layout = layout(column(w_header, widget, modelTable), sizing_mode="scale_height")
return model_layout
def createFTable(data, ctx):
fheader = Div(text="""
F Summary
""",
sizing_mode=SIZING_MODE)
dataTableCols = []
dateFormatter = DateFormatter(format='%Y-%m-%d')
dataTableCols.append(TableColumn(field="aLabel", title="A-label"))
dataTableCols.append(TableColumn(field="oLabel", title="O-label"))
dataTableCols.append(TableColumn(field="date", title="Date", formatter=dateFormatter))
dataTableCols.append(TableColumn(field="active", title="A"))
dataTableCols.append(TableColumn(field="offset", title="O"))
dataTableCols.append(TableColumn(field="name", title="Name"))
dataTable = DataTable(source=data,
columns=dataTableCols,
sizing_mode=SIZING_MODE,
width_policy="max")
table_layout = layout(column(fheader, dataTable), sizing_mode=SIZING_MODE)
return table_layout
def createBokehChart(data, ctx):
wCols = ['id', 'date', 'totalChildren', 'totalParents', 'totalSiblings']
wData = createSource(data, wCols, 'wData')
fCols = ['id', 'active', 'offset', 'aLabel', 'olabel', 'date', 'name']
fData = createSource(data, fCols, 'fData')
sources = dict(wData=wData, fData=fData)
summary_view = createSummary(sources, ctx, dict())
return summary_view
def createSource(data, cols, key):
data_dict = dict([(key, []) for key in cols])
if len(data) > 0 and key in data[0]:
data_dict = dict([(col, data[0][key][col]) for col in cols])
source = ColumnDataSource(data_dict, name=key)
return source