| re: Why does event for SELECT not fire in Mozilla?
On Fri, 24 Sep 2004 09:35:01 GMT, "Michael Winter"
<M.Winter@blueyonder.co.invalid> wrote:
[color=blue]
>[Follow-ups set to comp.lang.javascript]
>
>On Fri, 24 Sep 2004 10:02:55 +0100, mark4asp
><mark4asp#killspam#@ntlworld.com> wrote:
>[color=green]
>> Why does this not work in Mozilla ?
>>
>> <http://homepage.ntlworld.com/mark.pawelek/code/animals.html>
>>
>> The optHabitat_change() event does not fire. What am I doing wrong
>> here?[/color]
>
>It does fire. If you look at the error console, you'll see Mozilla
>complain.
>
>You see unfortunately, IE hasn't followed the W3C with regards to the
>HTMLSelectElement.add method. IE uses a number for the second argument,
>and an optional one at that. However, the W3C DOM states that the second
>argument is a required object reference.
>
>The two simply aren't compatible (though good 'ol Opera allows both).
>
>There seems to be four options available.
>
>1) Fall back on the old approach of using the Option constructor to create
>new OPTION elements and append them using the options collection. This
>will be supported by older scriptable browsers.
>2) Use try/catch to determine whether an error occurs whilst trying to use
>the object or number version of the method. Use the other approach in the
>catch clause. This won't be supported by older browsers because a) they
>don't support try/catch, and b) they won't support DOM 1.
>3) Use appendChild to add the OPTION elements. I haven't thoroughly tested
>this, but it appears to work. This won't be supported by older browsers as
>they don't support DOM 1.
>4) Use the (preferred) server-side approach. This will be supported by old
>and new browsers alike, scriptable or otherwise.
>
>Hope that helps,
>Mike[/color]
It helped but the code still didn't work in Mozilla - for a different
reason which I was never able to figure out!
I fixed it by passing in the value of the item to be selected instead
of the index to be selected into the two functions loadOpt() and
optHabitat_change(). This is much more logical even if it needs a line
or two of code more. I dispense with the stupid index positions and
use the values (which are the numbers in my data arrays anyway).
I include the fixed code because I always like a complete solution for
the benefit of any stranger who may have a similar problem in future.
[Oh yeh, and I've decided that Google is a nice place to store bits of
code that one may need in future too!]
I also had to change the way options were deleted as well as created.
<html>
<head>
<title>Funny Animals</title>
<script language="javascript" type="text/javascript">
<!--
// Start of database
habitats = {
1:"arctic",
2:"desert",
3:"ocean" }
// "name", "habitat", "type", "page #"
creatures = {
1:["camel", "2", "10", "1¸14"],
2:["polar bear", "1", "10", "1¸14"],
3:["scorpion", "2", "10", "1¸14"],
4:["tuna", "3", "10", "1¸14"],
5:["whale", "3", "", "9"] }
// Initialise HTML
window.onload = Initialise;
// Core code
function getObj(oTxt) {
return document.getElementById(oTxt);
}
function toUpper(w) {
return (w.charAt(0).toUpperCase() + w.substring(1))
}
function Int(n){
return parseInt(n);
}
// Core code END
// Initialise & Events
function Initialise(){
loadOpt(getObj('optHabitat'), habitats, 1);
optHabitat_change(getObj('optCreature'), 1);
}
// selVal = value of row to be selected.
function loadOpt(oCbo, ary, selVal) {
var key;
var i = 0;
for (key in ary) {
oCbo.options[oCbo.options.length] = new Option(toUpper(ary[key]),
key);
oCbo[i].selected = (oCbo.options.value==selVal) ? true : false;
i++;
}
}
function makeOption(obj, text) {
if (obj!=null && obj.options!=null)
obj.options[obj.options.length] = new Option(text, value)
}
function removeAllOptions(oCbo) {
for (var i=(oCbo.options.length-1); i>=0; i--)
oCbo.options[i] = null;
oCbo.selectedIndex = -1
}
function optHabitat_change(oCbo, habitat) {
var s = '';
var key;
removeAllOptions(oCbo);
for (key in creatures) {
s = creatures[key][1].toString();
arow = s.split('¸');
if (habitat==Int(arow[0]))
oCbo.options[oCbo.options.length] = new
Option(toUpper(creatures[key][0]), key);
}
return true
}
// Initialise & Events END
//-->
</script>
</head>
<body>
<p>Creatures:<br />
<select id="optHabitat"
onchange="optHabitat_change(getObj('optCreature'), this.value)"></select><br>
<!-- ,this.options(this.selectedIndex).value -->
<select id="optCreature"></select></p>
</body>
</html> |