Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

SVG speed?

84 views
Skip to first unread message

voipme

unread,
Dec 4, 2008, 9:45:13 PM12/4/08
to
I've been messing with SVG for a while now, and managed to come up
with a relatively good library that I use for all of my SVG
animations. I'm running into a problem where I'm trying to animate
multiple (upwards of 20) SVG elements at the same time, and I keep
running into crazy framerate issues. Its expected, but its a nasty
visual effect that I'm trying to avoid. All of my animations are
being performed with setTimeout, and I'm curious if there's a better
way to do it. (perhaps setInterval?)

HelderMagalhaes

unread,
Dec 5, 2008, 6:55:29 AM12/5/08
to
> I've been messing with SVG for a while now, and managed to come up
> with a relatively good library that I use for all of my SVG
> animations.

Great, please consider sharing it if not similar to existing libraries
(such as FakeSmile [1]). :-)


> I'm running into a problem where I'm trying to animate
> multiple (upwards of 20) SVG elements at the same time, and I keep
> running into crazy framerate issues. Its expected, but its a nasty
> visual effect that I'm trying to avoid.

Updating this number of objects shouldn't be a problem. Of course this
will depend, as far as I know, on a number of parameters: the
complexity of the objects, the complexity of the canvas around them
(which may required more repainting whenever the objects are changed,
etc.).


> All of my animations are being performed with setTimeout, and I'm curious if there's a better
> way to do it. (perhaps setInterval?)

Using "setInterval" is not recommended due to a Firefox issue [2]. A
script animation study was recently published [3], and discussion is
being done through a thread [4] in the Yahoo's SVG Developers group.


Hope this helps,

Helder Magalhães


[1] http://leunen.d.free.fr/fakesmile/index.html
[2] https://bugzilla.mozilla.org/show_bug.cgi?id=291386
[3] http://anomaly.org/wade/projects/svg/profiling/
[4] http://tech.groups.yahoo.com/group/svg-developers/message/61533

Boris Zbarsky

unread,
Dec 5, 2008, 11:26:48 AM12/5/08
to
voipme wrote:
> I've been messing with SVG for a while now, and managed to come up
> with a relatively good library that I use for all of my SVG
> animations. I'm running into a problem where I'm trying to animate
> multiple (upwards of 20) SVG elements at the same time, and I keep
> running into crazy framerate issues. Its expected

It is? Sounds like a performance bug to me. A testcase would help.

>, but its a nasty
> visual effect that I'm trying to avoid. All of my animations are
> being performed with setTimeout, and I'm curious if there's a better
> way to do it. (perhaps setInterval?)

Hard to say without a testcase and absent some serious telepathic abilities.

-Boris

Boris Zbarsky

unread,
Dec 5, 2008, 11:29:36 AM12/5/08
to
HelderMagalhaes wrote:
> Using "setInterval" is not recommended due to a Firefox issue [2].

Er... say what? Note that setInterval and setTimeout use the same exact
code in Firefox, pretty much, so you'll get very similar behavior with
the two.

-Boris

Jonas Sicking

unread,
Dec 8, 2008, 5:32:55 PM12/8/08
to
>> All of my animations are being performed with setTimeout, and I'm curious if there's a better
>> way to do it. (perhaps setInterval?)
>
> Using "setInterval" is not recommended due to a Firefox issue [2].

Err.. I think you are reading way too much into that bug. Do you have
any data to back up that it's causing enough problem that setInterval
and/or setTimeout should be stayed away from?

/ Jonas

HelderMagalhaes

unread,
Dec 16, 2008, 6:26:45 AM12/16/08
to
> > Using "setInterval" is not recommended due to a Firefox issue [2].
>
> Err.. I think you are reading way too much into that bug. Do you have
> any data to back up that it's causing enough problem that setInterval
> and/or setTimeout should be stayed away from?

I don't think that they should be stayed away from. John Resig even
made a great overall look on the current status of browser timing [1]
and Firefox was one of the most accurate. Nevertheless, trying to
clear up a bit on my previous post, my understanding of this is that:

