Move styleScope from Page to View

Fix image-source test for API 27
setupAsRootView now makes the component styleScope
set css, addCss & addCssFile makes view to be styleScopeHost which cannot be overriden later from parent
Android modals now call setupAsRootView
Small fixes on ios layouts
launch event fired in andriod too
Moved some requestLayout calls to ios files where they belongs
This commit is contained in:
Hristo Hristov
2017-12-19 16:35:15 +02:00
parent 63ab46eb2a
commit 058a216ac9
19 changed files with 185 additions and 268 deletions

View File

@@ -20,6 +20,7 @@ import {
} from "../../gestures";
import { createViewFromEntry } from "../../builder";
import { StyleScope } from "../../styling/style-scope";
export * from "../../styling/style-properties";
export * from "../view-base";
@@ -74,6 +75,52 @@ export abstract class ViewCommon extends ViewBase implements ViewDefinition {
public _gestureObservers = {};
get css(): string {
const scope = this._styleScope;
return scope && scope.css;
}
set css(value: string) {
this.updateStyleScope(undefined, undefined, value);
}
public addCss(cssString: string): void {
this.updateStyleScope(undefined, cssString);
}
public addCssFile(cssFileName: string) {
this.updateStyleScope(cssFileName);
}
private updateStyleScope(cssFileName?: string, cssString?: string, css?: string): void {
let scope = this._styleScope;
if (!scope) {
scope = new StyleScope();
this.setScopeProperty(scope, cssFileName, cssString, css);
this._inheritStyleScope(scope);
this._isStyleScopeHost = true;
} else {
this.setScopeProperty(scope, cssFileName, cssString, css);
this._onCssStateChange();
}
}
private setScopeProperty(scope: StyleScope, cssFileName?: string, cssString?: string, css?: string): void {
if (cssFileName !== undefined) {
scope.addCssFile(cssFileName);
} else if (cssString !== undefined) {
scope.addCss(cssString);
} else if (css !== undefined) {
scope.css = css;
}
}
_setupAsRootView(context: any): void {
super._setupAsRootView(context);
if (!this._styleScope) {
this.updateStyleScope();
}
}
observe(type: GestureTypes, callback: (args: GestureEventData) => void, thisArg?: any): void {
if (!this._gestureObservers[type]) {
this._gestureObservers[type] = [];
@@ -157,9 +204,9 @@ export abstract class ViewCommon extends ViewBase implements ViewDefinition {
const context: any = arguments[1];
const closeCallback: Function = arguments[2];
const fullscreen: boolean = arguments[3];
const animated = arguments[4];
const animated = arguments[4];
const view: ViewDefinition = firstAgrument instanceof ViewCommon
const view: ViewDefinition = firstAgrument instanceof ViewCommon
? firstAgrument : createViewFromEntry({ moduleName: firstAgrument });
(<ViewCommon>view)._showNativeModalView(this, context, closeCallback, fullscreen, animated);
@@ -886,10 +933,6 @@ export abstract class ViewCommon extends ViewBase implements ViewDefinition {
public _redrawNativeBackground(value: any): void {
//
}
addCssFile(cssFileName: string): void {
// TODO: Implement
}
}
export const automationTextProperty = new Property<ViewCommon, string>({ name: "automationText" });

View File

@@ -152,7 +152,7 @@ function initializeDialogFragment() {
public onCreateView(inflater: android.view.LayoutInflater, container: android.view.ViewGroup, savedInstanceState: android.os.Bundle): android.view.View {
const owner = this.owner;
owner._setupUI(this.getActivity());
owner._setupAsRootView(this.getActivity());
owner._isAddedToNativeVisualTree = true;
return this.owner.nativeViewProtected;
@@ -323,7 +323,7 @@ export class View extends ViewCommon {
public requestLayout(): void {
super.requestLayout();
if (this.nativeViewProtected) {
return this.nativeViewProtected.requestLayout();
this.nativeViewProtected.requestLayout();
}
}

View File

@@ -515,7 +515,7 @@ export abstract class View extends ViewBase {
* Returns the current modal view that this page is showing (is parent of), if any.
*/
modal: View;
/**
* Animates one or more properties of the view based on the supplied options.
*/
@@ -638,6 +638,20 @@ export abstract class View extends ViewBase {
* @private
*/
_getFragmentManager(): any; /* android.app.FragmentManager */
/**
* @private
* A valid css string which will be applied for all nested UI components (based on css rules).
*/
css: string;
/**
* @private
* Adds a new values to current css.
* @param cssString - A valid css which will be added to current css.
*/
addCss(cssString: string): void;
/**
* @private
* Adds the content of the file to the current css.
@@ -649,12 +663,12 @@ export abstract class View extends ViewBase {
/**
* __Obsolete:__ There is a new property system that does not rely on _getValue.
*/
public _getValue(property: any): never;
_getValue(property: any): never;
/**
* __Obsolete:__ There is a new property system that does not rely on _setValue.
*/
public _setValue(property: any, value: any): never;
_setValue(property: any, value: any): never;
}
/**

View File

@@ -57,7 +57,7 @@ export class View extends ViewCommon {
super.requestLayout();
this._privateFlags |= PFLAG_FORCE_LAYOUT;
const parent = <View>this.parent;
const parent = this.parent;
if (parent) {
parent.requestLayout();
}
@@ -586,134 +586,45 @@ function isScrollable(controller: UIViewController, owner: View): boolean {
const majorVersion = iosUtils.MajorVersion;
interface ExtendedController extends UIViewController {
scrollable: boolean;
navBarHidden: boolean;
hasChildControllers: boolean;
// safeAreaLeft: NSLayoutConstraint;
// safeAreaTop: NSLayoutConstraint;
// safeAreaRight: NSLayoutConstraint;
// safeAreaBottom: NSLayoutConstraint;
// fullscreenTop: NSLayoutConstraint;
// fullscreenBottom: NSLayoutConstraint;
// fullscreenLeft: NSLayoutConstraint;
// fullscreenRight: NSLayoutConstraint;
// activeConstraints: NSLayoutConstraint[];
}
export namespace ios {
function constrainView(controller: ExtendedController, owner: View): void {
export function updateConstraints(controller: UIViewController, owner: View): void {
const root = controller.view;
root.autoresizesSubviews = false;
// const view = controller.view.subviews.length > 0 ? controller.view.subviews[0] : null;
// if (view) {
// view.translatesAutoresizingMaskIntoConstraints = false;
// }
if (!root.safeAreaLayoutGuide) {
const layoutGuide = (<any>root).safeAreaLayoutGuide = UILayoutGuide.alloc().init();
root.addLayoutGuide(layoutGuide);
// // view.translatesAutoresizingMaskIntoConstraints = false;
// if (majorVersion > 10) {
// const safeArea = root.safeAreaLayoutGuide;
// layoutGuide.topAnchor.constraintEqualToAnchor(safeArea.topAnchor);
// layoutGuide.bottomAnchor.constraintEqualToAnchor(safeArea.bottomAnchor);
// layoutGuide.leftAnchor.constraintEqualToAnchor(safeArea.leftAnchor);
// layoutGuide.rightAnchor.constraintEqualToAnchor(safeArea.rightAnchor);
// } else {
NSLayoutConstraint.activateConstraints(<any>[
layoutGuide.topAnchor.constraintEqualToAnchor(controller.topLayoutGuide.bottomAnchor),
layoutGuide.bottomAnchor.constraintEqualToAnchor(controller.bottomLayoutGuide.topAnchor),
layoutGuide.leadingAnchor.constraintEqualToAnchor(root.leadingAnchor),
layoutGuide.trailingAnchor.constraintEqualToAnchor(root.trailingAnchor)
]);
// }
}
// const view = root.subviews[0];
// if (!controller.safeAreaTop) {
// view.translatesAutoresizingMaskIntoConstraints = false;
// if (majorVersion > 10) {
// const safeArea = root.safeAreaLayoutGuide;
// controller.safeAreaTop = view.topAnchor.constraintEqualToAnchor(safeArea.topAnchor);
// controller.fullscreenTop = view.topAnchor.constraintEqualToAnchor(root.topAnchor);
// controller.safeAreaBottom = view.bottomAnchor.constraintEqualToAnchor(safeArea.bottomAnchor);
// controller.fullscreenBottom = view.bottomAnchor.constraintEqualToAnchor(root.bottomAnchor);
// controller.safeAreaLeft = view.leftAnchor.constraintEqualToAnchor(safeArea.leftAnchor);
// controller.fullscreenLeft = view.leftAnchor.constraintEqualToAnchor(root.leftAnchor);
// controller.safeAreaRight = view.rightAnchor.constraintEqualToAnchor(safeArea.rightAnchor);
// controller.fullscreenRight = view.rightAnchor.constraintEqualToAnchor(root.rightAnchor);
// } else {
// controller.safeAreaTop = view.topAnchor.constraintEqualToAnchor(controller.topLayoutGuide.bottomAnchor);
// controller.fullscreenTop = view.topAnchor.constraintEqualToAnchor(root.topAnchor);
// controller.safeAreaBottom = view.bottomAnchor.constraintEqualToAnchor(controller.bottomLayoutGuide.topAnchor);
// controller.fullscreenBottom = view.bottomAnchor.constraintEqualToAnchor(root.bottomAnchor);
// controller.safeAreaLeft = view.leadingAnchor.constraintEqualToAnchor(root.leadingAnchor);
// controller.fullscreenLeft = controller.safeAreaLeft;
// controller.safeAreaRight = view.trailingAnchor.constraintEqualToAnchor(root.trailingAnchor);
// controller.fullscreenRight = controller.safeAreaRight;
// }
// }
// // check if this works
// const fullscreenHorizontally = controller ===
// iosUtils.getter(UIApplication, UIApplication.sharedApplication).keyWindow.rootViewController
// || !!(<any>owner).wantsFullscreen;
// const navBarHidden = controller.navBarHidden;
// const scrollable = controller.scrollable;;
// const hasChildControllers = controller.hasChildControllers;
// const constraints = [
// hasChildControllers || scrollable ? controller.fullscreenBottom : controller.safeAreaBottom,
// fullscreenHorizontally ? controller.fullscreenLeft : controller.safeAreaLeft,
// fullscreenHorizontally ? controller.fullscreenRight : controller.safeAreaRight
// ];
// if (hasChildControllers) {
// // If not inner most extend to fullscreen
// constraints.push(controller.fullscreenTop);
// } else if (!scrollable) {
// // If not scrollable dock under safe area
// constraints.push(controller.safeAreaTop);
// } else if (navBarHidden) {
// // If scrollable but no navigation bar dock under safe area
// constraints.push(controller.safeAreaTop);
// } else {
// // If scrollable and navigation bar extend to fullscreen
// constraints.push(controller.fullscreenTop);
// }
// const activeConstraints = controller.activeConstraints;
// if (activeConstraints) {
// NSLayoutConstraint.deactivateConstraints(<any>activeConstraints);
// }
// NSLayoutConstraint.activateConstraints(<any>constraints);
// controller.activeConstraints = constraints;
}
export function updateConstraints(controller: UIViewController, owner: View): void {
const extendedController = <ExtendedController>controller;
// const navController = controller.navigationController;
// const navBarHidden = navController ? navController.navigationBarHidden : true;
// const scrollable = isScrollable(controller, owner);
// const hasChildControllers = controller.childViewControllers.count > 0;
function getStatusBarHeight(viewController?: UIViewController): number {
const app = iosUtils.getter(UIApplication, UIApplication.sharedApplication);
if (!app || app.statusBarHidden) {
return 0;
}
// if (extendedController.scrollable !== scrollable
// || extendedController.navBarHidden !== navBarHidden
// || extendedController.hasChildControllers !== hasChildControllers) {
// extendedController.scrollable = scrollable;
// extendedController.navBarHidden = navBarHidden;
// extendedController.hasChildControllers = hasChildControllers;
// constrainView(extendedController, owner);
// }
if (viewController && viewController.prefersStatusBarHidden) {
return 0;
}
constrainView(extendedController, owner);
const statusFrame = app.statusBarFrame;
return Math.min(statusFrame.size.width, statusFrame.size.height);
}
export function layoutView(controller: UIViewController, owner: View): void {
// const frame = controller.view.subviews[0].bounds;
// check if this works
const fullscreen = controller ===
iosUtils.getter(UIApplication, UIApplication.sharedApplication).keyWindow.rootViewController;
// || !!(<any>owner).wantsFullscreen;
let left: number, top: number, width: number, height: number;
@@ -739,28 +650,32 @@ export namespace ios {
const safeAreaTopLength = safeOrigin.y - fullscreenOrigin.y;
const safeAreaBottomLength = fullscreenSize.height - safeAreaSize.height - safeAreaTopLength;
if (!(controller.edgesForExtendedLayout & UIRectEdge.Top)) {
const statusBarHeight = getStatusBarHeight(controller);
const navBarHeight = controller.navigationController ? controller.navigationController.navigationBar.frame.size.height : 0;
fullscreenOrigin.y = safeOrigin.y;
fullscreenSize.height -= (statusBarHeight + navBarHeight);
}
left = safeOrigin.x;
width = safeAreaSize.width;
if (hasChildControllers) {
// If not inner most extend to fullscreen
top = fullscreenOrigin.y; // constraints.push(controller.fullscreenTop);
top = fullscreenOrigin.y;
height = fullscreenSize.height;
} else if (!scrollable) {
// If not scrollable dock under safe area
top = safeOrigin.y;
height = safeAreaSize.height;
// constraints.push(controller.safeAreaTop);
} else if (navBarHidden) {
// If scrollable but no navigation bar dock under safe area
top = safeOrigin.y; // constraints.push(controller.safeAreaTop);
// const adjusted = parentControllerAdjustedScrollViewInsets(controller);
height = safeAreaSize.height + safeAreaBottomLength;
// if ()
top = safeOrigin.y;
height = navController ? (fullscreenSize.height - top) : safeAreaSize.height;
} else {
// If scrollable and navigation bar extend to fullscreen
top = fullscreenOrigin.y; // constraints.push(controller.fullscreenTop);
height = fullscreenOrigin.y + fullscreenSize.height;
top = fullscreenOrigin.y;
height = fullscreenSize.height;
}
left = layout.toDevicePixels(left);
@@ -769,34 +684,10 @@ export namespace ios {
height = layout.toDevicePixels(height);
}
// const frame = controller.view.safeAreaLayoutGuide.layoutFrame;
// const origin = frame.origin;
// const size = frame.size;
// width = layout.toDevicePixels(fullscreenSize.width);
// height = layout.toDevicePixels(fullscreenSize.height);
// if (iosUtils.MajorVersion < 11) {
// const window = controller.view.window;
// if (window) {
// const windowSize = window.frame.size;
// const windowInPortrait = windowSize.width < windowSize.height;
// const viewInPortrait = width < height;
// if (windowInPortrait !== viewInPortrait) {
// // NOTE: This happens on iOS <11.
// // We were not visible (probably in backstack) when orientation happened.
// // request layout so we get the new dimensions.
// // There is no sync way to force a layout.
// setTimeout(() => owner.requestLayout());
// }
// }
// }
const widthSpec = layout.makeMeasureSpec(width, layout.EXACTLY);
const heightSpec = layout.makeMeasureSpec(height, layout.EXACTLY);
View.measureChild(null, owner, widthSpec, heightSpec);
// const left = layout.toDevicePixels(fullscreenOrigin.x);
// const top = layout.toDevicePixels(fullscreenOrigin.y);
View.layoutChild(null, owner, left, top, width + left, height + top);
layoutParent(owner.parent);