mirror of
https://github.com/nasa/openmct.git
synced 2024-12-19 05:07:52 +00:00
Overlay Service re-written in Vue (#2186)
* working overlayService * wire to snapshot, and add onDestroy Callback * increment overlayId * New branch from topic-core-refactor to use as central point for common CSS work - Manually migrated changes from vue-toolbar, expect conflicts there and in vue-layout; * Manually update constants-snow from vue-toolbar branch * Update markup to use latest button classnames - c-menu-button > c-button--menu; - c-icon-button > c-click-icon; * Various from vue-conductor-style - Mods to input styling; - Input[] styles moved to _controls; - New/revised constants vals; * Resolve bizarre merge conflict when applying stash * Code cleanup * remove duplicate div * Alias and type-icon fixes - More robust approach to alias indicators; - Added alias indication to tree-item.vue; - TODO: wire up alias indication tree-item.vue; * Accessibility mods, convert elements to <button> - Better reset styles for htmlInputReset mixin to allow use of <button> without browser default styling; - Create button; - BrowseBar action buttons; - c-click-icons; - Removed Preview button from BrowseBar.vue; * Overlay styling WIP - Base markup pretty solid; - Stubbed in temp values for overlayTypeCssClass in overlayService.js; - TODO: styling for contents area; * add options object, scope variables to show function, add destroy callback to active Overlay Object (for easier retrieval
This commit is contained in:
parent
e7cdb334de
commit
f40c9fa6f9
@ -40,6 +40,7 @@ define([
|
||||
'./styles-new/core.scss',
|
||||
'./styles-new/notebook.scss',
|
||||
'./ui/components/layout/Layout.vue',
|
||||
'./ui/overlayService/overlayService',
|
||||
'vue'
|
||||
], function (
|
||||
EventEmitter,
|
||||
@ -61,6 +62,7 @@ define([
|
||||
coreStyles,
|
||||
NotebookStyles,
|
||||
Layout,
|
||||
OverlayService,
|
||||
Vue
|
||||
) {
|
||||
/**
|
||||
@ -225,6 +227,8 @@ define([
|
||||
|
||||
this.editor = new api.EditorAPI.default(this);
|
||||
|
||||
this.OverlayService = new OverlayService();
|
||||
|
||||
this.legacyRegistry = defaultRegistry;
|
||||
this.install(this.plugins.Plot());
|
||||
this.install(this.plugins.TelemetryTable());
|
||||
|
29
src/plugins/notebook/res/templates/snapshotTemplate.html
Normal file
29
src/plugins/notebook/res/templates/snapshotTemplate.html
Normal file
@ -0,0 +1,29 @@
|
||||
<div class="u-contents">
|
||||
|
||||
<div class="t-snapshot abs l-view-header">
|
||||
<div class="abs object-browse-bar l-flex-row">
|
||||
<div class="left flex-elem l-flex-row grows">
|
||||
<div class="object-header flex-elem l-flex-row grows">
|
||||
<div class="type-icon flex-elem embed-icon holder" v-bind:class="embed.cssClass"></div>
|
||||
<div class="title-label flex-elem holder flex-can-shrink">{{embed.name}}</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="btn-bar right l-flex-row flex-elem flex-justify-end flex-fixed">
|
||||
<div class="flex-elem holder flex-can-shrink s-snapshot-datetime">
|
||||
SNAPSHOT {{formatTime(embed.createdOn, 'YYYY-MM-DD HH:mm:ss')}}
|
||||
</div>
|
||||
<a class="s-button icon-pencil" title="Annotate">
|
||||
<span class="title-label">Annotate</span>
|
||||
</a>
|
||||
</div>
|
||||
|
||||
<div class="abs object-holder t-image-holder s-image-holder">
|
||||
<div
|
||||
class="image-main s-image-main"
|
||||
v-bind:style="{ backgroundImage: 'url(' + embed.snapshot.src + ')' }">
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
@ -24,11 +24,15 @@ define([
|
||||
'moment',
|
||||
'zepto',
|
||||
'../utils/SnapshotOverlay',
|
||||
'../../res/templates/snapshotTemplate.html',
|
||||
'vue'
|
||||
],
|
||||
function (
|
||||
Moment,
|
||||
$,
|
||||
SnapshotOverlay
|
||||
SnapshotOverlay,
|
||||
SnapshotTemplate,
|
||||
Vue
|
||||
) {
|
||||
function EmbedController (openmct, domainObject) {
|
||||
this.openmct = openmct;
|
||||
@ -53,11 +57,24 @@ function (
|
||||
};
|
||||
|
||||
EmbedController.prototype.openSnapshot = function () {
|
||||
if (!this.snapshotOverlay) {
|
||||
this.snapShotOverlay = new SnapshotOverlay(this.embed, this.formatTime);
|
||||
} else {
|
||||
this.snapShotOverlay = undefined;
|
||||
var self = this,
|
||||
snapshot = new Vue({
|
||||
template: SnapshotTemplate,
|
||||
data: function () {
|
||||
return {
|
||||
embed: self.embed
|
||||
};
|
||||
},
|
||||
methods: {
|
||||
formatTime: self.formatTime
|
||||
}
|
||||
});
|
||||
|
||||
function onDestroyCallback() {
|
||||
snapshot.$destroy(true);
|
||||
}
|
||||
|
||||
this.openmct.OverlayService.show(snapshot.$mount().$el, {onDestroy: onDestroyCallback, cssClass: 'l-large-view'});
|
||||
};
|
||||
|
||||
EmbedController.prototype.formatTime = function (unixTime, timeFormat) {
|
||||
|
@ -60,6 +60,7 @@ function (
|
||||
this.container = container;
|
||||
|
||||
var notebookEmbed = {
|
||||
inject:['openmct'],
|
||||
props:['embed', 'entry'],
|
||||
template: EmbedTemplate,
|
||||
data: embedController.exposedData,
|
||||
@ -80,6 +81,7 @@ function (
|
||||
|
||||
var notebookVue = Vue.extend({
|
||||
template: NotebookTemplate,
|
||||
provide: {openmct: self.openmct},
|
||||
components: {
|
||||
'notebook-entry': entryComponent,
|
||||
'search': search.default
|
||||
|
@ -224,9 +224,9 @@ $colorThumbsBubbleFg: pullForward($colorBodyFg, 10%);
|
||||
$colorThumbsBubbleBg: pullForward($colorBodyBg, 10%);
|
||||
|
||||
// Overlay
|
||||
$colorOvrBlocker: rgba(black, 0.7);//
|
||||
$colorOvrBg: $colorBodyBg;
|
||||
$colorOvrFg: $colorBodyFg;
|
||||
$colorOvrBlocker: rgba(black, 0.7); // Used
|
||||
$colorOvrBg: $colorBodyBg; // Used
|
||||
$colorOvrFg: $colorBodyFg; // Used
|
||||
$colorOvrBtnBg: pullForward($colorOvrBg, 40%);
|
||||
$colorOvrBtnFg: #fff;
|
||||
$colorFieldHintOverlay: pullForward($colorOvrBg, 40%);
|
||||
|
@ -40,6 +40,8 @@ $inputTextP: $inputTextPTopBtm $inputTextPLeftRight;
|
||||
$menuLineH: 1.5rem;
|
||||
$treeItemIndent: 16px;
|
||||
$treeTypeIconW: 18px;
|
||||
$overlayOuterMargin: 5%;
|
||||
$overlayInnerMargin: 25px;
|
||||
|
||||
/*************** Items */
|
||||
$itemPadLR: 5px;
|
||||
|
@ -20,6 +20,8 @@
|
||||
* at runtime from the About dialog for additional information.
|
||||
*****************************************************************************/
|
||||
|
||||
// VERSION MANUALLY MIGRATED FROM VUE-TOOLBAR
|
||||
|
||||
/************************** VISUALS */
|
||||
@mixin ancillaryIcon($d, $c) {
|
||||
// Used for small icons used in combination with larger icons,
|
||||
|
@ -30,7 +30,7 @@
|
||||
import viewControl from '../controls/viewControl.vue'
|
||||
export default {
|
||||
name: 'tree-item',
|
||||
inject: ['openmct'],
|
||||
inject: ['openmct', 'domainObject'],
|
||||
props: {
|
||||
node: Object
|
||||
},
|
||||
|
91
src/ui/overlayService/overlay.vue
Normal file
91
src/ui/overlayService/overlay.vue
Normal file
@ -0,0 +1,91 @@
|
||||
<template>
|
||||
<div class="c-overlay">
|
||||
<div class="c-overlay__blocker"
|
||||
v-on:click="destroy">
|
||||
</div>
|
||||
<div class="c-overlay__outer">
|
||||
<button class="c-click-icon c-overlay__close-button icon-x-in-circle"
|
||||
v-on:click="destroy">
|
||||
</button>
|
||||
<div class="c-overlay__contents" ref="element"></div>
|
||||
<div class="c-overlay__button-bar">
|
||||
<button class="c-button c-button--major"
|
||||
v-on:click="destroy">Done</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="scss">
|
||||
@import "~styles/sass-base";
|
||||
|
||||
.l-overlay-wrapper {
|
||||
// Created by overlayService.js, contains this template.
|
||||
// Acts as an anchor for one or more overlays.
|
||||
display: contents;
|
||||
}
|
||||
|
||||
.c-overlay {
|
||||
@include abs();
|
||||
z-index: 100;
|
||||
|
||||
&__blocker {
|
||||
display: none; // Mobile-first
|
||||
}
|
||||
|
||||
&__outer {
|
||||
@include abs();
|
||||
background: $colorOvrBg;
|
||||
color: $colorOvrFg;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
padding: $overlayInnerMargin;
|
||||
}
|
||||
|
||||
&__close-button {
|
||||
$p: $interiorMarginSm;
|
||||
border-radius: 100%;
|
||||
display: inline-block;
|
||||
position: absolute;
|
||||
top: $p; right: $p;
|
||||
}
|
||||
|
||||
&__contents {
|
||||
flex: 1 1 auto;
|
||||
overflow: auto;
|
||||
}
|
||||
|
||||
&__button-bar {
|
||||
flex: 0 0 auto;
|
||||
display: flex;
|
||||
justify-content: flex-end;
|
||||
margin-top: $interiorMargin;
|
||||
}
|
||||
|
||||
body.desktop & {
|
||||
&__blocker {
|
||||
@include abs();
|
||||
background: $colorOvrBlocker;
|
||||
cursor: pointer;
|
||||
display: block;
|
||||
}
|
||||
|
||||
&__outer {
|
||||
$m: $overlayOuterMargin;
|
||||
top: $m; right: $m; bottom: $m; left: $m;
|
||||
border-radius: $overlayCr;
|
||||
box-shadow: rgba(black, 0.5) 0 2px 25px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
</style>
|
||||
|
||||
<script>
|
||||
export default {
|
||||
inject: ['destroy', 'element'],
|
||||
mounted() {
|
||||
this.$refs.element.appendChild(this.element);
|
||||
}
|
||||
}
|
||||
</script>
|
87
src/ui/overlayService/overlayService.js
Normal file
87
src/ui/overlayService/overlayService.js
Normal file
@ -0,0 +1,87 @@
|
||||
/*****************************************************************************
|
||||
* Open MCT, Copyright (c) 2014-2018, United States Government
|
||||
* as represented by the Administrator of the National Aeronautics and Space
|
||||
* Administration. All rights reserved.
|
||||
*
|
||||
* Open MCT is 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.
|
||||
*
|
||||
* Open MCT includes source code licensed under additional open source
|
||||
* licenses. See the Open Source Licenses file (LICENSES.md) included with
|
||||
* this source code distribution or the Licensing information page available
|
||||
* at runtime from the About dialog for additional information.
|
||||
*****************************************************************************/
|
||||
|
||||
define([
|
||||
'./overlay.vue',
|
||||
'vue'
|
||||
], function (
|
||||
OverlayComponent,
|
||||
Vue
|
||||
) {
|
||||
|
||||
function OverlayService() {
|
||||
this.activeOverlays = [];
|
||||
this.overlayId = 0;
|
||||
}
|
||||
|
||||
OverlayService.prototype.show = function (element, options) {
|
||||
if(this.activeOverlays.length) {
|
||||
this.activeOverlays[this.activeOverlays.length - 1].overlay.classList.add('invisible');
|
||||
}
|
||||
|
||||
let overlayTypeCssClass = options.cssClass, // Values could be l-large-view, l-dialog, l-message
|
||||
overlay = document.createElement('div'),
|
||||
component = new Vue({
|
||||
provide: {
|
||||
destroy: this.destroy.bind(this),
|
||||
element: element
|
||||
},
|
||||
components: {
|
||||
OverlayComponent: OverlayComponent.default
|
||||
},
|
||||
template: '<overlay-component></overlay-component>'
|
||||
});
|
||||
|
||||
overlay.classList.add('l-overlay-wrapper', overlayTypeCssClass);
|
||||
document.body.appendChild(overlay);
|
||||
|
||||
overlay.appendChild(component.$mount().$el);
|
||||
|
||||
this.activeOverlays.push({
|
||||
overlay: overlay,
|
||||
component: component,
|
||||
onDestroy: options.onDestroy,
|
||||
id: this.overlayId
|
||||
});
|
||||
|
||||
this.overlayId++;
|
||||
};
|
||||
|
||||
OverlayService.prototype.destroy = function () {
|
||||
var lastActiveOverlayObject = this.activeOverlays.pop(),
|
||||
lastActiveOverlay = lastActiveOverlayObject.overlay,
|
||||
lastActiveComponent = lastActiveOverlayObject.component;
|
||||
|
||||
if (lastActiveOverlayObject.onDestroy && typeof lastActiveOverlayObject.onDestroy === 'function') {
|
||||
lastActiveOverlayObject.onDestroy();
|
||||
}
|
||||
|
||||
lastActiveComponent.$destroy(true);
|
||||
document.body.removeChild(lastActiveOverlay);
|
||||
|
||||
if (this.activeOverlays.length) {
|
||||
this.activeOverlays[this.activeOverlays.length - 1].overlay.classList.remove('invisible');
|
||||
}
|
||||
};
|
||||
|
||||
return OverlayService;
|
||||
});
|
Loading…
Reference in New Issue
Block a user