s2maps-gpu
Version:
S2 Maps GPU - An open source, high-performance, and GPU-accelerated map engine for rendering large-scale, interactive maps.
79 lines (78 loc) • 2.83 kB
JavaScript
import ImageSource from './imageSource.js';
/**
* # SpriteSource
*
* A collection of images relating to a single source
*/
export default class SpriteSource extends ImageSource {
/**
* Build the image source metadata
* @param mapID - the id of the map to build for
* @returns the image metadata
*/
async build(mapID) {
const { name, fileType, path, texturePack } = this;
// grab the metadata and sprites
const [spriteMeta, sprites] = await Promise.all([
this._fetch(`${path}.json`, mapID),
this._fetch(`${path}.${fileType}`, mapID),
]).catch((err) => {
console.error(err);
return [undefined, undefined];
});
// if either failed, stop their
if (spriteMeta === undefined || sprites === undefined) {
this.active = false;
console.error(`Failed to fetch sprite source ${name}`);
}
else {
const metadata = {};
// store the metadata
let texW = 0;
let texH = 0;
for (const meta of Object.values(spriteMeta)) {
texW = Math.max(texW, meta.width + meta.x);
texH = Math.max(texH, meta.height + meta.y);
}
// update the texture pack
const [offsetX, offsetY] = texturePack.addGlyph(texW, texH);
// invert the y axis for each glyph & add offsets
for (const [name, meta] of Object.entries(spriteMeta)) {
// fix the y axis to be inverted
meta.y = texH - meta.y - meta.height + offsetY;
const { x, y, width, height, pixelRatio } = meta;
metadata[name] = {
code: name,
texX: x + offsetX,
texY: y + offsetY,
texW: width,
texH: height,
xOffset: 0,
yOffset: 0,
width: width / pixelRatio,
height: height / pixelRatio,
advanceWidth: 0,
};
}
// prebuild the sprite sheet if possible
const image = await createImageBitmap(new Blob([sprites]), {
premultiplyAlpha: 'none',
imageOrientation: 'flipY',
});
// ship the sprites to the map
const spriteImageMessage = {
type: 'spriteimage',
mapID,
name,
offsetX,
offsetY,
width: texW,
height: texH,
maxHeight: texturePack.height,
image,
};
postMessage(spriteImageMessage, [image]);
return { name, metadata };
}
}
}