Re: [jQuery] jQuery Kinda Plugin: every

2006-10-20 Thread Blair Mitchelmore
Good suggestions John as always. .in() can't be done because 'in' is a 
JS keyword and I wouldn't want to have to call it like $()['in']() all 
the time. So I figured two JS keywords smashed together would work and 
chose .doin() as the function name; if you have any better ideas (maybe 
.timeout() and .interval()) let me know.

So this can handle multiple different one-off delays and interval-ed 
events. These can then be canceled based on their reference label or 
their interval if you didn't provide a label (not both).

Example:
$('p.display')
.doin(500,function() { window.alert(a); })
.doin(1000,function() { window.alert(b); })
.doin(500,function() { window.alert(c); })
.doin(1000,'other',function() { window.alert(d); })
.doin(500,'other',function() { window.alert(e); });

// Alerts: 'a','b','c'
$('p.display').stop('other');

// Alerts: 'b','d','e'
$('p.display').stop(500);

// Alerts: 'a','c','d','e'
$('p.display').stop(1000);

// Alerts Nothing
$('p.display').stop();

I'll probably host this on my server if there's any interest. Any Questions?

-blair

Code Below:
jQuery.fn.extend({
every: function(interval,id,fn) {
return this.each(function() {
var self = this;
interval = jQuery.speed(interval);
if (fn == undefined) {
fn = id;
id = interval;
}
if (!this.timers) this.timers = {};
if (!this.timers[id]) this.timers[id] = [];
this.timers[id].push(window.setInterval(function() {
fn.call(self);
},interval));
});
},
doin: function(interval,id,fn) {
return this.each(function() {
var self = this, counter = 0;
interval = jQuery.speed(interval);
if (fn == undefined) {
fn = id;
id = interval;
}
if (!this.timers) this.timers = {};
if (!this.timers[id]) this.timers[id] = [];
this.timers[id].push(window.setInterval(function() {
if (counter++ = 1) return jQuery(self).stop(id);
fn.call(self);
},interval));
});
},
stop: function(id) {
return this.each(function() {
if (!this.timers) return;
if (id == undefined)
jQuery.each(this.timers, function(i) {
jQuery.each(this,function(j) {
window.clearInterval(this);
});
});
else if (this.timers[id])
jQuery.each(this.timers[id],function(i) {
window.clearInterval(this);
});
});
}
});

