##// END OF EJS Templates
Updated require.js references
Jonathan Frederic -
Show More
@@ -1,24 +1,24 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // Basic Widgets
10 10 //============================================================================
11 11
12 12 define([
13 "notebook/js/widgets/bool",
14 "notebook/js/widgets/button",
15 "notebook/js/widgets/container",
16 "notebook/js/widgets/float",
17 "notebook/js/widgets/float_range",
18 "notebook/js/widgets/image",
19 "notebook/js/widgets/int",
20 "notebook/js/widgets/int_range",
21 "notebook/js/widgets/multicontainer",
22 "notebook/js/widgets/selection",
23 "notebook/js/widgets/string",
13 "notebook/js/widgets/widget_bool",
14 "notebook/js/widgets/widget_button",
15 "notebook/js/widgets/widget_container",
16 "notebook/js/widgets/widget_float",
17 "notebook/js/widgets/widget_float_range",
18 "notebook/js/widgets/widget_image",
19 "notebook/js/widgets/widget_int",
20 "notebook/js/widgets/widget_int_range",
21 "notebook/js/widgets/widget_multicontainer",
22 "notebook/js/widgets/widget_selection",
23 "notebook/js/widgets/widget_string",
24 24 ], function(){ return true; });
@@ -1,123 +1,123 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // BoolWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18
19 19 var BoolWidgetModel = IPython.WidgetModel.extend({});
20 20 widget_manager.register_widget_model('BoolWidgetModel', BoolWidgetModel);
21 21
22 22 var CheckboxView = IPython.WidgetView.extend({
23 23
24 24 // Called when view is rendered.
25 25 render : function(){
26 26 this.$el
27 27 .addClass('widget-hbox-single');
28 28 this.$label = $('<div />')
29 29 .addClass('widget-hlabel')
30 30 .appendTo(this.$el)
31 31 .hide();
32 32 var that = this;
33 33 this.$checkbox = $('<input />')
34 34 .attr('type', 'checkbox')
35 35 .click(function(el) {
36 36 that.user_invoked_update = true;
37 37 that.model.set('value', that.$checkbox.prop('checked'));
38 38 that.touch();
39 39 that.user_invoked_update = false;
40 40 })
41 41 .appendTo(this.$el);
42 42
43 43 this.$el_to_style = this.$checkbox; // Set default element to style
44 44 this.update(); // Set defaults.
45 45 },
46 46
47 47 // Handles: Backend -> Frontend Sync
48 48 // Frontent -> Frontend Sync
49 49 update : function(){
50 50 if (!this.user_invoked_update) {
51 51 this.$checkbox.prop('checked', this.model.get('value'));
52 52
53 53 var disabled = this.model.get('disabled');
54 54 this.$checkbox.prop('disabled', disabled);
55 55
56 56 var description = this.model.get('description');
57 57 if (description.length === 0) {
58 58 this.$label.hide();
59 59 } else {
60 60 this.$label.html(description);
61 61 this.$label.show();
62 62 }
63 63 }
64 64 return IPython.WidgetView.prototype.update.call(this);
65 65 },
66 66
67 67 });
68 68
69 69 widget_manager.register_widget_view('CheckboxView', CheckboxView);
70 70
71 71 var ToggleButtonView = IPython.WidgetView.extend({
72 72
73 73 // Called when view is rendered.
74 74 render : function(){
75 75 this.$el
76 76 .html('');
77 77 this.$button = $('<button />')
78 78 .addClass('btn')
79 79 .attr('type', 'button')
80 80 .attr('data-toggle', 'button')
81 81 .appendTo(this.$el);
82 82 this.$el_to_style = this.$button; // Set default element to style
83 83
84 84 this.update(); // Set defaults.
85 85 },
86 86
87 87 // Handles: Backend -> Frontend Sync
88 88 // Frontent -> Frontend Sync
89 89 update : function(){
90 90 if (!this.user_invoked_update) {
91 91 if (this.model.get('value')) {
92 92 this.$button.addClass('active');
93 93 } else {
94 94 this.$button.removeClass('active');
95 95 }
96 96
97 97 var disabled = this.model.get('disabled');
98 98 this.$button.prop('disabled', disabled);
99 99
100 100 var description = this.model.get('description');
101 101 if (description.length === 0) {
102 102 this.$button.html(' '); // Preserve button height
103 103 } else {
104 104 this.$button.html(description);
105 105 }
106 106 }
107 107 return IPython.WidgetView.prototype.update.call(this);
108 108 },
109 109
110 110 events: {"click button" : "handleClick"},
111 111
112 112 // Handles and validates user input.
113 113 handleClick: function(e) {
114 114 this.user_invoked_update = true;
115 115 this.model.set('value', ! $(e.target).hasClass('active'));
116 116 this.touch();
117 117 this.user_invoked_update = false;
118 118 },
119 119 });
120 120
121 121 widget_manager.register_widget_view('ToggleButtonView', ToggleButtonView);
122 122
123 123 });
@@ -1,65 +1,65 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // ButtonWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18
19 19 var ButtonWidgetModel = IPython.WidgetModel.extend({});
20 20 widget_manager.register_widget_model('ButtonWidgetModel', ButtonWidgetModel);
21 21
22 22 var ButtonView = IPython.WidgetView.extend({
23 23
24 24 // Called when view is rendered.
25 25 render : function(){
26 26 var that = this;
27 27 this.setElement($("<button />")
28 28 .addClass('btn'));
29 29
30 30 this.update(); // Set defaults.
31 31 },
32 32
33 33 // Handles: Backend -> Frontend Sync
34 34 // Frontent -> Frontend Sync
35 35 update : function(){
36 36 var description = this.model.get('description');
37 37 description = description.replace(/ /g, '&nbsp;', 'm');
38 38 description = description.replace(/\n/g, '<br>\n', 'm');
39 39 if (description.length === 0) {
40 40 this.$el.html('&nbsp;'); // Preserve button height
41 41 } else {
42 42 this.$el.html(description);
43 43 }
44 44
45 45 if (this.model.get('disabled')) {
46 46 this.$el.attr('disabled','disabled');
47 47 } else {
48 48 this.$el.removeAttr('disabled');
49 49 }
50 50
51 51 return IPython.WidgetView.prototype.update.call(this);
52 52 },
53 53
54 54 events: {
55 55 'click': '_handle_click',
56 56 },
57 57
58 58 _handle_click: function(){
59 59 this.send({event: 'click'});
60 60 },
61 61 });
62 62
63 63 widget_manager.register_widget_view('ButtonView', ButtonView);
64 64
65 65 });
@@ -1,279 +1,279 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // ContainerWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager) {
17 define(["notebook/js/widgets/widget"], function(widget_manager) {
18 18
19 19 var set_flex_property = function(element, property_name, enabled) {
20 20 if (enabled) {
21 21 element.addClass(property_name);
22 22 } else {
23 23 element.removeClass(property_name);
24 24 }
25 25 };
26 26
27 27 var set_flex_properties = function(context, element) {
28 28
29 29 // Apply flexible box model properties by adding and removing
30 30 // corrosponding CSS classes.
31 31 // Defined in IPython/html/static/base/less/flexbox.less
32 32 set_flex_property(element, 'vbox', context.model.get('_vbox'));
33 33 set_flex_property(element, 'hbox', context.model.get('_hbox'));
34 34 set_flex_property(element, 'start', context.model.get('_pack_start'));
35 35 set_flex_property(element, 'center', context.model.get('_pack_center'));
36 36 set_flex_property(element, 'end', context.model.get('_pack_end'));
37 37 set_flex_property(element, 'align-start', context.model.get('_align_start'));
38 38 set_flex_property(element, 'align-center', context.model.get('_align_center'));
39 39 set_flex_property(element, 'align-end', context.model.get('_align_end'));
40 40 set_flex_property(element, 'box-flex0', context.model.get('_flex0'));
41 41 set_flex_property(element, 'box-flex1', context.model.get('_flex1'));
42 42 set_flex_property(element, 'box-flex2', context.model.get('_flex2'));
43 43 };
44 44
45 45
46 46
47 47 var ContainerModel = IPython.WidgetModel.extend({});
48 48 widget_manager.register_widget_model('ContainerWidgetModel', ContainerModel);
49 49
50 50 var ContainerView = IPython.WidgetView.extend({
51 51
52 52 render: function(){
53 53 this.$el
54 54 .addClass('widget-container');
55 55 this.children={};
56 56 this.update_children([], this.model.get('children'));
57 57 this.model.on('change:children', function(model, value, options) {
58 58 this.update_children(model.previous('children'), value);
59 59 }, this);
60 60 this.update()
61 61 },
62 62
63 63 update_children: function(old_list, new_list) {
64 64 this.$el.empty();
65 65 this.update_child_views(old_list, new_list);
66 66 _.each(new_list, function(element, index, list) {
67 67 this.$el.append(this.child_views[element].$el);
68 68 }, this)
69 69 },
70 70
71 71 update: function(){
72 72 set_flex_properties(this, this.$el);
73 73 return IPython.WidgetView.prototype.update.call(this);
74 74 },
75 75 });
76 76
77 77 widget_manager.register_widget_view('ContainerView', ContainerView);
78 78
79 79
80 80 var ModalView = IPython.WidgetView.extend({
81 81
82 82 render: function(){
83 83 var that = this;
84 84 this.children={};
85 85 this.update_children([], this.model.get('children'));
86 86 this.model.on('change:children', function(model, value, options) {
87 87 this.update_children(model.previous('children'), value);
88 88 }, this);
89 89
90 90 this.$el
91 91 .html('')
92 92 .on("remove", function(){
93 93 that.$window.remove();
94 94 });
95 95 this.$window = $('<div />')
96 96 .addClass('modal widget-modal')
97 97 .appendTo($('#notebook-container'))
98 98 .mousedown(function(){
99 99 that.bring_to_front();
100 100 });
101 101 this.$title_bar = $('<div />')
102 102 .addClass('popover-title')
103 103 .appendTo(this.$window)
104 104 .mousedown(function(){
105 105 that.bring_to_front();
106 106 });
107 107 this.$close = $('<button />')
108 108 .addClass('close icon-remove')
109 109 .css('margin-left', '5px')
110 110 .appendTo(this.$title_bar)
111 111 .click(function(){
112 112 that.hide();
113 113 event.stopPropagation();
114 114 });
115 115 this.$minimize = $('<button />')
116 116 .addClass('close icon-arrow-down')
117 117 .appendTo(this.$title_bar)
118 118 .click(function(){
119 119 that.popped_out = !that.popped_out;
120 120 if (!that.popped_out) {
121 121 that.$minimize
122 122 .removeClass('icon-arrow-down')
123 123 .addClass('icon-arrow-up');
124 124
125 125 that.$window
126 126 .draggable('destroy')
127 127 .resizable('destroy')
128 128 .removeClass('widget-modal modal')
129 129 .addClass('docked-widget-modal')
130 130 .detach()
131 131 .insertBefore(that.$show_button);
132 132 that.$show_button.hide();
133 133 that.$close.hide();
134 134 } else {
135 135 that.$minimize
136 136 .addClass('icon-arrow-down')
137 137 .removeClass('icon-arrow-up');
138 138
139 139 that.$window
140 140 .removeClass('docked-widget-modal')
141 141 .addClass('widget-modal modal')
142 142 .detach()
143 143 .appendTo($('#notebook-container'))
144 144 .draggable({handle: '.popover-title', snap: '#notebook, .modal', snapMode: 'both'})
145 145 .resizable()
146 146 .children('.ui-resizable-handle').show();
147 147 that.show();
148 148 that.$show_button.show();
149 149 that.$close.show();
150 150 }
151 151 event.stopPropagation();
152 152 });
153 153 this.$title = $('<div />')
154 154 .addClass('widget-modal-title')
155 155 .html('&nbsp;')
156 156 .appendTo(this.$title_bar);
157 157 this.$body = $('<div />')
158 158 .addClass('modal-body')
159 159 .addClass('widget-modal-body')
160 160 .addClass('widget-container')
161 161 .appendTo(this.$window);
162 162
163 163 this.$show_button = $('<button />')
164 164 .html('&nbsp;')
165 165 .addClass('btn btn-info widget-modal-show')
166 166 .appendTo(this.$el)
167 167 .click(function(){
168 168 that.show();
169 169 });
170 170
171 171 this.$window.draggable({handle: '.popover-title', snap: '#notebook, .modal', snapMode: 'both'});
172 172 this.$window.resizable();
173 173 this.$window.on('resize', function(){
174 174 that.$body.outerHeight(that.$window.innerHeight() - that.$title_bar.outerHeight());
175 175 });
176 176
177 177 this.$el_to_style = this.$body;
178 178 this._shown_once = false;
179 179 this.popped_out = true;
180 180 },
181 181
182 182 hide: function() {
183 183 this.$window.hide();
184 184 this.$show_button.removeClass('btn-info');
185 185 },
186 186
187 187 show: function() {
188 188 this.$show_button.addClass('btn-info');
189 189
190 190 this.$window.show();
191 191 if (this.popped_out) {
192 192 this.$window.css("positon", "absolute");
193 193 this.$window.css("top", "0px");
194 194 this.$window.css("left", Math.max(0, (($('body').outerWidth() - this.$window.outerWidth()) / 2) +
195 195 $(window).scrollLeft()) + "px");
196 196 this.bring_to_front();
197 197 }
198 198 },
199 199
200 200 bring_to_front: function() {
201 201 var $widget_modals = $(".widget-modal");
202 202 var max_zindex = 0;
203 203 $widget_modals.each(function (index, el){
204 204 max_zindex = Math.max(max_zindex, parseInt($(el).css('z-index')));
205 205 });
206 206
207 207 // Start z-index of widget modals at 2000
208 208 max_zindex = Math.max(max_zindex, 2000);
209 209
210 210 $widget_modals.each(function (index, el){
211 211 $el = $(el);
212 212 if (max_zindex == parseInt($el.css('z-index'))) {
213 213 $el.css('z-index', max_zindex - 1);
214 214 }
215 215 });
216 216 this.$window.css('z-index', max_zindex);
217 217 },
218 218
219 219 update_children: function(old_list, new_list) {
220 220 this.$el.empty();
221 221 this.update_child_views(old_list, new_list);
222 222 _.each(new_list, function(element, index, list) {
223 223 this.$body.append(this.child_views[element].$el);
224 224 }, this)
225 225 },
226 226
227 227 update: function(){
228 228 set_flex_properties(this, this.$body);
229 229
230 230 var description = this.model.get('description');
231 231 description = description.replace(/ /g, '&nbsp;', 'm');
232 232 description = description.replace(/\n/g, '<br>\n', 'm');
233 233 if (description.length === 0) {
234 234 this.$title.html('&nbsp;'); // Preserve title height
235 235 } else {
236 236 this.$title.html(description);
237 237 }
238 238
239 239 var button_text = this.model.get('button_text');
240 240 button_text = button_text.replace(/ /g, '&nbsp;', 'm');
241 241 button_text = button_text.replace(/\n/g, '<br>\n', 'm');
242 242 if (button_text.length === 0) {
243 243 this.$show_button.html('&nbsp;'); // Preserve button height
244 244 } else {
245 245 this.$show_button.html(button_text);
246 246 }
247 247
248 248 if (!this._shown_once) {
249 249 this._shown_once = true;
250 250 this.show();
251 251 }
252 252
253 253 return IPython.WidgetView.prototype.update.call(this);
254 254 },
255 255
256 256 _get_selector_element: function(selector) {
257 257
258 258 // Since the modal actually isn't within the $el in the DOM, we need to extend
259 259 // the selector logic to allow the user to set css on the modal if need be.
260 260 // The convention used is:
261 261 // "modal" - select the modal div
262 262 // "modal [selector]" - select element(s) within the modal div.
263 263 // "[selector]" - select elements within $el
264 264 // "" - select the $el_to_style
265 265 if (selector.substring(0, 5) == 'modal') {
266 266 if (selector == 'modal') {
267 267 return this.$window;
268 268 } else {
269 269 return this.$window.find(selector.substring(6));
270 270 }
271 271 } else {
272 272 return IPython.WidgetView.prototype._get_selector_element.call(this, selector);
273 273 }
274 274 },
275 275
276 276 });
277 277
278 278 widget_manager.register_widget_view('ModalView', ModalView);
279 279 });
@@ -1,20 +1,20 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // FloatWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18 var FloatWidgetModel = IPython.WidgetModel.extend({});
19 19 widget_manager.register_widget_model('FloatWidgetModel', FloatWidgetModel);
20 20 }); No newline at end of file
@@ -1,255 +1,255 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // FloatRangeWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18 var FloatRangeWidgetModel = IPython.WidgetModel.extend({});
19 19 widget_manager.register_widget_model('FloatRangeWidgetModel', FloatRangeWidgetModel);
20 20
21 21 var FloatSliderView = IPython.WidgetView.extend({
22 22
23 23 // Called when view is rendered.
24 24 render : function(){
25 25 this.$el
26 26 .addClass('widget-hbox-single')
27 27 .html('');
28 28 this.$label = $('<div />')
29 29 .appendTo(this.$el)
30 30 .addClass('widget-hlabel')
31 31 .hide();
32 32 this.$slider = $('<div />')
33 33 .slider({})
34 34 .addClass('slider');
35 35
36 36 // Put the slider in a container
37 37 this.$slider_container = $('<div />')
38 38 .addClass('widget-hslider')
39 39 .append(this.$slider);
40 40 this.$el_to_style = this.$slider_container; // Set default element to style
41 41 this.$el.append(this.$slider_container);
42 42
43 43 // Set defaults.
44 44 this.update();
45 45 },
46 46
47 47 // Handles: Backend -> Frontend Sync
48 48 // Frontent -> Frontend Sync
49 49 update : function(){
50 50 // Slider related keys.
51 51 var _keys = ['step', 'max', 'min', 'disabled'];
52 52 for (var index in _keys) {
53 53 var key = _keys[index];
54 54 if (this.model.get(key) !== undefined) {
55 55 this.$slider.slider("option", key, this.model.get(key));
56 56 }
57 57 }
58 58
59 59 // WORKAROUND FOR JQUERY SLIDER BUG.
60 60 // The horizontal position of the slider handle
61 61 // depends on the value of the slider at the time
62 62 // of orientation change. Before applying the new
63 63 // workaround, we set the value to the minimum to
64 64 // make sure that the horizontal placement of the
65 65 // handle in the vertical slider is always
66 66 // consistent.
67 67 var orientation = this.model.get('orientation');
68 68 var value = this.model.get('min');
69 69 this.$slider.slider('option', 'value', value);
70 70 this.$slider.slider('option', 'orientation', orientation);
71 71 value = this.model.get('value');
72 72 this.$slider.slider('option', 'value', value);
73 73
74 74 // Use the right CSS classes for vertical & horizontal sliders
75 75 if (orientation=='vertical') {
76 76 this.$slider_container
77 77 .removeClass('widget-hslider')
78 78 .addClass('widget-vslider');
79 79 this.$el
80 80 .removeClass('widget-hbox-single')
81 81 .addClass('widget-vbox-single');
82 82 this.$label
83 83 .removeClass('widget-hlabel')
84 84 .addClass('widget-vlabel');
85 85
86 86 } else {
87 87 this.$slider_container
88 88 .removeClass('widget-vslider')
89 89 .addClass('widget-hslider');
90 90 this.$el
91 91 .removeClass('widget-vbox-single')
92 92 .addClass('widget-hbox-single');
93 93 this.$label
94 94 .removeClass('widget-vlabel')
95 95 .addClass('widget-hlabel');
96 96 }
97 97
98 98 var description = this.model.get('description');
99 99 if (description.length === 0) {
100 100 this.$label.hide();
101 101 } else {
102 102 this.$label.html(description);
103 103 this.$label.show();
104 104 }
105 105 return IPython.WidgetView.prototype.update.call(this);
106 106 },
107 107
108 108 // Handles: User input
109 109 events: { "slide" : "handleSliderChange" },
110 110 handleSliderChange: function(e, ui) {
111 111 this.model.set('value', ui.value);
112 112 this.touch();
113 113 },
114 114 });
115 115
116 116 widget_manager.register_widget_view('FloatSliderView', FloatSliderView);
117 117
118 118
119 119 var FloatTextView = IPython.WidgetView.extend({
120 120
121 121 // Called when view is rendered.
122 122 render : function(){
123 123 this.$el
124 124 .addClass('widget-hbox-single')
125 125 .html('');
126 126 this.$label = $('<div />')
127 127 .appendTo(this.$el)
128 128 .addClass('widget-hlabel')
129 129 .hide();
130 130 this.$textbox = $('<input type="text" />')
131 131 .addClass('input')
132 132 .addClass('widget-numeric-text')
133 133 .appendTo(this.$el);
134 134 this.$el_to_style = this.$textbox; // Set default element to style
135 135 this.update(); // Set defaults.
136 136 },
137 137
138 138 // Handles: Backend -> Frontend Sync
139 139 // Frontent -> Frontend Sync
140 140 update : function(){
141 141 var value = this.model.get('value');
142 142 if (!this.changing && parseFloat(this.$textbox.val()) != value) {
143 143 this.$textbox.val(value);
144 144 }
145 145
146 146 if (this.model.get('disabled')) {
147 147 this.$textbox.attr('disabled','disabled');
148 148 } else {
149 149 this.$textbox.removeAttr('disabled');
150 150 }
151 151
152 152 var description = this.model.get('description');
153 153 if (description.length === 0) {
154 154 this.$label.hide();
155 155 } else {
156 156 this.$label.html(description);
157 157 this.$label.show();
158 158 }
159 159 return IPython.WidgetView.prototype.update.call(this);
160 160 },
161 161
162 162
163 163 events: {"keyup input" : "handleChanging",
164 164 "paste input" : "handleChanging",
165 165 "cut input" : "handleChanging",
166 166 "change input" : "handleChanged"}, // Fires only when control is validated or looses focus.
167 167
168 168 // Handles and validates user input.
169 169 handleChanging: function(e) {
170 170
171 171 // Try to parse value as a float.
172 172 var numericalValue = 0.0;
173 173 if (e.target.value !== '') {
174 174 numericalValue = parseFloat(e.target.value);
175 175 }
176 176
177 177 // If parse failed, reset value to value stored in model.
178 178 if (isNaN(numericalValue)) {
179 179 e.target.value = this.model.get('value');
180 180 } else if (!isNaN(numericalValue)) {
181 181 if (this.model.get('max') !== undefined) {
182 182 numericalValue = Math.min(this.model.get('max'), numericalValue);
183 183 }
184 184 if (this.model.get('min') !== undefined) {
185 185 numericalValue = Math.max(this.model.get('min'), numericalValue);
186 186 }
187 187
188 188 // Apply the value if it has changed.
189 189 if (numericalValue != this.model.get('value')) {
190 190 this.changing = true;
191 191 this.model.set('value', numericalValue);
192 192 this.touch();
193 193 this.changing = false;
194 194 }
195 195 }
196 196 },
197 197
198 198 // Applies validated input.
199 199 handleChanged: function(e) {
200 200 // Update the textbox
201 201 if (this.model.get('value') != e.target.value) {
202 202 e.target.value = this.model.get('value');
203 203 }
204 204 }
205 205 });
206 206
207 207 widget_manager.register_widget_view('FloatTextView', FloatTextView);
208 208
209 209
210 210 var ProgressView = IPython.WidgetView.extend({
211 211
212 212 // Called when view is rendered.
213 213 render : function(){
214 214 this.$el
215 215 .addClass('widget-hbox-single')
216 216 .html('');
217 217 this.$label = $('<div />')
218 218 .appendTo(this.$el)
219 219 .addClass('widget-hlabel')
220 220 .hide();
221 221 this.$progress = $('<div />')
222 222 .addClass('progress')
223 223 .addClass('widget-progress')
224 224 .appendTo(this.$el);
225 225 this.$el_to_style = this.$progress; // Set default element to style
226 226 this.$bar = $('<div />')
227 227 .addClass('bar')
228 228 .css('width', '50%')
229 229 .appendTo(this.$progress);
230 230 this.update(); // Set defaults.
231 231 },
232 232
233 233 // Handles: Backend -> Frontend Sync
234 234 // Frontent -> Frontend Sync
235 235 update : function(){
236 236 var value = this.model.get('value');
237 237 var max = this.model.get('max');
238 238 var min = this.model.get('min');
239 239 var percent = 100.0 * (value - min) / (max - min);
240 240 this.$bar.css('width', percent + '%');
241 241
242 242 var description = this.model.get('description');
243 243 if (description.length === 0) {
244 244 this.$label.hide();
245 245 } else {
246 246 this.$label.html(description);
247 247 this.$label.show();
248 248 }
249 249 return IPython.WidgetView.prototype.update.call(this);
250 250 },
251 251
252 252 });
253 253
254 254 widget_manager.register_widget_view('ProgressView', ProgressView);
255 255 });
@@ -1,55 +1,55 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // ImageWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18 var ImageWidgetModel = IPython.WidgetModel.extend({});
19 19 widget_manager.register_widget_model('ImageWidgetModel', ImageWidgetModel);
20 20
21 21 var ImageView = IPython.WidgetView.extend({
22 22
23 23 // Called when view is rendered.
24 24 render : function(){
25 25 this.setElement($("<img />"));
26 26 this.update(); // Set defaults.
27 27 },
28 28
29 29 // Handles: Backend -> Frontend Sync
30 30 // Frontent -> Frontend Sync
31 31 update : function(){
32 32 var image_src = 'data:image/' + this.model.get('image_format') + ';base64,' + this.model.get('_b64value');
33 33 this.$el.attr('src', image_src);
34 34
35 35 var width = this.model.get('width');
36 36 if (width !== undefined && width.length > 0) {
37 37 this.$el.attr('width', width);
38 38 } else {
39 39 this.$el.removeAttr('width');
40 40 }
41 41
42 42 var height = this.model.get('height');
43 43 if (height !== undefined && height.length > 0) {
44 44 this.$el.attr('height', height);
45 45 } else {
46 46 this.$el.removeAttr('height');
47 47 }
48 48 return IPython.WidgetView.prototype.update.call(this);
49 49 },
50 50
51 51 });
52 52
53 53 widget_manager.register_widget_view('ImageView', ImageView);
54 54
55 55 });
@@ -1,20 +1,20 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // IntWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18 var IntWidgetModel = IPython.WidgetModel.extend({});
19 19 widget_manager.register_widget_model('IntWidgetModel', IntWidgetModel);
20 20 }); No newline at end of file
@@ -1,207 +1,207 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // IntRangeWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18 var IntRangeWidgetModel = IPython.WidgetModel.extend({});
19 19 widget_manager.register_widget_model('IntRangeWidgetModel', IntRangeWidgetModel);
20 20
21 21 var IntSliderView = IPython.WidgetView.extend({
22 22
23 23 // Called when view is rendered.
24 24 render : function(){
25 25 this.$el
26 26 .addClass('widget-hbox-single')
27 27 .html('');
28 28 this.$label = $('<div />')
29 29 .appendTo(this.$el)
30 30 .addClass('widget-hlabel')
31 31 .hide();
32 32 this.$slider = $('<div />')
33 33 .slider({})
34 34 .addClass('slider');
35 35
36 36 // Put the slider in a container
37 37 this.$slider_container = $('<div />')
38 38 .addClass('widget-hslider')
39 39 .append(this.$slider);
40 40 this.$el_to_style = this.$slider_container; // Set default element to style
41 41 this.$el.append(this.$slider_container);
42 42
43 43 // Set defaults.
44 44 this.update();
45 45 },
46 46
47 47 // Handles: Backend -> Frontend Sync
48 48 // Frontent -> Frontend Sync
49 49 update : function(){
50 50 // Slider related keys.
51 51 var _keys = ['step', 'max', 'min', 'disabled'];
52 52 for (var index in _keys) {
53 53 var key = _keys[index];
54 54 if (this.model.get(key) !== undefined) {
55 55 this.$slider.slider("option", key, this.model.get(key));
56 56 }
57 57 }
58 58
59 59 // WORKAROUND FOR JQUERY SLIDER BUG.
60 60 // The horizontal position of the slider handle
61 61 // depends on the value of the slider at the time
62 62 // of orientation change. Before applying the new
63 63 // workaround, we set the value to the minimum to
64 64 // make sure that the horizontal placement of the
65 65 // handle in the vertical slider is always
66 66 // consistent.
67 67 var orientation = this.model.get('orientation');
68 68 var value = this.model.get('min');
69 69 this.$slider.slider('option', 'value', value);
70 70 this.$slider.slider('option', 'orientation', orientation);
71 71 value = this.model.get('value');
72 72 this.$slider.slider('option', 'value', value);
73 73
74 74 // Use the right CSS classes for vertical & horizontal sliders
75 75 if (orientation=='vertical') {
76 76 this.$slider_container
77 77 .removeClass('widget-hslider')
78 78 .addClass('widget-vslider');
79 79 this.$el
80 80 .removeClass('widget-hbox-single')
81 81 .addClass('widget-vbox-single');
82 82 this.$label
83 83 .removeClass('widget-hlabel')
84 84 .addClass('widget-vlabel');
85 85
86 86 } else {
87 87 this.$slider_container
88 88 .removeClass('widget-vslider')
89 89 .addClass('widget-hslider');
90 90 this.$el
91 91 .removeClass('widget-vbox-single')
92 92 .addClass('widget-hbox-single');
93 93 this.$label
94 94 .removeClass('widget-vlabel')
95 95 .addClass('widget-hlabel');
96 96 }
97 97
98 98 var description = this.model.get('description');
99 99 if (description.length === 0) {
100 100 this.$label.hide();
101 101 } else {
102 102 this.$label.html(description);
103 103 this.$label.show();
104 104 }
105 105 return IPython.WidgetView.prototype.update.call(this);
106 106 },
107 107
108 108 // Handles: User input
109 109 events: { "slide" : "handleSliderChange" },
110 110 handleSliderChange: function(e, ui) {
111 111 this.model.set('value', ~~ui.value); // Double bit-wise not to truncate decimel
112 112 this.touch();
113 113 },
114 114 });
115 115
116 116 widget_manager.register_widget_view('IntSliderView', IntSliderView);
117 117
118 118 var IntTextView = IPython.WidgetView.extend({
119 119
120 120 // Called when view is rendered.
121 121 render : function(){
122 122 this.$el
123 123 .addClass('widget-hbox-single')
124 124 .html('');
125 125 this.$label = $('<div />')
126 126 .appendTo(this.$el)
127 127 .addClass('widget-hlabel')
128 128 .hide();
129 129 this.$textbox = $('<input type="text" />')
130 130 .addClass('input')
131 131 .addClass('widget-numeric-text')
132 132 .appendTo(this.$el);
133 133 this.$el_to_style = this.$textbox; // Set default element to style
134 134 this.update(); // Set defaults.
135 135 },
136 136
137 137 // Handles: Backend -> Frontend Sync
138 138 // Frontent -> Frontend Sync
139 139 update : function(){
140 140 var value = this.model.get('value');
141 141 if (!this.changing && parseInt(this.$textbox.val()) != value) {
142 142 this.$textbox.val(value);
143 143 }
144 144
145 145 if (this.model.get('disabled')) {
146 146 this.$textbox.attr('disabled','disabled');
147 147 } else {
148 148 this.$textbox.removeAttr('disabled');
149 149 }
150 150
151 151 var description = this.model.get('description');
152 152 if (description.length === 0) {
153 153 this.$label.hide();
154 154 } else {
155 155 this.$label.html(description);
156 156 this.$label.show();
157 157 }
158 158 return IPython.WidgetView.prototype.update.call(this);
159 159 },
160 160
161 161
162 162 events: {"keyup input" : "handleChanging",
163 163 "paste input" : "handleChanging",
164 164 "cut input" : "handleChanging",
165 165 "change input" : "handleChanged"}, // Fires only when control is validated or looses focus.
166 166
167 167 // Handles and validates user input.
168 168 handleChanging: function(e) {
169 169
170 170 // Try to parse value as a float.
171 171 var numericalValue = 0;
172 172 if (e.target.value !== '') {
173 173 numericalValue = parseInt(e.target.value);
174 174 }
175 175
176 176 // If parse failed, reset value to value stored in model.
177 177 if (isNaN(numericalValue)) {
178 178 e.target.value = this.model.get('value');
179 179 } else if (!isNaN(numericalValue)) {
180 180 if (this.model.get('max') !== undefined) {
181 181 numericalValue = Math.min(this.model.get('max'), numericalValue);
182 182 }
183 183 if (this.model.get('min') !== undefined) {
184 184 numericalValue = Math.max(this.model.get('min'), numericalValue);
185 185 }
186 186
187 187 // Apply the value if it has changed.
188 188 if (numericalValue != this.model.get('value')) {
189 189 this.changing = true;
190 190 this.model.set('value', numericalValue);
191 191 this.touch();
192 192 this.changing = false;
193 193 }
194 194 }
195 195 },
196 196
197 197 // Applies validated input.
198 198 handleChanged: function(e) {
199 199 // Update the textbox
200 200 if (this.model.get('value') != e.target.value) {
201 201 e.target.value = this.model.get('value');
202 202 }
203 203 }
204 204 });
205 205
206 206 widget_manager.register_widget_view('IntTextView', IntTextView);
207 207 });
@@ -1,208 +1,208 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // MultiContainerWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18 var MulticontainerModel = IPython.WidgetModel.extend({});
19 19 widget_manager.register_widget_model('MulticontainerWidgetModel', MulticontainerModel);
20 20
21 21 var AccordionView = IPython.WidgetView.extend({
22 22
23 23 render: function(){
24 24 var guid = 'accordion' + IPython.utils.uuid();
25 25 this.$el
26 26 .attr('id', guid)
27 27 .addClass('accordion');
28 28 this.containers = [];
29 29 this.update_children([], this.model.get('children'));
30 30 this.model.on('change:children', function(model, value, options) {
31 31 this.update_children(model.previous('children'), value);
32 32 }, this);
33 33 },
34 34
35 35 update_children: function(old_list, new_list) {
36 36 _.each(this.containers, function(element, index, list) {
37 37 element.remove();
38 38 }, this);
39 39 this.containers = [];
40 40 this.update_child_views(old_list, new_list);
41 41 _.each(new_list, function(element, index, list) {
42 42 this.add_child_view(this.child_views[element]);
43 43 }, this)
44 44 },
45 45
46 46
47 47 update: function() {
48 48 // Set tab titles
49 49 var titles = this.model.get('_titles');
50 50 for (var page_index in titles) {
51 51
52 52 var accordian = this.containers[page_index];
53 53 if (accordian !== undefined) {
54 54 accordian
55 55 .find('.accordion-heading')
56 56 .find('.accordion-toggle')
57 57 .html(titles[page_index]);
58 58 }
59 59 }
60 60
61 61 // Set selected page
62 62 var selected_index = this.model.get("selected_index");
63 63 if (0 <= selected_index && selected_index < this.containers.length) {
64 64 for (var index in this.containers) {
65 65 if (index==selected_index) {
66 66 this.containers[index].find('.accordion-body').collapse('show');
67 67 } else {
68 68 this.containers[index].find('.accordion-body').collapse('hide');
69 69 }
70 70
71 71 }
72 72 }
73 73
74 74 return IPython.WidgetView.prototype.update.call(this);
75 75 },
76 76
77 77 add_child_view: function(view) {
78 78
79 79 var index = this.containers.length;
80 80 var uuid = IPython.utils.uuid();
81 81 var accordion_group = $('<div />')
82 82 .addClass('accordion-group')
83 83 .appendTo(this.$el);
84 84 var accordion_heading = $('<div />')
85 85 .addClass('accordion-heading')
86 86 .appendTo(accordion_group);
87 87 var that = this;
88 88 var accordion_toggle = $('<a />')
89 89 .addClass('accordion-toggle')
90 90 .attr('data-toggle', 'collapse')
91 91 .attr('data-parent', '#' + this.$el.attr('id'))
92 92 .attr('href', '#' + uuid)
93 93 .click(function(evt){
94 94 that.model.set("selected_index", index);
95 95 that.touch();
96 96 })
97 97 .html('Page ' + index)
98 98 .appendTo(accordion_heading);
99 99 var accordion_body = $('<div />', {id: uuid})
100 100 .addClass('accordion-body collapse')
101 101 .appendTo(accordion_group);
102 102 var accordion_inner = $('<div />')
103 103 .addClass('accordion-inner')
104 104 .appendTo(accordion_body);
105 105 this.containers.push(accordion_group);
106 106 accordion_inner.append(view.$el);
107 107
108 108 this.update();
109 109
110 110 // Stupid workaround to close the bootstrap accordion tabs which
111 111 // open by default even though they don't have the `in` class
112 112 // attached to them. For some reason a delay is required.
113 113 // TODO: Better fix.
114 114 setTimeout(function(){ that.update(); }, 500);
115 115 },
116 116 });
117 117
118 118 widget_manager.register_widget_view('AccordionView', AccordionView);
119 119
120 120 var TabView = IPython.WidgetView.extend({
121 121
122 122 initialize: function() {
123 123 this.containers = [];
124 124 IPython.WidgetView.prototype.initialize.apply(this, arguments);
125 125 },
126 126
127 127 render: function(){
128 128 var uuid = 'tabs'+IPython.utils.uuid();
129 129 var that = this;
130 130 this.$tabs = $('<div />', {id: uuid})
131 131 .addClass('nav')
132 132 .addClass('nav-tabs')
133 133 .appendTo(this.$el);
134 134 this.$tab_contents = $('<div />', {id: uuid + 'Content'})
135 135 .addClass('tab-content')
136 136 .appendTo(this.$el);
137 137 this.containers = [];
138 138 this.update_children([], this.model.get('children'));
139 139 this.model.on('change:children', function(model, value, options) {
140 140 this.update_children(model.previous('children'), value);
141 141 }, this);
142 142 },
143 143
144 144 update_children: function(old_list, new_list) {
145 145 _.each(this.containers, function(element, index, list) {
146 146 element.remove();
147 147 }, this);
148 148 this.containers = [];
149 149 this.update_child_views(old_list, new_list);
150 150 _.each(new_list, function(element, index, list) {
151 151 this.add_child_view(this.child_views[element]);
152 152 }, this)
153 153 },
154 154
155 155 update: function() {
156 156 // Set tab titles
157 157 var titles = this.model.get('_titles');
158 158 for (var page_index in titles) {
159 159 var tab_text = this.containers[page_index];
160 160 if (tab_text !== undefined) {
161 161 tab_text.html(titles[page_index]);
162 162 }
163 163 }
164 164
165 165 var selected_index = this.model.get('selected_index');
166 166 if (0 <= selected_index && selected_index < this.containers.length) {
167 167 this.select_page(selected_index);
168 168 }
169 169
170 170 return IPython.WidgetView.prototype.update.call(this);
171 171 },
172 172
173 173 add_child_view: function(view) {
174 174 var index = this.containers.length;
175 175 var uuid = IPython.utils.uuid();
176 176
177 177 var that = this;
178 178 var tab = $('<li />')
179 179 .css('list-style-type', 'none')
180 180 .appendTo(this.$tabs);
181 181 var tab_text = $('<a />')
182 182 .attr('href', '#' + uuid)
183 183 .attr('data-toggle', 'tab')
184 184 .html('Page ' + index)
185 185 .appendTo(tab)
186 186 .click(function (e) {
187 187 that.model.set("selected_index", index);
188 188 that.touch();
189 189 that.select_page(index);
190 190 });
191 191 this.containers.push(tab_text);
192 192
193 193 var contents_div = $('<div />', {id: uuid})
194 194 .addClass('tab-pane')
195 195 .addClass('fade')
196 196 .append(view.$el)
197 197 .appendTo(this.$tab_contents);
198 198 },
199 199
200 200 select_page: function(index) {
201 201 this.$tabs.find('li')
202 202 .removeClass('active');
203 203 this.containers[index].tab('show');
204 204 },
205 205 });
206 206
207 207 widget_manager.register_widget_view('TabView', TabView);
208 208 });
@@ -1,360 +1,360 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // SelectionWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18 var SelectionWidgetModel = IPython.WidgetModel.extend({});
19 19 widget_manager.register_widget_model('SelectionWidgetModel', SelectionWidgetModel);
20 20
21 21 var DropdownView = IPython.WidgetView.extend({
22 22
23 23 // Called when view is rendered.
24 24 render : function(){
25 25
26 26 this.$el
27 27 .addClass('widget-hbox-single')
28 28 .html('');
29 29 this.$label = $('<div />')
30 30 .appendTo(this.$el)
31 31 .addClass('widget-hlabel')
32 32 .hide();
33 33 this.$buttongroup = $('<div />')
34 34 .addClass('widget_item')
35 35 .addClass('btn-group')
36 36 .appendTo(this.$el);
37 37 this.$el_to_style = this.$buttongroup; // Set default element to style
38 38 this.$droplabel = $('<button />')
39 39 .addClass('btn')
40 40 .addClass('widget-combo-btn')
41 41 .html('&nbsp;')
42 42 .appendTo(this.$buttongroup);
43 43 this.$dropbutton = $('<button />')
44 44 .addClass('btn')
45 45 .addClass('dropdown-toggle')
46 46 .addClass('widget-combo-carrot-btn')
47 47 .attr('data-toggle', 'dropdown')
48 48 .html('<span class="caret"></span>')
49 49 .appendTo(this.$buttongroup);
50 50 this.$droplist = $('<ul />')
51 51 .addClass('dropdown-menu')
52 52 .appendTo(this.$buttongroup);
53 53
54 54 // Set defaults.
55 55 this.update();
56 56 },
57 57
58 58 // Handles: Backend -> Frontend Sync
59 59 // Frontent -> Frontend Sync
60 60 update : function(){
61 61
62 62 var selected_item_text = this.model.get('value');
63 63 selected_item_text = selected_item_text.replace(/ /g, '&nbsp;');
64 64 selected_item_text = selected_item_text.replace(/\n/g, '<br>\n');
65 65 if (selected_item_text.length === 0) {
66 66 this.$droplabel.html('&nbsp;');
67 67 } else {
68 68 this.$droplabel.html(selected_item_text);
69 69 }
70 70
71 71 var items = this.model.get('values');
72 72 this.$droplist.html('');
73 73 for (var index in items) {
74 74 var that = this;
75 75 var item_button = $('<a href="#"/>')
76 76 .html(items[index])
77 77 .on('click', $.proxy(this.handle_click, this));
78 78 this.$droplist.append($('<li />').append(item_button));
79 79 }
80 80
81 81 if (this.model.get('disabled')) {
82 82 this.$buttongroup.attr('disabled','disabled');
83 83 this.$droplabel.attr('disabled','disabled');
84 84 this.$dropbutton.attr('disabled','disabled');
85 85 this.$droplist.attr('disabled','disabled');
86 86 } else {
87 87 this.$buttongroup.removeAttr('disabled');
88 88 this.$droplabel.removeAttr('disabled');
89 89 this.$dropbutton.removeAttr('disabled');
90 90 this.$droplist.removeAttr('disabled');
91 91 }
92 92
93 93 var description = this.model.get('description');
94 94 if (description.length === 0) {
95 95 this.$label.hide();
96 96 } else {
97 97 this.$label.html(description);
98 98 this.$label.show();
99 99 }
100 100 return IPython.WidgetView.prototype.update.call(this);
101 101 },
102 102
103 103 // Handle when a value is clicked.
104 104 handle_click: function (e) {
105 105 this.model.set('value', $(e.target).html(), this);
106 106 this.touch();
107 107 },
108 108
109 109 });
110 110
111 111 widget_manager.register_widget_view('DropdownView', DropdownView);
112 112
113 113 var RadioButtonsView = IPython.WidgetView.extend({
114 114
115 115 // Called when view is rendered.
116 116 render : function(){
117 117 this.$el
118 118 .addClass('widget-hbox')
119 119 .html('');
120 120 this.$label = $('<div />')
121 121 .appendTo(this.$el)
122 122 .addClass('widget-hlabel')
123 123 .hide();
124 124 this.$container = $('<div />')
125 125 .appendTo(this.$el)
126 126 .addClass('widget-container')
127 127 .addClass('vbox');
128 128 this.$el_to_style = this.$container; // Set default element to style
129 129 this.update();
130 130 },
131 131
132 132 // Handles: Backend -> Frontend Sync
133 133 // Frontent -> Frontend Sync
134 134 update : function(){
135 135
136 136 // Add missing items to the DOM.
137 137 var items = this.model.get('values');
138 138 var disabled = this.model.get('disabled');
139 139 for (var index in items) {
140 140 var item_query = ' :input[value="' + items[index] + '"]';
141 141 if (this.$el.find(item_query).length === 0) {
142 142 var $label = $('<label />')
143 143 .addClass('radio')
144 144 .html(items[index])
145 145 .appendTo(this.$container);
146 146
147 147 $('<input />')
148 148 .attr('type', 'radio')
149 149 .addClass(this.model)
150 150 .val(items[index])
151 151 .prependTo($label)
152 152 .on('click', $.proxy(this.handle_click, this));
153 153 }
154 154
155 155 var $item_element = this.$container.find(item_query);
156 156 if (this.model.get('value') == items[index]) {
157 157 $item_element.prop('checked', true);
158 158 } else {
159 159 $item_element.prop('checked', false);
160 160 }
161 161 $item_element.prop('disabled', disabled);
162 162 }
163 163
164 164 // Remove items that no longer exist.
165 165 this.$container.find('input').each(function(i, obj) {
166 166 var value = $(obj).val();
167 167 var found = false;
168 168 for (var index in items) {
169 169 if (items[index] == value) {
170 170 found = true;
171 171 break;
172 172 }
173 173 }
174 174
175 175 if (!found) {
176 176 $(obj).parent().remove();
177 177 }
178 178 });
179 179
180 180 var description = this.model.get('description');
181 181 if (description.length === 0) {
182 182 this.$label.hide();
183 183 } else {
184 184 this.$label.html(description);
185 185 this.$label.show();
186 186 }
187 187 return IPython.WidgetView.prototype.update.call(this);
188 188 },
189 189
190 190 // Handle when a value is clicked.
191 191 handle_click: function (e) {
192 192 this.model.set('value', $(e.target).val(), this);
193 193 this.touch();
194 194 },
195 195 });
196 196
197 197 widget_manager.register_widget_view('RadioButtonsView', RadioButtonsView);
198 198
199 199
200 200 var ToggleButtonsView = IPython.WidgetView.extend({
201 201
202 202 // Called when view is rendered.
203 203 render : function(){
204 204 this.$el
205 205 .addClass('widget-hbox-single')
206 206 .html('');
207 207 this.$label = $('<div />')
208 208 .appendTo(this.$el)
209 209 .addClass('widget-hlabel')
210 210 .hide();
211 211 this.$buttongroup = $('<div />')
212 212 .addClass('btn-group')
213 213 .attr('data-toggle', 'buttons-radio')
214 214 .appendTo(this.$el);
215 215 this.$el_to_style = this.$buttongroup; // Set default element to style
216 216 this.update();
217 217 },
218 218
219 219 // Handles: Backend -> Frontend Sync
220 220 // Frontent -> Frontend Sync
221 221 update : function(){
222 222
223 223 // Add missing items to the DOM.
224 224 var items = this.model.get('values');
225 225 var disabled = this.model.get('disabled');
226 226 for (var index in items) {
227 227 var item_query = ' :contains("' + items[index] + '")';
228 228 if (this.$buttongroup.find(item_query).length === 0) {
229 229 $('<button />')
230 230 .attr('type', 'button')
231 231 .addClass('btn')
232 232 .html(items[index])
233 233 .appendTo(this.$buttongroup)
234 234 .on('click', $.proxy(this.handle_click, this));
235 235 }
236 236
237 237 var $item_element = this.$buttongroup.find(item_query);
238 238 if (this.model.get('value') == items[index]) {
239 239 $item_element.addClass('active');
240 240 } else {
241 241 $item_element.removeClass('active');
242 242 }
243 243 $item_element.prop('disabled', disabled);
244 244 }
245 245
246 246 // Remove items that no longer exist.
247 247 this.$buttongroup.find('button').each(function(i, obj) {
248 248 var value = $(obj).html();
249 249 var found = false;
250 250 for (var index in items) {
251 251 if (items[index] == value) {
252 252 found = true;
253 253 break;
254 254 }
255 255 }
256 256
257 257 if (!found) {
258 258 $(obj).remove();
259 259 }
260 260 });
261 261
262 262 var description = this.model.get('description');
263 263 if (description.length === 0) {
264 264 this.$label.hide();
265 265 } else {
266 266 this.$label.html(description);
267 267 this.$label.show();
268 268 }
269 269 return IPython.WidgetView.prototype.update.call(this);
270 270 },
271 271
272 272 // Handle when a value is clicked.
273 273 handle_click: function (e) {
274 274 this.model.set('value', $(e.target).html(), this);
275 275 this.touch();
276 276 },
277 277
278 278 });
279 279
280 280 widget_manager.register_widget_view('ToggleButtonsView', ToggleButtonsView);
281 281
282 282 var ListBoxView = IPython.WidgetView.extend({
283 283
284 284 // Called when view is rendered.
285 285 render : function(){
286 286 this.$el
287 287 .addClass('widget-hbox')
288 288 .html('');
289 289 this.$label = $('<div />')
290 290 .appendTo(this.$el)
291 291 .addClass('widget-hlabel')
292 292 .hide();
293 293 this.$listbox = $('<select />')
294 294 .addClass('widget-listbox')
295 295 .attr('size', 6)
296 296 .appendTo(this.$el);
297 297 this.$el_to_style = this.$listbox; // Set default element to style
298 298 this.update();
299 299 },
300 300
301 301 // Handles: Backend -> Frontend Sync
302 302 // Frontent -> Frontend Sync
303 303 update : function(){
304 304
305 305 // Add missing items to the DOM.
306 306 var items = this.model.get('values');
307 307 for (var index in items) {
308 308 var item_query = ' :contains("' + items[index] + '")';
309 309 if (this.$listbox.find(item_query).length === 0) {
310 310 $('<option />')
311 311 .html(items[index])
312 312 .attr('value', items[index])
313 313 .appendTo(this.$listbox)
314 314 .on('click', $.proxy(this.handle_click, this));
315 315 }
316 316 }
317 317
318 318 // Select the correct element
319 319 this.$listbox.val(this.model.get('value'));
320 320
321 321 // Disable listbox if needed
322 322 var disabled = this.model.get('disabled');
323 323 this.$listbox.prop('disabled', disabled);
324 324
325 325 // Remove items that no longer exist.
326 326 this.$listbox.find('option').each(function(i, obj) {
327 327 var value = $(obj).html();
328 328 var found = false;
329 329 for (var index in items) {
330 330 if (items[index] == value) {
331 331 found = true;
332 332 break;
333 333 }
334 334 }
335 335
336 336 if (!found) {
337 337 $(obj).remove();
338 338 }
339 339 });
340 340
341 341 var description = this.model.get('description');
342 342 if (description.length === 0) {
343 343 this.$label.hide();
344 344 } else {
345 345 this.$label.html(description);
346 346 this.$label.show();
347 347 }
348 348 return IPython.WidgetView.prototype.update.call(this);
349 349 },
350 350
351 351 // Handle when a value is clicked.
352 352 handle_click: function (e) {
353 353 this.model.set('value', $(e.target).html(), this);
354 354 this.touch();
355 355 },
356 356
357 357 });
358 358
359 359 widget_manager.register_widget_view('ListBoxView', ListBoxView);
360 360 });
@@ -1,188 +1,188 b''
1 1 //----------------------------------------------------------------------------
2 2 // Copyright (C) 2013 The IPython Development Team
3 3 //
4 4 // Distributed under the terms of the BSD License. The full license is in
5 5 // the file COPYING, distributed as part of this software.
6 6 //----------------------------------------------------------------------------
7 7
8 8 //============================================================================
9 9 // StringWidget
10 10 //============================================================================
11 11
12 12 /**
13 13 * @module IPython
14 14 * @namespace IPython
15 15 **/
16 16
17 define(["notebook/js/widgets/base"], function(widget_manager){
17 define(["notebook/js/widgets/widget"], function(widget_manager){
18 18 var StringWidgetModel = IPython.WidgetModel.extend({});
19 19 widget_manager.register_widget_model('StringWidgetModel', StringWidgetModel);
20 20
21 21 var HTMLView = IPython.WidgetView.extend({
22 22
23 23 // Called when view is rendered.
24 24 render : function(){
25 25 this.update(); // Set defaults.
26 26 },
27 27
28 28 // Handles: Backend -> Frontend Sync
29 29 // Frontent -> Frontend Sync
30 30 update : function(){
31 31 this.$el.html(this.model.get('value'));
32 32 return IPython.WidgetView.prototype.update.call(this);
33 33 },
34 34
35 35 });
36 36
37 37 widget_manager.register_widget_view('HTMLView', HTMLView);
38 38
39 39
40 40 var LatexView = IPython.WidgetView.extend({
41 41
42 42 // Called when view is rendered.
43 43 render : function(){
44 44 this.update(); // Set defaults.
45 45 },
46 46
47 47 // Handles: Backend -> Frontend Sync
48 48 // Frontent -> Frontend Sync
49 49 update : function(){
50 50 this.$el.html(this.model.get('value'));
51 51 MathJax.Hub.Queue(["Typeset",MathJax.Hub,this.$el.get(0)]);
52 52
53 53 return IPython.WidgetView.prototype.update.call(this);
54 54 },
55 55
56 56 });
57 57
58 58 widget_manager.register_widget_view('LatexView', LatexView);
59 59
60 60 var TextAreaView = IPython.WidgetView.extend({
61 61
62 62 // Called when view is rendered.
63 63 render: function(){
64 64 this.$el
65 65 .addClass('widget-hbox')
66 66 .html('');
67 67 this.$label = $('<div />')
68 68 .appendTo(this.$el)
69 69 .addClass('widget-hlabel')
70 70 .hide();
71 71 this.$textbox = $('<textarea />')
72 72 .attr('rows', 5)
73 73 .addClass('widget-text')
74 74 .appendTo(this.$el);
75 75 this.$el_to_style = this.$textbox; // Set default element to style
76 76 this.update(); // Set defaults.
77 77
78 78 this.model.on('msg:custom', $.proxy(this._handle_textarea_msg, this));
79 79 },
80 80
81 81
82 82 _handle_textarea_msg: function (content){
83 83 if (content.method == "scroll_to_bottom") {
84 84 this.scroll_to_bottom();
85 85 }
86 86 },
87 87
88 88
89 89 scroll_to_bottom: function (){
90 90 this.$textbox.scrollTop(this.$textbox[0].scrollHeight);
91 91 },
92 92
93 93
94 94 // Handles: Backend -> Frontend Sync
95 95 // Frontent -> Frontend Sync
96 96 update: function(){
97 97 if (!this.user_invoked_update) {
98 98 this.$textbox.val(this.model.get('value'));
99 99 }
100 100
101 101 var disabled = this.model.get('disabled');
102 102 this.$textbox.prop('disabled', disabled);
103 103
104 104 var description = this.model.get('description');
105 105 if (description.length === 0) {
106 106 this.$label.hide();
107 107 } else {
108 108 this.$label.html(description);
109 109 this.$label.show();
110 110 }
111 111 return IPython.WidgetView.prototype.update.call(this);
112 112 },
113 113
114 114 events: {"keyup textarea": "handleChanging",
115 115 "paste textarea": "handleChanging",
116 116 "cut textarea": "handleChanging"},
117 117
118 118 // Handles and validates user input.
119 119 handleChanging: function(e) {
120 120 this.user_invoked_update = true;
121 121 this.model.set('value', e.target.value);
122 122 this.touch();
123 123 this.user_invoked_update = false;
124 124 },
125 125 });
126 126
127 127 widget_manager.register_widget_view('TextAreaView', TextAreaView);
128 128
129 129 var TextBoxView = IPython.WidgetView.extend({
130 130
131 131 // Called when view is rendered.
132 132 render: function(){
133 133 this.$el
134 134 .addClass('widget-hbox-single')
135 135 .html('');
136 136 this.$label = $('<div />')
137 137 .addClass('widget-hlabel')
138 138 .appendTo(this.$el)
139 139 .hide();
140 140 this.$textbox = $('<input type="text" />')
141 141 .addClass('input')
142 142 .addClass('widget-text')
143 143 .appendTo(this.$el);
144 144 this.$el_to_style = this.$textbox; // Set default element to style
145 145 this.update(); // Set defaults.
146 146 },
147 147
148 148 // Handles: Backend -> Frontend Sync
149 149 // Frontent -> Frontend Sync
150 150 update: function(){
151 151 if (this.$textbox.val() != this.model.get('value')) {
152 152 this.$textbox.val(this.model.get('value'));
153 153 }
154 154
155 155 var disabled = this.model.get('disabled');
156 156 this.$textbox.prop('disabled', disabled);
157 157
158 158 var description = this.model.get('description');
159 159 if (description.length === 0) {
160 160 this.$label.hide();
161 161 } else {
162 162 this.$label.html(description);
163 163 this.$label.show();
164 164 }
165 165 return IPython.WidgetView.prototype.update.call(this);
166 166 },
167 167
168 168 events: {"keyup input": "handleChanging",
169 169 "paste input": "handleChanging",
170 170 "cut input": "handleChanging",
171 171 "keypress input": "handleKeypress"},
172 172
173 173 // Handles and validates user input.
174 174 handleChanging: function(e) {
175 175 this.model.set('value', e.target.value);
176 176 this.touch();
177 177 },
178 178
179 179 // Handles text submition
180 180 handleKeypress: function(e) {
181 181 if (e.keyCode == 13) { // Return key
182 182 this.send({event: 'submit'});
183 183 }
184 184 },
185 185 });
186 186
187 187 widget_manager.register_widget_view('TextBoxView', TextBoxView);
188 188 });
General Comments 0
You need to be logged in to leave comments. Login now