mirror of
https://github.com/NativeScript/NativeScript.git
synced 2025-11-05 13:26:48 +08:00
chore: default tabs
This commit is contained in:
@@ -6,277 +6,277 @@ import { LinearGradient } from './linear-gradient';
|
||||
import { Color } from '../../color';
|
||||
|
||||
export class Background implements BackgroundDefinition {
|
||||
public static default = new Background();
|
||||
public static default = new Background();
|
||||
|
||||
public color: Color;
|
||||
public image: string | LinearGradient;
|
||||
public repeat: BackgroundRepeat;
|
||||
public position: string;
|
||||
public size: string;
|
||||
public borderTopColor: Color;
|
||||
public borderRightColor: Color;
|
||||
public borderBottomColor: Color;
|
||||
public borderLeftColor: Color;
|
||||
public borderTopWidth: number = 0;
|
||||
public borderRightWidth: number = 0;
|
||||
public borderBottomWidth: number = 0;
|
||||
public borderLeftWidth: number = 0;
|
||||
public borderTopLeftRadius: number = 0;
|
||||
public borderTopRightRadius: number = 0;
|
||||
public borderBottomLeftRadius: number = 0;
|
||||
public borderBottomRightRadius: number = 0;
|
||||
public clipPath: string;
|
||||
public color: Color;
|
||||
public image: string | LinearGradient;
|
||||
public repeat: BackgroundRepeat;
|
||||
public position: string;
|
||||
public size: string;
|
||||
public borderTopColor: Color;
|
||||
public borderRightColor: Color;
|
||||
public borderBottomColor: Color;
|
||||
public borderLeftColor: Color;
|
||||
public borderTopWidth: number = 0;
|
||||
public borderRightWidth: number = 0;
|
||||
public borderBottomWidth: number = 0;
|
||||
public borderLeftWidth: number = 0;
|
||||
public borderTopLeftRadius: number = 0;
|
||||
public borderTopRightRadius: number = 0;
|
||||
public borderBottomLeftRadius: number = 0;
|
||||
public borderBottomRightRadius: number = 0;
|
||||
public clipPath: string;
|
||||
|
||||
private clone(): Background {
|
||||
const clone = new Background();
|
||||
private clone(): Background {
|
||||
const clone = new Background();
|
||||
|
||||
clone.color = this.color;
|
||||
clone.image = this.image;
|
||||
clone.repeat = this.repeat;
|
||||
clone.position = this.position;
|
||||
clone.size = this.size;
|
||||
clone.borderTopColor = this.borderTopColor;
|
||||
clone.borderRightColor = this.borderRightColor;
|
||||
clone.borderBottomColor = this.borderBottomColor;
|
||||
clone.borderLeftColor = this.borderLeftColor;
|
||||
clone.borderTopWidth = this.borderTopWidth;
|
||||
clone.borderRightWidth = this.borderRightWidth;
|
||||
clone.borderBottomWidth = this.borderBottomWidth;
|
||||
clone.borderLeftWidth = this.borderLeftWidth;
|
||||
clone.borderTopLeftRadius = this.borderTopLeftRadius;
|
||||
clone.borderTopRightRadius = this.borderTopRightRadius;
|
||||
clone.borderBottomRightRadius = this.borderBottomRightRadius;
|
||||
clone.borderBottomLeftRadius = this.borderBottomLeftRadius;
|
||||
clone.clipPath = this.clipPath;
|
||||
clone.color = this.color;
|
||||
clone.image = this.image;
|
||||
clone.repeat = this.repeat;
|
||||
clone.position = this.position;
|
||||
clone.size = this.size;
|
||||
clone.borderTopColor = this.borderTopColor;
|
||||
clone.borderRightColor = this.borderRightColor;
|
||||
clone.borderBottomColor = this.borderBottomColor;
|
||||
clone.borderLeftColor = this.borderLeftColor;
|
||||
clone.borderTopWidth = this.borderTopWidth;
|
||||
clone.borderRightWidth = this.borderRightWidth;
|
||||
clone.borderBottomWidth = this.borderBottomWidth;
|
||||
clone.borderLeftWidth = this.borderLeftWidth;
|
||||
clone.borderTopLeftRadius = this.borderTopLeftRadius;
|
||||
clone.borderTopRightRadius = this.borderTopRightRadius;
|
||||
clone.borderBottomRightRadius = this.borderBottomRightRadius;
|
||||
clone.borderBottomLeftRadius = this.borderBottomLeftRadius;
|
||||
clone.clipPath = this.clipPath;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.color = value;
|
||||
public withColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.color = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withImage(value: string | LinearGradient): Background {
|
||||
const clone = this.clone();
|
||||
clone.image = value;
|
||||
public withImage(value: string | LinearGradient): Background {
|
||||
const clone = this.clone();
|
||||
clone.image = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withRepeat(value: BackgroundRepeat): Background {
|
||||
const clone = this.clone();
|
||||
clone.repeat = value;
|
||||
public withRepeat(value: BackgroundRepeat): Background {
|
||||
const clone = this.clone();
|
||||
clone.repeat = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withPosition(value: string): Background {
|
||||
const clone = this.clone();
|
||||
clone.position = value;
|
||||
public withPosition(value: string): Background {
|
||||
const clone = this.clone();
|
||||
clone.position = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withSize(value: string): Background {
|
||||
const clone = this.clone();
|
||||
clone.size = value;
|
||||
public withSize(value: string): Background {
|
||||
const clone = this.clone();
|
||||
clone.size = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderTopColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderTopColor = value;
|
||||
public withBorderTopColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderTopColor = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderRightColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderRightColor = value;
|
||||
public withBorderRightColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderRightColor = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderBottomColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderBottomColor = value;
|
||||
public withBorderBottomColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderBottomColor = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderLeftColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderLeftColor = value;
|
||||
public withBorderLeftColor(value: Color): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderLeftColor = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderTopWidth(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderTopWidth = value;
|
||||
public withBorderTopWidth(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderTopWidth = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderRightWidth(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderRightWidth = value;
|
||||
public withBorderRightWidth(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderRightWidth = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderBottomWidth(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderBottomWidth = value;
|
||||
public withBorderBottomWidth(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderBottomWidth = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderLeftWidth(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderLeftWidth = value;
|
||||
public withBorderLeftWidth(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderLeftWidth = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderTopLeftRadius(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderTopLeftRadius = value;
|
||||
public withBorderTopLeftRadius(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderTopLeftRadius = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderTopRightRadius(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderTopRightRadius = value;
|
||||
public withBorderTopRightRadius(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderTopRightRadius = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderBottomRightRadius(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderBottomRightRadius = value;
|
||||
public withBorderBottomRightRadius(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderBottomRightRadius = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withBorderBottomLeftRadius(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderBottomLeftRadius = value;
|
||||
public withBorderBottomLeftRadius(value: number): Background {
|
||||
const clone = this.clone();
|
||||
clone.borderBottomLeftRadius = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public withClipPath(value: string): Background {
|
||||
const clone = this.clone();
|
||||
clone.clipPath = value;
|
||||
public withClipPath(value: string): Background {
|
||||
const clone = this.clone();
|
||||
clone.clipPath = value;
|
||||
|
||||
return clone;
|
||||
}
|
||||
return clone;
|
||||
}
|
||||
|
||||
public isEmpty(): boolean {
|
||||
return !this.color && !this.image && !this.hasBorderWidth() && !this.hasBorderRadius() && !this.clipPath;
|
||||
}
|
||||
public isEmpty(): boolean {
|
||||
return !this.color && !this.image && !this.hasBorderWidth() && !this.hasBorderRadius() && !this.clipPath;
|
||||
}
|
||||
|
||||
public static equals(value1: Background, value2: Background): boolean {
|
||||
// both values are falsy
|
||||
if (!value1 && !value2) {
|
||||
return true;
|
||||
}
|
||||
public static equals(value1: Background, value2: Background): boolean {
|
||||
// both values are falsy
|
||||
if (!value1 && !value2) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// only one is falsy
|
||||
if (!value1 || !value2) {
|
||||
return false;
|
||||
}
|
||||
// only one is falsy
|
||||
if (!value1 || !value2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
let imagesEqual = false;
|
||||
if (value1 instanceof LinearGradient && value2 instanceof LinearGradient) {
|
||||
imagesEqual = LinearGradient.equals(value1, value2);
|
||||
} else {
|
||||
imagesEqual = value1.image === value2.image;
|
||||
}
|
||||
let imagesEqual = false;
|
||||
if (value1 instanceof LinearGradient && value2 instanceof LinearGradient) {
|
||||
imagesEqual = LinearGradient.equals(value1, value2);
|
||||
} else {
|
||||
imagesEqual = value1.image === value2.image;
|
||||
}
|
||||
|
||||
return (
|
||||
Color.equals(value1.color, value2.color) &&
|
||||
imagesEqual &&
|
||||
value1.position === value2.position &&
|
||||
value1.repeat === value2.repeat &&
|
||||
value1.size === value2.size &&
|
||||
Color.equals(value1.borderTopColor, value2.borderTopColor) &&
|
||||
Color.equals(value1.borderRightColor, value2.borderRightColor) &&
|
||||
Color.equals(value1.borderBottomColor, value2.borderBottomColor) &&
|
||||
Color.equals(value1.borderLeftColor, value2.borderLeftColor) &&
|
||||
value1.borderTopWidth === value2.borderTopWidth &&
|
||||
value1.borderRightWidth === value2.borderRightWidth &&
|
||||
value1.borderBottomWidth === value2.borderBottomWidth &&
|
||||
value1.borderLeftWidth === value2.borderLeftWidth &&
|
||||
value1.borderTopLeftRadius === value2.borderTopLeftRadius &&
|
||||
value1.borderTopRightRadius === value2.borderTopRightRadius &&
|
||||
value1.borderBottomRightRadius === value2.borderBottomRightRadius &&
|
||||
value1.borderBottomLeftRadius === value2.borderBottomLeftRadius &&
|
||||
value1.clipPath === value2.clipPath
|
||||
);
|
||||
}
|
||||
return (
|
||||
Color.equals(value1.color, value2.color) &&
|
||||
imagesEqual &&
|
||||
value1.position === value2.position &&
|
||||
value1.repeat === value2.repeat &&
|
||||
value1.size === value2.size &&
|
||||
Color.equals(value1.borderTopColor, value2.borderTopColor) &&
|
||||
Color.equals(value1.borderRightColor, value2.borderRightColor) &&
|
||||
Color.equals(value1.borderBottomColor, value2.borderBottomColor) &&
|
||||
Color.equals(value1.borderLeftColor, value2.borderLeftColor) &&
|
||||
value1.borderTopWidth === value2.borderTopWidth &&
|
||||
value1.borderRightWidth === value2.borderRightWidth &&
|
||||
value1.borderBottomWidth === value2.borderBottomWidth &&
|
||||
value1.borderLeftWidth === value2.borderLeftWidth &&
|
||||
value1.borderTopLeftRadius === value2.borderTopLeftRadius &&
|
||||
value1.borderTopRightRadius === value2.borderTopRightRadius &&
|
||||
value1.borderBottomRightRadius === value2.borderBottomRightRadius &&
|
||||
value1.borderBottomLeftRadius === value2.borderBottomLeftRadius &&
|
||||
value1.clipPath === value2.clipPath
|
||||
);
|
||||
}
|
||||
|
||||
public hasBorderColor(): boolean {
|
||||
return !!this.borderTopColor || !!this.borderRightColor || !!this.borderBottomColor || !!this.borderLeftColor;
|
||||
}
|
||||
public hasBorderColor(): boolean {
|
||||
return !!this.borderTopColor || !!this.borderRightColor || !!this.borderBottomColor || !!this.borderLeftColor;
|
||||
}
|
||||
|
||||
public hasBorderWidth(): boolean {
|
||||
return this.borderTopWidth > 0 || this.borderRightWidth > 0 || this.borderBottomWidth > 0 || this.borderLeftWidth > 0;
|
||||
}
|
||||
public hasBorderWidth(): boolean {
|
||||
return this.borderTopWidth > 0 || this.borderRightWidth > 0 || this.borderBottomWidth > 0 || this.borderLeftWidth > 0;
|
||||
}
|
||||
|
||||
public hasBorderRadius(): boolean {
|
||||
return this.borderTopLeftRadius > 0 || this.borderTopRightRadius > 0 || this.borderBottomRightRadius > 0 || this.borderBottomLeftRadius > 0;
|
||||
}
|
||||
public hasBorderRadius(): boolean {
|
||||
return this.borderTopLeftRadius > 0 || this.borderTopRightRadius > 0 || this.borderBottomRightRadius > 0 || this.borderBottomLeftRadius > 0;
|
||||
}
|
||||
|
||||
public hasUniformBorderColor(): boolean {
|
||||
return Color.equals(this.borderTopColor, this.borderRightColor) && Color.equals(this.borderTopColor, this.borderBottomColor) && Color.equals(this.borderTopColor, this.borderLeftColor);
|
||||
}
|
||||
public hasUniformBorderColor(): boolean {
|
||||
return Color.equals(this.borderTopColor, this.borderRightColor) && Color.equals(this.borderTopColor, this.borderBottomColor) && Color.equals(this.borderTopColor, this.borderLeftColor);
|
||||
}
|
||||
|
||||
public hasUniformBorderWidth(): boolean {
|
||||
return this.borderTopWidth === this.borderRightWidth && this.borderTopWidth === this.borderBottomWidth && this.borderTopWidth === this.borderLeftWidth;
|
||||
}
|
||||
public hasUniformBorderWidth(): boolean {
|
||||
return this.borderTopWidth === this.borderRightWidth && this.borderTopWidth === this.borderBottomWidth && this.borderTopWidth === this.borderLeftWidth;
|
||||
}
|
||||
|
||||
public hasUniformBorderRadius(): boolean {
|
||||
return this.borderTopLeftRadius === this.borderTopRightRadius && this.borderTopLeftRadius === this.borderBottomRightRadius && this.borderTopLeftRadius === this.borderBottomLeftRadius;
|
||||
}
|
||||
public hasUniformBorderRadius(): boolean {
|
||||
return this.borderTopLeftRadius === this.borderTopRightRadius && this.borderTopLeftRadius === this.borderBottomRightRadius && this.borderTopLeftRadius === this.borderBottomLeftRadius;
|
||||
}
|
||||
|
||||
public hasUniformBorder(): boolean {
|
||||
return this.hasUniformBorderColor() && this.hasUniformBorderWidth() && this.hasUniformBorderRadius();
|
||||
}
|
||||
public hasUniformBorder(): boolean {
|
||||
return this.hasUniformBorderColor() && this.hasUniformBorderWidth() && this.hasUniformBorderRadius();
|
||||
}
|
||||
|
||||
public getUniformBorderColor(): Color {
|
||||
if (this.hasUniformBorderColor()) {
|
||||
return this.borderTopColor;
|
||||
}
|
||||
public getUniformBorderColor(): Color {
|
||||
if (this.hasUniformBorderColor()) {
|
||||
return this.borderTopColor;
|
||||
}
|
||||
|
||||
return undefined;
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
|
||||
public getUniformBorderWidth(): number {
|
||||
if (this.hasUniformBorderWidth()) {
|
||||
return this.borderTopWidth;
|
||||
}
|
||||
public getUniformBorderWidth(): number {
|
||||
if (this.hasUniformBorderWidth()) {
|
||||
return this.borderTopWidth;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
public getUniformBorderRadius(): number {
|
||||
if (this.hasUniformBorderRadius()) {
|
||||
return this.borderTopLeftRadius;
|
||||
}
|
||||
public getUniformBorderRadius(): number {
|
||||
if (this.hasUniformBorderRadius()) {
|
||||
return this.borderTopLeftRadius;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
public toString(): string {
|
||||
return `isEmpty: ${this.isEmpty()}; color: ${this.color}; image: ${this.image}; repeat: ${this.repeat}; position: ${this.position}; size: ${this.size}; borderTopColor: ${this.borderTopColor}; borderRightColor: ${this.borderRightColor}; borderBottomColor: ${this.borderBottomColor}; borderLeftColor: ${this.borderLeftColor}; borderTopWidth: ${this.borderTopWidth}; borderRightWidth: ${this.borderRightWidth}; borderBottomWidth: ${this.borderBottomWidth}; borderLeftWidth: ${this.borderLeftWidth}; borderTopLeftRadius: ${this.borderTopLeftRadius}; borderTopRightRadius: ${
|
||||
this.borderTopRightRadius
|
||||
}; borderBottomRightRadius: ${this.borderBottomRightRadius}; borderBottomLeftRadius: ${this.borderBottomLeftRadius}; clipPath: ${this.clipPath};`;
|
||||
}
|
||||
public toString(): string {
|
||||
return `isEmpty: ${this.isEmpty()}; color: ${this.color}; image: ${this.image}; repeat: ${this.repeat}; position: ${this.position}; size: ${this.size}; borderTopColor: ${this.borderTopColor}; borderRightColor: ${this.borderRightColor}; borderBottomColor: ${this.borderBottomColor}; borderLeftColor: ${this.borderLeftColor}; borderTopWidth: ${this.borderTopWidth}; borderRightWidth: ${this.borderRightWidth}; borderBottomWidth: ${this.borderBottomWidth}; borderLeftWidth: ${this.borderLeftWidth}; borderTopLeftRadius: ${this.borderTopLeftRadius}; borderTopRightRadius: ${
|
||||
this.borderTopRightRadius
|
||||
}; borderBottomRightRadius: ${this.borderBottomRightRadius}; borderBottomLeftRadius: ${this.borderBottomLeftRadius}; clipPath: ${this.clipPath};`;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,262 +9,262 @@ import { profile } from '../../profiling';
|
||||
export * from './background-common';
|
||||
|
||||
interface AndroidView {
|
||||
_cachedDrawable: android.graphics.drawable.Drawable.ConstantState | android.graphics.drawable.Drawable;
|
||||
_cachedDrawable: android.graphics.drawable.Drawable.ConstantState | android.graphics.drawable.Drawable;
|
||||
}
|
||||
|
||||
// TODO: Change this implementation to use
|
||||
// We are using "ad" here to avoid namespace collision with the global android object
|
||||
export module ad {
|
||||
let SDK: number;
|
||||
function getSDK() {
|
||||
if (!SDK) {
|
||||
SDK = android.os.Build.VERSION.SDK_INT;
|
||||
}
|
||||
let SDK: number;
|
||||
function getSDK() {
|
||||
if (!SDK) {
|
||||
SDK = android.os.Build.VERSION.SDK_INT;
|
||||
}
|
||||
|
||||
return SDK;
|
||||
}
|
||||
return SDK;
|
||||
}
|
||||
|
||||
function isSetColorFilterOnlyWidget(nativeView: android.view.View): boolean {
|
||||
return (
|
||||
nativeView instanceof android.widget.Button || (nativeView instanceof androidx.appcompat.widget.Toolbar && getSDK() >= 21) // There is an issue with the DrawableContainer which was fixed for API version 21 and above: https://code.google.com/p/android/issues/detail?id=60183
|
||||
);
|
||||
}
|
||||
function isSetColorFilterOnlyWidget(nativeView: android.view.View): boolean {
|
||||
return (
|
||||
nativeView instanceof android.widget.Button || (nativeView instanceof androidx.appcompat.widget.Toolbar && getSDK() >= 21) // There is an issue with the DrawableContainer which was fixed for API version 21 and above: https://code.google.com/p/android/issues/detail?id=60183
|
||||
);
|
||||
}
|
||||
|
||||
export function onBackgroundOrBorderPropertyChanged(view: View) {
|
||||
const nativeView = <android.view.View>view.nativeViewProtected;
|
||||
if (!nativeView) {
|
||||
return;
|
||||
}
|
||||
export function onBackgroundOrBorderPropertyChanged(view: View) {
|
||||
const nativeView = <android.view.View>view.nativeViewProtected;
|
||||
if (!nativeView) {
|
||||
return;
|
||||
}
|
||||
|
||||
const background = view.style.backgroundInternal;
|
||||
let drawable = nativeView.getBackground();
|
||||
const androidView = (<any>view) as AndroidView;
|
||||
// use undefined as not set. getBackground will never return undefined only Drawable or null;
|
||||
if (androidView._cachedDrawable === undefined && drawable) {
|
||||
const constantState = drawable.getConstantState();
|
||||
androidView._cachedDrawable = constantState || drawable;
|
||||
}
|
||||
const background = view.style.backgroundInternal;
|
||||
let drawable = nativeView.getBackground();
|
||||
const androidView = (<any>view) as AndroidView;
|
||||
// use undefined as not set. getBackground will never return undefined only Drawable or null;
|
||||
if (androidView._cachedDrawable === undefined && drawable) {
|
||||
const constantState = drawable.getConstantState();
|
||||
androidView._cachedDrawable = constantState || drawable;
|
||||
}
|
||||
|
||||
if (isSetColorFilterOnlyWidget(nativeView) && drawable && !background.hasBorderWidth() && !background.hasBorderRadius() && !background.clipPath && !background.image && background.color) {
|
||||
if (drawable instanceof org.nativescript.widgets.BorderDrawable && androidView._cachedDrawable) {
|
||||
if (!(androidView._cachedDrawable instanceof android.graphics.drawable.Drawable.ConstantState)) {
|
||||
return;
|
||||
}
|
||||
if (isSetColorFilterOnlyWidget(nativeView) && drawable && !background.hasBorderWidth() && !background.hasBorderRadius() && !background.clipPath && !background.image && background.color) {
|
||||
if (drawable instanceof org.nativescript.widgets.BorderDrawable && androidView._cachedDrawable) {
|
||||
if (!(androidView._cachedDrawable instanceof android.graphics.drawable.Drawable.ConstantState)) {
|
||||
return;
|
||||
}
|
||||
|
||||
drawable = androidView._cachedDrawable.newDrawable(nativeView.getResources());
|
||||
nativeView.setBackground(drawable);
|
||||
}
|
||||
drawable = androidView._cachedDrawable.newDrawable(nativeView.getResources());
|
||||
nativeView.setBackground(drawable);
|
||||
}
|
||||
|
||||
const backgroundColor = ((<any>drawable).backgroundColor = background.color.android);
|
||||
drawable.mutate();
|
||||
drawable.setColorFilter(backgroundColor, android.graphics.PorterDuff.Mode.SRC_IN);
|
||||
drawable.invalidateSelf(); // Make sure the drawable is invalidated. Android forgets to invalidate it in some cases: toolbar
|
||||
(<any>drawable).backgroundColor = backgroundColor;
|
||||
} else if (!background.isEmpty()) {
|
||||
let backgroundDrawable = drawable as org.nativescript.widgets.BorderDrawable;
|
||||
if (!(drawable instanceof org.nativescript.widgets.BorderDrawable)) {
|
||||
backgroundDrawable = new org.nativescript.widgets.BorderDrawable(layout.getDisplayDensity(), view.toString());
|
||||
refreshBorderDrawable(view, backgroundDrawable);
|
||||
nativeView.setBackground(backgroundDrawable);
|
||||
} else {
|
||||
refreshBorderDrawable(view, backgroundDrawable);
|
||||
}
|
||||
} else {
|
||||
const cachedDrawable = androidView._cachedDrawable;
|
||||
let defaultDrawable: android.graphics.drawable.Drawable = null;
|
||||
if (cachedDrawable) {
|
||||
if (cachedDrawable instanceof android.graphics.drawable.Drawable.ConstantState) {
|
||||
defaultDrawable = cachedDrawable.newDrawable(nativeView.getResources());
|
||||
} else if (cachedDrawable instanceof android.graphics.drawable.Drawable) {
|
||||
defaultDrawable = cachedDrawable;
|
||||
}
|
||||
}
|
||||
const backgroundColor = ((<any>drawable).backgroundColor = background.color.android);
|
||||
drawable.mutate();
|
||||
drawable.setColorFilter(backgroundColor, android.graphics.PorterDuff.Mode.SRC_IN);
|
||||
drawable.invalidateSelf(); // Make sure the drawable is invalidated. Android forgets to invalidate it in some cases: toolbar
|
||||
(<any>drawable).backgroundColor = backgroundColor;
|
||||
} else if (!background.isEmpty()) {
|
||||
let backgroundDrawable = drawable as org.nativescript.widgets.BorderDrawable;
|
||||
if (!(drawable instanceof org.nativescript.widgets.BorderDrawable)) {
|
||||
backgroundDrawable = new org.nativescript.widgets.BorderDrawable(layout.getDisplayDensity(), view.toString());
|
||||
refreshBorderDrawable(view, backgroundDrawable);
|
||||
nativeView.setBackground(backgroundDrawable);
|
||||
} else {
|
||||
refreshBorderDrawable(view, backgroundDrawable);
|
||||
}
|
||||
} else {
|
||||
const cachedDrawable = androidView._cachedDrawable;
|
||||
let defaultDrawable: android.graphics.drawable.Drawable = null;
|
||||
if (cachedDrawable) {
|
||||
if (cachedDrawable instanceof android.graphics.drawable.Drawable.ConstantState) {
|
||||
defaultDrawable = cachedDrawable.newDrawable(nativeView.getResources());
|
||||
} else if (cachedDrawable instanceof android.graphics.drawable.Drawable) {
|
||||
defaultDrawable = cachedDrawable;
|
||||
}
|
||||
}
|
||||
|
||||
nativeView.setBackground(defaultDrawable);
|
||||
}
|
||||
nativeView.setBackground(defaultDrawable);
|
||||
}
|
||||
|
||||
// TODO: Can we move BorderWidths as separate native setter?
|
||||
// This way we could skip setPadding if borderWidth is not changed.
|
||||
const leftPadding = Math.ceil(view.effectiveBorderLeftWidth + view.effectivePaddingLeft);
|
||||
const topPadding = Math.ceil(view.effectiveBorderTopWidth + view.effectivePaddingTop);
|
||||
const rightPadding = Math.ceil(view.effectiveBorderRightWidth + view.effectivePaddingRight);
|
||||
const bottomPadding = Math.ceil(view.effectiveBorderBottomWidth + view.effectivePaddingBottom);
|
||||
// TODO: Can we move BorderWidths as separate native setter?
|
||||
// This way we could skip setPadding if borderWidth is not changed.
|
||||
const leftPadding = Math.ceil(view.effectiveBorderLeftWidth + view.effectivePaddingLeft);
|
||||
const topPadding = Math.ceil(view.effectiveBorderTopWidth + view.effectivePaddingTop);
|
||||
const rightPadding = Math.ceil(view.effectiveBorderRightWidth + view.effectivePaddingRight);
|
||||
const bottomPadding = Math.ceil(view.effectiveBorderBottomWidth + view.effectivePaddingBottom);
|
||||
|
||||
nativeView.setPadding(leftPadding, topPadding, rightPadding, bottomPadding);
|
||||
}
|
||||
nativeView.setPadding(leftPadding, topPadding, rightPadding, bottomPadding);
|
||||
}
|
||||
}
|
||||
|
||||
function fromBase64(source: string): android.graphics.Bitmap {
|
||||
const bytes = android.util.Base64.decode(source, android.util.Base64.DEFAULT);
|
||||
const bytes = android.util.Base64.decode(source, android.util.Base64.DEFAULT);
|
||||
|
||||
return android.graphics.BitmapFactory.decodeByteArray(bytes, 0, bytes.length);
|
||||
return android.graphics.BitmapFactory.decodeByteArray(bytes, 0, bytes.length);
|
||||
}
|
||||
|
||||
function fromGradient(gradient: LinearGradient): org.nativescript.widgets.LinearGradientDefinition {
|
||||
const colors = Array.create('int', gradient.colorStops.length);
|
||||
const stops = Array.create('float', gradient.colorStops.length);
|
||||
let hasStops = false;
|
||||
gradient.colorStops.forEach((stop, index) => {
|
||||
colors[index] = stop.color.android;
|
||||
if (stop.offset) {
|
||||
stops[index] = stop.offset.value;
|
||||
hasStops = true;
|
||||
}
|
||||
});
|
||||
const colors = Array.create('int', gradient.colorStops.length);
|
||||
const stops = Array.create('float', gradient.colorStops.length);
|
||||
let hasStops = false;
|
||||
gradient.colorStops.forEach((stop, index) => {
|
||||
colors[index] = stop.color.android;
|
||||
if (stop.offset) {
|
||||
stops[index] = stop.offset.value;
|
||||
hasStops = true;
|
||||
}
|
||||
});
|
||||
|
||||
const alpha = gradient.angle / (Math.PI * 2);
|
||||
const startX = Math.pow(Math.sin(Math.PI * (alpha + 0.75)), 2);
|
||||
const startY = Math.pow(Math.sin(Math.PI * (alpha + 0.5)), 2);
|
||||
const endX = Math.pow(Math.sin(Math.PI * (alpha + 0.25)), 2);
|
||||
const endY = Math.pow(Math.sin(Math.PI * alpha), 2);
|
||||
const alpha = gradient.angle / (Math.PI * 2);
|
||||
const startX = Math.pow(Math.sin(Math.PI * (alpha + 0.75)), 2);
|
||||
const startY = Math.pow(Math.sin(Math.PI * (alpha + 0.5)), 2);
|
||||
const endX = Math.pow(Math.sin(Math.PI * (alpha + 0.25)), 2);
|
||||
const endY = Math.pow(Math.sin(Math.PI * alpha), 2);
|
||||
|
||||
return new org.nativescript.widgets.LinearGradientDefinition(startX, startY, endX, endY, colors, hasStops ? stops : null);
|
||||
return new org.nativescript.widgets.LinearGradientDefinition(startX, startY, endX, endY, colors, hasStops ? stops : null);
|
||||
}
|
||||
|
||||
const pattern: RegExp = /url\(('|")(.*?)\1\)/;
|
||||
function refreshBorderDrawable(this: void, view: View, borderDrawable: org.nativescript.widgets.BorderDrawable) {
|
||||
const nativeView = <android.view.View>view.nativeViewProtected;
|
||||
const context = nativeView.getContext();
|
||||
const nativeView = <android.view.View>view.nativeViewProtected;
|
||||
const context = nativeView.getContext();
|
||||
|
||||
const background = view.style.backgroundInternal;
|
||||
if (background) {
|
||||
const backgroundPositionParsedCSSValues = createNativeCSSValueArray(background.position);
|
||||
const backgroundSizeParsedCSSValues = createNativeCSSValueArray(background.size);
|
||||
const blackColor = -16777216; //android.graphics.Color.BLACK;
|
||||
const background = view.style.backgroundInternal;
|
||||
if (background) {
|
||||
const backgroundPositionParsedCSSValues = createNativeCSSValueArray(background.position);
|
||||
const backgroundSizeParsedCSSValues = createNativeCSSValueArray(background.size);
|
||||
const blackColor = -16777216; //android.graphics.Color.BLACK;
|
||||
|
||||
let imageUri: string;
|
||||
if (background.image && typeof background.image === 'string') {
|
||||
imageUri = background.image;
|
||||
const match = imageUri.match(pattern);
|
||||
if (match && match[2]) {
|
||||
imageUri = match[2];
|
||||
}
|
||||
}
|
||||
let imageUri: string;
|
||||
if (background.image && typeof background.image === 'string') {
|
||||
imageUri = background.image;
|
||||
const match = imageUri.match(pattern);
|
||||
if (match && match[2]) {
|
||||
imageUri = match[2];
|
||||
}
|
||||
}
|
||||
|
||||
let bitmap: android.graphics.Bitmap = null;
|
||||
if (isDataURI(imageUri)) {
|
||||
const base64Data = imageUri.split(',')[1];
|
||||
if (base64Data !== undefined) {
|
||||
bitmap = fromBase64(base64Data);
|
||||
imageUri = null;
|
||||
}
|
||||
} else if (isFileOrResourcePath(imageUri)) {
|
||||
if (imageUri.indexOf(RESOURCE_PREFIX) !== 0) {
|
||||
let fileName = imageUri;
|
||||
if (fileName.indexOf('~/') === 0) {
|
||||
fileName = path.join(knownFolders.currentApp().path, fileName.replace('~/', ''));
|
||||
}
|
||||
let bitmap: android.graphics.Bitmap = null;
|
||||
if (isDataURI(imageUri)) {
|
||||
const base64Data = imageUri.split(',')[1];
|
||||
if (base64Data !== undefined) {
|
||||
bitmap = fromBase64(base64Data);
|
||||
imageUri = null;
|
||||
}
|
||||
} else if (isFileOrResourcePath(imageUri)) {
|
||||
if (imageUri.indexOf(RESOURCE_PREFIX) !== 0) {
|
||||
let fileName = imageUri;
|
||||
if (fileName.indexOf('~/') === 0) {
|
||||
fileName = path.join(knownFolders.currentApp().path, fileName.replace('~/', ''));
|
||||
}
|
||||
|
||||
imageUri = FILE_PREFIX + fileName;
|
||||
}
|
||||
}
|
||||
imageUri = FILE_PREFIX + fileName;
|
||||
}
|
||||
}
|
||||
|
||||
let gradient: org.nativescript.widgets.LinearGradientDefinition = null;
|
||||
if (background.image && background.image instanceof LinearGradient) {
|
||||
gradient = fromGradient(background.image);
|
||||
}
|
||||
let gradient: org.nativescript.widgets.LinearGradientDefinition = null;
|
||||
if (background.image && background.image instanceof LinearGradient) {
|
||||
gradient = fromGradient(background.image);
|
||||
}
|
||||
|
||||
borderDrawable.refresh(
|
||||
background.borderTopColor ? background.borderTopColor.android : blackColor,
|
||||
background.borderRightColor ? background.borderRightColor.android : blackColor,
|
||||
background.borderBottomColor ? background.borderBottomColor.android : blackColor,
|
||||
background.borderLeftColor ? background.borderLeftColor.android : blackColor,
|
||||
borderDrawable.refresh(
|
||||
background.borderTopColor ? background.borderTopColor.android : blackColor,
|
||||
background.borderRightColor ? background.borderRightColor.android : blackColor,
|
||||
background.borderBottomColor ? background.borderBottomColor.android : blackColor,
|
||||
background.borderLeftColor ? background.borderLeftColor.android : blackColor,
|
||||
|
||||
background.borderTopWidth,
|
||||
background.borderRightWidth,
|
||||
background.borderBottomWidth,
|
||||
background.borderLeftWidth,
|
||||
background.borderTopWidth,
|
||||
background.borderRightWidth,
|
||||
background.borderBottomWidth,
|
||||
background.borderLeftWidth,
|
||||
|
||||
background.borderTopLeftRadius,
|
||||
background.borderTopRightRadius,
|
||||
background.borderBottomRightRadius,
|
||||
background.borderBottomLeftRadius,
|
||||
background.borderTopLeftRadius,
|
||||
background.borderTopRightRadius,
|
||||
background.borderBottomRightRadius,
|
||||
background.borderBottomLeftRadius,
|
||||
|
||||
background.clipPath,
|
||||
background.clipPath,
|
||||
|
||||
background.color ? background.color.android : 0,
|
||||
imageUri,
|
||||
bitmap,
|
||||
gradient,
|
||||
context,
|
||||
background.repeat,
|
||||
background.position,
|
||||
backgroundPositionParsedCSSValues,
|
||||
background.size,
|
||||
backgroundSizeParsedCSSValues
|
||||
);
|
||||
//console.log(`>>> ${borderDrawable.toDebugString()}`);
|
||||
}
|
||||
background.color ? background.color.android : 0,
|
||||
imageUri,
|
||||
bitmap,
|
||||
gradient,
|
||||
context,
|
||||
background.repeat,
|
||||
background.position,
|
||||
backgroundPositionParsedCSSValues,
|
||||
background.size,
|
||||
backgroundSizeParsedCSSValues
|
||||
);
|
||||
//console.log(`>>> ${borderDrawable.toDebugString()}`);
|
||||
}
|
||||
}
|
||||
|
||||
function createNativeCSSValueArray(css: string): native.Array<org.nativescript.widgets.CSSValue> {
|
||||
if (!css) {
|
||||
return null;
|
||||
}
|
||||
if (!css) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const cssValues = parse(css);
|
||||
const nativeArray = Array.create(org.nativescript.widgets.CSSValue, cssValues.length);
|
||||
for (let i = 0, length = cssValues.length; i < length; i++) {
|
||||
nativeArray[i] = new org.nativescript.widgets.CSSValue(cssValues[i].type, cssValues[i].string, cssValues[i].unit, cssValues[i].value);
|
||||
}
|
||||
const cssValues = parse(css);
|
||||
const nativeArray = Array.create(org.nativescript.widgets.CSSValue, cssValues.length);
|
||||
for (let i = 0, length = cssValues.length; i < length; i++) {
|
||||
nativeArray[i] = new org.nativescript.widgets.CSSValue(cssValues[i].type, cssValues[i].string, cssValues[i].unit, cssValues[i].value);
|
||||
}
|
||||
|
||||
return nativeArray;
|
||||
return nativeArray;
|
||||
}
|
||||
|
||||
export enum CacheMode {
|
||||
none,
|
||||
memory,
|
||||
diskAndMemory,
|
||||
none,
|
||||
memory,
|
||||
diskAndMemory,
|
||||
}
|
||||
|
||||
let currentCacheMode: CacheMode;
|
||||
let imageFetcher: org.nativescript.widgets.image.Fetcher;
|
||||
|
||||
export function initImageCache(context: android.content.Context, mode = CacheMode.diskAndMemory, memoryCacheSize: number = 0.25, diskCacheSize: number = 10 * 1024 * 1024): void {
|
||||
if (currentCacheMode === mode) {
|
||||
return;
|
||||
}
|
||||
if (currentCacheMode === mode) {
|
||||
return;
|
||||
}
|
||||
|
||||
currentCacheMode = mode;
|
||||
if (!imageFetcher) {
|
||||
imageFetcher = org.nativescript.widgets.image.Fetcher.getInstance(context);
|
||||
} else {
|
||||
imageFetcher.clearCache();
|
||||
}
|
||||
currentCacheMode = mode;
|
||||
if (!imageFetcher) {
|
||||
imageFetcher = org.nativescript.widgets.image.Fetcher.getInstance(context);
|
||||
} else {
|
||||
imageFetcher.clearCache();
|
||||
}
|
||||
|
||||
const params = new org.nativescript.widgets.image.Cache.CacheParams();
|
||||
params.memoryCacheEnabled = mode !== CacheMode.none;
|
||||
params.setMemCacheSizePercent(memoryCacheSize); // Set memory cache to % of app memory
|
||||
params.diskCacheEnabled = mode === CacheMode.diskAndMemory;
|
||||
params.diskCacheSize = diskCacheSize;
|
||||
const imageCache = org.nativescript.widgets.image.Cache.getInstance(params);
|
||||
imageFetcher.addImageCache(imageCache);
|
||||
imageFetcher.initCache();
|
||||
const params = new org.nativescript.widgets.image.Cache.CacheParams();
|
||||
params.memoryCacheEnabled = mode !== CacheMode.none;
|
||||
params.setMemCacheSizePercent(memoryCacheSize); // Set memory cache to % of app memory
|
||||
params.diskCacheEnabled = mode === CacheMode.diskAndMemory;
|
||||
params.diskCacheSize = diskCacheSize;
|
||||
const imageCache = org.nativescript.widgets.image.Cache.getInstance(params);
|
||||
imageFetcher.addImageCache(imageCache);
|
||||
imageFetcher.initCache();
|
||||
}
|
||||
|
||||
function onLivesync(args): void {
|
||||
if (imageFetcher) {
|
||||
imageFetcher.clearCache();
|
||||
}
|
||||
if (imageFetcher) {
|
||||
imageFetcher.clearCache();
|
||||
}
|
||||
}
|
||||
application.on('livesync', onLivesync);
|
||||
|
||||
application.android.on(
|
||||
'activityStarted',
|
||||
<any>profile('initImageCache', (args) => {
|
||||
if (!imageFetcher) {
|
||||
initImageCache(args.activity);
|
||||
} else {
|
||||
imageFetcher.initCache();
|
||||
}
|
||||
})
|
||||
'activityStarted',
|
||||
<any>profile('initImageCache', (args) => {
|
||||
if (!imageFetcher) {
|
||||
initImageCache(args.activity);
|
||||
} else {
|
||||
imageFetcher.initCache();
|
||||
}
|
||||
})
|
||||
);
|
||||
|
||||
application.android.on(
|
||||
'activityStopped',
|
||||
<any>profile('closeImageCache', (args) => {
|
||||
if (imageFetcher) {
|
||||
imageFetcher.closeCache();
|
||||
}
|
||||
})
|
||||
'activityStopped',
|
||||
<any>profile('closeImageCache', (args) => {
|
||||
if (imageFetcher) {
|
||||
imageFetcher.closeCache();
|
||||
}
|
||||
})
|
||||
);
|
||||
|
||||
108
nativescript-core/ui/styling/background.d.ts
vendored
108
nativescript-core/ui/styling/background.d.ts
vendored
@@ -4,71 +4,71 @@ import { BackgroundRepeat } from '../../css/parser';
|
||||
import { LinearGradient } from '../styling/linear-gradient';
|
||||
|
||||
export enum CacheMode {
|
||||
none,
|
||||
memory,
|
||||
diskAndMemory,
|
||||
none,
|
||||
memory,
|
||||
diskAndMemory,
|
||||
}
|
||||
|
||||
export declare class Background {
|
||||
public static default: Background;
|
||||
public color: Color;
|
||||
public image: string | LinearGradient;
|
||||
public repeat: BackgroundRepeat;
|
||||
public position: string;
|
||||
public size: string;
|
||||
public borderTopColor: Color;
|
||||
public borderRightColor: Color;
|
||||
public borderBottomColor: Color;
|
||||
public borderLeftColor: Color;
|
||||
public borderTopWidth: number;
|
||||
public borderRightWidth: number;
|
||||
public borderBottomWidth: number;
|
||||
public borderLeftWidth: number;
|
||||
public borderTopLeftRadius: number;
|
||||
public borderTopRightRadius: number;
|
||||
public borderBottomRightRadius: number;
|
||||
public borderBottomLeftRadius: number;
|
||||
public clipPath: string;
|
||||
public static default: Background;
|
||||
public color: Color;
|
||||
public image: string | LinearGradient;
|
||||
public repeat: BackgroundRepeat;
|
||||
public position: string;
|
||||
public size: string;
|
||||
public borderTopColor: Color;
|
||||
public borderRightColor: Color;
|
||||
public borderBottomColor: Color;
|
||||
public borderLeftColor: Color;
|
||||
public borderTopWidth: number;
|
||||
public borderRightWidth: number;
|
||||
public borderBottomWidth: number;
|
||||
public borderLeftWidth: number;
|
||||
public borderTopLeftRadius: number;
|
||||
public borderTopRightRadius: number;
|
||||
public borderBottomRightRadius: number;
|
||||
public borderBottomLeftRadius: number;
|
||||
public clipPath: string;
|
||||
|
||||
public withColor(value: Color): Background;
|
||||
public withImage(value: string | LinearGradient): Background;
|
||||
public withRepeat(value: BackgroundRepeat): Background;
|
||||
public withPosition(value: string): Background;
|
||||
public withSize(value: string): Background;
|
||||
public withBorderTopColor(value: Color): Background;
|
||||
public withBorderRightColor(value: Color): Background;
|
||||
public withBorderBottomColor(value: Color): Background;
|
||||
public withBorderLeftColor(value: Color): Background;
|
||||
public withBorderTopWidth(value: number): Background;
|
||||
public withBorderRightWidth(value: number): Background;
|
||||
public withBorderBottomWidth(value: number): Background;
|
||||
public withBorderLeftWidth(value: number): Background;
|
||||
public withBorderTopLeftRadius(value: number): Background;
|
||||
public withBorderTopRightRadius(value: number): Background;
|
||||
public withBorderBottomRightRadius(value: number): Background;
|
||||
public withBorderBottomLeftRadius(value: number): Background;
|
||||
public withClipPath(value: string): Background;
|
||||
public withColor(value: Color): Background;
|
||||
public withImage(value: string | LinearGradient): Background;
|
||||
public withRepeat(value: BackgroundRepeat): Background;
|
||||
public withPosition(value: string): Background;
|
||||
public withSize(value: string): Background;
|
||||
public withBorderTopColor(value: Color): Background;
|
||||
public withBorderRightColor(value: Color): Background;
|
||||
public withBorderBottomColor(value: Color): Background;
|
||||
public withBorderLeftColor(value: Color): Background;
|
||||
public withBorderTopWidth(value: number): Background;
|
||||
public withBorderRightWidth(value: number): Background;
|
||||
public withBorderBottomWidth(value: number): Background;
|
||||
public withBorderLeftWidth(value: number): Background;
|
||||
public withBorderTopLeftRadius(value: number): Background;
|
||||
public withBorderTopRightRadius(value: number): Background;
|
||||
public withBorderBottomRightRadius(value: number): Background;
|
||||
public withBorderBottomLeftRadius(value: number): Background;
|
||||
public withClipPath(value: string): Background;
|
||||
|
||||
public isEmpty(): boolean;
|
||||
public isEmpty(): boolean;
|
||||
|
||||
public static equals(value1: Background, value2: Background): boolean;
|
||||
public static equals(value1: Background, value2: Background): boolean;
|
||||
|
||||
public hasBorderColor(): boolean;
|
||||
public hasBorderWidth(): boolean;
|
||||
public hasBorderRadius(): boolean;
|
||||
public hasUniformBorderColor(): boolean;
|
||||
public hasUniformBorderWidth(): boolean;
|
||||
public hasUniformBorderRadius(): boolean;
|
||||
public hasUniformBorder(): boolean;
|
||||
public getUniformBorderColor(): Color;
|
||||
public getUniformBorderWidth(): number;
|
||||
public getUniformBorderRadius(): number;
|
||||
public hasBorderColor(): boolean;
|
||||
public hasBorderWidth(): boolean;
|
||||
public hasBorderRadius(): boolean;
|
||||
public hasUniformBorderColor(): boolean;
|
||||
public hasUniformBorderWidth(): boolean;
|
||||
public hasUniformBorderRadius(): boolean;
|
||||
public hasUniformBorder(): boolean;
|
||||
public getUniformBorderColor(): Color;
|
||||
public getUniformBorderWidth(): number;
|
||||
public getUniformBorderRadius(): number;
|
||||
}
|
||||
|
||||
export module ios {
|
||||
export function createBackgroundUIColor(view: View, callback: (uiColor: any /* UIColor */) => void, flip?: boolean): void;
|
||||
export function createBackgroundUIColor(view: View, callback: (uiColor: any /* UIColor */) => void, flip?: boolean): void;
|
||||
}
|
||||
|
||||
export module ad {
|
||||
export function onBackgroundOrBorderPropertyChanged(v: View);
|
||||
export function onBackgroundOrBorderPropertyChanged(v: View);
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -1,47 +1,47 @@
|
||||
import { AnimationCurve } from '../enums';
|
||||
|
||||
const STYLE_CURVE_MAP = Object.freeze({
|
||||
ease: AnimationCurve.ease,
|
||||
linear: AnimationCurve.linear,
|
||||
'ease-in': AnimationCurve.easeIn,
|
||||
'ease-out': AnimationCurve.easeOut,
|
||||
'ease-in-out': AnimationCurve.easeInOut,
|
||||
spring: AnimationCurve.spring,
|
||||
ease: AnimationCurve.ease,
|
||||
linear: AnimationCurve.linear,
|
||||
'ease-in': AnimationCurve.easeIn,
|
||||
'ease-out': AnimationCurve.easeOut,
|
||||
'ease-in-out': AnimationCurve.easeInOut,
|
||||
spring: AnimationCurve.spring,
|
||||
});
|
||||
|
||||
export function timeConverter(value: string): number {
|
||||
let result = parseFloat(value);
|
||||
if (value.indexOf('ms') === -1) {
|
||||
result = result * 1000;
|
||||
}
|
||||
let result = parseFloat(value);
|
||||
if (value.indexOf('ms') === -1) {
|
||||
result = result * 1000;
|
||||
}
|
||||
|
||||
return Math.max(0.0, result);
|
||||
return Math.max(0.0, result);
|
||||
}
|
||||
|
||||
export function animationTimingFunctionConverter(value: string): any {
|
||||
return value ? STYLE_CURVE_MAP[value] || parseCubicBezierCurve(value) : AnimationCurve.ease;
|
||||
return value ? STYLE_CURVE_MAP[value] || parseCubicBezierCurve(value) : AnimationCurve.ease;
|
||||
}
|
||||
|
||||
function parseCubicBezierCurve(value: string) {
|
||||
const coordsString = /\((.*?)\)/.exec(value);
|
||||
const coords = coordsString && coordsString[1].split(',').map(stringToBezieCoords);
|
||||
const coordsString = /\((.*?)\)/.exec(value);
|
||||
const coords = coordsString && coordsString[1].split(',').map(stringToBezieCoords);
|
||||
|
||||
if (value.startsWith('cubic-bezier') && coordsString && coords.length === 4) {
|
||||
const [x1, x2, y1, y2] = [...coords];
|
||||
if (value.startsWith('cubic-bezier') && coordsString && coords.length === 4) {
|
||||
const [x1, x2, y1, y2] = [...coords];
|
||||
|
||||
return AnimationCurve.cubicBezier(x1, x2, y1, y2);
|
||||
} else {
|
||||
throw new Error(`Invalid value for animation: ${value}`);
|
||||
}
|
||||
return AnimationCurve.cubicBezier(x1, x2, y1, y2);
|
||||
} else {
|
||||
throw new Error(`Invalid value for animation: ${value}`);
|
||||
}
|
||||
}
|
||||
|
||||
function stringToBezieCoords(value: string): number {
|
||||
let result = parseFloat(value);
|
||||
if (result < 0) {
|
||||
return 0;
|
||||
} else if (result > 1) {
|
||||
return 1;
|
||||
}
|
||||
let result = parseFloat(value);
|
||||
if (result < 0) {
|
||||
return 0;
|
||||
} else if (result > 1) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
return result;
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -1,9 +1,9 @@
|
||||
import { KeyframeAnimationInfo, KeyframeDeclaration, KeyframeInfo, UnparsedKeyframe } from '../animation/keyframe-animation';
|
||||
|
||||
export class CssAnimationParser {
|
||||
public static keyframeAnimationsFromCSSDeclarations(declarations: KeyframeDeclaration[]): KeyframeAnimationInfo[];
|
||||
public static keyframeAnimationsFromCSSDeclarations(declarations: KeyframeDeclaration[]): KeyframeAnimationInfo[];
|
||||
|
||||
public static keyframesArrayFromCSS(keyframes: UnparsedKeyframe[]): KeyframeInfo[];
|
||||
public static keyframesArrayFromCSS(keyframes: UnparsedKeyframe[]): KeyframeInfo[];
|
||||
}
|
||||
|
||||
export function parseKeyframeDeclarations(unparsedKeyframeDeclarations: KeyframeDeclaration[]): KeyframeDeclaration[];
|
||||
|
||||
@@ -6,138 +6,138 @@ import { timeConverter, animationTimingFunctionConverter } from '../styling/conv
|
||||
import { transformConverter } from '../styling/style-properties';
|
||||
|
||||
const ANIMATION_PROPERTY_HANDLERS = Object.freeze({
|
||||
'animation-name': (info: any, value: any) => (info.name = value),
|
||||
'animation-duration': (info: any, value: any) => (info.duration = timeConverter(value)),
|
||||
'animation-delay': (info: any, value: any) => (info.delay = timeConverter(value)),
|
||||
'animation-timing-function': (info: any, value: any) => (info.curve = animationTimingFunctionConverter(value)),
|
||||
'animation-iteration-count': (info: any, value: any) => (info.iterations = value === 'infinite' ? Number.MAX_VALUE : parseFloat(value)),
|
||||
'animation-direction': (info: any, value: any) => (info.isReverse = value === 'reverse'),
|
||||
'animation-fill-mode': (info: any, value: any) => (info.isForwards = value === 'forwards'),
|
||||
'animation-name': (info: any, value: any) => (info.name = value),
|
||||
'animation-duration': (info: any, value: any) => (info.duration = timeConverter(value)),
|
||||
'animation-delay': (info: any, value: any) => (info.delay = timeConverter(value)),
|
||||
'animation-timing-function': (info: any, value: any) => (info.curve = animationTimingFunctionConverter(value)),
|
||||
'animation-iteration-count': (info: any, value: any) => (info.iterations = value === 'infinite' ? Number.MAX_VALUE : parseFloat(value)),
|
||||
'animation-direction': (info: any, value: any) => (info.isReverse = value === 'reverse'),
|
||||
'animation-fill-mode': (info: any, value: any) => (info.isForwards = value === 'forwards'),
|
||||
});
|
||||
|
||||
export class CssAnimationParser {
|
||||
public static keyframeAnimationsFromCSSDeclarations(declarations: KeyframeDeclaration[]): KeyframeAnimationInfo[] {
|
||||
if (declarations === null || declarations === undefined) {
|
||||
return undefined;
|
||||
}
|
||||
public static keyframeAnimationsFromCSSDeclarations(declarations: KeyframeDeclaration[]): KeyframeAnimationInfo[] {
|
||||
if (declarations === null || declarations === undefined) {
|
||||
return undefined;
|
||||
}
|
||||
|
||||
let animations = new Array<KeyframeAnimationInfo>();
|
||||
let animationInfo: KeyframeAnimationInfo = undefined;
|
||||
let animations = new Array<KeyframeAnimationInfo>();
|
||||
let animationInfo: KeyframeAnimationInfo = undefined;
|
||||
|
||||
declarations.forEach(({ property, value }) => {
|
||||
if (property === 'animation') {
|
||||
keyframeAnimationsFromCSSProperty(value, animations);
|
||||
} else {
|
||||
const propertyHandler = ANIMATION_PROPERTY_HANDLERS[property];
|
||||
if (propertyHandler) {
|
||||
if (animationInfo === undefined) {
|
||||
animationInfo = new KeyframeAnimationInfo();
|
||||
animations.push(animationInfo);
|
||||
}
|
||||
propertyHandler(animationInfo, value);
|
||||
}
|
||||
}
|
||||
});
|
||||
declarations.forEach(({ property, value }) => {
|
||||
if (property === 'animation') {
|
||||
keyframeAnimationsFromCSSProperty(value, animations);
|
||||
} else {
|
||||
const propertyHandler = ANIMATION_PROPERTY_HANDLERS[property];
|
||||
if (propertyHandler) {
|
||||
if (animationInfo === undefined) {
|
||||
animationInfo = new KeyframeAnimationInfo();
|
||||
animations.push(animationInfo);
|
||||
}
|
||||
propertyHandler(animationInfo, value);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return animations.length === 0 ? undefined : animations;
|
||||
}
|
||||
return animations.length === 0 ? undefined : animations;
|
||||
}
|
||||
|
||||
public static keyframesArrayFromCSS(keyframes: UnparsedKeyframe[]): KeyframeInfo[] {
|
||||
let parsedKeyframes = new Array<KeyframeInfo>();
|
||||
for (let keyframe of keyframes) {
|
||||
let declarations = parseKeyframeDeclarations(keyframe.declarations);
|
||||
for (let time of keyframe.values) {
|
||||
if (time === 'from') {
|
||||
time = 0;
|
||||
} else if (time === 'to') {
|
||||
time = 1;
|
||||
} else {
|
||||
time = parseFloat(time) / 100;
|
||||
if (time < 0) {
|
||||
time = 0;
|
||||
}
|
||||
if (time > 100) {
|
||||
time = 100;
|
||||
}
|
||||
}
|
||||
let current = parsedKeyframes[time];
|
||||
if (current === undefined) {
|
||||
current = <KeyframeInfo>{};
|
||||
current.duration = time;
|
||||
parsedKeyframes[time] = current;
|
||||
}
|
||||
for (let declaration of keyframe.declarations) {
|
||||
if (declaration.property === 'animation-timing-function') {
|
||||
current.curve = animationTimingFunctionConverter(declaration.value);
|
||||
}
|
||||
}
|
||||
current.declarations = declarations;
|
||||
}
|
||||
}
|
||||
let array = new Array();
|
||||
for (let parsedKeyframe in parsedKeyframes) {
|
||||
array.push(parsedKeyframes[parsedKeyframe]);
|
||||
}
|
||||
array.sort(function (a, b) {
|
||||
return a.duration - b.duration;
|
||||
});
|
||||
public static keyframesArrayFromCSS(keyframes: UnparsedKeyframe[]): KeyframeInfo[] {
|
||||
let parsedKeyframes = new Array<KeyframeInfo>();
|
||||
for (let keyframe of keyframes) {
|
||||
let declarations = parseKeyframeDeclarations(keyframe.declarations);
|
||||
for (let time of keyframe.values) {
|
||||
if (time === 'from') {
|
||||
time = 0;
|
||||
} else if (time === 'to') {
|
||||
time = 1;
|
||||
} else {
|
||||
time = parseFloat(time) / 100;
|
||||
if (time < 0) {
|
||||
time = 0;
|
||||
}
|
||||
if (time > 100) {
|
||||
time = 100;
|
||||
}
|
||||
}
|
||||
let current = parsedKeyframes[time];
|
||||
if (current === undefined) {
|
||||
current = <KeyframeInfo>{};
|
||||
current.duration = time;
|
||||
parsedKeyframes[time] = current;
|
||||
}
|
||||
for (let declaration of keyframe.declarations) {
|
||||
if (declaration.property === 'animation-timing-function') {
|
||||
current.curve = animationTimingFunctionConverter(declaration.value);
|
||||
}
|
||||
}
|
||||
current.declarations = declarations;
|
||||
}
|
||||
}
|
||||
let array = new Array();
|
||||
for (let parsedKeyframe in parsedKeyframes) {
|
||||
array.push(parsedKeyframes[parsedKeyframe]);
|
||||
}
|
||||
array.sort(function (a, b) {
|
||||
return a.duration - b.duration;
|
||||
});
|
||||
|
||||
return array;
|
||||
}
|
||||
return array;
|
||||
}
|
||||
}
|
||||
|
||||
function keyframeAnimationsFromCSSProperty(value: any, animations: KeyframeAnimationInfo[]) {
|
||||
if (typeof value === 'string') {
|
||||
let values = value.split(/[,]+/);
|
||||
for (let parsedValue of values) {
|
||||
let animationInfo = new KeyframeAnimationInfo();
|
||||
let arr = (<string>parsedValue).trim().split(/[ ]+/);
|
||||
if (typeof value === 'string') {
|
||||
let values = value.split(/[,]+/);
|
||||
for (let parsedValue of values) {
|
||||
let animationInfo = new KeyframeAnimationInfo();
|
||||
let arr = (<string>parsedValue).trim().split(/[ ]+/);
|
||||
|
||||
if (arr.length > 0) {
|
||||
animationInfo.name = arr[0];
|
||||
}
|
||||
if (arr.length > 1) {
|
||||
animationInfo.duration = timeConverter(arr[1]);
|
||||
}
|
||||
if (arr.length > 2) {
|
||||
animationInfo.curve = animationTimingFunctionConverter(arr[2]);
|
||||
}
|
||||
if (arr.length > 3) {
|
||||
animationInfo.delay = timeConverter(arr[3]);
|
||||
}
|
||||
if (arr.length > 4) {
|
||||
animationInfo.iterations = parseInt(arr[4]);
|
||||
}
|
||||
if (arr.length > 5) {
|
||||
animationInfo.isReverse = arr[4] === 'reverse';
|
||||
}
|
||||
if (arr.length > 6) {
|
||||
animationInfo.isForwards = arr[5] === 'forwards';
|
||||
}
|
||||
if (arr.length > 7) {
|
||||
throw new Error('Invalid value for animation: ' + value);
|
||||
}
|
||||
animations.push(animationInfo);
|
||||
}
|
||||
}
|
||||
if (arr.length > 0) {
|
||||
animationInfo.name = arr[0];
|
||||
}
|
||||
if (arr.length > 1) {
|
||||
animationInfo.duration = timeConverter(arr[1]);
|
||||
}
|
||||
if (arr.length > 2) {
|
||||
animationInfo.curve = animationTimingFunctionConverter(arr[2]);
|
||||
}
|
||||
if (arr.length > 3) {
|
||||
animationInfo.delay = timeConverter(arr[3]);
|
||||
}
|
||||
if (arr.length > 4) {
|
||||
animationInfo.iterations = parseInt(arr[4]);
|
||||
}
|
||||
if (arr.length > 5) {
|
||||
animationInfo.isReverse = arr[4] === 'reverse';
|
||||
}
|
||||
if (arr.length > 6) {
|
||||
animationInfo.isForwards = arr[5] === 'forwards';
|
||||
}
|
||||
if (arr.length > 7) {
|
||||
throw new Error('Invalid value for animation: ' + value);
|
||||
}
|
||||
animations.push(animationInfo);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export function parseKeyframeDeclarations(unparsedKeyframeDeclarations: KeyframeDeclaration[]): KeyframeDeclaration[] {
|
||||
const declarations = unparsedKeyframeDeclarations.reduce((declarations, { property: unparsedProperty, value: unparsedValue }) => {
|
||||
const property = CssAnimationProperty._getByCssName(unparsedProperty);
|
||||
const declarations = unparsedKeyframeDeclarations.reduce((declarations, { property: unparsedProperty, value: unparsedValue }) => {
|
||||
const property = CssAnimationProperty._getByCssName(unparsedProperty);
|
||||
|
||||
if (typeof unparsedProperty === 'string' && property && property._valueConverter) {
|
||||
declarations[property.name] = property._valueConverter(<string>unparsedValue);
|
||||
} else if (typeof unparsedValue === 'string' && unparsedProperty === 'transform') {
|
||||
const transformations = transformConverter(unparsedValue);
|
||||
Object.assign(declarations, transformations);
|
||||
}
|
||||
if (typeof unparsedProperty === 'string' && property && property._valueConverter) {
|
||||
declarations[property.name] = property._valueConverter(<string>unparsedValue);
|
||||
} else if (typeof unparsedValue === 'string' && unparsedProperty === 'transform') {
|
||||
const transformations = transformConverter(unparsedValue);
|
||||
Object.assign(declarations, transformations);
|
||||
}
|
||||
|
||||
return declarations;
|
||||
}, {});
|
||||
return declarations;
|
||||
}, {});
|
||||
|
||||
return Object.keys(declarations).map((property) => ({
|
||||
property,
|
||||
value: declarations[property],
|
||||
}));
|
||||
return Object.keys(declarations).map((property) => ({
|
||||
property,
|
||||
value: declarations[property],
|
||||
}));
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -5,85 +5,85 @@ import { makeValidator, makeParser } from '../core/properties';
|
||||
export * from './font-interfaces';
|
||||
|
||||
export abstract class Font implements FontDefinition {
|
||||
public static default = undefined;
|
||||
public static default = undefined;
|
||||
|
||||
get isItalic(): boolean {
|
||||
return this.fontStyle === FontStyle.ITALIC;
|
||||
}
|
||||
get isItalic(): boolean {
|
||||
return this.fontStyle === FontStyle.ITALIC;
|
||||
}
|
||||
|
||||
get isBold(): boolean {
|
||||
return this.fontWeight === FontWeight.SEMI_BOLD || this.fontWeight === FontWeight.BOLD || this.fontWeight === '700' || this.fontWeight === FontWeight.EXTRA_BOLD || this.fontWeight === FontWeight.BLACK;
|
||||
}
|
||||
get isBold(): boolean {
|
||||
return this.fontWeight === FontWeight.SEMI_BOLD || this.fontWeight === FontWeight.BOLD || this.fontWeight === '700' || this.fontWeight === FontWeight.EXTRA_BOLD || this.fontWeight === FontWeight.BLACK;
|
||||
}
|
||||
|
||||
protected constructor(public readonly fontFamily: string, public readonly fontSize: number, public readonly fontStyle: FontStyle, public readonly fontWeight: FontWeight) {}
|
||||
protected constructor(public readonly fontFamily: string, public readonly fontSize: number, public readonly fontStyle: FontStyle, public readonly fontWeight: FontWeight) {}
|
||||
|
||||
public abstract getAndroidTypeface(): any /* android.graphics.Typeface */;
|
||||
public abstract getUIFont(defaultFont: any /* UIFont */): any /* UIFont */;
|
||||
public abstract withFontFamily(family: string): Font;
|
||||
public abstract withFontStyle(style: string): Font;
|
||||
public abstract withFontWeight(weight: string): Font;
|
||||
public abstract withFontSize(size: number): Font;
|
||||
public abstract getAndroidTypeface(): any /* android.graphics.Typeface */;
|
||||
public abstract getUIFont(defaultFont: any /* UIFont */): any /* UIFont */;
|
||||
public abstract withFontFamily(family: string): Font;
|
||||
public abstract withFontStyle(style: string): Font;
|
||||
public abstract withFontWeight(weight: string): Font;
|
||||
public abstract withFontSize(size: number): Font;
|
||||
|
||||
public static equals(value1: Font, value2: Font): boolean {
|
||||
// both values are falsy
|
||||
if (!value1 && !value2) {
|
||||
return true;
|
||||
}
|
||||
public static equals(value1: Font, value2: Font): boolean {
|
||||
// both values are falsy
|
||||
if (!value1 && !value2) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// only one is falsy
|
||||
if (!value1 || !value2) {
|
||||
return false;
|
||||
}
|
||||
// only one is falsy
|
||||
if (!value1 || !value2) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return value1.fontFamily === value2.fontFamily && value1.fontSize === value2.fontSize && value1.fontStyle === value2.fontStyle && value1.fontWeight === value2.fontWeight;
|
||||
}
|
||||
return value1.fontFamily === value2.fontFamily && value1.fontSize === value2.fontSize && value1.fontStyle === value2.fontStyle && value1.fontWeight === value2.fontWeight;
|
||||
}
|
||||
}
|
||||
|
||||
export type FontStyle = 'normal' | 'italic';
|
||||
export namespace FontStyle {
|
||||
export const NORMAL: 'normal' = 'normal';
|
||||
export const ITALIC: 'italic' = 'italic';
|
||||
export const isValid = makeValidator<FontStyle>(NORMAL, ITALIC);
|
||||
export const parse = makeParser<FontStyle>(isValid);
|
||||
export const NORMAL: 'normal' = 'normal';
|
||||
export const ITALIC: 'italic' = 'italic';
|
||||
export const isValid = makeValidator<FontStyle>(NORMAL, ITALIC);
|
||||
export const parse = makeParser<FontStyle>(isValid);
|
||||
}
|
||||
|
||||
export type FontWeight = '100' | '200' | '300' | 'normal' | '400' | '500' | '600' | 'bold' | '700' | '800' | '900';
|
||||
export namespace FontWeight {
|
||||
export const THIN: '100' = '100';
|
||||
export const EXTRA_LIGHT: '200' = '200';
|
||||
export const LIGHT: '300' = '300';
|
||||
export const NORMAL: 'normal' = 'normal';
|
||||
export const MEDIUM: '500' = '500';
|
||||
export const SEMI_BOLD: '600' = '600';
|
||||
export const BOLD: 'bold' = 'bold';
|
||||
export const EXTRA_BOLD: '800' = '800';
|
||||
export const BLACK: '900' = '900';
|
||||
export const isValid = makeValidator<FontWeight>(THIN, EXTRA_LIGHT, LIGHT, NORMAL, '400', MEDIUM, SEMI_BOLD, BOLD, '700', EXTRA_BOLD, BLACK);
|
||||
export const parse = makeParser<FontStyle>(isValid);
|
||||
export const THIN: '100' = '100';
|
||||
export const EXTRA_LIGHT: '200' = '200';
|
||||
export const LIGHT: '300' = '300';
|
||||
export const NORMAL: 'normal' = 'normal';
|
||||
export const MEDIUM: '500' = '500';
|
||||
export const SEMI_BOLD: '600' = '600';
|
||||
export const BOLD: 'bold' = 'bold';
|
||||
export const EXTRA_BOLD: '800' = '800';
|
||||
export const BLACK: '900' = '900';
|
||||
export const isValid = makeValidator<FontWeight>(THIN, EXTRA_LIGHT, LIGHT, NORMAL, '400', MEDIUM, SEMI_BOLD, BOLD, '700', EXTRA_BOLD, BLACK);
|
||||
export const parse = makeParser<FontStyle>(isValid);
|
||||
}
|
||||
|
||||
export function parseFontFamily(value: string): Array<string> {
|
||||
const result = new Array<string>();
|
||||
if (!value) {
|
||||
return result;
|
||||
}
|
||||
const result = new Array<string>();
|
||||
if (!value) {
|
||||
return result;
|
||||
}
|
||||
|
||||
const split = value.split(',');
|
||||
for (let i = 0; i < split.length; i++) {
|
||||
let str = split[i].trim().replace(/['"]+/g, '');
|
||||
if (str) {
|
||||
result.push(str);
|
||||
}
|
||||
}
|
||||
const split = value.split(',');
|
||||
for (let i = 0; i < split.length; i++) {
|
||||
let str = split[i].trim().replace(/['"]+/g, '');
|
||||
if (str) {
|
||||
result.push(str);
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
return result;
|
||||
}
|
||||
|
||||
export module genericFontFamilies {
|
||||
export const serif = 'serif';
|
||||
export const sansSerif = 'sans-serif';
|
||||
export const monospace = 'monospace';
|
||||
export const system = 'system';
|
||||
export const serif = 'serif';
|
||||
export const sansSerif = 'sans-serif';
|
||||
export const monospace = 'monospace';
|
||||
export const system = 'system';
|
||||
}
|
||||
|
||||
const styles = new Set();
|
||||
@@ -105,36 +105,36 @@ const weights = new Set();
|
||||
[FontWeight.THIN, FontWeight.EXTRA_LIGHT, FontWeight.LIGHT, FontWeight.NORMAL, '400', FontWeight.MEDIUM, FontWeight.SEMI_BOLD, FontWeight.BOLD, '700', FontWeight.EXTRA_BOLD, FontWeight.BLACK].forEach((val, i, a) => weights.add(val));
|
||||
|
||||
export function parseFont(fontValue: string): ParsedFont {
|
||||
let result: ParsedFont = {
|
||||
fontStyle: 'normal',
|
||||
fontVariant: 'normal',
|
||||
fontWeight: 'normal',
|
||||
};
|
||||
let result: ParsedFont = {
|
||||
fontStyle: 'normal',
|
||||
fontVariant: 'normal',
|
||||
fontWeight: 'normal',
|
||||
};
|
||||
|
||||
const parts = fontValue.split(/\s+/);
|
||||
let part: string;
|
||||
while ((part = parts.shift())) {
|
||||
if (part === 'normal') {
|
||||
// nothing to do here
|
||||
} else if (part === 'small-caps') {
|
||||
// The only supported font variant in shorthand font
|
||||
result.fontVariant = part;
|
||||
} else if (styles.has(part)) {
|
||||
result.fontStyle = <any>part;
|
||||
} else if (weights.has(part)) {
|
||||
result.fontWeight = <any>part;
|
||||
} else if (!result.fontSize) {
|
||||
let sizes = part.split('/');
|
||||
result.fontSize = sizes[0];
|
||||
result.lineHeight = sizes.length > 1 ? sizes[1] : undefined;
|
||||
} else {
|
||||
result.fontFamily = part;
|
||||
if (parts.length) {
|
||||
result.fontFamily += ' ' + parts.join(' ');
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
const parts = fontValue.split(/\s+/);
|
||||
let part: string;
|
||||
while ((part = parts.shift())) {
|
||||
if (part === 'normal') {
|
||||
// nothing to do here
|
||||
} else if (part === 'small-caps') {
|
||||
// The only supported font variant in shorthand font
|
||||
result.fontVariant = part;
|
||||
} else if (styles.has(part)) {
|
||||
result.fontStyle = <any>part;
|
||||
} else if (weights.has(part)) {
|
||||
result.fontWeight = <any>part;
|
||||
} else if (!result.fontSize) {
|
||||
let sizes = part.split('/');
|
||||
result.fontSize = sizes[0];
|
||||
result.lineHeight = sizes.length > 1 ? sizes[1] : undefined;
|
||||
} else {
|
||||
result.fontFamily = part;
|
||||
if (parts.length) {
|
||||
result.fontFamily += ' ' + parts.join(' ');
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -3,10 +3,10 @@
|
||||
export type FontWeight = '100' | '200' | '300' | 'normal' | '400' | '500' | '600' | 'bold' | '700' | '800' | '900';
|
||||
|
||||
export interface ParsedFont {
|
||||
fontStyle?: FontStyle;
|
||||
fontVariant?: string;
|
||||
fontWeight?: FontWeight;
|
||||
lineHeight?: string;
|
||||
fontSize?: string;
|
||||
fontFamily?: string;
|
||||
fontStyle?: FontStyle;
|
||||
fontVariant?: string;
|
||||
fontWeight?: FontWeight;
|
||||
lineHeight?: string;
|
||||
fontSize?: string;
|
||||
fontFamily?: string;
|
||||
}
|
||||
|
||||
@@ -10,152 +10,152 @@ const typefaceCache = new Map<string, android.graphics.Typeface>();
|
||||
let appAssets: android.content.res.AssetManager;
|
||||
|
||||
export class Font extends FontBase {
|
||||
public static default = new Font(undefined, undefined, 'normal', 'normal');
|
||||
public static default = new Font(undefined, undefined, 'normal', 'normal');
|
||||
|
||||
private _typeface: android.graphics.Typeface;
|
||||
private _typeface: android.graphics.Typeface;
|
||||
|
||||
constructor(family: string, size: number, style: 'normal' | 'italic', weight: FontWeight) {
|
||||
super(family, size, style, weight);
|
||||
}
|
||||
constructor(family: string, size: number, style: 'normal' | 'italic', weight: FontWeight) {
|
||||
super(family, size, style, weight);
|
||||
}
|
||||
|
||||
public withFontFamily(family: string): Font {
|
||||
return new Font(family, this.fontSize, this.fontStyle, this.fontWeight);
|
||||
}
|
||||
public withFontFamily(family: string): Font {
|
||||
return new Font(family, this.fontSize, this.fontStyle, this.fontWeight);
|
||||
}
|
||||
|
||||
public withFontStyle(style: 'normal' | 'italic'): Font {
|
||||
return new Font(this.fontFamily, this.fontSize, style, this.fontWeight);
|
||||
}
|
||||
public withFontStyle(style: 'normal' | 'italic'): Font {
|
||||
return new Font(this.fontFamily, this.fontSize, style, this.fontWeight);
|
||||
}
|
||||
|
||||
public withFontWeight(weight: FontWeight): Font {
|
||||
return new Font(this.fontFamily, this.fontSize, this.fontStyle, weight);
|
||||
}
|
||||
public withFontWeight(weight: FontWeight): Font {
|
||||
return new Font(this.fontFamily, this.fontSize, this.fontStyle, weight);
|
||||
}
|
||||
|
||||
public withFontSize(size: number): Font {
|
||||
return new Font(this.fontFamily, size, this.fontStyle, this.fontWeight);
|
||||
}
|
||||
public withFontSize(size: number): Font {
|
||||
return new Font(this.fontFamily, size, this.fontStyle, this.fontWeight);
|
||||
}
|
||||
|
||||
public getAndroidTypeface(): android.graphics.Typeface {
|
||||
if (!this._typeface) {
|
||||
this._typeface = createTypeface(this);
|
||||
}
|
||||
public getAndroidTypeface(): android.graphics.Typeface {
|
||||
if (!this._typeface) {
|
||||
this._typeface = createTypeface(this);
|
||||
}
|
||||
|
||||
return this._typeface;
|
||||
}
|
||||
return this._typeface;
|
||||
}
|
||||
|
||||
public getUIFont(defaultFont: UIFont): UIFont {
|
||||
return undefined;
|
||||
}
|
||||
public getUIFont(defaultFont: UIFont): UIFont {
|
||||
return undefined;
|
||||
}
|
||||
}
|
||||
|
||||
function loadFontFromFile(fontFamily: string): android.graphics.Typeface {
|
||||
appAssets = appAssets || application.android.context.getAssets();
|
||||
if (!appAssets) {
|
||||
return null;
|
||||
}
|
||||
appAssets = appAssets || application.android.context.getAssets();
|
||||
if (!appAssets) {
|
||||
return null;
|
||||
}
|
||||
|
||||
let result = typefaceCache.get(fontFamily);
|
||||
// Check for undefined explicitly as null mean we tried to load the font, but failed.
|
||||
if (result === undefined) {
|
||||
result = null;
|
||||
let result = typefaceCache.get(fontFamily);
|
||||
// Check for undefined explicitly as null mean we tried to load the font, but failed.
|
||||
if (result === undefined) {
|
||||
result = null;
|
||||
|
||||
let fontAssetPath: string;
|
||||
const basePath = fs.path.join(fs.knownFolders.currentApp().path, 'fonts', fontFamily);
|
||||
if (fs.File.exists(basePath + '.ttf')) {
|
||||
fontAssetPath = FONTS_BASE_PATH + fontFamily + '.ttf';
|
||||
} else if (fs.File.exists(basePath + '.otf')) {
|
||||
fontAssetPath = FONTS_BASE_PATH + fontFamily + '.otf';
|
||||
} else {
|
||||
if (Trace.isEnabled()) {
|
||||
Trace.write('Could not find font file for ' + fontFamily, Trace.categories.Error, Trace.messageType.error);
|
||||
}
|
||||
}
|
||||
let fontAssetPath: string;
|
||||
const basePath = fs.path.join(fs.knownFolders.currentApp().path, 'fonts', fontFamily);
|
||||
if (fs.File.exists(basePath + '.ttf')) {
|
||||
fontAssetPath = FONTS_BASE_PATH + fontFamily + '.ttf';
|
||||
} else if (fs.File.exists(basePath + '.otf')) {
|
||||
fontAssetPath = FONTS_BASE_PATH + fontFamily + '.otf';
|
||||
} else {
|
||||
if (Trace.isEnabled()) {
|
||||
Trace.write('Could not find font file for ' + fontFamily, Trace.categories.Error, Trace.messageType.error);
|
||||
}
|
||||
}
|
||||
|
||||
if (fontAssetPath) {
|
||||
try {
|
||||
fontAssetPath = fs.path.join(fs.knownFolders.currentApp().path, fontAssetPath);
|
||||
result = android.graphics.Typeface.createFromFile(fontAssetPath);
|
||||
} catch (e) {
|
||||
if (Trace.isEnabled()) {
|
||||
Trace.write('Error loading font asset: ' + fontAssetPath, Trace.categories.Error, Trace.messageType.error);
|
||||
}
|
||||
}
|
||||
}
|
||||
typefaceCache.set(fontFamily, result);
|
||||
}
|
||||
if (fontAssetPath) {
|
||||
try {
|
||||
fontAssetPath = fs.path.join(fs.knownFolders.currentApp().path, fontAssetPath);
|
||||
result = android.graphics.Typeface.createFromFile(fontAssetPath);
|
||||
} catch (e) {
|
||||
if (Trace.isEnabled()) {
|
||||
Trace.write('Error loading font asset: ' + fontAssetPath, Trace.categories.Error, Trace.messageType.error);
|
||||
}
|
||||
}
|
||||
}
|
||||
typefaceCache.set(fontFamily, result);
|
||||
}
|
||||
|
||||
return result;
|
||||
return result;
|
||||
}
|
||||
|
||||
function createTypeface(font: Font): android.graphics.Typeface {
|
||||
let fontStyle = 0;
|
||||
if (font.isBold) {
|
||||
fontStyle |= android.graphics.Typeface.BOLD;
|
||||
}
|
||||
if (font.isItalic) {
|
||||
fontStyle |= android.graphics.Typeface.ITALIC;
|
||||
}
|
||||
let fontStyle = 0;
|
||||
if (font.isBold) {
|
||||
fontStyle |= android.graphics.Typeface.BOLD;
|
||||
}
|
||||
if (font.isItalic) {
|
||||
fontStyle |= android.graphics.Typeface.ITALIC;
|
||||
}
|
||||
|
||||
//http://stackoverflow.com/questions/19691530/valid-values-for-androidfontfamily-and-what-they-map-to
|
||||
const fonts = parseFontFamily(font.fontFamily);
|
||||
let result = null;
|
||||
for (let i = 0; i < fonts.length; i++) {
|
||||
switch (fonts[i].toLowerCase()) {
|
||||
case genericFontFamilies.serif:
|
||||
result = android.graphics.Typeface.create('serif' + getFontWeightSuffix(font.fontWeight), fontStyle);
|
||||
break;
|
||||
//http://stackoverflow.com/questions/19691530/valid-values-for-androidfontfamily-and-what-they-map-to
|
||||
const fonts = parseFontFamily(font.fontFamily);
|
||||
let result = null;
|
||||
for (let i = 0; i < fonts.length; i++) {
|
||||
switch (fonts[i].toLowerCase()) {
|
||||
case genericFontFamilies.serif:
|
||||
result = android.graphics.Typeface.create('serif' + getFontWeightSuffix(font.fontWeight), fontStyle);
|
||||
break;
|
||||
|
||||
case genericFontFamilies.sansSerif:
|
||||
case genericFontFamilies.system:
|
||||
result = android.graphics.Typeface.create('sans-serif' + getFontWeightSuffix(font.fontWeight), fontStyle);
|
||||
break;
|
||||
case genericFontFamilies.sansSerif:
|
||||
case genericFontFamilies.system:
|
||||
result = android.graphics.Typeface.create('sans-serif' + getFontWeightSuffix(font.fontWeight), fontStyle);
|
||||
break;
|
||||
|
||||
case genericFontFamilies.monospace:
|
||||
result = android.graphics.Typeface.create('monospace' + getFontWeightSuffix(font.fontWeight), fontStyle);
|
||||
break;
|
||||
case genericFontFamilies.monospace:
|
||||
result = android.graphics.Typeface.create('monospace' + getFontWeightSuffix(font.fontWeight), fontStyle);
|
||||
break;
|
||||
|
||||
default:
|
||||
result = loadFontFromFile(fonts[i]);
|
||||
if (result && fontStyle) {
|
||||
result = android.graphics.Typeface.create(result, fontStyle);
|
||||
}
|
||||
break;
|
||||
}
|
||||
default:
|
||||
result = loadFontFromFile(fonts[i]);
|
||||
if (result && fontStyle) {
|
||||
result = android.graphics.Typeface.create(result, fontStyle);
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
if (result) {
|
||||
// Found the font!
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (result) {
|
||||
// Found the font!
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!result) {
|
||||
result = android.graphics.Typeface.create('sans-serif' + getFontWeightSuffix(font.fontWeight), fontStyle);
|
||||
}
|
||||
if (!result) {
|
||||
result = android.graphics.Typeface.create('sans-serif' + getFontWeightSuffix(font.fontWeight), fontStyle);
|
||||
}
|
||||
|
||||
return result;
|
||||
return result;
|
||||
}
|
||||
|
||||
function getFontWeightSuffix(fontWeight: FontWeight): string {
|
||||
switch (fontWeight) {
|
||||
case FontWeight.THIN:
|
||||
return android.os.Build.VERSION.SDK_INT >= 16 ? '-thin' : '';
|
||||
case FontWeight.EXTRA_LIGHT:
|
||||
case FontWeight.LIGHT:
|
||||
return android.os.Build.VERSION.SDK_INT >= 16 ? '-light' : '';
|
||||
case FontWeight.NORMAL:
|
||||
case '400':
|
||||
case undefined:
|
||||
case null:
|
||||
return '';
|
||||
case FontWeight.MEDIUM:
|
||||
case FontWeight.SEMI_BOLD:
|
||||
return android.os.Build.VERSION.SDK_INT >= 21 ? '-medium' : '';
|
||||
case FontWeight.BOLD:
|
||||
case '700':
|
||||
case FontWeight.EXTRA_BOLD:
|
||||
return '';
|
||||
case FontWeight.BLACK:
|
||||
return android.os.Build.VERSION.SDK_INT >= 21 ? '-black' : '';
|
||||
default:
|
||||
throw new Error(`Invalid font weight: "${fontWeight}"`);
|
||||
}
|
||||
switch (fontWeight) {
|
||||
case FontWeight.THIN:
|
||||
return android.os.Build.VERSION.SDK_INT >= 16 ? '-thin' : '';
|
||||
case FontWeight.EXTRA_LIGHT:
|
||||
case FontWeight.LIGHT:
|
||||
return android.os.Build.VERSION.SDK_INT >= 16 ? '-light' : '';
|
||||
case FontWeight.NORMAL:
|
||||
case '400':
|
||||
case undefined:
|
||||
case null:
|
||||
return '';
|
||||
case FontWeight.MEDIUM:
|
||||
case FontWeight.SEMI_BOLD:
|
||||
return android.os.Build.VERSION.SDK_INT >= 21 ? '-medium' : '';
|
||||
case FontWeight.BOLD:
|
||||
case '700':
|
||||
case FontWeight.EXTRA_BOLD:
|
||||
return '';
|
||||
case FontWeight.BLACK:
|
||||
return android.os.Build.VERSION.SDK_INT >= 21 ? '-black' : '';
|
||||
default:
|
||||
throw new Error(`Invalid font weight: "${fontWeight}"`);
|
||||
}
|
||||
}
|
||||
|
||||
74
nativescript-core/ui/styling/font.d.ts
vendored
74
nativescript-core/ui/styling/font.d.ts
vendored
@@ -1,61 +1,61 @@
|
||||
export class Font {
|
||||
public static default: Font;
|
||||
public static default: Font;
|
||||
|
||||
public fontFamily: string;
|
||||
public fontStyle: FontStyle;
|
||||
public fontWeight: FontWeight;
|
||||
public fontSize: number;
|
||||
public fontFamily: string;
|
||||
public fontStyle: FontStyle;
|
||||
public fontWeight: FontWeight;
|
||||
public fontSize: number;
|
||||
|
||||
public isBold: boolean;
|
||||
public isItalic: boolean;
|
||||
public isBold: boolean;
|
||||
public isItalic: boolean;
|
||||
|
||||
constructor(family: string, size: number, style: FontStyle, weight: FontWeight);
|
||||
constructor(family: string, size: number, style: FontStyle, weight: FontWeight);
|
||||
|
||||
public getAndroidTypeface(): any /* android.graphics.Typeface */;
|
||||
public getUIFont(defaultFont: any /* UIFont */): any /* UIFont */;
|
||||
public getAndroidTypeface(): any /* android.graphics.Typeface */;
|
||||
public getUIFont(defaultFont: any /* UIFont */): any /* UIFont */;
|
||||
|
||||
public withFontFamily(family: string): Font;
|
||||
public withFontStyle(style: string): Font;
|
||||
public withFontWeight(weight: string): Font;
|
||||
public withFontSize(size: number): Font;
|
||||
public withFontFamily(family: string): Font;
|
||||
public withFontStyle(style: string): Font;
|
||||
public withFontWeight(weight: string): Font;
|
||||
public withFontSize(size: number): Font;
|
||||
|
||||
public static equals(value1: Font, value2: Font): boolean;
|
||||
public static equals(value1: Font, value2: Font): boolean;
|
||||
}
|
||||
|
||||
export type FontStyle = 'normal' | 'italic';
|
||||
export namespace FontStyle {
|
||||
export const NORMAL: 'normal';
|
||||
export const ITALIC: 'italic';
|
||||
export function isValid(value: any): boolean;
|
||||
export function parse(value: string): FontStyle;
|
||||
export const NORMAL: 'normal';
|
||||
export const ITALIC: 'italic';
|
||||
export function isValid(value: any): boolean;
|
||||
export function parse(value: string): FontStyle;
|
||||
}
|
||||
|
||||
export type FontWeight = '100' | '200' | '300' | 'normal' | '400' | '500' | '600' | 'bold' | '700' | '800' | '900';
|
||||
export namespace FontWeight {
|
||||
export const THIN: '100';
|
||||
export const EXTRA_LIGHT: '200';
|
||||
export const LIGHT: '300';
|
||||
export const NORMAL: 'normal';
|
||||
export const MEDIUM: '500';
|
||||
export const SEMI_BOLD: '600';
|
||||
export const BOLD: 'bold';
|
||||
export const EXTRA_BOLD: '800';
|
||||
export const BLACK: '900';
|
||||
export function isValid(value: any): boolean;
|
||||
export function parse(value: string): FontWeight;
|
||||
export const THIN: '100';
|
||||
export const EXTRA_LIGHT: '200';
|
||||
export const LIGHT: '300';
|
||||
export const NORMAL: 'normal';
|
||||
export const MEDIUM: '500';
|
||||
export const SEMI_BOLD: '600';
|
||||
export const BOLD: 'bold';
|
||||
export const EXTRA_BOLD: '800';
|
||||
export const BLACK: '900';
|
||||
export function isValid(value: any): boolean;
|
||||
export function parse(value: string): FontWeight;
|
||||
}
|
||||
|
||||
export interface ParsedFont {
|
||||
fontStyle?: FontStyle;
|
||||
fontVariant?: string;
|
||||
fontWeight?: FontWeight;
|
||||
lineHeight?: string;
|
||||
fontSize?: string;
|
||||
fontFamily?: string;
|
||||
fontStyle?: FontStyle;
|
||||
fontVariant?: string;
|
||||
fontWeight?: FontWeight;
|
||||
lineHeight?: string;
|
||||
fontSize?: string;
|
||||
fontFamily?: string;
|
||||
}
|
||||
|
||||
export function parseFont(fontValue: string): ParsedFont;
|
||||
|
||||
export module ios {
|
||||
export function registerFont(fontFile: string);
|
||||
export function registerFont(fontFile: string);
|
||||
}
|
||||
|
||||
@@ -11,213 +11,213 @@ const DEFAULT_MONOSPACE = 'Courier New';
|
||||
const SUPPORT_FONT_WEIGHTS = parseFloat(Device.osVersion) >= 10.0;
|
||||
|
||||
export class Font extends FontBase {
|
||||
public static default = new Font(undefined, undefined, FontStyle.NORMAL, FontWeight.NORMAL);
|
||||
public static default = new Font(undefined, undefined, FontStyle.NORMAL, FontWeight.NORMAL);
|
||||
|
||||
private _uiFont: UIFont;
|
||||
private _uiFont: UIFont;
|
||||
|
||||
constructor(family: string, size: number, style: FontStyle, weight: FontWeight) {
|
||||
super(family, size, style, weight);
|
||||
}
|
||||
constructor(family: string, size: number, style: FontStyle, weight: FontWeight) {
|
||||
super(family, size, style, weight);
|
||||
}
|
||||
|
||||
public withFontFamily(family: string): Font {
|
||||
return new Font(family, this.fontSize, this.fontStyle, this.fontWeight);
|
||||
}
|
||||
public withFontFamily(family: string): Font {
|
||||
return new Font(family, this.fontSize, this.fontStyle, this.fontWeight);
|
||||
}
|
||||
|
||||
public withFontStyle(style: FontStyle): Font {
|
||||
return new Font(this.fontFamily, this.fontSize, style, this.fontWeight);
|
||||
}
|
||||
public withFontStyle(style: FontStyle): Font {
|
||||
return new Font(this.fontFamily, this.fontSize, style, this.fontWeight);
|
||||
}
|
||||
|
||||
public withFontWeight(weight: FontWeight): Font {
|
||||
return new Font(this.fontFamily, this.fontSize, this.fontStyle, weight);
|
||||
}
|
||||
public withFontWeight(weight: FontWeight): Font {
|
||||
return new Font(this.fontFamily, this.fontSize, this.fontStyle, weight);
|
||||
}
|
||||
|
||||
public withFontSize(size: number): Font {
|
||||
return new Font(this.fontFamily, size, this.fontStyle, this.fontWeight);
|
||||
}
|
||||
public withFontSize(size: number): Font {
|
||||
return new Font(this.fontFamily, size, this.fontStyle, this.fontWeight);
|
||||
}
|
||||
|
||||
public getUIFont(defaultFont: UIFont): UIFont {
|
||||
if (!this._uiFont) {
|
||||
this._uiFont = createUIFont(this, defaultFont);
|
||||
}
|
||||
public getUIFont(defaultFont: UIFont): UIFont {
|
||||
if (!this._uiFont) {
|
||||
this._uiFont = createUIFont(this, defaultFont);
|
||||
}
|
||||
|
||||
return this._uiFont;
|
||||
}
|
||||
return this._uiFont;
|
||||
}
|
||||
|
||||
public getAndroidTypeface(): android.graphics.Typeface {
|
||||
return undefined;
|
||||
}
|
||||
public getAndroidTypeface(): android.graphics.Typeface {
|
||||
return undefined;
|
||||
}
|
||||
}
|
||||
|
||||
function getFontFamilyRespectingGenericFonts(fontFamily: string): string {
|
||||
if (!fontFamily) {
|
||||
return fontFamily;
|
||||
}
|
||||
if (!fontFamily) {
|
||||
return fontFamily;
|
||||
}
|
||||
|
||||
switch (fontFamily.toLowerCase()) {
|
||||
case genericFontFamilies.serif:
|
||||
return DEFAULT_SERIF;
|
||||
switch (fontFamily.toLowerCase()) {
|
||||
case genericFontFamilies.serif:
|
||||
return DEFAULT_SERIF;
|
||||
|
||||
case genericFontFamilies.monospace:
|
||||
return DEFAULT_MONOSPACE;
|
||||
case genericFontFamilies.monospace:
|
||||
return DEFAULT_MONOSPACE;
|
||||
|
||||
default:
|
||||
return fontFamily;
|
||||
}
|
||||
default:
|
||||
return fontFamily;
|
||||
}
|
||||
}
|
||||
|
||||
function shouldUseSystemFont(fontFamily: string) {
|
||||
return !fontFamily || fontFamily === genericFontFamilies.sansSerif || fontFamily === genericFontFamilies.system;
|
||||
return !fontFamily || fontFamily === genericFontFamilies.sansSerif || fontFamily === genericFontFamilies.system;
|
||||
}
|
||||
|
||||
function getNativeFontWeight(fontWeight: FontWeight): number {
|
||||
switch (fontWeight) {
|
||||
case FontWeight.THIN:
|
||||
return UIFontWeightUltraLight;
|
||||
case FontWeight.EXTRA_LIGHT:
|
||||
return UIFontWeightThin;
|
||||
case FontWeight.LIGHT:
|
||||
return UIFontWeightLight;
|
||||
case FontWeight.NORMAL:
|
||||
case '400':
|
||||
case undefined:
|
||||
case null:
|
||||
return UIFontWeightRegular;
|
||||
case FontWeight.MEDIUM:
|
||||
return UIFontWeightMedium;
|
||||
case FontWeight.SEMI_BOLD:
|
||||
return UIFontWeightSemibold;
|
||||
case FontWeight.BOLD:
|
||||
case '700':
|
||||
return UIFontWeightBold;
|
||||
case FontWeight.EXTRA_BOLD:
|
||||
return UIFontWeightHeavy;
|
||||
case FontWeight.BLACK:
|
||||
return UIFontWeightBlack;
|
||||
default:
|
||||
throw new Error(`Invalid font weight: "${fontWeight}"`);
|
||||
}
|
||||
switch (fontWeight) {
|
||||
case FontWeight.THIN:
|
||||
return UIFontWeightUltraLight;
|
||||
case FontWeight.EXTRA_LIGHT:
|
||||
return UIFontWeightThin;
|
||||
case FontWeight.LIGHT:
|
||||
return UIFontWeightLight;
|
||||
case FontWeight.NORMAL:
|
||||
case '400':
|
||||
case undefined:
|
||||
case null:
|
||||
return UIFontWeightRegular;
|
||||
case FontWeight.MEDIUM:
|
||||
return UIFontWeightMedium;
|
||||
case FontWeight.SEMI_BOLD:
|
||||
return UIFontWeightSemibold;
|
||||
case FontWeight.BOLD:
|
||||
case '700':
|
||||
return UIFontWeightBold;
|
||||
case FontWeight.EXTRA_BOLD:
|
||||
return UIFontWeightHeavy;
|
||||
case FontWeight.BLACK:
|
||||
return UIFontWeightBlack;
|
||||
default:
|
||||
throw new Error(`Invalid font weight: "${fontWeight}"`);
|
||||
}
|
||||
}
|
||||
|
||||
function getSystemFont(size: number, nativeWeight: number, italic: boolean, symbolicTraits: number): UIFont {
|
||||
let result = UIFont.systemFontOfSizeWeight(size, nativeWeight);
|
||||
if (italic) {
|
||||
let descriptor = result.fontDescriptor.fontDescriptorWithSymbolicTraits(symbolicTraits);
|
||||
result = UIFont.fontWithDescriptorSize(descriptor, size);
|
||||
}
|
||||
let result = UIFont.systemFontOfSizeWeight(size, nativeWeight);
|
||||
if (italic) {
|
||||
let descriptor = result.fontDescriptor.fontDescriptorWithSymbolicTraits(symbolicTraits);
|
||||
result = UIFont.fontWithDescriptorSize(descriptor, size);
|
||||
}
|
||||
|
||||
return result;
|
||||
return result;
|
||||
}
|
||||
|
||||
function createUIFont(font: Font, defaultFont: UIFont): UIFont {
|
||||
let result: UIFont;
|
||||
const size = font.fontSize || defaultFont.pointSize;
|
||||
const nativeWeight = getNativeFontWeight(font.fontWeight);
|
||||
const fontFamilies = parseFontFamily(font.fontFamily);
|
||||
let result: UIFont;
|
||||
const size = font.fontSize || defaultFont.pointSize;
|
||||
const nativeWeight = getNativeFontWeight(font.fontWeight);
|
||||
const fontFamilies = parseFontFamily(font.fontFamily);
|
||||
|
||||
let symbolicTraits: number = 0;
|
||||
if (font.isBold) {
|
||||
symbolicTraits |= UIFontDescriptorSymbolicTraits.TraitBold;
|
||||
}
|
||||
if (font.isItalic) {
|
||||
symbolicTraits |= UIFontDescriptorSymbolicTraits.TraitItalic;
|
||||
}
|
||||
let symbolicTraits: number = 0;
|
||||
if (font.isBold) {
|
||||
symbolicTraits |= UIFontDescriptorSymbolicTraits.TraitBold;
|
||||
}
|
||||
if (font.isItalic) {
|
||||
symbolicTraits |= UIFontDescriptorSymbolicTraits.TraitItalic;
|
||||
}
|
||||
|
||||
let fontDescriptorTraits = {
|
||||
[UIFontSymbolicTrait]: symbolicTraits,
|
||||
};
|
||||
let fontDescriptorTraits = {
|
||||
[UIFontSymbolicTrait]: symbolicTraits,
|
||||
};
|
||||
|
||||
// IOS versions below 10 will not return the correct font when UIFontWeightTrait is set
|
||||
// In this case - rely on UIFontSymbolicTrait only
|
||||
if (SUPPORT_FONT_WEIGHTS) {
|
||||
fontDescriptorTraits[UIFontWeightTrait] = nativeWeight;
|
||||
}
|
||||
// IOS versions below 10 will not return the correct font when UIFontWeightTrait is set
|
||||
// In this case - rely on UIFontSymbolicTrait only
|
||||
if (SUPPORT_FONT_WEIGHTS) {
|
||||
fontDescriptorTraits[UIFontWeightTrait] = nativeWeight;
|
||||
}
|
||||
|
||||
for (let i = 0; i < fontFamilies.length; i++) {
|
||||
const fontFamily = getFontFamilyRespectingGenericFonts(fontFamilies[i]);
|
||||
for (let i = 0; i < fontFamilies.length; i++) {
|
||||
const fontFamily = getFontFamilyRespectingGenericFonts(fontFamilies[i]);
|
||||
|
||||
if (shouldUseSystemFont(fontFamily)) {
|
||||
result = getSystemFont(size, nativeWeight, font.isItalic, symbolicTraits);
|
||||
break;
|
||||
} else {
|
||||
const fontAttributes = {
|
||||
[UIFontDescriptorFamilyAttribute]: fontFamily,
|
||||
[UIFontDescriptorTraitsAttribute]: fontDescriptorTraits,
|
||||
};
|
||||
if (shouldUseSystemFont(fontFamily)) {
|
||||
result = getSystemFont(size, nativeWeight, font.isItalic, symbolicTraits);
|
||||
break;
|
||||
} else {
|
||||
const fontAttributes = {
|
||||
[UIFontDescriptorFamilyAttribute]: fontFamily,
|
||||
[UIFontDescriptorTraitsAttribute]: fontDescriptorTraits,
|
||||
};
|
||||
|
||||
let descriptor = UIFontDescriptor.fontDescriptorWithFontAttributes(<any>fontAttributes);
|
||||
result = UIFont.fontWithDescriptorSize(descriptor, size);
|
||||
let descriptor = UIFontDescriptor.fontDescriptorWithFontAttributes(<any>fontAttributes);
|
||||
result = UIFont.fontWithDescriptorSize(descriptor, size);
|
||||
|
||||
let actualItalic = result.fontDescriptor.symbolicTraits & UIFontDescriptorSymbolicTraits.TraitItalic;
|
||||
if (font.isItalic && !actualItalic && EMULATE_OBLIQUE) {
|
||||
// The font we got is not actually italic so emulate that with a matrix
|
||||
descriptor = descriptor.fontDescriptorWithMatrix(OBLIQUE_TRANSFORM);
|
||||
result = UIFont.fontWithDescriptorSize(descriptor, size);
|
||||
}
|
||||
let actualItalic = result.fontDescriptor.symbolicTraits & UIFontDescriptorSymbolicTraits.TraitItalic;
|
||||
if (font.isItalic && !actualItalic && EMULATE_OBLIQUE) {
|
||||
// The font we got is not actually italic so emulate that with a matrix
|
||||
descriptor = descriptor.fontDescriptorWithMatrix(OBLIQUE_TRANSFORM);
|
||||
result = UIFont.fontWithDescriptorSize(descriptor, size);
|
||||
}
|
||||
|
||||
// Check if the resolved font has the correct font-family
|
||||
// If not - fallback to the next font-family
|
||||
if (result.familyName === fontFamily) {
|
||||
break;
|
||||
} else {
|
||||
result = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
// Check if the resolved font has the correct font-family
|
||||
// If not - fallback to the next font-family
|
||||
if (result.familyName === fontFamily) {
|
||||
break;
|
||||
} else {
|
||||
result = null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Couldn't resolve font - fallback to the system font
|
||||
if (!result) {
|
||||
result = getSystemFont(size, nativeWeight, font.isItalic, symbolicTraits);
|
||||
}
|
||||
// Couldn't resolve font - fallback to the system font
|
||||
if (!result) {
|
||||
result = getSystemFont(size, nativeWeight, font.isItalic, symbolicTraits);
|
||||
}
|
||||
|
||||
return result;
|
||||
return result;
|
||||
}
|
||||
|
||||
export module ios {
|
||||
export function registerFont(fontFile: string) {
|
||||
let filePath = fs.path.join(fs.knownFolders.currentApp().path, 'fonts', fontFile);
|
||||
if (!fs.File.exists(filePath)) {
|
||||
filePath = fs.path.join(fs.knownFolders.currentApp().path, fontFile);
|
||||
}
|
||||
const fontData = NSFileManager.defaultManager.contentsAtPath(filePath);
|
||||
if (!fontData) {
|
||||
throw new Error('Could not load font from: ' + fontFile);
|
||||
}
|
||||
const provider = CGDataProviderCreateWithCFData(fontData);
|
||||
const font = CGFontCreateWithDataProvider(provider);
|
||||
export function registerFont(fontFile: string) {
|
||||
let filePath = fs.path.join(fs.knownFolders.currentApp().path, 'fonts', fontFile);
|
||||
if (!fs.File.exists(filePath)) {
|
||||
filePath = fs.path.join(fs.knownFolders.currentApp().path, fontFile);
|
||||
}
|
||||
const fontData = NSFileManager.defaultManager.contentsAtPath(filePath);
|
||||
if (!fontData) {
|
||||
throw new Error('Could not load font from: ' + fontFile);
|
||||
}
|
||||
const provider = CGDataProviderCreateWithCFData(fontData);
|
||||
const font = CGFontCreateWithDataProvider(provider);
|
||||
|
||||
if (!font) {
|
||||
throw new Error('Could not load font from: ' + fontFile);
|
||||
}
|
||||
if (!font) {
|
||||
throw new Error('Could not load font from: ' + fontFile);
|
||||
}
|
||||
|
||||
const error = new interop.Reference<NSError>();
|
||||
if (!CTFontManagerRegisterGraphicsFont(font, error)) {
|
||||
if (Trace.isEnabled()) {
|
||||
Trace.write('Error occur while registering font: ' + CFErrorCopyDescription(<NSError>error.value), Trace.categories.Error, Trace.messageType.error);
|
||||
}
|
||||
}
|
||||
}
|
||||
const error = new interop.Reference<NSError>();
|
||||
if (!CTFontManagerRegisterGraphicsFont(font, error)) {
|
||||
if (Trace.isEnabled()) {
|
||||
Trace.write('Error occur while registering font: ' + CFErrorCopyDescription(<NSError>error.value), Trace.categories.Error, Trace.messageType.error);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function registerFontsInFolder(fontsFolderPath) {
|
||||
const fontsFolder = fs.Folder.fromPath(fontsFolderPath);
|
||||
const fontsFolder = fs.Folder.fromPath(fontsFolderPath);
|
||||
|
||||
fontsFolder.eachEntity((fileEntity: fs.FileSystemEntity) => {
|
||||
if (fs.Folder.exists(fs.path.join(fontsFolderPath, fileEntity.name))) {
|
||||
return true;
|
||||
}
|
||||
if (fileEntity instanceof fs.File && ((<fs.File>fileEntity).extension === '.ttf' || (<fs.File>fileEntity).extension === '.otf')) {
|
||||
ios.registerFont(fileEntity.name);
|
||||
}
|
||||
fontsFolder.eachEntity((fileEntity: fs.FileSystemEntity) => {
|
||||
if (fs.Folder.exists(fs.path.join(fontsFolderPath, fileEntity.name))) {
|
||||
return true;
|
||||
}
|
||||
if (fileEntity instanceof fs.File && ((<fs.File>fileEntity).extension === '.ttf' || (<fs.File>fileEntity).extension === '.otf')) {
|
||||
ios.registerFont(fileEntity.name);
|
||||
}
|
||||
|
||||
return true;
|
||||
});
|
||||
return true;
|
||||
});
|
||||
}
|
||||
|
||||
function registerCustomFonts() {
|
||||
const appDir = fs.knownFolders.currentApp().path;
|
||||
const fontsDir = fs.path.join(appDir, 'fonts');
|
||||
if (fs.Folder.exists(fontsDir)) {
|
||||
registerFontsInFolder(fontsDir);
|
||||
}
|
||||
const appDir = fs.knownFolders.currentApp().path;
|
||||
const fontsDir = fs.path.join(appDir, 'fonts');
|
||||
if (fs.Folder.exists(fontsDir)) {
|
||||
registerFontsInFolder(fontsDir);
|
||||
}
|
||||
}
|
||||
registerCustomFonts();
|
||||
|
||||
12
nativescript-core/ui/styling/gradient.d.ts
vendored
12
nativescript-core/ui/styling/gradient.d.ts
vendored
@@ -3,15 +3,15 @@ import { Color } from '../../color';
|
||||
import { LinearGradient as LinearGradientDefinition } from '../../css/parser';
|
||||
|
||||
export class LinearGradient {
|
||||
public angle: number;
|
||||
public colorStops: ColorStop[];
|
||||
public angle: number;
|
||||
public colorStops: ColorStop[];
|
||||
|
||||
public static parse(value: LinearGradientDefinition): LinearGradientDefinition;
|
||||
public static parse(value: LinearGradientDefinition): LinearGradientDefinition;
|
||||
|
||||
public static equals(first: LinearGradientDefinition, second: LinearGradientDefinition): boolean;
|
||||
public static equals(first: LinearGradientDefinition, second: LinearGradientDefinition): boolean;
|
||||
}
|
||||
|
||||
export interface ColorStop {
|
||||
color: Color;
|
||||
offset?: LengthPercentUnit;
|
||||
color: Color;
|
||||
offset?: LengthPercentUnit;
|
||||
}
|
||||
|
||||
@@ -4,58 +4,58 @@ import { ColorStop } from './gradient';
|
||||
import { LinearGradient as CSSLinearGradient } from '../../css/parser';
|
||||
|
||||
export class LinearGradient {
|
||||
public angle: number;
|
||||
public colorStops: ColorStop[];
|
||||
public angle: number;
|
||||
public colorStops: ColorStop[];
|
||||
|
||||
public static parse(value: CSSLinearGradient): LinearGradient {
|
||||
const result = new LinearGradient();
|
||||
result.angle = value.angle;
|
||||
result.colorStops = value.colors.map((color) => {
|
||||
const offset = color.offset || null;
|
||||
let offsetUnit: LengthPercentUnit;
|
||||
public static parse(value: CSSLinearGradient): LinearGradient {
|
||||
const result = new LinearGradient();
|
||||
result.angle = value.angle;
|
||||
result.colorStops = value.colors.map((color) => {
|
||||
const offset = color.offset || null;
|
||||
let offsetUnit: LengthPercentUnit;
|
||||
|
||||
if (offset && offset.unit === '%') {
|
||||
offsetUnit = {
|
||||
unit: '%',
|
||||
value: offset.value,
|
||||
};
|
||||
}
|
||||
if (offset && offset.unit === '%') {
|
||||
offsetUnit = {
|
||||
unit: '%',
|
||||
value: offset.value,
|
||||
};
|
||||
}
|
||||
|
||||
return {
|
||||
color: new Color(color.argb),
|
||||
offset: offsetUnit,
|
||||
};
|
||||
});
|
||||
return {
|
||||
color: new Color(color.argb),
|
||||
offset: offsetUnit,
|
||||
};
|
||||
});
|
||||
|
||||
return result;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
public static equals(first: LinearGradient, second: LinearGradient): boolean {
|
||||
if (!first && !second) {
|
||||
return true;
|
||||
} else if (!first || !second) {
|
||||
return false;
|
||||
}
|
||||
public static equals(first: LinearGradient, second: LinearGradient): boolean {
|
||||
if (!first && !second) {
|
||||
return true;
|
||||
} else if (!first || !second) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (first.angle !== second.angle) {
|
||||
return false;
|
||||
}
|
||||
if (first.angle !== second.angle) {
|
||||
return false;
|
||||
}
|
||||
|
||||
if (first.colorStops.length !== second.colorStops.length) {
|
||||
return false;
|
||||
}
|
||||
if (first.colorStops.length !== second.colorStops.length) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for (let i = 0; i < first.colorStops.length; i++) {
|
||||
const firstStop = first.colorStops[i];
|
||||
const secondStop = second.colorStops[i];
|
||||
if (firstStop.offset !== secondStop.offset) {
|
||||
return false;
|
||||
}
|
||||
if (!Color.equals(firstStop.color, secondStop.color)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
for (let i = 0; i < first.colorStops.length; i++) {
|
||||
const firstStop = first.colorStops[i];
|
||||
const secondStop = second.colorStops[i];
|
||||
if (firstStop.offset !== secondStop.offset) {
|
||||
return false;
|
||||
}
|
||||
if (!Color.equals(firstStop.color, secondStop.color)) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -14,28 +14,28 @@ export type Length = 'auto' | dip | LengthDipUnit | LengthPxUnit;
|
||||
export type PercentLength = 'auto' | dip | LengthDipUnit | LengthPxUnit | LengthPercentUnit;
|
||||
|
||||
export namespace Length {
|
||||
export function parse(text: string): Length;
|
||||
export function equals(a: Length, b: Length): boolean;
|
||||
/**
|
||||
* Converts Length unit to device pixels.
|
||||
* @param length The Length to convert.
|
||||
* @param auto Value to use for conversion of "auto". By default is Math.NaN.
|
||||
*/
|
||||
export function toDevicePixels(length: Length, auto?: number): number;
|
||||
export function convertToString(length: Length): string;
|
||||
export function parse(text: string): Length;
|
||||
export function equals(a: Length, b: Length): boolean;
|
||||
/**
|
||||
* Converts Length unit to device pixels.
|
||||
* @param length The Length to convert.
|
||||
* @param auto Value to use for conversion of "auto". By default is Math.NaN.
|
||||
*/
|
||||
export function toDevicePixels(length: Length, auto?: number): number;
|
||||
export function convertToString(length: Length): string;
|
||||
}
|
||||
|
||||
export namespace PercentLength {
|
||||
export function parse(text: string): PercentLength;
|
||||
export function equals(a: PercentLength, b: PercentLength): boolean;
|
||||
/**
|
||||
* Converts PercentLength unit to device pixels.
|
||||
* @param length The PercentLength to convert.
|
||||
* @param auto Value to use for conversion of "auto". By default is Math.NaN.
|
||||
* @param parentAvailableWidth Value to use as base when converting percent unit. By default is Math.NaN.
|
||||
*/
|
||||
export function toDevicePixels(length: PercentLength, auto?: number, parentAvailableWidth?: px): number;
|
||||
export function convertToString(length: PercentLength): string;
|
||||
export function parse(text: string): PercentLength;
|
||||
export function equals(a: PercentLength, b: PercentLength): boolean;
|
||||
/**
|
||||
* Converts PercentLength unit to device pixels.
|
||||
* @param length The PercentLength to convert.
|
||||
* @param auto Value to use for conversion of "auto". By default is Math.NaN.
|
||||
* @param parentAvailableWidth Value to use as base when converting percent unit. By default is Math.NaN.
|
||||
*/
|
||||
export function toDevicePixels(length: PercentLength, auto?: number, parentAvailableWidth?: px): number;
|
||||
export function convertToString(length: PercentLength): string;
|
||||
}
|
||||
|
||||
export const zeroLength: Length;
|
||||
@@ -112,20 +112,20 @@ export type BackgroundRepeat = 'repeat' | 'repeat-x' | 'repeat-y' | 'no-repeat';
|
||||
export type Visibility = 'visible' | 'hidden' | 'collapse';
|
||||
export type HorizontalAlignment = 'left' | 'center' | 'right' | 'stretch';
|
||||
export namespace HorizontalAlignment {
|
||||
export const LEFT: 'left';
|
||||
export const CENTER: 'center';
|
||||
export const RIGHT: 'right';
|
||||
export const STRETCH: 'stretch';
|
||||
export const LEFT: 'left';
|
||||
export const CENTER: 'center';
|
||||
export const RIGHT: 'right';
|
||||
export const STRETCH: 'stretch';
|
||||
}
|
||||
export type VerticalAlignment = 'top' | 'middle' | 'bottom' | 'stretch' | 'text-top' | 'text-bottom' | 'super' | 'sub' | 'baseline';
|
||||
export namespace VerticalAlignment {
|
||||
export const TOP: 'top';
|
||||
export const MIDDLE: 'middle';
|
||||
export const BOTTOM: 'bottom';
|
||||
export const STRETCH: 'stretch';
|
||||
export const TEXTTOP: 'text-top';
|
||||
export const TEXTBOTTOM: 'text-bottom';
|
||||
export const SUPER: 'super';
|
||||
export const SUB: 'sub';
|
||||
export const BASELINE: 'baseline';
|
||||
export const TOP: 'top';
|
||||
export const MIDDLE: 'middle';
|
||||
export const BOTTOM: 'bottom';
|
||||
export const STRETCH: 'stretch';
|
||||
export const TEXTTOP: 'text-top';
|
||||
export const TEXTBOTTOM: 'text-bottom';
|
||||
export const SUPER: 'super';
|
||||
export const SUB: 'sub';
|
||||
export const BASELINE: 'baseline';
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
58
nativescript-core/ui/styling/style-scope.d.ts
vendored
58
nativescript-core/ui/styling/style-scope.d.ts
vendored
@@ -5,44 +5,44 @@ import { RuleSet, Node, SelectorCore, ChangeMap } from '../styling/css-selector'
|
||||
import { KeyframeAnimationInfo } from '../animation/keyframe-animation';
|
||||
|
||||
export class CssState {
|
||||
/**
|
||||
* Re-evaluate the selectors and apply any changes to the underlying view.
|
||||
*/
|
||||
public apply(): void;
|
||||
/**
|
||||
* Re-evaluate the selectors and apply any changes to the underlying view.
|
||||
*/
|
||||
public apply(): void;
|
||||
|
||||
/**
|
||||
* Gets the static selectors that match the view and the dynamic selectors that may potentially match the view.
|
||||
*/
|
||||
public changeMap: ChangeMap<ViewBase>;
|
||||
/**
|
||||
* Gets the static selectors that match the view and the dynamic selectors that may potentially match the view.
|
||||
*/
|
||||
public changeMap: ChangeMap<ViewBase>;
|
||||
|
||||
/**
|
||||
* Checks whether style scope and CSS state selectors are in sync.
|
||||
*/
|
||||
public isSelectorsLatestVersionApplied(): boolean;
|
||||
/**
|
||||
* Checks whether style scope and CSS state selectors are in sync.
|
||||
*/
|
||||
public isSelectorsLatestVersionApplied(): boolean;
|
||||
}
|
||||
|
||||
export class StyleScope {
|
||||
public css: string;
|
||||
public addCss(cssString: string, cssFileName?: string): void;
|
||||
public addCssFile(cssFileName: string): void;
|
||||
public changeCssFile(cssFileName: string): void;
|
||||
public css: string;
|
||||
public addCss(cssString: string, cssFileName?: string): void;
|
||||
public addCssFile(cssFileName: string): void;
|
||||
public changeCssFile(cssFileName: string): void;
|
||||
|
||||
public static createSelectorsFromCss(css: string, cssFileName: string, keyframes: Object): RuleSet[];
|
||||
public static createSelectorsFromImports(tree: SyntaxTree, keyframes: Object): RuleSet[];
|
||||
public ensureSelectors(): number;
|
||||
public static createSelectorsFromCss(css: string, cssFileName: string, keyframes: Object): RuleSet[];
|
||||
public static createSelectorsFromImports(tree: SyntaxTree, keyframes: Object): RuleSet[];
|
||||
public ensureSelectors(): number;
|
||||
|
||||
/**
|
||||
* Increase the application CSS selector version.
|
||||
*/
|
||||
public _increaseApplicationCssSelectorVersion(): void;
|
||||
public isApplicationCssSelectorsLatestVersionApplied(): boolean;
|
||||
public isLocalCssSelectorsLatestVersionApplied(): boolean;
|
||||
/**
|
||||
* Increase the application CSS selector version.
|
||||
*/
|
||||
public _increaseApplicationCssSelectorVersion(): void;
|
||||
public isApplicationCssSelectorsLatestVersionApplied(): boolean;
|
||||
public isLocalCssSelectorsLatestVersionApplied(): boolean;
|
||||
|
||||
public applySelectors(view: ViewBase): void;
|
||||
public query(options: Node): SelectorCore[];
|
||||
public applySelectors(view: ViewBase): void;
|
||||
public query(options: Node): SelectorCore[];
|
||||
|
||||
public getKeyframeAnimationWithName(animationName: string): KeyframeAnimationInfo;
|
||||
public getAnimations(ruleset: RuleSet): KeyframeAnimationInfo[];
|
||||
public getKeyframeAnimationWithName(animationName: string): KeyframeAnimationInfo;
|
||||
public getAnimations(ruleset: RuleSet): KeyframeAnimationInfo[];
|
||||
}
|
||||
|
||||
export function resolveFileNameFromUrl(url: string, appDirectory: string, fileExists: (string) => boolean, importSource?: string): string;
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -13,215 +13,215 @@ import { Trace } from '../../../trace';
|
||||
import { TextAlignment, TextDecoration, TextTransform, WhiteSpace } from '../../text-base';
|
||||
|
||||
export interface CommonLayoutParams {
|
||||
width: number;
|
||||
height: number;
|
||||
width: number;
|
||||
height: number;
|
||||
|
||||
widthPercent: number;
|
||||
heightPercent: number;
|
||||
widthPercent: number;
|
||||
heightPercent: number;
|
||||
|
||||
leftMargin: number;
|
||||
topMargin: number;
|
||||
rightMargin: number;
|
||||
bottomMargin: number;
|
||||
leftMargin: number;
|
||||
topMargin: number;
|
||||
rightMargin: number;
|
||||
bottomMargin: number;
|
||||
|
||||
leftMarginPercent: number;
|
||||
topMarginPercent: number;
|
||||
rightMarginPercent: number;
|
||||
bottomMarginPercent: number;
|
||||
leftMarginPercent: number;
|
||||
topMarginPercent: number;
|
||||
rightMarginPercent: number;
|
||||
bottomMarginPercent: number;
|
||||
|
||||
horizontalAlignment: HorizontalAlignment;
|
||||
verticalAlignment: VerticalAlignment;
|
||||
horizontalAlignment: HorizontalAlignment;
|
||||
verticalAlignment: VerticalAlignment;
|
||||
}
|
||||
|
||||
export class Style extends Observable implements StyleDefinition {
|
||||
private unscopedCssVariables = new Map<string, string>();
|
||||
private scopedCssVariables = new Map<string, string>();
|
||||
private unscopedCssVariables = new Map<string, string>();
|
||||
private scopedCssVariables = new Map<string, string>();
|
||||
|
||||
constructor(ownerView: ViewBase | WeakRef<ViewBase>) {
|
||||
super();
|
||||
constructor(ownerView: ViewBase | WeakRef<ViewBase>) {
|
||||
super();
|
||||
|
||||
// HACK: Could not find better way for cross platform WeakRef type checking.
|
||||
if (ownerView.constructor.toString().indexOf('[native code]') !== -1) {
|
||||
this.viewRef = <WeakRef<ViewBase>>ownerView;
|
||||
} else {
|
||||
this.viewRef = new WeakRef(<ViewBase>ownerView);
|
||||
}
|
||||
}
|
||||
// HACK: Could not find better way for cross platform WeakRef type checking.
|
||||
if (ownerView.constructor.toString().indexOf('[native code]') !== -1) {
|
||||
this.viewRef = <WeakRef<ViewBase>>ownerView;
|
||||
} else {
|
||||
this.viewRef = new WeakRef(<ViewBase>ownerView);
|
||||
}
|
||||
}
|
||||
|
||||
public setScopedCssVariable(varName: string, value: string): void {
|
||||
this.scopedCssVariables.set(varName, value);
|
||||
}
|
||||
public setScopedCssVariable(varName: string, value: string): void {
|
||||
this.scopedCssVariables.set(varName, value);
|
||||
}
|
||||
|
||||
public setUnscopedCssVariable(varName: string, value: string): void {
|
||||
this.unscopedCssVariables.set(varName, value);
|
||||
}
|
||||
public setUnscopedCssVariable(varName: string, value: string): void {
|
||||
this.unscopedCssVariables.set(varName, value);
|
||||
}
|
||||
|
||||
public getCssVariable(varName: string): string | null {
|
||||
const view = this.view;
|
||||
if (!view) {
|
||||
return null;
|
||||
}
|
||||
public getCssVariable(varName: string): string | null {
|
||||
const view = this.view;
|
||||
if (!view) {
|
||||
return null;
|
||||
}
|
||||
|
||||
if (this.unscopedCssVariables.has(varName)) {
|
||||
return this.unscopedCssVariables.get(varName);
|
||||
}
|
||||
if (this.unscopedCssVariables.has(varName)) {
|
||||
return this.unscopedCssVariables.get(varName);
|
||||
}
|
||||
|
||||
if (this.scopedCssVariables.has(varName)) {
|
||||
return this.scopedCssVariables.get(varName);
|
||||
}
|
||||
if (this.scopedCssVariables.has(varName)) {
|
||||
return this.scopedCssVariables.get(varName);
|
||||
}
|
||||
|
||||
if (!view.parent || !view.parent.style) {
|
||||
return null;
|
||||
}
|
||||
if (!view.parent || !view.parent.style) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return view.parent.style.getCssVariable(varName);
|
||||
}
|
||||
return view.parent.style.getCssVariable(varName);
|
||||
}
|
||||
|
||||
public resetScopedCssVariables() {
|
||||
this.scopedCssVariables.clear();
|
||||
}
|
||||
public resetScopedCssVariables() {
|
||||
this.scopedCssVariables.clear();
|
||||
}
|
||||
|
||||
public resetUnscopedCssVariables() {
|
||||
this.unscopedCssVariables.clear();
|
||||
}
|
||||
public resetUnscopedCssVariables() {
|
||||
this.unscopedCssVariables.clear();
|
||||
}
|
||||
|
||||
toString() {
|
||||
const view = this.viewRef.get();
|
||||
if (!view) {
|
||||
Trace.write(`toString() of Style cannot execute correctly because ".viewRef" is cleared`, Trace.categories.Animation, Trace.messageType.warn);
|
||||
toString() {
|
||||
const view = this.viewRef.get();
|
||||
if (!view) {
|
||||
Trace.write(`toString() of Style cannot execute correctly because ".viewRef" is cleared`, Trace.categories.Animation, Trace.messageType.warn);
|
||||
|
||||
return '';
|
||||
}
|
||||
return '';
|
||||
}
|
||||
|
||||
return `${view}.style`;
|
||||
}
|
||||
return `${view}.style`;
|
||||
}
|
||||
|
||||
public fontInternal: Font;
|
||||
public backgroundInternal: Background;
|
||||
public fontInternal: Font;
|
||||
public backgroundInternal: Background;
|
||||
|
||||
public rotate: number;
|
||||
public rotateX: number;
|
||||
public rotateY: number;
|
||||
public perspective: number;
|
||||
public rotate: number;
|
||||
public rotateX: number;
|
||||
public rotateY: number;
|
||||
public perspective: number;
|
||||
|
||||
public scaleX: number;
|
||||
public scaleY: number;
|
||||
public translateX: dip;
|
||||
public translateY: dip;
|
||||
public scaleX: number;
|
||||
public scaleY: number;
|
||||
public translateX: dip;
|
||||
public translateY: dip;
|
||||
|
||||
public clipPath: string;
|
||||
public color: Color;
|
||||
public tintColor: Color;
|
||||
public placeholderColor: Color;
|
||||
public clipPath: string;
|
||||
public color: Color;
|
||||
public tintColor: Color;
|
||||
public placeholderColor: Color;
|
||||
|
||||
public background: string;
|
||||
public backgroundColor: Color;
|
||||
public backgroundImage: string | LinearGradient;
|
||||
public backgroundRepeat: BackgroundRepeat;
|
||||
public backgroundSize: string;
|
||||
public backgroundPosition: string;
|
||||
public background: string;
|
||||
public backgroundColor: Color;
|
||||
public backgroundImage: string | LinearGradient;
|
||||
public backgroundRepeat: BackgroundRepeat;
|
||||
public backgroundSize: string;
|
||||
public backgroundPosition: string;
|
||||
|
||||
public borderColor: string | Color;
|
||||
public borderTopColor: Color;
|
||||
public borderRightColor: Color;
|
||||
public borderBottomColor: Color;
|
||||
public borderLeftColor: Color;
|
||||
public borderWidth: string | Length;
|
||||
public borderTopWidth: Length;
|
||||
public borderRightWidth: Length;
|
||||
public borderBottomWidth: Length;
|
||||
public borderLeftWidth: Length;
|
||||
public borderRadius: string | Length;
|
||||
public borderTopLeftRadius: Length;
|
||||
public borderTopRightRadius: Length;
|
||||
public borderBottomRightRadius: Length;
|
||||
public borderBottomLeftRadius: Length;
|
||||
public borderColor: string | Color;
|
||||
public borderTopColor: Color;
|
||||
public borderRightColor: Color;
|
||||
public borderBottomColor: Color;
|
||||
public borderLeftColor: Color;
|
||||
public borderWidth: string | Length;
|
||||
public borderTopWidth: Length;
|
||||
public borderRightWidth: Length;
|
||||
public borderBottomWidth: Length;
|
||||
public borderLeftWidth: Length;
|
||||
public borderRadius: string | Length;
|
||||
public borderTopLeftRadius: Length;
|
||||
public borderTopRightRadius: Length;
|
||||
public borderBottomRightRadius: Length;
|
||||
public borderBottomLeftRadius: Length;
|
||||
|
||||
public fontSize: number;
|
||||
public fontFamily: string;
|
||||
public fontStyle: FontStyle;
|
||||
public fontWeight: FontWeight;
|
||||
public font: string;
|
||||
public fontSize: number;
|
||||
public fontFamily: string;
|
||||
public fontStyle: FontStyle;
|
||||
public fontWeight: FontWeight;
|
||||
public font: string;
|
||||
|
||||
public androidElevation: number;
|
||||
public androidDynamicElevationOffset: number;
|
||||
public zIndex: number;
|
||||
public opacity: number;
|
||||
public visibility: Visibility;
|
||||
public androidElevation: number;
|
||||
public androidDynamicElevationOffset: number;
|
||||
public zIndex: number;
|
||||
public opacity: number;
|
||||
public visibility: Visibility;
|
||||
|
||||
public letterSpacing: number;
|
||||
public lineHeight: number;
|
||||
public textAlignment: TextAlignment;
|
||||
public textDecoration: TextDecoration;
|
||||
public textTransform: TextTransform;
|
||||
public whiteSpace: WhiteSpace;
|
||||
public letterSpacing: number;
|
||||
public lineHeight: number;
|
||||
public textAlignment: TextAlignment;
|
||||
public textDecoration: TextDecoration;
|
||||
public textTransform: TextTransform;
|
||||
public whiteSpace: WhiteSpace;
|
||||
|
||||
public minWidth: Length;
|
||||
public minHeight: Length;
|
||||
public width: PercentLength;
|
||||
public height: PercentLength;
|
||||
public margin: string | PercentLength;
|
||||
public marginLeft: PercentLength;
|
||||
public marginTop: PercentLength;
|
||||
public marginRight: PercentLength;
|
||||
public marginBottom: PercentLength;
|
||||
public padding: string | Length;
|
||||
public paddingLeft: Length;
|
||||
public paddingTop: Length;
|
||||
public paddingRight: Length;
|
||||
public paddingBottom: Length;
|
||||
public horizontalAlignment: HorizontalAlignment;
|
||||
public verticalAlignment: VerticalAlignment;
|
||||
public minWidth: Length;
|
||||
public minHeight: Length;
|
||||
public width: PercentLength;
|
||||
public height: PercentLength;
|
||||
public margin: string | PercentLength;
|
||||
public marginLeft: PercentLength;
|
||||
public marginTop: PercentLength;
|
||||
public marginRight: PercentLength;
|
||||
public marginBottom: PercentLength;
|
||||
public padding: string | Length;
|
||||
public paddingLeft: Length;
|
||||
public paddingTop: Length;
|
||||
public paddingRight: Length;
|
||||
public paddingBottom: Length;
|
||||
public horizontalAlignment: HorizontalAlignment;
|
||||
public verticalAlignment: VerticalAlignment;
|
||||
|
||||
// TabView-specific props
|
||||
public tabTextFontSize: number;
|
||||
public tabTextColor: Color;
|
||||
public tabBackgroundColor: Color;
|
||||
public selectedTabTextColor: Color;
|
||||
public androidSelectedTabHighlightColor: Color;
|
||||
// TabView-specific props
|
||||
public tabTextFontSize: number;
|
||||
public tabTextColor: Color;
|
||||
public tabBackgroundColor: Color;
|
||||
public selectedTabTextColor: Color;
|
||||
public androidSelectedTabHighlightColor: Color;
|
||||
|
||||
// ListView-specific props
|
||||
public separatorColor: Color;
|
||||
// ListView-specific props
|
||||
public separatorColor: Color;
|
||||
|
||||
//SegmentedBar-specific props
|
||||
public selectedBackgroundColor: Color;
|
||||
//SegmentedBar-specific props
|
||||
public selectedBackgroundColor: Color;
|
||||
|
||||
// Page-specific props
|
||||
public statusBarStyle: 'light' | 'dark';
|
||||
public androidStatusBarBackground: Color;
|
||||
// Page-specific props
|
||||
public statusBarStyle: 'light' | 'dark';
|
||||
public androidStatusBarBackground: Color;
|
||||
|
||||
// ActionBar-specific props
|
||||
public androidContentInset: string | Length;
|
||||
public androidContentInsetLeft: Length;
|
||||
public androidContentInsetRight: Length;
|
||||
// ActionBar-specific props
|
||||
public androidContentInset: string | Length;
|
||||
public androidContentInsetLeft: Length;
|
||||
public androidContentInsetRight: Length;
|
||||
|
||||
//flexbox layout properties
|
||||
public flexDirection: FlexDirection;
|
||||
public flexWrap: FlexWrap;
|
||||
public justifyContent: JustifyContent;
|
||||
public alignItems: AlignItems;
|
||||
public alignContent: AlignContent;
|
||||
public order: Order;
|
||||
public flexGrow: FlexGrow;
|
||||
public flexShrink: FlexShrink;
|
||||
public flexWrapBefore: FlexWrapBefore;
|
||||
public alignSelf: AlignSelf;
|
||||
//flexbox layout properties
|
||||
public flexDirection: FlexDirection;
|
||||
public flexWrap: FlexWrap;
|
||||
public justifyContent: JustifyContent;
|
||||
public alignItems: AlignItems;
|
||||
public alignContent: AlignContent;
|
||||
public order: Order;
|
||||
public flexGrow: FlexGrow;
|
||||
public flexShrink: FlexShrink;
|
||||
public flexWrapBefore: FlexWrapBefore;
|
||||
public alignSelf: AlignSelf;
|
||||
|
||||
public PropertyBag: {
|
||||
new (): { [property: string]: string };
|
||||
prototype: { [property: string]: string };
|
||||
};
|
||||
public PropertyBag: {
|
||||
new (): { [property: string]: string };
|
||||
prototype: { [property: string]: string };
|
||||
};
|
||||
|
||||
public viewRef: WeakRef<ViewBase>;
|
||||
public viewRef: WeakRef<ViewBase>;
|
||||
|
||||
public get view(): ViewBase {
|
||||
if (this.viewRef) {
|
||||
return this.viewRef.get();
|
||||
}
|
||||
public get view(): ViewBase {
|
||||
if (this.viewRef) {
|
||||
return this.viewRef.get();
|
||||
}
|
||||
|
||||
return undefined;
|
||||
}
|
||||
return undefined;
|
||||
}
|
||||
}
|
||||
Style.prototype.PropertyBag = class {
|
||||
[property: string]: string;
|
||||
[property: string]: string;
|
||||
};
|
||||
|
||||
Reference in New Issue
Block a user