diff --git a/frontend/app_flowy/lib/workspace/application/grid/cell/url_cell_bloc.dart b/frontend/app_flowy/lib/workspace/application/grid/cell/url_cell_bloc.dart index 609c625001..e1fe39c3bf 100644 --- a/frontend/app_flowy/lib/workspace/application/grid/cell/url_cell_bloc.dart +++ b/frontend/app_flowy/lib/workspace/application/grid/cell/url_cell_bloc.dart @@ -24,6 +24,9 @@ class URLCellBloc extends Bloc { url: cellData?.url ?? "", )); }, + updateURL: (String url) { + cellContext.saveCellData(url, deduplicate: true); + }, ); }, ); @@ -53,6 +56,7 @@ class URLCellBloc extends Bloc { @freezed class URLCellEvent with _$URLCellEvent { const factory URLCellEvent.initial() = _InitialCell; + const factory URLCellEvent.updateURL(String url) = _UpdateURL; const factory URLCellEvent.didReceiveCellUpdate(URLCellData? cell) = _DidReceiveCellUpdate; } diff --git a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/cell_builder.dart b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/cell_builder.dart index 9a1911f003..8bfab28f65 100755 --- a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/cell_builder.dart +++ b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/cell_builder.dart @@ -1,5 +1,6 @@ import 'package:app_flowy/workspace/application/grid/cell/cell_service/cell_service.dart'; import 'package:flowy_sdk/protobuf/flowy-grid-data-model/grid.pb.dart' show FieldType; +import 'package:flutter/services.dart'; import 'package:flutter/widgets.dart'; import 'package:app_flowy/workspace/presentation/plugins/grid/src/widgets/row/grid_row.dart'; import 'package:flowy_infra/theme.dart'; @@ -69,6 +70,15 @@ abstract class GridCellState extends State { @override void initState() { widget.beginFocus.setListener(() => requestBeginFocus()); + widget.shortcutHandlers[CellKeyboardKey.onCopy] = () => onCopy(); + widget.shortcutHandlers[CellKeyboardKey.onInsert] = () { + Clipboard.getData("text/plain").then((data) { + final s = data?.text; + if (s is String) { + onInsert(s); + } + }); + }; super.initState(); } @@ -87,6 +97,10 @@ abstract class GridCellState extends State { } void requestBeginFocus(); + + String? onCopy() => null; + + void onInsert(String value) {} } abstract class GridFocusNodeCellState extends GridCellState { diff --git a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/cell_shortcuts.dart b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/cell_shortcuts.dart index 2146c939d2..f4f222f219 100644 --- a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/cell_shortcuts.dart +++ b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/cell_shortcuts.dart @@ -88,7 +88,7 @@ class GridCellInsertAction extends Action { @override void invoke(covariant GridCellInsertIntent intent) { - final callback = child.shortcutHandlers[CellKeyboardKey.onEnter]; + final callback = child.shortcutHandlers[CellKeyboardKey.onInsert]; if (callback != null) { callback(); } diff --git a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/checkbox_cell.dart b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/checkbox_cell.dart index 21f44bf2ab..384d85737f 100644 --- a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/checkbox_cell.dart +++ b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/checkbox_cell.dart @@ -5,7 +5,6 @@ import 'package:flowy_infra_ui/style_widget/icon_button.dart'; import 'package:flutter/widgets.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'cell_builder.dart'; -import 'cell_shortcuts.dart'; class CheckboxCell extends GridCellWidget { final GridCellContextBuilder cellContextBuilder; @@ -25,13 +24,6 @@ class _CheckboxCellState extends GridCellState { void initState() { final cellContext = widget.cellContextBuilder.build(); _cellBloc = getIt(param1: cellContext)..add(const CheckboxCellEvent.initial()); - widget.shortcutHandlers[CellKeyboardKey.onCopy] = () { - if (_cellBloc.state.isSelected) { - return "Yes"; - } else { - return "No"; - } - }; super.initState(); } @@ -66,4 +58,13 @@ class _CheckboxCellState extends GridCellState { void requestBeginFocus() { _cellBloc.add(const CheckboxCellEvent.select()); } + + @override + String? onCopy() { + if (_cellBloc.state.isSelected) { + return "Yes"; + } else { + return "No"; + } + } } diff --git a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/date_cell/date_cell.dart b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/date_cell/date_cell.dart index ecc297e4c4..eb382a0971 100644 --- a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/date_cell/date_cell.dart +++ b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/date_cell/date_cell.dart @@ -1,4 +1,3 @@ -import 'package:app_flowy/workspace/presentation/plugins/grid/src/widgets/cell/cell_shortcuts.dart'; import 'package:flowy_infra_ui/style_widget/text.dart'; import 'package:flutter/widgets.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; @@ -36,17 +35,16 @@ class DateCell extends GridCellWidget { } @override - State createState() => _DateCellState(); + GridCellState createState() => _DateCellState(); } -class _DateCellState extends State { +class _DateCellState extends GridCellState { late DateCellBloc _cellBloc; @override void initState() { final cellContext = widget.cellContextBuilder.build(); _cellBloc = getIt(param1: cellContext)..add(const DateCellEvent.initial()); - widget.shortcutHandlers[CellKeyboardKey.onCopy] = () => _cellBloc.state.dateStr; super.initState(); } @@ -91,4 +89,10 @@ class _DateCellState extends State { _cellBloc.close(); super.dispose(); } + + @override + void requestBeginFocus() {} + + @override + String? onCopy() => _cellBloc.state.dateStr; } diff --git a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/number_cell.dart b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/number_cell.dart index 3983a7d3c3..7d16b16ef0 100644 --- a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/number_cell.dart +++ b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/number_cell.dart @@ -1,12 +1,10 @@ import 'dart:async'; - import 'package:app_flowy/startup/startup.dart'; import 'package:app_flowy/workspace/application/grid/prelude.dart'; import 'package:flutter/material.dart'; import 'package:flutter_bloc/flutter_bloc.dart'; import 'cell_builder.dart'; -import 'cell_shortcuts.dart'; class NumberCell extends GridCellWidget { final GridCellContextBuilder cellContextBuilder; @@ -30,9 +28,6 @@ class _NumberCellState extends GridFocusNodeCellState { final cellContext = widget.cellContextBuilder.build(); _cellBloc = getIt(param1: cellContext)..add(const NumberCellEvent.initial()); _controller = TextEditingController(text: contentFromState(_cellBloc.state)); - widget.shortcutHandlers[CellKeyboardKey.onCopy] = () { - return _cellBloc.state.content.fold((content) => content, (r) => null); - }; super.initState(); } @@ -85,4 +80,14 @@ class _NumberCellState extends GridFocusNodeCellState { String contentFromState(NumberCellState state) { return state.content.fold((l) => l, (r) => ""); } + + @override + String? onCopy() { + return _cellBloc.state.content.fold((content) => content, (r) => null); + } + + @override + void onInsert(String value) { + _cellBloc.add(NumberCellEvent.updateCell(value)); + } } diff --git a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/text_cell.dart b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/text_cell.dart index 48b5628bbd..1bece5a3d7 100644 --- a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/text_cell.dart +++ b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/text_cell.dart @@ -4,7 +4,6 @@ import 'package:flutter_bloc/flutter_bloc.dart'; import 'package:app_flowy/startup/startup.dart'; import 'package:app_flowy/workspace/application/grid/prelude.dart'; import 'cell_builder.dart'; -import 'cell_shortcuts.dart'; class GridTextCellStyle extends GridCellStyle { String? placeholder; @@ -44,8 +43,6 @@ class _GridTextCellState extends GridFocusNodeCellState { _cellBloc = getIt(param1: cellContext); _cellBloc.add(const TextCellEvent.initial()); _controller = TextEditingController(text: _cellBloc.state.content); - - widget.shortcutHandlers[CellKeyboardKey.onCopy] = () => _cellBloc.state.content; super.initState(); } @@ -95,4 +92,12 @@ class _GridTextCellState extends GridFocusNodeCellState { }); } } + + @override + String? onCopy() => _cellBloc.state.content; + + @override + void onInsert(String value) { + _cellBloc.add(TextCellEvent.updateText(value)); + } } diff --git a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/url_cell/cell_editor.dart b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/url_cell/cell_editor.dart index 15af124749..f4da18be86 100644 --- a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/url_cell/cell_editor.dart +++ b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/url_cell/cell_editor.dart @@ -8,7 +8,8 @@ import 'package:flutter_bloc/flutter_bloc.dart'; class URLCellEditor extends StatefulWidget with FlowyOverlayDelegate { final GridURLCellContext cellContext; - const URLCellEditor({required this.cellContext, Key? key}) : super(key: key); + final VoidCallback completed; + const URLCellEditor({required this.cellContext, required this.completed, Key? key}) : super(key: key); @override State createState() => _URLCellEditorState(); @@ -16,10 +17,12 @@ class URLCellEditor extends StatefulWidget with FlowyOverlayDelegate { static void show( BuildContext context, GridURLCellContext cellContext, + VoidCallback completed, ) { FlowyOverlay.of(context).remove(identifier()); final editor = URLCellEditor( cellContext: cellContext, + completed: completed, ); // @@ -46,6 +49,11 @@ class URLCellEditor extends StatefulWidget with FlowyOverlayDelegate { bool asBarrier() { return true; } + + @override + void didRemove() { + completed(); + } } class _URLCellEditorState extends State { diff --git a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/url_cell/url_cell.dart b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/url_cell/url_cell.dart index 4b4e671901..b3e9c3c919 100644 --- a/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/url_cell/url_cell.dart +++ b/frontend/app_flowy/lib/workspace/presentation/plugins/grid/src/widgets/cell/url_cell/url_cell.dart @@ -3,7 +3,6 @@ import 'package:app_flowy/generated/locale_keys.g.dart'; import 'package:app_flowy/workspace/application/grid/cell/url_cell_bloc.dart'; import 'package:app_flowy/workspace/presentation/home/toast.dart'; import 'package:app_flowy/workspace/presentation/plugins/grid/src/widgets/cell/cell_accessory.dart'; -import 'package:app_flowy/workspace/presentation/plugins/grid/src/widgets/cell/cell_shortcuts.dart'; import 'package:easy_localization/easy_localization.dart'; import 'package:flowy_infra/image.dart'; import 'package:flowy_infra/theme.dart'; @@ -87,8 +86,6 @@ class _GridURLCellState extends GridCellState { final cellContext = widget.cellContextBuilder.build() as GridURLCellContext; _cellBloc = URLCellBloc(cellContext: cellContext); _cellBloc.add(const URLCellEvent.initial()); - - widget.shortcutHandlers[CellKeyboardKey.onCopy] = () => _cellBloc.state.content; super.initState(); } @@ -134,10 +131,13 @@ class _GridURLCellState extends GridCellState { Future _openUrlOrEdit(String url) async { final uri = Uri.parse(url); if (url.isNotEmpty && await canLaunchUrl(uri)) { + widget.isFocus.value = false; await launchUrl(uri); } else { final cellContext = widget.cellContextBuilder.build() as GridURLCellContext; - URLCellEditor.show(context, cellContext); + URLCellEditor.show(context, cellContext, () { + widget.isFocus.value = false; + }); } } @@ -145,6 +145,14 @@ class _GridURLCellState extends GridCellState { void requestBeginFocus() { _openUrlOrEdit(_cellBloc.state.url); } + + @override + String? onCopy() => _cellBloc.state.content; + + @override + void onInsert(String value) { + _cellBloc.add(URLCellEvent.updateURL(value)); + } } class _EditURLAccessory extends StatelessWidget with GridCellAccessory { @@ -164,7 +172,7 @@ class _EditURLAccessory extends StatelessWidget with GridCellAccessory { @override void onTap() { - URLCellEditor.show(anchorContext, cellContext); + URLCellEditor.show(anchorContext, cellContext, () {}); } }