use smallvec::SmallVec;
use utils::Extent;
use crate::{
rt, AttachmentInformation, BaseBufferHandle, BaseImageHandle, BufferCopyDescriptor, BufferDescriptor, BufferHandle,
BufferImageCopyDescriptor, ClearValue, DescriptorSetHandle, DispatchExtent, FrameKey, ImageBufferCopyDescriptor, Layouts,
MeshHandle, PipelineHandle, RGBAu8, SynchronizerHandle, TextureCopyHandle,
};
pub struct DebugLabelWriter {
bytes: SmallVec<[u8; 128]>,
}
impl DebugLabelWriter {
pub fn new() -> Self {
Self { bytes: SmallVec::new() }
}
pub fn as_str(&self) -> &str {
std::str::from_utf8(&self.bytes).expect("Invalid debug label. The label writer most likely received non UTF-8 bytes.")
}
pub fn write_str(&mut self, s: &str) -> std::fmt::Result {
self.bytes.extend_from_slice(s.as_bytes());
Ok(())
}
pub fn null_terminate(&mut self) {
self.bytes.push(0);
}
pub fn as_bytes(&self) -> &[u8] {
&self.bytes
}
}
impl Default for DebugLabelWriter {
fn default() -> Self {
Self::new()
}
}
impl std::fmt::Write for DebugLabelWriter {
fn write_str(&mut self, s: &str) -> std::fmt::Result {
self.write_str(s)
}
}
pub trait CommandBuffer {
fn create_command_buffer_recording(&mut self) -> impl CommandBufferRecording + CommonCommandBufferMode;
}
pub trait CommandBufferRecording
where
Self: Sized,
{
fn frame_key(&self) -> FrameKey;
fn build_top_level_acceleration_structure(&mut self, acceleration_structure_build: &rt::TopLevelAccelerationStructureBuild);
fn build_bottom_level_acceleration_structures(
&mut self,
acceleration_structure_builds: &[rt::BottomLevelAccelerationStructureBuild],
);
fn start_render_pass(
&mut self,
extent: Extent,
attachments: &[AttachmentInformation],
) -> &mut impl RasterizationRenderPassMode;
fn clear_images(&mut self, textures: &[(BaseImageHandle, ClearValue)]);
fn clear_buffers(&mut self, buffer_handles: &[BaseBufferHandle]);
fn copy_buffers(&mut self, copies: &[BufferCopyDescriptor]);
fn copy_buffer_to_images(&mut self, copies: &[BufferImageCopyDescriptor]);
fn copy_images_to_buffer(&mut self, copies: &[ImageBufferCopyDescriptor]);
fn sync_buffer(&mut self, buffer_handle: impl Into<BaseBufferHandle>);
fn transfer_textures(&mut self, texture_handles: &[BaseImageHandle]) -> Vec<TextureCopyHandle>;
fn write_image_data(&mut self, image_handle: BaseImageHandle, data: &[RGBAu8]);
fn blit_image(
&mut self,
source_image: BaseImageHandle,
source_layout: Layouts,
destination_image: BaseImageHandle,
destination_layout: Layouts,
);
fn execute(self, synchronizer: SynchronizerHandle);
}
pub trait CommonCommandBufferMode {
fn bind_compute_pipeline(&mut self, pipeline_handle: PipelineHandle) -> &mut impl BoundComputePipelineMode;
fn bind_ray_tracing_pipeline(&mut self, pipeline_handle: PipelineHandle) -> &mut impl BoundRayTracingPipelineMode;
fn start_region(&self, write_label: impl FnOnce(&mut DebugLabelWriter) -> std::fmt::Result);
fn end_region(&self);
fn region(&mut self, write_label: impl FnOnce(&mut DebugLabelWriter) -> std::fmt::Result, f: impl FnOnce(&mut Self));
}
pub trait RasterizationRenderPassMode: CommonCommandBufferMode {
fn bind_raster_pipeline(&mut self, pipeline_handle: PipelineHandle) -> &mut impl BoundRasterizationPipelineMode;
fn bind_vertex_buffers(&mut self, buffer_descriptors: &[BufferDescriptor]);
fn bind_index_buffer(&mut self, buffer_descriptor: &BufferDescriptor);
fn end_render_pass(&mut self);
}
pub trait BoundPipelineLayoutMode: CommonCommandBufferMode {
fn bind_descriptor_sets(&mut self, sets: &[DescriptorSetHandle]) -> &mut Self;
fn write_push_constant<T: Copy + 'static>(&mut self, offset: u32, data: T)
where
[(); std::mem::size_of::<T>()]: Sized;
}
pub trait BoundRasterizationPipelineMode: BoundPipelineLayoutMode + RasterizationRenderPassMode {
fn draw_mesh(&mut self, mesh_handle: &MeshHandle);
fn draw(&mut self, vertex_count: u32, instance_count: u32, first_vertex: u32, first_instance: u32);
fn draw_indexed(
&mut self,
index_count: u32,
instance_count: u32,
first_index: u32,
vertex_offset: i32,
first_instance: u32,
);
fn dispatch_meshes(&mut self, x: u32, y: u32, z: u32);
}
pub trait BoundComputePipelineMode: BoundPipelineLayoutMode + CommandBufferRecording {
fn dispatch(&mut self, dispatch: DispatchExtent);
fn indirect_dispatch<const N: usize>(&mut self, buffer: BufferHandle<[[u32; 4]; N]>, entry_index: usize);
}
pub trait BoundRayTracingPipelineMode: BoundPipelineLayoutMode + CommandBufferRecording {
fn trace_rays(&mut self, binding_tables: rt::BindingTables, x: u32, y: u32, z: u32);
}
pub enum CommandBufferType {
GRAPHICS,
COMPUTE,
TRANSFER,
}