Skip to main content
Version: Next

Saving viewer state

Reveal supports saving the camera state and styled filters that have been applied to the loaded model(s). This functionality can help support sharing links and local storage of a given view. Internally the input to a given filter is stored and is replayed when restoring the view. This usually means that substantially less data needs to be serialized in order to share the given state of the viewer. The serialized JSON blob also keeps information about styling/filtering of the model by storing all styled sets.

Getting the viewer state

In the example below we apply some filter to our loaded model using the NodeCollection type from Styling CAD models. Then we can call the viewer.getViewState() function which return a serialized JSON blob containing the view state. Depending on the application, the view state can be additionally transformed into e.g. a URL parameter and transferred through a link.

In the example below, we keep simply print it to the developer console.

Live Editor

Setting the viewer state

Restoring the viewer state is simply a matter of feeding back the JSON blob retrieved from const myState = viewer.getViewState() into viewer.setViewState(myState). In the example below, a previously stored state is applied which applies a red color to nodes that have an attribute 'PDMS.Type'.

note

Setting the viewer state assumes that model has already been loaded. An error will be thrown if a given state is loaded for a model which does not exist.

Live Editor

Serializing and deserializing custom node collections

When working with styled custom node collections, the Reveal viewer needs to know how to serialize and deserialize the set. Serialization is handled through the abstract method serialize which needs to be implemented when extending NodeCollection. The output of serialize is of type SerializedNodeCollection and contains a token which is used to recreate the NodeCollection during deserialization, and a state object which contains the data needed to restore the NodeCollection. It is up to the application developer to fill this state object with any nessesary data needed to recreate the state of the NodeCollection. An optional options object can also be supplied containing any metadata for loading data (e.g. the number of API calls to fetch the needed data in parallel). The contents returned from serialize is contained in the result of getViewState.

In addition to serialization, Reveal also needs to know how to recreate the custom NodeCollection during deserialization. This is done by calling the free-function registerNodeCollectionType with the same token defined by the custom NodeCollection and a lambda function which instantiates and restore the state of the NodeCollection. The lambda function has two parameters: the descriptor containing the state and options which should be applied to the NodeCollection and the context containing an instance of the CogniteClient from the Cognite SDK and the CogniteCadModel which the NodeCollection was originally applied to. It is up to the application developer how and if they want to use the context and/or descriptor, but it is provided as a convinience.

An example of a simple custom NodeCollection can be seen below. For more information on creating a custom NodeCollection, see create custom node collections.

// import { IndexSet, NodeCollection, registerNodeCollectionType } from '@cognite/reveal';

class MyNodeCollection extends NodeCollection {

isLoading = false;
_indexSet = new IndexSet();

constructor(model) {
// token used for serialization / deserialization
super('MyNodeCollection');

for (let i = 0; i < model.nodeCount / 2; i++) {
this._indexSet.add(i);
}
}

getIndexSet() {
return this._indexSet;
}

serialize() {
return {
token: this.classToken,
state: this._indexSet.toRangeArray()
}
}

clear() {
this._indexSet.clear();
this.notifyChanged();
}
}

// Register deserializer for type
registerNodeCollectionType(
'MyNodeCollection',
(descriptor, context) => {
return Promise.resolve(new MyNodeCollection(context.model));
}
);