@codexo/exojs-tilemap 0.15.3 → 0.16.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +33 -26
- package/dist/esm/ChunkSource.d.ts +33 -0
- package/dist/esm/ChunkSource.d.ts.map +1 -0
- package/dist/esm/ChunkStreamer.d.ts +98 -0
- package/dist/esm/ChunkStreamer.d.ts.map +1 -0
- package/dist/esm/ChunkStreamer.js +201 -0
- package/dist/esm/ChunkStreamer.js.map +1 -0
- package/dist/esm/ImageLayer.d.ts +11 -3
- package/dist/esm/ImageLayer.d.ts.map +1 -0
- package/dist/esm/ImageLayer.js +71 -64
- package/dist/esm/ImageLayer.js.map +1 -1
- package/dist/esm/ImageLayerNode.d.ts +89 -0
- package/dist/esm/ImageLayerNode.d.ts.map +1 -0
- package/dist/esm/ImageLayerNode.js +205 -0
- package/dist/esm/ImageLayerNode.js.map +1 -0
- package/dist/esm/MapObject.d.ts +70 -0
- package/dist/esm/MapObject.d.ts.map +1 -0
- package/dist/esm/MapObject.js +34 -0
- package/dist/esm/MapObject.js.map +1 -0
- package/dist/esm/MapObjectSpawner.d.ts +133 -0
- package/dist/esm/MapObjectSpawner.d.ts.map +1 -0
- package/dist/esm/MapObjectSpawner.js +147 -0
- package/dist/esm/MapObjectSpawner.js.map +1 -0
- package/dist/esm/MapSpawnSession.d.ts +53 -0
- package/dist/esm/MapSpawnSession.d.ts.map +1 -0
- package/dist/esm/MapSpawnSession.js +88 -0
- package/dist/esm/MapSpawnSession.js.map +1 -0
- package/dist/esm/MapWorld.d.ts +134 -0
- package/dist/esm/MapWorld.d.ts.map +1 -0
- package/dist/esm/MapWorld.js +150 -0
- package/dist/esm/MapWorld.js.map +1 -0
- package/dist/esm/MapWorldRuntime.d.ts +182 -0
- package/dist/esm/MapWorldRuntime.d.ts.map +1 -0
- package/dist/esm/MapWorldRuntime.js +261 -0
- package/dist/esm/MapWorldRuntime.js.map +1 -0
- package/dist/esm/ObjectLayer.d.ts +93 -7
- package/dist/esm/ObjectLayer.d.ts.map +1 -0
- package/dist/esm/ObjectLayer.js +184 -167
- package/dist/esm/ObjectLayer.js.map +1 -1
- package/dist/esm/SampledChunkSource.d.ts +43 -0
- package/dist/esm/SampledChunkSource.d.ts.map +1 -0
- package/dist/esm/SampledChunkSource.js +48 -0
- package/dist/esm/SampledChunkSource.js.map +1 -0
- package/dist/esm/TileAnimator.d.ts +12 -2
- package/dist/esm/TileAnimator.d.ts.map +1 -0
- package/dist/esm/TileAnimator.js +154 -165
- package/dist/esm/TileAnimator.js.map +1 -1
- package/dist/esm/TileChunk.d.ts +30 -5
- package/dist/esm/TileChunk.d.ts.map +1 -0
- package/dist/esm/TileChunk.js +190 -188
- package/dist/esm/TileChunk.js.map +1 -1
- package/dist/esm/TileChunkNode.d.ts +18 -3
- package/dist/esm/TileChunkNode.d.ts.map +1 -0
- package/dist/esm/TileChunkNode.js +104 -85
- package/dist/esm/TileChunkNode.js.map +1 -1
- package/dist/esm/TileLayer.d.ts +104 -24
- package/dist/esm/TileLayer.d.ts.map +1 -0
- package/dist/esm/TileLayer.js +511 -469
- package/dist/esm/TileLayer.js.map +1 -1
- package/dist/esm/TileLayerNode.d.ts +52 -11
- package/dist/esm/TileLayerNode.d.ts.map +1 -0
- package/dist/esm/TileLayerNode.js +224 -166
- package/dist/esm/TileLayerNode.js.map +1 -1
- package/dist/esm/TileMap.d.ts +96 -31
- package/dist/esm/TileMap.d.ts.map +1 -0
- package/dist/esm/TileMap.js +401 -357
- package/dist/esm/TileMap.js.map +1 -1
- package/dist/esm/TileMapBand.d.ts +42 -29
- package/dist/esm/TileMapBand.d.ts.map +1 -0
- package/dist/esm/TileMapBand.js +151 -158
- package/dist/esm/TileMapBand.js.map +1 -1
- package/dist/esm/TileMapNode.d.ts +34 -18
- package/dist/esm/TileMapNode.d.ts.map +1 -0
- package/dist/esm/TileMapNode.js +122 -109
- package/dist/esm/TileMapNode.js.map +1 -1
- package/dist/esm/TileMapView.d.ts +108 -47
- package/dist/esm/TileMapView.d.ts.map +1 -0
- package/dist/esm/TileMapView.js +385 -338
- package/dist/esm/TileMapView.js.map +1 -1
- package/dist/esm/TileSet.d.ts +15 -6
- package/dist/esm/TileSet.d.ts.map +1 -0
- package/dist/esm/TileSet.js +161 -181
- package/dist/esm/TileSet.js.map +1 -1
- package/dist/esm/WangSet.d.ts +5 -4
- package/dist/esm/WangSet.d.ts.map +1 -0
- package/dist/esm/WangSet.js +70 -78
- package/dist/esm/WangSet.js.map +1 -1
- package/dist/esm/WorkerSampledChunkSource.d.ts +95 -0
- package/dist/esm/WorkerSampledChunkSource.d.ts.map +1 -0
- package/dist/esm/WorkerSampledChunkSource.js +117 -0
- package/dist/esm/WorkerSampledChunkSource.js.map +1 -0
- package/dist/esm/autoTile.d.ts +10 -5
- package/dist/esm/autoTile.d.ts.map +1 -0
- package/dist/esm/autoTile.js +164 -205
- package/dist/esm/autoTile.js.map +1 -1
- package/dist/esm/chunkGeometry.d.ts +8 -7
- package/dist/esm/chunkGeometry.d.ts.map +1 -0
- package/dist/esm/chunkGeometry.js +83 -94
- package/dist/esm/chunkGeometry.js.map +1 -1
- package/dist/esm/index.d.ts +1 -0
- package/dist/esm/index.d.ts.map +1 -0
- package/dist/esm/index.js +26 -15
- package/dist/esm/nodeBounds.d.ts +20 -0
- package/dist/esm/nodeBounds.d.ts.map +1 -0
- package/dist/esm/nodeBounds.js +40 -0
- package/dist/esm/nodeBounds.js.map +1 -0
- package/dist/esm/pixelSnap.d.ts +4 -3
- package/dist/esm/pixelSnap.d.ts.map +1 -0
- package/dist/esm/pixelSnap.js +18 -16
- package/dist/esm/pixelSnap.js.map +1 -1
- package/dist/esm/public.d.ts +23 -3
- package/dist/esm/public.d.ts.map +1 -0
- package/dist/esm/tileCollision.d.ts +190 -0
- package/dist/esm/tileCollision.d.ts.map +1 -0
- package/dist/esm/tileCollision.js +367 -0
- package/dist/esm/tileCollision.js.map +1 -0
- package/dist/esm/tileWord.d.ts +12 -0
- package/dist/esm/tileWord.d.ts.map +1 -0
- package/dist/esm/tileWord.js +16 -0
- package/dist/esm/tileWord.js.map +1 -0
- package/dist/esm/tilemapExtension.d.ts +4 -3
- package/dist/esm/tilemapExtension.d.ts.map +1 -0
- package/dist/esm/tilemapExtension.js +47 -47
- package/dist/esm/tilemapExtension.js.map +1 -1
- package/dist/esm/tilemapSerializers.d.ts +5 -4
- package/dist/esm/tilemapSerializers.d.ts.map +1 -0
- package/dist/esm/tilemapSerializers.js +48 -41
- package/dist/esm/tilemapSerializers.js.map +1 -1
- package/dist/esm/types.d.ts +34 -18
- package/dist/esm/types.d.ts.map +1 -0
- package/dist/esm/types.js +111 -120
- package/dist/esm/types.js.map +1 -1
- package/dist/esm/webgl2/WebGl2TileChunkRenderer.d.ts +50 -2
- package/dist/esm/webgl2/WebGl2TileChunkRenderer.d.ts.map +1 -0
- package/dist/esm/webgl2/WebGl2TileChunkRenderer.js +366 -332
- package/dist/esm/webgl2/WebGl2TileChunkRenderer.js.map +1 -1
- package/dist/esm/webgl2/shaders/tile-chunk.frag.js +6 -0
- package/dist/esm/webgl2/shaders/tile-chunk.frag.js.map +1 -0
- package/dist/esm/webgl2/shaders/tile-chunk.vert.js +6 -0
- package/dist/esm/webgl2/shaders/tile-chunk.vert.js.map +1 -0
- package/dist/esm/webgpu/WebGpuTileChunkRenderer.d.ts +70 -4
- package/dist/esm/webgpu/WebGpuTileChunkRenderer.d.ts.map +1 -0
- package/dist/esm/webgpu/WebGpuTileChunkRenderer.js +496 -383
- package/dist/esm/webgpu/WebGpuTileChunkRenderer.js.map +1 -1
- package/dist/esm/webgpu/shaders/tile-chunk.wgsl.js +6 -0
- package/dist/esm/webgpu/shaders/tile-chunk.wgsl.js.map +1 -0
- package/package.json +8 -15
- package/dist/esm/index.js.map +0 -1
- package/dist/esm/register.d.ts +0 -1
- package/dist/esm/register.js +0 -25
- package/dist/esm/register.js.map +0 -1
package/dist/esm/types.js
CHANGED
|
@@ -1,138 +1,129 @@
|
|
|
1
|
-
|
|
1
|
+
//#region src/types.ts
|
|
2
2
|
/**
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
3
|
+
* Discriminant for the three structured, non-scalar {@link TilePropertyValue}
|
|
4
|
+
* variants: {@link TilePropertyPoint}, {@link TilePropertyObjectRef}, and
|
|
5
|
+
* {@link TilePropertyTileRef}.
|
|
6
|
+
*
|
|
7
|
+
* Modelled as a frozen string map (not a TS `enum`) so the values stay
|
|
8
|
+
* wire-stable, survive `verbatimModuleSyntax` (no emitted runtime helper),
|
|
9
|
+
* and follow the package convention for enum-like constants (see
|
|
10
|
+
* {@link import('./ObjectLayer').ObjectKind}).
|
|
11
|
+
* @stable
|
|
12
|
+
*/
|
|
13
13
|
const TilePropertyKind = {
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
14
|
+
Point: "point",
|
|
15
|
+
ObjectRef: "objectRef",
|
|
16
|
+
TileRef: "tileRef"
|
|
17
17
|
};
|
|
18
18
|
/** The identity transform: no flip, no diagonal. */
|
|
19
19
|
const TILE_TRANSFORM_IDENTITY = Object.freeze({
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
20
|
+
flipX: false,
|
|
21
|
+
flipY: false,
|
|
22
|
+
diagonal: false
|
|
23
23
|
});
|
|
24
24
|
/** Bit width allocated to the local tile ID within a packed tile word. */
|
|
25
25
|
const PACKED_LOCAL_BITS = 20;
|
|
26
|
-
|
|
27
|
-
const
|
|
28
|
-
|
|
29
|
-
const
|
|
30
|
-
const
|
|
31
|
-
const PACKED_TILESET_MASK = ((1 << PACKED_TILESET_BITS) - 1) << PACKED_LOCAL_BITS;
|
|
32
|
-
const PACKED_TRANSFORM_MASK = ((1 << PACKED_TRANSFORM_BITS) - 1) << (PACKED_LOCAL_BITS + PACKED_TILESET_BITS);
|
|
33
|
-
const PACKED_TILESET_SHIFT = PACKED_LOCAL_BITS;
|
|
34
|
-
const PACKED_TRANSFORM_SHIFT = PACKED_LOCAL_BITS + PACKED_TILESET_BITS;
|
|
26
|
+
const PACKED_LOCAL_MASK = (1 << 20) - 1;
|
|
27
|
+
const PACKED_TILESET_MASK = 511 << 20;
|
|
28
|
+
const PACKED_TRANSFORM_MASK = 7 << 29;
|
|
29
|
+
const PACKED_TILESET_SHIFT = 20;
|
|
30
|
+
const PACKED_TRANSFORM_SHIFT = 29;
|
|
35
31
|
/** Maximum tileset index representable in a packed tile. */
|
|
36
|
-
const MAX_TILESET_INDEX =
|
|
32
|
+
const MAX_TILESET_INDEX = 511;
|
|
37
33
|
/** Maximum local tile ID representable in a packed tile (1-based storage). */
|
|
38
|
-
const MAX_LOCAL_TILE_ID = (1 <<
|
|
39
|
-
|
|
40
|
-
const
|
|
41
|
-
const
|
|
42
|
-
const TRANSFORM_DIAGONAL = 1 << 2;
|
|
34
|
+
const MAX_LOCAL_TILE_ID = (1 << 20) - 2;
|
|
35
|
+
const TRANSFORM_FLIP_X = 1;
|
|
36
|
+
const TRANSFORM_FLIP_Y = 2;
|
|
37
|
+
const TRANSFORM_DIAGONAL = 4;
|
|
43
38
|
/**
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
bits |= TRANSFORM_DIAGONAL;
|
|
65
|
-
// +1 so 0 means "empty" not "tile 0 without transform"
|
|
66
|
-
const storedId = localTileId + 1;
|
|
67
|
-
return (storedId & PACKED_LOCAL_MASK)
|
|
68
|
-
| ((tilesetIndex << PACKED_TILESET_SHIFT) & PACKED_TILESET_MASK)
|
|
69
|
-
| ((bits << PACKED_TRANSFORM_SHIFT) & PACKED_TRANSFORM_MASK);
|
|
70
|
-
}
|
|
39
|
+
* Encode a tileset-local tile reference and transform into a packed word.
|
|
40
|
+
* The localTileId is stored as (localTileId + 1) so that a packed value of 0
|
|
41
|
+
* cleanly represents an empty cell, while tile 0 from tileset 0 with identity
|
|
42
|
+
* transform is stored as 1 (non-zero).
|
|
43
|
+
* Returns 0 for an empty cell.
|
|
44
|
+
*
|
|
45
|
+
* Public so chunk-provider authors (e.g. a format adapter or procedural
|
|
46
|
+
* generator) can build a {@link ChunkPayload}'s `tiles` array without
|
|
47
|
+
* duplicating this encoding.
|
|
48
|
+
* @advanced
|
|
49
|
+
*/
|
|
50
|
+
const packTile = (tilesetIndex, localTileId, transform) => {
|
|
51
|
+
if (tilesetIndex < 0 || tilesetIndex > 511) throw new Error(`Tileset index ${tilesetIndex} exceeds maximum ${511}.`);
|
|
52
|
+
if (localTileId < 0 || localTileId > 1048574) throw new Error(`Local tile ID ${localTileId} exceeds maximum ${MAX_LOCAL_TILE_ID}.`);
|
|
53
|
+
let bits = 0;
|
|
54
|
+
if (transform.flipX) bits |= TRANSFORM_FLIP_X;
|
|
55
|
+
if (transform.flipY) bits |= TRANSFORM_FLIP_Y;
|
|
56
|
+
if (transform.diagonal) bits |= TRANSFORM_DIAGONAL;
|
|
57
|
+
return localTileId + 1 & PACKED_LOCAL_MASK | tilesetIndex << 20 & PACKED_TILESET_MASK | bits << 29 & PACKED_TRANSFORM_MASK;
|
|
58
|
+
};
|
|
71
59
|
/**
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
},
|
|
92
|
-
};
|
|
93
|
-
}
|
|
60
|
+
* Decode a packed word into its components.
|
|
61
|
+
* Returns null for an empty cell (packed === 0).
|
|
62
|
+
* @advanced
|
|
63
|
+
*/
|
|
64
|
+
const unpackTile = (packed) => {
|
|
65
|
+
if (packed === 0) return null;
|
|
66
|
+
const localTileId = (packed & PACKED_LOCAL_MASK) - 1;
|
|
67
|
+
const tilesetIndex = (packed & PACKED_TILESET_MASK) >>> 20;
|
|
68
|
+
const rawTransform = (packed & PACKED_TRANSFORM_MASK) >>> 29;
|
|
69
|
+
return {
|
|
70
|
+
tilesetIndex,
|
|
71
|
+
localTileId,
|
|
72
|
+
transform: {
|
|
73
|
+
flipX: !!(rawTransform & TRANSFORM_FLIP_X),
|
|
74
|
+
flipY: !!(rawTransform & TRANSFORM_FLIP_Y),
|
|
75
|
+
diagonal: !!(rawTransform & TRANSFORM_DIAGONAL)
|
|
76
|
+
}
|
|
77
|
+
};
|
|
78
|
+
};
|
|
94
79
|
/** Convert tile coordinates to chunk coordinates given a chunk size. */
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
};
|
|
100
|
-
}
|
|
80
|
+
const tileToChunkCoord = (tx, ty, chunkW, chunkH) => ({
|
|
81
|
+
cx: Math.floor(tx / chunkW),
|
|
82
|
+
cy: Math.floor(ty / chunkH)
|
|
83
|
+
});
|
|
101
84
|
/** Convert tile coordinates to local-in-chunk coordinates. */
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
};
|
|
107
|
-
}
|
|
85
|
+
const tileToLocalInChunk = (tx, ty, chunkW, chunkH) => ({
|
|
86
|
+
lx: (tx % chunkW + chunkW) % chunkW,
|
|
87
|
+
ly: (ty % chunkH + chunkH) % chunkH
|
|
88
|
+
});
|
|
108
89
|
/**
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
if (value > Number.MAX_SAFE_INTEGER) {
|
|
117
|
-
throw new Error(`${label} exceeds safe integer range (got ${value}).`);
|
|
118
|
-
}
|
|
119
|
-
}
|
|
90
|
+
* Validate that a value is a finite, safe, positive integer.
|
|
91
|
+
* Used for dimensions, tile counts, chunk sizes.
|
|
92
|
+
*/
|
|
93
|
+
const validatePositiveInteger = (value, label) => {
|
|
94
|
+
if (!Number.isFinite(value) || !Number.isInteger(value) || value <= 0) throw new Error(`${label} must be a positive integer (got ${value}).`);
|
|
95
|
+
if (value > Number.MAX_SAFE_INTEGER) throw new Error(`${label} exceeds safe integer range (got ${value}).`);
|
|
96
|
+
};
|
|
120
97
|
/**
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
98
|
+
* Validate a non-negative finite integer.
|
|
99
|
+
*/
|
|
100
|
+
const validateNonNegativeInteger = (value, label) => {
|
|
101
|
+
if (!Number.isFinite(value) || !Number.isInteger(value) || value < 0) throw new Error(`${label} must be a non-negative integer (got ${value}).`);
|
|
102
|
+
};
|
|
103
|
+
/**
|
|
104
|
+
* Validate that a value is a finite integer (may be negative).
|
|
105
|
+
*/
|
|
106
|
+
const validateInteger = (value, label) => {
|
|
107
|
+
if (!Number.isFinite(value) || !Number.isInteger(value)) throw new Error(`${label} must be a finite integer (got ${value}).`);
|
|
108
|
+
};
|
|
128
109
|
/**
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
}
|
|
110
|
+
* Validate a `width`/`height` pair that must be provided together (bounded)
|
|
111
|
+
* or omitted together (unbounded) - shared by {@link import('./TileLayer').TileLayer}
|
|
112
|
+
* and {@link import('./TileMap').TileMap}. When both are provided, each is
|
|
113
|
+
* validated as a positive integer via {@link validatePositiveInteger}.
|
|
114
|
+
*
|
|
115
|
+
* @param entityName Used in the paired-presence error message (e.g. `"TileLayer"`).
|
|
116
|
+
* @param fieldPrefix Used as the field-name prefix passed to {@link validatePositiveInteger} (e.g. `"layer"` for `"layer.width"`).
|
|
117
|
+
* @throws If exactly one of `width`/`height` is provided, or either is not a positive integer.
|
|
118
|
+
*/
|
|
119
|
+
const validatePairedDimensions = (width, height, entityName, fieldPrefix) => {
|
|
120
|
+
if (width !== void 0 || height !== void 0) {
|
|
121
|
+
if (width === void 0 || height === void 0) throw new Error(`${entityName} width and height must both be provided (bounded) or both omitted (unbounded).`);
|
|
122
|
+
validatePositiveInteger(width, `${fieldPrefix}.width`);
|
|
123
|
+
validatePositiveInteger(height, `${fieldPrefix}.height`);
|
|
124
|
+
}
|
|
125
|
+
};
|
|
136
126
|
|
|
137
|
-
|
|
138
|
-
|
|
127
|
+
//#endregion
|
|
128
|
+
export { MAX_LOCAL_TILE_ID, PACKED_LOCAL_MASK, PACKED_TILESET_MASK, PACKED_TRANSFORM_MASK, TILE_TRANSFORM_IDENTITY, TilePropertyKind, packTile, tileToChunkCoord, tileToLocalInChunk, unpackTile, validateInteger, validateNonNegativeInteger, validatePairedDimensions, validatePositiveInteger };
|
|
129
|
+
//# sourceMappingURL=types.js.map
|
package/dist/esm/types.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.js","sources":["../../../src/types.ts"],"sourcesContent":[null],"names":[],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"types.js","names":[],"sources":["../../src/types.ts"],"sourcesContent":["import type { TileMapObject } from './ObjectLayer';\nimport type { TileSet } from './TileSet';\n\n// ── Properties ────────────────────────────────────────────────────────────\n\n/**\n * Discriminant for the three structured, non-scalar {@link TilePropertyValue}\n * variants: {@link TilePropertyPoint}, {@link TilePropertyObjectRef}, and\n * {@link TilePropertyTileRef}.\n *\n * Modelled as a frozen string map (not a TS `enum`) so the values stay\n * wire-stable, survive `verbatimModuleSyntax` (no emitted runtime helper),\n * and follow the package convention for enum-like constants (see\n * {@link import('./ObjectLayer').ObjectKind}).\n * @stable\n */\nexport const TilePropertyKind = {\n Point: 'point',\n ObjectRef: 'objectRef',\n TileRef: 'tileRef',\n} as const;\n\n/** Structured-value discriminant for {@link TilePropertyValue}. */\nexport type TilePropertyKind = (typeof TilePropertyKind)[keyof typeof TilePropertyKind];\n\n/** A 2D point-valued tile property (e.g. an LDtk `Point` field). */\nexport interface TilePropertyPoint {\n readonly kind: typeof TilePropertyKind.Point;\n readonly cx: number;\n readonly cy: number;\n}\n\n/**\n * A reference to another object/entity. `id` is the referenced object's\n * identity - Tiled's numeric object id, or LDtk's `entityIid`. The extra\n * fields are LDtk-only navigation context (`undefined` for Tiled-sourced\n * refs) that lets a consumer resolve the reference without searching the\n * whole level tree.\n */\nexport interface TilePropertyObjectRef {\n readonly kind: typeof TilePropertyKind.ObjectRef;\n readonly id: string | number;\n readonly layerIid?: string;\n readonly levelIid?: string;\n readonly worldIid?: string;\n}\n\n/** A reference into a tileset region (e.g. an LDtk `Tile`-typed field). */\nexport interface TilePropertyTileRef {\n readonly kind: typeof TilePropertyKind.TileRef;\n readonly tilesetUid: number;\n readonly x: number;\n readonly y: number;\n readonly w: number;\n readonly h: number;\n}\n\n/**\n * Union of legal tile-property value types in the generic runtime.\n * Format-neutral; adapters map their native property systems into this set -\n * including the structured {@link TilePropertyPoint}, {@link TilePropertyObjectRef},\n * and {@link TilePropertyTileRef} variants, arrays of any of the above, and\n * nested property bags (e.g. Tiled `class`-typed properties).\n * @advanced\n */\nexport type TilePropertyValue =\n null | boolean | number | string | TilePropertyPoint | TilePropertyObjectRef | TilePropertyTileRef | readonly TilePropertyValue[] | TileProperties;\n\n/**\n * An immutable, flat key-value bag of generic tile properties.\n * Adapters copy and freeze source properties; the runtime never retains\n * a caller-owned mutable object.\n *\n * Declared as an interface (not a `Record<...>` type alias) so it can\n * mutually recurse with {@link TilePropertyValue} - a nested-bag member of\n * that union - without TypeScript's \"circularly references itself\" alias\n * restriction; structurally it behaves exactly like\n * `Readonly<Record<string, TilePropertyValue>>`.\n * @advanced\n */\nexport interface TileProperties {\n readonly [key: string]: TilePropertyValue;\n}\n\n// ── Tile orientation / transform ──────────────────────────────────────────\n\n/**\n * Describes the orientation of a placed tile independent of source-format\n * flip-bit encodings. The eight legal combinations map to the eight distinct\n * 90°-rotation-and-flip states of a rectangular texture quad.\n *\n * Applying the transform at geometry-build time (reordering UV corners)\n * avoids per-tile runtime cost and per-frame matrix allocation.\n * @stable\n */\nexport interface TileTransform {\n /** Horizontal flip (mirror left-right). */\n readonly flipX: boolean;\n /** Vertical flip (mirror top-bottom). */\n readonly flipY: boolean;\n /** Anti-diagonal flip (transpose of the UV axes). Combined with flips produces 90° rotations. */\n readonly diagonal: boolean;\n}\n\n/** The identity transform: no flip, no diagonal. */\nexport const TILE_TRANSFORM_IDENTITY: Readonly<TileTransform> = Object.freeze({\n flipX: false,\n flipY: false,\n diagonal: false,\n});\n\n/**\n * Short string label for a {@link TileTransform} (debug / serialisation).\n * Returns one of the eight deterministic names, e.g. `\"flipX\"` or `\"diag+flipX+flipY\"`.\n * @internal\n */\nexport const tileTransformLabel = (t: TileTransform): string => {\n const parts: string[] = [];\n if (t.diagonal) parts.push('diag');\n if (t.flipX) parts.push('flipX');\n if (t.flipY) parts.push('flipY');\n return parts.length === 0 ? 'identity' : parts.join('+');\n};\n\n// ── Tile identity ─────────────────────────────────────────────────────────\n\n/**\n * Opaque packed tile data stored in a {@link TileChunk}'s compact array.\n * 0 means \"empty cell\". Any non-zero value encodes localTileId, tilesetIndex,\n * and flip bits according to the bit-layout constants below.\n *\n * A `PackedTile` is **not** a source-format GID - it is a fully resolved\n * internal compact representation. Use {@link packTile} / {@link unpackTile}\n * to convert between packed form and a {@link ResolvedTile} if writing\n * adapters.\n *\n * In public APIs, prefer {@link ResolvedTile} or null for queries.\n * `PackedTile` is exposed as `@advanced` so `ReadonlyTileChunk.getRawAt()`\n * has a self-documenting return type.\n * @advanced\n */\nexport type PackedTile = number;\n\n/** Bit width allocated to the local tile ID within a packed tile word. */\nexport const PACKED_LOCAL_BITS = 20;\n/** Bit width allocated to the tileset index within a packed tile word. */\nexport const PACKED_TILESET_BITS = 9;\n/** Bit width allocated to the transform/flip bits. */\nexport const PACKED_TRANSFORM_BITS = 3;\n\nexport const PACKED_LOCAL_MASK = (1 << PACKED_LOCAL_BITS) - 1;\nexport const PACKED_TILESET_MASK = ((1 << PACKED_TILESET_BITS) - 1) << PACKED_LOCAL_BITS;\nexport const PACKED_TRANSFORM_MASK = ((1 << PACKED_TRANSFORM_BITS) - 1) << (PACKED_LOCAL_BITS + PACKED_TILESET_BITS);\n\nexport const PACKED_TILESET_SHIFT = PACKED_LOCAL_BITS;\nexport const PACKED_TRANSFORM_SHIFT = PACKED_LOCAL_BITS + PACKED_TILESET_BITS;\n\n/** Maximum tileset index representable in a packed tile. */\nexport const MAX_TILESET_INDEX = (1 << PACKED_TILESET_BITS) - 1;\n/** Maximum local tile ID representable in a packed tile (1-based storage). */\nexport const MAX_LOCAL_TILE_ID = (1 << PACKED_LOCAL_BITS) - 2;\n\n// Transform bit-field values (bit 0 = flipX, bit 1 = flipY, bit 2 = diagonal).\nconst TRANSFORM_FLIP_X = 1 << 0;\nconst TRANSFORM_FLIP_Y = 1 << 1;\nconst TRANSFORM_DIAGONAL = 1 << 2;\n\n/**\n * Encode a tileset-local tile reference and transform into a packed word.\n * The localTileId is stored as (localTileId + 1) so that a packed value of 0\n * cleanly represents an empty cell, while tile 0 from tileset 0 with identity\n * transform is stored as 1 (non-zero).\n * Returns 0 for an empty cell.\n *\n * Public so chunk-provider authors (e.g. a format adapter or procedural\n * generator) can build a {@link ChunkPayload}'s `tiles` array without\n * duplicating this encoding.\n * @advanced\n */\nexport const packTile = (tilesetIndex: number, localTileId: number, transform: TileTransform): PackedTile => {\n if (tilesetIndex < 0 || tilesetIndex > MAX_TILESET_INDEX) {\n throw new Error(`Tileset index ${tilesetIndex} exceeds maximum ${MAX_TILESET_INDEX}.`);\n }\n if (localTileId < 0 || localTileId > MAX_LOCAL_TILE_ID) {\n throw new Error(`Local tile ID ${localTileId} exceeds maximum ${MAX_LOCAL_TILE_ID}.`);\n }\n let bits = 0;\n if (transform.flipX) bits |= TRANSFORM_FLIP_X;\n if (transform.flipY) bits |= TRANSFORM_FLIP_Y;\n if (transform.diagonal) bits |= TRANSFORM_DIAGONAL;\n // +1 so 0 means \"empty\" not \"tile 0 without transform\"\n const storedId = localTileId + 1;\n return (\n (storedId & PACKED_LOCAL_MASK) | ((tilesetIndex << PACKED_TILESET_SHIFT) & PACKED_TILESET_MASK) | ((bits << PACKED_TRANSFORM_SHIFT) & PACKED_TRANSFORM_MASK)\n );\n};\n\n/**\n * Decode a packed word into its components.\n * Returns null for an empty cell (packed === 0).\n * @advanced\n */\nexport const unpackTile = (\n packed: PackedTile,\n): {\n tilesetIndex: number;\n localTileId: number;\n transform: TileTransform;\n} | null => {\n if (packed === 0) return null;\n const storedId = packed & PACKED_LOCAL_MASK;\n // Undo the +1 offset applied during packTile.\n const localTileId = storedId - 1;\n const tilesetIndex = (packed & PACKED_TILESET_MASK) >>> PACKED_TILESET_SHIFT;\n const rawTransform = (packed & PACKED_TRANSFORM_MASK) >>> PACKED_TRANSFORM_SHIFT;\n return {\n tilesetIndex,\n localTileId,\n transform: {\n flipX: !!(rawTransform & TRANSFORM_FLIP_X),\n flipY: !!(rawTransform & TRANSFORM_FLIP_Y),\n diagonal: !!(rawTransform & TRANSFORM_DIAGONAL),\n },\n };\n};\n\n// ── Resolved tile reference (public query result) ─────────────────────────\n\n/**\n * A fully resolved, format-independent tile reference returned by queries.\n * Materialised on-demand from the packed storage; never stored as a per-cell\n * heap object.\n * @advanced\n */\nexport interface ResolvedTile {\n /** The owning tileset (already resolved from source-format GID). */\n readonly tileset: TileSet;\n /** 0-based tile index within the tileset. */\n readonly localTileId: number;\n /** Orientation transform for this placed tile. */\n readonly transform: TileTransform;\n}\n\n// ── Tile animation ────────────────────────────────────────────────────────\n\n/**\n * One frame of a tile animation: which local tile to show, and for how long.\n * Mirrors Tiled's per-tile animation frame model.\n * @advanced\n */\nexport interface TileAnimationFrame {\n /** Local tile ID shown during this frame (within the tile's own tileset). */\n readonly localTileId: number;\n /** Frame duration in milliseconds. */\n readonly duration: number;\n}\n\n// ── TileDefinition ────────────────────────────────────────────────────────\n\n/**\n * Optional per-tile metadata in a {@link TileSet}. Sparse - only defined\n * tiles carry a definition.\n * @advanced\n */\nexport interface TileDefinition {\n /** The local tile ID this definition belongs to. */\n readonly localTileId: number;\n /** Tile properties (copied and frozen by the tileset). */\n readonly properties?: TileProperties;\n /**\n * Animation frame sequence for this tile, if animated. The frames are\n * driven at runtime by a {@link import('./TileAnimator').TileAnimator};\n * frame[0] is the tile's resting/base frame.\n */\n readonly animation?: readonly TileAnimationFrame[];\n /**\n * Per-tile collision shapes sourced from the Tiled `objectgroup` on the tile.\n * Shapes are in tile-local pixel space (origin = top-left of the tile cell).\n * Only present when the source map defines collision geometry for this tile.\n */\n readonly collision?: readonly TileMapObject[];\n}\n\n// ── Chunk coordinate helpers ──────────────────────────────────────────────\n\n/** A signed chunk coordinate pair. */\nexport interface ChunkCoord {\n readonly cx: number;\n readonly cy: number;\n}\n\n/** Convert tile coordinates to chunk coordinates given a chunk size. */\nexport const tileToChunkCoord = (tx: number, ty: number, chunkW: number, chunkH: number): ChunkCoord => ({\n cx: Math.floor(tx / chunkW),\n cy: Math.floor(ty / chunkH),\n});\n\n/** Convert tile coordinates to local-in-chunk coordinates. */\nexport const tileToLocalInChunk = (tx: number, ty: number, chunkW: number, chunkH: number): { lx: number; ly: number } => ({\n lx: ((tx % chunkW) + chunkW) % chunkW,\n ly: ((ty % chunkH) + chunkH) % chunkH,\n});\n\n/**\n * Validate that a value is a finite, safe, positive integer.\n * Used for dimensions, tile counts, chunk sizes.\n */\nexport const validatePositiveInteger = (value: number, label: string): void => {\n if (!Number.isFinite(value) || !Number.isInteger(value) || value <= 0) {\n throw new Error(`${label} must be a positive integer (got ${value}).`);\n }\n if (value > Number.MAX_SAFE_INTEGER) {\n throw new Error(`${label} exceeds safe integer range (got ${value}).`);\n }\n};\n\n/**\n * Validate a non-negative finite integer.\n */\nexport const validateNonNegativeInteger = (value: number, label: string): void => {\n if (!Number.isFinite(value) || !Number.isInteger(value) || value < 0) {\n throw new Error(`${label} must be a non-negative integer (got ${value}).`);\n }\n};\n\n/**\n * Validate that a value is a finite integer (may be negative).\n */\nexport const validateInteger = (value: number, label: string): void => {\n if (!Number.isFinite(value) || !Number.isInteger(value)) {\n throw new Error(`${label} must be a finite integer (got ${value}).`);\n }\n};\n\n/**\n * Validate a `width`/`height` pair that must be provided together (bounded)\n * or omitted together (unbounded) - shared by {@link import('./TileLayer').TileLayer}\n * and {@link import('./TileMap').TileMap}. When both are provided, each is\n * validated as a positive integer via {@link validatePositiveInteger}.\n *\n * @param entityName Used in the paired-presence error message (e.g. `\"TileLayer\"`).\n * @param fieldPrefix Used as the field-name prefix passed to {@link validatePositiveInteger} (e.g. `\"layer\"` for `\"layer.width\"`).\n * @throws If exactly one of `width`/`height` is provided, or either is not a positive integer.\n */\nexport const validatePairedDimensions = (width: number | undefined, height: number | undefined, entityName: string, fieldPrefix: string): void => {\n if (width !== undefined || height !== undefined) {\n if (width === undefined || height === undefined) {\n throw new Error(`${entityName} width and height must both be provided (bounded) or both omitted (unbounded).`);\n }\n validatePositiveInteger(width, `${fieldPrefix}.width`);\n validatePositiveInteger(height, `${fieldPrefix}.height`);\n }\n};\n"],"mappings":";;;;;;;;;;;;AAgBA,MAAa,mBAAmB;CAC9B,OAAO;CACP,WAAW;CACX,SAAS;AACX;;AAqFA,MAAa,0BAAmD,OAAO,OAAO;CAC5E,OAAO;CACP,OAAO;CACP,UAAU;AACZ,CAAC;;AAmCD,MAAa,oBAAoB;AAMjC,MAAa,qBAAqB,WAA0B;AAC5D,MAAa,sBAAuB;AACpC,MAAa,wBAAyB,KAAsC;AAE5E,MAAa;AACb,MAAa,yBAAyB;;AAGtC,MAAa,oBAAoB;;AAEjC,MAAa,qBAAqB,WAA0B;AAG5D,MAAM,mBAAmB;AACzB,MAAM,mBAAmB;AACzB,MAAM,qBAAqB;;;;;;;;;;;;;AAc3B,MAAa,YAAY,cAAsB,aAAqB,cAAyC;CAC3G,IAAI,eAAe,KAAK,oBACtB,MAAM,IAAI,MAAM,iBAAiB,aAAa,uBAAqC,EAAE;CAEvF,IAAI,cAAc,KAAK,uBACrB,MAAM,IAAI,MAAM,iBAAiB,YAAY,mBAAmB,kBAAkB,EAAE;CAEtF,IAAI,OAAO;CACX,IAAI,UAAU,OAAO,QAAQ;CAC7B,IAAI,UAAU,OAAO,QAAQ;CAC7B,IAAI,UAAU,UAAU,QAAQ;CAGhC,OADiB,cAAc,IAEjB,oBAAuB,qBAAwC,sBAAyB,aAAkC;AAE1I;;;;;;AAOA,MAAa,cACX,WAKU;CACV,IAAI,WAAW,GAAG,OAAO;CAGzB,MAAM,eAFW,SAAS,qBAEK;CAC/B,MAAM,gBAAgB,SAAS;CAC/B,MAAM,gBAAgB,SAAS;CAC/B,OAAO;EACL;EACA;EACA,WAAW;GACT,OAAO,CAAC,EAAE,eAAe;GACzB,OAAO,CAAC,EAAE,eAAe;GACzB,UAAU,CAAC,EAAE,eAAe;EAC9B;CACF;AACF;;AAoEA,MAAa,oBAAoB,IAAY,IAAY,QAAgB,YAAgC;CACvG,IAAI,KAAK,MAAM,KAAK,MAAM;CAC1B,IAAI,KAAK,MAAM,KAAK,MAAM;AAC5B;;AAGA,MAAa,sBAAsB,IAAY,IAAY,QAAgB,YAAgD;CACzH,KAAM,KAAK,SAAU,UAAU;CAC/B,KAAM,KAAK,SAAU,UAAU;AACjC;;;;;AAMA,MAAa,2BAA2B,OAAe,UAAwB;CAC7E,IAAI,CAAC,OAAO,SAAS,KAAK,KAAK,CAAC,OAAO,UAAU,KAAK,KAAK,SAAS,GAClE,MAAM,IAAI,MAAM,GAAG,MAAM,mCAAmC,MAAM,GAAG;CAEvE,IAAI,QAAQ,OAAO,kBACjB,MAAM,IAAI,MAAM,GAAG,MAAM,mCAAmC,MAAM,GAAG;AAEzE;;;;AAKA,MAAa,8BAA8B,OAAe,UAAwB;CAChF,IAAI,CAAC,OAAO,SAAS,KAAK,KAAK,CAAC,OAAO,UAAU,KAAK,KAAK,QAAQ,GACjE,MAAM,IAAI,MAAM,GAAG,MAAM,uCAAuC,MAAM,GAAG;AAE7E;;;;AAKA,MAAa,mBAAmB,OAAe,UAAwB;CACrE,IAAI,CAAC,OAAO,SAAS,KAAK,KAAK,CAAC,OAAO,UAAU,KAAK,GACpD,MAAM,IAAI,MAAM,GAAG,MAAM,iCAAiC,MAAM,GAAG;AAEvE;;;;;;;;;;;AAYA,MAAa,4BAA4B,OAA2B,QAA4B,YAAoB,gBAA8B;CAChJ,IAAI,UAAU,UAAa,WAAW,QAAW;EAC/C,IAAI,UAAU,UAAa,WAAW,QACpC,MAAM,IAAI,MAAM,GAAG,WAAW,+EAA+E;EAE/G,wBAAwB,OAAO,GAAG,YAAY,OAAO;EACrD,wBAAwB,QAAQ,GAAG,YAAY,QAAQ;CACzD;AACF"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import type { WebGl2Backend } from '@codexo/exojs/renderer-sdk';
|
|
1
|
+
import type { WebGl2Backend, WebGl2RetainedBatchPayload, WebGl2RetainedBatchReplayer, WebGl2RetainedNodeIndexRange } from '@codexo/exojs/renderer-sdk';
|
|
2
2
|
import { AbstractWebGl2Renderer } from '@codexo/exojs/renderer-sdk';
|
|
3
3
|
import type { TileChunkNode } from '../TileChunkNode';
|
|
4
4
|
/**
|
|
@@ -9,19 +9,35 @@ import type { TileChunkNode } from '../TileChunkNode';
|
|
|
9
9
|
* orientation-neutral and never re-uploaded for a camera pan.
|
|
10
10
|
* @internal
|
|
11
11
|
*/
|
|
12
|
-
export declare class WebGl2TileChunkRenderer extends AbstractWebGl2Renderer<TileChunkNode> {
|
|
12
|
+
export declare class WebGl2TileChunkRenderer extends AbstractWebGl2Renderer<TileChunkNode> implements WebGl2RetainedBatchReplayer {
|
|
13
|
+
/**
|
|
14
|
+
* Retained-batch capability opt-in: a tile chunk's per-flush
|
|
15
|
+
* instanced batches (fixed 32-byte layout, tile word at word 7) can be
|
|
16
|
+
* recorded into a group's instruction set and replayed from group-owned
|
|
17
|
+
* resources. Pixel-snapped draws are excluded by the collect-time
|
|
18
|
+
* recordability predicate (and belt-and-braces poisoning in {@link render});
|
|
19
|
+
* tile chunks have no custom-material path to exclude.
|
|
20
|
+
* @internal
|
|
21
|
+
*/
|
|
22
|
+
readonly _supportsRetainedBatches = true;
|
|
13
23
|
private readonly _shader;
|
|
14
24
|
private readonly _batchSize;
|
|
15
25
|
private readonly _instanceData;
|
|
16
26
|
private readonly _instanceFloat32;
|
|
17
27
|
private readonly _instanceUint32;
|
|
18
28
|
private readonly _transformUnitScratch;
|
|
29
|
+
private readonly _baseTextureUnitScratch;
|
|
30
|
+
private readonly _recordTextures;
|
|
19
31
|
private _quadIndex;
|
|
20
32
|
private _maxNodeIndex;
|
|
33
|
+
private _batchNodeCount;
|
|
34
|
+
private _nodeBooked;
|
|
21
35
|
private _currentBlendMode;
|
|
22
36
|
private _currentTexture;
|
|
23
37
|
private _currentView;
|
|
24
38
|
private _currentViewId;
|
|
39
|
+
private _hasWrittenGroup;
|
|
40
|
+
private readonly _writtenGroupData;
|
|
25
41
|
private _instanceBuffer;
|
|
26
42
|
private _vao;
|
|
27
43
|
private _connection;
|
|
@@ -30,6 +46,37 @@ export declare class WebGl2TileChunkRenderer extends AbstractWebGl2Renderer<Tile
|
|
|
30
46
|
private _renderPage;
|
|
31
47
|
private _writeRun;
|
|
32
48
|
flush(): void;
|
|
49
|
+
/**
|
|
50
|
+
* Stage `u_projection` (live view) and `u_group` (live composed group
|
|
51
|
+
* matrix) on the shader, guarded by cached view/group stamps. Shared by the
|
|
52
|
+
* live flush path and retained-batch replay - replay resolves exactly the
|
|
53
|
+
* same live state a slow-path flush would.
|
|
54
|
+
*/
|
|
55
|
+
private _stageViewUniforms;
|
|
56
|
+
/** @internal See {@link WebGl2RetainedBatchReplayer._scanRetainedNodeIndexRange}. */
|
|
57
|
+
_scanRetainedNodeIndexRange(payload: WebGl2RetainedBatchPayload, range: WebGl2RetainedNodeIndexRange): void;
|
|
58
|
+
/** @internal See {@link WebGl2RetainedBatchReplayer._rebaseRetainedNodeIndices} (group-local indices). */
|
|
59
|
+
_rebaseRetainedNodeIndices(payload: WebGl2RetainedBatchPayload, base: number): void;
|
|
60
|
+
/**
|
|
61
|
+
* Point the batch VAO's per-instance attributes at the bundle's persistent
|
|
62
|
+
* instance buffer, based at the batch's byte offset (WebGL2 has no
|
|
63
|
+
* baseInstance, hence one small VAO per recorded batch). Same attribute
|
|
64
|
+
* set/locations as the live VAO in {@link onConnect}.
|
|
65
|
+
* @internal
|
|
66
|
+
*/
|
|
67
|
+
_configureRetainedVao(payload: WebGl2RetainedBatchPayload): void;
|
|
68
|
+
/**
|
|
69
|
+
* Replay one recorded batch: all STATE is resolved live - blend mode via
|
|
70
|
+
* the backend's dedup, `u_projection`/`u_group` from the live view + live
|
|
71
|
+
* composed group matrix (the camera-pan / group-move win), the single
|
|
72
|
+
* tileset texture bound to unit 0 by recorded slot order - and only the
|
|
73
|
+
* DATA is cached: the instance bytes in the bundle buffer (bound through
|
|
74
|
+
* the per-batch VAO) and the group-owned transform texture on the shared
|
|
75
|
+
* transform unit. The backend hook flushed any pending live batch before
|
|
76
|
+
* dispatching here and bumps the stats from the instruction descriptor.
|
|
77
|
+
* @internal
|
|
78
|
+
*/
|
|
79
|
+
_replayRetainedBatch(payload: WebGl2RetainedBatchPayload): void;
|
|
33
80
|
protected onConnect(backend: WebGl2Backend): void;
|
|
34
81
|
protected onDisconnect(): void;
|
|
35
82
|
destroy(): void;
|
|
@@ -37,3 +84,4 @@ export declare class WebGl2TileChunkRenderer extends AbstractWebGl2Renderer<Tile
|
|
|
37
84
|
private _createBufferRuntime;
|
|
38
85
|
private _createVaoRuntime;
|
|
39
86
|
}
|
|
87
|
+
//# sourceMappingURL=WebGl2TileChunkRenderer.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"WebGl2TileChunkRenderer.d.ts","sourceRoot":"","sources":["../../../src/webgl2/WebGl2TileChunkRenderer.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAIV,aAAa,EAEb,0BAA0B,EAC1B,2BAA2B,EAC3B,4BAA4B,EAE7B,MAAM,4BAA4B,CAAC;AACpC,OAAO,EACL,sBAAsB,EAavB,MAAM,4BAA4B,CAAC;AAGpC,OAAO,KAAK,EAAE,aAAa,EAAE,MAAM,kBAAkB,CAAC;AAqBtD;;;;;;;GAOG;AACH,qBAAa,uBAAwB,SAAQ,sBAAsB,CAAC,aAAa,CAAE,YAAW,2BAA2B;IACvH;;;;;;;;OAQG;IACH,SAAgB,wBAAwB,QAAQ;IAEhD,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAS;IACjC,OAAO,CAAC,QAAQ,CAAC,UAAU,CAAS;IACpC,OAAO,CAAC,QAAQ,CAAC,aAAa,CAAc;IAC5C,OAAO,CAAC,QAAQ,CAAC,gBAAgB,CAAe;IAChD,OAAO,CAAC,QAAQ,CAAC,eAAe,CAAc;IAE9C,OAAO,CAAC,QAAQ,CAAC,qBAAqB,CAAsD;IAG5F,OAAO,CAAC,QAAQ,CAAC,uBAAuB,CAAmC;IAG3E,OAAO,CAAC,QAAQ,CAAC,eAAe,CAAiD;IAEjF,OAAO,CAAC,UAAU,CAAK;IACvB,OAAO,CAAC,aAAa,CAAK;IAM1B,OAAO,CAAC,eAAe,CAAK;IAC5B,OAAO,CAAC,WAAW,CAAS;IAC5B,OAAO,CAAC,iBAAiB,CAA2B;IACpD,OAAO,CAAC,eAAe,CAAwB;IAC/C,OAAO,CAAC,YAAY,CAAqB;IACzC,OAAO,CAAC,cAAc,CAAM;IAC5B,OAAO,CAAC,gBAAgB,CAAS;IACjC,OAAO,CAAC,QAAQ,CAAC,iBAAiB,CAAuB;IAEzD,OAAO,CAAC,eAAe,CAAmC;IAC1D,OAAO,CAAC,IAAI,CAAwC;IACpD,OAAO,CAAC,WAAW,CAAuC;gBAEvC,SAAS,EAAE,MAAM;IAU7B,MAAM,CAAC,IAAI,EAAE,aAAa,GAAG,IAAI;IAsBxC,OAAO,CAAC,WAAW;IA8CnB,OAAO,CAAC,SAAS;IA0DV,KAAK,IAAI,IAAI;IAqDpB;;;;;OAKG;IACH,OAAO,CAAC,kBAAkB;IA4B1B,qFAAqF;IAC9E,2BAA2B,CAAC,OAAO,EAAE,0BAA0B,EAAE,KAAK,EAAE,4BAA4B,GAAG,IAAI;IAqBlH,0GAA0G;IACnG,0BAA0B,CAAC,OAAO,EAAE,0BAA0B,EAAE,IAAI,EAAE,MAAM,GAAG,IAAI;IAgB1F;;;;;;OAMG;IACI,qBAAqB,CAAC,OAAO,EAAE,0BAA0B,GAAG,IAAI;IAkBvE;;;;;;;;;;OAUG;IACI,oBAAoB,CAAC,OAAO,EAAE,0BAA0B,GAAG,IAAI;IAgDtE,SAAS,CAAC,SAAS,CAAC,OAAO,EAAE,aAAa,GAAG,IAAI;IAkBjD,SAAS,CAAC,YAAY,IAAI,IAAI;IAkBvB,OAAO,IAAI,IAAI;IAKtB,OAAO,CAAC,iBAAiB;IAUzB,OAAO,CAAC,oBAAoB;IAiC5B,OAAO,CAAC,iBAAiB;CA8C1B"}
|