HTML5 プロフェッショナル認定試験 Level.2の要点[API編]

[HTML5認定試験](https://html5exam.jp/)のLevel.2に合格したので、要点メモを共有します。
まずはAPI編。あとJavascript編も書く予定。
本番の試験ではJavascriptの仕様に関する問題が割と多く出たので、そっちのほうが重要かも。。。

>追記（2018/12/09）
[Javascript編](https://qiita.com/tfuruya/items/938565802c9fb8eed611)


# Storage
## Web Storage
- クライアントアプリケーションから利用可能な、ユーザエージェントがもつ永続的なデータ格納領域

### ローカルストレージ：
- JSで明示的に削除する必要あり
- 2MB ~ 5MB
- 各種操作

```javascript 
var localstorage = window.localStroage
localstorage.setItem(key, val)
a = localstorage.getItem(key)
// 同義
localstorage.key = val
a = localstorage.key
a=localstorage[key]

//削除
localstorage.removeItem(key)
localStorage.clear()

// others
len = localStorage.length
akey = localStorage.key(index)  // 指定したindex番号のkeyを取得可能
```

### セッションストレージ
- 2MB ~ 無制限
- ブラウザを閉じると削除
 - `window.sessionStorage`
- `スキーム＋ホスト＋ポート番号`をオリジンとして捉え、それぞれデータを持つ
- WebStorageが更新されると storageイベントが発生
```javascript
window.addEventListener("storage", 
  function(e) {
    alert("StorageEvent")
  }, false
}
```

### WebStorageイベント
|プロパティ|説明|
|---------|---------|
|key| 変更されたキー|
|oldValue| 変更前の値|
|newValue| 変更後の値|
|url|オリジンのURL|
|storageArea|　localStorage or sessionStorage|


### JSON (JavaScript Object Notation)
JavaScriptオブジェクトはJSONに変換して保存可能

```javascript
// Object --> JSON
a = JSON.stringify(object)
// JSON --> Object
b = JSON.parse(a)
```


## Indexed Database API
- 検索、トランザクション、カーソルが可能なインデックス付きデータベース
- オブジェクトを保存可能
- 非同期処理を行う

> データベース
>> オブジェクトストア
>>> Key
Index
Record

```javascript
// ブラウザごとに異なるIDBFactoryオブエクトを選択
var indexedDB = window.indexedDB || window.mozIndexedDB || window.msIndexedDB;

// データベースを開く：データベース名とバージョンを選択
var request = indexedDB.open('sample', 1)

// 新規作成orバージョンが上がった時にイベント発生
request.onupgradeneeded = function(e) {　
  db = request.result;
  // ObjectStore名を指定して作成
  db.createObjectSore("store1", {autoIncrement:true}); // 自動採番
}

// transaction
// オブジェクトストアとモードを選択。オブジェクトストアは複数選択可
// デフォルトモードはreadonly
var tr = db.transaction(['store1', 'store2'], 'readwrite');
// オブジェクトストアを選択
var store1 = tf.objectStore('store1');
// レコード追加: 第二引数にキーを指定することも可能
// putかaddで追加
var req = store1.add({id:1, text:'HTML5'}); 

// キーを指定して、レコードを取得
var req = store1.get(1)
req.onsuccess = function() {
  var obj = req.result;
}

// 削除
indexedDB.deleteDatabase('db名');
db.deleteObjectSore("オブジェクトストア名");
// 閉じる
db.close();
// 

```

## File API
- HTML文章からローカルファイルにアクセスするためのAPI
- `<input type="file">` で選択された、またはWebブラウザにドラッグ＆ドロップされたファイルを、JSで読み込むことができる
- アクセスできるファイルは、ユーザが選択またはドラッグ
ドロップしたもののみ
- 新規保存や上書き保存は不可能。
 - 作成、編集したファイルをユーザにダウンロードさせることは可能

```html

<input id="fileItem" type="file" multiple>

<script>
var fileItem = document.getElementById('fileItem')
fileItem.addEventListener('change', function() {
  // Input要素からFileListオブジェクトを取得
  var fileList = fileItem.files;

  alert(fileList.length)

  // fileオブジェクト
  file = fileList.item(0);  // 0から
  // プロパティ：name, lastModifiedDate
  // Blobオブジェクトのプロパティ・メソッドを継承
  alert(file.size) // バイト数
  alert(file.type) // MIMEタイプ
}, false)
</script>
```

### FileReader
Fileオブジェクトから、内容を読み出すためのオブジェクト

```javascript
var fileItem = document.getElementById('fileItem');
// ローカルファイルの読み込み
var reader = new FileReader();
reader.onload = function() {
  alert(reader.result); 
}
fileItem.addEventListener('change', function() {
  var item = fileItem.files.item(0);
  reader.readAsText(item);
});
</script>
```

|プロパティ|概要|
|--------|--------|
|readyState|状態（0:EMPTY, 1:LOADING, 2:DONE)|
|result| ファイル内容|
|error| 読み込み中のエラー|


|メソッド|概要|
|--------|--------|
|readAsArrayBuffer|ArrayBufferオブジェクトとして読み込み|
|readAsText|文字列として読み込み|
|readAsDateURL|data:URLとして読み込む|
|abort|読み込み処理を中断|


## Binary
1 byte = 8 bit

```js
// byte数を指定
var buffer = new ArrayBuffer(4)
// DataView(ArrayBuffer, byteoffset, byteLength)
var dv = new DataView(buffer, 0)
// 設定
dv.setInt16(0, 16)
dv.setInt16(1, 22)
// 取り出し
dv.getInt16(0)
dv.getInt16(1)
```

## Tes/Debug
```javascript
console.debug() // logと同等。FFでは非推奨
console.error() // エラー
console.info() // メッセージ
console.log() // ログ
console.warm() // 警告

console.assert(条件, msg) // 条件がfalseのとき、msgを出力
console.dirxml(HTML要素) // HTML要素を表示
console.trace() // 関数呼び出し情報表示

// 実行時間計測
console.profile()
console.profileEnd()
```

---
# Canvas / SVG

## Canvas
### プロパティ
- globalAlpha 透明度
- globalCompositeOperation 合成方法
- font テキストフォント

### メソッド
- save() 　現在の描画状態を保存する（描くわけではない。複数ストック可能）
- restore() 保存した状態に戻す（新しいものから利用）
- scale()　拡大縮小
- rotate()　回転
- translate() 移動（X,Y）
- setTransform()　変換マトリックスで変形（A, B, C, D, E, F）
- clearRect(x, y, w, h) 四角形の形にクリアする
- fillRect(x, y, h, w) 塗りつぶしの四角形
- strokeRect(x, y, h, w) 輪郭の四角形
- beginPath() これまでのパスをリセット
- stroke() 現在の線スタイルでサブパスを輪郭表示
- clip() パスで切り抜く
- fillText(txt, x, y) 塗りつぶしテキスト
- strokeText(txt, x, y)　輪郭テキスト
- measureText()
- drawImage() イメージを描画（videoも）
- createImageData() ImageDataオブジェクトを生成
- moveTo(x, y) サブパス開始点
- lineTo(x, y) 直前の座標から指定点に向けて直線を引く
- quadraticCurveTo() ２次ベジェ曲線
- begierCurveTo() ３次ベジェ曲線
- arcTo(x,y) 直前の座標から円弧を引く
- rect(x, y, h, w) 四角形
- arc(x, y, r, start, end, 反時計回り?) 円弧を作成

### requestAnimationFrame()
Webブラウザの描画タイミングに合わせて、再描画が行われる前に指定された関数が実行される
Webブラウザがアクティブ出ない場合は、更新頻度が抑制される
コールバックにはマイクロ秒スケールのタイムスタンプが引数として渡される

```js

function animate(time) {
  document.getElementById(“animated”).style.left = (time - animationStartTime) % 2000 /4 + “px”
  requestId = window.requestAnimationFrame(animate)
}

function start() {
  animationStartTime = window.performance.now();
  requestId = window.requestAnimationFrame(animate);
}

function stop() {
  if (requestId) window.cancelAnimationFrame(requestId);
  requestId = 0;
}
```

## SVG
Scalable Vector Graphics

```html
<svg xmlns="http://www.w3.org/2000/svg" version="1.1">
  <circle cx=100 cy=100 r=30 stroke=black stroke-width=3 fill=blue> 
  <text x=0 y=15 fill=blue>This is SVG</text>
</svg>
```

- elipse 楕円
- line 線
- path 任意のパス
- polygon ポリゴン
- polyline 複数の線分の定義で構成された形状を定義
- rect 四角形


## メデイア要素 (audio/video)
### プロパティ
- readyState メデイア要素の準備状態
 - 0: HAVE_NOTHING　利用不可な状態
 - 1: HAVE_METADATA　リソースに関する十分な情報あり
 - 2: HAVE_CURRENT_DATA　再生情報もあり。早送りは☓
 - 3: HAVE_FUTURE_DATA　早送り情報もあり。
 - 4: HAVE_ENOUGH_DATA　３＋早送りしても受信待ちにならない＋追加受信なし
- networkState ネットワーク状態
 - 0: NETWORK_EMPTY　すべての属性が初期状態
 - 1: NETWORK_IDLE　一時停止中
 - 2: NETWORK_LOADING　ユーザエージェントはデータをダウンロード中
 - 3: NETWORK_NO_SOURCE　利用リソースが見つからない
- error 
 - 1: MEDIA_ERR_ABORTED　ユーザからのリクエストで、ユーザエージェントによって中止された
 - 2: MEDIA_ERR_NETWORK　ネットワークエラー
 - 3: MEDIA_ERR_DECODE　デコード中にエラー
 - 4: MEDIA_ERR_SRC_NOT_SUPPORTED　メディアリソースが不適切
- paused 再生中断中はtrue
- ended  再生完了時はtrue
- duration 再生時間
- currentTime 現在の再生時間

### メソッド
- load()　該当要素をリセットし、新しいリソースを選択してロードする
- play()　paused属性をfalseに設定し、ロード・再生開始
- pause()　paused属性をtrueに設定し、再生を中断する

### イベント
- onplay　再生開始
- onplaying　中断した再生がサイド再生可能になった時
- ontimeupdate　再生位置が変更された時
- onpause　
- onwaiting
- onstalled　メタデータをフェッチしようとしているが、データを受信できていない
- onended　再生完了時
- onerror
- onabort

### videoとcanvasの連携
```html

<video id=video width=400 height=300 autoplay>
  <source src="sample.mp4">
</video>
<button it=btn>画像生成</button>
<canvas id=canvas width=400px height=300px></canvas>

<script>
var video = document.getElementById('video');
var canvas = document.getElementById('canvas');
var buton = document.getElementById('btn');

button.addEventListener("click", function() {
  canvas.getContext('2d').drawImage(video, 0, 0, 400, 300);
});
</script>
```

---
# Communication / Security
[slide 13]
## Messaging
以下処理で利用する
- クロスドキュメントメッセージング：異なるオリジンと安全に通信する仕組み。メインページとiframe間のドキュメントメッセージングなど
- チャネルメッセージング：チャネルを介したデータやり取り
- サーバプッシュイベント：サーバからのプッシュ通信
- WebSocket：リモートホストとの双方向通信

### WebSocket
```javascript
// URLを指定して、セッションを確立する
var websocket = new WebSocket("ws://www.testsv1.com:3000");

websocket.onopen = function(){
 // 接続完了時の処理
}

// データ送信
// 文字列、Blob, ArrayBuffer, ArrayBufferView
// 戻り値：true/falset 
websocket.send(data)

// データ受信
websocket.onmessage = function(e) {
  alert(e.data)
}

// セッション切断
websocket.close()

// 切断時のイベント
websocket.onclose = function(e) {
  alert(e.data)
}
```

### ServerSentEvents
クライアントがサーバからリアルタイムにメッセージを受信する仕組み
イベントストリームと呼ばれる、サーバがプッシュする文字列を受信する（UTF-8, text/event-stream)

