0
2

More than 3 years have passed since last update.

[Javascript] Javascript Pattern要約 - DOMとブラウザパターン

Posted at

DOMアクセス

DOMアクセス

・DOMアクセスは最小化する。
・ループ内でのDOMアクセスは避ける。

// アンチパターン
for (var i = 0; i < 100; i += 1) {
  document.getElementById("result").innerHTML += i + ", ";
}

// 変数を利用した改善
var i, content = "";
for (var i = 0; i < 100; i += 1) {
  content += i + ", ";
}
document.getElementById("result").innerHTML += content;

・DOM参照を変数に割り当てて使用する。

// アンチパターン
var padding = document.getElementById("result").style.padding,
    margin = document.getElementById("result").style.margin;

// 改善案
var style = document.getElementById("result").style.
    padding = style.padding;
    margin = style.margin;

document.querySelector("ul .selected");
// クエリーセレクターは他のDOMメソッド選択方式より速い。

・頻繁にアクセスするエレメントにid属性を追加するのも性能向上に役立つ。 なぜなら、document.getElementById("id")がノードを探す最も早い方法。

DOM操作

DOM操作

・DOMアップデートは最小化した方が良い。
・アップデート時に画面をrepaintしてエレメントをreflowするのに費用がたくさんかかるため。
・サブツリーを追加する時は、サブツリーの構成要素をすべて生成した後、最後に一度だけ追加してくれる。

// アンチパターン
var p, t;
p = document.createElement("p");
t = document.createTextNode("first paragraph");
p.appendChild(t);
document.body.appendChild(p);

p = document.createElement("p");
t = document.createTextNode("second paragraph");
p.appendChild(t);
document.body.appendChild(p);

// 改善案
var p, t, frag;
frag = document.createDocumentFragment();

p = document.createElement("p");
t = document.createTextNode("first paragraph");
p.appendChild(t);
frag.appendChild(p);

p = document.createElement("p");
t = document.createTextNode("second paragraph");
p.appendChild(t);
frag.appendChild(p);

document.body.appendChild(frag);

・存在するツリーを変更する場合には、サブツリーのルートを複製して変更した後、元のノードと変える。

var oldnode = document.getElementById("result"),
    clone = oldnode.cloneNode(true);

oldnode.parentNode.replaceChild(clone, oldnode);

イベント

イベントリスナーは以下のように実装できる。

var b = document.getElementById("clickme");
if (document.addEventListener) {
  b.addEventListener("click", myHandler, false);
} else if (document.attachEvent) {
  b.attachEvent("onclick". myHandler);
} else {
  b.onclick = myHandler;
}

function myHandler(e) {
    var src, parts;

    e = e || window.event;
    src = e.target || e.srcElement;

    if (src.nodeName.toLowerCase() !== "button") {
      return ;
    }

    parts = src.innerHTML.split(": ");
    parts[1] = parseInt(parts[1], 10) + 1;
    src.innerHTML = parts[0] + ": " + parts[1];

    if (typeof e.stopPropagation === "function") {
      e.stopPropagation();
    }
    if (typeof e.cancelBubble !== "undefined") {
      e.cancelBubble = true;
    }

    if (typeof e.preventDefault() === "funtion") {
      e.preventDefault();
    }
    if (typeof e.preventDefault() !== "undefined") {
      e.returnValue = false;
    }

}

setTimeOut()WebWorkerを利用してスレッドのような機能を実現することができる。

XMLHttpRequest

XMLHttpRequest

・JavaScript から HTTP リクエストを生成する特別なオブジェクト
・生成過程は以下の通りである。

var xhr = new XMLHttpRequest();

xhr.onreadystatechange = handleResponse;

xhr.open("GET", "page.html", true); 
xhr.send();

JSONP

JSONP

・JSON with padding
・ブラウザの同一ドメインポリシーの制約を受けない。
・JSONPリクエストURL形態

http://example.org/getdata.php?callback=myHandler

・上でgetdata.phpがウェブページかスクリプトになることができる。
・getdata.php ファイルが受信されると、myHandler({"hello":"world"}) のようなコールバック関数が実行される。

ウェブページロード戦略

ウェブページロード戦略

・scriptタグに入るエレメントを見てみよう。
・type="textjavascript":HTML5では必須属性ではなく、マークアップ有効性検査のための場合でなければ使用しない。
・async (defer):非同期スクリプトのロードで、スクリプトを受け取る間、他のダウンロードを妨げない。

0
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
2