| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201 | import Cartesian2 from "../Core/Cartesian2.js";import Check from "../Core/Check.js";import defaultValue from "../Core/defaultValue.js";import defined from "../Core/defined.js";import Matrix3 from "../Core/Matrix3.js";import Sampler from "../Renderer/Sampler.js";import TextureMagnificationFilter from "../Renderer/TextureMagnificationFilter.js";import TextureMinificationFilter from "../Renderer/TextureMinificationFilter.js";import TextureWrap from "../Renderer/TextureWrap.js";import ModelComponents from "./ModelComponents.js";/** * glTF loading utilities. * * @namespace GltfLoaderUtil * * @private */const GltfLoaderUtil = {};/** * Get the image ID referenced by a texture. * <p> * When the texture has the EXT_texture_webp extension and the browser supports * WebP images the WebP image ID is returned. * </p> * * @param {Object} options Object with the following properties: * @param {Object} options.gltf The glTF JSON. * @param {Number} options.textureId The texture ID. * @param {SupportedImageFormats} options.supportedImageFormats The supported image formats. * * @returns {Number} The image ID. * @private */GltfLoaderUtil.getImageIdFromTexture = function (options) {  options = defaultValue(options, defaultValue.EMPTY_OBJECT);  const gltf = options.gltf;  const textureId = options.textureId;  const supportedImageFormats = options.supportedImageFormats;  //>>includeStart('debug', pragmas.debug);  Check.typeOf.object("options.gltf", gltf);  Check.typeOf.number("options.textureId", textureId);  Check.typeOf.object("options.supportedImageFormats", supportedImageFormats);  //>>includeEnd('debug');  const texture = gltf.textures[textureId];  const extensions = texture.extensions;  if (defined(extensions)) {    if (supportedImageFormats.webp && defined(extensions.EXT_texture_webp)) {      return extensions.EXT_texture_webp.source;    } else if (      supportedImageFormats.basis &&      defined(extensions.KHR_texture_basisu)    ) {      return extensions.KHR_texture_basisu.source;    }  }  return texture.source;};/** * Create a sampler for a texture. * * @param {Object} options Object with the following properties: * @param {Object} options.gltf The glTF JSON. * @param {Object} options.textureInfo The texture info object. * @param {Boolean} [options.compressedTextureNoMipmap=false] True when the texture is compressed and does not have an embedded mipmap. * * @returns {Sampler} The sampler. * @private */GltfLoaderUtil.createSampler = function (options) {  options = defaultValue(options, defaultValue.EMPTY_OBJECT);  const gltf = options.gltf;  const textureInfo = options.textureInfo;  const compressedTextureNoMipmap = defaultValue(    options.compressedTextureNoMipmap,    false  );  //>>includeStart('debug', pragmas.debug);  Check.typeOf.object("options.gltf", gltf);  Check.typeOf.object("options.textureInfo", textureInfo);  //>>includeEnd('debug');  // Default sampler properties  let wrapS = TextureWrap.REPEAT;  let wrapT = TextureWrap.REPEAT;  let minFilter = TextureMinificationFilter.LINEAR;  let magFilter = TextureMagnificationFilter.LINEAR;  const textureId = textureInfo.index;  const texture = gltf.textures[textureId];  const samplerId = texture.sampler;  if (defined(samplerId)) {    const sampler = gltf.samplers[samplerId];    wrapS = defaultValue(sampler.wrapS, wrapS);    wrapT = defaultValue(sampler.wrapT, wrapT);    minFilter = defaultValue(sampler.minFilter, minFilter);    magFilter = defaultValue(sampler.magFilter, magFilter);  }  let usesTextureTransform = false;  const extensions = textureInfo.extensions;  if (defined(extensions) && defined(extensions.KHR_texture_transform)) {    usesTextureTransform = true;  }  if (    (compressedTextureNoMipmap || usesTextureTransform) &&    minFilter !== TextureMinificationFilter.LINEAR &&    minFilter !== TextureMinificationFilter.NEAREST  ) {    if (      minFilter === TextureMinificationFilter.NEAREST_MIPMAP_NEAREST ||      minFilter === TextureMinificationFilter.NEAREST_MIPMAP_LINEAR    ) {      minFilter = TextureMinificationFilter.NEAREST;    } else {      minFilter = TextureMinificationFilter.LINEAR;    }  }  return new Sampler({    wrapS: wrapS,    wrapT: wrapT,    minificationFilter: minFilter,    magnificationFilter: magFilter,  });};const defaultScale = new Cartesian2(1.0, 1.0);/** * Create a model texture reader. * * @param {Object} options Object with the following properties: * @param {Object} options.textureInfo The texture info JSON. * @param {String} [options.channels] The texture channels to read from. * @param {Texture} [options.texture] The texture object. * * @returns {ModelComponents.TextureReader} The texture reader for this model. */GltfLoaderUtil.createModelTextureReader = function (options) {  options = defaultValue(options, defaultValue.EMPTY_OBJECT);  const textureInfo = options.textureInfo;  const channels = options.channels;  const texture = options.texture;  //>>includeStart('debug', pragmas.debug);  Check.typeOf.object("options.textureInfo", textureInfo);  //>>includeEnd('debug');  let texCoord = defaultValue(textureInfo.texCoord, 0);  let transform;  const textureTransform = defaultValue(    textureInfo.extensions,    defaultValue.EMPTY_OBJECT  ).KHR_texture_transform;  if (defined(textureTransform)) {    texCoord = defaultValue(textureTransform.texCoord, texCoord);    const offset = defined(textureTransform.offset)      ? Cartesian2.unpack(textureTransform.offset)      : Cartesian2.ZERO;    let rotation = defaultValue(textureTransform.rotation, 0.0);    const scale = defined(textureTransform.scale)      ? Cartesian2.unpack(textureTransform.scale)      : defaultScale;    // glTF assumes UV coordinates start with (0, 0) in the top left corner    // (y-down) unlike WebGL which puts (0, 0) in the bottom left corner (y-up).    // This means rotations are reversed since the angle from x to y is now    // clockwise instead of CCW. Translations and scales are not impacted by    // this.    rotation = -rotation;    // prettier-ignore    transform = new Matrix3(        Math.cos(rotation) * scale.x, -Math.sin(rotation) * scale.y, offset.x,        Math.sin(rotation) * scale.x, Math.cos(rotation) * scale.y, offset.y,        0.0, 0.0, 1.0      );  }  const modelTextureReader = new ModelComponents.TextureReader();  modelTextureReader.index = textureInfo.index;  modelTextureReader.texture = texture;  modelTextureReader.texCoord = texCoord;  modelTextureReader.transform = transform;  modelTextureReader.channels = channels;  return modelTextureReader;};export default GltfLoaderUtil;
 |