@web-atoms/core
Version:
75 lines (60 loc) • 2.17 kB
text/typescript
import { App } from "../../App";
import { IClassOf, INameValuePairs, INotifyPropertyChanging } from "../../core/types";
import { TypeKey } from "../../di/TypeKey";
import { AtomStyle } from "./AtomStyle";
export class AtomStyleSheet implements INotifyPropertyChanging {
public styleElement: any;
public styles: {[key: string]: AtomStyle} = {};
private lastUpdateId: any = 0;
private isAttaching: boolean = false;
constructor(public readonly app: App, public readonly name: string) {
this.pushUpdate(0);
}
public getNamedStyle<T extends AtomStyle>(c: IClassOf<T>): AtomStyle {
const name = TypeKey.getName(c);
return this.createNamedStyle(c, name);
}
public createNamedStyle<T extends AtomStyle>(c: IClassOf<T>, name: string, updateTimeout?: number): T {
const style = this.styles[name] = new (c)(this, `${this.name}-${name}`);
style.build();
this.pushUpdate(updateTimeout);
return style;
}
public onPropertyChanging(name: string, newValue: any, oldValue: any): void {
this.pushUpdate();
}
public pushUpdate(delay: number = 1): void {
if (this.isAttaching) {
return;
}
// special case for Xamarin Forms
if (delay === 0) {
this.attach();
return;
}
if (this.lastUpdateId) {
clearTimeout(this.lastUpdateId);
}
this.lastUpdateId = setTimeout(() => {
this.attach();
}, delay);
}
public dispose(): void {
if (this.styleElement) {
this.styleElement.remove();
}
}
public attach(): void {
this.isAttaching = true;
const text = [];
for (const key in this.styles) {
if (this.styles.hasOwnProperty(key)) {
const element = this.styles[key];
text.push(element.toString());
}
}
const textContent = text.join("\n");
this.app.updateDefaultStyle(textContent);
this.isAttaching = false;
}
}