import PropTypes from 'prop-types'; import React, { Component } from 'react'; import TetherComponent from 'react-tether'; import classNames from 'classnames'; import { kinds, tooltipPositions } from 'Helpers/Props'; import styles from './Tooltip.css'; const baseTetherOptions = { skipMoveElement: true, constraints: [ { to: 'window', attachment: 'together', pin: true } ] }; const tetherOptions = { [tooltipPositions.TOP]: { ...baseTetherOptions, attachment: 'bottom center', targetAttachment: 'top center' }, [tooltipPositions.RIGHT]: { ...baseTetherOptions, attachment: 'middle left', targetAttachment: 'middle right' }, [tooltipPositions.BOTTOM]: { ...baseTetherOptions, attachment: 'top center', targetAttachment: 'bottom center' }, [tooltipPositions.LEFT]: { ...baseTetherOptions, attachment: 'middle right', targetAttachment: 'middle left' } }; class Tooltip extends Component { // // Lifecycle constructor(props, context) { super(props, context); this.state = { isOpen: false }; this._closeTimeout = null; } componentWillUnmount() { if (this._closeTimeout) { this._closeTimeout = clearTimeout(this._closeTimeout); } } // // Listeners onClick = () => { this.setState({ isOpen: !this.state.isOpen }); } onMouseEnter = () => { if (this._closeTimeout) { clearTimeout(this._closeTimeout); } this.setState({ isOpen: true }); } onMouseLeave = () => { this._closeTimeout = setTimeout(() => { this.setState({ isOpen: false }); }, 100); } // // Render render() { const { className, anchor, tooltip, kind, position } = this.props; return ( {anchor} { this.state.isOpen &&
{tooltip}
} ); } } Tooltip.propTypes = { className: PropTypes.string, anchor: PropTypes.node.isRequired, tooltip: PropTypes.oneOfType([PropTypes.string, PropTypes.node]).isRequired, kind: PropTypes.oneOf([kinds.DEFAULT, kinds.INVERSE]), position: PropTypes.oneOf(tooltipPositions.all) }; Tooltip.defaultProps = { kind: kinds.DEFAULT, position: tooltipPositions.TOP }; export default Tooltip;