Skip to content

Commit c85b399

Browse files
committed
Spread direct lighting calculation for LightmapGI over several submissions to avoid TDR on Windows devices
Also add percentage progress for direct lighting step
1 parent 1586c56 commit c85b399

File tree

1 file changed

+50
-19
lines changed

1 file changed

+50
-19
lines changed

modules/lightmapper_rd/lightmapper_rd.cpp

+50-19
Original file line numberDiff line numberDiff line change
@@ -1649,6 +1649,10 @@ LightmapperRD::BakeError LightmapperRD::bake(BakeQuality p_quality, bool p_use_d
16491649
}
16501650
}
16511651

1652+
const int max_region_size = nearest_power_of_2_templated(int(GLOBAL_GET("rendering/lightmapping/bake_performance/region_size")));
1653+
const int x_regions = Math::division_round_up(atlas_size.width, max_region_size);
1654+
const int y_regions = Math::division_round_up(atlas_size.height, max_region_size);
1655+
16521656
// Set ray count to the quality used for direct light and bounces.
16531657
switch (p_quality) {
16541658
case BAKE_QUALITY_LOW: {
@@ -1718,18 +1722,53 @@ LightmapperRD::BakeError LightmapperRD::bake(BakeQuality p_quality, bool p_use_d
17181722

17191723
RID light_uniform_set = rd->uniform_set_create(uniforms, compute_shader_primary, 1);
17201724

1721-
RD::ComputeListID compute_list = rd->compute_list_begin();
1722-
rd->compute_list_bind_compute_pipeline(compute_list, compute_shader_primary_pipeline);
1723-
rd->compute_list_bind_uniform_set(compute_list, compute_base_uniform_set, 0);
1724-
rd->compute_list_bind_uniform_set(compute_list, light_uniform_set, 1);
1725+
int count = 0;
1726+
for (int s = 0; s < atlas_slices; s++) {
1727+
push_constant.atlas_slice = s;
17251728

1726-
for (int i = 0; i < atlas_slices; i++) {
1727-
push_constant.atlas_slice = i;
1728-
rd->compute_list_set_push_constant(compute_list, &push_constant, sizeof(PushConstant));
1729-
rd->compute_list_dispatch(compute_list, group_size.x, group_size.y, group_size.z);
1730-
//no barrier, let them run all together
1729+
for (int i = 0; i < x_regions; i++) {
1730+
for (int j = 0; j < y_regions; j++) {
1731+
int x = i * max_region_size;
1732+
int y = j * max_region_size;
1733+
int w = MIN((i + 1) * max_region_size, atlas_size.width) - x;
1734+
int h = MIN((j + 1) * max_region_size, atlas_size.height) - y;
1735+
1736+
push_constant.region_ofs[0] = x;
1737+
push_constant.region_ofs[1] = y;
1738+
1739+
group_size = Vector3i(Math::division_round_up(w, 8), Math::division_round_up(h, 8), 1);
1740+
RD::ComputeListID compute_list = rd->compute_list_begin();
1741+
rd->compute_list_bind_compute_pipeline(compute_list, compute_shader_primary_pipeline);
1742+
rd->compute_list_bind_uniform_set(compute_list, compute_base_uniform_set, 0);
1743+
rd->compute_list_bind_uniform_set(compute_list, light_uniform_set, 1);
1744+
push_constant.atlas_slice = i;
1745+
rd->compute_list_set_push_constant(compute_list, &push_constant, sizeof(PushConstant));
1746+
rd->compute_list_dispatch(compute_list, group_size.x, group_size.y, group_size.z);
1747+
rd->compute_list_end();
1748+
1749+
rd->submit();
1750+
rd->sync();
1751+
1752+
count++;
1753+
if (p_step_function) {
1754+
int total = (atlas_slices * x_regions * y_regions);
1755+
int percent = count * 100 / total;
1756+
float p = float(count) / total * 0.1;
1757+
if (p_step_function(0.5 + p, vformat(RTR("Plot direct lighting %d%%"), percent), p_bake_userdata, false)) {
1758+
FREE_TEXTURES
1759+
FREE_BUFFERS
1760+
FREE_RASTER_RESOURCES
1761+
FREE_COMPUTE_RESOURCES
1762+
memdelete(rd);
1763+
if (rcd != nullptr) {
1764+
memdelete(rcd);
1765+
}
1766+
return BAKE_ERROR_USER_ABORTED;
1767+
}
1768+
}
1769+
}
1770+
}
17311771
}
1732-
rd->compute_list_end(); //done
17331772
}
17341773

17351774
#ifdef DEBUG_TEXTURES
@@ -1802,17 +1841,9 @@ LightmapperRD::BakeError LightmapperRD::bake(BakeQuality p_quality, bool p_use_d
18021841
RID secondary_uniform_set;
18031842
secondary_uniform_set = rd->uniform_set_create(uniforms, compute_shader_secondary, 1);
18041843

1805-
int max_region_size = nearest_power_of_2_templated(int(GLOBAL_GET("rendering/lightmapping/bake_performance/region_size")));
1806-
int max_rays = GLOBAL_GET("rendering/lightmapping/bake_performance/max_rays_per_pass");
1807-
1808-
int x_regions = Math::division_round_up(atlas_size.width, max_region_size);
1809-
int y_regions = Math::division_round_up(atlas_size.height, max_region_size);
1810-
1844+
const int max_rays = GLOBAL_GET("rendering/lightmapping/bake_performance/max_rays_per_pass");
18111845
int ray_iterations = Math::division_round_up((int32_t)push_constant.ray_count, max_rays);
18121846

1813-
rd->submit();
1814-
rd->sync();
1815-
18161847
if (p_step_function) {
18171848
if (p_step_function(0.6, RTR("Integrate indirect lighting"), p_bake_userdata, true)) {
18181849
FREE_TEXTURES

0 commit comments

Comments
 (0)