Skip to content

Commit

Permalink
Merge branch 'lightConversion' into 'main'
Browse files Browse the repository at this point in the history
REMIX-3461 Adding more control over converted light intensity

See merge request lightspeedrtx/dxvk-remix-nv!1024
  • Loading branch information
MarkEHenderson committed Oct 4, 2024
2 parents e232de9 + 8ed9023 commit 863bf11
Show file tree
Hide file tree
Showing 5 changed files with 45 additions and 5 deletions.
2 changes: 2 additions & 0 deletions RtxOptions.md
Original file line number Diff line number Diff line change
Expand Up @@ -343,6 +343,8 @@ Tables below enumerate all the options and their defaults set by RTX Remix. Note
|rtx.legacyMaterial.useAlbedoTextureIfPresent|bool|True|A flag to determine if an "albedo" texture \(a qualifying color texture\) from the original application should be used if present on non\-replaced "legacy" materials\.|
|rtx.lightConversionDistantLightFixedAngle|float|0.0349|The angular size in radians of the distant light source for legacy lights converted to distant lights\. Set to ~2 degrees in radians by default\. Should only be within the range \[0, pi\]\.|
|rtx.lightConversionDistantLightFixedIntensity|float|1|The fixed intensity \(in W/sr\) to use for legacy lights converted to distant lights \(currently directional lights will convert to distant lights\)\.|
|rtx.lightConversionIntensityFactor|float|1|Scales the converted light intensities\.|
|rtx.lightConversionMaxIntensity|float|3.40282e+38|The highest intensity value a converted light can have\.|
|rtx.lightConversionSphereLightFixedRadius|float|4|The fixed radius in world units to use for legacy lights converted to sphere lights \(currently point and spot lights will convert to sphere lights\)\. Use caution with large light radii as many legacy lights will be placed close to geometry and intersect it, causing suboptimal light sampling performance or other visual artifacts \(lights clipping through walls, etc\)\.|
|rtx.lights.debugDrawLightHashes|bool|False|Draw light hashes of all visible ob screen lights, when enableDebugMode=true\.|
|rtx.lights.enableDebugMode|bool|False|Enables light debug visualization\.|
Expand Down
26 changes: 26 additions & 0 deletions src/dxvk/rtx_render/rtx_imgui.h
Original file line number Diff line number Diff line change
Expand Up @@ -177,6 +177,32 @@ namespace ImGui {
return IMGUI_ADD_TOOLTIP(DragFloat(label, &rtxOption->getValue(), std::forward<Args>(args)...), rtxOption->getDescription());
}

// DragFloat wrapped by a checkbox.
// Disabling the checkbox resets the value to the default value.
// Enabling the checkbox sets the value to `enabledValue`.
template <typename ... Args>
IMGUI_API bool OptionalDragFloat(const char* label, dxvk::RtxOption<float>* rtxOption, float enabledValue, Args&& ... args) {
// enabledValue and the default value can't match, otherwise the checkbox won't stay checked.
assert(enabledValue != rtxOption->getDefaultValue());
bool enabled = rtxOption->getValue() != rtxOption->getDefaultValue();
std::string hiddenLabel = dxvk::str::format("##", label);
bool changed = IMGUI_ADD_TOOLTIP(Checkbox(hiddenLabel.c_str(), &enabled), "Check to enable the option.\nUncheck to disable it and reset to default value.");
ImGui::SameLine();
if (changed) {
rtxOption->setValue(enabled ? enabledValue : rtxOption->getDefaultValue());
}
if (enabled) {
changed |= IMGUI_ADD_TOOLTIP(DragFloat(label, &rtxOption->getValue(), std::forward<Args>(args)...), rtxOption->getDescription());
} else {
ImGui::TextDisabled("%s (Disabled)", label);
if (ImGui::IsItemHovered()) {
ImGui::SetTooltipUnformatted(rtxOption->getDescription());
}
}

return changed;
}

// Variant handling RtxOption as input
template <typename ... Args>
IMGUI_API bool DragFloat2(const char* label, dxvk::RtxOption<dxvk::Vector2>* rtxOption, Args&& ... args) {
Expand Down
2 changes: 2 additions & 0 deletions src/dxvk/rtx_render/rtx_light_manager.h
Original file line number Diff line number Diff line change
Expand Up @@ -170,6 +170,8 @@ struct LightManager : public CommonDeviceObject {
RTX_OPTION("rtx", float, lightConversionSphereLightFixedRadius, 4.f, "The fixed radius in world units to use for legacy lights converted to sphere lights (currently point and spot lights will convert to sphere lights). Use caution with large light radii as many legacy lights will be placed close to geometry and intersect it, causing suboptimal light sampling performance or other visual artifacts (lights clipping through walls, etc).");
RTX_OPTION("rtx", float, lightConversionDistantLightFixedIntensity, 1.0f, "The fixed intensity (in W/sr) to use for legacy lights converted to distant lights (currently directional lights will convert to distant lights).");
RTX_OPTION("rtx", float, lightConversionDistantLightFixedAngle, 0.0349f, "The angular size in radians of the distant light source for legacy lights converted to distant lights. Set to ~2 degrees in radians by default. Should only be within the range [0, pi].");
RTX_OPTION("rtx", float, lightConversionMaxIntensity, FLT_MAX, "The highest intensity value a converted light can have.");
RTX_OPTION("rtx", float, lightConversionIntensityFactor, 1.f, "Scales the converted light intensities.");
};

} // namespace dxvk
Expand Down
18 changes: 14 additions & 4 deletions src/dxvk/rtx_render/rtx_light_manager_gui.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -103,16 +103,26 @@ namespace dxvk {
const bool disableDirectional = ignoreGameDirectionalLights();
const bool disablePointSpot = ignoreGamePointLights() && ignoreGameSpotLights();

// TODO(REMIX-3124) remove this warning
ImGui::TextColored(ImVec4{ 0.87f, 0.75f, 0.20f, 1.0f }, "Warning: changing Light Conversion values can cause crashes.\nManually entering values is safer than dragging.");
ImGui::BeginDisabled(disablePointSpot);
lightSettingsDirty |= ImGui::Checkbox("Use Least Squares Intensity for Sphere/Spot", &calculateLightIntensityUsingLeastSquaresObject());
lightSettingsDirty |= ImGui::DragFloat("Sphere/Spot Light Radius", &lightConversionSphereLightFixedRadiusObject(), 0.01f, 0.0f, FLT_MAX, "%.3f", ImGuiSliderFlags_AlwaysClamp);
ImGui::Text("Sphere / Spot Light settings");
lightSettingsDirty |= ImGui::Checkbox("Use Least Squares Intensity", &calculateLightIntensityUsingLeastSquaresObject());
lightSettingsDirty |= ImGui::DragFloat("Light Radius", &lightConversionSphereLightFixedRadiusObject(), 0.01f, 0.0f, FLT_MAX, "%.3f", ImGuiSliderFlags_AlwaysClamp);
lightSettingsDirty |= ImGui::DragFloat("Intensity Factor", &lightConversionIntensityFactorObject(), 0.01f, 0.0f, 2.f, "%.3f");
lightSettingsDirty |= ImGui::OptionalDragFloat("Max Intensity", &lightConversionMaxIntensityObject(), 1000000.f, 1.f, 0.0f, FLT_MAX, "%.1f", ImGuiSliderFlags_AlwaysClamp);
ImGui::EndDisabled();

separator();

ImGui::BeginDisabled(disableDirectional);
lightSettingsDirty |= ImGui::DragFloat("Distant Light Fixed Intensity", &lightConversionDistantLightFixedIntensityObject(), 0.01f, 0.0f, FLT_MAX, "%.3f", ImGuiSliderFlags_AlwaysClamp);
lightSettingsDirty |= ImGui::DragFloat("Distant Light Fixed Angle", &lightConversionDistantLightFixedAngleObject(), 0.01f, 0.0f, kPi, "%.4f rad", ImGuiSliderFlags_AlwaysClamp);
ImGui::Text("Distant Light settings");
lightSettingsDirty |= ImGui::DragFloat("Fixed Intensity", &lightConversionDistantLightFixedIntensityObject(), 0.01f, 0.0f, FLT_MAX, "%.3f", ImGuiSliderFlags_AlwaysClamp);
lightSettingsDirty |= ImGui::DragFloat("Fixed Angle", &lightConversionDistantLightFixedAngleObject(), 0.01f, 0.0f, kPi, "%.4f rad", ImGuiSliderFlags_AlwaysClamp);
ImGui::EndDisabled();

separator();

ImGui::Text("Ignore Game Lights:");
ImGui::Indent();
lightSettingsDirty |= ImGui::Checkbox("Directional", &ignoreGameDirectionalLightsObject());
Expand Down
2 changes: 1 addition & 1 deletion src/dxvk/rtx_render/rtx_light_utils.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -178,7 +178,7 @@ float LightUtils::calculateIntensity(const D3DLIGHT9& light, const float radius)
// r = (d^2 * t) / (pi * r^2) (Solve and Substitute)
const float kDistanceSqToRadiance = kNewLightEndValue / (kPi * radius * radius);

return kDistanceSqToRadiance * endDistanceSq;
return std::min(kDistanceSqToRadiance * endDistanceSq * LightManager::lightConversionIntensityFactor(), LightManager::lightConversionMaxIntensity());
}


Expand Down

0 comments on commit 863bf11

Please sign in to comment.