Merge pull request #785 from AppFlowy-IO/feat/handle-triple-click-in-flowy-editor

Feat: handle triple tap for flowy editor
This commit is contained in:
Vincent Chan 2022-08-08 15:35:06 +08:00 committed by GitHub
commit e1b10ec791
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -160,6 +160,7 @@ class _FlowySelectionState extends State<FlowySelection>
onPanEnd: _onPanEnd, onPanEnd: _onPanEnd,
onTapDown: _onTapDown, onTapDown: _onTapDown,
onDoubleTapDown: _onDoubleTapDown, onDoubleTapDown: _onDoubleTapDown,
onTripleTapDown: _onTripleTapDown,
child: widget.child, child: widget.child,
); );
} }
@ -252,6 +253,25 @@ class _FlowySelectionState extends State<FlowySelection>
.updateCursorSelection(selectable.getWorldBoundaryInOffset(offset)); .updateCursorSelection(selectable.getWorldBoundaryInOffset(offset));
} }
void _onTripleTapDown(TapDownDetails details) {
final offset = details.globalPosition;
final node = getNodeInOffset(offset);
if (node == null) {
editorState.updateCursorSelection(null);
return;
}
Selection selection;
if (node is TextNode) {
final textLen = node.delta.length;
selection = Selection(
start: Position(path: node.path, offset: 0),
end: Position(path: node.path, offset: textLen));
} else {
selection = Selection.collapsed(Position(path: node.path, offset: 0));
}
editorState.updateCursorSelection(selection);
}
void _onTapDown(TapDownDetails details) { void _onTapDown(TapDownDetails details) {
// clear old state. // clear old state.
panStartOffset = null; panStartOffset = null;
@ -576,6 +596,7 @@ class _SelectionGestureDetector extends StatefulWidget {
this.child, this.child,
this.onTapDown, this.onTapDown,
this.onDoubleTapDown, this.onDoubleTapDown,
this.onTripleTapDown,
this.onPanStart, this.onPanStart,
this.onPanUpdate, this.onPanUpdate,
this.onPanEnd}) this.onPanEnd})
@ -589,14 +610,19 @@ class _SelectionGestureDetector extends StatefulWidget {
final GestureTapDownCallback? onTapDown; final GestureTapDownCallback? onTapDown;
final GestureTapDownCallback? onDoubleTapDown; final GestureTapDownCallback? onDoubleTapDown;
final GestureTapDownCallback? onTripleTapDown;
final GestureDragStartCallback? onPanStart; final GestureDragStartCallback? onPanStart;
final GestureDragUpdateCallback? onPanUpdate; final GestureDragUpdateCallback? onPanUpdate;
final GestureDragEndCallback? onPanEnd; final GestureDragEndCallback? onPanEnd;
} }
const Duration kTripleTapTimeout = Duration(milliseconds: 500);
class _SelectionGestureDetectorState extends State<_SelectionGestureDetector> { class _SelectionGestureDetectorState extends State<_SelectionGestureDetector> {
bool _isDoubleTap = false; bool _isDoubleTap = false;
Timer? _doubleTapTimer; Timer? _doubleTapTimer;
int _tripleTabCount = 0;
Timer? _tripleTabTimer;
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
return RawGestureDetector( return RawGestureDetector(
@ -625,13 +651,21 @@ class _SelectionGestureDetectorState extends State<_SelectionGestureDetector> {
} }
_tapDownDelegate(TapDownDetails tapDownDetails) { _tapDownDelegate(TapDownDetails tapDownDetails) {
if (_isDoubleTap) { if (_tripleTabCount == 2) {
_tripleTabCount = 0;
_tripleTabTimer?.cancel();
_tripleTabTimer = null;
if (widget.onTripleTapDown != null) {
widget.onTripleTapDown!(tapDownDetails);
}
} else if (_isDoubleTap) {
_isDoubleTap = false; _isDoubleTap = false;
_doubleTapTimer?.cancel(); _doubleTapTimer?.cancel();
_doubleTapTimer = null; _doubleTapTimer = null;
if (widget.onDoubleTapDown != null) { if (widget.onDoubleTapDown != null) {
widget.onDoubleTapDown!(tapDownDetails); widget.onDoubleTapDown!(tapDownDetails);
} }
_tripleTabCount++;
} else { } else {
if (widget.onTapDown != null) { if (widget.onTapDown != null) {
widget.onTapDown!(tapDownDetails); widget.onTapDown!(tapDownDetails);
@ -643,12 +677,20 @@ class _SelectionGestureDetectorState extends State<_SelectionGestureDetector> {
_isDoubleTap = false; _isDoubleTap = false;
_doubleTapTimer = null; _doubleTapTimer = null;
}); });
_tripleTabCount = 1;
_tripleTabTimer?.cancel();
_tripleTabTimer = Timer(kTripleTapTimeout, () {
_tripleTabCount = 0;
_tripleTabTimer = null;
});
} }
} }
@override @override
void dispose() { void dispose() {
_doubleTapTimer?.cancel(); _doubleTapTimer?.cancel();
_tripleTabTimer?.cancel();
super.dispose(); super.dispose();
} }
} }