move making contents valid from brush parsing into gamedef

This commit is contained in:
Jonathan 2022-06-15 09:07:37 -04:00
parent 3474dd00c5
commit 8afcc54b74
3 changed files with 49 additions and 23 deletions

View File

@ -110,6 +110,8 @@ struct gamedef_generic_t : public gamedef_t
std::string get_contents_display(const contentflags_t &) const override { throw std::bad_cast(); }
void contents_make_valid(contentflags_t &contents) const override { throw std::bad_cast(); }
const std::initializer_list<aabb3d> &get_hull_sizes() const override { throw std::bad_cast(); }
contentflags_t face_get_contents(const std::string &, const surfflags_t &, const contentflags_t &) const override { throw std::bad_cast(); }
@ -457,27 +459,36 @@ public:
}
if (contents_are_clip(contents)) {
base += "| CLIP";
base += " | CLIP";
}
if (contents_are_origin(contents)) {
base += "| ORIGIN";
base += " | ORIGIN";
}
switch (get_data(contents).detail) {
case detail_type_t::DETAIL:
base += "| DETAIL";
base += " | DETAIL";
break;
case detail_type_t::ILLUSIONARY:
base += "| DETAIL[ILLUSIONARY]";
base += " | DETAIL[ILLUSIONARY]";
break;
case detail_type_t::FENCE:
base += "| DETAIL[FENCE]";
base += " | DETAIL[FENCE]";
break;
}
return base;
}
void contents_make_valid(contentflags_t &contents) const override
{
// todo: anything smarter we can do here?
// think this can't even happen in Q1 anyways
if (!contents_are_valid(contents, false)) {
contents = { CONTENTS_SOLID };
}
}
const std::initializer_list<aabb3d> &get_hull_sizes() const
{
static std::initializer_list<aabb3d> hulls = {
@ -1007,6 +1018,26 @@ struct gamedef_q2_t : public gamedef_t
return s;
}
void contents_make_valid(contentflags_t &contents) const override
{
if (contents_are_valid(contents, false)) {
return;
}
bool got = false;
for (int32_t i = 0; i < 8; i++) {
if (!got) {
if (contents.native & nth_bit(i)) {
got = true;
continue;
}
} else {
contents.native &= ~nth_bit(i);
}
}
}
const std::initializer_list<aabb3d> &get_hull_sizes() const
{
static constexpr std::initializer_list<aabb3d> hulls = {};
@ -1477,6 +1508,11 @@ bool contentflags_t::is_origin(const gamedef_t *game) const
return game->contents_are_origin(*this);
}
void contentflags_t::make_valid(const gamedef_t *game)
{
game->contents_make_valid(*this);
}
std::string contentflags_t::to_string(const gamedef_t *game) const
{
std::string s = game->get_contents_display(*this);

View File

@ -614,6 +614,8 @@ struct contentflags_t
bool is_clip(const gamedef_t *game) const;
bool is_origin(const gamedef_t *game) const;
void make_valid(const gamedef_t *game);
inline bool is_fence(const gamedef_t *game) const {
return is_detail_fence(game) || is_detail_illusionary(game);
}
@ -1825,6 +1827,7 @@ struct gamedef_t
virtual contentflags_t contents_remap_for_export(const contentflags_t &contents) const = 0;
virtual contentflags_t combine_contents(const contentflags_t &a, const contentflags_t &b) const = 0;
virtual std::string get_contents_display(const contentflags_t &contents) const = 0;
virtual void contents_make_valid(contentflags_t &contents) const = 0;
virtual const std::initializer_list<aabb3d> &get_hull_sizes() const = 0;
virtual contentflags_t face_get_contents(
const std::string &texname, const surfflags_t &flags, const contentflags_t &contents) const = 0;

View File

@ -1410,25 +1410,12 @@ static void ParseTextureDef(parser_t &parser, mapface_t &mapface, const mapbrush
tx->flags = mapface.flags = {extinfo.info->flags};
tx->value = mapface.value = extinfo.info->value;
if (!contentflags_t{mapface.contents}.is_valid(options.target_game, false))
{
logging::print("WARNING: line {}: face has invalid contents {} ({})\n", mapface.linenum, mapface.contents.to_string(options.target_game), mapface.contents.native);
// TODO: move into game
if (options.target_game->id == GAME_QUAKE_II) {
bool got = false;
contentflags_t contents { mapface.contents };
for (int i = 0; i < 8; i++) {
if (!got) {
if (mapface.contents.native & nth_bit(i)) {
got = true;
continue;
}
} else {
mapface.contents.native &= ~nth_bit(i);
}
}
}
if (!contents.is_valid(options.target_game, false)) {
auto old_contents = contents;
options.target_game->contents_make_valid(contents);
logging::print("WARNING: line {}: face has invalid contents {}, remapped to {}\n", mapface.linenum, old_contents.to_string(options.target_game), contents.to_string(options.target_game));
}
switch (tx_type) {