@flowscape-ui/core-sdk 1.0.8 → 2.0.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/LICENSE +21 -21
- package/README.md +124 -384
- package/dist/index.cjs +1 -112
- package/dist/index.d.cts +6073 -2467
- package/dist/index.d.ts +6073 -2467
- package/dist/index.js +1 -112
- package/package.json +110 -105
package/LICENSE
CHANGED
|
@@ -1,21 +1,21 @@
|
|
|
1
|
-
MIT License
|
|
2
|
-
|
|
3
|
-
Copyright (c) 2025 Flowscape UI
|
|
4
|
-
|
|
5
|
-
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
-
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
-
in the Software without restriction, including without limitation the rights
|
|
8
|
-
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
-
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
-
furnished to do so, subject to the following conditions:
|
|
11
|
-
|
|
12
|
-
The above copyright notice and this permission notice shall be included in all
|
|
13
|
-
copies or substantial portions of the Software.
|
|
14
|
-
|
|
15
|
-
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
-
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
-
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
-
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
-
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
-
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
-
SOFTWARE.
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2025 Flowscape UI
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|
package/README.md
CHANGED
|
@@ -1,384 +1,124 @@
|
|
|
1
|
-
<div align="center">
|
|
2
|
-
|
|
3
|
-
# 🎨 @flowscape-ui/core-sdk
|
|
4
|
-
|
|
5
|
-
**
|
|
6
|
-
|
|
7
|
-
[](https://opensource.org/licenses/MIT)
|
|
9
|
-
[](https://bundlephobia.com/package/@flowscape-ui/core-sdk)
|
|
10
|
-
[](https://x.com/FlowscapeUI)
|
|
11
|
-
|
|
12
|
-
[](https://flowscape-ui.github.io/core-sdk/)
|
|
13
|
-
[](https://flowscape-ui.github.io/core-sdk/?path=/story/interactive-playground--interactive-playground)
|
|
14
|
-
[](./CHANGELOG.md)
|
|
15
|
-
|
|
16
|
-
<img
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
</div>
|
|
23
|
-
|
|
24
|
-
---
|
|
25
|
-
|
|
26
|
-
##
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
│ │ - Zoom (Ctrl+Wheel) │ │
|
|
126
|
-
│ └──────────────────────────────┘ │
|
|
127
|
-
└─────────────────────────────────────┘
|
|
128
|
-
```
|
|
129
|
-
|
|
130
|
-
### Plugin System
|
|
131
|
-
|
|
132
|
-
Plugins extend engine functionality without modifying the core:
|
|
133
|
-
|
|
134
|
-
```typescript
|
|
135
|
-
import { Plugin, CoreEngine } from '@flowscape-ui/core-sdk';
|
|
136
|
-
|
|
137
|
-
class CustomPlugin extends Plugin {
|
|
138
|
-
protected onAttach(core: CoreEngine): void {
|
|
139
|
-
// Initialize on attach
|
|
140
|
-
core.eventBus.on('node:created', (node) => {
|
|
141
|
-
console.log('Node created:', node);
|
|
142
|
-
});
|
|
143
|
-
}
|
|
144
|
-
|
|
145
|
-
protected onDetach(core: CoreEngine): void {
|
|
146
|
-
// Cleanup on detach
|
|
147
|
-
core.eventBus.off('node:created');
|
|
148
|
-
}
|
|
149
|
-
}
|
|
150
|
-
|
|
151
|
-
// Usage
|
|
152
|
-
const engine = new CoreEngine({
|
|
153
|
-
container: element,
|
|
154
|
-
plugins: [new CustomPlugin()],
|
|
155
|
-
});
|
|
156
|
-
```
|
|
157
|
-
|
|
158
|
-
---
|
|
159
|
-
|
|
160
|
-
| Plugin | Description |
|
|
161
|
-
| ---------------------- | ------------------------------------------------ |
|
|
162
|
-
| `GridPlugin` | Adaptive grid with automatic scaling |
|
|
163
|
-
| `SelectionPlugin` | Selection, transformation, drag & drop, grouping |
|
|
164
|
-
| `NodeHotkeysPlugin` | Copy/paste/cut nodes, delete, z-index management |
|
|
165
|
-
| `CameraHotkeysPlugin` | Zoom and pan controls with keyboard |
|
|
166
|
-
| `RulerPlugin` | Rulers with measurement units |
|
|
167
|
-
| `RulerGuidesPlugin` | Draggable guide lines from rulers |
|
|
168
|
-
| `RulerHighlightPlugin` | Ruler highlighting on hover |
|
|
169
|
-
| `RulerManagerPlugin` | Toggle rulers and manage guides |
|
|
170
|
-
| `AreaSelectionPlugin` | Area selection with frame (Shift+Drag) |
|
|
171
|
-
| `VisualGuidesPlugin` | Smart alignment guides during movement/resize |
|
|
172
|
-
| `HistoryPlugin` | Undo/redo functionality with Ctrl+Z |
|
|
173
|
-
| `PersistencePlugin` | Local persistence: auto-save, export/import JSON |
|
|
174
|
-
| `LogoPlugin` | Watermark/logo on canvas |
|
|
175
|
-
|
|
176
|
-
| Plugin | Description |
|
|
177
|
-
| ------------------------ | ----------------------------------------------------- |
|
|
178
|
-
| **GridPlugin** | Adaptive grid with automatic scaling and snap-to-grid |
|
|
179
|
-
| **SelectionPlugin** | Selection, transformation, drag & drop, grouping |
|
|
180
|
-
| **AreaSelectionPlugin** | Area selection with frame (Shift+Drag) |
|
|
181
|
-
| **NodeHotkeysPlugin** | Copy/paste/cut nodes, delete, z-index management |
|
|
182
|
-
| **CameraHotkeysPlugin** | Zoom and pan controls with keyboard |
|
|
183
|
-
| **RulerPlugin** | Rulers with measurement units |
|
|
184
|
-
| **RulerGuidesPlugin** | Draggable guide lines from rulers |
|
|
185
|
-
| **RulerHighlightPlugin** | Ruler highlighting on hover |
|
|
186
|
-
| **RulerManagerPlugin** | Toggle rulers and manage guides |
|
|
187
|
-
| **LogoPlugin** | Watermark/logo on canvas |
|
|
188
|
-
|
|
189
|
-
---
|
|
190
|
-
|
|
191
|
-
## ⌨️ Keyboard Shortcuts
|
|
192
|
-
|
|
193
|
-
### Node Operations (NodeHotkeysPlugin)
|
|
194
|
-
|
|
195
|
-
| Shortcut | Action |
|
|
196
|
-
| ---------------------- | -------------------------------- |
|
|
197
|
-
| `Ctrl+C` | Copy selected nodes |
|
|
198
|
-
| `Ctrl+X` | Cut selected nodes |
|
|
199
|
-
| `Ctrl+V` | Paste nodes |
|
|
200
|
-
| `Delete` / `Backspace` | Delete selected nodes |
|
|
201
|
-
| `Alt+Drag (LMB)` | Clone selected nodes by dragging |
|
|
202
|
-
| `Ctrl+]` | Move node forward (z-index) |
|
|
203
|
-
| `Ctrl+[` | Move node backward (z-index) |
|
|
204
|
-
| `Ctrl+Shift+]` | Bring to front |
|
|
205
|
-
| `Ctrl+Shift+[` | Send to back |
|
|
206
|
-
|
|
207
|
-
### Grouping (SelectionPlugin)
|
|
208
|
-
|
|
209
|
-
| Shortcut | Action |
|
|
210
|
-
| ----------------------- | --------------------------------- |
|
|
211
|
-
| `Ctrl+G` | Group selected nodes |
|
|
212
|
-
| `Ctrl+Shift+G` | Ungroup selected group |
|
|
213
|
-
| `Shift+Click` | Add/remove node to/from selection |
|
|
214
|
-
| `Shift` (during resize) | Lock aspect ratio |
|
|
215
|
-
|
|
216
|
-
#### History (HistoryPlugin)
|
|
217
|
-
|
|
218
|
-
| Shortcut | Action |
|
|
219
|
-
| -------------- | ------ |
|
|
220
|
-
| `Ctrl+Z` | Undo |
|
|
221
|
-
| `Ctrl+Shift+Z` | Redo |
|
|
222
|
-
|
|
223
|
-
#### Camera Controls (CameraHotkeysPlugin)
|
|
224
|
-
|
|
225
|
-
| Shortcut | Action |
|
|
226
|
-
| ------------------- | ----------- |
|
|
227
|
-
| `Ctrl+Wheel` | Zoom in/out |
|
|
228
|
-
| `+` / `=` | Zoom in |
|
|
229
|
-
| `-` | Zoom out |
|
|
230
|
-
| `Arrow Keys` | Pan camera |
|
|
231
|
-
| `Middle Mouse+Drag` | Pan camera |
|
|
232
|
-
| `Right Mouse+Drag` | Pan camera |
|
|
233
|
-
|
|
234
|
-
### Ruler Controls (RulerManagerPlugin)
|
|
235
|
-
|
|
236
|
-
| Shortcut | Action |
|
|
237
|
-
| ---------------------- | ------------------------ |
|
|
238
|
-
| `Shift+R` | Toggle rulers visibility |
|
|
239
|
-
| `Delete` / `Backspace` | Delete active guide |
|
|
240
|
-
| Drag from ruler | Create guide line |
|
|
241
|
-
|
|
242
|
-
---
|
|
243
|
-
|
|
244
|
-
## 📚 Usage Examples
|
|
245
|
-
|
|
246
|
-
### Creating Shapes
|
|
247
|
-
|
|
248
|
-
```typescript
|
|
249
|
-
// Rectangle with rounded corners
|
|
250
|
-
const rect = engine.nodes.addShape({
|
|
251
|
-
x: 50,
|
|
252
|
-
y: 50,
|
|
253
|
-
width: 200,
|
|
254
|
-
height: 100,
|
|
255
|
-
fill: '#10b981',
|
|
256
|
-
cornerRadius: 12,
|
|
257
|
-
});
|
|
258
|
-
|
|
259
|
-
// Circle
|
|
260
|
-
const circle = engine.nodes.addCircle({
|
|
261
|
-
x: 300,
|
|
262
|
-
y: 100,
|
|
263
|
-
radius: 50,
|
|
264
|
-
fill: '#f59e0b',
|
|
265
|
-
stroke: '#d97706',
|
|
266
|
-
strokeWidth: 3,
|
|
267
|
-
});
|
|
268
|
-
|
|
269
|
-
// Text
|
|
270
|
-
const text = engine.nodes.addText({
|
|
271
|
-
x: 400,
|
|
272
|
-
y: 50,
|
|
273
|
-
text: 'Flowscape UI',
|
|
274
|
-
fontSize: 32,
|
|
275
|
-
fontFamily: 'Inter',
|
|
276
|
-
fill: '#1f2937',
|
|
277
|
-
});
|
|
278
|
-
|
|
279
|
-
// Image
|
|
280
|
-
const image = engine.nodes.addImage({
|
|
281
|
-
x: 100,
|
|
282
|
-
y: 200,
|
|
283
|
-
width: 200,
|
|
284
|
-
height: 150,
|
|
285
|
-
src: '/path/to/image.jpg',
|
|
286
|
-
});
|
|
287
|
-
```
|
|
288
|
-
|
|
289
|
-
### Working with Events
|
|
290
|
-
|
|
291
|
-
```typescript
|
|
292
|
-
// Subscribe to events
|
|
293
|
-
engine.eventBus.on('node:created', (node) => {
|
|
294
|
-
console.log('Node created:', node);
|
|
295
|
-
});
|
|
296
|
-
|
|
297
|
-
engine.eventBus.on('node:selected', (node) => {
|
|
298
|
-
console.log('Node selected:', node);
|
|
299
|
-
});
|
|
300
|
-
|
|
301
|
-
engine.eventBus.on('camera:zoom', ({ scale }) => {
|
|
302
|
-
console.log('Zoom changed:', scale);
|
|
303
|
-
});
|
|
304
|
-
|
|
305
|
-
// Unsubscribe
|
|
306
|
-
const handler = (node) => console.log(node);
|
|
307
|
-
engine.eventBus.on('node:created', handler);
|
|
308
|
-
engine.eventBus.off('node:created', handler);
|
|
309
|
-
```
|
|
310
|
-
|
|
311
|
-
### Grouping and Management
|
|
312
|
-
|
|
313
|
-
```typescript
|
|
314
|
-
// Create group
|
|
315
|
-
const group = engine.nodes.addGroup({ x: 0, y: 0 });
|
|
316
|
-
|
|
317
|
-
// Add nodes to group
|
|
318
|
-
const rect1 = engine.nodes.addShape({ x: 10, y: 10, width: 50, height: 50 });
|
|
319
|
-
const rect2 = engine.nodes.addShape({ x: 70, y: 10, width: 50, height: 50 });
|
|
320
|
-
|
|
321
|
-
rect1.getNode().moveTo(group.getNode());
|
|
322
|
-
rect2.getNode().moveTo(group.getNode());
|
|
323
|
-
|
|
324
|
-
// Manage z-index
|
|
325
|
-
rect1.getNode().moveUp(); // Move up one level
|
|
326
|
-
rect2.getNode().moveDown(); // Move down one level
|
|
327
|
-
rect1.getNode().moveToTop(); // Move to top
|
|
328
|
-
```
|
|
329
|
-
|
|
330
|
-
### Camera and Navigation
|
|
331
|
-
|
|
332
|
-
```typescript
|
|
333
|
-
// Programmatic zoom
|
|
334
|
-
engine.camera.zoomIn(); // Zoom in
|
|
335
|
-
engine.camera.zoomOut(); // Zoom out
|
|
336
|
-
engine.camera.setZoom(1.5); // Set specific scale
|
|
337
|
-
|
|
338
|
-
// Panning
|
|
339
|
-
engine.camera.pan(100, 50); // Pan by dx, dy
|
|
340
|
-
|
|
341
|
-
// Center on node
|
|
342
|
-
const node = engine.nodes.addShape({ x: 500, y: 500, width: 100, height: 100 });
|
|
343
|
-
engine.camera.centerOn(node);
|
|
344
|
-
|
|
345
|
-
// Reset camera
|
|
346
|
-
engine.camera.reset();
|
|
347
|
-
```
|
|
348
|
-
|
|
349
|
-
---
|
|
350
|
-
|
|
351
|
-
## 🔧 Development
|
|
352
|
-
|
|
353
|
-
```bash
|
|
354
|
-
# Install dependencies
|
|
355
|
-
bun install
|
|
356
|
-
|
|
357
|
-
# Run playground
|
|
358
|
-
bun run dev
|
|
359
|
-
|
|
360
|
-
# Build library
|
|
361
|
-
bun run build
|
|
362
|
-
|
|
363
|
-
# Tests
|
|
364
|
-
bun run test # Watch mode
|
|
365
|
-
bun run test:run # Single run
|
|
366
|
-
bun run test:coverage # With coverage
|
|
367
|
-
|
|
368
|
-
# Linting
|
|
369
|
-
bun run lint # ESLint
|
|
370
|
-
bun run lint:ts # TypeScript check
|
|
371
|
-
bun run lint:fix # Auto-fix
|
|
372
|
-
```
|
|
373
|
-
|
|
374
|
-
## 📄 License
|
|
375
|
-
|
|
376
|
-
MIT © Flowscape UI Team
|
|
377
|
-
|
|
378
|
-
---
|
|
379
|
-
|
|
380
|
-
<div align="center">
|
|
381
|
-
|
|
382
|
-
⭐ [Star on GitHub](https://github.com/Flowscape-UI/core-sdk) • 🐛 [Report Bug](https://github.com/Flowscape-UI/core-sdk/issues) • 💡 [Request Feature](https://github.com/Flowscape-UI/core-sdk/issues)
|
|
383
|
-
|
|
384
|
-
</div>
|
|
1
|
+
<div align="center">
|
|
2
|
+
|
|
3
|
+
# 🎨 @flowscape-ui/core-sdk
|
|
4
|
+
|
|
5
|
+
**A scene-based 2D engine for building interactive editor products on infinite canvas**
|
|
6
|
+
|
|
7
|
+
[](https://www.npmjs.com/package/@flowscape-ui/core-sdk)
|
|
8
|
+
[](https://opensource.org/licenses/MIT)
|
|
9
|
+
[](https://bundlephobia.com/package/@flowscape-ui/core-sdk)
|
|
10
|
+
[](https://x.com/FlowscapeUI)
|
|
11
|
+
|
|
12
|
+
[](https://flowscape-ui.github.io/core-sdk/)
|
|
13
|
+
[](https://flowscape-ui.github.io/core-sdk/?path=/story/interactive-playground--interactive-playground)
|
|
14
|
+
[](./CHANGELOG.md)
|
|
15
|
+
|
|
16
|
+
<img
|
|
17
|
+
src="./assets/readme/preview.gif"
|
|
18
|
+
alt="Flowscape Canvas Demo"
|
|
19
|
+
width="900"
|
|
20
|
+
/>
|
|
21
|
+
|
|
22
|
+
</div>
|
|
23
|
+
|
|
24
|
+
---
|
|
25
|
+
|
|
26
|
+
## What is Flowscape?
|
|
27
|
+
|
|
28
|
+
Flowscape is a 2D engine for building products like whiteboards, visual builders, diagram tools, and design editors.
|
|
29
|
+
It is not a UI framework and not a template SDK.
|
|
30
|
+
It gives you a structured scene, nodes, camera, and rendering pipeline so you can build your own editor architecture.
|
|
31
|
+
|
|
32
|
+
## Why use it?
|
|
33
|
+
|
|
34
|
+
- Scene architecture with 4 layers: `Background`, `World`, `Overlay`, `UI`
|
|
35
|
+
- Node-based model with transforms, hierarchy, bounds (`OBB`, `AABB`), hit testing
|
|
36
|
+
- Built-in pan/zoom input controllers for editor-like interactions
|
|
37
|
+
- TypeScript-first API
|
|
38
|
+
- Renderer architecture that can evolve without rewriting product logic
|
|
39
|
+
- Works in browser apps and can be used inside desktop/mobile stacks via web technologies
|
|
40
|
+
|
|
41
|
+
## 📦 Installation
|
|
42
|
+
|
|
43
|
+
```bash
|
|
44
|
+
npm install @flowscape-ui/core-sdk
|
|
45
|
+
# or
|
|
46
|
+
pnpm add @flowscape-ui/core-sdk
|
|
47
|
+
# or
|
|
48
|
+
yarn add @flowscape-ui/core-sdk
|
|
49
|
+
# or
|
|
50
|
+
bun add @flowscape-ui/core-sdk
|
|
51
|
+
```
|
|
52
|
+
|
|
53
|
+
## 🚀 Quick Start
|
|
54
|
+
|
|
55
|
+
```ts
|
|
56
|
+
import {
|
|
57
|
+
Scene,
|
|
58
|
+
NodeRect,
|
|
59
|
+
RendererLayerBackgroundCanvas,
|
|
60
|
+
RendererLayerWorldCanvas,
|
|
61
|
+
CanvasRendererHost,
|
|
62
|
+
LayerWorldInputController,
|
|
63
|
+
} from '@flowscape-ui/core-sdk';
|
|
64
|
+
|
|
65
|
+
const container = document.getElementById('app');
|
|
66
|
+
if (!container) throw new Error('Container #app not found');
|
|
67
|
+
|
|
68
|
+
const scene = new Scene(container.clientWidth, container.clientHeight);
|
|
69
|
+
|
|
70
|
+
// Background layer
|
|
71
|
+
const bgRenderer = new RendererLayerBackgroundCanvas();
|
|
72
|
+
scene.layerManager.add(scene.layerBackground, bgRenderer, scene.layerBackground);
|
|
73
|
+
scene.layerBackground.setFill('#101010');
|
|
74
|
+
|
|
75
|
+
// World layer
|
|
76
|
+
const worldRenderer = new RendererLayerWorldCanvas();
|
|
77
|
+
scene.layerManager.add(scene.layerWorld, worldRenderer, scene.layerWorld);
|
|
78
|
+
|
|
79
|
+
// Render host
|
|
80
|
+
const host = new CanvasRendererHost(container, -1);
|
|
81
|
+
scene.hostManager.add(host);
|
|
82
|
+
|
|
83
|
+
// Input controller (pan/zoom)
|
|
84
|
+
scene.inputManager.add(scene.layerWorld, new LayerWorldInputController(), {
|
|
85
|
+
stage: host.getRenderNode(),
|
|
86
|
+
world: scene.layerWorld,
|
|
87
|
+
options: {
|
|
88
|
+
enabled: true,
|
|
89
|
+
panMode: 'right',
|
|
90
|
+
zoomEnabled: true,
|
|
91
|
+
zoomFactor: 1.08,
|
|
92
|
+
preventWheelDefault: false,
|
|
93
|
+
keyboardPanSpeed: 900,
|
|
94
|
+
keyboardPanShiftMultiplier: 1.5,
|
|
95
|
+
},
|
|
96
|
+
emitChange: () => scene.invalidate(),
|
|
97
|
+
});
|
|
98
|
+
|
|
99
|
+
// Add a node
|
|
100
|
+
const rect = new NodeRect(1);
|
|
101
|
+
rect.setPosition(300, 220);
|
|
102
|
+
rect.setSize(220, 140);
|
|
103
|
+
rect.setFill('#2f7cf6');
|
|
104
|
+
scene.layerWorld.addNode(rect);
|
|
105
|
+
|
|
106
|
+
scene.invalidate();
|
|
107
|
+
```
|
|
108
|
+
|
|
109
|
+
## 🔒 Public API Policy
|
|
110
|
+
|
|
111
|
+
- Import only from `@flowscape-ui/core-sdk`
|
|
112
|
+
- Do not import internals from `src/...`
|
|
113
|
+
- Internal files can change between releases
|
|
114
|
+
|
|
115
|
+
## 📚 Links
|
|
116
|
+
|
|
117
|
+
- Documentation: https://flowscape-ui.github.io/core-sdk/
|
|
118
|
+
- Interactive demo: https://flowscape-ui.github.io/core-sdk/?path=/story/interactive-playground--interactive-playground
|
|
119
|
+
- GitHub Issues: https://github.com/Flowscape-UI/core-sdk/issues
|
|
120
|
+
- Changelog: `./CHANGELOG.md`
|
|
121
|
+
|
|
122
|
+
## 📄 License
|
|
123
|
+
|
|
124
|
+
MIT © Flowscape UI Team
|