Compare commits

..

2 commits

Author SHA1 Message Date
griffi-gh a71d898860 fix 2023-07-20 09:55:10 +02:00
griffi-gh cafd0a4b3d uniforms, bind groups and other nice stuff 2023-07-20 03:03:52 +02:00
18 changed files with 416 additions and 322 deletions

View file

@ -2,7 +2,7 @@ use serde::{Serialize, Deserialize};
use strum::EnumIter;
#[derive(Serialize, Deserialize, Clone, Copy, Debug, EnumIter)]
#[repr(u8)]
#[repr(u32)]
pub enum BlockTexture {
Stone,
Dirt,

View file

@ -1,4 +1,4 @@
use shipyard::{NonSendSync, UniqueView, Unique, AllStoragesView};
use shipyard::{UniqueView, Unique, AllStoragesView};
use kubi_shared::block::BlockTexture;
use crate::rendering::Renderer;
@ -6,7 +6,6 @@ mod texture;
mod shaders;
use texture::load_asset_texture_array;
use shaders::include_shader_prefab;
pub trait AssetPaths {
fn file_name(self) -> &'static str;
@ -41,10 +40,10 @@ pub struct BlockTexturesAsset(pub wgpu::Texture);
pub fn load_prefabs(
storages: AllStoragesView,
renderer: NonSendSync<UniqueView<Renderer>>
renderer: UniqueView<Renderer>
) {
log::info!("Loading textures...");
storages.add_unique_non_send_sync(BlockTexturesAsset(
storages.add_unique(BlockTexturesAsset(
load_asset_texture_array::<BlockTexture>("blocks".into(), &renderer)
));
}

View file

@ -8,6 +8,8 @@ mod frustum;
use matrices::update_matrices;
use frustum::{Frustum, update_frustum};
//TODO: handle cases where we have multiple cameras
#[derive(Component)]
pub struct Camera {
pub view_matrix: Mat4,

View file

@ -7,7 +7,7 @@ pub struct CursorLock(pub bool);
pub fn update_cursor_lock_state(
lock: UniqueView<CursorLock>,
renderer: NonSendSync<UniqueView<Renderer>>
renderer: UniqueView<Renderer>
) {
#[cfg(not(target_os = "android"))]
if lock.is_inserted_or_modified() {

View file

@ -82,7 +82,7 @@ pub fn initial_resize_event(
mut storages: AllStoragesViewMut,
) {
let size = {
let renderer = storages.borrow::<NonSendSync<UniqueView<Renderer>>>().unwrap();
let renderer = storages.borrow::<UniqueView<Renderer>>().unwrap();
UVec2::new(renderer.size.width, renderer.size.height)
};
storages.add_entity((

View file

@ -59,10 +59,11 @@ use rendering::{
Renderer,
RenderTarget,
BackgroundColor,
init_rendering_internals,
world::{draw_world, draw_current_chunk_border},
selection_box::render_selection_box,
entities::render_entities,
renderer_finish_init,
camera_uniform::update_camera_uniform,
};
use block_placement::update_block_placement;
use delta_time::{DeltaTime, init_delta_time};
@ -84,7 +85,7 @@ fn pre_startup() -> Workload {
fn startup() -> Workload {
(
renderer_finish_init,
init_rendering_internals,
init_fixed_timestamp_storage,
initial_resize_event,
load_prefabs,
@ -133,9 +134,11 @@ fn update() -> Workload {
).into_sequential_workload()
}
//TODO move this to the renderer module
fn render() -> Workload {
(
(
update_camera_uniform,
draw_world,
draw_current_chunk_border,
render_selection_box,
@ -191,7 +194,7 @@ pub fn kubi_main() {
//Initialize renderer
{
let settings = world.borrow::<UniqueView<GameSettings>>().unwrap();
world.add_unique_non_send_sync(Renderer::init_blocking(&event_loop, &settings));
world.add_unique(Renderer::init_blocking(&event_loop, &settings));
}
world.add_unique(BackgroundColor(vec3(0.5, 0.5, 1.)));
@ -215,7 +218,7 @@ pub fn kubi_main() {
Event::WindowEvent { event, .. } => match event {
WindowEvent::Resized(new_size) => {
//this can be in a system but I don't care
world.borrow::<NonSendSync<UniqueViewMut<Renderer>>>().unwrap().resize(new_size);
world.borrow::<UniqueViewMut<Renderer>>().unwrap().resize(new_size);
}
WindowEvent::CloseRequested => {
log::info!("exit requested");
@ -237,7 +240,7 @@ pub fn kubi_main() {
//Start rendering (maybe use custom views for this?)
let target = {
let renderer = world.borrow::<NonSendSync<UniqueView<Renderer>>>().unwrap();
let renderer = world.borrow::<UniqueView<Renderer>>().unwrap();
renderer.begin()
};
world.add_unique(target);

View file

@ -1,4 +1,4 @@
use shipyard::{Unique, View, Workload, SystemModificator, IntoWorkload};
use shipyard::{Unique, Workload, IntoWorkload, WorkloadModificator};
use winit::{
event_loop::EventLoop,
window::{Window, WindowBuilder, Fullscreen},
@ -6,17 +6,18 @@ use winit::{
};
use glam::{Vec3, Mat4};
use pollster::FutureExt as _;
use crate::{events::WindowResizedEvent, settings::{GameSettings, FullscreenMode}};
use crate::settings::{GameSettings, FullscreenMode};
use self::{pipelines::init_pipelines, primitives::init_primitives, shaders::compile_shaders};
use self::{primitives::init_primitives, shaders::compile_shaders, camera_uniform::init_camera_uniform};
pub mod shaders;
pub mod pipelines;
pub mod primitives;
pub mod world;
pub mod selection_box;
pub mod entities;
pub mod world;
pub mod camera_uniform;
//TODO remove this if possible
pub const OPENGL_TO_WGPU_MATRIX: Mat4 = Mat4::from_cols_array(&[
1.0, 0.0, 0.0, 0.0,
0.0, 1.0, 0.0, 0.0,
@ -24,7 +25,6 @@ pub const OPENGL_TO_WGPU_MATRIX: Mat4 = Mat4::from_cols_array(&[
0.0, 0.0, 0.5, 1.0,
]);
#[derive(Unique)]
pub struct RenderTarget {
pub output: wgpu::SurfaceTexture,
@ -218,17 +218,14 @@ impl Renderer {
}
}
pub fn renderer_finish_init() -> Workload {
/// THIS DOES NOT INIT [`Renderer`]!
pub fn init_rendering_internals() -> Workload {
(
compile_shaders,
init_pipelines.after_all(compile_shaders),
init_camera_uniform,
init_primitives,
compile_shaders,
(
world::init_gpu_data,
).into_workload().after_all(compile_shaders),
).into_workload()
}
#[deprecated]
pub fn if_resized (
resize: View<WindowResizedEvent>,
) -> bool {
resize.len() > 0
}

View file

@ -0,0 +1,45 @@
use shipyard::{Unique, UniqueView, AllStoragesView, View, IntoIter};
use wgpu::util::DeviceExt;
use crate::camera::Camera;
use super::{Renderer, OPENGL_TO_WGPU_MATRIX};
#[repr(C, packed)]
#[derive(Clone, Copy, Default, bytemuck::Pod, bytemuck::Zeroable)]
struct CameraUniform {
view_proj: [[f32; 4]; 4],
}
#[derive(Unique)]
pub struct CameraUniformBuffer(pub wgpu::Buffer);
pub fn init_camera_uniform(
storages: AllStoragesView
) {
let buffer = {
let renderer = storages.borrow::<UniqueView<Renderer>>().unwrap();
CameraUniformBuffer(
renderer.device.create_buffer_init(
&wgpu::util::BufferInitDescriptor {
label: Some("CameraUniformBuffer"),
contents: bytemuck::cast_slice(&[CameraUniform::default()]),
usage: wgpu::BufferUsages::UNIFORM | wgpu::BufferUsages::COPY_DST,
}
)
)
};
storages.add_unique(buffer);
}
pub fn update_camera_uniform(
renderer: UniqueView<Renderer>,
camera: View<Camera>,
buffer: UniqueView<CameraUniformBuffer>,
) {
//Just pick the first camera, if it exists, of course
let Some(camera) = camera.iter().next() else { return };
renderer.queue.write_buffer(&buffer.0, 0, bytemuck::cast_slice(&[
CameraUniform {
view_proj: (camera.perspective_matrix * camera.view_matrix * OPENGL_TO_WGPU_MATRIX).to_cols_array_2d()
}
]));
}

View file

@ -10,48 +10,47 @@ use super::shaders::Shaders;
pub fn render_entities() {}
#[cfg(fuck)]
pub fn render_entities(
mut target: NonSendSync<UniqueViewMut<RenderTarget>>,
buffers: NonSendSync<UniqueView<CenteredCubePrimitive>>,
shaders: NonSendSync<UniqueView<Shaders>>,
camera: View<Camera>,
settings: UniqueView<GameSettings>,
entities: View<Entity>,
transform: View<Transform>,
) {
let (camera_id, camera) = camera.iter().with_id().next().expect("No cameras in the scene");
// pub fn render_entities(
// mut target: NonSendSync<UniqueViewMut<RenderTarget>>,
// buffers: NonSendSync<UniqueView<CenteredCubePrimitive>>,
// shaders: NonSendSync<UniqueView<Shaders>>,
// camera: View<Camera>,
// settings: UniqueView<GameSettings>,
// entities: View<Entity>,
// transform: View<Transform>,
// ) {
// let (camera_id, camera) = camera.iter().with_id().next().expect("No cameras in the scene");
let draw_parameters = DrawParameters {
depth: Depth {
test: DepthTest::IfLess,
write: true,
..Default::default()
},
multisampling: settings.msaa.is_some(),
polygon_mode: PolygonMode::Fill,
backface_culling: BackfaceCullingMode::CullClockwise,
..Default::default()
};
let view = camera.view_matrix.to_cols_array_2d();
let perspective = camera.perspective_matrix.to_cols_array_2d();
// let draw_parameters = DrawParameters {
// depth: Depth {
// test: DepthTest::IfLess,
// write: true,
// ..Default::default()
// },
// multisampling: settings.msaa.is_some(),
// polygon_mode: PolygonMode::Fill,
// backface_culling: BackfaceCullingMode::CullClockwise,
// ..Default::default()
// };
// let view = camera.view_matrix.to_cols_array_2d();
// let perspective = camera.perspective_matrix.to_cols_array_2d();
for (entity_id, (_, trans)) in (&entities, &transform).iter().with_id() {
//skip rendering camera holder (as the entity would block the view)
if entity_id == camera_id { continue }
// for (entity_id, (_, trans)) in (&entities, &transform).iter().with_id() {
// //skip rendering camera holder (as the entity would block the view)
// if entity_id == camera_id { continue }
//render entity
// target.0.draw(
// &buffers.0,
// &buffers.1,
// &program.0,
// &uniform! {
// color: [1.0, 1.0, 1.0, 1.0_f32],
// model: trans.0.to_cols_array_2d(),
// view: view,
// perspective: perspective,
// },
// &draw_parameters
// ).unwrap();
}
}
// render entity
// target.0.draw(
// &buffers.0,
// &buffers.1,
// &program.0,
// &uniform! {
// color: [1.0, 1.0, 1.0, 1.0_f32],
// model: trans.0.to_cols_array_2d(),
// view: view,
// perspective: perspective,
// },
// &draw_parameters
// ).unwrap();
// }
// }

View file

@ -1,51 +0,0 @@
use shipyard::{Unique, AllStoragesView, NonSendSync, UniqueView};
use super::{shaders::Shaders, Renderer};
#[derive(Unique)]
pub struct Pipelines {
pub world: wgpu::RenderPipeline
}
pub fn init_pipelines(
storages: AllStoragesView
) {
let renderer = storages.borrow::<NonSendSync<UniqueView<Renderer>>>().unwrap();
let shaders = storages.borrow::<UniqueView<Shaders>>().unwrap();
storages.add_unique(Pipelines {
world: renderer.device.create_render_pipeline(&wgpu::RenderPipelineDescriptor {
label: Some("WorldRenderPipeline"),
layout: Some(&renderer.device.create_pipeline_layout(&wgpu::PipelineLayoutDescriptor {
label: Some("WorldRenderPipelineLayout"),
bind_group_layouts: &[],
push_constant_ranges: &[],
})),
vertex: wgpu::VertexState {
module: &shaders.world,
entry_point: "vs_main",
buffers: &[],
},
fragment: Some(wgpu::FragmentState {
module: &shaders.world,
entry_point: "fs_main",
targets: &[Some(wgpu::ColorTargetState {
format: renderer.config.format,
blend: Some(wgpu::BlendState::REPLACE),
write_mask: wgpu::ColorWrites::ALL,
})],
}),
primitive: wgpu::PrimitiveState {
topology: wgpu::PrimitiveTopology::TriangleList,
strip_index_format: None,
front_face: wgpu::FrontFace::Ccw,
cull_mode: Some(wgpu::Face::Back),
polygon_mode: wgpu::PolygonMode::Fill,
unclipped_depth: false,
conservative: false,
},
//TODO enable depth buffer
depth_stencil: None,
multisample: wgpu::MultisampleState::default(),
multiview: None,
}),
})
}

View file

@ -57,7 +57,7 @@ const CUBE_INDICES: &[u16] = &[
pub(super) fn init_cube_primitive(
storages: AllStoragesView,
renderer: NonSendSync<UniqueView<Renderer>>
renderer: UniqueView<Renderer>
) {
storages.add_unique(
CubePrimitive {

View file

@ -19,7 +19,7 @@ const RECT_INDEX: &[u16] = &[0, 1, 2, 1, 3, 2];
pub(super) fn init_rect_primitive(
storages: AllStoragesView,
renderer: NonSendSync<UniqueView<Renderer>>
renderer: UniqueView<Renderer>
) {
let vert = renderer.device.create_buffer_init(
&wgpu::util::BufferInitDescriptor {

View file

@ -13,42 +13,41 @@ const SMOL: f32 = 0.0001;
pub fn render_selection_box() { }
#[cfg(fuck)]
pub fn render_selection_box(
lookat: View<LookingAtBlock>,
camera: View<Camera>,
mut target: NonSendSync<UniqueViewMut<RenderTarget>>,
program: NonSendSync<UniqueView<ColoredShaderPrefab>>,
buffers: UniqueView<CubePrimitive>,
) {
let camera = camera.iter().next().unwrap();
let Some(lookat) = lookat.iter().next() else { return };
let Some(lookat) = lookat.0 else { return };
// pub fn render_selection_box(
// lookat: View<LookingAtBlock>,
// camera: View<Camera>,
// mut target: NonSendSync<UniqueViewMut<RenderTarget>>,
// program: NonSendSync<UniqueView<ColoredShaderPrefab>>,
// buffers: UniqueView<CubePrimitive>,
// ) {
// let camera = camera.iter().next().unwrap();
// let Some(lookat) = lookat.iter().next() else { return };
// let Some(lookat) = lookat.0 else { return };
//Darken block
target.0.draw(
&buffers.0,
&buffers.1,
&program.0,
&uniform! {
color: [0., 0., 0., 0.5_f32],
model: Mat4::from_scale_rotation_translation(
Vec3::splat(1. + SMOL * 2.),
Quat::default(),
lookat.block_position.as_vec3() - Vec3::splat(SMOL)
).to_cols_array_2d(),
perspective: camera.perspective_matrix.to_cols_array_2d(),
view: camera.view_matrix.to_cols_array_2d(),
},
&DrawParameters {
backface_culling: BackfaceCullingMode::CullClockwise,
blend: Blend::alpha_blending(),
depth: Depth {
//this may be unreliable... unless scale is applied! hacky...
test: DepthTest::IfLessOrEqual,
..Default::default()
},
..Default::default()
}
).unwrap();
}
// //Darken block
// target.0.draw(
// &buffers.0,
// &buffers.1,
// &program.0,
// &uniform! {
// color: [0., 0., 0., 0.5_f32],
// model: Mat4::from_scale_rotation_translation(
// Vec3::splat(1. + SMOL * 2.),
// Quat::default(),
// lookat.block_position.as_vec3() - Vec3::splat(SMOL)
// ).to_cols_array_2d(),
// perspective: camera.perspective_matrix.to_cols_array_2d(),
// view: camera.view_matrix.to_cols_array_2d(),
// },
// &DrawParameters {
// backface_culling: BackfaceCullingMode::CullClockwise,
// blend: Blend::alpha_blending(),
// depth: Depth {
// //this may be unreliable... unless scale is applied! hacky...
// test: DepthTest::IfLessOrEqual,
// ..Default::default()
// },
// ..Default::default()
// }
// ).unwrap();
// }

View file

@ -31,7 +31,7 @@ macro_rules! build_shaders {
pub fn compile_shaders(
storages: AllStoragesView,
) {
let renderer = &storages.borrow::<NonSendSync<UniqueView<Renderer>>>().unwrap();
let renderer = &storages.borrow::<UniqueView<Renderer>>().unwrap();
storages.add_unique(build_shaders! {
Shaders [renderer, "../../shaders"] {
world: "world.wgsl",

View file

@ -1,5 +1,5 @@
use glam::{Vec3, Mat4, Quat, ivec3};
use shipyard::{NonSendSync, UniqueView, UniqueViewMut, View, IntoIter, track, Unique};
use shipyard::{NonSendSync, UniqueView, UniqueViewMut, View, IntoIter, track, Unique, AllStoragesView};
use wgpu::util::DeviceExt;
use crate::{
camera::Camera,
@ -12,7 +12,7 @@ use crate::{
chunk::CHUNK_SIZE,
}, settings::GameSettings,
};
use super::{RenderTarget, shaders::Shaders, Renderer};
use super::{Renderer, RenderTarget, shaders::Shaders, camera_uniform::CameraUniformBuffer};
#[repr(C, packed)]
#[derive(Clone, Copy, bytemuck::Pod, bytemuck::Zeroable)]
@ -20,181 +20,282 @@ pub struct ChunkVertex {
pub position: [f32; 3],
pub normal: [f32; 3],
pub uv: [f32; 2],
pub tex_index: u8,
pub tex_index: u32,
}
#[repr(C, packed)]
#[derive(Clone, Copy, bytemuck::Pod, bytemuck::Zeroable)]
#[derive(Clone, Copy, Default, bytemuck::Pod, bytemuck::Zeroable)]
struct WorldUniform {
position_offset: [f32; 3],
view_proj: [[f32; 4]; 4],
position: [f32; 3], //XXX: should use i32?
}
///private type
#[derive(Unique)]
pub struct GpuData {
pipeline: wgpu::RenderPipeline,
uniform_buffer: wgpu::Buffer,
bind_group: wgpu::BindGroup,
}
pub fn init_gpu_data(
storages: AllStoragesView,
) {
let renderer = storages.borrow::<UniqueView<Renderer>>().unwrap();
let shaders: UniqueView<'_, Shaders> = storages.borrow::<UniqueView<Shaders>>().unwrap();
let camera_uniform = storages.borrow::<UniqueView<CameraUniformBuffer>>().unwrap();
let pipeline = renderer.device.create_render_pipeline(&wgpu::RenderPipelineDescriptor {
label: Some("WorldRenderPipeline"),
layout: Some(&renderer.device.create_pipeline_layout(&wgpu::PipelineLayoutDescriptor {
label: Some("WorldRenderPipelineLayout"),
bind_group_layouts: &[],
push_constant_ranges: &[],
})),
vertex: wgpu::VertexState {
module: &shaders.world,
entry_point: "vs_main",
buffers: &[],
},
fragment: Some(wgpu::FragmentState {
module: &shaders.world,
entry_point: "fs_main",
targets: &[Some(wgpu::ColorTargetState {
format: renderer.config.format,
blend: Some(wgpu::BlendState::REPLACE),
write_mask: wgpu::ColorWrites::ALL,
})],
}),
primitive: wgpu::PrimitiveState {
topology: wgpu::PrimitiveTopology::TriangleList,
strip_index_format: None,
front_face: wgpu::FrontFace::Ccw,
cull_mode: Some(wgpu::Face::Back),
polygon_mode: wgpu::PolygonMode::Fill,
unclipped_depth: false,
conservative: false,
},
//TODO enable depth buffer
depth_stencil: None,
multisample: wgpu::MultisampleState::default(),
multiview: None,
});
let uniform_buffer = renderer.device.create_buffer_init(
&wgpu::util::BufferInitDescriptor {
label: Some("WorldUniformBuffer"),
contents: bytemuck::cast_slice(&[WorldUniform::default()]),
usage: wgpu::BufferUsages::UNIFORM | wgpu::BufferUsages::COPY_DST,
}
);
let bind_group_layout = renderer.device.create_bind_group_layout(&wgpu::BindGroupLayoutDescriptor {
entries: &[
wgpu::BindGroupLayoutEntry {
binding: 0,
visibility: wgpu::ShaderStages::VERTEX,
ty: wgpu::BindingType::Buffer {
ty: wgpu::BufferBindingType::Uniform,
has_dynamic_offset: false,
min_binding_size: None,
},
count: None,
},
wgpu::BindGroupLayoutEntry {
binding: 1,
visibility: wgpu::ShaderStages::VERTEX,
ty: wgpu::BindingType::Buffer {
ty: wgpu::BufferBindingType::Uniform,
has_dynamic_offset: false,
min_binding_size: None,
},
count: None,
}
],
label: Some("WorldBindGroupLayout"),
});
let bind_group = renderer.device.create_bind_group(&wgpu::BindGroupDescriptor {
layout: &bind_group_layout,
entries: &[
wgpu::BindGroupEntry {
binding: 0,
resource: camera_uniform.0.as_entire_binding(),
},
wgpu::BindGroupEntry {
binding: 1,
resource: uniform_buffer.as_entire_binding(),
}
],
label: Some("WorldBindGroup"),
});
storages.add_unique(GpuData { pipeline, uniform_buffer, bind_group });
}
pub fn draw_world(
renderer: UniqueView<Renderer>,
mut target: UniqueViewMut<RenderTarget>,
gpu_data: UniqueView<GpuData>,
chunks: UniqueView<ChunkStorage>,
meshes: UniqueView<ChunkMeshStorage>,
shaders: UniqueView<Shaders>,
texture: UniqueView<BlockTexturesAsset>,
camera: View<Camera>,
settings: UniqueView<GameSettings>
) {
let camera = camera.iter().next().expect("No cameras in the scene");
for (&position, chunk) in &chunks.chunks {
if let Some(key) = chunk.mesh_index {
let mesh = meshes.get(key).expect("Mesh index pointing to nothing");
let world_position = position.as_vec3() * CHUNK_SIZE as f32;
//TODO culling
//TODO culling like in the glium version
//Draw chunk mesh
//TODO: i need renderpass here!
}
}
}
#[cfg(fuck)]
pub fn draw_world(
mut target: NonSendSync<UniqueViewMut<RenderTarget>>,
chunks: UniqueView<ChunkStorage>,
meshes: NonSendSync<UniqueView<ChunkMeshStorage>>,
program: NonSendSync<UniqueView<ChunkShaderPrefab>>,
texture: NonSendSync<UniqueView<BlockTexturesAsset>>,
camera: View<Camera>,
settings: UniqueView<GameSettings>
) {
let camera = camera.iter().next().expect("No cameras in the scene");
let draw_parameters = DrawParameters {
depth: Depth {
test: DepthTest::IfLess,
write: true,
..Default::default()
},
multisampling: settings.msaa.is_some(),
polygon_mode: PolygonMode::Fill, //Change to Line for wireframe
backface_culling: BackfaceCullingMode::CullClockwise,
..Default::default()
};
let texture_sampler = Sampler(&texture.0, SamplerBehavior {
minify_filter: MinifySamplerFilter::LinearMipmapLinear,
magnify_filter: MagnifySamplerFilter::Nearest,
max_anisotropy: settings.max_anisotropy.unwrap_or_default(),
wrap_function: (SamplerWrapFunction::Clamp, SamplerWrapFunction::Clamp, SamplerWrapFunction::Clamp),
..Default::default()
});
let view = camera.view_matrix.to_cols_array_2d();
let perspective = camera.perspective_matrix.to_cols_array_2d();
for (&position, chunk) in &chunks.chunks {
if let Some(key) = chunk.mesh_index {
let mesh = meshes.get(key).expect("Mesh index pointing to nothing");
let world_position = position.as_vec3() * CHUNK_SIZE as f32;
// pub fn draw_world(
// mut target: NonSendSync<UniqueViewMut<RenderTarget>>,
// chunks: UniqueView<ChunkStorage>,
// meshes: NonSendSync<UniqueView<ChunkMeshStorage>>,
// program: NonSendSync<UniqueView<ChunkShaderPrefab>>,
// texture: NonSendSync<UniqueView<BlockTexturesAsset>>,
// camera: View<Camera>,
// settings: UniqueView<GameSettings>
// ) {
// let camera = camera.iter().next().expect("No cameras in the scene");
// let draw_parameters = DrawParameters {
// depth: Depth {
// test: DepthTest::IfLess,
// write: true,
// ..Default::default()
// },
// multisampling: settings.msaa.is_some(),
// polygon_mode: PolygonMode::Fill, //Change to Line for wireframe
// backface_culling: BackfaceCullingMode::CullClockwise,
// ..Default::default()
// };
// let texture_sampler = Sampler(&texture.0, SamplerBehavior {
// minify_filter: MinifySamplerFilter::LinearMipmapLinear,
// magnify_filter: MagnifySamplerFilter::Nearest,
// max_anisotropy: settings.max_anisotropy.unwrap_or_default(),
// wrap_function: (SamplerWrapFunction::Clamp, SamplerWrapFunction::Clamp, SamplerWrapFunction::Clamp),
// ..Default::default()
// });
// let view = camera.view_matrix.to_cols_array_2d();
// let perspective = camera.perspective_matrix.to_cols_array_2d();
// for (&position, chunk) in &chunks.chunks {
// if let Some(key) = chunk.mesh_index {
// let mesh = meshes.get(key).expect("Mesh index pointing to nothing");
// let world_position = position.as_vec3() * CHUNK_SIZE as f32;
//Skip mesh if its empty
if mesh.index_buffer.len() == 0 {
continue
}
// //Skip mesh if its empty
// if mesh.index_buffer.len() == 0 {
// continue
// }
//Frustum culling
{
let minp = world_position;
let maxp = world_position + Vec3::splat(CHUNK_SIZE as f32);
if !camera.frustum.is_box_visible(minp, maxp) {
continue
}
}
// //Frustum culling
// {
// let minp = world_position;
// let maxp = world_position + Vec3::splat(CHUNK_SIZE as f32);
// if !camera.frustum.is_box_visible(minp, maxp) {
// continue
// }
// }
//Draw chunk mesh
target.0.draw(
&mesh.vertex_buffer,
&mesh.index_buffer,
&program.0,
&uniform! {
position_offset: world_position.to_array(),
view: view,
perspective: perspective,
tex: texture_sampler,
},
&draw_parameters
).unwrap();
}
}
}
// //Draw chunk mesh
// target.0.draw(
// &mesh.vertex_buffer,
// &mesh.index_buffer,
// &program.0,
// &uniform! {
// position_offset: world_position.to_array(),
// view: view,
// perspective: perspective,
// tex: texture_sampler,
// },
// &draw_parameters
// ).unwrap();
// }
// }
// }
pub fn draw_current_chunk_border() {}
#[cfg(fuck)]
pub fn draw_current_chunk_border(
mut target: NonSendSync<UniqueViewMut<RenderTarget>>,
player: View<MainPlayer>,
transforms: View<Transform, track::All>,
buffers: UniqueView<CubePrimitive>,
program: NonSendSync<UniqueView<ColoredShaderPrefab>>,
camera: View<Camera>,
settings: UniqueView<GameSettings>,
) {
#[cfg(fuck)] {
if cfg!(target_os = "android") {
return
}
if !settings.debug_draw_current_chunk_border {
return
}
let camera = camera.iter().next().expect("No cameras in the scene");
let view = camera.view_matrix.to_cols_array_2d();
let perspective = camera.perspective_matrix.to_cols_array_2d();
let (_, &player_transform) = (&player, &transforms).iter().next().expect("No player");
let (_, _, player_position) = player_transform.0.to_scale_rotation_translation();
let player_in_chunk = ivec3(
(player_position.x as i32).div_euclid(CHUNK_SIZE as i32),
(player_position.y as i32).div_euclid(CHUNK_SIZE as i32),
(player_position.z as i32).div_euclid(CHUNK_SIZE as i32),
);
let world_position = player_in_chunk.as_vec3() * CHUNK_SIZE as f32;
target.0.draw(
&buffers.0,
&buffers.1,
&program.0,
&uniform! {
model: Mat4::from_scale_rotation_translation(
Vec3::splat(CHUNK_SIZE as f32),
Quat::default(),
world_position
).to_cols_array_2d(),
color: [0.25f32; 4],
view: view,
perspective: perspective,
},
&DrawParameters {
depth: Depth {
test: DepthTest::IfLess,
..Default::default()
},
blend: Blend::alpha_blending(),
..Default::default()
}
).unwrap();
target.0.draw(
&buffers.0,
&buffers.1,
&program.0,
&uniform! {
model: Mat4::from_scale_rotation_translation(
Vec3::splat(CHUNK_SIZE as f32),
Quat::default(),
world_position
).to_cols_array_2d(),
color: [0.0f32; 4],
view: view,
perspective: perspective,
},
&DrawParameters {
polygon_mode: PolygonMode::Point,
line_width: Some(2.),
point_size: Some(5.),
..Default::default()
}
).unwrap();
}
}
// pub fn draw_current_chunk_border(
// mut target: NonSendSync<UniqueViewMut<RenderTarget>>,
// player: View<MainPlayer>,
// transforms: View<Transform, track::All>,
// buffers: UniqueView<CubePrimitive>,
// program: NonSendSync<UniqueView<ColoredShaderPrefab>>,
// camera: View<Camera>,
// settings: UniqueView<GameSettings>,
// ) {
// #[cfg(fuck)] {
// if cfg!(target_os = "android") {
// return
// }
// if !settings.debug_draw_current_chunk_border {
// return
// }
// let camera = camera.iter().next().expect("No cameras in the scene");
// let view = camera.view_matrix.to_cols_array_2d();
// let perspective = camera.perspective_matrix.to_cols_array_2d();
// let (_, &player_transform) = (&player, &transforms).iter().next().expect("No player");
// let (_, _, player_position) = player_transform.0.to_scale_rotation_translation();
// let player_in_chunk = ivec3(
// (player_position.x as i32).div_euclid(CHUNK_SIZE as i32),
// (player_position.y as i32).div_euclid(CHUNK_SIZE as i32),
// (player_position.z as i32).div_euclid(CHUNK_SIZE as i32),
// );
// let world_position = player_in_chunk.as_vec3() * CHUNK_SIZE as f32;
// target.0.draw(
// &buffers.0,
// &buffers.1,
// &program.0,
// &uniform! {
// model: Mat4::from_scale_rotation_translation(
// Vec3::splat(CHUNK_SIZE as f32),
// Quat::default(),
// world_position
// ).to_cols_array_2d(),
// color: [0.25f32; 4],
// view: view,
// perspective: perspective,
// },
// &DrawParameters {
// depth: Depth {
// test: DepthTest::IfLess,
// ..Default::default()
// },
// blend: Blend::alpha_blending(),
// ..Default::default()
// }
// ).unwrap();
// target.0.draw(
// &buffers.0,
// &buffers.1,
// &program.0,
// &uniform! {
// model: Mat4::from_scale_rotation_translation(
// Vec3::splat(CHUNK_SIZE as f32),
// Quat::default(),
// world_position
// ).to_cols_array_2d(),
// color: [0.0f32; 4],
// view: view,
// perspective: perspective,
// },
// &DrawParameters {
// polygon_mode: PolygonMode::Point,
// line_width: Some(2.),
// point_size: Some(5.),
// ..Default::default()
// }
// ).unwrap();
// }
// }

View file

@ -91,7 +91,7 @@ pub fn update_chunks_if_player_moved(
fn unload_downgrade_chunks(
mut vm_world: UniqueViewMut<ChunkStorage>,
mut vm_meshes: NonSendSync<UniqueViewMut<ChunkMeshStorage>>
mut vm_meshes: UniqueViewMut<ChunkMeshStorage>
) {
if !vm_world.is_modified() {
return
@ -184,8 +184,8 @@ fn start_required_tasks(
fn process_completed_tasks(
task_manager: UniqueView<ChunkTaskManager>,
mut world: UniqueViewMut<ChunkStorage>,
mut meshes: NonSendSync<UniqueViewMut<ChunkMeshStorage>>,
renderer: NonSendSync<UniqueView<Renderer>>,
mut meshes: UniqueViewMut<ChunkMeshStorage>,
renderer: UniqueView<Renderer>,
state: UniqueView<GameState>,
mut queue: UniqueViewMut<BlockUpdateQueue>,
) {

View file

@ -65,22 +65,22 @@ pub fn generate_mesh(data: MeshGenData) -> (Vec<ChunkVertex>, Vec<u32>) {
CubeFace::Back => textures.back,
CubeFace::Bottom => textures.bottom,
};
builder.add_face(face, coord, face_texture as u8);
builder.add_face(face, coord, face_texture as u32);
}
}
},
RenderType::CrossShape(textures) => {
builder.add_diagonal_face(
coord,
DiagonalFace::LeftZ,
textures.0.front as u8,
textures.0.back as u8
coord,
DiagonalFace::LeftZ,
textures.0.front as u32,
textures.0.back as u32
);
builder.add_diagonal_face(
coord,
coord,
DiagonalFace::RigthZ,
textures.1.front as u8,
textures.1.back as u8
textures.1.front as u32,
textures.1.back as u32
);
},
}

View file

@ -96,7 +96,7 @@ impl MeshBuilder {
Self::default()
}
pub fn add_face(&mut self, face: CubeFace, coord: IVec3, texture: u8) {
pub fn add_face(&mut self, face: CubeFace, coord: IVec3, texture: u32) {
let coord = coord.as_vec3();
let face_index = face as usize;
@ -120,7 +120,7 @@ impl MeshBuilder {
self.idx_counter += 4;
}
pub fn add_diagonal_face(&mut self, coord: IVec3, face_type: DiagonalFace, front_texture: u8, back_texture: u8) {
pub fn add_diagonal_face(&mut self, coord: IVec3, face_type: DiagonalFace, front_texture: u32, back_texture: u32) {
//Push vertices
let face_type = face_type as usize;
let vertices = CROSS_FACES[face_type];