Actualmente, el <datalist>elemento HTML5 es compatible con la mayoría de los principales navegadores (excepto Safari) y parece una forma interesante de agregar sugerencias a una entrada.
Sin embargo, parece haber algunas discrepancias entre la implementación del valueatributo y el texto interno en <option>. Por ejemplo:
<input list="answers" name="answer">
<datalist id="answers">
<option value="42">The answer</option>
</datalist>
Esto se maneja de manera diferente por diferentes navegadores:
Chrome y Opera:

FireFox e IE 11:

Después de seleccionar uno, la entrada se llena con el valor y no con el texto interno. Solo quiero que el usuario vea el texto ("La respuesta") en el menú desplegable y en la entrada, pero pase el valor 42al enviar, como lo selectharía.
¿Cómo puedo hacer que todos los navegadores tengan la lista desplegable que muestre las etiquetas (texto interno) de los <option>correos electrónicos, pero envíen el valueatributo cuando se envíe el formulario?
fuente

value=""debería tener prioridad sobre una cadena dentro de las etiquetas, siempre que haya unvalue=""declarado. Entonces, la sugerencia sería hacer de "la respuesta" su atributo de valor.Respuestas:
Tenga en cuenta que
datalistno es lo mismo que aselect. Permite a los usuarios ingresar un valor personalizado que no está en la lista, y sería imposible obtener un valor alternativo para dicha entrada sin definirlo primero.Las posibles formas de manejar la entrada del usuario son enviar el valor ingresado como está, enviar un valor en blanco o evitar el envío. Esta respuesta maneja solo las dos primeras opciones.
Si desea no permitir la entrada del usuario por completo, tal vez
selectsea una mejor opción.Para mostrar solo el valor de texto de
optionen el menú desplegable, usamos el texto interno y omitimos elvalueatributo. El valor real que queremos enviar se almacena en undata-valueatributo personalizado :Para enviar esto
data-valuetenemos que usar un<input type="hidden">. En este caso, dejamos fuera laname="answer"entrada normal y la movemos a la copia oculta.<input list="suggestionList" id="answerInput"> <datalist id="suggestionList"> <option data-value="42">The answer</option> </datalist> <input type="hidden" name="answer" id="answerInput-hidden">De esta manera, cuando el texto en la entrada original cambia, podemos usar javascript para verificar si el texto también está presente en
datalisty recuperar sudata-value. Ese valor se inserta en la entrada oculta y se envía.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.getAttribute('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; } } });La identificación
answeryanswer-hiddenla entrada normal y oculta son necesarios para que el script sepa qué entrada pertenece a qué versión oculta. De esta manera, es posible tener varios correosinputelectrónicos en la misma página con uno o másdatalistcorreos electrónicos que brinden sugerencias.Cualquier entrada de usuario se envía tal cual. Para enviar un valor vacío cuando la entrada del usuario no está presente en la lista de datos, cambie
hiddenInput.value = inputValueahiddenInput.value = ""Ejemplos de trabajo de jsFiddle: JavaScript simple y jQuery
fuente
La solución que utilizo es la siguiente:
<input list="answers" id="answer"> <datalist id="answers"> <option data-value="42" value="The answer"> </datalist>Luego acceda al valor que se enviará al servidor usando JavaScript como este:
var shownVal = document.getElementById("answer").value; var value2send = document.querySelector("#answers option[value='"+shownVal+"']").dataset.value;Espero eso ayude.
fuente
inputelemento con atributodata-value="1". Luego escribí el siguiente bloque en los lugares donde se tomó y usó el valor:if (typeof $(this).attr('data-value') != 'undefined') { var id = $(this).attr('name'); val = $('#'+id).find('option[value="'+val+'"]').attr('data-value'); }Me doy cuenta de que esto puede ser un poco tarde, pero me topé con esto y me preguntaba cómo manejar situaciones con múltiples valores idénticos, pero claves diferentes (según el comentario de bigbearzhu).
Así que modifiqué ligeramente la respuesta de Stephan Muller:
Un datalist con valores no únicos:
<input list="answers" name="answer" id="answerInput"> <datalist id="answers"> <option value="42">The answer</option> <option value="43">The answer</option> <option value="44">Another Answer</option> </datalist> <input type="hidden" name="answer" id="answerInput-hidden">Cuando el usuario selecciona una opción, el navegador reemplaza
input.valuecon elvaluede ladatalistopción en lugar delinnerText.El siguiente código luego busca un
optioncon esovalue, lo empuja al campo oculto y lo reemplazainput.valuecon elinnerText.document.querySelector('#answerInput').addEventListener('input', function(e) { var input = e.target, list = input.getAttribute('list'), options = document.querySelectorAll('#' + list + ' option[value="'+input.value+'"]'), hiddenInput = document.getElementById(input.getAttribute('id') + '-hidden'); if (options.length > 0) { hiddenInput.value = input.value; input.value = options[0].innerText; } });Como consecuencia, el usuario ve lo que
innerTextdice la opción , pero la identificación única deoption.valueestá disponible al enviar el formulario. Demostración jsFiddlefuente
Al hacer clic en el botón de búsqueda, puede encontrarlo sin un bucle.
Simplemente agregue a la opción un atributo con el valor que necesita (me gusta
id) y búsquelo específico.$('#search_wrapper button').on('click', function(){ console.log($('option[value="'+ $('#autocomplete_input').val() +'"]').data('value')); })fuente
Usando PHP he encontrado una forma bastante simple de hacer esto. Chicos, usen algo como esto
<input list="customers" name="customer_id" required class="form-control" placeholder="Customer Name"> <datalist id="customers"> <?php $querySnamex = "SELECT * FROM `customer` WHERE fname!='' AND lname!='' order by customer_id ASC"; $resultSnamex = mysqli_query($con,$querySnamex) or die(mysql_error()); while ($row_this = mysqli_fetch_array($resultSnamex)) { echo '<option data-value="'.$row_this['customer_id'].'">'.$row_this['fname'].' '.$row_this['lname'].'</option> <input type="hidden" name="customer_id_real" value="'.$row_this['customer_id'].'" id="answerInput-hidden">'; } ?> </datalist>El código de arriba permite que el formulario lleve la identificación de la opción también seleccionada.
fuente
customer_id_realenviado, no el valor seleccionado.