@vcmap/core 6.0.0-rc.4 → 6.0.0-rc.6

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 (209) hide show
  1. package/dist/cesium.d.ts +11 -0
  2. package/dist/index.d.ts +23 -16
  3. package/dist/index.js +21 -14
  4. package/dist/index.js.map +1 -1
  5. package/dist/ol.d.ts +15 -2
  6. package/dist/src/layer/cesium/clusterContext.d.ts +8 -14
  7. package/dist/src/layer/cesium/clusterContext.js +62 -41
  8. package/dist/src/layer/cesium/clusterContext.js.map +1 -1
  9. package/dist/src/layer/cesium/vectorCesiumImpl.d.ts +2 -3
  10. package/dist/src/layer/cesium/vectorCesiumImpl.js +16 -10
  11. package/dist/src/layer/cesium/vectorCesiumImpl.js.map +1 -1
  12. package/dist/src/layer/cesium/vectorContext.d.ts +10 -53
  13. package/dist/src/layer/cesium/vectorContext.js +88 -172
  14. package/dist/src/layer/cesium/vectorContext.js.map +1 -1
  15. package/dist/src/layer/geojsonHelpers.d.ts +1 -1
  16. package/dist/src/layer/geojsonHelpers.js +5 -10
  17. package/dist/src/layer/geojsonHelpers.js.map +1 -1
  18. package/dist/src/layer/oblique/obliqueHelpers.js +6 -6
  19. package/dist/src/layer/oblique/obliqueHelpers.js.map +1 -1
  20. package/dist/src/layer/vectorLayer.d.ts +0 -37
  21. package/dist/src/layer/vectorLayer.js.map +1 -1
  22. package/dist/src/layer/vectorProperties.d.ts +8 -3
  23. package/dist/src/layer/vectorProperties.js +30 -5
  24. package/dist/src/layer/vectorProperties.js.map +1 -1
  25. package/dist/src/map/baseOLMap.js +1 -1
  26. package/dist/src/map/baseOLMap.js.map +1 -1
  27. package/dist/src/map/obliqueMap.d.ts +3 -0
  28. package/dist/src/map/obliqueMap.js +27 -6
  29. package/dist/src/map/obliqueMap.js.map +1 -1
  30. package/dist/src/map/vcsMap.d.ts +8 -0
  31. package/dist/src/map/vcsMap.js +11 -0
  32. package/dist/src/map/vcsMap.js.map +1 -1
  33. package/dist/src/oblique/helpers.js +5 -5
  34. package/dist/src/oblique/helpers.js.map +1 -1
  35. package/dist/src/oblique/obliqueDataSet.js +4 -4
  36. package/dist/src/oblique/obliqueDataSet.js.map +1 -1
  37. package/dist/src/ol/geom/geometryCollection.js +19 -2
  38. package/dist/src/ol/geom/geometryCollection.js.map +1 -1
  39. package/dist/src/style/arcStyle.js +1 -0
  40. package/dist/src/style/arcStyle.js.map +1 -1
  41. package/dist/src/util/editor/createFeatureSession.d.ts +5 -1
  42. package/dist/src/util/editor/createFeatureSession.js +48 -4
  43. package/dist/src/util/editor/createFeatureSession.js.map +1 -1
  44. package/dist/src/util/editor/editFeaturesSession.d.ts +10 -4
  45. package/dist/src/util/editor/editFeaturesSession.js +74 -37
  46. package/dist/src/util/editor/editFeaturesSession.js.map +1 -1
  47. package/dist/src/util/editor/editGeometrySession.d.ts +5 -1
  48. package/dist/src/util/editor/editGeometrySession.js +77 -55
  49. package/dist/src/util/editor/editGeometrySession.js.map +1 -1
  50. package/dist/src/util/editor/editorHelpers.d.ts +12 -6
  51. package/dist/src/util/editor/editorHelpers.js +47 -20
  52. package/dist/src/util/editor/editorHelpers.js.map +1 -1
  53. package/dist/src/util/editor/editorSessionHelpers.d.ts +5 -0
  54. package/dist/src/util/editor/editorSessionHelpers.js +1 -0
  55. package/dist/src/util/editor/editorSessionHelpers.js.map +1 -1
  56. package/dist/src/util/editor/editorSymbols.d.ts +1 -1
  57. package/dist/src/util/editor/editorSymbols.js +1 -1
  58. package/dist/src/util/editor/editorSymbols.js.map +1 -1
  59. package/dist/src/util/editor/interactions/createBBoxInteraction.d.ts +1 -0
  60. package/dist/src/util/editor/interactions/createBBoxInteraction.js +20 -16
  61. package/dist/src/util/editor/interactions/createBBoxInteraction.js.map +1 -1
  62. package/dist/src/util/editor/interactions/createCircleInteraction.js +1 -1
  63. package/dist/src/util/editor/interactions/createCircleInteraction.js.map +1 -1
  64. package/dist/src/util/editor/interactions/createLineStringInteraction.js +3 -3
  65. package/dist/src/util/editor/interactions/createLineStringInteraction.js.map +1 -1
  66. package/dist/src/util/editor/interactions/createPointInteraction.js +1 -1
  67. package/dist/src/util/editor/interactions/createPointInteraction.js.map +1 -1
  68. package/dist/src/util/editor/interactions/createPolygonInteraction.d.ts +4 -0
  69. package/dist/src/util/editor/interactions/createPolygonInteraction.js +9 -3
  70. package/dist/src/util/editor/interactions/createPolygonInteraction.js.map +1 -1
  71. package/dist/src/util/editor/interactions/creationSnapping.d.ts +26 -0
  72. package/dist/src/util/editor/interactions/creationSnapping.js +139 -0
  73. package/dist/src/util/editor/interactions/creationSnapping.js.map +1 -0
  74. package/dist/src/util/editor/interactions/editGeometryMouseOverInteraction.js +3 -2
  75. package/dist/src/util/editor/interactions/editGeometryMouseOverInteraction.js.map +1 -1
  76. package/dist/src/util/editor/interactions/insertVertexInteraction.d.ts +3 -1
  77. package/dist/src/util/editor/interactions/insertVertexInteraction.js +14 -6
  78. package/dist/src/util/editor/interactions/insertVertexInteraction.js.map +1 -1
  79. package/dist/src/util/editor/interactions/layerSnapping.d.ts +19 -0
  80. package/dist/src/util/editor/interactions/layerSnapping.js +87 -0
  81. package/dist/src/util/editor/interactions/layerSnapping.js.map +1 -0
  82. package/dist/src/util/editor/interactions/translateVertexInteraction.js +2 -2
  83. package/dist/src/util/editor/interactions/translateVertexInteraction.js.map +1 -1
  84. package/dist/src/util/editor/interactions/translationSnapping.d.ts +25 -0
  85. package/dist/src/util/editor/interactions/translationSnapping.js +179 -0
  86. package/dist/src/util/editor/interactions/translationSnapping.js.map +1 -0
  87. package/dist/src/util/editor/snappingHelpers.d.ts +44 -0
  88. package/dist/src/util/editor/snappingHelpers.js +329 -0
  89. package/dist/src/util/editor/snappingHelpers.js.map +1 -0
  90. package/dist/src/util/editor/transformation/create2DHandlers.js +26 -26
  91. package/dist/src/util/editor/transformation/create2DHandlers.js.map +1 -1
  92. package/dist/src/util/editor/transformation/create3DHandlers.js +65 -14
  93. package/dist/src/util/editor/transformation/create3DHandlers.js.map +1 -1
  94. package/dist/src/util/editor/transformation/scaleInteraction.js +27 -5
  95. package/dist/src/util/editor/transformation/scaleInteraction.js.map +1 -1
  96. package/dist/src/util/editor/transformation/transformationHandler.js +56 -38
  97. package/dist/src/util/editor/transformation/transformationHandler.js.map +1 -1
  98. package/dist/src/util/editor/transformation/transformationTypes.d.ts +2 -0
  99. package/dist/src/util/editor/transformation/transformationTypes.js +4 -0
  100. package/dist/src/util/editor/transformation/transformationTypes.js.map +1 -1
  101. package/dist/src/util/featureconverter/arcToCesium.d.ts +5 -19
  102. package/dist/src/util/featureconverter/arcToCesium.js +15 -42
  103. package/dist/src/util/featureconverter/arcToCesium.js.map +1 -1
  104. package/dist/src/util/featureconverter/circleToCesium.d.ts +2 -27
  105. package/dist/src/util/featureconverter/circleToCesium.js +84 -63
  106. package/dist/src/util/featureconverter/circleToCesium.js.map +1 -1
  107. package/dist/src/util/featureconverter/clampedPrimitive.d.ts +2 -0
  108. package/dist/src/util/featureconverter/clampedPrimitive.js +29 -0
  109. package/dist/src/util/featureconverter/clampedPrimitive.js.map +1 -0
  110. package/dist/src/util/featureconverter/convert.d.ts +26 -7
  111. package/dist/src/util/featureconverter/convert.js +221 -44
  112. package/dist/src/util/featureconverter/convert.js.map +1 -1
  113. package/dist/src/util/featureconverter/extent3D.d.ts +4 -3
  114. package/dist/src/util/featureconverter/extent3D.js +4 -3
  115. package/dist/src/util/featureconverter/extent3D.js.map +1 -1
  116. package/dist/src/util/featureconverter/lineStringToCesium.d.ts +12 -27
  117. package/dist/src/util/featureconverter/lineStringToCesium.js +85 -107
  118. package/dist/src/util/featureconverter/lineStringToCesium.js.map +1 -1
  119. package/dist/src/util/featureconverter/pointHelpers.d.ts +8 -11
  120. package/dist/src/util/featureconverter/pointHelpers.js +134 -120
  121. package/dist/src/util/featureconverter/pointHelpers.js.map +1 -1
  122. package/dist/src/util/featureconverter/pointToCesium.d.ts +14 -17
  123. package/dist/src/util/featureconverter/pointToCesium.js +47 -96
  124. package/dist/src/util/featureconverter/pointToCesium.js.map +1 -1
  125. package/dist/src/util/featureconverter/polygonToCesium.d.ts +2 -26
  126. package/dist/src/util/featureconverter/polygonToCesium.js +62 -72
  127. package/dist/src/util/featureconverter/polygonToCesium.js.map +1 -1
  128. package/dist/src/util/featureconverter/storeyHelpers.d.ts +17 -0
  129. package/dist/src/util/featureconverter/storeyHelpers.js +78 -0
  130. package/dist/src/util/featureconverter/storeyHelpers.js.map +1 -0
  131. package/dist/src/util/featureconverter/vectorGeometryFactory.d.ts +54 -0
  132. package/dist/src/util/featureconverter/vectorGeometryFactory.js +278 -0
  133. package/dist/src/util/featureconverter/vectorGeometryFactory.js.map +1 -0
  134. package/dist/src/util/featureconverter/vectorHeightInfo.d.ts +86 -0
  135. package/dist/src/util/featureconverter/vectorHeightInfo.js +242 -0
  136. package/dist/src/util/featureconverter/vectorHeightInfo.js.map +1 -0
  137. package/dist/src/util/geometryHelpers.d.ts +22 -1
  138. package/dist/src/util/geometryHelpers.js +65 -2
  139. package/dist/src/util/geometryHelpers.js.map +1 -1
  140. package/dist/src/util/mapCollection.js +8 -0
  141. package/dist/src/util/mapCollection.js.map +1 -1
  142. package/dist/src/util/math.d.ts +6 -2
  143. package/dist/src/util/math.js +34 -12
  144. package/dist/src/util/math.js.map +1 -1
  145. package/dist/tests/unit/helpers/cesiumHelpers.js +3 -1
  146. package/dist/tests/unit/helpers/cesiumHelpers.js.map +1 -1
  147. package/dist/tests/unit/helpers/helpers.d.ts +2 -9
  148. package/dist/tests/unit/helpers/helpers.js +2 -8
  149. package/dist/tests/unit/helpers/helpers.js.map +1 -1
  150. package/index.ts +74 -35
  151. package/package.json +3 -3
  152. package/src/cesium/cesium.d.ts +11 -0
  153. package/src/layer/cesium/clusterContext.ts +82 -91
  154. package/src/layer/cesium/vectorCesiumImpl.ts +17 -11
  155. package/src/layer/cesium/vectorContext.ts +120 -348
  156. package/src/layer/geojsonHelpers.ts +9 -12
  157. package/src/layer/oblique/obliqueHelpers.ts +6 -6
  158. package/src/layer/vectorLayer.ts +0 -71
  159. package/src/layer/vectorProperties.ts +46 -9
  160. package/src/map/baseOLMap.ts +1 -1
  161. package/src/map/obliqueMap.ts +46 -6
  162. package/src/map/vcsMap.ts +20 -2
  163. package/src/oblique/helpers.ts +11 -5
  164. package/src/oblique/obliqueDataSet.ts +4 -4
  165. package/src/ol/geom/geometryCollection.js +21 -2
  166. package/src/ol/ol.d.ts +15 -2
  167. package/src/style/arcStyle.ts +1 -0
  168. package/src/util/editor/createFeatureSession.ts +64 -6
  169. package/src/util/editor/editFeaturesSession.ts +105 -39
  170. package/src/util/editor/editGeometrySession.ts +118 -75
  171. package/src/util/editor/editorHelpers.ts +78 -30
  172. package/src/util/editor/editorSessionHelpers.ts +7 -0
  173. package/src/util/editor/editorSymbols.ts +1 -1
  174. package/src/util/editor/interactions/createBBoxInteraction.ts +25 -16
  175. package/src/util/editor/interactions/createCircleInteraction.ts +1 -1
  176. package/src/util/editor/interactions/createLineStringInteraction.ts +9 -3
  177. package/src/util/editor/interactions/createPointInteraction.ts +1 -1
  178. package/src/util/editor/interactions/createPolygonInteraction.ts +16 -3
  179. package/src/util/editor/interactions/creationSnapping.ts +226 -0
  180. package/src/util/editor/interactions/editGeometryMouseOverInteraction.ts +3 -2
  181. package/src/util/editor/interactions/insertVertexInteraction.ts +27 -7
  182. package/src/util/editor/interactions/layerSnapping.ts +136 -0
  183. package/src/util/editor/interactions/translateVertexInteraction.ts +8 -2
  184. package/src/util/editor/interactions/translationSnapping.ts +302 -0
  185. package/src/util/editor/snappingHelpers.ts +490 -0
  186. package/src/util/editor/transformation/create2DHandlers.ts +38 -26
  187. package/src/util/editor/transformation/create3DHandlers.ts +84 -22
  188. package/src/util/editor/transformation/scaleInteraction.ts +28 -5
  189. package/src/util/editor/transformation/transformationHandler.ts +72 -41
  190. package/src/util/editor/transformation/transformationTypes.ts +5 -0
  191. package/src/util/featureconverter/arcToCesium.ts +25 -95
  192. package/src/util/featureconverter/circleToCesium.ts +127 -113
  193. package/src/util/featureconverter/clampedPrimitive.ts +70 -0
  194. package/src/util/featureconverter/convert.ts +446 -114
  195. package/src/util/featureconverter/extent3D.ts +13 -6
  196. package/src/util/featureconverter/lineStringToCesium.ts +132 -179
  197. package/src/util/featureconverter/pointHelpers.ts +271 -214
  198. package/src/util/featureconverter/pointToCesium.ts +111 -175
  199. package/src/util/featureconverter/polygonToCesium.ts +98 -117
  200. package/src/util/featureconverter/storeyHelpers.ts +104 -0
  201. package/src/util/featureconverter/vectorGeometryFactory.ts +601 -0
  202. package/src/util/featureconverter/vectorHeightInfo.ts +393 -0
  203. package/src/util/geometryHelpers.ts +79 -5
  204. package/src/util/mapCollection.ts +8 -0
  205. package/src/util/math.ts +59 -12
  206. package/dist/src/util/featureconverter/featureconverterHelper.d.ts +0 -35
  207. package/dist/src/util/featureconverter/featureconverterHelper.js +0 -404
  208. package/dist/src/util/featureconverter/featureconverterHelper.js.map +0 -1
  209. package/src/util/featureconverter/featureconverterHelper.ts +0 -672
