18bf80f4bSopenharmony_ci/*
28bf80f4bSopenharmony_ci * Copyright (c) 2024 Huawei Device Co., Ltd.
38bf80f4bSopenharmony_ci * Licensed under the Apache License, Version 2.0 (the "License");
48bf80f4bSopenharmony_ci * you may not use this file except in compliance with the License.
58bf80f4bSopenharmony_ci * You may obtain a copy of the License at
68bf80f4bSopenharmony_ci *
78bf80f4bSopenharmony_ci *     http://www.apache.org/licenses/LICENSE-2.0
88bf80f4bSopenharmony_ci *
98bf80f4bSopenharmony_ci * Unless required by applicable law or agreed to in writing, software
108bf80f4bSopenharmony_ci * distributed under the License is distributed on an "AS IS" BASIS,
118bf80f4bSopenharmony_ci * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
128bf80f4bSopenharmony_ci * See the License for the specific language governing permissions and
138bf80f4bSopenharmony_ci * limitations under the License.
148bf80f4bSopenharmony_ci */
158bf80f4bSopenharmony_ci
168bf80f4bSopenharmony_ci#include "property_animation.h"
178bf80f4bSopenharmony_ci
188bf80f4bSopenharmony_ci#include <meta/api/make_callback.h>
198bf80f4bSopenharmony_ci#include <meta/interface/intf_any.h>
208bf80f4bSopenharmony_ci
218bf80f4bSopenharmony_ciMETA_BEGIN_NAMESPACE()
228bf80f4bSopenharmony_ci
238bf80f4bSopenharmony_cinamespace Internal {
248bf80f4bSopenharmony_ci
258bf80f4bSopenharmony_cibool PropertyAnimation::Build(const IMetadata::Ptr& meta)
268bf80f4bSopenharmony_ci{
278bf80f4bSopenharmony_ci    return Super::Build(meta);
288bf80f4bSopenharmony_ci}
298bf80f4bSopenharmony_ci
308bf80f4bSopenharmony_civoid PropertyAnimation::Step(const IClock::ConstPtr& clock)
318bf80f4bSopenharmony_ci{
328bf80f4bSopenharmony_ci    Super::Step(clock);
338bf80f4bSopenharmony_ci}
348bf80f4bSopenharmony_ci
358bf80f4bSopenharmony_civoid PropertyAnimation::Evaluate()
368bf80f4bSopenharmony_ci{
378bf80f4bSopenharmony_ci    const PropertyAnimationState::EvaluationData data { currentValue_, from_, to_, META_ACCESS_PROPERTY_VALUE(Progress),
388bf80f4bSopenharmony_ci        META_ACCESS_PROPERTY_VALUE(Curve) };
398bf80f4bSopenharmony_ci    if (GetState().EvaluateValue(data) == AnyReturn::SUCCESS) {
408bf80f4bSopenharmony_ci        NotifyChanged();
418bf80f4bSopenharmony_ci    }
428bf80f4bSopenharmony_ci}
438bf80f4bSopenharmony_ci
448bf80f4bSopenharmony_civoid PropertyAnimation::OnPropertyChanged(const TargetProperty& property, const IStackProperty::Ptr& previous)
458bf80f4bSopenharmony_ci{
468bf80f4bSopenharmony_ci    auto me = GetSelf<IModifier>();
478bf80f4bSopenharmony_ci    if (previous) {
488bf80f4bSopenharmony_ci        previous->RemoveModifier(me);
498bf80f4bSopenharmony_ci    }
508bf80f4bSopenharmony_ci    if (property) {
518bf80f4bSopenharmony_ci        property.stack->AddModifier(me);
528bf80f4bSopenharmony_ci    }
538bf80f4bSopenharmony_ci}
548bf80f4bSopenharmony_ci
558bf80f4bSopenharmony_ciEvaluationResult PropertyAnimation::ProcessOnGet(IAny& value)
568bf80f4bSopenharmony_ci{
578bf80f4bSopenharmony_ci    if (currentValue_ && GetState().IsRunning()) {
588bf80f4bSopenharmony_ci        if (auto result = value.CopyFrom(*currentValue_)) {
598bf80f4bSopenharmony_ci            return result == AnyReturn::NOTHING_TO_DO ? EvaluationResult::EVAL_CONTINUE
608bf80f4bSopenharmony_ci                                                      : EvaluationResult::EVAL_VALUE_CHANGED;
618bf80f4bSopenharmony_ci        }
628bf80f4bSopenharmony_ci    }
638bf80f4bSopenharmony_ci
648bf80f4bSopenharmony_ci    return EvaluationResult::EVAL_CONTINUE;
658bf80f4bSopenharmony_ci}
668bf80f4bSopenharmony_ci
678bf80f4bSopenharmony_ciEvaluationResult PropertyAnimation::ProcessOnSet(IAny& value, const IAny& current)
688bf80f4bSopenharmony_ci{
698bf80f4bSopenharmony_ci    if (META_ACCESS_PROPERTY_VALUE(Valid) || META_ACCESS_PROPERTY_VALUE(Enabled)) {
708bf80f4bSopenharmony_ci        from_ = current.Clone();
718bf80f4bSopenharmony_ci        to_ = value.Clone();
728bf80f4bSopenharmony_ci        currentValue_ = current.Clone();
738bf80f4bSopenharmony_ci        auto& state = GetState();
748bf80f4bSopenharmony_ci        // Start animating
758bf80f4bSopenharmony_ci        state.Start();
768bf80f4bSopenharmony_ci        // Temp shared_ptr<IAny> which does not delete our source IAny
778bf80f4bSopenharmony_ci        auto tmp = IAny::Ptr(&value, [](auto*) {});
788bf80f4bSopenharmony_ci        // Evaluate the animation with progress=1.f and pass the value down the property stack
798bf80f4bSopenharmony_ci        PropertyAnimationState::EvaluationData data { tmp, from_, to_, 1.f, META_ACCESS_PROPERTY_VALUE(Curve) };
808bf80f4bSopenharmony_ci        state.EvaluateValue(data);
818bf80f4bSopenharmony_ci    }
828bf80f4bSopenharmony_ci    return EvaluationResult::EVAL_CONTINUE;
838bf80f4bSopenharmony_ci}
848bf80f4bSopenharmony_ci
858bf80f4bSopenharmony_ciAnimationState::AnimationStateParams PropertyAnimation::GetParams()
868bf80f4bSopenharmony_ci{
878bf80f4bSopenharmony_ci    AnimationState::AnimationStateParams params;
888bf80f4bSopenharmony_ci    params.owner = GetSelf<IAnimation>();
898bf80f4bSopenharmony_ci    params.runningProperty = META_ACCESS_PROPERTY(Running);
908bf80f4bSopenharmony_ci    params.progressProperty = META_ACCESS_PROPERTY(Progress);
918bf80f4bSopenharmony_ci    params.totalDuration = META_ACCESS_PROPERTY(TotalDuration);
928bf80f4bSopenharmony_ci    return params;
938bf80f4bSopenharmony_ci}
948bf80f4bSopenharmony_ci
958bf80f4bSopenharmony_ci} // namespace Internal
968bf80f4bSopenharmony_ciMETA_END_NAMESPACE()
97