ONOS-4359: continued work on theming UI
- topo view: device icon and label re-theming (WIP)

Change-Id: I5ecbc1c5b8a8315bfadfaacf62cfdb0e6d1f5a9c
(cherry picked from commit 92eaf44)
diff --git a/web/gui/src/main/webapp/app/view/topo/topoD3.js b/web/gui/src/main/webapp/app/view/topo/topoD3.js
index d6cf986..278fc25 100644
--- a/web/gui/src/main/webapp/app/view/topo/topoD3.js
+++ b/web/gui/src/main/webapp/app/view/topo/topoD3.js
@@ -39,28 +39,17 @@
      */
 
     // configuration
-    var devCfg = {
-            xoff: -20,
-            yoff: -18
-        },
-        labelConfig = {
-            imgPad: 16,
-            padLR: 4,
-            padTB: 3,
-            marginLR: 3,
-            marginTB: 2,
-            port: {
-                gap: 3,
-                width: 18,
-                height: 14
-            }
-        },
-        badgeConfig = {
+    var devIconDim = 36;
+    var labelPad = 4;
+
+    var badgeConfig = {
             radius: 12,
             yoff: 5,
             gdelta: 10
-        },
-        icfg;
+        };
+
+    // TODO: remove dependence on this
+    var icfg;
 
     var status = {
         i: 'badgeInfo',
@@ -87,77 +76,32 @@
     var deviceLabelIndex = 0,
         hostLabelIndex = 0;
 
-
-    var dCol = {
-        black: '#000',
-        paleblue: '#acf',
-        offwhite: '#ddd',
-        darkgrey: '#444',
-        midgrey: '#888',
-        lightgrey: '#bbb',
-        orange: '#f90'
-    };
-
     // note: these are the device icon colors without affinity
     var dColTheme = {
         light: {
-            rfill: dCol.offwhite,
-            online: {
-                glyph: dCol.darkgrey,
-                rect: dCol.paleblue
-            },
-            offline: {
-                glyph: dCol.midgrey,
-                rect: dCol.lightgrey
-            }
+            online: '#444444',
+            offline: '#cccccc'
         },
         dark: {
-            rfill: dCol.midgrey,
-            online: {
-                glyph: dCol.darkgrey,
-                rect: dCol.paleblue
-            },
-            offline: {
-                glyph: dCol.midgrey,
-                rect: dCol.darkgrey
-            }
+            // TODO: theme
+            online: '#444444',
+            offline: '#cccccc'
         }
     };
 
-    function devBaseColor(d) {
-        var o = d.online ? 'online' : 'offline';
-        return dColTheme[ts.theme()][o];
+    function devGlyphColor(d) {
+        var o = d.online,
+            id = d.master,
+            otag = o ? 'online' : 'offline';
+        return o ? sus.cat7().getColor(id, 0, ts.theme())
+                 : dColTheme[ts.theme()][otag];
     }
 
     function setDeviceColor(d) {
-        var o = d.online,
-            s = d.el.classed('selected'),
-            c = devBaseColor(d),
-            a = instColor(d.master, o),
-            icon = d.el.select('g.deviceIcon'),
-            g, r;
-
-        if (s) {
-            g = c.glyph;
-            r = dCol.orange;
-        } else if (api.instVisible()) {
-            g = o ? a : c.glyph;
-            r = o ? c.rfill : a;
-        } else {
-            g = c.glyph;
-            r = c.rect;
-        }
-
-        icon.select('use').style('fill', g);
-        icon.select('rect').style('fill', r);
+        d.el.select('use')
+            .style('fill', devGlyphColor(d));
     }
 
-    function instColor(id, online) {
-        return sus.cat7().getColor(id, !online, ts.theme());
-    }
-
-    // ====
-
     function incDevLabIndex() {
         setDevLabIndex(deviceLabelIndex+1);
         switch(deviceLabelIndex) {
@@ -174,82 +118,51 @@
         ps.setPrefs('topo_prefs', p);
     }
 
-    // Returns the newly computed bounding box of the rectangle
-    function adjustRectToFitText(n) {
-        var text = n.select('text'),
-            box = text.node().getBBox(),
-            lab = labelConfig;
-
-        text.attr('text-anchor', 'middle')
-            .attr('y', '-0.8em')
-            .attr('x', lab.imgPad/2);
-
-        // translate the bbox so that it is centered on [x,y]
-        box.x = -box.width / 2;
-        box.y = -box.height / 2;
-
-        // add padding
-        box.x -= (lab.padLR + lab.imgPad/2);
-        box.width += lab.padLR * 2 + lab.imgPad;
-        box.y -= lab.padTB;
-        box.height += lab.padTB * 2;
-
-        return box;
-    }
-
     function hostLabel(d) {
         var idx = (hostLabelIndex < d.labels.length) ? hostLabelIndex : 0;
         return d.labels[idx];
     }
+
     function deviceLabel(d) {
         var idx = (deviceLabelIndex < d.labels.length) ? deviceLabelIndex : 0;
         return d.labels[idx];
     }
+
     function trimLabel(label) {
         return (label && label.trim()) || '';
     }
 
-    function emptyBox() {
+    function computeLabelWidth(n) {
+        var text = n.select('text'),
+            box = text.node().getBBox();
+        return box.width + labelPad * 2;
+    }
+
+    function iconBox(dim, labelWidth) {
         return {
-            x: -2,
-            y: -2,
-            width: 4,
-            height: 4
-        };
+            x: -dim/2,
+            y: -dim/2,
+            width: dim + labelWidth,
+            height: dim
+        }
     }
 
     function updateDeviceRendering(d) {
-        var label = trimLabel(deviceLabel(d)),
-            noLabel = !label,
-            node = d.el,
-            dim = icfg.device.dim,
-            box, dx, dy,
-            bdg = d.badge;
+        var node = d.el,
+            bdg = d.badge,
+            label = trimLabel(deviceLabel(d)),
+            labelWidth;
 
-        node.select('text')
-            .text(label);
-
-        if (noLabel) {
-            box = emptyBox();
-            dx = -dim/2;
-            dy = -dim/2;
-        } else {
-            box = adjustRectToFitText(node);
-            dx = box.x + devCfg.xoff;
-            dy = box.y + devCfg.yoff;
-        }
+        node.select('text').text(label);
+        labelWidth = label ? computeLabelWidth(node) : 0;
 
         node.select('rect')
             .transition()
-            .attr(box);
+            .attr(iconBox(devIconDim, labelWidth));
 
-        node.select('g.deviceIcon')
-            .transition()
-            .attr('transform', sus.translate(dx, dy));
-
-        // handle badge, if defined
+        // TODO: verify badge placement
         if (bdg) {
-            renderBadge(node, bdg, { dx: dx + dim, dy: dy });
+            renderBadge(node, bdg, { dx: devIconDim, dy: 0 });
         }
     }
 
@@ -259,7 +172,6 @@
 
         updateHostLabel(d);
 
-        // handle badge, if defined
         if (bdg) {
             renderBadge(node, bdg, icfg.host.badge);
         }
@@ -331,28 +243,26 @@
         var node = d3.select(this),
             glyphId = mapDeviceTypeToGlyph(d.type),
             label = trimLabel(deviceLabel(d)),
-            noLabel = !label,
-            box, dx, dy, icon;
+            xlate = -devIconDim/2,
+            rect, text, glyph, labelWidth;
 
         d.el = node;
 
-        node.append('rect').attr({ rx: 5, ry: 5 });
-        node.append('text').text(label).attr('dy', '1.1em');
-        box = adjustRectToFitText(node);
-        node.select('rect').attr(box);
+        rect = node.append('rect');
 
-        icon = is.addDeviceIcon(node, glyphId);
+        text = node.append('text').text(label)
+            .attr('text-anchor', 'left')
+            .attr('y', '0.3em')
+            .attr('x', devIconDim / 2 + labelPad);
 
-        if (noLabel) {
-            dx = -icon.dim/2;
-            dy = -icon.dim/2;
-        } else {
-            box = adjustRectToFitText(node);
-            dx = box.x + devCfg.xoff;
-            dy = box.y + devCfg.yoff;
-        }
+        glyph = is.addDeviceIcon(node, glyphId, devIconDim);
 
-        icon.attr('transform', sus.translate(dx, dy));
+        labelWidth = label ? computeLabelWidth(node) : 0;
+
+        rect.attr(iconBox(devIconDim, labelWidth));
+        glyph.attr(iconBox(devIconDim, 0));
+
+        node.attr('transform', sus.translate(xlate, xlate));
     }
 
     function hostEnter(d) {
@@ -631,7 +541,6 @@
 
                 incDevLabIndex: incDevLabIndex,
                 setDevLabIndex: setDevLabIndex,
-                adjustRectToFitText: adjustRectToFitText,
                 hostLabel: hostLabel,
                 deviceLabel: deviceLabel,
                 trimLabel: trimLabel,