Use enum class for bitmap_index

This commit is contained in:
Kp 2022-12-31 16:21:47 +00:00
parent 147dd52f7d
commit e3553586c1
36 changed files with 280 additions and 280 deletions

View file

@ -29,12 +29,10 @@ COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
#include "maths.h" #include "maths.h"
#include "fwd-vclip.h" #include "fwd-vclip.h"
#include "fwd-game.h" #include "fwd-game.h"
#include "fwd-piggy.h"
#include "fwd-robot.h" #include "fwd-robot.h"
#include "d_array.h" #include "d_array.h"
#include "inferno.h" #include "inferno.h"
struct bitmap_index;
#include <cstdint> #include <cstdint>
namespace dcx { namespace dcx {

View file

@ -19,8 +19,6 @@
#include "polyobj.h" #include "polyobj.h"
#include <array> #include <array>
struct bitmap_index;
namespace dcx { namespace dcx {
// Movement types // Movement types

View file

@ -71,7 +71,7 @@ extern uint8_t Pigfile_initialized;
#endif #endif
// an index into the bitmap collection of the piggy file // an index into the bitmap collection of the piggy file
struct bitmap_index; enum class bitmap_index : uint16_t;
struct BitmapFile; struct BitmapFile;
#if defined(DXX_BUILD_DESCENT_I) #if defined(DXX_BUILD_DESCENT_I)
@ -100,7 +100,7 @@ constexpr std::integral_constant<unsigned, 2620> MAX_BITMAP_FILES{};
#endif #endif
#define MAX_SOUND_FILES MAX_SOUNDS #define MAX_SOUND_FILES MAX_SOUNDS
using GameBitmaps_array = std::array<grs_bitmap, MAX_BITMAP_FILES>; using GameBitmaps_array = enumerated_array<grs_bitmap, MAX_BITMAP_FILES, bitmap_index>;
extern std::array<digi_sound, MAX_SOUND_FILES> GameSounds; extern std::array<digi_sound, MAX_SOUND_FILES> GameSounds;
extern GameBitmaps_array GameBitmaps; extern GameBitmaps_array GameBitmaps;
void piggy_bitmap_page_in(GameBitmaps_array &, bitmap_index bmp); void piggy_bitmap_page_in(GameBitmaps_array &, bitmap_index bmp);
@ -153,7 +153,7 @@ extern ubyte bogus_bitmap_initialized;
extern hashtable AllBitmapsNames; extern hashtable AllBitmapsNames;
extern hashtable AllDigiSndNames; extern hashtable AllDigiSndNames;
#elif defined(DXX_BUILD_DESCENT_II) #elif defined(DXX_BUILD_DESCENT_II)
extern std::array<BitmapFile, MAX_BITMAP_FILES> AllBitmaps; extern enumerated_array<BitmapFile, MAX_BITMAP_FILES, bitmap_index> AllBitmaps;
#endif #endif
void swap_0_255(grs_bitmap &bmp); void swap_0_255(grs_bitmap &bmp);

View file

@ -25,10 +25,8 @@ COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
#pragma once #pragma once
#include "fwd-piggy.h"
#include "fwd-player.h" #include "fwd-player.h"
struct bitmap_index;
#include "fwd-object.h" #include "fwd-object.h"
#include "kconfig.h" #include "kconfig.h"
#include "game.h" #include "game.h"

View file

@ -36,6 +36,7 @@ COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
#include "mission.h" #include "mission.h"
#include "powerup.h" #include "powerup.h"
#include "fwd-object.h" #include "fwd-object.h"
#include "fwd-piggy.h"
#include "fwd-robot.h" #include "fwd-robot.h"
#include "fwd-segment.h" #include "fwd-segment.h"
#include "fwd-wall.h" #include "fwd-wall.h"

View file

@ -42,12 +42,10 @@ struct alias
#endif #endif
// an index into the bitmap collection of the piggy file // an index into the bitmap collection of the piggy file
struct bitmap_index enum class bitmap_index : uint16_t
{ {
ushort index; None = UINT16_MAX
constexpr bool operator==(const bitmap_index &) const = default;
}; };
#define DEFINE_BITMAP_SERIAL_UDT() DEFINE_SERIAL_UDT_TO_MESSAGE(bitmap_index, b, (b.index))
struct BitmapFile struct BitmapFile
{ {
@ -60,7 +58,7 @@ namespace dsx {
# define PIGGY_PAGE_IN(bmp) _piggy_page_in(GameBitmaps, bmp) # define PIGGY_PAGE_IN(bmp) _piggy_page_in(GameBitmaps, bmp)
static inline void _piggy_page_in(GameBitmaps_array &GameBitmaps, bitmap_index bmp) static inline void _piggy_page_in(GameBitmaps_array &GameBitmaps, bitmap_index bmp)
{ {
if (GameBitmaps[bmp.index].get_flag_mask(BM_FLAG_PAGED_OUT)) if (GameBitmaps[bmp].get_flag_mask(BM_FLAG_PAGED_OUT))
piggy_bitmap_page_in(GameBitmaps, bmp); piggy_bitmap_page_in(GameBitmaps, bmp);
} }

View file

@ -25,11 +25,9 @@ COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
#pragma once #pragma once
#include "fwd-piggy.h"
#include "vecmat.h" #include "vecmat.h"
#include "3d.h" #include "3d.h"
struct bitmap_index;
#include <cstddef> #include <cstddef>
#include <cstdint> #include <cstdint>
#include <memory> #include <memory>

View file

@ -89,7 +89,7 @@ void vclip_write(PHYSFS_File *fp, const vclip &vc);
/* Defer expansion to source file so that serial.h not needed here */ /* Defer expansion to source file so that serial.h not needed here */
#define DEFINE_VCLIP_SERIAL_UDT() \ #define DEFINE_VCLIP_SERIAL_UDT() \
DEFINE_SERIAL_UDT_TO_MESSAGE(bitmap_index, bi, (bi.index)); \ /* DEFINE_SERIAL_UDT_TO_MESSAGE(bitmap_index, bi, (bi.index)); */ \
DEFINE_SERIAL_UDT_TO_MESSAGE(vclip, vc, (vc.play_time, vc.num_frames, vc.frame_time, vc.flags, serial::pad<3>(), vc.sound_num, vc.frames, vc.light_value)); \ DEFINE_SERIAL_UDT_TO_MESSAGE(vclip, vc, (vc.play_time, vc.num_frames, vc.frame_time, vc.flags, serial::pad<3>(), vc.sound_num, vc.frames, vc.light_value)); \
ASSERT_SERIAL_UDT_MESSAGE_SIZE(vclip, 82); ASSERT_SERIAL_UDT_MESSAGE_SIZE(vclip, 82);
#endif #endif

View file

@ -288,7 +288,8 @@ static int load_pigpog(const d_fname &pogname)
return rc; return rc;
} }
bmp = &GameBitmaps[x]; const bitmap_index bi{static_cast<uint16_t>(x)};
bmp = &GameBitmaps[bi];
auto &bmo = BitmapOriginal[x].b; auto &bmo = BitmapOriginal[x].b;
if (bmo.get_flag_mask(BM_FLAG_CUSTOMIZED)) // already customized? if (bmo.get_flag_mask(BM_FLAG_CUSTOMIZED)) // already customized?
@ -307,7 +308,7 @@ static int load_pigpog(const d_fname &pogname)
// save original bitmap info // save original bitmap info
bmo = *bmp; bmo = *bmp;
bmo.add_flags(BM_FLAG_CUSTOMIZED); bmo.add_flags(BM_FLAG_CUSTOMIZED);
if (GameBitmapOffset[x] != pig_bitmap_offset::None) // from pig? if (GameBitmapOffset[bi] != pig_bitmap_offset::None) // from pig?
{ {
/* Borrow the data field to store the offset within /* Borrow the data field to store the offset within
* the pig file, which is not a pointer. Attempts * the pig file, which is not a pointer. Attempts
@ -315,11 +316,11 @@ static int load_pigpog(const d_fname &pogname)
* crash. * crash.
*/ */
bmo.add_flags(BM_FLAG_PAGED_OUT); bmo.add_flags(BM_FLAG_PAGED_OUT);
bmo.bm_data = reinterpret_cast<uint8_t *>(static_cast<uintptr_t>(GameBitmapOffset[x])); bmo.bm_data = reinterpret_cast<uint8_t *>(static_cast<uintptr_t>(GameBitmapOffset[bi]));
} }
} }
GameBitmapOffset[x] = pig_bitmap_offset::None; // not in pig GameBitmapOffset[bi] = pig_bitmap_offset::None; // not in pig
*bmp = {}; *bmp = {};
gr_init_bitmap(*bmp, bm_mode::linear, 0, 0, cip->width, cip->height, cip->width, p); gr_init_bitmap(*bmp, bm_mode::linear, 0, 0, cip->width, cip->height, cip->width, p);
gr_set_bitmap_flags(*bmp, cip->flags & 255); gr_set_bitmap_flags(*bmp, cip->flags & 255);
@ -557,7 +558,7 @@ static void load_hxm(const d_fname &hxmname)
const auto oi = static_cast<object_bitmap_index>(PHYSFSX_readInt(f)); const auto oi = static_cast<object_bitmap_index>(PHYSFSX_readInt(f));
auto v = PHYSFSX_readShort(f); auto v = PHYSFSX_readShort(f);
if (ObjBitmaps.valid_index(oi)) if (ObjBitmaps.valid_index(oi))
ObjBitmaps[oi].index = v; ObjBitmaps[oi] = bitmap_index{static_cast<uint16_t>(v)};
} }
} }
} }

View file

@ -10,20 +10,17 @@
#include "pstypes.h" #include "pstypes.h"
#include "piggy.h" #include "piggy.h"
#ifdef __cplusplus
#include "dxxsconf.h" #include "dxxsconf.h"
#include <array> #include "d_array.h"
/* from piggy.c */ /* from piggy.c */
#define DBM_FLAG_LARGE 128 // Flags added onto the flags struct in b #define DBM_FLAG_LARGE 128 // Flags added onto the flags struct in b
#define DBM_FLAG_ABM 64 #define DBM_FLAG_ABM 64
extern std::array<pig_bitmap_offset, MAX_BITMAP_FILES> GameBitmapOffset; extern enumerated_array<pig_bitmap_offset, MAX_BITMAP_FILES, bitmap_index> GameBitmapOffset;
void load_custom_data(const d_fname &level_file); void load_custom_data(const d_fname &level_file);
void custom_close(); void custom_close();
#endif #endif
#endif

View file

@ -382,9 +382,9 @@ void ogl_cache_polymodel_textures(const polygon_model_index model_num)
const unsigned last_texture = i + po.n_textures; const unsigned last_texture = i + po.n_textures;
for (; i != last_texture; ++i) for (; i != last_texture; ++i)
{ {
auto &objbitmap = ObjBitmaps[ObjBitmapPtrs[i]]; const auto objbitmap = ObjBitmaps[ObjBitmapPtrs[i]];
PIGGY_PAGE_IN(objbitmap); PIGGY_PAGE_IN(objbitmap);
ogl_loadbmtexture(GameBitmaps[objbitmap.index], 1); ogl_loadbmtexture(GameBitmaps[objbitmap], 1);
} }
} }
@ -392,10 +392,10 @@ void ogl_cache_polymodel_textures(const polygon_model_index model_num)
static void ogl_cache_vclip_textures(const vclip &vc) static void ogl_cache_vclip_textures(const vclip &vc)
{ {
range_for (auto &i, partial_const_range(vc.frames, vc.num_frames)) for (const auto i : partial_const_range(vc.frames, vc.num_frames))
{ {
PIGGY_PAGE_IN(i); PIGGY_PAGE_IN(i);
ogl_loadbmtexture(GameBitmaps[i.index], 0); ogl_loadbmtexture(GameBitmaps[i], 0);
} }
} }
@ -463,14 +463,14 @@ void ogl_cache_level_textures(void)
// tmap1=0; // tmap1=0;
continue; continue;
} }
auto &texture1 = Textures[tmap1idx]; const auto texture1 = Textures[tmap1idx];
PIGGY_PAGE_IN(texture1); PIGGY_PAGE_IN(texture1);
grs_bitmap *bm = &GameBitmaps[texture1.index]; grs_bitmap *bm = &GameBitmaps[texture1];
if (tmap2 != texture2_value::None) if (tmap2 != texture2_value::None)
{ {
const auto texture2 = Textures[get_texture_index(tmap2)]; const auto texture2 = Textures[get_texture_index(tmap2)];
PIGGY_PAGE_IN(texture2); PIGGY_PAGE_IN(texture2);
auto &bm2 = GameBitmaps[texture2.index]; auto &bm2 = GameBitmaps[texture2];
if (CGameArg.DbgUseOldTextureMerge || bm2.get_flag_mask(BM_FLAG_SUPER_TRANSPARENT)) if (CGameArg.DbgUseOldTextureMerge || bm2.get_flag_mask(BM_FLAG_SUPER_TRANSPARENT))
bm = &texmerge_get_cached_bitmap( tmap1, tmap2 ); bm = &texmerge_get_cached_bitmap( tmap1, tmap2 );
else { else {
@ -537,9 +537,9 @@ void ogl_cache_level_textures(void)
} }
if (objp->rtype.pobj_info.tmap_override != -1) if (objp->rtype.pobj_info.tmap_override != -1)
{ {
auto &t = Textures[objp->rtype.pobj_info.tmap_override]; const auto t = Textures[objp->rtype.pobj_info.tmap_override];
PIGGY_PAGE_IN(t); PIGGY_PAGE_IN(t);
ogl_loadbmtexture(GameBitmaps[t.index], 1); ogl_loadbmtexture(GameBitmaps[t], 1);
} }
else else
ogl_cache_polymodel_textures(objp->rtype.pobj_info.model_num); ogl_cache_polymodel_textures(objp->rtype.pobj_info.model_num);

View file

@ -497,7 +497,7 @@ window_event_result trigger_dialog::callback_handler(const d_event &event)
{ {
auto &t = Textures[get_texture_index(tmap_num)]; auto &t = Textures[get_texture_index(tmap_num)];
PIGGY_PAGE_IN(t); PIGGY_PAGE_IN(t);
gr_ubitmap(canvas, GameBitmaps[t.index]); gr_ubitmap(canvas, GameBitmaps[t]);
} else } else
gr_clear_canvas(canvas, CGREY); gr_clear_canvas(canvas, CGREY);
} }

View file

