diff --git a/IPython/html/static/widgets/js/widget_container.js b/IPython/html/static/widgets/js/widget_container.js
index e56873304..45f0cc1f5 100644
--- a/IPython/html/static/widgets/js/widget_container.js
+++ b/IPython/html/static/widgets/js/widget_container.js
@@ -19,7 +19,7 @@ define([
render: function(){
// Called when view is rendered.
- this.$el.addClass('widget-container').addClass('vbox');
+ this.$el.addClass('widget-container');
},
update_children: function(old_list, new_list) {
@@ -45,6 +45,56 @@ define([
});
},
});
+
+
+ var FlexContainerView = ContainerView.extend({
+ render: function(){
+ FlexContainerView.__super__.render.apply(this);
+ this.model.on('change:flex', this._flex_changed, this);
+ this.model.on('change:pack', this._pack_changed, this);
+ this.model.on('change:align', this._align_changed, this);
+ this._flex_changed();
+ this._pack_changed();
+ this._align_changed();
+ },
+
+ _flex_changed: function(){
+ if (this.model.previous('flex')) {
+ this.$el.removeClass('box-flex' + this.model.previous('flex'));
+ }
+ this.$el.addClass('box-flex' + this.model.get('flex'));
+ },
+
+ _pack_changed: function(){
+ if (this.model.previous('pack')) {
+ this.$el.removeClass(this.model.previous('pack'));
+ }
+ this.$el.addClass(this.model.get('pack'));
+ },
+
+ _align_changed: function(){
+ if (this.model.previous('align')) {
+ this.$el.removeClass('align-' + this.model.previous('align'));
+ }
+ this.$el.addClass('align-' + this.model.get('align'));
+ },
+ });
+
+
+ var VBoxContainerView = FlexContainerView.extend({
+ render: function(){
+ this.$el.addClass('vbox');
+ FlexContainerView.__super__.render.apply(this);
+ },
+ });
+
+
+ var HBoxContainerView = FlexContainerView.extend({
+ render: function(){
+ this.$el.addClass('hbox');
+ FlexContainerView.__super__.render.apply(this);
+ },
+ });
var PopupView = widget.DOMWidgetView.extend({
@@ -279,5 +329,8 @@ define([
return {
'ContainerView': ContainerView,
'PopupView': PopupView,
+ 'FlexContainerView': FlexContainerView,
+ 'VBoxContainerView': VBoxContainerView,
+ 'HBoxContainerView': HBoxContainerView,
};
});
diff --git a/IPython/html/widgets/__init__.py b/IPython/html/widgets/__init__.py
index 7b6d0a836..42fe52215 100644
--- a/IPython/html/widgets/__init__.py
+++ b/IPython/html/widgets/__init__.py
@@ -2,7 +2,7 @@ from .widget import Widget, DOMWidget, CallbackDispatcher
from .widget_bool import CheckboxWidget, ToggleButtonWidget
from .widget_button import ButtonWidget
-from .widget_container import ContainerWidget, PopupWidget
+from .widget_container import ContainerWidget, PopupWidget, FlexContainerWidget, HBoxContainerWidget, VBoxContainerWidget
from .widget_float import FloatTextWidget, BoundedFloatTextWidget, FloatSliderWidget, FloatProgressWidget
from .widget_image import ImageWidget
from .widget_int import IntTextWidget, BoundedIntTextWidget, IntSliderWidget, IntProgressWidget
diff --git a/IPython/html/widgets/widget_container.py b/IPython/html/widgets/widget_container.py
index 6ba8206a0..bbafdd695 100644
--- a/IPython/html/widgets/widget_container.py
+++ b/IPython/html/widgets/widget_container.py
@@ -7,7 +7,7 @@ Represents a container that can be used to group other widgets.
# Distributed under the terms of the Modified BSD License.
from .widget import DOMWidget
-from IPython.utils.traitlets import Unicode, Tuple, TraitError
+from IPython.utils.traitlets import Unicode, Tuple, TraitError, Int, CaselessStrEnum
class ContainerWidget(DOMWidget):
_view_name = Unicode('ContainerView', sync=True)
@@ -32,3 +32,24 @@ class PopupWidget(ContainerWidget):
description = Unicode(sync=True)
button_text = Unicode(sync=True)
+
+
+class FlexContainerWidget(ContainerWidget):
+ _view_name = Unicode('FlexContainerView', sync=True)
+ flex = Int(0, sync=True, help="""Specify the flexible-ness of the model.""")
+ def _flex_changed(self, name, old, new):
+ new = min(max(0, new), 2)
+ if self.flex != new:
+ self.flex = new
+
+ _locations = ['start', 'center', 'end']
+ pack = CaselessStrEnum(values=_locations, default_value='start', allow_none=False, sync=True)
+ align = CaselessStrEnum(values=_locations, default_value='start', allow_none=False, sync=True)
+
+
+class VBoxContainerWidget(FlexContainerWidget):
+ _view_name = Unicode('VBoxContainerView', sync=True)
+
+
+class HBoxContainerWidget(FlexContainerWidget):
+ _view_name = Unicode('HBoxContainerView', sync=True)