Skip to content

Commit 842c1dc

Browse files
committed
Changes from review
- Convert ViewModel from a mixin to an abstract base class - Remove unnecessary @action and @computed - Add Observer widgets in views to handle state instead of a global one
1 parent 5d81630 commit 842c1dc

23 files changed

+62
-65
lines changed

android/.gitignore

+1
Original file line numberDiff line numberDiff line change
@@ -12,3 +12,4 @@ key.properties
1212
**/*.keystore
1313
**/*.jks
1414
**/*.pwd
15+
app/.cxx

lib/view_model/abstract.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ import 'package:cupcake/l10n/app_localizations.dart';
66
import 'package:cupcake/utils/alerts/basic.dart';
77
import 'package:flutter/material.dart';
88

9-
mixin ViewModel {
9+
abstract class ViewModel {
1010
bool canPop = true;
1111
String get screenName => "screenName";
1212

lib/view_model/barcode_scanner_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ part 'barcode_scanner_view_model.g.dart';
88

99
class BarcodeScannerViewModel = BarcodeScannerViewModelBase with _$BarcodeScannerViewModel;
1010

11-
abstract class BarcodeScannerViewModelBase with ViewModel, Store {
11+
abstract class BarcodeScannerViewModelBase extends ViewModel with Store {
1212
BarcodeScannerViewModelBase({required this.wallet});
1313

1414
@override

lib/view_model/create_wallet_view_model.dart

+1-2
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@ part 'create_wallet_view_model.g.dart';
2222

2323
class CreateWalletViewModel = CreateWalletViewModelBase with _$CreateWalletViewModel;
2424

25-
abstract class CreateWalletViewModelBase with ViewModel, Store {
25+
abstract class CreateWalletViewModelBase extends ViewModel with Store {
2626
CreateWalletViewModelBase({
2727
required this.createMethod,
2828
required this.needsPasswordConfirm,
@@ -40,7 +40,6 @@ abstract class CreateWalletViewModelBase with ViewModel, Store {
4040
@observable
4141
late String screenName = screenNameOriginal;
4242

43-
@computed
4443
String get screenNameOriginal => switch (createMethod) {
4544
CreateMethod.create => L.create_wallet,
4645
CreateMethod.restore => L.restore_wallet,

lib/view_model/form_builder_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ part 'form_builder_view_model.g.dart';
77

88
class FormBuilderViewModel = FormBuilderViewModelBase with _$FormBuilderViewModel;
99

10-
abstract class FormBuilderViewModelBase with ViewModel, Store {
10+
abstract class FormBuilderViewModelBase extends ViewModel with Store {
1111
FormBuilderViewModelBase({
1212
required this.formElements,
1313
required this.scaffoldContext,

lib/view_model/home_screen_view_model.dart

+2-5
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@ part 'home_screen_view_model.g.dart';
1212

1313
class HomeScreenViewModel = HomeScreenViewModelBase with _$HomeScreenViewModel;
1414

15-
abstract class HomeScreenViewModelBase with ViewModel, Store {
15+
abstract class HomeScreenViewModelBase extends ViewModel with Store {
1616
HomeScreenViewModelBase({required this.openLastWallet, this.lastOpenedWallet});
1717

1818
@override
@@ -29,7 +29,6 @@ abstract class HomeScreenViewModelBase with ViewModel, Store {
2929
return WalletEdit(walletInfo: walletInfo).push(c!);
3030
}
3131

32-
@action
3332
Future<void> createWallet(final CreateMethod method) async {
3433
if (!mounted) return;
3534
return CreateWallet(
@@ -38,7 +37,6 @@ abstract class HomeScreenViewModelBase with ViewModel, Store {
3837
).push(c!);
3938
}
4039

41-
@action
4240
Future<void> loadInitialState(final BuildContext context) async {
4341
await Future.delayed(Duration.zero); // load the screen
4442
if (CupcakeConfig.instance.lastWallet == null) return;
@@ -48,7 +46,6 @@ abstract class HomeScreenViewModelBase with ViewModel, Store {
4846
return CupcakeConfig.instance.lastWallet!.openUI(context);
4947
}
5048

51-
@action
5249
Future<List<CoinWalletInfo>> wallets(final int sort) async {
5350
final List<CoinWalletInfo> wallets = [];
5451
for (final coin in walletCoins) {
@@ -68,7 +65,6 @@ abstract class HomeScreenViewModelBase with ViewModel, Store {
6865
@observable
6966
int varWalletSort = CupcakeConfig.instance.walletSort;
7067

71-
@computed
7268
set walletSort(final int value) {
7369
varWalletSort = value;
7470
CupcakeConfig.instance.walletSort = value;
@@ -80,5 +76,6 @@ abstract class HomeScreenViewModelBase with ViewModel, Store {
8076
walletSort = (varWalletSort + 1) % 2;
8177
}
8278

79+
@computed
8380
Future<bool> get showLandingInfo async => (await wallets(varWalletSort)).isEmpty;
8481
}
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import 'package:cupcake/view_model/abstract.dart';
22

3-
class InitialSetupViewModel with ViewModel {
3+
class InitialSetupViewModel extends ViewModel {
44
@override
55
String get screenName => "";
66
}

lib/view_model/new_wallet_info_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ part 'new_wallet_info_view_model.g.dart';
66

77
class NewWalletInfoViewModel = NewWalletInfoViewModelBase with _$NewWalletInfoViewModel;
88

9-
abstract class NewWalletInfoViewModelBase with ViewModel, Store {
9+
abstract class NewWalletInfoViewModelBase extends ViewModel with Store {
1010
NewWalletInfoViewModelBase(this.pages);
1111

1212
@override

lib/view_model/open_wallet_view_model.dart

+1-4
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ part 'open_wallet_view_model.g.dart';
1010

1111
class OpenWalletViewModel = OpenWalletViewModelBase with _$OpenWalletViewModel;
1212

13-
abstract class OpenWalletViewModelBase with ViewModel, Store {
13+
abstract class OpenWalletViewModelBase extends ViewModel with Store {
1414
OpenWalletViewModelBase({required this.coinWalletInfo});
1515

1616
final CoinWalletInfo coinWalletInfo;
@@ -35,7 +35,6 @@ abstract class OpenWalletViewModelBase with ViewModel, Store {
3535
errorHandler: errorHandler,
3636
);
3737

38-
@action
3938
Future<void> openWallet() async {
4039
await callThrowable(
4140
() async {
@@ -49,7 +48,6 @@ abstract class OpenWalletViewModelBase with ViewModel, Store {
4948
);
5049
}
5150

52-
@action
5351
Future<bool> checkWalletPassword() async {
5452
try {
5553
return coinWalletInfo.checkWalletPassword(await walletPassword.value);
@@ -58,7 +56,6 @@ abstract class OpenWalletViewModelBase with ViewModel, Store {
5856
}
5957
}
6058

61-
@action
6259
Future<void> openWalletIfPasswordCorrect() async {
6360
if (await checkWalletPassword()) {
6461
if (!mounted) return;

lib/view_model/receive_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ part 'receive_view_model.g.dart';
66

77
class ReceiveViewModel = ReceiveViewModelBase with _$ReceiveViewModel;
88

9-
abstract class ReceiveViewModelBase with ViewModel, Store {
9+
abstract class ReceiveViewModelBase extends ViewModel with Store {
1010
ReceiveViewModelBase(this.wallet);
1111
final CoinWallet wallet;
1212

lib/view_model/security_backup_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,7 @@ part 'security_backup_view_model.g.dart';
1010

1111
class SecurityBackupViewModel = SecurityBackupViewModelBase with _$SecurityBackupViewModel;
1212

13-
abstract class SecurityBackupViewModelBase with ViewModel, Store {
13+
abstract class SecurityBackupViewModelBase extends ViewModel with Store {
1414
SecurityBackupViewModelBase({required this.wallet});
1515

1616
@override

lib/view_model/settings_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ part 'settings_view_model.g.dart';
66

77
class SettingsViewModel = SettingsViewModelBase with _$SettingsViewModel;
88

9-
abstract class SettingsViewModelBase with ViewModel, Store {
9+
abstract class SettingsViewModelBase extends ViewModel with Store {
1010
SettingsViewModelBase();
1111

1212
@override

lib/view_model/unconfirmed_transaction_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ part 'unconfirmed_transaction_view_model.g.dart';
1111
class UnconfirmedTransactionViewModel = UnconfirmedTransactionViewModelBase
1212
with _$UnconfirmedTransactionViewModel;
1313

14-
abstract class UnconfirmedTransactionViewModelBase with ViewModel, Store {
14+
abstract class UnconfirmedTransactionViewModelBase extends ViewModel with Store {
1515
UnconfirmedTransactionViewModelBase({
1616
required this.wallet,
1717
required this.fee,

lib/view_model/urqr_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ part 'urqr_view_model.g.dart';
55

66
class URQRViewModel = URQRViewModelBase with _$URQRViewModel;
77

8-
abstract class URQRViewModelBase with ViewModel, Store {
8+
abstract class URQRViewModelBase extends ViewModel with Store {
99
URQRViewModelBase({
1010
required this.urqrList,
1111
});

lib/view_model/wallet_edit_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,7 @@ part 'wallet_edit_view_model.g.dart';
1313

1414
class WalletEditViewModel = WalletEditViewModelBase with _$WalletEditViewModel;
1515

16-
abstract class WalletEditViewModelBase with ViewModel, Store {
16+
abstract class WalletEditViewModelBase extends ViewModel with Store {
1717
WalletEditViewModelBase({
1818
required this.walletInfo,
1919
});

lib/view_model/wallet_home_view_model.dart

+1-1
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ part 'wallet_home_view_model.g.dart';
88

99
class WalletHomeViewModel = WalletHomeViewModelBase with _$WalletHomeViewModel;
1010

11-
abstract class WalletHomeViewModelBase with ViewModel, Store {
11+
abstract class WalletHomeViewModelBase extends ViewModel with Store {
1212
WalletHomeViewModelBase({required this.wallet});
1313

1414
final CoinWallet wallet;

lib/views/abstract.dart

+7-12
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@ import 'package:cupcake/view_model/abstract.dart';
55
import 'package:cupcake/views/widgets/cupcake_appbar_title.dart';
66
import 'package:flutter/cupertino.dart';
77
import 'package:flutter/material.dart';
8-
import 'package:flutter_mobx/flutter_mobx.dart';
98

109
// Since there is no performance penalty for using stateful widgets I would just
1110
// use them everywhere, but honestly all I need in stateless widgets is easy
@@ -85,17 +84,13 @@ class AbstractView extends StatefulWidget {
8584
viewModel.register(context);
8685
return PopScope(
8786
canPop: canPop,
88-
child: Observer(
89-
builder: (final BuildContext context) {
90-
return Scaffold(
91-
key: viewModel.scaffoldKey,
92-
appBar: appBar,
93-
body: body(context),
94-
endDrawer: drawer,
95-
floatingActionButton: floatingActionButton(context),
96-
bottomNavigationBar: bottomNavigationBar(context),
97-
);
98-
},
87+
child: Scaffold(
88+
key: viewModel.scaffoldKey,
89+
appBar: appBar,
90+
body: body(context),
91+
endDrawer: drawer,
92+
floatingActionButton: floatingActionButton(context),
93+
bottomNavigationBar: bottomNavigationBar(context),
9994
),
10095
);
10196
}

lib/views/barcode_scanner.dart

+29-24
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ import 'package:cupcake/views/widgets/barcode_scanner/toggle_flashlight_button.d
88
import 'package:cupcake/views/widgets/barcode_scanner/urqr_progress.dart';
99
import 'package:fast_scanner/fast_scanner.dart';
1010
import 'package:flutter/material.dart';
11+
import 'package:flutter_mobx/flutter_mobx.dart';
1112

1213
class BarcodeScanner extends AbstractView {
1314
BarcodeScanner({
@@ -22,34 +23,38 @@ class BarcodeScanner extends AbstractView {
2223

2324
@override
2425
Widget? body(final BuildContext context) {
25-
final ur = URQRData.parse(viewModel.urCodes);
26-
return Stack(
27-
children: [
28-
MobileScanner(
29-
onDetect: (final BarcodeCapture bc) => viewModel.handleBarcode(bc),
30-
controller: viewModel.mobileScannerCtrl,
31-
),
32-
if (ur.inputs.isNotEmpty)
33-
Center(
34-
child: Text(
35-
"${ur.inputs.length}/${ur.count}",
36-
style: Theme.of(context).textTheme.displayLarge?.copyWith(color: Colors.white),
26+
return Observer(
27+
builder: (final BuildContext context) {
28+
final ur = URQRData.parse(viewModel.urCodes);
29+
return Stack(
30+
children: [
31+
MobileScanner(
32+
onDetect: (final BarcodeCapture bc) => viewModel.handleBarcode(bc),
33+
controller: viewModel.mobileScannerCtrl,
3734
),
38-
),
39-
SizedBox(
40-
child: Center(
41-
child: SizedBox(
42-
width: 250,
43-
height: 250,
44-
child: CustomPaint(
45-
painter: ProgressPainter(
46-
urQrProgress: URQrProgress.fromURQRData(ur),
35+
if (ur.inputs.isNotEmpty)
36+
Center(
37+
child: Text(
38+
"${ur.inputs.length}/${ur.count}",
39+
style: Theme.of(context).textTheme.displayLarge?.copyWith(color: Colors.white),
40+
),
41+
),
42+
SizedBox(
43+
child: Center(
44+
child: SizedBox(
45+
width: 250,
46+
height: 250,
47+
child: CustomPaint(
48+
painter: ProgressPainter(
49+
urQrProgress: URQrProgress.fromURQRData(ur),
50+
),
51+
),
4752
),
4853
),
4954
),
50-
),
51-
),
52-
],
55+
],
56+
);
57+
},
5358
);
5459
}
5560

lib/views/home_screen.dart

+8-2
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import 'package:cupcake/views/abstract.dart';
55
import 'package:cupcake/views/widgets/buttons/long_primary.dart';
66
import 'package:cupcake/views/widgets/buttons/long_secondary.dart';
77
import 'package:flutter/material.dart';
8+
import 'package:flutter_mobx/flutter_mobx.dart';
89
import 'package:path/path.dart' as p;
910

1011
class HomeScreen extends AbstractView {
@@ -22,7 +23,6 @@ class HomeScreen extends AbstractView {
2223

2324
@override
2425
Widget? body(final BuildContext context) {
25-
final _ = viewModel.varWalletSort; // work around for mobx not updating
2626
return FutureBuilder(
2727
future: viewModel.showLandingInfo,
2828
builder: (final BuildContext context, final AsyncSnapshot<bool> value) {
@@ -32,7 +32,13 @@ class HomeScreen extends AbstractView {
3232
}
3333
return FutureBuilder(
3434
future: viewModel.wallets(viewModel.varWalletSort),
35-
builder: walletsBody,
35+
builder: (final BuildContext context, final AsyncSnapshot<List<CoinWalletInfo>> wallets) {
36+
return Observer(
37+
builder: (final BuildContext context) {
38+
return walletsBody(context, wallets);
39+
},
40+
);
41+
},
3642
);
3743
},
3844
);

lib/views/open_wallet.dart

-2
Original file line numberDiff line numberDiff line change
@@ -29,8 +29,6 @@ class OpenWallet extends AbstractView {
2929
],
3030
scaffoldContext: context,
3131
isPinSet: false,
32-
toggleIsPinSet: (final bool val) {},
33-
onLabelChange: (final String? _) {},
3432
),
3533
),
3634
],

lib/views/security_backup.dart

-1
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,6 @@ class SecurityBackup extends AbstractView {
4040
formElements: viewModel.form,
4141
scaffoldContext: context,
4242
isPinSet: !viewModel.isLocked,
43-
onLabelChange: null,
4443
),
4544
);
4645
}

lib/views/settings.dart

+1
Original file line numberDiff line numberDiff line change
@@ -52,6 +52,7 @@ class SettingsView extends AbstractView {
5252
await secureStorage.delete(key: key);
5353
}
5454
}
55+
viewModel.save();
5556
},
5657
),
5758
if (viewModel.config.didFoundInsecureBiometric)

lib/views/wallet_edit.dart

-1
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,6 @@ class WalletEdit extends AbstractView {
2828
formElements: viewModel.form,
2929
scaffoldContext: context,
3030
isPinSet: false,
31-
onLabelChange: (final _) {},
3231
),
3332
),
3433
const Spacer(),

0 commit comments

Comments
 (0)