Vector3DTileClampedPolylines.js 24 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765
  1. import ApproximateTerrainHeights from "../Core/ApproximateTerrainHeights.js";
  2. import arraySlice from "../Core/arraySlice.js";
  3. import Cartesian2 from "../Core/Cartesian2.js";
  4. import Cartesian3 from "../Core/Cartesian3.js";
  5. import Color from "../Core/Color.js";
  6. import ComponentDatatype from "../Core/ComponentDatatype.js";
  7. import defaultValue from "../Core/defaultValue.js";
  8. import defer from "../Core/defer.js";
  9. import defined from "../Core/defined.js";
  10. import destroyObject from "../Core/destroyObject.js";
  11. import Ellipsoid from "../Core/Ellipsoid.js";
  12. import FeatureDetection from "../Core/FeatureDetection.js";
  13. import IndexDatatype from "../Core/IndexDatatype.js";
  14. import OrientedBoundingBox from "../Core/OrientedBoundingBox.js";
  15. import Matrix4 from "../Core/Matrix4.js";
  16. import Rectangle from "../Core/Rectangle.js";
  17. import TaskProcessor from "../Core/TaskProcessor.js";
  18. import Buffer from "../Renderer/Buffer.js";
  19. import BufferUsage from "../Renderer/BufferUsage.js";
  20. import DrawCommand from "../Renderer/DrawCommand.js";
  21. import Pass from "../Renderer/Pass.js";
  22. import RenderState from "../Renderer/RenderState.js";
  23. import ShaderProgram from "../Renderer/ShaderProgram.js";
  24. import ShaderSource from "../Renderer/ShaderSource.js";
  25. import VertexArray from "../Renderer/VertexArray.js";
  26. import PolylineCommon from "../Shaders/PolylineCommon.js";
  27. import Vector3DTileClampedPolylinesVS from "../Shaders/Vector3DTileClampedPolylinesVS.js";
  28. import Vector3DTileClampedPolylinesFS from "../Shaders/Vector3DTileClampedPolylinesFS.js";
  29. import BlendingState from "./BlendingState.js";
  30. import Cesium3DTileFeature from "./Cesium3DTileFeature.js";
  31. import ClassificationType from "./ClassificationType.js";
  32. import CullFace from "./CullFace.js";
  33. import StencilConstants from "./StencilConstants.js";
  34. import StencilFunction from "./StencilFunction.js";
  35. import StencilOperation from "./StencilOperation.js";
  36. import Vector3DTilePolylines from "./Vector3DTilePolylines.js";
  37. /**
  38. * Creates a batch of polylines as volumes with shader-adjustable width.
  39. *
  40. * @alias Vector3DTileClampedPolylines
  41. * @constructor
  42. *
  43. * @param {Object} options An object with following properties:
  44. * @param {Uint16Array} options.positions The positions of the polylines
  45. * @param {Uint32Array} options.counts The number or positions in the each polyline.
  46. * @param {Uint16Array} options.widths The width of each polyline.
  47. * @param {Number} options.minimumHeight The minimum height of the tile's region.
  48. * @param {Number} options.maximumHeight The maximum height of the tile's region.
  49. * @param {Rectangle} options.rectangle The rectangle containing the tile.
  50. * @param {Cartesian3} [options.center=Cartesian3.ZERO] The RTC center.
  51. * @param {Cesium3DTileBatchTable} options.batchTable The batch table for the tile containing the batched polylines.
  52. * @param {Uint16Array} options.batchIds The batch ids for each polyline.
  53. * @param {ClassificationType} options.classificationType The classification type.
  54. * @param {Boolean} options.keepDecodedPositions Whether to keep decoded positions in memory.
  55. *
  56. * @private
  57. */
  58. function Vector3DTileClampedPolylines(options) {
  59. // these arrays hold data from the tile payload
  60. // and are all released after the first update.
  61. this._positions = options.positions;
  62. this._widths = options.widths;
  63. this._counts = options.counts;
  64. this._batchIds = options.batchIds;
  65. this._ellipsoid = defaultValue(options.ellipsoid, Ellipsoid.WGS84);
  66. this._minimumHeight = options.minimumHeight;
  67. this._maximumHeight = options.maximumHeight;
  68. this._center = options.center;
  69. this._rectangle = options.rectangle;
  70. this._batchTable = options.batchTable;
  71. this._va = undefined;
  72. this._sp = undefined;
  73. this._rs = undefined;
  74. this._uniformMap = undefined;
  75. this._command = undefined;
  76. this._transferrableBatchIds = undefined;
  77. this._packedBuffer = undefined;
  78. this._minimumMaximumVectorHeights = new Cartesian2(
  79. ApproximateTerrainHeights._defaultMinTerrainHeight,
  80. ApproximateTerrainHeights._defaultMaxTerrainHeight
  81. );
  82. this._boundingVolume = OrientedBoundingBox.fromRectangle(
  83. options.rectangle,
  84. ApproximateTerrainHeights._defaultMinTerrainHeight,
  85. ApproximateTerrainHeights._defaultMaxTerrainHeight,
  86. this._ellipsoid
  87. );
  88. this._classificationType = options.classificationType;
  89. this._keepDecodedPositions = options.keepDecodedPositions;
  90. this._decodedPositions = undefined;
  91. this._decodedPositionOffsets = undefined;
  92. // Fat vertices - all information for each volume packed to a vec3 and 5 vec4s
  93. this._startEllipsoidNormals = undefined;
  94. this._endEllipsoidNormals = undefined;
  95. this._startPositionAndHeights = undefined;
  96. this._startFaceNormalAndVertexCornerIds = undefined;
  97. this._endPositionAndHeights = undefined;
  98. this._endFaceNormalAndHalfWidths = undefined;
  99. this._vertexBatchIds = undefined;
  100. this._indices = undefined;
  101. this._constantColor = Color.clone(Color.WHITE);
  102. this._highlightColor = this._constantColor;
  103. this._trianglesLength = 0;
  104. this._geometryByteLength = 0;
  105. this._ready = false;
  106. this._readyPromise = defer();
  107. this._verticesPromise = undefined;
  108. const that = this;
  109. ApproximateTerrainHeights.initialize()
  110. .then(function () {
  111. updateMinimumMaximumHeights(that, that._rectangle, that._ellipsoid);
  112. })
  113. .catch(function (error) {
  114. this._readyPromise.reject(error);
  115. });
  116. }
  117. Object.defineProperties(Vector3DTileClampedPolylines.prototype, {
  118. /**
  119. * Gets the number of triangles.
  120. *
  121. * @memberof Vector3DTileClampedPolylines.prototype
  122. *
  123. * @type {Number}
  124. * @readonly
  125. */
  126. trianglesLength: {
  127. get: function () {
  128. return this._trianglesLength;
  129. },
  130. },
  131. /**
  132. * Gets the geometry memory in bytes.
  133. *
  134. * @memberof Vector3DTileClampedPolylines.prototype
  135. *
  136. * @type {Number}
  137. * @readonly
  138. */
  139. geometryByteLength: {
  140. get: function () {
  141. return this._geometryByteLength;
  142. },
  143. },
  144. /**
  145. * Gets a promise that resolves when the primitive is ready to render.
  146. * @memberof Vector3DTileClampedPolylines.prototype
  147. * @type {Promise}
  148. * @readonly
  149. */
  150. readyPromise: {
  151. get: function () {
  152. return this._readyPromise.promise;
  153. },
  154. },
  155. });
  156. function updateMinimumMaximumHeights(polylines, rectangle, ellipsoid) {
  157. const result = ApproximateTerrainHeights.getMinimumMaximumHeights(
  158. rectangle,
  159. ellipsoid
  160. );
  161. const min = result.minimumTerrainHeight;
  162. const max = result.maximumTerrainHeight;
  163. const minimumMaximumVectorHeights = polylines._minimumMaximumVectorHeights;
  164. minimumMaximumVectorHeights.x = min;
  165. minimumMaximumVectorHeights.y = max;
  166. const obb = polylines._boundingVolume;
  167. const rect = polylines._rectangle;
  168. OrientedBoundingBox.fromRectangle(rect, min, max, ellipsoid, obb);
  169. }
  170. function packBuffer(polylines) {
  171. const rectangle = polylines._rectangle;
  172. const minimumHeight = polylines._minimumHeight;
  173. const maximumHeight = polylines._maximumHeight;
  174. const ellipsoid = polylines._ellipsoid;
  175. const center = polylines._center;
  176. const packedLength =
  177. 2 +
  178. Rectangle.packedLength +
  179. Ellipsoid.packedLength +
  180. Cartesian3.packedLength;
  181. const packedBuffer = new Float64Array(packedLength);
  182. let offset = 0;
  183. packedBuffer[offset++] = minimumHeight;
  184. packedBuffer[offset++] = maximumHeight;
  185. Rectangle.pack(rectangle, packedBuffer, offset);
  186. offset += Rectangle.packedLength;
  187. Ellipsoid.pack(ellipsoid, packedBuffer, offset);
  188. offset += Ellipsoid.packedLength;
  189. Cartesian3.pack(center, packedBuffer, offset);
  190. return packedBuffer;
  191. }
  192. const createVerticesTaskProcessor = new TaskProcessor(
  193. "createVectorTileClampedPolylines"
  194. );
  195. const attributeLocations = {
  196. startEllipsoidNormal: 0,
  197. endEllipsoidNormal: 1,
  198. startPositionAndHeight: 2,
  199. endPositionAndHeight: 3,
  200. startFaceNormalAndVertexCorner: 4,
  201. endFaceNormalAndHalfWidth: 5,
  202. a_batchId: 6,
  203. };
  204. function createVertexArray(polylines, context) {
  205. if (defined(polylines._va)) {
  206. return;
  207. }
  208. if (!defined(polylines._verticesPromise)) {
  209. let positions = polylines._positions;
  210. let widths = polylines._widths;
  211. let counts = polylines._counts;
  212. let batchIds = polylines._transferrableBatchIds;
  213. let packedBuffer = polylines._packedBuffer;
  214. if (!defined(packedBuffer)) {
  215. // Copy because they may be the views on the same buffer.
  216. positions = polylines._positions = arraySlice(positions);
  217. widths = polylines._widths = arraySlice(widths);
  218. counts = polylines._counts = arraySlice(counts);
  219. batchIds = polylines._transferrableBatchIds = arraySlice(
  220. polylines._batchIds
  221. );
  222. packedBuffer = polylines._packedBuffer = packBuffer(polylines);
  223. }
  224. const transferrableObjects = [
  225. positions.buffer,
  226. widths.buffer,
  227. counts.buffer,
  228. batchIds.buffer,
  229. packedBuffer.buffer,
  230. ];
  231. const parameters = {
  232. positions: positions.buffer,
  233. widths: widths.buffer,
  234. counts: counts.buffer,
  235. batchIds: batchIds.buffer,
  236. packedBuffer: packedBuffer.buffer,
  237. keepDecodedPositions: polylines._keepDecodedPositions,
  238. };
  239. const verticesPromise = (polylines._verticesPromise = createVerticesTaskProcessor.scheduleTask(
  240. parameters,
  241. transferrableObjects
  242. ));
  243. if (!defined(verticesPromise)) {
  244. // Postponed
  245. return;
  246. }
  247. Promise.resolve(verticesPromise)
  248. .then(function (result) {
  249. if (polylines._keepDecodedPositions) {
  250. polylines._decodedPositions = new Float64Array(
  251. result.decodedPositions
  252. );
  253. polylines._decodedPositionOffsets = new Uint32Array(
  254. result.decodedPositionOffsets
  255. );
  256. }
  257. polylines._startEllipsoidNormals = new Float32Array(
  258. result.startEllipsoidNormals
  259. );
  260. polylines._endEllipsoidNormals = new Float32Array(
  261. result.endEllipsoidNormals
  262. );
  263. polylines._startPositionAndHeights = new Float32Array(
  264. result.startPositionAndHeights
  265. );
  266. polylines._startFaceNormalAndVertexCornerIds = new Float32Array(
  267. result.startFaceNormalAndVertexCornerIds
  268. );
  269. polylines._endPositionAndHeights = new Float32Array(
  270. result.endPositionAndHeights
  271. );
  272. polylines._endFaceNormalAndHalfWidths = new Float32Array(
  273. result.endFaceNormalAndHalfWidths
  274. );
  275. polylines._vertexBatchIds = new Uint16Array(result.vertexBatchIds);
  276. const indexDatatype = result.indexDatatype;
  277. polylines._indices =
  278. indexDatatype === IndexDatatype.UNSIGNED_SHORT
  279. ? new Uint16Array(result.indices)
  280. : new Uint32Array(result.indices);
  281. polylines._ready = true;
  282. })
  283. .catch(function (error) {
  284. polylines._readyPromise.reject(error);
  285. });
  286. }
  287. if (polylines._ready && !defined(polylines._va)) {
  288. const startEllipsoidNormals = polylines._startEllipsoidNormals;
  289. const endEllipsoidNormals = polylines._endEllipsoidNormals;
  290. const startPositionAndHeights = polylines._startPositionAndHeights;
  291. const endPositionAndHeights = polylines._endPositionAndHeights;
  292. const startFaceNormalAndVertexCornerIds =
  293. polylines._startFaceNormalAndVertexCornerIds;
  294. const endFaceNormalAndHalfWidths = polylines._endFaceNormalAndHalfWidths;
  295. const batchIdAttribute = polylines._vertexBatchIds;
  296. const indices = polylines._indices;
  297. let byteLength =
  298. startEllipsoidNormals.byteLength + endEllipsoidNormals.byteLength;
  299. byteLength +=
  300. startPositionAndHeights.byteLength + endPositionAndHeights.byteLength;
  301. byteLength +=
  302. startFaceNormalAndVertexCornerIds.byteLength +
  303. endFaceNormalAndHalfWidths.byteLength;
  304. byteLength += batchIdAttribute.byteLength + indices.byteLength;
  305. polylines._trianglesLength = indices.length / 3;
  306. polylines._geometryByteLength = byteLength;
  307. const startEllipsoidNormalsBuffer = Buffer.createVertexBuffer({
  308. context: context,
  309. typedArray: startEllipsoidNormals,
  310. usage: BufferUsage.STATIC_DRAW,
  311. });
  312. const endEllipsoidNormalsBuffer = Buffer.createVertexBuffer({
  313. context: context,
  314. typedArray: endEllipsoidNormals,
  315. usage: BufferUsage.STATIC_DRAW,
  316. });
  317. const startPositionAndHeightsBuffer = Buffer.createVertexBuffer({
  318. context: context,
  319. typedArray: startPositionAndHeights,
  320. usage: BufferUsage.STATIC_DRAW,
  321. });
  322. const endPositionAndHeightsBuffer = Buffer.createVertexBuffer({
  323. context: context,
  324. typedArray: endPositionAndHeights,
  325. usage: BufferUsage.STATIC_DRAW,
  326. });
  327. const startFaceNormalAndVertexCornerIdsBuffer = Buffer.createVertexBuffer({
  328. context: context,
  329. typedArray: startFaceNormalAndVertexCornerIds,
  330. usage: BufferUsage.STATIC_DRAW,
  331. });
  332. const endFaceNormalAndHalfWidthsBuffer = Buffer.createVertexBuffer({
  333. context: context,
  334. typedArray: endFaceNormalAndHalfWidths,
  335. usage: BufferUsage.STATIC_DRAW,
  336. });
  337. const batchIdAttributeBuffer = Buffer.createVertexBuffer({
  338. context: context,
  339. typedArray: batchIdAttribute,
  340. usage: BufferUsage.STATIC_DRAW,
  341. });
  342. const indexBuffer = Buffer.createIndexBuffer({
  343. context: context,
  344. typedArray: indices,
  345. usage: BufferUsage.STATIC_DRAW,
  346. indexDatatype:
  347. indices.BYTES_PER_ELEMENT === 2
  348. ? IndexDatatype.UNSIGNED_SHORT
  349. : IndexDatatype.UNSIGNED_INT,
  350. });
  351. const vertexAttributes = [
  352. {
  353. index: attributeLocations.startEllipsoidNormal,
  354. vertexBuffer: startEllipsoidNormalsBuffer,
  355. componentDatatype: ComponentDatatype.FLOAT,
  356. componentsPerAttribute: 3,
  357. },
  358. {
  359. index: attributeLocations.endEllipsoidNormal,
  360. vertexBuffer: endEllipsoidNormalsBuffer,
  361. componentDatatype: ComponentDatatype.FLOAT,
  362. componentsPerAttribute: 3,
  363. },
  364. {
  365. index: attributeLocations.startPositionAndHeight,
  366. vertexBuffer: startPositionAndHeightsBuffer,
  367. componentDatatype: ComponentDatatype.FLOAT,
  368. componentsPerAttribute: 4,
  369. },
  370. {
  371. index: attributeLocations.endPositionAndHeight,
  372. vertexBuffer: endPositionAndHeightsBuffer,
  373. componentDatatype: ComponentDatatype.FLOAT,
  374. componentsPerAttribute: 4,
  375. },
  376. {
  377. index: attributeLocations.startFaceNormalAndVertexCorner,
  378. vertexBuffer: startFaceNormalAndVertexCornerIdsBuffer,
  379. componentDatatype: ComponentDatatype.FLOAT,
  380. componentsPerAttribute: 4,
  381. },
  382. {
  383. index: attributeLocations.endFaceNormalAndHalfWidth,
  384. vertexBuffer: endFaceNormalAndHalfWidthsBuffer,
  385. componentDatatype: ComponentDatatype.FLOAT,
  386. componentsPerAttribute: 4,
  387. },
  388. {
  389. index: attributeLocations.a_batchId,
  390. vertexBuffer: batchIdAttributeBuffer,
  391. componentDatatype: ComponentDatatype.UNSIGNED_SHORT,
  392. componentsPerAttribute: 1,
  393. },
  394. ];
  395. polylines._va = new VertexArray({
  396. context: context,
  397. attributes: vertexAttributes,
  398. indexBuffer: indexBuffer,
  399. });
  400. polylines._positions = undefined;
  401. polylines._widths = undefined;
  402. polylines._counts = undefined;
  403. polylines._ellipsoid = undefined;
  404. polylines._minimumHeight = undefined;
  405. polylines._maximumHeight = undefined;
  406. polylines._rectangle = undefined;
  407. polylines._transferrableBatchIds = undefined;
  408. polylines._packedBuffer = undefined;
  409. polylines._startEllipsoidNormals = undefined;
  410. polylines._endEllipsoidNormals = undefined;
  411. polylines._startPositionAndHeights = undefined;
  412. polylines._startFaceNormalAndVertexCornerIds = undefined;
  413. polylines._endPositionAndHeights = undefined;
  414. polylines._endFaceNormalAndHalfWidths = undefined;
  415. polylines._vertexBatchIds = undefined;
  416. polylines._indices = undefined;
  417. polylines._readyPromise.resolve();
  418. }
  419. }
  420. const modifiedModelViewScratch = new Matrix4();
  421. const rtcScratch = new Cartesian3();
  422. function createUniformMap(primitive, context) {
  423. if (defined(primitive._uniformMap)) {
  424. return;
  425. }
  426. primitive._uniformMap = {
  427. u_modifiedModelView: function () {
  428. const viewMatrix = context.uniformState.view;
  429. Matrix4.clone(viewMatrix, modifiedModelViewScratch);
  430. Matrix4.multiplyByPoint(
  431. modifiedModelViewScratch,
  432. primitive._center,
  433. rtcScratch
  434. );
  435. Matrix4.setTranslation(
  436. modifiedModelViewScratch,
  437. rtcScratch,
  438. modifiedModelViewScratch
  439. );
  440. return modifiedModelViewScratch;
  441. },
  442. u_highlightColor: function () {
  443. return primitive._highlightColor;
  444. },
  445. u_minimumMaximumVectorHeights: function () {
  446. return primitive._minimumMaximumVectorHeights;
  447. },
  448. };
  449. }
  450. function getRenderState(mask3DTiles) {
  451. /**
  452. * Cull front faces of each volume (relative to camera) to prevent
  453. * classification drawing from both the front and back faces, double-draw.
  454. * The geometry is "inverted" (inside-out winding order for the indices) but
  455. * the vertex shader seems to re-invert so that the triangles face "out" again.
  456. * So cull FRONT faces.
  457. */
  458. return RenderState.fromCache({
  459. cull: {
  460. enabled: true,
  461. face: CullFace.FRONT,
  462. },
  463. blending: BlendingState.PRE_MULTIPLIED_ALPHA_BLEND,
  464. depthMask: false,
  465. stencilTest: {
  466. enabled: mask3DTiles,
  467. frontFunction: StencilFunction.EQUAL,
  468. frontOperation: {
  469. fail: StencilOperation.KEEP,
  470. zFail: StencilOperation.KEEP,
  471. zPass: StencilOperation.KEEP,
  472. },
  473. backFunction: StencilFunction.EQUAL,
  474. backOperation: {
  475. fail: StencilOperation.KEEP,
  476. zFail: StencilOperation.KEEP,
  477. zPass: StencilOperation.KEEP,
  478. },
  479. reference: StencilConstants.CESIUM_3D_TILE_MASK,
  480. mask: StencilConstants.CESIUM_3D_TILE_MASK,
  481. },
  482. });
  483. }
  484. function createRenderStates(primitive) {
  485. if (defined(primitive._rs)) {
  486. return;
  487. }
  488. primitive._rs = getRenderState(false);
  489. primitive._rs3DTiles = getRenderState(true);
  490. }
  491. function createShaders(primitive, context) {
  492. if (defined(primitive._sp)) {
  493. return;
  494. }
  495. const batchTable = primitive._batchTable;
  496. const vsSource = batchTable.getVertexShaderCallback(
  497. false,
  498. "a_batchId",
  499. undefined
  500. )(Vector3DTileClampedPolylinesVS);
  501. const fsSource = batchTable.getFragmentShaderCallback(
  502. false,
  503. undefined,
  504. true
  505. )(Vector3DTileClampedPolylinesFS);
  506. const vs = new ShaderSource({
  507. defines: [
  508. "VECTOR_TILE",
  509. !FeatureDetection.isInternetExplorer() ? "CLIP_POLYLINE" : "",
  510. ],
  511. sources: [PolylineCommon, vsSource],
  512. });
  513. const fs = new ShaderSource({
  514. defines: ["VECTOR_TILE"],
  515. sources: [fsSource],
  516. });
  517. primitive._sp = ShaderProgram.fromCache({
  518. context: context,
  519. vertexShaderSource: vs,
  520. fragmentShaderSource: fs,
  521. attributeLocations: attributeLocations,
  522. });
  523. }
  524. function queueCommands(primitive, frameState) {
  525. let command = primitive._command;
  526. if (!defined(primitive._command)) {
  527. const uniformMap = primitive._batchTable.getUniformMapCallback()(
  528. primitive._uniformMap
  529. );
  530. command = primitive._command = new DrawCommand({
  531. owner: primitive,
  532. vertexArray: primitive._va,
  533. renderState: primitive._rs,
  534. shaderProgram: primitive._sp,
  535. uniformMap: uniformMap,
  536. boundingVolume: primitive._boundingVolume,
  537. pass: Pass.TERRAIN_CLASSIFICATION,
  538. pickId: primitive._batchTable.getPickId(),
  539. });
  540. const derivedTilesetCommand = DrawCommand.shallowClone(
  541. command,
  542. command.derivedCommands.tileset
  543. );
  544. derivedTilesetCommand.renderState = primitive._rs3DTiles;
  545. derivedTilesetCommand.pass = Pass.CESIUM_3D_TILE_CLASSIFICATION;
  546. command.derivedCommands.tileset = derivedTilesetCommand;
  547. }
  548. const classificationType = primitive._classificationType;
  549. if (
  550. classificationType === ClassificationType.TERRAIN ||
  551. classificationType === ClassificationType.BOTH
  552. ) {
  553. frameState.commandList.push(command);
  554. }
  555. if (
  556. classificationType === ClassificationType.CESIUM_3D_TILE ||
  557. classificationType === ClassificationType.BOTH
  558. ) {
  559. frameState.commandList.push(command.derivedCommands.tileset);
  560. }
  561. }
  562. /**
  563. * Get the polyline positions for the given feature.
  564. *
  565. * @param {Number} batchId The batch ID of the feature.
  566. */
  567. Vector3DTileClampedPolylines.prototype.getPositions = function (batchId) {
  568. return Vector3DTilePolylines.getPolylinePositions(this, batchId);
  569. };
  570. /**
  571. * Creates features for each polyline and places it at the batch id index of features.
  572. *
  573. * @param {Vector3DTileContent} content The vector tile content.
  574. * @param {Cesium3DTileFeature[]} features An array of features where the polygon features will be placed.
  575. */
  576. Vector3DTileClampedPolylines.prototype.createFeatures = function (
  577. content,
  578. features
  579. ) {
  580. const batchIds = this._batchIds;
  581. const length = batchIds.length;
  582. for (let i = 0; i < length; ++i) {
  583. const batchId = batchIds[i];
  584. features[batchId] = new Cesium3DTileFeature(content, batchId);
  585. }
  586. };
  587. /**
  588. * Colors the entire tile when enabled is true. The resulting color will be (polyline batch table color * color).
  589. *
  590. * @param {Boolean} enabled Whether to enable debug coloring.
  591. * @param {Color} color The debug color.
  592. */
  593. Vector3DTileClampedPolylines.prototype.applyDebugSettings = function (
  594. enabled,
  595. color
  596. ) {
  597. this._highlightColor = enabled ? color : this._constantColor;
  598. };
  599. function clearStyle(polygons, features) {
  600. const batchIds = polygons._batchIds;
  601. const length = batchIds.length;
  602. for (let i = 0; i < length; ++i) {
  603. const batchId = batchIds[i];
  604. const feature = features[batchId];
  605. feature.show = true;
  606. feature.color = Color.WHITE;
  607. }
  608. }
  609. const scratchColor = new Color();
  610. const DEFAULT_COLOR_VALUE = Color.WHITE;
  611. const DEFAULT_SHOW_VALUE = true;
  612. /**
  613. * Apply a style to the content.
  614. *
  615. * @param {Cesium3DTileStyle} style The style.
  616. * @param {Cesium3DTileFeature[]} features The dictionary of features.
  617. */
  618. Vector3DTileClampedPolylines.prototype.applyStyle = function (style, features) {
  619. if (!defined(style)) {
  620. clearStyle(this, features);
  621. return;
  622. }
  623. const batchIds = this._batchIds;
  624. const length = batchIds.length;
  625. for (let i = 0; i < length; ++i) {
  626. const batchId = batchIds[i];
  627. const feature = features[batchId];
  628. feature.color = defined(style.color)
  629. ? style.color.evaluateColor(feature, scratchColor)
  630. : DEFAULT_COLOR_VALUE;
  631. feature.show = defined(style.show)
  632. ? style.show.evaluate(feature)
  633. : DEFAULT_SHOW_VALUE;
  634. }
  635. };
  636. /**
  637. * Updates the batches and queues the commands for rendering.
  638. *
  639. * @param {FrameState} frameState The current frame state.
  640. */
  641. Vector3DTileClampedPolylines.prototype.update = function (frameState) {
  642. const context = frameState.context;
  643. createVertexArray(this, context);
  644. createUniformMap(this, context);
  645. createShaders(this, context);
  646. createRenderStates(this);
  647. if (!this._ready) {
  648. return;
  649. }
  650. const passes = frameState.passes;
  651. if (passes.render || passes.pick) {
  652. queueCommands(this, frameState);
  653. }
  654. };
  655. /**
  656. * Returns true if this object was destroyed; otherwise, false.
  657. * <p>
  658. * If this object was destroyed, it should not be used; calling any function other than
  659. * <code>isDestroyed</code> will result in a {@link DeveloperError} exception.
  660. * </p>
  661. *
  662. * @returns {Boolean} <code>true</code> if this object was destroyed; otherwise, <code>false</code>.
  663. */
  664. Vector3DTileClampedPolylines.prototype.isDestroyed = function () {
  665. return false;
  666. };
  667. /**
  668. * Destroys the WebGL resources held by this object. Destroying an object allows for deterministic
  669. * release of WebGL resources, instead of relying on the garbage collector to destroy this object.
  670. * <p>
  671. * Once an object is destroyed, it should not be used; calling any function other than
  672. * <code>isDestroyed</code> will result in a {@link DeveloperError} exception. Therefore,
  673. * assign the return value (<code>undefined</code>) to the object as done in the example.
  674. * </p>
  675. *
  676. * @exception {DeveloperError} This object was destroyed, i.e., destroy() was called.
  677. */
  678. Vector3DTileClampedPolylines.prototype.destroy = function () {
  679. this._va = this._va && this._va.destroy();
  680. this._sp = this._sp && this._sp.destroy();
  681. return destroyObject(this);
  682. };
  683. export default Vector3DTileClampedPolylines;