```
data: seman
id: name //idは1つのイベントストリームの最後に付与
// 空行
data: Osaka
id: address
```

#### 利用方法
```javascript
var es = new EventSource("http://www.testsv1.com/event.cgi")

es.open = function(e) {
  // 接続完了時
}

// イベントストリーム受診時
es.onmessage = function(e) {
  alert(e.data)
}
```

#### Transfer-Encoding: Chunked
メッセージボディをチャンク（Chunk）に分割し、チャンクごとのサイズと共に送信すること

#### readyStateプロパティ
- CONNECTING　コネクション未確立or再接続中
- OPEN　確立済み
- CLOSED　切断済みor失敗

#### イベント
- onopen
- onmessage
- onerror

### XMLHTTPRequest
スクリプトからHTTPサーバと通信を可能。Ajaxに利用する。

#### readyStateプロパティ
- UNSENT　XMLHTTPRequestオブジェクトが正常に生成された
- OPENED　open()メソッドが成功
- HEADERS_RECEIVED　ヘッダ受信
- LOADING　レスポンスボディを受信
- DONE　データ転送完了

#### メソッド
リクエスト

- open()　メソッド、URL、非同期フラグ、ユーザ名、パスワードを設定
- setRequestHeader()　リクエストヘッダを追加
- send()　リクエスト送信
- abort()　通信を中止

