vasille
Version:
The first Developer eXperience Orientated front-end framework (core library).
63 lines (62 loc) • 1.81 kB
JavaScript
import { Reference } from "./reference.js";
import { IValue } from "../core/ivalue.js";
/**
* Bind some values to one expression
* @class Expression
* @extends IValue
*/
export class Expression extends IValue {
/**
* Creates a function bounded to N values
* @param func {Function} the function to bound
* @param values
* @param link {Boolean} links immediately if true
*/
constructor(func, values) {
super();
/**
* Expression will link different handler for each value of the list
*/
this.linkedFunc = [];
const handler = (i) => {
/* istanbul ignore else */
if (typeof i === "number") {
this.valuesCache[i] = this.values[i].$;
}
this.sync.$ = func.apply(this, this.valuesCache);
};
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
this.valuesCache = values.map(item => item.$);
this.sync = new Reference(func.apply(this, this.valuesCache));
let i = 0;
values.forEach(value => {
const updater = handler.bind(this, Number(i++));
this.linkedFunc.push(updater);
value.on(updater);
});
this.values = values;
this.func = handler;
}
get $() {
return this.sync.$;
}
set $(value) {
this.sync.$ = value;
}
on(handler) {
this.sync.on(handler);
}
off(handler) {
this.sync.off(handler);
}
destroy() {
for (let i = 0; i < this.values.length; i++) {
this.values[i].off(this.linkedFunc[i]);
}
this.values.splice(0);
this.valuesCache.splice(0);
this.linkedFunc.splice(0);
super.destroy();
}
}