Skip to content

Commit

Permalink
Implemented OctreeGPUView, refactored bevy module
Browse files Browse the repository at this point in the history
  • Loading branch information
davids91 committed Nov 16, 2024
1 parent 80c44fc commit b056da4
Show file tree
Hide file tree
Showing 13 changed files with 809 additions and 401 deletions.
2 changes: 1 addition & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[package]
name = "shocovox-rs"
version = "0.4.2"
version = "0.5.0"
edition = "2021"
authors = ["Dávid Tóth <[email protected]>"]
license = "MIT OR Apache-2.0"
Expand Down
12 changes: 11 additions & 1 deletion assets/shaders/viewport_render.wgsl
Original file line number Diff line number Diff line change
Expand Up @@ -283,6 +283,10 @@ fn set_brick_used(brick_index: u32) {
}
}

fn request_node(node: u32, child_octant: u32){

}

//crate::spatial::math::step_octant
fn step_octant(octant: u32, step: ptr<function, vec3f>) -> u32 {
return (
Expand Down Expand Up @@ -404,7 +408,7 @@ fn probe_brick(
let brick_index = node_children[((leaf_node_key * 8) + brick_octant)];
//set_brick_used(brick_index);
// +++ DEBUG +++
if(0 == metadata[arrayLength(&metadata) - 1]){
if(0 == debug_interface){
set_brick_used(brick_index);
}
if(0 != ((0x01u << (8 + brick_octant)) & metadata[leaf_node_key])) { // brick is not empty
Expand Down Expand Up @@ -804,6 +808,12 @@ var<storage, read_write> voxels: array<Voxelement>;
@group(1) @binding(5)
var<storage, read_write> color_palette: array<vec4f>;

// +++ DEBUG +++
@group(1) @binding(6)
var<storage, read_write> debug_interface: u32;
// --- DEBUG ---


@compute @workgroup_size(8, 8, 1)
fn update(
@builtin(global_invocation_id) invocation_id: vec3<u32>,
Expand Down
124 changes: 98 additions & 26 deletions examples/dot_cube.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,10 +9,8 @@ use iyes_perf_ui::{

#[cfg(feature = "bevy_wgpu")]
use shocovox_rs::octree::{
raytracing::{
bevy::create_viewing_glass, ShocoVoxRenderPlugin, ShocoVoxViewingGlass, Viewport,
},
Albedo, V3c,
raytracing::{OctreeGPUView, Ray, ShocoVoxRenderPlugin, Viewport},
Albedo, Octree, V3c, VoxelData,
};

#[cfg(feature = "bevy_wgpu")]
Expand All @@ -24,6 +22,15 @@ const BRICK_DIMENSION: usize = 2;
#[cfg(feature = "bevy_wgpu")]
const TREE_SIZE: u32 = 16;

#[cfg(feature = "bevy_wgpu")]
#[derive(Resource)]
struct TreeResource<T, const DIM: usize>
where
T: Default + Clone + PartialEq + VoxelData,
{
tree: Octree<T, DIM>,
}

#[cfg(feature = "bevy_wgpu")]
fn main() {
App::new()
Expand Down Expand Up @@ -109,14 +116,14 @@ fn setup(mut commands: Commands, images: ResMut<Assets<Image>>) {
}
}

let render_data = tree.create_bevy_view();
let viewing_glass = create_viewing_glass(
&Viewport {
let output_texture = tree.create_new_gpu_view(
Viewport {
origin,
direction: (V3c::new(0., 0., 0.) - origin).normalized(),
w_h_fov: V3c::new(10., 10., 3.),
},
DISPLAY_RESOLUTION,
&mut commands,
images,
);

Expand All @@ -130,13 +137,11 @@ fn setup(mut commands: Commands, images: ResMut<Assets<Image>>) {
custom_size: Some(Vec2::new(1024., 768.)),
..default()
},
texture: viewing_glass.output_texture.clone(),
texture: output_texture,
..default()
});
commands.spawn(Camera2dBundle::default());
commands.insert_resource(render_data);
commands.insert_resource(viewing_glass);

commands.insert_resource(TreeResource { tree });
commands.spawn((
PerfUiRoot::default(),
PerfUiEntryFPS {
Expand All @@ -163,31 +168,34 @@ struct DomePosition {
yaw: f32,
roll: f32,
}

#[cfg(feature = "bevy_wgpu")]
fn rotate_camera(
angles_query: Query<&mut DomePosition>,
mut viewing_glass: ResMut<ShocoVoxViewingGlass>,
) {
fn rotate_camera(angles_query: Query<&mut DomePosition>, mut tree_view: ResMut<OctreeGPUView>) {
let (yaw, roll) = (angles_query.single().yaw, angles_query.single().roll);

let radius = angles_query.single().radius;
viewing_glass.viewport.origin = V3c::new(

tree_view.viewing_glass.viewport.origin = V3c::new(
radius / 2. + yaw.sin() * radius,
radius + roll.sin() * radius * 2.,
radius / 2. + yaw.cos() * radius,
);
viewing_glass.viewport.direction =
(V3c::unit(radius / 2.) - viewing_glass.viewport.origin).normalized();
tree_view.viewing_glass.viewport.direction =
(V3c::unit(radius / 2.) - tree_view.viewing_glass.viewport.origin).normalized();
}

#[cfg(feature = "bevy_wgpu")]
fn handle_zoom(
keys: Res<ButtonInput<KeyCode>>,
mut viewing_glass: ResMut<ShocoVoxViewingGlass>,
mut tree_view: ResMut<OctreeGPUView>,
mut angles_query: Query<&mut DomePosition>,
tree: Res<TreeResource<Albedo, BRICK_DIMENSION>>,
) {
const ADDITION: f32 = 0.02;
if keys.pressed(KeyCode::Delete) {
tree_view.do_the_thing = true;
}
// if tree_view.is_changed() {
// println!("changed!! --> {:?}", tree_view.read_back);
// }
const ADDITION: f32 = 0.05;
let angle_update_fn = |angle, delta| -> f32 {
let new_angle = angle + delta;
if new_angle < 360. {
Expand All @@ -196,11 +204,75 @@ fn handle_zoom(
0.
}
};
if keys.pressed(KeyCode::Tab) {
// Render the current view with CPU
let viewport_up_direction = V3c::new(0., 1., 0.);
let viewport_right_direction = viewport_up_direction
.cross(tree_view.viewing_glass.viewport.direction)
.normalized();
let pixel_width =
tree_view.viewing_glass.viewport.w_h_fov.x as f32 / DISPLAY_RESOLUTION[0] as f32;
let pixel_height =
tree_view.viewing_glass.viewport.w_h_fov.y as f32 / DISPLAY_RESOLUTION[1] as f32;
let viewport_bottom_left = tree_view.viewing_glass.viewport.origin
+ (tree_view.viewing_glass.viewport.direction
* tree_view.viewing_glass.viewport.w_h_fov.z)
- (viewport_up_direction * (tree_view.viewing_glass.viewport.w_h_fov.y / 2.))
- (viewport_right_direction * (tree_view.viewing_glass.viewport.w_h_fov.x / 2.));

// define light
let diffuse_light_normal = V3c::new(0., -1., 1.).normalized();

use image::ImageBuffer;
use image::Rgb;
let mut img = ImageBuffer::new(DISPLAY_RESOLUTION[0], DISPLAY_RESOLUTION[1]);

// cast each ray for a hit
for x in 0..DISPLAY_RESOLUTION[0] {
for y in 0..DISPLAY_RESOLUTION[1] {
let actual_y_in_image = DISPLAY_RESOLUTION[1] - y - 1;
//from the origin of the camera to the current point of the viewport
let glass_point = viewport_bottom_left
+ viewport_right_direction * x as f32 * pixel_width
+ viewport_up_direction * y as f32 * pixel_height;
let ray = Ray {
origin: tree_view.viewing_glass.viewport.origin,
direction: (glass_point - tree_view.viewing_glass.viewport.origin).normalized(),
};

use std::io::Write;
std::io::stdout().flush().ok().unwrap();

if let Some(hit) = tree.tree.get_by_ray(&ray) {
let (data, _, normal) = hit;
//Because both vector should be normalized, the dot product should be 1*1*cos(angle)
//That means it is in range -1, +1, which should be accounted for
let diffuse_light_strength =
1. - (normal.dot(&diffuse_light_normal) / 2. + 0.5);
img.put_pixel(
x,
actual_y_in_image,
Rgb([
(data.r as f32 * diffuse_light_strength) as u8,
(data.g as f32 * diffuse_light_strength) as u8,
(data.b as f32 * diffuse_light_strength) as u8,
]),
);
} else {
img.put_pixel(x, actual_y_in_image, Rgb([128, 128, 128]));
}
}
}

img.save("example_junk_cpu_render.png").ok().unwrap();
}

let multiplier = if keys.pressed(KeyCode::ShiftLeft) {
10.0 // Doesn't have any effect?!
} else {
1.0
};

if keys.pressed(KeyCode::ArrowUp) {
angles_query.single_mut().roll = angle_update_fn(angles_query.single().roll, ADDITION);
}
Expand All @@ -222,12 +294,12 @@ fn handle_zoom(
angles_query.single_mut().radius *= 1. + 0.02 * multiplier;
}
if keys.pressed(KeyCode::Home) {
viewing_glass.viewport.w_h_fov.x *= 1. + 0.09 * multiplier;
viewing_glass.viewport.w_h_fov.y *= 1. + 0.09 * multiplier;
tree_view.viewing_glass.viewport.w_h_fov.x *= 1. + 0.09 * multiplier;
tree_view.viewing_glass.viewport.w_h_fov.y *= 1. + 0.09 * multiplier;
}
if keys.pressed(KeyCode::End) {
viewing_glass.viewport.w_h_fov.x *= 1. - 0.09 * multiplier;
viewing_glass.viewport.w_h_fov.y *= 1. - 0.09 * multiplier;
tree_view.viewing_glass.viewport.w_h_fov.x *= 1. - 0.09 * multiplier;
tree_view.viewing_glass.viewport.w_h_fov.y *= 1. - 0.09 * multiplier;
}
}

Expand Down
Loading

0 comments on commit b056da4

Please sign in to comment.