feat: reloading withdraws ammo from inventory
This commit is contained in:
parent
a2035e0db0
commit
ed85b557a7
|
@ -9,7 +9,6 @@ void WeaponBase::_bind_methods() {
|
|||
BIND_HPROPERTY(Variant::OBJECT, anim, PROPERTY_HINT_NODE_TYPE, AnimationPlayer::get_class_static());
|
||||
BIND_PROPERTY(Variant::INT, max_ammo);
|
||||
BIND_PROPERTY(Variant::INT, loaded_ammo);
|
||||
ClassDB::bind_method(D_METHOD("reload_full"), &self_type::reload_full);
|
||||
ClassDB::bind_method(D_METHOD("reload_num", "num"), &self_type::reload_num);
|
||||
ClassDB::bind_method(D_METHOD("ammo_empty"), &self_type::ammo_empty);
|
||||
}
|
||||
|
@ -62,6 +61,14 @@ PlayerCamera *WeaponBase::get_camera() const {
|
|||
return this->camera;
|
||||
}
|
||||
|
||||
WeaponInventory *WeaponBase::get_inventory() const {
|
||||
return this->inventory;
|
||||
}
|
||||
|
||||
void WeaponBase::_set_inventory(WeaponInventory *inventory) {
|
||||
this->inventory = inventory;
|
||||
}
|
||||
|
||||
void WeaponBase::set_body(PlayerBody *body) {
|
||||
this->body = body;
|
||||
}
|
||||
|
@ -99,11 +106,6 @@ bool WeaponBase::ammo_empty() const {
|
|||
return this->loaded_ammo <= 0;
|
||||
}
|
||||
|
||||
void WeaponBase::reload_full() {
|
||||
// TODO: take difference between loaded and max out of inventory
|
||||
set_loaded_ammo(this->max_ammo);
|
||||
}
|
||||
|
||||
void WeaponBase::reload_num(int num) {
|
||||
int const space{ this->max_ammo - this->loaded_ammo };
|
||||
num = MIN(num, space);
|
||||
|
|
|
@ -6,6 +6,7 @@ class AnimationPlayer;
|
|||
class PlayerCamera;
|
||||
class PlayerBody;
|
||||
class PlayerInput;
|
||||
class WeaponInventory;
|
||||
|
||||
class WeaponBase : public Node3D {
|
||||
GDCLASS(WeaponBase, Node3D);
|
||||
|
@ -22,6 +23,8 @@ public:
|
|||
AnimationPlayer *get_anim() const;
|
||||
PlayerInput *get_input() const;
|
||||
PlayerCamera *get_camera() const;
|
||||
WeaponInventory *get_inventory() const;
|
||||
void _set_inventory(WeaponInventory *inventory);
|
||||
|
||||
void set_body(PlayerBody *body);
|
||||
PlayerBody *get_body() const;
|
||||
|
@ -32,8 +35,7 @@ public:
|
|||
int get_loaded_ammo() const;
|
||||
bool try_use_ammo(int amount = 1);
|
||||
bool ammo_empty() const;
|
||||
void reload_full();
|
||||
void reload_num(int num);
|
||||
void reload_num(int num); // !< Increase loaded_ammo by num up to a maximum of max_ammo. NOTE: this will _not_ check if the ammo is available. And assumes that the ammo was already subtracted from the weapon inventory's store.
|
||||
|
||||
virtual bool allows_running() const { return false; }
|
||||
virtual bool allows_jumping() const { return true; }
|
||||
|
@ -44,6 +46,7 @@ private:
|
|||
AnimationPlayer *anim{ nullptr };
|
||||
PlayerCamera *camera{ nullptr };
|
||||
PlayerBody *body{ nullptr };
|
||||
WeaponInventory *inventory{ nullptr };
|
||||
|
||||
int loaded_ammo{ 0 };
|
||||
int max_ammo{ 1 };
|
||||
|
|
|
@ -4,6 +4,8 @@
|
|||
|
||||
void WeaponInventory::_bind_methods() {
|
||||
BIND_HPROPERTY(Variant::OBJECT, starting_weapon, PROPERTY_HINT_RESOURCE_TYPE, "PackedScene");
|
||||
BIND_PROPERTY(Variant::INT, pistol_ammo);
|
||||
BIND_PROPERTY(Variant::INT, rifle_ammo);
|
||||
}
|
||||
|
||||
void WeaponInventory::on_switch_input() {
|
||||
|
@ -65,6 +67,7 @@ void WeaponInventory::pickup_weapon(Ref<PackedScene> weapon_scene) {
|
|||
}
|
||||
Node *weapon_as_node{ weapon_scene->instantiate() };
|
||||
if (WeaponBase * weapon{ cast_to<WeaponBase>(weapon_as_node) }) {
|
||||
weapon->_set_inventory(this);
|
||||
this->weapon_parent->add_child(weapon_as_node);
|
||||
// Where to put the new weapon, consider empty slot 1, then empty slot 2, then replace current.
|
||||
if (this->weapons[0] == nullptr) {
|
||||
|
@ -100,3 +103,49 @@ void WeaponInventory::set_starting_weapon(Ref<PackedScene> scene) {
|
|||
Ref<PackedScene> WeaponInventory::get_starting_weapon() const {
|
||||
return this->starting_weapon;
|
||||
}
|
||||
|
||||
void WeaponInventory::deposit_pistol_ammo(int amount) {
|
||||
this->pistol_ammo += amount;
|
||||
}
|
||||
|
||||
void WeaponInventory::set_pistol_ammo(int amount) {
|
||||
this->rifle_ammo = abs(amount);
|
||||
}
|
||||
|
||||
int WeaponInventory::get_pistol_ammo() const {
|
||||
return this->pistol_ammo;
|
||||
}
|
||||
|
||||
int WeaponInventory::withdraw_pistol_ammo(int max_amount) {
|
||||
if (max_amount < this->pistol_ammo) {
|
||||
this->pistol_ammo -= max_amount;
|
||||
return max_amount;
|
||||
} else {
|
||||
int const val{ this->pistol_ammo };
|
||||
this->pistol_ammo = 0;
|
||||
return val;
|
||||
}
|
||||
}
|
||||
|
||||
void WeaponInventory::deposit_rifle_ammo(int amount) {
|
||||
this->rifle_ammo += amount;
|
||||
}
|
||||
|
||||
void WeaponInventory::set_rifle_ammo(int amount) {
|
||||
this->rifle_ammo = abs(amount);
|
||||
}
|
||||
|
||||
int WeaponInventory::get_rifle_ammo() const {
|
||||
return this->rifle_ammo;
|
||||
}
|
||||
|
||||
int WeaponInventory::withdraw_rifle_ammo(int max_amount) {
|
||||
if (max_amount < this->rifle_ammo) {
|
||||
this->rifle_ammo -= max_amount;
|
||||
return max_amount;
|
||||
} else {
|
||||
int const val{ this->rifle_ammo };
|
||||
this->rifle_ammo = 0;
|
||||
return val;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -28,6 +28,15 @@ public:
|
|||
void pickup_demo_pack();
|
||||
bool try_use_demo_pack();
|
||||
|
||||
void deposit_pistol_ammo(int amount);
|
||||
void set_pistol_ammo(int amount);
|
||||
int get_pistol_ammo() const;
|
||||
int withdraw_pistol_ammo(int max_amount);
|
||||
void deposit_rifle_ammo(int amount);
|
||||
void set_rifle_ammo(int amount);
|
||||
int get_rifle_ammo() const;
|
||||
int withdraw_rifle_ammo(int max_amount);
|
||||
|
||||
private:
|
||||
Node3D *weapon_parent{ nullptr };
|
||||
unsigned current{ 0 };
|
||||
|
@ -36,8 +45,8 @@ private:
|
|||
|
||||
Ref<PackedScene> starting_weapon{};
|
||||
|
||||
int pistol_ammo{ 60 };
|
||||
int rifle_ammo{ 0 };
|
||||
int pistol_ammo{ 16 };
|
||||
int rifle_ammo{ 30 };
|
||||
};
|
||||
|
||||
#endif // !WEAPON_INVENTORY_H
|
||||
|
|
|
@ -4,6 +4,7 @@
|
|||
#include "wave_survival/player_body.h"
|
||||
#include "wave_survival/player_camera.h"
|
||||
#include "wave_survival/player_input.h"
|
||||
#include "wave_survival/weapon_inventory.h"
|
||||
|
||||
void Revolver::_bind_methods() {
|
||||
ClassDB::bind_method(D_METHOD("start_recoil"), &self_type::start_recoil);
|
||||
|
@ -51,9 +52,11 @@ void Revolver::stop_running() {
|
|||
}
|
||||
|
||||
void Revolver::start_reloading() {
|
||||
if (get_inventory()->get_pistol_ammo() > 0) {
|
||||
this->alt_active = false;
|
||||
get_anim()->queue("double_to_reload");
|
||||
get_anim()->queue("reload_one");
|
||||
}
|
||||
}
|
||||
|
||||
void Revolver::play_equip_anim() {
|
||||
|
@ -106,8 +109,9 @@ void Revolver::on_reload() {
|
|||
|
||||
void Revolver::on_animation_finished(String old_anim) {
|
||||
if (old_anim == "reload_one" && get_anim()->get_queue().is_empty()) {
|
||||
reload_num(1);
|
||||
if (get_loaded_ammo() < get_max_ammo()) {
|
||||
int const available{ get_inventory()->withdraw_pistol_ammo(1) };
|
||||
reload_num(available);
|
||||
if (available > 0 && get_loaded_ammo() < get_max_ammo()) {
|
||||
get_anim()->queue("reload_one");
|
||||
} else {
|
||||
get_anim()->queue("reload_to_double");
|
||||
|
|
|
@ -4,12 +4,14 @@
|
|||
#include "wave_survival/macros.h"
|
||||
#include "wave_survival/player_body.h"
|
||||
#include "wave_survival/player_input.h"
|
||||
#include "wave_survival/weapon_inventory.h"
|
||||
|
||||
void Rifle::_bind_methods() {
|
||||
BIND_PROPERTY(Variant::FLOAT, ads_factor);
|
||||
BIND_PROPERTY(Variant::FLOAT, run_factor);
|
||||
BIND_PROPERTY(Variant::FLOAT, recoil_force);
|
||||
BIND_PROPERTY(Variant::FLOAT, recoil_time);
|
||||
ClassDB::bind_method(D_METHOD("reload_full"), &self_type::reload_full);
|
||||
}
|
||||
|
||||
void Rifle::queue_enter_alt() {
|
||||
|
@ -53,7 +55,7 @@ void Rifle::shoot() {
|
|||
}
|
||||
|
||||
void Rifle::start_reload_animation() {
|
||||
if (!is_animating() && get_loaded_ammo() != get_max_ammo()) {
|
||||
if (!is_animating() && get_loaded_ammo() < get_max_ammo() && get_inventory()->get_rifle_ammo() > 0) {
|
||||
if (this->in_alt_mode) {
|
||||
get_anim()->queue("aim_to_hip");
|
||||
}
|
||||
|
@ -181,6 +183,11 @@ void Rifle::notify_selected() {
|
|||
play_equip_anim();
|
||||
}
|
||||
|
||||
void Rifle::reload_full() {
|
||||
int const available = get_inventory()->withdraw_rifle_ammo(get_max_ammo());
|
||||
reload_num(available);
|
||||
}
|
||||
|
||||
void Rifle::set_ads_factor(float value) {
|
||||
this->ads_factor = value;
|
||||
}
|
||||
|
|
|
@ -30,6 +30,7 @@ public:
|
|||
virtual bool allows_running() const override;
|
||||
bool run_requested() const;
|
||||
virtual void notify_selected() override;
|
||||
void reload_full();
|
||||
|
||||
void set_ads_factor(float value);
|
||||
float get_ads_factor() const;
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
[gd_scene load_steps=6 format=3 uid="uid://snjgu4yp5swd"]
|
||||
|
||||
[ext_resource type="PackedScene" uid="uid://ce40pq785yoyi" path="res://objects/weapons/rifle.tscn" id="1_eqqp1"]
|
||||
[ext_resource type="PackedScene" uid="uid://cfgwif53qypko" path="res://objects/weapons/revolver.tscn" id="1_eqqp1"]
|
||||
|
||||
[sub_resource type="SphereShape3D" id="SphereShape3D_eqqp1"]
|
||||
radius = 0.2
|
||||
|
|
Loading…
Reference in a new issue