Files
react-native/packages/react-native/Libraries/AppDelegate/RCTReactNativeFactory.h
T
Dawid Malecki 29d5aa582f iOS: Add new configuration for RCTDevMenu (#53505)
Summary:
Following the [RFC](https://github.com/react-native-community/discussions-and-proposals/pull/925), this PR adds new `RCTDevMenu` configuration  and extends `RCTReactNativeFactory` API for passing it to the particular `RCTHost`.  The `RCTDevMenuConfiguration` includes:

- isDevMenuEnabled,
- isShakeGestureEnabled,
- areKeyboardShortcutsEnabled

## Changelog:

[IOS][ADDED] - Add new configuration for `RCTDevMenu`

<!-- Help reviewers and the release process by writing your own changelog entry.

Pick one each for the category and type tags:

[ANDROID|GENERAL|IOS|INTERNAL] [BREAKING|ADDED|CHANGED|DEPRECATED|REMOVED|FIXED|SECURITY] - Message

For more details, see:
https://reactnative.dev/contributing/changelogs-in-pull-requests

Pull Request resolved: https://github.com/facebook/react-native/pull/53505

Test Plan:
Tested with different configurations on `RCTDevMenuConfiguration`:

<details>
<summary>Click to view code</summary>

```objc
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
  self.reactNativeFactory = [[RCTReactNativeFactory alloc] initWithDelegate:self];
#if USE_OSS_CODEGEN
  self.dependencyProvider = [RCTAppDependencyProvider new];
#endif

  RCTDevMenuConfiguration *devMenuConfiguration = [[RCTDevMenuConfiguration alloc] initWithDevMenuEnabled:true shakeGestureEnabled:false keyboardShortcutsEnabled:false];

  [self.reactNativeFactory setDevMenuConfiguration:devMenuConfiguration];

  self.window = [[UIWindow alloc] initWithFrame:[UIScreen mainScreen].bounds];

  [self.reactNativeFactory startReactNativeWithModuleName:@"RNTesterApp"
                                                 inWindow:self.window
                                        initialProperties:[self prepareInitialProps]
                                            launchOptions:launchOptions];

  [[UNUserNotificationCenter currentNotificationCenter] setDelegate:self];

  return YES;
}
```

</details>

Run helloworld:

<img src="https://github.com/user-attachments/assets/16c35176-6fbe-498c-96fd-a0fe988a5e3c" alt="hello-world-screenshot" width="300">

Reviewed By: cipolleschi

Differential Revision: D81684275

Pulled By: coado

fbshipit-source-id: 500e170c93df25949de433970442d20c442be7f2
2025-10-01 02:42:54 -07:00

125 lines
5.1 KiB
Objective-C

/*
* Copyright (c) Meta Platforms, Inc. and affiliates.
*
* This source code is licensed under the MIT license found in the
* LICENSE file in the root directory of this source tree.
*/
#import <React/RCTBridgeDelegate.h>
#import <React/RCTConvert.h>
#import <UIKit/UIKit.h>
#import "RCTArchConfiguratorProtocol.h"
#import "RCTDependencyProvider.h"
#import "RCTJSRuntimeConfiguratorProtocol.h"
#import "RCTRootViewFactory.h"
#import "RCTUIConfiguratorProtocol.h"
#if defined(__cplusplus) // Don't conform to protocols requiring C++ when it's not defined.
#import <React/RCTComponentViewFactory.h>
#import <ReactCommon/RCTHost.h>
#import <ReactCommon/RCTTurboModuleManager.h>
#endif
@class RCTBridge;
@protocol RCTComponentViewProtocol;
@class RCTSurfacePresenterBridgeAdapter;
@class RCTDevMenuConfiguration;
NS_ASSUME_NONNULL_BEGIN
typedef NS_ENUM(NSInteger, RCTReleaseLevel) { Canary, Experimental, Stable };
@protocol RCTReactNativeFactoryDelegate <
RCTBridgeDelegate,
RCTUIConfiguratorProtocol,
#if defined(__cplusplus) // Don't conform to protocols requiring C++ when it's not defined.
RCTHostDelegate,
RCTTurboModuleManagerDelegate,
RCTComponentViewFactoryComponentProvider,
#endif
RCTJSRuntimeConfiguratorProtocol,
RCTArchConfiguratorProtocol>
/// Return the bundle URL for the main bundle.
- (NSURL *__nullable)bundleURL;
@property (nonatomic, strong) id<RCTDependencyProvider> dependencyProvider;
@optional
/**
* It creates a `RCTBridge` using a delegate and some launch options.
* By default, it is invoked passing `self` as a delegate.
* You can override this function to customize the logic that creates the RCTBridge
*
* @parameter: delegate - an object that implements the `RCTBridgeDelegate` protocol.
* @parameter: launchOptions - a dictionary with a set of options.
*
* @returns: a newly created instance of RCTBridge.
*/
- (RCTBridge *)createBridgeWithDelegate:(id<RCTBridgeDelegate>)delegate
launchOptions:(NSDictionary *)launchOptions
__attribute__((deprecated(
"createBridgeWithDelegate:launchOptions: is deprecated and will be removed when removing the legacy architecture.")));
/**
* It creates a `UIView` starting from a bridge, a module name and a set of initial properties.
* By default, it is invoked using the bridge created by `createBridgeWithDelegate:launchOptions` and
* the name in the `self.moduleName` variable.
* You can override this function to customize the logic that creates the Root View.
*
* @parameter: bridge - an instance of the `RCTBridge` object.
* @parameter: moduleName - the name of the app, used by Metro to resolve the module.
* @parameter: initProps - a set of initial properties.
*
* @returns: a UIView properly configured with a bridge for React Native.
*/
- (UIView *)createRootViewWithBridge:(RCTBridge *)bridge
moduleName:(NSString *)moduleName
initProps:(NSDictionary *)initProps
__attribute__((deprecated(
"createRootViewWithBridge:moduleName:initProps is deprecated and will be removed when removing the legacy architecture.")));
/// This method returns a map of Component Descriptors and Components classes that needs to be registered in the
/// new renderer. The Component Descriptor is a string which represent the name used in JS to refer to the native
/// component. The default implementation returns an empty dictionary. Subclasses can override this method to register
/// the required components.
///
/// @return a dictionary that associate a component for the new renderer with his descriptor.
- (NSDictionary<NSString *, Class<RCTComponentViewProtocol>> *)thirdPartyFabricComponents;
@end
@interface RCTReactNativeFactory : NSObject
- (instancetype)initWithDelegate:(id<RCTReactNativeFactoryDelegate>)delegate;
- (instancetype)initWithDelegate:(id<RCTReactNativeFactoryDelegate>)delegate releaseLevel:(RCTReleaseLevel)releaseLevel;
- (void)startReactNativeWithModuleName:(NSString *)moduleName inWindow:(UIWindow *_Nullable)window;
- (void)startReactNativeWithModuleName:(NSString *)moduleName
inWindow:(UIWindow *_Nullable)window
launchOptions:(NSDictionary *_Nullable)launchOptions;
- (void)startReactNativeWithModuleName:(NSString *)moduleName
inWindow:(UIWindow *_Nullable)window
initialProperties:(NSDictionary *_Nullable)initialProperties
launchOptions:(NSDictionary *_Nullable)launchOptions;
@property (nonatomic, nullable) RCTBridge *bridge
__attribute__((deprecated("The bridge is deprecated and will be removed when removing the legacy architecture.")));
@property (nonatomic, strong, nonnull) RCTRootViewFactory *rootViewFactory;
@property (nonatomic, nullable) RCTSurfacePresenterBridgeAdapter *bridgeAdapter __attribute__((
deprecated("The bridgeAdapter is deprecated and will be removed when removing the legacy architecture.")));
;
@property (nonatomic, weak) id<RCTReactNativeFactoryDelegate> delegate;
@property (nonatomic, nullable) RCTDevMenuConfiguration *devMenuConfiguration;
@end
NS_ASSUME_NONNULL_END