mirror of
https://github.com/jmarshall23/DoomRTX.git
synced 2026-08-12 08:11:10 +02:00
Decal screen space is now projection based.
This commit is contained in:
@@ -4513,8 +4513,6 @@ float4 PSScreenDecals(VSOut i) : SV_Target0
|
||||
{
|
||||
uint2 pixel = uint2(i.pos.xy);
|
||||
float3 worldPos = gScreenDecalPosition.Load(int3(pixel, 0)).xyz;
|
||||
float3 normal = QD3D12_SafeNormalizeOr(gScreenDecalNormal.Load(int3(pixel, 0)).xyz, float3(0.0, 0.0, 1.0));
|
||||
float3 geometricNormal = QD3D12_SafeNormalizeOr(cross(ddx(worldPos), ddy(worldPos)), normal);
|
||||
float3 decalColor = 0.0;
|
||||
float decalAlpha = 0.0;
|
||||
uint decalIndex = (uint)gScreenDecalIndex;
|
||||
@@ -4522,28 +4520,23 @@ float4 PSScreenDecals(VSOut i) : SV_Target0
|
||||
return float4(0.0, 0.0, 0.0, 0.0);
|
||||
|
||||
ScreenSpaceDecal d = gScreenDecals[decalIndex];
|
||||
float3 decalN = QD3D12_SafeNormalizeOr(d.normal, normal);
|
||||
float facing = saturate(abs(dot(geometricNormal, decalN)) * 4.0);
|
||||
if (facing <= 0.0)
|
||||
return float4(0.0, 0.0, 0.0, 0.0);
|
||||
float3 decalN = QD3D12_SafeNormalizeOr(d.normal, float3(0.0, 0.0, 1.0));
|
||||
|
||||
float3 rel = worldPos - d.origin;
|
||||
float decalDepth = max(d.depth, 1.0e-3);
|
||||
float depthDistance = abs(dot(rel, decalN));
|
||||
float depthFade = 1.0 - smoothstep(decalDepth, decalDepth + max(decalDepth * 0.25, 1.0), depthDistance);
|
||||
if (depthFade <= 0.0)
|
||||
float projectorDepth = max(d.depth, 1.0e-3);
|
||||
float projectorZ = dot(rel, decalN);
|
||||
if (abs(projectorZ) > projectorDepth)
|
||||
return float4(0.0, 0.0, 0.0, 0.0);
|
||||
|
||||
float3 axisU = QD3D12_SafeNormalizeOr(d.axisU, float3(1.0, 0.0, 0.0));
|
||||
float3 axisV = QD3D12_SafeNormalizeOr(d.axisV, cross(decalN, axisU));
|
||||
float2 uv = float2(dot(rel, axisU), dot(rel, axisV)) / max(d.halfSize, 1.0e-3);
|
||||
if (abs(uv.x) >= 1.0 || abs(uv.y) >= 1.0)
|
||||
if (abs(uv.x) > 1.0 || abs(uv.y) > 1.0)
|
||||
return float4(0.0, 0.0, 0.0, 0.0);
|
||||
|
||||
float2 texUv = float2(uv.x * 0.5 + 0.5, -uv.y * 0.5 + 0.5);
|
||||
float4 texel = gTex0.Sample(gSamp0, texUv);
|
||||
float edge = smoothstep(1.0, 0.75, max(abs(uv.x), abs(uv.y)));
|
||||
float mask = saturate(d.opacity) * facing * depthFade * edge * saturate(d.color.a) * saturate(texel.a);
|
||||
float mask = saturate(d.opacity) * saturate(d.color.a) * saturate(texel.a);
|
||||
if (d.blendMode == 1u)
|
||||
{
|
||||
decalColor = saturate(texel.rgb * mask);
|
||||
|
||||
@@ -124,8 +124,12 @@ static void R_NormalizeDecalBasis(renderWorldDecal_t& decal) {
|
||||
if (decal.size <= 0.0f) {
|
||||
decal.size = 64.0f;
|
||||
}
|
||||
const float minProjectorDepth = decal.size * 2.0f;
|
||||
if (decal.depth <= 0.0f) {
|
||||
decal.depth = 8.0f;
|
||||
decal.depth = minProjectorDepth;
|
||||
}
|
||||
else if (decal.depth < minProjectorDepth) {
|
||||
decal.depth = minProjectorDepth;
|
||||
}
|
||||
if (decal.opacity <= 0.0f) {
|
||||
decal.opacity = 1.0f;
|
||||
@@ -190,7 +194,8 @@ void idRenderWorldLocal::SubmitWorldDecalsToScreenSpace() const {
|
||||
dst.axisV.y = src.axisV.y;
|
||||
dst.axisV.z = src.axisV.z;
|
||||
dst.halfSize = src.size * 0.5f;
|
||||
dst.depth = src.depth;
|
||||
const float minProjectorDepth = src.size * 2.0f;
|
||||
dst.depth = (src.depth > minProjectorDepth) ? src.depth : minProjectorDepth;
|
||||
dst.opacity = src.opacity;
|
||||
dst.color[0] = src.color.x;
|
||||
dst.color[1] = src.color.y;
|
||||
|
||||
@@ -1980,18 +1980,22 @@ static bool CamWnd_BuildDecalAtPoint(CCamWnd* cam, const CPoint& point, renderWo
|
||||
}
|
||||
CamWnd_DecalColorFromSelectedMaterial(decal.material, decal.color);
|
||||
decal.origin = hitPoint;
|
||||
decal.normal = hitNormal;
|
||||
if ((decal.normal * dir) > 0.0f) {
|
||||
decal.normal = -decal.normal;
|
||||
}
|
||||
decal.axisU = decal.normal.Cross(cam->Camera().vup);
|
||||
decal.normal = -dir;
|
||||
decal.normal.Normalize();
|
||||
|
||||
decal.axisU = cam->Camera().vright - decal.normal * (cam->Camera().vright * decal.normal);
|
||||
if (decal.axisU.LengthSqr() < 0.0001f) {
|
||||
decal.axisU = decal.normal.Cross(cam->Camera().vright);
|
||||
decal.axisU = decal.normal.Cross(cam->Camera().vup);
|
||||
}
|
||||
decal.axisU.Normalize();
|
||||
decal.axisV = decal.normal.Cross(decal.axisU);
|
||||
CamWnd_RotateDecalBasis(decal, s_camWndDecalPreviewRotation);
|
||||
decal.size = CamWnd_DecalFloat("size", "64");
|
||||
decal.depth = CamWnd_DecalFloat("depth", "8");
|
||||
decal.depth = CamWnd_DecalFloat("depth", "0");
|
||||
const float minProjectorDepth = decal.size * 2.0f;
|
||||
if (decal.depth < minProjectorDepth) {
|
||||
decal.depth = minProjectorDepth;
|
||||
}
|
||||
decal.opacity = CamWnd_DecalFloat("opacity", "1");
|
||||
if (hitSource) {
|
||||
*hitSource = localHitSource;
|
||||
|
||||
@@ -109,8 +109,12 @@ static void Map_NormalizeDecal(renderWorldDecal_t& decal) {
|
||||
if (decal.size <= 0.0f) {
|
||||
decal.size = 64.0f;
|
||||
}
|
||||
const float minProjectorDepth = decal.size * 2.0f;
|
||||
if (decal.depth <= 0.0f) {
|
||||
decal.depth = 8.0f;
|
||||
decal.depth = minProjectorDepth;
|
||||
}
|
||||
else if (decal.depth < minProjectorDepth) {
|
||||
decal.depth = minProjectorDepth;
|
||||
}
|
||||
if (decal.opacity <= 0.0f) {
|
||||
decal.opacity = 1.0f;
|
||||
@@ -346,6 +350,7 @@ void Map_LoadDecals(const char* filename) {
|
||||
if (!token.Icmp("material")) {
|
||||
src.ExpectAnyToken(&token);
|
||||
decal.material = token;
|
||||
Texture_ForName(decal.material.c_str());
|
||||
} else if (!token.Icmp("origin")) {
|
||||
src.Parse1DMatrix(3, decal.origin.ToFloatPtr());
|
||||
} else if (!token.Icmp("normal")) {
|
||||
@@ -364,6 +369,7 @@ void Map_LoadDecals(const char* filename) {
|
||||
src.Parse1DMatrix(4, decal.color.ToFloatPtr());
|
||||
}
|
||||
}
|
||||
Texture_ForName(decal.material.c_str());
|
||||
Map_AddDecal(decal);
|
||||
}
|
||||
s_selectedWorldDecal = -1;
|
||||
|
||||
@@ -757,6 +757,15 @@ void Texture_ShowInuse(void) {
|
||||
}
|
||||
}
|
||||
|
||||
if (g_qeglobals.rw) {
|
||||
for (int i = 0; i < g_qeglobals.rw->NumWorldDecals(); ++i) {
|
||||
const renderWorldDecal_t* decal = g_qeglobals.rw->GetWorldDecal(i);
|
||||
if (decal) {
|
||||
Texture_ForName(decal->material.c_str());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
Sys_UpdateWindows(W_TEXTURE);
|
||||
|
||||
g_Inspectors->SetWindowText("Textures (in use)");
|
||||
|
||||
Reference in New Issue
Block a user