import 'dart:io';
import 'dart:math';

import 'package:PiliPlus/common/widgets/color_palette.dart';
import 'package:PiliPlus/common/widgets/custom_toast.dart';
import 'package:PiliPlus/common/widgets/dialog/dialog.dart';
import 'package:PiliPlus/common/widgets/image/network_img_layer.dart';
import 'package:PiliPlus/main.dart';
import 'package:PiliPlus/models/common/dynamic/dynamic_badge_mode.dart';
import 'package:PiliPlus/models/common/dynamic/up_panel_position.dart';
import 'package:PiliPlus/models/common/home_tab_type.dart';
import 'package:PiliPlus/models/common/msg/msg_unread_type.dart';
import 'package:PiliPlus/models/common/nav_bar_config.dart';
import 'package:PiliPlus/models/common/theme/theme_color_type.dart';
import 'package:PiliPlus/models/common/theme/theme_type.dart';
import 'package:PiliPlus/pages/main/controller.dart';
import 'package:PiliPlus/pages/mine/controller.dart';
import 'package:PiliPlus/pages/setting/models/model.dart';
import 'package:PiliPlus/pages/setting/pages/color_select.dart';
import 'package:PiliPlus/pages/setting/slide_color_picker.dart';
import 'package:PiliPlus/pages/setting/widgets/dual_slide_dialog.dart';
import 'package:PiliPlus/pages/setting/widgets/multi_select_dialog.dart';
import 'package:PiliPlus/pages/setting/widgets/select_dialog.dart';
import 'package:PiliPlus/pages/setting/widgets/slide_dialog.dart';
import 'package:PiliPlus/plugin/pl_player/utils/fullscreen.dart';
import 'package:PiliPlus/utils/extension/get_ext.dart';
import 'package:PiliPlus/utils/extension/num_ext.dart';
import 'package:PiliPlus/utils/extension/theme_ext.dart';
import 'package:PiliPlus/utils/global_data.dart';
import 'package:PiliPlus/utils/platform_utils.dart';
import 'package:PiliPlus/utils/storage.dart';
import 'package:PiliPlus/utils/storage_key.dart';
import 'package:PiliPlus/utils/storage_pref.dart';
import 'package:auto_orientation/auto_orientation.dart';
import 'package:flutter/material.dart' hide StatefulBuilder;
import 'package:flutter/services.dart';
import 'package:flutter_smart_dialog/flutter_smart_dialog.dart';
import 'package:get/get.dart';
import 'package:material_design_icons_flutter/material_design_icons_flutter.dart';

