kopia lustrzana https://gitlab.com/soapbox-pub/soapbox
Partially fix post navigation
Signed-off-by: marcin mikołajczak <git@mkljczk.pl>strip-front-mentions
rodzic
4bc3a0c7dc
commit
1796a35951
|
@ -11,6 +11,10 @@ export default class Column extends React.PureComponent {
|
||||||
label: PropTypes.string,
|
label: PropTypes.string,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
setRef = c => {
|
||||||
|
this.node = c;
|
||||||
|
}
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
const { className, label, children, transparent, ...rest } = this.props;
|
const { className, label, children, transparent, ...rest } = this.props;
|
||||||
|
|
||||||
|
@ -20,6 +24,7 @@ export default class Column extends React.PureComponent {
|
||||||
aria-label={label}
|
aria-label={label}
|
||||||
className={classNames('column', className, { 'column--transparent': transparent })}
|
className={classNames('column', className, { 'column--transparent': transparent })}
|
||||||
{...rest}
|
{...rest}
|
||||||
|
ref={this.setRef}
|
||||||
>
|
>
|
||||||
{children}
|
{children}
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -4,24 +4,24 @@
|
||||||
|
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
import StatusContainer from 'soapbox/containers/status_container';
|
|
||||||
|
|
||||||
export default class MaterialStatus extends React.Component {
|
export default class MaterialStatus extends React.Component {
|
||||||
|
|
||||||
static propTypes = {
|
static propTypes = {
|
||||||
|
children: PropTypes.node,
|
||||||
hidden: PropTypes.bool,
|
hidden: PropTypes.bool,
|
||||||
}
|
}
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
// Performance: when hidden, don't render the wrapper divs
|
// Performance: when hidden, don't render the wrapper divs
|
||||||
if (this.props.hidden) {
|
if (this.props.hidden) {
|
||||||
return <StatusContainer {...this.props} />;
|
return this.props.children;
|
||||||
}
|
}
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className='material-status' tabIndex={-1}>
|
<div className='material-status' tabIndex={-1}>
|
||||||
<div className='material-status__status focusable' tabIndex={0}>
|
<div className='material-status__status focusable' tabIndex={0}>
|
||||||
<StatusContainer {...this.props} focusable={false} />
|
{this.props.children}
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
|
|
|
@ -95,6 +95,7 @@ class Status extends ImmutablePureComponent {
|
||||||
displayMedia: PropTypes.string,
|
displayMedia: PropTypes.string,
|
||||||
allowedEmoji: ImmutablePropTypes.list,
|
allowedEmoji: ImmutablePropTypes.list,
|
||||||
focusable: PropTypes.bool,
|
focusable: PropTypes.bool,
|
||||||
|
component: PropTypes.func,
|
||||||
};
|
};
|
||||||
|
|
||||||
static defaultProps = {
|
static defaultProps = {
|
||||||
|
@ -316,7 +317,7 @@ class Status extends ImmutablePureComponent {
|
||||||
const poll = null;
|
const poll = null;
|
||||||
let statusAvatar, prepend, rebloggedByText, reblogContent;
|
let statusAvatar, prepend, rebloggedByText, reblogContent;
|
||||||
|
|
||||||
const { intl, hidden, featured, otherAccounts, unread, showThread, group } = this.props;
|
const { intl, hidden, featured, otherAccounts, unread, showThread, group, wrapperComponent: WrapperComponent } = this.props;
|
||||||
|
|
||||||
// FIXME: why does this need to reassign status and account??
|
// FIXME: why does this need to reassign status and account??
|
||||||
let { status, account, ...other } = this.props; // eslint-disable-line prefer-const
|
let { status, account, ...other } = this.props; // eslint-disable-line prefer-const
|
||||||
|
@ -494,72 +495,76 @@ class Status extends ImmutablePureComponent {
|
||||||
const favicon = status.getIn(['account', 'pleroma', 'favicon']);
|
const favicon = status.getIn(['account', 'pleroma', 'favicon']);
|
||||||
const domain = getDomain(status.get('account'));
|
const domain = getDomain(status.get('account'));
|
||||||
|
|
||||||
|
const wrappedStatus = (
|
||||||
|
<div className={classNames('status__wrapper', `status__wrapper-${status.get('visibility')}`, { 'status__wrapper-reply': !!status.get('in_reply_to_id'), read: unread === false, focusable: this.props.focusable && !this.props.muted })} tabIndex={this.props.focusable && !this.props.muted ? 0 : null} data-featured={featured ? 'true' : null} aria-label={textForScreenReader(intl, status, rebloggedByText)} ref={this.handleRef}>
|
||||||
|
{prepend}
|
||||||
|
|
||||||
|
<div className={classNames('status', `status-${status.get('visibility')}`, { 'status-reply': !!status.get('in_reply_to_id'), muted: this.props.muted, read: unread === false })} data-id={status.get('id')}>
|
||||||
|
<div className='status__expand' onClick={this.handleExpandClick} role='presentation' />
|
||||||
|
<div className='status__info'>
|
||||||
|
<NavLink to={statusUrl} className='status__relative-time'>
|
||||||
|
<RelativeTimestamp timestamp={status.get('created_at')} />
|
||||||
|
</NavLink>
|
||||||
|
|
||||||
|
{favicon &&
|
||||||
|
<div className='status__favicon'>
|
||||||
|
<Link to={`/timeline/${domain}`}>
|
||||||
|
<img src={favicon} alt='' title={domain} />
|
||||||
|
</Link>
|
||||||
|
</div>}
|
||||||
|
|
||||||
|
<div className='status__profile'>
|
||||||
|
<div className='status__avatar'>
|
||||||
|
<HoverRefWrapper accountId={status.getIn(['account', 'id'])}>
|
||||||
|
<NavLink to={`/@${status.getIn(['account', 'acct'])}`} title={status.getIn(['account', 'acct'])}>
|
||||||
|
{statusAvatar}
|
||||||
|
</NavLink>
|
||||||
|
</HoverRefWrapper>
|
||||||
|
</div>
|
||||||
|
<NavLink to={`/@${status.getIn(['account', 'acct'])}`} title={status.getIn(['account', 'acct'])} className='status__display-name'>
|
||||||
|
<DisplayName account={status.get('account')} others={otherAccounts} />
|
||||||
|
</NavLink>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
{!group && status.get('group') && (
|
||||||
|
<div className='status__meta'>
|
||||||
|
Posted in <NavLink to={`/groups/${status.getIn(['group', 'id'])}`}>{status.getIn(['group', 'title'])}</NavLink>
|
||||||
|
</div>
|
||||||
|
)}
|
||||||
|
|
||||||
|
<StatusContent
|
||||||
|
status={status}
|
||||||
|
reblogContent={reblogContent}
|
||||||
|
onClick={this.handleClick}
|
||||||
|
expanded={!status.get('hidden')}
|
||||||
|
onExpandedToggle={this.handleExpandedToggle}
|
||||||
|
collapsable
|
||||||
|
/>
|
||||||
|
|
||||||
|
{media}
|
||||||
|
{poll}
|
||||||
|
|
||||||
|
{showThread && status.get('in_reply_to_id') && status.get('in_reply_to_account_id') === status.getIn(['account', 'id']) && (
|
||||||
|
<button className='status__content__read-more-button' onClick={this.handleClick}>
|
||||||
|
<FormattedMessage id='status.show_thread' defaultMessage='Show thread' />
|
||||||
|
</button>
|
||||||
|
)}
|
||||||
|
|
||||||
|
<StatusActionBar
|
||||||
|
status={status}
|
||||||
|
account={account}
|
||||||
|
emojiSelectorFocused={this.state.emojiSelectorFocused}
|
||||||
|
handleEmojiSelectorUnfocus={this.handleEmojiSelectorUnfocus}
|
||||||
|
{...other}
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<HotKeys handlers={handlers}>
|
<HotKeys handlers={handlers}>
|
||||||
<div className={classNames('status__wrapper', `status__wrapper-${status.get('visibility')}`, { 'status__wrapper-reply': !!status.get('in_reply_to_id'), read: unread === false, focusable: this.props.focusable && !this.props.muted })} tabIndex={this.props.focusable && !this.props.muted ? 0 : null} data-featured={featured ? 'true' : null} aria-label={textForScreenReader(intl, status, rebloggedByText)} ref={this.handleRef}>
|
{WrapperComponent ? <WrapperComponent>{wrappedStatus}</WrapperComponent> : wrappedStatus}
|
||||||
{prepend}
|
|
||||||
|
|
||||||
<div className={classNames('status', `status-${status.get('visibility')}`, { 'status-reply': !!status.get('in_reply_to_id'), muted: this.props.muted, read: unread === false })} data-id={status.get('id')}>
|
|
||||||
<div className='status__expand' onClick={this.handleExpandClick} role='presentation' />
|
|
||||||
<div className='status__info'>
|
|
||||||
<NavLink to={statusUrl} className='status__relative-time'>
|
|
||||||
<RelativeTimestamp timestamp={status.get('created_at')} />
|
|
||||||
</NavLink>
|
|
||||||
|
|
||||||
{favicon &&
|
|
||||||
<div className='status__favicon'>
|
|
||||||
<Link to={`/timeline/${domain}`}>
|
|
||||||
<img src={favicon} alt='' title={domain} />
|
|
||||||
</Link>
|
|
||||||
</div>}
|
|
||||||
|
|
||||||
<div className='status__profile'>
|
|
||||||
<div className='status__avatar'>
|
|
||||||
<HoverRefWrapper accountId={status.getIn(['account', 'id'])}>
|
|
||||||
<NavLink to={`/@${status.getIn(['account', 'acct'])}`} title={status.getIn(['account', 'acct'])}>
|
|
||||||
{statusAvatar}
|
|
||||||
</NavLink>
|
|
||||||
</HoverRefWrapper>
|
|
||||||
</div>
|
|
||||||
<NavLink to={`/@${status.getIn(['account', 'acct'])}`} title={status.getIn(['account', 'acct'])} className='status__display-name'>
|
|
||||||
<DisplayName account={status.get('account')} others={otherAccounts} />
|
|
||||||
</NavLink>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
{!group && status.get('group') && (
|
|
||||||
<div className='status__meta'>
|
|
||||||
Posted in <NavLink to={`/groups/${status.getIn(['group', 'id'])}`}>{status.getIn(['group', 'title'])}</NavLink>
|
|
||||||
</div>
|
|
||||||
)}
|
|
||||||
|
|
||||||
<StatusContent
|
|
||||||
status={status}
|
|
||||||
reblogContent={reblogContent}
|
|
||||||
onClick={this.handleClick}
|
|
||||||
expanded={!status.get('hidden')}
|
|
||||||
onExpandedToggle={this.handleExpandedToggle}
|
|
||||||
collapsable
|
|
||||||
/>
|
|
||||||
|
|
||||||
{media}
|
|
||||||
{poll}
|
|
||||||
|
|
||||||
{showThread && status.get('in_reply_to_id') && status.get('in_reply_to_account_id') === status.getIn(['account', 'id']) && (
|
|
||||||
<button className='status__content__read-more-button' onClick={this.handleClick}>
|
|
||||||
<FormattedMessage id='status.show_thread' defaultMessage='Show thread' />
|
|
||||||
</button>
|
|
||||||
)}
|
|
||||||
|
|
||||||
<StatusActionBar
|
|
||||||
status={status}
|
|
||||||
account={account}
|
|
||||||
emojiSelectorFocused={this.state.emojiSelectorFocused}
|
|
||||||
handleEmojiSelectorUnfocus={this.handleEmojiSelectorUnfocus}
|
|
||||||
{...other}
|
|
||||||
/>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</HotKeys>
|
</HotKeys>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
|
@ -3,6 +3,7 @@ import React from 'react';
|
||||||
import { FormattedMessage, defineMessages } from 'react-intl';
|
import { FormattedMessage, defineMessages } from 'react-intl';
|
||||||
import ImmutablePropTypes from 'react-immutable-proptypes';
|
import ImmutablePropTypes from 'react-immutable-proptypes';
|
||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
|
import StatusContainer from 'soapbox/containers/status_container';
|
||||||
import MaterialStatus from 'soapbox/components/material_status';
|
import MaterialStatus from 'soapbox/components/material_status';
|
||||||
import PendingStatus from 'soapbox/features/ui/components/pending_status';
|
import PendingStatus from 'soapbox/features/ui/components/pending_status';
|
||||||
import ImmutablePureComponent from 'react-immutable-pure-component';
|
import ImmutablePureComponent from 'react-immutable-pure-component';
|
||||||
|
@ -110,7 +111,7 @@ export default class StatusList extends ImmutablePureComponent {
|
||||||
const { timelineId, withGroupAdmin, group } = this.props;
|
const { timelineId, withGroupAdmin, group } = this.props;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<MaterialStatus
|
<StatusContainer
|
||||||
key={statusId}
|
key={statusId}
|
||||||
id={statusId}
|
id={statusId}
|
||||||
onMoveUp={this.handleMoveUp}
|
onMoveUp={this.handleMoveUp}
|
||||||
|
@ -119,6 +120,8 @@ export default class StatusList extends ImmutablePureComponent {
|
||||||
group={group}
|
group={group}
|
||||||
withGroupAdmin={withGroupAdmin}
|
withGroupAdmin={withGroupAdmin}
|
||||||
showThread
|
showThread
|
||||||
|
wrapperComponent={MaterialStatus}
|
||||||
|
focusable={false}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -150,7 +153,7 @@ export default class StatusList extends ImmutablePureComponent {
|
||||||
if (!featuredStatusIds) return null;
|
if (!featuredStatusIds) return null;
|
||||||
|
|
||||||
return featuredStatusIds.map(statusId => (
|
return featuredStatusIds.map(statusId => (
|
||||||
<MaterialStatus
|
<StatusContainer
|
||||||
key={`f-${statusId}`}
|
key={`f-${statusId}`}
|
||||||
id={statusId}
|
id={statusId}
|
||||||
featured
|
featured
|
||||||
|
@ -158,6 +161,8 @@ export default class StatusList extends ImmutablePureComponent {
|
||||||
onMoveDown={this.handleMoveDown}
|
onMoveDown={this.handleMoveDown}
|
||||||
contextType={timelineId}
|
contextType={timelineId}
|
||||||
showThread
|
showThread
|
||||||
|
wrapperComponent={MaterialStatus}
|
||||||
|
focusable={false}
|
||||||
/>
|
/>
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
import { OrderedSet as ImmutableOrderedSet } from 'immutable';
|
import { List as ImmutableList, OrderedSet as ImmutableOrderedSet } from 'immutable';
|
||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { connect } from 'react-redux';
|
import { connect } from 'react-redux';
|
||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
|
@ -410,10 +410,10 @@ class Status extends ImmutablePureComponent {
|
||||||
if (id === status.get('id')) {
|
if (id === status.get('id')) {
|
||||||
this._selectChild(ancestorsIds.size - 1, true);
|
this._selectChild(ancestorsIds.size - 1, true);
|
||||||
} else {
|
} else {
|
||||||
let index = ancestorsIds.indexOf(id);
|
let index = ImmutableList(ancestorsIds).indexOf(id);
|
||||||
|
|
||||||
if (index === -1) {
|
if (index === -1) {
|
||||||
index = descendantsIds.indexOf(id);
|
index = ImmutableList(descendantsIds).indexOf(id);
|
||||||
this._selectChild(ancestorsIds.size + index, true);
|
this._selectChild(ancestorsIds.size + index, true);
|
||||||
} else {
|
} else {
|
||||||
this._selectChild(index - 1, true);
|
this._selectChild(index - 1, true);
|
||||||
|
@ -427,10 +427,10 @@ class Status extends ImmutablePureComponent {
|
||||||
if (id === status.get('id')) {
|
if (id === status.get('id')) {
|
||||||
this._selectChild(ancestorsIds.size + 1, false);
|
this._selectChild(ancestorsIds.size + 1, false);
|
||||||
} else {
|
} else {
|
||||||
let index = ancestorsIds.indexOf(id);
|
let index = ImmutableList(ancestorsIds).indexOf(id);
|
||||||
|
|
||||||
if (index === -1) {
|
if (index === -1) {
|
||||||
index = descendantsIds.indexOf(id);
|
index = ImmutableList(descendantsIds).indexOf(id);
|
||||||
this._selectChild(ancestorsIds.size + index + 2, false);
|
this._selectChild(ancestorsIds.size + index + 2, false);
|
||||||
} else {
|
} else {
|
||||||
this._selectChild(index + 1, false);
|
this._selectChild(index + 1, false);
|
||||||
|
|
Ładowanie…
Reference in New Issue