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 #ifndef FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_MODIFIER_H 17 #define FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_MODIFIER_H 18 19 #include <atomic> 20 #include <cstdint> 21 #include <functional> 22 #include <optional> 23 #include <vector> 24 25 #include "base/geometry/ng/rect_t.h" 26 #include "base/memory/ace_type.h" 27 #include "base/utils/utils.h" 28 #include "core/components/common/properties/animation_option.h" 29 #include "core/components_ng/animation/gradient_arithmetic.h" 30 #include "core/components_ng/base/linear_vector.h" 31 #include "core/components_ng/render/canvas_image.h" 32 #include "core/components_ng/render/drawing_forward.h" 33 #include "core/components_ng/render/modifier_adapter.h" 34 35 enum class ThresholdType { 36 LAYOUT, // 0.5f for properties like position, as the difference in properties by 0.5 appears visually unchanged 37 COARSE, // 1.0f / 256.0f 38 MEDIUM, // 1.0f / 1000.0f 39 FINE, // 1.0f / 3072.0f 40 COLOR, // 0.0f 41 DEFAULT, // 1.0f / 256.0f 42 ZERO, // 0.0f for noanimatable property 43 }; 44 45 enum class PropertyUnit { 46 UNKNOWN, 47 PIXEL_POSITION, // animatable properties are related to position of the object, the unit is pixels 48 }; 49 50 namespace OHOS::Ace::NG { 51 52 class ExtensionHandler; 53 54 class ACE_FORCE_EXPORT Modifier : public virtual AceType { 55 DECLARE_ACE_TYPE(Modifier, AceType); 56 57 public: 58 Modifier(); ~Modifier()59 ~Modifier() override 60 { 61 ModifierAdapter::RemoveModifier(id_); 62 } 63 GetId()64 int32_t GetId() const 65 { 66 return id_; 67 } 68 69 private: 70 int32_t id_ = 0; 71 ACE_DISALLOW_COPY_AND_MOVE(Modifier); 72 }; 73 74 class PropertyBase : public virtual AceType { 75 DECLARE_ACE_TYPE(PropertyBase, AceType); 76 77 public: 78 PropertyBase() = default; 79 ~PropertyBase() override = default; 80 81 private: 82 ACE_DISALLOW_COPY_AND_MOVE(PropertyBase); 83 }; 84 85 struct DrawingContext { 86 RSCanvas& canvas; 87 float width = 0; 88 float height = 0; 89 }; 90 91 using DrawModifierFunc = std::function<void(NG::DrawingContext& drawingContext)>; 92 93 class ACE_EXPORT DrawModifier : public virtual AceType { 94 public: 95 DECLARE_ACE_TYPE(DrawModifier, AceType); 96 97 public: 98 DrawModifierFunc drawBehindFunc; 99 DrawModifierFunc drawContentFunc; 100 DrawModifierFunc drawFrontFunc; 101 }; 102 103 template<typename T> 104 class NormalProperty : public PropertyBase { 105 DECLARE_ACE_TYPE(NormalProperty, PropertyBase); 106 107 public: NormalProperty(const T & value)108 explicit NormalProperty(const T& value) : value_(value) {} 109 ~NormalProperty() override = default; 110 111 void SetUpCallbacks(std::function<T()>&& getFunc, std::function<void(const T&)>&& setFunc, 112 std::function<T()>&& getStageFunc = nullptr) 113 { 114 getFunc_ = std::move(getFunc); 115 setFunc_ = std::move(setFunc); 116 getStageFunc_ = std::move(getStageFunc); 117 } 118 Get()119 T Get() 120 { 121 if (getFunc_) { 122 return getFunc_(); 123 } else { 124 return value_; 125 } 126 } 127 Set(const T & value)128 void Set(const T& value) 129 { 130 if (setFunc_) { 131 setFunc_(value); 132 } else { 133 value_ = value; 134 } 135 } 136 GetStagingValue()137 T GetStagingValue() const 138 { 139 if (getStageFunc_) { 140 return getStageFunc_(); 141 } else { 142 return value_; 143 } 144 } 145 SetUpdateCallback(std::function<void (const T &)> && callback)146 void SetUpdateCallback(std::function<void(const T&)>&& callback) 147 { 148 updateCallback_ = std::move(callback); 149 } 150 GetUpdateCallback()151 std::function<void(const T&)> GetUpdateCallback() const 152 { 153 return updateCallback_; 154 } 155 156 private: 157 T value_; 158 std::function<T()> getFunc_; 159 std::function<void(const T&)> setFunc_; 160 std::function<T()> getStageFunc_; 161 std::function<void(const T&)> updateCallback_; 162 ACE_DISALLOW_COPY_AND_MOVE(NormalProperty); 163 }; 164 165 template<typename T> 166 class AnimatableProperty : public NormalProperty<T> { 167 DECLARE_ACE_TYPE(AnimatableProperty, NormalProperty<T>); 168 169 public: AnimatableProperty(const T & value)170 explicit AnimatableProperty(const T& value) : NormalProperty<T>(value) {} 171 ~AnimatableProperty() override = default; 172 private: 173 ACE_DISALLOW_COPY_AND_MOVE(AnimatableProperty); 174 }; 175 176 #define DECLARE_PROP_TYPED_CLASS(classname, template_class, type) \ 177 class classname : public template_class<type> { \ 178 DECLARE_ACE_TYPE(classname, template_class); \ 179 \ 180 public: \ 181 explicit classname(const type& value) : template_class(value) {} \ 182 ~classname() override = default; \ 183 ACE_DISALLOW_COPY_AND_MOVE(classname); \ 184 } 185 186 DECLARE_PROP_TYPED_CLASS(PropertyBool, NormalProperty, bool); 187 DECLARE_PROP_TYPED_CLASS(PropertySizeF, NormalProperty, SizeF); 188 DECLARE_PROP_TYPED_CLASS(PropertyOffsetF, NormalProperty, OffsetF); 189 DECLARE_PROP_TYPED_CLASS(PropertyInt, NormalProperty, int32_t); 190 DECLARE_PROP_TYPED_CLASS(PropertyFloat, NormalProperty, float); 191 DECLARE_PROP_TYPED_CLASS(PropertyString, NormalProperty, std::string); 192 DECLARE_PROP_TYPED_CLASS(PropertyU16String, NormalProperty, std::u16string); 193 DECLARE_PROP_TYPED_CLASS(PropertyColor, NormalProperty, Color); 194 DECLARE_PROP_TYPED_CLASS(PropertyRectF, NormalProperty, RectF); 195 DECLARE_PROP_TYPED_CLASS(PropertyVectorFloat, NormalProperty, LinearVector<float>); 196 DECLARE_PROP_TYPED_CLASS(PropertyCanvasImageModifierWrapper, NormalProperty, CanvasImageModifierWrapper); 197 DECLARE_PROP_TYPED_CLASS(AnimatablePropertyFloat, AnimatableProperty, float); 198 DECLARE_PROP_TYPED_CLASS(AnimatablePropertyUint8, AnimatableProperty, uint8_t); 199 DECLARE_PROP_TYPED_CLASS(AnimatablePropertyColor, AnimatableProperty, LinearColor); 200 DECLARE_PROP_TYPED_CLASS(AnimatablePropertyVectorFloat, AnimatableProperty, LinearVector<float>); 201 DECLARE_PROP_TYPED_CLASS(AnimatablePropertyVectorColor, AnimatableProperty, GradientArithmetic); 202 DECLARE_PROP_TYPED_CLASS(AnimatablePropertyVectorLinearVector, AnimatableProperty, LinearVector<LinearColor>); 203 DECLARE_PROP_TYPED_CLASS(AnimatablePropertyOffsetF, AnimatableProperty, OffsetF); 204 DECLARE_PROP_TYPED_CLASS(AnimatablePropertySizeF, AnimatableProperty, SizeF); 205 DECLARE_PROP_TYPED_CLASS(AnimatableArithmeticProperty, AnimatableProperty, RefPtr<CustomAnimatableArithmetic>); 206 207 class OverlayModifier : public Modifier { 208 DECLARE_ACE_TYPE(OverlayModifier, Modifier); 209 210 public: OverlayModifier()211 OverlayModifier() 212 { 213 changeCount_ = MakeRefPtr<PropertyInt>(0); 214 AttachProperty(changeCount_); 215 }; 216 ~OverlayModifier() override = default; 217 virtual void onDraw(DrawingContext& Context) = 0; 218 void Draw(DrawingContext& Context); 219 AttachProperty(const RefPtr<PropertyBase> & prop)220 void AttachProperty(const RefPtr<PropertyBase>& prop) 221 { 222 attachedProperties_.push_back(prop); 223 } 224 GetAttachedProperties()225 const std::vector<RefPtr<PropertyBase>>& GetAttachedProperties() 226 { 227 return attachedProperties_; 228 } 229 GetBoundsRect()230 const RectF& GetBoundsRect() 231 { 232 return rect_; 233 } 234 SetBoundsRect(const RectF & rect)235 void SetBoundsRect(const RectF& rect) 236 { 237 rect_ = rect; 238 } 239 240 void SetExtensionHandler(const RefPtr<ExtensionHandler>& extensionHandler); 241 SetOverlayChange()242 void SetOverlayChange() 243 { 244 changeCount_->Set(changeCount_->Get() + 1); 245 } 246 247 private: 248 std::vector<RefPtr<PropertyBase>> attachedProperties_; 249 RectF rect_; 250 RefPtr<PropertyInt> changeCount_; 251 ACE_DISALLOW_COPY_AND_MOVE(OverlayModifier); 252 WeakPtr<ExtensionHandler> extensionHandler_; 253 }; 254 255 class ForegroundModifier : public Modifier { 256 DECLARE_ACE_TYPE(ForegroundModifier, Modifier); 257 258 public: ForegroundModifier()259 ForegroundModifier() 260 { 261 changeCount_ = MakeRefPtr<PropertyInt>(0); 262 AttachProperty(changeCount_); 263 }; 264 ~ForegroundModifier() override = default; 265 virtual void onDraw(DrawingContext& Context) = 0; 266 void Draw(DrawingContext& Context); 267 AttachProperty(const RefPtr<PropertyBase> & prop)268 void AttachProperty(const RefPtr<PropertyBase>& prop) 269 { 270 attachedProperties_.push_back(prop); 271 } 272 GetAttachedProperties()273 const std::vector<RefPtr<PropertyBase>>& GetAttachedProperties() const 274 { 275 return attachedProperties_; 276 } 277 GetBoundsRect()278 const RectF& GetBoundsRect() const 279 { 280 return rect_; 281 } 282 SetBoundsRect(const RectF & rect)283 void SetBoundsRect(const RectF& rect) 284 { 285 rect_ = rect; 286 } 287 288 void SetExtensionHandler(const RefPtr<ExtensionHandler>& extensionHandler); 289 SetForegroundChange()290 void SetForegroundChange() 291 { 292 changeCount_->Set(changeCount_->Get() + 1); 293 } 294 295 private: 296 std::vector<RefPtr<PropertyBase>> attachedProperties_; 297 RectF rect_; 298 RefPtr<PropertyInt> changeCount_; 299 ACE_DISALLOW_COPY_AND_MOVE(ForegroundModifier); 300 WeakPtr<ExtensionHandler> extensionHandler_; 301 }; 302 303 class ContentModifier : public Modifier { 304 DECLARE_ACE_TYPE(ContentModifier, Modifier); 305 306 public: ContentModifier()307 ContentModifier() 308 { 309 changeCount_ = MakeRefPtr<PropertyInt>(0); 310 AttachProperty(changeCount_); 311 }; 312 ~ContentModifier() override = default; 313 virtual void onDraw(DrawingContext& Context) = 0; 314 315 void Draw(DrawingContext& Context); 316 AttachProperty(const RefPtr<PropertyBase> & prop)317 void AttachProperty(const RefPtr<PropertyBase>& prop) 318 { 319 attachedProperties_.push_back(prop); 320 } 321 GetAttachedProperties()322 const std::vector<RefPtr<PropertyBase>>& GetAttachedProperties() 323 { 324 return attachedProperties_; 325 } 326 GetBoundsRect()327 const std::optional<RectF>& GetBoundsRect() 328 { 329 return rect_; 330 } 331 SetBoundsRect(const std::optional<RectF> & rect)332 void SetBoundsRect(const std::optional<RectF>& rect) 333 { 334 rect_ = rect; 335 } 336 SetIsCustomFont(bool isCustomFont)337 void SetIsCustomFont(bool isCustomFont) 338 { 339 isCustomFont_ = isCustomFont; 340 } 341 GetIsCustomFont()342 bool GetIsCustomFont() const 343 { 344 return isCustomFont_; 345 } 346 SetContentChange()347 void SetContentChange() 348 { 349 changeCount_->Set(changeCount_->Get() + 1); 350 } 351 352 void SetExtensionHandler(const RefPtr<ExtensionHandler>& extensionHandler); 353 354 private: 355 std::vector<RefPtr<PropertyBase>> attachedProperties_; 356 std::optional<RectF> rect_; 357 bool isCustomFont_ = false; 358 RefPtr<PropertyInt> changeCount_; // use to trigger rerendering 359 WeakPtr<ExtensionHandler> extensionHandler_; 360 361 ACE_DISALLOW_COPY_AND_MOVE(ContentModifier); 362 }; 363 364 class ModifierImpl { 365 }; 366 367 class NodeAnimatablePropertyBase : public AceType { 368 DECLARE_ACE_TYPE(NodeAnimatablePropertyBase, AceType); 369 370 public: 371 NodeAnimatablePropertyBase() = default; 372 ~NodeAnimatablePropertyBase() override = default; 373 GetModifyImpl()374 const std::shared_ptr<ModifierImpl>& GetModifyImpl() const 375 { 376 return modifyImpl_; 377 } 378 SetModifyImpl(const std::shared_ptr<ModifierImpl> & impl)379 void SetModifyImpl(const std::shared_ptr<ModifierImpl>& impl) 380 { 381 modifyImpl_ = impl; 382 } 383 GetProperty()384 const RefPtr<PropertyBase>& GetProperty() const 385 { 386 return property_; 387 } 388 SetProperty(const RefPtr<PropertyBase> & property)389 void SetProperty(const RefPtr<PropertyBase>& property) 390 { 391 property_ = property; 392 } 393 394 private: 395 std::shared_ptr<ModifierImpl> modifyImpl_; 396 RefPtr<PropertyBase> property_; 397 398 ACE_DISALLOW_COPY_AND_MOVE(NodeAnimatablePropertyBase); 399 }; 400 401 using FinishCallback = std::function<void()>; 402 403 template<typename T, typename S> 404 class NodeAnimatableProperty : public NodeAnimatablePropertyBase { 405 DECLARE_ACE_TYPE(NodeAnimatableProperty, NodeAnimatablePropertyBase); 406 407 public: NodeAnimatableProperty(const T & value,std::function<void (const T &)> && updateCallback)408 NodeAnimatableProperty(const T& value, std::function<void(const T&)>&& updateCallback) 409 { 410 auto property = AceType::MakeRefPtr<S>(value); 411 property->SetUpdateCallback(std::move(updateCallback)); 412 SetProperty(property); 413 } 414 ~NodeAnimatableProperty() override = default; 415 Set(const T & value)416 void Set(const T& value) 417 { 418 auto property = AceType::DynamicCast<S>(GetProperty()); 419 if (property) { 420 property->Set(value); 421 } 422 } 423 424 void SetThresholdType(ThresholdType type); 425 426 void SetPropertyUnit(PropertyUnit unit); 427 Get()428 T Get() const 429 { 430 auto property = AceType::DynamicCast<S>(GetProperty()); 431 if (property) { 432 return property->Get(); 433 } 434 return {}; 435 } 436 void AnimateWithVelocity(const AnimationOption& option, T value, T velocity, 437 const FinishCallback& finishCallback); 438 private: 439 ACE_DISALLOW_COPY_AND_MOVE(NodeAnimatableProperty); 440 }; 441 442 using NodeAnimatablePropertyFloat = NodeAnimatableProperty<float, AnimatablePropertyFloat>; 443 using NodeAnimatableArithmeticProperty = 444 NodeAnimatableProperty<RefPtr<CustomAnimatableArithmetic>, AnimatableArithmeticProperty>; 445 } // namespace OHOS::Ace::NG 446 447 #endif // FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_MODIFIER_H 448