From 1d90950e59c51ffc06067daca18c81ca1848e6f0 Mon Sep 17 00:00:00 2001 From: Alex Gleason Date: Fri, 11 Sep 2020 11:37:05 -0500 Subject: [PATCH] Hovercard: refactor with HoverRefWrapper --- app/soapbox/components/hover_ref_wrapper.js | 50 +++++++++++++++++++ app/soapbox/components/profile_hover_card.js | 2 +- app/soapbox/components/status.js | 39 ++++----------- app/soapbox/containers/status_container.js | 12 ----- app/styles/components/profile_hover_card.scss | 1 - 5 files changed, 62 insertions(+), 42 deletions(-) create mode 100644 app/soapbox/components/hover_ref_wrapper.js diff --git a/app/soapbox/components/hover_ref_wrapper.js b/app/soapbox/components/hover_ref_wrapper.js new file mode 100644 index 000000000..64d62ba5c --- /dev/null +++ b/app/soapbox/components/hover_ref_wrapper.js @@ -0,0 +1,50 @@ +import React, { useRef } from 'react'; +import PropTypes from 'prop-types'; +import { + openProfileHoverCard, + closeProfileHoverCard, +} from 'soapbox/actions/profile_hover_card'; +import { useDispatch } from 'react-redux'; +import { debounce } from 'lodash'; +import { isMobile } from 'soapbox/is_mobile'; + +const showProfileHoverCard = debounce((dispatch, ref, accountId) => { + dispatch(openProfileHoverCard(ref, accountId)); +}, 1200); + +const handleMouseEnter = (dispatch, ref, accountId) => { + return e => { + if (!isMobile(window.innerWidth)) + showProfileHoverCard(dispatch, ref, accountId); + }; +}; + +const handleMouseLeave = (dispatch) => { + return e => { + showProfileHoverCard.cancel(); + setTimeout(() => dispatch(closeProfileHoverCard()), 300); + }; +}; + +export const HoverRefWrapper = ({ accountId, children }) => { + const dispatch = useDispatch(); + const ref = useRef(); + + return ( +
+ {children} +
+ ); +}; + +HoverRefWrapper.propTypes = { + accountId: PropTypes.string, + children: PropTypes.node, +}; + +export default HoverRefWrapper; diff --git a/app/soapbox/components/profile_hover_card.js b/app/soapbox/components/profile_hover_card.js index ae3f8bc3a..b545b87bc 100644 --- a/app/soapbox/components/profile_hover_card.js +++ b/app/soapbox/components/profile_hover_card.js @@ -45,7 +45,7 @@ export const ProfileHoverCard = ({ visible }) => { const accountId = useSelector(state => state.getIn(['profile_hover_card', 'accountId'])); const account = useSelector(state => accountId && getAccount(state, accountId)); - const targetRef = useSelector(state => state.getIn(['profile_hover_card', 'ref'])); + const targetRef = useSelector(state => state.getIn(['profile_hover_card', 'ref', 'current'])); const badges = account ? getBadges(account) : []; useEffect(() => { diff --git a/app/soapbox/components/status.js b/app/soapbox/components/status.js index 275603bcc..e52dfdc5c 100644 --- a/app/soapbox/components/status.js +++ b/app/soapbox/components/status.js @@ -18,9 +18,8 @@ import classNames from 'classnames'; import Icon from 'soapbox/components/icon'; import PollContainer from 'soapbox/containers/poll_container'; import { NavLink } from 'react-router-dom'; -import { isMobile } from '../../../app/soapbox/is_mobile'; -import { debounce } from 'lodash'; import { getDomain } from 'soapbox/utils/accounts'; +import HoverRefWrapper from 'soapbox/components/hover_ref_wrapper'; // We use the component (and not the container) since we do not want // to use the progress bar to show download progress @@ -255,20 +254,6 @@ class Status extends ImmutablePureComponent { this.handleToggleMediaVisibility(); } - showProfileHoverCard = debounce(() => { - const { onShowProfileHoverCard, status } = this.props; - onShowProfileHoverCard(this.profileNode, status.getIn(['account', 'id'])); - }, 1200); - - handleProfileHover = e => { - if (!isMobile(window.innerWidth)) this.showProfileHoverCard(); - } - - handleProfileLeave = e => { - this.showProfileHoverCard.cancel(); - this.props.onClearProfileHoverCard(); - } - _properStatus() { const { status } = this.props; @@ -283,10 +268,6 @@ class Status extends ImmutablePureComponent { this.node = c; } - setProfileRef = c => { - this.profileNode = c; - } - render() { let media = null; let poll = null; @@ -481,15 +462,17 @@ class Status extends ImmutablePureComponent { } -
-
- - {statusAvatar} + +
+
+ + {statusAvatar} +
+ + +
- - - -
+
{!group && status.get('group') && ( diff --git a/app/soapbox/containers/status_container.js b/app/soapbox/containers/status_container.js index fb976a82d..02dc76c21 100644 --- a/app/soapbox/containers/status_container.js +++ b/app/soapbox/containers/status_container.js @@ -35,10 +35,6 @@ import { groupRemoveStatus, } from '../actions/groups'; import { getSettings } from '../actions/settings'; -import { - openProfileHoverCard, - closeProfileHoverCard, -} from 'soapbox/actions/profile_hover_card'; const messages = defineMessages({ deleteConfirm: { id: 'confirmations.delete.confirm', defaultMessage: 'Delete' }, @@ -210,14 +206,6 @@ const mapDispatchToProps = (dispatch, { intl }) => ({ dispatch(groupRemoveStatus(groupId, statusId)); }, - onShowProfileHoverCard(ref, accountId) { - dispatch(openProfileHoverCard(ref, accountId)); - }, - - onClearProfileHoverCard() { - setTimeout(() => dispatch(closeProfileHoverCard()), 300); - }, - }); export default injectIntl(connect(makeMapStateToProps, mapDispatchToProps)(Status)); diff --git a/app/styles/components/profile_hover_card.scss b/app/styles/components/profile_hover_card.scss index 47a5242a2..e89998901 100644 --- a/app/styles/components/profile_hover_card.scss +++ b/app/styles/components/profile_hover_card.scss @@ -17,7 +17,6 @@ z-index: 200; top: 0; left: 0; - margin-bottom: 10px; &--visible { opacity: 1;