[flutter]: fix compile errors after update flutter sdk

This commit is contained in:
appflowy 2021-10-08 18:14:19 +08:00
parent c4a6342c96
commit c4e9fd0697
6 changed files with 248 additions and 167 deletions

View file

@ -2,5 +2,8 @@
"svgviewer.enableautopreview": true, "svgviewer.enableautopreview": true,
"svgviewer.previewcolumn": "Active", "svgviewer.previewcolumn": "Active",
"svgviewer.showzoominout": true, "svgviewer.showzoominout": true,
"editor.wordWrapColumn": 120 "editor.wordWrapColumn": 120,
"editor.minimap.maxColumn": 140,
"prettier.printWidth": 140,
"editor.wordWrap": "wordWrapColumn"
} }

View file

@ -1,32 +1,25 @@
import 'package:flutter/foundation.dart'; import 'package:flutter/foundation.dart';
import 'package:flutter/services.dart'; import 'package:flutter/services.dart';
import 'package:flutter/widgets.dart';
/* --------------------------------- Typedef -------------------------------- */ //fixme workaround flutter MacOS issue https://github.com/flutter/flutter/issues/75595
extension _LogicalKeyboardKeyCaseExt on LogicalKeyboardKey {
static const _kUpperToLowerDist = 0x20;
static final _kLowerCaseA = LogicalKeyboardKey.keyA.keyId;
static final _kLowerCaseZ = LogicalKeyboardKey.keyZ.keyId;
enum InputShortcut { LogicalKeyboardKey toUpperCase() {
CUT, if (keyId < _kLowerCaseA || keyId > _kLowerCaseZ) return this;
COPY, return LogicalKeyboardKey(keyId - _kUpperToLowerDist);
PASTE, }
SELECT_ALL,
SAVE,
} }
enum InputShortcut { CUT, COPY, PASTE, SELECT_ALL, UNDO, REDO }
typedef CursorMoveCallback = void Function( typedef CursorMoveCallback = void Function(
LogicalKeyboardKey key, LogicalKeyboardKey key, bool wordModifier, bool lineModifier, bool shift);
bool wordModifier, typedef InputShortcutCallback = void Function(InputShortcut? shortcut);
bool lineModifier, typedef OnDeleteCallback = void Function(bool forward);
bool shift,
);
typedef InputShortcutCallback = void Function(
InputShortcut? shortcut,
);
typedef OnDeleteCallback = void Function(
bool forward,
);
/* -------------------------------- Listener -------------------------------- */
class FlowyKeyboardListener { class FlowyKeyboardListener {
FlowyKeyboardListener(this.onCursorMove, this.onShortcut, this.onDelete); FlowyKeyboardListener(this.onCursorMove, this.onShortcut, this.onDelete);
@ -35,43 +28,45 @@ class FlowyKeyboardListener {
final InputShortcutCallback onShortcut; final InputShortcutCallback onShortcut;
final OnDeleteCallback onDelete; final OnDeleteCallback onDelete;
static final Set<LogicalKeyboardKey> _moveKeys = { static final Set<LogicalKeyboardKey> _moveKeys = <LogicalKeyboardKey>{
LogicalKeyboardKey.arrowRight,
LogicalKeyboardKey.arrowLeft,
LogicalKeyboardKey.arrowUp, LogicalKeyboardKey.arrowUp,
LogicalKeyboardKey.arrowDown, LogicalKeyboardKey.arrowDown,
LogicalKeyboardKey.arrowLeft,
LogicalKeyboardKey.arrowRight,
}; };
static final Set<LogicalKeyboardKey> _shortcutKeys = { static final Set<LogicalKeyboardKey> _shortcutKeys = <LogicalKeyboardKey>{
LogicalKeyboardKey.keyA, LogicalKeyboardKey.keyA,
LogicalKeyboardKey.keyC, LogicalKeyboardKey.keyC,
LogicalKeyboardKey.keyV, LogicalKeyboardKey.keyV,
LogicalKeyboardKey.keyX, LogicalKeyboardKey.keyX,
LogicalKeyboardKey.keyS, LogicalKeyboardKey.keyZ.toUpperCase(),
LogicalKeyboardKey.keyZ,
LogicalKeyboardKey.delete, LogicalKeyboardKey.delete,
LogicalKeyboardKey.backspace, LogicalKeyboardKey.backspace,
}; };
static final Set<LogicalKeyboardKey> _nonModifierKeys = { static final Set<LogicalKeyboardKey> _nonModifierKeys = <LogicalKeyboardKey>{
..._moveKeys,
..._shortcutKeys, ..._shortcutKeys,
..._moveKeys,
}; };
static final Set<LogicalKeyboardKey> _winModifierKeys = { static final Set<LogicalKeyboardKey> _modifierKeys = <LogicalKeyboardKey>{
LogicalKeyboardKey.shift,
LogicalKeyboardKey.control, LogicalKeyboardKey.control,
LogicalKeyboardKey.alt, LogicalKeyboardKey.alt,
LogicalKeyboardKey.shift,
}; };
static final Set<LogicalKeyboardKey> _osxModifierKeys = { static final Set<LogicalKeyboardKey> _macOsModifierKeys =
<LogicalKeyboardKey>{
LogicalKeyboardKey.shift,
LogicalKeyboardKey.meta, LogicalKeyboardKey.meta,
LogicalKeyboardKey.alt, LogicalKeyboardKey.alt,
LogicalKeyboardKey.shift,
}; };
static final Set<LogicalKeyboardKey> _interestingKeys = { static final Set<LogicalKeyboardKey> _interestingKeys = <LogicalKeyboardKey>{
..._winModifierKeys, ..._modifierKeys,
..._osxModifierKeys, ..._macOsModifierKeys,
..._nonModifierKeys, ..._nonModifierKeys,
}; };
@ -80,66 +75,55 @@ class FlowyKeyboardListener {
LogicalKeyboardKey.keyC: InputShortcut.COPY, LogicalKeyboardKey.keyC: InputShortcut.COPY,
LogicalKeyboardKey.keyV: InputShortcut.PASTE, LogicalKeyboardKey.keyV: InputShortcut.PASTE,
LogicalKeyboardKey.keyA: InputShortcut.SELECT_ALL, LogicalKeyboardKey.keyA: InputShortcut.SELECT_ALL,
LogicalKeyboardKey.keyS: InputShortcut.SAVE,
}; };
bool handleRawKeyEvent(RawKeyEvent event) { KeyEventResult handleRawKeyEvent(RawKeyEvent event) {
if (kIsWeb) { if (kIsWeb) {
// On web platform, we should ignore the key because it's processed already. // On web platform, we ignore the key because it's already processed.
return false; return KeyEventResult.ignored;
}
if (event is! RawKeyDownEvent) {
return false;
} }
final keysPressed = LogicalKeyboardKey.collapseSynonyms(RawKeyboard.instance.keysPressed); if (event is! RawKeyDownEvent) {
return KeyEventResult.ignored;
}
final keysPressed =
LogicalKeyboardKey.collapseSynonyms(RawKeyboard.instance.keysPressed);
final key = event.logicalKey; final key = event.logicalKey;
final isMacOS = event.data is RawKeyEventDataMacOs; final isMacOS = event.data is RawKeyEventDataMacOs;
final modifierKeys = isMacOS ? _osxModifierKeys : _winModifierKeys;
// If any one of below cases is hitten:
// 1. None of the nonModifierKeys is pressed
// 2. Press the key except the keys that trigger shortcut
// We will skip this event
if (!_nonModifierKeys.contains(key) || if (!_nonModifierKeys.contains(key) ||
keysPressed.difference(modifierKeys).length > 1 || keysPressed
.difference(isMacOS ? _macOsModifierKeys : _modifierKeys)
.length >
1 ||
keysPressed.difference(_interestingKeys).isNotEmpty) { keysPressed.difference(_interestingKeys).isNotEmpty) {
return false; return KeyEventResult.ignored;
} }
if (_isCursorMoveAction(key)) { final isShortcutModifierPressed =
isMacOS ? event.isMetaPressed : event.isControlPressed;
if (_moveKeys.contains(key)) {
onCursorMove( onCursorMove(
key, key,
isMacOS ? event.isAltPressed : event.isControlPressed, isMacOS ? event.isAltPressed : event.isControlPressed,
isMacOS ? event.isMetaPressed : event.isAltPressed, isMacOS ? event.isMetaPressed : event.isAltPressed,
event.isShiftPressed, event.isShiftPressed);
); } else if (isShortcutModifierPressed && (_shortcutKeys.contains(key))) {
return true; if (key == LogicalKeyboardKey.keyZ ||
} else if (_isShortcutAction(event, key)) { key == LogicalKeyboardKey.keyZ.toUpperCase()) {
onShortcut(_keyToShortcut[key]); onShortcut(
return true; event.isShiftPressed ? InputShortcut.REDO : InputShortcut.UNDO);
} else if (LogicalKeyboardKey.delete == key) { } else {
onShortcut(_keyToShortcut[key]);
}
} else if (key == LogicalKeyboardKey.delete) {
onDelete(true); onDelete(true);
return true; } else if (key == LogicalKeyboardKey.backspace) {
} else if (LogicalKeyboardKey.backspace == key) {
onDelete(false); onDelete(false);
return true;
}
return false;
}
// Helper
bool _isCursorMoveAction(LogicalKeyboardKey key) => _moveKeys.contains(key);
bool _isShortcutAction(RawKeyEvent event, LogicalKeyboardKey key) {
if (!_shortcutKeys.contains(key)) {
return false;
}
if (event.data is RawKeyEventDataMacOs) {
return event.isMetaPressed;
} else { } else {
return event.isControlPressed; return KeyEventResult.ignored;
} }
return KeyEventResult.handled;
} }
} }

