Ib33X
Ib33X

Reputation: 7254

HTML select form with option to enter custom value

I would like to have an input field that users can enter custom text value or choose from drop down. A regular <select> only offers drop down options.

How can I make a <select> accept custom value? For instance: Ford?

<select>
  <option value="volvo">Volvo</option>
  <option value="saab">Saab</option>
  <option value="mercedes">Mercedes</option>
  <option value="audi">Audi</option>
</select>

Upvotes: 167

Views: 348448

Answers (7)

mickmackusa
mickmackusa

Reputation: 48069

Alen Saqe's latest JSFiddle didn't toggle for me on Firefox, so I thought I would provide a simple html/javascript workaround that will function nicely within forms (regarding submission) until the day that the datalist tag is accepted by all browsers/devices. For more details and see it in action, go to: http://jsfiddle.net/6nq7w/4/ Note: Do not allow any spaces between toggling siblings (in other words </select> must be immediately followed by <input -- no gap)!

<!DOCTYPE html>
<html>
<script>
function toggleField(hideObj,showObj){
  hideObj.disabled=true;        
  hideObj.style.display='none';
  showObj.disabled=false;   
  showObj.style.display='inline';
  showObj.focus();
}
</script>
<body>
<form name="BrowserSurvey" action="#">
Browser: <select name="browser" 
          onchange="if(this.options[this.selectedIndex].value=='customOption'){
              toggleField(this,this.nextSibling);
              this.selectedIndex='0';
          }">
            <option></option>
            <option value="customOption">[type a custom value]</option>
            <option>Chrome</option>
            <option>Firefox</option>
            <option>Internet Explorer</option>
            <option>Opera</option>
            <option>Safari</option>
        </select><input name="browser" style="display:none;" disabled="disabled" 
            onblur="if(this.value==''){toggleField(this,this.previousSibling);}">
<input type="submit" value="Submit">
</form>
</body>
</html>

One advantage of this technique is that the user will not need to start typing into an input field to see what the list options are -- they are shown by default and hidden if desired by the user.

Upvotes: 30

adnanmuttaleb
adnanmuttaleb

Reputation: 3624

This is the same solution as @mickmackusa but written using jquery:

<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<form name="BrowserSurvey" action="#">
  Browser: <select name="browser" onchange="if($(this).val()=='customOption'){$(this).hide().prop('disabled',true);$('input[name=browser]').show().prop('disabled', false).focus();$(this).val(null);}">
    <option></option>
    <option value="customOption">[type a custom value]</option>
    <option>Chrome</option>
    <option>Firefox</option>
    <option>Internet Explorer</option>
    <option>Opera</option>
    <option>Safari</option></select><input name="browser" style="display:none;" disabled="disabled" onblur="if($(this).val()==''){$(this).hide().prop('disabled',true);$('select[name=browser]').show().prop('disabled', false).focus();}">
  <input type="submit" value="Submit">
</form>

Maybe a more readable version:

function toggle($toBeHidden, $toBeShown) {
  $toBeHidden.hide().prop('disabled', true);
  $toBeShown.show().prop('disabled', false).focus();
}

function showOptions(inputName) {
  var $select = $(`select[name=${inputName}]`);
  toggle($(`input[name=${inputName}]`), $select);
  $select.val(null);
}


function showCustomInput(inputName) {
  toggle($(`select[name=${inputName}]`), $(`input[name=${inputName}]`));
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<form name="BrowserSurvey" action="#">
Browser: <select name="browser" onchange="if($(this).val()=='customOption')showCustomInput('browser')">
    <option></option>
    <option value="customOption">[type a custom value]</option>
    <option>Chrome</option>
    <option>Firefox</option>
    <option>Internet Explorer</option>
    <option>Opera</option>
    <option>Safari</option></select><input name="browser" style="display:none;" disabled="disabled" onblur="if($(this).val()=='')showOptions('browser')">
<input type="submit" value="Submit">
</form>

Upvotes: 2

Dmitry
Dmitry

Reputation: 7276

HTML5 has a built-in combo box. You create a text input and a datalist. Then you add a list attribute to the input, with a value of the id of the datalist.

Update: As of March 2019 all major browsers (now including Safari 12.1 and iOS Safari 12.3) support datalist to the level needed for this functionality. See caniuse for detailed browser support.

It looks like this:

<input type="text" list="cars" />
<datalist id="cars">
  <option>Volvo</option>
  <option>Saab</option>
  <option>Mercedes</option>
  <option>Audi</option>
</datalist>

Upvotes: 376

dano
dano

Reputation: 5630

Using one of the above solutions ( @mickmackusa ), I made a working prototype in React 16.8+ using Hooks.

https://codesandbox.io/s/heuristic-dewdney-0h2y2

I hope it helps someone.

Upvotes: 2

Sogeking
Sogeking

Reputation: 830

If the datalist option doesn't fulfill your requirements, take a look to the Select2 library and the "Dynamic option creation"

$(".js-example-tags").select2({
  tags: true
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<link href="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.6-rc.0/css/select2.min.css" rel="stylesheet"/>
<script src="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.6-rc.0/js/select2.min.js"></script>


<select class="form-control js-example-tags">
  <option selected="selected">orange</option>
  <option>white</option>
  <option>purple</option>
</select>

Upvotes: 16

Alen Saqe
Alen Saqe

Reputation: 479

jQuery Solution!

Demo: http://jsfiddle.net/69wP6/2/

Another Demo Below(updated!)

I needed something similar in a case when i had some fixed Options and i wanted one other option to be editable! In this case i made a hidden input that would overlap the select option and would be editable and used jQuery to make it all work seamlessly.

I am sharing the fiddle with all of you!

HTML

<div id="billdesc">
    <select id="test">
      <option class="non" value="option1">Option1</option>
      <option class="non" value="option2">Option2</option>
      <option class="editable" value="other">Other</option>
    </select>
    <input class="editOption" style="display:none;"></input>
</div>

CSS

body{
    background: blue;
}
#billdesc{
    padding-top: 50px;
}
#test{
    width: 100%;
    height: 30px;
}
option {
    height: 30px;
    line-height: 30px;
}

.editOption{
    width: 90%;
    height: 24px;
    position: relative;
    top: -30px

}

jQuery

var initialText = $('.editable').val();
$('.editOption').val(initialText);

$('#test').change(function(){
var selected = $('option:selected', this).attr('class');
var optionText = $('.editable').text();

if(selected == "editable"){
  $('.editOption').show();


  $('.editOption').keyup(function(){
      var editText = $('.editOption').val();
      $('.editable').val(editText);
      $('.editable').html(editText);
  });

}else{
  $('.editOption').hide();
}
});

Edit : Added some simple touches design wise, so people can clearly see where the input ends!

JS Fiddle : http://jsfiddle.net/69wP6/4/

Upvotes: 16

Sam
Sam

Reputation: 1243

You can't really. You'll have to have both the drop down, and the text box, and have them pick or fill in the form. Without javascript you could create a separate radio button set where they choose dropdown or text input, but this seems messy to me. With some javascript you could toggle disable one or the other depending on which one they choose, for instance, have an 'other' option in the dropdown that triggers the text field.

Upvotes: 10

Related Questions