显示datalist标签,但提交实际值
目前,大多数主stream浏览器(Safari除外)都支持HTML5 <datalist>
元素,这似乎是向input添加build议的有趣方式。
但是, value
属性的实现和<option>
的内部文本之间似乎有一些差异。 例如:
<input list="answers" name="answer"> <datalist id="answers"> <option value="42">The answer</option> </datalist>
这由不同的浏览器处理不同:
Chrome和Opera:
FireFox和IE 11:
select一个之后,input将填充值而不是内部文本。 我只希望用户在下拉菜单和input框中看到文本(“答案”),但是在提交时传递值42
,就像select
一样。
我怎样才能使所有的浏览器有下拉列表显示<option>
的标签(内部文本),但发送表单提交时的value
属性?
请注意, datalist
与select
。 它允许用户input一个不在列表中的自定义值,如果不先定义这个input,就不可能获取这个input的替代值。
处理用户input的可能方法是按原样提交input的值,提交一个空白值或防止提交。 这个答案只处理前两个选项。
如果你想完全禁止用户input,也许select
将是一个更好的select。
要在下拉列表中只显示option
的文本值,我们使用它的内部文本并省略value
属性。 我们想要发送的实际值存储在一个自定义data-value
属性中:
要提交这个data-value
我们必须使用<input type="hidden">
。 在这种情况下,我们在常规input上省略name="answer"
,并将其移至隐藏的副本。
<input list="suggestionList" id="answerInput"> <datalist id="suggestionList"> <option data-value="42" >The answer</option> </datalist> <input type="hidden" name="answer" id="answerInput-hidden">
这样,当原始input中的文本发生变化时,我们可以使用javascript来检查文本是否存在于datalist
并获取其data-value
。 该值被插入到隐藏的input并提交。
document.querySelector('input[list]').addEventListener('input', function(e) { var input = e.target, list = input.getAttribute('list'), options = document.querySelectorAll('#' + list + ' option'), hiddenInput = document.getElementById(input.id + '-hidden'), inputValue = input.value; hiddenInput.value = inputValue; for(var i = 0; i < options.length; i++) { var option = options[i]; if(option.innerText === inputValue) { hiddenInput.value = option.getAttribute('data-value'); break; } } });
标准answer
和answer-hidden
在常规和隐藏的input是脚本需要知道哪个input属于哪个隐藏的版本。 通过这种方式,可以在同一页面上有多个input
,并且有一个或多个datalist
提供build议。
任何用户input都按原样提交。 要在数据列表中不存在用户input时提交一个空值, hiddenInput.value = label
更改为hiddenInput.value = ""
工作jsFiddle的例子: 纯javascript和jQuery
我使用的解决scheme是
<input list="answers" id="answer"> <datalist id="answers"> <option data-value="42" value="The answer"> </datalist>
通过javascript访问要发送到服务器的值
var shownVal= document.getElementById("answer").value; var value2send=document.querySelector("#answers option[value='"+shownVal+"']").dataset.value;
希望它有帮助