This commit is contained in:
Hristo Hristov
2016-11-28 13:34:15 +02:00
parent 645f428f59
commit d795ee94e4
19 changed files with 1053 additions and 1196 deletions

View File

@ -11,6 +11,7 @@ import { ViewBase, getEventOrGestureName } from "./view-base";
import { propagateInheritedProperties, clearInheritedProperties, Property, InheritedProperty, CssProperty, ShorthandProperty, InheritedCssProperty } from "./properties";
import { observe, fromString as gestureFromString, GesturesObserver, GestureTypes, GestureEventData } from "ui/gestures";
import { isIOS } from "platform";
import { Font } from "ui/styling/font";
// TODO: Remove this and start using string as source (for android).
import { fromFileOrResource, fromBase64, fromUrl } from "image-source";
@ -2171,3 +2172,134 @@ opacityProperty.register(Style);
export const colorProperty = new InheritedCssProperty<Style, Color>({ name: "color", cssName: "color", equalityComparer: Color.equals, valueConverter: (v: string) => new Color(v) });
colorProperty.register(Style);
export let fontInternalProperty = new CssProperty<Style, Font>({ name: "fontInternal", cssName: "_fontInternal", defaultValue: Font.default });
export let fontFamilyProperty = new InheritedCssProperty<Style, string>({
name: "fontFamily", cssName: "font-family", valueChanged: (target, newValue) => {
let currentFont = target.fontInternal;
if (currentFont.fontFamily !== newValue) {
target.fontInternal = currentFont.withFontFamily(newValue);
}
}
});
fontFamilyProperty.register(Style);
export let fontSizeProperty = new InheritedCssProperty<Style, number>({
name: "fontSize", cssName: "font-size", valueChanged: (target, newValue) => {
let currentFont = target.fontInternal;
if (currentFont.fontSize !== newValue) {
target.fontInternal = currentFont.withFontSize(newValue);
}
},
valueConverter: (v) => parseFloat(v)
});
fontSizeProperty.register(Style);
export let fontStyleProperty = new InheritedCssProperty<Style, "normal" | "italic">({
name: "fontStyle", cssName: "font-style", defaultValue: "normal", valueChanged: (target, newValue) => {
if (!(newValue === "normal" || newValue === "italic")) {
throw new Error(`font-style should be 'normal' or 'italic'. value: ${newValue}`)
}
let currentFont = target.fontInternal;
if (currentFont.fontStyle !== newValue) {
target.fontInternal = currentFont.withFontStyle(newValue);
}
}
});
fontStyleProperty.register(Style);
export let fontWeightProperty = new InheritedCssProperty<Style, "100" | "200" | "300" | "normal" | "400" | "500" | "600" | "bold" | "700" | "800" | "900">({
name: "fontWeight", cssName: "font-weight", defaultValue: "normal", valueChanged: (target, newValue) => {
if (!newValue) {
console.trace();
}
// TODO: Console.log errors or throw error?
if (!(newValue === "normal" || newValue === "bold"
|| newValue === "100" || newValue === "200" || newValue === "300"
|| newValue === "400" || newValue === "500" || newValue === "600"
|| newValue === "700" || newValue === "800" || newValue === "900")) {
throw new Error(`Invalid font-weight value: ${newValue}`);
}
let currentFont = target.fontInternal;
if (currentFont.fontWeight !== newValue) {
target.fontInternal = currentFont.withFontWeight(newValue);
}
}
});
fontWeightProperty.register(Style);
export let fontProperty = new ShorthandProperty<Style>({
name: "font", cssName: "font",
getter: function (this: Style) {
return `${this.fontStyle} ${this.fontWeight} ${this.fontSize} ${this.fontFamily}`;
},
converter: function (value: string) {
return parseFont(value);
}
})
fontProperty.register(Style);
function parseFont(font: string): [CssProperty<any, any>, any][] {
let fontSize: number;
let fontFamily: string;
let fontStyle: "normal" | "italic" = "normal";
let fontWeight: string = "normal";
let elements = font.split(/\s+/);
let element: string;
while (element = elements.shift()) {
switch (element) {
case "normal":
break;
// TODO: add support for oblique font style.
case "italic":
// case "oblique":
fontStyle = "italic";
break;
case "100":
case "200":
case "300":
case "normal":
case "400":
case "500":
case "600":
case "bold":
case "700":
case "800":
case "900":
fontWeight = element;
break;
default:
if (!fontSize) {
let parts = element.split("/");
// TODO: add support for px support.
fontSize = parseFloat(parts[0]);
// TODO: add support for lineHeight.
// if (parts.length > 1) {
// lineHeight = parts[1];
// }
break;
}
fontFamily = element;
// if (elements.length) {
// fontFamily += " " + elements.join(" ");
// }
}
}
return [
[fontStyleProperty, fontStyle],
[fontWeightProperty, fontWeight],
[fontSizeProperty, fontSize],
[fontFamilyProperty, fontFamily]
]
}

View File

@ -5,10 +5,11 @@ declare module "ui/core/view" {
import { Color } from "color";
import { Animation, AnimationDefinition, AnimationPromise } from "ui/animation";
import { KeyframeAnimation } from "ui/animation/keyframe-animation";
import { Property, CssProperty, InheritedCssProperty } from "ui/core/properties";
import { Property, CssProperty, InheritedCssProperty, ShorthandProperty } from "ui/core/properties";
import { BindingOptions } from "ui/core/bindable";
import { ViewBase } from "ui/core/view-base";
import { Background } from "ui/styling/background";
import { Font } from "ui/styling/font";
/**
* Gets a child view by id.
@ -771,5 +772,11 @@ declare module "ui/core/view" {
export const verticalAlignmentProperty: CssProperty<Style, string>;
export const horizontalAlignmentProperty: CssProperty<Style, string>;
export const fontSizeProperty: InheritedCssProperty<Style, number>;
export const fontFamilyProperty: InheritedCssProperty<Style, string>;
export const fontStyleProperty: InheritedCssProperty<Style, string>;
export const fontWeightProperty: InheritedCssProperty<Style, string>;
export const backgroundInternalProperty: CssProperty<Style, Background>;
export const fontInternalProperty: InheritedCssProperty<Style, Font>;
}

File diff suppressed because it is too large Load Diff

View File

@ -350,7 +350,7 @@ declare module "ui/frame" {
* Gets or sets the visibility of navigationBar.
* Use NavBarVisibility enumeration - auto, never, always
*/
navBarVisibility: string;
navBarVisibility: "auto" | "never" | "always";
//@private
_disableNavBarAnimation: boolean;

View File

@ -2,7 +2,6 @@
import { FrameBase } from "./frame-common";
import { Page } from "ui/page";
import { View } from "ui/core/view";
import { NavigationBarVisibility, AnimationCurve } from "ui/enums";
import * as transitionModule from "ui/transition";
import * as trace from "trace";
@ -206,13 +205,13 @@ export class Frame extends FrameBase {
public _getNavBarVisible(page: Page): boolean {
switch (this._ios.navBarVisibility) {
case NavigationBarVisibility.always:
case "always":
return true;
case NavigationBarVisibility.never:
case "never":
return false;
case NavigationBarVisibility.auto:
case "auto":
let newValue: boolean;
if (page && page.actionBarHidden !== undefined) {
@ -637,26 +636,30 @@ function _getNativeTransition(navigationTransition: NavigationTransition, push:
export function _getNativeCurve(transition: NavigationTransition): UIViewAnimationCurve {
if (transition.curve) {
switch (transition.curve) {
case AnimationCurve.easeIn:
case "easeIn":
if (trace.enabled) {
trace.write("Transition curve resolved to UIViewAnimationCurve.EaseIn.", trace.categories.Transition);
}
return UIViewAnimationCurve.EaseIn;
case AnimationCurve.easeOut:
case "easeOut":
if (trace.enabled) {
trace.write("Transition curve resolved to UIViewAnimationCurve.EaseOut.", trace.categories.Transition);
}
return UIViewAnimationCurve.EaseOut;
case AnimationCurve.easeInOut:
case "easeInOut":
if (trace.enabled) {
trace.write("Transition curve resolved to UIViewAnimationCurve.EaseInOut.", trace.categories.Transition);
}
return UIViewAnimationCurve.EaseInOut;
case AnimationCurve.linear:
case "linear":
if (trace.enabled) {
trace.write("Transition curve resolved to UIViewAnimationCurve.Linear.", trace.categories.Transition);
}
return UIViewAnimationCurve.Linear;
default:
if (trace.enabled) {
trace.write("Transition curve resolved to original: " + transition.curve, trace.categories.Transition);
@ -673,7 +676,7 @@ class iOSFrame implements iOSFrameDefinition {
/* tslint:enable */
private _controller: UINavigationControllerImpl;
private _showNavigationBar: boolean;
private _navBarVisibility: string;
private _navBarVisibility: "auto" | "never" | "always" = "auto";
private _frame: Frame;
// TabView uses this flag to disable animation while showing/hiding the navigation bar because of the "< More" bar.
@ -684,8 +687,6 @@ class iOSFrame implements iOSFrameDefinition {
this._frame = frame;
this._controller = UINavigationControllerImpl.initWithOwner(new WeakRef(frame));
this._controller.automaticallyAdjustsScrollViewInsets = false;
//this.showNavigationBar = false;
this._navBarVisibility = NavigationBarVisibility.auto;
}
public get controller() {
@ -708,10 +709,10 @@ class iOSFrame implements iOSFrameDefinition {
}
}
public get navBarVisibility(): string {
public get navBarVisibility(): "auto" | "never" | "always" {
return this._navBarVisibility;
}
public set navBarVisibility(value: string) {
public set navBarVisibility(value: "auto" | "never" | "always") {
this._navBarVisibility = value;
}
}

View File

@ -8,12 +8,6 @@ import types = require("utils/types");
import getter = utils.ios.getter;
export * from "./gestures-common";
// import common = require("./gestures-common");
// import definition = require("ui/gestures");
// import view = require("ui/core/view");
// import observable = require("data/observable");
// import trace = require("trace");
export function observe(target: View, type: GestureTypes, callback: (args: GestureEventData) => void, context?: any): GesturesObserver {
let observer = new GesturesObserver(target, callback, context);

View File

@ -123,5 +123,5 @@ isLoadingProperty.register(ImageBase);
export const stretchProperty = new Property<ImageBase, "none" | "aspectFill" | "aspectFit" | "fill">({ name: "stretch", defaultValue: "aspectFit", affectsLayout: isIOS })
stretchProperty.register(ImageBase);
export const tintColorProperty = new CssProperty<Style, Color>({ name: "tintColor", cssName: "tint-color", equalityComparer: Color.equals, valueConverter: (value) => new Color(value) });
export const tintColorProperty = new InheritedCssProperty<Style, Color>({ name: "tintColor", cssName: "tint-color", equalityComparer: Color.equals, valueConverter: (value) => new Color(value) });
tintColorProperty.register(Style);

View File

@ -3,7 +3,7 @@
*/
declare module "ui/image" {
import { View } from "ui/core/view";
import { Property, CssProperty } from "ui/core/properties";
import { Property, InheritedCssProperty } from "ui/core/properties";
import { Color } from "color";
import { ImageSource } from "image-source";
import { Style } from "ui/styling/style";
@ -61,5 +61,5 @@ declare module "ui/image" {
export const isLoadingProperty: Property<Image, string>;
export const loadMode: Property<Image, "sync" | "async">;
export const stretchProperty: Property<Image, "none" | "aspectFill" | "aspectFit" | "fill">;
export const tintColorProperty: CssProperty<Style, Color>;
export const tintColorProperty: InheritedCssProperty<Style, Color>;
}

View File

@ -3,7 +3,7 @@ import { TextBase } from "ui/text-base";
export * from "ui/text-base";
export class LabelBase extends TextBase implements LabelDefinition {
export class Label extends TextBase implements LabelDefinition {
private _android: android.widget.TextView;
get textWrap(): boolean {

View File

@ -1,6 +1,11 @@
import { Label as LabelDefinition } from "ui/label";
import { TextBase, View, whiteSpaceProperty, layout } from "ui/text-base";
import { Background } from "ui/styling/background";
import { TextBase, whiteSpaceProperty } from "ui/text-base";
import {
View, layout, backgroundInternalProperty,
borderTopWidthProperty, borderRightWidthProperty, borderBottomWidthProperty, borderLeftWidthProperty,
paddingTopProperty, paddingRightProperty, paddingBottomProperty, paddingLeftProperty
} from "ui/core/view";
import { Background, ios } from "ui/styling/background";
export * from "ui/text-base";
@ -11,8 +16,8 @@ enum FixedSize {
BOTH = 3
}
export class LabelBase extends TextBase implements LabelDefinition {
private _ios: UILabel;
export class Label extends TextBase implements LabelDefinition {
private _ios: TNSLabel;
private _fixedSize: FixedSize;
constructor() {
@ -22,11 +27,11 @@ export class LabelBase extends TextBase implements LabelDefinition {
this._ios.userInteractionEnabled = true;
}
get ios(): UILabel {
get ios(): TNSLabel {
return this._ios;
}
get _nativeView(): UILabel {
get _nativeView(): TNSLabel {
return this._ios;
}
@ -53,13 +58,13 @@ export class LabelBase extends TextBase implements LabelDefinition {
}
public onMeasure(widthMeasureSpec: number, heightMeasureSpec: number): void {
var nativeView = this._nativeView;
let nativeView = this._nativeView;
if (nativeView) {
var width = layout.getMeasureSpecSize(widthMeasureSpec);
var widthMode = layout.getMeasureSpecMode(widthMeasureSpec);
let width = layout.getMeasureSpecSize(widthMeasureSpec);
let widthMode = layout.getMeasureSpecMode(widthMeasureSpec);
var height = layout.getMeasureSpecSize(heightMeasureSpec);
var heightMode = layout.getMeasureSpecMode(heightMeasureSpec);
let height = layout.getMeasureSpecSize(heightMeasureSpec);
let heightMode = layout.getMeasureSpecMode(heightMeasureSpec);
if (widthMode === layout.UNSPECIFIED) {
width = Number.POSITIVE_INFINITY;
@ -72,30 +77,30 @@ export class LabelBase extends TextBase implements LabelDefinition {
this._fixedSize = (widthMode === layout.EXACTLY ? FixedSize.WIDTH : FixedSize.NONE)
| (heightMode === layout.EXACTLY ? FixedSize.HEIGHT : FixedSize.NONE);
var nativeSize = nativeView.sizeThatFits(CGSizeMake(width, height));
var labelWidth = nativeSize.width;
let nativeSize = nativeView.sizeThatFits(CGSizeMake(width, height));
let labelWidth = nativeSize.width;
if (!this.textWrap && this.style.whiteSpace !== "nowrap") {
labelWidth = Math.min(labelWidth, width);
}
let style = this.sltye;
var measureWidth = Math.max(labelWidth, style.effectiveMinWidth);
var measureHeight = Math.max(nativeSize.height, style.effectiveMinHeight);
let style = this.style;
let measureWidth = Math.max(labelWidth, style.effectiveMinWidth);
let measureHeight = Math.max(nativeSize.height, style.effectiveMinHeight);
var widthAndState = View.resolveSizeAndState(measureWidth, width, widthMode, 0);
var heightAndState = View.resolveSizeAndState(measureHeight, height, heightMode, 0);
let widthAndState = View.resolveSizeAndState(measureWidth, width, widthMode, 0);
let heightAndState = View.resolveSizeAndState(measureHeight, height, heightMode, 0);
this.setMeasuredDimension(widthAndState, heightAndState);
}
}
get [whiteSpaceProperty.native](): string {
return WhiteSpace.normal;
get [whiteSpaceProperty.native](): "nowrap" | "normal" {
return "normal";
}
set [whiteSpaceProperty.native](value: string) {
let nativeView = this.nativeView;
if (value === WhiteSpace.normal) {
if (value === "normal") {
nativeView.lineBreakMode = NSLineBreakMode.ByWordWrapping;
nativeView.numberOfLines = 0;
}
@ -104,204 +109,138 @@ export class LabelBase extends TextBase implements LabelDefinition {
nativeView.numberOfLines = 1;
}
}
}
let zeroInsets = UIEdgeInsetsZero;
export class LabelStyler implements style.Styler {
//Background methods
private static setBackgroundInternalProperty(view: View, newValue: any) {
var uiLabel: UILabel = <UILabel>view._nativeView;
if (uiLabel && uiLabel.layer) {
var flipImage = true;
ensureBackground();
var uiColor = <UIColor>background.ios.createBackgroundUIColor(view, flipImage);
var cgColor = uiColor ? uiColor.CGColor : null;
uiLabel.layer.backgroundColor = cgColor;
}
}
private static resetBackgroundInternalProperty(view: View, nativeValue: any) {
var uiLabel: UILabel = <UILabel>view._nativeView;
if (uiLabel && uiLabel.layer) {
var uiColor = <UIColor>nativeValue;
var cgColor = uiColor ? uiColor.CGColor : null;
uiLabel.layer.backgroundColor = cgColor;
}
}
private static getNativeBackgroundInternalValue(view: View): any {
var uiLabel: UILabel = <UILabel>view._nativeView;
if (uiLabel && uiLabel.layer && uiLabel.layer.backgroundColor) {
return UIColor.colorWithCGColor(uiLabel.layer.backgroundColor);
get [backgroundInternalProperty.native](): UIColor {
let nativeView = this._nativeView;
if (nativeView.layer && nativeView.layer.backgroundColor) {
return UIColor.colorWithCGColor(nativeView.layer.backgroundColor);
}
return undefined;
}
set [backgroundInternalProperty.native](value: UIColor | Background) {
let nativeView = this._nativeView;
private static setBorderTopWidthProperty(view: View, newValue: number) {
LabelStyler.setNativeBorderTopWidth(view, newValue);
}
private static resetBorderTopWidthProperty(view: View, nativeValue: number) {
LabelStyler.setNativeBorderTopWidth(view, nativeValue);
}
private static setNativeBorderTopWidth(view: View, newValue: number) {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
nativeView.borderThickness = {
top: newValue,
right: nativeView.borderThickness.right,
bottom: nativeView.borderThickness.bottom,
left: nativeView.borderThickness.left
};
let cgColor = null;
if (value instanceof UIColor) {
cgColor = value.CGColor;
} else {
let uiColor = <UIColor>ios.createBackgroundUIColor(this, true);
cgColor = uiColor ? uiColor.CGColor : null;
}
nativeView.layer.backgroundColor = cgColor;
}
private static getBorderTopWidthProperty(view: View): number {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
return nativeView.borderThickness.top;
}
get [borderTopWidthProperty.native](): number {
return 0;
}
private static setBorderRightWidthProperty(view: View, newValue: number) {
LabelStyler.setNativeBorderRightWidth(view, newValue);
set [borderTopWidthProperty.native](value: number) {
let nativeView = this._nativeView;
let border = nativeView.borderThickness;
nativeView.borderThickness = {
top: value,
right: border.right,
bottom: border.bottom,
left: border.left
};
}
private static resetBorderRightWidthProperty(view: View, nativeValue: number) {
LabelStyler.setNativeBorderRightWidth(view, nativeValue);
}
private static setNativeBorderRightWidth(view: View, newValue: number) {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
nativeView.borderThickness = {
top: nativeView.borderThickness.top,
right: newValue,
bottom: nativeView.borderThickness.bottom,
left: nativeView.borderThickness.left
};
}
}
private static getBorderRightWidthProperty(view: View): number {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
return nativeView.borderThickness.right;
}
get [borderRightWidthProperty.native](): number {
return 0;
}
private static setBorderBottomWidthProperty(view: View, newValue: number) {
LabelStyler.setNativeBorderBottomWidth(view, newValue);
set [borderRightWidthProperty.native](value: number) {
let nativeView = this._nativeView;
let border = nativeView.borderThickness;
nativeView.borderThickness = {
top: border.top,
right: value,
bottom: border.bottom,
left: border.left
};
}
private static resetBorderBottomWidthProperty(view: View, nativeValue: number) {
LabelStyler.setNativeBorderBottomWidth(view, nativeValue);
}
private static setNativeBorderBottomWidth(view: View, newValue: number) {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
nativeView.borderThickness = {
top: nativeView.borderThickness.top,
right: nativeView.borderThickness.right,
bottom: newValue,
left: nativeView.borderThickness.left
};
}
}
private static getBorderBottomWidthProperty(view: View): number {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
return nativeView.borderThickness.bottom;
}
get [borderBottomWidthProperty.native](): number {
return 0;
}
private static setBorderLeftWidthProperty(view: View, newValue: number) {
LabelStyler.setNativeBorderLeftWidth(view, newValue);
set [borderBottomWidthProperty.native](value: number) {
let nativeView = this._nativeView;
let border = nativeView.borderThickness;
nativeView.borderThickness = {
top: border.top,
right: border.right,
bottom: value,
left: border.left
};
}
private static resetBorderLeftWidthProperty(view: View, nativeValue: number) {
LabelStyler.setNativeBorderLeftWidth(view, nativeValue);
}
private static setNativeBorderLeftWidth(view: View, newValue: number) {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
nativeView.borderThickness = {
top: nativeView.borderThickness.top,
right: nativeView.borderThickness.right,
bottom: nativeView.borderThickness.bottom,
left: newValue
};
}
}
private static getBorderLeftWidthProperty(view: View): number {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
return nativeView.borderThickness.left;
}
get [borderLeftWidthProperty.native](): number {
return 0;
}
private static setPaddingProperty(view: View, newValue: UIEdgeInsets) {
LabelStyler.setNativePadding(view, newValue);
set [borderLeftWidthProperty.native](value: number) {
let nativeView = this._nativeView;
let border = nativeView.borderThickness;
nativeView.borderThickness = {
top: border.top,
right: border.right,
bottom: border.bottom,
left: value
};
}
private static resetPaddingProperty(view: View, nativeValue: UIEdgeInsets) {
LabelStyler.setNativePadding(view, nativeValue);
get [paddingTopProperty.native](): number {
return 0;
}
set [paddingTopProperty.native](value: number) {
let nativeView = this._nativeView;
let padding = nativeView.padding;
nativeView.padding = {
top: value,
right: padding.right,
bottom: padding.bottom,
left: padding.left
};
}
private static setNativePadding(view: View, padding: UIEdgeInsets) {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
nativeView.padding = { top: padding.top, left: padding.left, bottom: padding.bottom, right: padding.right };
}
get [paddingRightProperty.native](): number {
return 0;
}
set [paddingRightProperty.native](value: number) {
let nativeView = this._nativeView;
let padding = nativeView.padding;
nativeView.padding = {
top: padding.top,
right: value,
bottom: padding.bottom,
left: padding.left
};
}
private static getPaddingProperty(view: View): UIEdgeInsets {
let nativeView = <UIView>view._nativeView;
if (nativeView instanceof TNSLabel) {
return nativeView.padding;
}
return zeroInsets;
get [paddingBottomProperty.native](): number {
return 0;
}
set [paddingBottomProperty.native](value: number) {
let nativeView = this._nativeView;
let padding = nativeView.padding;
nativeView.padding = {
top: padding.top,
right: padding.right,
bottom: value,
left: padding.left
};
}
public static registerHandlers() {
style.registerHandler(style.backgroundInternalProperty, new style.StylePropertyChangedHandler(
LabelStyler.setBackgroundInternalProperty,
LabelStyler.resetBackgroundInternalProperty,
LabelStyler.getNativeBackgroundInternalValue), "Label");
style.registerHandler(style.borderTopWidthProperty, new style.StylePropertyChangedHandler(
LabelStyler.setBorderTopWidthProperty,
LabelStyler.resetBorderTopWidthProperty,
LabelStyler.getBorderTopWidthProperty), "Label");
style.registerHandler(style.borderRightWidthProperty, new style.StylePropertyChangedHandler(
LabelStyler.setBorderRightWidthProperty,
LabelStyler.resetBorderRightWidthProperty,
LabelStyler.getBorderRightWidthProperty), "Label");
style.registerHandler(style.borderBottomWidthProperty, new style.StylePropertyChangedHandler(
LabelStyler.setBorderBottomWidthProperty,
LabelStyler.resetBorderBottomWidthProperty,
LabelStyler.getBorderBottomWidthProperty), "Label");
style.registerHandler(style.borderLeftWidthProperty, new style.StylePropertyChangedHandler(
LabelStyler.setBorderLeftWidthProperty,
LabelStyler.resetBorderLeftWidthProperty,
LabelStyler.getBorderLeftWidthProperty), "Label");
style.registerHandler(style.nativePaddingsProperty, new style.StylePropertyChangedHandler(
LabelStyler.setPaddingProperty,
LabelStyler.resetPaddingProperty,
LabelStyler.getPaddingProperty), "Label");
get [paddingLeftProperty.native](): number {
return 0;
}
}
LabelStyler.registerHandlers();
set [paddingLeftProperty.native](value: number) {
let nativeView = this._nativeView;
let padding = nativeView.padding;
nativeView.padding = {
top: padding.top,
right: padding.right,
bottom: padding.bottom,
left: value
};
}
}

View File

@ -1,92 +1,32 @@
import definition = require("ui/list-picker");
import dependencyObservable = require("ui/core/dependency-observable");
import proxy = require("ui/core/proxy");
import view = require("ui/core/view");
import types = require("utils/types");
import trace = require("trace");
import { ListPicker as ListPickerDefinition, ItemsSource } from "ui/list-picker";
import { View } from "ui/core/view";
import { Property } from "ui/core/properties";
export var traceCategory = "ListPicker";
export class ListPickerBase extends View implements ListPickerDefinition {
export class ListPicker extends view.View implements definition.ListPicker {
public static selectedIndexProperty = new dependencyObservable.Property("selectedIndex", "ListPicker", new proxy.PropertyMetadata(undefined));
public static itemsProperty = new dependencyObservable.Property("items", "ListPicker", new proxy.PropertyMetadata(undefined));
get selectedIndex(): number {
return this._getValue(ListPicker.selectedIndexProperty);
}
set selectedIndex(value: number) {
this._setValue(ListPicker.selectedIndexProperty, value);
}
get items(): any {
return this._getValue(ListPicker.itemsProperty);
}
set items(value: any) {
this._setValue(ListPicker.itemsProperty, value);
}
public selectedIndex: number;
public items: any[] | ItemsSource;
public _getItemAsString(index: number): any {
if (!this.items || !this.items.length) {
if (!this.items) {
return " ";
}
if (types.isDefined(this.items)) {
var item = this.items.getItem ? this.items.getItem(index) : this.items[index];
return types.isString(item) ? item : (types.isDefined(item) ? item.toString() : index.toString());
}
return index.toString();
let getItem = (<ItemsSource>this.items).getItem;
let item = typeof getItem === "function" ? getItem(index) : this.items[index];
return item === undefined || item === null ? index + "" : item + "";
}
public _onSelectedIndexPropertyChanged(data: dependencyObservable.PropertyChangeData) {
if (trace.enabled) {
trace.write("ListPicker._onSelectedIndexPropertyChanged("+data.oldValue+" => "+data.newValue+");", traceCategory);
}
var index = this.selectedIndex;
if (types.isUndefined(index)) {
return;
protected getSelectedIndex(items: any[] | ItemsSource): number {
let maxValue = items && items.length > 0 ? items.length - 1 : 0;
let selectedIndex = this.selectedIndex;
if (selectedIndex < 0 || selectedIndex > maxValue) {
selectedIndex = 0;
}
if (types.isDefined(this.items)) {
if (index < 0 || index >= this.items.length) {
this.selectedIndex = undefined;
throw new Error("selectedIndex should be between [0, items.length - 1]");
}
}
return selectedIndex;
}
public _onItemsPropertyChanged(data: dependencyObservable.PropertyChangeData) {
//trace.write("ListPicker._onItemsPropertyChanged(" + data.oldValue + " => " + data.newValue + ");", traceCategory);
}
public _updateSelectedIndexOnItemsPropertyChanged(newItems) {
if (trace.enabled) {
trace.write("ListPicker._updateSelectedIndexOnItemsPropertyChanged(" + newItems + ");", traceCategory);
}
var newItemsCount = 0;
if (newItems && newItems.length) {
newItemsCount = newItems.length;
}
if (newItemsCount === 0) {
this.selectedIndex = undefined;
}
else if (types.isUndefined(this.selectedIndex) || this.selectedIndex >= newItemsCount) {
this.selectedIndex = 0;
}
}
}
function onSelectedIndexPropertyChanged(data: dependencyObservable.PropertyChangeData) {
var picker = <ListPicker>data.object;
picker._onSelectedIndexPropertyChanged(data);
}
function onItemsPropertyChanged(data: dependencyObservable.PropertyChangeData) {
var picker = <ListPicker>data.object;
picker._onItemsPropertyChanged(data);
}
(<proxy.PropertyMetadata>ListPicker.selectedIndexProperty.metadata).onSetNativeValue = onSelectedIndexPropertyChanged;
(<proxy.PropertyMetadata>ListPicker.itemsProperty.metadata).onSetNativeValue = onItemsPropertyChanged;
export const selectedIndexProperty = new Property<ListPickerBase, number>({ name: "selectedIndex", defaultValue: -1 });
export const itemsProperty = new Property<ListPickerBase, any[] | ItemsSource>({ name: "items" });

View File

@ -1,17 +1,44 @@
import common = require("./list-picker-common");
import dependencyObservable = require("ui/core/dependency-observable");
import utils = require("utils/utils")
import * as types from "utils/types";
import { Styler, colorProperty, registerHandler, StylePropertyChangedHandler } from "ui/styling/style";
import { View } from "ui/core/view";
import { ListPickerBase, selectedIndexProperty, itemsProperty } from "./list-picker-common";
import { ItemsSource } from "ui/list-picker";
global.moduleMerge(common, exports);
export * from "./list-picker-common";
export class ListPicker extends common.ListPicker {
@Interfaces([android.widget.NumberPicker.Formatter])
class Formatter implements android.widget.NumberPicker.Formatter {
constructor(private owner: WeakRef<ListPicker>) {
return global.__native(this);
}
format(index: number): string {
let owner = this.owner.get();
if (owner) {
return owner._getItemAsString(index);
}
return " ";
}
}
@Interfaces([android.widget.NumberPicker.OnValueChangeListener])
class ValueChangeListener implements android.widget.NumberPicker.OnValueChangeListener {
constructor(private owner: WeakRef<ListPicker>) {
return global.__native(this);
}
onValueChange(picker: android.widget.NumberPicker, oldVal: number, newVal: number): void {
let owner = this.owner.get();
if (owner) {
owner.nativePropertyChanged(selectedIndexProperty, newVal);
}
}
}
export class ListPicker extends ListPickerBase {
private _android: android.widget.NumberPicker;
private _valueChangedListener: android.widget.NumberPicker.OnValueChangeListener;
private _formatter: android.widget.NumberPicker.Formatter;
private _editText: android.widget.EditText;
private itemsSet: boolean;
get android(): android.widget.NumberPicker {
return this._android;
@ -25,35 +52,10 @@ export class ListPicker extends common.ListPicker {
this._android.setMaxValue(0);
this._android.setValue(0);
var that = new WeakRef(this);
this._formatter = new android.widget.NumberPicker.Formatter(
<utils.Owned & android.widget.NumberPicker.IFormatter>{
get owner(): ListPicker {
return that.get();
},
format: function (index: number) {
if (this.owner) {
return this.owner._getItemAsString(index);
}
return " ";
}
});
let formatter = this._formatter || new Formatter(new WeakRef(this));
this._android.setFormatter(this._formatter);
this._valueChangedListener = new android.widget.NumberPicker.OnValueChangeListener(<utils.Owned & android.widget.NumberPicker.IOnValueChangeListener>{
get owner() {
return that.get();
},
onValueChange: function (picker: android.widget.NumberPicker, oldVal: number, newVal: number) {
if (this.owner) {
this.owner._onPropertyChangedFromNative(common.ListPicker.selectedIndexProperty, newVal);
}
}
});
let valueChangedListener = this._valueChangedListener || new ValueChangeListener(new WeakRef(this));
this._android.setOnValueChangedListener(this._valueChangedListener);
//Fix the disappearing selected item.
@ -65,37 +67,25 @@ export class ListPicker extends common.ListPicker {
//Since the Android NumberPicker has to always have at least one item, i.e. minValue=maxValue=value=0, we don't want this zero showing up when this.items is empty.
this._editText.setText(" ", android.widget.TextView.BufferType.NORMAL);
this.android.setWrapSelectorWheel(false);
}
public _onSelectedIndexPropertyChanged(data: dependencyObservable.PropertyChangeData) {
super._onSelectedIndexPropertyChanged(data);
if (this.android && types.isNumber(data.newValue)) {
this.android.setValue(data.newValue);
}
private updateSelectedValue(): void {
let selectedIndex = this.getSelectedIndex(this.items);
this.android.setValue(selectedIndex);
}
public _onItemsPropertyChanged(data: dependencyObservable.PropertyChangeData) {
if (this.android) {
if (!data.newValue || !data.newValue.length) {
this.android.setMaxValue(0);
}
else {
this.android.setMaxValue(data.newValue.length - 1);
}
private onItemsPropertyChanged(items: any[] | ItemsSource) {
let maxValue = items && items.length > 0 ? items.length - 1 : 0;
this.android.setWrapSelectorWheel(false);
}
this._updateSelectedIndexOnItemsPropertyChanged(data.newValue);
this.android.setMaxValue(maxValue);
this.updateSelectedValue();
this._fixNumberPickerRendering();
}
private _fixNumberPickerRendering() {
if (!this.android) {
return;
}
//HACK: Force the stubborn NumberPicker to render correctly when we have 0 or 1 items.
this.android.setFormatter(null);
this.android.setFormatter(this._formatter); //Force the NumberPicker to call our Formatter
@ -105,40 +95,30 @@ export class ListPicker extends common.ListPicker {
this._editText.invalidate(); //Force the EditText to redraw
this.android.invalidate();
}
}
export class ListPickerStyler implements Styler {
// color
private static setColorProperty(view: View, newValue: any) {
var picker = <android.widget.NumberPicker>view._nativeView;
ListPickerStyler._setNumberPickerTextColor(picker, newValue);
get [selectedIndexProperty.native](): number {
return -1;
}
set [selectedIndexProperty.native](value: number) {
if (this.itemsSet) {
this.updateSelectedValue();
}
}
private static resetColorProperty(view: View, nativeValue: any) {
var picker = <android.widget.NumberPicker>view._nativeView;
ListPickerStyler._setNumberPickerTextColor(picker, nativeValue);
get [itemsProperty.native](): any[] {
return null;
}
public static registerHandlers() {
registerHandler(colorProperty, new StylePropertyChangedHandler(
ListPickerStyler.setColorProperty,
ListPickerStyler.resetColorProperty), "ListPicker");
}
private static _setNumberPickerTextColor(picker: android.widget.NumberPicker, newValue: any) {
let childrenCount = picker.getChildCount();
for (let i = 0; i < childrenCount; i++) {
let child = picker.getChildAt(i);
if (child instanceof android.widget.EditText) {
let selectorWheelPaintField = picker.getClass().getDeclaredField("mSelectorWheelPaint");
selectorWheelPaintField.setAccessible(true);
selectorWheelPaintField.get(picker).setColor(newValue);
(<android.widget.EditText>picker.getChildAt(i)).setTextColor(newValue);
}
set [itemsProperty.native](value: any[] | ItemsSource) {
this.onItemsPropertyChanged(value);
// items are cleared - set selectedIndex to -1
if (!value) {
this.itemsSet = false;
this.selectedIndex = -1;
} else if (this.selectedIndex < 0) {
// items are set and selectedIndex is set - update maxValue & value.
this.selectedIndex = 0;
// set this flag later so no native call happens
this.itemsSet = true;
}
}
}
ListPickerStyler.registerHandlers();

View File

@ -2,18 +2,13 @@
* Contains the ListPicker class.
*/
declare module "ui/list-picker" {
import view = require("ui/core/view");
import dependencyObservable = require("ui/core/dependency-observable");
import { View } from "ui/core/view";
import { Property } from "ui/core/properties";
/**
* Represents an list picker.
*/
export class ListPicker extends view.View {
public static selectedIndexProperty: dependencyObservable.Property;
public static itemsProperty: dependencyObservable.Property;
constructor();
export class ListPicker extends View {
/**
* Gets the native [android.widget.NumberPicker](http://developer.android.com/reference/android/widget/NumberPicker.html) that represents the user interface for this component. Valid only when running on Android OS.
*/
@ -35,4 +30,12 @@ declare module "ui/list-picker" {
*/
items: any;
}
}
export interface ItemsSource {
length: number;
getItem(index: number): any;
}
export const selectedIndexProperty: Property<ListPicker, number>;
export const itemsProperty: Property<ListPicker, any[] | ItemsSource>;
}

View File

@ -1,15 +1,13 @@
import common = require("./list-picker-common");
import dependencyObservable = require("ui/core/dependency-observable");
import * as types from "utils/types";
import { backgroundColorProperty, colorProperty, registerHandler, Styler, StylePropertyChangedHandler } from "ui/styling/style";
import { View } from "ui/core/view";
import { ListPickerBase, selectedIndexProperty, itemsProperty } from "./list-picker-common";
import { ItemsSource } from "ui/list-picker";
global.moduleMerge(common, exports);
export * from "./list-picker-common";
export class ListPicker extends common.ListPicker {
export class ListPicker extends ListPickerBase {
private _ios: UIPickerView;
private _dataSource: ListPickerDataSource;
private _delegate: ListPickerDelegateImpl;
private itemsSet: boolean;
constructor() {
super();
@ -33,19 +31,42 @@ export class ListPicker extends common.ListPicker {
return this._ios;
}
public _onSelectedIndexPropertyChanged(data: dependencyObservable.PropertyChangeData) {
super._onSelectedIndexPropertyChanged(data);
if (this.ios && types.isNumber(data.newValue)) {
this.ios.selectRowInComponentAnimated(data.newValue, 0, false);
private updateSelectedValue(): void {
let selectedIndex = this.getSelectedIndex(this.items);
if (selectedIndex >= 0) {
this.ios.selectRowInComponentAnimated(selectedIndex, 0, false);
}
}
public _onItemsPropertyChanged(data: dependencyObservable.PropertyChangeData) {
if (this.ios) {
this.ios.reloadAllComponents();
}
private onItemsPropertyChanged(items: any[] | ItemsSource) {
this.ios.reloadAllComponents();
this.updateSelectedValue();
}
this._updateSelectedIndexOnItemsPropertyChanged(data.newValue);
get [selectedIndexProperty.native](): number {
return -1;
}
set [selectedIndexProperty.native](value: number) {
if (this.itemsSet) {
this.updateSelectedValue();
}
}
get [itemsProperty.native](): any[] {
return null;
}
set [itemsProperty.native](value: any[] | ItemsSource) {
this.onItemsPropertyChanged(value);
// items are cleared - set selectedIndex to -1
if (!value) {
this.itemsSet = false;
this.selectedIndex = -1;
} else if (this.selectedIndex < 0) {
// items are set and selectedIndex is set - update maxValue & value.
this.selectedIndex = 0;
// set this flag later so no native call happens
this.itemsSet = true;
}
}
}
@ -93,7 +114,7 @@ class ListPickerDelegateImpl extends NSObject implements UIPickerViewDelegate {
public pickerViewDidSelectRowInComponent(pickerView: UIPickerView, row: number, component: number): void {
let owner = this._owner.get();
if (owner) {
owner._onPropertyChangedFromNative(common.ListPicker.selectedIndexProperty, row);
owner.nativePropertyChanged(selectedIndexProperty, row);
}
}
}
@ -144,4 +165,4 @@ export class ListPickerStyler implements Styler {
}
}
ListPickerStyler.registerHandlers();
ListPickerStyler.registerHandlers();

View File

@ -2,7 +2,6 @@ declare module "ui/styling/style" {
import { Observable } from "data/observable";
import { ViewBase } from "ui/core/view-base";
import { Color } from "color";
import { CssProperty, InheritedCssProperty } from "ui/core/properties";
import { Font } from "ui/styling/font";
import { Background } from "ui/styling/background";
import { Length } from "ui/core/view";
@ -83,7 +82,7 @@ declare module "ui/styling/style" {
public fontSize: number;
public fontFamily: string;
public fontStyle: "normal" | "italic";
public fontWeight: string;
public fontWeight: "100" | "200" | "300" | "normal" | "400" | "500" | "600" | "bold" | "700" | "800" | "900";
public font: string;
public zIndex: number;
@ -141,21 +140,6 @@ declare module "ui/styling/style" {
// export function getHandler(property: Property, view: View): StylePropertyChangedHandler;
// Property registration
export let tintColorProperty: InheritedCssProperty<Style, Color>;
export let placeholderColorProperty: InheritedCssProperty<Style, Color>;
export let fontSizeProperty: InheritedCssProperty<Style, number>;
export let fontFamilyProperty: InheritedCssProperty<Style, string>;
export let fontStyleProperty: InheritedCssProperty<Style, string>;
export let fontWeightProperty: InheritedCssProperty<Style, string>;
export let fontProperty: InheritedCssProperty<Style, Font>;
export let textAlignmentProperty: InheritedCssProperty<Style, string>;
export let textDecorationProperty: CssProperty<Style, string>;
export let textTransformProperty: CssProperty<Style, string>;
export let letterSpacingProperty: CssProperty<Style, number>;
export let whiteSpaceProperty: CssProperty<Style, string>;
// /**
// * Represents an object that defines how style property should be applied on a native view/widget.
// */

View File

@ -284,149 +284,6 @@ Style.prototype.effectiveBorderBottomWidth = 0;
Style.prototype.effectiveBorderLeftWidth = 0;
// Property registration
export let fontInternalProperty = new CssProperty<Style, Font>({ name: "fontInternal", cssName: "_fontInternal", defaultValue: Font.default });
export let fontFamilyProperty = new InheritedCssProperty<Style, string>({
name: "fontFamily", cssName: "font-family", valueChanged: (target, newValue) => {
let currentFont = target.fontInternal;
if (currentFont.fontFamily !== newValue) {
target.fontInternal = currentFont.withFontFamily(newValue);
}
}
});
fontFamilyProperty.register(Style);
export let fontSizeProperty = new InheritedCssProperty<Style, number>({
name: "fontSize", cssName: "font-size", valueChanged: (target, newValue) => {
let currentFont = target.fontInternal;
if (currentFont.fontSize !== newValue) {
target.fontInternal = currentFont.withFontSize(newValue);
}
},
valueConverter: (v) => parseFloat(v)
});
fontSizeProperty.register(Style);
export let fontStyleProperty = new InheritedCssProperty<Style, string>({
name: "fontStyle", cssName: "font-style", defaultValue: FontStyle.normal, valueChanged: (target, newValue) => {
if (newValue !== FontStyle.normal && newValue !== FontStyle.italic) {
throw new Error(`font-style should be 'normal' or 'italic'. value: ${newValue}`)
}
let currentFont = target.fontInternal;
if (currentFont.fontStyle !== newValue) {
target.fontInternal = currentFont.withFontStyle(newValue);
}
}
});
fontStyleProperty.register(Style);
export let fontWeightProperty = new InheritedCssProperty<Style, string>({
name: "fontWeight", cssName: "font-weight", defaultValue: FontWeight.normal, valueChanged: (target, newValue) => {
if (!newValue) {
console.trace();
}
if (!(newValue === FontWeight.thin
|| newValue === FontWeight.extraLight
|| newValue === FontWeight.light
|| newValue === FontWeight.normal || newValue === "400"
|| newValue === FontWeight.medium
|| newValue === FontWeight.semiBold
|| newValue === FontWeight.bold || newValue === "700"
|| newValue === FontWeight.extraBold
|| newValue === FontWeight.black)) {
throw new Error(`Invalid font-weight value: ${newValue}`);
}
let currentFont = target.fontInternal;
if (currentFont.fontWeight !== newValue) {
target.fontInternal = currentFont.withFontWeight(newValue);
}
}
});
fontWeightProperty.register(Style);
function onFontChanged(style: Style, oldValue: Font, newValue: Font): void {
// TODO: Do we need these here?
style.fontFamily = newValue.fontFamily;
style.fontStyle = newValue.fontStyle;
style.fontWeight = newValue.fontWeight;
style.fontSize = newValue.fontSize;
}
export let fontProperty = new ShorthandProperty<Style>({
name: "font", cssName: "font",
getter: function (this: Style) {
return `${this.fontStyle} ${this.fontWeight} ${this.fontSize} ${this.fontFamily}`;
},
converter: function (value: string) {
return parseFont(value);
}
})
fontProperty.register(Style);
function parseFont(font: string): [CssProperty<any, any>, any][] {
let fontSize: number;
let fontFamily: string;
let fontStyle: "normal" | "italic" = "normal";
let fontWeight = "normal";
let elements = font.split(/\s+/);
let element: string;
while (element = elements.shift()) {
switch (element) {
case "normal":
break;
// TODO: add support for oblique font style.
case "italic":
// case "oblique":
fontStyle = "italic";
break;
case FontWeight.thin:
case FontWeight.extraLight:
case FontWeight.light:
case FontWeight.normal:
case "400":
case FontWeight.medium:
case FontWeight.semiBold:
case FontWeight.bold:
case "700":
case FontWeight.extraBold:
case FontWeight.black:
fontWeight = element;
break;
default:
if (!fontSize) {
let parts = element.split("/");
// TODO: add support for px support.
fontSize = parseFloat(parts[0]);
// TODO: add support for lineHeight.
// if (parts.length > 1) {
// lineHeight = parts[1];
// }
break;
}
fontFamily = element;
// if (elements.length) {
// fontFamily += " " + elements.join(" ");
// }
}
}
return [
[fontStyleProperty, fontStyle],
[fontWeightProperty, fontWeight],
[fontSizeProperty, fontSize],
[fontFamilyProperty, fontFamily]
]
}
// register default shorthand callbacks.
// styleProperty.registerShorthandCallback("font", onFontChanged);
// styleProperty.registerShorthandCallback("margin", onMarginChanged);

View File

@ -122,8 +122,8 @@ textProperty.register(TextBaseCommon);
export let formattedTextProperty = new Property<TextBaseCommon, FormattedString>({ name: "formattedText", affectsLayout: isIOS, valueChanged: onFormattedTextPropertyChanged });
formattedTextProperty.register(TextBaseCommon);
export let textAlignmentProperty = new InheritedCssProperty<Style, string>({
name: "textAlignment", cssName: "text-align", valueConverter: (value: string) => {
export let textAlignmentProperty = new InheritedCssProperty<Style, "left" | "center" | "right">({
name: "textAlignment", cssName: "text-align", valueConverter: (value) => {
switch (value) {
case "left":
case "center":
@ -131,27 +131,27 @@ export let textAlignmentProperty = new InheritedCssProperty<Style, string>({
return value;
default:
throw new Error("CSS text-align \"" + value + "\" is not supported.");
throw new Error(`CSS text-align ${value} is not supported.`);
}
}
});
textAlignmentProperty.register(Style);
export let textDecorationProperty = new CssProperty<Style, string>({
name: "textDecoration", cssName: "text-decoration", defaultValue: "none", valueConverter: (value: string) => {
export let textDecorationProperty = new CssProperty<Style, "none" | "underline" | "line-through">({
name: "textDecoration", cssName: "text-decoration", defaultValue: "none", valueConverter: (value) => {
let values = (value + "").split(" ");
if (values.indexOf("none") !== -1 || values.indexOf("underline") !== -1 || values.indexOf("lineThrough") !== -1) {
return value;
} else {
throw new Error("CSS text-decoration \"" + value + "\" is not supported.");
throw new Error(`CSS text-decoration ${value} is not supported.`);
}
}
});
textDecorationProperty.register(Style);
export let textTransformProperty = new CssProperty<Style, string>({
name: "textTransform", cssName: "text-transform", defaultValue: "none", valueConverter: (value: string) => {
export let textTransformProperty = new CssProperty<Style, "none" | "capitalize" | "uppercase" | "lowercase">({
name: "textTransform", cssName: "text-transform", defaultValue: "none", valueConverter: (value) => {
switch (value) {
case "none":
case "uppercase":
@ -160,7 +160,7 @@ export let textTransformProperty = new CssProperty<Style, string>({
return value;
default:
throw new Error("CSS text-transform \"" + value + "\" is not supported.");
throw new Error(`CSS text-transform ${value} is not supported.`);
}
}
});
@ -173,7 +173,7 @@ export let whiteSpaceProperty = new CssProperty<Style, "normal" | "nowrap">({
case "nowrap":
return value;
default:
throw new Error("CSS white-space \"" + value + "\" is not supported.");
throw new Error(`CSS white-space ${value} is not supported.`);
}
}
});

View File

@ -67,12 +67,12 @@
//@endprivate
}
export let textProperty: Property<TextBase, string>;
export let formattedTextProperty: Property<TextBase, FormattedString>;
export const textProperty: Property<TextBase, string>;
export const formattedTextProperty: Property<TextBase, FormattedString>;
export let textAlignmentProperty: InheritedCssProperty<Style, string>;
export let textDecorationProperty: CssProperty<Style, string>;
export let textTransformProperty: CssProperty<Style, string>;
export let whiteSpaceProperty: CssProperty<Style, string>;
export let letterSpacingProperty: CssProperty<Style, number>;
export const textAlignmentProperty: InheritedCssProperty<Style, "left" | "center" | "right">;
export const textDecorationProperty: CssProperty<Style, "none" | "underline" | "line-through">;
export const textTransformProperty: CssProperty<Style, "none" | "capitalize" | "uppercase" | "lowercase">;
export const whiteSpaceProperty: CssProperty<Style, "normal" | "nowrap">;
export const letterSpacingProperty: CssProperty<Style, number>;
}

View File

@ -1,10 +1,9 @@
import { TextBaseCommon, textProperty, formattedTextProperty } from "./text-base-common";
import { FormattedString } from "text/formatted-string";
import {
colorProperty, fontInternalProperty, textAlignmentProperty, textDecorationProperty,
import {
TextBaseCommon, textProperty, formattedTextProperty, textAlignmentProperty, textDecorationProperty,
textTransformProperty, whiteSpaceProperty, letterSpacingProperty
} from "ui/styling/style";
import { TextAlignment, TextDecoration, TextTransform, WhiteSpace } from "ui/enums";
} from "./text-base-common";
import { FormattedString } from "text/formatted-string";
import { colorProperty, fontInternalProperty } from "ui/core/view";
import { toUIString, isNumber } from "utils/types";
import { Font } from "ui/styling/font";
import { Color } from "color";
@ -15,18 +14,18 @@ function NSStringFromNSAttributedString(source: NSAttributedString | string): NS
return NSString.stringWithString(source instanceof NSAttributedString && source.string || <string>source);
}
function getTransformedText(text: string, transform: string): string {
function getTransformedText(text: string, transform: "none" | "capitalize" | "uppercase" | "lowercase"): string {
switch (transform) {
case TextTransform.uppercase:
case "uppercase":
return NSStringFromNSAttributedString(text).uppercaseString;
case TextTransform.lowercase:
case "lowercase":
return NSStringFromNSAttributedString(text).lowercaseString;
case TextTransform.capitalize:
case "capitalize":
return NSStringFromNSAttributedString(text).capitalizedString;
case TextTransform.none:
case "none":
default:
return text;
}