@react-native-oh/react-native-harmony 0.72.82 → 0.77.18

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.
Files changed (81) hide show
  1. package/LICENSE +21 -0
  2. package/LICENSE-Meta +21 -0
  3. package/Libraries/Alert/delegates/AlertDelegate.harmony.ts +84 -0
  4. package/Libraries/Alert/{AlertManager.ts → delegates/AlertManager.harmony.ts} +10 -4
  5. package/Libraries/Animated/shouldUseTurboAnimatedModule.harmony.ts +10 -0
  6. package/Libraries/Components/AccessibilityInfo/delegates/AccessibilityInfoDelegate.harmony.ts +44 -0
  7. package/Libraries/Components/AccessibilityInfo/{NativeAccessibilityInfoHarmony.ts → delegates/NativeAccessibilityInfoHarmony.harmony.ts} +9 -2
  8. package/Libraries/Components/Keyboard/delegates/KeyboardAvoidingViewDelegate.harmony.ts +42 -0
  9. package/Libraries/Components/RefreshControl/delegates/RefreshControlDelegate.harmony.tsx +29 -0
  10. package/Libraries/Components/SafeAreaView/SafeAreaView.harmony.tsx +93 -31
  11. package/Libraries/Components/ScrollView/delegates/ScrollViewDelegate.harmony.tsx +41 -0
  12. package/Libraries/Components/ScrollView/delegates/ScrollViewNativeComponentDelegate.harmony.ts +89 -0
  13. package/Libraries/Components/ScrollView/processDecelerationRate.harmony.ts +19 -0
  14. package/Libraries/Components/StatusBar/delegates/NativeStatusBarManagerHarmony.harmony.ts +53 -0
  15. package/Libraries/Components/StatusBar/delegates/StatusBarDelegate.harmony.ts +83 -0
  16. package/Libraries/Components/TextInput/delegates/TextInputDelegate.harmony.tsx +98 -0
  17. package/Libraries/Components/TextInput/delegates/TextInputStateDelegate.harmony.tsx +20 -0
  18. package/Libraries/Components/Touchable/delegates/TouchableHighlightDelegate.harmony.ts +14 -0
  19. package/Libraries/Components/Touchable/delegates/TouchableNativeFeedbackDelegate.harmony.ts +14 -0
  20. package/Libraries/Components/Touchable/delegates/TouchableWithoutFeedbackDelegate.harmony.ts +14 -0
  21. package/Libraries/Components/delegates/ButtonDelegate.harmony.ts +41 -0
  22. package/Libraries/Core/setUpPlatform.harmony.js +30 -0
  23. package/Libraries/Image/AssetSourceResolver.harmony.ts +75 -29
  24. package/Libraries/Image/Image.harmony.ts +17 -0
  25. package/Libraries/NativeComponent/BaseViewConfig.harmony.js +12 -326
  26. package/Libraries/NativeComponent/delegates/ViewConfigIgnoreDelegate.harmony.ts +13 -0
  27. package/Libraries/ReactNative/delegates/BridgelessUIManagerDelegate.harmony.ts +14 -0
  28. package/Libraries/ReactNative/delegates/I18nManagerDelegate.harmony.ts +22 -0
  29. package/Libraries/Settings/Settings.harmony.ts +20 -0
  30. package/Libraries/Share/delegates/ShareDelegate.harmony.ts +42 -0
  31. package/Libraries/StyleSheet/NativePlatformColor.harmony.ts +15 -0
  32. package/Libraries/StyleSheet/PlatformColorValueTypes.harmony.ts +8 -1
  33. package/Libraries/Utilities/BackHandler.harmony.ts +10 -0
  34. package/Libraries/Utilities/NativePlatformConstantsHarmony.harmony.ts +17 -0
  35. package/Libraries/Utilities/Platform.harmony.ts +38 -13
  36. package/Libraries/Vibration/delegates/VibrationDelegate.harmony.ts +14 -0
  37. package/NOTICE.md +846 -0
  38. package/README.md +2 -2
  39. package/index.js +53 -63
  40. package/jest.config.js +0 -7
  41. package/metro.config.d.ts +17 -0
  42. package/metro.config.js +398 -115
  43. package/package.json +58 -37
  44. package/react-native.config.js +57 -9
  45. package/react_native_openharmony.har +0 -0
  46. package/tsconfig.json +10 -4
  47. package/types/index.harmony.d.ts +99 -0
  48. package/Libraries/Alert/Alert.harmony.js +0 -77
  49. package/Libraries/Animated/NativeAnimatedHelper.harmony.js +0 -601
  50. package/Libraries/Components/AccessibilityInfo/AccessibilityInfo.harmony.js +0 -441
  51. package/Libraries/Components/Button/Button.harmony.js +0 -451
  52. package/Libraries/Components/Image/Image.flow.harmony.js +0 -53
  53. package/Libraries/Components/Image/Image.harmony.js +0 -317
  54. package/Libraries/Components/Image/NativeImageLoaderHarmony.js +0 -38
  55. package/Libraries/Components/Keyboard/KeyboardAvoidingView.harmony.js +0 -256
  56. package/Libraries/Components/RefreshControl/RefreshControl.harmony.js +0 -210
  57. package/Libraries/Components/ScrollView/ScrollView.harmony.js +0 -1951
  58. package/Libraries/Components/ScrollView/processDecelerationRate.harmony.js +0 -24
  59. package/Libraries/Components/StatusBar/NativeStatusBarManagerHarmony.js +0 -71
  60. package/Libraries/Components/StatusBar/StatusBar.harmony.js +0 -447
  61. package/Libraries/Components/TextInput/TextInput.harmony.js +0 -1716
  62. package/Libraries/Components/TextInput/TextInputState.harmony.js +0 -220
  63. package/Libraries/Components/Touchable/TouchableHighlight.harmony.js +0 -396
  64. package/Libraries/Components/Touchable/TouchableNativeFeedback.harmony.js +0 -364
  65. package/Libraries/Components/Touchable/TouchableWithoutFeedback.harmony.js +0 -227
  66. package/Libraries/Components/View/View.harmony.js +0 -149
  67. package/Libraries/Core/setUpReactDevTools.harmony.js +0 -93
  68. package/Libraries/ReactNative/I18nManager.harmony.js +0 -78
  69. package/Libraries/ReactNative/UIManager.harmony.js +0 -210
  70. package/Libraries/Settings/Settings.harmony.js +0 -15
  71. package/Libraries/Share/Share.harmony.js +0 -174
  72. package/Libraries/StyleSheet/NativePlatformColor.ts +0 -8
  73. package/Libraries/Utilities/BackHandler.harmony.js +0 -109
  74. package/Libraries/Utilities/NativePlatformConstants.harmony.ts +0 -8
  75. package/Libraries/Utilities/Platform.d.ts +0 -117
  76. package/Libraries/Utilities/createPerformanceLogger.harmony.js +0 -328
  77. package/Libraries/Vibration/Vibration.harmony.js +0 -88
  78. package/harmony/.keep +0 -0
  79. package/harmony/rnoh-hvigor-plugin-0.2.0.tgz +0 -0
  80. package/react_native_openharmony_release.har +0 -0
  81. package/types/index.d.ts +0 -108
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2024 Huawei Technologies Co., Ltd.
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/LICENSE-Meta ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) Meta Platforms, Inc. and affiliates.
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,84 @@
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import type { AlertOptions } from './AlertManager.harmony';
9
+ import {
10
+ BaseAlertDelegate,
11
+ AlertDelegateButton,
12
+ AlertDelegateOptions,
13
+ AlertDelegateType,
14
+ } from './BaseAlertDelegate';
15
+ import { UnsupportedByPlatformError } from '../../../delegates/DelegateError';
16
+
17
+ export default class AlertDelegate extends BaseAlertDelegate {
18
+ override alert(
19
+ title: string,
20
+ message?: string,
21
+ buttons?: AlertDelegateButton[],
22
+ options?: AlertDelegateOptions
23
+ ): void {
24
+ const AlertManager = require('./AlertManager').default;
25
+ if (!AlertManager) {
26
+ return;
27
+ }
28
+ const alertOptions: AlertOptions = {
29
+ title: title || '',
30
+ message: message || '',
31
+ cancelable: false,
32
+ };
33
+ const constants = AlertManager.getConstants();
34
+ if (options && options.cancelable) {
35
+ alertOptions.cancelable = options.cancelable;
36
+ }
37
+ // At most three buttons. Ignore rest.
38
+ const validButtons: AlertDelegateButton[] = (
39
+ buttons ?? [{ text: 'OK' }]
40
+ ).slice(0, 3);
41
+ const tertiaryButton = validButtons.pop();
42
+ const secondaryButton = validButtons.pop();
43
+ const primaryButton = validButtons.pop();
44
+ if (primaryButton) {
45
+ alertOptions.primaryButton = primaryButton.text || '';
46
+ }
47
+ if (secondaryButton) {
48
+ alertOptions.secondaryButton = secondaryButton.text || '';
49
+ }
50
+ if (tertiaryButton) {
51
+ alertOptions.tertiaryButton = tertiaryButton.text || '';
52
+ }
53
+ const onAction = (
54
+ action: 'buttonClicked' | 'dismissed',
55
+ buttonKey: number
56
+ ) => {
57
+ if (action === constants.buttonClicked) {
58
+ if (buttonKey === constants.primaryButton) {
59
+ primaryButton?.onPress && primaryButton.onPress();
60
+ } else if (buttonKey === constants.secondaryButton) {
61
+ secondaryButton?.onPress && secondaryButton.onPress();
62
+ } else if (buttonKey === constants.tertiaryButton) {
63
+ tertiaryButton?.onPress && tertiaryButton.onPress();
64
+ }
65
+ } else if (action === constants.dismissed) {
66
+ options && options.onDismiss && options.onDismiss();
67
+ }
68
+ };
69
+ const onError = (errorMessage: string) => console.warn(errorMessage);
70
+ AlertManager.alert(alertOptions, onError, onAction);
71
+ }
72
+
73
+ override prompt(
74
+ title: string,
75
+ message?: string,
76
+ callbackOrButtons?: ((text: string) => void) | AlertDelegateButton[],
77
+ type?: AlertDelegateType,
78
+ defaultValue?: string,
79
+ keyboardType?: string,
80
+ options?: AlertDelegateOptions
81
+ ): void {
82
+ throw new UnsupportedByPlatformError();
83
+ }
84
+ }
@@ -1,13 +1,19 @@
1
- import type { TurboModule } from "react-native/Libraries/TurboModule/RCTExport";
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
2
7
 
