【JavaScript】１日で基本を学ぶ〜中編

# オブジェクトとは

まず最初に、前回に引き続きこちらの本を参考にさせていただいた。
[岩田宇史「いちばんやさしいJavaScriptの教本」（インプレス）](https://book.impress.co.jp/books/1116101117)

オブジェクトとは・・・人によって様々な説明ができると思うが、自分はこう考えている。周辺の用語も含めて説明してみる。

- ``オブジェクト``とは「人」や「車」などの``大雑把な「モノ」``
- ``クラス``はオブジェクトの設計図
- ``インスタンス``はクラスによって具現化されたモノ
- ``プロパティ``はインスタンスのプロフィール（「性別」や「車種」など）
- ``メソッド``はインスタンスの持つ行動パターン（「座る」や「走る」など）

時と場合によってはオブジェクトとインスタンスが同じ意味で扱われていたりするが、ここは実際にコードを記述しながら理解できれば良いと思う。

オブジェクトについての理解は、JavaScriptに限らずどの言語でも必要になるだろうが、今回はオブジェクトを中心として学んでいくので改めて確認をした。

# JavaScriptのオブジェクト

JavaScriptではHTMLやCSSから要素を取得し、それをオブジェクトとして扱い様々な変更（プロパティの変更）を行うことができる。

オブジェクトは入れ子構造（ネスト）になっていて、Webページのトップには``windowオブジェクト``が君臨している。

そこからHTMLの構造である``documentオブジェクト``、その下に``elementオブジェクト``や``各要素（ノード）``であるhead、body、pなどが広がっていく。これを``DOM（Document Object Model）``と言う。

# HTMLの要素を扱う

## 要素の取得

まず、HTMLにテスト用のタグである``greeting``を記述する。

```test.html
<body>
  <div id="greeting">
    <h1>こんにちは</h1>
  </div>
  <script src="js/app.js"></script>
</body>
```

次に、JavaScriptで先ほど記述した``greeting``を取得する。``documentオブジェクトのgetElementById``メソッドを使用し、取得した結果をオブジェクトとして``element``に代入している。

``console.dir関数``を使用すると、コンソールに引数の詳細が表示されるので理解しやすい。

```app.js
var element = document.getElementById('greeting');
// console.dir(element);
```

## 要素の変更

``elementオブジェクトのinnerHTMLプロパティ``を上書きするという方法で、指定した要素の内容を書き替えることができる。

``console.dir関数``は``オブジェクト名.プロパティ``の指定でも内容を取得できるので、参考に。

```app.js
// console.dir(element.innerHTML);
element.innerHTML = "<h2>Hello!</h2>";  
```

ちなみに\<h2\>のようなタグを、タグとしてではなく文字として扱いたい場合は、``innerTextプロパティ``を使用する。

```app.js
element.innerText = "<h2>Hello!</h2>";
```

## 要素の追加

要素を追加する時は、必ず``親要素``を指定しなければならない。今回は``greetingの子要素``として``second_greeting``と``third_greeting``を追加する。

```app.js
var second_element = document.createElement('div');
second_element.setAttribute('id', 'second_greeting');
second_element.innerHTML = "<h2>ニーハオ！</h2>";
// console.dir(second_element.innerHTML);
greeting.insertBefore(second_element, null);

var third_element = document.createElement('div');
third_element.setAttribute('id', 'third_greeting');
third_element.innerHTML = "<h2>グーテンターク！</h2>";
// console.dir(third_element.innerHTML);
greeting.insertBefore(third_element, null);
```
このような段階を経て、要素が追加される。

- ``documentオブジェクトのcreateElementメソッド``で作成したいタグを用意する。それを``second_element``に代入し、オブジェクトとして扱う。
- ``second_elementオブジェクトのsetAttributeメソッド``でタグ内の``属性名id``と``属性値second_greeting``を指定する。
- ``second_elementのinnerHTMLプロパティ``に記述したい内容を代入する。
- ``親要素greetingのinsertBeforeメソッド``で、``第１引数``に追加するsecond_elementオブジェクト、``第２引数``に追加する位置を指定する。
- 同様の手順で``third_greeting``を追加する。


最後の``insertBeforeメソッド``を``greeting.insertBefore(third_element, second_element);``に書き替えれば、second_elementの前にthird_greetingが追記される。一番後ろに追記したい場合は、上記コードのように``null``を指定する。

``insertBeforeメソッド``ではidである``greeting``を直に指定しているが、既存のタグは全てオブジェクト化されているということだろうか？（あらかじめ``getElementByIdメソッド``を使用しなくても良いのだろうか？）

## 要素の削除

最後に、``<div id="second_greeting">``を削除する。要素の追加と同様、この作業にも親要素の取得が必要だ。

```app.js
var parent = second_greeting.parentElement;
parent.removeChild(second_greeting);
```

- ``second_greetingのparentElementメソッド``で親要素を取得し、``parentオブジェクト``として扱う。
- ``parentオブジェクトのremoveChildメソッド``で削除したい子要素を指定し、削除を実行する。

ここでも、idである``second_greeting``を直に指定している。代入によるオブジェクト化が必要な作業と、そうでない作業があるのだろうか？

気になったので、以下の記述でどうなるか実験してみた。

```app.js
greeting.removeChild(second_greeting);
```

この一文でも同様の削除ができた。

親要素を直に指定しなかったのは、実際の作業では``膨大なコードの中から指定した子要素の親要素を探すのが困難``だから、あえてメソッドを使用してその手間を省いたのだろう・・・と思う。

# CSSの要素を扱う

オブジェクトの``styleプロパティ``を使用し、さらに``CSSのプロパティ``を指定することにより、その内容がHTMLに反映される。

CSSのプロパティは``キャメルケース（font-sizeはfontSizeのように）``にした状態で使用できる。

先ほどのidとオブジェクト云々から以下２通りの書き方を試したが、どちらも同じ結果になった。（文字の色が赤になり、50pxサイズになる。）

``console.dir関数``を使用しても、third_elementとthird_greetingはやはり同じ結果だった。

```app.js
var third_element = document.getElementById('third_greeting');
third_element.style.color = "#FF0000";
third_element.style.fontSize = "50px";
```

```app.js
third_greeting.style.color = "#FF0000";
third_greeting.style.fontSize = "50px";
```

結局アウトプットは１日で終わらなかった。基本書の読み込みは終了しているので、自分の中での学習は一応終了している・・・と信じたい。

最後はいよいよ``イベント``だ。

今回はここまで。