@@ -0,0 +1,393 @@
1
+ import { is } from '@vcsuite/check';
2
+ import { Geometry, SimpleGeometry } from 'ol/geom.js';
3
+ import type { Coordinate } from 'ol/coordinate.js';
4
+ import { Cartesian3, HeightReference } from '@vcmap-cesium/engine';
5
+ import { GeometryLayout } from 'ol/geom/Geometry.js';
6
+ import type { Feature } from 'ol';
7
+ import type VectorProperties from '../../layer/vectorProperties.js';
8
+ import { is2DLayout } from '../geometryHelpers.js';
9
+ import { getStoreyHeights, validateStoreys } from './storeyHelpers.js';
10
+ import Projection from '../projection.js';
11
+
12
+ export type ExtrusionHeightInfo = {
13
+ /**
14
+ * if the object is extruded
15
+ */
16
+ extruded: boolean;
17
+ /**
18
+ * storey heights above ground, list has the same length as storeysAboveGround
19
+ */
20
+ storeyHeightsAboveGround: number[];
21
+ /**
22
+ * storey heights below ground, list has the same length as storeysBelowGround
23
+ */
24
+ storeyHeightsBelowGround: number[];
25
+ /**
26
+ * a negative height to <i>push</i> the geometry visually into the ground
27
+ */
28
+ skirt: number;
29
+ };
30
+ export type ClampedHeightReference =
31
+ | HeightReference.CLAMP_TO_GROUND
32
+ | HeightReference.CLAMP_TO_TERRAIN
33
+ | HeightReference.CLAMP_TO_3D_TILE;
34
+ export type RelativeHeightReference =
35
+ | HeightReference.RELATIVE_TO_GROUND
36
+ | HeightReference.RELATIVE_TO_TERRAIN
37
+ | HeightReference.RELATIVE_TO_3D_TILE;
38
+ export type VectorHeightInfo<
39
+ T extends HeightReference = HeightReference,
40
+ L extends GeometryLayout = GeometryLayout,
41
+ > = T extends ClampedHeightReference
42
+ ? {
43
+ heightReference: T;
44
+ layout: L;
45
+ }
46
+ : T extends RelativeHeightReference
47
+ ? {
48
+ heightReference: T;
49
+ layout: L;
50
+ clampOrigin?: [number, number];
51
+ heightAboveGround?: number;
52
+ /**
53
+ * the level above or below mean sea level
54
+ */
55
+ groundLevel?: number;
56
+ /**
57
+ * true if not all z values are identical, e.g no height above ground was provided and no or only one storey was provided
58
+ */
59
+ perPositionHeight: boolean;
60
+ } & ExtrusionHeightInfo
61
+ : T extends HeightReference.NONE
62
+ ? {
63
+ heightReference: T;
64
+ layout: L;
65
+ /**
66
+ * the level above or below mean sea level (minZ value or ground_level or 0)
67
+ */
68
+ groundLevelOrMinHeight: number;
69
+ /**
70
+ * true if not all z values are identical, e.g no ground level was provided and no or only one storey was provided
71
+ */
72
+ perPositionHeight: boolean;
73
+ } & ExtrusionHeightInfo
74
+ : never;
75
+
76
+ export function isClampedHeightReference(
77
+ heightReference: HeightReference,
78
+ ): heightReference is ClampedHeightReference {
79
+ return (
80
+ heightReference === HeightReference.CLAMP_TO_GROUND ||
81
+ heightReference === HeightReference.CLAMP_TO_TERRAIN ||
82
+ heightReference === HeightReference.CLAMP_TO_3D_TILE
83
+ );
84
+ }
85
+
86
+ export function isRelativeHeightReference(
87
+ heightReference: HeightReference,
88
+ ): heightReference is RelativeHeightReference {
89
+ return (
90
+ heightReference === HeightReference.RELATIVE_TO_GROUND ||
91
+ heightReference === HeightReference.RELATIVE_TO_TERRAIN ||
92
+ heightReference === HeightReference.RELATIVE_TO_3D_TILE
93
+ );
94
+ }
95
+
96
+ export function isAbsoluteHeightReference(
97
+ heightReference: HeightReference,
98
+ ): heightReference is HeightReference.NONE {
99
+ return heightReference === HeightReference.NONE;
100
+ }
101
+
102
+ export function getRelativeEquivalent(
103
+ clampedHeightReference: ClampedHeightReference,
104
+ ): RelativeHeightReference {
105
+ if (clampedHeightReference === HeightReference.CLAMP_TO_GROUND) {
106
+ return HeightReference.RELATIVE_TO_GROUND;
107
+ }
108
+ if (clampedHeightReference === HeightReference.CLAMP_TO_TERRAIN) {
109
+ return HeightReference.RELATIVE_TO_TERRAIN;
110
+ }
111
+ return HeightReference.RELATIVE_TO_3D_TILE;
112
+ }
113
+
114
+ export function getExtrusionHeightInfo(
115
+ feature: Feature,
116
+ vectorProperties: VectorProperties,
117
+ ): ExtrusionHeightInfo {
118
+ const extrudedHeight = vectorProperties.getExtrudedHeight(feature);
119
+
120
+ let storeysAboveGround = vectorProperties.getStoreysAboveGround(feature);
121
+ let storeysBelowGround = vectorProperties.getStoreysBelowGround(feature);
122
+ let storeyHeightsAboveGround =
123
+ vectorProperties.getStoreyHeightsAboveGround(feature);
124
+ let storeyHeightsBelowGround =
125
+ vectorProperties.getStoreyHeightsBelowGround(feature);
126
+ if (extrudedHeight) {
127
+ // current Case only extrudedHeight
128
+ if (extrudedHeight > 0) {
129
+ storeyHeightsAboveGround = getStoreyHeights(
130
+ extrudedHeight,
131
+ storeyHeightsAboveGround,
132
+ storeysAboveGround,
133
+ );
134
+ storeysAboveGround = storeyHeightsAboveGround.length;
135
+ storeyHeightsBelowGround = [];
136
+ storeysBelowGround = 0;
137
+ } else if (extrudedHeight < 0) {
138
+ storeyHeightsBelowGround = getStoreyHeights(
139
+ extrudedHeight,
140
+ storeyHeightsBelowGround,
141
+ storeysBelowGround,
142
+ );
143
+ storeysBelowGround = storeyHeightsBelowGround.length;
144
+ storeyHeightsAboveGround = [];
145
+ storeysAboveGround = 0;
146
+ }
147
+ }
148
+
149
+ validateStoreys(storeysAboveGround, storeyHeightsAboveGround);
150
+ validateStoreys(storeysBelowGround, storeyHeightsBelowGround);
151
+
152
+ const skirt = vectorProperties.getSkirt(feature);
153
+ const extruded = !!(
154
+ storeyHeightsAboveGround.length ||
155
+ storeyHeightsBelowGround.length ||
156
+ skirt
157
+ );
158
+
159
+ return {
160
+ extruded,
161
+ storeyHeightsAboveGround,
162
+ storeyHeightsBelowGround,
163
+ skirt,
164
+ };
165
+ }
166
+
167
+ /**
168
+ * @param geometry - feature must return simple geometry
169
+ * @retruns the center of mass
170
+ */
171
+ export function getClampOrigin(geometry: SimpleGeometry): [number, number] {
172
+ const stride = geometry.getStride();
173
+ const coordinates = geometry.getFlatCoordinates();
174
+ let x = 0;
175
+ let y = 0;
176
+ for (let i = 0; i < coordinates.length; i += stride) {
177
+ // calculates center of mass, maybe add
178
+ x += coordinates[i];
179
+ y += coordinates[i + 1];
180
+ }
181
+
182
+ const numberOfPoints = coordinates.length / stride;
183
+
184
+ return [x / numberOfPoints, y / numberOfPoints];
185
+ }
186
+
187
+ /**
188
+ * the minimum height of a geometry with a 3D layout
189
+ * @param geometry - with an XYZ layout
190
+ * @returns the minimum height
191
+ */
192
+ export function getMinHeight(geometry: Geometry): number {
193
+ if (!is(geometry, SimpleGeometry) || is2DLayout(geometry.getLayout())) {
194
+ throw new Error('expected geometry to be a simple YXZ geometry');
195
+ }
196
+
197
+ const stride = geometry.getStride();
198
+ const coordinates = geometry.getFlatCoordinates();
199
+
200
+ let minZ = Infinity;
201
+ for (let i = 0; i < coordinates.length; i += stride) {
202
+ const Z = coordinates[i + 2];
203
+ minZ = Z < minZ ? Z : minZ;
204
+ }
205
+
206
+ return minZ;
207
+ }
208
+
209
+ export function getHeightInfo(
210
+ feature: Feature,
211
+ geometry: SimpleGeometry,
212
+ vectorProperties: VectorProperties,
213
+ ): VectorHeightInfo {
214
+ const extrusionHeightInfo = getExtrusionHeightInfo(feature, vectorProperties);
215
+
216
+ let heightReference = vectorProperties.getAltitudeMode(feature);
217
+ let heightAboveGround: number | undefined;
218
+
219
+ const layout = geometry.getLayout();
220
+ const groundLevel = vectorProperties.getGroundLevel(feature);
221
+
222
+ // we cannot render a two D coordinate absolutely without having a Z value (ground level)
223
+ // switch altitude mode to clamp
224
+ if (
225
+ is2DLayout(layout) &&
226
+ isAbsoluteHeightReference(heightReference) &&
227
+ groundLevel == null
228
+ ) {
229
+ heightReference = HeightReference.CLAMP_TO_GROUND;
230
+ }
231
+
232
+ if (isClampedHeightReference(heightReference)) {
233
+ const geometryType = geometry.getType();
234
+ let pointAsPrimitive = false;
235
+ if (geometryType === 'Point' || geometryType === 'MultiPoint') {
236
+ pointAsPrimitive = vectorProperties.renderAs(feature) !== 'geometry';
237
+ }
238
+
239
+ // clamped extrusions or primitives get rendered relative to ground with a height above ground of 0;
240
+ if (extrusionHeightInfo.extruded || pointAsPrimitive) {
241
+ heightReference = getRelativeEquivalent(heightReference);
242
+ heightAboveGround = 0;
243
+ } else {
244
+ return {
245
+ heightReference,
246
+ layout,
247
+ };
248
+ }
249
+ }
250
+
251
+ if (isRelativeHeightReference(heightReference)) {
252
+ heightAboveGround =
253
+ vectorProperties.getHeightAboveGround(feature) ??
254
+ heightAboveGround ??
255
+ (is2DLayout(layout) ? 0 : undefined);
256
+
257
+ // we only need a clamp origin, if we dont already have a ground level
258
+ const clampOrigin =
259
+ groundLevel != null ? undefined : getClampOrigin(geometry);
260
+
261
+ // true if not all z values are identical. in case of relative geometries, we set Z to height above ground, not ground level
262
+ const perPositionHeight =
263
+ !is2DLayout(layout) &&
264
+ heightAboveGround == null &&
265
+ (!extrusionHeightInfo.extruded ||
266
+ (extrusionHeightInfo.extruded &&
267
+ extrusionHeightInfo.storeyHeightsAboveGround.length +
268
+ extrusionHeightInfo.storeyHeightsBelowGround.length ===
269
+ 1));
270
+
271
+ return {
272
+ ...extrusionHeightInfo,
273
+ heightReference,
274
+ layout,
275
+ heightAboveGround,
276
+ clampOrigin,
277
+ groundLevel,
278
+ perPositionHeight,
279
+ };
280
+ }
281
+
282
+ // true if not all z values are identical. if ground level is provided, all z values are equal to ground level.
283
+ const perPositionHeight =
284
+ !is2DLayout(layout) &&
285
+ groundLevel == null &&
286
+ (!extrusionHeightInfo.extruded ||
287
+ (extrusionHeightInfo.extruded &&
288
+ extrusionHeightInfo.storeyHeightsAboveGround.length +
289
+ extrusionHeightInfo.storeyHeightsBelowGround.length ===
290
+ 1));
291
+
292
+ return {
293
+ ...extrusionHeightInfo,
294
+ groundLevelOrMinHeight: groundLevel ?? getMinHeight(geometry),
295
+ perPositionHeight,
296
+ heightReference,
297
+ layout,
298
+ };
299
+ }
300
+
301
+ /**
302
+ * Returns the geometry height (as used in the cesium geometry options) depending on the height info. 0 for clamped, groundLevelOrMinHeight for absolute & heightAboveGround + groundLevel (if present) for relative
303
+ * If you pass "with extrusion" the height will be returned including the extrusion, otherwise you get the height of the actual geometry
304
+ */
305
+ export function getGeometryHeight(
306
+ geometry: SimpleGeometry,
307
+ heightInfo: VectorHeightInfo,
308
+ ): number {
309
+ let height = 0;
310
+ if (heightInfo.heightReference === HeightReference.NONE) {
311
+ height = heightInfo.groundLevelOrMinHeight;
312
+ } else if (isRelativeHeightReference(heightInfo.heightReference)) {
313
+ const relativeHeightInfo =
314
+ heightInfo as VectorHeightInfo<RelativeHeightReference>;
315
+ if (relativeHeightInfo.heightAboveGround != null) {
316
+ height = relativeHeightInfo.heightAboveGround;
317
+ } else {
318
+ // height info ensures this can only be a 3D layout
319
+ height = getMinHeight(geometry);
320
+ }
321
+
322
+ if (relativeHeightInfo.groundLevel) {
323
+ height += relativeHeightInfo.groundLevel;
324
+ }
325
+ }
326
+
327
+ return height;
328
+ }
329
+
330
+ /**
331
+ * @param {VectorHeightInfo} heightInfo
332
+ * @returns a callback function accepting a mercator coordinate. it will return a wgs84coordinate with its Z value adjusted according to the height info
333
+ */
334
+ export function mercatorToWgs84TransformerForHeightInfo(
335
+ heightInfo: VectorHeightInfo,
336
+ ): (coord: Coordinate) => Coordinate {
337
+ if (isClampedHeightReference(heightInfo.heightReference)) {
338
+ const layoutIs2D = is2DLayout(heightInfo.layout);
339
+ return (coord: Coordinate) => {
340
+ const wgs84Coords = Projection.mercatorToWgs84(coord);
341
+ wgs84Coords[2] = layoutIs2D ? 0 : wgs84Coords[2];
342
+ return wgs84Coords;
343
+ };
344
+ } else if (isRelativeHeightReference(heightInfo.heightReference)) {
345
+ const { heightAboveGround, groundLevel } =
346
+ heightInfo as VectorHeightInfo<RelativeHeightReference>;
347
+
348
+ return (coord: Coordinate) => {
349
+ // disregard layout, since height info guarantees either height above ground OR 3D layout
350
+ const wgs84Coords = Projection.mercatorToWgs84(coord);
351
+ if (heightAboveGround != null) {
352
+ wgs84Coords[2] = heightAboveGround;
353
+ }
354
+ if (groundLevel) {
355
+ wgs84Coords[2] += groundLevel;
356
+ }
357
+
358
+ return wgs84Coords;
359
+ };
360
+ }
361
+
362
+ const { groundLevelOrMinHeight, perPositionHeight } =
363
+ heightInfo as VectorHeightInfo<HeightReference.NONE>;
364
+
365
+ return (coord: Coordinate) => {
366
+ // disregard layout, since height info guarantees ground level OR 3D layout
367
+ const wgs84Coords = Projection.mercatorToWgs84(coord);
368
+ if (!perPositionHeight && groundLevelOrMinHeight) {
369
+ wgs84Coords[2] = groundLevelOrMinHeight;
370
+ }
371
+
372
+ return wgs84Coords;
373
+ };
374
+ }
375
+
376
+ /**
377
+ * @param {VectorHeightInfo} heightInfo
378
+ * @returns a callback function accepting a mercator coordinate. it will return a Cartesian3 with its Z value adjusted according to the height info
379
+ */
380
+ export function mercatorToCartesianTransformerForHeightInfo(
381
+ heightInfo: VectorHeightInfo,
382
+ ): (coord: Coordinate) => Cartesian3 {
383
+ const toWgs84 = mercatorToWgs84TransformerForHeightInfo(heightInfo);
384
+
385
+ return (coord) => {
386
+ const wgs84Coords = toWgs84(coord);
387
+ return Cartesian3.fromDegrees(
388
+ wgs84Coords[0],
389
+ wgs84Coords[1],
390
+ wgs84Coords[2],
391
+ );
392
+ };
393
+ }
@@ -1,19 +1,26 @@
1
+ import {
2
+ HeightReference,
3
+ sampleTerrainMostDetailed,
4
+ Scene,
5
+ } from '@vcmap-cesium/engine';
1
6
  import { offset as offsetSphere } from 'ol/sphere.js';
