labellife-design-tool 1.0.8 → 1.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +186 -0
- package/dist/lib/lib/index.js +67 -14
- package/dist/lib/wordpress.js +67 -14
- package/dist/types/CanvasEditor.d.ts.map +1 -1
- package/dist/types/lib/index.d.ts +5 -2
- package/dist/types/lib/index.d.ts.map +1 -1
- package/dist/types/utils/exportImportUtils.d.ts +39 -0
- package/dist/types/utils/exportImportUtils.d.ts.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -117,6 +117,32 @@ The `CanvasEditorRef` interface provides the following properties and methods:
|
|
|
117
117
|
- `exportToJSON()`: Export the design to a JSON file
|
|
118
118
|
- `getDesign()`: Get the current design object
|
|
119
119
|
- `setCanvasSize(width, height)`: Set the canvas dimensions programmatically
|
|
120
|
+
- `loadDesign(jsonData)`: Load a design from JSON data (Promise-based)
|
|
121
|
+
|
|
122
|
+
### Export Helpers (JSON object + Base64)
|
|
123
|
+
|
|
124
|
+
In addition to the UI download helpers, the library also provides functions that return data directly (no file download):
|
|
125
|
+
|
|
126
|
+
```ts
|
|
127
|
+
import { exportToJSONObject, canvasToDataURL } from 'labellife-design-tool';
|
|
128
|
+
```
|
|
129
|
+
|
|
130
|
+
#### Get a JSON-safe design object
|
|
131
|
+
|
|
132
|
+
```ts
|
|
133
|
+
const designObject = exportToJSONObject(editorRef.current.getDesign());
|
|
134
|
+
// designObject is a plain JSON-compatible object you can send to an API
|
|
135
|
+
```
|
|
136
|
+
|
|
137
|
+
#### Get a base64 data URL of the canvas
|
|
138
|
+
|
|
139
|
+
```ts
|
|
140
|
+
const stage = editorRef.current.stage;
|
|
141
|
+
if (stage) {
|
|
142
|
+
const dataUrl = canvasToDataURL(stage, 'png', { pixelRatio: 2 });
|
|
143
|
+
// dataUrl is like: "data:image/png;base64,iVBORw0..."
|
|
144
|
+
}
|
|
145
|
+
```
|
|
120
146
|
|
|
121
147
|
### Canvas Size Management
|
|
122
148
|
|
|
@@ -366,6 +392,166 @@ importFromJSONData(
|
|
|
366
392
|
| **Use Case** | User file uploads | API data, database, programmatic imports |
|
|
367
393
|
| **Processing** | Identical | Identical |
|
|
368
394
|
|
|
395
|
+
### Simplified Template Loading (Recommended)
|
|
396
|
+
|
|
397
|
+
For the easiest template loading experience, we recommend using the new `loadDesign` method or `loadTemplateFromJSON` utility. These methods handle all the complexity internally and provide a clean, promise-based API.
|
|
398
|
+
|
|
399
|
+
#### Method 1: Using loadDesign with CanvasEditor Ref
|
|
400
|
+
|
|
401
|
+
This is the most straightforward approach - just pass the JSON data directly to the editor:
|
|
402
|
+
|
|
403
|
+
```tsx
|
|
404
|
+
import { useRef } from 'react';
|
|
405
|
+
import { CanvasEditor, CanvasEditorRef } from 'labellife-design-tool';
|
|
406
|
+
|
|
407
|
+
function TemplateLoader() {
|
|
408
|
+
const canvasEditorRef = useRef<CanvasEditorRef>(null);
|
|
409
|
+
|
|
410
|
+
const loadTemplate = async (templateData: any) => {
|
|
411
|
+
try {
|
|
412
|
+
await canvasEditorRef.current?.loadDesign(templateData);
|
|
413
|
+
console.log('Template loaded successfully!');
|
|
414
|
+
} catch (error) {
|
|
415
|
+
console.error('Failed to load template:', error);
|
|
416
|
+
alert('Failed to load template: ' + error.message);
|
|
417
|
+
}
|
|
418
|
+
};
|
|
419
|
+
|
|
420
|
+
// Example: Load template from API
|
|
421
|
+
const loadTemplateFromAPI = async (templateId: string) => {
|
|
422
|
+
try {
|
|
423
|
+
const response = await fetch(`/api/templates/${templateId}`);
|
|
424
|
+
const templateData = await response.json();
|
|
425
|
+
|
|
426
|
+
await canvasEditorRef.current?.loadDesign(templateData);
|
|
427
|
+
console.log('Template loaded successfully!');
|
|
428
|
+
} catch (error) {
|
|
429
|
+
console.error('API error:', error);
|
|
430
|
+
alert('Failed to load template: ' + error.message);
|
|
431
|
+
}
|
|
432
|
+
};
|
|
433
|
+
|
|
434
|
+
return (
|
|
435
|
+
<div>
|
|
436
|
+
<CanvasEditor ref={canvasEditorRef} name="Template Editor" />
|
|
437
|
+
<button onClick={() => loadTemplateFromAPI('123')}>
|
|
438
|
+
Load Template
|
|
439
|
+
</button>
|
|
440
|
+
</div>
|
|
441
|
+
);
|
|
442
|
+
}
|
|
443
|
+
```
|
|
444
|
+
|
|
445
|
+
#### Method 2: Using loadTemplateFromJSON Utility
|
|
446
|
+
|
|
447
|
+
This provides a convenient wrapper with additional error checking:
|
|
448
|
+
|
|
449
|
+
```tsx
|
|
450
|
+
import { useRef } from 'react';
|
|
451
|
+
import { CanvasEditor, CanvasEditorRef, loadTemplateFromJSON } from 'labellife-design-tool';
|
|
452
|
+
|
|
453
|
+
function TemplateLoader() {
|
|
454
|
+
const canvasEditorRef = useRef<CanvasEditorRef>(null);
|
|
455
|
+
|
|
456
|
+
const loadTemplate = async (templateData: any) => {
|
|
457
|
+
try {
|
|
458
|
+
await loadTemplateFromJSON(canvasEditorRef, templateData);
|
|
459
|
+
console.log('Template loaded successfully!');
|
|
460
|
+
} catch (error) {
|
|
461
|
+
console.error('Failed to load template:', error);
|
|
462
|
+
}
|
|
463
|
+
};
|
|
464
|
+
|
|
465
|
+
return <CanvasEditor ref={canvasEditorRef} name="Template Editor" />;
|
|
466
|
+
}
|
|
467
|
+
```
|
|
468
|
+
|
|
469
|
+
#### Your Colleague's Use Case
|
|
470
|
+
|
|
471
|
+
Here's how your colleague can now load templates with the simplified API:
|
|
472
|
+
|
|
473
|
+
```javascript
|
|
474
|
+
const loadTemplate = async (id) => {
|
|
475
|
+
try {
|
|
476
|
+
const response = await fetch(`${window.wpDesignData.baseUrl}/api/polotno/get-template/${id}/`, {
|
|
477
|
+
headers: { 'Authorization': `Bearer ${window.wpDesignData.userToken}` }
|
|
478
|
+
});
|
|
479
|
+
const templateData = await response.json();
|
|
480
|
+
|
|
481
|
+
if (templateData) {
|
|
482
|
+
const detailFileJson = templateData.details_file;
|
|
483
|
+
const responseFile = await fetch(detailFileJson);
|
|
484
|
+
const templateDataJson = await responseFile.json();
|
|
485
|
+
|
|
486
|
+
// Simple one-line call - no callbacks needed!
|
|
487
|
+
await canvasEditorRef.current.loadDesign(templateDataJson);
|
|
488
|
+
console.log('Template loaded successfully');
|
|
489
|
+
}
|
|
490
|
+
} catch (error) {
|
|
491
|
+
console.error('Failed to load template:', error);
|
|
492
|
+
alert('Failed to load template: ' + error.message);
|
|
493
|
+
}
|
|
494
|
+
};
|
|
495
|
+
```
|
|
496
|
+
|
|
497
|
+
**Key Benefits:**
|
|
498
|
+
- **No callbacks required** - uses promises for cleaner async handling
|
|
499
|
+
- **Automatic error handling** - throws descriptive errors
|
|
500
|
+
- **Internal state management** - handles `setDesign` automatically
|
|
501
|
+
- **History integration** - automatically saves to undo/redo history
|
|
502
|
+
- **Modal integration** - uses existing TemplateInputModal for user inputs
|
|
503
|
+
- **TypeScript support** - full type safety
|
|
504
|
+
|
|
505
|
+
#### What is canvasEditorRef?
|
|
506
|
+
|
|
507
|
+
`canvasEditorRef` is a React ref object that provides access to the CanvasEditor component's internal methods. Here's how to create and use it:
|
|
508
|
+
|
|
509
|
+
```tsx
|
|
510
|
+
import { useRef } from 'react';
|
|
511
|
+
import { CanvasEditor, CanvasEditorRef } from 'labellife-design-tool';
|
|
512
|
+
|
|
513
|
+
function MyComponent() {
|
|
514
|
+
// 1. Create the ref with proper typing
|
|
515
|
+
const canvasEditorRef = useRef<CanvasEditorRef>(null);
|
|
516
|
+
|
|
517
|
+
// 2. Pass it to the CanvasEditor component
|
|
518
|
+
return (
|
|
519
|
+
<CanvasEditor
|
|
520
|
+
ref={canvasEditorRef}
|
|
521
|
+
name="My Editor"
|
|
522
|
+
config={{ /* your config */ }}
|
|
523
|
+
/>
|
|
524
|
+
);
|
|
525
|
+
}
|
|
526
|
+
```
|
|
527
|
+
|
|
528
|
+
**Important Notes:**
|
|
529
|
+
- The ref is `null` until the component mounts
|
|
530
|
+
- Always check `canvasEditorRef.current` before using it
|
|
531
|
+
- The ref provides access to methods like `loadDesign`, `exportToPNG`, etc.
|
|
532
|
+
- TypeScript provides full autocomplete and type checking
|
|
533
|
+
|
|
534
|
+
#### Function Signature
|
|
535
|
+
|
|
536
|
+
```typescript
|
|
537
|
+
loadDesign(jsonData: any): Promise<void>
|
|
538
|
+
```
|
|
539
|
+
|
|
540
|
+
**Parameters:**
|
|
541
|
+
- `jsonData` (any): The raw JSON template data to load
|
|
542
|
+
|
|
543
|
+
**Returns:**
|
|
544
|
+
- `Promise<void>`: Resolves when the design is loaded, rejects on error
|
|
545
|
+
|
|
546
|
+
**Behavior:**
|
|
547
|
+
- Converts template format to internal CanvasDesign format
|
|
548
|
+
- Shows the existing TemplateInputModal for required user inputs
|
|
549
|
+
- Automatically handles optional inputs with empty values
|
|
550
|
+
- Updates the editor state
|
|
551
|
+
- Saves to undo/redo history
|
|
552
|
+
- Throws descriptive errors for invalid data or user cancellation
|
|
553
|
+
- Supports both required and optional user input fields
|
|
554
|
+
|
|
369
555
|
### Canvas to Blob Export
|
|
370
556
|
|
|
371
557
|
The library provides a flexible `canvasToBlob` function that allows converting the canvas to a Blob for various use cases:
|
package/dist/lib/lib/index.js
CHANGED
|
@@ -2552,6 +2552,9 @@ var exportToJPG = (stage, design) => {
|
|
|
2552
2552
|
document.body.removeChild(link);
|
|
2553
2553
|
}
|
|
2554
2554
|
};
|
|
2555
|
+
var exportToJSONObject = (design) => {
|
|
2556
|
+
return JSON.parse(JSON.stringify(design));
|
|
2557
|
+
};
|
|
2555
2558
|
var exportToJSON = (design) => {
|
|
2556
2559
|
const json = JSON.stringify(design, null, 2);
|
|
2557
2560
|
const blob = new Blob([json], { type: "application/json" });
|
|
@@ -2564,6 +2567,22 @@ var exportToJSON = (design) => {
|
|
|
2564
2567
|
document.body.removeChild(link);
|
|
2565
2568
|
URL.revokeObjectURL(url);
|
|
2566
2569
|
};
|
|
2570
|
+
var canvasToDataURL = (stage, format = "png", options) => {
|
|
2571
|
+
if (!stage) {
|
|
2572
|
+
throw new Error("Stage is required");
|
|
2573
|
+
}
|
|
2574
|
+
const oldScale = stage.scaleX();
|
|
2575
|
+
stage.scale({ x: 1, y: 1 });
|
|
2576
|
+
const pixelRatio = options?.pixelRatio ?? 2;
|
|
2577
|
+
const quality = options?.quality ?? 0.9;
|
|
2578
|
+
const dataUrl = stage.toDataURL({
|
|
2579
|
+
pixelRatio,
|
|
2580
|
+
mimeType: format === "jpg" ? "image/jpeg" : "image/png",
|
|
2581
|
+
quality: format === "jpg" ? quality : undefined
|
|
2582
|
+
});
|
|
2583
|
+
stage.scale({ x: oldScale, y: oldScale });
|
|
2584
|
+
return dataUrl;
|
|
2585
|
+
};
|
|
2567
2586
|
var canvasToBlob = (stage, format = "png", options) => {
|
|
2568
2587
|
if (!stage) {
|
|
2569
2588
|
return Promise.reject(new Error("Stage is required"));
|
|
@@ -2589,6 +2608,12 @@ var canvasToBlob = (stage, format = "png", options) => {
|
|
|
2589
2608
|
resolve(new Blob([arrayBuffer], { type: mimeType }));
|
|
2590
2609
|
});
|
|
2591
2610
|
};
|
|
2611
|
+
var loadTemplateFromJSON = async (canvasEditorRef, jsonData) => {
|
|
2612
|
+
if (!canvasEditorRef.current) {
|
|
2613
|
+
throw new Error("Canvas editor reference is not available. Make sure the CanvasEditor component is mounted.");
|
|
2614
|
+
}
|
|
2615
|
+
return canvasEditorRef.current.loadDesign(jsonData);
|
|
2616
|
+
};
|
|
2592
2617
|
var importFromJSONData = (jsonData, onLoad, onError, onInputsRequired) => {
|
|
2593
2618
|
try {
|
|
2594
2619
|
const convertedDesign = convertTemplateToCanvasDesign(jsonData);
|
|
@@ -3067,20 +3092,6 @@ var CanvasEditor = forwardRef(({
|
|
|
3067
3092
|
}));
|
|
3068
3093
|
}, []);
|
|
3069
3094
|
const stageRef = useRef5(null);
|
|
3070
|
-
useImperativeHandle(ref, () => ({
|
|
3071
|
-
stage: stageRef.current,
|
|
3072
|
-
exportToPNG: () => {
|
|
3073
|
-
if (stageRef.current)
|
|
3074
|
-
exportToPNG(stageRef.current, design);
|
|
3075
|
-
},
|
|
3076
|
-
exportToJPG: () => {
|
|
3077
|
-
if (stageRef.current)
|
|
3078
|
-
exportToJPG(stageRef.current, design);
|
|
3079
|
-
},
|
|
3080
|
-
exportToJSON: () => exportToJSON(design),
|
|
3081
|
-
getDesign: () => design,
|
|
3082
|
-
setCanvasSize
|
|
3083
|
-
}), [design, setCanvasSize]);
|
|
3084
3095
|
const fileInputRef = useRef5(null);
|
|
3085
3096
|
const jsonInputRef = useRef5(null);
|
|
3086
3097
|
const containerRef = useRef5(null);
|
|
@@ -3104,6 +3115,39 @@ var CanvasEditor = forwardRef(({
|
|
|
3104
3115
|
setDesign(JSON.parse(JSON.stringify(history[historyIndex + 1])));
|
|
3105
3116
|
}
|
|
3106
3117
|
}, [history, historyIndex]);
|
|
3118
|
+
useImperativeHandle(ref, () => ({
|
|
3119
|
+
stage: stageRef.current,
|
|
3120
|
+
exportToPNG: () => {
|
|
3121
|
+
if (stageRef.current)
|
|
3122
|
+
exportToPNG(stageRef.current, design);
|
|
3123
|
+
},
|
|
3124
|
+
exportToJPG: () => {
|
|
3125
|
+
if (stageRef.current)
|
|
3126
|
+
exportToJPG(stageRef.current, design);
|
|
3127
|
+
},
|
|
3128
|
+
exportToJSON: () => exportToJSON(design),
|
|
3129
|
+
getDesign: () => design,
|
|
3130
|
+
setCanvasSize,
|
|
3131
|
+
loadDesign: async (jsonData) => {
|
|
3132
|
+
return new Promise((resolve, reject) => {
|
|
3133
|
+
importFromJSONData(jsonData, (loadedDesign) => {
|
|
3134
|
+
setDesign(loadedDesign);
|
|
3135
|
+
saveToHistory(loadedDesign);
|
|
3136
|
+
resolve();
|
|
3137
|
+
}, (error) => {
|
|
3138
|
+
reject(new Error(error));
|
|
3139
|
+
}, (inputs, onComplete) => {
|
|
3140
|
+
setPendingInputs(inputs);
|
|
3141
|
+
setShowInputModal(true);
|
|
3142
|
+
window.__pendingImportComplete = (values) => {
|
|
3143
|
+
onComplete(values);
|
|
3144
|
+
resolve();
|
|
3145
|
+
};
|
|
3146
|
+
window.__pendingImportReject = reject;
|
|
3147
|
+
});
|
|
3148
|
+
});
|
|
3149
|
+
}
|
|
3150
|
+
}), [design, setCanvasSize, setDesign, saveToHistory, setShowInputModal, setPendingInputs]);
|
|
3107
3151
|
const addText = useCallback4(() => {
|
|
3108
3152
|
const newElement = {
|
|
3109
3153
|
id: Date.now().toString(),
|
|
@@ -3508,6 +3552,7 @@ var CanvasEditor = forwardRef(({
|
|
|
3508
3552
|
if (onComplete) {
|
|
3509
3553
|
onComplete(values);
|
|
3510
3554
|
delete window.__pendingImportComplete;
|
|
3555
|
+
delete window.__pendingImportReject;
|
|
3511
3556
|
}
|
|
3512
3557
|
setPendingInputs([]);
|
|
3513
3558
|
};
|
|
@@ -3515,6 +3560,11 @@ var CanvasEditor = forwardRef(({
|
|
|
3515
3560
|
setShowInputModal(false);
|
|
3516
3561
|
setPendingInputs([]);
|
|
3517
3562
|
delete window.__pendingImportComplete;
|
|
3563
|
+
const onReject = window.__pendingImportReject;
|
|
3564
|
+
if (onReject) {
|
|
3565
|
+
onReject(new Error("User cancelled template import"));
|
|
3566
|
+
delete window.__pendingImportReject;
|
|
3567
|
+
}
|
|
3518
3568
|
};
|
|
3519
3569
|
const panelConfigs = [
|
|
3520
3570
|
{
|
|
@@ -3890,14 +3940,17 @@ initJsxCompat();
|
|
|
3890
3940
|
export {
|
|
3891
3941
|
setUnsplashAccessKey,
|
|
3892
3942
|
replaceUserInputs,
|
|
3943
|
+
loadTemplateFromJSON,
|
|
3893
3944
|
importFromJSONData,
|
|
3894
3945
|
importFromJSON,
|
|
3895
3946
|
getUnsplashAccessKey,
|
|
3896
3947
|
findRequiredInputs,
|
|
3897
3948
|
exportToPNG,
|
|
3949
|
+
exportToJSONObject,
|
|
3898
3950
|
exportToJSON,
|
|
3899
3951
|
exportToJPG,
|
|
3900
3952
|
convertTemplateToCanvasDesign,
|
|
3953
|
+
canvasToDataURL,
|
|
3901
3954
|
canvasToBlob,
|
|
3902
3955
|
UrlImageElement,
|
|
3903
3956
|
ShapeElement,
|
package/dist/lib/wordpress.js
CHANGED
|
@@ -2552,6 +2552,9 @@ var exportToJPG = (stage, design) => {
|
|
|
2552
2552
|
document.body.removeChild(link);
|
|
2553
2553
|
}
|
|
2554
2554
|
};
|
|
2555
|
+
var exportToJSONObject = (design) => {
|
|
2556
|
+
return JSON.parse(JSON.stringify(design));
|
|
2557
|
+
};
|
|
2555
2558
|
var exportToJSON = (design) => {
|
|
2556
2559
|
const json = JSON.stringify(design, null, 2);
|
|
2557
2560
|
const blob = new Blob([json], { type: "application/json" });
|
|
@@ -2564,6 +2567,22 @@ var exportToJSON = (design) => {
|
|
|
2564
2567
|
document.body.removeChild(link);
|
|
2565
2568
|
URL.revokeObjectURL(url);
|
|
2566
2569
|
};
|
|
2570
|
+
var canvasToDataURL = (stage, format = "png", options) => {
|
|
2571
|
+
if (!stage) {
|
|
2572
|
+
throw new Error("Stage is required");
|
|
2573
|
+
}
|
|
2574
|
+
const oldScale = stage.scaleX();
|
|
2575
|
+
stage.scale({ x: 1, y: 1 });
|
|
2576
|
+
const pixelRatio = options?.pixelRatio ?? 2;
|
|
2577
|
+
const quality = options?.quality ?? 0.9;
|
|
2578
|
+
const dataUrl = stage.toDataURL({
|
|
2579
|
+
pixelRatio,
|
|
2580
|
+
mimeType: format === "jpg" ? "image/jpeg" : "image/png",
|
|
2581
|
+
quality: format === "jpg" ? quality : undefined
|
|
2582
|
+
});
|
|
2583
|
+
stage.scale({ x: oldScale, y: oldScale });
|
|
2584
|
+
return dataUrl;
|
|
2585
|
+
};
|
|
2567
2586
|
var canvasToBlob = (stage, format = "png", options) => {
|
|
2568
2587
|
if (!stage) {
|
|
2569
2588
|
return Promise.reject(new Error("Stage is required"));
|
|
@@ -2589,6 +2608,12 @@ var canvasToBlob = (stage, format = "png", options) => {
|
|
|
2589
2608
|
resolve(new Blob([arrayBuffer], { type: mimeType }));
|
|
2590
2609
|
});
|
|
2591
2610
|
};
|
|
2611
|
+
var loadTemplateFromJSON = async (canvasEditorRef, jsonData) => {
|
|
2612
|
+
if (!canvasEditorRef.current) {
|
|
2613
|
+
throw new Error("Canvas editor reference is not available. Make sure the CanvasEditor component is mounted.");
|
|
2614
|
+
}
|
|
2615
|
+
return canvasEditorRef.current.loadDesign(jsonData);
|
|
2616
|
+
};
|
|
2592
2617
|
var importFromJSONData = (jsonData, onLoad, onError, onInputsRequired) => {
|
|
2593
2618
|
try {
|
|
2594
2619
|
const convertedDesign = convertTemplateToCanvasDesign(jsonData);
|
|
@@ -3067,20 +3092,6 @@ var CanvasEditor = forwardRef(({
|
|
|
3067
3092
|
}));
|
|
3068
3093
|
}, []);
|
|
3069
3094
|
const stageRef = useRef5(null);
|
|
3070
|
-
useImperativeHandle(ref, () => ({
|
|
3071
|
-
stage: stageRef.current,
|
|
3072
|
-
exportToPNG: () => {
|
|
3073
|
-
if (stageRef.current)
|
|
3074
|
-
exportToPNG(stageRef.current, design);
|
|
3075
|
-
},
|
|
3076
|
-
exportToJPG: () => {
|
|
3077
|
-
if (stageRef.current)
|
|
3078
|
-
exportToJPG(stageRef.current, design);
|
|
3079
|
-
},
|
|
3080
|
-
exportToJSON: () => exportToJSON(design),
|
|
3081
|
-
getDesign: () => design,
|
|
3082
|
-
setCanvasSize
|
|
3083
|
-
}), [design, setCanvasSize]);
|
|
3084
3095
|
const fileInputRef = useRef5(null);
|
|
3085
3096
|
const jsonInputRef = useRef5(null);
|
|
3086
3097
|
const containerRef = useRef5(null);
|
|
@@ -3104,6 +3115,39 @@ var CanvasEditor = forwardRef(({
|
|
|
3104
3115
|
setDesign(JSON.parse(JSON.stringify(history[historyIndex + 1])));
|
|
3105
3116
|
}
|
|
3106
3117
|
}, [history, historyIndex]);
|
|
3118
|
+
useImperativeHandle(ref, () => ({
|
|
3119
|
+
stage: stageRef.current,
|
|
3120
|
+
exportToPNG: () => {
|
|
3121
|
+
if (stageRef.current)
|
|
3122
|
+
exportToPNG(stageRef.current, design);
|
|
3123
|
+
},
|
|
3124
|
+
exportToJPG: () => {
|
|
3125
|
+
if (stageRef.current)
|
|
3126
|
+
exportToJPG(stageRef.current, design);
|
|
3127
|
+
},
|
|
3128
|
+
exportToJSON: () => exportToJSON(design),
|
|
3129
|
+
getDesign: () => design,
|
|
3130
|
+
setCanvasSize,
|
|
3131
|
+
loadDesign: async (jsonData) => {
|
|
3132
|
+
return new Promise((resolve, reject) => {
|
|
3133
|
+
importFromJSONData(jsonData, (loadedDesign) => {
|
|
3134
|
+
setDesign(loadedDesign);
|
|
3135
|
+
saveToHistory(loadedDesign);
|
|
3136
|
+
resolve();
|
|
3137
|
+
}, (error) => {
|
|
3138
|
+
reject(new Error(error));
|
|
3139
|
+
}, (inputs, onComplete) => {
|
|
3140
|
+
setPendingInputs(inputs);
|
|
3141
|
+
setShowInputModal(true);
|
|
3142
|
+
window.__pendingImportComplete = (values) => {
|
|
3143
|
+
onComplete(values);
|
|
3144
|
+
resolve();
|
|
3145
|
+
};
|
|
3146
|
+
window.__pendingImportReject = reject;
|
|
3147
|
+
});
|
|
3148
|
+
});
|
|
3149
|
+
}
|
|
3150
|
+
}), [design, setCanvasSize, setDesign, saveToHistory, setShowInputModal, setPendingInputs]);
|
|
3107
3151
|
const addText = useCallback4(() => {
|
|
3108
3152
|
const newElement = {
|
|
3109
3153
|
id: Date.now().toString(),
|
|
@@ -3508,6 +3552,7 @@ var CanvasEditor = forwardRef(({
|
|
|
3508
3552
|
if (onComplete) {
|
|
3509
3553
|
onComplete(values);
|
|
3510
3554
|
delete window.__pendingImportComplete;
|
|
3555
|
+
delete window.__pendingImportReject;
|
|
3511
3556
|
}
|
|
3512
3557
|
setPendingInputs([]);
|
|
3513
3558
|
};
|
|
@@ -3515,6 +3560,11 @@ var CanvasEditor = forwardRef(({
|
|
|
3515
3560
|
setShowInputModal(false);
|
|
3516
3561
|
setPendingInputs([]);
|
|
3517
3562
|
delete window.__pendingImportComplete;
|
|
3563
|
+
const onReject = window.__pendingImportReject;
|
|
3564
|
+
if (onReject) {
|
|
3565
|
+
onReject(new Error("User cancelled template import"));
|
|
3566
|
+
delete window.__pendingImportReject;
|
|
3567
|
+
}
|
|
3518
3568
|
};
|
|
3519
3569
|
const panelConfigs = [
|
|
3520
3570
|
{
|
|
@@ -3942,15 +3992,18 @@ function initWordPressCanvasEditor(containerId, props) {
|
|
|
3942
3992
|
export {
|
|
3943
3993
|
setUnsplashAccessKey,
|
|
3944
3994
|
replaceUserInputs,
|
|
3995
|
+
loadTemplateFromJSON,
|
|
3945
3996
|
initWordPressCanvasEditor,
|
|
3946
3997
|
importFromJSONData,
|
|
3947
3998
|
importFromJSON,
|
|
3948
3999
|
getUnsplashAccessKey,
|
|
3949
4000
|
findRequiredInputs,
|
|
3950
4001
|
exportToPNG,
|
|
4002
|
+
exportToJSONObject,
|
|
3951
4003
|
exportToJSON,
|
|
3952
4004
|
exportToJPG,
|
|
3953
4005
|
convertTemplateToCanvasDesign,
|
|
4006
|
+
canvasToDataURL,
|
|
3954
4007
|
canvasToBlob,
|
|
3955
4008
|
UrlImageElement,
|
|
3956
4009
|
ShapeElement,
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"CanvasEditor.d.ts","sourceRoot":"","sources":["../../src/CanvasEditor.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAoF,MAAM,OAAO,CAAC;AAGzG,OAAO,KAAK,MAAM,OAAO,CAAC;AA0C1B,OAAO,EAEL,YAAY,EAKb,MAAM,SAAS,CAAC;AAiCjB,OAAO,EAAE,MAAM,EAAE,MAAM,gBAAgB,CAAC;AAGxC,MAAM,WAAW,eAAe;IAC9B,KAAK,EAAE,KAAK,CAAC,KAAK,GAAG,IAAI,CAAC;IAC1B,WAAW,EAAE,MAAM,IAAI,CAAC;IACxB,WAAW,EAAE,MAAM,IAAI,CAAC;IACxB,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB,SAAS,EAAE,MAAM,YAAY,CAAC;IAC9B,aAAa,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;CACxD;AAED,QAAA,MAAM,YAAY;UAAuC,MAAM;aAAW,MAAM;
|
|
1
|
+
{"version":3,"file":"CanvasEditor.d.ts","sourceRoot":"","sources":["../../src/CanvasEditor.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAoF,MAAM,OAAO,CAAC;AAGzG,OAAO,KAAK,MAAM,OAAO,CAAC;AA0C1B,OAAO,EAEL,YAAY,EAKb,MAAM,SAAS,CAAC;AAiCjB,OAAO,EAAE,MAAM,EAAE,MAAM,gBAAgB,CAAC;AAGxC,MAAM,WAAW,eAAe;IAC9B,KAAK,EAAE,KAAK,CAAC,KAAK,GAAG,IAAI,CAAC;IAC1B,WAAW,EAAE,MAAM,IAAI,CAAC;IACxB,WAAW,EAAE,MAAM,IAAI,CAAC;IACxB,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB,SAAS,EAAE,MAAM,YAAY,CAAC;IAC9B,aAAa,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;CACxD;AAED,QAAA,MAAM,YAAY;UAAuC,MAAM;aAAW,MAAM;yCAwqC9E,CAAC;AAEH,eAAe,YAAY,CAAC"}
|
|
@@ -10,11 +10,14 @@ export interface CanvasEditorRef {
|
|
|
10
10
|
exportToJPG: () => void;
|
|
11
11
|
exportToJSON: () => void;
|
|
12
12
|
getDesign: () => CanvasDesign;
|
|
13
|
+
setCanvasSize: (width: number, height: number) => void;
|
|
14
|
+
loadDesign: (jsonData: any) => Promise<void>;
|
|
13
15
|
}
|
|
14
16
|
export { default as CanvasEditor } from '../CanvasEditor';
|
|
15
17
|
export * from '../types';
|
|
16
|
-
export { exportToPNG, exportToJPG, exportToJSON, importFromJSON, importFromJSONData, //
|
|
17
|
-
|
|
18
|
+
export { exportToPNG, exportToJPG, exportToJSON, exportToJSONObject, importFromJSON, importFromJSONData, // Import JSON data directly (no file needed)
|
|
19
|
+
loadTemplateFromJSON, // Simplified template loading utility
|
|
20
|
+
findRequiredInputs, replaceUserInputs, convertTemplateToCanvasDesign, canvasToDataURL, canvasToBlob, } from '../utils/exportImportUtils';
|
|
18
21
|
export * from '../elements';
|
|
19
22
|
export { FONT_FAMILIES, DEFAULT_COLORS, CANVAS_PRESETS } from '../constants';
|
|
20
23
|
export { setUnsplashAccessKey, getUnsplashAccessKey } from '../config';
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AASxC,MAAM,WAAW,eAAe;IAC9B,KAAK,EAAE,KAAK,CAAC,KAAK,GAAG,IAAI,CAAC;IAC1B,WAAW,EAAE,MAAM,IAAI,CAAC;IACxB,WAAW,EAAE,MAAM,IAAI,CAAC;IACxB,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB,SAAS,EAAE,MAAM,YAAY,CAAC;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/lib/index.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,KAAK,MAAM,OAAO,CAAC;AAC1B,OAAO,EAAE,YAAY,EAAE,MAAM,UAAU,CAAC;AASxC,MAAM,WAAW,eAAe;IAC9B,KAAK,EAAE,KAAK,CAAC,KAAK,GAAG,IAAI,CAAC;IAC1B,WAAW,EAAE,MAAM,IAAI,CAAC;IACxB,WAAW,EAAE,MAAM,IAAI,CAAC;IACxB,YAAY,EAAE,MAAM,IAAI,CAAC;IACzB,SAAS,EAAE,MAAM,YAAY,CAAC;IAC9B,aAAa,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,KAAK,IAAI,CAAC;IACvD,UAAU,EAAE,CAAC,QAAQ,EAAE,GAAG,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;CAC9C;AAGD,OAAO,EAAE,OAAO,IAAI,YAAY,EAAE,MAAM,iBAAiB,CAAC;AAG1D,cAAc,UAAU,CAAC;AAGzB,OAAO,EACL,WAAW,EACX,WAAW,EACX,YAAY,EACZ,kBAAkB,EAClB,cAAc,EACd,kBAAkB,EAAE,6CAA6C;AACjE,oBAAoB,EAAE,sCAAsC;AAC5D,kBAAkB,EAClB,iBAAiB,EACjB,6BAA6B,EAC7B,eAAe,EACf,YAAY,GACb,MAAM,4BAA4B,CAAC;AAGpC,cAAc,aAAa,CAAC;AAG5B,OAAO,EAAE,aAAa,EAAE,cAAc,EAAE,cAAc,EAAE,MAAM,cAAc,CAAC;AAG7E,OAAO,EAAE,oBAAoB,EAAE,oBAAoB,EAAE,MAAM,WAAW,CAAC"}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import { type CanvasDesign } from "../types/CanvasDesign";
|
|
2
2
|
import { type UserInputItem } from "../types/UserInput";
|
|
3
|
+
import { type CanvasEditorRef } from "../lib";
|
|
3
4
|
import Konva from "konva";
|
|
4
5
|
/**
|
|
5
6
|
* Converts a template JSON format to CanvasDesign format
|
|
@@ -19,6 +20,7 @@ export declare function findRequiredInputs(design: CanvasDesign): UserInputItem[
|
|
|
19
20
|
export declare function replaceUserInputs(design: CanvasDesign, collectedInputs: Record<string, any>): CanvasDesign;
|
|
20
21
|
export declare const exportToPNG: (stage: Konva.Stage, design: CanvasDesign) => void;
|
|
21
22
|
export declare const exportToJPG: (stage: Konva.Stage, design: CanvasDesign) => void;
|
|
23
|
+
export declare const exportToJSONObject: (design: CanvasDesign) => CanvasDesign;
|
|
22
24
|
export declare const exportToJSON: (design: CanvasDesign) => void;
|
|
23
25
|
/**
|
|
24
26
|
* Converts the canvas to a Blob that can be used for various purposes
|
|
@@ -27,6 +29,10 @@ export declare const exportToJSON: (design: CanvasDesign) => void;
|
|
|
27
29
|
* @param options - Additional options for conversion
|
|
28
30
|
* @returns Promise that resolves with a Blob
|
|
29
31
|
*/
|
|
32
|
+
export declare const canvasToDataURL: (stage: Konva.Stage, format?: "png" | "jpg", options?: {
|
|
33
|
+
quality?: number;
|
|
34
|
+
pixelRatio?: number;
|
|
35
|
+
}) => string;
|
|
30
36
|
export declare const canvasToBlob: (stage: Konva.Stage, format?: "png" | "jpg", options?: {
|
|
31
37
|
quality?: number;
|
|
32
38
|
pixelRatio?: number;
|
|
@@ -126,6 +132,39 @@ export declare const canvasToBlob: (stage: Konva.Stage, format?: "png" | "jpg",
|
|
|
126
132
|
* @see findRequiredInputs - User input detection
|
|
127
133
|
* @see replaceUserInputs - Input replacement logic
|
|
128
134
|
*/
|
|
135
|
+
/**
|
|
136
|
+
* Simplified function to load a template from JSON data using a CanvasEditor ref
|
|
137
|
+
*
|
|
138
|
+
* This is a convenience wrapper around the loadDesign method that provides
|
|
139
|
+
* a cleaner API for loading templates from external sources.
|
|
140
|
+
*
|
|
141
|
+
* @param canvasEditorRef - React ref object pointing to a CanvasEditor instance
|
|
142
|
+
* @param jsonData - The raw JSON template data to load
|
|
143
|
+
*
|
|
144
|
+
* @example
|
|
145
|
+
* ```typescript
|
|
146
|
+
* import { useRef } from 'react';
|
|
147
|
+
* import { CanvasEditor, CanvasEditorRef, loadTemplateFromJSON } from 'labellife-design-tool';
|
|
148
|
+
*
|
|
149
|
+
* function MyComponent() {
|
|
150
|
+
* const canvasEditorRef = useRef<CanvasEditorRef>(null);
|
|
151
|
+
*
|
|
152
|
+
* const loadTemplate = async (templateData: any) => {
|
|
153
|
+
* try {
|
|
154
|
+
* await loadTemplateFromJSON(canvasEditorRef, templateData);
|
|
155
|
+
* console.log('Template loaded successfully!');
|
|
156
|
+
* } catch (error) {
|
|
157
|
+
* console.error('Failed to load template:', error);
|
|
158
|
+
* }
|
|
159
|
+
* };
|
|
160
|
+
*
|
|
161
|
+
* return (
|
|
162
|
+
* <CanvasEditor ref={canvasEditorRef} />
|
|
163
|
+
* );
|
|
164
|
+
* }
|
|
165
|
+
* ```
|
|
166
|
+
*/
|
|
167
|
+
export declare const loadTemplateFromJSON: (canvasEditorRef: React.RefObject<CanvasEditorRef>, jsonData: any) => Promise<void>;
|
|
129
168
|
export declare const importFromJSONData: (jsonData: any, onLoad: (design: CanvasDesign) => void, onError: (message: string) => void, onInputsRequired?: (inputs: UserInputItem[], onComplete: (values: Record<string, any>) => void) => void) => void;
|
|
130
169
|
export declare const importFromJSON: (event: React.ChangeEvent<HTMLInputElement>, onLoad: (design: CanvasDesign) => void, onError: (message: string) => void, onInputsRequired?: (inputs: UserInputItem[], onComplete: (values: Record<string, any>) => void) => void) => void;
|
|
131
170
|
//# sourceMappingURL=exportImportUtils.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"exportImportUtils.d.ts","sourceRoot":"","sources":["../../../src/utils/exportImportUtils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,YAAY,EAAE,MAAM,uBAAuB,CAAC;AAE1D,OAAO,EAAE,KAAK,aAAa,EAAE,MAAM,oBAAoB,CAAC;AAExD,OAAO,KAAK,MAAM,OAAO,CAAC;AAE1B;;;;;;GAMG;AACH,wBAAgB,6BAA6B,CAAC,IAAI,EAAE,GAAG,GAAG,YAAY,CAuHrE;AAED;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,YAAY,GAAG,aAAa,EAAE,CAsHxE;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAC7B,MAAM,EAAE,YAAY,EACpB,eAAe,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GACrC,YAAY,CA6Nd;AAGD,eAAO,MAAM,WAAW,GAAI,OAAO,KAAK,CAAC,KAAK,EAAE,QAAQ,YAAY,SAanE,CAAC;AAEF,eAAO,MAAM,WAAW,GAAI,OAAO,KAAK,CAAC,KAAK,EAAE,QAAQ,YAAY,SAiBnE,CAAC;AAEF,eAAO,MAAM,YAAY,GAAI,QAAQ,YAAY,SAWhD,CAAC;AAEF;;;;;;GAMG;AACH,eAAO,MAAM,YAAY,GACrB,OAAO,KAAK,CAAC,KAAK,EAClB,SAAQ,KAAK,GAAG,KAAa,EAC7B,UAAU;IACN,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,UAAU,CAAC,EAAE,MAAM,CAAC;CACvB,KACF,OAAO,CAAC,IAAI,CAsCd,CAAC;AAEF;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8FG;AACH,eAAO,MAAM,kBAAkB,GAC3B,UAAU,GAAG,EACb,QAAQ,CAAC,MAAM,EAAE,YAAY,KAAK,IAAI,EACtC,SAAS,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,EAClC,mBAAmB,CAAC,MAAM,EAAE,aAAa,EAAE,EAAE,UAAU,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,KAAK,IAAI,KAAK,IAAI,SAuB1G,CAAC;AAEF,eAAO,MAAM,cAAc,GACvB,OAAO,KAAK,CAAC,WAAW,CAAC,gBAAgB,CAAC,EAC1C,QAAQ,CAAC,MAAM,EAAE,YAAY,KAAK,IAAI,EACtC,SAAS,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,EAClC,mBAAmB,CAAC,MAAM,EAAE,aAAa,EAAE,EAAE,UAAU,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,KAAK,IAAI,KAAK,IAAI,SA0C1G,CAAC"}
|
|
1
|
+
{"version":3,"file":"exportImportUtils.d.ts","sourceRoot":"","sources":["../../../src/utils/exportImportUtils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,YAAY,EAAE,MAAM,uBAAuB,CAAC;AAE1D,OAAO,EAAE,KAAK,aAAa,EAAE,MAAM,oBAAoB,CAAC;AAExD,OAAO,EAAE,KAAK,eAAe,EAAE,MAAM,QAAQ,CAAC;AAC9C,OAAO,KAAK,MAAM,OAAO,CAAC;AAE1B;;;;;;GAMG;AACH,wBAAgB,6BAA6B,CAAC,IAAI,EAAE,GAAG,GAAG,YAAY,CAuHrE;AAED;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,YAAY,GAAG,aAAa,EAAE,CAsHxE;AAED;;GAEG;AACH,wBAAgB,iBAAiB,CAC7B,MAAM,EAAE,YAAY,EACpB,eAAe,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,GACrC,YAAY,CA6Nd;AAGD,eAAO,MAAM,WAAW,GAAI,OAAO,KAAK,CAAC,KAAK,EAAE,QAAQ,YAAY,SAanE,CAAC;AAEF,eAAO,MAAM,WAAW,GAAI,OAAO,KAAK,CAAC,KAAK,EAAE,QAAQ,YAAY,SAiBnE,CAAC;AAEF,eAAO,MAAM,kBAAkB,GAAI,QAAQ,YAAY,KAAG,YAEzD,CAAC;AAEF,eAAO,MAAM,YAAY,GAAI,QAAQ,YAAY,SAWhD,CAAC;AAEF;;;;;;GAMG;AACH,eAAO,MAAM,eAAe,GACxB,OAAO,KAAK,CAAC,KAAK,EAClB,SAAQ,KAAK,GAAG,KAAa,EAC7B,UAAU;IACN,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,UAAU,CAAC,EAAE,MAAM,CAAC;CACvB,KACF,MAoBF,CAAC;AAEF,eAAO,MAAM,YAAY,GACrB,OAAO,KAAK,CAAC,KAAK,EAClB,SAAQ,KAAK,GAAG,KAAa,EAC7B,UAAU;IACN,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,UAAU,CAAC,EAAE,MAAM,CAAC;CACvB,KACF,OAAO,CAAC,IAAI,CAsCd,CAAC;AAEF;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA8FG;AACH;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA+BG;AACH,eAAO,MAAM,oBAAoB,GAC/B,iBAAiB,KAAK,CAAC,SAAS,CAAC,eAAe,CAAC,EACjD,UAAU,GAAG,KACZ,OAAO,CAAC,IAAI,CAMd,CAAC;AAEF,eAAO,MAAM,kBAAkB,GAC3B,UAAU,GAAG,EACb,QAAQ,CAAC,MAAM,EAAE,YAAY,KAAK,IAAI,EACtC,SAAS,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,EAClC,mBAAmB,CAAC,MAAM,EAAE,aAAa,EAAE,EAAE,UAAU,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,KAAK,IAAI,KAAK,IAAI,SAuB1G,CAAC;AAEF,eAAO,MAAM,cAAc,GACvB,OAAO,KAAK,CAAC,WAAW,CAAC,gBAAgB,CAAC,EAC1C,QAAQ,CAAC,MAAM,EAAE,YAAY,KAAK,IAAI,EACtC,SAAS,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,EAClC,mBAAmB,CAAC,MAAM,EAAE,aAAa,EAAE,EAAE,UAAU,EAAE,CAAC,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,KAAK,IAAI,KAAK,IAAI,SA0C1G,CAAC"}
|