- From: Philip Taylor <excors+whatwg@gmail.com>
- Date: Tue, 3 Jul 2007 21:21:40 +0100
For the 'arc' function: What if startAngle = endAngle? What if endAngle > 2? + startAngle? (The endAngle = 2? + startAngle case isn't interesting since floating-point imprecision means it will never occur.) In practice: (see the left half of <http://canvex.lazyilluminati.com/misc/arc.html> for a (unhelpfully unlabelled) random collection of examples) If startAngle = endAngle: Firefox (2+3), Safari (3): Nothing is drawn. Opera (9.2+9.5): If anticlockwise = true, a full circle is drawn; otherwise, nothing is drawn. If endAngle > startAngle + 2?: Opera is weird and buggy and would require too much effort to analyse. Firefox and Safari mostly match: (Assume startAngle = 0 in all the following) If endAngle = 2? + ? [where ? is a small positive real number]: A full circle is drawn. If endAngle = 3? - ?: If anticlockwise, 0 to -? is drawn; otherwise a full circle is drawn, and the 0 to ? part is drawn twice (i.e. drawn on top of itself, which is visible due to antialiasing effects). If endAngle = 2n? - ? for integer n > 1: If anticlockwise, nothing is drawn; otherwise: Firefox: A full circle is drawn twice. Safari: A full circle is drawn n times. (Swapping startAngle vs endAngle is equivalent to swapping clockwise vs anticlockwise.) So, for FF/Safari: When startAngle -> endAngle is in the opposite direction to the (anti)clockwise flag, the two angles are treated modulo 2? and the arc is drawn between them in the appropriate direction. When it's the same direction as the (anti)clockwise flag, Safari extends the path all the way from startAngle to endAngle (going round the whole circle multiple times if necessary), and Firefox does the same except it skips all but the first full going-round-the-whole-circle bit (so it goes round 1 <= n < 2 times, if abs(startAngle-endAngle) > 2?). It seems sensible to adopt either Firefox's or Safari's approach (which differ only in the amount of overdraw). It's probably easier to use Firefox's, so then Safari would just have to mod the angles a little before drawing them, because I can't see any other reason to choose one approach over the other, and I can't see any reason to choose a totally different approach. Talking about arcs is confusing when the arc is more than a full circle and wraps around itself and isn't really a mathematical arc any more, so I think it's necessary to not define the operation in terms of arcs. The best I can think of is: """ Let da = endAngle - startAngle. If anticlockwise is true, and da > 0 or da < -2?, then let d = (da % 2?) - 2?. If anticlockwise is false, and da < 0 or da > 2?, then let d = (da % 2?) + 2?. If neither of these cases applies, then let d = (da % 2?). In this algorithm, the % operator is defined to have the same semantics as the ECMAScript % operator. The arc is defined by the points (radius*cos(a), radius*sin(a)) for all a between startAngle and startAngle + d. The points at a = startAngle and at a = startAngle + d are the path's start and end points respectively. """ (The relevance of using the ECMAScript % operator is that (-3) % 2 = -1, etc, so it handles negative numbers (and floating-point numbers) in the way that is needed here, and I can't think of a better way to say the same thing that's still as well-defined and not horribly verbose.) The right half of <http://canvex.lazyilluminati.com/misc/arc.html> is implemented as above, and gives exactly the same behaviour as FF in all the cases I have tried. -- Philip Taylor excors at gmail.com
Received on Tuesday, 3 July 2007 13:21:40 UTC