• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (c) 2021-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 #include "adapter/preview/entrance/ace_container.h"
17 
18 #include <functional>
19 
20 #ifndef ENABLE_ROSEN_BACKEND
21 #include "flutter/lib/ui/ui_dart_state.h"
22 
23 #include "adapter/preview/entrance/dir_asset_provider.h"
24 #include "core/common/flutter/flutter_asset_manager.h"
25 #include "core/common/flutter/flutter_task_executor.h"
26 #else // ENABLE_ROSEN_BACKEND == true
27 #include <ui/rs_surface_node.h>
28 #include <ui/rs_ui_director.h>
29 
30 #include "flutter/lib/ui/ui_dart_state.h"
31 #include "adapter/preview/entrance/rs_dir_asset_provider.h"
32 #include "core/common/rosen/rosen_asset_manager.h"
33 #include "core/common/flutter/flutter_task_executor.h"
34 #endif
35 
36 #include "adapter/preview/entrance/ace_application_info.h"
37 #include "adapter/preview/osal/stage_card_parser.h"
38 #include "base/log/ace_trace.h"
39 #include "base/log/event_report.h"
40 #include "base/log/log.h"
41 #include "base/utils/system_properties.h"
42 #include "base/utils/utils.h"
43 #include "bridge/card_frontend/card_frontend.h"
44 #include "bridge/card_frontend/card_frontend_declarative.h"
45 #include "bridge/card_frontend/form_frontend_declarative.h"
46 #include "bridge/common/utils/engine_helper.h"
47 #include "bridge/declarative_frontend/declarative_frontend.h"
48 #include "bridge/js_frontend/engine/common/js_engine_loader.h"
49 #include "bridge/js_frontend/js_frontend.h"
50 #include "core/common/ace_engine.h"
51 #include "core/common/ace_view.h"
52 #include "core/common/container_scope.h"
53 #include "core/common/platform_bridge.h"
54 #include "core/common/platform_window.h"
55 #include "core/common/text_field_manager.h"
56 #include "core/common/window.h"
57 #include "core/components/theme/app_theme.h"
58 #include "core/components/theme/theme_constants.h"
59 #include "core/components/theme/theme_manager_impl.h"
60 #include "core/components_ng/pattern/text_field/text_field_manager.h"
61 #include "core/components_ng/render/adapter/rosen_window.h"
62 #include "core/components_ng/render/adapter/window_prviewer.h"
63 #include "core/pipeline/base/element.h"
64 #include "core/pipeline/pipeline_context.h"
65 #include "core/pipeline_ng/pipeline_context.h"
66 #include "adapter/ohos/entrance/ace_new_pipe_judgement.h"
67 
68 namespace OHOS::Ace::Platform {
69 namespace {
70 const char LANGUAGE_TAG[] = "language";
71 const char COUNTRY_TAG[] = "countryOrRegion";
72 const char DIRECTION_TAG[] = "dir";
73 const char UNICODE_SETTING_TAG[] = "unicodeSetting";
74 const char LOCALE_DIR_LTR[] = "ltr";
75 const char LOCALE_DIR_RTL[] = "rtl";
76 const char LOCALE_KEY[] = "locale";
77 } // namespace
78 
79 std::once_flag AceContainer::onceFlag_;
80 bool AceContainer::isComponentMode_ = false;
81 
AceContainer(int32_t instanceId,FrontendType type,RefPtr<Context> context)82 AceContainer::AceContainer(int32_t instanceId, FrontendType type, RefPtr<Context> context)
83     : instanceId_(instanceId), messageBridge_(AceType::MakeRefPtr<PlatformBridge>()), type_(type), context_(context)
84 {
85     ThemeConstants::InitDeviceType();
86 
87     auto state = flutter::UIDartState::Current()->GetStateById(instanceId);
88     auto taskExecutor = Referenced::MakeRefPtr<FlutterTaskExecutor>(state->GetTaskRunners());
89     if (type_ != FrontendType::DECLARATIVE_JS && type_ != FrontendType::ETS_CARD) {
90         taskExecutor->InitJsThread();
91     }
92     taskExecutor_ = taskExecutor;
93 }
94 
Initialize()95 void AceContainer::Initialize()
96 {
97     ContainerScope scope(instanceId_);
98     auto stageContext = AceType::DynamicCast<StageContext>(context_);
99     auto faContext = AceType::DynamicCast<FaContext>(context_);
100     bool useNewPipe = true;
101     if (type_ != FrontendType::DECLARATIVE_JS && type_ != FrontendType::ETS_CARD) {
102         useNewPipe = false;
103     } else if (stageContext) {
104         auto appInfo = stageContext->GetAppInfo();
105         CHECK_NULL_VOID(appInfo);
106         auto hapModuleInfo = stageContext->GetHapModuleInfo();
107         CHECK_NULL_VOID(hapModuleInfo);
108         auto compatibleVersion = appInfo->GetMinAPIVersion();
109         auto targetVersion = appInfo->GetTargetAPIVersion();
110         auto releaseType = appInfo->GetApiReleaseType();
111         labelId_ = hapModuleInfo->GetLabelId();
112         bool enablePartialUpdate = hapModuleInfo->GetPartialUpdateFlag();
113         // only app should have menubar, card don't need
114         if (type_ == FrontendType::DECLARATIVE_JS) {
115             installationFree_ = appInfo->IsInstallationFree();
116         }
117         useNewPipe = AceNewPipeJudgement::QueryAceNewPipeEnabledStage("", compatibleVersion, targetVersion,
118             releaseType, !enablePartialUpdate);
119     } else if (faContext) {
120         auto appInfo = faContext->GetAppInfo();
121         CHECK_NULL_VOID(appInfo);
122         auto compatibleVersion = appInfo->GetMinAPIVersion();
123         auto targetVersion = appInfo->GetTargetAPIVersion();
124         auto releaseType = appInfo->GetApiReleaseType();
125         useNewPipe = AceNewPipeJudgement::QueryAceNewPipeEnabledFA("", compatibleVersion, targetVersion, releaseType);
126     }
127     LOGI("Using %{public}s pipeline context ...", (useNewPipe ? "new" : "old"));
128     if (useNewPipe) {
129         SetUseNewPipeline();
130     }
131     if (type_ != FrontendType::DECLARATIVE_JS && type_ != FrontendType::ETS_CARD) {
132         InitializeFrontend();
133     }
134 }
135 
Destroy()136 void AceContainer::Destroy()
137 {
138     ContainerScope scope(instanceId_);
139     LOGI("AceContainer::Destroy begin");
140     if (!pipelineContext_) {
141         LOGE("no context find in %{private}d container", instanceId_);
142         return;
143     }
144     if (!taskExecutor_) {
145         LOGE("no taskExecutor find in %{private}d container", instanceId_);
146         return;
147     }
148     auto weak = AceType::WeakClaim(AceType::RawPtr(pipelineContext_));
149     taskExecutor_->PostTask(
150         [weak]() {
151             auto context = weak.Upgrade();
152             if (context == nullptr) {
153                 LOGE("context is nullptr");
154                 return;
155             }
156             context->Destroy();
157         },
158         TaskExecutor::TaskType::UI);
159 
160     RefPtr<Frontend> frontend;
161     frontend_.Swap(frontend);
162     if (frontend && taskExecutor_) {
163         taskExecutor_->PostTask(
164             [frontend]() {
165                 frontend->UpdateState(Frontend::State::ON_DESTROY);
166                 frontend->Destroy();
167             },
168             TaskExecutor::TaskType::JS);
169     }
170 
171     messageBridge_.Reset();
172     resRegister_.Reset();
173     assetManager_.Reset();
174     pipelineContext_.Reset();
175     aceView_ = nullptr;
176     LOGI("AceContainer::Destroy end");
177 }
178 
DestroyView()179 void AceContainer::DestroyView()
180 {
181     if (aceView_ != nullptr) {
182         delete aceView_;
183         aceView_ = nullptr;
184     }
185 }
186 
InitializeFrontend()187 void AceContainer::InitializeFrontend()
188 {
189     if (type_ == FrontendType::JS) {
190         frontend_ = Frontend::Create();
191         auto jsFrontend = AceType::DynamicCast<JsFrontend>(frontend_);
192         auto jsEngine = Framework::JsEngineLoader::Get().CreateJsEngine(GetInstanceId());
193         EngineHelper::AddEngine(instanceId_, jsEngine);
194         jsFrontend->SetJsEngine(jsEngine);
195         jsFrontend->SetNeedDebugBreakPoint(AceApplicationInfo::GetInstance().IsNeedDebugBreakPoint());
196         jsFrontend->SetDebugVersion(AceApplicationInfo::GetInstance().IsDebugVersion());
197     } else if (type_ == FrontendType::DECLARATIVE_JS) {
198         frontend_ = AceType::MakeRefPtr<DeclarativeFrontend>();
199         auto declarativeFrontend = AceType::DynamicCast<DeclarativeFrontend>(frontend_);
200         auto jsEngine = Framework::JsEngineLoader::GetDeclarative().CreateJsEngine(instanceId_);
201         EngineHelper::AddEngine(instanceId_, jsEngine);
202         declarativeFrontend->SetJsEngine(jsEngine);
203         declarativeFrontend->SetPageProfile(pageProfile_);
204     } else if (type_ == FrontendType::JS_CARD) {
205         AceApplicationInfo::GetInstance().SetCardType();
206         frontend_ = AceType::MakeRefPtr<CardFrontend>();
207     } else if (type_ == FrontendType::ETS_CARD) {
208         frontend_ = AceType::MakeRefPtr<FormFrontendDeclarative>();
209         auto cardFrontend = AceType::DynamicCast<FormFrontendDeclarative>(frontend_);
210         auto jsEngine = Framework::JsEngineLoader::GetDeclarative().CreateJsEngine(instanceId_);
211         EngineHelper::AddEngine(instanceId_, jsEngine);
212         cardFrontend->SetJsEngine(jsEngine);
213         cardFrontend->SetPageProfile(pageProfile_);
214         cardFrontend->SetRunningCardId(0);
215         cardFrontend->SetIsFormRender(true);
216         cardFrontend->SetTaskExecutor(taskExecutor_);
217         SetIsFRSCardContainer(true);
218     } else {
219         LOGE("Frontend type not supported");
220         return;
221     }
222     ACE_DCHECK(frontend_);
223     frontend_->DisallowPopLastPage();
224     frontend_->Initialize(type_, taskExecutor_);
225     if (assetManager_) {
226         frontend_->SetAssetManager(assetManager_);
227     }
228 }
229 
RunNativeEngineLoop()230 void AceContainer::RunNativeEngineLoop()
231 {
232     taskExecutor_->PostTask([frontend = frontend_]() { frontend->RunNativeEngineLoop(); }, TaskExecutor::TaskType::JS);
233 }
234 
InitializeStageAppConfig(const std::string & assetPath,bool formsEnabled)235 void AceContainer::InitializeStageAppConfig(const std::string& assetPath, bool formsEnabled)
236 {
237     auto stageContext = AceType::DynamicCast<StageContext>(context_);
238     CHECK_NULL_VOID(stageContext);
239     auto appInfo = stageContext->GetAppInfo();
240     CHECK_NULL_VOID(appInfo);
241     auto hapModuleInfo = stageContext->GetHapModuleInfo();
242     CHECK_NULL_VOID(hapModuleInfo);
243     if (pipelineContext_) {
244         LOGI("Set MinPlatformVersion to %{public}d", appInfo->GetMinAPIVersion());
245         pipelineContext_->SetMinPlatformVersion(appInfo->GetMinAPIVersion());
246     }
247     auto& bundleName = appInfo->GetBundleName();
248     auto& compileMode = hapModuleInfo->GetCompileMode();
249     auto& moduleName = hapModuleInfo->GetModuleName();
250     bool isBundle = (compileMode != "esmodule");
251     auto declarativeFrontend = AceType::DynamicCast<DeclarativeFrontend>(frontend_);
252     CHECK_NULL_VOID(declarativeFrontend);
253     declarativeFrontend->InitializeModuleSearcher(bundleName, moduleName, assetPath, isBundle);
254 
255     auto formFrontend = AceType::DynamicCast<FormFrontendDeclarative>(frontend_);
256     CHECK_NULL_VOID(formFrontend);
257     formFrontend->SetBundleName(bundleName);
258     formFrontend->SetModuleName(moduleName);
259     formFrontend->SetIsBundle(isBundle);
260 }
261 
SetStageCardConfig(const std::string & pageProfile,const std::string & selectUrl)262 void AceContainer::SetStageCardConfig(const std::string& pageProfile, const std::string& selectUrl)
263 {
264     std::string fullPageProfile = pageProfile + ".json";
265     std::string formConfigs;
266     RefPtr<StageCardParser> stageCardParser = AceType::MakeRefPtr<StageCardParser>();
267     if (!Framework::GetAssetContentImpl(assetManager_, fullPageProfile, formConfigs)) {
268         LOGI("Can not load the form config.");
269         return;
270     }
271     const std::string prefix("./js/");
272     stageCardParser->Parse(formConfigs, prefix + selectUrl);
273     auto cardFront = static_cast<CardFrontend*>(RawPtr(frontend_));
274     if (cardFront) {
275         cardFront->SetFormSrc(selectUrl);
276         cardFront->SetCardWindowConfig(stageCardParser->GetWindowConfig());
277     }
278 }
279 
InitializeCallback()280 void AceContainer::InitializeCallback()
281 {
282     ACE_FUNCTION_TRACE();
283 
284     ACE_DCHECK(aceView_ && taskExecutor_ && pipelineContext_);
285 
286     auto weak = AceType::WeakClaim(AceType::RawPtr(pipelineContext_));
287     auto&& touchEventCallback = [weak, id = instanceId_](
288                                     const TouchEvent& event, const std::function<void()>& ignoreMark) {
289         ContainerScope scope(id);
290         auto context = weak.Upgrade();
291         if (context == nullptr) {
292             LOGE("context is nullptr");
293             return;
294         }
295         context->GetTaskExecutor()->PostTask(
296             [context, event]() { context->OnTouchEvent(event); }, TaskExecutor::TaskType::UI);
297     };
298     aceView_->RegisterTouchEventCallback(touchEventCallback);
299 
300     auto&& keyEventCallback = [weak, id = instanceId_](const KeyEvent& event) {
301         ContainerScope scope(id);
302         auto context = weak.Upgrade();
303         if (context == nullptr) {
304             LOGE("context is nullptr");
305             return false;
306         }
307         bool result = false;
308         context->GetTaskExecutor()->PostSyncTask(
309             [context, event, &result]() { result = context->OnKeyEvent(event); }, TaskExecutor::TaskType::UI);
310         return result;
311     };
312     aceView_->RegisterKeyEventCallback(keyEventCallback);
313 
314     auto&& mouseEventCallback = [weak, id = instanceId_](
315                                     const MouseEvent& event, const std::function<void()>& ignoreMark) {
316         ContainerScope scope(id);
317         auto context = weak.Upgrade();
318         if (context == nullptr) {
319             LOGE("context is nullptr");
320             return;
321         }
322         context->GetTaskExecutor()->PostTask(
323             [context, event]() { context->OnMouseEvent(event); }, TaskExecutor::TaskType::UI);
324     };
325     aceView_->RegisterMouseEventCallback(mouseEventCallback);
326 
327     auto&& axisEventCallback = [weak, id = instanceId_](
328                                    const AxisEvent& event, const std::function<void()>& ignoreMark) {
329         ContainerScope scope(id);
330         auto context = weak.Upgrade();
331         if (context == nullptr) {
332             LOGE("context is nullptr");
333             return;
334         }
335         context->GetTaskExecutor()->PostTask(
336             [context, event]() { context->OnAxisEvent(event); }, TaskExecutor::TaskType::UI);
337     };
338     aceView_->RegisterAxisEventCallback(axisEventCallback);
339 
340     auto&& rotationEventCallback = [weak, id = instanceId_](const RotationEvent& event) {
341         ContainerScope scope(id);
342         auto context = weak.Upgrade();
343         if (context == nullptr) {
344             LOGE("context is nullptr");
345             return false;
346         }
347         bool result = false;
348         context->GetTaskExecutor()->PostSyncTask(
349             [context, event, &result]() { result = context->OnRotationEvent(event); }, TaskExecutor::TaskType::UI);
350         return result;
351     };
352     aceView_->RegisterRotationEventCallback(rotationEventCallback);
353 
354     auto&& cardViewPositionCallback = [weak, instanceId = instanceId_](int id, float offsetX, float offsetY) {
355         ContainerScope scope(instanceId);
356         auto context = AceType::DynamicCast<PipelineContext>(weak.Upgrade());
357         if (context == nullptr) {
358             LOGE("context is nullptr");
359             return;
360         }
361         context->GetTaskExecutor()->PostSyncTask(
362             [context, id, offsetX, offsetY]() { context->SetCardViewPosition(id, offsetX, offsetY); },
363             TaskExecutor::TaskType::UI);
364     };
365     aceView_->RegisterCardViewPositionCallback(cardViewPositionCallback);
366 
367     auto&& cardViewParamsCallback = [weak, id = instanceId_](const std::string& key, bool focus) {
368         ContainerScope scope(id);
369         auto context = AceType::DynamicCast<PipelineContext>(weak.Upgrade());
370         if (context == nullptr) {
371             LOGE("context is nullptr");
372             return;
373         }
374         context->GetTaskExecutor()->PostSyncTask(
375             [context, key, focus]() { context->SetCardViewAccessibilityParams(key, focus); },
376             TaskExecutor::TaskType::UI);
377     };
378     aceView_->RegisterCardViewAccessibilityParamsCallback(cardViewParamsCallback);
379 
380     auto&& viewChangeCallback = [weak, id = instanceId_](int32_t width, int32_t height, WindowSizeChangeReason type) {
381         ContainerScope scope(id);
382         auto context = weak.Upgrade();
383         if (context == nullptr) {
384             LOGE("context is nullptr");
385             return;
386         }
387         ACE_SCOPED_TRACE("ViewChangeCallback(%d, %d)", width, height);
388         context->GetTaskExecutor()->PostTask(
389             [context, width, height, type]() { context->OnSurfaceChanged(width, height, type); },
390             TaskExecutor::TaskType::UI);
391     };
392     aceView_->RegisterViewChangeCallback(viewChangeCallback);
393 
394     auto&& densityChangeCallback = [weak, id = instanceId_](double density) {
395         ContainerScope scope(id);
396         auto context = weak.Upgrade();
397         if (context == nullptr) {
398             LOGE("context is nullptr");
399             return;
400         }
401         ACE_SCOPED_TRACE("DensityChangeCallback(%lf)", density);
402         context->GetTaskExecutor()->PostTask(
403             [context, density]() { context->OnSurfaceDensityChanged(density); }, TaskExecutor::TaskType::UI);
404     };
405     aceView_->RegisterDensityChangeCallback(densityChangeCallback);
406 
407     auto&& systemBarHeightChangeCallback = [weak, id = instanceId_](double statusBar, double navigationBar) {
408         ContainerScope scope(id);
409         auto context = weak.Upgrade();
410         if (context == nullptr) {
411             LOGE("context is nullptr");
412             return;
413         }
414         ACE_SCOPED_TRACE("SystemBarHeightChangeCallback(%lf, %lf)", statusBar, navigationBar);
415         context->GetTaskExecutor()->PostTask(
416             [context, statusBar, navigationBar]() { context->OnSystemBarHeightChanged(statusBar, navigationBar); },
417             TaskExecutor::TaskType::UI);
418     };
419     aceView_->RegisterSystemBarHeightChangeCallback(systemBarHeightChangeCallback);
420 
421     auto&& surfaceDestroyCallback = [weak, id = instanceId_]() {
422         ContainerScope scope(id);
423         auto context = weak.Upgrade();
424         if (context == nullptr) {
425             LOGE("context is nullptr");
426             return;
427         }
428         context->GetTaskExecutor()->PostTask(
429             [context]() { context->OnSurfaceDestroyed(); }, TaskExecutor::TaskType::UI);
430     };
431     aceView_->RegisterSurfaceDestroyCallback(surfaceDestroyCallback);
432 
433     auto&& idleCallback = [weak, id = instanceId_](int64_t deadline) {
434         ContainerScope scope(id);
435         auto context = weak.Upgrade();
436         if (context == nullptr) {
437             LOGE("context is nullptr");
438             return;
439         }
440         context->GetTaskExecutor()->PostTask(
441             [context, deadline]() { context->OnIdle(deadline); }, TaskExecutor::TaskType::UI);
442     };
443     aceView_->RegisterIdleCallback(idleCallback);
444 }
445 
CreateContainer(int32_t instanceId,FrontendType type,const AceRunArgs & runArgs)446 void AceContainer::CreateContainer(int32_t instanceId, FrontendType type, const AceRunArgs& runArgs)
447 {
448     // for ohos container use newPipeline
449     SystemProperties::SetExtSurfaceEnabled(!runArgs.containerSdkPath.empty());
450 
451     auto context = Context::CreateContext(runArgs.projectModel == ProjectModel::STAGE, runArgs.appResourcesPath);
452     auto aceContainer = AceType::MakeRefPtr<AceContainer>(instanceId, type, context);
453     AceEngine::Get().AddContainer(aceContainer->GetInstanceId(), aceContainer);
454     aceContainer->Initialize();
455     ContainerScope scope(instanceId);
456     auto front = aceContainer->GetFrontend();
457     if (front) {
458         front->UpdateState(Frontend::State::ON_CREATE);
459         front->SetJsMessageDispatcher(aceContainer);
460     }
461     auto platMessageBridge = aceContainer->GetMessageBridge();
462     platMessageBridge->SetJsMessageDispatcher(aceContainer);
463 }
464 
DestroyContainer(int32_t instanceId)465 void AceContainer::DestroyContainer(int32_t instanceId)
466 {
467     auto container = AceEngine::Get().GetContainer(instanceId);
468     if (!container) {
469         LOGE("no AceContainer with id %{private}d in AceEngine", instanceId);
470         return;
471     }
472     container->Destroy();
473     // unregister watchdog before stop thread to avoid UI_BLOCK report
474     AceEngine::Get().UnRegisterFromWatchDog(instanceId);
475     auto taskExecutor = container->GetTaskExecutor();
476     if (taskExecutor) {
477         taskExecutor->PostSyncTask([] { LOGI("Wait UI thread..."); }, TaskExecutor::TaskType::UI);
478         taskExecutor->PostSyncTask([] { LOGI("Wait JS thread..."); }, TaskExecutor::TaskType::JS);
479     }
480     container->DestroyView(); // Stop all threads(ui,gpu,io) for current ability.
481     EngineHelper::RemoveEngine(instanceId);
482     AceEngine::Get().RemoveContainer(instanceId);
483 }
484 
RunPage(int32_t instanceId,int32_t pageId,const std::string & url,const std::string & params)485 bool AceContainer::RunPage(int32_t instanceId, int32_t pageId, const std::string& url, const std::string& params)
486 {
487     ACE_FUNCTION_TRACE();
488     auto container = AceEngine::Get().GetContainer(instanceId);
489     if (!container) {
490         return false;
491     }
492 
493     ContainerScope scope(instanceId);
494     auto front = container->GetFrontend();
495     if (front) {
496         auto type = front->GetType();
497         if ((type == FrontendType::JS) || (type == FrontendType::DECLARATIVE_JS) || (type == FrontendType::JS_CARD) ||
498             (type == FrontendType::ETS_CARD)) {
499             front->RunPage(pageId, url, params);
500             return true;
501         } else {
502             LOGE("Frontend type not supported when runpage");
503             EventReport::SendAppStartException(AppStartExcepType::FRONTEND_TYPE_ERR);
504             return false;
505         }
506     }
507     return false;
508 }
509 
UpdateResourceConfiguration(const std::string & jsonStr)510 void AceContainer::UpdateResourceConfiguration(const std::string& jsonStr)
511 {
512     ContainerScope scope(instanceId_);
513     uint32_t updateFlags = 0;
514     auto resConfig = resourceInfo_.GetResourceConfiguration();
515     if (!resConfig.UpdateFromJsonString(jsonStr, updateFlags) || !updateFlags) {
516         return;
517     }
518     resourceInfo_.SetResourceConfiguration(resConfig);
519     if (ResourceConfiguration::TestFlag(updateFlags, ResourceConfiguration::COLOR_MODE_UPDATED_FLAG)) {
520         SystemProperties::SetColorMode(resConfig.GetColorMode());
521         if (frontend_) {
522             frontend_->SetColorMode(resConfig.GetColorMode());
523         }
524     }
525     if (!pipelineContext_) {
526         return;
527     }
528     auto themeManager = pipelineContext_->GetThemeManager();
529     if (!themeManager) {
530         return;
531     }
532     themeManager->UpdateConfig(resConfig);
533     taskExecutor_->PostTask(
534         [weakThemeManager = WeakPtr<ThemeManager>(themeManager), colorScheme = colorScheme_, config = resConfig,
535             weakContext = WeakPtr<PipelineBase>(pipelineContext_)]() {
536             auto themeManager = weakThemeManager.Upgrade();
537             auto context = weakContext.Upgrade();
538             if (!themeManager || !context) {
539                 return;
540             }
541             themeManager->LoadResourceThemes();
542             themeManager->ParseSystemTheme();
543             themeManager->SetColorScheme(colorScheme);
544             context->RefreshRootBgColor();
545             context->UpdateFontWeightScale();
546             context->SetFontScale(config.GetFontRatio());
547         },
548         TaskExecutor::TaskType::UI);
549     if (frontend_) {
550         frontend_->RebuildAllPages();
551     }
552 }
553 
NativeOnConfigurationUpdated(int32_t instanceId)554 void AceContainer::NativeOnConfigurationUpdated(int32_t instanceId)
555 {
556     auto container = GetContainerInstance(instanceId);
557     if (!container) {
558         return;
559     }
560     ContainerScope scope(instanceId);
561     auto front = container->GetFrontend();
562     if (!front) {
563         return;
564     }
565 
566     std::unique_ptr<JsonValue> value = JsonUtil::Create(true);
567     value->Put("fontScale", container->GetResourceConfiguration().GetFontRatio());
568     value->Put("colorMode", SystemProperties::GetColorMode() == ColorMode::LIGHT ? "light" : "dark");
569     auto declarativeFrontend = AceType::DynamicCast<DeclarativeFrontend>(front);
570     if (declarativeFrontend) {
571         container->UpdateResourceConfiguration(value->ToString());
572         declarativeFrontend->OnConfigurationUpdated(value->ToString());
573         return;
574     }
575 
576     std::unique_ptr<JsonValue> localeValue = JsonUtil::Create(false);
577     localeValue->Put(LANGUAGE_TAG, AceApplicationInfo::GetInstance().GetLanguage().c_str());
578     localeValue->Put(COUNTRY_TAG, AceApplicationInfo::GetInstance().GetCountryOrRegion().c_str());
579     localeValue->Put(
580         DIRECTION_TAG, AceApplicationInfo::GetInstance().IsRightToLeft() ? LOCALE_DIR_RTL : LOCALE_DIR_LTR);
581     localeValue->Put(UNICODE_SETTING_TAG, AceApplicationInfo::GetInstance().GetUnicodeSetting().c_str());
582     value->Put(LOCALE_KEY, localeValue);
583     front->OnConfigurationUpdated(value->ToString());
584 }
585 
Dispatch(const std::string & group,std::vector<uint8_t> && data,int32_t id,bool replyToComponent) const586 void AceContainer::Dispatch(
587     const std::string& group, std::vector<uint8_t>&& data, int32_t id, bool replyToComponent) const
588 {}
589 
FetchResponse(const ResponseData responseData,const int32_t callbackId) const590 void AceContainer::FetchResponse(const ResponseData responseData, const int32_t callbackId) const
591 {
592     auto container = AceType::DynamicCast<AceContainer>(AceEngine::Get().GetContainer(0));
593     if (!container) {
594         LOGE("FetchResponse container is null!");
595         return;
596     }
597     ContainerScope scope(instanceId_);
598     auto front = container->GetFrontend();
599     auto type = container->GetType();
600     if (type == FrontendType::JS) {
601         auto jsFrontend = AceType::DynamicCast<JsFrontend>(front);
602         if (jsFrontend) {
603             jsFrontend->TransferJsResponseDataPreview(callbackId, ACTION_SUCCESS, responseData);
604         }
605     } else if (type == FrontendType::DECLARATIVE_JS) {
606         auto declarativeFrontend = AceType::DynamicCast<DeclarativeFrontend>(front);
607         if (declarativeFrontend) {
608             declarativeFrontend->TransferJsResponseDataPreview(callbackId, ACTION_SUCCESS, responseData);
609         }
610     } else {
611         LOGE("Frontend type not supported");
612         return;
613     }
614 }
615 
CallCurlFunction(const RequestData requestData,const int32_t callbackId) const616 void AceContainer::CallCurlFunction(const RequestData requestData, const int32_t callbackId) const
617 {
618     auto container = AceType::DynamicCast<AceContainer>(AceEngine::Get().GetContainer(ACE_INSTANCE_ID));
619     if (!container) {
620         LOGE("CallCurlFunction container is null!");
621         return;
622     }
623 
624     ContainerScope scope(instanceId_);
625     taskExecutor_->PostTask(
626         [container, requestData, callbackId]() mutable {
627             ResponseData responseData;
628             if (FetchManager::GetInstance().Fetch(requestData, callbackId, responseData)) {
629                 container->FetchResponse(responseData, callbackId);
630             }
631         },
632         TaskExecutor::TaskType::BACKGROUND);
633 }
634 
DispatchPluginError(int32_t callbackId,int32_t errorCode,std::string && errorMessage) const635 void AceContainer::DispatchPluginError(int32_t callbackId, int32_t errorCode, std::string&& errorMessage) const
636 {
637     auto front = GetFrontend();
638     if (!front) {
639         LOGE("the front jni is nullptr");
640         return;
641     }
642 
643     ContainerScope scope(instanceId_);
644     taskExecutor_->PostTask(
645         [front, callbackId, errorCode, errorMessage = std::move(errorMessage)]() mutable {
646             front->TransferJsPluginGetError(callbackId, errorCode, std::move(errorMessage));
647         },
648         TaskExecutor::TaskType::BACKGROUND);
649 }
650 
Dump(const std::vector<std::string> & params)651 bool AceContainer::Dump(const std::vector<std::string>& params)
652 {
653     ContainerScope scope(instanceId_);
654     if (aceView_ && aceView_->Dump(params)) {
655         return true;
656     }
657 
658     if (pipelineContext_) {
659         pipelineContext_->Dump(params);
660         return true;
661     }
662     return false;
663 }
664 
AddRouterChangeCallback(int32_t instanceId,const OnRouterChangeCallback & onRouterChangeCallback)665 void AceContainer::AddRouterChangeCallback(int32_t instanceId, const OnRouterChangeCallback& onRouterChangeCallback)
666 {
667     auto container = GetContainerInstance(instanceId);
668     if (!container) {
669         return;
670     }
671     ContainerScope scope(instanceId);
672     if (!container->pipelineContext_) {
673         LOGE("container pipelineContext not init");
674         return;
675     }
676     container->pipelineContext_->AddRouterChangeCallback(onRouterChangeCallback);
677 }
678 
679 #ifndef ENABLE_ROSEN_BACKEND
AddAssetPath(int32_t instanceId,const std::string & packagePath,const std::vector<std::string> & paths)680 void AceContainer::AddAssetPath(
681     int32_t instanceId, const std::string& packagePath, const std::vector<std::string>& paths)
682 {
683     auto container = GetContainerInstance(instanceId);
684     CHECK_NULL_VOID(container);
685 
686     if (!container->assetManager_) {
687         RefPtr<FlutterAssetManager> flutterAssetManager = Referenced::MakeRefPtr<FlutterAssetManager>();
688         container->assetManager_ = flutterAssetManager;
689         if (container->frontend_) {
690             container->frontend_->SetAssetManager(flutterAssetManager);
691         }
692     }
693 
694     for (const auto& path : paths) {
695         LOGD("Current path is: %{private}s", path.c_str());
696         auto dirAssetProvider = AceType::MakeRefPtr<DirAssetProvider>(
697             path, std::make_unique<flutter::DirectoryAssetBundle>(
698                       fml::OpenDirectory(path.c_str(), false, fml::FilePermission::kRead)));
699         container->assetManager_->PushBack(std::move(dirAssetProvider));
700     }
701 }
702 #else
AddAssetPath(int32_t instanceId,const std::string & packagePath,const std::vector<std::string> & paths)703 void AceContainer::AddAssetPath(
704     int32_t instanceId, const std::string& packagePath, const std::vector<std::string>& paths)
705 {
706     auto container = GetContainerInstance(instanceId);
707     CHECK_NULL_VOID(container);
708 
709     if (!container->assetManager_) {
710         RefPtr<RSAssetManager> rsAssetManager = Referenced::MakeRefPtr<RSAssetManager>();
711         container->assetManager_ = rsAssetManager;
712         if (container->frontend_) {
713             container->frontend_->SetAssetManager(rsAssetManager);
714         }
715     }
716 
717     for (const auto& path : paths) {
718         LOGD("Current path is: %{private}s", path.c_str());
719         auto dirAssetProvider = AceType::MakeRefPtr<RSDirAssetProvider>(path);
720         container->assetManager_->PushBack(std::move(dirAssetProvider));
721     }
722 }
723 #endif
724 
SetResourcesPathAndThemeStyle(int32_t instanceId,const std::string & systemResourcesPath,const std::string & appResourcesPath,const int32_t & themeId,const ColorMode & colorMode)725 void AceContainer::SetResourcesPathAndThemeStyle(int32_t instanceId, const std::string& systemResourcesPath,
726     const std::string& appResourcesPath, const int32_t& themeId, const ColorMode& colorMode)
727 {
728     auto container = GetContainerInstance(instanceId);
729     if (!container) {
730         return;
731     }
732     ContainerScope scope(instanceId);
733     auto resConfig = container->resourceInfo_.GetResourceConfiguration();
734     resConfig.SetColorMode(static_cast<OHOS::Ace::ColorMode>(colorMode));
735     container->resourceInfo_.SetResourceConfiguration(resConfig);
736     container->resourceInfo_.SetPackagePath(appResourcesPath);
737     container->resourceInfo_.SetSystemPackagePath(systemResourcesPath);
738     container->resourceInfo_.SetThemeId(themeId);
739 }
740 
UpdateDeviceConfig(const DeviceConfig & deviceConfig)741 void AceContainer::UpdateDeviceConfig(const DeviceConfig& deviceConfig)
742 {
743     ContainerScope scope(instanceId_);
744     SystemProperties::InitDeviceType(deviceConfig.deviceType);
745     SystemProperties::SetDeviceOrientation(deviceConfig.orientation == DeviceOrientation::PORTRAIT ? 0 : 1);
746     SystemProperties::SetResolution(deviceConfig.density);
747     SystemProperties::SetColorMode(deviceConfig.colorMode);
748     auto resConfig = resourceInfo_.GetResourceConfiguration();
749     if (resConfig.GetDeviceType() == deviceConfig.deviceType &&
750         resConfig.GetOrientation() == deviceConfig.orientation && resConfig.GetDensity() == deviceConfig.density &&
751         resConfig.GetColorMode() == deviceConfig.colorMode && resConfig.GetFontRatio() == deviceConfig.fontRatio) {
752         return;
753     } else {
754         resConfig.SetDeviceType(deviceConfig.deviceType);
755         resConfig.SetOrientation(deviceConfig.orientation);
756         resConfig.SetDensity(deviceConfig.density);
757         resConfig.SetColorMode(deviceConfig.colorMode);
758         resConfig.SetFontRatio(deviceConfig.fontRatio);
759         if (frontend_) {
760             frontend_->SetColorMode(deviceConfig.colorMode);
761         }
762     }
763     resourceInfo_.SetResourceConfiguration(resConfig);
764     if (!pipelineContext_) {
765         return;
766     }
767     auto themeManager = pipelineContext_->GetThemeManager();
768     if (!themeManager) {
769         return;
770     }
771     themeManager->UpdateConfig(resConfig);
772     taskExecutor_->PostTask(
773         [weakThemeManager = WeakPtr<ThemeManager>(themeManager), colorScheme = colorScheme_,
774             weakContext = WeakPtr<PipelineBase>(pipelineContext_)]() {
775             auto themeManager = weakThemeManager.Upgrade();
776             auto context = weakContext.Upgrade();
777             if (!themeManager || !context) {
778                 return;
779             }
780             themeManager->LoadResourceThemes();
781             themeManager->ParseSystemTheme();
782             themeManager->SetColorScheme(colorScheme);
783             context->RefreshRootBgColor();
784         },
785         TaskExecutor::TaskType::UI);
786 }
787 
788 #ifndef ENABLE_ROSEN_BACKEND
SetView(FlutterAceView * view,double density,int32_t width,int32_t height)789 void AceContainer::SetView(FlutterAceView* view, double density, int32_t width, int32_t height)
790 {
791     if (view == nullptr) {
792         return;
793     }
794 
795     auto container = AceType::DynamicCast<AceContainer>(AceEngine::Get().GetContainer(view->GetInstanceId()));
796     if (!container) {
797         return;
798     }
799     auto platformWindow = PlatformWindow::Create(view);
800     if (!platformWindow) {
801         LOGE("Create PlatformWindow failed!");
802         return;
803     }
804 
805     std::unique_ptr<Window> window = std::make_unique<Window>(std::move(platformWindow));
806     container->AttachView(std::move(window), view, density, width, height);
807 }
808 #else
SetView(RSAceView * view,double density,int32_t width,int32_t height,SendRenderDataCallback onRender)809 void AceContainer::SetView(
810     RSAceView* view, double density, int32_t width, int32_t height, SendRenderDataCallback onRender)
811 {
812     CHECK_NULL_VOID(view);
813     auto container = AceType::DynamicCast<AceContainer>(AceEngine::Get().GetContainer(view->GetInstanceId()));
814     CHECK_NULL_VOID(container);
815     auto taskExecutor = container->GetTaskExecutor();
816     CHECK_NULL_VOID(taskExecutor);
817     auto rsWindow = new Rosen::Window(onRender);
818     auto window = std::make_unique<NG::RosenWindow>(rsWindow, taskExecutor, view->GetInstanceId());
819     container->AttachView(std::move(window), view, density, width, height, onRender);
820 }
821 #endif
822 
823 #ifndef ENABLE_ROSEN_BACKEND
AttachView(std::unique_ptr<Window> window,FlutterAceView * view,double density,int32_t width,int32_t height)824 void AceContainer::AttachView(
825     std::unique_ptr<Window> window, FlutterAceView* view, double density, int32_t width, int32_t height)
826 {
827     ContainerScope scope(instanceId_);
828     aceView_ = view;
829     auto instanceId = aceView_->GetInstanceId();
830 
831     auto state = flutter::UIDartState::Current()->GetStateById(instanceId);
832     ACE_DCHECK(state != nullptr);
833     auto flutterTaskExecutor = AceType::DynamicCast<FlutterTaskExecutor>(taskExecutor_);
834     flutterTaskExecutor->InitOtherThreads(state->GetTaskRunners());
835     if (type_ == FrontendType::DECLARATIVE_JS) {
836         // For DECLARATIVE_JS frontend display UI in JS thread temporarily.
837         flutterTaskExecutor->InitJsThread(false);
838         InitializeFrontend();
839         auto front = GetFrontend();
840         if (front) {
841             front->UpdateState(Frontend::State::ON_CREATE);
842             front->SetJsMessageDispatcher(AceType::Claim(this));
843         }
844     }
845     resRegister_ = aceView_->GetPlatformResRegister();
846     auto pipelineContext = AceType::MakeRefPtr<PipelineContext>(
847         std::move(window), taskExecutor_, assetManager_, resRegister_, frontend_, instanceId);
848     pipelineContext->SetRootSize(density, width, height);
849     pipelineContext->SetTextFieldManager(AceType::MakeRefPtr<TextFieldManager>());
850     pipelineContext->SetIsRightToLeft(AceApplicationInfo::GetInstance().IsRightToLeft());
851     pipelineContext->SetMessageBridge(messageBridge_);
852     pipelineContext->SetWindowModal(windowModal_);
853     pipelineContext->SetDrawDelegate(aceView_->GetDrawDelegate());
854     pipelineContext->SetIsJsCard(type_ == FrontendType::JS_CARD);
855     pipelineContext_ = pipelineContext;
856     InitializeCallback();
857 
858     ThemeConstants::InitDeviceType();
859     // Only init global resource here, construct theme in UI thread
860     auto themeManager = AceType::MakeRefPtr<ThemeManagerImpl>();
861     if (themeManager) {
862         pipelineContext_->SetThemeManager(themeManager);
863         // Init resource, load theme map.
864         themeManager->InitResource(resourceInfo_);
865         themeManager->LoadSystemTheme(resourceInfo_.GetThemeId());
866         taskExecutor_->PostTask(
867             [themeManager, assetManager = assetManager_, colorScheme = colorScheme_, aceView = aceView_]() {
868                 themeManager->ParseSystemTheme();
869                 themeManager->SetColorScheme(colorScheme);
870                 themeManager->LoadCustomTheme(assetManager);
871                 // get background color from theme
872                 aceView->SetBackgroundColor(themeManager->GetBackgroundColor());
873             },
874             TaskExecutor::TaskType::UI);
875     }
876 
877     auto weak = AceType::WeakClaim(AceType::RawPtr(pipelineContext_));
878     taskExecutor_->PostTask(
879         [weak]() {
880             auto context = weak.Upgrade();
881             if (context == nullptr) {
882                 LOGE("context is nullptr");
883                 return;
884             }
885             context->SetupRootElement();
886         },
887         TaskExecutor::TaskType::UI);
888     aceView_->Launch();
889 
890     frontend_->AttachPipelineContext(pipelineContext_);
891     auto cardFronted = AceType::DynamicCast<CardFrontend>(frontend_);
892     if (cardFronted) {
893         cardFronted->SetDensity(static_cast<double>(density));
894         taskExecutor_->PostTask(
895             [weak, width, height]() {
896                 auto context = weak.Upgrade();
897                 if (context == nullptr) {
898                     LOGE("context is nullptr");
899                     return;
900                 }
901                 context->OnSurfaceChanged(width, height);
902             },
903             TaskExecutor::TaskType::UI);
904     }
905 
906     AceEngine::Get().RegisterToWatchDog(instanceId, taskExecutor_, GetSettings().useUIAsJSThread);
907 }
908 #else
AttachView(std::unique_ptr<Window> window,RSAceView * view,double density,int32_t width,int32_t height,SendRenderDataCallback onRender)909 void AceContainer::AttachView(std::unique_ptr<Window> window, RSAceView* view, double density, int32_t width,
910     int32_t height, SendRenderDataCallback onRender)
911 {
912     ContainerScope scope(instanceId_);
913     aceView_ = view;
914     auto instanceId = aceView_->GetInstanceId();
915 
916     auto state = flutter::UIDartState::Current()->GetStateById(instanceId);
917     ACE_DCHECK(state != nullptr);
918     auto rsTaskExecutor = AceType::DynamicCast<FlutterTaskExecutor>(taskExecutor_);
919     rsTaskExecutor->InitOtherThreads(state->GetTaskRunners());
920     if (type_ == FrontendType::DECLARATIVE_JS || type_ == FrontendType::ETS_CARD) {
921         // For DECLARATIVE_JS frontend display UI in JS thread temporarily.
922         rsTaskExecutor->InitJsThread(false);
923         InitializeFrontend();
924         auto front = GetFrontend();
925         if (front) {
926             front->UpdateState(Frontend::State::ON_CREATE);
927             front->SetJsMessageDispatcher(AceType::Claim(this));
928         }
929     }
930     resRegister_ = aceView_->GetPlatformResRegister();
931     if (useNewPipeline_) {
932         LOGI("New pipeline version creating...");
933         pipelineContext_ = AceType::MakeRefPtr<NG::PipelineContext>(
934             std::move(window), taskExecutor_, assetManager_, resRegister_, frontend_, instanceId);
935         pipelineContext_->SetTextFieldManager(AceType::MakeRefPtr<NG::TextFieldManagerNG>());
936     } else {
937         pipelineContext_ = AceType::MakeRefPtr<PipelineContext>(
938             std::move(window), taskExecutor_, assetManager_, resRegister_, frontend_, instanceId);
939         pipelineContext_->SetTextFieldManager(AceType::MakeRefPtr<TextFieldManager>());
940     }
941     pipelineContext_->SetRootSize(density, width, height);
942     pipelineContext_->SetIsRightToLeft(AceApplicationInfo::GetInstance().IsRightToLeft());
943     pipelineContext_->SetMessageBridge(messageBridge_);
944     pipelineContext_->SetWindowModal(windowModal_);
945     pipelineContext_->SetDrawDelegate(aceView_->GetDrawDelegate());
946     pipelineContext_->SetIsJsCard(type_ == FrontendType::JS_CARD);
947     if (installationFree_ && !isComponentMode_) {
948         LOGD("installationFree:%{public}d, labelId:%{public}d", installationFree_, labelId_);
949         pipelineContext_->SetInstallationFree(installationFree_);
950         pipelineContext_->SetAppLabelId(labelId_);
951     }
952     pipelineContext_->OnShow();
953     InitializeCallback();
954 
955     auto cardFrontend = AceType::DynamicCast<FormFrontendDeclarative>(frontend_);
956     if (cardFrontend) {
957         pipelineContext_->SetIsFormRender(true);
958         cardFrontend->SetLoadCardCallBack(WeakPtr<PipelineBase>(pipelineContext_));
959     }
960 
961     ThemeConstants::InitDeviceType();
962     // Only init global resource here, construct theme in UI thread
963     auto themeManager = AceType::MakeRefPtr<ThemeManagerImpl>();
964     if (themeManager) {
965         pipelineContext_->SetThemeManager(themeManager);
966         // Init resource, load theme map.
967         themeManager->InitResource(resourceInfo_);
968         themeManager->LoadSystemTheme(resourceInfo_.GetThemeId());
969         taskExecutor_->PostTask(
970             [themeManager, assetManager = assetManager_, colorScheme = colorScheme_, aceView = aceView_]() {
971                 themeManager->ParseSystemTheme();
972                 themeManager->SetColorScheme(colorScheme);
973                 themeManager->LoadCustomTheme(assetManager);
974                 // get background color from theme
975                 aceView->SetBackgroundColor(themeManager->GetBackgroundColor());
976             },
977             TaskExecutor::TaskType::UI);
978     }
979 
980     taskExecutor_->PostTask(
981         [pipelineContext = AceType::DynamicCast<PipelineContext>(pipelineContext_), onRender, this]() {
982             CHECK_NULL_VOID(pipelineContext);
983             auto director = Rosen::RSUIDirector::Create();
984             if (director == nullptr) {
985                 return;
986             }
987 
988             struct Rosen::RSSurfaceNodeConfig rsSurfaceNodeConfig = {
989                 .SurfaceNodeName = "preview_surface",
990                 .onRender = onRender,
991             };
992             static auto snode = Rosen::RSSurfaceNode::Create(rsSurfaceNodeConfig);
993             director->SetRSSurfaceNode(snode);
994 
995             auto func = [taskExecutor = taskExecutor_, id = instanceId_](const std::function<void()>& task) {
996                 ContainerScope scope(id);
997                 taskExecutor->PostTask(task, TaskExecutor::TaskType::UI);
998             };
999             director->SetUITaskRunner(func);
1000 
1001             director->Init();
1002             pipelineContext->SetRSUIDirector(director);
1003             LOGI("Init Rosen Backend");
1004         },
1005         TaskExecutor::TaskType::UI);
1006 
1007     auto weak = AceType::WeakClaim(AceType::RawPtr(pipelineContext_));
1008     taskExecutor_->PostTask(
1009         [weak]() {
1010             auto context = weak.Upgrade();
1011             if (context == nullptr) {
1012                 LOGE("context is nullptr");
1013                 return;
1014             }
1015             context->SetupRootElement();
1016         },
1017         TaskExecutor::TaskType::UI);
1018     aceView_->Launch();
1019 
1020     frontend_->AttachPipelineContext(pipelineContext_);
1021     auto cardFronted = AceType::DynamicCast<CardFrontend>(frontend_);
1022     if (cardFronted) {
1023         cardFronted->SetDensity(static_cast<double>(density));
1024         taskExecutor_->PostTask(
1025             [weak, width, height]() {
1026                 auto context = weak.Upgrade();
1027                 if (context == nullptr) {
1028                     LOGE("context is nullptr");
1029                     return;
1030                 }
1031                 context->OnSurfaceChanged(width, height);
1032             },
1033             TaskExecutor::TaskType::UI);
1034     }
1035 
1036     AceEngine::Get().RegisterToWatchDog(instanceId, taskExecutor_, GetSettings().useUIAsJSThread);
1037 }
1038 #endif
1039 
InitDeviceInfo(int32_t instanceId,const AceRunArgs & runArgs)1040 void AceContainer::InitDeviceInfo(int32_t instanceId, const AceRunArgs& runArgs)
1041 {
1042     ContainerScope scope(instanceId);
1043     SystemProperties::InitDeviceInfo(runArgs.deviceWidth, runArgs.deviceHeight,
1044         runArgs.deviceConfig.orientation == DeviceOrientation::PORTRAIT ? 0 : 1, runArgs.deviceConfig.density,
1045         runArgs.isRound);
1046     SystemProperties::InitDeviceType(runArgs.deviceConfig.deviceType);
1047     SystemProperties::SetColorMode(runArgs.deviceConfig.colorMode);
1048     auto container = GetContainerInstance(instanceId);
1049     if (!container) {
1050         LOGE("container is null, AceContainer::InitDeviceInfo failed.");
1051         return;
1052     }
1053     auto config = container->GetResourceConfiguration();
1054     config.SetDeviceType(SystemProperties::GetDeviceType());
1055     config.SetOrientation(SystemProperties::GetDeviceOrientation());
1056     config.SetDensity(runArgs.deviceConfig.density);
1057     config.SetColorMode(runArgs.deviceConfig.colorMode);
1058     config.SetFontRatio(runArgs.deviceConfig.fontRatio);
1059     container->SetResourceConfiguration(config);
1060     isComponentMode_ = runArgs.isComponentMode;
1061 }
1062 
GetContainerInstance(int32_t instanceId)1063 RefPtr<AceContainer> AceContainer::GetContainerInstance(int32_t instanceId)
1064 {
1065     auto container = AceType::DynamicCast<AceContainer>(AceEngine::Get().GetContainer(instanceId));
1066     return container;
1067 }
1068 
LoadDocument(const std::string & url,const std::string & componentName)1069 void AceContainer::LoadDocument(const std::string& url, const std::string& componentName)
1070 {
1071     ContainerScope scope(instanceId_);
1072     if (type_ != FrontendType::DECLARATIVE_JS) {
1073         LOGE("component preview not supported");
1074         return;
1075     }
1076     auto frontend = AceType::DynamicCast<OHOS::Ace::DeclarativeFrontend>(frontend_);
1077     if (!frontend) {
1078         LOGE("frontend is null, AceContainer::LoadDocument failed");
1079         return;
1080     }
1081     auto jsEngine = frontend->GetJsEngine();
1082     if (!jsEngine) {
1083         LOGE("jsEngine is null, AceContainer::LoadDocument failed");
1084         return;
1085     }
1086     taskExecutor_->PostTask(
1087         [front = frontend, componentName, url, jsEngine]() {
1088             front->SetPagePath(url);
1089             jsEngine->ReplaceJSContent(url, componentName);
1090         },
1091         TaskExecutor::TaskType::JS);
1092 }
1093 } // namespace OHOS::Ace::Platform
1094