Use enumerated_array for difficulty-level-specific arrays

This commit is contained in:
Kp 2021-09-19 10:53:48 +00:00
parent 7fc8c736b3
commit 21c530a3e2
9 changed files with 57 additions and 43 deletions

View file

@ -65,6 +65,8 @@ class is_cxx_array : public std::false_type
template <typename T, std::size_t N>
class is_cxx_array<std::array<T, N>> : public std::true_type
{
public:
using array_type = std::array<T, N>;
};
template <typename T>
@ -419,8 +421,8 @@ template <typename T>
class message_dispatch_type<T, typename std::enable_if<is_cxx_array<T>::value, void>::type> :
public detail::message_dispatch_base<
detail::size_base<
message_type<typename T::value_type>::maximum_size * std::tuple_size<T>::value,
message_type<typename T::value_type>::minimum_size * std::tuple_size<T>::value
message_type<typename T::value_type>::maximum_size * std::tuple_size<typename is_cxx_array<T>::array_type>::value,
message_type<typename T::value_type>::minimum_size * std::tuple_size<typename is_cxx_array<T>::array_type>::value
>
>
{

View file

@ -35,6 +35,7 @@ COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
#include "weapon_id.h"
#include "object.h"
#include "fwd-partial_range.h"
#include "d_array.h"
#include "digi.h"
#define MAX_GUNS 8 //should be multiple of 4 for ubyte array
@ -113,7 +114,7 @@ struct robot_info : prohibit_void_ptr<robot_info>
fix mass; // how heavy is this thing?
fix drag; // how much drag does it have?
std::array<fix, NDL> field_of_view, // compare this value with forward_vector.dot.vector_to_player, if field_of_view <, then robot can see player
enumerated_array<fix, NDL, Difficulty_level_type> field_of_view, // compare this value with forward_vector.dot.vector_to_player, if field_of_view <, then robot can see player
firing_wait, // time in seconds between shots
#if defined(DXX_BUILD_DESCENT_II)
firing_wait2, // time in seconds between shots
@ -122,7 +123,7 @@ struct robot_info : prohibit_void_ptr<robot_info>
max_speed, // maximum speed attainable by this robot
circle_distance; // distance at which robot circles player
std::array<int8_t, NDL> rapidfire_count, // number of shots fired rapidly
enumerated_array<int8_t, NDL, Difficulty_level_type> rapidfire_count, // number of shots fired rapidly
evade_speed; // rate at which robot can evade shots, 0=none, 4=very fast
sbyte cloak_type; // 0=never, 1=always, 2=except-when-firing
sbyte attack_type; // 0=firing, 1=charge (like green guy)

View file

@ -133,8 +133,8 @@ struct weapon_info : prohibit_void_ptr<weapon_info>
fix blob_size; // Size of blob if blob type
fix flash_size; // How big to draw the flash
fix impact_size; // How big of an impact
std::array<fix, NDL> strength; // How much damage it can inflict
std::array<fix, NDL> speed; // How fast it can move, difficulty level based.
enumerated_array<fix, NDL, Difficulty_level_type> strength; // How much damage it can inflict
enumerated_array<fix, NDL, Difficulty_level_type> speed; // How fast it can move, difficulty level based.
fix mass; // How much mass it has
fix drag; // How much drag it has
fix thrust; // How much thrust it has
@ -186,8 +186,8 @@ struct weapon_info : prohibit_void_ptr<weapon_info>
fix blob_size; // Size of blob if blob type
fix flash_size; // How big to draw the flash
fix impact_size; // How big of an impact
std::array<fix, NDL> strength; // How much damage it can inflict
std::array<fix, NDL> speed; // How fast it can move, difficulty level based.
enumerated_array<fix, NDL, Difficulty_level_type> strength; // How much damage it can inflict
enumerated_array<fix, NDL, Difficulty_level_type> speed; // How fast it can move, difficulty level based.
fix mass; // How much mass it has
fix drag; // How much drag it has
fix thrust; // How much thrust it has

View file

@ -413,28 +413,28 @@ static int read_d2_robot_info(PHYSFS_File *fp, robot_info &ri)
ri.strength = PHYSFSX_readFix(fp);
ri.mass = PHYSFSX_readFix(fp);
ri.drag = PHYSFSX_readFix(fp);
for (j = 0; j < NDL; j++)
ri.field_of_view[j] = PHYSFSX_readFix(fp);
for (j = 0; j < NDL; j++)
ri.firing_wait[j] = PHYSFSX_readFix(fp);
for (auto &j : ri.field_of_view)
j = PHYSFSX_readFix(fp);
for (auto &j : ri.firing_wait)
j = PHYSFSX_readFix(fp);
for (j = 0; j < NDL; j++)
/*ri.firing_wait2[j] =*/ PHYSFSX_readFix(fp);
for (j = 0; j < NDL; j++)
ri.turn_time[j] = PHYSFSX_readFix(fp);
for (auto &j : ri.turn_time)
j = PHYSFSX_readFix(fp);
#if 0 // not used in d1, removed in d2
for (j = 0; j < NDL; j++)
ri.fire_power[j] = PHYSFSX_readFix(fp);
for (j = 0; j < NDL; j++)
ri.shield[j] = PHYSFSX_readFix(fp);
#endif
for (j = 0; j < NDL; j++)
ri.max_speed[j] = PHYSFSX_readFix(fp);
for (j = 0; j < NDL; j++)
ri.circle_distance[j] = PHYSFSX_readFix(fp);
for (j = 0; j < NDL; j++)
ri.rapidfire_count[j] = PHYSFSX_readByte(fp);
for (j = 0; j < NDL; j++)
ri.evade_speed[j] = PHYSFSX_readByte(fp);
for (auto &j : ri.max_speed)
j = PHYSFSX_readFix(fp);
for (auto &j : ri.circle_distance)
j = PHYSFSX_readFix(fp);
for (auto &j : ri.rapidfire_count)
j = PHYSFSX_readByte(fp);
for (auto &j : ri.evade_speed)
j = PHYSFSX_readByte(fp);
ri.cloak_type = PHYSFSX_readByte(fp);
ri.attack_type = PHYSFSX_readByte(fp);
ri.see_sound = PHYSFSX_readByte(fp);

View file

@ -1426,9 +1426,9 @@ void recreate_thief(const uint8_t thief_id)
// ----------------------------------------------------------------------------
#define THIEF_ATTACK_TIME (F1_0*10)
constexpr std::array<fix, NDL> Thief_wait_times = {{
constexpr enumerated_array<fix, NDL, Difficulty_level_type> Thief_wait_times = {{{
F1_0*30, F1_0*25, F1_0*20, F1_0*15, F1_0*10
}};
}}};
// -------------------------------------------------------------------------------------------------
void do_thief_frame(const vmobjptridx_t objp, const fix dist_to_player, const player_visibility_state player_visibility, const vms_vector &vec_to_player)

View file

@ -1357,7 +1357,7 @@ void ai_path_set_orient_and_vel(object &objp, const vms_vector &goal_point
vm_vec_negate(norm_vec_to_goal);
}
#endif
rate = robptr.turn_time[NDL - 1] / 2;
rate = robptr.turn_time[Difficulty_4] / 2;
} else
rate = robptr.turn_time[Difficulty_level];
ai_turn_towards_vector(norm_vec_to_goal, objp, rate);

