V4.6.3 bug fixes (#896)

* Add blocking screenshots native function to Monero.com [skip ci]

* Fix seeds QR data

* Update app versions and release notes [skip ci]

* Update only build number for macos since it wasn't released yet [skip ci]

* Fix adding sub-address

* Fix Accounts Popup UI

* Update app versions and release notes [skip ci]

* Fix add/edit node issue

* Update app versions and release notes [skip ci]

* Fix input fields focus/keyboard issues

* Update app versions and release notes [skip ci]
This commit is contained in:
Omar Hatem 2023-04-26 14:59:27 +02:00 committed by GitHub
parent 9d47e0e67c
commit 82b513d1f8
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
14 changed files with 282 additions and 188 deletions

View file

@ -23,6 +23,7 @@ import java.security.SecureRandom;
public class MainActivity extends FlutterFragmentActivity {
final String UTILS_CHANNEL = "com.cake_wallet/native_utils";
final int UNSTOPPABLE_DOMAIN_MIN_VERSION_SDK = 24;
boolean isAppSecure = false;
@Override
public void configureFlutterEngine(@NonNull FlutterEngine flutterEngine) {
@ -48,13 +49,21 @@ public class MainActivity extends FlutterFragmentActivity {
handler.post(() -> result.success(bytes));
break;
case "getUnstoppableDomainAddress":
int version = Build.VERSION.SDK_INT;
int version = Build.VERSION.SDK_INT;
if (version >= UNSTOPPABLE_DOMAIN_MIN_VERSION_SDK) {
getUnstoppableDomainAddress(call, result);
} else {
handler.post(() -> result.success(""));
}
break;
case "setIsAppSecure":
isAppSecure = call.argument("isAppSecure");
if (isAppSecure) {
getWindow().setFlags(WindowManager.LayoutParams.FLAG_SECURE, WindowManager.LayoutParams.FLAG_SECURE);
} else {
getWindow().clearFlags(WindowManager.LayoutParams.FLAG_SECURE);
}
break;
default:
handler.post(() -> result.notImplemented());
}

View file

@ -1,13 +1,4 @@
This update includes a HUGE number of usability improvements!
Type a fiat amount in the receive screen
Easily restore wallets from QR code
Pay Bitcoin Lightning invoices in exchange
Optionally disable the marketplace in display settings
Better warning messages if trying to exchange outside the min/max limits
More address flexibility when exchanging the currently-active wallet asset
Modernized the seed language selection picker
Adjusted pickers to resize if the keyboard is active
Improved accessibility
Click to copy additional fields in the exchange checkout
Fix padding on some devices
Bug fixes and code refactoring
Fix for QR codes
Fix for creating sub-addresses
Fix Add/Edit nodes
Fix issues with text/amount fields

View file

@ -1,16 +1,4 @@
This update includes a HUGE number of usability improvements!
BTC/LTC coin control enhancements and bugfixes; easily look up Ordinals
Type a fiat amount in the receive screen
New Onramper Buy widget
Easily restore wallets from QR code
Substantially better reliability for seeing incoming, unconfirmed BTC/LTC transactions
Pay Bitcoin Lightning invoices in exchange
Optionally disable the marketplace in display settings
Better warning messages if trying to exchange outside the min/max limits
More address flexibility when exchanging the currently-active wallet asset
Modernized the seed language selection picker
Adjusted pickers to resize if the keyboard is active
Improved accessibility
Click to copy additional fields in the exchange checkout
Fix padding on some devices
Bug fixes and code refactoring
Fix for QR codes
Fix for creating sub-addresses
Fix Add/Edit nodes
Fix issues with text/amount fields

View file

@ -115,6 +115,8 @@ PODS:
- Flutter
- flutter_secure_storage (3.3.1):
- Flutter
- in_app_review (0.2.0):
- Flutter
- local_auth_ios (0.0.1):
- Flutter
- MTBBarcodeScanner (5.0.11)
@ -165,6 +167,7 @@ DEPENDENCIES:
- flutter_inappwebview (from `.symlinks/plugins/flutter_inappwebview/ios`)
- flutter_mailer (from `.symlinks/plugins/flutter_mailer/ios`)
- flutter_secure_storage (from `.symlinks/plugins/flutter_secure_storage/ios`)
- in_app_review (from `.symlinks/plugins/in_app_review/ios`)
- local_auth_ios (from `.symlinks/plugins/local_auth_ios/ios`)
- package_info (from `.symlinks/plugins/package_info/ios`)
- path_provider_foundation (from `.symlinks/plugins/path_provider_foundation/ios`)
@ -220,6 +223,8 @@ EXTERNAL SOURCES:
:path: ".symlinks/plugins/flutter_mailer/ios"
flutter_secure_storage:
:path: ".symlinks/plugins/flutter_secure_storage/ios"
in_app_review:
:path: ".symlinks/plugins/in_app_review/ios"
local_auth_ios:
:path: ".symlinks/plugins/local_auth_ios/ios"
package_info:
@ -260,6 +265,7 @@ SPEC CHECKSUMS:
flutter_inappwebview: bfd58618f49dc62f2676de690fc6dcda1d6c3721
flutter_mailer: 2ef5a67087bc8c6c4cefd04a178bf1ae2c94cd83
flutter_secure_storage: 7953c38a04c3fdbb00571bcd87d8e3b5ceb9daec
in_app_review: 318597b3a06c22bb46dc454d56828c85f444f99d
local_auth_ios: c6cf091ded637a88f24f86a8875d8b0f526e2605
MTBBarcodeScanner: f453b33c4b7dfe545d8c6484ed744d55671788cb
OrderedSet: aaeb196f7fef5a9edf55d89760da9176ad40b93c

View file

@ -1,5 +1,4 @@
import 'package:cake_wallet/themes/theme_base.dart';
import 'package:cake_wallet/utils/responsive_layout_util.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:cake_wallet/palette.dart';
@ -21,8 +20,6 @@ abstract class BasePage extends StatelessWidget {
String? get title => null;
bool get canUseCloseIcon => false;
Color get backgroundLightColor => Colors.white;
Color get backgroundDarkColor => PaletteDark.backgroundColor;
@ -53,27 +50,22 @@ abstract class BasePage extends StatelessWidget {
final _backButton = Icon(Icons.arrow_back_ios,
color: titleColor ?? Theme.of(context).primaryTextTheme.headline6!.color!,
size: 16,);
final _closeButton = currentTheme.type == ThemeType.dark
? closeButtonImageDarkTheme : closeButtonImage;
bool isMobileView = ResponsiveLayoutUtil.instance.isMobile(context);
return MergeSemantics(
child: SizedBox(
height: isMobileView ? 37 : 45,
width: isMobileView ? 37 : 45,
height: 37,
width: 37,
child: ButtonTheme(
minWidth: double.minPositive,
child: Semantics(
label: canUseCloseIcon && !isMobileView ? 'Close' : 'Back',
label: 'Back',
child: TextButton(
style: ButtonStyle(
overlayColor: MaterialStateColor.resolveWith(
(states) => Colors.transparent),
),
onPressed: () => onClose(context),
child:
canUseCloseIcon && !isMobileView ? _closeButton : _backButton,
child: _backButton,
),
),
),

View file

@ -6,6 +6,7 @@ import 'package:cake_wallet/src/screens/dashboard/widgets/present_receive_option
import 'package:cake_wallet/src/widgets/alert_with_two_actions.dart';
import 'package:cake_wallet/src/widgets/keyboard_done_button.dart';
import 'package:cake_wallet/themes/theme_base.dart';
import 'package:cake_wallet/utils/responsive_layout_util.dart';
import 'package:cake_wallet/utils/share_util.dart';
import 'package:cake_wallet/utils/show_pop_up.dart';
import 'package:cake_wallet/view_model/dashboard/receive_option_view_model.dart';
@ -62,7 +63,37 @@ class AddressPage extends BasePage {
Color get titleColor => Colors.white;
@override
bool get canUseCloseIcon => true;
Widget? leading(BuildContext context) {
final _backButton = Icon(Icons.arrow_back_ios,
color: titleColor,
size: 16,
);
final _closeButton = currentTheme.type == ThemeType.dark
? closeButtonImageDarkTheme : closeButtonImage;
bool isMobileView = ResponsiveLayoutUtil.instance.isMobile(context);
return MergeSemantics(
child: SizedBox(
height: isMobileView ? 37 : 45,
width: isMobileView ? 37 : 45,
child: ButtonTheme(
minWidth: double.minPositive,
child: Semantics(
label: !isMobileView ? 'Close' : 'Back',
child: TextButton(
style: ButtonStyle(
overlayColor: MaterialStateColor.resolveWith(
(states) => Colors.transparent),
),
onPressed: () => onClose(context),
child: !isMobileView ? _closeButton : _backButton,
),
),
),
),
);
}
@override
Widget middle(BuildContext context) =>

View file

@ -2,6 +2,7 @@ import 'package:cake_wallet/di.dart';
import 'package:cake_wallet/src/screens/exchange/widgets/desktop_exchange_cards_section.dart';
import 'package:cake_wallet/src/screens/exchange/widgets/mobile_exchange_cards_section.dart';
import 'package:cake_wallet/src/widgets/add_template_button.dart';
import 'package:cake_wallet/themes/theme_base.dart';
import 'package:cake_wallet/utils/debounce.dart';
import 'package:cake_wallet/utils/responsive_layout_util.dart';
import 'package:cw_core/sync_status.dart';
@ -108,7 +109,37 @@ class ExchangePage extends BasePage {
});
@override
bool get canUseCloseIcon => true;
Widget? leading(BuildContext context) {
final _backButton = Icon(Icons.arrow_back_ios,
color: titleColor,
size: 16,
);
final _closeButton = currentTheme.type == ThemeType.dark
? closeButtonImageDarkTheme : closeButtonImage;
bool isMobileView = ResponsiveLayoutUtil.instance.isMobile(context);
return MergeSemantics(
child: SizedBox(
height: isMobileView ? 37 : 45,
width: isMobileView ? 37 : 45,
child: ButtonTheme(
minWidth: double.minPositive,
child: Semantics(
label: !isMobileView ? 'Close' : 'Back',
child: TextButton(
style: ButtonStyle(
overlayColor: MaterialStateColor.resolveWith(
(states) => Colors.transparent),
),
onPressed: () => onClose(context),
child: !isMobileView ? _closeButton : _backButton,
),
),
),
),
);
}
@override
Widget body(BuildContext context) {

View file

@ -1,9 +1,7 @@
import 'dart:ui';
import 'package:cake_wallet/src/widgets/section_divider.dart';
import 'package:cake_wallet/utils/responsive_layout_util.dart';
import 'package:flutter/material.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter_mobx/flutter_mobx.dart';
import 'package:cake_wallet/palette.dart';
import 'package:cake_wallet/routes.dart';
import 'package:cake_wallet/generated/i18n.dart';
import 'package:cake_wallet/view_model/monero_account_list/monero_account_list_view_model.dart';
@ -36,131 +34,138 @@ class MoneroAccountListPage extends StatelessWidget {
@override
Widget build(BuildContext context) {
return AlertBackground(
child: Stack(
alignment: Alignment.center,
children: <Widget>[
Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Container(
padding: EdgeInsets.only(left: 24, right: 24),
child: Text(
S.of(context).choose_account,
textAlign: TextAlign.center,
style: TextStyle(
fontSize: 18,
fontWeight: FontWeight.bold,
fontFamily: 'Lato',
decoration: TextDecoration.none,
color: Colors.white
),
),
),
Padding(
padding: EdgeInsets.only(left: 24, right: 24, top: 24),
child: GestureDetector(
onTap: () => null,
child: ClipRRect(
borderRadius: BorderRadius.all(Radius.circular(14)),
child: Container(
height: 296,
color: Theme.of(context).textTheme!.headline1!.decorationColor!,
child: Column(
children: <Widget>[
Expanded(
child: Observer(
builder: (_) {
final accounts = accountListViewModel.accounts;
isAlwaysShowScrollThumb = accounts == null
? false
: accounts.length > 3;
return Stack(
alignment: Alignment.center,
children: <Widget>[
ListView.separated(
padding: EdgeInsets.zero,
controller: controller,
separatorBuilder: (context, index) =>
const SectionDivider(),
itemCount: accounts.length ?? 0,
itemBuilder: (context, index) {
final account = accounts[index];
return AccountTile(
isCurrent: account.isSelected,
accountName: account.label,
onTap: () {
if (account.isSelected) {
return;
}
accountListViewModel
.select(account);
Navigator.of(context).pop();
},
onEdit: () async =>
await Navigator.of(context)
.pushNamed(
Routes.accountCreation,
arguments: account));
},
),
isAlwaysShowScrollThumb
? CakeScrollbar(
backgroundHeight: backgroundHeight,
thumbHeight: thumbHeight,
fromTop: accountListViewModel
.scrollOffsetFromTop
)
: Offstage(),
],
);
}
)
),
GestureDetector(
onTap: () async => await Navigator.of(context)
.pushNamed(Routes.accountCreation),
child: Container(
height: 62,
color: Theme.of(context).cardColor,
padding: EdgeInsets.only(left: 24, right: 24),
child: Center(
child: Row(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Icon(
Icons.add,
color: Colors.white,
),
Padding(
padding: EdgeInsets.only(left: 5),
child: Text(
S.of(context).create_new_account,
style: TextStyle(
fontSize: 15,
fontWeight: FontWeight.w600,
fontFamily: 'Lato',
color: Colors.white,
decoration: TextDecoration.none,
),
),
)
],
),
),
),
)
],
child: Column(
children: [
Expanded(
child: Stack(
alignment: Alignment.center,
children: <Widget>[
Column(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Container(
padding: EdgeInsets.only(left: 24, right: 24),
child: Text(
S.of(context).choose_account,
textAlign: TextAlign.center,
style: TextStyle(
fontSize: 18,
fontWeight: FontWeight.bold,
fontFamily: 'Lato',
decoration: TextDecoration.none,
color: Colors.white
),
),
),
),
Padding(
padding: EdgeInsets.only(left: 24, right: 24, top: 24),
child: GestureDetector(
onTap: () => null,
child: ClipRRect(
borderRadius: BorderRadius.all(Radius.circular(14)),
child: Container(
height: 296,
color: Theme.of(context).textTheme!.headline1!.decorationColor!,
child: Column(
children: <Widget>[
Expanded(
child: Observer(
builder: (_) {
final accounts = accountListViewModel.accounts;
isAlwaysShowScrollThumb = accounts == null
? false
: accounts.length > 3;
return Stack(
alignment: Alignment.center,
children: <Widget>[
ListView.separated(
padding: EdgeInsets.zero,
controller: controller,
separatorBuilder: (context, index) =>
const SectionDivider(),
itemCount: accounts.length ?? 0,
itemBuilder: (context, index) {
final account = accounts[index];
return AccountTile(
isCurrent: account.isSelected,
accountName: account.label,
onTap: () {
if (account.isSelected) {
return;
}
accountListViewModel
.select(account);
Navigator.of(context).pop();
},
onEdit: () async =>
await Navigator.of(context)
.pushNamed(
Routes.accountCreation,
arguments: account));
},
),
isAlwaysShowScrollThumb
? CakeScrollbar(
backgroundHeight: backgroundHeight,
thumbHeight: thumbHeight,
fromTop: accountListViewModel
.scrollOffsetFromTop
)
: Offstage(),
],
);
}
)
),
GestureDetector(
onTap: () async => await Navigator.of(context)
.pushNamed(Routes.accountCreation),
child: Container(
height: 62,
color: Theme.of(context).cardColor,
padding: EdgeInsets.only(left: 24, right: 24),
child: Center(
child: Row(
mainAxisSize: MainAxisSize.min,
children: <Widget>[
Icon(
Icons.add,
color: Colors.white,
),
Padding(
padding: EdgeInsets.only(left: 5),
child: Text(
S.of(context).create_new_account,
style: TextStyle(
fontSize: 15,
fontWeight: FontWeight.w600,
fontFamily: 'Lato',
color: Colors.white,
decoration: TextDecoration.none,
),
),
)
],
),
),
),
)
],
),
),
),
),
)
],
),
)
],
SizedBox(height: ResponsiveLayoutUtil.kPopupSpaceHeight),
AlertCloseButton()
],
),
),
AlertCloseButton()
],
),
);

View file

@ -5,6 +5,7 @@ import 'package:cake_wallet/src/widgets/add_template_button.dart';
import 'package:cake_wallet/src/widgets/alert_with_two_actions.dart';
import 'package:cake_wallet/src/widgets/picker.dart';
import 'package:cake_wallet/src/widgets/template_tile.dart';
import 'package:cake_wallet/themes/theme_base.dart';
import 'package:cake_wallet/utils/payment_request.dart';
import 'package:cake_wallet/utils/request_review_handler.dart';
import 'package:cake_wallet/utils/responsive_layout_util.dart';
@ -53,7 +54,37 @@ class SendPage extends BasePage {
bool get extendBodyBehindAppBar => true;
@override
bool get canUseCloseIcon => true;
Widget? leading(BuildContext context) {
final _backButton = Icon(Icons.arrow_back_ios,
color: titleColor,
size: 16,
);
final _closeButton = currentTheme.type == ThemeType.dark
? closeButtonImageDarkTheme : closeButtonImage;
bool isMobileView = ResponsiveLayoutUtil.instance.isMobile(context);
return MergeSemantics(
child: SizedBox(
height: isMobileView ? 37 : 45,
width: isMobileView ? 37 : 45,
child: ButtonTheme(
minWidth: double.minPositive,
child: Semantics(
label: !isMobileView ? 'Close' : 'Back',
child: TextButton(
style: ButtonStyle(
overlayColor: MaterialStateColor.resolveWith(
(states) => Colors.transparent),
),
onPressed: () => onClose(context),
child: !isMobileView ? _closeButton : _backButton,
),
),
),
),
);
}
@override
AppBarStyle get appBarStyle => AppBarStyle.transparent;

View file

@ -1,5 +1,4 @@
import 'package:mobx/mobx.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_mobx/flutter_mobx.dart';
import 'package:cake_wallet/generated/i18n.dart';
@ -23,18 +22,14 @@ class AddressEditOrCreatePage extends BasePage {
final GlobalKey<FormState> _formKey;
final TextEditingController _labelController;
bool _isEffectsInstalled = false;
@override
String get title => S.current.new_subaddress_title;
@override
Widget body(BuildContext context) {
reaction((_) => addressEditOrCreateViewModel.state,
(AddressEditOrCreateState state) {
if (state is AddressSavedSuccessfully) {
WidgetsBinding.instance
.addPostFrameCallback((_) => Navigator.of(context).pop());
}
});
_setEffects(context);
return Form(
key: _formKey,
@ -70,4 +65,19 @@ class AddressEditOrCreatePage extends BasePage {
),
));
}
void _setEffects(BuildContext context) {
if (_isEffectsInstalled) {
return;
}
reaction((_) => addressEditOrCreateViewModel.state,
(AddressEditOrCreateState state) {
if (state is AddressSavedSuccessfully) {
WidgetsBinding.instance
.addPostFrameCallback((_) => Navigator.of(context).pop());
}
});
_isEffectsInstalled = true;
}
}

View file

@ -4,7 +4,6 @@ import 'package:cake_wallet/src/widgets/section_divider.dart';
import 'package:cake_wallet/utils/show_bar.dart';
import 'package:device_display_brightness/device_display_brightness.dart';
import 'package:flutter/material.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/services.dart';
import 'package:flutter_mobx/flutter_mobx.dart';
import 'package:cake_wallet/generated/i18n.dart';
@ -26,13 +25,14 @@ class WalletKeysPage extends BasePage {
onPressed: () async {
// Get the current brightness:
final double brightness = await DeviceDisplayBrightness.getBrightness();
final url = await walletKeysViewModel.url;
// ignore: unawaited_futures
DeviceDisplayBrightness.setBrightness(1.0);
await Navigator.pushNamed(
context,
Routes.fullscreenQR,
arguments: QrViewData(data: await walletKeysViewModel.url.toString()),
arguments: QrViewData(data: url.toString()),
);
// ignore: unawaited_futures
DeviceDisplayBrightness.setBrightness(brightness);

View file

@ -14,14 +14,14 @@ TYPES=($MONERO_COM $CAKEWALLET $HAVEN)
APP_ANDROID_TYPE=$1
MONERO_COM_NAME="Monero.com"
MONERO_COM_VERSION="1.3.3"
MONERO_COM_BUILD_NUMBER=43
MONERO_COM_VERSION="1.3.4"
MONERO_COM_BUILD_NUMBER=47
MONERO_COM_BUNDLE_ID="com.monero.app"
MONERO_COM_PACKAGE="com.monero.app"
CAKEWALLET_NAME="Cake Wallet"
CAKEWALLET_VERSION="4.6.3"
CAKEWALLET_BUILD_NUMBER=154
CAKEWALLET_VERSION="4.6.4"
CAKEWALLET_BUILD_NUMBER=158
CAKEWALLET_BUNDLE_ID="com.cakewallet.cake_wallet"
CAKEWALLET_PACKAGE="com.cakewallet.cake_wallet"

View file

@ -13,13 +13,13 @@ TYPES=($MONERO_COM $CAKEWALLET $HAVEN)
APP_IOS_TYPE=$1
MONERO_COM_NAME="Monero.com"
MONERO_COM_VERSION="1.3.3"
MONERO_COM_BUILD_NUMBER=41
MONERO_COM_VERSION="1.3.4"
MONERO_COM_BUILD_NUMBER=45
MONERO_COM_BUNDLE_ID="com.cakewallet.monero"
CAKEWALLET_NAME="Cake Wallet"
CAKEWALLET_VERSION="4.6.3"
CAKEWALLET_BUILD_NUMBER=148
CAKEWALLET_VERSION="4.6.4"
CAKEWALLET_BUILD_NUMBER=153
CAKEWALLET_BUNDLE_ID="com.fotolockr.cakewallet"
HAVEN_NAME="Haven"

View file

@ -16,7 +16,7 @@ fi
CAKEWALLET_NAME="Cake Wallet"
CAKEWALLET_VERSION="1.0.2"
CAKEWALLET_BUILD_NUMBER=14
CAKEWALLET_BUILD_NUMBER=18
CAKEWALLET_BUNDLE_ID="com.fotolockr.cakewallet"
if ! [[ " ${TYPES[*]} " =~ " ${APP_MACOS_TYPE} " ]]; then