Skip to content

Commit 7e4d71c

Browse files
committed
继承
1 parent 5eb558c commit 7e4d71c

File tree

1 file changed

+29
-12
lines changed

1 file changed

+29
-12
lines changed

unity/native/papi-python/source/CppObjectMapperPython.cpp

Lines changed: 29 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -858,7 +858,7 @@ static PyType_Spec DynType_spec = {
858858
.name = "NativeClass",
859859
.basicsize = sizeof(DynObj),
860860
.itemsize = 0,
861-
.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HEAPTYPE,
861+
.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HEAPTYPE | Py_TPFLAGS_BASETYPE,
862862
.slots = DynType_slots
863863
};
864864

@@ -870,7 +870,7 @@ static PyType_Spec StaticPropMetaClass_spec = {
870870
.name = "builtins.PuerStaticPropMetaClass",
871871
.basicsize = sizeof(PyHeapTypeObject),
872872
.itemsize = 0,
873-
.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HEAPTYPE,
873+
.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HEAPTYPE | Py_TPFLAGS_BASETYPE,
874874
.slots = StaticPropMetaClass_slots
875875
};
876876

@@ -920,30 +920,47 @@ PyObject* CppObjectMapper::FindOrCreateClass(const puerts::ScriptClassDefinition
920920
char* typeName = (char*) PyMem_Malloc(strlen(ClassDefinition->ScriptName) + 10); // "builtins." + name + '\0'
921921
sprintf(typeName, "builtins.%s", ClassDefinition->ScriptName);
922922
spec.name = typeName;
923-
spec.flags = Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HEAPTYPE | Py_TPFLAGS_BASETYPE;
923+
924+
PyType_Spec Meta_Spec = StaticPropMetaClass_spec;
925+
char* meta_type_name = (char*) PyMem_Malloc(strlen(ClassDefinition->ScriptName) + 25); // "builtins.PuerStaticPropMetaClass." + name + '\0'
926+
sprintf(meta_type_name, "builtins.PuerStaticPropMetaClass.%s", ClassDefinition->ScriptName);
927+
Meta_Spec.name = meta_type_name;
928+
924929

925930
PyObject* type_obj = nullptr;
926931
PyObject* meta_class_type_obj = nullptr;
927932
if (ClassDefinition->SuperTypeId)
928933
{
929-
PyType_Spec Meta_Spec = StaticPropMetaClass_spec;
930-
char* meta_type_name = (char*) PyMem_Malloc(strlen(ClassDefinition->ScriptName) + 25); // "builtins.PuerStaticPropMetaClass." + name + '\0'
931-
sprintf(meta_type_name, "builtins.PuerStaticPropMetaClass.%s", ClassDefinition->ScriptName);
932-
Meta_Spec.name = meta_type_name;
933-
PyObject* bases = PyTuple_Pack(1, FindOrCreateClass(puerts::LoadClassByID(registry, ClassDefinition->SuperTypeId)));
934-
PyObject* meta_bases = PyTuple_Pack(1, (PyObject*)&PyType_Type);
934+
auto super_type_obj = FindOrCreateClass(puerts::LoadClassByID(registry, ClassDefinition->SuperTypeId));
935+
PyObject* bases = PyTuple_Pack(1, super_type_obj);
936+
auto super_meta = PyObject_GetAttrString(super_type_obj, "__puerts_metaclass__");
937+
if (!super_meta)
938+
{
939+
printf("Failed to get super metaclass for %s\n", ClassDefinition->ScriptName);
940+
PyErr_SetString(PyExc_RuntimeError, "Failed to get super metaclass");
941+
Py_DECREF(bases);
942+
return NULL;
943+
}
944+
PyObject* meta_bases = PyTuple_Pack(1, super_meta);
935945
meta_class_type_obj = PyType_FromSpecWithBases(&StaticPropMetaClass_spec, meta_bases);
936946
Py_DECREF(meta_bases);
937947
type_obj = PyType_FromMetaclass(reinterpret_cast<PyTypeObject *>(meta_class_type_obj), nullptr, &spec, bases);
938948
Py_DECREF(bases);
939949
}
940950
else
941951
{
942-
type_obj = PyType_FromSpec(&spec);
952+
PyObject* meta_bases = PyTuple_Pack(1, (PyObject*)&PyType_Type);
953+
meta_class_type_obj = PyType_FromSpecWithBases(&StaticPropMetaClass_spec, meta_bases);
954+
if (!meta_class_type_obj) {
955+
printf("Failed to create metaclass type object for %s\n", ClassDefinition->ScriptName);
956+
PyErr_SetString(PyExc_RuntimeError, "Failed to create metaclass type object");
957+
}
958+
Py_DECREF(meta_bases);
959+
type_obj = PyType_FromMetaclass(reinterpret_cast<PyTypeObject *>(meta_class_type_obj), nullptr, &spec, nullptr);
943960
}
944-
PyHeapTypeObject* type = (PyHeapTypeObject*)type_obj;
945961
if (!type_obj) return NULL;
946-
962+
if (!meta_class_type_obj) return NULL;
963+
PyObject_SetAttrString(type_obj, "__puerts_metaclass__", meta_class_type_obj);
947964

948965
ContextObj* ctx = (ContextObj*)PyObject_New(ContextObj, &Context_Type);
949966
if (!ctx) {

0 commit comments

Comments
 (0)