diff --git a/kubi/shaders/gui/progressbar.frag b/kubi/shaders/gui/progressbar.frag deleted file mode 100644 index e598692..0000000 --- a/kubi/shaders/gui/progressbar.frag +++ /dev/null @@ -1,17 +0,0 @@ -#version 300 es - -precision highp float; - -in vec2 v_uv; -out vec4 out_color; -uniform float progress; -uniform vec4 color; -uniform vec4 bg_color; - -void main() { - if (v_uv.x <= progress) { - out_color = color; - } else { - out_color = bg_color; - } -} diff --git a/kubi/shaders/gui/progressbar.vert b/kubi/shaders/gui/progressbar.vert deleted file mode 100644 index 2b43f0c..0000000 --- a/kubi/shaders/gui/progressbar.vert +++ /dev/null @@ -1,12 +0,0 @@ -#version 300 es - -in vec2 position; -out vec2 v_uv; -uniform mat4 ui_view; -uniform mat3 transform; - -void main() { - v_uv = position; - vec2 transformed = (transform * vec3(position, 1.)).xy; - gl_Position = ui_view * vec4(transformed, 0., 1.); -} diff --git a/kubi/src/prefabs.rs b/kubi/src/assets.rs similarity index 83% rename from kubi/src/prefabs.rs rename to kubi/src/assets.rs index f44598c..6a75a51 100644 --- a/kubi/src/prefabs.rs +++ b/kubi/src/assets.rs @@ -5,7 +5,7 @@ use crate::rendering::Renderer; mod texture; mod shaders; -use texture::load_texture2darray_prefab; +use texture::load_asset_texture_array; use shaders::include_shader_prefab; pub trait AssetPaths { @@ -57,11 +57,7 @@ pub fn load_prefabs( ) { log::info!("Loading textures..."); storages.add_unique_non_send_sync(BlockTexturesPrefab( - load_texture2darray_prefab::( - "blocks".into(), - &renderer.display, - MipmapsOption::AutoGeneratedMipmaps - ) + load_asset_texture_array::("blocks".into(), &renderer) )); log::info!("Compiling shaders..."); @@ -81,13 +77,5 @@ pub fn load_prefabs( &renderer.display ) )); - storages.add_unique_non_send_sync(ProgressbarShaderPrefab( - include_shader_prefab!( - "gui/progressbar", - "../shaders/gui/progressbar.vert", - "../shaders/gui/progressbar.frag", - &renderer.display - ) - )); renderer.display.release_shader_compiler(); } diff --git a/kubi/src/prefabs/shaders.rs b/kubi/src/assets/shaders.rs similarity index 100% rename from kubi/src/prefabs/shaders.rs rename to kubi/src/assets/shaders.rs diff --git a/kubi/src/assets/texture.rs b/kubi/src/assets/texture.rs new file mode 100644 index 0000000..33cf932 --- /dev/null +++ b/kubi/src/assets/texture.rs @@ -0,0 +1,109 @@ +use glam::UVec2; +use strum::IntoEnumIterator; +use rayon::prelude::*; +use std::{path::PathBuf, io::BufReader, sync::Mutex, num::NonZeroU32}; +use crate::{filesystem::open_asset, rendering::Renderer}; +use super::AssetPaths; + +pub fn load_asset_texture_array< + T: AssetPaths + IntoEnumIterator, +>( + directory: PathBuf, + renderer: &Renderer, +) -> wgpu::Texture { + log::info!("started loading texture array from: \"{}\"", directory.as_os_str().to_str().unwrap()); + + //Load raw images + let (texture_data, texture_dimensions): (Vec>, UVec2) = { + //Image dimensions + //Mutex is required to ensure exact size, without extra temporary allocations + let img_dim: Mutex> = Mutex::new(None); + + //Get image file names into a Vec (because par_iter can't be called directly on IntoEnumIterator::iter()) + let file_names: Vec<&'static str> = T::iter().map(|x| x.file_name()).collect(); + + //Load data in parallel + let raw_images: Vec> = file_names.par_iter().map(|&file_name| { + log::info!("loading texture \"{file_name}\"..."); + + //Get path to the image and open the file + let reader = { + let path = directory.join(file_name); + BufReader::new(open_asset(&path).expect("Failed to open texture file")) + }; + + //Load and parse image data + let image = image::load( + reader, + image::ImageFormat::Png + ).unwrap().to_rgba8(); + + //Get image dimensions + let dimensions = image.dimensions(); + let dim_nonzero = ( + NonZeroU32::new(dimensions.0).expect("image dimensions must be non-zero"), + NonZeroU32::new(dimensions.1).expect("image dimensions must be non-zero") + ); + + //Ensure same size (skip if poisoned) + if !img_dim.is_poisoned() { + let img_dim = img_dim.lock().unwrap(); + if let Some(current_size) = img_dim.replace(dim_nonzero) { + assert!(dim_nonzero == current_size, "image dimensions do not match"); + } + } + + image.into_raw() + }).collect(); + + //Lock for the final time and retrieve the dimensions + let img_dim = img_dim.lock().unwrap().expect("No images were loaded").clone(); + let img_dim_vec = UVec2::new(img_dim.0.get(), img_dim.1.get()); + + (raw_images, img_dim_vec) + }; + + //Flatten the texture data + let texture_data_flat = texture_data.concat(); + + log::info!("done loading texture files, uploading to the gpu"); + + let texture_extent = wgpu::Extent3d { + width: texture_dimensions.x, + height: texture_dimensions.y, + depth_or_array_layers: texture_data.len() as u32, + }; + + //Create a wgpu texture + let texture_handle = renderer.device.create_texture( + &wgpu::TextureDescriptor { + size: texture_extent, + mip_level_count: 1, + sample_count: 1, + dimension: wgpu::TextureDimension::D2, ///XXX: is this supposed to be D2 for array tex.? + format: wgpu::TextureFormat::Rgba8UnormSrgb, + usage: wgpu::TextureUsages::TEXTURE_BINDING | wgpu::TextureUsages::COPY_DST, + label: Some("diffuse_texture"), + view_formats: &[], + } + ); + + //Upload texture data + renderer.queue.write_texture( + wgpu::ImageCopyTexture { + texture: &texture_handle, + mip_level: 0, + origin: wgpu::Origin3d::ZERO, + aspect: wgpu::TextureAspect::All, + }, + &texture_data_flat, + wgpu::ImageDataLayout { + offset: 0, + bytes_per_row: Some(4 * texture_dimensions.x), + rows_per_image: Some(texture_dimensions.y), + }, + texture_extent, + ); + + texture_handle +} diff --git a/kubi/src/gui/progressbar.rs b/kubi/src/gui/progressbar.rs index 8d155cf..af04b45 100644 --- a/kubi/src/gui/progressbar.rs +++ b/kubi/src/gui/progressbar.rs @@ -1,6 +1,6 @@ use shipyard::{UniqueView, UniqueViewMut, NonSendSync, View, Component, IntoIter, IntoWithId, Get, track}; use crate::{ - prefabs::ProgressbarShaderPrefab, + assets::ProgressbarShaderPrefab, rendering::{ RenderTarget, primitives::rect::RectPrimitive diff --git a/kubi/src/lib.rs b/kubi/src/lib.rs index ea235d4..db6c077 100644 --- a/kubi/src/lib.rs +++ b/kubi/src/lib.rs @@ -18,7 +18,7 @@ pub use kubi_shared::transform; pub(crate) mod rendering; pub(crate) mod world; pub(crate) mod player; -pub(crate) mod prefabs; +pub(crate) mod assets; pub(crate) mod settings; pub(crate) mod camera; pub(crate) mod events; @@ -48,7 +48,7 @@ use world::{ tasks::ChunkTaskManager, }; use player::{spawn_player, MainPlayer}; -use prefabs::load_prefabs; +use assets::load_prefabs; use settings::{load_settings, GameSettings}; use camera::compute_cameras; use events::{ diff --git a/kubi/src/prefabs/texture.rs b/kubi/src/prefabs/texture.rs deleted file mode 100644 index 6107ffc..0000000 --- a/kubi/src/prefabs/texture.rs +++ /dev/null @@ -1,44 +0,0 @@ -use strum::IntoEnumIterator; -use rayon::prelude::*; -use std::{path::PathBuf, io::BufReader}; -use crate::filesystem::open_asset; -use super::AssetPaths; - -pub fn load_texture2darray_prefab< - T: AssetPaths + IntoEnumIterator, - E: Facade ->( - directory: PathBuf, - facade: &E, - mipmaps: MipmapsOption, -) -> SrgbTexture2dArray { - log::info!("started loading {}", directory.as_os_str().to_str().unwrap()); - //Load raw images - let tex_files: Vec<&'static str> = T::iter().map(|x| x.file_name()).collect(); - let raw_images: Vec> = tex_files.par_iter().map(|&file_name| { - log::info!("loading texture {}", file_name); - //Get path to the image and open the file - let reader = { - let path = directory.join(file_name); - BufReader::new(open_asset(&path).expect("Failed to open texture file")) - }; - //Parse image data - let (image_data, dimensions) = { - let image = image::load( - reader, - image::ImageFormat::Png - ).unwrap().to_rgba8(); - let dimensions = image.dimensions(); - (image.into_raw(), dimensions) - }; - //Create a glium RawImage - RawImage2d::from_raw_rgba_reversed( - &image_data, - dimensions - ) - }).collect(); - log::info!("done loading texture files, uploading to the gpu"); - //Upload images to the GPU - SrgbTexture2dArray::with_mipmaps(facade, raw_images, mipmaps) - .expect("Failed to upload texture array to GPU") -} diff --git a/kubi/src/rendering/entities.rs b/kubi/src/rendering/entities.rs index d408c8c..0bdebde 100644 --- a/kubi/src/rendering/entities.rs +++ b/kubi/src/rendering/entities.rs @@ -1,7 +1,7 @@ use shipyard::{NonSendSync, UniqueViewMut, UniqueView, View, IntoIter, IntoWithId}; use kubi_shared::{entity::Entity, transform::Transform}; use crate::{ - prefabs::ColoredShaderPrefab, + assets::ColoredShaderPrefab, camera::Camera, settings::GameSettings }; diff --git a/kubi/src/rendering/selection_box.rs b/kubi/src/rendering/selection_box.rs index c6e8586..a96992b 100644 --- a/kubi/src/rendering/selection_box.rs +++ b/kubi/src/rendering/selection_box.rs @@ -10,7 +10,7 @@ use glium::{ use crate::{ world::raycast::LookingAtBlock, camera::Camera, - prefabs::ColoredShaderPrefab + assets::ColoredShaderPrefab }; use super::{ RenderTarget, diff --git a/kubi/src/rendering/world.rs b/kubi/src/rendering/world.rs index 29227c5..ff58252 100644 --- a/kubi/src/rendering/world.rs +++ b/kubi/src/rendering/world.rs @@ -4,7 +4,7 @@ use crate::{ camera::Camera, player::MainPlayer, transform::Transform, - prefabs::{ + assets::{ ChunkShaderPrefab, BlockTexturesPrefab, ColoredShaderPrefab,