UNPKG

ember-material-icons

Version:

Google Material icons for your ember-cli app

181 lines (138 loc) 4.95 kB
import { PropertyReference } from './references/descriptors'; import RootReference from './references/root'; import { MetaOptions } from './types'; import { Dict, DictSet, HasGuid, Set, dict } from '@glimmer/util'; import { RootReferenceFactory, PathReferenceFactory, Meta as IMeta, RootReference as IRootReference } from './types'; import { PathReference as IPathReference, VOLATILE_TAG } from '@glimmer/reference'; import { InnerReferenceFactory } from './references/descriptors'; const NOOP_DESTROY = { destroy() {} }; class ConstPath implements IPathReference<any> { private parent: any; private property: string; public tag = VOLATILE_TAG; constructor(parent: any, property: string) { this.parent = parent; } chain() { return NOOP_DESTROY; } notify() {} value() { return this.parent[this.property]; } get(prop: string): IPathReference<any> { return new ConstPath(this.parent[this.property], prop); } } class ConstRoot implements IRootReference<any> { private inner: any; public tag = VOLATILE_TAG; constructor(value) { this.inner = value; } update(inner: any) { this.inner = inner; } chain() { return NOOP_DESTROY; } notify() {} value(): any { return this.inner; } referenceFromParts(parts: string[]): IPathReference<any> { throw new Error("Not implemented"); } chainFor(prop: string): IPathReference<any> { throw new Error("Not implemented"); } get(prop: string): IPathReference<any> { return new ConstPath(this.inner, prop); } } class ConstMeta /*implements IMeta*/ { private object: any; constructor(object: any) { this.object = object; } root(): ConstRoot { return new ConstRoot(this.object); } } export const CLASS_META = "df8be4c8-4e89-44e2-a8f9-550c8dacdca7"; const hasOwnProperty = Object.hasOwnProperty; class Meta implements IMeta, HasGuid { static for(obj: any): IMeta { if (obj === null || obj === undefined) return new Meta(obj, {}); if (hasOwnProperty.call(obj, '_meta') && obj._meta) return obj._meta; if (!Object.isExtensible(obj)) return <any>new ConstMeta(obj); let MetaToUse: typeof Meta = Meta; if (obj.constructor && obj.constructor[CLASS_META]) { let classMeta: ClassMeta = obj.constructor[CLASS_META]; MetaToUse = classMeta.InstanceMetaConstructor; } else if (obj[CLASS_META]) { MetaToUse = obj[CLASS_META].InstanceMetaConstructor; } return (obj._meta = new MetaToUse(obj, {})); } static exists(obj: any): boolean { return typeof obj === 'object' && obj._meta; } static metadataForProperty(key: string): any { return null; } private object: any; private RootReferenceFactory: RootReferenceFactory<any>; private DefaultPathReferenceFactory: InnerReferenceFactory<any>; private rootCache: IRootReference<any>; private references: Dict<DictSet<IPathReference<any> & HasGuid>> = null; public _guid; protected slots: Dict<any> = null; protected referenceTypes: Dict<InnerReferenceFactory<any>> = null; protected propertyMetadata: Dict<any> = null; constructor(object: any, { RootReferenceFactory, DefaultPathReferenceFactory }: MetaOptions) { this.object = object; this.RootReferenceFactory = RootReferenceFactory || RootReference; this.DefaultPathReferenceFactory = DefaultPathReferenceFactory || PropertyReference; } addReference(property: string, reference: IPathReference<any> & HasGuid) { let refs = this.references = this.references || dict<DictSet<IPathReference<any> & HasGuid>>(); let set = refs[property] = refs[property] || new DictSet<IPathReference<any> & HasGuid>(); set.add(reference); } addReferenceTypeFor(property: string, type: PathReferenceFactory<any>) { this.referenceTypes = this.referenceTypes || dict<PathReferenceFactory<any>>(); this.referenceTypes[property] = type; } referenceTypeFor(property: string): InnerReferenceFactory<any> { if (!this.referenceTypes) return PropertyReference; return this.referenceTypes[property] || PropertyReference; } removeReference(property: string, reference: IPathReference<any> & HasGuid) { if (!this.references) return; let set = this.references[property]; set.delete(reference); } getReferenceTypes(): Dict<InnerReferenceFactory<any>> { this.referenceTypes = this.referenceTypes || dict<PathReferenceFactory<any>>(); return this.referenceTypes; } referencesFor(property: string): Set<IPathReference<any>> { if (!this.references) return; return this.references[property]; } getSlots() { return (this.slots = this.slots || dict()); } root(): IRootReference<any> { return (this.rootCache = this.rootCache || new this.RootReferenceFactory(this.object)); } } export default Meta; interface ClassMeta { InstanceMetaConstructor: typeof Meta; } export function metaFor(obj: any): IMeta { return Meta.for(obj); }