UNPKG

@arcgis/core

Version:

ArcGIS Maps SDK for JavaScript: A complete 2D and 3D mapping and data visualization API

3 lines (2 loc) 5.8 kB
/* COPYRIGHT Esri - https://js.arcgis.com/5.0.8/LICENSE.txt */ import t from"../../../../core/Error.js";import has from"../../../../core/has.js";import{spritePadding as e}from"./definitions.js";import{log2 as i}from"./GeometryUtils.js";import s from"./Rect.js";import a from"./RectangleBinPack.js";import r from"../../../webgl/Texture.js";import{TextureDescriptor as o}from"../../../webgl/TextureDescriptor.js";function h(t){return t&&"static"===t.type}class c{constructor(t,e,i=0){this._mosaicPages=[],this._maxItemSize=0,this._currentPage=0,this._pageWidth=0,this._pageHeight=0,this._mosaicRects=new Map,this._spriteCopyQueue=[],this.pixelRatio=1,this._pageWidth=t,this._pageHeight=e,i>0&&(this._maxItemSize=i),this.pixelRatio=window.devicePixelRatio||1,this._binPack=new a(this._pageWidth,this._pageHeight);const s=Math.floor(this._pageWidth),r=Math.floor(this._pageHeight);this._mosaicPages.push({mosaicsData:{type:"static",data:new Uint32Array(s*r)},size:[this._pageWidth,this._pageHeight],dirty:!0,texture:void 0})}getWidth(t){return t>=this._mosaicPages.length?-1:this._mosaicPages[t].size[0]}getHeight(t){return t>=this._mosaicPages.length?-1:this._mosaicPages[t].size[1]}getPageTexture(t){return t<this._mosaicPages.length?this._mosaicPages[t].texture:null}has(t){return this._mosaicRects.has(t)}get itemCount(){return this._mosaicRects.size}getSpriteItem(t){return this._mosaicRects.get(t)}addSpriteItem(t,i,a,r,o,c,n=1,g="Linear",p=.5,m=1){if(this._mosaicRects.has(t))return this._mosaicRects.get(t);let d,u,l;if(h(a))[d,u,l]=this._allocateImage(i[0],i[1]);else{d=new s(0,0,i[0],i[1]),u=this._mosaicPages.length;const t=void 0;this._mosaicPages.push({mosaicsData:a,size:[i[0]+2*e,i[1]+2*e],dirty:!0,texture:t})}if(d.width<=0||d.height<=0)return null;const _={type:"sprite",rect:d,width:i[0],height:i[1],sdf:o,simplePattern:c,rasterizationScale:n,samplingMode:g,sdfPaddingRatio:p,sdfDecodeCoeff:m,page:u};return this._mosaicRects.set(t,_),h(a)&&(has("esri-mosaic-debug")&&this._showDebugSprite(i,a.data),this._copy({rect:d,spriteSize:i,spriteData:a.data,page:u,pageSize:l,repeat:r,sdf:o})),_}hasItemsToProcess(){return 0!==this._spriteCopyQueue.length}processNextItem(){const t=this._spriteCopyQueue.pop();t&&this._copy(t)}getMosaicItemPosition(t){const i=this.getSpriteItem(t),s=i?.rect;if(!s)return null;s.width=i.width,s.height=i.height;const a=i.width,r=i.height,o=e,h=this._mosaicPages[i.page].size;return{size:[i.width,i.height],tl:[(s.x+o)/h[0],(s.y+o)/h[1]],br:[(s.x+o+a)/h[0],(s.y+o+r)/h[1]],page:i.page}}bind(t,e,i=0,s=0){const a=this._mosaicPages[i],r=a.mosaicsData;let o=a.texture;if(o||(o=g(t,a.size),a.texture=o),o.setSamplingMode(e),t.bindTexture(o,s),h(r))a.dirty&&(o.setData(new Uint8Array(r.data.buffer)),o.generateMipmap(),has("esri-mosaic-debug")&&this._showDebugPage(i));else{const t=r.data;t.hasFrameData&&(t.loadFrame(o),o.generateMipmap())}a.dirty=!1}getTexture(t,e=0){const{context:i}=t,s=this._mosaicPages[e],a=s.mosaicsData;let r=s.texture;if(r||(r=g(i,s.size),s.texture=r),h(a))s.dirty&&(r.setData(new Uint8Array(a.data.buffer)),r.generateMipmap(),has("esri-mosaic-debug")&&this._showDebugPage(e));else{const e=a.data;e.update(t),e.hasFrameData&&(e.loadFrame(r),r.generateMipmap())}return s.dirty=!1,r}dispose(){this._binPack=null;for(const t of this._mosaicPages){const e=t.texture;e&&e.dispose();const i=t.mosaicsData;if(!h(i)){i.data.destroy()}}this._mosaicPages=null,this._mosaicRects.clear()}static _copyBits(t,e,i,s,a,r,o,h,c,n,g){let p=s*e+i,m=h*r+o;if(g){m-=r;for(let o=-1;o<=n;o++,p=((o+n)%n+s)*e+i,m+=r)for(let e=-1;e<=c;e++)a[m+e]=t[p+(e+c)%c]}else for(let d=0;d<n;d++){for(let e=0;e<c;e++)a[m+e]=t[p+e];p+=e,m+=r}}_copy(i){if(i.page>=this._mosaicPages.length)return;const s=this._mosaicPages[i.page],a=s.mosaicsData;if(!h(s.mosaicsData))throw new t("mapview-invalid-resource","unsuitable data type!");const r=i.spriteData,o=a.data;c._copyBits(r,i.spriteSize[0],0,0,o,i.pageSize[0],i.rect.x+e,i.rect.y+e,i.spriteSize[0],i.spriteSize[1],i.repeat),s.dirty=!0}_allocateImage(t,r){t+=2*e,r+=2*e;const o=Math.max(t,r);if(this._maxItemSize&&this._maxItemSize<o){const e=2**Math.ceil(i(t)),a=2**Math.ceil(i(r)),o=new s(0,0,t,r);return this._mosaicPages.push({mosaicsData:{type:"static",data:new Uint32Array(e*a)},size:[e,a],dirty:!0,texture:void 0}),[o,this._mosaicPages.length-1,[e,a]]}const c=this._binPack.allocate(t,r);if(c.width<=0){const e=this._mosaicPages[this._currentPage];return!e.dirty&&h(e.mosaicsData)&&(e.mosaicsData.data=null),this._currentPage=this._mosaicPages.length,this._mosaicPages.push({mosaicsData:{type:"static",data:new Uint32Array(this._pageWidth*this._pageHeight)},size:[this._pageWidth,this._pageHeight],dirty:!0,texture:void 0}),this._binPack=new a(this._pageWidth,this._pageHeight),this._allocateImage(t,r)}return[c,this._currentPage,[this._pageWidth,this._pageHeight]]}_showDebugSprite([t,e],i){const s=document.createElement("canvas");s.width=t,s.height=e,s.setAttribute("style",`position: absolute; top: ${4+204*n++}px; right: 208px; width: 200px; height: 200px; border: 1px solid black;`);const a=s.getContext("2d"),r=new ImageData(t,e);r.data.set(new Uint8Array(i.buffer)),a.putImageData(r,0,0),document.body.appendChild(s)}_showDebugPage(t){const e=this._mosaicPages[t],{size:[i,s],mosaicsData:a}=e;if(!h(a))return;const r=`mosaicDebugPage${t}`,o=document.getElementById(r)??document.createElement("canvas");o.id=r,o.width=i,o.height=s,o.setAttribute("style",`position: absolute; top: ${4+204*t}px; right: 4px; width: 200px; height: 200px; border: 1px solid black;`);const c=o.getContext("2d"),n=new ImageData(i,s);n.data.set(new Uint8Array(a.data.buffer)),c.putImageData(n,0,0),document.body.appendChild(o)}}let n=0;function g(t,e){const i=new o(e[0],e[1]);return i.wrapMode=33071,new r(t,i,null)}export{c as default};