レスポンス

- getResponseHeader()　Cookie以外のヘッダ内で引数に指定された名前を持つヘッダの値を返す
- getAllResponseHeaders()　Cookie寒冷ん以外のヘッダを返却
- overrideMimeType()　Content-Typeヘッダを上書き


### イベント
- onloadstart　リクエスト開始
- onprogress　データ送受信中
- onabort　リクエスト中止
- onerror　エラー
- onload　正常に完了
- ontimeout　タイムアウト
- onloadend　正常・異常問わず、完了
- onreadystatechange　コネクション状態に変化が生じたとき


#### データ受信処理サンプル

```
function processData(data) {
  // 何かしらの処理
}

function handler() {
if(this.readyState == this.Done) {
  if((this.status == 200 && this.responseXML != null && this.responseXML.getElementById('test').textContext){
    processData(this.responseXML.getElementById('test').textContent);
    return;
  }
  processData(null);
}
}
```

## Security
### クロスオリジン制約
そのHTMLファイルが保存されているオリジンとしかデータのやり取りが行えない成約
XSS（Cross Site Scripting）を防ぐ
`XMLHttpRequest`や`Canvas`など
クロスオリジン制約の回避策として、CORSやMessaging、JSONPがある。





---
# Others
## Geolocation API
`navigator`オブジェクトから取得可能
### メソッド
- getCurrentPosition()　位置情報の一度取得
 - `navigator.geolocation.getCurrentPosition()`
 - コールバック関数（PositionCallback, PositionErrorCallback）を指定可能
