Change account note design to match upstream's (#2495)
parent
046141d2a4
commit
335cfab32f
|
@ -4,19 +4,12 @@ export const ACCOUNT_NOTE_SUBMIT_REQUEST = 'ACCOUNT_NOTE_SUBMIT_REQUEST';
|
||||||
export const ACCOUNT_NOTE_SUBMIT_SUCCESS = 'ACCOUNT_NOTE_SUBMIT_SUCCESS';
|
export const ACCOUNT_NOTE_SUBMIT_SUCCESS = 'ACCOUNT_NOTE_SUBMIT_SUCCESS';
|
||||||
export const ACCOUNT_NOTE_SUBMIT_FAIL = 'ACCOUNT_NOTE_SUBMIT_FAIL';
|
export const ACCOUNT_NOTE_SUBMIT_FAIL = 'ACCOUNT_NOTE_SUBMIT_FAIL';
|
||||||
|
|
||||||
export const ACCOUNT_NOTE_INIT_EDIT = 'ACCOUNT_NOTE_INIT_EDIT';
|
export function submitAccountNote(id, value) {
|
||||||
export const ACCOUNT_NOTE_CANCEL = 'ACCOUNT_NOTE_CANCEL';
|
|
||||||
|
|
||||||
export const ACCOUNT_NOTE_CHANGE_COMMENT = 'ACCOUNT_NOTE_CHANGE_COMMENT';
|
|
||||||
|
|
||||||
export function submitAccountNote() {
|
|
||||||
return (dispatch, getState) => {
|
return (dispatch, getState) => {
|
||||||
dispatch(submitAccountNoteRequest());
|
dispatch(submitAccountNoteRequest());
|
||||||
|
|
||||||
const id = getState().getIn(['account_notes', 'edit', 'account_id']);
|
|
||||||
|
|
||||||
api(getState).post(`/api/v1/accounts/${id}/note`, {
|
api(getState).post(`/api/v1/accounts/${id}/note`, {
|
||||||
comment: getState().getIn(['account_notes', 'edit', 'comment']),
|
comment: value,
|
||||||
}).then(response => {
|
}).then(response => {
|
||||||
dispatch(submitAccountNoteSuccess(response.data));
|
dispatch(submitAccountNoteSuccess(response.data));
|
||||||
}).catch(error => dispatch(submitAccountNoteFail(error)));
|
}).catch(error => dispatch(submitAccountNoteFail(error)));
|
||||||
|
@ -42,28 +35,3 @@ export function submitAccountNoteFail(error) {
|
||||||
error,
|
error,
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export function initEditAccountNote(account) {
|
|
||||||
return (dispatch, getState) => {
|
|
||||||
const comment = getState().getIn(['relationships', account.get('id'), 'note']);
|
|
||||||
|
|
||||||
dispatch({
|
|
||||||
type: ACCOUNT_NOTE_INIT_EDIT,
|
|
||||||
account,
|
|
||||||
comment,
|
|
||||||
});
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
export function cancelAccountNote() {
|
|
||||||
return {
|
|
||||||
type: ACCOUNT_NOTE_CANCEL,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
||||||
export function changeAccountNoteComment(comment) {
|
|
||||||
return {
|
|
||||||
type: ACCOUNT_NOTE_CHANGE_COMMENT,
|
|
||||||
comment,
|
|
||||||
};
|
|
||||||
}
|
|
||||||
|
|
|
@ -1,108 +1,174 @@
|
||||||
import PropTypes from 'prop-types';
|
import PropTypes from 'prop-types';
|
||||||
|
import { PureComponent } from 'react';
|
||||||
|
|
||||||
import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
|
import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
|
||||||
|
|
||||||
|
import { is } from 'immutable';
|
||||||
import ImmutablePropTypes from 'react-immutable-proptypes';
|
import ImmutablePropTypes from 'react-immutable-proptypes';
|
||||||
import ImmutablePureComponent from 'react-immutable-pure-component';
|
import ImmutablePureComponent from 'react-immutable-pure-component';
|
||||||
|
|
||||||
import Textarea from 'react-textarea-autosize';
|
import Textarea from 'react-textarea-autosize';
|
||||||
|
|
||||||
import { Icon } from 'flavours/glitch/components/icon';
|
|
||||||
|
|
||||||
const messages = defineMessages({
|
const messages = defineMessages({
|
||||||
placeholder: { id: 'account_note.glitch_placeholder', defaultMessage: 'No comment provided' },
|
placeholder: { id: 'account_note.placeholder', defaultMessage: 'Click to add a note' },
|
||||||
});
|
});
|
||||||
|
|
||||||
class Header extends ImmutablePureComponent {
|
class InlineAlert extends PureComponent {
|
||||||
|
|
||||||
|
static propTypes = {
|
||||||
|
show: PropTypes.bool,
|
||||||
|
};
|
||||||
|
|
||||||
|
state = {
|
||||||
|
mountMessage: false,
|
||||||
|
};
|
||||||
|
|
||||||
|
static TRANSITION_DELAY = 200;
|
||||||
|
|
||||||
|
UNSAFE_componentWillReceiveProps (nextProps) {
|
||||||
|
if (!this.props.show && nextProps.show) {
|
||||||
|
this.setState({ mountMessage: true });
|
||||||
|
} else if (this.props.show && !nextProps.show) {
|
||||||
|
setTimeout(() => this.setState({ mountMessage: false }), InlineAlert.TRANSITION_DELAY);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
render () {
|
||||||
|
const { show } = this.props;
|
||||||
|
const { mountMessage } = this.state;
|
||||||
|
|
||||||
|
return (
|
||||||
|
<span aria-live='polite' role='status' className='inline-alert' style={{ opacity: show ? 1 : 0 }}>
|
||||||
|
{mountMessage && <FormattedMessage id='generic.saved' defaultMessage='Saved' />}
|
||||||
|
</span>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
class AccountNote extends ImmutablePureComponent {
|
||||||
|
|
||||||
static propTypes = {
|
static propTypes = {
|
||||||
account: ImmutablePropTypes.map.isRequired,
|
account: ImmutablePropTypes.map.isRequired,
|
||||||
isEditing: PropTypes.bool,
|
value: PropTypes.string,
|
||||||
isSubmitting: PropTypes.bool,
|
onSave: PropTypes.func.isRequired,
|
||||||
accountNote: PropTypes.string,
|
|
||||||
onEditAccountNote: PropTypes.func.isRequired,
|
|
||||||
onCancelAccountNote: PropTypes.func.isRequired,
|
|
||||||
onSaveAccountNote: PropTypes.func.isRequired,
|
|
||||||
onChangeAccountNote: PropTypes.func.isRequired,
|
|
||||||
intl: PropTypes.object.isRequired,
|
intl: PropTypes.object.isRequired,
|
||||||
};
|
};
|
||||||
|
|
||||||
handleChangeAccountNote = (e) => {
|
state = {
|
||||||
this.props.onChangeAccountNote(e.target.value);
|
value: null,
|
||||||
|
saving: false,
|
||||||
|
saved: false,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
UNSAFE_componentWillMount () {
|
||||||
|
this._reset();
|
||||||
|
}
|
||||||
|
|
||||||
|
UNSAFE_componentWillReceiveProps (nextProps) {
|
||||||
|
const accountWillChange = !is(this.props.account, nextProps.account);
|
||||||
|
const newState = {};
|
||||||
|
|
||||||
|
if (accountWillChange && this._isDirty()) {
|
||||||
|
this._save(false);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (accountWillChange || nextProps.value === this.state.value) {
|
||||||
|
newState.saving = false;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this.props.value !== nextProps.value) {
|
||||||
|
newState.value = nextProps.value;
|
||||||
|
}
|
||||||
|
|
||||||
|
this.setState(newState);
|
||||||
|
}
|
||||||
|
|
||||||
componentWillUnmount () {
|
componentWillUnmount () {
|
||||||
if (this.props.isEditing) {
|
if (this._isDirty()) {
|
||||||
this.props.onCancelAccountNote();
|
this._save(false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
setTextareaRef = c => {
|
||||||
|
this.textarea = c;
|
||||||
|
};
|
||||||
|
|
||||||
|
handleChange = e => {
|
||||||
|
this.setState({ value: e.target.value, saving: false });
|
||||||
|
};
|
||||||
|
|
||||||
handleKeyDown = e => {
|
handleKeyDown = e => {
|
||||||
if (e.keyCode === 13 && (e.ctrlKey || e.metaKey)) {
|
if (e.keyCode === 13 && (e.ctrlKey || e.metaKey)) {
|
||||||
this.props.onSaveAccountNote();
|
e.preventDefault();
|
||||||
|
|
||||||
|
this._save();
|
||||||
|
|
||||||
|
if (this.textarea) {
|
||||||
|
this.textarea.blur();
|
||||||
|
}
|
||||||
} else if (e.keyCode === 27) {
|
} else if (e.keyCode === 27) {
|
||||||
this.props.onCancelAccountNote();
|
e.preventDefault();
|
||||||
|
|
||||||
|
this._reset(() => {
|
||||||
|
if (this.textarea) {
|
||||||
|
this.textarea.blur();
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
handleBlur = () => {
|
||||||
|
if (this._isDirty()) {
|
||||||
|
this._save();
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
_save (showMessage = true) {
|
||||||
|
this.setState({ saving: true }, () => this.props.onSave(this.state.value));
|
||||||
|
|
||||||
|
if (showMessage) {
|
||||||
|
this.setState({ saved: true }, () => setTimeout(() => this.setState({ saved: false }), 2000));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
_reset (callback) {
|
||||||
|
this.setState({ value: this.props.value }, callback);
|
||||||
|
}
|
||||||
|
|
||||||
|
_isDirty () {
|
||||||
|
return !this.state.saving && this.props.value !== null && this.state.value !== null && this.state.value !== this.props.value;
|
||||||
|
}
|
||||||
|
|
||||||
render () {
|
render () {
|
||||||
const { account, accountNote, isEditing, isSubmitting, intl } = this.props;
|
const { account, intl } = this.props;
|
||||||
|
const { value, saved } = this.state;
|
||||||
|
|
||||||
if (!account || (!accountNote && !isEditing)) {
|
if (!account) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
let action_buttons = null;
|
|
||||||
if (isEditing) {
|
|
||||||
action_buttons = (
|
|
||||||
<div className='account__header__account-note__buttons'>
|
|
||||||
<button className='icon-button' tabIndex={0} onClick={this.props.onCancelAccountNote} disabled={isSubmitting}>
|
|
||||||
<Icon id='times' size={15} /> <FormattedMessage id='account_note.cancel' defaultMessage='Cancel' />
|
|
||||||
</button>
|
|
||||||
<div className='flex-spacer' />
|
|
||||||
<button className='icon-button' tabIndex={0} onClick={this.props.onSaveAccountNote} disabled={isSubmitting}>
|
|
||||||
<Icon id='check' size={15} /> <FormattedMessage id='account_note.save' defaultMessage='Save' />
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
} else {
|
|
||||||
action_buttons = (
|
|
||||||
<div className='account__header__account-note__buttons'>
|
|
||||||
<button className='icon-button' tabIndex={0} onClick={this.props.onEditAccountNote} disabled={isSubmitting}>
|
|
||||||
<Icon id='pencil' size={15} /> <FormattedMessage id='account_note.edit' defaultMessage='Edit' />
|
|
||||||
</button>
|
|
||||||
</div>
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
let note_container = null;
|
|
||||||
if (isEditing) {
|
|
||||||
note_container = (
|
|
||||||
<Textarea
|
|
||||||
className='account__header__account-note__content'
|
|
||||||
disabled={isSubmitting}
|
|
||||||
placeholder={intl.formatMessage(messages.placeholder)}
|
|
||||||
value={accountNote}
|
|
||||||
onChange={this.handleChangeAccountNote}
|
|
||||||
onKeyDown={this.handleKeyDown}
|
|
||||||
autoFocus
|
|
||||||
/>
|
|
||||||
);
|
|
||||||
} else {
|
|
||||||
note_container = (<div className='account__header__account-note__content'>{accountNote}</div>);
|
|
||||||
}
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div className='account__header__account-note'>
|
<div className='account__header__account-note'>
|
||||||
<div className='account__header__account-note__header'>
|
<label htmlFor={`account-note-${account.get('id')}`}>
|
||||||
<strong><FormattedMessage id='account.account_note_header' defaultMessage='Note' /></strong>
|
<FormattedMessage id='account.account_note_header' defaultMessage='Note' /> <InlineAlert show={saved} />
|
||||||
{action_buttons}
|
</label>
|
||||||
</div>
|
|
||||||
{note_container}
|
<Textarea
|
||||||
|
id={`account-note-${account.get('id')}`}
|
||||||
|
className='account__header__account-note__content'
|
||||||
|
disabled={this.props.value === null || value === null}
|
||||||
|
placeholder={intl.formatMessage(messages.placeholder)}
|
||||||
|
value={value || ''}
|
||||||
|
onChange={this.handleChange}
|
||||||
|
onKeyDown={this.handleKeyDown}
|
||||||
|
onBlur={this.handleBlur}
|
||||||
|
ref={this.setTextareaRef}
|
||||||
|
/>
|
||||||
</div>
|
</div>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export default injectIntl(Header);
|
export default injectIntl(AccountNote);
|
||||||
|
|
|
@ -59,7 +59,6 @@ const messages = defineMessages({
|
||||||
add_or_remove_from_list: { id: 'account.add_or_remove_from_list', defaultMessage: 'Add or Remove from lists' },
|
add_or_remove_from_list: { id: 'account.add_or_remove_from_list', defaultMessage: 'Add or Remove from lists' },
|
||||||
admin_account: { id: 'status.admin_account', defaultMessage: 'Open moderation interface for @{name}' },
|
admin_account: { id: 'status.admin_account', defaultMessage: 'Open moderation interface for @{name}' },
|
||||||
admin_domain: { id: 'status.admin_domain', defaultMessage: 'Open moderation interface for {domain}' },
|
admin_domain: { id: 'status.admin_domain', defaultMessage: 'Open moderation interface for {domain}' },
|
||||||
add_account_note: { id: 'account.add_account_note', defaultMessage: 'Add note for @{name}' },
|
|
||||||
languages: { id: 'account.languages', defaultMessage: 'Change subscribed languages' },
|
languages: { id: 'account.languages', defaultMessage: 'Change subscribed languages' },
|
||||||
openOriginalPage: { id: 'account.open_original_page', defaultMessage: 'Open original page' },
|
openOriginalPage: { id: 'account.open_original_page', defaultMessage: 'Open original page' },
|
||||||
});
|
});
|
||||||
|
@ -98,7 +97,6 @@ class Header extends ImmutablePureComponent {
|
||||||
onUnblockDomain: PropTypes.func.isRequired,
|
onUnblockDomain: PropTypes.func.isRequired,
|
||||||
onEndorseToggle: PropTypes.func.isRequired,
|
onEndorseToggle: PropTypes.func.isRequired,
|
||||||
onAddToList: PropTypes.func.isRequired,
|
onAddToList: PropTypes.func.isRequired,
|
||||||
onEditAccountNote: PropTypes.func.isRequired,
|
|
||||||
onChangeLanguages: PropTypes.func.isRequired,
|
onChangeLanguages: PropTypes.func.isRequired,
|
||||||
onInteractionModal: PropTypes.func.isRequired,
|
onInteractionModal: PropTypes.func.isRequired,
|
||||||
onOpenAvatar: PropTypes.func.isRequired,
|
onOpenAvatar: PropTypes.func.isRequired,
|
||||||
|
@ -167,8 +165,6 @@ class Header extends ImmutablePureComponent {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
const accountNote = account.getIn(['relationship', 'note']);
|
|
||||||
|
|
||||||
const suspended = account.get('suspended');
|
const suspended = account.get('suspended');
|
||||||
const isRemote = account.get('acct') !== account.get('username');
|
const isRemote = account.get('acct') !== account.get('username');
|
||||||
const remoteDomain = isRemote ? account.get('acct').split('@')[1] : null;
|
const remoteDomain = isRemote ? account.get('acct').split('@')[1] : null;
|
||||||
|
@ -237,10 +233,6 @@ class Header extends ImmutablePureComponent {
|
||||||
menu.push(null);
|
menu.push(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (accountNote === null || accountNote === '') {
|
|
||||||
menu.push({ text: intl.formatMessage(messages.add_account_note, { name: account.get('username') }), action: this.props.onEditAccountNote });
|
|
||||||
}
|
|
||||||
|
|
||||||
if (account.get('id') === me) {
|
if (account.get('id') === me) {
|
||||||
if (profileLink) menu.push({ text: intl.formatMessage(messages.edit_profile), href: profileLink });
|
if (profileLink) menu.push({ text: intl.formatMessage(messages.edit_profile), href: profileLink });
|
||||||
if (preferencesLink) menu.push({ text: intl.formatMessage(messages.preferences), href: preferencesLink });
|
if (preferencesLink) menu.push({ text: intl.formatMessage(messages.preferences), href: preferencesLink });
|
||||||
|
|
|
@ -1,36 +1,19 @@
|
||||||
import { connect } from 'react-redux';
|
import { connect } from 'react-redux';
|
||||||
|
|
||||||
import { changeAccountNoteComment, submitAccountNote, initEditAccountNote, cancelAccountNote } from 'flavours/glitch/actions/account_notes';
|
import { submitAccountNote } from 'flavours/glitch/actions/account_notes';
|
||||||
|
|
||||||
import AccountNote from '../components/account_note';
|
import AccountNote from '../components/account_note';
|
||||||
|
|
||||||
const mapStateToProps = (state, { account }) => {
|
const mapStateToProps = (state, { account }) => ({
|
||||||
const isEditing = state.getIn(['account_notes', 'edit', 'account_id']) === account.get('id');
|
value: account.getIn(['relationship', 'note']),
|
||||||
|
});
|
||||||
return {
|
|
||||||
isSubmitting: state.getIn(['account_notes', 'edit', 'isSubmitting']),
|
|
||||||
accountNote: isEditing ? state.getIn(['account_notes', 'edit', 'comment']) : account.getIn(['relationship', 'note']),
|
|
||||||
isEditing,
|
|
||||||
};
|
|
||||||
};
|
|
||||||
|
|
||||||
const mapDispatchToProps = (dispatch, { account }) => ({
|
const mapDispatchToProps = (dispatch, { account }) => ({
|
||||||
|
|
||||||
onEditAccountNote() {
|
onSave (value) {
|
||||||
dispatch(initEditAccountNote(account));
|
dispatch(submitAccountNote(account.get('id'), value));
|
||||||
},
|
},
|
||||||
|
|
||||||
onSaveAccountNote() {
|
|
||||||
dispatch(submitAccountNote());
|
|
||||||
},
|
|
||||||
|
|
||||||
onCancelAccountNote() {
|
|
||||||
dispatch(cancelAccountNote());
|
|
||||||
},
|
|
||||||
|
|
||||||
onChangeAccountNote(comment) {
|
|
||||||
dispatch(changeAccountNoteComment(comment));
|
|
||||||
},
|
|
||||||
});
|
});
|
||||||
|
|
||||||
export default connect(mapStateToProps, mapDispatchToProps)(AccountNote);
|
export default connect(mapStateToProps, mapDispatchToProps)(AccountNote);
|
||||||
|
|
|
@ -2,7 +2,6 @@ import { defineMessages, injectIntl, FormattedMessage } from 'react-intl';
|
||||||
|
|
||||||
import { connect } from 'react-redux';
|
import { connect } from 'react-redux';
|
||||||
|
|
||||||
import { initEditAccountNote } from '../../../actions/account_notes';
|
|
||||||
import {
|
import {
|
||||||
followAccount,
|
followAccount,
|
||||||
unfollowAccount,
|
unfollowAccount,
|
||||||
|
@ -139,10 +138,6 @@ const mapDispatchToProps = (dispatch, { intl }) => ({
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
onEditAccountNote (account) {
|
|
||||||
dispatch(initEditAccountNote(account));
|
|
||||||
},
|
|
||||||
|
|
||||||
onBlockDomain (domain) {
|
onBlockDomain (domain) {
|
||||||
dispatch(openModal({
|
dispatch(openModal({
|
||||||
modalType: 'CONFIRM',
|
modalType: 'CONFIRM',
|
||||||
|
|
|
@ -1,6 +1,5 @@
|
||||||
{
|
{
|
||||||
"about.fork_disclaimer": "Glitch-soc is free open source software forked from Mastodon.",
|
"about.fork_disclaimer": "Glitch-soc is free open source software forked from Mastodon.",
|
||||||
"account.add_account_note": "Add note for @{name}",
|
|
||||||
"account.disclaimer_full": "Information below may reflect the user's profile incompletely.",
|
"account.disclaimer_full": "Information below may reflect the user's profile incompletely.",
|
||||||
"account.follows": "Follows",
|
"account.follows": "Follows",
|
||||||
"account.joined": "Joined {date}",
|
"account.joined": "Joined {date}",
|
||||||
|
@ -8,10 +7,6 @@
|
||||||
"account.suspended_disclaimer_full": "This user has been suspended by a moderator.",
|
"account.suspended_disclaimer_full": "This user has been suspended by a moderator.",
|
||||||
"account.unmute_notifications": "Unmute notifications from @{name}",
|
"account.unmute_notifications": "Unmute notifications from @{name}",
|
||||||
"account.view_full_profile": "View full profile",
|
"account.view_full_profile": "View full profile",
|
||||||
"account_note.cancel": "Cancel",
|
|
||||||
"account_note.edit": "Edit",
|
|
||||||
"account_note.glitch_placeholder": "No comment provided",
|
|
||||||
"account_note.save": "Save",
|
|
||||||
"advanced_options.icon_title": "Advanced options",
|
"advanced_options.icon_title": "Advanced options",
|
||||||
"advanced_options.local-only.long": "Do not post to other instances",
|
"advanced_options.local-only.long": "Do not post to other instances",
|
||||||
"advanced_options.local-only.short": "Local-only",
|
"advanced_options.local-only.short": "Local-only",
|
||||||
|
@ -187,14 +182,5 @@
|
||||||
"status.local_only": "Only visible from your instance",
|
"status.local_only": "Only visible from your instance",
|
||||||
"status.sensitive_toggle": "Click to view",
|
"status.sensitive_toggle": "Click to view",
|
||||||
"status.uncollapse": "Uncollapse",
|
"status.uncollapse": "Uncollapse",
|
||||||
"web_app_crash.change_your_settings": "Change your {settings}",
|
"suggestions.dismiss": "Dismiss suggestion"
|
||||||
"web_app_crash.content": "You could try any of the following:",
|
|
||||||
"web_app_crash.debug_info": "Debug information",
|
|
||||||
"web_app_crash.disable_addons": "Disable browser add-ons or built-in translation tools",
|
|
||||||
"web_app_crash.issue_tracker": "issue tracker",
|
|
||||||
"web_app_crash.reload": "Reload",
|
|
||||||
"web_app_crash.reload_page": "{reload} the current page",
|
|
||||||
"web_app_crash.report_issue": "Report a bug in the {issuetracker}",
|
|
||||||
"web_app_crash.settings": "settings",
|
|
||||||
"web_app_crash.title": "We're sorry, but something went wrong with the Mastodon app."
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,44 +0,0 @@
|
||||||
import { Map as ImmutableMap } from 'immutable';
|
|
||||||
|
|
||||||
import {
|
|
||||||
ACCOUNT_NOTE_INIT_EDIT,
|
|
||||||
ACCOUNT_NOTE_CANCEL,
|
|
||||||
ACCOUNT_NOTE_CHANGE_COMMENT,
|
|
||||||
ACCOUNT_NOTE_SUBMIT_REQUEST,
|
|
||||||
ACCOUNT_NOTE_SUBMIT_FAIL,
|
|
||||||
ACCOUNT_NOTE_SUBMIT_SUCCESS,
|
|
||||||
} from '../actions/account_notes';
|
|
||||||
|
|
||||||
const initialState = ImmutableMap({
|
|
||||||
edit: ImmutableMap({
|
|
||||||
isSubmitting: false,
|
|
||||||
account_id: null,
|
|
||||||
comment: null,
|
|
||||||
}),
|
|
||||||
});
|
|
||||||
|
|
||||||
export default function account_notes(state = initialState, action) {
|
|
||||||
switch (action.type) {
|
|
||||||
case ACCOUNT_NOTE_INIT_EDIT:
|
|
||||||
return state.withMutations((state) => {
|
|
||||||
state.setIn(['edit', 'isSubmitting'], false);
|
|
||||||
state.setIn(['edit', 'account_id'], action.account.get('id'));
|
|
||||||
state.setIn(['edit', 'comment'], action.comment);
|
|
||||||
});
|
|
||||||
case ACCOUNT_NOTE_CHANGE_COMMENT:
|
|
||||||
return state.setIn(['edit', 'comment'], action.comment);
|
|
||||||
case ACCOUNT_NOTE_SUBMIT_REQUEST:
|
|
||||||
return state.setIn(['edit', 'isSubmitting'], true);
|
|
||||||
case ACCOUNT_NOTE_SUBMIT_FAIL:
|
|
||||||
return state.setIn(['edit', 'isSubmitting'], false);
|
|
||||||
case ACCOUNT_NOTE_SUBMIT_SUCCESS:
|
|
||||||
case ACCOUNT_NOTE_CANCEL:
|
|
||||||
return state.withMutations((state) => {
|
|
||||||
state.setIn(['edit', 'isSubmitting'], false);
|
|
||||||
state.setIn(['edit', 'account_id'], null);
|
|
||||||
state.setIn(['edit', 'comment'], null);
|
|
||||||
});
|
|
||||||
default:
|
|
||||||
return state;
|
|
||||||
}
|
|
||||||
}
|
|
|
@ -3,7 +3,6 @@ import { Record as ImmutableRecord } from 'immutable';
|
||||||
import { loadingBarReducer } from 'react-redux-loading-bar';
|
import { loadingBarReducer } from 'react-redux-loading-bar';
|
||||||
import { combineReducers } from 'redux-immutable';
|
import { combineReducers } from 'redux-immutable';
|
||||||
|
|
||||||
import account_notes from './account_notes';
|
|
||||||
import accounts from './accounts';
|
import accounts from './accounts';
|
||||||
import accounts_counters from './accounts_counters';
|
import accounts_counters from './accounts_counters';
|
||||||
import accounts_map from './accounts_map';
|
import accounts_map from './accounts_map';
|
||||||
|
@ -87,7 +86,6 @@ const reducers = {
|
||||||
polls,
|
polls,
|
||||||
trends,
|
trends,
|
||||||
markers,
|
markers,
|
||||||
account_notes,
|
|
||||||
picture_in_picture,
|
picture_in_picture,
|
||||||
history,
|
history,
|
||||||
tags,
|
tags,
|
||||||
|
|
|
@ -689,12 +689,13 @@
|
||||||
border-top: 1px solid lighten($ui-base-color, 12%);
|
border-top: 1px solid lighten($ui-base-color, 12%);
|
||||||
border-bottom: 1px solid lighten($ui-base-color, 12%);
|
border-bottom: 1px solid lighten($ui-base-color, 12%);
|
||||||
|
|
||||||
&__header {
|
label {
|
||||||
display: flex;
|
display: block;
|
||||||
flex-direction: row;
|
font-size: 12px;
|
||||||
justify-content: space-between;
|
font-weight: 500;
|
||||||
margin-bottom: 5px;
|
|
||||||
color: $darker-text-color;
|
color: $darker-text-color;
|
||||||
|
text-transform: uppercase;
|
||||||
|
margin-bottom: 5px;
|
||||||
}
|
}
|
||||||
|
|
||||||
&__content {
|
&__content {
|
||||||
|
@ -702,41 +703,6 @@
|
||||||
padding: 10px 0;
|
padding: 10px 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
&__buttons {
|
|
||||||
display: flex;
|
|
||||||
flex-direction: row;
|
|
||||||
justify-content: flex-end;
|
|
||||||
flex: 1 0;
|
|
||||||
|
|
||||||
.icon-button {
|
|
||||||
font-size: 14px;
|
|
||||||
padding: 2px 6px;
|
|
||||||
color: $darker-text-color;
|
|
||||||
|
|
||||||
&:hover,
|
|
||||||
&:active,
|
|
||||||
&:focus {
|
|
||||||
color: lighten($darker-text-color, 7%);
|
|
||||||
background-color: rgba($darker-text-color, 0.15);
|
|
||||||
}
|
|
||||||
|
|
||||||
&:focus {
|
|
||||||
background-color: rgba($darker-text-color, 0.3);
|
|
||||||
}
|
|
||||||
|
|
||||||
&[disabled] {
|
|
||||||
color: darken($darker-text-color, 13%);
|
|
||||||
background-color: transparent;
|
|
||||||
cursor: default;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
.flex-spacer {
|
|
||||||
flex: 0 0 5px;
|
|
||||||
background: transparent;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
strong {
|
strong {
|
||||||
font-size: 12px;
|
font-size: 12px;
|
||||||
font-weight: 500;
|
font-weight: 500;
|
||||||
|
|
|
@ -11,6 +11,15 @@
|
||||||
position: relative;
|
position: relative;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.inline-alert {
|
||||||
|
color: $valid-value-color;
|
||||||
|
font-weight: 400;
|
||||||
|
|
||||||
|
.no-reduce-motion & {
|
||||||
|
transition: opacity 200ms ease;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
.link-button {
|
.link-button {
|
||||||
display: block;
|
display: block;
|
||||||
font-size: 15px;
|
font-size: 15px;
|
||||||
|
|
Loading…
Reference in New Issue