> Manuales > Trabajo con Ajax en PHP utilizando Xajax

Usando la librería xajax veremos como construir fácilmente un sistema de select combinados con PHP y Ajax.

Un ejemplo típico de las prestaciones de Ajax es la creación de selects combinados, es decir, una estructura de dos selects, donde uno tiene las posibles opciones en función de lo que se haya elegido en el otro. Veremos como hacer este sistema en PHP y Ajax, con la ayuda de la librería xajax, que nos facilitará bastante las cosas.

Este artículo viene a continuar una serie de artículos sobre el uso de xajax, que comenzamos en el artículo Xajax: Ajax para PHP.

Veamos el ejemplo que vamos a desarrollar en este artículo.

Nota: en este artículo presentamos una manera de hacer los selects combinados con Ajax y PHP utilizando Xajax versión 0.2.5. Hemos publicado unas notas para actualizar este código a la versión 0.5, por lo que os recomendamos leer el artículo Actualizar a Xajax 0.5.

Para empezar veremos el formulario inicial con el primer select y el segundo sin opciones.

<form name="formulario">
Provincia:
<br>
<select name="provincia" onchange="xajax_generar_select(document.formulario.provincia.options[document.formulario.provincia.selectedIndex].value)">
<option value="999">Selecciona provincia</option>
<option value=0>Madrid</option>
<option value=1>Valencia</option>
<option value=2>Barcelona</option>
<option value=3>León</option>
</select>
<br>
<br>
Población: <div id="seleccombinado">
<select name="poblaciones">
<option value=0>Elegir provincia</option>
</select>
</div>
</form>


Vemos que se tiene dos campos select, el primero para las provincias y el segundo para las poblaciones. El primer campo tiene todas las opciones posibles. El segundo select inicialmente no tiene ninguna opción, porque estas se deben incluir en función de la provincia escogida en el primer campo. Vemos que el segundo select está metido en una capa con id="selectcombinado", que actualizaremos luego con Ajax.

Además, hay que fijarse en el atributo onchange del primer select, que llama con Ajax, por medio de xajax, a la función PHP que se encargará de generar las opciones del segundo select.

Ahora vamos a ver una función PHP que generaría el código de un select en función de un parámetro que recibirá: la provincia. Con ese identificador de provincia generará el código del select con todas las poblaciones de esa provincia.

function select_combinado($id_provincia){
   //función para crear el select combinado
   //debe extraer las opciones de un select a partir de un parámetro
   
   //generamos unos arrays con distintas poblaciones de varias provincias
   //estos valores en un caso práctico seguramente se extraerán de base de datos
   //no habría que cargar todos en memoria, sólo hacer el select de las poblaciones de la provincia deseada
   $madrid = array("Madrid", "Las Rozas", "Móstoles", "San Sebastián de los Reyes");
   $valencia = array("Valencia", "La Eliana", "Paterna", "Cullera");
   $barcelona = array("Barcelona", "Badalona");
   $leon = array ("León", "Astorga", "Villamejil");
   $poblaciones = array($madrid, $valencia, $barcelona, $leon);
   
   //creo las distintas opciones del select
   $nuevo_select = "<select name='poblaciones'>";
   
   for ($i=0; $i<count($poblaciones[$id_provincia]); $i++){
      $nuevo_select .= '<option value="' . $i . '">' . $poblaciones[$id_provincia][$i] . '</option>';
   }
   $nuevo_select .= "</select>";
   return $nuevo_select;
}


La función anterior tiene poco de interés para lo que es el manejo de Ajax. Aquí hemos creado unos arrays para almacenar las poblaciones de las distintas provincias, pero en nuestras aplicaciones posiblemente tengamos las poblaciones en una base de datos. En ese caso lo que tendríamos que hacer es simplemente es una consulta y recorrer un conjunto de registros.

En definitiva, la función recibe un identificador de provincia, que se utiliza para recorrer el array asociado a la provincia y generar un campo select con una opción por cada población.

Ahora vamos a ver la función que hace uso de xajax para procesar y actualizar la página con Ajax para cambiar las opciones del segundo select.

function generar_select($cod_provincia){
   //instanciamos el objeto para generar la respuesta con ajax
   $respuesta = new xajaxResponse('ISO-8859-1');
   
   if ($cod_provincia==999){
      //escribimos el select de poblaciones vacío
      $nuevo_select = '<select name="poblaciones">
                  <option value=0>Elegir provincia</option>
                  </select>
                  ';
   }else{
      $nuevo_select = select_combinado($cod_provincia);
   }
   //escribimos en la capa con id="seleccombinado"
   $respuesta->addAssign("seleccombinado","innerHTML",$nuevo_select);
   
   //tenemos que devolver la instancia del objeto xajaxResponse
   return $respuesta;
}


