Skip to content

Commit ba6fa14

Browse files
author
Roberto De Ioris
committed
again subclassing api improvements
1 parent 323a3e1 commit ba6fa14

9 files changed

Lines changed: 273 additions & 185 deletions

File tree

‎Source/UnrealEnginePython/Private/UEPyModule.cpp‎

Lines changed: 164 additions & 130 deletions
Large diffs are not rendered by default.

‎Source/UnrealEnginePython/Private/UObject/UEPyActor.cpp‎

Lines changed: 18 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -274,7 +274,8 @@ PyObject *py_ue_register_component(ue_PyUObject *self, PyObject * args) {
274274

275275
UActorComponent *component = (UActorComponent *)self->ue_object;
276276

277-
component->RegisterComponent();
277+
if (!component->IsRegistered())
278+
component->RegisterComponent();
278279

279280
Py_INCREF(Py_None);
280281
return Py_None;
@@ -324,7 +325,8 @@ PyObject *py_ue_unregister_component(ue_PyUObject * self, PyObject * args) {
324325
if (!component)
325326
return PyErr_Format(PyExc_Exception, "uobject is not an UActorComponent");
326327

327-
component->UnregisterComponent();
328+
if (component->IsRegistered())
329+
component->UnregisterComponent();
328330

329331
Py_RETURN_NONE;
330332
}
@@ -392,11 +394,11 @@ PyObject *py_ue_add_actor_component(ue_PyUObject * self, PyObject * args) {
392394
scene_component->SetupAttachment(parent_component);
393395
}
394396

395-
if (actor->GetWorld()) {
397+
if (actor->GetWorld() && !component->IsRegistered()) {
396398
component->RegisterComponent();
397399
}
398400

399-
if (component->bWantsInitializeComponent && !component->HasBeenInitialized())
401+
if (component->bWantsInitializeComponent && !component->HasBeenInitialized() && component->IsRegistered())
400402
component->InitializeComponent();
401403

402404
PyObject *ret = (PyObject *)ue_get_python_wrapper(component);
@@ -429,11 +431,11 @@ PyObject *py_ue_add_python_component(ue_PyUObject * self, PyObject * args) {
429431
component->PythonModule = FString(UTF8_TO_TCHAR(module_name));
430432
component->PythonClass = FString(UTF8_TO_TCHAR(class_name));
431433

432-
if (actor->GetWorld()) {
434+
if (actor->GetWorld() && !component->IsRegistered()) {
433435
component->RegisterComponent();
434436
}
435437

436-
if (component->bWantsInitializeComponent && !component->HasBeenInitialized())
438+
if (component->bWantsInitializeComponent && !component->HasBeenInitialized() && component->IsRegistered())
437439
component->InitializeComponent();
438440

439441
PyObject *ret = (PyObject *)ue_get_python_wrapper(component);
@@ -453,23 +455,18 @@ PyObject *py_ue_actor_create_default_subobject(ue_PyUObject * self, PyObject * a
453455
return NULL;
454456
}
455457

456-
if (!self->ue_object->IsA<AActor>()) {
458+
AActor *actor = ue_py_check_type<AActor>(self);
459+
if (!actor)
457460
return PyErr_Format(PyExc_Exception, "uobject is not an AActor");
458-
}
459-
460-
AActor *actor = (AActor *)self->ue_object;
461-
462-
if (!ue_is_pyuobject(obj)) {
463-
return PyErr_Format(PyExc_Exception, "argument is not a UObject");
464-
}
465461

466-
ue_PyUObject *py_obj = (ue_PyUObject *)obj;
462+
UClass *u_class = ue_py_check_type<UClass>(obj);
463+
if (!u_class)
464+
return PyErr_Format(PyExc_Exception, "argument is not a UClass");
467465

468-
if (!py_obj->ue_object->IsA<UClass>()) {
469-
return PyErr_Format(PyExc_Exception, "argument is not a class");
470-
}
466+
if (!FUObjectThreadContext::Get().TopInitializer())
467+
return PyErr_Format(PyExc_Exception, "CreateDefaultSubobject() can be called only in a constructor");
471468

472-
UObject *ret_obj = actor->CreateDefaultSubobject(FName(UTF8_TO_TCHAR(name)), UObject::StaticClass(), (UClass *)py_obj->ue_object, false, false, true);
469+
UObject *ret_obj = actor->CreateDefaultSubobject(FName(UTF8_TO_TCHAR(name)), UObject::StaticClass(), u_class, false, false, true);
473470
if (!ret_obj)
474471
return PyErr_Format(PyExc_Exception, "unable to create component");
475472

@@ -513,11 +510,11 @@ PyObject *py_ue_add_actor_root_component(ue_PyUObject * self, PyObject * args) {
513510

514511
actor->SetRootComponent(component);
515512

516-
if (actor->GetWorld()) {
513+
if (actor->GetWorld() && !component->IsRegistered()) {
517514
component->RegisterComponent();
518515
}
519516

520-
if (component->bWantsInitializeComponent && !component->HasBeenInitialized())
517+
if (component->bWantsInitializeComponent && !component->HasBeenInitialized() && component->IsRegistered())
521518
component->InitializeComponent();
522519

523520
PyObject *ret = (PyObject *)ue_get_python_wrapper(component);

‎Source/UnrealEnginePython/Private/UObject/UEPyController.cpp‎

Lines changed: 34 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -10,22 +10,13 @@ PyObject *py_ue_controller_posses(ue_PyUObject * self, PyObject * args) {
1010
return NULL;
1111
}
1212

13-
if (!self->ue_object->IsA<AController>()) {
13+
AController *controller = ue_py_check_type<AController>(self);
14+
if (!controller)
1415
return PyErr_Format(PyExc_Exception, "uobject is not an AController");
15-
}
16-
17-
if (!ue_is_pyuobject(obj)) {
18-
return PyErr_Format(PyExc_Exception, "argument is not a UObject");
19-
}
20-
21-
ue_PyUObject *py_obj = (ue_PyUObject *)obj;
22-
23-
if (!py_obj->ue_object->IsA<APawn>()) {
24-
return PyErr_Format(PyExc_Exception, "argument is not a APAwn");
25-
}
2616

27-
APawn *pawn = (APawn *)py_obj->ue_object;
28-
AController *controller = (AController *)self->ue_object;
17+
APawn *pawn = ue_py_check_type<APawn>(obj);
18+
if (!pawn)
19+
return PyErr_Format(PyExc_Exception, "uobject is not an APawn");
2920

3021
controller->Possess(pawn);
3122

@@ -37,11 +28,11 @@ PyObject *py_ue_controller_get_hud(ue_PyUObject * self, PyObject * args) {
3728

3829
ue_py_check(self);
3930

40-
AController *controller = ue_py_check_type<AController>(self);
31+
APlayerController *controller = ue_py_check_type<APlayerController>(self);
4132
if (!controller)
4233
return PyErr_Format(PyExc_Exception, "uobject is not an AController");
4334

44-
ue_PyUObject *ret = ue_get_python_wrapper((UObject *)controller);
35+
ue_PyUObject *ret = ue_get_python_wrapper((UObject *)controller->GetHUD());
4536
if (!ret)
4637
return PyErr_Format(PyExc_Exception, "uobject is in invalid state");
4738
Py_INCREF(ret);
@@ -52,14 +43,35 @@ PyObject *py_ue_controller_unposses(ue_PyUObject * self, PyObject * args) {
5243

5344
ue_py_check(self);
5445

55-
if (!self->ue_object->IsA<AController>()) {
46+
AController *controller = ue_py_check_type<AController>(self);
47+
if (!controller)
5648
return PyErr_Format(PyExc_Exception, "uobject is not an AController");
57-
}
58-
59-
AController *controller = (AController *)self->ue_object;
6049

6150
controller->UnPossess();
6251

63-
Py_INCREF(Py_None);
64-
return Py_None;
52+
Py_RETURN_NONE;
53+
}
54+
55+
PyObject *py_ue_get_controlled_pawn(ue_PyUObject * self, PyObject * args) {
56+
57+
ue_py_check(self);
58+
59+
AController *controller = ue_py_check_type<AController>(self);
60+
if (!controller)
61+
return PyErr_Format(PyExc_Exception, "uobject is not an AController");
62+
63+
#if ENGINE_MINOR_VERSION >= 17
64+
APawn *pawn = controller->GetPawn();
65+
#else
66+
APawn *pawn = controller->GetControlledPawn();
67+
#endif
68+
if (!pawn) {
69+
Py_RETURN_NONE;
70+
}
71+
72+
ue_PyUObject *ret = ue_get_python_wrapper(pawn);
73+
if (!ret)
74+
return PyErr_Format(PyExc_Exception, "uobject is in invalid state");
75+
Py_INCREF(ret);
76+
return (PyObject *)ret;
6577
}

‎Source/UnrealEnginePython/Private/UObject/UEPyController.h‎

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6,4 +6,5 @@
66

77
PyObject *py_ue_controller_posses(ue_PyUObject *, PyObject *);
88
PyObject *py_ue_controller_unposses(ue_PyUObject *, PyObject *);
9-
PyObject *py_ue_controller_get_hud(ue_PyUObject *, PyObject *);
9+
PyObject *py_ue_controller_get_hud(ue_PyUObject *, PyObject *);
10+
PyObject *py_ue_get_controlled_pawn(ue_PyUObject *, PyObject *);

‎Source/UnrealEnginePython/Private/UObject/UEPyMovements.cpp‎

Lines changed: 48 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
#include "UnrealEnginePythonPrivatePCH.h"
22

33

4-
54
PyObject *py_ue_add_controller_yaw_input(ue_PyUObject *self, PyObject * args) {
65

76
ue_py_check(self);
@@ -16,23 +15,25 @@ PyObject *py_ue_add_controller_yaw_input(ue_PyUObject *self, PyObject * args) {
1615
if (self->ue_object->IsA<APawn>()) {
1716
pawn = (APawn *)self->ue_object;
1817
}
19-
else if (self->ue_object->IsA<UActorComponent>()) {
20-
UActorComponent *component = (UActorComponent *)self->ue_object;
18+
else if (UActorComponent *component = ue_py_check_type<UActorComponent>(self)) {
2119
AActor *actor = component->GetOwner();
2220
if (actor) {
2321
if (actor->IsA<APawn>()) {
2422
pawn = (APawn *)actor;
2523
}
2624
}
2725
}
26+
else if (APlayerController *player = ue_py_check_type<APlayerController>(self)) {
27+
player->AddYawInput(val);
28+
Py_RETURN_NONE;
29+
}
2830

2931
if (!pawn)
30-
return PyErr_Format(PyExc_Exception, "uobject is not a pawn");
32+
return PyErr_Format(PyExc_Exception, "uobject is not a Pawn or a PlayerController");
3133

3234
pawn->AddControllerYawInput(val);
3335

34-
Py_INCREF(Py_None);
35-
return Py_None;
36+
Py_RETURN_NONE;
3637
}
3738

3839
PyObject *py_ue_add_controller_pitch_input(ue_PyUObject *self, PyObject * args) {
@@ -58,14 +59,52 @@ PyObject *py_ue_add_controller_pitch_input(ue_PyUObject *self, PyObject * args)
5859
}
5960
}
6061
}
62+
else if (APlayerController *player = ue_py_check_type<APlayerController>(self)) {
63+
player->AddPitchInput(val);
64+
Py_RETURN_NONE;
65+
}
6166

6267
if (!pawn)
63-
return PyErr_Format(PyExc_Exception, "uobject is not a pawn");
68+
return PyErr_Format(PyExc_Exception, "uobject is not a Pawn or a PlayerController");
6469

6570
pawn->AddControllerPitchInput(val);
6671

67-
Py_INCREF(Py_None);
68-
return Py_None;
72+
Py_RETURN_NONE;
73+
}
74+
75+
PyObject *py_ue_add_controller_roll_input(ue_PyUObject *self, PyObject * args) {
76+
77+
ue_py_check(self);
78+
79+
float val;
80+
if (!PyArg_ParseTuple(args, "f:add_controller_roll_input", &val)) {
81+
return NULL;
82+
}
83+
84+
APawn *pawn = nullptr;
85+
86+
if (self->ue_object->IsA<APawn>()) {
87+
pawn = (APawn *)self->ue_object;
88+
}
89+
else if (UActorComponent *component = ue_py_check_type<UActorComponent>(self)) {
90+
AActor *actor = component->GetOwner();
91+
if (actor) {
92+
if (actor->IsA<APawn>()) {
93+
pawn = (APawn *)actor;
94+
}
95+
}
96+
}
97+
else if (APlayerController *player = ue_py_check_type<APlayerController>(self)) {
98+
player->AddRollInput(val);
99+
Py_RETURN_NONE;
100+
}
101+
102+
if (!pawn)
103+
return PyErr_Format(PyExc_Exception, "uobject is not a Pawn or a PlayerController");
104+
105+
pawn->AddControllerRollInput(val);
106+
107+
Py_RETURN_NONE;
69108
}
70109

71110
PyObject *py_ue_add_movement_input(ue_PyUObject *self, PyObject * args) {

‎Source/UnrealEnginePython/Private/UObject/UEPyMovements.h‎

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77

88
PyObject *py_ue_add_controller_yaw_input(ue_PyUObject *, PyObject *);
99
PyObject *py_ue_add_controller_pitch_input(ue_PyUObject *, PyObject *);
10+
PyObject *py_ue_add_controller_roll_input(ue_PyUObject *, PyObject *);
1011
PyObject *py_ue_get_control_rotation(ue_PyUObject *, PyObject *);
1112
PyObject *py_ue_add_movement_input(ue_PyUObject *, PyObject *);
1213

‎Source/UnrealEnginePython/Private/UObject/UEPyPlayer.cpp‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -149,7 +149,7 @@ PyObject *py_ue_create_player(ue_PyUObject *self, PyObject * args) {
149149

150150
APlayerController *controller = UGameplayStatics::CreatePlayer(world, controller_id, b_spawn_pawn);
151151
if (!controller)
152-
return PyErr_Format(PyExc_Exception, "unable to create a new player fro controller %d", controller_id);
152+
return PyErr_Format(PyExc_Exception, "unable to create a new player from controller %d", controller_id);
153153

154154
return PyLong_FromLong(controller->PlayerState->PlayerId);
155155
}

‎Source/UnrealEnginePython/Private/Wrappers/UEPyFVector.cpp‎

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -325,6 +325,10 @@ void ue_python_init_fvector(PyObject *ue_module) {
325325
if (PyType_Ready(&ue_PyFVectorType) < 0)
326326
return;
327327

328+
PyDict_SetItemString(ue_PyFVectorType.tp_dict, "forward", py_ue_new_fvector(FVector(1, 0, 0)));
329+
PyDict_SetItemString(ue_PyFVectorType.tp_dict, "right", py_ue_new_fvector(FVector(0, 1, 0)));
330+
PyDict_SetItemString(ue_PyFVectorType.tp_dict, "up", py_ue_new_fvector(FVector(0, 0, 1)));
331+
328332
Py_INCREF(&ue_PyFVectorType);
329333
PyModule_AddObject(ue_module, "FVector", (PyObject *)&ue_PyFVectorType);
330334
}

‎Source/UnrealEnginePython/Public/PythonClass.h‎

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -30,7 +30,7 @@ class UPythonClass : public UClass
3030
ue_PyUObject *py_uobject;
3131

3232
private:
33-
33+
3434
PyObject *py_constructor;
3535
};
3636

0 commit comments

Comments
 (0)