import CSSTransitionGroup from 'react-addons-css-transition-group'; import React from 'react'; import ReactDOM from 'react-dom'; export default class ContextMenu extends React.Component { constructor() { super(); this.state = { menuPosition: {}, isMenuPositionIdeal: false }; } componentDidMount() { if (this.props.onMenuOpen) { this.props.onMenuOpen(); } this.checkMenuPosition(); } componentDidUpdate() { this.checkMenuPosition(); } componentWillUnmount() { if (this.props.onMenuClose) { this.props.onMenuClose(); } } componentWillUpdate(nextProps) { if (nextProps.clickPosition.x !== this.props.clickPosition.x || nextProps.clickPosition.y !== this.props.clickPosition.y) { this.setState({ isMenuPositionIdeal: false, menuPosition: this.getMenuPosition() }); } } checkMenuPosition() { if (!this.state.isMenuPositionIdeal) { this.setState({ isMenuPositionIdeal: true, menuPosition: this.getMenuPosition() }); } } getMenuPosition() { let menuBorderBox = this.getRenderedMenuBorderBox(); let viewportDimensions = this.getViewportDimensions(); let menuPosition = {}; if (menuBorderBox.left + menuBorderBox.width > viewportDimensions.width) { menuPosition.right = viewportDimensions.width - this.props.clickPosition.x; } else { menuPosition.left = menuBorderBox.left; } if (menuBorderBox.height + this.props.clickPosition.y > viewportDimensions.height) { menuPosition.bottom = viewportDimensions.height - this.props.clickPosition.y; } else { menuPosition.top = menuBorderBox.top; } return menuPosition; } getViewportDimensions() { let height = global.window.innerHeight; let width = global.window.innerWidth; return {height, width}; } getRenderedMenuBorderBox() { let menuDOMNode = ReactDOM.findDOMNode(this); if (menuDOMNode) { return menuDOMNode.getBoundingClientRect(); } return null; } getMenuItems(items) { return items.map((item, index) => { return (