<?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:itunes="http://www.itunes.com/dtds/podcast-1.0.dtd"
	xmlns:media="http://search.yahoo.com/mrss/"
>

<channel>
	<title>SitePoint &#187; JavaScript &amp; CSS</title>
	<atom:link href="http://www.sitepoint.com/blogs/category/tech/dhtml-css/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.sitepoint.com/blogs</link>
	<description>News, opinion, and fresh thinking for web developers and designers. The official podcast of sitepoint.com.</description>
	<pubDate>Fri, 21 Nov 2008 22:08:15 +0000</pubDate>
	<generator>http://wordpress.org/?v=2.5</generator>
	<language>en</language>
		<!-- podcast_generator="podPress/8.8" -->
		<copyright>&#xA9;SitePoint </copyright>
		<managingEditor>kevin@sitepoint.com (SitePoint)</managingEditor>
		<webMaster>kevin@sitepoint.com(SitePoint)</webMaster>
		<category>Technology</category>
		<ttl>1440</ttl>
		<itunes:keywords>web,development,design,technology,standards,HTML,CSS,JavaScript</itunes:keywords>
		<itunes:subtitle>Fresh Thinking for Web Developers and Designers</itunes:subtitle>
		<itunes:summary>News, opinion, and fresh thinking for web developers and designers. The official podcast of sitepoint.com.</itunes:summary>
		<itunes:author>SitePoint</itunes:author>
		<itunes:category text="Technology"/>
<itunes:category text="Technology">
  <itunes:category text="Tech News"/>
