fix: mobile slash menu position error (#7747)

* fix: mobile slash menu position error

* fix: mobile slash menu sometimes not showing up
This commit is contained in:
Morn 2025-04-15 17:43:50 +08:00 committed by GitHub
parent 69b5452af5
commit c6511cfb55
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 49 additions and 34 deletions

View File

@ -1,5 +1,4 @@
import 'dart:async';
import 'dart:math';
import 'package:appflowy/mobile/presentation/selection_menu/mobile_selection_menu_item.dart';
import 'package:appflowy_editor/appflowy_editor.dart';
@ -166,7 +165,8 @@ class MobileSelectionMenu extends SelectionMenuService {
if (selectionRects.isEmpty) {
return null;
}
calculateSelectionMenuOffset(selectionRects.first);
final screenSize = MediaQuery.of(context).size;
calculateSelectionMenuOffset(selectionRects.first, screenSize);
final (left, top, right, bottom) = getPosition();
return _Position(left, top, right, bottom);
}
@ -205,50 +205,65 @@ class MobileSelectionMenu extends SelectionMenuService {
return (left, top, right, bottom);
}
void calculateSelectionMenuOffset(Rect rect) {
void calculateSelectionMenuOffset(Rect rect, Size screenSize) {
// Workaround: We can customize the padding through the [EditorStyle],
// but the coordinates of overlay are not properly converted currently.
// Just subtract the padding here as a result.
const menuHeight = 192.0, menuWidth = 240.0 + 10;
const menuOffset = Offset(0, 10);
const menuHeight = 192.0, menuWidth = 240.0;
final editorOffset =
editorState.renderBox?.localToGlobal(Offset.zero) ?? Offset.zero;
final editorHeight = editorState.renderBox!.size.height;
final screenHeight = screenSize.height;
final editorWidth = editorState.renderBox!.size.width;
final rectHeight = rect.height;
// show below default
_alignment = Alignment.topLeft;
final bottomRight = rect.bottomRight;
final topRight = rect.topRight;
var offset = bottomRight + menuOffset;
final limitX = editorWidth - menuWidth + editorOffset.dx;
_alignment = Alignment.bottomRight;
final bottomRight = rect.topLeft;
final offset = bottomRight;
final limitX = editorWidth + editorOffset.dx - menuWidth,
limitY = screenHeight -
editorHeight +
editorOffset.dy -
menuHeight -
rectHeight;
_offset = Offset(
min(offset.dx, limitX),
offset.dy,
editorWidth - offset.dx - menuWidth,
screenHeight - offset.dy - menuHeight - rectHeight,
);
// show above
if (offset.dy + menuHeight >= editorOffset.dy + editorHeight) {
offset = topRight - menuOffset;
_alignment = Alignment.bottomLeft;
_offset = Offset(
offset.dx,
editorOffset.dy + editorHeight - offset.dy,
);
/// show above
if (offset.dy > menuHeight) {
_offset = Offset(
_offset.dx,
offset.dy - menuHeight,
);
_alignment = Alignment.topRight;
} else {
_offset = Offset(
_offset.dx,
limitY,
);
}
}
// show on left
if (_offset.dx - editorOffset.dx > editorWidth / 2) {
_alignment = _alignment == Alignment.topLeft
? Alignment.topRight
: Alignment.bottomRight;
final x = editorWidth - _offset.dx + editorOffset.dx;
_offset = Offset(
min(x, limitX),
_offset.dy,
);
if (offset.dx + menuWidth >= editorOffset.dx + editorWidth) {
/// show left
if (offset.dx > menuWidth) {
_alignment = _alignment == Alignment.bottomRight
? Alignment.bottomLeft
: Alignment.topLeft;
_offset = Offset(
offset.dx - menuWidth,
_offset.dy,
);
} else {
_offset = Offset(
limitX,
_offset.dy,
);
}
}
}
}

View File

@ -98,8 +98,8 @@ packages:
dependency: "direct main"
description:
path: "."
ref: "361b99c38370abeeb19656f89e8c31cb3666623b"
resolved-ref: "361b99c38370abeeb19656f89e8c31cb3666623b"
ref: "4967ed5"
resolved-ref: "4967ed57d9190948c08f868972c0babfdc470ba7"
url: "https://github.com/AppFlowy-IO/appflowy-editor.git"
source: git
version: "5.1.0"

View File

@ -185,7 +185,7 @@ dependency_overrides:
appflowy_editor:
git:
url: https://github.com/AppFlowy-IO/appflowy-editor.git
ref: '361b99c38370abeeb19656f89e8c31cb3666623b'
ref: '4967ed5'
appflowy_editor_plugins:
git: