|
@@ -1,5 +1,6 @@
|
|
import 'package:appflowy_editor/src/editor_state.dart';
|
|
import 'package:appflowy_editor/src/editor_state.dart';
|
|
import 'package:appflowy_editor/src/infra/flowy_svg.dart';
|
|
import 'package:appflowy_editor/src/infra/flowy_svg.dart';
|
|
|
|
+import 'package:appflowy_editor/src/render/image/image_upload_widget.dart';
|
|
import 'package:appflowy_editor/src/render/rich_text/rich_text_style.dart';
|
|
import 'package:appflowy_editor/src/render/rich_text/rich_text_style.dart';
|
|
import 'package:appflowy_editor/src/render/selection_menu/selection_menu_widget.dart';
|
|
import 'package:appflowy_editor/src/render/selection_menu/selection_menu_widget.dart';
|
|
import 'package:appflowy_editor/src/service/default_text_operations/format_rich_text_style.dart';
|
|
import 'package:appflowy_editor/src/service/default_text_operations/format_rich_text_style.dart';
|
|
@@ -23,6 +24,7 @@ class SelectionMenu implements SelectionMenuService {
|
|
|
|
|
|
OverlayEntry? _selectionMenuEntry;
|
|
OverlayEntry? _selectionMenuEntry;
|
|
bool _selectionUpdateByInner = false;
|
|
bool _selectionUpdateByInner = false;
|
|
|
|
+ Offset? _topLeft;
|
|
|
|
|
|
@override
|
|
@override
|
|
void dismiss() {
|
|
void dismiss() {
|
|
@@ -53,6 +55,7 @@ class SelectionMenu implements SelectionMenuService {
|
|
return;
|
|
return;
|
|
}
|
|
}
|
|
final offset = selectionRects.first.bottomRight + const Offset(10, 10);
|
|
final offset = selectionRects.first.bottomRight + const Offset(10, 10);
|
|
|
|
+ _topLeft = offset;
|
|
|
|
|
|
_selectionMenuEntry = OverlayEntry(builder: (context) {
|
|
_selectionMenuEntry = OverlayEntry(builder: (context) {
|
|
return Positioned(
|
|
return Positioned(
|
|
@@ -84,8 +87,9 @@ class SelectionMenu implements SelectionMenuService {
|
|
}
|
|
}
|
|
|
|
|
|
@override
|
|
@override
|
|
- // TODO: implement topLeft
|
|
|
|
- Offset get topLeft => throw UnimplementedError();
|
|
|
|
|
|
+ Offset get topLeft {
|
|
|
|
+ return _topLeft ?? Offset.zero;
|
|
|
|
+ }
|
|
|
|
|
|
void _onSelectionChange() {
|
|
void _onSelectionChange() {
|
|
// workaround: SelectionService has been released after hot reload.
|
|
// workaround: SelectionService has been released after hot reload.
|
|
@@ -115,7 +119,7 @@ final List<SelectionMenuItem> _defaultSelectionMenuItems = [
|
|
name: 'Text',
|
|
name: 'Text',
|
|
icon: _selectionMenuIcon('text'),
|
|
icon: _selectionMenuIcon('text'),
|
|
keywords: ['text'],
|
|
keywords: ['text'],
|
|
- handler: (editorState, menuService) {
|
|
|
|
|
|
+ handler: (editorState, _, __) {
|
|
insertTextNodeAfterSelection(editorState, {});
|
|
insertTextNodeAfterSelection(editorState, {});
|
|
},
|
|
},
|
|
),
|
|
),
|
|
@@ -123,7 +127,7 @@ final List<SelectionMenuItem> _defaultSelectionMenuItems = [
|
|
name: 'Heading 1',
|
|
name: 'Heading 1',
|
|
icon: _selectionMenuIcon('h1'),
|
|
icon: _selectionMenuIcon('h1'),
|
|
keywords: ['heading 1, h1'],
|
|
keywords: ['heading 1, h1'],
|
|
- handler: (editorState, menuService) {
|
|
|
|
|
|
+ handler: (editorState, _, __) {
|
|
insertHeadingAfterSelection(editorState, StyleKey.h1);
|
|
insertHeadingAfterSelection(editorState, StyleKey.h1);
|
|
},
|
|
},
|
|
),
|
|
),
|
|
@@ -131,7 +135,7 @@ final List<SelectionMenuItem> _defaultSelectionMenuItems = [
|
|
name: 'Heading 2',
|
|
name: 'Heading 2',
|
|
icon: _selectionMenuIcon('h2'),
|
|
icon: _selectionMenuIcon('h2'),
|
|
keywords: ['heading 2, h2'],
|
|
keywords: ['heading 2, h2'],
|
|
- handler: (editorState, menuService) {
|
|
|
|
|
|
+ handler: (editorState, _, __) {
|
|
insertHeadingAfterSelection(editorState, StyleKey.h2);
|
|
insertHeadingAfterSelection(editorState, StyleKey.h2);
|
|
},
|
|
},
|
|
),
|
|
),
|
|
@@ -139,15 +143,21 @@ final List<SelectionMenuItem> _defaultSelectionMenuItems = [
|
|
name: 'Heading 3',
|
|
name: 'Heading 3',
|
|
icon: _selectionMenuIcon('h3'),
|
|
icon: _selectionMenuIcon('h3'),
|
|
keywords: ['heading 3, h3'],
|
|
keywords: ['heading 3, h3'],
|
|
- handler: (editorState, menuService) {
|
|
|
|
|
|
+ handler: (editorState, _, __) {
|
|
insertHeadingAfterSelection(editorState, StyleKey.h3);
|
|
insertHeadingAfterSelection(editorState, StyleKey.h3);
|
|
},
|
|
},
|
|
),
|
|
),
|
|
|
|
+ SelectionMenuItem(
|
|
|
|
+ name: 'Image',
|
|
|
|
+ icon: _selectionMenuIcon('image'),
|
|
|
|
+ keywords: ['image'],
|
|
|
|
+ handler: showImageUploadMenu,
|
|
|
|
+ ),
|
|
SelectionMenuItem(
|
|
SelectionMenuItem(
|
|
name: 'Bulleted list',
|
|
name: 'Bulleted list',
|
|
icon: _selectionMenuIcon('bulleted_list'),
|
|
icon: _selectionMenuIcon('bulleted_list'),
|
|
keywords: ['bulleted list', 'list', 'unordered list'],
|
|
keywords: ['bulleted list', 'list', 'unordered list'],
|
|
- handler: (editorState, menuService) {
|
|
|
|
|
|
+ handler: (editorState, _, __) {
|
|
insertBulletedListAfterSelection(editorState);
|
|
insertBulletedListAfterSelection(editorState);
|
|
},
|
|
},
|
|
),
|
|
),
|
|
@@ -155,7 +165,7 @@ final List<SelectionMenuItem> _defaultSelectionMenuItems = [
|
|
name: 'Checkbox',
|
|
name: 'Checkbox',
|
|
icon: _selectionMenuIcon('checkbox'),
|
|
icon: _selectionMenuIcon('checkbox'),
|
|
keywords: ['todo list', 'list', 'checkbox list'],
|
|
keywords: ['todo list', 'list', 'checkbox list'],
|
|
- handler: (editorState, menuService) {
|
|
|
|
|
|
+ handler: (editorState, _, __) {
|
|
insertCheckboxAfterSelection(editorState);
|
|
insertCheckboxAfterSelection(editorState);
|
|
},
|
|
},
|
|
),
|
|
),
|