import 'dart:async'; import 'dart:convert'; import 'package:flutter/material.dart'; import 'package:flutter_hbb/common/widgets/setting_widgets.dart'; import 'package:flutter_hbb/common/widgets/toolbar.dart'; import 'package:get/get.dart'; import '../../common.dart'; import '../../models/platform_model.dart'; void _showSuccess() { showToast(translate("Successful")); } void setTemporaryPasswordLengthDialog( OverlayDialogManager dialogManager) async { List lengths = ['6', '8', '10']; String length = await bind.mainGetOption(key: "temporary-password-length"); var index = lengths.indexOf(length); if (index < 0) index = 0; length = lengths[index]; dialogManager.show((setState, close, context) { setLength(newValue) { final oldValue = length; if (oldValue == newValue) return; setState(() { length = newValue; }); bind.mainSetOption(key: "temporary-password-length", value: newValue); bind.mainUpdateTemporaryPassword(); Future.delayed(Duration(milliseconds: 200), () { close(); _showSuccess(); }); } return CustomAlertDialog( title: Text(translate("Set one-time password length")), content: Row( mainAxisAlignment: MainAxisAlignment.spaceEvenly, children: lengths .map( (value) => Row( children: [ Text(value), Radio( value: value, groupValue: length, onChanged: setLength), ], ), ) .toList()), ); }, backDismiss: true, clickMaskDismiss: true); } void showServerSettings(OverlayDialogManager dialogManager, void Function(VoidCallback) setState) async { Map options = {}; try { options = jsonDecode(await bind.mainGetOptions()); } catch (e) { print("Invalid server config: $e"); } showServerSettingsWithValue( ServerConfig.fromOptions(options), dialogManager, setState); } void showServerSettingsWithValue( ServerConfig serverConfig, OverlayDialogManager dialogManager, void Function(VoidCallback)? upSetState) async { var isInProgress = false; final idCtrl = TextEditingController(text: serverConfig.idServer); final relayCtrl = TextEditingController(text: serverConfig.relayServer); final apiCtrl = TextEditingController(text: serverConfig.apiServer); final keyCtrl = TextEditingController(text: serverConfig.key); RxString idServerMsg = ''.obs; RxString relayServerMsg = ''.obs; RxString apiServerMsg = ''.obs; final controllers = [idCtrl, relayCtrl, apiCtrl, keyCtrl]; final errMsgs = [ idServerMsg, relayServerMsg, apiServerMsg, ]; dialogManager.show((setState, close, context) { Future submit() async { setState(() { isInProgress = true; }); bool ret = await setServerConfig( null, errMsgs, ServerConfig( idServer: idCtrl.text.trim(), relayServer: relayCtrl.text.trim(), apiServer: apiCtrl.text.trim(), key: keyCtrl.text.trim())); setState(() { isInProgress = false; }); return ret; } Widget buildField( String label, TextEditingController controller, String errorMsg, {String? Function(String?)? validator, bool autofocus = false}) { if (isDesktop || isWeb) { return Row( children: [ SizedBox( width: 120, child: Text(label), ), SizedBox(width: 8), Expanded( child: TextFormField( controller: controller, decoration: InputDecoration( errorText: errorMsg.isEmpty ? null : errorMsg, contentPadding: EdgeInsets.symmetric(horizontal: 8, vertical: 12), ), validator: validator, autofocus: autofocus, ).workaroundFreezeLinuxMint(), ), ], ); } return TextFormField( controller: controller, decoration: InputDecoration( labelText: label, errorText: errorMsg.isEmpty ? null : errorMsg, ), validator: validator, ).workaroundFreezeLinuxMint(); } return CustomAlertDialog( title: Row( children: [ Expanded(child: Text(translate('ID/Relay Server'))), ...ServerConfigImportExportWidgets(controllers, errMsgs), ], ), content: ConstrainedBox( constraints: const BoxConstraints(minWidth: 500), child: Form( child: Obx(() => Column( mainAxisSize: MainAxisSize.min, children: [ buildField(translate('ID Server'), idCtrl, idServerMsg.value, autofocus: true), SizedBox(height: 8), if (!isIOS && !isWeb) ...[ buildField(translate('Relay Server'), relayCtrl, relayServerMsg.value), SizedBox(height: 8), ], buildField( translate('API Server'), apiCtrl, apiServerMsg.value, validator: (v) { if (v != null && v.isNotEmpty) { if (!(v.startsWith('http://') || v.startsWith("https://"))) { return translate("invalid_http"); } } return null; }, ), SizedBox(height: 8), buildField('Key', keyCtrl, ''), if (isInProgress) Padding( padding: EdgeInsets.only(top: 8), child: LinearProgressIndicator(), ), ], )), ), ), actions: [ dialogButton('Cancel', onPressed: () { close(); }, isOutline: true), dialogButton( 'OK', onPressed: () async { if (await submit()) { close(); showToast(translate('Successful')); upSetState?.call(() {}); } else { showToast(translate('Failed')); } }, ), ], ); }); } void setPrivacyModeDialog( OverlayDialogManager dialogManager, List privacyModeList, RxString privacyModeState, ) async { dialogManager.dismissAll(); dialogManager.show((setState, close, context) { return CustomAlertDialog( title: Text(translate('Privacy mode')), content: Column( mainAxisAlignment: MainAxisAlignment.spaceEvenly, children: privacyModeList .map((value) => CheckboxListTile( contentPadding: EdgeInsets.zero, visualDensity: VisualDensity.compact, title: value.child, value: value.value, onChanged: value.onChanged, )) .toList()), ); }, backDismiss: true, clickMaskDismiss: true); }