Cw 430 find a better way to decide when to show the desktop UI (#977)

* Find a better way to decide when to show the desktop UI * fix UI issue for tablet view * fix trocar invoice issue for landscape layout * fix present receive option piker UI issue * fix dascktop layout * - Fix AnonPay Navigation - Fix Wallet changing on Mobile --------- Co-authored-by: Serhii <borodenko.sv@gmail.com> Co-authored-by: OmarHatem <omarh.ismail1@gmail.com>

Godwin Asuquo committed Jul 13, 2023 at 16:05 UTC ff420c7c7eb7adb30c6e1c40537874840760e6d1
8 files changed +80 -48
android/app/src/main/AndroidManifestBase.xml
-1
@@ -22,7 +22,6 @@
22 android:configChanges="orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
23 android:hardwareAccelerated="true"
24 android:windowSoftInputMode="adjustResize"
25 - android:screenOrientation="portrait"
25 android:exported="true">
26 <meta-data
27 android:name="io.flutter.embedding.android.SplashScreenDrawable"
lib/main.dart
+37 -6
@@ -193,12 +193,7 @@ class App extends StatefulWidget {
193 }
194
195 class AppState extends State<App> with SingleTickerProviderStateMixin {
196 - AppState() : yatStore = getIt.get<YatStore>() {
197 - SystemChrome.setPreferredOrientations(
198 - ResponsiveLayoutUtil.instance.isIpad ?
199 - [DeviceOrientation.landscapeLeft, DeviceOrientation.landscapeRight] :
200 - [DeviceOrientation.portraitUp, DeviceOrientation.portraitDown]);
201 - }
196 + AppState() : yatStore = getIt.get<YatStore>();
197
198 YatStore yatStore;
199 StreamSubscription? stream;
@@ -290,7 +285,43 @@ class AppState extends State<App> with SingleTickerProviderStateMixin {
285 locale: Locale(settingsStore.languageCode),
286 onGenerateRoute: (settings) => Router.createRoute(settings),
287 initialRoute: initialRoute,
288 + home: _Home(),
289 ));
290 });
291 }
292 }
293 +
294 +class _Home extends StatefulWidget {
295 + const _Home();
296 +
297 + @override
298 + State<_Home> createState() => _HomeState();
299 +}
300 +
301 +class _HomeState extends State<_Home> {
302 + @override
303 + void didChangeDependencies() {
304 + if(!ResponsiveLayoutUtil.instance.isMobile){
305 + _setOrientation(context);
306 + }
307 + super.didChangeDependencies();
308 + }
309 +
310 +
311 + void _setOrientation(BuildContext context){
312 + final orientation = MediaQuery.of(context).orientation;
313 + final width = MediaQuery.of(context).size.width;
314 + final height = MediaQuery.of(context).size.height;
315 + if (orientation == Orientation.portrait && width < height) {
316 + SystemChrome.setPreferredOrientations([DeviceOrientation.portraitUp, DeviceOrientation.portraitDown]);
317 + } else if (orientation == Orientation.landscape && width > height) {
318 + SystemChrome.setPreferredOrientations([DeviceOrientation.landscapeLeft, DeviceOrientation.landscapeRight]);
319 + }
320 +
321 + }
322 +
323 + @override
324 + Widget build(BuildContext context) {
325 + return const SizedBox.shrink();
326 + }
327 +}
lib/src/screens/dashboard/dashboard_page.dart
+23 -7
@@ -4,6 +4,7 @@ import 'package:cake_wallet/di.dart';
4 import 'package:cake_wallet/entities/main_actions.dart';
5 import 'package:cake_wallet/src/screens/dashboard/desktop_widgets/desktop_sidebar_wrapper.dart';
6 import 'package:cake_wallet/src/screens/dashboard/widgets/market_place_page.dart';
7 +import 'package:cake_wallet/utils/device_info.dart';
8 import 'package:cake_wallet/utils/version_comparator.dart';
9 import 'package:cake_wallet/view_model/dashboard/market_place_view_model.dart';
10 import 'package:cake_wallet/generated/i18n.dart';
@@ -42,15 +43,30 @@ class DashboardPage extends StatelessWidget {
43
44 @override
45 Widget build(BuildContext context) {
45 - return Scaffold(
46 - body: ResponsiveLayoutUtil.instance.isMobile
47 - ? _DashboardPageView(
46 + return Scaffold(body: LayoutBuilder(
47 + builder: (context, constraints) {
48 + if (DeviceInfo.instance.isDesktop) {
49 + if (constraints.maxWidth > ResponsiveLayoutUtil.kDesktopMaxDashBoardWidthConstraint) {
50 + return getIt.get<DesktopSidebarWrapper>();
51 + } else {
52 + return _DashboardPageView(
53 balancePage: balancePage,
54 dashboardViewModel: dashboardViewModel,
55 addressListViewModel: addressListViewModel,
51 - )
52 - : getIt.get<DesktopSidebarWrapper>(),
53 - );
56 + );
57 + }
58 + } else if (ResponsiveLayoutUtil.instance.shouldRenderMobileUI()) {
59 + return _DashboardPageView(
60 + balancePage: balancePage,
61 + dashboardViewModel: dashboardViewModel,
62 + addressListViewModel: addressListViewModel,
63 + );
64 + } else {
65 + return getIt.get<DesktopSidebarWrapper>();
66 + }
67 +
68 + },
69 + ));
70 }
71 }
72
@@ -251,7 +267,7 @@ class _DashboardPageView extends BasePage {
267 pages.add(Semantics(
268 label: S.of(context).market_place,
269 child: MarketPlacePage(
254 - dashboardViewModel: dashboardViewModel,
270 + dashboardViewModel: dashboardViewModel,
271 marketPlaceViewModel: getIt.get<MarketPlaceViewModel>(),
272 ),
273 ),
lib/src/screens/dashboard/widgets/present_receive_option_picker.dart
+1 -1
@@ -138,7 +138,7 @@ class PresentReceiveOptionPicker extends StatelessWidget {
138 Container(
139 margin: EdgeInsets.only(bottom: 40),
140 child: InkWell(
141 - onTap: () => Navigator.pop(context),
141 + onTap: () => Navigator.pop(popUpContext),
142 child: CircleAvatar(
143 child: Icon(
144 Icons.close,
lib/src/screens/receive/anonpay_invoice_page.dart
+1 -4
@@ -8,7 +8,6 @@ import 'package:cake_wallet/src/screens/dashboard/widgets/present_receive_option
8 import 'package:cake_wallet/src/screens/receive/widgets/anonpay_input_form.dart';
9 import 'package:cake_wallet/src/widgets/alert_with_one_action.dart';
10 import 'package:cake_wallet/src/widgets/keyboard_done_button.dart';
11 -import 'package:cake_wallet/utils/device_info.dart';
11 import 'package:cake_wallet/utils/responsive_layout_util.dart';
12 import 'package:cake_wallet/view_model/anon_invoice_page_view_model.dart';
13 import 'package:cake_wallet/view_model/dashboard/receive_option_view_model.dart';
@@ -54,9 +53,7 @@ class AnonPayInvoicePage extends BasePage {
53 AppBarStyle get appBarStyle => AppBarStyle.transparent;
54
55 @override
57 - void onClose(BuildContext context) {
58 - Navigator.popUntil(context, ModalRoute.withName(Routes.dashboard));
59 - }
56 + void onClose(BuildContext context) => Navigator.popUntil(context, (route) => route.isFirst);
57
58 @override
59 Widget middle(BuildContext context) =>
lib/src/screens/receive/anonpay_receive_page.dart
+1 -22
@@ -32,28 +32,7 @@ class AnonPayReceivePage extends BasePage {
32 bool get resizeToAvoidBottomInset => false;
33
34 @override
35 - Widget leading(BuildContext context) {
36 - final _backButton = Icon(
37 - Icons.arrow_back_ios,
38 - color: Theme.of(context)
39 - .accentTextTheme!
40 - .displayMedium!
41 - .backgroundColor!,
42 - size: 16,
43 - );
44 -
45 - return SizedBox(
46 - height: 37,
47 - width: 37,
48 - child: ButtonTheme(
49 - minWidth: double.minPositive,
50 - child: TextButton(
51 - onPressed: () =>
52 - Navigator.pushNamedAndRemoveUntil(context, Routes.dashboard, (route) => false),
53 - child: _backButton),
54 - ),
55 - );
56 - }
35 + void onClose(BuildContext context) => Navigator.popUntil(context, (route) => route.isFirst);
36
37 @override
38 Widget middle(BuildContext context) {
lib/src/screens/wallet_list/wallet_list_page.dart
+1 -1
@@ -220,7 +220,7 @@ class WalletListBodyState extends State<WalletListBody> {
220 await hideProgressText();
221 // only pop the wallets route in mobile as it will go back to dashboard page
222 // in desktop platforms the navigation tree is different
223 - if (ResponsiveLayoutUtil.instance.isMobile) {
223 + if (ResponsiveLayoutUtil.instance.shouldRenderMobileUI()) {
224 WidgetsBinding.instance.addPostFrameCallback((_) {
225 Navigator.of(context).pop();
226 });
lib/utils/responsive_layout_util.dart
+16 -6
@@ -1,22 +1,32 @@
1 import 'package:flutter/material.dart';
2
3 class ResponsiveLayoutUtil {
4 - static const double _kMobileThreshold = 768;
4 + static const double _kMobileThreshold = 550;
5 static const double kDesktopMaxWidthConstraint = 400;
6 + static const double kDesktopMaxDashBoardWidthConstraint = 900;
7 static const double kPopupWidth = 400;
8 static const double kPopupSpaceHeight = 100;
8 - static const _kIpadMaxWidth = 2560.0;
9
10 const ResponsiveLayoutUtil._();
11
12 static final instance = ResponsiveLayoutUtil._();
13
14 bool get isMobile =>
15 - MediaQueryData.fromWindow(WidgetsBinding.instance.window).size.width < _kMobileThreshold;
15 + MediaQueryData.fromWindow(WidgetsBinding.instance.window).size.shortestSide <=
16 + _kMobileThreshold;
17
17 - bool get isIpad {
18 - final width = MediaQueryData.fromWindow(WidgetsBinding.instance.window).size.width;
19 - return width >= _kMobileThreshold && !(width > _kIpadMaxWidth);
18 + bool shouldRenderMobileUI() {
19 + final mediaQuery = MediaQueryData.fromWindow(WidgetsBinding.instance.window);
20 + final orientation = mediaQuery.orientation;
21 + final width = mediaQuery.size.width;
22 + final height = mediaQuery.size.height;
23 + if (isMobile ||
24 + (orientation == Orientation.portrait && width < height) ||
25 + (orientation == Orientation.landscape && width < height)) {
26 + return true;
27 + } else {
28 + return false;
29 + }
30 }
31
32 /// Returns dynamic size.