Lo primero es instanciar un objeto de la clase xajaxResponse para generar la respuesta. Como se puede ver, recibimos el código de la provincia como parámetro. Comprobamos si ese código de la provincia es 999, porque es un caso especial (no se ha seleccionado ninguna provincia) y tenemos que generar el select de provincias vacío. En caso que el código de la provincia sea otra cosa entonces se lo pasamos a la función select_combinado(), vista anteriormente, para generar el select con las poblaciones de la provincia dada.

Para acabar, escribimos en la capa con id="selectcombinado" la cadena con el select que hemos generado. Para escribirlo utilizamos el método addAssign() del objeto de la clase xajaxResponse que ya conocíamos de anteriores ejercicios.

El código completo es el siguiente:

<?
//incluímos la clase ajax
require ('xajax/xajax.inc.php');

//instanciamos el objeto de la clase xajax
$xajax = new xajax();
$xajax->setCharEncoding('ISO-8859-1');
$xajax->decodeUTF8InputOn();

function select_combinado($id_provincia){
   //función para crear el select combinado
   //debe extraer las opciones de un select a partir de un parámetro
   
   //generamos unos arrays con distintas poblaciones de varias provincias
   //estos valores en un caso práctico seguramente se extraerán de base de datos
   //no habría que cargar todos en memoria, sólo hacer el select de las poblaciones de la provincia deseada
   $madrid = array("Madrid", "Las Rozas", "Móstoles", "San Sebastián de los Reyes");
   $valencia = array("Valencia", "La Eliana", "Paterna", "Cullera");
   $barcelona = array("Barcelona", "Badalona");
   $leon = array ("León", "Astorga", "Villamejil");
   $poblaciones = array($madrid, $valencia, $barcelona, $leon);
   
   //creo las distintas opciones del select
   $nuevo_select = "<select name='poblaciones'>";
   
   for ($i=0; $i<count($poblaciones[$id_provincia]); $i++){
   //for ($i=0; $i<2; $i++){
      $nuevo_select .= '<option value="' . $i . '">' . $poblaciones[$id_provincia][$i] . '</option>';
   }
   $nuevo_select .= "</select>";
   return $nuevo_select;
}

function generar_select($cod_provincia){
   //instanciamos el objeto para generar la respuesta con ajax
   $respuesta = new xajaxResponse('ISO-8859-1');
   
   if ($cod_provincia==999){
      //escribimos el select de poblaciones vacío
      $nuevo_select = '<select name="poblaciones">
                  <option value=0>Elegir provincia</option>
                  </select>
                  ';
   }else{
      $nuevo_select = select_combinado($cod_provincia);
   }
   //escribimos en la capa con id="seleccombinado"
   $respuesta->addAssign("seleccombinado","innerHTML",$nuevo_select);
   
   //tenemos que devolver la instanciación del objeto xajaxResponse
   return $respuesta;
}
   
//asociamos la función creada anteriormente al objeto xajax
$xajax->registerFunction("generar_select");

//El objeto xajax tiene que procesar cualquier petición
$xajax->processRequests();
?>

<html>
<head>
   <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
   <META HTTP-EQUIV="Content-Type" CONTENT="text/html;charset=ISO-8859-1">
   <title>Validar usuario en Ajax</title>
   <?
   //En el <head> indicamos al objeto xajax se encargue de generar el javascript necesario
   $xajax->printJavascript("xajax/");
   ?>
</head>

<body>

<form name="formulario">
Provincia:
<br>
<select name="provincia" onchange="xajax_generar_select(document.formulario.provincia.options[document.formulario.provincia.selectedIndex].value)">
<option value="999">Selecciona provincia</option>
<option value=0>Madrid</option>
<option value=1>Valencia</option>
<option value=2>Barcelona</option>
<option value=3>León</option>
</select>
<br>
<br>
Población: <div id="seleccombinado">
<select name="poblaciones">
<option value=0>Elegir provincia</option>
</select>
</div>
</form>
</body>
</html>


Finalmente, podemos ver ejemplo en marcha aquí.

Miguel Angel Alvarez

Miguel es fundador de DesarrolloWeb.com y la plataforma de formación online Escu...

Manual