@ -612,9 +612,9 @@ window_event_result wall_dialog::callback_handler(const d_event &event)
if (framenum >= wa.num_frames) if (framenum >= wa.num_frames)
framenum=0; framenum=0;
const auto frame = wa.frames[framenum]; const auto frame = wa.frames[framenum];
auto &texture = Textures[frame]; const auto texture = Textures[frame];
PIGGY_PAGE_IN(texture); PIGGY_PAGE_IN(texture);
gr_ubitmap(*grd_curcanv, GameBitmaps[texture.index]); gr_ubitmap(*grd_curcanv, GameBitmaps[texture]);
} else { } else {
if (type == WALL_OPEN) if (type == WALL_OPEN)
gr_clear_canvas(*grd_curcanv, CBLACK); gr_clear_canvas(*grd_curcanv, CBLACK);
@ -624,9 +624,9 @@ window_event_result wall_dialog::callback_handler(const d_event &event)
if (curside.tmap_num2 != texture2_value::None) if (curside.tmap_num2 != texture2_value::None)
gr_ubitmap(*grd_curcanv, texmerge_get_cached_bitmap(tmap_num, curside.tmap_num2)); gr_ubitmap(*grd_curcanv, texmerge_get_cached_bitmap(tmap_num, curside.tmap_num2));
else { else {
auto &texture1 = Textures[get_texture_index(tmap_num)]; const auto texture1 = Textures[get_texture_index(tmap_num)];
PIGGY_PAGE_IN(texture1); PIGGY_PAGE_IN(texture1);
gr_ubitmap(*grd_curcanv, GameBitmaps[texture1.index]); gr_ubitmap(*grd_curcanv, GameBitmaps[texture1]);
} }
} }
} }

View file

@ -86,13 +86,13 @@ void draw_object_picture(grs_canvas &canvas, const unsigned id, const vms_angvec
case OBJ_HOSTAGE: case OBJ_HOSTAGE:
PIGGY_PAGE_IN(Vclip[Hostage_vclip_num[id]].frames[0]); PIGGY_PAGE_IN(Vclip[Hostage_vclip_num[id]].frames[0]);
gr_bitmap(canvas, 0, 0, GameBitmaps[Vclip[Hostage_vclip_num[id]].frames[0].index]); gr_bitmap(canvas, 0, 0, GameBitmaps[Vclip[Hostage_vclip_num[id]].frames[0]]);
break; break;
case OBJ_POWERUP: case OBJ_POWERUP:
if ( Powerup_info[id].vclip_num > -1 ) { if ( Powerup_info[id].vclip_num > -1 ) {
PIGGY_PAGE_IN(Vclip[Powerup_info[id].vclip_num].frames[0]); PIGGY_PAGE_IN(Vclip[Powerup_info[id].vclip_num].frames[0]);
gr_bitmap(canvas, 0, 0, GameBitmaps[Vclip[Powerup_info[id].vclip_num].frames[0].index]); gr_bitmap(canvas, 0, 0, GameBitmaps[Vclip[Powerup_info[id].vclip_num].frames[0]]);
} }
break; break;

View file

@ -94,7 +94,7 @@ static void texpage_redraw()
if (i + TexturePage*TMAPS_PER_PAGE < NumTextures) if (i + TexturePage*TMAPS_PER_PAGE < NumTextures)
{ {
PIGGY_PAGE_IN(Textures[i + TexturePage*TMAPS_PER_PAGE]); PIGGY_PAGE_IN(Textures[i + TexturePage*TMAPS_PER_PAGE]);
gr_ubitmap(*grd_curcanv, GameBitmaps[Textures[i + TexturePage*TMAPS_PER_PAGE].index]); gr_ubitmap(*grd_curcanv, GameBitmaps[Textures[i + TexturePage * TMAPS_PER_PAGE]]);
} else } else
gr_clear_canvas(*grd_curcanv, CGREY); gr_clear_canvas(*grd_curcanv, CGREY);
} }
@ -109,7 +109,7 @@ static void texpage_show_current()
const auto ct = CurrentTexture; const auto ct = CurrentTexture;
auto &t = Textures[ct]; auto &t = Textures[ct];
PIGGY_PAGE_IN(t); PIGGY_PAGE_IN(t);
gr_ubitmap(*grd_curcanv, GameBitmaps[t.index]); gr_ubitmap(*grd_curcanv, GameBitmaps[t]);
texpage_print_name(TmapInfo[ct].filename); texpage_print_name(TmapInfo[ct].filename);
} }

View file