List<SettingsModel> get styleSettings => [
  if (PlatformUtils.isDesktop) ...[
    const SwitchModel(
      title: '显示窗口标题栏',
      leading: Icon(Icons.window),
      setKey: SettingBoxKey.showWindowTitleBar,
      defaultVal: true,
      needReboot: true,
    ),
    const SwitchModel(
      title: '显示托盘图标',
      leading: Icon(Icons.donut_large_rounded),
      setKey: SettingBoxKey.showTrayIcon,
      defaultVal: true,
      needReboot: true,
    ),
  ],
  NormalModel(
    title: '界面缩放',
    getSubtitle: () => '当前缩放比例：${Pref.uiScale.toStringAsFixed(2)}',
    leading: const Icon(Icons.zoom_in_outlined),
    onTap: _showUiScaleDialog,
  ),
  SwitchModel(
    title: '横屏适配',
    subtitle: '启用横屏布局与逻辑，平板、折叠屏等可开启；建议全屏方向设为【不改变当前方向】',
    leading: const Icon(Icons.phonelink_outlined),
    setKey: SettingBoxKey.horizontalScreen,
    defaultVal: Pref.horizontalScreen,
    onChanged: (value) {
      if (value) {
        autoScreen();
      } else {
        AutoOrientation.portraitUpMode();
      }
    },
  ),
  const SwitchModel(
    title: '改用侧边栏',
    subtitle: '开启后底栏与顶栏被替换，且相关设置失效',
    leading: Icon(Icons.chrome_reader_mode_outlined),
    setKey: SettingBoxKey.useSideBar,
    defaultVal: false,
    needReboot: true,
  ),
  SwitchModel(
    title: 'App字体字重',
    subtitle: '点击设置',
    setKey: SettingBoxKey.appFontWeight,
    defaultVal: false,
    onTap: (context) {
      showDialog<double>(
        context: context,
        builder: (context) {
          return SlideDialog(
            title: 'App字体字重',
            value: Pref.appFontWeight.toDouble() + 1,
            min: 1,
            max: FontWeight.values.length.toDouble(),
            divisions: FontWeight.values.length - 1,
          );
        },
      ).then((res) async {
        if (res != null) {
          await GStorage.setting.put(
            SettingBoxKey.appFontWeight,
            res.toInt() - 1,
          );
          Get.forceAppUpdate();
        }
      });
    },
    leading: const Icon(Icons.text_fields),
    onChanged: (value) {
      Get.forceAppUpdate();
    },
  ),
  NormalModel(
    title: '页面过渡动画',
    leading: const Icon(Icons.animation),
    getSubtitle: () => '当前：${Pref.pageTransition.name}',
    onTap: (context, setState) async {
      final result = await showDialog<Transition>(
        context: context,
        builder: (context) {
          return SelectDialog<Transition>(
            title: '页面过渡动画',
            value: Pref.pageTransition,
            values: Transition.values.map((e) => (e, e.name)).toList(),
          );
        },
      );
      if (result != null) {
        await GStorage.setting.put(SettingBoxKey.pageTransition, result.index);
        SmartDialog.showToast('重启生效');
        setState();
      }
    },
  ),
  const SwitchModel(
    title: '优化平板导航栏',
    leading: Icon(MdiIcons.soundbar),
    setKey: SettingBoxKey.optTabletNav,
    defaultVal: true,
    needReboot: true,
  ),
  const SwitchModel(
    title: 'MD3样式底栏',
    subtitle: 'Material You设计规范底栏，关闭可变窄',
    leading: Icon(Icons.design_services_outlined),
    setKey: SettingBoxKey.enableMYBar,
    defaultVal: true,
    needReboot: true,
  ),
  NormalModel(
    onTap: (context, setState) async {
      final result = await showDialog<(double, double)>(
        context: context,
        builder: (context) {
          return DualSlideDialog(
            title: '列表最大列宽度（默认240dp）',
            value1: Pref.recommendCardWidth,
            value2: Pref.smallCardWidth,
            description1: '主页推荐流',
            description2: '其他',
            min: 150.0,
            max: 500.0,
            divisions: 35,
            suffix: 'dp',
          );
        },
      );
      if (result != null) {
        await GStorage.setting.putAll({
          SettingBoxKey.recommendCardWidth: result.$1,
          SettingBoxKey.smallCardWidth: result.$2,
        });
        SmartDialog.showToast('重启生效');
        setState();
      }
    },
    leading: const Icon(Icons.calendar_view_week_outlined),
    title: '列表宽度（dp）限制',
    getSubtitle: () =>
        '当前: 主页${Pref.recommendCardWidth.toInt()}dp 其他${Pref.smallCardWidth.toInt()}dp，屏幕宽度:${MediaQuery.widthOf(Get.context!).toPrecision(2)}dp。宽度越小列数越多。',
  ),
  SwitchModel(
    title: '视频播放页使用深色主题',
    leading: const Icon(Icons.dark_mode_outlined),
    setKey: SettingBoxKey.darkVideoPage,
    defaultVal: false,
    onChanged: (value) {
      if (value && MyApp.darkThemeData == null) {
        Get.forceAppUpdate();
      }
    },
  ),
  const SwitchModel(
    title: '动态页启用瀑布流',
    subtitle: '关闭会显示为单列',
    leading: Icon(Icons.view_array_outlined),
    setKey: SettingBoxKey.dynamicsWaterfallFlow,
    defaultVal: true,
    needReboot: true,
  ),
  NormalModel(
    title: '动态页UP主显示位置',
    leading: const Icon(Icons.person_outlined),
    getSubtitle: () => '当前：${Pref.upPanelPosition.label}',
    onTap: (context, setState) async {
      final result = await showDialog<UpPanelPosition>(
        context: context,
        builder: (context) {
          return SelectDialog<UpPanelPosition>(
            title: '动态页UP主显示位置',
            value: Pref.upPanelPosition,
            values: UpPanelPosition.values.map((e) => (e, e.label)).toList(),
          );
        },
      );
      if (result != null) {
        await GStorage.setting.put(SettingBoxKey.upPanelPosition, result.index);
        SmartDialog.showToast('重启生效');
        setState();
      }
    },
  ),
  const SwitchModel(
    title: '动态页显示所有已关注UP主',
    leading: Icon(Icons.people_alt_outlined),
    setKey: SettingBoxKey.dynamicsShowAllFollowedUp,
    defaultVal: false,
    needReboot: true,
  ),
  const SwitchModel(
    title: '动态页展开正在直播UP列表',
    leading: Icon(Icons.live_tv),
    setKey: SettingBoxKey.expandDynLivePanel,
    defaultVal: false,
    needReboot: true,
  ),
  NormalModel(
    onTap: (context, setState) async {
      final result = await showDialog<DynamicBadgeMode>(
        context: context,
        builder: (context) {
          return SelectDialog<DynamicBadgeMode>(
            title: '动态未读标记',
            value: Pref.dynamicBadgeType,
            values: DynamicBadgeMode.values.map((e) => (e, e.desc)).toList(),
          );
        },
      );
      if (result != null) {
        final mainController = Get.find<MainController>()
          ..dynamicBadgeMode = DynamicBadgeMode.values[result.index];
        if (mainController.dynamicBadgeMode != DynamicBadgeMode.hidden) {
          mainController.getUnreadDynamic();
        }
        await GStorage.setting.put(
          SettingBoxKey.dynamicBadgeMode,
          result.index,
        );
        SmartDialog.showToast('设置成功');
        setState();
      }
    },
    title: '动态未读标记',
    leading: const Icon(Icons.motion_photos_on_outlined),
    getSubtitle: () => '当前标记样式：${Pref.dynamicBadgeType.desc}',
  ),
  NormalModel(
    onTap: (context, setState) async {
      final result = await showDialog<DynamicBadgeMode>(
        context: context,
        builder: (context) {
          return SelectDialog<DynamicBadgeMode>(
            title: '消息未读标记',
            value: Pref.msgBadgeMode,
            values: DynamicBadgeMode.values.map((e) => (e, e.desc)).toList(),
          );
        },
      );
      if (result != null) {
        final mainController = Get.find<MainController>()
          ..msgBadgeMode = DynamicBadgeMode.values[result.index];
        if (mainController.msgBadgeMode != DynamicBadgeMode.hidden) {
          mainController.queryUnreadMsg(true);
        } else {
          mainController.msgUnReadCount.value = '';
        }
        await GStorage.setting.put(SettingBoxKey.msgBadgeMode, result.index);
        SmartDialog.showToast('设置成功');
        setState();
      }
    },
    title: '消息未读标记',
    leading: const Icon(MdiIcons.bellBadgeOutline),
    getSubtitle: () => '当前标记样式：${Pref.msgBadgeMode.desc}',
  ),
  NormalModel(
    onTap: (context, setState) async {
      final result = await showDialog<Set<MsgUnReadType>>(
        context: context,
        builder: (context) {
          return MultiSelectDialog<MsgUnReadType>(
            title: '消息未读类型',
            initValues: Pref.msgUnReadTypeV2,
            values: {for (final i in MsgUnReadType.values) i: i.title},
          );
        },
      );
      if (result != null) {
        final mainController = Get.find<MainController>()
          ..msgUnReadTypes = result;
        if (mainController.msgBadgeMode != DynamicBadgeMode.hidden) {
          mainController.queryUnreadMsg();
        }
        await GStorage.setting.put(
          SettingBoxKey.msgUnReadTypeV2,
          result.map((item) => item.index).toList()..sort(),
        );
        SmartDialog.showToast('设置成功');
        setState();
      }
    },
    title: '消息未读类型',
    leading: const Icon(MdiIcons.bellCogOutline),
    getSubtitle: () =>
        '当前消息类型：${Pref.msgUnReadTypeV2.map((item) => item.title).join('、')}',
  ),
  const SwitchModel(
    title: '首页顶栏收起',
    subtitle: '首页列表滑动时，收起顶栏',
    leading: Icon(Icons.vertical_align_top_outlined),
    setKey: SettingBoxKey.hideSearchBar,
    defaultVal: true,
    needReboot: true,
  ),
  const SwitchModel(
    title: '首页底栏收起',
    subtitle: '首页列表滑动时，收起底栏',
    leading: Icon(Icons.vertical_align_bottom_outlined),
    setKey: SettingBoxKey.hideTabBar,
    defaultVal: true,
    needReboot: true,
  ),
  SwitchModel(
    title: '顶/底栏滚动阈值',
    subtitle: '滚动多少像素后收起/展开顶底栏，默认50像素',
    leading: const Icon(Icons.swipe_vertical),
    defaultVal: false,
    setKey: SettingBoxKey.enableScrollThreshold,
    needReboot: true,
    onTap: (context) {
      String scrollThreshold = Pref.scrollThreshold.toString();
      showDialog(
        context: context,
        builder: (context) {
          return AlertDialog(
            title: const Text('滚动阈值'),
            content: TextFormField(
              autofocus: true,
              initialValue: scrollThreshold,
              keyboardType: const TextInputType.numberWithOptions(
                decimal: true,
              ),
              onChanged: (value) {
                scrollThreshold = value;
              },
              inputFormatters: [
                FilteringTextInputFormatter.allow(RegExp(r'[\d\.]+')),
              ],
              decoration: const InputDecoration(suffixText: 'px'),
            ),
            actions: [
              TextButton(
                onPressed: Get.back,
                child: Text(
                  '取消',
                  style: TextStyle(
                    color: Theme.of(context).colorScheme.outline,
                  ),
                ),
              ),
              TextButton(
                onPressed: () {
                  Get.back();
                  GStorage.setting.put(
                    SettingBoxKey.scrollThreshold,
                    max(
                      10.0,
                      double.tryParse(scrollThreshold) ?? 50.0,
                    ),
                  );
                  SmartDialog.showToast('重启生效');
                },
                child: const Text('确定'),
              ),
            ],
          );
        },
      );
    },
  ),
  NormalModel(
    onTap: (context, setState) {
      _showQualityDialog(
        context: context,
        title: '图片质量',
        initValue: Pref.picQuality,
        onChanged: (picQuality) async {
          GlobalData().imgQuality = picQuality;
          await GStorage.setting.put(SettingBoxKey.defaultPicQa, picQuality);
          setState();
        },
      );
    },
    title: '图片质量',
    subtitle: '选择合适的图片清晰度，上限100%',
    leading: const Icon(Icons.image_outlined),
    getTrailing: () => Padding(
      padding: const EdgeInsets.symmetric(horizontal: 8.0),
      child: Text(
        '${Pref.picQuality}%',
        style: Get.theme.textTheme.titleSmall,
      ),
    ),
  ),
  // preview quality
  NormalModel(
    onTap: (context, setState) {
      _showQualityDialog(
        context: context,
        title: '查看大图质量',
        initValue: Pref.previewQ,
        onChanged: (picQuality) async {
          await GStorage.setting.put(SettingBoxKey.previewQuality, picQuality);
          setState();
        },
      );
    },
    title: '查看大图质量',
    subtitle: '选择合适的图片清晰度，上限100%',
    leading: const Icon(Icons.image_outlined),
    getTrailing: () => Padding(
      padding: const EdgeInsets.symmetric(horizontal: 8.0),
      child: Text(
        '${Pref.previewQ}%',
        style: Get.theme.textTheme.titleSmall,
      ),
    ),
  ),
  NormalModel(
    onTap: (context, setState) {
      final reduceLuxColor = Pref.reduceLuxColor;
      showDialog(
        context: context,
        builder: (context) => AlertDialog(
          clipBehavior: Clip.hardEdge,
          contentPadding: const EdgeInsets.symmetric(vertical: 16),
          title: const Text('Color Picker'),
          content: SlideColorPicker(
            color: reduceLuxColor ?? Colors.white,
            onChanged: (Color? color) {
              if (color != null && color != reduceLuxColor) {
                if (color == Colors.white) {
                  NetworkImgLayer.reduceLuxColor = null;
                  GStorage.setting.delete(SettingBoxKey.reduceLuxColor);
                  SmartDialog.showToast('设置成功');
                  setState();
                } else {
                  void onConfirm() {
                    NetworkImgLayer.reduceLuxColor = color;
                    GStorage.setting.put(
                      SettingBoxKey.reduceLuxColor,
                      color.toARGB32(),
                    );
                    SmartDialog.showToast('设置成功');
                    setState();
                  }

                  if (color.computeLuminance() < 0.2) {
                    showConfirmDialog(
                      context: context,
                      title:
                          '确认使用#${(color.toARGB32() & 0xFFFFFF).toRadixString(16).toUpperCase().padLeft(6)}？',
                      content: '所选颜色过于昏暗，可能会影响图片观看',
                      onConfirm: onConfirm,
                    );
                  } else {
                    onConfirm();
                  }
                }
              }
            },
          ),
        ),
      );
    },
    title: '深色下图片颜色叠加',
    subtitle: '显示颜色=图片原色x所选颜色，大图查看不受影响',
    leading: const Icon(Icons.format_color_fill_outlined),
    getTrailing: () => Container(
      padding: const EdgeInsets.only(right: 8.0),
      width: 20,
      height: 20,
      decoration: BoxDecoration(
        color: Pref.reduceLuxColor ?? Colors.white,
        shape: BoxShape.circle,
      ),
    ),
  ),
  NormalModel(
    onTap: (context, setState) async {
      final result = await showDialog<double>(
        context: context,
        builder: (context) {
          return SlideDialog(
            title: 'Toast不透明度',
            value: CustomToast.toastOpacity,
            min: 0.0,
            max: 1.0,
            divisions: 10,
          );
        },
      );
      if (result != null) {
        CustomToast.toastOpacity = result;
        await GStorage.setting.put(SettingBoxKey.defaultToastOp, result);
        SmartDialog.showToast('设置成功');
        setState();
      }
    },
    leading: const Icon(Icons.opacity_outlined),
    title: '气泡提示不透明度',
    subtitle: '自定义气泡提示(Toast)不透明度',
    getTrailing: () => Padding(
      padding: const EdgeInsets.symmetric(horizontal: 8.0),
      child: Text(
        CustomToast.toastOpacity.toStringAsFixed(1),
        style: Get.theme.textTheme.titleSmall,
      ),
    ),
  ),
  NormalModel(
    onTap: (context, setState) async {
      final result = await showDialog<ThemeType>(
        context: context,
        builder: (context) {
          return SelectDialog<ThemeType>(
            title: '主题模式',
            value: Pref.themeType,
            values: ThemeType.values.map((e) => (e, e.desc)).toList(),
          );
        },
      );
      if (result != null) {
        try {
          Get.find<MineController>().themeType.value = result;
        } catch (_) {}
        GStorage.setting.put(SettingBoxKey.themeMode, result.index);
        Get.putOrFind(ColorSelectController.new).themeType.value = result;
        Get.changeThemeMode(result.toThemeMode);
        setState();
      }
    },
    leading: const Icon(Icons.flashlight_on_outlined),
    title: '主题模式',
    getSubtitle: () => '当前模式：${Pref.themeType.desc}',
  ),
  SwitchModel(
    leading: const Icon(Icons.invert_colors),
    title: '纯黑主题',
    setKey: SettingBoxKey.isPureBlackTheme,
    defaultVal: false,
    onChanged: (value) {
      if (Get.isDarkMode || Pref.darkVideoPage) {
        Get.forceAppUpdate();
      }
    },
  ),
  NormalModel(
    onTap: (context, setState) => Get.toNamed('/colorSetting'),
    leading: const Icon(Icons.color_lens_outlined),
    title: '应用主题',
    getSubtitle: () => '当前主题：${Pref.dynamicColor ? '动态取色' : '指定颜色'}',
    getTrailing: () => Pref.dynamicColor
        ? Icon(Icons.color_lens_rounded, color: Get.theme.colorScheme.primary)
        : SizedBox.square(
            dimension: 32,
            child: ColorPalette(
              colorScheme: colorThemeTypes[Pref.customColor].color
                  .asColorSchemeSeed(Pref.schemeVariant, Get.theme.brightness),
              selected: false,
              showBgColor: false,
            ),
          ),
  ),
  NormalModel(
    onTap: (context, setState) async {
      final result = await showDialog<NavigationBarType>(
        context: context,
        builder: (context) {
          return SelectDialog<NavigationBarType>(
            title: '首页启动页',
            value: Pref.defaultHomePage,
            values: NavigationBarType.values.map((e) => (e, e.label)).toList(),
          );
        },
      );
      if (result != null) {
        await GStorage.setting.put(SettingBoxKey.defaultHomePage, result.index);
        SmartDialog.showToast('设置成功，重启生效');
        setState();
      }
    },
    leading: const Icon(Icons.home_outlined),
    title: '默认启动页',
    getSubtitle: () => '当前启动页：${Pref.defaultHomePage.label}',
  ),
  NormalModel(
    title: '滑动动画弹簧参数',
    leading: const Icon(Icons.chrome_reader_mode_outlined),
    onTap: (context, setState) {
      final List<String> springDescription = Pref.springDescription
          .map((i) => i.toString())
          .toList();
      showDialog(
        context: context,
        builder: (context) {
          return AlertDialog(
            title: const Text('弹簧参数'),
            content: Column(
              mainAxisSize: MainAxisSize.min,
              children: List.generate(
                3,
                (index) => TextFormField(
                  autofocus: index == 0,
                  initialValue: springDescription[index],
                  keyboardType: const TextInputType.numberWithOptions(
                    decimal: true,
                  ),
                  onChanged: (value) => springDescription[index] = value,
                  inputFormatters: [
                    FilteringTextInputFormatter.allow(RegExp(r'[\d\.]+')),
                  ],
                  decoration: InputDecoration(
                    labelText: const ['mass', 'stiffness', 'damping'][index],
                  ),
                ),
              ),
            ),
            actions: [
              TextButton(
                onPressed: () {
                  Get.back();
                  GStorage.setting.delete(SettingBoxKey.springDescription);
                  SmartDialog.showToast('重置成功，重启生效');
                },
                child: const Text('重置'),
              ),
              TextButton(
                onPressed: Get.back,
                child: Text(
                  '取消',
                  style: TextStyle(
                    color: Theme.of(context).colorScheme.outline,
                  ),
                ),
              ),
              TextButton(
                onPressed: () {
                  try {
                    final res = springDescription.map(double.parse).toList();
                    Get.back();
                    GStorage.setting.put(SettingBoxKey.springDescription, res);
                    SmartDialog.showToast('设置成功，重启生效');
                  } catch (e) {
                    SmartDialog.showToast(e.toString());
                  }
                },
                child: const Text('确定'),
              ),
            ],
          );
        },
      );
    },
  ),
  NormalModel(
    onTap: (context, setState) async {
      final result = await Get.toNamed('/fontSizeSetting');
      if (result != null) {
        Get.putOrFind(ColorSelectController.new).currentTextScale.value =
            result;
      }
    },
    title: '字体大小',
    leading: const Icon(Icons.format_size_outlined),
    getSubtitle: () =>
        Get.putOrFind(ColorSelectController.new).currentTextScale.value == 1.0
        ? '默认'
        : Get.putOrFind(
            ColorSelectController.new,
          ).currentTextScale.value.toString(),
  ),
  NormalModel(
    onTap: (context, setState) => Get.toNamed(
      '/barSetting',
      arguments: {
        'key': SettingBoxKey.tabBarSort,
        'defaultBars': HomeTabType.values,
        'title': '首页标签页',
      },
    ),
    title: '首页标签页',
    subtitle: '删除或调换首页标签页',
    leading: const Icon(Icons.toc_outlined),
  ),
  NormalModel(
    onTap: (context, setState) => Get.toNamed(
      '/barSetting',
      arguments: {
        'key': SettingBoxKey.navBarSort,
        'defaultBars': NavigationBarType.values,
        'title': 'Navbar',
      },
    ),
    title: 'Navbar编辑',
    subtitle: '删除或调换Navbar',
    leading: const Icon(Icons.toc_outlined),
  ),
  SwitchModel(
    title: '返回时直接退出',
    subtitle: '开启后在主页任意tab按返回键都直接退出，关闭则先回到Navbar的第一个tab',
    leading: const Icon(Icons.exit_to_app_outlined),
    setKey: SettingBoxKey.directExitOnBack,
    defaultVal: false,
    onChanged: (value) {
      Get.find<MainController>().directExitOnBack = value;
    },
  ),
  if (Platform.isAndroid)
    NormalModel(
      onTap: (context, setState) => Get.toNamed('/displayModeSetting'),
      title: '屏幕帧率',
      leading: const Icon(Icons.autofps_select_outlined),
    ),
];

