<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Advent Calendar 2013 &#8211; Mach3.laBlog</title>
	<atom:link href="https://blog.mach3.jp/tag/advent-calendar-2013/feed" rel="self" type="application/rss+xml" />
	<link>https://blog.mach3.jp</link>
	<description></description>
	<lastBuildDate>Wed, 25 Dec 2013 01:49:14 +0000</lastBuildDate>
	<language>ja</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
	<generator>https://wordpress.org/?v=6.9</generator>
	<item>
		<title>&#034;zipcode&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/25/jaac2013-z-zipcode.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Wed, 25 Dec 2013 01:49:14 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[zipcode]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3796</guid>

					<description><![CDATA[&#8220;Z&#8221; は zipcode の &#8220;Z&#8221;。 郵便番号から住所を自動入力する ユーザが入力する手間を省いたり入力間違いを避ける為に、住所の一部を自動入力する補助UIを見たことが [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;Z&#8221; は zipcode の &#8220;Z&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh3.googleusercontent.com/-h245sNZb3Fo/UqR4nI5Ck5I/AAAAAAAACYg/wpovIbDxLBs/s400/ac2013-z.png" alt="Z"/></figure>



<p></p>



<span id="more-3796"></span>



<h2 class="wp-block-heading">郵便番号から住所を自動入力する</h2>



<p>ユーザが入力する手間を省いたり入力間違いを避ける為に、住所の一部を自動入力する補助UIを見たことがあると思います。 例えばこんなHTMLで、「郵便番号から住所を検索する」ボタンをクリックすると自動的に都道府県と住所が入力される仕組みです。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">ul</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">li</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">label</span> <span class="hljs-attr">for</span>=<span class="hljs-string">"zipcode"</span>&gt;</span>郵便番号:<span class="hljs-tag">&lt;/<span class="hljs-name">label</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">input</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"text"</span> <span class="hljs-attr">name</span>=<span class="hljs-string">"zipcode"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"zipcode"</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">input</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"button"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"button-getaddress"</span> <span class="hljs-attr">value</span>=<span class="hljs-string">"郵便番号から住所を検索する"</span>&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">li</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">li</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">label</span> <span class="hljs-attr">for</span>=<span class="hljs-string">"state"</span>&gt;</span>都道府県:<span class="hljs-tag">&lt;/<span class="hljs-name">label</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">input</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"text"</span> <span class="hljs-attr">name</span>=<span class="hljs-string">"state"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"state"</span>&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">li</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">li</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">label</span> <span class="hljs-attr">for</span>=<span class="hljs-string">"address"</span>&gt;</span>住所:<span class="hljs-tag">&lt;/<span class="hljs-name">label</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">input</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"text"</span> <span class="hljs-attr">name</span>=<span class="hljs-string">"address"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"address"</span>&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">li</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">ul</span>&gt;</span>
</code></span></pre>


<p>お問い合わせフォームやユーザー登録などで良く見られますね。 郵便番号からの住所検索は各所でAPIやライブラリが提供されておりますが、 ここでご紹介するのは次の２つのリソースです。</p>



<ol class="wp-block-list">
<li>zipaddress.net <a href="http://zipaddress.net/">http://zipaddress.net/</a></li>



<li>ajaxzip3 <a href="https://code.google.com/p/ajaxzip3/">https://code.google.com/p/ajaxzip3/</a></li>
</ol>



<p>共に商用利用可能で、リンクの設置などの制限は特にない様です。</p>



<h2 class="wp-block-heading">zipaddress.net</h2>



<p><a href="http://zipaddress.net">zipaddress.net</a> は、<a href="http://twitter.com/sugimoto1981">@sugimoto1981</a> 氏が公開している郵便番号検索APIです。</p>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p><strong>郵便番号-住所検索API</strong><br />
  <a href="http://zipaddress.net">http://zipaddress.net</a><br />
  郵便番号データをパラメータに含めてリクエストを送信することで、都道府県、市区町村のデータをJSONフォーマットで返却するシンプルなサービスです。</p>
</blockquote>



<p>APIの利用方法はシンプルで、郵便番号を7桁の数字で送ると JSON で住所の内容を返してくれます。 JSONPにも対応しているのでクライアントサイドでの利用も簡単です。 というよりむしろ、クライアントサイドでの利用を前提としているサービスなのでしょう。 簡単に組み込みが出来るSDKも公開されています。</p>



<p>試しに jQuery で上に挙げたHTMLに組み込んでみます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">$(<span class="hljs-string">"#button-getaddress"</span>).on(<span class="hljs-string">"click"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-keyword">var</span> code;
    <span class="hljs-keyword">if</span>(! (code = $(<span class="hljs-string">"#zipcode"</span>).val())){
        <span class="hljs-keyword">return</span>;
    }
    $.ajax({
        <span class="hljs-attr">url</span>: <span class="hljs-string">"http://api.zipaddress.net"</span>,
        <span class="hljs-attr">dataType</span>: <span class="hljs-string">"jsonp"</span>,
        <span class="hljs-attr">data</span>: {
            <span class="hljs-attr">zipcode</span>: code
        }
    })
    .then(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
        <span class="hljs-keyword">if</span>(! data.pref){
            alert(<span class="hljs-string">"失敗しました。"</span>);
        } <span class="hljs-keyword">else</span> {
            $(<span class="hljs-string">"#state"</span>).val(data.pref);
            $(<span class="hljs-string">"#address"</span>).val(data.address);
        }
    });
});
</code></span></pre>


<p>エンドポイントは <strong>&#8220;http://api.zipaddress.net&#8221;</strong> で、SSLにも対応しています。 返ってくるデータには以下の住所情報が含まれていますので、これらをテキストインプットに流し込めば完了です。</p>



<ul class="wp-block-list">
<li>pref: 都道府県</li>



<li>address: 市区町村以降の住所</li>



<li>fullAddress: pref + address の結合文字列</li>
</ul>



<p>また、提供されているSDKを使って情報を取得する事も出来ます。 SDKにある <strong>ZA.request</strong> メソッドを使用する事で、JSONP周りの処理をかなり簡略化してくれます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">ZA.request(code, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data, error</span>)</span>{
    <span class="hljs-comment">/* data から住所を取得する */</span>
});
</code></span></pre>


<p>ZA.request には郵便番号と、受け取る為のコールバックを渡して使用します。 この他にも、予め各項目を入力する要素を渡しておいてハンドリングする <strong>ZA.regiester</strong> もあります。 詳しくは SDK のリファレンスをご参照ください。</p>



<h2 class="wp-block-heading">ajaxzip3</h2>



<p><strong>ajaxzip3</strong> は、<a href="http://www.kawa.net/works/ajax/ajaxzip2/ajaxzip2.html">ajaxzip2</a> をJSONP対応にしてリリースされたライブラリです。</p>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p><strong>ajaxzip3</strong><br />
  <a href="https://code.google.com/p/ajaxzip3/">https://code.google.com/p/ajaxzip3/</a><br />
  世界一、簡単に設置できる郵便番号検索を目指して！</p>
</blockquote>



<p>他の郵便番号検索APIとは一線を画しており、 リポジトリに検索用のデータを静的なJavaScriptファイルとして設置しておき、 JSONPとしてアクセスする事で住所データを取得する仕組みです。 データは郵便番号の上3桁毎に別ファイルにされて、 <a href="http://ajaxzip3.googlecode.com/svn/trunk/ajaxzip3/zipdata">/zipdata ディレクトリ</a> に格納されています。</p>



<p>上述の HTML に組み込んでみましょう。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">script</span> <span class="hljs-attr">src</span>=<span class="hljs-string">"http://ajaxzip3.googlecode.com/svn/trunk/ajaxzip3/ajaxzip3.js"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="javascript">
    $(<span class="hljs-string">"#button-getaddress"</span>).on(<span class="hljs-string">"click"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
        <span class="hljs-keyword">if</span>(! $(<span class="hljs-string">"#zipcode"</span>).val()){
            <span class="hljs-keyword">return</span>;
        }
        AjaxZip3.zip2addr(<span class="hljs-string">"zipcode"</span>, <span class="hljs-string">""</span>, <span class="hljs-string">"state"</span>, <span class="hljs-string">"address"</span>);
    });
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p>データの展開は <strong>AjaxZip3.zip2addr</strong> メソッドで行います。 引数には郵便番号等の文字列ではなく、input 要素の <strong>name</strong> 属性を渡す事に注意してください。 （丁度、先に挙げた zipaddress.net の ZA.register がこれに倣ったような実装になっている様です。）</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">AjaxZip3.zip2addr(
    <span class="hljs-string">"zipcode"</span>, <span class="hljs-comment">// 郵便番号上3桁を入力した input 要素,</span>
    <span class="hljs-string">""</span>, <span class="hljs-comment">// 郵便番号下4桁を入力した input 要素</span>
    <span class="hljs-string">"state"</span>, <span class="hljs-comment">// 都道府県を入力する input 要素</span>
    <span class="hljs-string">"address"</span> <span class="hljs-comment">// 市区町村以下を入力する input 要素</span>
);
</code></span></pre>


<p>静的ファイルで取得する都合上、jQuery等の動的なJSONPは使用できません。 コールバック関数は <strong>zipdata()</strong> で固定されていますので、 処理を弄りたい場合はこれを上書きする事になります。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-built_in">window</span>.zipdata = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{ ... };
</code></span></pre>


<p>制作者の手間を極力省く設計になっている反面、融通を効かせる為には一手間必要です。</p>



<h2 class="wp-block-heading">その他のヒント</h2>



<p>上であげたいずれのリソースも、利用するにあたって正しい郵便番号（7桁の半角数字）が渡される事が前提となります。 広い層に使われるUIなので、間違った入力に柔軟に対応出来るように配慮してあげたいと思います。 例えば、番号入力が完了した時に誤った入力を自動修正する処理を挟む事で、 フォームの使い勝手が向上するのではないでしょうか。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">$(<span class="hljs-string">"#zipcode"</span>).on(<span class="hljs-string">"blur"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-keyword">var</span> map = {
        <span class="hljs-attr">zen</span>: <span class="hljs-string">"０１２３４５６７８９"</span>,
        <span class="hljs-attr">han</span>: <span class="hljs-string">"0123456789"</span>
    };
    <span class="hljs-keyword">this</span>.value = <span class="hljs-keyword">this</span>.value.replace(<span class="hljs-regexp">/&#91;^\d]/g</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">s</span>)</span>{
        <span class="hljs-keyword">var</span> index = map.zen.indexOf(s);
        <span class="hljs-keyword">if</span>(index &gt;= <span class="hljs-number">0</span>){
            <span class="hljs-keyword">return</span> map.han.substr(index, <span class="hljs-number">1</span>);
        }
        <span class="hljs-keyword">return</span> <span class="hljs-string">""</span>;
    });
});
</code></span></pre>


<p>上のコードは、カーソルが離れた時に全角数字を半角数字に変換したのち、余計な文字を削除する簡単な例です。 誤ってハイフン等が入力されてしまった場合でも、正しい形式でAPIにリクエストする事ができます。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="http://zipaddress.net/">郵便番号-住所検索API</a></li>



