<?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>Dark Crimson Blog &#187; AJAX</title>
	<atom:link href="http://blog.darkcrimson.com/tag/ajax/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.darkcrimson.com</link>
	<description>The Blog of Ben Lister</description>
	<lastBuildDate>Fri, 13 Aug 2010 02:18:06 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.8.6</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>Set a Dynamic Width / Height on Fancybox</title>
		<link>http://blog.darkcrimson.com/2010/03/set-a-dynamic-width-height-on-fancybox/</link>
		<comments>http://blog.darkcrimson.com/2010/03/set-a-dynamic-width-height-on-fancybox/#comments</comments>
		<pubDate>Wed, 10 Mar 2010 02:55:56 +0000</pubDate>
		<dc:creator>Ben Lister</dc:creator>
				<category><![CDATA[jQuery]]></category>
		<category><![CDATA[AJAX]]></category>
		<category><![CDATA[Fancybox]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Tutorial]]></category>

		<guid isPermaLink="false">http://blog.darkcrimson.com/?p=182</guid>
		<description><![CDATA[Fancybox is a powerful, lightweight jQuery based lightbox script that offers developers an impressive variety of content display options. I&#8217;ve used this script many times in the past (including my portfolio) and have never run into any  limitations in terms of functionality until a recent project required many lightboxes with varying sizes. Since the site [...]]]></description>
			<content:encoded><![CDATA[<p><a href="http://fancybox.net/">Fancybox</a> is a powerful, lightweight jQuery based lightbox script that offers developers an impressive variety of content display options. I&#8217;ve used this script many times in the past (including <a href="http://darkcrimson.com/portfolio" target="_blank">my portfolio</a>) and have never run into any  limitations in terms of functionality until a recent project required many lightboxes with varying sizes. <span id="more-182"></span>Since the site used Fancybox&#8217;s <code>iframe</code> functionality to display articles with custom-sized graphics and Fancybox&#8217;s API does not offer a dynamic size option I created a simple DOM based jQuery solution:</p>
<pre name="code" class="javascript">
    $('a.fb_dynamic').each(function(){
           var dWidth 	= parseInt($(this).attr('href').match(/width=[0-9]+/i)[0].replace('width=',''));
           var dHeight 	=  parseInt($(this).attr('href').match(/height=[0-9]+/i)[0].replace('height=',''));
			$(this).fancybox({
				'width':dWidth,
				'height':dHeight,
				'autoScale'     	: false,
				'transitionIn'		: 'elastic',
				'transitionOut'		: 'elastic',
				'type'			: 'iframe'
			});
      });
</pre>
<p>With this code in place Fancybox can be called by simply adding the class <code>fb_dynamic</code> and then specifying the width and height in the URL&#8217;s parameters:</p>
<pre name="code" class="html">
<a class="fb_dynamic" href="http://darkcrimson.com/?width=400&#038;height=300">Free iPods!!!!</a>
</pre>
<p><strong>Going one step further</strong>, if you need to make the Fancybox call from Flash (another feature not in the API) you can create a simple JavaScript function and make the call from your <code>SWF</code> or <code>AS</code> file:</p>
<pre name="code" class="javascript">
	/**************************************************************
	Call Fancybox from Flash with a Dynamic width and Height
		@w = integer [width]
     @h = integer [height]
     @u = string [url]
      example funtion call: flashFancybox(500,600,'http://darkcrimson.com')
	***************************************************************/
			function flashFancybox(w,h,u) {
			    var fbflash = $('a#fbflash');
                                fbflash.attr('href', u+ '?width=' + w + '&#038;height=' + h );
				fbflash.trigger('click');
			}
          $(function () {
              // Create dynamic link, change append location to change FB animation start point
	      $('#body').append(' <a href="javascript:void(0)" id="fbflash" class="fb_dynamic">&nbsp;</a>');
          });
</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.darkcrimson.com/2010/03/set-a-dynamic-width-height-on-fancybox/feed/</wfw:commentRss>
		<slash:comments>15</slash:comments>
		</item>
		<item>
		<title>jQuery XML Parser with Sorting and Filtering</title>
		<link>http://blog.darkcrimson.com/2010/01/jquery-xml-parser/</link>
		<comments>http://blog.darkcrimson.com/2010/01/jquery-xml-parser/#comments</comments>
		<pubDate>Mon, 11 Jan 2010 06:45:11 +0000</pubDate>
		<dc:creator>Ben Lister</dc:creator>
				<category><![CDATA[jQuery]]></category>
		<category><![CDATA[AJAX]]></category>
		<category><![CDATA[JavaScript]]></category>
		<category><![CDATA[Tutorial]]></category>
		<category><![CDATA[XML]]></category>

		<guid isPermaLink="false">http://blog.darkcrimson.com/?p=115</guid>
		<description><![CDATA[In early 2009, I experimented with XML based iPhone / Safari Mobile web app which used jQuery to parse and traverse multiple levels of nodes in an XML file and display the data. While that project never panned out, the core code has become quite useful in a number of professional and personal projects. This [...]]]></description>
			<content:encoded><![CDATA[<p>In early 2009, I <a title="(example was built *specifically* for Safari mobile)" href="http://darkcrimson.com/lab/itunes" target="_blank">experimented with XML based iPhone / Safari Mobile web app</a> which used jQuery to parse and traverse multiple levels of nodes in an XML file and display the data. While that project never panned out, the core code has become quite useful in a number of professional and personal projects. This tutorial provides working examples and demonstrates the concept of parsing and traversing an XML file with jQuery using AJAX.<span id="more-115"></span></p>
<div style="text-align:center;margin: 20px auto;width:75%;padding:8px; background:#4F0000"><strong>UPDATE 4/25/10</strong><br />Moved the XML data append outside of the loop to increase performance</div>
<p><a class="view_demo ext" href="http://blog.darkcrimson.com/samples/jquery-xml-parser">View Demo</a><a class="view_source" href="http://blog.darkcrimson.com/samples/jquery-xml-parser/jq_xml_parser.zip">Download Source</a><br />
<br class="clearall "/></p>
<h3 class="blog_ttl">The XML</h3>
<p>First, lets take a look at the XML structure:</p>
<pre name="code" class="javascript">
<?xml version="1.0" encoding="UTF-8"?>
<data>
	<entry date="1/08/10" cost="27" category="Mobile Phone Accessories">
		<name>
			<![CDATA[ iPhone Case]]&gt;
		</name>
		<description>
			<![CDATA[ Black Matte Finish, fits all 3G and 3Gs models. ]]&gt;
		</description>
	</entry>

</data>
</pre>
<p>In it&#8217;s most basic form, the XML file contains the main <code>&lt;data&gt;</code> node with subsequent <code>&lt;entry&gt;</code> nodes. Within each entry we are defining the meta data such as <code>&lt;date&gt;</code>, <code>&lt;cost&gt;</code> and <code>&lt;category&gt;</code>. Also within the entry are a <code>&lt;name&gt;</code> and <code>&lt;description&gt;</code> field which are wrapped in <a href="http://en.wikipedia.org/wiki/CDATA" target="_blank">CDATA</a> blocks that will allow us to use special characters and punctuation without compromising the validity of the XML file.</p>
<h3 class="blog_ttl">AJAX</h3>
<p>Using jQuery&#8217;s wonderfully simple AJAX method to make an <code>XMLHttpRequest</code>. The basic code for making the AJAX request for the example XML file shown below:</p>
<pre name="code" class="javascript">
$.ajax({
type: 'GET',
url: 'xml/data.xml',
dataType: 'xml',
success: function(xml_list) {</code>

var xmlArr = [];

$(xml_list).find('entry').each(function() {

	var xml_date      	= $(this).attr('date');
	var xml_cost 	  	= $(this).attr('cost');
	var xml_category  	= $(this).attr('category');

	var xml_name  	  	= $(this).find('name').text();
	var xml_description = $(this).find('description').text();
					  // Add matched items to an array
	xmlArr += '&lt;tr filterCriteria="';
	xmlArr += xml_cost;
	xmlArr += '"&gt;&lt;td&gt;';
	xmlArr += xml_date;
	xmlArr += '&lt;/td&gt;&lt;td class="xml_name"&gt;';
	xmlArr += xml_name;
	xmlArr += '&lt;/td&gt;&lt;td&gt;';
	xmlArr += xml_description;
	xmlArr += '&lt;/td&gt;&lt;td&gt;';
	xmlArr += xml_category;
	xmlArr += '&lt;/td&gt;&lt;td class="xml_cost"&gt;$';
	xmlArr += xml_cost;
	xmlArr += '&lt;/td&gt;&lt;/tr&gt;';

}); // end each loop

 //Append array to table (this way is much faster than doing this individually for each item)

	$(xmlArr).appendTo(wrapper +' table tbody');
</pre>
<p>The first two things to note in the code are the <code>dataType</code> and <code>success</code> parameters. We use <code>dataType</code> to specify that we are requesting an XML fie and using a function in <code>success</code> to manipulate and display the XML data. Next, we use jQuery&#8217;s super handy <code>find()</code> method to search the XML document for entry nodes. We then chain the <code>each()</code> function to iterate through the data that is returned from the <code>find()</code>. Next, variables are created for each of the items we will be displaying. Using variables as opposed to the selector name caches the data so that it is not called in each iteration. Note that there are two methods of assigning the variables in this example; the first simply assigns available attributes to the variables while the second has to traverse one step deeper to return the values of the name and description nodes.</p>
<h3 class="blog_ttl">Making it work</h3>
<p>At this point we&#8217;ve covered the basic concepts but it is time to actually do something practical with the data. Displaying the results in HTML is easy but while we&#8217;re writing the markup, lets add some placeholders for filtering the data.</p>
<pre name="code" class="javascript">
<div id="xml_wrapper">
<ul id="xml_nav">
<li><a class="filter_10" href="javascript:void(0)"><span>&lt; $10</span></a></li>
<li><a class="filter_10_20" href="javascript:void(0)"><span>$10 – $20</span></a></li>
<li><a class="filter_20" href="javascript:void(0)"><span>$20 +</span></a></li>
<li class="xml_nav_hit"><a class="filter_0 hit" href="javascript:void(0)"><span>Any price</span></a></li>
</ul>
<table border="0">
<thead>
<tr>
<th class="header headerSortUp">Date</th>
<th class="header">Name</th>
<th class="header">Description</th>
<th class="header">Category</th>
<th class="header">$</th>
</tr>
</thead>
<tbody></tbody>
</table>
</div>
</pre>
<p>Ignore the <code>&lt;UL&gt;</code> for now and notice that we are adding elements to the the <code>&lt;thead&gt;</code> but not the <code>&lt;tbody&gt;</code>. Jump back to the JavaScript file and add this line below the var declaration for <code>description</code> and add:</p>
<pre name="code" class="javascript">
$('&lt;tr filterCriteria= "'+ xml_cost +'"&gt;&lt;/tr&gt;')
.html('
<td>'+ xml_date  +'</td>
<td class="xml_name">'+ xml_name  +'</td>
<td>'+ xml_description  +'</td>
<td>'+ xml_category +'</td>
<td class="xml_cost">$'+ xml_cost  +'</td>

')
.appendTo(wrapper +' table tbody');
</pre>
<p>This line is in our loop so it will iterate a populated <code>&lt;tr&gt;</code> for each <code>entry</code> in our XML and append it to the <code>&lt;tbody&gt;&lt;/tbody&gt;</code> of the table.</p>
<h3 class="blog_ttl">Making it useful</h3>
<p>The parser is now built and displays the data from our XML file but it lacks practicality. What if you want to sort by Computer Accessories? What if you want to show all items less than $20?  These start to become serious issues as the length of the XML document increases.</p>
<p>We will cheat a little bit and tie in Christian Bach&#8217;s incredibly useful <a href="http://tablesorter.com/docs/" target="_blank">tablesorter jQuery plugin</a> to do the sorting in this example. I won&#8217;t go into detail on the options and uses of this plugin because they are already covered thoroughly on the <a href="http://tablesorter.com/docs/#Configuration" target="_blank">tablesorter plugin site</a>.</p>
<p>Filtering is done by simply using jQuery&#8217;s <code>hide()</code> and <code>show()</code> on specifically tagged table rows. We&#8217;ve already created the HTML in previous steps so all that is left is to assign a <code>onClick</code> event and add a switch to create the filter. To add sorting to the table we&#8217;ve created add the following after the <code>each()</code> function inside the AJAX call:</p>
<pre name="code" class="javascript"> window.setTimeout('$("'+ wrapper +' table").tablesorter({sortList:[[0,0],[0,0]], widgets: [\'zebra\']});', 120);</pre>
<p>The selector is wrapped in an interval because both the tablesorter script call and our AJAX call happen concurrently on page load which causes the tablesorter to fire before the table is fully populated with or XML. The 120ms on the interval is somewhat arbitrary and it can be changed as needed. Additionally, if you prefer not to use the interval, you might be able to do so depending on your particular use and XML file size. Also, note the use of the &#8220;zebra widget&#8221; option; this will assign a &#8220;stripe&#8221; class to odd numbered rows which allows for alternate row background colors. </p>
<pre name="code" class="javascript">var nav_link = $('#xml_nav li a');
nav_link.click( function() {
var tr = wrapper +' table tbody tr';
$(tr).show(); //Show all rows
switch ($(this).attr("class")) {
case  "filter_10 hit" :
$(tr).filter(function (index) {
return parseFloat($(this).attr('filterCriteria')) &gt; 10;
}).hide();
break;

case  "filter_10_20 hit" :
$(tr).filter(function (index) {
return parseFloat($(this).attr('filterCriteria')) &lt; 10 || parseFloat($(this).attr("filterCriteria")) &gt; 20  ;
}).hide();
break;

case  "filter_20 hit" :
$(tr).filter(function (index) {
return parseFloat($(this).attr('filterCriteria')) &lt; 20;
}).hide();

break;

case  "filter_0 hit" :
$(tr).show();
break;

}
/* Remove all instances of the stripe (alternating row) class
   Then re-apply stripe class as to visible alternating rows
*/
$(tr).removeClass('stripe');
$(tr + ':visible:odd').addClass('stripe');
});
</pre>
<p>In a previous step we generated the HTML that is inserted into our table and you might have noticed an attribute was added to the <code>cost</code> <code>&lt;td&gt;</code> called <code>filterCriteria</code>. The code above uses the value of this attribute to determine which items to show / hide. Obviously, this will only work if the value of cost is an integer. Feel free to develop a more elegant solution.</p>
<h3 class="blog_ttl">Finishing up</h3>
<p>The last step that I will cover is adding a simple preloader to display as AJAX grabs the XML data. At the top of the function place the following line:</p>
<pre name="code" class="javascript">
     $('
<div id="preload_xml"></div>

').html('<img src="images/ajax-loader.gif" alt="loading data" />
<h3>Loading Data...</h3>

').prependTo($('body'));
</pre>
<p>Inside of the <code>xml_parser()</code> function in the AJAX call&#8217;s <code>success</code> parameter place these two lines:</p>
<pre name="code" class="javascript">
$('#preload_xml').remove();
$(wrapper).show();</pre>
<p>Thes four lines of code will first hide our wrapper div and then dynamically construct a div with a loading message and then remove the code from the page once everything is loaded and finally show the wrapper again.</p>
<p>We now have a parser that sorts and filters XML data. There are many other features that could be added such as a more complex content filter and code cleanup to make things even more re-usable. If you find this code useful and decide to use it in your projects, I encourage you to modify the code as you find necessary and please feel free to share your examples.</p>
<h3 class="blog_ttl">Other Considerations</h3>
<p>There is a great jQuery XML parser plugin called <a title="jParse" href="http://jparse.kylerush.net/demo" target="_blank">jParse</a> which can be used to grab display the contents of an XML file with little effort. Other than the reliance on AJAX to call the XML file, the approach used by jParse differs considerably from the approach that I took in this article. If you are looking strictly for XML display, I recommend looking into jParse.</p>
<p><a class="view_demo ext" href="http://blog.darkcrimson.com/samples/jquery-xml-parser">View Demo</a><a class="view_source" href="http://blog.darkcrimson.com/samples/jquery-xml-parser/jq_xml_parser.zip">Download Source</a><br />
<br class="clearall "/></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.darkcrimson.com/2010/01/jquery-xml-parser/feed/</wfw:commentRss>
		<slash:comments>26</slash:comments>
		</item>
	</channel>
</rss>