John Resig wrote:
 What if you had a trifecta of functions:
 .every()
 .in()
 .stop()

 and allow for function calls like this:

 .every( 100, text, function(){
 if ( !$(this).val() )
 $(this).stop(text);
 });

 or if you don't care about a name:

 .in( slow, function(){
 $(this).hide();
 })
 .mouseover(function(){
 $(this).stop();
 });

 or if you wanna get really interesting, make it so that you can stop
 function calls by how long their timer is set for:

 .every( 500, function(){
 $(#foo).load(test.html);
 })
 .every( 100, function(){
 if ( !$(this).val() )
 $(this).stop(100);
 });

 Just throwing out some ideas, let me know which ones stick.


___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-20 Thread Blair Mitchelmore
Once again, I have an 11th hour code change. I had forgotten about 
Jörn's suggestion of allowing additional passed arguments. I'm not 
entirely sure what kind of implementation or usage was expected but I 
added my own version. Any argument provided to the .doin()/.every() 
function beyond the action function will be passed to the action 
function as an argument. Hopefully that's what he was talking about. 
Code Below:

jQuery.fn.extend({
every: function(interval,id,fn) {
var args = jQuery.map(arguments,a), slice = 3;
return this.each(function() {
var self = this;
interval = jQuery.speed(interval);
if (fn == undefined || id.constructor == Function) {
fn = id;
id = interval;
slice = 2;
}
if (!this.timers) this.timers = {};
if (!this.timers[id]) this.timers[id] = [];
this.timers[id].push(window.setInterval(function() {
fn.apply(self,args.slice(slice));
},interval));
});
},
doin: function(interval,id,fn) {
var args = jQuery.map(arguments,a), slice = 3;
return this.each(function() {
var self = this, counter = 0;
interval = jQuery.speed(interval);
if (fn == undefined || id.constructor == Function) {
fn = id;
id = interval;
slice = 2;
}
if (!this.timers) this.timers = {};
if (!this.timers[id]) this.timers[id] = [];
this.timers[id].push(window.setInterval(function() {
if (counter++ = 1) return jQuery(self).stop(id);
fn.apply(self,args.slice(slice));
},interval));
});
},
stop: function(id) {
return this.each(function() {
if (!this.timers) return;
if (id == undefined)
jQuery.each(this.timers, function(i) {
jQuery.each(this,function(j) {
window.clearInterval(this);
});
});
else if (this.timers[id])
jQuery.each(this.timers[id],function(i) {
window.clearInterval(this);
});
});
}
});

Blair Mitchelmore wrote:
 Good suggestions John as always. .in() can't be done because 'in' is a 
 JS keyword and I wouldn't want to have to call it like $()['in']() all 
 the time. So I figured two JS keywords smashed together would work and 
 chose .doin() as the function name; if you have any better ideas (maybe 
 .timeout() and .interval()) let me know.

 So this can handle multiple different one-off delays and interval-ed 
 events. These can then be canceled based on their reference label or 
 their interval if you didn't provide a label (not both).

 Example:
 $('p.display')
 .doin(500,function() { window.alert(a); })
 .doin(1000,function() { window.alert(b); })
 .doin(500,function() { window.alert(c); })
 .doin(1000,'other',function() { window.alert(d); })
 .doin(500,'other',function() { window.alert(e); });

 // Alerts: 'a','b','c'
 $('p.display').stop('other');

 // Alerts: 'b','d','e'
 $('p.display').stop(500);

 // Alerts: 'a','c','d','e'
 $('p.display').stop(1000);

 // Alerts Nothing
 $('p.display').stop();

 I'll probably host this on my server if there's any interest. Any Questions?

 -blair


___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-20 Thread Blair Mitchelmore

Michael Geary wrote:

 You can simplify that code quite a bit. every() and doin() are nearly
 identical, so they can both call a common implementation. Ditto for the two
 inner loops in stop().
Great suggestions Mike. I noticed that they were very similar but I was 
too lazy to combine them but now you have challenged me, and I have 
realized that just as with the immortals, there can be only one.

The code you modified was the original rewrite which didn't include the 
additional passed arguments feature so my version of the rewrite is 
slightly different but inspired by yours.

 Since I was moving the whole thing inside a function to get a local scope
 for the every() helper, that gave me a chance to rename jQuery as $. This is
 a matter of taste, of course, but I like being able to write plugin code the
 same way as ordinary jQuery code, using $.
It's definitely a matter of taste, as I tend to prefer to use the jQuery 
in plug-in development seeing as the ultimate result is intended for 
much generic uses than my page specfici code so it brings me into a 
different more methodical mindset.

 One last thing - in the inner function inside every(), I changed the uses of
 this to self, because there's a var self = this; at the top of the
 function. I think it helps readability to only use self after a var self
 = this; instead of mixing this and self.
That's probably because self was an afterthought. I always forget about 
the intransitive nature of 'this' so my this closures are usually not 
written until I realize I need them.

 The code is untested, but should work the same as the original unless I
 goofed. :-)

 -Mike
Well Actually it wouldn't have worked because I made a goof in my code! 
Initially by setting interval to the result of jQuery.speed rather than 
the duration property of the result. Noticed when testing the new code.

Here's the updated code (it'll probably be wrapped by my mail client):
jQuery.fn.extend({
every: function(interval,id,fn) {
return 
jQuery.timer.add.apply(this,[false].concat(jQuery.map(arguments,a)));
},
doin: function(interval,id,fn) {
return 
jQuery.timer.add.apply(this,[true].concat(jQuery.map(arguments,a)));
},
stop: function(id) {
return jQuery.timer.remove.apply(this,[id]);
}
});

