From 89e8a4aaa41ea30e17e5b487c015197718ae45dc Mon Sep 17 00:00:00 2001 From: dab246 Date: Thu, 28 Sep 2023 16:05:39 +0700 Subject: [PATCH] TF-2118 Set width/height for drop zone view (cherry picked from commit f4d844b636750f413f0b65fab78d5f00e6a8d424) --- .../presentation/composer_view_web.dart | 352 +++++++++--------- .../view/web/web_editor_view.dart | 16 + .../widgets/web/web_editor_widget.dart | 26 +- 3 files changed, 223 insertions(+), 171 deletions(-) diff --git a/lib/features/composer/presentation/composer_view_web.dart b/lib/features/composer/presentation/composer_view_web.dart index a6457b483..b81584db0 100644 --- a/lib/features/composer/presentation/composer_view_web.dart +++ b/lib/features/composer/presentation/composer_view_web.dart @@ -1,6 +1,7 @@ import 'package:core/presentation/resources/image_paths.dart'; import 'package:core/presentation/utils/responsive_utils.dart'; import 'package:core/presentation/views/responsive/responsive_widget.dart'; +import 'package:core/utils/app_logger.dart'; import 'package:file_picker/file_picker.dart'; import 'package:flutter/material.dart'; import 'package:get/get.dart'; @@ -145,44 +146,49 @@ class ComposerView extends GetWidget { padding: ComposerStyle.mobileSubjectPadding, margin: ComposerStyle.mobileSubjectMargin, ), - Obx(() => Expanded( - child: Stack( - children: [ - Padding( - padding: ComposerStyle.mobileEditorPadding, - child: WebEditorView( - editorController: controller.richTextWebController.editorController, - arguments: controller.composerArguments.value, - contentViewState: controller.emailContentsViewState.value, - currentWebContent: controller.textEditorWeb, - onInitial: controller.handleInitHtmlEditorWeb, - onChangeContent: controller.onChangeTextEditorWeb, - onFocus: controller.handleOnFocusHtmlEditorWeb, - onUnFocus: controller.handleOnUnFocusHtmlEditorWeb, - onMouseDown: controller.handleOnMouseDownHtmlEditorWeb, - onEditorSettings: controller.richTextWebController.onEditorSettingsChange, - onImageUploadSuccessAction: (fileUpload) => controller.handleImageUploadSuccess(context, fileUpload), - onImageUploadFailureAction: (fileUpload, base64Str, uploadError) { - return controller.handleImageUploadFailure( - context: context, - uploadError: uploadError, - fileUpload: fileUpload, - base64Str: base64Str, - ); - } + Expanded( + child: LayoutBuilder(builder: (context, constraints) { + log('ComposerView::build:mobile:constraints: $constraints'); + return Stack( + children: [ + Padding( + padding: ComposerStyle.mobileEditorPadding, + child: Obx(() => WebEditorView( + editorController: controller.richTextWebController.editorController, + arguments: controller.composerArguments.value, + contentViewState: controller.emailContentsViewState.value, + currentWebContent: controller.textEditorWeb, + onInitial: controller.handleInitHtmlEditorWeb, + onChangeContent: controller.onChangeTextEditorWeb, + onFocus: controller.handleOnFocusHtmlEditorWeb, + onUnFocus: controller.handleOnUnFocusHtmlEditorWeb, + onMouseDown: controller.handleOnMouseDownHtmlEditorWeb, + onEditorSettings: controller.richTextWebController.onEditorSettingsChange, + onImageUploadSuccessAction: (fileUpload) => controller.handleImageUploadSuccess(context, fileUpload), + onImageUploadFailureAction: (fileUpload, base64Str, uploadError) { + return controller.handleImageUploadFailure( + context: context, + uploadError: uploadError, + fileUpload: fileUpload, + base64Str: base64Str, + ); + }, + width: constraints.maxWidth, + height: constraints.maxHeight, + )), ), - ), - Obx(() => Align( - alignment: AlignmentDirectional.topCenter, - child: InsertImageLoadingBarWidget( - uploadInlineViewState: controller.uploadController.uploadInlineViewState.value, - viewState: controller.viewState.value, - padding: ComposerStyle.insertImageLoadingBarPadding, + Align( + alignment: AlignmentDirectional.topCenter, + child: Obx(() => InsertImageLoadingBarWidget( + uploadInlineViewState: controller.uploadController.uploadInlineViewState.value, + viewState: controller.viewState.value, + padding: ComposerStyle.insertImageLoadingBarPadding, + )), ), - )), - ], - ), - )), + ], + ); + }), + ), Obx(() { if (controller.uploadController.listUploadAttachments.isNotEmpty) { return AttachmentComposerWidget( @@ -321,75 +327,80 @@ class ComposerView extends GetWidget { ), color: ComposerStyle.backgroundEditorColor ), - child: Stack( - children: [ - Column( - children: [ - Obx(() => Expanded( - child: Padding( - padding: ComposerStyle.desktopEditorPadding, - child: WebEditorView( - editorController: controller.richTextWebController.editorController, - arguments: controller.composerArguments.value, - contentViewState: controller.emailContentsViewState.value, - currentWebContent: controller.textEditorWeb, - onInitial: controller.handleInitHtmlEditorWeb, - onChangeContent: controller.onChangeTextEditorWeb, - onFocus: controller.handleOnFocusHtmlEditorWeb, - onUnFocus: controller.handleOnUnFocusHtmlEditorWeb, - onMouseDown: controller.handleOnMouseDownHtmlEditorWeb, - onEditorSettings: controller.richTextWebController.onEditorSettingsChange, - onImageUploadSuccessAction: (fileUpload) => controller.handleImageUploadSuccess(context, fileUpload), - onImageUploadFailureAction: (fileUpload, base64Str, uploadError) { - return controller.handleImageUploadFailure( - context: context, - uploadError: uploadError, - fileUpload: fileUpload, - base64Str: base64Str, - ); - } + child: LayoutBuilder(builder: (context, constraints) { + log('ComposerView::build:desktop:constraints: $constraints'); + return Stack( + children: [ + Column( + children: [ + Expanded( + child: Padding( + padding: ComposerStyle.desktopEditorPadding, + child: Obx(() => WebEditorView( + editorController: controller.richTextWebController.editorController, + arguments: controller.composerArguments.value, + contentViewState: controller.emailContentsViewState.value, + currentWebContent: controller.textEditorWeb, + onInitial: controller.handleInitHtmlEditorWeb, + onChangeContent: controller.onChangeTextEditorWeb, + onFocus: controller.handleOnFocusHtmlEditorWeb, + onUnFocus: controller.handleOnUnFocusHtmlEditorWeb, + onMouseDown: controller.handleOnMouseDownHtmlEditorWeb, + onEditorSettings: controller.richTextWebController.onEditorSettingsChange, + onImageUploadSuccessAction: (fileUpload) => controller.handleImageUploadSuccess(context, fileUpload), + onImageUploadFailureAction: (fileUpload, base64Str, uploadError) { + return controller.handleImageUploadFailure( + context: context, + uploadError: uploadError, + fileUpload: fileUpload, + base64Str: base64Str, + ); + }, + width: constraints.maxWidth, + height: constraints.maxHeight, + )), ), ), - )), - Obx(() { - if (controller.uploadController.listUploadAttachments.isNotEmpty) { - return AttachmentComposerWidget( - listFileUploaded: controller.uploadController.listUploadAttachments, - isCollapsed: controller.isAttachmentCollapsed, - onDeleteAttachmentAction: (fileState) => controller.deleteAttachmentUploaded(fileState.uploadTaskId), - onToggleExpandAttachmentAction: (isCollapsed) => controller.isAttachmentCollapsed = isCollapsed, - ); - } else { - return const SizedBox.shrink(); - } - }), - Obx(() { - if (controller.richTextWebController.isFormattingOptionsEnabled) { - return ToolbarRichTextWebBuilder( - richTextWebController: controller.richTextWebController, - padding: ComposerStyle.richToolbarPadding, - decoration: const BoxDecoration( - color: ComposerStyle.richToolbarColor, - boxShadow: ComposerStyle.richToolbarShadow - ), - ); - } else { - return const SizedBox.shrink(); - } - }) - ], - ), - Obx(() => Align( - alignment: AlignmentDirectional.topCenter, - child: InsertImageLoadingBarWidget( - uploadInlineViewState: controller.uploadController.uploadInlineViewState.value, - viewState: controller.viewState.value, - padding: ComposerStyle.insertImageLoadingBarPadding, + Obx(() { + if (controller.uploadController.listUploadAttachments.isNotEmpty) { + return AttachmentComposerWidget( + listFileUploaded: controller.uploadController.listUploadAttachments, + isCollapsed: controller.isAttachmentCollapsed, + onDeleteAttachmentAction: (fileState) => controller.deleteAttachmentUploaded(fileState.uploadTaskId), + onToggleExpandAttachmentAction: (isCollapsed) => controller.isAttachmentCollapsed = isCollapsed, + ); + } else { + return const SizedBox.shrink(); + } + }), + Obx(() { + if (controller.richTextWebController.isFormattingOptionsEnabled) { + return ToolbarRichTextWebBuilder( + richTextWebController: controller.richTextWebController, + padding: ComposerStyle.richToolbarPadding, + decoration: const BoxDecoration( + color: ComposerStyle.richToolbarColor, + boxShadow: ComposerStyle.richToolbarShadow + ), + ); + } else { + return const SizedBox.shrink(); + } + }) + ], ), - )), - ], - ), - ) + Align( + alignment: AlignmentDirectional.topCenter, + child: Obx(() => InsertImageLoadingBarWidget( + uploadInlineViewState: controller.uploadController.uploadInlineViewState.value, + viewState: controller.viewState.value, + padding: ComposerStyle.insertImageLoadingBarPadding, + )), + ), + ], + ); + }), + ), ), Obx(() => BottomBarComposerWidget( isCodeViewEnabled: controller.richTextWebController.codeViewEnabled, @@ -523,75 +534,80 @@ class ComposerView extends GetWidget { ), color: ComposerStyle.backgroundEditorColor ), - child: Stack( - children: [ - Column( - children: [ - Obx(() => Expanded( - child: Padding( - padding: ComposerStyle.tabletEditorPadding, - child: WebEditorView( - editorController: controller.richTextWebController.editorController, - arguments: controller.composerArguments.value, - contentViewState: controller.emailContentsViewState.value, - currentWebContent: controller.textEditorWeb, - onInitial: controller.handleInitHtmlEditorWeb, - onChangeContent: controller.onChangeTextEditorWeb, - onFocus: controller.handleOnFocusHtmlEditorWeb, - onUnFocus: controller.handleOnUnFocusHtmlEditorWeb, - onMouseDown: controller.handleOnMouseDownHtmlEditorWeb, - onEditorSettings: controller.richTextWebController.onEditorSettingsChange, - onImageUploadSuccessAction: (fileUpload) => controller.handleImageUploadSuccess(context, fileUpload), - onImageUploadFailureAction: (fileUpload, base64Str, uploadError) { - return controller.handleImageUploadFailure( - context: context, - uploadError: uploadError, - fileUpload: fileUpload, - base64Str: base64Str, - ); - } + child: LayoutBuilder(builder: (context, constraints) { + log('ComposerView::build:tablet:constraints: $constraints'); + return Stack( + children: [ + Column( + children: [ + Expanded( + child: Padding( + padding: ComposerStyle.tabletEditorPadding, + child: Obx(() => WebEditorView( + editorController: controller.richTextWebController.editorController, + arguments: controller.composerArguments.value, + contentViewState: controller.emailContentsViewState.value, + currentWebContent: controller.textEditorWeb, + onInitial: controller.handleInitHtmlEditorWeb, + onChangeContent: controller.onChangeTextEditorWeb, + onFocus: controller.handleOnFocusHtmlEditorWeb, + onUnFocus: controller.handleOnUnFocusHtmlEditorWeb, + onMouseDown: controller.handleOnMouseDownHtmlEditorWeb, + onEditorSettings: controller.richTextWebController.onEditorSettingsChange, + onImageUploadSuccessAction: (fileUpload) => controller.handleImageUploadSuccess(context, fileUpload), + onImageUploadFailureAction: (fileUpload, base64Str, uploadError) { + return controller.handleImageUploadFailure( + context: context, + uploadError: uploadError, + fileUpload: fileUpload, + base64Str: base64Str, + ); + }, + width: constraints.maxWidth, + height: constraints.maxHeight, + )), ), ), - )), - Obx(() { - if (controller.uploadController.listUploadAttachments.isNotEmpty) { - return AttachmentComposerWidget( - listFileUploaded: controller.uploadController.listUploadAttachments, - isCollapsed: controller.isAttachmentCollapsed, - onDeleteAttachmentAction: (fileState) => controller.deleteAttachmentUploaded(fileState.uploadTaskId), - onToggleExpandAttachmentAction: (isCollapsed) => controller.isAttachmentCollapsed = isCollapsed, - ); - } else { - return const SizedBox.shrink(); - } - }), - Obx(() { - if (controller.richTextWebController.isFormattingOptionsEnabled) { - return ToolbarRichTextWebBuilder( - richTextWebController: controller.richTextWebController, - padding: ComposerStyle.richToolbarPadding, - decoration: const BoxDecoration( - color: ComposerStyle.richToolbarColor, - boxShadow: ComposerStyle.richToolbarShadow - ), - ); - } else { - return const SizedBox.shrink(); - } - }) - ], - ), - Obx(() => Align( - alignment: AlignmentDirectional.topCenter, - child: InsertImageLoadingBarWidget( - uploadInlineViewState: controller.uploadController.uploadInlineViewState.value, - viewState: controller.viewState.value, - padding: ComposerStyle.insertImageLoadingBarPadding, + Obx(() { + if (controller.uploadController.listUploadAttachments.isNotEmpty) { + return AttachmentComposerWidget( + listFileUploaded: controller.uploadController.listUploadAttachments, + isCollapsed: controller.isAttachmentCollapsed, + onDeleteAttachmentAction: (fileState) => controller.deleteAttachmentUploaded(fileState.uploadTaskId), + onToggleExpandAttachmentAction: (isCollapsed) => controller.isAttachmentCollapsed = isCollapsed, + ); + } else { + return const SizedBox.shrink(); + } + }), + Obx(() { + if (controller.richTextWebController.isFormattingOptionsEnabled) { + return ToolbarRichTextWebBuilder( + richTextWebController: controller.richTextWebController, + padding: ComposerStyle.richToolbarPadding, + decoration: const BoxDecoration( + color: ComposerStyle.richToolbarColor, + boxShadow: ComposerStyle.richToolbarShadow + ), + ); + } else { + return const SizedBox.shrink(); + } + }) + ], ), - )), - ], - ), - ) + Align( + alignment: AlignmentDirectional.topCenter, + child: Obx(() => InsertImageLoadingBarWidget( + uploadInlineViewState: controller.uploadController.uploadInlineViewState.value, + viewState: controller.viewState.value, + padding: ComposerStyle.insertImageLoadingBarPadding, + )), + ), + ], + ); + }), + ), ), Obx(() => BottomBarComposerWidget( isCodeViewEnabled: controller.richTextWebController.codeViewEnabled, diff --git a/lib/features/composer/presentation/view/web/web_editor_view.dart b/lib/features/composer/presentation/view/web/web_editor_view.dart index ff7727b78..c8fa71d01 100644 --- a/lib/features/composer/presentation/view/web/web_editor_view.dart +++ b/lib/features/composer/presentation/view/web/web_editor_view.dart @@ -28,6 +28,8 @@ class WebEditorView extends StatelessWidget with EditorViewMixin { final OnEditorSettingsChange? onEditorSettings; final OnImageUploadSuccessAction? onImageUploadSuccessAction; final OnImageUploadFailureAction? onImageUploadFailureAction; + final double? width; + final double? height; const WebEditorView({ super.key, @@ -43,6 +45,8 @@ class WebEditorView extends StatelessWidget with EditorViewMixin { this.onEditorSettings, this.onImageUploadSuccessAction, this.onImageUploadFailureAction, + this.width, + this.height, }); @override @@ -67,6 +71,8 @@ class WebEditorView extends StatelessWidget with EditorViewMixin { onEditorSettings: onEditorSettings, onImageUploadSuccessAction: onImageUploadSuccessAction, onImageUploadFailureAction: onImageUploadFailureAction, + width: width, + height: height, ); case EmailActionType.editDraft: case EmailActionType.editSendingEmail: @@ -88,6 +94,8 @@ class WebEditorView extends StatelessWidget with EditorViewMixin { onEditorSettings: onEditorSettings, onImageUploadSuccessAction: onImageUploadSuccessAction, onImageUploadFailureAction: onImageUploadFailureAction, + width: width, + height: height, ), (success) { if (success is GetEmailContentLoading) { @@ -111,6 +119,8 @@ class WebEditorView extends StatelessWidget with EditorViewMixin { onEditorSettings: onEditorSettings, onImageUploadSuccessAction: onImageUploadSuccessAction, onImageUploadFailureAction: onImageUploadFailureAction, + width: width, + height: height, ); } } @@ -141,6 +151,8 @@ class WebEditorView extends StatelessWidget with EditorViewMixin { onEditorSettings: onEditorSettings, onImageUploadSuccessAction: onImageUploadSuccessAction, onImageUploadFailureAction: onImageUploadFailureAction, + width: width, + height: height, ); }, (success) { @@ -167,6 +179,8 @@ class WebEditorView extends StatelessWidget with EditorViewMixin { onEditorSettings: onEditorSettings, onImageUploadSuccessAction: onImageUploadSuccessAction, onImageUploadFailureAction: onImageUploadFailureAction, + width: width, + height: height, ); } } @@ -184,6 +198,8 @@ class WebEditorView extends StatelessWidget with EditorViewMixin { onEditorSettings: onEditorSettings, onImageUploadSuccessAction: onImageUploadSuccessAction, onImageUploadFailureAction: onImageUploadFailureAction, + width: width, + height: height, ); } } diff --git a/lib/features/composer/presentation/widgets/web/web_editor_widget.dart b/lib/features/composer/presentation/widgets/web/web_editor_widget.dart index f2dd73275..1cb67cbe3 100644 --- a/lib/features/composer/presentation/widgets/web/web_editor_widget.dart +++ b/lib/features/composer/presentation/widgets/web/web_editor_widget.dart @@ -24,6 +24,8 @@ class WebEditorWidget extends StatefulWidget { final OnEditorSettingsChange? onEditorSettings; final OnImageUploadSuccessAction? onImageUploadSuccessAction; final OnImageUploadFailureAction? onImageUploadFailureAction; + final double? width; + final double? height; const WebEditorWidget({ super.key, @@ -38,6 +40,8 @@ class WebEditorWidget extends StatefulWidget { this.onEditorSettings, this.onImageUploadSuccessAction, this.onImageUploadFailureAction, + this.width, + this.height, }); @override @@ -46,12 +50,24 @@ class WebEditorWidget extends StatefulWidget { class _WebEditorState extends State { + static const double _offsetHeight = 50; + static const double _offsetWidth = 90; + late HtmlEditorController _editorController; + double? dropZoneWidth; + double? dropZoneHeight; @override void initState() { - _editorController = widget.editorController; super.initState(); + _editorController = widget.editorController; + if (widget.height != null) { + dropZoneHeight = widget.height! - _offsetHeight; + } + if (widget.width != null) { + dropZoneWidth = widget.width! - _offsetWidth; + } + log('_WebEditorState::initState:dropZoneWidth: $dropZoneWidth | dropZoneHeight: $dropZoneHeight'); } @override @@ -77,9 +93,13 @@ class _WebEditorState extends State { ), htmlToolbarOptions: const HtmlToolbarOptions( toolbarType: ToolbarType.hide, - defaultToolbarButtons: [] + defaultToolbarButtons: [], + ), + otherOptions: OtherOptions( + height: 550, + dropZoneWidth: dropZoneWidth, + dropZoneHeight: dropZoneHeight, ), - otherOptions: const OtherOptions(height: 550), callbacks: Callbacks( onBeforeCommand: widget.onChangeContent, onChangeContent: widget.onChangeContent,