Skip to content

Commit

Permalink
增加宏,允许ts不主动持有ueobject
Browse files Browse the repository at this point in the history
  • Loading branch information
Tangxinwei committed Feb 19, 2024
1 parent a94cefc commit de74f97
Show file tree
Hide file tree
Showing 7 changed files with 80 additions and 13 deletions.
3 changes: 3 additions & 0 deletions unreal/Puerts/Content/JavaScript/puerts/uelazyload.js
Original file line number Diff line number Diff line change
Expand Up @@ -122,6 +122,9 @@ var global = global || (function () { return this; }());

let rawmakeclass = global.__tgjsMakeUClass
global.__tgjsMakeUClass = undefined;

puerts.SetJsTakeRef = global.__tgjsSetJsTakeRef
global.__tgjsSetJsTakeRef = undefined

function defaultUeConstructor(){};

Expand Down
10 changes: 10 additions & 0 deletions unreal/Puerts/Source/JsEnv/JsEnv.Build.cs
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,16 @@ public JsEnv(ReadOnlyTargetRules Target) : base(Target)
PublicDefinitions.Add("PUERTS_FORCE_CPP_UFUNCTION=0");
}

bool bTsKeepReference = true;
if(bTsKeepReference)
{
PublicDefinitions.Add("PUERTS_TS_KEEP_REFERENCE=1");
}
else
{
PublicDefinitions.Add("PUERTS_TS_KEEP_REFERENCE=0");
}