<li><a href="https://code.google.com/p/ajaxzip3/">ajaxzip3 &#8211; 郵便番号検索API, JSONP対応 &#8211; Google Project Hosting</a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;YQL&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/24/jaac2013-y-yql.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Tue, 24 Dec 2013 01:33:27 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Yahoo]]></category>
		<category><![CDATA[YQL]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3791</guid>

					<description><![CDATA[&#8220;Y&#8221; は YQL の &#8220;Y&#8221;。 YQL (Yahoo Query Language) YQL（Yahoo Query Language） は Yahoo が提供する開発者 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;Y&#8221; は YQL の &#8220;Y&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh4.googleusercontent.com/-wXGTXbO5yNs/UqR4nPMXEdI/AAAAAAAACYg/yIffyPI1E1k/s400/ac2013-y.png" alt="Y"/></figure>



<p></p>



<span id="more-3791"></span>



<h2 class="wp-block-heading">YQL (Yahoo Query Language)</h2>



<p><a href="http://developer.yahoo.com/yql/">YQL（Yahoo Query Language）</a> は Yahoo が提供する開発者向けのAPIで、 SQLライクなクエリを送ると様々な情報を取得する事が出来るサービスです。 受け取るデータは XML か JSON かを選択可能で、 JSONPにも対応しているのでクライアントJavaScriptからも簡単に利用できます。</p>



<p>例えば場所情報や地域の天気情報を取得したり、 Flickr から写真を検索したり、Webページのフィードを取得したりする事等が出来ます。</p>



<h3 class="wp-block-heading">利用方法</h3>



<p>パブリックAPIのエンドポイントは <strong>http://query.yahooapis.com/v1/public/yql</strong> です。 パラメータは、形式を指定する <strong>format</strong> 、クエリを送る <strong>q</strong>、JSONPのコールバック用の <strong>callback</strong> を渡す事ができます。 次のようなリクエストを送る事になりますね。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">http:<span class="hljs-comment">//query.yahooapis.com/v1/public/yql?format=json&amp;q=&#91;YQLクエリ]&amp;callback=&#91;コールバック関数]</span>
</code></span></pre>


<p>YQL の書き方については、公式の Yahoo Developper Network でテスト出来るコンソールを用意しているので、 どんな書式でどんな情報が得られるかを試してみると良いですね。</p>



<ul class="wp-block-list">
<li><a href="http://developer.yahoo.com/yql/console/">YQL Console: show tables</a></li>
</ul>



<p>テーブルによっては別途アプリケーションIDが必要です。 また、Flickr 関連のテーブルは flickr で登録したアプリケーションIDが必要な様です。</p>



<h3 class="wp-block-heading">位置情報から天気情報を取得してみる</h3>



<p>天気情報は <strong>weather.forecast</strong> から取得できますが、位置情報の指定に <strong>woeid</strong> という者が必要になります。 <a href="http://developer.yahoo.com/geo/geoplanet/guide/concepts.html">woeid</a> というのは &#8220;Where On Earth Identifier&#8221; の事で、 全世界の地域ごとに ID を振って管理をしています。</p>



<p>woeid は、<strong>geo.places</strong> テーブルから都市名で引く事が出来ます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">SELECT woeid FROM geo.places WHERE text = <span class="hljs-string">'神奈川県横浜市'</span>
</code></span></pre>


<p>そこで得られた woeid を使って、天気情報を引きます。ちなみに神奈川県横浜市の woeid は 1118550 です。</p>


<pre class="wp-block-code"><span><code class="hljs">SELECT * FROM weather.forecast WHERE woeid = 1118550
</code></span></pre>


<p>一通りの処理を jQuery で書いてみましょう。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> rest = <span class="hljs-string">"http://query.yahooapis.com/v1/public/yql"</span>;

$.ajax({
    <span class="hljs-attr">dataType</span>: <span class="hljs-string">"jsonp"</span>,
    <span class="hljs-attr">url</span>: rest,
    <span class="hljs-attr">data</span>: {
        <span class="hljs-attr">format</span>: <span class="hljs-string">"json"</span>,
        <span class="hljs-attr">q</span>: <span class="hljs-string">"SELECT woeid FROM geo.places WHERE text = '神奈川県横浜市'"</span>
    }
})
.then(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
    <span class="hljs-keyword">var</span> woeid = data.query.results.place.woeid;
    <span class="hljs-keyword">return</span> $.ajax({
        <span class="hljs-attr">dataType</span>: <span class="hljs-string">"jsonp"</span>,
        <span class="hljs-attr">url</span>: rest,
        <span class="hljs-attr">data</span>: {
            <span class="hljs-attr">format</span>: <span class="hljs-string">"json"</span>,
            <span class="hljs-attr">q</span>: <span class="hljs-string">"SELECT * FROM weather.forecast WHERE woeid = "</span> + woeid
        }
    });
})
.then(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
    $(<span class="hljs-string">"#widget-weather"</span>).html(data.query.results.channel.item.description);
});
</code></span></pre>


<p>結果のデータを辿って得られる <strong>description</strong> には出力用のHTMLが格納されているので、 それをそのままコンテナに表示しています。 ただ、内容は全て英語で温度の単位も華氏なので、実際に使う時は翻訳や換算をしてあげないといけません。</p>



<h3 class="wp-block-heading">RSSフィードを利用する</h3>



<p>YQL の <strong>feed</strong> テーブルでは、Web上にあるRSSフィードをJSONに変換して返す事が出来ます。 試しにJSONPで Mach3.laBlog のフィードを取得してみようと思います。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> query = <span class="hljs-string">"SELECT * FROM feed WHERE url = 'https://blog.mach3.jp/feed'"</span>;
<span class="hljs-keyword">var</span> rest = <span class="hljs-string">"http://query.yahooapis.com/v1/public/yql"</span>;

$.ajax({
    <span class="hljs-attr">dataType</span>: <span class="hljs-string">"jsonp"</span>,
    <span class="hljs-attr">url</span>: rest,
    <span class="hljs-attr">data</span>: { <span class="hljs-attr">format</span>: <span class="hljs-string">"json"</span>, <span class="hljs-attr">q</span>: query }
})
.then(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
    <span class="hljs-built_in">console</span>.log(data); <span class="hljs-comment">// フィードのデータ出力</span>
});
</code></span></pre>


<p>自サイトのフィードを読む分には特に必要ないですが、クロスドメインでRSSを引っ張りたい時や、 サービスのAPIがXMLしか対応していない場合などに使えます。 勿論、利用規約はそのソースを提供しているコンテンツプロバイダの物に従う事になるので、 それに則って正しく利用しましょう。</p>



<h2 class="wp-block-heading">爆速YQL</h2>



<p>Yahoo! Japan デベロッパーネットワークのブログで <strong>「爆速YQL」</strong> なる物が紹介されていました。 これは何かというと、YQLの結果取得と出力をブログパーツのような感覚で出来てしまうコンポーネントです。</p>



<ul class="wp-block-list">
<li><a href="http://techblog.yahoo.co.jp/programming/bakusoku-yql/">XMLのWebAPIを爆速で使いこなせるフレームワーク &#8211; Yahoo! JAPAN Tech Blog</a></li>
</ul>



