diff --git a/agrilink_vocpro/android/app/src/main/AndroidManifest.xml b/agrilink_vocpro/android/app/src/main/AndroidManifest.xml index 7f64aa4..2088e2f 100644 --- a/agrilink_vocpro/android/app/src/main/AndroidManifest.xml +++ b/agrilink_vocpro/android/app/src/main/AndroidManifest.xml @@ -1,4 +1,7 @@ + + + setupMqtt() async {} +} diff --git a/agrilink_vocpro/lib/domain/service/mqtt_service.dart b/agrilink_vocpro/lib/domain/service/mqtt_service.dart new file mode 100644 index 0000000..37ea7e8 --- /dev/null +++ b/agrilink_vocpro/lib/domain/service/mqtt_service.dart @@ -0,0 +1,71 @@ +import 'package:agrilink_vocpro/core/state/result_state.dart'; +import 'package:mqtt_client/mqtt_client.dart'; +import 'package:mqtt_client/mqtt_server_client.dart'; + +class MQTTService { + MqttServerClient? client; + + Future setupMqtt() async { + client = MqttServerClient('armadillo.rmq.cloudamqp.com', ''); + client!.port = 1883; + + client!.connectionMessage = MqttConnectMessage() + .authenticateAs('obyskxhx:obyskxhx', 'Fe_3_tBuwmc8vMMqT2hYiboTsBlBmPz1') + .withClientIdentifier('mobile_client_controller') + .startClean() // reset session + .withWillQos(MqttQos.atLeastOnce); + + try { + print('MQTT: Connecting....'); + await client!.connect(); + print('MQTT: Connected'); + return ResultState.hasData; + } catch (e) { + print('MQTT: Error: $e'); + return ResultState.error; + } + } + + Future publishMessage(String topic, String message) async { + final bool isConnected = await isMqttConnected(); + if (isConnected) { + final builder = MqttClientPayloadBuilder(); + + try { + builder.addString(message); + client!.publishMessage(topic, MqttQos.atLeastOnce, builder.payload!); + return ResultState.hasData; + } catch (e) { + print(e); + return ResultState.error; + } + } else { + return ResultState.error; + } + } + + Future disconnectMqtt() async { + final bool isConnected = await isMqttConnected(); + if (isConnected) { + print('Memutus koneksi dari broker...'); + + client!.disconnect(); + + await Future.delayed(const Duration(seconds: 1)); + print('Koneksi telah terputus.'); + return ResultState.hasData; + } else { + print('Tidak ada koneksi yang sedang aktif.'); + return ResultState.error; + } + } + + Future isMqttConnected() async { + if (client != null && + client!.connectionStatus!.state == MqttConnectionState.connected) { + return true; //connected + } else { + return false; //not connected + } + } +} diff --git a/agrilink_vocpro/lib/domain/service/service.dart b/agrilink_vocpro/lib/domain/service/service.dart index e69de29..97df96f 100644 --- a/agrilink_vocpro/lib/domain/service/service.dart +++ b/agrilink_vocpro/lib/domain/service/service.dart @@ -0,0 +1 @@ +class Service {} diff --git a/agrilink_vocpro/lib/features/control/provider/control_provider.dart b/agrilink_vocpro/lib/features/control/provider/control_provider.dart index 07e0594..59f82ab 100644 --- a/agrilink_vocpro/lib/features/control/provider/control_provider.dart +++ b/agrilink_vocpro/lib/features/control/provider/control_provider.dart @@ -1,56 +1,93 @@ +import 'package:agrilink_vocpro/core/state/result_state.dart'; +import 'package:agrilink_vocpro/domain/service/mqtt_service.dart'; import 'package:flutter/material.dart'; class ControlProvider extends ChangeNotifier { - // control 1 bool _control_1 = false; - bool get control_1 => _control_1; + bool _control_2 = false; + bool _control_3 = false; + bool _control_4 = false; + bool _control_5 = false; + bool _control_6 = false; - switchControl1() { + // Getters + bool get control_1 => _control_1; + bool get control_2 => _control_2; + bool get control_3 => _control_3; + bool get control_4 => _control_4; + bool get control_5 => _control_5; + bool get control_6 => _control_6; + + ControlProvider() { + connectMqtt(); + } + + ResultState mqttState = ResultState.initial; + + // Koneksi MQTT + Future connectMqtt() async { + mqttState = ResultState.loading; + try { + final result = await MQTTService().setupMqtt(); + if (result == ResultState.hasData) { + mqttState = result; + print('Connected to MQTT'); + } else { + mqttState = ResultState.error; + print('Failed to connect to MQTT'); + } + } catch (e) { + print(e); + } + notifyListeners(); + } + + Future disconnectMqtt() async { + try { + final result = await MQTTService().disconnectMqtt(); + if (result == ResultState.hasData) print('Disconnected from MQTT'); + } catch (e) { + rethrow; + } + notifyListeners(); + } + + Future isMqttConnected() async { + return true; + } + + @override + void dispose() { + disconnectMqtt(); + super.dispose(); + } + + void switchControl1() { _control_1 = !_control_1; notifyListeners(); } -// control 2 - bool _control_2 = false; - bool get control_2 => _control_2; - - switchControl2() { + void switchControl2() { _control_2 = !_control_2; notifyListeners(); } -// control 3 - bool _control_3 = false; - bool get control_3 => _control_3; - - switchControl3() { + void switchControl3() { _control_3 = !_control_3; notifyListeners(); } -// control 4 - bool _control_4 = false; - bool get control_4 => _control_4; - - switchControl4() { + void switchControl4() { _control_4 = !_control_4; notifyListeners(); } -// control 5 - bool _control_5 = false; - bool get control_5 => _control_5; - - switchControl5() { + void switchControl5() { _control_5 = !_control_5; notifyListeners(); } -// control 6 - bool _control_6 = false; - bool get control_6 => _control_6; - - switchControl6() { + void switchControl6() { _control_6 = !_control_6; notifyListeners(); } diff --git a/agrilink_vocpro/lib/features/control/view/control_screen.dart b/agrilink_vocpro/lib/features/control/view/control_screen.dart index 98f4802..22943de 100644 --- a/agrilink_vocpro/lib/features/control/view/control_screen.dart +++ b/agrilink_vocpro/lib/features/control/view/control_screen.dart @@ -1,6 +1,6 @@ import 'package:agrilink_vocpro/core/constant/app_theme.dart'; +import 'package:agrilink_vocpro/core/state/result_state.dart'; import 'package:agrilink_vocpro/features/control/provider/control_provider.dart'; -import 'package:agrilink_vocpro/features/home/widgets/graphic_widget.dart'; import 'package:flutter/material.dart'; import 'package:flutter_screenutil/flutter_screenutil.dart'; import 'package:provider/provider.dart'; @@ -21,6 +21,17 @@ class ControlScreen extends StatelessWidget { return SafeArea( child: ListView( children: [ + SizedBox( + height: 16.h, + child: Center( + child: provider.mqttState == ResultState.loading + ? const CircularProgressIndicator() + : provider.mqttState == ResultState.error + ? const Text('Failed to connect to MQTT') + : const Text('Connected to MQTT'), + ), + ), + SizedBox(height: 16.h), ListTile( title: Text('Control 1', style: AppTheme.labelMedium), subtitle: const Text('Control 1 description'), @@ -31,56 +42,7 @@ class ControlScreen extends StatelessWidget { }, ), ), - ListTile( - title: const Text('Control 2'), - subtitle: const Text('Control 2 description'), - trailing: Switch( - value: provider.control_2, - onChanged: (value) { - provider.switchControl2(); - }, - ), - ), - ListTile( - title: const Text('Control 3'), - subtitle: const Text('Control 3 description'), - trailing: Switch( - value: provider.control_3, - onChanged: (value) { - provider.switchControl3(); - }, - ), - ), - ListTile( - title: const Text('Control 4'), - subtitle: const Text('Control 4 description'), - trailing: Switch( - value: provider.control_4, - onChanged: (value) { - provider.switchControl4(); - }, - ), - ), - ListTile( - title: const Text('Control 5'), - subtitle: const Text('Control 5 description'), - trailing: Switch( - value: provider.control_5, - onChanged: (value) { - provider.switchControl5(); - }, - ), - ), - ListTile( - title: const Text('Control 6'), - subtitle: const Text('Control 6 description'), - trailing: Switch( - value: provider.control_6, - onChanged: (value) { - provider.switchControl6(); - }, - ), - ), + // Control lainnya... ], )); }), diff --git a/agrilink_vocpro/pubspec.lock b/agrilink_vocpro/pubspec.lock index c10bae7..e33a1a3 100644 --- a/agrilink_vocpro/pubspec.lock +++ b/agrilink_vocpro/pubspec.lock @@ -41,6 +41,14 @@ packages: url: "https://pub.dev" source: hosted version: "1.3.0" + charcode: + dependency: transitive + description: + name: charcode + sha256: fb98c0f6d12c920a02ee2d998da788bca066ca5f148492b7085ee23372b12306 + url: "https://pub.dev" + source: hosted + version: "1.3.1" clock: dependency: transitive description: @@ -65,6 +73,14 @@ packages: url: "https://pub.dev" source: hosted version: "3.0.5" + csslib: + dependency: transitive + description: + name: csslib + sha256: "706b5707578e0c1b4b7550f64078f0a0f19dec3f50a178ffae7006b0a9ca58fb" + url: "https://pub.dev" + source: hosted + version: "1.0.0" cupertino_icons: dependency: "direct main" description: @@ -97,6 +113,14 @@ packages: url: "https://pub.dev" source: hosted version: "2.0.5" + event_bus: + dependency: transitive + description: + name: event_bus + sha256: "1a55e97923769c286d295240048fc180e7b0768902c3c2e869fe059aafa15304" + url: "https://pub.dev" + source: hosted + version: "2.0.1" fake_async: dependency: transitive description: @@ -184,6 +208,14 @@ packages: url: "https://pub.dev" source: hosted version: "6.2.1" + html: + dependency: transitive + description: + name: html + sha256: "3a7812d5bcd2894edf53dfaf8cd640876cf6cef50a8f238745c8b8120ea74d3a" + url: "https://pub.dev" + source: hosted + version: "0.15.4" http: dependency: transitive description: @@ -272,6 +304,14 @@ packages: url: "https://pub.dev" source: hosted version: "1.15.0" + mqtt_client: + dependency: "direct main" + description: + name: mqtt_client + sha256: "37aae360fac0b3322cb37267696c1535e1ad2984a13064d877273ffe4b16ca7a" + url: "https://pub.dev" + source: hosted + version: "10.5.1" nested: dependency: transitive description: @@ -477,6 +517,22 @@ packages: url: "https://pub.dev" source: hosted version: "1.3.2" + universal_html: + dependency: transitive + description: + name: universal_html + sha256: "56536254004e24d9d8cfdb7dbbf09b74cf8df96729f38a2f5c238163e3d58971" + url: "https://pub.dev" + source: hosted + version: "2.2.4" + universal_io: + dependency: transitive + description: + name: universal_io + sha256: "1722b2dcc462b4b2f3ee7d188dad008b6eb4c40bbd03a3de451d82c78bba9aad" + url: "https://pub.dev" + source: hosted + version: "2.2.2" vector_math: dependency: transitive description: diff --git a/agrilink_vocpro/pubspec.yaml b/agrilink_vocpro/pubspec.yaml index 91f3ef9..108f867 100644 --- a/agrilink_vocpro/pubspec.yaml +++ b/agrilink_vocpro/pubspec.yaml @@ -45,6 +45,7 @@ dependencies: animated_segmented_tab_control: ^2.0.0 flutter_screenutil: ^5.9.3 gauge_indicator: ^0.4.3 + mqtt_client: ^10.5.1 dev_dependencies: flutter_test: