Search code examples
reactjsgrommet

Can't deselect initial values from Select component with options and values as an object


I can't unselect the default values I have set in state.

I'm pulling from an example in Grommet's codesandbox.

Only change thus far is adding an object array instead of an array of strings. See VALUE prop in docs mention object array..

const OPTIONS = [
  {
    label: "Expansion",
    value: "1"
  },
  {
    label: "Rollout",
    value: "2"
  }
];

export default class extends Component {
  state = {
    value: [
      {
        label: "Rollout",
        value: "2"
      }
    ],
    options: OPTIONS
  };

  render() {
    const { options, value } = this.state;
    return (
      <Select
        multiple={true}
        value={value}
        labelKey="label"
        valueKey="value"
        onSearch={searchText => {
          const regexp = new RegExp(searchText, "i");
          this.setState({ options: OPTIONS.filter(o => o.match(regexp)) });
        }}
        onChange={event => {
          console.log({ event });
          this.setState({
            value: event.value,
            options: OPTIONS
          });
        }}
        options={options}
      />
    );
  }
}

In the logs, I'm getting selected: [ -1, 1 ] when I attempt to unselect the Rollout option, and Rollout is still visually highlighted/selected in the view.


Solution

  • Here is your working code, You need to check if currently clicked value is already there in selection then remove it from values and if it is not in selected then add in values. I changed onChange function as below. Let me know if any issues.

    import React, { Component } from "react";
    import { Select } from "grommet";
    import SandboxComponent from "./SandboxComponent";
    
    const OPTIONS = [
      {
        label: "Expansion",
        value: "1"
      },
      {
        label: "Rollout",
        value: "2"
      }
    ];
    
    export default class extends Component {
      state = {
        value: [
          {
            label: "Rollout",
            value: "2"
          }
        ],
        options: OPTIONS
      };
    
      render() {
        const { options, value } = this.state;
        return (
          <Select
            multiple={true}
            value={value}
            labelKey="label"
            valueKey="value"
            selected={0}
            onSearch={searchText => {
              const regexp = new RegExp(searchText, "i");
              this.setState({ options: OPTIONS.filter(o => o.match(regexp)) });
            }}
            onChange={event => {
              let isExist = value.find(item => {
                return item.value === event.option.value;
              });
              let newValue;
              if (isExist) {
                newValue = value.filter(item => {
                  return item.value !== event.option.value;
                });
              } else {
                newValue = value;
                newValue.push(event.option);
              }
    
              this.setState({
                value: newValue
              });
            }}
            options={options}
          />
        );
      }
    }