<p>上で挙げたフィードの取得を試してみましょう。なるほどこれは爆速です。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">script</span> <span class="hljs-attr">src</span>=<span class="hljs-string">"http://i.yimg.jp/images/yjdn/js/bakusoku-yql-v1-min.js"</span>
    <span class="hljs-attr">data-yql</span>=<span class="hljs-string">"SELECT * FROM feed WHERE url='https://blog.mach3.jp/feed'"</span>&gt;</span><span class="handlebars"><span class="xml">
    <span class="hljs-tag">&lt;<span class="hljs-name">ul</span>&gt;</span>
    </span><span class="hljs-template-tag">{{#<span class="hljs-name">query</span>.results.item}}</span><span class="xml">
        <span class="hljs-tag">&lt;<span class="hljs-name">li</span>&gt;</span><span class="hljs-tag">&lt;<span class="hljs-name">a</span> <span class="hljs-attr">href</span>=<span class="hljs-string">"</span></span></span><span class="hljs-template-variable">{{link}}</span><span class="xml"><span class="hljs-tag"><span class="hljs-string">"</span>&gt;</span></span><span class="hljs-template-variable">{{title}}</span><span class="xml"><span class="hljs-tag">&lt;/<span class="hljs-name">a</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">li</span>&gt;</span>
    </span><span class="hljs-template-tag">{{/<span class="hljs-name">query</span>.results.item}}</span><span class="xml">
    <span class="hljs-tag">&lt;/<span class="hljs-name">ul</span>&gt;</span>
</span></span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p>script 要素の <strong>data-yql</strong> 属性に YQL のクエリを入力すると、 要素内のビューを使ってコンテンツを表示します。 ビュー部分には <a href="http://mustache.github.io/">Mustache</a> を採用しており、ループや条件分岐等もする事ができます。</p>



<p>こういう形でのウィジェットの公開も良いですね。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="http://developer.yahoo.com/yql/">Yahoo! Query Language &#8211; YDN</a></li>



<li><a href="http://developer.yahoo.com/yql/console/">YQL Console: show tables</a></li>



<li><a href="http://techblog.yahoo.co.jp/programming/bakusoku-yql/">XMLのWebAPIを爆速で使いこなせるフレームワーク &#8211; Yahoo! JAPAN Tech Blog</a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;extend&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/23/jaac2013-x-extend.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Mon, 23 Dec 2013 01:33:25 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[extend]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jQuery]]></category>
		<category><![CDATA[underscore.js]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3785</guid>

					<description><![CDATA[&#8220;X&#8221; は extend の &#8220;X&#8221;。 extend JavaScript で extend というと、幾つかのオブジェクトをマージして拡張する処理の事として知られます。  [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;X&#8221; は extend の &#8220;X&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh4.googleusercontent.com/-l3QAKVYOUrk/UqR4nATH8CI/AAAAAAAACYg/QzWinpmaz-4/s400/ac2013-x.png" alt="X"/></figure>



<p></p>



<span id="more-3785"></span>



<h2 class="wp-block-heading">extend</h2>



<p>JavaScript で <strong>extend</strong> というと、幾つかのオブジェクトをマージして拡張する処理の事として知られます。<br />
かなり頻繁に使われるこの機能は、多くのJavaScriptフレームワーク・ライブラリに備えられています。</p>



<p>例えば jQuery の場合は <strong>$.extend</strong> として実装されています。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> dest = {<span class="hljs-attr">a</span>: <span class="hljs-number">1</span>, <span class="hljs-attr">b</span>: <span class="hljs-number">2</span>};
<span class="hljs-keyword">var</span> src = {<span class="hljs-attr">a</span>: <span class="hljs-number">2</span>, <span class="hljs-attr">c</span>: <span class="hljs-number">3</span>};

$.extend(dest, src);
<span class="hljs-built_in">console</span>.log(dest); <span class="hljs-comment">// {a: 2, b: 2, c: 3}</span>
</code></span></pre>


<p>$.extend は複数のオブジェクトを引数に渡し、先頭に渡したオブジェクトの拡張をします。<br />
その他のフレームワークにおいても基本的な使い方は共通で、<br />
underscore.js の <strong>_.extend</strong> もほぼ同様の記述で利用できます。</p>



<h3 class="wp-block-heading">いくつかのパターン</h3>



<p>extend 機能を実装する上で、いくつかのパターンが考えられます。</p>



<ul class="wp-block-list">
<li>値がオブジェクトだった場合に再帰的にコピー（ディープコピー）するか否か</li>



<li>既に同じ名前のプロパティが存在した場合に上書きするか否か</li>
</ul>



<p>これらは正解不正解なくケースによって使い分ける物だと思いますが、<br />
利用する extend 関数がどのパターンで機能を提供するのかは把握しておいた方が良いでしょう。<br />
特に、ディープコピーの有無によるミスは気づきにくいかもしれません。</p>



<p>ちなみに jQuery はディープコピーの有無をコントロールする事が出来、underscore.js はディープコピーを行いません。<br />
同名プロパティについては両者ともに後から渡された値で上書きを行います。</p>



<h3 class="wp-block-heading">ディープコピーと参照</h3>



<p>コピー元のプロパティの値がオブジェクトであった場合、<br />
それをそのままコピーしてもそれは元のオブジェクトへの参照になります。<br />
例えば次のように src のプロパティに <strong>data</strong> というオブジェクトがぶら下がっているとします。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> dest = {};
<span class="hljs-keyword">var</span> src = {
    <span class="hljs-attr">data</span>: {
        <span class="hljs-attr">a</span>: <span class="hljs-number">1</span>,
        <span class="hljs-attr">b</span>: <span class="hljs-number">2</span>
    }
};
</code></span></pre>


<p>この src を元にして dest を拡張してみます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">$.extend(dest, src);
<span class="hljs-built_in">console</span>.log(dest); <span class="hljs-comment">// {"data":{"a":1,"b":2}}</span>
</code></span></pre>


<p>問題なく拡張出来たように見えますが、<br />
ここでコピー元の src.data のプロパティを変更してみると、それが dest.data にも反映される事が分かります。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">src.data.a = <span class="hljs-number">0</span>;
<span class="hljs-built_in">console</span>.log(dest); <span class="hljs-comment">// {"data":{"a":0,"b":2}}</span>
</code></span></pre>


<p>これは dest.data が src.data に紐付いている為に引き起こる様です。<br />
この時 dest.data を src.data から切り離した新しいオブジェクトとして複製したい場合は、<strong>ディープコピー</strong> を使います。<br />
jQuery の場合は引数の先頭に <strong>true</strong> を足してあげることでディープコピーが出来ます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">$.extend(<span class="hljs-literal">true</span>, dest, src);
</code></span></pre>


<h3 class="wp-block-heading">同名プロパティの上書き</h3>



<p>あまりないケースかもしれませんが、<br />
コピー先のプロパティを活かしたい場合は引数の最後に渡して改めてコピーする事になります。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">$.extend(dest, src, {
    <span class="hljs-attr">propToProtect</span>: dest.propToProtect
});
</code></span></pre>


<h3 class="wp-block-heading">新しいオブジェクトとして生成する</h3>



<p>継承した結果を新しいオブジェクトとして取得したい場合は、<br />
空のオブジェクトを先頭に渡します。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> obj = $.extend({}, src1, src2);
</code></span></pre>


<p>src1 / src2 共にプロパティの変更はされず、空のオブジェクトに継承された結果が返り値として返ります。</p>



<h2 class="wp-block-heading">extend の習作</h2>



<p>なんとなく extend の働きを理解したところで、簡単な extend 関数を習作してみます。<br />
まずはシンプルにディープコピー無しの extend です。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> extend = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"><span class="hljs-regexp">/* dest, src1, src2 */</span></span>)</span>{
    <span class="hljs-keyword">var</span> i = <span class="hljs-number">0</span>, dest, src, name;
    dest = <span class="hljs-built_in">arguments</span>&#91;i++];
    <span class="hljs-keyword">for</span>(; i&lt;<span class="hljs-built_in">arguments</span>.length; i++){
        src = <span class="hljs-built_in">arguments</span>&#91;i];
        <span class="hljs-keyword">for</span>(name <span class="hljs-keyword">in</span> src){
            <span class="hljs-keyword">if</span>(! src.hasOwnProperty(name)){ <span class="hljs-keyword">continue</span>; }
            dest&#91;name] = src&#91;name];
        }
    }
    <span class="hljs-keyword">return</span> dest;
};
</code></span></pre>


<p>次に、ディープコピーの有効・無効をコントロール出来るようにしたタイプです。<br />
（コントロールをなくして別名関数にしてしまった方がシンプルに済むかもしれません）</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">// obj のタイプを文字列で返す</span>
<span class="hljs-keyword">var</span> type = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">obj</span>)</span>{
    <span class="hljs-keyword">var</span> m = <span class="hljs-built_in">Object</span>.prototype.toString.call(obj).match(<span class="hljs-regexp">/\&#91;object\s(\w+)\]/</span>);
    <span class="hljs-keyword">return</span> m ? m&#91;<span class="hljs-number">1</span>].toLowerCase() : <span class="hljs-literal">null</span>;
};

<span class="hljs-keyword">var</span> extend = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"> <span class="hljs-regexp">/* &#91;deep,] dest, src &#91;, src2 ...] */</span> </span>)</span>{
    <span class="hljs-keyword">var</span> i = <span class="hljs-number">0</span>, deep = <span class="hljs-literal">false</span>, dest, merge;
    <span class="hljs-keyword">if</span>(type(<span class="hljs-built_in">arguments</span>&#91;<span class="hljs-number">0</span>]) === <span class="hljs-string">"boolean"</span>){
        deep = <span class="hljs-built_in">arguments</span>&#91;i++];
    }
    dest = <span class="hljs-built_in">arguments</span>&#91;i++];
    merge = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">deep, dest, src</span>)</span>{
        <span class="hljs-keyword">var</span> name;
        <span class="hljs-keyword">for</span>(name <span class="hljs-keyword">in</span> src){
            <span class="hljs-keyword">if</span>(! src.hasOwnProperty(name)){ <span class="hljs-keyword">continue</span>; }
            <span class="hljs-keyword">if</span>(deep &amp;&amp; type(src&#91;name]) === <span class="hljs-string">"object"</span>){
                dest&#91;name] = extend(deep, dest&#91;name] || {}, src&#91;name]);
                <span class="hljs-keyword">continue</span>;
            }
            dest&#91;name] = src&#91;name];
        }
    };
    <span class="hljs-keyword">for</span>(; i&lt;<span class="hljs-built_in">arguments</span>.length; i++){
        merge(deep, dest, <span class="hljs-built_in">arguments</span>&#91;i]);
    }
    <span class="hljs-keyword">return</span> dest;
};
</code></span></pre>


<p>jQuery等がない状況でコードを書く時や、<br />
好みの動作を行う extend 関数が欲しい時には自作のスニペットを用意しておくと捗るかもしれませんね。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="http://api.jquery.com/jQuery.extend/">jQuery.extend() | jQuery API Documentation</a></li>



<li><a href="http://underscorejs.org/">Underscore.js</a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;WebSocket&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/22/jaac2013-w-websocket.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Sun, 22 Dec 2013 01:58:46 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[node.js]]></category>
		<category><![CDATA[Socket.io]]></category>
		<category><![CDATA[WebSocket]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3781</guid>

					<description><![CDATA[&#8220;W&#8221; は WebSocket の &#8220;W&#8221;。 WebSocket WebSocket は、サーバーとクライアント間の双方向の通信をスムーズに行う為の技術です。 XMLHtt [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;W&#8221; は WebSocket の &#8220;W&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh4.googleusercontent.com/-nLLyR4zNEGA/UqR4mAUDnyI/AAAAAAAACYg/LwX_sRpA7Xk/s400/ac2013-w.png" alt="W"/></figure>



<p></p>



<span id="more-3781"></span>



<h2 class="wp-block-heading">WebSocket</h2>



<p><strong>WebSocket</strong> は、サーバーとクライアント間の双方向の通信をスムーズに行う為の技術です。 XMLHttpRequest のように都度リクエストを送るのではなく、 一旦コネクションが貼られた後はそのコネクション上でメッセージを送り合ってデータのやり取りを行う為、 よりリアルタイム性が必要なアプリケーション、例えばチャットやオンラインゲーム等での活躍が期待されます。</p>



<h2 class="wp-block-heading">Socket.io</h2>



<p>WebSocket を恐ろしく簡単で使いやすい物に変えてしまうのが <strong>Socket.io</strong> です。</p>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p><a href="http://socket.io/">http://socket.io/</a><br />
  Socket.IO aims to make realtime apps possible in every browser and mobile device, blurring the differences between the different transport mechanisms. It&#8217;s care-free realtime 100% in JavaScript.</p>
</blockquote>



<p>node.js で楽にWebSocketのサーバが立ち上がるうえ、クライアントサイドでは WebSocket に非対応な環境の為に、 Flash で ActionScript3 の WebSocket API を使用してフォールバックを備えてくれています。</p>



<h3 class="wp-block-heading">WebSocket サーバの起動</h3>



<p>まず socket.io をインストールしましょう。</p>


<pre class="wp-block-code"><span><code class="hljs">$ npm install socket.io
</code></span></pre>


<p>そして起動用のスクリプトを書きます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">// server.js</span>
<span class="hljs-keyword">var</span> io = <span class="hljs-built_in">require</span>(<span class="hljs-string">'socket.io'</span>).listen(<span class="hljs-number">8080</span>);
io.sockets.on(<span class="hljs-string">"connection"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">socket</span>)</span>{
    socket.emit(<span class="hljs-string">"hello"</span>, {<span class="hljs-attr">message</span>: <span class="hljs-string">"Thanks to connect !"</span>});
});
</code></span></pre>


<p>これは接続したクライアントに &#8220;hello&#8221; メッセージを送るだけのコードです。</p>



<p><strong>listen</strong> メソッドでポートを指定してサーバを起動します。 <strong>io.sockets.on</strong> メソッドでは、新たにリクエストのあったコネクションを受け取り、 そのコールバックの中で <strong>emit</strong> コマンドでクライアント側にメッセージを送ります。</p>



<p>node コマンドで WebSocket サーバを起動します。</p>


<pre class="wp-block-code"><span><code class="hljs">$ node server.js
</code></span></pre>


<p>これでサーバが立ち上がったと思います。 デーモン化したい時には <a href="https://github.com/nodejitsu/forever">forever</a> が便利です。</p>



<h3 class="wp-block-heading">クライアント側の処理</h3>



<p>WebSocketとは別に、Webサーバが立ち上がっていると仮定しましょう。 クライアント側では <strong>socket.io-client</strong> を使って WebSocket に接続します。 <strong>socket.io-client</strong> は bower でも npm でもインストールできます。</p>


<pre class="wp-block-code"><span><code class="hljs">$ bower install socket.io-client
</code></span></pre>


<p>ここではサーバから送った &#8220;hello&#8221; メッセージを受け取ってみます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">script</span> <span class="hljs-attr">src</span>=<span class="hljs-string">"bower_components/socket.io-client/dist/socket.io.js"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="javascript">
    <span class="hljs-keyword">var</span> socket = io.connect(<span class="hljs-string">"http://example.com:8080"</span>);
    socket.on(<span class="hljs-string">"hello"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
        <span class="hljs-built_in">console</span>.log(data.message); <span class="hljs-comment">// "Thanks to connect !"</span>
    });
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p>サーバから <strong>emit</strong> で送ったメッセージは、クライアント側で <strong>on</strong> で受け取る事ができます。 逆に、サーバ側にメッセージを送る時はクライアント側で <strong>emit</strong> し、サーバ側で <strong>on</strong> で受け取ります。</p>



<h3 class="wp-block-heading">全てのソケットにメッセージを送る</h3>



<p>上のサーバスクリプトでは、引数で渡された <strong>socket</strong> オブジェクトで emit を行っていましたが、 この socket はそのクライアントのみのコネクションです。 接続している全てのユーザにメッセージを送りたい場合は、socket にぶら下がっている broadcast を使用します。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">socket.emit(<span class="hljs-string">"message"</span>, ... ); <span class="hljs-comment">// 自分にメッセージを送る</span>
socket.broadcast.emit(<span class="hljs-string">"message"</span>, ...); <span class="hljs-comment">// 自分以外にメッセージを送る</span>
</code></span></pre>


<p>broadcast は自分以外のコネクションを指します。</p>



<h2 class="wp-block-heading">極めてシンプルなチャットの習作</h2>



<p>Socket.io を使って極めてシンプルなチャットプログラムを作ってみます。 上で挙げた機能のみを使用して、その場限りのチャットをする事が出来ます。 ルームや認証などは一切省いています。</p>



<p>まずHTMLは、ニックネームとメッセージを入力するインプットと、メッセージログを出力する #log で構成されます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-comment">&lt;!-- HTML --&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">form</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"form-message"</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">label</span>&gt;</span>ニックネーム: <span class="hljs-tag">&lt;<span class="hljs-name">input</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"text"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"nickname"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">label</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">label</span>&gt;</span>メッセージ: <span class="hljs-tag">&lt;<span class="hljs-name">input</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"text"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"message"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">label</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">input</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"submit"</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">form</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">hr</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">ul</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"log"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">ul</span>&gt;</span>
</code></span></pre>


<p>次にクライアント側の JavaScript ですが、例をシンプルにする為に jQuery を使用します。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">/* クライアント JavaScript */</span>
<span class="hljs-keyword">var</span> socket = io.connect(<span class="hljs-string">"http://example.com:8080"</span>);

socket.on(<span class="hljs-string">"connect"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    $(<span class="hljs-string">"#nickname"</span>).on(<span class="hljs-string">"change"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">e</span>)</span>{
        socket.emit(<span class="hljs-string">"set nickname"</span>, {
            <span class="hljs-attr">nickname</span>: <span class="hljs-keyword">this</span>.value
        });
    });
    $(<span class="hljs-string">"#form-message"</span>).on(<span class="hljs-string">"submit"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">e</span>)</span>{
        e.preventDefault();
        <span class="hljs-keyword">var</span> input = $(<span class="hljs-string">"#message"</span>);
        socket.emit(<span class="hljs-string">"send message"</span>, {
            <span class="hljs-attr">message</span>: input.val()
        });
        input.val(<span class="hljs-string">""</span>);
    });
});

socket.on(<span class="hljs-string">"message"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
    $(<span class="hljs-string">"&lt;li&gt;"</span>).append($(<span class="hljs-string">"&lt;strong&gt;"</span>).text(data.nickname))
    .append($(<span class="hljs-string">"&lt;span&gt;"</span>).text(data.message))
    .prependTo(<span class="hljs-string">"#log"</span>);
});
</code></span></pre>


<p>クライアントサイドの JavaScript はこのような働きをします。</p>



