feat: weapon swapping

This commit is contained in:
Sara 2025-08-11 16:49:49 +02:00
parent 6b7a092961
commit 7a13823c97
6 changed files with 44 additions and 18 deletions

View file

@ -1,5 +1,6 @@
#include "weapon_inventory.h"
#include "macros.h"
#include "player_input.h"
#include "weapon_base.h"
void WeaponInventory::_bind_methods() {
@ -10,13 +11,18 @@ void WeaponInventory::_bind_methods() {
}
void WeaponInventory::on_switch_input() {
this->current = (this->current + 1) % 1;
this->select_weapon(this->weapons[this->current]);
unsigned next{ (this->current + 1) % 2 };
if (this->weapons[next] != nullptr) {
this->select_weapon(this->weapons[next]);
}
}
void WeaponInventory::ready() {
callable_mp(this, &self_type::pickup_weapon).call_deferred(this->starting_weapon);
this->weapon_parent = cast_to<Node3D>(get_node(NodePath("%PlayerCamera")));
if (PlayerInput * input{ cast_to<PlayerInput>(get_node(NodePath("%PlayerInput"))) }) {
input->connect(PlayerInput::sig_switch_weapon, callable_mp(this, &self_type::on_switch_input));
}
}
void WeaponInventory::_notification(int what) {
@ -37,6 +43,9 @@ void WeaponInventory::select_weapon(WeaponBase *new_weapon) {
print_error("WeaponInventory::select_weapon: Weapon invalid, returning before taking any action.");
return;
}
if (this->current_weapon != nullptr && !this->current_weapon->allows_swapping()) {
return;
}
if (new_weapon == this->weapons[0]) {
this->current = 0;
} else if (new_weapon == this->weapons[1]) {
@ -48,6 +57,7 @@ void WeaponInventory::select_weapon(WeaponBase *new_weapon) {
if (this->current_weapon != nullptr) {
this->current_weapon->set_process_mode(PROCESS_MODE_DISABLED);
this->current_weapon->set_visible(false);
this->current_weapon->notify_deselected();
}
this->current_weapon = new_weapon;
if (this->current_weapon != nullptr) {
@ -63,7 +73,7 @@ WeaponBase *WeaponInventory::get_current_weapon() const {
void WeaponInventory::pickup_weapon(Ref<PackedScene> weapon_scene) {
if (!weapon_scene.is_valid()) {
print_error("WeaponInventory::pickup_weapon: passed weapon scene");
print_error("WeaponInventory::pickup_weapon: passed weapon scene is invalid");
return;
}
Node *weapon_as_node{ weapon_scene->instantiate() };
@ -73,22 +83,18 @@ void WeaponInventory::pickup_weapon(Ref<PackedScene> weapon_scene) {
// Where to put the new weapon, consider empty slot 1, then empty slot 2, then replace current.
if (this->weapons[0] == nullptr) {
this->weapons[0] = weapon;
select_weapon(weapon);
return;
} else if (this->weapons[1] == nullptr) {
this->weapons[1] = weapon;
select_weapon(weapon);
return;
} else {
// replace current weapon, assign the slot
this->weapons[this->current] = weapon;
// free the current weapon
this->current_weapon->queue_free();
// set the point to null, so select_weapon will skip dropping the current weapon.
// set the current to null, so select_weapon will skip dropping it
this->current_weapon = nullptr;
// equip new weapon
select_weapon(weapon);
}
// equip new weapon
select_weapon(weapon);
} else if (weapon_as_node != nullptr) {
print_error(vformat("WeaponInventory::pickup_weapon: weapon scene '%s' instantiated a node of type '%s', which does not inherit from 'WeaponBase'", weapon_scene->get_path(), weapon_as_node->get_class()));
weapon_as_node->queue_free();