@doegis/core
Version:
DOE GIS API
3 lines (1 loc) • 5.82 kB
JavaScript
import{result as e,assertResult as t}from"../../../../core/asyncUtils.js";import has from"../../../../core/has.js";import{clone as r}from"../../../../core/lang.js";import{isNone as i,isSome as o}from"../../../../core/maybe.js";import{eachAlways as n,isAbortError as s}from"../../../../core/promiseUtils.js";import{makeAbsolute as a}from"../../../../core/urlUtils.js";import{TextureEncoding as u}from"./enums.js";import{readBinaryAttribute as l,createGeometryDescriptor as f}from"./I3SBinaryReader.js";import{getMaterialAndTextures as d,getMaterialAndTexturesFromShared as c,selectEncoding as h}from"./I3SMaterialUtil.js";class m{constructor(e,t,r,i,o,n){if(this._streamDataController=t,this._logger=r,this._defaultGeometrySchema=i,this._requiredAttributes=o,this._options=n,this._logLayer=e,this._layerUrl=e.parsedUrl.path,this._geometryDefinitions=e.geometryDefinitions,e.materialDefinitions){const t=e.textureSetDefinitions;this._materialAndTextures=e.materialDefinitions.map((e=>d(t,e)))}}_load(e,t,r){return this._streamDataController.request(e,t,r)}_loadAttribute(e,t,r){const i=`${this._layerUrl}/nodes/${e.resources.attributes}/attributes/${t.key}/0`;return this._load(i,"binary",r).then((e=>l(t,e)))}loadAttributes(e,t,r){return n(t.map((t=>this._loadAttribute(e,t.attributeStorageInfo,r)))).then((r=>{const i={};for(let o=0;o<t.length;++o){const n=r[o].value;if(n)i[t[o].name]=n;else{if(s(r[o].error))throw r[o].error;this._logger.error("#loadAttributes",this._logLayer,`Failed to load attributeData for '${t[o].name}' on node '${e.id}'`,r[o].error)}}return i}))}async loadNodeData(r,n){const s=null!=this._requiredAttributes&&r.resources.attributes?e(this.loadAttributes(r,this._requiredAttributes,n)):null,{bufferDefinition:a,bufferIndex:u}=D(this._geometryDefinitions,r),l=!!r.resources.geometry,d=l?e(this._loadGeometry(r.resources.geometry,u,n)):null,h=r.resources.hasSharedResource?await this._loadShared(r,n):null,m=r.resources.materialDefinition,p=this._materialAndTextures&&null!=m&&m>=0?this._materialAndTextures[m]:null!=h?c(h):null,x=p?.material,A=p?.textures??[],w=`${r.id}`,T=!l&&this._options.loadFeatureData,$=T?await this._loadFeatureData(w,n):null,j=T?_($):g(x),I=i(j)?b($):null,U=A.length>0?e(this.loadTextures(r,A,n)):null;let S=null,q=null;if(d){S=t(await d);const e=y(this._defaultGeometrySchema,h);q=f(a,e)}const B=U?t(await U):null,C=s?t(await s):{},E=C?{attributeData:C,loadedAttributes:this._requiredAttributes}:null;if(o(j))return{geometryData:j,attributeDataInfo:E,geometryBuffer:S,geometryDescriptor:q,requiredTextures:A,textureData:B};if(o(I))return{pointData:I,attributeDataInfo:E,geometryBuffer:S,geometryDescriptor:q,requiredTextures:A,textureData:B};throw new Error}static _addAbsoluteHrefTexture(e,t){const r=e.textureDefinitions;if(null!=r)for(const i of Object.keys(r))for(const e of r[i].images)Array.isArray(e.href)?e.hrefConcat=e.href.map((e=>a(e,t))):e.hrefConcat=a(e.href,t)}static _fixTextureEncodings(e){const t=e.textureDefinitions;if(null!=t)for(const r in t){const e=t[r];if(Array.isArray(e.encoding))for(let t=0;t<e.encoding.length;t++){const r=e.encoding[t];"data:"===r.substring(0,5)&&(e.encoding[t]=r.substring(5))}else{const t=e.encoding;"data:"===t.substring(0,5)&&(e.encoding=t.substring(5))}}}_loadShared(e,t){const r=`${this._layerUrl}/nodes/${e.resources.geometry}/shared`;return this._load(r,"json",t).then((e=>(m._fixTextureEncodings(e),m._addAbsoluteHrefTexture(e,r),e)))}_loadTexture(e,t,r,i,o,n){let s=!1;return o===u.DDS_S3TC||o===u.KTX2||o===u.Basis?this._load(e,"binary",n).then((e=>({id:t,usage:r,data:e,encoding:o,downsampled:s}))):this._load(e,"image",n).then((e=>{let n=e;const a=4096,u=2;if(i&&e.width*e.height>=a){const t=Math.ceil(e.width/u),r=Math.ceil(e.height/u),i=document.createElement("canvas");i.width=t,i.height=r;i.getContext("2d").drawImage(e,0,0,t,r),n=i,s=!0}return{id:t,usage:r,data:n,encoding:o,downsampled:s}}))}loadTextures(e,t,r){const i=!!this._options.uncompressedTextureDownsamplingEnabled,o=this._options.textureUsageMask;return Promise.all(t.map((t=>{if(0==(t.usage&o))return null;const n=h(t.encodings,this._options.textureEncodings);if(null==n)return this._logger.error("#loadTextures",this._logLayer,`No known encoding for texture found on node ${e.id}`),Promise.reject();const s=e.resources.texture||e.id,a=`${this._layerUrl}/nodes/${s}/textures/${n.name}`;return this._loadTexture(a,t.id,t.usage,i,n.encoding,r)})))}_loadFeatureData(e,t){const r=`${this._layerUrl}/nodes/${e}/features/0`;return this._load(r,"json",t)}_loadGeometry(e,t,r){const i=`${this._layerUrl}/nodes/${e}/geometries/${t}`;return this._load(i,"binary",r)}}function g(e){return{featureIds:[],geometries:[{type:"ArrayBufferView",params:{material:e}}],featureDataPosition:[0,0,0]}}function _(e){if(!e)return null;for(const t of e.featureData){const e=t.geometries;if(null!=e)for(const r of e)return{featureIds:[t.id],featureDataPosition:t.position,geometries:[r]}}return null}function b(e){if(!e)return null;const t=new Array;for(const r of e.featureData)null!=r.position&&t.push({featureIds:[r.id],featureDataPosition:r.position,geometries:[]});return t}function y(e,t){if(!e||!t||!t.materialDefinitions)return e;const i=Object.keys(t.materialDefinitions)[0];return!t.materialDefinitions[i].params.vertexRegions&&e.vertexAttributes.region&&delete(e=r(e)).vertexAttributes.region,e}function D(e,t){const r={bufferDefinition:null,bufferIndex:0},i=t.resources.geometryDefinition;if(null==e||null==i||i<0)return r;const o=i>=0?e[i].geometryBuffers:null;if(null==o)return r;for(let n=0;n<o.length;n++){const e=o[n];if(null==e.compressedAttributes)r.bufferIndex=n,r.bufferDefinition=o[n];else if("draco"===e.compressedAttributes.encoding&&!has("disable-feature:i3s-draco"))return r.bufferIndex=n,r.bufferDefinition=e,r}return r}export{m as default};