Aggregate Callback
Author: Samuel Williams When: Thursday, 03 June 2010April 2009
May 2009
August 2009
September 2009
October 2009
- Building a Concrete Bath
- LED Lighting Comparison
- Thinking about Programming Languages
- How To Be A Consultant
- Lucid Programming Dojo
- Exim4 + ClamAV + SpamAssassin
- Secure login using AJAX
- Ramaze And Rack
- ActiveMerchant
- Concurrency And Immutability
- Floating Point Numbers
- Programming And Debugging
- Useful jQuery Plugins
- Loading Anonymous Ruby Classes
- 尺八 (Shakuhachi)
- Card Trick
- Object Oriented C
- Gemcutter
- Writing Clearly
- Richard Stallman In Christchurch
- Magnatune
- Client Side Graphing
- Zena CMS
November 2009
February 2010
March 2010
April 2010
May 2010
June 2010
July 2010
August 2010
September 2010
December 2010
January 2011
March 2011
May 2011
August 2011
September 2011
In a comment form, you might want to send the data using AJAX to get a preview. In this case, you generally want to aggregate the events so that you only fetch a new preview when the user stops typing or a certain timeout is reached.
Here is some JavaScript code for implementing this kind of behaviour.
// Released under the GNU GPLv3. Copyright 2010 Samuel Williams.
function AggregateCallback (timeout, enforce, callback) {
this.timeout = timeout;
this.enforce = enforce;
this.callback = callback;
this.timer = null;
this.fired = null;
}
AggregateCallback.prototype.fire = function () {
this.fired = new Date();
this.callback();
}
AggregateCallback.prototype._expired = function () {
// Returns true if we have been fired further than maxTimeout in the past.
return !this.fired || ((new Date() - this.fired) > this.timeout);
}
AggregateCallback.prototype.update = function () {
if (this._expired() && this.enforce)
this.fire()
if (this.timer) {
clearTimeout(this.timer);
this.timer = null;
}
var target = this;
this.timer = setTimeout(function () { target.fire(); }, this.timeout);
}
Here is an example of how to use it:
// Released under the GNU GPLv3. Copyright 2010 Samuel Williams.
var commentsForm = $(...);
var livePreview = new AggregateCallback(1000, true, function() {
$.post("comments/preview", {'body': $('textarea[name=body]', commentsForm).val()}, function(data) {
$('.preview', commentsForm).html(data);
$.syntax({context: $('.preview', commentsForm)});
});
});
$('textarea[name=body]', commentsForm).keyup(function() {
livePreview.update();
});
Here is an explanation of how it works: You create an AggregateCallback with a timeout value (in milliseconds). You call update a number of times. If you don't call update within the timeout, the callback is fired.
If you set enforce to true, the callback will be fired every timeout milliseconds, and also finally timeout milliseconds after the last call to update. This means that, in the case of a live preview, the server will be polled once every second even while the user is continuing to type.
Comments
Please note, you can leave a comment that uses (limited) XHTML and Textile syntax.