View file

@ -22,7 +22,8 @@ class BaselineProxy extends SingleChildRenderObjectWidget {
} }
@override @override
void updateRenderObject(BuildContext context, covariant RenderBaselineProxy renderObject) { void updateRenderObject(
BuildContext context, covariant RenderBaselineProxy renderObject) {
renderObject renderObject
..textStyle = textStyle! ..textStyle = textStyle!
..padding = padding!; ..padding = padding!;
@ -37,7 +38,8 @@ class EmbedProxy extends SingleChildRenderObjectWidget {
const EmbedProxy(Widget child) : super(child: child); const EmbedProxy(Widget child) : super(child: child);
@override @override
RenderEmbedProxy createRenderObject(BuildContext context) => RenderEmbedProxy(null); RenderEmbedProxy createRenderObject(BuildContext context) =>
RenderEmbedProxy(null);
} }
/* ---------------------------------- Text ---------------------------------- */ /* ---------------------------------- Text ---------------------------------- */
@ -80,7 +82,8 @@ class RichTextProxy extends SingleChildRenderObjectWidget {
} }
@override @override
void updateRenderObject(BuildContext context, covariant RenderParagraphProxy renderObject) { void updateRenderObject(
BuildContext context, covariant RenderParagraphProxy renderObject) {
renderObject renderObject
..textStyle = textStyle ..textStyle = textStyle
..textAlign = textAlign ..textAlign = textAlign

View file

@ -60,7 +60,8 @@ class RawEditor extends StatefulWidget {
this.embedBuilder, this.embedBuilder,
) : assert(maxHeight == null || maxHeight > 0, 'maxHeight cannot be null'), ) : assert(maxHeight == null || maxHeight > 0, 'maxHeight cannot be null'),
assert(minHeight == null || minHeight >= 0, 'minHeight cannot be null'), assert(minHeight == null || minHeight >= 0, 'minHeight cannot be null'),
assert(maxHeight == null || minHeight == null || maxHeight >= minHeight), assert(
maxHeight == null || minHeight == null || maxHeight >= minHeight),
showCursor = showCursor ?? true, showCursor = showCursor ?? true,
super(key: key); super(key: key);
@ -111,7 +112,10 @@ abstract class EditorState extends State<RawEditor> {
} }
class _RawEditorState extends EditorState class _RawEditorState extends EditorState
with AutomaticKeepAliveClientMixin<RawEditor>, WidgetsBindingObserver, TickerProviderStateMixin<RawEditor> with
AutomaticKeepAliveClientMixin<RawEditor>,
WidgetsBindingObserver,
TickerProviderStateMixin<RawEditor>
implements TextSelectionDelegate, TextInputClient { implements TextSelectionDelegate, TextInputClient {
final GlobalKey _editorKey = GlobalKey(); final GlobalKey _editorKey = GlobalKey();
final List<TextEditingValue> _sentRemoteValues = []; final List<TextEditingValue> _sentRemoteValues = [];
@ -129,7 +133,8 @@ class _RawEditorState extends EditorState
bool _didAutoFocus = false; bool _didAutoFocus = false;
bool _keyboardVisible = false; bool _keyboardVisible = false;
DefaultStyles? _styles; DefaultStyles? _styles;
final ClipboardStatusNotifier? _clipboardStatus = kIsWeb ? null : ClipboardStatusNotifier(); final ClipboardStatusNotifier? _clipboardStatus =
kIsWeb ? null : ClipboardStatusNotifier();
final LayerLink _toolbarLayerLink = LayerLink(); final LayerLink _toolbarLayerLink = LayerLink();
final LayerLink _startHandleLayerLink = LayerLink(); final LayerLink _startHandleLayerLink = LayerLink();
final LayerLink _endHandleLayerLink = LayerLink(); final LayerLink _endHandleLayerLink = LayerLink();
@ -177,57 +182,78 @@ class _RawEditorState extends EditorState
downKey = key == LogicalKeyboardKey.arrowDown; downKey = key == LogicalKeyboardKey.arrowDown;
if ((rightKey || leftKey) && !(rightKey && leftKey)) { if ((rightKey || leftKey) && !(rightKey && leftKey)) {
newSelection = newSelection = _jumpToBeginOrEndOfWord(newSelection, wordModifier,
_jumpToBeginOrEndOfWord(newSelection, wordModifier, leftKey, rightKey, plainText, lineModifier, shift); leftKey, rightKey, plainText, lineModifier, shift);
} }
if (downKey || upKey) { if (downKey || upKey) {
newSelection = _handleMovingCursorVertically(upKey, downKey, shift, selection, newSelection, plainText); newSelection = _handleMovingCursorVertically(
upKey, downKey, shift, selection, newSelection, plainText);
} }
if (!shift) { if (!shift) {
newSelection = _placeCollapsedSelection(selection, newSelection, leftKey, rightKey); newSelection =
_placeCollapsedSelection(selection, newSelection, leftKey, rightKey);
} }
widget.controller.updateSelection(newSelection, ChangeSource.LOCAL); widget.controller.updateSelection(newSelection, ChangeSource.LOCAL);
} }
TextSelection _placeCollapsedSelection( TextSelection _placeCollapsedSelection(TextSelection selection,
TextSelection selection, TextSelection newSelection, bool leftKey, bool rightKey) { TextSelection newSelection, bool leftKey, bool rightKey) {
var newOffset = newSelection.extentOffset; var newOffset = newSelection.extentOffset;
if (!selection.isCollapsed) { if (!selection.isCollapsed) {
if (leftKey) { if (leftKey) {
newOffset = newOffset = newSelection.baseOffset < newSelection.extentOffset
newSelection.baseOffset < newSelection.extentOffset ? newSelection.baseOffset : newSelection.extentOffset; ? newSelection.baseOffset
: newSelection.extentOffset;
} else if (rightKey) { } else if (rightKey) {
newOffset = newOffset = newSelection.baseOffset > newSelection.extentOffset
newSelection.baseOffset > newSelection.extentOffset ? newSelection.baseOffset : newSelection.extentOffset; ? newSelection.baseOffset
: newSelection.extentOffset;
} }
} }
return TextSelection.fromPosition(TextPosition(offset: newOffset)); return TextSelection.fromPosition(TextPosition(offset: newOffset));
} }
TextSelection _handleMovingCursorVertically( TextSelection _handleMovingCursorVertically(
bool upKey, bool downKey, bool shift, TextSelection selection, TextSelection newSelection, String plainText) { bool upKey,
final originPosition = TextPosition(offset: upKey ? selection.baseOffset : selection.extentOffset); bool downKey,
bool shift,
TextSelection selection,
TextSelection newSelection,
String plainText) {
final originPosition = TextPosition(
offset: upKey ? selection.baseOffset : selection.extentOffset);
final child = getRenderEditor()!.childAtPosition(originPosition); final child = getRenderEditor()!.childAtPosition(originPosition);
final localPosition = TextPosition(offset: originPosition.offset - child.container.documentOffset); final localPosition = TextPosition(
offset: originPosition.offset - child.container.documentOffset);
var position = upKey ? child.getPositionAbove(localPosition) : child.getPositionBelow(localPosition); var position = upKey
? child.getPositionAbove(localPosition)
: child.getPositionBelow(localPosition);
if (position == null) { if (position == null) {
final sibling = upKey ? getRenderEditor()!.childBefore(child) : getRenderEditor()!.childAfter(child); final sibling = upKey
? getRenderEditor()!.childBefore(child)
: getRenderEditor()!.childAfter(child);
if (sibling == null) { if (sibling == null) {
position = TextPosition(offset: upKey ? 0 : plainText.length - 1); position = TextPosition(offset: upKey ? 0 : plainText.length - 1);
} else { } else {
final finalOffset = Offset(child.getOffsetForCaret(localPosition).dx, final finalOffset = Offset(
sibling.getOffsetForCaret(TextPosition(offset: upKey ? sibling.container.length - 1 : 0)).dy); child.getOffsetForCaret(localPosition).dx,
sibling
.getOffsetForCaret(TextPosition(
offset: upKey ? sibling.container.length - 1 : 0))
.dy);
final siblingPosition = sibling.getPositionForOffset(finalOffset); final siblingPosition = sibling.getPositionForOffset(finalOffset);
position = TextPosition(offset: sibling.container.documentOffset + siblingPosition.offset); position = TextPosition(
offset: sibling.container.documentOffset + siblingPosition.offset);
} }
} else { } else {
position = TextPosition(offset: child.container.documentOffset + position.offset); position = TextPosition(
offset: child.container.documentOffset + position.offset);
} }
if (position.offset == newSelection.extentOffset) { if (position.offset == newSelection.extentOffset) {
@ -250,33 +276,49 @@ class _RawEditorState extends EditorState
return newSelection; return newSelection;
} }
TextSelection _jumpToBeginOrEndOfWord(TextSelection newSelection, bool wordModifier, bool leftKey, bool rightKey, TextSelection _jumpToBeginOrEndOfWord(
String plainText, bool lineModifier, bool shift) { TextSelection newSelection,
bool wordModifier,
bool leftKey,
bool rightKey,
String plainText,
bool lineModifier,
bool shift) {
if (wordModifier) { if (wordModifier) {
if (leftKey) { if (leftKey) {
final textSelection = getRenderEditor()!.selectWordAtPosition( final textSelection = getRenderEditor()!.selectWordAtPosition(
TextPosition(offset: _previousCharacter(newSelection.extentOffset, plainText, false))); TextPosition(
offset: _previousCharacter(
newSelection.extentOffset, plainText, false)));
return newSelection.copyWith(extentOffset: textSelection.baseOffset); return newSelection.copyWith(extentOffset: textSelection.baseOffset);
} }
final textSelection = getRenderEditor()! final textSelection = getRenderEditor()!.selectWordAtPosition(
.selectWordAtPosition(TextPosition(offset: _nextCharacter(newSelection.extentOffset, plainText, false))); TextPosition(
offset:
_nextCharacter(newSelection.extentOffset, plainText, false)));
return newSelection.copyWith(extentOffset: textSelection.extentOffset); return newSelection.copyWith(extentOffset: textSelection.extentOffset);
} else if (lineModifier) { } else if (lineModifier) {
if (leftKey) { if (leftKey) {
final textSelection = getRenderEditor()!.selectLineAtPosition( final textSelection = getRenderEditor()!.selectLineAtPosition(
TextPosition(offset: _previousCharacter(newSelection.extentOffset, plainText, false))); TextPosition(
offset: _previousCharacter(
newSelection.extentOffset, plainText, false)));
return newSelection.copyWith(extentOffset: textSelection.baseOffset); return newSelection.copyWith(extentOffset: textSelection.baseOffset);
} }
final startPoint = newSelection.extentOffset; final startPoint = newSelection.extentOffset;
if (startPoint < plainText.length) { if (startPoint < plainText.length) {
final textSelection = getRenderEditor()!.selectLineAtPosition(TextPosition(offset: startPoint)); final textSelection = getRenderEditor()!
.selectLineAtPosition(TextPosition(offset: startPoint));
return newSelection.copyWith(extentOffset: textSelection.extentOffset); return newSelection.copyWith(extentOffset: textSelection.extentOffset);
} }
return newSelection; return newSelection;
} }
if (rightKey && newSelection.extentOffset < plainText.length) { if (rightKey && newSelection.extentOffset < plainText.length) {
final nextExtent = _nextCharacter(newSelection.extentOffset, plainText, true); final nextExtent =
_nextCharacter(newSelection.extentOffset, plainText, true);
final distance = nextExtent - newSelection.extentOffset; final distance = nextExtent - newSelection.extentOffset;
newSelection = newSelection.copyWith(extentOffset: nextExtent); newSelection = newSelection.copyWith(extentOffset: nextExtent);
if (shift) { if (shift) {
@ -286,7 +328,8 @@ class _RawEditorState extends EditorState
} }
if (leftKey && newSelection.extentOffset > 0) { if (leftKey && newSelection.extentOffset > 0) {
final previousExtent = _previousCharacter(newSelection.extentOffset, plainText, true); final previousExtent =
_previousCharacter(newSelection.extentOffset, plainText, true);
final distance = newSelection.extentOffset - previousExtent; final distance = newSelection.extentOffset - previousExtent;
newSelection = newSelection.copyWith(extentOffset: previousExtent); newSelection = newSelection.copyWith(extentOffset: previousExtent);
if (shift) { if (shift) {
@ -326,7 +369,9 @@ class _RawEditorState extends EditorState
var count = 0; var count = 0;
int? lastNonWhitespace; int? lastNonWhitespace;
for (final currentString in string.characters) { for (final currentString in string.characters) {
if (!includeWhitespace && !WHITE_SPACE.contains(currentString.characters.first.toString().codeUnitAt(0))) { if (!includeWhitespace &&
!WHITE_SPACE.contains(
currentString.characters.first.toString().codeUnitAt(0))) {
lastNonWhitespace = count; lastNonWhitespace = count;
} }
if (count + currentString.length >= index) { if (count + currentString.length >= index) {
@ -337,7 +382,8 @@ class _RawEditorState extends EditorState
return 0; return 0;
} }
bool get hasConnection => _textInputConnection != null && _textInputConnection!.attached; bool get hasConnection =>
_textInputConnection != null && _textInputConnection!.attached;
void openConnectionIfNeeded() { void openConnectionIfNeeded() {
if (!shouldCreateInputConnection) { if (!shouldCreateInputConnection) {
@ -388,7 +434,8 @@ class _RawEditorState extends EditorState
return; return;
} }
final shouldRemember = textEditingValue.text != _lastKnownRemoteTextEditingValue!.text; final shouldRemember =
textEditingValue.text != _lastKnownRemoteTextEditingValue!.text;
_lastKnownRemoteTextEditingValue = actualValue; _lastKnownRemoteTextEditingValue = actualValue;
_textInputConnection!.setEditingState(actualValue); _textInputConnection!.setEditingState(actualValue);
if (shouldRemember) { if (shouldRemember) {
@ -397,7 +444,8 @@ class _RawEditorState extends EditorState
} }
@override @override
TextEditingValue? get currentTextEditingValue => _lastKnownRemoteTextEditingValue; TextEditingValue? get currentTextEditingValue =>
_lastKnownRemoteTextEditingValue;
@override @override
AutofillScope? get currentAutofillScope => null; AutofillScope? get currentAutofillScope => null;
@ -429,7 +477,8 @@ class _RawEditorState extends EditorState
final text = value.text; final text = value.text;
final cursorPosition = value.selection.extentOffset; final cursorPosition = value.selection.extentOffset;
final diff = getDiff(oldText, text, cursorPosition); final diff = getDiff(oldText, text, cursorPosition);
widget.controller.replaceText(diff.start, diff.deleted.length, diff.inserted, value.selection); widget.controller.replaceText(
diff.start, diff.deleted.length, diff.inserted, value.selection);
} }
@override @override
@ -472,6 +521,20 @@ class _RawEditorState extends EditorState
_sentRemoteValues.clear(); _sentRemoteValues.clear();
} }
@override
void copySelection(SelectionChangedCause cause) {}
@override
void cutSelection(SelectionChangedCause cause) {}
@override
Future<void> pasteText(SelectionChangedCause cause) {
return Future(() => {});
}
@override
void selectAll(SelectionChangedCause cause) {}
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
assert(debugCheckHasMediaQuery(context)); assert(debugCheckHasMediaQuery(context));
@ -479,8 +542,11 @@ class _RawEditorState extends EditorState
super.build(context); super.build(context);
var _doc = widget.controller.document; var _doc = widget.controller.document;
if (_doc.isEmpty() && !widget.focusNode.hasFocus && widget.placeholder != null) { if (_doc.isEmpty() &&
_doc = Document.fromJson(jsonDecode('[{"attributes":{"placeholder":true},"insert":"${widget.placeholder}\\n"}]')); !widget.focusNode.hasFocus &&
widget.placeholder != null) {
_doc = Document.fromJson(jsonDecode(
'[{"attributes":{"placeholder":true},"insert":"${widget.placeholder}\\n"}]'));
} }
Widget child = CompositedTransformTarget( Widget child = CompositedTransformTarget(
@ -503,7 +569,8 @@ class _RawEditorState extends EditorState
); );
if (widget.scrollable) { if (widget.scrollable) {
final baselinePadding = EdgeInsets.only(top: _styles!.paragraph!.verticalSpacing.item1); final baselinePadding =
EdgeInsets.only(top: _styles!.paragraph!.verticalSpacing.item1);
child = BaselineProxy( child = BaselineProxy(
textStyle: _styles!.paragraph!.style, textStyle: _styles!.paragraph!.style,
padding: baselinePadding, padding: baselinePadding,
@ -534,7 +601,8 @@ class _RawEditorState extends EditorState
); );
} }
void _handleSelectionChanged(TextSelection selection, SelectionChangedCause cause) { void _handleSelectionChanged(
TextSelection selection, SelectionChangedCause cause) {
widget.controller.updateSelection(selection, ChangeSource.LOCAL); widget.controller.updateSelection(selection, ChangeSource.LOCAL);
_selectionOverlay?.handlesVisible = _shouldShowSelectionHandles(); _selectionOverlay?.handlesVisible = _shouldShowSelectionHandles();
@ -563,7 +631,9 @@ class _RawEditorState extends EditorState
_styles, _styles,
widget.enableInteractiveSelection, widget.enableInteractiveSelection,
_hasFocus, _hasFocus,
attrs.containsKey(Attribute.codeBlock.key) ? const EdgeInsets.all(16) : null, attrs.containsKey(Attribute.codeBlock.key)
? const EdgeInsets.all(16)
: null,
widget.embedBuilder, widget.embedBuilder,
_cursorController, _cursorController,
indentLevelCounts); indentLevelCounts);
@ -575,7 +645,8 @@ class _RawEditorState extends EditorState
return result; return result;
} }
EditableTextLine _getEditableTextLineFromNode(Line node, BuildContext context) { EditableTextLine _getEditableTextLineFromNode(
Line node, BuildContext context) {
final textLine = TextLine( final textLine = TextLine(
line: node, line: node,
textDirection: _textDirection, textDirection: _textDirection,
@ -598,7 +669,8 @@ class _RawEditorState extends EditorState
return editableTextLine; return editableTextLine;
} }
Tuple2<double, double> _getVerticalSpacingForLine(Line line, DefaultStyles? defaultStyles) { Tuple2<double, double> _getVerticalSpacingForLine(
Line line, DefaultStyles? defaultStyles) {
final attrs = line.style.attributes; final attrs = line.style.attributes;
if (attrs.containsKey(Attribute.header.key)) { if (attrs.containsKey(Attribute.header.key)) {
final int? level = attrs[Attribute.header.key]!.value; final int? level = attrs[Attribute.header.key]!.value;
@ -623,7 +695,8 @@ class _RawEditorState extends EditorState
return defaultStyles!.paragraph!.verticalSpacing; return defaultStyles!.paragraph!.verticalSpacing;
} }
Tuple2<double, double> _getVerticalSpacingForBlock(Block node, DefaultStyles? defaultStyles) { Tuple2<double, double> _getVerticalSpacingForBlock(
Block node, DefaultStyles? defaultStyles) {
final attrs = node.style.attributes; final attrs = node.style.attributes;
if (attrs.containsKey(Attribute.quoteBlock.key)) { if (attrs.containsKey(Attribute.quoteBlock.key)) {
return defaultStyles!.quote!.verticalSpacing; return defaultStyles!.quote!.verticalSpacing;
@ -666,7 +739,8 @@ class _RawEditorState extends EditorState
} else { } else {
_keyboardVisibilityController = KeyboardVisibilityController(); _keyboardVisibilityController = KeyboardVisibilityController();
_keyboardVisible = _keyboardVisibilityController!.isVisible; _keyboardVisible = _keyboardVisibilityController!.isVisible;
_keyboardVisibilitySubscription = _keyboardVisibilityController?.onChange.listen((visible) { _keyboardVisibilitySubscription =
_keyboardVisibilityController?.onChange.listen((visible) {
_keyboardVisible = visible; _keyboardVisible = visible;
if (visible) { if (visible) {
_onChangeTextEditingValue(); _onChangeTextEditingValue();
@ -674,13 +748,8 @@ class _RawEditorState extends EditorState
}); });
} }
_focusAttachment = widget.focusNode.attach(context, onKey: (node, event) { _focusAttachment = widget.focusNode.attach(context,
if (_keyboardListener.handleRawKeyEvent(event)) { onKey: (node, event) => _keyboardListener.handleRawKeyEvent(event));
return KeyEventResult.handled;
} else {
return KeyEventResult.ignored;
}
});
widget.focusNode.addListener(_handleFocusChanged); widget.focusNode.addListener(_handleFocusChanged);
} }
@ -689,7 +758,9 @@ class _RawEditorState extends EditorState
super.didChangeDependencies(); super.didChangeDependencies();
final parentStyles = EditorStyles.getStyles(context, true); final parentStyles = EditorStyles.getStyles(context, true);
final defaultStyles = DefaultStyles.getInstance(context); final defaultStyles = DefaultStyles.getInstance(context);
_styles = (parentStyles != null) ? defaultStyles.merge(parentStyles) : defaultStyles; _styles = (parentStyles != null)
? defaultStyles.merge(parentStyles)
: defaultStyles;
if (widget.customStyles != null) { if (widget.customStyles != null) {
_styles = _styles!.merge(widget.customStyles!); _styles = _styles!.merge(widget.customStyles!);
@ -723,13 +794,8 @@ class _RawEditorState extends EditorState
if (widget.focusNode != oldWidget.focusNode) { if (widget.focusNode != oldWidget.focusNode) {
oldWidget.focusNode.removeListener(_handleFocusChanged); oldWidget.focusNode.removeListener(_handleFocusChanged);
_focusAttachment?.detach(); _focusAttachment?.detach();
_focusAttachment = widget.focusNode.attach(context, onKey: (node, event) { _focusAttachment = widget.focusNode.attach(context,
if (_keyboardListener.handleRawKeyEvent(event)) { onKey: (node, event) => _keyboardListener.handleRawKeyEvent(event));
return KeyEventResult.handled;
} else {
return KeyEventResult.ignored;
}
});
widget.focusNode.addListener(_handleFocusChanged); widget.focusNode.addListener(_handleFocusChanged);
updateKeepAlive(); updateKeepAlive();
} }
@ -749,7 +815,8 @@ class _RawEditorState extends EditorState
} }
bool _shouldShowSelectionHandles() { bool _shouldShowSelectionHandles() {
return widget.showSelectionHandles && !widget.controller.selection.isCollapsed; return widget.showSelectionHandles &&
!widget.controller.selection.isCollapsed;
} }
void handleDelete(bool forward) { void handleDelete(bool forward) {
@ -760,7 +827,8 @@ class _RawEditorState extends EditorState
var textAfter = selection.textAfter(plainText); var textAfter = selection.textAfter(plainText);
if (selection.isCollapsed) { if (selection.isCollapsed) {
if (!forward && textBefore.isNotEmpty) { if (!forward && textBefore.isNotEmpty) {
final characterBoundary = _previousCharacter(textBefore.length, textBefore, true); final characterBoundary =
_previousCharacter(textBefore.length, textBefore, true);
textBefore = textBefore.substring(0, characterBoundary); textBefore = textBefore.substring(0, characterBoundary);
cursorPosition = characterBoundary; cursorPosition = characterBoundary;
} }
@ -783,13 +851,24 @@ class _RawEditorState extends EditorState
Future<void> handleShortcut(InputShortcut? shortcut) async { Future<void> handleShortcut(InputShortcut? shortcut) async {
final selection = widget.controller.selection; final selection = widget.controller.selection;
final plainText = textEditingValue.text; final plainText = textEditingValue.text;
if (shortcut == InputShortcut.SAVE) {
widget.controller.save(); if (shortcut == InputShortcut.UNDO) {
if (widget.controller.hasUndo) {
widget.controller.undo();
}
return; return;
} }
if (shortcut == InputShortcut.REDO) {
if (widget.controller.hasRedo) {
widget.controller.redo();
}
return;
}
if (shortcut == InputShortcut.COPY) { if (shortcut == InputShortcut.COPY) {
if (!selection.isCollapsed) { if (!selection.isCollapsed) {
await Clipboard.setData(ClipboardData(text: selection.textInside(plainText))); await Clipboard.setData(
ClipboardData(text: selection.textInside(plainText)));
} }
return; return;
} }
@ -806,7 +885,8 @@ class _RawEditorState extends EditorState
); );
textEditingValue = TextEditingValue( textEditingValue = TextEditingValue(
text: selection.textBefore(plainText) + selection.textAfter(plainText), text:
selection.textBefore(plainText) + selection.textAfter(plainText),
selection: TextSelection.collapsed(offset: selection.start), selection: TextSelection.collapsed(offset: selection.start),
); );
} }
@ -824,7 +904,8 @@ class _RawEditorState extends EditorState
} }
return; return;
} }
if (shortcut == InputShortcut.SELECT_ALL && widget.enableInteractiveSelection) { if (shortcut == InputShortcut.SELECT_ALL &&
widget.enableInteractiveSelection) {
widget.controller.updateSelection( widget.controller.updateSelection(
selection.copyWith( selection.copyWith(
baseOffset: 0, baseOffset: 0,
@ -878,14 +959,16 @@ class _RawEditorState extends EditorState
void _onChangeTextEditingValue() { void _onChangeTextEditingValue() {
_showCaretOnScreen(); _showCaretOnScreen();
updateRemoteValueIfNeeded(); updateRemoteValueIfNeeded();
_cursorController.startOrStopCursorTimerIfNeeded(_hasFocus, widget.controller.selection); _cursorController.startOrStopCursorTimerIfNeeded(
_hasFocus, widget.controller.selection);
if (hasConnection) { if (hasConnection) {
_cursorController _cursorController
..stopCursorTimer(resetCharTicks: false) ..stopCursorTimer(resetCharTicks: false)
..startCursorTimer(); ..startCursorTimer();
} }
SchedulerBinding.instance!.addPostFrameCallback((_) => _updateOrDisposeSelectionOverlayIfNeeded()); SchedulerBinding.instance!.addPostFrameCallback(
(_) => _updateOrDisposeSelectionOverlayIfNeeded());
if (mounted) { if (mounted) {
setState(() { setState(() {
// Use widget.controller.value in build() // Use widget.controller.value in build()
@ -928,7 +1011,8 @@ class _RawEditorState extends EditorState
void _handleFocusChanged() { void _handleFocusChanged() {
openOrCloseConnection(); openOrCloseConnection();
_cursorController.startOrStopCursorTimerIfNeeded(_hasFocus, widget.controller.selection); _cursorController.startOrStopCursorTimerIfNeeded(
_hasFocus, widget.controller.selection);
_updateOrDisposeSelectionOverlayIfNeeded(); _updateOrDisposeSelectionOverlayIfNeeded();
if (_hasFocus) { if (_hasFocus) {
WidgetsBinding.instance!.addObserver(this); WidgetsBinding.instance!.addObserver(this);
@ -959,7 +1043,8 @@ class _RawEditorState extends EditorState
_showCaretOnScreenScheduled = false; _showCaretOnScreenScheduled = false;
final viewport = RenderAbstractViewport.of(getRenderEditor())!; final viewport = RenderAbstractViewport.of(getRenderEditor())!;
final editorOffset = getRenderEditor()!.localToGlobal(const Offset(0, 0), ancestor: viewport); final editorOffset = getRenderEditor()!
.localToGlobal(const Offset(0, 0), ancestor: viewport);
final offsetInViewport = _scrollController!.offset + editorOffset.dy; final offsetInViewport = _scrollController!.offset + editorOffset.dy;
final offset = getRenderEditor()!.getOffsetToRevealCursor( final offset = getRenderEditor()!.getOffsetToRevealCursor(
@ -1042,7 +1127,8 @@ class _RawEditorState extends EditorState
final value = textEditingValue; final value = textEditingValue;
final data = await Clipboard.getData(Clipboard.kTextPlain); final data = await Clipboard.getData(Clipboard.kTextPlain);
if (data != null) { if (data != null) {
final length = textEditingValue.selection.end - textEditingValue.selection.start; final length =
textEditingValue.selection.end - textEditingValue.selection.start;
widget.controller.replaceText( widget.controller.replaceText(
value.selection.start, value.selection.start,
length, length,
@ -1051,7 +1137,9 @@ class _RawEditorState extends EditorState
); );
// move cursor to the end of pasted text selection // move cursor to the end of pasted text selection
widget.controller.updateSelection( widget.controller.updateSelection(
TextSelection.collapsed(offset: value.selection.start + data.text!.length), ChangeSource.LOCAL); TextSelection.collapsed(
offset: value.selection.start + data.text!.length),
ChangeSource.LOCAL);
} }
} }
} }
@ -1061,7 +1149,8 @@ class _RawEditorState extends EditorState
if (data == null) { if (data == null) {
return false; return false;
} }
return textEditingValue.text.length - value.text.length == data.text!.length; return textEditingValue.text.length - value.text.length ==
data.text!.length;
} }
@override @override
@ -1094,7 +1183,8 @@ class _RawEditorState extends EditorState
} }
@override @override
void userUpdateTextEditingValue(TextEditingValue value, SelectionChangedCause cause) { void userUpdateTextEditingValue(
TextEditingValue value, SelectionChangedCause cause) {
// TODO: implement userUpdateTextEditingValue // TODO: implement userUpdateTextEditingValue
} }
} }
@ -1144,7 +1234,8 @@ class _Editor extends MultiChildRenderObjectWidget {
} }
@override @override
void updateRenderObject(BuildContext context, covariant RenderEditor renderObject) { void updateRenderObject(
BuildContext context, covariant RenderEditor renderObject) {
renderObject renderObject
..document = document ..document = document
..container = document.root ..container = document.root

View file

@ -474,7 +474,7 @@ class __CheckboxState extends State<_Checkbox> {
return Container( return Container(
alignment: AlignmentDirectional.topEnd, alignment: AlignmentDirectional.topEnd,
width: widget.width, width: widget.width,
padding: const EdgeInsetsDirectional.only(end: 13), padding: const EdgeInsetsDirectional.only(end: 2),
child: Checkbox( child: Checkbox(
value: widget.isChecked, value: widget.isChecked,
onChanged: _onCheckboxChanged, onChanged: _onCheckboxChanged,

View file

@ -35,7 +35,7 @@ packages:
name: async name: async
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "2.7.0" version: "2.8.2"
bloc: bloc:
dependency: transitive dependency: transitive
description: description:
@ -112,7 +112,7 @@ packages:
name: characters name: characters
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.1.0" version: "1.2.0"
charcode: charcode:
dependency: transitive dependency: transitive
description: description:
@ -470,7 +470,7 @@ packages:
name: matcher name: matcher
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "0.12.10" version: "0.12.11"
meta: meta:
dependency: transitive dependency: transitive
description: description:
@ -743,7 +743,7 @@ packages:
name: test_api name: test_api
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "0.4.1" version: "0.4.3"
textstyle_extensions: textstyle_extensions:
dependency: transitive dependency: transitive
description: description: