@anov/gis-skills-cli 0.0.0-stage → 0.3.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.
Files changed (57) hide show
  1. package/CHANGELOG.md +618 -0
  2. package/INSTALL.md +478 -0
  3. package/LICENSE +15 -0
  4. package/README.md +148 -2
  5. package/RELEASING.md +160 -0
  6. package/bin/anov-gis-skills.mjs +408 -0
  7. package/lib/mcp-config.mjs +273 -0
  8. package/package.json +42 -4
  9. package/skills/anovgis-analysis/SKILL.md +585 -0
  10. package/skills/anovgis-effects/SKILL.md +260 -0
  11. package/skills/anovgis-imagery-terrain/SKILL.md +505 -0
  12. package/skills/anovgis-layers/SKILL.md +627 -0
  13. package/skills/anovgis-materials/SKILL.md +635 -0
  14. package/skills/anovgis-models-3dtiles/SKILL.md +448 -0
  15. package/skills/anovgis-pitfalls/SKILL.md +561 -0
  16. package/skills/anovgis-popup-widget/SKILL.md +474 -0
  17. package/skills/anovgis-primitives/SKILL.md +482 -0
  18. package/skills/anovgis-vector-graphics/SKILL.md +602 -0
  19. package/skills/anovgis-viewer/SKILL.md +618 -0
  20. package/skills/using-anovgis/DEMO-MAP.md +64 -0
  21. package/skills/using-anovgis/DEMO-SKILL-MAP.md +248 -0
  22. package/skills/using-anovgis/DOMAINS.md +183 -0
  23. package/skills/using-anovgis/REFERENCE.md +114 -0
  24. package/skills/using-anovgis/SKILL.md +392 -0
  25. package/skills/using-anovgis/templates/README.md +154 -0
  26. package/skills/using-anovgis/templates/combo1-vue3-vite.md +295 -0
  27. package/skills/using-anovgis/templates/combo2-vue2-cli.md +119 -0
  28. package/skills/using-anovgis/templates/combo3-html-cdn.md +107 -0
  29. package/skills/using-anovgis/templates/combo4-vanilla-webpack.md +91 -0
  30. package/skills/using-anovgis/templates/wizard-profiles.md +105 -0
  31. package/vendor/cesiumjs-skills/LICENSE +201 -0
  32. package/vendor/cesiumjs-skills/NOTICE +18 -0
  33. package/vendor/cesiumjs-skills/skills/cesiumjs-3d-tiles/SKILL.md +465 -0
  34. package/vendor/cesiumjs-skills/skills/cesiumjs-camera/SKILL.md +500 -0
  35. package/vendor/cesiumjs-skills/skills/cesiumjs-core-utilities/SKILL.md +403 -0
  36. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/REFERENCE.md +397 -0
  37. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/SKILL.md +351 -0
  38. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/01-diffuse-tint.js +38 -0
  39. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/02-texture-swap.js +42 -0
  40. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/03-feature-id-tileset.js +29 -0
  41. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/04-translucent-override.js +37 -0
  42. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/05-vertex-displacement.js +49 -0
  43. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/06-metadata-ramp.js +34 -0
  44. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/07-voxel-shader.js +27 -0
  45. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/README.md +19 -0
  46. package/vendor/cesiumjs-skills/skills/cesiumjs-custom-shader/examples/_sandcastle-template.html +9 -0
  47. package/vendor/cesiumjs-skills/skills/cesiumjs-entities/SKILL.md +389 -0
  48. package/vendor/cesiumjs-skills/skills/cesiumjs-imagery/SKILL.md +471 -0
  49. package/vendor/cesiumjs-skills/skills/cesiumjs-interaction/SKILL.md +423 -0
  50. package/vendor/cesiumjs-skills/skills/cesiumjs-materials-shaders/SKILL.md +292 -0
  51. package/vendor/cesiumjs-skills/skills/cesiumjs-models-particles/SKILL.md +423 -0
  52. package/vendor/cesiumjs-skills/skills/cesiumjs-primitives/SKILL.md +537 -0
  53. package/vendor/cesiumjs-skills/skills/cesiumjs-spatial-math/SKILL.md +358 -0
  54. package/vendor/cesiumjs-skills/skills/cesiumjs-terrain-environment/SKILL.md +401 -0
  55. package/vendor/cesiumjs-skills/skills/cesiumjs-time-properties/SKILL.md +353 -0
  56. package/vendor/cesiumjs-skills/skills/cesiumjs-viewer-setup/SKILL.md +434 -0
  57. package/vendor/cesiumjs-skills/skills/using-cesiumjs-skills/SKILL.md +35 -0