<ul class="wp-block-list">
<li>#nickname の内容が変更されると <strong>&#8220;set nickname&#8221;</strong> メッセージを送ってニックネームを変更する</li>



<li>#form-message がサブミットされると、#message から <strong>&#8220;send message&#8221;</strong> でメッセージを送信する</li>



<li>サーバから <strong>&#8220;message&#8221;</strong> が届いたら、 #log の中に追加して表示する</li>
</ul>



<p>最後にサーバ側では、上記の処理をサポートするように記述します。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">/* サーバ JavaScript */</span>
<span class="hljs-keyword">var</span> io = <span class="hljs-built_in">require</span>(<span class="hljs-string">'socket.io'</span>).listen(<span class="hljs-number">8080</span>);

io.sockets.on(<span class="hljs-string">"connection"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">socket</span>)</span>{
    <span class="hljs-keyword">var</span> anonymous = <span class="hljs-string">"名無しさん"</span>;
    <span class="hljs-keyword">var</span> nickname = <span class="hljs-literal">null</span>;
    socket.on(<span class="hljs-string">"set nickname"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
        nickname = data.nickname;
    });
    socket.on(<span class="hljs-string">"send message"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
        <span class="hljs-keyword">if</span>(! data.message){ <span class="hljs-keyword">return</span>; }
        <span class="hljs-keyword">var</span> vars = {
            <span class="hljs-attr">nickname</span>: nickname || anonymous,
            <span class="hljs-attr">message</span>: data.message
        };
        socket.emit(<span class="hljs-string">"message"</span>, vars);
        socket.broadcast.emit(<span class="hljs-string">"message"</span>, vars);
    });
});
</code></span></pre>


<p>socket オブジェクトには set/get が実装されており、その接続毎のデータを保持する事ができますが、 コールバックを受け取るタイプで少し例が冗長になってしまう為、ここでは単なる変数として <strong>nickname</strong> を定義しています。</p>



<p>WebSocket の働きが、なんとなく伝わったでしょうか。</p>



<h2 class="wp-block-heading">その他のヒント</h2>



<h3 class="wp-block-heading">限定されたユーザにメッセージを送りたい</h3>



<p>例えばチャットルームのような物が存在していて、その中だけでメッセージをやりとりしたい時の為に、 Socket.io には <a href="https://github.com/LearnBoost/socket.io/wiki/Rooms">「ルーム機能」</a> なる物があります。 ルームは入室・退室する事ができ、そのルームの中にいるメンバーだけに通知をする事ができます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">/*  サーバ JavaScript */</span>
socket.join(<span class="hljs-string">"ChatRoom"</span>); <span class="hljs-comment">// 入室します</span>
socket.leave(<span class="hljs-string">"ChatRoom"</span>); <span class="hljs-comment">// 退室します</span>
io.sockets.in(<span class="hljs-string">"ChatRoom"</span>).emit( ... ); <span class="hljs-comment">// ルーム内のメンバーにだけ emit</span>
</code></span></pre>


<p>ルーム内にメッセージを送るには、<strong>io.sockets</strong> を <strong>in()</strong> メソッドで絞り込んで emit します。</p>



<p>また、コネクションからクライアントを切り分ける <a href="http://socket.io/#how-to-use">ネームスペース機能</a> という物もあります。 &#8220;/chat&#8221; のようにネームスペースを定義してそこに接続したクライアントだけでデータのやり取りをします。 サーバ側では <strong>of()</strong> でクライアントを絞り込んで処理をかき分けます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">/*  サーバ JavaScript */</span>
<span class="hljs-keyword">var</span> chat = io.sockets.of(<span class="hljs-string">"/chat"</span>);
chat.on(<span class="hljs-string">"connection"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">socket</span>)</span>{
    socket.on(<span class="hljs-string">"send message"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">data</span>)</span>{
        chat.emit( ... );
    });
});
</code></span></pre>


<p>クライアント側では、コネクション時に &#8220;/chat&#8221; を足して接続します。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">/* クライアント JavaScript */</span>
<span class="hljs-keyword">var</span> socket = io.connect(<span class="hljs-string">"http://example.com:8080/chat"</span>);
</code></span></pre>


<p>また、ネームスペースとルーム両方で絞り込む事もできます。</p>



<h3 class="wp-block-heading">セッションを管理したい</h3>



<p>socket.io のセッションは基本的にその接続限りです。 ページをリロードしたり、新しいタブで開いたりした時点で新しいコネクションが貼り直され、id も更新されてしまいます。 その為、認証などでセッションの保持をしたい場合は少し工夫が必要です。</p>



<p><a href="https://github.com/learnboost/socket.io/wiki">socket.io の wiki</a> にいくつかその為のレシピやモジュールが公開されていますが、 基本的に <strong>express</strong> や <strong>connect</strong> など、node.js ベースの解決策になっているので、 socket.io を採用する場合はWebサーバも express を選択した方が良さそうですね。 （特に他の物を使う理由もなさそうですが）</p>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p><a href="https://github.com/wcamarao/session.socket.io">session.socket.io (SessionSockets) </a><br />
  This tiny node module simplifies your web sockets app when using http sessions from express or connect middlewares. It has no dependencies and can be initialized using any session store and cookie parser compatible with express or connect.</p>
</blockquote>



<p>こちらは socket.io でセッションを管理する為の node モジュールです。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="http://ja.wikipedia.org/wiki/WebSocket">WebSocket &#8211; Wikipedia</a></li>



<li><a href="http://socket.io/">Socket.IO: the cross-browser WebSocket for realtime apps.</a></li>



<li><a href="https://github.com/learnboost/socket.io/wiki">Home · LearnBoost/socket.io Wiki</a></li>



<li><a href="http://d.hatena.ne.jp/Jxck/20110730/1312042603">Socket.IO API 解説 &#8211; Block Rockin’ Codes</a></li>



