From 8af88c0091f7e3489a641fb798fbe96c27a2c5fa Mon Sep 17 00:00:00 2001 From: dab246 Date: Mon, 10 Jul 2023 14:39:52 +0700 Subject: [PATCH] TF-1994 Enable long press to copy an email address in email view --- lib/features/base/widget/material_text_button.dart | 4 ++++ .../controller/single_email_controller.dart | 8 ++------ .../presentation/widgets/email_receiver_builder.dart | 4 ++++ .../presentation/widgets/email_sender_builder.dart | 7 +++++++ lib/main/utils/app_utils.dart | 10 ++++++++++ 5 files changed, 27 insertions(+), 6 deletions(-) diff --git a/lib/features/base/widget/material_text_button.dart b/lib/features/base/widget/material_text_button.dart index 53638156cf..7a7774fc68 100644 --- a/lib/features/base/widget/material_text_button.dart +++ b/lib/features/base/widget/material_text_button.dart @@ -3,11 +3,13 @@ import 'package:core/presentation/extensions/color_extension.dart'; import 'package:flutter/material.dart'; typedef OnTapMaterialTextButton = Function(); +typedef OnLongPressMaterialTextButton = Function(); class MaterialTextButton extends StatelessWidget { final String label; final OnTapMaterialTextButton? onTap; + final OnLongPressMaterialTextButton? onLongPress; final double borderRadius; final Color? labelColor; final double labelSize; @@ -21,6 +23,7 @@ class MaterialTextButton extends StatelessWidget { Key? key, required this.label, required this.onTap, + this.onLongPress, this.borderRadius = 12, this.labelColor, this.labelSize = 15, @@ -37,6 +40,7 @@ class MaterialTextButton extends StatelessWidget { color: Colors.transparent, child: InkWell( onTap: onTap, + onLongPress: onLongPress, customBorder: RoundedRectangleBorder(borderRadius: BorderRadius.circular(borderRadius)), child: Padding( padding: padding ?? const EdgeInsets.symmetric(horizontal: 8, vertical: 5), diff --git a/lib/features/email/presentation/controller/single_email_controller.dart b/lib/features/email/presentation/controller/single_email_controller.dart index 30297f50b6..cb7208ea46 100644 --- a/lib/features/email/presentation/controller/single_email_controller.dart +++ b/lib/features/email/presentation/controller/single_email_controller.dart @@ -72,6 +72,7 @@ import 'package:tmail_ui_user/main/routes/dialog_router.dart'; import 'package:tmail_ui_user/main/routes/navigation_router.dart'; import 'package:tmail_ui_user/main/routes/route_navigation.dart'; import 'package:tmail_ui_user/main/routes/route_utils.dart'; +import 'package:tmail_ui_user/main/utils/app_utils.dart'; import 'package:uuid/uuid.dart'; class SingleEmailController extends BaseController with AppLoaderMixin { @@ -950,12 +951,7 @@ class SingleEmailController extends BaseController with AppLoaderMixin { void copyEmailAddress(BuildContext context, EmailAddress emailAddress) { popBack(); - - Clipboard.setData(ClipboardData(text: emailAddress.emailAddress)).then((_){ - ScaffoldMessenger.of(context).showSnackBar( - SnackBar(content: Text(AppLocalizations.of(context).email_address_copied_to_clipboard)) - ); - }); + AppUtils.copyEmailAddressToClipboard(context, emailAddress.emailAddress); } void composeEmailFromEmailAddress(EmailAddress emailAddress) { diff --git a/lib/features/email/presentation/widgets/email_receiver_builder.dart b/lib/features/email/presentation/widgets/email_receiver_builder.dart index e5f0266114..b2e3fb4b34 100644 --- a/lib/features/email/presentation/widgets/email_receiver_builder.dart +++ b/lib/features/email/presentation/widgets/email_receiver_builder.dart @@ -17,6 +17,7 @@ import 'package:tmail_ui_user/features/base/widget/material_text_button.dart'; import 'package:tmail_ui_user/features/composer/presentation/extensions/prefix_email_address_extension.dart'; import 'package:tmail_ui_user/features/email/presentation/controller/single_email_controller.dart'; import 'package:tmail_ui_user/main/localizations/app_localizations.dart'; +import 'package:tmail_ui_user/main/utils/app_utils.dart'; class EmailReceiverBuilder extends StatelessWidget { @@ -190,6 +191,9 @@ class EmailReceiverBuilder extends StatelessWidget { ? emailAddress.asString() : '${emailAddress.asString()},', onTap: () => controller.openEmailAddressDialog(context, emailAddress), + onLongPress: () { + AppUtils.copyEmailAddressToClipboard(context, emailAddress.emailAddress); + }, borderRadius: 8, labelColor: Colors.black, labelSize: 16, diff --git a/lib/features/email/presentation/widgets/email_sender_builder.dart b/lib/features/email/presentation/widgets/email_sender_builder.dart index 0d523d6f2d..70a399e73f 100644 --- a/lib/features/email/presentation/widgets/email_sender_builder.dart +++ b/lib/features/email/presentation/widgets/email_sender_builder.dart @@ -5,6 +5,7 @@ import 'package:flutter/material.dart'; import 'package:jmap_dart_client/jmap/mail/email/email_address.dart'; import 'package:model/extensions/email_address_extension.dart'; import 'package:tmail_ui_user/features/base/widget/material_text_button.dart'; +import 'package:tmail_ui_user/main/utils/app_utils.dart'; typedef OnOpenEmailAddressDetailAction = Function(BuildContext context, EmailAddress emailAddress); @@ -32,6 +33,9 @@ class EmailSenderBuilder extends StatelessWidget { MaterialTextButton( label: emailAddress.displayName, onTap: () => openEmailAddressDetailAction?.call(context, emailAddress), + onLongPress: () { + AppUtils.copyEmailAddressToClipboard(context, emailAddress.emailAddress); + }, borderRadius: 8, padding: const EdgeInsets.all(3), labelSize: 20, @@ -45,6 +49,9 @@ class EmailSenderBuilder extends StatelessWidget { child: MaterialTextButton( label: '<${emailAddress.emailAddress}>', onTap: () => openEmailAddressDetailAction?.call(context, emailAddress), + onLongPress: () { + AppUtils.copyEmailAddressToClipboard(context, emailAddress.emailAddress); + }, borderRadius: 8, padding: const EdgeInsets.all(3), labelSize: 16, diff --git a/lib/main/utils/app_utils.dart b/lib/main/utils/app_utils.dart index 7fa2b8b150..4f62d697e2 100644 --- a/lib/main/utils/app_utils.dart +++ b/lib/main/utils/app_utils.dart @@ -1,6 +1,8 @@ import 'package:core/utils/platform_info.dart'; import 'package:flutter/material.dart'; +import 'package:flutter/services.dart'; import 'package:flutter_dotenv/flutter_dotenv.dart'; +import 'package:tmail_ui_user/main/localizations/app_localizations.dart'; import 'package:tmail_ui_user/main/utils/app_config.dart'; import 'package:url_launcher/url_launcher.dart'; import 'package:intl/intl.dart' as intl; @@ -38,4 +40,12 @@ class AppUtils { static bool isEmailLocalhost(String email) { return RegExp(r'^(([^<>()[\]\\.,;:\s@"]+(\.[^<>()[\]\\.,;:\s@"]+)*)|(".+"))@localhost$').hasMatch(email); } + + static void copyEmailAddressToClipboard(BuildContext context, String emailAddress) { + Clipboard.setData(ClipboardData(text: emailAddress)).then((_){ + ScaffoldMessenger.maybeOf(context)?.showSnackBar( + SnackBar(content: Text(AppLocalizations.of(context).email_address_copied_to_clipboard)) + ); + }); + } } \ No newline at end of file