add progress bar to lightmap rendering

This commit is contained in:
2019-01-15 22:25:23 +01:00
parent c3220b5b15
commit f5c4aed4fd
8 changed files with 98 additions and 53 deletions

View File

@@ -264,6 +264,12 @@ void NodePanelGrid::bake_uvs()
fb.unbindFramebuffer();
fb.destroy();
auto pb = root()->add_child<NodeProgressBar>();
pb->m_progress->SetWidthP(0);
pb->m_title->set_text("Lightmap Rendering");
pb->btn_cancel->destroy();
async_update();
if (m_rt_dirty)
{
nanort::BVHBuildOptions<float> build_options; // Use default option
@@ -281,56 +287,71 @@ void NodePanelGrid::bake_uvs()
auto light_pos = glm::vec3(sinf(light_yaw), light_pitch + get_offset(), cosf(light_yaw));
auto light_dir = glm::normalize(light_pos);
std::atomic_int pb_value(0);
__block auto data_out = std::make_unique<uint8_t[]>(fb.getWidth() * fb.getHeight() * 4);
#if _WIN32
concurrency::parallel_for(int(0), fb.getHeight(), [&](int y)
#elif __IOS__ || __OSX__
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_apply((size_t)fb.getHeight(), queue, ^(size_t y)
#else
for (int y = 0; y < fb.getHeight(); y++)
#endif
std::thread worker([&]
{
for (int x = 0; x < fb.getWidth(); x++)
{
int i = y * fb.getHeight() + x;
auto nor = glm::make_vec3(&data_nor[i * 4]);
auto pos = glm::make_vec3(&data_pos[i * 4]);
auto& out = *reinterpret_cast<glm::i8vec4*>(&data_out[i * 4]);
// if (glm::dot(nor, light_dir) <= 0.f)
// {
// out = { 50, 50, 50, 255 };
// continue;
// }
int hit = 0;
for (int s = 0; s < 16; s++)
{
auto dir = glm::normalize(light_dir + glm::sphericalRand(.1f));
nanort::Ray<float> ray;
ray.org[0] = pos.x;// + nor.x * 0.005;
ray.org[1] = pos.y;// + nor.y * 0.005;
ray.org[2] = pos.z;// + nor.z * 0.005;
ray.dir[0] = dir.x;
ray.dir[1] = dir.y;
ray.dir[2] = dir.z;
float kFar = 2000.0;
ray.min_t = 0.005f;
ray.max_t = kFar;
nanort::TriangleIntersector<> triangle_intersector(reinterpret_cast<float*>(m_hm_plane.vertices.data()), m_hm_plane.idx.data(), sizeof(vertex_t));
nanort::TriangleIntersection<> isect;
hit += m_rt_accel.Traverse(ray, triangle_intersector, &isect);
}
out = glm::lerp(glm::vec4(255, 255, 255, 255), glm::vec4(50, 50, 50, 255), hit / 16.f);
}
}
#if _WIN32 || __IOS__ || __OSX__
);
#if _WIN32
concurrency::parallel_for(int(0), fb.getHeight(), [&](int y)
#elif __IOS__ || __OSX__
dispatch_queue_t queue = dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_DEFAULT, 0);
dispatch_apply((size_t)fb.getHeight(), queue, ^ (size_t y)
#else
for (int y = 0; y < fb.getHeight(); y++)
#endif
{
for (int x = 0; x < fb.getWidth(); x++)
{
int i = y * fb.getHeight() + x;
auto nor = glm::make_vec3(&data_nor[i * 4]);
auto pos = glm::make_vec3(&data_pos[i * 4]);
auto& out = *reinterpret_cast<glm::i8vec4*>(&data_out[i * 4]);
if (glm::dot(nor, light_dir) <= 0.f)
{
out = { 50, 50, 50, 255 };
continue;
}
int hit = 0;
for (int s = 0; s < 16; s++)
{
auto dir = glm::normalize(light_dir + glm::sphericalRand(.1f));
nanort::Ray<float> ray;
ray.org[0] = pos.x;// + nor.x * 0.005;
ray.org[1] = pos.y;// + nor.y * 0.005;
ray.org[2] = pos.z;// + nor.z * 0.005;
ray.dir[0] = dir.x;
ray.dir[1] = dir.y;
ray.dir[2] = dir.z;
float kFar = 2000.0;
ray.min_t = 0.005f;
ray.max_t = kFar;
nanort::TriangleIntersector<> triangle_intersector(reinterpret_cast<float*>(m_hm_plane.vertices.data()), m_hm_plane.idx.data(), sizeof(vertex_t));
nanort::TriangleIntersection<> isect;
hit += m_rt_accel.Traverse(ray, triangle_intersector, &isect);
}
out = glm::lerp(glm::vec4(255, 255, 255, 255), glm::vec4(50, 50, 50, 255), hit / 16.f);
}
pb_value++;
}
#if _WIN32 || __IOS__ || __OSX__
);
#endif
}
);
while (pb_value < fb.getHeight())
{
pb->m_progress->SetWidthP((float)pb_value / (float)fb.getHeight() * 100.f);
async_update();
std::this_thread::sleep_for(std::chrono::milliseconds(100));
}
worker.join();
pb->destroy();
//stbi_write_jpg("bake-out.jpg", fb.getWidth(), fb.getHeight(), 4, data_out.get(), 75);
m_texture.update(data_out.get());
m_texture.create_mipmaps();