Change icons

This commit is contained in:
problematicconsumer
2024-02-15 15:23:02 +03:30
parent 97a308a351
commit 7e3442a310
25 changed files with 146 additions and 111 deletions

View File

@@ -0,0 +1,23 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart';
class AdaptiveIcon {
AdaptiveIcon(BuildContext context) : platform = Theme.of(context).platform;
final TargetPlatform platform;
IconData get more => switch (platform) {
TargetPlatform.iOS ||
TargetPlatform.macOS =>
FluentIcons.more_horizontal_24_regular,
_ => FluentIcons.more_vertical_24_regular,
};
IconData get share => switch (platform) {
TargetPlatform.android => FluentIcons.share_android_24_regular,
TargetPlatform.iOS ||
TargetPlatform.macOS =>
FluentIcons.share_ios_24_regular,
_ => FluentIcons.share_24_regular,
};
}

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_hooks/flutter_hooks.dart'; import 'package:flutter_hooks/flutter_hooks.dart';
import 'package:hiddify/utils/platform_utils.dart'; import 'package:hiddify/utils/platform_utils.dart';
@@ -120,7 +121,8 @@ class AdaptiveMenu extends HookConsumerWidget {
ListTile( ListTile(
title: Text(item.title), title: Text(item.title),
leading: item.icon != null ? Icon(item.icon) : null, leading: item.icon != null ? Icon(item.icon) : null,
trailing: const Icon(Icons.chevron_right), trailing:
const Icon(FluentIcons.chevron_right_20_regular, size: 20),
onTap: () { onTap: () {
pageIndexNotifier.value = subSheetIndex; pageIndexNotifier.value = subSheetIndex;
}, },

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
class TipCard extends StatelessWidget { class TipCard extends StatelessWidget {
@@ -16,7 +17,7 @@ class TipCard extends StatelessWidget {
children: [ children: [
const Padding( const Padding(
padding: EdgeInsets.all(8.0), padding: EdgeInsets.all(8.0),
child: Icon(Icons.lightbulb), child: Icon(FluentIcons.lightbulb_24_regular),
), ),
Expanded( Expanded(
child: Column( child: Column(

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:go_router/go_router.dart'; import 'package:go_router/go_router.dart';
@@ -12,7 +13,7 @@ Future<bool> showConfirmationDialog(
builder: (context) { builder: (context) {
final localizations = MaterialLocalizations.of(context); final localizations = MaterialLocalizations.of(context);
return AlertDialog( return AlertDialog(
icon: const Icon(Icons.delete_forever), icon: const Icon(FluentIcons.delete_24_regular),
title: Text(title), title: Text(title),
content: Text(message), content: Text(message),
actions: [ actions: [

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hiddify/core/analytics/analytics_controller.dart'; import 'package:hiddify/core/analytics/analytics_controller.dart';
import 'package:hiddify/core/localization/locale_extensions.dart'; import 'package:hiddify/core/localization/locale_extensions.dart';
@@ -19,7 +20,7 @@ class LocalePrefTile extends HookConsumerWidget {
return ListTile( return ListTile(
title: Text(t.settings.general.locale), title: Text(t.settings.general.locale),
subtitle: Text(locale.localeName), subtitle: Text(locale.localeName),
leading: const Icon(Icons.language), leading: const Icon(FluentIcons.local_language_24_regular),
onTap: () async { onTap: () async {
final selectedLocale = await showDialog<AppLocale>( final selectedLocale = await showDialog<AppLocale>(
context: context, context: context,
@@ -61,7 +62,7 @@ class RegionPrefTile extends HookConsumerWidget {
return ListTile( return ListTile(
title: Text(t.settings.general.region), title: Text(t.settings.general.region),
subtitle: Text(region.present(t)), subtitle: Text(region.present(t)),
leading: const Icon(Icons.my_location), leading: const Icon(FluentIcons.globe_location_24_regular),
onTap: () async { onTap: () async {
final selectedRegion = await showDialog<Region>( final selectedRegion = await showDialog<Region>(
context: context, context: context,
@@ -111,7 +112,7 @@ class EnableAnalyticsPrefTile extends HookConsumerWidget {
t.settings.general.enableAnalyticsMsg, t.settings.general.enableAnalyticsMsg,
style: Theme.of(context).textTheme.bodySmall, style: Theme.of(context).textTheme.bodySmall,
), ),
secondary: const Icon(Icons.bug_report), secondary: const Icon(FluentIcons.bug_24_regular),
value: enabled, value: enabled,
onChanged: (value) async { onChanged: (value) async {
if (onChanged != null) { if (onChanged != null) {

View File

@@ -1,4 +1,5 @@
import 'package:dartx/dartx.dart'; import 'package:dartx/dartx.dart';
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_hooks/flutter_hooks.dart'; import 'package:flutter_hooks/flutter_hooks.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
@@ -46,9 +47,15 @@ class QRCodeScannerScreen extends HookConsumerWidget with PresLogger {
builder: (context, state, child) { builder: (context, state, child) {
switch (state) { switch (state) {
case TorchState.off: case TorchState.off:
return const Icon(Icons.flash_off, color: Colors.grey); return const Icon(
FluentIcons.flash_off_24_regular,
color: Colors.grey,
);
case TorchState.on: case TorchState.on:
return const Icon(Icons.flash_on, color: Colors.yellow); return const Icon(
FluentIcons.flash_24_regular,
color: Colors.yellow,
);
} }
}, },
), ),
@@ -56,17 +63,7 @@ class QRCodeScannerScreen extends HookConsumerWidget with PresLogger {
onPressed: () => controller.toggleTorch(), onPressed: () => controller.toggleTorch(),
), ),
IconButton( IconButton(
icon: ValueListenableBuilder( icon: const Icon(FluentIcons.camera_switch_24_regular),
valueListenable: controller.cameraFacingState,
builder: (context, state, child) {
switch (state) {
case CameraFacing.front:
return const Icon(Icons.camera_front);
case CameraFacing.back:
return const Icon(Icons.camera_rear);
}
},
),
tooltip: t.profile.add.qrScanner.facingSemanticLabel, tooltip: t.profile.add.qrScanner.facingSemanticLabel,
onPressed: () => controller.switchCamera(), onPressed: () => controller.switchCamera(),
), ),
@@ -103,7 +100,10 @@ class QRCodeScannerScreen extends HookConsumerWidget with PresLogger {
children: [ children: [
const Padding( const Padding(
padding: EdgeInsets.only(bottom: 8), padding: EdgeInsets.only(bottom: 8),
child: Icon(Icons.error, color: Colors.white), child: Icon(
FluentIcons.error_circle_24_regular,
color: Colors.white,
),
), ),
Text(message), Text(message),
Text(error.errorDetails?.message ?? ''), Text(error.errorDetails?.message ?? ''),

View File

@@ -1,10 +1,12 @@
import 'package:dartx/dartx.dart'; import 'package:dartx/dartx.dart';
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter/services.dart'; import 'package:flutter/services.dart';
import 'package:gap/gap.dart'; import 'package:gap/gap.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/model/failures.dart'; import 'package:hiddify/core/model/failures.dart';
import 'package:hiddify/core/model/range.dart'; import 'package:hiddify/core/model/range.dart';
import 'package:hiddify/core/widget/adaptive_icon.dart';
import 'package:hiddify/core/widget/tip_card.dart'; import 'package:hiddify/core/widget/tip_card.dart';
import 'package:hiddify/features/common/nested_app_bar.dart'; import 'package:hiddify/features/common/nested_app_bar.dart';
import 'package:hiddify/features/config_option/model/config_option_entity.dart'; import 'package:hiddify/features/config_option/model/config_option_entity.dart';
@@ -45,6 +47,7 @@ class ConfigOptionsPage extends HookConsumerWidget {
actions: [ actions: [
if (asyncOptions case AsyncData(value: final options)) if (asyncOptions case AsyncData(value: final options))
PopupMenuButton( PopupMenuButton(
icon: Icon(AdaptiveIcon(context).more),
itemBuilder: (context) { itemBuilder: (context) {
return [ return [
PopupMenuItem( PopupMenuItem(
@@ -483,7 +486,7 @@ class ConfigOptionsPage extends HookConsumerWidget {
child: Column( child: Column(
mainAxisAlignment: MainAxisAlignment.center, mainAxisAlignment: MainAxisAlignment.center,
children: [ children: [
const Icon(Icons.error), const Icon(FluentIcons.error_circle_24_regular),
const Gap(2), const Gap(2),
Text(t.presentShortError(error)), Text(t.presentShortError(error)),
const Gap(2), const Gap(2),

View File

@@ -1,6 +1,9 @@
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:gap/gap.dart'; import 'package:gap/gap.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/widget/adaptive_icon.dart';
import 'package:hiddify/core/widget/animated_visibility.dart';
import 'package:hiddify/core/widget/tip_card.dart';
import 'package:hiddify/features/geo_asset/overview/geo_assets_overview_notifier.dart'; import 'package:hiddify/features/geo_asset/overview/geo_assets_overview_notifier.dart';
import 'package:hiddify/features/geo_asset/widget/geo_asset_tile.dart'; import 'package:hiddify/features/geo_asset/widget/geo_asset_tile.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart';
@@ -22,6 +25,7 @@ class GeoAssetsOverviewPage extends HookConsumerWidget {
pinned: true, pinned: true,
actions: [ actions: [
PopupMenuButton( PopupMenuButton(
icon: Icon(AdaptiveIcon(context).more),
itemBuilder: (context) { itemBuilder: (context) {
return [ return [
PopupMenuItem( PopupMenuItem(
@@ -39,13 +43,13 @@ class GeoAssetsOverviewPage extends HookConsumerWidget {
), ),
if (state case AsyncData(value: (:final geoip, :final geosite))) if (state case AsyncData(value: (:final geoip, :final geosite)))
SliverPinnedHeader( SliverPinnedHeader(
child: AnimatedSwitcher( child: AnimatedVisibility(
duration: const Duration(milliseconds: 200), visible: (geoip + geosite)
child: (geoip + geosite)
.where((e) => e.$1.active && e.$2 == null) .where((e) => e.$1.active && e.$2 == null)
.isNotEmpty .isNotEmpty,
? const MissingRoutingAssetsCard() axis: Axis.vertical,
: const SizedBox(), child:
TipCard(message: t.settings.geoAssets.missingGeoAssetsMsg),
), ),
), ),
switch (state) { switch (state) {
@@ -96,39 +100,3 @@ class GeoAssetsOverviewPage extends HookConsumerWidget {
); );
} }
} }
class MissingRoutingAssetsCard extends HookConsumerWidget {
const MissingRoutingAssetsCard({super.key});
@override
Widget build(BuildContext context, WidgetRef ref) {
final t = ref.watch(translationsProvider);
return Card(
margin: const EdgeInsets.symmetric(
horizontal: 12,
vertical: 4,
),
child: Row(
children: [
const Padding(
padding: EdgeInsets.all(8.0),
child: Icon(Icons.lightbulb),
),
Expanded(
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
Padding(
padding:
const EdgeInsets.symmetric(horizontal: 8, vertical: 8),
child: Text(t.settings.geoAssets.missingGeoAssetsMsg),
),
],
),
),
],
),
);
}
}

View File

@@ -2,6 +2,7 @@ import 'package:dartx/dartx.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/model/failures.dart'; import 'package:hiddify/core/model/failures.dart';
import 'package:hiddify/core/widget/adaptive_icon.dart';
import 'package:hiddify/features/geo_asset/model/geo_asset_entity.dart'; import 'package:hiddify/features/geo_asset/model/geo_asset_entity.dart';
import 'package:hiddify/features/geo_asset/model/geo_asset_failure.dart'; import 'package:hiddify/features/geo_asset/model/geo_asset_failure.dart';
import 'package:hiddify/features/geo_asset/notifier/geo_asset_notifier.dart'; import 'package:hiddify/features/geo_asset/notifier/geo_asset_notifier.dart';
@@ -95,6 +96,7 @@ class GeoAssetTile extends HookConsumerWidget {
selected: geoAsset.active, selected: geoAsset.active,
onTap: onMarkAsActive, onTap: onMarkAsActive,
trailing: PopupMenuButton( trailing: PopupMenuButton(
icon: Icon(AdaptiveIcon(context).more),
itemBuilder: (context) { itemBuilder: (context) {
return [ return [
PopupMenuItem( PopupMenuItem(

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:gap/gap.dart'; import 'package:gap/gap.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
@@ -20,7 +21,7 @@ class EmptyProfilesHomeBody extends HookConsumerWidget {
const Gap(16), const Gap(16),
OutlinedButton.icon( OutlinedButton.icon(
onPressed: () => const AddProfileRoute().push(context), onPressed: () => const AddProfileRoute().push(context),
icon: const Icon(Icons.add), icon: const Icon(FluentIcons.add_24_regular),
label: Text(t.profile.add.buttonText), label: Text(t.profile.add.buttonText),
), ),
], ],

View File

@@ -1,6 +1,5 @@
import 'dart:io';
import 'package:dartx/dartx.dart'; import 'package:dartx/dartx.dart';
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hiddify/core/app_info/app_info_provider.dart'; import 'package:hiddify/core/app_info/app_info_provider.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
@@ -48,7 +47,7 @@ class HomePage extends HookConsumerWidget {
actions: [ actions: [
IconButton( IconButton(
onPressed: () => const AddProfileRoute().push(context), onPressed: () => const AddProfileRoute().push(context),
icon: const Icon(Icons.add_circle), icon: const Icon(FluentIcons.add_circle_24_filled),
tooltip: t.profile.add.buttonText, tooltip: t.profile.add.buttonText,
), ),
], ],

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_hooks/flutter_hooks.dart'; import 'package:flutter_hooks/flutter_hooks.dart';
import 'package:fpdart/fpdart.dart'; import 'package:fpdart/fpdart.dart';
@@ -5,6 +6,7 @@ import 'package:gap/gap.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/model/failures.dart'; import 'package:hiddify/core/model/failures.dart';
import 'package:hiddify/core/preferences/general_preferences.dart'; import 'package:hiddify/core/preferences/general_preferences.dart';
import 'package:hiddify/core/widget/adaptive_icon.dart';
import 'package:hiddify/features/common/nested_app_bar.dart'; import 'package:hiddify/features/common/nested_app_bar.dart';
import 'package:hiddify/features/log/data/log_data_providers.dart'; import 'package:hiddify/features/log/data/log_data_providers.dart';
import 'package:hiddify/features/log/model/log_level.dart'; import 'package:hiddify/features/log/model/log_level.dart';
@@ -65,22 +67,26 @@ class LogsOverviewPage extends HookConsumerWidget with PresLogger {
if (state.paused) if (state.paused)
IconButton( IconButton(
onPressed: notifier.resume, onPressed: notifier.resume,
icon: const Icon(Icons.play_arrow), icon: const Icon(FluentIcons.play_20_regular),
tooltip: t.logs.resumeTooltip, tooltip: t.logs.resumeTooltip,
iconSize: 20,
) )
else else
IconButton( IconButton(
onPressed: notifier.pause, onPressed: notifier.pause,
icon: const Icon(Icons.pause), icon: const Icon(FluentIcons.pause_20_regular),
tooltip: t.logs.pauseTooltip, tooltip: t.logs.pauseTooltip,
iconSize: 20,
), ),
IconButton( IconButton(
onPressed: notifier.clear, onPressed: notifier.clear,
icon: const Icon(Icons.clear_all), icon: const Icon(FluentIcons.delete_lines_20_regular),
tooltip: t.logs.clearTooltip, tooltip: t.logs.clearTooltip,
iconSize: 20,
), ),
if (popupButtons.isNotEmpty) if (popupButtons.isNotEmpty)
PopupMenuButton( PopupMenuButton(
icon: Icon(AdaptiveIcon(context).more),
itemBuilder: (context) { itemBuilder: (context) {
return popupButtons; return popupButtons;
}, },

View File

@@ -1,9 +1,11 @@
import 'package:dartx/dartx.dart'; import 'package:dartx/dartx.dart';
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_hooks/flutter_hooks.dart'; import 'package:flutter_hooks/flutter_hooks.dart';
import 'package:go_router/go_router.dart'; import 'package:go_router/go_router.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/preferences/general_preferences.dart'; import 'package:hiddify/core/preferences/general_preferences.dart';
import 'package:hiddify/core/widget/adaptive_icon.dart';
import 'package:hiddify/features/per_app_proxy/model/installed_package_info.dart'; import 'package:hiddify/features/per_app_proxy/model/installed_package_info.dart';
import 'package:hiddify/features/per_app_proxy/model/per_app_proxy_mode.dart'; import 'package:hiddify/features/per_app_proxy/model/per_app_proxy_mode.dart';
import 'package:hiddify/features/per_app_proxy/overview/per_app_proxy_notifier.dart'; import 'package:hiddify/features/per_app_proxy/overview/per_app_proxy_notifier.dart';
@@ -83,11 +85,12 @@ class PerAppProxyPage extends HookConsumerWidget with PresLogger {
title: Text(t.settings.network.perAppProxyPageTitle), title: Text(t.settings.network.perAppProxyPageTitle),
actions: [ actions: [
IconButton( IconButton(
icon: const Icon(Icons.search), icon: const Icon(FluentIcons.search_24_regular),
onPressed: () => isSearching.value = true, onPressed: () => isSearching.value = true,
tooltip: localizations.searchFieldLabel, tooltip: localizations.searchFieldLabel,
), ),
PopupMenuButton( PopupMenuButton(
icon: Icon(AdaptiveIcon(context).more),
itemBuilder: (context) { itemBuilder: (context) {
return [ return [
PopupMenuItem( PopupMenuItem(
@@ -179,7 +182,8 @@ class PerAppProxyPage extends HookConsumerWidget with PresLogger {
.watch(packageIconProvider(package.packageName)) .watch(packageIconProvider(package.packageName))
.when( .when(
data: (data) => Image(image: data), data: (data) => Image(image: data),
error: (error, _) => const Icon(Icons.error), error: (error, _) =>
const Icon(FluentIcons.error_circle_24_regular),
loading: () => const Center( loading: () => const Center(
child: CircularProgressIndicator(), child: CircularProgressIndicator(),
), ),

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter/services.dart'; import 'package:flutter/services.dart';
import 'package:flutter_hooks/flutter_hooks.dart'; import 'package:flutter_hooks/flutter_hooks.dart';
@@ -99,7 +100,7 @@ class AddProfileModal extends HookConsumerWidget {
_Button( _Button(
key: const ValueKey("add_from_clipboard_button"), key: const ValueKey("add_from_clipboard_button"),
label: t.profile.add.fromClipboard, label: t.profile.add.fromClipboard,
icon: Icons.content_paste, icon: FluentIcons.clipboard_paste_24_regular,
size: buttonWidth, size: buttonWidth,
onTap: () async { onTap: () async {
final captureResult = final captureResult =
@@ -116,7 +117,7 @@ class AddProfileModal extends HookConsumerWidget {
_Button( _Button(
key: const ValueKey("add_by_qr_code_button"), key: const ValueKey("add_by_qr_code_button"),
label: t.profile.add.scanQr, label: t.profile.add.scanQr,
icon: Icons.qr_code_scanner, icon: FluentIcons.qr_code_24_regular,
size: buttonWidth, size: buttonWidth,
onTap: () async { onTap: () async {
final captureResult = final captureResult =
@@ -133,7 +134,7 @@ class AddProfileModal extends HookConsumerWidget {
_Button( _Button(
key: const ValueKey("add_manually_button"), key: const ValueKey("add_manually_button"),
label: t.profile.add.manually, label: t.profile.add.manually,
icon: Icons.add, icon: FluentIcons.add_24_regular,
size: buttonWidth, size: buttonWidth,
onTap: () async { onTap: () async {
context.pop(); context.pop();
@@ -170,7 +171,7 @@ class AddProfileModal extends HookConsumerWidget {
mainAxisAlignment: MainAxisAlignment.center, mainAxisAlignment: MainAxisAlignment.center,
children: [ children: [
Icon( Icon(
Icons.add, FluentIcons.add_24_regular,
color: theme.colorScheme.primary, color: theme.colorScheme.primary,
), ),
const Gap(8), const Gap(8),

View File

@@ -1,8 +1,10 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:fpdart/fpdart.dart'; import 'package:fpdart/fpdart.dart';
import 'package:go_router/go_router.dart'; import 'package:go_router/go_router.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/model/failures.dart'; import 'package:hiddify/core/model/failures.dart';
import 'package:hiddify/core/widget/adaptive_icon.dart';
import 'package:hiddify/features/common/confirmation_dialogs.dart'; import 'package:hiddify/features/common/confirmation_dialogs.dart';
import 'package:hiddify/features/profile/details/profile_details_notifier.dart'; import 'package:hiddify/features/profile/details/profile_details_notifier.dart';
import 'package:hiddify/features/profile/model/profile_entity.dart'; import 'package:hiddify/features/profile/model/profile_entity.dart';
@@ -95,6 +97,7 @@ class ProfileDetailsPage extends HookConsumerWidget with PresLogger {
actions: [ actions: [
if (state.isEditing) if (state.isEditing)
PopupMenuButton( PopupMenuButton(
icon: Icon(AdaptiveIcon(context).more),
itemBuilder: (context) { itemBuilder: (context) {
return [ return [
if (state.profile case RemoteProfileEntity()) if (state.profile case RemoteProfileEntity())
@@ -175,7 +178,8 @@ class ProfileDetailsPage extends HookConsumerWidget with PresLogger {
) ?? ) ??
t.general.toggle.disabled, t.general.toggle.disabled,
), ),
leading: const Icon(Icons.update), leading:
const Icon(FluentIcons.arrow_sync_24_regular),
onTap: () async { onTap: () async {
final intervalInHours = final intervalInHours =
await SettingsInputDialog( await SettingsInputDialog(
@@ -185,7 +189,8 @@ class ProfileDetailsPage extends HookConsumerWidget with PresLogger {
optionalAction: ( optionalAction: (
t.general.state.disable, t.general.state.disable,
() => notifier.setField( () => notifier.setField(
updateInterval: none()), updateInterval: none(),
),
), ),
validator: isPort, validator: isPort,
mapTo: int.tryParse, mapTo: int.tryParse,

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
@@ -13,8 +14,8 @@ enum ProfilesSort {
} }
IconData get icon => switch (this) { IconData get icon => switch (this) {
lastUpdate => Icons.update, lastUpdate => FluentIcons.history_24_regular,
name => Icons.sort_by_alpha, name => FluentIcons.text_sort_ascending_24_regular,
}; };
} }

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:gap/gap.dart'; import 'package:gap/gap.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
@@ -79,7 +80,7 @@ class ProfilesOverviewModal extends HookConsumerWidget {
onPressed: () { onPressed: () {
const AddProfileRoute().push(context); const AddProfileRoute().push(context);
}, },
icon: const Icon(Icons.add), icon: const Icon(FluentIcons.add_24_filled),
label: Text(t.profile.add.shortBtnTxt), label: Text(t.profile.add.shortBtnTxt),
), ),
FilledButton.icon( FilledButton.icon(
@@ -91,7 +92,7 @@ class ProfilesOverviewModal extends HookConsumerWidget {
}, },
); );
}, },
icon: const Icon(Icons.sort), icon: const Icon(FluentIcons.arrow_sort_24_filled),
label: Text(t.general.sort), label: Text(t.general.sort),
), ),
FilledButton.icon( FilledButton.icon(
@@ -102,7 +103,7 @@ class ProfilesOverviewModal extends HookConsumerWidget {
) )
.trigger(); .trigger();
}, },
icon: const Icon(Icons.update), icon: const Icon(FluentIcons.arrow_sync_24_filled),
label: Text(t.profile.update.updateSubscriptions), label: Text(t.profile.update.updateSubscriptions),
), ),
], ],
@@ -159,7 +160,7 @@ class ProfilesSortModal extends HookConsumerWidget {
turns: arrowTurn, turns: arrowTurn,
duration: const Duration(milliseconds: 100), duration: const Duration(milliseconds: 100),
child: Icon( child: Icon(
Icons.arrow_upward, FluentIcons.arrow_sort_up_24_regular,
semanticLabel: sort.mode.name, semanticLabel: sort.mode.name,
), ),
), ),

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart'; import 'package:flutter/rendering.dart';
import 'package:flutter/services.dart'; import 'package:flutter/services.dart';
@@ -6,6 +7,7 @@ import 'package:go_router/go_router.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/model/failures.dart'; import 'package:hiddify/core/model/failures.dart';
import 'package:hiddify/core/router/router.dart'; import 'package:hiddify/core/router/router.dart';
import 'package:hiddify/core/widget/adaptive_icon.dart';
import 'package:hiddify/core/widget/adaptive_menu.dart'; import 'package:hiddify/core/widget/adaptive_menu.dart';
import 'package:hiddify/features/common/confirmation_dialogs.dart'; import 'package:hiddify/features/common/confirmation_dialogs.dart';
import 'package:hiddify/features/common/qr_code_dialog.dart'; import 'package:hiddify/features/common/qr_code_dialog.dart';
@@ -132,7 +134,10 @@ class ProfileTile extends HookConsumerWidget {
), ),
), ),
), ),
const Icon(Icons.arrow_drop_down), const Icon(
FluentIcons.caret_down_16_filled,
size: 16,
),
], ],
), ),
), ),
@@ -196,7 +201,7 @@ class ProfileActionButton extends HookConsumerWidget {
.read(updateProfileProvider(profile.id).notifier) .read(updateProfileProvider(profile.id).notifier)
.updateProfile(profile as RemoteProfileEntity); .updateProfile(profile as RemoteProfileEntity);
}, },
child: const Icon(Icons.update), child: const Icon(FluentIcons.arrow_sync_24_filled),
), ),
), ),
); );
@@ -210,7 +215,7 @@ class ProfileActionButton extends HookConsumerWidget {
message: MaterialLocalizations.of(context).showMenuTooltip, message: MaterialLocalizations.of(context).showMenuTooltip,
child: InkWell( child: InkWell(
onTap: toggleVisibility, onTap: toggleVisibility,
child: const Icon(Icons.more_vert), child: Icon(AdaptiveIcon(context).more),
), ),
), ),
); );
@@ -248,7 +253,7 @@ class ProfileActionsMenu extends HookConsumerWidget {
if (profile case RemoteProfileEntity()) if (profile case RemoteProfileEntity())
AdaptiveMenuItem( AdaptiveMenuItem(
title: t.profile.update.buttonTxt, title: t.profile.update.buttonTxt,
icon: Icons.update, icon: FluentIcons.arrow_sync_24_regular,
onTap: () { onTap: () {
if (ref.read(updateProfileProvider(profile.id)).isLoading) { if (ref.read(updateProfileProvider(profile.id)).isLoading) {
return; return;
@@ -260,7 +265,7 @@ class ProfileActionsMenu extends HookConsumerWidget {
), ),
AdaptiveMenuItem( AdaptiveMenuItem(
title: t.profile.share.buttonText, title: t.profile.share.buttonText,
icon: Icons.share, icon: AdaptiveIcon(context).share,
subItems: [ subItems: [
if (profile case RemoteProfileEntity(:final url, :final name)) ...[ if (profile case RemoteProfileEntity(:final url, :final name)) ...[
AdaptiveMenuItem( AdaptiveMenuItem(
@@ -305,14 +310,14 @@ class ProfileActionsMenu extends HookConsumerWidget {
], ],
), ),
AdaptiveMenuItem( AdaptiveMenuItem(
icon: Icons.edit, icon: FluentIcons.edit_24_regular,
title: t.profile.edit.buttonTxt, title: t.profile.edit.buttonTxt,
onTap: () async { onTap: () async {
await ProfileDetailsRoute(profile.id).push(context); await ProfileDetailsRoute(profile.id).push(context);
}, },
), ),
AdaptiveMenuItem( AdaptiveMenuItem(
icon: Icons.delete, icon: FluentIcons.delete_24_regular,
title: t.profile.delete.buttonTxt, title: t.profile.delete.buttonTxt,
onTap: () async { onTap: () async {
if (deleteProfileMutation.state.isInProgress) { if (deleteProfileMutation.state.isInProgress) {

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/model/failures.dart'; import 'package:hiddify/core/model/failures.dart';
@@ -29,7 +30,7 @@ class ProxiesOverviewPage extends HookConsumerWidget with PresLogger {
PopupMenuButton<ProxiesSort>( PopupMenuButton<ProxiesSort>(
initialValue: sortBy, initialValue: sortBy,
onSelected: ref.read(proxiesSortNotifierProvider.notifier).update, onSelected: ref.read(proxiesSortNotifierProvider.notifier).update,
icon: const Icon(Icons.sort), icon: const Icon(FluentIcons.arrow_sort_24_regular),
tooltip: t.proxies.sortTooltip, tooltip: t.proxies.sortTooltip,
itemBuilder: (context) { itemBuilder: (context) {
return [ return [
@@ -131,7 +132,7 @@ class ProxiesOverviewPage extends HookConsumerWidget with PresLogger {
floatingActionButton: FloatingActionButton( floatingActionButton: FloatingActionButton(
onPressed: () async => notifier.urlTest(group.tag), onPressed: () async => notifier.urlTest(group.tag),
tooltip: t.proxies.delayTestTooltip, tooltip: t.proxies.delayTestTooltip,
child: const Icon(Icons.bolt), child: const Icon(FluentIcons.flash_24_filled),
), ),
); );

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter/services.dart'; import 'package:flutter/services.dart';
import 'package:gap/gap.dart'; import 'package:gap/gap.dart';
@@ -6,6 +7,7 @@ import 'package:hiddify/core/directories/directories_provider.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/model/constants.dart'; import 'package:hiddify/core/model/constants.dart';
import 'package:hiddify/core/model/failures.dart'; import 'package:hiddify/core/model/failures.dart';
import 'package:hiddify/core/widget/adaptive_icon.dart';
import 'package:hiddify/features/app_update/notifier/app_update_notifier.dart'; import 'package:hiddify/features/app_update/notifier/app_update_notifier.dart';
import 'package:hiddify/features/app_update/notifier/app_update_state.dart'; import 'package:hiddify/features/app_update/notifier/app_update_state.dart';
import 'package:hiddify/features/app_update/widget/new_version_dialog.dart'; import 'package:hiddify/features/app_update/widget/new_version_dialog.dart';
@@ -54,7 +56,7 @@ class AboutPage extends HookConsumerWidget {
height: 24, height: 24,
child: CircularProgressIndicator(), child: CircularProgressIndicator(),
), ),
_ => const Icon(Icons.update), _ => const Icon(FluentIcons.arrow_sync_24_regular),
}, },
onTap: () async { onTap: () async {
await ref.read(appUpdateNotifierProvider.notifier).check(); await ref.read(appUpdateNotifierProvider.notifier).check();
@@ -63,7 +65,7 @@ class AboutPage extends HookConsumerWidget {
if (PlatformUtils.isDesktop) if (PlatformUtils.isDesktop)
ListTile( ListTile(
title: Text(t.settings.general.openWorkingDir), title: Text(t.settings.general.openWorkingDir),
trailing: const Icon(Icons.arrow_outward_outlined), trailing: const Icon(FluentIcons.open_folder_24_regular),
onTap: () async { onTap: () async {
final path = final path =
ref.watch(appDirectoriesProvider).requireValue.workingDir.uri; ref.watch(appDirectoriesProvider).requireValue.workingDir.uri;
@@ -79,6 +81,7 @@ class AboutPage extends HookConsumerWidget {
title: Text(t.about.pageTitle), title: Text(t.about.pageTitle),
actions: [ actions: [
PopupMenuButton( PopupMenuButton(
icon: Icon(AdaptiveIcon(context).more),
itemBuilder: (context) { itemBuilder: (context) {
return [ return [
PopupMenuItem( PopupMenuItem(
@@ -126,7 +129,7 @@ class AboutPage extends HookConsumerWidget {
if (conditionalTiles.isNotEmpty) const Divider(), if (conditionalTiles.isNotEmpty) const Divider(),
ListTile( ListTile(
title: Text(t.about.sourceCode), title: Text(t.about.sourceCode),
trailing: const Icon(Icons.open_in_new), trailing: const Icon(FluentIcons.open_24_regular),
onTap: () async { onTap: () async {
await UriUtils.tryLaunch( await UriUtils.tryLaunch(
Uri.parse(Constants.githubUrl), Uri.parse(Constants.githubUrl),
@@ -135,7 +138,7 @@ class AboutPage extends HookConsumerWidget {
), ),
ListTile( ListTile(
title: Text(t.about.telegramChannel), title: Text(t.about.telegramChannel),
trailing: const Icon(Icons.open_in_new), trailing: const Icon(FluentIcons.open_24_regular),
onTap: () async { onTap: () async {
await UriUtils.tryLaunch( await UriUtils.tryLaunch(
Uri.parse(Constants.telegramChannelUrl), Uri.parse(Constants.telegramChannelUrl),
@@ -144,7 +147,7 @@ class AboutPage extends HookConsumerWidget {
), ),
ListTile( ListTile(
title: Text(t.about.termsAndConditions), title: Text(t.about.termsAndConditions),
trailing: const Icon(Icons.open_in_new), trailing: const Icon(FluentIcons.open_24_regular),
onTap: () async { onTap: () async {
await UriUtils.tryLaunch( await UriUtils.tryLaunch(
Uri.parse(Constants.termsAndConditionsUrl), Uri.parse(Constants.termsAndConditionsUrl),
@@ -153,7 +156,7 @@ class AboutPage extends HookConsumerWidget {
), ),
ListTile( ListTile(
title: Text(t.about.privacyPolicy), title: Text(t.about.privacyPolicy),
trailing: const Icon(Icons.open_in_new), trailing: const Icon(FluentIcons.open_24_regular),
onTap: () async { onTap: () async {
await UriUtils.tryLaunch( await UriUtils.tryLaunch(
Uri.parse(Constants.privacyPolicyUrl), Uri.parse(Constants.privacyPolicyUrl),

View File

@@ -1,5 +1,6 @@
import 'dart:io'; import 'dart:io';
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/preferences/general_preferences.dart'; import 'package:hiddify/core/preferences/general_preferences.dart';
@@ -25,7 +26,9 @@ class AdvancedSettingTiles extends HookConsumerWidget {
const RegionPrefTile(), const RegionPrefTile(),
ListTile( ListTile(
title: Text(t.settings.geoAssets.pageTitle), title: Text(t.settings.geoAssets.pageTitle),
leading: const Icon(Icons.folder), leading: const Icon(
FluentIcons.arrow_routing_rectangle_multiple_24_regular,
),
onTap: () async { onTap: () async {
await const GeoAssetsRoute().push(context); await const GeoAssetsRoute().push(context);
}, },
@@ -33,7 +36,7 @@ class AdvancedSettingTiles extends HookConsumerWidget {
if (Platform.isAndroid) ...[ if (Platform.isAndroid) ...[
ListTile( ListTile(
title: Text(t.settings.network.perAppProxyPageTitle), title: Text(t.settings.network.perAppProxyPageTitle),
leading: const Icon(Icons.apps), leading: const Icon(FluentIcons.apps_list_detail_24_regular),
trailing: Switch( trailing: Switch(
value: perAppProxy, value: perAppProxy,
onChanged: (value) async { onChanged: (value) async {
@@ -61,7 +64,7 @@ class AdvancedSettingTiles extends HookConsumerWidget {
title: Text(t.settings.advanced.memoryLimit), title: Text(t.settings.advanced.memoryLimit),
subtitle: Text(t.settings.advanced.memoryLimitMsg), subtitle: Text(t.settings.advanced.memoryLimitMsg),
value: !disableMemoryLimit, value: !disableMemoryLimit,
secondary: const Icon(Icons.memory), secondary: const Icon(FluentIcons.developer_board_24_regular),
onChanged: (value) async { onChanged: (value) async {
await ref.read(disableMemoryLimitProvider.notifier).update(!value); await ref.read(disableMemoryLimitProvider.notifier).update(!value);
}, },
@@ -69,7 +72,7 @@ class AdvancedSettingTiles extends HookConsumerWidget {
if (Platform.isIOS) if (Platform.isIOS)
ListTile( ListTile(
title: Text(t.settings.advanced.resetTunnel), title: Text(t.settings.advanced.resetTunnel),
leading: const Icon(Icons.restart_alt), leading: const Icon(FluentIcons.arrow_reset_24_regular),
onTap: () async { onTap: () async {
await ref.read(resetTunnelProvider.notifier).run(); await ref.read(resetTunnelProvider.notifier).run();
}, },
@@ -77,7 +80,7 @@ class AdvancedSettingTiles extends HookConsumerWidget {
SwitchListTile( SwitchListTile(
title: Text(t.settings.advanced.debugMode), title: Text(t.settings.advanced.debugMode),
value: debug, value: debug,
secondary: const Icon(Icons.bug_report), secondary: const Icon(FluentIcons.window_dev_tools_24_regular),
onChanged: (value) async { onChanged: (value) async {
if (value) { if (value) {
await showDialog<bool>( await showDialog<bool>(

View File

@@ -1,5 +1,6 @@
import 'dart:io'; import 'dart:io';
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/core/preferences/general_preferences.dart'; import 'package:hiddify/core/preferences/general_preferences.dart';
@@ -25,7 +26,7 @@ class GeneralSettingTiles extends HookConsumerWidget {
ListTile( ListTile(
title: Text(t.settings.general.themeMode), title: Text(t.settings.general.themeMode),
subtitle: Text(themeMode.present(t)), subtitle: Text(themeMode.present(t)),
leading: const Icon(Icons.light_mode), leading: const Icon(FluentIcons.weather_moon_20_regular),
onTap: () async { onTap: () async {
final selectedThemeMode = await showDialog<AppThemeMode>( final selectedThemeMode = await showDialog<AppThemeMode>(
context: context, context: context,
@@ -56,7 +57,7 @@ class GeneralSettingTiles extends HookConsumerWidget {
if (Platform.isAndroid) if (Platform.isAndroid)
SwitchListTile( SwitchListTile(
title: Text(t.settings.general.dynamicNotification), title: Text(t.settings.general.dynamicNotification),
secondary: const Icon(Icons.speed), secondary: const Icon(FluentIcons.top_speed_24_regular),
value: ref.watch(dynamicNotificationProvider), value: ref.watch(dynamicNotificationProvider),
onChanged: (value) async { onChanged: (value) async {
await ref await ref

View File

@@ -1,5 +1,6 @@
import 'dart:io'; import 'dart:io';
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:hiddify/core/localization/translations.dart'; import 'package:hiddify/core/localization/translations.dart';
import 'package:hiddify/features/settings/notifier/platform_settings_notifier.dart'; import 'package:hiddify/features/settings/notifier/platform_settings_notifier.dart';
@@ -18,7 +19,7 @@ class PlatformSettingsTiles extends HookConsumerWidget {
ListTile buildIgnoreTile(bool enabled) => ListTile( ListTile buildIgnoreTile(bool enabled) => ListTile(
title: Text(t.settings.general.ignoreBatteryOptimizations), title: Text(t.settings.general.ignoreBatteryOptimizations),
subtitle: Text(t.settings.general.ignoreBatteryOptimizationsMsg), subtitle: Text(t.settings.general.ignoreBatteryOptimizationsMsg),
leading: const Icon(Icons.running_with_errors), leading: const Icon(FluentIcons.battery_saver_24_regular),
enabled: enabled, enabled: enabled,
onTap: () async { onTap: () async {
await ref await ref

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:toastification/toastification.dart'; import 'package:toastification/toastification.dart';
@@ -73,13 +74,13 @@ class CustomToast extends StatelessWidget {
this.message, { this.message, {
this.duration = const Duration(seconds: 5), this.duration = const Duration(seconds: 5),
}) : type = AlertType.error, }) : type = AlertType.error,
icon = Icons.error; icon = FluentIcons.error_circle_24_regular;
const CustomToast.success( const CustomToast.success(
this.message, { this.message, {
this.duration = const Duration(seconds: 3), this.duration = const Duration(seconds: 3),
}) : type = AlertType.success, }) : type = AlertType.success,
icon = Icons.check; icon = FluentIcons.checkmark_24_regular;
final String message; final String message;
final AlertType type; final AlertType type;

View File

@@ -1,3 +1,4 @@
import 'package:fluentui_system_icons/fluentui_system_icons.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:gap/gap.dart'; import 'package:gap/gap.dart';
import 'package:hooks_riverpod/hooks_riverpod.dart'; import 'package:hooks_riverpod/hooks_riverpod.dart';
@@ -39,7 +40,7 @@ class SliverErrorBodyPlaceholder extends HookConsumerWidget {
const SliverErrorBodyPlaceholder( const SliverErrorBodyPlaceholder(
this.msg, { this.msg, {
super.key, super.key,
this.icon = Icons.error, this.icon = FluentIcons.error_circle_24_regular,
}); });
final String msg; final String msg;