diff --git a/app/javascript/flavours/glitch/components/status_action_bar.jsx b/app/javascript/flavours/glitch/components/status_action_bar.jsx
index 7652eb11d..5420fb7c3 100644
--- a/app/javascript/flavours/glitch/components/status_action_bar.jsx
+++ b/app/javascript/flavours/glitch/components/status_action_bar.jsx
@@ -8,13 +8,15 @@ import ImmutablePropTypes from 'react-immutable-proptypes';
import ImmutablePureComponent from 'react-immutable-pure-component';
import DropdownMenuContainer from 'flavours/glitch/containers/dropdown_menu_container';
-import { me } from 'flavours/glitch/initial_state';
+import { me, maxReactions } from 'flavours/glitch/initial_state';
import { PERMISSION_MANAGE_USERS, PERMISSION_MANAGE_FEDERATION } from 'flavours/glitch/permissions';
import { accountAdminLink, statusAdminLink } from 'flavours/glitch/utils/backend_links';
import { IconButton } from './icon_button';
import { RelativeTimestamp } from './relative_timestamp';
+import EmojiPickerDropdown from '../features/compose/containers/emoji_picker_dropdown_container';
+
const messages = defineMessages({
delete: { id: 'status.delete', defaultMessage: 'Delete' },
redraft: { id: 'status.redraft', defaultMessage: 'Delete & re-draft' },
@@ -32,6 +34,7 @@ const messages = defineMessages({
cancel_reblog_private: { id: 'status.cancel_reblog_private', defaultMessage: 'Unboost' },
cannot_reblog: { id: 'status.cannot_reblog', defaultMessage: 'This post cannot be boosted' },
favourite: { id: 'status.favourite', defaultMessage: 'Favourite' },
+ react: { id: 'status.react', defaultMessage: 'React' },
bookmark: { id: 'status.bookmark', defaultMessage: 'Bookmark' },
open: { id: 'status.open', defaultMessage: 'Expand this status' },
report: { id: 'status.report', defaultMessage: 'Report @{name}' },
@@ -117,6 +120,16 @@ class StatusActionBar extends ImmutablePureComponent {
}
};
+ handleEmojiPick = data => {
+ const { signedIn } = this.context.identity;
+
+ if (signedIn) {
+ this.props.onReactionAdd(this.props.status.get('id'), data.native.replace(/:/g, ''));
+ } else {
+ this.props.onInteractionModal('favourite', this.props.status);
+ }
+ }
+
handleReblogClick = e => {
const { signedIn } = this.context.identity;
@@ -197,6 +210,8 @@ class StatusActionBar extends ImmutablePureComponent {
this.props.onAddFilter(this.props.status);
};
+ nop = () => {}
+
render () {
const { status, intl, withDismiss, withCounters, showReplyCount, scrollKey } = this.props;
const { permissions } = this.context.identity;
@@ -301,6 +316,17 @@ class StatusActionBar extends ImmutablePureComponent {
);
+ const canReact = status.get('reactions').filter(r => r.get('count') > 0 && r.get('me')).size < maxReactions;
+ const reactButton = (
+
+ );
+
return (
+
{filterButton}
diff --git a/app/javascript/flavours/glitch/components/status_reactions_bar.js b/app/javascript/flavours/glitch/components/status_reactions_bar.js
index 54f075d40..912e1b1ba 100644
--- a/app/javascript/flavours/glitch/components/status_reactions_bar.js
+++ b/app/javascript/flavours/glitch/components/status_reactions_bar.js
@@ -5,13 +5,11 @@ import { reduceMotion } from '../initial_state';
import spring from 'react-motion/lib/spring';
import TransitionMotion from 'react-motion/lib/TransitionMotion';
import classNames from 'classnames';
-import EmojiPickerDropdown from '../features/compose/containers/emoji_picker_dropdown_container';
-import Icon from './icon';
import React from 'react';
import unicodeMapping from '../features/emoji/emoji_unicode_mapping_light';
import AnimatedNumber from './animated_number';
import { assetHost } from '../utils/config';
-import { autoPlayGif, maxReactions } from '../initial_state';
+import { autoPlayGif } from '../initial_state';
export default class StatusReactionsBar extends ImmutablePureComponent {
@@ -61,8 +59,6 @@ export default class StatusReactionsBar extends ImmutablePureComponent {
emojiMap={this.props.emojiMap}
/>
))}
-
- {visibleReactions.size < maxReactions && } />}
)}
diff --git a/app/javascript/flavours/glitch/features/compose/components/emoji_picker_dropdown.jsx b/app/javascript/flavours/glitch/features/compose/components/emoji_picker_dropdown.jsx
index c2c803061..eaaa0a1ba 100644
--- a/app/javascript/flavours/glitch/features/compose/components/emoji_picker_dropdown.jsx
+++ b/app/javascript/flavours/glitch/features/compose/components/emoji_picker_dropdown.jsx
@@ -324,6 +324,7 @@ class EmojiPickerDropdown extends PureComponent {
onSkinTone: PropTypes.func.isRequired,
skinTone: PropTypes.number.isRequired,
button: PropTypes.node,
+ disabled: PropTypes.bool,
};
state = {
@@ -357,7 +358,7 @@ class EmojiPickerDropdown extends PureComponent {
};
onToggle = (e) => {
- if (!this.state.loading && (!e.key || e.key === 'Enter')) {
+ if (!this.state.disabled && !this.state.loading && (!e.key || e.key === 'Enter')) {
if (this.state.active) {
this.onHideDropdown();
} else {
diff --git a/app/javascript/flavours/glitch/features/status/components/action_bar.jsx b/app/javascript/flavours/glitch/features/status/components/action_bar.jsx
index 0ee947f41..aa8b6e515 100644
--- a/app/javascript/flavours/glitch/features/status/components/action_bar.jsx
+++ b/app/javascript/flavours/glitch/features/status/components/action_bar.jsx
@@ -9,9 +9,10 @@ import ImmutablePropTypes from 'react-immutable-proptypes';
import { IconButton } from 'flavours/glitch/components/icon_button';
import DropdownMenuContainer from 'flavours/glitch/containers/dropdown_menu_container';
-import { me } from 'flavours/glitch/initial_state';
+import { me, maxReactions } from 'flavours/glitch/initial_state';
import { PERMISSION_MANAGE_USERS, PERMISSION_MANAGE_FEDERATION } from 'flavours/glitch/permissions';
import { accountAdminLink, statusAdminLink } from 'flavours/glitch/utils/backend_links';
+import EmojiPickerDropdown from '../../compose/containers/emoji_picker_dropdown_container';
const messages = defineMessages({
delete: { id: 'status.delete', defaultMessage: 'Delete' },
@@ -25,6 +26,7 @@ const messages = defineMessages({
cancel_reblog_private: { id: 'status.cancel_reblog_private', defaultMessage: 'Unboost' },
cannot_reblog: { id: 'status.cannot_reblog', defaultMessage: 'This post cannot be boosted' },
favourite: { id: 'status.favourite', defaultMessage: 'Favourite' },
+ react: { id: 'status.react', defaultMessage: 'React' },
bookmark: { id: 'status.bookmark', defaultMessage: 'Bookmark' },
more: { id: 'status.more', defaultMessage: 'More' },
mute: { id: 'status.mute', defaultMessage: 'Mute @{name}' },
@@ -55,6 +57,7 @@ class ActionBar extends PureComponent {
onReply: PropTypes.func.isRequired,
onReblog: PropTypes.func.isRequired,
onFavourite: PropTypes.func.isRequired,
+ onReactionAdd: PropTypes.func.isRequired,
onBookmark: PropTypes.func.isRequired,
onMute: PropTypes.func,
onMuteConversation: PropTypes.func,
@@ -81,6 +84,10 @@ class ActionBar extends PureComponent {
this.props.onFavourite(this.props.status, e);
};
+ handleEmojiPick = data => {
+ this.props.onReactionAdd(this.props.status.get('id'), data.native.replace(/:/g, ''));
+ }
+
handleBookmarkClick = (e) => {
this.props.onBookmark(this.props.status, e);
};
@@ -140,6 +147,8 @@ class ActionBar extends PureComponent {
navigator.clipboard.writeText(url);
};
+ nop = () => {}
+
render () {
const { status, intl } = this.props;
const { signedIn, permissions } = this.context.identity;
@@ -202,6 +211,17 @@ class ActionBar extends PureComponent {
}
}
+ const canReact = status.get('reactions').filter(r => r.get('count') > 0 && r.get('me')).size < maxReactions;
+ const reactButton = (
+
+ );
+
const reblogPrivate = status.getIn(['account', 'id']) === me && status.get('visibility') === 'private';
let reblogTitle;
@@ -220,6 +240,7 @@ class ActionBar extends PureComponent {
+
diff --git a/app/javascript/flavours/glitch/features/status/index.jsx b/app/javascript/flavours/glitch/features/status/index.jsx
index f4b96acc2..797b5af2b 100644
--- a/app/javascript/flavours/glitch/features/status/index.jsx
+++ b/app/javascript/flavours/glitch/features/status/index.jsx
@@ -763,6 +763,7 @@ class Status extends ImmutablePureComponent {
status={status}
onReply={this.handleReplyClick}
onFavourite={this.handleFavouriteClick}
+ onReactionAdd={this.handleReactionAdd}
onReblog={this.handleReblogClick}
onBookmark={this.handleBookmarkClick}
onDelete={this.handleDeleteClick}