I am using jQuery Mobile to populate a series of list views from information stored in a database, each list view populates the following one in a parent-child relationship (ex: first list view allows you to choose animals, you choose dog, next list view is populated with pedigrees, and so on).
Right now my code properly populates the list views properly, the problem I have is that if I go back to a parent list view and make a different selection, the child list views do not refresh and we end up with a bunch of appended information. I have read a lot everywhere but I cannot seem to find a proper implementation for my code.
<ul data-role="listview" data-filter="false" data-inset="true" data-theme="a" data-divider-theme="a">
<li>
<label for="pet" class="select">Pet</label>
<select id="pet" data-mini="true" onchange="fill_list('pedigree', this);">
<option value=""></option>
</select>
</li>
<li>
<label for="pedigree" class="select">Pedigree</label>
<select id="pedigree" data-mini="true" onchange="fill_list('pet_name', this);">
<option value=""></option>
</select>
</li>
<li>
<label for="pet_name" class="select">Pet Name</label>
<select id="pet_name" data-mini="true">
<option value=""></option>
</select>
</li>
</ul>
function fill_list(next_list, this_list){
var pet_url = server_root_url + 'controler/pet/find_pet.php';
var value = this_list.options[this_list.selectedIndex].value;
var params = {
control: next_list,
value: value
};
$.ajax({
type: "POST",
url: pet_url,
async:false,
data: params,
success: function(json){
do_fill_list(json, next_list);
}
});
}
function do_fill_list(json, next_list){
var x = "#" + next_list;
var option = $(x);
/*------------------------------------------------------------------------------
EDIT:
Below is the solution I found for this issue.
Basically we capture the current list with the switch, empty it,
append it with a blank line, then let the rest of the code populate the list.
-------------------------------------------------------------------------------*/
switch(next_list){
case "pet":
options.html("").append("<option />");
break;
case "pedigree":
options.html("").append("<option />");
break;
case "pet_name":
options.html("").append("<option />");
break;
}
//-------------------------------------END EDIT------------------------------------
$.each(json.control,
function(i,control){
switch(next_list){
case "pet":
option.append($("<option />").val(control.pet).text(control.pet));
break;
case "pedigree":
option.append($("<option />").val(control.pedigree).text(control.pedigree));
break;
case "pet_name":
options.append($("<option />").val(control.pet_name).text(control.pet_name));
break;
}
}
);
}
Note that I call a PHP function to handle the backend fetching of the data, but you can hardcode this data if you need to test it out. Also, I have a commented line in the last JS function of which I have read plenty about: the refresh method, which should be implemented to solve my issue. I have tried countless ways of doing this, clearly not enough.
EDIT: I have added a switch statement that resolves this issue, it is within the "do fill list" JS method.
The code below is the solution to my question (see above for full code AND edited code. Basically all that needed to be done is capture the selected list view, empty it and append an empty option. Why an empty option? Because otherwise you would click on the list view and you would not be able to select the first choice; it happens that you cannot select it if you wanted to change it.
Insert this code in the do_fill_list method, right in between var option = $(x); AND the $.each(json.control (...) function:
switch(next_list){
case "pet":
options.html("").append("<option />");
break;
case "pedigree":
options.html("").append("<option />");
break;
case "pet_name":
options.html("").append("<option />");
break;
}
This code can be enhanced to clear child selections when a parent selection has been changed. I am still working on this functionality, if anyone needs it you can ask for it, I am sure I will get it done soon.