From 73c0c36e7be8a543e4d6b326a22dcbfa9d5b566d Mon Sep 17 00:00:00 2001 From: Eugen Rochko Date: Fri, 1 Jun 2018 19:18:37 +0200 Subject: Improve trends layout (#7700) * Allow collapsing trends, responsively hide trends * Add trends column --- .../features/getting_started/components/trends.js | 19 ++++++- .../getting_started/containers/trends_container.js | 3 + .../mastodon/features/getting_started/index.js | 10 +++- app/javascript/mastodon/features/trends/index.js | 66 ++++++++++++++++++++++ app/javascript/mastodon/features/ui/index.js | 2 + .../mastodon/features/ui/util/async-components.js | 4 ++ app/javascript/mastodon/reducers/settings.js | 4 ++ app/javascript/styles/mastodon/components.scss | 24 ++++++-- 8 files changed, 124 insertions(+), 8 deletions(-) create mode 100644 app/javascript/mastodon/features/trends/index.js (limited to 'app/javascript') diff --git a/app/javascript/mastodon/features/getting_started/components/trends.js b/app/javascript/mastodon/features/getting_started/components/trends.js index 5d6b7ed8c..96a646bea 100644 --- a/app/javascript/mastodon/features/getting_started/components/trends.js +++ b/app/javascript/mastodon/features/getting_started/components/trends.js @@ -5,6 +5,7 @@ import PropTypes from 'prop-types'; import ImmutablePropTypes from 'react-immutable-proptypes'; import { FormattedMessage, defineMessages } from 'react-intl'; import Hashtag from '../../../components/hashtag'; +import { Link } from 'react-router-dom'; const messages = defineMessages({ refresh_trends: { id: 'trends.refresh', defaultMessage: 'Refresh' }, @@ -19,6 +20,9 @@ export default class Trends extends ImmutablePureComponent { static propTypes = { trends: ImmutablePropTypes.list, loading: PropTypes.bool.isRequired, + showTrends: PropTypes.bool.isRequired, + fetchTrends: PropTypes.func.isRequired, + toggleTrends: PropTypes.func.isRequired, }; componentDidMount () { @@ -29,8 +33,12 @@ export default class Trends extends ImmutablePureComponent { this.props.fetchTrends(); } + handleToggle = () => { + this.props.toggleTrends(!this.props.showTrends); + } + render () { - const { intl, trends, loading } = this.props; + const { intl, trends, loading, showTrends } = this.props; if (!trends || trends.size < 1) { return null; @@ -44,13 +52,18 @@ export default class Trends extends ImmutablePureComponent { +
- + {showTrends && } +
-
{trends.take(3).map(hashtag => )}
+ {showTrends &&
+ {trends.take(3).map(hashtag => )} + +
} ); } diff --git a/app/javascript/mastodon/features/getting_started/containers/trends_container.js b/app/javascript/mastodon/features/getting_started/containers/trends_container.js index 549556b76..65faeae86 100644 --- a/app/javascript/mastodon/features/getting_started/containers/trends_container.js +++ b/app/javascript/mastodon/features/getting_started/containers/trends_container.js @@ -2,14 +2,17 @@ import { connect } from 'react-redux'; import { injectIntl } from 'react-intl'; import { fetchTrends } from '../../../actions/trends'; import Trends from '../components/trends'; +import { changeSetting } from '../../../actions/settings'; const mapStateToProps = state => ({ trends: state.getIn(['trends', 'items']), loading: state.getIn(['trends', 'isLoading']), + showTrends: state.getIn(['settings', 'trends', 'show']), }); const mapDispatchToProps = dispatch => ({ fetchTrends: () => dispatch(fetchTrends()), + toggleTrends: show => dispatch(changeSetting(['trends', 'show'], show)), }); export default injectIntl(connect(mapStateToProps, mapDispatchToProps)(Trends)); diff --git a/app/javascript/mastodon/features/getting_started/index.js b/app/javascript/mastodon/features/getting_started/index.js index 9575afd7a..67a5b282a 100644 --- a/app/javascript/mastodon/features/getting_started/index.js +++ b/app/javascript/mastodon/features/getting_started/index.js @@ -80,6 +80,7 @@ export default class GettingStarted extends ImmutablePureComponent { const navItems = []; let i = 1; + let height = 0; if (multiColumn) { navItems.push( @@ -88,6 +89,8 @@ export default class GettingStarted extends ImmutablePureComponent { , ); + + height += 34*2 + 48*2; } navItems.push( @@ -96,8 +99,11 @@ export default class GettingStarted extends ImmutablePureComponent { ); + height += 48*3; + if (myAccount.get('locked')) { navItems.push(); + height += 48; } if (!multiColumn) { @@ -106,6 +112,8 @@ export default class GettingStarted extends ImmutablePureComponent { , ); + + height += 34 + 48*2; } return ( @@ -119,7 +127,7 @@ export default class GettingStarted extends ImmutablePureComponent { } -
+
{!multiColumn && } {navItems}
diff --git a/app/javascript/mastodon/features/trends/index.js b/app/javascript/mastodon/features/trends/index.js new file mode 100644 index 000000000..f33af3e2e --- /dev/null +++ b/app/javascript/mastodon/features/trends/index.js @@ -0,0 +1,66 @@ +import React from 'react'; +import PropTypes from 'prop-types'; +import ImmutablePropTypes from 'react-immutable-proptypes'; +import ImmutablePureComponent from 'react-immutable-pure-component'; +import { connect } from 'react-redux'; +import { injectIntl, defineMessages } from 'react-intl'; +import Column from '../ui/components/column'; +import ColumnHeader from '../../components/column_header'; +import Hashtag from '../../components/hashtag'; +import classNames from 'classnames'; +import { fetchTrends } from '../../actions/trends'; + +const messages = defineMessages({ + title: { id: 'trends.header', defaultMessage: 'Trending now' }, + refreshTrends: { id: 'trends.refresh', defaultMessage: 'Refresh trends' }, +}); + +const mapStateToProps = state => ({ + trends: state.getIn(['trends', 'items']), + loading: state.getIn(['trends', 'isLoading']), +}); + +const mapDispatchToProps = dispatch => ({ + fetchTrends: () => dispatch(fetchTrends()), +}); + +@connect(mapStateToProps, mapDispatchToProps) +@injectIntl +export default class Trends extends ImmutablePureComponent { + + static propTypes = { + intl: PropTypes.object.isRequired, + trends: ImmutablePropTypes.list, + fetchTrends: PropTypes.func.isRequired, + loading: PropTypes.bool, + }; + + componentDidMount () { + this.props.fetchTrends(); + } + + handleRefresh = () => { + this.props.fetchTrends(); + } + + render () { + const { trends, loading, intl } = this.props; + + return ( + + + )} + /> + +
+ {trends && trends.map(hashtag => )} +
+
+ ); + } + +} diff --git a/app/javascript/mastodon/features/ui/index.js b/app/javascript/mastodon/features/ui/index.js index f1409b946..bfed02f98 100644 --- a/app/javascript/mastodon/features/ui/index.js +++ b/app/javascript/mastodon/features/ui/index.js @@ -42,6 +42,7 @@ import { Mutes, PinnedStatuses, Lists, + Trends, } from './util/async-components'; import { HotKeys } from 'react-hotkeys'; import { me } from '../../initial_state'; @@ -154,6 +155,7 @@ class SwitchingColumnsArea extends React.PureComponent { + diff --git a/app/javascript/mastodon/features/ui/util/async-components.js b/app/javascript/mastodon/features/ui/util/async-components.js index 8cf2a6e7d..dfc796a09 100644 --- a/app/javascript/mastodon/features/ui/util/async-components.js +++ b/app/javascript/mastodon/features/ui/util/async-components.js @@ -129,3 +129,7 @@ export function EmbedModal () { export function ListEditor () { return import(/* webpackChunkName: "features/list_editor" */'../../list_editor'); } + +export function Trends () { + return import(/* webpackChunkName: "features/trends" */'../../trends'); +} diff --git a/app/javascript/mastodon/reducers/settings.js b/app/javascript/mastodon/reducers/settings.js index de8865e43..0a034d739 100644 --- a/app/javascript/mastodon/reducers/settings.js +++ b/app/javascript/mastodon/reducers/settings.js @@ -64,6 +64,10 @@ const initialState = ImmutableMap({ body: '', }), }), + + trends: ImmutableMap({ + show: true, + }), }); const defaultColumns = fromJS([ diff --git a/app/javascript/styles/mastodon/components.scss b/app/javascript/styles/mastodon/components.scss index 124998a48..39eaf5061 100644 --- a/app/javascript/styles/mastodon/components.scss +++ b/app/javascript/styles/mastodon/components.scss @@ -2178,8 +2178,7 @@ a.account__display-name { } .getting-started__wrapper { - position: relative; - overflow-y: auto; + flex: 0 0 auto; } .flex-spacer { @@ -2187,7 +2186,6 @@ a.account__display-name { } .getting-started { - flex: 1 0 auto; color: $dark-text-color; p { @@ -2228,7 +2226,23 @@ a.account__display-name { &__trends { background: $ui-base-color; - flex: 1 1 auto; + flex: 0 1 auto; + + @media screen and (max-height: 810px) { + .trends__item:nth-child(3) { + display: none; + } + } + + @media screen and (max-height: 720px) { + .trends__item:nth-child(2) { + display: none; + } + } + + @media screen and (max-height: 670px) { + display: none; + } } &__scrollable { @@ -2460,8 +2474,10 @@ a.status-card { line-height: inherit; margin: 0; padding: 15px; + box-sizing: border-box; width: 100%; clear: both; + text-decoration: none; &:hover { background: lighten($ui-base-color, 2%); -- cgit