Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Input field not updating when option is selected #828

Closed
coxjonc opened this issue Mar 11, 2016 · 23 comments
Closed

Input field not updating when option is selected #828

coxjonc opened this issue Mar 11, 2016 · 23 comments

Comments

@coxjonc
Copy link

coxjonc commented Mar 11, 2016

Forgive me if this is a stupid question, but I'm having trouble with v1.0.0 of react-select not updating the input field with the selected value after an option is clicked. When I use versions <1.0.0 it automatically updated the input field when I clicked an option. But with v1.0.0 the input field remains empty. Do I need to manually set the value? If so, how? Any help would be greatly appreciated :).

And thanks for putting all the painstaking work into making this awesome tool 👍

@ammarhaider7
Copy link

I'm finding a similar issue but only when I've declared an onChange function..

@jljorgenson18
Copy link

Are you passing the value back into the component? In v1, react-select is now "controlled" so the actual value has to be passed back in as a prop. https://github.com/JedWatson/react-select/blob/master/CHANGES.md

Also, if you are doing async then you often need to pass in a whole object as { label: string, value: string })

@coxjonc
Copy link
Author

coxjonc commented Mar 12, 2016

That explains it. Thought it must be something like this! Since it sounds like I'm not the only one who has been bitten by this, it might help if this was shown in the examples in the docs. Thanks @jljorgenson18

@sehmaschine
Copy link

still trying to figure this out ... could you give an example on "the actual value has to be passed back in as a prop"? it seems that setState doesn't work anymore, but how do you pass back the value/option?

@jljorgenson18
Copy link

That depends on how you are storing your value. If you were storing your value in state, you would add <Select value={this.state.yourValue} options={yourOptions} onChange={this.handleSelectChange} />

@sehmaschine
Copy link

Thanks. But this only seems to work if the selected value is part of the initial options array (with using async, this is not necessarily the case).

@jljorgenson18
Copy link

In v1.0.0, you can pass the value back in as a "full option." In this case, you are not simply passing in the value, but rather the value combined with the label. For my async select components, I use a getValue method. Here is a snippet as to how I have it setup with a few properties removed for brevity

...
    getValue: function() {
        // To work around react-select's weird input api
        const {val} = this.props.targetObj;
        if(val) {
            return ({
                label: val,
                value: val
            });
        }
    },

    render: function() {
        const {targetName, targetObj} = this.props;
        return (
            <div>
              <label htmlFor={ targetName }>
                { targetObj.label }
              </label>
              <Async onChange={ this.onSelectChange }
                name={ targetName }
                value={ this.getValue() }
                loadOptions={ getOptions }
                searchable={ true }
                clearable={ true } />
              <div className="formErrorFeedback">
                { targetObj.errorMessage }
              </div>
            </div>
            );

...

@cema-sp
Copy link

cema-sp commented Mar 16, 2016

As @jljorgenson18 and others said, loadOptions should return option objects array:

[
    { label: "Option 1", value: 1 },
    { label: "Option 2", value: 2 },
]

And to properly display selected item, set value prop of Select.Async to option object:

{ label: "Option 1", value: 1 }

@FranBran
Copy link

@sehmaschine I'm facing this problem too. The value passed as a prop has to be an instance of an option passed via the loadOptions-func. Therefore it's unfortunatly not possible to pass value={{a:1}} as a property to Select.

It would be useful if the passed value would be compared to the passed options by _.isEqual() instead of indexOf().

see https://github.com/JedWatson/react-select/blob/master/src/Select.js#L679 for reference

@genyded
Copy link

genyded commented Apr 10, 2016

Also is there a reason the event is not passed in the onChange? Seems like setting the value with e.target,value would be another possibility that is currently disallowed.

@dspoonia7
Copy link

Thanks @jljorgenson18 what you suggested is fixed this issue. but it is causing a new issue, now the dropdown list is hiding every time I select a option. I have to type/search again to see dropdown list (In multi select).

@cchanningallen
Copy link

Thank you so much @jljorgenson18! This fixed a similar issue I was having with Select.Creatable.

Here's my code, for anyone who encounters this:

import React, { PropTypes, Component } from 'react';
import ReactSelect from 'react-select';

class CreatableSelectInput extends Component {
  static propTypes = {
    options: PropTypes.arrayOf(PropTypes.shape({
      label: PropTypes.string.isRequired,
      value: PropTypes.string.isRequired,
    })),
    onChange: PropTypes.func,
    value: PropTypes.string,
  };

  getValue = (value, options) => {
    if (!value) { return value }

    // If value is represented in the current options, just return that option.
    const currentOption = options.find(option => option.value === value);
    if (currentOption) { return currentOption }

    // If value is truthy but not contained in the options, it must be new.
    // Pass as an option object to satisfy react-select's Creatable value api.
    // Ref: https://github.com/JedWatson/react-select/issues/828
    return { value, label: value };
  };

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

    return(
      <ReactSelect.Creatable
        options={options}
        onChange={onChange}
        value={this.getValue(value, options)}
      />
    );
  }
}

