• 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 <meta/api/make_callback.h>
17 #include <meta/interface/intf_recyclable.h>
18 
19 #include "instantiating_object_provider.h"
20 
META_BEGIN_NAMESPACE()21 META_BEGIN_NAMESPACE()
22 
23 ObjectProviderBase::~ObjectProviderBase()
24 {
25     SetDataModel(nullptr);
26 }
27 
CreateObject(const DataModelIndex & index)28 IObject::Ptr ObjectProviderBase::CreateObject(const DataModelIndex& index)
29 {
30     if (!index.IsValid() || !model_) {
31         return nullptr;
32     }
33 
34     IObject::Ptr obj;
35     if (auto data = model_->GetModelData(index)) {
36         if (!recyclebin_.empty()) {
37             obj = recyclebin_.back();
38             recyclebin_.pop_back();
39         } else {
40             obj = Construct(data);
41         }
42         if (auto i = interface_cast<IRecyclable>(obj)) {
43             i->ReBuild(data);
44         } else {
45             BindProperties(obj, data);
46         }
47     }
48     return obj;
49 }
50 
DisposeObject(const META_NS::IObject::Ptr & item)51 bool ObjectProviderBase::DisposeObject(const META_NS::IObject::Ptr& item)
52 {
53     if (auto i = interface_cast<IRecyclable>(item)) {
54         i->Dispose();
55     } else if (auto d = interface_cast<IMetadata>(item)) {
56         for (auto&& p : d->GetProperties()) {
57             if (!IsFlagSet(p, ObjectFlagBits::NATIVE)) {
58                 PropertyLock l { p };
59                 l->ResetBind();
60             }
61         }
62     }
63     bool recycle = recyclebin_.size() < CacheHint()->GetValue();
64     if (recycle) {
65         recyclebin_.push_back(item);
66     }
67     return recycle;
68 }
69 
GetObjectCount(const DataModelIndex & index) const70 size_t ObjectProviderBase::GetObjectCount(const DataModelIndex& index) const
71 {
72     return model_ ? model_->GetSize() : 0;
73 }
74 
SetDataModel(const IDataModel::Ptr & model)75 bool ObjectProviderBase::SetDataModel(const IDataModel::Ptr& model)
76 {
77     if (model_) {
78         model_->OnDataAdded()->RemoveHandler(uintptr_t(this));
79         model_->OnDataRemoved()->RemoveHandler(uintptr_t(this));
80         model_->OnDataMoved()->RemoveHandler(uintptr_t(this));
81     }
82     model_ = model;
83     if (model_) {
84         model_->OnDataAdded()->AddHandler(MakeCallback<IOnDataAdded>([this](DataModelIndex base, size_t count) {
85             Invoke<IOnDataAdded>(META_ACCESS_EVENT(OnDataAdded), base, count);
86         }),
87             uintptr_t(this));
88         model_->OnDataRemoved()->AddHandler(MakeCallback<IOnDataRemoved>([this](DataModelIndex base, size_t count) {
89             Invoke<IOnDataRemoved>(META_ACCESS_EVENT(OnDataRemoved), base, count);
90         }),
91             uintptr_t(this));
92         model_->OnDataMoved()->AddHandler(
93             MakeCallback<IOnDataMoved>([this](DataModelIndex from, size_t count, DataModelIndex to) {
94                 Invoke<IOnDataMoved>(META_ACCESS_EVENT(OnDataMoved), from, count, to);
95             }),
96             uintptr_t(this));
97     }
98     return true;
99 }
100 
GetDataModel() const101 IDataModel::Ptr ObjectProviderBase::GetDataModel() const
102 {
103     return model_;
104 }
105 
BindProperties(const IObject::Ptr & object,const IMetadata::Ptr & data) const106 void ObjectProviderBase::BindProperties(const IObject::Ptr& object, const IMetadata::Ptr& data) const
107 {
108     if (auto odata = interface_cast<IMetadata>(object)) {
109         for (auto&& p : data->GetProperties()) {
110             BASE_NS::string name = "Model." + p->GetName();
111             IProperty::Ptr prop = odata->GetProperty(name);
112             if (!prop) {
113                 prop = DuplicatePropertyType(META_NS::GetObjectRegistry(), p, name);
114                 if (prop) {
115                     odata->AddProperty(prop);
116                 }
117             }
118             if (prop) {
119                 PropertyLock l { prop };
120                 l->SetBind(p);
121             }
122         }
123     }
124 }
125 
Construct(const IMetadata::Ptr & data)126 IObject::Ptr ObjectProviderBase::Construct(const IMetadata::Ptr& data)
127 {
128     return nullptr;
129 }
130 
131 META_END_NAMESPACE()
132