Flutter Impeller
round_rect.h
Go to the documentation of this file.
1 // Copyright 2013 The Flutter Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef FLUTTER_IMPELLER_GEOMETRY_ROUND_RECT_H_
6 #define FLUTTER_IMPELLER_GEOMETRY_ROUND_RECT_H_
7 
13 
14 namespace impeller {
15 
16 struct RoundRect {
17  RoundRect() = default;
18 
19  inline static RoundRect MakeRect(const Rect& rect) {
20  return MakeRectRadii(rect, RoundingRadii());
21  }
22 
23  inline static RoundRect MakeOval(const Rect& rect) {
24  return MakeRectRadii(rect, RoundingRadii::MakeRadii(rect.GetSize() * 0.5f));
25  }
26 
27  inline static RoundRect MakeRectRadius(const Rect& rect, Scalar radius) {
28  return MakeRectRadii(rect, RoundingRadii::MakeRadius(radius));
29  }
30 
31  inline static RoundRect MakeRectXY(const Rect& rect,
32  Scalar x_radius,
33  Scalar y_radius) {
34  return MakeRectRadii(rect,
35  RoundingRadii::MakeRadii(Size(x_radius, y_radius)));
36  }
37 
38  inline static RoundRect MakeRectXY(const Rect& rect, Size corner_radii) {
39  return MakeRectRadii(rect, RoundingRadii::MakeRadii(corner_radii));
40  }
41 
42  inline static RoundRect MakeNinePatch(const Rect& rect,
43  Scalar left,
44  Scalar top,
45  Scalar right,
46  Scalar bottom) {
47  return MakeRectRadii(
48  rect, RoundingRadii::MakeNinePatch(left, top, right, bottom));
49  }
50 
51  static RoundRect MakeRectRadii(const Rect& rect, const RoundingRadii& radii);
52 
53  constexpr const Rect& GetBounds() const { return bounds_; }
54 
55  constexpr const RoundingRadii& GetRadii() const { return radii_; }
56 
57  [[nodiscard]] constexpr bool IsFinite() const {
58  return bounds_.IsFinite() && //
59  radii_.top_left.IsFinite() && //
60  radii_.top_right.IsFinite() && //
61  radii_.bottom_left.IsFinite() && //
62  radii_.bottom_right.IsFinite();
63  }
64 
65  [[nodiscard]] constexpr bool IsEmpty() const { return bounds_.IsEmpty(); }
66 
67  [[nodiscard]] constexpr bool IsRect() const {
68  return !bounds_.IsEmpty() && radii_.AreAllCornersEmpty();
69  }
70 
71  [[nodiscard]] constexpr bool IsOval() const {
72  return !bounds_.IsEmpty() && radii_.AreAllCornersSame() &&
74  bounds_.GetWidth() * 0.5f) &&
76  bounds_.GetHeight() * 0.5f);
77  }
78 
79  /// @brief Returns true iff the provided point |p| is inside the
80  /// half-open interior of this rectangle.
81  ///
82  /// For purposes of containment, a rectangle contains points
83  /// along the top and left edges but not points along the
84  /// right and bottom edges so that a point is only ever
85  /// considered inside one of two abutting rectangles.
86  [[nodiscard]] bool Contains(const Point& p) const;
87 
88  /// @brief Returns a new round rectangle translated by the given offset.
89  [[nodiscard]] inline RoundRect Shift(Scalar dx, Scalar dy) const {
90  // Just in case, use the factory rather than the internal constructor
91  // as shifting the rectangle may increase/decrease its bit precision
92  // so we should re-validate the radii to the newly located rectangle.
93  return MakeRectRadii(bounds_.Shift(dx, dy), radii_);
94  }
95 
96  /// @brief Returns a round rectangle with expanded edges. Negative expansion
97  /// results in shrinking.
98  [[nodiscard]] inline RoundRect Expand(Scalar left,
99  Scalar top,
100  Scalar right,
101  Scalar bottom) const {
102  // Use the factory rather than the internal constructor as the changing
103  // size of the rectangle requires that we re-validate the radii to the
104  // newly sized rectangle.
105  return MakeRectRadii(bounds_.Expand(left, top, right, bottom), radii_);
106  }
107 
108  /// @brief Returns a round rectangle with expanded edges. Negative expansion
109  /// results in shrinking.
110  [[nodiscard]] inline RoundRect Expand(Scalar horizontal,
111  Scalar vertical) const {
112  // Use the factory rather than the internal constructor as the changing
113  // size of the rectangle requires that we re-validate the radii to the
114  // newly sized rectangle.
115  return MakeRectRadii(bounds_.Expand(horizontal, vertical), radii_);
116  }
117 
118  /// @brief Returns a round rectangle with expanded edges. Negative expansion
119  /// results in shrinking.
120  [[nodiscard]] inline RoundRect Expand(Scalar amount) const {
121  // Use the factory rather than the internal constructor as the changing
122  // size of the rectangle requires that we re-validate the radii to the
123  // newly sized rectangle.
124  return MakeRectRadii(bounds_.Expand(amount), radii_);
125  }
126 
127  [[nodiscard]] constexpr bool operator==(const RoundRect& rr) const {
128  return bounds_ == rr.bounds_ && radii_ == rr.radii_;
129  }
130 
131  [[nodiscard]] constexpr bool operator!=(const RoundRect& r) const {
132  return !(*this == r);
133  }
134 
135  private:
136  constexpr RoundRect(const Rect& bounds, const RoundingRadii& radii)
137  : bounds_(bounds), radii_(radii) {}
138 
139  Rect bounds_;
140  RoundingRadii radii_;
141 
142  // Helps with RoundRectPathSource and DiffRoundRectPathSource
143  void Dispatch(PathReceiver& receiver) const;
144 
145  friend class RoundRectPathSource;
147 };
148 
150  public:
151  explicit RoundRectPathSource(const RoundRect& round_rect);
152 
154 
155  const RoundRect& GetRoundRect() const { return round_rect_; }
156 
157  // |PathSource|
158  FillType GetFillType() const override;
159 
160  // |PathSource|
161  Rect GetBounds() const override;
162 
163  // |PathSource|
164  bool IsConvex() const override;
165 
166  // |PathSource|
167  void Dispatch(PathReceiver& receiver) const override;
168 
169  private:
170  const RoundRect round_rect_;
171 };
172 
174  public:
175  explicit DiffRoundRectPathSource(const RoundRect& outer,
176  const RoundRect& inner);
177 
179 
180  const RoundRect& GetOuter() const { return outer_; }
181  const RoundRect& GetInner() const { return inner_; }
182 
183  // |PathSource|
184  FillType GetFillType() const override;
185 
186  // |PathSource|
187  Rect GetBounds() const override;
188 
189  // |PathSource|
190  bool IsConvex() const override;
191 
192  // |PathSource|
193  void Dispatch(PathReceiver& receiver) const override;
194 
195  private:
196  const RoundRect outer_;
197  const RoundRect inner_;
198 };
199 
200 } // namespace impeller
201 
202 namespace std {
203 
204 inline std::ostream& operator<<(std::ostream& out,
205  const impeller::RoundRect& rr) {
206  out << "(" //
207  << "rect: " << rr.GetBounds() << ", " //
208  << "radii: " << rr.GetRadii() //
209  << ")";
210  return out;
211 }
212 
213 } // namespace std
214 
215 #endif // FLUTTER_IMPELLER_GEOMETRY_ROUND_RECT_H_
const RoundRect & GetInner() const
Definition: round_rect.h:181
DiffRoundRectPathSource(const RoundRect &outer, const RoundRect &inner)
Definition: round_rect.cc:145
Rect GetBounds() const override
Definition: round_rect.cc:155
bool IsConvex() const override
Definition: round_rect.cc:159
void Dispatch(PathReceiver &receiver) const override
Definition: round_rect.cc:163
FillType GetFillType() const override
Definition: round_rect.cc:151
const RoundRect & GetOuter() const
Definition: round_rect.h:180
Collection of functions to receive path segments from the underlying path representation via the DlPa...
Definition: path_source.h:42
RoundRectPathSource(const RoundRect &round_rect)
Definition: round_rect.cc:124
Rect GetBounds() const override
Definition: round_rect.cc:133
bool IsConvex() const override
Definition: round_rect.cc:137
void Dispatch(PathReceiver &receiver) const override
Definition: round_rect.cc:141
const RoundRect & GetRoundRect() const
Definition: round_rect.h:155
FillType GetFillType() const override
Definition: round_rect.cc:129
float Scalar
Definition: scalar.h:19
TRect< Scalar > Rect
Definition: rect.h:792
TSize< Scalar > Size
Definition: size.h:159
constexpr bool ScalarNearlyEqual(Scalar x, Scalar y, Scalar tolerance=kEhCloseEnough)
Definition: scalar.h:36
Definition: comparable.h:95
std::ostream & operator<<(std::ostream &out, const impeller::Arc &a)
Definition: arc.h:141
constexpr bool IsFinite() const
Definition: round_rect.h:57
static RoundRect MakeRectRadius(const Rect &rect, Scalar radius)
Definition: round_rect.h:27
constexpr const RoundingRadii & GetRadii() const
Definition: round_rect.h:55
static RoundRect MakeRectRadii(const Rect &rect, const RoundingRadii &radii)
Definition: round_rect.cc:9
RoundRect Expand(Scalar amount) const
Returns a round rectangle with expanded edges. Negative expansion results in shrinking.
Definition: round_rect.h:120
static RoundRect MakeNinePatch(const Rect &rect, Scalar left, Scalar top, Scalar right, Scalar bottom)
Definition: round_rect.h:42
constexpr bool IsEmpty() const
Definition: round_rect.h:65
constexpr bool operator==(const RoundRect &rr) const
Definition: round_rect.h:127
static RoundRect MakeOval(const Rect &rect)
Definition: round_rect.h:23
static RoundRect MakeRectXY(const Rect &rect, Scalar x_radius, Scalar y_radius)
Definition: round_rect.h:31
constexpr bool IsRect() const
Definition: round_rect.h:67
RoundRect Expand(Scalar left, Scalar top, Scalar right, Scalar bottom) const
Returns a round rectangle with expanded edges. Negative expansion results in shrinking.
Definition: round_rect.h:98
static RoundRect MakeRectXY(const Rect &rect, Size corner_radii)
Definition: round_rect.h:38
constexpr bool operator!=(const RoundRect &r) const
Definition: round_rect.h:131
bool Contains(const Point &p) const
Returns true iff the provided point |p| is inside the half-open interior of this rectangle.
Definition: round_rect.cc:73
RoundRect Expand(Scalar horizontal, Scalar vertical) const
Returns a round rectangle with expanded edges. Negative expansion results in shrinking.
Definition: round_rect.h:110
constexpr const Rect & GetBounds() const
Definition: round_rect.h:53
constexpr bool IsOval() const
Definition: round_rect.h:71
static RoundRect MakeRect(const Rect &rect)
Definition: round_rect.h:19
RoundRect Shift(Scalar dx, Scalar dy) const
Returns a new round rectangle translated by the given offset.
Definition: round_rect.h:89
constexpr static RoundingRadii MakeNinePatch(Scalar left, Scalar top, Scalar right, Scalar bottom)
constexpr bool AreAllCornersEmpty() const
constexpr static RoundingRadii MakeRadii(Size radii)
constexpr bool AreAllCornersSame(Scalar tolerance=kEhCloseEnough) const
constexpr static RoundingRadii MakeRadius(Scalar radius)
constexpr TRect< T > Expand(T left, T top, T right, T bottom) const
Returns a rectangle with expanded edges. Negative expansion results in shrinking.
Definition: rect.h:622
constexpr Type GetHeight() const
Returns the height of the rectangle, equivalent to |GetSize().height|.
Definition: rect.h:351
constexpr bool IsEmpty() const
Returns true if either of the width or height are 0, negative, or NaN.
Definition: rect.h:301
constexpr TSize< Type > GetSize() const
Returns the size of the rectangle which may be negative in either width or height and may have been c...
Definition: rect.h:331
IsFinite() const
Returns true if all of the fields of this floating point rectangle are finite.
Definition: rect.h:292
constexpr TRect< T > Shift(T dx, T dy) const
Returns a new rectangle translated by the given offset.
Definition: rect.h:606
constexpr Type GetWidth() const
Returns the width of the rectangle, equivalent to |GetSize().width|.
Definition: rect.h:345
Type height
Definition: size.h:29
Type width
Definition: size.h:28
IsFinite() const
Definition: size.h:126