• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021 Huawei Device Co., Ltd.
3  * Licensed under the Apache License, Version 2.0 (the "License");
4  * you may not use this file except in compliance with the License.
5  * You may obtain a copy of the License at
6  *
7  *     http://www.apache.org/licenses/LICENSE-2.0
8  *
9  * Unless required by applicable law or agreed to in writing, software
10  * distributed under the License is distributed on an "AS IS" BASIS,
11  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12  * See the License for the specific language governing permissions and
13  * limitations under the License.
14  */
15 
16 #include "common/rs_obj_abs_geometry.h"
17 
18 #ifndef USE_ROSEN_DRAWING
19 #include "include/utils/SkCamera.h"
20 #ifdef NEW_SKIA
21 #include "include/core/SkM44.h"
22 #else
23 #include "include/core/SkMatrix44.h"
24 #endif
25 #else // USE_ROSEN_DRAWING
26 #include "utils/camera3d.h"
27 #include "utils/matrix44.h"
28 #endif
29 
30 namespace OHOS {
31 namespace Rosen {
32 constexpr unsigned RECT_POINT_NUM = 4;
33 constexpr unsigned LEFT_TOP_POINT = 0;
34 constexpr unsigned RIGHT_TOP_POINT = 1;
35 constexpr unsigned RIGHT_BOTTOM_POINT = 2;
36 constexpr unsigned LEFT_BOTTOM_POINT = 3;
37 constexpr float INCH_TO_PIXEL = 72;
38 constexpr float EPSILON = 1e-4f;
39 constexpr float DEGREE_TO_RADIAN = M_PI / 180;
40 
41 RSObjAbsGeometry::RSObjAbsGeometry() = default;
42 RSObjAbsGeometry::~RSObjAbsGeometry() = default;
43 
44 #ifndef USE_ROSEN_DRAWING
ConcatMatrix(const SkMatrix & matrix)45 void RSObjAbsGeometry::ConcatMatrix(const SkMatrix& matrix)
46 {
47     if (matrix.isIdentity()) {
48         return;
49     }
50     matrix_.preConcat(matrix);
51     if (absMatrix_.has_value()) {
52         absMatrix_->preConcat(matrix);
53     }
54     SetAbsRect();
55 }
56 #else
ConcatMatrix(const Drawing::Matrix & matrix)57 void RSObjAbsGeometry::ConcatMatrix(const Drawing::Matrix& matrix)
58 {
59     if (matrix.IsIdentity()) {
60         return;
61     }
62     matrix_.PreConcat(matrix);
63     if (absMatrix_.has_value()) {
64         absMatrix_->PreConcat(matrix);
65     }
66     SetAbsRect();
67 }
68 #endif
69 
70 /**
71  * @brief Updates the matrix of the view with respect to its parent view.
72  *
73  * @param parent The parent view of the current view.
74  * @param offset The offset of the current view with respect to its parent.
75  * @param clipRect The optional clipping rectangle of the current view.
76  */
77 #ifndef USE_ROSEN_DRAWING
UpdateMatrix(const std::shared_ptr<RSObjAbsGeometry> & parent,const std::optional<SkPoint> & offset,const std::optional<SkRect> & clipRect)78 void RSObjAbsGeometry::UpdateMatrix(const std::shared_ptr<RSObjAbsGeometry>& parent,
79     const std::optional<SkPoint>& offset, const std::optional<SkRect>& clipRect)
80 #else
81 void RSObjAbsGeometry::UpdateMatrix(const std::shared_ptr<RSObjAbsGeometry>& parent,
82     const std::optional<Drawing::Point>& offset, const std::optional<Drawing::Rect>& clipRect)
83 #endif
84 {
85     // Initialize the absolute matrix with the absolute matrix of the parent view if the parent view exists
86     if (parent == nullptr) {
87         absMatrix_.reset();
88     } else {
89         absMatrix_ = parent->GetAbsMatrix();
90     }
91 #ifndef USE_ROSEN_DRAWING
92     if (absMatrix_.has_value() && offset.has_value() && !offset.value().isZero()) {
93         absMatrix_->preTranslate(offset->x(), offset->y());
94     }
95 #else
96     if (absMatrix_.has_value() && offset.has_value() && !offset.value().IsZero()) {
97         absMatrix_->PreTranslate(offset->GetX(), offset->GetY());
98     }
99 #endif
100     // Reset the matrix of the current view
101 #ifndef USE_ROSEN_DRAWING
102     matrix_.reset();
103 #else
104     matrix_.Reset();
105 #endif
106     // filter invalid width and height
107     if (IsEmpty()) {
108         return;
109     }
110     // If the view has no transformations or only 2D transformations, update the absolute matrix with 2D
111     // transformations
112     if (!trans_ || (ROSEN_EQ(trans_->translateZ_, 0.f) && ROSEN_EQ(trans_->rotationX_, 0.f) &&
113         ROSEN_EQ(trans_->rotationY_, 0.f) && trans_->quaternion_.IsIdentity())) {
114         UpdateAbsMatrix2D();
115     } else {
116         // Otherwise, update the absolute matrix with 3D transformations
117         UpdateAbsMatrix3D();
118     }
119     // If the absolute matrix of the current view exists, update it with the context matrix and the current matrix
120     if (absMatrix_.has_value()) {
121 #ifndef USE_ROSEN_DRAWING
122         if (contextMatrix_.has_value()) {
123             absMatrix_->preConcat(*contextMatrix_);
124         }
125         absMatrix_->preConcat(matrix_);
126 #else
127         if (contextMatrix_.has_value()) {
128             absMatrix_->PreConcat(*contextMatrix_);
129         }
130         absMatrix_->PreConcat(matrix_);
131 #endif
132     }
133     // if clipRect is valid, update rect with clipRect
134 #ifndef USE_ROSEN_DRAWING
135     if (clipRect.has_value() && !clipRect.value().isEmpty()) {
136 #else
137     if (clipRect.has_value() && !clipRect.value().IsEmpty()) {
138 #endif
139         auto mappedClipRect = clipRect.value();
140 #ifndef USE_ROSEN_DRAWING
141         if (!matrix_.isIdentity()) {
142             SkMatrix invertMatrix;
143             if (matrix_.invert(&invertMatrix)) {
144                 mappedClipRect = invertMatrix.mapRect(mappedClipRect);
145             }
146             // matrix_ already includes bounds offset, we need to revert it
147             mappedClipRect.offset(GetX(), GetY());
148         }
149 
150 #ifdef NEW_SKIA
151         if (!mappedClipRect.intersect({x_, y_, x_ + width_, y_ + height_})) {
152 #else
153         if (!mappedClipRect.intersect(x_, y_, x_ + width_, y_ + height_)) {
154 #endif
155             // No visible area
156             x_ = y_ = width_ = height_ = 0.0f;
157             return;
158         }
159         x_ = mappedClipRect.left();
160         y_ = mappedClipRect.top();
161         width_ = mappedClipRect.width();
162         height_ = mappedClipRect.height();
163 #else
164         if (!matrix_.IsIdentity()) {
165             Drawing::Matrix invertMatrix;
166             if (matrix_.Invert(invertMatrix)) {
167                 invertMatrix.MapRect(mappedClipRect, mappedClipRect);
168             }
169             // matrix_ already includes bounds offset, we need to revert it
170             mappedClipRect.Offset(GetX(), GetY());
171         }
172 
173         if (!mappedClipRect.Intersect({ x_, y_, x_ + width_, y_ + height_ })) {
174             // No visible area
175             x_ = y_ = width_ = height_ = 0.0f;
176             return;
177         }
178         x_ = mappedClipRect.GetLeft();
179         y_ = mappedClipRect.GetTop();
180         width_ = mappedClipRect.GetWidth();
181         height_ = mappedClipRect.GetHeight();
182 #endif
183     }
184     // If the context matrix of the current view exists, update the current matrix with it
185     if (contextMatrix_.has_value()) {
186 #ifndef USE_ROSEN_DRAWING
187         matrix_.preConcat(*contextMatrix_);
188 #else
189         matrix_.PreConcat(*contextMatrix_);
190 #endif
191     }
192     // Update the absolute rectangle of the current view
193     SetAbsRect();
194 }
195 
196 /**
197  * @brief Updates the matrix of the view without its parent view.
198  */
199 void RSObjAbsGeometry::UpdateByMatrixFromSelf()
200 {
201     absMatrix_.reset();
202 #ifndef USE_ROSEN_DRAWING
203     matrix_.reset();
204 #else
205     matrix_.Reset();
206 #endif
207 
208     // If the view has no transformations or only 2D transformations, update the absolute matrix with 2D transformations
209     if (!trans_ || (ROSEN_EQ(trans_->translateZ_, 0.f) && ROSEN_EQ(trans_->rotationX_, 0.f) &&
210         ROSEN_EQ(trans_->rotationY_, 0.f) && trans_->quaternion_.IsIdentity())) {
211         UpdateAbsMatrix2D();
212     } else {
213         // Otherwise, update the absolute matrix with 3D transformations
214         UpdateAbsMatrix3D();
215     }
216 
217     // If the context matrix of the view exists, update the current matrix with it
218     if (contextMatrix_.has_value()) {
219 #ifndef USE_ROSEN_DRAWING
220         matrix_.preConcat(*contextMatrix_);
221 #else
222         matrix_.PreConcat(*contextMatrix_);
223 #endif
224     }
225 
226     // Update the absolute rectangle of the view
227     SetAbsRect();
228 }
229 
230 bool RSObjAbsGeometry::IsNeedClientCompose() const
231 {
232     if (!trans_) {
233         return false;
234     }
235     // return false if rotation degree is times of 90
236     return !ROSEN_EQ(std::remainder(trans_->rotation_, 90.f), 0.f, EPSILON);
237 }
238 
239 void RSObjAbsGeometry::UpdateAbsMatrix2D()
240 {
241     if (!trans_) {
242 #ifndef USE_ROSEN_DRAWING
243         matrix_.preTranslate(x_, y_);
244 #else
245         matrix_.PreTranslate(x_, y_);
246 #endif
247     } else {
248         // Translate
249         if ((x_ + trans_->translateX_ != 0) || (y_ + trans_->translateY_ != 0)) {
250 #ifndef USE_ROSEN_DRAWING
251             matrix_.preTranslate(x_ + trans_->translateX_, y_ + trans_->translateY_);
252 #else
253             matrix_.PreTranslate(x_ + trans_->translateX_, y_ + trans_->translateY_);
254 #endif
255         }
256         // rotation
257         if (!ROSEN_EQ(trans_->rotation_, 0.f, EPSILON)) {
258 #ifndef USE_ROSEN_DRAWING
259             matrix_.preRotate(trans_->rotation_, trans_->pivotX_ * width_, trans_->pivotY_ * height_);
260 #else
261             matrix_.PreRotate(trans_->rotation_, trans_->pivotX_ * width_, trans_->pivotY_ * height_);
262 #endif
263         }
264         // Scale
265         if (!ROSEN_EQ(trans_->scaleX_, 1.f) || !ROSEN_EQ(trans_->scaleY_, 1.f)) {
266 #ifndef USE_ROSEN_DRAWING
267             matrix_.preScale(trans_->scaleX_, trans_->scaleY_, trans_->pivotX_ * width_, trans_->pivotY_ * height_);
268 #else
269             matrix_.PreScale(trans_->scaleX_, trans_->scaleY_, trans_->pivotX_ * width_, trans_->pivotY_ * height_);
270 #endif
271         }
272     }
273 }
274 
275 /**
276  * Update the absolute matrix in 3D space
277  */
278 void RSObjAbsGeometry::UpdateAbsMatrix3D()
279 {
280     // If the view has a non-identity quaternion, apply 3D transformations
281     if (!trans_->quaternion_.IsIdentity()) {
282 #ifndef USE_ROSEN_DRAWING
283         SkM44 matrix3D;
284         // Translate
285         matrix3D.setTranslate(trans_->pivotX_ * width_ + x_ + trans_->translateX_,
286             trans_->pivotY_ * height_ + y_ + trans_->translateY_, z_ + trans_->translateZ_);
287 #else // USE_ROSEN_DRAWING
288         Drawing::Matrix44 matrix3D;
289         // Translate
290         matrix3D.Translate(trans_->pivotX_ * width_ + x_ + trans_->translateX_,
291             trans_->pivotY_ * height_ + y_ + trans_->translateY_, z_ + trans_->translateZ_);
292 #endif
293         // Rotate
294         float x = trans_->quaternion_[0];
295         float y = trans_->quaternion_[1];
296         float z = trans_->quaternion_[2];
297         float w = trans_->quaternion_[3];
298 #ifndef USE_ROSEN_DRAWING
299         SkScalar r[16] = {
300             1.f - 2.f * (y * y + z * z), 2.f * (x * y + z * w), 2.f * (x * z - y * w), 0,
301             2.f * (x * y - z * w), 1.f - 2.f * (x * x + z * z), 2.f * (y * z + x * w), 0,
302             2.f * (x * z + y * w), 2.f * (y * z - x * w), 1.f - 2.f * (x * x + y * y), 0,
303             0, 0, 0, 1
304         };
305         SkM44 matrix4 = SkM44::ColMajor(r);
306 #else // USE_ROSEN_DRAWING
307         Drawing::Matrix44::Buffer buffer = {
308             1.f - 2.f * (y * y + z * z), 2.f * (x * y + z * w), 2.f * (x * z - y * w), 0,   // m00 ~ m30
309             2.f * (x * y - z * w), 1.f - 2.f * (x * x + z * z), 2.f * (y * z + x * w), 0,   // m01 ~ m31
310             2.f * (x * z + y * w), 2.f * (y * z - x * w), 1.f - 2.f * (x * x + y * y), 0,   // m02 ~ m32
311             0, 0, 0, 1 };                                                                   // m03 ~ m33
312         Drawing::Matrix44 matrix4;
313         matrix4.SetMatrix44ColMajor(buffer);
314 #endif
315         matrix3D = matrix3D * matrix4;
316         // Scale
317         if (!ROSEN_EQ(trans_->scaleX_, 1.f) || !ROSEN_EQ(trans_->scaleY_, 1.f)) {
318 #ifndef USE_ROSEN_DRAWING
319             matrix3D.preScale(trans_->scaleX_, trans_->scaleY_, 1.f);
320 #else
321             matrix3D.PreScale(trans_->scaleX_, trans_->scaleY_, 1.f);
322 #endif
323         }
324         // Translate
325 #ifndef USE_ROSEN_DRAWING
326         matrix3D.preTranslate(-trans_->pivotX_ * width_, -trans_->pivotY_ * height_, 0);
327 
328         // Concatenate the 3D matrix with the 2D matrix
329         matrix_.preConcat(matrix3D.asM33());
330 #else // USE_ROSEN_DRAWING
331         matrix3D.PreTranslate(-trans_->pivotX_ * width_, -trans_->pivotY_ * height_, 0);
332 
333         // Concatenate the 3D matrix with the 2D matrix
334         matrix_.PreConcat(matrix3D);
335 #endif
336     } else {
337 #ifndef USE_ROSEN_DRAWING
338         SkMatrix matrix3D;
339         Sk3DView camera;
340 
341         // Z Position
342         camera.translate(0, 0, z_ + trans_->translateZ_);
343         // Set camera distance
344         if (trans_->cameraDistance_ == 0) {
345             float zOffSet = sqrt(width_ * width_ + height_ * height_) / 2;
346             camera.setCameraLocation(0, 0, camera.getCameraLocationZ() - zOffSet / INCH_TO_PIXEL);
347         } else {
348             camera.setCameraLocation(0, 0, trans_->cameraDistance_);
349         }
350 
351         // Rotate
352         if (trans_->pivotZ_ != 0.f) {
353             camera.translate(-sin(trans_->rotationY_ * DEGREE_TO_RADIAN) * trans_->pivotZ_,
354                 -sin(trans_->rotationX_ * DEGREE_TO_RADIAN) * trans_->pivotZ_,
355                 (1 - cos(trans_->rotationX_ * DEGREE_TO_RADIAN) * cos(trans_->rotationY_ * DEGREE_TO_RADIAN)) *
356                     trans_->pivotZ_);
357         }
358         camera.rotateX(-trans_->rotationX_);
359         camera.rotateY(-trans_->rotationY_);
360         camera.rotateZ(-trans_->rotation_);
361         camera.getMatrix(&matrix3D);
362 #else
363         Drawing::Matrix matrix3D;
364         Drawing::Camera3D camera;
365         // Z Position
366         camera.Translate(0, 0, z_ + trans_->translateZ_);
367 
368         // Set camera distance
369         if (trans_->cameraDistance_ == 0) {
370             float zOffSet = sqrt(width_ * width_ + height_ * height_) / 2;
371             camera.SetCameraPos(0, 0, camera.GetCameraPosZ() - zOffSet / INCH_TO_PIXEL);
372         } else {
373             camera.SetCameraPos(0, 0, trans_->cameraDistance_);
374         }
375         // Rotate
376         if (trans_->pivotZ_ != 0.f) {
377             camera.Translate(-sin(trans_->rotationY_ * DEGREE_TO_RADIAN) * trans_->pivotZ_,
378                 -sin(trans_->rotationX_ * DEGREE_TO_RADIAN) * trans_->pivotZ_,
379                 (1 - cos(trans_->rotationX_ * DEGREE_TO_RADIAN) * cos(trans_->rotationY_ * DEGREE_TO_RADIAN)) *
380                     trans_->pivotZ_);
381         }
382         camera.RotateXDegrees(-trans_->rotationX_);
383         camera.RotateYDegrees(-trans_->rotationY_);
384         camera.RotateZDegrees(-trans_->rotation_);
385         camera.ApplyToMatrix(matrix3D);
386 #endif
387         // Scale
388         if (!ROSEN_EQ(trans_->scaleX_, 1.f) || !ROSEN_EQ(trans_->scaleY_, 1.f)) {
389 #ifndef USE_ROSEN_DRAWING
390             matrix3D.preScale(trans_->scaleX_, trans_->scaleY_);
391 #else
392             matrix3D.PreScale(trans_->scaleX_, trans_->scaleY_);
393 #endif
394         }
395         // Translate
396 #ifndef USE_ROSEN_DRAWING
397         matrix3D.preTranslate(-trans_->pivotX_ * width_, -trans_->pivotY_ * height_);
398 
399         // Concatenate the 3D matrix with the 2D matrix
400         matrix3D.postTranslate(
401             trans_->pivotX_ * width_ + x_ + trans_->translateX_, trans_->pivotY_ * height_ + y_ + trans_->translateY_);
402         matrix_.preConcat(matrix3D);
403 #else
404         matrix3D.PreTranslate(-trans_->pivotX_ * width_, -trans_->pivotY_ * height_);
405 
406         // Concatenate the 3D matrix with the 2D matrix
407         matrix3D.PostTranslate(
408             trans_->pivotX_ * width_ + x_ + trans_->translateX_, trans_->pivotY_ * height_ + y_ + trans_->translateY_);
409         matrix_.PreConcat(matrix3D);
410 #endif
411     }
412 }
413 
414 void RSObjAbsGeometry::SetAbsRect()
415 {
416     absRect_ = MapAbsRect(RectF(0.f, 0.f, width_, height_));
417 }
418 
419 /**
420  * Map the absolute rectangle
421  * @param rect the rectangle to map
422  * @return the mapped absolute rectangle
423  */
424 RectI RSObjAbsGeometry::MapAbsRect(const RectF& rect) const
425 {
426     RectI absRect;
427     auto& matrix = GetAbsMatrix();
428 #ifndef USE_ROSEN_DRAWING
429     // Check if the matrix has skew or negative scaling
430     if (!ROSEN_EQ(matrix.getSkewX(), 0.f) || (matrix.getScaleX() < 0) ||
431         !ROSEN_EQ(matrix.getSkewY(), 0.f) || (matrix.getScaleY() < 0)) {
432         // Map the rectangle's points to the absolute matrix
433         SkPoint p[RECT_POINT_NUM];
434         p[LEFT_TOP_POINT].set(rect.left_, rect.top_);
435         p[RIGHT_TOP_POINT].set(rect.left_ + rect.width_, rect.top_);
436         p[RIGHT_BOTTOM_POINT].set(rect.left_ + rect.width_, rect.top_ + rect.height_);
437         p[LEFT_BOTTOM_POINT].set(rect.left_, rect.top_ + rect.height_);
438         matrix.mapPoints(p, RECT_POINT_NUM);
439 
440         // Get the data range of the mapped points
441         Vector2f xRange = GetDataRange(p[LEFT_TOP_POINT].x(), p[RIGHT_TOP_POINT].x(),
442             p[RIGHT_BOTTOM_POINT].x(), p[LEFT_BOTTOM_POINT].x());
443         Vector2f yRange = GetDataRange(p[LEFT_TOP_POINT].y(), p[RIGHT_TOP_POINT].y(),
444             p[RIGHT_BOTTOM_POINT].y(), p[LEFT_BOTTOM_POINT].y());
445 #else
446     // Check if the matrix has skew or negative scaling
447     if (!ROSEN_EQ(matrix.Get(Drawing::Matrix::SKEW_X), 0.f) || (matrix.Get(Drawing::Matrix::SCALE_X) < 0) ||
448         !ROSEN_EQ(matrix.Get(Drawing::Matrix::SKEW_Y), 0.f) || (matrix.Get(Drawing::Matrix::SCALE_Y) < 0)) {
449         // Map the rectangle's points to the absolute matrix
450         std::vector<Drawing::Point> p(RECT_POINT_NUM);
451         p[LEFT_TOP_POINT] = {rect.left_, rect.top_};
452         p[RIGHT_TOP_POINT] = {rect.left_ + rect.width_, rect.top_};
453         p[RIGHT_BOTTOM_POINT] = {rect.left_ + rect.width_, rect.top_ + rect.height_};
454         p[LEFT_BOTTOM_POINT] = {rect.left_, rect.top_ + rect.height_};
455         matrix.MapPoints(p, p, RECT_POINT_NUM);
456 
457         Vector2f xRange = GetDataRange(p[LEFT_TOP_POINT].GetX(), p[RIGHT_TOP_POINT].GetX(),
458             p[RIGHT_BOTTOM_POINT].GetX(), p[LEFT_BOTTOM_POINT].GetX());
459         Vector2f yRange = GetDataRange(p[LEFT_TOP_POINT].GetY(), p[RIGHT_TOP_POINT].GetY(),
460             p[RIGHT_BOTTOM_POINT].GetY(), p[LEFT_BOTTOM_POINT].GetY());
461 #endif
462 
463         // Set the absolute rectangle's properties
464         absRect.left_ = static_cast<int>(xRange[0]);
465         absRect.top_ = static_cast<int>(yRange[0]);
466         absRect.width_ = static_cast<int>(std::ceil(xRange[1] - absRect.left_));
467         absRect.height_ = static_cast<int>(std::ceil(yRange[1] - absRect.top_));
468     } else {
469         // Calculate the absolute rectangle based on the matrix's translation and scaling
470 #ifndef USE_ROSEN_DRAWING
471         absRect.left_ = static_cast<int>(rect.left_ * matrix.getScaleX() + matrix.getTranslateX());
472         absRect.top_ = static_cast<int>(rect.top_ * matrix.getScaleY() + matrix.getTranslateY());
473         float right = (rect.left_ + rect.width_) * matrix.getScaleX() + matrix.getTranslateX();
474         float bottom = (rect.top_ + rect.height_) * matrix.getScaleY() + matrix.getTranslateY();
475         absRect.width_ = static_cast<int>(std::ceil(right - absRect.left_));
476         absRect.height_ = static_cast<int>(std::ceil(bottom - absRect.top_));
477 #else
478         Drawing::scalar transX = matrix.Get(Drawing::Matrix::TRANS_X);
479         Drawing::scalar transY = matrix.Get(Drawing::Matrix::TRANS_Y);
480         Drawing::scalar scaleX = matrix.Get(Drawing::Matrix::SCALE_X);
481         Drawing::scalar scaleY = matrix.Get(Drawing::Matrix::SCALE_Y);
482         absRect.left_ = static_cast<int>(rect.left_ * scaleX + transX);
483         absRect.top_ = static_cast<int>(rect.top_ * scaleY + transY);
484         float right = (rect.left_ + rect.width_) * scaleX + transX;
485         float bottom = (rect.top_ + rect.height_) * scaleY + transY;
486         absRect.width_ = static_cast<int>(std::ceil(right - absRect.left_));
487         absRect.height_ = static_cast<int>(std::ceil(bottom - absRect.top_));
488 #endif
489     }
490     return absRect;
491 }
492 
493 Vector2f RSObjAbsGeometry::GetDataRange(float d0, float d1, float d2, float d3) const
494 {
495     float min = d0;
496     float max = d0;
497     if (d0 > d1) {
498         min = d1;
499     } else {
500         max = d1;
501     }
502     if (d2 > d3) {
503         if (min > d3) {
504             min = d3;
505         }
506         if (max < d2) {
507             max = d2;
508         }
509     } else {
510         if (min > d2) {
511             min = d2;
512         }
513         if (max < d3) {
514             max = d3;
515         }
516     }
517     return Vector2f(min, max);
518 }
519 
520 #ifndef USE_ROSEN_DRAWING
521 void RSObjAbsGeometry::SetContextMatrix(const std::optional<SkMatrix>& matrix)
522 #else
523 void RSObjAbsGeometry::SetContextMatrix(const std::optional<Drawing::Matrix>& matrix)
524 #endif
525 {
526     contextMatrix_ = matrix;
527 }
528 
529 #ifndef USE_ROSEN_DRAWING
530 const SkMatrix& RSObjAbsGeometry::GetMatrix() const
531 #else
532 const Drawing::Matrix& RSObjAbsGeometry::GetMatrix() const
533 #endif
534 {
535     return matrix_;
536 }
537 
538 #ifndef USE_ROSEN_DRAWING
539 const SkMatrix& RSObjAbsGeometry::GetAbsMatrix() const
540 #else
541 const Drawing::Matrix& RSObjAbsGeometry::GetAbsMatrix() const
542 #endif
543 {
544     // if absMatrix_ is empty, return matrix_ instead
545     return absMatrix_ ? *absMatrix_ : matrix_;
546 }
547 } // namespace Rosen
548 } // namespace OHOS
549