• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-2023 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 "property/rs_properties.h"
17 
18 #include <algorithm>
19 #include <securec.h>
20 
21 #include "common/rs_common_def.h"
22 #include "common/rs_obj_abs_geometry.h"
23 #include "common/rs_vector4.h"
24 #include "pipeline/rs_uni_render_judgement.h"
25 #include "platform/common/rs_system_properties.h"
26 #include "property/rs_point_light_manager.h"
27 #include "property/rs_properties_def.h"
28 #include "render/rs_filter.h"
29 #include "render/rs_material_filter.h"
30 #include "render/rs_linear_gradient_blur_filter.h"
31 
32 namespace OHOS {
33 namespace Rosen {
34 namespace {
35 constexpr int32_t INDEX_2 = 2;
36 constexpr int32_t INDEX_4 = 4;
37 constexpr int32_t INDEX_5 = 5;
38 constexpr int32_t INDEX_6 = 6;
39 constexpr int32_t INDEX_7 = 7;
40 constexpr int32_t INDEX_9 = 9;
41 constexpr int32_t INDEX_10 = 10;
42 constexpr int32_t INDEX_11 = 11;
43 constexpr int32_t INDEX_12 = 12;
44 constexpr int32_t INDEX_14 = 14;
45 constexpr int32_t INDEX_18 = 18;
46 
47 const Vector4f Vector4fZero { 0.f, 0.f, 0.f, 0.f };
48 const auto EMPTY_RECT = RectF();
49 constexpr float SPHERIZE_VALID_EPSILON = 0.001f; // used to judge if spherize valid
50 constexpr uint8_t BORDER_TYPE_NONE = (uint32_t)BorderStyle::NONE;
51 
52 using ResetPropertyFunc = void (*)(RSProperties* prop);
53 // Every modifier before RSModifierType::CUSTOM is property modifier, and it should have a ResetPropertyFunc
54 // NOTE: alway add new resetter when adding new property modifier
55 const std::array<ResetPropertyFunc, static_cast<int>(RSModifierType::CUSTOM)> g_propertyResetterLUT = {
56     nullptr,                                                             // INVALID
57     nullptr,                                                             // BOUNDS
58     nullptr,                                                             // FRAME
__anon9b0d40c30202() 59     [](RSProperties* prop) { prop->SetPositionZ(0.f); },                 // POSITION_Z
__anon9b0d40c30302() 60     [](RSProperties* prop) { prop->SetPivot(Vector2f(0.5f, 0.5f)); },    // PIVOT
__anon9b0d40c30402() 61     [](RSProperties* prop) { prop->SetPivotZ(0.f); },                    // PIVOT_Z
__anon9b0d40c30502() 62     [](RSProperties* prop) { prop->SetQuaternion(Quaternion()); },       // QUATERNION
__anon9b0d40c30602() 63     [](RSProperties* prop) { prop->SetRotation(0.f); },                  // ROTATION
__anon9b0d40c30702() 64     [](RSProperties* prop) { prop->SetRotationX(0.f); },                 // ROTATION_X
__anon9b0d40c30802() 65     [](RSProperties* prop) { prop->SetRotationY(0.f); },                 // ROTATION_Y
__anon9b0d40c30902() 66     [](RSProperties* prop) { prop->SetCameraDistance(0.f); },            // CAMERA_DISTANCE
__anon9b0d40c30a02() 67     [](RSProperties* prop) { prop->SetScale(Vector2f(1.f, 1.f)); },      // SCALE
__anon9b0d40c30b02() 68     [](RSProperties* prop) { prop->SetTranslate(Vector2f(0.f, 0.f)); },  // TRANSLATE
__anon9b0d40c30c02() 69     [](RSProperties* prop) { prop->SetTranslateZ(0.f); },                // TRANSLATE_Z
__anon9b0d40c30d02() 70     [](RSProperties* prop) { prop->SetSublayerTransform({}); },          // SUBLAYER_TRANSFORM
__anon9b0d40c30e02() 71     [](RSProperties* prop) { prop->SetCornerRadius(0.f); },              // CORNER_RADIUS
__anon9b0d40c30f02() 72     [](RSProperties* prop) { prop->SetAlpha(1.f); },                     // ALPHA
__anon9b0d40c31002() 73     [](RSProperties* prop) { prop->SetAlphaOffscreen(false); },          // ALPHA_OFFSCREEN
__anon9b0d40c31102() 74     [](RSProperties* prop) { prop->SetForegroundColor({}); },            // FOREGROUND_COLOR
__anon9b0d40c31202() 75     [](RSProperties* prop) { prop->SetBackgroundColor({}); },            // BACKGROUND_COLOR
__anon9b0d40c31302() 76     [](RSProperties* prop) { prop->SetBackgroundShader({}); },           // BACKGROUND_SHADER
__anon9b0d40c31402() 77     [](RSProperties* prop) { prop->SetBgImage({}); },                    // BG_IMAGE
__anon9b0d40c31502() 78     [](RSProperties* prop) { prop->SetBgImageWidth(0.f); },              // BG_IMAGE_WIDTH
__anon9b0d40c31602() 79     [](RSProperties* prop) { prop->SetBgImageHeight(0.f); },             // BG_IMAGE_HEIGHT
__anon9b0d40c31702() 80     [](RSProperties* prop) { prop->SetBgImagePositionX(0.f); },          // BG_IMAGE_POSITION_X
__anon9b0d40c31802() 81     [](RSProperties* prop) { prop->SetBgImagePositionY(0.f); },          // BG_IMAGE_POSITION_Y
82     nullptr,                                                             // SURFACE_BG_COLOR
__anon9b0d40c31902() 83     [](RSProperties* prop) { prop->SetBorderColor(RSColor()); },         // BORDER_COLOR
__anon9b0d40c31a02() 84     [](RSProperties* prop) { prop->SetBorderWidth(0.f); },               // BORDER_WIDTH
__anon9b0d40c31b02() 85     [](RSProperties* prop) { prop->SetBorderStyle(BORDER_TYPE_NONE); },  // BORDER_STYLE
__anon9b0d40c31c02() 86     [](RSProperties* prop) { prop->SetFilter({}); },                     // FILTER
__anon9b0d40c31d02() 87     [](RSProperties* prop) { prop->SetBackgroundFilter({}); },           // BACKGROUND_FILTER
__anon9b0d40c31e02() 88     [](RSProperties* prop) { prop->SetLinearGradientBlurPara({}); },     // LINEAR_GRADIENT_BLUR_PARA
__anon9b0d40c31f02() 89     [](RSProperties* prop) { prop->SetDynamicLightUpRate({}); },         // DYNAMIC_LIGHT_UP_RATE
__anon9b0d40c32002() 90     [](RSProperties* prop) { prop->SetDynamicLightUpDegree({}); },       // DYNAMIC_LIGHT_UP_DEGREE
__anon9b0d40c32102() 91     [](RSProperties* prop) { prop->SetFrameGravity(Gravity::DEFAULT); }, // FRAME_GRAVITY
__anon9b0d40c32202() 92     [](RSProperties* prop) { prop->SetClipRRect({}); },                  // CLIP_RRECT
__anon9b0d40c32302() 93     [](RSProperties* prop) { prop->SetClipBounds({}); },                 // CLIP_BOUNDS
__anon9b0d40c32402() 94     [](RSProperties* prop) { prop->SetClipToBounds(false); },            // CLIP_TO_BOUNDS
__anon9b0d40c32502() 95     [](RSProperties* prop) { prop->SetClipToFrame(false); },             // CLIP_TO_FRAME
__anon9b0d40c32602() 96     [](RSProperties* prop) { prop->SetVisible(true); },                  // VISIBLE
__anon9b0d40c32702() 97     [](RSProperties* prop) { prop->SetShadowColor({}); },                // SHADOW_COLOR
__anon9b0d40c32802() 98     [](RSProperties* prop) { prop->SetShadowOffsetX(0.f); },             // SHADOW_OFFSET_X
__anon9b0d40c32902() 99     [](RSProperties* prop) { prop->SetShadowOffsetY(0.f); },             // SHADOW_OFFSET_Y
__anon9b0d40c32a02() 100     [](RSProperties* prop) { prop->SetShadowAlpha(0.f); },               // SHADOW_ALPHA
__anon9b0d40c32b02() 101     [](RSProperties* prop) { prop->SetShadowElevation(0.f); },           // SHADOW_ELEVATION
__anon9b0d40c32c02() 102     [](RSProperties* prop) { prop->SetShadowRadius(0.f); },              // SHADOW_RADIUS
__anon9b0d40c32d02() 103     [](RSProperties* prop) { prop->SetShadowPath({}); },                 // SHADOW_PATH
__anon9b0d40c32e02() 104     [](RSProperties* prop) { prop->SetShadowMask(false); },              // SHADOW_MASK
__anon9b0d40c32f02() 105     [](RSProperties* prop) { prop->SetShadowColorStrategy(0); },         // ShadowColorStrategy
__anon9b0d40c33002() 106     [](RSProperties* prop) { prop->SetMask({}); },                       // MASK
__anon9b0d40c33102() 107     [](RSProperties* prop) { prop->SetSpherize(0.f); },                  // SPHERIZE
__anon9b0d40c33202() 108     [](RSProperties* prop) { prop->SetLightUpEffect(1.f); },             // LIGHT_UP_EFFECT
__anon9b0d40c33302() 109     [](RSProperties* prop) { prop->SetPixelStretch({}); },               // PIXEL_STRETCH
__anon9b0d40c33402() 110     [](RSProperties* prop) { prop->SetPixelStretchPercent({}); },        // PIXEL_STRETCH_PERCENT
__anon9b0d40c33502() 111     [](RSProperties* prop) { prop->SetUseEffect(false); },               // USE_EFFECT
__anon9b0d40c33602() 112     [](RSProperties* prop) { prop->SetColorBlendMode(0); },              // COLOR_BLENDMODE
__anon9b0d40c33702() 113     [](RSProperties* prop) { prop->SetColorBlendApplyType(0); },         // COLOR_BLENDAPPLY_TYPE
__anon9b0d40c33802() 114     [](RSProperties* prop) { prop->ResetSandBox(); },                    // SANDBOX
__anon9b0d40c33902() 115     [](RSProperties* prop) { prop->SetGrayScale({}); },                  // GRAY_SCALE
__anon9b0d40c33a02() 116     [](RSProperties* prop) { prop->SetBrightness({}); },                 // BRIGHTNESS
__anon9b0d40c33b02() 117     [](RSProperties* prop) { prop->SetContrast({}); },                   // CONTRAST
__anon9b0d40c33c02() 118     [](RSProperties* prop) { prop->SetSaturate({}); },                   // SATURATE
__anon9b0d40c33d02() 119     [](RSProperties* prop) { prop->SetSepia({}); },                      // SEPIA
__anon9b0d40c33e02() 120     [](RSProperties* prop) { prop->SetInvert({}); },                     // INVERT
__anon9b0d40c33f02() 121     [](RSProperties* prop) { prop->SetAiInvert({}); },                   // AIINVERT
__anon9b0d40c34002() 122     [](RSProperties* prop) { prop->SetSystemBarEffect({}); },            // SYSTEMBAREFFECT
__anon9b0d40c34102() 123     [](RSProperties* prop) { prop->SetHueRotate({}); },                  // HUE_ROTATE
__anon9b0d40c34202() 124     [](RSProperties* prop) { prop->SetColorBlend({}); },                 // COLOR_BLEND
__anon9b0d40c34302() 125     [](RSProperties* prop) { prop->SetParticles({}); },                  // PARTICLE
__anon9b0d40c34402() 126     [](RSProperties* prop) { prop->SetShadowIsFilled(false); },          // SHADOW_IS_FILLED
__anon9b0d40c34502() 127     [](RSProperties* prop) { prop->SetOutlineColor(RSColor()); },        // OUTLINE_COLOR
__anon9b0d40c34602() 128     [](RSProperties* prop) { prop->SetOutlineWidth(0.f); },              // OUTLINE_WIDTH
__anon9b0d40c34702() 129     [](RSProperties* prop) { prop->SetOutlineStyle(BORDER_TYPE_NONE); }, // OUTLINE_STYLE
__anon9b0d40c34802() 130     [](RSProperties* prop) { prop->SetOutlineRadius(0.f); },             // OUTLINE_RADIUS
__anon9b0d40c34902() 131     [](RSProperties* prop) { prop->SetUseShadowBatching(false); },       // USE_SHADOW_BATCHING
__anon9b0d40c34a02() 132     [](RSProperties* prop) { prop->SetGreyCoef1(0.f); },                 // GREY_COEF1
__anon9b0d40c34b02() 133     [](RSProperties* prop) { prop->SetGreyCoef2(0.f); },                 // GREY_COEF2
__anon9b0d40c34c02() 134     [](RSProperties* prop) { prop->SetLightIntensity(-1.f); },           // LIGHT_INTENSITY
__anon9b0d40c34d02() 135     [](RSProperties* prop) { prop->SetLightPosition({}); },              // LIGHT_POSITION
__anon9b0d40c34e02() 136     [](RSProperties* prop) { prop->SetIlluminatedBorderWidth({}); },     // ILLUMINATED_BORDER_WIDTH
__anon9b0d40c34f02() 137     [](RSProperties* prop) { prop->SetIlluminatedType(-1); },            // ILLUMINATED_TYPE
__anon9b0d40c35002() 138     [](RSProperties* prop) { prop->SetBloom({}); },                      // BLOOM
139 };
140 } // namespace
141 
142 // Only enable filter cache when uni-render is enabled and filter cache is enabled
143 
144 #if defined(NEW_SKIA) && (defined(RS_ENABLE_GL) || defined(RS_ENABLE_VK))
145 #ifndef ROSEN_ARKUI_X
146 const bool RSProperties::FilterCacheEnabled =
147     RSSystemProperties::GetFilterCacheEnabled() && RSUniRenderJudgement::IsUniRender();
148 #else
149 const bool RSProperties::FilterCacheEnabled = false;
150 #endif
151 #endif
152 
RSProperties()153 RSProperties::RSProperties()
154 {
155     boundsGeo_ = std::make_shared<RSObjAbsGeometry>();
156     frameGeo_ = std::make_shared<RSObjGeometry>();
157 }
158 
159 RSProperties::~RSProperties() = default;
160 
161 #ifndef USE_ROSEN_DRAWING
ResetProperty(const std::unordered_set<RSModifierType> & dirtyTypes)162 void RSProperties::ResetProperty(const std::unordered_set<RSModifierType>& dirtyTypes)
163 {
164     for (const auto& type : dirtyTypes) {
165         if (type >= RSModifierType::CUSTOM) {
166             continue;
167         }
168         if (auto& resetFunc = g_propertyResetterLUT[static_cast<uint8_t>(type)]) {
169             resetFunc(this);
170         }
171     }
172 }
173 #else
ResetProperty(const std::bitset<static_cast<int> (RSModifierType::MAX_RS_MODIFIER_TYPE)> & dirtyTypes)174 void RSProperties::ResetProperty(const std::bitset<static_cast<int>(RSModifierType::MAX_RS_MODIFIER_TYPE)>& dirtyTypes)
175 {
176     if (dirtyTypes.none()) {
177         return;
178     }
179     for (uint8_t type = 0; type < static_cast<size_t>(RSModifierType::CUSTOM); type++) {
180         if (dirtyTypes[type]) {
181             if (auto& resetFunc = g_propertyResetterLUT[type]) {
182                 resetFunc(this);
183             }
184         }
185     }
186 }
187 #endif
188 
SetBounds(Vector4f bounds)189 void RSProperties::SetBounds(Vector4f bounds)
190 {
191     if (bounds.z_ != boundsGeo_->GetWidth() || bounds.w_ != boundsGeo_->GetHeight()) {
192         contentDirty_ = true;
193     }
194     boundsGeo_->SetRect(bounds.x_, bounds.y_, bounds.z_, bounds.w_);
195     hasBounds_ = true;
196     geoDirty_ = true;
197     SetDirty();
198 }
199 
SetBoundsSize(Vector2f size)200 void RSProperties::SetBoundsSize(Vector2f size)
201 {
202     boundsGeo_->SetSize(size.x_, size.y_);
203     hasBounds_ = true;
204     geoDirty_ = true;
205     contentDirty_ = true;
206     SetDirty();
207 }
208 
SetBoundsWidth(float width)209 void RSProperties::SetBoundsWidth(float width)
210 {
211     boundsGeo_->SetWidth(width);
212     hasBounds_ = true;
213     geoDirty_ = true;
214     contentDirty_ = true;
215     SetDirty();
216 }
217 
SetBoundsHeight(float height)218 void RSProperties::SetBoundsHeight(float height)
219 {
220     boundsGeo_->SetHeight(height);
221     hasBounds_ = true;
222     geoDirty_ = true;
223     contentDirty_ = true;
224     SetDirty();
225 }
226 
SetBoundsPosition(Vector2f position)227 void RSProperties::SetBoundsPosition(Vector2f position)
228 {
229     boundsGeo_->SetPosition(position.x_, position.y_);
230     geoDirty_ = true;
231     SetDirty();
232 }
233 
SetBoundsPositionX(float positionX)234 void RSProperties::SetBoundsPositionX(float positionX)
235 {
236     boundsGeo_->SetX(positionX);
237     geoDirty_ = true;
238     SetDirty();
239 }
240 
SetBoundsPositionY(float positionY)241 void RSProperties::SetBoundsPositionY(float positionY)
242 {
243     boundsGeo_->SetY(positionY);
244     geoDirty_ = true;
245     SetDirty();
246 }
247 
GetBounds() const248 Vector4f RSProperties::GetBounds() const
249 {
250     return { boundsGeo_->GetX(), boundsGeo_->GetY(), boundsGeo_->GetWidth(), boundsGeo_->GetHeight() };
251 }
252 
GetBoundsSize() const253 Vector2f RSProperties::GetBoundsSize() const
254 {
255     return { boundsGeo_->GetWidth(), boundsGeo_->GetHeight() };
256 }
257 
GetBoundsWidth() const258 float RSProperties::GetBoundsWidth() const
259 {
260     return boundsGeo_->GetWidth();
261 }
262 
GetBoundsHeight() const263 float RSProperties::GetBoundsHeight() const
264 {
265     return boundsGeo_->GetHeight();
266 }
267 
GetBoundsPositionX() const268 float RSProperties::GetBoundsPositionX() const
269 {
270     return boundsGeo_->GetX();
271 }
272 
GetBoundsPositionY() const273 float RSProperties::GetBoundsPositionY() const
274 {
275     return boundsGeo_->GetY();
276 }
277 
GetBoundsPosition() const278 Vector2f RSProperties::GetBoundsPosition() const
279 {
280     return { GetBoundsPositionX(), GetBoundsPositionY() };
281 }
282 
SetFrame(Vector4f frame)283 void RSProperties::SetFrame(Vector4f frame)
284 {
285     if (frame.z_ != frameGeo_->GetWidth() || frame.w_ != frameGeo_->GetHeight()) {
286         contentDirty_ = true;
287     }
288     frameGeo_->SetRect(frame.x_, frame.y_, frame.z_, frame.w_);
289     geoDirty_ = true;
290     SetDirty();
291 }
292 
SetFrameSize(Vector2f size)293 void RSProperties::SetFrameSize(Vector2f size)
294 {
295     frameGeo_->SetSize(size.x_, size.y_);
296     geoDirty_ = true;
297     contentDirty_ = true;
298     SetDirty();
299 }
300 
SetFrameWidth(float width)301 void RSProperties::SetFrameWidth(float width)
302 {
303     frameGeo_->SetWidth(width);
304     geoDirty_ = true;
305     contentDirty_ = true;
306     SetDirty();
307 }
308 
SetFrameHeight(float height)309 void RSProperties::SetFrameHeight(float height)
310 {
311     frameGeo_->SetHeight(height);
312     geoDirty_ = true;
313     contentDirty_ = true;
314     SetDirty();
315 }
316 
SetFramePosition(Vector2f position)317 void RSProperties::SetFramePosition(Vector2f position)
318 {
319     frameGeo_->SetPosition(position.x_, position.y_);
320     geoDirty_ = true;
321     SetDirty();
322 }
323 
SetFramePositionX(float positionX)324 void RSProperties::SetFramePositionX(float positionX)
325 {
326     frameGeo_->SetX(positionX);
327     geoDirty_ = true;
328     SetDirty();
329 }
330 
SetFramePositionY(float positionY)331 void RSProperties::SetFramePositionY(float positionY)
332 {
333     frameGeo_->SetY(positionY);
334     geoDirty_ = true;
335     SetDirty();
336 }
337 
GetFrame() const338 Vector4f RSProperties::GetFrame() const
339 {
340     return { frameGeo_->GetX(), frameGeo_->GetY(), frameGeo_->GetWidth(), frameGeo_->GetHeight() };
341 }
342 
GetFrameSize() const343 Vector2f RSProperties::GetFrameSize() const
344 {
345     return { frameGeo_->GetWidth(), frameGeo_->GetHeight() };
346 }
347 
GetFrameWidth() const348 float RSProperties::GetFrameWidth() const
349 {
350     return frameGeo_->GetWidth();
351 }
352 
GetFrameHeight() const353 float RSProperties::GetFrameHeight() const
354 {
355     return frameGeo_->GetHeight();
356 }
357 
GetFramePositionX() const358 float RSProperties::GetFramePositionX() const
359 {
360     return frameGeo_->GetX();
361 }
362 
GetFramePositionY() const363 float RSProperties::GetFramePositionY() const
364 {
365     return frameGeo_->GetY();
366 }
367 
GetFramePosition() const368 Vector2f RSProperties::GetFramePosition() const
369 {
370     return { GetFramePositionX(), GetFramePositionY() };
371 }
372 
GetFrameOffsetX() const373 float RSProperties::GetFrameOffsetX() const
374 {
375     return frameOffsetX_;
376 }
377 
GetFrameOffsetY() const378 float RSProperties::GetFrameOffsetY() const
379 {
380     return frameOffsetY_;
381 }
382 
GetBoundsGeometry() const383 const std::shared_ptr<RSObjAbsGeometry>& RSProperties::GetBoundsGeometry() const
384 {
385     return boundsGeo_;
386 }
387 
GetFrameGeometry() const388 const std::shared_ptr<RSObjGeometry>& RSProperties::GetFrameGeometry() const
389 {
390     return frameGeo_;
391 }
392 
393 #ifndef USE_ROSEN_DRAWING
UpdateGeometry(const RSProperties * parent,bool dirtyFlag,const std::optional<SkPoint> & offset,const std::optional<SkRect> & clipRect)394 bool RSProperties::UpdateGeometry(const RSProperties* parent, bool dirtyFlag, const std::optional<SkPoint>& offset,
395     const std::optional<SkRect>& clipRect)
396 #else
397 bool RSProperties::UpdateGeometry(const RSProperties* parent, bool dirtyFlag,
398     const std::optional<Drawing::Point>& offset, const std::optional<Drawing::Rect>& clipRect)
399 #endif
400 {
401     if (boundsGeo_ == nullptr) {
402         return false;
403     }
404     auto boundsGeoPtr = (boundsGeo_);
405 
406     if (!dirtyFlag && !geoDirty_) {
407         return false;
408     }
409     auto parentGeo = parent == nullptr ? nullptr : (parent->boundsGeo_);
410     if (parentGeo && sandbox_ && sandbox_->matrix_) {
411         parentGeo = std::make_shared<RSObjAbsGeometry>();
412         parentGeo->ConcatMatrix(*(sandbox_->matrix_));
413     }
414     CheckEmptyBounds();
415     boundsGeoPtr->UpdateMatrix(parentGeo, offset, clipRect);
416     if (lightSourcePtr_ && lightSourcePtr_->IsLightSourceValid()) {
417         CalculateAbsLightPosition();
418         RSPointLightManager::Instance()->AddDirtyLightSource(backref_);
419     }
420     if (illuminatedPtr_ && illuminatedPtr_->IsIlluminatedValid()) {
421         RSPointLightManager::Instance()->AddDirtyIlluminated(backref_);
422     }
423     if (RSSystemProperties::GetSkipGeometryNotChangeEnabled()) {
424         auto rect = boundsGeoPtr->GetAbsRect();
425         if (!lastRect_.has_value()) {
426             lastRect_ = rect;
427             return true;
428         }
429         dirtyFlag = dirtyFlag || rect != lastRect_.value();
430         lastRect_ = rect;
431         return dirtyFlag;
432     } else {
433         return true;
434     }
435 }
436 
SetSandBox(const std::optional<Vector2f> & parentPosition)437 void RSProperties::SetSandBox(const std::optional<Vector2f>& parentPosition)
438 {
439     if (!sandbox_) {
440         sandbox_ = std::make_unique<Sandbox>();
441     }
442     sandbox_->position_ = parentPosition;
443     geoDirty_ = true;
444     SetDirty();
445 }
446 
GetSandBox() const447 std::optional<Vector2f> RSProperties::GetSandBox() const
448 {
449     return sandbox_ ? sandbox_->position_ : std::nullopt;
450 }
451 
ResetSandBox()452 void RSProperties::ResetSandBox()
453 {
454     sandbox_ = nullptr;
455 }
456 
457 #ifndef USE_ROSEN_DRAWING
UpdateSandBoxMatrix(const std::optional<SkMatrix> & rootMatrix)458 void RSProperties::UpdateSandBoxMatrix(const std::optional<SkMatrix>& rootMatrix)
459 #else
460 void RSProperties::UpdateSandBoxMatrix(const std::optional<Drawing::Matrix>& rootMatrix)
461 #endif
462 {
463     if (!sandbox_) {
464         return;
465     }
466     if (!rootMatrix || !sandbox_->position_) {
467         sandbox_->matrix_ = std::nullopt;
468         return;
469     }
470     auto rootMat = rootMatrix.value();
471     bool hasScale = false;
472 #ifndef USE_ROSEN_DRAWING
473     // skScaleFactors[0]-minimum scaling factor, skScaleFactors[1]-maximum scaling factor
474     SkScalar skScaleFactors[2];
475     bool getMinMaxScales = rootMat.getMinMaxScales(skScaleFactors);
476     if (getMinMaxScales) {
477         hasScale = !ROSEN_EQ(skScaleFactors[0], 1.f) || !ROSEN_EQ(skScaleFactors[1], 1.f);
478     }
479 #else
480     // scaleFactors[0]-minimum scaling factor, scaleFactors[1]-maximum scaling factor
481     Drawing::scalar scaleFactors[2];
482     bool getMinMaxScales = rootMat.GetMinMaxScales(scaleFactors);
483     if (getMinMaxScales) {
484         hasScale = !ROSEN_EQ(scaleFactors[0], 1.f) || !ROSEN_EQ(scaleFactors[1], 1.f);
485     }
486 #endif
487     if (hasScale) {
488         sandbox_->matrix_ = std::nullopt;
489         return;
490     }
491 #ifndef USE_ROSEN_DRAWING
492     sandbox_->matrix_ = rootMat.preTranslate(sandbox_->position_->x_, sandbox_->position_->y_);
493 #else
494     Drawing::Matrix matrix = rootMatrix.value();
495     matrix.PreTranslate(sandbox_->position_->x_, sandbox_->position_->y_);
496     sandbox_->matrix_ = matrix;
497 #endif
498 }
499 
500 #ifndef USE_ROSEN_DRAWING
GetSandBoxMatrix() const501 std::optional<SkMatrix> RSProperties::GetSandBoxMatrix() const
502 #else
503 std::optional<Drawing::Matrix> RSProperties::GetSandBoxMatrix() const
504 #endif
505 {
506     return sandbox_ ? sandbox_->matrix_ : std::nullopt;
507 }
508 
SetPositionZ(float positionZ)509 void RSProperties::SetPositionZ(float positionZ)
510 {
511     boundsGeo_->SetZ(positionZ);
512     frameGeo_->SetZ(positionZ);
513     geoDirty_ = true;
514     SetDirty();
515 }
516 
GetPositionZ() const517 float RSProperties::GetPositionZ() const
518 {
519     return boundsGeo_->GetZ();
520 }
521 
SetPivot(Vector2f pivot)522 void RSProperties::SetPivot(Vector2f pivot)
523 {
524     boundsGeo_->SetPivot(pivot.x_, pivot.y_);
525     geoDirty_ = true;
526     SetDirty();
527 }
528 
SetPivotX(float pivotX)529 void RSProperties::SetPivotX(float pivotX)
530 {
531     boundsGeo_->SetPivotX(pivotX);
532     geoDirty_ = true;
533     SetDirty();
534 }
535 
SetPivotY(float pivotY)536 void RSProperties::SetPivotY(float pivotY)
537 {
538     boundsGeo_->SetPivotY(pivotY);
539     geoDirty_ = true;
540     SetDirty();
541 }
542 
SetPivotZ(float pivotZ)543 void RSProperties::SetPivotZ(float pivotZ)
544 {
545     boundsGeo_->SetPivotZ(pivotZ);
546     geoDirty_ = true;
547     SetDirty();
548 }
549 
GetPivot() const550 Vector2f RSProperties::GetPivot() const
551 {
552     return { boundsGeo_->GetPivotX(), boundsGeo_->GetPivotY() };
553 }
554 
GetPivotX() const555 float RSProperties::GetPivotX() const
556 {
557     return boundsGeo_->GetPivotX();
558 }
559 
GetPivotY() const560 float RSProperties::GetPivotY() const
561 {
562     return boundsGeo_->GetPivotY();
563 }
564 
GetPivotZ() const565 float RSProperties::GetPivotZ() const
566 {
567     return boundsGeo_->GetPivotZ();
568 }
569 
SetCornerRadius(const Vector4f & cornerRadius)570 void RSProperties::SetCornerRadius(const Vector4f& cornerRadius)
571 {
572     cornerRadius_ = cornerRadius;
573     SetDirty();
574 }
575 
GetCornerRadius() const576 const Vector4f& RSProperties::GetCornerRadius() const
577 {
578     return cornerRadius_ ? cornerRadius_.value() : Vector4fZero;
579 }
580 
SetQuaternion(Quaternion quaternion)581 void RSProperties::SetQuaternion(Quaternion quaternion)
582 {
583     boundsGeo_->SetQuaternion(quaternion);
584     geoDirty_ = true;
585     SetDirty();
586 }
587 
SetRotation(float degree)588 void RSProperties::SetRotation(float degree)
589 {
590     boundsGeo_->SetRotation(degree);
591     geoDirty_ = true;
592     SetDirty();
593 }
594 
SetRotationX(float degree)595 void RSProperties::SetRotationX(float degree)
596 {
597     boundsGeo_->SetRotationX(degree);
598     geoDirty_ = true;
599     SetDirty();
600 }
601 
SetRotationY(float degree)602 void RSProperties::SetRotationY(float degree)
603 {
604     boundsGeo_->SetRotationY(degree);
605     geoDirty_ = true;
606     SetDirty();
607 }
608 
SetCameraDistance(float cameraDistance)609 void RSProperties::SetCameraDistance(float cameraDistance)
610 {
611     boundsGeo_->SetCameraDistance(cameraDistance);
612     geoDirty_ = true;
613     SetDirty();
614 }
615 
SetScale(Vector2f scale)616 void RSProperties::SetScale(Vector2f scale)
617 {
618     boundsGeo_->SetScale(scale.x_, scale.y_);
619     geoDirty_ = true;
620     SetDirty();
621 }
622 
SetScaleX(float sx)623 void RSProperties::SetScaleX(float sx)
624 {
625     boundsGeo_->SetScaleX(sx);
626     geoDirty_ = true;
627     SetDirty();
628 }
629 
SetScaleY(float sy)630 void RSProperties::SetScaleY(float sy)
631 {
632     boundsGeo_->SetScaleY(sy);
633     geoDirty_ = true;
634     SetDirty();
635 }
636 
SetTranslate(Vector2f translate)637 void RSProperties::SetTranslate(Vector2f translate)
638 {
639     boundsGeo_->SetTranslateX(translate[0]);
640     boundsGeo_->SetTranslateY(translate[1]);
641     geoDirty_ = true;
642     SetDirty();
643 }
644 
SetTranslateX(float translate)645 void RSProperties::SetTranslateX(float translate)
646 {
647     boundsGeo_->SetTranslateX(translate);
648     geoDirty_ = true;
649     SetDirty();
650 }
651 
SetTranslateY(float translate)652 void RSProperties::SetTranslateY(float translate)
653 {
654     boundsGeo_->SetTranslateY(translate);
655     geoDirty_ = true;
656     SetDirty();
657 }
658 
SetTranslateZ(float translate)659 void RSProperties::SetTranslateZ(float translate)
660 {
661     boundsGeo_->SetTranslateZ(translate);
662     geoDirty_ = true;
663     SetDirty();
664 }
665 
GetQuaternion() const666 Quaternion RSProperties::GetQuaternion() const
667 {
668     return boundsGeo_->GetQuaternion();
669 }
670 
GetRotation() const671 float RSProperties::GetRotation() const
672 {
673     return boundsGeo_->GetRotation();
674 }
675 
GetRotationX() const676 float RSProperties::GetRotationX() const
677 {
678     return boundsGeo_->GetRotationX();
679 }
680 
GetRotationY() const681 float RSProperties::GetRotationY() const
682 {
683     return boundsGeo_->GetRotationY();
684 }
685 
GetCameraDistance() const686 float RSProperties::GetCameraDistance() const
687 {
688     return boundsGeo_->GetCameraDistance();
689 }
690 
GetScaleX() const691 float RSProperties::GetScaleX() const
692 {
693     return boundsGeo_->GetScaleX();
694 }
695 
GetScaleY() const696 float RSProperties::GetScaleY() const
697 {
698     return boundsGeo_->GetScaleY();
699 }
700 
GetScale() const701 Vector2f RSProperties::GetScale() const
702 {
703     return { boundsGeo_->GetScaleX(), boundsGeo_->GetScaleY() };
704 }
705 
GetTranslate() const706 Vector2f RSProperties::GetTranslate() const
707 {
708     return Vector2f(GetTranslateX(), GetTranslateY());
709 }
710 
GetTranslateX() const711 float RSProperties::GetTranslateX() const
712 {
713     return boundsGeo_->GetTranslateX();
714 }
715 
GetTranslateY() const716 float RSProperties::GetTranslateY() const
717 {
718     return boundsGeo_->GetTranslateY();
719 }
720 
GetTranslateZ() const721 float RSProperties::GetTranslateZ() const
722 {
723     return boundsGeo_->GetTranslateZ();
724 }
725 
SetParticles(const RSRenderParticleVector & particles)726 void RSProperties::SetParticles(const RSRenderParticleVector& particles)
727 {
728     particles_ = particles;
729     if (particles_.GetParticleSize() > 0) {
730         isDrawn_ = true;
731     }
732     SetDirty();
733     contentDirty_ = true;
734 }
735 
GetParticles() const736 const RSRenderParticleVector& RSProperties::GetParticles() const
737 {
738     return particles_;
739 }
740 
SetAlpha(float alpha)741 void RSProperties::SetAlpha(float alpha)
742 {
743     alpha_ = alpha;
744     if (alpha_ < 1.f) {
745         alphaNeedApply_ = true;
746     }
747     SetDirty();
748 }
749 
GetAlpha() const750 float RSProperties::GetAlpha() const
751 {
752     return alpha_;
753 }
SetAlphaOffscreen(bool alphaOffscreen)754 void RSProperties::SetAlphaOffscreen(bool alphaOffscreen)
755 {
756     alphaOffscreen_ = alphaOffscreen;
757     SetDirty();
758     contentDirty_ = true;
759 }
760 
GetAlphaOffscreen() const761 bool RSProperties::GetAlphaOffscreen() const
762 {
763     return alphaOffscreen_;
764 }
765 
SetSublayerTransform(const std::optional<Matrix3f> & sublayerTransform)766 void RSProperties::SetSublayerTransform(const std::optional<Matrix3f>& sublayerTransform)
767 {
768     sublayerTransform_ = sublayerTransform;
769     SetDirty();
770 }
771 
GetSublayerTransform() const772 const std::optional<Matrix3f>& RSProperties::GetSublayerTransform() const
773 {
774     return sublayerTransform_;
775 }
776 
777 // foreground properties
SetForegroundColor(Color color)778 void RSProperties::SetForegroundColor(Color color)
779 {
780     if (!decoration_) {
781         decoration_ = std::make_optional<Decoration>();
782     }
783     decoration_->foregroundColor_ = color;
784     SetDirty();
785     contentDirty_ = true;
786 }
787 
GetForegroundColor() const788 Color RSProperties::GetForegroundColor() const
789 {
790     return decoration_ ? decoration_->foregroundColor_ : RgbPalette::Transparent();
791 }
792 
793 // background properties
SetBackgroundColor(Color color)794 void RSProperties::SetBackgroundColor(Color color)
795 {
796     if (!decoration_) {
797         decoration_ = std::make_optional<Decoration>();
798     }
799     if (color.GetAlpha() > 0) {
800         isDrawn_ = true;
801     }
802     decoration_->backgroundColor_ = color;
803     SetDirty();
804     contentDirty_ = true;
805 }
806 
GetBackgroundColor() const807 const Color& RSProperties::GetBackgroundColor() const
808 {
809     return decoration_ ? decoration_->backgroundColor_ : RgbPalette::Transparent();
810 }
811 
SetBackgroundShader(const std::shared_ptr<RSShader> & shader)812 void RSProperties::SetBackgroundShader(const std::shared_ptr<RSShader>& shader)
813 {
814     if (!decoration_) {
815         decoration_ = std::make_optional<Decoration>();
816     }
817     if (shader) {
818         isDrawn_ = true;
819     }
820     decoration_->bgShader_ = shader;
821     SetDirty();
822     contentDirty_ = true;
823 }
824 
GetBackgroundShader() const825 std::shared_ptr<RSShader> RSProperties::GetBackgroundShader() const
826 {
827     return decoration_ ? decoration_->bgShader_ : nullptr;
828 }
829 
SetBgImage(const std::shared_ptr<RSImage> & image)830 void RSProperties::SetBgImage(const std::shared_ptr<RSImage>& image)
831 {
832     if (!decoration_) {
833         decoration_ = std::make_optional<Decoration>();
834     }
835     if (image) {
836         isDrawn_ = true;
837     }
838     decoration_->bgImage_ = image;
839     SetDirty();
840     contentDirty_ = true;
841 }
842 
GetBgImage() const843 std::shared_ptr<RSImage> RSProperties::GetBgImage() const
844 {
845     return decoration_ ? decoration_->bgImage_ : nullptr;
846 }
847 
SetBgImageWidth(float width)848 void RSProperties::SetBgImageWidth(float width)
849 {
850     if (!decoration_) {
851         decoration_ = std::make_optional<Decoration>();
852     }
853     decoration_->bgImageRect_.width_ = width;
854     SetDirty();
855     contentDirty_ = true;
856 }
857 
SetBgImageHeight(float height)858 void RSProperties::SetBgImageHeight(float height)
859 {
860     if (!decoration_) {
861         decoration_ = std::make_optional<Decoration>();
862     }
863     decoration_->bgImageRect_.height_ = height;
864     SetDirty();
865     contentDirty_ = true;
866 }
867 
SetBgImagePositionX(float positionX)868 void RSProperties::SetBgImagePositionX(float positionX)
869 {
870     if (!decoration_) {
871         decoration_ = std::make_optional<Decoration>();
872     }
873     decoration_->bgImageRect_.left_ = positionX;
874     SetDirty();
875     contentDirty_ = true;
876 }
877 
SetBgImagePositionY(float positionY)878 void RSProperties::SetBgImagePositionY(float positionY)
879 {
880     if (!decoration_) {
881         decoration_ = std::make_optional<Decoration>();
882     }
883     decoration_->bgImageRect_.top_ = positionY;
884     SetDirty();
885     contentDirty_ = true;
886 }
887 
GetBgImageWidth() const888 float RSProperties::GetBgImageWidth() const
889 {
890     return decoration_ ? decoration_->bgImageRect_.width_ : 0.f;
891 }
892 
GetBgImageHeight() const893 float RSProperties::GetBgImageHeight() const
894 {
895     return decoration_ ? decoration_->bgImageRect_.height_ : 0.f;
896 }
897 
GetBgImagePositionX() const898 float RSProperties::GetBgImagePositionX() const
899 {
900     return decoration_ ? decoration_->bgImageRect_.left_ : 0.f;
901 }
902 
GetBgImagePositionY() const903 float RSProperties::GetBgImagePositionY() const
904 {
905     return decoration_ ? decoration_->bgImageRect_.top_ : 0.f;
906 }
907 
908 // border properties
SetBorderColor(Vector4<Color> color)909 void RSProperties::SetBorderColor(Vector4<Color> color)
910 {
911     if (!border_) {
912         border_ = std::make_shared<RSBorder>();
913     }
914     border_->SetColorFour(color);
915     if (border_->GetColor().GetAlpha() > 0) {
916         isDrawn_ = true;
917     }
918     SetDirty();
919     contentDirty_ = true;
920 }
921 
SetBorderWidth(Vector4f width)922 void RSProperties::SetBorderWidth(Vector4f width)
923 {
924     if (!border_) {
925         border_ = std::make_shared<RSBorder>();
926     }
927     border_->SetWidthFour(width);
928     if (!width.IsZero()) {
929         isDrawn_ = true;
930     }
931     SetDirty();
932     contentDirty_ = true;
933 }
934 
SetBorderStyle(Vector4<uint32_t> style)935 void RSProperties::SetBorderStyle(Vector4<uint32_t> style)
936 {
937     if (!border_) {
938         border_ = std::make_shared<RSBorder>();
939     }
940     border_->SetStyleFour(style);
941     SetDirty();
942     contentDirty_ = true;
943 }
944 
GetBorderColor() const945 Vector4<Color> RSProperties::GetBorderColor() const
946 {
947     return border_ ? border_->GetColorFour() : Vector4<Color>(RgbPalette::Transparent());
948 }
949 
GetBorderWidth() const950 Vector4f RSProperties::GetBorderWidth() const
951 {
952     return border_ ? border_->GetWidthFour() : Vector4f(0.f);
953 }
954 
GetBorderStyle() const955 Vector4<uint32_t> RSProperties::GetBorderStyle() const
956 {
957     return border_ ? border_->GetStyleFour() : Vector4<uint32_t>(static_cast<uint32_t>(BorderStyle::NONE));
958 }
959 
GetBorder() const960 const std::shared_ptr<RSBorder>& RSProperties::GetBorder() const
961 {
962     return border_;
963 }
964 
SetOutlineColor(Vector4<Color> color)965 void RSProperties::SetOutlineColor(Vector4<Color> color)
966 {
967     if (!outline_) {
968         outline_ = std::make_shared<RSBorder>(true);
969     }
970     outline_->SetColorFour(color);
971     if (outline_->GetColor().GetAlpha() > 0) {
972         isDrawn_ = true;
973     }
974     SetDirty();
975     contentDirty_ = true;
976 }
977 
SetOutlineWidth(Vector4f width)978 void RSProperties::SetOutlineWidth(Vector4f width)
979 {
980     if (!outline_) {
981         outline_ = std::make_shared<RSBorder>(true);
982     }
983     outline_->SetWidthFour(width);
984     if (!width.IsZero()) {
985         isDrawn_ = true;
986     }
987     SetDirty();
988     contentDirty_ = true;
989 }
990 
SetOutlineStyle(Vector4<uint32_t> style)991 void RSProperties::SetOutlineStyle(Vector4<uint32_t> style)
992 {
993     if (!outline_) {
994         outline_ = std::make_shared<RSBorder>(true);
995     }
996     outline_->SetStyleFour(style);
997     SetDirty();
998     contentDirty_ = true;
999 }
1000 
SetOutlineRadius(Vector4f radius)1001 void RSProperties::SetOutlineRadius(Vector4f radius)
1002 {
1003     if (!outline_) {
1004         outline_ = std::make_shared<RSBorder>(true);
1005     }
1006     outline_->SetRadiusFour(radius);
1007     isDrawn_ = true;
1008     SetDirty();
1009     contentDirty_ = true;
1010 }
1011 
GetOutlineColor() const1012 Vector4<Color> RSProperties::GetOutlineColor() const
1013 {
1014     return outline_ ? outline_->GetColorFour() : Vector4<Color>(RgbPalette::Transparent());
1015 }
1016 
GetOutlineWidth() const1017 Vector4f RSProperties::GetOutlineWidth() const
1018 {
1019     return outline_ ? outline_->GetWidthFour() : Vector4f(0.f);
1020 }
1021 
GetOutlineStyle() const1022 Vector4<uint32_t> RSProperties::GetOutlineStyle() const
1023 {
1024     return outline_ ? outline_->GetStyleFour() : Vector4<uint32_t>(static_cast<uint32_t>(BorderStyle::NONE));
1025 }
1026 
GetOutlineRadius() const1027 Vector4f RSProperties::GetOutlineRadius() const
1028 {
1029     return outline_ ? outline_->GetRadiusFour() : Vector4fZero;
1030 }
1031 
GetOutline() const1032 const std::shared_ptr<RSBorder>& RSProperties::GetOutline() const
1033 {
1034     return outline_;
1035 }
1036 
SetBackgroundFilter(const std::shared_ptr<RSFilter> & backgroundFilter)1037 void RSProperties::SetBackgroundFilter(const std::shared_ptr<RSFilter>& backgroundFilter)
1038 {
1039     backgroundFilter_ = backgroundFilter;
1040     if (backgroundFilter_) {
1041         isDrawn_ = true;
1042     }
1043     SetDirty();
1044     filterNeedUpdate_ = true;
1045     contentDirty_ = true;
1046 }
1047 
SetLinearGradientBlurPara(const std::shared_ptr<RSLinearGradientBlurPara> & para)1048 void RSProperties::SetLinearGradientBlurPara(const std::shared_ptr<RSLinearGradientBlurPara>& para)
1049 {
1050     linearGradientBlurPara_ = para;
1051     if (para && para->blurRadius_ > 0.f) {
1052         isDrawn_ = true;
1053     }
1054     filterNeedUpdate_ = true;
1055     SetDirty();
1056     contentDirty_ = true;
1057 }
1058 
SetDynamicLightUpRate(const std::optional<float> & rate)1059 void RSProperties::SetDynamicLightUpRate(const std::optional<float>& rate)
1060 {
1061     dynamicLightUpRate_ = rate;
1062     if (rate.has_value()) {
1063         isDrawn_ = true;
1064     }
1065     filterNeedUpdate_ = true;
1066     SetDirty();
1067     contentDirty_ = true;
1068 }
1069 
SetDynamicLightUpDegree(const std::optional<float> & lightUpDegree)1070 void RSProperties::SetDynamicLightUpDegree(const std::optional<float>& lightUpDegree)
1071 {
1072     dynamicLightUpDegree_ = lightUpDegree;
1073     if (lightUpDegree.has_value()) {
1074         isDrawn_ = true;
1075     }
1076     filterNeedUpdate_ = true;
1077     SetDirty();
1078     contentDirty_ = true;
1079 }
1080 
SetGreyCoef1(float greyCoef1)1081 void RSProperties::SetGreyCoef1(float greyCoef1)
1082 {
1083     greyCoef1_ = greyCoef1;
1084     filterNeedUpdate_ = true;
1085     SetDirty();
1086     contentDirty_ = true;
1087 }
1088 
SetGreyCoef2(float greyCoef2)1089 void RSProperties::SetGreyCoef2(float greyCoef2)
1090 {
1091     greyCoef2_ = greyCoef2;
1092     filterNeedUpdate_ = true;
1093     SetDirty();
1094     contentDirty_ = true;
1095 }
1096 
SetFilter(const std::shared_ptr<RSFilter> & filter)1097 void RSProperties::SetFilter(const std::shared_ptr<RSFilter>& filter)
1098 {
1099     filter_ = filter;
1100     if (filter) {
1101         isDrawn_ = true;
1102     }
1103     SetDirty();
1104     filterNeedUpdate_ = true;
1105     contentDirty_ = true;
1106 }
1107 
GetBackgroundFilter() const1108 const std::shared_ptr<RSFilter>& RSProperties::GetBackgroundFilter() const
1109 {
1110     return backgroundFilter_;
1111 }
1112 
GetLinearGradientBlurPara() const1113 const std::shared_ptr<RSLinearGradientBlurPara>& RSProperties::GetLinearGradientBlurPara() const
1114 {
1115     return linearGradientBlurPara_;
1116 }
1117 
IfLinearGradientBlurInvalid()1118 void RSProperties::IfLinearGradientBlurInvalid()
1119 {
1120     if (linearGradientBlurPara_ != nullptr) {
1121         bool isValid = ROSEN_GNE(linearGradientBlurPara_->blurRadius_, 0.0);
1122         if (!isValid) {
1123             linearGradientBlurPara_.reset();
1124         }
1125     }
1126 }
1127 
GetDynamicLightUpRate() const1128 const std::optional<float>& RSProperties::GetDynamicLightUpRate() const
1129 {
1130     return dynamicLightUpRate_;
1131 }
1132 
GetDynamicLightUpDegree() const1133 const std::optional<float>& RSProperties::GetDynamicLightUpDegree() const
1134 {
1135     return dynamicLightUpDegree_;
1136 }
1137 
GetGreyCoef1() const1138 float RSProperties::GetGreyCoef1() const
1139 {
1140     return greyCoef1_;
1141 }
1142 
GetGreyCoef2() const1143 float RSProperties::GetGreyCoef2() const
1144 {
1145     return greyCoef2_;
1146 }
1147 
IsGreyAdjustmentValid() const1148 bool RSProperties::IsGreyAdjustmentValid() const
1149 {
1150     return ROSEN_GNE(greyCoef1_, 0.0) && ROSEN_LE(greyCoef1_, 127.0) &&   // 127.0 number
1151         ROSEN_GNE(greyCoef2_, 0.0) && ROSEN_LE(greyCoef2_, 127.0);        // 127.0 number
1152 }
1153 
GetFilter() const1154 const std::shared_ptr<RSFilter>& RSProperties::GetFilter() const
1155 {
1156     return filter_;
1157 }
1158 
IsDynamicLightUpValid() const1159 bool RSProperties::IsDynamicLightUpValid() const
1160 {
1161     return dynamicLightUpRate_.has_value() && dynamicLightUpDegree_.has_value() &&
1162            ROSEN_GNE(*dynamicLightUpRate_, 0.0) && ROSEN_GE(*dynamicLightUpDegree_, -1.0) &&
1163            ROSEN_LE(*dynamicLightUpDegree_, 1.0);
1164 }
1165 
1166 // shadow properties
SetShadowColor(Color color)1167 void RSProperties::SetShadowColor(Color color)
1168 {
1169     if (!shadow_.has_value()) {
1170         shadow_ = std::make_optional<RSShadow>();
1171     }
1172     shadow_->SetColor(color);
1173     SetDirty();
1174     // [planning] if shadow stores as texture and out of node
1175     // node content would not be affected
1176     contentDirty_ = true;
1177 }
1178 
SetShadowOffsetX(float offsetX)1179 void RSProperties::SetShadowOffsetX(float offsetX)
1180 {
1181     if (!shadow_.has_value()) {
1182         shadow_ = std::make_optional<RSShadow>();
1183     }
1184     shadow_->SetOffsetX(offsetX);
1185     SetDirty();
1186     // [planning] if shadow stores as texture and out of node
1187     // node content would not be affected
1188     contentDirty_ = true;
1189 }
1190 
SetShadowOffsetY(float offsetY)1191 void RSProperties::SetShadowOffsetY(float offsetY)
1192 {
1193     if (!shadow_.has_value()) {
1194         shadow_ = std::make_optional<RSShadow>();
1195     }
1196     shadow_->SetOffsetY(offsetY);
1197     SetDirty();
1198     // [planning] if shadow stores as texture and out of node
1199     // node content would not be affected
1200     contentDirty_ = true;
1201 }
1202 
SetShadowAlpha(float alpha)1203 void RSProperties::SetShadowAlpha(float alpha)
1204 {
1205     if (!shadow_.has_value()) {
1206         shadow_ = std::make_optional<RSShadow>();
1207     }
1208     shadow_->SetAlpha(alpha);
1209     if (shadow_->IsValid()) {
1210         isDrawn_ = true;
1211     }
1212     SetDirty();
1213     // [planning] if shadow stores as texture and out of node
1214     // node content would not be affected
1215     contentDirty_ = true;
1216 }
1217 
SetShadowElevation(float elevation)1218 void RSProperties::SetShadowElevation(float elevation)
1219 {
1220     if (!shadow_.has_value()) {
1221         shadow_ = std::make_optional<RSShadow>();
1222     }
1223     shadow_->SetElevation(elevation);
1224     if (shadow_->IsValid()) {
1225         isDrawn_ = true;
1226     }
1227     SetDirty();
1228     // [planning] if shadow stores as texture and out of node
1229     // node content would not be affected
1230     contentDirty_ = true;
1231 }
1232 
SetShadowRadius(float radius)1233 void RSProperties::SetShadowRadius(float radius)
1234 {
1235     if (!shadow_.has_value()) {
1236         shadow_ = std::make_optional<RSShadow>();
1237     }
1238     shadow_->SetRadius(radius);
1239     if (shadow_->IsValid()) {
1240         isDrawn_ = true;
1241     }
1242     SetDirty();
1243     // [planning] if shadow stores as texture and out of node
1244     // node content would not be affected
1245     contentDirty_ = true;
1246 }
1247 
SetShadowPath(std::shared_ptr<RSPath> shadowPath)1248 void RSProperties::SetShadowPath(std::shared_ptr<RSPath> shadowPath)
1249 {
1250     if (!shadow_.has_value()) {
1251         shadow_ = std::make_optional<RSShadow>();
1252     }
1253     shadow_->SetPath(shadowPath);
1254     SetDirty();
1255     // [planning] if shadow stores as texture and out of node
1256     // node content would not be affected
1257     contentDirty_ = true;
1258 }
1259 
SetShadowMask(bool shadowMask)1260 void RSProperties::SetShadowMask(bool shadowMask)
1261 {
1262     if (!shadow_.has_value()) {
1263         shadow_ = std::make_optional<RSShadow>();
1264     }
1265     shadow_->SetMask(shadowMask);
1266     SetDirty();
1267     // [planning] if shadow stores as texture and out of node
1268     // node content would not be affected
1269     contentDirty_ = true;
1270 }
1271 
SetShadowIsFilled(bool shadowIsFilled)1272 void RSProperties::SetShadowIsFilled(bool shadowIsFilled)
1273 {
1274     if (!shadow_.has_value()) {
1275         shadow_ = std::make_optional<RSShadow>();
1276     }
1277     shadow_->SetIsFilled(shadowIsFilled);
1278     SetDirty();
1279     // [planning] if shadow stores as texture and out of node
1280     // node content would not be affected
1281     contentDirty_ = true;
1282 }
1283 
SetShadowColorStrategy(int shadowColorStrategy)1284 void RSProperties::SetShadowColorStrategy(int shadowColorStrategy)
1285 {
1286     if (!shadow_.has_value()) {
1287         shadow_ = std::make_optional<RSShadow>();
1288     }
1289     shadow_->SetColorStrategy(shadowColorStrategy);
1290     SetDirty();
1291     filterNeedUpdate_ = true;
1292     // [planning] if shadow stores as texture and out of node
1293     // node content would not be affected
1294     contentDirty_ = true;
1295     if (shadowColorStrategy != SHADOW_COLOR_STRATEGY::COLOR_STRATEGY_NONE && colorPickerTaskShadow_ == nullptr) {
1296         CreateColorPickerTaskForShadow();
1297         colorPickerTaskShadow_->SetShadowColorStrategy(shadowColorStrategy);
1298     }
1299 }
1300 
1301 
GetShadowColor() const1302 const Color& RSProperties::GetShadowColor() const
1303 {
1304     static const auto DEFAULT_SPOT_COLOR_VALUE = Color::FromArgbInt(DEFAULT_SPOT_COLOR);
1305     return shadow_ ? shadow_->GetColor() : DEFAULT_SPOT_COLOR_VALUE;
1306 }
1307 
GetShadowOffsetX() const1308 float RSProperties::GetShadowOffsetX() const
1309 {
1310     return shadow_ ? shadow_->GetOffsetX() : DEFAULT_SHADOW_OFFSET_X;
1311 }
1312 
GetShadowOffsetY() const1313 float RSProperties::GetShadowOffsetY() const
1314 {
1315     return shadow_ ? shadow_->GetOffsetY() : DEFAULT_SHADOW_OFFSET_Y;
1316 }
1317 
GetShadowAlpha() const1318 float RSProperties::GetShadowAlpha() const
1319 {
1320     return shadow_ ? shadow_->GetAlpha() : 0.f;
1321 }
1322 
GetShadowElevation() const1323 float RSProperties::GetShadowElevation() const
1324 {
1325     return shadow_ ? shadow_->GetElevation() : 0.f;
1326 }
1327 
GetShadowRadius() const1328 float RSProperties::GetShadowRadius() const
1329 {
1330     return shadow_ ? shadow_->GetRadius() : DEFAULT_SHADOW_RADIUS;
1331 }
1332 
GetShadowPath() const1333 std::shared_ptr<RSPath> RSProperties::GetShadowPath() const
1334 {
1335     return shadow_ ? shadow_->GetPath() : nullptr;
1336 }
1337 
GetShadowMask() const1338 bool RSProperties::GetShadowMask() const
1339 {
1340     return shadow_ ? shadow_->GetMask() : false;
1341 }
1342 
GetShadowIsFilled() const1343 bool RSProperties::GetShadowIsFilled() const
1344 {
1345     return shadow_ ? shadow_->GetIsFilled() : false;
1346 }
1347 
GetShadowColorStrategy() const1348 int RSProperties::GetShadowColorStrategy() const
1349 {
1350     return shadow_ ? shadow_->GetColorStrategy() : SHADOW_COLOR_STRATEGY::COLOR_STRATEGY_NONE;
1351 }
1352 
GetShadow() const1353 const std::optional<RSShadow>& RSProperties::GetShadow() const
1354 {
1355     return shadow_;
1356 }
1357 
IsShadowValid() const1358 bool RSProperties::IsShadowValid() const
1359 {
1360     return shadow_ && shadow_->IsValid();
1361 }
1362 
SetFrameGravity(Gravity gravity)1363 void RSProperties::SetFrameGravity(Gravity gravity)
1364 {
1365     if (frameGravity_ != gravity) {
1366         frameGravity_ = gravity;
1367         SetDirty();
1368         contentDirty_ = true;
1369     }
1370 }
1371 
GetFrameGravity() const1372 Gravity RSProperties::GetFrameGravity() const
1373 {
1374     return frameGravity_;
1375 }
1376 
SetDrawRegion(const std::shared_ptr<RectF> & rect)1377 void RSProperties::SetDrawRegion(const std::shared_ptr<RectF>& rect)
1378 {
1379     drawRegion_ = rect;
1380     SetDirty();
1381     geoDirty_ = true;  // since drawRegion affect dirtyRegion, mark it as geoDirty
1382 }
1383 
GetDrawRegion() const1384 std::shared_ptr<RectF> RSProperties::GetDrawRegion() const
1385 {
1386     return drawRegion_;
1387 }
1388 
SetClipRRect(RRect clipRRect)1389 void RSProperties::SetClipRRect(RRect clipRRect)
1390 {
1391     clipRRect_ = clipRRect;
1392     if (GetClipToRRect()) {
1393         isDrawn_ = true;
1394     }
1395     SetDirty();
1396     geoDirty_ = true;  // [planning] all clip ops should be checked
1397 }
1398 
GetClipRRect() const1399 RRect RSProperties::GetClipRRect() const
1400 {
1401     return clipRRect_ ? *clipRRect_ : RRect();
1402 }
1403 
GetClipToRRect() const1404 bool RSProperties::GetClipToRRect() const
1405 {
1406     return clipRRect_.has_value();
1407 }
1408 
SetClipBounds(const std::shared_ptr<RSPath> & path)1409 void RSProperties::SetClipBounds(const std::shared_ptr<RSPath>& path)
1410 {
1411     if (path) {
1412         isDrawn_ = true;
1413     }
1414     if (clipPath_ != path) {
1415         clipPath_ = path;
1416         SetDirty();
1417         geoDirty_ = true;  // [planning] all clip ops should be checked
1418     }
1419 }
1420 
GetClipBounds() const1421 const std::shared_ptr<RSPath>& RSProperties::GetClipBounds() const
1422 {
1423     return clipPath_;
1424 }
1425 
SetClipToBounds(bool clipToBounds)1426 void RSProperties::SetClipToBounds(bool clipToBounds)
1427 {
1428     if (clipToBounds) {
1429         isDrawn_ = true;
1430     }
1431     if (clipToBounds_ != clipToBounds) {
1432         clipToBounds_ = clipToBounds;
1433         SetDirty();
1434         geoDirty_ = true;  // [planning] all clip ops should be checked
1435     }
1436 }
1437 
GetClipToBounds() const1438 bool RSProperties::GetClipToBounds() const
1439 {
1440     return clipToBounds_;
1441 }
1442 
SetClipToFrame(bool clipToFrame)1443 void RSProperties::SetClipToFrame(bool clipToFrame)
1444 {
1445     if (clipToFrame) {
1446         isDrawn_ = true;
1447     }
1448     if (clipToFrame_ != clipToFrame) {
1449         clipToFrame_ = clipToFrame;
1450         SetDirty();
1451         geoDirty_ = true;  // [planning] all clip ops should be checked
1452     }
1453 }
1454 
GetClipToFrame() const1455 bool RSProperties::GetClipToFrame() const
1456 {
1457     return clipToFrame_;
1458 }
1459 
GetBoundsRect() const1460 RectF RSProperties::GetBoundsRect() const
1461 {
1462     if (boundsGeo_->IsEmpty()) {
1463         return {0, 0, GetFrameWidth(), GetFrameHeight()};
1464     } else {
1465         return {0, 0, GetBoundsWidth(), GetBoundsHeight()};
1466     }
1467 }
1468 
GetFrameRect() const1469 RectF RSProperties::GetFrameRect() const
1470 {
1471     return {0, 0, GetFrameWidth(), GetFrameHeight()};
1472 }
1473 
GetBgImageRect() const1474 const RectF& RSProperties::GetBgImageRect() const
1475 {
1476     return decoration_ ? decoration_->bgImageRect_ : EMPTY_RECT;
1477 }
1478 
SetVisible(bool visible)1479 void RSProperties::SetVisible(bool visible)
1480 {
1481     if (visible_ != visible) {
1482         visible_ = visible;
1483         SetDirty();
1484         contentDirty_ = true;
1485     }
1486 }
1487 
GetVisible() const1488 bool RSProperties::GetVisible() const
1489 {
1490     return visible_;
1491 }
1492 
GetRRect() const1493 const RRect& RSProperties::GetRRect() const
1494 {
1495     return rrect_;
1496 }
1497 
GenerateRRect()1498 void RSProperties::GenerateRRect()
1499 {
1500     RectF rect = GetBoundsRect();
1501     rrect_ = RRect(rect, GetCornerRadius());
1502 }
1503 
GetInnerRRect() const1504 RRect RSProperties::GetInnerRRect() const
1505 {
1506     auto rect = GetBoundsRect();
1507     Vector4f cornerRadius = GetCornerRadius();
1508     if (border_) {
1509         rect.left_ += border_->GetWidth(RSBorder::LEFT);
1510         rect.top_ += border_->GetWidth(RSBorder::TOP);
1511         rect.width_ -= border_->GetWidth(RSBorder::LEFT) + border_->GetWidth(RSBorder::RIGHT);
1512         rect.height_ -= border_->GetWidth(RSBorder::TOP) + border_->GetWidth(RSBorder::BOTTOM);
1513     }
1514     RRect rrect = RRect(rect, cornerRadius);
1515     if (border_) {
1516         rrect.radius_[0] -= { border_->GetWidth(RSBorder::LEFT), border_->GetWidth(RSBorder::TOP) };
1517         rrect.radius_[1] -= { border_->GetWidth(RSBorder::RIGHT), border_->GetWidth(RSBorder::TOP) };
1518         rrect.radius_[2] -= { border_->GetWidth(RSBorder::RIGHT), border_->GetWidth(RSBorder::BOTTOM) };
1519         rrect.radius_[3] -= { border_->GetWidth(RSBorder::LEFT), border_->GetWidth(RSBorder::BOTTOM) };
1520     }
1521     return rrect;
1522 }
1523 
NeedFilter() const1524 bool RSProperties::NeedFilter() const
1525 {
1526     return needFilter_;
1527 }
1528 
NeedClip() const1529 bool RSProperties::NeedClip() const
1530 {
1531     return clipToBounds_ || clipToFrame_;
1532 }
1533 
SetDirty()1534 void RSProperties::SetDirty()
1535 {
1536     isDirty_ = true;
1537 }
1538 
ResetDirty()1539 void RSProperties::ResetDirty()
1540 {
1541     isDirty_ = false;
1542     geoDirty_ = false;
1543     contentDirty_ = false;
1544 }
1545 
IsDirty() const1546 bool RSProperties::IsDirty() const
1547 {
1548     return isDirty_;
1549 }
1550 
IsGeoDirty() const1551 bool RSProperties::IsGeoDirty() const
1552 {
1553     return geoDirty_;
1554 }
1555 
IsContentDirty() const1556 bool RSProperties::IsContentDirty() const
1557 {
1558     return contentDirty_;
1559 }
1560 
GetDirtyRect() const1561 RectI RSProperties::GetDirtyRect() const
1562 {
1563     RectI dirtyRect;
1564     auto boundsGeometry = (boundsGeo_);
1565     if (clipToBounds_ || std::isinf(GetFrameWidth()) || std::isinf(GetFrameHeight())) {
1566         dirtyRect = boundsGeometry->GetAbsRect();
1567     } else {
1568         auto frameRect =
1569             boundsGeometry->MapAbsRect(RectF(GetFrameOffsetX(), GetFrameOffsetY(), GetFrameWidth(), GetFrameHeight()));
1570         dirtyRect = boundsGeometry->GetAbsRect().JoinRect(frameRect);
1571     }
1572     if (drawRegion_ == nullptr || drawRegion_->IsEmpty()) {
1573         return dirtyRect;
1574     } else {
1575         auto drawRegion = boundsGeometry->MapAbsRect(*drawRegion_);
1576         // this is used to fix the scene with drawRegion problem, which is need to be optimized
1577         drawRegion.SetRight(drawRegion.GetRight() + 1);
1578         drawRegion.SetBottom(drawRegion.GetBottom() + 1);
1579         drawRegion.SetAll(drawRegion.left_ - 1, drawRegion.top_ - 1,
1580             drawRegion.width_ + 1, drawRegion.height_ + 1);
1581         return dirtyRect.JoinRect(drawRegion);
1582     }
1583 }
1584 
GetDirtyRect(RectI & drawRegion) const1585 RectI RSProperties::GetDirtyRect(RectI& drawRegion) const
1586 {
1587     RectI dirtyRect;
1588     auto boundsGeometry = (boundsGeo_);
1589     if (clipToBounds_ || std::isinf(GetFrameWidth()) || std::isinf(GetFrameHeight())) {
1590         dirtyRect = boundsGeometry->GetAbsRect();
1591     } else {
1592         auto frameRect =
1593             boundsGeometry->MapAbsRect(RectF(GetFrameOffsetX(), GetFrameOffsetY(), GetFrameWidth(), GetFrameHeight()));
1594         dirtyRect = boundsGeometry->GetAbsRect().JoinRect(frameRect);
1595     }
1596     if (drawRegion_ == nullptr || drawRegion_->IsEmpty()) {
1597         drawRegion = RectI();
1598         return dirtyRect;
1599     } else {
1600         drawRegion = boundsGeometry->MapAbsRect(*drawRegion_);
1601         // this is used to fix the scene with drawRegion problem, which is need to be optimized
1602         drawRegion.SetRight(drawRegion.GetRight() + 1);
1603         drawRegion.SetBottom(drawRegion.GetBottom() + 1);
1604         drawRegion.SetAll(drawRegion.left_ - 1, drawRegion.top_ - 1,
1605             drawRegion.width_ + 1, drawRegion.height_ + 1);
1606         return dirtyRect.JoinRect(drawRegion);
1607     }
1608 }
1609 
CheckEmptyBounds()1610 void RSProperties::CheckEmptyBounds()
1611 {
1612     // [planning] remove this func and fallback to framerect after surfacenode using frame
1613     if (!hasBounds_) {
1614         boundsGeo_->SetRect(frameGeo_->GetX(), frameGeo_->GetY(), frameGeo_->GetWidth(), frameGeo_->GetHeight());
1615     }
1616 }
1617 
1618 // mask properties
SetMask(const std::shared_ptr<RSMask> & mask)1619 void RSProperties::SetMask(const std::shared_ptr<RSMask>& mask)
1620 {
1621     mask_ = mask;
1622     if (mask_) {
1623         isDrawn_ = true;
1624     }
1625     SetDirty();
1626     contentDirty_ = true;
1627 }
1628 
GetMask() const1629 std::shared_ptr<RSMask> RSProperties::GetMask() const
1630 {
1631     return mask_;
1632 }
1633 
SetSpherize(float spherizeDegree)1634 void RSProperties::SetSpherize(float spherizeDegree)
1635 {
1636     spherizeDegree_ = spherizeDegree;
1637     isSpherizeValid_ = spherizeDegree_ > SPHERIZE_VALID_EPSILON;
1638     SetDirty();
1639     contentDirty_ = true;
1640 }
1641 
GetSpherize() const1642 float RSProperties::GetSpherize() const
1643 {
1644     return spherizeDegree_;
1645 }
1646 
IsSpherizeValid() const1647 bool RSProperties::IsSpherizeValid() const
1648 {
1649     return isSpherizeValid_;
1650 }
1651 
SetLightUpEffect(float lightUpEffectDegree)1652 void RSProperties::SetLightUpEffect(float lightUpEffectDegree)
1653 {
1654     lightUpEffectDegree_ = lightUpEffectDegree;
1655     if (IsLightUpEffectValid()) {
1656         isDrawn_ = true;
1657     }
1658     filterNeedUpdate_ = true;
1659     SetDirty();
1660     contentDirty_ = true;
1661 }
1662 
GetLightUpEffect() const1663 float RSProperties::GetLightUpEffect() const
1664 {
1665     return lightUpEffectDegree_;
1666 }
1667 
IsLightUpEffectValid() const1668 bool RSProperties::IsLightUpEffectValid() const
1669 {
1670     return ROSEN_GE(GetLightUpEffect(), 0.0) && ROSEN_LNE(GetLightUpEffect(), 1.0);
1671 }
1672 
SetUseEffect(bool useEffect)1673 void RSProperties::SetUseEffect(bool useEffect)
1674 {
1675     useEffect_ = useEffect;
1676     if (GetUseEffect()) {
1677         isDrawn_ = true;
1678     }
1679     filterNeedUpdate_ = true;
1680     SetDirty();
1681 }
1682 
GetUseEffect() const1683 bool RSProperties::GetUseEffect() const
1684 {
1685     return useEffect_;
1686 }
1687 
SetUseShadowBatching(bool useShadowBatching)1688 void RSProperties::SetUseShadowBatching(bool useShadowBatching)
1689 {
1690     if (useShadowBatching) {
1691         isDrawn_ = true;
1692     }
1693     useShadowBatching_ = useShadowBatching;
1694     SetDirty();
1695 }
1696 
GetUseShadowBatching() const1697 bool RSProperties::GetUseShadowBatching() const
1698 {
1699     return useShadowBatching_;
1700 }
1701 
SetNeedSkipShadow(bool needSkipShadow)1702 void RSProperties::SetNeedSkipShadow(bool needSkipShadow)
1703 {
1704     needSkipShadow_ = needSkipShadow;
1705 }
1706 
GetNeedSkipShadow() const1707 bool RSProperties::GetNeedSkipShadow() const
1708 {
1709     return needSkipShadow_;
1710 }
1711 
SetPixelStretch(const std::optional<Vector4f> & stretchSize)1712 void RSProperties::SetPixelStretch(const std::optional<Vector4f>& stretchSize)
1713 {
1714     pixelStretch_ = stretchSize;
1715     SetDirty();
1716     pixelStretchNeedUpdate_ = true;
1717     contentDirty_ = true;
1718     if (pixelStretch_.has_value() && pixelStretch_->IsZero()) {
1719         pixelStretch_ = std::nullopt;
1720     }
1721 }
1722 
GetPixelStretch() const1723 const std::optional<Vector4f>& RSProperties::GetPixelStretch() const
1724 {
1725     return pixelStretch_;
1726 }
1727 
GetPixelStretchDirtyRect() const1728 RectI RSProperties::GetPixelStretchDirtyRect() const
1729 {
1730     auto dirtyRect = GetDirtyRect();
1731 
1732     auto scaledBounds = RectF(dirtyRect.left_ - pixelStretch_->x_, dirtyRect.top_ - pixelStretch_->y_,
1733         dirtyRect.width_ + pixelStretch_->x_ + pixelStretch_->z_,
1734         dirtyRect.height_ + pixelStretch_->y_ + pixelStretch_->w_);
1735 
1736     auto scaledIBounds = RectI(std::floor(scaledBounds.left_), std::floor(scaledBounds.top_),
1737         std::ceil(scaledBounds.width_) + 1, std::ceil(scaledBounds.height_) + 1);
1738     return dirtyRect.JoinRect(scaledIBounds);
1739 }
1740 
SetPixelStretchPercent(const std::optional<Vector4f> & stretchPercent)1741 void RSProperties::SetPixelStretchPercent(const std::optional<Vector4f>& stretchPercent)
1742 {
1743     pixelStretchPercent_ = stretchPercent;
1744     SetDirty();
1745     pixelStretchNeedUpdate_ = true;
1746     contentDirty_ = true;
1747     if (pixelStretchPercent_.has_value() && pixelStretchPercent_->IsZero()) {
1748         pixelStretchPercent_ = std::nullopt;
1749     }
1750 }
1751 
GetPixelStretchPercent() const1752 const std::optional<Vector4f>& RSProperties::GetPixelStretchPercent() const
1753 {
1754     return pixelStretchPercent_;
1755 }
1756 
1757 // Image effect properties
SetGrayScale(const std::optional<float> & grayScale)1758 void RSProperties::SetGrayScale(const std::optional<float>& grayScale)
1759 {
1760     grayScale_ = grayScale;
1761     colorFilterNeedUpdate_ = true;
1762     SetDirty();
1763     contentDirty_ = true;
1764 }
1765 
GetGrayScale() const1766 const std::optional<float>& RSProperties::GetGrayScale() const
1767 {
1768     return grayScale_;
1769 }
1770 
SetLightIntensity(float lightIntensity)1771 void RSProperties::SetLightIntensity(float lightIntensity)
1772 {
1773     if (!lightSourcePtr_) {
1774         lightSourcePtr_ = std::make_shared<RSLightSource>();
1775     }
1776     lightSourcePtr_->SetLightIntensity(lightIntensity);
1777     SetDirty();
1778     contentDirty_ = true;
1779 
1780     if (ROSEN_EQ(lightIntensity, INVALID_INTENSITY)) { // skip when resetFunc call
1781         return;
1782     }
1783     auto preIntensity = lightSourcePtr_->GetPreLightIntensity();
1784     auto renderNode = backref_.lock();
1785     bool preIntensityIsZero = ROSEN_EQ(preIntensity, 0.f);
1786     bool curIntensityIsZero = ROSEN_EQ(lightIntensity, 0.f);
1787     if (preIntensityIsZero && !curIntensityIsZero) { // 0 --> non-zero
1788         RSPointLightManager::Instance()->RegisterLightSource(renderNode);
1789     } else if (!preIntensityIsZero && curIntensityIsZero) { // non-zero --> 0
1790         RSPointLightManager::Instance()->UnRegisterLightSource(renderNode);
1791     }
1792 }
1793 
SetLightPosition(const Vector4f & lightPosition)1794 void RSProperties::SetLightPosition(const Vector4f& lightPosition)
1795 {
1796     if (!lightSourcePtr_) {
1797         lightSourcePtr_ = std::make_shared<RSLightSource>();
1798     }
1799     lightSourcePtr_->SetLightPosition(lightPosition);
1800     SetDirty();
1801     contentDirty_ = true;
1802 }
1803 
SetIlluminatedBorderWidth(float illuminatedBorderWidth)1804 void RSProperties::SetIlluminatedBorderWidth(float illuminatedBorderWidth)
1805 {
1806     if (!illuminatedPtr_) {
1807         illuminatedPtr_ = std::make_shared<RSIlluminated>();
1808     }
1809     illuminatedPtr_->SetIlluminatedBorderWidth(illuminatedBorderWidth);
1810     SetDirty();
1811     contentDirty_ = true;
1812 }
1813 
SetIlluminatedType(int illuminatedType)1814 void RSProperties::SetIlluminatedType(int illuminatedType)
1815 {
1816     if (!illuminatedPtr_) {
1817         illuminatedPtr_ = std::make_shared<RSIlluminated>();
1818     }
1819     auto curIlluminateType = IlluminatedType(illuminatedType);
1820     illuminatedPtr_->SetIlluminatedType(curIlluminateType);
1821     isDrawn_ = true;
1822     SetDirty();
1823     contentDirty_ = true;
1824 
1825     if (curIlluminateType == IlluminatedType::INVALID) { // skip when resetFunc call
1826         return;
1827     }
1828     auto renderNode = backref_.lock();
1829     auto preIlluminatedType = illuminatedPtr_->GetPreIlluminatedType();
1830     bool preTypeIsNone = preIlluminatedType == IlluminatedType::NONE;
1831     bool curTypeIsNone = curIlluminateType == IlluminatedType::NONE;
1832     if (preTypeIsNone && !curTypeIsNone) {
1833         RSPointLightManager::Instance()->RegisterIlluminated(renderNode);
1834     } else if (!preTypeIsNone && curTypeIsNone) {
1835         RSPointLightManager::Instance()->UnRegisterIlluminated(renderNode);
1836     }
1837 }
1838 
SetBloom(float bloomIntensity)1839 void RSProperties::SetBloom(float bloomIntensity)
1840 {
1841     if (!illuminatedPtr_) {
1842         illuminatedPtr_ = std::make_shared<RSIlluminated>();
1843     }
1844     illuminatedPtr_->SetBloomIntensity(bloomIntensity);
1845     isDrawn_ = true;
1846     SetDirty();
1847     contentDirty_ = true;
1848 }
1849 
GetLightIntensity() const1850 float RSProperties::GetLightIntensity() const
1851 {
1852     return lightSourcePtr_ ? lightSourcePtr_->GetLightIntensity() : 0.f;
1853 }
1854 
GetLightPosition() const1855 Vector4f RSProperties::GetLightPosition() const
1856 {
1857     return lightSourcePtr_ ? lightSourcePtr_->GetLightPosition() : Vector4f(0.f);
1858 }
1859 
GetIlluminatedType() const1860 int RSProperties::GetIlluminatedType() const
1861 {
1862     return illuminatedPtr_ ? static_cast<int>(illuminatedPtr_->GetIlluminatedType()) : 0;
1863 }
1864 
GetBloom() const1865 float RSProperties::GetBloom() const
1866 {
1867     return illuminatedPtr_ ? illuminatedPtr_->GetBloomIntensity() : 0.f;
1868 }
1869 
GetIlluminatedBorderWidth() const1870 float RSProperties::GetIlluminatedBorderWidth() const
1871 {
1872     return illuminatedPtr_ ? illuminatedPtr_->GetIlluminatedBorderWidth() : 0.f;
1873 }
1874 
CalculateAbsLightPosition()1875 void RSProperties::CalculateAbsLightPosition()
1876 {
1877     auto lightSourceAbsRect = boundsGeo_->GetAbsRect();
1878     auto rotation = RSPointLightManager::Instance()->GetScreenRotation();
1879     Vector4f lightAbsPosition = Vector4f();
1880     auto lightPos = lightSourcePtr_->GetLightPosition();
1881     switch (rotation) {
1882         case ScreenRotation::ROTATION_0:
1883             lightAbsPosition.x_ = static_cast<int>(lightSourceAbsRect.GetLeft() + lightPos.x_);
1884             lightAbsPosition.y_ = static_cast<int>(lightSourceAbsRect.GetTop() + lightPos.y_);
1885             break;
1886         case ScreenRotation::ROTATION_90:
1887             lightAbsPosition.x_ = static_cast<int>(lightSourceAbsRect.GetBottom() - lightPos.x_);
1888             lightAbsPosition.y_ = static_cast<int>(lightSourceAbsRect.GetLeft() + lightPos.y_);
1889             break;
1890         case ScreenRotation::ROTATION_180:
1891             lightAbsPosition.x_ = static_cast<int>(lightSourceAbsRect.GetRight() - lightPos.x_);
1892             lightAbsPosition.y_ = static_cast<int>(lightSourceAbsRect.GetBottom() - lightPos.y_);
1893             break;
1894         case ScreenRotation::ROTATION_270:
1895             lightAbsPosition.x_ = static_cast<int>(lightSourceAbsRect.GetTop() + lightPos.x_);
1896             lightAbsPosition.y_ = static_cast<int>(lightSourceAbsRect.GetRight() - lightPos.y_);
1897             break;
1898         default:
1899             break;
1900     }
1901     lightAbsPosition.z_ = lightPos.z_;
1902     lightAbsPosition.w_ = lightPos.w_;
1903     lightSourcePtr_->SetAbsLightPosition(lightAbsPosition);
1904 }
1905 
GetLightSource() const1906 const std::shared_ptr<RSLightSource>& RSProperties::GetLightSource() const
1907 {
1908     return lightSourcePtr_;
1909 }
1910 
GetIlluminated() const1911 const std::shared_ptr<RSIlluminated>& RSProperties::GetIlluminated() const
1912 {
1913     return illuminatedPtr_;
1914 }
1915 
SetBrightness(const std::optional<float> & brightness)1916 void RSProperties::SetBrightness(const std::optional<float>& brightness)
1917 {
1918     brightness_ = brightness;
1919     colorFilterNeedUpdate_ = true;
1920     SetDirty();
1921     contentDirty_ = true;
1922 }
1923 
GetBrightness() const1924 const std::optional<float>& RSProperties::GetBrightness() const
1925 {
1926     return brightness_;
1927 }
1928 
SetContrast(const std::optional<float> & contrast)1929 void RSProperties::SetContrast(const std::optional<float>& contrast)
1930 {
1931     contrast_ = contrast;
1932     colorFilterNeedUpdate_ = true;
1933     SetDirty();
1934     contentDirty_ = true;
1935 }
1936 
GetContrast() const1937 const std::optional<float>& RSProperties::GetContrast() const
1938 {
1939     return contrast_;
1940 }
1941 
SetSaturate(const std::optional<float> & saturate)1942 void RSProperties::SetSaturate(const std::optional<float>& saturate)
1943 {
1944     saturate_ = saturate;
1945     colorFilterNeedUpdate_ = true;
1946     SetDirty();
1947     contentDirty_ = true;
1948 }
1949 
GetSaturate() const1950 const std::optional<float>& RSProperties::GetSaturate() const
1951 {
1952     return saturate_;
1953 }
1954 
SetSepia(const std::optional<float> & sepia)1955 void RSProperties::SetSepia(const std::optional<float>& sepia)
1956 {
1957     sepia_ = sepia;
1958     colorFilterNeedUpdate_ = true;
1959     SetDirty();
1960     contentDirty_ = true;
1961 }
1962 
GetSepia() const1963 const std::optional<float>& RSProperties::GetSepia() const
1964 {
1965     return sepia_;
1966 }
1967 
SetInvert(const std::optional<float> & invert)1968 void RSProperties::SetInvert(const std::optional<float>& invert)
1969 {
1970     invert_ = invert;
1971     colorFilterNeedUpdate_ = true;
1972     SetDirty();
1973     contentDirty_ = true;
1974 }
1975 
GetInvert() const1976 const std::optional<float>& RSProperties::GetInvert() const
1977 {
1978     return invert_;
1979 }
1980 
1981 
SetAiInvert(const std::optional<Vector4f> & aiInvert)1982 void RSProperties::SetAiInvert(const std::optional<Vector4f>& aiInvert)
1983 {
1984     aiInvert_ = aiInvert;
1985     colorFilterNeedUpdate_ = true;
1986     SetDirty();
1987     contentDirty_ = true;
1988     isDrawn_ = true;
1989 }
1990 
GetAiInvert() const1991 const std::optional<Vector4f>& RSProperties::GetAiInvert() const
1992 {
1993     return aiInvert_;
1994 }
1995 
SetSystemBarEffect(bool systemBarEffect)1996 void RSProperties::SetSystemBarEffect(bool systemBarEffect)
1997 {
1998     systemBarEffect_ = systemBarEffect;
1999     colorFilterNeedUpdate_ = true;
2000     filterNeedUpdate_ = true;
2001     SetDirty();
2002     contentDirty_ = true;
2003     isDrawn_ = true;
2004 }
2005 
GetSystemBarEffect() const2006 bool RSProperties::GetSystemBarEffect() const
2007 {
2008     return systemBarEffect_;
2009 }
2010 
SetHueRotate(const std::optional<float> & hueRotate)2011 void RSProperties::SetHueRotate(const std::optional<float>& hueRotate)
2012 {
2013     hueRotate_ = hueRotate;
2014     colorFilterNeedUpdate_ = true;
2015     SetDirty();
2016     contentDirty_ = true;
2017 }
2018 
GetHueRotate() const2019 const std::optional<float>& RSProperties::GetHueRotate() const
2020 {
2021     return hueRotate_;
2022 }
2023 
SetColorBlend(const std::optional<Color> & colorBlend)2024 void RSProperties::SetColorBlend(const std::optional<Color>& colorBlend)
2025 {
2026     colorBlend_ = colorBlend;
2027     colorFilterNeedUpdate_ = true;
2028     SetDirty();
2029     contentDirty_ = true;
2030 }
2031 
GetColorBlend() const2032 const std::optional<Color>& RSProperties::GetColorBlend() const
2033 {
2034     return colorBlend_;
2035 }
2036 
GreatNotEqual(double left,double right)2037 static bool GreatNotEqual(double left, double right)
2038 {
2039     constexpr double epsilon = 0.001f;
2040     return (left - right) > epsilon;
2041 }
2042 
NearEqual(const double left,const double right)2043 static bool NearEqual(const double left, const double right)
2044 {
2045     constexpr double epsilon = 0.001f;
2046     return (std::abs(left - right) <= epsilon);
2047 }
2048 
GreatOrEqual(double left,double right)2049 static bool GreatOrEqual(double left, double right)
2050 {
2051     constexpr double epsilon = -0.001f;
2052     return (left - right) > epsilon;
2053 }
2054 
2055 #ifndef USE_ROSEN_DRAWING
GetColorFilter() const2056 const sk_sp<SkColorFilter>& RSProperties::GetColorFilter() const
2057 #else
2058 const std::shared_ptr<Drawing::ColorFilter>& RSProperties::GetColorFilter() const
2059 #endif
2060 {
2061     return colorFilter_;
2062 }
2063 
GenerateColorFilter()2064 void RSProperties::GenerateColorFilter()
2065 {
2066     // No update needed if color filter is valid
2067     if (!colorFilterNeedUpdate_) {
2068         return;
2069     }
2070 
2071     colorFilterNeedUpdate_ = false;
2072     colorFilter_ = nullptr;
2073     if (!grayScale_ && !brightness_ && !contrast_ && !saturate_ && !sepia_ && !invert_ && !hueRotate_ && !colorBlend_) {
2074         return;
2075     }
2076 
2077 #ifndef USE_ROSEN_DRAWING
2078     sk_sp<SkColorFilter> filter = nullptr;
2079 #else
2080     std::shared_ptr<Drawing::ColorFilter> filter = nullptr;
2081 #endif
2082 
2083     if (grayScale_.has_value() && GreatNotEqual(*grayScale_, 0.f)) {
2084         auto grayScale = grayScale_.value();
2085         float matrix[20] = { 0.0f }; // 20 : matrix size
2086         matrix[0] = matrix[INDEX_5] = matrix[INDEX_10] = 0.2126f * grayScale; // 0.2126 : gray scale coefficient
2087         matrix[1] = matrix[INDEX_6] = matrix[INDEX_11] = 0.7152f * grayScale; // 0.7152 : gray scale coefficient
2088         matrix[INDEX_2] = matrix[INDEX_7] = matrix[INDEX_12] = 0.0722f * grayScale; // 0.0722 : gray scale coefficient
2089         matrix[INDEX_18] = 1.0 * grayScale;
2090 #ifndef USE_ROSEN_DRAWING
2091         filter = SkColorFilters::Matrix(matrix);
2092         colorFilter_ = filter->makeComposed(colorFilter_);
2093 #else
2094         filter = Drawing::ColorFilter::CreateFloatColorFilter(matrix);
2095         if (colorFilter_) {
2096             filter->Compose(*colorFilter_);
2097         }
2098         colorFilter_ = filter;
2099 #endif
2100     }
2101     if (brightness_.has_value() && !NearEqual(*brightness_, 1.0)) {
2102         auto brightness = brightness_.value();
2103         float matrix[20] = { 0.0f }; // 20 : matrix size
2104         // shift brightness to (-1, 1)
2105         brightness = brightness - 1;
2106         matrix[0] = matrix[INDEX_6] = matrix[INDEX_12] = matrix[INDEX_18] = 1.0f;
2107         matrix[INDEX_4] = matrix[INDEX_9] = matrix[INDEX_14] = brightness;
2108 #ifndef USE_ROSEN_DRAWING
2109         filter = SkColorFilters::Matrix(matrix);
2110         colorFilter_ = filter->makeComposed(colorFilter_);
2111 #else
2112         filter = Drawing::ColorFilter::CreateFloatColorFilter(matrix);
2113         if (colorFilter_) {
2114             filter->Compose(*colorFilter_);
2115         }
2116         colorFilter_ = filter;
2117 #endif
2118     }
2119     if (contrast_.has_value() && !NearEqual(*contrast_, 1.0)) {
2120         auto contrast = contrast_.value();
2121         uint32_t contrastValue128 = 128;
2122         uint32_t contrastValue255 = 255;
2123         float matrix[20] = { 0.0f }; // 20 : matrix size
2124         matrix[0] = matrix[INDEX_6] = matrix[INDEX_12] = contrast;
2125         matrix[INDEX_4] = matrix[INDEX_9] = matrix[INDEX_14] = contrastValue128 * (1 - contrast) / contrastValue255;
2126         matrix[INDEX_18] = 1.0f;
2127 #ifndef USE_ROSEN_DRAWING
2128         filter = SkColorFilters::Matrix(matrix);
2129         colorFilter_ = filter->makeComposed(colorFilter_);
2130 #else
2131         filter = Drawing::ColorFilter::CreateFloatColorFilter(matrix);
2132         if (colorFilter_) {
2133             filter->Compose(*colorFilter_);
2134         }
2135         colorFilter_ = filter;
2136 #endif
2137     }
2138     if (saturate_.has_value() && !NearEqual(*saturate_, 1.0) && GreatOrEqual(*saturate_, 0.0)) {
2139         auto saturate = saturate_.value();
2140         float matrix[20] = { 0.0f }; // 20 : matrix size
2141         matrix[0] = 0.3086f * (1 - saturate) + saturate; // 0.3086 : saturate coefficient
2142         matrix[1] = matrix[INDEX_11] = 0.6094f * (1 - saturate); // 0.6094 : saturate coefficient
2143         matrix[INDEX_2] = matrix[INDEX_7] = 0.0820f * (1 - saturate); // 0.0820 : saturate coefficient
2144         matrix[INDEX_5] = matrix[INDEX_10] = 0.3086f * (1 - saturate); // 0.3086 : saturate coefficient
2145         matrix[INDEX_6] = 0.6094f * (1 - saturate) + saturate; // 0.6094 : saturate coefficient
2146         matrix[INDEX_12] = 0.0820f * (1 - saturate) + saturate; // 0.0820 : saturate coefficient
2147         matrix[INDEX_18] = 1.0f;
2148 #ifndef USE_ROSEN_DRAWING
2149         filter = SkColorFilters::Matrix(matrix);
2150         colorFilter_ = filter->makeComposed(colorFilter_);
2151 #else
2152         filter = Drawing::ColorFilter::CreateFloatColorFilter(matrix);
2153         if (colorFilter_) {
2154             filter->Compose(*colorFilter_);
2155         }
2156         colorFilter_ = filter;
2157 #endif
2158     }
2159     if (sepia_.has_value() && GreatNotEqual(*sepia_, 0.0)) {
2160         auto sepia = sepia_.value();
2161         float matrix[20] = { 0.0f }; // 20 : matrix size
2162         matrix[0] = 0.393f * sepia;
2163         matrix[1] = 0.769f * sepia;
2164         matrix[INDEX_2] = 0.189f * sepia;
2165 
2166         matrix[INDEX_5] = 0.349f * sepia;
2167         matrix[INDEX_6] = 0.686f * sepia;
2168         matrix[INDEX_7] = 0.168f * sepia;
2169 
2170         matrix[INDEX_10] = 0.272f * sepia;
2171         matrix[INDEX_11] = 0.534f * sepia;
2172         matrix[INDEX_12] = 0.131f * sepia;
2173         matrix[INDEX_18] = 1.0f * sepia;
2174 #ifndef USE_ROSEN_DRAWING
2175         filter = SkColorFilters::Matrix(matrix);
2176         colorFilter_ = filter->makeComposed(colorFilter_);
2177 #else
2178         filter = Drawing::ColorFilter::CreateFloatColorFilter(matrix);
2179         if (colorFilter_) {
2180             filter->Compose(*colorFilter_);
2181         }
2182         colorFilter_ = filter;
2183 #endif
2184     }
2185     if (invert_.has_value() && GreatNotEqual(*invert_, 0.0)) {
2186         auto invert = invert_.value();
2187         float matrix[20] = { 0.0f }; // 20 : matrix size
2188         if (invert > 1.0) {
2189             invert = 1.0;
2190         }
2191         // complete color invert when dstRGB = 1 - srcRGB
2192         // map (0, 1) to (1, -1)
2193         matrix[0] = matrix[INDEX_6] = matrix[INDEX_12] = 1.0 - 2.0 * invert; // 2.0: invert
2194         matrix[INDEX_18] = 1.0f;
2195         // invert = 0.5 -> RGB = (0.5, 0.5, 0.5) -> image completely gray
2196         matrix[INDEX_4] = matrix[INDEX_9] = matrix[INDEX_14] = invert;
2197 #ifndef USE_ROSEN_DRAWING
2198         filter = SkColorFilters::Matrix(matrix);
2199         colorFilter_ = filter->makeComposed(colorFilter_);
2200 #else
2201         filter = Drawing::ColorFilter::CreateFloatColorFilter(matrix);
2202         if (colorFilter_) {
2203             filter->Compose(*colorFilter_);
2204         }
2205         colorFilter_ = filter;
2206 #endif
2207     }
2208     if (hueRotate_.has_value() && GreatNotEqual(*hueRotate_, 0.0)) {
2209         auto hueRotate = hueRotate_.value();
2210         while (GreatOrEqual(hueRotate, 360)) { // 360 : degree
2211             hueRotate -= 360; // 360 : degree
2212         }
2213         float matrix[20] = { 0.0f }; // 20 : matrix size
2214         int32_t type = hueRotate / 120; // 120 : degree
2215         float N = (hueRotate - 120 * type) / 120; // 120 : degree
2216         switch (type) {
2217             case 0:
2218                 // color change = R->G, G->B, B->R
2219                 matrix[INDEX_2] = matrix[INDEX_5] = matrix[INDEX_11] = N;
2220                 matrix[0] = matrix[INDEX_6] = matrix[INDEX_12] = 1 - N;
2221                 matrix[INDEX_18] = 1.0f;
2222                 break;
2223             case 1:
2224                 // compare to original: R->B, G->R, B->G
2225                 matrix[1] = matrix[INDEX_7] = matrix[INDEX_10] = N;
2226                 matrix[INDEX_2] = matrix[INDEX_5] = matrix[INDEX_11] = 1 - N;
2227                 matrix[INDEX_18] = 1.0f;
2228                 break;
2229             case 2: // 2: back to normal color
2230                 matrix[0] = matrix[INDEX_6] = matrix[INDEX_12] = N;
2231                 matrix[1] = matrix[INDEX_7] = matrix[INDEX_10] = 1 - N;
2232                 matrix[INDEX_18] = 1.0f;
2233                 break;
2234             default:
2235                 break;
2236         }
2237 #ifndef USE_ROSEN_DRAWING
2238         filter = SkColorFilters::Matrix(matrix);
2239         colorFilter_ = filter->makeComposed(colorFilter_);
2240 #else
2241         filter = Drawing::ColorFilter::CreateFloatColorFilter(matrix);
2242         if (colorFilter_) {
2243             filter->Compose(*colorFilter_);
2244         }
2245         colorFilter_ = filter;
2246 #endif
2247     }
2248     if (colorBlend_.has_value() && *colorBlend_ != RgbPalette::Transparent()) {
2249         auto colorBlend = colorBlend_.value();
2250 #ifndef USE_ROSEN_DRAWING
2251         filter = SkColorFilters::Blend(
2252             SkColorSetARGB(colorBlend.GetAlpha(), colorBlend.GetRed(), colorBlend.GetGreen(), colorBlend.GetBlue()),
2253             SkBlendMode::kPlus);
2254         colorFilter_ = filter->makeComposed(colorFilter_);
2255 #else
2256         filter = Drawing::ColorFilter::CreateBlendModeColorFilter(Drawing::Color::ColorQuadSetARGB(
2257             colorBlend.GetAlpha(), colorBlend.GetRed(), colorBlend.GetGreen(), colorBlend.GetBlue()),
2258             Drawing::BlendMode::PLUS);
2259         if (colorFilter_) {
2260             filter->Compose(*colorFilter_);
2261         }
2262         colorFilter_ = filter;
2263 #endif
2264     }
2265     isDrawn_ = true;
2266 }
2267 
Dump() const2268 std::string RSProperties::Dump() const
2269 {
2270     std::string dumpInfo;
2271     char buffer[UINT8_MAX] = { 0 };
2272     if (sprintf_s(buffer, UINT8_MAX, "Bounds[%.1f %.1f %.1f %.1f] Frame[%.1f %.1f %.1f %.1f]",
2273         GetBoundsPositionX(), GetBoundsPositionY(), GetBoundsWidth(), GetBoundsHeight(),
2274         GetFramePositionX(), GetFramePositionY(), GetFrameWidth(), GetFrameHeight()) != -1) {
2275         dumpInfo.append(buffer);
2276     }
2277 
2278     // PositionZ
2279     auto ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2280     if (ret != EOK) {
2281         return "Failed to memset_s for PositionZ, ret=" + std::to_string(ret);
2282     }
2283     if (!ROSEN_EQ(GetPositionZ(), 0.f) &&
2284         sprintf_s(buffer, UINT8_MAX, ", PositionZ[%.1f]", GetPositionZ()) != -1) {
2285         dumpInfo.append(buffer);
2286     }
2287 
2288     // blendmode
2289     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2290     if (ret != EOK) {
2291         return "Failed to memset_s for blendmode, ret=" + std::to_string(ret);
2292     }
2293     if (!ROSEN_EQ(GetColorBlendMode(), 0) &&
2294         sprintf_s(buffer, UINT8_MAX, ", skblendmode[%d], blendType[%d]",
2295         GetColorBlendMode() - 1, GetColorBlendApplyType()) != -1) {
2296         dumpInfo.append(buffer);
2297     }
2298     // Pivot
2299     std::unique_ptr<Transform> defaultTrans = std::make_unique<Transform>();
2300     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2301     if (ret != EOK) {
2302         return "Failed to memset_s for Pivot, ret=" + std::to_string(ret);
2303     }
2304     Vector2f pivot = GetPivot();
2305     if ((!ROSEN_EQ(pivot[0], defaultTrans->pivotX_) || !ROSEN_EQ(pivot[1], defaultTrans->pivotY_)) &&
2306         sprintf_s(buffer, UINT8_MAX, ", Pivot[%.1f,%.1f]", pivot[0], pivot[1]) != -1) {
2307         dumpInfo.append(buffer);
2308     }
2309 
2310     // CornerRadius
2311     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2312     if (ret != EOK) {
2313         return "Failed to memset_s for CornerRadius, ret=" + std::to_string(ret);
2314     }
2315     if (!GetCornerRadius().IsZero() &&
2316         sprintf_s(buffer, UINT8_MAX, ", CornerRadius[%.1f %.1f %.1f %.1f]",
2317             GetCornerRadius().x_, GetCornerRadius().y_, GetCornerRadius().z_, GetCornerRadius().w_) != -1) {
2318         dumpInfo.append(buffer);
2319     }
2320 
2321     // PixelStretch PixelStretchPercent
2322     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2323     if (ret != EOK) {
2324         return "Failed to memset_s for PixelStretch, ret=" + std::to_string(ret);
2325     }
2326     if (pixelStretch_.has_value() &&
2327         sprintf_s(buffer, UINT8_MAX, ", PixelStretch[left:%.1f top:%.1f right:%.1f bottom:%.1f]",
2328             pixelStretch_->x_, pixelStretch_->y_, pixelStretch_->z_, pixelStretch_->w_) != -1) {
2329         dumpInfo.append(buffer);
2330     }
2331 
2332     // Rotation
2333     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2334     if (ret != EOK) {
2335         return "Failed to memset_s for Rotation, ret=" + std::to_string(ret);
2336     }
2337     if (!ROSEN_EQ(GetRotation(), defaultTrans->rotation_) &&
2338         sprintf_s(buffer, UINT8_MAX, ", Rotation[%.1f]", GetRotation()) != -1) {
2339         dumpInfo.append(buffer);
2340     }
2341     // RotationX
2342     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2343     if (ret != EOK) {
2344         return "Failed to memset_s for RotationX, ret=" + std::to_string(ret);
2345     }
2346     if (!ROSEN_EQ(GetRotationX(), defaultTrans->rotationX_) &&
2347         sprintf_s(buffer, UINT8_MAX, ", RotationX[%.1f]", GetRotationX()) != -1) {
2348         dumpInfo.append(buffer);
2349     }
2350     // RotationY
2351     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2352     if (ret != EOK) {
2353         return "Failed to memset_s for RotationY, ret=" + std::to_string(ret);
2354     }
2355     if (!ROSEN_EQ(GetRotationY(), defaultTrans->rotationY_) &&
2356         sprintf_s(buffer, UINT8_MAX, ", RotationY[%.1f]", GetRotationY()) != -1) {
2357         dumpInfo.append(buffer);
2358     }
2359 
2360     // TranslateX
2361     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2362     if (ret != EOK) {
2363         return "Failed to memset_s for TranslateX, ret=" + std::to_string(ret);
2364     }
2365     if (!ROSEN_EQ(GetTranslateX(), defaultTrans->translateX_) &&
2366         sprintf_s(buffer, UINT8_MAX, ", TranslateX[%.1f]", GetTranslateX()) != -1) {
2367         dumpInfo.append(buffer);
2368     }
2369 
2370     // TranslateY
2371     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2372     if (ret != EOK) {
2373         return "Failed to memset_s for TranslateY, ret=" + std::to_string(ret);
2374     }
2375     if (!ROSEN_EQ(GetTranslateY(), defaultTrans->translateY_) &&
2376         sprintf_s(buffer, UINT8_MAX, ", TranslateY[%.1f]", GetTranslateY()) != -1) {
2377         dumpInfo.append(buffer);
2378     }
2379 
2380     // TranslateZ
2381     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2382     if (ret != EOK) {
2383         return "Failed to memset_s for TranslateZ, ret=" + std::to_string(ret);
2384     }
2385     if (!ROSEN_EQ(GetTranslateZ(), defaultTrans->translateZ_) &&
2386         sprintf_s(buffer, UINT8_MAX, ", TranslateZ[%.1f]", GetTranslateZ()) != -1) {
2387         dumpInfo.append(buffer);
2388     }
2389 
2390     // ScaleX
2391     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2392     if (ret != EOK) {
2393         return "Failed to memset_s for ScaleX, ret=" + std::to_string(ret);
2394     }
2395     if (!ROSEN_EQ(GetScaleX(), defaultTrans->scaleX_) &&
2396         sprintf_s(buffer, UINT8_MAX, ", ScaleX[%.1f]", GetScaleX()) != -1) {
2397         dumpInfo.append(buffer);
2398     }
2399 
2400     // ScaleY
2401     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2402     if (ret != EOK) {
2403         return "Failed to memset_s for ScaleY, ret=" + std::to_string(ret);
2404     }
2405     if (!ROSEN_EQ(GetScaleY(), defaultTrans->scaleY_) &&
2406         sprintf_s(buffer, UINT8_MAX, ", ScaleY[%.1f]", GetScaleY()) != -1) {
2407         dumpInfo.append(buffer);
2408     }
2409 
2410     // Alpha
2411     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2412     if (ret != EOK) {
2413         return "Failed to memset_s for Alpha, ret=" + std::to_string(ret);
2414     }
2415     if (!ROSEN_EQ(GetAlpha(), 1.f) &&
2416         sprintf_s(buffer, UINT8_MAX, ", Alpha[%.1f]", GetAlpha()) != -1) {
2417         dumpInfo.append(buffer);
2418     }
2419 
2420     // Spherize
2421     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2422     if (ret != EOK) {
2423         return "Failed to memset_s for Spherize, ret=" + std::to_string(ret);
2424     }
2425     if (!ROSEN_EQ(GetSpherize(), 0.f) &&
2426         sprintf_s(buffer, UINT8_MAX, ", Spherize[%.1f]", GetSpherize()) != -1) {
2427         dumpInfo.append(buffer);
2428     }
2429 
2430     // LightUpEffect
2431     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2432     if (ret != EOK) {
2433         return "Failed to memset_s for LightUpEffect, ret=" + std::to_string(ret);
2434     }
2435     if (!ROSEN_EQ(GetLightUpEffect(), 1.f) &&
2436         sprintf_s(buffer, UINT8_MAX, ", LightUpEffect[%.1f]", GetLightUpEffect()) != -1) {
2437         dumpInfo.append(buffer);
2438     }
2439 
2440     // ForegroundColor
2441     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2442     if (ret != EOK) {
2443         return "Failed to memset_s for ForegroundColor, ret=" + std::to_string(ret);
2444     }
2445     if (!ROSEN_EQ(GetForegroundColor(), RgbPalette::Transparent()) &&
2446         sprintf_s(buffer, UINT8_MAX, ", ForegroundColor[#%08X]", GetForegroundColor().AsArgbInt()) != -1) {
2447         dumpInfo.append(buffer);
2448     }
2449 
2450     // BackgroundColor
2451     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2452     if (ret != EOK) {
2453         return "Failed to memset_s for BackgroundColor, ret=" + std::to_string(ret);
2454     }
2455     if (!ROSEN_EQ(GetBackgroundColor(), RgbPalette::Transparent()) &&
2456         sprintf_s(buffer, UINT8_MAX, ", BackgroundColor[#%08X]", GetBackgroundColor().AsArgbInt()) != -1) {
2457         dumpInfo.append(buffer);
2458     }
2459 
2460     // BgImage
2461     std::unique_ptr<Decoration> defaultDecoration = std::make_unique<Decoration>();
2462     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2463     if (ret != EOK) {
2464         return "Failed to memset_s for BgImage, ret=" + std::to_string(ret);
2465     }
2466     if ((!ROSEN_EQ(GetBgImagePositionX(), defaultDecoration->bgImageRect_.left_) ||
2467         !ROSEN_EQ(GetBgImagePositionY(), defaultDecoration->bgImageRect_.top_) ||
2468         !ROSEN_EQ(GetBgImageWidth(), defaultDecoration->bgImageRect_.width_) ||
2469         !ROSEN_EQ(GetBgImageHeight(), defaultDecoration->bgImageRect_.height_)) &&
2470         sprintf_s(buffer, UINT8_MAX, ", BgImage[%.1f %.1f %.1f %.1f]", GetBgImagePositionX(),
2471             GetBgImagePositionY(), GetBgImageWidth(), GetBgImageHeight()) != -1) {
2472         dumpInfo.append(buffer);
2473     }
2474 
2475     // Border
2476     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2477     if (ret != EOK) {
2478         return "Failed to memset_s for Border, ret=" + std::to_string(ret);
2479     }
2480     if (border_ && border_->HasBorder() &&
2481         sprintf_s(buffer, UINT8_MAX, ", Border[%s]", border_->ToString().c_str()) != -1) {
2482         dumpInfo.append(buffer);
2483     }
2484 
2485     // Filter
2486     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2487     if (ret != EOK) {
2488         return "Failed to memset_s for Filter, ret=" + std::to_string(ret);
2489     }
2490     auto filter_ = GetFilter();
2491     if (filter_ && filter_->IsValid() &&
2492         sprintf_s(buffer, UINT8_MAX, ", Filter[%s]", filter_->GetDescription().c_str()) != -1) {
2493         dumpInfo.append(buffer);
2494     }
2495 
2496     // BackgroundFilter
2497     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2498     if (ret != EOK) {
2499         return "Failed to memset_s for BackgroundFilter, ret=" + std::to_string(ret);
2500     }
2501     auto backgroundFilter_ = GetBackgroundFilter();
2502     if (backgroundFilter_ && backgroundFilter_->IsValid() &&
2503         sprintf_s(buffer, UINT8_MAX, ", BackgroundFilter[%s]", backgroundFilter_->GetDescription().c_str()) != -1) {
2504         dumpInfo.append(buffer);
2505     }
2506 
2507     // Outline
2508     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2509     if (ret != EOK) {
2510         return "Failed to memset_s for Outline, ret=" + std::to_string(ret);
2511     }
2512     if (outline_ && outline_->HasBorder() &&
2513         sprintf_s(buffer, UINT8_MAX, ", Outline[%s]", outline_->ToString().c_str()) != -1) {
2514         dumpInfo.append(buffer);
2515     }
2516 
2517     // ShadowColor
2518     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2519     if (ret != EOK) {
2520         return "Failed to memset_s for ShadowColor, ret=" + std::to_string(ret);
2521     }
2522     if (!ROSEN_EQ(GetShadowColor(), Color(DEFAULT_SPOT_COLOR)) &&
2523         sprintf_s(buffer, UINT8_MAX, ", ShadowColor[#%08X]", GetShadowColor().AsArgbInt()) != -1) {
2524         dumpInfo.append(buffer);
2525     }
2526 
2527     // ShadowOffsetX
2528     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2529     if (ret != EOK) {
2530         return "Failed to memset_s for ShadowOffsetX, ret=" + std::to_string(ret);
2531     }
2532     if (!ROSEN_EQ(GetShadowOffsetX(), DEFAULT_SHADOW_OFFSET_X) &&
2533         sprintf_s(buffer, UINT8_MAX, ", ShadowOffsetX[%.1f]", GetShadowOffsetX()) != -1) {
2534         dumpInfo.append(buffer);
2535     }
2536 
2537     // ShadowOffsetY
2538     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2539     if (ret != EOK) {
2540         return "Failed to memset_s for ShadowOffsetY, ret=" + std::to_string(ret);
2541     }
2542     if (!ROSEN_EQ(GetShadowOffsetY(), DEFAULT_SHADOW_OFFSET_Y) &&
2543         sprintf_s(buffer, UINT8_MAX, ", ShadowOffsetY[%.1f]", GetShadowOffsetY()) != -1) {
2544         dumpInfo.append(buffer);
2545     }
2546 
2547     // ShadowAlpha
2548     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2549     if (ret != EOK) {
2550         return "Failed to memset_s for ShadowAlpha, ret=" + std::to_string(ret);
2551     }
2552     if (!ROSEN_EQ(GetShadowAlpha(), 0.f) &&
2553         sprintf_s(buffer, UINT8_MAX, ", ShadowAlpha[%.1f]", GetShadowAlpha()) != -1) {
2554         dumpInfo.append(buffer);
2555     }
2556 
2557     // ShadowElevation
2558     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2559     if (ret != EOK) {
2560         return "Failed to memset_s for ShadowElevation, ret=" + std::to_string(ret);
2561     }
2562     if (!ROSEN_EQ(GetShadowElevation(), 0.f) &&
2563         sprintf_s(buffer, UINT8_MAX, ", ShadowElevation[%.1f]", GetShadowElevation()) != -1) {
2564         dumpInfo.append(buffer);
2565     }
2566 
2567     // ShadowRadius
2568     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2569     if (ret != EOK) {
2570         return "Failed to memset_s for ShadowRadius, ret=" + std::to_string(ret);
2571     }
2572     if (!ROSEN_EQ(GetShadowRadius(), 0.f) &&
2573         sprintf_s(buffer, UINT8_MAX, ", ShadowRadius[%.1f]", GetShadowRadius()) != -1) {
2574         dumpInfo.append(buffer);
2575     }
2576 
2577     // ShadowIsFilled
2578     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2579     if (ret != EOK) {
2580         return "Failed to memset_s for ShadowIsFilled, ret=" + std::to_string(ret);
2581     }
2582     if (!ROSEN_EQ(GetShadowIsFilled(), false) &&
2583         sprintf_s(buffer, UINT8_MAX, ", ShadowIsFilled[%d]", GetShadowIsFilled()) != -1) {
2584         dumpInfo.append(buffer);
2585     }
2586 
2587     // FrameGravity
2588     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2589     if (ret != EOK) {
2590         return "Failed to memset_s for FrameGravity, ret=" + std::to_string(ret);
2591     }
2592     if (!ROSEN_EQ(GetFrameGravity(), Gravity::DEFAULT) &&
2593         sprintf_s(buffer, UINT8_MAX, ", FrameGravity[%d]", GetFrameGravity()) != -1) {
2594         dumpInfo.append(buffer);
2595     }
2596 
2597     // IsVisible
2598     if (!GetVisible()) {
2599         dumpInfo.append(", IsVisible[false]");
2600     }
2601 
2602     // UseEffect
2603     if (GetUseEffect()) {
2604         dumpInfo.append(", GetUseEffect[true]");
2605     }
2606 
2607     // Gray Scale
2608     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2609     if (ret != EOK) {
2610         return "Failed to memset_s for GrayScale, ret=" + std::to_string(ret);
2611     }
2612     auto grayScale = GetGrayScale();
2613     if (grayScale.has_value() && !ROSEN_EQ(*grayScale, 0.f) &&
2614         sprintf_s(buffer, UINT8_MAX, ", GrayScale[%.1f]", *grayScale) != -1) {
2615         dumpInfo.append(buffer);
2616     }
2617 
2618     // DynamicLightUpRate
2619     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2620     if (ret != EOK) {
2621         return "Failed to memset_s for DynamicLightUpRate, ret=" + std::to_string(ret);
2622     }
2623     auto dynamicLightUpRate = GetDynamicLightUpRate();
2624     if (dynamicLightUpRate.has_value() && !ROSEN_EQ(*dynamicLightUpRate, 0.f) &&
2625         sprintf_s(buffer, UINT8_MAX, ", DynamicLightUpRate[%.1f]", *dynamicLightUpRate) != -1) {
2626         dumpInfo.append(buffer);
2627     }
2628 
2629     // DynamicLightUpDegree
2630     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2631     if (ret != EOK) {
2632         return "Failed to memset_s for DynamicLightUpDegree, ret=" + std::to_string(ret);
2633     }
2634     auto dynamicLightUpDegree = GetDynamicLightUpDegree();
2635     if (dynamicLightUpDegree.has_value() && !ROSEN_EQ(*dynamicLightUpDegree, 0.f) &&
2636         sprintf_s(buffer, UINT8_MAX, ", DynamicLightUpDegree[%.1f]", *dynamicLightUpDegree) != -1) {
2637         dumpInfo.append(buffer);
2638     }
2639 
2640     // Brightness
2641     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2642     if (ret != EOK) {
2643         return "Failed to memset_s for Brightness, ret=" + std::to_string(ret);
2644     }
2645     auto brightness = GetBrightness();
2646     if (brightness.has_value() && !ROSEN_EQ(*brightness, 1.f) &&
2647         sprintf_s(buffer, UINT8_MAX, ", Brightness[%.1f]", *brightness) != -1) {
2648         dumpInfo.append(buffer);
2649     }
2650 
2651     // Contrast
2652     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2653     if (ret != EOK) {
2654         return "Failed to memset_s for Contrast, ret=" + std::to_string(ret);
2655     }
2656     auto contrast = GetContrast();
2657     if (contrast.has_value() && !ROSEN_EQ(*contrast, 1.f) &&
2658         sprintf_s(buffer, UINT8_MAX, ", Contrast[%.1f]", *contrast) != -1) {
2659         dumpInfo.append(buffer);
2660     }
2661 
2662     // Saturate
2663     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2664     if (ret != EOK) {
2665         return "Failed to memset_s for Saturate, ret=" + std::to_string(ret);
2666     }
2667     auto saturate = GetSaturate();
2668     if (saturate.has_value() && !ROSEN_EQ(*saturate, 1.f) &&
2669         sprintf_s(buffer, UINT8_MAX, ", Saturate[%.1f]", *saturate) != -1) {
2670         dumpInfo.append(buffer);
2671     }
2672 
2673     // Sepia
2674     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2675     if (ret != EOK) {
2676         return "Failed to memset_s for Sepia, ret=" + std::to_string(ret);
2677     }
2678     auto sepia = GetSepia();
2679     if (sepia.has_value() && !ROSEN_EQ(*sepia, 0.f) &&
2680         sprintf_s(buffer, UINT8_MAX, ", Sepia[%.1f]", *sepia) != -1) {
2681         dumpInfo.append(buffer);
2682     }
2683 
2684     // Invert
2685     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2686     if (ret != EOK) {
2687         return "Failed to memset_s for Invert, ret=" + std::to_string(ret);
2688     }
2689     auto invert = GetInvert();
2690     if (invert.has_value() && !ROSEN_EQ(*invert, 0.f) &&
2691         sprintf_s(buffer, UINT8_MAX, ", Invert[%.1f]", *invert) != -1) {
2692         dumpInfo.append(buffer);
2693     }
2694 
2695     // Hue Rotate
2696     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2697     if (ret != EOK) {
2698         return "Failed to memset_s for HueRotate, ret=" + std::to_string(ret);
2699     }
2700     auto hueRotate = GetHueRotate();
2701     if (hueRotate.has_value() && !ROSEN_EQ(*hueRotate, 0.f) &&
2702         sprintf_s(buffer, UINT8_MAX, ", HueRotate[%.1f]", *hueRotate) != -1) {
2703         dumpInfo.append(buffer);
2704     }
2705 
2706     // Color Blend
2707     ret = memset_s(buffer, UINT8_MAX, 0, UINT8_MAX);
2708     if (ret != EOK) {
2709         return "Failed to memset_s for ColorBlend, ret=" + std::to_string(ret);
2710     }
2711     auto colorBlend = GetColorBlend();
2712     if (colorBlend.has_value() && !ROSEN_EQ(*colorBlend, RgbPalette::Transparent()) &&
2713         sprintf_s(buffer, UINT8_MAX, ", ColorBlend[#%08X]", colorBlend->AsArgbInt()) != -1) {
2714         dumpInfo.append(buffer);
2715     }
2716 
2717     return dumpInfo;
2718 }
2719 
2720 #if defined(NEW_SKIA) && (defined(RS_ENABLE_GL) || defined(RS_ENABLE_VK))
CreateFilterCacheManagerIfNeed()2721 void RSProperties::CreateFilterCacheManagerIfNeed()
2722 {
2723     if (!FilterCacheEnabled) {
2724         return;
2725     }
2726     if (auto& filter = GetBackgroundFilter()) {
2727         auto& cacheManager = backgroundFilterCacheManager_;
2728         if (cacheManager == nullptr) {
2729             cacheManager = std::make_unique<RSFilterCacheManager>();
2730         }
2731         cacheManager->UpdateCacheStateWithFilterHash(filter);
2732     } else {
2733         if (backgroundFilterCacheManager_ != nullptr) {
2734             backgroundFilterCacheManager_->ReleaseCacheOffTree();
2735         }
2736         backgroundFilterCacheManager_.reset();
2737     }
2738     if (auto& filter = GetFilter()) {
2739         auto& cacheManager = foregroundFilterCacheManager_;
2740         if (cacheManager == nullptr) {
2741             cacheManager = std::make_unique<RSFilterCacheManager>();
2742         }
2743         cacheManager->UpdateCacheStateWithFilterHash(filter);
2744     } else {
2745         if (foregroundFilterCacheManager_ != nullptr) {
2746             foregroundFilterCacheManager_->ReleaseCacheOffTree();
2747         }
2748         foregroundFilterCacheManager_.reset();
2749     }
2750 }
2751 
GetFilterCacheManager(bool isForeground) const2752 const std::unique_ptr<RSFilterCacheManager>& RSProperties::GetFilterCacheManager(bool isForeground) const
2753 {
2754     return isForeground ? foregroundFilterCacheManager_ : backgroundFilterCacheManager_;
2755 }
2756 
ClearFilterCache()2757 void RSProperties::ClearFilterCache()
2758 {
2759     if (foregroundFilterCacheManager_ != nullptr) {
2760         foregroundFilterCacheManager_->ReleaseCacheOffTree();
2761     }
2762     if (backgroundFilterCacheManager_ != nullptr) {
2763         backgroundFilterCacheManager_->ReleaseCacheOffTree();
2764     }
2765     if (backgroundFilter_ != nullptr && (backgroundFilter_->GetFilterType() == RSFilter::MATERIAL)) {
2766         auto filter = std::static_pointer_cast<RSMaterialFilter>(backgroundFilter_);
2767         filter->ReleaseColorPickerFilter();
2768     }
2769     if (filter_ != nullptr && (filter_->GetFilterType() == RSFilter::MATERIAL)) {
2770         auto filter = std::static_pointer_cast<RSMaterialFilter>(filter_);
2771         filter->ReleaseColorPickerFilter();
2772     }
2773 }
2774 
CreateColorPickerTaskForShadow()2775 void RSProperties::CreateColorPickerTaskForShadow()
2776 {
2777     if (colorPickerTaskShadow_ == nullptr) {
2778         colorPickerTaskShadow_ = std::make_shared<RSColorPickerCacheTask>();
2779     }
2780 }
2781 
2782 #endif
2783 
OnApplyModifiers()2784 void RSProperties::OnApplyModifiers()
2785 {
2786     if (geoDirty_) {
2787         if (!hasBounds_) {
2788             CheckEmptyBounds();
2789         } else {
2790             CalculateFrameOffset();
2791         }
2792         // frame and bounds are the same, no need to clip twice
2793         if (clipToFrame_ && clipToBounds_ && frameOffsetX_ == 0 && frameOffsetY_ == 0) {
2794             clipToFrame_ = false;
2795         }
2796         if (RSSystemProperties::IsPcType()) {
2797             frameGeo_->Round();
2798             boundsGeo_->Round();
2799         }
2800     }
2801     if (colorFilterNeedUpdate_) {
2802         GenerateColorFilter();
2803     }
2804     if (pixelStretchNeedUpdate_ || geoDirty_) {
2805         CalculatePixelStretch();
2806     }
2807     if (filterNeedUpdate_) {
2808         filterNeedUpdate_ = false;
2809         if (GetShadowColorStrategy() != SHADOW_COLOR_STRATEGY::COLOR_STRATEGY_NONE) {
2810             filterNeedUpdate_ = true;
2811         }
2812         if (systemBarEffect_) {
2813             auto aiBarFilter = std::make_shared<RSAIBarFilter>();
2814             backgroundFilter_ = aiBarFilter;
2815         }
2816         if (backgroundFilter_ != nullptr && !backgroundFilter_->IsValid()) {
2817             backgroundFilter_.reset();
2818         }
2819         if (filter_ != nullptr && !filter_->IsValid()) {
2820             filter_.reset();
2821         }
2822         IfLinearGradientBlurInvalid();
2823         if (linearGradientBlurPara_) {
2824             auto linearBlurFilter = std::make_shared<RSLinearGradientBlurFilter>(linearGradientBlurPara_,
2825                 frameGeo_->GetWidth(), frameGeo_->GetHeight());
2826             filter_ = linearBlurFilter;
2827         }
2828         needFilter_ = backgroundFilter_ != nullptr || filter_ != nullptr || useEffect_ || IsLightUpEffectValid() ||
2829                         IsDynamicLightUpValid() || IsGreyAdjustmentValid() || linearGradientBlurPara_ != nullptr ||
2830                         GetShadowColorStrategy() != SHADOW_COLOR_STRATEGY::COLOR_STRATEGY_NONE;
2831 #if defined(NEW_SKIA) && (defined(RS_ENABLE_GL) || defined(RS_ENABLE_VK))
2832         CreateFilterCacheManagerIfNeed();
2833 #endif
2834     }
2835     GenerateRRect();
2836 }
2837 
CalculatePixelStretch()2838 void RSProperties::CalculatePixelStretch()
2839 {
2840     pixelStretchNeedUpdate_ = false;
2841     // no pixel stretch
2842     if (!pixelStretch_.has_value() && !pixelStretchPercent_.has_value()) {
2843         return;
2844     }
2845     // convert pixel stretch percent to pixel stretch
2846     if (pixelStretchPercent_) {
2847         auto width = GetBoundsWidth();
2848         auto height = GetBoundsHeight();
2849         if (isinf(width) || isinf(height)) {
2850             return;
2851         }
2852         pixelStretch_ = *pixelStretchPercent_ * Vector4f(width, height, width, height);
2853     }
2854     constexpr static float EPS = 1e-5f;
2855     // parameter check: near zero
2856     if (abs(pixelStretch_->x_) < EPS && abs(pixelStretch_->y_) < EPS && abs(pixelStretch_->z_) < EPS &&
2857         abs(pixelStretch_->w_) < EPS) {
2858         pixelStretch_ = std::nullopt;
2859         return;
2860     }
2861     // parameter check: all >= 0 or all <= 0
2862     if ((pixelStretch_->x_ < EPS && pixelStretch_->y_ < EPS && pixelStretch_->z_ < EPS && pixelStretch_->w_ < EPS) ||
2863         (pixelStretch_->x_ > -EPS && pixelStretch_->y_ > -EPS && pixelStretch_->z_ > -EPS &&
2864             pixelStretch_->w_ > -EPS)) {
2865         isDrawn_ = true;
2866         return;
2867     }
2868     pixelStretch_ = std::nullopt;
2869 }
2870 
CalculateFrameOffset()2871 void RSProperties::CalculateFrameOffset()
2872 {
2873     frameOffsetX_ = frameGeo_->GetX() - boundsGeo_->GetX();
2874     frameOffsetY_ = frameGeo_->GetY() - boundsGeo_->GetY();
2875     if (isinf(frameOffsetX_)) {
2876         frameOffsetX_ = 0.;
2877     }
2878     if (isinf(frameOffsetY_)) {
2879         frameOffsetY_ = 0.;
2880     }
2881     if (frameOffsetX_ != 0. || frameOffsetY_ != 0.) {
2882         isDrawn_ = true;
2883     }
2884 }
2885 
2886 // blend with background
SetColorBlendMode(int colorBlendMode)2887 void RSProperties::SetColorBlendMode(int colorBlendMode)
2888 {
2889     colorBlendMode_ = std::clamp<int>(colorBlendMode, 0, static_cast<int>(RSColorBlendMode::MAX));
2890     if (colorBlendMode_ != static_cast<int>(RSColorBlendMode::NONE)) {
2891         isDrawn_ = true;
2892     }
2893     SetDirty();
2894     contentDirty_ = true;
2895 }
2896 
GetColorBlendMode() const2897 int RSProperties::GetColorBlendMode() const
2898 {
2899     return colorBlendMode_;
2900 }
2901 
SetColorBlendApplyType(int colorBlendApplyType)2902 void RSProperties::SetColorBlendApplyType(int colorBlendApplyType)
2903 {
2904     colorBlendApplyType_ = std::clamp<int>(colorBlendApplyType, 0, static_cast<int>(RSColorBlendApplyType::MAX));
2905     isDrawn_ = true;
2906     SetDirty();
2907     contentDirty_ = true;
2908 }
2909 
GetColorBlendApplyType() const2910 int RSProperties::GetColorBlendApplyType() const
2911 {
2912     return colorBlendApplyType_;
2913 }
2914 
GetColorPickerCacheTaskShadow() const2915 const std::shared_ptr<RSColorPickerCacheTask>& RSProperties::GetColorPickerCacheTaskShadow() const
2916 {
2917     return colorPickerTaskShadow_;
2918 }
2919 
ReleaseColorPickerTaskShadow() const2920 void RSProperties::ReleaseColorPickerTaskShadow() const
2921 {
2922     if (colorPickerTaskShadow_ == nullptr) {
2923         return;
2924     }
2925     colorPickerTaskShadow_->ReleaseColorPicker();
2926 }
2927 
2928 
GetHaveEffectRegion() const2929 bool RSProperties::GetHaveEffectRegion() const
2930 {
2931     return haveEffectRegion_;
2932 }
2933 
SetHaveEffectRegion(bool haveEffectRegion)2934 void RSProperties::SetHaveEffectRegion(bool haveEffectRegion)
2935 {
2936     // clear cache if new region is null or outside current region
2937     if (auto& manager = GetFilterCacheManager(false);
2938         manager && manager->IsCacheValid() && haveEffectRegion == false) {
2939         manager->UpdateCacheStateWithFilterRegion();
2940     }
2941     haveEffectRegion_ = haveEffectRegion;
2942 }
2943 } // namespace Rosen
2944 } // namespace OHOS
2945