react-native-tvos 0.83.9-0 → 0.83.10-0

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 (159) hide show
  1. package/Libraries/ActionSheetIOS/React-RCTActionSheet.podspec +1 -1
  2. package/Libraries/Animated/components/AnimatedScrollView.js +1 -1
  3. package/Libraries/AppDelegate/React-RCTAppDelegate.podspec +1 -1
  4. package/Libraries/Blob/React-RCTBlob.podspec +1 -1
  5. package/Libraries/Components/Button.js +2 -2
  6. package/Libraries/Components/ScrollView/ScrollView.d.ts +1 -1
  7. package/Libraries/Components/ScrollView/ScrollView.js +1 -1
  8. package/Libraries/Components/TV/TVViewPropTypes.js +9 -0
  9. package/Libraries/Components/TextInput/AndroidTextInputNativeComponent.js +1 -1
  10. package/Libraries/Components/TextInput/TextInput.flow.js +1 -1
  11. package/Libraries/Components/Touchable/Touchable.d.ts +1 -1
  12. package/Libraries/Components/View/View.js +7 -3
  13. package/Libraries/Components/View/ViewAccessibility.d.ts +1 -1
  14. package/Libraries/Components/View/ViewAccessibility.js +1 -1
  15. package/Libraries/Core/ReactNativeVersion.js +1 -1
  16. package/Libraries/Core/Timers/JSTimers.js +1 -1
  17. package/Libraries/Core/setUpNavigator.js +1 -1
  18. package/Libraries/EventEmitter/RCTNativeAppEventEmitter.d.ts +1 -1
  19. package/Libraries/FBLazyVector/FBLazyVector.podspec +1 -1
  20. package/Libraries/Image/ImageSource.d.ts +1 -1
  21. package/Libraries/Image/RCTImageLoader.mm +1 -1
  22. package/Libraries/Image/React-RCTImage.podspec +1 -1
  23. package/Libraries/Interaction/PanResponder.js +1 -1
  24. package/Libraries/LinkingIOS/React-RCTLinking.podspec +1 -1
  25. package/Libraries/NativeAnimation/React-RCTAnimation.podspec +1 -1
  26. package/Libraries/NativeComponent/TVViewConfig.js +1 -0
  27. package/Libraries/Network/React-RCTNetwork.podspec +1 -1
  28. package/Libraries/PushNotificationIOS/React-RCTPushNotification.podspec +1 -1
  29. package/Libraries/Renderer/README.md +2 -2
  30. package/Libraries/Required/RCTRequired.podspec +1 -1
  31. package/Libraries/Settings/React-RCTSettings.podspec +1 -1
  32. package/Libraries/Text/React-RCTText.podspec +1 -1
  33. package/Libraries/TypeSafety/RCTTypeSafety.podspec +1 -1
  34. package/Libraries/Utilities/PolyfillFunctions.js +1 -1
  35. package/Libraries/Vibration/React-RCTVibration.podspec +1 -1
  36. package/README-core.md +6 -6
  37. package/README.md +13 -1
  38. package/React/Base/RCTVersion.m +1 -1
  39. package/React/CoreModules/React-CoreModules.podspec +1 -1
  40. package/React/Fabric/Mounting/ComponentViews/ScrollView/RCTScrollViewComponentView.mm +49 -17
  41. package/React/Fabric/Mounting/ComponentViews/TextInput/RCTTextInputComponentView.mm +12 -1
  42. package/React/Fabric/Mounting/ComponentViews/View/RCTViewComponentView.mm +34 -5
  43. package/React/React-RCTFBReactNativeSpec.podspec +1 -1
  44. package/React/React-RCTFabric.podspec +1 -1
  45. package/React/Runtime/React-RCTRuntime.podspec +1 -1
  46. package/React/Tests/Mounting/RCTViewComponentViewTests.mm +145 -0
  47. package/React/Views/ScrollView/RCTScrollView.m +1 -1
  48. package/React-Core.podspec +1 -1
  49. package/React.podspec +1 -1
  50. package/ReactAndroid/build.gradle.kts +1 -1
  51. package/ReactAndroid/gradle.properties +1 -1
  52. package/ReactAndroid/hermes-engine/build.gradle.kts +6 -0
  53. package/ReactAndroid/publish.gradle +5 -5
  54. package/ReactAndroid/src/main/java/com/facebook/react/devsupport/CxxInspectorPackagerConnection.kt +99 -9
  55. package/ReactAndroid/src/main/java/com/facebook/react/devsupport/inspector/InspectorNetworkHelper.kt +1 -1
  56. package/ReactAndroid/src/main/java/com/facebook/react/fabric/mounting/SurfaceMountingManager.java +2 -2
  57. package/ReactAndroid/src/main/java/com/facebook/react/modules/core/JavaTimerManager.kt +1 -1
  58. package/ReactAndroid/src/main/java/com/facebook/react/modules/core/ReactAndroidHWInputDeviceHelper.java +1 -0
  59. package/ReactAndroid/src/main/java/com/facebook/react/modules/intent/IntentModule.kt +1 -1
  60. package/ReactAndroid/src/main/java/com/facebook/react/modules/network/NetworkingModule.kt +3 -3
  61. package/ReactAndroid/src/main/java/com/facebook/react/modules/systeminfo/ReactNativeVersion.kt +1 -1
  62. package/ReactAndroid/src/main/java/com/facebook/react/runtime/ReactInstance.kt +1 -1
  63. package/ReactAndroid/src/main/java/com/facebook/react/uimanager/BaseViewManager.java +1 -1
  64. package/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactHorizontalScrollView.java +14 -4
  65. package/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollView.java +14 -4
  66. package/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewHelper.kt +46 -6
  67. package/ReactAndroid/src/main/java/com/facebook/react/views/scroll/ReactScrollViewManager.kt +1 -1
  68. package/ReactAndroid/src/main/java/com/facebook/react/views/text/ReactTextView.java +1 -1
  69. package/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactEditText.kt +2 -2
  70. package/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextInputManager.kt +2 -2
  71. package/ReactAndroid/src/main/java/com/facebook/react/views/textinput/ReactTextSelectionWatcher.kt +1 -1
  72. package/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewGroup.kt +1 -0
  73. package/ReactAndroid/src/main/java/com/facebook/react/views/view/ReactViewManager.kt +5 -0
  74. package/ReactAndroid/src/main/jni/react/devsupport/JCxxInspectorPackagerConnectionWebSocket.cpp +29 -2
  75. package/ReactApple/Libraries/RCTFoundation/RCTDeprecation/RCTDeprecation.podspec +1 -1
  76. package/ReactApple/RCTSwiftUI/RCTSwiftUI.podspec +1 -1
  77. package/ReactApple/RCTSwiftUIWrapper/RCTSwiftUIWrapper.podspec +1 -1
  78. package/ReactCommon/React-Fabric.podspec +1 -1
  79. package/ReactCommon/React-FabricComponents.podspec +1 -1
  80. package/ReactCommon/React-FabricImage.podspec +1 -1
  81. package/ReactCommon/React-Mapbuffer.podspec +1 -1
  82. package/ReactCommon/ReactCommon.podspec +1 -1
  83. package/ReactCommon/callinvoker/React-callinvoker.podspec +1 -1
  84. package/ReactCommon/cxxreact/React-cxxreact.podspec +1 -1
  85. package/ReactCommon/cxxreact/ReactNativeVersion.h +2 -2
  86. package/ReactCommon/hermes/React-hermes.podspec +1 -1
  87. package/ReactCommon/hermes/executor/React-jsitracing.podspec +1 -1
  88. package/ReactCommon/jserrorhandler/React-jserrorhandler.podspec +1 -1
  89. package/ReactCommon/jsi/React-jsi.podspec +1 -1
  90. package/ReactCommon/jsiexecutor/React-jsiexecutor.podspec +1 -1
  91. package/ReactCommon/jsinspector-modern/InspectorInterfaces.cpp +7 -3
  92. package/ReactCommon/jsinspector-modern/React-jsinspector.podspec +1 -1
  93. package/ReactCommon/jsinspector-modern/TracingAgent.cpp +1 -5
  94. package/ReactCommon/jsinspector-modern/cdp/React-jsinspectorcdp.podspec +1 -1
  95. package/ReactCommon/jsinspector-modern/network/React-jsinspectornetwork.podspec +1 -1
  96. package/ReactCommon/jsinspector-modern/tracing/React-jsinspectortracing.podspec +1 -1
  97. package/ReactCommon/jsitooling/React-jsitooling.podspec +1 -1
  98. package/ReactCommon/logger/React-logger.podspec +1 -1
  99. package/ReactCommon/oscompat/React-oscompat.podspec +1 -1
  100. package/ReactCommon/react/debug/React-debug.podspec +1 -1
  101. package/ReactCommon/react/debug/redbox/JscSafeUrl.h +1 -1
  102. package/ReactCommon/react/featureflags/React-featureflags.podspec +1 -1
  103. package/ReactCommon/react/nativemodule/core/platform/android/ReactCommon/JavaTurboModule.cpp +1 -1
  104. package/ReactCommon/react/nativemodule/core/platform/ios/React-NativeModulesApple.podspec +1 -1
  105. package/ReactCommon/react/nativemodule/core/platform/ios/ReactCommon/RCTInteropTurboModule.mm +1 -1
  106. package/ReactCommon/react/nativemodule/core/platform/ios/ReactCommon/RCTTurboModule.mm +1 -1
  107. package/ReactCommon/react/nativemodule/defaults/React-defaultsnativemodule.podspec +1 -1
  108. package/ReactCommon/react/nativemodule/dom/React-domnativemodule.podspec +1 -1
  109. package/ReactCommon/react/nativemodule/featureflags/React-featureflagsnativemodule.podspec +1 -1
  110. package/ReactCommon/react/nativemodule/idlecallbacks/React-idlecallbacksnativemodule.podspec +1 -1
  111. package/ReactCommon/react/nativemodule/intersectionobserver/React-intersectionobservernativemodule.podspec +1 -1
  112. package/ReactCommon/react/nativemodule/microtasks/React-microtasksnativemodule.podspec +1 -1
  113. package/ReactCommon/react/nativemodule/mutationobserver/React-mutationobservernativemodule.podspec +1 -1
  114. package/ReactCommon/react/nativemodule/samples/ReactCommon-Samples.podspec +1 -1
  115. package/ReactCommon/react/nativemodule/webperformance/React-webperformancenativemodule.podspec +1 -1
  116. package/ReactCommon/react/networking/React-networking.podspec +1 -1
  117. package/ReactCommon/react/performance/cdpmetrics/React-performancecdpmetrics.podspec +1 -1
  118. package/ReactCommon/react/performance/timeline/React-performancetimeline.podspec +1 -1
  119. package/ReactCommon/react/renderer/animated/internal/primitives.h +1 -1
  120. package/ReactCommon/react/renderer/components/view/BaseViewProps.cpp +7 -0
  121. package/ReactCommon/react/renderer/components/view/BaseViewProps.h +1 -0
  122. package/ReactCommon/react/renderer/components/view/platform/android/react/renderer/components/view/HostPlatformViewProps.cpp +18 -0
  123. package/ReactCommon/react/renderer/components/view/platform/android/react/renderer/components/view/HostPlatformViewProps.h +1 -0
  124. package/ReactCommon/react/renderer/consistency/React-rendererconsistency.podspec +1 -1
  125. package/ReactCommon/react/renderer/css/React-renderercss.podspec +1 -1
  126. package/ReactCommon/react/renderer/debug/React-rendererdebug.podspec +1 -1
  127. package/ReactCommon/react/renderer/graphics/React-graphics.podspec +1 -1
  128. package/ReactCommon/react/renderer/imagemanager/platform/ios/React-ImageManager.podspec +1 -1
  129. package/ReactCommon/react/renderer/mounting/internal/CullingContext.cpp +1 -1
  130. package/ReactCommon/react/renderer/runtimescheduler/React-runtimescheduler.podspec +1 -1
  131. package/ReactCommon/react/runtime/React-RuntimeCore.podspec +1 -1
  132. package/ReactCommon/react/runtime/React-RuntimeHermes.podspec +1 -1
  133. package/ReactCommon/react/runtime/platform/ios/React-RuntimeApple.podspec +1 -1
  134. package/ReactCommon/react/timing/React-timing.podspec +1 -1
  135. package/ReactCommon/react/utils/React-utils.podspec +1 -1
  136. package/ReactCommon/reactperflogger/React-perflogger.podspec +1 -1
  137. package/ReactCommon/runtimeexecutor/React-runtimeexecutor.podspec +1 -1
  138. package/ReactCommon/yoga/Yoga.podspec +2 -2
  139. package/ReactCommon/yoga/yoga/algorithm/AbsoluteLayout.cpp +2 -0
  140. package/ReactCommon/yoga/yoga/algorithm/CalculateLayout.cpp +11 -7
  141. package/ReactCommon/yoga/yoga/algorithm/CalculateLayout.h +2 -0
  142. package/ReactCommon/yoga/yoga/node/Node.cpp +6 -1
  143. package/package.json +9 -9
  144. package/scripts/cocoapods/rncore.rb +26 -8
  145. package/scripts/cocoapods/rndependencies.rb +26 -5
  146. package/scripts/cocoapods/spm.rb +1 -1
  147. package/scripts/cocoapods/utils.rb +2 -2
  148. package/scripts/codegen/templates/ReactAppDependencyProvider.podspec.template +1 -1
  149. package/scripts/codegen/templates/ReactCodegen.podspec.template +1 -1
  150. package/scripts/ios-configure-glog.sh +1 -1
  151. package/sdks/hermes-engine/hermes-engine.podspec +6 -1
  152. package/sdks/hermes-engine/hermes-utils.rb +27 -5
  153. package/src/private/types/HostInstance.js +1 -1
  154. package/src/types/globals.d.ts +2 -2
  155. package/third-party-podspecs/RCT-Folly.podspec +1 -1
  156. package/third-party-podspecs/ReactNativeDependencies.podspec +1 -1
  157. package/third-party-podspecs/glog.podspec +1 -1
  158. package/types/public/ReactNativeTVTypes.d.ts +9 -0
  159. package/types/public/ReactNativeTypes.d.ts +2 -2
@@ -775,12 +775,23 @@ static NSSet<NSNumber *> *returnKeyTypesSet;
775
775
 
776
776
  - (void)_setAttributedString:(NSAttributedString *)attributedString
777
777
  {
778
+ #if TARGET_OS_TV
779
+ // Attribute-free string prevents the tvOS keyboard from inheriting the component's small font.
780
+ if ([attributedString.string isEqualToString:_backedTextInputView.attributedText.string]) {
781
+ return;
782
+ }
783
+ #else
778
784
  if ([self _textOf:attributedString equals:_backedTextInputView.attributedText]) {
779
785
  return;
780
786
  }
787
+ #endif
781
788
  UITextRange *selectedRange = _backedTextInputView.selectedTextRange;
782
789
  NSInteger oldTextLength = _backedTextInputView.attributedText.string.length;
790
+ #if TARGET_OS_TV
791
+ _backedTextInputView.attributedText = [[NSAttributedString alloc] initWithString:attributedString.string];
792
+ #else
783
793
  _backedTextInputView.attributedText = attributedString;
794
+ #endif
784
795
  // Updating the UITextView attributedText, for example changing the lineHeight, the color or adding
785
796
  // a new paragraph with \n, causes the cursor to move to the end of the Text and scroll.
786
797
  // This is fixed by restoring the cursor position and scrolling to that position (iOS issue 652653).
@@ -805,7 +816,7 @@ static NSSet<NSNumber *> *returnKeyTypesSet;
805
816
  // Ensure that newly typed text will inherit any custom attributes. We follow the logic of RN Android, where attributes
806
817
  // to the left of the cursor are copied into new text, unless we are at the start of the field, in which case we will
807
818
  // copy the attributes from text to the right. This allows consistency between backed input and new AttributedText
808
- // https://github.com/facebook/react-native/blob/3102a58df38d96f3dacef0530e4dbb399037fcd2/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/internal/span/SetSpanOperation.kt#L30
819
+ // https://github.com/react/react-native/blob/3102a58df38d96f3dacef0530e4dbb399037fcd2/packages/react-native/ReactAndroid/src/main/java/com/facebook/react/views/text/internal/span/SetSpanOperation.kt#L30
809
820
  - (void)_updateTypingAttributes
810
821
  {
811
822
  if (_backedTextInputView.attributedText.length > 0 && _backedTextInputView.selectedTextRange != nil) {
@@ -697,11 +697,18 @@ const CGFloat BACKGROUND_COLOR_ZPOSITION = -1024.0f;
697
697
  [_reactSubviews removeObjectAtIndex:index];
698
698
  } else {
699
699
  RCTAssert(
700
- childComponentView.superview == self.currentContainerView,
701
- @"Attempt to unmount a view which is mounted inside different view. (parent: %@, child: %@, index: %@)",
700
+ childComponentView.superview != nil,
701
+ @"Attempt to unmount a view which is not mounted. (parent: %@, child: %@, index: %@)",
702
702
  self,
703
703
  childComponentView,
704
704
  @(index));
705
+ RCTAssert(
706
+ childComponentView.superview == self.currentContainerView,
707
+ @"Attempt to unmount a view which is mounted inside a different view. (parent: %@, child: %@, index: %@, existing parent: %@)",
708
+ self,
709
+ childComponentView,
710
+ @(index),
711
+ @([childComponentView.superview tag]));
705
712
  RCTAssert(
706
713
  (self.currentContainerView.subviews.count > index) &&
707
714
  [self.currentContainerView.subviews objectAtIndex:index] == childComponentView,
@@ -716,6 +723,30 @@ const CGFloat BACKGROUND_COLOR_ZPOSITION = -1024.0f;
716
723
  [childComponentView removeFromSuperview];
717
724
  }
718
725
 
726
+ - (void)_updateRemoveClippedSubviewsState
727
+ {
728
+ if (_removeClippedSubviews) {
729
+ // Toggled ON: populate _reactSubviews from the current view hierarchy.
730
+ // Actual clipping will happen on the next scroll event.
731
+ RCTAssert(
732
+ _reactSubviews.count == 0,
733
+ @"_reactSubviews should be empty when toggling removeClippedSubviews on. (view: %@, count: %@)",
734
+ self,
735
+ @(_reactSubviews.count));
736
+ if (self.currentContainerView.subviews.count > 0) {
737
+ _reactSubviews = [NSMutableArray arrayWithArray:self.currentContainerView.subviews];
738
+ }
739
+ } else {
740
+ // Toggled OFF: re-mount all children in the correct order, then clear the tracking array.
741
+ // addSubview: on an already-present child moves it to the front, so iterating in order
742
+ // produces the correct subview ordering.
743
+ for (UIView *view in _reactSubviews) {
744
+ [self.currentContainerView addSubview:view];
745
+ }
746
+ [_reactSubviews removeAllObjects];
747
+ }
748
+ }
749
+
719
750
  - (void)updateClippedSubviewsWithClipRect:(CGRect)clipRect relativeToView:(UIView *)clipView
720
751
  {
721
752
  if (!_removeClippedSubviews) {
@@ -781,9 +812,7 @@ const CGFloat BACKGROUND_COLOR_ZPOSITION = -1024.0f;
781
812
  if (!ReactNativeFeatureFlags::enableViewCulling()) {
782
813
  if (oldViewProps.removeClippedSubviews != newViewProps.removeClippedSubviews) {
783
814
  _removeClippedSubviews = newViewProps.removeClippedSubviews;
784
- if (_removeClippedSubviews && self.currentContainerView.subviews.count > 0) {
785
- _reactSubviews = [NSMutableArray arrayWithArray:self.currentContainerView.subviews];
786
- }
815
+ [self _updateRemoveClippedSubviewsState];
787
816
  }
788
817
  }
789
818
 
@@ -11,7 +11,7 @@ require "json"
11
11
  package = JSON.parse(File.read(File.join(__dir__, "..", "package.json")))
12
12
  version = package['version']
13
13
 
14
- source = { :git => 'https://github.com/facebook/react-native.git' }
14
+ source = { :git => 'https://github.com/react/react-native.git' }
15
15
  if version == '1000.0.0'
16
16
  # This is an unpublished version, use the latest commit hash of the react-native repo, which we’re presumably in.
17
17
  source[:commit] = `git rev-parse HEAD`.strip if system("git rev-parse --git-dir > /dev/null 2>&1")
@@ -8,7 +8,7 @@ require "json"
8
8
  package = JSON.parse(File.read(File.join(__dir__, "..", "package.json")))
9
9
  version = package['version']
10
10
 
11
- source = { :git => 'https://github.com/facebook/react-native.git' }
11
+ source = { :git => 'https://github.com/react/react-native.git' }
12
12
  if version == '1000.0.0'
13
13
  # This is an unpublished version, use the latest commit hash of the react-native repo, which we’re presumably in.
14
14
  source[:commit] = `git rev-parse HEAD`.strip if system("git rev-parse --git-dir > /dev/null 2>&1")
@@ -8,7 +8,7 @@ require "json"
8
8
  package = JSON.parse(File.read(File.join(__dir__, "..", "..", "package.json")))
9
9
  version = package['version']
10
10
 
11
- source = { :git => 'https://github.com/facebook/react-native.git' }
11
+ source = { :git => 'https://github.com/react/react-native.git' }
12
12
  if version == '1000.0.0'
13
13
  # This is an unpublished version, use the latest commit hash of the react-native repo, which we’re presumably in.
14
14
  source[:commit] = `git rev-parse HEAD`.strip if system("git rev-parse --git-dir > /dev/null 2>&1")
@@ -0,0 +1,145 @@
1
+ /*
2
+ * Copyright (c) Meta Platforms, Inc. and affiliates.
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/RCTViewComponentView.h>
9
+ #import <XCTest/XCTest.h>
10
+ #import <react/renderer/components/view/ViewProps.h>
11
+ #import <react/renderer/components/view/ViewShadowNode.h>
12
+
13
+ using namespace facebook::react;
14
+
15
+ static Props::Shared makeViewProps(bool removeClippedSubviews)
16
+ {
17
+ auto props = std::make_shared<ViewProps>();
18
+ props->removeClippedSubviews = removeClippedSubviews;
19
+ return props;
20
+ }
21
+
22
+ @interface RCTViewComponentViewTests : XCTestCase
23
+ @end
24
+
25
+ @implementation RCTViewComponentViewTests
26
+
27
+ #pragma mark - removeClippedSubviews toggle
28
+
29
+ - (void)testToggleRemoveClippedSubviewsOffRemountsClippedChildren
30
+ {
31
+ RCTViewComponentView *parent = [RCTViewComponentView new];
32
+ UIView *child1 = [UIView new];
33
+ child1.frame = CGRectMake(0, 0, 50, 50);
34
+ UIView *child2 = [UIView new];
35
+ child2.frame = CGRectMake(0, 200, 50, 50);
36
+ UIView *child3 = [UIView new];
37
+ child3.frame = CGRectMake(0, 400, 50, 50);
38
+
39
+ // Mount children normally
40
+ [parent mountChildComponentView:(id)child1 index:0];
41
+ [parent mountChildComponentView:(id)child2 index:1];
42
+ [parent mountChildComponentView:(id)child3 index:2];
43
+
44
+ XCTAssertEqual(parent.subviews.count, 3u);
45
+
46
+ // Toggle removeClippedSubviews ON via props
47
+ auto propsOn = makeViewProps(true);
48
+ [parent updateProps:propsOn oldProps:ViewShadowNode::defaultSharedProps()];
49
+
50
+ // Simulate clipping: remove child2 and child3 from superview (as updateClippedSubviewsWithClipRect would)
51
+ [child2 removeFromSuperview];
52
+ [child3 removeFromSuperview];
53
+ XCTAssertEqual(parent.subviews.count, 1u);
54
+ XCTAssertNil(child2.superview);
55
+ XCTAssertNil(child3.superview);
56
+
57
+ // Toggle removeClippedSubviews OFF via props
58
+ auto propsOff = makeViewProps(false);
59
+ [parent updateProps:propsOff oldProps:propsOn];
60
+
61
+ // All children should be re-mounted
62
+ XCTAssertEqual(parent.subviews.count, 3u);
63
+ XCTAssertEqual(child1.superview, parent);
64
+ XCTAssertEqual(child2.superview, parent);
65
+ XCTAssertEqual(child3.superview, parent);
66
+ }
67
+
68
+ - (void)testToggleRemoveClippedSubviewsOffPreservesOrder
69
+ {
70
+ RCTViewComponentView *parent = [RCTViewComponentView new];
71
+ UIView *child1 = [UIView new];
72
+ child1.frame = CGRectMake(0, 0, 50, 50);
73
+ UIView *child2 = [UIView new];
74
+ child2.frame = CGRectMake(0, 100, 50, 50);
75
+ UIView *child3 = [UIView new];
76
+ child3.frame = CGRectMake(0, 200, 50, 50);
77
+
78
+ [parent mountChildComponentView:(id)child1 index:0];
79
+ [parent mountChildComponentView:(id)child2 index:1];
80
+ [parent mountChildComponentView:(id)child3 index:2];
81
+
82
+ // Toggle ON and clip child1 (first child)
83
+ auto propsOn = makeViewProps(true);
84
+ [parent updateProps:propsOn oldProps:ViewShadowNode::defaultSharedProps()];
85
+ [child1 removeFromSuperview];
86
+ XCTAssertEqual(parent.subviews.count, 2u);
87
+
88
+ // Toggle OFF — all children re-mounted in correct order
89
+ auto propsOff = makeViewProps(false);
90
+ [parent updateProps:propsOff oldProps:propsOn];
91
+
92
+ XCTAssertEqual(parent.subviews.count, 3u);
93
+ XCTAssertEqual(parent.subviews[0], child1);
94
+ XCTAssertEqual(parent.subviews[1], child2);
95
+ XCTAssertEqual(parent.subviews[2], child3);
96
+ }
97
+
98
+ - (void)testToggleRemoveClippedSubviewsOffClearsReactSubviews
99
+ {
100
+ RCTViewComponentView *parent = [RCTViewComponentView new];
101
+ UIView *child1 = [UIView new];
102
+ child1.frame = CGRectMake(0, 0, 50, 50);
103
+
104
+ [parent mountChildComponentView:(id)child1 index:0];
105
+
106
+ // Toggle ON
107
+ auto propsOn = makeViewProps(true);
108
+ [parent updateProps:propsOn oldProps:ViewShadowNode::defaultSharedProps()];
109
+
110
+ // Toggle OFF
111
+ auto propsOff = makeViewProps(false);
112
+ [parent updateProps:propsOff oldProps:propsOn];
113
+
114
+ // _reactSubviews should be cleared
115
+ NSMutableArray *reactSubviews = [parent valueForKey:@"_reactSubviews"];
116
+ XCTAssertEqual(reactSubviews.count, 0u);
117
+ }
118
+
119
+ - (void)testUnmountAfterToggleOffCleansUpReactSubviews
120
+ {
121
+ RCTViewComponentView *parent = [RCTViewComponentView new];
122
+ UIView *child1 = [UIView new];
123
+ child1.frame = CGRectMake(0, 0, 50, 50);
124
+ UIView *child2 = [UIView new];
125
+ child2.frame = CGRectMake(0, 100, 50, 50);
126
+
127
+ // Toggle ON first, then mount children
128
+ auto propsOn = makeViewProps(true);
129
+ [parent updateProps:propsOn oldProps:ViewShadowNode::defaultSharedProps()];
130
+ [parent mountChildComponentView:(id)child1 index:0];
131
+ [parent mountChildComponentView:(id)child2 index:1];
132
+
133
+ // Toggle OFF — re-mounts children
134
+ auto propsOff = makeViewProps(false);
135
+ [parent updateProps:propsOff oldProps:propsOn];
136
+
137
+ XCTAssertEqual(parent.subviews.count, 2u);
138
+
139
+ // Unmount child2 — should succeed without assert failures
140
+ [parent unmountChildComponentView:(id)child2 index:1];
141
+ XCTAssertEqual(parent.subviews.count, 1u);
142
+ XCTAssertNil(child2.superview);
143
+ }
144
+
145
+ @end
@@ -366,7 +366,7 @@ static inline UIViewAnimationOptions animationOptionsWithCurve(UIViewAnimationCu
366
366
  if (@available(iOS 14.0, *)) {
367
367
  // On iOS when Prefer Cross-Fade Transitions is enabled, the keyboard position
368
368
  // & height is reported differently (0 instead of Y position value matching height of frame)
369
- // Fixes similar issue we saw with https://github.com/facebook/react-native/pull/34503
369
+ // Fixes similar issue we saw with https://github.com/react/react-native/pull/34503
370
370
  if (UIAccessibilityPrefersCrossFadeTransitions() && endFrame.size.height == 0) {
371
371
  newContentOffset.y = 0;
372
372
  newEdgeInsets.bottom = 0;
@@ -8,7 +8,7 @@ require "json"
8
8
  package = JSON.parse(File.read(File.join(__dir__, "package.json")))
9
9
  version = package['version']
10
10
 
11
- source = { :git => 'https://github.com/facebook/react-native.git' }
11
+ source = { :git => 'https://github.com/react/react-native.git' }
12
12
  if version == '1000.0.0'
13
13
  # This is an unpublished version, use the latest commit hash of the react-native repo, which we’re presumably in.
14
14
  source[:commit] = `git rev-parse HEAD`.strip if system("git rev-parse --git-dir > /dev/null 2>&1")
package/React.podspec CHANGED
@@ -8,7 +8,7 @@ require "json"
8
8
  package = JSON.parse(File.read(File.join(__dir__, "package.json")))
9
9
  version = package['version']
10
10
 
11
- source = { :git => 'https://github.com/facebook/react-native.git' }
11
+ source = { :git => 'https://github.com/react/react-native.git' }
12
12
  if version == '1000.0.0'
13
13
  # This is an unpublished version, use the latest commit hash of the react-native repo, which we’re presumably in.
14
14
  source[:commit] = `git rev-parse HEAD`.strip if system("git rev-parse --git-dir > /dev/null 2>&1")
@@ -749,7 +749,7 @@ apply(from = "./publish.gradle")
749
749
  // We need to override the artifact ID as this project is called `ReactAndroid` but
750
750
  // the maven coordinates are on `react-android`.
751
751
  // Please note that the original coordinates, `react-native`, have been voided
752
- // as they caused https://github.com/facebook/react-native/issues/35210
752
+ // as they caused https://github.com/react/react-native/issues/35210
753
753
  publishing {
754
754
  publications { getByName("release", MavenPublication::class) { artifactId = "react-android" } }
755
755
  }
@@ -1,4 +1,4 @@
1
- VERSION_NAME=0.83.9-0
1
+ VERSION_NAME=0.83.10-0
2
2
  react.internal.publishingGroup=io.github.react-native-tvos
3
3
  react.internal.hermesPublishingGroup=com.facebook.hermes
4
4
 
@@ -392,3 +392,9 @@ tasks.withType<JavaCompile>().configureEach {
392
392
  options.compilerArgs.add("-Xlint:deprecation,unchecked")
393
393
  options.compilerArgs.add("-Werror")
394
394
  }
395
+
396
+ /* Publishing Configuration */
397
+ // Reuses the publish.gradle template applied to ReactAndroid; the file is
398
+ // generated by the build-android-artifacts EAS workflow. Resulting artifact
399
+ // coordinate: io.github.react-native-tvos:hermes-engine:<version>.
400
+ apply(from = "../publish.gradle")
@@ -37,7 +37,7 @@ publishing {
37
37
  pom {
38
38
  name = "react-native"
39
39
  description = "A framework for building native apps with React"
40
- url = "https://github.com/facebook/react-native"
40
+ url = "https://github.com/react/react-native"
41
41
 
42
42
  developers {
43
43
  developer {
@@ -49,15 +49,15 @@ publishing {
49
49
  licenses {
50
50
  license {
51
51
  name = "MIT License"
52
- url = "https://github.com/facebook/react-native/blob/HEAD/LICENSE"
52
+ url = "https://github.com/react/react-native/blob/HEAD/LICENSE"
53
53
  distribution = "repo"
54
54
  }
55
55
  }
56
56
 
57
57
  scm {
58
- url = "https://github.com/facebook/react-native.git"
59
- connection = "scm:git:https://github.com/facebook/react-native.git"
60
- developerConnection = "scm:git:git@github.com:facebook/react-native.git"
58
+ url = "https://github.com/react/react-native.git"
59
+ connection = "scm:git:https://github.com/react/react-native.git"
60
+ developerConnection = "scm:git:git@github.com:react/react-native.git"
61
61
  }
62
62
  }
63
63
  }
@@ -9,12 +9,18 @@ package com.facebook.react.devsupport
9
9
 
10
10
  import android.os.Handler
11
11
  import android.os.Looper
12
+ import com.facebook.common.logging.FLog
12
13
  import com.facebook.jni.HybridData
13
14
  import com.facebook.proguard.annotations.DoNotStrip
14
15
  import com.facebook.proguard.annotations.DoNotStripAny
16
+ import com.facebook.react.common.annotations.VisibleForTesting
15
17
  import com.facebook.react.devsupport.inspector.DevSupportHttpClient
16
18
  import com.facebook.soloader.SoLoader
17
19
  import java.io.Closeable
20
+ import java.nio.ByteBuffer
21
+ import java.nio.charset.StandardCharsets
22
+ import java.util.ArrayDeque
23
+ import java.util.Queue
18
24
  import okhttp3.Request
19
25
  import okhttp3.Response
20
26
  import okhttp3.WebSocket
@@ -66,7 +72,7 @@ internal class CxxInspectorPackagerConnection(
66
72
  */
67
73
  @DoNotStripAny
68
74
  private interface IWebSocket : Closeable {
69
- fun send(message: String)
75
+ fun send(chunk: ByteBuffer)
70
76
 
71
77
  /**
72
78
  * Close the WebSocket connection. NOTE: There is no close() method in the C++ interface.
@@ -75,6 +81,95 @@ internal class CxxInspectorPackagerConnection(
75
81
  override fun close()
76
82
  }
77
83
 
84
+ /**
85
+ * A simple WebSocket wrapper that prevents having more than 16MiB of messages queued
86
+ * simultaneously. This is done to stop OkHttp from closing the WebSocket connection.
87
+ *
88
+ * https://github.com/react/react-native/issues/39651.
89
+ * https://github.com/square/okhttp/blob/4e7dbec1ea6c9cf8d80422ac9d44b9b185c749a3/okhttp/src/commonJvmAndroid/kotlin/okhttp3/internal/ws/RealWebSocket.kt#L684.
90
+ */
91
+ private class InspectorPackagerWebSocketImpl(
92
+ private val nativeWebSocket: WebSocket,
93
+ private val handler: Handler,
94
+ ) : IWebSocket {
95
+ private val messageQueue: Queue<Pair<String, Int>> = ArrayDeque()
96
+ private val queueLock = Any()
97
+ private val drainRunnable =
98
+ object : Runnable {
99
+ override fun run() {
100
+ FLog.d(TAG, "Attempting to drain the message queue after ${drainDelayMs}ms")
101
+ tryDrainQueue()
102
+ }
103
+ }
104
+
105
+ /**
106
+ * We are providing a String to OkHttp's WebSocket, because there is no guarantee that all CDP
107
+ * clients will support binary data format.
108
+ */
109
+ override fun send(chunk: ByteBuffer) {
110
+ synchronized(queueLock) {
111
+ val messageSize = chunk.capacity()
112
+ val message = StandardCharsets.UTF_8.decode(chunk).toString()
113
+ val currentQueueSize = nativeWebSocket.queueSize()
114
+
115
+ if (currentQueueSize + messageSize > MAX_QUEUE_SIZE) {
116
+ FLog.d(TAG, "Reached queue size limit. Queueing the message.")
117
+ messageQueue.offer(Pair(message, messageSize))
118
+ scheduleDrain()
119
+ } else {
120
+ if (messageQueue.isEmpty()) {
121
+ nativeWebSocket.send(message)
122
+ } else {
123
+ messageQueue.offer(Pair(message, messageSize))
124
+ tryDrainQueue()
125
+ }
126
+ }
127
+ }
128
+ }
129
+
130
+ override fun close() {
131
+ synchronized(queueLock) {
132
+ handler.removeCallbacks(drainRunnable)
133
+ messageQueue.clear()
134
+ nativeWebSocket.close(1000, "End of session")
135
+ }
136
+ }
137
+
138
+ private fun tryDrainQueue() {
139
+ synchronized(queueLock) {
140
+ while (messageQueue.isNotEmpty()) {
141
+ val (nextMessage, nextMessageSize) = messageQueue.peek() ?: break
142
+ val currentQueueSize = nativeWebSocket.queueSize()
143
+
144
+ if (currentQueueSize + nextMessageSize <= MAX_QUEUE_SIZE) {
145
+ messageQueue.poll()
146
+ if (!nativeWebSocket.send(nextMessage)) {
147
+ // The WebSocket is closing, closed, or cancelled.
148
+ handler.removeCallbacks(drainRunnable)
149
+ messageQueue.clear()
150
+
151
+ break
152
+ }
153
+ } else {
154
+ scheduleDrain()
155
+ break
156
+ }
157
+ }
158
+ }
159
+ }
160
+
161
+ private fun scheduleDrain() {
162
+ FLog.d(TAG, "Scheduled a task to drain messages queue.")
163
+ handler.removeCallbacks(drainRunnable)
164
+ handler.postDelayed(drainRunnable, drainDelayMs)
165
+ }
166
+
167
+ companion object {
168
+ private val TAG: String = InspectorPackagerWebSocketImpl::class.java.simpleName
169
+ private const val drainDelayMs: Long = 100
170
+ }
171
+ }
172
+
78
173
  /** Java implementation of the C++ InspectorPackagerConnectionDelegate interface. */
79
174
  private class DelegateImpl {
80
175
  private val httpClient = DevSupportHttpClient.websocketClient
@@ -124,15 +219,8 @@ internal class CxxInspectorPackagerConnection(
124
219
  }
125
220
  },
126
221
  )
127
- return object : IWebSocket {
128
- override fun send(message: String) {
129
- webSocket.send(message)
130
- }
131
222
 
132
- override fun close() {
133
- webSocket.close(1000, "End of session")
134
- }
135
- }
223
+ return InspectorPackagerWebSocketImpl(webSocket, handler)
136
224
  }
137
225
 
138
226
  @DoNotStrip
@@ -146,6 +234,8 @@ internal class CxxInspectorPackagerConnection(
146
234
  SoLoader.loadLibrary("react_devsupportjni")
147
235
  }
148
236
 
237
+ @VisibleForTesting internal const val MAX_QUEUE_SIZE = 16L * 1024 * 1024 // 16MiB
238
+
149
239
  @JvmStatic
150
240
  private external fun initHybrid(
151
241
  url: String,
@@ -55,7 +55,7 @@ internal object InspectorNetworkHelper {
55
55
  response.body().use { responseBody ->
56
56
  if (responseBody != null) {
57
57
  val inputStream = responseBody.byteStream()
58
- val chunkSize = 1024
58
+ val chunkSize = 8 * 1024 // 8Kb
59
59
  val buffer = ByteArray(chunkSize)
60
60
  var bytesRead: Int
61
61
 
@@ -1190,8 +1190,8 @@ public class SurfaceMountingManager {
1190
1190
  // If the view that went offscreen is still being touched, we can't delete it yet.
1191
1191
  // We have to delay the deletion till the touch is completed.
1192
1192
  // This is causing bugs like those otherwise:
1193
- // - https://github.com/facebook/react-native/issues/44610
1194
- // - https://github.com/facebook/react-native/issues/45126
1193
+ // - https://github.com/react/react-native/issues/44610
1194
+ // - https://github.com/react/react-native/issues/45126
1195
1195
  mViewsToDeleteAfterTouchFinishes.add(reactTag);
1196
1196
  } else {
1197
1197
  // To delete we simply remove the tag from the registry.
@@ -326,7 +326,7 @@ public open class JavaTimerManager(
326
326
 
327
327
  // If the JS thread is busy for multiple frames we cancel any other pending runnable.
328
328
  // We also capture the idleCallbackRunnable to tentatively fix:
329
- // https://github.com/facebook/react-native/issues/44842
329
+ // https://github.com/react/react-native/issues/44842
330
330
  currentIdleCallbackRunnable?.cancel()
331
331
  currentIdleCallbackRunnable = IdleCallbackRunnable(frameTimeNanos)
332
332
  reactApplicationContext.runOnJSQueueThread(currentIdleCallbackRunnable)
@@ -63,6 +63,7 @@ public class ReactAndroidHWInputDeviceHelper {
63
63
  .put(KeyEvent.KEYCODE_9, "9")
64
64
  .put(KeyEvent.KEYCODE_CHANNEL_DOWN, "channelDown")
65
65
  .put(KeyEvent.KEYCODE_CHANNEL_UP, "channelUp")
66
+ .put(KeyEvent.KEYCODE_DEL, "delete")
66
67
  .put(KeyEvent.KEYCODE_BOOKMARK, "bookmark")
67
68
  .put(KeyEvent.KEYCODE_AVR_INPUT, "avrInput")
68
69
  .put(KeyEvent.KEYCODE_AVR_POWER, "avrPower")
@@ -223,7 +223,7 @@ public open class IntentModule(reactContext: ReactApplicationContext) :
223
223
  }
224
224
  ReadableType.Number -> {
225
225
  // We cannot know from JS if is an Integer or Double
226
- // See: https://github.com/facebook/react-native/issues/4141
226
+ // See: https://github.com/react/react-native/issues/4141
227
227
  // We might need to find a workaround if this is really an issue
228
228
  val number = map.getDouble(EXTRA_MAP_KEY_FOR_VALUE)
229
229
  intent.putExtra(name, number)
@@ -165,7 +165,7 @@ public class NetworkingModule(
165
165
 
166
166
  @Deprecated(
167
167
  """To be removed in a future release. See
168
- https://github.com/facebook/react-native/pull/37798#pullrequestreview-1518338914"""
168
+ https://github.com/react/react-native/pull/37798#pullrequestreview-1518338914"""
169
169
  )
170
170
  public interface CustomClientBuilder : com.facebook.react.modules.network.CustomClientBuilder
171
171
 
@@ -479,7 +479,7 @@ public class NetworkingModule(
479
479
  } else {
480
480
  // Use getBytes() to convert the body into a byte[], preventing okhttp from
481
481
  // appending the character set to the Content-Type header when otherwise unspecified
482
- // https://github.com/facebook/react-native/issues/8237
482
+ // https://github.com/react/react-native/issues/8237
483
483
  val charset =
484
484
  if (contentMediaType == null) {
485
485
  StandardCharsets.UTF_8
@@ -636,7 +636,7 @@ public class NetworkingModule(
636
636
  reactApplicationContext,
637
637
  requestId,
638
638
  devToolsRequestId,
639
- url,
639
+ response.request().url().toString(),
640
640
  response.code(),
641
641
  NetworkEventUtil.okHttpHeadersToMap(response.headers()),
642
642
  response.body()?.contentLength() ?: 0L,
@@ -14,7 +14,7 @@ public object ReactNativeVersion {
14
14
  public val VERSION: Map<String, Any?> = mapOf(
15
15
  "major" to 0,
16
16
  "minor" to 83,
17
- "patch" to 9,
17
+ "patch" to 10,
18
18
  "prerelease" to "0"
19
19
  )
20
20
  }
@@ -563,7 +563,7 @@ internal class ReactInstance(
563
563
  // We need to null check here because some Java implementation of the
564
564
  // `ViewManagerOnDemandReactPackage` interface could still return null even
565
565
  // if the method is marked as returning a non-nullable collection in Kotlin.
566
- // See https://github.com/facebook/react-native/issues/52014
566
+ // See https://github.com/react/react-native/issues/52014
567
567
  @Suppress("SENSELESS_COMPARISON")
568
568
  if (names == null) {
569
569
  RNLog.w(
@@ -631,7 +631,7 @@ public abstract class BaseViewManager<T extends View, C extends LayoutShadowNode
631
631
  // The native Android implementation removed the screen density from the
632
632
  // calculation, so squaring and a normalization value of
633
633
  // sqrt(5) produces an exact replica with iOS.
634
- // For more information, see https://github.com/facebook/react-native/pull/18302
634
+ // For more information, see https://github.com/react/react-native/pull/18302
635
635
  float normalizedCameraDistance =
636
636
  sanitizeFloatPropertyValue(
637
637
  scale * scale * cameraDistance * CAMERA_DISTANCE_NORMALIZATION_MULTIPLIER);