jQuery.extend({
timer: {
add: function(oneOff,interval,id,fn) {
var args = jQuery.map(arguments,a), slice = 4;
return this.each(function() {
var self = this, counter = 0;
interval = jQuery.speed(interval)['duration'];
if (fn == undefined || id.constructor == Function) {
fn = id;
id = interval;
slice = 3;
}
if (!self.timers) self.timers = {};
if (!self.timers[id]) self.timers[id] = [];
self.timers[id].push(window.setInterval(function() {
if (oneOff  counter++ = 1) return 
jQuery(self).stop(id);
fn.apply(self,args.slice(slice));
},interval));
});
},
remove: function(id) {
return this.each(function() {
if (!this.timers) return;
jQuery.each(id == undefined ? this.timers : 
[this.timers[id]], function(i) {
jQuery.each(this,function(j) {
window.clearInterval(this);
});
});
});
}
}
});

-blair

___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


[jQuery] jQuery Kinda Plugin: every

2006-10-19 Thread Blair Mitchelmore
I don't know if this exists already but I needed this and assumed it 
didn't and wrote it myself. Essentially it lets you do something to an 
element every given time interval.

jQuery.fn.every = function(interval,fn) {
return this.each(function() {
var self = this;
window.setInterval(function() { fn.call(self) },interval);
});
};

I used it to get a millisecond amount display every so often to produce 
a live updated element. It's mostly for live clock updating (and I 
suppose it could be useful to implement polling) but I'm sure the 
creative among you could find some other purpose for it.

Example:
// Display the current time updated every 500 ms
$(p.display).every(500,function() {
$(this).html(new Date());
});

-blair

___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-19 Thread Blair Mitchelmore
And I just realized I should make it possible to stop the repeating 
function later on.

Code:
jQuery.fn.every = function(interval,fn) {
return this.each(function() {
var self = this;
this.$every = window.setInterval(function() { fn.call(self) 
},interval);
});
};

Example:
// Display the current time updated every 500 ms
$(p.display).every(500,function() {
$(this).html(new Date());
});

//... some point later in the code execution
$(p.display).each(function() {
window.clearInterval(this.$every);
this.$every = null;
});

-blair

Blair Mitchelmore wrote:
 I don't know if this exists already but I needed this and assumed it 
 didn't and wrote it myself. Essentially it lets you do something to an 
 element every given time interval.


 -blair



___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-19 Thread Brian Miller
While it's not very jQuery-like, timers lend themselves to registration. 
I would attach an object to window or a more permanently/easily available
object.  This way, you don't have to leave closures around just to keep
references to the timers, just so you can stop them later.

Also, if you're attaching the timer references to DOM objects, then I
think that you are opening the door to possible serious memory leakage. 
Clever, but perhaps dangerous.

- Brian


 And I just realized I should make it possible to stop the repeating
 function later on.

 Code:
 jQuery.fn.every = function(interval,fn) {
 return this.each(function() {
 var self = this;
 this.$every = window.setInterval(function() { fn.call(self)
 },interval);
 });
 };

 Example:
 // Display the current time updated every 500 ms
 $(p.display).every(500,function() {
 $(this).html(new Date());
 });

 //... some point later in the code execution
 $(p.display).each(function() {
 window.clearInterval(this.$every);
 this.$every = null;
 });

 -blair

 Blair Mitchelmore wrote:
 I don't know if this exists already but I needed this and assumed it
 didn't and wrote it myself. Essentially it lets you do something to an
 element every given time interval.


 -blair



 ___
 jQuery mailing list
 discuss@jquery.com
 http://jquery.com/discuss/




___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-19 Thread Jörn Zaefferer
Blair Mitchelmore schrieb:
 And I just realized I should make it possible to stop the repeating 
 function later on.

 Code:
 jQuery.fn.every = function(interval,fn) {
 return this.each(function() {
 var self = this;
 this.$every = window.setInterval(function() { fn.call(self) 
 },interval);
 });
 };

 Example:
 // Display the current time updated every 500 ms
 $(p.display).every(500,function() {
 $(this).html(new Date());
 });

 //... some point later in the code execution
 $(p.display).each(function() {
 window.clearInterval(this.$every);
 this.$every = null;
 });
   
You could package that in a second plugin method. Just need to find a 
nice name...

In addition, it may be helpful to be able to pass arguments to the 
function. There may be cases where you can't rely on a closure to pass 
arguments.

-- Jörn

___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-19 Thread John Resig
What if you had a trifecta of functions:
.every()
.in()
.stop()

and allow for function calls like this:

