nc-photos/app/lib/widget/account_picker_dialog.dart

187 lines
5.9 KiB
Dart
Raw Normal View History

2021-04-10 06:28:12 +02:00
import 'package:flutter/material.dart';
import 'package:kiwi/kiwi.dart';
import 'package:logging/logging.dart';
2021-04-10 06:28:12 +02:00
import 'package:nc_photos/account.dart';
2021-07-25 07:00:38 +02:00
import 'package:nc_photos/app_localizations.dart';
import 'package:nc_photos/di_container.dart';
import 'package:nc_photos/entity/sqlite_table_extension.dart' as sql;
import 'package:nc_photos/exception_util.dart' as exception_util;
2021-04-10 06:28:12 +02:00
import 'package:nc_photos/k.dart' as k;
import 'package:nc_photos/pref.dart';
import 'package:nc_photos/snack_bar_manager.dart';
2021-04-17 10:59:16 +02:00
import 'package:nc_photos/theme.dart';
2021-04-10 06:28:12 +02:00
import 'package:nc_photos/widget/home.dart';
2021-10-19 22:11:35 +02:00
import 'package:nc_photos/widget/settings.dart';
2021-04-10 06:28:12 +02:00
import 'package:nc_photos/widget/sign_in.dart';
/// A dialog that allows the user to switch between accounts
2021-04-10 06:28:12 +02:00
class AccountPickerDialog extends StatefulWidget {
2021-09-15 08:58:06 +02:00
const AccountPickerDialog({
2021-07-23 22:05:57 +02:00
Key? key,
required this.account,
2021-04-10 06:28:12 +02:00
}) : super(key: key);
@override
createState() => _AccountPickerDialogState();
final Account account;
}
class _AccountPickerDialogState extends State<AccountPickerDialog> {
@override
initState() {
super.initState();
2021-12-05 13:02:22 +01:00
_accounts = Pref().getAccounts3Or([]);
2021-04-10 06:28:12 +02:00
}
@override
build(BuildContext context) {
2022-07-10 17:53:24 +02:00
final otherAccountOptions =
_accounts.where((a) => a != widget.account).map((a) {
final label = AccountPref.of(a).getAccountLabel();
return SimpleDialogOption(
padding: const EdgeInsets.symmetric(horizontal: 8),
onPressed: () => _onItemPressed(a),
child: ListTile(
dense: true,
title: Text(label ?? a.url),
subtitle: label == null ? Text(a.username2) : null,
2022-07-10 17:53:24 +02:00
trailing: IconButton(
icon: Icon(
Icons.close,
color: AppTheme.getUnfocusedIconColor(context),
),
tooltip: L10n.global().deleteTooltip,
onPressed: () => _onRemoveItemPressed(a),
),
),
);
}).toList();
2021-04-10 06:28:12 +02:00
final addAccountOptions = [
SimpleDialogOption(
2021-07-05 07:24:09 +02:00
padding: const EdgeInsets.all(8),
2021-04-10 06:28:12 +02:00
onPressed: () {
Navigator.of(context)
..pop()
..pushNamed(SignIn.routeName);
},
child: Tooltip(
message: L10n.global().addServerTooltip,
2021-04-17 10:59:16 +02:00
child: Center(
child: Icon(
Icons.add,
color: AppTheme.getSecondaryTextColor(context),
),
2021-04-10 06:28:12 +02:00
),
),
),
];
2022-07-10 17:53:24 +02:00
final accountLabel = AccountPref.of(widget.account).getAccountLabel();
return AppTheme(
child: SimpleDialog(
title: ListTile(
dense: true,
title: Text(
2022-07-10 17:53:24 +02:00
accountLabel ?? widget.account.url,
style: const TextStyle(fontWeight: FontWeight.bold),
),
2022-07-10 17:53:24 +02:00
subtitle: accountLabel == null
? Text(
widget.account.username2,
2022-07-10 17:53:24 +02:00
style: const TextStyle(fontWeight: FontWeight.bold),
)
: null,
trailing: IconButton(
icon: Icon(
2021-10-19 22:11:35 +02:00
Icons.settings_outlined,
2021-10-19 22:15:43 +02:00
color: AppTheme.getUnfocusedIconColor(context),
),
2021-10-19 22:11:35 +02:00
tooltip: L10n.global().settingsAccountPageTitle,
onPressed: _onEditPressed,
),
),
titlePadding: const EdgeInsetsDirectional.fromSTEB(8, 16, 8, 0),
contentPadding: const EdgeInsetsDirectional.fromSTEB(0, 12, 0, 8),
children: otherAccountOptions + addAccountOptions,
2021-04-10 06:28:12 +02:00
),
);
}
2021-12-05 13:02:22 +01:00
void _onItemPressed(Account account) {
2021-10-27 22:40:54 +02:00
Pref().setCurrentAccountIndex(_accounts.indexOf(account));
2021-04-10 06:28:12 +02:00
Navigator.of(context).pushNamedAndRemoveUntil(Home.routeName, (_) => false,
2021-12-05 13:02:22 +01:00
arguments: HomeArguments(account));
2021-04-10 06:28:12 +02:00
}
2021-12-05 13:02:22 +01:00
Future<void> _onRemoveItemPressed(Account account) async {
2021-07-23 22:05:57 +02:00
try {
2021-12-05 13:02:22 +01:00
await _removeAccount(account);
2021-07-23 22:05:57 +02:00
setState(() {
2021-12-05 13:02:22 +01:00
_accounts = Pref().getAccounts3()!;
2021-07-23 22:05:57 +02:00
});
SnackBarManager().showSnackBar(SnackBar(
2021-12-05 13:02:22 +01:00
content:
Text(L10n.global().removeServerSuccessNotification(account.url)),
2021-07-23 22:05:57 +02:00
duration: k.snackBarDurationNormal,
));
} catch (e) {
SnackBarManager().showSnackBar(SnackBar(
content: Text(exception_util.toUserString(e)),
2021-07-23 22:05:57 +02:00
duration: k.snackBarDurationNormal,
));
}
2021-04-10 06:28:12 +02:00
}
2021-10-19 22:11:35 +02:00
void _onEditPressed() {
Navigator.of(context)
..pop()
..pushNamed(AccountSettingsWidget.routeName,
arguments: AccountSettingsWidgetArguments(widget.account));
}
2021-12-05 13:02:22 +01:00
Future<void> _removeAccount(Account account) async {
_log.info("[_removeAccount] Remove account: $account");
final accounts = Pref().getAccounts3()!;
final currentAccount = accounts[Pref().getCurrentAccountIndex()!];
accounts.remove(account);
final newAccountIndex = accounts.indexOf(currentAccount);
2021-04-10 06:28:12 +02:00
if (newAccountIndex == -1) {
throw StateError("Active account not found in resulting account list");
}
2021-12-05 13:02:22 +01:00
try {
await AccountPref.of(account).provider.clear();
} catch (e, stackTrace) {
_log.shout(
"[_removeAccount] Failed while removing account pref", e, stackTrace);
}
2021-10-27 22:40:54 +02:00
Pref()
2021-12-05 13:02:22 +01:00
..setAccounts3(accounts)
2021-04-10 06:28:12 +02:00
..setCurrentAccountIndex(newAccountIndex);
// check if the same account (server + userId) still exists in known
// accounts
if (!accounts
.any((a) => a.url == account.url && a.userId == account.userId)) {
// account removed, clear cache db
await _removeAccountFromDb(account);
}
}
Future<void> _removeAccountFromDb(Account account) async {
try {
final c = KiwiContainer().resolve<DiContainer>();
await c.sqliteDb.use((db) async {
await db.deleteAccountOf(account);
});
} catch (e, stackTrace) {
_log.shout("[_removeAccountFromDb] Failed while removing account from db",
e, stackTrace);
}
2021-04-10 06:28:12 +02:00
}
2021-12-05 13:02:22 +01:00
late List<Account> _accounts;
static final _log =
Logger("widget.account_picker_dialog._AccountPickerDialogState");
2021-04-10 06:28:12 +02:00
}