第17話:Webページの書き換え
目次
マンガ
マンガ台詞
説明
この章では、『Webページの書き換え』について学びます。
JavaScriptから見たWebページは、『window』オブジェクトを頂点とした、階層構造を持っています。これらは全てオブジェクトですので、通常のオブジェクトと同じようにプロパティやメソッドを持っており、プログラムで操作できます。
これまでも『window.alert』や『document.write』メソッド、『document.title』といったプロパティを利用してきました。
○window ┣○alert ┣○…… ┗○document ┣○write ┣○title ┣○……
Webページでは、HTMLタグを元に、『DOM』(Document Object Model)と呼ばれる、部品(『element』)の階層構造を作っています。
JavaScriptでは、『document』の各種メソッドを利用して、目的の部品を『element』オブジェクトとして取得できます。そして、この『element』オブジェクトに対して各種操作を行います。
それでは以下、JavaScriptを使い、この『DOM』を操作する方法を学んでいきましょう。
『DOM』でのオブジェクト操作
『DOM』(Document Object Model)は、HTMLファイルのタグから作られたWebページの部品(『Element』)にアクセスする方法です。
JavaScriptでは『getElementById』などのメソッドを使い、特定の『Element』オブジェクトを取得できます(『Element』は『要素』という意味)。
以下、簡単な例を示します。
『getElementById』メソッド
<div id="target">目標の文字列</div>
// 『id』が『target』の要素(<div id="target">目標の文字列</div>)を選択 var ele = document.getElementById("target"); // 要素の内部のHTML(ここでは『目標の文字列』)を書き換え ele.innerHTML = "書き換えたよ!";
『id』は、タグの中に書く属性の1つです。この『id』属性の値には、そのWebページでユニークな値(他に同じ値がない値)を記入します。ユニークな値を記入しているので、『getElementById』メソッドを使うことで、その要素1つだけを特定して、取り出すことができます。
上記のプログラムでは、変数『ele』に格納した要素(『element』オブジェクト)の『innerHTML』プロパティの値を書き換えています。『innerHTML』プロパティは、その要素の配下にあるHTMLを、テキストとして読み込んだり、書き換えたりするためのプロパティです。
このプログラムでは、『書き換えたよ!』という文字列を入れています。そのため、画面内の『目標の文字列』は『書き換えたよ!』という文字列に書き換わります。
『src』プロパティ
要素の中には、画像のように『src』属性を持つものがあります。
<img src="pic/a.gif">
<img id="target" src="pic/a.gif">
『img』タグでは、『Element』オブジェクトの『src』プロパティの値を書き換えることで、画像ファイルのパスを変更できます。パスを変更すると、画面に表示される画像が差し替わります。
var ele = document.getElementById("target");
ele.src = "pic/b.gif"; // 画像ファイルのパスを変更
上記のプログラムでは、id『target』の画像のパスが、『pic/a.gif』から『pic/b.gif』に書き換わります。
『getElementsByTagName』メソッド
さて、これまでの例では、要素は全て『getElementById』メソッドを使って取得してきました。しかし、HTMLファイルの全てのタグに『ID』属性を指定するのは大変です。実際のHTMLファイルでは、ほとんどのタグには『id』属性を設定していないでしょう。そういった場合は、要素を選択することはできないのでしょうか?
こういった場合は、いくつかの方法が用意されています。まずはその1つ目を紹介します。『タグの種類』から要素を選択する『getElementsByTagName』メソッドです。以下のように、タグの名前を引数に設定することで、そのタグの全要素の配列を取得できます。
// 『<img>』タグの要素を、配列として選択
var imgs = document.getElementsByTagName("img");
注意するのは、『getElementsByTagName』と、『Element』が複数形になっていることです。この『s』を忘れる人が多いので注意してください。取得した要素の配列は、『for』文で順次処理していくことで操作できます。
// 配列に格納された各要素に対して処理を実行 for (var i = 0; i < imgs.length; i ++) { // 『width』(横幅)の値を書き換える imgs[i].width = (1 + i) * 32; }
ここでは、全ての画像の『width』属性の値を書き換えて、画像の横幅を変更しています。
『getElementsByClassName』メソッド
次は、クラス名から要素を選択する『getElementsByClassName』メソッドです。『class』は、タグの中に書く属性の1つです。『class』属性は『id』属性と違い、同じWebページ中に複数配置することが可能です。
以下、簡単な例を示します。
<div class="target">目標の文字列1</div> <div class="target">目標の文字列2</div> <div class="target">目標の文字列3</div>
// 『class』属性が『target』の要素を、配列として選択
var targets = document.getElementsByClassName("target");
// 配列に格納された各要素に対して処理を実行
for (var i = 0; i < targets.length; i ++) {
// 内部のHTMLを書き換える
targets[i].innerHTML = i + ". 書き換え!";
}
こちらも『Elements』と、『Element』が複数形になっています。そのため取得した要素の配列は、『for』文で順次処理して操作できます。
『querySelector』『querySelectorAll』メソッド
次は、『セレクタ』と呼ばれる、特殊な記法で要素を選択する『querySelector』『querySelectorAll』メソッドです。『セレクタ』は、『CSS』などで、要素を指定するための書き方です。『CSS』は、もっと先の章で出てくるので、そのタイミングでまた見直してください。
『querySelector』はセレクタにマッチした最初の要素を、『querySelectorAll』は全ての要素を戻します。
以下、簡単な例を示します。
<div class="animal">犬</div> <div class="animal">猫</div> <div class="animal">猿</div>
// 『class』属性が『target』の要素を、配列として選択
var animals = document.querySelectorAll(".animal");
// 配列に格納された各要素に対して処理を実行
for (var i = 0; i < animals.length; i ++) {
// 内部のHTMLを書き換える
animals[i].innerHTML = "\" + animals[i].innerHTML + "/";
}
こちらも『Elements』と、『Element』が複数形になっています。そのため取得した要素の配列は、『for』文で順次処理して操作できます。
『DOM』で使用できる代表的なメソッド
以下、『DOM』操作で使用できるメソッドのうち、代表的なものを挙げておきます。
注:以下、『element』と書いてあるオブジェクトは、『document』もしくは『その他の要素』になります。
要素の取得
式 | 意味 |
---|---|
document.getElementById(id) | 『document』から、指定『ID』の要素を取得 |
element.getElementsByTagName(タグ名) | 指定タグ名の要素の配列を取得 |
element.getElementsByName(nameの値) | 指定『name』属性の要素の配列を取得 |
element.getElementsByClassName(classの値) | 指定『class』属性の要素の配列を取得 |
element.querySelector(セレクタ) | 指定『セレクタ』の要素の配列を取得 |
element.parentNode | 親要素を取得 |
element.childNodes | 子要素の配列を取得 |
element.firstChild | 最初の子要素を取得 |
element.lastChild | 最後の子要素を取得 |
element.previousSibling | 1つ前の要素を取得 |
element.nextSibling | 1つ後の要素を取得 |
要素内のHTMLやテキストにアクセス
式 | 意味 |
---|---|
element.innerHTML | 要素内のHTMLの文字列 |
element.textContent | 要素内の文字列のみ |
以下、プログラムのサンプルです。
<!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> </head> <body> aaa<div>bbb</div>ccc <script> alert(document.body.innerHTML); alert(document.body.textContent); </script> </body> </html>
『document.body.innerHTML』は、HTMLファイルの『<body>』タグ内のHTML文字列です。
『document.body.textContent』は、HTMLファイルの『<body>』タグ内の内部テキストです。
要素内の属性にアクセス(例は『id』へのアクセス)
式 | 意味 | 使い方 | 説明 |
---|---|---|---|
element.属性名 | 属性の参照 | a = element.id; | 変数『a』に『id』の値を入れる |
element.id = a; | 『id』に変数『a』の値を入れる | ||
element.getAttribute(属性名) | 属性の取得 | a = element.getAttribute("id"); | 変数『a』に『id』の値を入れる |
element.setAttribute(属性名, 値) | 属性の設定 | element.setAttribute("id", a); | 『id』に変数『a』の値を入れる |
要素の追加
要素の追加は、『innerHTML』の値に、文字列を設定することで行えます。また、要素を作成して、『DOM』の要素として追加することもできます。
以下、2種類の方法で、要素を追加する例を示します。
<!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> </head> <body> <div id="a"></div> <div id="b"></div> <script> var a = document.getElementById("a"); var b = document.getElementById("b"); a.innerHTML = '<div style="color: red">red</div>'; var textEle = document.createTextNode("blue"); var newEle = document.createElement("div"); newEle.appendChild(textEle); newEle.setAttribute("style", "color: blue;"); b.appendChild(newEle); </script> </body> </html>
ここでは、『createTextNode』『createElement』というメソッドで新しい要素を作成しています。また、『appendChild』メソッドで、要素を子要素として、親要素に追加しています。
以下、それぞれのメソッドの意味を表に示します。
式 | 意味 |
---|---|
element.createElement(タグ名) | 『タグ名』の要素の作成 |
element.createTextNode(文字列) | 文字列要素の作成 |
element.appendChild(要素) | 要素を、子要素として追加 |
『DOM』は、それだけで本になるぐらい、様々なテクニックがあります。詳しく知りたければ、インターネットや書籍で調べてください。
『フォーム』の操作
Webページには、『フォーム』と呼ばれるオブジェクトがあります。これは、ボタンやリスト、ラジオボタンや、チェックボックスなどです。
<form name="form1" method="get" action="index.cgi"> テキスト: <input type="text" name="text1" value="text value" size=30> <br> テキスト エリア:<br> <textarea name="tarea1" cols=40 rows=4></textarea> <br> <input type="checkbox" name="cbox1" checked>チェックボタン1 <br> <input type="radio" name="radio1" value="r1" checked>ラジオボタン1 <input type="radio" name="radio1" value="r2">ラジオボタン2 <br> <select name="select1"> <option value="1">セレクト1</option> <option value="2">セレクト2</option> <option value="3" selected>セレクト3</option> </select> <br> <input type="hidden" name="hidden1" value="隠れた値"> <br> <input type="submit" value="実行"> <input type="reset" value="取消"> </form>
これらの要素には、『DOM』以外の簡易な方法でもアクセスできます。
『document.(『フォーム』の『name』の値).(『フォームの部品』の『name』の値)』と書くことで、その要素を取得できます。
var element = document.form1.text1;
こうやって取得した要素は、部品の種類によって、操作方法が異なります。
文字列を入力する部品(『<input type="text">』『<textarea>』『<input type="hidden">』など)は、『value』プロパティを使って、内部の文字列を取得したり、書き換えたりできます。
var element = document.form1.text1; alert("text1 : " + element.value); element.value = "新しい値";
チェックボタン(『<input type="checkbox">』)や、ラジオボタン(『<input type="radio">』)は、『checked』プロパティを使って、選択状態を取得したり、変更したりできます。
var ele = document.form1.cbox1; alert("cbox1 : " + ele.checked); ele.checked = false; var ele = document.form1.radio1; if (ele.length) { // 配列の場合 for (var i = 0; i < ele.length; i ++) { alert("radio1[" + i + "] : " + ele[i].checked); } } else { // 1つしかない場合 alert("radio1 : " + ele.checked); }
セレクト(『<select>』)は、『selectedIndex』プロパティを使って、選択要素の番号を取得したり、変更したりできます。
var ele = document.form1.select1; alert("select1 : " + ele.selectedIndex); ele.selectedIndex = 0;
また『options』を利用して、セレクト配下の『<option>』の配列を取得できます。この配列は、『selected』プロパティを使って、選択状態を取得したり、変更したりできます。
var ele = document.form1.select1;
for (var i = 0; i < ele.length; i ++) {
alert("select1[" + i + "] : " + ele[i].selected);
}
これらの要素には、『DOM』を使ってもアクセスできます。
<!DOCTYPE html> <html lang="ja"> <head> <meta charset="UTF-8"> </head> <body> <input type="text" id="input" value="AAA"><br> <select id="select"> <option>0 : BBB</option> <option>1 : CCC</option> </select><br> <input type="checkbox" id="check" value="DDD"> <script> var input = document.getElementById("input"); input.value = "入力"; var select = document.getElementById("select"); select.selectedIndex = 1; var check = document.getElementById("check"); check.checked = true; </script> </body> </html>
さらに詳しく知りたい場合は、下記を参考にしてください。
『location』オブジェクト
WebページのURLが保持されているオブジェクトです。『window.location』『location』のどちらの書き方でも利用できます。
以下、よく利用するプロパティを示します。
式 | 意味 | 中身の例 |
---|---|---|
location.href | URL | https://www.google.com/hoge/hoge/index.cgi?q=search#result |
location.protocol | プロトコル | https: |
location.host | ホスト | www.google.com:8000 |
location.hostname | ホスト名 | www.google.com |
location.port | ポート | 8000 |
location.pathname | パスとファイル名 | /hoge/hoge/index.cgi |
location.search | 検索などのCGIの値 | ?q=search |
location.hash | #以降の内部リンク | #result |
この中で、『location.href』は特殊なプロパティです。『location.href』に新しいURLを代入すれば、そのページに移動することができます。
location.href = "https://crocro.com/";
上記のプログラムを実行すると、WebページのURLが『https://crocro.com/』に変わり、表示されているページが、このページに書き換わります。
サンプルの入手
以下は、今回出てきたサンプルです。
ZIPでまとめてダウンロード (右クリックから保存してください)
『sample1.html』(要素内部の書き換え)を表示
『sample2.html』(要素のプロパティ一覧)を表示
『sample3.html』(画像の『src』を書き換え)を表示
『sample4.html』(様々な方法で要素を選択)を表示
『sample5.html』(要素内のHTMLやテキスト)を表示
『sample6.html』(要素の追加)を表示
『sample7.html』(フォームの操作)を表示
『sample8.html』(フォームの操作)を表示
『sample9.html』(『location』の書き換え)を表示
プログラムの中身を見たい場合は、それぞれのHTMLファイルをブラウザで開いたあと、右クリックをして『ソースの表示』を選択してください。
メモ帳で、ファイルの中身を見ることができます。