- watchPosition()　位置情報の定期監視開始
 - コールバック関数（PositionCallback, PositionErrorCallback）を指定可能
- clearWatch()　watchPosition()をクリア

### Positionプロパティ
- timestamp
- coords
 - latitude　緯度
 - longitude　経度
 - altitude　高度
 - accuracy　緯度経度の制度
 - altitudeAccuracy　高度の精度
 - heading　方角
 - speed　速度


## DeviceOrientation
加速度センサやコンパス情報をリアルタイム取得するAPI

### イベント
- DeviceOrientationEvent　デバイスの方向変化を検出時
 - absolute　姿勢情報が取得可能かどうか
 - alpha　z軸を中心としたデバイスの動き
 - beta　x軸を中心としたデバイスの動き
 - gamma　y軸を中心としたデバイスの動き
- DeviceMotionEvent　加速度発生時
 - acceleration　DeviceAccelerationオブジェクト（加速度）
 - rotationRate　DeviceRotaionRateオブジェクト（回転量）

## Web Workers
バックグラウンドスクリプトを生成するためのAPI

```js

var worker = new Worker('example.js')
```

### メソッド
- terminate()　終了
- postMessage()　メッセージ送信

### イベント
- onerror
- onmessage

## High Resolution Time
ミリ秒以下の分解能を持つ時刻を扱うためのAPI

## アプリケーションキャッシュ
- status
 - UNCACHED
 - IDLE
 - CHECKING　確認中
 - DOWNLOADING　ダウンロード中
 - UPDATEREADY　アイドル中で更新待ち
 - OBSOLETE　キャッシュ廃止
- update()　キャッシュ更新
- abort() 　ダウンロードを中断
- swapCache()　新しい情報がある場合はアプリケーションキャッシュを更新

### イベント
- onchecking
- onerror
- onnoupdate　更新するキャッシュがない
- ondownloading
- onprogress　キャッシュ処理中
- onupdateready　キャッシュ適用準備完了
- oncached　キャッシュ済み
- onobsolete　キャッシュ廃止