Is there an existing issue for this?
Description of the bug
Repo: https://github.com/googlemaps/react-native-navigation-sdk/issues/new
Title: Android: setDestinations throws ClassCastException when a waypoint sets preferredHeading (Double cast to Integer)
Environment
@googlemaps/react-native-navigation-sdk 0.16.3 (the cast is unchanged on main at 036c83e, 2026-09-07)
- React Native 0.86, Expo SDK 57, new architecture
- Android (Samsung, Android 15); iOS is unaffected
Steps
await navigationController.setDestinations(
[
{ title: 'Entry', position: { lat: 42.27853, lng: -83.67608 }, preferredHeading: 0 },
{ title: 'Destination', position: { lat: 42.32438, lng: -83.62626 } },
],
{ routingOptions: { travelMode: TravelMode.DRIVING } },
);
Expected
The route is computed with the heading preference applied to the first waypoint (as on iOS).
Actual
The promise rejects before the SDK is called:
Exception in HostFunction: java.lang.Double cannot be cast to java.lang.Integer
at com.google.android.react.navsdk.NavModule.createWaypoint(NavModule.java:571)
at com.google.android.react.navsdk.NavModule.setDestinations(NavModule.java:604)
Cause
NavModule.createWaypoint casts the raw map value:
if (map.containsKey("preferredHeading")) {
int preferredHeading = (int) map.get("preferredHeading"); // line 571
waypointBuilder.setPreferredHeading(preferredHeading);
}
Every JS number crosses the bridge as a java.lang.Double, so the (int) cast throws. The same file already handles this correctly two lines earlier for travelMode via CollectionUtil.getInt, which does ((Double) map.get(name)).intValue().
Fix (one line)
if (map.containsKey("preferredHeading")) {
int preferredHeading = CollectionUtil.getInt("preferredHeading", map, 0);
waypointBuilder.setPreferredHeading(preferredHeading);
}
Happy to open a PR if that is welcome.
Workaround
Omit preferredHeading on Android (Platform.OS === 'android'), which loses the side-of-road hint there.
iOS Platform
Not affected
Android Platform
Affected
React Native version
0.86.2
React version
19.2.3
Package version
wrapper 0.16.3 with its stock native pins, Navigation SDK for iOS 10.13.0 and for Android 7.6.1.
Native SDK versions
React Native Doctor Output
Common
✓ Node.js - Required to execute JavaScript code
✓ yarn - Required to install NPM dependencies
✓ npm - Required to install NPM dependencies
● Watchman - Used for watching changes in the filesystem when in development mode
● Metro - Metro Bundler is not running
Android
✖ Adb - No devices and/or emulators connected. Please create emulator with Android Studio or connect Android device.
✓ JDK - Required to compile Java code
✓ Android Studio - Required for building and installing your app on Android
✓ ANDROID_HOME - Environment variable that points to your Android SDK installation
✖ Gradlew - Build tool required for Android builds
✖ Android SDK - Required for building and installing your app on Android
- Versions found: 30.0.3, 33.0.2, 34.0.0, 34.0.0, 35.0.0, 36.0.0
- Version supported: Not Found
iOS
✓ Xcode - Required for building and installing your app on iOS
✓ Ruby
✖ CocoaPods - Required for installing iOS dependencies
- Version found: N/A
- Version supported: >= 1.10.0
✓ .xcode.env - File to customize Xcode environment
Errors: 4
Warnings: 2
Expo SDK 57 managed project, native builds on EAS; no local android/ or ios/ checkout, hence Gradlew and CocoaPods missing and no supported SDK version detected. The Samsung device was disconnected when this ran.
Steps to reproduce
- Install @googlemaps/react-native-navigation-sdk 0.16.3 in a React Native 0.86 app (new architecture) and run it on an Android device. iOS is not needed; it is unaffected.
- Initialize navigation as usual: NavigationView mounted, terms accepted, navigationController.init() returned OK, and a location fix has arrived.
- Call setDestinations with any waypoint that sets preferredHeading, for example:
await navigationController.setDestinations(
[
{ title: 'Entry', position: { lat: 42.27853, lng: -83.67608 }, preferredHeading: 0 },
{ title: 'Destination', position: { lat: 42.32438, lng: -83.62626 } },
],
{ routingOptions: { travelMode: TravelMode.DRIVING } },
);
- Observe: the promise rejects immediately, before the native SDK computes a route:
Exception in HostFunction: java.lang.Double cannot be cast to java.lang.Integer
at com.google.android.react.navsdk.NavModule.createWaypoint(NavModule.java:571)
at com.google.android.react.navsdk.NavModule.setDestinations(NavModule.java:604)
Any value reproduces it, including 0, 12, and 12.0, because the JS number always arrives as a java.lang.Double.
- Remove preferredHeading from the waypoint and call again: the route is computed and guidance starts. The same waypoint with preferredHeading works on iOS.
Expected vs Actual Behavior
The route is computed with the heading preference applied to the first waypoint (as on iOS).
Code Sample
if (map.containsKey("preferredHeading")) {
int preferredHeading = CollectionUtil.getInt("preferredHeading", map, 0);
waypointBuilder.setPreferredHeading(preferredHeading);
}
Additional Context
No response
Is there an existing issue for this?
Description of the bug
Repo: https://github.com/googlemaps/react-native-navigation-sdk/issues/new
Title: Android:
setDestinationsthrows ClassCastException when a waypoint setspreferredHeading(Double cast to Integer)Environment
@googlemaps/react-native-navigation-sdk0.16.3 (the cast is unchanged onmainat 036c83e, 2026-09-07)Steps
Expected
The route is computed with the heading preference applied to the first waypoint (as on iOS).
Actual
The promise rejects before the SDK is called:
Cause
NavModule.createWaypointcasts the raw map value:Every JS number crosses the bridge as a
java.lang.Double, so the(int)cast throws. The same file already handles this correctly two lines earlier fortravelModeviaCollectionUtil.getInt, which does((Double) map.get(name)).intValue().Fix (one line)
Happy to open a PR if that is welcome.
Workaround
Omit
preferredHeadingon Android (Platform.OS === 'android'), which loses the side-of-road hint there.iOS Platform
Not affected
Android Platform
Affected
React Native version
0.86.2
React version
19.2.3
Package version
wrapper 0.16.3 with its stock native pins, Navigation SDK for iOS 10.13.0 and for Android 7.6.1.
Native SDK versions
React Native Doctor Output
Common
✓ Node.js - Required to execute JavaScript code
✓ yarn - Required to install NPM dependencies
✓ npm - Required to install NPM dependencies
● Watchman - Used for watching changes in the filesystem when in development mode
● Metro - Metro Bundler is not running
Android
✖ Adb - No devices and/or emulators connected. Please create emulator with Android Studio or connect Android device.
✓ JDK - Required to compile Java code
✓ Android Studio - Required for building and installing your app on Android
✓ ANDROID_HOME - Environment variable that points to your Android SDK installation
✖ Gradlew - Build tool required for Android builds
✖ Android SDK - Required for building and installing your app on Android
iOS
✓ Xcode - Required for building and installing your app on iOS
✓ Ruby
✖ CocoaPods - Required for installing iOS dependencies
✓ .xcode.env - File to customize Xcode environment
Errors: 4
Warnings: 2
Expo SDK 57 managed project, native builds on EAS; no local android/ or ios/ checkout, hence Gradlew and CocoaPods missing and no supported SDK version detected. The Samsung device was disconnected when this ran.
Steps to reproduce
await navigationController.setDestinations(
[
{ title: 'Entry', position: { lat: 42.27853, lng: -83.67608 }, preferredHeading: 0 },
{ title: 'Destination', position: { lat: 42.32438, lng: -83.62626 } },
],
{ routingOptions: { travelMode: TravelMode.DRIVING } },
);
Exception in HostFunction: java.lang.Double cannot be cast to java.lang.Integer
at com.google.android.react.navsdk.NavModule.createWaypoint(NavModule.java:571)
at com.google.android.react.navsdk.NavModule.setDestinations(NavModule.java:604)
Any value reproduces it, including 0, 12, and 12.0, because the JS number always arrives as a java.lang.Double.
Expected vs Actual Behavior
The route is computed with the heading preference applied to the first waypoint (as on iOS).
Code Sample
Additional Context
No response