[cairo] Extents under rotation
psychon at znc.in
Sat Dec 7 10:22:18 PST 2013
On 07.12.2013 08:31, Donn wrote:
> On 06/12/2013 17:13, Bill Spitzak wrote:
>> The matrices are multiplied before this is done, so this error does not
>> accumulate. For instance if you rotate by 45 degrees and then back by 45
>> degrees, it will act like a rotation of 0 and produce your expected
>> bounding box, rather than enlarging the bounding box twice.
> I'm sure I will face these things soon when I institute picking beyond a
> basic bbox hit approach.
That sounds like it could be a job for cairo_in_fill/stroke/clip(), but that
does not tell you which part of the path/clip was hit.
> Bill, Do you have a way to draw a tight bbox in user-space around a path?
> I have tried various things like getting the extents in device space (by
> doing a identity_matrix call before extents) and then using device_to_user
> on each returned x,y coordinate -- in order to try get those corners *in
> user space* and I just can't get it right.
Doesn't this result in a non-axis-aligned rectangle? Anyway, if I had to do
this, I would try something like this:
/* Helper function to save some variable assignments */
void device_to_user_line(cairo_t *cr, double x, double y)
cairo_device_to_user (cr, &x, &y);
cairo_line_to (cr, x, y);
double x1, y1, x2, y2;
double x, y;
cairo_path_extents (cr, &x1, &y1, &x2, &y2);
/* Make sure there is no current path and the next line_to becomes a move */
/* Top left corner */
device_to_user_line (cr, x1, y1);
/* Top right corner */
device_to_user_line (cr, x2, y1);
/* Bottom right corner */
device_to_user_line (cr, x2, y2);
/* Bottom left corner */
device_to_user_line (cr, x1, y2);
(Disclaimer: completely untested)
> I'd like to draw an X shape over my original path: At first I have a
> complex shape - so I want to measure extents and thereafter substitute a
> simple X shape [*] that can be drawn quickly(into user/local space) and
> re-measured by extents in the future.
> [*] X from top-left to bottom-right and reverse. Or just a rect, or just
> four dots in the bbox corners.
Uhm. So the above code should do just this, right?
"For saving the Earth.. and eating cheesecake!"
More information about the cairo