diff options
| author | xengineering <me@xengineering.eu> | 2026-01-16 21:49:22 +0100 |
|---|---|---|
| committer | xengineering <me@xengineering.eu> | 2026-01-17 20:56:45 +0100 |
| commit | 1dc47d1991910d95b4472ed3e415adb0d46a6617 (patch) | |
| tree | f7dba1ec72756d8460a770d3fe655872d32599dd | |
| parent | e2a1b271e2cf417cd3104e6e0679cb54993e6d8f (diff) | |
| download | sia-app-1dc47d1991910d95b4472ed3e415adb0d46a6617.tar sia-app-1dc47d1991910d95b4472ed3e415adb0d46a6617.tar.zst sia-app-1dc47d1991910d95b4472ed3e415adb0d46a6617.zip | |
Display MQTT connection status
The user otherwise cannot trust the state of the contacts because the
app could just be disconnected from the broker.
| -rw-r--r-- | lib/data.dart | 12 | ||||
| -rw-r--r-- | lib/ui.dart | 30 |
2 files changed, 40 insertions, 2 deletions
diff --git a/lib/data.dart b/lib/data.dart index 08f8881..f5a24e8 100644 --- a/lib/data.dart +++ b/lib/data.dart @@ -10,8 +10,9 @@ const String topicPrefix = 'sia'; class AppState with ChangeNotifier { Map<String, bool> contacts = <String, bool>{}; - late final MqttServerClient _client; + bool _brokerConnected = false; + bool get brokerConnected => _brokerConnected; AppState() { _initMqtt(); @@ -31,9 +32,11 @@ class AppState with ChangeNotifier { _client.port = brokerPort; _client.keepAlivePeriod = 2; + _client.disconnectOnNoResponsePeriod = 1; _client.logging(on: false); _client.onConnected = _onConnected; + _client.onDisconnected = _onDisconnected; try { await _client.connect(); @@ -47,6 +50,13 @@ class AppState with ChangeNotifier { void _onConnected() { _client.subscribe('$topicPrefix/contact/+/state', MqttQos.exactlyOnce); + _brokerConnected = true; + notifyListeners(); + } + + void _onDisconnected() { + _brokerConnected = false; + notifyListeners(); } void _onMessage(List<MqttReceivedMessage<MqttMessage>> messages) { diff --git a/lib/ui.dart b/lib/ui.dart index ff8c3a8..38ace9a 100644 --- a/lib/ui.dart +++ b/lib/ui.dart @@ -11,7 +11,12 @@ class UI extends StatelessWidget { return MaterialApp( home: Scaffold( appBar: AppBar(title: const Text("Contacts")), - body: const ContactList(), + body: const Column( + children: <Widget>[ + Expanded(child: ContactList()), + ], + ), + bottomNavigationBar: const ConnectionStatus(), ), ); } @@ -43,3 +48,26 @@ class ContactList extends StatelessWidget { ); } } + +class ConnectionStatus extends StatelessWidget { + const ConnectionStatus({super.key}); + + @override + Widget build(BuildContext context) { + return Consumer<AppState>( + builder: (BuildContext context, AppState state, Widget? child) { + Icon icon; + Text text; + if (state.brokerConnected) { + icon = const Icon(Icons.cloud, color: Colors.green); + text = const Text('Connected'); + } else { + icon = const Icon(Icons.cloud_off, color: Colors.red); + text = const Text('Disconnected'); + } + + return ListTile(leading: icon, title: text); + }, + ); + } +} |
