1 /*
2 * Copyright (c) 2022 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 "modifier/rs_render_modifier.h"
17 #include "draw/color.h"
18 #include "image/bitmap.h"
19 #include <memory>
20 #include <unordered_map>
21
22 #include "pixel_map.h"
23
24 #include "common/rs_obj_abs_geometry.h"
25 #include "common/rs_vector2.h"
26 #include "common/rs_vector4.h"
27 #include "modifier/rs_modifier_type.h"
28 #include "pipeline/rs_draw_cmd_list.h"
29 #include "pipeline/rs_paint_filter_canvas.h"
30 #include "platform/common/rs_log.h"
31 #include "property/rs_properties.h"
32 #include "property/rs_properties_def.h"
33 #include "property/rs_properties_painter.h"
34 #include "render/rs_filter.h"
35 #include "render/rs_image.h"
36 #include "render/rs_mask.h"
37 #include "render/rs_path.h"
38 #include "render/rs_shader.h"
39
40 namespace OHOS {
41 namespace Rosen {
42 namespace {
43 using ModifierUnmarshallingFunc = RSRenderModifier* (*)(Parcel& parcel);
44
45 #define DECLARE_ANIMATABLE_MODIFIER(MODIFIER_NAME, TYPE, MODIFIER_TYPE, DELTA_OP, MODIFIER_TIER, THRESHOLD_TYPE) \
46 { RSModifierType::MODIFIER_TYPE, [](Parcel& parcel) -> RSRenderModifier* { \
47 std::shared_ptr<RSRenderAnimatableProperty<TYPE>> prop; \
48 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) { \
49 return nullptr; \
50 } \
51 auto modifier = new RS##MODIFIER_NAME##RenderModifier(prop); \
52 return ((!modifier) ? nullptr : modifier); \
53 }, \
54 },
55
56 #define DECLARE_NOANIMATABLE_MODIFIER(MODIFIER_NAME, TYPE, MODIFIER_TYPE, MODIFIER_TIER) \
57 { RSModifierType::MODIFIER_TYPE, [](Parcel& parcel) -> RSRenderModifier* { \
58 std::shared_ptr<RSRenderProperty<TYPE>> prop; \
59 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) { \
60 return nullptr; \
61 } \
62 auto modifier = new RS##MODIFIER_NAME##RenderModifier(prop); \
63 return ((!modifier) ? nullptr : modifier); \
64 }, \
65 },
66
67 static std::unordered_map<RSModifierType, ModifierUnmarshallingFunc> funcLUT = {
68 #include "modifier/rs_modifiers_def.in"
__anon22ea1eed0202() 69 { RSModifierType::EXTENDED, [](Parcel& parcel) -> RSRenderModifier* {
70 std::shared_ptr<RSRenderProperty<std::shared_ptr<Drawing::DrawCmdList>>> prop;
71 int16_t type;
72 if (!RSMarshallingHelper::Unmarshalling(parcel, prop) || !parcel.ReadInt16(type)) {
73 ROSEN_LOGE("RSModifierType::EXTENDE Unmarshalling or ReadInt16 failed");
74 return nullptr;
75 }
76 RSDrawCmdListRenderModifier* modifier = new RSDrawCmdListRenderModifier(prop);
77 modifier->SetType(static_cast<RSModifierType>(type));
78 return modifier;
79 },
80 },
__anon22ea1eed0302() 81 { RSModifierType::ENV_FOREGROUND_COLOR, [](Parcel& parcel) -> RSRenderModifier* {
82 std::shared_ptr<RSRenderAnimatableProperty<Color>> prop;
83 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
84 ROSEN_LOGE("RSModifierType::ENV_FOREGROUND_COLOR Unmarshalling failed");
85 return nullptr;
86 }
87 auto modifier = new RSEnvForegroundColorRenderModifier(prop);
88 return modifier;
89 },
90 },
__anon22ea1eed0402() 91 { RSModifierType::ENV_FOREGROUND_COLOR_STRATEGY, [](Parcel& parcel) -> RSRenderModifier* {
92 std::shared_ptr<RSRenderProperty<ForegroundColorStrategyType>> prop;
93 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
94 ROSEN_LOGE("RSModifierType::ENV_FOREGROUND_COLOR_STRATEGY Unmarshalling failed");
95 return nullptr;
96 }
97 auto modifier = new RSEnvForegroundColorStrategyRenderModifier(prop);
98 return modifier;
99 },
100 },
__anon22ea1eed0502() 101 { RSModifierType::CUSTOM_CLIP_TO_FRAME, [](Parcel& parcel) -> RSRenderModifier* {
102 std::shared_ptr<RSRenderAnimatableProperty<Vector4f>> prop;
103 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
104 ROSEN_LOGE("RSModifierType::CUSTOM_CLIP_TO_FRAME Unmarshalling failed");
105 return nullptr;
106 }
107 auto modifier = new RSCustomClipToFrameRenderModifier(prop);
108 return modifier;
109 },
110 },
__anon22ea1eed0602() 111 { RSModifierType::HDR_BRIGHTNESS, [](Parcel& parcel) -> RSRenderModifier* {
112 std::shared_ptr<RSRenderAnimatableProperty<float>> prop;
113 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
114 ROSEN_LOGE("RSModifierType::HDR_BRIGHTNESS Unmarshalling failed");
115 return nullptr;
116 }
117 auto modifier = new RSHDRBrightnessRenderModifier(prop);
118 return modifier;
119 },
120 },
__anon22ea1eed0702() 121 { RSModifierType::GEOMETRYTRANS, [](Parcel& parcel) -> RSRenderModifier* {
122 std::shared_ptr<RSRenderProperty<Drawing::Matrix>> prop;
123 int16_t type;
124 if (!RSMarshallingHelper::Unmarshalling(parcel, prop) || !parcel.ReadInt16(type)) {
125 ROSEN_LOGE("RSModifierType::GEOMETRYTRANS Unmarshalling or ReadInt16 failed");
126 return nullptr;
127 }
128 auto modifier = new RSGeometryTransRenderModifier(prop);
129 modifier->SetType(static_cast<RSModifierType>(type));
130 return modifier;
131 },
132 },
__anon22ea1eed0802() 133 { RSModifierType::BEHIND_WINDOW_FILTER_ENABLED, [](Parcel& parcel) -> RSRenderModifier* {
134 std::shared_ptr<RSRenderProperty<bool>> prop;
135 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
136 ROSEN_LOGE("RSModifierType::BEHIND_WINDOW_FILTER_ENABLED Unmarshalling failed");
137 return nullptr;
138 }
139 auto modifier = new RSBehindWindowFilterEnabledRenderModifier(prop);
140 return modifier;
141 },
142 },
__anon22ea1eed0902() 143 { RSModifierType::BEHIND_WINDOW_FILTER_RADIUS, [](Parcel& parcel) -> RSRenderModifier* {
144 std::shared_ptr<RSRenderAnimatableProperty<float>> prop;
145 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
146 ROSEN_LOGE("RSModifierType::BEHIND_WINDOW_FILTER_RADIUS Unmarshalling failed");
147 return nullptr;
148 }
149 auto modifier = new RSBehindWindowFilterRadiusRenderModifier(prop);
150 return modifier;
151 },
152 },
__anon22ea1eed0a02() 153 { RSModifierType::BEHIND_WINDOW_FILTER_SATURATION, [](Parcel& parcel) -> RSRenderModifier* {
154 std::shared_ptr<RSRenderAnimatableProperty<float>> prop;
155 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
156 ROSEN_LOGE("RSModifierType::BEHIND_WINDOW_FILTER_SATURATION Unmarshalling failed");
157 return nullptr;
158 }
159 auto modifier = new RSBehindWindowFilterSaturationRenderModifier(prop);
160 return modifier;
161 },
162 },
__anon22ea1eed0b02() 163 { RSModifierType::BEHIND_WINDOW_FILTER_BRIGHTNESS, [](Parcel& parcel) -> RSRenderModifier* {
164 std::shared_ptr<RSRenderAnimatableProperty<float>> prop;
165 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
166 ROSEN_LOGE("RSModifierType::BEHIND_WINDOW_FILTER_BRIGHTNESS Unmarshalling failed");
167 return nullptr;
168 }
169 auto modifier = new RSBehindWindowFilterBrightnessRenderModifier(prop);
170 return modifier;
171 },
172 },
__anon22ea1eed0c02() 173 { RSModifierType::BEHIND_WINDOW_FILTER_MASK_COLOR, [](Parcel& parcel) -> RSRenderModifier* {
174 std::shared_ptr<RSRenderAnimatableProperty<Color>> prop;
175 if (!RSMarshallingHelper::Unmarshalling(parcel, prop)) {
176 ROSEN_LOGE("RSModifierType::BEHIND_WINDOW_FILTER_MASK_COLOR Unmarshalling failed");
177 return nullptr;
178 }
179 auto modifier = new RSBehindWindowFilterMaskColorRenderModifier(prop);
180 return modifier;
181 },
182 },
183 };
184
185 #undef DECLARE_ANIMATABLE_MODIFIER
186 #undef DECLARE_NOANIMATABLE_MODIFIER
187 }
188
Apply(RSModifierContext & context) const189 void RSDrawCmdListRenderModifier::Apply(RSModifierContext& context) const
190 {
191 if (context.canvas_) {
192 auto& cmds = property_->GetRef();
193 RSPropertiesPainter::DrawFrame(context.properties_, *context.canvas_, cmds);
194 }
195 }
196
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)197 void RSDrawCmdListRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta)
198 {
199 if (auto property = std::static_pointer_cast<RSRenderProperty<Drawing::DrawCmdListPtr>>(prop)) {
200 property_->Set(property->Get());
201 }
202 }
203
Marshalling(Parcel & parcel)204 bool RSDrawCmdListRenderModifier::Marshalling(Parcel& parcel)
205 {
206 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::EXTENDED)) &&
207 RSMarshallingHelper::Marshalling(parcel, property_) && parcel.WriteInt16(static_cast<int16_t>(GetType()));
208 if (!flag) {
209 ROSEN_LOGE("RSDrawCmdListRenderModifier::Marshalling failed");
210 }
211 return flag;
212 }
213
Marshalling(Parcel & parcel)214 bool RSEnvForegroundColorRenderModifier::Marshalling(Parcel& parcel)
215 {
216 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<Color>>(property_);
217 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::ENV_FOREGROUND_COLOR)) &&
218 RSMarshallingHelper::Marshalling(parcel, renderProperty);
219 if (!flag) {
220 ROSEN_LOGE("RSEnvForegroundColorRenderModifier::Marshalling failed");
221 }
222 return flag;
223 }
224
Apply(RSModifierContext & context) const225 void RSEnvForegroundColorRenderModifier::Apply(RSModifierContext& context) const
226 {
227 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<Color>>(property_);
228 context.canvas_->SetEnvForegroundColor(renderProperty->Get());
229 }
230
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)231 void RSEnvForegroundColorRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta)
232 {
233 if (auto property = std::static_pointer_cast<RSRenderAnimatableProperty<Color>>(prop)) {
234 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<Color>>(property_);
235 renderProperty->Set(isDelta ? (renderProperty->Get() + property->Get()) : property->Get());
236 }
237 }
238
Marshalling(Parcel & parcel)239 bool RSEnvForegroundColorStrategyRenderModifier::Marshalling(Parcel& parcel)
240 {
241 auto renderProperty = std::static_pointer_cast<RSRenderProperty<ForegroundColorStrategyType>>(property_);
242 bool flag = parcel.WriteInt16(static_cast<short>(RSModifierType::ENV_FOREGROUND_COLOR_STRATEGY)) &&
243 RSMarshallingHelper::Marshalling(parcel, renderProperty);
244 if (!flag) {
245 ROSEN_LOGE("RSEnvForegroundColorStrategyRenderModifier::Marshalling failed");
246 }
247 return flag;
248 }
249
250
Apply(RSModifierContext & context) const251 void RSEnvForegroundColorStrategyRenderModifier::Apply(RSModifierContext& context) const
252 {
253 auto renderProperty = std::static_pointer_cast<RSRenderProperty<ForegroundColorStrategyType>>(property_);
254 switch (renderProperty->Get()) {
255 case ForegroundColorStrategyType::INVERT_BACKGROUNDCOLOR: {
256 // calculate the color by screebshot
257 Color color = GetInvertBackgroundColor(context);
258 context.canvas_->SetEnvForegroundColor(color);
259 break;
260 }
261 default: {
262 break;
263 }
264 }
265 }
266
CalculateInvertColor(Color backgroundColor) const267 Color RSEnvForegroundColorStrategyRenderModifier::CalculateInvertColor(Color backgroundColor) const
268 {
269 int16_t a = std::clamp<int16_t>(backgroundColor.GetAlpha(), 0, UINT8_MAX);
270 int16_t r = 255 - std::clamp<int16_t>(backgroundColor.GetRed(), 0, UINT8_MAX);
271 int16_t g = 255 - std::clamp<int16_t>(backgroundColor.GetGreen(), 0, UINT8_MAX);
272 int16_t b = 255 - std::clamp<int16_t>(backgroundColor.GetBlue(), 0, UINT8_MAX);
273 return Color(r, g, b, a);
274 }
275
GetInvertBackgroundColor(RSModifierContext & context) const276 Color RSEnvForegroundColorStrategyRenderModifier::GetInvertBackgroundColor(RSModifierContext& context) const
277 {
278 Drawing::AutoCanvasRestore acr(*context.canvas_, true);
279 if (!context.properties_.GetClipToBounds()) {
280 RS_LOGI("RSRenderModifier::GetInvertBackgroundColor not GetClipToBounds");
281 Vector4f clipRegion = context.properties_.GetBounds();
282 Drawing::Rect rect = Drawing::Rect(0, 0, clipRegion.z_, clipRegion.w_);
283 context.canvas_->ClipRect(rect, Drawing::ClipOp::INTERSECT, false);
284 }
285 Color backgroundColor = context.properties_.GetBackgroundColor();
286 if (backgroundColor.GetAlpha() == 0xff) {
287 RS_LOGI("RSRenderModifier::GetInvertBackgroundColor not alpha");
288 return CalculateInvertColor(backgroundColor);
289 }
290 auto imageSnapshot = context.canvas_->GetSurface()->GetImageSnapshot(context.canvas_->GetDeviceClipBounds());
291 if (imageSnapshot == nullptr) {
292 RS_LOGI("RSRenderModifier::GetInvertBackgroundColor imageSnapshot null");
293 return Color(0);
294 }
295 auto colorPicker = RSPropertiesPainter::CalcAverageColor(imageSnapshot);
296 return CalculateInvertColor(Color(
297 Drawing::Color::ColorQuadGetR(colorPicker), Drawing::Color::ColorQuadGetG(colorPicker),
298 Drawing::Color::ColorQuadGetB(colorPicker), Drawing::Color::ColorQuadGetA(colorPicker)));
299 }
300
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)301 void RSEnvForegroundColorStrategyRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta)
302 {
303 if (auto property = std::static_pointer_cast<RSRenderProperty<ForegroundColorStrategyType >>(prop)) {
304 auto renderProperty = std::static_pointer_cast<RSRenderProperty<ForegroundColorStrategyType >>(property_);
305 renderProperty->Set(property->Get());
306 }
307 }
308
Marshalling(Parcel & parcel)309 bool RSCustomClipToFrameRenderModifier::Marshalling(Parcel& parcel)
310 {
311 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<Vector4f>>(property_);
312 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::CUSTOM_CLIP_TO_FRAME)) &&
313 RSMarshallingHelper::Marshalling(parcel, renderProperty);
314 if (!flag) {
315 ROSEN_LOGE("RSCustomClipToFrameRenderModifier::Marshalling failed");
316 }
317 return flag;
318 }
319
Apply(RSModifierContext & context) const320 void RSCustomClipToFrameRenderModifier::Apply(RSModifierContext& context) const
321 {
322 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<Vector4f>>(property_);
323 const auto& rect4f = renderProperty->Get();
324 Drawing::Rect customClipRect(rect4f.x_, rect4f.y_, rect4f.z_, rect4f.w_);
325 context.canvas_->ClipRect(customClipRect);
326 }
327
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)328 void RSCustomClipToFrameRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta)
329 {
330 if (auto property = std::static_pointer_cast<RSRenderAnimatableProperty<Vector4f>>(prop)) {
331 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<Vector4f>>(property_);
332 renderProperty->Set(isDelta ? (renderProperty->Get() + property->Get()) : property->Get());
333 }
334 }
335
Marshalling(Parcel & parcel)336 bool RSHDRBrightnessRenderModifier::Marshalling(Parcel& parcel)
337 {
338 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(property_);
339 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::HDR_BRIGHTNESS)) &&
340 RSMarshallingHelper::Marshalling(parcel, renderProperty);
341 if (!flag) {
342 ROSEN_LOGE("RSHDRBrightnessRenderModifier::Marshalling failed");
343 }
344 return flag;
345 }
346
Apply(RSModifierContext & context) const347 void RSHDRBrightnessRenderModifier::Apply(RSModifierContext& context) const {}
348
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)349 void RSHDRBrightnessRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta)
350 {
351 if (auto property = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(prop)) {
352 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(property_);
353 renderProperty->Set(isDelta ? (renderProperty->Get() + property->Get()) : property->Get());
354 }
355 }
356
Apply(RSModifierContext & context) const357 void RSGeometryTransRenderModifier::Apply(RSModifierContext& context) const
358 {
359 auto& geoPtr = (context.properties_.GetBoundsGeometry());
360 geoPtr->ConcatMatrix(property_->Get());
361 }
362
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)363 void RSGeometryTransRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta)
364 {
365 if (auto property = std::static_pointer_cast<RSRenderProperty<Drawing::Matrix>>(prop)) {
366 property_->Set(property->Get());
367 }
368 }
369
Marshalling(Parcel & parcel)370 bool RSGeometryTransRenderModifier::Marshalling(Parcel& parcel)
371 {
372 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::GEOMETRYTRANS)) &&
373 RSMarshallingHelper::Marshalling(parcel, property_) && parcel.WriteInt16(static_cast<int16_t>(GetType()));
374 if (!flag) {
375 ROSEN_LOGE("RSGeometryTransRenderModifier::Marshalling failed");
376 }
377 return flag;
378 }
379
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)380 void RSBehindWindowFilterEnabledRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta)
381 {
382 if (auto property = std::static_pointer_cast<RSRenderProperty<bool>>(prop)) {
383 auto renderProperty = std::static_pointer_cast<RSRenderProperty<bool>>(property_);
384 renderProperty->Set(property->GetRef());
385 }
386 }
387
Marshalling(Parcel & parcel)388 bool RSBehindWindowFilterEnabledRenderModifier::Marshalling(Parcel& parcel)
389 {
390 auto renderProperty = std::static_pointer_cast<RSRenderProperty<bool>>(property_);
391 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::BEHIND_WINDOW_FILTER_ENABLED)) &&
392 RSMarshallingHelper::Marshalling(parcel, renderProperty);
393 if (!flag) {
394 ROSEN_LOGE("RSBehindWindowFilterEnabledRenderModifier::Marshalling failed");
395 }
396 return flag;
397 }
398
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)399 void RSBehindWindowFilterRadiusRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta)
400 {
401 if (auto property = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(prop)) {
402 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(property_);
403 renderProperty->Set(isDelta ? (renderProperty->Get() + property->Get()) : property->Get());
404 }
405 }
406
Marshalling(Parcel & parcel)407 bool RSBehindWindowFilterRadiusRenderModifier::Marshalling(Parcel& parcel)
408 {
409 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(property_);
410 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::BEHIND_WINDOW_FILTER_RADIUS)) &&
411 RSMarshallingHelper::Marshalling(parcel, renderProperty);
412 if (!flag) {
413 ROSEN_LOGE("RSBehindWindowFilterRadiusRenderModifier::Marshalling failed");
414 }
415 return flag;
416 }
417
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)418 void RSBehindWindowFilterSaturationRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop,
419 bool isDelta)
420 {
421 if (auto property = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(prop)) {
422 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(property_);
423 renderProperty->Set(isDelta ? (renderProperty->Get() + property->Get()) : property->Get());
424 }
425 }
426
Marshalling(Parcel & parcel)427 bool RSBehindWindowFilterSaturationRenderModifier::Marshalling(Parcel& parcel)
428 {
429 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(property_);
430 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::BEHIND_WINDOW_FILTER_SATURATION)) &&
431 RSMarshallingHelper::Marshalling(parcel, renderProperty);
432 if (!flag) {
433 ROSEN_LOGE("RSBehindWindowFilterSaturationRenderModifier::Marshalling failed");
434 }
435 return flag;
436 }
437
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)438 void RSBehindWindowFilterBrightnessRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop,
439 bool isDelta)
440 {
441 if (auto property = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(prop)) {
442 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(property_);
443 renderProperty->Set(isDelta ? (renderProperty->Get() + property->Get()) : property->Get());
444 }
445 }
446
Marshalling(Parcel & parcel)447 bool RSBehindWindowFilterBrightnessRenderModifier::Marshalling(Parcel& parcel)
448 {
449 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<float>>(property_);
450 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::BEHIND_WINDOW_FILTER_BRIGHTNESS)) &&
451 RSMarshallingHelper::Marshalling(parcel, renderProperty);
452 if (!flag) {
453 ROSEN_LOGE("RSBehindWindowFilterBrightnessRenderModifier::Marshalling failed");
454 }
455 return flag;
456 }
457
Update(const std::shared_ptr<RSRenderPropertyBase> & prop,bool isDelta)458 void RSBehindWindowFilterMaskColorRenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop,
459 bool isDelta)
460 {
461 if (auto property = std::static_pointer_cast<RSRenderAnimatableProperty<Color>>(prop)) {
462 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<Color>>(property_);
463 renderProperty->Set(isDelta ? (renderProperty->Get() + property->Get()) : property->Get());
464 }
465 }
466
Marshalling(Parcel & parcel)467 bool RSBehindWindowFilterMaskColorRenderModifier::Marshalling(Parcel& parcel)
468 {
469 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<Color>>(property_);
470 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::BEHIND_WINDOW_FILTER_MASK_COLOR)) &&
471 RSMarshallingHelper::Marshalling(parcel, renderProperty);
472 if (!flag) {
473 ROSEN_LOGE("RSBehindWindowFilterMaskColorRenderModifier::Marshalling failed");
474 }
475 return flag;
476 }
477
Unmarshalling(Parcel & parcel)478 RSRenderModifier* RSRenderModifier::Unmarshalling(Parcel& parcel)
479 {
480 int16_t type = 0;
481 if (!parcel.ReadInt16(type)) {
482 ROSEN_LOGE("RSRenderModifier::Unmarshalling ReadInt16 failed");
483 return nullptr;
484 }
485 auto it = funcLUT.find(static_cast<RSModifierType>(type));
486 if (it == funcLUT.end()) {
487 ROSEN_LOGE("RSRenderModifier Unmarshalling cannot find func in lut %{public}d", type);
488 return nullptr;
489 }
490 return it->second(parcel);
491 }
492
493 namespace {
494 template<typename T>
Add(const T & a,const T && b)495 T Add(const T& a, const T&& b)
496 {
497 return a + b;
498 }
499 template<typename T>
Add(const std::optional<T> & a,const T && b)500 T Add(const std::optional<T>& a, const T&& b)
501 {
502 return a.has_value() ? *a + b : b;
503 }
504
505 template<typename T>
Multiply(const T & a,const T && b)506 T Multiply(const T& a, const T&& b)
507 {
508 return a * b;
509 }
510 template<typename T>
Multiply(const std::optional<T> & a,const T && b)511 T Multiply(const std::optional<T>& a, const T&& b)
512 {
513 return a.has_value() ? *a * b : b;
514 }
515
516 template<typename T>
Replace(const T & a,const T && b)517 const T& Replace(const T& a, const T&& b)
518 {
519 return b;
520 }
521 template<typename T>
Replace(const std::optional<T> & a,T && b)522 const T& Replace(const std::optional<T>& a, T&& b)
523 {
524 return b;
525 }
526 } // namespace
527
528 #define DECLARE_ANIMATABLE_MODIFIER(MODIFIER_NAME, TYPE, MODIFIER_TYPE, DELTA_OP, MODIFIER_TIER, THRESHOLD_TYPE) \
529 bool RS##MODIFIER_NAME##RenderModifier::Marshalling(Parcel& parcel) \
530 { \
531 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<TYPE>>(property_); \
532 bool flag = parcel.WriteInt16(static_cast<int16_t>(RSModifierType::MODIFIER_TYPE)) && \
533 RSMarshallingHelper::Marshalling(parcel, renderProperty); \
534 if (!flag) { \
535 ROSEN_LOGE("ANIMATABLE_MODIFIER RenderModifier::Marshalling WriteInt16 or Marshalling failed"); \
536 } \
537 return flag; \
538 } \
539 void RS##MODIFIER_NAME##RenderModifier::Apply(RSModifierContext& context) const \
540 { \
541 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<TYPE>>(property_); \
542 context.properties_.Set##MODIFIER_NAME( \
543 DELTA_OP(context.properties_.Get##MODIFIER_NAME(), renderProperty->Get())); \
544 } \
545 void RS##MODIFIER_NAME##RenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta) \
546 { \
547 if (auto property = std::static_pointer_cast<RSRenderAnimatableProperty<TYPE>>(prop)) { \
548 auto renderProperty = std::static_pointer_cast<RSRenderAnimatableProperty<TYPE>>(property_); \
549 renderProperty->Set(isDelta ? (renderProperty->Get() + property->Get()) : property->Get()); \
550 } \
551 }
552
553 #define DECLARE_NOANIMATABLE_MODIFIER(MODIFIER_NAME, TYPE, MODIFIER_TYPE, MODIFIER_TIER) \
554 bool RS##MODIFIER_NAME##RenderModifier::Marshalling(Parcel& parcel) \
555 { \
556 auto renderProperty = std::static_pointer_cast<RSRenderProperty<TYPE>>(property_); \
557 bool flag = parcel.WriteInt16(static_cast<short>(RSModifierType::MODIFIER_TYPE)) && \
558 RSMarshallingHelper::Marshalling(parcel, renderProperty); \
559 if (!flag) { \
560 ROSEN_LOGE("NOANIMATABLE_MODIFIER RenderModifier::Marshalling WriteInt16 or Marshalling failed"); \
561 } \
562 return flag; \
563 } \
564 void RS##MODIFIER_NAME##RenderModifier::Apply(RSModifierContext& context) const \
565 { \
566 auto renderProperty = std::static_pointer_cast<RSRenderProperty<TYPE>>(property_); \
567 context.properties_.Set##MODIFIER_NAME(renderProperty->GetRef()); \
568 } \
569 void RS##MODIFIER_NAME##RenderModifier::Update(const std::shared_ptr<RSRenderPropertyBase>& prop, bool isDelta) \
570 { \
571 if (auto property = std::static_pointer_cast<RSRenderProperty<TYPE>>(prop)) { \
572 auto renderProperty = std::static_pointer_cast<RSRenderProperty<TYPE>>(property_); \
573 renderProperty->Set(property->GetRef()); \
574 } \
575 }
576
577 #include "modifier/rs_modifiers_def.in"
578 DECLARE_NOANIMATABLE_MODIFIER(Particles, RSRenderParticleVector, PARTICLE, Foreground)
579
580 #undef DECLARE_ANIMATABLE_MODIFIER
581 #undef DECLARE_NOANIMATABLE_MODIFIER
582 } // namespace Rosen
583 } // namespace OHOS
584