@@ -7,6 +7,7 @@ import android.app.Activity
7
7
import android.content.res.Configuration
8
8
import android.graphics.Color
9
9
import android.util.TypedValue
10
+ import android.view.Window
10
11
import android.view.WindowManager
11
12
12
13
import androidx.core.view.WindowCompat
@@ -26,6 +27,9 @@ object EdgeToEdgeModuleImpl {
26
27
private const val NO_ACTIVITY_ERROR = " $NAME : Ignored system bars change, current activity is null."
27
28
private val boolAttributes = mutableMapOf<Int , Boolean >()
28
29
30
+ private var statusBarHidden = false
31
+ private var navigationBarHidden = false
32
+
29
33
private fun resolveBoolAttribute (activity : Activity , resId : Int ): Boolean =
30
34
boolAttributes.getOrPut(resId) {
31
35
val value = TypedValue ()
@@ -40,14 +44,30 @@ object EdgeToEdgeModuleImpl {
40
44
private fun isNavigationBarTransparent (activity : Activity ): Boolean =
41
45
! resolveBoolAttribute(activity, R .attr.enforceNavigationBarContrast)
42
46
47
+ // re-apply statusBarHidden / navigationBarHidden each time we instantiate a WindowInsetsControllerCompat
48
+ // see https://github.com/zoontek/react-native-edge-to-edge/issues/66
49
+ private fun initInsetsController (window : Window ): WindowInsetsControllerCompat =
50
+ WindowInsetsControllerCompat (window, window.decorView).apply {
51
+ systemBarsBehavior = WindowInsetsControllerCompat .BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE
52
+
53
+ when (statusBarHidden) {
54
+ true -> hide(WindowInsetsCompat .Type .statusBars())
55
+ else -> show(WindowInsetsCompat .Type .statusBars())
56
+ }
57
+ when (navigationBarHidden) {
58
+ true -> hide(WindowInsetsCompat .Type .navigationBars())
59
+ else -> show(WindowInsetsCompat .Type .navigationBars())
60
+ }
61
+ }
62
+
43
63
@Suppress(" DEPRECATION" )
44
64
fun applyEdgeToEdge (reactContext : ReactApplicationContext ? ) {
45
65
val activity = reactContext?.currentActivity
46
66
? : return FLog .w(ReactConstants .TAG , " $NAME : Ignored, current activity is null." )
47
67
48
68
activity.runOnUiThread {
49
69
val window = activity.window
50
- val insetsController = WindowInsetsControllerCompat (window, window.decorView )
70
+ val insetsController = initInsetsController (window)
51
71
52
72
WindowCompat .setDecorFitsSystemWindows(window, false )
53
73
@@ -88,11 +108,6 @@ object EdgeToEdgeModuleImpl {
88
108
else -> WindowManager .LayoutParams .LAYOUT_IN_DISPLAY_CUTOUT_MODE_SHORT_EDGES
89
109
}
90
110
}
91
-
92
- // re-apply WindowInsetsController systemBarsBehavior each time
93
- // see https://github.com/zoontek/react-native-edge-to-edge/issues/66
94
- insetsController.systemBarsBehavior =
95
- WindowInsetsControllerCompat .BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE
96
111
}
97
112
}
98
113
@@ -101,16 +116,12 @@ object EdgeToEdgeModuleImpl {
101
116
? : return FLog .w(ReactConstants .TAG , NO_ACTIVITY_ERROR )
102
117
103
118
activity.runOnUiThread {
104
- val window = activity.window
105
- val insetsController = WindowInsetsControllerCompat (window, window.decorView)
106
-
107
- insetsController.systemBarsBehavior =
108
- WindowInsetsControllerCompat .BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE
109
-
110
- insetsController.isAppearanceLightStatusBars = when (style) {
111
- " dark-content" -> true
112
- " light-content" -> false
113
- else -> isDefaultLightSystemBars(activity)
119
+ initInsetsController(activity.window).run {
120
+ isAppearanceLightStatusBars = when (style) {
121
+ " light-content" -> false
122
+ " dark-content" -> true
123
+ else -> isDefaultLightSystemBars(activity)
124
+ }
114
125
}
115
126
}
116
127
}
@@ -121,16 +132,12 @@ object EdgeToEdgeModuleImpl {
121
132
122
133
if (VERSION .SDK_INT >= VERSION_CODES .O_MR1 && isNavigationBarTransparent(activity)) {
123
134
activity.runOnUiThread {
124
- val window = activity.window
125
- val insetsController = WindowInsetsControllerCompat (window, window.decorView)
126
-
127
- insetsController.systemBarsBehavior =
128
- WindowInsetsControllerCompat .BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE
129
-
130
- insetsController.isAppearanceLightNavigationBars = when (style) {
131
- " dark-content" -> true
132
- " light-content" -> false
133
- else -> isDefaultLightSystemBars(activity)
135
+ initInsetsController(activity.window).run {
136
+ isAppearanceLightNavigationBars = when (style) {
137
+ " light-content" -> false
138
+ " dark-content" -> true
139
+ else -> isDefaultLightSystemBars(activity)
140
+ }
134
141
}
135
142
}
136
143
}
@@ -140,35 +147,15 @@ object EdgeToEdgeModuleImpl {
140
147
val activity = reactContext?.currentActivity
141
148
? : return FLog .w(ReactConstants .TAG , NO_ACTIVITY_ERROR )
142
149
143
- activity.runOnUiThread {
144
- val window = activity.window
145
- val insetsController = WindowInsetsControllerCompat (window, window.decorView)
146
-
147
- insetsController.systemBarsBehavior =
148
- WindowInsetsControllerCompat .BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE
149
-
150
- when (hidden) {
151
- true -> insetsController.hide(WindowInsetsCompat .Type .statusBars())
152
- else -> insetsController.show(WindowInsetsCompat .Type .statusBars())
153
- }
154
- }
150
+ statusBarHidden = hidden
151
+ activity.runOnUiThread { initInsetsController(activity.window) }
155
152
}
156
153
157
154
fun setNavigationBarHidden (reactContext : ReactApplicationContext ? , hidden : Boolean ) {
158
155
val activity = reactContext?.currentActivity
159
156
? : return FLog .w(ReactConstants .TAG , NO_ACTIVITY_ERROR )
160
157
161
- activity.runOnUiThread {
162
- val window = activity.window
163
- val insetsController = WindowInsetsControllerCompat (window, window.decorView)
164
-
165
- insetsController.systemBarsBehavior =
166
- WindowInsetsControllerCompat .BEHAVIOR_SHOW_TRANSIENT_BARS_BY_SWIPE
167
-
168
- when (hidden) {
169
- true -> insetsController.hide(WindowInsetsCompat .Type .navigationBars())
170
- else -> insetsController.show(WindowInsetsCompat .Type .navigationBars())
171
- }
172
- }
158
+ navigationBarHidden = hidden
159
+ activity.runOnUiThread { initInsetsController(activity.window) }
173
160
}
174
161
}
0 commit comments