React-Select losing focus for custom component “ValueContainer”

我是研究僧i 提交于 2021-02-04 21:15:34

问题


We have a use case where we have to render multiple different versions of the value container for the multiselect dropdown depending on how many options are selected. The code snippet below shows one of the cases. Another version of this renders a <SingleValue /> instead of placeholder.

<ValueContainer {...props}>
    <Placeholder {...props}>
    {!props.selectProps.inputValue && `${length} selected`}
    </Placeholder>
    {children[1]}
</ValueContainer>

This seems to be working well, however we lose keyboard navigation upon selection of one of the options. Am I forgetting to pass certain props or a ref?

An example of dropped keyboard navigation for custom ValueContainers can be found here: https://codesandbox.io/s/rjvkzk1nn?from-embed


回答1:


Keyboard is not working anymore because you miss the Input component that is focused when you open the Menu.

ValueContainer has two objects when there's no value selected:

  • Placeholder
  • Input

when you select one (or multiple) value(s) then it changes for:

  • SingleValue or MultiValue
  • Input

with your previous example, you were removing those two.

To keep the keyboard features, you need to keep the Input component. The following code is a combination of your code and expectation and keeping the Input component:

const ValueContainer = ({ children, ...props }) => {
  const { getValue, hasValue } = props;
  const newChildren = _.cloneDeep(children);
  const nbValues = getValue().length;
  newChildren[0] = `${nbValues} items selected`;

  if (!hasValue) {
    return (
      <components.ValueContainer {...props}>
        {children}
      </components.ValueContainer>
    );
  }
  return (
    <components.ValueContainer {...props}>
      {newChildren}
    </components.ValueContainer>
  );
};

const options = [
  { label: "label 1", value: 1 },
  { label: "label 2", value: 2 },
  { label: "label 3", value: 3 },
  { label: "label 4", value: 4 }
];

function App() {
  const components = { ValueContainer };
  return <Select isMulti components={components} options={options} />;
}

Live example.




回答2:


It turns out that you should put the custom value container outside the render

const CustomValueContainer: React.FC = props => (
  <components.ValueContainer {...props} />
);

const App = () => {
  const [selectValue, setSelectValue] = useState();
  return (
    <div className="App">
      <Select
        options={options}
        value={selectValue}
        closeMenuOnSelect={false}
        onChange={value => setSelectValue(value)}
        components={{
          ValueContainer: CustomValueContainer,
        }}
      />
    </div>
  );
};

https://github.com/JedWatson/react-select/issues/2810#issuecomment-569117980




回答3:


My solution is simple, React is not complaining about missing key prop and web browser won't hang.

imports

import Select, { components } from 'react-select'

ValueContainer function

  const ValueContainer = ({ children, ...props }) => {
    const length = children[0].length
    let tmpChildren = [...children];
    if(length >= 2){
      tmpChildren[0] = `${length} languages`
    }
    return (
      <components.ValueContainer {...props}>{tmpChildren}</components.ValueContainer>
    );
  };

<Select/> component

<Select
      isMulti
      components={{ ValueContainer }}
      classNamePrefix="simplelocalize-select"
      placeholder="Showing all languages"
      closeMenuOnSelect={false}
/>


来源:https://stackoverflow.com/questions/58804769/react-select-losing-focus-for-custom-component-valuecontainer

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!