ember-material-icons
Version:
Google Material icons for your ember-cli app
78 lines (62 loc) • 2.42 kB
text/typescript
import { RevisionTag, ConstReference, PathReference, Reference } from '@glimmer/reference';
import { Option, Opaque } from '@glimmer/util';
export type Primitive = undefined | null | boolean | number | string;
export class PrimitiveReference<T extends Primitive> extends ConstReference<T> implements PathReference<T> {
static create<T extends Primitive>(value: T): PrimitiveReference<T> {
if (value === undefined) {
return UNDEFINED_REFERENCE as PrimitiveReference<T>;
} else if (value === null) {
return NULL_REFERENCE as PrimitiveReference<T>;
} else if (value === true) {
return TRUE_REFERENCE as PrimitiveReference<T>;
} else if (value === false) {
return FALSE_REFERENCE as PrimitiveReference<T>;
} else if (typeof value === 'number') {
return new ValueReference(value as number) as PrimitiveReference<T>;
} else {
return new StringReference(value as string) as any as PrimitiveReference<T>;
}
}
protected constructor(value: T) {
super(value);
}
get(_key: string): PrimitiveReference<Primitive> {
return UNDEFINED_REFERENCE;
}
}
class StringReference extends PrimitiveReference<string> {
private lengthReference: Option<PrimitiveReference<number>> = null;
get(key: string): PrimitiveReference<Primitive> {
if (key === 'length') {
let { lengthReference } = this;
if (lengthReference === null) {
lengthReference = this.lengthReference = new ValueReference(this.inner.length);
}
return lengthReference;
} else {
return super.get(key);
}
}
}
type Value = undefined | null | number | boolean;
class ValueReference<T extends Value> extends PrimitiveReference<T> {
constructor(value: T) {
super(value);
}
}
export const UNDEFINED_REFERENCE: PrimitiveReference<undefined> = new ValueReference(undefined);
export const NULL_REFERENCE: PrimitiveReference<null> = new ValueReference(null);
const TRUE_REFERENCE: PrimitiveReference<boolean> = new ValueReference(true);
const FALSE_REFERENCE: PrimitiveReference<boolean> = new ValueReference(false);
export class ConditionalReference implements Reference<boolean> {
public tag: RevisionTag;
constructor(private inner: Reference<Opaque>) {
this.tag = inner.tag;
}
value(): boolean {
return this.toBool(this.inner.value());
}
protected toBool(value: Opaque): boolean {
return !!value;
}
}