<li><a href="https://github.com/wcamarao/session.socket.io">session.socket.io (SessionSockets) </a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;Video&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/21/jaac2013-v-video.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Sat, 21 Dec 2013 01:10:28 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[MediaElement]]></category>
		<category><![CDATA[Video]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3778</guid>

					<description><![CDATA[&#8220;V&#8221; は video の &#8220;V&#8221;。 Video 古くは Flash だったり wmv だったりしたWeb上での動画ファイルの再生も、 最近では HTML5 で追加された  [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;V&#8221; は video の &#8220;V&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh3.googleusercontent.com/-0EyMicsS5I0/UqR4mEQ-BGI/AAAAAAAACYg/_vfWt_n5kgs/s400/ac2013-v.png" alt="V"/></figure>



<p></p>



<span id="more-3778"></span>



<h2 class="wp-block-heading">Video</h2>



<p>古くは Flash だったり wmv だったりしたWeb上での動画ファイルの再生も、 最近では HTML5 で追加された <strong>video</strong> 要素のおかげで統一化が図られています。 勿論IE8以下ではサポートしていないので Flash 等で対応してあげる必要がありますが、 その辺の面倒をしっかり見てくれるライブラリも公開されています。</p>



<h2 class="wp-block-heading">video 要素</h2>



<p>まずは <strong>video</strong> 要素を簡単におさらいします。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">video</span> <span class="hljs-attr">poster</span>=<span class="hljs-string">"img/poster.jpg"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"my-video"</span> <span class="hljs-attr">controls</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">source</span> <span class="hljs-attr">src</span>=<span class="hljs-string">"movies/movie.mp4"</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"video/mp4"</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">source</span> <span class="hljs-attr">src</span>=<span class="hljs-string">"movies/movie.webm"</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"video/webm"</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">video</span>&gt;</span>
</code></span></pre>


<p>video 要素は <strong>source</strong> 要素をぶらさげ、形式ごとに動画ファイルを列挙していきます。 video の src 属性で指定する事もできますが、ブラウザ環境ごとに再生が出来る形式が限定されているので、 複数の形式を連ねて再生可能な形式で再生する方法が広く使われます。 どの環境でどの形式がサポートされているかは下記URLにて詳細がまとめられています。</p>



<ul class="wp-block-list">
<li><a href="https://developer.mozilla.org/ja/docs/Web/HTML/Supported_media_formats#Browser_compatibility">HTML5 の audio 要素と video 要素でサポートされているメディアフォーマット &#8211; HTML | MDN</a></li>
</ul>



<h3 class="wp-block-heading">ムービーのコントロール</h3>



<p>video 要素の元となる <strong>HTMLMediaElement</strong> には動画の再生をコントロールするメソッドがぶら下がっているので、 それを利用して操作する事ができます。ブラウザによっては他にもメソッドも独自に実装されている事があります。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> video = <span class="hljs-built_in">document</span>.getElementById(<span class="hljs-string">"#my-video"</span>);
...
video.load(); <span class="hljs-comment">// ビデオのロード</span>
video.play(); <span class="hljs-comment">// 再生</span>
video.pause(); <span class="hljs-comment">// 停止</span>
</code></span></pre>


<h3 class="wp-block-heading">ムービーのシーク</h3>



<p>動画の指定した時間へのジャンプは <strong>currentTime</strong> プロパティの値を変更する事で可能です。 currentTime プロパティは通常の呼び出しでは現在の再生位置を返しますが、 値を指定する事でその再生位置にジャンプする事が出来ます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">video.currentTime; <span class="hljs-comment">// 12.345 など（再生位置を秒で返す）</span>
video.currentTime = <span class="hljs-number">30</span>; <span class="hljs-comment">// 30秒の位置に移動する</span>
</code></span></pre>


<p>しかし、currentTime に代入してシークを行おうとした場合にエラーが発生する場合があります。</p>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p>InvalidStateError: An attempt was made to use an object that is not, or is no longer, usable</p>
</blockquote>



<p>これは動画ファイルの情報がまだ利用可能でない為起こる様です。 他の外部リソース同様にメタ情報のロードを待つ必要がありますね。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">video.addEventListener(<span class="hljs-string">"loadedmetadata"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">e</span>)</span>{
    e.target.currentTime = <span class="hljs-number">30</span>;
}, <span class="hljs-literal">false</span>);
</code></span></pre>


<p>この他にも多くのプロパティが実装されているので、 JavaScript でさらに進んだ処理をしたい時は <a href="http://www.whatwg.org/specs/web-apps/current-work/multipage/the-video-element.html#htmlmediaelement">W3Cのページ</a> を訪れてみましょう。</p>



<h2 class="wp-block-heading">ビデオプレイヤーライブラリ</h2>



<p>限られた環境で動画を再生するだけならば素のまま使えば良いのですが、 やはりどうしてもレガシーな環境に対応しなければならない時があります。 面倒な部分は優秀なライブラリにお願いしてしまいましょう。</p>



<h3 class="wp-block-heading"><a href="http://www.videojs.com/">Video.js</a></h3>



<p><a href="http://www.videojs.com/">http://www.videojs.com/</a></p>



<p><strong>Video.js</strong> は Flash をフォールバックに使用しているプレイヤーライブラリです。 スタイルシートとJavaScriptファイルを読み込み、video 属性に専用のクラスを指定して使用します。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">video</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"my-video"</span> <span class="hljs-attr">class</span>=<span class="hljs-string">"video-js vjs-default-skin"</span>&gt;</span> ... <span class="hljs-tag">&lt;/<span class="hljs-name">video</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="actionscript">
<span class="hljs-keyword">var</span> player = videojs(<span class="hljs-string">"my-video"</span>, { <span class="hljs-comment">/* options */</span> });
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p>プレイヤーに好みのスキンを着せる事が出来るのが特徴で、 ブラウザ上でプレビューを確認しながらスキンを編集出来るツールも公開しています。 スタイルの編集は Less で行う事ができます。</p>



<ul class="wp-block-list">
<li><a href="http://designer.videojs.com/">Video.js | Video Player Skin Designer</a></li>
</ul>



<p>Video.js の <a href="https://github.com/videojs/video.js/blob/master/docs/api/vjs.Player.md">API</a> は、 イベント・メソッドの名前や仕様などが MediaElement API に倣った形になっています。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">player.on(<span class="hljs-string">"loadedmetadata"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{ ... }); <span class="hljs-comment">// on メソッドでイベントの設定</span>
player.play(); <span class="hljs-comment">// 再生</span>
</code></span></pre>


<h3 class="wp-block-heading"><a href="http://mediaelementjs.com/">MediaElement.js</a></h3>



<p><a href="http://mediaelementjs.com/">http://mediaelementjs.com/</a></p>



<p><strong>MediaElement.js</strong> は、Flash や Silverlight のプレイヤーを使い、 古いブラウザでも HTML5 の MediaElement の API を使用出来るように振る舞ってくれます。 多くのCMS向けのプラグインが公開されており、WordPress はコアにバンドルされているそうです。 動作には jQuery が必要です。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">video</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"my-video"</span>&gt;</span> ... <span class="hljs-tag">&lt;/<span class="hljs-name">video</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="javascript">
    <span class="hljs-keyword">var</span> player = <span class="hljs-keyword">new</span> MediaElementPlayer(<span class="hljs-string">"#my-video"</span>, <span class="hljs-comment">/* options */</span>);
    <span class="hljs-comment">// あるいは</span>
    <span class="hljs-keyword">var</span> $media = $(<span class="hljs-string">"#my-video"</span>).mediaelementplayer({ <span class="hljs-comment">/* options */</span> });
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p>プレイヤーの初期化は <strong>MediaElementPlayer</strong> から生成するか、 <strong>$.fn.mediaelementplayer</strong> を使用して行います。 それぞれ返り値が違うので注意しましょう。</p>



<h3 class="wp-block-heading">ライブラリ使用上の共通の注意</h3>



<p>video 要素に対応していないブラウザで使用する場合は、 html5shiv や Modernizr 等で video 要素へのCSSの適用を有効化しておかなければなりません。 あるいは手作業で対応しておきましょう。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-built_in">document</span>.createElement(<span class="hljs-string">"video"</span>);
<span class="hljs-built_in">document</span>.createElement(<span class="hljs-string">"audio"</span>);
</code></span></pre>


<p>また、古い環境でエミュレートしてくれるといっても、 コールするタイミングによっては使えなかったり、細かい点で本来の物と挙動が異なってしまったりします。 結局中でIE用の処理を分けざるをえない、といった状況は結構ありますので、がんばりましょう。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="https://developer.mozilla.org/en/docs/Web/HTML/Element/video">video &#8211; HTML | MDN</a></li>



<li><a href="https://developer.mozilla.org/ja/docs/Web/HTML/Supported_media_formats">HTML5 の audio 要素と video 要素でサポートされているメディアフォーマット &#8211; HTML | MDN</a></li>



<li><a href="http://www.videojs.com/">HTML5 Video Player | Video.js</a></li>



<li><a href="http://mediaelementjs.com/">MediaElement.js &#8211; HTML5 video player and audio player with Flash and Silverlight shims</a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;userData&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/20/jaac2013-u-userdata.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Fri, 20 Dec 2013 01:39:00 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[Internet Exploer]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[userData]]></category>
		<category><![CDATA[Web Storage]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3775</guid>

					<description><![CDATA[&#8220;U&#8221; は userData の &#8220;U&#8221;。 userData userData は、旧来の Internet Explorer で使用出来るローカルのストレージです。 ロー [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;U&#8221; は userData の &#8220;U&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh4.googleusercontent.com/-sHTfojjN8VA/UqR4lhb5EMI/AAAAAAAACYg/-W3cAHkju48/s400/ac2013-u.png" alt="U"/></figure>



<p></p>



<span id="more-3775"></span>



<h2 class="wp-block-heading">userData</h2>



<p><strong>userData</strong> は、旧来の Internet Explorer で使用出来るローカルのストレージです。 ローカルの記憶領域というと今では <a href="http://www.w3.org/TR/webstorage/">Web Storage</a> がありますが、 しばしばその代替として使用されています。</p>



<p>何が凄いのかというと、これが IE5（1999年）から実装されている点で、 Web黎明期を少し抜けたあたりで Web Storage に近しい物が既に存在していたという事になります。 一方の DOM Storage はIE8からサポートされている為あまり出番はないかもしれませんが、 いまだ息が絶えないIE6-7対応で活躍する事ができます。</p>



<h3 class="wp-block-heading">Cookie との比較</h3>



<p>Web Storage の代替として広く使われている Cookie と比較すると、容量と範囲で大きな差があります。</p>



<ul class="wp-block-list">
<li><strong>容量</strong>
<ul class="wp-block-list">
<li>userData: およそ1MB</li>



<li>Cookie: およそ5KB</li>
</ul>
</li>



<li><strong>範囲</strong>
<ul class="wp-block-list">
<li>userData: 同じディレクトリ内のみ</li>



<li>Cookie: フレキシブルに設定可能</li>
</ul>
</li>
</ul>



<p>容量は、5MBほど利用できる Web Storage には及びませんが、Cookie と比較するとかなり大きいです。 その半面、データを共有出来る範囲が同じディレクトリ内に限られてしまいます。 互いに一長一短なので、場面によってい使い分けたいところです。</p>



<h2 class="wp-block-heading">userData の使い方</h2>



<p>userData は IE独自の <strong>behavior</strong> でスタイル指定をして使います。 下の例では input 要素にしていますが、恐らくどの要素でも使えると思います。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">input</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"hidden"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"my-storage"</span> <span class="hljs-attr">style</span>=<span class="hljs-string">"behavior:url(#default#userData)"</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="javascript">
    <span class="hljs-keyword">var</span> myStorage = <span class="hljs-built_in">document</span>.getElementById(<span class="hljs-string">"my-storage"</span>);
    myStorage.load(<span class="hljs-string">"myStorageData"</span>);
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p><strong>#default#userData</strong> を behavior で指定した要素は userData を使用する為のメソッドが使えるようになります。</p>



<ul class="wp-block-list">
<li><strong>load(name)</strong>: ストレージからデータをロードする</li>



<li><strong>save(name)</strong>: ストレージにデータを保存する</li>



<li><strong>getAttribute(key)</strong>: 値を取得する</li>



<li><strong>setAttribute(key, value)</strong>: 値をセットする</li>



<li><strong>removeAttribute(key)</strong>: 値を削除する</li>
</ul>



<p>ストレージ名を &#8220;myStorageData&#8221; とし、適当な値を設定してみる例です。 ロードとセーブが都度必要になる以外は、別段注意すべき所はなさそうですね。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">myStorage.load(<span class="hljs-string">"myStorageData"</span>);
myStorage.setAttribute(<span class="hljs-string">"name"</span>, <span class="hljs-string">"john"</span>);
myStorage.setAttribute(<span class="hljs-string">"email"</span>, <span class="hljs-string">"john@example.com"</span>);
myStorage.save(<span class="hljs-string">"myStorageData"</span>);
</code></span></pre>


<p>ストレージに使用する要素を動的に生成する事もできますが、DOMに追加されていないと働かないので注意が必要です。 動的生成の際には <strong>addBehavior</strong> メソッドが便利です。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> myStorage = <span class="hljs-built_in">document</span>.createElement(<span class="hljs-string">"input"</span>);
myStorage.setAttribute(<span class="hljs-string">"type"</span>, <span class="hljs-string">"hidden"</span>);
myStorage.addBehavior(<span class="hljs-string">"#default#userData"</span>);
<span class="hljs-built_in">document</span>.body.appendChild(myStorage);
myStorage.load(<span class="hljs-string">"myStorageData"</span>);
</code></span></pre>


<h2 class="wp-block-heading">localStorage の polyfill を userData で書いてみる</h2>



<p>少し長くなりますが、IE7以下向けの localStorage の代替処理を書いてみます。 先述の通り、同じディレクトリ内でしかデータを共有する事は出来ません。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-comment">// Detect supports</span>
    <span class="hljs-keyword">if</span>(<span class="hljs-string">"localStorage"</span> <span class="hljs-keyword">in</span> <span class="hljs-built_in">window</span> || ! (<span class="hljs-string">"addBehavior"</span> <span class="hljs-keyword">in</span> <span class="hljs-built_in">document</span>.body)){
        <span class="hljs-keyword">return</span>;
    }

    <span class="hljs-comment">// Create element for strage</span>
    <span class="hljs-keyword">var</span> createStorage = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">name</span>)</span>{
        <span class="hljs-keyword">var</span> input = <span class="hljs-built_in">document</span>.createElement(<span class="hljs-string">"input"</span>);
        <span class="hljs-built_in">document</span>.getElementsByTagName(<span class="hljs-string">"head"</span>)&#91;<span class="hljs-number">0</span>].appendChild(input);
        input.setAttribute(<span class="hljs-string">"type"</span>, <span class="hljs-string">"hidden"</span>);
        input.addBehavior(<span class="hljs-string">"#default#userData"</span>);
        input.load(name);
        input._commit = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
            <span class="hljs-keyword">this</span>.save(name);
        };
        <span class="hljs-keyword">return</span> input;
    };

    <span class="hljs-comment">// Storage and index object</span>
    <span class="hljs-keyword">var</span> storage = createStorage(<span class="hljs-string">"altLocalStorage"</span>);
    <span class="hljs-keyword">var</span> index = createStorage(<span class="hljs-string">"altLocalStorageKeys"</span>);

    <span class="hljs-comment">// Fetures for index</span>
    index._get = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
        <span class="hljs-keyword">var</span> keys = <span class="hljs-keyword">this</span>.getAttribute(<span class="hljs-string">"keys"</span>) || <span class="hljs-string">""</span>;
        <span class="hljs-keyword">if</span>(keys){ <span class="hljs-keyword">return</span> keys.split(<span class="hljs-string">","</span>); }
        <span class="hljs-keyword">return</span> &#91;];
    };
    index._indexOf = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">key, keys</span>)</span>{
        <span class="hljs-keyword">var</span> i=<span class="hljs-number">0</span>; keys = keys || <span class="hljs-keyword">this</span>._get();
        <span class="hljs-keyword">for</span>(; i&lt;keys.length; i++){
            <span class="hljs-keyword">if</span>(keys&#91;i] === key){ <span class="hljs-keyword">return</span> i; }
        }
        <span class="hljs-keyword">return</span> <span class="hljs-number">-1</span>;
    };
    index._set = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">keys</span>)</span>{
        <span class="hljs-keyword">this</span>.setAttribute(<span class="hljs-string">"keys"</span>, keys.join(<span class="hljs-string">","</span>));
        <span class="hljs-keyword">this</span>._commit();
    };

    <span class="hljs-comment">// API</span>
    <span class="hljs-built_in">window</span>.localStorage = {
        <span class="hljs-attr">setItem</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">key, value</span>)</span>{
            <span class="hljs-keyword">var</span> keys;
            <span class="hljs-keyword">if</span>(index._indexOf(key) &lt; <span class="hljs-number">0</span>){
                keys = index._get();
                keys.push(key);
                index._set(keys);
            }
            storage.setAttribute(key, value);
            storage._commit();
        },
        <span class="hljs-attr">getItem</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">key</span>)</span>{
            <span class="hljs-keyword">return</span> storage.getAttribute(key);
        },
        <span class="hljs-attr">removeItem</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">key</span>)</span>{
            <span class="hljs-keyword">var</span> keys, i;
            keys = index._get(),
            i = index._indexOf(key, keys);
            <span class="hljs-keyword">if</span>(i &gt;= <span class="hljs-number">0</span>){
                keys.splice(i, <span class="hljs-number">1</span>);
                index._set(keys);
            }
            storage.removeAttribute(key);
            storage._commit();
        },
        <span class="hljs-attr">clear</span>: <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
            <span class="hljs-keyword">var</span> i = <span class="hljs-number">0</span>, keys = index._get();
            <span class="hljs-keyword">for</span>(; i&lt;keys.length; i++){
                storage.removeAttribute(keys&#91;i]);
            }
            storage._commit();
            index._set(&#91;]);
        }
    };
}());
</code></span></pre>


<p>保存されたデータを列挙する手段が見つからなかった為、キーを保存するストレージを別に作っています。 <strong>clear</strong> メソッドを実装しなければそれは必要ないので、半分以下のコード量に収まると思います。</p>



<p>余談ですが、IEの開発者ツールでモードを Internet Exlorer 7 にしても &#8220;localStorage&#8221; は実装されてしまっていますので、 上のコードはネイティブのIE7でないと検証する事が出来ません。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="http://msdn.microsoft.com/en-us/library/ms531424(v=vs.85).aspx">userData Behavior (A, ABBR, ACRONYM, &#8230;)</a></li>



<li><a href="https://developer.mozilla.org/ja/docs/DOM/Storage">DOM Storage &#8211; DOM | MDN</a></li>



