Skip to content

Commit 82687f0

Browse files
authored
Merge branch 'master' into chlog8
2 parents 895be5c + ad14ad1 commit 82687f0

File tree

10 files changed

+310
-123
lines changed

10 files changed

+310
-123
lines changed

docs/source/examples/Widget List.ipynb

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1388,9 +1388,9 @@
13881388
"cell_type": "markdown",
13891389
"metadata": {},
13901390
"source": [
1391-
"### Stacked\n",
1391+
"### Stack\n",
13921392
"\n",
1393-
"The `Stacked` widget can have multiple children widgets as for `Tab` and `Accordion`, but only shows one at a time depending on the value of ``selected_index``:"
1393+
"The `Stack` widget can have multiple children widgets as for `Tab` and `Accordion`, but only shows one at a time depending on the value of ``selected_index``:"
13941394
]
13951395
},
13961396
{
@@ -1401,8 +1401,8 @@
14011401
"source": [
14021402
"button = widgets.Button(description='Click here')\n",
14031403
"slider = widgets.IntSlider()\n",
1404-
"stacked = widgets.Stacked([button, slider], selected_index=0)\n",
1405-
"stacked # will show only the button"
1404+
"stack = widgets.Stack([button, slider], selected_index=0)\n",
1405+
"stack # will show only the button"
14061406
]
14071407
},
14081408
{
@@ -1419,15 +1419,15 @@
14191419
"outputs": [],
14201420
"source": [
14211421
"dropdown = widgets.Dropdown(options=['button', 'slider'])\n",
1422-
"widgets.jslink((dropdown, 'index'), (stacked, 'selected_index'))\n",
1423-
"widgets.VBox([dropdown, stacked])"
1422+
"widgets.jslink((dropdown, 'index'), (stack, 'selected_index'))\n",
1423+
"widgets.VBox([dropdown, stack])"
14241424
]
14251425
},
14261426
{
14271427
"cell_type": "markdown",
14281428
"metadata": {},
14291429
"source": [
1430-
"### Accordion, Tab, and Stacked use `selected_index`, not value\n",
1430+
"### Accordion, Tab, and Stack use `selected_index`, not value\n",
14311431
"\n",
14321432
"Unlike the rest of the widgets discussed earlier, the container widgets `Accordion` and `Tab` update their `selected_index` attribute when the user changes which accordion or tab is selected. That means that you can both see what the user is doing *and* programmatically set what the user sees by setting the value of `selected_index`.\n",
14331433
"\n",

docs/source/migration_guides.md

Lines changed: 26 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -88,7 +88,7 @@ The ``DOMWidgetView.pWidget`` property has been renamed ``DOMWidgetView.luminoWi
8888
+ this.luminoWidget
8989
```
9090

91-
The ``DOMWidgetView.processPhosphorMessage`` method has been renamed ``DOMWidgetView.processLuminoMessage``. If you want to support both ipywidgets 7.x and 8.x, you should implement both methods:
91+
The ``DOMWidgetView.processPhosphorMessage`` method has been renamed ``DOMWidgetView.processLuminoMessage``. If you want to support both ipywidgets 7.x and 8.x, you should implement both methods and call the correct super method:
9292

9393
```diff
9494
- processPhosphorMessage(msg: Message): void {
@@ -109,15 +109,15 @@ The ``DOMWidgetView.processPhosphorMessage`` method has been renamed ``DOMWidget
109109
+ }
110110
+
111111
+ processPhosphorMessage(msg: Message): void {
112-
+ this._processLuminoMessage(msg, (DOMWidgetView as any).processPhosphorMessage);
112+
+ this._processLuminoMessage(msg, super.processPhosphorMessage);
113113
+ }
114114
+
115115
+ processLuminoMessage(msg: Message): void {
116-
+ this._processLuminoMessage(msg, (DOMWidgetView as any).processLuminoMessage);
116+
+ this._processLuminoMessage(msg, super.processLuminoMessage);
117117
+ }
118118
```
119119

120-
I you're dropping ipywidgets 7.x support, you can simply rename the `processPhosphorMessage` method into `processLuminoMessage`.
120+
If you're dropping ipywidgets 7.x support, you can simply rename the `processPhosphorMessage` method to `processLuminoMessage`.
121121

122122
#### Widget manager import
123123

@@ -128,7 +128,7 @@ As mentioned before, if you depend on the ``ManagerBase`` class, you will **eith
128128
+ import { ManagerBase } from '@jupyter-widgets/base-manager';
129129
```
130130

131-
**or**, siwtch to using the new `IWidgetManager` interface in the `base` package:
131+
**or**, switch to using the new `IWidgetManager` interface in the `base` package:
132132

133133
```diff
134134
- import { ManagerBase } from '@jupyter-widgets/base';
@@ -153,7 +153,7 @@ export async function myDeserializer(
153153

154154
#### Backbone extend
155155

156-
The version of backbone that ipywidgets depend on has changed from 1.2.3 to 1.4.0. If you were extending the base widget model with `var CustomWidgetModel = Widget.extend({ ... });` you will need to update the class definition using the ES6 notation:
156+
The version of [Backbone.js](https://backbonejs.org/) that ipywidgets depends on has changed from 1.2.3 to 1.4.0. If you were extending the base widget model with `var CustomWidgetModel = Widget.extend({ ... });` you will need to update the class definition using the ES6 notation:
157157

158158
```diff
159159
- var CustomWidgetModel = Widget.extend({
@@ -164,8 +164,27 @@ The version of backbone that ipywidgets depend on has changed from 1.2.3 to 1.4.
164164
+ }
165165
```
166166

167-
Note: If you were relying on setting certain instance attributes via the `extend` method, you might now need override the `preinitialize` method in order for their values to be set in time.
167+
#### Custom tag names
168168

169+
If you were changing the base HTML tag for your widget by defining the `tagName` property, this can now be done in ipywidgets 8 in the `preinitialize` method (see https://github.com/jupyter-widgets/ipywidgets/commit/a342e0dbc7c779bb668e5a21c097d7cec9a6ac44 for example changes in core widgets):
170+
171+
```diff
172+
- get tagName() {
173+
- return 'button';
174+
- }
175+
+ preinitialize() {
176+
+ this.tagName = 'button';
177+
+ }
178+
```
179+
180+
If you need compatibility with ipywidgets 7, continue using the `get tagName` accessor instead of `preinitialize`. However, newer versions of Typescript will complain that you are overriding a property with a function. If you want to maintain compatibility with both ipywidgets 7 and ipywidgets 8, and you are using Typescript, you can add a `ts-ignore` directive to mollify Typescript, like is done in [ipydatawidgets](https://github.com/vidartf/ipydatawidgets/blob/489586982c375c03d5ffd3089dd4f427c8266443/packages/jupyter-datawidgets/src/media.ts#L131):
181+
182+
```diff
183+
+ // @ts-ignore: 2611
184+
get tagName() {
185+
return 'button';
186+
}
187+
```
169188

170189
Migrating from 6.0 to 7.0
171190
-------------------------

docs/source/user_migration_guides.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,8 @@ As part of an effort to make it possible to
3333
the old `description_tooltip` attribute for certain widgets was deprecated. Now all widgets
3434
that inherit `DOMWidget` have the attribute `tooltip` instead.
3535

36-
Suggested migration: Search and replace `description_tooltip` to `tooltip`.
36+
Suggested migration: Search and replace `description_tooltip` to `tooltip` when you no longer
37+
need to support ipywidgets 7.
3738

3839
#### Selection Widgets
3940

packages/controls/src/widget_selectioncontainer.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -422,17 +422,17 @@ export class TabView extends DOMWidgetView {
422422
luminoWidget: JupyterLuminoTabPanelWidget;
423423
}
424424

425-
export class StackedModel extends SelectionContainerModel {
425+
export class StackModel extends SelectionContainerModel {
426426
defaults(): Backbone.ObjectHash {
427427
return {
428428
...super.defaults(),
429-
_model_name: 'StackedModel',
430-
_view_name: 'StackedView',
429+
_model_name: 'StackModel',
430+
_view_name: 'StackView',
431431
};
432432
}
433433
}
434434

435-
export class StackedView extends BoxView {
435+
export class StackView extends BoxView {
436436
initialize(parameters: WidgetView.IInitializeParameters): void {
437437
super.initialize(parameters);
438438
this.listenTo(this.model, 'change:selected_index', this.update_children);

packages/schema/jupyterwidgetmodels.latest.json

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -6554,7 +6554,7 @@
65546554
"type": "string"
65556555
},
65566556
{
6557-
"default": "StackedModel",
6557+
"default": "StackModel",
65586558
"help": "",
65596559
"name": "_model_name",
65606560
"type": "string"
@@ -6572,7 +6572,7 @@
65726572
"type": "string"
65736573
},
65746574
{
6575-
"default": "StackedView",
6575+
"default": "StackView",
65766576
"help": "",
65776577
"name": "_view_name",
65786578
"type": "string"
@@ -6634,12 +6634,12 @@
66346634
],
66356635
"model": {
66366636
"module": "@jupyter-widgets/controls",
6637-
"name": "StackedModel",
6637+
"name": "StackModel",
66386638
"version": "2.0.0"
66396639
},
66406640
"view": {
66416641
"module": "@jupyter-widgets/controls",
6642-
"name": "StackedView",
6642+
"name": "StackView",
66436643
"version": "2.0.0"
66446644
}
66456645
},

packages/schema/jupyterwidgetmodels.latest.md

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1168,17 +1168,17 @@ Attribute | Type | Default | Help
11681168
`description_width` | string | `''` | Width of the description to the side of the control.
11691169
`handle_color` | `null` or string | `null` | Color of the slider handle.
11701170

1171-
### StackedModel (@jupyter-widgets/controls, 2.0.0); StackedView (@jupyter-widgets/controls, 2.0.0)
1171+
### StackModel (@jupyter-widgets/controls, 2.0.0); StackView (@jupyter-widgets/controls, 2.0.0)
11721172

11731173
Attribute | Type | Default | Help
11741174
-----------------|------------------|------------------|----
11751175
`_dom_classes` | array of string | `[]` | CSS classes applied to widget DOM element
11761176
`_model_module` | string | `'@jupyter-widgets/controls'` |
11771177
`_model_module_version` | string | `'2.0.0'` |
1178-
`_model_name` | string | `'StackedModel'` |
1178+
`_model_name` | string | `'StackModel'` |
11791179
`_view_module` | string | `'@jupyter-widgets/controls'` |
11801180
`_view_module_version` | string | `'2.0.0'` |
1181-
`_view_name` | string | `'StackedView'` |
1181+
`_view_name` | string | `'StackView'` |
11821182
`box_style` | string (one of `'success'`, `'info'`, `'warning'`, `'danger'`, `''`) | `''` | Use a predefined styling for the box.
11831183
`children` | array of reference to Widget widget | `[]` | List of widget children
11841184
`layout` | reference to Layout widget | reference to new instance |

python/ipywidgets/ipywidgets/widgets/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@
1919
from .widget_time import TimePicker
2020
from .widget_output import Output
2121
from .widget_selection import RadioButtons, ToggleButtons, ToggleButtonsStyle, Dropdown, Select, SelectionSlider, SelectMultiple, SelectionRangeSlider
22-
from .widget_selectioncontainer import Tab, Accordion, Stacked
22+
from .widget_selectioncontainer import Tab, Accordion, Stack
2323
from .widget_string import HTML, HTMLMath, Label, Text, Textarea, Password, Combobox
2424
from .widget_controller import Controller
2525
from .interaction import interact, interactive, fixed, interact_manual, interactive_output

python/ipywidgets/ipywidgets/widgets/tests/test_selectioncontainer.py

Lines changed: 136 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -5,50 +5,164 @@
55

66
from traitlets import TraitError
77

8-
from ipywidgets.widgets import Accordion, HTML
8+
from ipywidgets.widgets import Accordion, Tab, Stack, HTML
99

10+
class TestTab(TestCase):
11+
12+
def setUp(self):
13+
self.children = [HTML('0'), HTML('1')]
14+
self.widget = Tab
15+
16+
def test_selected_index_none(self):
17+
widget = self.widget(self.children, selected_index=None)
18+
state = widget.get_state()
19+
assert state['selected_index'] == 0
20+
21+
def test_selected_index_default(self):
22+
widget = self.widget(self.children)
23+
state = widget.get_state()
24+
assert state['selected_index'] == 0
25+
26+
def test_selected_index(self):
27+
widget = self.widget(self.children, selected_index=1)
28+
state = widget.get_state()
29+
assert state['selected_index'] == 1
30+
31+
def test_selected_index_out_of_bounds(self):
32+
with self.assertRaises(TraitError):
33+
self.widget(self.children, selected_index=-1)
34+
35+
def test_children_position_argument(self):
36+
self.widget(self.children)
37+
38+
def test_titles(self):
39+
widget = self.widget(self.children, selected_index=None)
40+
assert widget.get_state()['titles'] == ('', '')
41+
assert widget.titles == ('', '')
42+
43+
widget.set_title(1, 'Title 1')
44+
assert widget.get_state()['titles'] == ('', 'Title 1')
45+
assert widget.titles[1] == 'Title 1'
46+
assert widget.get_title(1) == 'Title 1'
47+
48+
# Backwards compatible with 7.x api
49+
widget.set_title(1, None)
50+
assert widget.get_state()['titles'] == ('', '')
51+
assert widget.titles[1] == ''
52+
assert widget.get_title(1) == ''
53+
54+
with self.assertRaises(IndexError):
55+
widget.set_title(2, 'out of bounds')
56+
with self.assertRaises(IndexError):
57+
widget.get_title(2)
58+
59+
widget.children = tuple(widget.children[:1])
60+
assert len(widget.children) == 1
61+
assert widget.titles == ('',)
1062

1163
class TestAccordion(TestCase):
1264

1365
def setUp(self):
1466
self.children = [HTML('0'), HTML('1')]
67+
self.widget = Accordion
68+
69+
def test_selected_index_none(self):
70+
widget = self.widget(self.children, selected_index=None)
71+
state = widget.get_state()
72+
assert state['selected_index'] is None
73+
74+
def test_selected_index_default(self):
75+
widget = self.widget(self.children)
76+
state = widget.get_state()
77+
assert state['selected_index'] is None
78+
79+
def test_selected_index(self):
80+
widget = self.widget(self.children, selected_index=1)
81+
state = widget.get_state()
82+
assert state['selected_index'] == 1
83+
84+
def test_selected_index_out_of_bounds(self):
85+
with self.assertRaises(TraitError):
86+
self.widget(self.children, selected_index=-1)
87+
88+
def test_children_position_argument(self):
89+
self.widget(self.children)
90+
91+
def test_titles(self):
92+
widget = self.widget(self.children, selected_index=None)
93+
assert widget.get_state()['titles'] == ('', '')
94+
assert widget.titles == ('', '')
95+
96+
widget.set_title(1, 'Title 1')
97+
assert widget.get_state()['titles'] == ('', 'Title 1')
98+
assert widget.titles[1] == 'Title 1'
99+
assert widget.get_title(1) == 'Title 1'
100+
101+
# Backwards compatible with 7.x api
102+
widget.set_title(1, None)
103+
assert widget.get_state()['titles'] == ('', '')
104+
assert widget.titles[1] == ''
105+
assert widget.get_title(1) == ''
106+
107+
with self.assertRaises(IndexError):
108+
widget.set_title(2, 'out of bounds')
109+
with self.assertRaises(IndexError):
110+
widget.get_title(2)
111+
112+
widget.children = tuple(widget.children[:1])
113+
assert len(widget.children) == 1
114+
assert widget.titles == ('',)
115+
116+
class TestStack(TestCase):
117+
118+
def setUp(self):
119+
self.children = [HTML('0'), HTML('1')]
120+
self.widget = Stack
15121

16122
def test_selected_index_none(self):
17-
accordion = Accordion(self.children, selected_index=None)
18-
state = accordion.get_state()
123+
widget = self.widget(self.children, selected_index=None)
124+
state = widget.get_state()
125+
assert state['selected_index'] is None
126+
127+
def test_selected_index_default(self):
128+
widget = self.widget(self.children)
129+
state = widget.get_state()
19130
assert state['selected_index'] is None
20131

21132
def test_selected_index(self):
22-
accordion = Accordion(self.children, selected_index=1)
23-
state = accordion.get_state()
133+
widget = self.widget(self.children, selected_index=1)
134+
state = widget.get_state()
24135
assert state['selected_index'] == 1
25136

26137
def test_selected_index_out_of_bounds(self):
27138
with self.assertRaises(TraitError):
28-
Accordion(self.children, selected_index=-1)
139+
self.widget(self.children, selected_index=-1)
29140

141+
def test_children_position_argument(self):
142+
self.widget(self.children)
30143

31144
def test_titles(self):
32-
accordion = Accordion(self.children, selected_index=None)
33-
assert accordion.get_state()['titles'] == ('', '')
34-
assert accordion.titles == ('', '')
145+
widget = self.widget(self.children, selected_index=None)
146+
assert widget.get_state()['titles'] == ('', '')
147+
assert widget.titles == ('', '')
35148

36-
accordion.set_title(1, 'Title 1')
37-
assert accordion.get_state()['titles'] == ('', 'Title 1')
38-
assert accordion.titles[1] == 'Title 1'
39-
assert accordion.get_title(1) == 'Title 1'
149+
widget.set_title(1, 'Title 1')
150+
assert widget.get_state()['titles'] == ('', 'Title 1')
151+
assert widget.titles[1] == 'Title 1'
152+
assert widget.get_title(1) == 'Title 1'
40153

41154
# Backwards compatible with 7.x api
42-
accordion.set_title(1, None)
43-
assert accordion.get_state()['titles'] == ('', '')
44-
assert accordion.titles[1] == ''
45-
assert accordion.get_title(1) == ''
155+
widget.set_title(1, None)
156+
assert widget.get_state()['titles'] == ('', '')
157+
assert widget.titles[1] == ''
158+
assert widget.get_title(1) == ''
46159

47160
with self.assertRaises(IndexError):
48-
accordion.set_title(2, 'out of bounds')
161+
widget.set_title(2, 'out of bounds')
49162
with self.assertRaises(IndexError):
50-
accordion.get_title(2)
163+
widget.get_title(2)
164+
165+
widget.children = tuple(widget.children[:1])
166+
assert len(widget.children) == 1
167+
assert widget.titles == ('',)
51168

52-
accordion.children = tuple(accordion.children[:1])
53-
assert len(accordion.children) == 1
54-
assert accordion.titles == ('',)

0 commit comments

Comments
 (0)