Alameda Dev.
Published in

Alameda Dev.

Installing React Native with Mapbox Navigation in iOS

For many years we researched a way to have the Google Direction ability in React Native. Right now this package exists thanks to https://www.homee.com/ team.

You can find the package at https://github.com/homeeondemand/react-native-mapbox-navigation

Unfortunately I had a lot of trouble installing this package, encountered many errors, and wanted to give a step by step tutorial integration.

Create a react-native app

react-native init MapboxNavigation

Check everything is running

Unfortunately Flipper was producing many errors for me on iOS, like:


> cd MapboxNavigation
> react-native run-ios
...
The following build commands failed:
CompileC /Users/os/Library/Developer/Xcode/DerivedData/MapboxNavigation-fihdhqqvpzufydfwkiousnssilfq/Build/Intermediates.noindex/Pods.build/Debug-iphonesimulator/Flipper.build/Objects-normal/x86_64/FlipperRSocketResponder.o /Users/os/Desktop/Bouncing/MapboxNavigation/ios/Pods/Flipper/xplat/Flipper/FlipperRSocketResponder.cpp normal x86_64 c++ com.apple.compilers.llvm.clang.1_0.compiler
(1 failure)

Open your ‘Podfile’ file and replace:

use_flipper to use_flipper!({ 'Flipper-Folly' => '2.3.0' })

Remove ‘Podfile.lock’ and then run pod install

> react-native run-ios
...
Build Succeeded

Our app is running now

Install react-native-mapbox-navigation

Lets add the package react-native-mapbox-navigation to our project.

yarn add @homee/react-native-mapbox-navigation

Have you secret and public Mapbox Token at hand. You can generate those here:

  • Your Public access token: From your account’s tokens page , you can either copy your default_public_token or click the Create a token button to create a new public token.
  • A secret access token with the Downloads:Read scope.
    1. From your account’s tokens page, click the Create a token button.
    2. From the token creation page, give your token a name and make sure the box next to the Downloads:Read scope is checked.
    3. Click the Create token button at the bottom of the page to create your token.
    4. The token you’ve created is a secret_token, which means you will only have one opportunity to copy it somewhere secure.

Now, following their documentation and BEFORE you do pod install, let’s do some previous and necessary steps first.

  1. Create a ‘.netrc’ file on your computer home folder (not you project folder)
    touch ~/.netrc
    And open the file with your editor
    code ~/.netrc
    Add the following to the file
machine api.mapbox.com
login mapbox
password YOUR_SECRET_ACCESS_TOKEN

2. Open your ‘.MapboxNavigation.xcworkspace’ project in Xcode
Now as we are using Mapbox Native SDK under the hood we need to have a Objective-C bridging header for swift, otherwise the package won’t work.

To do this:

  • From Xcode, select your ‘AppDelegate.m’ file and right click on it.
  • Select New File…
  • Select Swift File.
  • Name your file Dummy or whatever you want, I named it ‘MapboxDirection’.
  • In the Group dropdown, make sure to select the group folder for your app, not the project itself.
  • After you create the Swift file, you should be prompted to choose if you want to configure an Objective-C Bridging Header. Select “Create Bridging Header”.

Here is aGIF for these steps.

3. Place your public token in your project’s ‘Info.plist’ and and add a ‘MGLMapboxAccessToken’ key whose value is your public access token.

<key>MGLMapboxAccessToken</key>
<sring>YOUR_PUBLIC_ACCESS_TOKEN</sring>

Now we can run pod install from the iOS folder
cd ios ; pod install

You will see all additional packages are installed.

Installing Mapbox-iOS-SDK (6.3.0)
Installing MapboxAccounts (2.3.1)
Installing MapboxCommon (9.2.0)
Installing MapboxCoreNavigation (1.2.1)
Installing MapboxDirections (1.2.0)
Installing MapboxMobileEvents (0.10.8)
Installing MapboxNavigation (1.2.1)
Installing MapboxNavigationNative (30.0.0)
Installing MapboxSpeech (1.0.0)
Installing Polyline (5.0.2)
Installing Solar (2.1.0)
Installing Turf (1.2.0)
Installing react-native-mapbox-navigation (1.0.0)

Check everything is running

Let’s check if everything is running.