bool UseWasm = false;
if (UseWasm)
{
Expand Down
68 changes: 56 additions & 12 deletions unreal/Puerts/Source/JsEnv/Private/JsEnvImpl.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -498,6 +498,8 @@ FJsEnvImpl::FJsEnvImpl(std::shared_ptr<IJSModuleLoader> InModuleLoader, std::sha

MethodBindingHelper<&FJsEnvImpl::NewObjectByClass>::Bind(Isolate, Context, Global, "__tgjsNewObject", This);

MethodBindingHelper<&FJsEnvImpl::SetJsTakeRefInTs>::Bind(Isolate, Context, Global, "__tgjsSetJsTakeRef", This);

MethodBindingHelper<&FJsEnvImpl::NewStructByScriptStruct>::Bind(Isolate, Context, Global, "__tgjsNewStruct", This);

#if !defined(ENGINE_INDEPENDENT_JSENV)
Expand Down Expand Up @@ -1032,7 +1034,7 @@ void FJsEnvImpl::NewObjectByClass(const v8::FunctionCallbackInfo<v8::Value>& Inf

if (Class)
{
if (Info.Length() > 1)
if (Info.Length() > 1 && !Info[1]->IsNullOrUndefined())
{
Outer = FV8Utils::GetUObject(Context, Info[1]);
if (FV8Utils::IsReleasedPtr(Outer))
Expand All @@ -1041,17 +1043,37 @@ void FJsEnvImpl::NewObjectByClass(const v8::FunctionCallbackInfo<v8::Value>& Inf
return;
}
}
if (Info.Length() > 2)
if (Info.Length() > 2 && !Info[2]->IsNullOrUndefined())
{
Name = FName(*FV8Utils::ToFString(Isolate, Info[2]));
}
if (Info.Length() > 3)
if (Info.Length() > 3 && !Info[3]->IsNullOrUndefined())
{
ObjectFlags = (EObjectFlags) (Info[3]->Int32Value(Context).ToChecked());
}
UObject* Object = NewObject<UObject>(Outer, Class, Name, ObjectFlags);

auto Result = FV8Utils::IsolateData<IObjectMapper>(Isolate)->FindOrAdd(Isolate, Context, Object->GetClass(), Object);
bool NeedJsTakeRef = true;
if (Info.Length() > 4 && !Info[4]->IsNullOrUndefined())
{
if (Info[4]->BooleanValue(Isolate))
{

}
else
{
NeedJsTakeRef = false;
}
}
#if PUERTS_TS_KEEP_REFERENCE
#else
if (NeedJsTakeRef) {
bool Existed;
auto TemplateInfoPtr = GetTemplateInfoOfType(Class, Existed);
SetJsTakeRef(Object,static_cast<FClassWrapper*>(TemplateInfoPtr->StructWrapper.get()));
}
#endif
Info.GetReturnValue().Set(Result);
}
else
Expand Down Expand Up @@ -1683,22 +1705,31 @@ bool FJsEnvImpl::IsTypeScriptGeneratedClass(UClass* Class)
void FJsEnvImpl::Bind(FClassWrapper* ClassWrapper, UObject* UEObject,
v8::Local<v8::Object> JSObject) // Just call in FClassReflection::Call, new a Object
{
if (!ClassWrapper->IsNativeTakeJsRef)
{
UserObjectRetainer.Retain(UEObject);
}
#if PUERTS_TS_KEEP_REFERENCE
const bool IsNativeTakeJsRef = ClassWrapper->IsNativeTakeJsRef;
#else
const bool ClassWrapperIsNativeTakeJsRef = ClassWrapper->IsNativeTakeJsRef; //这个值只有mixin会进行设置
const bool IsAsset = UEObject->HasAnyFlags(RF_DefaultSubObject | RF_ClassDefaultObject | RF_ArchetypeObject) || UEObject->IsAsset();
const bool IsUClass = UEObject->IsA<UClass>();
const bool IsNativeTakeJsRef = (IsAsset || IsUClass) ? false : ClassWrapperIsNativeTakeJsRef;
#endif

DataTransfer::SetPointer(MainIsolate, JSObject, UEObject, 0);
DataTransfer::SetPointer(MainIsolate, JSObject, nullptr, 1);
ObjectMap.Emplace(UEObject, v8::UniquePersistent<v8::Value>(MainIsolate, JSObject));

if (!ClassWrapper->IsNativeTakeJsRef)
if (!IsNativeTakeJsRef)
{
ObjectMap[UEObject].SetWeak<UClass>(
(UClass*) ClassWrapper->Struct.Get(), FClassWrapper::OnGarbageCollected, v8::WeakCallbackType::kInternalFields);
SetJsTakeRef(UEObject, ClassWrapper);
}
}

void FJsEnvImpl::SetJsTakeRef(UObject* UEObject, FClassWrapper* ClassWrapper)
{
UserObjectRetainer.Retain(UEObject);
ObjectMap[UEObject].SetWeak<UClass>(Cast<UClass>(ClassWrapper->Struct.Get()), FClassWrapper::OnGarbageCollected, v8::WeakCallbackType::kInternalFields);
}

void FJsEnvImpl::UnBind(UClass* Class, UObject* UEObject, bool ResetPointer)
{
auto PersistentValuePtr = ObjectMap.Find(UEObject);
Expand Down Expand Up @@ -3012,9 +3043,9 @@ FJsEnvImpl::FTemplateInfo* FJsEnvImpl::GetTemplateInfoOfType(UStruct* InStruct,
.ToLocalChecked());
#endif
}

#if PUERTS_TS_KEEP_REFERENCE
StructWrapper->IsNativeTakeJsRef = StructWrapper->IsTypeScriptGeneratedClass = IsTypeScriptGeneratedClass(Class);

#endif
auto SuperClass = Class->GetSuperClass();
if (SuperClass)
{
Expand Down Expand Up @@ -3286,6 +3317,19 @@ void FJsEnvImpl::UEClassToJSClass(const v8::FunctionCallbackInfo<v8::Value>& Inf
}
}

void FJsEnvImpl::SetJsTakeRefInTs(const v8::FunctionCallbackInfo<v8::Value>& Info)
{
v8::Isolate* Isolate = Info.GetIsolate();
v8::Local<v8::Context> Context = Isolate->GetCurrentContext();
CHECK_V8_ARGS(EArgObject);

UObject* Object = FV8Utils::GetUObject(Context, Info[0]);

bool Existed;
auto TemplateInfoPtr = GetTemplateInfoOfType(Object->GetClass(), Existed);
SetJsTakeRef(Object, static_cast<FClassWrapper*>(TemplateInfoPtr->StructWrapper.get()));
}

bool FJsEnvImpl::GetContainerTypeProperty(v8::Local<v8::Context> Context, v8::Local<v8::Value> Value, PropertyMacro** PropertyPtr)
{
if (Value->IsInt32())
Expand Down
4 changes: 4 additions & 0 deletions unreal/Puerts/Source/JsEnv/Private/JsEnvImpl.h
Original file line number Diff line number Diff line change
Expand Up @@ -134,6 +134,8 @@ class FJsEnvImpl : public IJsEnv, IObjectMapper, public FUObjectArray::FUObjectD

public:
bool IsTypeScriptGeneratedClass(UClass* Class);

void SetJsTakeRef(UObject* UEObject, FClassWrapper* ClassWrapper);

virtual void Bind(FClassWrapper* ClassWrapper, UObject* UEObject, v8::Local<v8::Object> JSObject) override;

Expand Down Expand Up @@ -281,6 +283,8 @@ class FJsEnvImpl : public IJsEnv, IObjectMapper, public FUObjectArray::FUObjectD

void UEClassToJSClass(const v8::FunctionCallbackInfo<v8::Value>& Info);

void SetJsTakeRefInTs(const v8::FunctionCallbackInfo<v8::Value>& Info);

bool GetContainerTypeProperty(v8::Local<v8::Context> Context, v8::Local<v8::Value> Value, PropertyMacro** PropertyPtr);

void NewContainer(const v8::FunctionCallbackInfo<v8::Value>& Info);
Expand Down
4 changes: 4 additions & 0 deletions unreal/Puerts/Source/JsEnv/Private/StructWrapper.h
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,11 @@ class FStructWrapper

TWeakObjectPtr<UStruct> Struct;

#if PUERTS_TS_KEEP_REFERENCE
bool IsNativeTakeJsRef = false;
#else
bool IsNativeTakeJsRef = true;
#endif

bool IsTypeScriptGeneratedClass = false;

Expand Down
2 changes: 2 additions & 0 deletions unreal/Puerts/Typing/puerts/index.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -89,4 +89,6 @@ declare module "puerts" {
} & T
function $async<T>(x: T) : AsyncObject<T>;*/

function SetJsTakeRef(object : Object) : void;
}
2 changes: 1 addition & 1 deletion unreal/Puerts/Typing/ue/puerts.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -122,7 +122,7 @@ declare module "ue" {
[P in DataPropertyNames<T>]: T[P] extends object ? DataPropertiesOnly<T[P]> : T[P]
};

function NewObject(Cls: Class, Outer?: Object, Name?:string, ObjectFlags?: number): Object;
function NewObject(Cls: Class, Outer?: Object, Name?:string, ObjectFlags?: number, JsTakeRef?: boolean): Object;

function NewStruct(St: ScriptStruct): object;

Expand Down

0 comments on commit de74f97

Please sign in to comment.