--- The translation matrix that should be applied to a given point when
--- doing the decoration.
-function translation(bbox, point)
- local dx = 0
- local dy = 0
- if (point.x > 0) then
- dx = dx + bbox:width()
- end
- if (point.y > 0) then
- dy = dy + bbox:height()
+-- Resizes a given shape such that the same transformation also
+-- transforms bbox_source to bbox_target. The transformation is done
+-- by translating points of the shape such that all points in the same
+-- quadrant with respect to center are translated in the same way.
+--
+-- Clearly, the center has to lie inside bbox_source.
+function resize_shape(shape, center, bbox_source, bbox_target)
+ -- assert that the center lies inside bbox_source
+ assert(bbox_source:left() < center.x)
+ assert(center.x < bbox_source:left() + bbox_source:width())
+ assert(bbox_source:bottom() < center.y)
+ assert(center.y < bbox_source:bottom() + bbox_source:height())
+
+ -- translation of points to the left/right/top/bottom of the center
+ local dx_left = bbox_target:left() - bbox_source:left()
+ local dy_bottom = bbox_target:bottom() - bbox_source:bottom()
+ local dx_right = bbox_target:width() - bbox_source:width()
+ local dy_top = bbox_target:height() - bbox_source:height()
+
+ -- transformation
+ local matrix_func = function (point)
+ local dx = dx_left
+ local dy = dy_bottom
+ if (center.x < point.x) then dx = dx + dx_right end
+ if (center.y < point.y) then dy = dy + dy_top end
+ return ipe.Translation(dx, dy)