first working version of volumetric shadows
This commit is contained in:
parent
51760f30f1
commit
e9e6aec8f8
20 changed files with 426 additions and 94 deletions
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
@ -30,7 +30,7 @@ layout (local_size_x = 16, local_size_y = 1, local_size_z = 1) in;
|
|||
void main() {
|
||||
uint index = gl_GlobalInvocationID.x;
|
||||
uint output_offset = 0;
|
||||
uint compound_start = 0;
|
||||
uint compound_start = 1;
|
||||
// iterate over the compounds and find the work index inside of it
|
||||
while (index > compounds[compound_start] * compounds[compound_start]) {
|
||||
output_offset += compounds[compound_start] * compounds[compound_start] * compounds[compound_start];
|
||||
|
|
|
@ -32,9 +32,9 @@ layout(binding = 8) buffer SizeBuffer3D {
|
|||
layout (local_size_x = 16, local_size_y = 1, local_size_z = 1) in;
|
||||
|
||||
void main() {
|
||||
uint index = gl_GlobalInvocationID.x;
|
||||
uint index = gl_GlobalInvocationID.x * 2 + 1;
|
||||
uint output_offset = 0;
|
||||
uint compound_start = 0;
|
||||
uint compound_start = 1;
|
||||
// iterate over the compounds and find the work index inside of it
|
||||
while (index > compounds[compound_start] * compounds[compound_start]) {
|
||||
output_offset += compounds[compound_start] * compounds[compound_start] * compounds[compound_start];
|
||||
|
|
|
@ -32,9 +32,9 @@ layout(binding = 8) readonly buffer SizeBuffer3D {
|
|||
layout (local_size_x = 16, local_size_y = 1, local_size_z = 1) in;
|
||||
|
||||
void main() {
|
||||
uint index = gl_GlobalInvocationID.x;
|
||||
uint index = gl_GlobalInvocationID.x * 2 + 1;
|
||||
uint output_offset = 0;
|
||||
uint compound_start = 0;
|
||||
uint compound_start = 1;
|
||||
// iterate over the compounds and find the work index inside of it
|
||||
while (index > compounds[compound_start] * compounds[compound_start]) {
|
||||
output_offset += compounds[compound_start] * compounds[compound_start] * compounds[compound_start];
|
||||
|
|
|
@ -198,22 +198,28 @@ void add_cube(uint cube_num, float scale, vec3 pos, vec3 color) {
|
|||
|
||||
}
|
||||
|
||||
uint cohort_index_from_pos(uint x, uint y, uint z, uint block_size, uint compound_size) {
|
||||
uint steps = compound_size / block_size;
|
||||
return (z / block_size) * (steps*steps) + (y / block_size) * steps + (x / block_size);
|
||||
}
|
||||
|
||||
void main() {
|
||||
uint index = gl_GlobalInvocationID.x;
|
||||
uint output_offset = 1;
|
||||
uint input_offset = 0;
|
||||
uint compound_start = 0;
|
||||
uint compound_start = 1;
|
||||
|
||||
uint nodes = num_nodes(compounds[compound_start]);
|
||||
// iterate over the compounds and find the work index inside of it
|
||||
while (index > nodes) {
|
||||
output_offset += nodes * 9;
|
||||
input_offset += compounds[compound_start] * compounds[compound_start] * compounds[compound_start];
|
||||
index -= nodes;
|
||||
compound_start = compounds[compound_start + 2];
|
||||
nodes = num_nodes(compounds[compound_start]);
|
||||
}
|
||||
|
||||
output_offset = compounds[compound_start + 8];
|
||||
|
||||
uint compound_grid_size = compounds[compound_start];
|
||||
uint parent_start = 0;
|
||||
uint cohort_start = 0;
|
||||
|
@ -230,21 +236,30 @@ void main() {
|
|||
size = size / 2;
|
||||
}
|
||||
|
||||
uint parent = parent_start + ((cohort_index - cohort_index % 8) / 8) * 9;
|
||||
uint start = cohort_start + 9 * cohort_index;
|
||||
uint steps = compounds[compound_start] / size;
|
||||
|
||||
float compound_scale = uintBitsToFloat(compounds[compound_start + 1]);
|
||||
vec3 mid_offset = vec3(compound_scale * 0.5, compound_scale * 0.5, compound_scale * 0.5);
|
||||
|
||||
uint x = (cohort_index % steps) * size;
|
||||
uint y = (((cohort_index - (cohort_index % steps)) % (steps * steps)) / (steps)) * size;
|
||||
uint z = (((cohort_index - (cohort_index % (steps * steps)))) / (steps * steps)) * size;
|
||||
uint x_no_offset = (cohort_index % steps) * size;
|
||||
uint y_no_offset = (((cohort_index - (cohort_index % steps)) % (steps * steps)) / (steps)) * size;
|
||||
uint z_no_offset = (((cohort_index - (cohort_index % (steps * steps)))) / (steps * steps)) * size;
|
||||
|
||||
uint parent_size = size * 2;
|
||||
uint parent_steps = compounds[compound_start] / parent_size;
|
||||
uint x_parent = uint(floor(float(x_no_offset) / float(parent_size))) * parent_size;
|
||||
uint y_parent = uint(floor(float(y_no_offset) / float(parent_size))) * parent_size;
|
||||
uint z_parent = uint(floor(float(z_no_offset) / float(parent_size))) * parent_size;
|
||||
|
||||
uint parent = output_offset + parent_start + cohort_index_from_pos(x_parent, y_parent, z_parent, parent_size, compound_grid_size) * 9;;
|
||||
if (size == compounds[compound_start]) {
|
||||
parent = 0;
|
||||
}
|
||||
|
||||
// plus one size offset, since we want to place the nodes at the far end. This aligns with the iteration directions in the previous shaders
|
||||
x = x + (size - 1);
|
||||
y = y + (size - 1);
|
||||
z = z + (size - 1);
|
||||
uint x = x_no_offset + (size - 1);
|
||||
uint y = y_no_offset + (size - 1);
|
||||
uint z = z_no_offset + (size - 1);
|
||||
|
||||
// sum of all elements with coordinates lower than x, y, z
|
||||
uint contained_entries = grid_size_in[input_offset + x * compound_grid_size * compound_grid_size + y * compound_grid_size + z];
|
||||
|
@ -283,19 +298,20 @@ void main() {
|
|||
}
|
||||
|
||||
if (contained_entries > 0) {
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 0] = parent * uint(size != 64);
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 0] = parent;
|
||||
|
||||
if (size > 2) {
|
||||
// add child node reference
|
||||
uint child_size = size / 2;
|
||||
uint cohort_end = cohort_start + 9 * add_size;
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 1] = cohort_end + cohort_index * 9 + 9 * 0; // xyz
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 2] = cohort_end + cohort_index * 9 + 9 * 1; // Xyz
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 3] = cohort_end + cohort_index * 9 + 9 * 2; // xYz
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 4] = cohort_end + cohort_index * 9 + 9 * 3; // XYz
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 5] = cohort_end + cohort_index * 9 + 9 * 4; // xyZ
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 6] = cohort_end + cohort_index * 9 + 9 * 5; // XyZ
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 7] = cohort_end + cohort_index * 9 + 9 * 6; // xYZ
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 8] = cohort_end + cohort_index * 9 + 9 * 7; // XYZ
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 1] = output_offset + cohort_end + cohort_index_from_pos(x_no_offset, y_no_offset, z_no_offset, child_size, compound_grid_size) * 9; // xyz
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 2] = output_offset + cohort_end + cohort_index_from_pos(x_no_offset + child_size, y_no_offset, z_no_offset, child_size, compound_grid_size) * 9; // Xyz
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 3] = output_offset + cohort_end + cohort_index_from_pos(x_no_offset, y_no_offset + child_size, z_no_offset, child_size, compound_grid_size) * 9; // xYz
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 4] = output_offset + cohort_end + cohort_index_from_pos(x_no_offset + child_size, y_no_offset + child_size, z_no_offset, child_size, compound_grid_size) * 9; // XYz
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 5] = output_offset + cohort_end + cohort_index_from_pos(x_no_offset, y_no_offset, z_no_offset + child_size, child_size, compound_grid_size) * 9; // xyZ
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 6] = output_offset + cohort_end + cohort_index_from_pos(x_no_offset + child_size, y_no_offset, z_no_offset + child_size, child_size, compound_grid_size) * 9; // XyZ
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 7] = output_offset + cohort_end + cohort_index_from_pos(x_no_offset, y_no_offset + child_size, z_no_offset + child_size, child_size, compound_grid_size) * 9; // xYZ
|
||||
out_memory[output_offset + cohort_start + cohort_index * 9 + 8] = output_offset + cohort_end + cohort_index_from_pos(x_no_offset + child_size, y_no_offset + child_size, z_no_offset + child_size, child_size, compound_grid_size) * 9; // XYZ
|
||||
|
||||
} else {
|
||||
// copy color values and add cubes to rendering
|
||||
|
|
|
@ -9,7 +9,7 @@ layout(binding = 0) uniform UniformBufferObject {
|
|||
bool[16] use_geom_shader;
|
||||
} ubo;
|
||||
|
||||
layout(binding = 3) readonly buffer SceneInfoBuffer {
|
||||
layout(binding = 3) readonly buffer CompoundBuffer {
|
||||
uint compounds[];
|
||||
};
|
||||
|
||||
|
@ -175,7 +175,7 @@ void add_cube(uint cube_num, float scale, vec3 pos, vec3 color) {
|
|||
void main() {
|
||||
uint index = gl_GlobalInvocationID.x;
|
||||
uint output_offset = 0;
|
||||
uint compound_start = 0;
|
||||
uint compound_start = 1;
|
||||
// iterate over the compounds and find the work index inside of it
|
||||
while (index > compounds[compound_start] * compounds[compound_start]) {
|
||||
output_offset += compounds[compound_start] * compounds[compound_start] * compounds[compound_start];
|
||||
|
|
|
@ -24,13 +24,19 @@ layout(binding = 0) uniform UniformBufferObject {
|
|||
// 3 - diffuse raster size (float, needs to be decoded)
|
||||
// 4 - max recursive rays
|
||||
// 5 - diffuse rays per hit
|
||||
// 6 - maximum number of compounds per light
|
||||
layout(binding = 2) readonly buffer SceneInfoBuffer{
|
||||
uint infos[];
|
||||
} scene_info;
|
||||
|
||||
layout(binding = 4) buffer SceneInfoBuffer2 {
|
||||
uint infos[];
|
||||
} scene_info2;
|
||||
layout(binding = 3) readonly buffer CompoundBuffer {
|
||||
uint compounds[];
|
||||
};
|
||||
|
||||
layout(binding = 10) readonly buffer OctTreeMemory {
|
||||
uint oct_tree_mem[];
|
||||
};
|
||||
|
||||
uint max_num_lights = scene_info.infos[0];
|
||||
uint max_iterations_per_light = scene_info.infos[1];
|
||||
// diffuse raytracing using a quadratic raster of rays
|
||||
|
@ -41,6 +47,7 @@ float pos_infinity = uintBitsToFloat(0x7F800000);
|
|||
// set limit for maximal iterations
|
||||
uint max_iterations = max_num_lights * max_iterations_per_light * raster_points;
|
||||
uint iteration_num = 0;
|
||||
uint max_num_compounds = scene_info.infos[6];
|
||||
|
||||
uvec4 unpack_color(uint val) {
|
||||
// left most 8 bits first
|
||||
|
@ -52,7 +59,7 @@ uvec4 unpack_color(uint val) {
|
|||
return uvec4(val4, val3, val2, val1);
|
||||
}
|
||||
|
||||
uint array_descr_offset = 6 + max_num_lights;
|
||||
uint array_descr_offset = 6 + max_num_lights + max_num_compounds;
|
||||
uint color_array_offset = 24 + 1;
|
||||
|
||||
uint sample_neighbor_from_scene_info(uint volume_start, uvec2 raster_pos, uint f) {
|
||||
|
@ -204,6 +211,63 @@ vec3 reflect_vector(vec3 direction, uint facing) {
|
|||
return direction - 2.0 * dot(direction, normal) * normal;
|
||||
}
|
||||
|
||||
uvec3 parent_child_vec(uint child_size, uint child_index) {
|
||||
if (child_index == 1) {
|
||||
return uvec3(0, 0, 0);
|
||||
}
|
||||
if (child_index == 2) {
|
||||
return uvec3(child_size, 0, 0);
|
||||
}
|
||||
if (child_index == 3) {
|
||||
return uvec3(0, child_size, 0);
|
||||
}
|
||||
if (child_index == 4) {
|
||||
return uvec3(child_size, child_size, 0);
|
||||
}
|
||||
if (child_index == 5) {
|
||||
return uvec3(0, 0, child_size);
|
||||
}
|
||||
if (child_index == 6) {
|
||||
return uvec3(child_size, 0, child_size);
|
||||
}
|
||||
if (child_index == 7) {
|
||||
return uvec3(0, child_size, child_size);
|
||||
}
|
||||
if (child_index == 8) {
|
||||
return uvec3(child_size, child_size, child_size);
|
||||
}
|
||||
return uvec3(0, 0, 0);
|
||||
}
|
||||
|
||||
uint next_oct_tree_child(vec3 mid_point, vec3 check_pos, bool child_open[8]) {
|
||||
if (check_pos.x <= mid_point.x && check_pos.y <= mid_point.y && check_pos.z <= mid_point.z && child_open[0]) {
|
||||
return 1;
|
||||
}
|
||||
if (check_pos.x >= mid_point.x && check_pos.y <= mid_point.y && check_pos.z <= mid_point.z && child_open[1]) {
|
||||
return 2;
|
||||
}
|
||||
if (check_pos.x <= mid_point.x && check_pos.y >= mid_point.y && check_pos.z <= mid_point.z && child_open[2]) {
|
||||
return 3;
|
||||
}
|
||||
if (check_pos.x >= mid_point.x && check_pos.y >= mid_point.y && check_pos.z <= mid_point.z && child_open[3]) {
|
||||
return 4;
|
||||
}
|
||||
if (check_pos.x <= mid_point.x && check_pos.y <= mid_point.y && check_pos.z >= mid_point.z && child_open[4]) {
|
||||
return 5;
|
||||
}
|
||||
if (check_pos.x >= mid_point.x && check_pos.y <= mid_point.y && check_pos.z >= mid_point.z && child_open[5]) {
|
||||
return 6;
|
||||
}
|
||||
if (check_pos.x <= mid_point.x && check_pos.y >= mid_point.y && check_pos.z >= mid_point.z && child_open[6]) {
|
||||
return 7;
|
||||
}
|
||||
if (check_pos.x >= mid_point.x && check_pos.y >= mid_point.y && check_pos.z >= mid_point.z && child_open[7]) {
|
||||
return 8;
|
||||
}
|
||||
|
||||
return 0; // return to parent
|
||||
}
|
||||
|
||||
struct Tracing {
|
||||
vec3 end_pos;
|
||||
uvec4 end_color;
|
||||
|
@ -259,6 +323,210 @@ Tracing trace_ray(uint volume_start, vec3 starting_pos, vec3 start_direction, fl
|
|||
|
||||
while (iteration_num < max_iterations) {
|
||||
iteration_num ++;
|
||||
|
||||
uint compound_num = 0;
|
||||
while (scene_info.infos[volume_index + 6 + max_num_lights + compound_num] != 0 && compound_num < max_num_compounds && iteration_num < max_iterations && !result.has_hit) {
|
||||
//iteration_num ++;
|
||||
uint compound_start = scene_info.infos[volume_index + 6 + max_num_lights + compound_num];
|
||||
uint oct_tree_index = compounds[compound_start + 8];
|
||||
uint compound_grid_size = compounds[compound_start];
|
||||
float compound_scale = uintBitsToFloat(compounds[compound_start + 1]);
|
||||
vec3 compound_pos = vec3(uintBitsToFloat(compounds[compound_start + 5]), uintBitsToFloat(compounds[compound_start + 6]), uintBitsToFloat(compounds[compound_start + 7]));
|
||||
// check if we hit the volume
|
||||
float x_border = compound_pos.x + float((compound_grid_size) * uint(!x_pos)) * compound_scale;
|
||||
float y_border = compound_pos.y + float((compound_grid_size) * uint(!y_pos)) * compound_scale;
|
||||
float z_border = compound_pos.z + float((compound_grid_size) * uint(!z_pos)) * compound_scale;
|
||||
|
||||
if (!x_null) {
|
||||
x_factor = (x_border - pos.x) / direction.x;
|
||||
} else {
|
||||
x_factor = max_factor;
|
||||
}
|
||||
if (!y_null) {
|
||||
y_factor = (y_border - pos.y) / direction.y;
|
||||
} else {
|
||||
y_factor = max_factor;
|
||||
}
|
||||
if (!z_null) {
|
||||
z_factor = (z_border - pos.z) / direction.z;
|
||||
} else {
|
||||
z_factor = max_factor;
|
||||
}
|
||||
|
||||
vec3 intersection_pos = pos;
|
||||
bool is_x_hit = false;
|
||||
bool is_y_hit = false;
|
||||
bool is_z_hit = false;
|
||||
bool hit_inside = false;
|
||||
if ((compound_pos.x <= intersection_pos.x && intersection_pos.x <= compound_pos.x + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.y <= intersection_pos.y && intersection_pos.y <= compound_pos.y + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.z <= intersection_pos.z && intersection_pos.z <= compound_pos.z + float(compound_grid_size) * compound_scale)){
|
||||
hit_inside = true;
|
||||
} else {
|
||||
vec3 intersection_pos_x = pos + x_factor * direction;
|
||||
vec3 intersection_pos_y = pos + y_factor * direction;
|
||||
vec3 intersection_pos_z = pos + z_factor * direction;
|
||||
if ((compound_pos.x <= intersection_pos_x.x && intersection_pos_x.x <= compound_pos.x + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.y <= intersection_pos_x.y && intersection_pos_x.y <= compound_pos.y + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.z <= intersection_pos_x.z && intersection_pos_x.z <= compound_pos.z + float(compound_grid_size) * compound_scale) && x_factor > 0.0) {
|
||||
hit_inside = true;
|
||||
is_x_hit = true;
|
||||
intersection_pos = intersection_pos_x;
|
||||
}
|
||||
|
||||
if ((compound_pos.x <= intersection_pos_y.x && intersection_pos_y.x <= compound_pos.x + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.y <= intersection_pos_y.y && intersection_pos_y.y <= compound_pos.y + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.z <= intersection_pos_y.z && intersection_pos_y.z <= compound_pos.z + float(compound_grid_size) * compound_scale) && y_factor > 0.0 && (y_factor < x_factor || !is_x_hit)) {
|
||||
hit_inside = true;
|
||||
is_y_hit = true;
|
||||
intersection_pos = intersection_pos_y;
|
||||
}
|
||||
|
||||
if ((compound_pos.x <= intersection_pos_z.x && intersection_pos_z.x <= compound_pos.x + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.y <= intersection_pos_z.y && intersection_pos_z.y <= compound_pos.y + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.z <= intersection_pos_z.z && intersection_pos_z.z <= compound_pos.z + float(compound_grid_size) * compound_scale) && z_factor > 0.0 && (z_factor < x_factor || !is_x_hit) && (z_factor < y_factor || !is_y_hit)) {
|
||||
hit_inside = true;
|
||||
is_z_hit = true;
|
||||
intersection_pos = intersection_pos_z;
|
||||
}
|
||||
}
|
||||
|
||||
// check that either the hit is in range or we are inside of the compound from the start
|
||||
if (hit_inside) {
|
||||
vec3 oct_tree_pos = vec3(compound_pos);
|
||||
uint current_size = compound_grid_size;
|
||||
vec3 mid_point = oct_tree_pos + float(current_size / 2) * vec3(compound_scale, compound_scale, compound_scale);
|
||||
bool children_open[8] = {true, true, true, true, true, true, true, true};
|
||||
uint oct_tree_address = oct_tree_index;
|
||||
// iterate through the oct_tree
|
||||
uint check_it = 0;
|
||||
uint prev_child = 0;
|
||||
uint prev_prev_child = 0;
|
||||
|
||||
uvec3 grid_pos = uvec3(0, 0, 0);
|
||||
uvec3 parent_pos = uvec3(0, 0, 0);
|
||||
|
||||
bool has_moved = false;
|
||||
while (!result.has_hit && check_it < 60) {
|
||||
// failsafe to get out in case has_moved runs into an accuracy issue
|
||||
check_it ++;
|
||||
oct_tree_pos = vec3(grid_pos) * compound_scale + compound_pos;
|
||||
mid_point = oct_tree_pos + (float(current_size / 2) * vec3(compound_scale, compound_scale, compound_scale));
|
||||
|
||||
uint child_index = next_oct_tree_child(mid_point, intersection_pos, children_open);
|
||||
if (child_index == 0) {
|
||||
// go up to parent
|
||||
// if parent is 0 abort, as we have reached the root node again and try to exit it
|
||||
if (oct_tree_mem[oct_tree_address] == 0) {
|
||||
break;
|
||||
}
|
||||
for (int i=0; i < 8; i++) {
|
||||
children_open[i] = true;
|
||||
}
|
||||
uint parent_index = oct_tree_mem[oct_tree_address];
|
||||
// check which child we came from
|
||||
child_index = 1 * uint(oct_tree_address == oct_tree_mem[parent_index + 1]) + 2 * uint(oct_tree_address == oct_tree_mem[parent_index + 2]) + 3 * uint(oct_tree_address == oct_tree_mem[parent_index + 3]) + 4 * uint(oct_tree_address == oct_tree_mem[parent_index + 4]) + 5 * uint(oct_tree_address == oct_tree_mem[parent_index + 5]) + 6 * uint(oct_tree_address == oct_tree_mem[parent_index + 6]) + 7 * uint(oct_tree_address == oct_tree_mem[parent_index + 7]) + 8 * uint(oct_tree_address == oct_tree_mem[parent_index + 8]);
|
||||
// mark as done to avoid reinvestigating, since intersection_pos is on its edge
|
||||
children_open[child_index - 1] = false;
|
||||
if (!has_moved) {
|
||||
for (int i=0; i < child_index; i++) {
|
||||
children_open[i] = false;
|
||||
}
|
||||
}
|
||||
prev_prev_child = prev_child;
|
||||
prev_child = oct_tree_address;
|
||||
|
||||
uvec3 back_vec = parent_child_vec(current_size, child_index);
|
||||
grid_pos -= parent_child_vec(current_size, child_index);
|
||||
current_size *= 2;
|
||||
oct_tree_address = parent_index;
|
||||
// todo remove once parent is implemented
|
||||
//break;
|
||||
} else {
|
||||
// go down into child
|
||||
if (current_size == 2) {
|
||||
// check block if hit break
|
||||
if (oct_tree_mem[oct_tree_address + child_index] != 0) {
|
||||
result.has_hit = true;
|
||||
result.end_color = uvec4(255, 0, 0, 32);
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
// check if the child has content, else skip to next child of current parent
|
||||
uint x = oct_tree_mem[oct_tree_address + child_index];
|
||||
if (oct_tree_mem[x] != 0) {
|
||||
// change base address and position to child
|
||||
current_size /= 2;
|
||||
oct_tree_address = x;
|
||||
grid_pos += parent_child_vec(current_size, child_index);
|
||||
for (int i=0; i < 8; i++) {
|
||||
children_open[i] = true;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
}
|
||||
children_open[child_index - 1] = false;
|
||||
|
||||
// we did not go deeper or had a hit, so intersection pos needs to be updated
|
||||
// new intersection pos calc
|
||||
vec3 offset = vec3(parent_child_vec(current_size / 2, child_index)) * compound_scale;
|
||||
vec3 low = oct_tree_pos + offset;
|
||||
float x_border = low.x + float((compound_scale * current_size / 2) * uint(x_pos));
|
||||
float y_border = low.y + float((compound_scale * current_size / 2) * uint(y_pos));
|
||||
float z_border = low.z + float((compound_scale * current_size / 2) * uint(z_pos));
|
||||
|
||||
if (!x_null) {
|
||||
x_factor = (x_border - pos.x) / direction.x;
|
||||
} else {
|
||||
x_factor = max_factor;
|
||||
}
|
||||
if (!y_null) {
|
||||
y_factor = (y_border - pos.y) / direction.y;
|
||||
} else {
|
||||
y_factor = max_factor;
|
||||
}
|
||||
if (!z_null) {
|
||||
z_factor = (z_border - pos.z) / direction.z;
|
||||
} else {
|
||||
z_factor = max_factor;
|
||||
}
|
||||
float smallest_factor = min(min(x_factor, y_factor), z_factor);
|
||||
|
||||
has_moved = length(intersection_pos - (pos + smallest_factor * direction)) > 0.00001;
|
||||
//has_moved = intersection_pos != (pos + smallest_factor * direction);
|
||||
intersection_pos = pos + smallest_factor * direction;
|
||||
}
|
||||
}
|
||||
|
||||
uint hit_facing = uint(is_x_hit) * (2 + uint(x_pos)) + uint(is_y_hit) * (4 + uint(y_pos)) + uint(is_z_hit && !z_pos);
|
||||
//result.has_hit = true;
|
||||
if (!has_moved) {
|
||||
//result.has_hit = true;
|
||||
}
|
||||
if (!((compound_pos.x <= intersection_pos.x && intersection_pos.x <= compound_pos.x + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.y <= intersection_pos.y && intersection_pos.y <= compound_pos.y + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.z <= intersection_pos.z && intersection_pos.z <= compound_pos.z + float(compound_grid_size) * compound_scale))) {
|
||||
//result.has_hit = true;
|
||||
}
|
||||
|
||||
if (!((compound_pos.x <= oct_tree_pos.x && oct_tree_pos.x <= compound_pos.x + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.y <= oct_tree_pos.y && oct_tree_pos.y <= compound_pos.y + float(compound_grid_size) * compound_scale) &&
|
||||
(compound_pos.z <= oct_tree_pos.z && oct_tree_pos.z <= compound_pos.z + float(compound_grid_size) * compound_scale))) {
|
||||
//result.has_hit = true;
|
||||
}
|
||||
result.end_pos = intersection_pos;
|
||||
result.end_facing = hit_facing;
|
||||
result.end_volume = volume_index;
|
||||
result.end_direction = direction;
|
||||
}
|
||||
|
||||
compound_num += 1;
|
||||
}
|
||||
|
||||
if (result.has_hit) {
|
||||
break;
|
||||
}
|
||||
|
||||
float x_border = volume_pos_x + float((scene_info.infos[volume_index + 3]) * uint(x_pos)) * volume_scale - 0.5 * volume_scale;
|
||||
float y_border = volume_pos_y + float((scene_info.infos[volume_index + 4]) * uint(y_pos)) * volume_scale - 0.5 * volume_scale;
|
||||
float z_border = volume_pos_z + float((scene_info.infos[volume_index + 5]) * uint(z_pos)) * volume_scale - 0.5 * volume_scale;
|
||||
|
@ -267,12 +535,18 @@ Tracing trace_ray(uint volume_start, vec3 starting_pos, vec3 start_direction, fl
|
|||
|
||||
if (!x_null) {
|
||||
x_factor = (x_border - pos.x) / direction.x;
|
||||
} else {
|
||||
x_factor = max_factor;
|
||||
}
|
||||
if (!y_null) {
|
||||
y_factor = (y_border - pos.y) / direction.y;
|
||||
} else {
|
||||
y_factor = max_factor;
|
||||
}
|
||||
if (!z_null) {
|
||||
z_factor = (z_border - pos.z) / direction.z;
|
||||
} else {
|
||||
z_factor = max_factor;
|
||||
}
|
||||
|
||||
if ((x_factor >= max_factor) && (y_factor >= max_factor) && (z_factor >= max_factor)) {
|
||||
|
@ -515,6 +789,7 @@ void main() {
|
|||
float opacity = float(color_roughness.w) / 255.0;
|
||||
vec3 color_seen_through;
|
||||
if (t.has_hit) {
|
||||
//color_seen_through = vec3(float(t.end_color.x) / 255.0, float(t.end_color.y) / 255.0, float(t.end_color.z) / 255.0);
|
||||
color_seen_through = diffuse_tracing(t.end_volume, t.end_raster, t.end_pos, t.end_facing) * orig_color_sample * t.color_mul;
|
||||
color_seen_through = add_reflection(t.end_direction, t.end_facing, t.end_volume, t.end_pos, t.end_color, color_seen_through);
|
||||
}
|
||||
|
@ -525,6 +800,8 @@ void main() {
|
|||
|
||||
color_direct = add_reflection(normalize(clamped_pos - ubo.camera_pos), facing, fragVolumeStart, clamped_pos, color_roughness, color_direct);
|
||||
color_sum = opacity * color_direct + (1.0 - opacity) * color_seen_through;
|
||||
|
||||
//color_sum = color_seen_through;
|
||||
}
|
||||
else {
|
||||
color_sum = diffuse_tracing(fragVolumeStart, clamped_raster_pos, clamped_pos, facing);
|
||||
|
|
|
@ -99,6 +99,7 @@ pub struct AppData {
|
|||
pub compute_task_oct_tree_nodes: u64,
|
||||
// values passed to shader
|
||||
pub num_lights_per_volume: u32,
|
||||
pub num_compound_per_volume: u32,
|
||||
pub min_light_weight: f32,
|
||||
pub max_iterations_per_light: u32,
|
||||
pub diffuse_raster_steps: u32,
|
||||
|
|
|
@ -212,7 +212,7 @@ pub unsafe fn create_descriptor_set_layout(
|
|||
.binding(3)
|
||||
.descriptor_type(vk::DescriptorType::STORAGE_BUFFER)
|
||||
.descriptor_count(1)
|
||||
.stage_flags(vk::ShaderStageFlags::COMPUTE);
|
||||
.stage_flags(vk::ShaderStageFlags::COMPUTE | vk::ShaderStageFlags::FRAGMENT);
|
||||
|
||||
let storage_binding_compute_out_color = vk::DescriptorSetLayoutBinding::builder()
|
||||
.binding(4)
|
||||
|
|
|
@ -85,14 +85,6 @@ pub unsafe fn create_command_buffers(device: &Device, data: &mut app_data::AppDa
|
|||
.size(vk::WHOLE_SIZE as u64)
|
||||
.build();
|
||||
|
||||
device.cmd_pipeline_barrier(*command_buffer,
|
||||
vk::PipelineStageFlags::COMPUTE_SHADER,
|
||||
vk::PipelineStageFlags::VERTEX_INPUT,
|
||||
vk::DependencyFlags::DEVICE_GROUP,
|
||||
&[] as &[vk::MemoryBarrier],
|
||||
&[buffer_memory_barrier_index, buffer_memory_barrier_vertex],
|
||||
&[] as &[vk::ImageMemoryBarrier]);
|
||||
|
||||
// compute storage barrier
|
||||
let buffer_memory_barrier_color = vk::BufferMemoryBarrier::builder()
|
||||
.buffer(data.compute_out_storage_buffers_color[i])
|
||||
|
@ -155,7 +147,7 @@ pub unsafe fn create_command_buffers(device: &Device, data: &mut app_data::AppDa
|
|||
&[data.descriptor_sets[i]],
|
||||
&[]);
|
||||
|
||||
device.cmd_dispatch(*command_buffer, (data.compute_task_one_size as f64 / 16.0).ceil() as u32, 1, 1);
|
||||
device.cmd_dispatch(*command_buffer, ((data.compute_task_one_size / 2) as f64 / 16.0).ceil() as u32, 1, 1);
|
||||
|
||||
let buffer_memory_barrier_in = vk::BufferMemoryBarrier::builder()
|
||||
.buffer(data.compute_out_storage_buffers_size_three[i])
|
||||
|
@ -191,7 +183,7 @@ pub unsafe fn create_command_buffers(device: &Device, data: &mut app_data::AppDa
|
|||
&[data.descriptor_sets[i]],
|
||||
&[]);
|
||||
|
||||
device.cmd_dispatch(*command_buffer, (data.compute_task_one_size as f64 / 16.0).ceil() as u32, 1, 1);
|
||||
device.cmd_dispatch(*command_buffer, ((data.compute_task_one_size / 2) as f64 / 16.0).ceil() as u32, 1, 1);
|
||||
|
||||
let buffer_memory_barrier_in = vk::BufferMemoryBarrier::builder()
|
||||
.buffer(data.compute_out_storage_buffers_size_two[i])
|
||||
|
@ -227,17 +219,10 @@ pub unsafe fn create_command_buffers(device: &Device, data: &mut app_data::AppDa
|
|||
&[data.descriptor_sets[i]],
|
||||
&[]);
|
||||
|
||||
device.cmd_dispatch(*command_buffer, data.compute_task_oct_tree_nodes as u32, 1, 1);
|
||||
|
||||
let buffer_memory_barrier_in = vk::BufferMemoryBarrier::builder()
|
||||
.buffer(data.compute_out_storage_buffers_size_three[i])
|
||||
.src_access_mask(vk::AccessFlags::SHADER_READ)
|
||||
.dst_access_mask(vk::AccessFlags::SHADER_WRITE)
|
||||
.size(vk::WHOLE_SIZE as u64)
|
||||
.build();
|
||||
device.cmd_dispatch(*command_buffer, (data.compute_task_oct_tree_nodes as f64 / 16.0).ceil() as u32, 1, 1);
|
||||
|
||||
let buffer_memory_barrier_out = vk::BufferMemoryBarrier::builder()
|
||||
.buffer(data.compute_out_storage_buffers_size_two[i])
|
||||
.buffer(data.compute_out_storage_buffers_oct_tree[i])
|
||||
.src_access_mask(vk::AccessFlags::SHADER_WRITE)
|
||||
.dst_access_mask(vk::AccessFlags::SHADER_READ)
|
||||
.size(vk::WHOLE_SIZE as u64)
|
||||
|
@ -245,10 +230,18 @@ pub unsafe fn create_command_buffers(device: &Device, data: &mut app_data::AppDa
|
|||
|
||||
device.cmd_pipeline_barrier(*command_buffer,
|
||||
vk::PipelineStageFlags::COMPUTE_SHADER,
|
||||
vk::PipelineStageFlags::COMPUTE_SHADER,
|
||||
vk::PipelineStageFlags::FRAGMENT_SHADER,
|
||||
vk::DependencyFlags::DEVICE_GROUP,
|
||||
&[] as &[vk::MemoryBarrier],
|
||||
&[buffer_memory_barrier_in, buffer_memory_barrier_out],
|
||||
&[buffer_memory_barrier_out],
|
||||
&[] as &[vk::ImageMemoryBarrier]);
|
||||
|
||||
device.cmd_pipeline_barrier(*command_buffer,
|
||||
vk::PipelineStageFlags::COMPUTE_SHADER,
|
||||
vk::PipelineStageFlags::VERTEX_INPUT,
|
||||
vk::DependencyFlags::DEVICE_GROUP,
|
||||
&[] as &[vk::MemoryBarrier],
|
||||
&[buffer_memory_barrier_index, buffer_memory_barrier_vertex],
|
||||
&[] as &[vk::ImageMemoryBarrier]);
|
||||
}
|
||||
// start render pass
|
||||
|
|
|
@ -195,6 +195,7 @@ impl App {
|
|||
let mut data = app_data::AppData::default();
|
||||
data.use_geometry_shader = false;
|
||||
data.num_lights_per_volume = 5;
|
||||
data.num_compound_per_volume = 5;
|
||||
data.min_light_weight = 0.0001;
|
||||
data.max_iterations_per_light = 20;
|
||||
data.diffuse_raster_steps = 0;
|
||||
|
@ -281,7 +282,7 @@ impl App {
|
|||
|
||||
self.update_uniform_buffer(image_index)?;
|
||||
let time = self.appstart.elapsed().as_secs_f32() / 1.0;
|
||||
self.scene_handler.point_lights[0].borrow_mut().set_pos(cgmath::vec3((10.0 + 64.0) as f32 + time.sin() * 2.0, (10.0 + 64.0) as f32 + time.cos() * 2.0, 11.0));
|
||||
//self.scene_handler.point_lights[0].borrow_mut().set_pos(cgmath::vec3((10.0 + 64.0) as f32 + time.sin() * 2.0, (10.0 + 64.0) as f32 + time.cos() * 2.0, 11.0));
|
||||
self.synchronized = 0;
|
||||
|
||||
if self.synchronized < MAX_FRAMES_IN_FLIGHT {
|
||||
|
|
|
@ -13,6 +13,7 @@ use crate::scene::oct_tree::OctTree;
|
|||
use super::memorizable::Memorizable;
|
||||
use super::light::LightSource;
|
||||
use super::light::PointLight;
|
||||
use super::volumetrics::ShapeComposition;
|
||||
use super::AppData;
|
||||
use super::LightsIter;
|
||||
use super::Scene;
|
||||
|
@ -1063,10 +1064,10 @@ impl EmptyVolume {
|
|||
|
||||
let mut out_index = vec![];
|
||||
for index in 0..weighted_indices.len() {
|
||||
out_index.push(weighted_indices[weighted_indices.len() - (index + 1)].1 as u32);
|
||||
if out_index.len() == light_number as usize {
|
||||
break;
|
||||
}
|
||||
out_index.push(weighted_indices[weighted_indices.len() - (index + 1)].1 as u32);
|
||||
}
|
||||
while out_index.len() < light_number as usize {
|
||||
out_index.push(0);
|
||||
|
@ -1074,6 +1075,31 @@ impl EmptyVolume {
|
|||
out_index
|
||||
}
|
||||
|
||||
pub fn select_compounds(&self, compounds: &Vec<Rc<RefCell<ShapeComposition>>>, compound_number: u32) -> Vec<u32> {
|
||||
let mut weighted_indices = vec![];
|
||||
for compound in compounds {
|
||||
let bbox_low = compound.borrow().bbox_low;
|
||||
let bbox_high = compound.borrow().bbox_high;
|
||||
let diag = bbox_high - bbox_low;
|
||||
if (self.real_position.x < bbox_high.x || self.real_position.y < bbox_high.y || self.real_position.z < bbox_high.z) && (bbox_low.x < self.real_position.x + self.size_x as f32 || bbox_low.y < self.real_position.y + self.size_y as f32 || bbox_low.z < self.real_position.z + self.size_z as f32) {
|
||||
let le = diag.dot(diag);
|
||||
weighted_indices.push((le, compound.borrow().get_memory_start()));
|
||||
}
|
||||
}
|
||||
weighted_indices.sort_by(|a, b| a.0.partial_cmp(&b.0).unwrap());
|
||||
let mut out_index = vec![];
|
||||
for index in 0..weighted_indices.len() {
|
||||
if out_index.len() == compound_number as usize {
|
||||
break;
|
||||
}
|
||||
out_index.push(weighted_indices[weighted_indices.len() - (index + 1)].1 as u32);
|
||||
}
|
||||
while out_index.len() < compound_number as usize {
|
||||
out_index.push(0);
|
||||
}
|
||||
out_index
|
||||
}
|
||||
|
||||
pub fn combine_results(first: &Rc<RefCell<OctTree<Cube>>>,first_neighbors: &Rc<OctTree<Rc<RefCell<EmptyVolume>>>>, second: &Rc<RefCell<OctTree<Cube>>>, second_neighbors: &Rc<OctTree<Rc<RefCell<EmptyVolume>>>>, facing: vertex::Facing) {
|
||||
let mut first_start;
|
||||
let mut second_start;
|
||||
|
@ -1261,6 +1287,7 @@ impl Memorizable for EmptyVolume {
|
|||
mem_size += 12; //color/roughness buffer sizes, 2 values each
|
||||
mem_size += 12; //neighbor buffer sizes, 2 values each
|
||||
mem_size += 1; //scale of the volume, 1 float
|
||||
mem_size += data.num_compound_per_volume; // compound references
|
||||
|
||||
// this covers full color and roughness
|
||||
mem_size += (self.color_top.len() as u32).max(1);
|
||||
|
@ -1296,12 +1323,20 @@ impl Memorizable for EmptyVolume {
|
|||
mem_index += 1;
|
||||
v[mem_index] = self.size_z as u32;
|
||||
mem_index += 1;
|
||||
//Todo: insert lights
|
||||
//insert lights
|
||||
let selected_lights = self.select_lights(scene.get_light_iter(), data.num_lights_per_volume, data.min_light_weight);
|
||||
for light in selected_lights {
|
||||
v[mem_index] = light;
|
||||
mem_index += 1;
|
||||
}
|
||||
|
||||
// compound references
|
||||
let selected_compounds = self.select_compounds(&scene.volumetrics, data.num_compound_per_volume);
|
||||
for compound in selected_compounds {
|
||||
v[mem_index] = compound;
|
||||
mem_index += 1;
|
||||
}
|
||||
|
||||
//color/roughness buffer sizes, 2 values each
|
||||
if self.color_top.len() > 1 {
|
||||
v[mem_index] = self.size_x as u32;
|
||||
|
|
|
@ -57,7 +57,7 @@ pub fn generate_test_scene(scene: &mut Scene, data: &mut AppData) -> Result<(Poi
|
|||
let shade = (rng.gen_range(0..25) as f32) / 100.0;
|
||||
let cube = Cube {
|
||||
pos: vec3(10.0, 10.0, 10.0),
|
||||
color: vec3(0.0, 0.0, 0.9),
|
||||
color: vec3(0.9, 0.9, 0.9),
|
||||
tex_coord: vec2(0.0, 0.0),
|
||||
transparent: true,
|
||||
roughness: 32,
|
||||
|
@ -66,7 +66,7 @@ pub fn generate_test_scene(scene: &mut Scene, data: &mut AppData) -> Result<(Poi
|
|||
|
||||
let cube = Cube {
|
||||
pos: vec3(10.0, 10.0, 9.0),
|
||||
color: vec3(0.0, 0.0, 0.9),
|
||||
color: vec3(0.9, 0.9, 0.9),
|
||||
tex_coord: vec2(0.0, 0.0),
|
||||
transparent: true,
|
||||
roughness: 32,
|
||||
|
@ -93,7 +93,7 @@ pub fn generate_test_scene(scene: &mut Scene, data: &mut AppData) -> Result<(Poi
|
|||
oct_tree2.set_cube(cube.clone());
|
||||
|
||||
scene.point_lights.push(Rc::new(RefCell::new(PointLight::init(vec3(11.0 + grid_size as f32, 11.0 + grid_size as f32, 11.0) * scale, vec3(2.0, 2.0, 2.0)))));
|
||||
scene.point_lights.push(Rc::new(RefCell::new(PointLight::init(vec3(9.0 + grid_size as f32, 9.0 + grid_size as f32, 11.0) * scale, vec3(0.5, 0.5, 0.5)))));
|
||||
//scene.point_lights.push(Rc::new(RefCell::new(PointLight::init(vec3(9.0 + grid_size as f32, 9.0 + grid_size as f32, 11.0) * scale, vec3(0.5, 0.5, 0.5)))));
|
||||
scene.directional_lights.push(Rc::new(RefCell::new(DirectionalLight::init(vec3(1.0, 1.0, -1.0), vec3(0.1, 0.1, 0.1)))));
|
||||
|
||||
let cube = Cuboid {
|
||||
|
@ -112,13 +112,16 @@ pub fn generate_test_scene(scene: &mut Scene, data: &mut AppData) -> Result<(Poi
|
|||
size: Vector3 {x: 0.5, y: 0.5, z: 0.5} * scale
|
||||
};
|
||||
let index = scene.sized_vertices.len();
|
||||
cube.draw(&data.topology, index, scene);
|
||||
//cube.draw(&data.topology, index, scene);
|
||||
|
||||
let tree_ref_one = Rc::new(RefCell::new(oct_tree1.clone()));
|
||||
let tree_ref_two = Rc::new(RefCell::new(oct_tree2.clone()));
|
||||
scene.oct_trees = vec![vec![vec![tree_ref_two.clone(), tree_ref_two.clone(), tree_ref_two.clone()], vec![tree_ref_two.clone(), tree_ref_one.clone(), tree_ref_two.clone()], vec![tree_ref_two.clone(), tree_ref_two.clone(), tree_ref_two.clone()]], vec![vec![tree_ref_two.clone(), tree_ref_two.clone(), tree_ref_two.clone()], vec![tree_ref_two.clone(), tree_ref_one.clone(), tree_ref_two.clone()], vec![tree_ref_two.clone(), tree_ref_two.clone(), tree_ref_two.clone()]]];
|
||||
//scene.oct_trees = vec![vec![vec![tree_ref_two.clone(), tree_ref_two.clone(), tree_ref_two.clone()], vec![tree_ref_two.clone(), tree_ref_one.clone(), tree_ref_two.clone()], vec![tree_ref_two.clone(), tree_ref_two.clone(), tree_ref_two.clone()]]];
|
||||
|
||||
let mut comp = ShapeComposition::new(64);
|
||||
//comp.included_shapes.push(Rc::new(RefCell::new(Rect::new(Vector3 { x: 5.0 + grid_size as f32, y: 5.0 + grid_size as f32, z: 10.0 }, Vector3 { x: 0.0, y: 0.0, z: 0.0 }, Vector3 { x: 5.0, y: 5.0, z: 5.0 },Vector3 { x: 0, y: 0, z: 255 }, 64, false))));
|
||||
|
||||
comp.included_shapes.push(Rc::new(RefCell::new(Sphere::new(Vector3 { x: 5.0 + grid_size as f32, y: 5.0 + grid_size as f32, z: 10.0 }, Vector3 { x: 0.0, y: 0.0, z: 0.0 }, 2.0, Vector3 { x: 0, y: 255, z: 0 }, 64, false))));
|
||||
comp.included_shapes.push(Rc::new(RefCell::new(Sphere::new(Vector3 { x: 5.0 + grid_size as f32, y: 5.0 + grid_size as f32, z: 10.0 }, Vector3 { x: 0.0, y: 0.0, z: 0.0 }, 2.5, Vector3 { x: 255, y: 0, z: 0 }, 64, false))));
|
||||
comp.excluded_shapes.push(Rc::new(RefCell::new(Sphere::new(Vector3 { x: 5.0 + grid_size as f32, y: 5.0 + grid_size as f32, z: 11.5 }, Vector3 { x: 0.0, y: 0.0, z: 0.0 }, 1.5, Vector3 { x: 0, y: 255, z: 0 }, 64, false))));
|
||||
|
|
|
@ -181,49 +181,25 @@ impl Scene {
|
|||
|
||||
pub fn update_memory(&mut self, data: &mut AppData, reuse_memory: bool) {
|
||||
// reuse_memory controls whether a fresh data vector is created or the existing one is used if it is the right size
|
||||
let mut memory_index = 6;
|
||||
let mut memory_index = 7;
|
||||
// 0 - location for the maximum number of lights referenced per chunk (also will be the invalid memory allocation for pointing to a nonexistant neighbor)
|
||||
// 1 - location for the max iterations per light
|
||||
// 2 - diffuse raster samples (2*n + 1) * (2*n + 1) so as to always have at least the central fragment covered
|
||||
// 3 - diffuse raster size
|
||||
// 4 - max recursive rays
|
||||
// 5 - diffuse rays per hit
|
||||
// 6 - maximum number of compounds per light
|
||||
for memorizable in &self.memorizables {
|
||||
memorizable.borrow_mut().set_memory_start(memory_index);
|
||||
memory_index += memorizable.borrow_mut().get_buffer_mem_size(data) as usize;
|
||||
}
|
||||
|
||||
//println!("Memory size is {} kB, max indes is {}", memory_index * 32 / 8 /1024 + 1, memory_index);
|
||||
let mut volume_vec;
|
||||
let needs_overwrite;
|
||||
if !reuse_memory || memory_index != self.rt_memory.len() {
|
||||
volume_vec = vec![data.num_lights_per_volume; memory_index];
|
||||
needs_overwrite = true;
|
||||
} else {
|
||||
needs_overwrite = false;
|
||||
volume_vec = self.rt_memory.clone();
|
||||
}
|
||||
volume_vec[1] = data.max_iterations_per_light;
|
||||
volume_vec[2] = data.diffuse_raster_steps;
|
||||
volume_vec[3] = u32::from_ne_bytes(data.diffuse_raster_size.to_ne_bytes());
|
||||
volume_vec[4] = data.max_recursive_rays;
|
||||
volume_vec[5] = data.diffuse_rays_per_hit;
|
||||
|
||||
for memorizable in &self.memorizables {
|
||||
if needs_overwrite || memorizable.borrow().is_dirty() {
|
||||
volume_vec = memorizable.borrow_mut().insert_into_memory(volume_vec, data, &self);
|
||||
}
|
||||
}
|
||||
|
||||
self.rt_memory = volume_vec;
|
||||
data.scene_rt_memory_size = (self.rt_memory.len() * 4) as u64; // size of the needed buffer size in bytes
|
||||
|
||||
let mut data_len = 0;
|
||||
let mut compound_data_len = 1;
|
||||
for compound in &self.volumetrics {
|
||||
compound.borrow_mut().set_memory_start(data_len);
|
||||
data_len += compound.borrow().get_compound_buffer_mem_size(data) as usize;
|
||||
compound.borrow_mut().set_memory_start(compound_data_len);
|
||||
compound_data_len += compound.borrow().get_compound_buffer_mem_size(data) as usize;
|
||||
}
|
||||
let mut volumetrics_memory = vec![0; data_len];
|
||||
let mut volumetrics_memory = vec![compound_data_len as u32; compound_data_len];
|
||||
|
||||
let mut compute_task_one_size = 0;
|
||||
let mut compute_task_one_out_size = 0;
|
||||
|
@ -238,13 +214,40 @@ impl Scene {
|
|||
compute_task_one_out_size += compound.borrow().size.pow(3) as usize;
|
||||
}
|
||||
|
||||
//println!("Memory size is {} kB, max indes is {}", memory_index * 32 / 8 /1024 + 1, memory_index);
|
||||
let mut volume_vec;
|
||||
let needs_overwrite;
|
||||
if !reuse_memory || memory_index != self.rt_memory.len() {
|
||||
volume_vec = vec![data.num_lights_per_volume; memory_index];
|
||||
needs_overwrite = true;
|
||||
} else {
|
||||
needs_overwrite = false;
|
||||
volume_vec = self.rt_memory.clone();
|
||||
}
|
||||
volume_vec[0] = data.num_lights_per_volume;
|
||||
volume_vec[1] = data.max_iterations_per_light;
|
||||
volume_vec[2] = data.diffuse_raster_steps;
|
||||
volume_vec[3] = u32::from_ne_bytes(data.diffuse_raster_size.to_ne_bytes());
|
||||
volume_vec[4] = data.max_recursive_rays;
|
||||
volume_vec[5] = data.diffuse_rays_per_hit;
|
||||
volume_vec[6] = data.num_compound_per_volume;
|
||||
|
||||
for memorizable in &self.memorizables {
|
||||
if needs_overwrite || memorizable.borrow().is_dirty() {
|
||||
volume_vec = memorizable.borrow_mut().insert_into_memory(volume_vec, data, &self);
|
||||
}
|
||||
}
|
||||
|
||||
self.rt_memory = volume_vec;
|
||||
data.scene_rt_memory_size = (self.rt_memory.len() * 4) as u64; // size of the needed buffer size in bytes
|
||||
|
||||
self.volumetrics_memory = volumetrics_memory;
|
||||
data.scene_rt_volumetric_size = (self.volumetrics_memory.len() * 4) as u64; // size of the needed buffer size in bytes
|
||||
data.compute_task_one_size = compute_task_one_size;
|
||||
data.compute_task_one_out_buffer_size = (compute_task_one_out_size * 4) as u64;
|
||||
data.compute_task_one_out_size = compute_task_one_out_size as u64;
|
||||
data.compute_task_oct_tree_size = target_index as u64;
|
||||
data.compute_task_oct_tree_nodes = node_count as u64;
|
||||
data.compute_task_oct_tree_nodes = (node_count) as u64;
|
||||
}
|
||||
|
||||
pub unsafe fn destroy(&mut self, device: &vulkanalia::Device) {
|
||||
|
|
|
@ -37,11 +37,13 @@ pub struct ShapeComposition {
|
|||
pub included_shapes: Vec<Rc<RefCell<dyn Volumetrics>>>,
|
||||
pub excluded_shapes: Vec<Rc<RefCell<dyn Volumetrics>>>,
|
||||
dirty: bool,
|
||||
pub bbox_low: Vector3<f32>,
|
||||
pub bbox_high: Vector3<f32>,
|
||||
}
|
||||
|
||||
impl ShapeComposition {
|
||||
pub fn new(size: u32) -> Self {
|
||||
Self { memory_start: 0, target_memory_start: 0, prev_memory_size: 0, size: size, included_shapes: vec![], excluded_shapes: vec![], dirty: true }
|
||||
Self { memory_start: 0, target_memory_start: 0, prev_memory_size: 0, size: size, included_shapes: vec![], excluded_shapes: vec![], dirty: true, bbox_low: Vector3 { x: 0.0, y: 0.0, z: 0.0 }, bbox_high: Vector3 { x: 0.0, y: 0.0, z: 0.0 } }
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -61,7 +63,7 @@ impl CompoundMemorizable for ShapeComposition {
|
|||
|
||||
impl Memorizable for ShapeComposition {
|
||||
fn get_buffer_mem_size(&self, data: &AppData) -> u32 {
|
||||
//size, scale, memory_end, num_included, num_excluded, pos, wrapping address, included_address, excluded_address
|
||||
//size, scale, memory_end, num_included, num_excluded, pos, target address, included_address, excluded_address
|
||||
1 + 1 + 1 + 1 + 1 + 3 + 1 + self.included_shapes.len() as u32 + self.excluded_shapes.len() as u32
|
||||
}
|
||||
|
||||
|
@ -118,6 +120,8 @@ impl Memorizable for ShapeComposition {
|
|||
}
|
||||
|
||||
let bbox_high_pos_ind = bbox_high - bbox_low;
|
||||
self.bbox_low = bbox_low;
|
||||
self.bbox_high = bbox_high;
|
||||
let scale = bbox_high_pos_ind.x.max(bbox_high_pos_ind.y.max(bbox_high_pos_ind.z)) / (self.size as f32);
|
||||
|
||||
v[self.memory_start + 1] = u32::from_ne_bytes(scale.to_ne_bytes());
|
||||
|
@ -127,7 +131,7 @@ impl Memorizable for ShapeComposition {
|
|||
v[self.memory_start + 5] = u32::from_ne_bytes(bbox_low.x.to_ne_bytes());
|
||||
v[self.memory_start + 6] = u32::from_ne_bytes(bbox_low.y.to_ne_bytes());
|
||||
v[self.memory_start + 7] = u32::from_ne_bytes(bbox_low.z.to_ne_bytes());
|
||||
v[self.memory_start + 8] = 0; //TODO add wrapping reference
|
||||
v[self.memory_start + 8] = self.target_memory_start as u32;
|
||||
|
||||
self.prev_memory_size = self.get_compound_buffer_mem_size(data);
|
||||
self.dirty = false;
|
||||
|
@ -153,7 +157,6 @@ impl ShapeComposition {
|
|||
add_size *= 8;
|
||||
size /= 2;
|
||||
}
|
||||
|
||||
nodes
|
||||
}
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue