react-native-screens 3.11.1 → 3.12.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 (88) hide show
  1. package/README.md +4 -0
  2. package/RNScreens.podspec +36 -6
  3. package/android/build.gradle +73 -1
  4. package/android/src/fabric/java/com/swmansion/rnscreens/FabricEnabledViewGroup.kt +49 -0
  5. package/android/src/fabric/java/com/swmansion/rnscreens/RNScreensComponentsRegistry.java +28 -0
  6. package/android/src/main/java/com/swmansion/rnscreens/RNScreensPackage.kt +11 -2
  7. package/android/src/main/java/com/swmansion/rnscreens/Screen.kt +24 -10
  8. package/android/src/main/java/com/swmansion/rnscreens/ScreenStackHeaderConfigViewManager.kt +83 -18
  9. package/android/src/main/java/com/swmansion/rnscreens/ScreenStackHeaderSubviewManager.kt +17 -5
  10. package/android/src/main/java/com/swmansion/rnscreens/ScreenStackViewManager.kt +14 -1
  11. package/android/src/main/java/com/swmansion/rnscreens/ScreenViewManager.kt +33 -16
  12. package/android/src/main/jni/Android.mk +45 -0
  13. package/android/src/main/jni/OnLoad.cpp +9 -0
  14. package/android/src/main/jni/RNScreensComponentsRegistry.cpp +66 -0
  15. package/android/src/main/jni/RNScreensComponentsRegistry.h +34 -0
  16. package/android/src/paper/java/com/facebook/react/viewmanagers/RNSScreenManagerDelegate.java +71 -0
  17. package/android/src/paper/java/com/facebook/react/viewmanagers/RNSScreenManagerInterface.java +30 -0
  18. package/android/src/paper/java/com/facebook/react/viewmanagers/RNSScreenStackHeaderConfigManagerDelegate.java +104 -0
  19. package/android/src/paper/java/com/facebook/react/viewmanagers/RNSScreenStackHeaderConfigManagerInterface.java +41 -0
  20. package/android/src/paper/java/com/facebook/react/viewmanagers/RNSScreenStackHeaderSubviewManagerDelegate.java +31 -0
  21. package/android/src/paper/java/com/facebook/react/viewmanagers/RNSScreenStackHeaderSubviewManagerInterface.java +17 -0
  22. package/android/src/paper/java/com/facebook/react/viewmanagers/RNSScreenStackManagerDelegate.java +25 -0
  23. package/android/src/paper/java/com/facebook/react/viewmanagers/RNSScreenStackManagerInterface.java +16 -0
  24. package/android/src/paper/java/com/swmansion/rnscreens/FabricEnabledViewGroup.kt +16 -0
  25. package/common/cpp/Android.mk +38 -0
  26. package/common/cpp/rnscreens/RNSScreenComponentDescriptor.h +41 -0
  27. package/common/cpp/rnscreens/RNSScreenShadowNode.cpp +9 -0
  28. package/common/cpp/rnscreens/RNSScreenShadowNode.h +29 -0
  29. package/common/cpp/rnscreens/RNSScreenState.cpp +14 -0
  30. package/common/cpp/rnscreens/RNSScreenState.h +46 -0
  31. package/ios/RNSScreenComponentView.h +23 -0
  32. package/ios/RNSScreenComponentView.mm +159 -0
  33. package/ios/RNSScreenController.h +10 -0
  34. package/ios/RNSScreenController.mm +79 -0
  35. package/ios/RNSScreenStackComponentView.h +15 -0
  36. package/ios/RNSScreenStackComponentView.mm +295 -0
  37. package/ios/RNSScreenStackHeaderConfigComponentView.h +42 -0
  38. package/ios/RNSScreenStackHeaderConfigComponentView.mm +662 -0
  39. package/ios/RNSScreenStackHeaderSubviewComponentView.h +14 -0
  40. package/ios/RNSScreenStackHeaderSubviewComponentView.mm +77 -0
  41. package/ios/utils/RNSUIBarButtonItem.h +5 -0
  42. package/ios/utils/RNSUIBarButtonItem.mm +22 -0
  43. package/lib/commonjs/fabric/Screen.js +27 -0
  44. package/lib/commonjs/fabric/Screen.js.map +1 -0
  45. package/lib/commonjs/fabric/ScreenNativeComponent.js +23 -0
  46. package/lib/commonjs/fabric/ScreenNativeComponent.js.map +1 -0
  47. package/lib/commonjs/fabric/ScreenStack.js +27 -0
  48. package/lib/commonjs/fabric/ScreenStack.js.map +1 -0
  49. package/lib/commonjs/fabric/ScreenStackHeaderConfigNativeComponent.js +27 -0
  50. package/lib/commonjs/fabric/ScreenStackHeaderConfigNativeComponent.js.map +1 -0
  51. package/lib/commonjs/fabric/ScreenStackHeaderSubview.js +34 -0
  52. package/lib/commonjs/fabric/ScreenStackHeaderSubview.js.map +1 -0
  53. package/lib/commonjs/fabric/ScreenStackHeaderSubviewNativeComponent.js +27 -0
  54. package/lib/commonjs/fabric/ScreenStackHeaderSubviewNativeComponent.js.map +1 -0
  55. package/lib/commonjs/fabric/ScreenStackNativeComponent.js +21 -0
  56. package/lib/commonjs/fabric/ScreenStackNativeComponent.js.map +1 -0
  57. package/lib/commonjs/fabric/index.js +40 -0
  58. package/lib/commonjs/fabric/index.js.map +1 -0
  59. package/lib/commonjs/index.native.js +32 -15
  60. package/lib/commonjs/index.native.js.map +1 -1
  61. package/lib/module/fabric/Screen.js +11 -0
  62. package/lib/module/fabric/Screen.js.map +1 -0
  63. package/lib/module/fabric/ScreenNativeComponent.js +11 -0
  64. package/lib/module/fabric/ScreenNativeComponent.js.map +1 -0
  65. package/lib/module/fabric/ScreenStack.js +12 -0
  66. package/lib/module/fabric/ScreenStack.js.map +1 -0
  67. package/lib/module/fabric/ScreenStackHeaderConfigNativeComponent.js +10 -0
  68. package/lib/module/fabric/ScreenStackHeaderConfigNativeComponent.js.map +1 -0
  69. package/lib/module/fabric/ScreenStackHeaderSubview.js +21 -0
  70. package/lib/module/fabric/ScreenStackHeaderSubview.js.map +1 -0
  71. package/lib/module/fabric/ScreenStackHeaderSubviewNativeComponent.js +10 -0
  72. package/lib/module/fabric/ScreenStackHeaderSubviewNativeComponent.js.map +1 -0
  73. package/lib/module/fabric/ScreenStackNativeComponent.js +9 -0
  74. package/lib/module/fabric/ScreenStackNativeComponent.js.map +1 -0
  75. package/lib/module/fabric/index.js +6 -0
  76. package/lib/module/fabric/index.js.map +1 -0
  77. package/lib/module/index.native.js +32 -15
  78. package/lib/module/index.native.js.map +1 -1
  79. package/package.json +17 -3
  80. package/src/fabric/Screen.js +12 -0
  81. package/src/fabric/ScreenNativeComponent.js +64 -0
  82. package/src/fabric/ScreenStack.js +8 -0
  83. package/src/fabric/ScreenStackHeaderConfigNativeComponent.js +54 -0
  84. package/src/fabric/ScreenStackHeaderSubview.js +20 -0
  85. package/src/fabric/ScreenStackHeaderSubviewNativeComponent.js +31 -0
  86. package/src/fabric/ScreenStackNativeComponent.js +19 -0
  87. package/src/fabric/index.js +11 -0
  88. package/src/index.native.tsx +35 -14
package/README.md CHANGED
@@ -2,6 +2,10 @@
2
2
 
3
3
  This project aims to expose native navigation container components to React Native. It is not designed to be used as a standalone library but rather as a dependency of a [full-featured navigation library](https://github.com/react-navigation/react-navigation).
4
4
 
5
+ ## Fabric
6
+
7
+ To learn about how to use `react-native-screens` with Fabric architecture, head over to [Fabric README](README-Fabric.md). Instructions on how to run Fabric Example within this repo can be found in the [FabricExample README](FabricExample/README.md).
8
+
5
9
  ## Supported platforms
6
10
 
7
11
  - [x] iOS
package/RNScreens.podspec CHANGED
@@ -2,6 +2,13 @@ require "json"
2
2
 
3
3
  package = JSON.parse(File.read(File.join(__dir__, "package.json")))
4
4
 
5
+ fabric_enabled = ENV['RCT_NEW_ARCH_ENABLED']
6
+
7
+ # folly_version must match the version used in React Native
8
+ # See folly_version in react-native/React/FBReactNativeSpec/FBReactNativeSpec.podspec
9
+ folly_version = '2021.06.28.00-v2'
10
+ folly_compiler_flags = '-DFOLLY_NO_CONFIG -DFOLLY_MOBILE=1 -DFOLLY_USE_LIBCPP=1 -Wno-comma -Wno-shorten-64-to-32'
11
+
5
12
  Pod::Spec.new do |s|
6
13
  s.name = "RNScreens"
7
14
  s.version = package["version"]
@@ -16,10 +23,33 @@ Pod::Spec.new do |s|
16
23
  s.platforms = { :ios => "9.0", :tvos => "11.0" }
17
24
  s.source = { :git => "https://github.com/software-mansion/react-native-screens.git", :tag => "#{s.version}" }
18
25
 
19
- s.source_files = "ios/**/*.{h,m}"
20
- s.requires_arc = true
21
-
22
- s.dependency "React-Core"
23
- s.dependency "React-RCTImage"
26
+ if fabric_enabled
27
+ s.pod_target_xcconfig = {
28
+ 'HEADER_SEARCH_PATHS' => '"$(PODS_ROOT)/boost" "$(PODS_ROOT)/boost-for-react-native" "$(PODS_ROOT)/RCT-Folly"'
29
+ }
30
+ s.platforms = { ios: '11.0', tvos: '11.0' }
31
+ s.compiler_flags = folly_compiler_flags
32
+ s.source_files = 'ios/**/*.{h,m,mm,cpp}'
33
+ s.requires_arc = true
34
+
35
+ s.dependency "React"
36
+ s.dependency "React-RCTFabric"
37
+ s.dependency "React-Codegen"
38
+ s.dependency "RCT-Folly", folly_version
39
+ s.dependency "RCTRequired"
40
+ s.dependency "RCTTypeSafety"
41
+ s.dependency "ReactCommon/turbomodule/core"
42
+
43
+ s.subspec "common" do |ss|
44
+ ss.source_files = "common/cpp/**/*.{cpp,h}"
45
+ ss.header_dir = "rnscreens"
46
+ ss.pod_target_xcconfig = { "HEADER_SEARCH_PATHS" => "\"$(PODS_TARGET_SRCROOT)/common/cpp\"" }
47
+ end
48
+ else
49
+ s.source_files = "ios/**/*.{h,m}"
50
+ s.requires_arc = true
51
+
52
+ s.dependency "React-Core"
53
+ s.dependency "React-RCTImage"
54
+ end
24
55
  end
25
-
@@ -13,11 +13,22 @@ buildscript {
13
13
  }
14
14
  }
15
15
 
16
+ def isNewArchitectureEnabled() {
17
+ // To opt-in for the New Architecture, you can either:
18
+ // - Set `newArchEnabled` to true inside the `gradle.properties` file
19
+ // - Invoke gradle with `-newArchEnabled=true`
20
+ // - Set an environment variable `ORG_GRADLE_PROJECT_newArchEnabled=true`
21
+ return project.hasProperty("newArchEnabled") && project.newArchEnabled == "true"
22
+ }
23
+
16
24
  // spotless is only accessible within react-native-screens repo
17
25
  if (project == rootProject) {
18
26
  apply from: 'spotless.gradle'
19
27
  }
20
28
 
29
+ if (isNewArchitectureEnabled()) {
30
+ apply plugin: "com.facebook.react"
31
+ }
21
32
  apply plugin: 'com.android.library'
22
33
  apply plugin: 'kotlin-android'
23
34
 
@@ -29,6 +40,24 @@ android {
29
40
  targetSdkVersion safeExtGet('targetSdkVersion', 22)
30
41
  versionCode 1
31
42
  versionName "1.0"
43
+ buildConfigField "boolean", "IS_NEW_ARCHITECTURE_ENABLED", isNewArchitectureEnabled().toString()
44
+ if (isNewArchitectureEnabled()) {
45
+ var appProject = rootProject.allprojects.find {it.plugins.hasPlugin('com.android.application')}
46
+ externalNativeBuild {
47
+ ndkBuild {
48
+ arguments "APP_PLATFORM=android-21",
49
+ "APP_STL=c++_shared",
50
+ "NDK_TOOLCHAIN_VERSION=clang",
51
+ "GENERATED_SRC_DIR=${appProject.buildDir}/generated/source",
52
+ "PROJECT_BUILD_DIR=${appProject.buildDir}",
53
+ "REACT_ANDROID_DIR=${appProject.rootDir}/../node_modules/react-native/ReactAndroid",
54
+ "REACT_ANDROID_BUILD_DIR=${appProject.rootDir}/../node_modules/react-native/ReactAndroid/build"
55
+ cFlags "-Wall", "-Werror", "-fexceptions", "-frtti", "-DWITH_INSPECTOR=1"
56
+ cppFlags "-std=c++17"
57
+ targets "rnscreens_modules"
58
+ }
59
+ }
60
+ }
32
61
  }
