use crate::action::*;
use metal;
#[derive(Clone)]
pub enum RenderTarget {
Texture {
texture: metal::Texture,
width: usize,
height: usize
},
Multisampled {
samples: metal::Texture,
resolved: Option<metal::Texture>,
width: usize,
height: usize
}
}
impl RenderTarget {
pub fn new(device: &metal::Device, width: usize, height: usize, render_target_type: RenderTargetType) -> RenderTarget {
let texture_descriptor = metal::TextureDescriptor::new();
texture_descriptor.set_texture_type(metal::MTLTextureType::D2);
texture_descriptor.set_width(width as u64);
texture_descriptor.set_height(height as u64);
texture_descriptor.set_pixel_format(metal::MTLPixelFormat::BGRA8Unorm);
texture_descriptor.set_usage(metal::MTLTextureUsage::RenderTarget | metal::MTLTextureUsage::ShaderRead);
match render_target_type {
RenderTargetType::Standard => { }
RenderTargetType::StandardForReading => {
texture_descriptor.set_pixel_format(metal::MTLPixelFormat::RGBA8Unorm);
}
RenderTargetType::Multisampled |
RenderTargetType::MultisampledTexture => {
texture_descriptor.set_texture_type(metal::MTLTextureType::D2Multisample);
texture_descriptor.set_sample_count(4);
texture_descriptor.set_storage_mode(metal::MTLStorageMode::Private);
}
RenderTargetType::Monochrome => {
texture_descriptor.set_pixel_format(metal::MTLPixelFormat::R8Unorm);
}
RenderTargetType::MonochromeMultisampledTexture => {
texture_descriptor.set_texture_type(metal::MTLTextureType::D2Multisample);
texture_descriptor.set_pixel_format(metal::MTLPixelFormat::R8Unorm);
texture_descriptor.set_sample_count(4);
texture_descriptor.set_storage_mode(metal::MTLStorageMode::Private);
}
}
let render_texture = device.new_texture(&texture_descriptor);
match render_target_type {
RenderTargetType::Standard | RenderTargetType::StandardForReading | RenderTargetType::Monochrome => {
RenderTarget::Texture {
texture: render_texture,
width: width,
height: height
}
},
RenderTargetType::Multisampled | RenderTargetType::MultisampledTexture => {
RenderTarget::Multisampled {
samples: render_texture,
resolved: None,
width: width,
height: height
}
}
RenderTargetType::MonochromeMultisampledTexture => {
RenderTarget::Multisampled {
samples: render_texture,
resolved: None,
width: width,
height: height
}
}
}
}
pub fn size(&self) -> (usize, usize) {
match self {
RenderTarget::Texture { texture: _, width, height } => (*width, *height),
RenderTarget::Multisampled { samples: _, resolved: _, width, height } => (*width, *height)
}
}
pub fn render_texture(&self) -> &metal::Texture {
match self {
RenderTarget::Texture { texture, width: _, height: _ } => texture,
RenderTarget::Multisampled { samples, resolved: _, width: _, height: _ } => samples
}
}
pub fn is_multisampled(&self) -> bool {
match self {
RenderTarget::Texture { texture: _, width: _, height: _ } => false,
RenderTarget::Multisampled { samples: _, width: _, height: _, resolved: _ } => true
}
}
}