<li><a href="http://www.w3.org/TR/webstorage/">Web Storage</a></li>
</ul>



<h2 class="wp-block-heading">追記</h2>



<dl>
<dt>2014/01/23</dt>
<dd>コードの誤りを修正（urlの欠如）</dd>
</dl>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;Template&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/19/jaac2013-t-template.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Thu, 19 Dec 2013 01:46:39 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[EJS]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Mustache]]></category>
		<category><![CDATA[Template]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3771</guid>

					<description><![CDATA[&#8220;T&#8221; は Template の &#8220;T&#8221;。 テンプレート 動的なWebアプリケーションを制作する上で、 テンプレートは非常に強力な味方になります。 それだけにテンプレートエ [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;T&#8221; は Template の &#8220;T&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh3.googleusercontent.com/-ln2nacy3ZKQ/UqR4laWBsFI/AAAAAAAACYg/bPA0l76eL5o/s400/ac2013-t.png" alt="T"/></figure>



<p></p>



<span id="more-3771"></span>



<h2 class="wp-block-heading">テンプレート</h2>



<p>動的なWebアプリケーションを制作する上で、 テンプレートは非常に強力な味方になります。 それだけにテンプレートエンジンはまさに群雄割拠で、 それぞれ個性や独自の趣向をもったライブラリが至る所で開発されています。</p>



<h3 class="wp-block-heading">基本的な機能</h3>



<p>どのテンプレートエンジンも記法こそ様々ですが、提供する機能や使い方は基本的に共通しています。 出力用の関数が用意されており、その関数に元となるテンプレート文字列と、 その中で展開したいデータを格納したオブジェクトを渡します。</p>



<p>例えば <strong>Mustache</strong> では <strong>render</strong> メソッドがそれにあたります。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> output = Mustache.render(template, data);
</code></span></pre>


<p>render の中では、テンプレートの記述を元にして data オブジェクトの内容を展開していきます。 例えばこのようなテンプレートが文字列で用意されているとして、</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">a</span> <span class="hljs-attr">href</span>=<span class="hljs-string">"mailto:{{email}}"</span>&gt;</span>{{name}}<span class="hljs-tag">&lt;/<span class="hljs-name">a</span>&gt;</span>
</code></span></pre>


<p>これを次のような data オブジェクトで展開したいとします。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> data = {
    <span class="hljs-attr">name</span>: <span class="hljs-string">"John"</span>,
    <span class="hljs-attr">email</span>: <span class="hljs-string">"john@example.com"</span>
};
</code></span></pre>


<p>これらを Mustache.render メソッドに渡すと、次のような出力が文字列で返されます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">a</span> <span class="hljs-attr">href</span>=<span class="hljs-string">"mailto:john@example.com"</span>&gt;</span>John<span class="hljs-tag">&lt;/<span class="hljs-name">a</span>&gt;</span>
</code></span></pre>


<h3 class="wp-block-heading">制御構文</h3>



<p>テンプレートエンジンは、データのコレクションをループで回して全部出力させたり、 条件分岐を行なって true の場合のみ出力させたりといった機能を提供してくれます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">ul</span>&gt;</span>
    <span class="hljs-comment">&lt;!-- products（配列）の中のオブジェクトを全て出力 --&gt;</span>
    {{#products}}
    <span class="hljs-tag">&lt;<span class="hljs-name">li</span>&gt;</span>{{name}} : {{price}}<span class="hljs-tag">&lt;/<span class="hljs-name">li</span>&gt;</span>
    {{/products}}
<span class="hljs-tag">&lt;/<span class="hljs-name">ul</span>&gt;</span>

<span class="hljs-comment">&lt;!-- isError が true の場合だけ出力 --&gt;</span>
{{#isError}}
<span class="hljs-tag">&lt;<span class="hljs-name">strong</span>&gt;</span>エラーです<span class="hljs-tag">&lt;/<span class="hljs-name">strong</span>&gt;</span>
{{/isError}}
</code></span></pre>


<p>これは Mustache での制御構文の例です。（制御構文の書き方はライブラリによって大きく異なります）</p>



<h3 class="wp-block-heading">テンプレートのコンパイル</h3>



<p>Mustache.render のようにテンプレートとデータを渡して出力する方法の他に、 テンプレートをコンパイルしてしまって繰り返し再利用可能な関数にしてしまう事もできます。 コンパイルも多くのテンプレートエンジンで実装されています。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> render = Mustache.compile(template);
<span class="hljs-keyword">var</span> output = render(data);
</code></span></pre>


<p>何度も繰り返し使うようなパーツはコンパイルしてしまったほうが、 人にもパフォーマンスにも優しそうです。</p>



<h3 class="wp-block-heading">テンプレート文字列</h3>



<p>Web開発においてテンプレート文字列の内容は主に HTML であり、JavaScript の文字列リテラルで表現するには長過ぎます。 そこで、次のように script 要素の中に閉じ込めてしまう手法がよくとられます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">script</span> <span class="hljs-attr">type</span>=<span class="hljs-string">"text/template"</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"template-profile"</span>&gt;</span><span class="handlebars"><span class="xml">
    <span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">class</span>=<span class="hljs-string">"profile"</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">class</span>=<span class="hljs-string">"name"</span>&gt;</span></span><span class="hljs-template-variable">{{name}}</span><span class="xml"><span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">class</span>=<span class="hljs-string">"email"</span>&gt;</span></span><span class="hljs-template-variable">{{email}}</span><span class="xml"><span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
</span></span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>

<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="javascript">
    <span class="hljs-keyword">var</span> template = <span class="hljs-built_in">document</span>.getElementById(<span class="hljs-string">"template-profile"</span>).innerHTML;
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<h2 class="wp-block-heading">テンプレートエンジンライブラリの色々</h2>



<p>どのライブラリも記法・機能が千差万別です。 自分のスタイルや、プロジェクトに合ったテンプレートエンジンを選択しましょう。</p>



<h3 class="wp-block-heading">Mustache</h3>



<p><a href="http://mustache.github.io/">http://mustache.github.io/</a></p>



<p>Mustache の特徴として、「多言語に対応している」事と、「ロジックレスである」事が挙げられます。 JavaScript の他にも20言語（2013年12月現在）にわたって実装されていて、 サーバサイドでもフロントでも同じ記法でテンプレートを書くことができます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">section</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">h1</span>&gt;</span>{{title}}<span class="hljs-tag">&lt;/<span class="hljs-name">h1</span>&gt;</span>
    {{#onsale}}<span class="hljs-tag">&lt;<span class="hljs-name">strong</span>&gt;</span>セール中！<span class="hljs-tag">&lt;/<span class="hljs-name">strong</span>&gt;</span>{{/onsale}}
    <span class="hljs-tag">&lt;<span class="hljs-name">ul</span>&gt;</span>
    {{#items}}
        <span class="hljs-tag">&lt;<span class="hljs-name">li</span>&gt;</span>{{name}} : {{price}}<span class="hljs-tag">&lt;/<span class="hljs-name">li</span>&gt;</span>
    {{/items}}
    <span class="hljs-tag">&lt;/<span class="hljs-name">ul</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">section</span>&gt;</span>
</code></span></pre>


<p>ループや条件分岐は {{#name}} で表現する為、複雑な制御は出来ません。</p>



<h3 class="wp-block-heading">hogan.js</h3>



<p><a href="http://twitter.github.io/hogan.js/">http://twitter.github.io/hogan.js/</a></p>



<p>hogan.js は Mustache 互換のテンプレート記法を採用した、Twitter が提供するテンプレートエンジンです。 Mustache と変わらない記述で、本家よりも速く動作するとしています。 出力の仕方は Mustache と変わりありません。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> output = hogan.render(template, data); <span class="hljs-comment">// 出力</span>
<span class="hljs-keyword">var</span> render = hogan.compile(template); <span class="hljs-comment">// コンパイル</span>
</code></span></pre>


<h3 class="wp-block-heading">EJS</h3>



<figure class="wp-block-embed"><div class="wp-block-embed__wrapper">
https://github.com/visionmedia/ejs
</div></figure>



<p>Ruby の ERB スタイルでテンプレートを書ける JavaScript のライブラリです。 Mustache系と違って、テンプレート内にそのまま JavaScript コードを記述する事ができます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">section</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">h1</span>&gt;</span><span class="hljs-tag">&lt;<span class="hljs-name">%=</span> <span class="hljs-attr">title</span> %&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">h1</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">%</span> <span class="hljs-attr">if</span>(<span class="hljs-attr">onsale</span>) { %&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">strong</span>&gt;</span>セール中！<span class="hljs-tag">&lt;/<span class="hljs-name">strong</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">%</span> } %&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">ul</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">%</span> <span class="hljs-attr">items.forEach</span>(<span class="hljs-attr">function</span>(<span class="hljs-attr">item</span>){ %&gt;</span>
        <span class="hljs-tag">&lt;<span class="hljs-name">li</span>&gt;</span><span class="hljs-tag">&lt;<span class="hljs-name">%=</span> <span class="hljs-attr">item.name</span> %&gt;</span> : <span class="hljs-tag">&lt;<span class="hljs-name">%=</span> <span class="hljs-attr">item.price</span> %&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">li</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">%</span> }) %&gt;</span>
    <span class="hljs-tag">&lt;/<span class="hljs-name">ul</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">section</span>&gt;</span>
</code></span></pre>


<p>テンプレートにロジックが必要な場合は非常に強力な味方になりますね。 記述もタグで囲むだけのシンプルなもので、 Ruby 開発者は勿論、PHP の開発者にとっても馴染みのある書き方なのではないでしょうか。</p>



<p>出力に使うメソッド名は上に上げたものと変わりません。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> output = ejs.render(template, data); <span class="hljs-comment">// 出力</span>
<span class="hljs-keyword">var</span> render = ejs.compile(template); <span class="hljs-comment">// コンパイル</span>
</code></span></pre>


<h3 class="wp-block-heading">underscore</h3>



<p><a href="http://underscorejs.org/">http://underscorejs.org/</a></p>



<p>underscore.js は便利なメソッドを多数提供してくれる大変有難いライブラリですが、 その中の <strong>_.template</strong> メソッドがテンプレートエンジンとして働いてくれます。</p>



<p>テンプレートの記述は ERB に倣った物で、上の EJS で書いたテンプレートがそのまま _.template で動作します。 出力もコンパイルも同じメソッドで行います。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> output = _.template(template, data); <span class="hljs-comment">// 出力</span>
<span class="hljs-keyword">var</span> render = _.template(template); <span class="hljs-comment">// コンパイル</span>
</code></span></pre>


<p>一番の魅力は、この機能が underscore.js の一部でしかないという点だと思います。 他の便利なメソッドを使う為に、あるいは Backbone.js を使う為にインクルードしておいた underscore.js がテンプレートエンジンとしても働き、 新たに別のライブラリを読み込む必要がないのです。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="http://mustache.github.io/">{{ mustache }}</a></li>



<li><a href="http://twitter.github.io/hogan.js/">Hogan.js</a></li>



<li><a href="https://github.com/visionmedia/ejs">visionmedia/ejs</a></li>



<li><a href="http://underscorejs.org/">Underscore.js</a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;SVG&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/18/jaac2013-s-svg.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Wed, 18 Dec 2013 01:19:02 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Raphael]]></category>
		<category><![CDATA[Snap.svg]]></category>
		<category><![CDATA[SVG]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3754</guid>

					<description><![CDATA[&#8220;S&#8221; は SVG の &#8220;S&#8221;。 SVG SVG（Scalable Vector Graphics）は、Webページ上でベクターグラフィックを扱う為のマークアップ言語です。 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;S&#8221; は SVG の &#8220;S&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh4.googleusercontent.com/-XUrPw_pet0s/UqR4lTXOk8I/AAAAAAAACYg/EboU7AOOUJg/s400/ac2013-s.png" alt="S"/></figure>



<p></p>



<span id="more-3754"></span>



<h2 class="wp-block-heading">SVG</h2>



<p><strong>SVG（Scalable Vector Graphics）</strong>は、Webページ上でベクターグラフィックを扱う為のマークアップ言語です。 ベクターなので拡縮してもビットマップデータのように劣化しないのが特徴で、 アイコンやイラスト・アニメーション等で幅広く活躍できます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">svg</span> <span class="hljs-attr">width</span>=<span class="hljs-string">"40"</span> <span class="hljs-attr">height</span>=<span class="hljs-string">"40"</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">path</span> <span class="hljs-attr">d</span>=<span class="hljs-string">"M16,22.375L7.116,28.83l3.396-10.438l-8.883-6.458l10.979,0.002L16.002,1.5l3.391,10.434h10.981l-8.886,6.457l3.396,10.439L16,22.375L16,22.375z"</span> <span class="hljs-attr">fill</span>=<span class="hljs-string">"black"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">path</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">svg</span>&gt;</span>
</code></span></pre>


<p>このコードをHTMLに挿入すると、ベクターで描かれた星印が表示されます。 上で使用されている <strong>path</strong> の他、<strong>rect</strong> や <strong>circle</strong> などを使って様々なグラフィックを描く事が出来ます。</p>



<p>IEではSVGをサポートするのがバージョン9以降な為、 旧来より実装されていた <strong>VML（Vector Markup Language）</strong>で代用されたりします。</p>



<h2 class="wp-block-heading">Raphael</h2>



<p><a href="http://raphaeljs.com/">http://raphaeljs.com/</a></p>



<p><strong>Raphael</strong> は比較的老舗なべクターグラフィックライブラリで、 SVGライブラリの中ではデファクトスタンダードとの呼び声が高い物です。 SVGが使える環境ならばSVGを使い、そうでない場合はVMLで代用してベクターコンテンツを扱う事ができます。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"canvas"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="actionscript">

<span class="hljs-comment">// #canvas にキャンバスを生成する</span>
<span class="hljs-keyword">var</span> paper = Raphael(<span class="hljs-string">"canvas"</span>);

<span class="hljs-comment">// キャンバスに円を描く</span>
<span class="hljs-keyword">var</span> circle = paper.circle(<span class="hljs-number">24</span>, <span class="hljs-number">24</span>, <span class="hljs-number">16</span>);
circle.attr({
    <span class="hljs-string">"fill"</span>: <span class="hljs-string">"#c00"</span>,
    <span class="hljs-string">"stroke-width"</span>: <span class="hljs-number">0</span>
});

</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p><strong>Raphael()</strong> でキャンバスを生成し、 そのキャンバスに対して <strong>circle</strong> / <strong>rect</strong> / <strong>path</strong> などを使用してグラフィックを描きます。</p>



<p>Raphael で描かれた図形要素には、属性を編集する <strong>attr()</strong> の他、 各種イベントハンドラを設定する為のメソッド等が実装されています。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">// マウスオーバーイベントを設定する</span>
circle.hover(
    <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
        <span class="hljs-keyword">this</span>.animate({
            <span class="hljs-string">"fill"</span>: <span class="hljs-string">"#00c"</span>
        }, <span class="hljs-number">500</span>);
    },
    <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
        <span class="hljs-keyword">this</span>.animate({
            <span class="hljs-string">"fill"</span>: <span class="hljs-string">"#c00"</span>
        }, <span class="hljs-number">500</span>);
    }
);

<span class="hljs-comment">// クリックイベントを設定する</span>
button.click(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"click"</span>);
});
</code></span></pre>


<p>さながら jQuery のSVG版といった感覚で使えます。</p>



<h2 class="wp-block-heading">Snap.svg</h2>



<p><a href="http://snapsvg.io/">http://snapsvg.io/</a></p>



<p>Snap.svg はRaphaelの作者が開発し、Adobe からリリースされた生まれて間もないプロジェクトです。 （2013/10/23 に初リリースされています。）</p>



<p>最も大きな違いは、snap.svg は SVG をサポートする環境の為だけのもので、 VMLによる古い環境へのサポートは一切しないと宣言している点です。 そうすることで、SVG にあって VML にはないような先進的な機能を利用出来る為です。 また、VML対応を無くす事によりライブラリ自体の軽量化も図れている模様です。</p>



<p>開発者が同じなだけあり、使い方はRaphaelからほぼ変わりません。（これは素晴らしいことです） 試しに Raphael での例と同じ処理をしてみましょう。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">svg</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"canvas"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">svg</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="javascript">
    <span class="hljs-comment">// 対象要素は svg 要素である必要があります</span>
    <span class="hljs-keyword">var</span> paper = Snap(<span class="hljs-string">"#canvas"</span>);
    <span class="hljs-keyword">var</span> circle = paper.circle(<span class="hljs-number">24</span>, <span class="hljs-number">24</span>, <span class="hljs-number">16</span>);
    circle.attr({
        <span class="hljs-string">"fill"</span>: <span class="hljs-string">"#c00"</span>,
        <span class="hljs-string">"stroke-width"</span>: <span class="hljs-number">0</span>
    });
    circle.hover(
        <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
            <span class="hljs-keyword">this</span>.animate({
                <span class="hljs-string">"fill"</span>: <span class="hljs-string">"#00c"</span>
            }, <span class="hljs-number">500</span>);
        },
        <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
            <span class="hljs-keyword">this</span>.animate({
                <span class="hljs-string">"fill"</span>: <span class="hljs-string">"#c00"</span>
            }, <span class="hljs-number">500</span>);
        }
    );
    circle.click(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
        <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"click"</span>);
    });
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p>Raphael() が <strong>Snap()</strong> に変わったことと、渡す要素が svg 要素である必要がある事をのぞいて、 間違い探しの問題かと思うほどにほぼ一致しています。</p>



<p>また、Raphael にはなかった機能のひとつとして、「外部SVGリソースのインポート」があります。 外部SVGファイルをAjaxで取得し、その結果をコールバックで展開する事が出来ます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript">Snap.load(<span class="hljs-string">"external.svg"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">f</span>)</span>{ ... });
</code></span></pre>


<p>他にもマスキングやパターンのクリッピングなど先鋭的な機能が揃えられています。 <a href="http://snapsvg.io/start/">公式のチュートリアル</a> ではコードを追いながら使い方を学ぶ事が出来ます。 ここのページャーのアニメーションも気が利いていてかわいいですね。</p>



<p>Raphael がそうであったように、新世代のSVGライブラリのスタンダードになりそうな予感がしますね。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="http://ja.wikipedia.org/wiki/Scalable_Vector_Graphics">Scalable Vector Graphics &#8211; Wikipedia</a></li>



<li><a href="https://developer.mozilla.org/en/docs/Web/SVG">SVG | MDN</a></li>



<li><a href="http://www.w3.org/Graphics/SVG/">W3C SVG Working Group</a></li>



<li><a href="http://raphaeljs.com/">Raphaël—JavaScript Library</a></li>



<li><a href="http://snapsvg.io/">Snap.svg &#8211; Home</a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;readyState&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/17/jaac2013-r-readystate.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Tue, 17 Dec 2013 01:25:37 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[async]]></category>
		<category><![CDATA[DOMContentLoaded]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[readyState]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3749</guid>

					<description><![CDATA[&#8220;R&#8221; は readyState の &#8220;R&#8221;。 readyState document.readyState は、HTMLのダウンロード・パース状況を取得できるAPIです。 [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;R&#8221; は readyState の &#8220;R&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh5.googleusercontent.com/-gbMxSuEuhoc/UqR4k8DxMOI/AAAAAAAACYg/j4SKZcO5ldo/s400/ac2013-r.png" alt="R"/></figure>



<p></p>



<span id="more-3749"></span>



<h2 class="wp-block-heading">readyState</h2>



<p><strong>document.readyState</strong> は、HTMLのダウンロード・パース状況を取得できるAPIです。 値は &#8220;loading&#8221; / &#8220;interactive&#8221; / &#8220;complete&#8221; などが返され、 それぞれ以下のような状態を表します。</p>



<ul class="wp-block-list">
<li>loading: ダウンロード中</li>



<li>interactive: HTMLのダウンロードとパースが完了</li>



<li>complete: サブリソースのダウンロードが完了</li>
</ul>



<p>また、readyState の状態が移り変わる毎に、<strong>readystatechange</strong> イベントが発火されます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-built_in">document</span>.addEventListener(<span class="hljs-string">"readystatechange"</span>, <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">e</span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-built_in">document</span>.readyState); <span class="hljs-comment">// "loading", "interactive", "complete" など</span>
}, <span class="hljs-literal">false</span>);
</code></span></pre>


<h3 class="wp-block-heading">DOMContentLoaded</h3>



<p>readystatechange と似た働きをもつ物に <strong>DOMContentLoaded</strong> イベントがありますが、 DOMContentLoaded をサポートしていないブラウザ、例えばIE8以下向けのフォールバックとして readystatechange が使用されたりします。</p>



<p>ごくシンプルに書くと、このような処理をする事になります。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> initialize = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
    <span class="hljs-built_in">console</span>.log(<span class="hljs-string">"ready"</span>);
    <span class="hljs-comment">// アプリケーションの初期化...</span>
};

<span class="hljs-keyword">var</span> domReadyHandler = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">e</span>)</span>{
    <span class="hljs-keyword">if</span>(e.type === <span class="hljs-string">"DOMContentLoaded"</span>){
        <span class="hljs-built_in">document</span>.removeEventListener(<span class="hljs-string">"DOMContentLoaded"</span>, domReadyHandler);
    } <span class="hljs-keyword">else</span> {
        <span class="hljs-keyword">if</span>(<span class="hljs-built_in">document</span>.readyState !== <span class="hljs-string">"complete"</span>){ <span class="hljs-keyword">return</span>; }
        <span class="hljs-built_in">document</span>.detachEvent(<span class="hljs-string">"onreadystatechange"</span>, domReadyHandler);
        <span class="hljs-built_in">window</span>.detachEvent(<span class="hljs-string">"onload"</span>, domReadyHandler);
    }
    initialize();
};

<span class="hljs-keyword">if</span>(<span class="hljs-string">"addEventListener"</span> <span class="hljs-keyword">in</span> <span class="hljs-built_in">document</span>){
    <span class="hljs-built_in">document</span>.addEventListener(<span class="hljs-string">"DOMContentLoaded"</span>, domReadyHandler, <span class="hljs-literal">false</span>);
} <span class="hljs-keyword">else</span> <span class="hljs-keyword">if</span>(<span class="hljs-string">"attachEvent"</span> <span class="hljs-keyword">in</span> <span class="hljs-built_in">document</span>){
    <span class="hljs-built_in">document</span>.attachEvent(<span class="hljs-string">"onreadystatechange"</span>, domReadyHandler);
    <span class="hljs-built_in">window</span>.attachEvent(<span class="hljs-string">"onload"</span>, domReadyHandler);
}
</code></span></pre>


<p>DOMContentLoaded の代替として readystatechange の &#8220;complete&#8221; のタイミングで処理を行います。 環境の判別に &#8220;addEventListener&#8221; の有無を使用していますが、 これはたまたま DOMContentLoaded のサポート環境と被っていた為です。 （DOMContentLoaded は document.ondomcontentloaded として参照できない為、イベントのサポートの有無で判別しようとすると冗長になってしまいます）</p>



<p>フレーム内コンテンツなどを考慮するとさらに長いコードになりますが、 下記リンクにて詳細に説明されています。</p>



<ul class="wp-block-list">
<li><a href="https://github.com/addyosmani/jquery.parts/blob/master/jquery.documentReady.js">https://github.com/addyosmani/jquery.parts/blob/master/jquery.documentReady.js</a></li>
</ul>



<h2 class="wp-block-heading">document 以外での readyState</h2>



<p>IE10以下に限っては document 以外にも、img要素やscript要素で readyState が使えます。 従来のIEでは script 要素の onload イベントが使用出来なかった為、 スクリプトローダー等ではこれをフォールバックとして使用していたりします。</p>



<p>例えば、複数のスクリプトを動的・同期的に読み込んで実行したいケースでは、 script 要素の async を false にすれば想定する動きをしてくれます。</p>



<blockquote class="wp-block-quote is-layout-flow wp-block-quote-is-layout-flow">
<p><strong><a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/script">https://developer.mozilla.org/en-US/docs/Web/HTML/Element/script</a></strong><br />
  Set this Boolean attribute to indicate that the browser should, if possible, execute the script asynchronously&#8230;</p>
</blockquote>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> loadSync = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">resources</span>)</span>{
    resources.forEach(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">name</span>)</span>{
        <span class="hljs-keyword">var</span> script = <span class="hljs-built_in">document</span>.createElement(<span class="hljs-string">"script"</span>);
        script.async = <span class="hljs-literal">false</span>;
        script.src = name;
        <span class="hljs-built_in">document</span>.getElementsByTagName(<span class="hljs-string">"head"</span>)&#91;<span class="hljs-number">0</span>].appendChild(script);
    });
};

loadSync(&#91;<span class="hljs-string">"jquery.js"</span>, <span class="hljs-string">"underscore.js"</span>, <span class="hljs-string">"backbone.js"</span>, <span class="hljs-string">"main.js"</span>]);
</code></span></pre>


<p>しかし async 属性はIE8以下ではサポートされていない為、 readystatechange イベントでスクリプトのロード状況を監視し、 読み込みが完了した時点でDOMに挿入する事で再現してみます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">// async がサポートしているかを確認</span>
<span class="hljs-keyword">var</span> supportAsync = <span class="hljs-string">"async"</span> <span class="hljs-keyword">in</span> <span class="hljs-built_in">document</span>.createElement(<span class="hljs-string">"script"</span>);

<span class="hljs-keyword">var</span> loadSync = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">resources</span>)</span>{
    <span class="hljs-keyword">var</span> nodes = &#91;];
    <span class="hljs-keyword">var</span> count = resources.length;
    <span class="hljs-keyword">var</span> head = <span class="hljs-built_in">document</span>.getElementsByTagName(<span class="hljs-string">"head"</span>)&#91;<span class="hljs-number">0</span>];

    <span class="hljs-keyword">var</span> process = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params"></span>)</span>{
        <span class="hljs-keyword">if</span>(<span class="hljs-keyword">this</span>.readyState === <span class="hljs-string">"loaded"</span>){ count--; }
        <span class="hljs-keyword">if</span>(! count){
            nodes.forEach(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">node</span>)</span>{
                node.onreadystatechange = <span class="hljs-literal">null</span>;
                head.appendChild(node);
            });
        }
    };

    <span class="hljs-keyword">var</span> createNode = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">src</span>)</span>{
        <span class="hljs-keyword">var</span> node = <span class="hljs-built_in">document</span>.createElement(<span class="hljs-string">"script"</span>);
        <span class="hljs-keyword">if</span>(supportAsync){
            node.async = <span class="hljs-literal">false</span>;
            node.src = src;
            head.appendChild(node);
        } <span class="hljs-keyword">else</span> {
            node.onreadystatechange = process;
            node.src = src;
        }
        <span class="hljs-keyword">return</span> node;
    };

    <span class="hljs-comment">// forEach が polyfill で定義されている前提</span>
    resources.forEach(<span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">name</span>)</span>{
        nodes.push(createNode(name));
    });
};