> react-native run-ios
...
error Failed to build iOS project. We ran “xcodebuild” command but it exited with error code 65. To debug build logs further, consider building your app with Xcode.app, by opening MapboxNavigation.xcworkspace. Run CLI with — verbose flag for more details.
...
Build system information
error: Multiple commands produce ‘/Users/os/Library/Developer/Xcode/DerivedData/MapboxNavigation-fihdhqqvpzufydfwkiousnssilfq/Build/Products/Debug-iphonesimulator/MapboxNavigation.app/Assets.car’:
1) Target ‘MapboxNavigation’ (project ‘MapboxNavigation’) has compile command with input ‘/Users/os/Desktop/Bouncing/MapboxNavigation/ios/MapboxNavigation/Images.xcassets’
2) That command depends on command in Target ‘MapboxNavigation’ (project ‘MapboxNavigation’): script phase “[CP] Copy Pods Resources”

Ok, the integration guide tells something about this. We need to add some code to the top of the ‘Podfile’:

require_relative '../node_modules/react-native/scripts/react_native_pods'
require_relative '../node_modules/@react-native-community/cli-platform-ios/native_modules'
platform :ios, '10.0'// add the next line
install! 'cocoapods', :disable_input_output_paths => true
...

In the terminal execute:
cd ios; pod update; pod install

Lets try to tun the app again:

> react-native run-ios
...
▸ Build Succeeded
success Successfully built the app
error Failed to get the target build directory. Run CLI with — verbose flag for more details.

Not sure what is happening so I opt for running the project in Xcode to see if there is any other clue of why it is failing.

On Xcode Product -> Build

*Showing Recent Messages*
Signing for “MapboxNavigation” requires a development team. Select a development team in the Signing & Capabilities editor.

Ok, let’s select a development team for this project, make sure you do it on all your targets.

Again, On Xcode Product -> Build

Undefined symbols for architecture arm64:
“_swift_getFunctionReplacement”, referenced from:
_swift_getFunctionReplacement50 in libswiftCompatibilityDynamicReplacements.a(DynamicReplaceable.cpp.o)
(maybe you meant: _swift_getFunctionReplacement50)
ld: symbol(s) not found for architecture arm64
clang: error: linker command failed with exit code 1 (use -v to see invocation)

Ok, new error, I searched in the react-native-mapbox-navigation issues and found so many steps to do:

  1. Go to Project > Build Settings > Library search path
  2. Remove “$(TOOLCHAIN_DIR)/usr/lib/swift-5.0/$(PLATFORM_NAME)”

3. Set ‘Don’t Dead-strip Inits and Terms’ to ‘Yes’ for both Project and all Targets

4. Set ‘Always Embed Swift Standard Libraries’ to ‘Yes’ in the build settings Project and all Targets.

Next, On Xcode Product -> Build

Seems like this Build does success, so lets run the project in the simulator

It failed with this error:

dyld: Library not loaded: @rpath/MapboxMobileEvents.framework/MapboxMobileEvents
Referenced from: /Users/os/Library/Developer/CoreSimulator/Devices/F4BE899E-D625–45DE-9708–649C8263A45A/data/Containers/Bundle/Application/717BD298-BB7F-4AFB-8FA9–8000D3611B4F/MapboxNavigation.app/Frameworks/Mapbox.framework/Mapbox
Reason: image not found