</itunes:category>
		<itunes:owner>
			<itunes:name>SitePoint</itunes:name>
			<itunes:email>kevin@sitepoint.com</itunes:email>
		</itunes:owner>
		<itunes:block>No</itunes:block>
		<itunes:explicit>no</itunes:explicit>
		<itunes:image href="http://www.sitepoint.com/blogs/wp-content/themes/sitepoint/images/sitepointpodcast300.png" />
		<image>
			<url>http://www.sitepoint.com/blogs/wp-content/themes/sitepoint/images/sitepointpodcast144.png</url>
			<title>SitePoint</title>
			<link>http://www.sitepoint.com/blogs</link>
			<width>144</width>
			<height>144</height>
		</image>
		<item>
		<title>arguments: A JavaScript Oddity</title>
		<link>http://www.sitepoint.com/blogs/2008/11/11/arguments-a-javascript-oddity/</link>
		<comments>http://www.sitepoint.com/blogs/2008/11/11/arguments-a-javascript-oddity/#comments</comments>
		<pubDate>Tue, 11 Nov 2008 06:06:19 +0000</pubDate>
		<dc:creator>Andrew Tetlaw</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=3170</guid>
		<description><![CDATA[arguments is the name of a local, array-like object available inside every function. It&#8217;s quirky, often ignored, but the source of much programming wizardry; all the major JavaScript libraries tap into the power of the arguments object. It&#8217;s something every JavaScript programmer should become familiar with.
Inside any function you can access it through the variable: [...]]]></description>
			<content:encoded><![CDATA[<p><strong><code>arguments</code> is the name of a local, array-like object available inside every function. It&#8217;s quirky, often ignored, but the source of much programming wizardry; all the major JavaScript libraries tap into the power of the <code>arguments</code> object. It&#8217;s something every JavaScript programmer should become familiar with.</strong></p>
<p>Inside any function you can access it through the variable: <code>arguments</code>, and it contains an array of all the arguments that were supplied to the function when it was called. It&#8217;s not actually a JavaScript array; <code>typeof arguments</code> will return the value: <code>"object"</code>. You can access the individual argument values through an array index, and it has a <code>length</code> property like other arrays, but it doesn&#8217;t have the standard <code>Array</code> methods like <code>push</code> and <code>pop</code>.</p>
<h2>Create Flexible Functions</h2>
<p>Even though it may appear limited, <code>arguments</code> is a very useful object. For example, you can make functions that accept a variable number of arguments. The <code>format</code> function, found in the <a href="http://base2.googlecode.com/">base2</a> library by Dean Edwards, demonstrates this flexibility:</p>
<pre><code class="javascript">function format(string) {
  var args = arguments;
  var pattern = new RegExp("%([1-" + arguments.length + "])", "g");
  return String(string).replace(pattern, function(match, index) {
    return args[index];
  });
};</code></pre>
<p>You supply a template string, in which you add place-holders for values using <code>%1</code> to <code>%9</code>, and then supply up to 9 other arguments which represent the strings to insert. For example:</p>
<pre><code class="javascript">format("And the %1 want to know whose %2 you %3", "papers", "shirt", "wear");</code></pre>
<p>The above code will return the string <code>"And the papers want to know whose shirt you wear"</code>.</p>
<p>One thing you may have noticed is that, in the function definition for <code>format</code>, we only specified one argument: <code>string</code>. JavaScript allows us to pass any number of arguments to a function, regardless of the function definition, and the <code>arguments</code> object has access to all of them.</p>
<h2>Convert it to a Real Array</h2>
<p>Even though <code>arguments</code> is not an actual JavaScript array we can easily convert it to one by using the standard <code>Array</code> method,  <code>slice</code>, like this:</p>
<pre><code class="javascript">var args = Array.prototype.slice.call(arguments);</code></pre>
<p>The variable <code>args</code> will now contain a proper JavaScript <code>Array</code> object containing all the values from the <code>arguments</code> object.</p>
<h2>Create Functions with Preset Arguments</h2>
<p>The <code>arguments</code> object allows us to perform all sorts of JavaScript tricks. Here is the definition for the <code>makeFunc</code> function. This function allows you to supply a function reference and any number of arguments for that function. It will return an anonymous function that calls the function you specified, and supplies the preset arguments together with any new arguments supplied when the anonymous function is called:</p>
<pre><code class="javascript">function makeFunc() {
  var args = Array.prototype.slice.call(arguments);
  var func = args.shift();
  return function() {
    return func.apply(null, args.concat(Array.prototype.slice.call(arguments)));
  };
}</code></pre>
<p>The first argument supplied to <code>makeFunc</code> is considered to be a reference to the function you wish to call (yes, there&#8217;s no error checking in this simple example) and it&#8217;s removed from the arguments array. <code>makeFunc</code> then returns an anonymous function that uses the <code>apply</code> method of the <code>Function</code> object to call the function specified.</p>
<div id="adz" class="vertical"></div><p>The first argument for <code>apply</code> refers to the scope the function will be called in; basically what the keyword <code>this</code> will refer to inside the function being called. That&#8217;s a little advanced for now, so we just keep it <code>null</code>. The second argument is an array of values that will be converted into the <code>arguments</code> object for the function. <code>makeFunc</code> concatenates the original array of values onto the array of arguments supplied to the anonymous function and supplies this to the called function.</p>
<p>Lets say there was a message you needed to output where the template was always the same. To save you from always having to quote the template every time you called the <code>format</code> function you could use the <code>makeFunc</code> utility function to return a function that will call <code>format</code> for you and fill in the template argument automatically:</p>
<pre><code class="javascript">var majorTom = makeFunc(format, "This is Major Tom to ground control. I'm %1.");</code></pre>
<p>You can call the <code>majorTom</code> function repeatedly like this:</p>
<pre><code class="javascript">majorTom("stepping through the door");
majorTom("floating in a most peculiar way");</code></pre>
<p>Each time you call the <code>majorTom</code> function it calls the <code>format</code> function with the first argument, the template, already filled in. The above calls return:</p>
<pre><code>"This is Major Tom to ground control. I'm stepping through the door."
"This is Major Tom to ground control. I'm floating in a most peculiar way."</code></pre>
<h2>Create Self-referencing Functions</h2>
<p>You may think that&#8217;s pretty cool, but wait, arguments has one more surprise; it has another useful property: <code>callee</code>. <code>arguments.callee</code> contains a reference to the function that created the <code>arguments</code> object. How can we use such a thing? <code>arguments.callee</code> is a handy way an anonymous function can refer to itself.</p>
<p><code>repeat</code> is a function that takes a function reference, and 2 numbers. The first number is how many times to call the function and the second represents the delay, in milliseconds, between each call. Here&#8217;s the definition for <code>repeat</code>:</p>
<pre><code class="javascript">function repeat(fn, times, delay) {
  return function() {
    if(times-- > 0) {
      fn.apply(null, arguments);
      var args = Array.prototype.slice.call(arguments);
      var self = arguments.callee;
      setTimeout(function(){self.apply(null,args)}, delay);
    }
  };
}</code></pre>
<p><code>repeat</code> uses <code>arguments.callee</code> to get a reference, in the variable <code>self</code>, to the anonymous function that runs the originally supplied function. This way the anonymous function can call itself again after a delay using the standard <code>setTimeout</code> function.</p>
<p>So, I have this, admittedly simplistic, function in my application that takes a string and pops-up an alert box containing that string:</p>
<pre><code class="javascript">function comms(s) {
  alert(s);
}</code></pre>
<p>However, I want to create a special version of that function that repeats 3 times with a delay of 2 seconds between each time. With my <code>repeat</code> function, I can do this:</p>
<pre><code class="javascript">var somethingWrong = repeat(comms, 3, 2000);

somethingWrong("Can you hear me, major tom?");</code></pre>
<p>The result of calling the <code>somethingWrong</code> function is an alert box repeated 3 times with a 2 second delay between each alert.</p>
<p><code>arguments</code> is not often used, a little quirky, but full of surprises and well worth getting to know!</p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=136&amp;did=adz&amp;adtype=vertical" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/11/11/arguments-a-javascript-oddity/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Is Using Lots of div Tags Really That Bad?</title>
		<link>http://www.sitepoint.com/blogs/2008/10/28/is-using-lots-of-div-tags-really-that-bad/</link>
		<comments>http://www.sitepoint.com/blogs/2008/10/28/is-using-lots-of-div-tags-really-that-bad/#comments</comments>
		<pubDate>Tue, 28 Oct 2008 12:27:44 +0000</pubDate>
		<dc:creator>Andrew Tetlaw</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=3131</guid>
		<description><![CDATA[Our latest book has caused much debate, and one comment we've seen posted frequently is that “replacing table tags with divs that display as tables is no different; you may as well just use tables.” Let's take a closer look at that argument.]]></description>
			<content:encoded><![CDATA[<p>Our latest book &#8212; <a href="http://www.sitepoint.com/books/csswrong1/">the one with the controversial title</a> &#8212; has caused much debate and more knee-jerk reactions than a bucket of frogs at a barn dance. A comment I&#8217;ve seen posted frequently is that &#8220;replacing <code>table</code> tags with <code>div</code>s that display as tables is no different; you may as well just use tables.&#8221; The argument is interesting because it sounds like the commenter is implying that the only reason not to use <code>table</code> tags is the number of tags involved.</p>
<p>I&#8217;m going to stick my neck out and say yes, even if you just replace all your <code>table</code>, <code>tr</code>, and <code>td</code> tags with <code>div</code> tags that display like those table elements, it&#8217;s better than using HTML tables for layout.</p>
<p>No one is negatively affected by the overuse of structural <code>div</code> tags. The same can&#8217;t be said for the use of HTML tables for layout.</p>
<p>A web page that uses nested tables for layout will be difficult to print, difficult to view on a mobile device, and difficult to navigate for users of screen readers. A screen reader application will often stumble over nested HTML tables, announcing something like &#8220;table with 5 rows and 2 columns&#8221; as it enters the table content and &#8220;table end&#8221; as it leaves. The same web page using nested <code>div</code> elements can be styled to stack neatly for print and viewing on a mobile device, and screen readers ignore <code>div</code> elements.</p>
<div id="adz" class="vertical"></div><p>By using HTML tables you are implying that the contents of each cell relate to the contents of other cells in 2 dimensions: in the same row and in the same column. On the other hand a <code>div</code> implies no such relation with other <code>div</code> elements. It&#8217;s simply content scaffolding, and no meaning is derived from their use.</p>
<p>OK, blindly replacing all table-related tags with <code>div</code> elements may not be the correct approach to the problem, but to say that it is &#8220;just as bad&#8221; as using HTML tables for layout is wrong. <a href="http://www.w3.org/TR/html401/struct/global.html#edef-DIV">HTML 4.01</a> defines the <code>div</code> as a &#8220;generic language/style container&#8221; or more specifically:</p>
<blockquote><p>The <code>DIV</code> and <code>SPAN</code> elements, in conjunction with the <code>id</code> and <code>class</code> attributes, offer a generic mechanism for adding structure to documents. These elements define content to be inline (<code>SPAN</code>) or block-level (<code>DIV</code>) but impose no other presentational idioms on the content. Thus, authors may use these elements in conjunction with style sheets, the <code>lang</code> attribute, etc., to tailor HTML to their own needs and tastes.</p></blockquote>
<p>So we can use <code>div</code> elements to define content blocks; sounds like using nested <code>div</code> elements for structuring content is perfectly valid. As long as you don&#8217;t use <code>div</code> elements in place of more appropriate ones like headings, paragraphs, blockquotes, lists, and of course, tables for tabular data, then you&#8217;re doing fine.</p>
<p>The approach you take when creating a layout using HTML table elements is to first lock-in the layout in HTML before you style your web page. This is wrong and flies in the face of established best practice: separate your presentation from your content.</p>
<p>This is completely different to the CSS layout approach, even when using a lot of <code>div</code> elements. For example, I could wrap all of the content that represents site branding in a <code>div</code> tag, and all of the content that represents additional site information in a another <code>div</code> tag. The fact that, in CSS, I may apply a style that places the site branding at the top of the web page and the additional site information at the bottom, is not important yet. At the layout stage I might do that, or I may use the CSS table-related display values to make them into columns or rows. The markup can be styled in multiple ways because the approach does not lock-in the layout in the HTML markup.</p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=136&amp;did=adz&amp;adtype=vertical" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/10/28/is-using-lots-of-div-tags-really-that-bad/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Techy Treasure #2: Twitter Buzz Widget</title>
		<link>http://www.sitepoint.com/blogs/2008/10/24/techy-treasure-2-twitter-buzz-widget/</link>
		<comments>http://www.sitepoint.com/blogs/2008/10/24/techy-treasure-2-twitter-buzz-widget/#comments</comments>
		<pubDate>Fri, 24 Oct 2008 03:15:48 +0000</pubDate>
		<dc:creator>craiga</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<category><![CDATA[Web Tech]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=3124</guid>
		<description><![CDATA[Personally I’m not a huge fan of Twitter, but it is all the rage at the moment. In fact, there was so much buzz about the launch of "Everything You Know About CSS Is Wrong!" that we’ve added a simple “Twitter Buzz” widget to it’s sales page.  Here's how.]]></description>
			<content:encoded><![CDATA[<p>Personally I&#8217;m not a huge fan of Twitter, but it is <a href="http://www.sitepoint.com/blogs/2008/10/23/follow-us-on-twitter-attend-edge-of-the-web-for-free/">all</a> <a href="http://www.sitepoint.com/blogs/2008/10/21/twitter-as-a-tool-for-social-change/">the</a> <a href="http://technology.timesonline.co.uk/tol/news/tech_and_web/the_web/article4908374.ece">rage</a> at the moment and even a cynic like me can see that it&#8217;s a valuable tool for connecting with your clients. In fact, there was so much buzz about the launch of <a href="http://www.sitepoint.com/books/csswrong1/">Everything You Know About CSS Is Wrong!</a>  that we&#8217;ve added a simple &#8220;Twitter Buzz&#8221; widget to it&#8217;s sales page.</p>
<p>While building my little widget I couldn&#8217;t find anything <em>quite</em> like what I was after, so I threw something together with PHP and <a href="http://jquery.com/">jQuery</a>, and now I&#8217;d like share it with you.</p>
<h2>The Server-Side Twitter Proxy</h2>
<p>This one&#8217;s dead simple. Check it out:</p>
<div id="adz" class="horizontal"></div><pre><code class="php">&lt;?php
header("Content-Type: text/xml");
// replace Foobar with your URL-encoded search term
echo(file_get_contents(
    "http://search.twitter.com/search.atom?q=Foobar"));
?&gt;</code></pre>
<p>Here we simply grab the search results from <code>http://search.twitter.com/search.atom?q=Foobar</code>, and return it straight to the client. We also set the content type of the response to <code>text/xml</code>; without this, jQuery doesn&#8217;t know to handle the response as an XML DOM Document.</p>
<p><h2>Client-Side Twitter Buzz Widget</h2>
</p>
<p>With our server-side proxy and jQuery in place, we can start injecting the response into our document. Place a hidden <code>div</code> with the <code>id</code> <code>twitter-buzz</code> somewhere in your document, then include the following JavaScript:</p>
<pre><code class="javascript">$(function() {
    $.get("twitter-proxy.php", function(data, status) {
      // check for success
      if(status == "success") {
        // check for entries
        if($("entry", data).size() > 0) {   
          // create the list               
          var list = $("&lt;ul&gt;").get(0);
          // iterate through entries
          $("entry", data).each(function(index, entry) {
            // parse out the details of the tweet
            var authorElement = $("author", entry).get(0);
            var authorName = $("name", authorElement).text();
            var authorUri = $("uri", authorElement).text();
            var authorImage = $("link[rel='image']", entry).attr("href");
            var text = $("title", entry).text();
            // add the tweet to our list
            $(list).append("&lt;li&gt;&lt;a href=\"" + authorUri + "\"&gt;" +
                "&lt;img src=\"" + authorImage + "\" alt=\"" + authorName + "\" /&gt;" +
                "&lt;/a>&lt;span&gt;" + text + "&lt;/span&gt;");
          });
          // add the list to the document
          $("#twitter-buzz").append(list);
          // reveal the area
          $("#twitter-buzz").show("slow");
        }
      }
    });
});</code></pre>
<p>This simply grabs the Atom response from the Twitter proxy we created earlier, creates an unordered list of tweets, then adds them to the document. Even if something goes wrong, or the search returns zero tweets, the page won&#8217;t be corrupted at all; all we&#8217;ll have is a hidden, empty <code>div</code> in the page.</p>
<p>There are certainly improvements that could be made to this widget, such as adding automatically refreshing itself on a timer and automagically adding links for @replies, but I&#8217;ll leave adding these features up to you.</p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=137&amp;did=adz&amp;adtype=horizontal" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/10/24/techy-treasure-2-twitter-buzz-widget/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Techy Treasures #1: Feelin&#8217; Empty</title>
		<link>http://www.sitepoint.com/blogs/2008/10/16/techy-treasures-1/</link>
		<comments>http://www.sitepoint.com/blogs/2008/10/16/techy-treasures-1/#comments</comments>
		<pubDate>Thu, 16 Oct 2008 06:03:23 +0000</pubDate>
		<dc:creator>brothercake</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=3100</guid>
		<description><![CDATA[Techy Treasures is a new, regular feature where we'll be publishing tips, tricks and code snippets for web developers. And to start with, a neat little function that checks whether a variable is empty, inspired by PHP’s function of the same name.

 And to start with, a neat little function that checks whether a variable is…]]></description>
			<content:encoded><![CDATA[<p><cite>Techy Treasures</cite> is a new, regular feature where we&#8217;ll be publishing tips, tricks and code snippets for web developers. These are not blue-sky bubbles, they&#8217;re solid, proven ideas that you can use in the wild with confidence.</p>
<p>And to start with, a neat little function that checks whether a variable is empty, inspired by <a href="http://au.php.net/empty">PHP&#8217;s function of the same name</a>:</p>
<pre><code class="javascript">function empty(data)
{
	if(typeof data == 'undefined' || data === null) { return true; }
	else if(typeof data == 'string' &amp;&amp; (data === '0' || data.replace(/^\s+|\s+$/g, '') === '')) { return true; }
	else if(typeof data == 'number' &amp;&amp; data === 0) { return true; }
	else if(typeof data == 'boolean' &amp;&amp; data === false) { return true; }
	else if(typeof data == 'object')
	{
		if(data instanceof Array &amp;&amp; data.length == 0) { return true; }
		else
		{
			var n = 0;
			for(var i in data)
			{
				if(!data.hasOwnProperty(i)) { continue; }
				n++;
			}
			if(n == 0) { return true; }
		}
	}
	return false;
}</code></pre>
<p>So a variable is considered empty if it&#8217;s:</p>
<ul>
<li>undefined</li>
<li><code>null</code></li>
<li>a string, and its value is <code>"0"</code>, or an empty string, or only whitespace</li>
<li>a number, and its value is <code>0</code></li>
<li>a boolean, and its value is <code>false</code></li>
<li>an array, and it has no values</li>
<li>an object, and it has no enumerable properties</li>
</ul>
<div id="adz" class="horizontal"></div><p>It works for any kind of variable, for example, used as a condition:</p>
<pre><code class="javascript">if(!empty(data)) 
{
	//data is not empty
}</code></pre>
<p>You could even pass the return value of another process, thanks (as ever!) to JavaScript&#8217;s ability to handle almost anything as an argument:</p>
<pre><code class="javascript">if(!empty(function()
{
	//do some process and return a value
}))
{
	//return value was non-empty
}</code></pre>
<p>I&#8217;ve been finding it particularly useful for validating function arguments, for example a simple shortcut function for getting element references:</p>
<pre><code class="javascript">function get(id)
{
	return document.getElementById(id);
}</code></pre>
<p>But what if the <code>id</code> parameter is empty, or <code>null</code>, or not there at all? We can check all those possibilities with a single statement, and then handle the situation accordingly:</p>
<pre><code class="javascript">function get(id)
{
	if(empty(id)) { return null; }
	return document.getElementById(id);
}</code></pre>
<p>And there you go &#8212; a neat, simple, and elegant method for validating any kind of variable.</p>
<p>See you soon for another Techy Treasure!</p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=137&amp;did=adz&amp;adtype=horizontal" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/10/16/techy-treasures-1/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Douglas Crockford on Web Standards and JavaScript</title>
		<link>http://www.sitepoint.com/blogs/2008/10/07/douglas-crockford-on-web-standards-and-javascript/</link>
		<comments>http://www.sitepoint.com/blogs/2008/10/07/douglas-crockford-on-web-standards-and-javascript/#comments</comments>
		<pubDate>Tue, 07 Oct 2008 06:27:33 +0000</pubDate>
		<dc:creator>Kevin Yank</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=3064</guid>
		<description><![CDATA[
I became a bit of a JavaScript fanboy while writing Simply JavaScript last year, so it was especially thrilling to get to sit down with Douglas Crockford—possibly the world’s biggest JavaScript fanboy—and geek out on our mutual love of JavaScript at Web Directions South 2008 a couple of weeks ago.
One of the most amazing things [...]]]></description>
			<content:encoded><![CDATA[<p><img src="http://i2.sitepoint.com/graphics/1679_feature.jpg" alt="Douglas Crockford at Web Directions South 2008" class="imgright" /></p>
<p><strong>I became a bit of a JavaScript fanboy while writing <a href="http://www.sitepoint.com/books/javascript1"><cite>Simply JavaScript</cite></a> last year, so it was especially thrilling to get to sit down with <a href="http://www.crockford.com/">Douglas Crockford</a>—possibly the world’s <em>biggest</em> JavaScript fanboy—and geek out on our mutual love of JavaScript at <a href="http://south08.webdirections.org/">Web Directions South 2008</a> a couple of weeks ago.</strong></p>
<p>One of the most amazing things about JavaScript is that such an elegant, subtly powerful, and forward-looking language could have been born of the fiercely competitive innovation of the so-called “browser wars” of the mid-nineties. Really, all Netscape needed to get ahead was a simple scripting language to run in its browser, but somehow what it ended up building was this amazingly capable little programming language. I asked Douglas Crockford how this happened:</p>
<blockquote><p>They were really lucky. Given the process that created the language, we should have gotten something much, much worse, because they didn’t do a careful design of requirements. They certainly didn’t give enough time for its design or its implementation. They took a prototype, which was intended just as a proof of concept, and that’s what they shipped. And it had all the problems that you would expect such an implementation to have. That’s what we had. And it was partly on the basis of that implementation that the language got the terrible reputation that it had. And a lot of those defects are still in the language.</p></blockquote>
<div id="adz" class="vertical"></div><p>In his talk at the conference, Crockford had outlined a number of fundamental security problems that he would like to see fixed as JavaScript moves forward. Problems aside, perhaps JavaScript’s greatest strength as a language is how accessible it is to beginners.</p>
<p>As JavaScript moves forward, I wondered, would we be able to preserve that low barrier to entry that makes JavaScript something you can pick up as your first language and feel confident after just a day or two?</p>
<blockquote><p>I think so, and I think we need to. I think we would be making a tragic mistake if we didn’t retain the language’s simplicity. Most of the modifications I would like to make in the language would be to make it even simpler. There’s some cruft on it, there are some attractive nuisances in it, which we don’t need, which people become dependant on. We’d be better off without that.</p>
<p>Unfortunately, the thing about the Web is, once something bad gets in it, it takes years to get it out. Ajax didn’t happen until 2005, but all of the technology that we needed to do Ajax was in place and in the field in 2000. Most of that five years was spent removing old browsers from the marketplace until there was enough of an audience on IE6 that Ajax became a viable application platform.</p></blockquote>
<p>The main set piece of Crockford’s talk was the story of how he became convinced that a second “browser war”—as scary a prospect as that might be—was exactly what would be needed to kick the evolution of JavaScript and the Web back on track.</p>
<p>Fundamentally, Crockford believes, web standards have failed in their attempt to lead innovation on the Web:</p>
<blockquote><p>For example, CSS2 was un-implementable, and eventually it had to be revised as CSS2.1, which was an attempt to cut CSS2 down to what people were actually able to figure out how to implement. That sequence was totally backwards—or it started backwards, but eventually they got it right. Let&#8217;s look at what can actually work and make a standard out of that, and then let everybody catch up with each other. I think that&#8217;s a proper role for standards.</p>
<p>What I see happening now with HTML5 is appalling. There is some stuff there that I really like: I really like that they figured out what the rules of HTML parsing are. Brilliant. That&#8217;s long overdue. And you can look at any individual feature that they&#8217;re doing and say, “Yeah, that makes sense.” But there’s just too much stuff, and there’s not a good set of tradeoffs, there’s not a complexity budget. It’s not motivated by real need, it’s more motivated by what’s shiny in front of a committee.</p>
<p>So, I would like to find a way to inject more discipline into the process, and I think one way to do it is to change it to an evaluation and description process, where we’ll observe what’s going on out in the wild, and document the best of it.</p></blockquote>
<p><a href="http://www.sitepoint.com/article/interview-doug-crockford/">Read my full interview with Douglas Crockford</a> at sitepoint.com.</p>
<p><em>Image credit: <a href="http://flickr.com/photos/webdirections/2902790539/" class="sublink">Web Directions</a></em></p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=136&amp;did=adz&amp;adtype=vertical" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/10/07/douglas-crockford-on-web-standards-and-javascript/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Pixel Fonts a Hot Button Topic at WDS08</title>
		<link>http://www.sitepoint.com/blogs/2008/10/03/pixel-fonts-a-hot-button-topic-at-wds08/</link>
		<comments>http://www.sitepoint.com/blogs/2008/10/03/pixel-fonts-a-hot-button-topic-at-wds08/#comments</comments>
		<pubDate>Thu, 02 Oct 2008 23:48:27 +0000</pubDate>
		<dc:creator>Kevin Yank</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=3054</guid>
		<description><![CDATA[In his talk on Elegant Web Typography at the Web Directions South 2008 conference last week in Sydney, Jeff Croft raised a few eyebrows when he mentioned that, for many of his projects, he has made the transition to specifying font sizes in pixels, rather than a relative unit of measurement like ems.
Traditionally, web designers [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://www.flickr.com/photos/jcroft/2886749135/"><img class="imgright" src="http://i2.sitepoint.com/graphics/1677_feature.jpg" alt="Derek Featherstone" /></a>In his talk on <a href="http://www.webdirections.org/resources/jeff-croft-elegant-web-typography/">Elegant Web Typography</a> at the <a href="http://south08.webdirections.org/">Web Directions South 2008</a> conference last week in Sydney, <a href="http://jeffcroft.com/">Jeff Croft</a> raised a few eyebrows when he mentioned that, for many of his projects, he has made the transition to specifying font sizes in pixels, rather than a <a href="http://reference.sitepoint.com/css/lengthunits">relative unit of measurement</a> like ems.</p>
<p>Traditionally, web designers have avoided specifying font sizes in pixels, because the text could not be resized by users who needed a larger font size to read it. Today, every major browser provides a Page Zoom feature that works even with pixel fonts, but one older browser version still in common use does not: Internet Explorer 6.</p>
<p>Pixel font sizes make it easier for the designer to match up the heights of lines of text with the other design elements on the page and achieve a uniform <a href="http://www.sitepoint.com/blogs/2007/04/30/typography-baseline-rhythm-deciphered/">“vertical rhythm”</a>. The same can be achieved with relative font sizes, but the math involved for the designer is considerably trickier.</p>
<p>Jeff argued that users who needed the ability to resize all text could simply upgrade to a current browser version, so for most projects pixel fonts were fair game. He admitted, however, that in projects where he had a little extra time, or where accessibility was a particular concern, he would still use relative font sizes for now.</p>
<div id="adz" class="vertical"></div><p>This approach to the issue didn’t sit well with a number of audience members at the conference.</p>
<p>I asked web accessibility expert <a href="http://boxofchocolates.ca/">Derek Featherstone</a> what he thought about the controversy in an <a href="http://www.sitepoint.com/article/interview-derek-featherstone/" id="interview">interview</a> the following day. Here’s what he had to say:</p>
<blockquote cite="#interview"><p>I’m still going to use relative units basically until IE6 disappears. And I don’t know when that will be. I know one of the metrics that I’ve used to gauge whether or not I’m going to support a particular browser is when Microsoft basically says they’re not going to support that browser anymore, or whatever piece of technology—whether it’s a browser, or operating system, or whatever it is. When they stop support for it, that’s when I feel much more comfortable eliminating my support for it as well.</p>
<p>[…] the assumption that Jeff makes is that somebody that will require the capability to resize text will choose a better tool, to me that’s still a bit of a jump. I would like to believe that, I really do. I think we have a long way to go, though, in terms of end-user education, because people don’t… there’s a lot of people that use computers, sadly, that … they don’t necessarily know that they can change browsers. They use what’s on their computer and that’s the end of the story.</p>
<p>Now, having said that, we’re in a position now where, I mean, I have three children; they know more about computers at age four, seven, and nine, than probably I did when I was nineteen, just because we didn’t use them when I was younger. So, times are definitely changing. We still have a group of people that did not grow up with computers, and they’re not necessarily as comfortable. Is that our problem? That’s a really good question, and I’m not sure.</p></blockquote>
<p>Hear or read the full interview on sitepoint.com:</p>
<p><a href="http://sitepointstatic.com/audio/2008-09-27_derekfeatherstone.mp3">Listen to the interview</a> (16&#8242;06, 11.1MB)<br />
<a href="http://www.sitepoint.com/article/interview-derek-featherstone/">Read the transcript</a></p>
<p><em>Image credit: <a href="http://www.flickr.com/photos/jcroft/2886749135/">Jeff Croft</a></em></p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=136&amp;did=adz&amp;adtype=vertical" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/10/03/pixel-fonts-a-hot-button-topic-at-wds08/feed/</wfw:commentRss>
<enclosure url="http://sitepointstatic.com/audio/2008-09-27_derekfeatherstone.mp3" length="11598527" type="audio/mpeg" />
		</item>
		<item>
		<title>Dmitry Baranovskiy Talks about Raphaël</title>
		<link>http://www.sitepoint.com/blogs/2008/10/01/dmitry-baranovskiy-talks-about-raphael/</link>
		<comments>http://www.sitepoint.com/blogs/2008/10/01/dmitry-baranovskiy-talks-about-raphael/#comments</comments>
		<pubDate>Wed, 01 Oct 2008 10:37:12 +0000</pubDate>
		<dc:creator>Andrew Tetlaw</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=3044</guid>
		<description><![CDATA[Dmitry Baranovskiy is the author of the amazing Raphaël JavaScript library. In this interview, he discusses with SitePoint's Andrew Tetlaw how the library came about, and to what degree we should ensure the accessibility of graphics on the Web.]]></description>
			<content:encoded><![CDATA[<p>
  <strong><a href="http://dmitry.baranovskiy.com/">Dmitry</a> is the author of the amazing <a href="http://raphaeljs.com/">Rapha&#235;l</a> JavaScript library, which I discussed back in <a href="http://www.sitepoint.com/newsletter/viewissue.php?id=3&amp;issue=205&amp;format=html">Tech Times #205</a>. At <a href="http://south08.webdirections.org/">Web Directions South</a>, I managed to catch <a href="http://south08.webdirections.org/?page_id=7#post-39">his presentation</a> and chat about how Rapha&#235;l came about. </strong>
</p>
<p>
  <strong>SitePoint: Right, I thought my first question should be: why did you write Rapha&#235;l? What inspired you to write it?</strong>
</p>
<p>
  I was doing a FedEx project. Internally at <a href="http://www.atlassian.com/">Atlassian</a>, we have FedEx Days when you are given the time to present a project you&#8217;ve been working on.
</p>
<p>
  <strong>SP: <em>FedEx Day&#8211;</em>did you say?</strong>
</p>
<div id="adz" class="vertical"></div><p>
  It&#8217;s called &quot;FedEx&quot; because you have to deliver something cool. You show it off at a small competition (it&#8217;s not about big prizes&#8211;it&#8217;s more for fun), and of course it should be related to the projects you work on. Because I&#8217;m a front end engineer and all the other guys are Java developers, I thought I&#8217;d focus on a front end project that will impress people. It&#8217;s hard to impress back end developers.
</p>
<p>
  So I thought I&#8217;d do something the programmers might not know anything about, and because I&#8217;ve had experience with SVG before, it made sense to work with SVG. But, as a front end developer, I&#8217;m concerned about creating something that only works in Firefox, so I wanted to create a bridge for VML on IE. My original project was to create a charting application, like a simple line chart. I quickly knocked it up in a day and a half from scratch, showed it, but it didn&#8217;t win anything. It didn&#8217;t impress people.
</p>
<p>
  <strong>SP: Not even a little bit?</strong>
</p>
<p>
  Oh, maybe a little bit, but not in general. So I left it for a while. Then we started our 20% projects (just like Google). I decided to pick up this project and extend it a little bit. I got rid of the charting part and turned it into a generic drawing library. Just a bridge between SVG and VML to enable me to do more cool stuff without worrying about browser compatibility.
</p>
<p>
  So at the next FedEx Day, I used this library to create a <a href="http://skitch.com/">Skitch</a>-like application. You could take a picture and add things like arrows and ellipses. It even saved the image, but obviously that&#8217;s not the hardest part.
</p>
<p>
  Then I started working more on this 20% project. To be honest, I spent more than one day a week: I worked with my laptop on the train &#8212; one hour to work and one hour back &#8212; two days a week in general, for about a month. Then I decided that it was good enough to release, because it&#8217;s better to do so before another developer releases the same thing. So, I released it in the middle of August.
</p>
<p>
  I was stunned by the feedback. I didn&#8217;t expect it, to be honest, because I wrote about it on my blog and I usually get about 20 hits per day; but after it was released and made it to the front page of <a href="http://delicious.com/">Delicious</a> and <a href="http://www.reddit.com/">Reddit</a>, I got about 8,000 hits per day. It chewed through my bandwidth and I had to create a new domain. It actually started costing me money!
</p>
<p><strong>SP: So do you actually use it in your job at Atlassian?</strong></p>
<p>Not yet, but we have plans to integrate it into products for charting and so on, but we haven&#8217;t found many use cases for it so far. I Personally think people are a bit afraid of the technology. But I hope it will find a place. It&#8217;s still quite raw. So it&#8217;s enough to show the concept, have fun, and do some stuff here and there. I&#8217;m always finding bugs (especially bugs for IE), so it&#8217;s not really, absolutely ready. Well, it&#8217;s only one month old.</p>
<p><strong>SP: Where would you like to see it used?</strong></p>
<p>Oh, well, everywhere. World domination is my goal! Of course the first thing people think of is charting, and that&#8217;s how I came to this idea, but what I was trying to show was that charting is just one obvious part. You could use it to add effects to a page, like the rotation of an image.</p>
<p>Say, if you&#8217;re on Flickr and you want to rotate an image by 90 degrees because you&#8217;ve shot the photo on the side. Currently, you press a button, it sends the request to the server, the server does the rotation, sends it back, and you see the rotated picture. Instead, you could use Ajax to just send the basic information: rotate 90% to the right, and on the client you&#8217;d have a smooth animation of rotating to the right. That would be a much more pleasant experience to the user for obvious reasons.</p>
<p>It&#8217;d be cool, and it&#8217;s really easy to implement using Raphaël. Without it, it&#8217;s a bit complicated to implement because you have to do a the IE version separately from the version for all other browsers. Actually that&#8217;s the whole reason why I built Raphaël &#8212; you do something in FireFox and in IE it just works. It&#8217;s not absolutely there yet, but it&#8217;s getting there.</p>
<p><strong>SP: When I was doing my demo I did notice one snag. In all the non-IE browsers you could do a path, then avoid specifing a fill color, and it would just draw the line. But in IE if you didn&#8217;t specify a fill color it would choose white, and it would start attempting to fill in the white.</strong></p>
<p>Yeah, I fixed it.</p>
<p><strong>SP: Oh really? Oh good, fantastic. Because I resorted to setting the fill opacity to 0.</strong></p>
<p>Yeah I noticed it when I looked at the code I thought &#8220;Oh, why did you use opacity for the fill?&#8221; So I started playing around and thought &#8220;Ah yeah, oh, ok.&#8221;</p>
<p><strong>SP: Hey thanks!</strong></p>
<p>Yeah, I often find bugs when I test in IE. SVG and VML are absolutely different languages. You can&#8217;t really replace one with the other. Sometimes it&#8217;s just impossible to do something in IE that&#8217;s easy to do in SVG. So I have to find a compromise solution. I can&#8217;t have an API for something you can&#8217;t do.</p>
<p>For example, in SVG you can rotate an object around a point, while in IE rotation is very wonky; you can&#8217;t specify the point. It rotates around some magical center and this center point is very randomly located in the center of&#8230; well I don&#8217;t know what it&#8217;s the center of. I found if you put the object inside a group it will be the center of the group, and it would do some juggling of the objects and they&#8217;d be jumping around the place. So I&#8217;ve succeeded in getting all the objects to rotate around their centers in all the implementations, but people ask me if they can specify the point of rotation. I say &#8220;Oh yeah, I wish.&#8221; So, not yet, but maybe later. I wish to do it, but it&#8217;s not that easy to do. In SVG it&#8217;s easy; it&#8217;s built in. But in VML it&#8217;s not.</p>
<p><strong>SP: I thought it was maybe a weakness but also a strength of Raphaël, that if you approach the task thinking about how you can doing it using the Raphaël API then you avoid those kinds of problems.</strong></p>
<p>Well maybe, sort of&#8230; Well for example I was trying to implement a blur effect and you can do it in Explorer, Firefox, and Opera, but Safari doesn&#8217;t support it, surprisingly. As soon as I discover I can&#8217;t do something across all browsers I don&#8217;t add it to the API. As soon as Safari supports it I&#8217;ll put it in. But for now there&#8217;s no point because the whole point of Raphaël is that you write it and it just works. Well, I hope it will. In version 1 it should be like that.</p>
<p>It could also help you to understand, you know, if you try to do something and you say &#8220;Could I do this cross-browser?&#8221; The answer may well be &#8220;No.&#8221; Of course, when I was creating Raphaël I was trying to cover as much functionality as possible, so if I removed something I removed it for reason. Maybe I&#8217;ll find a way to do it later, maybe there&#8217;s no way to do it in Internet Explorer.</p>
<p>Sometimes I do some extra calculations in SVG to emulate IE functionality. If I have a choice I&#8217;ll probably add the extra calculation into the SVG side because the JavaScript engines are faster in browsers other than IE. If you have to compromise and do a calculation in IE or do a calculation in Firefox, for example, it&#8217;s better to do the calculation in Firefox, it will be faster, and the user wont notice. If you do it in IE, it will be slower, and IE users will be upset.</p>
<p>
  <strong>SP: I was talking to some of the developers at SitePoint and a few of us agreed that, down the track, using SVG and VML driven by JavaScript could easily replace Flash.</strong>
</p>
<p>
  I wouldn&#8217;t say easily. There are some things that Flash is good at, like streaming video and animations. But if you look at, for example, the Google Analytics charts, then I can&#8217;t see any reason why it can&#8217;t be done with Rapha&#235;l.
</p>
<p>
  Yesterday morning I was trying to reproduce the Google charts functionality. I did it on the train; it&#8217;s really easy to do, and it works cross-browser straight away. Of course, to do this you need a JavaScript developer in your team who will use a program like Rapha&#235;l, or as I mentioned in my talk, <a href="http://excanvas.sourceforge.net/">excanvas</a>, or <a href="http://dojotoolkit.org/projects/dojox">dojox</a>. To be honest, I think that Rapha&#235;l has the more correct approach. It&#8217;s probably not as well-developed yet, but those other libraries don&#8217;t approach the usage correctly. They mix canvas, SVG, and VML together, and canvas is completely different. SVG and VML are ideologically the same. Well, to some extent, I guess.
</p>
<p>
  I don&#8217;t think it will replace Flash, but if in some task you could use SVG instead of Flash, I&#8217;d be happy to see that. Something native, something you can hack&#8211;the whole concept of the open web. SVG, and even VML, is more open than Flash. You can hack it up, you can view source, whatever. And, of course, Flash doesn&#8217;t work on iPhone. That&#8217;s another reason for doing this using native browser technologies. I&#8217;m not talking about Rapha&#235;l specifically; I think SVG is the way to go for a lot of things.
</p>
<p>
  <strong>SP: The issue of accessibility comes up a lot in regards to Rapha&#235;l, although when I look at your demos you tend to stick to the ideal of unobtrusive JavaScript anyway.</strong>
</p>
<p>
  When you talk about images and charts&#8211;and whatever SVG produces, it&#8217;s always an image, dynamic or not&#8211;it&#8217;s always an accessibility issue. At my talk, we spoke about how a screen reader should read SVG; how they should read circles, and ellipses, and combinations of them. Even if you had a good parser that could read the shapes you create on the page, you couldn&#8217;t tell what the shapes actually create: the final image. It&#8217;s really complicated and very difficult to explain if the user is blind. Like how would you explain the Web Directions logo to a blind user? I don&#8217;t think screen readers will ever be able to do this.
</p>
<p>
  So it&#8217;s all up to the developer to do it properly. For example, in the case of my charts, I have a table on the page. A screen reader can see that table, and if you have JavaScript turned off, you can see the table. You still have access to the data; it&#8217;s not as pretty, not as visually rich, but you can still read it and understand.
</p>
<p>
  I don&#8217;t think it&#8217;s a problem with SVG, or a problem with Rapha&#235;l; I think it&#8217;s a generic problem and there are already many articles and books about how to deal with it.
</p>
<p><strong>SP: Well thank you very much, really good to talk to you</strong></p>
<p>No worries.</p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=136&amp;did=adz&amp;adtype=vertical" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/10/01/dmitry-baranovskiy-talks-about-raphael/feed/</wfw:commentRss>
		</item>
		<item>
		<title>A Free JavaScript Speed Boost for Everyone!</title>
		<link>http://www.sitepoint.com/blogs/2008/09/16/a-free-javascript-speed-boost-for-everyone/</link>
		<comments>http://www.sitepoint.com/blogs/2008/09/16/a-free-javascript-speed-boost-for-everyone/#comments</comments>
		<pubDate>Tue, 16 Sep 2008 13:33:07 +0000</pubDate>
		<dc:creator>Andrew Tetlaw</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=2996</guid>
		<description><![CDATA[The new W3C Selector API provides a new—and fast—way to query an HTML page's DOM for specific elements. As Andrew explains, with support for the new API in versions of all major browsers, a speed boost is around the corner for web applications everywhere!]]></description>
			<content:encoded><![CDATA[<p><em>The following is republished from <a href="http://www.sitepoint.com/newsletter/viewissue.php?id=3&#038;issue=207&#038;format=html">The Tech Times #207</a>.</em></p>
<p><img src="http://sitepointstatic.com/images/blogs/race-car.jpg" alt="" class="imgright" />
<p>An exciting development in the world of DOM scripting is the <a href="http://www.w3.org/TR/selectors-api/">W3C Selector API</a>. Up until now, using the DOM Level 2 API, the only way to obtain references to HTML elements in the DOM was to use either <code>document.getElementById</code> or <code>document.getElementsByTagName</code> and filter the results manually. With the rise of CSS, JavaScript programmers asked the obvious question, &#8220;If the browser has a really fast way of selecting HTML elements that match CSS selectors why can&#8217;t we?&#8221;.</p>
<p>The Selector API defines the <code>querySelector</code>, and <code>querySelectorAll</code> methods that take a CSS selector string and return the first matching element or a <code>StaticNodeList</code> of matching elements, respectively. The methods can be called from the <code>document</code> object in order to select elements from the whole document or a specific HTML element to select only from descendants of that element.</p>
<p>To illustrate how much easier your life will be using the Selector API, have a look at this example HTML:</p>
<pre><code>&lt;ul id="menu"&gt;
  &lt;li&gt;
    &lt;input type="checkbox" name="item1_done" id="item1_done"&gt; 
    &lt;label for="item1_done"&gt;bread&lt;/label&gt;
  &lt;/li&gt;
  &lt;li class="important"&gt;
    &lt;input type="checkbox" name="item2_done" id="item2_done"&gt; 
    &lt;label for="item2_done"&gt;milk&lt;/label&gt;
  &lt;/li&gt;
  &lt;!-- imagine more items --&gt;
&lt;/ul&gt;</code></pre>
<p>Our task is to check all the checkboxes for the list items that have the class &#8220;<code>important</code>&#8221;. Using only DOM Level 2 methods we could do it this way:</p>
<pre><code>var items = document.getElementById('menu').getElementsByTagName('li');
for(var i=0; i &lt; items.length; i++) {
  if(items[i].className.match(/important/)) {
    if(items[i].firstChild.type == "checkbox") {
      items[i].firstChild.checked = true;
    }
  }
}</code></pre>
<p>Using the new selector API we can simplify it to this:</p>
<pre><code>var items = document.querySelectorAll('#menu li.important input[type="checkbox"]');
for(var i=0; i &lt; items.length; i++) {
  items[i].checked = true;
}</code></pre>
<p>That&#8217;s much nicer! The methods also support selector grouping &#8212; multiple selectors separated by commas. The Selector API is working right now in Safari 3.1, the Internet Explorer 8 beta, and Firefox 3.1 alpha1. Opera is also working on adding support for the API.</p>
<div id="adz" class="vertical"></div><p>If you&#8217;re a fan of one of the many JavaScript libraries available you&#8217;re probably thinking &#8220;But, I can already do that.&#8221; One of the great examples of the benefits of using JavaScript libraries are the implementations of CSS selectors found in nearly all of them. Recently we&#8217;ve seen huge speed improvements in the CSS selector implementations because library authors have been sharing their techniques. So what&#8217;s the benefit of using the Selector API? In a word: speed &#8212; native implementations are fast! And better yet all of the javascript libraries are poised to benefit. <a href="http://jquery.com/">jQuery</a> and <a href="http://www.prototypejs.org/">Prototype</a> are already developing implementations that make use of the Selector API, while <a href="http://dojotoolkit.org/">The Dojo Toolkit</a>, <a href="http://www.domassistant.com/">DOMAssistant</a> and <a href="http://code.google.com/p/base2/">base2</a> have already made use of it.</p>
<p>There&#8217;s a reason why those 3 libraries were the first ones to benefit. Kevin talked about the potential problem back in <a href="http://www.sitepoint.com/newsletter/viewissue.php?id=3&amp;issue=190&amp;format=html">Tech Times #190</a> in the article titled &#8220;Is Your JavaScript Library Standards Compliant?&#8221; The Selector API makes use of standard CSS selectors so if the browser doesn&#8217;t support a certain selector then you won&#8217;t be able to use it. The libraries that have already taken advantage of the Selector API are those that only supported standard CSS selectors. For those libraries, supporting the API was (almost) as easy as doing this:</p>
<pre><code>if(document.querySelector) {
  return document.querySelector(selector);
} else {
  return oldSelectorFunction(selector);
}</code></pre>
<p>Libraries that support custom selectors will have more work to do. The risk is that if you have used custom CSS selectors extensively in your project, it may be difficult for your chosen library to pass on the speed benefit to you because the library will have to use its default selector instead of the Selector API. If the library somehow rewires its custom selectors so that they can utilize the Selector API, the secondary risk is increased code bloat.</p>
<p>Hopefully the Selector API will encourage the use of standard CSS selectors over custom ones. In fact if uptake of the new browser versions is good and the performance benefits of the new Selector API are compelling enough we could see custom selector functionality moved to supplementary libraries you only need to use in case of legacy compatibility requirements.</p>
<p>Dean Edwards&#8217; <a href="http://code.google.com/p/base2/">base2</a> Library has the nicest implementation in my opinion. Base2 implements the API exactly, which means you can write your JavaScript using standard the standard API methods &#8212; Base2 only creates custom querySelector and querySelectorAll methods if the browser doesn&#8217;t support them. You can&#8217;t get any cleaner than that. Base2 does, however, implement the non-standard &#8220;<code>!=</code>&#8221; attribute selector in it&#8217;s custom selector function, apparently because of peer pressure, so it&#8217;ll have to have points deducted for that.</p>
<p>Regardless of whether you use a JavaScript library or roll your own, the new browser implementations of the Selector API give everyone an instant speed boost. We all win, hooray!</p>
<p><em>Image credit: <a href="http://www.flickr.com/photos/yogi/320315208/">Yogi</a></em></p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=136&amp;did=adz&amp;adtype=vertical" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/09/16/a-free-javascript-speed-boost-for-everyone/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Rowspans &#038; Colspans in CSS Tables</title>
		<link>http://www.sitepoint.com/blogs/2008/09/09/rowspans-colspans-in-css-tables/</link>
		<comments>http://www.sitepoint.com/blogs/2008/09/09/rowspans-colspans-in-css-tables/#comments</comments>
		<pubDate>Tue, 09 Sep 2008 06:07:31 +0000</pubDate>
		<dc:creator>Kevin Yank</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=2964</guid>
		<description><![CDATA[If you’ve had experience building layouts using HTML tables, you’ll be familiar with the use of the colspan and rowspan attributes of the td element. In this demo, Kevin shows how these attributes can be mimicked using CSS3 tables, whilst keeping your markup relatively pure.]]></description>
			<content:encoded><![CDATA[<p><strong>&#8220;&#8230;we&#8217;ve implemented every property in CSS 2.1 and are closing in on our goal of complete support for the CSS 2.1 specification by the time we release.&#8221;</strong></p>
<p>If you were to guess who recently made that statement you&#8217;d be forgiven for thinking it came from the Opera, Safari, or Firefox team; they have always seemed to be the most standards-conscious browser vendors. In fact, this quote comes from Doug Stamper of Microsoft, <a href="http://blogs.msdn.com/ie/archive/2008/09/08/internet-explorer-8-beta-2-platform-improvements.aspx">regarding Internet Explorer 8</a>.</p>
<p>It seems the very thing web designers have been asking for—mature support for CSS2.1 across all major browsers—is actually about to happen. Back in <a href="http://www.sitepoint.com/newsletter/viewissue.php?id=3&#038;issue=185">Tech Times #185</a>, I wrote about what this would mean to web designers in <a href="http://www.sitepoint.com/blogs/2008/02/28/table-based-layout-is-the-next-big-thing/"><cite>Table-Based Layout Is The Next Big Thing</cite></a>. In short, I said that CSS tables would become the best tool for CSS page layout.</p>
<p>There were <a href="http://www.sitepoint.com/blogs/2008/02/28/table-based-layout-is-the-next-big-thing/#comments">mixed reactions</a> to that article, particularly on the point of row and column spans. HTML tables let you create cells that span multiple rows or columns, but CSS tables don&#8217;t provide that same freedom.</p>
<div id="adz" class="vertical"></div><p>Well, in my research for an as yet <strong>unannounced, potentially controversial book on CSS</strong>, I’ve figured out how to simulate row and column spans in CSS tables. Rather than make you wait for the book, I thought I’d show you this useful technique right away!</p>
<h2>Nothing Up My Sleeve…</h2>
<p>If you’ve had experience building layouts using HTML tables, you’ll be familiar with the use of the <code>colspan</code> and <code>rowspan</code> attributes of the <code>td</code> element. These attributes offer complex possibilities to a simple table, enabling cells to span columns and rows.</p>
<p>CSS tables lack any concept of row or column spanning, making it trickier to use one single layout structure than what might have been possible when using tables. However, similar layouts can be achieved by using nested CSS tables.</p>
<p>Of course, nested tables are not a perfect solution. When you want to match the dimensions of cells across nested tables, for example, things can get messy in a hurry, and the extra <code>&lt;div&gt;</code> tags really start to add up.</p>
<p>As it turns out, it’s also possible to simulate row and column spanning using absolute positioning of table cells, in many cases. In this example, we’ll make the second cell of the first row of a table span both rows of the table (as if it had a <code>rowspan</code> of <code>2</code>). First, let’s take a look at the HTML code:</p>
<pre><code class="html">&lt;div class="tablewrapper"&gt;
  &lt;div class="table"&gt;
    &lt;div class="row"&gt;
      &lt;div class="cell"&gt;
        Top left
      &lt;/div&gt;
      &lt;div class="rowspanned cell"&gt;
        Center
      &lt;/div&gt;
      &lt;div class="cell"&gt;
        Top right
      &lt;/div&gt;
    &lt;/div&gt;
    &lt;div class="row"&gt;
      &lt;div class="cell"&gt;
        Bottom left
      &lt;/div&gt;
      &lt;div class="empty cell"&gt;&lt;/div&gt;
      &lt;div class="cell"&gt;
        Bottom right
      &lt;/div&gt;
    &lt;/div&gt;
  &lt;/div&gt;
&lt;/div&gt;</code></pre>
<p>You’ll notice that we’ve wrapped our table <code>div</code> in an extra <code>div</code> with a <code>class</code> of <code>"tablewrapper"</code>. This extra <code>div</code> is needed to provide a CSS positioning context—which we create by giving it relative positioning:</p>
<pre><code class="css">.tablewrapper {
  position: relative;
}</code></pre>
<p>According to the CSS spec, we should be able to simply apply relative positioning to the table <code>div</code>, but current browsers don’t seem to support this.</p>
<h2>Sleight of Hand and Absolute Positioning</h2>
<p>Now, we can use absolute positioning to control the size and position of the <code>div</code> with <code>class</code> <code>"rowspanned cell"</code>:</p>
<pre><code class="css">.cell.rowspanned {
  position: absolute;
  top: 0;
  bottom: 0;
  width: 100px;
}</code></pre>
<p>With the <code>top</code> and <code>bottom</code> properties both set to zero, the cell will stretch to fill the full height of the table, simulating a row span. Depending on the needs of your layout, you could use different values for <code>top</code> and <code>bottom</code>, or even set the cell’s <code>height</code> directly to achieve other row-spanning layouts.</p>
<p>You also need to specify the width of the cell. Usually, the easiest way to do this is just to set its <code>width</code> property, but depending what you know of the dimensions of surrounding table cells, you could also do this by setting <code>left</code> and <code>right</code>.</p>
<p>Since the positioned cell doesn’t <em>actually</em> span multiple rows of the table, the table must still contain a corresponding cell in each of the other rows. These cells are simply empty placeholders, though; note the <code>div</code> with <code>class</code> <code>"empty cell"</code> in the HTML code above. The function of this cell is to hold open the space that will be occupied by the “spanned” cell, so we must ensure its width matches the width we specified for the <code>"rowspanned cell"</code>:</p>
<pre><code class="css">.cell.empty {
  width: 100px;
}</code></pre>
<p>And that’s all there is to it! To complete the style sheet for this example, we need only set the appropriate <code>display</code> property values, and add some borders so we can see what’s going on:</p>
<pre><code class="css">.tablewrapper {
  position: relative;
}
.table {
  display: table;
}
.row {
  display: table-row;
}
.cell {
  border: 1px solid red;
  display: table-cell;
}
.cell.empty
{
  border: none;
  width: 100px;
}
.cell.rowspanned {
  position: absolute;
  top: 0;
  bottom: 0;
  width: 100px;
}</code></pre>
<p>In essence, by using absolute positioning we are telling the browser, “Let me handle the layout of this table cell—you take care of the rest.” Here&#8217;s what the results look like:</p>
<p><img src="http://i2.sitepoint.com/g/nl/tt/csstables-rowspan.jpg" alt="" align="bottom" border="0" height="219" width="350"/></p>
<p><a href="http://www.sitepoint.com/blogs/wp-content/uploads/2008/09/csstable-rowspan.html">Try it for yourself.</a> This example works in all major browsers except for Internet Explorer 7, and also works in the current IE8 Beta 2 release.</p>
<p>What do you think? Can you see yourself switching to CSS tables for layout as your Internet Explorer users make the move to IE8?</p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=136&amp;did=adz&amp;adtype=vertical" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/09/09/rowspans-colspans-in-css-tables/feed/</wfw:commentRss>
		</item>
		<item>
		<title>Easy Vector Graphics with the Raphaël JavaScript Library</title>
		<link>http://www.sitepoint.com/blogs/2008/09/03/easy-vector-graphics-with-the-raphael-javascript-library/</link>
		<comments>http://www.sitepoint.com/blogs/2008/09/03/easy-vector-graphics-with-the-raphael-javascript-library/#comments</comments>
		<pubDate>Wed, 03 Sep 2008 06:17:48 +0000</pubDate>
		<dc:creator>Andrew Tetlaw</dc:creator>
		
		<category><![CDATA[JavaScript &amp; CSS]]></category>

		<guid isPermaLink="false">http://www.sitepoint.com/blogs/?p=2926</guid>
		<description><![CDATA[Raphaël is a small JavaScript library that allows you to create and manipulate vector graphics in your web pages. It's amazingly simple to use and is cross-browser compatible, as Andrew demonstrates in this short demo.]]></description>
			<content:encoded><![CDATA[<p><a href="http://raphaeljs.com/">Raphaël</a> is a small JavaScript library written by Dmitry Baranovskiy of <a href="http://www.atlassian.com/?s_kwcid=atlassianawsearch">Atlassian</a>, that allows you to create and manipulate vector graphics in your web pages. It&#8217;s amazingly simple to use and is cross-browser compatible; supporting Internet Explorer 6.0+, Safari 3.0+, Firefox 3.0+, and Opera 9.5+. Internally Raphaël uses VML in IE and SVG in the other browsers.</p>
<p>Now, demos involving circles and squares are fine, but I wanted to create an example that demonstrated a legitimate, practical use of vector graphics. So how about <a href="http://www.sitepoint.com/blogs/wp-content/uploads/2008/09/raphael-graph-demo/" title="Jump straight to the demo">real-time statistics measurement</a>? Here&#8217;s a screenshot of my Current Sprocket Usage line graph that plots real-time &#8220;sprocket&#8221; usage levels. Best of all, it was a snap to make.</p>
<p><img src="http://www.sitepoint.com/blogs/wp-content/uploads/2008/09/raphael-sprocket-graph1.gif" width="400" height="145" /></p>
<p>The HTML is simple;  we just need a heading and container to hold our canvas &#8212; a <code>div</code> element:</p>
<div id="adz" class="horizontal"></div><pre><code>&lt;h1&gt;Current Sprocket Usage: &lt;span id="readout"&gt;&lt;/span&gt;&lt;/h1&gt;
&lt;div id="graph"&gt;&lt;/div&gt;</code></pre>
<p>To start we have to generate a new graphics canvas. I always like to place all my code within an object definition in order to create a separate namespace, so we&#8217;ll start with the following code:</p>
<pre><code>var SpGraph = {
  init : function(){
    SpGraph.graph = Raphael("graph", 400, 200);
    SpGraph.graph.rect(0, 0, 390, 110, 10).attr("fill", "#000");
  }
}

window.onload = function () {
  SpGraph.init();
};</code></pre>
<p>Using the window.onload event we call our <code>SpGraph.init</code> method. Within this method we create our canvas using <code>Raphael("graph", 400, 200)</code>. The first argument is the ID of our container element, the other two represent width and height. We store the returned canvas object in our <code>SpGraph.graph</code> property.  With the next line we create a rectangle and set some attributes:</p>
<pre><code>SpGraph.graph.rect(0, 0, 390, 110, 10).attr("fill", "#000");</code></pre>
<p>The <code>rect</code> method allows us to draw a rectangle specifying the x coordinate, y coordinate, width, height, and optionally a corner radius. Notice that we&#8217;ve also chained a call to the <code>attr</code> method to set the fill color. All Raphaël graphic objects support the <code>attr</code> method and there&#8217;s a range of attributes you can set. Raphaël supports chaining all its methods, which we will take advantage of soon. Our effort so far has resulted in this lovely black rectangle with rounded corners.</p>
<p><img src="http://www.sitepoint.com/blogs/wp-content/uploads/2008/09/raphael-sprocket-graph2.gif" width="400" height="145" /></p>
<p>Now lets add stripes! To do this we add the following loop to the <code>SpGraph.init</code> method:</p>
<pre><code>for(var x = 10; x &lt; 110; x += 10) {
  var c = (x > 10) ? "#333" : "#f00";
  SpGraph.graph.path({stroke: c}).moveTo(0, x).lineTo(390,x);
}</code></pre>
<p>The loop executes 10 times drawing a line each time; a red line for the first one and a gray line for the others. The Raphaël <code>path</code> method initializes the path mode of drawing, returning a <code>path</code> object. It doesn&#8217;t actually draw anything itself; you have to use the <code>path</code> object methods, which are chainable. The <code>moveTo</code> method moves the drawing cursor to the specified x and y coordinates and the <code>lineTo</code> method draws a line from the cursor point to the point specified. The result is the stripey background below:</p>
<p><img src="http://www.sitepoint.com/blogs/wp-content/uploads/2008/09/raphael-sprocket-graph3.gif" width="400" height="145" /></p>
<p>So now we have to draw the actual graph line. The vertical axis (represented by the stripes) is the percentage usage level. The horizontal axis will represent time in 10 pixel increments. In the real world each update of the graph would be obtained via an Ajax call, say every 5 seconds, but here I just create random values and update the graph every second. Once again, we use the path method to draw a 5 pixel wide line.</p>
<p>We initialise the path and store the reference to it in the <code>SpGraph.path</code> property like so:</p>
<pre><code>SpGraph.path = SpGraph.graph.path({
    stroke: "#0f0",
    "stroke-width": 5, 
    "fill-opacity": 0
}).moveTo(20, 110);</code></pre>
<p>Every update, we extend the line using the <code>lineTo</code> method like so:</p>
<pre><code>SpGraph.path.lineTo(20+SpGraph.updates*10, 110-perf);</code></pre>
<p><code>perf</code> is a random value between 0 and 100. The <code>SpGraph.updates</code> property is a simple counter that allows us to control how many updates before the line is reset. The counter value is also used to plot the location of the line on the horizontal axis. After 35 updates the line is reset by removing it, using the <code>SpGraph.path.remove</code> method, and starting a new one.</p>
<p>So the whole script looks like this:</p>
<pre><code>var SpGraph = {
  init : function(){
    SpGraph.graph = Raphael("graph", 400, 200);
    SpGraph.graph.rect(0, 0, 390, 110, 10).attr("fill", "#000");

    for(var x = 10; x &lt; 110; x += 10) {
      var c = (x > 10) ? "#333" : "#f00";
      SpGraph.graph.path({stroke: c}).moveTo(0, x).lineTo(390,x);
    }
    SpGraph.startPath();
    SpGraph.updateGraph();
  },
  startPath : function() {
    if(SpGraph.path) {
      SpGraph.path.remove();
    }
    SpGraph.path = SpGraph.graph.path({
        stroke: "#0f0",
        "stroke-width": 5, 
        "fill-opacity": 0
    }).moveTo(20, 110);
  },
  updateGraph : function() {
    if(SpGraph.updates++ &lt; 36) {
      // imagine this value comes from an ajax request
      var perf = Math.floor(Math.random() * 100);
      SpGraph.path.lineTo(20+SpGraph.updates*10, 110-perf);
      document.getElementById('readout').innerHTML = perf+'%';
    } else {
      SpGraph.updates = 0;
      SpGraph.startPath();
    }
    SpGraph.timer = setTimeout("SpGraph.updateGraph();",1000);
  },
  updates : 0
}
window.onload = function () {
  SpGraph.init();
};</code></pre>
<p>Don&#8217;t forget to see it working in <a href="http://www.sitepoint.com/blogs/wp-content/uploads/2008/09/raphael-graph-demo/" title="Jump straight to the demo">the demo</a>. OK, so maybe a sprocket usage graph isn&#8217;t exactly the legitimate, practical example I promised, but at least you got a look at what you can achieve with Raphaël with only a little effort. The documentation on the site isn&#8217;t complete, but it&#8217;s not too difficult to work out anyway. Why don&#8217;t you have a go yourself? Quick, Simple, cross-browser compatible, vector graphics on the web has never been easier.</p>
<script src="http://ads.aws.sitepoint.com/adjs.php?region=137&amp;did=adz&amp;adtype=horizontal" type="text/javascript"></script>]]></content:encoded>
			<wfw:commentRss>http://www.sitepoint.com/blogs/2008/09/03/easy-vector-graphics-with-the-raphael-javascript-library/feed/</wfw:commentRss>
		</item>
	</channel>
</rss>

<!-- Dynamic Page Served (once) in 0.620 seconds -->
<!-- Cached page served by WP-Cache -->
