Skip to content

Commit

Permalink
Fixed tap to show toolbar on iOS when tapping on caret a second time (R…
Browse files Browse the repository at this point in the history
…esolves #1567) (#1573)
  • Loading branch information
matthew-carroll authored Oct 28, 2023
1 parent 867457d commit e63d479
Show file tree
Hide file tree
Showing 3 changed files with 30 additions and 27 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -626,7 +626,9 @@ class _IosDocumentTouchInteractorState extends State<IosDocumentTouchInteractor>
}

if (docPosition != null) {
final didTapOnExistingSelection = selection != null && selection.isCollapsed && selection.extent == docPosition;
final didTapOnExistingSelection = selection != null &&
selection.isCollapsed &&
selection.extent.nodePosition.isEquivalentTo(docPosition.nodePosition);

if (didTapOnExistingSelection) {
// Toggle the toolbar display when the user taps on the collapsed caret,
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import 'package:flutter/foundation.dart';
import 'package:flutter/material.dart';
import 'package:flutter/scheduler.dart';
import 'package:follow_the_leader/follow_the_leader.dart';
import 'package:overlord/follow_the_leader.dart';
import 'package:super_editor/src/core/document.dart';
Expand Down Expand Up @@ -410,7 +409,7 @@ class IosToolbarFocalPointDocumentLayer extends DocumentLayoutLayerStatefulWidge

class _IosToolbarFocalPointDocumentLayerState extends DocumentLayoutLayerState<IosToolbarFocalPointDocumentLayer, Rect>
with SingleTickerProviderStateMixin {
bool _wasSelectionExpanded = false;
DocumentSelection? _selectionUsedForMostRecentLayout;

@override
void initState() {
Expand Down Expand Up @@ -438,24 +437,14 @@ class _IosToolbarFocalPointDocumentLayerState extends DocumentLayoutLayerState<I

void _onSelectionChange() {
final selection = widget.selection.value;
_wasSelectionExpanded = !(selection?.isCollapsed == true);

if (selection == null && !_wasSelectionExpanded) {
// There's no selection now, and in the previous frame there either was no selection,
// or a collapsed selection. We don't need to worry about re-calculating or rebuilding
// our bounds.
return;
}
if (selection != null && selection.isCollapsed && !_wasSelectionExpanded) {
// The current selection is collapsed, and the selection in the previous frame was
// either null, or was also collapsed. We only need to position bounds when the selection
// is expanded, or goes from expanded to collapsed, or from collapsed to expanded.
if (selection == _selectionUsedForMostRecentLayout) {
// The selection didn't change from what it was the last time we calculated selection bounds.
return;
}
_selectionUsedForMostRecentLayout = selection;

// The current selection is expanded, or we went from expanded in the previous frame
// to non-expanded in this frame. Either way, we need to recalculate the toolbar focal
// point bounds.
// The selection changed, which means the selection bounds changed, we need to recalculate the
// toolbar focal point bounds.
setStateAsSoonAsPossible(() {
// The selection bounds, and Leader build, will take place in methods that
// run in response to setState().
Expand All @@ -477,27 +466,23 @@ class _IosToolbarFocalPointDocumentLayerState extends DocumentLayoutLayerState<I
return null;
}

if (documentSelection.isCollapsed) {
return null;
}

return documentLayout.getRectForSelection(
documentSelection.base,
documentSelection.extent,
);
}

@override
Widget doBuild(BuildContext context, Rect? expandedSelectionBounds) {
if (expandedSelectionBounds == null) {
Widget doBuild(BuildContext context, Rect? selectionBounds) {
if (selectionBounds == null) {
return const SizedBox();
}

return IgnorePointer(
child: Stack(
children: [
Positioned.fromRect(
rect: expandedSelectionBounds,
rect: selectionBounds,
child: Leader(
link: widget.toolbarFocalPointLink,
child: widget.showDebugLeaderBounds
Expand Down
Original file line number Diff line number Diff line change
@@ -1,7 +1,5 @@
import 'package:flutter/rendering.dart';
import 'package:flutter_test/flutter_test.dart';
import 'package:flutter_test_runners/flutter_test_runners.dart';
import 'package:super_editor/src/infrastructure/platforms/ios/ios_document_controls.dart';
import 'package:super_editor/super_editor_test.dart';

import '../../test_runners.dart';
Expand All @@ -20,6 +18,24 @@ void main() {
expect(SuperEditorInspector.isMobileToolbarVisible(), isFalse);
});

testWidgetsOnIos("shows toolbar when tapping on caret", (tester) async {
await _pumpSingleParagraphApp(tester);

// Place the caret.
await tester.tapInParagraph("1", 200);

// Ensure all controls are hidden.
expect(SuperEditorInspector.isMobileMagnifierVisible(), isFalse);
expect(SuperEditorInspector.isMobileToolbarVisible(), isFalse);

// Tap again on the caret.
await tester.tapInParagraph("1", 200);

// Ensure that the toolbar is visible.
expect(SuperEditorInspector.isMobileToolbarVisible(), isTrue);
expect(SuperEditorInspector.isMobileMagnifierVisible(), isFalse);
});

testWidgetsOnIos("shows magnifier when dragging the caret", (tester) async {
await _pumpSingleParagraphApp(tester);

Expand Down

0 comments on commit e63d479

Please sign in to comment.