Deferring force layout until quiet period.

Change-Id: I24c66eb695ece45df2b0291f42ccf7d980cad535
diff --git a/web/gui/src/main/java/org/onosproject/ui/impl/TopologyResource.java b/web/gui/src/main/java/org/onosproject/ui/impl/TopologyResource.java
index b71b9f8..3096091 100644
--- a/web/gui/src/main/java/org/onosproject/ui/impl/TopologyResource.java
+++ b/web/gui/src/main/java/org/onosproject/ui/impl/TopologyResource.java
@@ -55,7 +55,7 @@
         Map<String, ObjectNode> metaUi = TopologyViewMessageHandler.getMetaUi();
         for (String id : metaUi.keySet()) {
             ObjectNode memento = metaUi.get(id);
-            if (id.charAt(17) == '/') {
+            if (id.length() > 17 && id.charAt(17) == '/') {
                 addGeoData(hosts, "id", id, memento);
             } else {
                 addGeoData(devices, "uri", id, memento);
diff --git a/web/gui/src/main/java/org/onosproject/ui/impl/UiWebSocket.java b/web/gui/src/main/java/org/onosproject/ui/impl/UiWebSocket.java
index 958ad32..4df3edf 100644
--- a/web/gui/src/main/java/org/onosproject/ui/impl/UiWebSocket.java
+++ b/web/gui/src/main/java/org/onosproject/ui/impl/UiWebSocket.java
@@ -42,7 +42,7 @@
 
     private static final Logger log = LoggerFactory.getLogger(UiWebSocket.class);
 
-    private static final long MAX_AGE_MS = 15_000;
+    private static final long MAX_AGE_MS = 30_000;
 
     private static final byte PING = 0x9;
     private static final byte PONG = 0xA;
diff --git a/web/gui/src/main/webapp/app/view/topo/topoForce.js b/web/gui/src/main/webapp/app/view/topo/topoForce.js
index e087fa5..b99cb9a 100644
--- a/web/gui/src/main/webapp/app/view/topo/topoForce.js
+++ b/web/gui/src/main/webapp/app/view/topo/topoForce.js
@@ -58,6 +58,9 @@
         showHosts = false,      // whether hosts are displayed
         showOffline = true,     // whether offline devices are displayed
         nodeLock = false,       // whether nodes can be dragged or not (locked)
+        fTimer,                 // timer for delayed force layout
+        fNodesTimer,            // timer for delayed nodes update
+        fLinksTimer,            // timer for delayed links update
         dim;                    // the dimensions of the force layout [w,h]
 
     // SVG elements;
@@ -479,6 +482,13 @@
     // ==========================================
 
     function updateNodes() {
+        if (fNodesTimer) {
+            $timeout.cancel(fNodesTimer);
+        }
+        fNodesTimer = $timeout(_updateNodes, 150);
+    }
+
+    function _updateNodes() {
         // select all the nodes in the layout:
         node = nodeG.selectAll('.node')
             .data(network.nodes, function (d) { return d.id; });
@@ -526,6 +536,13 @@
     // ==========================
 
     function updateLinks() {
+        if (fLinksTimer) {
+            $timeout.cancel(fLinksTimer);
+        }
+        fLinksTimer = $timeout(_updateLinks, 150);
+    }
+
+    function _updateLinks() {
         var th = ts.theme();
 
         link = linkG.selectAll('.link')
@@ -589,7 +606,13 @@
 
     function fStart() {
         if (!tos.isOblique()) {
-            force.start();
+            if (fTimer) {
+                $timeout.cancel(fTimer);
+            }
+            fTimer = $timeout(function () {
+                $log.debug("Starting force-layout");
+                force.start();
+            }, 200);
         }
     }