diff --git a/src/MCT.js b/src/MCT.js index ed16d5d8a8..402ed1dd52 100644 --- a/src/MCT.js +++ b/src/MCT.js @@ -35,6 +35,7 @@ define([ './ui/registries/InspectorViewRegistry', './ui/registries/ToolbarRegistry', './ui/router/ApplicationRouter', + './ui/router/Browse', '../platform/framework/src/Main', './styles-new/core.scss', './ui/components/layout/Layout.vue', @@ -54,6 +55,7 @@ define([ InspectorViewRegistry, ToolbarRegistry, ApplicationRouter, + Browse, Main, coreStyles, Layout, @@ -273,6 +275,7 @@ define([ }.bind(this) }); + // TODO: remove with legacy types. this.types.listKeys().forEach(function (typeKey) { var type = this.types.get(typeKey); var legacyDefinition = type.toLegacyDefinition(); @@ -280,26 +283,6 @@ define([ this.legacyExtension('types', legacyDefinition); }.bind(this)); - // TODO: move this to adapter bundle. - this.legacyExtension('runs', { - depends: ['types[]'], - implementation: (types) => { - this.types.importLegacyTypes(types); - } - }); - - this.objectViews.getAllProviders().forEach(function (p) { - this.legacyExtension('views', { - key: p.key, - provider: p, - name: p.name, - cssClass: p.cssClass, - description: p.description, - editable: p.editable, - template: '' - }); - }, this); - legacyRegistry.register('adapter', this.legacyBundle); legacyRegistry.enable('adapter'); @@ -324,8 +307,6 @@ define([ // something has depended upon objectService. Cool, right? this.$injector.get('objectService'); - console.log('Rendering app layout.'); - var appLayout = new Vue({ mixins: [Layout.default], provide: { @@ -334,7 +315,8 @@ define([ }); domElement.appendChild(appLayout.$mount().$el); - + this.layout = appLayout; + Browse(this); this.router.start(); this.emit('start'); }.bind(this)); diff --git a/src/adapter/bundle.js b/src/adapter/bundle.js index fef4bd9939..f32cbb11d8 100644 --- a/src/adapter/bundle.js +++ b/src/adapter/bundle.js @@ -34,7 +34,9 @@ define([ './runs/TimeSettingsURLHandler', './runs/TypeDeprecationChecker', './runs/LegacyTelemetryProvider', - './services/LegacyObjectAPIInterceptor' + './runs/RegisterLegacyTypes', + './services/LegacyObjectAPIInterceptor', + './views/installLegacyViews' ], function ( legacyRegistry, ActionDialogDecorator, @@ -49,7 +51,9 @@ define([ TimeSettingsURLHandler, TypeDeprecationChecker, LegacyTelemetryProvider, - LegacyObjectAPIInterceptor + RegisterLegacyTypes, + LegacyObjectAPIInterceptor, + installLegacyViews ) { legacyRegistry.register('src/adapter', { "extensions": { @@ -149,6 +153,21 @@ define([ "openmct", "instantiate" ] + }, + { + implementation: installLegacyViews, + depends: [ + "openmct", + "views[]", + "instantiate" + ] + }, + { + implementation: RegisterLegacyTypes, + depends: [ + "types[]", + "openmct" + ] } ], licenses: [ diff --git a/src/adapter/runs/RegisterLegacyTypes.js b/src/adapter/runs/RegisterLegacyTypes.js new file mode 100644 index 0000000000..3527c62524 --- /dev/null +++ b/src/adapter/runs/RegisterLegacyTypes.js @@ -0,0 +1,17 @@ +define([ + +], function ( + +) { + function RegisterLegacyTypes(types, openmct) { + types.forEach(function (legacyDefinition) { + if (!openmct.types.get(legacyDefinition.key)) { + console.warn(`DEPRECATION WARNING: Migrate type ${legacyDefinition.key} from ${legacyDefinition.bundle.path} to use the new Types API. Legacy type support will be removed soon.`); + } + }); + + openmct.types.importLegacyTypes(types); + } + + return RegisterLegacyTypes; +}); diff --git a/src/adapter/views/LegacyViewProvider.js b/src/adapter/views/LegacyViewProvider.js new file mode 100644 index 0000000000..8afc187be9 --- /dev/null +++ b/src/adapter/views/LegacyViewProvider.js @@ -0,0 +1,93 @@ +define([ + +], function ( + +) { + + function LegacyViewProvider(legacyView, openmct, convertToLegacyObject) { + console.warn(`DEPRECATION WARNING: Migrate ${legacyView.key} from ${legacyView.bundle.path} to use the new View APIs. Legacy view support will be removed soon.`); + return { + key: legacyView.key, + name: legacyView.name, + cssClass: legacyView.cssClass, + description: legacyView.description, + editable: legacyView.editable, + canView: function (domainObject) { + if (!domainObject || !domainObject.identifier) { + return false; + } + if (legacyView.type) { + return domainObject.type === legacyView.type; + } + let legacyObject = convertToLegacyObject(domainObject); + if (legacyView.needs) { + let meetsNeeds = legacyView.needs.every(k => legacyObject.hasCapability(k)); + if (!meetsNeeds) { + return false; + } + } + return openmct.$injector.get('policyService').allow( + 'view', legacyView, legacyObject + ); + }, + view: function (domainObject) { + let $rootScope = openmct.$injector.get('$rootScope'); + let templateLinker = openmct.$injector.get('templateLinker'); + let scope = $rootScope.$new(); + let legacyObject = convertToLegacyObject(domainObject); + let isDestroyed = false; + scope.domainObject = legacyObject; + scope.model = legacyObject.getModel(); + + + return { + show: function (container) { + // TODO: implement "gestures" support ? + let uses = legacyView.uses || []; + let promises = []; + let results = uses.map(function (capabilityKey, i) { + let result = legacyObject.useCapability(capabilityKey); + if (result.then) { + promises.push(result.then(function (r) { + results[i] = r; + })); + } + return result; + }); + + function link() { + if (isDestroyed) { + return; + } + uses.forEach(function (key, i) { + scope[key] = results[i]; + }); + templateLinker.link( + scope, + openmct.$angular.element(container), + legacyView + ); + container.style.height = '100%'; + } + + if (promises.length) { + Promise.all(promises) + .then(function () { + link(); + scope.$digest(); + }); + } else { + link(); + } + }, + destroy: function () { + scope.$destroy(); + } + } + } + }; + }; + + return LegacyViewProvider; + +}); diff --git a/src/adapter/views/installLegacyViews.js b/src/adapter/views/installLegacyViews.js new file mode 100644 index 0000000000..f61a24085c --- /dev/null +++ b/src/adapter/views/installLegacyViews.js @@ -0,0 +1,22 @@ +define([ + './LegacyViewProvider', + '../../api/objects/object-utils' +], function ( + LegacyViewProvider, + objectUtils +) { + function installLegacyViews(openmct, legacyViews, instantiate) { + + function convertToLegacyObject(domainObject) { + let keyString = objectUtils.makeKeyString(domainObject.identifier); + let oldModel = objectUtils.toOldFormat(domainObject); + return instantiate(oldModel, keyString); + } + + legacyViews.forEach(function (legacyView) { + openmct.objectViews.addProvider(new LegacyViewProvider(legacyView, openmct, convertToLegacyObject)); + }); + } + + return installLegacyViews; +}); diff --git a/src/plugins/summaryWidget/src/views/SummaryWidgetViewProvider.js b/src/plugins/summaryWidget/src/views/SummaryWidgetViewProvider.js index b0aa7c01a0..c7e4e4174d 100644 --- a/src/plugins/summaryWidget/src/views/SummaryWidgetViewProvider.js +++ b/src/plugins/summaryWidget/src/views/SummaryWidgetViewProvider.js @@ -15,7 +15,8 @@ define([ function SummaryWidgetViewProvider(openmct) { return { key: 'summary-widget-viewer', - name: 'Widget View', + name: 'Summary View', + cssClass: 'icon-summary-widget', canView: function (domainObject) { return domainObject.type === 'summary-widget'; }, diff --git a/src/ui/components/controls/splitter.vue b/src/ui/components/controls/splitter.vue deleted file mode 100644 index eb15975c2a..0000000000 --- a/src/ui/components/controls/splitter.vue +++ /dev/null @@ -1,133 +0,0 @@ - - - - - \ No newline at end of file diff --git a/src/ui/components/controls/MainViewBrowseBar.vue b/src/ui/components/layout/BrowseBar.vue similarity index 68% rename from src/ui/components/controls/MainViewBrowseBar.vue rename to src/ui/components/layout/BrowseBar.vue index e60ca5524c..ed9744f738 100644 --- a/src/ui/components/controls/MainViewBrowseBar.vue +++ b/src/ui/components/layout/BrowseBar.vue @@ -2,10 +2,11 @@
-
- + {{ domainObject.name }} @@ -15,19 +16,22 @@
-
+
- {{ currentView.name }} + + {{ currentView.name }} +
-
+
    -
  • + :title="view.name"> {{ view.name }}
@@ -44,69 +48,64 @@ diff --git a/src/ui/components/layout/BrowseObject.vue b/src/ui/components/layout/BrowseObject.vue deleted file mode 100644 index 0d019111c3..0000000000 --- a/src/ui/components/layout/BrowseObject.vue +++ /dev/null @@ -1,160 +0,0 @@ - - - - - - - diff --git a/src/ui/components/layout/Layout.vue b/src/ui/components/layout/Layout.vue index 4cc922203a..51b4315e2d 100644 --- a/src/ui/components/layout/Layout.vue +++ b/src/ui/components/layout/Layout.vue @@ -22,8 +22,12 @@
- - + + + + @@ -184,28 +188,28 @@ import Inspector from '../inspector/Inspector.vue'; import MctStatus from './MctStatus.vue'; import MctTree from './mct-tree.vue'; - import BrowseObject from './BrowseObject.vue'; + import ObjectView from './ObjectView.vue'; import MctTemplate from '../legacy/mct-template.vue'; import ContextMenu from '../controls/ContextMenu.vue'; import CreateButton from '../controls/CreateButton.vue'; import search from '../controls/search.vue'; import multipane from '../controls/multipane.vue'; import pane from '../controls/pane.vue'; - import MainViewBrowseBar from '../controls/MainViewBrowseBar.vue'; + import BrowseBar from './BrowseBar.vue'; export default { components: { Inspector, MctStatus, MctTree, - BrowseObject, + ObjectView, 'mct-template': MctTemplate, ContextMenu, CreateButton, search, multipane, pane, - MainViewBrowseBar + BrowseBar } } diff --git a/src/ui/components/layout/ObjectView.vue b/src/ui/components/layout/ObjectView.vue new file mode 100644 index 0000000000..06ca0955cd --- /dev/null +++ b/src/ui/components/layout/ObjectView.vue @@ -0,0 +1,38 @@ + + + + + + + diff --git a/src/ui/components/legacy/mct-template.vue b/src/ui/components/legacy/mct-template.vue index 025e8bf473..143aa6d5ae 100644 --- a/src/ui/components/legacy/mct-template.vue +++ b/src/ui/components/legacy/mct-template.vue @@ -22,8 +22,6 @@ export default { let $rootScope = $injector.get('$rootScope'); this.$scope = $rootScope.$new(); - console.log('mounting', this.templateKey); - console.log('template:', templateMap[this.templateKey]); templateLinker.link( this.$scope, diff --git a/src/ui/router/ApplicationRouter.js b/src/ui/router/ApplicationRouter.js index ec935feb16..c3f0f4fd87 100644 --- a/src/ui/router/ApplicationRouter.js +++ b/src/ui/router/ApplicationRouter.js @@ -101,7 +101,7 @@ class ApplicationRouter extends EventEmitter { doPathChange(newPath, oldPath, newLocation) { let route = this.routes.filter(r => r.matcher.test(newPath))[0]; if (route) { - route.callback(newPath, route.matcher.exec(newPath)); + route.callback(newPath, route.matcher.exec(newPath), this.currentLocation.params); } this.emit('change:path', newPath, oldPath); } diff --git a/src/ui/router/Browse.js b/src/ui/router/Browse.js new file mode 100644 index 0000000000..4f50ef4316 --- /dev/null +++ b/src/ui/router/Browse.js @@ -0,0 +1,80 @@ +define([ + +], function ( + +) { + + return function install(openmct) { + let navigateCall = 0; + let browseObject; + + + function viewObject(object, viewProvider) { + openmct.layout.$refs.browseObject.show(object, viewProvider); + openmct.layout.$refs.browseBar.domainObject = object; + openmct.layout.$refs.browseBar.viewKey = viewProvider.key; + }; + + function navigateToPath(path, currentViewKey) { + navigateCall++; + let currentNavigation = navigateCall; + + if (!Array.isArray(path)) { + path = path.split('/'); + } + let keyString = path[path.length - 1]; + // TODO: retain complete path in navigation. + return openmct.objects.get(keyString) + .then((object) => { + if (currentNavigation !== navigateCall) { + return; // Prevent race. + } + openmct.layout.$refs.browseBar.domainObject = object; + browseObject = object; + if (!object) { + openmct.layout.$refs.browseObject.clear(); + return; + } + let currentProvider = openmct + .objectViews + .getByProviderKey(currentViewKey) + + if (currentProvider && currentProvider.canView(object)) { + viewObject(object, currentProvider); + return; + } + + let defaultProvider = openmct.objectViews.get(object)[0]; + if (defaultProvider) { + openmct.router.updateParams({ + view: defaultProvider.key + }); + } else { + openmct.router.updateParams({ + view: undefined + }); + openmct.layout.$refs.browseObject.clear(); + } + }); + } + + openmct.router.route(/^\/browse\/(.*)$/, (path, results, params) => { + let navigatePath = results[1]; + if (!navigatePath) { + navigatePath = 'mine'; + } + navigateToPath(navigatePath, params.view); + }); + + openmct.router.on('change:params', function (newParams, oldParams, changed) { + if (changed.view && browseObject) { + let provider = openmct + .objectViews + .getByProviderKey(changed.view); + viewObject(browseObject, provider); + } + }); + + } + +});