1. setInterval will conceptually not take into account the time took
to run the code in each call (please correct me if I'm wrong!) so, if
the benchmark code is too long and/or the timing too short, this can
cause really messed up results...

2. Running one of the test cases in the referenced bug [2] sometimes
still shows inaccurate timing. Sample using Firefox 3.0.4:
[...]
f1: 1404ms-> Greater than 10% error!
f2: 1403ms-> Greater than 10% error!
f1: 593ms-> Greater than 10% error!
f2: 593ms-> Greater than 10% error!
[...]
Intuitively, this specific result set makes some sense as we would
expect the average timing to correspond to the desired target trigger
time. But using this for accurate timing measurements can be naturally
misleading, reason why setTimeout is advised instead. Another sample
using Firefox 3.2a1:
[...]
f1: 2230ms-> Greater than 10% error!
f2: 2230ms-> Greater than 10% error!
[...]
This specific one doesn't make much sense as the samples before/
after are all within very close to 1 second, so here setInterval won't
even correspond to the desired "average" behavior above. I've also
noticed that using a high load machine makes the issue much easier to
reproduce, which makes sense. Nevertheless, these two samples were
obtained it the first run using a machine with almost (< 5%) no load.
Operating system used was Windows XP SP3 in a Pentium IV with 1GB RAM.
Would it be valuable to update the bug report with more information
such as this one and potentially more? If so, which details would also
be relevant regarding this?

Best regards,

Helder Magalhães

[1] http://ejohn.org/blog/accuracy-of-javascript-time/
[2] https://bugzilla.mozilla.org/attachment.cgi?id=263884

Boris Zbarsky

unread,
Dec 16, 2008, 10:06:01 AM12/16/08
to
HelderMagalhaes wrote:
> 1. setInterval will conceptually not take into account the time took
> to run the code in each call (please correct me if I'm wrong!)

In Gecko, you're wrong, in that the timer is reset based on when it
fired, not when the callback returned. So if you have a 150ms interval
and you have code that takes 10ms to run that's called from the interval
timer, the timer will fire every 150ms (and be reset for 140ms from
"now" when it gets reset after the code has run). If you use setTimeout
and reset it from the end of your code it'll fire at 150ms, and then the
next time at 310ms (150 + 10 + 150). If you use setTimeout and reset it
from the beginning of your code you should get behavior similar to
setInterval.

> so, if the benchmark code is too long and/or the timing too short, this can
> cause really messed up results...

If the benchmark code takes longer than a single interval to run, then
the interval timer will skip ahead to the next interval. So in the
example above, if you setInterval for 150ms, and your code takes 200ms
to run, then a timer will fire at time 150, then be reset at time 350 to
fire at time 450 (next multiple of 150 after 350).

If you use setTimeout, this doesn't happen. So if you set the timeout
at the end of your code, then it'll fire at 150ms the first time, be
reset at 350ms, and fire again at 500ms. If you set it at the beginning
of your code it'll fire at 150ms, then be reset at 150ms, and fire again
at 350ms (right after your code finishes, basically).

That all assumes there are no other timeouts racing with the one in
question, of course.

Note that the timer accuracy involved is rather low (order of 10ms in
some cases), so any timeouts smaller than about 20ms are likely to be
pretty unreliable.

> 2. Running one of the test cases in the referenced bug [2] sometimes
> still shows inaccurate timing. Sample using Firefox 3.0.4:
> [...]
> f1: 1404ms-> Greater than 10% error!
> f2: 1403ms-> Greater than 10% error!
> f1: 593ms-> Greater than 10% error!
> f2: 593ms-> Greater than 10% error!
> [...]

I can in fact reproduce this sometimes (not always). My best guess
based on things like disk activity and when this happens in relation to
pageload is that this happens when GC runs very close to the time the
timer is supposed to fire and takes a few hundred ms. Note that we do
correct as you can see above so that the average time taken is right.

> Intuitively, this specific result set makes some sense as we would
> expect the average timing to correspond to the desired target trigger
> time. But using this for accurate timing measurements can be naturally
> misleading, reason why setTimeout is advised instead.

See above for how setInterval and setTimeout differ (at least in Gecko).
Which one you want depends on what you're doing. Note that if GC
fires close to a setTimeout timer's due date that timer will file late
just like a setInterval timer. In fact, the only difference between the
two is that for an interval the previous firing time is taken into
account when scheduling the next firing time, whereas a timeout is just
scheduled based on when the setTimeout call happens. All the rest of
the code is the same. Using either one for "accurate timing
measurements" is asking for trouble.

To expand on that, the current interval and timeout timers are both
somewhat poor as high-quality timers. But any solution that preserves
the single-thread-no-reentrancy web programming model has the same
property, since it has to race other things that are going on. The way
to get high-quality timers is to have a system where you get an
interrupt signal that preempts whatever else is going on (like signals
in C, say). I doubt the web is ready to deal with that sort of thing...
There are proposals to have high-resolution timers available, but
given the above issues I'm not sure how much use they would be.

Your other option is to do Date() based timing. That will work great in
Gecko. It'll work really badly for short time intervals in webkit-based
browsers, since they update their date in 15ms increments (and don't
consider that a bug). I have no idea how well it works in Opera or IE.

-Boris

HelderMagalhaes

unread,
Dec 16, 2008, 12:19:24 PM12/16/08
to
> In Gecko, you're wrong, in that the timer is reset based on when it
> fired, not when the callback returned.

Thanks for clearing this up. I guess my thinking was quite a bit
biased... Of course this makes much more sense. ;-)


> I can in fact reproduce this sometimes (not always). [...] Note that we do


> correct as you can see above so that the average time taken is right.

Weird in deed. In terms of correction, my quick 3.2alpha test didn't
show that correction, although I'm currently not being able to
reproduce: it means, though, that there are circumstances where
results will be pretty unpredictable (but no surprise, according to
your post)... :-|


> Your other option is to do Date() based timing.  That will work great in
> Gecko.  It'll work really badly for short time intervals in webkit-based
> browsers, since they update their date in 15ms increments (and don't
> consider that a bug).  I have no idea how well it works in Opera or IE.

Thanks for bringing this into discussion. I've added a link to this
thread from the thread [1] which referred some profiling based in
these timing mechanisms :-)


Best regards,

Helder Magalhães


[1] http://tech.groups.yahoo.com/group/svg-developers/message/61612

Rick

unread,
Dec 16, 2008, 6:20:05 PM12/16/08
to HelderMagalhaes, dev-te...@lists.mozilla.org
On Tue, Dec 16, 2008 at 12:19 PM, HelderMagalhaes
<helder.m...@gmail.com> wrote:
>> In Gecko, you're wrong, in that the timer is reset based on when it
>> fired, not when the callback returned.
>
> Thanks for clearing this up. I guess my thinking was quite a bit
> biased... Of course this makes much more sense. ;-)
>

I was curious about that for other reasons, so yes, thanks for
clearing that up. Lurking works.

--
Cheers!
Rick

0 new messages