33
62
  lintOptions {
34
63
  abortOnError false
@@ -37,6 +66,35 @@ android {
37
66
  sourceCompatibility JavaVersion.VERSION_1_8
38
67
  targetCompatibility JavaVersion.VERSION_1_8
39
68
  }
69
+ if (isNewArchitectureEnabled()) {
70
+ externalNativeBuild {
71
+ ndkBuild {
72
+ path "src/main/jni/Android.mk"
73
+ }
74
+ }
75
+ }
76
+ packagingOptions {
77
+ // For some reason gradle only complains about the duplicated version of libreact_render libraries
78
+ // while there are more libraries copied in intermediates folder of the lib build directory, we exlude
79
+ // only the ones that make the build fail (ideally we should only include librnscreens_modules but we
80
+ // are only allowed to specify exlude patterns)
81
+ exclude "**/libreact_render*.so"
82
+ }
83
+ sourceSets.main {
84
+ java {
85
+ if (isNewArchitectureEnabled()) {
86
+ srcDirs += [
87
+ "src/fabric/java",
88
+ ]
89
+ } else {
90
+ srcDirs += [
91
+ "src/paper/java",
92
+ "build/generated/source/codegen/java"
93
+ ]
94
+ }
95
+
96
+ }
97
+ }
40
98
  }
41
99
 