@@ -0,0 +1,465 @@
1
+ ---
2
+ name: cesiumjs-3d-tiles
3
+ description: "CesiumJS 3D Tiles - Cesium3DTileset, MVTDataProvider, styling, metadata, feature picking, voxels, point clouds, I3S, Gaussian splats, clipping planes and polygons. Use when loading 3D Tiles tilesets or Mapbox Vector Tiles as runtime 3D Tiles, styling building/vector features, querying metadata properties, working with voxels or point clouds, or clipping spatial data."
4
+ ---
5
+ # CesiumJS 3D Tiles
6
+
7
+ Version baseline: CesiumJS v1.142 (ES module imports, async factory methods).
8
+
9
+ ## Loading a Tileset
10
+
11
+ Always use async factory methods -- never call the constructor directly.
12
+
13
+ ```js
14
+ import { Cesium3DTileset, HeadingPitchRange, Math as CesiumMath } from "cesium";
15
+
16
+ // From a URL
17
+ const tileset = await Cesium3DTileset.fromUrl(
18
+ "https://example.com/tileset.json",
19
+ { maximumScreenSpaceError: 16 }, // lower = higher quality
20
+ );
21
+ viewer.scene.primitives.add(tileset);
22
+ viewer.zoomTo(tileset, new HeadingPitchRange(
23
+ 0.0, CesiumMath.toRadians(-25.0), tileset.boundingSphere.radius * 2.0,
24
+ ));
25
+ ```
26
+
27
+ ```js
28
+ // From Cesium ion
29
+ const tileset = await Cesium3DTileset.fromIonAssetId(75343);
30
+ viewer.scene.primitives.add(tileset);
31
+ ```
32
+
33
+ ```js
34
+ // Google Photorealistic 3D Tiles
35
+ import { createGooglePhotorealistic3DTileset } from "cesium";
36
+ const google3D = await createGooglePhotorealistic3DTileset({
37
+ onlyUsingWithGoogleGeocoder: true,
38
+ });
39
+ viewer.scene.primitives.add(google3D);
40
+ ```
41
+
42
+ ```js
43
+ // OSM Buildings
44
+ import { createOsmBuildingsAsync } from "cesium";
45
+ const osmBuildings = await createOsmBuildingsAsync();
46
+ viewer.scene.primitives.add(osmBuildings);
47
+ ```
48
+
49
+ ## Key Constructor Options
50
+
51
+ | Option | Default | Purpose |
52
+ |--------|---------|---------|
53
+ | `maximumScreenSpaceError` | 16 | LOD quality threshold (pixels) |
54
+ | `cacheBytes` | 536870912 | Tile cache trim target (bytes) |
55
+ | `maximumCacheOverflowBytes` | 536870912 | Extra cache headroom |
56
+ | `shadows` | ShadowMode.ENABLED | Shadow casting/receiving |
57
+ | `modelMatrix` | Matrix4.IDENTITY | Root transform |
58
+ | `clippingPlanes` | undefined | ClippingPlaneCollection |
59
+ | `clippingPolygons` | undefined | ClippingPolygonCollection (WebGL 2) |
60
+ | `enableCollision` | false | Camera collision with tileset surface |
61
+ | `pointCloudShading` | undefined | Point attenuation options object |
62
+ | `classificationType` | undefined | TERRAIN, CESIUM_3D_TILE, or BOTH |
63
+ | `dynamicScreenSpaceError` | true | Horizon LOD optimization |
64
+ | `foveatedScreenSpaceError` | true | Center-screen tile priority |
65
+ | `preloadFlightDestinations` | true | Prefetch tiles at flight target |
66
+ | `featureIdLabel` | "featureId_0" | EXT_mesh_features ID set label |
67
+ | `backFaceCulling` | true | Cull back faces per glTF material |
68
+ | `edgeDisplayMode` | EdgeDisplayMode.SURFACES_ONLY | Render glTF edge-visibility data when present |
69
+
70
+ ## Mapbox Vector Tiles as Runtime 3D Tiles (Experimental, 1.142+)
71
+
72
+ `MVTDataProvider` loads `{z}/{x}/{y}` Mapbox Vector Tile `.mvt`/`.pbf`
73
+ templates and converts tile payloads into runtime 3D Tiles. Use it when vector
74
+ data is naturally tiled and you want 3D Tiles styling, metadata picking, and LOD
75
+ instead of a single GeoJSON primitive.
76
+
77
+ For one in-memory or URL-backed GeoJSON object, prefer `GeoJsonPrimitive` in
78
+ `cesiumjs-primitives`. For Entity/DataSource conveniences, prefer
79
+ `GeoJsonDataSource` in `cesiumjs-entities`.
80
+
81
+ ```js
82
+ import {
83
+ Cesium3DTileStyle,
84
+ MVTDataProvider,
85
+ Rectangle,
86
+ } from "cesium";
87
+
88
+ const provider = await MVTDataProvider.fromUrl(
89
+ "https://example.com/tiles/{z}/{x}/{y}.pbf",
90
+ {
91
+ minZoom: 4,
92
+ maxZoom: 14,
93
+ extent: Rectangle.fromDegrees(-125, 24, -66, 50),
94
+ featureIdProperty: "id",
95
+ },
96
+ );
97
+
98
+ viewer.scene.primitives.add(provider);
99
+
100
+ // The provider owns a generated Cesium3DTileset.
101
+ provider.tileset.style = new Cesium3DTileStyle({
102
+ color: {
103
+ conditions: [
104
+ ["${kind} === 'park'", "color('seagreen', 0.65)"],
105
+ ["${kind} === 'water'", "color('steelblue', 0.55)"],
106
+ ["true", "color('white', 0.45)"],
107
+ ],
108
+ },
109
+ });
110
+ ```
111
+
112
+ Feature properties are encoded as `EXT_structural_metadata`, so standard
113
+ 3D Tiles styling and picking patterns apply:
114
+
115
+ ```js
116
+ const picked = viewer.scene.pick(windowPosition);
117
+ if (picked && typeof picked.getProperty === "function") {
118
+ console.log(picked.getProperty("name"));
119
+ }
120
+ ```
121
+
122
+ Notes:
123
+ - URL templates must contain `{z}`, `{x}`, and `{y}` placeholders; tile URLs are parsed from `/z/x/y`.
124
+ - Empty 204/404 tiles are treated as missing instead of hard failures.
125
+ - `provider.show` proxies visibility to the generated tileset.
126
+ - Runtime vector glTF content uses draft `EXT_mesh_polygon` and `3DTILES_content_gltf_vector` support; treat this path as experimental.
127
+
128
+ ## Tileset Events
129
+
130
+ ```js
131
+ tileset.loadProgress.addEventListener((pending, processing) => {
132
+ if (pending === 0 && processing === 0) console.log("Loaded");
133
+ });
134
+ tileset.initialTilesLoaded.addEventListener(() => { /* first view ready */ });
135
+ tileset.allTilesLoaded.addEventListener(() => { /* all visible tiles ready */ });
136
+ tileset.tileLoad.addEventListener((tile) => { /* tile content loaded */ });
137
+ tileset.tileUnload.addEventListener((tile) => { /* tile evicted from cache */ });
138
+ tileset.tileFailed.addEventListener(({ url, message }) => {
139
+ console.error(`Tile ${url}: ${message}`);
140
+ });
141
+ // Per-frame manual styling
142
+ tileset.tileVisible.addEventListener((tile) => {
143
+ const content = tile.content;
144
+ for (let i = 0; i < content.featuresLength; i++) {
145
+ content.getFeature(i).color = Cesium.Color.fromRandom();
146
+ }
147
+ });
148
+ ```
149
+
150
+ ## Runtime Properties
151
+
152
+ ```js
153
+ tileset.show = false; // toggle visibility
154
+ tileset.maximumScreenSpaceError = 8; // increase quality
155
+ const { center, radius } = tileset.boundingSphere;
156
+
157
+ import { Matrix4, Cartesian3 } from "cesium";
158
+ tileset.modelMatrix = Matrix4.fromTranslation(new Cartesian3(0, 0, 100));
159
+ ```
160
+
161
+ ## Declarative Styling
162
+
163
+ Assign a `Cesium3DTileStyle` to `tileset.style`. Expressions reference feature
164
+ properties with `${PropertyName}`.
165
+
166
+ ```js
167
+ import { Cesium3DTileStyle } from "cesium";
168
+
169
+ // Color by height conditions
170
+ tileset.style = new Cesium3DTileStyle({
171
+ color: {
172
+ conditions: [
173
+ ["${Height} >= 100", "color('purple', 0.5)"],
174
+ ["${Height} >= 50", "color('red')"],
175
+ ["true", "color('blue')"],
176
+ ],
177
+ },
178
+ show: "${Height} > 0",
179
+ });
180
+ ```
181
+
182
+ ```js
183
+ // Use defines to simplify repeated sub-expressions
184
+ tileset.style = new Cesium3DTileStyle({
185
+ defines: { material: "${feature['building:material']}" },
186
+ color: {
187
+ conditions: [
188
+ ["${material} === null", "color('white')"],
189
+ ["${material} === 'glass'", "color('skyblue', 0.5)"],
190
+ ["${material} === 'brick'", "color('indianred')"],
191
+ ["true", "color('white')"],
192
+ ],
193
+ },
194
+ });
195
+ ```
196
+
197
+ ```js
198
+ // Show/hide by property
199
+ tileset.style = new Cesium3DTileStyle({
200
+ show: "${feature['building']} === 'office'",
201
+ });
202
+ ```
203
+
204
+ ```js
205
+ // Point cloud styling
206
+ tileset.style = new Cesium3DTileStyle({
207
+ color: "vec4(${Temperature})",
208
+ pointSize: "${Temperature} * 2.0",
209
+ });
210
+ ```
211
+
212
+ ```js
213
+ tileset.style = undefined; // reset to default appearance
214
+ ```
215
+
216
+ ### Color Blend Modes
217
+
218
+ ```js
219
+ import { Cesium3DTileColorBlendMode } from "cesium";
220
+ tileset.colorBlendMode = Cesium3DTileColorBlendMode.REPLACE; // HIGHLIGHT | REPLACE | MIX
221
+ tileset.colorBlendAmount = 0.5; // only used with MIX
222
+ ```
223
+
224
+ ### Edge Display Mode (Experimental, 1.142+)
225
+
226
+ `edgeDisplayMode` controls edges contributed by the draft glTF
227
+ `EXT_mesh_primitive_edge_visibility` extension. Tiles without that extension
228
+ render normally regardless of this setting.
229
+
230
+ ```js
231
+ import { Cesium3DTileset, EdgeDisplayMode } from "cesium";
232
+
233
+ const tileset = await Cesium3DTileset.fromUrl("/cad/tileset.json", {
234
+ edgeDisplayMode: EdgeDisplayMode.SURFACES_AND_EDGES,
235
+ });
236
+ viewer.scene.primitives.add(tileset);
237
+
238
+ // CAD-style wireframe for content that carries edge-visibility data.
239
+ tileset.edgeDisplayMode = EdgeDisplayMode.EDGES_ONLY;
240
+
241
+ // Default rendering: hide extension-provided edges.
242
+ tileset.edgeDisplayMode = EdgeDisplayMode.SURFACES_ONLY;
243
+ ```
244
+
245
+ ## Feature Picking and Properties
246
+
247
+ `Scene.pick` returns `Cesium3DTileFeature` for 3D Tiles features. Modifications
248
+ persist until the owning tile is evicted from the cache.
249
+
250
+ ```js
251
+ import {
252
+ ScreenSpaceEventHandler, ScreenSpaceEventType,
253
+ Cesium3DTileFeature, Color,
254
+ } from "cesium";
255
+
256
+ const handler = new ScreenSpaceEventHandler(viewer.scene.canvas);
257
+
258
+ // Hover: read properties
259
+ handler.setInputAction((movement) => {
260
+ const feature = viewer.scene.pick(movement.endPosition);
261
+ if (feature instanceof Cesium3DTileFeature) {
262
+ const ids = feature.getPropertyIds();
263
+ for (const id of ids) console.log(`${id}: ${feature.getProperty(id)}`);
264
+ feature.color = Color.YELLOW; // highlight
265
+ }
266
+ }, ScreenSpaceEventType.MOUSE_MOVE);
267
+
268
+ // Click: inspect a single property
269
+ handler.setInputAction((movement) => {
270
+ const feature = viewer.scene.pick(movement.position);
271
+ if (feature instanceof Cesium3DTileFeature) {
272
+ console.log("Height:", feature.getProperty("Height"));
273
+ feature.setProperty("selected", true); // write custom property
274
+ feature.show = false; // hide individual feature
275
+ }
276
+ }, ScreenSpaceEventType.LEFT_CLICK);
277
+ ```
278
+
279
+ ### Inherited Metadata (3D Tiles 1.1 / EXT_structural_metadata)
280
+
281
+ ```js
282
+ // Searches: batch table -> content -> tile -> subtree -> group -> tileset
283
+ const value = feature.getPropertyInherited("semanticOrPropertyName");
284
+ ```
285
+
286
+ ## Clipping Planes
287
+
288
+ `ClippingPlaneCollection` clips via half-space planes in the tileset's local
289
+ coordinate system.
290
+
291
+ ```js
292
+ import {
293
+ ClippingPlane, ClippingPlaneCollection,
294
+ Cartesian3, Color, Matrix4,
295
+ } from "cesium";
296
+
297
+ const clippingPlanes = new ClippingPlaneCollection({
298
+ planes: [new ClippingPlane(new Cartesian3(0.0, 0.0, -1.0), 0.0)],
299
+ edgeWidth: 1.0,
300
+ edgeColor: Color.WHITE,
301
+ unionClippingRegions: false, // false = intersection (AND); true = union (OR)
302
+ });
303
+
304
+ const tileset = await Cesium3DTileset.fromUrl(url, { clippingPlanes });
305
+ // Or: tileset.clippingPlanes = clippingPlanes;
306
+
307
+ // Offset the clip boundary at runtime
308
+ clippingPlanes.modelMatrix = Matrix4.fromTranslation(new Cartesian3(0, 0, 50));
309
+ clippingPlanes.get(0).distance = 25.0;
310
+ ```
311
+
312
+ ## Clipping Polygons
313
+
314
+ `ClippingPolygonCollection` clips using arbitrary polygons. **WebGL 2 only.**
315
+
316
+ ```js
317
+ import { ClippingPolygon, ClippingPolygonCollection, Cartesian3 } from "cesium";
318
+
319
+ const polygon = new ClippingPolygon({
320
+ positions: Cartesian3.fromDegreesArray([
321
+ -105.0077, 39.7519, -105.0095, 39.7504,
322
+ -105.0071, 39.7513, -105.0077, 39.7519,
323
+ ]),
324
+ });
325
+
326
+ tileset.clippingPolygons = new ClippingPolygonCollection({
327
+ polygons: [polygon],
328
+ inverse: false, // false = clip inside polygon; true = clip outside
329
+ });
330
+
331
+ // Also works on the globe
332
+ viewer.scene.globe.clippingPolygons = new ClippingPolygonCollection({
333
+ polygons: [polygon],
334
+ });
335
+ ```
336
+
337
+ ## Point Cloud Shading
338
+
339
+ ```js
340
+ const tileset = await Cesium3DTileset.fromUrl(pointCloudUrl, {
341
+ pointCloudShading: {
342
+ attenuation: true, // scale points by geometric error
343
+ geometricErrorScale: 1.0,
344
+ maximumAttenuation: 10, // max pixel size; undefined = maximumScreenSpaceError
345
+ eyeDomeLighting: true, // depth-aware edge enhancement
346
+ eyeDomeLightingStrength: 1.0,
347
+ eyeDomeLightingRadius: 1.0,
348
+ backFaceCulling: false, // requires normals in point data
349
+ normalShading: true,
350
+ },
351
+ });
352
+ viewer.scene.primitives.add(tileset);
353
+
354
+ // Runtime adjustment
355
+ tileset.pointCloudShading.eyeDomeLightingStrength = 2.0;
356
+ ```
357
+
358
+ ## Voxel Primitives
359
+
360
+ `VoxelPrimitive` renders volumetric data from a `Cesium3DTilesVoxelProvider`.
361
+ Shapes: `BOX`, `CYLINDER`, `ELLIPSOID` (see `VoxelShapeType`).
362
+
363
+ ```js
364
+ import { VoxelPrimitive, Cesium3DTilesVoxelProvider, CustomShader } from "cesium";
365
+
366
+ const provider = await Cesium3DTilesVoxelProvider.fromUrl("voxel/tileset.json");
367
+
368
+ const voxelPrimitive = new VoxelPrimitive({
369
+ provider,
370
+ customShader: new CustomShader({
371
+ fragmentShaderText: `void fragmentMain(FragmentInput fsInput, inout czm_modelMaterial material) {
372
+ material.diffuse = fsInput.metadata.a.rgb;
373
+ material.alpha = fsInput.metadata.a.a;
374
+ }`,
375
+ }),
376
+ });
377
+ viewer.scene.primitives.add(voxelPrimitive);
378
+ voxelPrimitive.nearestSampling = true;
379
+ viewer.camera.flyToBoundingSphere(voxelPrimitive.boundingSphere, { duration: 0 });
380
+
381
+ // For voxel shader authoring — struct availability, raymarching semantics, metadata
382
+ // access — see the cesiumjs-custom-shader skill. This skill covers VoxelPrimitive setup.
383
+
384
+ // Optional inspector widget
385
+ viewer.extend(Cesium.viewerVoxelInspectorMixin);
386
+ viewer.voxelInspector.viewModel.voxelPrimitive = voxelPrimitive;
387
+ ```
388
+
389
+ ## I3S Data Provider
390
+
391
+ Load Esri I3S scene layers (3D Objects, IntegratedMesh, Building Scene Layer).
392
+
393
+ ```js
394
+ import { I3SDataProvider, ArcGISTiledElevationTerrainProvider, Ellipsoid, Rectangle } from "cesium";
395
+
396
+ const geoidService = await ArcGISTiledElevationTerrainProvider.fromUrl(
397
+ "https://tiles.arcgis.com/tiles/.../EGM2008/ImageServer",
398
+ );
399
+ const i3sProvider = await I3SDataProvider.fromUrl(
400
+ "https://tiles.arcgis.com/tiles/.../SceneServer/layers/0",
401
+ { geoidTiledTerrainProvider: geoidService },
402
+ );
403
+ viewer.scene.primitives.add(i3sProvider);
404
+
405
+ const center = Rectangle.center(i3sProvider.extent);
406
+ center.height = 5000.0;
407
+ viewer.camera.setView({
408
+ destination: Ellipsoid.WGS84.cartographicToCartesian(center),
409
+ });
410
+ ```
411
+
412
+ ## Gaussian Splats
413
+
414
+ Loaded as standard 3D Tiles; CesiumJS handles `KHR_gaussian_splatting` automatically.
415
+
416
+ ```js
417
+ const splats = await Cesium3DTileset.fromIonAssetId(3667783);
418
+ viewer.scene.primitives.add(splats);
419
+ viewer.zoomTo(splats);
420
+ ```
421
+
422
+ ## Classification
423
+
424
+ Drape tileset geometry as a classification overlay on terrain or other tilesets.
425
+
426
+ ```js
427
+ import { Cesium3DTileset, ClassificationType } from "cesium";
428
+ const classified = await Cesium3DTileset.fromUrl(url, {
429
+ classificationType: ClassificationType.BOTH, // TERRAIN | CESIUM_3D_TILE | BOTH
430
+ });
431
+ viewer.scene.primitives.add(classified);
432
+ ```
433
+
434
+ ## Adjusting Tileset Height
435
+
436
+ ```js
437
+ import { Cartographic, Cartesian3, Matrix4 } from "cesium";
438
+ const cartographic = Cartographic.fromCartesian(tileset.boundingSphere.center);
439
+ const surface = Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, 0.0);
440
+ const offset = Cartesian3.fromRadians(cartographic.longitude, cartographic.latitude, heightOffset);
441
+ const translation = Cartesian3.subtract(offset, surface, new Cartesian3());
442
+ tileset.modelMatrix = Matrix4.fromTranslation(translation);
443
+ ```
444
+
445
+ ## Performance Tips
446
+
447
+ 1. Keep `maximumScreenSpaceError` as high as acceptable (16 default; 32+ for mobile).
448
+ 2. Leave `dynamicScreenSpaceError: true` for street-level views with large tilesets.
449
+ 3. Leave `foveatedScreenSpaceError: true` to prioritize center-screen tiles.
450
+ 4. Size `cacheBytes` and `maximumCacheOverflowBytes` to device memory (512 MB each default).
451
+ 5. Use `preloadFlightDestinations: true` to prefetch tiles at the camera flight target.
452
+ 6. Enable `skipLevelOfDetail: true` for large replacement-refined tilesets to reduce memory.
453
+ 7. Avoid `maximumScreenSpaceError` below 4 -- diminishing returns, many more tile requests.
454
+ 8. For point clouds, enable `attenuation` and `eyeDomeLighting` to fill gaps and add depth.
455
+ 9. Keep `enableCollision: false` unless camera collision or CLAMP_TO_GROUND on tiles is needed.
456
+ 10. Preload hidden tilesets with `show: false` and `preloadWhenHidden: true`.
457
+ 11. Avoid translucent styles when possible -- they add rendering passes and disable optimizations.
458
+ 12. Listen to `tileFailed` to log errors; call `trimLoadedTiles()` after large camera jumps.
459
+
460
+ ## See Also
461
+
462
+ - **cesiumjs-custom-shader** -- GLSL authoring for `Cesium3DTileset.customShader` and `VoxelPrimitive.customShader` (struct reference, feature IDs, metadata)
463
+ - **cesiumjs-materials-shaders** -- ImageBasedLighting, post-processing stages for tilesets
464
+ - **cesiumjs-interaction** -- Scene.pick, drillPick, ScreenSpaceEventHandler for feature selection
465
+ - **cesiumjs-terrain-environment** -- Globe, terrain providers, atmosphere, lighting, shadows