UNPKG

the-world-engine

Version:

three.js based, unity like game engine for browser

293 lines (287 loc) 10.8 kB
import { GlobalConfig } from "../../../GlobalConfig"; import { Transform } from "../../hierarchy_object/Transform"; import { CssRenderer } from "./CssRenderer"; import { ImageRenderingMode } from "./CssSpriteRenderer"; export var CssSpriteAtlasRenderMode; (function(t) { t[t["ObjectFit"] = 0] = "ObjectFit"; t[t["ClipPath"] = 1] = "ClipPath"; })(CssSpriteAtlasRenderMode || (CssSpriteAtlasRenderMode = {})); export class CssSpriteAtlasRenderer extends CssRenderer { $a=CssSpriteAtlasRenderMode.ObjectFit; tp=0; ip=0; sp=false; ep=false; hp=1; cn=ImageRenderingMode.Pixelated; xa=1; Ra=1; rp=0; np=0; ap=0; wa=null; renderInitialize() { if (this.wa) { this.wa(); } else { this.asyncSetImageFromPath(GlobalConfig.defaultSpriteSrc, 1, 1); } } updateCenterOffset(t) { if (!this.css3DObject) return; if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { this.css3DObject.position.set(this.tp * this.centerOffset.x, this.ip * this.centerOffset.y, 0); if (t) { Transform.updateRawObject3DWorldMatrixRecursively(this.css3DObject); this.transform.enqueueRenderAttachedObject3D(this.css3DObject); } } else { const i = this.rp % this.xa; const s = Math.floor(this.rp / this.xa); const e = this.sp ? -(this.tp * this.xa / 2 - this.tp / 2) + i * this.tp : this.tp * this.xa / 2 - this.tp / 2 - i * this.tp; const h = this.ep ? this.ip * this.Ra / 2 - this.ip / 2 - s * this.ip : -(this.ip * this.Ra / 2 - this.ip / 2) + s * this.ip; this.css3DObject.position.set(this.tp * this.centerOffset.x + e, this.ip * this.centerOffset.y + h, 0); if (t) { Transform.updateRawObject3DWorldMatrixRecursively(this.css3DObject); this.transform.enqueueRenderAttachedObject3D(this.css3DObject); } } } updateViewScale(t) { if (!this.css3DObject) return; if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { const i = this.viewScale; const s = this.sp ? -1 : 1; const e = this.ep ? -1 : 1; this.css3DObject.scale.set(this.tp / this.np * i * s, this.ip / this.ap * i * e, 1); if (t) { Transform.updateRawObject3DWorldMatrixRecursively(this.css3DObject); this.transform.enqueueRenderAttachedObject3D(this.css3DObject); } } else { const i = this.viewScale; const s = this.htmlElement; s.style.width = this.tp * this.xa / i + "px"; s.style.height = this.ip * this.Ra / i + "px"; const e = this.sp ? -1 : 1; const h = this.ep ? -1 : 1; this.css3DObject.scale.set(i * e, i * h, i); if (t) { Transform.updateRawObject3DWorldMatrixRecursively(this.css3DObject); this.transform.enqueueRenderAttachedObject3D(this.css3DObject); } } } op() { if (!this.htmlElement) return; if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { const t = -(this.rp % this.xa * this.np); const i = -Math.floor(this.rp / this.xa) * this.ap; this.htmlElement.style.objectPosition = t + "px " + i + "px"; } else { const t = Math.floor(this.rp / this.xa); const i = this.xa - this.rp % this.xa - 1; this.htmlElement.style.clipPath = "inset(" + 100 / this.Ra * t + "% " + 100 / this.xa * i + "% " + (100 - (100 / this.Ra * t + 100 / this.Ra)) + "% " + (100 - (100 / this.xa * i + 100 / this.xa)) + "%)"; } } get image() { return this.htmlElement; } asyncSetImageFromPath(t, i, s, e) { if (!this.readyToDraw) { this.wa = () => this.asyncSetImageFromPath(t, i, s, e); return; } const h = this.htmlElement ?? new Image; h.src = t; const onLoad = t => { if (!this.exists) return; h.removeEventListener("load", onLoad); this.setImage(h, i, s); e?.(); }; h.addEventListener("load", onLoad); } setImage(t, i, s) { if (!t.complete) throw new Error(`Image {${t.src}} is not loaded.`); this.xa = i; this.Ra = s; this.htmlElement = t; t.alt = this.gameObject.name + "_sprite_atlas"; t.style.imageRendering = this.cn; t.style.opacity = this.hp.toString(); if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { if (this.viewScale !== 1) { console.warn("CssSpriteAtlas.viewScale is not supported in CssSpriteAtlasRenderMode.ObjectFit, for supressing this warning set viewScale to 1."); } this.np = t.naturalWidth / this.xa; this.ap = t.naturalHeight / this.Ra; if (this.tp === 0) this.tp = this.np * .1; if (this.ip === 0) this.ip = this.ap * .1; t.style.width = this.np + "px"; t.style.height = this.ap + "px"; t.style.objectFit = "none"; } else { if (this.tp === 0) this.tp = t.naturalWidth / this.xa * .1; if (this.ip === 0) this.ip = t.naturalHeight / this.Ra * .1; t.style.width = this.tp * this.xa / this.viewScale + "px"; t.style.height = this.ip * this.Ra / this.viewScale + "px"; } const e = this.initializeBaseComponents(false); this.op(); Transform.updateRawObject3DWorldMatrixRecursively(e); this.transform.enqueueRenderAttachedObject3D(e); } get renderMode() { return this.$a; } set renderMode(t) { if (this.$a === t) return; this.$a = t; if (this.htmlElement) { const t = this.htmlElement; if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { if (this.viewScale !== 1) { console.warn("CssSpriteAtlas.viewScale is not supported in CssSpriteAtlasRenderMode.ObjectFit"); } t.style.clipPath = ""; this.np = t.naturalWidth / this.xa; this.ap = t.naturalHeight / this.Ra; if (this.tp === 0) this.tp = this.np; if (this.ip === 0) this.ip = this.ap; t.style.width = this.np + "px"; t.style.height = this.ap + "px"; t.style.objectFit = "none"; } else { t.style.objectFit = ""; t.style.objectPosition = ""; if (this.tp === 0) this.tp = t.naturalWidth / this.xa; if (this.ip === 0) this.ip = t.naturalHeight / this.Ra; t.style.width = this.tp * this.xa / this.viewScale + "px"; t.style.height = this.ip * this.Ra / this.viewScale + "px"; } this.updateViewScale(false); this.updateCenterOffset(false); this.op(); Transform.updateRawObject3DWorldMatrixRecursively(this.css3DObject); this.transform.enqueueRenderAttachedObject3D(this.css3DObject); } } get imageIndex() { return this.rp; } set imageIndex(t) { this.rp = t; this.op(); if (this.$a === CssSpriteAtlasRenderMode.ClipPath) { this.updateCenterOffset(true); } } get columnCount() { return this.xa; } get rowCount() { return this.Ra; } get imageWidth() { return this.tp; } set imageWidth(t) { this.tp = t; if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { if (this.css3DObject) { this.css3DObject.scale.x = this.tp / this.np * this.viewScale; this.css3DObject.scale.x *= this.sp ? -1 : 1; } } else { if (this.htmlElement) { this.htmlElement.style.width = t * this.xa / this.viewScale + "px"; } } this.updateCenterOffset(true); } get imageHeight() { return this.ip; } set imageHeight(t) { this.ip = t; if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { if (this.css3DObject) { this.css3DObject.scale.y = this.ip / this.ap * this.viewScale; this.css3DObject.scale.y *= this.ep ? -1 : 1; } } else { if (this.htmlElement) { this.htmlElement.style.height = t * this.Ra / this.viewScale + "px"; } } this.updateCenterOffset(true); } get imageFlipX() { return this.sp; } set imageFlipX(t) { this.sp = t; if (this.css3DObject) { if (this.sp) { if (0 < this.css3DObject.scale.x) { this.css3DObject.scale.x *= -1; } } else { if (this.css3DObject.scale.x < 0) { this.css3DObject.scale.x *= -1; } } if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { Transform.updateRawObject3DWorldMatrixRecursively(this.css3DObject); this.transform.enqueueRenderAttachedObject3D(this.css3DObject); } else { this.op(); this.updateCenterOffset(true); } } } get imageFlipY() { return this.ep; } set imageFlipY(t) { this.ep = t; if (this.css3DObject) { if (this.ep) { if (0 < this.css3DObject.scale.y) { this.css3DObject.scale.y *= -1; } } else { if (this.css3DObject.scale.y < 0) { this.css3DObject.scale.y *= -1; } } if (this.$a === CssSpriteAtlasRenderMode.ObjectFit) { Transform.updateRawObject3DWorldMatrixRecursively(this.css3DObject); this.transform.enqueueRenderAttachedObject3D(this.css3DObject); } else { this.op(); this.updateCenterOffset(true); } } } get opacity() { return this.hp; } set opacity(t) { this.hp = t; if (this.htmlElement) { this.htmlElement.style.opacity = this.hp.toString(); } } get imageRenderingMode() { return this.cn; } set imageRenderingMode(t) { this.cn = t; if (this.htmlElement) { this.htmlElement.style.imageRendering = this.cn; } } }