mirror of
https://github.com/ZDoom/ZDRay.git
synced 2024-11-22 20:11:11 +00:00
Move sample distance, bounces and light probe grid size settings to the zdrayinfo actor as they affect map visuals
This commit is contained in:
parent
cd3563759c
commit
031dc4a4db
8 changed files with 62 additions and 61 deletions
33
README.md
33
README.md
|
@ -1,13 +1,29 @@
|
||||||
|
|
||||||
# ZDRay baking utility for GZDoom
|
# ZDRay baking utility for GZDoom
|
||||||
|
|
||||||
ZDRay is a node and lightmap generator. It is based on zdbsp for the node generation and dlight for the lightmap generation.
|
ZDRay is a node and lightmap generator for GZDoom. ZDRay is intended as a drop-in replacement for zdbsp, with the additional feature
|
||||||
|
that it can also bake lights. Once ZDRay has processed the level WAD it is ready to be used by GZDoom.
|
||||||
|
|
||||||
Special thanks to Randi Heit, Samuel Villarreal, Christoph Oelckers and anyone else involved in creating or maintaining those tools.
|
ZDRay is based on zdbsp for the node generation and originally used dlight for the lightmap generation. Special thanks to Randi Heit,
|
||||||
|
Samuel Villarreal, Christoph Oelckers and anyone else involved in creating or maintaining those tools.
|
||||||
|
|
||||||
|
The ray tracing code has been completely rewritten since. It now supports bounces and can do the ray tracing on the GPU.
|
||||||
|
|
||||||
## ZDRay UDMF properties
|
## ZDRay UDMF properties
|
||||||
|
|
||||||
<pre>
|
<pre>
|
||||||
|
thing // ZDRayInfo (zdray properties for the map)
|
||||||
|
{
|
||||||
|
type = 9890;
|
||||||
|
suncolor = <int> (color)
|
||||||
|
sundirx = <float> (X direction for the sun)
|
||||||
|
sundiry = <float> (Y direction for the sun)
|
||||||
|
sundirz = <float> (Z direction for the sun)
|
||||||
|
sampledistance = <int> (default: 8, map units each lightmap texel covers, must be in powers of two)
|
||||||
|
bounces = <int> (default: 1, how many times light bounces off walls)
|
||||||
|
gridsize = <float> (default: 32, grid density for the automatic light probes)
|
||||||
|
}
|
||||||
|
|
||||||
thing // StaticLight (point or spot light to be baked into the lightmap)
|
thing // StaticLight (point or spot light to be baked into the lightmap)
|
||||||
{
|
{
|
||||||
lightcolor = <int> (color)
|
lightcolor = <int> (color)
|
||||||
|
@ -22,23 +38,14 @@ thing // LightProbe (light sampling point for actors)
|
||||||
type = 9875;
|
type = 9875;
|
||||||
}
|
}
|
||||||
|
|
||||||
thing // Sunlight (sunlight properties for the map)
|
linedef // Line emissive surface
|
||||||
{
|
|
||||||
type = 9890;
|
|
||||||
suncolor = <int> (color)
|
|
||||||
sundirx = <float> (X direction for the sun)
|
|
||||||
sundiry = <float> (Y direction for the sun)
|
|
||||||
sundirz = <float> (Z direction for the sun)
|
|
||||||
}
|
|
||||||
|
|
||||||
linedef // Line surface emitting
|
|
||||||
{
|
{
|
||||||
lightcolor = <int> (color, default: white)
|
lightcolor = <int> (color, default: white)
|
||||||
lightintensity = <float> (default: 1)
|
lightintensity = <float> (default: 1)
|
||||||
lightdistance = <float> (default: 0, no light)
|
lightdistance = <float> (default: 0, no light)
|
||||||
}
|
}
|
||||||
|
|
||||||
sector // Sector planes emitting light
|
sector // Sector plane emissive surface
|
||||||
{
|
{
|
||||||
lightcolorfloor = <int> (color, default: white)
|
lightcolorfloor = <int> (color, default: white)
|
||||||
lightintensityfloor = <float> (default: 1)
|
lightintensityfloor = <float> (default: 1)
|
||||||
|
|
|
@ -387,8 +387,11 @@ struct FLevel
|
||||||
TArray<SurfaceLightDef> SurfaceLights;
|
TArray<SurfaceLightDef> SurfaceLights;
|
||||||
TArray<int> ThingLightProbes;
|
TArray<int> ThingLightProbes;
|
||||||
|
|
||||||
Vec3 defaultSunColor = Vec3(1, 1, 1);
|
Vec3 defaultSunColor;
|
||||||
Vec3 defaultSunDirection = Vec3(0.45f, 0.3f, 0.9f);
|
Vec3 defaultSunDirection;
|
||||||
|
int Samples;
|
||||||
|
int LightBounce;
|
||||||
|
float GridSize;
|
||||||
|
|
||||||
void FindMapBounds ();
|
void FindMapBounds ();
|
||||||
void RemoveExtraLines ();
|
void RemoveExtraLines ();
|
||||||
|
|
|
@ -30,7 +30,6 @@
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
extern int LMDims;
|
extern int LMDims;
|
||||||
extern int Samples;
|
|
||||||
extern bool CPURaytrace;
|
extern bool CPURaytrace;
|
||||||
|
|
||||||
extern void ShowView (FLevel *level);
|
extern void ShowView (FLevel *level);
|
||||||
|
@ -693,7 +692,7 @@ void FProcessor::BuildNodes()
|
||||||
void FProcessor::BuildLightmaps()
|
void FProcessor::BuildLightmaps()
|
||||||
{
|
{
|
||||||
Level.SetupLights();
|
Level.SetupLights();
|
||||||
LightmapMesh = std::make_unique<LevelMesh>(Level, Samples, LMDims);
|
LightmapMesh = std::make_unique<LevelMesh>(Level, Level.Samples, LMDims);
|
||||||
|
|
||||||
if (CPURaytrace)
|
if (CPURaytrace)
|
||||||
{
|
{
|
||||||
|
|
|
@ -84,6 +84,13 @@ void FLevel::SetupLights()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// GG to whoever memset'ed FLevel
|
||||||
|
defaultSunColor = Vec3(1, 1, 1);
|
||||||
|
defaultSunDirection = Vec3(0.45f, 0.3f, 0.9f);
|
||||||
|
Samples = 8;
|
||||||
|
LightBounce = 1;
|
||||||
|
GridSize = 32.0f;
|
||||||
|
|
||||||
for (int i = 0; i < (int)Things.Size(); ++i)
|
for (int i = 0; i < (int)Things.Size(); ++i)
|
||||||
{
|
{
|
||||||
IntThing* thing = &Things[i];
|
IntThing* thing = &Things[i];
|
||||||
|
@ -91,7 +98,7 @@ void FLevel::SetupLights()
|
||||||
{
|
{
|
||||||
ThingLightProbes.Push(i);
|
ThingLightProbes.Push(i);
|
||||||
}
|
}
|
||||||
else if (thing->type == 9890) // Sunlight
|
else if (thing->type == 9890) // ZDRayInfo
|
||||||
{
|
{
|
||||||
uint32_t lightcolor = 0xffffff;
|
uint32_t lightcolor = 0xffffff;
|
||||||
Vec3 sundir(0.0f, 0.0f, 0.0f);
|
Vec3 sundir(0.0f, 0.0f, 0.0f);
|
||||||
|
@ -116,6 +123,25 @@ void FLevel::SetupLights()
|
||||||
{
|
{
|
||||||
sundir.z = atof(key.value);
|
sundir.z = atof(key.value);
|
||||||
}
|
}
|
||||||
|
else if (!stricmp(key.key, "sampledistance"))
|
||||||
|
{
|
||||||
|
Samples = atoi(key.value);
|
||||||
|
if (Samples <= 0) Samples = 1;
|
||||||
|
if (Samples > 128) Samples = 128;
|
||||||
|
Samples = Math::RoundPowerOfTwo(Samples);
|
||||||
|
}
|
||||||
|
else if (!stricmp(key.key, "bounces"))
|
||||||
|
{
|
||||||
|
LightBounce = atoi(key.value);
|
||||||
|
if (LightBounce < 0) LightBounce = 0;
|
||||||
|
if (LightBounce > 8) LightBounce = 8;
|
||||||
|
}
|
||||||
|
else if (!stricmp(key.key, "gridsize"))
|
||||||
|
{
|
||||||
|
GridSize = atof(key.value);
|
||||||
|
if (GridSize < 0.f) GridSize = 0.f;
|
||||||
|
if (GridSize > 1024.f) GridSize = 1024.f;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Vec3::Dot(sundir, sundir) > 0.01f)
|
if (Vec3::Dot(sundir, sundir) > 0.01f)
|
||||||
|
|
|
@ -12,7 +12,6 @@
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <zlib.h>
|
#include <zlib.h>
|
||||||
|
|
||||||
extern int LightBounce;
|
|
||||||
extern bool VKDebug;
|
extern bool VKDebug;
|
||||||
|
|
||||||
CPURaytracer::CPURaytracer()
|
CPURaytracer::CPURaytracer()
|
||||||
|
@ -59,7 +58,7 @@ void CPURaytracer::Raytrace(LevelMesh* level)
|
||||||
CreateHemisphereVectors();
|
CreateHemisphereVectors();
|
||||||
CreateLights();
|
CreateLights();
|
||||||
|
|
||||||
printf("Ray tracing with %d bounce(s)\n", LightBounce);
|
printf("Ray tracing with %d bounce(s)\n", mesh->map->LightBounce);
|
||||||
|
|
||||||
Worker::RunJob((int)tasks.size(), [=](int id) { RaytraceTask(tasks[id]); });
|
Worker::RunJob((int)tasks.size(), [=](int id) { RaytraceTask(tasks[id]); });
|
||||||
|
|
||||||
|
@ -107,7 +106,7 @@ void CPURaytracer::RaytraceTask(const CPUTraceTask& task)
|
||||||
state.HemisphereVec = HemisphereVectors[state.SampleIndex];
|
state.HemisphereVec = HemisphereVectors[state.SampleIndex];
|
||||||
RunBounceTrace(state);
|
RunBounceTrace(state);
|
||||||
|
|
||||||
for (int bounce = 0; bounce < LightBounce && !state.EndTrace; bounce++)
|
for (int bounce = 0; bounce < mesh->map->LightBounce && !state.EndTrace; bounce++)
|
||||||
{
|
{
|
||||||
state.SampleCount = coverageSampleCount;
|
state.SampleCount = coverageSampleCount;
|
||||||
RunLightTrace(state);
|
RunLightTrace(state);
|
||||||
|
|
|
@ -21,7 +21,6 @@
|
||||||
#include "glsl_rmiss_light.h"
|
#include "glsl_rmiss_light.h"
|
||||||
#include "glsl_rmiss_sun.h"
|
#include "glsl_rmiss_sun.h"
|
||||||
|
|
||||||
extern int LightBounce;
|
|
||||||
extern bool VKDebug;
|
extern bool VKDebug;
|
||||||
|
|
||||||
GPURaytracer::GPURaytracer()
|
GPURaytracer::GPURaytracer()
|
||||||
|
@ -86,7 +85,7 @@ void GPURaytracer::Raytrace(LevelMesh* level)
|
||||||
HemisphereVectors.push_back(H);
|
HemisphereVectors.push_back(H);
|
||||||
}
|
}
|
||||||
|
|
||||||
printf("Ray tracing with %d bounce(s)\n", LightBounce);
|
printf("Ray tracing with %d bounce(s)\n", mesh->map->LightBounce);
|
||||||
|
|
||||||
size_t maxTasks = (size_t)rayTraceImageSize * rayTraceImageSize;
|
size_t maxTasks = (size_t)rayTraceImageSize * rayTraceImageSize;
|
||||||
for (size_t startTask = 0; startTask < tasks.size(); startTask += maxTasks)
|
for (size_t startTask = 0; startTask < tasks.size(); startTask += maxTasks)
|
||||||
|
@ -119,7 +118,7 @@ void GPURaytracer::Raytrace(LevelMesh* level)
|
||||||
uniforms.HemisphereVec = HemisphereVectors[uniforms.SampleIndex];
|
uniforms.HemisphereVec = HemisphereVectors[uniforms.SampleIndex];
|
||||||
RunTrace(uniforms, rgenBounceRegion);
|
RunTrace(uniforms, rgenBounceRegion);
|
||||||
|
|
||||||
for (int bounce = 0; bounce < LightBounce; bounce++)
|
for (int bounce = 0; bounce < mesh->map->LightBounce; bounce++)
|
||||||
{
|
{
|
||||||
uniforms.SampleCount = coverageSampleCount;
|
uniforms.SampleCount = coverageSampleCount;
|
||||||
RunTrace(uniforms, rgenLightRegion);
|
RunTrace(uniforms, rgenLightRegion);
|
||||||
|
|
|
@ -34,8 +34,6 @@
|
||||||
#include "pngwriter.h"
|
#include "pngwriter.h"
|
||||||
#include <map>
|
#include <map>
|
||||||
|
|
||||||
extern float GridSize;
|
|
||||||
|
|
||||||
#ifdef _MSC_VER
|
#ifdef _MSC_VER
|
||||||
#pragma warning(disable: 4267) // warning C4267: 'argument': conversion from 'size_t' to 'int', possible loss of data
|
#pragma warning(disable: 4267) // warning C4267: 'argument': conversion from 'size_t' to 'int', possible loss of data
|
||||||
#pragma warning(disable: 4244) // warning C4244: '=': conversion from '__int64' to 'int', possible loss of data
|
#pragma warning(disable: 4244) // warning C4244: '=': conversion from '__int64' to 'int', possible loss of data
|
||||||
|
@ -392,12 +390,12 @@ void LevelMesh::CreateLightProbes(FLevel& map)
|
||||||
float maxX = std::floor(map.MaxX / 65536.0f) + 1.0f;
|
float maxX = std::floor(map.MaxX / 65536.0f) + 1.0f;
|
||||||
float maxY = std::floor(map.MaxY / 65536.0f) + 1.0f;
|
float maxY = std::floor(map.MaxY / 65536.0f) + 1.0f;
|
||||||
|
|
||||||
float halfGridSize = GridSize * 0.5f;
|
float halfGridSize = map.GridSize * 0.5f;
|
||||||
float doubleGridSize = GridSize * 2.0f;
|
float doubleGridSize = map.GridSize * 2.0f;
|
||||||
|
|
||||||
for (float y = minY; y < maxY; y += GridSize)
|
for (float y = minY; y < maxY; y += map.GridSize)
|
||||||
{
|
{
|
||||||
for (float x = minX; x < maxX; x += GridSize)
|
for (float x = minX; x < maxX; x += map.GridSize)
|
||||||
{
|
{
|
||||||
MapSubsectorEx* ssec = map.PointInSubSector((int)x, (int)y);
|
MapSubsectorEx* ssec = map.PointInSubSector((int)x, (int)y);
|
||||||
IntSector* sec = ssec ? map.GetSectorFromSubSector(ssec) : nullptr;
|
IntSector* sec = ssec ? map.GetSectorFromSubSector(ssec) : nullptr;
|
||||||
|
|
32
src/main.cpp
32
src/main.cpp
|
@ -115,11 +115,8 @@ bool HaveSSE1, HaveSSE2;
|
||||||
int SSELevel;
|
int SSELevel;
|
||||||
int NumThreads = 0;
|
int NumThreads = 0;
|
||||||
int LMDims = 1024;
|
int LMDims = 1024;
|
||||||
int Samples = 8;
|
|
||||||
bool CPURaytrace = false;
|
bool CPURaytrace = false;
|
||||||
bool VKDebug = false;
|
bool VKDebug = false;
|
||||||
int LightBounce = 1;
|
|
||||||
float GridSize = 32.0f;
|
|
||||||
|
|
||||||
// PRIVATE DATA DEFINITIONS ------------------------------------------------
|
// PRIVATE DATA DEFINITIONS ------------------------------------------------
|
||||||
|
|
||||||
|
@ -155,16 +152,13 @@ static option long_opts[] =
|
||||||
{"no-sse2", no_argument, 0, 1003},
|
{"no-sse2", no_argument, 0, 1003},
|
||||||
{"comments", no_argument, 0, 'c'},
|
{"comments", no_argument, 0, 'c'},
|
||||||
{"threads", required_argument, 0, 'j'},
|
{"threads", required_argument, 0, 'j'},
|
||||||
{"samples", required_argument, 0, 'Q'},
|
|
||||||
{"size", required_argument, 0, 'S'},
|
{"size", required_argument, 0, 'S'},
|
||||||
{"cpu-raytrace", no_argument, 0, 'C'},
|
{"cpu-raytrace", no_argument, 0, 'C'},
|
||||||
{"bounce", required_argument, 0, 'B'},
|
|
||||||
{"gridsize", required_argument, 0, 'i'},
|
|
||||||
{"vkdebug", no_argument, 0, 'D'},
|
{"vkdebug", no_argument, 0, 'D'},
|
||||||
{0,0,0,0}
|
{0,0,0,0}
|
||||||
};
|
};
|
||||||
|
|
||||||
static const char short_opts[] = "wVgGvbNrReEm:o:f:p:s:d:PqtzZXx5cj:Q:S:CD";
|
static const char short_opts[] = "wVgGvbNrReEm:o:f:p:s:d:PqtzZXx5cj:S:CD";
|
||||||
|
|
||||||
// CODE --------------------------------------------------------------------
|
// CODE --------------------------------------------------------------------
|
||||||
|
|
||||||
|
@ -439,12 +433,6 @@ static void ParseArgs(int argc, char **argv)
|
||||||
case 'j':
|
case 'j':
|
||||||
NumThreads = atoi(optarg);
|
NumThreads = atoi(optarg);
|
||||||
break;
|
break;
|
||||||
case 'Q':
|
|
||||||
Samples = atoi(optarg);
|
|
||||||
if (Samples <= 0) Samples = 1;
|
|
||||||
if (Samples > 128) Samples = 128;
|
|
||||||
Samples = Math::RoundPowerOfTwo(Samples);
|
|
||||||
break;
|
|
||||||
case 'S':
|
case 'S':
|
||||||
LMDims = atoi(optarg);
|
LMDims = atoi(optarg);
|
||||||
if (LMDims <= 0) LMDims = 1;
|
if (LMDims <= 0) LMDims = 1;
|
||||||
|
@ -457,15 +445,6 @@ static void ParseArgs(int argc, char **argv)
|
||||||
case 'D':
|
case 'D':
|
||||||
VKDebug = true;
|
VKDebug = true;
|
||||||
break;
|
break;
|
||||||
case 'B':
|
|
||||||
LightBounce = atoi(optarg);
|
|
||||||
if (LightBounce < 0) LightBounce = 0;
|
|
||||||
if (LightBounce > 8) LightBounce = 8;
|
|
||||||
break;
|
|
||||||
case 'i':
|
|
||||||
GridSize = std::stof(optarg);
|
|
||||||
if (GridSize < 0.f) GridSize = 0.f;
|
|
||||||
break;
|
|
||||||
case 1000:
|
case 1000:
|
||||||
ShowUsage();
|
ShowUsage();
|
||||||
exit(0);
|
exit(0);
|
||||||
|
@ -508,15 +487,9 @@ static void ShowUsage()
|
||||||
" -d, --diagonal-cost=NNN Cost for avoiding diagonal splitters (default %d)\n"
|
" -d, --diagonal-cost=NNN Cost for avoiding diagonal splitters (default %d)\n"
|
||||||
" -P, --no-polyobjs Do not check for polyobject subsector splits\n"
|
" -P, --no-polyobjs Do not check for polyobject subsector splits\n"
|
||||||
" -j, --threads=NNN Number of threads used for raytracing (default %d)\n"
|
" -j, --threads=NNN Number of threads used for raytracing (default %d)\n"
|
||||||
" -Q, --samples=NNN Set texel sampling size (lowest = higher quaility but\n"
|
|
||||||
" slow compile time) must be in powers of two (default %d)\n"
|
|
||||||
" -S, --size=NNN lightmap texture dimensions for width and height\n"
|
" -S, --size=NNN lightmap texture dimensions for width and height\n"
|
||||||
" must be in powers of two (1, 2, 4, 8, 16, etc)\n"
|
" must be in powers of two (1, 2, 4, 8, 16, etc)\n"
|
||||||
" -C, --cpu-raytrace Use the CPU for ray tracing\n"
|
" -C, --cpu-raytrace Use the CPU for ray tracing\n"
|
||||||
" -B, --bounce=NNN Number of indirect light bounces (default %d, max 8)\n"
|
|
||||||
" -i, --gridsize=NNN Automatic light probe grid size, floating point\n"
|
|
||||||
" Lower values increase granularity at the expense of performance\n"
|
|
||||||
" Recommended: 32.0, 64.0, 128.0, etc (default %.1f)\n"
|
|
||||||
" -D, --vkdebug Print messages from the vulkan validation layer\n"
|
" -D, --vkdebug Print messages from the vulkan validation layer\n"
|
||||||
" -w, --warn Show warning messages\n"
|
" -w, --warn Show warning messages\n"
|
||||||
#if HAVE_TIMING
|
#if HAVE_TIMING
|
||||||
|
@ -531,9 +504,6 @@ static void ShowUsage()
|
||||||
, SplitCost
|
, SplitCost
|
||||||
, AAPreference
|
, AAPreference
|
||||||
, (int)std::thread::hardware_concurrency()
|
, (int)std::thread::hardware_concurrency()
|
||||||
, Samples
|
|
||||||
, LightBounce
|
|
||||||
, GridSize
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue