checked 属性
まず、気になったのはHTMLの部分。
HTML
1<input name="" type="checkbox" value="" id="test_chk" />
2<label for="test_chk">chk1</label>
3<input name="" type="text" id="test_input" disabled="disabled" />
チェックボックスにチェックすると #test_input が disabled 状態になりますが、既に disabled 状態になっているので初めの一回のクリックでは何も発生しません。
チェックボックスには初期状態で checked 状態にしておくと良いと思います。
考えられる原因
直接的な原因は分かりませんが、考えられる可能性は2通りあります。
- チェックボックスの状態遷移だけ発生し、clickイベントハンドラが実行されなかった
- clickイベントハンドラだけ実行され、チェックボックスの状態遷移が発生しなかった
clickイベントハンドラの方が後で発生する為、1. の可能性が高いと思われます。
ご掲示のコードは途中経過のclickイベントハンドラが発火しなかったとしても、最後のclickイベントハンドラが実行されれば期待撮りの動作するはずなので、少なくとも最後のclickイベントハンドラは発生していないと想像できます。
対策コード
対策は2通りあります。
- 素のJavaScriptでコードを書き、clickイベントハンドラの処理時間を短くする(高速化による処理堕ち防止)
- clickイベントハンドラ処理中はclickされても何も実行しないようにclickイベントをロックする
両方の対策を施すと、次のように書けます。
HTML
1<input name="" type="checkbox" value="" id="test_chk" />
2<label for="test_chk">chk1</label>
3<input name="" type="text" id="test_input" disabled="disabled" /><script>
4'use strict';
5document.getElementById('test_chk').addEventListener('click', {
6 input: document.getElementById('test_input'),
7 handleEvent: function (event) {
8 var checkbox = event.target;
9 checkbox.disabled = true;
10 this.input.disabled = checkbox.checked;
11 checkbox.disabled = false;
12 }
13}, false);
14</script>
ただ、checkbox変数初期化が余計に発生しているので、checkbox.disabled = true;
によるclickイベントロックが発生するまでの間にクリックされる可能性を考慮すると、ロックせずに1行でコードを実行した方がいい可能性もあるかもしれません。
JavaScript
1document.getElementById('test_chk').addEventListener('click', {
2 input: document.getElementById('test_input'),
3 handleEvent: function (event) {
4 this.input.disabled = event.target.checked;
5 }
6}, false);
これ以上、高速化しようとするなら event.target
, this.event
のプロパティ参照コストをなくす為に変数やthis値にinput要素ノードを束縛する必要があります。
JavaScript
1document.getElementById('test_chk').addEventListener('click', function (event) {
2 this.disabled = true;
3 document.getElementById('test_input').disabled = this.checked;
4 this.disabled = false;
5}.bind(document.getElementById('test_chk')), false);
#test_input
はキャッシュしていないのでまだ高速化する余地がありますが、#test_chk
が無効化(disabled)されるまでの処理時間としてはこれが最短のコードだと思います。
短時間で連続クリックすると、チェックボックスの遷移が行われない現象を確認できます。
Re: SUPER_SLiNKY さん