Hello @Jeyamani Sekar !
In well-designed application, device communication (like Bluetooth or WiFi) should be managed independently of the UI layer, which mean the connection and data polling should persist regardless of navigation or page lifecycle events (e.g., OnAppearing or OnDisappearing). Tying the Bluetooth connection to a ContentPage's state can cause issues like disconnections during navigation, as you're experiencing, because page loading can block the UI thread or interrupt event handlers.
Navigation Performance Optimizations
Regarding to the navigation, the lag is likely due to re‑creating and re‑binding complex views (especially RadSliders with multiple ContentViews) every time you switch. Here's what I can give to reduce it:
- Cache ContentViews instead of re‑instantiating
- Keep a dictionary of already created views in your MenuPageViewModel.
- Swap them into a
ContentPresenterinstead of navigating to new pages. - This avoids full page lifecycle overhead.
- Lazy load subviews
- For
RadSliderwith multiple subviews, don’t try create all at once but create only the visible one, and load others on demand.
- For
- Preload critical views in background
- After login, spin up lightweight instances of Dashboard, Settings, Client, Reports in a background task. That way, when the user navigates, they’re already in memory.
- Simplify XAML
- Replace deep nested
StackLayouts withGridorAbsoluteLayout. - Use compiled bindings (
x:DataType) to reduce runtime binding cost. - For lists, use
CollectionViewwithRecycleElement.
- Replace deep nested
- Avoid NavigationPage overhead
- Instead of pushing/popping pages, keep a single MenuPage with a
ContentPresenterand swap views inside it. This is much faster than full page navigation (which involves animations and lifecycle overhead).
- Instead of pushing/popping pages, keep a single MenuPage with a
Bluetooth/Wi‑Fi Connection Persistence
Right now, your device polling is tied to the UI lifecycle. You need to decouple device communication from the UI:
- Move device communication into a background service
- Create a singleton
DeviceServicethat manages Bluetooth/Wi‑Fi connections and run polling on a background thread (TimerorTask.RunwithCancellationToken):public class DeviceService { private Timer _pollTimer; public event EventHandler<DeviceDataEventArgs> DataUpdated; public void StartPolling() { _pollTimer = new Timer(async _ => await PollDeviceData(), null, 0, 1000); } private async Task PollDeviceData() { var data = await ReadFromDevice(); DataUpdated?.Invoke(this, new DeviceDataEventArgs(data)); } }
- Create a singleton
- UI subscribes/unsubscribes
- Each
ContentView(Dashboard, etc.) subscribes toDataUpdatedinOnAppearingand unsubscribes inOnDisappearing. - Use
Device.BeginInvokeOnMainThreadto update UI safely.
- Each
- Enable background modes
- On Android: use a
ForegroundServicefor Bluetooth. - On iOS: enable
bluetooth-centralbackground mode inInfo.plist.
- On Android: use a
- Graceful reconnection
- Add retry logic with exponential backoff if the connection drops.
- Notify the user only if reconnection fails after several attempts.
Once you isolate it into a background service and optimize navigation to reuse views, both problems (lag + disconnects) will disappear.
I hope this helps! Let me know if you have questions!