<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss' xmlns:gd='http://schemas.google.com/g/2005' xmlns:thr='http://purl.org/syndication/thread/1.0'><id>tag:blogger.com,1999:blog-31737895</id><updated>2012-01-08T23:07:34.418-08:00</updated><category term='scala'/><category term='reserved words'/><category term='javascript'/><category term='sql'/><category term='java'/><category term='jQuery closures javascript'/><category term='actors'/><title type='text'>A Simpler World</title><subtitle type='html'></subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://fjanon.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default?max-results=100'/><link rel='alternate' type='text/html' href='http://fjanon.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><author><name>Fred Janon</name><uri>http://www.blogger.com/profile/03149683223012183765</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>6</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>100</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-31737895.post-8637497171428286108</id><published>2012-01-08T23:07:00.000-08:00</published><updated>2012-01-08T23:07:34.451-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='jQuery closures javascript'/><title type='text'>Caching jQuery objects in callbacks</title><content type='html'>In my code I try to avoid re-computing things when they don't need to be. One thing that John Resig mentions in his blog is that we should avoid re-computing jQuery objects with selector over and over for performance reasons. He talks about Twitter's experience.&lt;br /&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;I was browsing through John Resig's blog when I saw his "Learning Advanced Javascript" interactive slides here:&amp;nbsp;&lt;a href="http://ejohn.org/apps/learn/"&gt;http://ejohn.org/apps/learn/&lt;/a&gt;&amp;nbsp;. #21 caught my eye, since I have been trying to improve my code when I write callbacks in jQuery:&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;function isPrime( num ) {&amp;nbsp;&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;&amp;nbsp; ...&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;&amp;nbsp; isPrime.cache[ num ] = prime&amp;nbsp;&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;&amp;nbsp; ...&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;&amp;nbsp; }&lt;/span&gt;&lt;/div&gt;&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;The important part here is that functions can have properties.&amp;nbsp;The issue is that we often need to access DOM elements or jQuery objects from inside the callback function, but we really should not re-calculate, i.e $('.someelements')), the jQuery&amp;nbsp;objects&amp;nbsp;every time the event callback is called. I also want to write the code as a one-liner if I can. I used to write:&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;var inp = $('#input');&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;var out = $('#output');&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;&lt;br /&gt;&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;$('#copyname').click( function(e) { out.val(inp.val()); } )&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;but then the variables would pollute the namespace and make the code more verbose.&amp;nbsp;Until recently I was using the jQuery 'data' property to *cache* the $() call:&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;$('#copyname').click( {src: $('#inputname')}, function(e) { $('#outputname').val(e.data.src.val()); } );&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;$('#inputname') is computed only once, but&amp;nbsp;$('#outputname') is still computed every time the callback is called. Also the 'e.data.src' construct assumes a knowledge of jQuery.&amp;nbsp;Granted, I could use an object &amp;nbsp;in 'src' with both jQuery objects. But instead, let's use a closure:&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;$('#copyname1').click(&lt;/span&gt;&lt;br /&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;&amp;nbsp; &amp;nbsp; (function x() { var i = $('#inputname1'); var o = $('#outputname1'); return function(e) { o.val(i.val()); }; })() );&lt;/span&gt;&lt;br /&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;It's easy to read and short, doesn't pollute the namespace.&amp;nbsp;We can also use John's caching technique like this:&lt;/div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;$('#copyname').click(&lt;/span&gt;&lt;/div&gt;&lt;div&gt;&lt;span class="Apple-style-span" style="background-color: #eeeeee;"&gt;&amp;nbsp; &amp;nbsp; (function x() { x.i = $('#inputname'); x.o = $('#outputname'); return function(e) { x.o.val(x.i.val()); }; })() );&lt;/span&gt;&lt;/div&gt;&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;Here function x is called before the jQuery click function is called. it returns the anonymous callback 'function(e)'. That callback function will be passed the 'e' event object when called by jQuery when the use clicks on the button. The cool thing is that the callback function has access to 'x.i' and 'x.o', created in a closure inside the function x. No need for jQuery repeated calls or data property. The namespace is free of x or any temporary variable.&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div&gt;I just hope that the function x is garbage collected when the click handler is unbound... Any idea how to check that?&amp;nbsp;Is it a good application of closures and function properties?&lt;/div&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31737895-8637497171428286108?l=fjanon.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://fjanon.blogspot.com/feeds/8637497171428286108/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31737895&amp;postID=8637497171428286108' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/8637497171428286108'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/8637497171428286108'/><link rel='alternate' type='text/html' href='http://fjanon.blogspot.com/2012/01/caching-jquery-objects-in-callbacks.html' title='Caching jQuery objects in callbacks'/><author><name>Fred Janon</name><uri>http://www.blogger.com/profile/03149683223012183765</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31737895.post-7106214881734668662</id><published>2011-03-18T20:42:00.000-07:00</published><updated>2011-03-18T20:42:47.147-07:00</updated><title type='text'>High order loop function in Javascript</title><content type='html'>Writing Javascript code after Groovy code makes you wish you could extend the language. So I tried to write a Javascript function to rewrite the 'for' loop in a different way, passing the loop parameters and a function to my new 'loop' function. Here are a few ways of doing it, the difference is how the 'for' parameters are passed to the 'loop' function. I wish this was integrated in jQuery, that would make some code more fluid than a 'for' loop in the middle of jQuery code. The next step could be to add the little bit of code to make it a jQuery extension.&lt;br /&gt;&lt;br /&gt;OBJECTIVE:&lt;br /&gt;I want to replace a *normal* for loop like this:&lt;br /&gt;&lt;br /&gt;var res = []; // array to hold all the results of the fn(args) calls&lt;br /&gt;for (var i = 0 ; i &amp;lt; max ; i + step) res.push(fn(args)); // loop and call the fn(args) function, collecting the results in the res array&lt;br /&gt;&lt;br /&gt;by something a bit less verbose like that:&lt;br /&gt;&lt;br /&gt;var res = loop(0, max, step, fn, args);&lt;br /&gt;&lt;br /&gt;First try:&lt;br /&gt;&lt;br /&gt;Passing the parameters in an array [start, end, increment] and the function to call as the second argument. The argument for the function is not there, because I worked out a second form that I like better before including the argument for the function.&lt;br /&gt;&lt;br /&gt;Params:&lt;br /&gt;p : number or array&lt;br /&gt;&lt;br /&gt;- if number: end index value. The start index is set to 0 and the increment to 1.&lt;br /&gt;- if array of numbers:&lt;br /&gt;p[0] = loop index start&lt;br /&gt;p[1] = loop index end + 1&lt;br /&gt;p[2] = loop index increment&lt;br /&gt;&lt;br /&gt;fn: function to apply in the loop. The function receives the loop index as its argument&lt;br /&gt;&lt;br /&gt;Result:&lt;br /&gt;Array of results returned by the function&lt;br /&gt;&lt;br /&gt;Loop function definition:&lt;br /&gt;&lt;br /&gt;function loop(p, fn)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; var ar = [];&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; for (var k = (p[0] || 0) ; k &amp;lt; (p[1] || p) ; k += (p[2] || 1))&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; var r = fn(k);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; if (r !== undefined) ar.push(r);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;}&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; return ar; // return an array of the function results&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;}&lt;br /&gt;&lt;br /&gt;Examples:&lt;br /&gt;&lt;br /&gt;var fn1 = function(index)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; alert("fn1 index: " + index);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; return (index);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;}&lt;br /&gt;&lt;br /&gt;var res = loop(4, fn1);&lt;br /&gt;alert("fn1 result: " + res); // [0,1,2,3]&lt;br /&gt;&lt;br /&gt;res = loop([1, 10, 2], fn1);&lt;br /&gt;alert("fn1 result: " + res); // [1,3,5,7,9]&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;Second try: to avoid the array for the loop parameters, the loop function can be written like the following. Parameters for the function have been added as well.&lt;br /&gt;&lt;br /&gt;function nloop(_s, _e, _i, _f, _c, _a0, _a1, _a2)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; // _a0, _a1, _a2 are the argument to pass to the function, on top of the index. Optional&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; // Default if all arguments are specified&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; // call arguments: (start, end, step, function [,context [arg0 [, arg1 [, arg2]]]]).&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; var c; // function context: 'this' for the function. Optional&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; var f; // function to call, required&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; var i; // &amp;nbsp;step, loop increment. Optional&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; var e; // loop end. Optional&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; var s; // loop count or loop start if _e is defined. Required&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; var ar = []; // result, array of results from the function _f calls&lt;br /&gt;&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; if (_f instanceof Function)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; c = _c;&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; f = _f; // function to call&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; i = _i; // &amp;nbsp;step&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; e = _e; // end&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; s = _s; // loop count or loop start if _e is defined. Required&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;}&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; // call arguments: (start, end, function, context). Default step = 1.&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; else if (_i instanceof Function)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; c = _f;&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; f = _i; // function to call&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; i = 1; // &amp;nbsp;step&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; e = _e; // end&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; s = _s; // loop count or loop start if _e is defined. Required&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;}&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; else if (_e instanceof Function)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; c = _i;&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; f = _e; // function to call&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; i = 1; // &amp;nbsp;step&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; e = _s; // end&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; s = 0; // loop count or loop start if _e is defined. Required&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;}&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; else return ar;&lt;br /&gt;//&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; alert('start: ' + s + ' end: ' + e + ' step: ' + s);&lt;br /&gt;//&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; var undef; // to test if the function result is undefined&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; for (var k = s ; k &amp;lt; e ; k += i)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; var r = f.call(c, k, _a0, _a1, _a2);&lt;br /&gt;//&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; if (!(r === undef)) // looks like it's working in FF and IE6. Is it a proper way to test for undefined?&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt; if (typeof(r) !== 'undefined') // would it be a bit slow to test for a string?&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;   &lt;/span&gt;{&lt;br /&gt;//&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;   &lt;/span&gt; alert('f result: ' + r);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;   &lt;/span&gt; ar.push(r);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;   &lt;/span&gt;}&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt;  &lt;/span&gt;}&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; return ar;&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;}&lt;br /&gt;&lt;br /&gt;Examples of calls:&lt;br /&gt;&lt;br /&gt;var fn2 = function(index, a, b, c)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; // check the parameters and the context&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; alert("fn2 index: " + index + ' a: ' + a + ' b: ' + b + ' c: ' + c + ' this.name: ' + this.name);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; return (index);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;}&lt;br /&gt;&lt;br /&gt;// An object to pass as the context (aka 'this') for the function called in the loop&lt;br /&gt;var anobject = { name: 'an Object' };&lt;br /&gt;&lt;br /&gt;// loop from 1 to 10 step 2, calling fn2 with 'anobject' as 'this' and with 'a', 'b' and 'c' as parameters to fn2&lt;br /&gt;res = nloop(1, 10, 2, fn2, anobject, 'a', 'b', 'c');&lt;br /&gt;alert('nloop fn2 result: ' + res);&lt;br /&gt;&lt;br /&gt;res = nloop(1, 3, 1, fn2, anobject, 'a', 'b', 'c');&lt;br /&gt;alert('nloop fn2 result: ' + res);&lt;br /&gt;&lt;br /&gt;// function parameters are optional&lt;br /&gt;res = nloop(1, 10, 2, fn2, anobject);&lt;br /&gt;alert('nloop fn2 result: ' + res);&lt;br /&gt;&lt;br /&gt;// step optional&lt;br /&gt;res = nloop(1, 5, fn2, anobject);&lt;br /&gt;alert('nloop fn2 result: ' + res);&lt;br /&gt;&lt;br /&gt;// start index optional, 4 is the end index + 1&lt;br /&gt;res = nloop(4, fn2, anobject);&lt;br /&gt;alert('nloop fn2 result: ' + res);&lt;br /&gt;&lt;br /&gt;var fn3 = function(index)&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;{&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; alert('fn2 index: ' + index);&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt; return index;&lt;br /&gt;&lt;span class="Apple-tab-span" style="white-space: pre;"&gt; &lt;/span&gt;}&lt;br /&gt;res = nloop(1, fn3, anobject);&lt;br /&gt;alert('nloop fn3 void result: ' + res + ' res == []: ' + (res == []) + ' res == null: ' + (res == null) + ' res.length: ' + res.length);&lt;br /&gt;&lt;br /&gt;&lt;div&gt;&lt;br /&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31737895-7106214881734668662?l=fjanon.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://fjanon.blogspot.com/feeds/7106214881734668662/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31737895&amp;postID=7106214881734668662' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/7106214881734668662'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/7106214881734668662'/><link rel='alternate' type='text/html' href='http://fjanon.blogspot.com/2011/03/high-order-loop-function-in-javascript.html' title='High order loop function in Javascript'/><author><name>Fred Janon</name><uri>http://www.blogger.com/profile/03149683223012183765</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31737895.post-2675684230095998543</id><published>2010-07-18T22:21:00.001-07:00</published><updated>2010-07-18T22:41:26.538-07:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='sql'/><category scheme='http://www.blogger.com/atom/ns#' term='javascript'/><category scheme='http://www.blogger.com/atom/ns#' term='reserved words'/><title type='text'></title><content type='html'>&lt;span style="font-family: arial;"&gt;On Reserved Words in Programming languages...&lt;/span&gt;&lt;br /&gt;&lt;br/&gt;&lt;br /&gt;&lt;span style="font-family: arial;"&gt;I just got bitten by IE when I inadvertently used 'class' as a variable name in Javascript. Firefox doesn't mind but IE generates an error (and I am glad it does). My reference (the David Flanagan "Javascript, The Definitive Guide", 4th Ed) shows that 'class' is not a reserved word in the ECMAScript (aka Javascript) Language definition, but is in the ECMA extension. I should not have used it anyway, I wasn't not paying attention, especially when Notepad++ was showing it as a reserved word in italic.&lt;/span&gt;&lt;br /&gt;&lt;br/&gt;&lt;br /&gt;&lt;span style="font-family: arial;"&gt;That's not the first time I encounter that issue, SQL has many variants and it's quite difficult to know and remember what words are reserved in which dialect of SQL. Using Hibernate or other layers on top of a SQL database complicates that as well. I spent some time in the past chasing a bug like this in one of my Grails applications.&lt;/span&gt;&lt;br /&gt;&lt;br/&gt;&lt;br /&gt;&lt;span style="font-family: arial;"&gt;So, in conclusion: if I was a good boy, I would get the list of reserved words of all the components that have some in each of my projects and keep them handy for a check when things look really weird, or as part of a final Q&amp;amp;A check.&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31737895-2675684230095998543?l=fjanon.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://fjanon.blogspot.com/feeds/2675684230095998543/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31737895&amp;postID=2675684230095998543' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/2675684230095998543'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/2675684230095998543'/><link rel='alternate' type='text/html' href='http://fjanon.blogspot.com/2010/07/on-reserved-words-in-programming.html' title=''/><author><name>Fred Janon</name><uri>http://www.blogger.com/profile/03149683223012183765</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31737895.post-6698518021733219643</id><published>2009-10-15T22:20:00.000-07:00</published><updated>2009-10-16T00:32:04.572-07:00</updated><title type='text'></title><content type='html'>&lt;div  style="text-align: left;font-family:arial;"&gt;&lt;span style="font-size:100%;"&gt;Over my last few Grails projects, although Grails cuts the number of code lines for a Web application down a lot, I realized that I was doing a lot more of code editing than I wanted to. A few areas on my projects needed some improvement: the controllers and the views (show, edit, create) are mostly the same for different domain objects and a lot of code for the persistence should be in services instead of the controllers.&lt;br /&gt;&lt;br /&gt;I also wanted to be able to test the persistence layer independently from the controllers and being able to switch to something else than Hibernate if I wanted to without having to touch the controller code. So I designed a project with an "InstanceController", two views and an "InstanceService" that implements the common code for most domain objects. This is really the first draft and I envision a lot of improvements over this concept. With the dynamic features of Groovy, it could be possible to add the same features in a Groovy-er way. Work in progress.&lt;br /&gt;&lt;br /&gt;The InstanceController works with two views for each domain object: "crud.gsp" and "list.gsp" and the InstanceService sub-classed for the particular domain object. So the structure of the Grails project is basically the same but "crud.gsp" implements all the functions of "edit.gsp", "show.gsp", "create.gsp".&lt;br /&gt;&lt;br /&gt;So no more of editing three files when the domain object changes or the GUI changes. The GUI is consistent across the CRUD operations. The controller has an additional action "formactions" used in "crud.gsp" to manage the "cancel", "save", "edit" and "delete" buttons in the "crud.gsp" view. It also has a "void bindmore(instance, params)" method that can be overridden to bind checkboxes or other particular HTML elements to the domain class properties.&lt;br /&gt;&lt;br /&gt;The usual "index", "list", "show", "create", "edit", "update", "delete" and "save" actions are still there if needed, but the view is handled by "crud.gsp" and the "formactions" in the controller. "formactions" calls "create", "edit", "save" and "delete" from the buttons clicked in "crud.gsp". All action closures call the methods of the same name to be able to override them in a subclass of the InstanceController.&lt;br /&gt;&lt;br /&gt;The UI flow is: display "list.gsp", from an application menu for example, then a click on an item in the list calls "show" in the subclass of InstanceController for the domain object, which displays "view/domainobject/crud.gsp". Then clicking "delete", "edit", "save" or "cancel" calls the "formactions" closure in "/controller/domainobjectController". "formactions" calls "save", "update", "delete", "create" or displays the "list.gsp" view.&lt;br /&gt;&lt;br /&gt;A couple of things there, the handling of "cancel" can be done with consistence, depending on the context and the application. "cancel" while editing means drop the changes and go back to the "show" mode, but "cancel" in show mode should go back to the "list" view. We could also hide the "cancel" button in "show" mode in "crud.gsp".&lt;br /&gt;&lt;br /&gt;A small, but quite appreciated by the users, feature is highlighting the last object worked on in the "list.gsp" view. The object instance "id" is passed to "list.gsp" which adds the "selected" class to the line where the object is displayed, so the line is highlighted in the table (in yellow with my CSS style). It makes it very easy for the user to locate the last line worked on.&lt;br /&gt;&lt;br /&gt;The GUI mode ("SHOW", "EDIT", "CREATE" is maintained between "crud.gsp" and "formactions" in the InstanceController and allows showing or hiding elements and buttons.&lt;br /&gt;&lt;br /&gt;The subclass of the "InstanceController" must implement the "setup" method to define the "InstanceService" associated with the controller for the persistence operations and the domain object name displayed in the views.  The "InstanceController" subclass can override any of the "InstanceController" methods if need be.&lt;br /&gt;&lt;br /&gt;For the persistence layer, the "InstanceService" implements "list", "getCount", "getById", "newinstance", "save", "update", "delete", "findByName", "createDefaults" (creates initial values if none exist in the database) and "archive" if the domain object has an "archived" property. The subclass of "InstanceService" for the domain object needs to implement the "setup" method, where the initial domain objects are defined in the "defaults" list if needed. The "instanceclassname" containing the domain class name must be defined as well as the domain object property name used for sorting the "list.gsp" view. Here too, the "InstanceService" subclass can override any of the "InstanceService" methods if need be. Last thing not to forget, the "setup" method of each "InstanceService" subclass must be called in "Bootstrap.groovy", or in the "setUp" method of any integration test.&lt;br /&gt;&lt;br /&gt;The domain class must implement "String toMessage()", to display a user-friendly domain object name. For example, my class name is "Streettype", but "toMessage" will return "Street Type". It's used in "crud.gsp" and "list.gsp". "toString" could be used, but then a bit tricky if "toString" is also used for debugging. I guess we could check if "toMessage" is implemented and use "toString" if not.&lt;br /&gt;&lt;br /&gt;The code is posted at &lt;a href="http://code.google.com/p/thecodefactory/wiki/GrailsRefactoring"&gt;http://code.google.com/p/thecodefactory/wiki/GrailsRefactoring&lt;br /&gt;&lt;/a&gt;&lt;br /&gt;&lt;span style="font-family:courier new;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;/div&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31737895-6698518021733219643?l=fjanon.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://fjanon.blogspot.com/feeds/6698518021733219643/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31737895&amp;postID=6698518021733219643' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/6698518021733219643'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/6698518021733219643'/><link rel='alternate' type='text/html' href='http://fjanon.blogspot.com/2009/10/over-my-last-few-grails-projects.html' title=''/><author><name>Fred Janon</name><uri>http://www.blogger.com/profile/03149683223012183765</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31737895.post-2501939934891694539</id><published>2007-11-23T23:56:00.000-08:00</published><updated>2007-11-24T04:06:49.894-08:00</updated><category scheme='http://www.blogger.com/atom/ns#' term='java'/><category scheme='http://www.blogger.com/atom/ns#' term='actors'/><category scheme='http://www.blogger.com/atom/ns#' term='scala'/><title type='text'></title><content type='html'>&lt;span style="font-family:arial;font-size:85%;"&gt;I just discovered the "Scala" language, thanks to an excellent article "Java EE meets Web 2.0" (&lt;/span&gt;&lt;a href="http://www.ibm.com/developerworks/web/library/wa-aj-web2jee/"&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;http://www.ibm.com/developerworks/web/library/wa-aj-web2jee/&lt;/span&gt;&lt;/a&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;) on IBM's developerWorks. Scala is very close to Java and generates class files that run on the JVM. I am a user and a fan of Groovy, but I am interested in Scala for its Actors library: Actors are "tasks" that can send and receive messages synchronously or asynchronously. There is a short tutorial at &lt;/span&gt;&lt;a href="http://lamp.epfl.ch/~phaller/doc/ActorsTutorial.html"&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;http://lamp.epfl.ch/~phaller/doc/ActorsTutorial.html&lt;/span&gt;&lt;/a&gt;&lt;span style="font-family:arial;font-size:85%;"&gt; by Philipp Haller, the author of the library.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;The Scala documentation says that Scala objects can call Java objects and vice-versa. I wanted to write a code snippet to see how a Java application can create and call Scala objects. It's very basic but it works!&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;A Java class "Zoo" with the "main" method creates a Scala object "Dog" and calls its method "talk".&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;Running the Zoo main on Windows:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;C:\ScalaTest&gt;java Zoo&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;Zoo...&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;Woof, woof!&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;Here it is the code for the 2 files Zoo.java and Dog.scala:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;Zoo.java:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;class Zoo {&lt;br /&gt;public static void main(String[] args) &lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;{&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;System.out.println("Zoo...");&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;Dog dog = new Dog();&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;dog.talk();&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;} // main&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;} // class Zoo&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;Dog.scala:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;class Dog&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;{&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;val sound = "Woof, woof!"&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;def talk() = println(sound)&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;} // class Dog&lt;br /&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;How to build it on Windows:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;Compile the Scala file first:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;C:\ScalaTest&gt;scalac Dog.scala&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;Then compile the main app, Java will find the Dog.class&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;C:\ScalaTest&gt;javac Zoo.java&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;Run it:&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;C:\ScalaTest&gt;java Zoo&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;Zoo...&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:courier new;font-size:85%;"&gt;Woof, woof!&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;"Zoo" is printed by the Java Zoo class&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;"Woof, woof" is printed by the Scala "Dog" class.&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;That's it!&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;&lt;/span&gt;&lt;br /&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;Preliminary steps to install Java and Scala:&lt;/span&gt;&lt;br /&gt;&lt;ul&gt;&lt;li&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;install a JDK (download it from &lt;/span&gt;&lt;a href="http://java.sun.com/javase/downloads"&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;http://java.sun.com/javase/downloads&lt;/span&gt;&lt;/a&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;)&lt;/span&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;add the path to your java \bin folder (something like C:\jdk1.5.0_09\bin) to your PATH environment variable.&lt;/span&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;check that the Java compiler is accessible by opening a cmd window an typing "javac" and return. A list of options will be displayed, starting like this: &lt;span style="font-family:courier new;"&gt;"Usage: javac &lt;options&gt;&lt;source&gt;..."&lt;/span&gt;.&lt;/span&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;add the Java libraries to the "classpath" environment variable, something like this: &lt;span style="font-family:courier new;"&gt;"classpath=.;C:\jdk1.5.0_09\jre\lib\rt.jar;C:\jdk1.5.0_09\lib\tools.jar;"&lt;/span&gt;&lt;/span&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;install Scala (download it from &lt;/span&gt;&lt;a href="http://www.scala-lang.org/"&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;http://www.scala-lang.org/&lt;/span&gt;&lt;/a&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;)&lt;/span&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;add the Scala bin folder to your PATH environment variable. Should look like this: &lt;span style="font-family:courier new;"&gt;"...;C:\scala-2.6.0-final\bin;"&lt;/span&gt;&lt;/span&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;add the Scala libraries to the "classpath" environment variable. Should look like this with the Java libraries: &lt;span style="font-family:courier new;"&gt;"classpath=.;C:\jdk1.5.0_09\jre\lib\rt.jar;C:\jdk1.5.0_09\lib\tools.jar;C:\scala-2.6.0-final\lib\scala-library.jar;"&lt;/span&gt;&lt;/span&gt;&lt;/li&gt;&lt;li&gt;&lt;span style="font-family:Courier New;font-size:85%;"&gt;&lt;span style="font-family:arial;"&gt;check that the Scala compiler is accessible from a cmd window:&lt;/span&gt; "C:\ScalaTest&gt;scalac" &lt;span style="font-family:arial;"&gt;will display a list of options:&lt;/span&gt; "Usage: scalac &lt;options&gt;..."&lt;/span&gt;&lt;/li&gt;&lt;/ul&gt;&lt;p&gt;&lt;span style="font-family:arial;font-size:85%;"&gt;That should do it. If not, check java.sun.com for Java installation issues and scala-lang.org for the Scala ones.&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-family:Arial;font-size:85%;"&gt;I am off to try some Actors code in Scala.&lt;/span&gt;&lt;/p&gt;&lt;p&gt;&lt;/p&gt;&lt;p&gt;&lt;span style="font-family:Arial;font-size:85%;"&gt;&lt;/span&gt;&lt;/p&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31737895-2501939934891694539?l=fjanon.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://fjanon.blogspot.com/feeds/2501939934891694539/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31737895&amp;postID=2501939934891694539' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/2501939934891694539'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/2501939934891694539'/><link rel='alternate' type='text/html' href='http://fjanon.blogspot.com/2007/11/i-just-discovered-scala-language-thanks.html' title=''/><author><name>Fred Janon</name><uri>http://www.blogger.com/profile/03149683223012183765</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-31737895.post-116177339989739287</id><published>2006-10-25T02:59:00.000-07:00</published><updated>2006-10-25T03:49:59.916-07:00</updated><title type='text'></title><content type='html'>&lt;span style="font-size:85%;"&gt;I just did some work with the YahooUI Calendar and created a helper to make it easier to use.  It is a Javascript file that you include in your HTML page header, a SPAN or DIV element where the icon for the calendar and the calendar itself will be displayed and a SCRIPT where the YahooCalendar object is created with a few parameters.&lt;br /&gt;&lt;br /&gt;&lt;br /&gt;&lt;/span&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/31737895-116177339989739287?l=fjanon.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://fjanon.blogspot.com/feeds/116177339989739287/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='http://www.blogger.com/comment.g?blogID=31737895&amp;postID=116177339989739287' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/116177339989739287'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/31737895/posts/default/116177339989739287'/><link rel='alternate' type='text/html' href='http://fjanon.blogspot.com/2006/10/i-just-did-some-work-with-yahooui_25.html' title=''/><author><name>Fred Janon</name><uri>http://www.blogger.com/profile/03149683223012183765</uri><email>noreply@blogger.com</email><gd:image rel='http://schemas.google.com/g/2005#thumbnail' width='16' height='16' src='http://img2.blogblog.com/img/b16-rounded.gif'/></author><thr:total>0</thr:total></entry></feed>