For this we need to add ‘use_frameworks!’ to the ‘Podfile’. Unfortunately Flipper can’t be use with ‘use_framweorks` so I had to disable it

...
install! ‘cocoapods’, :disable_input_output_paths => true
use_frameworks!
...
# Enables Flipper.
#
# Note that if you have use_frameworks! enabled, Flipper will not work and you should disable these next few lines.
# use_flipper!({ ‘Flipper-Folly’ => ‘2.3.0’ })
# post_install do |installer|
# flipper_post_install(installer)
# end
...

Exceute in the ios folder

cd ios; pod update; pod install

Removing CocoaAsyncSocket
Removing CocoaLibEvent
Removing Flipper
Removing Flipper-DoubleConversion
Removing Flipper-Folly
Removing Flipper-Glog
Removing Flipper-PeerTalk
Removing Flipper-RSocket
Removing FlipperKit
Removing OpenSSL-Universal
Removing YogaKit

Next, On Xcode Product -> Build

Undefined symbols for architecture x86_64:
“_OBJC_CLASS_$_RCTViewManager”, referenced from:
type metadata for react_native_mapbox_navigation.MapboxNavigationManager in MapboxNavigationManager-00758322f339d0e6dfca28eea53c318c2d7d6f5559454e4f45ca706c8ab22e30.o
“_OBJC_METACLASS_$_RCTViewManager”, referenced from:
_OBJC_METACLASS_$_MapboxNavigationManager in MapboxNavigationManager-00758322f339d0e6dfca28eea53c318c2d7d6f5559454e4f45ca706c8ab22e30.o
“_RCTRegisterModule”, referenced from:
_initialize_MapboxNavigationManager in MapboxNavigationManager-00758322f339d0e6dfca28eea53c318c9998a9e17a6bf7596501d341d52f1444.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)

Another error, “Undefined symbols for architecture x86_64”

  • Select your pod project
  • In Targets Select MapboxNavigation
  • Select Build phase at the top
  • Select Link Binary With Libraries
  • Click the +
  • Search for “MapboxMobileEvents.framework”
  • Click Add
  • Clean
  • Rebuild

Next, On Xcode Product -> Build
This still got me the error, so I had to:

  • Clear Xcode Cache
    rm -rf ~/Library/Developer/Xcode/DerivedData
  • Go into iOS folder
    cd ios
  • Clear CocoaPods Cache
    pod deintegrate && pod cache clean — all
  • Re-Install Pods
    pod install

Next, On Xcode Product -> Build
The app finally ran

Integrate react-native-mapbox-navigation

Lets change our ‘App.js’ file to the base for react-native-mapbox-navigation

import * as React from 'react';
import {StyleSheet, View} from 'react-native';
import MapboxNavigation from '@homee/react-native-mapbox-navigation';
const App = () => {
return (
<View style={styles.container}>
<MapboxNavigation
origin={[-97.760288, 30.273566]}
destination={[-97.918842, 30.494466]}
shouldSimulateRoute={true}
onLocationChange={(event) => {
const {latitude, longitude} = event.nativeEvent;
}}
onRouteProgressChange={(event) => {
const {
distanceTraveled,
durationRemaining,
fractionTraveled,
distanceRemaining,
} = event.nativeEvent;
}}
onError={(event) => {
const {message} = event.nativeEvent;
}}
onCancelNavigation={() => {
// User tapped the “X” cancel button in the nav UI
// or canceled via the OS system tray on android.
// Do whatever you need to here.
}}
onArrive={() => {
// Called when you arrive at the destination.
}}
/>
</View>
);
};
const styles = StyleSheet.create({
container: {
flex: 1,
},
});
export default App;

Run the app now.

The app stops and in Xcode we have this error:

Assertion failed: This application’s Info.plist file must include “audio” in UIBackgroundModes. This background mode is used for spoken instructions while the application is in the background.: file

We need to add audio in background mode for this to work
Add to your Info.plist

  • Required background modes
  • Item 0: audio

Run the app again.

And finally we have the app running!

Find the code for this tutorial at our GitLab account https://gitlab.com/alamedadev/mapboxnavigation

Do you want to test Mapbox Navigation?

Take a look for the main functionalities:

- Accurate turn-by-turn nav

Create a route, track the user’s progress to the destination and provide audio and visual guidance along the way.

- Traffic-aware routing

Traffic updates at a 5-minute granularity for 2.3 billion roads segments around the world.

- Offline routing

Keep the driver headed to their destination even when network connectivity is temporarily unavailable.

- Faster route detection

Check periodically for a faster route and generate alerts when one is available.

- Dynamic maps

Create on-brand map experiences with high performance rendering.

Hello We are Alameda Dev.!

We would love to help you, offer you a first conversation to talk about your ideas and help you focus on them.

Alameda Dev. Is a 100% remote team. Specialized in developing mobile applications, websites and advanced software in the React ecosystem.

You can read other interesting posts about technology: https://medium.com/alameda-dev

You can also enter the web: www.alamedadev.com

Follow us on:

Twitter: @AlamedaDev

--

--

--

We are a small agency 100% Remote. Specialized in Design and Development of Mobile Apps, Web and advanced software with React Ecosystem.

Recommended from Medium

Easy Google Maps Setup Tutorial— Swift 5

How do you use Hierarchical styles in SwiftUI?

foreground.hierarchical.png

How to make your first app

We want to use animation conversion on iPhone — — How to convert AnimeGAN2 to CoreML

A Quick Tip: Using Objects

UICollectionViewLayout With Self Sizing Cells (Part 3)

6 YouTube channels that every iOS developer should subscribe

Multi-Threading in Swift Using MongoDB Realm

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store
Alameda Dev.

Alameda Dev.

¡Hola! We are a team 100% Remote. Specialized Development of Mobile Apps, Web and advanced software with React and ReactNative. www.alamedadev.com

More from Medium

Flutter vs React Native: Stop Comparing & Competing Today

Building theme-based Mobile app for a Multi Backend Architecture

Hybrid Application: Native-like Experience with WebView

WebView

Visualizing multiple percentages as polygons: React Native polygon chart