@react-native-oh/react-native-harmony 0.72.28-8 → 0.72.29

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,5 +1,5 @@
1
1
  import type { TurboModule } from "react-native/Libraries/TurboModule/RCTExport";
2
- import { TurboModuleRegistry, View, ViewProps } from "react-native";
2
+ import { Dimensions, TurboModuleRegistry, View, ViewProps } from "react-native";
3
3
  import { useEffect, useState } from "react";
4
4
  import React from "react";
5
5
 
@@ -22,23 +22,68 @@ const safeAreaTurboModule = TurboModuleRegistry.get<Spec>(
22
22
  "SafeAreaTurboModule"
23
23
  )!;
24
24
 
25
+ const getPaddingTop = (inset: number, pageY: number) => {
26
+ return Math.max(0, inset - (pageY < 0 ? pageY * -1 : pageY));
27
+ }
28
+
29
+ const getPaddingBottom = (insetBottom: number, insetTop: number, paddingTop: number, height: number, windowHeight: number, pageY: number, positionY: number): number => {
30
+ // if SafeArea is not visible or outside the viewport or topped and not full height
31
+ if (height === 0 || (pageY === 0 && height < windowHeight)) {
32
+ return Math.max(0, insetBottom - (Math.round(windowHeight) - Math.round(height)));
33
+ }
34
+
35
+ // if SafeAreaView is not topped and not full height and not visible
36
+ if (pageY < windowHeight && pageY > height && positionY === 0) {
37
+ return 0;
38
+ };
39
+
40
+
41
+ // if SafeAreaView is topped, check for full height
42
+ if (Math.round(height) >= Math.round(windowHeight) && pageY === 0) {
43
+ // if SafeAreaView is full height and at the top without any offset
44
+ return positionY === 0 ? insetBottom : 0;
45
+ }
46
+
47
+ // if SafeAreaView is topped with margin and not full height
48
+ if (height < windowHeight && positionY === 0 && pageY <= insetTop) {
49
+ return Math.max(0, insetBottom - (windowHeight - (height + pageY)));
50
+ }
51
+
52
+ if (height < windowHeight && pageY < windowHeight && pageY > 0 && positionY > 0) {
53
+ return Math.max(0, insetBottom - (windowHeight - pageY));
54
+ }
55
+
56
+ // if SafeAreaView is not topped and not full height and is nested
57
+ if (height < windowHeight && pageY > 0 && pageY > windowHeight) {
58
+ return Math.max(0, insetBottom);
59
+ }
60
+
61
+ // Default case handling scenarios not captured above
62
+ return Math.max(0, insetBottom - (windowHeight - height + paddingTop));
63
+ }
64
+
25
65
  export default React.forwardRef<View, ViewProps>(
26
66
  ({ children, style, ...otherProps }, ref) => {
27
- const [topInset, setTopInset] = useState(
28
- safeAreaTurboModule.getInitialInsets().top
29
- );
30
- const [leftInset, setLeftInset] = useState(
31
- safeAreaTurboModule.getInitialInsets().left
32
- );
33
- const [rightInset, setRightInset] = useState(
34
- safeAreaTurboModule.getInitialInsets().right
35
- );
36
- const [bottomInset, setBottomInset] = useState(
37
- safeAreaTurboModule.getInitialInsets().bottom
38
- );
39
67
 
68
+ const safeAreaViewRef = React.useRef<View>(null);
69
+
70
+ const [topInset, setTopInset] = useState(safeAreaTurboModule.getInitialInsets().top);
71
+ const [leftInset, setLeftInset] = useState(safeAreaTurboModule.getInitialInsets().left);
72
+ const [rightInset, setRightInset] = useState(safeAreaTurboModule.getInitialInsets().right);
73
+ const [bottomInset, setBottomInset] = useState(safeAreaTurboModule.getInitialInsets().bottom);
74
+
75
+ const [measurement, setMeasurement] = useState({ x: 0, y: 0, width: 0, height: 0, pageX: 0, pageY: -1 });
76
+ const [layout, setLayout] = useState({ x: 0, y: 0, width: 0, height: 0 });
77
+
78
+ const measureView = () => {
79
+ safeAreaViewRef?.current?.measure((x, y, width, height, pageX, pageY) => {
80
+ setMeasurement({ x, y, width, height, pageX, pageY });
81
+ });
82
+ }
83
+
40
84
  useEffect(
41
85
  function subscribeToSafeAreaChanges() {
86
+
42
87
  const subscription = (RCTDeviceEventEmitter as any).addListener(
43
88
  "SAFE_AREA_INSETS_CHANGE",
44
89
  (insets: SafeAreaInsets) => {
@@ -52,21 +97,39 @@ export default React.forwardRef<View, ViewProps>(
52
97
  subscription.remove();
53
98
  };
54
99
  },
55
- [setTopInset, setLeftInset, setRightInset, setBottomInset]
100
+ [setTopInset, setLeftInset, setRightInset, setBottomInset, measurement.pageY]
56
101
  );
57
102
 
103
+ useEffect(() => {
104
+ measureView();
105
+ }, []);
106
+
107
+ const isPaddingBottomExplicit = style?.paddingBottom !== undefined;
108
+ const isPaddingTopExplicit = style?.paddingTop !== undefined;
109
+ const isPaddingLeftExplicit = style?.paddingLeft !== undefined;
110
+ const isPaddingRightExplicit = style?.paddingRight !== undefined;
111
+
112
+ const windowHeight = Dimensions.get('window').height;
113
+ const paddingTop = getPaddingTop(topInset, measurement.pageY);
114
+ const paddingBottom = getPaddingBottom(bottomInset, topInset, paddingTop, measurement.height, windowHeight, measurement.pageY, layout.y);
115
+
58
116
  return (
59
117
  <View
60
- ref={ref}
118
+ ref={safeAreaViewRef}
61
119
  style={[
62
120
  style,
63
121
  {
64
- paddingTop: topInset,
65
- paddingLeft: leftInset,
66
- paddingRight: rightInset,
67
- paddingBottom: bottomInset,
122
+ paddingTop: isPaddingTopExplicit ? style.paddingBottom : paddingTop,
123
+ paddingLeft: isPaddingLeftExplicit ? style.paddingLeft : leftInset,
124
+ paddingRight: isPaddingRightExplicit ? style.paddingRight : rightInset,
125
+ paddingBottom: isPaddingBottomExplicit ? style.paddingBottom : paddingBottom,
68
126
  },
69
127
  ]}
128
+ onLayout={(event) => {
129
+ setLayout(event.nativeEvent.layout);
130
+ measureView();
131
+ otherProps?.onLayout && otherProps.onLayout(event);
132
+ }}
70
133
  {...otherProps}
71
134
  >
72
135
  {children}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@react-native-oh/react-native-harmony",
3
- "version": "0.72.28-8",
3
+ "version": "0.72.29",
4
4
  "description": "",
5
5
  "publishConfig": {
6
6
  "registry": "https://registry.npmjs.org/",
@@ -49,7 +49,7 @@
49
49
  "./*.har"
50
50
  ],
51
51
  "dependencies": {
52
- "@react-native-oh/react-native-harmony-cli": "^0.0.26-19",
52
+ "@react-native-oh/react-native-harmony-cli": "^0.0.26-20",
53
53
  "colors": "^1.4.0",
54
54
  "fs-extra": "^11.1.1",
55
55
  "metro": "^0.76.3",
Binary file