2
7
  import type { Coordinate } from 'ol/coordinate.js';
3
8
  import { fromCircle } from 'ol/geom/Polygon.js';
9
+ import { GeometryLayout } from 'ol/geom/Geometry.js';
4
10
  import {
5
- SimpleGeometry,
11
+ Circle,
6
12
  type Geometry,
7
13
  GeometryCollection,
8
- MultiPolygon,
14
+ LineString,
9
15
  MultiLineString,
10
16
  MultiPoint,
17
+ MultiPolygon,
11
18
  Point,
12
- Circle,
13
19
  Polygon,
14
- LineString,
20
+ SimpleGeometry,
15
21
  } from 'ol/geom.js';
16
22
  import Projection from './projection.js';
23
+ import { mercatorToCartographic } from './math.js';
17
24
 
18
25
  export function getFlatCoordinatesFromSimpleGeometry(
19
26
  geometry: SimpleGeometry,
@@ -94,7 +101,7 @@ export function circleFromCenterRadius(
94
101
  const dx2 = dx * dx;
95
102
  const dy2 = dy * dy;
96
103
  const radiusProjected = Math.sqrt(dx2 + dy2);
97
- return new Circle(center, radiusProjected, 'XYZ');
104
+ return new Circle(center, radiusProjected);
98
105
  }
99
106
 
100
107
  export function convertGeometryToPolygon(geometry: Geometry): Geometry {
@@ -168,3 +175,70 @@ export function enforceRightHand(ring: Coordinate[]): Coordinate[] {
168
175
 
169
176
  return ring;
170
177
  }
178
+
179
+ /**
180
+ * determines if a layout has only 2D coordinate values (XY or XYM)
181
+ * @param layout
182
+ */
183
+ export function is2DLayout(layout: GeometryLayout): boolean {
184
+ return layout === 'XY' || layout === 'XYM';
185
+ }
186
+
187
+ /**
188
+ * Will convert a 3D layout (XYZ or XYZM) to XY (or XYM). This changes the geometry in place. will not apply any changes,
189
+ * if the layout is already a 2D layout
190
+ * @param geometry
191
+ */
192
+ export function from3Dto2DLayout(geometry: Geometry): void {
193
+ const layout = geometry.getLayout();
194
+ if (is2DLayout(layout)) {
195
+ return;
196
+ }
197
+ const coordinates = geometry.getCoordinates() as any[];
198
+ const flatCoordinates = getFlatCoordinatesFromGeometry(geometry, coordinates);
199
+ flatCoordinates.forEach((coordinate) => {
200
+ if (layout === 'XYZM') {
201
+ coordinate[2] = coordinate.pop()!;
202
+ } else {
203
+ coordinate.pop();
204
+ }
205
+ });
206
+ geometry.setCoordinates(coordinates, layout === 'XYZM' ? 'XYM' : 'XY');
207
+ }
208
+
209
+ /**
210
+ * Wil transform a 2D geometry (layout XY XYM) in place to 3D (XYZ XYZM) using the provided scene & height reference.
211
+ * will no apply anything, if the layout is already 3D
212
+ * @param geometry
213
+ * @param scene
214
+ * @param heightReference
215
+ */
216
+ export async function from2Dto3DLayout(
217
+ geometry: Geometry,
218
+ scene: Scene,
219
+ heightReference:
220
+ | HeightReference.CLAMP_TO_GROUND
221
+ | HeightReference.CLAMP_TO_TERRAIN,
222
+ ): Promise<void> {
223
+ const layout = geometry.getLayout();
224
+ if (!is2DLayout(layout)) {
225
+ return;
226
+ }
227
+ const coordinates = geometry.getCoordinates() as any[];
228
+ const flatCoordinates = getFlatCoordinatesFromGeometry(geometry, coordinates);
229
+ const cartographics = flatCoordinates.map((c) => mercatorToCartographic(c));
230
+ if (heightReference === HeightReference.CLAMP_TO_GROUND) {
231
+ await scene.sampleHeightMostDetailed(cartographics);
232
+ } else {
233
+ await sampleTerrainMostDetailed(scene.terrainProvider, cartographics);
234
+ }
235
+ cartographics.forEach((c, index) => {
236
+ if (layout === 'XYM') {
237
+ flatCoordinates[index][3] = flatCoordinates[index][2];
238
+ flatCoordinates[index][2] = c.height;
239
+ } else {
240
+ flatCoordinates[index][2] = c.height;
241
+ }
242
+ });
243
+ geometry.setCoordinates(coordinates, layout === 'XYM' ? 'XYZM' : 'XYZ');
244
+ }
@@ -317,6 +317,10 @@ class MapCollection extends Collection<VcsMap> {
317
317
  map,
318
318
  error: error as Error,
319
319
  });
320
+ if (!map.fallbackMap && map.fallbackToCurrentMap && this._activeMap) {
321
+ this.fallbackMapActivated.raiseEvent(map);
322
+ return Promise.resolve();
323
+ }
320
324
  if (fallbackMap) {
321
325
  this.fallbackMapActivated.raiseEvent(map);
322
326
  return this.setActiveMap(fallbackMap.name);
@@ -341,6 +345,10 @@ class MapCollection extends Collection<VcsMap> {
341
345
  this.fallbackMapActivated.raiseEvent(map);
342
346
  return this.setActiveMap(fallbackMap.name);
343
347
  }
348
+ if (map.fallbackToCurrentMap && this._activeMap) {
349
+ this.fallbackMapActivated.raiseEvent(map);
350
+ return Promise.resolve();
351
+ }
344
352
  }
345
353
  this._cachedViewpoint = null;
346
354
  if (this._activeMap) {
package/src/util/math.ts CHANGED
@@ -40,8 +40,8 @@ export function coordinateAtDistance(
40
40
 
41
41
  /**
42
42
  * returns the initial bearing in degrees (0-360) between two coordinates
43
- * @param coords1 [lon, lat] in degrees
44
- * @param coords2 [lon, lat] in degrees
43
+ * @param coords1 - [lon, lat] in degrees
44
+ * @param coords2 - [lon, lat] in degrees
45
45
  * @returns ;
46
46
  */
47
47
  export function initialBearingBetweenCoords(
@@ -77,6 +77,15 @@ export function getCartesianBearing(p1: Coordinate, p2: Coordinate): number {
77
77
  return theta;
78
78
  }
79
79
 
80
+ export function cartesian2DDistanceSquared(
81
+ point0: Coordinate,
82
+ point1: Coordinate,
83
+ ): number {
84
+ const distX = point0[0] - point1[0];
85
+ const distY = point0[1] - point1[1];
86
+ return distX ** 2 + distY ** 2;
87
+ }
88
+
80
89
  /**
81
90
  * returns distance between two coordinates
82
91
  * @param point0
@@ -86,9 +95,7 @@ export function cartesian2DDistance(
86
95
  point0: Coordinate,
87
96
  point1: Coordinate,
88
97
  ): number {
89
- const distX = point0[0] - point1[0];
90
- const distY = point0[1] - point1[1];
91
- return Math.sqrt(distX ** 2 + distY ** 2);
98
+ return Math.sqrt(cartesian2DDistanceSquared(point0, point1));
92
99
  }
93
100
 
94
101
  export function cartesian3DDistance(p1: Coordinate, p2: Coordinate): number {
@@ -112,6 +119,18 @@ export function cartographicToWgs84(cartographic: Cartographic): number[] {
112
119
  ];
113
120
  }
114
121
 
122
+ export function wgs84ToCartographic(
123
+ wgs84Coordinates: Coordinate,
124
+ result?: Cartographic,
125
+ ): Cartographic {
126
+ return Cartographic.fromDegrees(
127
+ wgs84Coordinates[0],
128
+ wgs84Coordinates[1],
129
+ wgs84Coordinates[2],
130
+ result,
131
+ );
132
+ }
133
+
115
134
  export function mercatorToCartesian(
116
135
  mercatorCoordinates: Coordinate,
117
136
  result?: Cartesian3,
@@ -126,6 +145,14 @@ export function mercatorToCartesian(
126
145
  );
127
146
  }
128
147
 
148
+ export function mercatorToCartographic(
149
+ mercatorCoordinates: Coordinate,
150
+ result?: Cartographic,
151
+ ): Cartographic {
152
+ const wgs84Coords = Projection.mercatorToWgs84(mercatorCoordinates);
153
+ return wgs84ToCartographic(wgs84Coords, result);
154
+ }
155
+
129
156
  export function cartesianToMercator(cartesian: Cartesian3): Coordinate {
130
157
  const cartographic = Cartographic.fromCartesian(cartesian);
131
158
  const wgs84 = cartographicToWgs84(cartographic);
@@ -133,14 +160,12 @@ export function cartesianToMercator(cartesian: Cartesian3): Coordinate {
133
160
  }
134
161
 
135
162
  export function getMidPoint(p1: Coordinate, p2: Coordinate): Coordinate {
136
- if (p1.length < 3 && p2.length < 3) {
137
- return [p1[0] + (p2[0] - p1[0]) / 2, p1[1] + (p2[1] - p1[1]) / 2, 0];
163
+ const stride = p1.length;
164
+ const output = new Array<number>(stride);
165
+ for (let i = 0; i < stride; i++) {
166
+ output[i] = p1[i] + (p2[i] - p1[i]) / 2;
138
167
  }
139
- return [
140
- p1[0] + (p2[0] - p1[0]) / 2,
141
- p1[1] + (p2[1] - p1[1]) / 2,
142
- p1[2] + (p2[2] - p1[2]) / 2,
143
- ];
168
+ return output;
144
169
  }
145
170
 
146
171
  /**
@@ -178,3 +203,25 @@ export function getCartesianPitch(p1: Coordinate, p2: Coordinate): number {
178
203
 
179
204
  return pitch;
180
205
  }
206
+
207
+ function perpDot(a: number[], b: number[]): number {
208
+ return a[0] * b[1] - a[1] * b[0];
209
+ }
210
+
211
+ // loosely copied from http://www.sunshine2k.de/coding/javascript/lineintersection2d/LineIntersect2D.html
212
+ export function cartesian2Intersection(
213
+ lineA: [Coordinate, Coordinate],
214
+ lineB: [Coordinate, Coordinate],
215
+ ): Coordinate | undefined {
216
+ const A = [lineA[1][0] - lineA[0][0], lineA[1][1] - lineA[0][1]];
217
+ const B = [lineB[1][0] - lineB[0][0], lineB[1][1] - lineB[0][1]];
218
+
219
+ if (CesiumMath.equalsEpsilon(perpDot(A, B), 0, CesiumMath.EPSILON8)) {
220
+ return undefined;
221
+ }
222
+
223
+ const U = [lineB[0][0] - lineA[0][0], lineB[0][1] - lineA[0][1]];
224
+ const s = perpDot(B, U) / perpDot(B, A);
225
+
226
+ return [lineA[0][0] + s * A[0], lineA[0][1] + s * A[1]];
227
+ }
@@ -1,35 +0,0 @@
1
- import type { Feature } from 'ol/index.js';
2
- import type { SimpleGeometry } from 'ol/geom.js';
3
- import type { Style, Fill } from 'ol/style.js';
4
- import type { Coordinate } from 'ol/coordinate.js';
5
- import { HeightReference, MaterialAppearance, ClassificationType, GroundPrimitive, GroundPolylinePrimitive, ClassificationPrimitive, Primitive, Color, type Scene, type PolylineGeometry, type GroundPolylineGeometry, type PolygonGeometry, type CircleGeometry, type WallGeometry } from '@vcmap-cesium/engine';
6
- import type VectorProperties from '../../layer/vectorProperties.js';
7
- import type { VectorGeometryFactoryType, VectorHeightInfo } from '../../layer/vectorLayer.js';
8
- import type { AsyncCesiumVectorContext } from '../../layer/cesium/vectorContext.js';
9
- export declare function getMaterialAppearance(scene: Scene, fill: Fill, feature: Feature): MaterialAppearance;
10
- export declare function createClassificationPrimitive(options: Partial<ConstructorParameters<typeof ClassificationPrimitive>[0]>, geometries: (PolygonGeometry | CircleGeometry | WallGeometry)[], color: Color, classificationType: ClassificationType): ClassificationPrimitive;
11
- export declare function createPrimitive(scene: Scene, vectorProperties: VectorProperties, allowPicking: boolean, feature: Feature, geometries: (PolygonGeometry | CircleGeometry | WallGeometry)[], style: Style, groundPrimitive: boolean): Primitive | GroundPrimitive | ClassificationPrimitive | null;
12
- export declare function createOutlinePrimitive(_scene: Scene, _vectorProperties: VectorProperties, allowPicking: boolean, feature: Feature, geometries: (PolygonGeometry | CircleGeometry | WallGeometry)[], style: Style): Primitive;
13
- export declare function createLinePrimitive(scene: Scene, vectorProperties: VectorProperties, allowPicking: boolean, feature: Feature, geometries: (PolylineGeometry | GroundPolylineGeometry)[], style: Style, groundPrimitive: boolean): Primitive | GroundPolylinePrimitive | null;
14
- /**
15
- * returns groundlevel or extracts the minimum height from the coordinates, returns 0 if no z coordinates are set
16
- * @param groundLevel
17
- * @param coordinates
18
- */
19
- export declare function getMinHeightOrGroundLevel(groundLevel: number | null | undefined, coordinates?: Coordinate[]): number;
20
- /**
21
- * @param extrudedHeight should be a number > 0
22
- * @param storeyHeights
23
- * @param storeyNumber
24
- */
25
- export declare function getStoreyHeights(extrudedHeight: number, storeyHeights: number[], storeyNumber: number): number[];
26
- export declare function validateStoreys(storeys: number, storeyHeights: number[]): void;
27
- export declare function getHeightAboveGround(feature: Feature, heightReference: HeightReference, vectorProperties: VectorProperties): number;
28
- export declare function getHeightInfo(feature: Feature, vectorProperties: VectorProperties, coordinates: Coordinate[]): VectorHeightInfo;
29
- type StoreyOptions = {
30
- currentHeight: number;
31
- extrudedHeight: number;
32
- };
33
- export declare function getStoreyOptions(storeyHeights: number[], initialHeight: number, down?: boolean, result?: StoreyOptions[]): StoreyOptions[];
34
- export declare function addPrimitivesToContext(feature: Feature, style: Style, geometries: SimpleGeometry[], vectorProperties: VectorProperties, scene: Scene, geometryFactory: VectorGeometryFactoryType, context: AsyncCesiumVectorContext): void;
35
- export {};