Compare commits
	
		
			12 Commits
		
	
	
		
			memory-lea
			...
			1.7.4-stab
		
	
	| Author | SHA1 | Date | |
|---|---|---|---|
| 
						 | 
					0fa71da7ba | ||
| 
						 | 
					b6cc1924aa | ||
| 
						 | 
					3e97f32dba | ||
| 
						 | 
					558b802228 | ||
| 
						 | 
					de13f67ae5 | ||
| 
						 | 
					0256cc4830 | ||
| 
						 | 
					8422add614 | ||
| 
						 | 
					2114697d6f | ||
| 
						 | 
					412eaf599e | ||
| 
						 | 
					0691a35dab | ||
| 
						 | 
					f57191fd89 | ||
| 
						 | 
					14066b5c4d | 
@@ -20,149 +20,196 @@
 | 
			
		||||
 * at runtime from the About dialog for additional information.
 | 
			
		||||
 *****************************************************************************/
 | 
			
		||||
 | 
			
		||||
define([
 | 
			
		||||
const DEFAULT_IMAGE_SAMPLES = [
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18731.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18732.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18733.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18734.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18735.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18736.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18737.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18738.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18739.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18740.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18741.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18742.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18743.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18744.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18745.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18746.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18747.jpg",
 | 
			
		||||
    "https://www.hq.nasa.gov/alsj/a16/AS16-117-18748.jpg"
 | 
			
		||||
];
 | 
			
		||||
 | 
			
		||||
], function (
 | 
			
		||||
const DEFAULT_IMAGE_DELAY = 20000;
 | 
			
		||||
 | 
			
		||||
) {
 | 
			
		||||
    function ImageryPlugin() {
 | 
			
		||||
 | 
			
		||||
        const IMAGE_SAMPLES = [
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18731.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18732.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18733.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18734.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18735.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18736.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18737.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18738.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18739.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18740.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18741.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18742.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18743.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18744.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18745.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18746.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18747.jpg",
 | 
			
		||||
            "https://www.hq.nasa.gov/alsj/a16/AS16-117-18748.jpg"
 | 
			
		||||
        ];
 | 
			
		||||
        const IMAGE_DELAY = 20000;
 | 
			
		||||
 | 
			
		||||
        function pointForTimestamp(timestamp, name) {
 | 
			
		||||
            const url = IMAGE_SAMPLES[Math.floor(timestamp / IMAGE_DELAY) % IMAGE_SAMPLES.length];
 | 
			
		||||
            const urlItems = url.split('/');
 | 
			
		||||
            const imageDownloadName = `example.imagery.${urlItems[urlItems.length - 1]}`;
 | 
			
		||||
 | 
			
		||||
            return {
 | 
			
		||||
                name,
 | 
			
		||||
                utc: Math.floor(timestamp / IMAGE_DELAY) * IMAGE_DELAY,
 | 
			
		||||
                local: Math.floor(timestamp / IMAGE_DELAY) * IMAGE_DELAY,
 | 
			
		||||
                url,
 | 
			
		||||
                imageDownloadName
 | 
			
		||||
            };
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        var realtimeProvider = {
 | 
			
		||||
            supportsSubscribe: function (domainObject) {
 | 
			
		||||
                return domainObject.type === 'example.imagery';
 | 
			
		||||
            },
 | 
			
		||||
            subscribe: function (domainObject, callback) {
 | 
			
		||||
                var interval = setInterval(function () {
 | 
			
		||||
                    callback(pointForTimestamp(Date.now(), domainObject.name));
 | 
			
		||||
                }, IMAGE_DELAY);
 | 
			
		||||
 | 
			
		||||
                return function () {
 | 
			
		||||
                    clearInterval(interval);
 | 
			
		||||
export default function () {
 | 
			
		||||
    return function install(openmct) {
 | 
			
		||||
        console.log('isntall');
 | 
			
		||||
        openmct.types.addType('example.imagery', {
 | 
			
		||||
            key: 'example.imagery',
 | 
			
		||||
            name: 'Example Imagery',
 | 
			
		||||
            cssClass: 'icon-image',
 | 
			
		||||
            description: 'For development use. Creates example imagery '
 | 
			
		||||
                + 'data that mimics a live imagery stream.',
 | 
			
		||||
            creatable: true,
 | 
			
		||||
            initialize: (object) => {
 | 
			
		||||
                object.configuration = {
 | 
			
		||||
                    imageLocation: '',
 | 
			
		||||
                    imageLoadDelayInMilliSeconds: DEFAULT_IMAGE_DELAY,
 | 
			
		||||
                    imageSamples: []
 | 
			
		||||
                };
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        var historicalProvider = {
 | 
			
		||||
            supportsRequest: function (domainObject, options) {
 | 
			
		||||
                return domainObject.type === 'example.imagery'
 | 
			
		||||
                    && options.strategy !== 'latest';
 | 
			
		||||
            },
 | 
			
		||||
            request: function (domainObject, options) {
 | 
			
		||||
                var start = options.start;
 | 
			
		||||
                var end = Math.min(options.end, Date.now());
 | 
			
		||||
                var data = [];
 | 
			
		||||
                while (start <= end && data.length < IMAGE_DELAY) {
 | 
			
		||||
                    data.push(pointForTimestamp(start, domainObject.name));
 | 
			
		||||
                    start += IMAGE_DELAY;
 | 
			
		||||
                }
 | 
			
		||||
 | 
			
		||||
                return Promise.resolve(data);
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        var ladProvider = {
 | 
			
		||||
            supportsRequest: function (domainObject, options) {
 | 
			
		||||
                return domainObject.type === 'example.imagery'
 | 
			
		||||
                    && options.strategy === 'latest';
 | 
			
		||||
            },
 | 
			
		||||
            request: function (domainObject, options) {
 | 
			
		||||
                return Promise.resolve([pointForTimestamp(Date.now(), domainObject.name)]);
 | 
			
		||||
            }
 | 
			
		||||
        };
 | 
			
		||||
 | 
			
		||||
        return function install(openmct) {
 | 
			
		||||
            openmct.types.addType('example.imagery', {
 | 
			
		||||
                key: 'example.imagery',
 | 
			
		||||
                name: 'Example Imagery',
 | 
			
		||||
                cssClass: 'icon-image',
 | 
			
		||||
                description: 'For development use. Creates example imagery '
 | 
			
		||||
                    + 'data that mimics a live imagery stream.',
 | 
			
		||||
                creatable: true,
 | 
			
		||||
                initialize: function (object) {
 | 
			
		||||
                    object.telemetry = {
 | 
			
		||||
                        values: [
 | 
			
		||||
                            {
 | 
			
		||||
                                name: 'Name',
 | 
			
		||||
                                key: 'name'
 | 
			
		||||
                            },
 | 
			
		||||
                            {
 | 
			
		||||
                                name: 'Time',
 | 
			
		||||
                                key: 'utc',
 | 
			
		||||
                                format: 'utc',
 | 
			
		||||
                                hints: {
 | 
			
		||||
                                    domain: 2
 | 
			
		||||
                                }
 | 
			
		||||
                            },
 | 
			
		||||
                            {
 | 
			
		||||
                                name: 'Local Time',
 | 
			
		||||
                                key: 'local',
 | 
			
		||||
                                format: 'local-format',
 | 
			
		||||
                                hints: {
 | 
			
		||||
                                    domain: 1
 | 
			
		||||
                                }
 | 
			
		||||
                            },
 | 
			
		||||
                            {
 | 
			
		||||
                                name: 'Image',
 | 
			
		||||
                                key: 'url',
 | 
			
		||||
                                format: 'image',
 | 
			
		||||
                                hints: {
 | 
			
		||||
                                    image: 1
 | 
			
		||||
                                }
 | 
			
		||||
                            },
 | 
			
		||||
                            {
 | 
			
		||||
                                name: 'Image Download Name',
 | 
			
		||||
                                key: 'imageDownloadName',
 | 
			
		||||
                                format: 'imageDownloadName',
 | 
			
		||||
                                hints: {
 | 
			
		||||
                                    imageDownloadName: 1
 | 
			
		||||
                                }
 | 
			
		||||
                object.telemetry = {
 | 
			
		||||
                    values: [
 | 
			
		||||
                        {
 | 
			
		||||
                            name: 'Name',
 | 
			
		||||
                            key: 'name'
 | 
			
		||||
                        },
 | 
			
		||||
                        {
 | 
			
		||||
                            name: 'Time',
 | 
			
		||||
                            key: 'utc',
 | 
			
		||||
                            format: 'utc',
 | 
			
		||||
                            hints: {
 | 
			
		||||
                                domain: 2
 | 
			
		||||
                            }
 | 
			
		||||
                        ]
 | 
			
		||||
                    };
 | 
			
		||||
                        },
 | 
			
		||||
                        {
 | 
			
		||||
                            name: 'Local Time',
 | 
			
		||||
                            key: 'local',
 | 
			
		||||
                            format: 'local-format',
 | 
			
		||||
                            hints: {
 | 
			
		||||
                                domain: 1
 | 
			
		||||
                            }
 | 
			
		||||
                        },
 | 
			
		||||
                        {
 | 
			
		||||
                            name: 'Image',
 | 
			
		||||
                            key: 'url',
 | 
			
		||||
                            format: 'image',
 | 
			
		||||
                            hints: {
 | 
			
		||||
                                image: 1
 | 
			
		||||
                            }
 | 
			
		||||
                        },
 | 
			
		||||
                        {
 | 
			
		||||
                            name: 'Image Download Name',
 | 
			
		||||
                            key: 'imageDownloadName',
 | 
			
		||||
                            format: 'imageDownloadName',
 | 
			
		||||
                            hints: {
 | 
			
		||||
                                imageDownloadName: 1
 | 
			
		||||
                            }
 | 
			
		||||
                        }
 | 
			
		||||
                    ]
 | 
			
		||||
                };
 | 
			
		||||
            },
 | 
			
		||||
            form: [
 | 
			
		||||
                {
 | 
			
		||||
                    key: 'imageLocation',
 | 
			
		||||
                    name: 'Images url list (comma separated)',
 | 
			
		||||
                    control: 'textarea',
 | 
			
		||||
                    cssClass: 'l-inline',
 | 
			
		||||
                    property: [
 | 
			
		||||
                        "configuration",
 | 
			
		||||
                        "imageLocation"
 | 
			
		||||
                    ]
 | 
			
		||||
                },
 | 
			
		||||
                {
 | 
			
		||||
                    key: 'imageLoadDelayInMilliSeconds',
 | 
			
		||||
                    name: 'Image load delay (milliSeconds)',
 | 
			
		||||
                    control: 'numberfield',
 | 
			
		||||
                    cssClass: 'l-inline',
 | 
			
		||||
                    property: [
 | 
			
		||||
                        "configuration",
 | 
			
		||||
                        "imageLoadDelayInMilliSeconds"
 | 
			
		||||
                    ]
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
            ]
 | 
			
		||||
        });
 | 
			
		||||
 | 
			
		||||
            openmct.telemetry.addProvider(realtimeProvider);
 | 
			
		||||
            openmct.telemetry.addProvider(historicalProvider);
 | 
			
		||||
            openmct.telemetry.addProvider(ladProvider);
 | 
			
		||||
        };
 | 
			
		||||
        openmct.telemetry.addProvider(getRealtimeProvider());
 | 
			
		||||
        openmct.telemetry.addProvider(getHistoricalProvider());
 | 
			
		||||
        openmct.telemetry.addProvider(getLadProvider());
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function getImageSamples(configuration) {
 | 
			
		||||
    let imageSamples = DEFAULT_IMAGE_SAMPLES;
 | 
			
		||||
 | 
			
		||||
    if (configuration.imageLocation && configuration.imageLocation.length) {
 | 
			
		||||
        imageSamples = getImageUrlListFromConfig(configuration);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return ImageryPlugin;
 | 
			
		||||
});
 | 
			
		||||
    return imageSamples;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function getImageUrlListFromConfig(configuration) {
 | 
			
		||||
    return configuration.imageLocation.split(',');
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function getCompassValues(min, max) {
 | 
			
		||||
    return min + Math.random() * (max - min);
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function getRealtimeProvider() {
 | 
			
		||||
    return {
 | 
			
		||||
        supportsSubscribe: domainObject => domainObject.type === 'example.imagery',
 | 
			
		||||
        subscribe: (domainObject, callback) => {
 | 
			
		||||
            const delay = domainObject.configuration.imageLoadDelayInMilliSeconds;
 | 
			
		||||
            const interval = setInterval(() => {
 | 
			
		||||
                callback(pointForTimestamp(Date.now(), domainObject.name, getImageSamples(domainObject.configuration), delay));
 | 
			
		||||
            }, delay);
 | 
			
		||||
 | 
			
		||||
            return () => {
 | 
			
		||||
                clearInterval(interval);
 | 
			
		||||
            };
 | 
			
		||||
        }
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function getHistoricalProvider() {
 | 
			
		||||
    return {
 | 
			
		||||
        supportsRequest: (domainObject, options) => {
 | 
			
		||||
            return domainObject.type === 'example.imagery'
 | 
			
		||||
                && options.strategy !== 'latest';
 | 
			
		||||
        },
 | 
			
		||||
        request: (domainObject, options) => {
 | 
			
		||||
            const delay = domainObject.configuration.imageLoadDelayInMilliSeconds;
 | 
			
		||||
            let start = options.start;
 | 
			
		||||
            const end = Math.min(options.end, Date.now());
 | 
			
		||||
            const data = [];
 | 
			
		||||
            while (start <= end && data.length < delay) {
 | 
			
		||||
                data.push(pointForTimestamp(start, domainObject.name, getImageSamples(domainObject.configuration), delay));
 | 
			
		||||
                start += delay;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            return Promise.resolve(data);
 | 
			
		||||
        }
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function getLadProvider() {
 | 
			
		||||
    return {
 | 
			
		||||
        supportsRequest: (domainObject, options) => {
 | 
			
		||||
            return domainObject.type === 'example.imagery'
 | 
			
		||||
                && options.strategy === 'latest';
 | 
			
		||||
        },
 | 
			
		||||
        request: (domainObject, options) => {
 | 
			
		||||
            const delay = domainObject.configuration.imageLoadDelayInMilliSeconds;
 | 
			
		||||
 | 
			
		||||
            return Promise.resolve([pointForTimestamp(Date.now(), domainObject.name, delay)]);
 | 
			
		||||
        }
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
function pointForTimestamp(timestamp, name, imageSamples, delay) {
 | 
			
		||||
    const url = imageSamples[Math.floor(timestamp / delay) % imageSamples.length];
 | 
			
		||||
    const urlItems = url.split('/');
 | 
			
		||||
    const imageDownloadName = `example.imagery.${urlItems[urlItems.length - 1]}`;
 | 
			
		||||
 | 
			
		||||
    return {
 | 
			
		||||
        name,
 | 
			
		||||
        utc: Math.floor(timestamp / delay) * delay,
 | 
			
		||||
        local: Math.floor(timestamp / delay) * delay,
 | 
			
		||||
        url,
 | 
			
		||||
        imageDownloadName
 | 
			
		||||
    };
 | 
			
		||||
}
 | 
			
		||||
 
 | 
			
		||||
@@ -1,6 +1,6 @@
 | 
			
		||||
{
 | 
			
		||||
  "name": "openmct",
 | 
			
		||||
  "version": "1.7.4-SNAPSHOT",
 | 
			
		||||
  "version": "1.7.4",
 | 
			
		||||
  "description": "The Open MCT core platform",
 | 
			
		||||
  "dependencies": {},
 | 
			
		||||
  "devDependencies": {
 | 
			
		||||
 
 | 
			
		||||
@@ -181,7 +181,7 @@ define([
 | 
			
		||||
                        ],
 | 
			
		||||
                        "category": "contextual",
 | 
			
		||||
                        "name": "Stop",
 | 
			
		||||
                        "cssClass": "icon-box",
 | 
			
		||||
                        "cssClass": "icon-box-round-corners",
 | 
			
		||||
                        "priority": "preferred"
 | 
			
		||||
                    }
 | 
			
		||||
                ],
 | 
			
		||||
 
 | 
			
		||||
@@ -101,7 +101,7 @@ define(
 | 
			
		||||
                    name: "Pause"
 | 
			
		||||
                });
 | 
			
		||||
                mockStop.getMetadata.and.returnValue({
 | 
			
		||||
                    cssClass: "icon-box",
 | 
			
		||||
                    cssClass: "icon-box-round-corners",
 | 
			
		||||
                    name: "Stop"
 | 
			
		||||
                });
 | 
			
		||||
                mockScope.domainObject = mockDomainObject;
 | 
			
		||||
 
 | 
			
		||||
@@ -399,25 +399,25 @@ ObjectAPI.prototype._toMutable = function (object) {
 | 
			
		||||
        mutableObject = object;
 | 
			
		||||
    } else {
 | 
			
		||||
        mutableObject = MutableDomainObject.createMutable(object, this.eventEmitter);
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    // Check if provider supports realtime updates
 | 
			
		||||
    let identifier = utils.parseKeyString(mutableObject.identifier);
 | 
			
		||||
    let provider = this.getProvider(identifier);
 | 
			
		||||
        // Check if provider supports realtime updates
 | 
			
		||||
        let identifier = utils.parseKeyString(mutableObject.identifier);
 | 
			
		||||
        let provider = this.getProvider(identifier);
 | 
			
		||||
 | 
			
		||||
    if (provider !== undefined
 | 
			
		||||
        && provider.observe !== undefined
 | 
			
		||||
        && this.SYNCHRONIZED_OBJECT_TYPES.includes(object.type)) {
 | 
			
		||||
        let unobserve = provider.observe(identifier, (updatedModel) => {
 | 
			
		||||
            if (updatedModel.persisted > mutableObject.modified) {
 | 
			
		||||
                //Don't replace with a stale model. This can happen on slow connections when multiple mutations happen
 | 
			
		||||
                //in rapid succession and intermediate persistence states are returned by the observe function.
 | 
			
		||||
                mutableObject.$refresh(updatedModel);
 | 
			
		||||
            }
 | 
			
		||||
        });
 | 
			
		||||
        mutableObject.$on('$_destroy', () => {
 | 
			
		||||
            unobserve();
 | 
			
		||||
        });
 | 
			
		||||
        if (provider !== undefined
 | 
			
		||||
            && provider.observe !== undefined
 | 
			
		||||
            && this.SYNCHRONIZED_OBJECT_TYPES.includes(object.type)) {
 | 
			
		||||
            let unobserve = provider.observe(identifier, (updatedModel) => {
 | 
			
		||||
                if (updatedModel.persisted > mutableObject.modified) {
 | 
			
		||||
                    //Don't replace with a stale model. This can happen on slow connections when multiple mutations happen
 | 
			
		||||
                    //in rapid succession and intermediate persistence states are returned by the observe function.
 | 
			
		||||
                    mutableObject.$refresh(updatedModel);
 | 
			
		||||
                }
 | 
			
		||||
            });
 | 
			
		||||
            mutableObject.$on('$_destroy', () => {
 | 
			
		||||
                unobserve();
 | 
			
		||||
            });
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    return mutableObject;
 | 
			
		||||
 
 | 
			
		||||
@@ -45,6 +45,7 @@ export default class URLTimeSettingsSynchronizer {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    initialize() {
 | 
			
		||||
        this.updateTimeSettings();
 | 
			
		||||
        this.openmct.router.on('change:params', this.updateTimeSettings);
 | 
			
		||||
 | 
			
		||||
        TIME_EVENTS.forEach(event => {
 | 
			
		||||
 
 | 
			
		||||
@@ -41,7 +41,7 @@ export default class ConditionManager extends EventEmitter {
 | 
			
		||||
        this.subscriptions = {};
 | 
			
		||||
        this.telemetryObjects = {};
 | 
			
		||||
        this.testData = {
 | 
			
		||||
            conditionTestData: [],
 | 
			
		||||
            conditionTestInputs: this.conditionSetDomainObject.configuration.conditionTestData,
 | 
			
		||||
            applied: false
 | 
			
		||||
        };
 | 
			
		||||
        this.initialize();
 | 
			
		||||
@@ -154,8 +154,10 @@ export default class ConditionManager extends EventEmitter {
 | 
			
		||||
 | 
			
		||||
    updateConditionDescription(condition) {
 | 
			
		||||
        const found = this.conditionSetDomainObject.configuration.conditionCollection.find(conditionConfiguration => (conditionConfiguration.id === condition.id));
 | 
			
		||||
        found.summary = condition.description;
 | 
			
		||||
        this.persistConditions();
 | 
			
		||||
        if (found.summary !== condition.description) {
 | 
			
		||||
            found.summary = condition.description;
 | 
			
		||||
            this.persistConditions();
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    initCondition(conditionConfiguration, index) {
 | 
			
		||||
@@ -414,8 +416,10 @@ export default class ConditionManager extends EventEmitter {
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    updateTestData(testData) {
 | 
			
		||||
        this.testData = testData;
 | 
			
		||||
        this.openmct.objects.mutate(this.conditionSetDomainObject, 'configuration.conditionTestData', this.testData.conditionTestInputs);
 | 
			
		||||
        if (!_.isEqual(testData, this.testData)) {
 | 
			
		||||
            this.testData = testData;
 | 
			
		||||
            this.openmct.objects.mutate(this.conditionSetDomainObject, 'configuration.conditionTestData', this.testData.conditionTestInputs);
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    persistConditions() {
 | 
			
		||||
 
 | 
			
		||||
@@ -37,7 +37,15 @@ export default class DuplicateAction {
 | 
			
		||||
        let duplicationTask = new DuplicateTask(this.openmct);
 | 
			
		||||
        let originalObject = objectPath[0];
 | 
			
		||||
        let parent = objectPath[1];
 | 
			
		||||
        let userInput = await this.getUserInput(originalObject, parent);
 | 
			
		||||
        let userInput;
 | 
			
		||||
 | 
			
		||||
        try {
 | 
			
		||||
            userInput = await this.getUserInput(originalObject, parent);
 | 
			
		||||
        } catch (error) {
 | 
			
		||||
            // user most likely canceled
 | 
			
		||||
            return;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        let newParent = userInput.location;
 | 
			
		||||
        let inNavigationPath = this.inNavigationPath(originalObject);
 | 
			
		||||
 | 
			
		||||
 
 | 
			
		||||
@@ -101,7 +101,6 @@ export default {
 | 
			
		||||
                buttons: [
 | 
			
		||||
                    {
 | 
			
		||||
                        label: 'Cancel',
 | 
			
		||||
                        emphasis: true,
 | 
			
		||||
                        callback: () => {
 | 
			
		||||
                            painterroInstance.dismiss();
 | 
			
		||||
                            annotateOverlay.dismiss();
 | 
			
		||||
@@ -109,6 +108,7 @@ export default {
 | 
			
		||||
                    },
 | 
			
		||||
                    {
 | 
			
		||||
                        label: 'Save',
 | 
			
		||||
                        emphasis: true,
 | 
			
		||||
                        callback: () => {
 | 
			
		||||
                            painterroInstance.save((snapshotObject) => {
 | 
			
		||||
                                annotateOverlay.dismiss();
 | 
			
		||||
 
 | 
			
		||||
@@ -7,10 +7,10 @@
 | 
			
		||||
                    <div class="c-object-label__type-icon icon-camera"></div>
 | 
			
		||||
                    <div class="c-object-label__name">
 | 
			
		||||
                        Notebook Snapshots
 | 
			
		||||
                        <span v-if="snapshots.length"
 | 
			
		||||
                              class="l-browse-bar__object-details"
 | 
			
		||||
                        > {{ snapshots.length }} of {{ getNotebookSnapshotMaxCount() }}
 | 
			
		||||
                        </span>
 | 
			
		||||
                    </div>
 | 
			
		||||
                    <div v-if="snapshots.length"
 | 
			
		||||
                         class="l-browse-bar__object-details"
 | 
			
		||||
                    >{{ snapshots.length }} of {{ getNotebookSnapshotMaxCount() }}
 | 
			
		||||
                    </div>
 | 
			
		||||
                </div>
 | 
			
		||||
                <PopupMenu v-if="snapshots.length > 0"
 | 
			
		||||
 
 | 
			
		||||
@@ -4,8 +4,10 @@
 | 
			
		||||
        <div class="l-browse-bar__start">
 | 
			
		||||
            <div class="l-browse-bar__object-name--w">
 | 
			
		||||
                <span class="c-object-label l-browse-bar__object-name"
 | 
			
		||||
                    v-bind:class="cssClass"
 | 
			
		||||
                >
 | 
			
		||||
                    <span class="c-object-label__type-icon"
 | 
			
		||||
                          v-bind:class="cssClass"
 | 
			
		||||
                    ></span>
 | 
			
		||||
                    <span class="c-object-label__name">{{ name }}</span>
 | 
			
		||||
                </span>
 | 
			
		||||
            </div>
 | 
			
		||||
 
 | 
			
		||||
@@ -49,10 +49,6 @@ describe('the plugin', function () {
 | 
			
		||||
        child.style.height = '480px';
 | 
			
		||||
        element.appendChild(child);
 | 
			
		||||
 | 
			
		||||
        openmct.time.timeSystem('utc', {
 | 
			
		||||
            start: 1597160002854,
 | 
			
		||||
            end: 1597181232854
 | 
			
		||||
        });
 | 
			
		||||
        openmct.on('start', done);
 | 
			
		||||
        openmct.start(appHolder);
 | 
			
		||||
    });
 | 
			
		||||
@@ -105,6 +101,11 @@ describe('the plugin', function () {
 | 
			
		||||
        let planView;
 | 
			
		||||
 | 
			
		||||
        beforeEach(() => {
 | 
			
		||||
            openmct.time.timeSystem('utc', {
 | 
			
		||||
                start: 1597160002854,
 | 
			
		||||
                end: 1597181232854
 | 
			
		||||
            });
 | 
			
		||||
 | 
			
		||||
            planDomainObject = {
 | 
			
		||||
                identifier: {
 | 
			
		||||
                    key: 'test-object',
 | 
			
		||||
 
 | 
			
		||||
@@ -102,7 +102,7 @@
 | 
			
		||||
                        >
 | 
			
		||||
                        </button>
 | 
			
		||||
                    </div>
 | 
			
		||||
                    <div v-if="isRealTime"
 | 
			
		||||
                    <div v-if="isRealTime && !options.compact"
 | 
			
		||||
                         class="c-button-set c-button-set--strip-h js-pause"
 | 
			
		||||
                    >
 | 
			
		||||
                        <button v-if="!isFrozen"
 | 
			
		||||
@@ -427,9 +427,12 @@ export default {
 | 
			
		||||
                this.skipReloadOnInteraction = false;
 | 
			
		||||
                this.loadMoreData(newRange, true);
 | 
			
		||||
            } else {
 | 
			
		||||
                // If we're not panning or zooming (time conductor and plot x-axis times are not out of sync)
 | 
			
		||||
                // Drop any data that is more than 1x (max-min) before min.
 | 
			
		||||
                // Limit these purges to once a second.
 | 
			
		||||
                if (!this.nextPurge || this.nextPurge < Date.now()) {
 | 
			
		||||
                const isPanningOrZooming = this.isTimeOutOfSync;
 | 
			
		||||
                const purgeRecords = !isPanningOrZooming && (!this.nextPurge || (this.nextPurge < Date.now()));
 | 
			
		||||
                if (purgeRecords) {
 | 
			
		||||
                    const keepRange = {
 | 
			
		||||
                        min: newRange.min - (newRange.max - newRange.min),
 | 
			
		||||
                        max: newRange.max
 | 
			
		||||
 
 | 
			
		||||
@@ -279,6 +279,10 @@ describe("the plugin", function () {
 | 
			
		||||
        let plotView;
 | 
			
		||||
 | 
			
		||||
        beforeEach(() => {
 | 
			
		||||
            openmct.time.timeSystem("utc", {
 | 
			
		||||
                start: 0,
 | 
			
		||||
                end: 4
 | 
			
		||||
            });
 | 
			
		||||
            const getFunc = openmct.$injector.get;
 | 
			
		||||
            spyOn(openmct.$injector, "get")
 | 
			
		||||
                .withArgs("exportImageService").and.returnValue({
 | 
			
		||||
 
 | 
			
		||||
@@ -175,7 +175,7 @@ define([
 | 
			
		||||
        return GeneratorPlugin;
 | 
			
		||||
    };
 | 
			
		||||
 | 
			
		||||
    plugins.ExampleImagery = ExampleImagery;
 | 
			
		||||
    plugins.ExampleImagery = ExampleImagery.default;
 | 
			
		||||
    plugins.ImageryPlugin = ImageryPlugin;
 | 
			
		||||
    plugins.Plot = PlotPlugin.default;
 | 
			
		||||
    plugins.TelemetryTable = TelemetryTablePlugin;
 | 
			
		||||
 
 | 
			
		||||
@@ -121,6 +121,11 @@ describe("the plugin", () => {
 | 
			
		||||
        let tableInstance;
 | 
			
		||||
 | 
			
		||||
        beforeEach(() => {
 | 
			
		||||
            openmct.time.timeSystem('utc', {
 | 
			
		||||
                start: 0,
 | 
			
		||||
                end: 4
 | 
			
		||||
            });
 | 
			
		||||
 | 
			
		||||
            testTelemetryObject = {
 | 
			
		||||
                identifier: {
 | 
			
		||||
                    namespace: "",
 | 
			
		||||
 
 | 
			
		||||
@@ -237,7 +237,6 @@
 | 
			
		||||
    }
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
// Prototype
 | 
			
		||||
[class^='pr-tc-input-menu'] {
 | 
			
		||||
    // Uses ^= here to target both start and end menus
 | 
			
		||||
    background: $colorBodyBg;
 | 
			
		||||
@@ -247,8 +246,7 @@
 | 
			
		||||
    grid-column-gap: 3px;
 | 
			
		||||
    grid-row-gap: 4px;
 | 
			
		||||
    align-items: start;
 | 
			
		||||
 | 
			
		||||
    filter: brightness(1.4);
 | 
			
		||||
    filter: $filterMenu;
 | 
			
		||||
    box-shadow: $shdwMenu;
 | 
			
		||||
    padding: $interiorMargin;
 | 
			
		||||
    position: absolute;
 | 
			
		||||
 
 | 
			
		||||
@@ -237,11 +237,12 @@ $shdwSelect: rgba(black, 0.5) 0 0.5px 3px;
 | 
			
		||||
$controlDisabledOpacity: 0.2;
 | 
			
		||||
 | 
			
		||||
// Menus
 | 
			
		||||
$colorMenuBg: pullForward($colorBodyBg, 15%);
 | 
			
		||||
$colorMenuFg: pullForward($colorBodyFg, 30%);
 | 
			
		||||
$colorMenuIc: pullForward($colorKey, 15%);
 | 
			
		||||
$colorMenuHovBg: $colorMenuIc;
 | 
			
		||||
$colorMenuHovFg: pullForward($colorMenuFg, 10%);
 | 
			
		||||
$colorMenuBg: $colorBodyBg;
 | 
			
		||||
$colorMenuFg: $colorBodyFg;
 | 
			
		||||
$colorMenuIc: $colorKey;
 | 
			
		||||
$filterMenu:  brightness(1.4);
 | 
			
		||||
$colorMenuHovBg: rgba($colorKey, 0.5);
 | 
			
		||||
$colorMenuHovFg: $colorBodyFgEm;
 | 
			
		||||
$colorMenuHovIc: $colorMenuHovFg;
 | 
			
		||||
$colorMenuElementHilite: pullForward($colorMenuBg, 10%);
 | 
			
		||||
$shdwMenu: rgba(black, 0.5) 0 1px 5px;
 | 
			
		||||
 
 | 
			
		||||
@@ -241,11 +241,12 @@ $shdwSelect: rgba(black, 0.5) 0 0.5px 3px;
 | 
			
		||||
$controlDisabledOpacity: 0.2;
 | 
			
		||||
 | 
			
		||||
// Menus
 | 
			
		||||
$colorMenuBg: pullForward($colorBodyBg, 15%);
 | 
			
		||||
$colorMenuFg: pullForward($colorBodyFg, 30%);
 | 
			
		||||
$colorMenuIc: pullForward($colorKey, 15%);
 | 
			
		||||
$colorMenuHovBg: $colorMenuIc;
 | 
			
		||||
$colorMenuHovFg: pullForward($colorMenuFg, 10%);
 | 
			
		||||
$colorMenuBg: $colorBodyBg;
 | 
			
		||||
$colorMenuFg: $colorBodyFg;
 | 
			
		||||
$colorMenuIc: $colorKey;
 | 
			
		||||
$filterMenu:  brightness(1.4);
 | 
			
		||||
$colorMenuHovBg: rgba($colorKey, 0.5);
 | 
			
		||||
$colorMenuHovFg: $colorBodyFgEm;
 | 
			
		||||
$colorMenuHovIc: $colorMenuHovFg;
 | 
			
		||||
$colorMenuElementHilite: pullForward($colorMenuBg, 10%);
 | 
			
		||||
$shdwMenu: rgba(black, 0.5) 0 1px 5px;
 | 
			
		||||
 
 | 
			
		||||
@@ -237,9 +237,10 @@ $shdwSelect: none;
 | 
			
		||||
$controlDisabledOpacity: 0.3;
 | 
			
		||||
 | 
			
		||||
// Menus
 | 
			
		||||
$colorMenuBg: pushBack($colorBodyBg, 10%);
 | 
			
		||||
$colorMenuFg: pullForward($colorMenuBg, 70%);
 | 
			
		||||
$colorMenuBg: $colorBodyBg;
 | 
			
		||||
$colorMenuFg: $colorBodyFg;
 | 
			
		||||
$colorMenuIc: $colorKey;
 | 
			
		||||
$filterMenu: brightness(0.95);
 | 
			
		||||
$colorMenuHovBg: $colorMenuIc;
 | 
			
		||||
$colorMenuHovFg: $colorMenuBg;
 | 
			
		||||
$colorMenuHovIc: $colorMenuBg;
 | 
			
		||||
 
 | 
			
		||||
@@ -458,6 +458,7 @@ select {
 | 
			
		||||
@mixin menuOuter() {
 | 
			
		||||
    border-radius: $basicCr;
 | 
			
		||||
    background: $colorMenuBg;
 | 
			
		||||
    filter: $filterMenu;
 | 
			
		||||
    text-shadow: $shdwMenuText;
 | 
			
		||||
    padding: $interiorMarginSm;
 | 
			
		||||
    box-shadow: $shdwMenu;
 | 
			
		||||
 
 | 
			
		||||
@@ -490,7 +490,7 @@
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
#snap-annotation {
 | 
			
		||||
    $m: $interiorMargin;
 | 
			
		||||
    $m: 0; //$interiorMargin;
 | 
			
		||||
    display: flex;
 | 
			
		||||
    flex-direction: column;
 | 
			
		||||
    position: absolute;
 | 
			
		||||
@@ -514,21 +514,32 @@
 | 
			
		||||
    // Holds tool buttons, color selectors, etc.
 | 
			
		||||
    $h: 22px;
 | 
			
		||||
    $fs: 0.8rem;
 | 
			
		||||
    $m: $interiorMarginSm;
 | 
			
		||||
 | 
			
		||||
    display: flex;
 | 
			
		||||
    align-items: center;
 | 
			
		||||
    height: $h + ($m * 2) !important;
 | 
			
		||||
    margin-bottom: $interiorMarginLg;
 | 
			
		||||
    order: 1;
 | 
			
		||||
    flex: 0 0 auto;
 | 
			
		||||
    height: auto;
 | 
			
		||||
    background-color: transparent !important;
 | 
			
		||||
    margin-bottom: $interiorMargin;
 | 
			
		||||
    padding: $interiorMarginSm;
 | 
			
		||||
 | 
			
		||||
    > div > span {
 | 
			
		||||
        display: flex;
 | 
			
		||||
        align-items: center;
 | 
			
		||||
        font-size: $fs;
 | 
			
		||||
    > div {
 | 
			
		||||
        display: contents;
 | 
			
		||||
 | 
			
		||||
        > * + * { margin-left: $interiorMargin !important; }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    .ptro-tool-controls {
 | 
			
		||||
        display: flex;
 | 
			
		||||
        margin-left: $interiorMarginLg !important;
 | 
			
		||||
 | 
			
		||||
        > * + * {
 | 
			
		||||
            margin-left: $interiorMargin !important;
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    > div,
 | 
			
		||||
    > div > span,
 | 
			
		||||
    .ptro-icon-btn,
 | 
			
		||||
    .ptro-named-btn,
 | 
			
		||||
    .ptro-color-btn,
 | 
			
		||||
@@ -538,27 +549,18 @@
 | 
			
		||||
    .tool-controls,
 | 
			
		||||
    .ptro-input {
 | 
			
		||||
        // Lot of resets for crappy CSS in Painterro
 | 
			
		||||
        &:first-child {
 | 
			
		||||
            margin-left: 0 !important;
 | 
			
		||||
        }
 | 
			
		||||
        display: inline-block;
 | 
			
		||||
        font-family: inherit;
 | 
			
		||||
        font-size: $fs !important;
 | 
			
		||||
        height: $h !important;
 | 
			
		||||
        margin: 0 0 0 5px;
 | 
			
		||||
        margin: 0;
 | 
			
		||||
        position: relative;
 | 
			
		||||
        width: auto !important;
 | 
			
		||||
        line-height: $h !important;
 | 
			
		||||
        top: auto;
 | 
			
		||||
        right: auto;
 | 
			
		||||
        bottom: auto;
 | 
			
		||||
        left: auto;
 | 
			
		||||
        vertical-align: top;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    .ptro-tool-ctl-name {
 | 
			
		||||
        border-radius: 0;
 | 
			
		||||
        background: none;
 | 
			
		||||
        color: $colorBodyFg;
 | 
			
		||||
        top: auto;
 | 
			
		||||
        font-family: inherit;
 | 
			
		||||
        padding: 0;
 | 
			
		||||
@@ -568,13 +570,15 @@
 | 
			
		||||
        width: $h !important;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    .ptro-check,
 | 
			
		||||
    .ptro-color-control,
 | 
			
		||||
    .ptro-icon-btn,
 | 
			
		||||
    .ptro-named-btn {
 | 
			
		||||
        // Buttons in toolbar. Why the f* they're named like this is a mystery
 | 
			
		||||
        background-color: $colorBtnBg;
 | 
			
		||||
        color: $colorBtnFg;
 | 
			
		||||
        padding: 0 $interiorMargin;
 | 
			
		||||
        // Buttons in toolbar
 | 
			
		||||
        border-radius: $smallCr;
 | 
			
		||||
        box-shadow: rgba($colorBtnFg, 0.3) 0 0 0 1px;
 | 
			
		||||
        color: $colorBtnFg !important;
 | 
			
		||||
        padding: 1px $interiorMargin;
 | 
			
		||||
 | 
			
		||||
        &:hover {
 | 
			
		||||
            background: $colorBtnBgHov;
 | 
			
		||||
@@ -588,6 +592,13 @@
 | 
			
		||||
        }
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    .ptro-color-control,
 | 
			
		||||
    .ptro-icon-btn,
 | 
			
		||||
    .ptro-named-btn {
 | 
			
		||||
        // Buttons in toolbar
 | 
			
		||||
        background-color: $colorBtnBg;
 | 
			
		||||
    }
 | 
			
		||||
 | 
			
		||||
    .ptro-color-active-control {
 | 
			
		||||
        background: $colorBtnMajorBg  !important;
 | 
			
		||||
        color: $colorBtnMajorFg !important;
 | 
			
		||||
 
 | 
			
		||||
@@ -17,15 +17,7 @@
 | 
			
		||||
        <div v-if="singleSelectNonObject"
 | 
			
		||||
             class="c-inspector__selected c-inspector__selected--non-domain-object  c-object-label"
 | 
			
		||||
        >
 | 
			
		||||
            <span class="c-object-label__type-icon"
 | 
			
		||||
                  :class="typeCssClass"
 | 
			
		||||
            ></span>
 | 
			
		||||
            <span v-if="!activity"
 | 
			
		||||
                  class="c-object-label__name"
 | 
			
		||||
            >Layout Object</span>
 | 
			
		||||
            <span v-else
 | 
			
		||||
                  class="c-object-label__name"
 | 
			
		||||
            >{{ activity.name }}</span>
 | 
			
		||||
            <span class="c-object-label__name">Layout Object</span>
 | 
			
		||||
        </div>
 | 
			
		||||
    </div>
 | 
			
		||||
    <div v-if="multiSelect"
 | 
			
		||||
 
 | 
			
		||||
@@ -32,6 +32,7 @@
 | 
			
		||||
 | 
			
		||||
        &__scrollable {
 | 
			
		||||
            overflow: auto;
 | 
			
		||||
            padding-right: $interiorMargin;
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        &__item--empty {
 | 
			
		||||
 
 | 
			
		||||
@@ -113,7 +113,7 @@ import search from '../components/search.vue';
 | 
			
		||||
const ITEM_BUFFER = 25;
 | 
			
		||||
const LOCAL_STORAGE_KEY__TREE_EXPANDED = 'mct-tree-expanded';
 | 
			
		||||
const RETURN_ALL_DESCDNDANTS = true;
 | 
			
		||||
const TREE_ITEM_INDENT_PX = 15;
 | 
			
		||||
const TREE_ITEM_INDENT_PX = 18;
 | 
			
		||||
 | 
			
		||||
export default {
 | 
			
		||||
    name: 'MctTree',
 | 
			
		||||
 
 | 
			
		||||
@@ -103,10 +103,16 @@ export default {
 | 
			
		||||
    },
 | 
			
		||||
    mounted() {
 | 
			
		||||
        if (this.actionCollection) {
 | 
			
		||||
            this.actionCollection.hide(HIDDEN_ACTIONS);
 | 
			
		||||
            this.actionCollection.on('update', this.updateActionItems);
 | 
			
		||||
            this.updateActionItems(this.actionCollection.getActionsObject());
 | 
			
		||||
        }
 | 
			
		||||
    },
 | 
			
		||||
    destroyed() {
 | 
			
		||||
        if (this.actionCollection) {
 | 
			
		||||
            this.actionCollection.off('update', this.updateActionItems);
 | 
			
		||||
        }
 | 
			
		||||
    },
 | 
			
		||||
    methods: {
 | 
			
		||||
        setView(view) {
 | 
			
		||||
            this.$emit('setView', view);
 | 
			
		||||
@@ -116,7 +122,6 @@ export default {
 | 
			
		||||
            delete this.actionCollection;
 | 
			
		||||
        },
 | 
			
		||||
        updateActionItems() {
 | 
			
		||||
            this.actionCollection.hide(HIDDEN_ACTIONS);
 | 
			
		||||
            this.statusBarItems = this.actionCollection.getStatusBarActions();
 | 
			
		||||
            this.menuActionItems = this.actionCollection.getVisibleActions();
 | 
			
		||||
        },
 | 
			
		||||
 
 | 
			
		||||
@@ -8,7 +8,7 @@ let resolveFunction;
 | 
			
		||||
 | 
			
		||||
let initialHash = '';
 | 
			
		||||
 | 
			
		||||
describe('Application router utility functions', () => {
 | 
			
		||||
xdescribe('Application router utility functions', () => {
 | 
			
		||||
    beforeAll(done => {
 | 
			
		||||
        appHolder = document.createElement('div');
 | 
			
		||||
        appHolder.style.width = '640px';
 | 
			
		||||
 
 | 
			
		||||
@@ -10,7 +10,6 @@ define([
 | 
			
		||||
        let unobserve = undefined;
 | 
			
		||||
        let currentObjectPath;
 | 
			
		||||
        let isRoutingInProgress = false;
 | 
			
		||||
        let mutable;
 | 
			
		||||
 | 
			
		||||
        openmct.router.route(/^\/browse\/?$/, navigateToFirstChildOfRoot);
 | 
			
		||||
        openmct.router.route(/^\/browse\/(.*)$/, (path, results, params) => {
 | 
			
		||||
@@ -37,24 +36,10 @@ define([
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
        function viewObject(object, viewProvider) {
 | 
			
		||||
            if (mutable) {
 | 
			
		||||
                openmct.objects.destroyMutable(mutable);
 | 
			
		||||
                mutable = undefined;
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            if (openmct.objects.supportsMutation(object.identifier)) {
 | 
			
		||||
                mutable = openmct.objects._toMutable(object);
 | 
			
		||||
            }
 | 
			
		||||
 | 
			
		||||
            currentObjectPath = openmct.router.path;
 | 
			
		||||
 | 
			
		||||
            if (mutable !== undefined) {
 | 
			
		||||
                openmct.layout.$refs.browseObject.show(mutable, viewProvider.key, true, currentObjectPath);
 | 
			
		||||
                openmct.layout.$refs.browseBar.domainObject = mutable;
 | 
			
		||||
            } else {
 | 
			
		||||
                openmct.layout.$refs.browseObject.show(object, viewProvider.key, true, currentObjectPath);
 | 
			
		||||
                openmct.layout.$refs.browseBar.domainObject = object;
 | 
			
		||||
            }
 | 
			
		||||
            openmct.layout.$refs.browseObject.show(object, viewProvider.key, true, currentObjectPath);
 | 
			
		||||
            openmct.layout.$refs.browseBar.domainObject = object;
 | 
			
		||||
 | 
			
		||||
            openmct.layout.$refs.browseBar.viewKey = viewProvider.key;
 | 
			
		||||
        }
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user