summaryrefslogtreecommitdiff
path: root/scene/3d/voxel_light_baker.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'scene/3d/voxel_light_baker.cpp')
-rw-r--r--scene/3d/voxel_light_baker.cpp99
1 files changed, 67 insertions, 32 deletions
diff --git a/scene/3d/voxel_light_baker.cpp b/scene/3d/voxel_light_baker.cpp
index edb9b9efd6..17aa649dff 100644
--- a/scene/3d/voxel_light_baker.cpp
+++ b/scene/3d/voxel_light_baker.cpp
@@ -1,5 +1,39 @@
+/*************************************************************************/
+/* voxel_light_baker.cpp */
+/*************************************************************************/
+/* This file is part of: */
+/* GODOT ENGINE */
+/* https://godotengine.org */
+/*************************************************************************/
+/* Copyright (c) 2007-2017 Juan Linietsky, Ariel Manzur. */
+/* Copyright (c) 2014-2017 Godot Engine contributors (cf. AUTHORS.md) */
+/* */
+/* Permission is hereby granted, free of charge, to any person obtaining */
+/* a copy of this software and associated documentation files (the */
+/* "Software"), to deal in the Software without restriction, including */
+/* without limitation the rights to use, copy, modify, merge, publish, */
+/* distribute, sublicense, and/or sell copies of the Software, and to */
+/* permit persons to whom the Software is furnished to do so, subject to */
+/* the following conditions: */
+/* */
+/* The above copyright notice and this permission notice shall be */
+/* included in all copies or substantial portions of the Software. */
+/* */
+/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
+/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
+/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.*/
+/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
+/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
+/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
+/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
+/*************************************************************************/
+
#include "voxel_light_baker.h"
#include "os/os.h"
+#include "os/threaded_array_processor.h"
+
+#include <stdlib.h>
+
#define FINDMINMAX(x0, x1, x2, min, max) \
min = max = x0; \
if (x1 < min) min = x1; \
@@ -1643,15 +1677,13 @@ Vector3 VoxelLightBaker::_compute_pixel_light_at_pos(const Vector3 &p_pos, const
return accum;
}
-uint32_t xorshiftstate[] = { 123 }; // anything non-zero will do here
-
-_ALWAYS_INLINE_ uint32_t xorshift32() {
+_ALWAYS_INLINE_ uint32_t xorshift32(uint32_t *state) {
/* Algorithm "xor" from p. 4 of Marsaglia, "Xorshift RNGs" */
- uint32_t x = xorshiftstate[0];
+ uint32_t x = *state;
x ^= x << 13;
x ^= x >> 17;
x ^= x << 5;
- xorshiftstate[0] = x;
+ *state = x;
return x;
}
@@ -1677,11 +1709,13 @@ Vector3 VoxelLightBaker::_compute_ray_trace_at_pos(const Vector3 &p_pos, const V
const Light *light = bake_light.ptr();
const Cell *cells = bake_cells.ptr();
+ uint32_t local_rng_state = rand(); //needs to be fixed again
+
for (int i = 0; i < samples; i++) {
- float random_angle1 = (((xorshift32() % 65535) / 65535.0) * 2.0 - 1.0) * spread;
+ float random_angle1 = (((xorshift32(&local_rng_state) % 65535) / 65535.0) * 2.0 - 1.0) * spread;
Vector3 axis(0, sin(random_angle1), cos(random_angle1));
- float random_angle2 = ((xorshift32() % 65535) / 65535.0) * Math_PI * 2.0;
+ float random_angle2 = ((xorshift32(&local_rng_state) % 65535) / 65535.0) * Math_PI * 2.0;
Basis rot(Vector3(0, 0, 1), random_angle2);
axis = rot.xform(axis);
@@ -1758,9 +1792,31 @@ Vector3 VoxelLightBaker::_compute_ray_trace_at_pos(const Vector3 &p_pos, const V
}
}
+ // Make sure we don't reset this thread's RNG state
+
return accum / samples;
}
+void VoxelLightBaker::_lightmap_bake_point(uint32_t p_x, LightMap *p_line) {
+
+
+ LightMap *pixel = &p_line[p_x];
+ if (pixel->pos == Vector3())
+ return;
+ //print_line("pos: " + pixel->pos + " normal " + pixel->normal);
+ switch (bake_mode) {
+ case BAKE_MODE_CONE_TRACE: {
+ pixel->light = _compute_pixel_light_at_pos(pixel->pos, pixel->normal) * energy;
+ } break;
+ case BAKE_MODE_RAY_TRACE: {
+ pixel->light = _compute_ray_trace_at_pos(pixel->pos, pixel->normal) * energy;
+ } break;
+ // pixel->light = Vector3(1, 1, 1);
+ //}
+ }
+
+}
+
Error VoxelLightBaker::make_lightmap(const Transform &p_xform, Ref<Mesh> &p_mesh, LightMapData &r_lightmap, bool (*p_bake_time_func)(void *, float, float), void *p_bake_time_ud) {
//transfer light information to a lightmap
@@ -1815,39 +1871,18 @@ Error VoxelLightBaker::make_lightmap(const Transform &p_xform, Ref<Mesh> &p_mesh
_plot_triangle(uv, vertex, normal, lightmap.ptrw(), width, height);
}
}
- //step 3 perform voxel cone trace on lightmap pixels
+ //step 3 perform voxel cone trace on lightmap pixels
{
LightMap *lightmap_ptr = lightmap.ptrw();
uint64_t begin_time = OS::get_singleton()->get_ticks_usec();
volatile int lines = 0;
+ // make sure our OS-level rng is seeded
+
for (int i = 0; i < height; i++) {
- //print_line("bake line " + itos(i) + " / " + itos(height));
-#ifdef _OPENMP
-#pragma omp parallel for schedule(dynamic, 1)
-#endif
- for (int j = 0; j < width; j++) {
-
- //if (i == 125 && j == 280) {
-
- LightMap *pixel = &lightmap_ptr[i * width + j];
- if (pixel->pos == Vector3())
- continue; //unused, skipe
-
- //print_line("pos: " + pixel->pos + " normal " + pixel->normal);
- switch (bake_mode) {
- case BAKE_MODE_CONE_TRACE: {
- pixel->light = _compute_pixel_light_at_pos(pixel->pos, pixel->normal) * energy;
- } break;
- case BAKE_MODE_RAY_TRACE: {
- pixel->light = _compute_ray_trace_at_pos(pixel->pos, pixel->normal) * energy;
- } break;
- // pixel->light = Vector3(1, 1, 1);
- //}
- }
- }
+ thread_process_array(width,this,&VoxelLightBaker::_lightmap_bake_point,&lightmap_ptr[i*width]);
lines = MAX(lines, i); //for multithread
if (p_bake_time_func) {