From 3f91c0bbcc8e916823b1379f78a2b042dc5def81 Mon Sep 17 00:00:00 2001 From: Philipp Rudiger Date: Mon, 20 Jan 2020 20:12:14 +0100 Subject: [PATCH 1/4] Improved handling of GridSpec layout --- panel/layout.py | 15 ++++----------- 1 file changed, 4 insertions(+), 11 deletions(-) diff --git a/panel/layout.py b/panel/layout.py index ce00110cd5..dcac6bd1d0 100644 --- a/panel/layout.py +++ b/panel/layout.py @@ -904,6 +904,10 @@ def _get_objects(self, model, old_objects, doc, root, comm=None): properties = {'width': w*width, 'height': h*height} else: properties = {'sizing_mode': self.sizing_mode} + if 'width' in self.sizing_mode: + properties['height'] = h*height + elif 'height' in self.sizing_mode: + properties['width'] = w*width obj.set_param(**properties) if obj in old_objects: @@ -914,17 +918,6 @@ def _get_objects(self, model, old_objects, doc, root, comm=None): except RerenderError: return self._get_objects(model, current_objects[:i], doc, root, comm) - if isinstance(child, BkMarkup) and self.sizing_mode not in ['fixed', None]: - if child.style is None: - child.style = {} - style = {} - if 'width' not in child.style: - style['width'] = '100%' - if 'height' not in child.style: - style['height'] = '100%' - if style: - child.style.update(style) - if isinstance(child, BkBox) and len(child.children) == 1: child.children[0].update(**properties) else: From f32fd3b37bd4fd1490ab8f9c0a86d522e8f41bbe Mon Sep 17 00:00:00 2001 From: Philipp Rudiger Date: Mon, 20 Jan 2020 20:12:20 +0100 Subject: [PATCH 2/4] Ensure ReplacementPane syncs layout properties with internal pane --- panel/pane/base.py | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/panel/pane/base.py b/panel/pane/base.py index 1e312b0d3d..aeb4e09249 100644 --- a/panel/pane/base.py +++ b/panel/pane/base.py @@ -315,6 +315,13 @@ def __init__(self, object=None, **params): self._pane = Pane(None) self._internal = True self._inner_layout = Row(self._pane, **{k: v for k, v in params.items() if k in Row.param}) + self.param.watch(self._update_inner_layout, list(Layoutable.param)) + + def _update_inner_layout(self, *events): + for event in events: + setattr(self._pane, event.name, event.new) + if event.name in ['sizing_mode', 'width_policy', 'height_policy']: + setattr(self._inner_layout, event.name, event.new) def _update_pane(self, *events): """ From 3e2c4815b9eb9ff49694e223dade7965629462df Mon Sep 17 00:00:00 2001 From: Philipp Rudiger Date: Mon, 20 Jan 2020 20:20:12 +0100 Subject: [PATCH 3/4] Fixed flake --- panel/layout.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/panel/layout.py b/panel/layout.py index dcac6bd1d0..ce0aca49cd 100644 --- a/panel/layout.py +++ b/panel/layout.py @@ -14,7 +14,7 @@ from bokeh.models import ( Box as BkBox, Column as BkColumn, Div as BkDiv, GridBox as BkGridBox, - Markup as BkMarkup, Row as BkRow, Spacer as BkSpacer + Row as BkRow, Spacer as BkSpacer ) from bokeh.models.widgets import Tabs as BkTabs, Panel as BkPanel From 1f7fd1eb3de17258b33082af15f09baa650f637a Mon Sep 17 00:00:00 2001 From: Philipp Rudiger Date: Mon, 20 Jan 2020 22:05:23 +0100 Subject: [PATCH 4/4] Added tests --- panel/tests/test_layout.py | 59 +++++++++++++++++++++++++++++++++++--- 1 file changed, 55 insertions(+), 4 deletions(-) diff --git a/panel/tests/test_layout.py b/panel/tests/test_layout.py index 5c6813f834..d7b92e02ef 100644 --- a/panel/tests/test_layout.py +++ b/panel/tests/test_layout.py @@ -4,9 +4,12 @@ from bokeh.models import (Div, Row as BkRow, Tabs as BkTabs, Column as BkColumn, Panel as BkPanel) + +from panel.depends import depends from panel.layout import Column, Row, Tabs, Spacer, GridSpec, GridBox, WidgetBox from panel.pane import Bokeh, Pane from panel.param import Param +from panel.widgets import IntSlider from panel.tests.util import check_layoutable_properties @@ -1029,9 +1032,7 @@ def test_gridspec_stretch_with_int_setitem(document, comm): model = gspec.get_root(document, comm=comm) assert model.children == [(div1, 0, 0, 1, 1), (div2, 1, 1, 1, 1)] assert div1.sizing_mode == 'stretch_both' - assert div1.style == {'width': '100%', 'height': '100%'} assert div2.sizing_mode == 'stretch_both' - assert div2.style == {'width': '100%', 'height': '100%'} def test_gridspec_stretch_with_slice_setitem(document, comm): @@ -1045,11 +1046,61 @@ def test_gridspec_stretch_with_slice_setitem(document, comm): model = gspec.get_root(document, comm=comm) assert model.children == [(div1, 0, 0, 1, 2), (div2, 1, 2, 1, 1)] assert div1.sizing_mode == 'stretch_both' - assert div1.style == {'width': '100%', 'height': '100%'} assert div2.sizing_mode == 'stretch_both' - assert div2.style == {'width': '100%', 'height': '100%'} +def test_gridspec_fixed_with_replacement_pane(document, comm): + slider = IntSlider(start=0, end=2) + + @depends(slider) + def div(value): + return Div(text=str(value)) + + gspec = GridSpec() + + gspec[0, 0:2] = Div() + gspec[1, 2] = div + + model = gspec.get_root(document, comm=comm) + ((div1, _, _, _, _), (row, _, _, _, _)) = model.children + div2 = row.children[0] + assert div1.width == 400 + assert div1.height == 300 + assert div2.width == 200 + assert div2.height == 300 + + slider.value = 1 + assert row.children[0] is not div2 + assert row.children[0].width == 200 + assert row.children[0].height == 300 + + +def test_gridspec_stretch_with_replacement_pane(document, comm): + slider = IntSlider(start=0, end=2) + + @depends(slider) + def div(value): + return Div(text=str(value)) + + gspec = GridSpec(sizing_mode='stretch_width') + + gspec[0, 0:2] = Div() + gspec[1, 2] = div + + model = gspec.get_root(document, comm=comm) + ((div1, _, _, _, _), (row, _, _, _, _)) = model.children + div2 = row.children[0] + assert div1.sizing_mode == 'stretch_width' + assert div1.height == 300 + assert div2.sizing_mode == 'stretch_width' + assert div2.height == 300 + + slider.value = 1 + assert row.children[0] is not div2 + assert row.children[0].sizing_mode == 'stretch_width' + assert row.children[0].height == 300 + + def test_widgetbox(document, comm): widget_box = WidgetBox("WidgetBox")