A React Native Expo app demonstrating Bluetooth Low Energy (BLE) communication with iOS Live Activities and Dynamic Island integration. This project showcases how to bridge IoT devices with iOS's real-time notification system using React Native, Expo Targets, and react-native-ble-manager.
DemoRNBleLiveActivities-Video.mov
- π΅ Bluetooth Low Energy Integration - Scan, connect, and communicate with BLE devices
- π± iOS Live Activities - Real-time device status updates on the lock screen
- ποΈ Dynamic Island Support - Compact and expanded views in the Dynamic Island
- π Real-time Data Sync - Live updates from BLE characteristics to Live Activities
- π Comprehensive Debug Logging - Detailed logs for development and troubleshooting
- β‘ Expo Targets - Native iOS Live Activity implementation using Expo's target system
This repository was used to demonstrate concepts presented at: Seamless BLE to Live Activity Sync in React Native β No Push Needed. Presented at React Summit (by GitNation), this talk explores how Bluetooth Low Energy (BLE) can be used to drive real-time UI updates (Live Activities) without relying on network connectivity or push notifications.
This app demonstrates a complete BLE-to-LiveActivity pipeline:
BLE Device β React Native App β Live Activity β iOS Lock Screen/Dynamic Island
- BLE Manager:
react-native-ble-managerfor Bluetooth communication - Live Activities: Native iOS implementation using
@bacons/apple-targets - Real-time Updates: Automatic sync between BLE characteristics and Live Activity state
- Debug System: Comprehensive logging for development and monitoring
The Live Activity displays:
- Device Status: Connected/Disconnected state with visual indicators
- Real-time Data: Button state (ON/OFF) and battery level updates
- Dynamic Island: Compact, expanded, and minimal views
- Lock Screen: Full widget with device information
- React Native 0.81.4
- Expo SDK 54
- TypeScript for type safety
- react-native-ble-manager for BLE communication
- @bacons/apple-targets for Live Activities
- Expo Router for navigation
- iOS Live Activities (ActivityKit)
- iOS 16.1+ (Live Activities requirement)
- Xcode 14+ for iOS development
- Node.js 18+
- Expo CLI latest version
- Physical iOS device (Live Activities don't work in simulator)
- Peripheral Device - You'll need to run a BLE peripheral to test with
git clone https://github.com/BMR11/DemoRNBleLiveActivities.git
cd DemoRNBleLiveActivities
npm installThis demo requires a BLE peripheral device to connect to. You have two options:
Clone and run the Swift Core Bluetooth peripheral demo:
# Clone the peripheral app
git clone https://github.com/BMR11/SwiftCoreBluetoothDemo.git
cd SwiftCoreBluetoothDemo
git checkout adding-fake-battery-service
# Open in Xcode
open SwiftCoreBluetoothDemo.xcodeproj- Open the project in Xcode
- Run the MyPeripheral target on a physical iOS device
- The app will advertise the LBS (Light Button Service) with battery characteristics
- This peripheral will simulate button presses and battery level changes
If you have a Nordic nRF52 DK:
- Flash the LBS sample code to your nRF52
- The device will advertise the required BLE service automatically
# Remove existing iOS folder and regenerate
rm -rf ios
npx expo prebuild -p ios
# Start the development server
npx expo start
# Open in Xcode
xed ios- Open the project in Xcode
- Select your physical iOS device (Live Activities require physical device)
- Build and run the app
- Grant Bluetooth permissions when prompted
- Start the peripheral app on another device
- Scan and connect to the peripheral from the central app
The app is configured to work with a specific BLE service:
const MY_LBS_SERVICE_UUID = "00001523-1212-EFDE-1523-785FEABCD123";
const MY_BUTTON_CHARACTERISTIC_UUID = "00001524-1212-EFDE-1523-785FEABCD123";
const MY_BATTERY_CHARACTERISTIC_UUID = "00001111-1212-EFDE-1523-785FEABCD123";The Live Activity is configured in targets/widget/WidgetLiveActivity.swift with:
- Lock Screen Widget: Full device status display
- Dynamic Island: Compact and expanded views
- Real-time Updates: Automatic state synchronization
-
Start the Peripheral (from SwiftCoreBluetoothDemo)
- Run the MyPeripheral target on a physical iOS device
- The app will advertise the LBS service with battery characteristics
- You'll see button and battery simulation controls
-
Start the Central App (this React Native app)
- Run the DemoRNBleLiveActivities app on another physical iOS device
- Grant Bluetooth permissions when prompted
- Tap "Scan for Devices" to discover nearby BLE devices
- The app will scan for 5 seconds and display found devices
- Look for the peripheral device from the Swift app
- Device information includes name, RSSI, and connection status
- Tap on the discovered peripheral device to connect
- The app will establish a BLE connection and start Live Activity
- Real-time data will begin flowing from device to Live Activity
- Button State: Press/release the button in the peripheral app
- Battery Level: Use the battery slider in the peripheral app
- Live Activity Updates: Watch the Live Activity update in real-time
- Dynamic Island: Check the Dynamic Island for compact updates
- Check your iOS lock screen for the Live Activity widget
- View device status in the Dynamic Island (if available)
- Real-time updates show button state and battery level
- Use the debug panel at the bottom to monitor BLE communication
- View detailed logs of all BLE operations and Live Activity updates
- Clear logs as needed for better monitoring
The app includes comprehensive debugging:
- Real-time Logging: All BLE operations are logged with timestamps
- Live Activity Tracking: Monitor when Live Activities start/stop/update
- Connection Status: Track device connection and disconnection events
- Data Flow: Monitor characteristic value changes and updates
βββ app/ # Expo Router app structure
β βββ (tabs)/
β β βββ index.tsx # Main BLE demo screen
β βββ _layout.tsx # Root layout
βββ components/bluetooth/ # BLE-related components
β βββ ConnectedState.tsx # Connected device UI
β βββ DisconnectedState.tsx # Device scanning UI
β βββ PeripheralList.tsx # Device list component
βββ targets/widget/ # iOS Live Activity target
β βββ WidgetLiveActivity.swift # Live Activity implementation
β βββ Attributes.swift # Live Activity data model
βββ modules/activity-controller/ # Live Activity management
βββ types/bluetooth.ts # TypeScript definitions
- Uses
react-native-ble-managerfor cross-platform BLE communication - Implements characteristic notifications for real-time data
- Handles connection state management and error recovery
- Native iOS implementation using
@bacons/apple-targets - Supports both Lock Screen widgets and Dynamic Island
- Real-time updates via ActivityKit
- React hooks for BLE state management
- Real-time Live Activity updates
- Comprehensive debug logging system
-
Live Activity not appearing
- Ensure you're using a physical iOS device (not simulator)
- Check that iOS version is 16.1 or later
- Verify Live Activity permissions in Settings
-
BLE scanning not working
- Ensure Bluetooth is enabled
- Check app permissions for Bluetooth
- Verify you're using a physical device
-
Connection failures
- Check that your BLE device is advertising the correct service UUID
- Ensure the device is within range
- Check debug logs for specific error messages
- Fork the repository
- Create a feature branch
- Make your changes
- Test on physical iOS device
- Submit a pull request
This project is licensed under the MIT License - see the LICENSE file for details.
- Expo for the amazing development platform
- react-native-ble-manager for BLE functionality
- @bacons/apple-targets for Live Activities support
- SwiftCoreBluetoothDemo for the peripheral implementation
- Apple for Live Activities and Dynamic Island APIs
Built with β€οΈ for the React Native community