<?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>へびにっき &#187; JavaScript</title>
	<atom:link href="http://wp.serpere.info/archives/tag/javascript/feed" rel="self" type="application/rss+xml" />
	<link>http://wp.serpere.info</link>
	<description>樹上で暮らすヘビのように生きたい</description>
	<lastBuildDate>Thu, 09 Feb 2012 11:35:51 +0000</lastBuildDate>
	<language>ja</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>doScrollによるDOMContentLoadedエミュレーションの落とし穴</title>
		<link>http://wp.serpere.info/archives/2454</link>
		<comments>http://wp.serpere.info/archives/2454#comments</comments>
		<pubDate>Thu, 24 Nov 2011 15:26:42 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=2454</guid>
		<description><![CDATA[今更こんなことが問題になるケースは稀だと思うが、『パーフェクトJavaScript』の中でも紹介されていたので注意として書いておく。 IE8以前でDOMContentLoadedイベントをエミュレートする方法として、doScrollを使ったハックは広く知られている。例として『パーフェクトJavaScript』230ページのリスト8.9より引用。 function IEContentLoaded &#40;callback&#41; &#123; &#40;function &#40;&#41; &#123; try &#123; document.documentElement.doScroll&#40;'left'&#41;; &#125; catch &#40;error&#41; &#123; setTimeout&#40;arguments.callee, 0&#41;; return; &#125; callback&#40;&#41;; &#125;&#41;&#40;&#41;; &#125; しかし実際に試してみればわかるが、これだとwindow.onloadより実行が遅くなる場合がある。 テスト1（画像なし） テスト2（画像あり） 具体的には 画像など外部から読み込まれるリソースが少ない場合 リロードした時にキャッシュがきいている場合 こういったケースではwindow.onloadとdoScrollハックの実行順序は逆転する場合がある。もちろん逆転しない場合もある。doScrollハックはあくまでハックであって正式なイベントシステムの一部ではないのだから、一貫した動作をしなくても当然だと言える。 この実行順序の逆転を防ぐために、世の中のライブラリではdocument.onreadystatechangeイベントを併用するのが習わしとなっている。例えばdoScrollハックを世に広めたDiego Perini氏の実装を見れば、trying to always fire before onload というコメントとともにreadyStateをチェックするコードが入っているのが分かる。 document.onreadystatechange = function&#40;&#41; &#123; if &#40;document.readyState == 'complete'&#41; &#123; //コールバック関数を実行し、以後はdoScrollハックが動かないようにしておく &#125; &#125;; テスト1（画像なし） テスト2（画像あり） 現実問題としては、わざわざ自前でdoScrollハックを書くような状況では、この順序の逆転が問題になることはまずないと思われる。しかし以下のような教訓を読み取ることはできるだろう: 広く知られていようがハックはハック。使うときは慎重になろう 可能な限り信頼できる既存の実装を使おう [...]]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F2454%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2FuQBkxp%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22doScroll%E3%81%AB%E3%82%88%E3%82%8BDOMContentLoaded%E3%82%A8%E3%83%9F%E3%83%A5%E3%83%AC%E3%83%BC%E3%82%B7%E3%83%A7%E3%83%B3%E3%81%AE%E8%90%BD%E3%81%A8%E3%81%97%E7%A9%B4%22%20%7D);"></div>
<p>
今更こんなことが問題になるケースは稀だと思うが、『<a href="http://www.amazon.co.jp/%E3%83%91%E3%83%BC%E3%83%95%E3%82%A7%E3%82%AF%E3%83%88JavaScript-PERFECT-4-%E4%BA%95%E4%B8%8A-%E8%AA%A0%E4%B8%80%E9%83%8E/dp/477414813X%3FSubscriptionId%3DAKIAJUX5XJO3NQFNQ4TQ%26tag%3Dhebinikki09-22%26linkCode%3Dxm2%26camp%3D2025%26creative%3D165953%26creativeASIN%3D477414813X">パーフェクトJavaScript</a>』の中でも紹介されていたので注意として書いておく。
</p>
<p>
IE8以前でDOMContentLoadedイベントをエミュレートする方法として、doScrollを使ったハックは広く知られている。例として『パーフェクトJavaScript』230ページのリスト8.9より引用。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> IEContentLoaded <span style="color: #009900;">&#40;</span>callback<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span> <span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000066; font-weight: bold;">try</span> <span style="color: #009900;">&#123;</span>
            document.<span style="color: #660066;">documentElement</span>.<span style="color: #660066;">doScroll</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'left'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span> <span style="color: #000066; font-weight: bold;">catch</span> <span style="color: #009900;">&#40;</span>error<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            setTimeout<span style="color: #009900;">&#40;</span>arguments.<span style="color: #660066;">callee</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">0</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            <span style="color: #000066; font-weight: bold;">return</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
        callback<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>



<p>
しかし実際に試してみればわかるが、これだとwindow.onloadより実行が遅くなる場合がある。
</p>
<p>
<a href="http://www.serpere.info/doscroll/loadtest.php">テスト1（画像なし）</a> <a href="http://www.serpere.info/doscroll/loadtest.php/naive_image">テスト2（画像あり）</a>
</p>
<p>
具体的には
</p>
<ul>
<li>画像など外部から読み込まれるリソースが少ない場合</li>
<li>リロードした時にキャッシュがきいている場合</li>
</ul>
<p>
こういったケースではwindow.onloadとdoScrollハックの実行順序は逆転する場合がある。もちろん逆転しない場合もある。doScrollハックはあくまでハックであって正式なイベントシステムの一部ではないのだから、一貫した動作をしなくても当然だと言える。
</p>
<p>
この実行順序の逆転を防ぐために、世の中のライブラリではdocument.onreadystatechangeイベントを併用するのが習わしとなっている。例えばdoScrollハックを世に広めた<a href="http://javascript.nwbox.com/IEContentLoaded/iecontentloaded.js">Diego Perini氏の実装</a>を見れば、<q>trying to always fire before onload</q> というコメントとともにreadyStateをチェックするコードが入っているのが分かる。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">document.<span style="color: #660066;">onreadystatechange</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>document.<span style="color: #660066;">readyState</span> <span style="color: #339933;">==</span> <span style="color: #3366CC;">'complete'</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #006600; font-style: italic;">//コールバック関数を実行し、以後はdoScrollハックが動かないようにしておく</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
<a href="http://www.serpere.info/doscroll/loadtest.php/correct_text">テスト1（画像なし）</a> <a href="http://www.serpere.info/doscroll/loadtest.php/correct_image">テスト2（画像あり）</a>
</p>
<p>
現実問題としては、わざわざ自前でdoScrollハックを書くような状況では、この順序の逆転が問題になることはまずないと思われる。しかし以下のような教訓を読み取ることはできるだろう:
</p>
<ul>
<li>広く知られていようがハックはハック。使うときは慎重になろう</li>
<li>可能な限り信頼できる既存の実装を使おう</li>
<li>自分の手で実験しよう</li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/2454/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>jQuery 1.5の新機能: jQueryのサブクラスが作れるようになる</title>
		<link>http://wp.serpere.info/archives/2050</link>
		<comments>http://wp.serpere.info/archives/2050#comments</comments>
		<pubDate>Sun, 16 Jan 2011 16:19:21 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jquery]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=2050</guid>
		<description><![CDATA[jQuery 1.5 beta1 のリリースノートを見ていたら面白そうな機能があったので紹介。 1.5正式版では jQuery.sub という名称に変更になったので、本文およびサンプルコードを修正しました。 jQuery.sub() でjQueryのサブクラスを作ることができる var MyjQuery = jQuery.sub&#40;&#41;; 作成したサブクラスには独自のメソッドを定義することができる。定義の仕方、使い方は通常のjQueryと全く同じ。 MyjQuery.fn.writeHello = function&#40;&#41;&#123; this.text&#40;'Hello World'&#41;; &#125;; &#160; MyjQuery&#40;'p'&#41;.writeHello&#40;&#41;; 通常のjQueryメソッドはサブクラスでもそのまま使える。サブクラスを作った後に追加したメソッドも使えるので、プラグインによる拡張と組み合わせても大丈夫。 MyjQuery&#40;'div'&#41;.css&#40;'border', '1px red solid'&#41;.writeHello&#40;&#41;; &#160; //元のjQueryを拡張 jQuery.fn.pluginMethod = function&#40;&#41;&#123; alert&#40;'OK'&#41;; &#125;; &#160; //OK MyjQuery&#40;'.klass'&#41;.pluginMethod&#40;&#41;; 逆にサブクラスで追加したメソッドは元のjQueryからは見えないので、プロジェクトやプラグインに固有なメソッドを定義したり、元のjQueryにあるメソッドを上書きしたりといったことが安全にできる。 // text メソッドを上書きする MyjQuery.fn.text = function&#40;val&#41; &#123; var orig = jQuery.fn.text; if&#40;typeof val === &#34;string&#34;&#41; &#123; return [...]]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F2050%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2FeYby46%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22jQuery%201.5%E3%81%AE%E6%96%B0%E6%A9%9F%E8%83%BD%3A%20jQuery%E3%81%AE%E3%82%B5%E3%83%96%E3%82%AF%E3%83%A9%E3%82%B9%E3%81%8C%E4%BD%9C%E3%82%8C%E3%82%8B%E3%82%88%E3%81%86%E3%81%AB%E3%81%AA%E3%82%8B%22%20%7D);"></div>
<p>
jQuery 1.5 beta1 の<a href="http://blog.jquery.com/2011/01/14/jquery-1-5-beta-1-released/">リリースノート</a>を見ていたら面白そうな機能があったので紹介。
</p>
<p>
<ins datetime="2011-02-08T01:15:29+00:00">1.5正式版では <a href="http://api.jquery.com/jQuery.sub/">jQuery.sub</a> という名称に変更になったので、本文およびサンプルコードを修正しました。</ins>
</p>
<h3>jQuery.sub() でjQueryのサブクラスを作ることができる</h3>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">var</span> MyjQuery <span style="color: #339933;">=</span> jQuery.<span style="color: #660066;">sub</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
作成したサブクラスには独自のメソッドを定義することができる。定義の仕方、使い方は通常のjQueryと全く同じ。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">MyjQuery.<span style="color: #660066;">fn</span>.<span style="color: #660066;">writeHello</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> <span style="color: #000066; font-weight: bold;">this</span>.<span style="color: #660066;">text</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'Hello World'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
&nbsp;
MyjQuery<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'p'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">writeHello</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
通常のjQueryメソッドはサブクラスでもそのまま使える。サブクラスを作った後に追加したメソッドも使えるので、プラグインによる拡張と組み合わせても大丈夫。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">MyjQuery<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'div'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">css</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'border'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'1px red solid'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">writeHello</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//元のjQueryを拡張</span>
jQuery.<span style="color: #660066;">fn</span>.<span style="color: #660066;">pluginMethod</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'OK'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//OK</span>
MyjQuery<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'.klass'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">pluginMethod</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
逆にサブクラスで追加したメソッドは元のjQueryからは見えないので、プロジェクトやプラグインに固有なメソッドを定義したり、元のjQueryにあるメソッドを上書きしたりといったことが安全にできる。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">// text	メソッドを上書きする</span>
MyjQuery.<span style="color: #660066;">fn</span>.<span style="color: #660066;">text</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>val<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
  <span style="color: #003366; font-weight: bold;">var</span> orig <span style="color: #339933;">=</span> jQuery.<span style="color: #660066;">fn</span>.<span style="color: #660066;">text</span><span style="color: #339933;">;</span>
  <span style="color: #000066; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">typeof</span> val <span style="color: #339933;">===</span> <span style="color: #3366CC;">&quot;string&quot;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">return</span> orig.<span style="color: #660066;">call</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">this</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">&quot;!!&quot;</span><span style="color: #339933;">+</span> val <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;!!&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
  <span style="color: #009900;">&#125;</span> <span style="color: #000066; font-weight: bold;">else</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">return</span> orig.<span style="color: #660066;">apply</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">this</span><span style="color: #339933;">,</span> arguments<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
  <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">// 上書きされたtextを呼び出す</span>
MyjQuery<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'#ex'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">text</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;foo&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">// 引数を与えなければ元のメソッドが呼ばれる</span>
MyjQuery<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'#ex'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">text</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>	<span style="color: #006600; font-style: italic;">//!!foo!!</span>
&nbsp;
<span style="color: #006600; font-style: italic;">// もちろん元のメソッドには影響ない</span>
jQuery<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'#ex'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">text</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'foo'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">//foo</span></pre></div></div>



<p>
さらに応用として、プラグインで拡張メソッドを提供する場合の名前空間としても使えるかもしれない。例えば私が前に作った<a href="http://wp.serpere.info/archives/1096">動的にSELECTを構築するためのjQueryプラグイン</a>は、グローバルなメソッド空間に2つのメソッドを追加してしまうのであまりマナーが良くない。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">addOption</span><span style="color: #009900;">&#40;</span>...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">clearOptions</span><span style="color: #009900;">&#40;</span>...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//本当は次のようにしたいが、動作しない</span>
$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">optionBuilder</span>.<span style="color: #660066;">addOption</span><span style="color: #009900;">&#40;</span>...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">optionBuilder</span>.<span style="color: #660066;">clearOptions</span><span style="color: #009900;">&#40;</span>...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//次のような実装が推奨されている</span>
$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">optionBuilder</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'addOption'</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">optionBuilder</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'clearOptions'</span><span style="color: #339933;">,</span> ...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
1.5のサブクラス機能を使えば、次のように隔離されたサブクラスでのみ使用可能なメソッドとして提供することができる。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">//サブクラスを使えば直接呼び出せる</span>
<span style="color: #003366; font-weight: bold;">var</span> optionBuilder <span style="color: #339933;">=</span> jQuery.<span style="color: #660066;">optionBuilder</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
optionBuilder<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">addOption</span><span style="color: #009900;">&#40;</span>...<span style="color: #009900;">&#41;</span>
optionBuilder<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">clearOptions</span><span style="color: #009900;">&#40;</span>...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//関数の中に隔離する方法も</span>
jQuery.<span style="color: #660066;">optionBuilder</span><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>$<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    $<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">addOption</span><span style="color: #009900;">&#40;</span>...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    $<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'select'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">clearOptions</span><span style="color: #009900;">&#40;</span>...<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
実装は次のような感じになるだろう。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">/*
 * jQuery.optionBuilder.fn[method](...);
 * を
 * jQuery.fn.optionBuilder(method, ...);
 * にマップする
 */</span>
jQuery.<span style="color: #660066;">optionBuilder</span> <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
  <span style="color: #003366; font-weight: bold;">var</span> sub <span style="color: #339933;">=</span> jQuery.<span style="color: #660066;">sub</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span>
      base <span style="color: #339933;">=</span> jQuery.<span style="color: #660066;">fn</span>.<span style="color: #660066;">optionBuilder</span><span style="color: #339933;">,</span>
      slice <span style="color: #339933;">=</span> Array.<span style="color: #660066;">prototype</span>.<span style="color: #660066;">slice</span><span style="color: #339933;">,</span>
      methods <span style="color: #339933;">=</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">'addOption'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'clearOptions'</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">;</span>
&nbsp;
  $.<span style="color: #660066;">each</span><span style="color: #009900;">&#40;</span>methods<span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>i<span style="color: #339933;">,</span> method<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    sub.<span style="color: #660066;">fn</span><span style="color: #009900;">&#91;</span>method<span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
      <span style="color: #000066; font-weight: bold;">return</span> base.<span style="color: #660066;">apply</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">this</span><span style="color: #339933;">,</span> <span style="color: #009900;">&#91;</span>method<span style="color: #009900;">&#93;</span>.<span style="color: #660066;">concat</span><span style="color: #009900;">&#40;</span>slice.<span style="color: #660066;">call</span><span style="color: #009900;">&#40;</span>arguments<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
  <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
  <span style="color: #000066; font-weight: bold;">return</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>fn<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">typeof</span> fn <span style="color: #339933;">===</span> <span style="color: #3366CC;">'function'</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
      <span style="color: #000066; font-weight: bold;">return</span> fn<span style="color: #009900;">&#40;</span>sub<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
    <span style="color: #000066; font-weight: bold;">return</span> sub<span style="color: #339933;">;</span>
  <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>参考:</p>
<ul>
<li><a href="https://github.com/deadlyicon/jquery/commit/4024e67d0f352e4a095f93456bc8e6da63e10759">Commit 4024e67d0f352e4a095f93456bc8e6da63e10759 to deadlyicon&#8217;s jquery &#8211; GitHub</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/2050/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Functionコンストラクタと関数式（function expression）の違いなど</title>
		<link>http://wp.serpere.info/archives/2022</link>
		<comments>http://wp.serpere.info/archives/2022#comments</comments>
		<pubDate>Thu, 06 Jan 2011 08:25:15 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[読書]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=2022</guid>
		<description><![CDATA[JavaScript Patterns 2章ではevalの代替としてFunctionコンストラクタを使う方法が紹介されています。Functionコンストラクタは、普通にJavaScriptを書いている分にはなかなか使うことがないので、馴染みがない人も多いだろうと思います。そこで関数式との比較を中心に簡単にまとめておきます。 Functionコンストラクタは、関数オブジェクト（つまりJavaScriptにおける関数）を作るためのコンストラクタです。文字列をJavaScriptコードとして扱えるという点ではevalにも似ていますが、戻り値は普通の関数なので、その他の方法で作った関数と全く同じ使い方ができます。 var funcObj = new Function&#40;'x', 'y', 'console.log(x + y);'&#41;; &#160; //普通に呼び出す funcObj&#40;1,2&#41;; // 3 &#160; //コンストラクタとして使ってみる funcObj.prototype.hello = function&#40;&#41;&#123; console.log&#40;'World'&#41;; &#125;; &#40;new funcObj&#40;4,5&#41;&#41;.hello&#40;&#41;; // 'World' ちなみにコンストラクタではなく関数として呼び出した場合は、コンストラクタとして呼び出した場合と同じ結果になります（仕様上そう規定されています）。よって以下の2つは同じ意味になります。 var funcObj1 = Function&#40;'x', 'y', 'console.log(x + y);'&#41;, funcObj2 = new Function&#40;'x', 'y', 'console.log(x + y);'&#41;; この形、関数式にnew演算子を適用した場合と見た目が似ていますが、全く意味が違うということに注意してください。 // 関数式で関数を作る var funcObj = function&#40;&#41;&#123;&#125; &#160; // [...]]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F2022%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2FgOvhDy%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22Function%E3%82%B3%E3%83%B3%E3%82%B9%E3%83%88%E3%83%A9%E3%82%AF%E3%82%BF%E3%81%A8%E9%96%A2%E6%95%B0%E5%BC%8F%EF%BC%88function%20expression%EF%BC%89%E3%81%AE%E9%81%95%E3%81%84%E3%81%AA%E3%81%A9%22%20%7D);"></div>
<p><a href="http://www.amazon.co.jp/JavaScript-Patterns-Stoyan-Stefanov/dp/0596806752%3FSubscriptionId%3DAKIAJUX5XJO3NQFNQ4TQ%26tag%3Dhebinikki09-22%26linkCode%3Dxm2%26camp%3D2025%26creative%3D165953%26creativeASIN%3D0596806752"><img class="alignleft" src="http://ecx.images-amazon.com/images/I/51mh1TB0n4L._SL160_.jpg" alt="" width="122" height="160" /></a></p>
<p><a href="http://www.amazon.co.jp/JavaScript-Patterns-Stoyan-Stefanov/dp/0596806752%3FSubscriptionId%3DAKIAJUX5XJO3NQFNQ4TQ%26tag%3Dhebinikki09-22%26linkCode%3Dxm2%26camp%3D2025%26creative%3D165953%26creativeASIN%3D0596806752">JavaScript Patterns</a> 2章ではevalの代替としてFunctionコンストラクタを使う方法が紹介されています。Functionコンストラクタは、普通にJavaScriptを書いている分にはなかなか使うことがないので、馴染みがない人も多いだろうと思います。そこで関数式との比較を中心に簡単にまとめておきます。</p>
<p>Functionコンストラクタは、関数オブジェクト（つまりJavaScriptにおける関数）を作るためのコンストラクタです。文字列をJavaScriptコードとして扱えるという点ではevalにも似ていますが、戻り値は普通の関数なので、その他の方法で作った関数と全く同じ使い方ができます。</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">var</span> funcObj <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">new</span> <span style="color: #003366; font-weight: bold;">Function</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'x'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'y'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'console.log(x + y);'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//普通に呼び出す</span>
funcObj<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">1</span><span style="color: #339933;">,</span><span style="color: #CC0000;">2</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// 3</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//コンストラクタとして使ってみる</span>
funcObj.<span style="color: #660066;">prototype</span>.<span style="color: #660066;">hello</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'World'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">new</span> funcObj<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">4</span><span style="color: #339933;">,</span><span style="color: #CC0000;">5</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">hello</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// 'World'</span></pre></div></div>



<p>ちなみにコンストラクタではなく関数として呼び出した場合は、コンストラクタとして呼び出した場合と同じ結果になります（仕様上そう規定されています）。よって以下の2つは同じ意味になります。</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">var</span> funcObj1 <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">Function</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'x'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'y'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'console.log(x + y);'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span>
    funcObj2 <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">new</span> <span style="color: #003366; font-weight: bold;">Function</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'x'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'y'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'console.log(x + y);'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>この形、関数式にnew演算子を適用した場合と見た目が似ていますが、全く意味が違うということに注意してください。</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">// 関数式で関数を作る</span>
<span style="color: #003366; font-weight: bold;">var</span> funcObj <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span><span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">// 関数式で作った関数をコンストラクタとして呼び出す</span>
<span style="color: #003366; font-weight: bold;">var</span> newlyCreatedObject <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">new</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span></pre></div></div>



<h3>varの解釈について</h3>
<p>Functionコンストラクタで作った関数においても、関数本体の中でvarステートメントを使って宣言した変数はローカル変数になります。</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">var</span> a <span style="color: #339933;">=</span> <span style="color: #CC0000;">100</span><span style="color: #339933;">,</span>
    func1 <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">new</span> <span style="color: #003366; font-weight: bold;">Function</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'var b = 200; return b;'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span>
    func2 <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> <span style="color: #003366; font-weight: bold;">var</span> c <span style="color: #339933;">=</span> <span style="color: #CC0000;">300</span><span style="color: #339933;">;</span> <span style="color: #000066; font-weight: bold;">return</span> c<span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
&nbsp;
console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span>a<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// 100</span>
console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span>func1<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// 200</span>
console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span>func2<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// 300</span>
&nbsp;
console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">typeof</span> b<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">//undefined</span>
console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span><span style="color: #000066; font-weight: bold;">typeof</span> c<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">//undefined</span></pre></div></div>



<p>変数の生成（instantiation）は<strong>関数が呼び出されたときに実行される</strong>プロセスなので、どのような方法で作った関数でも同じです。</p>
<h3>スコープについて</h3>
<p>関数式で作った関数は、関数式の外側のローカル変数を参照できます。しかしFunctionコンストラクタで作った関数はグローバル変数しか参照することができません。</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">//JavaScript Patterns Chapter2の例の改変</span>
<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> local <span style="color: #339933;">=</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> local <span style="color: #339933;">=</span> <span style="color: #CC0000;">3</span><span style="color: #339933;">;</span> console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span>local<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// 3</span>
    console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span>local<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">// 3</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> local <span style="color: #339933;">=</span> <span style="color: #CC0000;">1</span><span style="color: #339933;">;</span>
    <span style="color: #003366; font-weight: bold;">Function</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;console.log(typeof local)&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #006600; font-style: italic;">//undefined</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>言い換えると、関数式で作った関数オブジェクトが「関数式が評価された時点でのスコープの状態」を保持しているのに対し、Functionコンストラクタで作った関数オブジェクトは常にグローバルなスコープしか保持していません。なぜこの差が生じるかというと、単に仕様でそう決まっているからです。関数に保持されるスコープは<strong>関数が作られたときに決定される</strong>ので、関数をどこでどのように作ったかによって結果が変わるということです。そして一度作られたあとは変更されることはありません。</p>
<p>この理屈によって、関数式ではクロージャを作ることができるが、Functionコンストラクタでは作ることができない、ということになります。</p>
<p>全くの余談ですが、クロージャが&#8221;閉じる&#8221;のは、スコープチェーンに組み込まれたActivation Objectがプログラマからは操作不可能だから、という事情によります。よってその他のオブジェクトをスコープチェーンに組み込んでやれば、クロージャと似ているが&#8221;開いた&#8221;関数を作り出すこともできます（役に立つかどうかは不明ですが）。</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">var</span> func<span style="color: #339933;">,</span>
    scope <span style="color: #339933;">=</span> <span style="color: #009900;">&#123;</span><span style="color: #000066;">alert</span><span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>msg<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span>msg<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//スコープチェーンの中にオブジェクトを組み込む</span>
<span style="color: #000066; font-weight: bold;">with</span><span style="color: #009900;">&#40;</span>scope<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    func <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>x<span style="color: #339933;">,</span> y<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span> <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span>x <span style="color: #339933;">+</span> y<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//グローバルのalertは隠蔽されてconsole.logが実行される</span>
func<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">1</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">2</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//scopeのプロパティを削除することでグローバルなalertが実行されるようになる</span>
<span style="color: #000066; font-weight: bold;">delete</span> scope.<span style="color: #000066;">alert</span><span style="color: #339933;">;</span>
func<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">3</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">4</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//再びalertを隠蔽する</span>
scope.<span style="color: #000066;">alert</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
func<span style="color: #009900;">&#40;</span><span style="color: #CC0000;">5</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">6</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>ECMAScript5の用語で言うと、Declarative Environment Recordに関数外部から束縛を追加したり削除したりはできないが、Object Environment Recordならbinding objectを通してそれが可能だということです。</p>
<h3>参照</h3>
<p>仕様書の中で関連する部分は多岐にわたるため、一部のみを挙げておきます。</p>
<ul>
	<li>15.3 Function Objects &#8211; Standard ECMA-262 3rd/5th</li>
	<li>13 Function Definition &#8211; Standard ECMA-262 3rd/5th</li>
</ul>
<p>またこの記事はazuさんのJavaScript Patterns読書記録を踏まえて書かれました。</p>
<ul>
	<li><a href="http://efcl.info/adiary/JavaScriptPatterns/Chapter2Essentials">Chapter 2. Essentials &#8211; prog*sig</a></li>
</ul>

]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/2022/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Google AJAX Feed APIを使って複数のフィードをまとめて表示するjQueryプラグイン</title>
		<link>http://wp.serpere.info/archives/1908</link>
		<comments>http://wp.serpere.info/archives/1908#comments</comments>
		<pubDate>Fri, 03 Dec 2010 08:36:51 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jquery]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=1908</guid>
		<description><![CDATA[Google AJAX Feed APIを使うとJavaScriptだけでRSS/ATOMフィードを読み込むことができますが、標準の機能では「複数のフィードをまとめて」「日付順に（新しい順に）」表示することができないので、jQueryプラグインを作りました。 jquery.googleMultiFeed.js (github) タイマーを使って逐次処理を行っているので、全フィードの読み込みを待つことなく、読み込まれたものから順に表示されていきます。Google AJAX Feed APIの（というよりJSONPの）制約でフィードを並列的に読み込むことはできないのですが、Google側でキャッシュ＆タイムアウト処理が行われているため、多数のフィードを読み込んでもさほどストレスなく表示されるはずです。 jQuery 1.4以上が必要です。jqueryの.jsファイルはscriptタグを使って静的に読み込んでください。どうしても google.load を使う必要がある場合は setOnLoadCallback の中で initGoogleMultiFeed() を呼ぶ必要があります。 &#60;script type=&#34;text/javascript&#34; src=&#34;http://www.google.com/jsapi?key=API_KEY&#34;&#62;&#60;/script&#62; &#60;script type=&#34;text/javascript&#34; src=&#34;http://ajax.googleapis.com/ajax/libs/jquery/1.4/jquery.min.js&#34;&#62;&#60;/script&#62; &#60;script type=&#34;text/javascript&#34; src=&#34;jquery.googleMultiFeed.js&#34;&#62;&#60;/script&#62; &#60;script type=&#34;text/javascript&#34;&#62; //google.load('jquery', '1.4'); &#160; google.setOnLoadCallback(function(){ //jqueryをgoole.loadで読み込む場合のみ必要 //initGoogleMultiFeed(); &#160; $('#feed').googleMultiFeed({ urls: ['http://example.com/rss', 'http://example.net/feed'], numEntries: 5 }); }); &#60;/script&#62; ... &#60;div id=&#34;feed&#34;&#62;&#60;/div&#62; urls パラメータは必須で、読み込みたいフィードのURLを配列として指定します。 numEntries パラメータはオプションで、フィード一つあたりの件数です。 上の例を実行すると http://example.com/rss と [...]]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F1908%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2Fh2lDzl%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22Google%20AJAX%20Feed%20API%E3%82%92%E4%BD%BF%E3%81%A3%E3%81%A6%E8%A4%87%E6%95%B0%E3%81%AE%E3%83%95%E3%82%A3%E3%83%BC%E3%83%89%E3%82%92%E3%81%BE%E3%81%A8%E3%82%81%E3%81%A6%E8%A1%A8%E7%A4%BA%E3%81%99%E3%82%8BjQuery%E3%83%97%E3%83%A9%E3%82%B0%E3%82%A4%E3%83%B3%22%20%7D);"></div>
<p>
<a href="http://code.google.com/intl/ja/apis/ajaxfeeds/documentation/">Google AJAX Feed API</a>を使うとJavaScriptだけでRSS/ATOMフィードを読み込むことができますが、標準の機能では「複数のフィードをまとめて」「日付順に（新しい順に）」表示することができないので、jQueryプラグインを作りました。
</p>
<p>
<a href="https://github.com/tkyk/jquery-googleMultiFeed/raw/master/jquery.googleMultiFeed.js">jquery.googleMultiFeed.js</a> (<a href="https://github.com/tkyk/jquery-googleMultiFeed">github</a>)
</p>
<p>
タイマーを使って逐次処理を行っているので、全フィードの読み込みを待つことなく、読み込まれたものから順に表示されていきます。Google AJAX Feed APIの（というよりJSONPの）制約でフィードを並列的に読み込むことはできないのですが、Google側でキャッシュ＆タイムアウト処理が行われているため、多数のフィードを読み込んでもさほどストレスなく表示されるはずです。
</p>
<p>
jQuery 1.4以上が必要です。jqueryの.jsファイルはscriptタグを使って静的に読み込んでください。どうしても google.load を使う必要がある場合は setOnLoadCallback の中で initGoogleMultiFeed() を呼ぶ必要があります。
</p>


<div class="wp_syntax"><div class="code"><pre class="html4strict" style="font-family:monospace;"><span style="color: #009900;">&lt;<span style="color: #000000; font-weight: bold;">script</span> <span style="color: #000066;">type</span><span style="color: #66cc66;">=</span><span style="color: #ff0000;">&quot;text/javascript&quot;</span> <span style="color: #000066;">src</span><span style="color: #66cc66;">=</span><span style="color: #ff0000;">&quot;http://www.google.com/jsapi?key=API_KEY&quot;</span>&gt;&lt;<span style="color: #66cc66;">/</span><span style="color: #000000; font-weight: bold;">script</span>&gt;</span>
<span style="color: #009900;">&lt;<span style="color: #000000; font-weight: bold;">script</span> <span style="color: #000066;">type</span><span style="color: #66cc66;">=</span><span style="color: #ff0000;">&quot;text/javascript&quot;</span> <span style="color: #000066;">src</span><span style="color: #66cc66;">=</span><span style="color: #ff0000;">&quot;http://ajax.googleapis.com/ajax/libs/jquery/1.4/jquery.min.js&quot;</span>&gt;&lt;<span style="color: #66cc66;">/</span><span style="color: #000000; font-weight: bold;">script</span>&gt;</span>
<span style="color: #009900;">&lt;<span style="color: #000000; font-weight: bold;">script</span> <span style="color: #000066;">type</span><span style="color: #66cc66;">=</span><span style="color: #ff0000;">&quot;text/javascript&quot;</span> <span style="color: #000066;">src</span><span style="color: #66cc66;">=</span><span style="color: #ff0000;">&quot;jquery.googleMultiFeed.js&quot;</span>&gt;&lt;<span style="color: #66cc66;">/</span><span style="color: #000000; font-weight: bold;">script</span>&gt;</span>
<span style="color: #009900;">&lt;<span style="color: #000000; font-weight: bold;">script</span> <span style="color: #000066;">type</span><span style="color: #66cc66;">=</span><span style="color: #ff0000;">&quot;text/javascript&quot;</span>&gt;</span>
//google.load('jquery', '1.4');
&nbsp;
google.setOnLoadCallback(function(){
  //jqueryをgoole.loadで読み込む場合のみ必要
  //initGoogleMultiFeed();
&nbsp;
  $('#feed').googleMultiFeed({
    urls: ['http://example.com/rss', 'http://example.net/feed'],
    numEntries: 5
  });
});
<span style="color: #009900;">&lt;<span style="color: #66cc66;">/</span><span style="color: #000000; font-weight: bold;">script</span>&gt;</span>
...
<span style="color: #009900;">&lt;<span style="color: #000000; font-weight: bold;">div</span> <span style="color: #000066;">id</span><span style="color: #66cc66;">=</span><span style="color: #ff0000;">&quot;feed&quot;</span>&gt;&lt;<span style="color: #66cc66;">/</span><span style="color: #000000; font-weight: bold;">div</span>&gt;</span></pre></div></div>



<p>
urls パラメータは必須で、読み込みたいフィードのURLを配列として指定します。 numEntries パラメータはオプションで、フィード一つあたりの件数です。
</p>
<p>
上の例を実行すると http://example.com/rss と http://example.net/feed から5件ずつフィードを読み込んで、新しい順に並び替えた上で、指定したタグの中に次のようなHTMLで表示されます。
</p>


<div class="wp_syntax"><div class="code"><pre class="html4-strict" style="font-family:monospace;">&lt;div&gt;
&lt;a title=&quot;エントリータイトル | フィードタイトル&quot; href=&quot;リンク&quot;&gt;エントリータイトル [フィードタイトル]&lt;/a&gt;
&lt;span class=&quot;entry-date&quot;&gt;日付(YYYY-MM-DD)&lt;/span&gt;
&lt;/div&gt;
...（フィードの件数分繰り返し）...</pre></div></div>



<p>
表示されるHTMLをカスタマイズするには format パラメータでフォーマット用の関数を指定します。例えばエントリータイトルとリンクだけをリスト形式で表示したいなら、次のような関数を指定します。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">//第一引数がエントリ、第2引数がフィード</span>
<span style="color: #006600; font-style: italic;">//詳細は http://code.google.com/intl/ja/apis/feed/v1/reference.html#JSON</span>
<span style="color: #003366; font-weight: bold;">function</span> titleOnly<span style="color: #009900;">&#40;</span>entry<span style="color: #339933;">,</span> feed<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
  <span style="color: #003366; font-weight: bold;">var</span> link <span style="color: #339933;">=</span> $<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'&lt;a /&gt;'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">attr</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>href<span style="color: #339933;">:</span> entry.<span style="color: #660066;">link</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">text</span><span style="color: #009900;">&#40;</span>entry.<span style="color: #660066;">title</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
  <span style="color: #000066; font-weight: bold;">return</span> $<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'&lt;li /&gt;'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">append</span><span style="color: #009900;">&#40;</span>link<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">//ULタグに対して追加する</span>
$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'ul#feed'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">googleMultiFeed</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span>
  urls<span style="color: #339933;">:</span> <span style="color: #009900;">&#91;</span><span style="color: #3366CC;">'http://example.com/rss'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'http://example.net/feed'</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">,</span>
  format<span style="color: #339933;">:</span> titleOnly
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
その他、loadCompleted パラメータにカスタム関数を指定すると、全てが読み込まれた後に&#8221;読み込み中インジケータ&#8221;を消す等の処理も行うことができます。有効なパラメータについては<a href="https://github.com/tkyk/jquery-googleMultiFeed/wiki/jQuery-GoogleMultiFeed-plugin">GitHub上のWiki</a>を参照してください。
</p>
<p>
以下のサイトなどを参考にしました。
</p>
<ul>
<li><a href="http://blog.zige.jp/sake/kiji/21781.html">複数フィードをGoogle AJAX Feed APIで読み込み新着順に | No sake no japanese</a></li>
<li><a href="http://neta-times.net/entries/953/">複数の外部サイトからRSSフィードを取得し、日付順に一覧表示する方法 with はてブ数 | NETA-Times</a></li>
</ul>

]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/1908/feed</wfw:commentRss>
		<slash:comments>7</slash:comments>
		</item>
		<item>
		<title>Topsyのotter APIを使ってtwitter検索</title>
		<link>http://wp.serpere.info/archives/1817</link>
		<comments>http://wp.serpere.info/archives/1817#comments</comments>
		<pubDate>Mon, 01 Nov 2010 15:17:05 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jquery]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=1817</guid>
		<description><![CDATA[Topsyが提供しているOtter APIを使ってTwitter検索。 特定のURLに対するツイート一覧を得る 特定のURLに対するツイートは trackbacks というリソースで取得できる。 例: http://wp.serpere.info/に対するツイートを10件までテキストフォーマットで得る パラメータはtrackbackリソース固有のものと、共通のリスト用のものが使用できる。orderパラメータでレスポンスの順序を指定できるとあるのだが、現時点（2010-11-01）では正しく機能せず、何を指定しても常に新しい順で返ってくるようだ。 レスポンスの形式は拡張子で指定できる。デバッグ時はテキスト形式（.txt）が便利。実際にプログラムから使用する場合はJSON形式（.json）またはJSONP（.js）を使う。JSONの構造については今のところ実際に動かしてみて確認するしかない。 例: http://wp.serpere.info/に対する最新のツイート10件をjQueryによるJSONPで取得・表示する otter API trackback resource &#8211; jsdo.it &#8211; share JavaScript, HTML5 and CSS サイト全体に対するツイート一覧を得る サイト全体（特定のドメイン以下のページ）に対するツイートは search リソースで site: クエリを使うことで得られる。 例: このサイト全体に対する言及ツイートを、過去1ヶ月分10件まで取得 使用できるパラメータはsearchリソースに対するものと共通のリスト用オプション。windowオプションでは対象となるツイートの期間を指定する。d10で10日、w2で2週間、aで全期間など。 このsearchリソースの仕様には色々と謎が多い。 新しい順にソートして取得するためのsearchdateリソースを使った場合と、取得できる内容が大きく異なる。searchdateの方が反映が遅い？ 効かないはずのorderオプションが効いている？ order=date に設定すると searchdate を使った場合と結果が同じになる？ 例: このサイトに対する過去1か月の言及ツイートを20件、jQueryによるJSONPで取得し、自分（tkykmw）以外のものを表示 otter API search/searchdate resource &#8211; jsdo.it &#8211; share JavaScript, HTML5 and CSS]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F1817%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2F9KlUuU%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22Topsy%E3%81%AEotter%20API%E3%82%92%E4%BD%BF%E3%81%A3%E3%81%A6twitter%E6%A4%9C%E7%B4%A2%22%20%7D);"></div>
<script type="text/javascript">
var __topsy_otter_api_usage = {
_write: function(q){
  document.write('<a target="_blank" href="'+ q +'">'+ q +'</a>');
},
trackbacks: function(){
  var q = "http://otter.topsy.com/trackbacks.txt?perpage=10&amp;url=";
  q+= encodeURIComponent("http://wp.serpere.info/");
  this._write(q);
},
searchdate: function(){
  var q = "http://otter.topsy.com/search.txt?perpage=10&amp;window=m&amp;q=";
  q+= "site:"+ encodeURIComponent(location.host);
  this._write(q);
}
};
</script>
<p>
<a href="http://topsy.com/">Topsy</a>が提供しているOtter APIを使ってTwitter検索。
</p>
<h3>特定のURLに対するツイート一覧を得る</h3>
<p>
特定のURLに対するツイートは <code>trackbacks</code> というリソースで取得できる。
</p>
<p>
例: http://wp.serpere.info/に対するツイートを10件までテキストフォーマットで得る<br />
<script type="text/javascript"> __topsy_otter_api_usage.trackbacks() </script>
</p>
<p>
パラメータは<a href="http://code.google.com/p/otterapi/wiki/Resources#/trackbacks">trackbackリソース固有のもの</a>と、<a href="http://code.google.com/p/otterapi/wiki/ResListParameters">共通のリスト用のもの</a>が使用できる。orderパラメータでレスポンスの順序を指定できるとあるのだが、現時点（2010-11-01）では正しく機能せず、何を指定しても常に新しい順で返ってくるようだ。
</p>
<p>
レスポンスの形式は<a href="http://code.google.com/p/otterapi/wiki/ResponseFormats">拡張子</a>で指定できる。デバッグ時はテキスト形式（.txt）が便利。実際にプログラムから使用する場合はJSON形式（.json）またはJSONP（.js）を使う。JSONの構造については今のところ実際に動かしてみて確認するしかない。
</p>
<p>
例:  http://wp.serpere.info/に対する最新のツイート10件をjQueryによるJSONPで取得・表示する
</p>
<script type="text/javascript" src="http://jsdo.it/blogparts/GUPk/js"></script><p class="ttlBpJsdoit" style="width: 465px; margin: 0; text-align: right; font-size: 11px;"><a href="http://jsdo.it/tkykmw/GUPk" title="otter API trackback resource">otter API trackback resource &#8211; jsdo.it &#8211; share JavaScript, HTML5 and CSS</a></p>
<h3>サイト全体に対するツイート一覧を得る</h3>
<p>
サイト全体（特定のドメイン以下のページ）に対するツイートは <code>search</code> リソースで <code>site:</code> クエリを使うことで得られる。
</p>
<p>
例: このサイト全体に対する言及ツイートを、過去1ヶ月分10件まで取得<br />
<script type="text/javascript"> __topsy_otter_api_usage.searchdate() </script>
</p>
<p>
使用できるパラメータは<a href="http://code.google.com/p/otterapi/wiki/Resources#/search">searchリソース</a>に対するものと<a href="http://code.google.com/p/otterapi/wiki/ResListParameters">共通のリスト用オプション</a>。windowオプションでは対象となるツイートの期間を指定する。<code>d10</code>で10日、<code>w2</code>で2週間、<code>a</code>で全期間など。
</p>
<p>
このsearchリソースの仕様には色々と謎が多い。
</p>
<ul>
<li>新しい順にソートして取得するための<a href="http://code.google.com/p/otterapi/wiki/Resources#/searchdate">searchdateリソース</a>を使った場合と、取得できる内容が大きく異なる。searchdateの方が反映が遅い？</li>
<li>効かないはずのorderオプションが効いている？ order=date に設定すると searchdate を使った場合と結果が同じになる？
</li>
</ul>
<p>
例: このサイトに対する過去1か月の言及ツイートを20件、jQueryによるJSONPで取得し、自分（tkykmw）以外のものを表示
</p>
<script type="text/javascript" src="http://jsdo.it/blogparts/m2hy/js"></script><p class="ttlBpJsdoit" style="width: 465px; margin: 0; text-align: right; font-size: 11px;"><a href="http://jsdo.it/tkykmw/m2hy" title="otter API search/searchdate resource">otter API search/searchdate resource &#8211; jsdo.it &#8211; share JavaScript, HTML5 and CSS</a></p>
]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/1817/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Kanasan.JS jQuery コードリーディング#2に参加しました</title>
		<link>http://wp.serpere.info/archives/1771</link>
		<comments>http://wp.serpere.info/archives/1771#comments</comments>
		<pubDate>Tue, 05 Oct 2010 13:22:53 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jquery]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=1771</guid>
		<description><![CDATA[9月26日にKanasan.js主催で開催された「jQuery コードリーディング#2」に参加してきました。 複数人でペースを合わせてコードを読んでいくのは初めてだったので、最初は勝手がつかめなくて戸惑いましたが、慣れるとかなり面白かったです。一人で読んでいたら何気なく読み飛ばしてしまうような箇所でも、他の人の質問を受けて改めて読み返すと意外な発見があったりして、なかなか新鮮な体験でした。自分も途中からはほとんど独り言をつぶやくようなつもりで発言しまくっていました。 ただコードを読む前に、まずjquery.comのAPI Referenceを読むべきだったかなと思いました。たとえよく使うメソッドであっても、意外と知らない機能が隠れていたりするもので、そうなるとコードの意図を推測する時間が余計にかかります。例として jQuery.map が挙げられます。このメソッドは、JavaScriptの Array.prototype.map と違ってLispの mapcan みたいな機能を兼ねています。すなわち null, undefined は無視され、配列は concat されます。 $.map&#40;&#91;1,2,3,4&#93;, function&#40;x&#41;&#123; if&#40;x % 2 == 0&#41; return &#91;x, x&#93;; &#125;&#41;; // =&#62; [2,2,4,4] この動作を頭に入れておけば、最後の concat.apply は配列を一次元flattenするためのイディオムであることもすぐに見当がつきます。 ほとんど使ったことがないメソッドについては、この”意図を知る”作業は決定的に重要になります。今回の範囲で言うと私は queue, dequeue を全く使ったことがなかったので、かなり苦労しました。「これらはアニメーション（エフェクト）の基礎になっているメソッドだ」と別の方が指摘してくれたお陰でだいぶ助かりましたが、最初からAPIリファレンスを読んでいれば、もっと手っ取り早く正体がつかめたはずです。 実際にはこのqueque/dequeueは、非同期で実行される操作（関数）をあらかじめキューに溜めておいて、実行順序を保証するための仕組みです。アニメーション以外の例では、例えば jQuery.getScript によるスクリプトを読み込みを非同期かつ安全に実行するために使用できます。 /** * - LibraryA, * - LibraryA に依存する LibraryB * - LibraryA と LibraryB を使用する処理 [...]]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F1771%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2F9UxzOG%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22Kanasan.JS%20jQuery%20%E3%82%B3%E3%83%BC%E3%83%89%E3%83%AA%E3%83%BC%E3%83%87%E3%82%A3%E3%83%B3%E3%82%B0%232%E3%81%AB%E5%8F%82%E5%8A%A0%E3%81%97%E3%81%BE%E3%81%97%E3%81%9F%22%20%7D);"></div>
<p>
9月26日にKanasan.js主催で開催された「<a href="https://sites.google.com/site/kanasanjs/jquery_work_shop2">jQuery コードリーディング#2</a>」に参加してきました。
</p><p>
複数人でペースを合わせてコードを読んでいくのは初めてだったので、最初は勝手がつかめなくて戸惑いましたが、慣れるとかなり面白かったです。一人で読んでいたら何気なく読み飛ばしてしまうような箇所でも、他の人の質問を受けて改めて読み返すと意外な発見があったりして、なかなか新鮮な体験でした。自分も途中からはほとんど独り言をつぶやくようなつもりで発言しまくっていました。
</p><p>
ただコードを読む前に、まずjquery.comのAPI Referenceを読むべきだったかなと思いました。たとえよく使うメソッドであっても、意外と知らない機能が隠れていたりするもので、そうなるとコードの意図を推測する時間が余計にかかります。例として <code>jQuery.map</code> が挙げられます。このメソッドは、JavaScriptの <code>Array.prototype.map</code> と違ってLispの <code>mapcan</code> みたいな機能を兼ねています。すなわち <code>null</code>, <code>undefined</code> は無視され、配列は <code>concat</code> されます。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">$.<span style="color: #660066;">map</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#91;</span><span style="color: #CC0000;">1</span><span style="color: #339933;">,</span><span style="color: #CC0000;">2</span><span style="color: #339933;">,</span><span style="color: #CC0000;">3</span><span style="color: #339933;">,</span><span style="color: #CC0000;">4</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>x<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> <span style="color: #000066; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>x <span style="color: #339933;">%</span> <span style="color: #CC0000;">2</span> <span style="color: #339933;">==</span> <span style="color: #CC0000;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #000066; font-weight: bold;">return</span> <span style="color: #009900;">&#91;</span>x<span style="color: #339933;">,</span> x<span style="color: #009900;">&#93;</span><span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #006600; font-style: italic;">// =&gt; [2,2,4,4]</span></pre></div></div>



<p>
この動作を頭に入れておけば、最後の <code>concat.apply</code> は配列を一次元flattenするためのイディオムであることもすぐに見当がつきます。
</p><p>
ほとんど使ったことがないメソッドについては、この”意図を知る”作業は決定的に重要になります。今回の範囲で言うと私は <code>queue</code>, <code>dequeue</code> を全く使ったことがなかったので、かなり苦労しました。「これらはアニメーション（エフェクト）の基礎になっているメソッドだ」と別の方が指摘してくれたお陰でだいぶ助かりましたが、最初からAPIリファレンスを読んでいれば、もっと手っ取り早く正体がつかめたはずです。
</p><p>
実際にはこのqueque/dequeueは、非同期で実行される操作（関数）をあらかじめキューに溜めておいて、実行順序を保証するための仕組みです。アニメーション以外の例では、例えば <code>jQuery.getScript</code> によるスクリプトを読み込みを非同期かつ安全に実行するために使用できます。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">/**
 * - LibraryA,
 * - LibraryA に依存する LibraryB
 * - LibraryA と LibraryB を使用する処理
 * を順番に実行する.
 * 読み込みが失敗したら後続の処理は実行しない
 */</span>
&nbsp;
<span style="color: #006600; font-style: italic;">// script-loader という名前の queue を使用する</span>
jQuery.<span style="color: #660066;">fn</span>.<span style="color: #660066;">loaderQueue</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>func<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">return</span> <span style="color: #000066; font-weight: bold;">this</span>.<span style="color: #660066;">queue</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'script-loader'</span><span style="color: #339933;">,</span> func<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
jQuery.<span style="color: #660066;">fn</span>.<span style="color: #660066;">loaderDequeue</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">return</span> <span style="color: #000066; font-weight: bold;">this</span>.<span style="color: #660066;">dequeue</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'script-loader'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">// スクリプト読み込みが成功したら dequeue する $.getScript</span>
<span style="color: #003366; font-weight: bold;">function</span> dequeuingGetScript<span style="color: #009900;">&#40;</span>url<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">return</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>next<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        jQuery.<span style="color: #660066;">getScript</span><span style="color: #009900;">&#40;</span>url<span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>data<span style="color: #339933;">,</span> <span style="color: #000066;">status</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                next<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
jQuery<span style="color: #009900;">&#40;</span>document<span style="color: #009900;">&#41;</span>
    .<span style="color: #660066;">loaderQueue</span><span style="color: #009900;">&#40;</span>dequeuingGetScript<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'libraryA.js'</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>
    .<span style="color: #660066;">loaderQueue</span><span style="color: #009900;">&#40;</span>dequeuingGetScript<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'libraryB.js'</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>
    .<span style="color: #660066;">loaderQueue</span><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span>LibraryA.<span style="color: #660066;">func</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span> LibraryB.<span style="color: #660066;">func</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span> <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>
    .<span style="color: #660066;">loaderDequeue</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
ただ実装の中ではエフェクト用の処理（fx queue）を決め打ちで特別扱いしているので、メソッドを分割した方が良さそうだよね、という意見が会場で出ました。
</p>
<p>……</p>
<p>
その他諸々、会場での話題や気づいた点など。
</p>
<ul>
<li>ローカル関数 <code>access</code> は非常に複雑かつ名前も分かりにくすぎる。特に第6引数 <code>pass</code> が何のためにあるのかわからない。一応


<div class="wp_syntax"><div class="code"><pre class="jpgavascript" style="font-family:monospace;">$('#sss').attr({ key:function(){  }}, true)</pre></div></div>



という形で使用すれば機能することはわかったが、何に使うか不明。
</li>
<li>
<code>jQuery.support.hrefNormalized</code> の名前が意味と逆転している。
</li>
<li>
expando って何？=>実行時に動的に追加されるプロパティのこと。
</li>
<li>
ローカル関数 <code>eventSupported</code> は特定のイベントがbubbleするかどうかのチェックに使われている。IEではsubmit/changeはbubbleしない。jQuery 1.4からはjQueryがエミュレートしてくれるようになった。
</li>
<li>
<code>jQuery.data</code> まわりのコードで <code>jQuery.expando</code> とローカル変数 <code>expando</code> の参照が入り交じっている。ケアレスミス？
</li>
<li>
変数名 <code>jQuery.cache</code> は変。何かをキャッシュしているわけではなく、単なるデータストア。
</li>
</ul>
<p>
あと懇親会ではバイクで行ったせいでお酒が飲めず、大変残念な思いをしたので、次に参加するときには絶対にバスか電車で行こうと思いました。
</p>
]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/1771/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>jQuery History is now on Github</title>
		<link>http://wp.serpere.info/archives/1234</link>
		<comments>http://wp.serpere.info/archives/1234#comments</comments>
		<pubDate>Sat, 08 May 2010 12:47:14 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[jquery]]></category>
		<category><![CDATA[jQuery History]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=1234</guid>
		<description><![CDATA[I created a fork of jQuery History plugin on Github. http://github.com/tkyk/jquery-history-plugin (the latest source code) Issue Tracking System: http://github.com/tkyk/jquery-history-plugin/issues Test page: http://www.serpere.info/jquery-history-plugin/sample/ Though this is just a fork for now, Mikage Sawatari, the original author of this plugin, and I agreed that it could be the mainstream in the near future. I&#8217;ve already done some [...]]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F1234%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2Fc95nCZ%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22jQuery%20History%20is%20now%20on%20Github%22%20%7D);"></div>
<div id="jquery-history-en">
<p>I created a fork of jQuery History plugin on Github.</p>
<ul>
	<li><a href="http://github.com/tkyk/jquery-history-plugin">http://github.com/tkyk/jquery-history-plugin</a> (<a href="http://github.com/tkyk/jquery-history-plugin/raw/master/jquery.history.js">the latest source code</a>)</li>
	<li>Issue Tracking System: <a href="http://github.com/tkyk/jquery-history-plugin/issues">http://github.com/tkyk/jquery-history-plugin/issues</a></li>
	<li>Test page: <a href="http://www.serpere.info/jquery-history-plugin/sample/">http://www.serpere.info/jquery-history-plugin/sample/</a></li>
</ul>
<p>Though this is just a fork for now, Mikage Sawatari, the original author of this plugin, and I agreed that it could be the mainstream in the near future.</p>
<p>I&#8217;ve already done some major changes to the script structure:</p>
<ul>
	<li>It no longer uses the Webkit-specific hack for updating the location object, because recent versions of Webkit can correctly update the object just like Firefix and IE8.</li>
	<li>Hashes are percent-encoded with encodeURIComponent before being put to location.hash. So you can use any characters such as `?&#8217; in your hash.</li>
	<li>history.load does not execute the callback unless hash is changed.</li>
	<li>Updated API/code format. Thanks to <a href="http://www.mikage.to/jquery/history/rbbs.cgi?id=RA12619431290839983526&amp;focus=1">Kevin Dalman</a>.</li>
</ul>
<p>It works on IE6, IE7, IE8, Firefox3, Safari4, Chrome4, and Chrome5.</p>
<p>If you have any problems or feature requests, please create a new issue in the <a href="http://github.com/tkyk/jquery-history-plugin/issues">ITS</a>. And of course, you can create your own fork.</p>
</div>
<hr />
<div id="jquery-history-ja">
<p>jQuery Historyプラグインは今後Githubで管理されることになりました。</p>
<ul>
<li>プロジェクトページ: <a href="http://github.com/tkyk/jquery-history-plugin">http://github.com/tkyk/jquery-history-plugin</a> (<a href="http://github.com/tkyk/jquery-history-plugin/raw/master/jquery.history.js">最新版のソースコード</a>)</li>
<li>バグトラッキングシステム: <a href="http://github.com/tkyk/jquery-history-plugin/issues">http://github.com/tkyk/jquery-history-plugin/issues</a></li>
<li>動作サンプル: <a href="http://www.serpere.info/jquery-history-plugin/sample/">http://www.serpere.info/jquery-history-plugin/sample/</a></li>
</ul>
<p>Mikage Sawatariさんによる元々のバージョンに対し、次のような大きな変更が加えられています。</p>
<ul>
<li>Webkitで動かすためのハックは不要になったので取り除かれました。</li>
<li>location.hash に代入する前に encodeURIComponent によるパーセントエンコーディングを行うようにしました。これによって ? を含むあらゆる文字を hash として保存できるようになりました。</li>
<li>ハッシュが変更されていない場合はコールバックが実行されないようになりました。</li>
<li>API/コーディングスタイルを変更しました。この変更はフォーラムの<a href="http://www.mikage.to/jquery/history/rbbs.cgi?id=RA12619431290839983526&amp;focus=1">Kevin Dalman氏の投稿</a>に依ります。</li>
</ul>
<p>IE6, IE7, IE8, Firefox3, Safari4, Chrome4, Chrome5で動作します。</p>
<p><a href="http://github.com/tkyk/jquery-history-plugin/issues">Githubのバグトラッキングシステム</a>に登録してください。もちろん自分でforkを作って修正していただいても構いません。</p>
</div>
]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/1234/feed</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>XPCNativeWrapperとunsafeWindowの間で同期処理を行う</title>
		<link>http://wp.serpere.info/archives/1110</link>
		<comments>http://wp.serpere.info/archives/1110#comments</comments>
		<pubDate>Sat, 30 Jan 2010 04:06:00 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Greasemonkey]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=1110</guid>
		<description><![CDATA[先日使い方を学んだ MessageEvent と、location.href+javascript:ハックとJSDeferred userscript版とを組み合わせ、XPCNativeWrapper と unsafeWindow の間で同期処理を行うコードを書いてみた。 まずは MessageEvent を使って前回 evalInPage 相当の処理を作る。キャンセル処理も入れたかったので UnsafeWrapper というオブジェクトにまとめることにした。前回より長くなったように見えるが、実際には MessageEvent の lastEventId が使えるようになった分、簡潔になっている。 var UnsafeWrapper = new &#40;function&#40;&#41; &#123; var seqId = 0, waiting = &#123;&#125;, self = this, noop = function&#40;&#41;&#123;&#125;; &#160; function dispatch&#40;data, id&#41; &#123; var e = document.createEvent&#40;&#34;MessageEvent&#34;&#41;; e.initMessageEvent&#40;'GM_UnsafeWrapper_returned', true, false, data, location.protocol + &#34;//&#34; + location.host, [...]]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F1110%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2FcfbBWG%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22XPCNativeWrapper%E3%81%A8unsafeWindow%E3%81%AE%E9%96%93%E3%81%A7%E5%90%8C%E6%9C%9F%E5%87%A6%E7%90%86%E3%82%92%E8%A1%8C%E3%81%86%22%20%7D);"></div>
<p>
<a href="http://wp.serpere.info/archives/1107">先日</a>使い方を学んだ MessageEvent と、location.href+javascript:ハックと<a href="http://github.com/cho45/jsdeferred">JSDeferred</a> userscript版とを組み合わせ、XPCNativeWrapper と unsafeWindow の間で同期処理を行うコードを書いてみた。
</p>
<p>
まずは MessageEvent を使って前回 evalInPage 相当の処理を作る。キャンセル処理も入れたかったので UnsafeWrapper というオブジェクトにまとめることにした。前回より長くなったように見えるが、実際には MessageEvent の lastEventId が使えるようになった分、簡潔になっている。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">var</span> UnsafeWrapper <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">new</span> <span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #003366; font-weight: bold;">var</span> seqId <span style="color: #339933;">=</span> <span style="color: #CC0000;">0</span><span style="color: #339933;">,</span> waiting <span style="color: #339933;">=</span> <span style="color: #009900;">&#123;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span> self <span style="color: #339933;">=</span> <span style="color: #000066; font-weight: bold;">this</span><span style="color: #339933;">,</span> noop <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #003366; font-weight: bold;">function</span> dispatch<span style="color: #009900;">&#40;</span>data<span style="color: #339933;">,</span> id<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	    <span style="color: #003366; font-weight: bold;">var</span> e <span style="color: #339933;">=</span> document.<span style="color: #660066;">createEvent</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;MessageEvent&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	    e.<span style="color: #660066;">initMessageEvent</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'GM_UnsafeWrapper_returned'</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #339933;">,</span>
			       data<span style="color: #339933;">,</span> location.<span style="color: #660066;">protocol</span> <span style="color: #339933;">+</span> <span style="color: #3366CC;">&quot;//&quot;</span> <span style="color: #339933;">+</span> location.<span style="color: #660066;">host</span><span style="color: #339933;">,</span>
			       id<span style="color: #339933;">,</span> window<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	    document.<span style="color: #660066;">dispatchEvent</span><span style="color: #009900;">&#40;</span>e<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	<span style="color: #003366; font-weight: bold;">function</span> listen<span style="color: #009900;">&#40;</span>func<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	    document.<span style="color: #660066;">addEventListener</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'GM_UnsafeWrapper_returned'</span><span style="color: #339933;">,</span> func<span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span>
&nbsp;
	listen<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>e<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		<span style="color: #000066; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span>waiting<span style="color: #009900;">&#91;</span>e.<span style="color: #660066;">lastEventId</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		    waiting<span style="color: #009900;">&#91;</span>e.<span style="color: #660066;">lastEventId</span><span style="color: #009900;">&#93;</span>.<span style="color: #660066;">call</span><span style="color: #009900;">&#40;</span>self<span style="color: #339933;">,</span> JSON.<span style="color: #660066;">parse</span><span style="color: #009900;">&#40;</span>e.<span style="color: #660066;">data</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
		    <span style="color: #000066; font-weight: bold;">delete</span> waiting<span style="color: #009900;">&#91;</span>e.<span style="color: #660066;">lastEventId</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span>
	    <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000066; font-weight: bold;">this</span>.<span style="color: #660066;">exec</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>func<span style="color: #339933;">,</span> args<span style="color: #339933;">,</span> callback<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	    <span style="color: #003366; font-weight: bold;">var</span> userFunc <span style="color: #339933;">=</span> <span style="color: #3366CC;">&quot;(&quot;</span><span style="color: #339933;">+</span> func <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;).apply(null,&quot;</span><span style="color: #339933;">+</span> JSON.<span style="color: #660066;">stringify</span><span style="color: #009900;">&#40;</span>args <span style="color: #339933;">||</span> <span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;)&quot;</span><span style="color: #339933;">;</span>
	    waiting<span style="color: #009900;">&#91;</span>seqId<span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> callback <span style="color: #339933;">||</span> noop<span style="color: #339933;">;</span>
	    location.<span style="color: #660066;">href</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">&quot;javascript:void &quot;</span><span style="color: #339933;">+</span>
	    <span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>dispatch<span style="color: #339933;">,</span> ret<span style="color: #339933;">,</span> id<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span> dispatch<span style="color: #009900;">&#40;</span>JSON.<span style="color: #660066;">stringify</span><span style="color: #009900;">&#40;</span>ret<span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span> id<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span>
	    <span style="color: #3366CC;">&quot;(&quot;</span><span style="color: #339933;">+</span> dispatch <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;,&quot;</span><span style="color: #339933;">+</span> userFunc <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;,&quot;</span> <span style="color: #339933;">+</span> JSON.<span style="color: #660066;">stringify</span><span style="color: #009900;">&#40;</span>seqId<span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;)&quot;</span><span style="color: #339933;">;</span>
	    <span style="color: #000066; font-weight: bold;">return</span> seqId<span style="color: #339933;">++;</span>
	<span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
&nbsp;
	<span style="color: #000066; font-weight: bold;">this</span>.<span style="color: #660066;">cancel</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>id<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	    <span style="color: #000066; font-weight: bold;">delete</span> waiting<span style="color: #009900;">&#91;</span>id<span style="color: #009900;">&#93;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
そして Deferred に対するアダプタを書く。とても簡単。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #000066; font-weight: bold;">with</span><span style="color: #009900;">&#40;</span>D<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">function</span> unsafeExec<span style="color: #009900;">&#40;</span>func<span style="color: #339933;">,</span> args<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
	<span style="color: #003366; font-weight: bold;">var</span> d <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">new</span> Deferred<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #003366; font-weight: bold;">var</span> id <span style="color: #339933;">=</span> UnsafeWrapper.<span style="color: #660066;">exec</span><span style="color: #009900;">&#40;</span>func<span style="color: #339933;">,</span> args<span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>ret<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
		d.<span style="color: #660066;">call</span><span style="color: #009900;">&#40;</span>ret<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	    <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	d.<span style="color: #660066;">canceller</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> UnsafeWrapper.<span style="color: #660066;">cancel</span><span style="color: #009900;">&#40;</span>id<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
	<span style="color: #000066; font-weight: bold;">return</span> d<span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>



<p>
これで例えば、GM_xmlhttpRequest で外部ドメインからデータを取得して、そのデータを整形して、unsafeWindow 側で表示処理を行って、そしてその結果をuserscript側で受け取って…という処理は次のように書くことができる。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #000066; font-weight: bold;">with</span><span style="color: #009900;">&#40;</span>D<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
&nbsp;
xhttp.<span style="color: #660066;">get</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;http://example.com/&quot;</span><span style="color: #009900;">&#41;</span>
    .<span style="color: #660066;">next</span><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>res<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #003366; font-weight: bold;">var</span> data <span style="color: #339933;">=</span> res.<span style="color: #660066;">responseText</span><span style="color: #339933;">;</span>
            <span style="color: #006600; font-style: italic;">//....</span>
&nbsp;
	    <span style="color: #000066; font-weight: bold;">return</span> unsafeExec<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>data<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                    $.<span style="color: #660066;">each</span><span style="color: #009900;">&#40;</span>data<span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>k<span style="color: #339933;">,</span>v<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                      <span style="color: #006600; font-style: italic;">//...</span>
                    <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
                    <span style="color: #006600; font-style: italic;">//...</span>
		    <span style="color: #000066; font-weight: bold;">return</span> result<span style="color: #339933;">;</span>
		<span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
		<span style="color: #009900;">&#91;</span>data<span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
	<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>
    .<span style="color: #660066;">next</span><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>result<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
          <span style="color: #006600; font-style: italic;">//...</span>
	<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #009900;">&#125;</span></pre></div></div>



<p>
より実用性を高めるのであれば、location.href で実行するコード全体を try {} で囲み、catch したエラーをJSONに変換して _failed イベントを dispatch して、Deferred の fail に転送すれば、unsafeWindow 側で起こったエラーをuserscript側のDeferred chainで捕捉できるようになる。
</p>
<p>参考：</p>
<ul>
<li><a href="http://d.hatena.ne.jp/Constellation/20090326/1238073714">unsafeExec on JSDeferred &#8211; 枕を欹てて聴く</a></li>
<li><a href="http://cho45.stfuawsc.com/jsdeferred/doc/intro.html">JSDeferred 紹介</a></li>
</ul>

]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/1110/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>XPCNativeWrapperとunsafeWindowの間でデータを送受信する</title>
		<link>http://wp.serpere.info/archives/1107</link>
		<comments>http://wp.serpere.info/archives/1107#comments</comments>
		<pubDate>Sat, 23 Jan 2010 13:59:30 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Greasemonkey]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=1107</guid>
		<description><![CDATA[XPCNativeWrapperの外側でスクリプトを評価する関数。Firebugも同じことをしている。unsafeWindowを触らないので安全。 function evalInPage&#40;fun&#41; &#123; location.href = &#34;javascript:void (&#34; + fun + &#34;)()&#34;; &#125; SmartLDR更新 &#8211; 素人がプログラミングを勉強するブログ これは面白い！Function.prototype.toString が関数のソースコードを返すことを利用した、巧妙にして簡潔なハック。 次のように引数を渡せるように改良すればさらに強力になる（引数に渡せるのはJSON化可能な値のみ）。 function evalInPage&#40;func, args&#41; &#123; var argStr = JSON.stringify&#40;args &#124;&#124; &#91;&#93;&#41;; location.href = &#34;javascript:void &#34;+ func +&#34;.apply(null,&#34;+ argStr +&#34;)&#34;; &#125; GM_xmlhttpRequest を使って別ドメインから得たデータを、unsafeWindow 上のライブラリを使って表示する、といったコードが安全かつ自然に書けるようになる。 // データの取得は Greasemonkey で行う GM_xmlhttpRequest&#40;&#123; method:&#34;GET&#34;, url: &#34;http://example.com/api&#34;, onload: function&#40;response&#41; &#123; var data = [...]]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F1107%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2F8lBQsJ%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22XPCNativeWrapper%E3%81%A8unsafeWindow%E3%81%AE%E9%96%93%E3%81%A7%E3%83%87%E3%83%BC%E3%82%BF%E3%82%92%E9%80%81%E5%8F%97%E4%BF%A1%E3%81%99%E3%82%8B%22%20%7D);"></div>
<blockquote>
<p>
XPCNativeWrapperの外側でスクリプトを評価する関数。Firebugも同じことをしている。unsafeWindowを触らないので安全。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> evalInPage<span style="color: #009900;">&#40;</span>fun<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
  location.<span style="color: #660066;">href</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">&quot;javascript:void (&quot;</span> <span style="color: #339933;">+</span> fun <span style="color: #339933;">+</span> <span style="color: #3366CC;">&quot;)()&quot;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>



<p><cite><a href="http://d.hatena.ne.jp/javascripter/20090324/1237903880">SmartLDR更新 &#8211; 素人がプログラミングを勉強するブログ</a></cite></p>
</blockquote>
<p>
これは面白い！Function.prototype.toString が関数のソースコードを返すことを利用した、巧妙にして簡潔なハック。
</p>
<p>
次のように引数を渡せるように改良すればさらに強力になる（引数に渡せるのはJSON化可能な値のみ）。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> evalInPage<span style="color: #009900;">&#40;</span>func<span style="color: #339933;">,</span> args<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> argStr <span style="color: #339933;">=</span> JSON.<span style="color: #660066;">stringify</span><span style="color: #009900;">&#40;</span>args <span style="color: #339933;">||</span> <span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    location.<span style="color: #660066;">href</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">&quot;javascript:void &quot;</span><span style="color: #339933;">+</span> func <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;.apply(null,&quot;</span><span style="color: #339933;">+</span> argStr <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;)&quot;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>



<p>
GM_xmlhttpRequest を使って別ドメインから得たデータを、unsafeWindow 上のライブラリを使って表示する、といったコードが安全かつ自然に書けるようになる。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">// データの取得は Greasemonkey で行う</span>
GM_xmlhttpRequest<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#123;</span> method<span style="color: #339933;">:</span><span style="color: #3366CC;">&quot;GET&quot;</span><span style="color: #339933;">,</span>
                    url<span style="color: #339933;">:</span> <span style="color: #3366CC;">&quot;http://example.com/api&quot;</span><span style="color: #339933;">,</span>
                    <span style="color: #000066;">onload</span><span style="color: #339933;">:</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>response<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                      <span style="color: #003366; font-weight: bold;">var</span> data <span style="color: #339933;">=</span> response.<span style="color: #660066;">responseText</span><span style="color: #339933;">;</span>
                      <span style="color: #006600; font-style: italic;">//...</span>
                      evalInPage<span style="color: #009900;">&#40;</span>render<span style="color: #339933;">,</span> <span style="color: #009900;">&#91;</span>data<span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
                    <span style="color: #009900;">&#125;</span>
                  <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">// データの表示は unsafeWindow 上で行う</span>
<span style="color: #006600; font-style: italic;">// jQueryなど unsafeWindow 上のライブラリが使える</span>
<span style="color: #003366; font-weight: bold;">function</span> render<span style="color: #009900;">&#40;</span>data<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
  $.<span style="color: #660066;">each</span><span style="color: #009900;">&#40;</span>data<span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>k<span style="color: #339933;">,</span>v<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #006600; font-style: italic;">//...</span>
  <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>



<p>
これだけでも十分便利なのだが、「返り値が利用できない」「Firefoxのlocation.hrefは非同期で実行される」といった難点があるらしい。それを回避するために<a href="http://d.hatena.ne.jp/Constellation/20090326/1238073714">unsafeExec on JSDeferred &#8211; 枕を欹てて聴く</a>においてはJSDeferredというライブラリを使う方法が紹介されているのだが、コードを見る限り unsafeWindow に対するアクセスが必要になるようだ。
</p>
<p>
unsafeWindow にアクセスせずにGreasemonkeyに制御を戻すには、DOM Eventを使うのが良いと思う。以下、DOMNodeInserted イベントを使って実装してみた（返り値として利用できるのはJSON化可能な値のみ）。
</p>
<p>
<ins datetime="2010-01-24T02:29:03+00:00"><strong>追記:</strong> <a href="http://wp.serpere.info/archives/1107/comment-page-1#comment-809">Constellationさんからコメントをいただきました</a>。DOMNodeInsertedなどのイベントを使わなくても、直接createEvent/dispatchEventでイベントを生成・データを送受信する方法があるようです。 詳細はこのページの Constellationさんのコメントや、『<a href="http://nanto.asablo.jp/blog/2008/06/26/3596261">Greasemonkey スクリプトとイベントで通信: Days on the Moon</a>』など参照してください。</ins>
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> getUniqId<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">do</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #003366; font-weight: bold;">var</span> id <span style="color: #339933;">=</span> <span style="color: #3366CC;">&quot;_tmp&quot;</span> <span style="color: #339933;">+</span> String<span style="color: #009900;">&#40;</span>Math.<span style="color: #660066;">random</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">slice</span><span style="color: #009900;">&#40;</span><span style="color: #CC0000;">2</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span> <span style="color: #000066; font-weight: bold;">while</span><span style="color: #009900;">&#40;</span>document.<span style="color: #660066;">getElementById</span><span style="color: #009900;">&#40;</span>id<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #000066; font-weight: bold;">return</span> id<span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #003366; font-weight: bold;">function</span> evalInPage<span style="color: #009900;">&#40;</span>func<span style="color: #339933;">,</span> args<span style="color: #339933;">,</span> callback<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> argStr <span style="color: #339933;">=</span> JSON.<span style="color: #660066;">stringify</span><span style="color: #009900;">&#40;</span>args <span style="color: #339933;">||</span> <span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span>
        userFunc <span style="color: #339933;">=</span> <span style="color: #3366CC;">&quot;(&quot;</span><span style="color: #339933;">+</span> func <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;).apply(null,&quot;</span><span style="color: #339933;">+</span> argStr <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;)&quot;</span><span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #000066; font-weight: bold;">if</span><span style="color: #009900;">&#40;</span><span style="color: #339933;">!</span>callback<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        location.<span style="color: #660066;">href</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">&quot;javascript:void &quot;</span><span style="color: #339933;">+</span> userFunc<span style="color: #339933;">;</span>
        <span style="color: #000066; font-weight: bold;">return</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #003366; font-weight: bold;">var</span> div <span style="color: #339933;">=</span> document.<span style="color: #660066;">createElement</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'div'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">,</span>
        id <span style="color: #339933;">=</span> getUniqId<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    div.<span style="color: #660066;">id</span> <span style="color: #339933;">=</span> id<span style="color: #339933;">;</span>
    div.<span style="color: #660066;">style</span>.<span style="color: #660066;">display</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">'none'</span><span style="color: #339933;">;</span>
    document.<span style="color: #660066;">body</span>.<span style="color: #660066;">appendChild</span><span style="color: #009900;">&#40;</span>div<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    div.<span style="color: #660066;">addEventListener</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'DOMNodeInserted'</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>e<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
            callback<span style="color: #009900;">&#40;</span>JSON.<span style="color: #660066;">parse</span><span style="color: #009900;">&#40;</span>e.<span style="color: #660066;">target</span>.<span style="color: #660066;">nodeValue</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
            div.<span style="color: #660066;">parentNode</span>.<span style="color: #660066;">removeChild</span><span style="color: #009900;">&#40;</span>div<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">false</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
    location.<span style="color: #660066;">href</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">&quot;javascript:void &quot;</span><span style="color: #339933;">+</span> <span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>ret<span style="color: #339933;">,</span> id<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            document.<span style="color: #660066;">getElementById</span><span style="color: #009900;">&#40;</span>id<span style="color: #009900;">&#41;</span>
            .<span style="color: #660066;">appendChild</span><span style="color: #009900;">&#40;</span>document.<span style="color: #660066;">createTextNode</span><span style="color: #009900;">&#40;</span>JSON.<span style="color: #660066;">stringify</span><span style="color: #009900;">&#40;</span>ret<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">toString</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span> <span style="color: #3366CC;">&quot;.call(null,&quot;</span><span style="color: #339933;">+</span> userFunc <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;,&quot;</span> <span style="color: #339933;">+</span> JSON.<span style="color: #660066;">stringify</span><span style="color: #009900;">&#40;</span>id<span style="color: #009900;">&#41;</span> <span style="color: #339933;">+</span><span style="color: #3366CC;">&quot;)&quot;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>



<p>JSDreferredを使う方法と同じく、戻り値を受け取るコールバック関数を指定する。</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">evalInPage<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>obj<span style="color: #339933;">,</span> num<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #006600; font-style: italic;">//この中のコードは unsafeWindow で実行される</span>
        <span style="color: #000066; font-weight: bold;">return</span> <span style="color: #009900;">&#123;</span> answer<span style="color: #339933;">:</span> obj.<span style="color: #660066;">a</span> <span style="color: #339933;">+</span> num <span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span>
    <span style="color: #009900;">&#91;</span><span style="color: #009900;">&#123;</span>a<span style="color: #339933;">:</span><span style="color: #CC0000;">99</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">,</span> <span style="color: #CC0000;">1</span><span style="color: #009900;">&#93;</span><span style="color: #339933;">,</span>
    <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>ret<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #006600; font-style: italic;">//この中のコードは Greasemonkey で実行される</span>
	alret<span style="color: #009900;">&#40;</span>ret.<span style="color: #660066;">answer</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
多分まじめに作り込めば一種のRPCシステムみたいになると思う。
</p>
]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/1107/feed</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>JavaScriptで確実にglobalオブジェクトを得る方法</title>
		<link>http://wp.serpere.info/archives/1106</link>
		<comments>http://wp.serpere.info/archives/1106#comments</comments>
		<pubDate>Fri, 22 Jan 2010 08:59:41 +0000</pubDate>
		<dc:creator>tkykmw</dc:creator>
				<category><![CDATA[JavaScript]]></category>

		<guid isPermaLink="false">http://wp.serpere.info/?p=1106</guid>
		<description><![CDATA[確実にグローバル関数/変数にアクセスしたいとき。あるいはglobalオブジェクトの名前が分からないときに。 var global = &#40;function&#40;&#41;&#123; return this &#125;&#41;&#40;&#41;; ブラウザ上では window がglobalオブジェクトを指すことは暗黙の前提になっているが、そうでない環境もあり得る。 ちなみに Greasemonkey と Chrome user-script ではともに window でglobalオブジェクトにアクセスできるようだ。]]></description>
			<content:encoded><![CDATA[
<div class="topsy_widget_data topsy_theme_jade" style="float: right;margin-left: 0.75em; background: url(data:,%7B%20%22url%22%3A%20%22http%253A%252F%252Fwp.serpere.info%252Farchives%252F1106%22%2C%20%22shorturl%22%3A%20%22http%3A%2F%2Fbit.ly%2F7N4ovK%22%2C%20%22style%22%3A%20%22big%22%2C%20%22title%22%3A%20%22JavaScript%E3%81%A7%E7%A2%BA%E5%AE%9F%E3%81%ABglobal%E3%82%AA%E3%83%96%E3%82%B8%E3%82%A7%E3%82%AF%E3%83%88%E3%82%92%E5%BE%97%E3%82%8B%E6%96%B9%E6%B3%95%22%20%7D);"></div>
<p>
確実にグローバル関数/変数にアクセスしたいとき。あるいはglobalオブジェクトの名前が分からないときに。
</p>


<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">var</span> global <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> <span style="color: #000066; font-weight: bold;">return</span> <span style="color: #000066; font-weight: bold;">this</span> <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>



<p>
ブラウザ上では <code>window</code> がglobalオブジェクトを指すことは暗黙の前提になっているが、そうでない環境もあり得る。
</p>
<p>
ちなみに Greasemonkey と Chrome user-script ではともに <code>window</code> でglobalオブジェクトにアクセスできるようだ。
</p>
]]></content:encoded>
			<wfw:commentRss>http://wp.serpere.info/archives/1106/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