3
- import * as TurboModuleRegistry from "react-native/Libraries/TurboModule/TurboModuleRegistry";
8
+ import type { TurboModule } from '../../TurboModule/RCTExport';
9
+ import * as TurboModuleRegistry from '../../TurboModule/TurboModuleRegistry';
4
10
 
5
11
  /* 'buttonClicked' | 'dismissed' */
6
12
  type AlertAction = string;
7
13
  /*
8
14
  primaryButton = 1,
9
15
  secondaryButton = 2,
10
- tertiaryButton = 3,
16
+ thirdaryButton = 3,
11
17
  */
12
18
  type AlertButtonKey = number;
13
19
  export type AlertOptions = {
@@ -35,4 +41,4 @@ export interface Spec extends TurboModule {
35
41
  ) => void;
36
42
  }
37
43
 
38
- export default TurboModuleRegistry.get<Spec>("AlertManager");
44
+ export default TurboModuleRegistry.get<Spec>('AlertManager');
@@ -0,0 +1,10 @@
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ export default function shouldUseTurboAnimatedModule() {
9
+ return true;
10
+ }
@@ -0,0 +1,44 @@
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import { BaseAccessibilityInfoDelegate } from './BaseAccessibilityInfoDelegate';
9
+ import NativeAccessibilityInfoHarmony from './NativeAccessibilityInfoHarmony.harmony';
10
+
11
+ export default class AccessibilityInfoDelegate extends BaseAccessibilityInfoDelegate {
12
+ override isBoldTextEnabled(): Promise<boolean> {
13
+ return NativeAccessibilityInfoHarmony!.isBoldTextEnabled();
14
+ }
15
+
16
+ override isScreenReaderEnabled(): Promise<boolean> {
17
+ return NativeAccessibilityInfoHarmony!.isScreenReaderEnabled();
18
+ }
19
+
20
+ override isAccessibilityServiceEnabled(): Promise<boolean> {
21
+ return NativeAccessibilityInfoHarmony!.isAccessibilityServiceEnabled();
22
+ }
23
+
24
+ override setAccessibilityFocus(reactTag: number): void {
25
+ NativeAccessibilityInfoHarmony!.setAccessibilityFocus(reactTag);
26
+ }
27
+
28
+ override announceForAccessibility(announcement: string): void {
29
+ NativeAccessibilityInfoHarmony!.announceForAccessibility(announcement);
30
+ }
31
+
32
+ override announceForAccessibilityWithOptions(
33
+ announcement: string,
34
+ options: { queue?: boolean }
35
+ ) {
36
+ // NOOP
37
+ }
38
+
39
+ override async getRecommendedTimeoutMillis(
40
+ originalTimeout: number
41
+ ): Promise<number> {
42
+ return 0;
43
+ }
44
+ }
@@ -1,5 +1,12 @@
1
- import { TurboModuleRegistry } from 'react-native';
2
- import type { TurboModule } from 'react-native/Libraries/TurboModule/RCTExport';
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import * as TurboModuleRegistry from '../../../TurboModule/TurboModuleRegistry';
9
+ import type { TurboModule } from '../../../TurboModule/RCTExport';
3
10
 