@v-Zer0
Copy link

v-Zer0 commented Apr 17, 2017

@JedWatson this is also an issue when using a Creatable with no options specified.

@ericnewcomer
Copy link

ericnewcomer commented May 24, 2017

To expand on what @dspoonia7 said (I'm also seeing this behavior), even selecting the dropdown arrow does not reveal any options. If you type a character and delete it, then they'll get populated.

Updated:
The problem I'm seeing (and probably the same for @dspoonia7) is related to using the multi select case combined with Async. I'll open a separate issue.

@typeofgraphic
Copy link

typeofgraphic commented Jul 24, 2017

@geezhawk : I was also caught out by this. A couple of reasons why the input value might not have been updating:

The Changes doc states:

Using values that aren't in the options array is still supported, but they have to be full options (previous versions would expand strings into { label: string, value: string })

So, if you are using setState to set a value that is not in the props passed to the Select component, then the value needs to look like:

this.state = {
  selectedEvent: { label: <string>, value: <string> }
}

You cannot only do this.setState({ selectedEvent: value }) in this case.

If you are passing a value that is in the props array being passed to the Select component, then you can pass just the value in a handler function:

handleChange = (event) => {     
        if(val !== null){
            this.setState({ selectedEvent : event.value })
        } else {
            this.setState({ selectedEvent: null })
        }
    }

Other threads have indicated that passing "" will reset the Select form. However, I have found that unless null is passed the cross still appears as if there is something to clear. The console logs on http://jedwatson.github.io/react-select/ show this to be the case for the demos also.

@itsdouges
Copy link

This really needs to be updated in the docs.

@si-acus
Copy link

si-acus commented Nov 22, 2017

@geezhawk i have same trouble :'(

@jacobwicks
Copy link

jacobwicks commented Nov 22, 2017

I agree! I'm glad I found this topic.

I also found some working code by user Nazarlitvin here:
#1188

Although where it says "return(I" I changed "I" to "Select", which is what I called my react-select variable. Good luck to everyone else running into this issue.

@si-acus
Copy link

si-acus commented Nov 23, 2017

@jacobwicks thanks for the helpful responses!
it was worked for me

@JedWatson
Copy link
Owner

Thanks for helping out everyone, I'm cleaning up the docs now so hopefully this is all resolved.

@breville
Copy link

@JedWatson It would be very handy if https://github.com/JedWatson/react-select/tree/v1.x#usage mentioned this workaround for value. Something as succinct as the explanation at #865 (comment) would probably save quite a bit of time for the folks who are still living with the older version of this control. :)

@jmoe
Copy link

jmoe commented Nov 28, 2018

It seems like the component still does not select the value if passing a string that matches on the value property in the options property. Where in the documentation is this explained better?

@jmoe
Copy link

jmoe commented Nov 28, 2018

The case I'm running into is that the value is actually getting selected when I pass a string, but the label is just not displaying in the input field. If I click the dropdown I can see that the appropriate options is highlighted, just can't get it to display in the input field. Is this the same problem or new problem?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests