Compare commits

...

8 Commits

Author SHA1 Message Date
294bed974f not keeping background tabs alive 2021-10-14 11:47:37 -07:00
4c9c084eec #4197 - make time conductor history more readable (#4287) 2021-10-13 17:02:47 -07:00
b64ee10812 Fix #4299 (#4300) 2021-10-13 16:42:45 -07:00
ee1ecf43db Fix leftover lint errors/warnings (#4316) 2021-10-13 16:15:23 -07:00
4d8db8eb7c Update Conductor.vue (#4150)
* checking for NaN on pan

Lint resolved

Co-authored-by: Jamie V <jamie.j.vigliotta@nasa.gov>
2021-10-12 14:04:58 -07:00
1b13965200 Fix #3981 (#4302)
* Fix #3981
- Mods to markup and CSS for better approach to overflowing and min-heights;
- WIP!

* Fix #3981
- Refinements to min-height approach;
- CSS cleanups;

Co-authored-by: Jamie V <jamie.j.vigliotta@nasa.gov>
2021-10-07 14:50:54 -05:00
38db8f7fe5 Fix #4090 (#4298)
- HTML/CSS mods to remove button holding element that was blocking clicks,
instead position buttons independently;
- Disabled style now handled better in `show-on-hover` class;
- Removed overly-specific size and positioning defs from cArrowButtonBase mixin;
2021-10-07 10:41:39 -07:00
4ba8f893a6 authors should think about backwards compatibility (#4223)
* authors should think about backwards compatibility

* Add reviewer check for breaking changes
2021-09-23 10:45:07 -05:00
22 changed files with 145 additions and 127 deletions

View File

@ -2,6 +2,7 @@
* [ ] Have you followed the guidelines in our [Contributing document](https://github.com/nasa/openmct/blob/master/CONTRIBUTING.md)? * [ ] Have you followed the guidelines in our [Contributing document](https://github.com/nasa/openmct/blob/master/CONTRIBUTING.md)?
* [ ] Have you checked to ensure there aren't other open [Pull Requests](https://github.com/nasa/openmct/pulls) for the same update/change? * [ ] Have you checked to ensure there aren't other open [Pull Requests](https://github.com/nasa/openmct/pulls) for the same update/change?
* [ ] Is this change backwards compatible? Will users need to change how they are calling the API, or how they've extended core plugins such as Tables or Plots?
### Author Checklist ### Author Checklist

View File

@ -317,6 +317,7 @@ checklist).
### Reviewer Checklist ### Reviewer Checklist
* [ ] Changes appear to address issue? * [ ] Changes appear to address issue?
* [ ] Changes appear not to be breaking changes?
* [ ] Appropriate unit tests included? * [ ] Appropriate unit tests included?
* [ ] Code style and in-line documentation are appropriate? * [ ] Code style and in-line documentation are appropriate?
* [ ] Commit messages meet standards? * [ ] Commit messages meet standards?

View File

@ -25,15 +25,14 @@ define([
], function ( ], function (
moment moment
) { ) {
const DATE_FORMAT = "YYYY-MM-DD HH:mm:ss.SSS";
var DATE_FORMAT = "YYYY-MM-DD HH:mm:ss.SSS", const DATE_FORMATS = [
DATE_FORMATS = [ DATE_FORMAT,
DATE_FORMAT, DATE_FORMAT + "Z",
DATE_FORMAT + "Z", "YYYY-MM-DD HH:mm:ss",
"YYYY-MM-DD HH:mm:ss", "YYYY-MM-DD HH:mm",
"YYYY-MM-DD HH:mm", "YYYY-MM-DD"
"YYYY-MM-DD" ];
];
/** /**
* @typedef Scale * @typedef Scale
@ -53,15 +52,27 @@ define([
this.key = "utc"; this.key = "utc";
} }
/**
* @param {string} formatString
* @returns the value of formatString if the value is a string type and exists in the DATE_FORMATS array; otherwise the DATE_FORMAT value.
*/
function validateFormatString(formatString) {
return typeof formatString === 'string' && DATE_FORMATS.includes(formatString) ? formatString : DATE_FORMAT;
}
/** /**
* @param {number} value The value to format. * @param {number} value The value to format.
* @returns {string} the formatted date(s). If multiple values were requested, then an array of * @param {string} formatString The string format to format. Default "YYYY-MM-DD HH:mm:ss.SSS" + "Z"
* @returns {string} the formatted date(s) according to the proper parameter of formatString or the default value of "YYYY-MM-DD HH:mm:ss.SSS" + "Z".
* If multiple values were requested, then an array of
* formatted values will be returned. Where a value could not be formatted, `undefined` will be returned at its position * formatted values will be returned. Where a value could not be formatted, `undefined` will be returned at its position
* in the array. * in the array.
*/ */
UTCTimeFormat.prototype.format = function (value) { UTCTimeFormat.prototype.format = function (value, formatString) {
if (value !== undefined) { if (value !== undefined) {
return moment.utc(value).format(DATE_FORMAT) + "Z"; const format = validateFormatString(formatString);
return moment.utc(value).format(format) + (formatString ? '' : 'Z');
} else { } else {
return value; return value;
} }

View File

@ -30,10 +30,10 @@
<div v-if="staticStyle" <div v-if="staticStyle"
class="c-inspect-styles__style" class="c-inspect-styles__style"
> >
<style-editor class="c-inspect-styles__editor" <StyleEditor class="c-inspect-styles__editor"
:style-item="staticStyle" :style-item="staticStyle"
:is-editing="isEditing" :is-editing="isEditing"
@persist="updateStaticStyle" @persist="updateStaticStyle"
/> />
</div> </div>
<button <button
@ -87,10 +87,10 @@
<condition-description :show-label="true" <condition-description :show-label="true"
:condition="getCondition(conditionStyle.conditionId)" :condition="getCondition(conditionStyle.conditionId)"
/> />
<style-editor class="c-inspect-styles__editor" <StyleEditor class="c-inspect-styles__editor"
:style-item="conditionStyle" :style-item="conditionStyle"
:is-editing="isEditing" :is-editing="isEditing"
@persist="updateConditionalStyle" @persist="updateConditionalStyle"
/> />
</div> </div>
</div> </div>
@ -240,10 +240,10 @@ export default {
} }
let vm = new Vue({ let vm = new Vue({
components: {ConditionSetSelectorDialog},
provide: { provide: {
openmct: this.openmct openmct: this.openmct
}, },
components: {ConditionSetSelectorDialog},
data() { data() {
return { return {
handleItemSelection handleItemSelection

View File

@ -40,13 +40,13 @@
<div v-if="staticStyle" <div v-if="staticStyle"
class="c-inspect-styles__style" class="c-inspect-styles__style"
> >
<style-editor class="c-inspect-styles__editor" <StyleEditor class="c-inspect-styles__editor"
:style-item="staticStyle" :style-item="staticStyle"
:is-editing="allowEditing" :is-editing="allowEditing"
:mixed-styles="mixedStyles" :mixed-styles="mixedStyles"
:non-specific-font-properties="nonSpecificFontProperties" :non-specific-font-properties="nonSpecificFontProperties"
@persist="updateStaticStyle" @persist="updateStaticStyle"
@save-style="saveStyle" @save-style="saveStyle"
/> />
</div> </div>
<button <button
@ -108,12 +108,12 @@
<condition-description :show-label="true" <condition-description :show-label="true"
:condition="getCondition(conditionStyle.conditionId)" :condition="getCondition(conditionStyle.conditionId)"
/> />
<style-editor class="c-inspect-styles__editor" <StyleEditor class="c-inspect-styles__editor"
:style-item="conditionStyle" :style-item="conditionStyle"
:non-specific-font-properties="nonSpecificFontProperties" :non-specific-font-properties="nonSpecificFontProperties"
:is-editing="allowEditing" :is-editing="allowEditing"
@persist="updateConditionalStyle" @persist="updateConditionalStyle"
@save-style="saveStyle" @save-style="saveStyle"
/> />
</div> </div>
</div> </div>
@ -556,10 +556,10 @@ export default {
} }
let vm = new Vue({ let vm = new Vue({
components: {ConditionSetSelectorDialog},
provide: { provide: {
openmct: this.openmct openmct: this.openmct
}, },
components: {ConditionSetSelectorDialog},
data() { data() {
return { return {
handleItemSelection handleItemSelection

View File

@ -47,8 +47,8 @@
.is-editing { .is-editing {
.l-shell__main-container { .l-shell__main-container {
&[s-selected], [s-selected],
&[s-selected-parent] { [s-selected-parent] {
// Display grid and allow edit marquee to display in main layout holder when editing // Display grid and allow edit marquee to display in main layout holder when editing
> .l-layout { > .l-layout {
background: $editUIGridColorBg; background: $editUIGridColorBg;

View File

@ -84,18 +84,18 @@
/> />
</div> </div>
</div> </div>
<div class="c-local-controls c-local-controls--show-on-hover c-imagery__prev-next-buttons">
<button class="c-nav c-nav--prev" <button class="c-local-controls c-local-controls--show-on-hover c-imagery__prev-next-button c-nav c-nav--prev"
title="Previous image" title="Previous image"
:disabled="isPrevDisabled" :disabled="isPrevDisabled"
@click="prevImage()" @click="prevImage()"
></button> ></button>
<button class="c-nav c-nav--next"
title="Next image" <button class="c-local-controls c-local-controls--show-on-hover c-imagery__prev-next-button c-nav c-nav--next"
:disabled="isNextDisabled" title="Next image"
@click="nextImage()" :disabled="isNextDisabled"
></button> @click="nextImage()"
</div> ></button>
<div class="c-imagery__control-bar"> <div class="c-imagery__control-bar">
<div class="c-imagery__time"> <div class="c-imagery__time">

View File

@ -285,17 +285,17 @@
} }
} }
.c-imagery__prev-next-buttons { .c-imagery__prev-next-button {
display: flex; pointer-events: all;
width: 100%;
justify-content: space-between;
pointer-events: none;
position: absolute; position: absolute;
top: 50%; top: 50%;
transform: translateY(-75%); transform: translateY(-75%); // 75% due to transform: rotation approach to the button
.c-nav { &.c-nav {
pointer-events: all; position: absolute;
&--prev { left: 0; }
&--next { right: 0; }
} }
.s-status-taking-snapshot & { .s-status-taking-snapshot & {

View File

@ -45,8 +45,7 @@
</div> </div>
</div> </div>
</template> </template>
<style lang="sass">
</style>
<script> <script>
import packages from './third-party-licenses.json'; import packages from './third-party-licenses.json';

View File

@ -39,10 +39,6 @@ export default function BarGraphCompositionPolicy(openmct) {
return metadata.values().length > 0 && hasAggregateDomainAndRange(metadata); return metadata.values().length > 0 && hasAggregateDomainAndRange(metadata);
} }
function hasNoChildren(parentObject) {
return parentObject.composition && parentObject.composition.length < 1;
}
return { return {
allow: function (parent, child) { allow: function (parent, child) {
if ((parent.type === BAR_GRAPH_KEY) if ((parent.type === BAR_GRAPH_KEY)

View File

@ -19,6 +19,9 @@
this source code distribution or the Licensing information page available this source code distribution or the Licensing information page available
at runtime from the About dialog for additional information. at runtime from the About dialog for additional information.
--> -->
<!-- eslint-disable vue/no-v-html -->
<template> <template>
<div class="gl-plot-chart-area"> <div class="gl-plot-chart-area">
<span v-html="canvasTemplate"></span> <span v-html="canvasTemplate"></span>

View File

@ -52,17 +52,19 @@
> >
</button> </button>
</div> </div>
<stacked-plot-item v-for="object in compositionObjects" <div class="l-view-section">
:key="object.id" <stacked-plot-item v-for="object in compositionObjects"
class="c-plot--stacked-container" :key="object.id"
:object="object" class="c-plot--stacked-container"
:options="options" :object="object"
:grid-lines="gridLines" :options="options"
:cursor-guide="cursorGuide" :grid-lines="gridLines"
:plot-tick-width="maxTickWidth" :cursor-guide="cursorGuide"
@plotTickWidth="onTickWidthChange" :plot-tick-width="maxTickWidth"
@loadingUpdated="loadingUpdated" @plotTickWidth="onTickWidthChange"
/> @loadingUpdated="loadingUpdated"
/>
</div>
</div> </div>
</template> </template>

View File

@ -152,7 +152,11 @@ export default {
}, },
methods: { methods: {
addTabToLoaded(tab) { addTabToLoaded(tab) {
this.loadedTabs[tab.keyString] = true; if (this.internalDomainObject.keep_alive) {
this.loadedTabs[tab.keyString] = true;
} else {
this.loadedTabs = { [tab.keyString]: true };
}
}, },
setCurrentTabByIndex(index) { setCurrentTabByIndex(index) {
if (this.tabsList[index]) { if (this.tabsList[index]) {

View File

@ -48,17 +48,17 @@ define([
components: { components: {
TabsComponent: TabsComponent.default TabsComponent: TabsComponent.default
}, },
data() {
return {
isEditing: editMode
};
},
provide: { provide: {
openmct, openmct,
domainObject, domainObject,
objectPath, objectPath,
composition: openmct.composition.get(domainObject) composition: openmct.composition.get(domainObject)
}, },
data() {
return {
isEditing: editMode
};
},
template: '<tabs-component :isEditing="isEditing"></tabs-component>' template: '<tabs-component :isEditing="isEditing"></tabs-component>'
}); });
}, },

View File

@ -168,13 +168,16 @@ export default {
} }
}, },
zoom(bounds) { zoom(bounds) {
this.isZooming = true; if (isNaN(bounds.start) || isNaN(bounds.end)) {
this.formattedBounds.start = this.timeFormatter.format(bounds.start); this.isZooming = false;
this.formattedBounds.end = this.timeFormatter.format(bounds.end); } else {
this.isZooming = true;
this.formattedBounds.start = this.timeFormatter.format(bounds.start);
this.formattedBounds.end = this.timeFormatter.format(bounds.end);
}
}, },
endZoom(bounds) { endZoom(bounds) {
this.isZooming = false; this.isZooming = false;
if (bounds) { if (bounds) {
this.openmct.time.bounds(bounds); this.openmct.time.bounds(bounds);
} else { } else {

View File

@ -40,7 +40,7 @@ const LOCAL_STORAGE_HISTORY_KEY_FIXED = 'tcHistory';
const LOCAL_STORAGE_HISTORY_KEY_REALTIME = 'tcHistoryRealtime'; const LOCAL_STORAGE_HISTORY_KEY_REALTIME = 'tcHistoryRealtime';
const DEFAULT_RECORDS = 10; const DEFAULT_RECORDS = 10;
import { getDuration } from "utils/duration"; import { millisecondsToDHMS } from "utils/duration";
export default { export default {
inject: ['openmct', 'configuration'], inject: ['openmct', 'configuration'],
@ -142,7 +142,7 @@ export default {
let description = `${startTime} - ${this.formatTime(timespan.end)}`; let description = `${startTime} - ${this.formatTime(timespan.end)}`;
if (this.timeSystem.isUTCBased && !this.openmct.time.clock()) { if (this.timeSystem.isUTCBased && !this.openmct.time.clock()) {
name = `${startTime} ${getDuration(timespan.end - timespan.start)}`; name = `${startTime} ${millisecondsToDHMS(timespan.end - timespan.start)}`;
} else { } else {
name = description; name = description;
} }
@ -263,7 +263,7 @@ export default {
format: format format: format
}).formatter; }).formatter;
return (isNegativeOffset ? '-' : '') + formatter.format(time); return (isNegativeOffset ? '-' : '') + formatter.format(time, 'YYYY-MM-DD HH:mm:ss');
}, },
showHistoryMenu() { showHistoryMenu() {
const elementBoundingClientRect = this.$refs.historyButton.getBoundingClientRect(); const elementBoundingClientRect = this.$refs.historyButton.getBoundingClientRect();

View File

@ -1006,6 +1006,9 @@ input[type="range"] {
transition: $transIn; transition: $transIn;
opacity: 1; opacity: 1;
pointer-events: inherit; pointer-events: inherit;
&[disabled] { opacity: $controlDisabledOpacity; }
} }
} }

View File

@ -46,9 +46,6 @@ mct-plot {
.c-plot, .c-plot,
.gl-plot { .gl-plot {
overflow: hidden;
min-height: 100px;
.s-status-taking-snapshot & { .s-status-taking-snapshot & {
.c-control-bar { .c-control-bar {
display: none; display: none;
@ -67,16 +64,17 @@ mct-plot {
.c-plot { .c-plot {
@include abs($mainViewPad); @include abs($mainViewPad);
display: flex; display: flex;
flex-direction: column; flex-direction: column;
overflow: hidden;
min-height: $plotMinH;
.c-control-bar { .c-control-bar {
flex: 0 0 auto; flex: 0 0 auto;
margin-bottom: $interiorMargin; margin-bottom: $interiorMargin;
} }
.l-view-section, .c-plot--stacked-container { .l-view-section {
display: flex; display: flex;
flex: 1 1 auto; flex: 1 1 auto;
flex-direction: column; flex-direction: column;
@ -84,7 +82,18 @@ mct-plot {
overflow-x: hidden; overflow-x: hidden;
} }
.c-plot--stacked-container {
display: flex;
flex: 1 1 auto;
flex-direction: column;
min-height: $plotMinH;
overflow: hidden;
}
;
&--stacked { &--stacked {
min-height: auto !important;
.child-frame { .child-frame {
.has-control-bar { .has-control-bar {
.c-control-bar { .c-control-bar {
@ -124,7 +133,7 @@ mct-plot {
.plot-wrapper-axis-and-display-area { .plot-wrapper-axis-and-display-area {
position: relative; position: relative;
flex: 1 1 auto; flex: 1 1 auto;
min-height: $plotMinH; //min-height: $plotMinH;
} }
.gl-plot-wrapper-display-area-and-x-axis { .gl-plot-wrapper-display-area-and-x-axis {
@ -465,6 +474,7 @@ mct-plot {
.gl-plot-legend, .gl-plot-legend,
.c-plot-legend { .c-plot-legend {
overflow: hidden; overflow: hidden;
flex: 0 0 auto; // Prevents clipping for all legend placements (top, bottom, etc.)
&__wrapper { &__wrapper {
// Holds view-control and both collapsed and expanded legends // Holds view-control and both collapsed and expanded legends

View File

@ -599,8 +599,6 @@
@mixin cArrowButtonBase($colorBg: transparent, $colorFg: $colorBtnFg, $filterHov: $filterHov) { @mixin cArrowButtonBase($colorBg: transparent, $colorFg: $colorBtnFg, $filterHov: $filterHov) {
// Copied from branch new-tree-refactor // Copied from branch new-tree-refactor
flex: 0 0 auto;
position: relative;
background: $colorBg; background: $colorBg;
&:before { &:before {

View File

@ -54,15 +54,15 @@ export default {
let viewContainer = document.createElement('div'); let viewContainer = document.createElement('div');
this.$el.append(viewContainer); this.$el.append(viewContainer);
this.component = new Vue({ this.component = new Vue({
el: viewContainer,
components: {
StylesView
},
provide: { provide: {
openmct: this.openmct, openmct: this.openmct,
selection: selection, selection: selection,
stylesManager: this.stylesManager stylesManager: this.stylesManager
}, },
el: viewContainer,
components: {
StylesView
},
template: '<styles-view/>' template: '<styles-view/>'
}); });
} }

View File

@ -42,10 +42,10 @@ export default {
methods: { methods: {
launchAbout() { launchAbout() {
let vm = new Vue({ let vm = new Vue({
components: {AboutDialog},
provide: { provide: {
openmct: this.openmct openmct: this.openmct
}, },
components: {AboutDialog},
template: '<about-dialog></about-dialog>' template: '<about-dialog></about-dialog>'
}).$mount(); }).$mount();

View File

@ -20,7 +20,8 @@
* at runtime from the About dialog for additional information. * at runtime from the About dialog for additional information.
*****************************************************************************/ *****************************************************************************/
const ONE_MINUTE = 60 * 1000; const ONE_SECOND = 1000;
const ONE_MINUTE = 60 * ONE_SECOND;
const ONE_HOUR = ONE_MINUTE * 60; const ONE_HOUR = ONE_MINUTE * 60;
const ONE_DAY = ONE_HOUR * 24; const ONE_DAY = ONE_HOUR * 24;
@ -39,34 +40,20 @@ function toDoubleDigits(num) {
} }
} }
export function getDuration(numericDuration) { function addTimeSuffix(value, suffix) {
let result; return typeof value === 'number' && value > 0 ? `${value + suffix}` : '';
let age; }
if (numericDuration > ONE_DAY - 1) { export function millisecondsToDHMS(numericDuration) {
age = normalizeAge((numericDuration / ONE_DAY)).toFixed(2); const ms = numericDuration || 0;
result = `+ ${age} day`; const dhms = [
addTimeSuffix(Math.floor(normalizeAge(ms / ONE_DAY)), 'd'),
addTimeSuffix(Math.floor(normalizeAge((ms % ONE_DAY) / ONE_HOUR)), 'h'),
addTimeSuffix(Math.floor(normalizeAge((ms % ONE_HOUR) / ONE_MINUTE)), 'm'),
addTimeSuffix(Math.floor(normalizeAge((ms % ONE_MINUTE) / ONE_SECOND)), 's')
].filter(Boolean).join(' ');
if (age !== 1) { return `${ dhms ? '+' : ''} ${dhms}`;
result += 's';
}
} else if (numericDuration > ONE_HOUR - 1) {
age = normalizeAge((numericDuration / ONE_HOUR).toFixed(2));
result = `+ ${age} hour`;
if (age !== 1) {
result += 's';
}
} else {
age = normalizeAge((numericDuration / ONE_MINUTE).toFixed(2));
result = `+ ${age} min`;
if (age !== 1) {
result += 's';
}
}
return result;
} }
export function getPreciseDuration(numericDuration) { export function getPreciseDuration(numericDuration) {