@woosh/meep-engine
Version:
Pure JavaScript game engine. Fully featured and production ready.
144 lines (110 loc) • 3.33 kB
JavaScript
import { KeyValuePair } from "../../../core/collection/KeyValuePair.js";
import { noop } from "../../../core/function/noop.js";
import { ImmutableObjectPool } from "../../../core/model/object/ImmutableObjectPool.js";
import { ObjectPoolFactory } from "../../../core/model/object/ObjectPoolFactory.js";
import { HTMLElementCacheKey } from "../../common/HTMLElementCacheKey.js";
import View from "../../View.js";
/**
*
* @type {ObjectPoolFactory<HTMLElementCacheKey>}
*/
const pool = new ObjectPoolFactory(
() => new HTMLElementCacheKey(),
noop,
key => {
key.reset();
}
);
/**
*
* @type {ImmutableObjectPool<HTMLElementCacheKey, HTMLImageElement>}
*/
const view_pool = new ImmutableObjectPool({
capacity: 500,
perKeyCapacity: 100
});
/**
*
* @param {HTMLElementCacheKey} key
* @return {HTMLImageElement}
*/
function obtainImageElement(key) {
let element = view_pool.get(key);
if (element === undefined) {
element = key.createElement();
}
return element;
}
class ImageView extends View {
/**
*
* @param {String|ObservedString} url
* @param {String[]} classList
* @param {*} [attributes]
*/
constructor(url, { classList = [], attributes = {} } = {}) {
super();
/**
* @type {string}
*/
let src;
if (url === null || url === undefined) {
src = '';
} else if (typeof url === "string") {
src = url;
} else if (typeof url === "object" && typeof url.getValue === "function") {
src = url.getValue();
if (url.onChanged !== undefined) {
this.bindSignal(url.onChanged, this.__setSource, this);
}
}
const cacheKey = pool.create();
cacheKey.tag = 'img';
cacheKey.attributes = [
new KeyValuePair('src', src),
new KeyValuePair('class', classList.join(' '))
];
for (const attributesKey in attributes) {
const attributeValue = String(attributes[attributesKey]);
const attribute = new KeyValuePair(attributesKey, attributeValue);
cacheKey.attributes.push(attribute);
}
cacheKey.update();
this.el = obtainImageElement(cacheKey);
pool.release(cacheKey);
const classListSize = classList.length;
for (let i = 0; i < classListSize; i++) {
const c = classList[i];
this.addClass(c);
}
this.size.onChanged.add(this.__setSize, this);
}
destroy() {
super.destroy();
const key = pool.create();
key.initializeFromElement(this.el);
const added = view_pool.add(key, this.el);
if (!added) {
pool.release(key);
}
}
/**
*
* @param {number} x
* @param {number} y
* @private
*/
__setSize(x, y) {
this.el.setAttribute('width', x);
this.el.setAttribute('height', y);
}
/**
*
* @param {string} url
* @private
*/
__setSource(url) {
this.el.setAttribute('src', url);
}
}
export default ImageView;