| af0eb765f94aecba228edd3e3fe3c4f4 | |||||
| 440505e9ea1eee7043d2cbfeb318f6bc |
| "$(inherited)", | "$(inherited)", | ||||
| "$(PROJECT_DIR)/Flutter", | "$(PROJECT_DIR)/Flutter", | ||||
| ); | ); | ||||
| MARKETING_VERSION = 0.10.0; | |||||
| MARKETING_VERSION = 0.10.1; | |||||
| PRODUCT_BUNDLE_IDENTIFIER = vn.azteam.tpfarm; | PRODUCT_BUNDLE_IDENTIFIER = vn.azteam.tpfarm; | ||||
| PRODUCT_NAME = Runner; | PRODUCT_NAME = Runner; | ||||
| SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; | SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; | ||||
| "$(inherited)", | "$(inherited)", | ||||
| "$(PROJECT_DIR)/Flutter", | "$(PROJECT_DIR)/Flutter", | ||||
| ); | ); | ||||
| MARKETING_VERSION = 0.10.0; | |||||
| MARKETING_VERSION = 0.10.1; | |||||
| PRODUCT_BUNDLE_IDENTIFIER = vn.azteam.tpfarm; | PRODUCT_BUNDLE_IDENTIFIER = vn.azteam.tpfarm; | ||||
| PRODUCT_NAME = Runner; | PRODUCT_NAME = Runner; | ||||
| SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; | SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; | ||||
| "$(inherited)", | "$(inherited)", | ||||
| "$(PROJECT_DIR)/Flutter", | "$(PROJECT_DIR)/Flutter", | ||||
| ); | ); | ||||
| MARKETING_VERSION = 0.10.0; | |||||
| MARKETING_VERSION = 0.10.1; | |||||
| PRODUCT_BUNDLE_IDENTIFIER = vn.azteam.tpfarm; | PRODUCT_BUNDLE_IDENTIFIER = vn.azteam.tpfarm; | ||||
| PRODUCT_NAME = Runner; | PRODUCT_NAME = Runner; | ||||
| SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; | SWIFT_OBJC_BRIDGING_HEADER = "Runner/Runner-Bridging-Header.h"; |
| String name; | String name; | ||||
| String status; | String status; | ||||
| String location; | String location; | ||||
| num mode; | |||||
| bool isSelected; | bool isSelected; | ||||
| Device({this.id, this.name, this.status, this.location}); | |||||
| Device({this.id, this.name, this.status, this.location, this.mode}); | |||||
| Device.clone(Device device) { | Device.clone(Device device) { | ||||
| this.id = device.id; | this.id = device.id; | ||||
| this.name = device.name; | this.name = device.name; | ||||
| this.status = device.status; | this.status = device.status; | ||||
| this.location = device.location; | this.location = device.location; | ||||
| this.mode = device.mode; | |||||
| } | } | ||||
| Device.fromJson(Map<String, dynamic> json) { | Device.fromJson(Map<String, dynamic> json) { | ||||
| name = json['name']; | name = json['name']; | ||||
| status = json['status']; | status = json['status']; | ||||
| location = json['location']; | location = json['location']; | ||||
| mode = json['mode']; | |||||
| isSelected = false; | isSelected = false; | ||||
| } | } | ||||
| data['name'] = this.name; | data['name'] = this.name; | ||||
| data['status'] = this.status; | data['status'] = this.status; | ||||
| data['location'] = this.location; | data['location'] = this.location; | ||||
| data['mode'] = this.mode; | |||||
| return data; | return data; | ||||
| } | } | ||||
| } | } |
| var token = await pref.getString(DATA_CONST.TOKEN_KEY); | var token = await pref.getString(DATA_CONST.TOKEN_KEY); | ||||
| options.headers["Authorization"] = "Bearer $token"; | options.headers["Authorization"] = "Bearer $token"; | ||||
| options.receiveTimeout = 20000; | options.receiveTimeout = 20000; | ||||
| // log("onRequest: ${options.uri}\n" | |||||
| // "data=${options.data}\n" | |||||
| // "method=${options.method}\n" | |||||
| // "headers=${options.headers}\n" | |||||
| // "queryParameters=${options.queryParameters}"); | |||||
| log("onRequest: ${options.uri}\n" | |||||
| "data=${options.data}\n" | |||||
| "method=${options.method}\n" | |||||
| "headers=${options.headers}\n" | |||||
| "queryParameters=${options.queryParameters}"); | |||||
| return options; | return options; | ||||
| } | } | ||||
| @PUT("/api/tb-crops") | @PUT("/api/tb-crops") | ||||
| Future<void> updateCrop(@Body() TbCropDTO crop); | Future<void> updateCrop(@Body() TbCropDTO crop); | ||||
| //Device | //Device | ||||
| @GET("/api/listDeviceOfUserCustomers") | |||||
| Future<List<Device>> getDevices(); | |||||
| @GET("/api/listDeviceOfUserCustomers?query={query}") | |||||
| Future<List<Device>> getDevices({@Path() String query}); | |||||
| //Get environment parameter | //Get environment parameter | ||||
| @GET("/api/list-environment-updates-display/{cropId}?page={page}&size={size}") | @GET("/api/list-environment-updates-display/{cropId}?page={page}&size={size}") | ||||
| Future<List<EnvironmentParameter>> getEnvironmentParameters( | Future<List<EnvironmentParameter>> getEnvironmentParameters( |
| } | } | ||||
| @override | @override | ||||
| getDevices() async { | |||||
| getDevices({query}) async { | |||||
| const _extra = <String, dynamic>{}; | const _extra = <String, dynamic>{}; | ||||
| final queryParameters = <String, dynamic>{}; | final queryParameters = <String, dynamic>{}; | ||||
| final _data = <String, dynamic>{}; | final _data = <String, dynamic>{}; | ||||
| final Response<List<dynamic>> _result = await _dio.request( | final Response<List<dynamic>> _result = await _dio.request( | ||||
| '/api/listDeviceOfUserCustomers', | |||||
| '/api/listDeviceOfUserCustomers?query=$query', | |||||
| queryParameters: queryParameters, | queryParameters: queryParameters, | ||||
| options: RequestOptions( | options: RequestOptions( | ||||
| method: 'GET', | method: 'GET', |
| } | } | ||||
| //Device | //Device | ||||
| Future<List<Device>> getDevices() { | |||||
| Future<List<Device>> getDevices(String query) { | |||||
| final client = RestClient(dio); | final client = RestClient(dio); | ||||
| return client.getDevices(); | |||||
| return client.getDevices(query: query); | |||||
| } | } | ||||
| //Environment Parameter | //Environment Parameter |
| import 'package:farm_tpf/utils/const_color.dart'; | |||||
| import 'package:flutter/material.dart'; | |||||
| class SearchWidget extends StatefulWidget { | |||||
| final Function(String) searchPressed; | |||||
| SearchWidget({@required this.searchPressed}); | |||||
| @override | |||||
| _SearchWidgetState createState() => _SearchWidgetState(); | |||||
| } | |||||
| class _SearchWidgetState extends State<SearchWidget> { | |||||
| BuildContext _blocContext; | |||||
| TextEditingController _searchController = TextEditingController(); | |||||
| @override | |||||
| void initState() { | |||||
| super.initState(); | |||||
| _searchController.addListener(() { | |||||
| final keyword = _searchController.text; | |||||
| if (keyword.isNotEmpty) { | |||||
| //search when text change | |||||
| } | |||||
| }); | |||||
| } | |||||
| Widget getSearchBarUI() { | |||||
| _searchController.text = ""; | |||||
| return Padding( | |||||
| padding: const EdgeInsets.only(left: 8, right: 8, top: 4, bottom: 4), | |||||
| child: Row( | |||||
| children: <Widget>[ | |||||
| Expanded( | |||||
| child: Padding( | |||||
| padding: const EdgeInsets.only(right: 8, top: 8, bottom: 0), | |||||
| child: Container( | |||||
| decoration: BoxDecoration( | |||||
| color: Colors.white, | |||||
| borderRadius: const BorderRadius.all( | |||||
| Radius.circular(38.0), | |||||
| ), | |||||
| boxShadow: <BoxShadow>[ | |||||
| BoxShadow( | |||||
| color: Colors.grey.withOpacity(0.2), | |||||
| offset: const Offset(0, 2), | |||||
| blurRadius: 8.0), | |||||
| ], | |||||
| ), | |||||
| child: Padding( | |||||
| padding: const EdgeInsets.only( | |||||
| left: 16, right: 16, top: 4, bottom: 4), | |||||
| child: TextField( | |||||
| textInputAction: TextInputAction.done, | |||||
| controller: _searchController, | |||||
| onChanged: (String txt) {}, | |||||
| cursorColor: COLOR_CONST.GRAY1, | |||||
| decoration: InputDecoration( | |||||
| border: InputBorder.none, | |||||
| hintText: 'Tìm kiếm ...', | |||||
| ), | |||||
| onSubmitted: widget.searchPressed, | |||||
| ), | |||||
| ), | |||||
| ), | |||||
| ), | |||||
| ), | |||||
| ], | |||||
| ), | |||||
| ); | |||||
| } | |||||
| @override | |||||
| Widget build(BuildContext context) { | |||||
| _blocContext = context; | |||||
| return Container(child: getSearchBarUI()); | |||||
| } | |||||
| @override | |||||
| void dispose() { | |||||
| _searchController.dispose(); | |||||
| super.dispose(); | |||||
| } | |||||
| } |
| } else if (event is ControlDevice) { | } else if (event is ControlDevice) { | ||||
| yield* _mapControlDeviceToState( | yield* _mapControlDeviceToState( | ||||
| event.currentDevices, event.updatedDeviceId); | event.currentDevices, event.updatedDeviceId); | ||||
| } else if (event is OnSearch) { | |||||
| yield* _mapOnSearchToState(event.query); | |||||
| } | |||||
| } | |||||
| Stream<DeviceState> _mapOnSearchToState(String query) async* { | |||||
| yield DisplayDevice.loading(); | |||||
| try { | |||||
| List<Device> devices = new List<Device>(); | |||||
| final response = await repository.getDevices(query); | |||||
| devices = response; | |||||
| devices.sort((a, b) => (a.id).compareTo(b.id)); | |||||
| yield DisplayDevice.data(devices); | |||||
| } catch (e) { | |||||
| yield DisplayDevice.error(AppException.handleError(e)); | |||||
| } | } | ||||
| } | } | ||||
| yield DisplayDevice.loading(); | yield DisplayDevice.loading(); | ||||
| try { | try { | ||||
| List<Device> devices = new List<Device>(); | List<Device> devices = new List<Device>(); | ||||
| final response = await repository.getDevices(); | |||||
| final response = await repository.getDevices(""); | |||||
| devices = response; | devices = response; | ||||
| devices.sort((a, b) => (a.id).compareTo(b.id)); | devices.sort((a, b) => (a.id).compareTo(b.id)); | ||||
| yield DisplayDevice.data(devices); | yield DisplayDevice.data(devices); |
| List<Object> get props => []; | List<Object> get props => []; | ||||
| } | } | ||||
| class OnSearch extends DeviceEvent { | |||||
| final String query; | |||||
| OnSearch({@required this.query}); | |||||
| @override | |||||
| List<Object> get props => [query]; | |||||
| } | |||||
| class ControlDevice extends DeviceEvent { | class ControlDevice extends DeviceEvent { | ||||
| final List<Device> currentDevices; | final List<Device> currentDevices; | ||||
| final int updatedDeviceId; | final int updatedDeviceId; |
| import 'package:farm_tpf/data/repository/repository.dart'; | import 'package:farm_tpf/data/repository/repository.dart'; | ||||
| import 'package:farm_tpf/presentation/custom_widgets/widget_search.dart'; | |||||
| import 'package:farm_tpf/presentation/screens/control_device/widget_device_list.dart'; | import 'package:farm_tpf/presentation/screens/control_device/widget_device_list.dart'; | ||||
| import 'package:flutter/material.dart'; | import 'package:flutter/material.dart'; | ||||
| import 'package:flutter_bloc/flutter_bloc.dart'; | import 'package:flutter_bloc/flutter_bloc.dart'; | ||||
| class _ControlDeviceScreenState extends State<ControlDeviceScreen> { | class _ControlDeviceScreenState extends State<ControlDeviceScreen> { | ||||
| BuildContext _blocContext; | BuildContext _blocContext; | ||||
| DeviceBloc _deviceBloc = DeviceBloc(repository: Repository()); | |||||
| @override | @override | ||||
| void initState() { | void initState() { | ||||
| super.initState(); | super.initState(); | ||||
| _deviceBloc.add(OpenScreen()); | |||||
| } | } | ||||
| @override | @override | ||||
| } | } | ||||
| Widget _buildContent() { | Widget _buildContent() { | ||||
| return BlocBuilder<DeviceBloc, DeviceState>( | |||||
| builder: (context, state) { | |||||
| if (state is DisplayDevice) { | |||||
| if (state.loading) { | |||||
| return Container( | |||||
| child: Center( | |||||
| child: CircularProgressIndicator(), | |||||
| ), | |||||
| ); | |||||
| } | |||||
| return Column( | |||||
| children: [ | |||||
| SearchWidget(searchPressed: (value) { | |||||
| FocusScope.of(context).requestFocus(FocusNode()); | |||||
| _deviceBloc.add(OnSearch(query: value)); | |||||
| }), | |||||
| Expanded( | |||||
| child: BlocBuilder<DeviceBloc, DeviceState>( | |||||
| cubit: _deviceBloc, | |||||
| builder: (context, state) { | |||||
| if (state is DisplayDevice) { | |||||
| if (state.loading) { | |||||
| return Container( | |||||
| child: Center( | |||||
| child: CircularProgressIndicator(), | |||||
| ), | |||||
| ); | |||||
| } | |||||
| if (state.devices != null) { | |||||
| return Container( | |||||
| child: WidgetDeviceList(devices: state.devices), | |||||
| ); | |||||
| } | |||||
| return Container(); | |||||
| } else { | |||||
| return Container(); | |||||
| } | |||||
| }, | |||||
| if (state.devices != null) { | |||||
| return Container( | |||||
| child: WidgetDeviceList( | |||||
| devices: state.devices, | |||||
| deviceBloc: _deviceBloc, | |||||
| ), | |||||
| ); | |||||
| } | |||||
| return Container(); | |||||
| } else { | |||||
| return Container(); | |||||
| } | |||||
| }, | |||||
| )) | |||||
| ], | |||||
| ); | ); | ||||
| } | } | ||||
| } | } |
| import 'package:dio/dio.dart'; | import 'package:dio/dio.dart'; | ||||
| import 'package:farm_tpf/custom_model/Device.dart'; | import 'package:farm_tpf/custom_model/Device.dart'; | ||||
| import 'package:farm_tpf/data/api/app_exception.dart'; | |||||
| import 'package:farm_tpf/presentation/custom_widgets/widget_loading.dart'; | import 'package:farm_tpf/presentation/custom_widgets/widget_loading.dart'; | ||||
| import 'package:farm_tpf/presentation/custom_widgets/widget_utils.dart'; | import 'package:farm_tpf/presentation/custom_widgets/widget_utils.dart'; | ||||
| import 'package:farm_tpf/presentation/screens/control_device/bloc/device_bloc.dart'; | import 'package:farm_tpf/presentation/screens/control_device/bloc/device_bloc.dart'; | ||||
| import 'package:flutter_bloc/flutter_bloc.dart'; | import 'package:flutter_bloc/flutter_bloc.dart'; | ||||
| class WidgetDeviceList extends StatefulWidget { | class WidgetDeviceList extends StatefulWidget { | ||||
| List<Device> devices; | |||||
| WidgetDeviceList({@required this.devices}); | |||||
| final DeviceBloc deviceBloc; | |||||
| final List<Device> devices; | |||||
| WidgetDeviceList({@required this.devices, @required this.deviceBloc}); | |||||
| @override | @override | ||||
| _WidgetDeviceListState createState() => _WidgetDeviceListState(); | _WidgetDeviceListState createState() => _WidgetDeviceListState(); | ||||
| } | } | ||||
| } | } | ||||
| Widget widgetDeviceList(List<ItemDeviceVM> items, BuildContext context) { | Widget widgetDeviceList(List<ItemDeviceVM> items, BuildContext context) { | ||||
| return Container( | |||||
| child: GridView.count( | |||||
| childAspectRatio: (10 / 7), | |||||
| crossAxisCount: 2, | |||||
| children: items.map( | |||||
| (item) { | |||||
| return _widgetItemDevice(item, context); | |||||
| return RefreshIndicator( | |||||
| child: ListView.builder( | |||||
| itemBuilder: (BuildContext context, int index) { | |||||
| return _widgetItemDevice(items[index], context); | |||||
| }, | }, | ||||
| ).toList(), | |||||
| )); | |||||
| itemCount: items.length, | |||||
| ), | |||||
| onRefresh: () async { | |||||
| widget.deviceBloc.add(OpenScreen()); | |||||
| }, | |||||
| ); | |||||
| } | } | ||||
| Widget _widgetItemDevice(ItemDeviceVM item, BuildContext context) { | Widget _widgetItemDevice(ItemDeviceVM item, BuildContext context) { | ||||
| return GestureDetector( | return GestureDetector( | ||||
| onTap: () { | |||||
| //Navigator.of(context).push(MaterialPageRoute(builder: (context) => DeviceDetail(device: _device,))); | |||||
| }, | |||||
| child: Card( | |||||
| margin: EdgeInsets.all(8.0), | |||||
| shadowColor: Colors.grey, | |||||
| elevation: 3, | |||||
| child: Column( | |||||
| crossAxisAlignment: CrossAxisAlignment.center, | |||||
| mainAxisAlignment: MainAxisAlignment.center, | |||||
| children: <Widget>[ | |||||
| Column( | |||||
| children: <Widget>[ | |||||
| powerBtn(item, context), | |||||
| Text( | |||||
| item.name, | |||||
| style: TextStyle( | |||||
| color: Colors.black54, | |||||
| fontSize: 13, | |||||
| fontWeight: FontWeight.bold), | |||||
| overflow: TextOverflow.clip, | |||||
| maxLines: 2, | |||||
| textAlign: TextAlign.center, | |||||
| ), | |||||
| Text(""), | |||||
| widgetStatus(item) | |||||
| ], | |||||
| ) | |||||
| ]), | |||||
| )); | |||||
| onTap: () { | |||||
| //Navigator.of(context).push(MaterialPageRoute(builder: (context) => DeviceDetail(device: _device,))); | |||||
| }, | |||||
| child: Card( | |||||
| child: ListTile( | |||||
| leading: powerBtn(item, context), | |||||
| title: Text( | |||||
| '${item.name} - ${item.location ?? ''}', | |||||
| style: TextStyle( | |||||
| color: Colors.black54, fontSize: 13, fontWeight: FontWeight.bold), | |||||
| ), | |||||
| subtitle: widgetStatus(item), | |||||
| )), | |||||
| ); | |||||
| } | } | ||||
| Widget powerBtn(ItemDeviceVM item, BuildContext _context) { | Widget powerBtn(ItemDeviceVM item, BuildContext _context) { | ||||
| }, | }, | ||||
| builder: (context, state) { | builder: (context, state) { | ||||
| if (state is DisplayDevice) { | if (state is DisplayDevice) { | ||||
| if (state.loading) { | |||||
| return Container( | |||||
| child: Center( | |||||
| child: CircularProgressIndicator(), | |||||
| ), | |||||
| ); | |||||
| } | |||||
| if (state.devices != null) { | if (state.devices != null) { | ||||
| currentDevices = state.devices; | currentDevices = state.devices; | ||||
| if (item.status == "0") { | |||||
| //tat | |||||
| return IconButton( | |||||
| icon: Icon(Icons.power_settings_new), | |||||
| color: Colors.grey, | |||||
| onPressed: () async { | |||||
| //bat | |||||
| _controlSwitchDevice(item, context); | |||||
| }); | |||||
| } else if (item.status == "1") { | |||||
| //Bat | |||||
| return IconButton( | |||||
| icon: Icon(Icons.power_settings_new), | |||||
| color: Colors.blue, | |||||
| onPressed: () async { | |||||
| //tat | |||||
| _controlSwitchDevice(item, context); | |||||
| }); | |||||
| //mode = 1: auto -> cho phep dieu khien | |||||
| if (item.mode == 1) { | |||||
| if (item.status == "0") { | |||||
| //tat | |||||
| return IconButton( | |||||
| icon: Icon(Icons.power_settings_new), | |||||
| color: Colors.grey, | |||||
| onPressed: () async { | |||||
| //bat | |||||
| _controlSwitchDevice(item, context); | |||||
| }); | |||||
| } else if (item.status == "1") { | |||||
| //Bat | |||||
| return IconButton( | |||||
| icon: Icon(Icons.power_settings_new), | |||||
| color: Colors.blue, | |||||
| onPressed: () async { | |||||
| //tat | |||||
| _controlSwitchDevice(item, context); | |||||
| }); | |||||
| } else { | |||||
| //loi | |||||
| return IconButton( | |||||
| icon: Icon(Icons.power_settings_new), | |||||
| color: Colors.grey, | |||||
| onPressed: () {}); | |||||
| } | |||||
| } else { | } else { | ||||
| //loi | |||||
| return IconButton( | return IconButton( | ||||
| icon: Icon(Icons.power_settings_new), | icon: Icon(Icons.power_settings_new), | ||||
| color: Colors.grey, | color: Colors.grey, | ||||
| onPressed: () {}); | onPressed: () {}); | ||||
| } | } | ||||
| } | } | ||||
| return Container(); | |||||
| return IconButton( | |||||
| icon: Icon(Icons.power_settings_new), | |||||
| color: Colors.grey, | |||||
| onPressed: () {}); | |||||
| } else { | } else { | ||||
| return Container(); | |||||
| return IconButton( | |||||
| icon: Icon(Icons.power_settings_new), | |||||
| color: Colors.grey, | |||||
| onPressed: () {}); | |||||
| } | } | ||||
| }, | }, | ||||
| ); | ); | ||||
| } | } | ||||
| Widget widgetStatus(ItemDeviceVM item) { | Widget widgetStatus(ItemDeviceVM item) { | ||||
| var manualModeString = (item.mode != 1) ? ' - Điều khiển thủ công' : ''; | |||||
| if (item.status == "0") { | if (item.status == "0") { | ||||
| return Text( | |||||
| "Đang Tắt", | |||||
| style: TextStyle(color: Colors.black54, fontSize: 13), | |||||
| return RichText( | |||||
| text: TextSpan( | |||||
| text: 'Đang Tắt', | |||||
| style: TextStyle(color: Colors.black54, fontSize: 13), | |||||
| children: <TextSpan>[ | |||||
| TextSpan( | |||||
| text: manualModeString, | |||||
| style: TextStyle(color: Colors.black54, fontSize: 13)), | |||||
| ], | |||||
| ), | |||||
| ); | ); | ||||
| } else if (item.status == "1") { | } else if (item.status == "1") { | ||||
| return Text( | |||||
| "Đang Bật", | |||||
| style: TextStyle(color: Colors.green, fontSize: 13), | |||||
| return RichText( | |||||
| text: TextSpan( | |||||
| text: 'Đang Bật', | |||||
| style: TextStyle(color: Colors.green, fontSize: 13), | |||||
| children: <TextSpan>[ | |||||
| TextSpan( | |||||
| text: '$manualModeString', | |||||
| style: TextStyle(color: Colors.black54, fontSize: 13)), | |||||
| ], | |||||
| ), | |||||
| ); | ); | ||||
| } else { | } else { | ||||
| return Text( | return Text( | ||||
| var response = await client.put(urlTurnOff); | var response = await client.put(urlTurnOff); | ||||
| if (200 <= response.statusCode && response.statusCode < 299) { | if (200 <= response.statusCode && response.statusCode < 299) { | ||||
| BlocProvider.of<DeviceBloc>(_context).add(ControlDevice( | |||||
| LoadingDialog.hideLoadingDialog(_context); | |||||
| widget.deviceBloc.add(ControlDevice( | |||||
| currentDevices: currentDevices, updatedDeviceId: item.id)); | currentDevices: currentDevices, updatedDeviceId: item.id)); | ||||
| Utils.showSnackBarSuccess( | Utils.showSnackBarSuccess( | ||||
| message: 'Điều khiển thành công thiết bị ${item.name}'); | message: 'Điều khiển thành công thiết bị ${item.name}'); | ||||
| } | } | ||||
| } catch (error) { | } catch (error) { | ||||
| Utils.showSnackBarError( | |||||
| message: 'Điều khiển thiết bị ${item.name} thất bại'); | |||||
| LoadingDialog.hideLoadingDialog(_context); | |||||
| var errorMessage = AppException.handleError(error, | |||||
| customMessageError: | |||||
| "Thiết bị ${item.name} đã được $statusDialogView.\nTải lại để cập nhật trạng thái mới nhất"); | |||||
| Utils.showSnackBarError(message: errorMessage); | |||||
| } | } | ||||
| LoadingDialog.hideLoadingDialog(_context); | |||||
| }, | }, | ||||
| ); | ); | ||||
| CupertinoAlertDialog alert = CupertinoAlertDialog( | CupertinoAlertDialog alert = CupertinoAlertDialog( | ||||
| String name; | String name; | ||||
| String status; | String status; | ||||
| String location; | String location; | ||||
| num mode; | |||||
| ItemDeviceVM(this.id, this.name, this.status); | |||||
| ItemDeviceVM(this.id, this.name, this.status, this.location, this.mode); | |||||
| ItemDeviceVM.fromDevice(Device device) { | ItemDeviceVM.fromDevice(Device device) { | ||||
| this.device = device; | this.device = device; | ||||
| id = device.id; | id = device.id; | ||||
| name = device.name.toString(); | name = device.name.toString(); | ||||
| status = device.status; | status = device.status; | ||||
| location = device.location; | location = device.location; | ||||
| mode = device.mode; | |||||
| } | } | ||||
| } | } |