From a46130c9e91ed66e02163fd868a9e351f617dbfa Mon Sep 17 00:00:00 2001 From: l00913061 Date: Tue, 10 Jun 2025 22:24:27 +0800 Subject: [PATCH 1/3] arkuicompatible Signed-off-by: l00913061 Change-Id: I89ce4f89a212a0f7ded42666e9e1934b8658dd29 --- .../src/component/arkts/ArkUINativeModule.ts | 6 ++ .../arkui-ohos/src/component/interop.ts | 55 +++++++++++++++++++ .../src/generated/arkoala_api_generated.h | 12 +++- .../native/src/generated/bridge_custom.cc | 27 +++++++++ .../components_ng/base/view_stack_processor.h | 2 +- .../interfaces/native/common/api_impl.cpp | 21 +++++++ .../interface/arkoala_api_generated.h | 14 ++++- .../native/implementation/all_modifiers.cpp | 19 +++++++ 8 files changed, 152 insertions(+), 4 deletions(-) create mode 100644 frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/arkts/ArkUINativeModule.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/arkts/ArkUINativeModule.ts index 86e8c54ae83..68aac4c3937 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/arkts/ArkUINativeModule.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/arkts/ArkUINativeModule.ts @@ -108,4 +108,10 @@ export class ArkUINativeModule { native static _LoadUserView(userClass: string, params: string): Object @ani.unsafe.Direct native static _Hook_onClick0(ptr: KPointer, thisArray: KSerializerBuffer, thisLength: int32): void + @ani.unsafe.Direct + native static _CreateViewStackProcessor(): KPointer + @ani.unsafe.Direct + native static _PopViewStackProcessor(): KPointer + @ani.unsafe.Direct + native static _DeleteViewStackProcessor(ptr: KPointer): void } diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts new file mode 100644 index 00000000000..eb4f00be26d --- /dev/null +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts @@ -0,0 +1,55 @@ +/* + * Copyright (c) 2025 Huawei Device Co., Ltd. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { ArkUINativeModule } from '#components'; +import { KPointer } from '@koalaui/interop'; +import { PeerNode } from '../PeerNode'; +import { int32 } from '@koalaui/common'; +import { NodeAttach } from '@koalaui/runtime'; + +export class CompatiblePeerNode extends PeerNode { + protected constructor(peerPtr: KPointer, id: int32, view: Object, name: string = '', flags: int32 = 0) { + super(peerPtr, id, name, flags); + this.view = view; + } + public view: Object; + public static create(_peerPtr: KPointer, view: Object, flags: int32 = 0) { + const peerId = PeerNode.nextId(); + const _peer = new CompatiblePeerNode(_peerPtr, peerId, view, 'ComponentRoot', flags); + return _peer; + } +} + +export interface CompatibleComponentInfo { + name: string, + component: Object +} + +/** @memo */ +export function ArkUICompatible( + init: () => CompatibleComponentInfo, + update: (instance: Object) => void +): void { + NodeAttach((): CompatiblePeerNode => { + const ptr = ArkUINativeModule._CreateViewStackProcessor(); + const result = init(); + const realComponent = result.component; + const nodePtr = ArkUINativeModule._PopViewStackProcessor(); + ArkUINativeModule._DeleteViewStackProcessor(ptr); + return CompatiblePeerNode.create(nodePtr, realComponent); + }, (node: CompatiblePeerNode) => { + update(node.view); + }); +} diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala/framework/native/src/generated/arkoala_api_generated.h b/frameworks/bridge/arkts_frontend/koala_projects/arkoala/framework/native/src/generated/arkoala_api_generated.h index ab4f4acc034..5093150e539 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala/framework/native/src/generated/arkoala_api_generated.h +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala/framework/native/src/generated/arkoala_api_generated.h @@ -186,6 +186,7 @@ typedef struct InteropObject { #define GENERATED_ARKUI_EXTENDED_NODE_API_VERSION 8 #define GENERATED_ARKUI_NODE_GRAPHICS_API_VERSION 5 #define GENERATED_ARKUI_NODE_MODIFIERS_API_VERSION 6 +#define GENERATED_ARKUI_INTEROP_NODE_API_VERSION 1 #define GENERATED_ARKUI_AUTO_GENERATE_NODE_ID (-2) @@ -237,7 +238,8 @@ enum GENERATED_Ark_APIVariantKind { GENERATED_FULL = 11, GENERATED_GRAPHICS = 12, GENERATED_EXTENDED = 13, - GENERATED_COUNT = GENERATED_EXTENDED + 1 + GENERATED_INTEROP = 15, + GENERATED_COUNT = GENERATED_INTEROP + 1, }; enum Ark_APINodeFlags { @@ -27977,6 +27979,14 @@ typedef struct GENERATED_ArkUIFullNodeAPI { const GENERATED_ArkUIGraphicsAPI* (*getGraphicsAPI)(); } GENERATED_ArkUIFullNodeAPI; +typedef struct GENERATED_ArkUIInteropNodeAPI { + Ark_Int32 version; + Ark_NodeHandle (*createViewStackProcessor)(); + Ark_NodeHandle (*popViewStackProcessor)(); + void (*deleteViewStackProcessor)(Ark_NodeHandle ptr); +} GENERATED_ArkUIInteropNodeAPI; + + #ifndef GENERATED_FOUNDATION_ACE_FRAMEWORKS_CORE_INTERFACES_GENERIC_SERVICE_API_H #define GENERATED_FOUNDATION_ACE_FRAMEWORKS_CORE_INTERFACES_GENERIC_SERVICE_API_H #include diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala/framework/native/src/generated/bridge_custom.cc b/frameworks/bridge/arkts_frontend/koala_projects/arkoala/framework/native/src/generated/bridge_custom.cc index 8b91393da2c..583226b76e1 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala/framework/native/src/generated/bridge_custom.cc +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala/framework/native/src/generated/bridge_custom.cc @@ -41,6 +41,14 @@ const GENERATED_ArkUIExtendedNodeAPI* GetArkUIExtendedNodeAPI() { GENERATED_ARKUI_EXTENDED_NODE_API_VERSION, nullptr)); } +const GENERATED_ArkUIInteropNodeAPI* GetArkUIInteropNodeAPI() +{ + return reinterpret_cast( + GetAnyImpl(static_cast(GENERATED_Ark_APIVariantKind::GENERATED_INTEROP), + GENERATED_ARKUI_INTEROP_NODE_API_VERSION, + nullptr)); +} + CustomDeserializer* DeserializerBase::customDeserializers = nullptr; // TODO: Remove all this. @@ -576,3 +584,22 @@ KVMObjectHandle impl_LoadUserView(KVMContext vm, const KStringPtr& viewClass, co #endif } KOALA_INTEROP_CTX_2(LoadUserView, KVMObjectHandle, KStringPtr, KStringPtr) + +Ark_NativePointer impl_CreateViewStackProcessor() +{ + return GetArkUIInteropNodeAPI()->createViewStackProcessor(); +} +KOALA_INTEROP_DIRECT_0(CreateViewStackProcessor, Ark_NativePointer) + +Ark_NativePointer impl_PopViewStackProcessor() +{ + return GetArkUIInteropNodeAPI()->popViewStackProcessor(); +} +KOALA_INTEROP_DIRECT_0(PopViewStackProcessor, Ark_NativePointer) + +void impl_DeleteViewStackProcessor(Ark_NativePointer ptr) +{ + Ark_NodeHandle ptrCast = (Ark_NodeHandle) ptr; + GetArkUIInteropNodeAPI()->deleteViewStackProcessor(ptrCast); +} +KOALA_INTEROP_DIRECT_V1(DeleteViewStackProcessor, Ark_NativePointer) diff --git a/frameworks/core/components_ng/base/view_stack_processor.h b/frameworks/core/components_ng/base/view_stack_processor.h index cd6f36a89ef..96e69b6ca32 100644 --- a/frameworks/core/components_ng/base/view_stack_processor.h +++ b/frameworks/core/components_ng/base/view_stack_processor.h @@ -597,7 +597,7 @@ private: ACE_DISALLOW_COPY_AND_MOVE(ViewStackProcessor); }; -class ACE_FORCE_EXPORT ScopedViewStackProcessor final { +class ACE_FORCE_EXPORT ScopedViewStackProcessor final : public Referenced { public: ScopedViewStackProcessor(int32_t containerId = OHOS::Ace::INSTANCE_ID_UNDEFINED); ScopedViewStackProcessor(std::unique_ptr& instance, diff --git a/frameworks/core/interfaces/native/common/api_impl.cpp b/frameworks/core/interfaces/native/common/api_impl.cpp index a680d9b9afa..d514814e819 100644 --- a/frameworks/core/interfaces/native/common/api_impl.cpp +++ b/frameworks/core/interfaces/native/common/api_impl.cpp @@ -31,6 +31,27 @@ namespace OHOS::Ace::NG { namespace GeneratedApiImpl { +Ark_NodeHandle CreateViewStackProcessor() +{ + auto pointer = Referenced::MakeRefPtr(); + auto raw = AceType::RawPtr(pointer); + raw->IncRefCount(); + return reinterpret_cast(raw); +} + +Ark_NodeHandle PopViewStackProcessor() +{ + auto node = OHOS::Ace::NG::ViewStackProcessor::GetInstance()->Finish(); + auto pointer = AceType::RawPtr(node); + pointer->IncRefCount(); + return reinterpret_cast(pointer); +} + +void DeleteViewStackProcessor(Ark_NodeHandle pointer) +{ + reinterpret_cast(pointer)->DecRefCount(); +} + void ShowCrash(Ark_CharPtr message) { TAG_LOGE(AceLogTag::ACE_NATIVE_NODE, "Arkoala crash: %{public}s", message); diff --git a/frameworks/core/interfaces/native/generated/interface/arkoala_api_generated.h b/frameworks/core/interfaces/native/generated/interface/arkoala_api_generated.h index 3ab16d30943..a6d34d04f38 100644 --- a/frameworks/core/interfaces/native/generated/interface/arkoala_api_generated.h +++ b/frameworks/core/interfaces/native/generated/interface/arkoala_api_generated.h @@ -186,6 +186,7 @@ typedef struct InteropObject { #define GENERATED_ARKUI_EXTENDED_NODE_API_VERSION 8 #define GENERATED_ARKUI_NODE_GRAPHICS_API_VERSION 5 #define GENERATED_ARKUI_NODE_MODIFIERS_API_VERSION 6 +#define GENERATED_ARKUI_INTEROP_NODE_API_VERSION 1 #define GENERATED_ARKUI_AUTO_GENERATE_NODE_ID (-2) @@ -236,8 +237,9 @@ enum GENERATED_Ark_APIVariantKind { GENERATED_BASIC = 10, GENERATED_FULL = 11, GENERATED_GRAPHICS = 12, - GENERATED_EXTENDED = 13, - GENERATED_COUNT = GENERATED_EXTENDED + 1 + GENERATED_EXTENDED = 13, + GENERATED_INTEROP = 15, + GENERATED_COUNT = GENERATED_INTEROP + 1, }; enum Ark_APINodeFlags { @@ -27979,6 +27981,14 @@ typedef struct GENERATED_ArkUIFullNodeAPI { const GENERATED_ArkUIGraphicsAPI* (*getGraphicsAPI)(); } GENERATED_ArkUIFullNodeAPI; +typedef struct GENERATED_ArkUIInteropNodeAPI { + Ark_Int32 version; + Ark_NodeHandle (*createViewStackProcessor)(); + Ark_NodeHandle (*popViewStackProcessor)(); + void (*deleteViewStackProcessor)(Ark_NodeHandle ptr); +} GENERATED_ArkUIInteropNodeAPI; + + #ifndef GENERATED_FOUNDATION_ACE_FRAMEWORKS_CORE_INTERFACES_GENERIC_SERVICE_API_H #define GENERATED_FOUNDATION_ACE_FRAMEWORKS_CORE_INTERFACES_GENERIC_SERVICE_API_H #include diff --git a/frameworks/core/interfaces/native/implementation/all_modifiers.cpp b/frameworks/core/interfaces/native/implementation/all_modifiers.cpp index 822df00eab5..91a5b78cc1b 100644 --- a/frameworks/core/interfaces/native/implementation/all_modifiers.cpp +++ b/frameworks/core/interfaces/native/implementation/all_modifiers.cpp @@ -73,6 +73,9 @@ namespace GeneratedApiImpl { void SetChildTotalCount(Ark_NodeHandle node, Ark_Int32 totalCount); void ShowCrash(Ark_CharPtr message); void SetCallbackMethod(GENERATED_Ark_APICallbackMethod* method); + Ark_NodeHandle CreateViewStackProcessor(); + Ark_NodeHandle PopViewStackProcessor(); + void DeleteViewStackProcessor(Ark_NodeHandle ptr); } // namespace OHOS::Ace::NG::GeneratedApiImpl namespace GeneratedBridge { @@ -853,6 +856,17 @@ const GENERATED_ArkUIExtendedNodeAPI* GENERATED_GetExtendedAPI() return &extendedNodeAPIImpl; } +const GENERATED_ArkUIInteropNodeAPI* GENERATED_GetINTEROPAPI() +{ + static const GENERATED_ArkUIInteropNodeAPI interopAPIImpl = { + GENERATED_ARKUI_INTEROP_NODE_API_VERSION, // version + OHOS::Ace::NG::GeneratedApiImpl::CreateViewStackProcessor, + OHOS::Ace::NG::GeneratedApiImpl::PopViewStackProcessor, + OHOS::Ace::NG::GeneratedApiImpl::DeleteViewStackProcessor + }; + return &interopAPIImpl; +} + // TODO: remove me! const GENERATED_ArkUIFullNodeAPI* GENERATED_GetFullAPI() { @@ -901,6 +915,11 @@ EXTERN_C IDLIZE_API_EXPORT const OH_AnyAPI* GENERATED_GetArkAnyAPI( return reinterpret_cast(GetServiceAPI()); } break; + case GENERATED_INTEROP: + if (version == GENERATED_ARKUI_INTEROP_NODE_API_VERSION) { + return reinterpret_cast(GENERATED_GetINTEROPAPI()); + } + break; default: break; } -- Gitee From 04edf9d4e67cd5c6e86d9728ca70637f4f6da8ec Mon Sep 17 00:00:00 2001 From: l00913061 Date: Mon, 23 Jun 2025 22:10:50 +0800 Subject: [PATCH 2/3] interopviewstackprocessor Signed-off-by: l00913061 Change-Id: Ia3d9f06fb1f33991079a302f451ab7522c78c43d --- .../arkui-ohos/src/component/interop.ts | 12 ++++---- .../base/view_stack_processor.cpp | 28 +++++++++++++++++++ .../components_ng/base/view_stack_processor.h | 18 +++++++++++- .../interfaces/native/common/api_impl.cpp | 4 +-- 4 files changed, 53 insertions(+), 9 deletions(-) diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts index eb4f00be26d..1d43229a3d6 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts @@ -20,12 +20,12 @@ import { int32 } from '@koalaui/common'; import { NodeAttach } from '@koalaui/runtime'; export class CompatiblePeerNode extends PeerNode { - protected constructor(peerPtr: KPointer, id: int32, view: Object, name: string = '', flags: int32 = 0) { + protected constructor(peerPtr: KPointer, id: int32, view: ESValue, name: string = '', flags: int32 = 0) { super(peerPtr, id, name, flags); this.view = view; } - public view: Object; - public static create(_peerPtr: KPointer, view: Object, flags: int32 = 0) { + public view: ESValue; + public static create(_peerPtr: KPointer, view: ESValue, flags: int32 = 0) { const peerId = PeerNode.nextId(); const _peer = new CompatiblePeerNode(_peerPtr, peerId, view, 'ComponentRoot', flags); return _peer; @@ -34,13 +34,13 @@ export class CompatiblePeerNode extends PeerNode { export interface CompatibleComponentInfo { name: string, - component: Object + component: ESValue } /** @memo */ -export function ArkUICompatible( +export function compatibleComponent( init: () => CompatibleComponentInfo, - update: (instance: Object) => void + update: (instance: ESValue) => void ): void { NodeAttach((): CompatiblePeerNode => { const ptr = ArkUINativeModule._CreateViewStackProcessor(); diff --git a/frameworks/core/components_ng/base/view_stack_processor.cpp b/frameworks/core/components_ng/base/view_stack_processor.cpp index 7b678dada48..3c1249242da 100644 --- a/frameworks/core/components_ng/base/view_stack_processor.cpp +++ b/frameworks/core/components_ng/base/view_stack_processor.cpp @@ -285,4 +285,32 @@ ScopedViewStackProcessor::~ScopedViewStackProcessor() ViewStackProcessor::GetInstance()->SetRebuildContainerId(OHOS::Ace::INSTANCE_ID_UNDEFINED); std::swap(instance_, ViewStackProcessor::instance); } + +void InteropViewStackProcessor::Init(int32_t containerId) +{ + std::swap(instance_, ViewStackProcessor::instance); + ViewStackProcessor::GetInstance()->SetRebuildContainerId(containerId); +} + +void InteropViewStackProcessor::SwapViewStackProcessor(std::unique_ptr& instance) +{ + std::swap(instance, ViewStackProcessor::instance); +} + +InteropViewStackProcessor::InteropViewStackProcessor(int32_t containerId) +{ + Init(containerId); +} + +InteropViewStackProcessor::InteropViewStackProcessor(std::unique_ptr& instance, int32_t containerId) +{ + std::swap(instance_, instance); + Init(containerId); +} + +InteropViewStackProcessor::~InteropViewStackProcessor() +{ + ViewStackProcessor::GetInstance()->SetRebuildContainerId(OHOS::Ace::INSTANCE_ID_UNDEFINED); + std::swap(instance_, ViewStackProcessor::instance); +} } // namespace OHOS::Ace::NG diff --git a/frameworks/core/components_ng/base/view_stack_processor.h b/frameworks/core/components_ng/base/view_stack_processor.h index 96e69b6ca32..d15f1e20f72 100644 --- a/frameworks/core/components_ng/base/view_stack_processor.h +++ b/frameworks/core/components_ng/base/view_stack_processor.h @@ -197,6 +197,7 @@ struct PrebuildCompCmd { class ACE_EXPORT ViewStackProcessor final { public: friend class ScopedViewStackProcessor; + friend class InteropViewStackProcessor; ACE_FORCE_EXPORT static ViewStackProcessor* GetInstance(); ~ViewStackProcessor() = default; @@ -597,7 +598,7 @@ private: ACE_DISALLOW_COPY_AND_MOVE(ViewStackProcessor); }; -class ACE_FORCE_EXPORT ScopedViewStackProcessor final : public Referenced { +class ACE_FORCE_EXPORT ScopedViewStackProcessor final { public: ScopedViewStackProcessor(int32_t containerId = OHOS::Ace::INSTANCE_ID_UNDEFINED); ScopedViewStackProcessor(std::unique_ptr& instance, @@ -611,5 +612,20 @@ private: ACE_DISALLOW_COPY_AND_MOVE(ScopedViewStackProcessor); }; + +class ACE_FORCE_EXPORT InteropViewStackProcessor final : public Referenced { +public: + InteropViewStackProcessor(int32_t containerId = OHOS::Ace::INSTANCE_ID_UNDEFINED); + InteropViewStackProcessor(std::unique_ptr& instance, + int32_t containerId = OHOS::Ace::INSTANCE_ID_UNDEFINED); + ~InteropViewStackProcessor(); + void SwapViewStackProcessor(std::unique_ptr& instance); + +private: + void Init(int32_t containerId); + std::unique_ptr instance_; + + ACE_DISALLOW_COPY_AND_MOVE(InteropViewStackProcessor); +}; } // namespace OHOS::Ace::NG #endif // FOUNDATION_ACE_FRAMEWORKS_CORE_COMPONENTS_NG_BASE_VIEW_STACK_PROCESSOR_H diff --git a/frameworks/core/interfaces/native/common/api_impl.cpp b/frameworks/core/interfaces/native/common/api_impl.cpp index d514814e819..2c5f3c507a0 100644 --- a/frameworks/core/interfaces/native/common/api_impl.cpp +++ b/frameworks/core/interfaces/native/common/api_impl.cpp @@ -33,7 +33,7 @@ namespace OHOS::Ace::NG { namespace GeneratedApiImpl { Ark_NodeHandle CreateViewStackProcessor() { - auto pointer = Referenced::MakeRefPtr(); + auto pointer = Referenced::MakeRefPtr(); auto raw = AceType::RawPtr(pointer); raw->IncRefCount(); return reinterpret_cast(raw); @@ -49,7 +49,7 @@ Ark_NodeHandle PopViewStackProcessor() void DeleteViewStackProcessor(Ark_NodeHandle pointer) { - reinterpret_cast(pointer)->DecRefCount(); + reinterpret_cast(pointer)->DecRefCount(); } void ShowCrash(Ark_CharPtr message) -- Gitee From cf29de73ef13ee9565dde41e9f0d10d06b441407 Mon Sep 17 00:00:00 2001 From: l00913061 Date: Tue, 24 Jun 2025 19:16:26 +0800 Subject: [PATCH 3/3] state Signed-off-by: l00913061 Change-Id: I74087e39ddd0778ffb54859351ec35529957395a --- .../arkui-ohos/src/component/interop.ts | 163 +++++++++++++++++- .../src/stateManagement/base/iBackingValue.ts | 1 + .../stateManagement/base/stateMgmtFactory.ts | 8 + .../decoratorImpl/decoratorConsume.ts | 4 + .../decoratorImpl/decoratorLink.ts | 14 +- .../decoratorImpl/decoratorProp.ts | 34 +++- .../decoratorImpl/decoratorProvide.ts | 30 +++- .../decoratorImpl/decoratorState.ts | 30 +++- .../state_mgmt/files_to_watch.gni | 1 + .../state_mgmt/src/lib/interop/interop.ts | 55 ++++++ .../partial_update/pu_observed_property.ts | 11 ++ .../src/lib/partial_update/pu_view.ts | 17 +- .../state_mgmt/tsconfig.base.json | 1 + 13 files changed, 359 insertions(+), 10 deletions(-) diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts index 1d43229a3d6..2d0ac6e11ad 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/component/interop.ts @@ -13,11 +13,20 @@ * limitations under the License. */ -import { ArkUINativeModule } from '#components'; -import { KPointer } from '@koalaui/interop'; +import { ArkUINativeModule } from '#components' +import { KPointer } from '@koalaui/interop' import { PeerNode } from '../PeerNode'; -import { int32 } from '@koalaui/common'; -import { NodeAttach } from '@koalaui/runtime'; +import { int32 } from '@koalaui/common' +import { NodeAttach } from '@koalaui/runtime' +import { ExtendableComponent } from './extendableComponent' +import { + StateDecoratedVariable, + ProvideDecoratedVariable, + PropDecoratedVariable, + LinkDecoratedVariable, + ConsumeDecoratedVariable, +} from '../stateManagement'; +import { IDecoratedV1Variable } from '../stateManagement/decorator' export class CompatiblePeerNode extends PeerNode { protected constructor(peerPtr: KPointer, id: int32, view: ESValue, name: string = '', flags: int32 = 0) { @@ -37,19 +46,163 @@ export interface CompatibleComponentInfo { component: ESValue } + /** @memo */ export function compatibleComponent( init: () => CompatibleComponentInfo, update: (instance: ESValue) => void ): void { + let firstUpdate: boolean = false; NodeAttach((): CompatiblePeerNode => { + let global = ESValue.getGlobal(); const ptr = ArkUINativeModule._CreateViewStackProcessor(); + openInterop(global); const result = init(); + closeInterop(global); const realComponent = result.component; const nodePtr = ArkUINativeModule._PopViewStackProcessor(); ArkUINativeModule._DeleteViewStackProcessor(ptr); + firstUpdate = true; return CompatiblePeerNode.create(nodePtr, realComponent); }, (node: CompatiblePeerNode) => { - update(node.view); + if (!firstUpdate) { + update(node.view); + } }); } + + +function openInterop(global: ESValue): void { + let openInterop = global.getProperty('openInterop'); + openInterop.invoke(); +} + +function closeInterop(global: ESValue): void { + let closeInterop = global.getProperty('closeInterop'); + closeInterop.invoke(); +} + + +export type CompatibleStateChangeCallback = (value: T) => void; + + +export function getProvideInteropCallback(staticComponent: ExtendableComponent, createState: ESValue, setCallback: ESvalue, component?: ESValue): void { + const callback = (providedPropName: string): Object => { + let provide = staticComponent.findProvide(providedPropName); + if ((provide === null)) { + throw new Error('Cannot find Provide'); + } + let state = provide as ProvideDecoratedVariable; + if (state.getProxy() === undefined) { + let setSource = ((value: Object) => { + state!.set(value); + }); + let fireChangeCallback = () => { + state.fireChange(); + } + let proxy = createState.invoke(ESValue.wrap(state!.get()), ESValue.wrap(setSource), ESValue.wrap(fireChangeCallback)); + state.setProxy(proxy); + let setProxy = ((value: Object) => { + proxy.invokeMethod("set", ESValue.wrap(value)); + }); + state.setProxyValue = setProxy; + let notifyCallback = ((propertyName: string) => { + proxy.invokeMethod("notifyPropertyHasChangedPU"); + }); + state.setNotifyCallback(notifyCallback); + } + return state.getProxy()!.unwrap()! as Object; + } + setCallback.invoke(callback, component); + return; +} + +export function getStateProxy(staticState: IDecoratedV1Variable, createState: ESValue): ESValue { + let source = staticState; + + let isLink = staticState instanceof LinkDecoratedVariable; + let isConsume = staticState instanceof ConsumeDecoratedVariable; + + if (isLink) { + console.log('LinkDecoratedVariable;') + source = (staticState as LinkDecoratedVariable).getSource(); + } else if (isConsume) { + console.log('ConsumeDecoratedVariable;') + source = (staticState as ConsumeDecoratedVariable).getSource(); + } + + let isState = source instanceof StateDecoratedVariable; + let isProvide = source instanceof ProvideDecoratedVariable; + let isProp = source instanceof PropDecoratedVariable; + + if (isState) { + console.log('StateDecoratedVariable;1') + let state = source as StateDecoratedVariable; + console.log('StateDecoratedVariable;2') + if (state.getProxy() === undefined) { + console.log('StateDecoratedVariable;3') + let setSource = ((value: T) => { + state.set(value); + }); + let fireChangeCallback = () => { + state.fireChange(); + } + let proxy = createState.invoke(ESValue.wrap(state!.get()), ESValue.wrap(setSource), ESValue.wrap(fireChangeCallback)); + state.setProxy(proxy); + let setProxyValue = ((value: T) => { + proxy.invokeMethod("set", ESValue.wrap(value)); + }); + state.setProxyValue = setProxyValue; + let notifyCallback = ((propertyName: string) => { + proxy.invokeMethod("notifyPropertyHasChangedPU"); + }); + state.setNotifyCallback(notifyCallback); + } + return state.getProxy()!; + } else if (isProvide) { + console.log('ProvideDecoratedVariable;') + let state = source as ProvideDecoratedVariable; + if (state.getProxy() === undefined) { + let setSource = ((value: T) => { + state.set(value); + }); + let fireChangeCallback = () => { + state.fireChange(); + } + let proxy = createState.invoke(ESValue.wrap(state!.get()), ESValue.wrap(setSource), ESValue.wrap(fireChangeCallback)); + state.setProxy(proxy); + let setProxyValue = ((value: T) => { + proxy.invokeMethod("set", ESValue.wrap(value)); + }); + state.setProxyValue = setProxyValue; + let notifyCallback = ((propertyName: string) => { + proxy.invokeMethod("notifyPropertyHasChangedPU"); + }); + state.setNotifyCallback(notifyCallback); + } + return state.getProxy()!; + } else if (isProp) { + console.log('PropDecoratedVariable;') + let state = source as PropDecoratedVariable; + if (state.getProxy() === undefined) { + let setSource = ((value: T) => { + state.set(value); + }); + let fireChangeCallback = () => { + state.fireChange(); + } + let proxy = createState.invoke(ESValue.wrap(state!.get()), ESValue.wrap(setSource), ESValue.wrap(fireChangeCallback)); + state.setProxy(proxy); + let setProxyValue = ((value: T) => { + proxy.invokeMethod("set", ESValue.wrap(value)); + }); + state.setProxyValue = setProxyValue; + let notifyCallback = ((propertyName: string) => { + proxy.invokeMethod("notifyPropertyHasChangedPU"); + }); + state.setNotifyCallback(notifyCallback); + } + return state.getProxy()!; + } + throw Error('Error getStateProxy.'); +} diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/base/iBackingValue.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/base/iBackingValue.ts index 485d24ef411..67567901dfd 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/base/iBackingValue.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/base/iBackingValue.ts @@ -22,4 +22,5 @@ export interface IBackingValue { get(shouldAddRef: boolean): T; set(newValue: T): boolean; setSilently(newValue: T): void; + fireChange(): void; } diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/base/stateMgmtFactory.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/base/stateMgmtFactory.ts index 55ada3afc0a..2abba4d68c9 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/base/stateMgmtFactory.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/base/stateMgmtFactory.ts @@ -133,6 +133,7 @@ export class __StateMgmtFactoryImpl implements IStateMgmtFactory { const link = new LinkDecoratedVariable( owningView, varName, + source, () => source.get(), (newValue: T) => source.set(newValue), watchFunc @@ -150,6 +151,7 @@ export class __StateMgmtFactoryImpl implements IStateMgmtFactory { const link = new LinkDecoratedVariable( owningView, varName, + source, () => source.get(), (newValue: T) => source.set(newValue), watchFunc @@ -167,6 +169,7 @@ export class __StateMgmtFactoryImpl implements IStateMgmtFactory { const link = new LinkDecoratedVariable( owningView, varName, + source, () => source.get(), (newValue: T) => source.set(newValue), watchFunc @@ -184,6 +187,7 @@ export class __StateMgmtFactoryImpl implements IStateMgmtFactory { const link = new LinkDecoratedVariable( owningView, varName, + source, () => source.get(), (newValue: T) => source.set(newValue), watchFunc @@ -201,6 +205,7 @@ export class __StateMgmtFactoryImpl implements IStateMgmtFactory { const link = new LinkDecoratedVariable( owningView, varName, + source, () => source.get(), (newValue: T) => source.set(newValue), watchFunc @@ -218,6 +223,7 @@ export class __StateMgmtFactoryImpl implements IStateMgmtFactory { const link = new LinkDecoratedVariable( owningView, varName, + source, () => source.get(), (newValue: T) => source.set(newValue), watchFunc @@ -235,6 +241,7 @@ export class __StateMgmtFactoryImpl implements IStateMgmtFactory { const link = new LinkDecoratedVariable( owningView, varName, + source, () => source.get(), (newValue: T) => source.set(newValue), watchFunc @@ -252,6 +259,7 @@ export class __StateMgmtFactoryImpl implements IStateMgmtFactory { const link = new LinkDecoratedVariable( owningView, varName, + source, () => source.get(), (newValue: T) => { /* set do nothing */ diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorConsume.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorConsume.ts index 89bc3b24f54..9e0fb941406 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorConsume.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorConsume.ts @@ -51,4 +51,8 @@ export class ConsumeDecoratedVariable extends DecoratedV1VariableBase impl this.sourceProvide_!.set(newValue); // makeObserved should be called in source } } + + public getSource(): IProvideDecoratedVariable{ + return this.sourceProvide_!; + } } diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorLink.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorLink.ts index b66932ceb3d..8f640773f59 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorLink.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorLink.ts @@ -15,7 +15,7 @@ import { ExtendableComponent } from '../../component/extendableComponent'; import { DecoratedV1VariableBase } from './decoratorBase'; -import { WatchFuncType } from '../decorator'; +import { IDecoratedV1Variable, WatchFuncType } from '../decorator'; import { ILinkDecoratedVariable } from '../decorator'; import { ObserveSingleton } from '../base/observeSingleton'; import { NullableObject } from '../base/types'; @@ -40,6 +40,7 @@ export class LinkDecoratedVariable extends DecoratedV1VariableBase impleme constructor( owningView: ExtendableComponent | null, varName: string, + source: IDecoratedV1Variable, sourceGet: () => T, sourceSet: (newValue: T) => void, watchFunc?: WatchFuncType @@ -49,6 +50,11 @@ export class LinkDecoratedVariable extends DecoratedV1VariableBase impleme this.sourceGet_ = sourceGet; this.sourceSet_ = sourceSet; + if (source instanceof LinkDecoratedVariable) { + this.source_ = source.getSource(); + } else { + this.source_ = source; + } // @Watch // if initial value is object, register so that property changes trigger // @Watch function exec @@ -89,4 +95,10 @@ export class LinkDecoratedVariable extends DecoratedV1VariableBase impleme this.sourceSet_!(newValue); // makeObserved should be called in source } } + + private source_: IDecoratedV1Variable; + + public getSource(): IDecoratedV1Variable { + return this.source_; + } } diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorProp.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorProp.ts index 1edb4bad748..692895af53e 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorProp.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorProp.ts @@ -17,7 +17,7 @@ import { DecoratedV1VariableBase } from './decoratorBase'; import { propDeepCopy } from '@koalaui/common'; import { StateUpdateLoop } from '../base/stateUpdateLoop'; import { ExtendableComponent } from '../../component/extendableComponent'; -import { IPropDecoratedVariable } from '../decorator'; +import { IObservedObject, IPropDecoratedVariable } from '../decorator'; import { WatchFuncType } from '../decorator'; import { IBackingValue } from '../base/iBackingValue'; import { DecoratorBackingValue } from '../base/backingValue'; @@ -25,6 +25,9 @@ import { ObserveSingleton } from '../base/observeSingleton'; import { NullableObject } from '../base/types'; import { StateMgmtConsole } from '../tools/stateMgmtDFX'; import { UIUtils } from '../utils'; +import { CompatibleStateChangeCallback } from '../../component/interop'; +import { StateMgmtTool } from '../tools/arkts/stateMgmtTool'; +import { WatchFunc } from './decoratorWatch'; /** * implementation of V1 @Prop * @@ -82,6 +85,10 @@ export class PropDecoratedVariable extends DecoratedV1VariableBase impleme public set(newValue: T): void { const value = this.__localValue.get(false); if (value !== newValue) { + // for interop + if (typeof this.setProxyValue === 'function') { + this.setProxyValue!(newValue); + } // @Watch // if new value is object, register so that property changes trigger // Watch function exec @@ -122,4 +129,29 @@ export class PropDecoratedVariable extends DecoratedV1VariableBase impleme this.execWatchFuncs(); } } + + private proxy?: ESValue; + + public getProxy(): ESValue | undefined { + return this.proxy; + } + + public setProxy(proxy: ESValue): void { + this.proxy = proxy; + } + + public setProxyValue?: CompatibleStateChangeCallback; + + public setNotifyCallback(callback: WatchFuncType): void { + const func = new WatchFunc(callback); + const id = func.id(); + const value = this.__localValue.get(false); + if (StateMgmtTool.isIObservedObject(value as NullableObject)) { + (value as IObservedObject).addWatchSubscriber(id); + } + } + + public fireChange(): void { + this.__localValue.fireChange(); + } } diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorProvide.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorProvide.ts index 9580b5623c1..d9807d7f60d 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorProvide.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorProvide.ts @@ -15,13 +15,16 @@ import { ExtendableComponent } from '../../component/extendableComponent'; import { DecoratedV1VariableBase } from './decoratorBase'; -import { WatchFuncType } from '../decorator'; +import { IObservedObject, WatchFuncType } from '../decorator'; import { IProvideDecoratedVariable } from '../decorator'; import { IBackingValue } from '../base/iBackingValue'; import { FactoryInternal } from '../base/iFactoryInternal'; import { ObserveSingleton } from '../base/observeSingleton'; import { NullableObject } from '../base/types'; import { UIUtils } from '../utils'; +import { CompatibleStateChangeCallback } from "../../component/interop"; +import { WatchFunc } from "./decoratorWatch"; +import { StateMgmtTool } from "../tools/arkts/stateMgmtTool"; export class ProvideDecoratedVariable extends DecoratedV1VariableBase implements IProvideDecoratedVariable { private readonly provideAlias_: string; @@ -61,4 +64,29 @@ export class ProvideDecoratedVariable extends DecoratedV1VariableBase impl this.execWatchFuncs(); } } + + private proxy?: ESValue; + + public getProxy(): ESValue | undefined { + return this.proxy; + } + + public setProxy(proxy: ESValue): void { + this.proxy = proxy; + } + + public setProxyValue?: CompatibleStateChangeCallback; + + public setNotifyCallback(callback: WatchFuncType): void { + const func = new WatchFunc(callback); + const id = func.id(); + const value = this.backing_.get(false); + if (StateMgmtTool.isIObservedObject(value as NullableObject)) { + (value as IObservedObject).addWatchSubscriber(id); + } + } + + public fireChange(): void { + this.backing_.fireChange(); + } } diff --git a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorState.ts b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorState.ts index 098f12344e1..bd6392bc22f 100644 --- a/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorState.ts +++ b/frameworks/bridge/arkts_frontend/koala_projects/arkoala-arkts/arkui-ohos/src/stateManagement/decoratorImpl/decoratorState.ts @@ -14,7 +14,7 @@ */ import { DecoratedV1VariableBase } from './decoratorBase'; -import { IStateDecoratedVariable, IPropDecoratedVariable, ILinkDecoratedVariable } from '../decorator'; +import { IStateDecoratedVariable, IPropDecoratedVariable, ILinkDecoratedVariable, IObservedObject } from '../decorator'; import { ExtendableComponent } from '../../component/extendableComponent'; import { WatchFuncType, WatchIdType } from '../decorator'; import { IBackingValue } from '../base/iBackingValue'; @@ -26,6 +26,8 @@ import { WatchFunc } from './decoratorWatch'; import { StateMgmtConsole } from '../tools/stateMgmtDFX'; import { NullableObject } from '../base/types'; import { UIUtils } from '../utils'; +import { CompatibleStateChangeCallback } from '../../component/interop'; +import { StateMgmtTool } from '../tools/arkts/stateMgmtTool'; export interface __MkPropReturnType { prop: PropDecoratedVariable; watchId: WatchIdType; @@ -84,6 +86,7 @@ export class StateDecoratedVariable extends DecoratedV1VariableBase implem const link = new LinkDecoratedVariable( null, varName, + this, () => this.get(), (newValue: T) => this.set(newValue) ); @@ -116,4 +119,29 @@ export class StateDecoratedVariable extends DecoratedV1VariableBase implem this._watchFuncs.set(watchThis.id(), watchThis); return { prop: prop, watchId: watchThis.id() }; } + + private proxy?: ESValue; + + public getProxy(): ESValue | undefined { + return this.proxy; + } + + public setProxy(proxy: ESValue): void { + this.proxy = proxy; + } + + public setProxyValue?: CompatibleStateChangeCallback; + + public setNotifyCallback(callback: WatchFuncType): void { + const func = new WatchFunc(callback); + const id = func.id(); + const value = this.backing_.get(false); + if (StateMgmtTool.isIObservedObject(value as NullableObject)) { + (value as IObservedObject).addWatchSubscriber(id); + } + } + + public fireChange(): void { + this.backing_.fireChange(); + } } diff --git a/frameworks/bridge/declarative_frontend/state_mgmt/files_to_watch.gni b/frameworks/bridge/declarative_frontend/state_mgmt/files_to_watch.gni index 63945ae918b..13c8565e5db 100644 --- a/frameworks/bridge/declarative_frontend/state_mgmt/files_to_watch.gni +++ b/frameworks/bridge/declarative_frontend/state_mgmt/files_to_watch.gni @@ -98,5 +98,6 @@ state_mgmt_release_files_to_watch = [ "//foundation/arkui/ace_engine/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/common/gesture_span.ts", "//foundation/arkui/ace_engine/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/common/gesture_span_native.d.ts", "//foundation/arkui/ace_engine/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/interop/interop.ts", + "//foundation/arkui/ace_engine/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/interop/interop_configure.ts", "//foundation/arkui/ace_engine/frameworks/bridge/declarative_frontend/state_mgmt/src/index.ts", ] diff --git a/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/interop/interop.ts b/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/interop/interop.ts index b37a7603913..2d93899bb2c 100644 --- a/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/interop/interop.ts +++ b/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/interop/interop.ts @@ -21,4 +21,59 @@ function isStaticProxy(obj: T): boolean { } return Object.prototype.hasOwnProperty.call(prototype, '_isStaticProxy') && prototype._isStaticProxy === true; +} + +class Subscribe_Interop extends ISinglePropertyChangeSubscriber{ + constructor(callback: () => void) { + super(); + this.notifyInterop = callback; + } + + public id__(): number { + return 0; + } + + public aboutToBeDeleted(owningView?: IPropertySubscriber): void { + return; + } + + public hasChanged() { + + } + + public notifyInterop: () => void + + public syncPeerHasChanged(eventSource : ObservedPropertyAbstractPU) : void { + this.notifyInterop(); + } +} + +type setValue = (value: T) => void; + +function createStateVariable(value: T, callback: setValue, notifyCallback: () => void): ObservedPropertyPU { + const proxy = new ObservedPropertyPU(value, undefined, 'proxy'); + proxy.setInterop = callback; + const subscirbe_Interop = new Subscribe_Interop(notifyCallback); + proxy.addSubscriber(subscirbe_Interop); + return proxy; +} + +function resetViewPUFindProvideInterop(): void { + ViewPU.resetFindInterop(); +} + +function setFindProvideInterop(callback: (providedPropName: string) => any, view?: ViewPU): void { + if (view === undefined) { + ViewPU.findProvideInterop = callback; + } else { + view.findProvideInterop = callback; + } +} + +function openInterop() { + InteropConfigureStateMgmt.instance.openInterop(); +} + +function closeInterop() { + InteropConfigureStateMgmt.instance.closeInterop(); } \ No newline at end of file diff --git a/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/partial_update/pu_observed_property.ts b/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/partial_update/pu_observed_property.ts index 5894b07822c..121250c1060 100644 --- a/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/partial_update/pu_observed_property.ts +++ b/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/partial_update/pu_observed_property.ts @@ -29,6 +29,8 @@ class ObservedPropertyPU extends ObservedPropertyAbstractPU private wrappedValue_: T; + public setInterop?: setValue; + constructor(localInitValue: T, owningView: IPropertySubscriber, propertyName: PropertyInfo) { super(owningView, propertyName); @@ -104,6 +106,10 @@ class ObservedPropertyPU extends ObservedPropertyAbstractPU // undefined, null, simple type: // nothing to subscribe to in case of new value undefined || null || simple type this.wrappedValue_ = newValue; + } else if (InteropConfigureStateMgmt.instance.needsInterop() && + isStaticProxy(newValue) && !(Object.prototype.hasOwnProperty.call(newValue, '_permissibleAddRefDepth'))) { + // for interop + this.wrappedValue_ = newValue; } else if (newValue instanceof SubscribableAbstract) { stateMgmtConsole.propertyAccess(`${this.debugInfo()}: setValueInternal: new value is an SubscribableAbstract, subscribing to it.`); this.wrappedValue_ = newValue; @@ -153,6 +159,11 @@ class ObservedPropertyPU extends ObservedPropertyAbstractPU TrackedObject.notifyObjectValueAssignment(/* old value */ oldValue, /* new value */ this.wrappedValue_, this.notifyPropertyHasChangedPU, this.notifyTrackedObjectPropertyHasChanged, this); + // for interop + if (InteropConfigureStateMgmt.instance.needsInterop() && + this.setInterop !== undefined && typeof this.setInterop === 'function') { + this.setInterop(newValue); + } } } diff --git a/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/partial_update/pu_view.ts b/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/partial_update/pu_view.ts index 047bf712686..6ca1b82d0da 100644 --- a/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/partial_update/pu_view.ts +++ b/frameworks/bridge/declarative_frontend/state_mgmt/src/lib/partial_update/pu_view.ts @@ -596,12 +596,27 @@ abstract class ViewPU extends PUV2ViewBase this.providedVars_.set(providedPropName, store); } + static findProvideInterop?: (providedPropName: string) => any; + + findProvideInterop?: (providedPropName: string) => any; + /* findProvidePU finds @Provided property recursively by traversing ViewPU's towards that of the UI tree root @Component: if 'this' ViewPU has a @Provide('providedPropName') return it, otherwise ask from its parent ViewPU. */ public findProvidePU(providedPropName: string): ObservedPropertyAbstractPU | undefined { - return this.providedVars_.get(providedPropName) || (this.parent_ && this.parent_.findProvidePU(providedPropName)); + return !InteropConfigureStateMgmt.instance.needsInterop() ? + this.providedVars_.get(providedPropName) || (this.parent_ && this.parent_.findProvidePU(providedPropName)) : + // for interop + this.providedVars_.get(providedPropName) || (this.parent_ && this.parent_.findProvidePU(providedPropName)) || + (this.findProvideInterop !== undefined && typeof this.findProvideInterop === 'function' ? this.findProvideInterop(providedPropName) : undefined) || + (ViewPU.findProvideInterop !== undefined && typeof ViewPU.findProvideInterop === 'function' ? ViewPU.findProvideInterop(providedPropName) : undefined); + } + + static resetFindInterop() { + if (typeof ViewPU.findProvideInterop === 'function') { + ViewPU.findProvideInterop = undefined; + } } /** diff --git a/frameworks/bridge/declarative_frontend/state_mgmt/tsconfig.base.json b/frameworks/bridge/declarative_frontend/state_mgmt/tsconfig.base.json index 0a6063f3009..ddee5f9bef2 100644 --- a/frameworks/bridge/declarative_frontend/state_mgmt/tsconfig.base.json +++ b/frameworks/bridge/declarative_frontend/state_mgmt/tsconfig.base.json @@ -108,6 +108,7 @@ // interop "src/lib/interop/interop.ts", + "src/lib/interop/interop_configure.ts", // init "src/index.ts", -- Gitee