@canvas-tile-engine/react 0.0.4 → 0.2.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/dist/index.d.mts +143 -68
- package/dist/index.d.ts +143 -68
- package/dist/index.js +1 -1
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +1 -1
- package/dist/index.mjs.map +1 -1
- package/package.json +3 -3
package/dist/index.d.mts
CHANGED
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
|
-
import {
|
|
3
|
-
export { CanvasTileEngineConfig, CanvasTileEngine as CanvasTileEngineCore, Circle, Coords, DrawObject, EventHandlers, ImageItem, Line, Path, Rect, Text, onClickCallback, onDrawCallback, onHoverCallback, onMouseDownCallback, onMouseLeaveCallback, onMouseUpCallback } from '@canvas-tile-engine/core';
|
|
2
|
+
import { Rect, Circle, ImageItem, Line, Text, Path, Coords, CanvasTileEngineConfig, CanvasTileEngine as CanvasTileEngine$1, EventHandlers, LayerHandle, onClickCallback, onRightClickCallback, onHoverCallback, onMouseDownCallback, onMouseUpCallback, onMouseLeaveCallback, onDrawCallback, onZoomCallback } from '@canvas-tile-engine/core';
|
|
3
|
+
export { CanvasTileEngineConfig, CanvasTileEngine as CanvasTileEngineCore, Circle, Coords, DrawObject, EventHandlers, ImageItem, Line, Path, Rect, Text, gridToSize, onClickCallback, onDrawCallback, onHoverCallback, onMouseDownCallback, onMouseLeaveCallback, onMouseUpCallback } from '@canvas-tile-engine/core';
|
|
4
4
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
5
5
|
|
|
6
6
|
interface RectProps {
|
|
7
|
-
items:
|
|
7
|
+
items: Rect | Rect[];
|
|
8
8
|
layer?: number;
|
|
9
9
|
}
|
|
10
10
|
|
|
11
11
|
interface CircleProps {
|
|
12
|
-
items:
|
|
12
|
+
items: Circle | Circle[];
|
|
13
13
|
layer?: number;
|
|
14
14
|
}
|
|
15
15
|
|
|
@@ -26,13 +26,7 @@ interface GridLinesProps {
|
|
|
26
26
|
}
|
|
27
27
|
|
|
28
28
|
interface LineProps {
|
|
29
|
-
items:
|
|
30
|
-
from: Coords;
|
|
31
|
-
to: Coords;
|
|
32
|
-
} | {
|
|
33
|
-
from: Coords;
|
|
34
|
-
to: Coords;
|
|
35
|
-
}[];
|
|
29
|
+
items: Line | Line[];
|
|
36
30
|
style?: {
|
|
37
31
|
strokeStyle?: string;
|
|
38
32
|
lineWidth?: number;
|
|
@@ -41,24 +35,12 @@ interface LineProps {
|
|
|
41
35
|
}
|
|
42
36
|
|
|
43
37
|
interface TextProps {
|
|
44
|
-
items:
|
|
45
|
-
coords: Coords;
|
|
46
|
-
text: string;
|
|
47
|
-
} | {
|
|
48
|
-
coords: Coords;
|
|
49
|
-
text: string;
|
|
50
|
-
}[];
|
|
51
|
-
style?: {
|
|
52
|
-
fillStyle?: string;
|
|
53
|
-
font?: string;
|
|
54
|
-
textAlign?: CanvasTextAlign;
|
|
55
|
-
textBaseline?: CanvasTextBaseline;
|
|
56
|
-
};
|
|
38
|
+
items: Text | Text[];
|
|
57
39
|
layer?: number;
|
|
58
40
|
}
|
|
59
41
|
|
|
60
42
|
interface PathProps {
|
|
61
|
-
items:
|
|
43
|
+
items: Path | Path[];
|
|
62
44
|
style?: {
|
|
63
45
|
strokeStyle?: string;
|
|
64
46
|
lineWidth?: number;
|
|
@@ -67,13 +49,13 @@ interface PathProps {
|
|
|
67
49
|
}
|
|
68
50
|
|
|
69
51
|
interface StaticRectProps {
|
|
70
|
-
items:
|
|
52
|
+
items: Rect[];
|
|
71
53
|
cacheKey: string;
|
|
72
54
|
layer?: number;
|
|
73
55
|
}
|
|
74
56
|
|
|
75
57
|
interface StaticCircleProps {
|
|
76
|
-
items:
|
|
58
|
+
items: Circle[];
|
|
77
59
|
cacheKey: string;
|
|
78
60
|
layer?: number;
|
|
79
61
|
}
|
|
@@ -126,6 +108,8 @@ interface EngineHandle {
|
|
|
126
108
|
};
|
|
127
109
|
/** Get current canvas scale */
|
|
128
110
|
getScale(): number;
|
|
111
|
+
/** Set the canvas scale directly, clamped to min/max bounds. */
|
|
112
|
+
setScale(newScale: number): void;
|
|
129
113
|
/** Zoom in by a factor (default: 1.5) */
|
|
130
114
|
zoomIn(factor?: number): void;
|
|
131
115
|
/** Zoom out by a factor (default: 1.5) */
|
|
@@ -142,52 +126,29 @@ interface EngineHandle {
|
|
|
142
126
|
/** Dynamically update event handlers at runtime */
|
|
143
127
|
setEventHandlers(handlers: Partial<EventHandlers>): void;
|
|
144
128
|
/** Draw rectangles */
|
|
145
|
-
drawRect(items:
|
|
129
|
+
drawRect(items: Rect | Rect[], layer?: number): LayerHandle;
|
|
146
130
|
/** Draw static rectangles (cached) */
|
|
147
|
-
drawStaticRect(items:
|
|
131
|
+
drawStaticRect(items: Rect[], cacheKey: string, layer?: number): LayerHandle;
|
|
148
132
|
/** Draw circles */
|
|
149
|
-
drawCircle(items:
|
|
133
|
+
drawCircle(items: Circle | Circle[], layer?: number): LayerHandle;
|
|
150
134
|
/** Draw static circles (cached) */
|
|
151
|
-
drawStaticCircle(items:
|
|
135
|
+
drawStaticCircle(items: Circle[], cacheKey: string, layer?: number): LayerHandle;
|
|
152
136
|
/** Draw lines */
|
|
153
|
-
drawLine(items: {
|
|
154
|
-
from: Coords;
|
|
155
|
-
to: Coords;
|
|
156
|
-
} | {
|
|
157
|
-
from: Coords;
|
|
158
|
-
to: Coords;
|
|
159
|
-
}[], style?: {
|
|
137
|
+
drawLine(items: Line | Line[], style?: {
|
|
160
138
|
strokeStyle?: string;
|
|
161
139
|
lineWidth?: number;
|
|
162
140
|
}, layer?: number): LayerHandle;
|
|
163
141
|
/** Draw text */
|
|
164
|
-
drawText(items:
|
|
165
|
-
coords: Coords;
|
|
166
|
-
text: string;
|
|
167
|
-
} | {
|
|
168
|
-
coords: Coords;
|
|
169
|
-
text: string;
|
|
170
|
-
}[], style?: {
|
|
171
|
-
fillStyle?: string;
|
|
172
|
-
font?: string;
|
|
173
|
-
textAlign?: CanvasTextAlign;
|
|
174
|
-
textBaseline?: CanvasTextBaseline;
|
|
175
|
-
}, layer?: number): LayerHandle;
|
|
142
|
+
drawText(items: Text | Text[], layer?: number): LayerHandle;
|
|
176
143
|
/** Draw paths/polylines */
|
|
177
144
|
drawPath(items: Coords[] | Coords[][], style?: {
|
|
178
145
|
strokeStyle?: string;
|
|
179
146
|
lineWidth?: number;
|
|
180
147
|
}, layer?: number): LayerHandle;
|
|
181
148
|
/** Draw images */
|
|
182
|
-
drawImage(items:
|
|
183
|
-
img: HTMLImageElement;
|
|
184
|
-
}) | (Omit<DrawObject, "style"> & {
|
|
185
|
-
img: HTMLImageElement;
|
|
186
|
-
})[], layer?: number): LayerHandle;
|
|
149
|
+
drawImage(items: ImageItem | ImageItem[], layer?: number): LayerHandle;
|
|
187
150
|
/** Draw static images (cached) */
|
|
188
|
-
drawStaticImage(items:
|
|
189
|
-
img: HTMLImageElement;
|
|
190
|
-
})[], cacheKey: string, layer?: number): LayerHandle;
|
|
151
|
+
drawStaticImage(items: ImageItem[], cacheKey: string, layer?: number): LayerHandle;
|
|
191
152
|
/** Draw grid lines */
|
|
192
153
|
drawGridLines(cellSize: number, lineWidth?: number, strokeStyle?: string, layer?: number): LayerHandle;
|
|
193
154
|
/** Add custom draw function */
|
|
@@ -202,6 +163,17 @@ interface EngineHandle {
|
|
|
202
163
|
removeLayerHandle(handle: LayerHandle): void;
|
|
203
164
|
/** Image loader instance (undefined until engine mounts) */
|
|
204
165
|
readonly images: CanvasTileEngine$1["images"] | undefined;
|
|
166
|
+
/**
|
|
167
|
+
* Load an image using the engine's image loader.
|
|
168
|
+
* Returns a rejected promise if engine is not ready.
|
|
169
|
+
* @param src - Image URL to load
|
|
170
|
+
* @param retry - Number of retries on failure (default: 1)
|
|
171
|
+
* @example
|
|
172
|
+
* ```tsx
|
|
173
|
+
* const img = await engine.loadImage("/sprites/player.png");
|
|
174
|
+
* ```
|
|
175
|
+
*/
|
|
176
|
+
loadImage(src: string, retry?: number): Promise<HTMLImageElement>;
|
|
205
177
|
}
|
|
206
178
|
/**
|
|
207
179
|
* React hook that creates an engine handle for use with CanvasTileEngine component.
|
|
@@ -249,25 +221,128 @@ interface CanvasTileEngineProps {
|
|
|
249
221
|
style?: React.CSSProperties;
|
|
250
222
|
/** Draw components (Rect, Circle, Image, GridLines, etc.) */
|
|
251
223
|
children?: React.ReactNode;
|
|
252
|
-
/**
|
|
224
|
+
/**
|
|
225
|
+
* Callback when center coordinates change (pan or zoom).
|
|
226
|
+
* @param coords - Center world coordinates: `{ x, y }`
|
|
227
|
+
* @example
|
|
228
|
+
* ```tsx
|
|
229
|
+
* onCoordsChange={(coords) => {
|
|
230
|
+
* console.log(`Center: ${coords.x}, ${coords.y}`);
|
|
231
|
+
* }}
|
|
232
|
+
* ```
|
|
233
|
+
*/
|
|
253
234
|
onCoordsChange?: (coords: Coords) => void;
|
|
254
|
-
/**
|
|
235
|
+
/**
|
|
236
|
+
* Callback when a tile is clicked (mouse or touch tap).
|
|
237
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
238
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
239
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
240
|
+
* @example
|
|
241
|
+
* ```tsx
|
|
242
|
+
* onClick={(coords) => {
|
|
243
|
+
* console.log(`Clicked tile: ${coords.snapped.x}, ${coords.snapped.y}`);
|
|
244
|
+
* }}
|
|
245
|
+
* ```
|
|
246
|
+
*/
|
|
255
247
|
onClick?: onClickCallback;
|
|
256
|
-
/**
|
|
248
|
+
/**
|
|
249
|
+
* Callback when a tile is right-clicked.
|
|
250
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
251
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
252
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
253
|
+
* @example
|
|
254
|
+
* ```tsx
|
|
255
|
+
* onRightClick={(coords) => {
|
|
256
|
+
* showContextMenu(coords.snapped.x, coords.snapped.y);
|
|
257
|
+
* }}
|
|
258
|
+
* ```
|
|
259
|
+
*/
|
|
257
260
|
onRightClick?: onRightClickCallback;
|
|
258
|
-
/**
|
|
261
|
+
/**
|
|
262
|
+
* Callback when hovering over tiles.
|
|
263
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
264
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
265
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
266
|
+
* @example
|
|
267
|
+
* ```tsx
|
|
268
|
+
* onHover={(coords) => {
|
|
269
|
+
* setHoveredTile({ x: coords.snapped.x, y: coords.snapped.y });
|
|
270
|
+
* }}
|
|
271
|
+
* ```
|
|
272
|
+
*/
|
|
259
273
|
onHover?: onHoverCallback;
|
|
260
|
-
/**
|
|
274
|
+
/**
|
|
275
|
+
* Callback on mouse/touch down.
|
|
276
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
277
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
278
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
279
|
+
* @example
|
|
280
|
+
* ```tsx
|
|
281
|
+
* onMouseDown={(coords) => {
|
|
282
|
+
* startPainting(coords.snapped.x, coords.snapped.y);
|
|
283
|
+
* }}
|
|
284
|
+
* ```
|
|
285
|
+
*/
|
|
261
286
|
onMouseDown?: onMouseDownCallback;
|
|
262
|
-
/**
|
|
287
|
+
/**
|
|
288
|
+
* Callback on mouse/touch up.
|
|
289
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
290
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
291
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
292
|
+
* @example
|
|
293
|
+
* ```tsx
|
|
294
|
+
* onMouseUp={() => {
|
|
295
|
+
* stopPainting();
|
|
296
|
+
* }}
|
|
297
|
+
* ```
|
|
298
|
+
*/
|
|
263
299
|
onMouseUp?: onMouseUpCallback;
|
|
264
|
-
/**
|
|
300
|
+
/**
|
|
301
|
+
* Callback when mouse/touch leaves the canvas.
|
|
302
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
303
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
304
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
305
|
+
* @example
|
|
306
|
+
* ```tsx
|
|
307
|
+
* onMouseLeave={() => {
|
|
308
|
+
* clearHoveredTile();
|
|
309
|
+
* }}
|
|
310
|
+
* ```
|
|
311
|
+
*/
|
|
265
312
|
onMouseLeave?: onMouseLeaveCallback;
|
|
266
|
-
/**
|
|
313
|
+
/**
|
|
314
|
+
* Callback after each draw frame. Use for custom canvas drawing.
|
|
315
|
+
* @param ctx - The canvas 2D rendering context
|
|
316
|
+
* @param info - Frame info: `scale`, `width`, `height`, `coords` (center)
|
|
317
|
+
* @example
|
|
318
|
+
* ```tsx
|
|
319
|
+
* onDraw={(ctx, info) => {
|
|
320
|
+
* ctx.fillStyle = "red";
|
|
321
|
+
* ctx.fillText(`Scale: ${info.scale}`, 10, 20);
|
|
322
|
+
* }}
|
|
323
|
+
* ```
|
|
324
|
+
*/
|
|
267
325
|
onDraw?: onDrawCallback;
|
|
268
|
-
/**
|
|
326
|
+
/**
|
|
327
|
+
* Callback on canvas resize.
|
|
328
|
+
* @example
|
|
329
|
+
* ```tsx
|
|
330
|
+
* onResize={() => {
|
|
331
|
+
* console.log("Canvas resized");
|
|
332
|
+
* }}
|
|
333
|
+
* ```
|
|
334
|
+
*/
|
|
269
335
|
onResize?: () => void;
|
|
270
|
-
/**
|
|
336
|
+
/**
|
|
337
|
+
* Callback when zoom level changes (wheel or pinch).
|
|
338
|
+
* @param scale - The new scale value
|
|
339
|
+
* @example
|
|
340
|
+
* ```tsx
|
|
341
|
+
* onZoom={(scale) => {
|
|
342
|
+
* console.log(`Zoom level: ${scale}`);
|
|
343
|
+
* }}
|
|
344
|
+
* ```
|
|
345
|
+
*/
|
|
271
346
|
onZoom?: onZoomCallback;
|
|
272
347
|
}
|
|
273
348
|
|
package/dist/index.d.ts
CHANGED
|
@@ -1,15 +1,15 @@
|
|
|
1
1
|
import * as react from 'react';
|
|
2
|
-
import {
|
|
3
|
-
export { CanvasTileEngineConfig, CanvasTileEngine as CanvasTileEngineCore, Circle, Coords, DrawObject, EventHandlers, ImageItem, Line, Path, Rect, Text, onClickCallback, onDrawCallback, onHoverCallback, onMouseDownCallback, onMouseLeaveCallback, onMouseUpCallback } from '@canvas-tile-engine/core';
|
|
2
|
+
import { Rect, Circle, ImageItem, Line, Text, Path, Coords, CanvasTileEngineConfig, CanvasTileEngine as CanvasTileEngine$1, EventHandlers, LayerHandle, onClickCallback, onRightClickCallback, onHoverCallback, onMouseDownCallback, onMouseUpCallback, onMouseLeaveCallback, onDrawCallback, onZoomCallback } from '@canvas-tile-engine/core';
|
|
3
|
+
export { CanvasTileEngineConfig, CanvasTileEngine as CanvasTileEngineCore, Circle, Coords, DrawObject, EventHandlers, ImageItem, Line, Path, Rect, Text, gridToSize, onClickCallback, onDrawCallback, onHoverCallback, onMouseDownCallback, onMouseLeaveCallback, onMouseUpCallback } from '@canvas-tile-engine/core';
|
|
4
4
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
5
5
|
|
|
6
6
|
interface RectProps {
|
|
7
|
-
items:
|
|
7
|
+
items: Rect | Rect[];
|
|
8
8
|
layer?: number;
|
|
9
9
|
}
|
|
10
10
|
|
|
11
11
|
interface CircleProps {
|
|
12
|
-
items:
|
|
12
|
+
items: Circle | Circle[];
|
|
13
13
|
layer?: number;
|
|
14
14
|
}
|
|
15
15
|
|
|
@@ -26,13 +26,7 @@ interface GridLinesProps {
|
|
|
26
26
|
}
|
|
27
27
|
|
|
28
28
|
interface LineProps {
|
|
29
|
-
items:
|
|
30
|
-
from: Coords;
|
|
31
|
-
to: Coords;
|
|
32
|
-
} | {
|
|
33
|
-
from: Coords;
|
|
34
|
-
to: Coords;
|
|
35
|
-
}[];
|
|
29
|
+
items: Line | Line[];
|
|
36
30
|
style?: {
|
|
37
31
|
strokeStyle?: string;
|
|
38
32
|
lineWidth?: number;
|
|
@@ -41,24 +35,12 @@ interface LineProps {
|
|
|
41
35
|
}
|
|
42
36
|
|
|
43
37
|
interface TextProps {
|
|
44
|
-
items:
|
|
45
|
-
coords: Coords;
|
|
46
|
-
text: string;
|
|
47
|
-
} | {
|
|
48
|
-
coords: Coords;
|
|
49
|
-
text: string;
|
|
50
|
-
}[];
|
|
51
|
-
style?: {
|
|
52
|
-
fillStyle?: string;
|
|
53
|
-
font?: string;
|
|
54
|
-
textAlign?: CanvasTextAlign;
|
|
55
|
-
textBaseline?: CanvasTextBaseline;
|
|
56
|
-
};
|
|
38
|
+
items: Text | Text[];
|
|
57
39
|
layer?: number;
|
|
58
40
|
}
|
|
59
41
|
|
|
60
42
|
interface PathProps {
|
|
61
|
-
items:
|
|
43
|
+
items: Path | Path[];
|
|
62
44
|
style?: {
|
|
63
45
|
strokeStyle?: string;
|
|
64
46
|
lineWidth?: number;
|
|
@@ -67,13 +49,13 @@ interface PathProps {
|
|
|
67
49
|
}
|
|
68
50
|
|
|
69
51
|
interface StaticRectProps {
|
|
70
|
-
items:
|
|
52
|
+
items: Rect[];
|
|
71
53
|
cacheKey: string;
|
|
72
54
|
layer?: number;
|
|
73
55
|
}
|
|
74
56
|
|
|
75
57
|
interface StaticCircleProps {
|
|
76
|
-
items:
|
|
58
|
+
items: Circle[];
|
|
77
59
|
cacheKey: string;
|
|
78
60
|
layer?: number;
|
|
79
61
|
}
|
|
@@ -126,6 +108,8 @@ interface EngineHandle {
|
|
|
126
108
|
};
|
|
127
109
|
/** Get current canvas scale */
|
|
128
110
|
getScale(): number;
|
|
111
|
+
/** Set the canvas scale directly, clamped to min/max bounds. */
|
|
112
|
+
setScale(newScale: number): void;
|
|
129
113
|
/** Zoom in by a factor (default: 1.5) */
|
|
130
114
|
zoomIn(factor?: number): void;
|
|
131
115
|
/** Zoom out by a factor (default: 1.5) */
|
|
@@ -142,52 +126,29 @@ interface EngineHandle {
|
|
|
142
126
|
/** Dynamically update event handlers at runtime */
|
|
143
127
|
setEventHandlers(handlers: Partial<EventHandlers>): void;
|
|
144
128
|
/** Draw rectangles */
|
|
145
|
-
drawRect(items:
|
|
129
|
+
drawRect(items: Rect | Rect[], layer?: number): LayerHandle;
|
|
146
130
|
/** Draw static rectangles (cached) */
|
|
147
|
-
drawStaticRect(items:
|
|
131
|
+
drawStaticRect(items: Rect[], cacheKey: string, layer?: number): LayerHandle;
|
|
148
132
|
/** Draw circles */
|
|
149
|
-
drawCircle(items:
|
|
133
|
+
drawCircle(items: Circle | Circle[], layer?: number): LayerHandle;
|
|
150
134
|
/** Draw static circles (cached) */
|
|
151
|
-
drawStaticCircle(items:
|
|
135
|
+
drawStaticCircle(items: Circle[], cacheKey: string, layer?: number): LayerHandle;
|
|
152
136
|
/** Draw lines */
|
|
153
|
-
drawLine(items: {
|
|
154
|
-
from: Coords;
|
|
155
|
-
to: Coords;
|
|
156
|
-
} | {
|
|
157
|
-
from: Coords;
|
|
158
|
-
to: Coords;
|
|
159
|
-
}[], style?: {
|
|
137
|
+
drawLine(items: Line | Line[], style?: {
|
|
160
138
|
strokeStyle?: string;
|
|
161
139
|
lineWidth?: number;
|
|
162
140
|
}, layer?: number): LayerHandle;
|
|
163
141
|
/** Draw text */
|
|
164
|
-
drawText(items:
|
|
165
|
-
coords: Coords;
|
|
166
|
-
text: string;
|
|
167
|
-
} | {
|
|
168
|
-
coords: Coords;
|
|
169
|
-
text: string;
|
|
170
|
-
}[], style?: {
|
|
171
|
-
fillStyle?: string;
|
|
172
|
-
font?: string;
|
|
173
|
-
textAlign?: CanvasTextAlign;
|
|
174
|
-
textBaseline?: CanvasTextBaseline;
|
|
175
|
-
}, layer?: number): LayerHandle;
|
|
142
|
+
drawText(items: Text | Text[], layer?: number): LayerHandle;
|
|
176
143
|
/** Draw paths/polylines */
|
|
177
144
|
drawPath(items: Coords[] | Coords[][], style?: {
|
|
178
145
|
strokeStyle?: string;
|
|
179
146
|
lineWidth?: number;
|
|
180
147
|
}, layer?: number): LayerHandle;
|
|
181
148
|
/** Draw images */
|
|
182
|
-
drawImage(items:
|
|
183
|
-
img: HTMLImageElement;
|
|
184
|
-
}) | (Omit<DrawObject, "style"> & {
|
|
185
|
-
img: HTMLImageElement;
|
|
186
|
-
})[], layer?: number): LayerHandle;
|
|
149
|
+
drawImage(items: ImageItem | ImageItem[], layer?: number): LayerHandle;
|
|
187
150
|
/** Draw static images (cached) */
|
|
188
|
-
drawStaticImage(items:
|
|
189
|
-
img: HTMLImageElement;
|
|
190
|
-
})[], cacheKey: string, layer?: number): LayerHandle;
|
|
151
|
+
drawStaticImage(items: ImageItem[], cacheKey: string, layer?: number): LayerHandle;
|
|
191
152
|
/** Draw grid lines */
|
|
192
153
|
drawGridLines(cellSize: number, lineWidth?: number, strokeStyle?: string, layer?: number): LayerHandle;
|
|
193
154
|
/** Add custom draw function */
|
|
@@ -202,6 +163,17 @@ interface EngineHandle {
|
|
|
202
163
|
removeLayerHandle(handle: LayerHandle): void;
|
|
203
164
|
/** Image loader instance (undefined until engine mounts) */
|
|
204
165
|
readonly images: CanvasTileEngine$1["images"] | undefined;
|
|
166
|
+
/**
|
|
167
|
+
* Load an image using the engine's image loader.
|
|
168
|
+
* Returns a rejected promise if engine is not ready.
|
|
169
|
+
* @param src - Image URL to load
|
|
170
|
+
* @param retry - Number of retries on failure (default: 1)
|
|
171
|
+
* @example
|
|
172
|
+
* ```tsx
|
|
173
|
+
* const img = await engine.loadImage("/sprites/player.png");
|
|
174
|
+
* ```
|
|
175
|
+
*/
|
|
176
|
+
loadImage(src: string, retry?: number): Promise<HTMLImageElement>;
|
|
205
177
|
}
|
|
206
178
|
/**
|
|
207
179
|
* React hook that creates an engine handle for use with CanvasTileEngine component.
|
|
@@ -249,25 +221,128 @@ interface CanvasTileEngineProps {
|
|
|
249
221
|
style?: React.CSSProperties;
|
|
250
222
|
/** Draw components (Rect, Circle, Image, GridLines, etc.) */
|
|
251
223
|
children?: React.ReactNode;
|
|
252
|
-
/**
|
|
224
|
+
/**
|
|
225
|
+
* Callback when center coordinates change (pan or zoom).
|
|
226
|
+
* @param coords - Center world coordinates: `{ x, y }`
|
|
227
|
+
* @example
|
|
228
|
+
* ```tsx
|
|
229
|
+
* onCoordsChange={(coords) => {
|
|
230
|
+
* console.log(`Center: ${coords.x}, ${coords.y}`);
|
|
231
|
+
* }}
|
|
232
|
+
* ```
|
|
233
|
+
*/
|
|
253
234
|
onCoordsChange?: (coords: Coords) => void;
|
|
254
|
-
/**
|
|
235
|
+
/**
|
|
236
|
+
* Callback when a tile is clicked (mouse or touch tap).
|
|
237
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
238
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
239
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
240
|
+
* @example
|
|
241
|
+
* ```tsx
|
|
242
|
+
* onClick={(coords) => {
|
|
243
|
+
* console.log(`Clicked tile: ${coords.snapped.x}, ${coords.snapped.y}`);
|
|
244
|
+
* }}
|
|
245
|
+
* ```
|
|
246
|
+
*/
|
|
255
247
|
onClick?: onClickCallback;
|
|
256
|
-
/**
|
|
248
|
+
/**
|
|
249
|
+
* Callback when a tile is right-clicked.
|
|
250
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
251
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
252
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
253
|
+
* @example
|
|
254
|
+
* ```tsx
|
|
255
|
+
* onRightClick={(coords) => {
|
|
256
|
+
* showContextMenu(coords.snapped.x, coords.snapped.y);
|
|
257
|
+
* }}
|
|
258
|
+
* ```
|
|
259
|
+
*/
|
|
257
260
|
onRightClick?: onRightClickCallback;
|
|
258
|
-
/**
|
|
261
|
+
/**
|
|
262
|
+
* Callback when hovering over tiles.
|
|
263
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
264
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
265
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
266
|
+
* @example
|
|
267
|
+
* ```tsx
|
|
268
|
+
* onHover={(coords) => {
|
|
269
|
+
* setHoveredTile({ x: coords.snapped.x, y: coords.snapped.y });
|
|
270
|
+
* }}
|
|
271
|
+
* ```
|
|
272
|
+
*/
|
|
259
273
|
onHover?: onHoverCallback;
|
|
260
|
-
/**
|
|
274
|
+
/**
|
|
275
|
+
* Callback on mouse/touch down.
|
|
276
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
277
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
278
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
279
|
+
* @example
|
|
280
|
+
* ```tsx
|
|
281
|
+
* onMouseDown={(coords) => {
|
|
282
|
+
* startPainting(coords.snapped.x, coords.snapped.y);
|
|
283
|
+
* }}
|
|
284
|
+
* ```
|
|
285
|
+
*/
|
|
261
286
|
onMouseDown?: onMouseDownCallback;
|
|
262
|
-
/**
|
|
287
|
+
/**
|
|
288
|
+
* Callback on mouse/touch up.
|
|
289
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
290
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
291
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
292
|
+
* @example
|
|
293
|
+
* ```tsx
|
|
294
|
+
* onMouseUp={() => {
|
|
295
|
+
* stopPainting();
|
|
296
|
+
* }}
|
|
297
|
+
* ```
|
|
298
|
+
*/
|
|
263
299
|
onMouseUp?: onMouseUpCallback;
|
|
264
|
-
/**
|
|
300
|
+
/**
|
|
301
|
+
* Callback when mouse/touch leaves the canvas.
|
|
302
|
+
* @param coords - World coordinates: `raw` (exact), `snapped` (floored to tile)
|
|
303
|
+
* @param mouse - Canvas-relative position: `raw` (exact), `snapped` (tile-aligned)
|
|
304
|
+
* @param client - Viewport position: `raw` (exact), `snapped` (tile-aligned)
|
|
305
|
+
* @example
|
|
306
|
+
* ```tsx
|
|
307
|
+
* onMouseLeave={() => {
|
|
308
|
+
* clearHoveredTile();
|
|
309
|
+
* }}
|
|
310
|
+
* ```
|
|
311
|
+
*/
|
|
265
312
|
onMouseLeave?: onMouseLeaveCallback;
|
|
266
|
-
/**
|
|
313
|
+
/**
|
|
314
|
+
* Callback after each draw frame. Use for custom canvas drawing.
|
|
315
|
+
* @param ctx - The canvas 2D rendering context
|
|
316
|
+
* @param info - Frame info: `scale`, `width`, `height`, `coords` (center)
|
|
317
|
+
* @example
|
|
318
|
+
* ```tsx
|
|
319
|
+
* onDraw={(ctx, info) => {
|
|
320
|
+
* ctx.fillStyle = "red";
|
|
321
|
+
* ctx.fillText(`Scale: ${info.scale}`, 10, 20);
|
|
322
|
+
* }}
|
|
323
|
+
* ```
|
|
324
|
+
*/
|
|
267
325
|
onDraw?: onDrawCallback;
|
|
268
|
-
/**
|
|
326
|
+
/**
|
|
327
|
+
* Callback on canvas resize.
|
|
328
|
+
* @example
|
|
329
|
+
* ```tsx
|
|
330
|
+
* onResize={() => {
|
|
331
|
+
* console.log("Canvas resized");
|
|
332
|
+
* }}
|
|
333
|
+
* ```
|
|
334
|
+
*/
|
|
269
335
|
onResize?: () => void;
|
|
270
|
-
/**
|
|
336
|
+
/**
|
|
337
|
+
* Callback when zoom level changes (wheel or pinch).
|
|
338
|
+
* @param scale - The new scale value
|
|
339
|
+
* @example
|
|
340
|
+
* ```tsx
|
|
341
|
+
* onZoom={(scale) => {
|
|
342
|
+
* console.log(`Zoom level: ${scale}`);
|
|
343
|
+
* }}
|
|
344
|
+
* ```
|
|
345
|
+
*/
|
|
271
346
|
onZoom?: onZoomCallback;
|
|
272
347
|
}
|
|
273
348
|
|
package/dist/index.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
"use strict";var
|
|
1
|
+
"use strict";var z=Object.defineProperty;var te=Object.getOwnPropertyDescriptor;var oe=Object.getOwnPropertyNames;var ie=Object.prototype.hasOwnProperty;var ae=(r,o)=>{for(var t in o)z(r,t,{get:o[t],enumerable:!0})},se=(r,o,t,i)=>{if(o&&typeof o=="object"||typeof o=="function")for(let n of oe(o))!ie.call(r,n)&&n!==t&&z(r,n,{get:()=>o[n],enumerable:!(i=te(o,n))||i.enumerable});return r};var ce=r=>se(z({},"__esModule",{value:!0}),r);var me={};ae(me,{CanvasTileEngine:()=>q,CanvasTileEngineCore:()=>D.CanvasTileEngine,gridToSize:()=>D.gridToSize,useCanvasTileEngine:()=>F,useEngineContext:()=>c});module.exports=ce(me);var f=require("react"),re=require("@canvas-tile-engine/core");var T=require("react"),L=(0,T.createContext)(null);function c(){let r=(0,T.useContext)(L);if(!r)throw new Error("useEngineContext must be used within a CanvasTileEngine component");return r}var w=require("react");var B=(0,w.memo)(function({items:o,layer:t=1}){let{engine:i,requestRender:n}=c();return(0,w.useEffect)(()=>{let s=i.drawRect(o,t);return n(),()=>{s&&i.removeLayerHandle(s)}},[i,o,t,n]),null});var P=require("react");var O=(0,P.memo)(function({items:o,layer:t=1}){let{engine:i,requestRender:n}=c();return(0,P.useEffect)(()=>{let s=i.drawCircle(o,t);return n(),()=>{s&&i.removeLayerHandle(s)}},[i,o,t,n]),null});var h=require("react");var U=(0,h.memo)(function({items:o,layer:t=1}){let{engine:i,requestRender:n}=c();return(0,h.useEffect)(()=>{let s=i.drawImage(o,t);return n(),()=>{s&&i.removeLayerHandle(s)}},[i,o,t,n]),null});var S=require("react");var j=(0,S.memo)(function({cellSize:o,lineWidth:t=1,strokeStyle:i="black",layer:n=0}){let{engine:s,requestRender:e}=c();return(0,S.useEffect)(()=>{let a=s.drawGridLines(o,t,i,n);return e(),()=>{a&&s.removeLayerHandle(a)}},[s,o,t,i,n,e]),null});var I=require("react");var N=(0,I.memo)(function({items:o,style:t,layer:i=1}){let{engine:n,requestRender:s}=c();return(0,I.useEffect)(()=>{let e=n.drawLine(o,t,i);return s(),()=>{e&&n.removeLayerHandle(e)}},[n,o,t,i,s]),null});var H=require("react");var Z=(0,H.memo)(function({items:o,layer:t=2}){let{engine:i,requestRender:n}=c();return(0,H.useEffect)(()=>{let s=i.drawText(o,t);return n(),()=>{s&&i.removeLayerHandle(s)}},[i,o,t,n]),null});var k=require("react");var J=(0,k.memo)(function({items:o,style:t,layer:i=1}){let{engine:n,requestRender:s}=c();return(0,k.useEffect)(()=>{let e=n.drawPath(o,t,i);return s(),()=>{e&&n.removeLayerHandle(e)}},[n,o,t,i,s]),null});var y=require("react");var Q=(0,y.memo)(function({items:o,cacheKey:t,layer:i=1}){let{engine:n,requestRender:s}=c(),e=(0,y.useRef)(t);return(0,y.useEffect)(()=>{if(o.length===0)return;e.current!==t&&(n.clearStaticCache(e.current),e.current=t);let a=n.drawStaticRect(o,t,i);return s(),()=>{a&&n.removeLayerHandle(a)}},[n,o,t,i,s]),(0,y.useEffect)(()=>()=>{n.clearStaticCache(t)},[n,t]),null});var x=require("react");var $=(0,x.memo)(function({items:o,cacheKey:t,layer:i=1}){let{engine:n,requestRender:s}=c(),e=(0,x.useRef)(t);return(0,x.useEffect)(()=>{if(o.length===0)return;e.current!==t&&(n.clearStaticCache(e.current),e.current=t);let a=n.drawStaticCircle(o,t,i);return s(),()=>{a&&n.removeLayerHandle(a)}},[n,o,t,i,s]),(0,x.useEffect)(()=>()=>{n.clearStaticCache(t)},[n,t]),null});var v=require("react");var K=(0,v.memo)(function({items:o,cacheKey:t,layer:i=1}){let{engine:n,requestRender:s}=c(),e=(0,v.useRef)(t);return(0,v.useEffect)(()=>{if(o.length===0)return;e.current!==t&&(n.clearStaticCache(e.current),e.current=t);let a=n.drawStaticImage(o,t,i);return s(),()=>{a&&n.removeLayerHandle(a)}},[n,o,t,i,s]),(0,v.useEffect)(()=>()=>{n.clearStaticCache(t)},[n,t]),null});var b=require("react");var ee=(0,b.memo)(function({children:o,layer:t=1}){let{engine:i,requestRender:n}=c(),s=(0,b.useRef)(o);return(0,b.useEffect)(()=>{s.current=o}),(0,b.useEffect)(()=>{let e=i.addDrawFunction((a,u,g)=>{s.current(a,u,g)},t);return n(),()=>{e&&i.removeLayerHandle(e)}},[i,t,n]),null});var R=require("react/jsx-runtime");function ue({engine:r,config:o,center:t={x:0,y:0},className:i,style:n,children:s,onCoordsChange:e,onClick:a,onRightClick:u,onHover:g,onMouseDown:M,onMouseUp:G,onMouseLeave:V,onDraw:_,onResize:Y,onZoom:A}){let d=(0,f.useRef)({onCoordsChange:e,onClick:a,onRightClick:u,onHover:g,onMouseDown:M,onMouseUp:G,onMouseLeave:V,onDraw:_,onResize:Y,onZoom:A});(0,f.useEffect)(()=>{d.current={onCoordsChange:e,onClick:a,onRightClick:u,onHover:g,onMouseDown:M,onMouseUp:G,onMouseLeave:V,onDraw:_,onResize:Y,onZoom:A}});let E=(0,f.useRef)(null),W=(0,f.useCallback)(()=>{E.current===null&&(E.current=requestAnimationFrame(()=>{E.current=null,r.render()}))},[r]);(0,f.useEffect)(()=>()=>{E.current!==null&&cancelAnimationFrame(E.current)},[]);let ne=(0,f.useMemo)(()=>({engine:r,requestRender:W}),[r,W]);return(0,f.useEffect)(()=>{let X=r._containerRef.current;if(!X)return;let m=new re.CanvasTileEngine(X,o,t);return m.onCoordsChange=l=>d.current.onCoordsChange?.(l),m.onClick=(...l)=>d.current.onClick?.(...l),m.onRightClick=(...l)=>d.current.onRightClick?.(...l),m.onHover=(...l)=>d.current.onHover?.(...l),m.onMouseDown=(...l)=>d.current.onMouseDown?.(...l),m.onMouseUp=(...l)=>d.current.onMouseUp?.(...l),m.onMouseLeave=(...l)=>d.current.onMouseLeave?.(...l),m.onDraw=(...l)=>d.current.onDraw?.(...l),m.onResize=()=>d.current.onResize?.(),m.onZoom=l=>d.current.onZoom?.(l),r._setInstance(m),m.render(),()=>{m.destroy(),r._setInstance(null)}},[r]),(0,R.jsxs)(L.Provider,{value:ne,children:[(0,R.jsx)("div",{ref:r._containerRef,className:i,style:{...n},children:(0,R.jsx)("canvas",{})}),r.isReady&&s]})}var q=Object.assign(ue,{Rect:B,Circle:O,Image:U,GridLines:j,Line:N,Text:Z,Path:J,StaticRect:Q,StaticCircle:$,StaticImage:K,DrawFunction:ee});var C=require("react"),p={layer:-1,id:Symbol("dummy")},le={size:{width:0,height:0,minWidth:100,minHeight:100,maxWidth:1/0,maxHeight:1/0},responsive:!1,scale:1,minScale:.5,maxScale:2,backgroundColor:"#ffffff",gridAligned:!1,renderer:"canvas",eventHandlers:{drag:!0,zoom:!0,hover:!1,click:!1,rightClick:!1,resize:!1},bounds:{minX:-1/0,maxX:1/0,minY:-1/0,maxY:1/0},coordinates:{enabled:!1,shownScaleRange:{min:0,max:1/0}},cursor:{default:"default",move:"move"},debug:{enabled:!1,hud:{enabled:!1,topLeftCoordinates:!1,coordinates:!1,scale:!1,tilesInView:!1,fps:!1},eventHandlers:{click:!1,hover:!1,drag:!1,zoom:!1,resize:!1}}};function F(){let r=(0,C.useRef)(null),o=(0,C.useRef)(null),[,t]=(0,C.useState)(!1),i=(0,C.useRef)(!1),n=(0,C.useCallback)(e=>{r.current=e,i.current=e!==null,t(e!==null)},[]);return(0,C.useMemo)(()=>({_containerRef:o,_setInstance:n,get isReady(){return i.current},get instance(){return r.current},get images(){return r.current?.images},render(){r.current?.render()},getCenterCoords(){return r.current?.getCenterCoords()??{x:0,y:0}},getVisibleBounds(){return r.current?.getVisibleBounds()??{minX:0,maxX:0,minY:0,maxY:0}},updateCoords(e){r.current?.updateCoords(e)},goCoords(e,a,u,g){r.current?.goCoords(e,a,u,g)},resize(e,a,u,g){r.current?.resize(e,a,u,g)},getSize(){return r.current?.getSize()??{width:0,height:0}},getScale(){return r.current?.getScale()??1},setScale(e){r.current?.setScale(e)},zoomIn(e){r.current?.zoomIn(e)},zoomOut(e){r.current?.zoomOut(e)},getConfig(){return r.current?.getConfig()??le},setBounds(e){r.current?.setBounds(e)},setEventHandlers(e){r.current?.setEventHandlers(e)},drawRect(e,a){return r.current?.drawRect(e,a)??p},drawStaticRect(e,a,u){return r.current?.drawStaticRect(e,a,u)??p},drawCircle(e,a){return r.current?.drawCircle(e,a)??p},drawStaticCircle(e,a,u){return r.current?.drawStaticCircle(e,a,u)??p},drawLine(e,a,u){return r.current?.drawLine(e,a,u)??p},drawText(e,a){return r.current?.drawText(e,a)??p},drawPath(e,a,u){return r.current?.drawPath(e,a,u)??p},drawImage(e,a){return r.current?.drawImage(e,a)??p},drawStaticImage(e,a,u){return r.current?.drawStaticImage(e,a,u)??p},drawGridLines(e,a,u,g){return r.current?.drawGridLines(e,a,u,g)??p},addDrawFunction(e,a){return r.current?.addDrawFunction(e,a)??p},clearLayer(e){r.current?.clearLayer(e)},clearAll(){r.current?.clearAll()},clearStaticCache(e){r.current?.clearStaticCache(e)},removeLayerHandle(e){r.current?.removeLayerHandle(e)},loadImage(e,a){return r.current?r.current.images.load(e,a):Promise.reject(new Error("Engine not ready. Wait for isReady before loading images."))}}),[n])}var D=require("@canvas-tile-engine/core");0&&(module.exports={CanvasTileEngine,CanvasTileEngineCore,gridToSize,useCanvasTileEngine,useEngineContext});
|
|
2
2
|
//# sourceMappingURL=index.js.map
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/index.ts","../src/components/CanvasTileEngine.tsx","../src/context/EngineContext.tsx","../src/components/draw/Rect.tsx","../src/components/draw/Circle.tsx","../src/components/draw/Image.tsx","../src/components/draw/GridLines.tsx","../src/components/draw/Line.tsx","../src/components/draw/Text.tsx","../src/components/draw/Path.tsx","../src/components/draw/StaticRect.tsx","../src/components/draw/StaticCircle.tsx","../src/components/draw/StaticImage.tsx","../src/components/draw/DrawFunction.tsx","../src/hooks/useCanvasTileEngine.ts"],"sourcesContent":["// Main component\nexport { CanvasTileEngine } from \"./components\";\n\n// Draw components\nexport {\n type RectProps,\n type CircleProps,\n type ImageProps,\n type GridLinesProps,\n type LineProps,\n type TextProps,\n type PathProps,\n type StaticRectProps,\n type StaticCircleProps,\n type StaticImageProps,\n type DrawFunctionProps,\n} from \"./components\";\n\n// Hooks\nexport { useCanvasTileEngine } from \"./hooks\";\n\n// Context\nexport { useEngineContext, type EngineContextValue } from \"./context\";\n\n// Types\nexport type {\n CanvasTileEngineProps,\n CanvasTileEngineConfig,\n Coords,\n DrawObject,\n EventHandlers,\n onClickCallback,\n onHoverCallback,\n onMouseDownCallback,\n onMouseUpCallback,\n onMouseLeaveCallback,\n onDrawCallback,\n Rect,\n Line,\n Circle,\n Text,\n Path,\n ImageItem,\n} from \"./types\";\nexport type { EngineHandle } from \"./hooks/useCanvasTileEngine\";\n\n// Re-export core class with different name\nexport { CanvasTileEngine as CanvasTileEngineCore } from \"@canvas-tile-engine/core\";\n","import { useEffect, useRef, useCallback, useMemo } from \"react\";\nimport { CanvasTileEngine as CanvasTileEngineCore } from \"@canvas-tile-engine/core\";\nimport { EngineContext, type EngineContextValue } from \"../context/EngineContext\";\nimport type { CanvasTileEngineProps } from \"../types\";\n\n// Import draw components for compound pattern\nimport { Rect } from \"./draw/Rect\";\nimport { Circle } from \"./draw/Circle\";\nimport { Image } from \"./draw/Image\";\nimport { GridLines } from \"./draw/GridLines\";\nimport { Line } from \"./draw/Line\";\nimport { Text } from \"./draw/Text\";\nimport { Path } from \"./draw/Path\";\nimport { StaticRect } from \"./draw/StaticRect\";\nimport { StaticCircle } from \"./draw/StaticCircle\";\nimport { StaticImage } from \"./draw/StaticImage\";\nimport { DrawFunction } from \"./draw/DrawFunction\";\n\n/**\n * React component that renders a CanvasTileEngine.\n * Supports both imperative API (via engine handle) and declarative API (via children).\n *\n * @example Declarative API with compound components\n * ```tsx\n * function App() {\n * const engine = useCanvasTileEngine();\n *\n * return (\n * <CanvasTileEngine engine={engine} config={config}>\n * <CanvasTileEngine.GridLines cellSize={50} layer={0} />\n * <CanvasTileEngine.Image items={imageItems} layer={1} />\n * <CanvasTileEngine.Circle items={markers} layer={2} />\n * </CanvasTileEngine>\n * );\n * }\n * ```\n *\n * @example Imperative API\n * ```tsx\n * function App() {\n * const engine = useCanvasTileEngine();\n *\n * useEffect(() => {\n * if (engine.isReady) {\n * engine.drawGridLines(50);\n * engine.render();\n * }\n * }, [engine.isReady]);\n *\n * return <CanvasTileEngine engine={engine} config={config} />;\n * }\n * ```\n */\nfunction CanvasTileEngineBase({\n engine,\n config,\n center = { x: 0, y: 0 },\n className,\n style,\n children,\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n}: CanvasTileEngineProps) {\n // Stable callback refs\n const callbacksRef = useRef({\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n });\n\n // Update callback refs\n useEffect(() => {\n callbacksRef.current = {\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n };\n });\n\n // Debounced render - multiple draw components calling requestRender\n // in the same frame will trigger only one render\n const rafIdRef = useRef<number | null>(null);\n const requestRender = useCallback(() => {\n if (rafIdRef.current !== null) return;\n rafIdRef.current = requestAnimationFrame(() => {\n rafIdRef.current = null;\n engine.render();\n });\n }, [engine]);\n\n // Cleanup RAF on unmount\n useEffect(() => {\n return () => {\n if (rafIdRef.current !== null) {\n cancelAnimationFrame(rafIdRef.current);\n }\n };\n }, []);\n\n // Context value\n const contextValue = useMemo<EngineContextValue>(\n () => ({\n engine,\n requestRender,\n }),\n [engine, requestRender]\n );\n\n // Initialize engine when component mounts\n // Note: config and center are intentionally not in deps - we only want to create the engine once\n // Callbacks are accessed via callbacksRef which is always up-to-date\n useEffect(() => {\n const container = engine._containerRef.current;\n\n if (!container) {\n return;\n }\n\n // Create engine instance\n const instance = new CanvasTileEngineCore(container, config, center);\n\n // Set up callbacks using stable refs\n instance.onCoordsChange = (coords) => callbacksRef.current.onCoordsChange?.(coords);\n instance.onClick = (...args) => callbacksRef.current.onClick?.(...args);\n instance.onRightClick = (...args) => callbacksRef.current.onRightClick?.(...args);\n instance.onHover = (...args) => callbacksRef.current.onHover?.(...args);\n instance.onMouseDown = (...args) => callbacksRef.current.onMouseDown?.(...args);\n instance.onMouseUp = (...args) => callbacksRef.current.onMouseUp?.(...args);\n instance.onMouseLeave = (...args) => callbacksRef.current.onMouseLeave?.(...args);\n instance.onDraw = (...args) => callbacksRef.current.onDraw?.(...args);\n instance.onResize = () => callbacksRef.current.onResize?.();\n instance.onZoom = (scale) => callbacksRef.current.onZoom?.(scale);\n\n // Attach to handle\n engine._setInstance(instance);\n\n // Initial render\n instance.render();\n\n // Cleanup on unmount\n return () => {\n instance.destroy();\n engine._setInstance(null);\n };\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [engine]);\n\n return (\n <EngineContext.Provider value={contextValue}>\n <div\n ref={engine._containerRef}\n className={className}\n style={{\n ...style,\n }}\n >\n <canvas />\n </div>\n {/* Render children only when engine is ready */}\n {engine.isReady && children}\n </EngineContext.Provider>\n );\n}\n\n// Compound component pattern - attach draw components as static properties\nexport const CanvasTileEngine = Object.assign(CanvasTileEngineBase, {\n Rect,\n Circle,\n Image,\n GridLines,\n Line,\n Text,\n Path,\n StaticRect,\n StaticCircle,\n StaticImage,\n DrawFunction,\n});\n","import { createContext, useContext } from \"react\";\nimport type { EngineHandle } from \"../hooks/useCanvasTileEngine\";\n\nexport interface EngineContextValue {\n engine: EngineHandle;\n /** Request a re-render of the canvas */\n requestRender: () => void;\n}\n\nexport const EngineContext = createContext<EngineContextValue | null>(null);\n\n/**\n * Hook to access the engine context from child components.\n * Must be used within a CanvasTileEngine component.\n */\nexport function useEngineContext(): EngineContextValue {\n const context = useContext(EngineContext);\n\n if (!context) {\n throw new Error(\"useEngineContext must be used within a CanvasTileEngine component\");\n }\n\n return context;\n}\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { DrawObject } from \"@canvas-tile-engine/core\";\n\nexport interface RectProps {\n items: DrawObject | DrawObject[];\n layer?: number;\n}\n\n/**\n * Draws rectangles on the canvas.\n */\nexport const Rect = memo(function Rect({ items, layer = 1 }: RectProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawRect(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { DrawObject } from \"@canvas-tile-engine/core\";\n\nexport interface CircleProps {\n items: DrawObject | DrawObject[];\n layer?: number;\n}\n\n/**\n * Draws circles on the canvas.\n */\nexport const Circle = memo(function Circle({ items, layer = 1 }: CircleProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawCircle(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport { ImageItem } from \"@canvas-tile-engine/core\";\n\nexport interface ImageProps {\n items: ImageItem | ImageItem[];\n layer?: number;\n}\n\n/**\n * Draws images on the canvas.\n */\nexport const Image = memo(function Image({ items, layer = 1 }: ImageProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawImage(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\n\nexport interface GridLinesProps {\n cellSize: number;\n lineWidth?: number;\n strokeStyle?: string;\n layer?: number;\n}\n\n/**\n * Draws grid lines on the canvas.\n * Multiple GridLines can share the same layer (additive drawing).\n */\nexport const GridLines = memo(function GridLines({ cellSize, lineWidth = 1, strokeStyle = \"black\", layer = 0 }: GridLinesProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawGridLines(cellSize, lineWidth, strokeStyle, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, cellSize, lineWidth, strokeStyle, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Coords } from \"@canvas-tile-engine/core\";\n\nexport interface LineProps {\n items: { from: Coords; to: Coords } | { from: Coords; to: Coords }[];\n style?: { strokeStyle?: string; lineWidth?: number };\n layer?: number;\n}\n\n/**\n * Draws lines on the canvas.\n */\nexport const Line = memo(function Line({ items, style, layer = 1 }: LineProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawLine(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Coords } from \"@canvas-tile-engine/core\";\n\nexport interface TextProps {\n items: { coords: Coords; text: string } | { coords: Coords; text: string }[];\n style?: {\n fillStyle?: string;\n font?: string;\n textAlign?: CanvasTextAlign;\n textBaseline?: CanvasTextBaseline;\n };\n layer?: number;\n}\n\n/**\n * Draws text on the canvas.\n */\nexport const Text = memo(function Text({ items, style, layer = 2 }: TextProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawText(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Coords } from \"@canvas-tile-engine/core\";\n\nexport interface PathProps {\n items: Coords[] | Coords[][];\n style?: { strokeStyle?: string; lineWidth?: number };\n layer?: number;\n}\n\n/**\n * Draws paths/polylines on the canvas.\n */\nexport const Path = memo(function Path({ items, style, layer = 1 }: PathProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawPath(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { DrawObject } from \"@canvas-tile-engine/core\";\n\nexport interface StaticRectProps {\n items: DrawObject[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static rectangles with caching for performance.\n * Ideal for large datasets that don't change frequently.\n */\nexport const StaticRect = memo(function StaticRect({ items, cacheKey, layer = 1 }: StaticRectProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n // Clear previous cache if cacheKey changed\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticRect(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n // Cleanup cache on unmount\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { DrawObject } from \"@canvas-tile-engine/core\";\n\nexport interface StaticCircleProps {\n items: DrawObject[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static circles with caching for performance.\n */\nexport const StaticCircle = memo(function StaticCircle({ items, cacheKey, layer = 1 }: StaticCircleProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticCircle(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport { ImageItem } from \"@canvas-tile-engine/core\";\n\nexport interface StaticImageProps {\n items: ImageItem[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static images with caching for performance.\n * Ideal for terrain tiles or static decorations.\n */\nexport const StaticImage = memo(function StaticImage({ items, cacheKey, layer = 1 }: StaticImageProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticImage(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { CanvasTileEngineConfig, Coords } from \"@canvas-tile-engine/core\";\n\nexport interface DrawFunctionProps {\n /** The draw function to execute */\n children: (ctx: CanvasRenderingContext2D, coords: Coords, config: Required<CanvasTileEngineConfig>) => void;\n layer?: number;\n}\n\n/**\n * Custom draw function component.\n * Allows arbitrary canvas drawing within the engine's render cycle.\n * Multiple DrawFunction components can share the same layer (additive drawing).\n *\n * @example\n * ```tsx\n * <DrawFunction layer={3}>\n * {(ctx, coords, config) => {\n * ctx.fillStyle = \"red\";\n * ctx.fillRect(config.size.width / 2 - 5, config.size.height / 2 - 5, 10, 10);\n * }}\n * </DrawFunction>\n * ```\n */\nexport const DrawFunction = memo(function DrawFunction({ children, layer = 1 }: DrawFunctionProps) {\n const { engine, requestRender } = useEngineContext();\n const fnRef = useRef(children);\n\n // Keep function ref updated\n useEffect(() => {\n fnRef.current = children;\n });\n\n useEffect(() => {\n const handle = engine.addDrawFunction((ctx, coords, config) => {\n fnRef.current(ctx, coords, config);\n }, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, layer, requestRender]);\n\n return null;\n});\n","import { useRef, useCallback, useState, useMemo } from \"react\";\nimport type {\n CanvasTileEngine as CanvasTileEngineCore,\n CanvasTileEngineConfig,\n Coords,\n DrawObject,\n EventHandlers,\n LayerHandle,\n} from \"@canvas-tile-engine/core\";\n\n/** Dummy handle returned when engine is not ready */\nconst DUMMY_LAYER_HANDLE: LayerHandle = { layer: -1, id: Symbol(\"dummy\") };\n\n/** Default config when engine is not ready */\nconst DEFAULT_CONFIG: Required<CanvasTileEngineConfig> = {\n size: { width: 0, height: 0, minWidth: 100, minHeight: 100, maxWidth: Infinity, maxHeight: Infinity },\n scale: 1,\n minScale: 0.5,\n maxScale: 2,\n backgroundColor: \"#ffffff\",\n gridAligned: false,\n renderer: \"canvas\",\n eventHandlers: {\n drag: true,\n zoom: true,\n hover: false,\n click: false,\n rightClick: false,\n resize: false,\n },\n bounds: {\n minX: -Infinity,\n maxX: Infinity,\n minY: -Infinity,\n maxY: Infinity,\n },\n coordinates: {\n enabled: false,\n shownScaleRange: { min: 0, max: Infinity },\n },\n cursor: {\n default: \"default\",\n move: \"move\",\n },\n debug: {\n enabled: false,\n hud: {\n enabled: false,\n topLeftCoordinates: false,\n coordinates: false,\n scale: false,\n tilesInView: false,\n fps: false,\n },\n eventHandlers: {\n click: false,\n hover: false,\n drag: false,\n zoom: false,\n resize: false,\n },\n },\n};\n\n/**\n * Engine handle returned by useCanvasTileEngine hook.\n * Provides access to engine methods with proper typing.\n * \n * All methods return default/dummy values when engine is not ready,\n * allowing safe usage without null checks.\n */\nexport interface EngineHandle {\n /** @internal - Used by CanvasTileEngine component */\n readonly _containerRef: React.RefObject<HTMLDivElement>;\n /** @internal - Used by CanvasTileEngine component */\n _setInstance: (engine: CanvasTileEngineCore | null) => void;\n\n /** Whether the engine is ready (mounted and initialized) */\n readonly isReady: boolean;\n\n /** The underlying engine instance (null until component mounts) */\n readonly instance: CanvasTileEngineCore | null;\n\n /** Render a frame */\n render(): void;\n\n /** Get current center coordinates */\n getCenterCoords(): Coords;\n\n /** Get visible world coordinate bounds of the viewport */\n getVisibleBounds(): { minX: number; maxX: number; minY: number; maxY: number };\n\n /** Update center coordinates */\n updateCoords(center: Coords): void;\n\n /** Animate to target coordinates */\n goCoords(x: number, y: number, durationMs?: number, onComplete?: () => void): void;\n\n /** Resize the canvas */\n resize(width: number, height: number, durationMs?: number, onComplete?: () => void): void;\n\n /** Get current canvas size */\n getSize(): { width: number; height: number };\n\n /** Get current canvas scale */\n getScale(): number;\n\n /** Zoom in by a factor (default: 1.5) */\n zoomIn(factor?: number): void;\n\n /** Zoom out by a factor (default: 1.5) */\n zoomOut(factor?: number): void;\n\n /** Get current config */\n getConfig(): Required<CanvasTileEngineConfig>;\n\n /** Set map boundaries */\n setBounds(bounds: { minX: number; maxX: number; minY: number; maxY: number }): void;\n\n /** Dynamically update event handlers at runtime */\n setEventHandlers(handlers: Partial<EventHandlers>): void;\n\n /** Draw rectangles */\n drawRect(items: DrawObject | DrawObject[], layer?: number): LayerHandle;\n\n /** Draw static rectangles (cached) */\n drawStaticRect(items: DrawObject[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw circles */\n drawCircle(items: DrawObject | DrawObject[], layer?: number): LayerHandle;\n\n /** Draw static circles (cached) */\n drawStaticCircle(items: DrawObject[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw lines */\n drawLine(\n items: { from: Coords; to: Coords } | { from: Coords; to: Coords }[],\n style?: { strokeStyle?: string; lineWidth?: number },\n layer?: number\n ): LayerHandle;\n\n /** Draw text */\n drawText(\n items: { coords: Coords; text: string } | { coords: Coords; text: string }[],\n style?: { fillStyle?: string; font?: string; textAlign?: CanvasTextAlign; textBaseline?: CanvasTextBaseline },\n layer?: number\n ): LayerHandle;\n\n /** Draw paths/polylines */\n drawPath(\n items: Coords[] | Coords[][],\n style?: { strokeStyle?: string; lineWidth?: number },\n layer?: number\n ): LayerHandle;\n\n /** Draw images */\n drawImage(\n items:\n | (Omit<DrawObject, \"style\"> & { img: HTMLImageElement })\n | (Omit<DrawObject, \"style\"> & { img: HTMLImageElement })[],\n layer?: number\n ): LayerHandle;\n\n /** Draw static images (cached) */\n drawStaticImage(\n items: (Omit<DrawObject, \"style\"> & { img: HTMLImageElement })[],\n cacheKey: string,\n layer?: number\n ): LayerHandle;\n\n /** Draw grid lines */\n drawGridLines(cellSize: number, lineWidth?: number, strokeStyle?: string, layer?: number): LayerHandle;\n\n /** Add custom draw function */\n addDrawFunction(\n fn: (ctx: CanvasRenderingContext2D, coords: Coords, config: Required<CanvasTileEngineConfig>) => void,\n layer?: number\n ): LayerHandle;\n\n /** Clear a specific layer */\n clearLayer(layer: number): void;\n\n /** Clear all layers */\n clearAll(): void;\n\n /** Clear static cache */\n clearStaticCache(cacheKey?: string): void;\n\n /** Remove a previously registered draw callback */\n removeLayerHandle(handle: LayerHandle): void;\n\n /** Image loader instance (undefined until engine mounts) */\n readonly images: CanvasTileEngineCore[\"images\"] | undefined;\n}\n\n/**\n * React hook that creates an engine handle for use with CanvasTileEngine component.\n *\n * @returns Engine handle to pass to CanvasTileEngine component\n *\n * @example\n * ```tsx\n * function App() {\n * const mainMap = useCanvasTileEngine();\n * const miniMap = useCanvasTileEngine();\n *\n * useEffect(() => {\n * if (mainMap.isReady && miniMap.isReady) {\n * // Both engines are ready, draw items\n * mainMap.drawGridLines(50);\n * mainMap.render();\n * }\n * }, [mainMap.isReady, miniMap.isReady]);\n *\n * return (\n * <>\n * <CanvasTileEngine engine={mainMap} config={...} />\n * <CanvasTileEngine engine={miniMap} config={...} />\n * </>\n * );\n * }\n * ```\n */\nexport function useCanvasTileEngine(): EngineHandle {\n const instanceRef = useRef<CanvasTileEngineCore | null>(null);\n const containerRef = useRef<HTMLDivElement>(null!);\n // _isReady state is only used to trigger re-renders, actual value is read from isReadyRef\n const [, setIsReady] = useState(false);\n // Keep isReady in a ref so the handle getter can read it without recreating handle\n const isReadyRef = useRef(false);\n\n const setInstance = useCallback((engine: CanvasTileEngineCore | null) => {\n instanceRef.current = engine;\n isReadyRef.current = engine !== null;\n setIsReady(engine !== null);\n }, []);\n\n // Create stable handle object using useMemo\n // Note: isReady is NOT in deps - we read from isReadyRef to keep handle stable\n const handle = useMemo<EngineHandle>(\n () => ({\n _containerRef: containerRef,\n _setInstance: setInstance,\n\n get isReady() {\n return isReadyRef.current;\n },\n\n get instance() {\n return instanceRef.current;\n },\n\n get images() {\n return instanceRef.current?.images;\n },\n\n render() {\n instanceRef.current?.render();\n },\n\n getCenterCoords() {\n return instanceRef.current?.getCenterCoords() ?? { x: 0, y: 0 };\n },\n\n getVisibleBounds() {\n return instanceRef.current?.getVisibleBounds() ?? { minX: 0, maxX: 0, minY: 0, maxY: 0 };\n },\n\n updateCoords(center: Coords) {\n instanceRef.current?.updateCoords(center);\n },\n\n goCoords(x: number, y: number, durationMs?: number, onComplete?: () => void) {\n instanceRef.current?.goCoords(x, y, durationMs, onComplete);\n },\n\n resize(width: number, height: number, durationMs?: number, onComplete?: () => void) {\n instanceRef.current?.resize(width, height, durationMs, onComplete);\n },\n\n getSize() {\n return instanceRef.current?.getSize() ?? { width: 0, height: 0 };\n },\n\n getScale() {\n return instanceRef.current?.getScale() ?? 1;\n },\n\n zoomIn(factor?: number) {\n instanceRef.current?.zoomIn(factor);\n },\n\n zoomOut(factor?: number) {\n instanceRef.current?.zoomOut(factor);\n },\n\n getConfig() {\n return instanceRef.current?.getConfig() ?? DEFAULT_CONFIG;\n },\n\n setBounds(bounds) {\n instanceRef.current?.setBounds(bounds);\n },\n\n setEventHandlers(handlers) {\n instanceRef.current?.setEventHandlers(handlers);\n },\n\n drawRect(items, layer) {\n return instanceRef.current?.drawRect(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticRect(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticRect(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawCircle(items, layer) {\n return instanceRef.current?.drawCircle(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticCircle(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticCircle(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawLine(items, style, layer) {\n return instanceRef.current?.drawLine(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawText(items, style, layer) {\n return instanceRef.current?.drawText(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawPath(items, style, layer) {\n return instanceRef.current?.drawPath(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawImage(items, layer) {\n return instanceRef.current?.drawImage(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticImage(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticImage(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawGridLines(cellSize, lineWidth, strokeStyle, layer) {\n return instanceRef.current?.drawGridLines(cellSize, lineWidth, strokeStyle, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n addDrawFunction(fn, layer) {\n return instanceRef.current?.addDrawFunction(fn, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n clearLayer(layer) {\n instanceRef.current?.clearLayer(layer);\n },\n\n clearAll() {\n instanceRef.current?.clearAll();\n },\n\n clearStaticCache(cacheKey) {\n instanceRef.current?.clearStaticCache(cacheKey);\n },\n\n removeLayerHandle(handle) {\n instanceRef.current?.removeLayerHandle(handle);\n },\n }),\n [setInstance]\n );\n\n return handle;\n}\n"],"mappings":"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","names":["index_exports","__export","CanvasTileEngine","useCanvasTileEngine","useEngineContext","__toCommonJS","import_react","import_core","import_react","EngineContext","useEngineContext","context","import_react","Rect","items","layer","engine","requestRender","useEngineContext","handle","import_react","Circle","items","layer","engine","requestRender","useEngineContext","handle","import_react","Image","items","layer","engine","requestRender","useEngineContext","handle","import_react","GridLines","cellSize","lineWidth","strokeStyle","layer","engine","requestRender","useEngineContext","handle","import_react","Line","items","style","layer","engine","requestRender","useEngineContext","handle","import_react","Text","items","style","layer","engine","requestRender","useEngineContext","handle","import_react","Path","items","style","layer","engine","requestRender","useEngineContext","handle","import_react","StaticRect","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","handle","import_react","StaticCircle","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","handle","import_react","StaticImage","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","handle","import_react","DrawFunction","children","layer","engine","requestRender","useEngineContext","fnRef","handle","ctx","coords","config","import_jsx_runtime","CanvasTileEngineBase","engine","config","center","className","style","children","onCoordsChange","onClick","onRightClick","onHover","onMouseDown","onMouseUp","onMouseLeave","onDraw","onResize","onZoom","callbacksRef","rafIdRef","requestRender","contextValue","container","instance","CanvasTileEngineCore","coords","args","scale","EngineContext","CanvasTileEngine","Rect","Circle","Image","GridLines","Line","Text","Path","StaticRect","StaticCircle","StaticImage","DrawFunction","import_react","DUMMY_LAYER_HANDLE","DEFAULT_CONFIG","useCanvasTileEngine","instanceRef","containerRef","setIsReady","isReadyRef","setInstance","engine","center","x","y","durationMs","onComplete","width","height","factor","bounds","handlers","items","layer","cacheKey","style","cellSize","lineWidth","strokeStyle","fn","handle","import_core"]}
|
|
1
|
+
{"version":3,"sources":["../src/index.ts","../src/components/CanvasTileEngine.tsx","../src/context/EngineContext.tsx","../src/components/draw/Rect.tsx","../src/components/draw/Circle.tsx","../src/components/draw/Image.tsx","../src/components/draw/GridLines.tsx","../src/components/draw/Line.tsx","../src/components/draw/Text.tsx","../src/components/draw/Path.tsx","../src/components/draw/StaticRect.tsx","../src/components/draw/StaticCircle.tsx","../src/components/draw/StaticImage.tsx","../src/components/draw/DrawFunction.tsx","../src/hooks/useCanvasTileEngine.ts"],"sourcesContent":["// Main component\nexport { CanvasTileEngine } from \"./components\";\n\n// Draw components\nexport {\n type RectProps,\n type CircleProps,\n type ImageProps,\n type GridLinesProps,\n type LineProps,\n type TextProps,\n type PathProps,\n type StaticRectProps,\n type StaticCircleProps,\n type StaticImageProps,\n type DrawFunctionProps,\n} from \"./components\";\n\n// Hooks\nexport { useCanvasTileEngine } from \"./hooks\";\n\n// Context\nexport { useEngineContext, type EngineContextValue } from \"./context\";\n\n// Types\nexport type {\n CanvasTileEngineProps,\n CanvasTileEngineConfig,\n Coords,\n DrawObject,\n EventHandlers,\n onClickCallback,\n onHoverCallback,\n onMouseDownCallback,\n onMouseUpCallback,\n onMouseLeaveCallback,\n onDrawCallback,\n Rect,\n Line,\n Circle,\n Text,\n Path,\n ImageItem,\n} from \"./types\";\nexport type { EngineHandle } from \"./hooks/useCanvasTileEngine\";\n\n// Re-export core class and utilities\nexport { CanvasTileEngine as CanvasTileEngineCore, gridToSize } from \"@canvas-tile-engine/core\";\n","import { useEffect, useRef, useCallback, useMemo } from \"react\";\nimport { CanvasTileEngine as CanvasTileEngineCore } from \"@canvas-tile-engine/core\";\nimport { EngineContext, type EngineContextValue } from \"../context/EngineContext\";\nimport type { CanvasTileEngineProps } from \"../types\";\n\n// Import draw components for compound pattern\nimport { Rect } from \"./draw/Rect\";\nimport { Circle } from \"./draw/Circle\";\nimport { Image } from \"./draw/Image\";\nimport { GridLines } from \"./draw/GridLines\";\nimport { Line } from \"./draw/Line\";\nimport { Text } from \"./draw/Text\";\nimport { Path } from \"./draw/Path\";\nimport { StaticRect } from \"./draw/StaticRect\";\nimport { StaticCircle } from \"./draw/StaticCircle\";\nimport { StaticImage } from \"./draw/StaticImage\";\nimport { DrawFunction } from \"./draw/DrawFunction\";\n\n/**\n * React component that renders a CanvasTileEngine.\n * Supports both imperative API (via engine handle) and declarative API (via children).\n *\n * @example Declarative API with compound components\n * ```tsx\n * function App() {\n * const engine = useCanvasTileEngine();\n *\n * return (\n * <CanvasTileEngine engine={engine} config={config}>\n * <CanvasTileEngine.GridLines cellSize={50} layer={0} />\n * <CanvasTileEngine.Image items={imageItems} layer={1} />\n * <CanvasTileEngine.Circle items={markers} layer={2} />\n * </CanvasTileEngine>\n * );\n * }\n * ```\n *\n * @example Imperative API\n * ```tsx\n * function App() {\n * const engine = useCanvasTileEngine();\n *\n * useEffect(() => {\n * if (engine.isReady) {\n * engine.drawGridLines(50);\n * engine.render();\n * }\n * }, [engine.isReady]);\n *\n * return <CanvasTileEngine engine={engine} config={config} />;\n * }\n * ```\n */\nfunction CanvasTileEngineBase({\n engine,\n config,\n center = { x: 0, y: 0 },\n className,\n style,\n children,\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n}: CanvasTileEngineProps) {\n // Stable callback refs\n const callbacksRef = useRef({\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n });\n\n // Update callback refs\n useEffect(() => {\n callbacksRef.current = {\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n };\n });\n\n // Debounced render - multiple draw components calling requestRender\n // in the same frame will trigger only one render\n const rafIdRef = useRef<number | null>(null);\n const requestRender = useCallback(() => {\n if (rafIdRef.current !== null) return;\n rafIdRef.current = requestAnimationFrame(() => {\n rafIdRef.current = null;\n engine.render();\n });\n }, [engine]);\n\n // Cleanup RAF on unmount\n useEffect(() => {\n return () => {\n if (rafIdRef.current !== null) {\n cancelAnimationFrame(rafIdRef.current);\n }\n };\n }, []);\n\n // Context value\n const contextValue = useMemo<EngineContextValue>(\n () => ({\n engine,\n requestRender,\n }),\n [engine, requestRender]\n );\n\n // Initialize engine when component mounts\n // Note: config and center are intentionally not in deps - we only want to create the engine once\n // Callbacks are accessed via callbacksRef which is always up-to-date\n useEffect(() => {\n const container = engine._containerRef.current;\n\n if (!container) {\n return;\n }\n\n // Create engine instance\n const instance = new CanvasTileEngineCore(container, config, center);\n\n // Set up callbacks using stable refs\n instance.onCoordsChange = (coords) => callbacksRef.current.onCoordsChange?.(coords);\n instance.onClick = (...args) => callbacksRef.current.onClick?.(...args);\n instance.onRightClick = (...args) => callbacksRef.current.onRightClick?.(...args);\n instance.onHover = (...args) => callbacksRef.current.onHover?.(...args);\n instance.onMouseDown = (...args) => callbacksRef.current.onMouseDown?.(...args);\n instance.onMouseUp = (...args) => callbacksRef.current.onMouseUp?.(...args);\n instance.onMouseLeave = (...args) => callbacksRef.current.onMouseLeave?.(...args);\n instance.onDraw = (...args) => callbacksRef.current.onDraw?.(...args);\n instance.onResize = () => callbacksRef.current.onResize?.();\n instance.onZoom = (scale) => callbacksRef.current.onZoom?.(scale);\n\n // Attach to handle\n engine._setInstance(instance);\n\n // Initial render\n instance.render();\n\n // Cleanup on unmount\n return () => {\n instance.destroy();\n engine._setInstance(null);\n };\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [engine]);\n\n return (\n <EngineContext.Provider value={contextValue}>\n <div\n ref={engine._containerRef}\n className={className}\n style={{\n ...style,\n }}\n >\n <canvas />\n </div>\n {/* Render children only when engine is ready */}\n {engine.isReady && children}\n </EngineContext.Provider>\n );\n}\n\n// Compound component pattern - attach draw components as static properties\nexport const CanvasTileEngine = Object.assign(CanvasTileEngineBase, {\n Rect,\n Circle,\n Image,\n GridLines,\n Line,\n Text,\n Path,\n StaticRect,\n StaticCircle,\n StaticImage,\n DrawFunction,\n});\n","import { createContext, useContext } from \"react\";\nimport type { EngineHandle } from \"../hooks/useCanvasTileEngine\";\n\nexport interface EngineContextValue {\n engine: EngineHandle;\n /** Request a re-render of the canvas */\n requestRender: () => void;\n}\n\nexport const EngineContext = createContext<EngineContextValue | null>(null);\n\n/**\n * Hook to access the engine context from child components.\n * Must be used within a CanvasTileEngine component.\n */\nexport function useEngineContext(): EngineContextValue {\n const context = useContext(EngineContext);\n\n if (!context) {\n throw new Error(\"useEngineContext must be used within a CanvasTileEngine component\");\n }\n\n return context;\n}\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Rect as RectType } from \"@canvas-tile-engine/core\";\n\nexport interface RectProps {\n items: RectType | RectType[];\n layer?: number;\n}\n\n/**\n * Draws rectangles on the canvas.\n */\nexport const Rect = memo(function Rect({ items, layer = 1 }: RectProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawRect(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Circle as CircleType } from \"@canvas-tile-engine/core\";\n\nexport interface CircleProps {\n items: CircleType | CircleType[];\n layer?: number;\n}\n\n/**\n * Draws circles on the canvas.\n */\nexport const Circle = memo(function Circle({ items, layer = 1 }: CircleProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawCircle(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport { ImageItem } from \"@canvas-tile-engine/core\";\n\nexport interface ImageProps {\n items: ImageItem | ImageItem[];\n layer?: number;\n}\n\n/**\n * Draws images on the canvas.\n */\nexport const Image = memo(function Image({ items, layer = 1 }: ImageProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawImage(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\n\nexport interface GridLinesProps {\n cellSize: number;\n lineWidth?: number;\n strokeStyle?: string;\n layer?: number;\n}\n\n/**\n * Draws grid lines on the canvas.\n * Multiple GridLines can share the same layer (additive drawing).\n */\nexport const GridLines = memo(function GridLines({ cellSize, lineWidth = 1, strokeStyle = \"black\", layer = 0 }: GridLinesProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawGridLines(cellSize, lineWidth, strokeStyle, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, cellSize, lineWidth, strokeStyle, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Line as LineType } from \"@canvas-tile-engine/core\";\n\nexport interface LineProps {\n items: LineType | LineType[];\n style?: { strokeStyle?: string; lineWidth?: number };\n layer?: number;\n}\n\n/**\n * Draws lines on the canvas.\n */\nexport const Line = memo(function Line({ items, style, layer = 1 }: LineProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawLine(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Text as TextType } from \"@canvas-tile-engine/core\";\n\nexport interface TextProps {\n items: TextType | TextType[];\n layer?: number;\n}\n\n/**\n * Draws text on the canvas.\n * @example\n * ```tsx\n * <Text\n * items={{\n * x: 0,\n * y: 0,\n * text: \"Hello\",\n * size: 1,\n * style: { fillStyle: \"black\", fontFamily: \"Arial\" }\n * }}\n * />\n * ```\n */\nexport const Text = memo(function Text({ items, layer = 2 }: TextProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawText(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Path as PathType } from \"@canvas-tile-engine/core\";\n\nexport interface PathProps {\n items: PathType | PathType[];\n style?: { strokeStyle?: string; lineWidth?: number };\n layer?: number;\n}\n\n/**\n * Draws paths/polylines on the canvas.\n */\nexport const Path = memo(function Path({ items, style, layer = 1 }: PathProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawPath(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Rect as RectType } from \"@canvas-tile-engine/core\";\n\nexport interface StaticRectProps {\n items: RectType[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static rectangles with caching for performance.\n * Ideal for large datasets that don't change frequently.\n */\nexport const StaticRect = memo(function StaticRect({ items, cacheKey, layer = 1 }: StaticRectProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n // Clear previous cache if cacheKey changed\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticRect(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n // Cleanup cache on unmount\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Circle as CircleType } from \"@canvas-tile-engine/core\";\n\nexport interface StaticCircleProps {\n items: CircleType[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static circles with caching for performance.\n */\nexport const StaticCircle = memo(function StaticCircle({ items, cacheKey, layer = 1 }: StaticCircleProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticCircle(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport { ImageItem } from \"@canvas-tile-engine/core\";\n\nexport interface StaticImageProps {\n items: ImageItem[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static images with caching for performance.\n * Ideal for terrain tiles or static decorations.\n */\nexport const StaticImage = memo(function StaticImage({ items, cacheKey, layer = 1 }: StaticImageProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticImage(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { CanvasTileEngineConfig, Coords } from \"@canvas-tile-engine/core\";\n\nexport interface DrawFunctionProps {\n /** The draw function to execute */\n children: (ctx: CanvasRenderingContext2D, coords: Coords, config: Required<CanvasTileEngineConfig>) => void;\n layer?: number;\n}\n\n/**\n * Custom draw function component.\n * Allows arbitrary canvas drawing within the engine's render cycle.\n * Multiple DrawFunction components can share the same layer (additive drawing).\n *\n * @example\n * ```tsx\n * <DrawFunction layer={3}>\n * {(ctx, coords, config) => {\n * ctx.fillStyle = \"red\";\n * ctx.fillRect(config.size.width / 2 - 5, config.size.height / 2 - 5, 10, 10);\n * }}\n * </DrawFunction>\n * ```\n */\nexport const DrawFunction = memo(function DrawFunction({ children, layer = 1 }: DrawFunctionProps) {\n const { engine, requestRender } = useEngineContext();\n const fnRef = useRef(children);\n\n // Keep function ref updated\n useEffect(() => {\n fnRef.current = children;\n });\n\n useEffect(() => {\n const handle = engine.addDrawFunction((ctx, coords, config) => {\n fnRef.current(ctx, coords, config);\n }, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, layer, requestRender]);\n\n return null;\n});\n","import { useRef, useCallback, useState, useMemo } from \"react\";\nimport type {\n CanvasTileEngine as CanvasTileEngineCore,\n CanvasTileEngineConfig,\n Coords,\n EventHandlers,\n LayerHandle,\n ImageItem,\n Text,\n Circle,\n Line,\n Rect,\n} from \"@canvas-tile-engine/core\";\n\n/** Dummy handle returned when engine is not ready */\nconst DUMMY_LAYER_HANDLE: LayerHandle = { layer: -1, id: Symbol(\"dummy\") };\n\n/** Default config when engine is not ready */\nconst DEFAULT_CONFIG: Required<CanvasTileEngineConfig> = {\n size: { width: 0, height: 0, minWidth: 100, minHeight: 100, maxWidth: Infinity, maxHeight: Infinity },\n responsive: false,\n scale: 1,\n minScale: 0.5,\n maxScale: 2,\n backgroundColor: \"#ffffff\",\n gridAligned: false,\n renderer: \"canvas\",\n eventHandlers: {\n drag: true,\n zoom: true,\n hover: false,\n click: false,\n rightClick: false,\n resize: false,\n },\n bounds: {\n minX: -Infinity,\n maxX: Infinity,\n minY: -Infinity,\n maxY: Infinity,\n },\n coordinates: {\n enabled: false,\n shownScaleRange: { min: 0, max: Infinity },\n },\n cursor: {\n default: \"default\",\n move: \"move\",\n },\n debug: {\n enabled: false,\n hud: {\n enabled: false,\n topLeftCoordinates: false,\n coordinates: false,\n scale: false,\n tilesInView: false,\n fps: false,\n },\n eventHandlers: {\n click: false,\n hover: false,\n drag: false,\n zoom: false,\n resize: false,\n },\n },\n};\n\n/**\n * Engine handle returned by useCanvasTileEngine hook.\n * Provides access to engine methods with proper typing.\n *\n * All methods return default/dummy values when engine is not ready,\n * allowing safe usage without null checks.\n */\nexport interface EngineHandle {\n /** @internal - Used by CanvasTileEngine component */\n readonly _containerRef: React.RefObject<HTMLDivElement>;\n /** @internal - Used by CanvasTileEngine component */\n _setInstance: (engine: CanvasTileEngineCore | null) => void;\n\n /** Whether the engine is ready (mounted and initialized) */\n readonly isReady: boolean;\n\n /** The underlying engine instance (null until component mounts) */\n readonly instance: CanvasTileEngineCore | null;\n\n /** Render a frame */\n render(): void;\n\n /** Get current center coordinates */\n getCenterCoords(): Coords;\n\n /** Get visible world coordinate bounds of the viewport */\n getVisibleBounds(): { minX: number; maxX: number; minY: number; maxY: number };\n\n /** Update center coordinates */\n updateCoords(center: Coords): void;\n\n /** Animate to target coordinates */\n goCoords(x: number, y: number, durationMs?: number, onComplete?: () => void): void;\n\n /** Resize the canvas */\n resize(width: number, height: number, durationMs?: number, onComplete?: () => void): void;\n\n /** Get current canvas size */\n getSize(): { width: number; height: number };\n\n /** Get current canvas scale */\n getScale(): number;\n\n /** Set the canvas scale directly, clamped to min/max bounds. */\n setScale(newScale: number): void;\n\n /** Zoom in by a factor (default: 1.5) */\n zoomIn(factor?: number): void;\n\n /** Zoom out by a factor (default: 1.5) */\n zoomOut(factor?: number): void;\n\n /** Get current config */\n getConfig(): Required<CanvasTileEngineConfig>;\n\n /** Set map boundaries */\n setBounds(bounds: { minX: number; maxX: number; minY: number; maxY: number }): void;\n\n /** Dynamically update event handlers at runtime */\n setEventHandlers(handlers: Partial<EventHandlers>): void;\n\n /** Draw rectangles */\n drawRect(items: Rect | Rect[], layer?: number): LayerHandle;\n\n /** Draw static rectangles (cached) */\n drawStaticRect(items: Rect[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw circles */\n drawCircle(items: Circle | Circle[], layer?: number): LayerHandle;\n\n /** Draw static circles (cached) */\n drawStaticCircle(items: Circle[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw lines */\n drawLine(items: Line | Line[], style?: { strokeStyle?: string; lineWidth?: number }, layer?: number): LayerHandle;\n\n /** Draw text */\n drawText(items: Text | Text[], layer?: number): LayerHandle;\n\n /** Draw paths/polylines */\n drawPath(\n items: Coords[] | Coords[][],\n style?: { strokeStyle?: string; lineWidth?: number },\n layer?: number\n ): LayerHandle;\n\n /** Draw images */\n drawImage(items: ImageItem | ImageItem[], layer?: number): LayerHandle;\n\n /** Draw static images (cached) */\n drawStaticImage(items: ImageItem[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw grid lines */\n drawGridLines(cellSize: number, lineWidth?: number, strokeStyle?: string, layer?: number): LayerHandle;\n\n /** Add custom draw function */\n addDrawFunction(\n fn: (ctx: CanvasRenderingContext2D, coords: Coords, config: Required<CanvasTileEngineConfig>) => void,\n layer?: number\n ): LayerHandle;\n\n /** Clear a specific layer */\n clearLayer(layer: number): void;\n\n /** Clear all layers */\n clearAll(): void;\n\n /** Clear static cache */\n clearStaticCache(cacheKey?: string): void;\n\n /** Remove a previously registered draw callback */\n removeLayerHandle(handle: LayerHandle): void;\n\n /** Image loader instance (undefined until engine mounts) */\n readonly images: CanvasTileEngineCore[\"images\"] | undefined;\n\n /**\n * Load an image using the engine's image loader.\n * Returns a rejected promise if engine is not ready.\n * @param src - Image URL to load\n * @param retry - Number of retries on failure (default: 1)\n * @example\n * ```tsx\n * const img = await engine.loadImage(\"/sprites/player.png\");\n * ```\n */\n loadImage(src: string, retry?: number): Promise<HTMLImageElement>;\n}\n\n/**\n * React hook that creates an engine handle for use with CanvasTileEngine component.\n *\n * @returns Engine handle to pass to CanvasTileEngine component\n *\n * @example\n * ```tsx\n * function App() {\n * const mainMap = useCanvasTileEngine();\n * const miniMap = useCanvasTileEngine();\n *\n * useEffect(() => {\n * if (mainMap.isReady && miniMap.isReady) {\n * // Both engines are ready, draw items\n * mainMap.drawGridLines(50);\n * mainMap.render();\n * }\n * }, [mainMap.isReady, miniMap.isReady]);\n *\n * return (\n * <>\n * <CanvasTileEngine engine={mainMap} config={...} />\n * <CanvasTileEngine engine={miniMap} config={...} />\n * </>\n * );\n * }\n * ```\n */\nexport function useCanvasTileEngine(): EngineHandle {\n const instanceRef = useRef<CanvasTileEngineCore | null>(null);\n const containerRef = useRef<HTMLDivElement>(null!);\n // _isReady state is only used to trigger re-renders, actual value is read from isReadyRef\n const [, setIsReady] = useState(false);\n // Keep isReady in a ref so the handle getter can read it without recreating handle\n const isReadyRef = useRef(false);\n\n const setInstance = useCallback((engine: CanvasTileEngineCore | null) => {\n instanceRef.current = engine;\n isReadyRef.current = engine !== null;\n setIsReady(engine !== null);\n }, []);\n\n // Create stable handle object using useMemo\n // Note: isReady is NOT in deps - we read from isReadyRef to keep handle stable\n const handle = useMemo<EngineHandle>(\n () => ({\n _containerRef: containerRef,\n _setInstance: setInstance,\n\n get isReady() {\n return isReadyRef.current;\n },\n\n get instance() {\n return instanceRef.current;\n },\n\n get images() {\n return instanceRef.current?.images;\n },\n\n render() {\n instanceRef.current?.render();\n },\n\n getCenterCoords() {\n return instanceRef.current?.getCenterCoords() ?? { x: 0, y: 0 };\n },\n\n getVisibleBounds() {\n return instanceRef.current?.getVisibleBounds() ?? { minX: 0, maxX: 0, minY: 0, maxY: 0 };\n },\n\n updateCoords(center: Coords) {\n instanceRef.current?.updateCoords(center);\n },\n\n goCoords(x: number, y: number, durationMs?: number, onComplete?: () => void) {\n instanceRef.current?.goCoords(x, y, durationMs, onComplete);\n },\n\n resize(width: number, height: number, durationMs?: number, onComplete?: () => void) {\n instanceRef.current?.resize(width, height, durationMs, onComplete);\n },\n\n getSize() {\n return instanceRef.current?.getSize() ?? { width: 0, height: 0 };\n },\n\n getScale() {\n return instanceRef.current?.getScale() ?? 1;\n },\n\n setScale(newScale: number) {\n instanceRef.current?.setScale(newScale);\n },\n\n zoomIn(factor?: number) {\n instanceRef.current?.zoomIn(factor);\n },\n\n zoomOut(factor?: number) {\n instanceRef.current?.zoomOut(factor);\n },\n\n getConfig() {\n return instanceRef.current?.getConfig() ?? DEFAULT_CONFIG;\n },\n\n setBounds(bounds) {\n instanceRef.current?.setBounds(bounds);\n },\n\n setEventHandlers(handlers) {\n instanceRef.current?.setEventHandlers(handlers);\n },\n\n drawRect(items, layer) {\n return instanceRef.current?.drawRect(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticRect(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticRect(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawCircle(items, layer) {\n return instanceRef.current?.drawCircle(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticCircle(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticCircle(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawLine(items, style, layer) {\n return instanceRef.current?.drawLine(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawText(items, layer) {\n return instanceRef.current?.drawText(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawPath(items, style, layer) {\n return instanceRef.current?.drawPath(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawImage(items, layer) {\n return instanceRef.current?.drawImage(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticImage(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticImage(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawGridLines(cellSize, lineWidth, strokeStyle, layer) {\n return (\n instanceRef.current?.drawGridLines(cellSize, lineWidth, strokeStyle, layer) ?? DUMMY_LAYER_HANDLE\n );\n },\n\n addDrawFunction(fn, layer) {\n return instanceRef.current?.addDrawFunction(fn, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n clearLayer(layer) {\n instanceRef.current?.clearLayer(layer);\n },\n\n clearAll() {\n instanceRef.current?.clearAll();\n },\n\n clearStaticCache(cacheKey) {\n instanceRef.current?.clearStaticCache(cacheKey);\n },\n\n removeLayerHandle(handle) {\n instanceRef.current?.removeLayerHandle(handle);\n },\n\n loadImage(src: string, retry?: number) {\n if (!instanceRef.current) {\n return Promise.reject(new Error(\"Engine not ready. Wait for isReady before loading images.\"));\n }\n return instanceRef.current.images.load(src, retry);\n },\n }),\n [setInstance]\n );\n\n return handle;\n}\n"],"mappings":"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","names":["index_exports","__export","CanvasTileEngine","useCanvasTileEngine","useEngineContext","__toCommonJS","import_react","import_core","import_react","EngineContext","useEngineContext","context","import_react","Rect","items","layer","engine","requestRender","useEngineContext","handle","import_react","Circle","items","layer","engine","requestRender","useEngineContext","handle","import_react","Image","items","layer","engine","requestRender","useEngineContext","handle","import_react","GridLines","cellSize","lineWidth","strokeStyle","layer","engine","requestRender","useEngineContext","handle","import_react","Line","items","style","layer","engine","requestRender","useEngineContext","handle","import_react","Text","items","layer","engine","requestRender","useEngineContext","handle","import_react","Path","items","style","layer","engine","requestRender","useEngineContext","handle","import_react","StaticRect","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","handle","import_react","StaticCircle","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","handle","import_react","StaticImage","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","handle","import_react","DrawFunction","children","layer","engine","requestRender","useEngineContext","fnRef","handle","ctx","coords","config","import_jsx_runtime","CanvasTileEngineBase","engine","config","center","className","style","children","onCoordsChange","onClick","onRightClick","onHover","onMouseDown","onMouseUp","onMouseLeave","onDraw","onResize","onZoom","callbacksRef","rafIdRef","requestRender","contextValue","container","instance","CanvasTileEngineCore","coords","args","scale","EngineContext","CanvasTileEngine","Rect","Circle","Image","GridLines","Line","Text","Path","StaticRect","StaticCircle","StaticImage","DrawFunction","import_react","DUMMY_LAYER_HANDLE","DEFAULT_CONFIG","useCanvasTileEngine","instanceRef","containerRef","setIsReady","isReadyRef","setInstance","engine","center","x","y","durationMs","onComplete","width","height","newScale","factor","bounds","handlers","items","layer","cacheKey","style","cellSize","lineWidth","strokeStyle","fn","handle","src","retry","import_core"]}
|
package/dist/index.mjs
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{useEffect as
|
|
1
|
+
import{useEffect as y,useRef as W,useCallback as ye,useMemo as xe}from"react";import{CanvasTileEngine as ve}from"@canvas-tile-engine/core";import{createContext as j,useContext as N}from"react";var C=j(null);function c(){let r=N(C);if(!r)throw new Error("useEngineContext must be used within a CanvasTileEngine component");return r}import{useEffect as Z,memo as J}from"react";var h=J(function({items:a,layer:n=1}){let{engine:i,requestRender:t}=c();return Z(()=>{let s=i.drawRect(a,n);return t(),()=>{s&&i.removeLayerHandle(s)}},[i,a,n,t]),null});import{useEffect as Q,memo as $}from"react";var S=$(function({items:a,layer:n=1}){let{engine:i,requestRender:t}=c();return Q(()=>{let s=i.drawCircle(a,n);return t(),()=>{s&&i.removeLayerHandle(s)}},[i,a,n,t]),null});import{useEffect as K,memo as ee}from"react";var I=ee(function({items:a,layer:n=1}){let{engine:i,requestRender:t}=c();return K(()=>{let s=i.drawImage(a,n);return t(),()=>{s&&i.removeLayerHandle(s)}},[i,a,n,t]),null});import{useEffect as re,memo as ne}from"react";var H=ne(function({cellSize:a,lineWidth:n=1,strokeStyle:i="black",layer:t=0}){let{engine:s,requestRender:e}=c();return re(()=>{let o=s.drawGridLines(a,n,i,t);return e(),()=>{o&&s.removeLayerHandle(o)}},[s,a,n,i,t,e]),null});import{useEffect as te,memo as oe}from"react";var k=oe(function({items:a,style:n,layer:i=1}){let{engine:t,requestRender:s}=c();return te(()=>{let e=t.drawLine(a,n,i);return s(),()=>{e&&t.removeLayerHandle(e)}},[t,a,n,i,s]),null});import{useEffect as ie,memo as ae}from"react";var D=ae(function({items:a,layer:n=2}){let{engine:i,requestRender:t}=c();return ie(()=>{let s=i.drawText(a,n);return t(),()=>{s&&i.removeLayerHandle(s)}},[i,a,n,t]),null});import{useEffect as se,memo as ce}from"react";var z=ce(function({items:a,style:n,layer:i=1}){let{engine:t,requestRender:s}=c();return se(()=>{let e=t.drawPath(a,n,i);return s(),()=>{e&&t.removeLayerHandle(e)}},[t,a,n,i,s]),null});import{useEffect as q,useRef as ue,memo as le}from"react";var F=le(function({items:a,cacheKey:n,layer:i=1}){let{engine:t,requestRender:s}=c(),e=ue(n);return q(()=>{if(a.length===0)return;e.current!==n&&(t.clearStaticCache(e.current),e.current=n);let o=t.drawStaticRect(a,n,i);return s(),()=>{o&&t.removeLayerHandle(o)}},[t,a,n,i,s]),q(()=>()=>{t.clearStaticCache(n)},[t,n]),null});import{useEffect as M,useRef as me,memo as de}from"react";var G=de(function({items:a,cacheKey:n,layer:i=1}){let{engine:t,requestRender:s}=c(),e=me(n);return M(()=>{if(a.length===0)return;e.current!==n&&(t.clearStaticCache(e.current),e.current=n);let o=t.drawStaticCircle(a,n,i);return s(),()=>{o&&t.removeLayerHandle(o)}},[t,a,n,i,s]),M(()=>()=>{t.clearStaticCache(n)},[t,n]),null});import{useEffect as V,useRef as fe,memo as pe}from"react";var _=pe(function({items:a,cacheKey:n,layer:i=1}){let{engine:t,requestRender:s}=c(),e=fe(n);return V(()=>{if(a.length===0)return;e.current!==n&&(t.clearStaticCache(e.current),e.current=n);let o=t.drawStaticImage(a,n,i);return s(),()=>{o&&t.removeLayerHandle(o)}},[t,a,n,i,s]),V(()=>()=>{t.clearStaticCache(n)},[t,n]),null});import{useEffect as Y,useRef as ge,memo as Ce}from"react";var A=Ce(function({children:a,layer:n=1}){let{engine:i,requestRender:t}=c(),s=ge(a);return Y(()=>{s.current=a}),Y(()=>{let e=i.addDrawFunction((o,u,p)=>{s.current(o,u,p)},n);return t(),()=>{e&&i.removeLayerHandle(e)}},[i,n,t]),null});import{jsx as X,jsxs as Ee}from"react/jsx-runtime";function be({engine:r,config:a,center:n={x:0,y:0},className:i,style:t,children:s,onCoordsChange:e,onClick:o,onRightClick:u,onHover:p,onMouseDown:v,onMouseUp:b,onMouseLeave:E,onDraw:R,onResize:T,onZoom:L}){let d=W({onCoordsChange:e,onClick:o,onRightClick:u,onHover:p,onMouseDown:v,onMouseUp:b,onMouseLeave:E,onDraw:R,onResize:T,onZoom:L});y(()=>{d.current={onCoordsChange:e,onClick:o,onRightClick:u,onHover:p,onMouseDown:v,onMouseUp:b,onMouseLeave:E,onDraw:R,onResize:T,onZoom:L}});let g=W(null),w=ye(()=>{g.current===null&&(g.current=requestAnimationFrame(()=>{g.current=null,r.render()}))},[r]);y(()=>()=>{g.current!==null&&cancelAnimationFrame(g.current)},[]);let U=xe(()=>({engine:r,requestRender:w}),[r,w]);return y(()=>{let P=r._containerRef.current;if(!P)return;let m=new ve(P,a,n);return m.onCoordsChange=l=>d.current.onCoordsChange?.(l),m.onClick=(...l)=>d.current.onClick?.(...l),m.onRightClick=(...l)=>d.current.onRightClick?.(...l),m.onHover=(...l)=>d.current.onHover?.(...l),m.onMouseDown=(...l)=>d.current.onMouseDown?.(...l),m.onMouseUp=(...l)=>d.current.onMouseUp?.(...l),m.onMouseLeave=(...l)=>d.current.onMouseLeave?.(...l),m.onDraw=(...l)=>d.current.onDraw?.(...l),m.onResize=()=>d.current.onResize?.(),m.onZoom=l=>d.current.onZoom?.(l),r._setInstance(m),m.render(),()=>{m.destroy(),r._setInstance(null)}},[r]),Ee(C.Provider,{value:U,children:[X("div",{ref:r._containerRef,className:i,style:{...t},children:X("canvas",{})}),r.isReady&&s]})}var B=Object.assign(be,{Rect:h,Circle:S,Image:I,GridLines:H,Line:k,Text:D,Path:z,StaticRect:F,StaticCircle:G,StaticImage:_,DrawFunction:A});import{useRef as x,useCallback as Re,useState as Te,useMemo as Le}from"react";var f={layer:-1,id:Symbol("dummy")},we={size:{width:0,height:0,minWidth:100,minHeight:100,maxWidth:1/0,maxHeight:1/0},responsive:!1,scale:1,minScale:.5,maxScale:2,backgroundColor:"#ffffff",gridAligned:!1,renderer:"canvas",eventHandlers:{drag:!0,zoom:!0,hover:!1,click:!1,rightClick:!1,resize:!1},bounds:{minX:-1/0,maxX:1/0,minY:-1/0,maxY:1/0},coordinates:{enabled:!1,shownScaleRange:{min:0,max:1/0}},cursor:{default:"default",move:"move"},debug:{enabled:!1,hud:{enabled:!1,topLeftCoordinates:!1,coordinates:!1,scale:!1,tilesInView:!1,fps:!1},eventHandlers:{click:!1,hover:!1,drag:!1,zoom:!1,resize:!1}}};function O(){let r=x(null),a=x(null),[,n]=Te(!1),i=x(!1),t=Re(e=>{r.current=e,i.current=e!==null,n(e!==null)},[]);return Le(()=>({_containerRef:a,_setInstance:t,get isReady(){return i.current},get instance(){return r.current},get images(){return r.current?.images},render(){r.current?.render()},getCenterCoords(){return r.current?.getCenterCoords()??{x:0,y:0}},getVisibleBounds(){return r.current?.getVisibleBounds()??{minX:0,maxX:0,minY:0,maxY:0}},updateCoords(e){r.current?.updateCoords(e)},goCoords(e,o,u,p){r.current?.goCoords(e,o,u,p)},resize(e,o,u,p){r.current?.resize(e,o,u,p)},getSize(){return r.current?.getSize()??{width:0,height:0}},getScale(){return r.current?.getScale()??1},setScale(e){r.current?.setScale(e)},zoomIn(e){r.current?.zoomIn(e)},zoomOut(e){r.current?.zoomOut(e)},getConfig(){return r.current?.getConfig()??we},setBounds(e){r.current?.setBounds(e)},setEventHandlers(e){r.current?.setEventHandlers(e)},drawRect(e,o){return r.current?.drawRect(e,o)??f},drawStaticRect(e,o,u){return r.current?.drawStaticRect(e,o,u)??f},drawCircle(e,o){return r.current?.drawCircle(e,o)??f},drawStaticCircle(e,o,u){return r.current?.drawStaticCircle(e,o,u)??f},drawLine(e,o,u){return r.current?.drawLine(e,o,u)??f},drawText(e,o){return r.current?.drawText(e,o)??f},drawPath(e,o,u){return r.current?.drawPath(e,o,u)??f},drawImage(e,o){return r.current?.drawImage(e,o)??f},drawStaticImage(e,o,u){return r.current?.drawStaticImage(e,o,u)??f},drawGridLines(e,o,u,p){return r.current?.drawGridLines(e,o,u,p)??f},addDrawFunction(e,o){return r.current?.addDrawFunction(e,o)??f},clearLayer(e){r.current?.clearLayer(e)},clearAll(){r.current?.clearAll()},clearStaticCache(e){r.current?.clearStaticCache(e)},removeLayerHandle(e){r.current?.removeLayerHandle(e)},loadImage(e,o){return r.current?r.current.images.load(e,o):Promise.reject(new Error("Engine not ready. Wait for isReady before loading images."))}}),[t])}import{CanvasTileEngine as Mr,gridToSize as Gr}from"@canvas-tile-engine/core";export{B as CanvasTileEngine,Mr as CanvasTileEngineCore,Gr as gridToSize,O as useCanvasTileEngine,c as useEngineContext};
|
|
2
2
|
//# sourceMappingURL=index.mjs.map
|
package/dist/index.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/components/CanvasTileEngine.tsx","../src/context/EngineContext.tsx","../src/components/draw/Rect.tsx","../src/components/draw/Circle.tsx","../src/components/draw/Image.tsx","../src/components/draw/GridLines.tsx","../src/components/draw/Line.tsx","../src/components/draw/Text.tsx","../src/components/draw/Path.tsx","../src/components/draw/StaticRect.tsx","../src/components/draw/StaticCircle.tsx","../src/components/draw/StaticImage.tsx","../src/components/draw/DrawFunction.tsx","../src/hooks/useCanvasTileEngine.ts","../src/index.ts"],"sourcesContent":["import { useEffect, useRef, useCallback, useMemo } from \"react\";\nimport { CanvasTileEngine as CanvasTileEngineCore } from \"@canvas-tile-engine/core\";\nimport { EngineContext, type EngineContextValue } from \"../context/EngineContext\";\nimport type { CanvasTileEngineProps } from \"../types\";\n\n// Import draw components for compound pattern\nimport { Rect } from \"./draw/Rect\";\nimport { Circle } from \"./draw/Circle\";\nimport { Image } from \"./draw/Image\";\nimport { GridLines } from \"./draw/GridLines\";\nimport { Line } from \"./draw/Line\";\nimport { Text } from \"./draw/Text\";\nimport { Path } from \"./draw/Path\";\nimport { StaticRect } from \"./draw/StaticRect\";\nimport { StaticCircle } from \"./draw/StaticCircle\";\nimport { StaticImage } from \"./draw/StaticImage\";\nimport { DrawFunction } from \"./draw/DrawFunction\";\n\n/**\n * React component that renders a CanvasTileEngine.\n * Supports both imperative API (via engine handle) and declarative API (via children).\n *\n * @example Declarative API with compound components\n * ```tsx\n * function App() {\n * const engine = useCanvasTileEngine();\n *\n * return (\n * <CanvasTileEngine engine={engine} config={config}>\n * <CanvasTileEngine.GridLines cellSize={50} layer={0} />\n * <CanvasTileEngine.Image items={imageItems} layer={1} />\n * <CanvasTileEngine.Circle items={markers} layer={2} />\n * </CanvasTileEngine>\n * );\n * }\n * ```\n *\n * @example Imperative API\n * ```tsx\n * function App() {\n * const engine = useCanvasTileEngine();\n *\n * useEffect(() => {\n * if (engine.isReady) {\n * engine.drawGridLines(50);\n * engine.render();\n * }\n * }, [engine.isReady]);\n *\n * return <CanvasTileEngine engine={engine} config={config} />;\n * }\n * ```\n */\nfunction CanvasTileEngineBase({\n engine,\n config,\n center = { x: 0, y: 0 },\n className,\n style,\n children,\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n}: CanvasTileEngineProps) {\n // Stable callback refs\n const callbacksRef = useRef({\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n });\n\n // Update callback refs\n useEffect(() => {\n callbacksRef.current = {\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n };\n });\n\n // Debounced render - multiple draw components calling requestRender\n // in the same frame will trigger only one render\n const rafIdRef = useRef<number | null>(null);\n const requestRender = useCallback(() => {\n if (rafIdRef.current !== null) return;\n rafIdRef.current = requestAnimationFrame(() => {\n rafIdRef.current = null;\n engine.render();\n });\n }, [engine]);\n\n // Cleanup RAF on unmount\n useEffect(() => {\n return () => {\n if (rafIdRef.current !== null) {\n cancelAnimationFrame(rafIdRef.current);\n }\n };\n }, []);\n\n // Context value\n const contextValue = useMemo<EngineContextValue>(\n () => ({\n engine,\n requestRender,\n }),\n [engine, requestRender]\n );\n\n // Initialize engine when component mounts\n // Note: config and center are intentionally not in deps - we only want to create the engine once\n // Callbacks are accessed via callbacksRef which is always up-to-date\n useEffect(() => {\n const container = engine._containerRef.current;\n\n if (!container) {\n return;\n }\n\n // Create engine instance\n const instance = new CanvasTileEngineCore(container, config, center);\n\n // Set up callbacks using stable refs\n instance.onCoordsChange = (coords) => callbacksRef.current.onCoordsChange?.(coords);\n instance.onClick = (...args) => callbacksRef.current.onClick?.(...args);\n instance.onRightClick = (...args) => callbacksRef.current.onRightClick?.(...args);\n instance.onHover = (...args) => callbacksRef.current.onHover?.(...args);\n instance.onMouseDown = (...args) => callbacksRef.current.onMouseDown?.(...args);\n instance.onMouseUp = (...args) => callbacksRef.current.onMouseUp?.(...args);\n instance.onMouseLeave = (...args) => callbacksRef.current.onMouseLeave?.(...args);\n instance.onDraw = (...args) => callbacksRef.current.onDraw?.(...args);\n instance.onResize = () => callbacksRef.current.onResize?.();\n instance.onZoom = (scale) => callbacksRef.current.onZoom?.(scale);\n\n // Attach to handle\n engine._setInstance(instance);\n\n // Initial render\n instance.render();\n\n // Cleanup on unmount\n return () => {\n instance.destroy();\n engine._setInstance(null);\n };\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [engine]);\n\n return (\n <EngineContext.Provider value={contextValue}>\n <div\n ref={engine._containerRef}\n className={className}\n style={{\n ...style,\n }}\n >\n <canvas />\n </div>\n {/* Render children only when engine is ready */}\n {engine.isReady && children}\n </EngineContext.Provider>\n );\n}\n\n// Compound component pattern - attach draw components as static properties\nexport const CanvasTileEngine = Object.assign(CanvasTileEngineBase, {\n Rect,\n Circle,\n Image,\n GridLines,\n Line,\n Text,\n Path,\n StaticRect,\n StaticCircle,\n StaticImage,\n DrawFunction,\n});\n","import { createContext, useContext } from \"react\";\nimport type { EngineHandle } from \"../hooks/useCanvasTileEngine\";\n\nexport interface EngineContextValue {\n engine: EngineHandle;\n /** Request a re-render of the canvas */\n requestRender: () => void;\n}\n\nexport const EngineContext = createContext<EngineContextValue | null>(null);\n\n/**\n * Hook to access the engine context from child components.\n * Must be used within a CanvasTileEngine component.\n */\nexport function useEngineContext(): EngineContextValue {\n const context = useContext(EngineContext);\n\n if (!context) {\n throw new Error(\"useEngineContext must be used within a CanvasTileEngine component\");\n }\n\n return context;\n}\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { DrawObject } from \"@canvas-tile-engine/core\";\n\nexport interface RectProps {\n items: DrawObject | DrawObject[];\n layer?: number;\n}\n\n/**\n * Draws rectangles on the canvas.\n */\nexport const Rect = memo(function Rect({ items, layer = 1 }: RectProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawRect(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { DrawObject } from \"@canvas-tile-engine/core\";\n\nexport interface CircleProps {\n items: DrawObject | DrawObject[];\n layer?: number;\n}\n\n/**\n * Draws circles on the canvas.\n */\nexport const Circle = memo(function Circle({ items, layer = 1 }: CircleProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawCircle(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport { ImageItem } from \"@canvas-tile-engine/core\";\n\nexport interface ImageProps {\n items: ImageItem | ImageItem[];\n layer?: number;\n}\n\n/**\n * Draws images on the canvas.\n */\nexport const Image = memo(function Image({ items, layer = 1 }: ImageProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawImage(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\n\nexport interface GridLinesProps {\n cellSize: number;\n lineWidth?: number;\n strokeStyle?: string;\n layer?: number;\n}\n\n/**\n * Draws grid lines on the canvas.\n * Multiple GridLines can share the same layer (additive drawing).\n */\nexport const GridLines = memo(function GridLines({ cellSize, lineWidth = 1, strokeStyle = \"black\", layer = 0 }: GridLinesProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawGridLines(cellSize, lineWidth, strokeStyle, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, cellSize, lineWidth, strokeStyle, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Coords } from \"@canvas-tile-engine/core\";\n\nexport interface LineProps {\n items: { from: Coords; to: Coords } | { from: Coords; to: Coords }[];\n style?: { strokeStyle?: string; lineWidth?: number };\n layer?: number;\n}\n\n/**\n * Draws lines on the canvas.\n */\nexport const Line = memo(function Line({ items, style, layer = 1 }: LineProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawLine(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Coords } from \"@canvas-tile-engine/core\";\n\nexport interface TextProps {\n items: { coords: Coords; text: string } | { coords: Coords; text: string }[];\n style?: {\n fillStyle?: string;\n font?: string;\n textAlign?: CanvasTextAlign;\n textBaseline?: CanvasTextBaseline;\n };\n layer?: number;\n}\n\n/**\n * Draws text on the canvas.\n */\nexport const Text = memo(function Text({ items, style, layer = 2 }: TextProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawText(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Coords } from \"@canvas-tile-engine/core\";\n\nexport interface PathProps {\n items: Coords[] | Coords[][];\n style?: { strokeStyle?: string; lineWidth?: number };\n layer?: number;\n}\n\n/**\n * Draws paths/polylines on the canvas.\n */\nexport const Path = memo(function Path({ items, style, layer = 1 }: PathProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawPath(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { DrawObject } from \"@canvas-tile-engine/core\";\n\nexport interface StaticRectProps {\n items: DrawObject[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static rectangles with caching for performance.\n * Ideal for large datasets that don't change frequently.\n */\nexport const StaticRect = memo(function StaticRect({ items, cacheKey, layer = 1 }: StaticRectProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n // Clear previous cache if cacheKey changed\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticRect(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n // Cleanup cache on unmount\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { DrawObject } from \"@canvas-tile-engine/core\";\n\nexport interface StaticCircleProps {\n items: DrawObject[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static circles with caching for performance.\n */\nexport const StaticCircle = memo(function StaticCircle({ items, cacheKey, layer = 1 }: StaticCircleProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticCircle(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport { ImageItem } from \"@canvas-tile-engine/core\";\n\nexport interface StaticImageProps {\n items: ImageItem[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static images with caching for performance.\n * Ideal for terrain tiles or static decorations.\n */\nexport const StaticImage = memo(function StaticImage({ items, cacheKey, layer = 1 }: StaticImageProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticImage(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { CanvasTileEngineConfig, Coords } from \"@canvas-tile-engine/core\";\n\nexport interface DrawFunctionProps {\n /** The draw function to execute */\n children: (ctx: CanvasRenderingContext2D, coords: Coords, config: Required<CanvasTileEngineConfig>) => void;\n layer?: number;\n}\n\n/**\n * Custom draw function component.\n * Allows arbitrary canvas drawing within the engine's render cycle.\n * Multiple DrawFunction components can share the same layer (additive drawing).\n *\n * @example\n * ```tsx\n * <DrawFunction layer={3}>\n * {(ctx, coords, config) => {\n * ctx.fillStyle = \"red\";\n * ctx.fillRect(config.size.width / 2 - 5, config.size.height / 2 - 5, 10, 10);\n * }}\n * </DrawFunction>\n * ```\n */\nexport const DrawFunction = memo(function DrawFunction({ children, layer = 1 }: DrawFunctionProps) {\n const { engine, requestRender } = useEngineContext();\n const fnRef = useRef(children);\n\n // Keep function ref updated\n useEffect(() => {\n fnRef.current = children;\n });\n\n useEffect(() => {\n const handle = engine.addDrawFunction((ctx, coords, config) => {\n fnRef.current(ctx, coords, config);\n }, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, layer, requestRender]);\n\n return null;\n});\n","import { useRef, useCallback, useState, useMemo } from \"react\";\nimport type {\n CanvasTileEngine as CanvasTileEngineCore,\n CanvasTileEngineConfig,\n Coords,\n DrawObject,\n EventHandlers,\n LayerHandle,\n} from \"@canvas-tile-engine/core\";\n\n/** Dummy handle returned when engine is not ready */\nconst DUMMY_LAYER_HANDLE: LayerHandle = { layer: -1, id: Symbol(\"dummy\") };\n\n/** Default config when engine is not ready */\nconst DEFAULT_CONFIG: Required<CanvasTileEngineConfig> = {\n size: { width: 0, height: 0, minWidth: 100, minHeight: 100, maxWidth: Infinity, maxHeight: Infinity },\n scale: 1,\n minScale: 0.5,\n maxScale: 2,\n backgroundColor: \"#ffffff\",\n gridAligned: false,\n renderer: \"canvas\",\n eventHandlers: {\n drag: true,\n zoom: true,\n hover: false,\n click: false,\n rightClick: false,\n resize: false,\n },\n bounds: {\n minX: -Infinity,\n maxX: Infinity,\n minY: -Infinity,\n maxY: Infinity,\n },\n coordinates: {\n enabled: false,\n shownScaleRange: { min: 0, max: Infinity },\n },\n cursor: {\n default: \"default\",\n move: \"move\",\n },\n debug: {\n enabled: false,\n hud: {\n enabled: false,\n topLeftCoordinates: false,\n coordinates: false,\n scale: false,\n tilesInView: false,\n fps: false,\n },\n eventHandlers: {\n click: false,\n hover: false,\n drag: false,\n zoom: false,\n resize: false,\n },\n },\n};\n\n/**\n * Engine handle returned by useCanvasTileEngine hook.\n * Provides access to engine methods with proper typing.\n * \n * All methods return default/dummy values when engine is not ready,\n * allowing safe usage without null checks.\n */\nexport interface EngineHandle {\n /** @internal - Used by CanvasTileEngine component */\n readonly _containerRef: React.RefObject<HTMLDivElement>;\n /** @internal - Used by CanvasTileEngine component */\n _setInstance: (engine: CanvasTileEngineCore | null) => void;\n\n /** Whether the engine is ready (mounted and initialized) */\n readonly isReady: boolean;\n\n /** The underlying engine instance (null until component mounts) */\n readonly instance: CanvasTileEngineCore | null;\n\n /** Render a frame */\n render(): void;\n\n /** Get current center coordinates */\n getCenterCoords(): Coords;\n\n /** Get visible world coordinate bounds of the viewport */\n getVisibleBounds(): { minX: number; maxX: number; minY: number; maxY: number };\n\n /** Update center coordinates */\n updateCoords(center: Coords): void;\n\n /** Animate to target coordinates */\n goCoords(x: number, y: number, durationMs?: number, onComplete?: () => void): void;\n\n /** Resize the canvas */\n resize(width: number, height: number, durationMs?: number, onComplete?: () => void): void;\n\n /** Get current canvas size */\n getSize(): { width: number; height: number };\n\n /** Get current canvas scale */\n getScale(): number;\n\n /** Zoom in by a factor (default: 1.5) */\n zoomIn(factor?: number): void;\n\n /** Zoom out by a factor (default: 1.5) */\n zoomOut(factor?: number): void;\n\n /** Get current config */\n getConfig(): Required<CanvasTileEngineConfig>;\n\n /** Set map boundaries */\n setBounds(bounds: { minX: number; maxX: number; minY: number; maxY: number }): void;\n\n /** Dynamically update event handlers at runtime */\n setEventHandlers(handlers: Partial<EventHandlers>): void;\n\n /** Draw rectangles */\n drawRect(items: DrawObject | DrawObject[], layer?: number): LayerHandle;\n\n /** Draw static rectangles (cached) */\n drawStaticRect(items: DrawObject[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw circles */\n drawCircle(items: DrawObject | DrawObject[], layer?: number): LayerHandle;\n\n /** Draw static circles (cached) */\n drawStaticCircle(items: DrawObject[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw lines */\n drawLine(\n items: { from: Coords; to: Coords } | { from: Coords; to: Coords }[],\n style?: { strokeStyle?: string; lineWidth?: number },\n layer?: number\n ): LayerHandle;\n\n /** Draw text */\n drawText(\n items: { coords: Coords; text: string } | { coords: Coords; text: string }[],\n style?: { fillStyle?: string; font?: string; textAlign?: CanvasTextAlign; textBaseline?: CanvasTextBaseline },\n layer?: number\n ): LayerHandle;\n\n /** Draw paths/polylines */\n drawPath(\n items: Coords[] | Coords[][],\n style?: { strokeStyle?: string; lineWidth?: number },\n layer?: number\n ): LayerHandle;\n\n /** Draw images */\n drawImage(\n items:\n | (Omit<DrawObject, \"style\"> & { img: HTMLImageElement })\n | (Omit<DrawObject, \"style\"> & { img: HTMLImageElement })[],\n layer?: number\n ): LayerHandle;\n\n /** Draw static images (cached) */\n drawStaticImage(\n items: (Omit<DrawObject, \"style\"> & { img: HTMLImageElement })[],\n cacheKey: string,\n layer?: number\n ): LayerHandle;\n\n /** Draw grid lines */\n drawGridLines(cellSize: number, lineWidth?: number, strokeStyle?: string, layer?: number): LayerHandle;\n\n /** Add custom draw function */\n addDrawFunction(\n fn: (ctx: CanvasRenderingContext2D, coords: Coords, config: Required<CanvasTileEngineConfig>) => void,\n layer?: number\n ): LayerHandle;\n\n /** Clear a specific layer */\n clearLayer(layer: number): void;\n\n /** Clear all layers */\n clearAll(): void;\n\n /** Clear static cache */\n clearStaticCache(cacheKey?: string): void;\n\n /** Remove a previously registered draw callback */\n removeLayerHandle(handle: LayerHandle): void;\n\n /** Image loader instance (undefined until engine mounts) */\n readonly images: CanvasTileEngineCore[\"images\"] | undefined;\n}\n\n/**\n * React hook that creates an engine handle for use with CanvasTileEngine component.\n *\n * @returns Engine handle to pass to CanvasTileEngine component\n *\n * @example\n * ```tsx\n * function App() {\n * const mainMap = useCanvasTileEngine();\n * const miniMap = useCanvasTileEngine();\n *\n * useEffect(() => {\n * if (mainMap.isReady && miniMap.isReady) {\n * // Both engines are ready, draw items\n * mainMap.drawGridLines(50);\n * mainMap.render();\n * }\n * }, [mainMap.isReady, miniMap.isReady]);\n *\n * return (\n * <>\n * <CanvasTileEngine engine={mainMap} config={...} />\n * <CanvasTileEngine engine={miniMap} config={...} />\n * </>\n * );\n * }\n * ```\n */\nexport function useCanvasTileEngine(): EngineHandle {\n const instanceRef = useRef<CanvasTileEngineCore | null>(null);\n const containerRef = useRef<HTMLDivElement>(null!);\n // _isReady state is only used to trigger re-renders, actual value is read from isReadyRef\n const [, setIsReady] = useState(false);\n // Keep isReady in a ref so the handle getter can read it without recreating handle\n const isReadyRef = useRef(false);\n\n const setInstance = useCallback((engine: CanvasTileEngineCore | null) => {\n instanceRef.current = engine;\n isReadyRef.current = engine !== null;\n setIsReady(engine !== null);\n }, []);\n\n // Create stable handle object using useMemo\n // Note: isReady is NOT in deps - we read from isReadyRef to keep handle stable\n const handle = useMemo<EngineHandle>(\n () => ({\n _containerRef: containerRef,\n _setInstance: setInstance,\n\n get isReady() {\n return isReadyRef.current;\n },\n\n get instance() {\n return instanceRef.current;\n },\n\n get images() {\n return instanceRef.current?.images;\n },\n\n render() {\n instanceRef.current?.render();\n },\n\n getCenterCoords() {\n return instanceRef.current?.getCenterCoords() ?? { x: 0, y: 0 };\n },\n\n getVisibleBounds() {\n return instanceRef.current?.getVisibleBounds() ?? { minX: 0, maxX: 0, minY: 0, maxY: 0 };\n },\n\n updateCoords(center: Coords) {\n instanceRef.current?.updateCoords(center);\n },\n\n goCoords(x: number, y: number, durationMs?: number, onComplete?: () => void) {\n instanceRef.current?.goCoords(x, y, durationMs, onComplete);\n },\n\n resize(width: number, height: number, durationMs?: number, onComplete?: () => void) {\n instanceRef.current?.resize(width, height, durationMs, onComplete);\n },\n\n getSize() {\n return instanceRef.current?.getSize() ?? { width: 0, height: 0 };\n },\n\n getScale() {\n return instanceRef.current?.getScale() ?? 1;\n },\n\n zoomIn(factor?: number) {\n instanceRef.current?.zoomIn(factor);\n },\n\n zoomOut(factor?: number) {\n instanceRef.current?.zoomOut(factor);\n },\n\n getConfig() {\n return instanceRef.current?.getConfig() ?? DEFAULT_CONFIG;\n },\n\n setBounds(bounds) {\n instanceRef.current?.setBounds(bounds);\n },\n\n setEventHandlers(handlers) {\n instanceRef.current?.setEventHandlers(handlers);\n },\n\n drawRect(items, layer) {\n return instanceRef.current?.drawRect(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticRect(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticRect(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawCircle(items, layer) {\n return instanceRef.current?.drawCircle(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticCircle(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticCircle(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawLine(items, style, layer) {\n return instanceRef.current?.drawLine(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawText(items, style, layer) {\n return instanceRef.current?.drawText(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawPath(items, style, layer) {\n return instanceRef.current?.drawPath(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawImage(items, layer) {\n return instanceRef.current?.drawImage(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticImage(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticImage(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawGridLines(cellSize, lineWidth, strokeStyle, layer) {\n return instanceRef.current?.drawGridLines(cellSize, lineWidth, strokeStyle, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n addDrawFunction(fn, layer) {\n return instanceRef.current?.addDrawFunction(fn, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n clearLayer(layer) {\n instanceRef.current?.clearLayer(layer);\n },\n\n clearAll() {\n instanceRef.current?.clearAll();\n },\n\n clearStaticCache(cacheKey) {\n instanceRef.current?.clearStaticCache(cacheKey);\n },\n\n removeLayerHandle(handle) {\n instanceRef.current?.removeLayerHandle(handle);\n },\n }),\n [setInstance]\n );\n\n return handle;\n}\n","// Main component\nexport { CanvasTileEngine } from \"./components\";\n\n// Draw components\nexport {\n type RectProps,\n type CircleProps,\n type ImageProps,\n type GridLinesProps,\n type LineProps,\n type TextProps,\n type PathProps,\n type StaticRectProps,\n type StaticCircleProps,\n type StaticImageProps,\n type DrawFunctionProps,\n} from \"./components\";\n\n// Hooks\nexport { useCanvasTileEngine } from \"./hooks\";\n\n// Context\nexport { useEngineContext, type EngineContextValue } from \"./context\";\n\n// Types\nexport type {\n CanvasTileEngineProps,\n CanvasTileEngineConfig,\n Coords,\n DrawObject,\n EventHandlers,\n onClickCallback,\n onHoverCallback,\n onMouseDownCallback,\n onMouseUpCallback,\n onMouseLeaveCallback,\n onDrawCallback,\n Rect,\n Line,\n Circle,\n Text,\n Path,\n ImageItem,\n} from \"./types\";\nexport type { EngineHandle } from \"./hooks/useCanvasTileEngine\";\n\n// Re-export core class with different name\nexport { CanvasTileEngine as CanvasTileEngineCore } from \"@canvas-tile-engine/core\";\n"],"mappings":"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","names":["useEffect","useRef","useCallback","useMemo","CanvasTileEngineCore","createContext","useContext","EngineContext","useEngineContext","context","useEffect","memo","Rect","memo","items","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Circle","memo","items","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Image","memo","items","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","GridLines","memo","cellSize","lineWidth","strokeStyle","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Line","memo","items","style","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Text","memo","items","style","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Path","memo","items","style","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","useRef","memo","StaticRect","memo","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","useRef","useEffect","handle","useEffect","useRef","memo","StaticCircle","memo","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","useRef","useEffect","handle","useEffect","useRef","memo","StaticImage","memo","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","useRef","useEffect","handle","useEffect","useRef","memo","DrawFunction","memo","children","layer","engine","requestRender","useEngineContext","fnRef","useRef","useEffect","handle","ctx","coords","config","jsx","jsxs","CanvasTileEngineBase","engine","config","center","className","style","children","onCoordsChange","onClick","onRightClick","onHover","onMouseDown","onMouseUp","onMouseLeave","onDraw","onResize","onZoom","callbacksRef","useRef","useEffect","rafIdRef","requestRender","useCallback","contextValue","useMemo","container","instance","CanvasTileEngineCore","coords","args","scale","EngineContext","CanvasTileEngine","Rect","Circle","Image","GridLines","Line","Text","Path","StaticRect","StaticCircle","StaticImage","DrawFunction","useRef","useCallback","useState","useMemo","DUMMY_LAYER_HANDLE","DEFAULT_CONFIG","useCanvasTileEngine","instanceRef","containerRef","setIsReady","isReadyRef","setInstance","engine","center","x","y","durationMs","onComplete","width","height","factor","bounds","handlers","items","layer","cacheKey","style","cellSize","lineWidth","strokeStyle","fn","handle","CanvasTileEngine"]}
|
|
1
|
+
{"version":3,"sources":["../src/components/CanvasTileEngine.tsx","../src/context/EngineContext.tsx","../src/components/draw/Rect.tsx","../src/components/draw/Circle.tsx","../src/components/draw/Image.tsx","../src/components/draw/GridLines.tsx","../src/components/draw/Line.tsx","../src/components/draw/Text.tsx","../src/components/draw/Path.tsx","../src/components/draw/StaticRect.tsx","../src/components/draw/StaticCircle.tsx","../src/components/draw/StaticImage.tsx","../src/components/draw/DrawFunction.tsx","../src/hooks/useCanvasTileEngine.ts","../src/index.ts"],"sourcesContent":["import { useEffect, useRef, useCallback, useMemo } from \"react\";\nimport { CanvasTileEngine as CanvasTileEngineCore } from \"@canvas-tile-engine/core\";\nimport { EngineContext, type EngineContextValue } from \"../context/EngineContext\";\nimport type { CanvasTileEngineProps } from \"../types\";\n\n// Import draw components for compound pattern\nimport { Rect } from \"./draw/Rect\";\nimport { Circle } from \"./draw/Circle\";\nimport { Image } from \"./draw/Image\";\nimport { GridLines } from \"./draw/GridLines\";\nimport { Line } from \"./draw/Line\";\nimport { Text } from \"./draw/Text\";\nimport { Path } from \"./draw/Path\";\nimport { StaticRect } from \"./draw/StaticRect\";\nimport { StaticCircle } from \"./draw/StaticCircle\";\nimport { StaticImage } from \"./draw/StaticImage\";\nimport { DrawFunction } from \"./draw/DrawFunction\";\n\n/**\n * React component that renders a CanvasTileEngine.\n * Supports both imperative API (via engine handle) and declarative API (via children).\n *\n * @example Declarative API with compound components\n * ```tsx\n * function App() {\n * const engine = useCanvasTileEngine();\n *\n * return (\n * <CanvasTileEngine engine={engine} config={config}>\n * <CanvasTileEngine.GridLines cellSize={50} layer={0} />\n * <CanvasTileEngine.Image items={imageItems} layer={1} />\n * <CanvasTileEngine.Circle items={markers} layer={2} />\n * </CanvasTileEngine>\n * );\n * }\n * ```\n *\n * @example Imperative API\n * ```tsx\n * function App() {\n * const engine = useCanvasTileEngine();\n *\n * useEffect(() => {\n * if (engine.isReady) {\n * engine.drawGridLines(50);\n * engine.render();\n * }\n * }, [engine.isReady]);\n *\n * return <CanvasTileEngine engine={engine} config={config} />;\n * }\n * ```\n */\nfunction CanvasTileEngineBase({\n engine,\n config,\n center = { x: 0, y: 0 },\n className,\n style,\n children,\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n}: CanvasTileEngineProps) {\n // Stable callback refs\n const callbacksRef = useRef({\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n });\n\n // Update callback refs\n useEffect(() => {\n callbacksRef.current = {\n onCoordsChange,\n onClick,\n onRightClick,\n onHover,\n onMouseDown,\n onMouseUp,\n onMouseLeave,\n onDraw,\n onResize,\n onZoom,\n };\n });\n\n // Debounced render - multiple draw components calling requestRender\n // in the same frame will trigger only one render\n const rafIdRef = useRef<number | null>(null);\n const requestRender = useCallback(() => {\n if (rafIdRef.current !== null) return;\n rafIdRef.current = requestAnimationFrame(() => {\n rafIdRef.current = null;\n engine.render();\n });\n }, [engine]);\n\n // Cleanup RAF on unmount\n useEffect(() => {\n return () => {\n if (rafIdRef.current !== null) {\n cancelAnimationFrame(rafIdRef.current);\n }\n };\n }, []);\n\n // Context value\n const contextValue = useMemo<EngineContextValue>(\n () => ({\n engine,\n requestRender,\n }),\n [engine, requestRender]\n );\n\n // Initialize engine when component mounts\n // Note: config and center are intentionally not in deps - we only want to create the engine once\n // Callbacks are accessed via callbacksRef which is always up-to-date\n useEffect(() => {\n const container = engine._containerRef.current;\n\n if (!container) {\n return;\n }\n\n // Create engine instance\n const instance = new CanvasTileEngineCore(container, config, center);\n\n // Set up callbacks using stable refs\n instance.onCoordsChange = (coords) => callbacksRef.current.onCoordsChange?.(coords);\n instance.onClick = (...args) => callbacksRef.current.onClick?.(...args);\n instance.onRightClick = (...args) => callbacksRef.current.onRightClick?.(...args);\n instance.onHover = (...args) => callbacksRef.current.onHover?.(...args);\n instance.onMouseDown = (...args) => callbacksRef.current.onMouseDown?.(...args);\n instance.onMouseUp = (...args) => callbacksRef.current.onMouseUp?.(...args);\n instance.onMouseLeave = (...args) => callbacksRef.current.onMouseLeave?.(...args);\n instance.onDraw = (...args) => callbacksRef.current.onDraw?.(...args);\n instance.onResize = () => callbacksRef.current.onResize?.();\n instance.onZoom = (scale) => callbacksRef.current.onZoom?.(scale);\n\n // Attach to handle\n engine._setInstance(instance);\n\n // Initial render\n instance.render();\n\n // Cleanup on unmount\n return () => {\n instance.destroy();\n engine._setInstance(null);\n };\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [engine]);\n\n return (\n <EngineContext.Provider value={contextValue}>\n <div\n ref={engine._containerRef}\n className={className}\n style={{\n ...style,\n }}\n >\n <canvas />\n </div>\n {/* Render children only when engine is ready */}\n {engine.isReady && children}\n </EngineContext.Provider>\n );\n}\n\n// Compound component pattern - attach draw components as static properties\nexport const CanvasTileEngine = Object.assign(CanvasTileEngineBase, {\n Rect,\n Circle,\n Image,\n GridLines,\n Line,\n Text,\n Path,\n StaticRect,\n StaticCircle,\n StaticImage,\n DrawFunction,\n});\n","import { createContext, useContext } from \"react\";\nimport type { EngineHandle } from \"../hooks/useCanvasTileEngine\";\n\nexport interface EngineContextValue {\n engine: EngineHandle;\n /** Request a re-render of the canvas */\n requestRender: () => void;\n}\n\nexport const EngineContext = createContext<EngineContextValue | null>(null);\n\n/**\n * Hook to access the engine context from child components.\n * Must be used within a CanvasTileEngine component.\n */\nexport function useEngineContext(): EngineContextValue {\n const context = useContext(EngineContext);\n\n if (!context) {\n throw new Error(\"useEngineContext must be used within a CanvasTileEngine component\");\n }\n\n return context;\n}\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Rect as RectType } from \"@canvas-tile-engine/core\";\n\nexport interface RectProps {\n items: RectType | RectType[];\n layer?: number;\n}\n\n/**\n * Draws rectangles on the canvas.\n */\nexport const Rect = memo(function Rect({ items, layer = 1 }: RectProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawRect(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Circle as CircleType } from \"@canvas-tile-engine/core\";\n\nexport interface CircleProps {\n items: CircleType | CircleType[];\n layer?: number;\n}\n\n/**\n * Draws circles on the canvas.\n */\nexport const Circle = memo(function Circle({ items, layer = 1 }: CircleProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawCircle(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport { ImageItem } from \"@canvas-tile-engine/core\";\n\nexport interface ImageProps {\n items: ImageItem | ImageItem[];\n layer?: number;\n}\n\n/**\n * Draws images on the canvas.\n */\nexport const Image = memo(function Image({ items, layer = 1 }: ImageProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawImage(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\n\nexport interface GridLinesProps {\n cellSize: number;\n lineWidth?: number;\n strokeStyle?: string;\n layer?: number;\n}\n\n/**\n * Draws grid lines on the canvas.\n * Multiple GridLines can share the same layer (additive drawing).\n */\nexport const GridLines = memo(function GridLines({ cellSize, lineWidth = 1, strokeStyle = \"black\", layer = 0 }: GridLinesProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawGridLines(cellSize, lineWidth, strokeStyle, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, cellSize, lineWidth, strokeStyle, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Line as LineType } from \"@canvas-tile-engine/core\";\n\nexport interface LineProps {\n items: LineType | LineType[];\n style?: { strokeStyle?: string; lineWidth?: number };\n layer?: number;\n}\n\n/**\n * Draws lines on the canvas.\n */\nexport const Line = memo(function Line({ items, style, layer = 1 }: LineProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawLine(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Text as TextType } from \"@canvas-tile-engine/core\";\n\nexport interface TextProps {\n items: TextType | TextType[];\n layer?: number;\n}\n\n/**\n * Draws text on the canvas.\n * @example\n * ```tsx\n * <Text\n * items={{\n * x: 0,\n * y: 0,\n * text: \"Hello\",\n * size: 1,\n * style: { fillStyle: \"black\", fontFamily: \"Arial\" }\n * }}\n * />\n * ```\n */\nexport const Text = memo(function Text({ items, layer = 2 }: TextProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawText(items, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Path as PathType } from \"@canvas-tile-engine/core\";\n\nexport interface PathProps {\n items: PathType | PathType[];\n style?: { strokeStyle?: string; lineWidth?: number };\n layer?: number;\n}\n\n/**\n * Draws paths/polylines on the canvas.\n */\nexport const Path = memo(function Path({ items, style, layer = 1 }: PathProps) {\n const { engine, requestRender } = useEngineContext();\n\n useEffect(() => {\n const handle = engine.drawPath(items, style, layer);\n requestRender();\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, style, layer, requestRender]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Rect as RectType } from \"@canvas-tile-engine/core\";\n\nexport interface StaticRectProps {\n items: RectType[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static rectangles with caching for performance.\n * Ideal for large datasets that don't change frequently.\n */\nexport const StaticRect = memo(function StaticRect({ items, cacheKey, layer = 1 }: StaticRectProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n // Clear previous cache if cacheKey changed\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticRect(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n // Cleanup cache on unmount\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { Circle as CircleType } from \"@canvas-tile-engine/core\";\n\nexport interface StaticCircleProps {\n items: CircleType[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static circles with caching for performance.\n */\nexport const StaticCircle = memo(function StaticCircle({ items, cacheKey, layer = 1 }: StaticCircleProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticCircle(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport { ImageItem } from \"@canvas-tile-engine/core\";\n\nexport interface StaticImageProps {\n items: ImageItem[];\n cacheKey: string;\n layer?: number;\n}\n\n/**\n * Draws static images with caching for performance.\n * Ideal for terrain tiles or static decorations.\n */\nexport const StaticImage = memo(function StaticImage({ items, cacheKey, layer = 1 }: StaticImageProps) {\n const { engine, requestRender } = useEngineContext();\n const prevCacheKeyRef = useRef<string>(cacheKey);\n\n useEffect(() => {\n if (items.length === 0) {\n return;\n }\n\n if (prevCacheKeyRef.current !== cacheKey) {\n engine.clearStaticCache(prevCacheKeyRef.current);\n prevCacheKeyRef.current = cacheKey;\n }\n\n const handle = engine.drawStaticImage(items, cacheKey, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, items, cacheKey, layer, requestRender]);\n\n useEffect(() => {\n return () => {\n engine.clearStaticCache(cacheKey);\n };\n }, [engine, cacheKey]);\n\n return null;\n});\n","import { useEffect, useRef, memo } from \"react\";\nimport { useEngineContext } from \"../../context/EngineContext\";\nimport type { CanvasTileEngineConfig, Coords } from \"@canvas-tile-engine/core\";\n\nexport interface DrawFunctionProps {\n /** The draw function to execute */\n children: (ctx: CanvasRenderingContext2D, coords: Coords, config: Required<CanvasTileEngineConfig>) => void;\n layer?: number;\n}\n\n/**\n * Custom draw function component.\n * Allows arbitrary canvas drawing within the engine's render cycle.\n * Multiple DrawFunction components can share the same layer (additive drawing).\n *\n * @example\n * ```tsx\n * <DrawFunction layer={3}>\n * {(ctx, coords, config) => {\n * ctx.fillStyle = \"red\";\n * ctx.fillRect(config.size.width / 2 - 5, config.size.height / 2 - 5, 10, 10);\n * }}\n * </DrawFunction>\n * ```\n */\nexport const DrawFunction = memo(function DrawFunction({ children, layer = 1 }: DrawFunctionProps) {\n const { engine, requestRender } = useEngineContext();\n const fnRef = useRef(children);\n\n // Keep function ref updated\n useEffect(() => {\n fnRef.current = children;\n });\n\n useEffect(() => {\n const handle = engine.addDrawFunction((ctx, coords, config) => {\n fnRef.current(ctx, coords, config);\n }, layer);\n requestRender();\n\n return () => {\n if (handle) {\n engine.removeLayerHandle(handle);\n }\n };\n }, [engine, layer, requestRender]);\n\n return null;\n});\n","import { useRef, useCallback, useState, useMemo } from \"react\";\nimport type {\n CanvasTileEngine as CanvasTileEngineCore,\n CanvasTileEngineConfig,\n Coords,\n EventHandlers,\n LayerHandle,\n ImageItem,\n Text,\n Circle,\n Line,\n Rect,\n} from \"@canvas-tile-engine/core\";\n\n/** Dummy handle returned when engine is not ready */\nconst DUMMY_LAYER_HANDLE: LayerHandle = { layer: -1, id: Symbol(\"dummy\") };\n\n/** Default config when engine is not ready */\nconst DEFAULT_CONFIG: Required<CanvasTileEngineConfig> = {\n size: { width: 0, height: 0, minWidth: 100, minHeight: 100, maxWidth: Infinity, maxHeight: Infinity },\n responsive: false,\n scale: 1,\n minScale: 0.5,\n maxScale: 2,\n backgroundColor: \"#ffffff\",\n gridAligned: false,\n renderer: \"canvas\",\n eventHandlers: {\n drag: true,\n zoom: true,\n hover: false,\n click: false,\n rightClick: false,\n resize: false,\n },\n bounds: {\n minX: -Infinity,\n maxX: Infinity,\n minY: -Infinity,\n maxY: Infinity,\n },\n coordinates: {\n enabled: false,\n shownScaleRange: { min: 0, max: Infinity },\n },\n cursor: {\n default: \"default\",\n move: \"move\",\n },\n debug: {\n enabled: false,\n hud: {\n enabled: false,\n topLeftCoordinates: false,\n coordinates: false,\n scale: false,\n tilesInView: false,\n fps: false,\n },\n eventHandlers: {\n click: false,\n hover: false,\n drag: false,\n zoom: false,\n resize: false,\n },\n },\n};\n\n/**\n * Engine handle returned by useCanvasTileEngine hook.\n * Provides access to engine methods with proper typing.\n *\n * All methods return default/dummy values when engine is not ready,\n * allowing safe usage without null checks.\n */\nexport interface EngineHandle {\n /** @internal - Used by CanvasTileEngine component */\n readonly _containerRef: React.RefObject<HTMLDivElement>;\n /** @internal - Used by CanvasTileEngine component */\n _setInstance: (engine: CanvasTileEngineCore | null) => void;\n\n /** Whether the engine is ready (mounted and initialized) */\n readonly isReady: boolean;\n\n /** The underlying engine instance (null until component mounts) */\n readonly instance: CanvasTileEngineCore | null;\n\n /** Render a frame */\n render(): void;\n\n /** Get current center coordinates */\n getCenterCoords(): Coords;\n\n /** Get visible world coordinate bounds of the viewport */\n getVisibleBounds(): { minX: number; maxX: number; minY: number; maxY: number };\n\n /** Update center coordinates */\n updateCoords(center: Coords): void;\n\n /** Animate to target coordinates */\n goCoords(x: number, y: number, durationMs?: number, onComplete?: () => void): void;\n\n /** Resize the canvas */\n resize(width: number, height: number, durationMs?: number, onComplete?: () => void): void;\n\n /** Get current canvas size */\n getSize(): { width: number; height: number };\n\n /** Get current canvas scale */\n getScale(): number;\n\n /** Set the canvas scale directly, clamped to min/max bounds. */\n setScale(newScale: number): void;\n\n /** Zoom in by a factor (default: 1.5) */\n zoomIn(factor?: number): void;\n\n /** Zoom out by a factor (default: 1.5) */\n zoomOut(factor?: number): void;\n\n /** Get current config */\n getConfig(): Required<CanvasTileEngineConfig>;\n\n /** Set map boundaries */\n setBounds(bounds: { minX: number; maxX: number; minY: number; maxY: number }): void;\n\n /** Dynamically update event handlers at runtime */\n setEventHandlers(handlers: Partial<EventHandlers>): void;\n\n /** Draw rectangles */\n drawRect(items: Rect | Rect[], layer?: number): LayerHandle;\n\n /** Draw static rectangles (cached) */\n drawStaticRect(items: Rect[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw circles */\n drawCircle(items: Circle | Circle[], layer?: number): LayerHandle;\n\n /** Draw static circles (cached) */\n drawStaticCircle(items: Circle[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw lines */\n drawLine(items: Line | Line[], style?: { strokeStyle?: string; lineWidth?: number }, layer?: number): LayerHandle;\n\n /** Draw text */\n drawText(items: Text | Text[], layer?: number): LayerHandle;\n\n /** Draw paths/polylines */\n drawPath(\n items: Coords[] | Coords[][],\n style?: { strokeStyle?: string; lineWidth?: number },\n layer?: number\n ): LayerHandle;\n\n /** Draw images */\n drawImage(items: ImageItem | ImageItem[], layer?: number): LayerHandle;\n\n /** Draw static images (cached) */\n drawStaticImage(items: ImageItem[], cacheKey: string, layer?: number): LayerHandle;\n\n /** Draw grid lines */\n drawGridLines(cellSize: number, lineWidth?: number, strokeStyle?: string, layer?: number): LayerHandle;\n\n /** Add custom draw function */\n addDrawFunction(\n fn: (ctx: CanvasRenderingContext2D, coords: Coords, config: Required<CanvasTileEngineConfig>) => void,\n layer?: number\n ): LayerHandle;\n\n /** Clear a specific layer */\n clearLayer(layer: number): void;\n\n /** Clear all layers */\n clearAll(): void;\n\n /** Clear static cache */\n clearStaticCache(cacheKey?: string): void;\n\n /** Remove a previously registered draw callback */\n removeLayerHandle(handle: LayerHandle): void;\n\n /** Image loader instance (undefined until engine mounts) */\n readonly images: CanvasTileEngineCore[\"images\"] | undefined;\n\n /**\n * Load an image using the engine's image loader.\n * Returns a rejected promise if engine is not ready.\n * @param src - Image URL to load\n * @param retry - Number of retries on failure (default: 1)\n * @example\n * ```tsx\n * const img = await engine.loadImage(\"/sprites/player.png\");\n * ```\n */\n loadImage(src: string, retry?: number): Promise<HTMLImageElement>;\n}\n\n/**\n * React hook that creates an engine handle for use with CanvasTileEngine component.\n *\n * @returns Engine handle to pass to CanvasTileEngine component\n *\n * @example\n * ```tsx\n * function App() {\n * const mainMap = useCanvasTileEngine();\n * const miniMap = useCanvasTileEngine();\n *\n * useEffect(() => {\n * if (mainMap.isReady && miniMap.isReady) {\n * // Both engines are ready, draw items\n * mainMap.drawGridLines(50);\n * mainMap.render();\n * }\n * }, [mainMap.isReady, miniMap.isReady]);\n *\n * return (\n * <>\n * <CanvasTileEngine engine={mainMap} config={...} />\n * <CanvasTileEngine engine={miniMap} config={...} />\n * </>\n * );\n * }\n * ```\n */\nexport function useCanvasTileEngine(): EngineHandle {\n const instanceRef = useRef<CanvasTileEngineCore | null>(null);\n const containerRef = useRef<HTMLDivElement>(null!);\n // _isReady state is only used to trigger re-renders, actual value is read from isReadyRef\n const [, setIsReady] = useState(false);\n // Keep isReady in a ref so the handle getter can read it without recreating handle\n const isReadyRef = useRef(false);\n\n const setInstance = useCallback((engine: CanvasTileEngineCore | null) => {\n instanceRef.current = engine;\n isReadyRef.current = engine !== null;\n setIsReady(engine !== null);\n }, []);\n\n // Create stable handle object using useMemo\n // Note: isReady is NOT in deps - we read from isReadyRef to keep handle stable\n const handle = useMemo<EngineHandle>(\n () => ({\n _containerRef: containerRef,\n _setInstance: setInstance,\n\n get isReady() {\n return isReadyRef.current;\n },\n\n get instance() {\n return instanceRef.current;\n },\n\n get images() {\n return instanceRef.current?.images;\n },\n\n render() {\n instanceRef.current?.render();\n },\n\n getCenterCoords() {\n return instanceRef.current?.getCenterCoords() ?? { x: 0, y: 0 };\n },\n\n getVisibleBounds() {\n return instanceRef.current?.getVisibleBounds() ?? { minX: 0, maxX: 0, minY: 0, maxY: 0 };\n },\n\n updateCoords(center: Coords) {\n instanceRef.current?.updateCoords(center);\n },\n\n goCoords(x: number, y: number, durationMs?: number, onComplete?: () => void) {\n instanceRef.current?.goCoords(x, y, durationMs, onComplete);\n },\n\n resize(width: number, height: number, durationMs?: number, onComplete?: () => void) {\n instanceRef.current?.resize(width, height, durationMs, onComplete);\n },\n\n getSize() {\n return instanceRef.current?.getSize() ?? { width: 0, height: 0 };\n },\n\n getScale() {\n return instanceRef.current?.getScale() ?? 1;\n },\n\n setScale(newScale: number) {\n instanceRef.current?.setScale(newScale);\n },\n\n zoomIn(factor?: number) {\n instanceRef.current?.zoomIn(factor);\n },\n\n zoomOut(factor?: number) {\n instanceRef.current?.zoomOut(factor);\n },\n\n getConfig() {\n return instanceRef.current?.getConfig() ?? DEFAULT_CONFIG;\n },\n\n setBounds(bounds) {\n instanceRef.current?.setBounds(bounds);\n },\n\n setEventHandlers(handlers) {\n instanceRef.current?.setEventHandlers(handlers);\n },\n\n drawRect(items, layer) {\n return instanceRef.current?.drawRect(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticRect(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticRect(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawCircle(items, layer) {\n return instanceRef.current?.drawCircle(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticCircle(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticCircle(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawLine(items, style, layer) {\n return instanceRef.current?.drawLine(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawText(items, layer) {\n return instanceRef.current?.drawText(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawPath(items, style, layer) {\n return instanceRef.current?.drawPath(items, style, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawImage(items, layer) {\n return instanceRef.current?.drawImage(items, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawStaticImage(items, cacheKey, layer) {\n return instanceRef.current?.drawStaticImage(items, cacheKey, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n drawGridLines(cellSize, lineWidth, strokeStyle, layer) {\n return (\n instanceRef.current?.drawGridLines(cellSize, lineWidth, strokeStyle, layer) ?? DUMMY_LAYER_HANDLE\n );\n },\n\n addDrawFunction(fn, layer) {\n return instanceRef.current?.addDrawFunction(fn, layer) ?? DUMMY_LAYER_HANDLE;\n },\n\n clearLayer(layer) {\n instanceRef.current?.clearLayer(layer);\n },\n\n clearAll() {\n instanceRef.current?.clearAll();\n },\n\n clearStaticCache(cacheKey) {\n instanceRef.current?.clearStaticCache(cacheKey);\n },\n\n removeLayerHandle(handle) {\n instanceRef.current?.removeLayerHandle(handle);\n },\n\n loadImage(src: string, retry?: number) {\n if (!instanceRef.current) {\n return Promise.reject(new Error(\"Engine not ready. Wait for isReady before loading images.\"));\n }\n return instanceRef.current.images.load(src, retry);\n },\n }),\n [setInstance]\n );\n\n return handle;\n}\n","// Main component\nexport { CanvasTileEngine } from \"./components\";\n\n// Draw components\nexport {\n type RectProps,\n type CircleProps,\n type ImageProps,\n type GridLinesProps,\n type LineProps,\n type TextProps,\n type PathProps,\n type StaticRectProps,\n type StaticCircleProps,\n type StaticImageProps,\n type DrawFunctionProps,\n} from \"./components\";\n\n// Hooks\nexport { useCanvasTileEngine } from \"./hooks\";\n\n// Context\nexport { useEngineContext, type EngineContextValue } from \"./context\";\n\n// Types\nexport type {\n CanvasTileEngineProps,\n CanvasTileEngineConfig,\n Coords,\n DrawObject,\n EventHandlers,\n onClickCallback,\n onHoverCallback,\n onMouseDownCallback,\n onMouseUpCallback,\n onMouseLeaveCallback,\n onDrawCallback,\n Rect,\n Line,\n Circle,\n Text,\n Path,\n ImageItem,\n} from \"./types\";\nexport type { EngineHandle } from \"./hooks/useCanvasTileEngine\";\n\n// Re-export core class and utilities\nexport { CanvasTileEngine as CanvasTileEngineCore, gridToSize } from \"@canvas-tile-engine/core\";\n"],"mappings":"AAAA,OAAS,aAAAA,EAAW,UAAAC,EAAQ,eAAAC,GAAa,WAAAC,OAAe,QACxD,OAAS,oBAAoBC,OAA4B,2BCDzD,OAAS,iBAAAC,EAAe,cAAAC,MAAkB,QASnC,IAAMC,EAAgBF,EAAyC,IAAI,EAMnE,SAASG,GAAuC,CACnD,IAAMC,EAAUH,EAAWC,CAAa,EAExC,GAAI,CAACE,EACD,MAAM,IAAI,MAAM,mEAAmE,EAGvF,OAAOA,CACX,CCvBA,OAAS,aAAAC,EAAW,QAAAC,MAAY,QAYzB,IAAMC,EAAOC,EAAK,SAAc,CAAE,MAAAC,EAAO,MAAAC,EAAQ,CAAE,EAAc,CACpE,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAEnD,OAAAC,EAAU,IAAM,CACZ,IAAMC,EAASJ,EAAO,SAASF,EAAOC,CAAK,EAC3C,OAAAE,EAAc,EACP,IAAM,CACLG,GACAJ,EAAO,kBAAkBI,CAAM,CAEvC,CACJ,EAAG,CAACJ,EAAQF,EAAOC,EAAOE,CAAa,CAAC,EAEjC,IACX,CAAC,EC1BD,OAAS,aAAAI,EAAW,QAAAC,MAAY,QAYzB,IAAMC,EAASC,EAAK,SAAgB,CAAE,MAAAC,EAAO,MAAAC,EAAQ,CAAE,EAAgB,CAC1E,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAEnD,OAAAC,EAAU,IAAM,CACZ,IAAMC,EAASJ,EAAO,WAAWF,EAAOC,CAAK,EAC7C,OAAAE,EAAc,EACP,IAAM,CACLG,GACAJ,EAAO,kBAAkBI,CAAM,CAEvC,CACJ,EAAG,CAACJ,EAAQF,EAAOC,EAAOE,CAAa,CAAC,EAEjC,IACX,CAAC,EC1BD,OAAS,aAAAI,EAAW,QAAAC,OAAY,QAYzB,IAAMC,EAAQC,GAAK,SAAe,CAAE,MAAAC,EAAO,MAAAC,EAAQ,CAAE,EAAe,CACvE,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAEnD,OAAAC,EAAU,IAAM,CACZ,IAAMC,EAASJ,EAAO,UAAUF,EAAOC,CAAK,EAC5C,OAAAE,EAAc,EACP,IAAM,CACLG,GACAJ,EAAO,kBAAkBI,CAAM,CAEvC,CACJ,EAAG,CAACJ,EAAQF,EAAOC,EAAOE,CAAa,CAAC,EAEjC,IACX,CAAC,EC1BD,OAAS,aAAAI,GAAW,QAAAC,OAAY,QAczB,IAAMC,EAAYC,GAAK,SAAmB,CAAE,SAAAC,EAAU,UAAAC,EAAY,EAAG,YAAAC,EAAc,QAAS,MAAAC,EAAQ,CAAE,EAAmB,CAC5H,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAEnD,OAAAC,GAAU,IAAM,CACZ,IAAMC,EAASJ,EAAO,cAAcJ,EAAUC,EAAWC,EAAaC,CAAK,EAC3E,OAAAE,EAAc,EACP,IAAM,CACLG,GACAJ,EAAO,kBAAkBI,CAAM,CAEvC,CACJ,EAAG,CAACJ,EAAQJ,EAAUC,EAAWC,EAAaC,EAAOE,CAAa,CAAC,EAE5D,IACX,CAAC,EC5BD,OAAS,aAAAI,GAAW,QAAAC,OAAY,QAazB,IAAMC,EAAOC,GAAK,SAAc,CAAE,MAAAC,EAAO,MAAAC,EAAO,MAAAC,EAAQ,CAAE,EAAc,CAC3E,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAEnD,OAAAC,GAAU,IAAM,CACZ,IAAMC,EAASJ,EAAO,SAASH,EAAOC,EAAOC,CAAK,EAClD,OAAAE,EAAc,EACP,IAAM,CACLG,GACAJ,EAAO,kBAAkBI,CAAM,CAEvC,CACJ,EAAG,CAACJ,EAAQH,EAAOC,EAAOC,EAAOE,CAAa,CAAC,EAExC,IACX,CAAC,EC3BD,OAAS,aAAAI,GAAW,QAAAC,OAAY,QAwBzB,IAAMC,EAAOC,GAAK,SAAc,CAAE,MAAAC,EAAO,MAAAC,EAAQ,CAAE,EAAc,CACpE,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAEnD,OAAAC,GAAU,IAAM,CACZ,IAAMC,EAASJ,EAAO,SAASF,EAAOC,CAAK,EAC3C,OAAAE,EAAc,EACP,IAAM,CACLG,GACAJ,EAAO,kBAAkBI,CAAM,CAEvC,CACJ,EAAG,CAACJ,EAAQF,EAAOC,EAAOE,CAAa,CAAC,EAEjC,IACX,CAAC,ECtCD,OAAS,aAAAI,GAAW,QAAAC,OAAY,QAazB,IAAMC,EAAOC,GAAK,SAAc,CAAE,MAAAC,EAAO,MAAAC,EAAO,MAAAC,EAAQ,CAAE,EAAc,CAC3E,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAEnD,OAAAC,GAAU,IAAM,CACZ,IAAMC,EAASJ,EAAO,SAASH,EAAOC,EAAOC,CAAK,EAClD,OAAAE,EAAc,EACP,IAAM,CACLG,GACAJ,EAAO,kBAAkBI,CAAM,CAEvC,CACJ,EAAG,CAACJ,EAAQH,EAAOC,EAAOC,EAAOE,CAAa,CAAC,EAExC,IACX,CAAC,EC3BD,OAAS,aAAAI,EAAW,UAAAC,GAAQ,QAAAC,OAAY,QAcjC,IAAMC,EAAaC,GAAK,SAAoB,CAAE,MAAAC,EAAO,SAAAC,EAAU,MAAAC,EAAQ,CAAE,EAAoB,CAChG,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAC7CC,EAAkBC,GAAeN,CAAQ,EAE/C,OAAAO,EAAU,IAAM,CACZ,GAAIR,EAAM,SAAW,EACjB,OAIAM,EAAgB,UAAYL,IAC5BE,EAAO,iBAAiBG,EAAgB,OAAO,EAC/CA,EAAgB,QAAUL,GAG9B,IAAMQ,EAASN,EAAO,eAAeH,EAAOC,EAAUC,CAAK,EAC3D,OAAAE,EAAc,EAEP,IAAM,CACLK,GACAN,EAAO,kBAAkBM,CAAM,CAEvC,CACJ,EAAG,CAACN,EAAQH,EAAOC,EAAUC,EAAOE,CAAa,CAAC,EAGlDI,EAAU,IACC,IAAM,CACTL,EAAO,iBAAiBF,CAAQ,CACpC,EACD,CAACE,EAAQF,CAAQ,CAAC,EAEd,IACX,CAAC,EC/CD,OAAS,aAAAS,EAAW,UAAAC,GAAQ,QAAAC,OAAY,QAajC,IAAMC,EAAeC,GAAK,SAAsB,CAAE,MAAAC,EAAO,SAAAC,EAAU,MAAAC,EAAQ,CAAE,EAAsB,CACtG,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAC7CC,EAAkBC,GAAeN,CAAQ,EAE/C,OAAAO,EAAU,IAAM,CACZ,GAAIR,EAAM,SAAW,EACjB,OAGAM,EAAgB,UAAYL,IAC5BE,EAAO,iBAAiBG,EAAgB,OAAO,EAC/CA,EAAgB,QAAUL,GAG9B,IAAMQ,EAASN,EAAO,iBAAiBH,EAAOC,EAAUC,CAAK,EAC7D,OAAAE,EAAc,EAEP,IAAM,CACLK,GACAN,EAAO,kBAAkBM,CAAM,CAEvC,CACJ,EAAG,CAACN,EAAQH,EAAOC,EAAUC,EAAOE,CAAa,CAAC,EAElDI,EAAU,IACC,IAAM,CACTL,EAAO,iBAAiBF,CAAQ,CACpC,EACD,CAACE,EAAQF,CAAQ,CAAC,EAEd,IACX,CAAC,EC5CD,OAAS,aAAAS,EAAW,UAAAC,GAAQ,QAAAC,OAAY,QAcjC,IAAMC,EAAcC,GAAK,SAAqB,CAAE,MAAAC,EAAO,SAAAC,EAAU,MAAAC,EAAQ,CAAE,EAAqB,CACnG,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAC7CC,EAAkBC,GAAeN,CAAQ,EAE/C,OAAAO,EAAU,IAAM,CACZ,GAAIR,EAAM,SAAW,EACjB,OAGAM,EAAgB,UAAYL,IAC5BE,EAAO,iBAAiBG,EAAgB,OAAO,EAC/CA,EAAgB,QAAUL,GAG9B,IAAMQ,EAASN,EAAO,gBAAgBH,EAAOC,EAAUC,CAAK,EAC5D,OAAAE,EAAc,EAEP,IAAM,CACLK,GACAN,EAAO,kBAAkBM,CAAM,CAEvC,CACJ,EAAG,CAACN,EAAQH,EAAOC,EAAUC,EAAOE,CAAa,CAAC,EAElDI,EAAU,IACC,IAAM,CACTL,EAAO,iBAAiBF,CAAQ,CACpC,EACD,CAACE,EAAQF,CAAQ,CAAC,EAEd,IACX,CAAC,EC7CD,OAAS,aAAAS,EAAW,UAAAC,GAAQ,QAAAC,OAAY,QAyBjC,IAAMC,EAAeC,GAAK,SAAsB,CAAE,SAAAC,EAAU,MAAAC,EAAQ,CAAE,EAAsB,CAC/F,GAAM,CAAE,OAAAC,EAAQ,cAAAC,CAAc,EAAIC,EAAiB,EAC7CC,EAAQC,GAAON,CAAQ,EAG7B,OAAAO,EAAU,IAAM,CACZF,EAAM,QAAUL,CACpB,CAAC,EAEDO,EAAU,IAAM,CACZ,IAAMC,EAASN,EAAO,gBAAgB,CAACO,EAAKC,EAAQC,IAAW,CAC3DN,EAAM,QAAQI,EAAKC,EAAQC,CAAM,CACrC,EAAGV,CAAK,EACR,OAAAE,EAAc,EAEP,IAAM,CACLK,GACAN,EAAO,kBAAkBM,CAAM,CAEvC,CACJ,EAAG,CAACN,EAAQD,EAAOE,CAAa,CAAC,EAE1B,IACX,CAAC,EZ0HO,OAQQ,OAAAS,EARR,QAAAC,OAAA,oBArHR,SAASC,GAAqB,CAC1B,OAAAC,EACA,OAAAC,EACA,OAAAC,EAAS,CAAE,EAAG,EAAG,EAAG,CAAE,EACtB,UAAAC,EACA,MAAAC,EACA,SAAAC,EACA,eAAAC,EACA,QAAAC,EACA,aAAAC,EACA,QAAAC,EACA,YAAAC,EACA,UAAAC,EACA,aAAAC,EACA,OAAAC,EACA,SAAAC,EACA,OAAAC,CACJ,EAA0B,CAEtB,IAAMC,EAAeC,EAAO,CACxB,eAAAX,EACA,QAAAC,EACA,aAAAC,EACA,QAAAC,EACA,YAAAC,EACA,UAAAC,EACA,aAAAC,EACA,OAAAC,EACA,SAAAC,EACA,OAAAC,CACJ,CAAC,EAGDG,EAAU,IAAM,CACZF,EAAa,QAAU,CACnB,eAAAV,EACA,QAAAC,EACA,aAAAC,EACA,QAAAC,EACA,YAAAC,EACA,UAAAC,EACA,aAAAC,EACA,OAAAC,EACA,SAAAC,EACA,OAAAC,CACJ,CACJ,CAAC,EAID,IAAMI,EAAWF,EAAsB,IAAI,EACrCG,EAAgBC,GAAY,IAAM,CAChCF,EAAS,UAAY,OACzBA,EAAS,QAAU,sBAAsB,IAAM,CAC3CA,EAAS,QAAU,KACnBnB,EAAO,OAAO,CAClB,CAAC,EACL,EAAG,CAACA,CAAM,CAAC,EAGXkB,EAAU,IACC,IAAM,CACLC,EAAS,UAAY,MACrB,qBAAqBA,EAAS,OAAO,CAE7C,EACD,CAAC,CAAC,EAGL,IAAMG,EAAeC,GACjB,KAAO,CACH,OAAAvB,EACA,cAAAoB,CACJ,GACA,CAACpB,EAAQoB,CAAa,CAC1B,EAKA,OAAAF,EAAU,IAAM,CACZ,IAAMM,EAAYxB,EAAO,cAAc,QAEvC,GAAI,CAACwB,EACD,OAIJ,IAAMC,EAAW,IAAIC,GAAqBF,EAAWvB,EAAQC,CAAM,EAGnE,OAAAuB,EAAS,eAAkBE,GAAWX,EAAa,QAAQ,iBAAiBW,CAAM,EAClFF,EAAS,QAAU,IAAIG,IAASZ,EAAa,QAAQ,UAAU,GAAGY,CAAI,EACtEH,EAAS,aAAe,IAAIG,IAASZ,EAAa,QAAQ,eAAe,GAAGY,CAAI,EAChFH,EAAS,QAAU,IAAIG,IAASZ,EAAa,QAAQ,UAAU,GAAGY,CAAI,EACtEH,EAAS,YAAc,IAAIG,IAASZ,EAAa,QAAQ,cAAc,GAAGY,CAAI,EAC9EH,EAAS,UAAY,IAAIG,IAASZ,EAAa,QAAQ,YAAY,GAAGY,CAAI,EAC1EH,EAAS,aAAe,IAAIG,IAASZ,EAAa,QAAQ,eAAe,GAAGY,CAAI,EAChFH,EAAS,OAAS,IAAIG,IAASZ,EAAa,QAAQ,SAAS,GAAGY,CAAI,EACpEH,EAAS,SAAW,IAAMT,EAAa,QAAQ,WAAW,EAC1DS,EAAS,OAAUI,GAAUb,EAAa,QAAQ,SAASa,CAAK,EAGhE7B,EAAO,aAAayB,CAAQ,EAG5BA,EAAS,OAAO,EAGT,IAAM,CACTA,EAAS,QAAQ,EACjBzB,EAAO,aAAa,IAAI,CAC5B,CAEJ,EAAG,CAACA,CAAM,CAAC,EAGPF,GAACgC,EAAc,SAAd,CAAuB,MAAOR,EAC3B,UAAAzB,EAAC,OACG,IAAKG,EAAO,cACZ,UAAWG,EACX,MAAO,CACH,GAAGC,CACP,EAEA,SAAAP,EAAC,WAAO,EACZ,EAECG,EAAO,SAAWK,GACvB,CAER,CAGO,IAAM0B,EAAmB,OAAO,OAAOhC,GAAsB,CAChE,KAAAiC,EACA,OAAAC,EACA,MAAAC,EACA,UAAAC,EACA,KAAAC,EACA,KAAAC,EACA,KAAAC,EACA,WAAAC,EACA,aAAAC,EACA,YAAAC,EACA,aAAAC,CACJ,CAAC,EavMD,OAAS,UAAAC,EAAQ,eAAAC,GAAa,YAAAC,GAAU,WAAAC,OAAe,QAevD,IAAMC,EAAkC,CAAE,MAAO,GAAI,GAAI,OAAO,OAAO,CAAE,EAGnEC,GAAmD,CACrD,KAAM,CAAE,MAAO,EAAG,OAAQ,EAAG,SAAU,IAAK,UAAW,IAAK,SAAU,IAAU,UAAW,GAAS,EACpG,WAAY,GACZ,MAAO,EACP,SAAU,GACV,SAAU,EACV,gBAAiB,UACjB,YAAa,GACb,SAAU,SACV,cAAe,CACX,KAAM,GACN,KAAM,GACN,MAAO,GACP,MAAO,GACP,WAAY,GACZ,OAAQ,EACZ,EACA,OAAQ,CACJ,KAAM,KACN,KAAM,IACN,KAAM,KACN,KAAM,GACV,EACA,YAAa,CACT,QAAS,GACT,gBAAiB,CAAE,IAAK,EAAG,IAAK,GAAS,CAC7C,EACA,OAAQ,CACJ,QAAS,UACT,KAAM,MACV,EACA,MAAO,CACH,QAAS,GACT,IAAK,CACD,QAAS,GACT,mBAAoB,GACpB,YAAa,GACb,MAAO,GACP,YAAa,GACb,IAAK,EACT,EACA,cAAe,CACX,MAAO,GACP,MAAO,GACP,KAAM,GACN,KAAM,GACN,OAAQ,EACZ,CACJ,CACJ,EA+JO,SAASC,GAAoC,CAChD,IAAMC,EAAcP,EAAoC,IAAI,EACtDQ,EAAeR,EAAuB,IAAK,EAE3C,CAAC,CAAES,CAAU,EAAIP,GAAS,EAAK,EAE/BQ,EAAaV,EAAO,EAAK,EAEzBW,EAAcV,GAAaW,GAAwC,CACrEL,EAAY,QAAUK,EACtBF,EAAW,QAAUE,IAAW,KAChCH,EAAWG,IAAW,IAAI,CAC9B,EAAG,CAAC,CAAC,EAqJL,OAjJeT,GACX,KAAO,CACH,cAAeK,EACf,aAAcG,EAEd,IAAI,SAAU,CACV,OAAOD,EAAW,OACtB,EAEA,IAAI,UAAW,CACX,OAAOH,EAAY,OACvB,EAEA,IAAI,QAAS,CACT,OAAOA,EAAY,SAAS,MAChC,EAEA,QAAS,CACLA,EAAY,SAAS,OAAO,CAChC,EAEA,iBAAkB,CACd,OAAOA,EAAY,SAAS,gBAAgB,GAAK,CAAE,EAAG,EAAG,EAAG,CAAE,CAClE,EAEA,kBAAmB,CACf,OAAOA,EAAY,SAAS,iBAAiB,GAAK,CAAE,KAAM,EAAG,KAAM,EAAG,KAAM,EAAG,KAAM,CAAE,CAC3F,EAEA,aAAaM,EAAgB,CACzBN,EAAY,SAAS,aAAaM,CAAM,CAC5C,EAEA,SAASC,EAAWC,EAAWC,EAAqBC,EAAyB,CACzEV,EAAY,SAAS,SAASO,EAAGC,EAAGC,EAAYC,CAAU,CAC9D,EAEA,OAAOC,EAAeC,EAAgBH,EAAqBC,EAAyB,CAChFV,EAAY,SAAS,OAAOW,EAAOC,EAAQH,EAAYC,CAAU,CACrE,EAEA,SAAU,CACN,OAAOV,EAAY,SAAS,QAAQ,GAAK,CAAE,MAAO,EAAG,OAAQ,CAAE,CACnE,EAEA,UAAW,CACP,OAAOA,EAAY,SAAS,SAAS,GAAK,CAC9C,EAEA,SAASa,EAAkB,CACvBb,EAAY,SAAS,SAASa,CAAQ,CAC1C,EAEA,OAAOC,EAAiB,CACpBd,EAAY,SAAS,OAAOc,CAAM,CACtC,EAEA,QAAQA,EAAiB,CACrBd,EAAY,SAAS,QAAQc,CAAM,CACvC,EAEA,WAAY,CACR,OAAOd,EAAY,SAAS,UAAU,GAAKF,EAC/C,EAEA,UAAUiB,EAAQ,CACdf,EAAY,SAAS,UAAUe,CAAM,CACzC,EAEA,iBAAiBC,EAAU,CACvBhB,EAAY,SAAS,iBAAiBgB,CAAQ,CAClD,EAEA,SAASC,EAAOC,EAAO,CACnB,OAAOlB,EAAY,SAAS,SAASiB,EAAOC,CAAK,GAAKrB,CAC1D,EAEA,eAAeoB,EAAOE,EAAUD,EAAO,CACnC,OAAOlB,EAAY,SAAS,eAAeiB,EAAOE,EAAUD,CAAK,GAAKrB,CAC1E,EAEA,WAAWoB,EAAOC,EAAO,CACrB,OAAOlB,EAAY,SAAS,WAAWiB,EAAOC,CAAK,GAAKrB,CAC5D,EAEA,iBAAiBoB,EAAOE,EAAUD,EAAO,CACrC,OAAOlB,EAAY,SAAS,iBAAiBiB,EAAOE,EAAUD,CAAK,GAAKrB,CAC5E,EAEA,SAASoB,EAAOG,EAAOF,EAAO,CAC1B,OAAOlB,EAAY,SAAS,SAASiB,EAAOG,EAAOF,CAAK,GAAKrB,CACjE,EAEA,SAASoB,EAAOC,EAAO,CACnB,OAAOlB,EAAY,SAAS,SAASiB,EAAOC,CAAK,GAAKrB,CAC1D,EAEA,SAASoB,EAAOG,EAAOF,EAAO,CAC1B,OAAOlB,EAAY,SAAS,SAASiB,EAAOG,EAAOF,CAAK,GAAKrB,CACjE,EAEA,UAAUoB,EAAOC,EAAO,CACpB,OAAOlB,EAAY,SAAS,UAAUiB,EAAOC,CAAK,GAAKrB,CAC3D,EAEA,gBAAgBoB,EAAOE,EAAUD,EAAO,CACpC,OAAOlB,EAAY,SAAS,gBAAgBiB,EAAOE,EAAUD,CAAK,GAAKrB,CAC3E,EAEA,cAAcwB,EAAUC,EAAWC,EAAaL,EAAO,CACnD,OACIlB,EAAY,SAAS,cAAcqB,EAAUC,EAAWC,EAAaL,CAAK,GAAKrB,CAEvF,EAEA,gBAAgB2B,EAAIN,EAAO,CACvB,OAAOlB,EAAY,SAAS,gBAAgBwB,EAAIN,CAAK,GAAKrB,CAC9D,EAEA,WAAWqB,EAAO,CACdlB,EAAY,SAAS,WAAWkB,CAAK,CACzC,EAEA,UAAW,CACPlB,EAAY,SAAS,SAAS,CAClC,EAEA,iBAAiBmB,EAAU,CACvBnB,EAAY,SAAS,iBAAiBmB,CAAQ,CAClD,EAEA,kBAAkBM,EAAQ,CACtBzB,EAAY,SAAS,kBAAkByB,CAAM,CACjD,EAEA,UAAUC,EAAaC,EAAgB,CACnC,OAAK3B,EAAY,QAGVA,EAAY,QAAQ,OAAO,KAAK0B,EAAKC,CAAK,EAFtC,QAAQ,OAAO,IAAI,MAAM,2DAA2D,CAAC,CAGpG,CACJ,GACA,CAACvB,CAAW,CAChB,CAGJ,CCrVA,OAA6B,oBAApBwB,GAA0C,cAAAC,OAAkB","names":["useEffect","useRef","useCallback","useMemo","CanvasTileEngineCore","createContext","useContext","EngineContext","useEngineContext","context","useEffect","memo","Rect","memo","items","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Circle","memo","items","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Image","memo","items","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","GridLines","memo","cellSize","lineWidth","strokeStyle","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Line","memo","items","style","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Text","memo","items","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","memo","Path","memo","items","style","layer","engine","requestRender","useEngineContext","useEffect","handle","useEffect","useRef","memo","StaticRect","memo","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","useRef","useEffect","handle","useEffect","useRef","memo","StaticCircle","memo","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","useRef","useEffect","handle","useEffect","useRef","memo","StaticImage","memo","items","cacheKey","layer","engine","requestRender","useEngineContext","prevCacheKeyRef","useRef","useEffect","handle","useEffect","useRef","memo","DrawFunction","memo","children","layer","engine","requestRender","useEngineContext","fnRef","useRef","useEffect","handle","ctx","coords","config","jsx","jsxs","CanvasTileEngineBase","engine","config","center","className","style","children","onCoordsChange","onClick","onRightClick","onHover","onMouseDown","onMouseUp","onMouseLeave","onDraw","onResize","onZoom","callbacksRef","useRef","useEffect","rafIdRef","requestRender","useCallback","contextValue","useMemo","container","instance","CanvasTileEngineCore","coords","args","scale","EngineContext","CanvasTileEngine","Rect","Circle","Image","GridLines","Line","Text","Path","StaticRect","StaticCircle","StaticImage","DrawFunction","useRef","useCallback","useState","useMemo","DUMMY_LAYER_HANDLE","DEFAULT_CONFIG","useCanvasTileEngine","instanceRef","containerRef","setIsReady","isReadyRef","setInstance","engine","center","x","y","durationMs","onComplete","width","height","newScale","factor","bounds","handlers","items","layer","cacheKey","style","cellSize","lineWidth","strokeStyle","fn","handle","src","retry","CanvasTileEngine","gridToSize"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@canvas-tile-engine/react",
|
|
3
|
-
"version": "0.0
|
|
3
|
+
"version": "0.2.0",
|
|
4
4
|
"description": "React bindings for Canvas Tile Engine - build interactive 2D grid-based maps with declarative components",
|
|
5
5
|
"author": "Enes Yüksel",
|
|
6
6
|
"license": "MIT",
|
|
@@ -42,10 +42,10 @@
|
|
|
42
42
|
"peerDependencies": {
|
|
43
43
|
"react": ">=18.0.0",
|
|
44
44
|
"react-dom": ">=18.0.0",
|
|
45
|
-
"@canvas-tile-engine/core": ">=0.0
|
|
45
|
+
"@canvas-tile-engine/core": ">=0.2.0"
|
|
46
46
|
},
|
|
47
47
|
"dependencies": {
|
|
48
|
-
"@canvas-tile-engine/core": "0.0
|
|
48
|
+
"@canvas-tile-engine/core": "0.2.0"
|
|
49
49
|
},
|
|
50
50
|
"devDependencies": {
|
|
51
51
|
"@types/react": "^18.3.0",
|