diff --git a/src/common/PopupMenu/PopupMenu.js b/src/common/PopupMenu/PopupMenu.js new file mode 100644 index 000000000..f7530cfab --- /dev/null +++ b/src/common/PopupMenu/PopupMenu.js @@ -0,0 +1,102 @@ +import React, { Component } from 'react'; +import PropTypes from 'prop-types'; +import Icon from 'stremio-icons/dom'; +import colors from 'stremio-colors'; +import styles from './styles'; + +class PopupMenu extends Component { + constructor(props) { + super(props); + + this._rootRef = React.createRef(); + + this.state = { + isOpen: false + }; + } + + shouldComponentUpdate(nextProps, nextState) { + return nextState.isOpen !== this.state.isOpen; + } + + componentDidMount() { + window.addEventListener('blur', this._close); + window.addEventListener('resize', this._close); + } + + componentWillUnmount() { + window.removeEventListener('blur', this._close); + window.removeEventListener('resize', this._close); + } + + _open = (event) => { + event.stopPropagation(); + this.setState({ isOpen: true }); + } + + _close = (event) => { + event.stopPropagation(); + this.setState({ isOpen: false }); + } + + renderMenu() { + if (this.state.isOpen && this._rootRef.current) { + const rootRect = this._rootRef.current.getBoundingClientRect(); + const menuStyles = { + position: 'absolute', + backgroundColor: 'blue', + left: rootRect.x + }; + + if (rootRect.y + rootRect.height + this.props.menuHeight <= window.innerHeight) { + menuStyles.top = rootRect.y + rootRect.height; + menuStyles.height = this.props.menuHeight; + } else if (this.props.menuHeight < rootRect.y) { + menuStyles.bottom = window.innerHeight - rootRect.y; + menuStyles.height = this.props.menuHeight; + } else { + menuStyles.bottom = 0; + menuStyles.top = 0; + } + + if (typeof this.props.menuWidth === 'number') { + menuStyles.width = this.props.menuWidth; + } else { + menuStyles.width = rootRect.width; + } + + return ( +
+
+ +
+
+ ); + } + + return null; + } + + render() { + return ( +
+
+ Click me! + +
+ {this.renderMenu()} +
+ ); + } +} + +PopupMenu.propTypes = { + menuHeight: PropTypes.number.isRequired, + menuWidth: PropTypes.number +}; + +export default PopupMenu; diff --git a/src/common/PopupMenu/index.js b/src/common/PopupMenu/index.js new file mode 100644 index 000000000..5a71ec329 --- /dev/null +++ b/src/common/PopupMenu/index.js @@ -0,0 +1,3 @@ +import PopupMenu from './PopupMenu'; + +export default PopupMenu; diff --git a/src/common/PopupMenu/styles.less b/src/common/PopupMenu/styles.less new file mode 100644 index 000000000..ee3625d26 --- /dev/null +++ b/src/common/PopupMenu/styles.less @@ -0,0 +1,42 @@ +@import "stremio-colors"; + +@keyframes fadeIn { + from { + opacity: 0; + } + to { + opacity: 1; + } +} + +.menu-layer { + position: fixed; + top: 0; + left: 0; + right: 0; + bottom: 0; + z-index: 1; + animation: fadeIn 200ms; +} + +.button-container { + display: flex; + align-items: center; + justify-content: space-between; + height: 38px; + width: 230px; + padding-left: 10px; + padding-right: 10px; + background-color: @colorglass; + cursor: pointer; +} + +.button-label { + font-size: 18px; + color: @colorwhite80; +} + +.button-icon { + width: 16px; + height: 16px; +} diff --git a/src/common/index.js b/src/common/index.js index d4a1c16b0..7b2b5db00 100644 --- a/src/common/index.js +++ b/src/common/index.js @@ -1,5 +1,7 @@ import Checkbox from './checkbox'; +import PopupMenu from './PopupMenu'; export { - Checkbox + Checkbox, + PopupMenu };