TF-35 Add presentation for search mailbox

This commit is contained in:
dab246
2022-02-23 17:10:35 +07:00
committed by Dat H. Pham
parent 690de9483f
commit 9cca03fff3
14 changed files with 206 additions and 72 deletions
+3
View File
@@ -0,0 +1,3 @@
<svg width="16" height="16" viewBox="0 0 16 16" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M8 0C12.4183 0 16 3.58172 16 8C16 12.4183 12.4183 16 8 16C3.58172 16 0 12.4183 0 8C0 3.58172 3.58172 0 8 0ZM10.4657 4.26022L8 6.727L5.5357 4.26022C5.18423 3.90875 4.61438 3.90875 4.26291 4.26022C3.91144 4.6117 3.91144 5.18154 4.26291 5.53302L6.728 8.001L4.26291 10.47C3.91144 10.8215 3.91144 11.3913 4.26291 11.7428C4.61438 12.0943 5.18423 12.0943 5.5357 11.7428L8 9.275L10.4657 11.7428C10.8172 12.0943 11.387 12.0943 11.7385 11.7428C12.09 11.3913 12.09 10.8215 11.7385 10.47L9.272 8.001L11.7385 5.53302C12.09 5.18154 12.09 4.6117 11.7385 4.26022C11.387 3.90875 10.8172 3.90875 10.4657 4.26022Z" fill="#99A2AD"/>
</svg>

After

Width:  |  Height:  |  Size: 725 B

