• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022-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 "core/components_ng/render/adapter/rosen_render_context.h"
17 
18 #include <memory>
19 
20 #include "include/utils/SkParsePath.h"
21 #include "modifier/rs_property.h"
22 #include "render_service_base/include/property/rs_properties_def.h"
23 #include "render_service_base/include/render/rs_mask.h"
24 #include "render_service_client/core/pipeline/rs_node_map.h"
25 #include "render_service_client/core/transaction/rs_transaction.h"
26 #include "render_service_client/core/transaction/rs_interfaces.h"
27 #include "render_service_client/core/ui/rs_canvas_drawing_node.h"
28 #include "render_service_client/core/ui/rs_canvas_node.h"
29 #include "render_service_client/core/ui/rs_effect_node.h"
30 #include "render_service_client/core/ui/rs_node.h"
31 #include "render_service_client/core/ui/rs_root_node.h"
32 #include "render_service_client/core/ui/rs_surface_node.h"
33 #include "render_service_client/core/ui/rs_ui_context.h"
34 #include "rosen_render_context.h"
35 
36 #include "base/geometry/calc_dimension.h"
37 #include "base/geometry/dimension.h"
38 #include "base/geometry/matrix4.h"
39 #include "base/log/dump_log.h"
40 #include "base/utils/utils.h"
41 #include "core/animation/animation_pub.h"
42 #include "core/animation/native_curve_helper.h"
43 #include "core/components/theme/app_theme.h"
44 #include "core/components/theme/blur_style_theme.h"
45 #include "core/common/ace_engine.h"
46 #include "core/common/resource/resource_parse_utils.h"
47 #include "core/components_ng/pattern/overlay/accessibility_focus_paint_node_pattern.h"
48 #include "core/components_ng/pattern/particle/particle_pattern.h"
49 #include "core/components_ng/property/measure_utils.h"
50 #include "core/components_ng/pattern/stage/page_pattern.h"
51 #include "core/components_ng/render/adapter/background_modifier.h"
52 #include "core/components_ng/render/adapter/border_image_modifier.h"
53 #include "core/components_ng/render/adapter/component_snapshot.h"
54 #include "core/components_ng/render/adapter/debug_boundary_modifier.h"
55 #include "core/components_ng/render/adapter/focus_state_modifier.h"
56 #include "core/components_ng/render/adapter/gradient_style_modifier.h"
57 #include "core/components_ng/render/adapter/mouse_select_modifier.h"
58 #include "core/components_ng/render/adapter/overlay_modifier.h"
59 #include "core/components_ng/render/adapter/pixelmap_image.h"
60 #include "core/components_ng/render/adapter/rosen_window.h"
61 #include "core/components_ng/render/adapter/transition_modifier.h"
62 #if defined(ANDROID_PLATFORM) || defined(IOS_PLATFORM)
63 #include "render_service_client/core/pipeline/rs_render_thread.h"
64 #endif
65 #include "core/components_ng/render/adapter/drawing_decoration_painter.h"
66 #include "core/components_ng/render/adapter/drawing_image.h"
67 #include "core/components_ng/pattern/checkbox/checkbox_paint_property.h"
68 #include "core/components_ng/render/animation_utils.h"
69 #include "core/components_ng/render/border_image_painter.h"
70 #include "core/components_ng/render/debug_boundary_painter.h"
71 #include "core/components_ng/render/image_painter.h"
72 #include "interfaces/inner_api/ace_kit/include/ui/view/draw/modifier.h"
73 #include "core/pipeline/pipeline_base.h"
74 #include "base/utils/multi_thread.h"
75 
76 namespace OHOS::Ace::NG {
77 
78 using namespace OHOS::Rosen;
79 namespace {
80 RefPtr<PixelMap> g_pixelMap {};
81 std::mutex g_mutex;
82 std::condition_variable thumbnailGet;
83 constexpr std::chrono::duration<int, std::milli> PIXELMAP_TIMEOUT_DURATION(1000);
84 constexpr float ANIMATION_CURVE_VELOCITY_LIGHT_OR_MIDDLE = 10.0f;
85 constexpr float ANIMATION_CURVE_VELOCITY_HEAVY = 0.0f;
86 constexpr float ANIMATION_CURVE_MASS = 1.0f;
87 constexpr float ANIMATION_CURVE_STIFFNESS_LIGHT = 410.0f;
88 constexpr float ANIMATION_CURVE_STIFFNESS_MIDDLE = 350.0f;
89 constexpr float ANIMATION_CURVE_STIFFNESS_HEAVY = 240.0f;
90 constexpr float ANIMATION_CURVE_DAMPING_LIGHT = 38.0f;
91 constexpr float ANIMATION_CURVE_DAMPING_MIDDLE = 35.0f;
92 constexpr float ANIMATION_CURVE_DAMPING_HEAVY = 28.0f;
93 constexpr float DEFAULT_SCALE_LIGHT = 0.9f;
94 constexpr float DEFAULT_SCALE_MIDDLE_OR_HEAVY = 0.95f;
95 constexpr int32_t DEFAULT_OPTION_DURATION = 100;
96 constexpr int32_t PLATFORM_VERSION_TEN = 10;
97 constexpr int32_t PARTICLE_DEFAULT_COLOR = 0xFFFFFFFF;
98 constexpr float PARTICLE_DEFAULT_OPACITY = 1.0f;
99 constexpr float PARTICLE_DEFAULT_SCALE = 1.0f;
100 constexpr float PARTICLE_DEFAULT_SPEED = 0.0f;
101 constexpr float PARTICLE_DEFAULT_ANGLE = 0.0f;
102 constexpr float PARTICLE_DEFAULT_SPIN = 0.0f;
103 constexpr int64_t PARTICLE_DEFAULT_LIFETIME = 1000;
104 constexpr int32_t PARTICLE_DEFAULT_EMITTER_RATE = 5;
105 constexpr uint32_t DRAW_REGION_CONTENT_MODIFIER_INDEX = 0;
106 constexpr uint32_t DRAW_REGION_OVERLAY_MODIFIER_INDEX = 1;
107 constexpr uint32_t DRAW_REGION_FOCUS_MODIFIER_INDEX = 2;
108 constexpr uint32_t DRAW_REGION_ACCESSIBILITY_FOCUS_MODIFIER_INDEX = 3;
109 constexpr uint32_t DRAW_REGION_OVERLAY_TEXT_MODIFIER_INDEX = 4;
110 constexpr uint32_t DRAW_REGION_DEBUG_BOUNDARY_MODIFIER_INDEX = 5;
111 constexpr uint32_t DRAW_REGION_FOREGROUND_MODIFIER_INDEX = 6;
112 constexpr uint32_t DRAW_REGION_TRANSITION_MODIFIER_INDEX = 7;
113 constexpr int32_t RIGHT_ANGLE = 90;
114 constexpr int32_t STRAIGHT_ANGLE = 180;
115 constexpr int32_t REFLEX_ANGLE = 270;
116 constexpr int32_t FULL_ROTATION = 360;
117 constexpr int32_t ACCESSIBILITY_FOCUS_WITHOUT_EVENT = -2100001;
118 const Color MASK_COLOR = Color::FromARGB(25, 0, 0, 0);
119 const Color DEFAULT_MASK_COLOR = Color::FromARGB(0, 0, 0, 0);
120 constexpr Dimension DASH_GEP_WIDTH = -1.0_px;
121 constexpr int32_t INDEX_0 = 0;
122 constexpr int32_t INDEX_1 = 1;
123 constexpr int32_t INDEX_2 = 2;
124 constexpr int32_t INDEX_3 = 3;
125 constexpr float FLOAT_ZERO = 0.0f;
126 constexpr uint16_t NO_FORCE_ROUND = static_cast<uint16_t>(PixelRoundPolicy::NO_FORCE_ROUND_START) |
127                                     static_cast<uint16_t>(PixelRoundPolicy::NO_FORCE_ROUND_TOP) |
128                                     static_cast<uint16_t>(PixelRoundPolicy::NO_FORCE_ROUND_END) |
129                                     static_cast<uint16_t>(PixelRoundPolicy::NO_FORCE_ROUND_BOTTOM);
130 const int FACTOR_TWO = 2;
131 
DrawNodeChangeCallback(std::shared_ptr<RSNode> rsNode,bool isPositionZ)132 static void DrawNodeChangeCallback(std::shared_ptr<RSNode> rsNode, bool isPositionZ)
133 {
134     if (!SystemProperties::GetContainerDeleteFlag()) {
135         return;
136     }
137     CHECK_NULL_VOID(rsNode);
138     auto uiNode = ElementRegister::GetInstance()->GetUINodeById(rsNode->GetFrameNodeId());
139     auto frameNode = AceType::DynamicCast<NG::FrameNode>(uiNode);
140     CHECK_NULL_VOID(frameNode);
141     if (isPositionZ) {
142         frameNode->SetPositionZ(true);
143         auto pipeline = uiNode->GetContext();
144         CHECK_NULL_VOID(pipeline);
145         pipeline->AddPositionZNode(rsNode->GetFrameNodeId());
146         return;
147     }
148 
149     if (frameNode->GetRenderContext()) {
150         frameNode->GetRenderContext()->AddNodeToRsTree();
151     }
152 }
153 
SetDrawNodeChangeCallback()154 bool SetDrawNodeChangeCallback()
155 {
156     Rosen::RSNode::SetDrawNodeChangeCallback(DrawNodeChangeCallback);
157     return true;
158 }
159 
PropertyNodeChangeCallback()160 static void PropertyNodeChangeCallback()
161 {
162     AceEngine::Get().NotifyContainers([](const RefPtr<Container>& container) {
163         auto pipeline = AceType::DynamicCast<NG::PipelineContext>(container->GetPipelineContext());
164         if (pipeline) {
165             pipeline->SetNeedCallbackAreaChange(true);
166         }
167     });
168     Rosen::RSNode::SetNeedCallbackNodeChange(false);
169 }
170 
SetPropertyNodeChangeCallback()171 bool SetPropertyNodeChangeCallback()
172 {
173     Rosen::RSNode::SetPropertyNodeChangeCallback(PropertyNodeChangeCallback);
174     return true;
175 }
176 
GetRosenGravity(RenderFit renderFit)177 Rosen::Gravity GetRosenGravity(RenderFit renderFit)
178 {
179     static const LinearEnumMapNode<RenderFit, Rosen::Gravity> gravityMap[] = {
180         { RenderFit::CENTER, Rosen::Gravity::CENTER },
181         { RenderFit::TOP, Rosen::Gravity::TOP },
182         { RenderFit::BOTTOM, Rosen::Gravity::BOTTOM },
183         { RenderFit::LEFT, Rosen::Gravity::LEFT },
184         { RenderFit::RIGHT, Rosen::Gravity::RIGHT },
185         { RenderFit::TOP_LEFT, Rosen::Gravity::TOP_LEFT },
186         { RenderFit::TOP_RIGHT, Rosen::Gravity::TOP_RIGHT },
187         { RenderFit::BOTTOM_LEFT, Rosen::Gravity::BOTTOM_LEFT },
188         { RenderFit::BOTTOM_RIGHT, Rosen::Gravity::BOTTOM_RIGHT },
189         { RenderFit::RESIZE_FILL, Rosen::Gravity::RESIZE },
190         { RenderFit::RESIZE_CONTAIN, Rosen::Gravity::RESIZE_ASPECT },
191         { RenderFit::RESIZE_CONTAIN_TOP_LEFT, Rosen::Gravity::RESIZE_ASPECT_TOP_LEFT },
192         { RenderFit::RESIZE_CONTAIN_BOTTOM_RIGHT, Rosen::Gravity::RESIZE_ASPECT_BOTTOM_RIGHT },
193         { RenderFit::RESIZE_COVER, Rosen::Gravity::RESIZE_ASPECT_FILL },
194         { RenderFit::RESIZE_COVER_TOP_LEFT, Rosen::Gravity::RESIZE_ASPECT_FILL_TOP_LEFT },
195         { RenderFit::RESIZE_COVER_BOTTOM_RIGHT, Rosen::Gravity::RESIZE_ASPECT_FILL_BOTTOM_RIGHT },
196     };
197     int64_t idx = BinarySearchFindIndex(gravityMap, ArraySize(gravityMap), renderFit);
198     return idx != -1 ? gravityMap[idx].value : Rosen::Gravity::DEFAULT;
199 }
200 
GetResourceColorMode(PipelineContext * pipeline)201 ColorMode GetResourceColorMode(PipelineContext* pipeline)
202 {
203     auto themeManager = pipeline->GetThemeManager();
204     CHECK_NULL_RETURN(themeManager, ColorMode::LIGHT);
205     auto themeConstants = themeManager->GetThemeConstants();
206     CHECK_NULL_RETURN(themeConstants, ColorMode::LIGHT);
207     auto resourceAdapter = themeConstants->GetResourceAdapter();
208     CHECK_NULL_RETURN(resourceAdapter, ColorMode::LIGHT);
209     return resourceAdapter->GetResourceColorMode();
210 }
211 
CreateRSMaterialFilter(const BlurStyleOption & blurStyleOption,PipelineContext * pipeline,const SysOptions & sysOptions)212 std::shared_ptr<Rosen::RSFilter> CreateRSMaterialFilter(
213     const BlurStyleOption& blurStyleOption, PipelineContext* pipeline, const SysOptions& sysOptions)
214 {
215     auto blurStyleTheme = pipeline->GetTheme<BlurStyleTheme>();
216     if (!blurStyleTheme) {
217         LOGW("cannot find theme of blurStyle, create blurStyle failed");
218         return nullptr;
219     }
220     ThemeColorMode colorMode = blurStyleOption.colorMode;
221     if (blurStyleOption.colorMode == ThemeColorMode::SYSTEM) {
222         colorMode = GetResourceColorMode(pipeline) == ColorMode::DARK ? ThemeColorMode::DARK : ThemeColorMode::LIGHT;
223     }
224     auto blurParam = blurStyleTheme->GetBlurParameter(blurStyleOption.blurStyle, colorMode);
225     CHECK_NULL_RETURN(blurParam, nullptr);
226     auto ratio = blurStyleOption.scale;
227     auto maskColor = blurParam->maskColor.BlendOpacity(ratio);
228     auto radiusPx = blurParam->radius * pipeline->GetDipScale();
229     auto radiusBlur = DrawingDecorationPainter::ConvertRadiusToSigma(radiusPx) * ratio;
230     auto saturation = (blurParam->saturation - 1) * ratio + 1.0;
231     auto brightness = (blurParam->brightness - 1) * ratio + 1.0;
232     return Rosen::RSFilter::CreateMaterialFilter(radiusBlur, saturation, brightness, maskColor.GetValue(),
233         static_cast<Rosen::BLUR_COLOR_MODE>(blurStyleOption.adaptiveColor), sysOptions.disableSystemAdaptation);
234 }
235 
GetRsPen(uint32_t strokeColor,float strokeWidth)236 RSPen GetRsPen(uint32_t strokeColor, float strokeWidth)
237 {
238     RSColor rsStrokeColor;
239     rsStrokeColor.SetColorQuad(strokeColor);
240 
241     RSPen pen;
242     pen.SetColor(rsStrokeColor);
243     pen.SetWidth(strokeWidth);
244 
245     return pen;
246 }
247 
GetRsBrush(uint32_t fillColor)248 RSBrush GetRsBrush(uint32_t fillColor)
249 {
250     RSColor color;
251     color.SetColorQuad(fillColor);
252     RSBrush brush(color);
253 
254     return brush;
255 }
256 
257 template<typename ModifierName, typename T>
GetAnimatablePropertyStagingValue(std::shared_ptr<ModifierName> & modifier,Rosen::ModifierNG::RSPropertyType propertyType,const T & defaultValue={})258 T GetAnimatablePropertyStagingValue(
259     std::shared_ptr<ModifierName>& modifier, Rosen::ModifierNG::RSPropertyType propertyType, const T& defaultValue = {})
260 {
261     CHECK_NULL_RETURN(modifier, defaultValue);
262     auto property = std::static_pointer_cast<Rosen::RSAnimatableProperty<T>>(modifier->GetProperty(propertyType));
263     CHECK_NULL_RETURN(property, defaultValue);
264     return property->GetStagingValue();
265 }
266 
267 template<typename ModifierName, typename T>
CancelModifierAnimation(std::shared_ptr<ModifierName> & modifier,Rosen::ModifierNG::RSPropertyType propertyType)268 void CancelModifierAnimation(std::shared_ptr<ModifierName>& modifier, Rosen::ModifierNG::RSPropertyType propertyType)
269 {
270     // request cancel all the animations on rs modifier.
271     CHECK_NULL_VOID(modifier);
272     auto property = std::static_pointer_cast<Rosen::RSAnimatableProperty<T>>(modifier->GetProperty(propertyType));
273     CHECK_NULL_VOID(property);
274     property->RequestCancelAnimation();
275 }
276 } // namespace
277 
278 bool RosenRenderContext::initDrawNodeChangeCallback_ = SetDrawNodeChangeCallback();
279 bool RosenRenderContext::initPropertyNodeChangeCallback_ = SetPropertyNodeChangeCallback();
280 
ConvertDimensionToScaleBySize(const Dimension & dimension,float size)281 float RosenRenderContext::ConvertDimensionToScaleBySize(const Dimension& dimension, float size)
282 {
283     if (dimension.Unit() == DimensionUnit::PERCENT) {
284         return static_cast<float>(dimension.Value());
285     }
286     return size > 0.0f ? static_cast<float>(dimension.ConvertToPx() / size) : 0.5f;
287 }
288 
~RosenRenderContext()289 RosenRenderContext::~RosenRenderContext()
290 {
291     StopRecordingIfNeeded();
292     DetachModifiers();
293     auto host = GetHost();
294     CHECK_NULL_VOID(host);
295     host->RemoveExtraCustomProperty("RS_NODE");
296 }
297 
DetachModifiers()298 void RosenRenderContext::DetachModifiers()
299 {
300     CHECK_NULL_VOID(rsNode_ && rsNode_->GetType() == Rosen::RSUINodeType::SURFACE_NODE);
301     ClearModifiers();
302     auto pipeline = PipelineContext::GetCurrentContextPtrSafelyWithCheck();
303     if (pipeline) {
304         pipeline->RequestFrame();
305     }
306 }
307 
308 using RSModifierPtr = std::shared_ptr<Rosen::ModifierNG::RSModifier>;
309 
ClearModifiers()310 void RosenRenderContext::ClearModifiers()
311 {
312     CHECK_NULL_VOID(rsNode_);
313     if (transitionEffect_) {
314         transitionEffect_->Detach(this);
315     }
316     RSModifierPtr modifiers[] = { translateXYUserModifier_, translateZUserModifier_, scaleXYUserModifier_,
317         rotationXUserModifier_, rotationYUserModifier_, rotationZUserModifier_, cameraDistanceUserModifier_,
318         baseTranslateInXYModifier_, baseRotateInZModifier_, alphaUserModifier_ };
319     for (auto& modifier : modifiers) {
320         if (modifier) {
321             rsNode_->RemoveModifier(modifier);
322         }
323     }
324 }
325 
StartRecording()326 void RosenRenderContext::StartRecording()
327 {
328     CHECK_NULL_VOID(rsNode_);
329     auto rsCanvasNode = rsNode_->ReinterpretCastTo<Rosen::RSCanvasNode>();
330     CHECK_NULL_VOID(rsCanvasNode);
331     rsCanvasNode->BeginRecording(ceil(rsCanvasNode->GetPaintWidth()), ceil(rsCanvasNode->GetPaintHeight()));
332 }
333 
StopRecordingIfNeeded()334 void RosenRenderContext::StopRecordingIfNeeded()
335 {
336     auto rsCanvasNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasNode>(rsNode_);
337     if (rsCanvasNode) {
338         rsCanvasNode->FinishRecording();
339     }
340 }
341 
OnNodeAppear(bool recursive)342 void RosenRenderContext::OnNodeAppear(bool recursive)
343 {
344     isDisappearing_ = false;
345     auto host = GetHost();
346     CHECK_NULL_VOID(host);
347     // restore eventHub state when node appears.
348     auto eventHub = host->GetEventHub<EventHub>();
349     if (eventHub) {
350         eventHub->RestoreEnabled();
351     }
352     if (recursive && !propTransitionAppearing_ && !transitionEffect_) {
353         // recursive and has no transition, no need to handle transition.
354         return;
355     }
356 
357     isBreakingPoint_ = !recursive;
358     if (isSynced_) {
359         // has set size before, trigger transition directly.
360         auto rect = GetPaintRectWithoutTransform();
361         NotifyTransitionInner(rect.GetSize(), true);
362         return;
363     }
364     // pending transition in animation, will start on first layout
365     firstTransitionIn_ = true;
366 }
367 
OnNodeDisappear(bool recursive)368 void RosenRenderContext::OnNodeDisappear(bool recursive)
369 {
370     isDisappearing_ = true;
371     bool noneOrDefaultTransition = !propTransitionDisappearing_ && (!transitionEffect_ || hasDefaultTransition_);
372     if (recursive && noneOrDefaultTransition) {
373         // recursive, and has no transition or has default transition, no need to trigger transition.
374         return;
375     }
376     CHECK_NULL_VOID(rsNode_);
377     auto host = GetHost();
378     if (!recursive && host && host->GetOrCreateEventHub<EventHub>()) {
379         host->GetOrCreateEventHub<EventHub>()->SetEnabledInternal(false);
380     }
381     auto rect = GetPaintRectWithoutTransform();
382     // only start default transition on the break point of render node tree.
383     isBreakingPoint_ = !recursive;
384     NotifyTransitionInner(rect.GetSize(), false);
385 }
386 
SetPivot(float xPivot,float yPivot,float zPivot)387 void RosenRenderContext::SetPivot(float xPivot, float yPivot, float zPivot)
388 {
389     // change pivot without animation
390     CHECK_NULL_VOID(rsNode_);
391     auto changed = true;
392     if (pivotModifier_) {
393         auto pivot = pivotModifier_->GetPivot();
394         changed = pivot[0] != xPivot || pivot[1] != yPivot;
395         pivotModifier_->SetPivot({ xPivot, yPivot }, false);
396     } else {
397         pivotModifier_ = std::make_shared<Rosen::ModifierNG::RSTransformModifier>();
398         pivotModifier_->SetPivot({ xPivot, yPivot }, false);
399         rsNode_->AddModifier(pivotModifier_);
400     }
401     rsNode_->SetPivotZ(zPivot);
402     NotifyHostTransformUpdated(changed);
403 }
404 
SetTransitionPivot(const SizeF & frameSize,bool transitionIn)405 void RosenRenderContext::SetTransitionPivot(const SizeF& frameSize, bool transitionIn)
406 {
407     auto& transitionEffect = transitionIn ? propTransitionAppearing_ : propTransitionDisappearing_;
408     CHECK_NULL_VOID(transitionEffect);
409     float xPivot = 0.0f;
410     float yPivot = 0.0f;
411     float zPivot = 0.0f;
412     if (transitionEffect->HasRotate()) {
413         xPivot = ConvertDimensionToScaleBySize(transitionEffect->GetRotateValue().centerX, frameSize.Width());
414         yPivot = ConvertDimensionToScaleBySize(transitionEffect->GetRotateValue().centerY, frameSize.Height());
415         zPivot = static_cast<float>(transitionEffect->GetRotateValue().centerZ.ConvertToVp());
416     } else if (transitionEffect->HasScale()) {
417         xPivot = ConvertDimensionToScaleBySize(transitionEffect->GetScaleValue().centerX, frameSize.Width());
418         yPivot = ConvertDimensionToScaleBySize(transitionEffect->GetScaleValue().centerY, frameSize.Height());
419     } else {
420         return;
421     }
422     SetPivot(xPivot, yPivot, zPivot);
423 }
424 
SetSurfaceChangedCallBack(const std::function<void (float,float,float,float)> & callback)425 void RosenRenderContext::SetSurfaceChangedCallBack(const std::function<void(float, float, float, float)>& callback)
426 {
427 #if defined(ANDROID_PLATFORM) || defined(IOS_PLATFORM)
428     if (rsNode_) {
429         RSRenderThread::Instance().AddSurfaceChangedCallBack(rsNode_->GetId(), callback);
430     }
431 #endif
432 }
433 
RemoveSurfaceChangedCallBack()434 void RosenRenderContext::RemoveSurfaceChangedCallBack()
435 {
436 #if defined(ANDROID_PLATFORM) || defined(IOS_PLATFORM)
437     if (rsNode_) {
438         RSRenderThread::Instance().RemoveSurfaceChangedCallBack(rsNode_->GetId());
439     }
440 #endif
441 }
442 
AddFrameNodeInfoToRsNode()443 void RosenRenderContext::AddFrameNodeInfoToRsNode()
444 {
445     if (rsNode_) {
446         rsNode_->SetInstanceId(Container::CurrentId());
447         auto frameNodePtr = GetHost();
448         CHECK_NULL_VOID(frameNodePtr);
449         rsNode_->SetFrameNodeInfo(frameNodePtr->GetId(), frameNodePtr->GetTag());
450     }
451 }
452 
SetHostNode(const WeakPtr<FrameNode> & host)453 void RosenRenderContext::SetHostNode(const WeakPtr<FrameNode>& host)
454 {
455     RenderContext::SetHostNode(host);
456     AddFrameNodeInfoToRsNode();
457     auto frameNode = GetHost();
458     CHECK_NULL_VOID(frameNode);
459     frameNode->AddExtraCustomProperty("RS_NODE", rsNode_.get());
460 }
461 
GetRSUIContext(PipelineContext * pipeline)462 std::shared_ptr<Rosen::RSUIContext> RosenRenderContext::GetRSUIContext(PipelineContext* pipeline)
463 {
464     if (!SystemProperties::GetMultiInstanceEnabled()) {
465         return nullptr;
466     }
467     CHECK_NULL_RETURN(pipeline, nullptr);
468     auto window = pipeline->GetWindow();
469     CHECK_NULL_RETURN(window, nullptr);
470     auto rsUIDirector = window->GetRSUIDirector();
471     CHECK_NULL_RETURN(rsUIDirector, nullptr);
472     return rsUIDirector->GetRSUIContext();
473 }
474 
InitContext(bool isRoot,const std::optional<ContextParam> & param,bool isLayoutNode)475 void RosenRenderContext::InitContext(bool isRoot, const std::optional<ContextParam>& param, bool isLayoutNode)
476 {
477     if (isLayoutNode) {
478         return;
479     }
480     InitContext(isRoot, param);
481 }
482 
InitContext(bool isRoot,const std::optional<ContextParam> & param)483 void RosenRenderContext::InitContext(bool isRoot, const std::optional<ContextParam>& param)
484 {
485     // skip if node already created
486     CHECK_NULL_VOID(!rsNode_);
487     std::shared_ptr<Rosen::RSUIContext> rsContext;
488     if (SystemProperties::GetMultiInstanceEnabled()) {
489         auto pipeline = GetPipelineContext();
490         rsContext = GetRSUIContext(pipeline);
491         if (!rsContext) {
492             TAG_LOGI(AceLogTag::ACE_DEFAULT_DOMAIN, "rsnode create before rosenwindow");
493             rsUIDirector_ = OHOS::Rosen::RSUIDirector::Create();
494             rsUIDirector_->Init(true, true);
495             rsContext = rsUIDirector_->GetRSUIContext();
496         }
497     }
498     auto isTextureExportNode = ViewStackProcessor::GetInstance()->IsExportTexture();
499     if (isRoot) {
500         rsNode_ = Rosen::RSRootNode::Create(false, isTextureExportNode, rsContext);
501         SetSkipCheckInMultiInstance();
502         AddFrameNodeInfoToRsNode();
503         return;
504     } else if (!param.has_value()) {
505         rsNode_ = Rosen::RSCanvasNode::Create(false, isTextureExportNode, rsContext);
506         SetSkipCheckInMultiInstance();
507         AddFrameNodeInfoToRsNode();
508         return;
509     }
510     patternType_ = param->patternType;
511     // create proper RSNode base on input
512     switch (param->type) {
513         case ContextType::CANVAS:
514             rsNode_ = Rosen::RSCanvasNode::Create(false, isTextureExportNode, rsContext);
515             break;
516         case ContextType::ROOT:
517             rsNode_ = Rosen::RSRootNode::Create(false, isTextureExportNode, rsContext);
518             break;
519         case ContextType::SURFACE: {
520             Rosen::RSSurfaceNodeConfig surfaceNodeConfig = { .SurfaceNodeName = param->surfaceName.value_or(""),
521                 .isTextureExportNode = isTextureExportNode };
522             rsNode_ = Rosen::RSSurfaceNode::Create(surfaceNodeConfig, false, rsContext);
523             break;
524         }
525         case ContextType::HARDWARE_SURFACE: {
526             rsNode_ = CreateHardwareSurface(param, isTextureExportNode, rsContext);
527             break;
528         }
529 #ifdef RENDER_EXTRACT_SUPPORTED
530         case ContextType::HARDWARE_TEXTURE: {
531             rsNode_ = CreateHardwareTexture(param, isTextureExportNode);
532             break;
533         }
534 #endif
535         case ContextType::EFFECT:
536             rsNode_ = Rosen::RSEffectNode::Create(false, isTextureExportNode, rsContext);
537             break;
538         case ContextType::INCREMENTAL_CANVAS: {
539             if (RSUIDirector::GetHybridRenderSwitch(Rosen::ComponentEnableSwitch::CANVAS)) {
540                 rsNode_ = Rosen::RSCanvasNode::Create(false, isTextureExportNode, rsContext);
541                 rsNode_->SetHybridRenderCanvas(true);
542             } else {
543                 rsNode_ = Rosen::RSCanvasDrawingNode::Create(false, isTextureExportNode, rsContext);
544             }
545             break;
546         }
547         case ContextType::EXTERNAL:
548             break;
549         default:
550             break;
551     }
552     SetSkipCheckInMultiInstance();
553     AddFrameNodeInfoToRsNode();
554 }
555 
SetSkipCheckInMultiInstance()556 void RosenRenderContext::SetSkipCheckInMultiInstance()
557 {
558     if (SystemProperties::GetMultiInstanceEnabled() && rsNode_) {
559         rsNode_->SetSkipCheckInMultiInstance(true);
560     }
561 }
562 
CreateHardwareSurface(const std::optional<ContextParam> & param,bool isTextureExportNode,std::shared_ptr<Rosen::RSUIContext> & rsUIContext)563 std::shared_ptr<Rosen::RSNode> RosenRenderContext::CreateHardwareSurface(const std::optional<ContextParam>& param,
564     bool isTextureExportNode, std::shared_ptr<Rosen::RSUIContext>& rsUIContext)
565 {
566     Rosen::RSSurfaceNodeConfig surfaceNodeConfig = { .SurfaceNodeName = param->surfaceName.value_or(""),
567         .isTextureExportNode = isTextureExportNode, .isSync = true };
568     std::shared_ptr<Rosen::RSSurfaceNode> surfaceNode;
569     if (rsUIContext) {
570         surfaceNode = Rosen::RSSurfaceNode::Create(surfaceNodeConfig, false, rsUIContext);
571     } else {
572         surfaceNode = Rosen::RSSurfaceNode::Create(surfaceNodeConfig, false);
573     }
574     if (surfaceNode) {
575         if (param->patternType == PatternType::VIDEO) {
576             surfaceNode->SetHardwareEnabled(true, SelfDrawingNodeType::VIDEO);
577         } else if (param->patternType == PatternType::XCOM) {
578             surfaceNode->SetHardwareEnabled(true, SelfDrawingNodeType::XCOM);
579         } else {
580             surfaceNode->SetHardwareEnabled(true, SelfDrawingNodeType::DEFAULT);
581         }
582         surfaceNode->SetApiCompatibleVersion(Container::GetCurrentApiTargetVersion());
583     }
584     return surfaceNode;
585 }
586 
587 #ifdef RENDER_EXTRACT_SUPPORTED
CreateHardwareTexture(const std::optional<ContextParam> & param,bool isTextureExportNode)588 std::shared_ptr<Rosen::RSNode> RosenRenderContext::CreateHardwareTexture(
589     const std::optional<ContextParam>& param, bool isTextureExportNode)
590 {
591     Rosen::RSSurfaceNodeConfig surfaceNodeConfig = { .SurfaceNodeName = param->surfaceName.value_or(""),
592         .isTextureExportNode = isTextureExportNode };
593     auto surfaceNode = Rosen::RSSurfaceNode::Create(surfaceNodeConfig, RSSurfaceNodeType::SURFACE_TEXTURE_NODE, false);
594     return surfaceNode;
595 }
596 #endif
597 
SetSandBox(const std::optional<OffsetF> & parentPosition,bool force)598 void RosenRenderContext::SetSandBox(const std::optional<OffsetF>& parentPosition, bool force)
599 {
600     CHECK_NULL_VOID(rsNode_);
601     auto host = GetHost();
602     CHECK_NULL_VOID(host);
603     if (parentPosition.has_value()) {
604         if (!force) {
605             sandBoxCount_++;
606         }
607         Rosen::Vector2f value = { parentPosition.value().GetX(), parentPosition.value().GetY() };
608         TAG_LOGI(AceLogTag::ACE_GEOMETRY_TRANSITION, "node[%{public}s] Set SandBox",
609             std::to_string(rsNode_->GetId()).c_str());
610         rsNode_->SetSandBox(value);
611     } else {
612         if (!force) {
613             sandBoxCount_--;
614             if (sandBoxCount_ > 0) {
615                 return;
616             }
617         }
618         TAG_LOGI(AceLogTag::ACE_GEOMETRY_TRANSITION, "node[%{public}s] Remove SandBox",
619             std::to_string(rsNode_->GetId()).c_str());
620         sandBoxCount_ = 0;
621         rsNode_->SetSandBox(std::nullopt);
622     }
623 }
624 
SetFrameWithoutAnimation(const RectF & paintRect)625 void RosenRenderContext::SetFrameWithoutAnimation(const RectF& paintRect)
626 {
627     CHECK_NULL_VOID(rsNode_ && paintRect.IsValid());
628     auto rsUIContext = rsNode_->GetRSUIContext();
629     RSNode::ExecuteWithoutAnimation([rosenRenderContext = Claim(this), &paintRect]() {
630             rosenRenderContext->SyncGeometryFrame(paintRect);
631         }, rsUIContext);
632 }
633 
SyncGeometryProperties(GeometryNode *,bool,uint8_t)634 void RosenRenderContext::SyncGeometryProperties(GeometryNode* /*geometryNode*/, bool /* isRound */, uint8_t /* flag */)
635 {
636     CHECK_NULL_VOID(rsNode_);
637     auto host = GetHost();
638     CHECK_NULL_VOID(host);
639     if (isNeedAnimate_) {
640         SyncGeometryProperties(paintRect_);
641     } else {
642         auto rsUIContext = rsNode_->GetRSUIContext();
643         RSNode::ExecuteWithoutAnimation([rosenRenderContext = Claim(this)]() {
644                 rosenRenderContext->SyncGeometryProperties(rosenRenderContext->paintRect_);
645             }, rsUIContext);
646     }
647     host->OnPixelRoundFinish(paintRect_.GetSize());
648 }
649 
SyncGeometryFrame(const RectF & paintRect)650 void RosenRenderContext::SyncGeometryFrame(const RectF& paintRect)
651 {
652     CHECK_NULL_VOID(rsNode_);
653     rsNode_->SetBounds(paintRect.GetX(), paintRect.GetY(), paintRect.Width(), paintRect.Height());
654     if (rsTextureExport_) {
655         rsTextureExport_->UpdateBufferInfo(paintRect.GetX(), paintRect.GetY(), paintRect.Width(), paintRect.Height());
656     }
657     if (handleChildBounds_) {
658         SetChildBounds(paintRect);
659     }
660     if (useContentRectForRSFrame_) {
661         SetContentRectToFrame(paintRect);
662     } else {
663         rsNode_->SetFrame(paintRect.GetX(), paintRect.GetY(), paintRect.Width(), paintRect.Height());
664     }
665     if (frameOffset_.has_value()) {
666         rsNode_->SetFrame(paintRect.GetX() + frameOffset_->GetX(), paintRect.GetY() + frameOffset_->GetY(),
667             paintRect.Width(), paintRect.Height());
668     }
669     auto host = GetHost();
670     CHECK_NULL_VOID(host);
671     host->OnSyncGeometryFrameFinish(paintRect);
672 }
673 
SetChildBounds(const RectF & paintRect) const674 void RosenRenderContext::SetChildBounds(const RectF& paintRect) const
675 {
676     CHECK_NULL_VOID(rsNode_);
677     auto child = rsNode_->GetChildByIndex(0);
678     if (child) {
679         child->SetBounds(0.0f, 0.0f, paintRect.Width(), paintRect.Height());
680     }
681 }
682 
SyncGeometryProperties(const RectF & paintRect)683 void RosenRenderContext::SyncGeometryProperties(const RectF& paintRect)
684 {
685     CHECK_NULL_VOID(rsNode_);
686     if (isDisappearing_ && !paintRect.IsValid()) {
687         return;
688     }
689     if (SystemProperties::GetSyncDebugTraceEnabled()) {
690         auto host = GetHost();
691         ACE_LAYOUT_SCOPED_TRACE("SyncGeometryProperties [%s][self:%d] set bounds %s", host->GetTag().c_str(),
692             host->GetId(), paintRect.ToString().c_str());
693     }
694     if (extraOffset_.has_value()) {
695         SyncGeometryFrame(paintRect + extraOffset_.value());
696     } else {
697         SyncGeometryFrame(paintRect);
698     }
699 
700     if (!isSynced_) {
701         isSynced_ = true;
702         auto borderRadius = GetBorderRadius();
703         if (borderRadius.has_value()) {
704             OnBorderRadiusUpdate(borderRadius.value());
705         }
706     }
707 
708     if (firstTransitionIn_) {
709         // need to perform transitionIn early so not influence the following SetPivot
710         NotifyTransitionInner(paintRect.GetSize(), true);
711         firstTransitionIn_ = false;
712     }
713 
714     SyncPartialRsProperties();
715     SyncAdditionalGeometryProperties(paintRect);
716 }
717 
SyncAdditionalGeometryProperties(const RectF & paintRect)718 void RosenRenderContext::SyncAdditionalGeometryProperties(const RectF& paintRect)
719 {
720     if (propPointLight_ && propPointLight_->HasLightPosition()) {
721         // if lightPosition unit is percent, it is related with frameSize
722         OnLightPositionUpdate(propPointLight_->GetLightPositionValue());
723     }
724 
725     if (bgLoadingCtx_ && bgImage_) {
726         PaintBackground();
727     }
728 
729     auto sourceFromImage = GetBorderSourceFromImage().value_or(false);
730     if (sourceFromImage && bdImageLoadingCtx_ && bdImage_) {
731         PaintBorderImage();
732     } else if (!sourceFromImage && GetBorderImageGradient()) {
733         PaintBorderImageGradient();
734     }
735 
736     if (propGradient_) {
737         PaintGradient(paintRect.GetSize());
738     }
739 
740     if (propClip_) {
741         PaintClip(paintRect.GetSize());
742     }
743 
744     if (HasProgressMask() && GetProgressMaskValue()) {
745         PaintProgressMask();
746     }
747 
748     if (propGraphics_) {
749         PaintGraphics();
750     }
751 
752     if (propOverlay_) {
753         PaintOverlayText();
754     }
755 
756     if (SystemProperties::GetDebugBoundaryEnabled()) {
757         PaintDebugBoundary(true);
758     }
759 
760     if (propParticleOptionArray_.has_value()) {
761         if (!measureTriggered_ || particleAnimationPlaying_) {
762             measureTriggered_ = true;
763             OnParticleOptionArrayUpdate(propParticleOptionArray_.value());
764         }
765     }
766     OnEmitterPropertyUpdate();
767 }
768 
PaintDebugBoundary(bool flag)769 void RosenRenderContext::PaintDebugBoundary(bool flag)
770 {
771     if (!flag && !debugBoundaryModifier_) {
772         return;
773     }
774     if (!NeedDebugBoundary()) {
775         return;
776     }
777     CHECK_NULL_VOID(rsNode_);
778     auto host = GetHost();
779     CHECK_NULL_VOID(host);
780     auto geometryNode = host->GetGeometryNode();
781     auto paintTask = [contentSize = geometryNode->GetFrameSize(), frameSize = geometryNode->GetMarginFrameSize(),
782                          offset = geometryNode->GetMarginFrameOffset(), frameOffset = geometryNode->GetFrameOffset(),
783                          flag](RSCanvas& rsCanvas) mutable {
784         if (!flag) {
785             return;
786         }
787         DebugBoundaryPainter painter(contentSize, frameSize);
788         painter.SetFrameOffset(frameOffset);
789         painter.DrawDebugBoundaries(rsCanvas, offset);
790     };
791 
792     if (!debugBoundaryModifier_ && rsNode_->IsInstanceOf<Rosen::RSCanvasNode>()) {
793         debugBoundaryModifier_ = std::make_shared<DebugBoundaryModifier>();
794         debugBoundaryModifier_->SetPaintTask(std::move(paintTask));
795         debugBoundaryModifier_->SetNoNeedUICaptured(true);
796         auto rect = GetPaintRectWithoutTransform();
797         auto marginOffset = geometryNode->GetMarginFrameOffset();
798         std::shared_ptr<Rosen::RectF> drawRect =
799             std::make_shared<Rosen::RectF>(marginOffset.GetX() - rect.GetX(), marginOffset.GetY() - rect.GetY(),
800                 geometryNode->GetMarginFrameSize().Width(), geometryNode->GetMarginFrameSize().Height());
801         UpdateDrawRegion(DRAW_REGION_DEBUG_BOUNDARY_MODIFIER_INDEX, drawRect);
802         rsNode_->AddModifier(debugBoundaryModifier_);
803         // SetCustomData(AttachProperty to rs modifier) must be called after AddModifier.
804         debugBoundaryModifier_->SetCustomData(flag);
805     } else if (debugBoundaryModifier_) {
806         debugBoundaryModifier_->SetPaintTask(std::move(paintTask));
807         auto rect = GetPaintRectWithoutTransform();
808         auto marginOffset = geometryNode->GetMarginFrameOffset();
809         std::shared_ptr<Rosen::RectF> drawRect =
810             std::make_shared<Rosen::RectF>(marginOffset.GetX() - rect.GetX(), marginOffset.GetY() - rect.GetY(),
811                 geometryNode->GetMarginFrameSize().Width(), geometryNode->GetMarginFrameSize().Height());
812         UpdateDrawRegion(DRAW_REGION_DEBUG_BOUNDARY_MODIFIER_INDEX, drawRect);
813         debugBoundaryModifier_->SetCustomData(flag);
814     }
815 }
816 
ColorToRSColor(const Color & color,OHOS::Rosen::RSColor & rsColor)817 void RosenRenderContext::ColorToRSColor(const Color& color, OHOS::Rosen::RSColor& rsColor)
818 {
819     rsColor = OHOS::Rosen::RSColor::FromArgbInt(color.GetValue());
820     GraphicColorGamut colorSpace = GraphicColorGamut::GRAPHIC_COLOR_GAMUT_SRGB;
821     if (ColorSpace::DISPLAY_P3 == color.GetColorSpace()) {
822         colorSpace = GraphicColorGamut::GRAPHIC_COLOR_GAMUT_DISPLAY_P3;
823     }
824     rsColor.SetColorSpace(colorSpace);
825 }
826 
OnBackgroundColorUpdate(const Color & value)827 void RosenRenderContext::OnBackgroundColorUpdate(const Color& value)
828 {
829     CHECK_NULL_VOID(rsNode_);
830     OHOS::Rosen::RSColor rsColor;
831     ColorToRSColor(value, rsColor);
832     rsNode_->SetBackgroundColor(rsColor);
833     RequestNextFrame();
834 }
835 
OnForegroundColorUpdate(const Color & value)836 void RosenRenderContext::OnForegroundColorUpdate(const Color& value)
837 {
838     CHECK_NULL_VOID(rsNode_);
839     rsNode_->SetEnvForegroundColor(value.GetValue());
840     RequestNextFrame();
841     if (SystemProperties::ConfigChangePerform()) {
842         auto host = GetHost();
843         CHECK_NULL_VOID(host);
844         auto pattern = host->GetPattern();
845         CHECK_NULL_VOID(pattern);
846         pattern->OnForegroundColorUpdate();
847     }
848 }
849 
OnForegroundEffectUpdate(float radius)850 void RosenRenderContext::OnForegroundEffectUpdate(float radius)
851 {
852     CHECK_NULL_VOID(rsNode_);
853     auto context = GetPipelineContext();
854     CHECK_NULL_VOID(context);
855     CalcDimension value;
856     value.SetValue(static_cast<double>(radius));
857     float radiusPx = context->NormalizeToPx(value);
858     float foreRadius = DrawingDecorationPainter::ConvertRadiusToSigma(radiusPx);
859     rsNode_->SetForegroundEffectRadius(foreRadius);
860     RequestNextFrame();
861 }
862 
OnForegroundColorStrategyUpdate(const ForegroundColorStrategy & value)863 void RosenRenderContext::OnForegroundColorStrategyUpdate(const ForegroundColorStrategy& value)
864 {
865     CHECK_NULL_VOID(rsNode_);
866     Rosen::ForegroundColorStrategyType rsStrategy = Rosen::ForegroundColorStrategyType::INVALID;
867     switch (value) {
868         case ForegroundColorStrategy::INVERT:
869             rsStrategy = Rosen::ForegroundColorStrategyType::INVERT_BACKGROUNDCOLOR;
870             break;
871         default:
872             break;
873     }
874     rsNode_->SetEnvForegroundColorStrategy(rsStrategy);
875     RequestNextFrame();
876     if (SystemProperties::ConfigChangePerform()) {
877         auto host = GetHost();
878         CHECK_NULL_VOID(host);
879         auto pattern = host->GetPattern();
880         pattern->OnForegroundColorUpdate();
881     }
882 }
883 
CreateBgImageDataReadyCallback()884 DataReadyNotifyTask RosenRenderContext::CreateBgImageDataReadyCallback()
885 {
886     auto task = [weak = WeakClaim(this)](const ImageSourceInfo& sourceInfo) {
887         if (SystemProperties::GetDebugEnabled()) {
888             TAG_LOGD(AceLogTag::ACE_IMAGE, "backgroundImageDataReady src = %{private}s", sourceInfo.ToString().c_str());
889         }
890         auto rosenRenderContext = weak.Upgrade();
891         CHECK_NULL_VOID(rosenRenderContext);
892         auto imageSourceInfo = rosenRenderContext->GetBackgroundImage().value_or(ImageSourceInfo(""));
893         if (imageSourceInfo != sourceInfo) {
894             return;
895         }
896         rosenRenderContext->bgLoadingCtx_->MakeCanvasImage(SizeF(), true, ImageFit::NONE);
897     };
898     return task;
899 }
900 
CreateBgImageLoadSuccessCallback()901 LoadSuccessNotifyTask RosenRenderContext::CreateBgImageLoadSuccessCallback()
902 {
903     auto task = [weak = WeakClaim(this)](const ImageSourceInfo& sourceInfo) {
904         if (SystemProperties::GetDebugEnabled()) {
905             TAG_LOGD(
906                 AceLogTag::ACE_IMAGE, "backgroundImageLoadSuccess src = %{private}s", sourceInfo.ToString().c_str());
907         }
908         auto ctx = weak.Upgrade();
909         CHECK_NULL_VOID(ctx);
910         auto imageSourceInfo = ctx->GetBackgroundImage().value_or(ImageSourceInfo(""));
911         if (imageSourceInfo != sourceInfo) {
912             return;
913         }
914         CHECK_NULL_VOID(ctx->bgLoadingCtx_);
915         ctx->bgImage_ = ctx->bgLoadingCtx_->MoveCanvasImage();
916         CHECK_NULL_VOID(ctx->bgImage_);
917         CHECK_NULL_VOID(ctx->GetHost());
918         CHECK_NULL_VOID(ctx->GetHost()->GetGeometryNode());
919         if (ctx->GetHost()->GetGeometryNode()->GetFrameSize().IsPositive()) {
920             ctx->PaintBackground();
921             ctx->RequestNextFrame();
922         }
923     };
924     return task;
925 }
926 
PaintBackground()927 void RosenRenderContext::PaintBackground()
928 {
929     CHECK_NULL_VOID(rsNode_);
930     if (InstanceOf<PixelMapImage>(bgImage_)) {
931         PaintPixmapBgImage();
932     } else if (InstanceOf<DrawingImage>(bgImage_)) {
933         PaintRSBgImage();
934     } else {
935         if (Container::GreatOrEqualAPITargetVersion(PlatformVersion::VERSION_TWELVE)) {
936             rsNode_->SetBgImage(nullptr);
937         }
938         return;
939     }
940     auto srcSize = bgLoadingCtx_->GetImageSize();
941     SizeF renderSize = ImagePainter::CalculateBgImageSize(paintRect_.GetSize(), srcSize, GetBackgroundImageSize());
942     OffsetF positionOffset =
943         ImagePainter::CalculateBgImagePosition(paintRect_.GetSize(), renderSize, GetBackgroundImagePosition());
944     auto slice = GetBackgroundImageResizableSliceValue(ImageResizableSlice());
945     Rosen::Vector4f rect(slice.left.ConvertToPxWithSize(srcSize.Width()),
946         slice.top.ConvertToPxWithSize(srcSize.Height()),
947         srcSize.Width() - (slice.left + slice.right).ConvertToPxWithSize(srcSize.Width()),
948         srcSize.Height() - (slice.top + slice.bottom).ConvertToPxWithSize(srcSize.Height()));
949     rsNode_->SetBgImageWidth(renderSize.Width());
950     rsNode_->SetBgImageHeight(renderSize.Height());
951     rsNode_->SetBgImagePositionX(positionOffset.GetX());
952     rsNode_->SetBgImagePositionY(positionOffset.GetY());
953     rsNode_->SetBgImageInnerRect(rect);
954 }
955 
OnBackgroundImageUpdate(const ImageSourceInfo & src)956 void RosenRenderContext::OnBackgroundImageUpdate(const ImageSourceInfo& src)
957 {
958     CHECK_NULL_VOID(rsNode_);
959     if (src.GetSrc().empty() && src.GetPixmap() == nullptr) {
960         bgImage_ = nullptr;
961         bgLoadingCtx_ = nullptr;
962         auto frameNode = GetHost();
963         if (frameNode) {
964             frameNode->SetColorModeUpdateCallback(nullptr);
965         }
966         PaintBackground();
967         return;
968     }
969     if (!bgLoadingCtx_ || src != bgLoadingCtx_->GetSourceInfo()) {
970         auto frameNode = GetHost();
971         auto callback = [src, weak = WeakClaim(this)] {
972             auto renderContext = weak.Upgrade();
973             CHECK_NULL_VOID(renderContext);
974             renderContext->OnBackgroundImageUpdate(src);
975         };
976         frameNode->SetColorModeUpdateCallback(std::move(callback));
977     }
978     LoadNotifier bgLoadNotifier(CreateBgImageDataReadyCallback(), CreateBgImageLoadSuccessCallback(), nullptr);
979     auto syncMode = GetBackgroundImageSyncMode().value_or(false);
980     bgLoadingCtx_ = AceType::MakeRefPtr<ImageLoadingContext>(src, std::move(bgLoadNotifier), syncMode);
981     CHECK_NULL_VOID(bgLoadingCtx_);
982     bgLoadingCtx_->LoadImageData();
983 }
984 
OnBackgroundImageRepeatUpdate(const ImageRepeat &)985 void RosenRenderContext::OnBackgroundImageRepeatUpdate(const ImageRepeat& /*imageRepeat*/)
986 {
987     CHECK_NULL_VOID(rsNode_);
988     PaintBackground();
989 }
990 
OnBackgroundImageSyncModeUpdate(bool)991 void RosenRenderContext::OnBackgroundImageSyncModeUpdate(bool /*syncMode*/)
992 {
993     CHECK_NULL_VOID(rsNode_);
994     PaintBackground();
995 }
996 
OnBackgroundImageSizeUpdate(const BackgroundImageSize &)997 void RosenRenderContext::OnBackgroundImageSizeUpdate(const BackgroundImageSize& /*bgImgSize*/)
998 {
999     CHECK_NULL_VOID(rsNode_);
1000     PaintBackground();
1001 }
1002 
OnBackgroundImagePositionUpdate(const BackgroundImagePosition &)1003 void RosenRenderContext::OnBackgroundImagePositionUpdate(const BackgroundImagePosition& /*bgImgPosition*/)
1004 {
1005     CHECK_NULL_VOID(rsNode_);
1006     PaintBackground();
1007 }
1008 
OnBackgroundImageResizableSliceUpdate(const ImageResizableSlice &)1009 void RosenRenderContext::OnBackgroundImageResizableSliceUpdate(const ImageResizableSlice& /*ImageResizableSlice*/)
1010 {
1011     CHECK_NULL_VOID(rsNode_);
1012     PaintBackground();
1013 }
1014 
HasValidBgImageResizable()1015 bool RosenRenderContext::HasValidBgImageResizable()
1016 {
1017     CHECK_NULL_RETURN(bgLoadingCtx_, false);
1018     auto srcSize = bgLoadingCtx_->GetImageSize();
1019     auto slice = GetBackgroundImageResizableSliceValue(ImageResizableSlice());
1020     auto left = slice.left.ConvertToPxWithSize(srcSize.Width());
1021     auto right = slice.right.ConvertToPxWithSize(srcSize.Width());
1022     auto top = slice.top.ConvertToPxWithSize(srcSize.Width());
1023     auto bottom = slice.bottom.ConvertToPxWithSize(srcSize.Width());
1024     return srcSize.Width() > left + right && srcSize.Height() > top + bottom && right > 0 && bottom > 0;
1025 }
1026 
SetBackBlurFilter()1027 void RosenRenderContext::SetBackBlurFilter()
1028 {
1029     CHECK_NULL_VOID(rsNode_);
1030     auto context = GetPipelineContext();
1031     CHECK_NULL_VOID(context);
1032     const auto& background = GetBackground();
1033     CHECK_NULL_VOID(background);
1034     const auto& blurStyleOption = background->propBlurStyleOption;
1035     auto sysOptions = background->propSysOptions.value_or(SysOptions());
1036     std::shared_ptr<Rosen::RSFilter> backFilter;
1037     if (!blurStyleOption.has_value()) {
1038         const auto& radius = background->propBlurRadius;
1039         if (radius.has_value() && radius->IsValid()) {
1040             float radiusPx = context->NormalizeToPx(radius.value());
1041             float backblurRadius = DrawingDecorationPainter::ConvertRadiusToSigma(radiusPx);
1042             backFilter =
1043                 Rosen::RSFilter::CreateBlurFilter(backblurRadius, backblurRadius, sysOptions.disableSystemAdaptation);
1044         }
1045     } else {
1046         backFilter = CreateRSMaterialFilter(blurStyleOption.value(), context, sysOptions);
1047     }
1048     rsNode_->SetBackgroundFilter(backFilter);
1049 }
1050 
UpdateWindowFocusState(bool isFocused)1051 void RosenRenderContext::UpdateWindowFocusState(bool isFocused)
1052 {
1053     if (GetBackBlurStyle().has_value() &&
1054         GetBackBlurStyle()->policy == BlurStyleActivePolicy::FOLLOWS_WINDOW_ACTIVE_STATE) {
1055         auto blurStyle = GetBackBlurStyle().value();
1056         blurStyle.isWindowFocused = isFocused;
1057         UpdateBackBlurStyle(blurStyle);
1058     }
1059     if (GetBackgroundEffect().has_value() &&
1060         GetBackgroundEffect()->policy == BlurStyleActivePolicy::FOLLOWS_WINDOW_ACTIVE_STATE) {
1061         auto effect = GetBackgroundEffect().value();
1062         effect.isWindowFocused = isFocused;
1063         UpdateBackgroundEffect(effect);
1064     }
1065 }
1066 
UpdateWindowActiveState(bool isActive)1067 void RosenRenderContext::UpdateWindowActiveState(bool isActive)
1068 {
1069     auto useEffect = GetUseEffect().value_or(false);
1070     auto effectType = GetUseEffectType().value_or(EffectType::DEFAULT);
1071     if (effectType == EffectType::WINDOW_EFFECT) {
1072         OnUseEffectUpdate(useEffect);
1073     }
1074 }
1075 
SetFrontBlurFilter()1076 void RosenRenderContext::SetFrontBlurFilter()
1077 {
1078     auto host = GetHost();
1079     FREE_NODE_CHECK(host, SetFrontBlurFilter);
1080     CHECK_NULL_VOID(rsNode_);
1081     auto context = GetPipelineContext();
1082     CHECK_NULL_VOID(context);
1083     const auto& foreground = GetForeground();
1084     CHECK_NULL_VOID(foreground);
1085     const auto& blurStyleOption = foreground->propBlurStyleOption;
1086     auto sysOptions = foreground->propSysOptionsForBlur.value_or(SysOptions());
1087     std::shared_ptr<Rosen::RSFilter> frontFilter;
1088     if (!blurStyleOption.has_value()) {
1089         const auto& radius = foreground->propBlurRadius;
1090         if (radius.has_value() && radius->IsValid()) {
1091             float radiusPx = context->NormalizeToPx(radius.value());
1092             float backblurRadius = DrawingDecorationPainter::ConvertRadiusToSigma(radiusPx);
1093             frontFilter =
1094                 Rosen::RSFilter::CreateBlurFilter(backblurRadius, backblurRadius, sysOptions.disableSystemAdaptation);
1095         }
1096     } else {
1097         frontFilter = CreateRSMaterialFilter(blurStyleOption.value(), context, sysOptions);
1098     }
1099 
1100     rsNode_->SetFilter(frontFilter);
1101 }
1102 
UpdateBlurBackgroundColor(const std::optional<BlurStyleOption> & bgBlurStyle)1103 bool RosenRenderContext::UpdateBlurBackgroundColor(const std::optional<BlurStyleOption>& bgBlurStyle)
1104 {
1105     if (!bgBlurStyle.has_value()) {
1106         return false;
1107     }
1108     bool blurEnable =
1109         bgBlurStyle->policy == BlurStyleActivePolicy::ALWAYS_ACTIVE ||
1110         (bgBlurStyle->policy == BlurStyleActivePolicy::FOLLOWS_WINDOW_ACTIVE_STATE && bgBlurStyle->isWindowFocused);
1111     if (bgBlurStyle->isValidColor) {
1112         if (blurEnable) {
1113             rsNode_->SetBackgroundColor(GetBackgroundColor().value_or(Color::TRANSPARENT).GetValue());
1114         } else {
1115             rsNode_->SetBackgroundColor(bgBlurStyle->inactiveColor.GetValue());
1116         }
1117     }
1118     return blurEnable;
1119 }
1120 
UpdateBlurBackgroundColor(const std::optional<EffectOption> & efffectOption)1121 bool RosenRenderContext::UpdateBlurBackgroundColor(const std::optional<EffectOption>& efffectOption)
1122 {
1123     bool blurEnable =
1124         efffectOption->policy == BlurStyleActivePolicy::ALWAYS_ACTIVE ||
1125         (efffectOption->policy == BlurStyleActivePolicy::FOLLOWS_WINDOW_ACTIVE_STATE && efffectOption->isWindowFocused);
1126     if (efffectOption->isValidColor) {
1127         if (blurEnable) {
1128             rsNode_->SetBackgroundColor(GetBackgroundColor().value_or(Color::TRANSPARENT).GetValue());
1129         } else {
1130             rsNode_->SetBackgroundColor(efffectOption->inactiveColor.GetValue());
1131         }
1132     }
1133     return blurEnable;
1134 }
1135 
UpdateBackBlurStyle(const std::optional<BlurStyleOption> & bgBlurStyle,const SysOptions & sysOptions)1136 void RosenRenderContext::UpdateBackBlurStyle(
1137     const std::optional<BlurStyleOption>& bgBlurStyle, const SysOptions& sysOptions)
1138 {
1139     CHECK_NULL_VOID(rsNode_);
1140     const auto& groupProperty = GetOrCreateBackground();
1141     if (groupProperty->CheckBlurStyleOption(bgBlurStyle) && groupProperty->CheckSystemAdaptationSame(sysOptions)) {
1142         // Same with previous value.
1143         // If colorMode is following system and has valid blurStyle, still needs updating
1144         if (bgBlurStyle->colorMode != ThemeColorMode::SYSTEM) {
1145             return;
1146         }
1147         if (bgBlurStyle->blurOption.grayscale.size() > 1) {
1148             Rosen::Vector2f grayScale(bgBlurStyle->blurOption.grayscale[0], bgBlurStyle->blurOption.grayscale[1]);
1149             rsNode_->SetGreyCoef(grayScale);
1150         }
1151     } else {
1152         groupProperty->propBlurStyleOption = bgBlurStyle;
1153         groupProperty->propSysOptions = sysOptions;
1154     }
1155     if (!UpdateBlurBackgroundColor(bgBlurStyle)) {
1156         rsNode_->SetBackgroundFilter(nullptr);
1157         return;
1158     }
1159     SetBackBlurFilter();
1160 }
1161 
UpdateBackgroundEffect(const std::optional<EffectOption> & effectOption,const SysOptions & sysOptions)1162 void RosenRenderContext::UpdateBackgroundEffect(
1163     const std::optional<EffectOption>& effectOption, const SysOptions& sysOptions)
1164 {
1165     CHECK_NULL_VOID(rsNode_);
1166     const auto& groupProperty = GetOrCreateBackground();
1167     if (groupProperty->CheckEffectOption(effectOption) && groupProperty->CheckSystemAdaptationSame(sysOptions)) {
1168         return;
1169     }
1170     groupProperty->propEffectOption = effectOption;
1171     groupProperty->propSysOptions = sysOptions;
1172     if (!effectOption.has_value()) {
1173         return;
1174     }
1175     if (!UpdateBlurBackgroundColor(effectOption)) {
1176         rsNode_->SetBackgroundFilter(nullptr);
1177         return;
1178     }
1179     auto context = GetPipelineContext();
1180     CHECK_NULL_VOID(context);
1181     float radiusPx = context->NormalizeToPx(effectOption->radius);
1182     float backblurRadius = DrawingDecorationPainter::ConvertRadiusToSigma(radiusPx);
1183     auto fastAverage = Rosen::BLUR_COLOR_MODE::DEFAULT;
1184     if (effectOption->adaptiveColor == AdaptiveColor::AVERAGE) {
1185         fastAverage = Rosen::BLUR_COLOR_MODE::FASTAVERAGE;
1186     }
1187     std::shared_ptr<Rosen::RSFilter> backFilter =
1188         Rosen::RSFilter::CreateMaterialFilter(backblurRadius, static_cast<float>(effectOption->saturation),
1189             static_cast<float>(effectOption->brightness), effectOption->color.GetValue(),
1190             static_cast<Rosen::BLUR_COLOR_MODE>(fastAverage), sysOptions.disableSystemAdaptation);
1191     rsNode_->SetBackgroundFilter(backFilter);
1192     if (effectOption->blurOption.grayscale.size() > 1) {
1193         Rosen::Vector2f grayScale(effectOption->blurOption.grayscale[0], effectOption->blurOption.grayscale[1]);
1194         rsNode_->SetGreyCoef(grayScale);
1195     }
1196 }
1197 
UpdateForeBlurStyleForColorMode(const std::optional<BlurStyleOption> & fgBlurStyle,const SysOptions & sysOptions)1198 void RosenRenderContext::UpdateForeBlurStyleForColorMode(
1199     const std::optional<BlurStyleOption>& fgBlurStyle, const SysOptions& sysOptions)
1200 {
1201     auto host = GetHost();
1202     CHECK_NULL_VOID(host);
1203     auto pattern = host->GetPattern();
1204     CHECK_NULL_VOID(pattern);
1205     RefPtr<ResourceObject> resObj = AceType::MakeRefPtr<ResourceObject>("", "", -1);
1206     auto&& updateFunc = [weak = AceType::WeakClaim(this), fgBlurStyle, sysOptions](
1207                             const RefPtr<ResourceObject>& resObj) {
1208         auto render = weak.Upgrade();
1209         CHECK_NULL_VOID(render);
1210         CHECK_NULL_VOID(render->rsNode_);
1211         const auto& groupProperty = render->GetOrCreateForeground();
1212         if (groupProperty->CheckBlurStyleOption(fgBlurStyle) && groupProperty->CheckSysOptionsForBlurSame(sysOptions)) {
1213             // Same with previous value.
1214             // If colorMode is following system and has valid blurStyle, still needs updating
1215             if (fgBlurStyle->colorMode != ThemeColorMode::SYSTEM) {
1216                 return;
1217             }
1218             if (fgBlurStyle->blurOption.grayscale.size() > 1) {
1219                 Rosen::Vector2f grayScale(fgBlurStyle->blurOption.grayscale[0], fgBlurStyle->blurOption.grayscale[1]);
1220                 render->rsNode_->SetGreyCoef(grayScale);
1221             }
1222         } else {
1223             groupProperty->propBlurStyleOption = fgBlurStyle;
1224             groupProperty->propSysOptionsForBlur = sysOptions;
1225         }
1226         render->SetFrontBlurFilter();
1227     };
1228     updateFunc(resObj);
1229     pattern->AddResObj("foregroundBlurStyle.blurStyle", resObj, std::move(updateFunc));
1230 }
1231 
UpdateFrontBlurStyle(const std::optional<BlurStyleOption> & fgBlurStyle,const SysOptions & sysOptions)1232 void RosenRenderContext::UpdateFrontBlurStyle(
1233     const std::optional<BlurStyleOption>& fgBlurStyle, const SysOptions& sysOptions)
1234 {
1235     CHECK_NULL_VOID(rsNode_);
1236     const auto& groupProperty = GetOrCreateForeground();
1237     if (groupProperty->CheckBlurStyleOption(fgBlurStyle) && groupProperty->CheckSysOptionsForBlurSame(sysOptions)) {
1238         // Same with previous value.
1239         // If colorMode is following system and has valid blurStyle, still needs updating
1240         if (fgBlurStyle->colorMode != ThemeColorMode::SYSTEM) {
1241             return;
1242         }
1243         if (fgBlurStyle->blurOption.grayscale.size() > 1) {
1244             Rosen::Vector2f grayScale(fgBlurStyle->blurOption.grayscale[0], fgBlurStyle->blurOption.grayscale[1]);
1245             rsNode_->SetGreyCoef(grayScale);
1246         }
1247     } else {
1248         groupProperty->propBlurStyleOption = fgBlurStyle;
1249         groupProperty->propSysOptionsForBlur = sysOptions;
1250     }
1251     if (SystemProperties::ConfigChangePerform()) {
1252         UpdateForeBlurStyleForColorMode(fgBlurStyle, sysOptions);
1253     }
1254     SetFrontBlurFilter();
1255 }
1256 
ResetBackBlurStyle()1257 void RosenRenderContext::ResetBackBlurStyle()
1258 {
1259     const auto& groupProperty = GetOrCreateBackground();
1260     groupProperty->propBlurStyleOption.reset();
1261     SetBackBlurFilter();
1262 }
1263 
OnSphericalEffectUpdate(double radio)1264 void RosenRenderContext::OnSphericalEffectUpdate(double radio)
1265 {
1266     CHECK_NULL_VOID(rsNode_);
1267     rsNode_->SetSpherizeDegree(static_cast<float>(radio));
1268     RequestNextFrame();
1269 }
1270 
OnPixelStretchEffectUpdate(const PixStretchEffectOption & option)1271 void RosenRenderContext::OnPixelStretchEffectUpdate(const PixStretchEffectOption& option)
1272 {
1273     CHECK_NULL_VOID(rsNode_);
1274     Rosen::Vector4f pixStretchVector;
1275     if (option.IsPercentOption()) {
1276         pixStretchVector.SetValues(static_cast<float>(option.left.Value()), static_cast<float>(option.top.Value()),
1277             static_cast<float>(option.right.Value()), static_cast<float>(option.bottom.Value()));
1278         rsNode_->SetPixelStretchPercent(pixStretchVector);
1279         rsNode_->SetPixelStretch({ 0, 0, 0, 0 });
1280     } else {
1281         pixStretchVector.SetValues(static_cast<float>(option.left.ConvertToPx()),
1282             static_cast<float>(option.top.ConvertToPx()), static_cast<float>(option.right.ConvertToPx()),
1283             static_cast<float>(option.bottom.ConvertToPx()));
1284         rsNode_->SetPixelStretch(pixStretchVector);
1285         rsNode_->SetPixelStretchPercent({ 0, 0, 0, 0 });
1286     }
1287     RequestNextFrame();
1288 }
1289 
OnLightUpEffectUpdate(double radio)1290 void RosenRenderContext::OnLightUpEffectUpdate(double radio)
1291 {
1292     CHECK_NULL_VOID(rsNode_);
1293     rsNode_->SetLightUpEffectDegree(static_cast<float>(radio));
1294     RequestNextFrame();
1295 }
1296 
OnParticleOptionArrayUpdate(const std::list<ParticleOption> & optionList)1297 void RosenRenderContext::OnParticleOptionArrayUpdate(const std::list<ParticleOption>& optionList)
1298 {
1299     CHECK_NULL_VOID(rsNode_);
1300     RectF rect = GetPaintRectWithoutTransform();
1301     if (rect.IsEmpty()) {
1302         return;
1303     }
1304     if (NeedPreloadImage(optionList, rect)) {
1305         return;
1306     }
1307     auto pattern = GetHost()->GetPattern();
1308     auto particlePattern = AceType::DynamicCast<ParticlePattern>(pattern);
1309     if (particlePattern->HaveUnVisibleParent()) {
1310         return;
1311     }
1312     particleAnimationPlaying_ = true;
1313     std::vector<OHOS::Rosen::ParticleParams> particleParams;
1314     for (auto& item : optionList) {
1315         particleParams.emplace_back(ConvertParticleOptionToParams(item, rect));
1316     }
1317     auto finishCallback = [weak = WeakClaim(this)]() {
1318         auto renderContext = weak.Upgrade();
1319         CHECK_NULL_VOID(renderContext);
1320         renderContext->particleAnimationPlaying_ = false;
1321     };
1322     rsNode_->SetParticleParams(particleParams, finishCallback);
1323     RequestNextFrame();
1324 }
1325 
OnEmitterPropertyUpdate()1326 void RosenRenderContext::OnEmitterPropertyUpdate()
1327 {
1328     auto host = GetHost();
1329     CHECK_NULL_VOID(host);
1330     auto pattern = host->GetPattern();
1331     CHECK_NULL_VOID(pattern);
1332     auto particlePattern = AceType::DynamicCast<ParticlePattern>(pattern);
1333     CHECK_NULL_VOID(particlePattern);
1334     auto property = particlePattern->GetEmitterProperty();
1335     if (property.empty()) {
1336         return;
1337     }
1338     for (const auto& prop : property) {
1339         if (!prop.annulusRegion.has_value()) {
1340             continue;
1341         }
1342         const auto& annulusRegion = prop.annulusRegion.value();
1343         if (annulusRegion.GetCenter().first.Unit() == DimensionUnit::PERCENT ||
1344             annulusRegion.GetCenter().second.Unit() == DimensionUnit::PERCENT) {
1345             particlePattern->updateEmitterPosition(property);
1346             return;
1347         }
1348     }
1349 }
1350 
OnClickEffectLevelUpdate(const ClickEffectInfo & info)1351 void RosenRenderContext::OnClickEffectLevelUpdate(const ClickEffectInfo& info)
1352 {
1353     if (HasClickEffectLevel()) {
1354         InitEventClickEffect();
1355     }
1356 }
1357 
UpdateVisualEffect(const OHOS::Rosen::VisualEffect * visualEffect)1358 void RosenRenderContext::UpdateVisualEffect(const OHOS::Rosen::VisualEffect* visualEffect)
1359 {
1360     CHECK_NULL_VOID(visualEffect);
1361     rsNode_->SetVisualEffect(visualEffect);
1362 }
1363 
UpdateBackgroundFilter(const OHOS::Rosen::Filter * backgroundFilter)1364 void RosenRenderContext::UpdateBackgroundFilter(const OHOS::Rosen::Filter* backgroundFilter)
1365 {
1366     CHECK_NULL_VOID(backgroundFilter);
1367     rsNode_->SetUIBackgroundFilter(backgroundFilter);
1368 }
1369 
UpdateForegroundFilter(const OHOS::Rosen::Filter * foregroundFilter)1370 void RosenRenderContext::UpdateForegroundFilter(const OHOS::Rosen::Filter* foregroundFilter)
1371 {
1372     CHECK_NULL_VOID(foregroundFilter);
1373     rsNode_->SetUIForegroundFilter(foregroundFilter);
1374 }
1375 
UpdateCompositingFilter(const OHOS::Rosen::Filter * compositingFilter)1376 void RosenRenderContext::UpdateCompositingFilter(const OHOS::Rosen::Filter* compositingFilter)
1377 {
1378     CHECK_NULL_VOID(compositingFilter);
1379     rsNode_->SetUICompositingFilter(compositingFilter);
1380 }
1381 
NeedPreloadImage(const std::list<ParticleOption> & optionList,RectF & rect)1382 bool RosenRenderContext::NeedPreloadImage(const std::list<ParticleOption>& optionList, RectF& rect)
1383 {
1384     bool flag = false;
1385     std::vector<OHOS::Rosen::ParticleParams> particleParams;
1386     for (auto& item : optionList) {
1387         auto emitterOption = item.GetEmitterOption();
1388         auto particle = emitterOption.GetParticle();
1389         auto particleType = particle.GetParticleType();
1390         auto particleConfig = particle.GetConfig();
1391         if (particleType == ParticleType::IMAGE) {
1392             auto imageParameter = particleConfig.GetImageParticleParameter();
1393             auto imageSize = imageParameter.GetSize();
1394             auto imageWidth = Dimension(ConvertDimensionToPx(imageSize.first, rect.Width()), DimensionUnit::PX);
1395             auto imageHeight = Dimension(ConvertDimensionToPx(imageSize.second, rect.Height()), DimensionUnit::PX);
1396             auto canvasImageIter = particleImageMap_.find(imageParameter.GetImageSource());
1397             bool imageHasData = true;
1398             if (canvasImageIter->second) {
1399                 imageHasData = canvasImageIter->second->HasData();
1400             }
1401             if (canvasImageIter == particleImageMap_.end() || !imageHasData) {
1402                 LoadParticleImage(imageParameter.GetImageSource(), imageWidth, imageHeight);
1403                 flag = true;
1404             }
1405         }
1406     }
1407     return flag;
1408 }
1409 
ConvertParticleOptionToParams(const ParticleOption & particleOption,const RectF & rect)1410 Rosen::ParticleParams RosenRenderContext::ConvertParticleOptionToParams(
1411     const ParticleOption& particleOption, const RectF& rect)
1412 {
1413     auto emitterOption = particleOption.GetEmitterOption();
1414     auto colorOptionOpt = particleOption.GetParticleColorOption();
1415     auto opacityOptionOpt = particleOption.GetParticleOpacityOption();
1416     auto scaleOptionOpt = particleOption.GetParticleScaleOption();
1417     auto velocityOptionOpt = particleOption.GetParticleVelocityOption();
1418     auto accelerationOpt = particleOption.GetParticleAccelerationOption();
1419     auto spinOptionOpt = particleOption.GetParticleSpinOption();
1420     auto rsEmitterConfig = ConvertParticleEmitterOption(emitterOption, rect);
1421     std::optional<OHOS::Rosen::ParticleColorParaType> rsColorOpt;
1422     std::optional<OHOS::Rosen::ParticleParaType<float>> rsSpinOpt;
1423     std::optional<OHOS::Rosen::ParticleVelocity> rsVelocityOpt;
1424     std::optional<OHOS::Rosen::ParticleParaType<float>> rsOpacityOpt;
1425     std::optional<OHOS::Rosen::ParticleParaType<float>> rsScaleOpt;
1426     std::optional<OHOS::Rosen::ParticleAcceleration> rsAccelerationOpt;
1427     if (colorOptionOpt.has_value()) {
1428         rsColorOpt = ConvertParticleColorOption(colorOptionOpt.value());
1429     } else {
1430         rsColorOpt = ConvertParticleDefaultColorOption(std::nullopt);
1431     }
1432     if (opacityOptionOpt.has_value()) {
1433         rsOpacityOpt = ConvertParticleFloatOption(opacityOptionOpt.value());
1434     } else {
1435         OHOS::Rosen::Range<float> rsInitRange(PARTICLE_DEFAULT_OPACITY, PARTICLE_DEFAULT_OPACITY);
1436         rsOpacityOpt = ConvertParticleDefaultFloatOption(rsInitRange);
1437     }
1438     if (scaleOptionOpt.has_value()) {
1439         rsScaleOpt = ConvertParticleFloatOption(scaleOptionOpt.value());
1440     } else {
1441         OHOS::Rosen::Range<float> rsInitRange(PARTICLE_DEFAULT_SCALE, PARTICLE_DEFAULT_SCALE);
1442         rsScaleOpt = ConvertParticleDefaultFloatOption(rsInitRange);
1443     }
1444     if (velocityOptionOpt.has_value()) {
1445         rsVelocityOpt = ConvertParticleVelocityOption(velocityOptionOpt.value());
1446     } else {
1447         rsVelocityOpt = ConvertParticleDefaultVelocityOption();
1448     }
1449     if (accelerationOpt.has_value()) {
1450         rsAccelerationOpt = ConvertParticleAccelerationOption(accelerationOpt.value());
1451     } else {
1452         rsAccelerationOpt = ConvertParticleDefaultAccelerationOption();
1453     }
1454     if (spinOptionOpt.has_value()) {
1455         rsSpinOpt = ConvertParticleFloatOption(spinOptionOpt.value());
1456     } else {
1457         OHOS::Rosen::Range<float> rsInitRange(PARTICLE_DEFAULT_SPIN, PARTICLE_DEFAULT_SPIN);
1458         rsSpinOpt = ConvertParticleDefaultFloatOption(rsInitRange);
1459     }
1460     return OHOS::Rosen::ParticleParams(rsEmitterConfig, rsVelocityOpt.value(), rsAccelerationOpt.value(),
1461         rsColorOpt.value(), rsOpacityOpt.value(), rsScaleOpt.value(), rsSpinOpt.value());
1462 }
1463 
ConvertParticleEmitterOption(const EmitterOption & emitterOption,const RectF & rect)1464 Rosen::EmitterConfig RosenRenderContext::ConvertParticleEmitterOption(
1465     const EmitterOption& emitterOption, const RectF& rect)
1466 {
1467     auto emitterRateOpt = emitterOption.GetEmitterRate();
1468     auto pointOpt = emitterOption.GetPosition();
1469     auto sizeOpt = emitterOption.GetSize();
1470     auto shapeOpt = emitterOption.GetShape();
1471     auto particle = emitterOption.GetParticle();
1472     auto particleType = particle.GetParticleType();
1473     auto particleConfig = particle.GetConfig();
1474     auto particleCount = particle.GetCount();
1475     auto lifeTimeOpt = particle.GetLifeTime();
1476     auto lifeTimeRangeOpt = particle.GetLifeTimeRange();
1477     std::optional<int64_t> lifeTimeMin = 0;
1478     std::optional<int64_t> lifeTimeMax = lifeTimeOpt.value() + lifeTimeRangeOpt.value();
1479     if (lifeTimeOpt.value() == -1) {
1480         // when lifeTime == -1 particle life cycle is infinite
1481         lifeTimeMin = -1;
1482         lifeTimeMax = -1;
1483     } else if (lifeTimeOpt.value() - lifeTimeRangeOpt.value() > 0) {
1484         lifeTimeMin = lifeTimeOpt.value() - lifeTimeRangeOpt.value();
1485     }
1486     auto rsPoint = pointOpt.has_value()
1487                        ? OHOS::Rosen::Vector2f(ConvertDimensionToPx(pointOpt.value().first, rect.Width()),
1488                              ConvertDimensionToPx(pointOpt.value().second, rect.Height()))
1489                        : OHOS::Rosen::Vector2f(0.0f, 0.0f);
1490     auto rsSize = sizeOpt.has_value() ? OHOS::Rosen::Vector2f(ConvertDimensionToPx(sizeOpt.value().first, rect.Width()),
1491                                             ConvertDimensionToPx(sizeOpt.value().second, rect.Height()))
1492                                       : OHOS::Rosen::Vector2f(rect.Width(), rect.Height());
1493     auto shapeInt = static_cast<int32_t>(shapeOpt.value_or(ParticleEmitterShape::RECTANGLE));
1494     auto lifeTimeRange = OHOS::Rosen::Range<int64_t>(
1495         lifeTimeMin.value_or(PARTICLE_DEFAULT_LIFETIME), lifeTimeMax.value_or(PARTICLE_DEFAULT_LIFETIME));
1496 
1497     // The default value for the centerXY axis is 50 percent,
1498     // for the innerRadius or outerRadius is 0,
1499     // for the startAngle is 0, for the endAngle is 360.
1500     std::shared_ptr<Rosen::AnnulusRegion> rsAnnulusRegion = std::make_shared<Rosen::AnnulusRegion>(
1501         OHOS::Rosen::Vector2f(DEFAULT_CENTER_VALUE.ConvertToPxWithSize(rect.Width()),
1502         DEFAULT_CENTER_VALUE.ConvertToPxWithSize(rect.Height())),
1503         DEFAULT_RADIUS_VALUE, DEFAULT_RADIUS_VALUE, DEFAULT_START_ANGLE_VALUE, DEFAULT_END_ANGLE_VALUE);
1504     auto annulusRegionOpt = emitterOption.GetAnnulusRegion();
1505     if (annulusRegionOpt.has_value() && shapeInt == static_cast<int32_t>(ParticleEmitterShape::ANNULUS)) {
1506         auto annulusRegion = annulusRegionOpt.value();
1507         auto center = annulusRegion.GetCenter();
1508         auto rsCenter = OHOS::Rosen::Vector2f(center.first.ConvertToPxWithSize(rect.Width()),
1509             center.second.ConvertToPxWithSize(rect.Height()));
1510         auto innerRadius = annulusRegion.GetInnerRadius();
1511         auto rsInnerRadius =
1512             (LessOrEqual(innerRadius.ConvertToPx(), 0.0) || innerRadius.Unit() == DimensionUnit::PERCENT)
1513             ? 0.0
1514             : innerRadius.ConvertToPx();
1515         auto outerRadius = annulusRegion.GetOuterRadius();
1516         auto rsOuterRadius =
1517             (LessOrEqual(outerRadius.ConvertToPx(), 0.0) || outerRadius.Unit() == DimensionUnit::PERCENT)
1518             ? 0.0
1519             : outerRadius.ConvertToPx();
1520         rsAnnulusRegion = std::make_shared<Rosen::AnnulusRegion>(rsCenter, rsInnerRadius,
1521             rsOuterRadius, annulusRegion.GetStartAngle(), annulusRegion.GetEndAngle());
1522     }
1523     if (particleType == ParticleType::IMAGE) {
1524         auto imageParameter = particleConfig.GetImageParticleParameter();
1525         auto imageSource = imageParameter.GetImageSource();
1526         auto imageSize = imageParameter.GetSize();
1527         auto imageWidth = Dimension(ConvertDimensionToPx(imageSize.first, rect.Width()), DimensionUnit::PX);
1528         auto imageHeight = Dimension(ConvertDimensionToPx(imageSize.second, rect.Height()), DimensionUnit::PX);
1529         auto rsImagePtr = std::make_shared<Rosen::RSImage>();
1530         if (particleImageMap_.find(imageSource) != particleImageMap_.end()) {
1531             SetRsParticleImage(rsImagePtr, imageSource);
1532         }
1533         rsImagePtr->SetImageFit(static_cast<int32_t>(imageParameter.GetImageFit().value_or(ImageFit::COVER)));
1534         OHOS::Rosen::Vector2f rsImageSize(imageWidth.ConvertToPx(), imageHeight.ConvertToPx());
1535         auto emitterConfig =  OHOS::Rosen::EmitterConfig(emitterRateOpt.value_or(PARTICLE_DEFAULT_EMITTER_RATE),
1536             static_cast<OHOS::Rosen::ShapeType>(shapeInt), rsPoint, rsSize, particleCount, lifeTimeRange,
1537             OHOS::Rosen::ParticleType::IMAGES, 0.0f, rsImagePtr, rsImageSize);
1538         emitterConfig.SetConfigShape(rsAnnulusRegion);
1539         return emitterConfig;
1540     } else {
1541         auto pointParameter = particleConfig.GetPointParticleParameter();
1542         auto radius = pointParameter.GetRadius();
1543         auto emitterConfig =  OHOS::Rosen::EmitterConfig(emitterRateOpt.value_or(PARTICLE_DEFAULT_EMITTER_RATE),
1544             static_cast<OHOS::Rosen::ShapeType>(shapeInt), rsPoint, rsSize, particleCount, lifeTimeRange,
1545             OHOS::Rosen::ParticleType::POINTS, radius, std::make_shared<OHOS::Rosen::RSImage>(),
1546             OHOS::Rosen::Vector2f());
1547         emitterConfig.SetConfigShape(rsAnnulusRegion);
1548         return emitterConfig;
1549     }
1550 }
1551 
SetRsParticleImage(std::shared_ptr<Rosen::RSImage> & rsImagePtr,std::string & imageSource)1552 void RosenRenderContext::SetRsParticleImage(std::shared_ptr<Rosen::RSImage>& rsImagePtr, std::string& imageSource)
1553 {
1554     auto it = particleImageMap_.find(imageSource);
1555     if (it == particleImageMap_.end()) {
1556         return;
1557     }
1558     auto image = it->second;
1559     CHECK_NULL_VOID(image);
1560 
1561     if (InstanceOf<PixelMapImage>(image)) {
1562         auto pixmap = image->GetPixelMap();
1563         CHECK_NULL_VOID(pixmap);
1564         auto pixMapPtr = pixmap->GetPixelMapSharedPtr();
1565         rsImagePtr->SetPixelMap(pixMapPtr);
1566         if (pixMapPtr) {
1567             rsImagePtr->SetSrcRect(Rosen::RectF(0, 0, pixMapPtr->GetWidth(), pixMapPtr->GetHeight()));
1568         }
1569     } else if (InstanceOf<DrawingImage>(image)) {
1570         auto drawingImage = DynamicCast<DrawingImage>(image);
1571         CHECK_NULL_VOID(drawingImage);
1572         auto compressData = drawingImage->GetCompressData();
1573         if (compressData) {
1574             rsImagePtr->SetCompressData(compressData, drawingImage->GetUniqueID(), drawingImage->GetCompressWidth(),
1575                 drawingImage->GetCompressHeight());
1576             rsImagePtr->SetSrcRect(
1577                 Rosen::RectF(0, 0, drawingImage->GetCompressWidth(), drawingImage->GetCompressHeight()));
1578         } else {
1579             rsImagePtr->SetImage(drawingImage->GetImage());
1580             if (drawingImage->GetImage()) {
1581                 rsImagePtr->SetSrcRect(
1582                     Rosen::RectF(0, 0, drawingImage->GetImage()->GetWidth(), drawingImage->GetImage()->GetHeight()));
1583             }
1584         }
1585         if (!HasValidBgImageResizable()) {
1586             rsImagePtr->SetImageRepeat(static_cast<int>(GetBackgroundImageRepeat().value_or(ImageRepeat::NO_REPEAT)));
1587         }
1588     }
1589 }
1590 
LoadParticleImage(const std::string & src,Dimension & width,Dimension & height)1591 void RosenRenderContext::LoadParticleImage(const std::string& src, Dimension& width, Dimension& height)
1592 {
1593     if (particleImageContextMap_.find(src) != particleImageContextMap_.end()) {
1594         return;
1595     }
1596     ImageSourceInfo imageSourceInfo(src, width, height);
1597     imageSourceInfo.SetNeedCache(false);
1598     auto preLoadCallback = [weak = WeakClaim(this), imageSrc = src](const ImageSourceInfo& sourceInfo) {
1599         auto renderContent = weak.Upgrade();
1600         CHECK_NULL_VOID(renderContent);
1601         auto& imageContext = renderContent->particleImageContextMap_[imageSrc];
1602         CHECK_NULL_VOID(imageContext);
1603         imageContext->MakeCanvasImage(SizeF(), true, ImageFit::NONE);
1604     };
1605     auto loadingSuccessCallback = [weak = WeakClaim(this), imageSrc = src](const ImageSourceInfo& sourceInfo) {
1606         auto renderContent = weak.Upgrade();
1607         CHECK_NULL_VOID(renderContent);
1608         auto& imageContext = renderContent->particleImageContextMap_[imageSrc];
1609         CHECK_NULL_VOID(imageContext);
1610         auto imagePtr = imageContext->MoveCanvasImage();
1611         renderContent->OnParticleImageLoaded(imageSrc, imagePtr);
1612     };
1613     auto loadingErrorCallback = [weak = WeakClaim(this), imageSrc = src](const ImageSourceInfo& sourceInfo,
1614                                     const std::string& errorMsg, const ImageErrorInfo& /* errorInfo */) {
1615         auto renderContent = weak.Upgrade();
1616         CHECK_NULL_VOID(renderContent);
1617         renderContent->OnParticleImageLoaded(imageSrc, nullptr);
1618     };
1619     LoadNotifier loadNotifier(preLoadCallback, loadingSuccessCallback, loadingErrorCallback);
1620     auto particleImageLoadingCtx = AceType::MakeRefPtr<ImageLoadingContext>(imageSourceInfo, std::move(loadNotifier));
1621     imageSourceInfo.SetSrc(src, Color(0x00000000));
1622     particleImageLoadingCtx->LoadImageData();
1623     particleImageContextMap_.try_emplace(src, particleImageLoadingCtx);
1624 }
1625 
OnParticleImageLoaded(const std::string & src,RefPtr<CanvasImage> canvasImage)1626 void RosenRenderContext::OnParticleImageLoaded(const std::string& src, RefPtr<CanvasImage> canvasImage)
1627 {
1628     particleImageMap_.try_emplace(src, canvasImage);
1629     if (particleImageContextMap_.find(src) != particleImageContextMap_.end()) {
1630         particleImageContextMap_.erase(src);
1631     }
1632     if (particleImageContextMap_.empty() && propParticleOptionArray_.has_value()) {
1633         OnParticleOptionArrayUpdate(propParticleOptionArray_.value());
1634     }
1635 }
1636 
ConvertDimensionToPx(Dimension & src,float size)1637 float RosenRenderContext::ConvertDimensionToPx(Dimension& src, float size)
1638 {
1639     if (src.Unit() == DimensionUnit::PERCENT) {
1640         return src.ConvertToPxWithSize(size);
1641     }
1642     return src.ConvertToPx();
1643 }
1644 
ConvertParticleVelocityOption(const VelocityProperty & velocity)1645 Rosen::ParticleVelocity RosenRenderContext::ConvertParticleVelocityOption(const VelocityProperty& velocity)
1646 {
1647     auto rsSpeedRange = OHOS::Rosen::Range<float>(velocity.GetSpeedRange().first, velocity.GetSpeedRange().second);
1648     auto rsAngleRange = OHOS::Rosen::Range<float>(velocity.GetAngleRange().first, velocity.GetAngleRange().second);
1649     return OHOS::Rosen::ParticleVelocity(rsSpeedRange, rsAngleRange);
1650 }
1651 
ConvertParticleDefaultVelocityOption()1652 Rosen::ParticleVelocity RosenRenderContext::ConvertParticleDefaultVelocityOption()
1653 {
1654     auto rsSpeedRange = OHOS::Rosen::Range<float>(PARTICLE_DEFAULT_SPEED, PARTICLE_DEFAULT_SPEED);
1655     auto rsAngleRange = OHOS::Rosen::Range<float>(PARTICLE_DEFAULT_ANGLE, PARTICLE_DEFAULT_ANGLE);
1656     return OHOS::Rosen::ParticleVelocity(rsSpeedRange, rsAngleRange);
1657 }
1658 
ConvertParticleAccelerationOption(const AccelerationProperty & acceleration)1659 Rosen::ParticleAcceleration RosenRenderContext::ConvertParticleAccelerationOption(
1660     const AccelerationProperty& acceleration)
1661 {
1662     auto speedOpt = acceleration.GetSpeed();
1663     auto angleOpt = acceleration.GetAngle();
1664     std::optional<OHOS::Rosen::ParticleParaType<float>> rsSpeedOpt;
1665     std::optional<OHOS::Rosen::ParticleParaType<float>> rsAngleOpt;
1666     OHOS::Rosen::Range<float> rsInitSpeedRange(PARTICLE_DEFAULT_SPEED, PARTICLE_DEFAULT_SPEED);
1667     if (speedOpt.has_value()) {
1668         rsSpeedOpt = ConvertParticleFloatOption(speedOpt.value());
1669     } else {
1670         rsSpeedOpt = ConvertParticleDefaultFloatOption(rsInitSpeedRange);
1671     }
1672     OHOS::Rosen::Range<float> rsInitAngleRange(PARTICLE_DEFAULT_ANGLE, PARTICLE_DEFAULT_ANGLE);
1673     if (angleOpt.has_value()) {
1674         rsAngleOpt = ConvertParticleFloatOption(angleOpt.value());
1675     } else {
1676         rsAngleOpt = ConvertParticleDefaultFloatOption(rsInitAngleRange);
1677     }
1678     return OHOS::Rosen::ParticleAcceleration(rsSpeedOpt.value(), rsAngleOpt.value());
1679 }
1680 
ConvertParticleDefaultAccelerationOption()1681 Rosen::ParticleAcceleration RosenRenderContext::ConvertParticleDefaultAccelerationOption()
1682 {
1683     OHOS::Rosen::Range<float> rsInitRange(PARTICLE_DEFAULT_SPEED, PARTICLE_DEFAULT_SPEED);
1684     return OHOS::Rosen::ParticleAcceleration(
1685         ConvertParticleDefaultFloatOption(rsInitRange), ConvertParticleDefaultFloatOption(rsInitRange));
1686 }
1687 
ConvertParticleColorOption(const ParticleColorPropertyOption & colorOption)1688 Rosen::ParticleColorParaType RosenRenderContext::ConvertParticleColorOption(
1689     const ParticleColorPropertyOption& colorOption)
1690 {
1691     auto initRange = colorOption.GetRange();
1692     auto colorDist = colorOption.GetDistribution();
1693     auto updaterOpt = colorOption.GetUpdater();
1694     OHOS::Rosen::Range<OHOS::Rosen::RSColor> rsInitRange(
1695         OHOS::Rosen::RSColor(initRange.first.GetRed(), initRange.first.GetGreen(), initRange.first.GetBlue(),
1696             initRange.first.GetAlpha()),
1697         OHOS::Rosen::RSColor(initRange.second.GetRed(), initRange.second.GetGreen(), initRange.second.GetBlue(),
1698             initRange.second.GetAlpha()));
1699     auto colorDistInt = static_cast<int32_t>(colorDist.value_or(DistributionType::UNIFORM));
1700     if (updaterOpt.has_value()) {
1701         auto updater = updaterOpt.value();
1702         auto updateType = updater.GetUpdateType();
1703         auto config = updater.GetConfig();
1704         if (updateType == UpdaterType::RANDOM) {
1705             auto randomConfig = config.GetRandomConfig();
1706             auto redRandom = randomConfig.GetRedRandom();
1707             auto greenRandom = randomConfig.GetGreenRandom();
1708             auto blueRandom = randomConfig.GetBlueRandom();
1709             auto alphaRandom = randomConfig.GetAlphaRandom();
1710             OHOS::Rosen::Range<float> rsRedRandom(redRandom.first, redRandom.second);
1711             OHOS::Rosen::Range<float> rsGreenRandom(greenRandom.first, greenRandom.second);
1712             OHOS::Rosen::Range<float> rsBlueRandom(blueRandom.first, blueRandom.second);
1713             OHOS::Rosen::Range<float> rsAlphaRandom(alphaRandom.first, alphaRandom.second);
1714             std::vector<OHOS::Rosen::Change<OHOS::Rosen::RSColor>> invalidCurve;
1715             return OHOS::Rosen::ParticleColorParaType(rsInitRange,
1716                 static_cast<OHOS::Rosen::DistributionType>(colorDistInt), OHOS::Rosen::ParticleUpdator::RANDOM,
1717                 rsRedRandom, rsGreenRandom, rsBlueRandom, rsAlphaRandom, invalidCurve);
1718         } else if (updateType == UpdaterType::CURVE) {
1719             auto& curveConfig = config.GetAnimationArray();
1720             std::vector<OHOS::Rosen::Change<OHOS::Rosen::RSColor>> valChangeOverLife;
1721             for (const auto& colorAnimationConfig : curveConfig) {
1722                 auto fromColor = colorAnimationConfig.GetFrom();
1723                 auto toColor = colorAnimationConfig.GetTo();
1724                 auto startMills = colorAnimationConfig.GetStartMills();
1725                 auto endMills = colorAnimationConfig.GetEndMills();
1726                 auto curve = colorAnimationConfig.GetCurve();
1727                 auto rsCurve = NativeCurveHelper::ToNativeCurve(curve);
1728                 valChangeOverLife.emplace_back(OHOS::Rosen::Change<OHOS::Rosen::RSColor>(
1729                     OHOS::Rosen::RSColor(
1730                         fromColor.GetRed(), fromColor.GetGreen(), fromColor.GetBlue(), fromColor.GetAlpha()),
1731                     OHOS::Rosen::RSColor(toColor.GetRed(), toColor.GetGreen(), toColor.GetBlue(), toColor.GetAlpha()),
1732                     startMills, endMills, rsCurve));
1733             }
1734             return OHOS::Rosen::ParticleColorParaType(rsInitRange,
1735                 static_cast<OHOS::Rosen::DistributionType>(colorDistInt), ParticleUpdator::CURVE,
1736                 OHOS::Rosen::Range<float>(), OHOS::Rosen::Range<float>(), OHOS::Rosen::Range<float>(),
1737                 OHOS::Rosen::Range<float>(), valChangeOverLife);
1738         }
1739     }
1740     return ConvertParticleDefaultColorOption(rsInitRange);
1741 }
1742 
ConvertParticleDefaultColorOption(std::optional<OHOS::Rosen::Range<OHOS::Rosen::RSColor>> rsInitRangeOpt)1743 Rosen::ParticleColorParaType RosenRenderContext::ConvertParticleDefaultColorOption(
1744     std::optional<OHOS::Rosen::Range<OHOS::Rosen::RSColor>> rsInitRangeOpt)
1745 {
1746     std::vector<OHOS::Rosen::Change<OHOS::Rosen::RSColor>> invalidCurve;
1747     if (rsInitRangeOpt.has_value()) {
1748         return OHOS::Rosen::ParticleColorParaType(rsInitRangeOpt.value(), OHOS::Rosen::DistributionType::UNIFORM,
1749             OHOS::Rosen::ParticleUpdator::NONE, OHOS::Rosen::Range<float>(), OHOS::Rosen::Range<float>(),
1750             OHOS::Rosen::Range<float>(), OHOS::Rosen::Range<float>(), invalidCurve);
1751     }
1752     return OHOS::Rosen::ParticleColorParaType(
1753         OHOS::Rosen::Range<OHOS::Rosen::RSColor>(
1754             OHOS::Rosen::RSColor(PARTICLE_DEFAULT_COLOR), OHOS::Rosen::RSColor(PARTICLE_DEFAULT_COLOR)),
1755         OHOS::Rosen::DistributionType::UNIFORM, OHOS::Rosen::ParticleUpdator::NONE, OHOS::Rosen::Range<float>(),
1756         OHOS::Rosen::Range<float>(), OHOS::Rosen::Range<float>(), OHOS::Rosen::Range<float>(), invalidCurve);
1757 }
1758 
ConvertParticleFloatOption(const ParticleFloatPropertyOption & floatOption)1759 Rosen::ParticleParaType<float> RosenRenderContext::ConvertParticleFloatOption(
1760     const ParticleFloatPropertyOption& floatOption)
1761 {
1762     auto initRange = floatOption.GetRange();
1763     OHOS::Rosen::Range<float> rsInitRange(initRange.first, initRange.second);
1764     auto updaterOpt = floatOption.GetUpdater();
1765     if (updaterOpt.has_value()) {
1766         auto updater = updaterOpt.value();
1767         auto updateType = updater.GetUpdaterType();
1768         auto& config = updater.GetConfig();
1769         if (updateType == UpdaterType::RANDOM) {
1770             auto& randomRangeConfig = config.GetRandomConfig();
1771             std::vector<OHOS::Rosen::Change<float>> invalidChangeInOverLifeArray;
1772             return OHOS::Rosen::ParticleParaType<float>(rsInitRange, OHOS::Rosen::ParticleUpdator::RANDOM,
1773                 OHOS::Rosen::Range<float>(randomRangeConfig.first, randomRangeConfig.second),
1774                 invalidChangeInOverLifeArray);
1775         } else if (updateType == UpdaterType::CURVE) {
1776             auto curveConfig = config.GetAnimations();
1777             std::vector<OHOS::Rosen::Change<float>> valChangeOverLife;
1778             for (auto& animationConfig : curveConfig) {
1779                 auto from = animationConfig.GetFrom();
1780                 auto to = animationConfig.GetTo();
1781                 auto startMills = animationConfig.GetStartMills();
1782                 auto endMills = animationConfig.GetEndMills();
1783                 auto rsCurve = NativeCurveHelper::ToNativeCurve(animationConfig.GetCurve());
1784                 valChangeOverLife.emplace_back(OHOS::Rosen::Change<float>(from, to, startMills, endMills, rsCurve));
1785             }
1786             OHOS::Rosen::Range<float> rsInvalidRange;
1787             return OHOS::Rosen::ParticleParaType<float>(
1788                 rsInitRange, OHOS::Rosen::ParticleUpdator::CURVE, rsInvalidRange, valChangeOverLife);
1789         }
1790     }
1791     return ConvertParticleDefaultFloatOption(rsInitRange);
1792 }
1793 
ConvertParticleDefaultFloatOption(OHOS::Rosen::Range<float> & rsInitRange)1794 Rosen::ParticleParaType<float> RosenRenderContext::ConvertParticleDefaultFloatOption(
1795     OHOS::Rosen::Range<float>& rsInitRange)
1796 {
1797     std::vector<OHOS::Rosen::Change<float>> invalidChangeInOverLifeArray;
1798     return OHOS::Rosen::ParticleParaType<float>(
1799         rsInitRange, OHOS::Rosen::ParticleUpdator::NONE, OHOS::Rosen::Range<float>(), invalidChangeInOverLifeArray);
1800 }
1801 
OnOpacityUpdate(double opacity)1802 void RosenRenderContext::OnOpacityUpdate(double opacity)
1803 {
1804     CHECK_NULL_VOID(rsNode_);
1805     if (AnimationUtils::IsImplicitAnimationOpen() && alphaUserModifier_ && GetHost()) {
1806         auto preOpacity = alphaUserModifier_->GetAlpha();
1807         if (!NearEqual(preOpacity, opacity)) {
1808             auto host = GetHost();
1809             ACE_SCOPED_TRACE(
1810                 "opacity from %f to %f, id:%d, tag:%s", preOpacity, opacity, host->GetId(), host->GetTag().c_str());
1811         }
1812     }
1813     AddOrUpdateModifier<Rosen::ModifierNG::RSAlphaModifier, &Rosen::ModifierNG::RSAlphaModifier::SetAlpha, float>(
1814         alphaUserModifier_, opacity);
1815     MarkNeedDrawNode(opacity < 1.0);
1816     RequestNextFrame();
1817 }
1818 
OnDynamicRangeModeUpdate(DynamicRangeMode dynamicRangeMode)1819 void RosenRenderContext::OnDynamicRangeModeUpdate(DynamicRangeMode dynamicRangeMode)
1820 {
1821     auto rsCanvasNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasNode>(rsNode_);
1822     CHECK_NULL_VOID(rsCanvasNode);
1823     if (dynamicRangeMode < DynamicRangeMode::STANDARD && !isHdr_) {
1824         TAG_LOGD(AceLogTag::ACE_IMAGE, "Set HDRPresent True.");
1825         isHdr_ = true;
1826         rsCanvasNode->SetHDRPresent(true);
1827     } else if (isHdr_) {
1828         TAG_LOGD(AceLogTag::ACE_IMAGE, "Set HDRPresent False.");
1829         isHdr_ = false;
1830         rsCanvasNode->SetHDRPresent(false);
1831     }
1832 }
1833 
SetAlphaOffscreen(bool isOffScreen)1834 void RosenRenderContext::SetAlphaOffscreen(bool isOffScreen)
1835 {
1836     CHECK_NULL_VOID(rsNode_);
1837     rsNode_->SetAlphaOffscreen(isOffScreen);
1838 }
1839 
1840 class DrawDragThumbnailCallback : public SurfaceCaptureCallback {
1841 public:
OnSurfaceCapture(std::shared_ptr<Media::PixelMap> pixelMap)1842     void OnSurfaceCapture(std::shared_ptr<Media::PixelMap> pixelMap) override
1843     {
1844         if (pixelMap) {
1845 #ifdef PIXEL_MAP_SUPPORTED
1846             g_pixelMap = PixelMap::CreatePixelMap(reinterpret_cast<void*>(&pixelMap));
1847 #endif // PIXEL_MAP_SUPPORTED
1848         } else {
1849             g_pixelMap = nullptr;
1850             TAG_LOGE(AceLogTag::ACE_DRAG, "get thumbnail pixelMap failed!");
1851         }
1852         if (callback_ == nullptr) {
1853             std::unique_lock<std::mutex> lock(g_mutex);
1854             thumbnailGet.notify_all();
1855             return;
1856         }
1857         callback_(g_pixelMap);
1858     }
OnSurfaceCaptureHDR(std::shared_ptr<Media::PixelMap> pixelMap,std::shared_ptr<Media::PixelMap> hdrPixelMap)1859     void OnSurfaceCaptureHDR(std::shared_ptr<Media::PixelMap> pixelMap,
1860         std::shared_ptr<Media::PixelMap> hdrPixelMap) override {}
1861     std::function<void(const RefPtr<PixelMap>&)> callback_;
1862 };
1863 
GetThumbnailPixelMap(bool needScale,bool isOffline)1864 RefPtr<PixelMap> RosenRenderContext::GetThumbnailPixelMap(bool needScale, bool isOffline)
1865 {
1866     CHECK_NULL_RETURN(rsNode_, nullptr);
1867     std::shared_ptr<DrawDragThumbnailCallback> drawDragThumbnailCallback =
1868         std::make_shared<DrawDragThumbnailCallback>();
1869     CHECK_NULL_RETURN(drawDragThumbnailCallback, nullptr);
1870     drawDragThumbnailCallback->callback_ = nullptr;
1871     float scaleX = 1.0f;
1872     float scaleY = 1.0f;
1873     if (needScale) {
1874         UpdateThumbnailPixelMapScale(scaleX, scaleY);
1875     }
1876     AddRsNodeForCapture();
1877     auto ret = RSInterfaces::GetInstance().TakeSurfaceCaptureForUI(rsNode_, drawDragThumbnailCallback, scaleX, scaleY,
1878         isOffline);
1879     if (!ret) {
1880         LOGE("TakeSurfaceCaptureForUI failed!");
1881         return nullptr;
1882     }
1883     std::unique_lock<std::mutex> lock(g_mutex);
1884     if (thumbnailGet.wait_for(lock, PIXELMAP_TIMEOUT_DURATION) == std::cv_status::timeout) {
1885         LOGE("get thumbnail pixelMap timeout!");
1886         return nullptr;
1887     }
1888     return g_pixelMap;
1889 }
1890 
CreateThumbnailPixelMapAsyncTask(bool needScale,std::function<void (const RefPtr<PixelMap>)> && callback)1891 bool RosenRenderContext::CreateThumbnailPixelMapAsyncTask(
1892     bool needScale, std::function<void(const RefPtr<PixelMap>)>&& callback)
1893 {
1894     CHECK_NULL_RETURN(rsNode_, false);
1895     std::shared_ptr<DrawDragThumbnailCallback> thumbnailCallback = std::make_shared<DrawDragThumbnailCallback>();
1896     CHECK_NULL_RETURN(thumbnailCallback, false);
1897     thumbnailCallback->callback_ = std::move(callback);
1898     float scaleX = 1.0f;
1899     float scaleY = 1.0f;
1900     if (needScale) {
1901         UpdateThumbnailPixelMapScale(scaleX, scaleY);
1902     }
1903     AddRsNodeForCapture();
1904     return RSInterfaces::GetInstance().TakeSurfaceCaptureForUI(rsNode_, thumbnailCallback, scaleX, scaleY, true);
1905 }
1906 
UpdateThumbnailPixelMapScale(float & scaleX,float & scaleY)1907 void RosenRenderContext::UpdateThumbnailPixelMapScale(float& scaleX, float& scaleY)
1908 {
1909     CHECK_NULL_VOID(rsNode_);
1910     auto scale = rsNode_->GetStagingProperties().GetScale();
1911     auto frameNode = GetHost();
1912     CHECK_NULL_VOID(frameNode);
1913     auto context = frameNode->GetRenderContext();
1914     CHECK_NULL_VOID(context);
1915     auto parent = frameNode->GetAncestorNodeOfFrame(true);
1916     while (parent) {
1917         auto parentRenderContext = parent->GetRenderContext();
1918         CHECK_NULL_VOID(parentRenderContext);
1919         auto parentScale = parentRenderContext->GetTransformScale();
1920         if (parentScale) {
1921             scale[0] *= parentScale.value().x;
1922             scale[1] *= parentScale.value().y;
1923         }
1924         parent = parent->GetAncestorNodeOfFrame(true);
1925     }
1926     scaleX = scale[0];
1927     scaleY = scale[1];
1928 }
1929 
GetBitmap(RSBitmap & bitmap,std::shared_ptr<RSDrawCmdList> drawCmdList)1930 bool RosenRenderContext::GetBitmap(RSBitmap& bitmap, std::shared_ptr<RSDrawCmdList> drawCmdList)
1931 {
1932     if (RSUIDirector::GetHybridRenderSwitch(Rosen::ComponentEnableSwitch::CANVAS)) {
1933         auto rsCanvasNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasNode>(rsNode_);
1934         if (!rsCanvasNode || !rsCanvasNode->IsHybridRenderCanvas()) {
1935             return false;
1936         }
1937         return rsCanvasNode->GetBitmap(bitmap, drawCmdList);
1938     }
1939     auto rsCanvasDrawingNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasDrawingNode>(rsNode_);
1940     if (!rsCanvasDrawingNode) {
1941         return false;
1942     }
1943     return rsCanvasDrawingNode->GetBitmap(bitmap, drawCmdList);
1944 }
1945 
GetPixelMap(const std::shared_ptr<Media::PixelMap> & pixelMap,std::shared_ptr<RSDrawCmdList> drawCmdList,Rosen::Drawing::Rect * rect)1946 bool RosenRenderContext::GetPixelMap(const std::shared_ptr<Media::PixelMap>& pixelMap,
1947     std::shared_ptr<RSDrawCmdList> drawCmdList, Rosen::Drawing::Rect* rect)
1948 {
1949     if (RSUIDirector::GetHybridRenderSwitch(Rosen::ComponentEnableSwitch::CANVAS)) {
1950         auto rsCanvasNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasNode>(rsNode_);
1951         if (!rsCanvasNode || !rsCanvasNode->IsHybridRenderCanvas()) {
1952             return false;
1953         }
1954         return rsCanvasNode->GetPixelmap(pixelMap, drawCmdList, rect);
1955     }
1956     auto rsCanvasDrawingNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasDrawingNode>(rsNode_);
1957     if (!rsCanvasDrawingNode) {
1958         return false;
1959     }
1960     return rsCanvasDrawingNode->GetPixelmap(pixelMap, drawCmdList, rect);
1961 }
1962 
1963 template<typename ModifierName, auto Setter, typename T>
AddOrUpdateModifier(std::shared_ptr<ModifierName> & modifier,const T & value)1964 void RosenRenderContext::AddOrUpdateModifier(std::shared_ptr<ModifierName>& modifier, const T& value)
1965 {
1966     if (modifier != nullptr) {
1967         (*modifier.*Setter)(value);
1968     } else {
1969         modifier = std::make_shared<ModifierName>();
1970         (*modifier.*Setter)(value);
1971         AddModifier(modifier);
1972     }
1973 }
1974 
SetRSUIContext(PipelineContext * context)1975 void RosenRenderContext::SetRSUIContext(PipelineContext* context)
1976 {
1977     CHECK_NULL_VOID(context);
1978     auto window = context->GetWindow();
1979     CHECK_NULL_VOID(window);
1980     auto rsUIDirector = window->GetRSUIDirector();
1981     CHECK_NULL_VOID(rsUIDirector);
1982     auto rsUIContext = rsUIDirector->GetRSUIContext();
1983     CHECK_NULL_VOID(rsUIContext);
1984     auto rsNode = GetRSNode();
1985     CHECK_NULL_VOID(rsNode);
1986     rsNode->SetRSUIContext(rsUIContext);
1987 }
1988 
OnTransformScaleUpdate(const VectorF & scale)1989 void RosenRenderContext::OnTransformScaleUpdate(const VectorF& scale)
1990 {
1991     CHECK_NULL_VOID(rsNode_);
1992     auto curScale = rsNode_->GetStagingProperties().GetScale();
1993     hasScales_ = !NearEqual(curScale, Vector2f(1.0f, 1.0f)) && !NearEqual(scale, VectorF(1.0f, 1.0f));
1994     if (AnimationUtils::IsImplicitAnimationOpen() && scaleXYUserModifier_ && GetHost()) {
1995         auto preScale = scaleXYUserModifier_->GetScale();
1996         if (!(NearEqual(preScale[0], scale.x) && NearEqual(preScale[1], scale.y))) {
1997             auto host = GetHost();
1998             ACE_SCOPED_TRACE("scale from (%f, %f) to (%f, %f), id:%d, tag:%s", preScale[0], preScale[1], scale.x,
1999                 scale.y, host->GetId(), host->GetTag().c_str());
2000         }
2001     }
2002     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetScale,
2003         Rosen::Vector2f>(scaleXYUserModifier_, { scale.x, scale.y });
2004     NotifyHostTransformUpdated();
2005     RequestNextFrame();
2006 }
2007 
MarshallTranslate(const TranslateOptions & translate)2008 Vector3F RosenRenderContext::MarshallTranslate(const TranslateOptions& translate)
2009 {
2010     float xValue = 0.0f;
2011     float yValue = 0.0f;
2012     if (translate.x.Unit() == DimensionUnit::PERCENT || translate.y.Unit() == DimensionUnit::PERCENT) {
2013         auto rect = GetPaintRectWithoutTransform();
2014         if (rect.IsEmpty()) {
2015             // size is not determined yet
2016             return Vector3F();
2017         }
2018         xValue = translate.x.ConvertToPxWithSize(rect.Width());
2019         yValue = translate.y.ConvertToPxWithSize(rect.Height());
2020     } else {
2021         xValue = translate.x.ConvertToPx();
2022         yValue = translate.y.ConvertToPx();
2023     }
2024     // translateZ doesn't support percentage
2025     float zValue = translate.z.ConvertToPx();
2026     return Vector3F(xValue, yValue, zValue);
2027 }
2028 
OnTransformTranslateUpdate(const TranslateOptions & translate)2029 void RosenRenderContext::OnTransformTranslateUpdate(const TranslateOptions& translate)
2030 {
2031     CHECK_NULL_VOID(rsNode_);
2032     auto translateVec = MarshallTranslate(translate);
2033     auto changed = true;
2034     Rosen::Vector2f preTranslate;
2035     if (translateXYUserModifier_) {
2036         preTranslate = translateXYUserModifier_->GetTranslate();
2037         changed = !NearEqual(preTranslate[0], translateVec.x) || !NearEqual(preTranslate[1], translateVec.y);
2038     }
2039     if (AnimationUtils::IsImplicitAnimationOpen() && translateXYUserModifier_ && GetHost()) {
2040         if (!(NearEqual(preTranslate[0], translateVec.x) && NearEqual(preTranslate[1], translateVec.y))) {
2041             auto host = GetHost();
2042             ACE_SCOPED_TRACE("translate from (%f, %f) to (%f, %f), id:%d, tag:%s", preTranslate[0], preTranslate[1],
2043                 translateVec.x, translateVec.y, host->GetId(), host->GetTag().c_str());
2044         }
2045     }
2046     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetTranslate,
2047         Rosen::Vector2f>(translateXYUserModifier_, { translateVec.x, translateVec.y });
2048     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2049         &Rosen::ModifierNG::RSTransformModifier::SetTranslateZ, float>(translateZUserModifier_, translateVec.z);
2050     ElementRegister::GetInstance()->ReSyncGeometryTransition(GetHost());
2051     NotifyHostTransformUpdated(changed);
2052     RequestNextFrame();
2053 }
2054 
OnTransformRotateUpdate(const Vector5F & rotate)2055 void RosenRenderContext::OnTransformRotateUpdate(const Vector5F& rotate)
2056 {
2057     CHECK_NULL_VOID(rsNode_);
2058     float norm = std::sqrt(std::pow(rotate.x, 2) + std::pow(rotate.y, 2) + std::pow(rotate.z, 2));
2059     if (NearZero(norm)) {
2060         norm = 1.0f;
2061     }
2062     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotationX,
2063         float>(rotationXUserModifier_, -rotate.w * rotate.x / norm);
2064     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotationY,
2065         float>(rotationYUserModifier_, -rotate.w * rotate.y / norm);
2066     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotation,
2067         float>(rotationZUserModifier_, rotate.w * rotate.z / norm);
2068     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2069         &Rosen::ModifierNG::RSTransformModifier::SetCameraDistance, float>(cameraDistanceUserModifier_, rotate.v);
2070     NotifyHostTransformUpdated();
2071     RequestNextFrame();
2072 }
2073 
OnTransformRotateAngleUpdate(const Vector4F & rotate)2074 void RosenRenderContext::OnTransformRotateAngleUpdate(const Vector4F& rotate)
2075 {
2076     CHECK_NULL_VOID(rsNode_);
2077     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotationX,
2078         float>(rotationXUserModifier_, -rotate.x);
2079     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotationY,
2080         float>(rotationYUserModifier_, -rotate.y);
2081     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotation,
2082         float>(rotationZUserModifier_, rotate.z);
2083     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2084         &Rosen::ModifierNG::RSTransformModifier::SetCameraDistance, float>(cameraDistanceUserModifier_, rotate.w);
2085     NotifyHostTransformUpdated();
2086     RequestNextFrame();
2087 }
2088 
OnTransformCenterUpdate(const DimensionOffset & center)2089 void RosenRenderContext::OnTransformCenterUpdate(const DimensionOffset& center)
2090 {
2091     RectF rect = GetPaintRectWithoutTransform();
2092     if (!RectIsNull()) {
2093         float xPivot = ConvertDimensionToScaleBySize(center.GetX(), rect.Width());
2094         float yPivot = ConvertDimensionToScaleBySize(center.GetY(), rect.Height());
2095         float zPivot = 0.0f;
2096         auto& z = center.GetZ();
2097         if (z.has_value()) {
2098             zPivot = static_cast<float>(z.value().ConvertToVp());
2099         }
2100         SetPivot(xPivot, yPivot, zPivot);
2101         NotifyHostTransformUpdated();
2102     }
2103     RequestNextFrame();
2104 }
2105 
OnTransformMatrixUpdate(const Matrix4 & matrix)2106 void RosenRenderContext::OnTransformMatrixUpdate(const Matrix4& matrix)
2107 {
2108     CHECK_NULL_VOID(rsNode_);
2109     DecomposedTransform transform;
2110     if (!TransformUtil::DecomposeTransform(transform, matrix)) {
2111         // fallback to basic matrix decompose
2112         Rosen::Vector2f xyTranslateValue { static_cast<float>(matrix.Get(0, 3)), static_cast<float>(matrix.Get(1, 3)) };
2113         Rosen::Vector2f scaleValue { 0.0f, 0.0f };
2114         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2115             &Rosen::ModifierNG::RSTransformModifier::SetTranslate, Rosen::Vector2f>(
2116             transformModifier_, xyTranslateValue);
2117         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetScale,
2118             Rosen::Vector2f>(transformModifier_, scaleValue);
2119     } else {
2120         Rosen::Vector4f perspectiveValue { transform.perspective[0], transform.perspective[1], 0.0f, 1.0f };
2121         Rosen::Vector2f xyTranslateValue { transform.translate[0], transform.translate[1] };
2122         Rosen::Quaternion quaternion { static_cast<float>(transform.quaternion.GetX()),
2123             static_cast<float>(transform.quaternion.GetY()), static_cast<float>(transform.quaternion.GetZ()),
2124             static_cast<float>(transform.quaternion.GetW()) };
2125         Rosen::Vector2f xyScaleValue { transform.scale[0], transform.scale[1] };
2126         Rosen::Vector3f skewValue { transform.skew[0], transform.skew[1], 0.0f };
2127         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetPersp,
2128             Rosen::Vector4f>(transformModifier_, perspectiveValue);
2129         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2130             &Rosen::ModifierNG::RSTransformModifier::SetTranslate, Rosen::Vector2f>(
2131             transformModifier_, xyTranslateValue);
2132         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetScale,
2133             Rosen::Vector2f>(transformModifier_, xyScaleValue);
2134         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetSkew,
2135             Rosen::Vector3f>(transformModifier_, skewValue);
2136         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2137             &Rosen::ModifierNG::RSTransformModifier::SetQuaternion, Rosen::Quaternion>(transformModifier_, quaternion);
2138     }
2139     NotifyHostTransformUpdated();
2140     RequestNextFrame();
2141 }
2142 
OnTransform3DMatrixUpdate(const Matrix4 & matrix)2143 void RosenRenderContext::OnTransform3DMatrixUpdate(const Matrix4& matrix)
2144 {
2145     CHECK_NULL_VOID(rsNode_);
2146     DecomposedTransform transform;
2147     if (!TransformUtil::DecomposeTransform(transform, matrix)) {
2148         // fallback to basic matrix decompose
2149         Rosen::Vector2f xyTranslateValue { static_cast<float>(matrix.Get(INDEX_0, INDEX_3)),
2150             static_cast<float>(matrix.Get(INDEX_1, INDEX_3)) };
2151         Rosen::Vector2f scaleValue { FLOAT_ZERO, FLOAT_ZERO };
2152         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2153             &Rosen::ModifierNG::RSTransformModifier::SetTranslate, Rosen::Vector2f>(
2154             transformModifier_, xyTranslateValue);
2155         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetScale,
2156             Rosen::Vector2f>(transformModifier_, scaleValue);
2157     } else {
2158         Rosen::Vector4f perspectiveValue { transform.perspective[0], transform.perspective[1],
2159             transform.perspective[INDEX_2], transform.perspective[INDEX_3] };
2160         Rosen::Vector2f xyTranslateValue { transform.translate[0], transform.translate[1] };
2161         Rosen::Quaternion quaternion { static_cast<float>(transform.quaternion.GetX()),
2162             static_cast<float>(transform.quaternion.GetY()), static_cast<float>(transform.quaternion.GetZ()),
2163             static_cast<float>(transform.quaternion.GetW()) };
2164         Rosen::Vector2f xyScaleValue { transform.scale[0], transform.scale[1] };
2165         Rosen::Vector3f skewValue { transform.skew[0], transform.skew[1], transform.skew[INDEX_2] };
2166 
2167         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetPersp,
2168             Rosen::Vector4f>(transformModifier_, perspectiveValue);
2169         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2170             &Rosen::ModifierNG::RSTransformModifier::SetTranslate, Rosen::Vector2f>(
2171             transformModifier_, xyTranslateValue);
2172         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2173             &Rosen::ModifierNG::RSTransformModifier::SetTranslateZ, float>(
2174             transformModifier_, transform.translate[INDEX_2]);
2175         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetScale,
2176             Rosen::Vector2f>(transformModifier_, xyScaleValue);
2177         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2178             &Rosen::ModifierNG::RSTransformModifier::SetScaleZ, float>(transformModifier_, transform.scale[INDEX_2]);
2179         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetSkew,
2180             Rosen::Vector3f>(transformModifier_, skewValue);
2181         AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
2182             &Rosen::ModifierNG::RSTransformModifier::SetQuaternion, Rosen::Quaternion>(transformModifier_, quaternion);
2183     }
2184     NotifyHostTransformUpdated();
2185     RequestNextFrame();
2186 }
2187 
2188 RectF gRect;
2189 
Degree2Radian(int32_t degree)2190 double Degree2Radian(int32_t degree)
2191 {
2192     const float pi = 3.14159265;
2193     degree = degree % FULL_ROTATION;
2194     if (degree < 0) {
2195         degree += FULL_ROTATION;
2196     }
2197     return degree * pi / STRAIGHT_ANGLE;
2198 }
2199 
SetCorner(double & x,double & y,double width,double height,int32_t degree)2200 void SetCorner(double& x, double& y, double width, double height, int32_t degree)
2201 {
2202     if (degree == RIGHT_ANGLE) {
2203         x = 0;
2204         y = height;
2205     } else if (degree == STRAIGHT_ANGLE) {
2206         x = width;
2207         y = height;
2208     } else if (degree == REFLEX_ANGLE) {
2209         x = width;
2210         y = 0;
2211     }
2212 }
2213 
SkewRect(float sx,float sy,RectF & rect)2214 void SkewRect(float sx, float sy, RectF& rect)
2215 {
2216     auto left = rect.Left();
2217     auto right = rect.Right();
2218     auto top = rect.Top();
2219     auto bottom = rect.Bottom();
2220 
2221     auto leftAfterSkew = sx > 0 ? left + sx * top : left + sx * bottom;
2222     auto rightAfterSkew = sx > 0 ? right + sx * bottom : right + sx * top;
2223     auto topAfterSkew = sy > 0 ? top + sy * left : top + sy * right;
2224     auto bottomAfterSkew = sy > 0 ? bottom + sy * right : bottom + sy * left;
2225 
2226     rect.SetLeft(leftAfterSkew);
2227     rect.SetWidth(rightAfterSkew - leftAfterSkew);
2228     rect.SetTop(topAfterSkew);
2229     rect.SetHeight(bottomAfterSkew - topAfterSkew);
2230 }
2231 
PerspectiveRect(float px,float py,RectF & rect)2232 void PerspectiveRect(float px, float py, RectF& rect)
2233 {
2234     auto left = rect.Left();
2235     auto right = rect.Right();
2236     auto top = rect.Top();
2237     auto bottom = rect.Bottom();
2238 
2239     auto leftAfterSkew = Infinity<double>();
2240     auto rightAfterSkew = -Infinity<double>();
2241     auto topAfterSkew = Infinity<double>();
2242     auto bottomAfterSkew = -Infinity<double>();
2243 
2244     double xValues[] = { left, right };
2245     double yValues[] = { top, bottom };
2246 
2247     for (uint32_t i = 0; i < 2; i++) {
2248         for (uint32_t j = 0; j < 2; j++) {
2249             double perspectiveValue = px * xValues[i] + py * yValues[j] + 1;
2250             if (NearZero(perspectiveValue)) {
2251                 return;
2252             }
2253             leftAfterSkew = std::min(leftAfterSkew, xValues[i] / perspectiveValue);
2254             rightAfterSkew = std::max(rightAfterSkew, xValues[i] / perspectiveValue);
2255             topAfterSkew = std::min(topAfterSkew, yValues[i] / perspectiveValue);
2256             bottomAfterSkew = std::max(bottomAfterSkew, yValues[i] / perspectiveValue);
2257         }
2258     }
2259 
2260     rect.SetLeft(leftAfterSkew);
2261     rect.SetWidth(rightAfterSkew - leftAfterSkew);
2262     rect.SetTop(topAfterSkew);
2263     rect.SetHeight(bottomAfterSkew - topAfterSkew);
2264 }
2265 
SkewPoint(float sx,float sy,PointF & point)2266 void SkewPoint(float sx, float sy, PointF& point)
2267 {
2268     auto x = point.GetX();
2269     auto y = point.GetY();
2270 
2271     point.SetX(x + y * sx);
2272     point.SetY(y + x * sy);
2273 }
2274 
GetPaintRectWithTransform()2275 RectF RosenRenderContext::GetPaintRectWithTransform()
2276 {
2277     RectF rect;
2278 
2279     CHECK_NULL_RETURN(rsNode_, rect);
2280     rect = GetPaintRectWithoutTransform();
2281     // when the width and height of rect is -1, the func SkewRect will change to 1
2282     if (ShouldSkipAffineTransformation(rsNode_) && rect.Width() != -1 && rect.Height() != -1) {
2283         gRect = rect;
2284         return rect;
2285     }
2286     auto translate = rsNode_->GetStagingProperties().GetTranslate();
2287     auto skew = rsNode_->GetStagingProperties().GetSkew();
2288     auto perspective = rsNode_->GetStagingProperties().GetPersp();
2289     auto scale = rsNode_->GetStagingProperties().GetScale();
2290     auto center = rsNode_->GetStagingProperties().GetPivot();
2291     auto degree = rsNode_->GetStagingProperties().GetRotation();
2292     // calculate new pos.
2293     auto centOffset = OffsetF(center[0] * rect.Width(), center[1] * rect.Height());
2294     auto centerPos = rect.GetOffset() + centOffset;
2295     auto newPos = centerPos - OffsetF(centOffset.GetX() * scale[0], centOffset.GetY() * scale[1]);
2296     newPos = newPos + OffsetF(translate[0], translate[1]);
2297     rect.SetOffset(newPos);
2298     // calculate new size.
2299     auto oldSize = rect.GetSize();
2300     auto newSize = SizeF(oldSize.Width() * scale[0], oldSize.Height() * scale[1]);
2301     rect.SetSize(newSize);
2302     // calculate skew
2303     SkewRect(skew[0], skew[1], rect);
2304     // calculate rotate
2305     degree = static_cast<int32_t>(degree) % FULL_ROTATION;
2306     auto radian = Degree2Radian(degree);
2307     if (degree != 0) {
2308         auto newRect = GetPaintRectWithoutTransform();
2309         double leftX = 0.0;
2310         double leftY = 0.0;
2311         degree = degree < 0 ? degree + FULL_ROTATION : degree;
2312         SetCorner(leftX, leftY, oldSize.Width(), oldSize.Height(), degree);
2313         double centerX = oldSize.Width() * center[0];
2314         double centerY = oldSize.Height() * center[1];
2315         auto tmp = leftX;
2316         leftX = (leftX - centerX) * cos(-1 * radian) + (leftY - centerY) * sin(-1 * radian);
2317         leftY = -1 * (tmp - centerX) * sin(-1 * radian) + (leftY - centerY) * cos(-1 * radian);
2318         leftX += newRect.GetOffset().GetX() + centerX;
2319         leftY += newRect.GetOffset().GetY() + centerY;
2320         auto offset = OffsetF(leftX + translate[0], leftY + translate[1]);
2321         rect.SetOffset(offset);
2322         if (degree == STRAIGHT_ANGLE) {
2323             newSize = SizeF(oldSize.Width() * scale[0], oldSize.Height() * scale[1]);
2324         } else {
2325             newSize = SizeF(oldSize.Height() * scale[1], oldSize.Width() * scale[0]);
2326         }
2327         rect.SetSize(newSize);
2328 
2329         // calculate perspective
2330         PerspectiveRect(perspective[0], perspective[1], rect);
2331     }
2332     gRect = rect;
2333     return rect;
2334 }
2335 
GetPaintRectWithTranslate()2336 std::pair<RectF, bool> RosenRenderContext::GetPaintRectWithTranslate()
2337 {
2338     RectF rect;
2339     bool error = hasScales_;
2340     CHECK_NULL_RETURN(rsNode_, std::make_pair(rect, error));
2341     if (rsNode_->GetStagingProperties().GetRotation()) {
2342         return std::make_pair(RectF(0, 0, -1, -1), error);
2343     }
2344     rect = GetPaintRectWithoutTransform();
2345     if (ShouldSkipAffineTransformation(rsNode_)) {
2346         return std::make_pair(rect, error);
2347     }
2348     auto translate = rsNode_->GetStagingProperties().GetTranslate();
2349     rect.SetOffset(rect.GetOffset() + OffsetF(translate[0], translate[1]));
2350     return std::make_pair(rect, error);
2351 }
2352 
GetRevertMatrix()2353 Matrix4 RosenRenderContext::GetRevertMatrix()
2354 {
2355     CHECK_NULL_RETURN(rsNode_, {});
2356     if (ShouldSkipAffineTransformation(rsNode_)) {
2357         return Matrix4();
2358     }
2359     auto center = rsNode_->GetStagingProperties().GetPivot();
2360     Matrix4 rotateMat;
2361     if (transformModifier_ && !transformModifier_->GetQuaternion().IsIdentity()) {
2362         auto quaternionValue = transformModifier_->GetQuaternion();
2363         // 2: parameter index, 3: parameter index
2364         rotateMat =
2365             Matrix4::QuaternionToMatrix(quaternionValue[0], quaternionValue[1], quaternionValue[2], quaternionValue[3]);
2366     } else {
2367         int32_t degree = rsNode_->GetStagingProperties().GetRotation();
2368         if (rsNode_->GetType() == RSUINodeType::DISPLAY_NODE && degree != 0) {
2369             degree = 0;
2370             return Matrix4();
2371         }
2372         rotateMat = Matrix4::CreateRotate(degree, 0, 0, 1);
2373     }
2374 
2375     auto translate = rsNode_->GetStagingProperties().GetTranslate();
2376     auto skew = rsNode_->GetStagingProperties().GetSkew();
2377     auto scale = rsNode_->GetStagingProperties().GetScale();
2378     auto perspective = rsNode_->GetStagingProperties().GetPersp();
2379 
2380     RectF rect = GetPaintRectWithoutTransform();
2381     auto centOffset = OffsetF(center[0] * rect.Width(), center[1] * rect.Height());
2382     auto centerPos = rect.GetOffset() + centOffset;
2383 
2384     auto perspectiveMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2385                           Matrix4::CreateFactorPerspective(perspective[0], perspective[1]) *
2386                           Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2387     auto translateMat = Matrix4::CreateTranslate(translate[0], translate[1], 0);
2388     auto rotationMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) * rotateMat *
2389                        Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2390     auto skewMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2391                    Matrix4::CreateFactorSkew(skew[0], skew[1]) *
2392                    Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2393     auto scaleMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2394                     Matrix4::CreateScale(scale[0], scale[1], 1) *
2395                     Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2396 
2397     return Matrix4::Invert(perspectiveMat * translateMat * rotationMat * skewMat * scaleMat);
2398 }
2399 
GetMatrix()2400 Matrix4 RosenRenderContext::GetMatrix()
2401 {
2402     CHECK_NULL_RETURN(rsNode_, {});
2403     if (ShouldSkipAffineTransformation(rsNode_)) {
2404         return Matrix4();
2405     }
2406     auto center = rsNode_->GetStagingProperties().GetPivot();
2407     int32_t degree = rsNode_->GetStagingProperties().GetRotation();
2408     if (rsNode_->GetType() == RSUINodeType::DISPLAY_NODE && degree != 0) {
2409         degree = 0;
2410         return Matrix4();
2411     }
2412 
2413     auto translate = rsNode_->GetStagingProperties().GetTranslate();
2414     auto skew = rsNode_->GetStagingProperties().GetSkew();
2415     auto scale = rsNode_->GetStagingProperties().GetScale();
2416 
2417     RectF rect = GetPaintRectWithoutTransform();
2418     auto centOffset = OffsetF(center[0] * rect.Width(), center[1] * rect.Height());
2419     auto centerPos = rect.GetOffset() + centOffset;
2420 
2421     auto translateMat = Matrix4::CreateTranslate(translate[0], translate[1], 0);
2422     auto rotationMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2423                        Matrix4::CreateRotate(degree, 0, 0, 1) *
2424                        Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2425     auto skewMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2426                    Matrix4::CreateFactorSkew(skew[0], skew[1]) *
2427                    Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2428     auto scaleMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2429                     Matrix4::CreateScale(scale[0], scale[1], 1) *
2430                     Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2431 
2432     return translateMat * rotationMat * skewMat * scaleMat;
2433 }
2434 
2435 // only for GetPositionToXXXWithTransform in FrameNode.
2436 // contains rotate and perspective matrix set by tranform.
GetMatrixWithTransformRotate()2437 Matrix4 RosenRenderContext::GetMatrixWithTransformRotate()
2438 {
2439     CHECK_NULL_RETURN(rsNode_, {});
2440     if (ShouldSkipAffineTransformation(rsNode_)) {
2441         return Matrix4();
2442     }
2443     auto center = rsNode_->GetStagingProperties().GetPivot();
2444     Matrix4 rotateMat;
2445 
2446     if (transformModifier_ && !transformModifier_->GetQuaternion().IsIdentity()) {
2447         auto quaternionValue = transformModifier_->GetQuaternion();
2448         // 2: parameter index, 3: parameter index
2449         rotateMat =
2450             Matrix4::QuaternionToMatrix(quaternionValue[0], quaternionValue[1], quaternionValue[2], quaternionValue[3]);
2451     } else {
2452         int32_t degree = rsNode_->GetStagingProperties().GetRotation();
2453         if (rsNode_->GetType() == RSUINodeType::DISPLAY_NODE && degree != 0) {
2454             degree = 0;
2455             return Matrix4();
2456         }
2457         rotateMat = Matrix4::CreateRotate(degree, 0, 0, 1);
2458     }
2459 
2460     auto translate = rsNode_->GetStagingProperties().GetTranslate();
2461     auto skew = rsNode_->GetStagingProperties().GetSkew();
2462     auto scale = rsNode_->GetStagingProperties().GetScale();
2463     auto perspective = rsNode_->GetStagingProperties().GetPersp();
2464 
2465     RectF rect = GetPaintRectWithoutTransform();
2466     auto centOffset = OffsetF(center[0] * rect.Width(), center[1] * rect.Height());
2467     auto centerPos = rect.GetOffset() + centOffset;
2468 
2469     auto perspectiveMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2470                           Matrix4::CreateFactorPerspective(perspective[0], perspective[1]) *
2471                           Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2472     auto translateMat = Matrix4::CreateTranslate(translate[0], translate[1], 0);
2473     auto rotationMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) * rotateMat *
2474                        Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2475     auto skewMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2476                    Matrix4::CreateFactorSkew(skew[0], skew[1]) *
2477                    Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2478     auto scaleMat = Matrix4::CreateTranslate(centerPos.GetX(), centerPos.GetY(), 0) *
2479                     Matrix4::CreateScale(scale[0], scale[1], 1) *
2480                     Matrix4::CreateTranslate(-centerPos.GetX(), -centerPos.GetY(), 0);
2481 
2482     return perspectiveMat * translateMat * rotationMat * skewMat * scaleMat;
2483 }
2484 
GetLocalTransformMatrix()2485 Matrix4 RosenRenderContext::GetLocalTransformMatrix()
2486 {
2487     auto invertMat = GetRevertMatrix();
2488     RectF rect = GetPaintRectWithoutTransform();
2489     auto transformMat = Matrix4::CreateTranslate(-rect.GetOffset().GetX(), -rect.GetOffset().GetY(), 0) * invertMat;
2490     return transformMat;
2491 }
2492 
GetPointWithRevert(PointF & point)2493 void RosenRenderContext::GetPointWithRevert(PointF& point)
2494 {
2495     auto invertMat = GetRevertMatrix();
2496     Point tmp(point.GetX(), point.GetY());
2497     auto invertPoint = invertMat * tmp;
2498     point.SetX(invertPoint.GetX());
2499     point.SetY(invertPoint.GetY());
2500 }
2501 
GetPointTransform(PointF & point)2502 void RosenRenderContext::GetPointTransform(PointF& point)
2503 {
2504     auto transformMat = GetMatrix();
2505     Point tmp(point.GetX(), point.GetY());
2506     auto transformPoint = transformMat * tmp;
2507     point.SetX(transformPoint.GetX());
2508     point.SetY(transformPoint.GetY());
2509 }
2510 
2511 // only for GetPositionToXXXWithTransform in FrameNode
GetPointTransformRotate(PointF & point)2512 void RosenRenderContext::GetPointTransformRotate(PointF& point)
2513 {
2514     auto transformMat = GetMatrixWithTransformRotate();
2515     Point tmp(point.GetX(), point.GetY());
2516     auto transformPoint = transformMat * tmp;
2517     point.SetX(transformPoint.GetX());
2518     point.SetY(transformPoint.GetY());
2519 }
2520 
GetPointWithTransform(PointF & point)2521 void RosenRenderContext::GetPointWithTransform(PointF& point)
2522 {
2523     CHECK_NULL_VOID(rsNode_);
2524     if (ShouldSkipAffineTransformation(rsNode_)) {
2525         return;
2526     }
2527     auto skew = rsNode_->GetStagingProperties().GetSkew();
2528     auto scale = rsNode_->GetStagingProperties().GetScale();
2529     point = PointF(point.GetX() / scale[0], point.GetY() / scale[1]);
2530     SkewPoint(skew[0], skew[1], point);
2531     int32_t degree = rsNode_->GetStagingProperties().GetRotation();
2532     if (degree != 0 && rsNode_->GetType() == RSUINodeType::DISPLAY_NODE) {
2533         degree = 0;
2534     }
2535     degree = degree % FULL_ROTATION;
2536     if (degree != 0) {
2537         auto translate = rsNode_->GetStagingProperties().GetTranslate();
2538         auto perspective = rsNode_->GetStagingProperties().GetPersp();
2539         RectF rect = GetPaintRectWithoutTransform();
2540         auto center = rsNode_->GetStagingProperties().GetPivot();
2541         auto radian = Degree2Radian(degree);
2542         point = point + gRect.GetOffset();
2543         point = point - OffsetF(translate[0], translate[1]);
2544         auto centOffset = OffsetF(center[0] * gRect.Width(), center[1] * gRect.Height());
2545         auto centerPos = gRect.GetOffset() + centOffset - OffsetF(translate[0], translate[1]);
2546         auto centerX = centerPos.GetX();
2547         auto centerY = centerPos.GetY();
2548 
2549         double currentPointX = (point.GetX() - centerX) * cos(radian) + (point.GetY() - centerY) * sin(radian);
2550         double currentPointY = -1 * (point.GetX() - centerX) * sin(radian) + (point.GetY() - centerY) * cos(radian);
2551         currentPointX += centerX - rect.Left();
2552         currentPointY += centerY - rect.Top();
2553 
2554         double perspectiveValue = perspective[0] * currentPointX + perspective[1] * currentPointY + 1;
2555         if (NearZero(perspectiveValue)) {
2556             point.SetX(currentPointX);
2557             point.SetY(currentPointY);
2558             return;
2559         }
2560 
2561         point.SetX(currentPointX / perspectiveValue);
2562         point.SetY(currentPointY / perspectiveValue);
2563     }
2564 }
2565 
2566 // comparing to frameRect of geometryNode,
2567 // paint rect has position, offset, markAnchor, pixelGridRound and safeArea properties
GetPaintRectWithoutTransform()2568 RectF RosenRenderContext::GetPaintRectWithoutTransform()
2569 {
2570     return paintRect_;
2571 }
2572 
GetPaintRectWithTransformWithoutDegree()2573 RectF RosenRenderContext::GetPaintRectWithTransformWithoutDegree()
2574 {
2575     RectF rect;
2576     CHECK_NULL_RETURN(rsNode_, rect);
2577     rect = GetPaintRectWithoutTransform();
2578     // when the width and height of rect is -1, the func SkewRect will change to 1
2579     if (ShouldSkipAffineTransformation(rsNode_) && rect.Width() != -1 && rect.Height() != -1) {
2580         return rect;
2581     }
2582     auto translate = rsNode_->GetStagingProperties().GetTranslate();
2583     auto skew = rsNode_->GetStagingProperties().GetSkew();
2584     auto perspective = rsNode_->GetStagingProperties().GetPersp();
2585     auto scale = rsNode_->GetStagingProperties().GetScale();
2586     auto center = rsNode_->GetStagingProperties().GetPivot();
2587     auto degree = 0;
2588     auto centOffset = OffsetF(center[0] * rect.Width(), center[1] * rect.Height());
2589     auto centerPos = rect.GetOffset() + centOffset;
2590     auto newPos = centerPos - OffsetF(centOffset.GetX() * scale[0], centOffset.GetY() * scale[1]);
2591     newPos = newPos + OffsetF(translate[0], translate[1]);
2592     rect.SetOffset(newPos);
2593     auto oldSize = rect.GetSize();
2594     auto newSize = SizeF(oldSize.Width() * scale[0], oldSize.Height() * scale[1]);
2595     rect.SetSize(newSize);
2596     SkewRect(skew[0], skew[1], rect);
2597     degree = static_cast<int32_t>(degree) % FULL_ROTATION;
2598     auto radian = Degree2Radian(degree);
2599     if (degree != 0) {
2600         auto newRect = GetPaintRectWithoutTransform();
2601         double leftX = 0;
2602         double leftY = oldSize.Height();
2603         degree = degree < 0 ? degree + FULL_ROTATION : degree;
2604         SetCorner(leftX, leftY, oldSize.Width(), oldSize.Height(), degree);
2605         double centerX = oldSize.Width() * center[0];
2606         double centerY = oldSize.Height() * center[1];
2607         auto tmp = leftX;
2608         leftX = (leftX - centerX) * cos(-1 * radian) + (leftY - centerY) * sin(-1 * radian);
2609         leftY = -1 * (tmp - centerX) * sin(-1 * radian) + (leftY - centerY) * cos(-1 * radian);
2610         leftX += newRect.GetOffset().GetX() + centerX;
2611         leftY += newRect.GetOffset().GetY() + centerY;
2612         auto offset = OffsetF(leftX + translate[0], leftY + translate[1]);
2613         rect.SetOffset(offset);
2614         if (degree == STRAIGHT_ANGLE) {
2615             newSize = SizeF(oldSize.Width() * scale[0], oldSize.Height() * scale[1]);
2616         } else {
2617             newSize = SizeF(oldSize.Height() * scale[1], oldSize.Width() * scale[0]);
2618         }
2619         rect.SetSize(newSize);
2620         PerspectiveRect(perspective[0], perspective[1], rect);
2621     }
2622     gRect = rect;
2623     return rect;
2624 }
2625 
UpdateTranslateInXY(const OffsetF & offset)2626 void RosenRenderContext::UpdateTranslateInXY(const OffsetF& offset)
2627 {
2628     CHECK_NULL_VOID(rsNode_);
2629     auto xValue = offset.GetX();
2630     auto yValue = offset.GetY();
2631     bool changed = true;
2632 
2633     if (translateXYModifier_) {
2634         auto translate = translateXYModifier_->GetTranslate();
2635         changed = !NearEqual(translate[0], xValue) || !NearEqual(translate[1], yValue);
2636         translateXYModifier_->SetTranslate({ xValue, yValue });
2637     } else {
2638         translateXYModifier_ = std::make_shared<Rosen::ModifierNG::RSTransformModifier>();
2639         translateXYModifier_->SetTranslate({ xValue, yValue });
2640         rsNode_->AddModifier(translateXYModifier_);
2641     }
2642     ElementRegister::GetInstance()->ReSyncGeometryTransition(GetHost());
2643     NotifyHostTransformUpdated(changed);
2644 }
2645 
GetShowingTranslateProperty()2646 OffsetF RosenRenderContext::GetShowingTranslateProperty()
2647 {
2648     OffsetF offset;
2649     CHECK_NULL_RETURN(translateXYModifier_, offset);
2650     auto property = std::static_pointer_cast<RSAnimatableProperty<Vector2f>>(
2651         translateXYModifier_->GetProperty(Rosen::ModifierNG::RSPropertyType::TRANSLATE));
2652     CHECK_NULL_RETURN(property, offset);
2653     auto result = property->GetShowingValueAndCancelAnimation();
2654     if (!result) {
2655         return offset;
2656     }
2657     auto translate = property->Get();
2658     offset.SetX(translate[0]);
2659     offset.SetY(translate[1]);
2660     return offset;
2661 }
2662 
CancelTranslateXYAnimation()2663 void RosenRenderContext::CancelTranslateXYAnimation()
2664 {
2665     CHECK_NULL_VOID(translateXYModifier_);
2666     auto property = std::static_pointer_cast<RSAnimatableProperty<Vector2f>>(
2667         translateXYModifier_->GetProperty(Rosen::ModifierNG::RSPropertyType::TRANSLATE));
2668     CHECK_NULL_VOID(property);
2669     property->RequestCancelAnimation();
2670 }
2671 
GetTranslateXYProperty()2672 OffsetF RosenRenderContext::GetTranslateXYProperty()
2673 {
2674     OffsetF offset;
2675     CHECK_NULL_RETURN(translateXYModifier_, offset);
2676     auto property = std::static_pointer_cast<RSAnimatableProperty<Vector2f>>(
2677         translateXYModifier_->GetProperty(Rosen::ModifierNG::RSPropertyType::TRANSLATE));
2678     CHECK_NULL_RETURN(property, offset);
2679     auto translate = property->Get();
2680     offset.SetX(translate[0]);
2681     offset.SetY(translate[1]);
2682     return offset;
2683 }
2684 
NotifyTransitionInner(const SizeF & frameSize,bool isTransitionIn)2685 void RosenRenderContext::NotifyTransitionInner(const SizeF& frameSize, bool isTransitionIn)
2686 {
2687     CHECK_NULL_VOID(rsNode_);
2688     if (propTransitionAppearing_ || propTransitionDisappearing_) {
2689         // old transition
2690         auto& transOptions = isTransitionIn ? propTransitionAppearing_ : propTransitionDisappearing_;
2691         auto effect = GetRSTransitionWithoutType(transOptions, frameSize);
2692         CHECK_NULL_VOID(effect);
2693         SetTransitionPivot(frameSize, isTransitionIn);
2694         // notice that we have been in animateTo, so do not need to use Animation closure to notify transition.
2695         rsNode_->NotifyTransition(effect, isTransitionIn);
2696         return;
2697     }
2698     // add default transition effect on the 'breaking point' of render tree, if no user-defined transition effect
2699     // and triggered in AnimateTo closure.
2700     // Note: this default transition effect will be removed after all transitions finished, implemented in
2701     // OnTransitionInFinish. and OnTransitionOutFinish.
2702     if (isBreakingPoint_ && !transitionEffect_ && AnimationUtils::IsImplicitAnimationOpen()) {
2703         hasDefaultTransition_ = true;
2704         transitionEffect_ = RosenTransitionEffect::CreateDefaultRosenTransitionEffect();
2705         auto rsUIContext = rsNode_->GetRSUIContext();
2706         RSNode::ExecuteWithoutAnimation([this, isTransitionIn]() {
2707                 // transitionIn effects should be initialized as active if is transitionIn.
2708                 transitionEffect_->Attach(Claim(this), isTransitionIn);
2709             }, rsUIContext);
2710     }
2711     NotifyTransition(isTransitionIn);
2712 }
2713 
OpacityAnimation(const AnimationOption & option,double begin,double end)2714 void RosenRenderContext::OpacityAnimation(const AnimationOption& option, double begin, double end)
2715 {
2716     CHECK_NULL_VOID(rsNode_);
2717     AddOrUpdateModifier<Rosen::ModifierNG::RSAlphaModifier, &Rosen::ModifierNG::RSAlphaModifier::SetAlpha, float>(
2718         alphaUserModifier_, begin);
2719     AnimationUtils::Animate(
2720         option,
2721         [this, end]() {
2722             AddOrUpdateModifier<Rosen::ModifierNG::RSAlphaModifier, &Rosen::ModifierNG::RSAlphaModifier::SetAlpha,
2723                 float>(alphaUserModifier_, end);
2724         },
2725         option.GetOnFinishEvent());
2726     MarkNeedDrawNode(begin < 1.0 || end < 1.0);
2727 }
2728 
ScaleAnimation(const AnimationOption & option,double begin,double end)2729 void RosenRenderContext::ScaleAnimation(const AnimationOption& option, double begin, double end)
2730 {
2731     CHECK_NULL_VOID(rsNode_);
2732     SetScale(begin, begin);
2733     AnimationUtils::Animate(
2734         option, [this, end]() { SetScale(end, end); }, option.GetOnFinishEvent());
2735 }
2736 
SetBorderRadius(const BorderRadiusProperty & value)2737 void RosenRenderContext::SetBorderRadius(const BorderRadiusProperty& value)
2738 {
2739     CHECK_NULL_VOID(rsNode_);
2740     auto paintRect = AdjustPaintRect();
2741     if (isDisappearing_ && !paintRect.IsValid()) {
2742         return;
2743     }
2744     double width = paintRect.Width();
2745     Rosen::Vector4f cornerRadius;
2746     cornerRadius.SetValues(static_cast<float>(value.radiusTopLeft.value_or(Dimension()).ConvertToPxWithSize(width)),
2747         static_cast<float>(value.radiusTopRight.value_or(Dimension()).ConvertToPxWithSize(width)),
2748         static_cast<float>(value.radiusBottomRight.value_or(Dimension()).ConvertToPxWithSize(width)),
2749         static_cast<float>(value.radiusBottomLeft.value_or(Dimension()).ConvertToPxWithSize(width)));
2750     rsNode_->SetCornerRadius(cornerRadius);
2751     RequestNextFrame();
2752 }
2753 
OnBorderRadiusUpdate(const BorderRadiusProperty & value)2754 void RosenRenderContext::OnBorderRadiusUpdate(const BorderRadiusProperty& value)
2755 {
2756     CHECK_NULL_VOID(isSynced_);
2757     SetBorderRadius(value);
2758 }
2759 
OnBorderColorUpdate(const BorderColorProperty & value)2760 void RosenRenderContext::OnBorderColorUpdate(const BorderColorProperty& value)
2761 {
2762     SetBorderColor(value);
2763 }
2764 
SetBorderColor(const BorderColorProperty & value)2765 void RosenRenderContext::SetBorderColor(const BorderColorProperty& value)
2766 {
2767     CHECK_NULL_VOID(rsNode_);
2768     rsNode_->SetBorderColor(value.leftColor.value_or(Color::BLACK).GetValue(),
2769         value.topColor.value_or(Color::BLACK).GetValue(), value.rightColor.value_or(Color::BLACK).GetValue(),
2770         value.bottomColor.value_or(Color::BLACK).GetValue());
2771     RequestNextFrame();
2772 }
2773 
SetBorderWidth(const BorderWidthProperty & value)2774 void RosenRenderContext::SetBorderWidth(const BorderWidthProperty& value)
2775 {
2776     CHECK_NULL_VOID(rsNode_);
2777     Rosen::Vector4f cornerBorderWidth;
2778     cornerBorderWidth.SetValues(static_cast<float>((value.leftDimen.value()).ConvertToPx()),
2779         static_cast<float>((value.topDimen.value()).ConvertToPx()),
2780         static_cast<float>((value.rightDimen.value()).ConvertToPx()),
2781         static_cast<float>((value.bottomDimen.value()).ConvertToPx()));
2782     rsNode_->SetBorderWidth(cornerBorderWidth);
2783     borderWidth_ = cornerBorderWidth;
2784     RequestNextFrame();
2785 }
2786 
UpdateBorderWidthF(const BorderWidthPropertyF & value)2787 void RosenRenderContext::UpdateBorderWidthF(const BorderWidthPropertyF& value)
2788 {
2789     CHECK_NULL_VOID(rsNode_);
2790     Rosen::Vector4f cornerBorderWidth;
2791     cornerBorderWidth.SetValues(value.leftDimen.value_or(0), static_cast<float>(value.topDimen.value_or(0)),
2792         static_cast<float>(value.rightDimen.value_or(0)), static_cast<float>(value.bottomDimen.value_or(0)));
2793     rsNode_->SetBorderWidth(cornerBorderWidth);
2794     borderWidth_ = cornerBorderWidth;
2795     RequestNextFrame();
2796 }
2797 
OnBorderStyleUpdate(const BorderStyleProperty & value)2798 void RosenRenderContext::OnBorderStyleUpdate(const BorderStyleProperty& value)
2799 {
2800     SetBorderStyle(value);
2801 }
2802 
SetBorderStyle(const BorderStyleProperty & value)2803 void RosenRenderContext::SetBorderStyle(const BorderStyleProperty& value)
2804 {
2805     CHECK_NULL_VOID(rsNode_);
2806     rsNode_->SetBorderStyle(static_cast<uint32_t>(value.styleLeft.value_or(BorderStyle::SOLID)),
2807         static_cast<uint32_t>(value.styleTop.value_or(BorderStyle::SOLID)),
2808         static_cast<uint32_t>(value.styleRight.value_or(BorderStyle::SOLID)),
2809         static_cast<uint32_t>(value.styleBottom.value_or(BorderStyle::SOLID)));
2810     RequestNextFrame();
2811 }
2812 
OnDashGapUpdate(const BorderWidthProperty & value)2813 void RosenRenderContext::OnDashGapUpdate(const BorderWidthProperty& value)
2814 {
2815     SetDashGap(value);
2816 }
2817 
SetDashGap(const BorderWidthProperty & value)2818 void RosenRenderContext::SetDashGap(const BorderWidthProperty& value)
2819 {
2820     CHECK_NULL_VOID(rsNode_);
2821     Rosen::Vector4f cornerDashGap;
2822     cornerDashGap.SetValues(static_cast<float>((value.leftDimen.value_or(DASH_GEP_WIDTH)).ConvertToPx()),
2823         static_cast<float>((value.topDimen.value_or(DASH_GEP_WIDTH)).ConvertToPx()),
2824         static_cast<float>((value.rightDimen.value_or(DASH_GEP_WIDTH)).ConvertToPx()),
2825         static_cast<float>((value.bottomDimen.value_or(DASH_GEP_WIDTH)).ConvertToPx()));
2826     rsNode_->SetBorderDashGap(cornerDashGap);
2827     RequestNextFrame();
2828 }
2829 
OnDashWidthUpdate(const BorderWidthProperty & value)2830 void RosenRenderContext::OnDashWidthUpdate(const BorderWidthProperty& value)
2831 {
2832     SetDashWidth(value);
2833 }
2834 
SetDashWidth(const BorderWidthProperty & value)2835 void RosenRenderContext::SetDashWidth(const BorderWidthProperty& value)
2836 {
2837     CHECK_NULL_VOID(rsNode_);
2838     Rosen::Vector4f cornerDashWidth;
2839     cornerDashWidth.SetValues(static_cast<float>((value.leftDimen.value_or(DASH_GEP_WIDTH)).ConvertToPx()),
2840         static_cast<float>((value.topDimen.value_or(DASH_GEP_WIDTH)).ConvertToPx()),
2841         static_cast<float>((value.rightDimen.value_or(DASH_GEP_WIDTH)).ConvertToPx()),
2842         static_cast<float>((value.bottomDimen.value_or(DASH_GEP_WIDTH)).ConvertToPx()));
2843     rsNode_->SetBorderDashWidth(cornerDashWidth);
2844     RequestNextFrame();
2845 }
2846 
OnOuterBorderRadiusUpdate(const BorderRadiusProperty & value)2847 void RosenRenderContext::OnOuterBorderRadiusUpdate(const BorderRadiusProperty& value)
2848 {
2849     SetOuterBorderRadius(value);
2850 }
2851 
SetOuterBorderRadius(const BorderRadiusProperty & value)2852 void RosenRenderContext::SetOuterBorderRadius(const BorderRadiusProperty& value)
2853 {
2854     CHECK_NULL_VOID(rsNode_);
2855     auto paintRect = AdjustPaintRect();
2856     if (isDisappearing_ && !paintRect.IsValid()) {
2857         return;
2858     }
2859     double radiusX = paintRect.Width();
2860     Rosen::Vector4f cornerRadius;
2861     cornerRadius.SetValues(
2862         static_cast<float>(value.radiusTopLeft.value_or(Dimension(0.0)).ConvertToPxWithSize(radiusX)),
2863         static_cast<float>(value.radiusTopRight.value_or(Dimension(0.0)).ConvertToPxWithSize(radiusX)),
2864         static_cast<float>(value.radiusBottomRight.value_or(Dimension(0.0)).ConvertToPxWithSize(radiusX)),
2865         static_cast<float>(value.radiusBottomLeft.value_or(Dimension(0.0)).ConvertToPxWithSize(radiusX)));
2866     rsNode_->SetOuterBorderRadius(cornerRadius);
2867     RequestNextFrame();
2868 }
2869 
OnOuterBorderColorUpdate(const BorderColorProperty & value)2870 void RosenRenderContext::OnOuterBorderColorUpdate(const BorderColorProperty& value)
2871 {
2872     SetOuterBorderColor(value);
2873 }
2874 
SetOuterBorderColor(const BorderColorProperty & value)2875 void RosenRenderContext::SetOuterBorderColor(const BorderColorProperty& value)
2876 {
2877     CHECK_NULL_VOID(rsNode_);
2878     Rosen::Vector4<Rosen::RSColor> color(Rosen::RSColor::FromArgbInt(value.leftColor.value_or(Color::BLACK).GetValue()),
2879         Rosen::RSColor::FromArgbInt(value.topColor.value_or(Color::BLACK).GetValue()),
2880         Rosen::RSColor::FromArgbInt(value.rightColor.value_or(Color::BLACK).GetValue()),
2881         Rosen::RSColor::FromArgbInt(value.bottomColor.value_or(Color::BLACK).GetValue()));
2882     rsNode_->SetOuterBorderColor(color);
2883     RequestNextFrame();
2884 }
2885 
OnOuterBorderWidthUpdate(const BorderWidthProperty & value)2886 void RosenRenderContext::OnOuterBorderWidthUpdate(const BorderWidthProperty& value)
2887 {
2888     SetOuterBorderWidth(value);
2889 }
2890 
SetOuterBorderWidth(const BorderWidthProperty & value)2891 void RosenRenderContext::SetOuterBorderWidth(const BorderWidthProperty& value)
2892 {
2893     CHECK_NULL_VOID(rsNode_);
2894     Rosen::Vector4f cornerBorderWidth;
2895     cornerBorderWidth.SetValues(static_cast<float>((value.leftDimen.value_or(Dimension(0.0))).ConvertToPx()),
2896         static_cast<float>((value.topDimen.value_or(Dimension(0.0))).ConvertToPx()),
2897         static_cast<float>((value.rightDimen.value_or(Dimension(0.0))).ConvertToPx()),
2898         static_cast<float>((value.bottomDimen.value_or(Dimension(0.0))).ConvertToPx()));
2899     rsNode_->SetOuterBorderWidth(cornerBorderWidth);
2900     RequestNextFrame();
2901 }
2902 
SetExtraOffset(const std::optional<OffsetF> & offset)2903 void RosenRenderContext::SetExtraOffset(const std::optional<OffsetF>& offset)
2904 {
2905     extraOffset_ = offset;
2906 }
2907 
OnOuterBorderStyleUpdate(const BorderStyleProperty & value)2908 void RosenRenderContext::OnOuterBorderStyleUpdate(const BorderStyleProperty& value)
2909 {
2910     SetOuterBorderStyle(value);
2911 }
2912 
SetOuterBorderStyle(const BorderStyleProperty & value)2913 void RosenRenderContext::SetOuterBorderStyle(const BorderStyleProperty& value)
2914 {
2915     CHECK_NULL_VOID(rsNode_);
2916     Rosen::Vector4<Rosen::BorderStyle> borderStyle(
2917         static_cast<Rosen::BorderStyle>(static_cast<uint32_t>(value.styleLeft.value_or(BorderStyle::SOLID))),
2918         static_cast<Rosen::BorderStyle>(static_cast<uint32_t>(value.styleTop.value_or(BorderStyle::SOLID))),
2919         static_cast<Rosen::BorderStyle>(static_cast<uint32_t>(value.styleRight.value_or(BorderStyle::SOLID))),
2920         static_cast<Rosen::BorderStyle>(static_cast<uint32_t>(value.styleBottom.value_or(BorderStyle::SOLID))));
2921     rsNode_->SetOuterBorderStyle(borderStyle);
2922     RequestNextFrame();
2923 }
2924 
OnAccessibilityFocusUpdate(bool isAccessibilityFocus,const int64_t accessibilityIdForVirtualNode)2925 void RosenRenderContext::OnAccessibilityFocusUpdate(
2926     bool isAccessibilityFocus, const int64_t accessibilityIdForVirtualNode)
2927 {
2928     auto uiNode = GetHost();
2929     CHECK_NULL_VOID(uiNode);
2930     UpdateAccessibilityFocus(isAccessibilityFocus);
2931     if (isAccessibilityFocus) {
2932         PaintAccessibilityFocus();
2933     } else {
2934         ClearAccessibilityFocus();
2935     }
2936 
2937     if (accessibilityIdForVirtualNode == ACCESSIBILITY_FOCUS_WITHOUT_EVENT) {
2938         return;
2939     }
2940 
2941     if (accessibilityIdForVirtualNode == INVALID_PARENT_ID) {
2942         uiNode->OnAccessibilityEvent(isAccessibilityFocus ? AccessibilityEventType::ACCESSIBILITY_FOCUSED
2943                                                           : AccessibilityEventType::ACCESSIBILITY_FOCUS_CLEARED);
2944     } else {
2945         uiNode->OnAccessibilityEventForVirtualNode(isAccessibilityFocus
2946                                                        ? AccessibilityEventType::ACCESSIBILITY_FOCUSED
2947                                                        : AccessibilityEventType::ACCESSIBILITY_FOCUS_CLEARED,
2948             accessibilityIdForVirtualNode);
2949     }
2950 }
2951 
OnAccessibilityFocusRectUpdate(RectT<int32_t> accessibilityFocusRect)2952 void RosenRenderContext::OnAccessibilityFocusRectUpdate(RectT<int32_t> accessibilityFocusRect)
2953 {
2954     auto isAccessibilityFocus = GetAccessibilityFocus().value_or(false);
2955     if (isAccessibilityFocus) {
2956         PaintAccessibilityFocus();
2957     }
2958 }
2959 
GetStatusByEffectTypeAndWindow()2960 bool RosenRenderContext::GetStatusByEffectTypeAndWindow()
2961 {
2962     auto pipeline = GetPipelineContext();
2963     CHECK_NULL_RETURN(pipeline, false);
2964     auto isWindowActivated = pipeline->IsWindowActivated();
2965     auto effectType = GetUseEffectType().value_or(EffectType::DEFAULT);
2966     return effectType == EffectType::WINDOW_EFFECT && !isWindowActivated;
2967 }
2968 
OnUseEffectUpdate(bool useEffect)2969 void RosenRenderContext::OnUseEffectUpdate(bool useEffect)
2970 {
2971     CHECK_NULL_VOID(rsNode_);
2972     if (GetStatusByEffectTypeAndWindow()) {
2973         rsNode_->SetUseEffect(false);
2974     } else {
2975         rsNode_->SetUseEffect(useEffect);
2976     }
2977 }
2978 
OnUseEffectTypeUpdate(EffectType effectType)2979 void RosenRenderContext::OnUseEffectTypeUpdate(EffectType effectType)
2980 {
2981     CHECK_NULL_VOID(rsNode_);
2982     auto effectTypeParam = static_cast<Rosen::UseEffectType>(effectType);
2983     rsNode_->SetUseEffectType(effectTypeParam);
2984     auto useEffect = GetUseEffect().value_or(false);
2985     OnUseEffectUpdate(useEffect);
2986 }
2987 
OnUseShadowBatchingUpdate(bool useShadowBatching)2988 void RosenRenderContext::OnUseShadowBatchingUpdate(bool useShadowBatching)
2989 {
2990     CHECK_NULL_VOID(rsNode_);
2991     rsNode_->SetUseShadowBatching(useShadowBatching);
2992 }
2993 
OnFreezeUpdate(bool isFreezed)2994 void RosenRenderContext::OnFreezeUpdate(bool isFreezed)
2995 {
2996     CHECK_NULL_VOID(rsNode_);
2997     rsNode_->SetFreeze(isFreezed);
2998 }
2999 
PaintAccessibilityFocus()3000 void RosenRenderContext::PaintAccessibilityFocus()
3001 {
3002     CHECK_NULL_VOID(rsNode_);
3003     Dimension focusPaddingVp = Dimension(0.0, DimensionUnit::VP);
3004     constexpr uint32_t ACCESSIBILITY_FOCUS_COLOR = 0xbf39b500;
3005     constexpr double ACCESSIBILITY_FOCUS_WIDTH = 4.0;
3006     constexpr float kAccessibilityMinSize = 1.0f;
3007     double lineWidth = ACCESSIBILITY_FOCUS_WIDTH * PipelineBase::GetCurrentDensity();
3008     Color paintColor(ACCESSIBILITY_FOCUS_COLOR);
3009     Dimension paintWidth(lineWidth, DimensionUnit::PX);
3010     const auto& bounds = rsNode_->GetStagingProperties().GetBounds();
3011     RoundRect frameRect;
3012     double noGreenBorderWidth = (bounds.w_ - (2 * lineWidth)) > 0 ? (bounds.w_ - (2 * lineWidth)) : 0;
3013     double noGreenBorderHeight = (bounds.z_ - (2 * lineWidth)) > 0 ? (bounds.z_ - (2 * lineWidth)) : 0;
3014     frameRect.SetRect(RectF(lineWidth, lineWidth, noGreenBorderHeight, noGreenBorderWidth));
3015     RectT<int32_t> localRect = GetAccessibilityFocusRect().value_or(RectT<int32_t>());
3016     if (localRect != RectT<int32_t>()) {
3017         RectT<int32_t> containerRect;
3018         containerRect.SetRect(0, 0, bounds.z_, bounds.w_);
3019         RectF globalRect = frameRect.GetRect();
3020         auto localRectWidth = localRect.Width() - 2 * lineWidth;
3021         auto localRectHeight = localRect.Height() - 2 * lineWidth;
3022         if (NonPositive(localRectWidth)) {
3023             localRectWidth = kAccessibilityMinSize;
3024         }
3025         if (NonPositive(localRectHeight)) {
3026             localRectHeight = kAccessibilityMinSize;
3027         }
3028         globalRect.SetRect(globalRect.GetX() + localRect.GetX(), globalRect.GetY() + localRect.GetY(),
3029             localRectWidth, localRectHeight);
3030         if (globalRect.IsEmpty()) {
3031             ClearAccessibilityFocus();
3032             return;
3033         }
3034         frameRect.SetRect(globalRect);
3035     }
3036     PaintFocusState(frameRect, focusPaddingVp, paintColor, paintWidth, { true, false });
3037 }
3038 
UpdateAccessibilityRoundRect()3039 void RosenRenderContext::UpdateAccessibilityRoundRect()
3040 {
3041     CHECK_NULL_VOID(accessibilityFocusStateModifier_);
3042     const constexpr double accessibilityFocusWidth = 4.0;
3043     double lineWidth = accessibilityFocusWidth * PipelineBase::GetCurrentDensity();
3044     Dimension paintWidth(lineWidth, DimensionUnit::PX);
3045     Dimension focusPaddingVp = Dimension(0.0, DimensionUnit::VP);
3046 
3047     auto paintWidthPx = static_cast<float>(paintWidth.ConvertToPx());
3048     auto borderPaddingPx = static_cast<float>(focusPaddingVp.ConvertToPx());
3049 
3050     auto node = GetHost();
3051     CHECK_NULL_VOID(node);
3052     if (node->GetTag() == V2::ACCESSIBILITY_FOCUS_PAINT_NODE_TAG) {
3053         auto paintNodePattern = AceType::DynamicCast<AccessibilityFocusPaintNodePattern>(node->GetPattern());
3054         CHECK_NULL_VOID(paintNodePattern);
3055         auto focusNode = paintNodePattern->GetFocusNode().Upgrade();
3056         CHECK_NULL_VOID(focusNode);
3057         auto pipeline = focusNode->GetContextRefPtr();
3058         CHECK_NULL_VOID(pipeline);
3059         auto rect = pipeline->GetRootRect();
3060         std::shared_ptr<Rosen::RectF> drawRect =
3061             std::make_shared<Rosen::RectF>(rect.GetX(), rect.GetY(), rect.Width(), rect.Height());
3062         UpdateDrawRegion(DRAW_REGION_ACCESSIBILITY_FOCUS_MODIFIER_INDEX, drawRect);
3063     }
3064     auto nodeWidth = node->GetGeometryNode()->GetFrameSize().Width();
3065     auto nodeHeight = node->GetGeometryNode()->GetFrameSize().Height();
3066 
3067     double noGreenBorderWidth =
3068         GreatOrEqual(nodeWidth - (FACTOR_TWO * lineWidth), 0.0) ? (nodeWidth - (FACTOR_TWO * lineWidth)) : 0;
3069     double noGreenBorderHeight =
3070         GreatOrEqual(nodeHeight - (FACTOR_TWO * lineWidth), 0.0) ? (nodeHeight - (FACTOR_TWO * lineWidth)) : 0;
3071 
3072     RoundRect frameRect;
3073     std::shared_ptr<FocusStateModifier> modifier = accessibilityFocusStateModifier_;
3074     frameRect.SetRect(RectF(lineWidth - borderPaddingPx - paintWidthPx / FACTOR_TWO,
3075         lineWidth - borderPaddingPx - paintWidthPx / FACTOR_TWO,
3076         noGreenBorderWidth + FACTOR_TWO * borderPaddingPx + paintWidthPx,
3077         noGreenBorderHeight + FACTOR_TWO * borderPaddingPx + paintWidthPx));
3078 
3079     // SetCornerRadius
3080     EdgeF diffRadius = { borderPaddingPx + paintWidthPx / FACTOR_TWO, borderPaddingPx + paintWidthPx / FACTOR_TWO };
3081     auto focusPaintCornerTopLeft = frameRect.GetCornerRadius(RoundRect::CornerPos::TOP_LEFT_POS) + diffRadius;
3082     auto focusPaintCornerTopRight = frameRect.GetCornerRadius(RoundRect::CornerPos::TOP_RIGHT_POS) + diffRadius;
3083     auto focusPaintCornerBottomLeft = frameRect.GetCornerRadius(RoundRect::CornerPos::BOTTOM_LEFT_POS) + diffRadius;
3084     auto focusPaintCornerBottomRight = frameRect.GetCornerRadius(RoundRect::CornerPos::BOTTOM_RIGHT_POS) + diffRadius;
3085 
3086     frameRect.SetCornerRadius(RoundRect::CornerPos::TOP_LEFT_POS, focusPaintCornerTopLeft.x, focusPaintCornerTopLeft.y);
3087     frameRect.SetCornerRadius(
3088         RoundRect::CornerPos::TOP_RIGHT_POS, focusPaintCornerTopRight.x, focusPaintCornerTopRight.y);
3089     frameRect.SetCornerRadius(
3090         RoundRect::CornerPos::BOTTOM_LEFT_POS, focusPaintCornerBottomLeft.x, focusPaintCornerBottomLeft.y);
3091     frameRect.SetCornerRadius(
3092         RoundRect::CornerPos::BOTTOM_RIGHT_POS, focusPaintCornerBottomRight.x, focusPaintCornerBottomRight.y);
3093 
3094     modifier->SetRoundRect(frameRect, paintWidthPx);
3095 }
3096 
ClearAccessibilityFocus()3097 void RosenRenderContext::ClearAccessibilityFocus()
3098 {
3099     CHECK_NULL_VOID(rsNode_);
3100     CHECK_NULL_VOID(accessibilityFocusStateModifier_);
3101     rsNode_->RemoveModifier(accessibilityFocusStateModifier_);
3102     RequestNextFrame();
3103 }
3104 
BdImagePaintTask(RSCanvas & canvas)3105 void RosenRenderContext::BdImagePaintTask(RSCanvas& canvas)
3106 {
3107     CHECK_NULL_VOID(GetBorderImage());
3108     auto paintRect = GetPaintRectWithoutTransform();
3109     if (NearZero(paintRect.Width()) || NearZero(paintRect.Height())) {
3110         return;
3111     }
3112 
3113     auto host = GetHost();
3114     CHECK_NULL_VOID(host);
3115     auto layoutProps = host->GetLayoutProperty();
3116     CHECK_NULL_VOID(layoutProps);
3117     const auto& widthProp = layoutProps->GetBorderWidthProperty();
3118 
3119     auto pipeline = host->GetContextRefPtr();
3120     CHECK_NULL_VOID(pipeline);
3121     auto dipScale = pipeline->GetDipScale();
3122     auto lpxScale = pipeline->GetLogicScale();
3123 
3124     CHECK_NULL_VOID(bdImage_);
3125     std::shared_ptr<RSImage> image;
3126     if (InstanceOf<DrawingImage>(bdImage_)) {
3127         image = DynamicCast<DrawingImage>(bdImage_)->GetImage();
3128     } else if (InstanceOf<PixelMapImage>(bdImage_)) {
3129         auto pixmap = DynamicCast<PixelMapImage>(bdImage_)->GetPixelMap();
3130         CHECK_NULL_VOID(pixmap);
3131         image = DrawingImage::MakeRSImageFromPixmap(pixmap);
3132     } else {
3133         return;
3134     }
3135     CHECK_NULL_VOID(image);
3136     BorderImagePainter borderImagePainter(
3137         *GetBdImage(), widthProp, paintRect.GetSize(), *image, { dipScale, lpxScale });
3138     if (Container::GreatOrEqualAPITargetVersion(PlatformVersion::VERSION_FOURTEEN)) {
3139         auto rect = borderImagePainter.GetDrawRect(OffsetF(0.0, 0.0));
3140         std::shared_ptr<Rosen::RectF> drawRect =
3141             std::make_shared<Rosen::RectF>(rect.GetX(), rect.GetY(), rect.Width(), rect.Height());
3142         UpdateDrawRegion(DRAW_REGION_FOREGROUND_MODIFIER_INDEX, drawRect);
3143     }
3144     borderImagePainter.PaintBorderImage(OffsetF(0.0, 0.0), canvas);
3145 }
3146 
PaintBorderImage()3147 void RosenRenderContext::PaintBorderImage()
3148 {
3149     CHECK_NULL_VOID(rsNode_);
3150 
3151     auto paintTask = [weak = WeakClaim(this)](RSCanvas& canvas) {
3152         auto ctx = weak.Upgrade();
3153         CHECK_NULL_VOID(ctx);
3154         ctx->BdImagePaintTask(canvas);
3155     };
3156 
3157     if (!borderImageModifier_) {
3158         borderImageModifier_ = std::make_shared<BorderImageModifier>();
3159         rsNode_->AddModifier(borderImageModifier_);
3160     }
3161     borderImageModifier_->SetPaintTask(std::move(paintTask));
3162     borderImageModifier_->Modify();
3163 }
3164 
CreateBorderImageDataReadyCallback()3165 DataReadyNotifyTask RosenRenderContext::CreateBorderImageDataReadyCallback()
3166 {
3167     return [weak = WeakClaim(this)](const ImageSourceInfo& sourceInfo) {
3168         auto rosenRenderContext = weak.Upgrade();
3169         CHECK_NULL_VOID(rosenRenderContext);
3170         auto imageSourceInfo = rosenRenderContext->GetBorderImageSource().value_or(ImageSourceInfo(""));
3171         if (imageSourceInfo != sourceInfo) {
3172             return;
3173         }
3174         rosenRenderContext->bdImageLoadingCtx_->MakeCanvasImage(SizeF(), true, ImageFit::NONE);
3175     };
3176 }
3177 
CreateBorderImageLoadSuccessCallback()3178 LoadSuccessNotifyTask RosenRenderContext::CreateBorderImageLoadSuccessCallback()
3179 {
3180     return [weak = WeakClaim(this)](const ImageSourceInfo& sourceInfo) {
3181         auto ctx = weak.Upgrade();
3182         CHECK_NULL_VOID(ctx);
3183         auto imageSourceInfo = ctx->GetBorderImageSource().value_or(ImageSourceInfo(""));
3184         if (imageSourceInfo != sourceInfo) {
3185             return;
3186         }
3187         ctx->bdImage_ = ctx->bdImageLoadingCtx_->MoveCanvasImage();
3188         CHECK_NULL_VOID(ctx->bdImage_);
3189         if (ctx->GetHost()->GetGeometryNode()->GetFrameSize().IsPositive()) {
3190             ctx->PaintBorderImage();
3191             ctx->RequestNextFrame();
3192         }
3193     };
3194 }
3195 
UpdateCustomBackground()3196 void RosenRenderContext::UpdateCustomBackground()
3197 {
3198     ModifyCustomBackground();
3199     RequestNextFrame();
3200 }
3201 
OnBackgroundAlignUpdate(const Alignment & align)3202 void RosenRenderContext::OnBackgroundAlignUpdate(const Alignment& align)
3203 {
3204     CHECK_NULL_VOID(rsNode_);
3205     auto node = GetHost();
3206     CHECK_NULL_VOID(node);
3207     auto transitionModifier = GetOrCreateTransitionModifier();
3208     transitionModifier->SetHostNode(node);
3209     transitionModifier->SetAlign(align);
3210     auto backgroundModifier = GetOrCreateBackgroundModifier();
3211     backgroundModifier->SetHostNode(node);
3212     backgroundModifier->SetAlign(align);
3213     ModifyCustomBackground();
3214     RequestNextFrame();
3215 }
3216 
OnBackgroundPixelMapUpdate(const RefPtr<PixelMap> & pixelMap)3217 void RosenRenderContext::OnBackgroundPixelMapUpdate(const RefPtr<PixelMap>& pixelMap)
3218 {
3219     CHECK_NULL_VOID(rsNode_);
3220     auto node = GetHost();
3221     CHECK_NULL_VOID(node);
3222     auto transitionModifier = GetOrCreateTransitionModifier();
3223     auto backgroundRegion = node->GetBackGroundAccumulatedSafeAreaExpand();
3224     transitionModifier->SetHostNode(node);
3225     transitionModifier->SetPixelMap(pixelMap);
3226     transitionModifier->SetInitialBackgroundRegion(backgroundRegion);
3227     auto backgroundModifier = GetOrCreateBackgroundModifier();
3228     auto nodeWidth = node->GetGeometryNode()->GetFrameSize().Width();
3229     auto nodeHeight = node->GetGeometryNode()->GetFrameSize().Height();
3230     backgroundModifier->SetHostNode(node);
3231     backgroundModifier->SetPixelMap(pixelMap);
3232     backgroundModifier->SetInitialNodeSize(nodeWidth, nodeHeight);
3233     ModifyCustomBackground();
3234     RequestNextFrame();
3235 }
3236 
OnCustomBackgroundColorUpdate(const Color & color)3237 void RosenRenderContext::OnCustomBackgroundColorUpdate(const Color& color)
3238 {
3239     CHECK_NULL_VOID(rsNode_);
3240     auto node = GetHost();
3241     CHECK_NULL_VOID(node);
3242     auto transitionModifier = GetOrCreateTransitionModifier();
3243     transitionModifier->SetHostNode(node);
3244     transitionModifier->SetBackgroundColor(color);
3245     if (!GetIsTransitionBackgroundValue(false)) {
3246         return;
3247     }
3248     ModifyCustomBackground();
3249     RequestNextFrame();
3250 }
3251 
OnBuilderBackgroundFlagUpdate(bool isBuilderBackground)3252 void RosenRenderContext::OnBuilderBackgroundFlagUpdate(bool isBuilderBackground)
3253 {
3254     CHECK_NULL_VOID(rsNode_);
3255     auto transitionModifier = GetOrCreateTransitionModifier();
3256     transitionModifier->SetIsBuilderBackground(isBuilderBackground);
3257 }
3258 
CreateBackgroundPixelMap(const RefPtr<FrameNode> & customNode)3259 void RosenRenderContext::CreateBackgroundPixelMap(const RefPtr<FrameNode>& customNode)
3260 {
3261     NG::ComponentSnapshot::JsCallback callback =
3262         [weak = WeakPtr(GetHost()), containerId = Container::CurrentId(), backgroundTaskId = ++backgroundTaskId_](
3263             std::shared_ptr<Media::PixelMap> pixmap, int32_t errCode, std::function<void()> finishCallback) {
3264             CHECK_NULL_VOID(pixmap);
3265             auto frameNode = weak.Upgrade();
3266             CHECK_NULL_VOID(frameNode);
3267             ContainerScope scope(containerId);
3268             std::shared_ptr<Media::PixelMap> pmap = std::move(pixmap);
3269             auto pixelmap = PixelMap::CreatePixelMap(&pmap);
3270             auto task = [pixelmap, frameNode, containerId, backgroundTaskId]() {
3271                 ContainerScope scope(containerId);
3272                 auto context = frameNode->GetRenderContext();
3273                 if (context && (context->GetCurrentBackgroundTaskId() == backgroundTaskId)) {
3274                     context->UpdateBackgroundPixelMap(pixelmap);
3275                     context->RequestNextFrame();
3276                 }
3277             };
3278             auto taskExecutor = Container::CurrentTaskExecutor();
3279             CHECK_NULL_VOID(taskExecutor);
3280             taskExecutor->PostTask(task, TaskExecutor::TaskType::UI, "ArkUICreateBackgroundPixelMap");
3281         };
3282     auto firstCallback = callback;
3283     SnapshotParam firstParam;
3284     firstParam.delay = 0;
3285     firstParam.checkImageStatus = true;
3286     firstParam.options.waitUntilRenderFinished = true;
3287     NG::ComponentSnapshot::Create(customNode, std::move(firstCallback), false, firstParam, true);
3288 
3289     SnapshotParam param;
3290     NG::ComponentSnapshot::Create(customNode, std::move(callback), false, param, false);
3291 }
3292 
OnBorderImageUpdate(const RefPtr<BorderImage> &)3293 void RosenRenderContext::OnBorderImageUpdate(const RefPtr<BorderImage>& /*borderImage*/)
3294 {
3295     CHECK_NULL_VOID(rsNode_);
3296     if (bdImageLoadingCtx_ && bdImage_) {
3297         PaintBorderImage();
3298         RequestNextFrame();
3299     }
3300 }
3301 
OnBorderImageSourceUpdate(const ImageSourceInfo & borderImageSourceInfo)3302 void RosenRenderContext::OnBorderImageSourceUpdate(const ImageSourceInfo& borderImageSourceInfo)
3303 {
3304     CHECK_NULL_VOID(rsNode_);
3305     if (!bdImageLoadingCtx_ || borderImageSourceInfo != bdImageLoadingCtx_->GetSourceInfo()) {
3306         LoadNotifier bgLoadNotifier(
3307             CreateBorderImageDataReadyCallback(), CreateBorderImageLoadSuccessCallback(), nullptr);
3308         bdImageLoadingCtx_ = AceType::MakeRefPtr<ImageLoadingContext>(borderImageSourceInfo, std::move(bgLoadNotifier));
3309         CHECK_NULL_VOID(bdImageLoadingCtx_);
3310         bdImageLoadingCtx_->LoadImageData();
3311     }
3312     RequestNextFrame();
3313 }
3314 
OnBorderImageGradientUpdate(const Gradient & gradient)3315 void RosenRenderContext::OnBorderImageGradientUpdate(const Gradient& gradient)
3316 {
3317     CHECK_NULL_VOID(rsNode_);
3318     if (!gradient.IsValid()) {
3319         return;
3320     }
3321     if (GetHost()->GetGeometryNode()->GetFrameSize().IsPositive()) {
3322         PaintBorderImageGradient();
3323     }
3324     RequestNextFrame();
3325 }
3326 
PaintBorderImageGradient()3327 void RosenRenderContext::PaintBorderImageGradient()
3328 {
3329     CHECK_NULL_VOID(rsNode_);
3330     CHECK_NULL_VOID(GetBorderImage());
3331     CHECK_NULL_VOID(GetBorderImageGradient());
3332     auto gradient = GetBorderImageGradient().value();
3333     if (!gradient.IsValid()) {
3334         return;
3335     }
3336     auto paintSize = GetPaintRectWithoutTransform().GetSize();
3337     if (NearZero(paintSize.Width()) || NearZero(paintSize.Height())) {
3338         return;
3339     }
3340     auto layoutProperty = GetHost()->GetLayoutProperty();
3341     CHECK_NULL_VOID(layoutProperty);
3342 
3343     auto borderImageProperty = *GetBdImage();
3344     auto&& borderWidthProperty = layoutProperty->GetBorderWidthProperty();
3345     auto paintTask = [weak = WeakClaim(this), paintSize, borderImageProperty, &borderWidthProperty, gradient](
3346                          RSCanvas& rsCanvas) mutable {
3347         auto rsImage = DrawingDecorationPainter::CreateBorderImageGradient(gradient, paintSize);
3348         auto pattern = weak.Upgrade();
3349         CHECK_NULL_VOID(pattern);
3350         auto host = pattern->GetHost();
3351         CHECK_NULL_VOID(host);
3352         auto pipeline = host->GetContext();
3353         CHECK_NULL_VOID(pipeline);
3354         BorderImagePainter borderImagePainter(borderImageProperty, borderWidthProperty, paintSize, rsImage,
3355             { pipeline->GetDipScale(), pipeline->GetLogicScale() });
3356         borderImagePainter.PaintBorderImage(OffsetF(0.0, 0.0), rsCanvas);
3357     };
3358 
3359     if (!borderImageModifier_) {
3360         borderImageModifier_ = std::make_shared<BorderImageModifier>();
3361         rsNode_->AddModifier(borderImageModifier_);
3362     }
3363     borderImageModifier_->SetPaintTask(std::move(paintTask));
3364     borderImageModifier_->Modify();
3365 }
3366 
OnModifyDone()3367 void RosenRenderContext::OnModifyDone()
3368 {
3369     if (HasClickEffectLevel()) {
3370         InitEventClickEffect();
3371     }
3372 }
3373 
GetPropertyOfPosition()3374 RectF RosenRenderContext::GetPropertyOfPosition()
3375 {
3376     return AdjustPaintRect();
3377 }
3378 
AdjustPaintRect()3379 RectF RosenRenderContext::AdjustPaintRect()
3380 {
3381     RectF rect;
3382     auto frameNode = GetHost();
3383     CHECK_NULL_RETURN(frameNode, rect);
3384     CHECK_NULL_RETURN(rsNode_, rect);
3385     const auto& geometryNode = frameNode->GetGeometryNode();
3386     rect = geometryNode->GetFrameRect();
3387     if (Container::LessThanAPIVersion(PlatformVersion::VERSION_TEN)) {
3388         if (!rect.GetSize().IsPositive()) {
3389             geometryNode->SetPixelGridRoundOffset(rect.GetOffset());
3390             return rect;
3391         }
3392     } else {
3393         if (!rect.GetSize().IsPositive() && !frameNode->IsLayoutComplete()) {
3394             geometryNode->SetPixelGridRoundOffset(rect.GetOffset());
3395             return rect;
3396         }
3397     }
3398     bool hasPosition = (HasPosition() || HasPositionEdges()) && IsUsingPosition(frameNode);
3399     bool hasOffset = HasOffset() || HasOffsetEdges();
3400     if (!HasAnchor() && !hasOffset && !hasPosition) {
3401         geometryNode->SetPixelGridRoundOffset(rect.GetOffset());
3402         return rect;
3403     }
3404     auto percentReference = GetPercentReference(frameNode);
3405     auto widthPercentReference = percentReference.Width();
3406     auto heightPercentReference = percentReference.Height();
3407     auto anchor = GetAnchorValue({});
3408     auto anchorWidthReference = rect.Width();
3409     auto anchorHeightReference = rect.Height();
3410     auto anchorX = ConvertToPx(anchor.GetX(), ScaleProperty::CreateScaleProperty(), anchorWidthReference);
3411     auto anchorY = ConvertToPx(anchor.GetY(), ScaleProperty::CreateScaleProperty(), anchorHeightReference);
3412     Dimension resultX;
3413     Dimension resultY;
3414     Dimension parentPaddingLeft;
3415     Dimension parentPaddingTop;
3416     GetPaddingOfFirstFrameNodeParent(parentPaddingLeft, parentPaddingTop);
3417     // Position properties take precedence over offset locations.
3418     if (HasPosition() && IsUsingPosition(frameNode)) {
3419         CombineMarginAndPosition(
3420             resultX, resultY, parentPaddingLeft, parentPaddingTop, widthPercentReference, heightPercentReference);
3421         rect.SetLeft(resultX.ConvertToPx() - anchorX.value_or(0));
3422         rect.SetTop(resultY.ConvertToPx() - anchorY.value_or(0));
3423         geometryNode->SetPixelGridRoundOffset(rect.GetOffset());
3424         return rect;
3425     }
3426     if (HasPositionEdges() && IsUsingPosition(frameNode)) {
3427         auto positionEdges = GetPositionEdgesValue(EdgesParam {});
3428         OffsetF rectOffset =
3429             GetRectOffsetWithPositionEdges(positionEdges, widthPercentReference, heightPercentReference);
3430         rect.SetLeft(rectOffset.GetX() - anchorX.value_or(0));
3431         rect.SetTop(rectOffset.GetY() - anchorY.value_or(0));
3432         geometryNode->SetPixelGridRoundOffset(rect.GetOffset());
3433         return rect;
3434     }
3435     if (HasOffset()) {
3436         auto offset = GetOffsetValue({});
3437         if (PipelineBase::GetCurrentContext() &&
3438             PipelineBase::GetCurrentContext()->GetMinPlatformVersion() < PLATFORM_VERSION_TEN) {
3439             offset += OffsetT<Dimension>(parentPaddingLeft, parentPaddingTop);
3440         }
3441         auto offsetX = ConvertToPx(offset.GetX(), ScaleProperty::CreateScaleProperty(), widthPercentReference);
3442         auto offsetY = ConvertToPx(offset.GetY(), ScaleProperty::CreateScaleProperty(), heightPercentReference);
3443         rect.SetLeft(rect.GetX() + offsetX.value_or(0) - anchorX.value_or(0));
3444         rect.SetTop(rect.GetY() + offsetY.value_or(0) - anchorY.value_or(0));
3445         geometryNode->SetPixelGridRoundOffset(rect.GetOffset());
3446         return rect;
3447     }
3448     if (HasOffsetEdges()) {
3449         auto offsetEdges = GetOffsetEdgesValue(EdgesParam {});
3450         OffsetF rectOffset = GetRectOffsetWithOffsetEdges(offsetEdges, widthPercentReference, heightPercentReference);
3451         rect.SetLeft(rect.GetX() + rectOffset.GetX() - anchorX.value_or(0));
3452         rect.SetTop(rect.GetY() + rectOffset.GetY() - anchorY.value_or(0));
3453         geometryNode->SetPixelGridRoundOffset(rect.GetOffset());
3454         return rect;
3455     }
3456     rect.SetLeft(rect.GetX() - anchorX.value_or(0));
3457     rect.SetTop(rect.GetY() - anchorY.value_or(0));
3458     geometryNode->SetPixelGridRoundOffset(rect.GetOffset());
3459     return rect;
3460 }
3461 
RoundValueToPixelGrid(float value)3462 float RosenRenderContext::RoundValueToPixelGrid(float value)
3463 {
3464     float fractials = fmod(value, 1.0f);
3465     if (fractials < 0.0f) {
3466         ++fractials;
3467     }
3468     if (NearEqual(fractials, 1.0f) || GreatOrEqual(fractials, 0.75f)) {
3469         return (value - fractials + 1.0f);
3470     } else if (NearEqual(fractials, 0.0f) || !GreatOrEqual(fractials, 0.25f)) {
3471         return (value - fractials);
3472     } else {
3473         return (value - fractials + 0.5f);
3474     }
3475 }
3476 
GetRectOffsetWithOffsetEdges(const EdgesParam & offsetEdges,float widthPercentReference,float heightPercentReference)3477 OffsetF RosenRenderContext::GetRectOffsetWithOffsetEdges(
3478     const EdgesParam& offsetEdges, float widthPercentReference, float heightPercentReference)
3479 {
3480     OffsetF rectOffset;
3481     if (offsetEdges.top.has_value()) {
3482         rectOffset.SetY(
3483             ConvertToPx(offsetEdges.top.value(), ScaleProperty::CreateScaleProperty(), heightPercentReference)
3484                 .value_or(0));
3485     }
3486     if (offsetEdges.left.has_value()) {
3487         rectOffset.SetX(
3488             ConvertToPx(offsetEdges.left.value(), ScaleProperty::CreateScaleProperty(), widthPercentReference)
3489                 .value_or(0));
3490     }
3491     if (!offsetEdges.top.has_value() && offsetEdges.bottom.has_value()) {
3492         rectOffset.SetY(
3493             -ConvertToPx(offsetEdges.bottom.value(), ScaleProperty::CreateScaleProperty(), heightPercentReference)
3494                  .value_or(0));
3495     }
3496     if (!offsetEdges.left.has_value() && offsetEdges.right.has_value()) {
3497         rectOffset.SetX(
3498             -ConvertToPx(offsetEdges.right.value(), ScaleProperty::CreateScaleProperty(), widthPercentReference)
3499                  .value_or(0));
3500     }
3501     return rectOffset;
3502 }
3503 
GetRectOffsetWithPositionEdges(const EdgesParam & positionEdges,float widthPercentReference,float heightPercentReference)3504 OffsetF RosenRenderContext::GetRectOffsetWithPositionEdges(
3505     const EdgesParam& positionEdges, float widthPercentReference, float heightPercentReference)
3506 {
3507     float rectTop = 0.0f;
3508     float rectLeft = 0.0f;
3509 
3510     auto frameNode = GetHost();
3511     CHECK_NULL_RETURN(frameNode, OffsetF {});
3512     auto layoutProperty = frameNode->GetLayoutProperty();
3513     CHECK_NULL_RETURN(layoutProperty, OffsetF {});
3514     auto& marginOri = layoutProperty->GetMarginProperty();
3515     std::unique_ptr<MarginProperty> margin(
3516         marginOri ? std::make_unique<MarginProperty>(*marginOri) : std::make_unique<MarginProperty>());
3517 
3518     auto parentNode = frameNode->GetAncestorNodeOfFrame(true);
3519     CHECK_NULL_RETURN(parentNode, OffsetF {});
3520     auto parentLayoutProperty = parentNode->GetLayoutProperty();
3521     CHECK_NULL_RETURN(parentLayoutProperty, OffsetF {});
3522     auto& parentPaddingOri = parentLayoutProperty->GetPaddingProperty();
3523     std::unique_ptr<PaddingProperty> parentPadding(
3524         parentPaddingOri ? std::make_unique<PaddingProperty>(*parentPaddingOri) : std::make_unique<PaddingProperty>());
3525 
3526     auto parenPercentRef = GetPercentReference(parentNode);
3527     float parentWidthRef = parenPercentRef.Width();
3528     float parentHeightRef = parenPercentRef.Height();
3529 
3530     SizeF selfSize = frameNode->GetGeometryNode()->GetFrameSize();
3531     float selfWidth = selfSize.Width();
3532     float selfHeight = selfSize.Height();
3533     SizeF parentSize = parentNode->GetGeometryNode()->GetFrameSize();
3534     float parentWidth = parentSize.Width();
3535     float parentHeight = parentSize.Height();
3536 
3537     if (positionEdges.top.has_value()) {
3538         rectTop = ConvertToPx(parentPadding->top.value_or(CalcLength(Dimension(0))).GetDimension(),
3539                       ScaleProperty::CreateScaleProperty(), parentHeightRef)
3540                       .value_or(0) +
3541                   ConvertToPx(margin->top.value_or(CalcLength(Dimension(0))).GetDimension(),
3542                       ScaleProperty::CreateScaleProperty(), heightPercentReference)
3543                       .value_or(0) +
3544                   ConvertToPx(positionEdges.top.value(), ScaleProperty::CreateScaleProperty(), heightPercentReference)
3545                       .value_or(0);
3546     }
3547     if (positionEdges.left.has_value()) {
3548         rectLeft = ConvertToPx(parentPadding->left.value_or(CalcLength(Dimension(0))).GetDimension(),
3549                        ScaleProperty::CreateScaleProperty(), parentWidthRef)
3550                        .value_or(0) +
3551                    ConvertToPx(margin->left.value_or(CalcLength(Dimension(0))).GetDimension(),
3552                        ScaleProperty::CreateScaleProperty(), widthPercentReference)
3553                        .value_or(0) +
3554                    ConvertToPx(positionEdges.left.value(), ScaleProperty::CreateScaleProperty(), widthPercentReference)
3555                        .value_or(0);
3556     }
3557     if (!positionEdges.top.has_value() && positionEdges.bottom.has_value()) {
3558         rectTop =
3559             parentHeight - selfHeight -
3560             ConvertToPx(parentPadding->bottom.value_or(CalcLength(Dimension(0))).GetDimension(),
3561                 ScaleProperty::CreateScaleProperty(), parentHeightRef)
3562                 .value_or(0) -
3563             ConvertToPx(margin->bottom.value_or(CalcLength(Dimension(0))).GetDimension(),
3564                 ScaleProperty::CreateScaleProperty(), heightPercentReference)
3565                 .value_or(0) -
3566             ConvertToPx(positionEdges.bottom.value(), ScaleProperty::CreateScaleProperty(), heightPercentReference)
3567                 .value_or(0);
3568     }
3569     if (!positionEdges.left.has_value() && positionEdges.right.has_value()) {
3570         rectLeft = parentWidth - selfWidth -
3571                    ConvertToPx(parentPadding->right.value_or(CalcLength(Dimension(0))).GetDimension(),
3572                        ScaleProperty::CreateScaleProperty(), parentWidthRef)
3573                        .value_or(0) -
3574                    ConvertToPx(margin->right.value_or(CalcLength(Dimension(0))).GetDimension(),
3575                        ScaleProperty::CreateScaleProperty(), widthPercentReference)
3576                        .value_or(0) -
3577                    ConvertToPx(positionEdges.right.value(), ScaleProperty::CreateScaleProperty(), widthPercentReference)
3578                        .value_or(0);
3579     }
3580     return OffsetF(rectLeft, rectTop);
3581 }
3582 
RoundValueToPixelGrid(float value,bool isRound,bool forceCeil,bool forceFloor)3583 float RosenRenderContext::RoundValueToPixelGrid(float value, bool isRound, bool forceCeil, bool forceFloor)
3584 {
3585     float fractials = fmod(value, 1.0f);
3586     if (fractials < 0.0f) {
3587         ++fractials;
3588     }
3589     if (forceCeil) {
3590         return (value - fractials + 1.0f);
3591     } else if (forceFloor) {
3592         return (value - fractials);
3593     } else if (isRound) {
3594         if (NearEqual(fractials, 1.0f) || GreatOrEqual(fractials, 0.75f)) {
3595             return (value - fractials + 1.0f);
3596         } else if (NearEqual(fractials, 0.0f) || !GreatOrEqual(fractials, 0.25f)) {
3597             return (value - fractials);
3598         } else {
3599             return (value - fractials + 0.5f);
3600         }
3601     }
3602     return value;
3603 }
3604 
OnePixelValueRounding(float value)3605 float RosenRenderContext::OnePixelValueRounding(float value)
3606 {
3607     float fractials = fmod(value, 1.0f);
3608     if (fractials < 0.0f) {
3609         ++fractials;
3610     }
3611     if (NearEqual(fractials, 1.0f) || GreatOrEqual(fractials, 0.5f)) {
3612         return (value - fractials + 1.0f);
3613     } else {
3614         return (value - fractials);
3615     }
3616 }
3617 
OnePixelValueRounding(float value,bool isRound,bool forceCeil,bool forceFloor)3618 float RosenRenderContext::OnePixelValueRounding(float value, bool isRound, bool forceCeil, bool forceFloor)
3619 {
3620     float fractials = fmod(value, 1.0f);
3621     if (fractials < 0.0f) {
3622         ++fractials;
3623     }
3624     if (forceCeil) {
3625         return (value - fractials + 1.0f);
3626     } else if (forceFloor) {
3627         return (value - fractials);
3628     } else if (isRound) {
3629         if (NearEqual(fractials, 1.0f) || GreatOrEqual(fractials, 0.5f)) {
3630             return (value - fractials + 1.0f);
3631         } else {
3632             return (value - fractials);
3633         }
3634     }
3635     return value;
3636 }
3637 
RoundToPixelGrid()3638 void RosenRenderContext::RoundToPixelGrid()
3639 {
3640     auto frameNode = GetHost();
3641     CHECK_NULL_VOID(frameNode);
3642     auto geometryNode = frameNode->GetGeometryNode();
3643     float relativeLeft = geometryNode->GetPixelGridRoundOffset().GetX();
3644     float relativeTop = geometryNode->GetPixelGridRoundOffset().GetY();
3645     float nodeWidth = geometryNode->GetFrameSize().Width();
3646     float nodeHeight = geometryNode->GetFrameSize().Height();
3647     float absoluteRight = relativeLeft + nodeWidth;
3648     float absoluteBottom = relativeTop + nodeHeight;
3649     // round node
3650     float nodeLeftI = RoundValueToPixelGrid(relativeLeft);
3651     float nodeTopI = RoundValueToPixelGrid(relativeTop);
3652     geometryNode->SetPixelGridRoundOffset(OffsetF(nodeLeftI, nodeTopI));
3653     float nodeWidthI = RoundValueToPixelGrid(absoluteRight) - nodeLeftI;
3654     float nodeHeightI = RoundValueToPixelGrid(absoluteBottom) - nodeTopI;
3655     geometryNode->SetPixelGridRoundSize(SizeF(nodeWidthI, nodeHeightI));
3656     if (borderWidth_ != Rosen::Vector4f(0.0f, 0.0f, 0.0f, 0.0f)) {
3657         // round inner
3658         float innerLeft = relativeLeft + borderWidth_[0];
3659         float innerRight = relativeLeft + nodeWidth - borderWidth_[2];
3660         float innerTop = relativeTop + borderWidth_[1];
3661         float innerBottom = relativeTop + nodeHeight - borderWidth_[3];
3662         float innerWidthI = RoundValueToPixelGrid(innerRight) - RoundValueToPixelGrid(innerLeft);
3663         float innerHeightI = RoundValueToPixelGrid(innerBottom) - RoundValueToPixelGrid(innerTop);
3664         // update border
3665         float borderLeftI = RoundValueToPixelGrid(borderWidth_[0]);
3666         float borderTopI = RoundValueToPixelGrid(borderWidth_[1]);
3667         float borderRightI = nodeWidthI - innerWidthI - borderLeftI;
3668         float borderBottomI = nodeHeightI - innerHeightI - borderTopI;
3669         BorderWidthPropertyF borderWidthPropertyF;
3670         borderWidthPropertyF.leftDimen = borderLeftI;
3671         borderWidthPropertyF.topDimen = borderTopI;
3672         borderWidthPropertyF.rightDimen = borderRightI;
3673         borderWidthPropertyF.bottomDimen = borderBottomI;
3674         UpdateBorderWidthF(borderWidthPropertyF);
3675     }
3676 }
3677 
RoundToPixelGrid(bool isRound,uint16_t flag)3678 void RosenRenderContext::RoundToPixelGrid(bool isRound, uint16_t flag)
3679 {
3680     CHECK_NULL_VOID(rsNode_);
3681     auto frameNode = GetHost();
3682     CHECK_NULL_VOID(frameNode);
3683     auto geometryNode = frameNode->GetGeometryNode();
3684     float relativeLeft = geometryNode->GetPixelGridRoundOffset().GetX();
3685     float relativeTop = geometryNode->GetPixelGridRoundOffset().GetY();
3686     float nodeWidth = geometryNode->GetFrameSize().Width();
3687     float nodeHeight = geometryNode->GetFrameSize().Height();
3688     float absoluteRight = relativeLeft + nodeWidth;
3689     float absoluteBottom = relativeTop + nodeHeight;
3690     bool ceilLeft = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_CEIL_START);
3691     bool floorLeft = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_FLOOR_START);
3692     bool ceilTop = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_CEIL_TOP);
3693     bool floorTop = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_FLOOR_TOP);
3694     bool ceilRight = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_CEIL_END);
3695     bool floorRight = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_FLOOR_END);
3696     bool ceilBottom = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_CEIL_BOTTOM);
3697     bool floorBottom = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_FLOOR_BOTTOM);
3698     // round node
3699     float nodeLeftI = RoundValueToPixelGrid(relativeLeft, isRound, ceilLeft, floorLeft);
3700     float nodeTopI = RoundValueToPixelGrid(relativeTop, isRound, ceilTop, floorTop);
3701     geometryNode->SetPixelGridRoundOffset(OffsetF(nodeLeftI, nodeTopI));
3702     float nodeWidthI = RoundValueToPixelGrid(absoluteRight, isRound, ceilRight, floorRight) - nodeLeftI;
3703     float nodeHeightI = RoundValueToPixelGrid(absoluteBottom, isRound, ceilBottom, floorBottom) - nodeTopI;
3704     geometryNode->SetPixelGridRoundSize(SizeF(nodeWidthI, nodeHeightI));
3705     if (borderWidth_ != Rosen::Vector4f(0.0f, 0.0f, 0.0f, 0.0f)) {
3706         // round inner
3707         float innerLeft = relativeLeft + borderWidth_[0];
3708         float innerRight = relativeLeft + nodeWidth - borderWidth_[2];
3709         float innerTop = relativeTop + borderWidth_[1];
3710         float innerBottom = relativeTop + nodeHeight - borderWidth_[3];
3711         float innerWidthI = RoundValueToPixelGrid(innerRight, isRound, ceilRight, floorRight) -
3712                             RoundValueToPixelGrid(innerLeft, isRound, ceilLeft, floorLeft);
3713         float innerHeightI = RoundValueToPixelGrid(innerBottom, isRound, ceilBottom, floorBottom) -
3714                              RoundValueToPixelGrid(innerTop, isRound, ceilTop, floorTop);
3715         // update border
3716         float borderLeftI = RoundValueToPixelGrid(borderWidth_[0], isRound, ceilLeft, floorLeft);
3717         float borderTopI = RoundValueToPixelGrid(borderWidth_[1], isRound, ceilTop, floorTop);
3718         float borderRightI = nodeWidthI - innerWidthI - borderLeftI;
3719         float borderBottomI = nodeHeightI - innerHeightI - borderTopI;
3720         BorderWidthPropertyF borderWidthPropertyF;
3721         borderWidthPropertyF.leftDimen = borderLeftI;
3722         borderWidthPropertyF.topDimen = borderTopI;
3723         borderWidthPropertyF.rightDimen = borderRightI;
3724         borderWidthPropertyF.bottomDimen = borderBottomI;
3725         UpdateBorderWidthF(borderWidthPropertyF);
3726     }
3727 }
3728 
OnePixelRounding()3729 void RosenRenderContext::OnePixelRounding()
3730 {
3731     auto frameNode = GetHost();
3732     CHECK_NULL_VOID(frameNode);
3733     auto geometryNode = frameNode->GetGeometryNode();
3734     float relativeLeft = geometryNode->GetPixelGridRoundOffset().GetX();
3735     float relativeTop = geometryNode->GetPixelGridRoundOffset().GetY();
3736     float nodeWidth = geometryNode->GetFrameSize().Width();
3737     float nodeHeight = geometryNode->GetFrameSize().Height();
3738     float roundToPixelErrorX = 0.0f;
3739     float roundToPixelErrorY = 0.0f;
3740     float absoluteRight = relativeLeft + nodeWidth;
3741     float absoluteBottom = relativeTop + nodeHeight;
3742 
3743     float nodeLeftI = OnePixelValueRounding(relativeLeft);
3744     float nodeTopI = OnePixelValueRounding(relativeTop);
3745     roundToPixelErrorX += nodeLeftI - relativeLeft;
3746     roundToPixelErrorY += nodeTopI - relativeTop;
3747     geometryNode->SetPixelGridRoundOffset(OffsetF(nodeLeftI, nodeTopI));
3748 
3749     float nodeWidthI = OnePixelValueRounding(absoluteRight) - nodeLeftI;
3750     float nodeWidthTemp = OnePixelValueRounding(nodeWidth);
3751     roundToPixelErrorX += nodeWidthI - nodeWidth;
3752     if (roundToPixelErrorX > 0.5f) {
3753         nodeWidthI -= 1.0f;
3754         roundToPixelErrorX -= 1.0f;
3755     }
3756     if (roundToPixelErrorX < -0.5f) {
3757         nodeWidthI += 1.0f;
3758         roundToPixelErrorX += 1.0f;
3759     }
3760     if (nodeWidthI < nodeWidthTemp) {
3761         roundToPixelErrorX += nodeWidthTemp - nodeWidthI;
3762         nodeWidthI = nodeWidthTemp;
3763     }
3764 
3765     float nodeHeightI = OnePixelValueRounding(absoluteBottom) - nodeTopI;
3766     float nodeHeightTemp = OnePixelValueRounding(nodeHeight);
3767     roundToPixelErrorY += nodeHeightI - nodeHeight;
3768     if (roundToPixelErrorY > 0.5f) {
3769         nodeHeightI -= 1.0f;
3770         roundToPixelErrorY -= 1.0f;
3771     }
3772     if (roundToPixelErrorY < -0.5f) {
3773         nodeHeightI += 1.0f;
3774         roundToPixelErrorY += 1.0f;
3775     }
3776     if (nodeHeightI < nodeHeightTemp) {
3777         roundToPixelErrorY += nodeHeightTemp - nodeHeightI;
3778         nodeHeightI = nodeHeightTemp;
3779     }
3780     geometryNode->SetPixelGridRoundSize(SizeF(nodeWidthI, nodeHeightI));
3781 }
3782 
OnePixelRounding(uint16_t flag)3783 void RosenRenderContext::OnePixelRounding(uint16_t flag)
3784 {
3785     auto frameNode = GetHost();
3786     CHECK_NULL_VOID(frameNode);
3787     auto geometryNode = frameNode->GetGeometryNode();
3788     float relativeLeft = geometryNode->GetPixelGridRoundOffset().GetX();
3789     float relativeTop = geometryNode->GetPixelGridRoundOffset().GetY();
3790     float nodeWidth = geometryNode->GetFrameSize().Width();
3791     float nodeHeight = geometryNode->GetFrameSize().Height();
3792     float roundToPixelErrorX = 0.0f;
3793     float roundToPixelErrorY = 0.0f;
3794     float absoluteRight = relativeLeft + nodeWidth;
3795     float absoluteBottom = relativeTop + nodeHeight;
3796     bool ceilLeft = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_CEIL_START);
3797     bool floorLeft = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_FLOOR_START);
3798     bool noRoundLeft = flag & static_cast<uint16_t>(PixelRoundPolicy::NO_FORCE_ROUND_START);
3799     bool ceilTop = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_CEIL_TOP);
3800     bool floorTop = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_FLOOR_TOP);
3801     bool noRoundTop = flag & static_cast<uint16_t>(PixelRoundPolicy::NO_FORCE_ROUND_TOP);
3802     bool ceilRight = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_CEIL_END);
3803     bool floorRight = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_FLOOR_END);
3804     bool noRoundRight = flag & static_cast<uint16_t>(PixelRoundPolicy::NO_FORCE_ROUND_END);
3805     bool ceilBottom = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_CEIL_BOTTOM);
3806     bool floorBottom = flag & static_cast<uint16_t>(PixelRoundPolicy::FORCE_FLOOR_BOTTOM);
3807     bool noRoundBottom = flag & static_cast<uint16_t>(PixelRoundPolicy::NO_FORCE_ROUND_BOTTOM);
3808 
3809     float nodeLeftI = OnePixelValueRounding(relativeLeft, !noRoundLeft, ceilLeft, floorLeft);
3810     float nodeTopI = OnePixelValueRounding(relativeTop, !noRoundTop, ceilTop, floorTop);
3811     roundToPixelErrorX += nodeLeftI - relativeLeft;
3812     roundToPixelErrorY += nodeTopI - relativeTop;
3813     geometryNode->SetPixelGridRoundOffset(OffsetF(nodeLeftI, nodeTopI));
3814 
3815     float nodeWidthI = OnePixelValueRounding(absoluteRight, !noRoundRight, ceilRight, floorRight) - nodeLeftI;
3816     float nodeWidthTemp = OnePixelValueRounding(nodeWidth, !noRoundRight, ceilRight, floorRight);
3817     roundToPixelErrorX += nodeWidthI - nodeWidth;
3818     if (roundToPixelErrorX > 0.5f) {
3819         nodeWidthI -= 1.0f;
3820         roundToPixelErrorX -= 1.0f;
3821     }
3822     bool enableForceFloorX = SystemProperties::GetDeviceType() == DeviceType::TWO_IN_ONE && (floorLeft || floorRight);
3823     if (roundToPixelErrorX < -0.5f && !enableForceFloorX) {
3824         nodeWidthI += 1.0f;
3825         roundToPixelErrorX += 1.0f;
3826     }
3827     if (nodeWidthI < nodeWidthTemp) {
3828         roundToPixelErrorX += nodeWidthTemp - nodeWidthI;
3829         nodeWidthI = nodeWidthTemp;
3830     }
3831 
3832     float nodeHeightI = OnePixelValueRounding(absoluteBottom, !noRoundBottom, ceilBottom, floorBottom) - nodeTopI;
3833     float nodeHeightTemp = OnePixelValueRounding(nodeHeight, !noRoundBottom, ceilBottom, floorBottom);
3834     roundToPixelErrorY += nodeHeightI - nodeHeight;
3835     if (roundToPixelErrorY > 0.5f) {
3836         nodeHeightI -= 1.0f;
3837         roundToPixelErrorY -= 1.0f;
3838     }
3839     bool enableForceFloorY = SystemProperties::GetDeviceType() == DeviceType::TWO_IN_ONE && (floorTop || floorBottom);
3840     if (roundToPixelErrorY < -0.5f && !enableForceFloorY) {
3841         nodeHeightI += 1.0f;
3842         roundToPixelErrorY += 1.0f;
3843     }
3844     if (nodeHeightI < nodeHeightTemp) {
3845         roundToPixelErrorY += nodeHeightTemp - nodeHeightI;
3846         nodeHeightI = nodeHeightTemp;
3847     }
3848     geometryNode->SetPixelGridRoundSize(SizeF(nodeWidthI, nodeHeightI));
3849 }
3850 
CombineMarginAndPosition(Dimension & resultX,Dimension & resultY,const Dimension & parentPaddingLeft,const Dimension & parentPaddingTop,float widthPercentReference,float heightPercentReference)3851 void RosenRenderContext::CombineMarginAndPosition(Dimension& resultX, Dimension& resultY,
3852     const Dimension& parentPaddingLeft, const Dimension& parentPaddingTop, float widthPercentReference,
3853     float heightPercentReference)
3854 {
3855     Dimension selfMarginLeft;
3856     Dimension selfMarginTop;
3857     auto frameNode = GetHost();
3858     if (frameNode && frameNode->GetLayoutProperty() && frameNode->GetLayoutProperty()->GetMarginProperty()) {
3859         auto& margin = frameNode->GetLayoutProperty()->GetMarginProperty();
3860         if (margin->left.has_value()) {
3861             selfMarginLeft = margin->left.value().GetDimension();
3862         }
3863         if (margin->top.has_value()) {
3864             selfMarginTop = margin->top.value().GetDimension();
3865         }
3866     }
3867     // to distinguish cases ex. margin has percentage unit and padding has vp unit
3868     // final rect offset will be affected by parent padding, self margin and position property
3869     if (selfMarginLeft.Unit() != GetPositionValue({}).GetX().Unit() ||
3870         selfMarginLeft.Unit() != parentPaddingLeft.Unit() ||
3871         parentPaddingLeft.Unit() != GetPositionValue({}).GetX().Unit()) {
3872         resultX = Dimension(
3873             ConvertToPx(parentPaddingLeft, ScaleProperty::CreateScaleProperty(), widthPercentReference).value_or(0) +
3874                 ConvertToPx(selfMarginLeft, ScaleProperty::CreateScaleProperty(), widthPercentReference).value_or(0) +
3875                 ConvertToPx(GetPositionValue({}).GetX(), ScaleProperty::CreateScaleProperty(), widthPercentReference)
3876                     .value_or(0),
3877             DimensionUnit::PX);
3878     } else {
3879         resultX = selfMarginLeft + GetPositionValue({}).GetX() + parentPaddingLeft;
3880     }
3881     if (selfMarginTop.Unit() != GetPositionValue({}).GetY().Unit() || selfMarginTop.Unit() != parentPaddingTop.Unit() ||
3882         parentPaddingTop.Unit() != GetPositionValue({}).GetY().Unit()) {
3883         resultY = Dimension(
3884             ConvertToPx(parentPaddingTop, ScaleProperty::CreateScaleProperty(), heightPercentReference).value_or(0) +
3885                 ConvertToPx(selfMarginTop, ScaleProperty::CreateScaleProperty(), heightPercentReference).value_or(0) +
3886                 ConvertToPx(GetPositionValue({}).GetY(), ScaleProperty::CreateScaleProperty(), heightPercentReference)
3887                     .value_or(0),
3888             DimensionUnit::PX);
3889     } else {
3890         resultY = selfMarginTop + GetPositionValue({}).GetY() + parentPaddingTop;
3891     }
3892 }
3893 
IsUsingPosition(const RefPtr<FrameNode> & frameNode)3894 bool RosenRenderContext::IsUsingPosition(const RefPtr<FrameNode>& frameNode)
3895 {
3896     auto layoutProperty = frameNode->GetLayoutProperty();
3897     bool isUsingPosition = true;
3898     if (layoutProperty) {
3899         isUsingPosition = layoutProperty->IsUsingPosition();
3900     }
3901     return isUsingPosition;
3902 }
3903 
GetPaddingOfFirstFrameNodeParent(Dimension & parentPaddingLeft,Dimension & parentPaddingTop)3904 void RosenRenderContext::GetPaddingOfFirstFrameNodeParent(Dimension& parentPaddingLeft, Dimension& parentPaddingTop)
3905 {
3906     auto frameNode = GetHost();
3907     CHECK_NULL_VOID(frameNode);
3908     auto frameNodeParent = frameNode->GetAncestorNodeOfFrame(true);
3909     CHECK_NULL_VOID(frameNodeParent);
3910     auto layoutProperty = frameNodeParent->GetLayoutProperty();
3911     if (layoutProperty && layoutProperty->GetPaddingProperty()) {
3912         parentPaddingLeft =
3913             layoutProperty->GetPaddingProperty()->left.value_or(CalcLength(Dimension(0))).GetDimension();
3914         parentPaddingTop = layoutProperty->GetPaddingProperty()->top.value_or(CalcLength(Dimension(0))).GetDimension();
3915     }
3916 }
3917 
GetPercentReference(const RefPtr<FrameNode> & frameNode)3918 SizeF RosenRenderContext::GetPercentReference(const RefPtr<FrameNode>& frameNode)
3919 {
3920     SizeF percentReference = SizeF(PipelineContext::GetCurrentRootWidth(), PipelineContext::GetCurrentRootHeight());
3921     CHECK_NULL_RETURN(frameNode, percentReference);
3922     const auto& layoutConstraint = frameNode->GetGeometryNode()->GetParentLayoutConstraint();
3923     if (layoutConstraint.has_value()) {
3924         percentReference.SetWidth(layoutConstraint->percentReference.Width());
3925         percentReference.SetHeight(layoutConstraint->percentReference.Height());
3926     }
3927     return percentReference;
3928 }
3929 
SetPositionToRSNode()3930 void RosenRenderContext::SetPositionToRSNode()
3931 {
3932     auto frameNode = GetHost();
3933     CHECK_NULL_VOID(frameNode);
3934     CHECK_NULL_VOID(rsNode_);
3935     auto rect = AdjustPaintRect();
3936     if (!rect.GetSize().IsPositive()) {
3937         return;
3938     }
3939     paintRect_ = rect;
3940     if (frameNode->ParentExpansive() && !frameNode->SelfExpansive()) {
3941         // Dynamically modify position, need consider parent expand
3942         frameNode->AdjustNotExpandNode();
3943         rect = paintRect_;
3944     }
3945     if (AnimationUtils::IsImplicitAnimationOpen()) {
3946         auto preBounds = rsNode_->GetStagingProperties().GetBounds();
3947         if (!NearEqual(preBounds[0], rect.GetX()) || !NearEqual(preBounds[1], rect.GetY())) {
3948             ACE_SCOPED_TRACE("SetPosition, bounds from (%f, %f, %f, %f) to (%f, %f, %f, %f), id:%d, tag:%s",
3949                 preBounds[0], preBounds[1], preBounds[2], preBounds[3], rect.GetX(), rect.GetY(), rect.Width(),
3950                 rect.Height(), frameNode->GetId(), frameNode->GetTag().c_str());
3951         }
3952     }
3953     rsNode_->SetBounds(rect.GetX(), rect.GetY(), rect.Width(), rect.Height());
3954     if (useContentRectForRSFrame_) {
3955         SetContentRectToFrame(rect);
3956     } else {
3957         rsNode_->SetFrame(rect.GetX(), rect.GetY(), rect.Width(), rect.Height());
3958     }
3959     if (frameOffset_.has_value()) {
3960         rsNode_->SetFrame(
3961             rect.GetX() + frameOffset_->GetX(), rect.GetY() + frameOffset_->GetY(), rect.Width(), rect.Height());
3962     }
3963     frameNode->OnSyncGeometryFrameFinish(rect);
3964     ElementRegister::GetInstance()->ReSyncGeometryTransition(GetHost());
3965 }
3966 
OnPositionUpdate(const OffsetT<Dimension> &)3967 void RosenRenderContext::OnPositionUpdate(const OffsetT<Dimension>& /*value*/)
3968 {
3969     auto frameNode = GetHost();
3970     CHECK_NULL_VOID(frameNode);
3971 
3972     auto pipeline = frameNode->GetContext();
3973     CHECK_NULL_VOID(pipeline);
3974     pipeline->SetAreaChangeNodeMinDepth(frameNode->GetDepth());
3975 
3976     SetPositionToRSNode();
3977 }
3978 
OnPositionEdgesUpdate(const EdgesParam &)3979 void RosenRenderContext::OnPositionEdgesUpdate(const EdgesParam& /*value*/)
3980 {
3981     SetPositionToRSNode();
3982 }
3983 
OnOffsetUpdate(const OffsetT<Dimension> &)3984 void RosenRenderContext::OnOffsetUpdate(const OffsetT<Dimension>& /*value*/)
3985 {
3986     SetPositionToRSNode();
3987 }
3988 
OnOffsetEdgesUpdate(const EdgesParam &)3989 void RosenRenderContext::OnOffsetEdgesUpdate(const EdgesParam& /*value*/)
3990 {
3991     SetPositionToRSNode();
3992 }
3993 
OnAnchorUpdate(const OffsetT<Dimension> &)3994 void RosenRenderContext::OnAnchorUpdate(const OffsetT<Dimension>& /*value*/)
3995 {
3996     SetPositionToRSNode();
3997 }
3998 
RecalculatePosition()3999 void RosenRenderContext::RecalculatePosition()
4000 {
4001     SetPositionToRSNode();
4002 }
4003 
OnZIndexUpdate(int32_t value)4004 void RosenRenderContext::OnZIndexUpdate(int32_t value)
4005 {
4006     CHECK_NULL_VOID(rsNode_);
4007     // When zindex is combined with transform/rotate, zindex has the action of controlling camera height
4008     rsNode_->SetPositionZApplicableCamera3D(Container::LessThanAPITargetVersion(PlatformVersion::VERSION_FOURTEEN));
4009     rsNode_->SetPositionZ(static_cast<float>(value));
4010     auto uiNode = GetHost();
4011     CHECK_NULL_VOID(uiNode);
4012     auto parent = uiNode->GetAncestorNodeOfFrame(true);
4013     CHECK_NULL_VOID(parent);
4014     parent->MarkNeedSyncRenderTree();
4015     auto task = [weak = WeakClaim(AceType::RawPtr(parent))]() {
4016         auto parent = weak.Upgrade();
4017         CHECK_NULL_VOID(parent);
4018         parent->RebuildRenderContextTree();
4019     };
4020     auto pipeline = parent->GetContext();
4021     CHECK_NULL_VOID(pipeline);
4022     if (pipeline->IsLayouting()) {
4023         pipeline->AddAfterLayoutTask(std::move(task));
4024         return;
4025     }
4026     task();
4027 }
4028 
ResetBlendBgColor()4029 void RosenRenderContext::ResetBlendBgColor()
4030 {
4031     CHECK_NULL_VOID(rsNode_);
4032     blendColor_ = Color::TRANSPARENT;
4033     auto blendColor =
4034         GetBackgroundColor().value_or(Color::TRANSPARENT).BlendColor(blendColor_).BlendColor(hoveredColor_);
4035     OHOS::Rosen::RSColor rsColor;
4036     ColorToRSColor(blendColor, rsColor);
4037     rsNode_->SetBackgroundColor(rsColor);
4038     RequestNextFrame();
4039 }
4040 
BlendBgColor(const Color & color)4041 void RosenRenderContext::BlendBgColor(const Color& color)
4042 {
4043     CHECK_NULL_VOID(rsNode_);
4044     blendColor_ = color;
4045     auto blendColor =
4046         GetBackgroundColor().value_or(Color::TRANSPARENT).BlendColor(blendColor_).BlendColor(hoveredColor_);
4047     OHOS::Rosen::RSColor rsColor;
4048     ColorToRSColor(blendColor, rsColor);
4049     rsNode_->SetBackgroundColor(rsColor);
4050     RequestNextFrame();
4051 }
4052 
ResetBlendBorderColor()4053 void RosenRenderContext::ResetBlendBorderColor()
4054 {
4055     CHECK_NULL_VOID(rsNode_);
4056     auto leftColor = (Color::TRANSPARENT).GetValue();
4057     auto topColor = (Color::TRANSPARENT).GetValue();
4058     auto rightColor = (Color::TRANSPARENT).GetValue();
4059     auto bottomColor = (Color::TRANSPARENT).GetValue();
4060     if (GetBorderColor().has_value()) {
4061         leftColor = GetBorderColor()->leftColor.value_or(Color::TRANSPARENT).GetValue();
4062         topColor = GetBorderColor()->topColor.value_or(Color::TRANSPARENT).GetValue();
4063         rightColor = GetBorderColor()->rightColor.value_or(Color::TRANSPARENT).GetValue();
4064         bottomColor = GetBorderColor()->bottomColor.value_or(Color::TRANSPARENT).GetValue();
4065     }
4066     rsNode_->SetBorderColor(leftColor, topColor, rightColor, bottomColor);
4067     RequestNextFrame();
4068 }
4069 
BlendBorderColor(const Color & color)4070 void RosenRenderContext::BlendBorderColor(const Color& color)
4071 {
4072     CHECK_NULL_VOID(rsNode_);
4073     auto leftColor = color.GetValue();
4074     auto topColor = color.GetValue();
4075     auto rightColor = color.GetValue();
4076     auto bottomColor = color.GetValue();
4077     if (GetBorderColor().has_value()) {
4078         leftColor = (GetBorderColor()->leftColor.value_or(Color::TRANSPARENT).BlendColor(color)).GetValue();
4079         topColor = (GetBorderColor()->topColor.value_or(Color::TRANSPARENT).BlendColor(color)).GetValue();
4080         rightColor = (GetBorderColor()->rightColor.value_or(Color::TRANSPARENT).BlendColor(color)).GetValue();
4081         bottomColor = (GetBorderColor()->bottomColor.value_or(Color::TRANSPARENT).BlendColor(color)).GetValue();
4082     }
4083     rsNode_->SetBorderColor(leftColor, topColor, rightColor, bottomColor);
4084     RequestNextFrame();
4085 }
4086 
PaintFocusState(const RoundRect & paintRect,const Color & paintColor,const Dimension & paintWidth,bool isAccessibilityFocus,bool isFocusBoxGlow)4087 void RosenRenderContext::PaintFocusState(const RoundRect& paintRect, const Color& paintColor,
4088     const Dimension& paintWidth, bool isAccessibilityFocus, bool isFocusBoxGlow)
4089 {
4090 #ifndef IS_RELEASE_VERSION
4091     TAG_LOGD(AceLogTag::ACE_FOCUS,
4092         "PaintFocusState rect is (%{public}f, %{public}f, %{public}f, %{public}f). Color is %{public}s, PainWidth is "
4093         "%{public}s",
4094         paintRect.GetRect().Left(), paintRect.GetRect().Top(), paintRect.GetRect().Width(),
4095         paintRect.GetRect().Height(), paintColor.ColorToString().c_str(), paintWidth.ToString().c_str());
4096 #endif
4097     CHECK_NULL_VOID(paintRect.GetRect().IsValid());
4098     CHECK_NULL_VOID(rsNode_);
4099     auto borderWidthPx = static_cast<float>(paintWidth.ConvertToPx());
4100     isFocusBoxGlow_ = isFocusBoxGlow;
4101     if (isAccessibilityFocus) {
4102         InitAccessibilityFocusModidifer(paintRect, paintColor, borderWidthPx);
4103         auto host = GetHost();
4104         if (host && host->GetTag() != V2::ACCESSIBILITY_FOCUS_PAINT_NODE_TAG) {
4105             UpdateDrawRegion(
4106                 DRAW_REGION_ACCESSIBILITY_FOCUS_MODIFIER_INDEX, accessibilityFocusStateModifier_->GetOverlayRect());
4107         }
4108         rsNode_->AddModifier(accessibilityFocusStateModifier_);
4109         accessibilityFocusStateModifier_->AttachAnimationRectProperty();
4110         RequestNextFrame();
4111         return;
4112     }
4113     if (!isFocusBoxGlow_) {
4114         InitFocusStateModidifer(paintRect, paintColor, borderWidthPx);
4115         UpdateDrawRegion(DRAW_REGION_FOCUS_MODIFIER_INDEX, focusStateModifier_->GetOverlayRect());
4116         rsNode_->AddModifier(focusStateModifier_);
4117         focusStateModifier_->AttachAnimationRectProperty();
4118     } else {
4119         InitFocusAnimationModidifer(paintRect, paintColor, borderWidthPx);
4120         UpdateDrawRegion(DRAW_REGION_FOCUS_MODIFIER_INDEX, focusAnimationModifier_->GetOverlayRect());
4121         auto modifierAdapter =
4122             std::static_pointer_cast<OverlayModifierAdapter>(ConvertOverlayModifier(focusAnimationModifier_));
4123         rsNode_->AddModifier(modifierAdapter);
4124         modifierAdapter->AttachProperties();
4125         focusAnimationModifier_->StartFocusAnimation();
4126     }
4127     RequestNextFrame();
4128 }
4129 
InitAccessibilityFocusModidifer(const RoundRect & paintRect,const Color & paintColor,float borderWidthPx)4130 void RosenRenderContext::InitAccessibilityFocusModidifer(
4131     const RoundRect& paintRect, const Color& paintColor, float borderWidthPx)
4132 {
4133     auto frameNode = GetHost();
4134     if (!accessibilityFocusStateModifier_) {
4135         accessibilityFocusStateModifier_ = std::make_shared<FocusStateModifier>();
4136     }
4137     rsNode_->AddModifier(accessibilityFocusStateModifier_);
4138     accessibilityFocusStateModifier_->SetRoundRect(paintRect, borderWidthPx);
4139     accessibilityFocusStateModifier_->SetPaintColor(paintColor);
4140     accessibilityFocusStateModifier_->SetFrameNode(frameNode);
4141     accessibilityFocusStateModifier_->SetNoNeedUICaptured(true);
4142 }
4143 
InitFocusStateModidifer(const RoundRect & paintRect,const Color & paintColor,float borderWidthPx)4144 void RosenRenderContext::InitFocusStateModidifer(
4145     const RoundRect& paintRect, const Color& paintColor, float borderWidthPx)
4146 {
4147     auto frameNode = GetHost();
4148     if (!focusStateModifier_) {
4149         focusStateModifier_ = std::make_shared<FocusStateModifier>();
4150     }
4151     focusStateModifier_->SetRoundRect(paintRect, borderWidthPx);
4152     focusStateModifier_->SetPaintColor(paintColor);
4153     focusStateModifier_->SetFrameNode(frameNode);
4154 }
4155 
InitFocusAnimationModidifer(const RoundRect & paintRect,const Color & paintColor,float borderWidthPx)4156 void RosenRenderContext::InitFocusAnimationModidifer(
4157     const RoundRect& paintRect, const Color& paintColor, float borderWidthPx)
4158 {
4159     auto frameNode = GetHost();
4160     if (!focusAnimationModifier_) {
4161         focusAnimationModifier_ = AceType::MakeRefPtr<FocusAnimationModifier>();
4162     }
4163     focusAnimationModifier_->SetRoundRect(paintRect, borderWidthPx);
4164     focusAnimationModifier_->SetPaintColor(paintColor);
4165     focusAnimationModifier_->SetFrameNode(frameNode);
4166 }
4167 
PaintFocusState(const RoundRect & paintRect,const Dimension & focusPaddingVp,const Color & paintColor,const Dimension & paintWidth,const PaintFocusExtraInfo & paintFocusExtraInfo)4168 void RosenRenderContext::PaintFocusState(const RoundRect& paintRect, const Dimension& focusPaddingVp,
4169     const Color& paintColor, const Dimension& paintWidth, const PaintFocusExtraInfo& paintFocusExtraInfo)
4170 {
4171     auto paintWidthPx = static_cast<float>(paintWidth.ConvertToPx());
4172     auto borderPaddingPx = static_cast<float>(focusPaddingVp.ConvertToPx());
4173     auto focusPaintRectLeft = paintRect.GetRect().Left() - borderPaddingPx - paintWidthPx / 2;
4174     auto focusPaintRectTop = paintRect.GetRect().Top() - borderPaddingPx - paintWidthPx / 2;
4175     auto focusPaintRectWidth = paintRect.GetRect().Width() + 2 * borderPaddingPx + paintWidthPx;
4176     auto focusPaintRectHeight = paintRect.GetRect().Height() + 2 * borderPaddingPx + paintWidthPx;
4177 
4178     EdgeF diffRadius = { borderPaddingPx + paintWidthPx / 2, borderPaddingPx + paintWidthPx / 2 };
4179     auto focusPaintCornerTopLeft = paintRect.GetCornerRadius(RoundRect::CornerPos::TOP_LEFT_POS) + diffRadius;
4180     auto focusPaintCornerTopRight = paintRect.GetCornerRadius(RoundRect::CornerPos::TOP_RIGHT_POS) + diffRadius;
4181     auto focusPaintCornerBottomLeft = paintRect.GetCornerRadius(RoundRect::CornerPos::BOTTOM_LEFT_POS) + diffRadius;
4182     auto focusPaintCornerBottomRight = paintRect.GetCornerRadius(RoundRect::CornerPos::BOTTOM_RIGHT_POS) + diffRadius;
4183 
4184     RoundRect focusPaintRect;
4185     focusPaintRect.SetRect(RectF(focusPaintRectLeft, focusPaintRectTop, focusPaintRectWidth, focusPaintRectHeight));
4186     focusPaintRect.SetCornerRadius(
4187         RoundRect::CornerPos::TOP_LEFT_POS, focusPaintCornerTopLeft.x, focusPaintCornerTopLeft.y);
4188     focusPaintRect.SetCornerRadius(
4189         RoundRect::CornerPos::TOP_RIGHT_POS, focusPaintCornerTopRight.x, focusPaintCornerTopRight.y);
4190     focusPaintRect.SetCornerRadius(
4191         RoundRect::CornerPos::BOTTOM_LEFT_POS, focusPaintCornerBottomLeft.x, focusPaintCornerBottomLeft.y);
4192     focusPaintRect.SetCornerRadius(
4193         RoundRect::CornerPos::BOTTOM_RIGHT_POS, focusPaintCornerBottomRight.x, focusPaintCornerBottomRight.y);
4194 
4195     PaintFocusState(focusPaintRect, paintColor, paintWidth, paintFocusExtraInfo.isAccessibilityFocus,
4196         paintFocusExtraInfo.isFocusBoxGlow);
4197 }
4198 
PaintFocusState(const Dimension & focusPaddingVp,const Color & paintColor,const Dimension & paintWidth,bool isFocusBoxGlow)4199 void RosenRenderContext::PaintFocusState(
4200     const Dimension& focusPaddingVp, const Color& paintColor, const Dimension& paintWidth, bool isFocusBoxGlow)
4201 {
4202     CHECK_NULL_VOID(rsNode_);
4203     const auto& bounds = rsNode_->GetStagingProperties().GetBounds();
4204     const auto& radius = rsNode_->GetStagingProperties().GetCornerRadius();
4205 
4206     RoundRect frameRect;
4207     frameRect.SetRect(RectF(0, 0, bounds.z_, bounds.w_));
4208     frameRect.SetCornerRadius(RoundRect::CornerPos::TOP_LEFT_POS, radius.x_, radius.x_);
4209     frameRect.SetCornerRadius(RoundRect::CornerPos::TOP_RIGHT_POS, radius.y_, radius.y_);
4210     frameRect.SetCornerRadius(RoundRect::CornerPos::BOTTOM_RIGHT_POS, radius.z_, radius.z_);
4211     frameRect.SetCornerRadius(RoundRect::CornerPos::BOTTOM_LEFT_POS, radius.w_, radius.w_);
4212 
4213     PaintFocusState(frameRect, focusPaddingVp, paintColor, paintWidth, { false, isFocusBoxGlow });
4214 }
4215 
ClearFocusState()4216 void RosenRenderContext::ClearFocusState()
4217 {
4218     TAG_LOGD(AceLogTag::ACE_FOCUS, "Clear focus state.");
4219     CHECK_NULL_VOID(rsNode_);
4220     auto context = PipelineBase::GetCurrentContext();
4221     CHECK_NULL_VOID(context);
4222     if (!isFocusBoxGlow_) {
4223         CHECK_NULL_VOID(focusStateModifier_);
4224         UpdateDrawRegion(DRAW_REGION_FOCUS_MODIFIER_INDEX, focusStateModifier_->GetOverlayRect());
4225         rsNode_->RemoveModifier(focusStateModifier_);
4226         RequestNextFrame();
4227         return;
4228     }
4229     CHECK_NULL_VOID(focusAnimationModifier_);
4230     focusAnimationModifier_->StopFocusAnimation();
4231     UpdateDrawRegion(DRAW_REGION_FOCUS_MODIFIER_INDEX, focusAnimationModifier_->GetOverlayRect());
4232     auto modifierAdapter =
4233         std::static_pointer_cast<OverlayModifierAdapter>(ConvertOverlayModifier(focusAnimationModifier_));
4234     rsNode_->RemoveModifier(modifierAdapter);
4235     RequestNextFrame();
4236 }
4237 
FlushContentDrawFunction(CanvasDrawFunction && contentDraw)4238 void RosenRenderContext::FlushContentDrawFunction(CanvasDrawFunction&& contentDraw)
4239 {
4240     CHECK_NULL_VOID(rsNode_);
4241     CHECK_NULL_VOID(contentDraw);
4242     rsNode_->DrawOnNode(
4243         Rosen::RSModifierType::CONTENT_STYLE,
4244         [contentDraw = std::move(contentDraw)](std::shared_ptr<RSCanvas> canvas) {
4245             CHECK_NULL_VOID(canvas);
4246             contentDraw(*canvas);
4247         });
4248 }
4249 
FlushContentModifier(const RefPtr<Modifier> & modifier)4250 void RosenRenderContext::FlushContentModifier(const RefPtr<Modifier>& modifier)
4251 {
4252     CHECK_NULL_VOID(rsNode_);
4253     CHECK_NULL_VOID(modifier);
4254     auto modifierAdapter = std::static_pointer_cast<ContentModifierAdapter>(ConvertContentModifier(modifier));
4255     auto contentModifier = AceType::DynamicCast<ContentModifier>(modifier);
4256     CHECK_NULL_VOID(contentModifier);
4257     auto rect = contentModifier->GetBoundsRect();
4258     if (rect.has_value()) {
4259         std::shared_ptr<Rosen::RectF> overlayRect =
4260             std::make_shared<Rosen::RectF>(rect->GetX(), rect->GetY(), rect->Width(), rect->Height());
4261         UpdateDrawRegion(DRAW_REGION_CONTENT_MODIFIER_INDEX, overlayRect);
4262     }
4263     rsNode_->SetIsCustomTextType(contentModifier->GetIsCustomFont());
4264     rsNode_->AddModifier(modifierAdapter);
4265     modifierAdapter->AttachProperties();
4266 }
4267 
FlushKitContentModifier(const RefPtr<Kit::Modifier> & modifier)4268 void RosenRenderContext::FlushKitContentModifier(const RefPtr<Kit::Modifier>& modifier)
4269 {
4270     CHECK_NULL_VOID(rsNode_);
4271     CHECK_NULL_VOID(modifier);
4272 
4273     auto modifierAdapter = ConvertKitContentModifier(modifier);
4274     rsNode_->AddModifier(modifierAdapter);
4275     modifier->OnAttached();
4276 }
4277 
FlushForegroundDrawFunction(CanvasDrawFunction && foregroundDraw)4278 void RosenRenderContext::FlushForegroundDrawFunction(CanvasDrawFunction&& foregroundDraw)
4279 {
4280     CHECK_NULL_VOID(rsNode_);
4281     CHECK_NULL_VOID(foregroundDraw);
4282     rsNode_->DrawOnNode(Rosen::RSModifierType::FOREGROUND_STYLE,
4283         [foregroundDraw = std::move(foregroundDraw)](std::shared_ptr<RSCanvas> canvas) {
4284             CHECK_NULL_VOID(canvas);
4285             foregroundDraw(*canvas);
4286         });
4287 }
4288 
FlushOverlayDrawFunction(CanvasDrawFunction && overlayDraw)4289 void RosenRenderContext::FlushOverlayDrawFunction(CanvasDrawFunction&& overlayDraw)
4290 {
4291     CHECK_NULL_VOID(rsNode_);
4292     CHECK_NULL_VOID(overlayDraw);
4293     rsNode_->DrawOnNode(
4294         Rosen::RSModifierType::OVERLAY_STYLE,
4295         [overlayDraw = std::move(overlayDraw)](std::shared_ptr<RSCanvas> canvas) {
4296             CHECK_NULL_VOID(canvas);
4297             overlayDraw(*canvas);
4298         });
4299 }
4300 
FlushOverlayModifier(const RefPtr<Modifier> & modifier)4301 void RosenRenderContext::FlushOverlayModifier(const RefPtr<Modifier>& modifier)
4302 {
4303     CHECK_NULL_VOID(rsNode_);
4304     CHECK_NULL_VOID(modifier);
4305     auto modifierAdapter = std::static_pointer_cast<OverlayModifierAdapter>(ConvertOverlayModifier(modifier));
4306     auto overlayModifier = AceType::DynamicCast<OverlayModifier>(modifier);
4307     CHECK_NULL_VOID(overlayModifier);
4308     auto rect = overlayModifier->GetBoundsRect();
4309     std::shared_ptr<Rosen::RectF> overlayRect =
4310         std::make_shared<Rosen::RectF>(rect.GetX(), rect.GetY(), rect.Width(), rect.Height());
4311     UpdateDrawRegion(DRAW_REGION_OVERLAY_MODIFIER_INDEX, overlayRect);
4312     rsNode_->AddModifier(modifierAdapter);
4313     modifierAdapter->AttachProperties();
4314 }
4315 
FlushForegroundModifier(const RefPtr<Modifier> & modifier)4316 void RosenRenderContext::FlushForegroundModifier(const RefPtr<Modifier>& modifier)
4317 {
4318     CHECK_NULL_VOID(rsNode_);
4319     CHECK_NULL_VOID(modifier);
4320     auto modifierAdapter = std::static_pointer_cast<ForegroundModifierAdapter>(ConvertForegroundModifier(modifier));
4321     auto foregroundModifier = AceType::DynamicCast<ForegroundModifier>(modifier);
4322     CHECK_NULL_VOID(foregroundModifier);
4323     auto rect = foregroundModifier->GetBoundsRect();
4324     std::shared_ptr<Rosen::RectF> foregroundRect =
4325         std::make_shared<Rosen::RectF>(rect.GetX(), rect.GetY(), rect.Width(), rect.Height());
4326     UpdateDrawRegion(DRAW_REGION_OVERLAY_MODIFIER_INDEX, foregroundRect);
4327     rsNode_->AddModifier(modifierAdapter);
4328     modifierAdapter->AttachProperties();
4329 }
4330 
GetRSNode()4331 const std::shared_ptr<Rosen::RSNode>& RosenRenderContext::GetRSNode()
4332 {
4333     return rsNode_;
4334 }
4335 
RebuildFrame(FrameNode *,const std::list<RefPtr<FrameNode>> & children)4336 void RosenRenderContext::RebuildFrame(FrameNode* /*self*/, const std::list<RefPtr<FrameNode>>& children)
4337 {
4338     ReCreateRsNodeTree(children);
4339     RequestNextFrame();
4340 }
4341 
GetChildrenRSNodes(const std::list<RefPtr<FrameNode>> & frameChildren,std::unordered_map<Rosen::RSNode::SharedPtr,bool> & nodeMap)4342 std::vector<std::shared_ptr<Rosen::RSNode>> RosenRenderContext::GetChildrenRSNodes(
4343     const std::list<RefPtr<FrameNode>>& frameChildren, std::unordered_map<Rosen::RSNode::SharedPtr, bool>& nodeMap)
4344 {
4345     std::vector<std::shared_ptr<Rosen::RSNode>> rsNodes;
4346     for (const auto& child : frameChildren) {
4347         if (!child) {
4348             continue;
4349         }
4350         auto rosenRenderContext = DynamicCast<RosenRenderContext>(child->renderContext_);
4351         if (!rosenRenderContext) {
4352             continue;
4353         }
4354         auto rsnode = rosenRenderContext->GetRSNode();
4355         if (!rsnode) {
4356             continue;
4357         }
4358         auto result = nodeMap.try_emplace(rsnode, false);
4359         if (result.second) {
4360             rsNodes.emplace_back(rsnode);
4361         }
4362     }
4363     return rsNodes;
4364 }
4365 
SetDrawNode()4366 void RosenRenderContext::SetDrawNode()
4367 {
4368     CHECK_NULL_VOID(rsNode_);
4369     rsNode_->SetDrawNode();
4370 }
4371 
AddNodeToRsTree()4372 bool RosenRenderContext::AddNodeToRsTree()
4373 {
4374     auto node = GetHost();
4375     if (!node || !node->GetIsDelete()) {
4376         return true;
4377     }
4378     if (SystemProperties::GetDebugEnabled()) {
4379         TAG_LOGD(AceLogTag::ACE_DEFAULT_DOMAIN, "AddNodeToRsTree node(%{public}d, %{public}s)", node->GetId(),
4380             node->GetTag().c_str());
4381     }
4382     if (node->GetRenderContext()) {
4383         node->GetRenderContext()->SetRSUIContext(node->GetContext());
4384     }
4385     std::list<RefPtr<FrameNode>> childNodes;
4386     // get not be deleted children of node
4387     GetLiveChildren(node, childNodes);
4388 
4389     auto rsNode = GetRsNodeByFrame(node);
4390     CHECK_NULL_RETURN(rsNode, false);
4391 
4392     size_t rsNodeIndex = rsNode->GetChildren().size();
4393     for (auto& child : childNodes) {
4394         auto childRsNode = GetRsNodeByFrame(child);
4395         rsNode->AddChild(childRsNode, rsNodeIndex);
4396         rsNodeIndex++;
4397     }
4398     node->SetDeleteRsNode(false);
4399     // rebuild parent node
4400     auto parentNode = node->GetParentFrameNode();
4401     CHECK_NULL_RETURN(parentNode, false);
4402     parentNode->MarkNeedSyncRenderTree();
4403     parentNode->RebuildRenderContextTree();
4404     return true;
4405 }
4406 
GetRsNodeByFrame(const RefPtr<FrameNode> & frameNode)4407 std::shared_ptr<Rosen::RSNode> RosenRenderContext::GetRsNodeByFrame(const RefPtr<FrameNode>& frameNode)
4408 {
4409     if (!frameNode) {
4410         return nullptr;
4411     }
4412     auto rosenRenderContext = DynamicCast<RosenRenderContext>(frameNode->renderContext_);
4413     if (!rosenRenderContext) {
4414         return nullptr;
4415     }
4416     auto rsnode = rosenRenderContext->GetRSNode();
4417     return rsnode;
4418 }
4419 
CanNodeBeDeleted(const RefPtr<FrameNode> & node) const4420 bool RosenRenderContext::CanNodeBeDeleted(const RefPtr<FrameNode>& node) const
4421 {
4422     CHECK_NULL_RETURN(node, false);
4423     auto rsNode = GetRsNodeByFrame(node);
4424     CHECK_NULL_RETURN(rsNode, false);
4425     std::list <RefPtr<FrameNode>> childChildrenList;
4426     node->GenerateOneDepthVisibleFrameWithTransition(childChildrenList);
4427     if (rsNode->GetIsDrawn() || rsNode->GetType() != Rosen::RSUINodeType::CANVAS_NODE
4428         || childChildrenList.empty() || node->GetTag() == V2::PAGE_ETS_TAG
4429         || node->GetTag() == V2::STAGE_ETS_TAG) {
4430         return false;
4431     }
4432     return true;
4433 }
4434 
GetLiveChildren(const RefPtr<FrameNode> & node,std::list<RefPtr<FrameNode>> & childNodes)4435 void RosenRenderContext::GetLiveChildren(const RefPtr<FrameNode>& node, std::list<RefPtr<FrameNode>>& childNodes)
4436 {
4437     CHECK_NULL_VOID(node);
4438     std::list<RefPtr<FrameNode>> childrenList;
4439     auto pipeline = node->GetContext();
4440     CHECK_NULL_VOID(pipeline);
4441     node->GenerateOneDepthVisibleFrameWithTransition(childrenList);
4442     for (auto& child : childrenList) {
4443         if (!CanNodeBeDeleted(child)) {
4444             childNodes.emplace_back(child);
4445             if (pipeline && child->HasPositionZ()) {
4446                 pipeline->AddPositionZNode(child->GetId());
4447             }
4448         } else {
4449             child->SetDeleteRsNode(true);
4450             GetLiveChildren(child, childNodes);
4451         }
4452     }
4453     auto accessibilityFocusPaintNode = node->GetFocusPaintNode();
4454     if (accessibilityFocusPaintNode) {
4455         childNodes.emplace_back(accessibilityFocusPaintNode);
4456         if (accessibilityFocusPaintNode->HasPositionZ()) {
4457             pipeline->AddPositionZNode(accessibilityFocusPaintNode->GetId());
4458         }
4459     }
4460     auto overlayNode = node->GetOverlayNode();
4461     CHECK_NULL_VOID(overlayNode);
4462     auto property = overlayNode->GetLayoutProperty();
4463     if (property && property->GetVisibilityValue(VisibleType::VISIBLE) == VisibleType::VISIBLE) {
4464         if (!CanNodeBeDeleted(overlayNode)) {
4465             childNodes.emplace_back(overlayNode);
4466             if (pipeline && overlayNode->HasPositionZ()) {
4467                 pipeline->AddPositionZNode(overlayNode->GetId());
4468             }
4469         } else {
4470             overlayNode->SetDeleteRsNode(true);
4471             GetLiveChildren(overlayNode, childNodes);
4472         }
4473     }
4474 }
4475 
AddRsNodeForCapture()4476 void RosenRenderContext::AddRsNodeForCapture()
4477 {
4478     CHECK_NULL_VOID(rsNode_);
4479     auto host = GetHost();
4480     if (host && host->GetIsDelete()) {
4481         rsNode_->SetDrawNode();
4482         auto pipeline = host->GetContext();
4483         if (pipeline) {
4484             pipeline->FlushMessages();
4485         }
4486     }
4487 }
4488 
RemoveFromTree()4489 void RosenRenderContext::RemoveFromTree()
4490 {
4491     CHECK_NULL_VOID(rsNode_);
4492     rsNode_->RemoveFromTree();
4493 }
4494 
ReCreateRsNodeTree(const std::list<RefPtr<FrameNode>> & children)4495 void RosenRenderContext::ReCreateRsNodeTree(const std::list<RefPtr<FrameNode>>& children)
4496 {
4497     if (!rsNode_ || !isNeedRebuildRSTree_) {
4498         return;
4499     }
4500     auto childNodesNew = children;
4501     if (SystemProperties::GetContainerDeleteFlag()) {
4502         auto frameNode = GetHost();
4503         if (frameNode->GetIsDelete()) {
4504             return;
4505         }
4506         childNodesNew.clear();
4507         GetLiveChildren(frameNode, childNodesNew);
4508     }
4509     // now rsNode's children, key is id of rsNode, value means whether the node exists in previous children of rsNode.
4510     std::unordered_map<Rosen::RSNode::SharedPtr, bool> childNodeMap;
4511     auto nowRSNodes = GetChildrenRSNodes(childNodesNew, childNodeMap);
4512     std::vector<Rosen::RSNode::SharedPtr> childNodes;
4513     for (auto child : rsNode_->GetChildren()) {
4514         if (child.lock()) {
4515             childNodes.emplace_back(child.lock());
4516         }
4517     }
4518     if (nowRSNodes == childNodes) {
4519         return;
4520     }
4521     if (nowRSNodes.empty()) {
4522         rsNode_->ClearChildren();
4523         return;
4524     }
4525     // save a copy of previous children because for loop will delete child
4526     auto preChildNodes = rsNode_->GetChildren();
4527     for (auto node : preChildNodes) {
4528         if (node.lock() == nullptr) {
4529             continue;
4530         }
4531         auto iter = childNodeMap.find(node.lock());
4532         if (iter == childNodeMap.end()) {
4533             rsNode_->RemoveChildByNodeSelf(node);
4534         } else {
4535             iter->second = true;
4536         }
4537     }
4538     for (size_t index = 0; index != nowRSNodes.size(); ++index) {
4539         auto node = rsNode_->GetChildByIndex(index);
4540         if (node != nowRSNodes[index]) {
4541             auto iter = childNodeMap.find(nowRSNodes[index]);
4542             if (iter == childNodeMap.end()) {
4543                 continue;
4544             }
4545             if (iter->second) {
4546                 rsNode_->MoveChild(nowRSNodes[index], index);
4547             } else {
4548                 rsNode_->AddChild(nowRSNodes[index], index);
4549             }
4550         }
4551     }
4552 }
4553 
AddFrameChildren(FrameNode *,const std::list<RefPtr<FrameNode>> & children)4554 void RosenRenderContext::AddFrameChildren(FrameNode* /*self*/, const std::list<RefPtr<FrameNode>>& children)
4555 {
4556     CHECK_NULL_VOID(rsNode_);
4557     for (const auto& child : children) {
4558         if (!child) {
4559             continue;
4560         }
4561         auto rosenRenderContext = DynamicCast<RosenRenderContext>(child->renderContext_);
4562         if (!rosenRenderContext) {
4563             continue;
4564         }
4565         auto rsNode = rosenRenderContext->GetRSNode();
4566         if (rsNode) {
4567             rsNode_->AddChild(rsNode, -1);
4568         }
4569     }
4570 }
4571 
RemoveFrameChildren(FrameNode *,const std::list<RefPtr<FrameNode>> & children)4572 void RosenRenderContext::RemoveFrameChildren(FrameNode* /*self*/, const std::list<RefPtr<FrameNode>>& children)
4573 {
4574     CHECK_NULL_VOID(rsNode_);
4575     for (const auto& child : children) {
4576         if (!child) {
4577             continue;
4578         }
4579         auto rosenRenderContext = DynamicCast<RosenRenderContext>(child->renderContext_);
4580         if (!rosenRenderContext) {
4581             continue;
4582         }
4583         auto rsNode = rosenRenderContext->GetRSNode();
4584         if (rsNode) {
4585             rsNode_->RemoveChild(rsNode);
4586         }
4587     }
4588 }
4589 
MoveFrame(FrameNode *,const RefPtr<FrameNode> & child,int32_t index)4590 void RosenRenderContext::MoveFrame(FrameNode* /*self*/, const RefPtr<FrameNode>& child, int32_t index)
4591 {
4592     CHECK_NULL_VOID(rsNode_);
4593     CHECK_NULL_VOID(child);
4594     auto rosenRenderContext = DynamicCast<RosenRenderContext>(child->renderContext_);
4595     CHECK_NULL_VOID(rosenRenderContext);
4596     auto rsNode = rosenRenderContext->GetRSNode();
4597     // no need to check nullptr since MoveChild will take care of it
4598     rsNode_->MoveChild(rsNode, index);
4599 }
4600 
AnimateHoverEffectScale(bool isHovered)4601 void RosenRenderContext::AnimateHoverEffectScale(bool isHovered)
4602 {
4603 #ifdef ACE_STATIC
4604     FREE_NODE_CHECK(GetHost(), AnimateHoverEffectScale, isHovered);
4605 #endif
4606     if ((isHovered && isHoveredScale_) || (!isHovered && !isHoveredScale_)) {
4607         return;
4608     }
4609     CHECK_NULL_VOID(rsNode_);
4610     auto pipeline = PipelineBase::GetCurrentContext();
4611     CHECK_NULL_VOID(pipeline);
4612     auto appTheme = pipeline->GetTheme<AppTheme>();
4613     CHECK_NULL_VOID(appTheme);
4614 
4615     float hoverScaleFrom = isHovered ? appTheme->GetHoverScaleStart() : appTheme->GetHoverScaleEnd();
4616     float hoverColorTo = isHovered ? appTheme->GetHoverScaleEnd() : appTheme->GetHoverScaleStart();
4617     float scaleStart = hoverScaleFrom;
4618     float scaleEnd = hoverColorTo;
4619     int32_t themeDuration = appTheme->GetHoverDuration();
4620 
4621     SetScale(scaleStart, scaleStart);
4622     Rosen::RSAnimationTimingProtocol protocol;
4623     protocol.SetDuration(themeDuration);
4624     auto rsUIContext = rsNode_->GetRSUIContext();
4625     RSNode::Animate(rsUIContext, protocol, Rosen::RSAnimationTimingCurve::CreateCubicCurve(0.2f, 0.0f, 0.2f, 1.0f),
4626         [this, scaleEnd]() { SetScale(scaleEnd, scaleEnd); });
4627     isHoveredScale_ = isHovered;
4628 }
4629 
AnimateHoverEffectBoard(bool isHovered)4630 void RosenRenderContext::AnimateHoverEffectBoard(bool isHovered)
4631 {
4632 #ifdef ACE_STATIC
4633     FREE_NODE_CHECK(GetHost(), AnimateHoverEffectBoard, isHovered);
4634 #endif
4635     if ((isHovered && isHoveredBoard_) || (!isHovered && !isHoveredBoard_)) {
4636         return;
4637     }
4638     CHECK_NULL_VOID(rsNode_);
4639     auto pipeline = PipelineBase::GetCurrentContext();
4640     CHECK_NULL_VOID(pipeline);
4641     auto appTheme = pipeline->GetTheme<AppTheme>();
4642     CHECK_NULL_VOID(appTheme);
4643 
4644     Color hoverColorFrom = isHovered ? appTheme->GetHoverHighlightStart() : appTheme->GetHoverHighlightEnd();
4645     Color hoverColorTo = isHovered ? appTheme->GetHoverHighlightEnd() : appTheme->GetHoverHighlightStart();
4646     Color highlightStart =
4647         GetBackgroundColor().value_or(Color::TRANSPARENT).BlendColor(blendColor_).BlendColor(hoverColorFrom);
4648     Color highlightEnd =
4649         GetBackgroundColor().value_or(Color::TRANSPARENT).BlendColor(blendColor_).BlendColor(hoverColorTo);
4650     int32_t themeDuration = appTheme->GetHoverDuration();
4651 
4652     rsNode_->SetBackgroundColor(highlightStart.GetValue());
4653     Rosen::RSAnimationTimingProtocol protocol;
4654     protocol.SetDuration(themeDuration);
4655     auto rsUIContext = rsNode_->GetRSUIContext();
4656     RSNode::Animate(rsUIContext, protocol, Rosen::RSAnimationTimingCurve::CreateCubicCurve(0.2f, 0.0f, 0.2f, 1.0f),
4657         [rsNode = rsNode_, highlightEnd]() {
4658             CHECK_NULL_VOID(rsNode);
4659             rsNode->SetBackgroundColor(highlightEnd.GetValue());
4660         });
4661     hoveredColor_ = hoverColorTo;
4662     isHoveredBoard_ = isHovered;
4663 }
4664 
UpdateBackBlurRadius(const Dimension & radius)4665 void RosenRenderContext::UpdateBackBlurRadius(const Dimension& radius)
4666 {
4667     const auto& groupProperty = GetOrCreateBackground();
4668     if (groupProperty->CheckBlurRadiusChanged(radius)) {
4669         // Same with previous value
4670         return;
4671     }
4672     groupProperty->propBlurRadius = radius;
4673     SetBackBlurFilter();
4674 }
4675 
UpdateMotionBlur(const MotionBlurOption & motionBlurOption)4676 void RosenRenderContext::UpdateMotionBlur(const MotionBlurOption& motionBlurOption)
4677 {
4678     CHECK_NULL_VOID(rsNode_);
4679     const auto& groupProperty = GetOrCreateForeground();
4680     groupProperty->propMotionBlur = motionBlurOption;
4681     Rosen::Vector2f anchor(motionBlurOption.anchor.x, motionBlurOption.anchor.y);
4682     rsNode_->SetMotionBlurPara(motionBlurOption.radius, anchor);
4683 }
4684 
UpdateBackBlur(const Dimension & radius,const BlurOption & blurOption,const SysOptions & sysOptions)4685 void RosenRenderContext::UpdateBackBlur(
4686     const Dimension& radius, const BlurOption& blurOption, const SysOptions& sysOptions)
4687 {
4688     CHECK_NULL_VOID(rsNode_);
4689     const auto& groupProperty = GetOrCreateBackground();
4690     if (groupProperty->CheckBlurRadiusChanged(radius) && groupProperty->CheckSystemAdaptationSame(sysOptions)) {
4691         // Same with previous value
4692         return;
4693     }
4694     groupProperty->propBlurRadius = radius;
4695     groupProperty->propSysOptions = sysOptions;
4696     SetBackBlurFilter();
4697     if (blurOption.grayscale.size() > 1) {
4698         Rosen::Vector2f grayScale(blurOption.grayscale[0], blurOption.grayscale[0]);
4699         rsNode_->SetGreyCoef(grayScale);
4700     }
4701 }
4702 
UpdateNodeBackBlur(const Dimension & radius,const BlurOption & blurOption)4703 void RosenRenderContext::UpdateNodeBackBlur(const Dimension& radius, const BlurOption& blurOption)
4704 {
4705     CHECK_NULL_VOID(rsNode_);
4706     const auto& groupProperty = GetOrCreateBackground();
4707     groupProperty->propBackdropBlurOption = blurOption;
4708     if (groupProperty->CheckBlurRadiusChanged(radius) && groupProperty->CheckBlurOptionChanged(blurOption)) {
4709         // Same with previous value
4710         return;
4711     }
4712     groupProperty->propBlurRadius = radius;
4713     SetBackBlurFilter();
4714     if (blurOption.grayscale.size() > 1) {
4715         Rosen::Vector2f grayScale(blurOption.grayscale[0], blurOption.grayscale[1]);
4716         rsNode_->SetGreyCoef(grayScale);
4717     }
4718 }
4719 
UpdateFrontBlurRadius(const Dimension & radius)4720 void RosenRenderContext::UpdateFrontBlurRadius(const Dimension& radius)
4721 {
4722     const auto& groupProperty = GetOrCreateForeground();
4723     if (groupProperty->CheckBlurRadiusChanged(radius)) {
4724         // Same with previous value
4725         return;
4726     }
4727     groupProperty->propBlurRadius = radius;
4728     SetFrontBlurFilter();
4729 }
4730 
UpdateFrontBlur(const Dimension & radius,const BlurOption & blurOption,const SysOptions & sysOptions)4731 void RosenRenderContext::UpdateFrontBlur(
4732     const Dimension& radius, const BlurOption& blurOption, const SysOptions& sysOptions)
4733 {
4734     CHECK_NULL_VOID(rsNode_);
4735     const auto& groupProperty = GetOrCreateForeground();
4736     if (groupProperty->CheckBlurRadiusChanged(radius) && groupProperty->CheckSysOptionsForBlurSame(sysOptions)) {
4737         // Same with previous value
4738         return;
4739     }
4740     groupProperty->propBlurRadius = radius;
4741     groupProperty->propSysOptionsForBlur = sysOptions;
4742     SetFrontBlurFilter();
4743     if (blurOption.grayscale.size() > 1) {
4744         Rosen::Vector2f grayScale(blurOption.grayscale[0], blurOption.grayscale[1]);
4745         rsNode_->SetGreyCoef(grayScale);
4746     }
4747 }
4748 
ToShadowColorStrategy(ShadowColorStrategy shadowColorStrategy)4749 Rosen::SHADOW_COLOR_STRATEGY RosenRenderContext::ToShadowColorStrategy(ShadowColorStrategy shadowColorStrategy)
4750 {
4751     if (shadowColorStrategy == ShadowColorStrategy::NONE) {
4752         return Rosen::SHADOW_COLOR_STRATEGY::COLOR_STRATEGY_NONE;
4753     } else if (shadowColorStrategy == ShadowColorStrategy::AVERAGE) {
4754         return Rosen::SHADOW_COLOR_STRATEGY::COLOR_STRATEGY_AVERAGE;
4755     } else if (shadowColorStrategy == ShadowColorStrategy::PRIMARY) {
4756         return Rosen::SHADOW_COLOR_STRATEGY::COLOR_STRATEGY_MAIN;
4757     } else {
4758         return Rosen::SHADOW_COLOR_STRATEGY::COLOR_STRATEGY_NONE;
4759     }
4760 }
4761 
OnBackShadowUpdate(const Shadow & shadow)4762 void RosenRenderContext::OnBackShadowUpdate(const Shadow& shadow)
4763 {
4764     CHECK_NULL_VOID(rsNode_);
4765     if (!shadow.IsValid()) {
4766         if (shadow.GetHardwareAcceleration()) {
4767             rsNode_->SetShadowElevation(0.0);
4768         } else {
4769             rsNode_->SetShadowRadius(0.0);
4770         }
4771         RequestNextFrame();
4772         return;
4773     }
4774     rsNode_->SetShadowColor(shadow.GetColor().GetValue());
4775     rsNode_->SetShadowOffsetX(shadow.GetOffset().GetX());
4776     rsNode_->SetShadowOffsetY(shadow.GetOffset().GetY());
4777     rsNode_->SetShadowMask(shadow.GetShadowType() == ShadowType::BLUR);
4778     rsNode_->SetShadowIsFilled(shadow.GetIsFilled());
4779     rsNode_->SetShadowColorStrategy(ToShadowColorStrategy(shadow.GetShadowColorStrategy()));
4780     if (shadow.GetHardwareAcceleration()) {
4781         rsNode_->SetShadowElevation(shadow.GetElevation());
4782     } else {
4783         rsNode_->SetShadowRadius(DrawingDecorationPainter::ConvertRadiusToSigma(shadow.GetBlurRadius()));
4784     }
4785     RequestNextFrame();
4786 }
4787 
OnBackBlendModeUpdate(BlendMode blendMode)4788 void RosenRenderContext::OnBackBlendModeUpdate(BlendMode blendMode)
4789 {
4790     CHECK_NULL_VOID(rsNode_);
4791     if (blendMode == BlendMode::BACK_COMPAT_SOURCE_IN) {
4792         rsNode_->SetBackgroundShader(nullptr);
4793         rsNode_->SetColorBlendMode(Rosen::RSColorBlendMode::NONE);
4794     } else {
4795         auto rsBlendMode = static_cast<Rosen::RSColorBlendMode>(blendMode);
4796         rsNode_->SetColorBlendMode(rsBlendMode);
4797     }
4798     RequestNextFrame();
4799 }
4800 
OnBackBlendApplyTypeUpdate(BlendApplyType blendApplyType)4801 void RosenRenderContext::OnBackBlendApplyTypeUpdate(BlendApplyType blendApplyType)
4802 {
4803     CHECK_NULL_VOID(rsNode_);
4804     if (blendApplyType == BlendApplyType::FAST) {
4805         rsNode_->SetColorBlendApplyType(Rosen::RSColorBlendApplyType::FAST);
4806     } else if (Container::LessThanAPITargetVersion(PlatformVersion::VERSION_EIGHTEEN)) {
4807         rsNode_->SetColorBlendApplyType(Rosen::RSColorBlendApplyType::SAVE_LAYER_ALPHA);
4808     } else {
4809         rsNode_->SetColorBlendApplyType(Rosen::RSColorBlendApplyType::SAVE_LAYER);
4810     }
4811     RequestNextFrame();
4812 }
4813 
UpdateBlender(const OHOS::Rosen::Blender * blender)4814 void RosenRenderContext::UpdateBlender(const OHOS::Rosen::Blender* blender)
4815 {
4816     CHECK_NULL_VOID(rsNode_);
4817     CHECK_NULL_VOID(blender);
4818     rsNode_->SetBlender(blender);
4819     RequestNextFrame();
4820 }
4821 
4822 // called when frameNode size changes
PaintGraphics()4823 void RosenRenderContext::PaintGraphics()
4824 {
4825     CHECK_NULL_VOID(rsNode_);
4826     auto&& graphicProps = GetOrCreateGraphics();
4827 
4828     if (!graphics_) {
4829         graphics_ = std::make_unique<GraphicModifiers>();
4830     }
4831     if (graphicProps->HasFrontGrayScale()) {
4832         auto grayScale = graphicProps->GetFrontGrayScaleValue();
4833         OnFrontGrayScaleUpdate(grayScale);
4834     }
4835 
4836     if (graphicProps->HasFrontBrightness()) {
4837         auto brightness = graphicProps->GetFrontBrightnessValue();
4838         OnFrontBrightnessUpdate(brightness);
4839     }
4840 
4841     if (graphicProps->HasFrontContrast()) {
4842         auto contrast = graphicProps->GetFrontContrastValue();
4843         OnFrontContrastUpdate(contrast);
4844     }
4845 
4846     if (graphicProps->HasFrontSaturate()) {
4847         auto saturate = graphicProps->GetFrontSaturateValue();
4848         OnFrontSaturateUpdate(saturate);
4849     }
4850 
4851     if (graphicProps->HasFrontSepia()) {
4852         auto sepia = graphicProps->GetFrontSepiaValue();
4853         OnFrontSepiaUpdate(sepia);
4854     }
4855 
4856     if (graphicProps->HasFrontInvert()) {
4857         auto invert = graphicProps->GetFrontInvertValue();
4858         OnFrontInvertUpdate(invert);
4859     }
4860 
4861     if (graphicProps->HasFrontHueRotate()) {
4862         auto hueRotate = graphicProps->GetFrontHueRotateValue();
4863         OnFrontHueRotateUpdate(hueRotate);
4864     }
4865 
4866     if (graphicProps->HasFrontColorBlend()) {
4867         auto colorBlend = graphicProps->GetFrontColorBlendValue();
4868         OnFrontColorBlendUpdate(colorBlend);
4869     }
4870 }
4871 
4872 // helper function to check if frame react is valid
RectIsNull()4873 bool RosenRenderContext::RectIsNull()
4874 {
4875     RectF rect = GetPaintRectWithoutTransform();
4876     return NearZero(rect.Width()) || NearZero(rect.Height());
4877 }
4878 
4879 template<typename T, typename D>
SetGraphicModifier(std::shared_ptr<T> & modifier,D data)4880 void RosenRenderContext::SetGraphicModifier(std::shared_ptr<T>& modifier, D data)
4881 {
4882     CHECK_NULL_VOID(rsNode_);
4883     if (!modifier) {
4884         modifier = std::make_shared<T>();
4885         rsNode_->AddModifier(modifier);
4886     }
4887     modifier->SetCustomData(data);
4888 
4889     auto borderRadius = GetBorderRadius();
4890     if (borderRadius.has_value()) {
4891         Rosen::Vector4f rsRadius;
4892         ConvertRadius(*borderRadius, rsRadius);
4893         modifier->SetCornerRadius(rsRadius);
4894     }
4895 }
4896 
AddModifier(const std::shared_ptr<Rosen::ModifierNG::RSModifier> & modifier)4897 void RosenRenderContext::AddModifier(const std::shared_ptr<Rosen::ModifierNG::RSModifier>& modifier)
4898 {
4899     CHECK_NULL_VOID(modifier);
4900     CHECK_NULL_VOID(rsNode_);
4901     rsNode_->AddModifier(modifier);
4902 }
4903 
RemoveModifier(const std::shared_ptr<Rosen::ModifierNG::RSModifier> & modifier)4904 void RosenRenderContext::RemoveModifier(const std::shared_ptr<Rosen::ModifierNG::RSModifier>& modifier)
4905 {
4906     CHECK_NULL_VOID(modifier);
4907     CHECK_NULL_VOID(rsNode_);
4908     rsNode_->RemoveModifier(modifier);
4909 }
4910 
4911 // helper function to update one of the graphic effects
4912 template<typename T, typename D>
UpdateGraphic(std::shared_ptr<T> & modifier,D data)4913 void RosenRenderContext::UpdateGraphic(std::shared_ptr<T>& modifier, D data)
4914 {
4915     CHECK_NULL_VOID(!RectIsNull());
4916     SetGraphicModifier(modifier, data);
4917     RequestNextFrame();
4918 }
4919 
OnFrontBrightnessUpdate(const Dimension & brightness)4920 void RosenRenderContext::OnFrontBrightnessUpdate(const Dimension& brightness)
4921 {
4922     CHECK_NULL_VOID(rsNode_);
4923     rsNode_->SetBrightness(brightness.Value());
4924     RequestNextFrame();
4925 }
4926 
OnFrontGrayScaleUpdate(const Dimension & grayScale)4927 void RosenRenderContext::OnFrontGrayScaleUpdate(const Dimension& grayScale)
4928 {
4929     CHECK_NULL_VOID(rsNode_);
4930     rsNode_->SetGrayScale(grayScale.Value());
4931     RequestNextFrame();
4932 }
4933 
OnFrontContrastUpdate(const Dimension & contrast)4934 void RosenRenderContext::OnFrontContrastUpdate(const Dimension& contrast)
4935 {
4936     CHECK_NULL_VOID(rsNode_);
4937     rsNode_->SetContrast(contrast.Value());
4938     RequestNextFrame();
4939 }
4940 
OnFrontSaturateUpdate(const Dimension & saturate)4941 void RosenRenderContext::OnFrontSaturateUpdate(const Dimension& saturate)
4942 {
4943     CHECK_NULL_VOID(rsNode_);
4944     rsNode_->SetSaturate(saturate.Value());
4945     RequestNextFrame();
4946 }
4947 
OnFrontSepiaUpdate(const Dimension & sepia)4948 void RosenRenderContext::OnFrontSepiaUpdate(const Dimension& sepia)
4949 {
4950     CHECK_NULL_VOID(rsNode_);
4951     rsNode_->SetSepia(sepia.Value());
4952     RequestNextFrame();
4953 }
4954 
OnFrontInvertUpdate(const InvertVariant & invert)4955 void RosenRenderContext::OnFrontInvertUpdate(const InvertVariant& invert)
4956 {
4957     CHECK_NULL_VOID(rsNode_);
4958     if (invert.index() == 0) {
4959         rsNode_->SetInvert(std::get<float>(invert));
4960     } else {
4961         InvertOption option = std::get<InvertOption>(invert);
4962         Rosen::Vector4f invertVector;
4963         invertVector.SetValues(option.low_, option.high_, option.threshold_, option.thresholdRange_);
4964         rsNode_->SetAiInvert(invertVector);
4965     }
4966     RequestNextFrame();
4967 }
4968 
OnSystemBarEffectUpdate(bool systemBarEffect)4969 void RosenRenderContext::OnSystemBarEffectUpdate(bool systemBarEffect)
4970 {
4971     CHECK_NULL_VOID(rsNode_);
4972     rsNode_->SetSystemBarEffect();
4973     RequestNextFrame();
4974 }
4975 
OnFrontHueRotateUpdate(float hueRotate)4976 void RosenRenderContext::OnFrontHueRotateUpdate(float hueRotate)
4977 {
4978     CHECK_NULL_VOID(rsNode_);
4979     rsNode_->SetHueRotate(hueRotate);
4980     RequestNextFrame();
4981 }
4982 
OnFrontColorBlendUpdate(const Color & colorBlend)4983 void RosenRenderContext::OnFrontColorBlendUpdate(const Color& colorBlend)
4984 {
4985     CHECK_NULL_VOID(rsNode_);
4986     rsNode_->SetColorBlend(colorBlend.GetValue());
4987     RequestNextFrame();
4988 }
4989 
OnLinearGradientBlurUpdate(const NG::LinearGradientBlurPara & blurPara)4990 void RosenRenderContext::OnLinearGradientBlurUpdate(const NG::LinearGradientBlurPara& blurPara)
4991 {
4992     float blurRadius = 0.0f;
4993     if (blurPara.blurRadius_.IsValid()) {
4994         float radiusPx = blurPara.blurRadius_.ConvertToPx();
4995         blurRadius = radiusPx;
4996     }
4997 
4998     CHECK_NULL_VOID(rsNode_);
4999     std::shared_ptr<Rosen::RSLinearGradientBlurPara> rsLinearGradientBlurPara(
5000         std::make_shared<Rosen::RSLinearGradientBlurPara>(
5001             blurRadius, blurPara.fractionStops_, static_cast<Rosen::GradientDirection>(blurPara.direction_)));
5002 
5003     rsNode_->SetLinearGradientBlurPara(rsLinearGradientBlurPara);
5004     RequestNextFrame();
5005 }
5006 
OnMagnifierUpdate(const MagnifierParams & magnifierParams)5007 void RosenRenderContext::OnMagnifierUpdate(const MagnifierParams& magnifierParams)
5008 {
5009     CHECK_NULL_VOID(rsNode_);
5010     std::shared_ptr<Rosen::RSMagnifierParams> rsMagnifierParams(std::make_shared<Rosen::RSMagnifierParams>());
5011     rsMagnifierParams->factor_ = magnifierParams.factor_;
5012     rsMagnifierParams->width_ = magnifierParams.width_;
5013     rsMagnifierParams->height_ = magnifierParams.height_;
5014     rsMagnifierParams->borderWidth_ = magnifierParams.borderWidth_;
5015     rsMagnifierParams->cornerRadius_ = magnifierParams.cornerRadius_;
5016     rsMagnifierParams->offsetX_ = magnifierParams.offsetX_;
5017     rsMagnifierParams->offsetY_ = magnifierParams.offsetY_;
5018     rsMagnifierParams->shadowOffsetX_ = magnifierParams.shadowOffsetX_;
5019     rsMagnifierParams->shadowOffsetY_ = magnifierParams.shadowOffsetY_;
5020     rsMagnifierParams->shadowSize_ = magnifierParams.shadowSize_;
5021     rsMagnifierParams->shadowStrength_ = magnifierParams.shadowStrength_;
5022     rsMagnifierParams->gradientMaskColor1_ = magnifierParams.gradientMaskColor1_;
5023     rsMagnifierParams->gradientMaskColor2_ = magnifierParams.gradientMaskColor2_;
5024     rsMagnifierParams->outerContourColor1_ = magnifierParams.outerContourColor1_;
5025     rsMagnifierParams->outerContourColor2_ = magnifierParams.outerContourColor2_;
5026     rsNode_->SetMagnifierParams(rsMagnifierParams);
5027     RequestNextFrame();
5028 }
OnDynamicDimDegreeUpdate(const float degree)5029 void RosenRenderContext::OnDynamicDimDegreeUpdate(const float degree)
5030 {
5031     CHECK_NULL_VOID(rsNode_);
5032     rsNode_->SetDynamicDimDegree(degree);
5033     RequestNextFrame();
5034 }
5035 
OnDynamicLightUpRateUpdate(const float rate)5036 void RosenRenderContext::OnDynamicLightUpRateUpdate(const float rate)
5037 {
5038     CHECK_NULL_VOID(rsNode_);
5039     rsNode_->SetDynamicLightUpRate(rate);
5040     RequestNextFrame();
5041 }
5042 
OnDynamicLightUpDegreeUpdate(const float degree)5043 void RosenRenderContext::OnDynamicLightUpDegreeUpdate(const float degree)
5044 {
5045     CHECK_NULL_VOID(rsNode_);
5046     rsNode_->SetDynamicLightUpDegree(degree);
5047     RequestNextFrame();
5048 }
5049 
OnBgDynamicBrightnessOptionUpdate(const std::optional<BrightnessOption> & brightnessOption)5050 void RosenRenderContext::OnBgDynamicBrightnessOptionUpdate(const std::optional<BrightnessOption>& brightnessOption)
5051 {
5052     if (!brightnessOption.has_value()) {
5053         return;
5054     }
5055     CHECK_NULL_VOID(rsNode_);
5056     rsNode_->SetBgBrightnessParams({ brightnessOption->rate, brightnessOption->lightUpDegree,
5057         brightnessOption->cubicCoeff, brightnessOption->quadCoeff, brightnessOption->saturation,
5058         { brightnessOption->posRGB[0], brightnessOption->posRGB[1], brightnessOption->posRGB[2] },
5059         { brightnessOption->negRGB[0], brightnessOption->negRGB[1], brightnessOption->negRGB[2] } });
5060     rsNode_->SetBgBrightnessFract(brightnessOption->fraction);
5061     RequestNextFrame();
5062 }
5063 
OnFgDynamicBrightnessOptionUpdate(const std::optional<BrightnessOption> & brightnessOption)5064 void RosenRenderContext::OnFgDynamicBrightnessOptionUpdate(const std::optional<BrightnessOption>& brightnessOption)
5065 {
5066     if (!brightnessOption.has_value()) {
5067         return;
5068     }
5069     CHECK_NULL_VOID(rsNode_);
5070     rsNode_->SetFgBrightnessParams({ brightnessOption->rate, brightnessOption->lightUpDegree,
5071         brightnessOption->cubicCoeff, brightnessOption->quadCoeff, brightnessOption->saturation,
5072         { brightnessOption->posRGB[0], brightnessOption->posRGB[1], brightnessOption->posRGB[2] },
5073         { brightnessOption->negRGB[0], brightnessOption->negRGB[1], brightnessOption->negRGB[2] } });
5074     rsNode_->SetFgBrightnessFract(brightnessOption->fraction);
5075     RequestNextFrame();
5076 }
5077 
UpdateTransition(const TransitionOptions & options)5078 void RosenRenderContext::UpdateTransition(const TransitionOptions& options)
5079 {
5080     CHECK_NULL_VOID(rsNode_);
5081     if (options.Type == TransitionType::ALL || options.Type == TransitionType::APPEARING) {
5082         if (!propTransitionAppearing_) {
5083             propTransitionAppearing_ = std::make_unique<TransitionOptions>(options);
5084         } else {
5085             *propTransitionAppearing_ = options;
5086         }
5087         propTransitionAppearing_->Type = TransitionType::APPEARING;
5088     }
5089     if (options.Type == TransitionType::ALL || options.Type == TransitionType::DISAPPEARING) {
5090         if (!propTransitionDisappearing_) {
5091             propTransitionDisappearing_ = std::make_unique<TransitionOptions>(options);
5092         } else {
5093             *propTransitionDisappearing_ = options;
5094         }
5095         propTransitionDisappearing_->Type = TransitionType::DISAPPEARING;
5096     }
5097     NotifyHostTransformUpdated();
5098 }
5099 
CleanTransition()5100 void RosenRenderContext::CleanTransition()
5101 {
5102     propTransitionDisappearing_.reset();
5103     propTransitionDisappearing_.reset();
5104 }
5105 
GetRSTransitionWithoutType(const std::unique_ptr<TransitionOptions> & options,const SizeF & frameSize)5106 std::shared_ptr<Rosen::RSTransitionEffect> RosenRenderContext::GetRSTransitionWithoutType(
5107     const std::unique_ptr<TransitionOptions>& options, const SizeF& frameSize)
5108 {
5109     if (options == nullptr) {
5110         return nullptr;
5111     }
5112     std::shared_ptr<Rosen::RSTransitionEffect> effect = Rosen::RSTransitionEffect::Create();
5113     if (options->HasOpacity()) {
5114         effect = effect->Opacity(options->GetOpacityValue());
5115     }
5116     if (options->HasTranslate()) {
5117         const auto& translate = options->GetTranslateValue();
5118         effect = effect->Translate({ static_cast<float>(translate.x.ConvertToPxWithSize(frameSize.Width())),
5119             static_cast<float>(translate.y.ConvertToPxWithSize(frameSize.Height())),
5120             static_cast<float>(translate.z.ConvertToPx()) });
5121     }
5122     if (options->HasScale()) {
5123         const auto& scale = options->GetScaleValue();
5124         effect = effect->Scale({ scale.xScale, scale.yScale, scale.zScale });
5125     }
5126     if (options->HasRotate()) {
5127         const auto& rotate = options->GetRotateValue();
5128         effect = effect->Rotate({ rotate.xDirection, rotate.yDirection, rotate.zDirection, rotate.angle });
5129     }
5130     return effect;
5131 }
5132 
SetBackgroundShader(const std::shared_ptr<Rosen::RSShader> & shader)5133 void RosenRenderContext::SetBackgroundShader(const std::shared_ptr<Rosen::RSShader>& shader)
5134 {
5135     CHECK_NULL_VOID(rsNode_);
5136     // temporary code for back compat
5137     auto& graphicProps = GetOrCreateGraphics();
5138     if (graphicProps->GetBackBlendMode() == BlendMode::BACK_COMPAT_SOURCE_IN) {
5139         rsNode_->SetBackgroundShader(nullptr);
5140         return;
5141     }
5142     rsNode_->SetBackgroundShader(shader);
5143 }
5144 
PaintGradient(const SizeF & frameSize)5145 void RosenRenderContext::PaintGradient(const SizeF& frameSize)
5146 {
5147     CHECK_NULL_VOID(rsNode_);
5148     auto& gradientProperty = GetOrCreateGradient();
5149     Gradient gradient;
5150     if (gradientProperty->HasLastGradientType()) {
5151         switch (gradientProperty->GetLastGradientTypeValue()) {
5152             case GradientType::LINEAR:
5153                 gradient = gradientProperty->GetLinearGradientValue();
5154                 break;
5155             case GradientType::RADIAL:
5156                 gradient = gradientProperty->GetRadialGradientValue();
5157                 break;
5158             case GradientType::SWEEP:
5159                 gradient = gradientProperty->GetSweepGradientValue();
5160                 break;
5161             default:
5162                 return;
5163         }
5164     } else {
5165         if (gradientProperty->HasLinearGradient()) {
5166             gradient = gradientProperty->GetLinearGradientValue();
5167         }
5168         if (gradientProperty->HasRadialGradient()) {
5169             gradient = gradientProperty->GetRadialGradientValue();
5170         }
5171         if (gradientProperty->HasSweepGradient()) {
5172             gradient = gradientProperty->GetSweepGradientValue();
5173         }
5174     }
5175     if (!gradientStyleModifier_) {
5176         gradientStyleModifier_ = std::make_shared<GradientStyleModifier>(WeakClaim(this));
5177         rsNode_->AddModifier(gradientStyleModifier_);
5178     }
5179     gradientStyleModifier_->SetGradient(gradient);
5180     gradientStyleModifier_->SetSizeF(frameSize);
5181 }
5182 
OnLinearGradientUpdate(const NG::Gradient & gradient)5183 void RosenRenderContext::OnLinearGradientUpdate(const NG::Gradient& gradient)
5184 {
5185     RectF rect = GetPaintRectWithoutTransform();
5186     if (!RectIsNull()) {
5187         PaintGradient(rect.GetSize());
5188     }
5189     RequestNextFrame();
5190 }
5191 
OnRadialGradientUpdate(const NG::Gradient & gradient)5192 void RosenRenderContext::OnRadialGradientUpdate(const NG::Gradient& gradient)
5193 {
5194     RectF rect = GetPaintRectWithoutTransform();
5195     if (!RectIsNull()) {
5196         PaintGradient(rect.GetSize());
5197     }
5198     RequestNextFrame();
5199 }
5200 
OnSweepGradientUpdate(const NG::Gradient & gradient)5201 void RosenRenderContext::OnSweepGradientUpdate(const NG::Gradient& gradient)
5202 {
5203     RectF rect = GetPaintRectWithoutTransform();
5204     if (!RectIsNull()) {
5205         PaintGradient(rect.GetSize());
5206     }
5207     RequestNextFrame();
5208 }
5209 
PaintClipShape(const std::unique_ptr<ClipProperty> & clip,const SizeF & frameSize)5210 void RosenRenderContext::PaintClipShape(const std::unique_ptr<ClipProperty>& clip, const SizeF& frameSize)
5211 {
5212     CHECK_NULL_VOID(rsNode_);
5213     auto basicShape = clip->GetClipShapeValue();
5214     auto rsPath = DrawingDecorationPainter::DrawingCreatePath(basicShape, frameSize);
5215     auto shapePath = Rosen::RSPath::CreateRSPath(rsPath);
5216     AddOrUpdateModifier<Rosen::ModifierNG::RSBoundsClipModifier,
5217         &Rosen::ModifierNG::RSBoundsClipModifier::SetClipBounds, std::shared_ptr<Rosen::RSPath>>(
5218         clipBoundModifier_, shapePath);
5219 }
5220 
PaintClipMask(const std::unique_ptr<ClipProperty> & clip,const SizeF & frameSize)5221 void RosenRenderContext::PaintClipMask(const std::unique_ptr<ClipProperty>& clip, const SizeF& frameSize)
5222 {
5223     CHECK_NULL_VOID(rsNode_);
5224     auto basicShape = clip->GetClipMaskValue();
5225     auto rsPath = DrawingDecorationPainter::DrawingCreatePath(basicShape, frameSize);
5226 
5227     RSColor rsStrokeColor;
5228     rsStrokeColor.SetColorQuad(basicShape->GetStrokeColor());
5229     RSPen pen;
5230     pen.SetColor(rsStrokeColor);
5231     pen.SetWidth(basicShape->GetStrokeWidth());
5232 
5233     auto maskPath =
5234         Rosen::RSMask::CreatePathMask(rsPath, pen, DrawingDecorationPainter::CreateMaskDrawingBrush(basicShape));
5235     AddOrUpdateModifier<Rosen::ModifierNG::RSMaskModifier, &Rosen::ModifierNG::RSMaskModifier::SetMask,
5236         std::shared_ptr<Rosen::RSMask>>(clipMaskModifier_, maskPath);
5237 }
5238 
PaintClip(const SizeF & frameSize)5239 void RosenRenderContext::PaintClip(const SizeF& frameSize)
5240 {
5241     CHECK_NULL_VOID(rsNode_);
5242     auto& clip = GetOrCreateClip();
5243     if (clip->HasClipShape()) {
5244         PaintClipShape(clip, frameSize);
5245     }
5246 
5247     if (clip->HasClipMask()) {
5248         PaintClipMask(clip, frameSize);
5249     }
5250 }
5251 
PaintProgressMask()5252 void RosenRenderContext::PaintProgressMask()
5253 {
5254     CHECK_NULL_VOID(rsNode_);
5255     if (!moonProgressModifier_) {
5256         auto host = GetHost();
5257         CHECK_NULL_VOID(host);
5258         moonProgressModifier_ = AceType::MakeRefPtr<MoonProgressModifier>(host);
5259         auto modifierAdapter =
5260             std::static_pointer_cast<OverlayModifierAdapter>(ConvertOverlayModifier(moonProgressModifier_));
5261         rsNode_->AddModifier(modifierAdapter);
5262         modifierAdapter->AttachProperties();
5263     }
5264     auto progress = GetProgressMaskValue();
5265     moonProgressModifier_->SetMaskColor(LinearColor(progress->GetColor()));
5266     moonProgressModifier_->SetMaxValue(progress->GetMaxValue());
5267     if (progress->GetValue() > moonProgressModifier_->GetMaxValue()) {
5268         progress->SetValue(moonProgressModifier_->GetMaxValue());
5269     }
5270     moonProgressModifier_->SetValue(progress->GetValue());
5271     moonProgressModifier_->SetEnableBreathe(progress->GetEnableBreathe());
5272 }
5273 
SetClipBoundsWithCommands(const std::string & commands)5274 void RosenRenderContext::SetClipBoundsWithCommands(const std::string& commands)
5275 {
5276     CHECK_NULL_VOID(rsNode_);
5277     RSRecordingPath rsPath;
5278     rsPath.BuildFromSVGString(commands);
5279     rsNode_->SetClipBounds(Rosen::RSPath::CreateRSPath(rsPath));
5280 }
5281 
ClipWithRect(const RectF & rectF)5282 void RosenRenderContext::ClipWithRect(const RectF& rectF)
5283 {
5284     CHECK_NULL_VOID(rsNode_);
5285     RSRecordingPath rsPath;
5286     rsPath.AddRect({ rectF.GetX(), rectF.GetY(), rectF.GetX() + rectF.Width(), rectF.GetY() + rectF.Height() });
5287     rsNode_->SetClipBounds(Rosen::RSPath::CreateRSPath(rsPath));
5288 }
5289 
ClipWithRoundRect(const RoundRect & roundRect)5290 void RosenRenderContext::ClipWithRoundRect(const RoundRect& roundRect)
5291 {
5292     CHECK_NULL_VOID(rsNode_);
5293     RSRoundRect rsRoundRect;
5294 
5295     RSRect rsRect(roundRect.GetRect().Left(), roundRect.GetRect().Top(), roundRect.GetRect().Right(),
5296         roundRect.GetRect().Bottom());
5297     rsRoundRect.SetRect(rsRect);
5298 
5299     EdgeF edge = roundRect.GetCornerRadius(RoundRect::TOP_LEFT_POS);
5300     rsRoundRect.SetCornerRadius(RSRoundRect::TOP_LEFT_POS, edge.x, edge.y);
5301     edge = roundRect.GetCornerRadius(RoundRect::TOP_RIGHT_POS);
5302     rsRoundRect.SetCornerRadius(RSRoundRect::TOP_RIGHT_POS, edge.x, edge.y);
5303     edge = roundRect.GetCornerRadius(RoundRect::BOTTOM_LEFT_POS);
5304     rsRoundRect.SetCornerRadius(RSRoundRect::BOTTOM_LEFT_POS, edge.x, edge.y);
5305     edge = roundRect.GetCornerRadius(RoundRect::BOTTOM_RIGHT_POS);
5306     rsRoundRect.SetCornerRadius(RSRoundRect::BOTTOM_RIGHT_POS, edge.x, edge.y);
5307     RSRecordingPath rsPath;
5308     rsPath.AddRoundRect(rsRoundRect);
5309     rsNode_->SetClipBounds(Rosen::RSPath::CreateRSPath(rsPath));
5310 }
5311 
ClipWithOval(const RectF & rectF)5312 void RosenRenderContext::ClipWithOval(const RectF& rectF)
5313 {
5314     CHECK_NULL_VOID(rsNode_);
5315     RSRecordingPath rsPath;
5316     rsPath.AddOval({ rectF.GetX(), rectF.GetY(), rectF.GetX() + rectF.Width(), rectF.GetY() + rectF.Height() });
5317     rsNode_->SetClipBounds(Rosen::RSPath::CreateRSPath(rsPath));
5318 }
5319 
ClipWithCircle(const Circle & circle)5320 void RosenRenderContext::ClipWithCircle(const Circle& circle)
5321 {
5322     CHECK_NULL_VOID(rsNode_);
5323     RSRecordingPath rsPath;
5324     rsPath.AddCircle(circle.GetAxisX().Value(), circle.GetAxisY().Value(), circle.GetRadius().Value());
5325     rsNode_->SetClipBounds(Rosen::RSPath::CreateRSPath(rsPath));
5326 }
5327 
ClipWithRRect(const RectF & rectF,const RadiusF & radiusF)5328 void RosenRenderContext::ClipWithRRect(const RectF& rectF, const RadiusF& radiusF)
5329 {
5330     CHECK_NULL_VOID(rsNode_);
5331     Rosen::Vector4f rect;
5332     Rosen::Vector4f radius;
5333     rect.SetValues(rectF.GetX(), rectF.GetY(), rectF.GetX() + rectF.Width(), rectF.GetY() + rectF.Height());
5334     radius.SetValues(radiusF.GetCorner(RoundRect::CornerPos::TOP_LEFT_POS).x,
5335         radiusF.GetCorner(RoundRect::CornerPos::TOP_RIGHT_POS).x,
5336         radiusF.GetCorner(RoundRect::CornerPos::BOTTOM_LEFT_POS).x,
5337         radiusF.GetCorner(RoundRect::CornerPos::BOTTOM_RIGHT_POS).x);
5338     rsNode_->SetClipRRect(rect, radius);
5339     RequestNextFrame();
5340 }
5341 
SetContentClip(const std::variant<RectF,RefPtr<ShapeRect>> & rect)5342 void RosenRenderContext::SetContentClip(const std::variant<RectF, RefPtr<ShapeRect>>& rect)
5343 {
5344     CHECK_NULL_VOID(rsNode_);
5345     RectF rectF;
5346     Rosen::Vector4f clipRect;
5347     if (std::holds_alternative<RectF>(rect)) {
5348         rectF = std::get<RectF>(rect);
5349         clipRect =
5350             Rosen::Vector4f { rectF.GetX(), rectF.GetY(), rectF.GetX() + rectF.Width(), rectF.GetY() + rectF.Height() };
5351     } else {
5352         auto shape = std::get<RefPtr<ShapeRect>>(rect);
5353         CHECK_NULL_VOID(shape);
5354         using helper = DrawingDecorationPainter;
5355 
5356         const float x =
5357             helper::DrawingDimensionToPx(shape->GetOffset().GetX(), paintRect_.GetSize(), LengthMode::HORIZONTAL);
5358         const float y =
5359             helper::DrawingDimensionToPx(shape->GetOffset().GetY(), paintRect_.GetSize(), LengthMode::VERTICAL);
5360         const float width =
5361             helper::DrawingDimensionToPx(shape->GetWidth(), paintRect_.GetSize(), LengthMode::HORIZONTAL);
5362         const float height =
5363             helper::DrawingDimensionToPx(shape->GetHeight(), paintRect_.GetSize(), LengthMode::VERTICAL);
5364         rectF = RectF(x, y, width, height);
5365         clipRect = Rosen::Vector4f { x, y, x + width, y + height };
5366     }
5367     AddOrUpdateModifier<Rosen::ModifierNG::RSFrameClipModifier,
5368         &Rosen::ModifierNG::RSFrameClipModifier::SetCustomClipToFrame, Rosen::Vector4f>(
5369         customClipToFrameModifier_, clipRect);
5370     if (!contentClip_ || rectF != *contentClip_) {
5371         contentClip_ = std::make_unique<RectF>(rectF);
5372         GetHost()->AddFrameNodeChangeInfoFlag(FRAME_NODE_CONTENT_CLIP_CHANGE);
5373     }
5374 }
5375 
ResetContentClip()5376 void RosenRenderContext::ResetContentClip()
5377 {
5378     if (customClipToFrameModifier_) {
5379         rsNode_->RemoveModifier(customClipToFrameModifier_);
5380         customClipToFrameModifier_.reset();
5381     }
5382     if (contentClip_) {
5383         contentClip_.reset();
5384     }
5385 }
5386 
RemoveClipWithRRect()5387 void RosenRenderContext::RemoveClipWithRRect()
5388 {
5389     std::weak_ptr<Rosen::RSNode> weakRsNode = rsNode_;
5390     AnimationUtils::ExecuteWithoutAnimation([weakRsNode]() {
5391         auto rsNode = weakRsNode.lock();
5392         CHECK_NULL_VOID(rsNode);
5393         rsNode->SetClipRRect(nullptr);
5394     });
5395     RequestNextFrame();
5396 }
5397 
OnClipShapeUpdate(const RefPtr<BasicShape> & basicShape)5398 void RosenRenderContext::OnClipShapeUpdate(const RefPtr<BasicShape>& basicShape)
5399 {
5400     CHECK_NULL_VOID(rsNode_);
5401     if (basicShape) {
5402         if (!RectIsNull()) {
5403             RectF rect = GetPaintRectWithoutTransform();
5404             PaintClipShape(GetOrCreateClip(), rect.GetSize());
5405         }
5406     } else if (clipBoundModifier_) {
5407         rsNode_->RemoveModifier(clipBoundModifier_);
5408         clipBoundModifier_ = nullptr;
5409     }
5410     RequestNextFrame();
5411 }
5412 
OnClipEdgeUpdate(bool isClip)5413 void RosenRenderContext::OnClipEdgeUpdate(bool isClip)
5414 {
5415     CHECK_NULL_VOID(rsNode_);
5416     if (isClip) {
5417         rsNode_->SetClipToBounds(true);
5418     } else {
5419         // In the internal implementation, some nodes call SetClipToBounds(true), some call SetClipToFrame(true).
5420         // If the developer set clip to false, we should disable all internal clips
5421         // so that the child component can go beyond the parent component
5422         rsNode_->SetClipToBounds(false);
5423         rsNode_->SetClipToFrame(false);
5424     }
5425     RequestNextFrame();
5426 }
5427 
OnClipMaskUpdate(const RefPtr<BasicShape> & basicShape)5428 void RosenRenderContext::OnClipMaskUpdate(const RefPtr<BasicShape>& basicShape)
5429 {
5430     CHECK_NULL_VOID(rsNode_);
5431     if (basicShape) {
5432         if (!RectIsNull()) {
5433             RectF rect = GetPaintRectWithoutTransform();
5434             PaintClipMask(GetOrCreateClip(), rect.GetSize());
5435         }
5436     } else if (clipMaskModifier_) {
5437         rsNode_->RemoveModifier(clipMaskModifier_);
5438         clipMaskModifier_ = nullptr;
5439     }
5440     RequestNextFrame();
5441 }
5442 
OnProgressMaskUpdate(const RefPtr<ProgressMaskProperty> & progress)5443 void RosenRenderContext::OnProgressMaskUpdate(const RefPtr<ProgressMaskProperty>& progress)
5444 {
5445     CHECK_NULL_VOID(rsNode_);
5446     if (progress) {
5447         if (!RectIsNull()) {
5448             PaintProgressMask();
5449         }
5450         rsNode_->SetClipToBounds(true);
5451     } else if (moonProgressModifier_) {
5452         auto modifierAdapter =
5453             std::static_pointer_cast<OverlayModifierAdapter>(ConvertOverlayModifier(moonProgressModifier_));
5454         rsNode_->RemoveModifier(modifierAdapter);
5455         moonProgressModifier_ = nullptr;
5456     }
5457     RequestNextFrame();
5458 }
5459 
PaintOverlayText()5460 void RosenRenderContext::PaintOverlayText()
5461 {
5462     CHECK_NULL_VOID(rsNode_);
5463     auto& overlay = GetOrCreateOverlay();
5464     if (overlay->HasOverlayText()) {
5465         auto overlayText = overlay->GetOverlayTextValue();
5466         auto paintRect = GetPaintRectWithTransform();
5467         std::shared_ptr<Rosen::RectF> overlayRect;
5468         if (overlayTextModifier_) {
5469             overlayTextModifier_->SetCustomData(NG::OverlayTextData(overlayText));
5470             auto overlayOffset = overlayTextModifier_->GetOverlayOffset();
5471             auto paragraphSize = overlayTextModifier_->GetParagraphSize(paintRect.Width());
5472             overlayRect = std::make_shared<Rosen::RectF>(overlayOffset.GetX(), overlayOffset.GetY(),
5473                 std::max(paragraphSize.Width(), paintRect.Width()),
5474                 std::max(paragraphSize.Height(), paintRect.Height()));
5475             rsNode_->SetIsCustomTextType(overlayTextModifier_->IsCustomFont());
5476             UpdateDrawRegion(DRAW_REGION_OVERLAY_TEXT_MODIFIER_INDEX, overlayRect);
5477         } else {
5478             overlayTextModifier_ = std::make_shared<OverlayTextModifier>();
5479             rsNode_->AddModifier(overlayTextModifier_);
5480             overlayTextModifier_->SetCustomData(NG::OverlayTextData(overlayText));
5481             auto overlayOffset = overlayTextModifier_->GetOverlayOffset();
5482             auto paragraphSize = overlayTextModifier_->GetParagraphSize(paintRect.Width());
5483             overlayRect = std::make_shared<Rosen::RectF>(overlayOffset.GetX(), overlayOffset.GetY(),
5484                 std::max(paragraphSize.Width(), paintRect.Width()),
5485                 std::max(paragraphSize.Height(), paintRect.Height()));
5486             rsNode_->SetIsCustomTextType(overlayTextModifier_->IsCustomFont());
5487             UpdateDrawRegion(DRAW_REGION_OVERLAY_TEXT_MODIFIER_INDEX, overlayRect);
5488         }
5489     }
5490 }
5491 
OnOverlayTextUpdate(const OverlayOptions & overlay)5492 void RosenRenderContext::OnOverlayTextUpdate(const OverlayOptions& overlay)
5493 {
5494     if (!RectIsNull()) {
5495         PaintOverlayText();
5496     }
5497     RequestNextFrame();
5498 }
5499 
OnMotionPathUpdate(const MotionPathOption & motionPath)5500 void RosenRenderContext::OnMotionPathUpdate(const MotionPathOption& motionPath)
5501 {
5502     CHECK_NULL_VOID(rsNode_);
5503     if (!motionPath.IsValid()) {
5504         rsNode_->SetMotionPathOption(nullptr);
5505         return;
5506     }
5507     auto motionOption = Rosen::RSMotionPathOption(motionPath.GetPath());
5508     motionOption.SetBeginFraction(motionPath.GetBegin());
5509     motionOption.SetEndFraction(motionPath.GetEnd());
5510     motionOption.SetRotationMode(
5511         motionPath.GetRotate() ? Rosen::RotationMode::ROTATE_AUTO : Rosen::RotationMode::ROTATE_NONE);
5512     motionOption.SetPathNeedAddOrigin(HasOffset());
5513     rsNode_->SetMotionPathOption(std::make_shared<Rosen::RSMotionPathOption>(motionOption));
5514     RequestNextFrame();
5515 }
5516 
OnLightPositionUpdate(const TranslateOptions & translate)5517 void RosenRenderContext::OnLightPositionUpdate(const TranslateOptions& translate)
5518 {
5519     CHECK_NULL_VOID(rsNode_);
5520     float xValue = 0.0f;
5521     float yValue = 0.0f;
5522     if (translate.x.Unit() == DimensionUnit::PERCENT || translate.y.Unit() == DimensionUnit::PERCENT) {
5523         auto rect = GetPaintRectWithoutTransform();
5524         if (rect.IsEmpty()) {
5525             // size is not determined yet
5526             return;
5527         }
5528         xValue = translate.x.ConvertToPxWithSize(rect.Width());
5529         yValue = translate.y.ConvertToPxWithSize(rect.Height());
5530     } else {
5531         xValue = translate.x.ConvertToPx();
5532         yValue = translate.y.ConvertToPx();
5533     }
5534     // translateZ doesn't support percentage
5535     float zValue = translate.z.ConvertToPx();
5536     rsNode_->SetLightPosition(xValue, yValue, zValue);
5537     RequestNextFrame();
5538 }
5539 
OnLightIntensityUpdate(const float lightIntensity)5540 void RosenRenderContext::OnLightIntensityUpdate(const float lightIntensity)
5541 {
5542     CHECK_NULL_VOID(rsNode_);
5543     rsNode_->SetLightIntensity(lightIntensity);
5544     RequestNextFrame();
5545 }
5546 
OnLightColorUpdate(const Color & lightColor)5547 void RosenRenderContext::OnLightColorUpdate(const Color& lightColor)
5548 {
5549     CHECK_NULL_VOID(rsNode_);
5550     rsNode_->SetLightColor(lightColor.GetValue());
5551     RequestNextFrame();
5552 }
5553 
OnLightIlluminatedUpdate(const uint32_t lightIlluminated)5554 void RosenRenderContext::OnLightIlluminatedUpdate(const uint32_t lightIlluminated)
5555 {
5556     CHECK_NULL_VOID(rsNode_);
5557     rsNode_->SetIlluminatedType(lightIlluminated);
5558     RequestNextFrame();
5559 }
5560 
OnIlluminatedBorderWidthUpdate(const Dimension & illuminatedBorderWidth)5561 void RosenRenderContext::OnIlluminatedBorderWidthUpdate(const Dimension& illuminatedBorderWidth)
5562 {
5563     CHECK_NULL_VOID(rsNode_);
5564     rsNode_->SetIlluminatedBorderWidth(static_cast<float>(illuminatedBorderWidth.ConvertToPx()));
5565     RequestNextFrame();
5566 }
5567 
OnBloomUpdate(const float bloomIntensity)5568 void RosenRenderContext::OnBloomUpdate(const float bloomIntensity)
5569 {
5570     CHECK_NULL_VOID(rsNode_);
5571     rsNode_->SetBloom(bloomIntensity);
5572     RequestNextFrame();
5573 }
5574 
SetSharedTranslate(float xTranslate,float yTranslate)5575 void RosenRenderContext::SetSharedTranslate(float xTranslate, float yTranslate)
5576 {
5577     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetTranslate,
5578         Rosen::Vector2f>(sharedTransitionModifier_, { xTranslate, yTranslate });
5579     NotifyHostTransformUpdated();
5580 }
5581 
ResetSharedTranslate()5582 void RosenRenderContext::ResetSharedTranslate()
5583 {
5584     CHECK_NULL_VOID(sharedTransitionModifier_);
5585     CHECK_NULL_VOID(rsNode_);
5586     rsNode_->RemoveModifier(sharedTransitionModifier_);
5587     sharedTransitionModifier_ = nullptr;
5588     NotifyHostTransformUpdated();
5589 }
5590 
AddChild(const RefPtr<RenderContext> & renderContext,int index)5591 void RosenRenderContext::AddChild(const RefPtr<RenderContext>& renderContext, int index)
5592 {
5593     CHECK_NULL_VOID(rsNode_);
5594     auto rosenRenderContext = AceType::DynamicCast<RosenRenderContext>(renderContext);
5595     CHECK_NULL_VOID(rosenRenderContext);
5596     auto child = rosenRenderContext->GetRSNode();
5597     rsNode_->AddChild(child, index);
5598 }
5599 
RemoveChild(const RefPtr<RenderContext> & renderContext)5600 void RosenRenderContext::RemoveChild(const RefPtr<RenderContext>& renderContext)
5601 {
5602     CHECK_NULL_VOID(rsNode_);
5603     auto rosenRenderContext = AceType::DynamicCast<RosenRenderContext>(renderContext);
5604     CHECK_NULL_VOID(rosenRenderContext);
5605     auto child = rosenRenderContext->GetRSNode();
5606     rsNode_->RemoveChild(child);
5607 }
5608 
ClearChildren()5609 void RosenRenderContext::ClearChildren()
5610 {
5611     CHECK_NULL_VOID(rsNode_);
5612     rsNode_->ClearChildren();
5613 }
5614 
SetBounds(float positionX,float positionY,float width,float height)5615 void RosenRenderContext::SetBounds(float positionX, float positionY, float width, float height)
5616 {
5617     CHECK_NULL_VOID(rsNode_);
5618     paintRect_ = RectF(positionX, positionY, width, height);
5619     rsNode_->SetBounds(positionX, positionY, width, height);
5620 }
5621 
SetUsingContentRectForRenderFrame(bool value,bool adjustRSFrameByContentRect)5622 void RosenRenderContext::SetUsingContentRectForRenderFrame(bool value, bool adjustRSFrameByContentRect)
5623 {
5624     useContentRectForRSFrame_ = value;
5625     adjustRSFrameByContentRect_ = adjustRSFrameByContentRect;
5626 }
5627 
SetSecurityLayer(bool isSecure)5628 void RosenRenderContext::SetSecurityLayer(bool isSecure)
5629 {
5630     CHECK_NULL_VOID(rsNode_);
5631     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
5632     CHECK_NULL_VOID(rsSurfaceNode);
5633     rsSurfaceNode->SetSecurityLayer(isSecure);
5634 }
5635 
SetHDRBrightness(float hdrBrightness)5636 void RosenRenderContext::SetHDRBrightness(float hdrBrightness)
5637 {
5638     CHECK_NULL_VOID(rsNode_);
5639     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
5640     CHECK_NULL_VOID(rsSurfaceNode);
5641     rsSurfaceNode->SetHDRBrightness(hdrBrightness);
5642 }
5643 
SetImageHDRPresent(bool hdrPresent)5644 void RosenRenderContext::SetImageHDRPresent(bool hdrPresent)
5645 {
5646     auto rsCanvasDrawingNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasNode>(rsNode_);
5647     CHECK_NULL_VOID(rsCanvasDrawingNode);
5648     rsCanvasDrawingNode->SetHDRPresent(hdrPresent);
5649 }
5650 
SetImageHDRBrightness(float hdrBrightness)5651 void RosenRenderContext::SetImageHDRBrightness(float hdrBrightness)
5652 {
5653     CHECK_NULL_VOID(rsNode_);
5654     rsNode_->SetHDRBrightness(hdrBrightness);
5655 }
5656 
SetTransparentLayer(bool isTransparentLayer)5657 void RosenRenderContext::SetTransparentLayer(bool isTransparentLayer)
5658 {
5659     CHECK_NULL_VOID(rsNode_);
5660     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
5661     CHECK_NULL_VOID(rsSurfaceNode);
5662     rsSurfaceNode->SetHardwareEnableHint(isTransparentLayer);
5663 }
5664 
SetScreenId(uint64_t screenId)5665 void RosenRenderContext::SetScreenId(uint64_t screenId)
5666 {
5667     CHECK_NULL_VOID(rsNode_);
5668     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
5669     CHECK_NULL_VOID(rsSurfaceNode);
5670     rsSurfaceNode->SetSourceVirtualDisplayId(screenId);
5671 }
5672 
SetAlwaysSnapshot(bool enable)5673 void RosenRenderContext::SetAlwaysSnapshot(bool enable)
5674 {
5675     CHECK_NULL_VOID(rsNode_);
5676     if (rsNode_->GetType() != Rosen::RSUINodeType::EFFECT_NODE) {
5677         return;
5678     }
5679     rsNode_->SetAlwaysSnapshot(enable);
5680 }
5681 
SetFrameGravity(OHOS::Rosen::Gravity gravity)5682 void RosenRenderContext::SetFrameGravity(OHOS::Rosen::Gravity gravity)
5683 {
5684     CHECK_NULL_VOID(rsNode_);
5685     rsNode_->SetFrameGravity(gravity);
5686 }
5687 
SetUIFirstSwitch(OHOS::Rosen::RSUIFirstSwitch uiFirstSwitch)5688 void RosenRenderContext::SetUIFirstSwitch(OHOS::Rosen::RSUIFirstSwitch uiFirstSwitch)
5689 {
5690     CHECK_NULL_VOID(rsNode_);
5691     rsNode_->SetUIFirstSwitch(uiFirstSwitch);
5692 }
5693 
CalcExpectedFrameRate(const std::string & scene,float speed)5694 int32_t RosenRenderContext::CalcExpectedFrameRate(const std::string& scene, float speed)
5695 {
5696     if (rsNode_ == nullptr) {
5697         return 0;
5698     }
5699     return rsNode_->CalcExpectedFrameRate(scene, speed);
5700 }
5701 
DoTextureExport(uint64_t surfaceId)5702 bool RosenRenderContext::DoTextureExport(uint64_t surfaceId)
5703 {
5704     CHECK_NULL_RETURN(rsNode_, false);
5705     rsNode_->RemoveFromTree();
5706     if (!rsTextureExport_) {
5707         rsTextureExport_ = std::make_shared<Rosen::RSTextureExport>(rsNode_, surfaceId);
5708     }
5709     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
5710     if (rsSurfaceNode) {
5711         rsSurfaceNode->SetTextureExport(true);
5712     }
5713     return rsTextureExport_->DoTextureExport();
5714 }
5715 
StopTextureExport()5716 bool RosenRenderContext::StopTextureExport()
5717 {
5718     CHECK_NULL_RETURN(rsNode_, false);
5719     CHECK_NULL_RETURN(rsTextureExport_, false);
5720     rsTextureExport_->StopTextureExport();
5721     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
5722     if (rsSurfaceNode) {
5723         rsSurfaceNode->SetTextureExport(false);
5724     }
5725     return true;
5726 }
5727 
SetSurfaceRotation(bool isLock)5728 void RosenRenderContext::SetSurfaceRotation(bool isLock)
5729 {
5730     CHECK_NULL_VOID(rsNode_);
5731     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
5732     if (rsSurfaceNode) {
5733         rsSurfaceNode->SetForceHardwareAndFixRotation(isLock);
5734     }
5735 }
5736 
SetRenderFit(RenderFit renderFit)5737 void RosenRenderContext::SetRenderFit(RenderFit renderFit)
5738 {
5739     CHECK_NULL_VOID(rsNode_);
5740     propRenderFit_ = renderFit;
5741     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
5742     if (rsSurfaceNode) {
5743         rsSurfaceNode->SetFrameGravity(GetRosenGravity(renderFit));
5744     }
5745 }
5746 
ClearDrawCommands()5747 void RosenRenderContext::ClearDrawCommands()
5748 {
5749     StartRecording();
5750     StopRecordingIfNeeded();
5751 }
5752 
RemoveOverlayModifier(const RefPtr<OverlayModifier> & modifier)5753 void RosenRenderContext::RemoveOverlayModifier(const RefPtr<OverlayModifier>& modifier)
5754 {
5755     CHECK_NULL_VOID(rsNode_);
5756     CHECK_NULL_VOID(modifier);
5757     auto modifierAdapter = std::static_pointer_cast<OverlayModifierAdapter>(ConvertOverlayModifier(modifier));
5758     CHECK_NULL_VOID(modifierAdapter);
5759     rsNode_->RemoveModifier(modifierAdapter);
5760 }
5761 
RemoveContentModifier(const RefPtr<ContentModifier> & modifier)5762 void RosenRenderContext::RemoveContentModifier(const RefPtr<ContentModifier>& modifier)
5763 {
5764     CHECK_NULL_VOID(rsNode_);
5765     CHECK_NULL_VOID(modifier);
5766     auto modifierAdapter = std::static_pointer_cast<ContentModifierAdapter>(ConvertContentModifier(modifier));
5767     CHECK_NULL_VOID(modifierAdapter);
5768     rsNode_->RemoveModifier(modifierAdapter);
5769 }
5770 
SetRSNode(const std::shared_ptr<RSNode> & externalNode)5771 void RosenRenderContext::SetRSNode(const std::shared_ptr<RSNode>& externalNode)
5772 {
5773     // Update rsNode_ to externalNode.
5774     if (externalNode == rsNode_) {
5775         return;
5776     }
5777     rsNode_ = externalNode;
5778     AddFrameNodeInfoToRsNode();
5779     auto host = GetHost();
5780     CHECK_NULL_VOID(host);
5781     host->AddExtraCustomProperty("RS_NODE", rsNode_.get());
5782 
5783     ResetTransform();
5784     ResetTransformMatrix();
5785 
5786     // after update, tell parent to update RSNode hierarchy.
5787     auto uiNode = GetHost();
5788     CHECK_NULL_VOID(uiNode);
5789     auto parentUINode = uiNode->GetParent();
5790     CHECK_NULL_VOID(parentUINode);
5791     parentUINode->MarkNeedSyncRenderTree();
5792     parentUINode->RebuildRenderContextTree();
5793 }
5794 
OnMouseSelectUpdate(bool isSelected,const Color & fillColor,const Color & strokeColor)5795 void RosenRenderContext::OnMouseSelectUpdate(bool isSelected, const Color& fillColor, const Color& strokeColor)
5796 {
5797     auto host = GetHost();
5798     CHECK_NULL_VOID(host);
5799 
5800     RectF rect = RectF();
5801     if (isSelected) {
5802         auto geometryNode = host->GetGeometryNode();
5803         CHECK_NULL_VOID(geometryNode);
5804         rect = geometryNode->GetFrameRect();
5805         rect.SetOffset(OffsetF());
5806     }
5807 
5808     UpdateMouseSelectWithRect(rect, fillColor, strokeColor);
5809 }
5810 
UpdateMouseSelectWithRect(const RectF & rect,const Color & fillColor,const Color & strokeColor)5811 void RosenRenderContext::UpdateMouseSelectWithRect(const RectF& rect, const Color& fillColor, const Color& strokeColor)
5812 {
5813     if (!rect.IsValid()) {
5814         return;
5815     }
5816     PaintMouseSelectRect(rect, fillColor, strokeColor);
5817     RequestNextFrame();
5818 }
5819 
PaintMouseSelectRect(const RectF & rect,const Color & fillColor,const Color & strokeColor)5820 void RosenRenderContext::PaintMouseSelectRect(const RectF& rect, const Color& fillColor, const Color& strokeColor)
5821 {
5822     CHECK_NULL_VOID(rsNode_);
5823     if (mouseSelectModifier_) {
5824         mouseSelectModifier_->SetSelectRect(rect);
5825         return;
5826     }
5827 
5828     auto paintTask = [&fillColor, &strokeColor](const RectF& rect, RSCanvas& rsCanvas) mutable {
5829         RSBrush brush;
5830         brush.SetColor(ToRSColor(fillColor));
5831         rsCanvas.AttachBrush(brush);
5832         rsCanvas.DrawRect(ToRSRect(rect));
5833         rsCanvas.DetachBrush();
5834         RSPen pen;
5835         pen.SetColor(ToRSColor(strokeColor));
5836         rsCanvas.AttachPen(pen);
5837         rsCanvas.DrawRect(ToRSRect(rect));
5838         rsCanvas.DetachPen();
5839     };
5840 
5841     mouseSelectModifier_ = std::make_shared<MouseSelectModifier>();
5842     mouseSelectModifier_->SetPaintTask(std::move(paintTask));
5843     rsNode_->AddModifier(mouseSelectModifier_);
5844 }
5845 
DumpInfo()5846 void RosenRenderContext::DumpInfo()
5847 {
5848     if (rsNode_) {
5849         DumpLog::GetInstance().AddDesc("------------start print rsNode");
5850         DumpLog::GetInstance().AddDesc(rsNode_->DumpNode(0));
5851         auto center = rsNode_->GetStagingProperties().GetPivot();
5852         if (!NearEqual(center[0], 0.5) || !NearEqual(center[1], 0.5)) {
5853             DumpLog::GetInstance().AddDesc(std::string("Center: x:")
5854                                                .append(std::to_string(center[0]))
5855                                                .append(" y:")
5856                                                .append(std::to_string(center[1])));
5857         }
5858         if (!NearZero(rsNode_->GetStagingProperties().GetPivotZ())) {
5859             DumpLog::GetInstance().AddDesc(
5860                 std::string("PivotZ:").append(std::to_string(rsNode_->GetStagingProperties().GetPivotZ())));
5861         }
5862         std::string res = "";
5863         if (!NearZero(rsNode_->GetStagingProperties().GetRotation())) {
5864             res.append(" Rotation:").append(std::to_string(rsNode_->GetStagingProperties().GetRotation()));
5865         }
5866         if (!NearZero(rsNode_->GetStagingProperties().GetRotationX())) {
5867             res.append(" RotationX:").append(std::to_string(rsNode_->GetStagingProperties().GetRotationX()));
5868         }
5869         if (!NearZero(rsNode_->GetStagingProperties().GetRotationY())) {
5870             res.append(" RotationY:").append(std::to_string(rsNode_->GetStagingProperties().GetRotationY()));
5871         }
5872         if (!res.empty()) {
5873             DumpLog::GetInstance().AddDesc(res);
5874             res.clear();
5875         }
5876         const auto& groupProperty = GetOrCreateBackground();
5877         if (groupProperty->propEffectOption.has_value()) {
5878             auto backgroundEffect = groupProperty->propEffectOption->ToJsonValue()->ToString();
5879             DumpLog::GetInstance().AddDesc(std::string("backgroundEffect:").append(backgroundEffect));
5880         }
5881         if (groupProperty->propSysOptions.has_value()) {
5882             DumpLog::GetInstance().AddDesc(
5883                 std::string("backDisable:")
5884                     .append(std::to_string(groupProperty->propSysOptions->disableSystemAdaptation)));
5885         }
5886         const auto& foregroundProperty = GetOrCreateForeground();
5887         if (foregroundProperty->propSysOptionsForBlur.has_value()) {
5888             DumpLog::GetInstance().AddDesc(
5889                 std::string("blurDisable:")
5890                     .append(std::to_string(foregroundProperty->propSysOptionsForBlur->disableSystemAdaptation)));
5891         }
5892         auto&& graphicProps = GetOrCreateGraphics();
5893         if (graphicProps->propFgDynamicBrightnessOption.has_value()) {
5894             auto fgDynamicBrightness = graphicProps->propFgDynamicBrightnessOption->GetJsonObject();
5895             DumpLog::GetInstance().AddDesc(
5896                 std::string("foregroundBrightness:").append(fgDynamicBrightness->ToString().c_str()));
5897         }
5898         if (graphicProps->propBgDynamicBrightnessOption.has_value()) {
5899             auto bgDynamicBrightness = graphicProps->propBgDynamicBrightnessOption->GetJsonObject();
5900             DumpLog::GetInstance().AddDesc(
5901                 std::string("backgroundBrightnessInternal:").append(bgDynamicBrightness->ToString().c_str()));
5902         }
5903         if (!NearZero(rsNode_->GetStagingProperties().GetCameraDistance())) {
5904             DumpLog::GetInstance().AddDesc(
5905                 std::string("CameraDistance:")
5906                     .append(std::to_string(rsNode_->GetStagingProperties().GetCameraDistance())));
5907         }
5908         if (!NearZero(rsNode_->GetStagingProperties().GetTranslateZ())) {
5909             DumpLog::GetInstance().AddDesc(
5910                 std::string("TranslateZ:").append(std::to_string(rsNode_->GetStagingProperties().GetTranslateZ())));
5911         }
5912         if (!NearZero(rsNode_->GetStagingProperties().GetBgImageWidth())) {
5913             res.append(" BgImageWidth:").append(std::to_string(rsNode_->GetStagingProperties().GetBgImageWidth()));
5914         }
5915         if (!NearZero(rsNode_->GetStagingProperties().GetBgImageHeight())) {
5916             res.append(" BgImageHeight:").append(std::to_string(rsNode_->GetStagingProperties().GetBgImageHeight()));
5917         }
5918         if (!NearZero(rsNode_->GetStagingProperties().GetBgImagePositionX())) {
5919             res.append(" BgImagePositionX")
5920                 .append(std::to_string(rsNode_->GetStagingProperties().GetBgImagePositionX()));
5921         }
5922         if (!NearZero(rsNode_->GetStagingProperties().GetBgImagePositionY())) {
5923             res.append(" BgImagePositionY")
5924                 .append(std::to_string(rsNode_->GetStagingProperties().GetBgImagePositionY()));
5925         }
5926         if (!res.empty()) {
5927             DumpLog::GetInstance().AddDesc(res);
5928             res.clear();
5929         }
5930         if (!NearZero(rsNode_->GetStagingProperties().GetShadowOffsetX())) {
5931             res.append(" ShadowOffsetX:").append(std::to_string(rsNode_->GetStagingProperties().GetShadowOffsetX()));
5932         }
5933         if (!NearZero(rsNode_->GetStagingProperties().GetShadowOffsetY())) {
5934             res.append(" ShadowOffsetY:").append(std::to_string(rsNode_->GetStagingProperties().GetShadowOffsetY()));
5935         }
5936         if (!NearZero(rsNode_->GetStagingProperties().GetShadowAlpha())) {
5937             res.append(" ShadowAlpha:").append(std::to_string(rsNode_->GetStagingProperties().GetShadowAlpha()));
5938         }
5939         if (!NearZero(rsNode_->GetStagingProperties().GetShadowElevation())) {
5940             res.append(" ShadowElevation:")
5941                 .append(std::to_string(rsNode_->GetStagingProperties().GetShadowElevation()));
5942         }
5943         if (!NearZero(rsNode_->GetStagingProperties().GetShadowRadius())) {
5944             res.append(" ShadowRadius:").append(std::to_string(rsNode_->GetStagingProperties().GetShadowRadius()));
5945         }
5946         if (!res.empty()) {
5947             DumpLog::GetInstance().AddDesc(res);
5948             res.clear();
5949         }
5950         if (!NearZero(rsNode_->GetStagingProperties().GetSpherizeDegree())) {
5951             DumpLog::GetInstance().AddDesc(
5952                 std::string("SpherizeDegree:")
5953                     .append(std::to_string(rsNode_->GetStagingProperties().GetSpherizeDegree())));
5954         }
5955         if (!NearZero(rsNode_->GetStagingProperties().GetLightUpEffectDegree())) {
5956             DumpLog::GetInstance().AddDesc(
5957                 std::string("LightUpEffectDegree:")
5958                     .append(std::to_string(rsNode_->GetStagingProperties().GetLightUpEffectDegree())));
5959         }
5960         if (!NearEqual(rsNode_->GetStagingProperties().GetAlpha(), 1)) {
5961             DumpLog::GetInstance().AddDesc(
5962                 std::string("Alpha:").append(std::to_string(rsNode_->GetStagingProperties().GetAlpha())));
5963         }
5964         auto translate = rsNode_->GetStagingProperties().GetTranslate();
5965         if (!(NearZero(translate[0]) && NearZero(translate[1]))) {
5966             DumpLog::GetInstance().AddDesc(
5967                 std::string("translate(x,y): ")
5968                     .append(std::to_string(translate[0]).append(",").append(std::to_string(translate[1]))));
5969         }
5970         auto scale = rsNode_->GetStagingProperties().GetScale();
5971         if (!(NearEqual(scale[0], 1) && NearEqual(scale[1], 1))) {
5972             DumpLog::GetInstance().AddDesc(
5973                 std::string("scale(x,y): ")
5974                     .append(std::to_string(scale[0]).append(",").append(std::to_string(scale[1]))));
5975         }
5976         auto rect = GetPaintRectWithoutTransform();
5977         if (HasTransformTranslate()) {
5978             auto translateArk = GetTransformTranslate().value();
5979             auto arkTranslateX = translateArk.x.ConvertToPxWithSize(rect.Width());
5980             auto arkTranslateY = translateArk.y.ConvertToPxWithSize(rect.Height());
5981             if (!NearEqual(arkTranslateX, translate[0])) {
5982                 DumpLog::GetInstance().AddDesc(
5983                     std::string("TranlateX has difference,arkui:").append(std::to_string(arkTranslateX)));
5984             }
5985             if (!NearEqual(arkTranslateY, translate[1])) {
5986                 DumpLog::GetInstance().AddDesc(
5987                     std::string("TranlateY has difference,arkui:").append(std::to_string(arkTranslateY)));
5988             }
5989         }
5990         if (HasTransformScale()) {
5991             auto arkTransformScale = GetTransformScale().value();
5992             if (!NearEqual(arkTransformScale.x, scale[0])) {
5993                 DumpLog::GetInstance().AddDesc(
5994                     std::string("scaleX has difference,arkui:").append(std::to_string(arkTransformScale.x)));
5995             }
5996             if (!NearEqual(arkTransformScale.y, scale[1])) {
5997                 DumpLog::GetInstance().AddDesc(
5998                     std::string("scaleY has difference,arkui:").append(std::to_string(arkTransformScale.y)));
5999             }
6000         }
6001         if (HasOpacity()) {
6002             auto arkAlpha = GetOpacity();
6003             if (!NearEqual(arkAlpha.value(), rsNode_->GetStagingProperties().GetAlpha())) {
6004                 DumpLog::GetInstance().AddDesc(
6005                     std::string("Alpha has difference,arkui:").append(std::to_string(arkAlpha.value())));
6006             }
6007         }
6008         if (HasPosition()) {
6009             auto position = GetPosition();
6010             DumpLog::GetInstance().AddDesc(std::string("PositionX :")
6011                                                .append(position->GetX().ToString().c_str())
6012                                                .append(std::string(",PositionY :"))
6013                                                .append(position->GetY().ToString().c_str()));
6014         }
6015         if (HasOffset()) {
6016             auto offset = GetOffset();
6017             DumpLog::GetInstance().AddDesc(std::string("OffsetX :")
6018                                                .append(offset->GetX().ToString().c_str())
6019                                                .append(std::string(",OffsetY :"))
6020                                                .append(offset->GetY().ToString().c_str()));
6021         }
6022         if (HasPositionEdges()) {
6023             auto positionEdges = GetPositionEdges();
6024             DumpLog::GetInstance().AddDesc(std::string("positionEdges :").append(positionEdges->ToString().c_str()));
6025         }
6026         if (HasOffsetEdges()) {
6027             auto offsetEdges = GetOffsetEdges();
6028             DumpLog::GetInstance().AddDesc(std::string("offsetEdges :").append(offsetEdges->ToString().c_str()));
6029         }
6030         if (HasAnchor()) {
6031             auto anchor = GetAnchor();
6032             DumpLog::GetInstance().AddDesc(std::string("anchorX :")
6033                                                .append(anchor->GetX().ToString().c_str())
6034                                                .append(std::string(",anchorY :"))
6035                                                .append(anchor->GetY().ToString().c_str()));
6036         }
6037 
6038         auto rsBlendMode = static_cast<int16_t>(rsNode_->GetStagingProperties().GetColorBlendMode());
6039         if (GetBackBlendMode().has_value() || rsBlendMode) {
6040             DumpLog::GetInstance().AddDesc(
6041                 std::string("blendMode:") + std::to_string(rsBlendMode));
6042             auto blendMode = static_cast<int16_t>(GetBackBlendMode().value_or(BlendMode::NONE));
6043             if (rsBlendMode != blendMode) {
6044                 DumpLog::GetInstance().AddDesc(
6045                     std::string("blendMode has difference,arkui:") + std::to_string(blendMode));
6046             }
6047         }
6048 
6049         auto rsBlendApplyType = static_cast<int16_t>(rsNode_->GetStagingProperties().GetColorBlendApplyType());
6050         if (GetBackBlendApplyType().has_value() || rsBlendApplyType) {
6051             DumpLog::GetInstance().AddDesc(
6052                 std::string("blendApplyType:") + std::to_string(rsBlendApplyType));
6053             auto blendApplyType = static_cast<int16_t>(GetBackBlendApplyType().value_or(BlendApplyType::FAST));
6054             if (rsBlendApplyType != blendApplyType) {
6055                 DumpLog::GetInstance().AddDesc(
6056                     std::string("blendApplyType has difference,arkui:") + std::to_string(blendApplyType));
6057             }
6058         }
6059     }
6060     if (disappearingTransitionCount_) {
6061         DumpLog::GetInstance().AddDesc(
6062             std::string("transitionCnt:").append(std::to_string(disappearingTransitionCount_))
6063         );
6064     }
6065 
6066     if (HasProgressMask() && GetProgressMaskValue()) {
6067         auto progressMaskPropertyPtr = GetProgressMaskValue();
6068         DumpLog::GetInstance().AddDesc(
6069             std::string("ProgressMaskProperty value:") + std::to_string(progressMaskPropertyPtr->GetValue())
6070             + " maxValue:" + std::to_string(progressMaskPropertyPtr->GetMaxValue()) + " color:"
6071             + progressMaskPropertyPtr->GetColor().ToString() + " enableBreathe:"
6072             + std::to_string(progressMaskPropertyPtr->GetEnableBreathe())
6073         );
6074     }
6075 }
6076 
DumpAdvanceInfo()6077 void RosenRenderContext::DumpAdvanceInfo()
6078 {
6079     if (GetBackgroundAlign().has_value()) {
6080         DumpLog::GetInstance().AddDesc("BackgroundAlign:" + GetBackgroundAlign().value().ToString());
6081     }
6082     if (GetBackgroundImage().has_value()) {
6083         DumpLog::GetInstance().AddDesc("BackgroundImage:" + GetBackgroundImage().value().ToString());
6084     }
6085     if (GetSphericalEffect().has_value()) {
6086         DumpLog::GetInstance().AddDesc("SphericalEffect:" + std::to_string(GetSphericalEffect().value()));
6087     }
6088     if (GetPixelStretchEffect().has_value()) {
6089         DumpLog::GetInstance().AddDesc("PixelStretchEffect:" + GetPixelStretchEffect().value().ToString());
6090     }
6091     if (GetLightUpEffect().has_value()) {
6092         DumpLog::GetInstance().AddDesc("LightUpEffect:" + std::to_string(GetLightUpEffect().value()));
6093     }
6094     if (GetBorderColor().has_value()) {
6095         DumpLog::GetInstance().AddDesc("BorderColor:" + GetBorderColor().value().ToString());
6096     }
6097     if (GetBorderWidth().has_value()) {
6098         DumpLog::GetInstance().AddDesc("BorderWidth:" + GetBorderWidth().value().ToString());
6099     }
6100     if (GetOuterBorderRadius().has_value()) {
6101         DumpLog::GetInstance().AddDesc("OuterBorderRadius:" + GetOuterBorderRadius().value().ToString());
6102     }
6103     if (GetOuterBorderColor().has_value()) {
6104         DumpLog::GetInstance().AddDesc("OuterBorderColor:" + GetOuterBorderColor().value().ToString());
6105     }
6106     if (GetOuterBorderWidth().has_value()) {
6107         DumpLog::GetInstance().AddDesc("OuterBorderWidth:" + GetOuterBorderWidth().value().ToString());
6108     }
6109     if (GetDynamicLightUpRate().has_value()) {
6110         DumpLog::GetInstance().AddDesc("DynamicLightUpRate:" + std::to_string(GetDynamicLightUpRate().value()));
6111     }
6112     if (GetDynamicLightUpDegree().has_value()) {
6113         DumpLog::GetInstance().AddDesc("DynamicLightUpDegree:" + std::to_string(GetDynamicLightUpDegree().value()));
6114     }
6115     if (GetBackBlendMode().has_value()) {
6116         DumpLog::GetInstance().AddDesc("BlendMode:" + std::to_string(static_cast<int>(GetBackBlendMode().value())));
6117     }
6118     if (GetLinearGradient().has_value()) {
6119         DumpLog::GetInstance().AddDesc("LinearGradient:" + GetLinearGradient().value().ToString());
6120     }
6121     if (GetSweepGradient().has_value()) {
6122         DumpLog::GetInstance().AddDesc("SweepGradient:" + GetSweepGradient().value().ToString());
6123     }
6124     if (GetRadialGradient().has_value()) {
6125         DumpLog::GetInstance().AddDesc("RadialGradient:" + GetRadialGradient().value().ToString());
6126     }
6127     if (GetFrontBrightness().has_value()) {
6128         DumpLog::GetInstance().AddDesc("FrontBrightness:" + GetFrontBrightness().value().ToString());
6129     }
6130     if (GetFrontGrayScale().has_value()) {
6131         DumpLog::GetInstance().AddDesc("FrontGrayScale:" + GetFrontGrayScale().value().ToString());
6132     }
6133     if (GetFrontContrast().has_value()) {
6134         DumpLog::GetInstance().AddDesc("FrontContrast:" + GetFrontContrast().value().ToString());
6135     }
6136     if (GetFrontSaturate().has_value()) {
6137         DumpLog::GetInstance().AddDesc("FrontSaturate:" + GetFrontSaturate().value().ToString());
6138     }
6139     if (GetFrontSepia().has_value()) {
6140         DumpLog::GetInstance().AddDesc("FrontSepia:" + GetFrontSepia().value().ToString());
6141     }
6142     if (GetFrontHueRotate().has_value()) {
6143         DumpLog::GetInstance().AddDesc("FrontHueRotate:" + std::to_string(GetFrontHueRotate().value()));
6144     }
6145     if (GetFrontColorBlend().has_value()) {
6146         DumpLog::GetInstance().AddDesc("FrontColorBlend:" + GetFrontColorBlend().value().ColorToString());
6147     }
6148     if (GetBorderImageSource().has_value()) {
6149         DumpLog::GetInstance().AddDesc("BorderImageSource:" + GetBorderImageSource().value().ToString());
6150     }
6151     if (GetBorderImageGradient().has_value()) {
6152         DumpLog::GetInstance().AddDesc("BorderImageGradient:" + GetBorderImageGradient().value().ToString());
6153     }
6154     if (GetForegroundColor().has_value()) {
6155         DumpLog::GetInstance().AddDesc("ForegroundColor:" + GetForegroundColor().value().ColorToString());
6156     }
6157     if (GetLightIntensity().has_value()) {
6158         DumpLog::GetInstance().AddDesc("LightIntensity:" + std::to_string(GetLightIntensity().value()));
6159     }
6160     if (GetLightIlluminated().has_value()) {
6161         DumpLog::GetInstance().AddDesc("LightIlluminated:" + std::to_string(GetLightIlluminated().value()));
6162     }
6163     if (GetIlluminatedBorderWidth().has_value()) {
6164         DumpLog::GetInstance().AddDesc("IlluminatedBorderWidth:" + GetIlluminatedBorderWidth().value().ToString());
6165     }
6166     if (GetBloom().has_value()) {
6167         DumpLog::GetInstance().AddDesc("Bloom:" + std::to_string(GetBloom().value()));
6168     }
6169 }
6170 
MarkContentChanged(bool isChanged)6171 void RosenRenderContext::MarkContentChanged(bool isChanged)
6172 {
6173     CHECK_NULL_VOID(rsNode_);
6174     rsNode_->MarkContentChanged(isChanged);
6175 }
6176 
MarkDrivenRender(bool flag)6177 void RosenRenderContext::MarkDrivenRender(bool flag)
6178 {
6179     CHECK_NULL_VOID(rsNode_);
6180     rsNode_->MarkDrivenRender(flag);
6181 }
6182 
MarkDrivenRenderItemIndex(int32_t index)6183 void RosenRenderContext::MarkDrivenRenderItemIndex(int32_t index)
6184 {
6185     CHECK_NULL_VOID(rsNode_);
6186     rsNode_->MarkDrivenRenderItemIndex(index);
6187 }
6188 
MarkDrivenRenderFramePaintState(bool flag)6189 void RosenRenderContext::MarkDrivenRenderFramePaintState(bool flag)
6190 {
6191     CHECK_NULL_VOID(rsNode_);
6192     rsNode_->MarkDrivenRenderFramePaintState(flag);
6193 }
6194 
UpdateChainedTransition(const RefPtr<NG::ChainedTransitionEffect> & effect)6195 void RosenRenderContext::UpdateChainedTransition(const RefPtr<NG::ChainedTransitionEffect>& effect)
6196 {
6197     if (transitionEffect_) {
6198         // use effect to update rosenTransitionEffect activeValue
6199         if (RosenTransitionEffect::UpdateRosenTransitionEffect(transitionEffect_, effect)) {
6200             return;
6201         }
6202         transitionEffect_->Detach(this);
6203     }
6204     transitionEffect_ = RosenTransitionEffect::ConvertToRosenTransitionEffect(effect);
6205     hasDefaultTransition_ = false;
6206     CHECK_NULL_VOID(transitionEffect_);
6207     auto frameNode = GetHost();
6208     CHECK_NULL_VOID(frameNode);
6209     bool isOnTheTree = frameNode->IsOnMainTree();
6210     CHECK_NULL_VOID(rsNode_);
6211     auto rsUIContext = rsNode_->GetRSUIContext();
6212     // transition effects should be initialized without animation.
6213     RSNode::ExecuteWithoutAnimation([this, isOnTheTree]() {
6214         // transitionIn effects should be initialized as active if currently not on the tree.
6215         transitionEffect_->Attach(Claim(this), !isOnTheTree);
6216         }, rsUIContext);
6217 }
6218 
NotifyTransition(bool isTransitionIn)6219 void RosenRenderContext::NotifyTransition(bool isTransitionIn)
6220 {
6221     CHECK_NULL_VOID(transitionEffect_);
6222 
6223     auto frameNode = GetHost();
6224     CHECK_NULL_VOID(frameNode);
6225     CHECK_NULL_VOID(rsNode_);
6226     auto pipeline = Claim(frameNode->GetContextWithCheck());
6227     CHECK_NULL_VOID(pipeline);
6228     auto rsUIContext = rsNode_->GetRSUIContext();
6229     RSNode::ExecuteWithoutAnimation([this, &frameNode, isTransitionIn, &pipeline]() {
6230             if (isTransitionIn && disappearingTransitionCount_ == 0 && appearingTransitionCount_ == 0) {
6231                 // transitionIn, reset to state before attaching in case of node reappear
6232                 transitionEffect_->Attach(Claim(this), true);
6233             }
6234             SizeF rootSize(pipeline->GetRootWidth(), pipeline->GetRootHeight());
6235             auto parentOffset = frameNode->GetPaintRectOffset(true);
6236             auto rect = GetPaintRectWithoutTransform();
6237             // Do not consider the position after its own transform,
6238             // as the transition modifier also affects the transform
6239             rect.SetOffset(parentOffset + rect.GetOffset());
6240 
6241             transitionEffect_->UpdateTransitionContext(Claim(this), rect, rootSize);
6242         }, rsUIContext);
6243 
6244     if (isTransitionIn) {
6245         // Isolate the animation callback function, to avoid changing the callback timing of current implicit animation.
6246         AnimationUtils::AnimateWithCurrentOptions(
6247             [this]() {
6248                 transitionEffect_->Appear();
6249                 ++appearingTransitionCount_;
6250             },
6251             [weakThis = WeakClaim(this)]() {
6252                 auto context = weakThis.Upgrade();
6253                 CHECK_NULL_VOID(context);
6254                 context->OnTransitionInFinish();
6255             },
6256             false, pipeline);
6257     } else {
6258         if (!transitionEffect_->HasDisappearTransition()) {
6259             if (frameNode->GetTag() == V2::WINDOW_SCENE_ETS_TAG) {
6260                 auto frameParent = frameNode->GetAncestorNodeOfFrame(false);
6261                 CHECK_NULL_VOID(frameParent);
6262                 // for window surfaceNode, remove surfaceNode explicitly
6263                 frameParent->GetRenderContext()->RemoveChild(Claim(this));
6264             }
6265             if (transitionUserCallback_ && !disappearingTransitionCount_) {
6266                 PostTransitionUserOutCallback();
6267             }
6268             return;
6269         }
6270         // Re-use current implicit animation timing params, only replace the finish callback function.
6271         // The finish callback function will perform all the necessary cleanup work.
6272         // Important Note on timing:
6273         // 1. If any transition animations are created, the finish callback function will only be called when ALL
6274         //    animations have finished. This is accomplished by sharing the same shared_ptr<AnimationFinishCallback>
6275         //    among all animations.
6276         // 2. If no transition animations are created, the finish callback function will be called IMMEDIATELY. This
6277         //    is accomplished by setting the last param (timing sensitive) to false, which avoids creating an empty
6278         //    'timer' animation.
6279         AnimationUtils::AnimateWithCurrentOptions(
6280             [this]() {
6281                 transitionEffect_->Disappear();
6282                 // update transition out count
6283                 ++disappearingTransitionCount_;
6284             },
6285             [weakThis = WeakClaim(this), nodeId = frameNode->GetId(), id = Container::CurrentId()]() {
6286                 auto context = weakThis.Upgrade();
6287                 CHECK_NULL_VOID(context);
6288                 // update transition out count
6289                 context->OnTransitionOutFinish();
6290             },
6291             false, pipeline);
6292     }
6293     auto host = GetHost();
6294     CHECK_NULL_VOID(host);
6295     host->NotifyTransformInfoChanged();
6296     host->OnNodeTransitionInfoUpdate();
6297 }
6298 
RemoveDefaultTransition()6299 void RosenRenderContext::RemoveDefaultTransition()
6300 {
6301     if (hasDefaultTransition_ && transitionEffect_ && disappearingTransitionCount_ == 0 &&
6302         appearingTransitionCount_ == 0) {
6303         transitionEffect_->Detach(this);
6304         transitionEffect_ = nullptr;
6305         hasDefaultTransition_ = false;
6306     }
6307 }
6308 
OnTransitionInFinish()6309 void RosenRenderContext::OnTransitionInFinish()
6310 {
6311     --appearingTransitionCount_;
6312     // make sure we are the last transition out animation, if not, return.
6313     if (appearingTransitionCount_ > 0) {
6314         return;
6315     }
6316     if (appearingTransitionCount_ < 0) {
6317         appearingTransitionCount_ = 0;
6318     }
6319     // when all transition in/out animations are finished, we should remove the default transition effect.
6320     RemoveDefaultTransition();
6321     auto host = GetHost();
6322     CHECK_NULL_VOID(host);
6323     FireTransitionUserCallback(true);
6324     auto parent = host->GetParent();
6325     CHECK_NULL_VOID(parent);
6326     if (host->IsVisible()) {
6327         // trigger transition through visibility
6328         if (transitionInCallback_) {
6329             transitionInCallback_();
6330         }
6331     }
6332 }
6333 
OnTransitionOutFinish()6334 void RosenRenderContext::OnTransitionOutFinish()
6335 {
6336     // update transition out count
6337     --disappearingTransitionCount_;
6338     // make sure we are the last transition out animation, if not, return.
6339     if (disappearingTransitionCount_ > 0) {
6340         return;
6341     }
6342     if (disappearingTransitionCount_ < 0) {
6343         disappearingTransitionCount_ = 0;
6344     }
6345     // when all transition in/out animations are finished, we should remove the default transition effect.
6346     RemoveDefaultTransition();
6347     auto host = GetHost();
6348     CHECK_NULL_VOID(host);
6349     auto parent = host->GetParent();
6350     CHECK_NULL_VOID(parent);
6351     if (!host->IsVisible()) {
6352         // trigger transition through visibility
6353         if (host->IsOnMainTree()) {
6354             if (transitionOutCallback_) {
6355                 transitionOutCallback_();
6356             }
6357             parent->MarkNeedSyncRenderTree();
6358             parent->RebuildRenderContextTree();
6359             FireTransitionUserCallback(false);
6360             return;
6361         }
6362         parent->MarkNeedSyncRenderTree();
6363         parent->RebuildRenderContextTree();
6364     }
6365     RefPtr<UINode> breakPointChild = host;
6366     RefPtr<UINode> breakPointParent = breakPointChild->GetParent();
6367     UINode::GetBestBreakPoint(breakPointChild, breakPointParent);
6368     // if can not find the breakPoint, means the node is not disappearing (reappear? or the node of subtree), return.
6369     if (!breakPointParent) {
6370         FireTransitionUserCallback(false);
6371         return;
6372     }
6373     if (breakPointChild->RemoveImmediately()) {
6374         breakPointChild->OnRemoveFromParent(false);
6375         // remove breakPoint
6376         breakPointParent->RemoveDisappearingChild(breakPointChild);
6377         breakPointParent->MarkNeedSyncRenderTree();
6378         breakPointParent->RebuildRenderContextTree();
6379     }
6380     if (isModalRootNode_ && breakPointParent->GetChildren().empty()) {
6381         auto grandParent = breakPointParent->GetParent();
6382         CHECK_NULL_VOID(grandParent);
6383         grandParent->RemoveChild(breakPointParent);
6384         grandParent->RebuildRenderContextTree();
6385     }
6386     FireTransitionUserCallback(false);
6387 }
6388 
FireTransitionUserCallback(bool isTransitionIn)6389 void RosenRenderContext::FireTransitionUserCallback(bool isTransitionIn)
6390 {
6391     if (transitionUserCallback_) {
6392         auto callback = transitionUserCallback_;
6393         callback(isTransitionIn);
6394     }
6395 }
6396 
PostTransitionUserOutCallback()6397 void RosenRenderContext::PostTransitionUserOutCallback()
6398 {
6399     auto taskExecutor = Container::CurrentTaskExecutor();
6400     CHECK_NULL_VOID(taskExecutor);
6401     // post the callback to let it run on isolate environment
6402     taskExecutor->PostTask(
6403         [callback = transitionUserCallback_]() {
6404             if (callback) {
6405                 callback(false);
6406             }
6407         },
6408         TaskExecutor::TaskType::UI, "ArkUITransitionOutFinishCallback", PriorityType::HIGH);
6409 }
6410 
SetActualForegroundColor(const Color & value)6411 void RosenRenderContext::SetActualForegroundColor(const Color& value)
6412 {
6413     CHECK_NULL_VOID(rsNode_);
6414     rsNode_->SetForegroundColor(value.GetValue());
6415     RequestNextFrame();
6416 }
6417 
AttachNodeAnimatableProperty(RefPtr<NodeAnimatablePropertyBase> property)6418 void RosenRenderContext::AttachNodeAnimatableProperty(RefPtr<NodeAnimatablePropertyBase> property)
6419 {
6420     CHECK_NULL_VOID(rsNode_);
6421     CHECK_NULL_VOID(property);
6422     if (!property->GetModifyImpl()) {
6423         auto nodeModifierImpl = std::make_shared<RSNodeModifierImpl>();
6424         CHECK_NULL_VOID(nodeModifierImpl);
6425         property->SetModifyImpl(nodeModifierImpl);
6426         rsNode_->AddModifier(nodeModifierImpl);
6427         nodeModifierImpl->AddProperty(property->GetProperty());
6428     }
6429 }
6430 
DetachNodeAnimatableProperty(const RefPtr<NodeAnimatablePropertyBase> & property)6431 void RosenRenderContext::DetachNodeAnimatableProperty(const RefPtr<NodeAnimatablePropertyBase>& property)
6432 {
6433     CHECK_NULL_VOID(rsNode_);
6434     CHECK_NULL_VOID(property);
6435     std::shared_ptr<RSNodeModifierImpl> modifier =
6436         std::static_pointer_cast<RSNodeModifierImpl>(property->GetModifyImpl());
6437     RemoveModifier(modifier);
6438 }
6439 
InitEventClickEffect()6440 void RosenRenderContext::InitEventClickEffect()
6441 {
6442     if (touchListener_) {
6443         return;
6444     }
6445     auto host = GetHost();
6446     CHECK_NULL_VOID(host);
6447     auto gesture = host->GetOrCreateGestureEventHub();
6448     CHECK_NULL_VOID(gesture);
6449     auto touchCallback = [weak = WeakClaim(this)](const TouchEventInfo& info) {
6450         auto renderContext = weak.Upgrade();
6451         CHECK_NULL_VOID(renderContext);
6452         renderContext->ClickEffectPlayAnimation(info.GetTouches().front().GetTouchType());
6453     };
6454     touchListener_ = MakeRefPtr<TouchEventImpl>(std::move(touchCallback));
6455     gesture->AddTouchEvent(touchListener_);
6456 }
6457 
ClickEffectPlayAnimation(const TouchType & touchType)6458 void RosenRenderContext::ClickEffectPlayAnimation(const TouchType& touchType)
6459 {
6460     if (touchType != TouchType::DOWN && touchType != TouchType::UP && touchType != TouchType::CANCEL) {
6461         return;
6462     }
6463     auto value = GetClickEffectLevelValue();
6464     auto level = value.level;
6465     auto scaleValue = value.scaleNumber;
6466     auto springCurve = UpdatePlayAnimationValue(level, scaleValue);
6467 
6468     AnimationOption option;
6469     option.SetCurve(springCurve);
6470     option.SetDuration(DEFAULT_OPTION_DURATION);
6471 
6472     if (touchType == TouchType::DOWN && level != ClickEffectLevel::UNDEFINED) {
6473         if (isTouchUpFinished_) {
6474             auto defaultScale = VectorF(1.0f, 1.0f);
6475             auto currentScale = GetTransformScaleValue(defaultScale);
6476             currentScale_ = currentScale;
6477             UpdateTransformScale(currentScale_);
6478 
6479             AnimationUtils::OpenImplicitAnimation(option, springCurve, nullptr);
6480             VectorF valueScale(scaleValue, scaleValue);
6481             UpdateTransformScale(valueScale);
6482             AnimationUtils::CloseImplicitAnimation();
6483         }
6484         isTouchUpFinished_ = false;
6485     }
6486 
6487     if ((touchType == TouchType::UP || touchType == TouchType::CANCEL) && level != ClickEffectLevel::UNDEFINED) {
6488         AnimationUtils::OpenImplicitAnimation(option, springCurve, nullptr);
6489         UpdateTransformScale(currentScale_);
6490         AnimationUtils::CloseImplicitAnimation();
6491         isTouchUpFinished_ = true;
6492     }
6493 }
6494 
UpdatePlayAnimationValue(const ClickEffectLevel & level,float & scaleValue)6495 RefPtr<Curve> RosenRenderContext::UpdatePlayAnimationValue(const ClickEffectLevel& level, float& scaleValue)
6496 {
6497     float velocity = 0.0f;
6498     float mass = 0.0f;
6499     float stiffness = 0.0f;
6500     float damping = 0.0f;
6501     if (level == ClickEffectLevel::LIGHT) {
6502         velocity = ANIMATION_CURVE_VELOCITY_LIGHT_OR_MIDDLE;
6503         mass = ANIMATION_CURVE_MASS;
6504         stiffness = ANIMATION_CURVE_STIFFNESS_LIGHT;
6505         damping = ANIMATION_CURVE_DAMPING_LIGHT;
6506         if (GreatOrEqual(scaleValue, 0.0) && LessOrEqual(scaleValue, 1.0)) {
6507             scaleValue = sqrt(scaleValue);
6508         } else {
6509             scaleValue = sqrt(DEFAULT_SCALE_LIGHT);
6510         }
6511     } else if (level == ClickEffectLevel::MIDDLE) {
6512         velocity = ANIMATION_CURVE_VELOCITY_LIGHT_OR_MIDDLE;
6513         mass = ANIMATION_CURVE_MASS;
6514         stiffness = ANIMATION_CURVE_STIFFNESS_MIDDLE;
6515         damping = ANIMATION_CURVE_DAMPING_MIDDLE;
6516         if (GreatOrEqual(scaleValue, 0.0) && LessOrEqual(scaleValue, 1.0)) {
6517             scaleValue = sqrt(scaleValue);
6518         } else {
6519             scaleValue = sqrt(DEFAULT_SCALE_MIDDLE_OR_HEAVY);
6520         }
6521     } else if (level == ClickEffectLevel::HEAVY) {
6522         velocity = ANIMATION_CURVE_VELOCITY_HEAVY;
6523         mass = ANIMATION_CURVE_MASS;
6524         stiffness = ANIMATION_CURVE_STIFFNESS_HEAVY;
6525         damping = ANIMATION_CURVE_DAMPING_HEAVY;
6526         if (GreatOrEqual(scaleValue, 0.0) && LessOrEqual(scaleValue, 1.0)) {
6527             scaleValue = sqrt(scaleValue);
6528         } else {
6529             scaleValue = sqrt(DEFAULT_SCALE_MIDDLE_OR_HEAVY);
6530         }
6531     }
6532     return AceType::MakeRefPtr<InterpolatingSpring>(velocity, mass, stiffness, damping);
6533 }
6534 
RegisterSharedTransition(const RefPtr<RenderContext> & other,const bool isInSameWindow)6535 void RosenRenderContext::RegisterSharedTransition(const RefPtr<RenderContext>& other, const bool isInSameWindow)
6536 {
6537     auto otherContext = AceType::DynamicCast<RosenRenderContext>(other);
6538     if (!otherContext) {
6539         return;
6540     }
6541     CHECK_NULL_VOID(rsNode_);
6542     auto rsUIContext = rsNode_->GetRSUIContext();
6543     RSNode::RegisterTransitionPair(rsUIContext, rsNode_->GetId(), otherContext->rsNode_->GetId(), isInSameWindow);
6544 }
6545 
UnregisterSharedTransition(const RefPtr<RenderContext> & other)6546 void RosenRenderContext::UnregisterSharedTransition(const RefPtr<RenderContext>& other)
6547 {
6548     auto otherContext = AceType::DynamicCast<RosenRenderContext>(other);
6549     if (!otherContext) {
6550         // the paired node is already destroyed, we don't need to unregister it, Rosen will handle it.
6551         return;
6552     }
6553     CHECK_NULL_VOID(rsNode_);
6554     auto rsUIContext = rsNode_->GetRSUIContext();
6555     RSNode::UnregisterTransitionPair(rsUIContext, rsNode_->GetId(), otherContext->rsNode_->GetId());
6556 }
6557 
ConvertRadius(const BorderRadiusProperty & value,Rosen::Vector4f & cornerRadius)6558 inline void RosenRenderContext::ConvertRadius(const BorderRadiusProperty& value, Rosen::Vector4f& cornerRadius)
6559 {
6560     cornerRadius.SetValues(static_cast<float>(value.radiusTopLeft.value_or(Dimension()).ConvertToPx()),
6561         static_cast<float>(value.radiusTopRight.value_or(Dimension()).ConvertToPx()),
6562         static_cast<float>(value.radiusBottomRight.value_or(Dimension()).ConvertToPx()),
6563         static_cast<float>(value.radiusBottomLeft.value_or(Dimension()).ConvertToPx()));
6564 }
6565 
PaintRSBgImage()6566 void RosenRenderContext::PaintRSBgImage()
6567 {
6568     auto image = DynamicCast<NG::DrawingImage>(bgImage_);
6569     CHECK_NULL_VOID(bgLoadingCtx_ && image);
6570     CHECK_NULL_VOID(rsNode_);
6571     auto rosenImage = std::make_shared<Rosen::RSImage>();
6572     auto compressData = image->GetCompressData();
6573     if (compressData) {
6574         rosenImage->SetCompressData(
6575             compressData, image->GetUniqueID(), image->GetCompressWidth(), image->GetCompressHeight());
6576     } else {
6577         rosenImage->SetImage(image->GetImage());
6578     }
6579     if (!HasValidBgImageResizable()) {
6580         rosenImage->SetImageRepeat(static_cast<int>(GetBackgroundImageRepeat().value_or(ImageRepeat::NO_REPEAT)));
6581     }
6582     rsNode_->SetBgImage(rosenImage);
6583 }
6584 
PaintPixmapBgImage()6585 void RosenRenderContext::PaintPixmapBgImage()
6586 {
6587     CHECK_NULL_VOID(rsNode_);
6588     auto image = DynamicCast<NG::PixelMapImage>(bgImage_);
6589     CHECK_NULL_VOID(bgLoadingCtx_ && image);
6590     auto pixmap = image->GetPixelMap();
6591     CHECK_NULL_VOID(pixmap);
6592 
6593     auto rosenImage = std::make_shared<Rosen::RSImage>();
6594     rosenImage->SetPixelMap(pixmap->GetPixelMapSharedPtr());
6595     if (!HasValidBgImageResizable()) {
6596         rosenImage->SetImageRepeat(static_cast<int>(GetBackgroundImageRepeat().value_or(ImageRepeat::NO_REPEAT)));
6597     }
6598     rsNode_->SetBgImage(rosenImage);
6599     auto host = GetHost();
6600     CHECK_NULL_VOID(host);
6601     ACE_SCOPED_TRACE("PaintPixmapBgImage_node(%s/%d)", host->GetTag().c_str(), host->GetId());
6602 }
6603 
OnRenderGroupUpdate(bool isRenderGroup)6604 void RosenRenderContext::OnRenderGroupUpdate(bool isRenderGroup)
6605 {
6606     CHECK_NULL_VOID(rsNode_);
6607     rsNode_->MarkNodeGroup(isRenderGroup);
6608 }
6609 
UpdateRenderGroup(bool isRenderGroup,bool isForced,bool includeProperty)6610 void RosenRenderContext::UpdateRenderGroup(bool isRenderGroup, bool isForced, bool includeProperty)
6611 {
6612     CHECK_NULL_VOID(rsNode_);
6613     rsNode_->MarkNodeGroup(isRenderGroup, isForced, includeProperty);
6614 }
6615 
OnNodeNameUpdate(const std::string & id)6616 void RosenRenderContext::OnNodeNameUpdate(const std::string& id)
6617 {
6618     CHECK_NULL_VOID(rsNode_);
6619     rsNode_->SetNodeName(id);
6620 }
6621 
OnSuggestedRenderGroupUpdate(bool isRenderGroup)6622 void RosenRenderContext::OnSuggestedRenderGroupUpdate(bool isRenderGroup)
6623 {
6624     CHECK_NULL_VOID(rsNode_);
6625     rsNode_->MarkNodeGroup(isRenderGroup, false);
6626 }
6627 
OnRenderFitUpdate(RenderFit renderFit)6628 void RosenRenderContext::OnRenderFitUpdate(RenderFit renderFit)
6629 {
6630     CHECK_NULL_VOID(rsNode_);
6631     rsNode_->SetFrameGravity(GetRosenGravity(renderFit));
6632 }
6633 
SetContentRectToFrame(RectF rect)6634 void RosenRenderContext::SetContentRectToFrame(RectF rect)
6635 {
6636     CHECK_NULL_VOID(rsNode_);
6637     auto host = GetHost();
6638     CHECK_NULL_VOID(host);
6639     if (adjustRSFrameByContentRect_) {
6640         auto geometryNode = host->GetGeometryNode();
6641         CHECK_NULL_VOID(geometryNode);
6642         auto contentRect = geometryNode->GetContentRect();
6643         rect.SetOffset(rect.GetOffset() + contentRect.GetOffset());
6644         rect.SetSize(contentRect.GetSize());
6645     } else {
6646         auto&& padding = host->GetGeometryNode()->GetPadding();
6647         // minus padding to get contentRect
6648         if (padding) {
6649             rect.SetOffset(rect.GetOffset() + OffsetF { padding->left.value_or(0), padding->top.value_or(0) });
6650             auto size = rect.GetSize();
6651             MinusPaddingToSize(*padding, size);
6652             rect.SetSize(size);
6653         }
6654     }
6655     rsNode_->SetFrame(rect.GetX(), rect.GetY(), rect.Width(), rect.Height());
6656 }
6657 
MarkNewFrameAvailable(void * nativeWindow)6658 void RosenRenderContext::MarkNewFrameAvailable(void* nativeWindow)
6659 {
6660     CHECK_NULL_VOID(rsNode_);
6661     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
6662     CHECK_NULL_VOID(rsSurfaceNode);
6663 #if defined(ANDROID_PLATFORM)
6664     rsSurfaceNode->MarkUiFrameAvailable(true);
6665 #endif
6666 #if defined(IOS_PLATFORM)
6667 #if defined(PLATFORM_VIEW_SUPPORTED)
6668     if (patternType_ == PatternType::PLATFORM_VIEW) {
6669         RSSurfaceExtConfig config = {
6670             .type = RSSurfaceExtType::SURFACE_PLATFORM_TEXTURE,
6671             .additionalData = nativeWindow,
6672         };
6673         rsSurfaceNode->SetSurfaceTexture(config);
6674         rsSurfaceNode->MarkUiFrameAvailable(true);
6675         return;
6676     }
6677 #endif
6678     RSSurfaceExtConfig config = {
6679         .type = RSSurfaceExtType::SURFACE_TEXTURE,
6680         .additionalData = nativeWindow,
6681     };
6682     rsSurfaceNode->SetSurfaceTexture(config);
6683 #endif
6684 }
6685 
AddAttachCallBack(const std::function<void (int64_t,bool)> & attachCallback)6686 void RosenRenderContext::AddAttachCallBack(const std::function<void(int64_t, bool)>& attachCallback)
6687 {
6688     CHECK_NULL_VOID(rsNode_);
6689 #if defined(ANDROID_PLATFORM) || defined(IOS_PLATFORM)
6690     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
6691     CHECK_NULL_VOID(rsSurfaceNode);
6692     rsSurfaceNode->SetSurfaceTextureAttachCallBack(attachCallback);
6693 #endif
6694 }
6695 
AddUpdateCallBack(const std::function<void (std::vector<float> &)> & updateCallback)6696 void RosenRenderContext::AddUpdateCallBack(const std::function<void(std::vector<float>&)>& updateCallback)
6697 {
6698     CHECK_NULL_VOID(rsNode_);
6699 #if defined(ANDROID_PLATFORM) || defined(IOS_PLATFORM)
6700     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
6701     CHECK_NULL_VOID(rsSurfaceNode);
6702     rsSurfaceNode->SetSurfaceTextureUpdateCallBack(updateCallback);
6703 #endif
6704 }
6705 
AddInitTypeCallBack(const std::function<void (int32_t &)> & initTypeCallback)6706 void RosenRenderContext::AddInitTypeCallBack(const std::function<void(int32_t&)>& initTypeCallback)
6707 {
6708     CHECK_NULL_VOID(rsNode_);
6709 #if defined(IOS_PLATFORM)
6710     auto rsSurfaceNode = rsNode_->ReinterpretCastTo<Rosen::RSSurfaceNode>();
6711     CHECK_NULL_VOID(rsSurfaceNode);
6712     rsSurfaceNode->SetSurfaceTextureInitTypeCallBack(initTypeCallback);
6713 #endif
6714 }
6715 
IsUniRenderEnabled()6716 bool RosenRenderContext::IsUniRenderEnabled()
6717 {
6718     return Rosen::RSSystemProperties::GetUniRenderEnabled();
6719 }
6720 
SetRotation(float rotationX,float rotationY,float rotationZ)6721 void RosenRenderContext::SetRotation(float rotationX, float rotationY, float rotationZ)
6722 {
6723     CHECK_NULL_VOID(rsNode_);
6724     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotationX,
6725         float>(rotationXUserModifier_, rotationX);
6726     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotationY,
6727         float>(rotationYUserModifier_, rotationY);
6728     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotation,
6729         float>(rotationZUserModifier_, rotationZ);
6730     NotifyHostTransformUpdated();
6731 }
6732 
SetShadowColor(uint32_t color)6733 void RosenRenderContext::SetShadowColor(uint32_t color)
6734 {
6735     CHECK_NULL_VOID(rsNode_);
6736     rsNode_->SetShadowColor(color);
6737 }
6738 
SetShadowOffset(float offsetX,float offsetY)6739 void RosenRenderContext::SetShadowOffset(float offsetX, float offsetY)
6740 {
6741     CHECK_NULL_VOID(rsNode_);
6742     rsNode_->SetShadowOffset(offsetX, offsetY);
6743 }
6744 
SetShadowAlpha(float alpha)6745 void RosenRenderContext::SetShadowAlpha(float alpha)
6746 {
6747     CHECK_NULL_VOID(rsNode_);
6748     rsNode_->SetShadowAlpha(alpha);
6749 }
6750 
SetShadowElevation(float elevation)6751 void RosenRenderContext::SetShadowElevation(float elevation)
6752 {
6753     CHECK_NULL_VOID(rsNode_);
6754     rsNode_->SetShadowElevation(elevation);
6755 }
6756 
SetShadowRadius(float radius)6757 void RosenRenderContext::SetShadowRadius(float radius)
6758 {
6759     CHECK_NULL_VOID(rsNode_);
6760     rsNode_->SetShadowRadius(radius);
6761 }
6762 
SetRenderFrameOffset(const OffsetF & offset)6763 void RosenRenderContext::SetRenderFrameOffset(const OffsetF& offset)
6764 {
6765     frameOffset_ = offset;
6766 }
6767 
SetScale(float scaleX,float scaleY)6768 void RosenRenderContext::SetScale(float scaleX, float scaleY)
6769 {
6770     CHECK_NULL_VOID(rsNode_);
6771     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetScale,
6772         Rosen::Vector2f>(scaleXYUserModifier_, { scaleX, scaleY });
6773     NotifyHostTransformUpdated();
6774 }
6775 
SetScrollScale(float scale)6776 void RosenRenderContext::SetScrollScale(float scale)
6777 {
6778     CHECK_NULL_VOID(rsNode_);
6779     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetScale,
6780         Rosen::Vector2f>(scrollScaleModifier_, { scale, scale });
6781 }
6782 
ResetScrollScale()6783 void RosenRenderContext::ResetScrollScale()
6784 {
6785     CHECK_NULL_VOID(rsNode_);
6786     rsNode_->RemoveModifier(scrollScaleModifier_);
6787     scrollScaleModifier_.reset();
6788 }
6789 
SetBackgroundColor(uint32_t colorValue)6790 void RosenRenderContext::SetBackgroundColor(uint32_t colorValue)
6791 {
6792     CHECK_NULL_VOID(rsNode_);
6793     rsNode_->SetBackgroundColor(colorValue);
6794 }
6795 
SetRenderPivot(float pivotX,float pivotY)6796 void RosenRenderContext::SetRenderPivot(float pivotX, float pivotY)
6797 {
6798     CHECK_NULL_VOID(rsNode_);
6799     rsNode_->SetPivot(pivotX, pivotY);
6800     NotifyHostTransformUpdated();
6801 }
6802 
SetFrame(float positionX,float positionY,float width,float height)6803 void RosenRenderContext::SetFrame(float positionX, float positionY, float width, float height)
6804 {
6805     CHECK_NULL_VOID(rsNode_);
6806     rsNode_->SetFrame(positionX, positionY, width, height);
6807 }
6808 
SetOpacity(float opacity)6809 void RosenRenderContext::SetOpacity(float opacity)
6810 {
6811     CHECK_NULL_VOID(rsNode_);
6812     AddOrUpdateModifier<Rosen::ModifierNG::RSAlphaModifier, &Rosen::ModifierNG::RSAlphaModifier::SetAlpha, float>(
6813         alphaUserModifier_, opacity);
6814     MarkNeedDrawNode(opacity < 1.0);
6815 }
6816 
SetOpacityMultiplier(float opacity)6817 void RosenRenderContext::SetOpacityMultiplier(float opacity)
6818 {
6819     CHECK_NULL_VOID(rsNode_);
6820     AddOrUpdateModifier<Rosen::ModifierNG::RSAlphaModifier, &Rosen::ModifierNG::RSAlphaModifier::SetAlpha, float>(
6821         alphaModifier_, opacity);
6822 }
6823 
SetTranslate(float translateX,float translateY,float translateZ)6824 void RosenRenderContext::SetTranslate(float translateX, float translateY, float translateZ)
6825 {
6826     CHECK_NULL_VOID(rsNode_);
6827     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetTranslate,
6828         Rosen::Vector2f>(translateXYUserModifier_, { translateX, translateY });
6829     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetTranslateZ,
6830         float>(translateZUserModifier_, translateZ);
6831     NotifyHostTransformUpdated();
6832 }
6833 
SetTransitionInCallback(std::function<void ()> && callback)6834 void RosenRenderContext::SetTransitionInCallback(std::function<void()>&& callback)
6835 {
6836     transitionInCallback_ = std::move(callback);
6837 }
6838 
SetTransitionOutCallback(std::function<void ()> && callback)6839 void RosenRenderContext::SetTransitionOutCallback(std::function<void()>&& callback)
6840 {
6841     transitionOutCallback_ = std::move(callback);
6842 }
6843 
SetTransitionUserCallback(TransitionFinishCallback && callback)6844 void RosenRenderContext::SetTransitionUserCallback(TransitionFinishCallback&& callback)
6845 {
6846     transitionUserCallback_ = std::move(callback);
6847 }
6848 
GetBaseTransalteInXY() const6849 OffsetF RosenRenderContext::GetBaseTransalteInXY() const
6850 {
6851     OffsetF offset { 0.0f, 0.0f };
6852     CHECK_NULL_RETURN(baseTranslateInXYModifier_, offset);
6853     auto property = std::static_pointer_cast<RSAnimatableProperty<Rosen::Vector2f>>(
6854         baseTranslateInXYModifier_->GetProperty(Rosen::ModifierNG::RSPropertyType::TRANSLATE));
6855     CHECK_NULL_RETURN(property, offset);
6856     auto vec2 = property->Get();
6857     offset = OffsetF { vec2[0], vec2[1] };
6858     return offset;
6859 }
6860 
SetBaseTranslateInXY(const OffsetF & offset)6861 void RosenRenderContext::SetBaseTranslateInXY(const OffsetF& offset)
6862 {
6863     CHECK_NULL_VOID(rsNode_);
6864     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetTranslate,
6865         Rosen::Vector2f>(baseTranslateInXYModifier_, { offset.GetX(), offset.GetY() });
6866     ElementRegister::GetInstance()->ReSyncGeometryTransition(GetHost());
6867     NotifyHostTransformUpdated();
6868 }
6869 
GetBaseRotateInZ() const6870 float RosenRenderContext::GetBaseRotateInZ() const
6871 {
6872     float rotate = 0.0f;
6873     CHECK_NULL_RETURN(baseRotateInZModifier_, rotate);
6874     auto property = std::static_pointer_cast<RSAnimatableProperty<float>>(
6875         baseRotateInZModifier_->GetProperty(Rosen::ModifierNG::RSPropertyType::ROTATION));
6876     CHECK_NULL_RETURN(property, rotate);
6877     rotate = property->Get();
6878     return rotate;
6879 }
6880 
SetBaseRotateInZ(float degree)6881 void RosenRenderContext::SetBaseRotateInZ(float degree)
6882 {
6883     CHECK_NULL_VOID(rsNode_);
6884     AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier, &Rosen::ModifierNG::RSTransformModifier::SetRotation,
6885         float>(baseRotateInZModifier_, degree);
6886     ElementRegister::GetInstance()->ReSyncGeometryTransition(GetHost());
6887     NotifyHostTransformUpdated();
6888 }
6889 
SetRectMask(const RectF & rect,const ShapeMaskProperty & property)6890 void RosenRenderContext::SetRectMask(const RectF& rect, const ShapeMaskProperty& property)
6891 {
6892     CHECK_NULL_VOID(rsNode_);
6893     RSPath path;
6894     path.AddRect(rect.Left(), rect.Top(), rect.Right(), rect.Bottom());
6895 
6896     RSBrush brush = GetRsBrush(property.fillColor);
6897     RSPen pen = GetRsPen(property.strokeColor, property.strokeWidth);
6898 
6899     std::shared_ptr<RSMask> mask = RSMask::CreatePathMask(path, pen, brush);
6900     rsNode_->SetMask(mask);
6901 }
6902 
SetCircleMask(const Circle & circle,const ShapeMaskProperty & property)6903 void RosenRenderContext::SetCircleMask(const Circle& circle, const ShapeMaskProperty& property)
6904 {
6905     CHECK_NULL_VOID(rsNode_);
6906     RSPath path;
6907     path.AddCircle(circle.GetAxisX().Value(), circle.GetAxisY().Value(), circle.GetRadius().Value());
6908 
6909     RSBrush brush = GetRsBrush(property.fillColor);
6910     RSPen pen = GetRsPen(property.strokeColor, property.strokeWidth);
6911 
6912     std::shared_ptr<RSMask> mask = RSMask::CreatePathMask(path, pen, brush);
6913     rsNode_->SetMask(mask);
6914 }
6915 
SetRoundRectMask(const RoundRect & roundRect,const ShapeMaskProperty & property)6916 void RosenRenderContext::SetRoundRectMask(const RoundRect& roundRect, const ShapeMaskProperty& property)
6917 {
6918     CHECK_NULL_VOID(rsNode_);
6919     RSRoundRect rsRoundRect;
6920 
6921     RSRect rsRect(roundRect.GetRect().Left(), roundRect.GetRect().Top(), roundRect.GetRect().Right(),
6922         roundRect.GetRect().Bottom());
6923     rsRoundRect.SetRect(rsRect);
6924 
6925     EdgeF edge = roundRect.GetCornerRadius(RoundRect::TOP_LEFT_POS);
6926     rsRoundRect.SetCornerRadius(RSRoundRect::TOP_LEFT_POS, edge.x, edge.y);
6927     edge = roundRect.GetCornerRadius(RoundRect::TOP_RIGHT_POS);
6928     rsRoundRect.SetCornerRadius(RSRoundRect::TOP_RIGHT_POS, edge.x, edge.y);
6929     edge = roundRect.GetCornerRadius(RoundRect::BOTTOM_LEFT_POS);
6930     rsRoundRect.SetCornerRadius(RSRoundRect::BOTTOM_LEFT_POS, edge.x, edge.y);
6931     edge = roundRect.GetCornerRadius(RoundRect::BOTTOM_RIGHT_POS);
6932     rsRoundRect.SetCornerRadius(RSRoundRect::BOTTOM_RIGHT_POS, edge.x, edge.y);
6933 
6934     RSPath path;
6935     path.AddRoundRect(rsRoundRect);
6936 
6937     RSBrush brush = GetRsBrush(property.fillColor);
6938     RSPen pen = GetRsPen(property.strokeColor, property.strokeWidth);
6939 
6940     std::shared_ptr<RSMask> mask = Rosen::RSMask::CreatePathMask(path, pen, brush);
6941     rsNode_->SetMask(mask);
6942 }
6943 
SetOvalMask(const RectF & rect,const ShapeMaskProperty & property)6944 void RosenRenderContext::SetOvalMask(const RectF& rect, const ShapeMaskProperty& property)
6945 {
6946     CHECK_NULL_VOID(rsNode_);
6947     RSRect rsRect(rect.Left(), rect.Top(), rect.Right(), rect.Bottom());
6948     RSPath path;
6949     path.AddOval(rsRect);
6950 
6951     RSBrush brush = GetRsBrush(property.fillColor);
6952     RSPen pen = GetRsPen(property.strokeColor, property.strokeWidth);
6953 
6954     std::shared_ptr<RSMask> mask = RSMask::CreatePathMask(path, pen, brush);
6955     rsNode_->SetMask(mask);
6956 }
6957 
SetCommandPathMask(const std::string & commands,const ShapeMaskProperty & property)6958 void RosenRenderContext::SetCommandPathMask(const std::string& commands, const ShapeMaskProperty& property)
6959 {
6960     CHECK_NULL_VOID(rsNode_);
6961     RSPath path;
6962     path.BuildFromSVGString(commands);
6963 
6964     RSBrush brush = GetRsBrush(property.fillColor);
6965     RSPen pen = GetRsPen(property.strokeColor, property.strokeWidth);
6966 
6967     std::shared_ptr<RSMask> mask = RSMask::CreatePathMask(path, pen, brush);
6968     rsNode_->SetMask(mask);
6969 }
6970 
SetMarkNodeGroup(bool isNodeGroup)6971 void RosenRenderContext::SetMarkNodeGroup(bool isNodeGroup)
6972 {
6973     CHECK_NULL_VOID(rsNode_);
6974     rsNode_->MarkNodeGroup(isNodeGroup);
6975 }
6976 
GetRotateDegree()6977 int32_t RosenRenderContext::GetRotateDegree()
6978 {
6979     CHECK_NULL_RETURN(rsNode_, 0);
6980     return static_cast<int32_t>(rsNode_->GetStagingProperties().GetRotation());
6981 }
6982 
ResetSurface(int width,int height)6983 void RosenRenderContext::ResetSurface(int width, int height)
6984 {
6985     if (RSUIDirector::GetHybridRenderSwitch(Rosen::ComponentEnableSwitch::CANVAS)) {
6986         auto rsCanvasNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasNode>(rsNode_);
6987         CHECK_NULL_VOID(rsCanvasNode);
6988         if (rsCanvasNode->IsHybridRenderCanvas()) {
6989             rsCanvasNode->ResetSurface(width, height);
6990         }
6991         return;
6992     }
6993     auto rsCanvasDrawingNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasDrawingNode>(rsNode_);
6994     CHECK_NULL_VOID(rsCanvasDrawingNode);
6995     rsCanvasDrawingNode->ResetSurface(width, height);
6996 }
6997 
SavePaintRect(bool isRound,uint16_t flag)6998 void RosenRenderContext::SavePaintRect(bool isRound, uint16_t flag)
6999 {
7000     auto host = GetHost();
7001     CHECK_NULL_VOID(host);
7002     const auto& geometryNode = host->GetGeometryNode();
7003     CHECK_NULL_VOID(geometryNode);
7004     AdjustPaintRect();
7005     if (!SystemProperties::GetPixelRoundEnabled()) {
7006         // isRound is the switch of pixelRound of lower version
7007         isRound = false;
7008         // flag is the switch of pixelRound of upper version
7009         flag = NO_FORCE_ROUND;
7010     }
7011     if (host->GreatOrEqualAPITargetVersion(PlatformVersion::VERSION_TWELVE)) {
7012         OnePixelRounding(flag);
7013     } else {
7014         if (isRound && flag == 0) {
7015             RoundToPixelGrid(); // call RoundToPixelGrid without param to improve performance
7016         } else {
7017             RoundToPixelGrid(isRound, flag);
7018         }
7019     }
7020     paintRect_ = RectF(geometryNode->GetPixelGridRoundOffset(), geometryNode->GetPixelGridRoundSize());
7021     if (SystemProperties::GetSyncDebugTraceEnabled()) {
7022         ACE_LAYOUT_SCOPED_TRACE("SavePaintRect[%s][self:%d] rs SavePaintRect %s", host->GetTag().c_str(), host->GetId(),
7023             paintRect_.ToString().c_str());
7024     }
7025 }
7026 
UpdatePaintRect(const RectF & paintRect)7027 void RosenRenderContext::UpdatePaintRect(const RectF& paintRect)
7028 {
7029     auto host = GetHost();
7030     if (host && SystemProperties::GetSyncDebugTraceEnabled()) {
7031         ACE_LAYOUT_SCOPED_TRACE("UpdatePaintRect[%s][self:%d] from %s to %s", host->GetTag().c_str(), host->GetId(),
7032             paintRect_.ToString().c_str(), paintRect.ToString().c_str());
7033     }
7034     paintRect_ = paintRect;
7035 }
7036 
SyncPartialRsProperties()7037 void RosenRenderContext::SyncPartialRsProperties()
7038 {
7039     if (propTransform_ && propTransform_->HasTransformCenter()) {
7040         auto vec = propTransform_->GetTransformCenterValue();
7041         float xPivot = ConvertDimensionToScaleBySize(vec.GetX(), paintRect_.Width());
7042         float yPivot = ConvertDimensionToScaleBySize(vec.GetY(), paintRect_.Height());
7043         if (vec.GetZ().has_value()) {
7044             float zPivot = static_cast<float>(vec.GetZ().value().ConvertToVp());
7045             SetPivot(xPivot, yPivot, zPivot);
7046         } else {
7047             SetPivot(xPivot, yPivot);
7048         }
7049     }
7050 
7051     if (propTransform_ && propTransform_->HasTransformTranslate()) {
7052         // if translate unit is percent, it is related with frameSize
7053         OnTransformTranslateUpdate(propTransform_->GetTransformTranslateValue());
7054     }
7055 }
7056 
UpdateDrawRegion(uint32_t index,const std::shared_ptr<Rosen::RectF> & rect)7057 void RosenRenderContext::UpdateDrawRegion(uint32_t index, const std::shared_ptr<Rosen::RectF>& rect)
7058 {
7059     if (drawRegionRects_[index] && rect && *drawRegionRects_[index] == *rect) {
7060         return;
7061     } else if (!drawRegionRects_[index] && !rect) {
7062         return;
7063     }
7064     // the drawRegion of this index has changed
7065     drawRegionRects_[index] = rect;
7066     std::shared_ptr<Rosen::RectF> result;
7067     for (size_t index = 0; index < DRAW_REGION_RECT_COUNT; ++index) {
7068         if (drawRegionRects_[index]) {
7069             if (result) {
7070                 *result = result->JoinRect(*drawRegionRects_[index]);
7071             } else {
7072                 result = std::make_shared<Rosen::RectF>(*drawRegionRects_[index]);
7073             }
7074         }
7075     }
7076     if (!result) {
7077         return;
7078     }
7079     rsNode_->SetDrawRegion(result);
7080 }
7081 
NotifyHostTransformUpdated(bool changed)7082 void RosenRenderContext::NotifyHostTransformUpdated(bool changed)
7083 {
7084     auto host = GetHost();
7085     CHECK_NULL_VOID(host);
7086     FREE_NODE_CHECK(host, NotifyHostTransformUpdated, changed);
7087     host->NotifyTransformInfoChanged();
7088     host->OnNodeTransformInfoUpdate(changed);
7089     host->UpdateAccessibilityNodeRect();
7090 }
7091 
SuggestOpIncNode(bool isOpincNode,bool isNeedCalculate)7092 void RosenRenderContext::SuggestOpIncNode(bool isOpincNode, bool isNeedCalculate)
7093 {
7094     CHECK_NULL_VOID(rsNode_);
7095     rsNode_->MarkSuggestOpincNode(isOpincNode, isNeedCalculate);
7096 }
7097 
OnAttractionEffectUpdate(const AttractionEffect & effect)7098 void RosenRenderContext::OnAttractionEffectUpdate(const AttractionEffect& effect)
7099 {
7100     CHECK_NULL_VOID(rsNode_);
7101     Rosen::Vector2f destinationPoint(effect.destinationX.ConvertToPx(), effect.destinationY.ConvertToPx());
7102     rsNode_->SetAttractionEffect(effect.fraction, destinationPoint);
7103     RequestNextFrame();
7104 }
7105 
UpdateOcclusionCullingStatus(bool enable)7106 void RosenRenderContext::UpdateOcclusionCullingStatus(bool enable)
7107 {
7108     CHECK_NULL_VOID(rsNode_);
7109     const auto keyOcclusionNodeId = rsNode_->GetId();
7110     LOGD("RosenRenderContext::UpdateOcclusionCullingStatus enable %{public}d, "
7111         "keyOcclusionId %{public}" PRIu64, enable, keyOcclusionNodeId);
7112     ACE_SCOPED_TRACE("RosenRenderContext::UpdateOcclusionCullingStatus"
7113         "enable %d, keyOcclusionId %" PRIu64, enable, keyOcclusionNodeId);
7114     rsNode_->UpdateOcclusionCullingStatus(enable, keyOcclusionNodeId);
7115 }
7116 
GetPipelineContext() const7117 PipelineContext* RosenRenderContext::GetPipelineContext() const
7118 {
7119     auto host = GetHost();
7120     if (host) {
7121         return host->GetContextWithCheck();
7122     }
7123     return PipelineContext::GetCurrentContextPtrSafelyWithCheck();
7124 }
7125 
UpdateWindowBlur()7126 void RosenRenderContext::UpdateWindowBlur()
7127 {
7128     auto pipeline = GetPipelineContext();
7129     CHECK_NULL_VOID(pipeline);
7130     if (pipeline->IsFormRender()) {
7131         return;
7132     }
7133     auto blurStyleTheme = pipeline->GetTheme<BlurStyleTheme>();
7134     if (!blurStyleTheme) {
7135         LOGW("cannot find theme of blurStyle, create blurStyle failed");
7136         return;
7137     }
7138     ThemeColorMode colorMode =
7139         GetResourceColorMode(pipeline) == ColorMode::DARK ? ThemeColorMode::DARK : ThemeColorMode::LIGHT;
7140     auto blurParam = blurStyleTheme->GetBlurParameter(BlurStyle::COMPONENT_ULTRA_THICK_WINDOW, colorMode);
7141     if (NearZero(blurParam->radius)) {
7142         return;
7143     }
7144     auto maskColor = LinearColor(blurParam->maskColor.GetValue());
7145     auto rgbaColor = (static_cast<uint32_t>(std::clamp<uint16_t>(maskColor.GetAlpha(), 0, UINT8_MAX))) |
7146                      (static_cast<uint32_t>((std::clamp<uint16_t>(maskColor.GetBlue(), 0, UINT8_MAX)) << 8)) |
7147                      (static_cast<uint32_t>((std::clamp<uint16_t>(maskColor.GetGreen(), 0, UINT8_MAX)) << 16)) |
7148                      (static_cast<uint32_t>((std::clamp<uint16_t>(maskColor.GetRed(), 0, UINT8_MAX)) << 24));
7149     bool needAddModifier = false;
7150     if (!windowBlurModifier_) {
7151         windowBlurModifier_ = std::make_shared<Rosen::ModifierNG::RSBehindWindowFilterModifier>();
7152         needAddModifier = true;
7153     }
7154     auto window = reinterpret_cast<RosenWindow*>(pipeline->GetWindow());
7155     CHECK_NULL_VOID(window);
7156     auto rsWindow = window->GetRSWindow();
7157     CHECK_NULL_VOID(rsWindow);
7158     auto surfaceNode = rsWindow->GetSurfaceNode();
7159     CHECK_NULL_VOID(surfaceNode);
7160     auto rsUIContext = rsNode_->GetRSUIContext();
7161     auto rsNodeTmp = rsUIContext ? rsUIContext->GetNodeMap().GetNode(surfaceNode->GetId())
7162                                  : Rosen::RSNodeMap::Instance().GetNode(surfaceNode->GetId());
7163     AnimationOption option;
7164     const int32_t duration = 400;
7165     option.SetDuration(duration);
7166     option.SetCurve(Curves::FRICTION);
7167     AnimationUtils::OpenImplicitAnimation(option, option.GetCurve(), nullptr);
7168     windowBlurModifier_->SetBehindWindowFilterRadius(blurParam->radius);
7169     windowBlurModifier_->SetBehindWindowFilterSaturation(blurParam->saturation);
7170     windowBlurModifier_->SetBehindWindowFilterBrightness(blurParam->brightness);
7171     windowBlurModifier_->SetBehindWindowFilterMaskColor(Rosen::RSColor(rgbaColor));
7172     if (needAddModifier) {
7173         rsNodeTmp->AddModifier(windowBlurModifier_);
7174     }
7175     AnimationUtils::CloseImplicitAnimation();
7176 }
7177 
MarkUiFirstNode(bool isUiFirstNode)7178 void RosenRenderContext::MarkUiFirstNode(bool isUiFirstNode)
7179 {
7180     CHECK_NULL_VOID(rsNode_);
7181     rsNode_->MarkUifirstNode(isUiFirstNode);
7182 }
7183 
BuildShadowInfo(std::unique_ptr<JsonValue> & json)7184 void RosenRenderContext::BuildShadowInfo(std::unique_ptr<JsonValue>& json)
7185 {
7186     if (!NearZero(rsNode_->GetStagingProperties().GetShadowOffsetY())) {
7187         json->Put("ShadowOffsetY", rsNode_->GetStagingProperties().GetShadowOffsetY());
7188     }
7189     if (!NearZero(rsNode_->GetStagingProperties().GetShadowAlpha())) {
7190         json->Put("ShadowAlpha", rsNode_->GetStagingProperties().GetShadowAlpha());
7191     }
7192     if (!NearZero(rsNode_->GetStagingProperties().GetShadowElevation())) {
7193         json->Put("ShadowElevation", rsNode_->GetStagingProperties().GetShadowElevation());
7194     }
7195     if (!NearZero(rsNode_->GetStagingProperties().GetShadowRadius())) {
7196         json->Put("ShadowRadius", rsNode_->GetStagingProperties().GetShadowRadius());
7197     }
7198 }
7199 
BuildStagingInfo(std::unique_ptr<JsonValue> & json)7200 void RosenRenderContext::BuildStagingInfo(std::unique_ptr<JsonValue>& json)
7201 {
7202     if (!NearZero(rsNode_->GetStagingProperties().GetPivotZ())) {
7203         json->Put("PivotZ", rsNode_->GetStagingProperties().GetPivotZ());
7204     }
7205     if (!NearZero(rsNode_->GetStagingProperties().GetRotation())) {
7206         json->Put("Rotation", rsNode_->GetStagingProperties().GetRotation());
7207     }
7208     if (!NearZero(rsNode_->GetStagingProperties().GetRotationX())) {
7209         json->Put("RotationX", rsNode_->GetStagingProperties().GetRotationX());
7210     }
7211     if (!NearZero(rsNode_->GetStagingProperties().GetRotationY())) {
7212         json->Put("RotationY", rsNode_->GetStagingProperties().GetRotationY());
7213     }
7214     if (!NearZero(rsNode_->GetStagingProperties().GetCameraDistance())) {
7215         json->Put("CameraDistance", rsNode_->GetStagingProperties().GetCameraDistance());
7216     }
7217     if (!NearZero(rsNode_->GetStagingProperties().GetTranslateZ())) {
7218         json->Put("TranslateZ", rsNode_->GetStagingProperties().GetTranslateZ());
7219     }
7220     if (!NearZero(rsNode_->GetStagingProperties().GetBgImageWidth())) {
7221         json->Put("BgImageWidth", rsNode_->GetStagingProperties().GetBgImageWidth());
7222     }
7223     if (!NearZero(rsNode_->GetStagingProperties().GetBgImageHeight())) {
7224         json->Put("BgImageHeight", rsNode_->GetStagingProperties().GetBgImageHeight());
7225     }
7226     if (!NearZero(rsNode_->GetStagingProperties().GetBgImagePositionX())) {
7227         json->Put("BgImagePositionX", rsNode_->GetStagingProperties().GetBgImagePositionX());
7228     }
7229     if (!NearZero(rsNode_->GetStagingProperties().GetBgImagePositionY())) {
7230         json->Put("BgImagePositionY", rsNode_->GetStagingProperties().GetBgImagePositionY());
7231     }
7232     BuildShadowInfo(json);
7233     if (!NearZero(rsNode_->GetStagingProperties().GetSpherizeDegree())) {
7234         json->Put("SpherizeDegree", rsNode_->GetStagingProperties().GetSpherizeDegree());
7235     }
7236     if (!NearZero(rsNode_->GetStagingProperties().GetLightUpEffectDegree())) {
7237         json->Put("LightUpEffectDegree", rsNode_->GetStagingProperties().GetLightUpEffectDegree());
7238     }
7239     if (!NearEqual(rsNode_->GetStagingProperties().GetAlpha(), 1)) {
7240         json->Put("Alpha", rsNode_->GetStagingProperties().GetAlpha());
7241     }
7242 }
7243 
BuildPositionInfo(std::unique_ptr<JsonValue> & json)7244 void RosenRenderContext::BuildPositionInfo(std::unique_ptr<JsonValue>& json)
7245 {
7246     json->Put("rsNode", rsNode_->DumpNode(0).c_str());
7247     auto center = rsNode_->GetStagingProperties().GetPivot();
7248     if (!NearEqual(center[0], 0.5) || !NearEqual(center[1], 0.5)) {
7249         auto child = JsonUtil::Create(true);
7250         child->Put("x", center[0]);
7251         child->Put("y", center[1]);
7252         json->Put("Center", child);
7253     }
7254     BuildStagingInfo(json);
7255     auto translate = rsNode_->GetStagingProperties().GetTranslate();
7256     if (!(NearZero(translate[0]) && NearZero(translate[1]))) {
7257         auto child = JsonUtil::Create(true);
7258         child->Put("x", translate[0]);
7259         child->Put("y", translate[1]);
7260         json->Put("translate", child);
7261     }
7262     auto scale = rsNode_->GetStagingProperties().GetScale();
7263     if (!(NearEqual(scale[0], 1) && NearEqual(scale[1], 1))) {
7264         auto child = JsonUtil::Create(true);
7265         child->Put("x", scale[0]);
7266         child->Put("y", scale[1]);
7267         json->Put("scale", child);
7268     }
7269     auto rect = GetPaintRectWithoutTransform();
7270     if (HasTransformTranslate()) {
7271         auto translateArk = GetTransformTranslate().value();
7272         auto arkTranslateX = translateArk.x.ConvertToPxWithSize(rect.Width());
7273         auto arkTranslateY = translateArk.y.ConvertToPxWithSize(rect.Height());
7274         if (!NearEqual(arkTranslateX, translate[0])) {
7275             json->Put("TranlateX has difference,arkui", std::to_string(arkTranslateX).c_str());
7276         }
7277         if (!NearEqual(arkTranslateY, translate[1])) {
7278             json->Put("TranlateY has difference,arkui", std::to_string(arkTranslateY).c_str());
7279         }
7280     }
7281     if (HasTransformScale()) {
7282         auto arkTransformScale = GetTransformScale().value();
7283         if (!NearEqual(arkTransformScale.x, scale[0])) {
7284             json->Put("scaleX has difference,arkui", std::to_string(arkTransformScale.x).c_str());
7285         }
7286         if (!NearEqual(arkTransformScale.y, scale[1])) {
7287             json->Put("scaleY has difference,arkui", std::to_string(arkTransformScale.y).c_str());
7288         }
7289     }
7290 }
7291 
DumpInfo(std::unique_ptr<JsonValue> & json)7292 void RosenRenderContext::DumpInfo(std::unique_ptr<JsonValue>& json)
7293 {
7294     if (rsNode_) {
7295         auto children = JsonUtil::Create(true);
7296         BuildPositionInfo(children);
7297         if (HasOpacity()) {
7298             auto arkAlpha = GetOpacity();
7299             if (!NearEqual(arkAlpha.value(), rsNode_->GetStagingProperties().GetAlpha())) {
7300                 children->Put("Alpha has difference,arkui", std::to_string(arkAlpha.value()).c_str());
7301             }
7302         }
7303         if (HasPosition()) {
7304             auto position = GetPosition();
7305             children->Put("PositionX", position->GetX().ToString().c_str());
7306             children->Put("PositionY", position->GetY().ToString().c_str());
7307         }
7308         if (HasOffset()) {
7309             auto offset = GetOffset();
7310             children->Put("OffsetX", offset->GetX().ToString().c_str());
7311             children->Put("OffsetY", offset->GetY().ToString().c_str());
7312         }
7313         if (HasPositionEdges()) {
7314             auto positionEdges = GetPositionEdges();
7315             children->Put("positionEdges", positionEdges->ToString().c_str());
7316         }
7317         if (HasOffsetEdges()) {
7318             auto offsetEdges = GetOffsetEdges();
7319             children->Put("offsetEdges", offsetEdges->ToString().c_str());
7320         }
7321         if (HasAnchor()) {
7322             auto anchor = GetAnchor();
7323             children->Put("anchorX", anchor->GetX().ToString().c_str());
7324             children->Put("anchorY", anchor->GetY().ToString().c_str());
7325         }
7326         json->Put("rsNode", children);
7327     }
7328 }
7329 
DumpAdvanceInfo(std::unique_ptr<JsonValue> & json)7330 void RosenRenderContext::DumpAdvanceInfo(std::unique_ptr<JsonValue>& json)
7331 {
7332     if (GetBackgroundAlign().has_value()) {
7333         json->Put("BackgroundAlign", GetBackgroundAlign().value().ToString().c_str());
7334     }
7335     if (GetBackgroundImage().has_value()) {
7336         json->Put("BackgroundImage", GetBackgroundImage().value().ToString().c_str());
7337     }
7338     if (GetSphericalEffect().has_value()) {
7339         json->Put("SphericalEffect", std::to_string(GetSphericalEffect().value()).c_str());
7340     }
7341     if (GetPixelStretchEffect().has_value()) {
7342         json->Put("PixelStretchEffect", GetPixelStretchEffect().value().ToString().c_str());
7343     }
7344     if (GetLightUpEffect().has_value()) {
7345         json->Put("LightUpEffect", std::to_string(GetLightUpEffect().value()).c_str());
7346     }
7347     if (GetBorderColor().has_value()) {
7348         json->Put("BorderColor", GetBorderColor().value().ToString().c_str());
7349     }
7350     if (GetBorderWidth().has_value()) {
7351         json->Put("BorderWidth", GetBorderWidth().value().ToString().c_str());
7352     }
7353     if (GetOuterBorderRadius().has_value()) {
7354         json->Put("OuterBorderRadius", GetOuterBorderRadius().value().ToString().c_str());
7355     }
7356     if (GetOuterBorderColor().has_value()) {
7357         json->Put("OuterBorderColor", GetOuterBorderColor().value().ToString().c_str());
7358     }
7359     if (GetOuterBorderWidth().has_value()) {
7360         json->Put("OuterBorderWidth", GetOuterBorderWidth().value().ToString().c_str());
7361     }
7362     if (GetDynamicLightUpRate().has_value()) {
7363         json->Put("DynamicLightUpRate", std::to_string(GetDynamicLightUpRate().value()).c_str());
7364     }
7365     if (GetDynamicLightUpDegree().has_value()) {
7366         json->Put("DynamicLightUpDegree", std::to_string(GetDynamicLightUpDegree().value()).c_str());
7367     }
7368     if (GetBackBlendMode().has_value()) {
7369         json->Put("BlendMode", static_cast<int>(GetBackBlendMode().value()));
7370     }
7371     if (GetLinearGradient().has_value()) {
7372         json->Put("LinearGradient", GetLinearGradient().value().ToString().c_str());
7373     }
7374     if (GetSweepGradient().has_value()) {
7375         json->Put("SweepGradient", GetSweepGradient().value().ToString().c_str());
7376     }
7377     SetAdvanceInfo(json);
7378 }
7379 
SetAdvanceInfo(std::unique_ptr<JsonValue> & json)7380 void RosenRenderContext::SetAdvanceInfo(std::unique_ptr<JsonValue>& json)
7381 {
7382     if (GetRadialGradient().has_value()) {
7383         json->Put("RadialGradient", GetRadialGradient().value().ToString().c_str());
7384     }
7385     if (GetFrontBrightness().has_value()) {
7386         json->Put("FrontBrightness", GetFrontBrightness().value().ToString().c_str());
7387     }
7388     if (GetFrontGrayScale().has_value()) {
7389         json->Put("FrontGrayScale", GetFrontGrayScale().value().ToString().c_str());
7390     }
7391     if (GetFrontContrast().has_value()) {
7392         json->Put("FrontContrast", GetFrontContrast().value().ToString().c_str());
7393     }
7394     if (GetFrontSaturate().has_value()) {
7395         json->Put("FrontSaturate", GetFrontSaturate().value().ToString().c_str());
7396     }
7397     if (GetFrontSepia().has_value()) {
7398         json->Put("FrontSepia", GetFrontSepia().value().ToString().c_str());
7399     }
7400     if (GetFrontHueRotate().has_value()) {
7401         json->Put("FrontHueRotate", std::to_string(GetFrontHueRotate().value()).c_str());
7402     }
7403     if (GetFrontColorBlend().has_value()) {
7404         json->Put("FrontColorBlend", GetFrontColorBlend().value().ColorToString().c_str());
7405     }
7406     if (GetBorderImageSource().has_value()) {
7407         json->Put("BorderImageSource", GetBorderImageSource().value().ToString().c_str());
7408     }
7409     if (GetBorderImageGradient().has_value()) {
7410         json->Put("BorderImageGradient", GetBorderImageGradient().value().ToString().c_str());
7411     }
7412     if (GetForegroundColor().has_value()) {
7413         json->Put("ForegroundColor", GetForegroundColor().value().ColorToString().c_str());
7414     }
7415     if (GetLightIntensity().has_value()) {
7416         json->Put("LightIntensity", std::to_string(GetLightIntensity().value()).c_str());
7417     }
7418     if (GetLightIlluminated().has_value()) {
7419         json->Put("LightIlluminated", std::to_string(GetLightIlluminated().value()).c_str());
7420     }
7421     if (GetIlluminatedBorderWidth().has_value()) {
7422         json->Put("IlluminatedBorderWidth", GetIlluminatedBorderWidth().value().ToString().c_str());
7423     }
7424     if (GetBloom().has_value()) {
7425         json->Put("Bloom", std::to_string(GetBloom().value()).c_str());
7426     }
7427 }
7428 
DumpSimplifyStagingProperties(std::unique_ptr<JsonValue> & json)7429 void RosenRenderContext::DumpSimplifyStagingProperties(std::unique_ptr<JsonValue>& json)
7430 {
7431     auto center = rsNode_->GetStagingProperties().GetPivot();
7432     if (!NearEqual(center[0], 0.5) || !NearEqual(center[1], 0.5)) {
7433         json->Put("Center", std::to_string(center[0]).append(",").append(std::to_string(center[1])).c_str());
7434     }
7435     auto translate = rsNode_->GetStagingProperties().GetTranslate();
7436     if (!(NearZero(translate[0]) && NearZero(translate[1]))) {
7437         json->Put("Translate",
7438             std::to_string(translate[0]).append(",").append(std::to_string(translate[1])).c_str());
7439     }
7440     auto scale = rsNode_->GetStagingProperties().GetScale();
7441     if (!(NearEqual(scale[0], 1) && NearEqual(scale[1], 1))) {
7442         json->Put("Scale", std::to_string(scale[0]).append(",").append(std::to_string(scale[1])).c_str());
7443     }
7444     if (HasTransformScale()) {
7445         auto arkTransformScale = GetTransformScale().value();
7446         if (!NearEqual(arkTransformScale.x, scale[0])) {
7447             json->Put("TransformScaleX", std::to_string(arkTransformScale.x).c_str());
7448         }
7449         if (!NearEqual(arkTransformScale.y, scale[1])) {
7450             json->Put("TransformScaleY", std::to_string(arkTransformScale.y).c_str());
7451         }
7452     }
7453     auto rect = GetPaintRectWithoutTransform();
7454     if (HasTransformTranslate()) {
7455         auto translateArk = GetTransformTranslate().value();
7456         auto arkTranslateX = translateArk.x.ConvertToPxWithSize(rect.Width());
7457         auto arkTranslateY = translateArk.y.ConvertToPxWithSize(rect.Height());
7458         if (!NearEqual(arkTranslateX, translate[0])) {
7459             json->Put("TransformTranslateX", std::to_string(arkTranslateX).c_str());
7460         }
7461         if (!NearEqual(arkTranslateY, translate[1])) {
7462             json->Put("TransformTranslateY", std::to_string(arkTranslateY).c_str());
7463         }
7464     }
7465     if (HasOpacity()) {
7466         auto arkAlpha = GetOpacity();
7467         if (!NearEqual(arkAlpha.value(), rsNode_->GetStagingProperties().GetAlpha())) {
7468             json->Put("TransformAlpha", std::to_string(arkAlpha.value()).c_str());
7469         }
7470     }
7471 }
7472 
FreezeCanvasNode(bool freezeFlag)7473 void RosenRenderContext::FreezeCanvasNode(bool freezeFlag)
7474 {
7475     if (canvasNode_) {
7476         TAG_LOGD(AceLogTag::ACE_WINDOW, "FreezeCanvasNode. %{public}d", freezeFlag);
7477         canvasNode_->SetFreeze(freezeFlag);
7478     }
7479 }
7480 
RemoveCanvasNode()7481 void RosenRenderContext::RemoveCanvasNode()
7482 {
7483     if (reDraggingFlag_) {
7484         reDraggingFlag_ = false;
7485         return;
7486     }
7487     if (canvasNode_) {
7488         TAG_LOGD(AceLogTag::ACE_WINDOW, "RemoveCanvasNode.");
7489         canvasNode_->RemoveFromTree();
7490         canvasNode_ = nullptr;
7491     }
7492 }
7493 
CheckAnimationParametersValid(int32_t & animationParam)7494 void RosenRenderContext::CheckAnimationParametersValid(int32_t& animationParam)
7495 {
7496     const int32_t maxTime = 2000;
7497     const int32_t defaultTime = 100;
7498     if (animationParam <= 0 || animationParam > maxTime) {
7499         animationParam = defaultTime;
7500     }
7501 }
7502 
SetCanvasNodeOpacityAnimation(int32_t duration,int32_t delay,bool isDragEnd)7503 bool RosenRenderContext::SetCanvasNodeOpacityAnimation(int32_t duration, int32_t delay, bool isDragEnd)
7504 {
7505     static bool animationFlag = false;
7506     if (animationFlag) {
7507         TAG_LOGD(AceLogTag::ACE_WINDOW, "animationFlag is true.");
7508         return false;
7509     }
7510     if (!canvasNode_) {
7511         return true;
7512     }
7513 
7514     FreezeCanvasNode(true);
7515     canvasNode_->SetAlpha(1.0f);
7516     FlushImplicitTransaction();
7517 
7518     CheckAnimationParametersValid(duration);
7519     CheckAnimationParametersValid(delay);
7520     AnimationOption option;
7521     option.SetDuration(duration);
7522     option.SetDelay(delay);
7523     option.SetCurve(Curves::EASE_OUT);
7524     AnimationUtils::Animate(option,
7525         [this]() {
7526             if (canvasNode_) {
7527                 animationFlag = true;
7528                 canvasNode_->SetAlpha(0.0f);
7529             }
7530         },
7531         [this, isDragEnd]() {
7532             if (canvasNode_) {
7533                 canvasNode_->SetAlpha(1.0f);
7534             }
7535             FreezeCanvasNode(false);
7536             if (isDragEnd) {
7537                 RemoveCanvasNode();
7538             }
7539             if (callbackAnimateEnd_) {
7540                 callbackAnimateEnd_();
7541             }
7542             FlushImplicitTransaction();
7543             animationFlag = false;
7544             if (callbackCachedAnimateAction_) {
7545                 callbackCachedAnimateAction_();
7546             }
7547         });
7548     return true;
7549 }
7550 
FlushImplicitTransaction()7551 void RosenRenderContext::FlushImplicitTransaction()
7552 {
7553     if (!SystemProperties::GetMultiInstanceEnabled()) {
7554         return Rosen::RSTransaction::FlushImplicitTransaction();
7555     }
7556     auto pipeline = GetPipelineContext();
7557     auto rsUIContext = GetRSUIContext(pipeline);
7558     if (rsUIContext) {
7559         auto rsTransaction = rsUIContext->GetRSTransaction();
7560         if (rsTransaction) {
7561             rsTransaction->FlushImplicitTransaction();
7562             return;
7563         }
7564     }
7565     Rosen::RSTransaction::FlushImplicitTransaction();
7566 }
7567 
LinkCanvasNodeToRootNode(const RefPtr<FrameNode> & rootNode)7568 void RosenRenderContext::LinkCanvasNodeToRootNode(const RefPtr<FrameNode>& rootNode)
7569 {
7570     if (canvasNode_ && rootNode) {
7571         TAG_LOGD(AceLogTag::ACE_WINDOW, "SetLinkedRootNodeId");
7572         auto renderContext = rootNode->GetRenderContext();
7573         CHECK_NULL_VOID(renderContext);
7574         canvasNode_->SetLinkedRootNodeId(renderContext->GetNodeId());
7575         FlushImplicitTransaction();
7576     }
7577 }
7578 
CreateCanvasNode()7579 void RosenRenderContext::CreateCanvasNode()
7580 {
7581     if (!canvasNode_) {
7582         TAG_LOGD(AceLogTag::ACE_WINDOW, "Create RSCanvasNode.");
7583         if (!SystemProperties::GetMultiInstanceEnabled()) {
7584             canvasNode_ = Rosen::RSCanvasNode::Create();
7585             Rosen::RSTransaction::FlushImplicitTransaction();
7586         } else {
7587             auto pipeline = GetPipelineContext();
7588             auto rsUIContext = GetRSUIContext(pipeline);
7589             canvasNode_ = Rosen::RSCanvasNode::Create(false, false, rsUIContext);
7590             FlushImplicitTransaction();
7591         }
7592     }
7593 }
7594 
GetCanvasNode() const7595 std::shared_ptr<Rosen::RSCanvasNode> RosenRenderContext::GetCanvasNode() const
7596 {
7597     return canvasNode_;
7598 }
7599 
SetColorGamut(uint32_t colorGamut)7600 void RosenRenderContext::SetColorGamut(uint32_t colorGamut)
7601 {
7602     auto rsCanvasNode = Rosen::RSNode::ReinterpretCast<Rosen::RSCanvasNode>(rsNode_);
7603     CHECK_NULL_VOID(rsCanvasNode);
7604     if (colorGamut_ != colorGamut) {
7605         colorGamut = colorGamut_;
7606         rsCanvasNode->SetColorGamut(colorGamut);
7607         return;
7608     }
7609 }
7610 
SetAnimationPropertyValue(AnimationPropertyType property,const std::vector<float> & value)7611 void RosenRenderContext::SetAnimationPropertyValue(AnimationPropertyType property, const std::vector<float>& value)
7612 {
7613     CHECK_NULL_VOID(rsNode_);
7614     switch (property) {
7615         case AnimationPropertyType::ROTATION: {
7616             if (value.size() == ROTATION_PARAM_SIZE) {
7617                 // rotationX and rotationY are opposite between arkui and rs.
7618                 AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
7619                     &Rosen::ModifierNG::RSTransformModifier::SetRotationX, float>(rotationXUserModifier_, -value[0]);
7620                 AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
7621                     &Rosen::ModifierNG::RSTransformModifier::SetRotationY, float>(rotationYUserModifier_, -value[1]);
7622                 AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
7623                     &Rosen::ModifierNG::RSTransformModifier::SetRotation, float>(
7624                     rotationZUserModifier_, value[2]); // 2 is index of value
7625                 NotifyHostTransformUpdated();
7626             }
7627             break;
7628         }
7629         case AnimationPropertyType::TRANSLATION: {
7630             if (value.size() == TRANSLATION_PARAM_SIZE) {
7631                 AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
7632                     &Rosen::ModifierNG::RSTransformModifier::SetTranslate, Rosen::Vector2f>(
7633                     translateXYUserModifier_, { value[0], value[1] });
7634                 NotifyHostTransformUpdated();
7635             }
7636             break;
7637         }
7638         case AnimationPropertyType::SCALE: {
7639             if (value.size() == SCALE_PARAM_SIZE) {
7640                 AddOrUpdateModifier<Rosen::ModifierNG::RSTransformModifier,
7641                     &Rosen::ModifierNG::RSTransformModifier::SetScale, Rosen::Vector2f>(
7642                     scaleXYUserModifier_, { value[0], value[1] });
7643                 NotifyHostTransformUpdated();
7644             }
7645             break;
7646         }
7647         case AnimationPropertyType::OPACITY: {
7648             if (value.size() == OPACITY_PARAM_SIZE) {
7649                 AddOrUpdateModifier<Rosen::ModifierNG::RSAlphaModifier, &Rosen::ModifierNG::RSAlphaModifier::SetAlpha,
7650                     float>(alphaUserModifier_, value[0]);
7651                 MarkNeedDrawNode(value[0] < 1.0);
7652             }
7653             break;
7654         }
7655         default: {
7656             break;
7657         }
7658     }
7659 }
7660 
CancelPropertyAnimation(AnimationPropertyType property)7661 void RosenRenderContext::CancelPropertyAnimation(AnimationPropertyType property)
7662 {
7663     CHECK_NULL_VOID(rsNode_);
7664     switch (property) {
7665         case AnimationPropertyType::ROTATION: {
7666             CancelModifierAnimation<Rosen::ModifierNG::RSTransformModifier, float>(
7667                 rotationXUserModifier_, Rosen::ModifierNG::RSPropertyType::ROTATION_X);
7668             CancelModifierAnimation<Rosen::ModifierNG::RSTransformModifier, float>(
7669                 rotationYUserModifier_, Rosen::ModifierNG::RSPropertyType::ROTATION_Y);
7670             CancelModifierAnimation<Rosen::ModifierNG::RSTransformModifier, float>(
7671                 rotationZUserModifier_, Rosen::ModifierNG::RSPropertyType::ROTATION);
7672             NotifyHostTransformUpdated();
7673             break;
7674         }
7675         case AnimationPropertyType::TRANSLATION: {
7676             CancelModifierAnimation<Rosen::ModifierNG::RSTransformModifier, Rosen::Vector2f>(
7677                 translateXYUserModifier_, Rosen::ModifierNG::RSPropertyType::TRANSLATE);
7678             NotifyHostTransformUpdated();
7679             break;
7680         }
7681         case AnimationPropertyType::SCALE: {
7682             CancelModifierAnimation<Rosen::ModifierNG::RSTransformModifier, Rosen::Vector2f>(
7683                 scaleXYUserModifier_, Rosen::ModifierNG::RSPropertyType::SCALE);
7684             NotifyHostTransformUpdated();
7685             break;
7686         }
7687         case AnimationPropertyType::OPACITY: {
7688             CancelModifierAnimation<Rosen::ModifierNG::RSAlphaModifier, float>(
7689                 alphaUserModifier_, Rosen::ModifierNG::RSPropertyType::ALPHA);
7690             break;
7691         }
7692         default: {
7693             break;
7694         }
7695     }
7696 }
7697 
GetRenderNodePropertyValue(AnimationPropertyType property)7698 std::vector<float> RosenRenderContext::GetRenderNodePropertyValue(AnimationPropertyType property)
7699 {
7700     std::vector<float> result;
7701     CHECK_NULL_RETURN(rsNode_, result);
7702     switch (property) {
7703         case AnimationPropertyType::ROTATION: {
7704             auto angleX = GetAnimatablePropertyStagingValue<Rosen::ModifierNG::RSTransformModifier, float>(
7705                 rotationXUserModifier_, Rosen::ModifierNG::RSPropertyType::ROTATION_X, 0.0f);
7706             auto angleY = GetAnimatablePropertyStagingValue<Rosen::ModifierNG::RSTransformModifier, float>(
7707                 rotationYUserModifier_, Rosen::ModifierNG::RSPropertyType::ROTATION_Y, 0.0f);
7708             auto angleZ = GetAnimatablePropertyStagingValue<Rosen::ModifierNG::RSTransformModifier, float>(
7709                 rotationZUserModifier_, Rosen::ModifierNG::RSPropertyType::ROTATION, 0.0f);
7710             // reverse angleX and angleY, because the angle direction is inconsistent with the RS.
7711             result = { -angleX, -angleY, angleZ };
7712             break;
7713         }
7714         case AnimationPropertyType::TRANSLATION: {
7715             auto value = GetAnimatablePropertyStagingValue<Rosen::ModifierNG::RSTransformModifier, Rosen::Vector2f>(
7716                 translateXYUserModifier_, Rosen::ModifierNG::RSPropertyType::TRANSLATE);
7717             result = { value[0], value[1] };
7718             break;
7719         }
7720         case AnimationPropertyType::SCALE: {
7721             auto value = GetAnimatablePropertyStagingValue<Rosen::ModifierNG::RSTransformModifier, Rosen::Vector2f>(
7722                 scaleXYUserModifier_, Rosen::ModifierNG::RSPropertyType::SCALE, { 1.0f, 1.0f });
7723             result = { value[0], value[1] };
7724             break;
7725         }
7726         case AnimationPropertyType::OPACITY: {
7727             auto opacity = GetAnimatablePropertyStagingValue<Rosen::ModifierNG::RSAlphaModifier, float>(
7728                 alphaUserModifier_, Rosen::ModifierNG::RSPropertyType::ALPHA, 1.0f);
7729             result = { opacity };
7730             break;
7731         }
7732         default: {
7733             break;
7734         }
7735     }
7736     return result;
7737 }
7738 
SyncRSPropertyToRenderContext(AnimationPropertyType property)7739 void RosenRenderContext::SyncRSPropertyToRenderContext(AnimationPropertyType property)
7740 {
7741     auto rsValue = GetRenderNodePropertyValue(property);
7742     switch (property) {
7743         case AnimationPropertyType::ROTATION: {
7744             CHECK_NULL_VOID(rsValue.size() == ROTATION_PARAM_SIZE);
7745             auto& transformProperty = GetOrCreateTransform();
7746             float perspective = 0.0f;
7747             if (transformProperty->propTransformRotateAngle.has_value()) {
7748                 perspective = transformProperty->propTransformRotateAngle->w;
7749             } else if (transformProperty->propTransformRotate.has_value()) {
7750                 perspective = transformProperty->propTransformRotate->v;
7751                 transformProperty->ResetTransformRotate();
7752             }
7753             transformProperty->propTransformRotateAngle = { rsValue[0], rsValue[1], rsValue[2], perspective };
7754             break;
7755         }
7756         case AnimationPropertyType::TRANSLATION: {
7757             CHECK_NULL_VOID(rsValue.size() == TRANSLATION_PARAM_SIZE);
7758             auto& transformProperty = GetOrCreateTransform();
7759             CalcDimension translateZ { Dimension(0.0f, DimensionUnit::PX) };
7760             if (transformProperty->propTransformTranslate.has_value()) {
7761                 translateZ = transformProperty->propTransformTranslate->z;
7762             }
7763             transformProperty->propTransformTranslate = TranslateOptions(
7764                 Dimension(rsValue[0], DimensionUnit::PX), Dimension(rsValue[1], DimensionUnit::PX), translateZ);
7765             break;
7766         }
7767         case AnimationPropertyType::SCALE: {
7768             CHECK_NULL_VOID(rsValue.size() == SCALE_PARAM_SIZE);
7769             auto& transformProperty = GetOrCreateTransform();
7770             transformProperty->propTransformScale = { rsValue[0], rsValue[1] };
7771             break;
7772         }
7773         case AnimationPropertyType::OPACITY: {
7774             CHECK_NULL_VOID(rsValue.size() == OPACITY_PARAM_SIZE);
7775             propOpacity_ = rsValue[0];
7776             break;
7777         }
7778         default: {
7779             break;
7780         }
7781     }
7782 }
7783 
MarkNeedDrawNode(bool condition)7784 void RosenRenderContext::MarkNeedDrawNode(bool condition)
7785 {
7786     if (condition && rsNode_) {
7787         rsNode_->SetDrawNode();
7788     }
7789 }
7790 
ShouldSkipAffineTransformation(std::shared_ptr<RSNode> rsNode)7791 bool RosenRenderContext::ShouldSkipAffineTransformation(std::shared_ptr<RSNode> rsNode)
7792 {
7793     if (SystemProperties::GetContainerDeleteFlag() &&
7794         rsNode->GetDrawNodeType() != Rosen::DrawNodeType::GeometryPropertyType) {
7795         if (SystemProperties::GetDebugEnabled()) {
7796             TAG_LOGD(AceLogTag::ACE_DEFAULT_DOMAIN, "Should skip affine transformation, node(%{public}d, %{public}s)",
7797                 rsNode->GetFrameNodeId(), rsNode->GetFrameNodeTag().c_str());
7798         }
7799         return true;
7800     }
7801     return false;
7802 }
7803 
SetNeedCallbackNodeChange(bool needCallback)7804 void RenderContext::SetNeedCallbackNodeChange(bool needCallback)
7805 {
7806     Rosen::RSNode::SetNeedCallbackNodeChange(needCallback);
7807 }
7808 
GetOrCreateTransitionModifier()7809 std::shared_ptr<TransitionModifier> RosenRenderContext::GetOrCreateTransitionModifier()
7810 {
7811     if (!transitionModifier_) {
7812         transitionModifier_ = std::make_shared<TransitionModifier>();
7813         std::function<void(const std::shared_ptr<Rosen::RectF>& rect)> func =
7814             [weak = WeakClaim(this)](const std::shared_ptr<Rosen::RectF>& rect) {
7815                 auto renderContext = weak.Upgrade();
7816                 CHECK_NULL_VOID(renderContext);
7817                 renderContext->UpdateDrawRegion(DRAW_REGION_TRANSITION_MODIFIER_INDEX, rect);
7818             };
7819 
7820         transitionModifier_->SetDrawRegionUpdateFunc(std::move(func));
7821     }
7822 
7823     return transitionModifier_;
7824 }
7825 
GetOrCreateBackgroundModifier()7826 std::shared_ptr<BackgroundModifier> RosenRenderContext::GetOrCreateBackgroundModifier()
7827 {
7828     if (!backgroundModifier_) {
7829         backgroundModifier_ = std::make_shared<BackgroundModifier>();
7830     }
7831     return backgroundModifier_;
7832 }
7833 
ModifyCustomBackground()7834 void RosenRenderContext::ModifyCustomBackground()
7835 {
7836     CHECK_NULL_VOID(rsNode_);
7837     auto transitionModifier = GetOrCreateTransitionModifier();
7838     CHECK_NULL_VOID(transitionModifier);
7839     auto backgroundModifier = GetOrCreateBackgroundModifier();
7840     CHECK_NULL_VOID(backgroundModifier);
7841     if (GetIsTransitionBackgroundValue(false)) {
7842         rsNode_->RemoveModifier(backgroundModifier);
7843         rsNode_->AddModifier(transitionModifier);
7844         transitionModifier->Modify();
7845     } else {
7846         rsNode_->RemoveModifier(transitionModifier);
7847         rsNode_->AddModifier(backgroundModifier);
7848         backgroundModifier->Modify();
7849     }
7850 }
7851 
SetNeedUseCmdlistDrawRegion(bool needUseCmdlistDrawRegion)7852 void RosenRenderContext::SetNeedUseCmdlistDrawRegion(bool needUseCmdlistDrawRegion)
7853 {
7854     CHECK_NULL_VOID(rsNode_);
7855     rsNode_->SetNeedUseCmdlistDrawRegion(needUseCmdlistDrawRegion);
7856 }
7857 } // namespace OHOS::Ace::NG
7858