実は解決策があります。基本的にイベントハンドラはhtmlタグの中に書くことになっていますが、JavaScriptの中で書くことも可能です。今回はイベントハンドラの動的設定について学びましょう。
【1】テキストエディタで以下のように入力し、ファイル名は「sample009.html」で適当な場所に保存してください。コピーして貼り付けてもかまいません。
sample009.html
<html>
<head>
<script type="text/javascript" src="sample009.js"></script>
<title>sample009</title>
</head>
<body>
<form name="form1">
<input type="text" name="txtA" id="txtA">
<select name="selOpe" size=1>
<option value="1">+</option>
<option value="2">-</option>
<option value="3">×</option>
<option value="4">÷</option>
<option value="5">%</option>
</select>
<input type="text" name="txtB" id="txtB"> =
<input type="text" name="txtC" id="txtC">
<br>
<input type="button" name="cmdCalc" id="cmdCalc" value="計算">
<input type="reset" value="クリア">
</form>
</body>
</html>
【2】テキストエディタで以下のように入力し、ファイル名は「sample009.js」で上のhtmlと同じ場所に保存してください。コピーして貼り付けてもかまいません。
sample009.js
onload = init;
function init() {
document.getElementById("txtA").onblur = function (){Blur(this);}
document.getElementById("txtA").onfocus = function (){Focus(this);}
document.getElementById("txtB").onblur = function (){Blur(this);}
document.getElementById("txtB").onfocus = function (){Focus(this);}
document.getElementById("txtC").onblur = function (){Blur(this);}
document.getElementById("txtC").onfocus = function (){Focus(this);}
document.getElementById("cmdCalc").onclick = function (){Calc();}
}
function Calc() {
//変数の宣言
var a;
var b;
var c;
var ope;
//withを使って簡潔に書く
with (document.form1) {
a = parseInt(txtA.value);
b = parseInt(txtB.value);
ope = parseInt(selOpe.value);
}
//セレクトボックスによって処理を変える
switch (ope) {
case 1:
c = a + b;
break;
case 2:
c = a - b;
break;
case 3:
c = a * b;
break;
case 4:
c = a / b;
break;
case 5:
c = a % b;
break;
default:
break;
}
//計算結果を表示
document.form1.txtC.value = c;
}
function Focus(obj){
obj.style.backgroundColor = "#ffff00";
}
function Blur(obj){
obj.style.backgroundColor = "#ffffff";
}
【3】保存したら sample009.html をダブルクリックしてWebブラウザで開きます。
★sample009.htmlとsample009.jsは必ず同じフォルダ内に置いてください。
【4】プログラムの動き自体は変わっていないことを確認してください。
【解説】
まず、html側ではイベントハンドラを削除し、変わりにコントロール(テキストボックス、ボタンなどの部品)には id="" を追加しました。名前は name と同じでかまいません。
<input type="text" name="txtA" id="txtA">
これでhtmlがすっきりしました。イベントハンドラを追加したい場合もhtmlを変更する必要がありません。
次はJavaScript部分です。JavaScriptでイベントハンドラを設定する基本的は書き方は以下の通りです。関数名の後に()カッコが付かない点に注目してください。
オブジェクト.イベントハンドラ名 = 関数名;
html読み込み完了時を感知するイベントハンドラに関数initを設定しています。
onload = init;
正式には
window.onload = init;
と書きますが、windowは省略できます。これで最初にinit()が実行されるようになりました。イベントハンドラの設定は関数init()内で設定することにします。
オブジェクトは htmlで書いたid=""を使い以下のように取得できます。
document.getElementById("txtA")
上記を踏まえて、前回までhtml部分で指定していた部分をJavaScriptで書いてみましょう。
<input type="text" name="txtA" onblur="Blur(this);">
↓
こうなりそうですが、
document.getElementById("txtA").onblur = Blur;
このままでは上手く動きません。関数に引数を指定していないのでどのコントロールで起こったイベントか判断できないからです。
そこで「無名関数」を使います。無名関数とはその名の通り関数名がない関数です。無名関数を使うと基本的な書き方は次のように変わります。
オブジェクト.イベントハンドラ名 = = function (){
ここに処理を書く;
ここに処理を書く;
}
functionの後に関数名が無い点に注目してください。処理は{}カッコ内に書いても良いのですが、すでに Blur()という関数を作っていますので、無名関数内で別の関数を呼び出すことにしました。処理が1つしかない場合は1行で書いてもかまいません。
document.getElementById("txtA").onblur = function (){Blur(this);}
これで 関数Blur() に引数を渡すことができるのできちんと動くようになります。thisとはイベントが起こったテキストボックスのことを指します。
以上でプログラムとデザインが完全に分離できました。htmlはすっきりし、プログラム的な変更は「.js」ファイル側だけいじればよいことになりました。デザイナーがnameとidを設定してくれればプログラマーと作業が分担できます。