【まさかEdgeでも?】IEで<label>の中の<img>が反応しない現象にjQueryで対応する

【まさかEdgeでも?】IEで<label>の中の<img>が反応しない現象にjQueryで対応する
Javascript

タイトルの通り。どうやらIEでは、label要素内に設置した画像をクリックしても反応しないバグ?があるようです…。商品選択のフォーム作っててちょっとハマったので、対処法を書きます。

サムネイルをクリックしたら商品を選択できるUIを作りたかったんだけど

問題の部分は、商品のカラーを選択するところ。
実際はもっともっと複雑でしたが、ざっくりゆーとこんな感じの動きを実装したかったんです。

img2

サムネイル画像をlabel要素で囲い、for属性でラジオボタンと連携させてマス。

chromeやFireFoxでは問題なく動きましたが、IEではダメでした。IE11を使ってたんだけど、これってEdgeと同じレンダリングモードなんじゃないの?まさかEdgeでもダメなのか。なんなの?labelの中の画像が反応しないと不便だって、言わないとわからないの?

jQueryの.propでラジオボタンをcheckedにする

cssでz-index指定などなど試したけどダメだったので、jQueryで解決することにしました。jQueryで、label要素に「そのfor属性と同じid」のラジオボタンをチェックするクリックイベントを付与します。
jQueryの.propを使えばチェックできます。.propは、指定した要素のcheckedプロパティを取得したり、変更したりできるメソッドです。変更には、引数にtrueかfalseを使います。こんなかんじ。

//ラベルにクリックイベントを付与
$('label').on('click', changeBigImg);

//クリックイベントの動作
function changeBigImg(){
	//ラジオボタンと、クリックされたlabelのfor属性の値をそれぞれ変数に入れる
	var radios = $('input[type="radio"]');
	var attrFor = $(this).attr('for');
	//.eachを使ってラジオボタンを順番に検査し、forの値と同じならcheckedにしてループを抜ける
	//(.eachにより動作中の当該要素は、$(this)で指定できる)
	radios.each(function(i){
		if($(this).attr('id') == attrFor){
        		$(this).prop('checked',true);
        		return false;
      		}
	});
}

これでクリックしたlabel要素と紐づいたラジオボタンがチェックされるようになりました!
が、まだ意図通りに動きません…。実は、ラジオボタンにchangeイベントを付与して他の画像の切り替えなどを行っていたのですが、どうやら.propでcheckedプロパティを変更する方法だとchangeイベントが作動しないらしい。えー。

.change()でchangeイベントを発火

というわけでここもjQeryで発火させます。さきほどのコードに.changeを足して、ラジオボタンが変わったらchangeイベントが起こるようにします。

function changeBigImg(){
	var radios = $('input[type="radio"]');
	var attrFor = $(this).attr('for');
	
	radios.each(function(i){
		if($(this).attr('id') == attrFor){
        		$(this).prop('checked',true).change();//ここでchenge発火!
       			 return false;
      		}
	});
}

やっと意図通り動きました。わー。 IEは相変わらず、油断ならないですね。。

  • このエントリーをはてなブックマークに追加