Supongamos que tengo tres controles de lista desplegable llamados dd1
, dd2
y dd3
. El valor de cada lista desplegable proviene de la base de datos. El valor de dd3
depende del valor de dd2
y el valor de dd2
depende del valor de dd1
. ¿Alguien puede decirme cómo llamo a servlet para este problema?Llenar listas desplegables en cascada en JSP/Servlet
Respuesta
Básicamente, hay tres maneras de lograr esto:
Envíe el formulario a un servlet durante el evento onchange de la primera desplegable (se puede utilizar Javascript para esto), deja que el servlet obtener el elemento seleccionado de el primer menú desplegable como parámetro de solicitud, le permite obtener los valores asociados del segundo menú desplegable de la base de datos como
Map<String, String>
, deje que los almacene en el ámbito de la solicitud. Finalmente, deje que JSP/JSTL muestre los valores en el segundo menú desplegable. Puede usar JSTL (simplemente elimine jstl-1.2.jar en/WEB-INF/lib
)c:forEach
etiqueta para esto. Puede rellenar previamente la primera lista en el métododoGet()
delServlet
asociado a la página JSP.<select name="dd1" onchange="submit()"> <c:forEach items="${dd1options}" var="option"> <option value="${option.key}" ${param.dd1 == option.key ? 'selected' : ''}>${option.value}</option> </c:forEach> </select> <select name="dd2" onchange="submit()"> <c:if test="${empty dd2options}"> <option>Please select parent</option> </c:if> <c:forEach items="${dd2options}" var="option"> <option value="${option.key}" ${param.dd2 == option.key ? 'selected' : ''}>${option.value}</option> </c:forEach> </select> <select name="dd3"> <c:if test="${empty dd3options}"> <option>Please select parent</option> </c:if> <c:forEach items="${dd3options}" var="option"> <option value="${option.key}" ${param.dd3 == option.key ? 'selected' : ''}>${option.value}</option> </c:forEach> </select>
Una vez salvedad es sin embargo que esto va a someter la totalidad forma y provocar un "destello de contenido" que puede ser malo para la experiencia del usuario. También necesitará retener los otros campos en el mismo formulario en función de los parámetros de solicitud. También deberá determinar en el servlet si la solicitud es para actualizar un menú desplegable (el valor desplegable del elemento secundario es nulo) o para enviar el formulario real.
Imprime todos los valores posibles del segundo y tercer desplegable como un objeto Javascript y utiliza una función Javascript para completar el segundo menú desplegable basado en el elemento seleccionado del primer menú desplegable durante el evento onchange del primer menú desplegable. No se envía ningún formulario y no se necesita un ciclo de servidor aquí. Sin embargo
<script> var dd2options = ${dd2optionsAsJSObject}; var dd3options = ${dd3optionsAsJSObject}; function dd1change(dd1) { // Fill dd2 options based on selected dd1 value. var selected = dd1.options[dd1.selectedIndex].value; ... } function dd2change(dd2) { // Fill dd3 options based on selected dd2 value. var selected = dd2.options[dd2.selectedIndex].value; ... } </script> <select name="dd1" onchange="dd1change(this)"> <c:forEach items="${dd1options}" var="option"> <option value="${option.key}" ${param.dd1 == option.key ? 'selected' : ''}>${option.value}</option> </c:forEach> </select> <select name="dd2" onchange="dd2change(this)"> <option>Please select parent</option> </select> <select name="dd3"> <option>Please select parent</option> </select>
Una advertencia es que esto puede llegar a ser innecesariamente largo y costoso cuando se tiene una gran cantidad de artículos. Imagine que tiene 3 pasos de cada 100 elementos posibles, que significaría 100 * 100 * 100 = 1,000,000 de elementos en objetos JS. La página HTML crecerá más de 1 MB de longitud.
Utilice XMLHttpRequest en Javascript para iniciar una solicitud asincrónica a un servlet durante el evento onchange del primer menú desplegable, deje que el servlet obtenga el elemento seleccionado de la primera lista desplegable como parámetro de solicitud, permita obtener los valores asociados de la segunda lista desplegable de la base de datos, devuélvala como cadena XML o JSON. Finalmente, permita que Javascript muestre los valores en el segundo menú desplegable a través del árbol HTML DOM (el modo Ajax, como se sugirió anteriormente). La mejor forma de hacerlo sería usando jQuery.
<%@ page pageEncoding="UTF-8" %> <%@ taglib uri="http://java.sun.com/jsp/jstl/core" prefix="c" %> <!DOCTYPE html> <html lang="en"> <head> <title>SO question 2263996</title> <script src="http://code.jquery.com/jquery-latest.min.js"></script> <script> $(document).ready(function() { $('#dd1').change(function() { fillOptions('dd2', this); }); $('#dd2').change(function() { fillOptions('dd3', this); }); }); function fillOptions(ddId, callingElement) { var dd = $('#' + ddId); $.getJSON('json/options?dd=' + ddId + '&val=' + $(callingElement).val(), function(opts) { $('>option', dd).remove(); // Clean old options first. if (opts) { $.each(opts, function(key, value) { dd.append($('<option/>').val(key).text(value)); }); } else { dd.append($('<option/>').text("Please select parent")); } }); } </script> </head> <body> <form> <select id="dd1" name="dd1"> <c:forEach items="${dd1}" var="option"> <option value="${option.key}" ${param.dd1 == option.key ? 'selected' : ''}>${option.value}</option> </c:forEach> </select> <select id="dd2" name="dd2"> <option>Please select parent</option> </select> <select id="dd3" name="dd3"> <option>Please select parent</option> </select> </form> </body> </html>
..where la
Servlet
detrás/json/options
podría tener este aspecto:protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { String dd = request.getParameter("dd"); // ID of child DD to fill options for. String val = request.getParameter("val"); // Value of parent DD to find associated child DD options for. Map<String, String> options = optionDAO.find(dd, val); String json = new Gson().toJson(options); response.setContentType("application/json"); response.setCharacterEncoding("UTF-8"); response.getWriter().write(json); }
Aquí,
Gson
Google Gson es que facilita la conversión de fullworthy objetos Java a JSON y viceversa. Consulte también How to use Servlets and Ajax?
Es posible que necesite varios servlets para esto.
Servlet 1: Cargue los valores de la primera lista desplegable de la base de datos. En la página JSP construye la lista desplegable. En el usuario seleccionando un valor enviar a servlet dos.
Servlet 2: recupera el valor de la primera lista y realiza la búsqueda en la base de datos de los valores de la segunda lista. Construye la segunda lista. Cuando el usuario selecciona el segundo valor, preséntelo al servlet 3.
Servlet 3: recupera el valor seleccionado en el segundo menú desplegable y realiza la búsqueda en la base de datos para obtener los valores del último menú desplegable.
Es posible que desee considerar AJAX para que la población de las listas se muestre sin problemas a los usuarios. jQuery tiene algunos complementos muy buenos para hacer esto bastante fácil si estás dispuesto a hacer eso.
<form action="servlet2.do">
<select name="dd1" onchange="Your JavaScript Here">
<option>....
</select>
</form>
Puede escribir código JavaScript que envía el formulario en el evento onchange. Nuevamente, si usa una biblioteca existente como jQuery, será 10 veces más simple.
estoy teniendo Frend misma idea y gracias a la cooperación pero no sé cómo puedo llamarlo mientras DD1 pierde su enfoque – deven
Puede utilizar un poco un javascript para presentar el valor. Añadiré algunos. –
A juzgar por su pregunta, en realidad no está utilizando un marco web, pero el uso de servlets para procesar html.
Seré amable y deciré que estás a una década de los tiempos :), la gente usa JSP (y un framework web como puntales) para este tipo de cosas. Sin embargo, una vez dicho esto, aquí va:
- crear un campo oculto en el formulario y definir el valor a '1', '2' o '3' en función de la cual se cae abajo a poblarse;
- En su servlet, capture este valor (request.getParamter()) y utilícelo como una instrucción 'case'/if/else para devolver los valores desplegables correspondientes.
Lo diré de nuevo, solo use un framework web, o al menos antiguo jsp antiguo para hacer esto.
Esa fue una solución simple impresionante. Me gusta lo pequeño que es el código JQuery y realmente aprecio el enlace a la API GSON. Todos los ejemplos hicieron de esto una implementación fácil.
Tuve un problema al construir la URL del servidor JSON con la referencia al elemento primario SELECT (por ejemplo, $(this).val()
) [necesario para especificar el atributo :selected
]. Modifiqué un poco el guión para incluir las actualizaciones sugeridas. Gracias por el código inicial.
<script>
$(document).ready(function()
{
$('#dd1').change(function() { fillOptions('dd1', 'dd2'); });
$('#dd2').change(function() { fillOptions('dd2', 'dd3'); });
});
function fillOptions(parentId, ddId)
{
var dd = $('#' + ddId);
var jsonURL = 'json/options?dd=' + ddId + '&val=' + $('#' + parentId + ' :selected').val();
$.getJSON(jsonURL, function(opts)
{
$('>option', dd).remove(); // Clean old options first.
if (opts)
{
$.each(opts, function(key, value)
{
dd.append($('<option/>').val(key).text(value));
});
}
else
{
dd.append($('<option/>').text("Please select parent"));
}
});
}
</script>
- 1. Eventos de formulario de Symfony2: listas desplegables
- 2. Elemento seleccionado en listas desplegables de Enum en ASP.net MVC
- 3. Alternativas a enormes listas desplegables (24,000+ elementos)
- 4. ASP.NET MVC - Completar listas desplegables de uso común
- 5. Diseño de listas desplegables de autocompletar en navegadores
- 6. Xcode 4 listas desplegables faltantes en Configuraciones de compilación
- 7. Enlazar listas de abandono con JQuery en Asp.Net
- 8. Desplegaderas en cascada en MVC 3 Razor view
- 9. ¿Cómo doy estilo a las listas desplegables de formularios?
- 10. MVC - La mejor forma de organizar las listas desplegables de uso común en muchos puntos de vista
- 11. ¿Cómo hacer listas desplegables dinámicas en la página de compilación parametrizada en un complemento Hudson personalizado?
- 12. Dropdown en cascada utilizando knockout.js
- 13. ¿Cómo funciona "en cascada"?
- 14. ¿Hay algún patrón que pueda usar para editar listas desplegables en una aplicación MVC3?
- 15. jquery selector de fecha pero día mes y año en listas desplegables separadas
- 16. desencadenantes en cascada en SQLite
- 17. Usando los parámetros desplegables en el informe SSRS
- 18. Mantenerse ágil en una cascada
- 19. Entity Framework en eliminar cascada
- 20. ¿Debería instalarse IDisposable en cascada?
- 21. Desencadenar llamadas en cascada eliminando
- 22. Cómo dibujar sombras desplegables en iOS
- 23. Activando la segunda y tercera listas desplegables para basadas en el valor de la primera lista desplegable en MVC
- 24. Eliminar muchos en cascada muchos en NHibernate
- 25. Eliminar en cascada en Entity Framework
- 26. Django no en cascada en eliminar
- 27. Compilación en memoria en cascada con javax.tool
- 28. Telerik MVC Grid Master Detail Despliegues en cascada
- 29. La validación no intrusiva del cliente ASP.Net MVC 3 no funciona con las listas desplegables
- 30. ¿Cómo "desactivar" el estilo de jQuery Mobile de las listas desplegables <select>?
Código impresionante BalusC. Si no te importa, quiero hacerte un par de preguntas sobre tu último método. En su función fillOption(), la línea $ .getJSON, parece que envía una solicitud GET al servlet, pero ¿dónde especifica la url del servlet? Además, ¿el resultado que devuelve el servlet get store está en 'opts'? Entonces, ¿es 'opta' y el objeto JSON? ¿Puedes explicar esta línea? $ ('> Option', dd) .remove(); ¿un poco más? –
@Harry Pham: '$ .getJSON' está documentado aquí: http://api.jquery.com/jQuery.getJSON/ La URL es simplemente'/json/options'. También vea el texto (no solo mire el código). Solo puede elegir la URL que desee. El 'opts' es, de hecho, la cadena JSON devuelta por el servlet. También vea el enlace JSON para obtener más información al respecto.Si sabes que Javabeans es bueno, entonces JSON debería ser lo suficientemente familiar. El '$ ('> option', dd) .remove()' elimina todas las opciones previas del menú desplegable, de lo contrario solo se agregaría, anexaría, etc. Por cierto, si te gustan las respuestas, simplemente recípalas. Veo que casi nunca votaste. – BalusC
Lo veo ahora, el primer parámetro de getJSON es la url. Soy un completo idiota Sobre lo de votar, lo siento. Ni siquiera me di cuenta de eso. Miraré atrás en mi publicación anterior y actualizaré la votación. Muchas gracias. Si tengo más preguntas, volveré y te preguntaré. –