Operaの特殊な?挙動
Operaの動作について気づいたことがあるのでメモ。
JavascriptからDOMに対して一度に複数の処理を行った場合、多くのブラウザでは関数の終わりにまとめてそれらの操作が画面に反映されるのに対してOperaは操作が逐一画面に反映されます。下のコードを実行すると違いが分かります。
<html> <head> <meta http-equiv="Content-Type" content="text/html; charset=Shift_JIS"> <title>DOM test</title> <script type="text/javascript" src="jquery-1.5.1.min.js"> </script> </head> <body> <script> var addOptions = function(){ var target = document.getElementById("test"); target.disabled = false; //selectを選択可能にする //非常に重いのでIE8などで実行する場合は下の10000を減らしてください for(var i = 0; i < 10000; i++){ $("<option>").attr({value:i}).text(i + "分かりやすくするための文字列").appendTo(target); //選択肢を追加する } } </script> <form> <select id="test" disabled="disabled"> </select> <input type="button" value="選択肢を追加" onclick="addOptions()"> </form> </body> </html>
このコードは読み込み時点で"disabled"(操作不可能)になっている"select"要素に対し、"選択肢を追加"ボタンを押すことで"select"を操作可能にすると共に選択肢を1万個追加しています。(分かりやすさのために非常に重くしているのでIE8などでは2千程度に減らして実行してください。)
選択肢の追加処理より先に"select"を操作可能にする処理を書いています。
これを実行するとIE、Chrome、Firefoxではすべての選択肢が追加されてから"select"要素が操作可能な状態になります。正確に言うと関数が終わる時にすべての変更がまとめて画面に反映されます。非常に重い処理であるため処理の間はブラウザがいわゆる固まった状態になってしまいます。
これに対してOperaはまず"select"が操作可能な状態になってから選択肢の追加処理が行われます。つまり処理が逐一画面に反映されます。選択肢の追加が終わるまでは非常に不安定になりますが固まってしまうことはありません。
どちらが正しい挙動かといったことではないと思うのですが、上の例ですと
target.disabled = false;
という"select"を操作可能にする処理を選択肢追加より後に記述するのがよりクロスブラウザな書き方ではあると思います。
そもそもこの違いが現れるほど重い処理を書くのがまちがいではあるのですが覚えておくと何かの時に役に立つかも・・・?
という話でした。
(動作確認はすべてWindows版で行っています。)