##// END OF EJS Templates
s/ModalView/PopupView
Jonathan Frederic -
Show More
@@ -1,272 +1,272 b''
1 //----------------------------------------------------------------------------
1 //----------------------------------------------------------------------------
2 // Copyright (C) 2013 The IPython Development Team
2 // Copyright (C) 2013 The IPython Development Team
3 //
3 //
4 // Distributed under the terms of the BSD License. The full license is in
4 // Distributed under the terms of the BSD License. The full license is in
5 // the file COPYING, distributed as part of this software.
5 // the file COPYING, distributed as part of this software.
6 //----------------------------------------------------------------------------
6 //----------------------------------------------------------------------------
7
7
8 //============================================================================
8 //============================================================================
9 // ContainerWidget
9 // ContainerWidget
10 //============================================================================
10 //============================================================================
11
11
12 /**
12 /**
13 * @module IPython
13 * @module IPython
14 * @namespace IPython
14 * @namespace IPython
15 **/
15 **/
16
16
17 define(["notebook/js/widgets/widget"], function(WidgetManager) {
17 define(["notebook/js/widgets/widget"], function(WidgetManager) {
18
18
19 var ContainerView = IPython.DOMWidgetView.extend({
19 var ContainerView = IPython.DOMWidgetView.extend({
20 render: function(){
20 render: function(){
21 // Called when view is rendered.
21 // Called when view is rendered.
22 this.$el
22 this.$el
23 .addClass('widget-container');
23 .addClass('widget-container');
24 this.children={};
24 this.children={};
25 this.update_children([], this.model.get('_children'));
25 this.update_children([], this.model.get('_children'));
26 this.model.on('change:_children', function(model, value, options) {
26 this.model.on('change:_children', function(model, value, options) {
27 this.update_children(model.previous('_children'), value);
27 this.update_children(model.previous('_children'), value);
28 }, this);
28 }, this);
29 this.update()
29 this.update()
30 },
30 },
31
31
32 update_children: function(old_list, new_list) {
32 update_children: function(old_list, new_list) {
33 // Called when the children list changes.
33 // Called when the children list changes.
34 this.do_diff(old_list,
34 this.do_diff(old_list,
35 new_list,
35 new_list,
36 $.proxy(this.remove_child_model, this),
36 $.proxy(this.remove_child_model, this),
37 $.proxy(this.add_child_model, this));
37 $.proxy(this.add_child_model, this));
38 },
38 },
39
39
40 remove_child_model: function(model) {
40 remove_child_model: function(model) {
41 // Called when a model is removed from the children list.
41 // Called when a model is removed from the children list.
42 this.child_views[model.id].remove();
42 this.child_views[model.id].remove();
43 this.delete_child_view(model);
43 this.delete_child_view(model);
44 },
44 },
45
45
46 add_child_model: function(model) {
46 add_child_model: function(model) {
47 // Called when a model is added to the children list.
47 // Called when a model is added to the children list.
48 var view = this.create_child_view(model);
48 var view = this.create_child_view(model);
49 this.$el.append(view.$el);
49 this.$el.append(view.$el);
50 },
50 },
51
51
52 update: function(){
52 update: function(){
53 // Update the contents of this view
53 // Update the contents of this view
54 //
54 //
55 // Called when the model is changed. The model may have been
55 // Called when the model is changed. The model may have been
56 // changed by another view or by a state update from the back-end.
56 // changed by another view or by a state update from the back-end.
57 return ContainerView.__super__.update.apply(this);
57 return ContainerView.__super__.update.apply(this);
58 },
58 },
59 });
59 });
60 WidgetManager.register_widget_view('ContainerView', ContainerView);
60 WidgetManager.register_widget_view('ContainerView', ContainerView);
61
61
62
62
63 var ModalView = IPython.DOMWidgetView.extend({
63 var PopupView = IPython.DOMWidgetView.extend({
64 render: function(){
64 render: function(){
65 // Called when view is rendered.
65 // Called when view is rendered.
66 var that = this;
66 var that = this;
67 this.children={};
67 this.children={};
68 this.update_children([], this.model.get('_children'));
68 this.update_children([], this.model.get('_children'));
69 this.model.on('change:_children', function(model, value, options) {
69 this.model.on('change:_children', function(model, value, options) {
70 this.update_children(model.previous('_children'), value);
70 this.update_children(model.previous('_children'), value);
71 }, this);
71 }, this);
72
72
73 this.$el
73 this.$el
74 .on("remove", function(){
74 .on("remove", function(){
75 that.$window.remove();
75 that.$window.remove();
76 });
76 });
77 this.$window = $('<div />')
77 this.$window = $('<div />')
78 .addClass('modal widget-modal')
78 .addClass('modal widget-modal')
79 .appendTo($('#notebook-container'))
79 .appendTo($('#notebook-container'))
80 .mousedown(function(){
80 .mousedown(function(){
81 that.bring_to_front();
81 that.bring_to_front();
82 });
82 });
83 this.$title_bar = $('<div />')
83 this.$title_bar = $('<div />')
84 .addClass('popover-title')
84 .addClass('popover-title')
85 .appendTo(this.$window)
85 .appendTo(this.$window)
86 .mousedown(function(){
86 .mousedown(function(){
87 that.bring_to_front();
87 that.bring_to_front();
88 });
88 });
89 this.$close = $('<button />')
89 this.$close = $('<button />')
90 .addClass('close icon-remove')
90 .addClass('close icon-remove')
91 .css('margin-left', '5px')
91 .css('margin-left', '5px')
92 .appendTo(this.$title_bar)
92 .appendTo(this.$title_bar)
93 .click(function(){
93 .click(function(){
94 that.hide();
94 that.hide();
95 event.stopPropagation();
95 event.stopPropagation();
96 });
96 });
97 this.$minimize = $('<button />')
97 this.$minimize = $('<button />')
98 .addClass('close icon-arrow-down')
98 .addClass('close icon-arrow-down')
99 .appendTo(this.$title_bar)
99 .appendTo(this.$title_bar)
100 .click(function(){
100 .click(function(){
101 that.popped_out = !that.popped_out;
101 that.popped_out = !that.popped_out;
102 if (!that.popped_out) {
102 if (!that.popped_out) {
103 that.$minimize
103 that.$minimize
104 .removeClass('icon-arrow-down')
104 .removeClass('icon-arrow-down')
105 .addClass('icon-arrow-up');
105 .addClass('icon-arrow-up');
106
106
107 that.$window
107 that.$window
108 .draggable('destroy')
108 .draggable('destroy')
109 .resizable('destroy')
109 .resizable('destroy')
110 .removeClass('widget-modal modal')
110 .removeClass('widget-modal modal')
111 .addClass('docked-widget-modal')
111 .addClass('docked-widget-modal')
112 .detach()
112 .detach()
113 .insertBefore(that.$show_button);
113 .insertBefore(that.$show_button);
114 that.$show_button.hide();
114 that.$show_button.hide();
115 that.$close.hide();
115 that.$close.hide();
116 } else {
116 } else {
117 that.$minimize
117 that.$minimize
118 .addClass('icon-arrow-down')
118 .addClass('icon-arrow-down')
119 .removeClass('icon-arrow-up');
119 .removeClass('icon-arrow-up');
120
120
121 that.$window
121 that.$window
122 .removeClass('docked-widget-modal')
122 .removeClass('docked-widget-modal')
123 .addClass('widget-modal modal')
123 .addClass('widget-modal modal')
124 .detach()
124 .detach()
125 .appendTo($('#notebook-container'))
125 .appendTo($('#notebook-container'))
126 .draggable({handle: '.popover-title', snap: '#notebook, .modal', snapMode: 'both'})
126 .draggable({handle: '.popover-title', snap: '#notebook, .modal', snapMode: 'both'})
127 .resizable()
127 .resizable()
128 .children('.ui-resizable-handle').show();
128 .children('.ui-resizable-handle').show();
129 that.show();
129 that.show();
130 that.$show_button.show();
130 that.$show_button.show();
131 that.$close.show();
131 that.$close.show();
132 }
132 }
133 event.stopPropagation();
133 event.stopPropagation();
134 });
134 });
135 this.$title = $('<div />')
135 this.$title = $('<div />')
136 .addClass('widget-modal-title')
136 .addClass('widget-modal-title')
137 .text(' ')
137 .text(' ')
138 .appendTo(this.$title_bar);
138 .appendTo(this.$title_bar);
139 this.$body = $('<div />')
139 this.$body = $('<div />')
140 .addClass('modal-body')
140 .addClass('modal-body')
141 .addClass('widget-modal-body')
141 .addClass('widget-modal-body')
142 .addClass('widget-container')
142 .addClass('widget-container')
143 .appendTo(this.$window);
143 .appendTo(this.$window);
144
144
145 this.$show_button = $('<button />')
145 this.$show_button = $('<button />')
146 .text(' ')
146 .text(' ')
147 .addClass('btn btn-info widget-modal-show')
147 .addClass('btn btn-info widget-modal-show')
148 .appendTo(this.$el)
148 .appendTo(this.$el)
149 .click(function(){
149 .click(function(){
150 that.show();
150 that.show();
151 });
151 });
152
152
153 this.$window.draggable({handle: '.popover-title', snap: '#notebook, .modal', snapMode: 'both'});
153 this.$window.draggable({handle: '.popover-title', snap: '#notebook, .modal', snapMode: 'both'});
154 this.$window.resizable();
154 this.$window.resizable();
155 this.$window.on('resize', function(){
155 this.$window.on('resize', function(){
156 that.$body.outerHeight(that.$window.innerHeight() - that.$title_bar.outerHeight());
156 that.$body.outerHeight(that.$window.innerHeight() - that.$title_bar.outerHeight());
157 });
157 });
158
158
159 this.$el_to_style = this.$body;
159 this.$el_to_style = this.$body;
160 this._shown_once = false;
160 this._shown_once = false;
161 this.popped_out = true;
161 this.popped_out = true;
162 },
162 },
163
163
164 hide: function() {
164 hide: function() {
165 // Called when the modal hide button is clicked.
165 // Called when the modal hide button is clicked.
166 this.$window.hide();
166 this.$window.hide();
167 this.$show_button.removeClass('btn-info');
167 this.$show_button.removeClass('btn-info');
168 },
168 },
169
169
170 show: function() {
170 show: function() {
171 // Called when the modal show button is clicked.
171 // Called when the modal show button is clicked.
172 this.$show_button.addClass('btn-info');
172 this.$show_button.addClass('btn-info');
173 this.$window.show();
173 this.$window.show();
174 if (this.popped_out) {
174 if (this.popped_out) {
175 this.$window.css("positon", "absolute");
175 this.$window.css("positon", "absolute");
176 this.$window.css("top", "0px");
176 this.$window.css("top", "0px");
177 this.$window.css("left", Math.max(0, (($('body').outerWidth() - this.$window.outerWidth()) / 2) +
177 this.$window.css("left", Math.max(0, (($('body').outerWidth() - this.$window.outerWidth()) / 2) +
178 $(window).scrollLeft()) + "px");
178 $(window).scrollLeft()) + "px");
179 this.bring_to_front();
179 this.bring_to_front();
180 }
180 }
181 },
181 },
182
182
183 bring_to_front: function() {
183 bring_to_front: function() {
184 // Make the modal top-most, z-ordered about the other modals.
184 // Make the modal top-most, z-ordered about the other modals.
185 var $widget_modals = $(".widget-modal");
185 var $widget_modals = $(".widget-modal");
186 var max_zindex = 0;
186 var max_zindex = 0;
187 $widget_modals.each(function (index, el){
187 $widget_modals.each(function (index, el){
188 max_zindex = Math.max(max_zindex, parseInt($(el).css('z-index')));
188 max_zindex = Math.max(max_zindex, parseInt($(el).css('z-index')));
189 });
189 });
190
190
191 // Start z-index of widget modals at 2000
191 // Start z-index of widget modals at 2000
192 max_zindex = Math.max(max_zindex, 2000);
192 max_zindex = Math.max(max_zindex, 2000);
193
193
194 $widget_modals.each(function (index, el){
194 $widget_modals.each(function (index, el){
195 $el = $(el);
195 $el = $(el);
196 if (max_zindex == parseInt($el.css('z-index'))) {
196 if (max_zindex == parseInt($el.css('z-index'))) {
197 $el.css('z-index', max_zindex - 1);
197 $el.css('z-index', max_zindex - 1);
198 }
198 }
199 });
199 });
200 this.$window.css('z-index', max_zindex);
200 this.$window.css('z-index', max_zindex);
201 },
201 },
202
202
203 update_children: function(old_list, new_list) {
203 update_children: function(old_list, new_list) {
204 // Called when the children list is modified.
204 // Called when the children list is modified.
205 this.do_diff(old_list,
205 this.do_diff(old_list,
206 new_list,
206 new_list,
207 $.proxy(this.remove_child_model, this),
207 $.proxy(this.remove_child_model, this),
208 $.proxy(this.add_child_model, this));
208 $.proxy(this.add_child_model, this));
209 },
209 },
210
210
211 remove_child_model: function(model) {
211 remove_child_model: function(model) {
212 // Called when a child is removed from children list.
212 // Called when a child is removed from children list.
213 this.child_views[model.id].remove();
213 this.child_views[model.id].remove();
214 this.delete_child_view(model);
214 this.delete_child_view(model);
215 },
215 },
216
216
217 add_child_model: function(model) {
217 add_child_model: function(model) {
218 // Called when a child is added to children list.
218 // Called when a child is added to children list.
219 var view = this.create_child_view(model);
219 var view = this.create_child_view(model);
220 this.$body.append(view.$el);
220 this.$body.append(view.$el);
221 },
221 },
222
222
223 update: function(){
223 update: function(){
224 // Update the contents of this view
224 // Update the contents of this view
225 //
225 //
226 // Called when the model is changed. The model may have been
226 // Called when the model is changed. The model may have been
227 // changed by another view or by a state update from the back-end.
227 // changed by another view or by a state update from the back-end.
228 var description = this.model.get('description');
228 var description = this.model.get('description');
229 if (description.length === 0) {
229 if (description.length === 0) {
230 this.$title.text(' '); // Preserve title height
230 this.$title.text(' '); // Preserve title height
231 } else {
231 } else {
232 this.$title.text(description);
232 this.$title.text(description);
233 }
233 }
234
234
235 var button_text = this.model.get('button_text');
235 var button_text = this.model.get('button_text');
236 if (button_text.length === 0) {
236 if (button_text.length === 0) {
237 this.$show_button.text(' '); // Preserve button height
237 this.$show_button.text(' '); // Preserve button height
238 } else {
238 } else {
239 this.$show_button.text(button_text);
239 this.$show_button.text(button_text);
240 }
240 }
241
241
242 if (!this._shown_once) {
242 if (!this._shown_once) {
243 this._shown_once = true;
243 this._shown_once = true;
244 this.show();
244 this.show();
245 }
245 }
246
246
247 return ModalView.__super__.update.apply(this);
247 return PopupView.__super__.update.apply(this);
248 },
248 },
249
249
250 _get_selector_element: function(selector) {
250 _get_selector_element: function(selector) {
251 // Get an element view a 'special' jquery selector. (see widget.js)
251 // Get an element view a 'special' jquery selector. (see widget.js)
252 //
252 //
253 // Since the modal actually isn't within the $el in the DOM, we need to extend
253 // Since the modal actually isn't within the $el in the DOM, we need to extend
254 // the selector logic to allow the user to set css on the modal if need be.
254 // the selector logic to allow the user to set css on the modal if need be.
255 // The convention used is:
255 // The convention used is:
256 // "modal" - select the modal div
256 // "modal" - select the modal div
257 // "modal [selector]" - select element(s) within the modal div.
257 // "modal [selector]" - select element(s) within the modal div.
258 // "[selector]" - select elements within $el
258 // "[selector]" - select elements within $el
259 // "" - select the $el_to_style
259 // "" - select the $el_to_style
260 if (selector.substring(0, 5) == 'modal') {
260 if (selector.substring(0, 5) == 'modal') {
261 if (selector == 'modal') {
261 if (selector == 'modal') {
262 return this.$window;
262 return this.$window;
263 } else {
263 } else {
264 return this.$window.find(selector.substring(6));
264 return this.$window.find(selector.substring(6));
265 }
265 }
266 } else {
266 } else {
267 return ModalView.__super__._get_selector_element.apply(this, [selector]);
267 return PopupView.__super__._get_selector_element.apply(this, [selector]);
268 }
268 }
269 },
269 },
270 });
270 });
271 WidgetManager.register_widget_view('ModalView', ModalView);
271 WidgetManager.register_widget_view('PopupView', PopupView);
272 });
272 });
@@ -1,11 +1,11 b''
1 from .widget import Widget, DOMWidget
1 from .widget import Widget, DOMWidget
2
2
3 from .widget_bool import CheckBoxWidget, ToggleButtonWidget
3 from .widget_bool import CheckBoxWidget, ToggleButtonWidget
4 from .widget_button import ButtonWidget
4 from .widget_button import ButtonWidget
5 from .widget_container import ContainerWidget, ModalWidget
5 from .widget_container import ContainerWidget, PopupWidget
6 from .widget_float import FloatTextWidget, BoundedFloatTextWidget, FloatSliderWidget, FloatProgressWidget
6 from .widget_float import FloatTextWidget, BoundedFloatTextWidget, FloatSliderWidget, FloatProgressWidget
7 from .widget_image import ImageWidget
7 from .widget_image import ImageWidget
8 from .widget_int import IntTextWidget, BoundedIntTextWidget, IntSliderWidget, IntProgressWidget
8 from .widget_int import IntTextWidget, BoundedIntTextWidget, IntSliderWidget, IntProgressWidget
9 from .widget_selection import RadioButtonsWidget, ToggleButtonsWidget, DropdownWidget, ListBoxWidget
9 from .widget_selection import RadioButtonsWidget, ToggleButtonsWidget, DropdownWidget, ListBoxWidget
10 from .widget_selectioncontainer import TabWidget, AccordionWidget
10 from .widget_selectioncontainer import TabWidget, AccordionWidget
11 from .widget_string import HTMLWidget, LatexWidget, TextBoxWidget, TextAreaWidget
11 from .widget_string import HTMLWidget, LatexWidget, TextBoxWidget, TextAreaWidget
@@ -1,52 +1,52 b''
1 """ContainerWidget class.
1 """ContainerWidget class.
2
2
3 Represents a container that can be used to group other widgets.
3 Represents a container that can be used to group other widgets.
4 """
4 """
5 #-----------------------------------------------------------------------------
5 #-----------------------------------------------------------------------------
6 # Copyright (c) 2013, the IPython Development Team.
6 # Copyright (c) 2013, the IPython Development Team.
7 #
7 #
8 # Distributed under the terms of the Modified BSD License.
8 # Distributed under the terms of the Modified BSD License.
9 #
9 #
10 # The full license is in the file COPYING.txt, distributed with this software.
10 # The full license is in the file COPYING.txt, distributed with this software.
11 #-----------------------------------------------------------------------------
11 #-----------------------------------------------------------------------------
12
12
13 #-----------------------------------------------------------------------------
13 #-----------------------------------------------------------------------------
14 # Imports
14 # Imports
15 #-----------------------------------------------------------------------------
15 #-----------------------------------------------------------------------------
16 from .widget import DOMWidget
16 from .widget import DOMWidget
17 from IPython.utils.traitlets import Unicode, Bool, List, Instance
17 from IPython.utils.traitlets import Unicode, Bool, List, Instance
18
18
19 #-----------------------------------------------------------------------------
19 #-----------------------------------------------------------------------------
20 # Classes
20 # Classes
21 #-----------------------------------------------------------------------------
21 #-----------------------------------------------------------------------------
22 class ContainerWidget(DOMWidget):
22 class ContainerWidget(DOMWidget):
23 view_name = Unicode('ContainerView', sync=True)
23 view_name = Unicode('ContainerView', sync=True)
24
24
25 # Keys, all private and managed by helper methods. Flexible box model
25 # Keys, all private and managed by helper methods. Flexible box model
26 # classes...
26 # classes...
27 children = List(Instance(DOMWidget))
27 children = List(Instance(DOMWidget))
28 _children = List(Instance(DOMWidget), sync=True)
28 _children = List(Instance(DOMWidget), sync=True)
29
29
30 def __init__(self, *pargs, **kwargs):
30 def __init__(self, *pargs, **kwargs):
31 """Constructor"""
31 """Constructor"""
32 DOMWidget.__init__(self, *pargs, **kwargs)
32 DOMWidget.__init__(self, *pargs, **kwargs)
33 self.on_trait_change(self._validate, ['children'])
33 self.on_trait_change(self._validate, ['children'])
34
34
35 def _validate(self, name, old, new):
35 def _validate(self, name, old, new):
36 """Validate children list.
36 """Validate children list.
37
37
38 Makes sure only one instance of any given model can exist in the
38 Makes sure only one instance of any given model can exist in the
39 children list."""
39 children list."""
40 if new is not None and isinstance(new, list):
40 if new is not None and isinstance(new, list):
41 children = []
41 children = []
42 for child in new:
42 for child in new:
43 if child not in children:
43 if child not in children:
44 children.append(child)
44 children.append(child)
45 self._children = children
45 self._children = children
46
46
47
47
48 class ModalWidget(ContainerWidget):
48 class PopupWidget(ContainerWidget):
49 view_name = Unicode('ModalView', sync=True)
49 view_name = Unicode('PopupView', sync=True)
50
50
51 description = Unicode(sync=True)
51 description = Unicode(sync=True)
52 button_text = Unicode(sync=True)
52 button_text = Unicode(sync=True)
General Comments 0
You need to be logged in to leave comments. Login now