aboutsummaryrefslogtreecommitdiff
path: root/stockton-render/src/draw/buffers/dedicated_image.rs
diff options
context:
space:
mode:
Diffstat (limited to 'stockton-render/src/draw/buffers/dedicated_image.rs')
-rw-r--r--stockton-render/src/draw/buffers/dedicated_image.rs199
1 files changed, 4 insertions, 195 deletions
diff --git a/stockton-render/src/draw/buffers/dedicated_image.rs b/stockton-render/src/draw/buffers/dedicated_image.rs
index 38a23c9..878d304 100644
--- a/stockton-render/src/draw/buffers/dedicated_image.rs
+++ b/stockton-render/src/draw/buffers/dedicated_image.rs
@@ -1,18 +1,16 @@
//! A dedicated image. Used for depth buffers.
-use super::create_buffer;
-use crate::draw::texture::{LoadableImage, PIXEL_SIZE};
+use crate::draw::texture::PIXEL_SIZE;
use crate::types::*;
-use std::{array::IntoIter, convert::TryInto, iter::empty, mem::ManuallyDrop};
+use std::mem::ManuallyDrop;
use anyhow::{Context, Result};
use hal::{
- buffer::Usage as BufUsage,
- format::{Aspects, Format, Swizzle},
+ format::{Format, Swizzle},
image::{SubresourceRange, Usage, Usage as ImgUsage, ViewKind},
memory,
- memory::{Properties, Segment},
+ memory::Properties,
MemoryTypeId,
};
use thiserror::Error;
@@ -122,195 +120,6 @@ impl DedicatedLoadedImage {
})
}
- /// Load the given image
- pub fn load<T: LoadableImage>(
- &mut self,
- img: T,
- device: &mut DeviceT,
- adapter: &Adapter,
- command_queue: &mut QueueT,
- command_pool: &mut CommandPoolT,
- ) -> Result<()> {
- let initial_row_size = PIXEL_SIZE * img.width() as usize;
- let limits = adapter.physical_device.properties().limits;
- let row_alignment_mask = limits.optimal_buffer_copy_pitch_alignment as u32 - 1;
-
- let row_size =
- ((initial_row_size as u32 + row_alignment_mask) & !row_alignment_mask) as usize;
- let total_size = (row_size * (img.height() as usize)) as u64;
- debug_assert!(row_size as usize >= initial_row_size);
-
- // Make a staging buffer
- let (staging_buffer, mut staging_memory) = create_buffer(
- device,
- adapter,
- BufUsage::TRANSFER_SRC,
- memory::Properties::CPU_VISIBLE | memory::Properties::COHERENT,
- total_size,
- )
- .context("Error creating staging buffer")?;
-
- // Copy everything into it
- unsafe {
- let mapped_memory: *mut u8 = std::mem::transmute(
- device
- .map_memory(
- &mut staging_memory,
- Segment {
- offset: 0,
- size: None,
- },
- )
- .context("Error mapping staging memory")?,
- );
-
- for y in 0..img.height() as usize {
- let dest_base: isize = (y * row_size).try_into()?;
- img.copy_row(y as u32, mapped_memory.offset(dest_base));
- }
-
- device.unmap_memory(&mut staging_memory);
- }
-
- // Copy from staging to image memory
- let buf = unsafe {
- use hal::command::{BufferImageCopy, CommandBufferFlags};
- use hal::image::{Access, Extent, Layout, Offset, SubresourceLayers};
- use hal::memory::Barrier;
- use hal::pso::PipelineStage;
-
- // Get a command buffer
- let mut buf = command_pool.allocate_one(hal::command::Level::Primary);
- buf.begin_primary(CommandBufferFlags::ONE_TIME_SUBMIT);
-
- // Setup the layout of our image for copying
- let image_barrier = Barrier::Image {
- states: (Access::empty(), Layout::Undefined)
- ..(Access::TRANSFER_WRITE, Layout::TransferDstOptimal),
- target: &(*self.image),
- families: None,
- range: SubresourceRange {
- aspects: Aspects::COLOR,
- level_start: 0,
- level_count: Some(1),
- layer_start: 0,
- layer_count: Some(1),
- },
- };
- buf.pipeline_barrier(
- PipelineStage::TOP_OF_PIPE..PipelineStage::TRANSFER,
- memory::Dependencies::empty(),
- IntoIter::new([image_barrier]),
- );
-
- // Copy from buffer to image
- buf.copy_buffer_to_image(
- &staging_buffer,
- &(*self.image),
- Layout::TransferDstOptimal,
- IntoIter::new([BufferImageCopy {
- buffer_offset: 0,
- buffer_width: (row_size / PIXEL_SIZE) as u32,
- buffer_height: img.height(),
- image_layers: SubresourceLayers {
- aspects: Aspects::COLOR,
- level: 0,
- layers: 0..1,
- },
- image_offset: Offset { x: 0, y: 0, z: 0 },
- image_extent: Extent {
- width: img.width(),
- height: img.height(),
- depth: 1,
- },
- }]),
- );
-
- // Setup the layout of our image for shaders
- let image_barrier = Barrier::Image {
- states: (Access::TRANSFER_WRITE, Layout::TransferDstOptimal)
- ..(Access::SHADER_READ, Layout::ShaderReadOnlyOptimal),
- target: &(*self.image),
- families: None,
- range: SubresourceRange {
- aspects: Aspects::COLOR,
- level_start: 0,
- level_count: Some(1),
- layer_start: 0,
- layer_count: Some(1),
- },
- };
-
- buf.pipeline_barrier(
- PipelineStage::TRANSFER..PipelineStage::FRAGMENT_SHADER,
- memory::Dependencies::empty(),
- IntoIter::new([image_barrier]),
- );
-
- buf.finish();
-
- buf
- };
-
- // Submit our commands and wait for them to finish
- unsafe {
- let mut setup_finished = device
- .create_fence(false)
- .context("Error creating setup_finished fence")?;
- command_queue.submit(
- IntoIter::new([&buf]),
- empty(),
- empty(),
- Some(&mut setup_finished),
- );
-
- device
- .wait_for_fence(&setup_finished, core::u64::MAX)
- .context("Error waiting for image load to finish")?;
- device.destroy_fence(setup_finished);
- };
-
- // Clean up temp resources
- unsafe {
- command_pool.free(std::iter::once(buf));
-
- device.free_memory(staging_memory);
- device.destroy_buffer(staging_buffer);
- }
-
- Ok(())
- }
-
- /// Load the given image into a new buffer
- pub fn load_into_new<T: LoadableImage>(
- img: T,
- device: &mut DeviceT,
- adapter: &Adapter,
- command_queue: &mut QueueT,
- command_pool: &mut CommandPoolT,
- format: Format,
- usage: Usage,
- ) -> Result<DedicatedLoadedImage> {
- let mut loaded_image = Self::new(
- device,
- adapter,
- format,
- usage | Usage::TRANSFER_DST,
- SubresourceRange {
- aspects: Aspects::COLOR,
- level_start: 0,
- level_count: Some(1),
- layer_start: 0,
- layer_count: Some(1),
- },
- img.width() as usize,
- img.height() as usize,
- )?;
- loaded_image.load(img, device, adapter, command_queue, command_pool)?;
-
- Ok(loaded_image)
- }
-
/// Properly frees/destroys all the objects in this struct
/// Dropping without doing this is a bad idea
pub fn deactivate(self, device: &mut DeviceT) {