You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

85 lines
2.7 KiB

  1. import React from 'react';
  2. import PropTypes from 'prop-types';
  3. import ImmutablePropTypes from 'react-immutable-proptypes';
  4. import ImmutablePureComponent from 'react-immutable-pure-component';
  5. import { connect } from 'react-redux';
  6. import { makeGetAccount } from 'mastodon/selectors';
  7. import Avatar from 'mastodon/components/avatar';
  8. import DisplayName from 'mastodon/components/display_name';
  9. import Permalink from 'mastodon/components/permalink';
  10. import IconButton from 'mastodon/components/icon_button';
  11. import { injectIntl, defineMessages } from 'react-intl';
  12. import { followAccount, unfollowAccount } from 'mastodon/actions/accounts';
  13. const messages = defineMessages({
  14. follow: { id: 'account.follow', defaultMessage: 'Follow' },
  15. unfollow: { id: 'account.unfollow', defaultMessage: 'Unfollow' },
  16. });
  17. const makeMapStateToProps = () => {
  18. const getAccount = makeGetAccount();
  19. const mapStateToProps = (state, props) => ({
  20. account: getAccount(state, props.id),
  21. });
  22. return mapStateToProps;
  23. };
  24. const getFirstSentence = str => {
  25. const arr = str.split(/(([\.\?!]+\s)|[.。?!\n•])/);
  26. return arr[0];
  27. };
  28. export default @connect(makeMapStateToProps)
  29. @injectIntl
  30. class Account extends ImmutablePureComponent {
  31. static propTypes = {
  32. account: ImmutablePropTypes.map.isRequired,
  33. intl: PropTypes.object.isRequired,
  34. dispatch: PropTypes.func.isRequired,
  35. };
  36. handleFollow = () => {
  37. const { account, dispatch } = this.props;
  38. if (account.getIn(['relationship', 'following']) || account.getIn(['relationship', 'requested'])) {
  39. dispatch(unfollowAccount(account.get('id')));
  40. } else {
  41. dispatch(followAccount(account.get('id')));
  42. }
  43. }
  44. render () {
  45. const { account, intl } = this.props;
  46. let button;
  47. if (account.getIn(['relationship', 'following'])) {
  48. button = <IconButton icon='check' title={intl.formatMessage(messages.unfollow)} active onClick={this.handleFollow} />;
  49. } else {
  50. button = <IconButton icon='plus' title={intl.formatMessage(messages.follow)} onClick={this.handleFollow} />;
  51. }
  52. return (
  53. <div className='account follow-recommendations-account'>
  54. <div className='account__wrapper'>
  55. <Permalink className='account__display-name account__display-name--with-note' title={account.get('acct')} href={account.get('url')} to={`/accounts/${account.get('id')}`}>
  56. <div className='account__avatar-wrapper'><Avatar account={account} size={36} /></div>
  57. <DisplayName account={account} />
  58. <div className='account__note'>{getFirstSentence(account.get('note_plain'))}</div>
  59. </Permalink>
  60. <div className='account__relationship'>
  61. {button}
  62. </div>
  63. </div>
  64. </div>
  65. );
  66. }
  67. }