[< Back](../readme.md) # Integration Guide for `PenNav P&P` Native iOS Libraries in Flutter #### Requirements - iOS 13.0 or later - iPadOS 13.0 or later #### Prerequisites - Flutter SDK installed. - Basic knowledge of Flutter and iOS development. - Penguin native iOS libraries (Penguin.xcframework, PenguinRenderer.xcframework, PenNavUI.xcframework). - Mapbox Account: Register for a Mapbox account to obtain an access token for Mapbox services. ## Steps ### **Step 1 : Install Mapbox Maps SDK v10.6.4 for iOS** To install the Mapbox Maps SDK for iOS and get authorization, follow these steps: #### **1. Register and Get Authorization** 1. **Create a Mapbox Account:** - Go to [Mapbox's Sign Up page](https://www.mapbox.com/signup/) and create a free account. 2. **Get Your Access Token:** - After logging in, go to your [Mapbox account dashboard](https://account.mapbox.com/). - Navigate to the "Access Tokens" section. - Copy your default access token or create a new token with the desired permissions. 3. **Set Up Your Secret Token (Important)** - For guidance on configuring your secret token, please refer to the Mapbox installation guide at: [Mapbox iOS Maps Installation](https://docs.mapbox.com/ios/maps/guides/install/). 4. **Configure your public token** To configure your public access token, follow these steps: - Open your project's Info.plist file - Hover over a key and click the plus button - Type MBXAccessToken into the key field - Click the value field and paste in your public access token. --- ### **Step 2 : Add Native Libraries to Your Flutter Project** 1. **Create the Frameworks Folder:** - Open Finder and navigate to your Flutter project’s `ios` directory. - Right-click inside the `ios` folder, select **New Folder**, and name the folder **Frameworks**. 2. **Move .xcframework Files:** - Locate your `.xcframework` files in Finder. - Select the files, right-click, and choose **Copy**. - Navigate to the newly created **Frameworks** folder. - Right-click inside the **Frameworks** folder and select **Paste** to move the files. #### Update the Xcode Project 1. **Open Xcode Workspace:** - Open the `ios/Runner.xcworkspace` file in Xcode. 2. **Add .xcframework Files to Xcode:** - Drag and drop the `.xcframework` files into the "Frameworks" group in the Xcode project navigator. - Ensure the **Copy items if needed** checkbox is selected. #### Update Build Settings 1. **Configure Framework Search Paths:** - Select the **Runner** target in Xcode. - Go to the **Build Settings** tab. - Add `$(SRCROOT)/Frameworks` to the **Framework Search Paths**. 2. **Verify Framework Embedding:** - In the **General** tab of the Runner target, check that the frameworks are listed under **Frameworks, Libraries, and Embedded Content**. - Ensure the frameworks are set to **Embed & Sign**. --- ### **Step 3 : Configuring Privacy Permissions in `Info.plist`** In the iOS project, modify the `Info.plist` file to include the following keys. Set their data types to `String` and provide descriptive values that explain the necessity of your app's access to these privacy-sensitive resources: - `NSLocationAlwaysAndWhenInUseUsageDescription` - `NSLocationWhenInUseUsageDescription` - `NSBluetoothAlwaysUsageDescription` - `NSMotionUsageDescription` Ensure that each key is assigned a string value detailing the purpose for which your application requires access to the respective data. --- ### **Step 4 : Modify the Podfile** 1. Navigate to your Flutter project's `ios` directory: ```sh cd path/to/your/flutter/project/ios ``` 2. Open the `Podfile` in a text editor: ```sh open Podfile ``` 3. Update your `Podfile` to include the Mapbox Maps SDK dependency and apply the necessary build setting. Your `Podfile` should look like this: ```ruby target 'Runner' do use_frameworks! use_modular_headers! pod 'MapboxMaps', '10.16.4' flutter_install_all_ios_pods File.dirname(File.realpath(__FILE__)) target 'RunnerTests' do inherit! :search_paths end end post_install do |installer| installer.pods_project.targets.each do |target| target.build_configurations.each do |config| config.build_settings['BUILD_LIBRARY_FOR_DISTRIBUTION'] = 'YES' end end end ``` #### **3. Install CocoaPods Dependencies** 1. Install the CocoaPods dependencies by running: ```sh pod install ``` 2. This will create or update the `Pods` directory and the `.xcworkspace` file. #### **4. Open the Xcode Workspace** 1. Open the generated `.xcworkspace` file to make sure the Mapbox SDK is correctly integrated: ```sh open Runner.xcworkspace ``` 2. Always use this `.xcworkspace` file to open your project in Xcode, as it includes the CocoaPods dependencies. --- #### Native iOS configuration steps - **For detailed instructions on how to configure and initialize the Penguin SDKs, please start by checking out the [Configuration Steps](configuringPanNavUI.md#configuration-steps). It is important to begin here to ensure a proper setup.** --- ### **Step 5 : Create the Flutter Platform View Factory View** - **Implement the View Factory:** Create `PenguinViewFactory.swift` in `ios/Runner`. ```swift import Flutter import UIKit class PenguinViewFactory: NSObject, FlutterPlatformViewFactory { private var messenger: FlutterBinaryMessenger init(messenger: FlutterBinaryMessenger) { self.messenger = messenger super.init() } func create( withFrame frame: CGRect, viewIdentifier viewId: Int64, arguments args: Any? ) -> FlutterPlatformView { return PenguinView( frame: frame, viewIdentifier: viewId, arguments: args, binaryMessenger: messenger) } public func createArgsCodec() -> FlutterMessageCodec & NSObjectProtocol { return FlutterStandardMessageCodec.sharedInstance() } } ``` --- ### **Step 6 : Implement the Custom View:** Create `PenguinView.swift` in `ios/Runner`. ```swift import Flutter import UIKit class PenguinView: NSObject, FlutterPlatformView { private var _view: UIView init( frame: CGRect, viewIdentifier viewId: Int64, arguments args: Any?, binaryMessenger messenger: FlutterBinaryMessenger? ) { _view = UIView() super.init() // Initialize and configure the view using Penguin libraries // Example: // let penguinView = PenguinLibraryView(frame: frame) // _view.addSubview(penguinView) } func view() -> UIView { return _view } } ``` --- ### **Step 7 : Register the Platform View in AppDelegate** - **Modify `AppDelegate.swift`:** ```swift import UIKit import Flutter @UIApplicationMain @objc class AppDelegate: FlutterAppDelegate { override func application( _ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]? ) -> Bool { GeneratedPluginRegistrant.register(with: self) let penguinFactory = PenguinViewFactory(messenger: self.registrar(forPlugin: "penguin")!.messenger()) self.registrar(forPlugin: "PenguinView")!.register(penguinFactory, withId: "penguin_lib") return super.application(application, didFinishLaunchingWithOptions: launchOptions) } } ``` --- ### **Step 8 : Use the Platform View in Flutter** - **Modify Your Dart Code:** ```dart import 'package:flutter/material.dart'; import 'package:flutter/services.dart'; void main() { runApp(MyApp()); } class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { const viewType = 'penguin_lib'; final creationParams = {}; return MaterialApp( home: Scaffold( body: Container( child: Platform.isIOS ? UiKitView( viewType: viewType, layoutDirection: TextDirection.ltr, creationParams: creationParams, onPlatformViewCreated: onPlatformViewCreated, creationParamsCodec: const StandardMessageCodec(), ) : AndroidView( viewType: viewType, layoutDirection: TextDirection.ltr, creationParams: creationParams, onPlatformViewCreated: onPlatformViewCreated, creationParamsCodec: const StandardMessageCodec(), ), ), ), ); } Future onPlatformViewCreated(int id) async { // Handle platform view creation } } ``` ### **Test Your Integration** - Build and run your app on an iOS device or simulator. - Verify that the custom native view appears and functions as expected. ### Tips: - Ensure all framework dependencies are correctly resolved. - Check that you have the appropriate permissions and entitlements if required by the native libraries. - Debug using Xcode if you encounter any issues related to the view or integration. [< Back](../readme.md)