Skip to content

Commit 455ca8c

Browse files
sammy-SCfacebook-github-bot
authored andcommitted
Make UIManager.measure* compatible with Fabric
Summary: changelog: [internal] To make migration to the new architecture more straight forward, this change makes `UIManager.measure`, `UIManager.measureInWindow`, `UIManager.measureLayout` and `UIManager.measureLayoutRelativeToParent` functions backwards compatible. Users will not have to make any change to continue using the APIs. This will make [Migrating .measure*() ](https://reactnative.dev/docs/new-architecture-library-intro#migrating-measure) in the migration guide optional. Reviewed By: yungsters Differential Revision: D41613050 fbshipit-source-id: 3c65ced231590243d118fbc120a87b08d5261da0
1 parent 326109b commit 455ca8c

File tree

2 files changed

+144
-1
lines changed

2 files changed

+144
-1
lines changed

Libraries/ReactNative/FabricUIManager.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -58,6 +58,7 @@ export type Spec = {|
5858
errorCallback: (error: Object) => void,
5959
) => void,
6060
+sendAccessibilityEvent: (node: Node, eventType: string) => void,
61+
+findShadowNodeByTag_DEPRECATED: (reactTag: number) => ?Node,
6162
|};
6263

6364
const FabricUIManager: ?Spec = global.nativeFabricUIManager;

Libraries/ReactNative/UIManager.js

Lines changed: 143 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
*/
1010

1111
import type {RootTag} from '../Types/RootTagTypes';
12+
import type {Spec as FabricUIManagerSpec} from './FabricUIManager';
1213
import type {Spec} from './NativeUIManager';
1314

1415
export interface UIManagerJSInterface extends Spec {
@@ -31,9 +32,150 @@ export interface UIManagerJSInterface extends Spec {
3132
) => void;
3233
}
3334

34-
const UIManager: UIManagerJSInterface =
35+
function isFabricReactTag(reactTag: number): boolean {
36+
// React reserves even numbers for Fabric.
37+
return reactTag % 2 === 0;
38+
}
39+
40+
const UIManagerImpl: UIManagerJSInterface =
3541
global.RN$Bridgeless === true
3642
? require('./BridgelessUIManager')
3743
: require('./PaperUIManager');
3844

45+
// $FlowFixMe[cannot-spread-interface]
46+
const UIManager = {
47+
...UIManagerImpl,
48+
measure(
49+
reactTag: number,
50+
callback: (
51+
left: number,
52+
top: number,
53+
width: number,
54+
height: number,
55+
pageX: number,
56+
pageY: number,
57+
) => void,
58+
): void {
59+
if (isFabricReactTag(reactTag)) {
60+
const FabricUIManager: FabricUIManagerSpec =
61+
global?.nativeFabricUIManager;
62+
const shadowNode =
63+
FabricUIManager.findShadowNodeByTag_DEPRECATED(reactTag);
64+
if (shadowNode) {
65+
FabricUIManager.measure(shadowNode, callback);
66+
} else {
67+
console.warn(`measure cannot find view with tag #${reactTag}`);
68+
// $FlowFixMe[incompatible-call]
69+
callback();
70+
}
71+
} else {
72+
// Paper
73+
UIManagerImpl.measure(reactTag, callback);
74+
}
75+
},
76+
77+
measureInWindow(
78+
reactTag: number,
79+
callback: (
80+
left: number,
81+
top: number,
82+
width: number,
83+
height: number,
84+
) => void,
85+
): void {
86+
if (isFabricReactTag(reactTag)) {
87+
const FabricUIManager: FabricUIManagerSpec =
88+
global?.nativeFabricUIManager;
89+
const shadowNode =
90+
FabricUIManager.findShadowNodeByTag_DEPRECATED(reactTag);
91+
if (shadowNode) {
92+
FabricUIManager.measureInWindow(shadowNode, callback);
93+
} else {
94+
console.warn(`measure cannot find view with tag #${reactTag}`);
95+
// $FlowFixMe[incompatible-call]
96+
callback();
97+
}
98+
} else {
99+
// Paper
100+
UIManagerImpl.measureInWindow(reactTag, callback);
101+
}
102+
},
103+
104+
measureLayout(
105+
reactTag: number,
106+
ancestorReactTag: number,
107+
errorCallback: (error: Object) => void,
108+
callback: (
109+
left: number,
110+
top: number,
111+
width: number,
112+
height: number,
113+
) => void,
114+
): void {
115+
if (isFabricReactTag(reactTag)) {
116+
const FabricUIManager: FabricUIManagerSpec =
117+
global?.nativeFabricUIManager;
118+
const shadowNode =
119+
FabricUIManager.findShadowNodeByTag_DEPRECATED(reactTag);
120+
const ancestorShadowNode =
121+
FabricUIManager.findShadowNodeByTag_DEPRECATED(ancestorReactTag);
122+
123+
if (!shadowNode || !ancestorShadowNode) {
124+
return;
125+
}
126+
127+
FabricUIManager.measureLayout(
128+
shadowNode,
129+
ancestorShadowNode,
130+
errorCallback,
131+
callback,
132+
);
133+
} else {
134+
// Paper
135+
UIManagerImpl.measureLayout(
136+
reactTag,
137+
ancestorReactTag,
138+
errorCallback,
139+
callback,
140+
);
141+
}
142+
},
143+
144+
measureLayoutRelativeToParent(
145+
reactTag: number,
146+
errorCallback: (error: Object) => void,
147+
callback: (
148+
left: number,
149+
top: number,
150+
width: number,
151+
height: number,
152+
) => void,
153+
): void {
154+
if (isFabricReactTag(reactTag)) {
155+
console.warn(
156+
'RCTUIManager.measureLayoutRelativeToParent method is deprecated and it will not be implemented in newer versions of RN (Fabric) - T47686450',
157+
);
158+
const FabricUIManager: FabricUIManagerSpec =
159+
global?.nativeFabricUIManager;
160+
const shadowNode =
161+
FabricUIManager.findShadowNodeByTag_DEPRECATED(reactTag);
162+
if (shadowNode) {
163+
FabricUIManager.measure(
164+
shadowNode,
165+
(left, top, width, height, pageX, pageY) => {
166+
callback(left, top, width, height);
167+
},
168+
);
169+
}
170+
} else {
171+
// Paper
172+
UIManagerImpl.measureLayoutRelativeToParent(
173+
reactTag,
174+
errorCallback,
175+
callback,
176+
);
177+
}
178+
},
179+
};
180+
39181
module.exports = UIManager;

0 commit comments

Comments
 (0)