Ottenere i campi delle select
La prima cosa da implementare è il file PHP actor.select.php, nella directory ajax-scripts/, questo file accetta in ingresso dei paramentri in GET e ritorna un JSON per javascript.
Il file actor.select.php:
Codice PHP:
<?php
include_once('../inc/config.inc.php');
include_once('../inc/db.inc.php');
require_once("../inc/class/JSON.php");
//Se è passato il parametro GET regione, devo estrarre le Provincie con l'id_regione = a quello passato
if(isset($_GET['regione']))
{
//Estraggo le provincie per l'id_regione
//controllo che non mi passi niente di dannoso per il DB usando intval(), che trasforma una stringa nel numero corrispondente
$reg_id = intval($_GET['regione']);
//La query
$query = "SELECT * FROM Provincia WHERE id_regione = $reg_id";
$result = mysql_query($query, $db);
//Uso questo array per salvare i dati ce verranno poi convertiti in JSON
$toParseArray = array(
'values' => array(-1),
'texts' => array("Seleziona una Provincia")
);
//Ciclio su tutte le righe
while($row = mysql_fetch_array($result))
{
//Inserisco l'ID che verrà assegnato come value della option
$toParseArray['values'][] = intval($row['id']);
//Inserisco i testi che verranno inseriti nelle option
$toParseArray['texts'][] = $row['nome']." (".$row['abbr'].")";
}
//Istanzio la Service_JSON
$json = new Services_JSON();
//Creo la stringa
$output = $json->encode($toParseArray);
//La stampo
print($output);
//Fine
exit;
}
//Se non è stato passato la regione, controlle che sia passato il parametro GET provincia, in questo caso devo tornare
//le città con id_prov = al paramentro passato
else if(isset($_GET['provincia']))
{
//Estraggo le città per l'id_prov
//controllo che non mi passi niente di dannoso per il DB usando intval(), che trasforma una stringa nel numero corrispondente
$prov_id = intval($_GET['provincia']);
//La query
$query = "SELECT * FROM Citta WHERE id_prov = $prov_id";
$result = mysql_query($query, $db);
//Uso questo array per salvare i dati ce verranno poi convertiti in JSON
$toParseArray = array(
'values' => array(-1),
'texts' => array("Seleziona una Città")
);
//Ciclio su tutte le righe
while($row = mysql_fetch_array($result))
{
//Inserisco l'ID che verrà assegnato come value della option
$toParseArray['values'][] = intval($row['id']);
//Inserisco i testi che verranno inseriti nelle option
$toParseArray['texts'][] = $row['nome'];
}
//Istanzio la Service_JSON
$json = new Services_JSON();
//Creo la stringa
$output = $json->encode($toParseArray);
//La stampo
print($output);
//Fine
exit;
}
//Se, invine, non è stato passato niente, stampo tutte le regioni
else
{
//Esraggo tutte le regioni
//La query
$query = "SELECT * FROM Regione";
$result = mysql_query($query, $db);
//Uso questo array per salvare i dati ce verranno poi convertiti in JSON
$toParseArray = array(
'values' => array(-1),
'texts' => array("Seleziona una Regione")
);
//Ciclio su tutte le righe
while($row = mysql_fetch_array($result))
{
//Inserisco l'ID che verrà assegnato come value della option
$toParseArray['values'][] = intval($row['id']);
//Inserisco i testi che verranno inseriti nelle option
$toParseArray['texts'][] = $row['nome'];
}
//Istanzio la Service_JSON
$json = new Services_JSON();
//Creo la stringa
$output = $json->encode($toParseArray);
//La stampo
print($output);
//Fine
exit;
}
?>
Il file mi sembra ben commentato, unica nota: come prima option di ogni select inserisco una option con value="-1" e testo Selezionare una Regione, Provincia, Città.
Ora c'è la parte di functions.form.js che va a chiamare il file actor.select.php con chiamare AJAX.
Codice PHP:
var callRegione, callProvincia, callCitta;
var action_select = 'ajax-scripts/actor.select.php';
/**
* Questa funzione aggiunge all'Evento OnLoad della pagina le segueti azioni:
*/
window.addEvent('load' , function(){
//Istanza l'oggetto Request.JSON per il popolamento del select#citta
callCitta = new Request.JSON({
url: action_select,
onComplete: function(obj){
populateSelect('citta', obj);
}
});
//Istanza l'oggetto Request.JSON per il popolamento del select#provincia
callProvincia = new Request.JSON({
url: action_select,
onComplete: function(obj){
populateSelect('provincia', obj);
}
});
//Istanza l'oggetto Request.JSON per il popolamento del select#regione
callRegione = new Request.JSON({
url: action_select,
onComplete: function(obj){
populateSelect('regione', obj);
}
});
/*Popolo la select delle regioni*/
callRegione.get();
/*Aggiungo gli eventi sui Select che popoleranno i successivi*/
$('regione').addEvent('change', function(){
var selected = this.getSelected()[0].value;
callProvincia.get({
'regione': selected
});
})
$('provincia').addEvent('change', function(){
var selected = this.getSelected()[0].value;
callCitta.get({
'provincia': selected
});
})
})
/**
* Questa funzione cancella gli elementi in una SELECT, poi la ripopola con gli elementi di un Oggetto JSON.
* Struttura del JSON:
* {"values":[-1,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20],"texts":["Seleziona una Regione","Valle d´Aosta","Piemonte","Liguria","Lombardia","Trentino-Alto Adige","Veneto","Friuli-Venezia Giulia","Emilia-Romagna","Toscana","Marche","Umbria","Lazio","Abruzzo","Molise","Campania","Basilicata","Puglia","Calabria","Sicilia","Sardegna"]}
* @param {String} id : l'id della select da aggiornare
* @param {Object} jsonObj : l'oggetto JSON che la chiamata AJAX ritorna
*/
function populateSelect(id, jsonObj){
var select = $(id);
select.empty();
$A(jsonObj.values).each(function(item, index){
var opt = new Element('option', {
'value': item
}).set('html', jsonObj.texts[index]);
opt.inject(select);
});
}
Bisogna fare una nota sugli oggetto Request.JSON. Questi oggetti fanno sempre le stesse azioni, quindi li ho istanziati una volta sola. In questo modo c'è un utilizzo molto minore della memoria del browser.
Questo è quanto necessario per far funzionare le select modificabili con AJAX.