Sorry if I was unclear. What I want to do is remove all options from a select object in order to repopulate it.
Consider a simple form to illustrate what's at hand:
<form>
<select id="category" onchange="setPersonList()">
<option value="0">All</option>
<option value="1">Art Buyer</option>
...
<option value="20">Teacher</option>
</select>
<select id="person" onchange="personSelected()">
<option value="-1">Select Person</option>
<option value="1">Alex</option>
...
<option value="3000">Zed</option>
</select>
<input type="text" id="phoneNr">
</form>
When a person is selected, the input field will be filled out with the phone number registered for that person, so that it's possible to edit it.
When a category is selected, the person select object needs to be repopulated with only the people that are registered as matching that category.
Now, consider a very simple solution to this (no code to handle a category selection of "All", just specific categories):
function setPersonList() {
var d = document;
var oList = document.getElementById('person');
var oCat = document.getElementById('category');
var catIndex = oCat.options[oCat.selectedIndex].value;
// these variables are allready filled out with data
// sorted in the same order so that
// arrCat[i] holds the category type number for arrPerson[i]
arrPerson; // holds name of all people
arrID; // holds the id of all people
arrCat; // holds category id of all people
var i = 0;
var j = 0;
// Keep "replacing" options in oList until we reach the end of oList
// or until we reach the end of the arrays containing all people and categories
// arrPerson.length is always equal to arrCat.length
while (j < oList.options.length && i < arrPerson.length) {
// person is of the right category
if (arrCat[i] == catIndex) {
oList.options[j].value = arrID(i);
oList.options[j].text = arrPerson(i);
j++
}
i++;
}
// If we've gone through the whole arrPerson array
// we may have to remove options in oList that remains
// from before
if (i == arrPerson.length) {
for (i = oList.options.length; i > j; ) {
oList.remove(--i);
}
}
// Else we have to make sure that we add any remaining
// people that matches the category selection
else while (i < arrPerson.length) {
if (arrCat(i) == catIndex) {
var opt = d.createElement('option');
opt.value = arrID(i);
opt.text = arrPerson(i);
try {
oList.add(opt, null); // standards compliant
}
catch (ex) {
oList.add(opt); // IE
}
}
}
Now, if we start out with 3000 people in our person select, and the user picks a category with 10 people matching it, the following happens:
(A)
First we have 3000 iterations over the arrPerson array with 10 matching people so that we fill out the first 10 options with this info
And then we have
2990 iterations: remove the other 2990 options that are no longer needed
While (A) might be fine for 3000 entries, I doubt it will be so smooth for a few hundred thousand entries.
So instead, I'd like the above to be:
(😎
Remove all existing options from our person select
3000 iterations over arrPeople to add the 10 matches.
(😎 would effectively cut the number of iterations in half compared to (A) in some cases
And the last line in (😎 could of course be made more efficient if needs be by keeping an additional array containing data pairs of category id and array index (index into the other arrays) sorted by category to speed up the search process (o(log n) instead of o(n)).
So, my question is, how do I achieve (😎?
I tried:
oList; // contains 3000 items in the options array
oNewSelection; // newly created select object that now contains 10 items
oList.options = oNewSelection.options; // error: oList.options can't be assigned a value (message something like 'only has getter')
oList = oNewSelection; // gives me no error message, but also changes absolutely nothing
The code above was written on the fly to illustrate the problem and it's getting late, so it might contain errors, but I hope it's good enough to illustrate what I'm trying to do.
If it's still not clear enough or you want more to go on, I can post the code I have going currently (300 lines) if you think it would help. Or if I'm still expressing myself poorly, please don't hesitate to ask for more clarification in normal text.
I'd be most grateful for any input
regards
johan