From 3932d0661d571a2683bc903ffbc63e20d23b950c Mon Sep 17 00:00:00 2001 From: "Lucas.Xu" Date: Mon, 12 Dec 2022 15:10:38 +0800 Subject: [PATCH] feat: update emoji picker UI --- .../lib/plugins/document/document_page.dart | 9 +- .../selection_menu_service.dart | 8 +- .../lib/src/emoji_picker/emoji_menu_item.dart | 88 ++++++++----------- 3 files changed, 46 insertions(+), 59 deletions(-) diff --git a/frontend/app_flowy/lib/plugins/document/document_page.dart b/frontend/app_flowy/lib/plugins/document/document_page.dart index 0120f06e8a..52e223c982 100644 --- a/frontend/app_flowy/lib/plugins/document/document_page.dart +++ b/frontend/app_flowy/lib/plugins/document/document_page.dart @@ -1,6 +1,3 @@ -import 'package:app_flowy/plugins/document/editor_styles.dart'; -import 'package:app_flowy/startup/startup.dart'; -import 'package:app_flowy/plugins/document/presentation/banner.dart'; import 'package:appflowy_editor/appflowy_editor.dart'; import 'package:appflowy_editor_plugins/appflowy_editor_plugins.dart'; import 'package:flowy_infra_ui/widget/error_page.dart'; @@ -8,7 +5,11 @@ import 'package:flowy_sdk/protobuf/flowy-folder/view.pb.dart'; import 'package:flutter/material.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:intl/intl.dart'; + +import '../../startup/startup.dart'; import 'application/doc_bloc.dart'; +import 'editor_styles.dart'; +import 'presentation/banner.dart'; class DocumentPage extends StatefulWidget { final VoidCallback onDeleted; @@ -123,6 +124,8 @@ class _DocumentPageState extends State { mathEquationMenuItem, // Code Block codeBlockMenuItem, + // Emoji + emojiMenuItem, ], themeData: theme.copyWith(extensions: [ ...theme.extensions.values, diff --git a/frontend/app_flowy/packages/appflowy_editor/lib/src/render/selection_menu/selection_menu_service.dart b/frontend/app_flowy/packages/appflowy_editor/lib/src/render/selection_menu/selection_menu_service.dart index 37cd410488..01a14524ac 100644 --- a/frontend/app_flowy/packages/appflowy_editor/lib/src/render/selection_menu/selection_menu_service.dart +++ b/frontend/app_flowy/packages/appflowy_editor/lib/src/render/selection_menu/selection_menu_service.dart @@ -80,16 +80,16 @@ class SelectionMenu implements SelectionMenuService { // show above offset = topRight - menuOffset; showBelow = false; - _alignment = Alignment.topRight; + _alignment = Alignment.topLeft; } _topLeft = offset; - _offset = Offset(offset.dx, showBelow ? offset.dy : MediaQuery.of(context).size.height - offset.dy); + _offset = Offset(offset.dx, + showBelow ? offset.dy : MediaQuery.of(context).size.height - offset.dy); _selectionMenuEntry = OverlayEntry(builder: (context) { return Positioned( top: showBelow ? _offset.dy : null, - bottom: - showBelow ? null : _offset.dy, + bottom: showBelow ? null : _offset.dy, left: offset.dx, child: SelectionMenuWidget( items: [ diff --git a/frontend/app_flowy/packages/appflowy_editor_plugins/lib/src/emoji_picker/emoji_menu_item.dart b/frontend/app_flowy/packages/appflowy_editor_plugins/lib/src/emoji_picker/emoji_menu_item.dart index 0868d4c7d0..6ecd09328d 100644 --- a/frontend/app_flowy/packages/appflowy_editor_plugins/lib/src/emoji_picker/emoji_menu_item.dart +++ b/frontend/app_flowy/packages/appflowy_editor_plugins/lib/src/emoji_picker/emoji_menu_item.dart @@ -1,23 +1,21 @@ - import 'package:appflowy_editor/appflowy_editor.dart'; import 'package:flutter/material.dart'; import 'package:flutter/services.dart'; import 'emoji_picker.dart'; -SelectionMenuItem emojiMenuItem = - SelectionMenuItem( - name: () => 'emoji', - icon: (editorState, onSelected) => Icon( - Icons.emoji_emotions_outlined, - color: onSelected - ? editorState.editorStyle.selectionMenuItemSelectedIconColor - : editorState.editorStyle.selectionMenuItemIconColor, - size: 18.0, - ), - keywords: ['emoji'], - handler: _showEmojiSelectionMenu, - ); +SelectionMenuItem emojiMenuItem = SelectionMenuItem( + name: () => 'emoji', + icon: (editorState, onSelected) => Icon( + Icons.emoji_emotions_outlined, + color: onSelected + ? editorState.editorStyle.selectionMenuItemSelectedIconColor + : editorState.editorStyle.selectionMenuItemIconColor, + size: 18.0, + ), + keywords: ['emoji'], + handler: _showEmojiSelectionMenu, +); OverlayEntry? _emojiSelectionMenu; EditorState? _editorState; @@ -33,9 +31,8 @@ void _showEmojiSelectionMenu( _emojiSelectionMenu?.remove(); _emojiSelectionMenu = OverlayEntry(builder: (context) { return Positioned( - top: aligment == Alignment.bottomRight ? offset.dy : null, - bottom: - aligment == Alignment.topRight ? offset.dy : null, + top: aligment == Alignment.bottomLeft ? offset.dy : null, + bottom: aligment == Alignment.topLeft ? offset.dy : null, left: offset.dx, child: Material( child: EmojiSelectionMenu( @@ -73,19 +70,19 @@ class EmojiSelectionMenu extends StatefulWidget { Key? key, required this.onSubmitted, required this.onExit, - this.editorState, + required this.editorState, }) : super(key: key); final void Function(Emoji emoji) onSubmitted; final void Function() onExit; - final EditorState? editorState; + final EditorState editorState; @override State createState() => _EmojiSelectionMenuState(); } class _EmojiSelectionMenuState extends State { - EditorStyle? get style => widget.editorState?.editorStyle; + EditorStyle get style => widget.editorState.editorStyle; @override void initState() { @@ -119,9 +116,9 @@ class _EmojiSelectionMenuState extends State { Widget build(BuildContext context) { return Container( width: 300, - padding: const EdgeInsets.all(24.0), + padding: const EdgeInsets.all(8.0), decoration: BoxDecoration( - color: style?.selectionMenuBackgroundColor ?? Colors.white, + color: style.selectionMenuBackgroundColor, boxShadow: [ BoxShadow( blurRadius: 5, @@ -129,45 +126,26 @@ class _EmojiSelectionMenuState extends State { color: Colors.black.withOpacity(0.1), ), ], - // borderRadius: BorderRadius.circular(6.0), - ), - child: Column( - crossAxisAlignment: CrossAxisAlignment.start, - children: [ - _buildHeader(context), - // FlowyEmojiStyleButton(normalIcon: '', tooltipText: ''), - const SizedBox(height: 10.0), - _buildEmojiBox(context), - ], - ), - ); - } - - Widget _buildHeader(BuildContext context) { - return Text( - 'Pick Emoji', - textAlign: TextAlign.left, - style: TextStyle( - fontSize: 14.0, - color: style?.selectionMenuItemTextColor ?? Colors.black, - fontWeight: FontWeight.w500, + borderRadius: BorderRadius.circular(6.0), ), + child: _buildEmojiBox(context), ); } Widget _buildEmojiBox(BuildContext context) { return SizedBox( - height: 300, + height: 200, child: EmojiPicker( onEmojiSelected: (category, emoji) => widget.onSubmitted(emoji), - config: const Config( + config: Config( columns: 8, emojiSizeMax: 28, - bgColor: Color(0xffF2F2F2), + bgColor: + style.selectionMenuBackgroundColor ?? const Color(0xffF2F2F2), iconColor: Colors.grey, - iconColorSelected: Color(0xff333333), - indicatorColor: Color(0xff333333), - progressIndicatorColor: Color(0xff333333), + iconColorSelected: const Color(0xff333333), + indicatorColor: const Color(0xff333333), + progressIndicatorColor: const Color(0xff333333), buttonMode: ButtonMode.CUPERTINO, initCategory: Category.RECENT, ), @@ -181,12 +159,18 @@ extension on EditorState { final selectionService = service.selectionService; final currentSelection = selectionService.currentSelection.value; final nodes = selectionService.currentSelectedNodes; - if (currentSelection == null || !currentSelection.isCollapsed || nodes.first is! TextNode) { + if (currentSelection == null || + !currentSelection.isCollapsed || + nodes.first is! TextNode) { return; } final textNode = nodes.first as TextNode; final tr = transaction; - tr.insertText(textNode, currentSelection.endIndex, emoji.emoji,); + tr.insertText( + textNode, + currentSelection.endIndex, + emoji.emoji, + ); apply(tr); } }