@@ -80,6 +80,7 @@ class ImagePaths {
String get icFilterMessageAttachments => _getImagePath('ic_filter_message_attachments.svg'); String get icFilterMessageAttachments => _getImagePath('ic_filter_message_attachments.svg');
String get icLogoTMailV2 => _getImagePath('logo_tmail_v2.png'); String get icLogoTMailV2 => _getImagePath('logo_tmail_v2.png');
String get icSendToast => _getImagePath('ic_send_toast.svg'); String get icSendToast => _getImagePath('ic_send_toast.svg');
String get icClearTextSearch => _getImagePath('ic_clear_text_search.svg');
String _getImagePath(String imageName) { String _getImagePath(String imageName) {
return AssetsPaths.images + imageName; return AssetsPaths.images + imageName;
@@ -1,4 +1,5 @@
import 'package:core/core.dart'; import 'package:core/core.dart';
import 'package:flutter/material.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:shared_preferences/shared_preferences.dart'; import 'package:shared_preferences/shared_preferences.dart';
import 'package:tmail_ui_user/features/caching/caching_manager.dart'; import 'package:tmail_ui_user/features/caching/caching_manager.dart';
@@ -46,6 +47,8 @@ class MailboxBindings extends Bindings {
Get.lazyPut(() => TreeBuilder()); Get.lazyPut(() => TreeBuilder());
Get.lazyPut(() => CreateNewMailboxInteractor(Get.find<MailboxRepository>())); Get.lazyPut(() => CreateNewMailboxInteractor(Get.find<MailboxRepository>()));
Get.lazyPut(() => Uuid()); Get.lazyPut(() => Uuid());
Get.lazyPut(() => TextEditingController());
Get.lazyPut(() => FocusNode());
Get.put(MailboxController( Get.put(MailboxController(
Get.find<GetAllMailboxInteractor>(), Get.find<GetAllMailboxInteractor>(),
Get.find<DeleteCredentialInteractor>(), Get.find<DeleteCredentialInteractor>(),
@@ -56,6 +59,8 @@ class MailboxBindings extends Bindings {
Get.find<AppToast>(), Get.find<AppToast>(),
Get.find<ImagePaths>(), Get.find<ImagePaths>(),
Get.find<ResponsiveUtils>(), Get.find<ResponsiveUtils>(),
Get.find<TextEditingController>(),
Get.find<FocusNode>(),
Get.find<CachingManager>())); Get.find<CachingManager>()));
} }
} }
@@ -27,8 +27,11 @@ import 'package:tmail_ui_user/features/mailbox_creator/presentation/model/mailbo
import 'package:tmail_ui_user/features/mailbox_creator/presentation/model/new_mailbox_arguments.dart'; import 'package:tmail_ui_user/features/mailbox_creator/presentation/model/new_mailbox_arguments.dart';
import 'package:tmail_ui_user/features/mailbox_dashboard/domain/state/remove_email_drafts_state.dart'; import 'package:tmail_ui_user/features/mailbox_dashboard/domain/state/remove_email_drafts_state.dart';
import 'package:tmail_ui_user/features/mailbox_dashboard/presentation/mailbox_dashboard_controller.dart'; import 'package:tmail_ui_user/features/mailbox_dashboard/presentation/mailbox_dashboard_controller.dart';
import 'package:tmail_ui_user/features/thread/domain/model/search_query.dart';
import 'package:tmail_ui_user/features/thread/domain/state/mark_as_multiple_email_read_state.dart'; import 'package:tmail_ui_user/features/thread/domain/state/mark_as_multiple_email_read_state.dart';
import 'package:tmail_ui_user/features/thread/domain/state/move_multiple_email_to_mailbox_state.dart'; import 'package:tmail_ui_user/features/thread/domain/state/move_multiple_email_to_mailbox_state.dart';
import 'package:tmail_ui_user/features/thread/presentation/model/search_state.dart';
import 'package:tmail_ui_user/features/thread/presentation/model/search_status.dart';
import 'package:tmail_ui_user/main/localizations/app_localizations.dart'; import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
import 'package:tmail_ui_user/main/routes/app_routes.dart'; import 'package:tmail_ui_user/main/routes/app_routes.dart';
import 'package:tmail_ui_user/main/routes/route_navigation.dart'; import 'package:tmail_ui_user/main/routes/route_navigation.dart';
@@ -47,12 +50,17 @@ class MailboxController extends BaseController {
final AppToast _appToast; final AppToast _appToast;
final ImagePaths _imagePaths; final ImagePaths _imagePaths;
final ResponsiveUtils responsiveUtils; final ResponsiveUtils responsiveUtils;
final TextEditingController searchInputController;
final FocusNode searchFocus;
final CachingManager _cachingManager; final CachingManager _cachingManager;
final defaultMailboxList = <PresentationMailbox>[].obs; final defaultMailboxList = <PresentationMailbox>[].obs;
final folderMailboxNodeList = <MailboxNode>[].obs; final folderMailboxNodeList = <MailboxNode>[].obs;
final searchState = SearchState.initial().obs;
final searchQuery = SearchQuery.initial().obs;
List<PresentationMailbox> allMailboxes = <PresentationMailbox>[]; List<PresentationMailbox> allMailboxes = <PresentationMailbox>[];
List<PresentationMailbox> listMailboxSearched = <PresentationMailbox>[];
jmapState.State? currentMailboxState; jmapState.State? currentMailboxState;
@@ -66,6 +74,8 @@ class MailboxController extends BaseController {
this._appToast, this._appToast,
this._imagePaths, this._imagePaths,
this.responsiveUtils, this.responsiveUtils,
this.searchInputController,
this.searchFocus,
this._cachingManager, this._cachingManager,
); );
@@ -101,6 +111,7 @@ class MailboxController extends BaseController {
@override @override
void onClose() { void onClose() {
mailboxDashBoardController.accountId.close(); mailboxDashBoardController.accountId.close();
searchFocus.dispose();
super.onClose(); super.onClose();
} }
@@ -142,9 +153,11 @@ class MailboxController extends BaseController {
} }
void refreshAllMailbox() { void refreshAllMailbox() {
final accountId = mailboxDashBoardController.accountId.value; if (!isSearchActive()) {
if (accountId != null) { final accountId = mailboxDashBoardController.accountId.value;
consumeState(_getAllMailboxInteractor.execute(accountId)); if (accountId != null) {
consumeState(_getAllMailboxInteractor.execute(accountId));
}
} }
} }
@@ -287,7 +300,28 @@ class MailboxController extends BaseController {
} }
} }
void closeMailboxScreen() { bool isSearchActive() => searchState.value.searchStatus == SearchStatus.ACTIVE;
void enableSearch() => searchState.value = searchState.value.enableSearchState();
void disableSearch(BuildContext context) {
listMailboxSearched.clear();
searchState.value = searchState.value.disableSearchState();
searchQuery.value = SearchQuery.initial();
searchInputController.clear();
FocusScope.of(context).unfocus();
}
void clearSearchText() {
searchQuery.value = SearchQuery.initial();
searchFocus.requestFocus();
}
void searchMailbox(String value) {
searchQuery.value = SearchQuery(value);
}
void closeMailboxScreen(BuildContext context) {
mailboxDashBoardController.closeDrawer(); mailboxDashBoardController.closeDrawer();
} }
@@ -8,6 +8,7 @@ import 'package:tmail_ui_user/features/mailbox/presentation/model/mailbox_node.d
import 'package:tmail_ui_user/features/mailbox/presentation/widgets/mailbox_folder_tile_builder.dart'; import 'package:tmail_ui_user/features/mailbox/presentation/widgets/mailbox_folder_tile_builder.dart';
import 'package:tmail_ui_user/features/mailbox/presentation/widgets/mailbox_tile_builder.dart'; import 'package:tmail_ui_user/features/mailbox/presentation/widgets/mailbox_tile_builder.dart';
import 'package:tmail_ui_user/features/mailbox/presentation/widgets/user_information_widget_builder.dart'; import 'package:tmail_ui_user/features/mailbox/presentation/widgets/user_information_widget_builder.dart';
import 'package:tmail_ui_user/features/thread/presentation/widgets/search_app_bar_widget.dart';
import 'package:tmail_ui_user/features/thread/presentation/widgets/search_bar_thread_view_widget.dart'; import 'package:tmail_ui_user/features/thread/presentation/widgets/search_bar_thread_view_widget.dart';
import 'package:tmail_ui_user/main/localizations/app_localizations.dart'; import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
@@ -33,12 +34,15 @@ class MailboxView extends GetWidget<MailboxController> {
body: Column( body: Column(
children: [ children: [
_buildHeaderMailbox(context), _buildHeaderMailbox(context),
Obx(() => controller.isSearchActive() ? _buildInputSearchFormWidget(context) : SizedBox.shrink()),
Expanded(child: Container( Expanded(child: Container(
color: AppColor.colorBgMailbox, color: controller.isSearchActive() ? Colors.white : AppColor.colorBgMailbox,
child: RefreshIndicator( child: RefreshIndicator(
color: AppColor.primaryColor, color: AppColor.primaryColor,
onRefresh: () async => controller.refreshAllMailbox(), onRefresh: () async => controller.refreshAllMailbox(),
child: _buildListMailbox(context)), child: Obx(() => controller.isSearchActive()
? _buildListMailboxSearched(context, controller.listMailboxSearched)
: _buildListMailbox(context))),
)) ))
] ]
), ),
@@ -75,7 +79,7 @@ class MailboxView extends GetWidget<MailboxController> {
padding: EdgeInsets.only(left: 16, right: 16), padding: EdgeInsets.only(left: 16, right: 16),
child: IconButton( child: IconButton(
key: Key('mailbox_close_button'), key: Key('mailbox_close_button'),
onPressed: () => controller.closeMailboxScreen(), onPressed: () => controller.closeMailboxScreen(context),
icon: SvgPicture.asset(imagePaths.icCloseMailbox, width: 30, height: 30, fit: BoxFit.fill))); icon: SvgPicture.asset(imagePaths.icCloseMailbox, width: 30, height: 30, fit: BoxFit.fill)));
} }
@@ -99,12 +103,12 @@ class MailboxView extends GetWidget<MailboxController> {
.build())); .build()));
} }
Widget _buildSearchFormWidget(BuildContext context) { Widget _buildSearchBarWidget(BuildContext context) {
return Padding( return Padding(
padding: EdgeInsets.only(top: 12), padding: EdgeInsets.only(top: 12),
child: (SearchBarThreadViewWidget(imagePaths) child: (SearchBarThreadViewWidget(imagePaths)
..hintTextSearch(AppLocalizations.of(context).hint_search_mailboxes) ..hintTextSearch(AppLocalizations.of(context).hint_search_mailboxes)
..addOnOpenSearchViewAction(() {})) ..addOnOpenSearchViewAction(() => controller.enableSearch()))
.build()); .build());
} }
@@ -132,7 +136,7 @@ class MailboxView extends GetWidget<MailboxController> {
Padding( Padding(
padding: EdgeInsets.only(top: 16), padding: EdgeInsets.only(top: 16),
child: Divider(color: AppColor.colorDividerMailbox, height: 0.5, thickness: 0.2)), child: Divider(color: AppColor.colorDividerMailbox, height: 0.5, thickness: 0.2)),
_buildSearchFormWidget(context), _buildSearchBarWidget(context),
_buildLoadingView(), _buildLoadingView(),
Obx(() => controller.defaultMailboxList.isNotEmpty Obx(() => controller.defaultMailboxList.isNotEmpty
? Container( ? Container(
@@ -230,5 +234,66 @@ class MailboxView extends GetWidget<MailboxController> {
.toList(); .toList();
} }
// Widget _buildStorageWidget(BuildContext context) => StorageWidgetBuilder(context).build(); Widget _buildInputSearchFormWidget(BuildContext context) {
return Padding(
padding: EdgeInsets.only(top: 16, bottom: 16),
child: Row(
children: [
_buildBackSearchButton(context),
Expanded(child: (SearchAppBarWidget(
imagePaths,
controller.searchQuery.value,
controller.searchFocus,
controller.searchInputController,
hasBackButton: false,
hasSearchButton: true)
..addPadding(EdgeInsets.zero)
..setMargin(EdgeInsets.only(right: 16))
..addDecoration(BoxDecoration(borderRadius: BorderRadius.circular(12), color: AppColor.colorBgSearchBar))
..addIconClearText(SvgPicture.asset(imagePaths.icClearTextSearch, width: 20, height: 20, fit: BoxFit.fill))
..setHintText(AppLocalizations.of(context).hint_search_mailboxes)
..addOnCancelSearchPressed(() => controller.disableSearch(context))
..addOnClearTextSearchAction(() => controller.clearSearchText())
..addOnTextChangeSearchAction((query) => controller.searchMailbox(query))
..addOnSearchTextAction((query) => controller.searchMailbox(query)))
.build())
]
)
);
}
Widget _buildBackSearchButton(BuildContext context) {
return Padding(
padding: EdgeInsets.only(left: 5),
child: Material(
borderRadius: BorderRadius.circular(12),
color: Colors.transparent,
child: IconButton(
color: AppColor.colorTextButton,
icon: SvgPicture.asset(
imagePaths.icBack,
width: 20,
height: 20,
color: AppColor.colorTextButton,
fit: BoxFit.fill),
onPressed: () => controller.disableSearch(context)
)
));
}
Widget _buildListMailboxSearched(BuildContext context, List<PresentationMailbox> listMailbox) {
return ListView.builder(
padding: EdgeInsets.all(8),
key: Key('list_mailbox_searched'),
itemCount: listMailbox.length,
shrinkWrap: true,
primary: false,
itemBuilder: (context, index) =>
Obx(() => (MailboxTileBuilder(
imagePaths,
listMailbox[index],
isLastElement: index == listMailbox.length - 1)
..onOpenMailboxAction((mailbox) => controller.selectMailbox(context, mailbox)))
.build()));
}
} }
@@ -114,6 +114,7 @@ class MailboxCreatorView extends GetWidget<MailboxCreatorController> {
..autoFocus(true) ..autoFocus(true)
..textStyle(TextStyle(color: AppColor.colorNameEmail, fontSize: 16)) ..textStyle(TextStyle(color: AppColor.colorNameEmail, fontSize: 16))
..textDecoration((CreateMailboxNameInputDecorationBuilder() ..textDecoration((CreateMailboxNameInputDecorationBuilder()
..setHintText(AppLocalizations.of(context).hint_input_create_new_mailbox)
..setErrorText(controller.getErrorInputNameString(context))) ..setErrorText(controller.getErrorInputNameString(context)))
.build())) .build()))
.build()) .build())
@@ -1,4 +1,5 @@
import 'package:core/core.dart'; import 'package:core/core.dart';
import 'package:flutter/cupertino.dart';
import 'package:get/get.dart'; import 'package:get/get.dart';
import 'package:shared_preferences/shared_preferences.dart'; import 'package:shared_preferences/shared_preferences.dart';
import 'package:tmail_ui_user/features/base/base_bindings.dart'; import 'package:tmail_ui_user/features/base/base_bindings.dart';
@@ -28,6 +28,8 @@ class MailboxDashBoardController extends BaseController {
final AppToast _appToast; final AppToast _appToast;
final ImagePaths _imagePaths; final ImagePaths _imagePaths;
final RemoveEmailDraftsInteractor _removeEmailDraftsInteractor; final RemoveEmailDraftsInteractor _removeEmailDraftsInteractor;
final TextEditingController searchInputController;
final FocusNode searchFocus;
final scaffoldKey = GlobalKey<ScaffoldState>(); final scaffoldKey = GlobalKey<ScaffoldState>();
final selectedMailbox = Rxn<PresentationMailbox>(); final selectedMailbox = Rxn<PresentationMailbox>();
@@ -37,8 +39,6 @@ class MailboxDashBoardController extends BaseController {
final searchState = SearchState.initial().obs; final searchState = SearchState.initial().obs;
final suggestionSearch = <String>[].obs; final suggestionSearch = <String>[].obs;
TextEditingController searchInputController = TextEditingController();
FocusNode searchFocus = FocusNode();
SearchQuery? searchQuery; SearchQuery? searchQuery;
Session? sessionCurrent; Session? sessionCurrent;
Map<Role, MailboxId> mapDefaultMailboxId = Map(); Map<Role, MailboxId> mapDefaultMailboxId = Map();
@@ -48,6 +48,8 @@ class MailboxDashBoardController extends BaseController {
this._getUserProfileInteractor, this._getUserProfileInteractor,
this._appToast, this._appToast,
this._imagePaths, this._imagePaths,
this.searchInputController,
this.searchFocus,
this._removeEmailDraftsInteractor, this._removeEmailDraftsInteractor,
); );
@@ -176,14 +178,14 @@ class MailboxDashBoardController extends BaseController {
void disableSearch() { void disableSearch() {
searchState.value = searchState.value.disableSearchState(); searchState.value = searchState.value.disableSearchState();
searchQuery = SearchQuery(''); searchQuery = SearchQuery.initial();
clearSuggestionSearch(); clearSuggestionSearch();
searchInputController.clear(); searchInputController.clear();
FocusManager.instance.primaryFocus?.unfocus(); FocusManager.instance.primaryFocus?.unfocus();
} }
void clearSearchText() { void clearSearchText() {
searchQuery = SearchQuery(''); searchQuery = SearchQuery.initial();
clearSuggestionSearch(); clearSuggestionSearch();
searchFocus.requestFocus(); searchFocus.requestFocus();
} }
@@ -200,11 +202,11 @@ class MailboxDashBoardController extends BaseController {
} }
} }
void searchEmail(String value) { void searchEmail(BuildContext context, String value) {
searchQuery = SearchQuery(value); searchQuery = SearchQuery(value);
dispatchState(Right(SearchEmailNewQuery(searchQuery ?? SearchQuery('')))); dispatchState(Right(SearchEmailNewQuery(searchQuery ?? SearchQuery.initial())));
clearSuggestionSearch(); clearSuggestionSearch();
FocusManager.instance.primaryFocus?.unfocus(); FocusScope.of(context).unfocus();
} }
void _saveEmailAsDraftsSuccess(SaveEmailAsDraftsSuccess success) { void _saveEmailAsDraftsSuccess(SaveEmailAsDraftsSuccess success) {
@@ -6,6 +6,10 @@ class SearchQuery with EquatableMixin {
SearchQuery(this.value); SearchQuery(this.value);
factory SearchQuery.initial() {
return SearchQuery('');
}
@override @override
List<Object?> get props => [value]; List<Object?> get props => [value];
} }
@@ -128,17 +128,18 @@ class ThreadView extends GetWidget<ThreadController> {
Widget _buildSearchForm(BuildContext context) { Widget _buildSearchForm(BuildContext context) {
return (SearchAppBarWidget( return (SearchAppBarWidget(
context,
imagePaths, imagePaths,
controller.searchQuery, controller.searchQuery,
controller.mailboxDashBoardController.suggestionSearch,
controller.mailboxDashBoardController.searchFocus, controller.mailboxDashBoardController.searchFocus,
controller.mailboxDashBoardController.searchInputController) controller.mailboxDashBoardController.searchInputController,
suggestionSearch: controller.mailboxDashBoardController.suggestionSearch,)
..addDecoration(BoxDecoration(color: Colors.white)) ..addDecoration(BoxDecoration(color: Colors.white))
..setMargin(EdgeInsets.only(right: 10))
..setHintText(AppLocalizations.of(context).search_mail)
..addOnCancelSearchPressed(() => controller.disableSearch()) ..addOnCancelSearchPressed(() => controller.disableSearch())
..addOnClearTextSearchAction(() => controller.mailboxDashBoardController.clearSearchText()) ..addOnClearTextSearchAction(() => controller.mailboxDashBoardController.clearSearchText())
..addOnSuggestionSearchQuery((query) => controller.mailboxDashBoardController.addSuggestionSearch(query)) ..addOnTextChangeSearchAction((query) => controller.mailboxDashBoardController.addSuggestionSearch(query))
..addOnSearchTextAction((query) => controller.mailboxDashBoardController.searchEmail(query))) ..addOnSearchTextAction((query) => controller.mailboxDashBoardController.searchEmail(context, query)))
.build(); .build();
} }
@@ -409,7 +410,8 @@ class ThreadView extends GetWidget<ThreadController> {
context, context,
imagePaths, imagePaths,
controller.mailboxDashBoardController.suggestionSearch) controller.mailboxDashBoardController.suggestionSearch)
..addOnSelectedSuggestion((suggestion) => controller.mailboxDashBoardController.searchEmail(suggestion))) ..addOnSelectedSuggestion((suggestion) =>
controller.mailboxDashBoardController.searchEmail(context, suggestion)))
.build() .build()
: SizedBox.shrink() : SizedBox.shrink()
); );
@@ -3,45 +3,51 @@ import 'package:core/core.dart';
import 'package:flutter/material.dart'; import 'package:flutter/material.dart';
import 'package:flutter_svg/flutter_svg.dart'; import 'package:flutter_svg/flutter_svg.dart';
import 'package:tmail_ui_user/features/thread/domain/model/search_query.dart'; import 'package:tmail_ui_user/features/thread/domain/model/search_query.dart';
import 'package:tmail_ui_user/main/localizations/app_localizations.dart';
typedef OnCancelSearchPressed = Function(); typedef OnCancelSearchPressed = Function();
typedef OnClearTextSearchAction = Function(); typedef OnClearTextSearchAction = Function();
typedef OnSuggestionSearchQuery = Function(String); typedef OnTextChangeSearchAction = Function(String);
typedef OnSearchTextAction = Function(String); typedef OnSearchTextAction = Function(String);
class SearchAppBarWidget { class SearchAppBarWidget {
OnCancelSearchPressed? _onCancelSearchPressed; OnCancelSearchPressed? _onCancelSearchPressed;
OnSuggestionSearchQuery? _onSuggestionSearchQuery; OnTextChangeSearchAction? _onTextChangeSearchAction;
OnClearTextSearchAction? _onClearTextSearchAction; OnClearTextSearchAction? _onClearTextSearchAction;
OnSearchTextAction? _onSearchTextAction; OnSearchTextAction? _onSearchTextAction;
final BuildContext _context;
final ImagePaths _imagePaths; final ImagePaths _imagePaths;
final SearchQuery? _searchQuery; final SearchQuery? _searchQuery;
final TextEditingController? _searchInputController; final TextEditingController? _searchInputController;
final FocusNode? _searchFocusNode; final FocusNode? _searchFocusNode;
final List<String>? _suggestionSearch; final List<String>? suggestionSearch;
final bool hasBackButton;
final bool hasSearchButton;
double? _heightSearchBar; double? _heightSearchBar;
Decoration? _decoration; Decoration? _decoration;
EdgeInsets? _padding; EdgeInsets? _padding;
EdgeInsets? _margin;
String? _hintText;
Widget? _iconClearText;
SearchAppBarWidget( SearchAppBarWidget(
this._context,
this._imagePaths, this._imagePaths,
this._searchQuery, this._searchQuery,
this._suggestionSearch,
this._searchFocusNode, this._searchFocusNode,
this._searchInputController, this._searchInputController,
{
this.hasBackButton = true,
this.suggestionSearch,
this.hasSearchButton = false,
}
); );
void addOnCancelSearchPressed(OnCancelSearchPressed onCancelSearchPressed) { void addOnCancelSearchPressed(OnCancelSearchPressed onCancelSearchPressed) {
_onCancelSearchPressed = onCancelSearchPressed; _onCancelSearchPressed = onCancelSearchPressed;
} }
void addOnSuggestionSearchQuery(OnSuggestionSearchQuery onSuggestionSearchQuery) { void addOnTextChangeSearchAction(OnTextChangeSearchAction onTextChangeSearchAction) {
_onSuggestionSearchQuery = onSuggestionSearchQuery; _onTextChangeSearchAction = onTextChangeSearchAction;
} }
void addOnClearTextSearchAction(OnClearTextSearchAction onClearTextSearchAction) { void addOnClearTextSearchAction(OnClearTextSearchAction onClearTextSearchAction) {
@@ -64,6 +70,18 @@ class SearchAppBarWidget {
_padding = padding; _padding = padding;
} }
void setMargin(EdgeInsets margin) {
_margin = margin;
}
void setHintText(String text) {
_hintText = text;
}
void addIconClearText(Widget? icon) {
_iconClearText = icon;
}
Widget build() { Widget build() {
return Container( return Container(
key: Key('search_app_bar_widget'), key: Key('search_app_bar_widget'),
@@ -71,15 +89,16 @@ class SearchAppBarWidget {
height: _heightSearchBar, height: _heightSearchBar,
decoration: _decoration, decoration: _decoration,
padding: _padding ?? EdgeInsets.symmetric(vertical: 8), padding: _padding ?? EdgeInsets.symmetric(vertical: 8),
margin: _margin,
child: MediaQuery( child: MediaQuery(
data: MediaQueryData(padding: EdgeInsets.zero), data: MediaQueryData(padding: EdgeInsets.zero),
child: Row( child: Row(
crossAxisAlignment: CrossAxisAlignment.center,
mainAxisAlignment: MainAxisAlignment.center, mainAxisAlignment: MainAxisAlignment.center,
children: [ children: [
_buildBackButton(), if (hasBackButton) _buildBackButton(),
if (hasSearchButton) _buildSearchButton(),
Expanded(child: _buildSearchInputForm()), Expanded(child: _buildSearchInputForm()),
if (_suggestionSearch?.isNotEmpty == true || (_searchQuery != null && _searchQuery!.value.isNotEmpty)) if (suggestionSearch?.isNotEmpty == true || (_searchQuery != null && _searchQuery!.value.isNotEmpty))
_buildClearTextSearchButton(), _buildClearTextSearchButton(),
] ]
) )
@@ -109,56 +128,47 @@ class SearchAppBarWidget {
return Material( return Material(
borderRadius: BorderRadius.circular(12), borderRadius: BorderRadius.circular(12),
color: Colors.transparent, color: Colors.transparent,
child: Padding( child: IconButton(
padding: EdgeInsets.only(right: 8), padding: EdgeInsets.zero,
child: IconButton( icon: _iconClearText ?? SvgPicture.asset(_imagePaths.icComposerClose, fit: BoxFit.fill),
color: AppColor.baseTextColor,
icon: SvgPicture.asset(_imagePaths.icComposerClose, color: AppColor.baseTextColor, fit: BoxFit.fill),
onPressed: () { onPressed: () {
_searchInputController?.clear(); _searchInputController?.clear();
if (_onClearTextSearchAction != null) { _onClearTextSearchAction?.call();
_onClearTextSearchAction!();
}
} }
))); )
);
} }
Widget _buildSearchInputForm() { Widget _buildSearchInputForm() {
return (TextFieldBuilder() return (TextFieldBuilder()
..key(Key('search_input_form')) ..key(Key('search_input_form'))
..textInputAction(TextInputAction.done) ..textInputAction(TextInputAction.done)
..onChange((value) { ..onChange((value) => _onTextChangeSearchAction?.call(value))
if (_onSuggestionSearchQuery != null) { ..onSubmitted((value) => _onSearchTextAction?.call(value))
_onSuggestionSearchQuery!(value); ..cursorColor(AppColor.colorTextButton)
}})
..onSubmitted((value) {
if (_onSearchTextAction != null) {
_onSearchTextAction!(value);
}})
..cursorColor(AppColor.baseTextColor)
..autoFocus(true) ..autoFocus(true)
..addFocusNode(_searchFocusNode) ..addFocusNode(_searchFocusNode)
..textStyle(TextStyle( ..textStyle(TextStyle(color: AppColor.colorNameEmail, fontSize: 17))
color: _searchQuery != null && _searchQuery!.value.isNotEmpty && _suggestionSearch?.isEmpty == true
? AppColor.nameUserColor
: AppColor.baseTextColor,
fontSize: 15,
fontWeight: FontWeight.w500))
..textDecoration(InputDecoration( ..textDecoration(InputDecoration(
border: InputBorder.none, border: InputBorder.none,
focusedBorder: InputBorder.none, focusedBorder: InputBorder.none,
enabledBorder: InputBorder.none, enabledBorder: InputBorder.none,
contentPadding: EdgeInsets.symmetric(vertical: 15), contentPadding: EdgeInsets.symmetric(vertical: 7),
hintText: AppLocalizations.of(_context).search_mail, hintText: _hintText,
hintStyle: TextStyle( hintStyle: TextStyle(color: AppColor.colorHintSearchBar, fontSize: 17.0),
color: AppColor.baseTextColor, labelStyle: TextStyle(color: AppColor.colorHintSearchBar, fontSize: 17.0)))
fontWeight: FontWeight.w500,
fontSize: 15.0),
labelStyle: TextStyle(
color: AppColor.baseTextColor,
fontWeight: FontWeight.w500,
fontSize: 15.0)))
..addController(_searchInputController)) ..addController(_searchInputController))
.build(); .build();
} }
Widget _buildSearchButton() {
return Material(
borderRadius: BorderRadius.circular(12),
color: Colors.transparent,
child: IconButton(
icon: SvgPicture.asset(_imagePaths.icSearchBar, width: 18, height: 18, fit: BoxFit.fill),
onPressed: () => _onSearchTextAction?.call(_searchInputController?.text ?? '')
)
);
}
} }
@@ -73,7 +73,6 @@ class SearchBarThreadViewWidget {
child: Padding( child: Padding(
padding: EdgeInsets.only(left: 2), padding: EdgeInsets.only(left: 2),
child: IconButton( child: IconButton(
color: AppColor.appColor,
icon: SvgPicture.asset(_imagePaths.icSearchBar, width: 18, height: 18, fit: BoxFit.fill), icon: SvgPicture.asset(_imagePaths.icSearchBar, width: 18, height: 18, fit: BoxFit.fill),
onPressed: () => _onOpenSearchViewAction?.call() onPressed: () => _onOpenSearchViewAction?.call()
) )
@@ -75,7 +75,7 @@ class SuggestionBoxWidget {
'"${_listData[index]}"', '"${_listData[index]}"',
maxLines: 1, maxLines: 1,
overflow: TextOverflow.ellipsis, overflow: TextOverflow.ellipsis,
style: TextStyle(fontSize: 15, color: AppColor.nameUserColor, fontWeight: FontWeight.w500), style: TextStyle(fontSize: 15, color: AppColor.colorNameEmail),
)) ))
], ],
) )
@@ -663,4 +663,11 @@ class AppLocalizations {
name: 'discard' name: 'discard'
); );
} }
String get hint_input_create_new_mailbox {
return Intl.message(
'Enter name of mailbox',
name: 'hint_input_create_new_mailbox'
);
}
} }