View file

@ -1225,7 +1225,7 @@ static void bm_read_vclip(d_vclip_array &Vclip, int skip)
}
// ------------------------------------------------------------------------------
static void get4fix(std::array<fix, NDL> &fixp)
static void get4fix(enumerated_array<fix, NDL, Difficulty_level_type> &fixp)
{
char *curtext;
range_for (auto &i, fixp)
@ -1236,7 +1236,7 @@ static void get4fix(std::array<fix, NDL> &fixp)
}
// ------------------------------------------------------------------------------
static void get4byte(std::array<int8_t, NDL> &bytep)
static void get4byte(enumerated_array<int8_t, NDL, Difficulty_level_type> &bytep)
{
char *curtext;
range_for (auto &i, bytep)
@ -1248,7 +1248,7 @@ static void get4byte(std::array<int8_t, NDL> &bytep)
// ------------------------------------------------------------------------------
// Convert field of view from an angle in 0..360 to cosine.
static void adjust_field_of_view(std::array<fix, NDL> &fovp)
static void adjust_field_of_view(enumerated_array<fix, NDL, Difficulty_level_type> &fovp)
{
fixang tt;
float ff;
@ -1361,7 +1361,7 @@ void bm_read_robot_ai(const int skip)
get4byte(robptr.rapidfire_count);
get4fix(robptr.turn_time);
#if defined(DXX_BUILD_DESCENT_I)
std::array<fix, NDL> fire_power, // damage done by a hit from this robot
enumerated_array<fix, NDL, Difficulty_level_type> fire_power, // damage done by a hit from this robot
shield; // shield strength of this robot
get4fix(fire_power);
get4fix(shield);
@ -2222,10 +2222,10 @@ void bm_read_weapon(int skip, int unused_flag)
Weapon_info[n].wall_hit_vclip = vclip_none;
Weapon_info[n].wall_hit_sound = sound_none;
Weapon_info[n].impact_size = 0;
for (i=0; i<NDL; i++) {
Weapon_info[n].strength[i] = F1_0;
Weapon_info[n].speed[i] = F1_0*10;
}
for (auto &i : Weapon_info[n].strength)
i = F1_0;
for (auto &i : Weapon_info[n].speed)
i = F1_0*10;
Weapon_info[n].mass = F1_0;
Weapon_info[n].thrust = 0;
Weapon_info[n].drag = 0;
@ -2316,15 +2316,16 @@ void bm_read_weapon(int skip, int unused_flag)
// Load pof file
pof_file_inner = equal_ptr;
} else if (!d_stricmp( arg, "strength" )) {
for (i=0; i<NDL-1; i++) {
for (auto &i : unchecked_partial_range(Weapon_info[n].strength, Weapon_info[n].strength.size() - 1))
{
#if defined(DXX_BUILD_DESCENT_I)
Weapon_info[n].strength[i] = i2f(atoi(equal_ptr));
i = i2f(atoi(equal_ptr));
#elif defined(DXX_BUILD_DESCENT_II)
Weapon_info[n].strength[i] = fl2f(atof(equal_ptr));
i = fl2f(atof(equal_ptr));
#endif
equal_ptr = strtok(NULL, space_tab);
}
Weapon_info[n].strength[i] = i2f(atoi(equal_ptr));
Weapon_info[n].strength.back() = i2f(atoi(equal_ptr));
} else if (!d_stricmp( arg, "mass" )) {
Weapon_info[n].mass = fl2f(atof(equal_ptr));
} else if (!d_stricmp( arg, "drag" )) {
@ -2336,11 +2337,12 @@ void bm_read_weapon(int skip, int unused_flag)
} else if (!d_stricmp( arg, "bounce" )) {
Weapon_info[n].bounce = static_cast<weapon_info::bounce_type>(atoi(equal_ptr));
} else if (!d_stricmp( arg, "speed" )) {
for (i=0; i<NDL-1; i++) {
Weapon_info[n].speed[i] = i2f(atoi(equal_ptr));
for (auto &i : unchecked_partial_range(Weapon_info[n].speed, Weapon_info[n].speed.size() - 1))
{
i = i2f(atoi(equal_ptr));
equal_ptr = strtok(NULL, space_tab);
}
Weapon_info[n].speed[i] = i2f(atoi(equal_ptr));
Weapon_info[n].speed.back() = i2f(atoi(equal_ptr));
}
#if defined(DXX_BUILD_DESCENT_II)
else if (!d_stricmp( arg, "speedvar" )) {

View file

@ -933,17 +933,17 @@ int select_demo()
static int do_difficulty_menu()
{
using items_type = std::array<newmenu_item, NDL>;
using items_type = enumerated_array<newmenu_item, NDL, Difficulty_level_type>;
struct difficulty_prompt_menu : items_type, passive_newmenu
{
difficulty_prompt_menu(const unsigned Difficulty_level) :
items_type{{
items_type{{{
newmenu_item::nm_item_menu{MENU_DIFFICULTY_TEXT(Difficulty_0)},
newmenu_item::nm_item_menu{MENU_DIFFICULTY_TEXT(Difficulty_1)},
newmenu_item::nm_item_menu{MENU_DIFFICULTY_TEXT(Difficulty_2)},
newmenu_item::nm_item_menu{MENU_DIFFICULTY_TEXT(Difficulty_3)},
newmenu_item::nm_item_menu{MENU_DIFFICULTY_TEXT(Difficulty_4)},
}},
}}},
passive_newmenu(menu_title{nullptr}, menu_subtitle{TXT_DIFFICULTY_LEVEL}, menu_filename{nullptr}, tiny_mode_flag::normal, tab_processing_flag::ignore, adjusted_citem::create(*static_cast<items_type *>(this), Difficulty_level), grd_curscreen->sc_canvas)
{
}

View file

@ -1764,6 +1764,15 @@ void do_seismic_stuff(void)
DEFINE_BITMAP_SERIAL_UDT();
namespace serial {
template <typename T>
class is_cxx_array<enumerated_array<T, NDL, Difficulty_level_type>> : public is_cxx_array<std::array<T, NDL>>
{
};
}
#if defined(DXX_BUILD_DESCENT_I)
DEFINE_SERIAL_UDT_TO_MESSAGE(dsx::weapon_info, w, (w.render, w.model_num, w.model_num_inner, w.persistent, w.flash_vclip, w.flash_sound, w.robot_hit_vclip, w.robot_hit_sound, w.wall_hit_vclip, w.wall_hit_sound, w.fire_count, w.ammo_usage, w.weapon_vclip, w.destroyable, w.matter, w.bounce, w.homing_flag, w.dum1, w.dum2, w.dum3, w.energy_usage, w.fire_wait, w.bitmap, w.blob_size, w.flash_size, w.impact_size, w.strength, w.speed, w.mass, w.drag, w.thrust, w.po_len_to_width_ratio, w.light, w.lifetime, w.damage_radius, w.picture));
#elif defined(DXX_BUILD_DESCENT_II)