diff --git a/frontend/src/components/context-menu/context-menu.js b/frontend/src/components/context-menu/context-menu.js index 0346ddc288..1db73c93ad 100644 --- a/frontend/src/components/context-menu/context-menu.js +++ b/frontend/src/components/context-menu/context-menu.js @@ -7,11 +7,10 @@ import { Utils } from '../../utils/utils'; const propTypes = { id: PropTypes.string.isRequired, - rtl: PropTypes.bool, onMenuItemClick: PropTypes.func.isRequired, onShowMenu: PropTypes.func, onHideMenu: PropTypes.func, - hideOnLeave: PropTypes.bool, + getMenuContainerSize: PropTypes.func, }; class ContextMenu extends React.Component { @@ -38,7 +37,7 @@ class ContextMenu extends React.Component { wrapper(() => { const { x, y } = this.state; - const { top, left } = this.props.rtl ? this.getRTLMenuPosition(x, y) : this.getMenuPosition(x, y); + const { top, left } = this.getMenuPosition(x, y); wrapper(() => { if (!this.menu) return; @@ -85,9 +84,20 @@ class ContextMenu extends React.Component { if (e.detail.id !== this.props.id) return; const { x, y } = e.detail.position; - const { currentObject, menuList} = e.detail; + if (this.props.getMenuContainerSize) { + const containerSize = this.props.getMenuContainerSize(); + const relativeX = x - (window.innerWidth - parseFloat(containerSize.width)); + const relativeY = y - (window.innerHeight - parseFloat(containerSize.height)); + this.setState({ + x: relativeX, + y: relativeY, + }); + } else { + this.setState({ x, y }); + } - this.setState({ isVisible: true, x, y, currentObject, menuList }); + const { currentObject, menuList } = e.detail; + this.setState({ isVisible: true, currentObject, menuList }); this.registerHandlers(); callIfExists(this.props.onShowMenu, e); }; @@ -106,8 +116,6 @@ class ContextMenu extends React.Component { handleMouseLeave = (event) => { event.preventDefault(); - - if (this.props.hideOnLeave) hideMenu(); }; handleContextMenu = (e) => { @@ -136,56 +144,29 @@ class ContextMenu extends React.Component { if (!this.menu) return menuStyles; - const { innerWidth, innerHeight } = window; + let { innerWidth, innerHeight } = window; const rect = this.menu.getBoundingClientRect(); + if (this.props.getMenuContainerSize) { + let containerSize = this.props.getMenuContainerSize(); + innerWidth = parseFloat(containerSize.width); + innerHeight = parseFloat(containerSize.height); + } + if (y + rect.height > innerHeight) { menuStyles.top -= rect.height; } - if (x + rect.width > innerWidth) { - menuStyles.left -= rect.width; - } - - if (menuStyles.top < 0) { - menuStyles.top = rect.height < innerHeight ? (innerHeight - rect.height) / 2 : 0; - } - if (menuStyles.left < 0) { menuStyles.left = rect.width < innerWidth ? (innerWidth - rect.width) / 2 : 0; } - return menuStyles; - }; - - getRTLMenuPosition = (x = 0, y = 0) => { - let menuStyles = { - top: y, - left: x - }; - - if (!this.menu) return menuStyles; - - const { innerWidth, innerHeight } = window; - const rect = this.menu.getBoundingClientRect(); - - // Try to position the menu on the left side of the cursor - menuStyles.left = x - rect.width; - - if (y + rect.height > innerHeight) { - menuStyles.top -= rect.height; - } - - if (menuStyles.left < 0) { - menuStyles.left += rect.width; - } - if (menuStyles.top < 0) { menuStyles.top = rect.height < innerHeight ? (innerHeight - rect.height) / 2 : 0; } if (menuStyles.left + rect.width > innerWidth) { - menuStyles.left = rect.width < innerWidth ? (innerWidth - rect.width) / 2 : 0; + menuStyles.left = innerWidth - rect.width; } return menuStyles; diff --git a/frontend/src/components/dir-view-mode/dir-column-nav.js b/frontend/src/components/dir-view-mode/dir-column-nav.js index b584a52c26..067e5a657c 100644 --- a/frontend/src/components/dir-view-mode/dir-column-nav.js +++ b/frontend/src/components/dir-view-mode/dir-column-nav.js @@ -39,6 +39,7 @@ const propTypes = { onItemCopy: PropTypes.func.isRequired, selectedDirentList: PropTypes.array.isRequired, onItemsMove: PropTypes.func.isRequired, + getMenuContainerSize: PropTypes.func, }; class DirColumnNav extends React.Component { @@ -269,6 +270,7 @@ class DirColumnNav extends React.Component { selectedDirentList={this.props.selectedDirentList} onItemsMove={this.props.onItemsMove} repoID={this.props.repoID} + getMenuContainerSize={this.props.getMenuContainerSize} /> { @@ -125,6 +126,10 @@ class DirColumnView extends React.Component { this.dragHandlerRef.current.style.top = top + 'px'; }; + getMenuContainerSize = () => { + return window.getComputedStyle(this.viewModeContainer.current); + }; + render() { const { currentMode, isTreePanelShown } = this.props; const { navRate, inResizing } = this.state; @@ -132,7 +137,12 @@ class DirColumnView extends React.Component { const select = inResizing ? 'none' : ''; const mainFlex = '1 0 ' + (1 - navRate) * 100 + '%'; return ( -
+
{isTreePanelShown && ( <> )} -
{} : this.props.onItemsScroll}> +
{} : this.props.onItemsScroll} + ref={this.dirContentMain} + > {this.props.isViewFile ? ( : )}
diff --git a/frontend/src/components/dir-view-mode/dir-list-view.js b/frontend/src/components/dir-view-mode/dir-list-view.js index ca3ad5919f..ecd9553133 100644 --- a/frontend/src/components/dir-view-mode/dir-list-view.js +++ b/frontend/src/components/dir-view-mode/dir-list-view.js @@ -41,6 +41,7 @@ const propTypes = { showDirentDetail: PropTypes.func.isRequired, loadDirentList: PropTypes.func, fullDirentList: PropTypes.array, + getMenuContainerSize: PropTypes.func, }; class DirListView extends React.Component { @@ -103,6 +104,7 @@ class DirListView extends React.Component { onFileTagChanged={this.props.onFileTagChanged} showDirentDetail={this.props.showDirentDetail} loadDirentList={this.props.loadDirentList} + getMenuContainerSize={this.props.getMenuContainerSize} /> ); diff --git a/frontend/src/components/dirent-grid-view/dirent-grid-view.js b/frontend/src/components/dirent-grid-view/dirent-grid-view.js index effc9732e4..7ac83e218d 100644 --- a/frontend/src/components/dirent-grid-view/dirent-grid-view.js +++ b/frontend/src/components/dirent-grid-view/dirent-grid-view.js @@ -52,6 +52,7 @@ const propTypes = { posX: PropTypes.number, posY: PropTypes.number, dirent: PropTypes.object, + getMenuContainerSize: PropTypes.func, }; class DirentGridView extends React.Component { @@ -539,10 +540,12 @@ class DirentGridView extends React.Component { {this.state.isCreateFolderDialogShow && ( diff --git a/frontend/src/components/dirent-list-view/dirent-list-view.js b/frontend/src/components/dirent-list-view/dirent-list-view.js index f2a7483df0..3074890eeb 100644 --- a/frontend/src/components/dirent-list-view/dirent-list-view.js +++ b/frontend/src/components/dirent-list-view/dirent-list-view.js @@ -54,6 +54,7 @@ const propTypes = { fullDirentList: PropTypes.array, posX: PropTypes.string, posY: PropTypes.string, + getMenuContainerSize: PropTypes.func, }; class DirentListView extends React.Component { @@ -689,16 +690,19 @@ class DirentListView extends React.Component { {this.state.isShowDirentsDraggablePreview && diff --git a/frontend/src/components/tree-view/tree-view.js b/frontend/src/components/tree-view/tree-view.js index 6080807d82..33619f7c32 100644 --- a/frontend/src/components/tree-view/tree-view.js +++ b/frontend/src/components/tree-view/tree-view.js @@ -22,6 +22,7 @@ const propTypes = { repoID: PropTypes.string.isRequired, posX: PropTypes.number, posY: PropTypes.number, + getMenuContainerSize: PropTypes.func, }; const LEFT_INDENT = 20; @@ -347,6 +348,7 @@ class TreeView extends React.Component { onMenuItemClick={this.onMenuItemClick} onHideMenu={this.onHideMenu} onShowMenu={this.onShowMenu} + getMenuContainerSize={this.props.getMenuContainerSize} />
);