[Drawkit] Transforms / ScaleBy
Graham Cox
graham.cox at bigpond.com
Tue Apr 7 16:35:35 PDT 2009
On 08/04/2009, at 8:45 AM, Michael Caron wrote:
> Hi all,
>
> I'm trying to understand the use of Affine Transforms through the
> use of DKLayer::applyTransformToObjects. Let me give some context.
>
> So I have a Drawing with a grid layer, a guide layer and a drawing
> layer. The grid layer is setup to use a centimeter span. I
> programatically add some DK objects like a few DKDrawablePaths, a
> few DKArcPaths. At the end of adding objects, I get the bounding box
> for the layer. Then I create an Affine Transform to scale everything
> by 1000 (to go to cm to mm). I'm a bit surprised to find it doesn't
> work as I thought.
>
> Bounding Box Before Transform:
> x = 16.023.9811
> y = 15.9680157
> w = 18.1520519
> h = 18.1520519
>
> Transform:
> NSAffineTransform* txfm = [NSAffineTransform transform];
> [txfm scaleBy: 1000];
> [currentLayer applyTransformToObjects:txfm];
>
> Bounding Box After Transform:
> x = 25086.7695
> y = 25030.8047
> w = 26.4765625
> h = 26.4765625
>
> I would have expected the size of the bounding box to scale by 1000
> if the shapes contained in it scale by 1000. Thus yielding a
> bounding box like this:
>
> x = 16023.9811
> y = 15968.0157
> w = 18152.0519
> h = 18152.0519
>
> Am I missing something here? Did the transform take the grid into
> consideration when scaling? I expected that it would simply rescale
> in quartz.
>
Firstly, there are 10mm in 1 cm, so surely you only want to scale by 10?
Secondly, transforms affect the coordinate system as a whole, so you
must always be mindful of where the origin is and how objects are
located with respect to it. Just scaling without taking that into
account is rarely enough. In this case you probably would need to
treat the top, left of your original bounding box as the origin so
that the objects are all repositioned and sized relative to that
point. Then you should find that the resulting bounding box ends up as
you expected. This involves:
1. create an empty (identity) transform
2. translate by -x, -y to the origin.
3. scale by 10 (or whatever)
4. translate by x, y to undo step 1.
5. apply the transform.
The -applyTransformToObjects: method doesn't take into account the
grid. In fact, the grid really has very little involvement with the
internal structure of DK. What it does is provide a reference grid
that is meaningful to the user, so that sizes and positions can be
reported/displayed relative to that grid. Internally all drawing is
done using native Quartz units, always. Therefore you could simply
recalibrate the grid to convert objects from mm to cm. They wouldn't
need to move or change size, you just call them something else. The
view zoom factor can be changed to make them appear larger.
--Graham
More information about the Drawkit
mailing list