void _showQualityDialog({
  required BuildContext context,
  required String title,
  required int initValue,
  required ValueChanged<int> onChanged,
}) {
  showDialog<double>(
    context: context,
    builder: (context) => SlideDialog(
      value: initValue.toDouble(),
      title: title,
      min: 10,
      max: 100,
      divisions: 9,
      suffix: '%',
      precise: 0,
    ),
  ).then((result) {
    if (result != null) {
      SmartDialog.showToast('设置成功');
      onChanged(result.toInt());
    }
  });
}

Future<void> _showUiScaleDialog(
  BuildContext context,
  VoidCallback setState,
) async {
  const minUiScale = 0.5;
  const maxUiScale = 2.0;

  final result = await showDialog<double>(
    context: context,
    builder: (context) {
      return SlideDialog(
        value: Pref.uiScale,
        title: '界面缩放比例',
        min: minUiScale,
        max: maxUiScale,
        divisions: ((maxUiScale - minUiScale) * 20).toInt(),
        precise: 2,
        defVal: 1,
      );
    },
  );

  if (result != null) {
    if (result.isNaN) {
      Pref.uiScale = 1.0;
      await GStorage.setting.delete(SettingBoxKey.uiScale);
    } else {
      Pref.uiScale = result;
      await GStorage.setting.put(SettingBoxKey.uiScale, result);
    }
    Get.appUpdate();
  }
}