42
100
  repositories {
@@ -52,7 +110,11 @@ repositories {
52
110
  }
53
111
 
54
112
  dependencies {
55
- implementation 'com.facebook.react:react-native:+'
113
+ if (isNewArchitectureEnabled()) {
114
+ implementation project(":ReactAndroid")
115
+ } else {
116
+ implementation 'com.facebook.react:react-native:+'
117
+ }
56
118
  implementation 'androidx.appcompat:appcompat:1.1.0'
57
119
  implementation 'androidx.fragment:fragment:1.2.1'
58
120
  implementation 'androidx.coordinatorlayout:coordinatorlayout:1.1.0'
@@ -60,3 +122,13 @@ dependencies {
60
122
  implementation 'com.google.android.material:material:1.1.0'
61
123
  implementation "androidx.core:core-ktx:1.5.0"
62
124
  }
125
+
126
+ if (isNewArchitectureEnabled()) {
127
+ react {
128
+ reactRoot = rootProject.file("../node_modules/react-native/")
129
+ jsRootDir = file("../src/fabric/")
130
+ codegenDir = rootProject.file("../node_modules/react-native-codegen/")
131
+ libraryName = "rnscreens"
132
+ codegenJavaPackageName = "com.swmansion.rnscreens"
133
+ }
134
+ }
@@ -0,0 +1,49 @@
1
+ package com.swmansion.rnscreens
2
+
3
+ import android.view.ViewGroup
4
+ import androidx.annotation.UiThread
5
+ import com.facebook.react.bridge.ReactContext
6
+ import com.facebook.react.bridge.ReadableMap
7
+ import com.facebook.react.bridge.WritableMap
8
+ import com.facebook.react.bridge.WritableNativeMap
9
+ import com.facebook.react.uimanager.FabricViewStateManager
10
+ import com.facebook.react.uimanager.PixelUtil
11
+ import kotlin.math.abs
12
+
13
+ abstract class FabricEnabledViewGroup constructor(context: ReactContext?) : ViewGroup(context), FabricViewStateManager.HasFabricViewStateManager {
14
+ private val mFabricViewStateManager: FabricViewStateManager = FabricViewStateManager()
15
+
16
+ override fun getFabricViewStateManager(): FabricViewStateManager {
17
+ return mFabricViewStateManager
18
+ }
19
+
20
+ protected fun updateScreenSizeFabric(width: Int, height: Int) {
21
+ updateState(width, height)
22
+ }
23
+
24
+ @UiThread
25
+ fun updateState(width: Int, height: Int) {
26
+ val realWidth: Float = PixelUtil.toDIPFromPixel(width.toFloat())
27
+ val realHeight: Float = PixelUtil.toDIPFromPixel(height.toFloat())
28
+
29
+ // Check incoming state values. If they're already the correct value, return early to prevent
30
+ // infinite UpdateState/SetState loop.
31
+ val currentState: ReadableMap? = mFabricViewStateManager.getStateData()
32
+ if (currentState != null) {
33
+ val delta = 0.9f
34
+ val stateFrameHeight: Float = if (currentState.hasKey("frameHeight")) currentState.getDouble("frameHeight").toFloat() else 0f
35
+ val stateFrameWidth: Float = if (currentState.hasKey("frameWidth")) currentState.getDouble("frameWidth").toFloat() else 0f
36
+ if (abs(stateFrameWidth - realWidth) < delta &&
37
+ abs(stateFrameHeight - realHeight) < delta
38
+ ) {
39
+ return
40
+ }
41
+ }
42
+ mFabricViewStateManager.setState {
43
+ val map: WritableMap = WritableNativeMap()
44
+ map.putDouble("frameWidth", realWidth.toDouble())
45
+ map.putDouble("frameHeight", realHeight.toDouble())
46
+ map
47
+ }
48
+ }
49
+ }
@@ -0,0 +1,28 @@
1
+ package com.swmansion.rnscreens;
2
+
3
+ import com.facebook.jni.HybridData;
4
+ import com.facebook.proguard.annotations.DoNotStrip;
5
+ import com.facebook.react.fabric.ComponentFactory;
6
+ import com.facebook.soloader.SoLoader;
7
+
8
+ @DoNotStrip
9
+ public class RNScreensComponentsRegistry {
10
+ static {
11
+ SoLoader.loadLibrary("rnscreens_modules");
12
+ }
13
+
14
+ @DoNotStrip private final HybridData mHybridData;
15
+
16
+ @DoNotStrip
17
+ private native HybridData initHybrid(ComponentFactory componentFactory);
18
+
19
+ @DoNotStrip
20
+ private RNScreensComponentsRegistry(ComponentFactory componentFactory) {
21
+ mHybridData = initHybrid(componentFactory);
22
+ }
23
+
24
+ @DoNotStrip
25
+ public static RNScreensComponentsRegistry register(ComponentFactory componentFactory) {
26
+ return new RNScreensComponentsRegistry(componentFactory);
27
+ }
28
+ }
@@ -4,10 +4,19 @@ import com.facebook.react.ReactPackage
4
4
  import com.facebook.react.bridge.NativeModule
5
5
  import com.facebook.react.bridge.ReactApplicationContext
6
6
  import com.facebook.react.uimanager.ViewManager
7
+ import com.facebook.soloader.SoLoader
7
8
 
8
9
  class RNScreensPackage : ReactPackage {
9
- override fun createNativeModules(reactContext: ReactApplicationContext) =
10
- emptyList<NativeModule>()
10
+ override fun createNativeModules(reactContext: ReactApplicationContext): List<NativeModule> {
11
+ if (BuildConfig.IS_NEW_ARCHITECTURE_ENABLED) {
12
+ // For Fabric, we load c++ native library here, this triggers screen's Fabric
13
+ // component registration which is necessary in order to avoid asking users
14
+ // to manually add init calls in their application code.
15
+ // This should no longer be needed if RN's autolink mechanism has Fabric support
16
+ SoLoader.loadLibrary("rnscreens_modules")
17
+ }
18
+ return emptyList<NativeModule>()
19
+ }
11
20
 
12
21
  override fun createViewManagers(reactContext: ReactApplicationContext) =
13
22
  listOf<ViewManager<*, *>>(
@@ -8,12 +8,18 @@ import android.util.SparseArray
8
8
  import android.view.ViewGroup
9
9
  import android.view.WindowManager
10
10
  import android.webkit.WebView
11
+ import androidx.annotation.UiThread
11
12
  import com.facebook.react.bridge.GuardedRunnable
12
13
  import com.facebook.react.bridge.ReactContext
14
+ import com.facebook.react.bridge.ReadableMap
15
+ import com.facebook.react.bridge.WritableMap
16
+ import com.facebook.react.bridge.WritableNativeMap
17
+ import com.facebook.react.uimanager.PixelUtil
13
18
  import com.facebook.react.uimanager.UIManagerModule
14
19
 
15
20
  @SuppressLint("ViewConstructor")
16
- class Screen constructor(context: ReactContext?) : ViewGroup(context) {
21
+ class Screen constructor(context: ReactContext?) : FabricEnabledViewGroup(context) {
22
+
17
23
  var fragment: ScreenFragment? = null
18
24
  var container: ScreenContainer<*>? = null
19
25
  var activityState: ActivityState? = null
@@ -62,18 +68,26 @@ class Screen constructor(context: ReactContext?) : ViewGroup(context) {
62
68
  if (changed) {
63
69
  val width = r - l
64
70
  val height = b - t
65
- val reactContext = context as ReactContext
66
- reactContext.runOnNativeModulesQueueThread(
67
- object : GuardedRunnable(reactContext) {
68
- override fun runGuarded() {
69
- reactContext
70
- .getNativeModule(UIManagerModule::class.java)
71
- ?.updateNodeSize(id, width, height)
72
- }
73
- })
71
+ if (BuildConfig.IS_NEW_ARCHITECTURE_ENABLED) {
72
+ updateScreenSizeFabric(width, height)
73
+ } else {
74
+ updateScreenSizePaper(width, height)
75
+ }
74
76
  }
75
77
  }
76
78
 
79
+ private fun updateScreenSizePaper(width: Int, height: Int) {
80
+ val reactContext = context as ReactContext
81
+ reactContext.runOnNativeModulesQueueThread(
82
+ object : GuardedRunnable(reactContext) {
83
+ override fun runGuarded() {
84
+ reactContext
85
+ .getNativeModule(UIManagerModule::class.java)
86
+ ?.updateNodeSize(id, width, height)
87
+ }
88
+ })
89
+ }
90
+
77
91
  val headerConfig: ScreenStackHeaderConfig?
78
92
  get() {
79
93
  val child = getChildAt(0)
@@ -1,16 +1,26 @@
1
1
  package com.swmansion.rnscreens
2
2
 
3
+ import android.util.Log
3
4
  import android.view.View
4
5
  import com.facebook.react.bridge.JSApplicationCausedNativeException
5
6
  import com.facebook.react.common.MapBuilder
6
7
  import com.facebook.react.module.annotations.ReactModule
7
8
  import com.facebook.react.uimanager.ThemedReactContext
8
9
  import com.facebook.react.uimanager.ViewGroupManager
10
+ import com.facebook.react.uimanager.ViewManagerDelegate
9
11
  import com.facebook.react.uimanager.annotations.ReactProp
12
+ import com.facebook.react.viewmanagers.RNSScreenStackHeaderConfigManagerDelegate
13
+ import com.facebook.react.viewmanagers.RNSScreenStackHeaderConfigManagerInterface
10
14
  import javax.annotation.Nonnull
11
15
 
12
16
  @ReactModule(name = ScreenStackHeaderConfigViewManager.REACT_CLASS)
13
- class ScreenStackHeaderConfigViewManager : ViewGroupManager<ScreenStackHeaderConfig>() {
17
+ class ScreenStackHeaderConfigViewManager : ViewGroupManager<ScreenStackHeaderConfig>(), RNSScreenStackHeaderConfigManagerInterface<ScreenStackHeaderConfig> {
18
+ private val mDelegate: ViewManagerDelegate<ScreenStackHeaderConfig>
19
+
20
+ init {
21
+ mDelegate = RNSScreenStackHeaderConfigManagerDelegate<ScreenStackHeaderConfig, ScreenStackHeaderConfigViewManager>(this)
22
+ }
23
+
14
24
  override fun getName(): String {
15
25
  return REACT_CLASS
16
26
  }
@@ -58,67 +68,69 @@ class ScreenStackHeaderConfigViewManager : ViewGroupManager<ScreenStackHeaderCon
58
68
  }
59
69
 
60
70
  @ReactProp(name = "title")
61
- fun setTitle(config: ScreenStackHeaderConfig, title: String?) {
71
+ override fun setTitle(config: ScreenStackHeaderConfig, title: String?) {
62
72
  config.setTitle(title)
63
73
  }
64
74
 
65
75
  @ReactProp(name = "titleFontFamily")
66
- fun setTitleFontFamily(config: ScreenStackHeaderConfig, titleFontFamily: String?) {
76
+ override fun setTitleFontFamily(config: ScreenStackHeaderConfig, titleFontFamily: String?) {
67
77
  config.setTitleFontFamily(titleFontFamily)
68
78
  }
69
79
 
70
80
  @ReactProp(name = "titleFontSize")
71
- fun setTitleFontSize(config: ScreenStackHeaderConfig, titleFontSize: Float) {
72
- config.setTitleFontSize(titleFontSize)
81
+ override fun setTitleFontSize(config: ScreenStackHeaderConfig, titleFontSize: Int) {
82
+ config.setTitleFontSize(titleFontSize.toFloat())
73
83
  }
74
84
 
75
85
  @ReactProp(name = "titleFontWeight")
76
- fun setTitleFontWeight(config: ScreenStackHeaderConfig, titleFontWeight: String?) {
86
+ override fun setTitleFontWeight(config: ScreenStackHeaderConfig, titleFontWeight: String?) {
77
87
  config.setTitleFontWeight(titleFontWeight)
78
88
  }
79
89
 
80
90
  @ReactProp(name = "titleColor", customType = "Color")
81
- fun setTitleColor(config: ScreenStackHeaderConfig, titleColor: Int) {
82
- config.setTitleColor(titleColor)
91
+ override fun setTitleColor(config: ScreenStackHeaderConfig, titleColor: Int?) {
92
+ if (titleColor != null) {
93
+ config.setTitleColor(titleColor)
94
+ }
83
95
  }
84
96
 
85
97
  @ReactProp(name = "backgroundColor", customType = "Color")
86
- fun setBackgroundColor(config: ScreenStackHeaderConfig, backgroundColor: Int?) {
98
+ override fun setBackgroundColor(config: ScreenStackHeaderConfig, backgroundColor: Int?) {
87
99
  config.setBackgroundColor(backgroundColor)
88
100
  }
89
101
 
90
102
  @ReactProp(name = "hideShadow")
91
- fun setHideShadow(config: ScreenStackHeaderConfig, hideShadow: Boolean) {
103
+ override fun setHideShadow(config: ScreenStackHeaderConfig, hideShadow: Boolean) {
92
104
  config.setHideShadow(hideShadow)
93
105
  }
94
106
 
95
107
  @ReactProp(name = "hideBackButton")
96
- fun setHideBackButton(config: ScreenStackHeaderConfig, hideBackButton: Boolean) {
108
+ override fun setHideBackButton(config: ScreenStackHeaderConfig, hideBackButton: Boolean) {
97
109
  config.setHideBackButton(hideBackButton)
98
110
  }
99
111
 
100
112
  @ReactProp(name = "topInsetEnabled")
101
- fun setTopInsetEnabled(config: ScreenStackHeaderConfig, topInsetEnabled: Boolean) {
113
+ override fun setTopInsetEnabled(config: ScreenStackHeaderConfig, topInsetEnabled: Boolean) {
102
114
  config.setTopInsetEnabled(topInsetEnabled)
103
115
  }
104
116
 
105
117
  @ReactProp(name = "color", customType = "Color")
106
- fun setColor(config: ScreenStackHeaderConfig, color: Int) {
107
- config.setTintColor(color)
118
+ override fun setColor(config: ScreenStackHeaderConfig, color: Int?) {
119
+ config.setTintColor(color ?: 0)
108
120
  }
109
121
 
110
122
  @ReactProp(name = "hidden")
111
- fun setHidden(config: ScreenStackHeaderConfig, hidden: Boolean) {
123
+ override fun setHidden(config: ScreenStackHeaderConfig, hidden: Boolean) {
112
124
  config.setHidden(hidden)
113
125
  }
114
126
 
115
127
  @ReactProp(name = "translucent")
116
- fun setTranslucent(config: ScreenStackHeaderConfig, translucent: Boolean) {
128
+ override fun setTranslucent(config: ScreenStackHeaderConfig, translucent: Boolean) {
117
129
  config.setTranslucent(translucent)
118
130
  }
119
131
 
120
132
  @ReactProp(name = "backButtonInCustomView")
121
- fun setBackButtonInCustomView(
133
+ override fun setBackButtonInCustomView(
122
134
  config: ScreenStackHeaderConfig,
123
135
  backButtonInCustomView: Boolean
124
136
  ) {
@@ -126,7 +138,7 @@ class ScreenStackHeaderConfigViewManager : ViewGroupManager<ScreenStackHeaderCon
126
138
  }
127
139
 
128
140
  @ReactProp(name = "direction")
129
- fun setDirection(config: ScreenStackHeaderConfig, direction: String?) {
141
+ override fun setDirection(config: ScreenStackHeaderConfig, direction: String?) {
130
142
  config.setDirection(direction)
131
143
  }
132
144
 
@@ -137,7 +149,60 @@ class ScreenStackHeaderConfigViewManager : ViewGroupManager<ScreenStackHeaderCon
137
149
  .build()
138
150
  }
139
151
 
152
+ protected override fun getDelegate(): ViewManagerDelegate<ScreenStackHeaderConfig> {
153
+ return mDelegate
154
+ }
155
+
140
156
  companion object {
141
157
  const val REACT_CLASS = "RNSScreenStackHeaderConfig"
142
158
  }
159
+
160
+ // TODO: Find better way to handle platform specific props
161
+ private fun logNotAvailable(propName: String) {
162
+ Log.w("RN SCREENS", "$propName prop is not available on Android")
163
+ }
164
+
165
+ override fun setBackTitle(view: ScreenStackHeaderConfig?, value: String?) {
166
+ logNotAvailable("backTitle")
167
+ }
168
+
169
+ override fun setBackTitleFontFamily(view: ScreenStackHeaderConfig?, value: String?) {
170
+ logNotAvailable("backTitleFontFamily")
171
+ }
172
+
173
+ override fun setBackTitleFontSize(view: ScreenStackHeaderConfig?, value: Int) {
174
+ logNotAvailable("backTitleFontSize")
175
+ }
176
+
177
+ override fun setLargeTitle(view: ScreenStackHeaderConfig?, value: Boolean) {
178
+ logNotAvailable("largeTitle")
179
+ }
180
+
181
+ override fun setLargeTitleFontFamily(view: ScreenStackHeaderConfig?, value: String?) {
182
+ logNotAvailable("largeTitleFontFamily")
183
+ }
184
+
185
+ override fun setLargeTitleFontSize(view: ScreenStackHeaderConfig?, value: Int) {
186
+ logNotAvailable("largeTitleFontSize")
187
+ }
188
+
189
+ override fun setLargeTitleFontWeight(view: ScreenStackHeaderConfig?, value: String?) {
190
+ logNotAvailable("largeTitleFontWeight")
191
+ }
192
+
193
+ override fun setLargeTitleBackgroundColor(view: ScreenStackHeaderConfig?, value: Int?) {
194
+ logNotAvailable("largeTitleBackgroundColor")
195
+ }
196
+
197
+ override fun setLargeTitleHideShadow(view: ScreenStackHeaderConfig?, value: Boolean) {
198
+ logNotAvailable("largeTitleHideShadow")
199
+ }
200
+
201
+ override fun setLargeTitleColor(view: ScreenStackHeaderConfig?, value: Int?) {
202
+ logNotAvailable("largeTitleColor")
203
+ }
204
+
205
+ override fun setDisableBackButtonMenu(view: ScreenStackHeaderConfig?, value: Boolean) {
206
+ logNotAvailable("disableBackButtonMenu")
207
+ }
143
208
  }
@@ -3,22 +3,30 @@ package com.swmansion.rnscreens
3
3
  import com.facebook.react.bridge.JSApplicationIllegalArgumentException
4
4
  import com.facebook.react.module.annotations.ReactModule
5
5
  import com.facebook.react.uimanager.ThemedReactContext
6
+ import com.facebook.react.uimanager.ViewGroupManager
7
+ import com.facebook.react.uimanager.ViewManagerDelegate
6
8
  import com.facebook.react.uimanager.annotations.ReactProp
7
- import com.facebook.react.views.view.ReactViewGroup
8
- import com.facebook.react.views.view.ReactViewManager
9
+ import com.facebook.react.viewmanagers.RNSScreenStackHeaderSubviewManagerDelegate
10
+ import com.facebook.react.viewmanagers.RNSScreenStackHeaderSubviewManagerInterface
9
11
 
10
12
  @ReactModule(name = ScreenStackHeaderSubviewManager.REACT_CLASS)
11
- class ScreenStackHeaderSubviewManager : ReactViewManager() {
13
+ class ScreenStackHeaderSubviewManager : ViewGroupManager<ScreenStackHeaderSubview>(), RNSScreenStackHeaderSubviewManagerInterface<ScreenStackHeaderSubview> {
14
+ private val mDelegate: ViewManagerDelegate<ScreenStackHeaderSubview>
15
+
16
+ init {
17
+ mDelegate = RNSScreenStackHeaderSubviewManagerDelegate<ScreenStackHeaderSubview, ScreenStackHeaderSubviewManager>(this)
18
+ }
19
+
12
20
  override fun getName(): String {
13
21
  return REACT_CLASS
14
22
  }
15
23
 
16
- override fun createViewInstance(context: ThemedReactContext): ReactViewGroup {
24
+ override fun createViewInstance(context: ThemedReactContext): ScreenStackHeaderSubview {
17
25
  return ScreenStackHeaderSubview(context)
18
26
  }
19
27
 
20
28
  @ReactProp(name = "type")
21
- fun setType(view: ScreenStackHeaderSubview, type: String) {
29
+ override fun setType(view: ScreenStackHeaderSubview, type: String?) {
22
30
  view.type = when (type) {
23
31
  "left" -> ScreenStackHeaderSubview.Type.LEFT
24
32
  "center" -> ScreenStackHeaderSubview.Type.CENTER
@@ -29,6 +37,10 @@ class ScreenStackHeaderSubviewManager : ReactViewManager() {
29
37
  }
30
38
  }
31
39
 
40
+ protected override fun getDelegate(): ViewManagerDelegate<ScreenStackHeaderSubview> {
41
+ return mDelegate
42
+ }
43
+
32
44
  companion object {
33
45
  const val REACT_CLASS = "RNSScreenStackHeaderSubview"
34
46
  }
@@ -7,9 +7,18 @@ import com.facebook.react.module.annotations.ReactModule
7
7
  import com.facebook.react.uimanager.LayoutShadowNode
8
8
  import com.facebook.react.uimanager.ThemedReactContext
9
9
  import com.facebook.react.uimanager.ViewGroupManager
10
+ import com.facebook.react.uimanager.ViewManagerDelegate
11
+ import com.facebook.react.viewmanagers.RNSScreenStackManagerDelegate
12
+ import com.facebook.react.viewmanagers.RNSScreenStackManagerInterface
10
13
 
11
14
  @ReactModule(name = ScreenStackViewManager.REACT_CLASS)
12
- class ScreenStackViewManager : ViewGroupManager<ScreenStack>() {
15
+ class ScreenStackViewManager : ViewGroupManager<ScreenStack>(), RNSScreenStackManagerInterface<ScreenStack> {
16
+ private val mDelegate: ViewManagerDelegate<ScreenStack>
17
+
18
+ init {
19
+ mDelegate = RNSScreenStackManagerDelegate<ScreenStack, ScreenStackViewManager>(this)
20
+ }
21
+
13
22
  override fun getName(): String {
14
23
  return REACT_CLASS
15
24
  }
@@ -68,6 +77,10 @@ class ScreenStackViewManager : ViewGroupManager<ScreenStack>() {
68
77
  return true
69
78
  }
70
79
 
80
+ protected override fun getDelegate(): ViewManagerDelegate<ScreenStack> {
81
+ return mDelegate
82
+ }
83
+
71
84
  companion object {
72
85
  const val REACT_CLASS = "RNSScreenStack"
73
86
  }