@@ -4,6 +4,7 @@ export * from '../properties';
44
55import { ViewCommon , originXProperty , originYProperty } from './view-common' ;
66import type { CoreTypes } from '../../../core-types' ;
7+ import type { Point } from './view-interfaces' ;
78import { visibilityProperty , opacityProperty , backgroundInternalProperty , translateXProperty , translateYProperty , scaleXProperty , scaleYProperty , rotateProperty , rotateXProperty , rotateYProperty , perspectiveProperty , horizontalAlignmentProperty , verticalAlignmentProperty , paddingTopProperty , paddingRightProperty , paddingBottomProperty , paddingLeftProperty } from '../../styling/style-properties' ;
89import { LinearGradient } from '../../styling/linear-gradient' ;
910import { widthProperty , heightProperty , minWidthProperty , minHeightProperty , marginLeftProperty , marginTopProperty , marginRightProperty , marginBottomProperty } from '../../styling/style-properties' ;
@@ -13,7 +14,7 @@ import { Background } from '../../styling/background';
1314import { BoxShadow } from '../../styling/box-shadow' ;
1415import { Color } from '../../../color' ;
1516import { hiddenProperty } from '../view-base' ;
16- import { getCurrentWindowBounds , getCurrentWindowContent , getWindowBounds } from '../../../application/window-helper.windows' ;
17+ import { getClientOriginOnScreen , getCurrentWindowBounds , getCurrentWindowContent , getWindowBounds } from '../../../application/window-helper.windows' ;
1718import { ImageSource } from '../../../image-source' ;
1819import { ClipPathFunction } from '../../styling/clip-path-function' ;
1920import { nativeChildIndex , removeNativeChild } from './native-children.windows' ;
@@ -630,6 +631,11 @@ class CompositionBorderHandler {
630631 }
631632}
632633
634+ let _zeroPoint : Windows . Foundation . Point | undefined ;
635+ function zeroPoint ( ) : Windows . Foundation . Point {
636+ return ( _zeroPoint ??= Microsoft . UI . Xaml . PointHelper . FromCoordinates ( 0 , 0 ) ) ;
637+ }
638+
633639export class View extends ViewCommon {
634640 nativeViewProtected : Microsoft . UI . Xaml . FrameworkElement ;
635641
@@ -1178,6 +1184,32 @@ export class View extends ViewCommon {
11781184 }
11791185 }
11801186
1187+ private _originIn ( target : Microsoft . UI . Xaml . UIElement | null ) : Point {
1188+ try {
1189+ const p = ( this . nativeViewProtected as any ) . TransformToVisual ( target ) . TransformPoint ( zeroPoint ( ) ) ;
1190+ return { x : p . X , y : p . Y } ;
1191+ } catch ( _e ) {
1192+ return undefined ;
1193+ }
1194+ }
1195+
1196+ public getLocationInWindow ( ) : Point {
1197+ return ( this . nativeViewProtected as any ) ?. XamlRoot ? this . _originIn ( null ) : undefined ;
1198+ }
1199+
1200+ public getLocationOnScreen ( ) : Point {
1201+ const root = ( this . nativeViewProtected as any ) ?. XamlRoot ;
1202+ const inWindow = root ? this . _originIn ( null ) : undefined ;
1203+ const client = inWindow ? getClientOriginOnScreen ( root ) : null ;
1204+ return client ? { x : client . x + inWindow . x , y : client . y + inWindow . y } : undefined ;
1205+ }
1206+
1207+ public getLocationRelativeTo ( otherView : ViewCommon ) : Point {
1208+ const other = otherView ?. nativeViewProtected as any ;
1209+ const root = ( this . nativeViewProtected as any ) ?. XamlRoot ;
1210+ return root && other ?. XamlRoot === root ? this . _originIn ( other ) : undefined ;
1211+ }
1212+
11811213 // Button-family controls override their template's brush resources. Probed on first need: most
11821214 // views never set a colour or background, and the probe is a WinRT call.
11831215 protected _nativeIsButton ( ) : boolean {
@@ -1476,6 +1508,15 @@ export class View extends ViewCommon {
14761508 } catch ( _e ) { }
14771509 }
14781510
1511+ /**
1512+ * A parent that lays out its children itself can take over a child's percentage width or height
1513+ * (`fraction` 0-1, `null` once it is no longer a percentage) by returning `true`: the child then
1514+ * leaves its XAML size unset and skips its own percent sizing.
1515+ */
1516+ _setChildPercentSize ( child : View , horizontal : boolean , fraction : number | null ) : boolean {
1517+ return false ;
1518+ }
1519+
14791520 private _applyPercentSizing ( ) : void {
14801521 const nativeView = this . nativeViewProtected as any ;
14811522 if ( ! nativeView ) {
@@ -1521,6 +1562,11 @@ export class View extends ViewCommon {
15211562
15221563 if ( value && typeof value === 'object' && ( value as any ) . unit === '%' ) {
15231564 const pct = ( value as any ) . value ;
1565+ if ( this . parent instanceof View && this . parent . _setChildPercentSize ( this , true , pct ) ) {
1566+ this . _percentWidth = null ;
1567+ this . nativeViewProtected . Width = NaN ;
1568+ return ;
1569+ }
15241570 this . _percentWidth = pct ;
15251571 this . _ensureSizeWatch ( ) ; // re-apply percent when the parent resizes
15261572 this . nativeViewProtected . Width = NaN ;
@@ -1543,6 +1589,7 @@ export class View extends ViewCommon {
15431589 }
15441590
15451591 this . _percentWidth = null ;
1592+ if ( this . parent instanceof View ) this . parent . _setChildPercentSize ( this , true , null ) ;
15461593 // Clear any previously set flex-basis so the C++ widget falls back to DesiredSize.
15471594 try {
15481595 ( NativeScript as any ) . Widgets . FlexboxLayout . SetFlexBasisPercent (
@@ -1560,6 +1607,11 @@ export class View extends ViewCommon {
15601607
15611608 if ( value && typeof value === 'object' && ( value as any ) . unit === '%' ) {
15621609 const pct = ( value as any ) . value ;
1610+ if ( this . parent instanceof View && this . parent . _setChildPercentSize ( this , false , pct ) ) {
1611+ this . _percentHeight = null ;
1612+ this . nativeViewProtected . Height = NaN ;
1613+ return ;
1614+ }
15631615 this . _percentHeight = pct ;
15641616 this . _ensureSizeWatch ( ) ; // re-apply percent when the parent resizes
15651617 this . nativeViewProtected . Height = NaN ;
@@ -1577,6 +1629,7 @@ export class View extends ViewCommon {
15771629 }
15781630
15791631 this . _percentHeight = null ;
1632+ if ( this . parent instanceof View ) this . parent . _setChildPercentSize ( this , false , null ) ;
15801633 this . nativeViewProtected . Height = toXamlLength ( value ) ;
15811634 }
15821635
0 commit comments