allow a global override to enable radiosity mode on _surface
allow Q2-style rads and Q1-style rads to be added together; also mimic the behavior of _surface which loads multiple lights for a single surface
This commit is contained in:
parent
210d994445
commit
e97ad64bdc
|
|
@ -130,13 +130,6 @@ const std::vector<sun_t> &GetSuns();
|
||||||
|
|
||||||
const std::vector<std::unique_ptr<light_t>> &GetSurfaceLightTemplates();
|
const std::vector<std::unique_ptr<light_t>> &GetSurfaceLightTemplates();
|
||||||
|
|
||||||
enum {
|
|
||||||
// Q1-style surface light copies
|
|
||||||
SURFLIGHT_Q1 = 0,
|
|
||||||
// Q2/Q3-style radiosity
|
|
||||||
SURFLIGHT_RAD = 1
|
|
||||||
};
|
|
||||||
|
|
||||||
bool FaceMatchesSurfaceLightTemplate(const mbsp_t *bsp, const mface_t *face, const light_t &surflight, int surf_type);
|
bool FaceMatchesSurfaceLightTemplate(const mbsp_t *bsp, const mface_t *face, const light_t &surflight, int surf_type);
|
||||||
|
|
||||||
const entdict_t *FindEntDictWithKeyPair(const std::string &key, const std::string &value);
|
const entdict_t *FindEntDictWithKeyPair(const std::string &key, const std::string &value);
|
||||||
|
|
|
||||||
|
|
@ -268,6 +268,13 @@ enum class visapprox_t
|
||||||
// worldspawn keys / command-line settings
|
// worldspawn keys / command-line settings
|
||||||
//
|
//
|
||||||
|
|
||||||
|
enum {
|
||||||
|
// Q1-style surface light copies
|
||||||
|
SURFLIGHT_Q1 = 0,
|
||||||
|
// Q2/Q3-style radiosity
|
||||||
|
SURFLIGHT_RAD = 1
|
||||||
|
};
|
||||||
|
|
||||||
namespace settings
|
namespace settings
|
||||||
{
|
{
|
||||||
extern setting_group worldspawn_group;
|
extern setting_group worldspawn_group;
|
||||||
|
|
@ -333,6 +340,7 @@ public:
|
||||||
setting_scalar sun_deviance{this, "sunlight_penumbra", 0.0, 0.0, 180.0, &worldspawn_group};
|
setting_scalar sun_deviance{this, "sunlight_penumbra", 0.0, 0.0, 180.0, &worldspawn_group};
|
||||||
setting_vec3 sky_surface{
|
setting_vec3 sky_surface{
|
||||||
this, {"sky_surface", "sun_surface"}, 0, 0, 0, &worldspawn_group} /* arghrad surface lights on sky faces */;
|
this, {"sky_surface", "sun_surface"}, 0, 0, 0, &worldspawn_group} /* arghrad surface lights on sky faces */;
|
||||||
|
setting_int32 surflight_radiosity{this, "surflight_radiosity", SURFLIGHT_Q1, &worldspawn_group, "whether to use Q1-style surface subdivision (0) or Q2-style surface radiosity"};
|
||||||
};
|
};
|
||||||
|
|
||||||
extern setting_group output_group;
|
extern setting_group output_group;
|
||||||
|
|
|
||||||
|
|
@ -1182,8 +1182,17 @@ static aabb3d BoundPoly(int numverts, qvec3d *verts)
|
||||||
bool FaceMatchesSurfaceLightTemplate(const mbsp_t *bsp, const mface_t *face, const light_t &surflight, int surf_type)
|
bool FaceMatchesSurfaceLightTemplate(const mbsp_t *bsp, const mface_t *face, const light_t &surflight, int surf_type)
|
||||||
{
|
{
|
||||||
const char *texname = Face_TextureName(bsp, face);
|
const char *texname = Face_TextureName(bsp, face);
|
||||||
|
|
||||||
|
int32_t radiosity_type;
|
||||||
|
|
||||||
|
if (surflight.epairs->has("_surface_radiosity")) {
|
||||||
|
radiosity_type = surflight.epairs->get_int("_surface_radiosity");
|
||||||
|
} else {
|
||||||
|
radiosity_type = options.surflight_radiosity.value();
|
||||||
|
}
|
||||||
|
|
||||||
return !Q_strcasecmp(texname, surflight.epairs->get("_surface")) &&
|
return !Q_strcasecmp(texname, surflight.epairs->get("_surface")) &&
|
||||||
!!surflight.epairs->get_int("_surface_radiosity") == surf_type;
|
radiosity_type == surf_type;
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
|
||||||
|
|
@ -46,53 +46,8 @@ std::vector<surfacelight_t> surfacelights;
|
||||||
std::map<int, std::vector<int>> surfacelightsByFacenum;
|
std::map<int, std::vector<int>> surfacelightsByFacenum;
|
||||||
int total_surflight_points = 0;
|
int total_surflight_points = 0;
|
||||||
|
|
||||||
static void MakeSurfaceLightsThread(const mbsp_t *bsp, const settings::worldspawn_keys &cfg, size_t i)
|
static void MakeSurfaceLight(const mbsp_t *bsp, const settings::worldspawn_keys &cfg, const mface_t *face, std::optional<qvec3f> texture_color, bool is_directional, bool is_sky, int32_t style, int32_t light_value)
|
||||||
{
|
{
|
||||||
const mface_t *face = BSP_GetFace(bsp, i);
|
|
||||||
|
|
||||||
// Face casts light?
|
|
||||||
|
|
||||||
int32_t light_value = 0;
|
|
||||||
bool is_sky = false, is_directional = false;
|
|
||||||
int32_t style = 0;
|
|
||||||
std::optional<qvec3f> texture_color;
|
|
||||||
|
|
||||||
if (bsp->loadversion->game->id == GAME_QUAKE_II) {
|
|
||||||
// first, check if it's a Q2 surface
|
|
||||||
const mtexinfo_t *info = Face_Texinfo(bsp, face);
|
|
||||||
|
|
||||||
if (info == nullptr)
|
|
||||||
return;
|
|
||||||
|
|
||||||
if (!(info->flags.native & Q2_SURF_LIGHT) || info->value == 0) {
|
|
||||||
if (info->flags.native & Q2_SURF_LIGHT) {
|
|
||||||
qvec3d wc = winding_t::from_face(bsp, face).center();
|
|
||||||
logging::print("WARNING: surface light '{}' at [{}] has 0 intensity.\n", Face_TextureName(bsp, face), wc);
|
|
||||||
}
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
light_value = info->value;
|
|
||||||
is_sky = (info->flags.native & Q2_SURF_SKY);
|
|
||||||
}
|
|
||||||
|
|
||||||
// check matching templates
|
|
||||||
if (!light_value) {
|
|
||||||
for (const auto &surflight : GetSurfaceLightTemplates()) {
|
|
||||||
if (FaceMatchesSurfaceLightTemplate(bsp, face, *surflight, SURFLIGHT_RAD)) {
|
|
||||||
light_value = surflight->light.value();
|
|
||||||
is_sky = surflight->epairs->get_int("_surface_is_sky");
|
|
||||||
is_directional = !!surflight->epairs->get_int("_surface_spotlight");
|
|
||||||
style = surflight->epairs->get_int("style");
|
|
||||||
|
|
||||||
if (surflight->color.isChanged()) {
|
|
||||||
texture_color = surflight->color.value() / 255.f;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Create face points...
|
// Create face points...
|
||||||
auto poly = GLM_FacePoints(bsp, face);
|
auto poly = GLM_FacePoints(bsp, face);
|
||||||
const float facearea = qv::PolyArea(poly.begin(), poly.end());
|
const float facearea = qv::PolyArea(poly.begin(), poly.end());
|
||||||
|
|
@ -176,6 +131,45 @@ static void MakeSurfaceLightsThread(const mbsp_t *bsp, const settings::worldspaw
|
||||||
surfacelightsByFacenum[Face_GetNum(bsp, face)].push_back(index);
|
surfacelightsByFacenum[Face_GetNum(bsp, face)].push_back(index);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void MakeSurfaceLightsThread(const mbsp_t *bsp, const settings::worldspawn_keys &cfg, size_t i)
|
||||||
|
{
|
||||||
|
const mface_t *face = BSP_GetFace(bsp, i);
|
||||||
|
|
||||||
|
// Face casts light?
|
||||||
|
|
||||||
|
if (bsp->loadversion->game->id == GAME_QUAKE_II) {
|
||||||
|
// first, check if it's a Q2 surface
|
||||||
|
const mtexinfo_t *info = Face_Texinfo(bsp, face);
|
||||||
|
|
||||||
|
if (info == nullptr)
|
||||||
|
return;
|
||||||
|
|
||||||
|
if (!(info->flags.native & Q2_SURF_LIGHT) || info->value == 0) {
|
||||||
|
if (info->flags.native & Q2_SURF_LIGHT) {
|
||||||
|
qvec3d wc = winding_t::from_face(bsp, face).center();
|
||||||
|
logging::print("WARNING: surface light '{}' at [{}] has 0 intensity.\n", Face_TextureName(bsp, face), wc);
|
||||||
|
}
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
MakeSurfaceLight(bsp, cfg, face, std::nullopt, false, (info->flags.native & Q2_SURF_SKY), 0, info->value);
|
||||||
|
}
|
||||||
|
|
||||||
|
// check matching templates
|
||||||
|
for (const auto &surflight : GetSurfaceLightTemplates()) {
|
||||||
|
if (FaceMatchesSurfaceLightTemplate(bsp, face, *surflight, SURFLIGHT_RAD)) {
|
||||||
|
std::optional<qvec3f> texture_color;
|
||||||
|
|
||||||
|
if (surflight->color.isChanged()) {
|
||||||
|
texture_color = surflight->color.value() / 255.f;
|
||||||
|
}
|
||||||
|
|
||||||
|
MakeSurfaceLight(bsp, cfg, face, texture_color, !!surflight->epairs->get_int("_surface_spotlight"),
|
||||||
|
surflight->epairs->get_int("_surface_is_sky"), surflight->epairs->get_int("style"), surflight->light.value());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
const std::vector<surfacelight_t> &SurfaceLights()
|
const std::vector<surfacelight_t> &SurfaceLights()
|
||||||
{
|
{
|
||||||
return surfacelights;
|
return surfacelights;
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue