1 /*
2 * Copyright (c) 2021-2023 Huawei Device Co., Ltd.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
6 *
7 * http://www.apache.org/licenses/LICENSE-2.0
8 *
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
14 */
15
16 #include "animation/rs_render_transition_effect.h"
17
18 #include <climits>
19
20 #include "animation/rs_animation_common.h"
21 #include "animation/rs_value_estimator.h"
22 #include "modifier/rs_render_modifier.h"
23 #include "platform/common/rs_log.h"
24 #include "transaction/rs_marshalling_helper.h"
25
26 namespace OHOS {
27 namespace Rosen {
28 namespace {
29 enum RSTransitionEffectType : uint16_t {
30 FADE = 1,
31 SCALE,
32 TRANSLATE,
33 ROTATE,
34 UNDEFINED,
35 };
36 constexpr int PID_SHIFT = 32;
37
GenerateTransitionPropertyId()38 PropertyId GenerateTransitionPropertyId()
39 {
40 // manually set pid to INT_MAX to avoid conflict with other process (note: valid pid is smaller than 2^22)
41 static pid_t pid_ = INT_MAX;
42 static std::atomic<uint32_t> currentId_ = 1;
43
44 auto currentId = currentId_.fetch_add(1, std::memory_order_relaxed);
45 if (currentId == UINT32_MAX) {
46 // [PLANNING]:process the overflow situations
47 ROSEN_LOGE("Property Id overflow");
48 }
49
50 return ((PropertyId)pid_ << PID_SHIFT) | currentId;
51 }
52 } // namespace
53
Unmarshalling(Parcel & parcel)54 RSRenderTransitionEffect* RSRenderTransitionEffect::Unmarshalling(Parcel& parcel)
55 {
56 uint16_t transitionType = 0;
57 if (!parcel.ReadUint16(transitionType)) {
58 ROSEN_LOGE("RSRenderTransitionEffect::Unmarshalling, ParseParam Failed");
59 return nullptr;
60 }
61 switch (transitionType) {
62 case RSTransitionEffectType::FADE:
63 return RSTransitionFade::Unmarshalling(parcel);
64 case RSTransitionEffectType::SCALE:
65 return RSTransitionScale::Unmarshalling(parcel);
66 case RSTransitionEffectType::TRANSLATE:
67 return RSTransitionTranslate::Unmarshalling(parcel);
68 case RSTransitionEffectType::ROTATE:
69 return RSTransitionRotate::Unmarshalling(parcel);
70 default:
71 return nullptr;
72 }
73 }
74
GetModifier()75 const std::shared_ptr<RSRenderModifier>& RSRenderTransitionEffect::GetModifier()
76 {
77 if (modifier_ == nullptr) {
78 modifier_ = CreateModifier();
79 }
80 return modifier_;
81 }
82
Marshalling(Parcel & parcel) const83 bool RSTransitionFade::Marshalling(Parcel& parcel) const
84 {
85 return parcel.WriteUint16(RSTransitionEffectType::FADE) && parcel.WriteFloat(alpha_);
86 }
87
Unmarshalling(Parcel & parcel)88 RSRenderTransitionEffect* RSTransitionFade::Unmarshalling(Parcel& parcel)
89 {
90 float alpha;
91 if (!RSMarshallingHelper::Unmarshalling(parcel, alpha)) {
92 ROSEN_LOGE("RSTransitionFade::Unmarshalling, unmarshalling alpha failed");
93 return nullptr;
94 }
95 return new RSTransitionFade(alpha);
96 }
97
Marshalling(Parcel & parcel) const98 bool RSTransitionScale::Marshalling(Parcel& parcel) const
99 {
100 return parcel.WriteUint16(RSTransitionEffectType::SCALE) && parcel.WriteFloat(scaleX_) &&
101 parcel.WriteFloat(scaleY_) && parcel.WriteFloat(scaleZ_);
102 }
103
Unmarshalling(Parcel & parcel)104 RSRenderTransitionEffect* RSTransitionScale::Unmarshalling(Parcel& parcel)
105 {
106 float scaleX = 0.0;
107 float scaleY = 0.0;
108 float scaleZ = 0.0;
109 if (!parcel.ReadFloat(scaleX) || !parcel.ReadFloat(scaleY) || !parcel.ReadFloat(scaleZ)) {
110 ROSEN_LOGE("RSTransitionScale::Unmarshalling, unmarshalling failed");
111 return nullptr;
112 }
113 return new RSTransitionScale(scaleX, scaleY, scaleZ);
114 }
115
Marshalling(Parcel & parcel) const116 bool RSTransitionTranslate::Marshalling(Parcel& parcel) const
117 {
118 return parcel.WriteUint16(RSTransitionEffectType::TRANSLATE) && parcel.WriteFloat(translateX_) &&
119 parcel.WriteFloat(translateY_) && parcel.WriteFloat(translateZ_);
120 }
121
Unmarshalling(Parcel & parcel)122 RSRenderTransitionEffect* RSTransitionTranslate::Unmarshalling(Parcel& parcel)
123 {
124 float translateX;
125 float translateY;
126 float translateZ;
127 if (!parcel.ReadFloat(translateX) || !parcel.ReadFloat(translateY) || !parcel.ReadFloat(translateZ)) {
128 ROSEN_LOGE("RSTransitionTranslate::Unmarshalling, unmarshalling failed");
129 return nullptr;
130 }
131 return new RSTransitionTranslate(translateX, translateY, translateZ);
132 }
133
Marshalling(Parcel & parcel) const134 bool RSTransitionRotate::Marshalling(Parcel& parcel) const
135 {
136 return parcel.WriteUint16(RSTransitionEffectType::ROTATE) && parcel.WriteFloat(dx_) && parcel.WriteFloat(dy_) &&
137 parcel.WriteFloat(dz_) && parcel.WriteFloat(radian_);
138 }
139
Unmarshalling(Parcel & parcel)140 RSRenderTransitionEffect* RSTransitionRotate::Unmarshalling(Parcel& parcel)
141 {
142 Quaternion quaternion;
143 float dx;
144 float dy;
145 float dz;
146 float radian;
147 if (!parcel.ReadFloat(dx) || !parcel.ReadFloat(dy) || !parcel.ReadFloat(dz) || !parcel.ReadFloat(radian)) {
148 ROSEN_LOGE("RSTransitionRotate::Unmarshalling, unmarshalling failed");
149 return nullptr;
150 }
151 return new RSTransitionRotate(dx, dy, dz, radian);
152 }
153
CreateModifier()154 const std::shared_ptr<RSRenderModifier> RSTransitionFade::CreateModifier()
155 {
156 property_ = std::make_shared<RSRenderAnimatableProperty<float>>(0, GenerateTransitionPropertyId());
157 return std::make_shared<RSAlphaRenderModifier>(property_);
158 }
159
UpdateFraction(float fraction) const160 void RSTransitionFade::UpdateFraction(float fraction) const
161 {
162 if (property_ == nullptr) {
163 return;
164 }
165 float startValue(1.0f);
166 float endValue(alpha_);
167 auto value = startValue * (1.0f - fraction) + endValue * fraction;
168 property_->Set(value);
169 }
170
CreateModifier()171 const std::shared_ptr<RSRenderModifier> RSTransitionScale::CreateModifier()
172 {
173 property_ =
174 std::make_shared<RSRenderAnimatableProperty<Vector2f>>(Vector2f { 0, 0 }, GenerateTransitionPropertyId());
175 return std::make_shared<RSScaleRenderModifier>(property_);
176 }
177
UpdateFraction(float fraction) const178 void RSTransitionScale::UpdateFraction(float fraction) const
179 {
180 if (property_ == nullptr) {
181 return;
182 }
183 Vector2f startValue(1.0f, 1.0f);
184 Vector2f endValue(scaleX_, scaleY_);
185 auto value = startValue * (1.0f - fraction) + endValue * fraction;
186 property_->Set(value);
187 }
188
CreateModifier()189 const std::shared_ptr<RSRenderModifier> RSTransitionTranslate::CreateModifier()
190 {
191 property_ =
192 std::make_shared<RSRenderAnimatableProperty<Vector2f>>(Vector2f { 0, 0 }, GenerateTransitionPropertyId());
193 return std::make_shared<RSTranslateRenderModifier>(property_);
194 }
195
UpdateFraction(float fraction) const196 void RSTransitionTranslate::UpdateFraction(float fraction) const
197 {
198 if (property_ == nullptr) {
199 return;
200 }
201 Vector2f startValue(0.0f, 0.0f);
202 Vector2f endValue(translateX_, translateY_);
203 auto value = startValue * (1.0f - fraction) + endValue * fraction;
204 property_->Set(value);
205 }
206
CreateModifier()207 const std::shared_ptr<RSRenderModifier> RSTransitionRotate::CreateModifier()
208 {
209 property_ = std::make_shared<RSRenderAnimatableProperty<Quaternion>>(Quaternion {}, GenerateTransitionPropertyId());
210 return std::make_shared<RSQuaternionRenderModifier>(property_);
211 }
212
UpdateFraction(float fraction) const213 void RSTransitionRotate::UpdateFraction(float fraction) const
214 {
215 if (property_ == nullptr) {
216 return;
217 }
218 auto radian = radian_ * fraction;
219 float factor = std::sin(radian / 2);
220 float qx = dx_ * factor;
221 float qy = dy_ * factor;
222 float qz = dz_ * factor;
223 float qw = std::cos(radian / 2);
224 Quaternion value(qx, qy, qz, qw);
225 property_->Set(value);
226 }
227 } // namespace Rosen
228 } // namespace OHOS
229