• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2024 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 "property.h"
17 
18 #include <meta/interface/intf_owner.h>
19 
20 META_BEGIN_NAMESPACE()
21 namespace Internal {
22 
GetName() const23 BASE_NS::string PropertyBase::GetName() const
24 {
25     return name_;
26 }
GetOwner() const27 IOwner::WeakPtr PropertyBase::GetOwner() const
28 {
29     return owner_;
30 }
SetOwner(IOwner::Ptr owner)31 void PropertyBase::SetOwner(IOwner::Ptr owner)
32 {
33     owner_ = owner;
34 }
SetSelf(IProperty::Ptr self)35 void PropertyBase::SetSelf(IProperty::Ptr self)
36 {
37     self_ = self;
38 }
SetValue(const IAny & value)39 AnyReturnValue PropertyBase::SetValue(const IAny& value)
40 {
41     auto res = SetInternalValue(value);
42     if (res == AnyReturn::SUCCESS) {
43         CallOnChanged(false);
44     }
45     return res;
46 }
GetValue() const47 const IAny& PropertyBase::GetValue() const
48 {
49     auto v = GetData();
50     CORE_ASSERT_MSG(v, "Internal any not set");
51     return *v;
52 }
IsCompatible(const TypeId & id) const53 bool PropertyBase::IsCompatible(const TypeId& id) const
54 {
55     auto v = GetData();
56     return v && META_NS::IsCompatible(*v, id);
57 }
GetTypeId() const58 TypeId PropertyBase::GetTypeId() const
59 {
60     auto p = GetData();
61     return p ? p->GetTypeId() : TypeId {};
62 }
EventOnChanged(MetadataQuery q) const63 IEvent::Ptr PropertyBase::EventOnChanged(MetadataQuery q) const
64 {
65     // notice that this requires locking outside unlike the old system
66     // if needed, consider separate locking for the construction
67     if (!onChanged_ && q == MetadataQuery::CONSTRUCT_ON_REQUEST) {
68         onChanged_ = CreateShared<OnChangedEvent>("OnChanged");
69         onChangedAtomic_.store(onChanged_.get());
70     }
71     return onChanged_;
72 }
NotifyChange() const73 void PropertyBase::NotifyChange() const
74 {
75     CallOnChanged(false);
76 }
InvokeOnChanged(const BASE_NS::shared_ptr<OnChangedEvent> & onChanged,const IOwner::WeakPtr & owner) const77 void PropertyBase::InvokeOnChanged(
78     const BASE_NS::shared_ptr<OnChangedEvent>& onChanged, const IOwner::WeakPtr& owner) const
79 {
80     if (auto ow = interface_pointer_cast<IPropertyOwner>(owner)) {
81         ow->OnPropertyChanged(*this);
82     }
83     if (onChanged) {
84         onChanged->Invoke();
85     }
86 }
CallOnChanged(bool forcePending) const87 void PropertyBase::CallOnChanged(bool forcePending) const
88 {
89     bool pending = forcePending || locked_ != 0;
90     SetPendingInvoke(pending);
91     if (!pending) {
92         InvokeOnChanged(onChanged_, owner_);
93     }
94 }
Lock() const95 void PropertyBase::Lock() const
96 {
97     mutex_.lock();
98     ++locked_;
99 }
Unlock() const100 void PropertyBase::Unlock() const
101 {
102     BASE_NS::shared_ptr<OnChangedEvent> invoke;
103     IOwner::WeakPtr owner {};
104     if (--locked_ == 0 && HasPendingInvoke()) {
105         invoke = onChanged_;
106         SetPendingInvoke(false);
107         owner = owner_;
108     }
109     mutex_.unlock();
110     InvokeOnChanged(invoke, owner);
111 }
LockShared() const112 void PropertyBase::LockShared() const
113 {
114     Lock();
115 }
UnlockShared() const116 void PropertyBase::UnlockShared() const
117 {
118     Unlock();
119 }
Attaching(const IAttach::Ptr & target,const IObject::Ptr &)120 bool PropertyBase::Attaching(const IAttach::Ptr& target, const IObject::Ptr&)
121 {
122     owner_ = interface_pointer_cast<IOwner>(target);
123     return true;
124 }
Detaching(const IAttach::Ptr &)125 bool PropertyBase::Detaching(const IAttach::Ptr&)
126 {
127     owner_ = nullptr;
128     return true;
129 }
SetInternalValue(const IAny & value)130 AnyReturnValue PropertyBase::SetInternalValue(const IAny& value)
131 {
132     if (auto& d = GetData()) {
133         if (d.get() == &value) {
134             return AnyReturn::SUCCESS;
135         }
136         return d->CopyFrom(value);
137     }
138     return AnyReturn::FAIL;
139 }
140 
SetInternalAny(IAny::Ptr any)141 AnyReturnValue GenericProperty::SetInternalAny(IAny::Ptr any)
142 {
143     data_ = BASE_NS::move(any);
144     return AnyReturn::SUCCESS;
145 }
GetInternalAny() const146 IAny::Ptr GenericProperty::GetInternalAny() const
147 {
148     return data_;
149 }
150 
151 } // namespace Internal
152 META_END_NAMESPACE()
153