From 7c41b8612dbe013be0f11e98d6c404b04fb15d92 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=C5=A0imon=20Brandner?= Date: Sun, 17 Apr 2022 15:50:13 +0200 Subject: [PATCH] Put the right-click message context menu to the right (#8339) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit * Improve `alwaysAboveRightOf()` typing Signed-off-by: Šimon Brandner * Improve typing of `alwaysAboveLeftOf()` Signed-off-by: Šimon Brandner * Add `aboveRightOf()` Signed-off-by: Šimon Brandner * Use `aboveRightOf()` Signed-off-by: Šimon Brandner * Fix typo Signed-off-by: Šimon Brandner --- src/components/structures/ContextMenu.tsx | 36 +++++++++++++++++++++-- src/components/views/rooms/EventTile.tsx | 8 ++--- 2 files changed, 38 insertions(+), 6 deletions(-) diff --git a/src/components/structures/ContextMenu.tsx b/src/components/structures/ContextMenu.tsx index c84452a264..a3c214eb45 100644 --- a/src/components/structures/ContextMenu.tsx +++ b/src/components/structures/ContextMenu.tsx @@ -450,9 +450,37 @@ export const aboveLeftOf = ( return menuOptions; }; +// Placement method for to position context menu right-aligned and flowing to the right of elementRect, +// and either above or below: wherever there is more space (maybe this should be aboveOrBelowRightOf?) +export const aboveRightOf = ( + elementRect: Pick, + chevronFace = ChevronFace.None, + vPadding = 0, +): AboveLeftOf => { + const menuOptions: IPosition & { chevronFace: ChevronFace } = { chevronFace }; + + const buttonLeft = elementRect.left + window.pageXOffset; + const buttonBottom = elementRect.bottom + window.pageYOffset; + const buttonTop = elementRect.top + window.pageYOffset; + // Align the left edge of the menu to the left edge of the button + menuOptions.left = buttonLeft; + // Align the menu vertically on whichever side of the button has more space available. + if (buttonBottom < UIStore.instance.windowHeight / 2) { + menuOptions.top = buttonBottom + vPadding; + } else { + menuOptions.bottom = (UIStore.instance.windowHeight - buttonTop) + vPadding; + } + + return menuOptions; +}; + // Placement method for to position context menu right-aligned and flowing to the left of elementRect // and always above elementRect -export const alwaysAboveLeftOf = (elementRect: DOMRect, chevronFace = ChevronFace.None, vPadding = 0) => { +export const alwaysAboveLeftOf = ( + elementRect: Pick, + chevronFace = ChevronFace.None, + vPadding = 0, +) => { const menuOptions: IPosition & { chevronFace: ChevronFace } = { chevronFace }; const buttonRight = elementRect.right + window.pageXOffset; @@ -472,7 +500,11 @@ export const alwaysAboveLeftOf = (elementRect: DOMRect, chevronFace = ChevronFac // Placement method for to position context menu right-aligned and flowing to the right of elementRect // and always above elementRect -export const alwaysAboveRightOf = (elementRect: DOMRect, chevronFace = ChevronFace.None, vPadding = 0) => { +export const alwaysAboveRightOf = ( + elementRect: Pick, + chevronFace = ChevronFace.None, + vPadding = 0, +) => { const menuOptions: IPosition & { chevronFace: ChevronFace } = { chevronFace }; const buttonLeft = elementRect.left + window.pageXOffset; diff --git a/src/components/views/rooms/EventTile.tsx b/src/components/views/rooms/EventTile.tsx index a4eec106d8..9d5dc2cefe 100644 --- a/src/components/views/rooms/EventTile.tsx +++ b/src/components/views/rooms/EventTile.tsx @@ -39,7 +39,7 @@ import { E2EState } from "./E2EIcon"; import { toRem } from "../../../utils/units"; import RoomAvatar from "../avatars/RoomAvatar"; import MessageContextMenu, { IEventTileOps } from "../context_menus/MessageContextMenu"; -import { aboveLeftOf } from '../../structures/ContextMenu'; +import { aboveRightOf } from '../../structures/ContextMenu'; import { objectHasDiff } from "../../../utils/objects"; import Tooltip from "../elements/Tooltip"; import EditorStateTransfer from "../../../utils/EditorStateTransfer"; @@ -230,7 +230,7 @@ interface IState { // Position of the context menu contextMenu?: { - position: Pick; + position: Pick; showPermalink?: boolean; }; @@ -972,7 +972,7 @@ export class UnwrappedEventTile extends React.Component { this.setState({ contextMenu: { position: { - right: ev.clientX, + left: ev.clientX, top: ev.clientY, bottom: ev.clientY, }, @@ -1017,7 +1017,7 @@ export class UnwrappedEventTile extends React.Component { return (