I'm trying to use ABNewPersonViewController in my React Native app. This is how it's used in Objective-C:
ABNewPersonViewController *picker = [[ABNewPersonViewController alloc] init]; picker.newPersonViewDelegate = self; UINavigationController *navigation = [[UINavigationController alloc] initWithRootViewController:picker]; [self presentViewController:navigation animated:NO completion:nil];
How would I do this in React Native? I can't write a bridged UI component since it's a UIViewController, not a UIView.
Please don't tell me to reimplement it 😟
Here's what ended up working for me.
CreateContact.h:
#import <Foundation/Foundation.h> #import <UIKit/UIKit.h> #import <AddressBook/AddressBook.h> #import <AddressBookUI/AddressBookUI.h> #import "RCTBridgeModule.h" @interface CreateContact : NSObject <ABNewPersonViewControllerDelegate, RCTBridgeModule> @end
CreateContact.m:
#import "CreateContact.h" #import "AppDelegate.h" @implementation CreateContact RCT_EXPORT_MODULE(CreateContact); RCT_EXPORT_METHOD(presentContact) { dispatch_async(dispatch_get_main_queue(), ^{ ABNewPersonViewController *picker = [[ABNewPersonViewController alloc] init]; picker.newPersonViewDelegate = self; UINavigationController* contactNavigator = [[UINavigationController alloc] initWithRootViewController:picker]; AppDelegate *delegate = (AppDelegate *)[[UIApplication sharedApplication] delegate]; [delegate.window.rootViewController presentViewController:contactNavigator animated:NO completion:nil]; }); } - (void)newPersonViewController:(ABNewPersonViewController *)newPersonViewController didCompleteWithNewPerson:(ABRecordRef)person { [newPersonViewController dismissViewControllerAnimated:YES completion:nil]; } @end
This tutorial has more detail: http://moduscreate.com/leverage-existing-ios-views-react-native-app/
I'll update as I implement the best way to communicate information back to RN.
You want to implement a bridged UI component that mounts an empty UIView and is responsible primarily for presenting your UIViewController. The simplest example of this technique is in RCTModalHostView; check out the source code.
Notably, React Native defines a category on UIView that adds a property called reactViewController
which climbs the view hierarchy to find the closest UIViewController. Use this UIViewController to present your custom view controller:
- (void)didMoveToWindow { [super didMoveToWindow]; if (!_isPresented && self.window) { [self.reactViewController presentViewController:_customViewController animated:NO completion:nil]; _isPresented = YES; } }
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With