Skip to content

Commit 64ebe5b

Browse files
gabrieldonadelfacebook-github-bot
authored andcommitted
feat: Add dismissActionSheet method to ActionSheetIOS (#33189)
Summary: This PR adds a `dismissActionSheet` method to `ActionSheetIOS` in order to allow dismissing an ActionSheet programmatically. This is especially useful in apps where a user has the ability to open an ActionSheet and then open a push notification that will redirect them to another screen which usually leads to scenarios where the presented ActionSheet has no relation with the current screen. #### TODO - [ ] Submit react-native-website PR updating ActionSheetIOS documentation. ## Changelog [iOS] [Added] - Add dismissActionSheet method to ActionSheetIOS Pull Request resolved: #33189 Test Plan: 1. Open the RNTester app and navigate to the ActionSheetIOS page 2. Test `dismissActionSheet` through the `Show Action Sheet and automatically dismiss it` example https://user-images.githubusercontent.com/11707729/155867546-c6770a49-9b09-45e3-a6b1-4f7645d67dbf.mov Reviewed By: lunaleaps Differential Revision: D34518952 Pulled By: cortinico fbshipit-source-id: 912a9b83ee078f791b42efddf5abb7e1cd09d520
1 parent 1042a80 commit 64ebe5b

File tree

4 files changed

+72
-0
lines changed

4 files changed

+72
-0
lines changed

Libraries/ActionSheetIOS/ActionSheetIOS.js

+7
Original file line numberDiff line numberDiff line change
@@ -143,6 +143,13 @@ const ActionSheetIOS = {
143143
successCallback,
144144
);
145145
},
146+
147+
dismissActionSheet: () => {
148+
invariant(RCTActionSheetManager, "ActionSheetManager doesn't exist");
149+
if (typeof RCTActionSheetManager.dismissActionSheet === 'function') {
150+
RCTActionSheetManager.dismissActionSheet();
151+
}
152+
},
146153
};
147154

148155
module.exports = ActionSheetIOS;

Libraries/ActionSheetIOS/NativeActionSheetManager.js

+1
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ export interface Spec extends TurboModule {
4747
|}) => void,
4848
successCallback: (completed: boolean, activityType: ?string) => void,
4949
) => void;
50+
+dismissActionSheet?: () => void;
5051
}
5152

5253
export default (TurboModuleRegistry.get<Spec>('ActionSheetManager'): ?Spec);

React/CoreModules/RCTActionSheetManager.mm

+30
Original file line numberDiff line numberDiff line change
@@ -21,10 +21,27 @@
2121
using namespace facebook::react;
2222

2323
@interface RCTActionSheetManager () <UIActionSheetDelegate, NativeActionSheetManagerSpec>
24+
25+
@property (nonatomic, strong) NSMutableArray<UIAlertController *> *alertControllers;
26+
2427
@end
2528

2629
@implementation RCTActionSheetManager
2730

31+
- (instancetype)init
32+
{
33+
self = [super init];
34+
if (self) {
35+
_alertControllers = [NSMutableArray new];
36+
}
37+
return self;
38+
}
39+
40+
+ (BOOL)requiresMainQueueSetup
41+
{
42+
return NO;
43+
}
44+
2845
RCT_EXPORT_MODULE()
2946

3047
@synthesize viewRegistry_DEPRECATED = _viewRegistry_DEPRECATED;
@@ -137,6 +154,7 @@ - (void)presentViewController:(UIViewController *)alertController
137154
handler:^(__unused UIAlertAction *action) {
138155
if (!callbackInvoked) {
139156
callbackInvoked = true;
157+
[self->_alertControllers removeObject:alertController];
140158
callback(@[ @(localIndex) ]);
141159
}
142160
}];
@@ -178,9 +196,21 @@ - (void)presentViewController:(UIViewController *)alertController
178196
}
179197
#endif
180198

199+
[_alertControllers addObject:alertController];
181200
[self presentViewController:alertController onParentViewController:controller anchorViewTag:anchorViewTag];
182201
}
183202

203+
RCT_EXPORT_METHOD(dismissActionSheet)
204+
{
205+
if (_alertControllers.count == 0) {
206+
RCTLogWarn(@"Unable to dismiss action sheet");
207+
}
208+
209+
id _alertController = [_alertControllers lastObject];
210+
[_alertController dismissViewControllerAnimated:YES completion:nil];
211+
[_alertControllers removeLastObject];
212+
}
213+
184214
RCT_EXPORT_METHOD(showShareActionSheetWithOptions
185215
: (JS::NativeActionSheetManager::SpecShowShareActionSheetWithOptionsOptions &)options failureCallback
186216
: (RCTResponseSenderBlock)failureCallback successCallback

packages/rn-tester/js/examples/ActionSheetIOS/ActionSheetIOSExample.js

+34
Original file line numberDiff line numberDiff line change
@@ -204,6 +204,34 @@ class ActionSheetDisabledExample extends React.Component<Props, State> {
204204
};
205205
}
206206

207+
class ActionSheetDismissExample extends React.Component<{...}> {
208+
render() {
209+
return (
210+
<View>
211+
<Text onPress={this.showAndDismissActionSheet} style={style.button}>
212+
Click to show and automatically dismiss the ActionSheet after 3
213+
seconds
214+
</Text>
215+
</View>
216+
);
217+
}
218+
219+
showAndDismissActionSheet = () => {
220+
ActionSheetIOS.showActionSheetWithOptions(
221+
{
222+
options: BUTTONS,
223+
cancelButtonIndex: CANCEL_INDEX,
224+
destructiveButtonIndex: DESTRUCTIVE_INDEX,
225+
},
226+
() => {},
227+
);
228+
229+
setTimeout(() => {
230+
ActionSheetIOS.dismissActionSheet();
231+
}, 3000);
232+
};
233+
}
234+
207235
class ShareActionSheetExample extends React.Component<
208236
$FlowFixMeProps,
209237
$FlowFixMeState,
@@ -394,6 +422,12 @@ exports.examples = [
394422
return <ActionSheetDisabledExample />;
395423
},
396424
},
425+
{
426+
title: 'Show Action Sheet and automatically dismiss it',
427+
render(): React.Element<any> {
428+
return <ActionSheetDismissExample />;
429+
},
430+
},
397431
{
398432
title: 'Show Share Action Sheet',
399433
render(): React.Element<any> {

0 commit comments

Comments
 (0)