react-native-navigation 8.1.2 → 8.2.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.
- package/lib/android/app/build.gradle +2 -1
- package/lib/android/app/src/main/java/com/reactnativenavigation/FeatureToggles.kt +2 -0
- package/lib/android/app/src/main/java/com/reactnativenavigation/options/BottomTabsOptions.java +21 -1
- package/lib/android/app/src/main/java/com/reactnativenavigation/options/LayoutDirection.java +6 -1
- package/lib/android/app/src/main/java/com/reactnativenavigation/options/params/BottomTabsLayoutStyle.kt +20 -0
- package/lib/android/app/src/main/java/com/reactnativenavigation/utils/ColorUtils.java +4 -0
- package/lib/android/app/src/main/java/com/reactnativenavigation/viewcontrollers/bottomtabs/BottomTabsController.java +12 -2
- package/lib/android/app/src/main/java/com/reactnativenavigation/viewcontrollers/bottomtabs/BottomTabsPresenter.kt +129 -11
- package/lib/android/app/src/main/java/com/reactnativenavigation/viewcontrollers/component/ComponentViewController.java +2 -1
- package/lib/android/app/src/main/java/com/reactnativenavigation/views/bottomtabs/BottomTabs.java +6 -6
- package/lib/android/app/src/main/java/com/reactnativenavigation/views/bottomtabs/BottomTabsContainer.kt +83 -5
- package/lib/android/app/src/main/java/com/reactnativenavigation/views/bottomtabs/BottomTabsLayout.java +58 -6
- package/lib/android/app/src/main/java/com/reactnativenavigation/views/bottomtabs/ShadowLayout.kt +4 -8
- package/lib/dist/src/interfaces/Options.d.ts +37 -3
- package/lib/src/interfaces/Options.ts +37 -3
- package/package.json +1 -1
|
@@ -94,7 +94,8 @@ dependencies {
|
|
|
94
94
|
implementation 'androidx.annotation:annotation:1.2.0'
|
|
95
95
|
implementation 'com.google.android.material:material:1.2.0-alpha03'
|
|
96
96
|
|
|
97
|
-
implementation 'com.github.wix-playground:ahbottomnavigation:
|
|
97
|
+
implementation 'com.github.wix-playground:ahbottomnavigation:4.0.0'
|
|
98
|
+
implementation 'com.github.Dimezis:BlurView:version-3.0.0'
|
|
98
99
|
// implementation project(':AHBottomNavigation')
|
|
99
100
|
implementation 'com.github.wix-playground:reflow-animator:1.0.6'
|
|
100
101
|
implementation 'com.github.clans:fab:1.6.4'
|
|
@@ -5,11 +5,13 @@ import androidx.annotation.VisibleForTesting
|
|
|
5
5
|
enum class RNNToggles {
|
|
6
6
|
TOP_BAR_COLOR_ANIMATION__PUSH,
|
|
7
7
|
TOP_BAR_COLOR_ANIMATION__TABS,
|
|
8
|
+
TAB_BAR_TRANSLUCENCE,
|
|
8
9
|
}
|
|
9
10
|
|
|
10
11
|
private val ToggleDefaults = mapOf(
|
|
11
12
|
RNNToggles.TOP_BAR_COLOR_ANIMATION__PUSH to false,
|
|
12
13
|
RNNToggles.TOP_BAR_COLOR_ANIMATION__TABS to false,
|
|
14
|
+
RNNToggles.TAB_BAR_TRANSLUCENCE to false,
|
|
13
15
|
)
|
|
14
16
|
|
|
15
17
|
object RNNFeatureToggles {
|
package/lib/android/app/src/main/java/com/reactnativenavigation/options/BottomTabsOptions.java
CHANGED
|
@@ -3,6 +3,7 @@ package com.reactnativenavigation.options;
|
|
|
3
3
|
import android.content.Context;
|
|
4
4
|
|
|
5
5
|
import com.reactnativenavigation.options.params.Bool;
|
|
6
|
+
import com.reactnativenavigation.options.params.BottomTabsLayoutStyle;
|
|
6
7
|
import com.reactnativenavigation.options.params.Fraction;
|
|
7
8
|
import com.reactnativenavigation.options.params.NullBool;
|
|
8
9
|
import com.reactnativenavigation.options.params.NullFraction;
|
|
@@ -27,6 +28,11 @@ public class BottomTabsOptions {
|
|
|
27
28
|
if (json == null) return options;
|
|
28
29
|
|
|
29
30
|
options.backgroundColor = ThemeColour.parse(context, json.optJSONObject("backgroundColor"));
|
|
31
|
+
options.layoutStyle = BottomTabsLayoutStyle.fromString(json.optString("layoutStyle"));
|
|
32
|
+
options.bottomMargin = FractionParser.parse(json, "bottomMargin");
|
|
33
|
+
options.cornerRadius = FractionParser.parse(json, "cornerRadius");
|
|
34
|
+
options.translucent = BoolParser.parse(json, "translucent");
|
|
35
|
+
options.blurRadius = FractionParser.parse(json, "blurRadius");
|
|
30
36
|
options.currentTabId = TextParser.parse(json, "currentTabId");
|
|
31
37
|
options.currentTabIndex = NumberParser.parse(json, "currentTabIndex");
|
|
32
38
|
options.hideOnScroll = BoolParser.parse(json, "hideOnScroll");
|
|
@@ -46,6 +52,11 @@ public class BottomTabsOptions {
|
|
|
46
52
|
}
|
|
47
53
|
|
|
48
54
|
public ThemeColour backgroundColor = new NullThemeColour();
|
|
55
|
+
public BottomTabsLayoutStyle layoutStyle = BottomTabsLayoutStyle.LAYOUT_STYLE_UNDEFINED;
|
|
56
|
+
public Fraction bottomMargin = new NullFraction();
|
|
57
|
+
public Fraction cornerRadius = new NullFraction();
|
|
58
|
+
public Bool translucent = new NullBool();
|
|
59
|
+
public Fraction blurRadius = new NullFraction();
|
|
49
60
|
public Bool hideOnScroll = new NullBool();
|
|
50
61
|
public Bool visible = new NullBool();
|
|
51
62
|
public Bool drawBehind = new NullBool();
|
|
@@ -79,12 +90,21 @@ public class BottomTabsOptions {
|
|
|
79
90
|
if (other.shadowOptions.hasValue()) shadowOptions = shadowOptions.copy().mergeWith(other.shadowOptions);
|
|
80
91
|
if (other.borderColor.hasValue()) borderColor = other.borderColor;
|
|
81
92
|
if (other.backgroundColor.hasValue()) backgroundColor = other.backgroundColor;
|
|
82
|
-
|
|
93
|
+
if (other.translucent.hasValue()) translucent = other.translucent;
|
|
94
|
+
if (other.blurRadius.hasValue()) blurRadius = other.blurRadius;
|
|
95
|
+
if (other.layoutStyle.hasValue()) layoutStyle = other.layoutStyle;
|
|
96
|
+
if (other.bottomMargin.hasValue()) bottomMargin = other.bottomMargin;
|
|
97
|
+
if (other.cornerRadius.hasValue()) cornerRadius = other.cornerRadius;
|
|
83
98
|
}
|
|
84
99
|
|
|
85
100
|
void mergeWithDefault(final BottomTabsOptions defaultOptions) {
|
|
86
101
|
if (!borderColor.hasValue()) borderColor = defaultOptions.borderColor;
|
|
87
102
|
if (!backgroundColor.hasValue()) backgroundColor = defaultOptions.backgroundColor;
|
|
103
|
+
if (!translucent.hasValue()) translucent = defaultOptions.translucent;
|
|
104
|
+
if (!blurRadius.hasValue()) blurRadius = defaultOptions.blurRadius;
|
|
105
|
+
if (!layoutStyle.hasValue()) layoutStyle = defaultOptions.layoutStyle;
|
|
106
|
+
if (!bottomMargin.hasValue()) bottomMargin = defaultOptions.bottomMargin;
|
|
107
|
+
if (!cornerRadius.hasValue()) cornerRadius = defaultOptions.cornerRadius;
|
|
88
108
|
if (!currentTabId.hasValue()) currentTabId = defaultOptions.currentTabId;
|
|
89
109
|
if (!currentTabIndex.hasValue()) currentTabIndex = defaultOptions.currentTabIndex;
|
|
90
110
|
if (!hideOnScroll.hasValue()) hideOnScroll = defaultOptions.hideOnScroll;
|
package/lib/android/app/src/main/java/com/reactnativenavigation/options/LayoutDirection.java
CHANGED
|
@@ -35,7 +35,12 @@ public enum LayoutDirection {
|
|
|
35
35
|
}
|
|
36
36
|
|
|
37
37
|
public int get() {
|
|
38
|
-
return direction
|
|
38
|
+
return switch (direction) {
|
|
39
|
+
case View.LAYOUT_DIRECTION_RTL -> RTL.direction;
|
|
40
|
+
case View.LAYOUT_DIRECTION_LTR -> LTR.direction;
|
|
41
|
+
case View.LAYOUT_DIRECTION_LOCALE -> LOCALE.direction;
|
|
42
|
+
default -> DEFAULT.direction;
|
|
43
|
+
};
|
|
39
44
|
}
|
|
40
45
|
|
|
41
46
|
public int inverse() {
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
package com.reactnativenavigation.options.params
|
|
2
|
+
|
|
3
|
+
enum class BottomTabsLayoutStyle {
|
|
4
|
+
STRETCH,
|
|
5
|
+
COMPACT,
|
|
6
|
+
LAYOUT_STYLE_UNDEFINED;
|
|
7
|
+
|
|
8
|
+
fun hasValue(): Boolean = (this != LAYOUT_STYLE_UNDEFINED)
|
|
9
|
+
|
|
10
|
+
companion object {
|
|
11
|
+
@JvmStatic
|
|
12
|
+
fun fromString(mode: String?): BottomTabsLayoutStyle {
|
|
13
|
+
return when (mode?.lowercase()) {
|
|
14
|
+
"stretch" -> STRETCH
|
|
15
|
+
"compact" -> COMPACT
|
|
16
|
+
else -> LAYOUT_STYLE_UNDEFINED
|
|
17
|
+
}
|
|
18
|
+
}
|
|
19
|
+
}
|
|
20
|
+
}
|
|
@@ -63,7 +63,15 @@ public class BottomTabsController extends ParentController<BottomTabsLayout> imp
|
|
|
63
63
|
tabPresenter.onConfigurationChanged(resolveCurrentOptions());
|
|
64
64
|
}
|
|
65
65
|
|
|
66
|
-
public BottomTabsController(Activity activity,
|
|
66
|
+
public BottomTabsController(Activity activity,
|
|
67
|
+
List<ViewController<?>> tabs,
|
|
68
|
+
ChildControllersRegistry childRegistry,
|
|
69
|
+
EventEmitter eventEmitter,
|
|
70
|
+
ImageLoader imageLoader,
|
|
71
|
+
String id, Options initialOptions,
|
|
72
|
+
Presenter presenter,
|
|
73
|
+
BottomTabsAttacher tabsAttacher,
|
|
74
|
+
BottomTabsPresenter bottomTabsPresenter, BottomTabPresenter bottomTabPresenter) {
|
|
67
75
|
super(activity, childRegistry, id, presenter, initialOptions);
|
|
68
76
|
this.tabs = tabs;
|
|
69
77
|
this.eventEmitter = eventEmitter;
|
|
@@ -86,15 +94,17 @@ public class BottomTabsController extends ParentController<BottomTabsLayout> imp
|
|
|
86
94
|
@Override
|
|
87
95
|
public BottomTabsLayout createView() {
|
|
88
96
|
BottomTabsLayout root = new BottomTabsLayout(getActivity());
|
|
97
|
+
root.setTag("RNN.BottomTabsLayoutRoot");
|
|
89
98
|
|
|
90
99
|
this.bottomTabsContainer = createBottomTabsContainer();
|
|
91
100
|
this.bottomTabs = bottomTabsContainer.getBottomTabs();
|
|
92
101
|
Options resolveCurrentOptions = resolveCurrentOptions();
|
|
93
102
|
tabsAttacher.init(root, resolveCurrentOptions);
|
|
94
|
-
presenter.bindView(bottomTabsContainer, this);
|
|
103
|
+
presenter.bindView(bottomTabsContainer, root, this);
|
|
95
104
|
tabPresenter.bindView(bottomTabs);
|
|
96
105
|
bottomTabs.setOnTabSelectedListener(this);
|
|
97
106
|
root.addBottomTabsContainer(bottomTabsContainer);
|
|
107
|
+
|
|
98
108
|
bottomTabs.addItems(createTabs());
|
|
99
109
|
setInitialTab(resolveCurrentOptions);
|
|
100
110
|
tabsAttacher.attach();
|
|
@@ -3,13 +3,20 @@ package com.reactnativenavigation.viewcontrollers.bottomtabs
|
|
|
3
3
|
import android.animation.Animator
|
|
4
4
|
import android.graphics.Color
|
|
5
5
|
import android.view.ViewGroup
|
|
6
|
+
import android.view.ViewGroup.LayoutParams.WRAP_CONTENT
|
|
6
7
|
import androidx.annotation.IntRange
|
|
7
8
|
import androidx.core.view.updateMargins
|
|
8
9
|
import com.aurelhubert.ahbottomnavigation.AHBottomNavigation.TitleState
|
|
10
|
+
import com.reactnativenavigation.RNNFeatureToggles
|
|
11
|
+
import com.reactnativenavigation.RNNToggles.TAB_BAR_TRANSLUCENCE
|
|
9
12
|
import com.reactnativenavigation.options.Options
|
|
13
|
+
import com.reactnativenavigation.options.params.BottomTabsLayoutStyle
|
|
14
|
+
import com.reactnativenavigation.options.params.Fraction
|
|
15
|
+
import com.reactnativenavigation.utils.UiUtils
|
|
10
16
|
import com.reactnativenavigation.viewcontrollers.viewcontroller.ViewController
|
|
11
17
|
import com.reactnativenavigation.views.bottomtabs.BottomTabs
|
|
12
18
|
import com.reactnativenavigation.views.bottomtabs.BottomTabsContainer
|
|
19
|
+
import com.reactnativenavigation.views.bottomtabs.BottomTabsLayout
|
|
13
20
|
import kotlin.math.max
|
|
14
21
|
import kotlin.math.roundToInt
|
|
15
22
|
|
|
@@ -20,12 +27,13 @@ class BottomTabsPresenter(
|
|
|
20
27
|
) {
|
|
21
28
|
private val bottomTabFinder: BottomTabFinder = BottomTabFinder(tabs)
|
|
22
29
|
private lateinit var bottomTabsContainer: BottomTabsContainer
|
|
30
|
+
private lateinit var bottomTabsLayout: BottomTabsLayout
|
|
23
31
|
private lateinit var bottomTabs: BottomTabs
|
|
24
32
|
private lateinit var tabSelector: TabSelector
|
|
25
33
|
private val defaultTitleState: TitleState
|
|
26
34
|
get() {
|
|
27
35
|
for (i in 0 until bottomTabs.itemsCount) {
|
|
28
|
-
if (bottomTabs.getItem(i)
|
|
36
|
+
if (bottomTabs.getItem(i)?.hasIcon() == true) return TitleState.SHOW_WHEN_ACTIVE
|
|
29
37
|
}
|
|
30
38
|
return TitleState.ALWAYS_SHOW
|
|
31
39
|
}
|
|
@@ -34,8 +42,9 @@ class BottomTabsPresenter(
|
|
|
34
42
|
this.defaultOptions = defaultOptions
|
|
35
43
|
}
|
|
36
44
|
|
|
37
|
-
fun bindView(bottomTabsContainer: BottomTabsContainer, tabSelector: TabSelector) {
|
|
45
|
+
fun bindView(bottomTabsContainer: BottomTabsContainer, bottomTabsLayout: BottomTabsLayout, tabSelector: TabSelector) {
|
|
38
46
|
this.bottomTabsContainer = bottomTabsContainer
|
|
47
|
+
this.bottomTabsLayout = bottomTabsLayout
|
|
39
48
|
this.bottomTabs = bottomTabsContainer.bottomTabs
|
|
40
49
|
this.tabSelector = tabSelector
|
|
41
50
|
animator.bindView(this.bottomTabs)
|
|
@@ -65,14 +74,51 @@ class BottomTabsPresenter(
|
|
|
65
74
|
|
|
66
75
|
private fun mergeBottomTabsOptions(options: Options, view: ViewController<*>) {
|
|
67
76
|
val bottomTabsOptions = options.bottomTabsOptions
|
|
68
|
-
|
|
69
|
-
if (bottomTabsOptions.
|
|
70
|
-
|
|
71
|
-
bottomTabs.
|
|
77
|
+
|
|
78
|
+
if (bottomTabsOptions.layoutStyle == BottomTabsLayoutStyle.COMPACT) {
|
|
79
|
+
bottomTabs.layoutParams.width = WRAP_CONTENT
|
|
80
|
+
bottomTabs.refresh()
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
if (bottomTabsOptions.bottomMargin.hasValue()) {
|
|
84
|
+
val margin = extractBottomMarginPx(bottomTabsOptions.bottomMargin)
|
|
85
|
+
bottomTabsLayout.setBottomMargin(margin)
|
|
86
|
+
}
|
|
87
|
+
|
|
88
|
+
if (bottomTabsOptions.cornerRadius.hasValue()) {
|
|
89
|
+
val radius = extractCornerRadius(bottomTabsOptions.cornerRadius)
|
|
90
|
+
bottomTabsContainer.setRoundedCorners(radius)
|
|
72
91
|
}
|
|
92
|
+
|
|
93
|
+
// Keep this before the translucent check below
|
|
73
94
|
if (bottomTabsOptions.backgroundColor.hasValue()) {
|
|
74
95
|
bottomTabsContainer.setBackgroundColor(bottomTabsOptions.backgroundColor.get())
|
|
75
96
|
}
|
|
97
|
+
|
|
98
|
+
if (RNNFeatureToggles.isEnabled(TAB_BAR_TRANSLUCENCE)) {
|
|
99
|
+
if (bottomTabsOptions.translucent.isTrue) {
|
|
100
|
+
if (bottomTabsOptions.blurRadius.hasValue()) {
|
|
101
|
+
bottomTabsContainer.setBlurRadius(bottomTabsOptions.blurRadius.get().toFloat())
|
|
102
|
+
}
|
|
103
|
+
if (bottomTabsOptions.backgroundColor.hasValue()) {
|
|
104
|
+
bottomTabsContainer.setBlurColor(bottomTabsOptions.backgroundColor.get())
|
|
105
|
+
}
|
|
106
|
+
bottomTabsContainer.enableBackgroundBlur()
|
|
107
|
+
} else if (bottomTabsOptions.translucent.isFalse) {
|
|
108
|
+
bottomTabsContainer.disableBackgroundBlur()
|
|
109
|
+
}
|
|
110
|
+
}
|
|
111
|
+
|
|
112
|
+
if (bottomTabsOptions.elevation.hasValue()) {
|
|
113
|
+
bottomTabsContainer.setElevation(bottomTabsOptions.elevation)
|
|
114
|
+
}
|
|
115
|
+
|
|
116
|
+
if (options.layout.direction.hasValue()) bottomTabs.setLayoutDirection(options.layout.direction)
|
|
117
|
+
if (bottomTabsOptions.preferLargeIcons.hasValue()) bottomTabs.setPreferLargeIcons(bottomTabsOptions.preferLargeIcons.get())
|
|
118
|
+
if (bottomTabsOptions.titleDisplayMode.hasValue()) {
|
|
119
|
+
bottomTabs.setTitleState(bottomTabsOptions.titleDisplayMode.toState())
|
|
120
|
+
}
|
|
121
|
+
|
|
76
122
|
if (bottomTabsOptions.animateTabSelection.hasValue()) {
|
|
77
123
|
bottomTabs.setAnimateTabSelection(bottomTabsOptions.animateTabSelection.get())
|
|
78
124
|
}
|
|
@@ -88,7 +134,7 @@ class BottomTabsPresenter(
|
|
|
88
134
|
if (tabIndex >= 0) tabSelector.selectTab(tabIndex)
|
|
89
135
|
}
|
|
90
136
|
if (bottomTabsOptions.hideOnScroll.hasValue()) {
|
|
91
|
-
bottomTabs.
|
|
137
|
+
bottomTabs.setBehaviorTranslationEnabled(bottomTabsOptions.hideOnScroll.get())
|
|
92
138
|
}
|
|
93
139
|
|
|
94
140
|
if (bottomTabsOptions.borderColor.hasValue()) {
|
|
@@ -140,10 +186,39 @@ class BottomTabsPresenter(
|
|
|
140
186
|
|
|
141
187
|
private fun applyBottomTabsOptions(options: Options) {
|
|
142
188
|
val bottomTabsOptions = options.bottomTabsOptions
|
|
189
|
+
if (bottomTabsOptions.layoutStyle == BottomTabsLayoutStyle.COMPACT) {
|
|
190
|
+
bottomTabs.layoutParams.width = WRAP_CONTENT
|
|
191
|
+
}
|
|
192
|
+
|
|
193
|
+
if (bottomTabsOptions.bottomMargin.hasValue()) {
|
|
194
|
+
val margin = extractBottomMarginPx(bottomTabsOptions.bottomMargin)
|
|
195
|
+
bottomTabsLayout.setBottomMargin(margin)
|
|
196
|
+
}
|
|
197
|
+
|
|
198
|
+
if (bottomTabsOptions.cornerRadius.hasValue()) {
|
|
199
|
+
val radius = extractCornerRadius(bottomTabsOptions.cornerRadius)
|
|
200
|
+
bottomTabsContainer.setRoundedCorners(radius)
|
|
201
|
+
} else {
|
|
202
|
+
bottomTabsContainer.clearRoundedCorners()
|
|
203
|
+
}
|
|
204
|
+
|
|
205
|
+
if (RNNFeatureToggles.isEnabled(TAB_BAR_TRANSLUCENCE) && bottomTabsOptions.translucent.isTrue) {
|
|
206
|
+
if (bottomTabsOptions.blurRadius.hasValue()) {
|
|
207
|
+
bottomTabsContainer.setBlurRadius(bottomTabsOptions.blurRadius.get().toFloat())
|
|
208
|
+
}
|
|
209
|
+
if (bottomTabsOptions.backgroundColor.hasValue()) {
|
|
210
|
+
bottomTabsContainer.setBlurColor(bottomTabsOptions.backgroundColor.get())
|
|
211
|
+
}
|
|
212
|
+
bottomTabsContainer.enableBackgroundBlur()
|
|
213
|
+
} else {
|
|
214
|
+
bottomTabsContainer.disableBackgroundBlur()
|
|
215
|
+
bottomTabsContainer.setBackgroundColor(bottomTabsOptions.backgroundColor.get(Color.WHITE)!!)
|
|
216
|
+
}
|
|
217
|
+
|
|
143
218
|
bottomTabs.setLayoutDirection(options.layout.direction)
|
|
144
219
|
bottomTabs.setPreferLargeIcons(options.bottomTabsOptions.preferLargeIcons[false])
|
|
145
|
-
bottomTabs.
|
|
146
|
-
|
|
220
|
+
bottomTabs.setTitleState(bottomTabsOptions.titleDisplayMode[defaultTitleState])
|
|
221
|
+
|
|
147
222
|
bottomTabs.setAnimateTabSelection(bottomTabsOptions.animateTabSelection.get(true))
|
|
148
223
|
if (bottomTabsOptions.currentTabIndex.hasValue()) {
|
|
149
224
|
val tabIndex = bottomTabsOptions.currentTabIndex.get()
|
|
@@ -174,6 +249,7 @@ class BottomTabsPresenter(
|
|
|
174
249
|
bottomTabs.hideBottomNavigation(false)
|
|
175
250
|
}
|
|
176
251
|
}
|
|
252
|
+
|
|
177
253
|
if (bottomTabsOptions.elevation.hasValue()) {
|
|
178
254
|
bottomTabsContainer.setElevation(bottomTabsOptions.elevation)
|
|
179
255
|
}
|
|
@@ -203,7 +279,7 @@ class BottomTabsPresenter(
|
|
|
203
279
|
} else {
|
|
204
280
|
bottomTabsContainer.clearShadow()
|
|
205
281
|
}
|
|
206
|
-
bottomTabs.
|
|
282
|
+
bottomTabs.setBehaviorTranslationEnabled(bottomTabsOptions.hideOnScroll[false])
|
|
207
283
|
}
|
|
208
284
|
|
|
209
285
|
fun applyBottomInset(bottomInset: Int) {
|
|
@@ -246,7 +322,37 @@ class BottomTabsPresenter(
|
|
|
246
322
|
|
|
247
323
|
fun onConfigurationChanged(options: Options) {
|
|
248
324
|
val bottomTabsOptions = options.withDefaultOptions(defaultOptions).bottomTabsOptions
|
|
249
|
-
|
|
325
|
+
|
|
326
|
+
if (bottomTabsOptions.layoutStyle == BottomTabsLayoutStyle.COMPACT) {
|
|
327
|
+
bottomTabs.layoutParams.width = WRAP_CONTENT
|
|
328
|
+
}
|
|
329
|
+
|
|
330
|
+
if (bottomTabsOptions.bottomMargin.hasValue()) {
|
|
331
|
+
val margin = extractBottomMarginPx(bottomTabsOptions.bottomMargin)
|
|
332
|
+
bottomTabsLayout.setBottomMargin(margin)
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
if (bottomTabsOptions.cornerRadius.hasValue()) {
|
|
336
|
+
val radius = extractCornerRadius(bottomTabsOptions.cornerRadius)
|
|
337
|
+
bottomTabsContainer.setRoundedCorners(radius)
|
|
338
|
+
} else {
|
|
339
|
+
bottomTabsContainer.clearRoundedCorners()
|
|
340
|
+
}
|
|
341
|
+
|
|
342
|
+
if (RNNFeatureToggles.isEnabled(TAB_BAR_TRANSLUCENCE) && bottomTabsOptions.translucent.isTrue) {
|
|
343
|
+
if (bottomTabsOptions.blurRadius.hasValue()) {
|
|
344
|
+
bottomTabsContainer.setBlurRadius(bottomTabsOptions.blurRadius.get().toFloat())
|
|
345
|
+
}
|
|
346
|
+
if (bottomTabsOptions.backgroundColor.hasValue()) {
|
|
347
|
+
bottomTabsContainer.setBlurColor(bottomTabsOptions.backgroundColor.get())
|
|
348
|
+
}
|
|
349
|
+
bottomTabsContainer.enableBackgroundBlur()
|
|
350
|
+
} else {
|
|
351
|
+
bottomTabsContainer.disableBackgroundBlur()
|
|
352
|
+
|
|
353
|
+
// TODO Change to bottomTabsContainer.setBackgroundColor()?
|
|
354
|
+
bottomTabs.setBackgroundColor(bottomTabsOptions.backgroundColor.get(Color.WHITE)!!)
|
|
355
|
+
}
|
|
250
356
|
|
|
251
357
|
if (bottomTabsOptions.shadowOptions.hasValue()) {
|
|
252
358
|
if (bottomTabsOptions.shadowOptions.color.hasValue())
|
|
@@ -258,4 +364,16 @@ class BottomTabsPresenter(
|
|
|
258
364
|
bottomTabsContainer.showTopLine()
|
|
259
365
|
}
|
|
260
366
|
}
|
|
367
|
+
|
|
368
|
+
private fun extractCornerRadius(cornerRadius: Fraction): Float {
|
|
369
|
+
val radiusDp = cornerRadius.get()
|
|
370
|
+
val radius = UiUtils.dpToPx(bottomTabsContainer.context, radiusDp.toFloat())
|
|
371
|
+
return radius
|
|
372
|
+
}
|
|
373
|
+
|
|
374
|
+
private fun extractBottomMarginPx(bottomMargin: Fraction): Int {
|
|
375
|
+
val marginDp = bottomMargin.get()
|
|
376
|
+
val margin = UiUtils.dpToPx(bottomTabsContainer.context, marginDp.toFloat()).roundToInt()
|
|
377
|
+
return margin
|
|
378
|
+
}
|
|
261
379
|
}
|
|
@@ -84,8 +84,9 @@ public class ComponentViewController extends ChildController<ComponentLayout> {
|
|
|
84
84
|
@Override
|
|
85
85
|
public void onViewWillAppear() {
|
|
86
86
|
super.onViewWillAppear();
|
|
87
|
-
if (view != null)
|
|
87
|
+
if (view != null) {
|
|
88
88
|
view.sendComponentWillStart();
|
|
89
|
+
}
|
|
89
90
|
}
|
|
90
91
|
|
|
91
92
|
@Override
|
package/lib/android/app/src/main/java/com/reactnativenavigation/views/bottomtabs/BottomTabs.java
CHANGED
|
@@ -1,5 +1,8 @@
|
|
|
1
1
|
package com.reactnativenavigation.views.bottomtabs;
|
|
2
2
|
|
|
3
|
+
import static com.reactnativenavigation.utils.CollectionUtils.forEach;
|
|
4
|
+
import static com.reactnativenavigation.utils.ViewUtils.findChildByClass;
|
|
5
|
+
|
|
3
6
|
import android.annotation.SuppressLint;
|
|
4
7
|
import android.content.Context;
|
|
5
8
|
import android.graphics.Color;
|
|
@@ -7,6 +10,8 @@ import android.graphics.drawable.Drawable;
|
|
|
7
10
|
import android.view.View;
|
|
8
11
|
import android.widget.LinearLayout;
|
|
9
12
|
|
|
13
|
+
import androidx.annotation.IntRange;
|
|
14
|
+
|
|
10
15
|
import com.aurelhubert.ahbottomnavigation.AHBottomNavigation;
|
|
11
16
|
import com.aurelhubert.ahbottomnavigation.AHBottomNavigationItem;
|
|
12
17
|
import com.reactnativenavigation.R;
|
|
@@ -15,11 +20,6 @@ import com.reactnativenavigation.options.LayoutDirection;
|
|
|
15
20
|
import java.util.ArrayList;
|
|
16
21
|
import java.util.List;
|
|
17
22
|
|
|
18
|
-
import androidx.annotation.IntRange;
|
|
19
|
-
|
|
20
|
-
import static com.reactnativenavigation.utils.CollectionUtils.*;
|
|
21
|
-
import static com.reactnativenavigation.utils.ViewUtils.findChildByClass;
|
|
22
|
-
|
|
23
23
|
@SuppressLint("ViewConstructor")
|
|
24
24
|
public class BottomTabs extends AHBottomNavigation {
|
|
25
25
|
private boolean itemsCreationEnabled = true;
|
|
@@ -60,6 +60,7 @@ public class BottomTabs extends AHBottomNavigation {
|
|
|
60
60
|
}
|
|
61
61
|
}
|
|
62
62
|
|
|
63
|
+
// TODO Find a better way to do this
|
|
63
64
|
public void superCreateItems() {
|
|
64
65
|
super.createItems();
|
|
65
66
|
}
|
|
@@ -77,7 +78,6 @@ public class BottomTabs extends AHBottomNavigation {
|
|
|
77
78
|
onItemCreationEnabled.add(() -> super.setCurrentItem(position, useCallback));
|
|
78
79
|
}
|
|
79
80
|
}
|
|
80
|
-
|
|
81
81
|
|
|
82
82
|
@Override
|
|
83
83
|
public void setTitleState(TitleState titleState) {
|
|
@@ -3,12 +3,20 @@ package com.reactnativenavigation.views.bottomtabs
|
|
|
3
3
|
import android.annotation.SuppressLint
|
|
4
4
|
import android.content.Context
|
|
5
5
|
import android.graphics.Color
|
|
6
|
+
import android.graphics.Outline
|
|
7
|
+
import android.util.Log
|
|
6
8
|
import android.view.View
|
|
9
|
+
import android.view.ViewOutlineProvider
|
|
10
|
+
import android.widget.FrameLayout.LayoutParams.MATCH_PARENT
|
|
11
|
+
import android.widget.FrameLayout.LayoutParams.WRAP_CONTENT
|
|
7
12
|
import android.widget.LinearLayout
|
|
8
13
|
import androidx.annotation.RestrictTo
|
|
9
14
|
import androidx.core.graphics.ColorUtils
|
|
10
15
|
import com.reactnativenavigation.options.params.Fraction
|
|
11
16
|
import com.reactnativenavigation.utils.UiUtils.dpToPx
|
|
17
|
+
import eightbitlab.com.blurview.BlurTarget
|
|
18
|
+
import eightbitlab.com.blurview.BlurView
|
|
19
|
+
import java.lang.ref.WeakReference
|
|
12
20
|
import kotlin.math.roundToInt
|
|
13
21
|
|
|
14
22
|
|
|
@@ -20,16 +28,24 @@ internal const val DEFAULT_SHADOW_ANGLE = 270f
|
|
|
20
28
|
internal const val DEFAULT_TOP_OUTLINE_SIZE_PX = 1
|
|
21
29
|
internal const val DEFAULT_TOP_OUTLINE_COLOR = Color.DKGRAY
|
|
22
30
|
|
|
31
|
+
private const val LOG_TAG = "BottomTabs"
|
|
32
|
+
|
|
23
33
|
class TopOutlineView(context: Context) : View(context)
|
|
24
34
|
|
|
25
35
|
@SuppressLint("ViewConstructor")
|
|
26
36
|
class BottomTabsContainer(context: Context, val bottomTabs: BottomTabs) : ShadowLayout(context) {
|
|
27
37
|
|
|
38
|
+
private val blurringView: BlurView
|
|
39
|
+
private var blurringSurface = WeakReference<BlurTarget>(null)
|
|
40
|
+
private var blurEnabled: Boolean? = null
|
|
41
|
+
private var blurRadius: Float? = null
|
|
42
|
+
private var blurColor: Int? = null
|
|
43
|
+
|
|
28
44
|
var topOutLineView = TopOutlineView(context)
|
|
29
45
|
@RestrictTo(RestrictTo.Scope.TESTS, RestrictTo.Scope.SUBCLASSES) get
|
|
30
46
|
@RestrictTo(RestrictTo.Scope.TESTS) set(value) {
|
|
31
47
|
this.removeView(field)
|
|
32
|
-
addView(value, LayoutParams(
|
|
48
|
+
addView(value, LayoutParams(MATCH_PARENT, WRAP_CONTENT))
|
|
33
49
|
field = value
|
|
34
50
|
}
|
|
35
51
|
|
|
@@ -39,17 +55,23 @@ class BottomTabsContainer(context: Context, val bottomTabs: BottomTabs) : Shadow
|
|
|
39
55
|
shadowAngle = DEFAULT_SHADOW_ANGLE
|
|
40
56
|
shadowDistance = DEFAULT_SHADOW_DISTANCE
|
|
41
57
|
shadowColor = DEFAULT_SHADOW_COLOR
|
|
58
|
+
|
|
42
59
|
val linearLayout = LinearLayout(context).apply {
|
|
43
60
|
orientation = LinearLayout.VERTICAL
|
|
44
|
-
|
|
45
|
-
|
|
61
|
+
addView(topOutLineView, LayoutParams(MATCH_PARENT, DEFAULT_TOP_OUTLINE_SIZE_PX))
|
|
62
|
+
addView(bottomTabs, LinearLayout.LayoutParams.MATCH_PARENT, LinearLayout.LayoutParams.WRAP_CONTENT)
|
|
46
63
|
}
|
|
64
|
+
|
|
47
65
|
this.clipChildren = false
|
|
48
66
|
this.clipToPadding = false
|
|
49
67
|
setTopOutLineColor(DEFAULT_TOP_OUTLINE_COLOR)
|
|
50
68
|
this.topOutLineView.visibility = View.GONE
|
|
51
69
|
|
|
52
|
-
|
|
70
|
+
blurringView = BlurView(context).apply {
|
|
71
|
+
setBlurEnabled(false)
|
|
72
|
+
addView(linearLayout, WRAP_CONTENT, WRAP_CONTENT)
|
|
73
|
+
}
|
|
74
|
+
addView(blurringView, WRAP_CONTENT, WRAP_CONTENT)
|
|
53
75
|
}
|
|
54
76
|
|
|
55
77
|
override var shadowRadius: Float
|
|
@@ -70,6 +92,63 @@ class BottomTabsContainer(context: Context, val bottomTabs: BottomTabs) : Shadow
|
|
|
70
92
|
shadowColor = ColorUtils.setAlphaComponent(shadowColor, (opacity * 0xFF).roundToInt())
|
|
71
93
|
}
|
|
72
94
|
|
|
95
|
+
fun setBlurSurface(blurSurface: BlurTarget) {
|
|
96
|
+
if (blurSurface == blurringSurface.get()) {
|
|
97
|
+
return
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
blurringSurface = WeakReference(blurSurface)
|
|
101
|
+
blurringView
|
|
102
|
+
.setupWith(blurSurface)
|
|
103
|
+
.setBlurEnabled(blurEnabled == true).apply {
|
|
104
|
+
if (blurRadius != null) {
|
|
105
|
+
setBlurRadius(blurRadius!!)
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
if (blurColor != null) {
|
|
109
|
+
setOverlayColor(blurColor!!)
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
fun enableBackgroundBlur() {
|
|
115
|
+
blurringView.setBlurEnabled(true)
|
|
116
|
+
blurEnabled = true
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
fun disableBackgroundBlur() {
|
|
120
|
+
blurringView.setBlurEnabled(false)
|
|
121
|
+
blurEnabled = false
|
|
122
|
+
}
|
|
123
|
+
|
|
124
|
+
fun setBlurRadius(radius: Float) {
|
|
125
|
+
blurringView.setBlurRadius(radius)
|
|
126
|
+
blurRadius = radius
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
fun setBlurColor(color: Int) {
|
|
130
|
+
if (com.reactnativenavigation.utils.ColorUtils.isOpaque(color)) {
|
|
131
|
+
Log.w(LOG_TAG, "Opaque color (#${Integer.toHexString(color)}) set alongside blur-effect in bottom-tabs, rendering blur futile")
|
|
132
|
+
}
|
|
133
|
+
|
|
134
|
+
blurringView.setOverlayColor(color)
|
|
135
|
+
blurColor = color
|
|
136
|
+
}
|
|
137
|
+
|
|
138
|
+
fun setRoundedCorners(radius: Float) {
|
|
139
|
+
this.outlineProvider = object: ViewOutlineProvider() {
|
|
140
|
+
override fun getOutline(view: View, outline: Outline) {
|
|
141
|
+
outline.setRoundRect(0, 0, view.width, view.height, radius)
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
this.clipToOutline = true
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
fun clearRoundedCorners() {
|
|
148
|
+
this.outlineProvider = null
|
|
149
|
+
this.clipToOutline = true
|
|
150
|
+
}
|
|
151
|
+
|
|
73
152
|
fun showShadow() {
|
|
74
153
|
isShadowed = true
|
|
75
154
|
}
|
|
@@ -98,4 +177,3 @@ class BottomTabsContainer(context: Context, val bottomTabs: BottomTabs) : Shadow
|
|
|
98
177
|
setElevation(dpToPx(context, elevation.get().toFloat()))
|
|
99
178
|
}
|
|
100
179
|
}
|
|
101
|
-
|
|
@@ -1,18 +1,34 @@
|
|
|
1
1
|
package com.reactnativenavigation.views.bottomtabs;
|
|
2
2
|
|
|
3
|
+
import static android.view.Gravity.CENTER_HORIZONTAL;
|
|
4
|
+
import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
|
|
5
|
+
import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT;
|
|
6
|
+
|
|
3
7
|
import android.content.Context;
|
|
8
|
+
import android.graphics.Color;
|
|
4
9
|
import android.view.Gravity;
|
|
5
10
|
import android.view.View;
|
|
6
11
|
import android.view.ViewGroup;
|
|
12
|
+
import android.widget.LinearLayout;
|
|
7
13
|
|
|
8
14
|
import androidx.coordinatorlayout.widget.CoordinatorLayout;
|
|
9
15
|
|
|
10
|
-
import
|
|
11
|
-
import
|
|
16
|
+
import com.reactnativenavigation.RNNFeatureToggles;
|
|
17
|
+
import com.reactnativenavigation.RNNToggles;
|
|
18
|
+
|
|
19
|
+
import eightbitlab.com.blurview.BlurTarget;
|
|
12
20
|
|
|
21
|
+
/**
|
|
22
|
+
* Implementation note: The space-view and its containing linear-layout is a trick meant to force
|
|
23
|
+
* a bottom margin layout which isn't based on a `MarginLayoutParams.bottomMargin`. That's because
|
|
24
|
+
* it is not always honored by the CoordinatorLayout. This appears to be an ok work-around (which
|
|
25
|
+
* BTW actually would have been an idiomatic solution in ComposeUI).
|
|
26
|
+
*/
|
|
13
27
|
public class BottomTabsLayout extends CoordinatorLayout {
|
|
14
28
|
|
|
15
29
|
private BottomTabsContainer bottomTabsContainer;
|
|
30
|
+
private View spaceView;
|
|
31
|
+
private BlurTarget blurSurface;
|
|
16
32
|
|
|
17
33
|
public BottomTabsLayout(Context context) {
|
|
18
34
|
super(context);
|
|
@@ -21,16 +37,52 @@ public class BottomTabsLayout extends CoordinatorLayout {
|
|
|
21
37
|
@Override
|
|
22
38
|
public void addView(View child, int index, ViewGroup.LayoutParams params) {
|
|
23
39
|
if (bottomTabsContainer != null && child != bottomTabsContainer) {
|
|
24
|
-
|
|
40
|
+
if (RNNFeatureToggles.isEnabled(RNNToggles.TAB_BAR_TRANSLUCENCE)) {
|
|
41
|
+
// As loosely explained in BlurView's README, the blur *view* and blur *target* must
|
|
42
|
+
// reside in different sub-sections of the view-hierarchy
|
|
43
|
+
lazyInitBlurSurface();
|
|
44
|
+
blurSurface.addView(child, -1, params);
|
|
45
|
+
} else {
|
|
46
|
+
super.addView(child, getChildCount() - 1, params);
|
|
47
|
+
}
|
|
25
48
|
} else {
|
|
26
49
|
super.addView(child, 0, params);
|
|
27
50
|
}
|
|
51
|
+
|
|
52
|
+
if (bottomTabsContainer != null && blurSurface != null) {
|
|
53
|
+
bottomTabsContainer.setBlurSurface(blurSurface);
|
|
54
|
+
}
|
|
28
55
|
}
|
|
29
56
|
|
|
30
57
|
public void addBottomTabsContainer(BottomTabsContainer bottomTabsContainer) {
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
58
|
+
View spaceView = new View(getContext());
|
|
59
|
+
spaceView.setLayoutParams(new LinearLayout.LayoutParams(WRAP_CONTENT, 0));
|
|
60
|
+
|
|
61
|
+
LinearLayout surface = new LinearLayout(getContext());
|
|
62
|
+
surface.setOrientation(LinearLayout.VERTICAL);
|
|
63
|
+
surface.setGravity(CENTER_HORIZONTAL);
|
|
64
|
+
surface.setBackgroundColor(Color.TRANSPARENT);
|
|
65
|
+
surface.addView(bottomTabsContainer, new LinearLayout.LayoutParams(WRAP_CONTENT, WRAP_CONTENT));
|
|
66
|
+
surface.addView(spaceView);
|
|
67
|
+
|
|
68
|
+
// Note: Width should always be WRAP_CONTENT so we could delegate the width-related decision
|
|
69
|
+
// making to the bottom-tabs view hierarchy itself (i.e. based on user properties).
|
|
70
|
+
CoordinatorLayout.LayoutParams lp = new CoordinatorLayout.LayoutParams(WRAP_CONTENT, WRAP_CONTENT);
|
|
71
|
+
lp.gravity = Gravity.BOTTOM | CENTER_HORIZONTAL;
|
|
72
|
+
addView(surface, -1, lp);
|
|
73
|
+
|
|
34
74
|
this.bottomTabsContainer = bottomTabsContainer;
|
|
75
|
+
this.spaceView = spaceView;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
public void setBottomMargin(int bottomMargin) {
|
|
79
|
+
((MarginLayoutParams) spaceView.getLayoutParams()).bottomMargin = bottomMargin;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
private void lazyInitBlurSurface() {
|
|
83
|
+
if (blurSurface == null) {
|
|
84
|
+
blurSurface = new BlurTarget(getContext());
|
|
85
|
+
super.addView(blurSurface, super.getChildCount() - 1, new CoordinatorLayout.LayoutParams(MATCH_PARENT, MATCH_PARENT));
|
|
86
|
+
}
|
|
35
87
|
}
|
|
36
88
|
}
|
package/lib/android/app/src/main/java/com/reactnativenavigation/views/bottomtabs/ShadowLayout.kt
CHANGED
|
@@ -13,7 +13,7 @@ private const val MAX_ANGLE = 360.0f
|
|
|
13
13
|
private const val MIN_RADIUS = 0.1f
|
|
14
14
|
private const val MIN_ANGLE = 0.0f
|
|
15
15
|
|
|
16
|
-
open class ShadowLayout
|
|
16
|
+
open class ShadowLayout(context: Context) : FrameLayout(context) {
|
|
17
17
|
private val paint: Paint = Paint(ANTI_ALIAS_FLAG).apply {
|
|
18
18
|
isDither = true
|
|
19
19
|
isFilterBitmap = true
|
|
@@ -43,7 +43,7 @@ open class ShadowLayout constructor(context: Context) : FrameLayout(context) {
|
|
|
43
43
|
var isShadowed: Boolean = false
|
|
44
44
|
set(isShadowed) {
|
|
45
45
|
field = isShadowed
|
|
46
|
-
|
|
46
|
+
updatePadding()
|
|
47
47
|
postInvalidate()
|
|
48
48
|
}
|
|
49
49
|
|
|
@@ -108,11 +108,8 @@ open class ShadowLayout constructor(context: Context) : FrameLayout(context) {
|
|
|
108
108
|
if (isShadowed) {
|
|
109
109
|
if (invalidateShadow) {
|
|
110
110
|
if (bounds.width() != 0 && bounds.height() != 0) {
|
|
111
|
-
bitmap = Bitmap.createBitmap(
|
|
112
|
-
|
|
113
|
-
)
|
|
114
|
-
bitmap?.let {
|
|
115
|
-
mainCanvas.setBitmap(bitmap)
|
|
111
|
+
bitmap = Bitmap.createBitmap(bounds.width(), bounds.height(), Bitmap.Config.ARGB_8888).also {
|
|
112
|
+
mainCanvas.setBitmap(it)
|
|
116
113
|
invalidateShadow = false
|
|
117
114
|
|
|
118
115
|
super.dispatchDraw(mainCanvas)
|
|
@@ -135,5 +132,4 @@ open class ShadowLayout constructor(context: Context) : FrameLayout(context) {
|
|
|
135
132
|
|
|
136
133
|
super.dispatchDraw(canvas)
|
|
137
134
|
}
|
|
138
|
-
|
|
139
135
|
}
|
|
@@ -773,7 +773,9 @@ export interface OptionsBottomTabs {
|
|
|
773
773
|
*/
|
|
774
774
|
drawBehind?: boolean;
|
|
775
775
|
/**
|
|
776
|
-
* Set a background color for the bottom tabs
|
|
776
|
+
* Set a background color for the bottom tabs.<br/>
|
|
777
|
+
* On Android - also applicable when translucence is applied, but a semi-transparent
|
|
778
|
+
* color should be used (e.g. `rgba(255, 0, 0, 0.25)`).
|
|
777
779
|
*/
|
|
778
780
|
backgroundColor?: Color;
|
|
779
781
|
/**
|
|
@@ -789,10 +791,42 @@ export interface OptionsBottomTabs {
|
|
|
789
791
|
*/
|
|
790
792
|
barStyle?: 'default' | 'black';
|
|
791
793
|
/**
|
|
792
|
-
*
|
|
793
|
-
*
|
|
794
|
+
* Control the way the bottom tabs are laid out.
|
|
795
|
+
* - `stretch`: Fill the entire width of the screen.
|
|
796
|
+
* - `compact`: Occupy the minimum width needed to hold tab buttons. Recommended for
|
|
797
|
+
* usage in conjunction with `drawBehind: true`.
|
|
798
|
+
*
|
|
799
|
+
* #### (Android specific)
|
|
800
|
+
* @default 'stretch'
|
|
801
|
+
*/
|
|
802
|
+
layoutStyle?: 'stretch' | 'compact';
|
|
803
|
+
/**
|
|
804
|
+
* Specify a corner-radius (in dip) in order to apply round corners to the tabs container.<br/>
|
|
805
|
+
* Mainly suitable when used in conjunction with `layoutStyle: 'compact'`
|
|
806
|
+
* #### (Android specific)
|
|
807
|
+
*/
|
|
808
|
+
cornerRadius?: AndroidDensityNumber;
|
|
809
|
+
/**
|
|
810
|
+
* Bottom-margin to set in order to apply a "hover" effect.
|
|
811
|
+
* Works best when used in conjunction with `layoutStyle: 'compact'` and `drawBehind: true`.
|
|
812
|
+
* #### (Android specific)
|
|
813
|
+
*/
|
|
814
|
+
bottomMargin?: AndroidDensityNumber;
|
|
815
|
+
/**
|
|
816
|
+
* Allows the bottom tabs to be translucent (blurred). Doesn't necessarily play
|
|
817
|
+
* nice with shadow effects on Android.
|
|
818
|
+
* #### Android: experimental, turn on using native toggle `TAB_BAR_TRANSLUCENCE`.
|
|
794
819
|
*/
|
|
795
820
|
translucent?: boolean;
|
|
821
|
+
/**
|
|
822
|
+
* Set a custom radius to be used in the blur effect. Higher is blurrier, but
|
|
823
|
+
* also more CPU-intensive.<br/>
|
|
824
|
+
* Note: The blurring is performed following a bitmap downscale of x4.0, so
|
|
825
|
+
* ultimately the actual radius is (4*blurRadius).
|
|
826
|
+
* #### (Android specific)
|
|
827
|
+
* @defaultValue 1.0
|
|
828
|
+
*/
|
|
829
|
+
blurRadius?: AndroidDensityNumber;
|
|
796
830
|
/**
|
|
797
831
|
* Hide the top line of the Tab Bar
|
|
798
832
|
* #### (iOS specific)
|
|
@@ -855,7 +855,9 @@ export interface OptionsBottomTabs {
|
|
|
855
855
|
*/
|
|
856
856
|
drawBehind?: boolean;
|
|
857
857
|
/**
|
|
858
|
-
* Set a background color for the bottom tabs
|
|
858
|
+
* Set a background color for the bottom tabs.<br/>
|
|
859
|
+
* On Android - also applicable when translucence is applied, but a semi-transparent
|
|
860
|
+
* color should be used (e.g. `rgba(255, 0, 0, 0.25)`).
|
|
859
861
|
*/
|
|
860
862
|
backgroundColor?: Color;
|
|
861
863
|
/**
|
|
@@ -871,10 +873,42 @@ export interface OptionsBottomTabs {
|
|
|
871
873
|
*/
|
|
872
874
|
barStyle?: 'default' | 'black';
|
|
873
875
|
/**
|
|
874
|
-
*
|
|
875
|
-
*
|
|
876
|
+
* Control the way the bottom tabs are laid out.
|
|
877
|
+
* - `stretch`: Fill the entire width of the screen.
|
|
878
|
+
* - `compact`: Occupy the minimum width needed to hold tab buttons. Recommended for
|
|
879
|
+
* usage in conjunction with `drawBehind: true`.
|
|
880
|
+
*
|
|
881
|
+
* #### (Android specific)
|
|
882
|
+
* @default 'stretch'
|
|
883
|
+
*/
|
|
884
|
+
layoutStyle?: 'stretch' | 'compact';
|
|
885
|
+
/**
|
|
886
|
+
* Specify a corner-radius (in dip) in order to apply round corners to the tabs container.<br/>
|
|
887
|
+
* Mainly suitable when used in conjunction with `layoutStyle: 'compact'`
|
|
888
|
+
* #### (Android specific)
|
|
889
|
+
*/
|
|
890
|
+
cornerRadius?: AndroidDensityNumber;
|
|
891
|
+
/**
|
|
892
|
+
* Bottom-margin to set in order to apply a "hover" effect.
|
|
893
|
+
* Works best when used in conjunction with `layoutStyle: 'compact'` and `drawBehind: true`.
|
|
894
|
+
* #### (Android specific)
|
|
895
|
+
*/
|
|
896
|
+
bottomMargin?: AndroidDensityNumber;
|
|
897
|
+
/**
|
|
898
|
+
* Allows the bottom tabs to be translucent (blurred). Doesn't necessarily play
|
|
899
|
+
* nice with shadow effects on Android.
|
|
900
|
+
* #### Android: experimental, turn on using native toggle `TAB_BAR_TRANSLUCENCE`.
|
|
876
901
|
*/
|
|
877
902
|
translucent?: boolean;
|
|
903
|
+
/**
|
|
904
|
+
* Set a custom radius to be used in the blur effect. Higher is blurrier, but
|
|
905
|
+
* also more CPU-intensive.<br/>
|
|
906
|
+
* Note: The blurring is performed following a bitmap downscale of x4.0, so
|
|
907
|
+
* ultimately the actual radius is (4*blurRadius).
|
|
908
|
+
* #### (Android specific)
|
|
909
|
+
* @defaultValue 1.0
|
|
910
|
+
*/
|
|
911
|
+
blurRadius?: AndroidDensityNumber;
|
|
878
912
|
/**
|
|
879
913
|
* Hide the top line of the Tab Bar
|
|
880
914
|
* #### (iOS specific)
|