1 // Copyright 2013 The Flutter Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #ifndef FLUTTER_FLUTTERVIEWCONTROLLER_H_ 6 #define FLUTTER_FLUTTERVIEWCONTROLLER_H_ 7 8 #import <UIKit/UIKit.h> 9 #include <sys/cdefs.h> 10 11 #include "FlutterBinaryMessenger.h" 12 #include "FlutterDartProject.h" 13 #include "FlutterEngine.h" 14 #include "FlutterMacros.h" 15 #include "FlutterPlugin.h" 16 #include "FlutterTexture.h" 17 18 @class FlutterEngine; 19 20 /** 21 * The name used for semantic update notifications via `NSNotificationCenter`. 22 * 23 * The object passed as the sender is the `FlutterViewController` associated 24 * with the update. 25 */ 26 FLUTTER_EXPORT 27 extern NSNotificationName const FlutterSemanticsUpdateNotification; 28 29 /** 30 * A `UIViewController` implementation for Flutter views. 31 * 32 * Dart execution, channel communication, texture registration, and plugin registration are all 33 * handled by `FlutterEngine`. Calls on this class to those members all proxy through to the 34 * `FlutterEngine` attached FlutterViewController. 35 * 36 * A FlutterViewController can be initialized either with an already-running `FlutterEngine` via 37 * the `initWithEngine:` initializer, or it can be initialized with a `FlutterDartProject` that 38 * will be used to implicitly spin up a new `FlutterEngine`. Creating a `FlutterEngine before 39 * showing a `FlutterViewController` can be used to pre-initialize the Dart VM and to prepare the 40 * isolate in order to reduce the latency to the first rendered frame. Holding a `FlutterEngine` 41 * independently of FlutterViewControllers can also be used to not to lose Dart-related state and 42 * asynchronous tasks when navigating back and forth between a FlutterViewController and other 43 * `UIViewController`s. 44 */ 45 FLUTTER_EXPORT 46 @interface FlutterViewController : UIViewController <FlutterTextureRegistry, FlutterPluginRegistry> 47 48 /** 49 * Initializes this FlutterViewController with the specified `FlutterEngine`. 50 * 51 * The initialized viewcontroller will attach itself to the engine as part of this process. 52 * 53 * @param engine The `FlutterEngine` instance to attach to. 54 * @param nibNameOrNil The NIB name to initialize this UIViewController with. 55 * @param nibBundleOrNil The NIB bundle. 56 */ 57 - (instancetype)initWithEngine:(FlutterEngine*)engine 58 nibName:(NSString*)nibNameOrNil 59 bundle:(NSBundle*)nibBundleOrNil NS_DESIGNATED_INITIALIZER; 60 61 /** 62 * Initializes a new FlutterViewController and `FlutterEngine` with the specified 63 * `FlutterDartProject`. 64 * 65 * @param projectOrNil The `FlutterDartProject` to initialize the `FlutterEngine` with. 66 * @param nibNameOrNil The NIB name to initialize this UIViewController with. 67 * @param nibBundleOrNil The NIB bundle. 68 */ 69 - (instancetype)initWithProject:(FlutterDartProject*)projectOrNil 70 nibName:(NSString*)nibNameOrNil 71 bundle:(NSBundle*)nibBundleOrNil NS_DESIGNATED_INITIALIZER; 72 73 - (void)handleStatusBarTouches:(UIEvent*)event; 74 75 /** 76 * Registers a callback that will be invoked when the Flutter view has been rendered. 77 * The callback will be fired only once. 78 * 79 * Replaces an existing callback. Use a `nil` callback to unregister the existing one. 80 */ 81 - (void)setFlutterViewDidRenderCallback:(void (^)(void))callback; 82 83 /** 84 * Returns the file name for the given asset. 85 * The returned file name can be used to access the asset in the application's 86 * main bundle. 87 * 88 * @param asset The name of the asset. The name can be hierarchical. 89 * @return The file name to be used for lookup in the main bundle. 90 */ 91 - (NSString*)lookupKeyForAsset:(NSString*)asset; 92 93 /** 94 * Returns the file name for the given asset which originates from the specified 95 * package. 96 * The returned file name can be used to access the asset in the application's 97 * main bundle. 98 * 99 * @param asset The name of the asset. The name can be hierarchical. 100 * @param package The name of the package from which the asset originates. 101 * @return The file name to be used for lookup in the main bundle. 102 */ 103 - (NSString*)lookupKeyForAsset:(NSString*)asset fromPackage:(NSString*)package; 104 105 /** 106 * Sets the first route that the Flutter app shows. The default is "/". 107 * This method will guarnatee that the initial route is delivered, even if the 108 * Flutter window hasn't been created yet when called. It cannot be used to update 109 * the current route being shown in a visible FlutterViewController (see pushRoute 110 * and popRoute). 111 * 112 * @param route The name of the first route to show. 113 */ 114 - (void)setInitialRoute:(NSString*)route; 115 116 /** 117 * Instructs the Flutter Navigator (if any) to go back. 118 */ 119 - (void)popRoute; 120 121 /** 122 * Instructs the Flutter Navigator (if any) to push a route on to the navigation 123 * stack. The setInitialRoute method should be preferred if this is called before the 124 * FlutterViewController has come into view. 125 * 126 * @param route The name of the route to push to the navigation stack. 127 */ 128 - (void)pushRoute:(NSString*)route; 129 130 /** 131 * The `FlutterPluginRegistry` used by this FlutterViewController. 132 */ 133 - (id<FlutterPluginRegistry>)pluginRegistry; 134 135 /** 136 * True if at least one frame has rendered and the ViewController has appeared. 137 * 138 * This property is reset to false when the ViewController disappears. It is 139 * guaranteed to only alternate between true and false for observers. 140 */ 141 @property(nonatomic, readonly, getter=isDisplayingFlutterUI) BOOL displayingFlutterUI; 142 143 /** 144 * Specifies the view to use as a splash screen. Flutter's rendering is asynchronous, so the first 145 * frame rendered by the Flutter application might not immediately appear when theFlutter view is 146 * initially placed in the view hierarchy. The splash screen view will be used as 147 * a replacement until the first frame is rendered. 148 * 149 * The view used should be appropriate for multiple sizes; an autoresizing mask to 150 * have a flexible width and height will be applied automatically. 151 */ 152 @property(strong, nonatomic) UIView* splashScreenView; 153 154 /** 155 * Attempts to set the `splashScreenView` property from the `UILaunchStoryboardName` from the 156 * main bundle's `Info.plist` file. This method will not change the value of `splashScreenView` 157 * if it cannot find a default one from a storyboard or nib. 158 * 159 * @return `YES` if successful, `NO` otherwise. 160 */ 161 - (BOOL)loadDefaultSplashScreenView; 162 163 /** 164 * Controls whether the created view will be opaque or not. 165 * 166 * Default is `YES`. Note that setting this to `NO` may negatively impact performance 167 * when using hardware acceleration, and toggling this will trigger a re-layout of the 168 * view. 169 */ 170 @property(nonatomic, getter=isViewOpaque) BOOL viewOpaque; 171 172 /** 173 * The `FlutterEngine` instance for this view controller. 174 */ 175 @property(weak, nonatomic, readonly) FlutterEngine* engine; 176 177 /** 178 * The `FlutterBinaryMessenger` associated with this FlutterViewController (used for communicating 179 * with channels). 180 * 181 * This is just a convenient way to get the |FlutterEngine|'s binary messenger. 182 */ 183 @property(nonatomic, readonly) NSObject<FlutterBinaryMessenger>* binaryMessenger; 184 185 @end 186 187 #endif // FLUTTER_FLUTTERVIEWCONTROLLER_H_ 188