npm.io
2.76.0 • Published 6 months ago

@s-ui/react-molecule-autosuggest

Licence
MIT
Version
2.76.0
Deps
7
Size
33 kB
Vulns
0
Weekly
0
Stars
147

MoleculeAutosuggest

MoleculeAutosuggest is an input that will display a list of suggestions while values are entered It allows Single and Multiple Selection

documentation issue npm

Issues open NPM

Installation

$ npm install @s-ui/react-molecule-autosuggest --save

Usage

import MoleculeAutosuggest, { MoleculeAutosuggestDropdownListSizes } from '@s-ui/react-molecule-autosuggest'
import MoleculeAutosuggestOption from '@s-ui/react-molecule-dropdown-option'

const IconCloseTag = () => <span>x</span>  
const IconClear = () => <span>x</span>  

const suggestions = ['John','Johnny']
Single Selection
Basic usage
 <MoleculeAutosuggest
  value={'Jo'}
  placeholder="Select an option..."
  iconClear={<IconClose />}
  state="success"
>

  {suggestions.map((suggestion, i) => (
    <MoleculeAutosuggestOption key={i} value={suggestion}>
      {option}
    </MoleculeAutosuggestOption>
  ))}

</MoleculeAutosuggest>
Large List
<MoleculeAutosuggest
  value={'Jo'}
  placeholder="Select an option..."
  iconClear={<IconClose />}
  size={MoleculeAutosuggestDropdownListSizes.LARGE}
>
  {suggestions.map((suggestion, i) => (
    <MoleculeAutosuggestOption key={i} value={suggestion}>
      {option}
    </MoleculeAutosuggestOption>
  ))}
</MoleculeAutosuggest>
Multiple Selection
Basic usage
<MoleculeAutosuggest
  value={'Jo'}
  placeholder="Select some options..."
  iconCloseTag={<IconCloseTag />}
  iconClear={<IconClear />}
  multiselection
>
  {suggestions.map((suggestion, i) => (
    <MoleculeAutosuggestOption key={i} value={suggestion}>
      {option}
    </MoleculeAutosuggestOption>
  ))}
</MoleculeAutosuggest>
With Right Icon

You can add a right icon to the multiselection input:

<MoleculeAutosuggest
  value={'Jo'}
  placeholder="Select some options..."
  iconCloseTag={<IconCloseTag />}
  iconClear={<IconClear />}
  rightIcon={<IconInfo />}
  multiselection
>
  {suggestions.map((suggestion, i) => (
    <MoleculeAutosuggestOption key={i} value={suggestion}>
      {option}
    </MoleculeAutosuggestOption>
  ))}
</MoleculeAutosuggest>
With Right Icon and Click Handler

The right icon can be interactive with an onClickRightIcon callback:

<MoleculeAutosuggest
  value={'Jo'}
  placeholder="Select some options..."
  iconCloseTag={<IconCloseTag />}
  iconClear={<IconClear />}
  rightIcon={<IconSearch />}
  onClickRightIcon={(ev, {value}) => {
    console.log('Right icon clicked with value:', value)
  }}
  multiselection
>
  {suggestions.map((suggestion, i) => (
    <MoleculeAutosuggestOption key={i} value={suggestion}>
      {option}
    </MoleculeAutosuggestOption>
  ))}
</MoleculeAutosuggest>
Managing State
Custom component from MoleculeAutosuggest that handle State

MoleculeAutosuggest is a stateless component so to manage dynamic options we need to create a wrapper component that manages this and pass proper props and proper children (MoleculeAutosuggestOption) to MoleculeAutosuggest

Example:

import React, {Component} from 'react'

import MoleculeAutosuggest from '@s-ui/react-molecule-autosuggest'
import MoleculeAutosuggestOption from '@s-ui/react-molecule-dropdown-option'

import {getAsyncCountriesFromQuery} from '../services'

export default class AutosuggestSingleWithAsyncOptions extends Component {
  state = {value: '', options: []}

  onChange = async (e, {value}) => {
    const options = await getAsyncCountriesFromQuery({query: value})
    this.setState({value, options})
  }

  render() {
    const {options, value} = this.state
    const {onChange, props} = this

    return (
      <MoleculeAutosuggest {...props} value={value} onChange={onChange}>
        {options.map((option, i) => (
          <MoleculeAutosuggestOption key={i} value={option}>
            {option}
          </MoleculeAutosuggestOption>
        ))}
      </MoleculeAutosuggest>
    )
  }
}

so then, the AutosuggestSingleWithAsyncOptions can used in this way...

  <AutosuggestSingleWithAsyncOptions iconClear={<IconClear />} />
Using an hoc like withDynamicOptions

It can be useful creating a hoc (like the one withDynamicOptions available in the demo) that combined with other hoc from @s-ui/hoc can be used to simplify the use of this component with dinamyc suggestions based on the value

withDynamicOptions

import React, {Component} from 'react'

export default (BaseComponent, BaseChildComponent) => getDynamicOptions => {
  const displayName = BaseComponent.displayName

  return class withDynamicOptions extends Component {
    static displayName = `withDynamicOptions(${displayName})`

    state = { options: []}

    async componentDidUpdate({value: prevQuery}) {
      const {value: query} = this.props
      if (query !== prevQuery) {
        const options = await getDynamicOptions({query})
        this.setState({options}) // eslint-disable-line
      }
    }

    render() {
      const {props} = this
      const {options} = this.state
      return (
        <BaseComponent {...props}>
          {options.map((option, i) => (
            <BaseChildComponent key={i} value={option}>
              {option}
            </BaseChildComponent>
          ))}
        </BaseComponent>
      )
    }
  }
}

use of withDynamicOptions for creating a stateful version of MoleculeAutosuggest


import MoleculeAutosuggest from '@s-ui/react-molecule-autosuggest'
import MoleculeAutosuggestOption from '@s-ui/react-molecule-dropdown-option'

import withDynamicOptions from './hoc/withDynamicOptions'
import {withStateValue} from '@s-ui/hoc'

// some function that gets a `{query}` and returns asynchronoudly a list of values
import {getAsyncCountriesFromQuery} from './services'

const MoleculeAutosuggestWithDynamicOptions = withDynamicOptions(
  MoleculeAutosuggest,
  MoleculeAutosuggestOption
)(getAsyncCountriesFromQuery)


const MoleculeAutosuggestWithState = withStateValue(
  MoleculeAutosuggestWithDynamicOptions
)

so then, the MoleculeAutosuggestWithState can used in this way...

<MoleculeAutosuggestWithState
  placeholder="Type a Country name..."
  onChange={(_, {value}) => console.log(value)}
  iconClear={<IconClear />}
/>

Find full description and more examples in the demo page.

Keywords