diff --git a/app/soapbox/components/account_search.js b/app/soapbox/components/account_search.js
new file mode 100644
index 000000000..77eae54ba
--- /dev/null
+++ b/app/soapbox/components/account_search.js
@@ -0,0 +1,83 @@
+import React from 'react';
+import PropTypes from 'prop-types';
+import { defineMessages, injectIntl } from 'react-intl';
+import Icon from 'soapbox/components/icon';
+import AutosuggestAccountInput from 'soapbox/components/autosuggest_account_input';
+import classNames from 'classnames';
+
+const messages = defineMessages({
+ placeholder: { id: 'account_search.placeholder', defaultMessage: 'Search for an account' },
+});
+
+export default @injectIntl
+class AccountSearch extends React.PureComponent {
+
+ static propTypes = {
+ intl: PropTypes.object.isRequired,
+ onSelected: PropTypes.func.isRequired,
+ };
+
+ state = {
+ value: '',
+ }
+
+ isEmpty = () => {
+ const { value } = this.state;
+ return !(value.length > 0);
+ }
+
+ clearState = () => {
+ this.setState({ value: '' });
+ }
+
+ handleChange = ({ target }) => {
+ this.setState({ value: target.value });
+ }
+
+ handleSelected = accountId => {
+ this.clearState();
+ this.props.onSelected(accountId);
+ }
+
+ handleClear = e => {
+ e.preventDefault();
+
+ if (!this.isEmpty()) {
+ this.setState({ value: '' });
+ }
+ }
+
+ handleKeyDown = e => {
+ if (e.key === 'Escape') {
+ document.querySelector('.ui').parentElement.focus();
+ }
+ }
+
+ render() {
+ const { intl, onSelected, ...rest } = this.props;
+ const { value } = this.state;
+ const isEmpty = this.isEmpty();
+
+ return (
+
+
+
+
+
+
+
+ );
+ }
+
+}
diff --git a/app/soapbox/components/autosuggest_account_input.js b/app/soapbox/components/autosuggest_account_input.js
index 518a8548d..b359323ab 100644
--- a/app/soapbox/components/autosuggest_account_input.js
+++ b/app/soapbox/components/autosuggest_account_input.js
@@ -4,34 +4,29 @@ import PropTypes from 'prop-types';
import { CancelToken } from 'axios';
import ImmutablePureComponent from 'react-immutable-pure-component';
import { connect } from 'react-redux';
-import { injectIntl, defineMessages } from 'react-intl';
import { OrderedSet as ImmutableOrderedSet } from 'immutable';
import { accountSearch } from 'soapbox/actions/accounts';
import { throttle } from 'lodash';
const noOp = () => {};
-const messages = defineMessages({
- placeholder: { id: 'autosuggest_account_input.default_placeholder', defaultMessage: 'Search for an account' },
-});
-
export default @connect()
-@injectIntl
class AutosuggestAccountInput extends ImmutablePureComponent {
static propTypes = {
- intl: PropTypes.object.isRequired,
dispatch: PropTypes.func.isRequired,
+ onChange: PropTypes.func.isRequired,
onSelected: PropTypes.func.isRequired,
- limit: PropTypes.number,
+ value: PropTypes.string.isRequired,
+ limit: PropTypes.number.isRequired,
}
static defaultProps = {
+ value: '',
limit: 4,
}
state = {
- text: '',
accountIds: ImmutableOrderedSet(),
}
@@ -43,6 +38,10 @@ class AutosuggestAccountInput extends ImmutablePureComponent {
return this.source;
}
+ clearResults = () => {
+ this.setState({ accountIds: ImmutableOrderedSet() });
+ }
+
handleAccountSearch = throttle(q => {
const { dispatch, limit } = this.props;
const source = this.refreshCancelToken();
@@ -58,23 +57,28 @@ class AutosuggestAccountInput extends ImmutablePureComponent {
}, 900, { leading: true, trailing: true })
- handleChange = ({ target }) => {
- this.handleAccountSearch(target.value);
- this.setState({ text: target.value });
+ handleChange = e => {
+ this.handleAccountSearch(e.target.value);
+ this.props.onChange(e);
}
handleSelected = (tokenStart, lastToken, accountId) => {
this.props.onSelected(accountId);
}
+ componentDidUpdate(prevProps) {
+ if (this.props.value === '' && prevProps.value !== '') {
+ this.clearResults();
+ }
+ }
+
render() {
- const { intl, ...rest } = this.props;
- const { text, accountIds } = this.state;
+ const { intl, value, onChange, ...rest } = this.props;
+ const { accountIds } = this.state;
return (
({
@@ -62,7 +63,10 @@ class DirectTimeline extends React.PureComponent {
onPin={this.handlePin}
/>
-
+