diff options
Diffstat (limited to 'ui/gfx/geometry/axis_transform2d.h')
-rw-r--r-- | ui/gfx/geometry/axis_transform2d.h | 138 |
1 files changed, 138 insertions, 0 deletions
diff --git a/ui/gfx/geometry/axis_transform2d.h b/ui/gfx/geometry/axis_transform2d.h new file mode 100644 index 0000000000..1829bf60fc --- /dev/null +++ b/ui/gfx/geometry/axis_transform2d.h @@ -0,0 +1,138 @@ +// Copyright (c) 2017 The Chromium Authors. All rights reserved. +// Use of this source code is governed by a BSD-style license that can be +// found in the LICENSE file. + +#ifndef UI_GFX_GEOMETRY_AXIS_TRANSFORM2D_H_ +#define UI_GFX_GEOMETRY_AXIS_TRANSFORM2D_H_ + +#include "ui/gfx/geometry/rect_f.h" +#include "ui/gfx/geometry/vector2d_f.h" +#include "ui/gfx/gfx_export.h" + +namespace gfx { + +// This class implements the subset of 2D linear transforms that only +// translation and uniform scaling are allowed. +// Internally this is stored as a scalar pre-scale factor, and a vector +// for post-translation. The class constructor and member accessor follows +// the same convention. +class GFX_EXPORT AxisTransform2d { + public: + constexpr AxisTransform2d() = default; + constexpr AxisTransform2d(float scale, const Vector2dF& translation) + : scale_(scale), translation_(translation) {} + + bool operator==(const AxisTransform2d& other) const { + return scale_ == other.scale_ && translation_ == other.translation_; + } + bool operator!=(const AxisTransform2d& other) const { + return !(*this == other); + } + + void PreScale(float scale) { scale_ *= scale; } + void PostScale(float scale) { + scale_ *= scale; + translation_.Scale(scale); + } + void PreTranslate(const Vector2dF& translation) { + translation_ += ScaleVector2d(translation, scale_); + } + void PostTranslate(const Vector2dF& translation) { + translation_ += translation; + } + + void PreConcat(const AxisTransform2d& pre) { + PreTranslate(pre.translation_); + PreScale(pre.scale_); + } + void PostConcat(const AxisTransform2d& post) { + PostScale(post.scale_); + PostTranslate(post.translation_); + } + + void Invert() { + DCHECK(scale_); + scale_ = 1.f / scale_; + translation_.Scale(-scale_); + } + + PointF MapPoint(const PointF& p) const { + return ScalePoint(p, scale_) + translation_; + } + PointF InverseMapPoint(const PointF& p) const { + return ScalePoint(p - translation_, 1.f / scale_); + } + + RectF MapRect(const RectF& r) const { + DCHECK(scale_ >= 0.f); + return ScaleRect(r, scale_) + translation_; + } + RectF InverseMapRect(const RectF& r) const { + DCHECK(scale_ > 0.f); + return ScaleRect(r - translation_, 1.f / scale_); + } + + float scale() const { return scale_; } + const Vector2dF& translation() const { return translation_; } + + std::string ToString() const; + + private: + // Scale is applied before translation, i.e. + // this->Transform(p) == scale_ * p + translation_ + float scale_ = 1.f; + Vector2dF translation_; +}; + +static inline AxisTransform2d PreScaleAxisTransform2d(const AxisTransform2d& t, + float scale) { + AxisTransform2d result(t); + result.PreScale(scale); + return result; +} + +static inline AxisTransform2d PostScaleAxisTransform2d(const AxisTransform2d& t, + float scale) { + AxisTransform2d result(t); + result.PostScale(scale); + return result; +} + +static inline AxisTransform2d PreTranslateAxisTransform2d( + const AxisTransform2d& t, + const Vector2dF& translation) { + AxisTransform2d result(t); + result.PreTranslate(translation); + return result; +} + +static inline AxisTransform2d PostTranslateAxisTransform2d( + const AxisTransform2d& t, + const Vector2dF& translation) { + AxisTransform2d result(t); + result.PostTranslate(translation); + return result; +} + +static inline AxisTransform2d ConcatAxisTransform2d( + const AxisTransform2d& post, + const AxisTransform2d& pre) { + AxisTransform2d result(post); + result.PreConcat(pre); + return result; +} + +static inline AxisTransform2d InvertAxisTransform2d(const AxisTransform2d& t) { + AxisTransform2d result = t; + result.Invert(); + return result; +} + +// This is declared here for use in gtest-based unit tests but is defined in +// the //ui/gfx:test_support target. Depend on that to use this in your unit +// test. This should not be used in production code - call ToString() instead. +void PrintTo(const AxisTransform2d&, ::std::ostream* os); + +} // namespace gfx + +#endif // UI_GFX_GEOMETRY_AXIS_TRANSFORM2D_H_ |