react-native-navigation 7.23.0 → 7.23.1-hotfix.1
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/.buildkite/pipeline.yml +47 -11
- package/.nvmrc +1 -0
- package/lib/android/app/src/main/java/com/reactnativenavigation/views/stack/topbar/titlebar/TitleBarReactView.kt +22 -1
- package/lib/dist/Mock/Stores/LayoutStore.js +4 -1
- package/lib/dist/interfaces/Options.d.ts +5 -0
- package/lib/ios/RNNAssert.h +2 -2
- package/lib/ios/RNNBottomTabOptions.m +2 -1
- package/lib/ios/RNNButtonBuilder.m +2 -0
- package/lib/ios/RNNButtonOptions.h +1 -0
- package/lib/ios/RNNButtonOptions.m +4 -0
- package/lib/ios/RNNCommandsHandler.m +1 -4
- package/lib/ios/RNNDotIndicatorPresenter.m +2 -1
- package/lib/ios/RNNModalManager.h +2 -0
- package/lib/ios/RNNModalManager.m +5 -0
- package/lib/ios/RNNSegmentedControl.h +1 -1
- package/lib/ios/RNNStackPresenter.m +3 -0
- package/lib/ios/RNNTabBarItemCreator.m +3 -2
- package/lib/ios/RNNUIBarButtonItem.h +2 -0
- package/lib/ios/RNNUIBarButtonItem.m +17 -0
- package/lib/ios/TopBarPresenter.m +8 -4
- package/lib/src/Mock/Stores/LayoutStore.ts +2 -1
- package/lib/src/interfaces/Options.ts +5 -0
- package/package.json +3 -3
package/.buildkite/pipeline.yml
CHANGED
|
@@ -1,19 +1,55 @@
|
|
|
1
|
-
env:
|
|
2
|
-
CI: true
|
|
3
|
-
ANDROID_HOME: /usr/local/share/android-sdk/
|
|
4
|
-
PATH: "$PATH:/usr/local/share/android-sdk/platform-tools/"
|
|
5
1
|
steps:
|
|
6
|
-
-
|
|
2
|
+
- block: ":rocket: Release!"
|
|
3
|
+
prompt: "Fill out the details for release"
|
|
4
|
+
if: 'build.message =~ /^release\$/i'
|
|
5
|
+
fields:
|
|
6
|
+
- text: "VERSION"
|
|
7
|
+
key: "version"
|
|
8
|
+
- text: "NPM_TAG"
|
|
9
|
+
key: "npm-tag"
|
|
10
|
+
default: 'null'
|
|
11
|
+
required: false
|
|
12
|
+
- text: "BUILD_DOCUMENTATION_VERSION"
|
|
13
|
+
key: "build-documentation-version"
|
|
14
|
+
default: 'null'
|
|
15
|
+
hint: 'Leave NULL if no version is specified'
|
|
16
|
+
- text: "REMOVE_DOCUMENTATION_VERSION"
|
|
17
|
+
key: "remove-documentation-version"
|
|
18
|
+
default: 'null'
|
|
19
|
+
hint: 'Leave NULL if no version is specified'
|
|
20
|
+
|
|
21
|
+
- label: ":android: Android"
|
|
7
22
|
command:
|
|
8
|
-
- "
|
|
23
|
+
- "nvm install"
|
|
9
24
|
- "npm install"
|
|
10
|
-
- "npm run
|
|
25
|
+
- "npm run test-js"
|
|
11
26
|
- "npm run test-unit-android -- --release"
|
|
12
27
|
- "npm run test-e2e-android-multi -- --release --headless --verbose --ci"
|
|
13
|
-
|
|
14
|
-
|
|
28
|
+
key: "android_build"
|
|
29
|
+
|
|
30
|
+
- label: ":ios: iOS - Unit"
|
|
15
31
|
command:
|
|
16
|
-
- "
|
|
32
|
+
- "nvm install"
|
|
17
33
|
- "npm install"
|
|
18
|
-
- "npm run
|
|
34
|
+
- "npm run test-unit-ios -- --release"
|
|
35
|
+
key: "ios_unit"
|
|
36
|
+
|
|
37
|
+
- label: ":ios: iOS - E2E"
|
|
38
|
+
command:
|
|
39
|
+
- "nvm install"
|
|
40
|
+
- "npm install"
|
|
41
|
+
- "npm run test-snapshot-ios -- --release"
|
|
19
42
|
- "npm run test-e2e-ios -- --release --multi --ci"
|
|
43
|
+
key: "ios_e2e"
|
|
44
|
+
|
|
45
|
+
- label: ":package: Publish"
|
|
46
|
+
env:
|
|
47
|
+
if: "build.pull_request.id == null"
|
|
48
|
+
command:
|
|
49
|
+
- "nvm install"
|
|
50
|
+
- "npm install"
|
|
51
|
+
- "npm run release"
|
|
52
|
+
depends_on:
|
|
53
|
+
- "android_build"
|
|
54
|
+
- "ios_unit"
|
|
55
|
+
- "ios_e2e"
|
package/.nvmrc
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
14
|
|
@@ -2,9 +2,30 @@ package com.reactnativenavigation.views.stack.topbar.titlebar
|
|
|
2
2
|
|
|
3
3
|
import android.annotation.SuppressLint
|
|
4
4
|
import android.content.Context
|
|
5
|
+
import androidx.core.view.children
|
|
5
6
|
import com.facebook.react.ReactInstanceManager
|
|
6
7
|
import com.reactnativenavigation.react.ReactView
|
|
7
8
|
|
|
8
9
|
@SuppressLint("ViewConstructor")
|
|
9
10
|
class TitleBarReactView(context: Context?, reactInstanceManager: ReactInstanceManager?, componentId: String?,
|
|
10
|
-
componentName: String?) : ReactView(context, reactInstanceManager, componentId, componentName)
|
|
11
|
+
componentName: String?) : ReactView(context, reactInstanceManager, componentId, componentName) {
|
|
12
|
+
override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
|
|
13
|
+
super.onMeasure(interceptReactRootViewMeasureSpec(widthMeasureSpec), heightMeasureSpec)
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
private fun interceptReactRootViewMeasureSpec(widthMeasureSpec: Int): Int {
|
|
17
|
+
// This is a HACK.
|
|
18
|
+
// ReactRootView has problematic behavior when setting width to WRAP_CONTENT,
|
|
19
|
+
// It's causing infinite measurements, that hung up the UI.
|
|
20
|
+
// Intercepting largest child by width, and use its width as (parent) ReactRootView width fixed that.
|
|
21
|
+
// See for more details https://github.com/wix/react-native-navigation/pull/7096
|
|
22
|
+
var measuredWidth = 0;
|
|
23
|
+
this.children.forEach {
|
|
24
|
+
if (it.measuredWidth > measuredWidth) {
|
|
25
|
+
measuredWidth = it.measuredWidth
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
return if (measuredWidth > 0) MeasureSpec.makeMeasureSpec(measuredWidth, MeasureSpec.EXACTLY) else
|
|
29
|
+
widthMeasureSpec
|
|
30
|
+
}
|
|
31
|
+
}
|
|
@@ -75,7 +75,10 @@ const setters = remx.setters({
|
|
|
75
75
|
},
|
|
76
76
|
mergeOptions(componentId, options) {
|
|
77
77
|
const layout = getters.getLayoutById(componentId);
|
|
78
|
-
layout
|
|
78
|
+
if (layout)
|
|
79
|
+
layout.mergeOptions(options);
|
|
80
|
+
else
|
|
81
|
+
console.warn(`[RNN error] Merge options failure: cannot find layout for: ${componentId}`);
|
|
79
82
|
},
|
|
80
83
|
});
|
|
81
84
|
const getters = remx.getters({
|
|
@@ -430,6 +430,11 @@ export interface OptionsTopBarButton {
|
|
|
430
430
|
* Set the button icon
|
|
431
431
|
*/
|
|
432
432
|
icon?: ImageResource;
|
|
433
|
+
/**
|
|
434
|
+
* Set the SF symbol as icon (will be used primarily)
|
|
435
|
+
* #### (iOS 13+ specific)
|
|
436
|
+
*/
|
|
437
|
+
sfSymbol?: string;
|
|
433
438
|
/**
|
|
434
439
|
* Set the button icon insets
|
|
435
440
|
*/
|
package/lib/ios/RNNAssert.h
CHANGED
|
@@ -12,8 +12,8 @@ extern BOOL RNNIsMainQueue(void);
|
|
|
12
12
|
if ((condition) == 0) { \
|
|
13
13
|
if (RNN_NSASSERT) { \
|
|
14
14
|
[[NSAssertionHandler currentHandler] \
|
|
15
|
-
handleFailureInFunction:(NSString *
|
|
16
|
-
file:(NSString *
|
|
15
|
+
handleFailureInFunction:(NSString *_Nonnull)@(__func__) \
|
|
16
|
+
file:(NSString *_Nonnull)@(__FILE__) \
|
|
17
17
|
lineNumber:__LINE__ \
|
|
18
18
|
description:__VA_ARGS__]; \
|
|
19
19
|
} \
|
|
@@ -84,7 +84,8 @@
|
|
|
84
84
|
self.testID.hasValue || self.icon.hasValue || self.selectedIcon.hasValue ||
|
|
85
85
|
self.iconColor.hasValue || self.selectedIconColor.hasValue ||
|
|
86
86
|
self.selectedTextColor.hasValue || self.iconInsets.hasValue || self.textColor.hasValue ||
|
|
87
|
-
self.visible.hasValue || self.selectTabOnPress.hasValue || self.sfSymbol.hasValue ||
|
|
87
|
+
self.visible.hasValue || self.selectTabOnPress.hasValue || self.sfSymbol.hasValue ||
|
|
88
|
+
self.sfSelectedSymbol.hasValue;
|
|
88
89
|
}
|
|
89
90
|
|
|
90
91
|
@end
|
|
@@ -31,6 +31,8 @@
|
|
|
31
31
|
return [[RNNUIBarButtonItem alloc] initCustomIcon:button
|
|
32
32
|
iconCreator:_iconCreator
|
|
33
33
|
onPress:onPress];
|
|
34
|
+
} else if (button.sfSymbol.hasValue) {
|
|
35
|
+
return [[RNNUIBarButtonItem alloc] initWithSFSymbol:button onPress:onPress];
|
|
34
36
|
} else if (button.icon.hasValue) {
|
|
35
37
|
return [[RNNUIBarButtonItem alloc] initWithIcon:button onPress:onPress];
|
|
36
38
|
} else if (button.text.hasValue) {
|
|
@@ -16,6 +16,7 @@
|
|
|
16
16
|
@property(nonatomic, strong) Color *color;
|
|
17
17
|
@property(nonatomic, strong) Color *disabledColor;
|
|
18
18
|
@property(nonatomic, strong) Image *icon;
|
|
19
|
+
@property(nonatomic, strong) Text *sfSymbol;
|
|
19
20
|
@property(nonatomic, strong) Bool *enabled;
|
|
20
21
|
@property(nonatomic, strong) RNNInsetsOptions *iconInsets;
|
|
21
22
|
@property(nonatomic, strong) Bool *selectTabOnPress;
|
|
@@ -11,6 +11,7 @@
|
|
|
11
11
|
self.fontWeight = [TextParser parse:dict key:@"fontWeight"];
|
|
12
12
|
self.fontSize = [NumberParser parse:dict key:@"fontSize"];
|
|
13
13
|
self.text = [TextParser parse:dict key:@"text"];
|
|
14
|
+
self.sfSymbol = [TextParser parse:dict key:@"sfSymbol"];
|
|
14
15
|
self.testID = [TextParser parse:dict key:@"testID"];
|
|
15
16
|
self.accessibilityLabel = [TextParser parse:dict key:@"accessibilityLabel"];
|
|
16
17
|
self.color = [ColorParser parse:dict key:@"color"];
|
|
@@ -39,6 +40,7 @@
|
|
|
39
40
|
newOptions.color = self.color.copy;
|
|
40
41
|
newOptions.disabledColor = self.disabledColor.copy;
|
|
41
42
|
newOptions.icon = self.icon.copy;
|
|
43
|
+
newOptions.sfSymbol = self.sfSymbol.copy;
|
|
42
44
|
newOptions.iconInsets = self.iconInsets.copy;
|
|
43
45
|
newOptions.enabled = self.enabled.copy;
|
|
44
46
|
newOptions.selectTabOnPress = self.selectTabOnPress.copy;
|
|
@@ -71,6 +73,8 @@
|
|
|
71
73
|
self.disabledColor = options.disabledColor;
|
|
72
74
|
if (options.icon.hasValue)
|
|
73
75
|
self.icon = options.icon;
|
|
76
|
+
if (options.sfSymbol.hasValue)
|
|
77
|
+
self.sfSymbol = options.sfSymbol;
|
|
74
78
|
if (options.enabled.hasValue) {
|
|
75
79
|
self.enabled = options.enabled;
|
|
76
80
|
[self.iconBackground setEnabled:self.enabled];
|
|
@@ -82,10 +82,7 @@ static NSString *const setDefaultOptions = @"setDefaultOptions";
|
|
|
82
82
|
}
|
|
83
83
|
}
|
|
84
84
|
|
|
85
|
-
[_modalManager
|
|
86
|
-
completion:^{
|
|
87
|
-
|
|
88
|
-
}];
|
|
85
|
+
[_modalManager reset];
|
|
89
86
|
|
|
90
87
|
UIViewController *vc = [_controllerFactory createLayout:layout[@"root"]];
|
|
91
88
|
[_layoutManager addPendingViewController:vc];
|
|
@@ -92,7 +92,8 @@
|
|
|
92
92
|
return NO;
|
|
93
93
|
UIView *currentIndicator = [self getCurrentIndicator:child];
|
|
94
94
|
|
|
95
|
-
return
|
|
95
|
+
return
|
|
96
|
+
[[currentIndicator backgroundColor] isEqual:[options.color withDefault:[UIColor redColor]]];
|
|
96
97
|
}
|
|
97
98
|
|
|
98
99
|
- (UIView *)getCurrentIndicator:(UIViewController *)child {
|
|
@@ -143,6 +143,11 @@
|
|
|
143
143
|
}
|
|
144
144
|
}
|
|
145
145
|
|
|
146
|
+
- (void)reset {
|
|
147
|
+
[_presentedModals removeAllObjects];
|
|
148
|
+
[_pendingModalIdsToDismiss removeAllObjects];
|
|
149
|
+
}
|
|
150
|
+
|
|
146
151
|
#pragma mark - private
|
|
147
152
|
|
|
148
153
|
- (void)removePendingNextModalIfOnTop:(RNNTransitionCompletionBlock)completion
|
|
@@ -82,6 +82,9 @@
|
|
|
82
82
|
setNavigationBarClipsToBounds:[withDefault.topBar.background.clipToBounds withDefault:NO]];
|
|
83
83
|
|
|
84
84
|
[stack.view setBackgroundColor:[withDefault.layout.backgroundColor withDefault:nil]];
|
|
85
|
+
if (options.topBar.background.component.name.hasValue) {
|
|
86
|
+
[self setCustomNavigationComponentBackground:options perform:nil];
|
|
87
|
+
}
|
|
85
88
|
}
|
|
86
89
|
|
|
87
90
|
- (void)applyOptionsOnViewDidLayoutSubviews:(RNNNavigationOptions *)options {
|
|
@@ -18,11 +18,12 @@
|
|
|
18
18
|
|
|
19
19
|
if (@available(iOS 13.0, *)) {
|
|
20
20
|
if (bottomTabOptions.sfSymbol.hasValue) {
|
|
21
|
-
icon = [UIImage systemImageNamed:
|
|
21
|
+
icon = [UIImage systemImageNamed:[bottomTabOptions.sfSymbol withDefault:nil]];
|
|
22
22
|
}
|
|
23
23
|
|
|
24
24
|
if (bottomTabOptions.sfSelectedSymbol.hasValue) {
|
|
25
|
-
selectedIcon =
|
|
25
|
+
selectedIcon =
|
|
26
|
+
[UIImage systemImageNamed:[bottomTabOptions.sfSelectedSymbol withDefault:nil]];
|
|
26
27
|
}
|
|
27
28
|
}
|
|
28
29
|
|
|
@@ -14,6 +14,8 @@ typedef void (^RNNButtonPressCallback)(NSString *buttonId);
|
|
|
14
14
|
- (instancetype)initCustomIcon:(RNNButtonOptions *)buttonOptions
|
|
15
15
|
iconCreator:(RNNIconCreator *)iconCreator
|
|
16
16
|
onPress:(RNNButtonPressCallback)onPress;
|
|
17
|
+
- (instancetype)initWithSFSymbol:(RNNButtonOptions *)buttonOptions
|
|
18
|
+
onPress:(RNNButtonPressCallback)onPress;
|
|
17
19
|
- (instancetype)initWithIcon:(RNNButtonOptions *)buttonOptions
|
|
18
20
|
onPress:(RNNButtonPressCallback)onPress;
|
|
19
21
|
- (instancetype)initWithTitle:(RNNButtonOptions *)buttonOptions
|
|
@@ -20,6 +20,23 @@
|
|
|
20
20
|
return self;
|
|
21
21
|
}
|
|
22
22
|
|
|
23
|
+
- (instancetype)initWithSFSymbol:(RNNButtonOptions *)buttonOptions
|
|
24
|
+
onPress:(RNNButtonPressCallback)onPress {
|
|
25
|
+
UIImage *iconImage = [UIImage alloc];
|
|
26
|
+
|
|
27
|
+
if (@available(iOS 13.0, *)) {
|
|
28
|
+
iconImage = [UIImage systemImageNamed:[buttonOptions.sfSymbol withDefault:nil]];
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
self = [super initWithImage:iconImage
|
|
32
|
+
style:UIBarButtonItemStylePlain
|
|
33
|
+
target:self
|
|
34
|
+
action:@selector(onButtonPressed:)];
|
|
35
|
+
[self applyOptions:buttonOptions];
|
|
36
|
+
self.onPress = onPress;
|
|
37
|
+
return self;
|
|
38
|
+
}
|
|
39
|
+
|
|
23
40
|
- (instancetype)initWithIcon:(RNNButtonOptions *)buttonOptions
|
|
24
41
|
onPress:(RNNButtonPressCallback)onPress {
|
|
25
42
|
UIImage *iconImage = buttonOptions.icon.get;
|
|
@@ -160,17 +160,21 @@
|
|
|
160
160
|
UIBarButtonItem *backItem = [[RNNUIBarBackButtonItem alloc] initWithOptions:backButtonOptions];
|
|
161
161
|
UINavigationItem *previousNavigationItem = previousViewControllerInStack.navigationItem;
|
|
162
162
|
|
|
163
|
-
|
|
164
163
|
if (@available(iOS 13.0, *)) {
|
|
165
164
|
UIImage *sfSymbol = [UIImage systemImageNamed:[backButtonOptions.sfSymbol withDefault:nil]];
|
|
166
165
|
if (backButtonOptions.sfSymbol.hasValue) {
|
|
167
|
-
icon = color ? [sfSymbol imageWithTintColor:color
|
|
166
|
+
icon = color ? [sfSymbol imageWithTintColor:color
|
|
167
|
+
renderingMode:UIImageRenderingModeAlwaysOriginal]
|
|
168
168
|
: [sfSymbol imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal];
|
|
169
169
|
} else {
|
|
170
|
-
icon = color ? [[icon withTintColor:color]
|
|
170
|
+
icon = color ? [[icon withTintColor:color]
|
|
171
|
+
imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal]
|
|
172
|
+
: icon;
|
|
171
173
|
}
|
|
172
174
|
} else {
|
|
173
|
-
icon = color ? [[icon withTintColor:color]
|
|
175
|
+
icon = color ? [[icon withTintColor:color]
|
|
176
|
+
imageWithRenderingMode:UIImageRenderingModeAlwaysOriginal]
|
|
177
|
+
: icon;
|
|
174
178
|
}
|
|
175
179
|
|
|
176
180
|
[self setBackIndicatorImage:icon withColor:color];
|
|
@@ -77,7 +77,8 @@ const setters = remx.setters({
|
|
|
77
77
|
},
|
|
78
78
|
mergeOptions(componentId: string, options: Options) {
|
|
79
79
|
const layout = getters.getLayoutById(componentId);
|
|
80
|
-
layout.mergeOptions(options);
|
|
80
|
+
if (layout) layout.mergeOptions(options);
|
|
81
|
+
else console.warn(`[RNN error] Merge options failure: cannot find layout for: ${componentId}`);
|
|
81
82
|
},
|
|
82
83
|
});
|
|
83
84
|
|
|
@@ -488,6 +488,11 @@ export interface OptionsTopBarButton {
|
|
|
488
488
|
* Set the button icon
|
|
489
489
|
*/
|
|
490
490
|
icon?: ImageResource;
|
|
491
|
+
/**
|
|
492
|
+
* Set the SF symbol as icon (will be used primarily)
|
|
493
|
+
* #### (iOS 13+ specific)
|
|
494
|
+
*/
|
|
495
|
+
sfSymbol?: string;
|
|
491
496
|
/**
|
|
492
497
|
* Set the button icon insets
|
|
493
498
|
*/
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "react-native-navigation",
|
|
3
|
-
"version": "7.23.
|
|
3
|
+
"version": "7.23.1-hotfix.1",
|
|
4
4
|
"description": "React Native Navigation - truly native navigation for iOS and Android",
|
|
5
5
|
"license": "MIT",
|
|
6
6
|
"nativePackage": true,
|
|
@@ -76,7 +76,7 @@
|
|
|
76
76
|
"@react-native-community/netinfo": "^5.9.4",
|
|
77
77
|
"@testing-library/jest-native": "^4.0.1",
|
|
78
78
|
"@testing-library/react-native": "^7.2.0",
|
|
79
|
-
"@types/detox": "
|
|
79
|
+
"@types/detox": "17.14.3",
|
|
80
80
|
"@types/hoist-non-react-statics": "^3.0.1",
|
|
81
81
|
"@types/jasmine": "3.5.10",
|
|
82
82
|
"@types/jest": "26.0.3",
|
|
@@ -88,7 +88,7 @@
|
|
|
88
88
|
"@typescript-eslint/parser": "3.3.0",
|
|
89
89
|
"babel-jest": "26.1.0",
|
|
90
90
|
"clang-format": "^1.4.0",
|
|
91
|
-
"detox": "18.
|
|
91
|
+
"detox": "18.23.1",
|
|
92
92
|
"eslint": "7.3.0",
|
|
93
93
|
"eslint-config-prettier": "6.11.0",
|
|
94
94
|
"eslint-plugin-prettier": "3.1.4",
|