4
11
  export interface Spec extends TurboModule {
5
12
  isScreenReaderEnabled: () => Promise<boolean>;
@@ -0,0 +1,42 @@
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import React, { ReactNode } from 'react';
9
+ import { KeyboardMetrics } from '../../Keyboard/Keyboard';
10
+ import {
11
+ BaseKeyboardAvoidingViewDelegate,
12
+ PrepareChildrenOptions,
13
+ } from './BaseKeyboardAvoidingViewDelegate';
14
+
15
+ export default class KeyboardAvoidingViewDelegate extends BaseKeyboardAvoidingViewDelegate {
16
+ override getRelativeKeyboardHeight(
17
+ keyboardFrame: KeyboardMetrics
18
+ ): number | null {
19
+ if (this.ctx.getProps().enabled === false) {
20
+ return 0;
21
+ }
22
+ return super.getRelativeKeyboardHeight(keyboardFrame);
23
+ }
24
+
25
+ override prepareChildren(
26
+ children: ReactNode,
27
+ options: PrepareChildrenOptions
28
+ ): ReactNode {
29
+ const behavior = this.ctx.getProps().behavior;
30
+ if (behavior === 'height' || behavior === 'padding') {
31
+ return React.Children.map(children, (child) => {
32
+ if (!React.isValidElement(child)) {
33
+ return child;
34
+ }
35
+ return React.cloneElement(child, {
36
+ __keyboardAvoidingViewBottomHeight: options.bottomHeight ?? 0,
37
+ } as any);
38
+ });
39
+ }
40
+ return children;
41
+ }
42
+ }
@@ -0,0 +1,29 @@
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import {
9
+ BaseRefreshControlDelegate,
10
+ RefreshControlDelegateRenderInternalProps,
11
+ } from './BaseRefreshControlDelegate';
12
+
13
+ import PullToRefreshViewNativeComponent, {
14
+ Commands,
15
+ // @ts-ignore
16
+ } from '../PullToRefreshViewNativeComponent';
17
+
18
+ export default class RefreshControlDelegate extends BaseRefreshControlDelegate<any> {
19
+ override onSetNativeRefreshing(ref: unknown, refreshing: boolean): void {
20
+ Commands.setNativeRefreshing(ref, refreshing);
21
+ }
22
+
23
+ override renderNativeComponent(
24
+ internalProps: RefreshControlDelegateRenderInternalProps<any>
25
+ ): React.ReactNode {
26
+ const { colors, ...props } = this.ctx.getProps();
27
+ return <PullToRefreshViewNativeComponent {...internalProps} {...props} />;
28
+ }
29
+ }
@@ -1,9 +1,19 @@
1
- import type { TurboModule } from "react-native/Libraries/TurboModule/RCTExport";
2
- import { Dimensions, TurboModuleRegistry, View, ViewProps } from "react-native";
3
- import { useEffect, useState } from "react";
4
- import React from "react";
5
-
6
- import RCTDeviceEventEmitter from "react-native/Libraries/EventEmitter/RCTDeviceEventEmitter.js";
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import type { TurboModule } from '../../TurboModule/RCTExport';
9
+ import * as TurboModuleRegistry from '../../TurboModule/TurboModuleRegistry';
10
+ import { ViewProps } from '../View/ViewPropTypes';
11
+ import Dimensions from '../../Utilities/Dimensions';
12
+ import View from '../View/View';
13
+ import { useEffect, useState } from 'react';
14
+ import React from 'react';
15
+
16
+ import RCTDeviceEventEmitter from '../../EventEmitter/RCTDeviceEventEmitter.js';
7
17
 
8
18
  type SafeAreaInsets = {
9
19
  top: number;
@@ -19,77 +29,111 @@ interface SafeAreaTurboModuleProtocol {
19
29
  interface Spec extends TurboModule, SafeAreaTurboModuleProtocol {}
20
30
 
21
31
  const safeAreaTurboModule = TurboModuleRegistry.get<Spec>(
22
- "SafeAreaTurboModule"
32
+ 'SafeAreaTurboModule'
23
33
  )!;
24
34
 
25
35
  const getPaddingTop = (inset: number, pageY: number) => {
26
36
  return Math.max(0, inset - (pageY < 0 ? pageY * -1 : pageY));
27
- }
37
+ };
28
38
 
29
- const getPaddingBottom = (insetBottom: number, insetTop: number, paddingTop: number, height: number, windowHeight: number, pageY: number, positionY: number): number => {
39
+ const getPaddingBottom = (
40
+ insetBottom: number,
41
+ insetTop: number,
42
+ paddingTop: number,
43
+ height: number,
44
+ windowHeight: number,
45
+ pageY: number,
46
+ positionY: number
47
+ ): number => {
30
48
  // if SafeArea is not visible or outside the viewport or topped and not full height
31
49
  if (height === 0 || (pageY === 0 && height < windowHeight)) {
32
- return Math.max(0, insetBottom - (Math.round(windowHeight) - Math.round(height)));
50
+ return Math.max(
51
+ 0,
52
+ insetBottom - (Math.round(windowHeight) - Math.round(height))
53
+ );
33
54
  }
34
55
 
35
56
  // if SafeAreaView is not topped and not full height and not visible
36
57
  if (pageY < windowHeight && pageY > height && positionY === 0) {
37
58
  return 0;
38
- };
59
+ }
39
60
 
40
-
41
61
  // if SafeAreaView is topped, check for full height
42
62
  if (Math.round(height) >= Math.round(windowHeight) && pageY === 0) {
43
63
  // if SafeAreaView is full height and at the top without any offset
44
64
  return positionY === 0 ? insetBottom : 0;
45
65
  }
46
-
66
+
47
67
  // if SafeAreaView is topped with margin and not full height
48
68
  if (height < windowHeight && positionY === 0 && pageY <= insetTop) {
49
69
  return Math.max(0, insetBottom - (windowHeight - (height + pageY)));
50
70
  }
51
71
 
52
- if (height < windowHeight && pageY < windowHeight && pageY > 0 && positionY > 0) {
72
+ if (
73
+ height < windowHeight &&
74
+ pageY < windowHeight &&
75
+ pageY > 0 &&
76
+ positionY > 0
77
+ ) {
53
78
  return Math.max(0, insetBottom - (windowHeight - pageY));
54
79
  }
55
80
 
56
81
  // if SafeAreaView nested and outside of the current viewport - for example in scroll view
57
- if (height < windowHeight && pageY > 0 && pageY > windowHeight && positionY >= 0) {
82
+ if (
83
+ height < windowHeight &&
84
+ pageY > 0 &&
85
+ pageY > windowHeight &&
86
+ positionY >= 0
87
+ ) {
58
88
  return 0;
59
89
  }
90
+
60
91
  // if SafeAreaView is nested outside of the viewport - but on absolute position
61
92
  if (height < windowHeight && pageY > 0 && pageY > windowHeight) {
62
93
  return insetBottom;
63
94
  }
64
-
95
+
65
96
  // Default case handling scenarios not captured above
66
97
  return Math.max(0, insetBottom - (windowHeight - height + paddingTop));
67
- }
98
+ };
68
99
 
69
100
  export default React.forwardRef<View, ViewProps>(
70
101
  ({ children, style, ...otherProps }, ref) => {
71
-
72
102
  const safeAreaViewRef = React.useRef<View>(null);
73
103
 
74
- const [topInset, setTopInset] = useState(safeAreaTurboModule.getInitialInsets().top);
75
- const [leftInset, setLeftInset] = useState(safeAreaTurboModule.getInitialInsets().left);
76
- const [rightInset, setRightInset] = useState(safeAreaTurboModule.getInitialInsets().right);
77
- const [bottomInset, setBottomInset] = useState(safeAreaTurboModule.getInitialInsets().bottom);
104
+ const [topInset, setTopInset] = useState(
105
+ safeAreaTurboModule.getInitialInsets().top
106
+ );
107
+ const [leftInset, setLeftInset] = useState(
108
+ safeAreaTurboModule.getInitialInsets().left
109
+ );
110
+ const [rightInset, setRightInset] = useState(
111
+ safeAreaTurboModule.getInitialInsets().right
112
+ );
113
+ const [bottomInset, setBottomInset] = useState(
114
+ safeAreaTurboModule.getInitialInsets().bottom
115
+ );
78
116
 
79
- const [measurement, setMeasurement] = useState({ x: 0, y: 0, width: 0, height: 0, pageX: 0, pageY: -1 });
117
+ const [measurement, setMeasurement] = useState({
118
+ x: 0,
119
+ y: 0,
120
+ width: 0,
121
+ height: 0,
122
+ pageX: 0,
123
+ pageY: -1,
124
+ });
80
125
  const [layout, setLayout] = useState({ x: 0, y: 0, width: 0, height: 0 });
81
126
 
82
127
  const measureView = () => {
83
128
  safeAreaViewRef?.current?.measure((x, y, width, height, pageX, pageY) => {
84
129
  setMeasurement({ x, y, width, height, pageX, pageY });
85
130
  });
86
- }
87
-
131
+ };
132
+
88
133
  useEffect(
89
134
  function subscribeToSafeAreaChanges() {
90
-
91
135
  const subscription = (RCTDeviceEventEmitter as any).addListener(
92
- "SAFE_AREA_INSETS_CHANGE",
136
+ 'SAFE_AREA_INSETS_CHANGE',
93
137
  (insets: SafeAreaInsets) => {
94
138
  setTopInset(insets.top);
95
139
  setBottomInset(insets.bottom);
@@ -101,7 +145,13 @@ export default React.forwardRef<View, ViewProps>(
101
145
  subscription.remove();
102
146
  };
103
147
  },
104
- [setTopInset, setLeftInset, setRightInset, setBottomInset, measurement.pageY]
148
+ [
149
+ setTopInset,
150
+ setLeftInset,
151
+ setRightInset,
152
+ setBottomInset,
153
+ measurement.pageY,
154
+ ]
105
155
  );
106
156
 
107
157
  useEffect(() => {
@@ -115,7 +165,15 @@ export default React.forwardRef<View, ViewProps>(
115
165
 
116
166
  const windowHeight = Dimensions.get('window').height;
117
167
  const paddingTop = getPaddingTop(topInset, measurement.pageY);
118
- const paddingBottom = getPaddingBottom(bottomInset, topInset, paddingTop, measurement.height, windowHeight, measurement.pageY, layout.y);
168
+ const paddingBottom = getPaddingBottom(
169
+ bottomInset,
170
+ topInset,
171
+ paddingTop,
172
+ measurement.height,
173
+ windowHeight,
174
+ measurement.pageY,
175
+ layout.y
176
+ );
119
177
 
120
178
  return (
121
179
  <View
@@ -125,8 +183,12 @@ export default React.forwardRef<View, ViewProps>(
125
183
  {
126
184
  paddingTop: isPaddingTopExplicit ? style.paddingBottom : paddingTop,
127
185
  paddingLeft: isPaddingLeftExplicit ? style.paddingLeft : leftInset,
128
- paddingRight: isPaddingRightExplicit ? style.paddingRight : rightInset,
129
- paddingBottom: isPaddingBottomExplicit ? style.paddingBottom : paddingBottom,
186
+ paddingRight: isPaddingRightExplicit
187
+ ? style.paddingRight
188
+ : rightInset,
189
+ paddingBottom: isPaddingBottomExplicit
190
+ ? style.paddingBottom
191
+ : paddingBottom,
130
192
  },
131
193
  ]}
132
194
  onLayout={(event) => {
@@ -0,0 +1,41 @@
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import React from 'react';
9
+ import StyleSheet from '../../../StyleSheet/StyleSheet';
10
+ import {
11
+ BaseScrollViewDelegate,
12
+ RenderScrollViewWithRefreshControlArgs,
13
+ } from './BaseScrollViewDelegate';
14
+ // @ts-ignore
15
+ import flattenStyle from '../../../StyleSheet/flattenStyle';
16
+ // @ts-ignore
17
+ import splitLayoutProps from '../../../StyleSheet/splitLayoutProps';
18
+
19
+ export default class ScrollViewDelegate extends BaseScrollViewDelegate {
20
+ override renderScrollViewWithRefreshControl({
21
+ NativeScrollView,
22
+ contentContainer,
23
+ props,
24
+ refreshControl,
25
+ scrollViewRef,
26
+ baseStyle,
27
+ }: RenderScrollViewWithRefreshControlArgs): React.ReactNode {
28
+ const { outer, inner } = splitLayoutProps(flattenStyle(props.style));
29
+ return React.cloneElement(
30
+ refreshControl,
31
+ { style: (StyleSheet as any).compose(baseStyle, outer) },
32
+ <NativeScrollView
33
+ {...props}
34
+ style={(StyleSheet as any).compose(baseStyle, inner)}
35
+ ref={scrollViewRef}
36
+ >
37
+ {contentContainer}
38
+ </NativeScrollView>
39
+ );
40
+ }
41
+ }
@@ -0,0 +1,89 @@
1
+ /**
2
+ * @format
3
+ */
4
+
5
+ import { BaseScrollViewNativeComponentDelegate } from './BaseScrollViewNativeComponentDelegate';
6
+
7
+ export default class ScrollViewNativeComponentDelegate extends BaseScrollViewNativeComponentDelegate {
8
+ override getIntenalViewConfig() {
9
+ return {
10
+ uiViewClassName: 'RCTScrollView',
11
+ bubblingEventTypes: {},
12
+ directEventTypes: {
13
+ topMomentumScrollBegin: {
14
+ registrationName: 'onMomentumScrollBegin',
15
+ },
16
+ topMomentumScrollEnd: {
17
+ registrationName: 'onMomentumScrollEnd',
18
+ },
19
+ topScroll: {
20
+ registrationName: 'onScroll',
21
+ },
22
+ topScrollBeginDrag: {
23
+ registrationName: 'onScrollBeginDrag',
24
+ },
25
+ topScrollEndDrag: {
26
+ registrationName: 'onScrollEndDrag',
27
+ },
28
+ },
29
+ validAttributes: {
30
+ alwaysBounceHorizontal: true,
31
+ alwaysBounceVertical: true,
32
+ bounces: true,
33
+ centerContent: true,
34
+ contentOffset: {
35
+ diff: require('../../../Utilities/differ/pointsDiffer'),
36
+ },
37
+ decelerationRate: true,
38
+ disableIntervalMomentum: true,
39
+ indicatorStyle: true,
40
+ inverted: true,
41
+ keyboardDismissMode: true,
42
+ maintainVisibleContentPosition: true,
43
+ pagingEnabled: true,
44
+ scrollEnabled: true,
45
+ showsHorizontalScrollIndicator: true,
46
+ showsVerticalScrollIndicator: true,
47
+ snapToAlignment: true,
48
+ snapToEnd: true,
49
+ snapToInterval: true,
50
+ snapToOffsets: true,
51
+ snapToStart: true,
52
+ borderBottomLeftRadius: true,
53
+ borderBottomRightRadius: true,
54
+ sendMomentumEvents: true,
55
+ borderRadius: true,
56
+ nestedScrollEnabled: true,
57
+ scrollEventThrottle: true,
58
+ scrollToOverflowEnabled: true,
59
+ borderStyle: true,
60
+ borderRightColor: {
61
+ process: require('../../../StyleSheet/processColor').default,
62
+ },
63
+ borderColor: {
64
+ process: require('../../../StyleSheet/processColor').default,
65
+ },
66
+ borderBottomColor: {
67
+ process: require('../../../StyleSheet/processColor').default,
68
+ },
69
+ persistentScrollbar: true,
70
+ horizontal: true,
71
+ endFillColor: {
72
+ process: require('../../../StyleSheet/processColor').default,
73
+ },
74
+ overScrollMode: true,
75
+ borderTopLeftRadius: true,
76
+ borderTopColor: {
77
+ process: require('../../../StyleSheet/processColor').default,
78
+ },
79
+ removeClippedSubviews: true,
80
+ borderTopRightRadius: true,
81
+ borderLeftColor: {
82
+ process: require('../../../StyleSheet/processColor').default,
83
+ },
84
+ pointerEvents: true,
85
+ isInvertedVirtualizedList: true,
86
+ },
87
+ };
88
+ }
89
+ }
@@ -0,0 +1,19 @@
1
+ /**
2
+ * Copyright (c) 2024 Huawei Technologies Co., Ltd.
3
+ *
4
+ * This source code is licensed under the MIT license found in the
5
+ * LICENSE file in the root directory of this source tree.
6
+ */
7
+
8
+ import { DecelerationRateType } from '../ScrollView/delegates/types';
9
+
10
+ export default function processDecelerationRate(
11
+ decelerationRate: DecelerationRateType
12
+ ): number {
13
+ if (decelerationRate === 'normal') {
14
+ return 0.998;
15
+ } else if (decelerationRate === 'fast') {
16
+ return 0.99;
17
+ }
18
+ return decelerationRate;
19
+ }