ONOS-2850 : Beginnings of Topology Programmable Dialog box --- WIP.
Change-Id: I7e08b3c5d97f409c470eeb97b0f988a14b6d495f
diff --git a/web/gui/src/main/webapp/app/view/topo/topo.css b/web/gui/src/main/webapp/app/view/topo/topo.css
index 255ddbc..dda6d5c 100644
--- a/web/gui/src/main/webapp/app/view/topo/topo.css
+++ b/web/gui/src/main/webapp/app/view/topo/topo.css
@@ -96,6 +96,24 @@
height: 30px;
}
+/* --- Topo Dialog Panel --- */
+
+#topo-p-dialog .dialog-button {
+ display: inline-block;
+ cursor: pointer;
+ height: 20px;
+ padding: 2px 6px;
+ margin: 4px;
+ float: right;
+}
+
+.light #topo-p-dialog .dialog-button {
+ background-color: #fec;
+}
+.dark #topo-p-dialog .dialog-button {
+ background-color: #369;
+}
+
/* --- general topo-panel styling --- */
.topo-p div.header div.icon {
diff --git a/web/gui/src/main/webapp/app/view/topo/topoDialog.js b/web/gui/src/main/webapp/app/view/topo/topoDialog.js
new file mode 100644
index 0000000..e485804
--- /dev/null
+++ b/web/gui/src/main/webapp/app/view/topo/topoDialog.js
@@ -0,0 +1,182 @@
+/*
+ * Copyright 2015 Open Networking Laboratory
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+/*
+ ONOS GUI -- Topology Dialog Module.
+ Defines functions for manipulating a dialog box.
+ */
+
+(function () {
+ 'use strict';
+
+ // injected refs
+ var $log, $window, $rootScope, fs, ps, bns;
+
+ // constants
+ var pCls = 'topo-p',
+ idDialog = 'topo-p-dialog',
+ panelOpts = {
+ width: 300
+ };
+
+ // internal state
+ var pApi, panel, dApi;
+
+ // TODO: ESC key invokes Cancel callback
+ // TODO: Enter invokes OK callback
+
+ // create the dialog; return its API
+ function createDialog() {
+ var header, body, footer,
+ p = ps.createPanel(idDialog, panelOpts);
+ p.classed(pCls, true);
+ panel = p;
+
+ function reset() {
+ p.empty();
+ p.append('div').classed('header', true);
+ p.append('div').classed('body', true);
+ p.append('div').classed('footer', true);
+
+ header = p.el().select('.header');
+ body = p.el().select('.body');
+ footer = p.el().select('.footer');
+ }
+
+ function hAppend(x) {
+ if (typeof x === 'string') {
+ return header.append(x);
+ }
+ header.node().appendChild(x.node());
+ return header;
+ }
+
+ function bAppend(x) {
+ if (typeof x === 'string') {
+ return body.append(x);
+ }
+ body.node().appendChild(x.node());
+ return body;
+ }
+
+ function fAppend(x) {
+ if (typeof x === 'string') {
+ return footer.append(x);
+ }
+ footer.node().appendChild(x.node());
+ return footer;
+ }
+
+ function destroy() {
+ ps.destroyPanel(idDialog);
+ }
+
+ return {
+ reset: reset,
+ appendHeader: hAppend,
+ appendBody: bAppend,
+ appendFooter: fAppend,
+ destroy: destroy
+ };
+ }
+
+ function makeButton(text, callback) {
+ var cb = fs.isF(callback);
+
+ function invoke() {
+ cb && cb();
+ panel.hide();
+ }
+ return createDiv('dialog-button')
+ .text(text)
+ .on('click', invoke);
+ }
+
+ function addContent(content) {
+ if (pApi) {
+ pApi.appendBody(content);
+ }
+ return dApi;
+ }
+
+ function addButton(text, cb) {
+ if (pApi) {
+ pApi.appendFooter(makeButton(text, cb));
+ }
+ return dApi;
+ }
+
+ // opens the dialog (creates if necessary)
+ function openDialog() {
+ $log.debug('Open DIALOG');
+ if (!pApi) {
+ pApi = createDialog();
+ }
+ pApi.reset();
+ pApi.appendHeader('h2').text('=dialog=');
+ panel.show();
+
+ // return the dialog object API
+ dApi = {
+ addContent: addContent,
+ addButton: addButton
+ };
+ return dApi;
+ }
+
+ // closes the dialog (destroying panel)
+ function closeDialog() {
+ $log.debug('Close DIALOG');
+ if (pApi) {
+ panel.hide();
+ pApi.destroy();
+ pApi = null;
+ dApi = null;
+ }
+ }
+
+ // creates a detached div, returning D3 selection
+ // optional CSS class may be provided
+ function createDiv(cls) {
+ var div = d3.select(document.createElement('div'));
+ if (cls) {
+ div.classed(cls, true);
+ }
+ return div;
+ }
+
+ // ==========================
+
+ angular.module('ovTopo')
+ .factory('TopoDialogService',
+ ['$log', '$window', '$rootScope', 'FnService', 'PanelService', 'ButtonService',
+
+ function (_$log_, _$window_, _$rootScope_,
+ _fs_, _ps_, _bns_) {
+ $log = _$log_;
+ $window = _$window_;
+ $rootScope = _$rootScope_;
+ fs = _fs_;
+ ps = _ps_;
+ bns = _bns_;
+
+ return {
+ openDialog: openDialog,
+ closeDialog: closeDialog,
+ createDiv: createDiv
+ };
+ }]);
+}());
diff --git a/web/gui/src/main/webapp/app/view/topo/topoSelect.js b/web/gui/src/main/webapp/app/view/topo/topoSelect.js
index 483c4ba..4ad7690 100644
--- a/web/gui/src/main/webapp/app/view/topo/topoSelect.js
+++ b/web/gui/src/main/webapp/app/view/topo/topoSelect.js
@@ -240,6 +240,33 @@
return cc;
}
+ // returns a selection context, providing info about what is selected
+ function selectionContext() {
+ var devices = [],
+ hosts = [],
+ types = {};
+
+ angular.forEach(selections, function (d) {
+ var o = d.obj,
+ c = o.class;
+
+ if (c === 'device') {
+ devices.push(o.id);
+ types[o.id] = o.type;
+ }
+ if (c === 'host') {
+ hosts.push(o.id);
+ types[o.id] = o.type;
+ }
+ });
+
+ return {
+ devices: devices,
+ hosts: hosts,
+ types: types
+ };
+ }
+
// === -----------------------------------------------------
// === MODULE DEFINITION ===
@@ -280,7 +307,8 @@
selectOrder: function () { return selectOrder; },
somethingSelected: somethingSelected,
- clickConsumed: clickConsumed
+ clickConsumed: clickConsumed,
+ selectionContext: selectionContext
};
}]);
}());
diff --git a/web/gui/src/main/webapp/index.html b/web/gui/src/main/webapp/index.html
index 5df3c66..7e0d9b7 100644
--- a/web/gui/src/main/webapp/index.html
+++ b/web/gui/src/main/webapp/index.html
@@ -98,6 +98,7 @@
<script src="app/view/topo/topo.js"></script>
<script src="app/view/topo/topoD3.js"></script>
<script src="app/view/topo/topoEvent.js"></script>
+ <script src="app/view/topo/topoDialog.js"></script>
<script src="app/view/topo/topoFilter.js"></script>
<script src="app/view/topo/topoForce.js"></script>
<script src="app/view/topo/topoInst.js"></script>