• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2022 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 "core/components_ng/pattern/model/model_view_ng.h"
17 
18 #include "base/geometry/dimension.h"
19 #include "core/components_ng/base/frame_node.h"
20 #include "core/components_ng/base/view_abstract.h"
21 #include "core/components_ng/base/view_stack_processor.h"
22 #include "core/components_ng/pattern/model/model_pattern.h"
23 #include "core/components_v2/inspector/inspector_constants.h"
24 #include "core/pipeline/pipeline_base.h"
25 
26 namespace OHOS::Ace::NG {
27 
ModelViewNG()28 ModelViewNG::ModelViewNG()
29 {
30     const RefPtr<PipelineBase> pipeline = PipelineBase::GetCurrentContext();
31     CHECK_NULL_VOID(pipeline);
32     if (pipeline) {
33         cameraPosition_.SetContextAndCallbacks(pipeline,
34             std::bind(&ModelViewNG::PerformCameraUpdate, this));
35     } else {
36         LOGE("ModelViewNG() pipeline context is null");
37     }
38 }
39 
Create(const std::string & bundleName,const std::string & moduleName,Render3D::SurfaceType surfaceType)40 void ModelViewNG::Create(const std::string& bundleName, const std::string& moduleName,
41     Render3D::SurfaceType surfaceType)
42 {
43     auto* stack = ViewStackProcessor::GetInstance();
44     auto nodeId = stack->ClaimNodeId();
45     static int staticKey = 0;
46 
47     ACE_LAYOUT_SCOPED_TRACE("Create[%s][self:%d]", V2::MODEL_ETS_TAG, nodeId);
48     auto frameNode = FrameNode::GetOrCreateFrameNode(
49         V2::MODEL_ETS_TAG, nodeId, [&nodeId, surfaceType, &bundleName, &moduleName]() {
50             return AceType::MakeRefPtr<ModelPattern>(staticKey++, surfaceType,
51                 bundleName, moduleName);
52         });
53 
54     stack->Push(frameNode);
55     frameNode_ = AceType::WeakClaim(AceType::RawPtr(frameNode));
56 }
57 
SetBackground(const std::string & value)58 void ModelViewNG::SetBackground(const std::string& value)
59 {
60     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelBackground, value);
61 }
62 
SetHandleCameraMove(bool value)63 void ModelViewNG::SetHandleCameraMove(bool value)
64 {
65     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelCameraMove, value);
66 }
67 
SetModelSource(const std::string & value)68 void ModelViewNG::SetModelSource(const std::string& value)
69 {
70     LOGD("MODEL_NG: Model source: %s", value.c_str());
71     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelSource, value);
72 }
73 
SetTransparent(bool value)74 void ModelViewNG::SetTransparent(bool value)
75 {
76     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelTransparent, value);
77 }
78 
SetCameraPosition(AnimatableFloat x,AnimatableFloat y,AnimatableFloat z,AnimatableFloat distance,bool isAngular)79 void ModelViewNG::SetCameraPosition(AnimatableFloat x, AnimatableFloat y, AnimatableFloat z,
80     AnimatableFloat distance, bool isAngular)
81 {
82     if (NearEqual(cameraPosition_.GetDistance().GetValue(), std::numeric_limits<float>::max())) {
83         // Initial update. Set the values directly without the animation if any.
84         cameraPosition_.SetDistance(AnimatableFloat(distance.GetValue()));
85         cameraPosition_.SetPosition(Vec3(x.GetValue(), y.GetValue(), z.GetValue()));
86         ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraDistance, distance);
87         ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraPosition, Vec3(x, y, z));
88     } else {
89         cameraPosition_.SetDistance(distance);
90         cameraPosition_.SetPosition(Vec3(x, y, z));
91     }
92     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraIsAngular, isAngular);
93 }
94 
SetCameraRotation(Quaternion quat)95 void ModelViewNG::SetCameraRotation(Quaternion quat)
96 {
97     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraRotation, quat);
98 }
99 
SetCameraFrustum(float zNear,float zFar,float fovDegrees)100 void ModelViewNG::SetCameraFrustum(float zNear, float zFar, float fovDegrees)
101 {
102     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraZNear, zNear);
103     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraZFar, zFar);
104     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraFOV, fovDegrees);
105 }
106 
SetCameraLookAt(Vec3 lookAtVec)107 void ModelViewNG::SetCameraLookAt(Vec3 lookAtVec)
108 {
109     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraLookAt, lookAtVec);
110 }
111 
SetCameraUp(Vec3 upVec)112 void ModelViewNG::SetCameraUp(Vec3 upVec)
113 {
114     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, CameraUp, upVec);
115 }
116 
AddLight(const RefPtr<ModelLight> & light)117 void ModelViewNG::AddLight(const RefPtr<ModelLight>& light)
118 {
119     if (!light) {
120         LOGE("Add light invalid light");
121         return;
122     }
123 
124     if (lights_.empty()) {
125         // Set the animation callback.
126         RefPtr<PipelineBase> pipeline = PipelineBase::GetCurrentContext();
127         CHECK_NULL_VOID(pipeline);
128         if (pipeline) {
129             light->SetContextAndCallback(pipeline,
130                 std::bind(&ModelViewNG::PerformLightUpdate, this));
131         } else {
132             LOGE("ModelViewNG() pipeline context is null");
133         }
134     }
135 
136     lights_.push_back(light);
137     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelSingleLight, light);
138 }
139 
AddGeometry(const std::shared_ptr<Render3D::Geometry> & shape)140 void ModelViewNG::AddGeometry(const std::shared_ptr<Render3D::Geometry>& shape)
141 {
142     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelSingleGeometry, shape);
143 }
144 
AddGLTFAnimation(const std::shared_ptr<Render3D::GLTFAnimation> & animation)145 void ModelViewNG::AddGLTFAnimation(const std::shared_ptr<Render3D::GLTFAnimation>& animation)
146 {
147     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelSingleAnimation, animation);
148 }
149 
AddCustomRender(const std::shared_ptr<Render3D::CustomRenderDescriptor> & customRender)150 void ModelViewNG::AddCustomRender(const std::shared_ptr<Render3D::CustomRenderDescriptor>& customRender)
151 {
152     if (!customRender) {
153         return;
154     }
155     auto frameNode = frameNode_.Upgrade();
156     if (!frameNode) {
157         LOGE("frameNode is null!");
158         return;
159     }
160 
161     auto paintProperty = frameNode->GetPaintProperty<ModelPaintProperty>();
162     if (!paintProperty) {
163         LOGE("model paint property is null!");
164         return;
165     }
166 
167     const auto curCustomRender = paintProperty->GetModelCustomRenderValue({ });
168     if (!curCustomRender || (curCustomRender->GetUri() != customRender->GetUri())) {
169         ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelCustomRender, customRender);
170     }
171 }
172 
SetWidth(Dimension & width)173 void ModelViewNG::SetWidth(Dimension& width)
174 {
175     if (LessNotEqual(width.Value(), 0.0)) {
176         width.SetValue(0.0);
177     }
178     ViewAbstract::SetWidth(CalcLength(width));
179 }
180 
SetHeight(Dimension & height)181 void ModelViewNG::SetHeight(Dimension& height)
182 {
183     if (LessNotEqual(height.Value(), 0.0)) {
184         height.SetValue(0.0);
185     }
186     ViewAbstract::SetHeight(CalcLength(height));
187 }
188 
SetRenderHeight(Dimension & height)189 void ModelViewNG::SetRenderHeight(Dimension& height)
190 {
191     if (LessNotEqual(height.Value(), 0.0)) {
192         height.SetValue(1.0);
193         LOGE("MODEL_NG: ModelViewNG::SetRenderHeight() heigtScale set default 1.0");
194     }
195     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, RenderHeight, height.Value());
196 }
197 
SetRenderWidth(Dimension & width)198 void ModelViewNG::SetRenderWidth(Dimension& width)
199 {
200     if (LessNotEqual(width.Value(), 0.0)) {
201         width.SetValue(1.0);
202         LOGE("MODEL_NG: ModelViewNG::SetRenderHeight() heigtScale set default 1.0");
203     }
204     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, RenderWidth, width.Value());
205 }
206 
SetRenderFrameRate(float rate)207 void ModelViewNG::SetRenderFrameRate(float rate)
208 {
209     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, RenderFrameRate, rate);
210 }
211 
SetShader(const std::string & path)212 void ModelViewNG::SetShader(const std::string& path)
213 {
214     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ShaderPath, path);
215 }
216 
AddShaderImageTexture(const std::string & path)217 void ModelViewNG::AddShaderImageTexture(const std::string& path)
218 {
219     auto frameNode = frameNode_.Upgrade();
220     if (!frameNode) {
221         LOGE("frameNode is null!");
222         return;
223     }
224 
225     auto paintProperty = frameNode->GetPaintProperty<ModelPaintProperty>();
226     if (!paintProperty) {
227         LOGE("model paint property is null!");
228         return;
229     }
230 
231     const auto& images = paintProperty->GetModelImageTexturePathsValue({ });
232     for (auto& image : images) {
233         if (image == path) {
234             return;
235         }
236     }
237 
238     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelSingleImageTexturePath, path);
239 }
240 
AddShaderInputBuffer(const std::shared_ptr<Render3D::ShaderInputBuffer> & buffer)241 void ModelViewNG::AddShaderInputBuffer(const std::shared_ptr<Render3D::ShaderInputBuffer>& buffer)
242 {
243     ACE_UPDATE_PAINT_PROPERTY(ModelPaintProperty, ModelShaderInputBuffer, buffer);
244 }
245 
PerformCameraUpdate()246 void ModelViewNG::PerformCameraUpdate()
247 {
248     auto frameNode = frameNode_.Upgrade();
249     if (!frameNode) {
250         LOGE("frameNode is null!");
251         return;
252     }
253 
254     auto paintProperty = frameNode->GetPaintProperty<ModelPaintProperty>();
255     if (paintProperty) {
256         paintProperty->UpdateCameraDistance(cameraPosition_.GetDistance());
257         paintProperty->UpdateCameraPosition(cameraPosition_.GetPosition());
258         frameNode->MarkDirtyNode(PROPERTY_UPDATE_RENDER);
259     } else {
260         LOGE("ModelPaintProperty is null");
261     }
262 }
263 
PerformLightUpdate()264 void ModelViewNG::PerformLightUpdate()
265 {
266     auto frameNode = frameNode_.Upgrade();
267     if (!frameNode) {
268         LOGE("frameNode is null!");
269         return;
270     }
271 
272     auto paintProperty = frameNode->GetPaintProperty<ModelPaintProperty>();
273     if (!paintProperty) {
274         LOGE("ModelPaintProperty is null");
275         return;
276     }
277     paintProperty->ModelLightsAnimationUpdate(lights_);
278     frameNode->MarkDirtyNode(PROPERTY_UPDATE_RENDER);
279 }
280 
GetShaderInputBuffer()281 std::optional<std::shared_ptr<Render3D::ShaderInputBuffer>> ModelViewNG::GetShaderInputBuffer()
282 {
283     auto frameNode = frameNode_.Upgrade();
284     if (!frameNode) {
285         LOGE("frameNode is null!");
286         return {};
287     }
288 
289     auto paintProperty = frameNode->GetPaintProperty<ModelPaintProperty>();
290     if (!paintProperty) {
291         LOGE("ModelPaintProperty is null");
292         return {};
293     }
294 
295     return paintProperty->CloneModelShaderInputBuffer();
296 }
297 
298 } // namespace OHOS::Ace::NG
299