How To Save And Load
In DynaMaker it is possible to save and load your configurations. The configurations can be saved locally, however if you want to let the user load a configuration from another session, you would need to store said data in an external database. Below we show:
How It Works
To save a design, it needs to be converted to a stringified JSON object, which can be sent to a server and stored in a database. For this, in the UI Editor:
- in edit/hide imports..., import the available
DYNAMAKER
as it is another subcomponent. - generate
jsonToSave
from the top-level component handler as shown below usingDYNAMAKER
.const jsonToSave = Studio.getComponentHandler().generateJSON(DYNAMAKER.componentIdMappings)
- through
postMessage
you can send thisjsonToSave
to whatever external database (read more here).
Then to load a design, you would need to:
- fetch the
jsonToLoad
from your external database throughwindow.addEventListener()
(read more here). - use this
jsonToLoad
to generate the new top-level component handler and assign it to the app:const loadedComponentHandler = STUDIO.ComponentHandler.fromJSON(jsonToLoad, DYNAMAKER.componentIdMappings)
Studio.getManager().setComponentHandler(loadedComponentHandler) - update the geometry (
Studio.requestGeometryUpdate()
) to apply changes if needed.
Example App
Below we show an example of what could be an app that saves and loads configurations locally in the app through
the variable savedStates
that could work as a "external database" which is ideal path, since you would not only have
full control of all the saved designs, but also of who would have access to what design. In this case it is made so that
loading a configuration (i.e. previous JSON) means that it loads the latest saved JSON, which is the last of the list
savedStates
.
let savedStates: string[] = []
export function onInit() {
const newCubeComponent = new CUBE.Component()
Studio.getComponentHandler().add(newCubeComponent)
Studio.requestGeometryUpdate().then(() => {
Studio.setCameraToFitBounds()
})
const tab1 = new SKYUI.Tab({
title: 'Configure',
icon: 'cog',
onInit: () => {
const cube = Studio.getComponentHandler().getComponents(CUBE.Component)[0]
if (cube) {
const configurator = CUBE.generateConfigurator(cube)
configurator.addCompletionCallback(() => {
Studio.requestGeometryUpdate()
})
const saveJsonButton = new SKYUI.Button('Save JSON', () => {
const jsonToSave = Studio.getComponentHandler().generateJSON(DYNAMAKER.componentIdMappings)
savedStates.push(jsonToSave)
console.log('Saved', json)
Studio.displayNotification(`Configuration saved successfully!`, { type: 'success' })
// See suggestion below of downloading JSON file when saving
// const stringifiedJsonToSave = JSON.stringify(json)
// const blob = new Blob([stringifiedJsonToSave])
// Studio.downloadFile('save.json', blob)
})
const loadJsonButton = new SKYUI.Button('Load previous JSON', () => {
const jsonToLoad = savedStates[savedStates.length - 1] // last saved JSON
if (jsonToLoad) {
const loadedComponentHandler = STUDIO.ComponentHandler.fromJSON(jsonToLoad, DYNAMAKER.componentIdMappings)
Studio.getManager().setComponentHandler(loadedComponentHandler)
console.log('Loaded', jsonToLoad)
Studio.displayNotification(`Configuration loaded successfully!`, { type: 'success' })
Studio.requestGeometryUpdate()
savedStates.pop()
Studio.reloadActiveTab()
}
})
Studio.setTabContent([configurator, saveJsonButton, loadJsonButton])
}
},
})
Studio.setTabs([tab1])
}
Remember to read more about how to set up event-listeners and integration here. If you have questions or want this template in your team, you are welcome to ask us at support@dynamaker.com.