Skip to content

Mapbox integration#3

Merged
sbasu107 merged 18 commits intomainfrom
mapbox-integration
Jan 23, 2026
Merged

Mapbox integration#3
sbasu107 merged 18 commits intomainfrom
mapbox-integration

Conversation

@sbasu107
Copy link
Member

This pull request introduces a significant navigation system overhaul and migration to the Expo Router architecture, along with several supporting improvements. The most notable changes include enabling tab-based navigation with Expo Router, implementing a global navigation context and route visualization feature, updating configuration and environment management (notably for Mapbox integration), and improving documentation and developer tooling.

Navigation System & Expo Router Migration:

  • Migrated the app structure to use Expo Router for navigation, replacing the previous navigation setup. This includes new tab layouts in app/(tabs)/_layout.js and corresponding route files for each tab, enabling more modular and scalable navigation. (app/(tabs)/_layout.js, app/(tabs)/index.js, app/(tabs)/systems.js, app/(tabs)/signal-search.js, app/(tabs)/environmental.js, app/(tabs)/profile.js, app/_layout.js, index.js, package.json, [1] [2] [3] [4] [5] [6] [7] [8] [9]

  • Added a global NavigationContext to manage navigation state and route selection, supporting persistent navigation features across screens. (app/_layout.js, src/context/NavigationContext.js, app/_layout.jsR1-R48)

Navigation Features & Route Visualization:

  • Implemented a navigation system allowing users to select, visualize, and persistently track progress along pre-defined routes (stored as CSV files) on the map. This includes toggling navigation mode, selecting routes, and rendering waypoints and lines on both inline and fullscreen maps. (docs/NAVIGATION_FEATURES.md, metro.config.js, [1] [2]

Configuration, Environment, and Mapbox Integration:

  • Added support for loading a Mapbox access token from .env, environment variables, or app.json using a new app.config.js. This improves developer experience and makes Mapbox configuration more flexible and secure. (.env.example, app.config.js, README.md, [1] [2] [3]

  • Updated app.json and related files to set dark mode as default, add iOS/Android bundle/package identifiers, and register new Expo plugins. (app.json, app.jsonL8-R34)

Developer Experience & Tooling:

  • Added Babel and dotenv configuration for compatibility with Expo Router and environment variable loading. (babel.config.js, package.json, [1] [2] [3]

  • Updated Metro bundler config to support .csv files as assets, enabling dynamic route loading. (metro.config.js, metro.config.jsL29-R29)

Documentation and Scripts:

  • Expanded the README.md with detailed Mapbox setup instructions and updated screenshots to reflect the new navigation and tab structure. (README.md, [1] [2]

  • Added a conversion script for datasets, supporting easier data import and sampling. (scripts/convert_dataset.js, scripts/convert_dataset.jsR1-R26)


Summary of Key Changes:

Navigation & Routing:

  • Migrated to Expo Router for navigation, with new tab-based layout and modular route files. [1] [2] [3] [4] [5] [6] [7] [8] [9]
  • Implemented persistent global navigation state via NavigationContext.

Navigation Features:

  • Added route visualization and selection, with CSV-based route management and dynamic loading. [1] [2]

Configuration & Environment:

  • Enabled Mapbox token management via .env, environment variables, or app.json, with a new config loader and example file. [1] [2] [3]

Developer Tooling:

  • Added Babel and dotenv setup for Expo Router and environment variable support. [1] [2] [3]

Documentation:

  • Updated and expanded documentation for navigation features, Mapbox setup, and added new screenshots. [1] [2] [3]

These changes lay the foundation for advanced navigation features and a more maintainable, modular app architecture.

sbasu107 and others added 11 commits January 11, 2026 12:51
… and log helpful warning; update README troubleshooting
…nd route updates

- Add comprehensive Mapbox error handling with try-catch, map event listeners, and WebView error callbacks
- Implement global unit preferences in ThemeProvider (speed units, temperature units)
- Add functional 3D rendering toggle in settings
- Add gradient fade to 3D car viewer for smooth visual transition
- Replace Colorado ski trip with Madison ehall_trip route data (308 positions)
- Remove Australia route files and update routeLoader to use ehall_trip only
- Restructure navigation: rename Systems tab to Signal Search, create new Systems page with dropdown
- Add Sparky logo to Battery screen header
- Remove StarsOverlay from Battery/Strategy screens when embedded
- Separate weather temperature units from battery temperature units (weather uses local toggle, battery uses global setting)
- Add WebView compatibility props (allowsInlineMediaPlayback, mixedContentMode)
- Create conversion script for route data (ehall_trip.csv → dataset1_positions.json)
Copilot AI review requested due to automatic review settings January 23, 2026 04:52
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This pull request introduces a comprehensive navigation system overhaul by migrating from React Navigation to Expo Router, implementing Mapbox integration, and adding race strategy features with route visualization. The changes include new tab-based navigation, persistent navigation state management, unit preferences (speed and temperature), 3D rendering toggles, and CSV-based route loading with dynamic visualization on maps.

Changes:

  • Migrated from React Navigation to Expo Router with native tab bars and file-based routing
  • Added Mapbox GL JS integration with flexible token configuration via .env, app.config.js, or app.json
  • Implemented navigation features with CSV route loading, waypoint visualization, and persistent navigation state via NavigationContext
  • Added user preferences for speed units, temperature units, and 3D rendering to ThemeProvider
  • Restructured Systems screen with dropdown selector routing to Battery, Strategy, and placeholder subsystems
  • Created new StrategyScreen with race strategy recommendations, sparkline charts, and route preview

Reviewed changes

Copilot reviewed 34 out of 49 changed files in this pull request and generated 25 comments.

Show a summary per file
File Description
app/(tabs)/_layout.js New Expo Router tab layout with native tabs for iOS and Android
app/_layout.js Root layout with providers (Theme, Navigation, fonts)
index.js Updated to use Expo Router entry point
src/context/NavigationContext.js Global navigation state for route selection and nav mode
src/data/routeLoader.js CSV route loading with Asset API and waypoint parsing
src/data/routes/ehall_trip.csv Sample route data for navigation testing
src/data/dataset1_positions.json Position replay data for telemetry simulation
src/screens/SystemsScreen.js Refactored to dropdown-based system selector
src/screens/StrategyScreen.js New screen with race strategy metrics and map preview
src/screens/SignalSearchScreen.js Extracted from old SystemsScreen
src/screens/ProfileScreen.js Added speed/temp unit preferences UI
src/screens/Home2Screen.js Added battery temperature with global tempUnit preference
src/screens/BatteryScreen.js Added Sparky logo header image
src/components/MapView.js Added Mapbox GL JS support, navigation controls, route visualization
src/components/LocationWeatherDisplay.js Restructured location display with state/country
src/components/Battery3DViewer.js Added cell selection grid placeholder
src/theme/ThemeProvider.js Added speedUnit, tempUnit, render3D preferences
app.config.js Dynamic config loader for Mapbox token from .env
.env.example Template for environment variables
package.json Added expo-router, dotenv dependencies
metro.config.js Added CSV to asset extensions
babel.config.js Standard Expo preset for Expo Router support

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +166 to +183
useEffect(() => {
if (selectedRoute) {
loadRoute(selectedRoute)
.then(routeData => {
setLoadedRouteData(routeData);
// Draw route on map (both inline and fullscreen)
if (mapLoaded && webViewRef.current) {
drawRouteOnMap(routeData);
}
})
.catch(err => {
console.error('Failed to load route:', err);
if (!inline) {
Alert.alert('Error', 'Failed to load route');
}
});
}
}, [selectedRoute, mapLoaded, inline]);
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The useEffect that loads route data (lines 166-183) is missing drawRouteOnMap in its dependency array. If drawRouteOnMap is not wrapped in useCallback, this could lead to stale closures or missed updates. Either add drawRouteOnMap to the dependency array or wrap it in useCallback.

Copilot uses AI. Check for mistakes.
Comment on lines +17 to +31
const [useImperialUnits, setUseImperialUnits] = useState(true); // For weather only
const [locationName, setLocationName] = useState('Madison, WI');
const { theme } = useTheme();
const { theme, render3D, tempUnit } = useTheme();

// Temperature helpers (same logic as HomeScreen)
const convertTemperature = (celsius) => {
// Temperature helpers - for weather (uses local useImperialUnits)
const convertWeatherTemperature = (celsius) => {
return useImperialUnits ? Math.round(celsius * 9/5 + 32) : Math.round(celsius || 0);
};
const getTempUnit = () => useImperialUnits ? '°F' : '°C';
const getWeatherTempUnit = () => useImperialUnits ? '°F' : '°C';

// Battery temperature helper - uses global tempUnit setting
const convertBatteryTemperature = (celsius) => {
return tempUnit === 'imperial' ? Math.round(celsius * 9/5 + 32) : Math.round(celsius || 0);
};
const getBatteryTempUnit = () => tempUnit === 'imperial' ? '°F' : '°C';
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The Home2Screen has two separate unit systems: useImperialUnits for weather (local state) and tempUnit from theme context for battery temperature. This creates confusing UX where users might set temperature units in the profile/settings but only see it apply to battery temperature, not weather. Consider consolidating to use a single temperature unit preference from the theme context for both weather and battery, or clearly document why they need to be different.

Copilot uses AI. Check for mistakes.

// Selected cell for UI interactions (placeholder for real 3D selection)
const [selectedCell, setSelectedCell] = useState(null);
const CELL_COUNT = 12; // placeholder cell count; replace with actual count when model integration is added
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The cell grid UI (added in Battery3DViewer) shows 12 cells but the actual battery system has 29 modules as seen in BatteryScreen.js (line 301). This hardcoded CELL_COUNT of 12 doesn't match the actual system architecture and could confuse users. Either update CELL_COUNT to match the actual module count (29) or clarify in the UI that this is a placeholder visualization.

Copilot uses AI. Check for mistakes.
Comment on lines +37 to +44
const hasLatHeader = headers.includes('lat') || headers.includes('latitude');
const hasLngHeader = headers.includes('lng') || headers.includes('longitude');
const hasNameHeader = headers.includes('name');

// Determine column indices
const latIndex = headers.indexOf('latitude') !== -1 ? headers.indexOf('latitude') : headers.indexOf('lat');
const lngIndex = headers.indexOf('longitude') !== -1 ? headers.indexOf('longitude') : headers.indexOf('lng');
const nameIndex = headers.indexOf('name');
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The variables hasLatHeader and hasLngHeader are computed but never used. These checks should be removed or used to validate the CSV format before attempting to parse it. Currently, if a CSV file doesn't have the expected headers, latIndex or lngIndex will be -1, and the code will silently fail to parse waypoints correctly.

Copilot uses AI. Check for mistakes.
Comment on lines +12 to +17
// Unit preferences
const [speedUnit, setSpeedUnit] = useState('imperial'); // 'imperial' | 'metric'
const [tempUnit, setTempUnit] = useState('imperial'); // 'imperial' | 'metric'

// 3D rendering preference
const [render3D, setRender3D] = useState(true);
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The unit preferences (speedUnit, tempUnit) and render3D setting are stored only in React state, which means they will reset to default values every time the app restarts. These user preferences should be persisted using AsyncStorage or similar persistent storage mechanism so users don't have to reconfigure them on every app launch.

Copilot uses AI. Check for mistakes.
@@ -0,0 +1,236 @@
import React, { useState, useEffect } from 'react';
import { View, Text, StyleSheet, ScrollView, TouchableOpacity, Pressable, Dimensions } from 'react-native';
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unused import Dimensions.

Copilot uses AI. Check for mistakes.
import { SafeAreaView } from 'react-native-safe-area-context';
import { useTheme } from '../theme/ThemeProvider';
import { Ionicons } from '@expo/vector-icons';
import { BlurView } from 'expo-blur';
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unused import BlurView.

Copilot uses AI. Check for mistakes.
import { useNavigation } from '../context/NavigationContext';

export default function StrategyScreen() {
const { theme, isDark } = useTheme();
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unused variable isDark.

Copilot uses AI. Check for mistakes.
const { theme, isDark } = useTheme();
const { navigationEnabled, setNavigationEnabled, selectedRoute, setSelectedRoute } = useNavigation();
const [telemetryData, setTelemetryData] = useState(null);
const [lastUpdate, setLastUpdate] = useState(new Date());
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Unused variable lastUpdate.

Copilot uses AI. Check for mistakes.
</BlurView>

{/* Navigation Controls */}
{!inline && (
Copy link

Copilot AI Jan 23, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This negation always evaluates to true.

Copilot uses AI. Check for mistakes.
- Add overrides field to package.json to enforce tar >= 7.5.4 for all dependencies
- Fixes CVE: Race Condition in node-tar Path Reservations via Unicode collisions on macOS APFS
- Fixes CVE: Arbitrary File Overwrite and Symlink Poisoning via Insufficient Path Sanitization
- Current tar version: 7.5.6 (satisfies both security patches)
…rsions

- Update @react-navigation/bottom-tabs from ^6.6.1 to ^7.4.0 (installed: 7.10.1)
- Update @react-navigation/native from ^6.1.18 to ^7.1.8 (installed: 7.1.28)
- Fixes expo-doctor compatibility warnings
- Add expo.install.exclude config to ignore @react-navigation/bottom-tabs and @react-navigation/native
- Installed versions (7.10.1 and 7.1.28) are newer than minimum required (7.4.0 and 7.1.8)
- Fixes expo-doctor failing on minor/patch version differences
- All 17 expo-doctor checks now pass
- expo-doctor has a bug where it exits with code 1 without --verbose even when all checks pass
- With --verbose flag, all 17 checks pass correctly and exit with code 0
- Fixes CI pipeline failures on doctor check
- Remove --platform all and specify --platform ios --platform android explicitly
- Avoids requiring react-native-web since this is a mobile-only app
- Export now completes successfully with 1402 modules bundled
- expo-doctor has a bug where it exits with code 1 even when all checks pass
- Update CI to check for 'No issues detected' in verbose output instead of relying on exit code
- Script now correctly identifies when all 17 checks pass successfully
@sbasu107 sbasu107 merged commit 8ea57b2 into main Jan 23, 2026
3 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant