<?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>A Plus Design</title>
	<atom:link href="http://www.aplusdesign.com.au/blog/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.aplusdesign.com.au/blog</link>
	<description>Just another WordPress weblog</description>
	<lastBuildDate>Fri, 11 May 2012 10:31:17 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0</generator>
		<item>
		<title>jQuery Ajax Loader &amp; Spinner</title>
		<link>http://www.aplusdesign.com.au/blog/jquery-ajax-loader-spinner/</link>
		<comments>http://www.aplusdesign.com.au/blog/jquery-ajax-loader-spinner/#comments</comments>
		<pubDate>Wed, 03 Aug 2011 07:02:12 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[Ajax]]></category>
		<category><![CDATA[jQuery]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=276</guid>
		<description><![CDATA[The title is fairly generic, so if you have found this, congratulations, your life is about to become far simpler. When working on or with ajax enabled web sites we usually run into the issue of request times, users need to be shown that something is happening in the background and visually we accomplish this [...]]]></description>
			<content:encoded><![CDATA[<p>The title is fairly generic, so if you have found this, congratulations, your life is about to become far simpler. When working on or with ajax enabled web sites we usually run into the issue of request times, users need to be shown that something is happening in the background and visually we accomplish this with an Ajax Loader. You would have seen plenty of these by now, little animated gifs that give you a sense the web-page is loading something.</p>
<p>Now the drama here is they are a PITA to create all the time on the fly while your writing those fancy ajax queries, some of the framework simplify the task by letting you specify a loading attribute, but the behaviour isn&#8217;t standard and I find the implementation is lacking because it is usually an after thought of the original Ajax request in the framework. Also you don&#8217;t want to create useless mark-up in you page by having a permanent but hidden until needed ajax overlay like I see a lot of sites doing. Less code = better at everything, remember that.</p>
<p>So here is the solution, create on the fly ajax loaders when and where-ever you may need them!</p>
<h4>Demo</h4>
<p><a class="demo" href="http://www.aplusdesign.com.au/demos/ajax-loader/index.html" target="_blank">View Demo :: jQuery</a></p>
<p><span id="more-276"></span></p>
<h4>The HTML</h4>
<pre class="brush: plain;">
 See example page
</pre>
<p><strong>Note:</strong> Elements you intend to insert the ajax loader into must be &#8220;position:relative;&#8221;</p>
<h4>The CSS</h4>
<pre class="brush: css;">
 .ajax_overlay {}
 .ajax_loader {background: url("spinner_squares_circle.gif") no-repeat center center transparent;width:100%;height:100%;}
</pre>
<p><strong>Note:</strong> &#8216;.ajax_overlay &#8216; styles are mostly done by the script so you can dynamically change and control them</p>
<h4>The jQuery</h4>
<pre class="brush: javascript;">
function ajaxLoader (el, options) {
	// Becomes this.options
	var defaults = {
		bgColor 		: '#fff',
		duration		: 800,
		opacity			: 0.7,
		classOveride 	: false
	}
	this.options 	= jQuery.extend(defaults, options);
	this.container 	= $(el);
	this.init = function() {
		var container = this.container;
		// Delete any other loaders
		this.remove();
		// Create the overlay
		var overlay = $('
<div></div>
').css({
				'background-color': this.options.bgColor,
				'opacity':this.options.opacity,
				'width':container.width(),
				'height':container.height(),
				'position':'absolute',
				'top':'0px',
				'left':'0px',
				'z-index':99999
		}).addClass('ajax_overlay');
		// add an overiding class name to set new loader style
		if (this.options.classOveride) {
			overlay.addClass(this.options.classOveride);
		}
		// insert overlay and loader into DOM
		container.append(
			overlay.append(
				$('
<div></div>
').addClass('ajax_loader')
			).fadeIn(this.options.duration)
		);
    };
	this.remove = function(){
		var overlay = this.container.children(".ajax_overlay");
		if (overlay.length) {
			overlay.fadeOut(this.options.classOveride, function() {
				overlay.remove();
			});
		}
	}
    this.init();
}
</pre>
<p><strong>Note:</strong> paste this code into your scripts file. </p>
<h4>Usage examples</h4>
<pre class="brush: javascript;">
$(document).ready(function() {
	$(".box-1").live('click', function(){
		new ajaxLoader(this, options);
	});
});
</pre>
<p><strong>Note:</strong> For more detailed examples, please see the <a href="http://www.aplusdesign.com.au/demos/ajax-loader/index.html" target="_blank">Ajax Loader demo page</a></p>
<h4>Default options</h4>
<pre class="brush: javascript;">
var options = {
	bgColor 		: '#fff',
	duration		: 800,
	opacity		: 0.7,
	classOveride 	: false
}
</pre>
<p><strong>Set up options, explained below</strong></p>
<ul>
<li><strong>bgColor:</strong> string &#8211; colour of the background overlay</li>
<li><strong>duration:</strong> number &#8211; length of fadeIn and fadeOut effects</li>
<li><strong>opacity:</strong> number  &#8211; opacity of the background overlay</li>
<li><strong>classOveride:</strong> string &#8211; a class name to over-ride your default loader style </li>
</ul>
<h4>Download</h4>
<p>Contains &#8216;Ajax Loader &amp; Spinner&#8217; example and code</p>
<p><a class="download" href="http://www.aplusdesign.com.au/demos/ajax-loader/ajax-loader.zip" target="_blank">jQuery Ajax Loader &amp; Spinner</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/jquery-ajax-loader-spinner/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>MooTools Nested Sortable List</title>
		<link>http://www.aplusdesign.com.au/blog/mootools-nested-sortable-list/</link>
		<comments>http://www.aplusdesign.com.au/blog/mootools-nested-sortable-list/#comments</comments>
		<pubDate>Mon, 01 Aug 2011 23:15:05 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[MooTools]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=265</guid>
		<description><![CDATA[Ok guys and girls, I won&#8217;t write too much on this topic, except to say that over the years I have seen literally hundreds of forum threads about nested sortable lists in MooTools, many of these threads end with horrible patchwork solutions cobbling together 10 random unsupported plugins to get an outcome that works (miserably)&#8230; [...]]]></description>
			<content:encoded><![CDATA[<p>Ok guys and girls, I won&#8217;t write too much on this topic, except to say that over the years I have seen literally hundreds of forum threads about nested sortable lists in MooTools, many of these threads end with horrible patchwork solutions cobbling together 10 random unsupported plugins to get an outcome that works (miserably)&#8230;</p>
<p>This solution came about while working for a really cool start-up venture, they are not around any more so the code is going public with the intention that others may benefit from the work, enjoy <img src='http://www.aplusdesign.com.au/blog/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<h4>Demo</h4>
<p><a class="demo" href="http://www.aplusdesign.com.au/demos/nested-sortable/index.html" target="_blank">View Demo :: MooTools</a><br />
<span id="more-265"></span></p>
<h4>The HTML</h4>
<pre class="brush: plain;">
 Grab it from the 'example page' or the 'zip file' at the bottom of this post
</pre>
<h4>Usage</h4>
<pre class="brush: javascript;">
new Nested('ID-of-your-list', {
	onStart: function(el) {
		this.onStyle(el);
	},
	onComplete: function(el) {
		this.offStyle(el);
	}
});
</pre>
<h4>Options (example)</h4>
<pre class="brush: javascript;">
var options = {
	childTag: 'LI',
	lockClass: 'locked',
	ghost: true,
	collapse: true,
	childStep: 40,
	closedSpace: 3,
	onStart: function(el) {
		this.onStyle(el);
	},
	onComplete: function(el) {
		this.offStyle(el);
	}
}
</pre>
<p><strong>Set up options, explained below</strong></p>
<ul>
<li><strong>childTag:</strong> string &#8211; the child nodeType, you shouldn&#8217;t need to change this</li>
<li><strong>lockClass:</strong> string &#8211; class for locked nodes</li>
<li><strong>ghost:</strong> boolean &#8211; create visual ghosting node</li>
<li><strong>collapse:</strong> boolean &#8211; are options collapsible </li>
<li><strong>childStep:</strong> number &#8211; attempts to become a child of the previous Item if the mouse is moved this number of pixels right</li>
<li><strong>closedSpace:</strong> number &#8211; a space for top and bottom insert detection when near closed nodes</li>
<li><strong>onStart:</strong> function &#8211; things to do to an element when it STARTS dragging</li>
<li><strong>onComplete:</strong> function &#8211; things to do to an element when it STOPS dragging</li>
</ul>
<p>Ok the only options there that need some further explaining are probably, &#8216;childStep&#8217; and &#8216;closedSpace&#8217;.</p>
<p><strong>childStep:</strong> we need a value that behaves like a border, meaning as you would manually drag a node to the right to nest it, this value determines how far you need to drag it before accepting you want to nest it.</p>
<p><strong>closedSpace:</strong> when nearing a closed node it is nice to have the styles for this event to appear before hovering directly over the node that is closed. It provides your users with more of an idea about what can and can&#8217;t be done before they try to do it.</p>
<h4>Download</h4>
<p>Contains &#8216;MooTools Nested Sortable List&#8217; example and code</p>
<p><a href="http://www.aplusdesign.com.au/demos/nested-sortable/nested-sortable.zip" target="_blank">MooTools Nested Sortable Lists</a></p>
<h4>jQuery</h4>
<p>Sorry guys, no jQuery version yet, have not had the time to convert it.</p>
<h4>Disclaimer</h4>
<p>I do not intend to support this script with feature requests or bug fixes, I&#8217;m posting the last stable copy I have in my possession to help prevent other developers from going around in circles and provide a starting point for your own Nested Sortables implementations <img src='http://www.aplusdesign.com.au/blog/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/mootools-nested-sortable-list/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Mootools Mega Drop Down Menu</title>
		<link>http://www.aplusdesign.com.au/blog/mootools-mega-menu-drop-down/</link>
		<comments>http://www.aplusdesign.com.au/blog/mootools-mega-menu-drop-down/#comments</comments>
		<pubDate>Wed, 29 Sep 2010 12:12:15 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[MooTools]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=243</guid>
		<description><![CDATA[Anyone else noticing a trend in web browsing these days? Well I certainly have and so have the good people over at SitePoint.com. Mega Menu&#8217;s are similar to your standard navigation bars, but tend to have some javascript to help you navigate down the many levels you might find within one, but they are rife [...]]]></description>
			<content:encoded><![CDATA[<p>Anyone else noticing a trend in web browsing these days? Well I certainly have and so have the good people over at SitePoint.com. Mega Menu&#8217;s are similar to your standard navigation bars, but tend to have some javascript to help you navigate down the many levels you might find within one, but they are rife with issues, such as complexity, hidden content and use-ability concerns. So what is the solution when you have a lot of content or products that you wish to show in your nav without angering or frustrating your users, easy, enter the Mega Drop Down Menu. They have the extra cool and unique  advantage of having larger area&#8217;s for sub-links or inner pages, sometimes even including images, descriptions and popular items in that category within the newly shown element. </p>
<p><a href="http://www.actionenvelope.com/" target="blank">Here is a decent example</a> of a <strong>Mega Drop Down Menu</strong> to illustrate what I&#8217;m talking about. But it certainly takes way too long to load, and uses images for the drop down box, which I personally don&#8217;t like because you have to wait for it to load on a slow connection, such as this wireless laptop I&#8217;m on.</p>
<p>So I was looking around for a better implementation of a mega drop down menu and noticed that a couple I found were using jQuery wizardry to effectively prevent instant hover effects, because you don&#8217;t want the mega drop down from appearing every time a user rolls over your top level navigation items, and a few were using neat CSS3 effects instead of images. </p>
<p>Then I thought it would be nice to have all the positives in one Mega Drop Down combined together and since there were already a few jQuery implementations doing one or the other, I figured I&#8217;d do it in MooTools, since I still have a penchant for that framework, so I&#8217;ve converted one of the jQuery plugins to MooTools for you all, added some other nifty features and given you some basic css to play with. So without further ad-due, here is the code for a MooTools &#8211; Mega Drop Down Menu .</p>
<h4>Demo</h4>
<p><a class="demo" href="http://www.aplusdesign.com.au/demos/megamenu/index.html" target="_blank">View Demo :: MooTools</a><br />
<span id="more-243"></span></p>
<h4>The HTML</h4>
<pre class="brush: plain;">
 Grab it from the example page, as there is quite a bit of markup for the mega drops
</pre>
<h4>The MooTools Javascript</h4>
<pre class="brush: javascript;">
Element.implement({
	megaMenu: function(f,g){
		var cfg = {
			sensitivity: 7,
			interval: 100,
			timeout: 0
		};
		cfg = $extend(cfg, g ? { over: f, out: g } : f );
		var cX, cY, pX, pY;
		var track = function(ev) {
			cX = ev.page.x;
			cY = ev.page.y;
		};
		var compare = function(ev,ob) {
			ob.hoverIntent_t = clearTimeout(ob.hoverIntent_t);
			if ( ( Math.abs(pX-cX) + Math.abs(pY-cY) ) < cfg.sensitivity ) {
				$(ob).removeEvent("mousemove",track);
				ob.hoverIntent_s = 1;
				return cfg.over.apply(ob,[ev]);
			} else {
				pX = cX; pY = cY;
				ob.hoverIntent_t = setTimeout( function(){compare(ev, ob);} , cfg.interval );
			}
		};
		var delay = function(ev,ob) {
			ob.hoverIntent_t = clearTimeout(ob.hoverIntent_t);
			ob.hoverIntent_s = 0;
			return cfg.out.apply(ob,[ev]);
		};
		var handleHover = function(e) {
			var p = (e.type == "mouseover" ? e.fromElement : e.toElement) || e.relatedTarget;
			while ( p &#038;&#038; p != this ) { try { p = p.parentNode; } catch(e) { p = this; } }
			if ( p == this ) { return false; }
			var ev = $extend({},e);
			var ob = this;
			if (ob.hoverIntent_t) { ob.hoverIntent_t = clearTimeout(ob.hoverIntent_t); }
			if (e.type == "mouseover") {
				pX = ev.pageX; pY = ev.pageY;
				$(ob).addEvent("mousemove",track);
				if (ob.hoverIntent_s != 1) { ob.hoverIntent_t = setTimeout( function(){compare(ev,ob);} , cfg.interval );}
			} else {
				$(ob).removeEvent("mousemove",track);
				if (ob.hoverIntent_s == 1) { ob.hoverIntent_t = setTimeout( function(){delay(ev,ob);} , cfg.timeout );}
			}
		};
		return this.addEvent('mouseover', handleHover).addEvent('mouseout', handleHover)
	}
});
</pre>
<p>Paste this code into your scripts file. It will simply implement a new MooTools method for you, that will allow you to add the megaMenu functionality to any element/s that you desire. </p>
<h4>Usage</h4>
<pre class="brush: javascript;">
window.addEvent('domready', function() {
    // Function fired on mouseover
    function addMega(){
      $(this).addClass("hovering");
    }
    // Function fired on mouseout
    function removeMega(){
      $(this).removeClass("hovering");
    }
    var megaConfig = {
         interval: 200,
         sensitivity: 4,
         timeout: 200,
         over: addMega,
         out: removeMega
    };
    $$("li.mega").megaMenu(megaConfig)
});
</pre>
<p>Ok, so the first two functions "<strong>addMega</strong>" and "<strong>removeMega</strong>" are completely and utterly not needed, but you will most likely want to include them so that you can apply a class name or some other property to items that have the megaMenu method attached.</p>
<p><strong>megaConfig </strong> is simply your set up options, explained below.</p>
<ul>
<li><strong>interval:</strong> The number of milliseconds the function waits between reading/comparing mouse coordinates.</li>
<li><strong>sensitivity:</strong> If the mouse travels fewer than this number of pixels between polling intervals, then the "over" function will be called.</li>
<li><strong>timeout:</strong> A simple delay, in milliseconds, before the "out" function is called</li>
</ul>
<h4>Credits</h4>
<p>I can't claim full credit for the code and examples, I've borrowed heavily for times sake from the following sites.</p>
<p><a href="http://cherne.net/brian/resources/jquery.hoverIntent.html">Go here</a> for the jQuery mega drop down plugin</p>
<p><a href="http://blogs.sitepoint.com/2009/03/31/make-a-mega-drop-down-menu-with-jquery/" target="_blank">Go here</a> for the full SitePoint article on mega drop downs</p>
<p>Enjoy...</p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/mootools-mega-menu-drop-down/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Textarea Tabbing &#8211; code based tabs</title>
		<link>http://www.aplusdesign.com.au/blog/textarea-tabbing-code-based-tabs/</link>
		<comments>http://www.aplusdesign.com.au/blog/textarea-tabbing-code-based-tabs/#comments</comments>
		<pubDate>Wed, 28 Jul 2010 06:06:23 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[MooTools]]></category>
		<category><![CDATA[jQuery]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=227</guid>
		<description><![CDATA[Funny title I know, but really that is what this code will allow you to achieve. Recently I was working on a project that let users edit some source code in a HTML textarea box and send it back to us, so to provide some simple functionality and formatting whilst editing code in a textarea [...]]]></description>
			<content:encoded><![CDATA[<p>Funny title I know, but really that is what this code will allow you to achieve. Recently I was working on a project that let users edit some source code in a HTML textarea box and send it back to us, so to provide some simple functionality and formatting whilst editing code in a textarea I needed to find a way to mimic tab based behaviour from a text editor. </p>
<h4>Key features</h4>
<ul>
<li>Single tabbing from any point</li>
<li>Selection tabbing</li>
<li>Multiple line tabbing</li>
</ul>
<h4>Demo</h4>
<p><a class="demo" href="http://www.aplusdesign.com.au/demos/textarea-tabbing/tab_edit_mootools.php" target="_blank">View Demo :: MooTools</a><br />
<a class="demo" href="http://www.aplusdesign.com.au/demos/textarea-tabbing/tab_edit_jquery.php" target="_blank">View Demo :: jQuery</a></p>
<p>The demo has a textarea that has tabbing enabled and one below it that does not. That way you can see what pressing tab  does normally in a textarea and how it would be a real pain for someone trying to edit code. Basically tabbing in a normal textarea will move your focus elsewhere, if you are trying to tab a selection, it will in some browsers delete the selection.</p>
<p><span id="more-227"></span></p>
<h4>The HTML</h4>
<pre class="brush: plain;">
<textarea rows="20" cols="70" id="text-area-tab">
	// Some tabbed code
</textarea>
</pre>
<h4>The MooTools Javascript</h4>
<pre class="brush: javascript;">
var catchTab = new Class({
	initialize: function(id){
		var obj = this;
		$(id).addEvent( 'keydown', function(e){
			obj.tab(this, e);
		});
	},
	tab: function(textArea, evt) {
		if(evt.key == "tab"){
			evt.preventDefault();
			//internet explorer is Rtarded!
			if(Browser.Engine.trident) {
				var range = document.selection.createRange();
				range.text = '\t';
			}else{
				var start = textArea.selectionStart;
				var end = textArea.selectionEnd;
				var value = textArea.get('value');
				if (start!=end) {
					var lines = textArea.value.substring(start, end).split('\n');
					var lastI = lines.length;
					var tmpStr = '';
					lines.each(function(obj, key){
						tmpStr += '\t' + obj + (lastI != key+1 ? '\n' : '');
					}, this);
					textArea.set('value', value.substring(0, start) + tmpStr + value.substring(end, value.length));
					textArea.setSelectionRange(start, end+lastI);
				} else {
					textArea.set('value', value.substring(0, start) + '\t' + value.substring(end, value.length));
					start++;
					textArea.setSelectionRange(start, start);
				}
			}
		}
	}
});
</pre>
<h4>The jQuery Javascript</h4>
<pre class="brush: javascript;">
function catchTab(id) {
	this.init = function(id) {
		var obj = this;
		$('#'+id).bind('keydown', function(e) {
		  	obj.tab(this, e);
		});
    };
	this.tab = function(textArea, evt) {
		if(evt.keyCode == "9"){
			evt.preventDefault();
			if(jQuery.browser.msie) {
				//internet explorer is Rtarded!
				var range = document.selection.createRange();
				range.text = '\t';
			}else{
				var start = textArea.selectionStart;
				var end = textArea.selectionEnd;
				var value = textArea.value;
				if (start!=end) {
					var lines = textArea.value.substring(start, end).split('\n');
					var lastI = lines.length;
					var tmpStr = '';
					$.each(lines, function(key, obj){
						tmpStr += '\t' + obj + (lastI != key+1 ? '\n' : '');
					});
					textArea.value = (value.substring(0, start) + tmpStr + value.substring(end, value.length));
					textArea.setSelectionRange(start, end+lastI);
				} else {
					textArea.value = (value.substring(0, start) + '\t' + value.substring(end, value.length));
					start++;
					textArea.setSelectionRange(start, start);
				}
			}
		}
	};
    this.init(id);
}
</pre>
<h4>Usage</h4>
<pre class="brush: javascript;">
// MooTools
window.addEvent('domready', function() {
	// ID of textarea
	new catchTab('text-area-tab');
});
// jQuery
$(document).ready(function() {
	// ID of textarea
	new catchTab('text-area-tab');
});
</pre>
<h4>Instructions</h4>
<p>Pretty easy, add the HTML and Javascript to your page, target the textarea with your ID when you call <strong>&#8216;catchTab&#8217;</strong>, the script will do the rest of the work for you. Your textarea will now have tabbing enabled.</p>
<h4>Accessibility</h4>
<p>You could argue that removing the tabs natural functions from the textarea box is a bad move, it will prevent a user tabbing through your website, as once they are inside the textarea the tab will work like a text editing function, a user will need to focus off the textarea to somewhere else to regain normal tabbing functionality.</p>
<p>The key here is, it meets a purpose, that purpose is to allow tabbing inside a textarea so that you can correctly format code. We have all tried to edit our code on a post such as this in WordPress or other online editors only to find that every time we try to add a tab it moves our focus to the submit button or in the worst case deletes it. I&#8217;ve personally seen thousands of blog comments that suffer from poor formatting of reposted code, this is extremely useful if your users don&#8217;t know where those illusive [code] [/code]  tags are hidden.</p>
<p>So use it at your own leisure <img src='http://www.aplusdesign.com.au/blog/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>enjoy!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/textarea-tabbing-code-based-tabs/feed/</wfw:commentRss>
		<slash:comments>9</slash:comments>
		</item>
		<item>
		<title>Semantic Website Heading Trick</title>
		<link>http://www.aplusdesign.com.au/blog/semantic-website-heading-trick/</link>
		<comments>http://www.aplusdesign.com.au/blog/semantic-website-heading-trick/#comments</comments>
		<pubDate>Thu, 22 Jul 2010 07:38:56 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[CSS]]></category>
		<category><![CDATA[HTML]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=216</guid>
		<description><![CDATA[Ok this is thinking outside the box to solve a somewhat annoying and completely arguable problem. The problem: I want my websites heading to have two words and one of those words I want to be in bold, or, and maybe even in a different colour. The usual solution: &#60;h1&#62;firstWord &#60;span&#62;secondWord&#60;/span&#62;&#60;/h1&#62; Looks something like this [...]]]></description>
			<content:encoded><![CDATA[<p>Ok this is thinking outside the box to solve a somewhat annoying and completely arguable problem. </p>
<p><strong>The problem:</strong> I want my websites heading to have two words and one of those words I want  to be in bold, or, and maybe even in a different colour.</p>
<p><strong>The usual solution:</strong> </p>
<pre class="php"><span class="phpOperator">&lt;</span>h1<span class="phpOperator">&gt;</span>firstWord <span class="phpOperator">&lt;</span>span<span class="phpOperator">&gt;</span>secondWord<span class="phpOperator">&lt;</span>/span<span class="phpOperator">&gt;</span><span class="phpOperator">&lt;</span>/h1<span class="phpOperator">&gt;</span></pre>
<p>Looks something like this after some CSS &#8211; &#8220;firstWird <strong>secondWord</strong>&#8221;</p>
<p>The question I ask myself is simple, does Google like me putting spans, an element with no semantic value inside of my h1&#8242;s, h1&#8242;s being an element with very important semantic value?</p>
<p>If it doesn&#8217;t, why should I be punished for using text instead of an image to make my title stand out? Seems annoying doesn&#8217;t it. Well it annoyed me so much I came up with a solution.</p>
<p><span id="more-216"></span></p>
<h4>A+ solution:</h4>
<p><a href="http://www.aplusdesign.com.au/demos/tricks/semantic-title.html" target="_blank">View Demo</a></p>
<p><strong>The html</strong></p>
<pre class="html"><span class="htmlOtherTag">&lt;h1&gt;</span>firstWord secondWord<span class="htmlOtherTag">&lt;/h1&gt;</span></pre>
<p><strong>The CSS</strong></p>
<pre class="php">
h1 <span class="phpOperator">{</span>
	font<span class="phpOperator">:</span> normal  <span class="phpNumber">2</span><span class="phpOperator">.</span>25em Arial,Helvetica,Tahoma,Verdana,Sans-Serif<span class="phpText">;</span>
	position<span class="phpOperator">:</span>relative<span class="phpText">;</span>
	height<span class="phpOperator">:</span>0px<span class="phpText">;</span>
	padding<span class="phpOperator">:</span>50px 0px 0px 0px<span class="phpText">;</span>
	overflow<span class="phpOperator">:</span>hidden<span class="phpText">;</span>
<span class="phpOperator">}</span>
h1<span class="phpOperator">:</span>before <span class="phpOperator">{</span>
	content<span class="phpOperator">:</span> <span class="phpString">'firstWord '</span><span class="phpText">;</span>
	position<span class="phpOperator">:</span>absolute<span class="phpText">;</span>
	top<span class="phpOperator">:</span>0px<span class="phpText">;</span>
<span class="phpOperator">}</span>
h1<span class="phpOperator">:</span>after <span class="phpOperator">{</span>
	content<span class="phpOperator">:</span> <span class="phpString">'secondWord'</span><span class="phpText">;</span>
	font-weight<span class="phpOperator">:</span>bold<span class="phpText">;</span>
	position<span class="phpOperator">:</span>absolute<span class="phpText">;</span> top<span class="phpOperator">:</span>0px<span class="phpText">;</span>
	left<span class="phpOperator">:</span><span class="phpNumber">4</span><span class="phpOperator">.</span>5em<span class="phpText">;</span>
<span class="phpOperator">}</span>
</pre>
<p>That&#8217;s it you&#8217;re done. View the demo and you will see the bolded second word, you can set any number of different styles on the words to achieve your desired look. Plus it is semantically more correct, it requires no span inside your <strong>h1</strong> tag. If you have FireBug installed, inspect the element, you will see the inner value for the h1 node is simply &#8216;firstWord secondWord&#8217; and that is how a search engine will see it!</p>
<p>Obviously this solution is of limited use, you can&#8217;t use more than two words, as you can only define a single :before and a single :after on each element, in this case our <strong>h1</strong>. You also need to specifically set where the second word will appear, as it is inserted after the normal content, which is hidden by the extra padding, so your second word without the positioning styles will also be hidden until you move it into view.</p>
<p>Well that&#8217;s it folks, although it is dubious that this will become a mainstream solution it certainly solved my dilemma of useless markup in my headings.</p>
<p>Enjoy!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/semantic-website-heading-trick/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Title to URL &#8211; WordPress style</title>
		<link>http://www.aplusdesign.com.au/blog/title-to-url-wordpress-style/</link>
		<comments>http://www.aplusdesign.com.au/blog/title-to-url-wordpress-style/#comments</comments>
		<pubDate>Thu, 15 Jul 2010 02:22:47 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[MooTools]]></category>
		<category><![CDATA[jQuery]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=197</guid>
		<description><![CDATA[Have you ever wanted to immediatly create a valid URL from a text input field or some kind of semantic input filed, I know I&#8217;ve had to implement it a few times now for different projects. Typically it will be something like, this new created object needs a name or title and that name or [...]]]></description>
			<content:encoded><![CDATA[<p>Have you ever wanted to immediatly create a valid URL from a text input field or some kind of semantic input filed, I know I&#8217;ve had to implement it a few times now for different projects. Typically it will be something like, this new created object needs a name or title and that name or title needs to be converted into a URL which the user can see, and then edit to something more meaningful should they choose to. A good example of this already in action is in your wordpress blog, when you type in your post title Worpress automatically creates a URL for you and allows you to then edit and change the URL without also annoyingly changing the original title.</p>
<p>I&#8217;ve implemented this a few times now for different applications so here is the base code I tend to start with. </p>
<p><a class="demo" href="http://www.aplusdesign.com.au/demos/url-builder/title-to-url-mootools.html" target="_blank">View Demo :: MooTools</a><br />
<a class="demo" href="http://www.aplusdesign.com.au/demos/url-builder/title-to-url-jquery.html" target="_blank">View Demo :: jQuery</a></p>
<p>Notice how after editing the URL field the title will stop changing the URL value. The logic being that once you have edited the URL to your liking, updating the title will cease to overwrite your new URL.</p>
<p><span id="more-197"></span></p>
<h4>The HTML</h4>
<pre class="brush: plain;">
<input value="" id="pTitle" type="text" />
<div>
    <span>http://blah.com/</span>
<input value="" id="pTitle_url" type="text" class="myinput" />
    <span id="pTitle_update"></span>
    <span id="pTitle_edit">edit</span>
</div>
</pre>
<p>Add this html to your page. Take notice of the ID&#8217;s that is how the script will target all the necessary elements.</p>
<h4>The Style</h4>
<pre class="brush: css;">
.myinput {
	display:none;
}
</pre>
<p>Very basic stuff here. Theres more styles in the demo files.</p>
<h4>The MooTools Javascript</h4>
<pre class="brush: javascript;">
var urlBuilder = new Class({
	Implements: [Options, Events],
	options: {
		title : {
			regx	: [/[^0-9a-zA-Z\s.,'!@%#)(:\;\"]+?/,/\s+/g,/^[\s]+/g,/([0-9a-zA-Z\s.,'!@%#)(:\;\"]{50})(.+)/i],
			rep		: ['',' ','', '$1']
		},
		url : {
			regx	: [/[^0-9a-zA-Z]+?/g,/[\-]+/g,/^[-]+/,/[-]+$/],
			rep		: ['-','-','','-']
		}
	},
	initialize: function(element, urlFlag, options){
		this.setOptions(options);
		this.inputObj 	= element;
		this.newUrl		= $(element.id+'_url');
		this.updateUrl	= $(element.id+'_update');
		this.edit		= $(element.id+'_edit');
		this.ChangedURL = (!urlFlag ? false : urlFlag);
		this.init();
	},
	init: function() {
		this.inputObj.addEvent('keydown', this.getValue.bindWithEvent(this,  this.options.title ));
		this.inputObj.addEvent('keyup', this.getValue.bindWithEvent(this,  this.options.title ));
		this.newUrl.addEvent('keyup', this.getValue.bindWithEvent(this, this.options.url));
		this.edit.addEvent('mousedown', this.showURL.bindWithEvent(this));
	},
	getUri: function(uri, o) {
		o.regx.each(function(index, key) {
			uri = uri.replace(index, o.rep[key]);
		});
		return uri;
	},
	getValue: function(e, o) {
		var input = getTarget(e);
		if (input == this.newUrl) this.ChangedURL=true;
		var tmp = this.getUri(input.value, o);
		if (input.value != tmp )
			input.value = tmp;
		if (input != this.inputObj || !this.ChangedURL) {
			tmp = this.getUri(tmp, this.options.url);
			this.newUrl.value = tmp.toLowerCase();
			this.update(tmp + (tmp != '' ? '/' : ''));
		}
	},
	showURL: function(e) {
		var o = this.newUrl;
		var u = this.updateUrl;
		if (o.getStyle('display') == 'none') {
			o.setStyle('display', 'inline-block');
			u.setStyle('display', 'none');
			this.edit.set('html', 'Save');
		} else {
			o.setStyle('display', 'none');
			u.setStyle('display', '');
			this.edit.set('html', 'edit');
		}
	},
	update: function(s) {
		this.updateUrl.set('html', s);
	}
});
</pre>
<h4>The jQuery Javascript</h4>
<pre class="brush: javascript;">
function urlBuilder(el, urlFlag, options) {
	// Becomes this.options
	var defaults = {
		title : {
			regx	: [/[^0-9a-zA-Z\s.,'!@%#)(:\;\"]+?/,/\s+/g,/^[\s]+/g,/([0-9a-zA-Z\s.,'!@%#)(:\;\"]{30})(.+)/i],
			rep		: ['',' ','', '$1']
		},
		url : {
			regx	: [/[^0-9a-zA-Z]+?/g,/[\-]+/g,/^[-]+/,/[-]+$/],
			rep		: ['-','-','','-']
		}
	}
	this.options 	= jQuery.extend(defaults, options);
	this.init = function(el, urlFlag) {
		var id 			= el;
		this.inputObj 	= $('#'+el);
		this.newUrl		= $('#'+id+'_url');
		this.updateUrl	= $('#'+id+'_update');
		this.edit		= $('#'+id+'_edit');
		this.ChangedURL = (!urlFlag ? false : urlFlag);
		this.events();
    };
	this.events = function() {
		var obj = this;
		this.inputObj.bind('keyup', function(e) {
		  	obj.loadUri(e, 'title');
		});
		this.newUrl.bind('keyup', function(e) {
		  	obj.loadUri(e, 'url');
		});
		this.edit.bind('mousedown', function(e) {
			e.preventDefault();
		  	obj.showURL(e.target);
		});
	};
	this.loadUri = function(e, str) {
		e.preventDefault();
		this.getValue(e.target, this.options[str]);
	};
	this.getUri = function(uri, o) {
		var collection = o.regx;
		for (index in collection) {
			uri = uri.replace(collection[index], o.rep[index]);
		}
		return uri;
	};
	this.getValue = function(e, o) {
		var input = $(e);
		if (input[0] == this.newUrl[0]) this.ChangedURL=true;
		var tmp = this.getUri(input.attr('value'), o);
		input.attr('value', tmp);
		if (input[0] != this.inputObj[0] || !this.ChangedURL) {
			tmp = this.getUri(tmp, this.options.url);
			this.newUrl.attr('value', tmp.toLowerCase());
			this.update(tmp + (tmp != '' ? '/' : ''));
		}
	};
	this.showURL = function(e) {
		var o = this.newUrl;
		var u = this.updateUrl;
		if (o.css('display') == 'none') {
			o.css('display', 'inline-block');
			u.css('display', 'none');
			this.edit.html('save');
		} else {
			o.css('display', 'none');
			u.css('display', '');
			this.edit.html('edit');
		}
	};
	this.update = function(s) {
		this.updateUrl.html(s);
	};
    this.init(el, urlFlag);
}
</pre>
<h4>Usage</h4>
<pre class="brush: javascript;">
// MooTools
window.addEvent('domready', function() {
	new urlBuilder($('pTitle'));
});
// jQuery
$(document).ready(function() {
	new urlBuilder('pTitle');
});
</pre>
<p>The only thing to be aware of here is that I&#8217;m also giving you a field called &#8216;urlFlag&#8217; set it to true in your call to urlBuilder like this if the user has previously edited the URL field.</p>
<pre class="brush: javascript;">
        new urlBuilder($('pTitle'), true, { //options });
</pre>
<p>If not set it will default to false and assume the title will still update the URL field.</p>
<h4>Options</h4>
<pre class="brush: javascript;">
	title : {
		regx : [/[^0-9a-zA-Z\s.,'!@%#)(:\;\"]+?/,/\s+/g,/^[\s]+/g,/([0-9a-zA-Z\s.,'!@%#)(:\;\"]{50})(.+)/i],
		rep : ['',' ','', '$1']
	},
	url : {
		regx : [/[^0-9a-zA-Z]+?/g,/[\-]+/g,/^[-]+/,/[-]+$/],
		rep : ['-','-','','-']
	}
</pre>
<p>Here is the best part of this little plugin. In the options you have two objects, &#8216;title&#8217; and &#8216;url&#8217; consisting of <strong>four simple regular expressions</strong>. You can overide these from your set-up calls, or you can leave them as is. Basically I&#8217;m just giving you control over what to filter out on the input and url, and what to leave in. </p>
<p>The <strong>&#8216;title&#8217; option</strong> simply has four regex values in the array <strong>&#8216;regx&#8217;</strong>, and it has four matching replacment values in the array <strong>&#8216;rep&#8217;</strong>, so when the pattern from regx[0] is matched it will be replaced by the value of rep[0].</p>
<p>The <strong>&#8216;url&#8217; option</strong> works in the exact same way. I&#8217;ve done it this way to provide simpler regex values for those that are not rocket scientists. Plus I highly doubt its possible to build a regex that accomplishes everything we need to do to strip a title down for publishing whilst turning it into a valid URL for location.</p>
<h4>Required</h4>
<ul>
<li>MooTools Core</li>
<li>jQuery Core</li>
</ul>
<h4>Download</h4>
<p>Contains both MooTools and jQuery versions</p>
<p><a href="http://www.aplusdesign.com.au/demos/url-builder/url-builder.zip" target="_blank">URL  Builder</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/title-to-url-wordpress-style/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Speed up heavy Twitter feeds 2</title>
		<link>http://www.aplusdesign.com.au/blog/speed-up-heavy-twitter-feeds-2/</link>
		<comments>http://www.aplusdesign.com.au/blog/speed-up-heavy-twitter-feeds-2/#comments</comments>
		<pubDate>Wed, 14 Jul 2010 03:34:05 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[MooTools]]></category>
		<category><![CDATA[Optimisation]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=164</guid>
		<description><![CDATA[This is a follow up to Speed up heavy Twitter feeds The original post was quite simply a way for you to get yours or someone elses public Twitter timeline and display it on your own site. Twitter decided to kill off basic authentication for their API preventing simple Ajaxian requests to the API. So [...]]]></description>
			<content:encoded><![CDATA[<p><strong>This is a follow up to</strong> <a href="http://www.aplusdesign.com.au/blog/speed-up-heavy-twitter-feeds/">Speed up heavy Twitter feeds</a></p>
<p>The original post was quite simply a way for you to get yours or someone elses public Twitter timeline and display it on your own site. Twitter decided to kill off basic authentication for their API preventing simple Ajaxian requests to the API. So here is the solution and it comes in the form of JSONP (cross site scripting request).</p>
<p><a class="demo" href="http://www.aplusdesign.com.au/demos/twitter-feed2.php" target="blank" rel="nofollow">View Demo :: MooTools</a></p>
<p><span id="more-164"></span></p>
<h4>Original excerpt</h4>
<p><em>&#8220;<strong>Ever wondered where that missing second is in your blog or Web Sites loading time?</strong></p>
<p>Chances are that it is getting eaten up by your feeds or third party API&#8217;s like Twitter, Facebook, Google and Flickr. We all love social media, if you don&#8217;t then you were probably the school captain throughout your education and don&#8217;t posses the intrinsic ability to Tweet, Blog at update your feed from that shiny Iphone at any given time of the day, rain, hail or shine. But for the rest of us, here is a simple solution&#8230;&#8230;&#8221;</em></p>
<h4>The New HTML</h4>
<pre class="html"><span class="htmlOtherTag">&lt;div id=<span class="htmlAttributeValue">&quot;twitter-update&quot;</span>&gt;</span><span class="htmlOtherTag">&lt;/div&gt;</span></pre>
<p>Add this to your web-site. It is the container which the JavaScript will look for to insert your Twitter posts</p>
<h4>The MooTools Javascript</h4>
<pre class="php">
<span class="phpKeyword">
var </span>twitterUpdate <span class="phpOperator">=</span><span class="phpKeyword"> new </span>Class<span class="phpOperator">(</span><span class="phpOperator">{</span>
	Implements<span class="phpOperator">:</span> <span class="phpOperator">[</span>Options, Events<span class="phpOperator">]</span>,
	options<span class="phpOperator">:</span> <span class="phpOperator">{</span>
		count<span class="phpOperator">:</span> <span class="phpNumber">2</span>,
		user_id<span class="phpOperator">:</span> <span class="phpString">'default_user'</span>,
		id<span class="phpOperator">:</span> <span class="phpString">'twitter-update'</span>
	<span class="phpOperator">}</span>,
	initialize<span class="phpOperator">:</span> <span class="phpFunctionKeyword">function</span><span class="phpOperator">(</span>options<span class="phpOperator">)</span><span class="phpOperator">{</span>
		this<span class="phpOperator">.</span>setOptions<span class="phpOperator">(</span>options<span class="phpOperator">)</span><span class="phpText">;</span>
		this<span class="phpOperator">.</span>userName <span class="phpOperator">=</span> this<span class="phpOperator">.</span>options<span class="phpOperator">.</span>user_id<span class="phpText">;</span>
		this<span class="phpOperator">.</span>update <span class="phpOperator">=</span> $<span class="phpOperator">(</span>this<span class="phpOperator">.</span>options<span class="phpOperator">.</span>id<span class="phpOperator">)</span><span class="phpText">;</span>
	<span class="phpKeyword">	if </span><span class="phpOperator">(</span>this<span class="phpOperator">.</span>update<span class="phpOperator">)</span>
			this<span class="phpOperator">.</span>getTweets<span class="phpOperator">(</span><span class="phpOperator">)</span><span class="phpText">;</span>
	<span class="phpOperator">}</span>,
	getTweets<span class="phpOperator">:</span> <span class="phpFunctionKeyword">function</span><span class="phpOperator">(</span><span class="phpOperator">)</span> <span class="phpOperator">{</span>
	<span class="phpKeyword">	new </span>Request.JSONP<span class="phpOperator">(</span><span class="phpOperator">{</span>
		  url<span class="phpOperator">:</span> <span class="phpString">'http<span class="phpOperator">:</span><span class="phpComment">//twitter.com/statuses/user_timeline/'</span> <span class="phpOperator">+</span> this<span class="phpOperator">.</span>userName <span class="phpOperator">+</span> <span class="phpString">'<span class="phpOperator">.</span>json'</span>,
</span>			data<span class="phpOperator">:</span> <span class="phpOperator">{</span>
				count<span class="phpOperator">:</span> this<span class="phpOperator">.</span>options<span class="phpOperator">.</span>count
			<span class="phpOperator">}</span>,
			onSuccess<span class="phpOperator">:</span> <span class="phpFunctionKeyword">function</span><span class="phpOperator">(</span>tweets<span class="phpOperator">)</span><span class="phpOperator">{</span>
				tweets<span class="phpOperator">.</span><span class="phpFunction">each</span><span class="phpOperator">(</span><span class="phpFunctionKeyword">function</span><span class="phpOperator">(</span>tweet,i<span class="phpOperator">)</span> <span class="phpOperator">{</span>
				<span class="phpKeyword">	var </span>tmp <span class="phpOperator">=</span> this<span class="phpOperator">.</span>tweetify<span class="phpOperator">(</span>tweet.text<span class="phpOperator">)</span>
				<span class="phpKeyword">	new </span>Element<span class="phpOperator">(</span><span class="phpString">'li'</span>,<span class="phpOperator">{</span>
						html<span class="phpOperator">:</span> <span class="phpString">'<span class="phpOperator">&lt;</span>p<span class="phpOperator">&gt;</span><span class="phpOperator">&lt;</span>a href=<span class="phpString">"http<span class="phpOperator">:</span><span class="phpComment"><span class="phpComment">//twitter.com/'</span> <span class="phpOperator">+</span> this<span class="phpOperator">.</span>userName <span class="phpOperator">+</span> <span class="phpString">'"</span></span><span class="phpOperator">&gt;</span>#<span class="phpOperator">&lt;</span>/a<span class="phpOperator">&gt;</span> '</span> <span class="phpOperator">+</span> tmp <span class="phpOperator">+</span> <span class="phpString">'<span class="phpOperator">&lt;</span>/p<span class="phpOperator">&gt;</span>'</span>
</span>					<span class="phpOperator">}</span><span class="phpOperator">)</span>.inject<span class="phpOperator">(</span><span class="phpString">'twitter-updates'</span><span class="phpOperator">)</span><span class="phpText">;</span>
				<span class="phpOperator">}</span>, this<span class="phpOperator">)</span><span class="phpText">;</span>
			<span class="phpOperator">}</span>.bind<span class="phpOperator">(</span>this<span class="phpOperator">)</span>
		<span class="phpOperator">}</span><span class="phpOperator">)</span>.send<span class="phpOperator">(</span><span class="phpOperator">)</span><span class="phpText">;</span>
	<span class="phpOperator">}</span>,
	<span class="phpComment">/* Credit to David Walsh here */</span>
	tweetify<span class="phpOperator">:</span> <span class="phpFunctionKeyword">function</span><span class="phpOperator">(</span>str<span class="phpOperator">)</span> <span class="phpOperator">{</span>
	<span class="phpKeyword">	return </span>str.replace<span class="phpOperator">(</span>/<span class="phpOperator">(</span>https<span class="phpOperator">?</span><span class="phpOperator">:</span>\/\/\S<span class="phpOperator">+</span><span class="phpOperator">)</span>/gi,<span class="phpString">'<span class="phpOperator">&lt;</span>a href=<span class="phpString">"$<span class="phpNumber">1</span>"</span><span class="phpOperator">&gt;</span>$<span class="phpNumber">1</span><span class="phpOperator">&lt;</span>/a<span class="phpOperator">&gt;</span>'</span><span class="phpOperator">)</span>.replace<span class="phpOperator">(</span>/<span class="phpOperator">(</span>^<span class="phpOperator">|</span>\s<span class="phpOperator">)</span>@<span class="phpOperator">(</span>\w<span class="phpOperator">+</span><span class="phpOperator">)</span>/g,<span class="phpString">'$<span class="phpNumber">1</span><span class="phpOperator">&lt;</span>a href=<span class="phpString">"http<span class="phpOperator">:</span><span class="phpComment"><span class="phpComment">//twitter.com/$<span class="phpNumber">2</span>"</span></span><span class="phpOperator">&gt;</span>@$<span class="phpNumber">2</span><span class="phpOperator">&lt;</span>/a<span class="phpOperator">&gt;</span>'</span><span class="phpOperator">)</span>.replace<span class="phpOperator">(</span>/<span class="phpOperator">(</span>^<span class="phpOperator">|</span>\s<span class="phpOperator">)</span>#<span class="phpOperator">(</span>\w<span class="phpOperator">+</span><span class="phpOperator">)</span>/g,<span class="phpString">'$<span class="phpNumber">1</span><span class="phpOperator">&lt;</span>a href=<span class="phpString">"http<span class="phpOperator">:</span><span class="phpComment">//search<span class="phpOperator">.</span>twitter.com/search<span class="phpOperator">?</span>q<span class="phpOperator">=</span>%23$<span class="phpNumber">2</span>"</span></span><span class="phpOperator">&gt;</span>#$<span class="phpNumber">2</span><span class="phpOperator">&lt;</span>/a<span class="phpOperator">&gt;</span>'</span><span class="phpOperator">)</span><span class="phpText">;</span>
</span>	<span class="phpOperator">}</span>
<span class="phpOperator">}</span><span class="phpOperator">)</span><span class="phpText">;</span>
</pre>
<p>Copy this into your JavaScript file. It will run on &#8216;domready&#8217; to retrieve our twitter posts.</p>
<h4>Usage</h4>
<pre class="php">
window<span class="phpOperator">.</span>addEvent<span class="phpOperator">(</span><span class="phpString">'domready'</span>,<span class="phpFunctionKeyword">function</span><span class="phpOperator">(</span><span class="phpOperator">)</span><span class="phpOperator">{</span>
        <span class="phpComment">// Get <span class="phpNumber">2</span> tweets<span class="phpKeyword"> for </span>simon_ilett and insert them into the element with id <span class="phpString">'twitter-update'</span>
</span><span class="phpKeyword">	new </span>twitterUpdate<span class="phpOperator">(</span><span class="phpOperator">{</span> <span class="phpString">'user_id'</span> <span class="phpOperator">:</span> <span class="phpString">'simon_ilett'</span><span class="phpOperator">}</span><span class="phpOperator">)</span><span class="phpText">;</span> 
        <span class="phpComment">// Get <span class="phpNumber">5</span> tweets<span class="phpKeyword"> for </span>bill_henry and insert them into the element with id <span class="phpString">'twitter-feed'</span>
</span><span class="phpKeyword">	new </span>twitterUpdate<span class="phpOperator">(</span><span class="phpOperator">{</span> <span class="phpString">'user_id'</span> <span class="phpOperator">:</span> <span class="phpString">'bill_henry'</span>, <span class="phpString">'id'</span> <span class="phpOperator">:</span> <span class="phpString">'twitter-feed'</span>, <span class="phpString">'count'</span> <span class="phpOperator">:</span> <span class="phpNumber">5</span><span class="phpOperator">}</span><span class="phpOperator">)</span><span class="phpText">;</span> 
<span class="phpOperator">}</span><span class="phpOperator">)</span><span class="phpText">;</span>
</pre>
<h4>Options</h4>
<pre class="php">
<span class="phpComment">/* Default Options */</span>
<span class="phpOperator">{</span>
    count<span class="phpOperator">:</span> <span class="phpNumber">2</span>,
    user_id<span class="phpOperator">:</span> <span class="phpString">'default_user'</span>,
    id<span class="phpOperator">:</span> <span class="phpString">'twitter_update'</span>
<span class="phpOperator">}</span>
</pre>
<p>Here is a quick idea of what each option is doing.</p>
<ul>
<li><strong>count </strong> &#8211; How many tweets to return as JSON objects</li>
<li><strong>default user</strong> &#8211; A default user name to return tweets for</li>
<li><strong>id</strong> &#8211; A default element for the script to place return tweets in</li>
</ul>
<h4>Updating the output</h4>
<p>Again very simple, all you do is change the following snippet</p>
<pre class="php">
<span class="phpKeyword">
new </span>Element<span class="phpOperator">(</span><span class="phpString">'p'</span>,<span class="phpOperator">{</span>
	html<span class="phpOperator">:</span> <span class="phpString">'<span class="phpOperator">&lt;</span>a href=<span class="phpString">"http<span class="phpOperator">:</span><span class="phpComment"><span class="phpComment">//twitter.com/'</span> <span class="phpOperator">+</span> this<span class="phpOperator">.</span>userName <span class="phpOperator">+</span> <span class="phpString">'"</span></span><span class="phpOperator">&gt;</span><span class="phpOperator">&lt;</span>span<span class="phpOperator">&gt;</span>#<span class="phpOperator">&lt;</span>/span<span class="phpOperator">&gt;</span> '</span> <span class="phpOperator">+</span> tweet.text <span class="phpOperator">+</span> <span class="phpString">' <span class="phpOperator">&lt;</span>/a<span class="phpOperator">&gt;</span>'</span>
</span><span class="phpOperator">}</span><span class="phpOperator">)</span>.inject<span class="phpOperator">(</span>this<span class="phpOperator">.</span>update<span class="phpOperator">)</span><span class="phpText">;</span>
</pre>
<p>This way your not locked into any over-riding HTML output, easy to change to your liking.</p>
<h4>Required</h4>
<ul>
<li>MooTools Core</li>
<li>MooTools More &#8211; JsonP</li>
</ul>
<p>Enjoy!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/speed-up-heavy-twitter-feeds-2/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Opera CSS Integer bug</title>
		<link>http://www.aplusdesign.com.au/blog/opera-css-integer-bug/</link>
		<comments>http://www.aplusdesign.com.au/blog/opera-css-integer-bug/#comments</comments>
		<pubDate>Mon, 12 Jul 2010 01:30:30 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[CSS]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=156</guid>
		<description><![CDATA[Ok found this bug while working on a project that required a scrolling content bar that wound up needing widths defined in the stylesheet greater then 32,767 px. Some people will immediatly notice the 32,767 as the programatic max value for an &#8216;Integer&#8217;, which is exactly what the problem is. Opera for some reason, and [...]]]></description>
			<content:encoded><![CDATA[<p>Ok found this bug while working on a project that required a scrolling content bar that wound up needing widths defined in the stylesheet greater then 32,767 px.</p>
<p>Some people will immediatly notice the 32,767 as the programatic <strong>max value</strong> for an <strong>&#8216;Integer&#8217;</strong>, which is exactly what the problem is. Opera for some reason, and it is completly alone here, as all other browsers even the dreaded Internet Explorer 6, can handle CSS values that exceed this limit. Opera will silently fail, throw no warning about it and ignore all styles that follow non integer numbers in your selector.</p>
<p>There was no way around this I could find to make it work in Opera, simply put. </p>
<p>Any number bigger then 32,767 for a value in CSS when displaying with Opera 10, will be ignored and cause all following styles in that selector to be dropped.</p>
<p><strong>Heres an example.</strong></p>
<pre class="brush: css; highlight: [4]">
div #myElement {
    position:absolute;
    height:500px;
    width:50000px;
    background:#444;
    font-weight:bold;
}
</pre>
<p>The above code will cause the div &#8216;myElement&#8217; to have no selectable width, and will never apply the background or font-weight properties!</p>
<p><span id="more-156"></span></p>
<h4>Solutions</h4>
<p><strong>A bad solution</strong></p>
<pre class="brush: css; highlight: [6]">
div #myElement {
    position:absolute;
    height:500px;
    background:#444;
    font-weight:bold;
    width:50000px;
}
</pre>
<p>The div &#8216;myElement&#8217; will now get all styles applied correctly up until it hits the width:50000px property. But since no styles are applied after it is encountered the div is styled with all your properties correctly except of course for a width value. The div will still have no width.</p>
<p><strong>Correct solution</strong></p>
<pre class="brush: css;highlight: [6]">
div #myElement {
    position:absolute;
    height:500px;
    background:#444;
    font-weight:bold;
    width:32000px;
}
</pre>
<p>Now the div &#8216;myElement&#8217; will be styled correctly and have a width property. Its no 50,000 pixels, but 32,000 which is a valid width in Opera, remember anything greater then 32,767 will fail. Should you need greater then 32,000 pixels of space in Opera, you may need to re-think your design, or go hassle the Opera development team. </p>
<p>Last I saw there were a couple bug reports if you knew what to search for, but nothing had been posted in reply. SO we can only hope  that Opera know of the issue and are working to correct it. But in the meantime I&#8217;ve given you the power to detect and develop around this quite interesting bug.</p>
<p>Enjoy <img src='http://www.aplusdesign.com.au/blog/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/opera-css-integer-bug/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Ajax Pagination &amp; Back Button</title>
		<link>http://www.aplusdesign.com.au/blog/ajax-pagination-back-button/</link>
		<comments>http://www.aplusdesign.com.au/blog/ajax-pagination-back-button/#comments</comments>
		<pubDate>Thu, 24 Jun 2010 04:08:58 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[Ajax]]></category>
		<category><![CDATA[MooTools]]></category>
		<category><![CDATA[jQuery]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=130</guid>
		<description><![CDATA[Ok so hands up if your a fan of Ajax, you can&#8217;t see it but I certainly have my hands up as do many of the other developers out there, so what is this post about? Well if you have ever built an Ajax application or website you would know that Ajax breaks the browsers [...]]]></description>
			<content:encoded><![CDATA[<p>Ok so hands up if your a fan of Ajax, you can&#8217;t see it but I certainly have my hands up as do many of the other developers out there, so what is this post about? Well if you have ever built an Ajax application or website you would know that Ajax breaks the browsers natural navigation, things like the &#8216;back button&#8217;, &#8216;forward button&#8217;, history, favouriting a page or browsing to it via the URL input all become useless because there is no physical URL for those elements to use or save.</p>
<p>Now yes there are some solutions out there for providing Ajaxified links that keep your back buttons working, they are complex and usually written in a specific framework, so if you want to use them well your going to be adding a lot more code then you thought to your web site. Plus this is how Gmail and Facebook do it, you won&#8217;t find there code or get any help from them on the topic so I decided to build it myself so everyone could get the benefits of Ajax URL navigation. Below is an example of a simple yet elegant Ajax Pagination system I&#8217;ve written to relieve the navigation hicups Ajax causes.</p>
<h4>Demo</h4>
<p><a class="demo" href="http://www.aplusdesign.com.au/misc/pagination/pagination.php" target="_blank">View Demo :: MooTools</a><br />
<a class="demo" href="http://www.aplusdesign.com.au/misc/pagination/pagination_jquery.php" target="_blank">View Demo :: jQuery</a></p>
<p><span id="more-130"></span></p>
<h4>How it works</h4>
<p>Very simply the pagination class is loading each successive request via ajax into the dom and slides it into view, it also replaces the pagination controls each time with the new correct numbering of the new pagination controls including highlighting, prev, next buttons etc&#8230; Replacing the pagination controls each time is by far the smartest way of doing things, as the Pagination class has nothing to do with manipulating the controls, saving complexity in a grand way because in an ajaxed pagination application the JavaScript should never be responsible for rebuilding the pagination controls, that should be handled by your server side code! </p>
<p><strong>URL hash</strong> Now here is the kicker, after you have used the pagination controls, hit the <strong>Back Button</strong>, and there you go, BAM, you&#8217;ve gone back to your previously selected pagination results without causing a reload of your page.  This is accomplished by updating the <strong>hash (#)</strong> value of the URL, we have full access to the hash section of a URL via JavaScript, we have no access to the URL though, it is a security measure built into JavaScript which denies us the power to edit it. So the answer to creating new linkable URL&#8217;s is the hash value. We can update and check it as we need to.</p>
<pre class="php">
<span class="phpComment">/* get hash value */</span>
<span class="phpKeyword">
var </span>tmp <span class="phpOperator">=</span> window<span class="phpOperator">.</span>location<span class="phpOperator">.</span>hash<span class="phpText">;</span>
<span class="phpComment">/* set hash value */</span>
window<span class="phpOperator">.</span>location<span class="phpOperator">.</span>hash <span class="phpOperator">=</span> tmp<span class="phpText">;</span>
</pre>
<p>The Pagination class simply sets the hash value everytime you click the pagination controls, allowing the browser a history of what you have been doing in the application, then the Pagination class checks every half second or so to see whether you the user have done something in the browser that changes the hash value from the last one it has set in the URL. If the Pagination class determines the hash values are not the same it will use the new hash from the URL, which is essentially an Ajaxed URL, that will load the correct page.</p>
<p><strong>Browsing by URL</strong> The next cool thing is browsing by URL, on the demo page at the bottom there is a link that says, &#8216;Go To page 4&#8242; that link has no javascript attached to it, the link simply updates the URL which the pagination class will check and then browse to. You can also navigate straight to an ajaxed URL without going to page 1 of the paginator first, in essence you&#8217;re browsing by hard URL which will allow linking to it and favouriting of the link. </p>
<ul>
<li><a href="http://www.aplusdesign.com.au/misc/pagination/pagination.php#p=6" target="_blank">Goto page 6</a> &#8211; MooTools</li>
<li><a href="http://www.aplusdesign.com.au/misc/pagination/pagination_jquery.php#p=6" target="_blank">Goto page 6</a> &#8211; jQuery</li>
</ul>
<p>Why is that important in an Ajax application you ask, well lets say that you have an image gallery with 100 pictures in it, each page displays 10 pics and a user really likes the images on page 7. In 99% of Ajaxified pagination applications it would be impossible for that user to favourite page 7, or send a link to a friend, or link to it from his own web-page because your pagination will either in the worst case, force a user to click seven times to get to page seven, or require you to load page 1 of the results every time before they can click on page number 7 and have it load. Neither way allows you to save the URL in your browser, or link to it from another page, essentially making your very valuable image library somewhat un-navigatable. </p>
<p>We should always give users a valid URL to save and navigate to later! </p>
<h4>Usage</h4>
<pre class="php">
<span class="phpComment">/* Load the paginator with<span class="phpKeyword"> default </span>options */</span>
<span class="phpKeyword">
new </span>Paginator<span class="phpOperator">(</span><span class="phpString">'http<span class="phpOperator">:</span><span class="phpComment">//local<span class="phpOperator">.</span>dev<span class="phpOperator">.</span>com<span class="phpOperator">.</span>au/pagination/ajax<span class="phpOperator">.</span>php'</span><span class="phpOperator">)</span><span class="phpText">;</span>
</span>
<span class="phpComment">/* Load paginator, but change time between hash/url check to one second */</span>
<span class="phpKeyword">
new </span>Paginator<span class="phpOperator">(</span><span class="phpString">'http<span class="phpOperator">:</span><span class="phpComment">//local<span class="phpOperator">.</span>dev<span class="phpOperator">.</span>com<span class="phpOperator">.</span>au/pagination/ajax<span class="phpOperator">.</span>php'</span>, <span class="phpOperator">{</span>
</span>    <span class="phpString">'timer'</span> <span class="phpOperator">:</span> 1000
<span class="phpOperator">}</span><span class="phpOperator">)</span><span class="phpText">;</span>
</pre>
<h4>Options</h4>
<pre class="php">
<span class="phpComment">/* Default Options */</span>
<span class="phpOperator">{</span>
    xString <span class="phpOperator">=</span> <span class="phpOperator">{</span><span class="phpOperator">}</span>
    qString <span class="phpOperator">:</span> <span class="phpString">'<span class="phpOperator">?</span>p<span class="phpOperator">=</span>'</span>,
    items<span class="phpOperator">:</span>10,
    pagination<span class="phpOperator">:</span> <span class="phpString">'pagination_pager'</span>,
    container<span class="phpOperator">:</span>	<span class="phpString">'pagination_container'</span>,
    duration<span class="phpOperator">:</span> 800,
    timer<span class="phpOperator">:</span> 500
<span class="phpOperator">}</span>
</pre>
<p>Here is a quick idea of what each option is doing.</p>
<ul>
<li><strong>xParams </strong> &#8211; Allows extra params to be sent through the Ajax query</li>
<ul>
<li><strong>qString </strong> &#8211; The query section of your URL. By default it is &#8216;?p=3&#8242; . ie. Page number 3</li>
<li><strong>items </strong> &#8211; Items per page, defaults to 10</li>
<li><strong>pagination</strong> &#8211; The Id of the element that your pagination controls will be inserted into to</li>
<li><strong>container</strong> &#8211; The Id of the element that your pagination results will be inserted into to</li>
<li><strong>duration</strong> &#8211; Duration of the sliding animation, 800 = 8 tenths of a second</li>
<li><strong>timer</strong> &#8211; Time between checking for a new URL hash. Faster will make the application more responsive to changed hashes. I find 500 is a good number. ie. Half a second</li>
</ul>
<h4>Pagination on the server side</h4>
<p>You will need a PHP function to calculate your pagination, the one provided in &#8220;functions.php&#8221; is a simple 5 number step sliding pagination, very similar to Facebook&#8217;s and extremely useable and friendly. It is included in zip file download. I mention it because you can change it to any pagination function you would like, you don&#8217;t have to keep mine. You have all the necessary variables you need for a healthy pagination method including, max item count, page number, current page, items per page and the base path, so you can get totally creative with you pagination outputs. </p>
<h4>Download</h4>
<p><a class="demo" href="http://www.aplusdesign.com.au/misc/pagination/easyajaxpagination_mootools.zip" target="_blank">Easy Ajax Pagination:: MooTools</a><br />
<a class="demo" href="http://www.aplusdesign.com.au/misc/pagination/easyajaxpagination_jquery.zip" target="_blank">Easy Ajax Pagination:: jQuery</a></p>
<h4>Installing</h4>
<p><strong>Step 1.</strong> Change the URL in pagination.php or pagination_jquery.php</p>
<pre class="php">
<span class="phpKeyword">
new </span>Paginator<span class="phpOperator">(</span><span class="phpString">'http<span class="phpOperator">:</span><span class="phpComment">//local<span class="phpOperator">.</span>dev<span class="phpOperator">.</span>com<span class="phpOperator">.</span>au/pagination/ajax<span class="phpOperator">.</span>php'</span><span class="phpOperator">)</span><span class="phpText">;</span>
</span></pre>
<p><strong>Step 2.</strong> Upload it</p>
<p>Upload it to your server or testing environment. Then your done, now you just use ajax.php to get your result desired set, make it look how ever you&#8217;d like with whatever data you want and style up the application to suit your need.</p>
<p>I will be posting more on this code soon as I&#8217;m going to submit it as an jQuery &#038; MooTools plugin, so there will also be GitHub versions to check out and contribute to. </p>
<h4>Extending the parameter list</h4>
<p>A few people asked for ways to extend the parameters you send through the Ajax request, here is how I implemented it.</p>
<pre class="php">
<span class="phpKeyword">
var </span>pagination <span class="phpOperator">=</span><span class="phpKeyword"> new </span>Paginator<span class="phpOperator">(</span><span class="phpString">'http<span class="phpOperator">:</span><span class="phpComment">//local<span class="phpOperator">.</span>dev<span class="phpOperator">.</span>com<span class="phpOperator">.</span>au/pagination/ajax<span class="phpOperator">.</span>php'</span><span class="phpOperator">)</span><span class="phpText">;</span>
</span>
<span class="phpComment">// User event requiring extra data in Ajax request
</span>
pagination<span class="phpOperator">.</span>options<span class="phpOperator">.</span>xParams <span class="phpOperator">=</span> <span class="phpOperator">{</span> <span class="phpString">'someData'</span> <span class="phpOperator">:</span> <span class="phpString">'someValue'</span> <span class="phpOperator">}</span>
</pre>
<p>All new requests are now sending this parameter along with the pagination details. Any further changes to xParams just keeps merging the objects together to form your request.</p>
<p>Note: Edit your &#8216;pagination.php&#8217; file to capture and use the extra params.</p>
<p>Enjoy!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/ajax-pagination-back-button/feed/</wfw:commentRss>
		<slash:comments>17</slash:comments>
		</item>
		<item>
		<title>JavaScript Optimisation Techniques</title>
		<link>http://www.aplusdesign.com.au/blog/javascript-optimisation/</link>
		<comments>http://www.aplusdesign.com.au/blog/javascript-optimisation/#comments</comments>
		<pubDate>Thu, 01 Apr 2010 10:40:03 +0000</pubDate>
		<dc:creator>Simon</dc:creator>
				<category><![CDATA[Javascript]]></category>
		<category><![CDATA[Optimisation]]></category>

		<guid isPermaLink="false">http://www.aplusdesign.com.au/blog/?p=84</guid>
		<description><![CDATA[Speed up JavaScript by making it execute exceedingly fast with these Google certified techniques Ok everyone&#8217;s good friend David Walsh over at davidwalsh.name posted a link to a Google Talks presentation &#8211; Javascript and speed from back in 2009 in which they discuss some simple yet amazingly important JavaScript optimisation techniques. Ranging from Dom interaction [...]]]></description>
			<content:encoded><![CDATA[<p><strong>Speed up JavaScript by making it execute exceedingly fast with these Google certified techniques</strong></p>
<p>Ok everyone&#8217;s good friend David Walsh over at <a rel="nofollow" href="http://davidwalsh.name/" target="_blank">davidwalsh.name</a> posted a link to a  <a href="http://davidwalsh.name/javascript-speed" target="_blank">Google Talks presentation &#8211; Javascript and speed</a> from back in 2009 in which they discuss some simple yet amazingly important JavaScript optimisation techniques. Ranging from Dom interaction and Scope , all the way through to Reflow. Now if your not sure what Reflow is I will explain that below, but put simple it is the name given when the browser has to redraw the page because user interaction or JavaScript has changed its geometry.</p>
<p>So here is what I&#8217;m going to cover in this post for you optimisation fanatics, with code examples of the good, the bad and the ugly!</p>
<ul>
<li>Scope Management</li>
<li>Data Access</li>
<li>Loops</li>
<li>The DOM</li>
</ul>
<p><span id="more-84"></span></p>
<h4>Scope Management</h4>
<p>As JavaScript developers we should all have a decent handle on what scope is, but managing the scope within our apps and functions is a little trickier. There is no real best practice solution for how to pass around variables, literals, arrays and properties in the language, and many developers will live by, &#8220;if it works, it works&#8221;. Well sure, but if your users perceive your web-site to be slow because of that attitude, you lose out big time. So here are a few key concepts when it comes to scope management to improve performance.</p>
<p><strong>Key points</strong></p>
<ul>
<li>The further into the scope chain, the longer it will take to resolve identifiers</li>
<li>Local variables = fast!</li>
</ul>
<p><strong>1. The further into the scope chain, the longer it will take</strong></p>
<p>When your functions are executed what is called an <strong>execution context</strong> is created, this execution context is intialised with a scope collection, the collection contains that functions scope members. Examples of this would be your function now has references to window and document.</p>
<p>Now if that seemed a little complicated, here are some simple slides to illustrate.</p>
<h4>Scope chain for a typical function</h4>
<p><a href="http://davidwalsh.name/javascript-speed" target="_blank" rel="nofollow"><img class="alignnone size-full wp-image-88" title="scope-execution-context-1" src="http://www.aplusdesign.com.au/blog/wp-content/uploads/2010/03/scope-execution-context-1.jpg" alt="scope context with local variables" width="469" height="346" /></a></p>
<p>Next the function will create what is called an <strong>activation object</strong>, which contains all your local variables and pushes them to the front of your context&#8217;s scope chain.</p>
<h4>Scope chain for a function after activation object</h4>
<p><a href="http://davidwalsh.name/javascript-speed" target="_blank" rel="nofollow"><img class="alignnone size-full wp-image-87" title="scope-execution-context-2" src="http://www.aplusdesign.com.au/blog/wp-content/uploads/2010/03/scope-execution-context-2.jpg" alt="scope context global" width="469" height="346" /></a></p>
<p>So when the function is executed and it comes across a variable a process called Identifier resolution starts. It will always starts by looking in the first spot in the scope chain, and will make its way down the scope chain until that variable is found.</p>
<p>So quite simply, if you find your variable in position 0. Excellent, that is the best possible outcome and the fastest.</p>
<p>Anything beyond position 0 requires extra processing and time to find, and every step you go down the scope chains adds to how long it takes. So the further down the scope chain the bigger the hit to your performance. Hence why we try not to use Global variables, because they will always be in the last spot of the scope chain.</p>
<p><strong>2. Local Variables = fast!</strong></p>
<p>Local variables are extremely fast because they require only one step in the scope chain to find. Simple as that, and below are two pieces of code to demonstrate local variable importance.</p>
<h5>A typical function</h5>
<pre class="php">
<span class="phpComment">// slow
</span><span class="phpFunctionKeyword">function</span> <span class="phpOperator">(</span>items<span class="phpOperator">)</span> <span class="phpOperator">{</span>
<span class="phpKeyword">	var </span>divs 	<span class="phpOperator">=</span> document.getElementsByTagName<span class="phpOperator">(</span><span class="phpString">"div"</span><span class="phpOperator">)</span><span class="phpText">;</span>
<span class="phpKeyword">	var </span>images 	<span class="phpOperator">=</span> document.getElementsByTagName<span class="phpOperator">(</span><span class="phpString">"img"</span><span class="phpOperator">)</span><span class="phpText">;</span>
<span class="phpKeyword">	var </span>button 	<span class="phpOperator">=</span> document.getElementById<span class="phpOperator">(</span><span class="phpString">"save-btn"</span><span class="phpOperator">)</span><span class="phpText">;</span>
<span class="phpKeyword">	for </span><span class="phpKeyword"><span class="phpOperator">(</span>var </span>i<span class="phpOperator">=</span>0; i <span class="phpOperator">&lt;</span> items<span class="phpOperator">.</span>length<span class="phpText">;</span> i<span class="phpOperator"><span class="phpOperator">+</span><span class="phpOperator">+</span></span><span class="phpOperator">)</span> <span class="phpOperator">{</span>
		process<span class="phpOperator">(</span>items<span class="phpOperator">[</span>i<span class="phpOperator">]</span>, divs<span class="phpOperator">[</span>i<span class="phpOperator">]</span>, images<span class="phpOperator">[</span>i<span class="phpOperator">]</span><span class="phpOperator">)</span><span class="phpText">;</span>
	<span class="phpOperator">}</span>
<span class="phpOperator">}</span>
</pre>
<h5>Same function but faster</h5>
<pre class="php">
<span class="phpComment">// fast
</span><span class="phpFunctionKeyword">function</span> <span class="phpOperator">(</span>items<span class="phpOperator">)</span> <span class="phpOperator">{</span>
<span class="phpKeyword">	var </span>doc <span class="phpOperator">=</span> document;
<span class="phpKeyword">	var </span>divs 	<span class="phpOperator">=</span> doc<span class="phpOperator">.</span>getElementsByTagName<span class="phpOperator">(</span><span class="phpString">"div"</span><span class="phpOperator">)</span><span class="phpText">;</span>
<span class="phpKeyword">	var </span>images 	<span class="phpOperator">=</span> doc<span class="phpOperator">.</span>getElementsByTagName<span class="phpOperator">(</span><span class="phpString">"img"</span><span class="phpOperator">)</span><span class="phpText">;</span>
<span class="phpKeyword">	var </span>button 	<span class="phpOperator">=</span> doc<span class="phpOperator">.</span>getElementById<span class="phpOperator">(</span><span class="phpString">"save-btn"</span><span class="phpOperator">)</span><span class="phpText">;</span>
<span class="phpKeyword">	for </span><span class="phpKeyword"><span class="phpOperator">(</span>var </span>i<span class="phpOperator">=</span>0; i <span class="phpOperator">&lt;</span> items<span class="phpOperator">.</span>length<span class="phpText">;</span> i<span class="phpOperator"><span class="phpOperator">+</span><span class="phpOperator">+</span></span><span class="phpOperator">)</span> <span class="phpOperator">{</span>
		process<span class="phpOperator">(</span>items<span class="phpOperator">[</span>i<span class="phpOperator">]</span>, divs<span class="phpOperator">[</span>i<span class="phpOperator">]</span>, images<span class="phpOperator">[</span>i<span class="phpOperator">]</span><span class="phpOperator">)</span><span class="phpText">;</span>
	<span class="phpOperator">}</span>
<span class="phpOperator">}</span>
</pre>
<p>You will see a big difference when writing functions like this because instead of three global lookups, you now have one!</p>
]]></content:encoded>
			<wfw:commentRss>http://www.aplusdesign.com.au/blog/javascript-optimisation/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>
