The Actions API provides a centralized way to manage and customize actions for various user interactions in CE.SDK.
API Methods#
The Actions API provides three methods:
register(actionId, handler)
- Register an action function for a specific eventget(actionId)
- Retrieve a registered action functionrun(actionId, ...args)
- Execute a registered action with the provided arguments (throws if not registered)
Getting Started#
Register actions after initializing CE.SDK:
import CreativeEditorSDK from '@cesdk/cesdk-js';
const cesdk = await CreativeEditorSDK.create(container, { license: 'YOUR_CESDK_LICENSE_KEY'});
// Register an actioncesdk.actions.register('actionType', async (...args) => { // Your custom implementation return result;});
// Execute a registered actionawait cesdk.actions.run('actionType', arg1, arg2);
// Or retrieve an action to call it laterconst action = cesdk.actions.get('actionType');
Default Actions#
CE.SDK automatically registers the following default actions:
Action Handlers#
saveScene
- Saves the current scene (default: downloads scene file)shareScene
- Shares the current scene (no default implementation)exportDesign
- Exports design in various formats (default: downloads the exported file)importScene
- Imports scene or archive files (default: opens file picker)exportScene
- Exports scene or archive (default: downloads the file)uploadFile
- Uploads files to asset sources (default: local upload for development)onUnsupportedBrowser
- Handles unsupported browsers (no default implementation)
Scene Management Actions#
saveScene
#
Handles saving the current scene. Default implementation downloads the scene file.
// Basic implementationcesdk.actions.register('saveScene', async () => { const scene = await cesdk.engine.scene.saveToString(); console.log('Scene saved:', scene.length, 'characters');
// Production: // await yourAPI.saveScene(scene);
cesdk.ui.showNotification('Scene saved successfully');});
// With loading dialogcesdk.actions.register('saveScene', async () => { const dialogController = cesdk.utils.showLoadingDialog({ title: 'Saving Scene', message: 'Please wait...', progress: 'indeterminate' });
try { const scene = await cesdk.engine.scene.saveToString(); console.log('Scene saved:', scene.length, 'characters');
// Production: // await yourAPI.saveScene(scene);
dialogController.showSuccess({ title: 'Saved', message: 'Scene saved successfully' }); } catch (error) { dialogController.showError({ title: 'Save Failed', message: 'Could not save the scene' }); throw error; }});
shareScene
#
Handles scene sharing. No default implementation.
// Register share functionalitycesdk.actions.register('shareScene', async () => { const scene = await cesdk.engine.scene.saveToString(); const shareUrl = 'https://example.com/shared-scene-placeholder'; console.log('Scene ready to share:', scene.length, 'characters');
// Production: // const shareUrl = await yourAPI.createShareableLink(scene);
await navigator.share({ url: shareUrl });});
importScene
and exportScene
#
Handle scene import/export operations with support for both scene files and archives.
// Import scene or archivecesdk.actions.register('importScene', async ({ format }) => { if (format === 'archive') { console.log('Archive import requested');
// Production: // const archive = await yourAPI.loadArchive(); // await cesdk.engine.scene.loadFromArchiveURL(archive); } else { console.log('Scene import requested');
// Production: // const scene = await yourAPI.loadScene(); // await cesdk.engine.scene.loadFromString(scene); }});
// Export scene or archivecesdk.actions.register('exportScene', async ({ format }) => { if (format === 'archive') { const archive = await cesdk.engine.scene.saveToArchive(); console.log('Archive ready for export:', archive.length, 'bytes');
// Production: // await yourAPI.uploadArchive(archive); } else { const scene = await cesdk.engine.scene.saveToString(); console.log('Scene ready for export:', scene.length, 'characters');
// Production: // await yourAPI.uploadScene(scene); }});
Export Operations#
exportDesign
#
Handles all export operations (images, PDFs, videos). Default implementation downloads the exported file.
// Basic implementationcesdk.actions.register('exportDesign', async (options) => { // Use the utils API to perform the export with loading dialog const { blobs, options: exportOptions } = await cesdk.utils.export(options); console.log('Exported', blobs.length, 'files'); blobs.forEach((blob, i) => console.log(`File ${i + 1}:`, blob.size, 'bytes'));
// Production: // await Promise.all(blobs.map(blob => yourCDN.upload(blob)));
cesdk.ui.showNotification('Export completed successfully');});
// Direct engine export with custom loading dialog (bypassing utils)cesdk.actions.register('exportDesign', async (options) => { const dialogController = cesdk.utils.showLoadingDialog({ title: 'Exporting', message: 'Processing your export...' });
try { const page = cesdk.engine.scene.getCurrentPage(); if (page === null) { throw new Error('No page selected for export'); } let result;
if (options?.mimeType?.startsWith('video/')) { // Video export with progress result = await cesdk.engine.block.exportVideo(page, { ...options, onProgress: (rendered, encoded, total) => { dialogController.updateProgress({ value: rendered, max: total }); } }); } else { // Static export (image/PDF) result = await cesdk.engine.block.export(page, options); }
console.log('File ready for export:', result.size, 'bytes');
// Production: // await yourCDN.upload(result);
dialogController.showSuccess({ title: 'Export Complete', message: 'Files uploaded successfully' }); } catch (error) { dialogController.showError({ title: 'Export Failed', message: 'Could not complete the export' }); throw error; }});
File Upload Action#
uploadFile
#
Handles file uploads to asset sources. Default implementation uses local upload for development.
// Register production upload handlercesdk.actions.register('uploadFile', async (file, onProgress, context) => { console.log('Uploading file:', file.name, file.size, 'bytes'); onProgress(50); // Simulate progress await new Promise(resolve => setTimeout(resolve, 500)); onProgress(100);
// Production: // const asset = await yourStorageService.upload(file, { // onProgress: (percent) => onProgress(percent), // context // });
// Return AssetDefinition return { id: 'local-' + Date.now(), label: { en: file.name }, meta: { uri: URL.createObjectURL(file), thumbUri: URL.createObjectURL(file), kind: 'image', width: 1920, height: 1080 // Production: // uri: asset.url, // thumbUri: asset.thumbnailUrl, // width: asset.width, // height: asset.height } };});
You can control which file types users can upload by setting the upload/supportedMimeTypes
setting:
// Example 1: Only allow imagescesdk.engine.editor.setSettingString( 'upload/supportedMimeTypes', 'image/png,image/jpeg,image/gif,image/svg+xml');
// Example 2: Allow images and videoscesdk.engine.editor.setSettingString( 'upload/supportedMimeTypes', 'image/png,image/jpeg,image/gif,video/mp4,video/quicktime');
// Example 3: Allow specific document typescesdk.engine.editor.setSettingString( 'upload/supportedMimeTypes', 'application/pdf,image/png,image/jpeg');
Unsupported Browser Action#
onUnsupportedBrowser
#
Handles unsupported browser detection. No default implementation is provided.
// Register handler for unsupported browserscesdk.actions.register('onUnsupportedBrowser', () => { // Redirect to a custom compatibility page window.location.href = '/browser-not-supported';});
Utils API#
CE.SDK provides a Utils API with utility functions for common operations. These utilities are available through cesdk.utils
:
Loading Dialogs#
// Create and manage loading dialogsconst dialogController = cesdk.utils.showLoadingDialog({ title: 'Processing...', message: 'Please wait', // Can also be an array of strings progress: 0, // Initial progress value or 'indeterminate' cancelLabel: 'Cancel', abortTitle: 'Abort Operation?', abortMessage: 'Are you sure you want to abort?', abortLabel: 'Abort', size: 'large', // 'regular' or 'large' clickOutsideToClose: false, onAbort: () => console.log('User cancelled'), onDone: () => console.log('Dialog closed')});
// Update progressdialogController.updateProgress({ value: 50, max: 100 });
// Show success or errordialogController.showSuccess({ title: 'Done!', message: 'Operation completed' });dialogController.showError({ title: 'Error', message: 'Something went wrong' });
// Close dialogdialogController.close();
Export Utility#
The export utility automatically handles both static (images, PDFs) and video exports:
// Export image or PDFconst { blobs, options } = await cesdk.utils.export({ mimeType: 'image/png', pngCompressionLevel: 7});
// Export video (automatically detected by MIME type)const { blobs, options } = await cesdk.utils.export({ mimeType: 'video/mp4', onProgress: (rendered, encoded, total) => { console.log(`Progress: ${rendered}/${total} frames`); }});
File Operations#
// Load file from userconst file = await cesdk.utils.loadFile({ accept: 'image/*', returnType: 'File' // 'dataURL', 'text', 'blob', 'arrayBuffer', or 'File'});
// Download file to user's deviceawait cesdk.utils.downloadFile(blob, 'image/png');
// Local upload (development only)const asset = await cesdk.utils.localUpload(file, context);
Implementation Examples#
Environment-Based Upload Strategy#
// Use local upload in development, CDN in productioncesdk.actions.register('uploadFile', async (file, onProgress, context) => { if (process.env.NODE_ENV === 'development') { // Use utils for local upload return await cesdk.utils.localUpload(file, context); } else { console.log('Production upload for:', file.name); onProgress(100);
// Production: // const asset = await yourCDNService.upload(file, { // onProgress: onProgress // });
return { id: 'prod-' + Date.now(), label: { en: file.name }, meta: { uri: URL.createObjectURL(file), thumbUri: URL.createObjectURL(file) // Production: // uri: asset.url, // thumbUri: asset.thumbnailUrl } }; }});
Combining Utils with Custom Logic#
// Use utils for heavy lifting, add custom business logiccesdk.actions.register('exportDesign', async (options) => { console.log('Export started:', { format: options?.mimeType });
// Production: // analytics.track('export_started', { format: options?.mimeType });
// Use utils to handle the export with loading dialog const { blobs, options: exportOptions } = await cesdk.utils.export(options);
// Custom post-processing if (exportOptions.mimeType === 'application/pdf') { console.log('PDF ready for watermarking:', blobs[0].size, 'bytes');
// Production: // const watermarkedBlob = await addWatermark(blobs[0]); // await cesdk.utils.downloadFile(watermarkedBlob, 'application/pdf');
await cesdk.utils.downloadFile(blobs[0], 'application/pdf'); } else { // Direct download for other formats await cesdk.utils.downloadFile(blobs[0], exportOptions.mimeType); }
console.log('Export completed:', { format: exportOptions.mimeType });
// Production: // analytics.track('export_completed', { format: exportOptions.mimeType });});
Registering Custom Actions with Custom IDs#
Beyond the predefined action types, you can register actions with custom IDs for your own application-specific needs:
// Register a custom actioncesdk.actions.register('myCustomAction', async (data) => { console.log('Custom action triggered with:', data); return { success: true, processedData: data };});
// Execute the custom action using runconst result = await cesdk.actions.run('myCustomAction', { someData: 'value' });
// Or retrieve it for conditional executionconst customAction = cesdk.actions.get('myCustomAction');if (customAction) { const result = await customAction({ someData: 'value' });}
Using Actions with Navigation Actions#
The navigation bar actions in CE.SDK automatically use the registered actions:
Default Navigation Bar Actions#
The default navigation bar actions map to actions:
- Save action →
saveScene
action - Share action →
shareScene
action - Export actions →
exportDesign
action - Import scene/archive →
importScene
action - Export scene/archive →
exportScene
action