Committed by
Gerrit Code Review
GUI -- [ONOS-89] Creating affinity colors for ONOS instances. (WIP)
- added d3utils.cat7() to provide color scales. - added 'equals' and 'dash' ids for key binding. - added theme() callback to let views know when the theme changed. - re-bound test keys (0, dash, equals) Change-Id: Ie6c6140451ddab567e26c2ea17d65395fa9cc829
Showing
3 changed files
with
144 additions
and
9 deletions
... | @@ -119,10 +119,100 @@ | ... | @@ -119,10 +119,100 @@ |
119 | .attr('in', String); | 119 | .attr('in', String); |
120 | } | 120 | } |
121 | 121 | ||
122 | + // --- Ordinal scales for 7 values. | ||
123 | + // TODO: tune colors for light and dark themes | ||
124 | + | ||
125 | + var lightNorm = ['#1f77b4', '#2ca02c', '#d62728', '#9467bd', '#e377c2', '#bcbd22', '#17becf'], | ||
126 | + lightMute = ['#aec7e8', '#98df8a', '#ff9896', '#c5b0d5', '#f7b6d2', '#dbdb8d', '#9edae5'], | ||
127 | + darkNorm = ['#1f77b4', '#2ca02c', '#d62728', '#9467bd', '#e377c2', '#bcbd22', '#17becf'], | ||
128 | + darkMute = ['#aec7e8', '#98df8a', '#ff9896', '#c5b0d5', '#f7b6d2', '#dbdb8d', '#9edae5']; | ||
129 | + | ||
130 | + function cat7() { | ||
131 | + var colors = { | ||
132 | + light: { | ||
133 | + norm: d3.scale.ordinal().range(lightNorm), | ||
134 | + mute: d3.scale.ordinal().range(lightMute) | ||
135 | + }, | ||
136 | + dark: { | ||
137 | + norm: d3.scale.ordinal().range(darkNorm), | ||
138 | + mute: d3.scale.ordinal().range(darkMute) | ||
139 | + } | ||
140 | + }, | ||
141 | + tcid = 'd3utilTestCard'; | ||
142 | + | ||
143 | + function get(id, muted, theme) { | ||
144 | + // NOTE: since we are lazily assigning domain ids, we need to | ||
145 | + // get the color from all 4 scales, to keep the domains | ||
146 | + // in sync. | ||
147 | + var ln = colors.light.norm(id), | ||
148 | + lm = colors.light.mute(id), | ||
149 | + dn = colors.dark.norm(id), | ||
150 | + dm = colors.dark.mute(id); | ||
151 | + if (theme === 'dark') { | ||
152 | + return muted ? dm : dn; | ||
153 | + } else { | ||
154 | + return muted ? lm : ln; | ||
155 | + } | ||
156 | + } | ||
157 | + | ||
158 | + function testCard(svg) { | ||
159 | + var g = svg.select('g#' + tcid), | ||
160 | + dom = d3.range(7), | ||
161 | + k, muted, theme, what; | ||
162 | + | ||
163 | + if (!g.empty()) { | ||
164 | + g.remove(); | ||
165 | + | ||
166 | + } else { | ||
167 | + g = svg.append('g') | ||
168 | + .attr('id', tcid) | ||
169 | + .attr('transform', 'scale(4)translate(20,20)'); | ||
170 | + | ||
171 | + for (k=0; k<4; k++) { | ||
172 | + muted = k%2; | ||
173 | + what = muted ? ' muted' : ' normal'; | ||
174 | + theme = k < 2 ? 'light' : 'dark'; | ||
175 | + dom.forEach(function (id, i) { | ||
176 | + var x = i * 20, | ||
177 | + y = k * 20, | ||
178 | + f = get(id, muted, theme); | ||
179 | + g.append('circle').attr({ | ||
180 | + cx: x, | ||
181 | + cy: y, | ||
182 | + r: 5, | ||
183 | + fill: f | ||
184 | + }); | ||
185 | + }); | ||
186 | + g.append('rect').attr({ | ||
187 | + x: 140, | ||
188 | + y: k * 20 - 5, | ||
189 | + width: 32, | ||
190 | + height: 10, | ||
191 | + rx: 2, | ||
192 | + fill: '#888' | ||
193 | + }); | ||
194 | + g.append('text').text(theme + what) | ||
195 | + .attr({ | ||
196 | + x: 142, | ||
197 | + y: k * 20 + 2, | ||
198 | + fill: 'white' | ||
199 | + }) | ||
200 | + .style('font-size', '4pt'); | ||
201 | + } | ||
202 | + } | ||
203 | + } | ||
204 | + | ||
205 | + return { | ||
206 | + testCard: testCard, | ||
207 | + get: get | ||
208 | + }; | ||
209 | + } | ||
210 | + | ||
122 | // === register the functions as a library | 211 | // === register the functions as a library |
123 | onos.ui.addLib('d3util', { | 212 | onos.ui.addLib('d3util', { |
124 | createDragBehavior: createDragBehavior, | 213 | createDragBehavior: createDragBehavior, |
125 | - appendGlow: appendGlow | 214 | + appendGlow: appendGlow, |
215 | + cat7: cat7 | ||
126 | }); | 216 | }); |
127 | 217 | ||
128 | }(ONOS)); | 218 | }(ONOS)); | ... | ... |
... | @@ -93,6 +93,8 @@ | ... | @@ -93,6 +93,8 @@ |
93 | case 40: return 'downArrow'; | 93 | case 40: return 'downArrow'; |
94 | case 91: return 'cmdLeft'; | 94 | case 91: return 'cmdLeft'; |
95 | case 93: return 'cmdRight'; | 95 | case 93: return 'cmdRight'; |
96 | + case 187: return 'equals'; | ||
97 | + case 189: return 'dash'; | ||
96 | case 191: return 'slash'; | 98 | case 191: return 'slash'; |
97 | default: | 99 | default: |
98 | if ((code >= 48 && code <= 57) || | 100 | if ((code >= 48 && code <= 57) || |
... | @@ -446,6 +448,7 @@ | ... | @@ -446,6 +448,7 @@ |
446 | current.theme = (current.theme === 'light') ? 'dark' : 'light'; | 448 | current.theme = (current.theme === 'light') ? 'dark' : 'light'; |
447 | body.classed('light dark', false); | 449 | body.classed('light dark', false); |
448 | body.classed(current.theme, true); | 450 | body.classed(current.theme, true); |
451 | + theme(view); | ||
449 | return true; | 452 | return true; |
450 | } | 453 | } |
451 | 454 | ||
... | @@ -546,6 +549,13 @@ | ... | @@ -546,6 +549,13 @@ |
546 | } | 549 | } |
547 | } | 550 | } |
548 | 551 | ||
552 | + function theme() { | ||
553 | + // allow current view to react to theme event... | ||
554 | + if (current.view) { | ||
555 | + current.view.theme(current.ctx, current.flags); | ||
556 | + } | ||
557 | + } | ||
558 | + | ||
549 | // .......................................................... | 559 | // .......................................................... |
550 | // View class | 560 | // View class |
551 | // Captures state information about a view. | 561 | // Captures state information about a view. |
... | @@ -607,7 +617,7 @@ | ... | @@ -607,7 +617,7 @@ |
607 | dataLoadError: this.dataLoadError, | 617 | dataLoadError: this.dataLoadError, |
608 | alert: this.alert, | 618 | alert: this.alert, |
609 | flash: this.flash, | 619 | flash: this.flash, |
610 | - theme: this.theme | 620 | + getTheme: this.getTheme |
611 | } | 621 | } |
612 | }, | 622 | }, |
613 | 623 | ||
... | @@ -672,6 +682,16 @@ | ... | @@ -672,6 +682,16 @@ |
672 | } | 682 | } |
673 | }, | 683 | }, |
674 | 684 | ||
685 | + theme: function (ctx, flags) { | ||
686 | + var c = ctx | '', | ||
687 | + fn = isF(this.cb.theme); | ||
688 | + traceFn('View.theme', this.vid); | ||
689 | + if (fn) { | ||
690 | + trace('THEME cb for ' + this.vid); | ||
691 | + fn(this.token(), c, flags); | ||
692 | + } | ||
693 | + }, | ||
694 | + | ||
675 | error: function (ctx, flags) { | 695 | error: function (ctx, flags) { |
676 | var c = ctx || '', | 696 | var c = ctx || '', |
677 | fn = isF(this.cb.error); | 697 | fn = isF(this.cb.error); |
... | @@ -699,7 +719,7 @@ | ... | @@ -699,7 +719,7 @@ |
699 | setKeyBindings(keyArg); | 719 | setKeyBindings(keyArg); |
700 | }, | 720 | }, |
701 | 721 | ||
702 | - theme: function () { | 722 | + getTheme: function () { |
703 | return current.theme; | 723 | return current.theme; |
704 | }, | 724 | }, |
705 | 725 | ... | ... |
... | @@ -136,9 +136,9 @@ | ... | @@ -136,9 +136,9 @@ |
136 | // key bindings | 136 | // key bindings |
137 | var keyDispatch = { | 137 | var keyDispatch = { |
138 | // TODO: remove these "development only" bindings | 138 | // TODO: remove these "development only" bindings |
139 | - M: testMe, | 139 | + 0: testMe, |
140 | - S: injectStartupEvents, | 140 | + equals: injectStartupEvents, |
141 | - space: injectTestEvent, | 141 | + dash: injectTestEvent, |
142 | 142 | ||
143 | O: [toggleSummary, 'Toggle ONOS summary pane'], | 143 | O: [toggleSummary, 'Toggle ONOS summary pane'], |
144 | I: [toggleInstances, 'Toggle ONOS instances pane'], | 144 | I: [toggleInstances, 'Toggle ONOS instances pane'], |
... | @@ -189,7 +189,8 @@ | ... | @@ -189,7 +189,8 @@ |
189 | onosOrder = [], | 189 | onosOrder = [], |
190 | oiBox, | 190 | oiBox, |
191 | oiShowMaster = false, | 191 | oiShowMaster = false, |
192 | - portLabelsOn = false; | 192 | + portLabelsOn = false, |
193 | + cat7 = d3u.cat7(); | ||
193 | 194 | ||
194 | var hoverModeAll = 1, | 195 | var hoverModeAll = 1, |
195 | hoverModeFlows = 2, | 196 | hoverModeFlows = 2, |
... | @@ -240,8 +241,9 @@ | ... | @@ -240,8 +241,9 @@ |
240 | // Key Callbacks | 241 | // Key Callbacks |
241 | 242 | ||
242 | function testMe(view) { | 243 | function testMe(view) { |
243 | - //view.alert('Theme is ' + view.theme()); | 244 | + //view.alert('Theme is ' + view.getTheme()); |
244 | //view.flash('This is some text'); | 245 | //view.flash('This is some text'); |
246 | + cat7.testCard(svg); | ||
245 | } | 247 | } |
246 | 248 | ||
247 | function abortIfLive() { | 249 | function abortIfLive() { |
... | @@ -862,12 +864,17 @@ | ... | @@ -862,12 +864,17 @@ |
862 | return true; | 864 | return true; |
863 | } | 865 | } |
864 | 866 | ||
867 | + function colorAffinity(on) { | ||
868 | + // FIXME: need to code this portion up. | ||
869 | + } | ||
865 | 870 | ||
866 | function toggleInstances() { | 871 | function toggleInstances() { |
867 | if (!oiBox.isVisible()) { | 872 | if (!oiBox.isVisible()) { |
868 | oiBox.show(); | 873 | oiBox.show(); |
874 | + colorAffinity(true); | ||
869 | } else { | 875 | } else { |
870 | oiBox.hide(); | 876 | oiBox.hide(); |
877 | + colorAffinity(false); | ||
871 | } | 878 | } |
872 | } | 879 | } |
873 | 880 | ||
... | @@ -1123,6 +1130,13 @@ | ... | @@ -1123,6 +1130,13 @@ |
1123 | }); | 1130 | }); |
1124 | 1131 | ||
1125 | // operate on existing + new onoses here | 1132 | // operate on existing + new onoses here |
1133 | + // set the affinity colors... | ||
1134 | + onoses.each(function (d) { | ||
1135 | + var el = d3.select(this), | ||
1136 | + rect = el.select('svg').select('rect'), | ||
1137 | + col = instColor(d.id, d.online); | ||
1138 | + rect.style('fill', col); | ||
1139 | + }); | ||
1126 | 1140 | ||
1127 | // adjust the panel size appropriately... | 1141 | // adjust the panel size appropriately... |
1128 | oiBox.width(instDim.w * onosOrder.length); | 1142 | oiBox.width(instDim.w * onosOrder.length); |
... | @@ -1132,6 +1146,10 @@ | ... | @@ -1132,6 +1146,10 @@ |
1132 | onoses.exit().remove(); | 1146 | onoses.exit().remove(); |
1133 | } | 1147 | } |
1134 | 1148 | ||
1149 | + function instColor(id, online) { | ||
1150 | + return cat7.get(id, !online, network.view.getTheme()); | ||
1151 | + } | ||
1152 | + | ||
1135 | function clickInst(d) { | 1153 | function clickInst(d) { |
1136 | var el = d3.select(this), | 1154 | var el = d3.select(this), |
1137 | aff = el.classed('affinity'); | 1155 | aff = el.classed('affinity'); |
... | @@ -2571,6 +2589,12 @@ | ... | @@ -2571,6 +2589,12 @@ |
2571 | .select('g').attr('transform', birdTranslate(w, h)); | 2589 | .select('g').attr('transform', birdTranslate(w, h)); |
2572 | } | 2590 | } |
2573 | 2591 | ||
2592 | + function theme(view, ctx, flags) { | ||
2593 | + updateInstances(); | ||
2594 | + // TODO: update other theme-affected elements | ||
2595 | + | ||
2596 | + } | ||
2597 | + | ||
2574 | function birdTranslate(w, h) { | 2598 | function birdTranslate(w, h) { |
2575 | var bdim = config.birdDim; | 2599 | var bdim = config.birdDim; |
2576 | return 'translate('+((w-bdim)*.4)+','+((h-bdim)*.1)+')'; | 2600 | return 'translate('+((w-bdim)*.4)+','+((h-bdim)*.1)+')'; |
... | @@ -2583,7 +2607,8 @@ | ... | @@ -2583,7 +2607,8 @@ |
2583 | preload: preload, | 2607 | preload: preload, |
2584 | load: load, | 2608 | load: load, |
2585 | unload: unload, | 2609 | unload: unload, |
2586 | - resize: resize | 2610 | + resize: resize, |
2611 | + theme: theme | ||
2587 | }); | 2612 | }); |
2588 | 2613 | ||
2589 | summaryPane = onos.ui.addFloatingPanel('topo-summary'); | 2614 | summaryPane = onos.ui.addFloatingPanel('topo-summary'); | ... | ... |
-
Please register or login to post a comment