.every( 100, text, function(){
if ( !$(this).val() )
$(this).stop(text);
});

or if you don't care about a name:

.in( slow, function(){
$(this).hide();
})
.mouseover(function(){
$(this).stop();
});

or if you wanna get really interesting, make it so that you can stop
function calls by how long their timer is set for:

.every( 500, function(){
$(#foo).load(test.html);
})
.every( 100, function(){
if ( !$(this).val() )
$(this).stop(100);
});

Just throwing out some ideas, let me know which ones stick.

--John

On 10/19/06, Blair Mitchelmore [EMAIL PROTECTED] wrote:
 And I just realized I should make it possible to stop the repeating
 function later on.

 Code:
 jQuery.fn.every = function(interval,fn) {
 return this.each(function() {
 var self = this;
 this.$every = window.setInterval(function() { fn.call(self)
 },interval);
 });
 };

 Example:
 // Display the current time updated every 500 ms
 $(p.display).every(500,function() {
 $(this).html(new Date());
 });

 //... some point later in the code execution
 $(p.display).each(function() {
 window.clearInterval(this.$every);
 this.$every = null;
 });

 -blair

 Blair Mitchelmore wrote:
  I don't know if this exists already but I needed this and assumed it
  didn't and wrote it myself. Essentially it lets you do something to an
  element every given time interval.
 
 
  -blair
 


 ___
 jQuery mailing list
 discuss@jquery.com
 http://jquery.com/discuss/



-- 
John Resig
http://ejohn.org/
[EMAIL PROTECTED]

___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-19 Thread Yehuda Katz
Those 3 functions would be extremely nice, and provide some much-needed built-in observer functionality (a la prototype's observer).-- YehudaOn 10/19/06, 
John Resig [EMAIL PROTECTED] wrote:
What if you had a trifecta of functions:.every().in().stop()and allow for function calls like this:.every( 100, text, function(){if ( !$(this).val() )$(this).stop(text);
});or if you don't care about a name:.in( slow, function(){$(this).hide();}).mouseover(function(){$(this).stop();});or if you wanna get really interesting, make it so that you can stop
function calls by how long their timer is set for:.every( 500, function(){$(#foo).load(test.html);}).every( 100, function(){if ( !$(this).val() )$(this).stop(100);
});Just throwing out some ideas, let me know which ones stick.--JohnOn 10/19/06, Blair Mitchelmore [EMAIL PROTECTED] wrote: And I just realized I should make it possible to stop the repeating
 function later on. Code: jQuery.fn.every = function(interval,fn) { return this.each(function() { var self = this; this.$every = window.setInterval
(function() { fn.call(self) },interval); }); }; Example: // Display the current time updated every 500 ms $(p.display).every(500,function() { $(this).html(new Date());
 }); //... some point later in the code execution $(p.display).each(function() { window.clearInterval(this.$every); this.$every = null; });
 -blair Blair Mitchelmore wrote:  I don't know if this exists already but I needed this and assumed it  didn't and wrote it myself. Essentially it lets you do something to an
  element every given time interval.-blair  ___ jQuery mailing list 
discuss@jquery.com http://jquery.com/discuss/--John Resighttp://ejohn.org/
[EMAIL PROTECTED]___jQuery mailing listdiscuss@jquery.comhttp://jquery.com/discuss/
-- Yehuda KatzWeb Developer | Wycats Designs(ph)718.877.1325
___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-19 Thread Dave Methvin
Since the event handling has recently been fixed to avoid IE memory leaks,
could we leverage that? After all, a timer is an event.

$(#time).interval(1000);

basically would map to this:  

setInterval(function(){ $(#time).trigger(tick) }, 1000);

An interval of 0 would stop the timer. A one-time trigger could be done like
this:

$(#time).timeout(1000);

The handler looks like this:

$(#time).bind(tick, function(){
this.text(new Date());
});

BTW, Javascript timer receipts are just numbers so they can be assigned to
an object without causing a closure.

This approach would limit to one tick event per element--some might consider
that a feature--but you could always pass in another event name as the
second arg to timeout or interval.


-Original Message-
From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED] On
Behalf Of John Resig
Sent: Thursday, October 19, 2006 1:40 PM
To: jQuery Discussion.
Subject: Re: [jQuery] jQuery Kinda Plugin: every

What if you had a trifecta of functions:
.every()
.in()
.stop()

and allow for function calls like this:

.every( 100, text, function(){
if ( !$(this).val() )
$(this).stop(text);
});

or if you don't care about a name:

.in( slow, function(){
$(this).hide();
})
.mouseover(function(){
$(this).stop();
});

or if you wanna get really interesting, make it so that you can stop
function calls by how long their timer is set for:

.every( 500, function(){
$(#foo).load(test.html);
})
.every( 100, function(){
if ( !$(this).val() )
$(this).stop(100);
});

Just throwing out some ideas, let me know which ones stick.

--John

On 10/19/06, Blair Mitchelmore [EMAIL PROTECTED] wrote:
 And I just realized I should make it possible to stop the repeating 
 function later on.

 Code:
 jQuery.fn.every = function(interval,fn) {
 return this.each(function() {
 var self = this;
 this.$every = window.setInterval(function() { fn.call(self) 
 },interval);
 });
 };

 Example:
 // Display the current time updated every 500 ms
 $(p.display).every(500,function() {
 $(this).html(new Date());
 });

 //... some point later in the code execution
 $(p.display).each(function() {
 window.clearInterval(this.$every);
 this.$every = null;
 });

 -blair

 Blair Mitchelmore wrote:
  I don't know if this exists already but I needed this and assumed it 
  didn't and wrote it myself. Essentially it lets you do something to 
  an element every given time interval.
 
 
  -blair
 


___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/


Re: [jQuery] jQuery Kinda Plugin: every

2006-10-19 Thread Blair McKenzie
I like that :DA way around the one element-one tick would be to have an optional second argument on interval and timeout to label the tick. e.g. interval(1000, abc)...bind(tick-abc, function() {})
BlairOn 10/20/06, Dave Methvin [EMAIL PROTECTED] wrote:
Since the event handling has recently been fixed to avoid IE memory leaks,could we leverage that? After all, a timer is an event.$(#time).interval(1000);basically would map to this:
setInterval(function(){ $(#time).trigger(tick) }, 1000);An interval of 0 would stop the timer. A one-time trigger could be done likethis:$(#time).timeout(1000);
The handler looks like this:$(#time).bind(tick, function(){this.text(new Date());});BTW, _javascript_ timer receipts are just numbers so they can be assigned toan object without causing a closure.
This approach would limit to one tick event per element--some might considerthat a feature--but you could always pass in another event name as thesecond arg to timeout or interval.-Original Message-
From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED]] OnBehalf Of John ResigSent: Thursday, October 19, 2006 1:40 PM
To: jQuery Discussion.Subject: Re: [jQuery] jQuery Kinda Plugin: everyWhat if you had a trifecta of functions:.every().in().stop()and allow for function calls like this:.every( 100, text, function(){
if ( !$(this).val() )$(this).stop(text);});or if you don't care about a name:.in( slow, function(){$(this).hide();}).mouseover(function(){
$(this).stop();});or if you wanna get really interesting, make it so that you can stopfunction calls by how long their timer is set for:.every( 500, function(){$(#foo).load(
test.html);}).every( 100, function(){if ( !$(this).val() )$(this).stop(100);});Just throwing out some ideas, let me know which ones stick.--JohnOn 10/19/06, Blair Mitchelmore 
[EMAIL PROTECTED] wrote: And I just realized I should make it possible to stop the repeating function later on. Code: jQuery.fn.every = function(interval,fn) {
 return this.each(function() { var self = this; this.$every = window.setInterval(function() { fn.call(self) },interval); }); }; Example:
 // Display the current time updated every 500 ms $(p.display).every(500,function() { $(this).html(new Date()); }); //... some point later in the code execution
 $(p.display).each(function() { window.clearInterval(this.$every); this.$every = null; }); -blair Blair Mitchelmore wrote:  I don't know if this exists already but I needed this and assumed it
  didn't and wrote it myself. Essentially it lets you do something to  an element every given time interval.-blair ___
jQuery mailing listdiscuss@jquery.comhttp://jquery.com/discuss/
___
jQuery mailing list
discuss@jquery.com
http://jquery.com/discuss/