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.

126 lines
3.1 KiB

  1. import PureRenderMixin from 'react-addons-pure-render-mixin';
  2. import ImmutablePropTypes from 'react-immutable-proptypes';
  3. import Autosuggest from 'react-autosuggest';
  4. import AutosuggestAccountContainer from '../containers/autosuggest_account_container';
  5. const getSuggestionValue = suggestion => suggestion.value;
  6. const renderSuggestion = suggestion => {
  7. if (suggestion.type === 'account') {
  8. return <AutosuggestAccountContainer id={suggestion.id} />;
  9. } else {
  10. return <span>#{suggestion.id}</span>
  11. }
  12. };
  13. const renderSectionTitle = section => (
  14. <strong>{section.title}</strong>
  15. );
  16. const getSectionSuggestions = section => section.items;
  17. const outerStyle = {
  18. padding: '10px',
  19. lineHeight: '20px',
  20. position: 'relative'
  21. };
  22. const inputStyle = {
  23. boxSizing: 'border-box',
  24. display: 'block',
  25. width: '100%',
  26. border: 'none',
  27. padding: '10px',
  28. paddingRight: '30px',
  29. fontFamily: 'Roboto',
  30. background: '#282c37',
  31. color: '#9baec8',
  32. fontSize: '14px',
  33. margin: '0'
  34. };
  35. const iconStyle = {
  36. position: 'absolute',
  37. top: '18px',
  38. right: '20px',
  39. color: '#9baec8',
  40. fontSize: '18px',
  41. pointerEvents: 'none'
  42. };
  43. const Search = React.createClass({
  44. contextTypes: {
  45. router: React.PropTypes.object
  46. },
  47. propTypes: {
  48. suggestions: React.PropTypes.array.isRequired,
  49. value: React.PropTypes.string.isRequired,
  50. onChange: React.PropTypes.func.isRequired,
  51. onClear: React.PropTypes.func.isRequired,
  52. onFetch: React.PropTypes.func.isRequired,
  53. onReset: React.PropTypes.func.isRequired
  54. },
  55. mixins: [PureRenderMixin],
  56. onChange (_, { newValue }) {
  57. if (typeof newValue !== 'string') {
  58. return;
  59. }
  60. this.props.onChange(newValue);
  61. },
  62. onSuggestionsClearRequested () {
  63. this.props.onClear();
  64. },
  65. onSuggestionsFetchRequested ({ value }) {
  66. value = value.replace('#', '');
  67. this.props.onFetch(value.trim());
  68. },
  69. onSuggestionSelected (_, { suggestion }) {
  70. if (suggestion.type === 'account') {
  71. this.context.router.push(`/accounts/${suggestion.id}`);
  72. } else {
  73. this.context.router.push(`/statuses/tag/${suggestion.id}`);
  74. }
  75. },
  76. render () {
  77. const inputProps = {
  78. placeholder: 'Search',
  79. value: this.props.value,
  80. onChange: this.onChange,
  81. style: inputStyle
  82. };
  83. return (
  84. <div style={outerStyle}>
  85. <Autosuggest
  86. multiSection={true}
  87. suggestions={this.props.suggestions}
  88. focusFirstSuggestion={true}
  89. focusInputOnSuggestionClick={false}
  90. alwaysRenderSuggestions={false}
  91. onSuggestionsFetchRequested={this.onSuggestionsFetchRequested}
  92. onSuggestionsClearRequested={this.onSuggestionsClearRequested}
  93. onSuggestionSelected={this.onSuggestionSelected}
  94. getSuggestionValue={getSuggestionValue}
  95. renderSuggestion={renderSuggestion}
  96. renderSectionTitle={renderSectionTitle}
  97. getSectionSuggestions={getSectionSuggestions}
  98. inputProps={inputProps}
  99. />
  100. <div style={iconStyle}><i className='fa fa-search' /></div>
  101. </div>
  102. );
  103. },
  104. });
  105. export default Search;