loadSync(&#91;<span class="hljs-string">"jquery.js"</span>, <span class="hljs-string">"underscore.js"</span>, <span class="hljs-string">"backbone.js"</span>, <span class="hljs-string">"main.js"</span>]);
</code></span></pre>


<p>IE11からは script要素の readyState は使えなくなり、load イベントの使用が推奨されています。</p>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="https://developer.mozilla.org/ja/docs/DOM/document.readyState">document.readyState &#8211; DOM | MDN</a></li>



<li><a href="https://developer.mozilla.org/en-US/docs/Web/HTML/Element/script">script &#8211; HTML | MDN</a></li>



<li><a href="http://msdn.microsoft.com/en-us/library/ie/ms534359(v=vs.85).aspx">readyState property (Internet Explorer)</a></li>



<li><a href="http://msdn.microsoft.com/en-us/library/ie/bg182625(v=vs.85).aspx">Compatibility changes in IE11 (Windows)</a></li>



<li><a href="https://github.com/addyosmani/jquery.parts/blob/master/jquery.documentReady.js">jquery.parts/jquery.documentReady.js at master · addyosmani/jquery.parts</a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>&#034;querySelector&#034; &#8211; Alphabetical Advent Calendar 2013</title>
		<link>https://blog.mach3.jp/2013/12/16/jaac2013-q-queryselector.html</link>
		
		<dc:creator><![CDATA[mach3]]></dc:creator>
		<pubDate>Mon, 16 Dec 2013 01:57:03 +0000</pubDate>
				<category><![CDATA[Laboratory]]></category>
		<category><![CDATA[Advent Calendar 2013]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jQuery]]></category>
		<category><![CDATA[querySelector]]></category>
		<category><![CDATA[Sizzle]]></category>
		<guid isPermaLink="false">http://blog.mach3.jp/?p=3741</guid>

					<description><![CDATA[&#8220;Q&#8221; は querySelector の &#8220;Q&#8221;。 querySelector / querySelectorAll querySelector / querySelec [&#8230;]]]></description>
										<content:encoded><![CDATA[
<p>&#8220;Q&#8221; は querySelector の &#8220;Q&#8221;。</p>



<figure class="wp-block-image"><img decoding="async" src="https://lh4.googleusercontent.com/-D1beID9BBbY/UqR4klzFRzI/AAAAAAAACYg/rJ8BHc8ogu0/s400/ac2013-q.png" alt="Q"/></figure>



<p></p>



<span id="more-3741"></span>



<h2 class="wp-block-heading">querySelector / querySelectorAll</h2>



<p><strong>querySelector</strong> / <strong>querySelectorAll</strong> は、&#8221;#container .section&#8221; のようなCSSのセレクタで要素を絞り込んで取得する為のAPIです。 旧来jQuery等で使われていた要素の取得がネイティブのAPIとして実装されたと考えれば、特に難しいことはないですね。 IEは8以降でこの機能をサポートしていますが、IE8ではCSS2のセレクタのみ使用可能となっています。</p>



<p>querySelector[All] は document から呼び出して使用します。</p>


<pre class="wp-block-code"><span><code class="hljs language-css"><span class="hljs-selector-tag">document</span><span class="hljs-selector-class">.querySelector</span>("<span class="hljs-selector-id">#container</span> <span class="hljs-selector-class">.section</span>");
<span class="hljs-selector-tag">document</span><span class="hljs-selector-class">.querySelectorAll</span>("<span class="hljs-selector-id">#container</span> <span class="hljs-selector-class">.section</span>");
</code></span></pre>


<p>両者の違いは取得する要素の数です。 querySelector は条件に合致した最初の要素だけを返し、 querySelectorAll は合致した全ての物を返します。</p>


<pre class="wp-block-code"><span><code class="hljs language-xml"><span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">id</span>=<span class="hljs-string">"container"</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">class</span>=<span class="hljs-string">"section section-01"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">class</span>=<span class="hljs-string">"section section-02"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
    <span class="hljs-tag">&lt;<span class="hljs-name">div</span> <span class="hljs-attr">class</span>=<span class="hljs-string">"section section-03"</span>&gt;</span><span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
<span class="hljs-tag">&lt;/<span class="hljs-name">div</span>&gt;</span>
<span class="hljs-tag">&lt;<span class="hljs-name">script</span>&gt;</span><span class="javascript">
    <span class="hljs-keyword">var</span> firstSection = <span class="hljs-built_in">document</span>.querySelector(<span class="hljs-string">"#container .section"</span>); <span class="hljs-comment">// HTMLDivElement</span>
    <span class="hljs-keyword">var</span> allSections = <span class="hljs-built_in">document</span>.querySelectorAll(<span class="hljs-string">"#container .section"</span>); <span class="hljs-comment">// NodeList</span>
</span><span class="hljs-tag">&lt;/<span class="hljs-name">script</span>&gt;</span>
</code></span></pre>


<p>querySelectorAll で返される <strong>NodeList</strong> は Arrayライクなオブジェクトで、 配列のように添字で取得できるほか、インデックスで要素を返す <strong>item()</strong> メソッドが使用できます。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-comment">// これらは同じ要素を返します</span>
allSections&#91;<span class="hljs-number">0</span>];
allSections.item(<span class="hljs-number">0</span>);
</code></span></pre>


<h3 class="wp-block-heading">他の要素取得系APIと比べて</h3>



<p>要素の取得と言えば、<strong>getElementById</strong> / <strong>getElementsByClassName</strong> / <strong>getElementsByTagName</strong> がありますが、 想像に難くないようにこれらの方が高速な為、場面による使い分けが大切です。</p>



<p>使い分けが面倒、あるいは毎度 <strong>document&#8230;</strong> と書くのが鬱陶しい場合は、 セレクタから判別して処理する関数を書いてみても良いかもしれません。</p>


<pre class="wp-block-code"><span><code class="hljs language-javascript"><span class="hljs-keyword">var</span> _query = <span class="hljs-function"><span class="hljs-keyword">function</span>(<span class="hljs-params">selector</span>)</span>{
    <span class="hljs-keyword">var</span> nodes;
    <span class="hljs-keyword">if</span>(<span class="hljs-regexp">/^#&#91;\w\-]+$/</span>.test(selector)){
        <span class="hljs-keyword">return</span> &#91;<span class="hljs-built_in">document</span>.getElementById(
            selector.replace(<span class="hljs-regexp">/^#/</span>, <span class="hljs-string">""</span>)
        )];
    }
    <span class="hljs-keyword">if</span>(<span class="hljs-regexp">/^\.&#91;\w\-]+$/</span>.test(selector)){
        nodes = <span class="hljs-built_in">document</span>.getElementsByClassName(
            selector.replace(<span class="hljs-regexp">/^\./</span>, <span class="hljs-string">""</span>)
        );
    } <span class="hljs-keyword">else</span> <span class="hljs-keyword">if</span>((<span class="hljs-regexp">/^&#91;a-z]+$/i</span>).test(selector)) {
        nodes = <span class="hljs-built_in">document</span>.getElementsByTagName(selector);
    } <span class="hljs-keyword">else</span> {
        <span class="hljs-keyword">try</span> {
            nodes = <span class="hljs-built_in">document</span>.querySelectorAll(selector);
        } <span class="hljs-keyword">catch</span>(e){
            nodes = &#91;];
        }
    }
    <span class="hljs-keyword">return</span> &#91;].slice.call(nodes);
};
_query(<span class="hljs-string">"#container"</span>); <span class="hljs-comment">// Array</span>
_query(<span class="hljs-string">".section"</span>); <span class="hljs-comment">// Array</span>
_query(<span class="hljs-string">"div"</span>); <span class="hljs-comment">// Array</span>
_query(<span class="hljs-string">"#container .section"</span>); <span class="hljs-comment">// Array</span>
</code></span></pre>


<p>ここで使われる id や class の文字については半角英数字とハイフン/アンダースコアのみに絞っています。 ついでに、forEach などが使えるように NodeList から配列に変換しています。</p>



<p>ただ、この場合は正規表現などのコストで有り難みが半減するかもしれません。</p>



<h3 class="wp-block-heading">jQuery（Sizzle）と比べて</h3>



<p>jQueryの独自のセレクタは要素を1つずつ検証していく為、やはりネイティブの querySelector に比べて速度が落ちてしまいます。 そのためjQueryは、</p>



<ol class="wp-block-list">
<li>id や class やタグ名を渡された場合はそれに相応しいネイティブAPIを使用し、</li>



<li>ブラウザが querySelector が対応しているかどうかをチェックし、</li>



<li>querySelector で正常に解釈できるセレクタであるかどうかのテストを行い、</li>



<li>失敗した場合（例えばjQuery独自の記法が使用されていた場合）に自分のAPIを使用して要素を抽出する</li>
</ol>



<p>こんな感じのプロセスを踏んでいる様です。</p>



<p>つまりjQueryを使用する場合でも、まずは id や class で絞込み、 それに対して .find() などでフィルタリングする事で速度が改善しそうですね。</p>



<p>こちらで詳しく説明されています。</p>



<ul class="wp-block-list">
<li><a href="http://73log.jp/jquery-selector-speed/">jQueryのセレクタ高速化について | JavaScript | 73log.jp</a></li>
</ul>



<h2 class="wp-block-heading">参考資料</h2>



<ul class="wp-block-list">
<li><a href="https://developer.mozilla.org/ja/docs/Web/API/document.querySelector">document.querySelector &#8211; Web API リファレンス | MDN</a></li>



<li><a href="https://developer.mozilla.org/ja/docs/Web/API/document.querySelectorAll">document.querySelectorAll &#8211; Web API リファレンス | MDN</a></li>



<li><a href="http://73log.jp/jquery-selector-speed/">jQueryのセレクタ高速化について | JavaScript | 73log.jp</a></li>
</ul>
]]></content:encoded>
					
		
		
			</item>
	</channel>
</rss>