@ -430,7 +430,7 @@ static void bm_free_extra_objbitmaps()
for (i = Num_bitmap_files; i < extra_bitmap_num; i++) for (i = Num_bitmap_files; i < extra_bitmap_num; i++)
{ {
N_ObjBitmaps--; N_ObjBitmaps--;
d_free(GameBitmaps[i].bm_mdata); d_free(GameBitmaps[(bitmap_index{static_cast<uint16_t>(i)})].bm_mdata);
} }
extra_bitmap_num = Num_bitmap_files; extra_bitmap_num = Num_bitmap_files;
Exit_bitmaps_loaded = false; Exit_bitmaps_loaded = false;
@ -659,7 +659,7 @@ static grs_bitmap *bm_load_extra_objbitmap(const char *name)
{ {
auto &bitmap_idx = ObjBitmaps[oi]; auto &bitmap_idx = ObjBitmaps[oi];
const auto bitmap_store_index = bitmap_index{static_cast<uint16_t>(extra_bitmap_num)}; const auto bitmap_store_index = bitmap_index{static_cast<uint16_t>(extra_bitmap_num)};
grs_bitmap &n = GameBitmaps[bitmap_store_index.index]; grs_bitmap &n = GameBitmaps[bitmap_store_index];
if (!read_extra_bitmap_iff(name, n)) if (!read_extra_bitmap_iff(name, n))
{ {
const char *const dot = strrchr(name, '.'); const char *const dot = strrchr(name, '.');
@ -684,7 +684,7 @@ static void bm_unload_last_objbitmaps(unsigned count)
unsigned new_N_ObjBitmaps = N_ObjBitmaps - count; unsigned new_N_ObjBitmaps = N_ObjBitmaps - count;
range_for (auto &o, partial_range(ObjBitmaps, new_N_ObjBitmaps, N_ObjBitmaps)) range_for (auto &o, partial_range(ObjBitmaps, new_N_ObjBitmaps, N_ObjBitmaps))
d_free(GameBitmaps[o.index].bm_mdata); d_free(GameBitmaps[o].bm_mdata);
N_ObjBitmaps = new_N_ObjBitmaps; N_ObjBitmaps = new_N_ObjBitmaps;
} }

View file

@ -306,7 +306,7 @@ static void ab_load(int skip, const char * filename, std::array<bitmap_index, MA
#if defined(DXX_BUILD_DESCENT_I) #if defined(DXX_BUILD_DESCENT_I)
bmp[0] = piggy_register_bitmap(bogus_bitmap, "bogus", 0); bmp[0] = piggy_register_bitmap(bogus_bitmap, "bogus", 0);
#elif defined(DXX_BUILD_DESCENT_II) #elif defined(DXX_BUILD_DESCENT_II)
bmp[0].index = 0; //index of bogus bitmap==0 (I think) //&bogus_bitmap; bmp[0] = {}; //index of bogus bitmap==0 (I think) //&bogus_bitmap;
#endif #endif
*nframes = 1; *nframes = 1;
return; return;
@ -330,7 +330,7 @@ static void ab_load(int skip, const char * filename, std::array<bitmap_index, MA
const auto len = snprintf(tempname.data(), tempname.size(), "%.*s#%d", DXX_ptrdiff_cast_int(path.base_end - path.base_start), path.base_start, i); const auto len = snprintf(tempname.data(), tempname.size(), "%.*s#%d", DXX_ptrdiff_cast_int(path.base_end - path.base_start), path.base_start, i);
#endif #endif
const auto bi = piggy_find_bitmap(std::span<const char>(tempname.data(), len)); const auto bi = piggy_find_bitmap(std::span<const char>(tempname.data(), len));
if ( !bi.index ) if (bi == bitmap_index{})
break; break;
bmp[i] = bi; bmp[i] = bi;
} }
@ -793,7 +793,7 @@ int gamedata_read_tbl(d_level_shared_robot_info_state &LevelSharedRobotInfoState
LevelUniqueTmapInfoState.Num_tmaps = tmap_count; LevelUniqueTmapInfoState.Num_tmaps = tmap_count;
#if defined(DXX_BUILD_DESCENT_II) #if defined(DXX_BUILD_DESCENT_II)
Textures[NumTextures++].index = 0; //entry for bogus tmap Textures[NumTextures++] = {}; //entry for bogus tmap
InfoFile.reset(); InfoFile.reset();
#endif #endif
assert(LevelSharedRobotInfoState.N_robot_types == Num_robot_ais); //should be one ai info per robot assert(LevelSharedRobotInfoState.N_robot_types == Num_robot_ais); //should be one ai info per robot
@ -839,7 +839,7 @@ void verify_textures()
const auto Num_tmaps = LevelUniqueTmapInfoState.Num_tmaps; const auto Num_tmaps = LevelUniqueTmapInfoState.Num_tmaps;
for (uint_fast32_t i = 0; i < Num_tmaps; ++i) for (uint_fast32_t i = 0; i < Num_tmaps; ++i)
{ {
bmp = &GameBitmaps[Textures[i].index]; bmp = &GameBitmaps[Textures[i]];
if ( (bmp->bm_w!=64)||(bmp->bm_h!=64)||(bmp->bm_rowsize!=64) ) { if ( (bmp->bm_w!=64)||(bmp->bm_h!=64)||(bmp->bm_rowsize!=64) ) {
j++; j++;
} }
@ -851,8 +851,9 @@ void verify_textures()
for (uint_fast32_t i = 0; i < Num_effects; ++i) for (uint_fast32_t i = 0; i < Num_effects; ++i)
if (const auto changing_object_texture = Effects[i].changing_object_texture; changing_object_texture != object_bitmap_index::None) if (const auto changing_object_texture = Effects[i].changing_object_texture; changing_object_texture != object_bitmap_index::None)
{ {
const auto &o = ObjBitmaps[changing_object_texture].index; const auto o = ObjBitmaps[changing_object_texture];
if (GameBitmaps[o].bm_w != 64 || GameBitmaps[o].bm_h != 64) auto &gbo = GameBitmaps[o];
if (gbo.bm_w != 64 || gbo.bm_h != 64)
Error("Effect %" PRIuFAST32 " is used on object, but is not 64x64",i); Error("Effect %" PRIuFAST32 " is used on object, but is not 64x64",i);
} }
#endif #endif
@ -931,7 +932,7 @@ static void bm_read_eclip(int skip)
Assert(texture_count < MAX_TEXTURES); Assert(texture_count < MAX_TEXTURES);
NumTextures = texture_count; NumTextures = texture_count;
} }
else if (Textures[i].index == 0) //was found, but registered out else if (Textures[i] == bitmap_index{}) //was found, but registered out
Textures[i] = bm_load_sub(skip, dest_bm); Textures[i] = bm_load_sub(skip, dest_bm);
dest_bm_num = i; dest_bm_num = i;
} }
@ -947,7 +948,7 @@ static void bm_read_eclip(int skip)
Assert(clip_count < frames); Assert(clip_count < frames);
Effects[clip_num].vc.frames[clip_count] = bitmap; Effects[clip_num].vc.frames[clip_count] = bitmap;
set_lighting_flag(GameBitmaps[bitmap.index]); set_lighting_flag(GameBitmaps[bitmap]);
Assert(!obj_eclip); //obj eclips for non-abm files not supported! Assert(!obj_eclip); //obj eclips for non-abm files not supported!
Assert(crit_flag==0); Assert(crit_flag==0);
@ -976,7 +977,7 @@ static void bm_read_eclip(int skip)
Effects[clip_num].vc.frame_time = Effects[clip_num].vc.play_time/Effects[clip_num].vc.num_frames; Effects[clip_num].vc.frame_time = Effects[clip_num].vc.play_time/Effects[clip_num].vc.num_frames;
clip_count = 0; clip_count = 0;
set_lighting_flag(GameBitmaps[bm[clip_count].index]); set_lighting_flag(GameBitmaps[bm[clip_count]]);
Effects[clip_num].vc.frames[clip_count] = bm[clip_count]; Effects[clip_num].vc.frames[clip_count] = bm[clip_count];
if (!obj_eclip && !crit_flag) { if (!obj_eclip && !crit_flag) {
@ -1005,7 +1006,7 @@ static void bm_read_eclip(int skip)
//if for an object, Effects_bm_ptrs set in object load //if for an object, Effects_bm_ptrs set in object load
for(clip_count=1;clip_count < Effects[clip_num].vc.num_frames; clip_count++) { for(clip_count=1;clip_count < Effects[clip_num].vc.num_frames; clip_count++) {
set_lighting_flag(GameBitmaps[bm[clip_count].index]); set_lighting_flag(GameBitmaps[bm[clip_count]]);
Effects[clip_num].vc.frames[clip_count] = bm[clip_count]; Effects[clip_num].vc.frames[clip_count] = bm[clip_count];
} }
@ -1130,7 +1131,7 @@ static void bm_read_wclip(int skip)
wa.open_sound = wall_open_sound; wa.open_sound = wall_open_sound;
wa.close_sound = wall_close_sound; wa.close_sound = wall_close_sound;
Textures[texture_count] = bitmap; Textures[texture_count] = bitmap;
set_lighting_flag(GameBitmaps[bitmap.index]); set_lighting_flag(GameBitmaps[bitmap]);
set_texture_name( arg ); set_texture_name( arg );
Assert(texture_count < MAX_TEXTURES); Assert(texture_count < MAX_TEXTURES);
texture_count++; texture_count++;
@ -1157,11 +1158,11 @@ static void bm_read_wclip(int skip)
if (clip_num >= Num_wall_anims) Num_wall_anims = clip_num+1; if (clip_num >= Num_wall_anims) Num_wall_anims = clip_num+1;
set_lighting_flag(GameBitmaps[bm[clip_count].index]); set_lighting_flag(GameBitmaps[bm[clip_count]]);
for (clip_count=0;clip_count < wa.num_frames; clip_count++) { for (clip_count=0;clip_count < wa.num_frames; clip_count++) {
Textures[texture_count] = bm[clip_count]; Textures[texture_count] = bm[clip_count];
set_lighting_flag(GameBitmaps[bm[clip_count].index]); set_lighting_flag(GameBitmaps[bm[clip_count]]);
wa.frames[clip_count] = texture_count; wa.frames[clip_count] = texture_count;
REMOVE_DOTS(arg); REMOVE_DOTS(arg);
snprintf(&TmapInfo[texture_count].filename[0u], TmapInfo[texture_count].filename.size(), "%s#%d", arg, clip_count); snprintf(&TmapInfo[texture_count].filename[0u], TmapInfo[texture_count].filename.size(), "%s#%d", arg, clip_count);
@ -1194,7 +1195,7 @@ static void bm_read_vclip(d_vclip_array &Vclip, int skip)
Vclip[clip_num].frame_time = fl2f(play_time)/frames; Vclip[clip_num].frame_time = fl2f(play_time)/frames;
Vclip[clip_num].light_value = fl2f(vlighting); Vclip[clip_num].light_value = fl2f(vlighting);
Vclip[clip_num].sound_num = sound_num; Vclip[clip_num].sound_num = sound_num;
set_lighting_flag(GameBitmaps[bi.index]); set_lighting_flag(GameBitmaps[bi]);
Assert(clip_count < frames); Assert(clip_count < frames);
Vclip[clip_num].frames[clip_count++] = bi; Vclip[clip_num].frames[clip_count++] = bi;
if (rod_flag) { if (rod_flag) {
@ -1218,10 +1219,10 @@ static void bm_read_vclip(d_vclip_array &Vclip, int skip)
Vclip[clip_num].frame_time = fl2f(play_time)/Vclip[clip_num].num_frames; Vclip[clip_num].frame_time = fl2f(play_time)/Vclip[clip_num].num_frames;
Vclip[clip_num].light_value = fl2f(vlighting); Vclip[clip_num].light_value = fl2f(vlighting);
Vclip[clip_num].sound_num = sound_num; Vclip[clip_num].sound_num = sound_num;
set_lighting_flag(GameBitmaps[bm[clip_count].index]); set_lighting_flag(GameBitmaps[bm[clip_count]]);
for (clip_count=0;clip_count < Vclip[clip_num].num_frames; clip_count++) { for (clip_count=0;clip_count < Vclip[clip_num].num_frames; clip_count++) {
set_lighting_flag(GameBitmaps[bm[clip_count].index]); set_lighting_flag(GameBitmaps[bm[clip_count]]);
Vclip[clip_num].frames[clip_count] = bm[clip_count]; Vclip[clip_num].frames[clip_count] = bm[clip_count];
} }
} }
@ -1428,7 +1429,8 @@ static grs_bitmap *load_polymodel_bitmap(int skip, const char *name)
auto &ob = ObjBitmaps[oi]; auto &ob = ObjBitmaps[oi];
ob = loaded_value; ob = loaded_value;
#if defined(DXX_BUILD_DESCENT_II) #if defined(DXX_BUILD_DESCENT_II)
if (GameBitmaps[ob.index].bm_w != 64 || GameBitmaps[ob.index].bm_h != 64) auto &gbo = GameBitmaps[ob];
if (gbo.bm_w != 64 || gbo.bm_h != 64)
Error("Bitmap <%s> is not 64x64",name); Error("Bitmap <%s> is not 64x64",name);
#endif #endif
ObjBitmapPtrs[N_ObjBitmapPtrs++] = oi; ObjBitmapPtrs[N_ObjBitmapPtrs++] = oi;
@ -1437,7 +1439,7 @@ static grs_bitmap *load_polymodel_bitmap(int skip, const char *name)
assert(N_ObjBitmaps < ObjBitmaps.size()); assert(N_ObjBitmaps < ObjBitmaps.size());
assert(N_ObjBitmapPtrs < ObjBitmapPtrs.size()); assert(N_ObjBitmapPtrs < ObjBitmapPtrs.size());
#endif #endif
return &GameBitmaps[ob.index]; return &GameBitmaps[ob];
} }
} }
@ -2261,9 +2263,9 @@ void bm_read_weapon(int skip, int unused_flag)
Weapon_info[n].po_len_to_width_ratio = F1_0*10; Weapon_info[n].po_len_to_width_ratio = F1_0*10;
Weapon_info[n].picture.index = 0; Weapon_info[n].picture = {};
#if defined(DXX_BUILD_DESCENT_II) #if defined(DXX_BUILD_DESCENT_II)
Weapon_info[n].hires_picture.index = 0; Weapon_info[n].hires_picture = {};
#endif #endif
Weapon_info[n].homing_flag = 0; Weapon_info[n].homing_flag = 0;

View file

@ -602,7 +602,7 @@ int check_effect_blowup(const d_level_shared_destructible_light_state &LevelShar
{ {
const auto tmf = get_texture_rotation_high(tmap2); //tm flags const auto tmf = get_texture_rotation_high(tmap2); //tm flags
auto &texture2 = Textures[tm]; auto &texture2 = Textures[tm];
const grs_bitmap *bm = &GameBitmaps[texture2.index]; const grs_bitmap *bm = &GameBitmaps[texture2];
int x=0,y=0,t; int x=0,y=0,t;
PIGGY_PAGE_IN(texture2); PIGGY_PAGE_IN(texture2);

View file

@ -68,12 +68,12 @@ COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
namespace dsx { namespace dsx {
namespace { namespace {
#if defined(DXX_BUILD_DESCENT_I) #if defined(DXX_BUILD_DESCENT_I)
using perm_tmap_buffer_type = std::array<int, MAX_TEXTURES>; using perm_tmap_buffer_type = enumerated_array<int, MAX_TEXTURES, bitmap_index>;
using level_tmap_buffer_type = std::array<int8_t, MAX_TEXTURES>; using level_tmap_buffer_type = enumerated_array<int8_t, MAX_TEXTURES, bitmap_index>;
using wall_buffer_type = std::array<int, MAX_WALL_ANIMS>; using wall_buffer_type = std::array<int, MAX_WALL_ANIMS>;
#elif defined(DXX_BUILD_DESCENT_II) #elif defined(DXX_BUILD_DESCENT_II)
using perm_tmap_buffer_type = std::array<int, MAX_BITMAP_FILES>; using perm_tmap_buffer_type = enumerated_array<int, MAX_BITMAP_FILES, bitmap_index>;
using level_tmap_buffer_type = std::array<int8_t, MAX_BITMAP_FILES>; using level_tmap_buffer_type = enumerated_array<int8_t, MAX_BITMAP_FILES, bitmap_index>;
using wall_buffer_type = std::array<int, MAX_BITMAP_FILES>; using wall_buffer_type = std::array<int, MAX_BITMAP_FILES>;
#endif #endif
} }
@ -772,9 +772,7 @@ static void determine_used_textures_level(int load_level_flag, int shareware_fla
wall_buf[clip_num] = 1; wall_buf[clip_num] = 1;
for (j=0; j<num_frames; j++) { for (j=0; j<num_frames; j++) {
int tmap_num; const bitmap_index tmap_num{WallAnims[clip_num].frames[j]};
tmap_num = WallAnims[clip_num].frames[j];
tmap_buf[tmap_num]++; tmap_buf[tmap_num]++;
if (level_tmap_buf[tmap_num] == -1) if (level_tmap_buf[tmap_num] == -1)
level_tmap_buf[tmap_num] = level_num + (!shareware_flag) * NUM_SHAREWARE_LEVELS; level_tmap_buf[tmap_num] = level_num + (!shareware_flag) * NUM_SHAREWARE_LEVELS;
@ -783,8 +781,7 @@ static void determine_used_textures_level(int load_level_flag, int shareware_fla
} }
auto &uside = std::get<1>(z); auto &uside = std::get<1>(z);
const auto tmap1idx = get_texture_index(uside.tmap_num); if (const bitmap_index tmap1idx{get_texture_index(uside.tmap_num)}; underlying_value(tmap1idx) < max_tmap)
if (tmap1idx < max_tmap)
{ {
++ tmap_buf[tmap1idx]; ++ tmap_buf[tmap1idx];
if (auto &t = level_tmap_buf[tmap1idx]; t == -1) if (auto &t = level_tmap_buf[tmap1idx]; t == -1)
@ -795,9 +792,9 @@ static void determine_used_textures_level(int load_level_flag, int shareware_fla
Int3(); // Error, bogus texture map. Should not be greater than max_tmap. Int3(); // Error, bogus texture map. Should not be greater than max_tmap.
} }
if (const auto tmap_num2 = get_texture_index(uside.tmap_num2)) if (const bitmap_index tmap_num2{get_texture_index(uside.tmap_num2)}; tmap_num2 != bitmap_index{})
{ {
if (tmap_num2 < max_tmap) { if (underlying_value(tmap_num2) < max_tmap) {
++tmap_buf[tmap_num2]; ++tmap_buf[tmap_num2];
if (level_tmap_buf[tmap_num2] == -1) if (level_tmap_buf[tmap_num2] == -1)
level_tmap_buf[tmap_num2] = level_num + (!shareware_flag) * NUM_SHAREWARE_LEVELS; level_tmap_buf[tmap_num2] = level_num + (!shareware_flag) * NUM_SHAREWARE_LEVELS;
@ -822,13 +819,12 @@ static void determine_used_textures_level(int load_level_flag, int shareware_fla
for (unsigned i = 0; i < po->n_textures; ++i) for (unsigned i = 0; i < po->n_textures; ++i)
{ {
unsigned tli = ObjBitmaps[ObjBitmapPtrs[po->first_texture+i]].index; const auto tli = ObjBitmaps[ObjBitmapPtrs[po->first_texture + i]];
if (tmap_buf.valid_index(tli))
if (tli < tmap_buf.size())
{ {
tmap_buf[tli]++; tmap_buf[tli]++;
if (level_tmap_buf[tli] == -1) if (auto &ltb = level_tmap_buf[tli]; ltb == -1)
level_tmap_buf[tli] = level_num; ltb = level_num;
} else } else
Int3(); // Hmm, It seems this texture is bogus! Int3(); // Hmm, It seems this texture is bogus!
} }
@ -856,22 +852,22 @@ static void determine_used_textures_level(int load_level_flag, int shareware_fla
wall_buf[clip_num] = 1; wall_buf[clip_num] = 1;
for (j=0; j<1; j++) { // Used to do through num_frames, but don't really want all the door01#3 stuff. for (j=0; j<1; j++) { // Used to do through num_frames, but don't really want all the door01#3 stuff.
unsigned tmap_num = Textures[WallAnims[clip_num].frames[j]].index; const auto tmap_num = Textures[WallAnims[clip_num].frames[j]];
Assert(tmap_num < tmap_buf.size()); assert(tmap_buf.valid_index(tmap_num));
tmap_buf[tmap_num]++; tmap_buf[tmap_num]++;
if (level_tmap_buf[tmap_num] == -1) if (auto &ltb = level_tmap_buf[tmap_num]; ltb == -1)
level_tmap_buf[tmap_num] = level_num; ltb = level_num;
} }
} }
} else if (child == segment_none) { } else if (child == segment_none) {
{ {
const auto tmap1idx = get_texture_index(uside.tmap_num); const auto tmap1idx = get_texture_index(uside.tmap_num);
if (tmap1idx < Textures.size()) { if (tmap1idx < Textures.size()) {
const auto ti = Textures[tmap1idx].index; const auto ti = Textures[tmap1idx];
assert(ti < tmap_buf.size()); assert(tmap_buf.valid_index(ti));
++tmap_buf[ti]; ++tmap_buf[ti];
if (level_tmap_buf[ti] == -1) if (auto &ltb = level_tmap_buf[ti]; ltb == -1)
level_tmap_buf[ti] = level_num; ltb = level_num;
} else } else
Int3(); // Error, bogus texture map. Should not be greater than max_tmap. Int3(); // Error, bogus texture map. Should not be greater than max_tmap.
} }
@ -880,8 +876,8 @@ static void determine_used_textures_level(int load_level_flag, int shareware_fla
{ {
if (masked_tmap_num2 < Textures.size()) if (masked_tmap_num2 < Textures.size())
{ {
const auto ti = Textures[masked_tmap_num2].index; const auto ti = Textures[masked_tmap_num2];
assert(ti < tmap_buf.size()); assert(tmap_buf.valid_index(ti));
++tmap_buf[ti]; ++tmap_buf[ti];
if (level_tmap_buf[ti] == -1) if (level_tmap_buf[ti] == -1)
level_tmap_buf[ti] = level_num; level_tmap_buf[ti] = level_num;
@ -914,21 +910,26 @@ namespace dsx {
namespace { namespace {
static void say_used_tmaps(PHYSFS_File *const my_file, const perm_tmap_buffer_type &tb) static void say_used_tmaps(PHYSFS_File *const my_file, const perm_tmap_buffer_type &tb)
{ {
int i;
#if defined(DXX_BUILD_DESCENT_I) #if defined(DXX_BUILD_DESCENT_I)
int count = 0; int count = 0;
auto &TmapInfo = LevelUniqueTmapInfoState.TmapInfo; auto &TmapInfo = LevelUniqueTmapInfoState.TmapInfo;
const auto Num_tmaps = LevelUniqueTmapInfoState.Num_tmaps; const auto Num_tmaps = LevelUniqueTmapInfoState.Num_tmaps;
for (i=0; i<Num_tmaps; i++) for (const uint16_t i : xrange(Num_tmaps))
if (tb[i]) { {
PHYSFSX_printf(my_file, "[%3i %8s (%4i)]%s", i, static_cast<const char *>(TmapInfo[i].filename), tb[i], count++ >= 4 ? (count = 0, "\n") : " "); const bitmap_index bi{i};
if (tb[bi]) {
PHYSFSX_printf(my_file, "[%3i %8s (%4i)]%s", i, TmapInfo[i].filename.data(), tb[bi], count++ >= 4 ? (count = 0, "\n") : " ");
} }
}
#elif defined(DXX_BUILD_DESCENT_II) #elif defined(DXX_BUILD_DESCENT_II)
for (i = 0; i < tb.size(); ++i) for (const uint16_t i : xrange(std::size(tb)))
if (tb[i]) { {
PHYSFSX_printf(my_file, "[%3i %8s (%4i)]\n", i, AllBitmaps[i].name.data(), tb[i]); const bitmap_index bi{i};
if (tb[bi]) {
PHYSFSX_printf(my_file, "[%3i %8s (%4i)]\n", i, AllBitmaps[bi].name.data(), tb[bi]);
} }
}
#endif #endif
} }
@ -936,14 +937,16 @@ static void say_used_tmaps(PHYSFS_File *const my_file, const perm_tmap_buffer_ty
// ----------------------------------------------------------------------------- // -----------------------------------------------------------------------------
static void say_used_once_tmaps(PHYSFS_File *const my_file, const perm_tmap_buffer_type &tb, const level_tmap_buffer_type &tb_lnum) static void say_used_once_tmaps(PHYSFS_File *const my_file, const perm_tmap_buffer_type &tb, const level_tmap_buffer_type &tb_lnum)
{ {
int i;
const char *level_name; const char *level_name;
auto &TmapInfo = LevelUniqueTmapInfoState.TmapInfo; auto &TmapInfo = LevelUniqueTmapInfoState.TmapInfo;
const auto Num_tmaps = LevelUniqueTmapInfoState.Num_tmaps; const auto Num_tmaps = LevelUniqueTmapInfoState.Num_tmaps;
for (i=0; i<Num_tmaps; i++) for (const uint16_t i : xrange(Num_tmaps))
if (tb[i] == 1) { {
int level_num = tb_lnum[i]; const bitmap_index bi{i};
if (tb[bi] == 1)
{
const auto level_num = tb_lnum[bi];
if (level_num >= NUM_SHAREWARE_LEVELS) { if (level_num >= NUM_SHAREWARE_LEVELS) {
Assert((level_num - NUM_SHAREWARE_LEVELS >= 0) && (level_num - NUM_SHAREWARE_LEVELS < NUM_REGISTERED_LEVELS)); Assert((level_num - NUM_SHAREWARE_LEVELS >= 0) && (level_num - NUM_SHAREWARE_LEVELS < NUM_REGISTERED_LEVELS));
level_name = Registered_level_names[level_num - NUM_SHAREWARE_LEVELS]; level_name = Registered_level_names[level_num - NUM_SHAREWARE_LEVELS];
@ -954,6 +957,7 @@ static void say_used_once_tmaps(PHYSFS_File *const my_file, const perm_tmap_buff
PHYSFSX_printf(my_file, "Texture %3i %8s used only once on level %s\n", i, static_cast<const char *>(TmapInfo[i].filename), level_name); PHYSFSX_printf(my_file, "Texture %3i %8s used only once on level %s\n", i, static_cast<const char *>(TmapInfo[i].filename), level_name);
} }
}
} }
#endif #endif
@ -972,7 +976,7 @@ static void say_unused_tmaps(PHYSFS_File *my_file, perm_tmap_buffer_type &perm_t
for (auto &&[i, tb, texture, tmap_name] : enumerate(zip(partial_range(perm_tmap_buf, bound), Textures, tmap_name_source))) for (auto &&[i, tb, texture, tmap_name] : enumerate(zip(partial_range(perm_tmap_buf, bound), Textures, tmap_name_source)))
if (!tb) if (!tb)
{ {
const char usage_indicator = (GameBitmaps[texture.index].bm_data == bogus_data.data()) const char usage_indicator = (GameBitmaps[texture].bm_data == bogus_data.data())
? 'U' ? 'U'
: ' '; : ' ';

View file

@ -1214,7 +1214,7 @@ int check_trans_wall(const vms_vector &pnt, const vcsegptridx_t seg, const siden
: ( [tmap_num]() -> const grs_bitmap & { : ( [tmap_num]() -> const grs_bitmap & {
auto &texture1 = Textures[get_texture_index(tmap_num)]; auto &texture1 = Textures[get_texture_index(tmap_num)];
PIGGY_PAGE_IN(texture1); PIGGY_PAGE_IN(texture1);
return GameBitmaps[texture1.index]; return GameBitmaps[texture1];
} () ); } () );
const auto bm = rle_expand_texture(rbm); const auto bm = rle_expand_texture(rbm);

View file

@ -292,9 +292,9 @@ void init_cockpit()
#endif #endif
cockpit_mode_t::rear_view; cockpit_mode_t::rear_view;
auto &cb = cockpit_bitmap[mode]; const auto cb = cockpit_bitmap[mode];
PIGGY_PAGE_IN(cb); PIGGY_PAGE_IN(cb);
auto &bm = GameBitmaps[cb.index]; auto &bm = GameBitmaps[cb];
gr_bitblt_find_transparent_area(bm, x1, y1, x2, y2); gr_bitblt_find_transparent_area(bm, x1, y1, x2, y2);
game_init_render_sub_buffers(canvas, x1 * (static_cast<float>(SWIDTH) / bm.bm_w), y1 * (static_cast<float>(SHEIGHT) / bm.bm_h), (x2 - x1 + 1) * (static_cast<float>(SWIDTH) / bm.bm_w), (y2 - y1 + 2) * (static_cast<float>(SHEIGHT) / bm.bm_h)); game_init_render_sub_buffers(canvas, x1 * (static_cast<float>(SWIDTH) / bm.bm_w), y1 * (static_cast<float>(SHEIGHT) / bm.bm_h), (x2 - x1 + 1) * (static_cast<float>(SWIDTH) / bm.bm_w), (y2 - y1 + 2) * (static_cast<float>(SHEIGHT) / bm.bm_h));
break; break;

View file

@ -933,7 +933,6 @@ namespace {
// This actually renders the new cockpit onto the screen. // This actually renders the new cockpit onto the screen.
static void update_cockpits(grs_canvas &canvas) static void update_cockpits(grs_canvas &canvas)
{ {
grs_bitmap *bm;
const auto raw_cockpit_mode = PlayerCfg.CockpitMode[1]; const auto raw_cockpit_mode = PlayerCfg.CockpitMode[1];
auto mode = auto mode =
#if defined(DXX_BUILD_DESCENT_II) #if defined(DXX_BUILD_DESCENT_II)
@ -946,26 +945,32 @@ static void update_cockpits(grs_canvas &canvas)
switch( PlayerCfg.CockpitMode[1] ) { switch( PlayerCfg.CockpitMode[1] ) {
case cockpit_mode_t::full_cockpit: case cockpit_mode_t::full_cockpit:
case cockpit_mode_t::rear_view: case cockpit_mode_t::rear_view:
PIGGY_PAGE_IN(cockpit_bitmap[mode]); {
bm=&GameBitmaps[cockpit_bitmap[mode].index]; const auto bi = cockpit_bitmap[mode];
PIGGY_PAGE_IN(bi);
grs_bitmap *const bm = &GameBitmaps[bi];
#if DXX_USE_OGL #if DXX_USE_OGL
ogl_ubitmapm_cs(canvas, 0, 0, opengl_bitmap_use_dst_canvas, opengl_bitmap_use_dst_canvas, *bm, 255); ogl_ubitmapm_cs(canvas, 0, 0, opengl_bitmap_use_dst_canvas, opengl_bitmap_use_dst_canvas, *bm, 255);
#else #else
gr_ubitmapm(canvas, 0, 0, *bm); gr_ubitmapm(canvas, 0, 0, *bm);
#endif #endif
}
break; break;
case cockpit_mode_t::full_screen: case cockpit_mode_t::full_screen:
break; break;
case cockpit_mode_t::status_bar: case cockpit_mode_t::status_bar:
PIGGY_PAGE_IN(cockpit_bitmap[mode]); {
bm=&GameBitmaps[cockpit_bitmap[mode].index]; const auto bi = cockpit_bitmap[mode];
PIGGY_PAGE_IN(bi);
grs_bitmap *const bm = &GameBitmaps[bi];
#if DXX_USE_OGL #if DXX_USE_OGL
ogl_ubitmapm_cs(canvas, 0, (HIRESMODE ? (SHEIGHT * 2) / 2.6 : (SHEIGHT * 2) / 2.72), opengl_bitmap_use_dst_canvas, (static_cast<int>(static_cast<double>(bm->bm_h) * (HIRESMODE ? static_cast<double>(SHEIGHT) / 480 : static_cast<double>(SHEIGHT) / 200) + 0.5)), *bm, 255); ogl_ubitmapm_cs(canvas, 0, (HIRESMODE ? (SHEIGHT * 2) / 2.6 : (SHEIGHT * 2) / 2.72), opengl_bitmap_use_dst_canvas, (static_cast<int>(static_cast<double>(bm->bm_h) * (HIRESMODE ? static_cast<double>(SHEIGHT) / 480 : static_cast<double>(SHEIGHT) / 200) + 0.5)), *bm, 255);
#else #else
gr_ubitmapm(canvas, 0, SHEIGHT - bm->bm_h, *bm); gr_ubitmapm(canvas, 0, SHEIGHT - bm->bm_h, *bm);
#endif #endif
}
break; break;
case cockpit_mode_t::letterbox: case cockpit_mode_t::letterbox:

View file

@ -251,7 +251,7 @@ union weapon_index
#define SB_SECONDARY_W_BOX_RIGHT_L (SB_SECONDARY_W_BOX_LEFT_L+54) #define SB_SECONDARY_W_BOX_RIGHT_L (SB_SECONDARY_W_BOX_LEFT_L+54)
#define SB_SECONDARY_W_BOX_BOT_L (153+42) #define SB_SECONDARY_W_BOX_BOT_L (153+42)
#define SB_SECONDARY_AMMO_X (SB_SECONDARY_W_BOX_LEFT + (multires_gauge_graphic.get(14, 11))) //(212+9) #define SB_SECONDARY_AMMO_X (SB_SECONDARY_W_BOX_LEFT + (multires_gauge_graphic.get(14, 11))) //(212+9)
#define GET_GAUGE_INDEX(x) (Gauges[x].index) #define GET_GAUGE_INDEX(x) (Gauges[x])
#elif defined(DXX_BUILD_DESCENT_II) #elif defined(DXX_BUILD_DESCENT_II)
#define AFTERBURNER_GAUGE_X_L 45-1 #define AFTERBURNER_GAUGE_X_L 45-1
@ -295,7 +295,7 @@ union weapon_index
#define SB_SECONDARY_W_BOX_RIGHT_L (SB_SECONDARY_W_BOX_LEFT_L+54+1) #define SB_SECONDARY_W_BOX_RIGHT_L (SB_SECONDARY_W_BOX_LEFT_L+54+1)
#define SB_SECONDARY_W_BOX_BOT_L (SB_SECONDARY_W_BOX_TOP_L+43) #define SB_SECONDARY_W_BOX_BOT_L (SB_SECONDARY_W_BOX_TOP_L+43)
#define SB_SECONDARY_AMMO_X (SB_SECONDARY_W_BOX_LEFT + (multires_gauge_graphic.get(14 - 4, 11))) //(212+9) #define SB_SECONDARY_AMMO_X (SB_SECONDARY_W_BOX_LEFT + (multires_gauge_graphic.get(14 - 4, 11))) //(212+9)
#define GET_GAUGE_INDEX(x) ((multires_gauge_graphic.rget(Gauges_hires, Gauges)[x].index)) #define GET_GAUGE_INDEX(x) ((multires_gauge_graphic.rget(Gauges_hires, Gauges)[x]))
#endif #endif
@ -2188,9 +2188,9 @@ static void draw_wbu_overlay(const hud_draw_context_hs_mr hudctx)
: :
#endif #endif
raw_cockpit_mode; raw_cockpit_mode;
auto &cb = cockpit_bitmap[cockpit_idx]; const auto cb = cockpit_bitmap[cockpit_idx];
PIGGY_PAGE_IN(cb); PIGGY_PAGE_IN(cb);
grs_bitmap *bm = &GameBitmaps[cb.index]; grs_bitmap *const bm = &GameBitmaps[cb];
cockpit_decode_alpha(hudctx, bm); cockpit_decode_alpha(hudctx, bm);
@ -2596,7 +2596,7 @@ static void draw_weapon_info_sub(const hud_draw_context_hs_mr hudctx, const play
#endif #endif
gr_rect(hudctx.canvas, hudctx.xscale(box->left), hudctx.yscale(box->top), hudctx.xscale(box->right), hudctx.yscale(box->bot + bottom_bias), color); gr_rect(hudctx.canvas, hudctx.xscale(box->left), hudctx.yscale(box->top), hudctx.xscale(box->right), hudctx.yscale(box->bot + bottom_bias), color);
} }
const auto &picture = const auto picture =
#if defined(DXX_BUILD_DESCENT_II) #if defined(DXX_BUILD_DESCENT_II)
// !SHAREWARE // !SHAREWARE
(Piggy_hamfile_version >= pig_hamfile_version::_3 && hudctx.multires_gauge_graphic.is_hires()) ? (Piggy_hamfile_version >= pig_hamfile_version::_3 && hudctx.multires_gauge_graphic.is_hires()) ?
@ -2604,8 +2604,7 @@ static void draw_weapon_info_sub(const hud_draw_context_hs_mr hudctx, const play
#endif #endif
Weapon_info[info_index].picture; Weapon_info[info_index].picture;
PIGGY_PAGE_IN(picture); PIGGY_PAGE_IN(picture);
auto &bm = GameBitmaps[picture.index]; auto &bm = GameBitmaps[picture];
hud_bitblt(hudctx, pic_x, pic_y, bm); hud_bitblt(hudctx, pic_x, pic_y, bm);
if (PlayerCfg.HudMode == HudType::Standard) if (PlayerCfg.HudMode == HudType::Standard)
@ -2854,7 +2853,7 @@ static void draw_static(const d_vclip_array &Vclip, const hud_draw_context_hs_mr
PIGGY_PAGE_IN(vc->frames[framenum]); PIGGY_PAGE_IN(vc->frames[framenum]);
auto &bmp = GameBitmaps[vc->frames[framenum].index]; auto &bmp = GameBitmaps[vc->frames[framenum]];
auto &resbox = gauge_boxes[multires_gauge_graphic.hiresmode]; auto &resbox = gauge_boxes[multires_gauge_graphic.hiresmode];
auto &weaponbox = resbox[win]; auto &weaponbox = resbox[win];
auto &box = weaponbox[(PlayerCfg.CockpitMode[1] == cockpit_mode_t::status_bar) ? gauge_hud_type::statusbar : gauge_hud_type::cockpit]; auto &box = weaponbox[(PlayerCfg.CockpitMode[1] == cockpit_mode_t::status_bar) ? gauge_hud_type::statusbar : gauge_hud_type::cockpit];

View file

@ -438,37 +438,37 @@ static g3s_lrgb compute_light_emission(const d_robot_info_array &Robot_info, d_l
} }
else else
{ {
t_idx_s = ObjBitmaps[ObjBitmapPtrs[po->first_texture]].index; t_idx_s = underlying_value(ObjBitmaps[ObjBitmapPtrs[po->first_texture]]);
t_idx_e = t_idx_s + po->n_textures - 1; t_idx_e = t_idx_s + po->n_textures - 1;
} }
break; break;
} }
case RT_LASER: case RT_LASER:
{ {
t_idx_s = t_idx_e = Weapon_info[get_weapon_id(objp)].bitmap.index; t_idx_s = t_idx_e = underlying_value(Weapon_info[get_weapon_id(objp)].bitmap);
break; break;
} }
case RT_POWERUP: case RT_POWERUP:
{ {
auto &v = Vclip[objp.rtype.vclip_info.vclip_num]; auto &v = Vclip[objp.rtype.vclip_info.vclip_num];
auto &f = v.frames; auto &f = v.frames;
t_idx_s = f[0].index; t_idx_s = underlying_value(f[0]);
t_idx_e = f[v.num_frames - 1].index; t_idx_e = underlying_value(f[v.num_frames - 1]);
break; break;
} }
case RT_WEAPON_VCLIP: case RT_WEAPON_VCLIP:
{ {
auto &v = Vclip[Weapon_info[get_weapon_id(objp)].weapon_vclip]; auto &v = Vclip[Weapon_info[get_weapon_id(objp)].weapon_vclip];
auto &f = v.frames; auto &f = v.frames;
t_idx_s = f[0].index; t_idx_s = underlying_value(f[0]);
t_idx_e = f[v.num_frames - 1].index; t_idx_e = underlying_value(f[v.num_frames - 1]);
break; break;
} }
default: default:
{ {
const auto &vc = Vclip[objp.id]; const auto &vc = Vclip[objp.id];
t_idx_s = vc.frames[0].index; t_idx_s = underlying_value(vc.frames[0]);
t_idx_e = vc.frames[vc.num_frames-1].index; t_idx_e = underlying_value(vc.frames[vc.num_frames - 1]);
break; break;
} }
} }
@ -478,9 +478,9 @@ static g3s_lrgb compute_light_emission(const d_robot_info_array &Robot_info, d_l
obj_color = {}; obj_color = {};
for (const uint16_t i : xrange(t_idx_s, t_idx_e + 1)) for (const uint16_t i : xrange(t_idx_s, t_idx_e + 1))
{ {
grs_bitmap *bm = &GameBitmaps[i];
const bitmap_index bi{i}; const bitmap_index bi{i};
PIGGY_PAGE_IN(bi); PIGGY_PAGE_IN(bi);
grs_bitmap *const bm = &GameBitmaps[bi];
obj_color.r += bm->avg_color_rgb[0]; obj_color.r += bm->avg_color_rgb[0];
obj_color.g += bm->avg_color_rgb[1]; obj_color.g += bm->avg_color_rgb[1];
obj_color.b += bm->avg_color_rgb[2]; obj_color.b += bm->avg_color_rgb[2];

View file

@ -2966,7 +2966,6 @@ window_event_result gamebitmaps_viewer_window::event_handler(const d_event &even
#if DXX_USE_OGL #if DXX_USE_OGL
float scale = 1.0; float scale = 1.0;
#endif #endif
grs_bitmap *bm;
switch (event.type) switch (event.type)
{ {
@ -2998,7 +2997,7 @@ window_event_result gamebitmaps_viewer_window::event_handler(const d_event &even
case EVENT_WINDOW_DRAW: case EVENT_WINDOW_DRAW:
{ {
const bitmap_index bi{view_idx}; const bitmap_index bi{view_idx};
bm = &GameBitmaps[view_idx]; grs_bitmap *const bm = &GameBitmaps[bi];
timer_delay(F1_0/60); timer_delay(F1_0/60);
PIGGY_PAGE_IN(bi); PIGGY_PAGE_IN(bi);
auto &canvas = *grd_curcanv; auto &canvas = *grd_curcanv;

View file

@ -562,7 +562,7 @@ static void draw_model(grs_canvas &canvas, polygon_model_points &robot_points, p
const auto ptr = ObjBitmapPtrs[pm->first_texture + i]; const auto ptr = ObjBitmapPtrs[pm->first_texture + i];
const auto &bmp = ObjBitmaps[ptr]; const auto &bmp = ObjBitmaps[ptr];
texture_list_index[i] = bmp; texture_list_index[i] = bmp;
texture_list[i] = &GameBitmaps[bmp.index]; texture_list[i] = &GameBitmaps[bmp];
} }
// Make sure the textures for this object are paged in... // Make sure the textures for this object are paged in...

View file

@ -5429,10 +5429,10 @@ namespace {
class hoard_resources_type class hoard_resources_type
{ {
static constexpr auto invalid_bm_idx = std::integral_constant<int, -1>{}; static constexpr std::integral_constant<bitmap_index, bitmap_index{UINT16_MAX}> invalid_bm_idx{};
static constexpr auto invalid_snd_idx = std::integral_constant<unsigned, ~0u>{}; static constexpr auto invalid_snd_idx = std::integral_constant<unsigned, ~0u>{};
public: public:
int bm_idx = invalid_bm_idx; bitmap_index bm_idx = invalid_bm_idx;
unsigned snd_idx = invalid_snd_idx; unsigned snd_idx = invalid_snd_idx;
void reset(); void reset();
~hoard_resources_type() ~hoard_resources_type()
@ -5482,7 +5482,8 @@ void init_hoard_data(d_vclip_array &Vclip)
palette_array_t palette; palette_array_t palette;
uint8_t *bitmap_data1; uint8_t *bitmap_data1;
int save_pos; int save_pos;
int bitmap_num = hoard_resources.bm_idx = Num_bitmap_files; uint16_t bitmap_num = Num_bitmap_files;
hoard_resources.bm_idx = bitmap_index{bitmap_num};
auto &TmapInfo = LevelUniqueTmapInfoState.TmapInfo; auto &TmapInfo = LevelUniqueTmapInfoState.TmapInfo;
auto &&[ifile, physfserr] = PHYSFSX_openReadBuffered("hoard.ham"); auto &&[ifile, physfserr] = PHYSFSX_openReadBuffered("hoard.ham");
@ -5511,9 +5512,10 @@ void init_hoard_data(d_vclip_array &Vclip)
Vclip[orb_vclip].light_value = F1_0; Vclip[orb_vclip].light_value = F1_0;
range_for (auto &i, partial_range(Vclip[orb_vclip].frames, n_orb_frames)) range_for (auto &i, partial_range(Vclip[orb_vclip].frames, n_orb_frames))
{ {
i.index = bitmap_num; const bitmap_index bi{bitmap_num};
gr_init_bitmap(GameBitmaps[bitmap_num],bm_mode::linear,0,0,orb_w,orb_h,orb_w,bitmap_data1); i = bi;
gr_set_transparent(GameBitmaps[bitmap_num], 1); gr_init_bitmap(GameBitmaps[bi], bm_mode::linear, 0, 0, orb_w, orb_h, orb_w, bitmap_data1);
gr_set_transparent(GameBitmaps[bi], 1);
bitmap_data1 += orb_w*orb_h; bitmap_data1 += orb_w*orb_h;
bitmap_num++; bitmap_num++;
Assert(bitmap_num < MAX_BITMAP_FILES); Assert(bitmap_num < MAX_BITMAP_FILES);
@ -5539,8 +5541,9 @@ void init_hoard_data(d_vclip_array &Vclip)
Assert(NumTextures < MAX_TEXTURES); Assert(NumTextures < MAX_TEXTURES);
range_for (auto &i, partial_range(Effects[goal_eclip].vc.frames, n_goal_frames)) range_for (auto &i, partial_range(Effects[goal_eclip].vc.frames, n_goal_frames))
{ {
i.index = bitmap_num; const bitmap_index bi{bitmap_num};
gr_init_bitmap(GameBitmaps[bitmap_num],bm_mode::linear,0,0,64,64,64,bitmap_data1); i = bi;
gr_init_bitmap(GameBitmaps[bi], bm_mode::linear, 0, 0, 64, 64, 64, bitmap_data1);
bitmap_data1 += 64*64; bitmap_data1 += 64*64;
bitmap_num++; bitmap_num++;
Assert(bitmap_num < MAX_BITMAP_FILES); Assert(bitmap_num < MAX_BITMAP_FILES);
@ -5550,7 +5553,7 @@ void init_hoard_data(d_vclip_array &Vclip)
PHYSFS_read(ifile,&palette[0],sizeof(palette[0]),palette.size()); PHYSFS_read(ifile,&palette[0],sizeof(palette[0]),palette.size());
range_for (auto &i, partial_const_range(Vclip[orb_vclip].frames, n_orb_frames)) range_for (auto &i, partial_const_range(Vclip[orb_vclip].frames, n_orb_frames))
{ {
grs_bitmap *bm = &GameBitmaps[i.index]; grs_bitmap *const bm = &GameBitmaps[i];
PHYSFS_read(ifile,bm->get_bitmap_data(),1,orb_w*orb_h); PHYSFS_read(ifile,bm->get_bitmap_data(),1,orb_w*orb_h);
gr_remap_bitmap_good(*bm, palette, 255, -1); gr_remap_bitmap_good(*bm, palette, 255, -1);
} }
@ -5560,7 +5563,7 @@ void init_hoard_data(d_vclip_array &Vclip)
PHYSFS_read(ifile,&palette[0],sizeof(palette[0]),palette.size()); PHYSFS_read(ifile,&palette[0],sizeof(palette[0]),palette.size());
range_for (auto &i, partial_const_range(Effects[goal_eclip].vc.frames, n_goal_frames)) range_for (auto &i, partial_const_range(Effects[goal_eclip].vc.frames, n_goal_frames))
{ {
grs_bitmap *bm = &GameBitmaps[i.index]; grs_bitmap *const bm = &GameBitmaps[i];
PHYSFS_read(ifile,bm->get_bitmap_data(),1,64*64); PHYSFS_read(ifile,bm->get_bitmap_data(),1,64*64);
gr_remap_bitmap_good(*bm, palette, 255, -1); gr_remap_bitmap_good(*bm, palette, 255, -1);
} }

View file

@ -186,7 +186,7 @@ namespace dsx {
//draw an object that has one bitmap & doesn't rotate //draw an object that has one bitmap & doesn't rotate
void draw_object_blob(GameBitmaps_array &GameBitmaps, const object_base &Viewer, grs_canvas &canvas, const object_base &obj, const bitmap_index bmi) void draw_object_blob(GameBitmaps_array &GameBitmaps, const object_base &Viewer, grs_canvas &canvas, const object_base &obj, const bitmap_index bmi)
{ {
auto &bm = GameBitmaps[bmi.index]; auto &bm = GameBitmaps[bmi];
PIGGY_PAGE_IN( bmi ); PIGGY_PAGE_IN( bmi );
const auto osize = obj.size; const auto osize = obj.size;
@ -214,7 +214,7 @@ void draw_object_tmap_rod(grs_canvas &canvas, const d_level_unique_light_state *
g3s_lrgb light; g3s_lrgb light;
PIGGY_PAGE_IN(bitmapi); PIGGY_PAGE_IN(bitmapi);
auto &bitmap = GameBitmaps[bitmapi.index]; auto &bitmap = GameBitmaps[bitmapi];
const auto delta = vm_vec_copy_scale(obj->orient.uvec,obj->size); const auto delta = vm_vec_copy_scale(obj->orient.uvec,obj->size);

View file

@ -132,7 +132,7 @@ static void paging_touch_weapon(const d_vclip_array &Vclip, const weapon_info &w
{ {
// Page in the robot's weapons. // Page in the robot's weapons.
if(weapon.picture.index) if (weapon.picture != bitmap_index{})
{ {
PIGGY_PAGE_IN(weapon.picture); PIGGY_PAGE_IN(weapon.picture);
} }
@ -361,9 +361,8 @@ void paging_touch_all(const d_vclip_array &Vclip)
range_for (auto &s, Gauges) range_for (auto &s, Gauges)
{ {
if ( s.index ) { if (s != bitmap_index{})
PIGGY_PAGE_IN( s ); PIGGY_PAGE_IN( s );
}
} }
paging_touch_vclip(Vclip[VCLIP_PLAYER_APPEARANCE]); paging_touch_vclip(Vclip[VCLIP_PLAYER_APPEARANCE]);
paging_touch_vclip(Vclip[VCLIP_POWERUP_DISAPPEARANCE]); paging_touch_vclip(Vclip[VCLIP_POWERUP_DISAPPEARANCE]);

View file

@ -56,6 +56,7 @@ COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
#include "compiler-cf_assert.h" #include "compiler-cf_assert.h"
#include "compiler-range_for.h" #include "compiler-range_for.h"
#include "d_range.h" #include "d_range.h"
#include "d_zip.h"
#include "partial_range.h" #include "partial_range.h"
#include <memory> #include <memory>
@ -110,7 +111,7 @@ namespace {
#endif #endif
hashtable AllBitmapsNames; hashtable AllBitmapsNames;
hashtable AllDigiSndNames; hashtable AllDigiSndNames;
std::array<pig_bitmap_offset, MAX_BITMAP_FILES> GameBitmapOffset; enumerated_array<pig_bitmap_offset, MAX_BITMAP_FILES, bitmap_index> GameBitmapOffset;
#if defined(DXX_BUILD_DESCENT_II) #if defined(DXX_BUILD_DESCENT_II)
static std::unique_ptr<uint8_t[]> Bitmap_replacement_data; static std::unique_ptr<uint8_t[]> Bitmap_replacement_data;
} }
@ -127,7 +128,7 @@ GameBitmaps_array GameBitmaps;
#define DBM_FLAG_LARGE 128 // Flags added onto the flags struct in b #define DBM_FLAG_LARGE 128 // Flags added onto the flags struct in b
static static
#endif #endif
std::array<BitmapFile, MAX_BITMAP_FILES> AllBitmaps; enumerated_array<BitmapFile, MAX_BITMAP_FILES, bitmap_index> AllBitmaps;
namespace { namespace {
static std::array<SoundFile, MAX_SOUND_FILES> AllSounds; static std::array<SoundFile, MAX_SOUND_FILES> AllSounds;
@ -136,8 +137,8 @@ static std::array<SoundFile, MAX_SOUND_FILES> AllSounds;
static int Piggy_bitmap_cache_size; static int Piggy_bitmap_cache_size;
static int Piggy_bitmap_cache_next; static int Piggy_bitmap_cache_next;
static uint8_t *Piggy_bitmap_cache_data; static uint8_t *Piggy_bitmap_cache_data;
static std::array<uint8_t, MAX_BITMAP_FILES> GameBitmapFlags; static enumerated_array<uint8_t, MAX_BITMAP_FILES, bitmap_index> GameBitmapFlags;
static std::array<uint16_t, MAX_BITMAP_FILES> GameBitmapXlat; static enumerated_array<bitmap_index, MAX_BITMAP_FILES, bitmap_index> GameBitmapXlat;
static RAIIPHYSFS_File Piggy_fp; static RAIIPHYSFS_File Piggy_fp;
} }
@ -344,16 +345,16 @@ bitmap_index piggy_register_bitmap(grs_bitmap &bmp, const std::span<const char>
gr_bitmap_rle_compress(bmp); gr_bitmap_rle_compress(bmp);
} }
auto &abn = AllBitmaps[Num_bitmap_files].name; auto &abn = AllBitmaps[temp].name;
std::memcpy(abn.data(), name.data(), std::min(abn.size() - 1, name.size())); std::memcpy(abn.data(), name.data(), std::min(abn.size() - 1, name.size()));
abn.back() = 0; abn.back() = 0;
hashtable_insert(&AllBitmapsNames, AllBitmaps[Num_bitmap_files].name.data(), Num_bitmap_files); hashtable_insert(&AllBitmapsNames, AllBitmaps[temp].name.data(), Num_bitmap_files);
#if defined(DXX_BUILD_DESCENT_I) #if defined(DXX_BUILD_DESCENT_I)
GameBitmaps[Num_bitmap_files] = bmp; GameBitmaps[temp] = bmp;
#endif #endif
if ( !in_file ) { if ( !in_file ) {
GameBitmapOffset[Num_bitmap_files] = pig_bitmap_offset::None; GameBitmapOffset[temp] = pig_bitmap_offset::None;
GameBitmapFlags[Num_bitmap_files] = bmp.get_flags(); GameBitmapFlags[temp] = bmp.get_flags();
} }
Num_bitmap_files++; Num_bitmap_files++;
@ -413,10 +414,7 @@ bitmap_index piggy_find_bitmap(const std::span<const char> entry_name)
Assert( i != 0 ); Assert( i != 0 );
if ( i < 0 ) if ( i < 0 )
return bitmap_index{}; return bitmap_index{};
return bitmap_index{static_cast<uint16_t>(i)};
bitmap_index bmp;
bmp.index = i;
return bmp;
} }
} }
@ -456,10 +454,11 @@ int properties_init(d_level_shared_robot_info_state &LevelSharedRobotInfoState)
GameSounds = {}; GameSounds = {};
static_assert(GameBitmapXlat.size() == GameBitmaps.size(), "size mismatch"); static_assert(GameBitmapXlat.size() == GameBitmaps.size(), "size mismatch");
for (unsigned i = 0; i < GameBitmaps.size(); ++i) for (const uint16_t i : xrange(std::size(GameBitmaps)))
{ {
GameBitmapXlat[i] = i; const bitmap_index bi{i};
GameBitmaps[i].set_flags(BM_FLAG_PAGED_OUT); GameBitmapXlat[bi] = bi;
GameBitmaps[bi].set_flags(BM_FLAG_PAGED_OUT);
} }
if ( !bogus_bitmap_initialized ) { if ( !bogus_bitmap_initialized ) {
@ -485,7 +484,7 @@ int properties_init(d_level_shared_robot_info_state &LevelSharedRobotInfoState)
//added on 11/13/99 by Victor Rachels to ready for changing freq //added on 11/13/99 by Victor Rachels to ready for changing freq
bogus_sound.freq = 11025; bogus_sound.freq = 11025;
//end this section addition - VR //end this section addition - VR
GameBitmapOffset[0] = pig_bitmap_offset::None; GameBitmapOffset[(bitmap_index{0})] = pig_bitmap_offset::None;
} }
Piggy_fp = PHYSFSX_openReadBuffered(DEFAULT_PIGFILE_REGISTERED).first; Piggy_fp = PHYSFSX_openReadBuffered(DEFAULT_PIGFILE_REGISTERED).first;
@ -532,7 +531,8 @@ int properties_init(d_level_shared_robot_info_state &LevelSharedRobotInfoState)
properties_read_cmp(LevelSharedRobotInfoState, Vclip, Piggy_fp); // Note connection to above if!!! properties_read_cmp(LevelSharedRobotInfoState, Vclip, Piggy_fp); // Note connection to above if!!!
range_for (auto &i, GameBitmapXlat) range_for (auto &i, GameBitmapXlat)
{ {
i = PHYSFSX_readShort(Piggy_fp); const bitmap_index bi{static_cast<uint16_t>(PHYSFSX_readShort(Piggy_fp))};
i = GameBitmapXlat.valid_index(i) ? bi : bitmap_index::None;
if (PHYSFS_eof(Piggy_fp)) if (PHYSFS_eof(Piggy_fp))
break; break;
} }
@ -554,10 +554,10 @@ int properties_init(d_level_shared_robot_info_state &LevelSharedRobotInfoState)
for (const unsigned i : xrange(N_bitmaps)) for (const unsigned i : xrange(N_bitmaps))
{ {
const auto bmh = DiskBitmapHeader_read(Piggy_fp); const auto bmh = DiskBitmapHeader_read(Piggy_fp);
const bitmap_index bi{static_cast<uint16_t>(i + 1)};
GameBitmapFlags[i+1] = bmh.flags & (BM_FLAG_TRANSPARENT | BM_FLAG_SUPER_TRANSPARENT | BM_FLAG_NO_LIGHTING | BM_FLAG_RLE); GameBitmapFlags[bi] = bmh.flags & (BM_FLAG_TRANSPARENT | BM_FLAG_SUPER_TRANSPARENT | BM_FLAG_NO_LIGHTING | BM_FLAG_RLE);
GameBitmapOffset[i+1] = static_cast<pig_bitmap_offset>(bmh.offset + header_size + (sizeof(int)*2) + Pigdata_start); GameBitmapOffset[bi] = static_cast<pig_bitmap_offset>(bmh.offset + header_size + (sizeof(int)*2) + Pigdata_start);
Assert( (i+1) == Num_bitmap_files ); Assert( (i+1) == Num_bitmap_files );
//size -= sizeof(DiskBitmapHeader); //size -= sizeof(DiskBitmapHeader);
@ -578,8 +578,8 @@ int properties_init(d_level_shared_robot_info_state &LevelSharedRobotInfoState)
// HACK HACK HACK!!!!! // HACK HACK HACK!!!!!
if (!d_strnicmp(bmh.name, "cockpit") || !d_strnicmp(bmh.name, "status") || !d_strnicmp(bmh.name, "rearview")) { if (!d_strnicmp(bmh.name, "cockpit") || !d_strnicmp(bmh.name, "status") || !d_strnicmp(bmh.name, "rearview")) {
temp_bitmap.bm_w = temp_bitmap.bm_rowsize = 640; temp_bitmap.bm_w = temp_bitmap.bm_rowsize = 640;
if (GameBitmapFlags[i+1] & BM_FLAG_RLE) if (auto &f = GameBitmapFlags[bi]; f & BM_FLAG_RLE)
GameBitmapFlags[i+1] |= BM_FLAG_RLE_BIG; f |= BM_FLAG_RLE_BIG;
} }
if (!d_strnicmp(bmh.name, "cockpit") || !d_strnicmp(bmh.name, "rearview")) if (!d_strnicmp(bmh.name, "cockpit") || !d_strnicmp(bmh.name, "rearview"))
temp_bitmap.bm_h = 480; temp_bitmap.bm_h = 480;
@ -696,7 +696,8 @@ void piggy_init_pigfile(const char *filename)
for (i=0; i<N_bitmaps; i++ ) for (i=0; i<N_bitmaps; i++ )
{ {
int width; int width;
grs_bitmap *bm = &GameBitmaps[i + 1]; const bitmap_index bi{static_cast<uint16_t>(i + 1)};
grs_bitmap *const bm = &GameBitmaps[bi];
const auto bmh = DiskBitmapHeader_read(Piggy_fp); const auto bmh = DiskBitmapHeader_read(Piggy_fp);
get_bitmap_name_from_header(temp_name, bmh); get_bitmap_name_from_header(temp_name, bmh);
@ -707,9 +708,8 @@ void piggy_init_pigfile(const char *filename)
bm->avg_color = bmh.avg_color; bm->avg_color = bmh.avg_color;
#endif #endif
GameBitmapFlags[i+1] = bmh.flags & BM_FLAGS_TO_COPY; GameBitmapFlags[bi] = bmh.flags & BM_FLAGS_TO_COPY;
GameBitmapOffset[bi] = pig_bitmap_offset{bmh.offset + data_start};
GameBitmapOffset[i+1] = pig_bitmap_offset{bmh.offset + data_start};
Assert( (i+1) == Num_bitmap_files ); Assert( (i+1) == Num_bitmap_files );
piggy_register_bitmap(*bm, temp_name, 1); piggy_register_bitmap(*bm, temp_name, 1);
} }
@ -733,7 +733,6 @@ void piggy_init_pigfile(const char *filename)
//returns the size of all the bitmap data //returns the size of all the bitmap data
void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname) void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname)
{ {
int i;
std::array<char, 13> temp_name; std::array<char, 13> temp_name;
int header_size, N_bitmaps; int header_size, N_bitmaps;
#if DXX_USE_EDITOR #if DXX_USE_EDITOR
@ -805,23 +804,24 @@ void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname)
const unsigned data_start = header_size + PHYSFS_tell(Piggy_fp); const unsigned data_start = header_size + PHYSFS_tell(Piggy_fp);
for (i=1; i<=N_bitmaps; i++ ) for (unsigned i = 1; i <= N_bitmaps; ++i)
{ {
grs_bitmap *bm = &GameBitmaps[i]; const bitmap_index bi{static_cast<uint16_t>(i)};
grs_bitmap *const bm = &GameBitmaps[bi];
int width; int width;
const auto bmh = DiskBitmapHeader_read(Piggy_fp); const auto bmh = DiskBitmapHeader_read(Piggy_fp);
get_bitmap_name_from_header(temp_name, bmh); get_bitmap_name_from_header(temp_name, bmh);
#if DXX_USE_EDITOR #if DXX_USE_EDITOR
//Make sure name matches //Make sure name matches
if (strcmp(temp_name.data(), AllBitmaps[i].name.data())) if (strcmp(temp_name.data(), AllBitmaps[bi].name.data()))
{ {
//Int3(); //this pig is out of date. Delete it //Int3(); //this pig is out of date. Delete it
must_rewrite_pig=1; must_rewrite_pig=1;
} }
#endif #endif
AllBitmaps[i].name = temp_name; AllBitmaps[bi].name = temp_name;
width = bmh.width + (static_cast<short>(bmh.wh_extra & 0x0f) << 8); width = bmh.width + (static_cast<short>(bmh.wh_extra & 0x0f) << 8);
gr_set_bitmap_data(*bm, NULL); // free ogl texture gr_set_bitmap_data(*bm, NULL); // free ogl texture
@ -831,9 +831,8 @@ void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname)
bm->avg_color = bmh.avg_color; bm->avg_color = bmh.avg_color;
#endif #endif
GameBitmapFlags[i] = bmh.flags & BM_FLAGS_TO_COPY; GameBitmapFlags[bi] = bmh.flags & BM_FLAGS_TO_COPY;
GameBitmapOffset[bi] = pig_bitmap_offset{bmh.offset + data_start};
GameBitmapOffset[i] = pig_bitmap_offset{bmh.offset + data_start};
} }
} }
else else
@ -850,8 +849,10 @@ void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname)
//re-read the bitmaps that aren't in this pig //re-read the bitmaps that aren't in this pig
for (i=N_bitmaps+1;i<Num_bitmap_files;i++) { for (unsigned i = N_bitmaps + 1; i < Num_bitmap_files; ++i)
auto &abn = AllBitmaps[i].name; {
const bitmap_index bi{static_cast<uint16_t>(i)};
auto &abn = AllBitmaps[bi].name;
if (const auto p = strchr(abn.data(), '#')) if (const auto p = strchr(abn.data(), '#'))
{ // this is an ABM == animated bitmap { // this is an ABM == animated bitmap
char abmname[FILENAME_LEN]; char abmname[FILENAME_LEN];
@ -873,7 +874,8 @@ void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname)
int SuperX; int SuperX;
//SuperX = (GameBitmaps[i+fnum].bm_flags&BM_FLAG_SUPER_TRANSPARENT)?254:-1; //SuperX = (GameBitmaps[i+fnum].bm_flags&BM_FLAG_SUPER_TRANSPARENT)?254:-1;
SuperX = (GameBitmapFlags[i+fnum]&BM_FLAG_SUPER_TRANSPARENT)?254:-1; const bitmap_index bfi{static_cast<uint16_t>(i + fnum)};
SuperX = (GameBitmapFlags[bfi] & BM_FLAG_SUPER_TRANSPARENT) ? 254 : -1;
//above makes assumption that supertransparent color is 254 //above makes assumption that supertransparent color is 254
gr_remap_bitmap_good(*bm[fnum].get(), newpal, iff_has_transparency ? iff_transparent_color : -1, SuperX); gr_remap_bitmap_good(*bm[fnum].get(), newpal, iff_has_transparency ? iff_transparent_color : -1, SuperX);
@ -898,7 +900,7 @@ void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname)
bm[fnum]->bm_mdata = &Piggy_bitmap_cache_data[Piggy_bitmap_cache_next]; bm[fnum]->bm_mdata = &Piggy_bitmap_cache_data[Piggy_bitmap_cache_next];
Piggy_bitmap_cache_next += size; Piggy_bitmap_cache_next += size;
GameBitmaps[i+fnum] = std::move(*bm[fnum]); GameBitmaps[bfi] = std::move(*bm[fnum]);
} }
i += nframes-1; //filled in multiple bitmaps i += nframes-1; //filled in multiple bitmaps
@ -918,7 +920,7 @@ void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname)
Error("File %s - IFF error: %s",bbmname,iff_errormsg(iff_error)); Error("File %s - IFF error: %s",bbmname,iff_errormsg(iff_error));
} }
SuperX = (GameBitmapFlags[i]&BM_FLAG_SUPER_TRANSPARENT)?254:-1; SuperX = (GameBitmapFlags[bi] & BM_FLAG_SUPER_TRANSPARENT) ? 254 : -1;
//above makes assumption that supertransparent color is 254 //above makes assumption that supertransparent color is 254
gr_remap_bitmap_good(n, newpal, iff_has_transparency ? iff_transparent_color : -1, SuperX); gr_remap_bitmap_good(n, newpal, iff_has_transparency ? iff_transparent_color : -1, SuperX);
@ -942,8 +944,7 @@ void piggy_new_pigfile(const std::span<char, FILENAME_LEN> pigname)
d_free(n.bm_mdata); d_free(n.bm_mdata);
n.bm_mdata = &Piggy_bitmap_cache_data[Piggy_bitmap_cache_next]; n.bm_mdata = &Piggy_bitmap_cache_data[Piggy_bitmap_cache_next];
Piggy_bitmap_cache_next += size; Piggy_bitmap_cache_next += size;
GameBitmaps[bi] = std::move(n);
GameBitmaps[i] = n;
} }
} }
@ -1028,7 +1029,8 @@ int read_hamfile(d_level_shared_robot_info_state &LevelSharedRobotInfoState)
//PHYSFS_read( ham_fp, GameBitmapXlat, sizeof(ushort)*MAX_BITMAP_FILES, 1 ); //PHYSFS_read( ham_fp, GameBitmapXlat, sizeof(ushort)*MAX_BITMAP_FILES, 1 );
range_for (auto &i, GameBitmapXlat) range_for (auto &i, GameBitmapXlat)
{ {
i = PHYSFSX_readShort(ham_fp); const bitmap_index bi{static_cast<uint16_t>(PHYSFSX_readShort(ham_fp))};
i = GameBitmapXlat.valid_index(i) ? bi : bitmap_index::None;
if (PHYSFS_eof(ham_fp)) if (PHYSFS_eof(ham_fp))
break; break;
} }
@ -1126,9 +1128,10 @@ int properties_init(d_level_shared_robot_info_state &LevelSharedRobotInfoState)
{ {
int ham_ok=0,snd_ok=0; int ham_ok=0,snd_ok=0;
GameSounds = {}; GameSounds = {};
for (unsigned i = 0; i < GameBitmapXlat.size(); ++i) for (const uint16_t i : xrange(std::size(GameBitmapXlat)))
{ {
GameBitmapXlat[i] = i; const bitmap_index bi{i};
GameBitmapXlat[bi] = bi;
} }
if ( !bogus_bitmap_initialized ) { if ( !bogus_bitmap_initialized ) {
@ -1144,11 +1147,12 @@ int properties_init(d_level_shared_robot_info_state &LevelSharedRobotInfoState)
bogus_data[i*64+i] = c; bogus_data[i*64+i] = c;
bogus_data[i*64+(63-i)] = c; bogus_data[i*64+(63-i)] = c;
} }
gr_init_bitmap(GameBitmaps[Num_bitmap_files], bm_mode::linear, 0, 0, 64, 64, 64, bogus_data.data()); const bitmap_index bi{static_cast<uint16_t>(Num_bitmap_files)};
piggy_register_bitmap(GameBitmaps[Num_bitmap_files], "bogus", 1); gr_init_bitmap(GameBitmaps[bi], bm_mode::linear, 0, 0, 64, 64, 64, bogus_data.data());
piggy_register_bitmap(GameBitmaps[bi], "bogus", 1);
bogus_sound.length = 64*64; bogus_sound.length = 64*64;
bogus_sound.data = digi_sound::allocated_data{bogus_data.data(), game_sound_offset{INT_MAX}}; bogus_sound.data = digi_sound::allocated_data{bogus_data.data(), game_sound_offset{INT_MAX}};
GameBitmapOffset[0] = pig_bitmap_offset::None; GameBitmapOffset[(bitmap_index{0})] = pig_bitmap_offset::None;
} }
snd_ok = ham_ok = read_hamfile(LevelSharedRobotInfoState); snd_ok = ham_ok = read_hamfile(LevelSharedRobotInfoState);
@ -1265,15 +1269,9 @@ void piggy_read_sounds(void)
} }
#endif #endif
void piggy_bitmap_page_in(GameBitmaps_array &GameBitmaps, const bitmap_index bitmap) void piggy_bitmap_page_in(GameBitmaps_array &GameBitmaps, const bitmap_index entry_bitmap_index)
{ {
grs_bitmap * bmp; const auto i = underlying_value(entry_bitmap_index);
int i,org_i;
org_i = 0;
i = bitmap.index;
Assert( i >= 0 );
Assert( i < MAX_BITMAP_FILES ); Assert( i < MAX_BITMAP_FILES );
Assert( i < Num_bitmap_files ); Assert( i < Num_bitmap_files );
Assert( Piggy_bitmap_cache_size > 0 ); Assert( Piggy_bitmap_cache_size > 0 );
@ -1282,25 +1280,20 @@ void piggy_bitmap_page_in(GameBitmaps_array &GameBitmaps, const bitmap_index bit
if ( i >= MAX_BITMAP_FILES ) return; if ( i >= MAX_BITMAP_FILES ) return;
if ( i >= Num_bitmap_files ) return; if ( i >= Num_bitmap_files ) return;
if (GameBitmapOffset[i] == pig_bitmap_offset::None) if (GameBitmapOffset[entry_bitmap_index] == pig_bitmap_offset::None)
return; // A read-from-disk bitmap!!! return; // A read-from-disk bitmap!!!
if (CGameArg.SysLowMem) const auto xlat_bitmap_index = CGameArg.SysLowMem ? GameBitmapXlat[entry_bitmap_index] : entry_bitmap_index; // Xlat for low-memory settings!
{ grs_bitmap *const bmp = &GameBitmaps[xlat_bitmap_index];
org_i = i;
i = GameBitmapXlat[i]; // Xlat for low-memory settings!
}
bmp = &GameBitmaps[i];
if (bmp->get_flag_mask(BM_FLAG_PAGED_OUT)) if (bmp->get_flag_mask(BM_FLAG_PAGED_OUT))
{ {
pause_game_world_time p; pause_game_world_time p;
ReDoIt: ReDoIt:
PHYSFS_seek(Piggy_fp, static_cast<unsigned>(GameBitmapOffset[i])); PHYSFS_seek(Piggy_fp, static_cast<unsigned>(GameBitmapOffset[xlat_bitmap_index]));
gr_set_bitmap_flags(*bmp, GameBitmapFlags[i]); gr_set_bitmap_flags(*bmp, GameBitmapFlags[xlat_bitmap_index]);
#if defined(DXX_BUILD_DESCENT_I) #if defined(DXX_BUILD_DESCENT_I)
gr_set_bitmap_data (*bmp, &Piggy_bitmap_cache_data [Piggy_bitmap_cache_next]); gr_set_bitmap_data (*bmp, &Piggy_bitmap_cache_data [Piggy_bitmap_cache_next]);
#endif #endif
@ -1414,8 +1407,8 @@ void piggy_bitmap_page_in(GameBitmaps_array &GameBitmaps, const bitmap_index bit
if (CGameArg.SysLowMem) if (CGameArg.SysLowMem)
{ {
if ( org_i != i ) if (entry_bitmap_index != xlat_bitmap_index)
GameBitmaps[org_i] = GameBitmaps[i]; GameBitmaps[entry_bitmap_index] = GameBitmaps[xlat_bitmap_index];
} }
//@@Removed from John's code: //@@Removed from John's code:
@ -1431,21 +1424,19 @@ namespace {
void piggy_bitmap_page_out_all() void piggy_bitmap_page_out_all()
{ {
int i;
Piggy_bitmap_cache_next = 0; Piggy_bitmap_cache_next = 0;
texmerge_flush(); texmerge_flush();
rle_cache_flush(); rle_cache_flush();
for (i=0; i<Num_bitmap_files; i++ ) { for (auto &&[gbo, gb] : zip(partial_range(GameBitmapOffset, Num_bitmap_files), GameBitmaps))
if (GameBitmapOffset[i] != pig_bitmap_offset::None) {
if (gbo != pig_bitmap_offset::None)
{ // Don't page out bitmaps read from disk!!! { // Don't page out bitmaps read from disk!!!
GameBitmaps[i].set_flags(BM_FLAG_PAGED_OUT); gb.set_flags(BM_FLAG_PAGED_OUT);
gr_set_bitmap_data(GameBitmaps[i], nullptr); gr_set_bitmap_data(gb, nullptr);
} }
} }
} }
} }
@ -1465,8 +1456,6 @@ static void piggy_write_pigfile(const std::span<const char, FILENAME_LEN> filena
int bitmap_data_start, data_offset; int bitmap_data_start, data_offset;
DiskBitmapHeader bmh; DiskBitmapHeader bmh;
int org_offset; int org_offset;
int i;
for (const unsigned n = Num_bitmap_files; const uint16_t i : xrange(n)) for (const unsigned n = Num_bitmap_files; const uint16_t i : xrange(n))
{ {
const bitmap_index bi{i}; const bitmap_index bi{i};
@ -1498,10 +1487,12 @@ static void piggy_write_pigfile(const std::span<const char, FILENAME_LEN> filena
return; return;
auto fp2 = PHYSFSX_openWriteBuffered(tname.data()).first; auto fp2 = PHYSFSX_openWriteBuffered(tname.data()).first;
for (i=1; i < Num_bitmap_files; i++ ) { for (unsigned i = 1; i < Num_bitmap_files; ++i)
{
grs_bitmap *bmp; grs_bitmap *bmp;
const std::span name = AllBitmaps[i].name; const bitmap_index bi{static_cast<uint16_t>(i)};
const std::span name = AllBitmaps[bi].name;
{ {
char *p1; char *p1;
if (const auto p = strchr(name.data(), '#')) { // this is an ABM == animated bitmap if (const auto p = strchr(name.data(), '#')) { // this is an ABM == animated bitmap
@ -1522,7 +1513,7 @@ static void piggy_write_pigfile(const std::span<const char, FILENAME_LEN> filena
bmh.dflags = 0; bmh.dflags = 0;
} }
} }
bmp = &GameBitmaps[i]; bmp = &GameBitmaps[bi];
assert(!bmp->get_flag_mask(BM_FLAG_PAGED_OUT)); assert(!bmp->get_flag_mask(BM_FLAG_PAGED_OUT));
@ -1546,22 +1537,23 @@ static void piggy_write_pigfile(const std::span<const char, FILENAME_LEN> filena
PHYSFSX_puts_literal( fp1, ".\n" ); PHYSFSX_puts_literal( fp1, ".\n" );
} }
PHYSFS_seek(pig_fp, org_offset); PHYSFS_seek(pig_fp, org_offset);
Assert( GameBitmaps[i].bm_w < 4096 ); auto &gbi = GameBitmaps[bi];
bmh.width = (GameBitmaps[i].bm_w & 0xff); assert(gbi.bm_w < 4096);
bmh.wh_extra = ((GameBitmaps[i].bm_w >> 8) & 0x0f); bmh.width = (gbi.bm_w & 0xff);
Assert( GameBitmaps[i].bm_h < 4096 ); bmh.wh_extra = ((gbi.bm_w >> 8) & 0x0f);
bmh.height = GameBitmaps[i].bm_h; assert(gbi.bm_h < 4096);
bmh.wh_extra |= ((GameBitmaps[i].bm_h >> 4) & 0xf0); bmh.height = gbi.bm_h;
bmh.flags = GameBitmaps[i].get_flags(); bmh.wh_extra |= ((gbi.bm_h >> 4) & 0xf0);
bmh.flags = gbi.get_flags();
if (std::array<char, 32> subst_name; piggy_is_substitutable_bitmap(name, subst_name)) if (std::array<char, 32> subst_name; piggy_is_substitutable_bitmap(name, subst_name))
{ {
const auto other_bitmap = piggy_find_bitmap(subst_name); const auto other_bitmap = piggy_find_bitmap(subst_name);
GameBitmapXlat[i] = other_bitmap.index; GameBitmapXlat[bi] = other_bitmap;
bmh.flags |= BM_FLAG_PAGED_OUT; bmh.flags |= BM_FLAG_PAGED_OUT;
} else { } else {
bmh.flags &= ~BM_FLAG_PAGED_OUT; bmh.flags &= ~BM_FLAG_PAGED_OUT;
} }
bmh.avg_color = compute_average_pixel(&GameBitmaps[i]); bmh.avg_color = compute_average_pixel(&GameBitmaps[bi]);
PHYSFS_write(pig_fp, &bmh, sizeof(DiskBitmapHeader), 1); // Mark as a bitmap PHYSFS_write(pig_fp, &bmh, sizeof(DiskBitmapHeader), 1); // Mark as a bitmap
} }
PHYSFSX_printf( fp1, " Dumped %d assorted bitmaps.\n", Num_bitmap_files ); PHYSFSX_printf( fp1, " Dumped %d assorted bitmaps.\n", Num_bitmap_files );
@ -1756,7 +1748,8 @@ void load_bitmap_replacements(const std::span<const char, FILENAME_LEN> level_na
range_for (const auto i, unchecked_partial_range(indices.get(), n_bitmaps)) range_for (const auto i, unchecked_partial_range(indices.get(), n_bitmaps))
{ {
grs_bitmap *bm = &GameBitmaps[i]; const bitmap_index bi{i};
grs_bitmap *const bm = &GameBitmaps[bi];
int width; int width;
const auto bmh = DiskBitmapHeader_read(ifile); const auto bmh = DiskBitmapHeader_read(ifile);
@ -1770,15 +1763,15 @@ void load_bitmap_replacements(const std::span<const char, FILENAME_LEN> level_na
bm->bm_data = reinterpret_cast<uint8_t *>(static_cast<uintptr_t>(bmh.offset)); bm->bm_data = reinterpret_cast<uint8_t *>(static_cast<uintptr_t>(bmh.offset));
gr_set_bitmap_flags(*bm, bmh.flags & BM_FLAGS_TO_COPY); gr_set_bitmap_flags(*bm, bmh.flags & BM_FLAGS_TO_COPY);
GameBitmapOffset[bi] = pig_bitmap_offset::None; // don't try to read bitmap from current pigfile
GameBitmapOffset[i] = pig_bitmap_offset::None; // don't try to read bitmap from current pigfile
} }
PHYSFS_read(ifile,Bitmap_replacement_data,1,bitmap_data_size); PHYSFS_read(ifile,Bitmap_replacement_data,1,bitmap_data_size);
range_for (const auto i, unchecked_partial_range(indices.get(), n_bitmaps)) range_for (const auto i, unchecked_partial_range(indices.get(), n_bitmaps))
{ {
grs_bitmap *bm = &GameBitmaps[i]; const bitmap_index bi{i};
grs_bitmap *const bm = &GameBitmaps[bi];
gr_set_bitmap_data(*bm, &Bitmap_replacement_data[reinterpret_cast<uintptr_t>(bm->bm_data)]); gr_set_bitmap_data(*bm, &Bitmap_replacement_data[reinterpret_cast<uintptr_t>(bm->bm_data)]);
} }
last_palette_loaded_pig[0]= 0; //force pig re-load last_palette_loaded_pig[0]= 0; //force pig re-load
@ -1984,16 +1977,16 @@ static void read_d1_tmap_nums_from_hog(PHYSFS_File *d1_pig)
/* If the given d1_index is the index of a bitmap we have to load /* If the given d1_index is the index of a bitmap we have to load
* (because it is unique to descent 1), then returns the d2_index that * (because it is unique to descent 1), then returns the d2_index that
* the given d1_index replaces. * the given d1_index replaces.
* Returns -1 if the given d1_index is not unique to descent 1. * Returns bitmap_index::None if the given d1_index is not unique to descent 1.
*/ */
static short d2_index_for_d1_index(short d1_index) static bitmap_index d2_index_for_d1_index(short d1_index)
{ {
Assert(d1_index >= 0 && d1_index < D1_MAX_TMAP_NUM); Assert(d1_index >= 0 && d1_index < D1_MAX_TMAP_NUM);
if (! d1_tmap_nums || (*d1_tmap_nums)[d1_index] == -1 if (! d1_tmap_nums || (*d1_tmap_nums)[d1_index] == -1
|| ! d1_tmap_num_unique((*d1_tmap_nums)[d1_index])) || ! d1_tmap_num_unique((*d1_tmap_nums)[d1_index]))
return -1; return bitmap_index::None;
return Textures[convert_d1_tmap_num((*d1_tmap_nums)[d1_index])].index; return Textures[convert_d1_tmap_num((*d1_tmap_nums)[d1_index])];
} }
} }
@ -2004,7 +1997,7 @@ void load_d1_bitmap_replacements()
DiskBitmapHeader bmh; DiskBitmapHeader bmh;
int pig_data_start, bitmap_header_start, bitmap_data_start; int pig_data_start, bitmap_header_start, bitmap_data_start;
int N_bitmaps; int N_bitmaps;
short d1_index, d2_index; short d1_index;
uint8_t * next_bitmap; uint8_t * next_bitmap;
palette_array_t d1_palette; palette_array_t d1_palette;
char *p; char *p;
@ -2068,9 +2061,10 @@ void load_d1_bitmap_replacements()
next_bitmap = Bitmap_replacement_data.get(); next_bitmap = Bitmap_replacement_data.get();
for (d1_index = 1; d1_index <= N_bitmaps; d1_index++ ) { for (d1_index = 1; d1_index <= N_bitmaps; d1_index++ ) {
d2_index = d2_index_for_d1_index(d1_index); const auto d2_index = d2_index_for_d1_index(d1_index);
// only change bitmaps which are unique to d1 // only change bitmaps which are unique to d1
if (d2_index != -1) { if (d2_index != bitmap_index::None)
{
PHYSFS_seek(d1_Piggy_fp, bitmap_header_start + (d1_index - 1) * DISKBITMAPHEADER_D1_SIZE); PHYSFS_seek(d1_Piggy_fp, bitmap_header_start + (d1_index - 1) * DISKBITMAPHEADER_D1_SIZE);
DiskBitmapHeader_d1_read(&bmh, d1_Piggy_fp); DiskBitmapHeader_d1_read(&bmh, d1_Piggy_fp);
@ -2082,15 +2076,19 @@ void load_d1_bitmap_replacements()
auto &abname = AllBitmaps[d2_index].name; auto &abname = AllBitmaps[d2_index].name;
if ((p = strchr(abname.data(), '#')) /* d2 BM is animated */ if ((p = strchr(abname.data(), '#')) /* d2 BM is animated */
&& !(bmh.dflags & DBM_FLAG_ABM) ) { /* d1 bitmap is not animated */ && !(bmh.dflags & DBM_FLAG_ABM) ) { /* d1 bitmap is not animated */
int i, len = p - abname.data(); int len = p - abname.data();
for (i = 0; i < Num_bitmap_files; i++) const auto num_bitmap_files = Num_bitmap_files;
if (i != d2_index && ! memcmp(abname.data(), AllBitmaps[i].name.data(), len)) for (const uint16_t i : xrange(num_bitmap_files))
{
const bitmap_index bi{i};
if (bi != d2_index && ! memcmp(abname.data(), AllBitmaps[bi].name.data(), len))
{ {
gr_set_bitmap_data(GameBitmaps[i], NULL); // free ogl texture gr_set_bitmap_data(GameBitmaps[bi], nullptr); // free ogl texture
GameBitmaps[i] = GameBitmaps[d2_index]; GameBitmaps[bi] = GameBitmaps[d2_index];
GameBitmapOffset[i] = pig_bitmap_offset::None; GameBitmapOffset[bi] = pig_bitmap_offset::None;
GameBitmapFlags[i] = bmh.flags; GameBitmapFlags[bi] = bmh.flags;
} }
}
} }
} }
} }
@ -2185,7 +2183,8 @@ namespace dcx {
*/ */
void bitmap_index_read(PHYSFS_File *fp, bitmap_index &bi) void bitmap_index_read(PHYSFS_File *fp, bitmap_index &bi)
{ {
bi.index = PHYSFSX_readShort(fp); const bitmap_index i{static_cast<uint16_t>(PHYSFSX_readShort(fp))};
bi = GameBitmaps.valid_index(i) ? i : bitmap_index::None;
} }
/* /*
@ -2193,7 +2192,10 @@ void bitmap_index_read(PHYSFS_File *fp, bitmap_index &bi)
*/ */
void bitmap_index_read_n(PHYSFS_File *fp, const partial_range_t<bitmap_index *> r) void bitmap_index_read_n(PHYSFS_File *fp, const partial_range_t<bitmap_index *> r)
{ {
range_for (auto &i, r) for (auto &bi : r)
i.index = PHYSFSX_readShort(fp); {
const bitmap_index i{static_cast<uint16_t>(PHYSFSX_readShort(fp))};
bi = GameBitmaps.valid_index(i) ? i : bitmap_index::None;
}
} }
} }

View file

@ -439,7 +439,7 @@ void draw_polygon_model(grs_canvas &canvas, const vms_vector &pos, const vms_mat
// Make sure the textures for this object are paged in... // Make sure the textures for this object are paged in...
for (auto &&[tli, tl] : zip(tlir, partial_range(texture_list, n_textures))) for (auto &&[tli, tl] : zip(tlir, partial_range(texture_list, n_textures)))
{ {
tl = &GameBitmaps[tli.index]; tl = &GameBitmaps[tli];
PIGGY_PAGE_IN(tli); PIGGY_PAGE_IN(tli);
} }
} }

View file

@ -257,14 +257,14 @@ static void render_face(grs_canvas &canvas, const shared_segment &segp, const si
grs_bitmap *bm2 = nullptr; grs_bitmap *bm2 = nullptr;
if (!CGameArg.DbgUseOldTextureMerge) if (!CGameArg.DbgUseOldTextureMerge)
{ {
auto &texture1 = Textures[get_texture_index(tmap1)]; const auto texture1 = Textures[get_texture_index(tmap1)];
PIGGY_PAGE_IN(texture1); PIGGY_PAGE_IN(texture1);
bm = &GameBitmaps[texture1.index]; bm = &GameBitmaps[texture1];
if (tmap2 != texture2_value::None) if (tmap2 != texture2_value::None)
{ {
const auto texture2 = Textures[get_texture_index(tmap2)]; const auto texture2 = Textures[get_texture_index(tmap2)];
PIGGY_PAGE_IN(texture2); PIGGY_PAGE_IN(texture2);
bm2 = &GameBitmaps[texture2.index]; bm2 = &GameBitmaps[texture2];
if (bm2->get_flag_mask(BM_FLAG_SUPER_TRANSPARENT)) if (bm2->get_flag_mask(BM_FLAG_SUPER_TRANSPARENT))
{ {
bm2 = nullptr; bm2 = nullptr;
@ -278,8 +278,8 @@ static void render_face(grs_canvas &canvas, const shared_segment &segp, const si
{ {
bm = &texmerge_get_cached_bitmap( tmap1, tmap2 ); bm = &texmerge_get_cached_bitmap( tmap1, tmap2 );
} else { } else {
auto &texture1 = Textures[get_texture_index(tmap1)]; const auto texture1 = Textures[get_texture_index(tmap1)];
bm = &GameBitmaps[texture1.index]; bm = &GameBitmaps[texture1];
PIGGY_PAGE_IN(texture1); PIGGY_PAGE_IN(texture1);
} }
@ -351,7 +351,7 @@ static void render_face(grs_canvas &canvas, const shared_segment &segp, const si
#if DXX_USE_EDITOR #if DXX_USE_EDITOR
if (Render_only_bottom && sidenum == sidenum_t::WBOTTOM) if (Render_only_bottom && sidenum == sidenum_t::WBOTTOM)
g3_draw_tmap(canvas, nv, pointlist, uvl_copy, dyn_light, GameBitmaps[Textures[Bottom_bitmap_num].index]); g3_draw_tmap(canvas, nv, pointlist, uvl_copy, dyn_light, GameBitmaps[Textures[Bottom_bitmap_num]]);
else else
#endif #endif

View file

@ -37,6 +37,7 @@ COPYRIGHT 1993-1999 PARALLAX SOFTWARE CORPORATION. ALL RIGHTS RESERVED.
#include "compiler-range_for.h" #include "compiler-range_for.h"
#include "d_range.h" #include "d_range.h"
#include "d_underlying_value.h"
#include "partial_range.h" #include "partial_range.h"
#if DXX_USE_OGL #if DXX_USE_OGL
@ -213,9 +214,9 @@ grs_bitmap &texmerge_get_cached_bitmap(const texture1_value tmap_bottom, const t
int lowest_time_used; int lowest_time_used;
auto &texture_top = Textures[get_texture_index(tmap_top)]; auto &texture_top = Textures[get_texture_index(tmap_top)];
bitmap_top = &GameBitmaps[texture_top.index]; bitmap_top = &GameBitmaps[texture_top];
auto &texture_bottom = Textures[get_texture_index(tmap_bottom)]; auto &texture_bottom = Textures[get_texture_index(tmap_bottom)];
bitmap_bottom = &GameBitmaps[texture_bottom.index]; bitmap_bottom = &GameBitmaps[texture_bottom];
const auto orient = get_texture_rotation_high(tmap_top); const auto orient = get_texture_rotation_high(tmap_top);
@ -242,9 +243,9 @@ grs_bitmap &texmerge_get_cached_bitmap(const texture1_value tmap_bottom, const t
PIGGY_PAGE_IN(texture_top); PIGGY_PAGE_IN(texture_top);
PIGGY_PAGE_IN(texture_bottom); PIGGY_PAGE_IN(texture_bottom);
if (bitmap_bottom->bm_w != bitmap_bottom->bm_h || bitmap_top->bm_w != bitmap_top->bm_h) if (bitmap_bottom->bm_w != bitmap_bottom->bm_h || bitmap_top->bm_w != bitmap_top->bm_h)
Error("Texture width != texture height!\nbottom tmap = %u; bottom bitmap = %u; bottom width = %u; bottom height = %u\ntop tmap = %hu; top bitmap = %u; top width=%u; top height=%u", static_cast<uint16_t>(tmap_bottom), texture_bottom.index, bitmap_bottom->bm_w, bitmap_bottom->bm_h, static_cast<uint16_t>(tmap_top), texture_top.index, bitmap_top->bm_w, bitmap_top->bm_h); Error("Texture width != texture height!\nbottom tmap = %u; bottom bitmap = %u; bottom width = %u; bottom height = %u\ntop tmap = %hu; top bitmap = %u; top width=%u; top height=%u", underlying_value(tmap_bottom), underlying_value(texture_bottom), bitmap_bottom->bm_w, bitmap_bottom->bm_h, underlying_value(tmap_top), underlying_value(texture_top), bitmap_top->bm_w, bitmap_top->bm_h);
if (bitmap_bottom->bm_w != bitmap_top->bm_w || bitmap_bottom->bm_h != bitmap_top->bm_h) if (bitmap_bottom->bm_w != bitmap_top->bm_w || bitmap_bottom->bm_h != bitmap_top->bm_h)
Error("Top and Bottom textures have different size!\nbottom tmap = %u; bottom bitmap = %u; bottom width = %u; bottom height = %u\ntop tmap = %hu; top bitmap = %u; top width=%u; top height=%u", static_cast<uint16_t>(tmap_bottom), texture_bottom.index, bitmap_bottom->bm_w, bitmap_bottom->bm_h, static_cast<uint16_t>(tmap_top), texture_top.index, bitmap_top->bm_w, bitmap_top->bm_h); Error("Top and Bottom textures have different size!\nbottom tmap = %u; bottom bitmap = %u; bottom width = %u; bottom height = %u\ntop tmap = %hu; top bitmap = %u; top width=%u; top height=%u", underlying_value(tmap_bottom), underlying_value(texture_bottom), bitmap_bottom->bm_w, bitmap_bottom->bm_h, underlying_value(tmap_top), underlying_value(texture_top), bitmap_top->bm_w, bitmap_top->bm_h);
least_recently_used->bitmap = gr_create_bitmap(bitmap_bottom->bm_w, bitmap_bottom->bm_h); least_recently_used->bitmap = gr_create_bitmap(bitmap_bottom->bm_w, bitmap_bottom->bm_h);
#if DXX_USE_OGL #if DXX_USE_OGL

View file

@ -1104,7 +1104,6 @@ static void flash_cursor(grs_canvas &canvas, const grs_font &cv_font, briefing *
//----------------------------------------------------------------------------- //-----------------------------------------------------------------------------
static void show_animated_bitmap(grs_canvas &canvas, briefing *br) static void show_animated_bitmap(grs_canvas &canvas, briefing *br)
{ {
grs_bitmap *bitmap_ptr;
#if DXX_USE_OGL #if DXX_USE_OGL
float scale = 1.0; float scale = 1.0;
@ -1118,7 +1117,7 @@ static void show_animated_bitmap(grs_canvas &canvas, briefing *br)
if (br->door_div_count) { if (br->door_div_count) {
if (br->bitmap_name[0] != 0) { if (br->bitmap_name[0] != 0) {
const auto bi = piggy_find_bitmap(br->bitmap_name); const auto bi = piggy_find_bitmap(br->bitmap_name);
bitmap_ptr = &GameBitmaps[bi.index]; grs_bitmap *const bitmap_ptr = &GameBitmaps[bi];
PIGGY_PAGE_IN( bi ); PIGGY_PAGE_IN( bi );
#if DXX_USE_OGL #if DXX_USE_OGL
ogl_ubitmapm_cs(canvas, rescale_x(canvas.cv_bitmap, 220), rescale_y(canvas.cv_bitmap, 45), bitmap_ptr->bm_w * scale, bitmap_ptr->bm_h * scale, *bitmap_ptr, 255); ogl_ubitmapm_cs(canvas, rescale_x(canvas.cv_bitmap, 220), rescale_y(canvas.cv_bitmap, 45), bitmap_ptr->bm_w * scale, bitmap_ptr->bm_h * scale, *bitmap_ptr, 255);
@ -1190,7 +1189,7 @@ static void show_animated_bitmap(grs_canvas &canvas, briefing *br)
} }
const auto bi = piggy_find_bitmap(br->bitmap_name); const auto bi = piggy_find_bitmap(br->bitmap_name);
bitmap_ptr = &GameBitmaps[bi.index]; grs_bitmap *const bitmap_ptr = &GameBitmaps[bi];
PIGGY_PAGE_IN( bi ); PIGGY_PAGE_IN( bi );
#if DXX_USE_OGL #if DXX_USE_OGL
ogl_ubitmapm_cs(subcanvas, 0, 0, bitmap_ptr->bm_w*scale, bitmap_ptr->bm_h*scale, *bitmap_ptr, 255); ogl_ubitmapm_cs(subcanvas, 0, 0, bitmap_ptr->bm_w*scale, bitmap_ptr->bm_h*scale, *bitmap_ptr, 255);

View file

@ -153,7 +153,7 @@ static std::pair<uint_fast32_t, uint_fast32_t> get_transparency_check_values(con
static uint_fast32_t check_transparency(const GameBitmaps_array &GameBitmaps, const Textures_array &Textures, const unique_side &side) static uint_fast32_t check_transparency(const GameBitmaps_array &GameBitmaps, const Textures_array &Textures, const unique_side &side)
{ {
const auto &&v = get_transparency_check_values(side); const auto &&v = get_transparency_check_values(side);
return GameBitmaps[Textures[v.first].index].get_flag_mask(v.second); return GameBitmaps[Textures[v.first]].get_flag_mask(v.second);
} }
} }

View file

@ -1789,8 +1789,6 @@ void do_seismic_stuff(void)
} }
DEFINE_BITMAP_SERIAL_UDT();
namespace serial { namespace serial {
template <typename T> template <typename T>