<?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>Simone Carletti&#039;s Blog &#187; javascript</title>
	<atom:link href="http://www.simonecarletti.com/blog/tags/javascript/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.simonecarletti.com/blog</link>
	<description>Simone Carletti&#039;s personal ramblings on programming, syndication, search engines &#38; marketing.</description>
	<lastBuildDate>Tue, 07 Feb 2012 08:48:33 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.1</generator>
		<item>
		<title>Understanding the Unobtrusive JavaScript technique</title>
		<link>http://www.simonecarletti.com/blog/2010/06/unobtrusive-javascript-technique/</link>
		<comments>http://www.simonecarletti.com/blog/2010/06/unobtrusive-javascript-technique/#comments</comments>
		<pubDate>Mon, 07 Jun 2010 12:17:33 +0000</pubDate>
		<dc:creator>Simone Carletti</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[html]]></category>
		<category><![CDATA[html 5]]></category>
		<category><![CDATA[javascript]]></category>
		<category><![CDATA[jquery]]></category>
		<category><![CDATA[rails 3]]></category>
		<category><![CDATA[ujs]]></category>

		<guid isPermaLink="false">http://www.simonecarletti.com/blog/?p=1086</guid>
		<description><![CDATA[Introductory article about Unobtrusive JavaScript technique, featuring the usage of JavaScript frameworks and HTML 5.]]></description>
			<content:encoded><![CDATA[<p>I was writing an article about the Unobtrusive JavaScript in Rails 3 when I realized the UJS section was becoming large enough to deserve a separate post. So here&#8217;s my <strong>Unobtrusive JavaScript for dummies</strong> explanation.</p>
<p>If you don&#8217;t know what <strong>Unobtrusive Javascript</strong> term means, this technique reflects what happened a few years ago with HTML pages when Cascading Style Sheets (CSS) were introduced. Before CSS, the presentation of HTML elements was defined inline. Did you remember the ugly <code>font</code> tag or the widely-adopted <code>align</code> attribute?</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;p align=&quot;center&quot;&gt;This is a centered paragraph with a &lt;font color=&quot;#FF0000&quot;&gt;red&lt;/font&gt; word&lt;/p&gt;</div></td></tr></tbody></table></div>
<p>Then CSS come, and the document presentation attributes were slowly moved outside the main HTML document. Something similar is happening now with <strong>HTML and JavaScript</strong>. Before JavaScript frameworks made so easy to bind custom events to HTML elements, the most common way to append a JavaScript function was to use the HTML-Javascript bridges such as the <code>on<em>event</em></code> attributes.</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;a href=&quot;javascript:void(0);&quot; onclick=&quot;alert('Thanks for clicking me');&quot;&gt;Click me&lt;/a&gt;</div></td></tr></tbody></table></div>
<p>With the huge adoption of JavaScript programming, HTML documents fall again into the trap of mixing presentation/interaction elements within the page content and structure.</p>
<p>Let&#8217;s look the result of a <code>link_to</code> Rails helper call with a custom <code>:method</code> parameter.</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;%= link_to &quot;delete&quot;, domain_path(@domain), :method =&gt; :delete, :confirm =&gt; &quot;Are you sure?&quot; %&gt;</div></td></tr></tbody></table></div>
<p>generates</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;a href=&quot;/domains/1&quot; onclick=&quot;if (confirm('Are you sure?')) { var f = document.createElement('form'); f.style.display = 'none'; this.parentNode.appendChild(f); f.method = 'POST'; f.action = this.href;var m = document.createElement('input'); m.setAttribute('type', 'hidden'); m.setAttribute('name', '_method'); m.setAttribute('value', 'delete'); f.appendChild(m);var s = document.createElement('input'); s.setAttribute('type', 'hidden'); s.setAttribute('name', 'authenticity_token'); s.setAttribute('value', 'pKvg9hsnQ33uk='); f.appendChild(s);f.submit(); };return false;&quot;&gt;delete&lt;/a&gt;</div></td></tr></tbody></table></div>
<p>Pretty messy. Isn&#8217;t it? What this helper does on click is to generate a form element, set a few attributes and submit the form. This is necessary because the browsers doesn&#8217;t support the <code>DELETE</code> HTTP method by default so Rails needs to emulate it.</p>
<p>The essence of the Unobtrusive JavaScript technique is to <strong>define the JavaScript interaction in a separate behavior layer</strong>.  <span id="more-1086"></span>With Rails 3, the same execution is composed by the HTML output of the <code>link_to</code> helper</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;a href=&quot;/domains/1&quot; data-confirm=&quot;Are you sure?&quot; data-method=&quot;delete&quot; rel=&quot;nofollow&quot;&gt;delete&lt;/a&gt;</div></td></tr></tbody></table></div>
<p>and the separate definition of the JavaScript script to execute.</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;height:300px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br />14<br />15<br />16<br />17<br />18<br />19<br />20<br />21<br />22<br />23<br />24<br />25<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">[...]<br />
<br />
$('a[data-remote],input[data-remote]').live('click', function (e) {<br />
&nbsp; $(this).callRemote();<br />
&nbsp; e.preventDefault();<br />
});<br />
<br />
$('a[data-method]:not([data-remote])').live('click', function (e){<br />
&nbsp; var link = $(this),<br />
&nbsp; &nbsp; href = link.attr('href'),<br />
&nbsp; &nbsp; method = link.attr('data-method'),<br />
&nbsp; &nbsp; form = $('&lt;form method=&quot;post&quot; action=&quot;'+href+'&quot;&gt;'),<br />
&nbsp; &nbsp; metadata_input = '&lt;input name=&quot;_method&quot; value=&quot;'+method+'&quot; type=&quot;hidden&quot; /&gt;';<br />
<br />
&nbsp; if (csrf_param != null &amp;&amp; csrf_token != null) {<br />
&nbsp; &nbsp; metadata_input += '&lt;input name=&quot;'+csrf_param+'&quot; value=&quot;'+csrf_token+'&quot; type=&quot;hidden&quot; /&gt;';<br />
&nbsp; }<br />
<br />
&nbsp; form.hide()<br />
&nbsp; &nbsp; .append(metadata_input)<br />
&nbsp; &nbsp; .appendTo('body');<br />
<br />
&nbsp; e.preventDefault();<br />
&nbsp; form.submit();<br />
});</div></td></tr></tbody></table></div>
<h2>Benefits</h2>
<p>The major benefits of Unobtrusive JavaScripts are:</p>
<ul>
<li><strong>Separation of the behavior from the markup</strong> (as happened for CSS with the separation of the presentation from the markup)</li>
<li><strong>Reusable code</strong> (both HTML and JavaScript code)</li>
<li><a title="Progressive enhancement - Wikipedia, the free encyclopedia" href="http://en.wikipedia.org/wiki/Progressive_enhancement"><strong>Progressive enhancement</strong></a></li>
<li><strong>Capability detection</strong> and <strong>gracefully degradation</strong>, as the opposite of browser detection. You can easily skip an entire JavaScript fragment if the current browser doesn&#8217;t support it or likewise use the JavaScript to replace features not natively supported (such as HTML 5 features).</li>
<li>Better cache support</li>
</ul>
<p>Unobtrusive JavaScript allows developers to write <strong>code much more easier to maintain and debug</strong>, with the appropriate use of design patterns and high-quality development techniques already adopted in other mature programming environments.</p>
<h2>Unobtrusive JavaScript and JavaScript frameworks</h2>
<p>Despite the use of Unobtrusive JavaScript is not a language feature but rather a coding habit, the adoption of this technique has been largely influenced by the availability of high-level JavaScript frameworks.  The main reason is that <strong>JavaScript frameworks offer an easy approach to define and attach custom scripts to HTML elements</strong>, taking advantage of JavaScript features such as <strong>closures</strong> and relieving the user from dealing with cross-browser compatibility.</p>
<p>Let me show you an example using the <a title="jQuery: The Write Less, Do More, JavaScript Library" href="http://jquery.com/">jQuery JavaScript framework</a>. This is a traditional, inline, JavaScript code.</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;a id=&quot;alert&quot; href=&quot;javascript:void(0);&quot; onclick=&quot;alert('Thanks for clicking me');&quot;&gt;Click me&lt;/a&gt;</div></td></tr></tbody></table></div>
<p>This is the equivalent with jQuery</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;script&gt;<br />
jQuery(function($) {<br />
&nbsp; $(&quot;#alert&quot;).click(function() {<br />
&nbsp; &nbsp; alert(&quot;Thanks for clicking me&quot;);<br />
&nbsp; &nbsp; return false;<br />
&nbsp; });<br />
});<br />
&lt;/script&gt;<br />
<br />
&lt;a id=&quot;alert&quot; href=&quot;#&quot;&gt;Click me&lt;/a&gt;</div></td></tr></tbody></table></div>
<p>The advantages become more evident when the code complexity grown. With the following jQuery code you can show/hide all tables with the class <code>.special</code> by clicking a generic element with class <code>.button</code>.</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;script&gt;<br />
&nbsp; jQuery(function($) {<br />
&nbsp; &nbsp; $(&quot;#button&quot;).click(function() {<br />
&nbsp; &nbsp; &nbsp; $(&quot;table.special&quot;).toggle();<br />
&nbsp; &nbsp; });<br />
&nbsp; });<br />
&lt;/script&gt;</div></td></tr></tbody></table></div>
<p>Now, sit back for a moment an think about the example above. Using the traditional inline JavaScript programming you would have to place a call to your own toggle function in every single table element containing the <code>.special</code> class, with a lot of code duplication. Also, what happen if you don&#8217;t know in advance the number of these elements? What if the number of the elements can change, perhaps as the result of an other JavaScript execution?</p>
<p>With the separation of the behavior from the markup, you can easily<strong> change the behavior of an element leaving the DOM element as it is</strong>, exactly how you can change the color or the size of a link using CSS without actually modifying a single byte of the HTML document.</p>
<p>Equally important, you <strong>switch from a JavaScript framework to an other</strong>, simply replacing the behavior layer implementation. The switch won&#8217;t require any change on the HTML document side.</p>
<h2 id="s-html5">Unobtrusive JavaScript and HTML 5</h2>
<p>Technically speaking, there are no dependencies between <strong>Unobtrusive JavaScript and HTML 5</strong>. However, you can take advantage of some HTML 5 features to write even more flexible and reusable Unobtrusive JavaScript.</p>
<p>Again, a good example is represented by the Rails 3 Unobtrusive Javascript feature. Did you remember the click-and-confirm method?</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;a class=&quot;confirm&quot; href=&quot;/destroy&quot; onclick=&quot;return confirm('Are you sure?');&quot;&gt;Click to Destroy&lt;/a&gt;</div></td></tr></tbody></table></div>
<p>We already know we can write an unobtrusive version as follows</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;script&gt;<br />
jQuery(function($) {<br />
&nbsp; $(&quot;.confirm&quot;).click(function() {<br />
&nbsp; &nbsp; if (confirm(&quot;Are you sure?&quot;)) {<br />
&nbsp; &nbsp; &nbsp; // go ahead<br />
&nbsp; &nbsp; } else {<br />
&nbsp; &nbsp; &nbsp; return false;<br />
&nbsp; &nbsp; }<br />
&nbsp; });<br />
});<br />
&lt;/script&gt;<br />
<br />
&lt;a class=&quot;confirm&quot; href=&quot;/destroy&gt;Click to Destroy&lt;/a&gt;</div></td></tr></tbody></table></div>
<p>Let&#8217;s move one step forward. We can write a super-reusable script by moving the confirmation message back to the HTML document, having the script to automatically extract it. A new feature being introduced in HTML 5 is the addition of <a title="John Resig -   HTML 5 data- Attributes" href="http://ejohn.org/blog/html-5-data-attributes/">custom data attributes</a>.</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;script&gt;<br />
jQuery(function($) {<br />
&nbsp; $('a[data-confirm], input[data-confirm]').live('click', function() {<br />
&nbsp; &nbsp; if (!confirm($(this).attr('data-confirm'))) {<br />
&nbsp; &nbsp; &nbsp; return false;<br />
&nbsp; &nbsp; }<br />
&nbsp; });<br />
});<br />
&lt;/script&gt;<br />
<br />
&lt;a data-confirm=&quot;Are you sure?&quot; href=&quot;/destroy&gt;Click to Destroy&lt;/a&gt;</div></td></tr></tbody></table></div>
<p>Also note that, with the new <code>data-confirm</code> attribute we don&#8217;t need anymore to assign custom classes to identify the element.  An other important relationship between these two topics is that you can <strong>use Unobtrusive JavaScript to emulate HTML 5 features</strong> whenever a browser doesn&#8217;t support them natively. I already mentioned this before when I wrote about <strong>capability detection</strong>.</p>
<p>A real example is the jQuery autofocus plugin I created a few months ago to make the HTML 5 input autofocus attribute work with non-HTML-5-compliant browsers.</p>
<p><script src="http://gist.github.com/426727.js?file=jquery.autofocus.js"></script>Likewise, there are several plugins to <a title="Google" href="http://www.google.com/search?sourceid=chrome&amp;ie=UTF-8&amp;q=jquery+html+5+placeholder">emulate the HTML 5 placeholder feature</a>.</p>
<h2>More&#8230;</h2>
<p>Further readings about Unobtrusive JavaScript: <a title="Unobtrusive JavaScript - Wikipedia, the free encyclopedia" href="http://en.wikipedia.org/wiki/Unobtrusive_JavaScript">Wikipedia</a>, <a title="Unobtrusive Javascript" href="http://www.onlinetools.org/articles/unobtrusivejavascript/">Unobtrusive JavaScript Coursebook</a>.</p>
<p>Related posts<ol>
<li><a href='http://www.simonecarletti.com/blog/2010/06/unobtrusive-javascript-in-rails-3/' rel='bookmark' title='Unobtrusive JavaScript in Rails 3'>Unobtrusive JavaScript in Rails 3</a></li>
<li><a href='http://www.simonecarletti.com/blog/2006/11/how-to-add-a-new-feed-handler-in-firefox-20/' rel='bookmark' title='How to add a new feed handler in Firefox 2.0'>How to add a new feed handler in Firefox 2.0</a></li>
<li><a href='http://www.simonecarletti.com/blog/2010/04/inside-ruby-on-rails-serializing-ruby-objects-with-json/' rel='bookmark' title='Understanding Ruby and Rails: Serializing Ruby objects with JSON'>Understanding Ruby and Rails: Serializing Ruby objects with JSON</a></li>
</ol></p>]]></content:encoded>
			<wfw:commentRss>http://www.simonecarletti.com/blog/2010/06/unobtrusive-javascript-technique/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Learning jQuery 1.3 Book Review</title>
		<link>http://www.simonecarletti.com/blog/2010/03/book-review-learning-jquery/</link>
		<comments>http://www.simonecarletti.com/blog/2010/03/book-review-learning-jquery/#comments</comments>
		<pubDate>Mon, 22 Mar 2010 09:11:13 +0000</pubDate>
		<dc:creator>Simone Carletti</dc:creator>
				<category><![CDATA[Books]]></category>
		<category><![CDATA[Programming]]></category>
		<category><![CDATA[javascript]]></category>
		<category><![CDATA[jquery]]></category>
		<category><![CDATA[reviews]]></category>

		<guid isPermaLink="false">http://www.simonecarletti.com/blog/?p=990</guid>
		<description><![CDATA[Learning jQuery 1.3 is one of the most famous books about jQuery, the popular JavaScript framework.]]></description>
			<content:encoded><![CDATA[<p><a href="http://www.simonecarletti.com/blog/out/amzcom-learnjquery13"><img class="alignleft" title="Book Learning jQuery 1.3" src="http://share.weppos.net/simonecarletti/book-packt-learningjquery13-20110930-195149.png" alt="Book Learning jQuery 1.3" width="202" height="249" /></a> It&#8217;s been a while since I published <a title="Book Review: Design Patterns in Ruby" href="http://www.simonecarletti.com/blog/2009/03/book-review-design-patterns-in-ruby/">my last book review on this blog</a>. Last week I decided it was the time to brush up on my JavaScript skills and I pick up my copy of <em>Learning jQuery 1.3</em> I bought on December.</p>
<p><a href="http://www.simonecarletti.com/blog/out/amzcom-learnjquery13"><em>Learning jQuery 1.3</em></a> (<a href="http://www.simonecarletti.com/blog/out/amzcom-learnjquery13">US</a> | <a href="http://www.simonecarletti.com/blog/out/amzuk-learnjquery13">UK</a>) is one of the most famous books about jQuery, the popular JavaScript framework. It&#8217;s written by <strong>Karl Swedberg</strong> &amp; <strong>Jonathan Chaffer</strong> and published by <strong>Packt</strong>.<span id="more-990"></span></p>
<h2>Structure</h2>
<p>The book is implicitly divided into tree parts:</p>
<ul>
<li>The first part, from chapter 1 to 6, provides an <strong>introduction to the framework</strong>. You&#8217;ll learn the philosophy behind jQuery, how to use it and how jQuery can help you to write more powerful user interactions.</li>
<li>The second part, from chapter 7 to 9, contains several <strong>real-world examples</strong>, pulling together what you&#8217;ve learned in the previous part. Most of the examples are actually overtaken by existing jQuery plugins, however creating something from scratch it&#8217;s an important training and it forces you to have your finger in the pie.</li>
<li>The third part, from chapter 10 to 11, <strong>shows you how to extend the jQuery core library</strong> using existing plugins or creating and packaging your own extensions.</li>
</ul>
<h2>Requirements</h2>
<p>You don&#8217;t have to be a JavaScript master to read this book, though some JavaScript skills might be helpful. Moreover, a basic programming knowledge can help you to better understand the examples.</p>
<p>If you want to leverage your JavaScript skills, jump to Appendix C. It offers a really <strong>interesting overview about Closures</strong>: what they are and how you can use them to your advantage.<br />
Reading this section before the other chapters can make the difference later, when you&#8217;ll have to understand the usage of anonymous functions and callbacks in the examples throughout the book.</p>
<p>Quite obviously, you need a good HTML and CSS knowledge.</p>
<p>If you are looking for a JavaScript reference, this isn&#8217;t the book for you. Remember, this book covers the jQuery JavaScript framework, not the JavaScript language.</p>
<h2>Plus</h2>
<p>One of the aspects of the book I appreciate the most is the number of examples. You don&#8217;t have to wait more than ten pages to see the first example of a HTML page enriched by a jQuery effect. Examples are clear, effective and they never overshadow the narration.</p>
<p>Also, this book is not merely a learn-by-example publication. The authors never delegate to the example the role of teaching you how to learn jQuery but they always use them in support of the theoretical explanation. For me, this is a really important point. The risk of learn-by-example books is that, at the end, you are just able to reproduce what the examples show you without having a global mastery of the argument.</p>
<p>Two other important concepts I learned reading this book are g<strong>raceful degradation</strong> and <strong>progressive enhancement</strong>. I must admin I didn&#8217;t care too much about them before reading the book.<br />
The authors remarked these concepts multiple times throughout the book underlining the importance of using JavaScript and jQuery to improve interaction and usability <cite>ensuring that a page will render as accurately, even if not as beautifully, with JavaScript disabled as it does with JavaScript turned on</cite>.</p>
<h2>Minus</h2>
<p>The book does a good job to introduce jQuery and its most important features. However, I would have dedicated more pages to plugins.</p>
<p>Plugins are one of the reasons of the success of jQuery. The books dedicates two chapters to plugins: the first on using plugins and the second on developing plugins. Whilst the list of jQuery plugins continue to grow up and it&#8217;s impossible to keep a book up-to-date with it, I would have appreciated a more deep overview about <a title="Plugins/Authoring - jQuery JavaScript Library" href="http://docs.jquery.com/Plugins/Authoring">authoring a plugin</a>.</p>
<p>Something like plugin best practices, suggestions and why not, <a title="A Plugin Development Pattern" href="http://www.learningjquery.com/2007/10/a-plugin-development-pattern">plugin development patterns</a>.</p>
<h2>In conclusion</h2>
<p>If you are an <strong>user interface designer</strong> or <strong>interaction designer</strong>, the first part teaches you how to alter the structure of an HTML document attaching or moving page elements, fire off behaviors responding to user events and interact with server-side functionalities.</p>
<p>If you are a <strong>programmer</strong>, the third part offers some precious suggestions to package your scripts making your code more reusable and maintainable.</p>
<p>Regardless your activity, if you are looking for a book to better understand how jQuery works, <em>Learning jQuery</em> is definitely a recommended reading. Someone can argue that online you can easily find tons of articles and discussions about jQuery that make a book quite useless. In my opinion, this is exactly the reason why a book can make the difference. When reading a book, you find all the information you need concentrated in a single source, organized into a logical learning flow and you don&#8217;t need to waste your time searching for information, verifying blog credibility or discarding outdated solutions. A good book if often the preferred starting point if you want to learn a new technology in the minimum amount of time.</p>
<h2>Where to Find Learning jQuery</h2>
<p>You can get a printed copy at <a href="http://www.simonecarletti.com/blog/out/amzcom-learnjquery13">Amazon.com</a>, <a href="http://www.simonecarletti.com/blog/out/amzuk-learnjquery13">Amazon.co.uk</a>, or at your other favorite book seller.</p>
<p>Related posts<ol>
<li><a href='http://www.simonecarletti.com/blog/2011/03/book-review-html-5-up-and-running/' rel='bookmark' title='HTML 5 Up and Running Book Review'>HTML 5 Up and Running Book Review</a></li>
<li><a href='http://www.simonecarletti.com/blog/2009/03/book-review-design-patterns-in-ruby/' rel='bookmark' title='Design Patterns in Ruby Book Review'>Design Patterns in Ruby Book Review</a></li>
<li><a href='http://www.simonecarletti.com/blog/2011/10/eloquent-ruby/' rel='bookmark' title='Eloquent Ruby Book Review'>Eloquent Ruby Book Review</a></li>
</ol></p>]]></content:encoded>
			<wfw:commentRss>http://www.simonecarletti.com/blog/2010/03/book-review-learning-jquery/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Relative time&#8230; when the time does matter</title>
		<link>http://www.simonecarletti.com/blog/2009/12/robodomain-relative-time/</link>
		<comments>http://www.simonecarletti.com/blog/2009/12/robodomain-relative-time/#comments</comments>
		<pubDate>Tue, 29 Dec 2009 22:06:44 +0000</pubDate>
		<dc:creator>Simone Carletti</dc:creator>
				<category><![CDATA[Programming]]></category>
		<category><![CDATA[Softwares]]></category>
		<category><![CDATA[javascript]]></category>
		<category><![CDATA[jquery]]></category>
		<category><![CDATA[robodomain]]></category>
		<category><![CDATA[timeago]]></category>
		<category><![CDATA[usability]]></category>

		<guid isPermaLink="false">http://www.simonecarletti.com/blog/?p=867</guid>
		<description><![CDATA[The next RoboDomain EAP will include a small improvement on how dates are formatted.]]></description>
			<content:encoded><![CDATA[<p>When talking about deadlines, relative time it&#8217;s usually more effective than a raw timestamp. A banner with the message &#8220;the offer ends in 2 days&#8221; it&#8217;s likely to capture more attention rather than &#8220;the offer ends December 30th&#8221;.</p>
<p>Likewise, people tends to pay more attention when an expiration is expressed in words. For this reason, the next RoboDomain EAP will include a small improvement on how dates are formatted. When applicable, RoboDomain will use a relative time — <code>in 2 hours</code>, <code>in 3 days</code>, <code>in 1 month</code> — instead of the raw timestamp value.</p>
<div id="attachment_870" class="wp-caption aligncenter" style="width: 510px"><img class="size-medium wp-image-870" title="RoboDomain with Relative date" src="http://www.simonecarletti.com/blog/wp-content/uploads/2009/12/robodomain-timeago-500x228.png" alt="" width="500" height="228" /><p class="wp-caption-text">RoboDomain with Relative date</p></div>
<p><span id="more-867"></span>Under the hood, we used the <a title="timeago: a jQuery plugin" href="http://timeago.yarp.com/">awesome timeago jQuery plugin</a> with a couple of customizations.</p>
<p>This feature, along with the <a href="http://www.simonecarletti.com/blog/2009/12/robodomain-usability-improvements/">usability improvements</a> and many other changes, will be available with the next EAP release.</p>
<p>Related posts<ol>
<li><a href='http://www.simonecarletti.com/blog/2009/12/robodomain-usability-improvements/' rel='bookmark' title='RoboDomain usability improvements'>RoboDomain usability improvements</a></li>
<li><a href='http://www.simonecarletti.com/blog/2009/12/please-welcome-robodomain/' rel='bookmark' title='Welcome RoboDomain'>Welcome RoboDomain</a></li>
</ol></p>]]></content:encoded>
			<wfw:commentRss>http://www.simonecarletti.com/blog/2009/12/robodomain-relative-time/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>How to add a new feed handler in Firefox 2.0</title>
		<link>http://www.simonecarletti.com/blog/2006/11/how-to-add-a-new-feed-handler-in-firefox-20/</link>
		<comments>http://www.simonecarletti.com/blog/2006/11/how-to-add-a-new-feed-handler-in-firefox-20/#comments</comments>
		<pubDate>Sat, 04 Nov 2006 15:45:40 +0000</pubDate>
		<dc:creator>Simone Carletti</dc:creator>
				<category><![CDATA[Softwares]]></category>
		<category><![CDATA[firefox]]></category>
		<category><![CDATA[javascript]]></category>
		<category><![CDATA[registercontenthandler]]></category>

		<guid isPermaLink="false">http://www.simonecarletti.com/blog/2006/11/how-to-add-a-new-feed-handler-in-firefox-20/</guid>
		<description><![CDATA[How to add a new feed handler to Firefox 2.0 without tweaking the registry.
]]></description>
			<content:encoded><![CDATA[<div class="flash-message warning">
<p><strong>December 30th, 2008</strong>. This post was published long time ago on the Italian version of my blog then moved here after the English blog has been opened. Please note that the following post can contain outdated information and (probably) multiple typos.</p>
</div>
<p>Firefox 2.0 is out&#8230; uhm? what are you saying? what a great news?&#8230; oh yeah, but this isn&#8217;t the main topic of this post.</p>
<p>As someone of you probably remember, on June I made a few tests with Firefox 2.0 Bon Echo 3 focused on how the new Firefox handles feeds. Firefox 2 gives you full control over Web feeds, showing you a preview and letting you choose how you want to subscribe.</p>
<p>At the end of the tests I wrote an article showing how is possible to add a new content handler, aka web aggregator, in Firefox 2.0&#8230; <a href="http://digg.com/software/How_to_add_Rmail_as_a_choice_in_Firefox_2_0">it was digged too</a>! <em>(Note. The article is no longer available)</em>.<br />
Since Firefox 2.0 was not yet released at the time the article was written, I didn&#8217;t know that there was an easier way to add an content handler without tweaking by hand Firefox registry.</p>
<p>Using <code>registerContentHandler()</code> javascript function is possible to add with just one click a new feed handler&#8230; how? Let me show you.</p>
<p><span id="more-12"></span></p>
<h2>Adding a new feed handler to Firefox 2.0 with registerContentHandler()</h2>
<p><a href="https://developer.mozilla.org/En/DOM:window.navigator.registerContentHandler">registerContentHandler()</a> is a JavaScript function that allows you to register a new content handler in Firefox 2.0.<br />
It accepts 3 required params:</p>
<dl>
<dt><var>mimeType</var></dt>
<dd>the content mime type.<br />
For a feed must be <code>application/vnd.mozilla.maybe.feed</code>. </dd>
<dt><var>uri</var></dt>
<dd>the content handler URI.<br />
<code>%s</code> can be used as a placeholder for the resource URI. </dd>
<dt><var>title</var></dt>
<dd>the content handler Title</dd>
</dl>
<p>Once again, let&#8217;s use Rmail as example.<br />
Rmail add-new-subscription URI is (always the same) <code>http://www.r-mail.org/bm.aspx?rss=%s</code> while content handler title is Rmail.<br />
Thus, the final JavaScript should looks like the following.</p>
<div class="codecolorer-container text default brush: plain" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">navigator.registerContentHandler('application/vnd.mozilla.maybe.feed',<br />
'http://www.r-mail.org/bm.aspx?rss=%s',<br />
'Rmail');</div></td></tr></tbody></table></div>
<p>You can put/call this JavaScript function where everywhere in a HTML page, for example as a link (<a href="http://blog.netvibes.com/?2006/10/25/83-firefox-2-and-netvibes">as Netvibes did</a>)&#8230;</p>
<h3>Example 1.</h3>
<p><strong>Look &amp; feel</strong></p>
<p><!-- example 1 l&#038;f --></p>
<p><a href="javascript:window.navigator.registerContentHandler('application/vnd.mozilla.maybe.feed','http://www.r-mail.org/bm.aspx?rss=%s','Rmail');">Click here</a> and add Rmail</p>
<p><!-- /example 1 l&#038;f --></p>
<p><strong>Code</strong></p>
<p><!-- example 1 code --></p>
<div class="codecolorer-container text default brush: html" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;p&gt;<br />
&lt;a href=&quot;javascript:window.navigator.registerContentHandler('application/vnd.mozilla.maybe.feed',<br />
'http://www.r-mail.org/bm.aspx?rss=%s','Rmail');&quot;&gt;Click here&lt;/a&gt;<br />
and add Rmail<br />
&lt;/p&gt;</div></td></tr></tbody></table></div>
<p><!-- /example 1 code --></p>
<p>&#8230; you can put it into a form button&#8230;</p>
<h3>Example 2.</h3>
<p><strong>Look &amp; feel</strong></p>
<p><!-- example 2 l&#038;f --></p>
<input onclick="window.navigator.registerContentHandler('application/vnd.mozilla.maybe.feed',&lt;br /&gt; 'http://www.r-mail.org/bm.aspx?rss=%s','Rmail');" name="add" type="button" value="Click here and add Rmail" />
<p><!-- example 2 l&#038;f --></p>
<p><strong>Code</strong></p>
<p><!-- example 2 code --></p>
<div class="codecolorer-container text default brush: html" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;p&gt;<br />
&lt;input type=&quot;button&quot; name=&quot;add&quot; value=&quot;Click here and add Rmail&quot;<br />
onclick=&quot;window.navigator.registerContentHandler('application/vnd.mozilla.maybe.feed',<br />
'http://www.r-mail.org/bm.aspx?rss=%s','Rmail');&quot; /&gt;<br />
<br />
&lt;/p&gt;</div></td></tr></tbody></table></div>
<p><!-- /example 2 code --></p>
<p>or include it into a JavaScript function and call it anywhere in the page.</p>
<h3>Example 3.</h3>
<p><strong>Code</strong></p>
<p><!-- example 3 code --></p>
<div class="codecolorer-container text default brush: html" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;script type=&quot;text/javascript&quot;&gt;<br />
function subWith() {<br />
navigator.registerContentHandler('application/vnd.mozilla.maybe.feed', 'http://www.r-mail.org/bm.aspx?rss=%s', 'Rmail');<br />
}<br />
<br />
&lt;/script&gt;<br />
&lt;input type=&quot;button&quot; name=&quot;add&quot; value=&quot;Click here and add Rmail&quot;<br />
onclick=&quot;function subWith();&quot; /&gt;</div></td></tr></tbody></table></div>
<p><!-- /example 3 code --></p>
<h2>More power to registerContentHandler()</h2>
<p>This tutorial might be closed here, but the real reason why I wrote this post is to show how is possible to add more power to <code>registerContentHandler()</code> with a few JavaScript lines.</p>
<p>The idea comes from this post where <a href="http://www.therssweblog.com/">Randy</a> shows a button to add Rmail as a new content handler.<br />
In a comment <cite>pat</cite> asks which is the best technique between Randy&#8217;s magic button (see example 2 and example 3) and my tutorial <em>(Note. The tutorial is no longer available)</em>.</p>
<p>This is Randy&#8217;s answer.</p>
<blockquote><p>Pat,<br />
Simone&#8217;s technique is actually superior as it also includes the email address. I&#8217;m working on making that possible too!<br />
Randy</p></blockquote>
<p>Don&#8217;t worry Randy, I will give you an help! :D</p>
<p>The only difference between my code and Randy&#8217;s code is that I used the following Rmail subscription string (please note the mailto param)</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">http://www.r-mail.org/bm.aspx?rss=%s&lt;strong&gt;&amp;mailto=YOUR_EMAIL&lt;/strong&gt;</div></td></tr></tbody></table></div>
<p>instead of</p>
<div class="codecolorer-container text default" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">http://www.r-mail.org/bm.aspx?rss=%s</div></td></tr></tbody></table></div>
<p>Thus, what we should do is <strong>find a way to allow user to type its own email address and append it to the content handler URI</strong>.</p>
<p>My first idea was to <strong>create a new input text field</strong>. It&#8217;s better than using other techniques such as JavaScript input boxes since the field can be easily filled with a server side programming language in a more complex site, can be validated and you can re-use in thousand ways.<br />
While I was writing the code, I decided to do a little more. Why not creating a script that allows developers to add custom arguments to a content handler URI instead of a single one? Rmail just needs a <code>mailto</code> param but other readers may need <code>mail</code> and <code>user</code>&#8230;</p>
<p>This is what I wrote!</p>
<p>The following script allows you to register a new content handler in Firefox 2.0 just calling a simple function.<br />
In addition, you can create as many form field as you wish calling them <code>name="args"</code>. For each field, the script will collect its value and if the field isn&#8217;t empty, will appends the value to the content handler URI.</p>
<p>Let&#8217;s see an example. Again, I will use Rmail and I will show you how it&#8217;s easy to append your personal email to the URI.</p>
<h3>Example 4.</h3>
<div class="codecolorer-container text default brush: html" style="overflow:auto;white-space:nowrap;border:1px solid #9F9F9F;width:435px;"><table cellspacing="0" cellpadding="0"><tbody><tr><td style="padding:5px;text-align:center;color:#888888;background-color:#EEEEEE;border-right: 1px solid #9F9F9F;font: normal 12px/1.4em Monaco, Lucida Console, monospace;"><div>1<br />2<br />3<br />4<br />5<br />6<br />7<br />8<br />9<br />10<br />11<br />12<br />13<br /></div></td><td><div class="text codecolorer" style="padding:5px;font:normal 12px/1.4em Monaco, Lucida Console, monospace;white-space:nowrap">&lt;!-- include the script --&gt;<br />
&lt;script type=&quot;text/javascript&quot; src=&quot;firefox2-registerFeedHandler.js&quot;&gt;&lt;/script&gt;<br />
<br />
&lt;!-- add as many field as you wish.<br />
Each field called 'args' will be appended to content handler URI.<br />
The argument name will be its unique form Id, the value the field value.<br />
--&gt;<br />
&lt;input type=&quot;text&quot; name=&quot;args&quot; id=&quot;email&quot; value=&quot;&quot; /&gt;&lt;br /&gt;<br />
<br />
&lt;!-- call the function, use subWith(true) instead of subWith()<br />
to collect form fields.<br />
--&gt;<br />
&lt;input type=&quot;button&quot; name=&quot;subWith&quot; onclick=&quot;subWith(true);&quot; value=&quot;Make Rmail your Firefox RSS handler&quot; /&gt;</div></td></tr></tbody></table></div>
<p>First you must include the script.<br />
Don&#8217;t forget to customize <code>chUri</code> and <code>chTitle</code> variables, as written at the top of the javaScript file.</p>
<p>Then add an input text field for each argument you wish to append to the URI. You can also use hidden inputs to pass hidden values.<strong> Don&#8217;t forget to call them <code>args</code> or the script will not work.</strong></p>
<p>Now call the <code>subWith()</code> function. You can use a link, a button or a common JavaScript event.</p>
<p>Enjoy the confirmation dialog! :D</p>
<p><img class="centered" src="http://www.simonecarletti.com/blog/public/2006/11/firefox_new_feed_handler/dialog.gif" alt="Add new handler confirmation dialog" /></p>
<p>Related posts<ol>
<li><a href='http://www.simonecarletti.com/blog/2006/06/feedburner-stats-2-feed/' rel='bookmark' title='FeedBurner Stats 2 Feed'>FeedBurner Stats 2 Feed</a></li>
</ol></p>]]></content:encoded>
			<wfw:commentRss>http://www.simonecarletti.com/blog/2006/11/how-to-add-a-new-feed-handler-in-firefox-20/feed/</wfw:commentRss>
		<slash:comments>9</slash:comments>
		</item>
	</channel>
</rss>

