createVerticesFromGoogleEarthEnterpriseBuffer.js 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641
  1. /* This file is automatically rebuilt by the Cesium build process. */
  2. define(['./AxisAlignedBoundingBox-8103739f', './Transforms-a076dbe6', './Matrix2-fc7e9822', './defaultValue-94c3e563', './TerrainEncoding-f29761bd', './ComponentDatatype-4a60b8d6', './OrientedBoundingBox-417528c0', './RuntimeError-c581ca93', './WebMercatorProjection-843df830', './createTaskProcessorWorker', './_commonjsHelpers-3aae1032-f55dc0c4', './combine-761d9c3f', './AttributeCompression-4d18cc04', './WebGLConstants-7dccdc96', './EllipsoidTangentPlane-d2c0c530', './IntersectionTests-5deed78b', './Plane-e20fba8c'], (function (AxisAlignedBoundingBox, Transforms, Matrix2, defaultValue, TerrainEncoding, ComponentDatatype, OrientedBoundingBox, RuntimeError, WebMercatorProjection, createTaskProcessorWorker, _commonjsHelpers3aae1032, combine, AttributeCompression, WebGLConstants, EllipsoidTangentPlane, IntersectionTests, Plane) { 'use strict';
  3. const sizeOfUint16 = Uint16Array.BYTES_PER_ELEMENT;
  4. const sizeOfInt32 = Int32Array.BYTES_PER_ELEMENT;
  5. const sizeOfUint32 = Uint32Array.BYTES_PER_ELEMENT;
  6. const sizeOfFloat = Float32Array.BYTES_PER_ELEMENT;
  7. const sizeOfDouble = Float64Array.BYTES_PER_ELEMENT;
  8. function indexOfEpsilon(arr, elem, elemType) {
  9. elemType = defaultValue.defaultValue(elemType, ComponentDatatype.CesiumMath);
  10. const count = arr.length;
  11. for (let i = 0; i < count; ++i) {
  12. if (elemType.equalsEpsilon(arr[i], elem, ComponentDatatype.CesiumMath.EPSILON12)) {
  13. return i;
  14. }
  15. }
  16. return -1;
  17. }
  18. function createVerticesFromGoogleEarthEnterpriseBuffer(
  19. parameters,
  20. transferableObjects
  21. ) {
  22. parameters.ellipsoid = Matrix2.Ellipsoid.clone(parameters.ellipsoid);
  23. parameters.rectangle = Matrix2.Rectangle.clone(parameters.rectangle);
  24. const statistics = processBuffer(
  25. parameters.buffer,
  26. parameters.relativeToCenter,
  27. parameters.ellipsoid,
  28. parameters.rectangle,
  29. parameters.nativeRectangle,
  30. parameters.exaggeration,
  31. parameters.exaggerationRelativeHeight,
  32. parameters.skirtHeight,
  33. parameters.includeWebMercatorT,
  34. parameters.negativeAltitudeExponentBias,
  35. parameters.negativeElevationThreshold
  36. );
  37. const vertices = statistics.vertices;
  38. transferableObjects.push(vertices.buffer);
  39. const indices = statistics.indices;
  40. transferableObjects.push(indices.buffer);
  41. return {
  42. vertices: vertices.buffer,
  43. indices: indices.buffer,
  44. numberOfAttributes: statistics.encoding.stride,
  45. minimumHeight: statistics.minimumHeight,
  46. maximumHeight: statistics.maximumHeight,
  47. boundingSphere3D: statistics.boundingSphere3D,
  48. orientedBoundingBox: statistics.orientedBoundingBox,
  49. occludeePointInScaledSpace: statistics.occludeePointInScaledSpace,
  50. encoding: statistics.encoding,
  51. vertexCountWithoutSkirts: statistics.vertexCountWithoutSkirts,
  52. indexCountWithoutSkirts: statistics.indexCountWithoutSkirts,
  53. westIndicesSouthToNorth: statistics.westIndicesSouthToNorth,
  54. southIndicesEastToWest: statistics.southIndicesEastToWest,
  55. eastIndicesNorthToSouth: statistics.eastIndicesNorthToSouth,
  56. northIndicesWestToEast: statistics.northIndicesWestToEast,
  57. };
  58. }
  59. const scratchCartographic = new Matrix2.Cartographic();
  60. const scratchCartesian = new Matrix2.Cartesian3();
  61. const minimumScratch = new Matrix2.Cartesian3();
  62. const maximumScratch = new Matrix2.Cartesian3();
  63. const matrix4Scratch = new Matrix2.Matrix4();
  64. function processBuffer(
  65. buffer,
  66. relativeToCenter,
  67. ellipsoid,
  68. rectangle,
  69. nativeRectangle,
  70. exaggeration,
  71. exaggerationRelativeHeight,
  72. skirtHeight,
  73. includeWebMercatorT,
  74. negativeAltitudeExponentBias,
  75. negativeElevationThreshold
  76. ) {
  77. let geographicWest;
  78. let geographicSouth;
  79. let geographicEast;
  80. let geographicNorth;
  81. let rectangleWidth, rectangleHeight;
  82. if (!defaultValue.defined(rectangle)) {
  83. geographicWest = ComponentDatatype.CesiumMath.toRadians(nativeRectangle.west);
  84. geographicSouth = ComponentDatatype.CesiumMath.toRadians(nativeRectangle.south);
  85. geographicEast = ComponentDatatype.CesiumMath.toRadians(nativeRectangle.east);
  86. geographicNorth = ComponentDatatype.CesiumMath.toRadians(nativeRectangle.north);
  87. rectangleWidth = ComponentDatatype.CesiumMath.toRadians(rectangle.width);
  88. rectangleHeight = ComponentDatatype.CesiumMath.toRadians(rectangle.height);
  89. } else {
  90. geographicWest = rectangle.west;
  91. geographicSouth = rectangle.south;
  92. geographicEast = rectangle.east;
  93. geographicNorth = rectangle.north;
  94. rectangleWidth = rectangle.width;
  95. rectangleHeight = rectangle.height;
  96. }
  97. // Keep track of quad borders so we can remove duplicates around the borders
  98. const quadBorderLatitudes = [geographicSouth, geographicNorth];
  99. const quadBorderLongitudes = [geographicWest, geographicEast];
  100. const fromENU = Transforms.Transforms.eastNorthUpToFixedFrame(
  101. relativeToCenter,
  102. ellipsoid
  103. );
  104. const toENU = Matrix2.Matrix4.inverseTransformation(fromENU, matrix4Scratch);
  105. let southMercatorY;
  106. let oneOverMercatorHeight;
  107. if (includeWebMercatorT) {
  108. southMercatorY = WebMercatorProjection.WebMercatorProjection.geodeticLatitudeToMercatorAngle(
  109. geographicSouth
  110. );
  111. oneOverMercatorHeight =
  112. 1.0 /
  113. (WebMercatorProjection.WebMercatorProjection.geodeticLatitudeToMercatorAngle(geographicNorth) -
  114. southMercatorY);
  115. }
  116. const hasExaggeration = exaggeration !== 1.0;
  117. const includeGeodeticSurfaceNormals = hasExaggeration;
  118. const dv = new DataView(buffer);
  119. let minHeight = Number.POSITIVE_INFINITY;
  120. let maxHeight = Number.NEGATIVE_INFINITY;
  121. const minimum = minimumScratch;
  122. minimum.x = Number.POSITIVE_INFINITY;
  123. minimum.y = Number.POSITIVE_INFINITY;
  124. minimum.z = Number.POSITIVE_INFINITY;
  125. const maximum = maximumScratch;
  126. maximum.x = Number.NEGATIVE_INFINITY;
  127. maximum.y = Number.NEGATIVE_INFINITY;
  128. maximum.z = Number.NEGATIVE_INFINITY;
  129. // Compute sizes
  130. let offset = 0;
  131. let size = 0;
  132. let indicesSize = 0;
  133. let quadSize;
  134. let quad;
  135. for (quad = 0; quad < 4; ++quad) {
  136. let o = offset;
  137. quadSize = dv.getUint32(o, true);
  138. o += sizeOfUint32;
  139. const x = ComponentDatatype.CesiumMath.toRadians(dv.getFloat64(o, true) * 180.0);
  140. o += sizeOfDouble;
  141. if (indexOfEpsilon(quadBorderLongitudes, x) === -1) {
  142. quadBorderLongitudes.push(x);
  143. }
  144. const y = ComponentDatatype.CesiumMath.toRadians(dv.getFloat64(o, true) * 180.0);
  145. o += sizeOfDouble;
  146. if (indexOfEpsilon(quadBorderLatitudes, y) === -1) {
  147. quadBorderLatitudes.push(y);
  148. }
  149. o += 2 * sizeOfDouble; // stepX + stepY
  150. let c = dv.getInt32(o, true); // Read point count
  151. o += sizeOfInt32;
  152. size += c;
  153. c = dv.getInt32(o, true); // Read index count
  154. indicesSize += c * 3;
  155. offset += quadSize + sizeOfUint32; // Jump to next quad
  156. }
  157. // Quad Border points to remove duplicates
  158. const quadBorderPoints = [];
  159. const quadBorderIndices = [];
  160. // Create arrays
  161. const positions = new Array(size);
  162. const uvs = new Array(size);
  163. const heights = new Array(size);
  164. const webMercatorTs = includeWebMercatorT ? new Array(size) : [];
  165. const geodeticSurfaceNormals = includeGeodeticSurfaceNormals
  166. ? new Array(size)
  167. : [];
  168. const indices = new Array(indicesSize);
  169. // Points are laid out in rows starting at SW, so storing border points as we
  170. // come across them all points will be adjacent.
  171. const westBorder = [];
  172. const southBorder = [];
  173. const eastBorder = [];
  174. const northBorder = [];
  175. // Each tile is split into 4 parts
  176. let pointOffset = 0;
  177. let indicesOffset = 0;
  178. offset = 0;
  179. for (quad = 0; quad < 4; ++quad) {
  180. quadSize = dv.getUint32(offset, true);
  181. offset += sizeOfUint32;
  182. const startQuad = offset;
  183. const originX = ComponentDatatype.CesiumMath.toRadians(dv.getFloat64(offset, true) * 180.0);
  184. offset += sizeOfDouble;
  185. const originY = ComponentDatatype.CesiumMath.toRadians(dv.getFloat64(offset, true) * 180.0);
  186. offset += sizeOfDouble;
  187. const stepX = ComponentDatatype.CesiumMath.toRadians(dv.getFloat64(offset, true) * 180.0);
  188. const halfStepX = stepX * 0.5;
  189. offset += sizeOfDouble;
  190. const stepY = ComponentDatatype.CesiumMath.toRadians(dv.getFloat64(offset, true) * 180.0);
  191. const halfStepY = stepY * 0.5;
  192. offset += sizeOfDouble;
  193. const numPoints = dv.getInt32(offset, true);
  194. offset += sizeOfInt32;
  195. const numFaces = dv.getInt32(offset, true);
  196. offset += sizeOfInt32;
  197. //const level = dv.getInt32(offset, true);
  198. offset += sizeOfInt32;
  199. // Keep track of quad indices to overall tile indices
  200. const indicesMapping = new Array(numPoints);
  201. for (let i = 0; i < numPoints; ++i) {
  202. const longitude = originX + dv.getUint8(offset++) * stepX;
  203. scratchCartographic.longitude = longitude;
  204. const latitude = originY + dv.getUint8(offset++) * stepY;
  205. scratchCartographic.latitude = latitude;
  206. let height = dv.getFloat32(offset, true);
  207. offset += sizeOfFloat;
  208. // In order to support old clients, negative altitude values are stored as
  209. // height/-2^32. Old clients see the value as really close to 0 but new clients multiply
  210. // by -2^32 to get the real negative altitude value.
  211. if (height !== 0 && height < negativeElevationThreshold) {
  212. height *= -Math.pow(2, negativeAltitudeExponentBias);
  213. }
  214. // Height is stored in units of (1/EarthRadius) or (1/6371010.0)
  215. height *= 6371010.0;
  216. scratchCartographic.height = height;
  217. // Is it along a quad border - if so check if already exists and use that index
  218. if (
  219. indexOfEpsilon(quadBorderLongitudes, longitude) !== -1 ||
  220. indexOfEpsilon(quadBorderLatitudes, latitude) !== -1
  221. ) {
  222. const index = indexOfEpsilon(
  223. quadBorderPoints,
  224. scratchCartographic,
  225. Matrix2.Cartographic
  226. );
  227. if (index === -1) {
  228. quadBorderPoints.push(Matrix2.Cartographic.clone(scratchCartographic));
  229. quadBorderIndices.push(pointOffset);
  230. } else {
  231. indicesMapping[i] = quadBorderIndices[index];
  232. continue;
  233. }
  234. }
  235. indicesMapping[i] = pointOffset;
  236. if (Math.abs(longitude - geographicWest) < halfStepX) {
  237. westBorder.push({
  238. index: pointOffset,
  239. cartographic: Matrix2.Cartographic.clone(scratchCartographic),
  240. });
  241. } else if (Math.abs(longitude - geographicEast) < halfStepX) {
  242. eastBorder.push({
  243. index: pointOffset,
  244. cartographic: Matrix2.Cartographic.clone(scratchCartographic),
  245. });
  246. } else if (Math.abs(latitude - geographicSouth) < halfStepY) {
  247. southBorder.push({
  248. index: pointOffset,
  249. cartographic: Matrix2.Cartographic.clone(scratchCartographic),
  250. });
  251. } else if (Math.abs(latitude - geographicNorth) < halfStepY) {
  252. northBorder.push({
  253. index: pointOffset,
  254. cartographic: Matrix2.Cartographic.clone(scratchCartographic),
  255. });
  256. }
  257. minHeight = Math.min(height, minHeight);
  258. maxHeight = Math.max(height, maxHeight);
  259. heights[pointOffset] = height;
  260. const pos = ellipsoid.cartographicToCartesian(scratchCartographic);
  261. positions[pointOffset] = pos;
  262. if (includeWebMercatorT) {
  263. webMercatorTs[pointOffset] =
  264. (WebMercatorProjection.WebMercatorProjection.geodeticLatitudeToMercatorAngle(latitude) -
  265. southMercatorY) *
  266. oneOverMercatorHeight;
  267. }
  268. if (includeGeodeticSurfaceNormals) {
  269. const normal = ellipsoid.geodeticSurfaceNormal(pos);
  270. geodeticSurfaceNormals[pointOffset] = normal;
  271. }
  272. Matrix2.Matrix4.multiplyByPoint(toENU, pos, scratchCartesian);
  273. Matrix2.Cartesian3.minimumByComponent(scratchCartesian, minimum, minimum);
  274. Matrix2.Cartesian3.maximumByComponent(scratchCartesian, maximum, maximum);
  275. let u = (longitude - geographicWest) / (geographicEast - geographicWest);
  276. u = ComponentDatatype.CesiumMath.clamp(u, 0.0, 1.0);
  277. let v =
  278. (latitude - geographicSouth) / (geographicNorth - geographicSouth);
  279. v = ComponentDatatype.CesiumMath.clamp(v, 0.0, 1.0);
  280. uvs[pointOffset] = new Matrix2.Cartesian2(u, v);
  281. ++pointOffset;
  282. }
  283. const facesElementCount = numFaces * 3;
  284. for (let j = 0; j < facesElementCount; ++j, ++indicesOffset) {
  285. indices[indicesOffset] = indicesMapping[dv.getUint16(offset, true)];
  286. offset += sizeOfUint16;
  287. }
  288. if (quadSize !== offset - startQuad) {
  289. throw new RuntimeError.RuntimeError("Invalid terrain tile.");
  290. }
  291. }
  292. positions.length = pointOffset;
  293. uvs.length = pointOffset;
  294. heights.length = pointOffset;
  295. if (includeWebMercatorT) {
  296. webMercatorTs.length = pointOffset;
  297. }
  298. if (includeGeodeticSurfaceNormals) {
  299. geodeticSurfaceNormals.length = pointOffset;
  300. }
  301. const vertexCountWithoutSkirts = pointOffset;
  302. const indexCountWithoutSkirts = indicesOffset;
  303. // Add skirt points
  304. const skirtOptions = {
  305. hMin: minHeight,
  306. lastBorderPoint: undefined,
  307. skirtHeight: skirtHeight,
  308. toENU: toENU,
  309. ellipsoid: ellipsoid,
  310. minimum: minimum,
  311. maximum: maximum,
  312. };
  313. // Sort counter clockwise from NW corner
  314. // Corner points are in the east/west arrays
  315. westBorder.sort(function (a, b) {
  316. return b.cartographic.latitude - a.cartographic.latitude;
  317. });
  318. southBorder.sort(function (a, b) {
  319. return a.cartographic.longitude - b.cartographic.longitude;
  320. });
  321. eastBorder.sort(function (a, b) {
  322. return a.cartographic.latitude - b.cartographic.latitude;
  323. });
  324. northBorder.sort(function (a, b) {
  325. return b.cartographic.longitude - a.cartographic.longitude;
  326. });
  327. const percentage = 0.00001;
  328. addSkirt(
  329. positions,
  330. heights,
  331. uvs,
  332. webMercatorTs,
  333. geodeticSurfaceNormals,
  334. indices,
  335. skirtOptions,
  336. westBorder,
  337. -percentage * rectangleWidth,
  338. true,
  339. -percentage * rectangleHeight
  340. );
  341. addSkirt(
  342. positions,
  343. heights,
  344. uvs,
  345. webMercatorTs,
  346. geodeticSurfaceNormals,
  347. indices,
  348. skirtOptions,
  349. southBorder,
  350. -percentage * rectangleHeight,
  351. false
  352. );
  353. addSkirt(
  354. positions,
  355. heights,
  356. uvs,
  357. webMercatorTs,
  358. geodeticSurfaceNormals,
  359. indices,
  360. skirtOptions,
  361. eastBorder,
  362. percentage * rectangleWidth,
  363. true,
  364. percentage * rectangleHeight
  365. );
  366. addSkirt(
  367. positions,
  368. heights,
  369. uvs,
  370. webMercatorTs,
  371. geodeticSurfaceNormals,
  372. indices,
  373. skirtOptions,
  374. northBorder,
  375. percentage * rectangleHeight,
  376. false
  377. );
  378. // Since the corner between the north and west sides is in the west array, generate the last
  379. // two triangles between the last north vertex and the first west vertex
  380. if (westBorder.length > 0 && northBorder.length > 0) {
  381. const firstBorderIndex = westBorder[0].index;
  382. const firstSkirtIndex = vertexCountWithoutSkirts;
  383. const lastBorderIndex = northBorder[northBorder.length - 1].index;
  384. const lastSkirtIndex = positions.length - 1;
  385. indices.push(
  386. lastBorderIndex,
  387. lastSkirtIndex,
  388. firstSkirtIndex,
  389. firstSkirtIndex,
  390. firstBorderIndex,
  391. lastBorderIndex
  392. );
  393. }
  394. size = positions.length; // Get new size with skirt vertices
  395. const boundingSphere3D = Transforms.BoundingSphere.fromPoints(positions);
  396. let orientedBoundingBox;
  397. if (defaultValue.defined(rectangle)) {
  398. orientedBoundingBox = OrientedBoundingBox.OrientedBoundingBox.fromRectangle(
  399. rectangle,
  400. minHeight,
  401. maxHeight,
  402. ellipsoid
  403. );
  404. }
  405. const occluder = new TerrainEncoding.EllipsoidalOccluder(ellipsoid);
  406. const occludeePointInScaledSpace = occluder.computeHorizonCullingPointPossiblyUnderEllipsoid(
  407. relativeToCenter,
  408. positions,
  409. minHeight
  410. );
  411. const aaBox = new AxisAlignedBoundingBox.AxisAlignedBoundingBox(minimum, maximum, relativeToCenter);
  412. const encoding = new TerrainEncoding.TerrainEncoding(
  413. relativeToCenter,
  414. aaBox,
  415. skirtOptions.hMin,
  416. maxHeight,
  417. fromENU,
  418. false,
  419. includeWebMercatorT,
  420. includeGeodeticSurfaceNormals,
  421. exaggeration,
  422. exaggerationRelativeHeight
  423. );
  424. const vertices = new Float32Array(size * encoding.stride);
  425. let bufferIndex = 0;
  426. for (let k = 0; k < size; ++k) {
  427. bufferIndex = encoding.encode(
  428. vertices,
  429. bufferIndex,
  430. positions[k],
  431. uvs[k],
  432. heights[k],
  433. undefined,
  434. webMercatorTs[k],
  435. geodeticSurfaceNormals[k]
  436. );
  437. }
  438. const westIndicesSouthToNorth = westBorder
  439. .map(function (vertex) {
  440. return vertex.index;
  441. })
  442. .reverse();
  443. const southIndicesEastToWest = southBorder
  444. .map(function (vertex) {
  445. return vertex.index;
  446. })
  447. .reverse();
  448. const eastIndicesNorthToSouth = eastBorder
  449. .map(function (vertex) {
  450. return vertex.index;
  451. })
  452. .reverse();
  453. const northIndicesWestToEast = northBorder
  454. .map(function (vertex) {
  455. return vertex.index;
  456. })
  457. .reverse();
  458. southIndicesEastToWest.unshift(
  459. eastIndicesNorthToSouth[eastIndicesNorthToSouth.length - 1]
  460. );
  461. southIndicesEastToWest.push(westIndicesSouthToNorth[0]);
  462. northIndicesWestToEast.unshift(
  463. westIndicesSouthToNorth[westIndicesSouthToNorth.length - 1]
  464. );
  465. northIndicesWestToEast.push(eastIndicesNorthToSouth[0]);
  466. return {
  467. vertices: vertices,
  468. indices: new Uint16Array(indices),
  469. maximumHeight: maxHeight,
  470. minimumHeight: minHeight,
  471. encoding: encoding,
  472. boundingSphere3D: boundingSphere3D,
  473. orientedBoundingBox: orientedBoundingBox,
  474. occludeePointInScaledSpace: occludeePointInScaledSpace,
  475. vertexCountWithoutSkirts: vertexCountWithoutSkirts,
  476. indexCountWithoutSkirts: indexCountWithoutSkirts,
  477. westIndicesSouthToNorth: westIndicesSouthToNorth,
  478. southIndicesEastToWest: southIndicesEastToWest,
  479. eastIndicesNorthToSouth: eastIndicesNorthToSouth,
  480. northIndicesWestToEast: northIndicesWestToEast,
  481. };
  482. }
  483. function addSkirt(
  484. positions,
  485. heights,
  486. uvs,
  487. webMercatorTs,
  488. geodeticSurfaceNormals,
  489. indices,
  490. skirtOptions,
  491. borderPoints,
  492. fudgeFactor,
  493. eastOrWest,
  494. cornerFudge
  495. ) {
  496. const count = borderPoints.length;
  497. for (let j = 0; j < count; ++j) {
  498. const borderPoint = borderPoints[j];
  499. const borderCartographic = borderPoint.cartographic;
  500. const borderIndex = borderPoint.index;
  501. const currentIndex = positions.length;
  502. const longitude = borderCartographic.longitude;
  503. let latitude = borderCartographic.latitude;
  504. latitude = ComponentDatatype.CesiumMath.clamp(
  505. latitude,
  506. -ComponentDatatype.CesiumMath.PI_OVER_TWO,
  507. ComponentDatatype.CesiumMath.PI_OVER_TWO
  508. ); // Don't go over the poles
  509. const height = borderCartographic.height - skirtOptions.skirtHeight;
  510. skirtOptions.hMin = Math.min(skirtOptions.hMin, height);
  511. Matrix2.Cartographic.fromRadians(longitude, latitude, height, scratchCartographic);
  512. // Adjust sides to angle out
  513. if (eastOrWest) {
  514. scratchCartographic.longitude += fudgeFactor;
  515. }
  516. // Adjust top or bottom to angle out
  517. // Since corners are in the east/west arrays angle the first and last points as well
  518. if (!eastOrWest) {
  519. scratchCartographic.latitude += fudgeFactor;
  520. } else if (j === count - 1) {
  521. scratchCartographic.latitude += cornerFudge;
  522. } else if (j === 0) {
  523. scratchCartographic.latitude -= cornerFudge;
  524. }
  525. const pos = skirtOptions.ellipsoid.cartographicToCartesian(
  526. scratchCartographic
  527. );
  528. positions.push(pos);
  529. heights.push(height);
  530. uvs.push(Matrix2.Cartesian2.clone(uvs[borderIndex])); // Copy UVs from border point
  531. if (webMercatorTs.length > 0) {
  532. webMercatorTs.push(webMercatorTs[borderIndex]);
  533. }
  534. if (geodeticSurfaceNormals.length > 0) {
  535. geodeticSurfaceNormals.push(geodeticSurfaceNormals[borderIndex]);
  536. }
  537. Matrix2.Matrix4.multiplyByPoint(skirtOptions.toENU, pos, scratchCartesian);
  538. const minimum = skirtOptions.minimum;
  539. const maximum = skirtOptions.maximum;
  540. Matrix2.Cartesian3.minimumByComponent(scratchCartesian, minimum, minimum);
  541. Matrix2.Cartesian3.maximumByComponent(scratchCartesian, maximum, maximum);
  542. const lastBorderPoint = skirtOptions.lastBorderPoint;
  543. if (defaultValue.defined(lastBorderPoint)) {
  544. const lastBorderIndex = lastBorderPoint.index;
  545. indices.push(
  546. lastBorderIndex,
  547. currentIndex - 1,
  548. currentIndex,
  549. currentIndex,
  550. borderIndex,
  551. lastBorderIndex
  552. );
  553. }
  554. skirtOptions.lastBorderPoint = borderPoint;
  555. }
  556. }
  557. var createVerticesFromGoogleEarthEnterpriseBuffer$1 = createTaskProcessorWorker(
  558. createVerticesFromGoogleEarthEnterpriseBuffer
  559. );
  560. return createVerticesFromGoogleEarthEnterpriseBuffer$1;
  561. }));