diff options
| author | Jabier Arraiza Cenoz <jabier.arraiza@marker.es> | 2016-03-15 21:57:03 +0000 |
|---|---|---|
| committer | Jabiertxof <jtx@jtx.marker.es> | 2016-03-15 21:57:03 +0000 |
| commit | 6bd1c2a30b66e15fe055b22bd47dadb771f7fae2 (patch) | |
| tree | 1b991cc2736f84fb069666802d485bd29cff6394 /src/2geom/rect.cpp | |
| parent | Update to limit options to radius = 0, radious > 0 or both (diff) | |
| parent | fix-bug-1557192. paint-order crash with multiple items (diff) | |
| download | inkscape-6bd1c2a30b66e15fe055b22bd47dadb771f7fae2.tar.gz inkscape-6bd1c2a30b66e15fe055b22bd47dadb771f7fae2.zip | |
Update to trunk
(bzr r13645.1.119)
Diffstat (limited to 'src/2geom/rect.cpp')
| -rw-r--r-- | src/2geom/rect.cpp | 78 |
1 files changed, 78 insertions, 0 deletions
diff --git a/src/2geom/rect.cpp b/src/2geom/rect.cpp index 383e72c8e..5a821e9f9 100644 --- a/src/2geom/rect.cpp +++ b/src/2geom/rect.cpp @@ -30,9 +30,56 @@ */ #include <2geom/rect.h> +#include <2geom/transforms.h> namespace Geom { +Point align_factors(Align g) { + Point p; + switch (g) { + case ALIGN_XMIN_YMIN: + p[X] = 0.0; + p[Y] = 0.0; + break; + case ALIGN_XMID_YMIN: + p[X] = 0.5; + p[Y] = 0.0; + break; + case ALIGN_XMAX_YMIN: + p[X] = 1.0; + p[Y] = 0.0; + break; + case ALIGN_XMIN_YMID: + p[X] = 0.0; + p[Y] = 0.5; + break; + case ALIGN_XMID_YMID: + p[X] = 0.5; + p[Y] = 0.5; + break; + case ALIGN_XMAX_YMID: + p[X] = 1.0; + p[Y] = 0.5; + break; + case ALIGN_XMIN_YMAX: + p[X] = 0.0; + p[Y] = 1.0; + break; + case ALIGN_XMID_YMAX: + p[X] = 0.5; + p[Y] = 1.0; + break; + case ALIGN_XMAX_YMAX: + p[X] = 1.0; + p[Y] = 1.0; + break; + default: + break; + } + return p; +} + + /** @brief Transform the rectangle by an affine. * The result of the transformation might not be axis-aligned. The return value * of this operation will be the smallest axis-aligned rectangle containing @@ -49,6 +96,37 @@ Rect &Rect::operator*=(Affine const &m) { return *this; } +Affine Rect::transformTo(Rect const &viewport, Aspect const &aspect) const +{ + // 1. translate viewbox to origin + Geom::Affine total = Translate(-min()); + + // 2. compute scale + Geom::Point vdims = viewport.dimensions(); + Geom::Point dims = dimensions(); + Geom::Scale scale(vdims[X] / dims[X], vdims[Y] / dims[Y]); + + if (aspect.align == ALIGN_NONE) { + // apply non-uniform scale + total *= scale * Translate(viewport.min()); + } else { + double uscale = 0; + if (aspect.expansion == EXPANSION_MEET) { + uscale = std::min(scale[X], scale[Y]); + } else { + uscale = std::max(scale[X], scale[Y]); + } + scale = Scale(uscale); + + // compute offset for align + Geom::Point offset = vdims - dims * scale; + offset *= Scale(align_factors(aspect.align)); + total *= scale * Translate(viewport.min() + offset); + } + + return total; +} + Coord distanceSq(Point const &p, Rect const &rect) { double dx = 0, dy = 0; |
