TF-1813 Display list sending email in SendingQueueView

(cherry picked from commit 16699d68fa52d5a8dd450c68c64220def1d6a142)
This commit is contained in:
dab246
2023-06-01 14:26:13 +07:00
committed by Dat Vu
parent 86fe019b83
commit ba29dadea6
9 changed files with 401 additions and 2 deletions
@@ -10,6 +10,7 @@ import 'package:tmail_ui_user/features/mailbox/presentation/mailbox_view.dart';
import 'package:tmail_ui_user/features/mailbox_dashboard/presentation/base_mailbox_dashboard_view.dart';
import 'package:tmail_ui_user/features/mailbox_dashboard/presentation/model/dashboard_routes.dart';
import 'package:tmail_ui_user/features/search/email/presentation/search_email_view.dart';
import 'package:tmail_ui_user/features/sending_queue/presentation/sending_queue_view.dart';
import 'package:tmail_ui_user/features/thread/presentation/thread_view.dart';
class MailboxDashBoardView extends BaseMailboxDashBoardView {
@@ -33,7 +34,7 @@ class MailboxDashBoardView extends BaseMailboxDashBoardView {
child: Scaffold(
drawerEnableOpenDragGesture: responsiveUtils.hasLeftMenuDrawerActive(context),
body: Obx(() {
final bodyView = controller.searchController.isSearchEmailRunning
var bodyView = controller.searchController.isSearchEmailRunning
? EmailView()
: bodyLandscapeTablet;
@@ -54,6 +55,22 @@ class MailboxDashBoardView extends BaseMailboxDashBoardView {
mobile: EmailView());
case DashboardRoutes.searchEmail:
return SafeArea(child: SearchEmailView());
case DashboardRoutes.sendingQueue:
bodyView = Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
SizedBox(
width: ResponsiveUtils.defaultSizeLeftMenuMobile,
child: _buildScaffoldHaveDrawer(body: const SendingQueueView())),
Expanded(child: EmailView()),
],
);
return ResponsiveWidget(
responsiveUtils: responsiveUtils,
desktop: bodyView,
tabletLarge: bodyView,
landscapeTablet: bodyView,
mobile: _buildScaffoldHaveDrawer(body: const SendingQueueView()));
case DashboardRoutes.waiting:
return const Center(
child: SizedBox(
@@ -3,5 +3,6 @@ enum DashboardRoutes {
thread,
emailDetailed,
searchEmail,
waiting
waiting,
sendingQueue;
}
@@ -0,0 +1,15 @@
import 'package:get/get.dart';
import 'package:tmail_ui_user/features/sending_queue/presentation/sending_queue_controller.dart';
class SendingQueueBindings extends Bindings {
@override
void dependencies() {
_bindingsController();
}
void _bindingsController() {
Get.put(SendingQueueController());
}
}
@@ -0,0 +1,49 @@
import 'package:core/utils/file_utils.dart';
import 'package:get/get.dart';
import 'package:tmail_ui_user/features/base/interactors_bindings.dart';
import 'package:tmail_ui_user/features/email/data/datasource_impl/email_hive_cache_datasource_impl.dart';
import 'package:tmail_ui_user/features/sending_queue/data/repository/sending_queue_repository_impl.dart';
import 'package:tmail_ui_user/features/sending_queue/domain/repository/sending_queue_repository.dart';
import 'package:tmail_ui_user/features/sending_queue/domain/usecases/get_all_sending_email_interactor.dart';
import 'package:tmail_ui_user/features/offline_mode/manager/detailed_email_cache_manager.dart';
import 'package:tmail_ui_user/features/offline_mode/manager/detailed_email_cache_worker_queue.dart';
import 'package:tmail_ui_user/features/offline_mode/manager/opened_email_cache_manager.dart';
import 'package:tmail_ui_user/features/offline_mode/manager/opened_email_cache_worker_queue.dart';
import 'package:tmail_ui_user/features/offline_mode/manager/sending_email_cache_manager.dart';
import 'package:tmail_ui_user/features/thread/data/local/email_cache_manager.dart';
import 'package:tmail_ui_user/main/exceptions/cache_exception_thrower.dart';
class SendingQueueInteractorBindings extends InteractorsBindings {
@override
void bindingsDataSource() {}
@override
void bindingsDataSourceImpl() {
Get.lazyPut(() => EmailHiveCacheDataSourceImpl(
Get.find<DetailedEmailCacheManager>(),
Get.find<OpenedEmailCacheManager>(),
Get.find<DetailedEmailCacheWorkerQueue>(),
Get.find<OpenedEmailCacheWorkerQueue>(),
Get.find<EmailCacheManager>(),
Get.find<SendingEmailCacheManager>(),
Get.find<FileUtils>(),
Get.find<CacheExceptionThrower>()));
}
@override
void bindingsInteractor() {
Get.lazyPut(() => GetAllSendingEmailInteractor(Get.find<SendingQueueRepository>()));
}
@override
void bindingsRepository() {
Get.lazyPut<SendingQueueRepository>(() => Get.find<SendingQueueRepositoryImpl>());
}
@override
void bindingsRepositoryImpl() {
Get.lazyPut(() => SendingQueueRepositoryImpl(Get.find<EmailHiveCacheDataSourceImpl>()));
}
}
@@ -0,0 +1,22 @@
import 'package:flutter/cupertino.dart';
import 'package:tmail_ui_user/features/base/base_controller.dart';
import 'package:tmail_ui_user/features/mailbox_dashboard/presentation/controller/mailbox_dashboard_controller.dart';
import 'package:tmail_ui_user/main/routes/route_navigation.dart';
class SendingQueueController extends BaseController {
final dashboardController = getBinding<MailboxDashBoardController>();
final listSendingEmailController = ScrollController();
void openMailboxMenu() {
dashboardController!.openMailboxMenuDrawer();
}
@override
void onClose() {
listSendingEmailController.dispose();
super.onClose();
}
}
@@ -0,0 +1,60 @@
import 'package:core/presentation/extensions/color_extension.dart';
import 'package:flutter/material.dart';
import 'package:tmail_ui_user/features/base/mixin/app_loader_mixin.dart';
import 'package:tmail_ui_user/features/base/mixin/compose_floating_button_mixin.dart';
import 'package:tmail_ui_user/features/email/presentation/model/composer_arguments.dart';
import 'package:tmail_ui_user/features/sending_queue/presentation/sending_queue_controller.dart';
import 'package:get/get.dart';
import 'package:tmail_ui_user/features/sending_queue/presentation/widgets/app_bar_sending_queue_widget.dart';
import 'package:tmail_ui_user/features/sending_queue/presentation/widgets/banner_message_sending_queue_widget.dart';
import 'package:tmail_ui_user/features/sending_queue/presentation/widgets/sending_email_tile_widget.dart';
class SendingQueueView extends GetWidget<SendingQueueController>
with AppLoaderMixin,
ComposeFloatingButtonMixin {
const SendingQueueView({super.key});
@override
Widget build(BuildContext context) {
return Scaffold(
backgroundColor: Colors.white,
body: GestureDetector(
onTap: FocusScope.of(context).unfocus,
child: SafeArea(
child: Column(
children: [
AppBarSendingQueueWidget(onOpenMailboxMenu: controller.openMailboxMenu),
const Divider(color: AppColor.colorDividerComposer, height: 1),
const BannerMessageSendingQueueWidget(),
Expanded(child: _buildListSendingEmails(context))
]
),
),
),
floatingActionButton: buildComposeFloatingButton(
context,
controller.listSendingEmailController,
onTap: () => controller.dashboardController!.goToComposer(ComposerArguments())
),
);
}
Widget _buildListSendingEmails(BuildContext context) {
return Obx(() {
if (controller.dashboardController!.listSendingEmails.isNotEmpty) {
return ListView.builder(
controller: controller.listSendingEmailController,
padding: EdgeInsets.zero,
itemCount: controller.dashboardController!.listSendingEmails.length,
itemBuilder: (context, index) => SendingEmailTileWidget(
sendingEmail: controller.dashboardController!.listSendingEmails[index]
)
);
} else {
return const SizedBox.shrink();
}
});
}
}
@@ -0,0 +1,73 @@
import 'package:core/presentation/extensions/color_extension.dart';
import 'package:core/presentation/resources/image_paths.dart';
import 'package:core/presentation/utils/style_utils.dart';
import 'package:core/presentation/views/button/icon_button_web.dart';
import 'package:flutter/material.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:get/get.dart';
import 'package:model/mailbox/select_mode.dart';
import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
import 'package:tmail_ui_user/main/utils/app_utils.dart';
class AppBarSendingQueueWidget extends StatelessWidget {
final VoidCallback? onBackAction;
final VoidCallback? onOpenMailboxMenu;
final SelectMode selectMode;
const AppBarSendingQueueWidget({
super.key,
this.onBackAction,
this.onOpenMailboxMenu,
this.selectMode = SelectMode.INACTIVE,
});
@override
Widget build(BuildContext context) {
final imagePaths = Get.find<ImagePaths>();
return Container(
height: 52,
color: Colors.white,
padding: const EdgeInsets.symmetric(horizontal: 10),
child: Row(
children: [
if (selectMode == SelectMode.INACTIVE)
buildIconWeb(
icon: SvgPicture.asset(
imagePaths.icMenuMailbox,
colorFilter: AppColor.colorTextButton.asFilter(),
fit: BoxFit.fill
),
tooltip: AppLocalizations.of(context).openMailboxMenu,
onTap: onOpenMailboxMenu
)
else
buildIconWeb(
icon: SvgPicture.asset(
AppUtils.isDirectionRTL(context) ? imagePaths.icCollapseFolder : imagePaths.icBack,
colorFilter: AppColor.colorTextButton.asFilter(),
fit: BoxFit.fill
),
tooltip: AppLocalizations.of(context).back,
onTap: onBackAction
),
Expanded(child: Text(
AppLocalizations.of(context).sendingQueue,
maxLines: 1,
textAlign: TextAlign.center,
overflow: CommonTextStyle.defaultTextOverFlow,
softWrap: CommonTextStyle.defaultSoftWrap,
style: const TextStyle(
fontSize: 21,
color: Colors.black,
fontWeight: FontWeight.bold
)
)),
const SizedBox(width: 50)
],
),
);
}
}
@@ -0,0 +1,47 @@
import 'package:core/presentation/extensions/color_extension.dart';
import 'package:core/presentation/resources/image_paths.dart';
import 'package:flutter/material.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
import 'package:tmail_ui_user/main/routes/route_navigation.dart';
class BannerMessageSendingQueueWidget extends StatelessWidget {
const BannerMessageSendingQueueWidget({super.key});
@override
Widget build(BuildContext context) {
final imagePath = getBinding<ImagePaths>();
return Container(
margin: const EdgeInsets.only(top: 16, left: 16, right: 16),
padding: const EdgeInsets.all(16),
decoration: const BoxDecoration(
color: AppColor.colorBannerMessageSendingQueue,
borderRadius: BorderRadius.all(Radius.circular(8))
),
child: Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
SvgPicture.asset(
imagePath!.icMailboxSendingQueue,
fit: BoxFit.fill,
width: 20,
height: 20,
colorFilter: AppColor.colorTitleSendingItem.asFilter(),
),
const SizedBox(width: 8),
Expanded(child: Text(
AppLocalizations.of(context).bannerMessageSendingQueueView,
style: const TextStyle(
fontSize: 15,
color: Colors.black,
fontWeight: FontWeight.normal
)
))
]
),
);
}
}
@@ -0,0 +1,115 @@
import 'package:core/presentation/extensions/color_extension.dart';
import 'package:core/presentation/extensions/string_extension.dart';
import 'package:core/presentation/resources/image_paths.dart';
import 'package:core/presentation/utils/style_utils.dart';
import 'package:flutter/material.dart';
import 'package:flutter_svg/flutter_svg.dart';
import 'package:get/get.dart';
import 'package:model/extensions/presentation_email_extension.dart';
import 'package:model/model.dart';
import 'package:tmail_ui_user/features/composer/domain/model/sending_email.dart';
import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
class SendingEmailTileWidget extends StatelessWidget {
final SendingEmail sendingEmail;
const SendingEmailTileWidget({
super.key,
required this.sendingEmail
});
@override
Widget build(BuildContext context) {
final imagePath = Get.find<ImagePaths>();
return Material(
color: Colors.transparent,
child: InkWell(
onTap: () => {},
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Padding(
padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8),
child: Row(
children: [
SvgPicture.asset(
sendingEmail.presentationEmail.numberOfAllEmailAddress() == 1
? imagePath.icAvatarPersonal
: imagePath.icAvatarGroup,
fit: BoxFit.fill,
width: 60,
height: 60,
),
const SizedBox(width: 8),
Expanded(child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
Row(children: [
Expanded(child: Text(
AppLocalizations.of(context).titleRecipientSendingEmail(sendingEmail.presentationEmail.recipientsName()).withUnicodeCharacter,
softWrap: CommonTextStyle.defaultSoftWrap,
overflow: CommonTextStyle.defaultTextOverFlow,
maxLines: 1,
style: const TextStyle(
fontSize: 15,
color: AppColor.colorTitleSendingItem,
fontWeight: FontWeight.w600
)
)),
if (sendingEmail.email.attachments != null && sendingEmail.email.attachments!.isNotEmpty)
Padding(
padding: const EdgeInsets.only(left: 8),
child: SvgPicture.asset(
imagePath.icAttachment,
width: 20,
height: 20,
fit: BoxFit.fill
)
),
Padding(
padding: const EdgeInsets.only(left: 8),
child: Text(
sendingEmail.getCreateTimeAt(Localizations.localeOf(context).toLanguageTag()),
maxLines: 1,
softWrap: CommonTextStyle.defaultSoftWrap,
overflow: CommonTextStyle.defaultTextOverFlow,
style: const TextStyle(
fontSize: 13,
color: AppColor.colorTitleSendingItem,
fontWeight: FontWeight.normal
)
)
)
]),
const SizedBox(height: 8),
Text(
sendingEmail.presentationEmail.getEmailTitle().withUnicodeCharacter,
softWrap: CommonTextStyle.defaultSoftWrap,
overflow: CommonTextStyle.defaultTextOverFlow,
maxLines: 1,
style: const TextStyle(
fontSize: 13,
color: AppColor.colorTitleSendingItem,
fontWeight: FontWeight.normal
)
),
]
))
]),
),
const Padding(
padding: EdgeInsets.only(left: 84, right: 8),
child: Divider(
color: AppColor.lineItemListColor,
height: 1,
thickness: 0.2
),
)
],
),
),
);
}
}