d3d12: upload shaders
This commit is contained in:
parent
53e3732a93
commit
c2bef7f985
|
@ -220,30 +220,29 @@ impl FilterChainD3D11 {
|
||||||
passes: Vec<ShaderPassMeta>,
|
passes: Vec<ShaderPassMeta>,
|
||||||
semantics: &ShaderSemantics,
|
semantics: &ShaderSemantics,
|
||||||
) -> error::Result<Vec<FilterPass>> {
|
) -> error::Result<Vec<FilterPass>> {
|
||||||
// let mut filters = Vec::new();
|
|
||||||
let mut filters = Vec::new();
|
let mut filters = Vec::new();
|
||||||
|
|
||||||
for (index, (config, source, mut reflect)) in passes.into_iter().enumerate() {
|
for (index, (config, source, mut reflect)) in passes.into_iter().enumerate() {
|
||||||
let reflection = reflect.reflect(index, semantics)?;
|
let reflection = reflect.reflect(index, semantics)?;
|
||||||
let hlsl = reflect.compile(None)?;
|
let hlsl = reflect.compile(None)?;
|
||||||
|
|
||||||
let vertex_dxil =
|
let vertex_dxbc =
|
||||||
util::d3d_compile_shader(hlsl.vertex.as_bytes(), b"main\0", b"vs_5_0\0")?;
|
util::d3d_compile_shader(hlsl.vertex.as_bytes(), b"main\0", b"vs_5_0\0")?;
|
||||||
let vs = d3d11_compile_bound_shader(
|
let vs = d3d11_compile_bound_shader(
|
||||||
device,
|
device,
|
||||||
&vertex_dxil,
|
&vertex_dxbc,
|
||||||
None,
|
None,
|
||||||
ID3D11Device::CreateVertexShader,
|
ID3D11Device::CreateVertexShader,
|
||||||
)?;
|
)?;
|
||||||
|
|
||||||
let ia_desc = DrawQuad::get_spirv_cross_vbo_desc();
|
let ia_desc = DrawQuad::get_spirv_cross_vbo_desc();
|
||||||
let vao = util::d3d11_create_input_layout(device, &ia_desc, &vertex_dxil)?;
|
let vao = util::d3d11_create_input_layout(device, &ia_desc, &vertex_dxbc)?;
|
||||||
|
|
||||||
let fragment_dxil =
|
let fragment_dxbc =
|
||||||
util::d3d_compile_shader(hlsl.fragment.as_bytes(), b"main\0", b"ps_5_0\0")?;
|
util::d3d_compile_shader(hlsl.fragment.as_bytes(), b"main\0", b"ps_5_0\0")?;
|
||||||
let ps = d3d11_compile_bound_shader(
|
let ps = d3d11_compile_bound_shader(
|
||||||
device,
|
device,
|
||||||
&fragment_dxil,
|
&fragment_dxbc,
|
||||||
None,
|
None,
|
||||||
ID3D11Device::CreatePixelShader,
|
ID3D11Device::CreatePixelShader,
|
||||||
)?;
|
)?;
|
||||||
|
|
|
@ -126,6 +126,7 @@ pub fn d3d_compile_shader(source: &[u8], entry: &[u8], version: &[u8]) -> error:
|
||||||
None,
|
None,
|
||||||
)?;
|
)?;
|
||||||
|
|
||||||
|
// SAFETY: if D3DCompile succeeds then blob is Some
|
||||||
Ok(blob.unwrap())
|
Ok(blob.unwrap())
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,12 +1,12 @@
|
||||||
use std::borrow::Borrow;
|
use std::borrow::Borrow;
|
||||||
use crate::error;
|
use crate::{error, util};
|
||||||
use crate::heap::{D3D12DescriptorHeap, LutTextureHeap, ResourceWorkHeap};
|
use crate::heap::{D3D12DescriptorHeap, LutTextureHeap, ResourceWorkHeap};
|
||||||
use crate::samplers::SamplerSet;
|
use crate::samplers::SamplerSet;
|
||||||
use crate::texture::LutTexture;
|
use crate::texture::LutTexture;
|
||||||
use librashader_presets::{ShaderPreset, TextureConfig};
|
use librashader_presets::{ShaderPreset, TextureConfig};
|
||||||
use librashader_reflect::back::targets::HLSL;
|
use librashader_reflect::back::targets::HLSL;
|
||||||
use librashader_reflect::front::GlslangCompilation;
|
use librashader_reflect::front::GlslangCompilation;
|
||||||
use librashader_reflect::reflect::presets::CompilePresetTarget;
|
use librashader_reflect::reflect::presets::{CompilePresetTarget, ShaderPassArtifact};
|
||||||
use librashader_runtime::image::{Image, UVDirection};
|
use librashader_runtime::image::{Image, UVDirection};
|
||||||
use rustc_hash::FxHashMap;
|
use rustc_hash::FxHashMap;
|
||||||
use std::error::Error;
|
use std::error::Error;
|
||||||
|
@ -21,7 +21,16 @@ use windows::Win32::Graphics::Direct3D12::{
|
||||||
};
|
};
|
||||||
use windows::Win32::System::Threading::{CreateEventA, ResetEvent, WaitForSingleObject};
|
use windows::Win32::System::Threading::{CreateEventA, ResetEvent, WaitForSingleObject};
|
||||||
use windows::Win32::System::WindowsProgramming::INFINITE;
|
use windows::Win32::System::WindowsProgramming::INFINITE;
|
||||||
|
use librashader_common::ImageFormat;
|
||||||
|
use librashader_reflect::back::{CompileReflectShader, CompileShader};
|
||||||
|
use librashader_reflect::reflect::ReflectShader;
|
||||||
|
use librashader_reflect::reflect::semantics::ShaderSemantics;
|
||||||
|
use crate::filter_pass::FilterPass;
|
||||||
|
use crate::graphics_pipeline::{D3D12GraphicsPipeline, D3D12RootSignature};
|
||||||
use crate::mipmap::D3D12MipmapGen;
|
use crate::mipmap::D3D12MipmapGen;
|
||||||
|
use crate::quad_render::DrawQuad;
|
||||||
|
|
||||||
|
type ShaderPassMeta = ShaderPassArtifact<impl CompileReflectShader<HLSL, GlslangCompilation>>;
|
||||||
|
|
||||||
pub struct FilterChainD3D12 {
|
pub struct FilterChainD3D12 {
|
||||||
pub(crate) common: FilterCommon,
|
pub(crate) common: FilterCommon,
|
||||||
|
@ -30,6 +39,7 @@ pub struct FilterChainD3D12 {
|
||||||
// pub(crate) feedback_framebuffers: Box<[OwnedFramebuffer]>,
|
// pub(crate) feedback_framebuffers: Box<[OwnedFramebuffer]>,
|
||||||
// pub(crate) history_framebuffers: VecDeque<OwnedFramebuffer>,
|
// pub(crate) history_framebuffers: VecDeque<OwnedFramebuffer>,
|
||||||
// pub(crate) draw_quad: DrawQuad,
|
// pub(crate) draw_quad: DrawQuad,
|
||||||
|
pub(crate) filters: Vec<FilterPass>,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) struct FilterCommon {
|
pub(crate) struct FilterCommon {
|
||||||
|
@ -44,6 +54,7 @@ pub(crate) struct FilterCommon {
|
||||||
lut_heap: D3D12DescriptorHeap<LutTextureHeap>,
|
lut_heap: D3D12DescriptorHeap<LutTextureHeap>,
|
||||||
luts: FxHashMap<usize, LutTexture>,
|
luts: FxHashMap<usize, LutTexture>,
|
||||||
mipmap_gen: D3D12MipmapGen,
|
mipmap_gen: D3D12MipmapGen,
|
||||||
|
root_signature: D3D12RootSignature,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl FilterChainD3D12 {
|
impl FilterChainD3D12 {
|
||||||
|
@ -58,6 +69,41 @@ impl FilterChainD3D12 {
|
||||||
Self::load_from_preset(device, preset, options)
|
Self::load_from_preset(device, preset, options)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
/// Load a filter chain from a pre-parsed `ShaderPreset`.
|
||||||
|
pub fn load_from_preset(
|
||||||
|
device: &ID3D12Device,
|
||||||
|
preset: ShaderPreset,
|
||||||
|
options: Option<&()>,
|
||||||
|
) -> error::Result<FilterChainD3D12> {
|
||||||
|
let (passes, semantics) = HLSL::compile_preset_passes::<GlslangCompilation, Box<dyn Error>>(
|
||||||
|
preset.shaders,
|
||||||
|
&preset.textures,
|
||||||
|
)?;
|
||||||
|
|
||||||
|
let samplers = SamplerSet::new(device)?;
|
||||||
|
let mipmap_gen = D3D12MipmapGen::new(device).unwrap();
|
||||||
|
|
||||||
|
let mut lut_heap = D3D12DescriptorHeap::new(device, preset.textures.len())?;
|
||||||
|
let luts = FilterChainD3D12::load_luts(device, &mut lut_heap, &preset.textures, &mipmap_gen).unwrap();
|
||||||
|
|
||||||
|
let root_signature = D3D12RootSignature::new(device)?;
|
||||||
|
|
||||||
|
let filters = FilterChainD3D12::init_passes(device, &root_signature, passes, &semantics)?;
|
||||||
|
|
||||||
|
Ok(FilterChainD3D12 {
|
||||||
|
common: FilterCommon {
|
||||||
|
d3d12: device.clone(),
|
||||||
|
samplers,
|
||||||
|
lut_heap,
|
||||||
|
luts,
|
||||||
|
mipmap_gen,
|
||||||
|
root_signature,
|
||||||
|
},
|
||||||
|
filters
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
fn load_luts(
|
fn load_luts(
|
||||||
device: &ID3D12Device,
|
device: &ID3D12Device,
|
||||||
heap: &mut D3D12DescriptorHeap<LutTextureHeap>,
|
heap: &mut D3D12DescriptorHeap<LutTextureHeap>,
|
||||||
|
@ -142,36 +188,41 @@ impl FilterChainD3D12 {
|
||||||
unsafe { CloseHandle(fence_event) };
|
unsafe { CloseHandle(fence_event) };
|
||||||
}
|
}
|
||||||
|
|
||||||
std::mem::forget(residuals);
|
drop(residuals);
|
||||||
Ok(luts)
|
Ok(luts)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Load a filter chain from a pre-parsed `ShaderPreset`.
|
fn init_passes(device: &ID3D12Device,
|
||||||
pub fn load_from_preset(
|
root_signature: &D3D12RootSignature,
|
||||||
device: &ID3D12Device,
|
passes: Vec<ShaderPassMeta>,
|
||||||
preset: ShaderPreset,
|
semantics: &ShaderSemantics,)
|
||||||
options: Option<&()>,
|
-> error::Result<Vec<FilterPass>> {
|
||||||
) -> error::Result<FilterChainD3D12> {
|
|
||||||
let (passes, semantics) = HLSL::compile_preset_passes::<GlslangCompilation, Box<dyn Error>>(
|
let mut filters = Vec::new();
|
||||||
preset.shaders,
|
for (index, (config, source, mut reflect)) in passes.into_iter().enumerate() {
|
||||||
&preset.textures,
|
let reflection = reflect.reflect(index, semantics)?;
|
||||||
|
let hlsl = reflect.compile(None)?;
|
||||||
|
|
||||||
|
let graphics_pipeline = D3D12GraphicsPipeline::new(device,
|
||||||
|
&hlsl,
|
||||||
|
root_signature,
|
||||||
|
if let Some(format) = config.get_format_override() {
|
||||||
|
format
|
||||||
|
} else if source.format != ImageFormat::Unknown {
|
||||||
|
source.format
|
||||||
|
} else {
|
||||||
|
ImageFormat::R8G8B8A8Unorm
|
||||||
|
}.into()
|
||||||
)?;
|
)?;
|
||||||
|
|
||||||
let samplers = SamplerSet::new(device)?;
|
filters.push(FilterPass {
|
||||||
let mipmap_gen = D3D12MipmapGen::new(device).unwrap();
|
pipeline: graphics_pipeline,
|
||||||
|
|
||||||
let mut lut_heap = D3D12DescriptorHeap::new(device, preset.textures.len())?;
|
|
||||||
let luts = FilterChainD3D12::load_luts(device, &mut lut_heap, &preset.textures, &mipmap_gen).unwrap();
|
|
||||||
|
|
||||||
Ok(FilterChainD3D12 {
|
|
||||||
common: FilterCommon {
|
|
||||||
d3d12: device.clone(),
|
|
||||||
samplers,
|
|
||||||
lut_heap,
|
|
||||||
luts,
|
|
||||||
mipmap_gen,
|
|
||||||
},
|
|
||||||
})
|
})
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Ok(filters)
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
5
librashader-runtime-d3d12/src/filter_pass.rs
Normal file
5
librashader-runtime-d3d12/src/filter_pass.rs
Normal file
|
@ -0,0 +1,5 @@
|
||||||
|
use crate::graphics_pipeline::D3D12GraphicsPipeline;
|
||||||
|
|
||||||
|
pub(crate) struct FilterPass {
|
||||||
|
pub(crate) pipeline: D3D12GraphicsPipeline
|
||||||
|
}
|
204
librashader-runtime-d3d12/src/graphics_pipeline.rs
Normal file
204
librashader-runtime-d3d12/src/graphics_pipeline.rs
Normal file
|
@ -0,0 +1,204 @@
|
||||||
|
use windows::core::Vtable;
|
||||||
|
use windows::Win32::Foundation::BOOL;
|
||||||
|
use windows::Win32::Graphics::Direct3D12::{D3D12_BLEND_DESC, D3D12_BLEND_INV_SRC_ALPHA, D3D12_BLEND_OP, D3D12_BLEND_OP_ADD, D3D12_BLEND_SRC_ALPHA, D3D12_COLOR_WRITE_ENABLE_ALL, D3D12_CULL_MODE_NONE, D3D12_DESCRIPTOR_RANGE, D3D12_DESCRIPTOR_RANGE_TYPE, D3D12_DESCRIPTOR_RANGE_TYPE_SAMPLER, D3D12_DESCRIPTOR_RANGE_TYPE_SRV, D3D12_FILL_MODE_SOLID, D3D12_GRAPHICS_PIPELINE_STATE_DESC, D3D12_INPUT_LAYOUT_DESC, D3D12_LOGIC_OP_NOOP, D3D12_PRIMITIVE_TOPOLOGY_TYPE_TRIANGLE, D3D12_RASTERIZER_DESC, D3D12_RENDER_TARGET_BLEND_DESC, D3D12_ROOT_DESCRIPTOR, D3D12_ROOT_DESCRIPTOR_TABLE, D3D12_ROOT_PARAMETER, D3D12_ROOT_PARAMETER_0, D3D12_ROOT_PARAMETER_TYPE_CBV, D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE, D3D12_ROOT_SIGNATURE_DESC, D3D12_ROOT_SIGNATURE_FLAG_ALLOW_INPUT_ASSEMBLER_INPUT_LAYOUT, D3D12_SHADER_BYTECODE, D3D12_SHADER_VISIBILITY_ALL, D3D12_SHADER_VISIBILITY_PIXEL, D3D12SerializeRootSignature, D3D_ROOT_SIGNATURE_VERSION_1, D3D_ROOT_SIGNATURE_VERSION_1_0, ID3D12Device, ID3D12PipelineState, ID3D12RootSignature};
|
||||||
|
use windows::Win32::Graphics::Dxgi::Common::{DXGI_FORMAT, DXGI_FORMAT_UNKNOWN, DXGI_SAMPLE_DESC};
|
||||||
|
use librashader_reflect::back::cross::CrossHlslContext;
|
||||||
|
use librashader_reflect::back::ShaderCompilerOutput;
|
||||||
|
use crate::{error, util};
|
||||||
|
use crate::quad_render::DrawQuad;
|
||||||
|
|
||||||
|
pub struct D3D12GraphicsPipeline {
|
||||||
|
pipeline_state: ID3D12PipelineState,
|
||||||
|
}
|
||||||
|
|
||||||
|
const D3D12_SLANG_ROOT_PARAMETERS: &'static [D3D12_ROOT_PARAMETER; 4] = &[
|
||||||
|
// srvs
|
||||||
|
D3D12_ROOT_PARAMETER {
|
||||||
|
ParameterType: D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE,
|
||||||
|
Anonymous: D3D12_ROOT_PARAMETER_0 {
|
||||||
|
DescriptorTable: D3D12_ROOT_DESCRIPTOR_TABLE {
|
||||||
|
NumDescriptorRanges: 1,
|
||||||
|
pDescriptorRanges: &D3D12_DESCRIPTOR_RANGE {
|
||||||
|
RangeType: D3D12_DESCRIPTOR_RANGE_TYPE_SRV,
|
||||||
|
NumDescriptors: 16,
|
||||||
|
BaseShaderRegister: 0,
|
||||||
|
RegisterSpace: 0,
|
||||||
|
OffsetInDescriptorsFromTableStart: 0,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
},
|
||||||
|
ShaderVisibility: D3D12_SHADER_VISIBILITY_PIXEL,
|
||||||
|
},
|
||||||
|
// samplers
|
||||||
|
D3D12_ROOT_PARAMETER {
|
||||||
|
ParameterType: D3D12_ROOT_PARAMETER_TYPE_DESCRIPTOR_TABLE,
|
||||||
|
Anonymous: D3D12_ROOT_PARAMETER_0 {
|
||||||
|
DescriptorTable: D3D12_ROOT_DESCRIPTOR_TABLE {
|
||||||
|
NumDescriptorRanges: 1,
|
||||||
|
pDescriptorRanges: &D3D12_DESCRIPTOR_RANGE {
|
||||||
|
RangeType: D3D12_DESCRIPTOR_RANGE_TYPE_SAMPLER,
|
||||||
|
NumDescriptors: 16,
|
||||||
|
BaseShaderRegister: 0,
|
||||||
|
RegisterSpace: 0,
|
||||||
|
OffsetInDescriptorsFromTableStart: 0,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
},
|
||||||
|
ShaderVisibility: D3D12_SHADER_VISIBILITY_PIXEL,
|
||||||
|
},
|
||||||
|
|
||||||
|
// UBO
|
||||||
|
D3D12_ROOT_PARAMETER {
|
||||||
|
ParameterType: D3D12_ROOT_PARAMETER_TYPE_CBV,
|
||||||
|
Anonymous: D3D12_ROOT_PARAMETER_0 {
|
||||||
|
Descriptor: D3D12_ROOT_DESCRIPTOR {
|
||||||
|
ShaderRegister: 0,
|
||||||
|
RegisterSpace: 0,
|
||||||
|
}
|
||||||
|
},
|
||||||
|
ShaderVisibility: D3D12_SHADER_VISIBILITY_ALL,
|
||||||
|
},
|
||||||
|
D3D12_ROOT_PARAMETER {
|
||||||
|
ParameterType: D3D12_ROOT_PARAMETER_TYPE_CBV,
|
||||||
|
Anonymous: D3D12_ROOT_PARAMETER_0 {
|
||||||
|
Descriptor: D3D12_ROOT_DESCRIPTOR {
|
||||||
|
ShaderRegister: 1,
|
||||||
|
RegisterSpace: 0,
|
||||||
|
}
|
||||||
|
},
|
||||||
|
ShaderVisibility: D3D12_SHADER_VISIBILITY_ALL,
|
||||||
|
}
|
||||||
|
];
|
||||||
|
|
||||||
|
const D3D12_SLANG_ROOT_SIGNATURE: &'static D3D12_ROOT_SIGNATURE_DESC = &D3D12_ROOT_SIGNATURE_DESC {
|
||||||
|
NumParameters: D3D12_SLANG_ROOT_PARAMETERS.len() as u32,
|
||||||
|
pParameters: D3D12_SLANG_ROOT_PARAMETERS.as_ptr(),
|
||||||
|
NumStaticSamplers: 0,
|
||||||
|
pStaticSamplers: std::ptr::null(),
|
||||||
|
Flags: D3D12_ROOT_SIGNATURE_FLAG_ALLOW_INPUT_ASSEMBLER_INPUT_LAYOUT,
|
||||||
|
};
|
||||||
|
|
||||||
|
pub struct D3D12RootSignature {
|
||||||
|
signature: ID3D12RootSignature
|
||||||
|
}
|
||||||
|
|
||||||
|
impl D3D12RootSignature {
|
||||||
|
pub fn new(device: &ID3D12Device)
|
||||||
|
-> error::Result<D3D12RootSignature>
|
||||||
|
{
|
||||||
|
let signature = unsafe {
|
||||||
|
let mut rs_blob = None;
|
||||||
|
// todo: D3D12SerializeVersionedRootSignature
|
||||||
|
// todo: hlsl rootsig tbh
|
||||||
|
D3D12SerializeRootSignature(D3D12_SLANG_ROOT_SIGNATURE,
|
||||||
|
D3D_ROOT_SIGNATURE_VERSION_1,
|
||||||
|
&mut rs_blob,
|
||||||
|
None
|
||||||
|
)?;
|
||||||
|
|
||||||
|
// SAFETY: if D3D12SerializeRootSignature succeeds then blob is Some
|
||||||
|
let rs_blob = rs_blob.unwrap();
|
||||||
|
let blob = std::slice::from_raw_parts(rs_blob.GetBufferPointer().cast(),
|
||||||
|
rs_blob.GetBufferSize());
|
||||||
|
let root_signature: ID3D12RootSignature = device.CreateRootSignature(
|
||||||
|
0, blob
|
||||||
|
)?;
|
||||||
|
root_signature
|
||||||
|
};
|
||||||
|
|
||||||
|
Ok(D3D12RootSignature {
|
||||||
|
signature,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
||||||
|
impl D3D12GraphicsPipeline {
|
||||||
|
pub fn new(device: &ID3D12Device,
|
||||||
|
shader_assembly: &ShaderCompilerOutput<String, CrossHlslContext>,
|
||||||
|
root_signature: &D3D12RootSignature,
|
||||||
|
render_format: DXGI_FORMAT
|
||||||
|
) -> error::Result<D3D12GraphicsPipeline> {
|
||||||
|
let vertex_dxbc =
|
||||||
|
util::d3d_compile_shader(shader_assembly.vertex.as_bytes(),
|
||||||
|
b"main\0", b"vs_5_0\0")?;
|
||||||
|
let fragment_dxbc =
|
||||||
|
util::d3d_compile_shader(shader_assembly.fragment.as_bytes(), b"main\0",
|
||||||
|
b"ps_5_0\0")?;
|
||||||
|
|
||||||
|
let input_element = DrawQuad::get_spirv_cross_vbo_desc();
|
||||||
|
|
||||||
|
|
||||||
|
let pipeline_state: ID3D12PipelineState = unsafe {
|
||||||
|
let pipeline_desc = D3D12_GRAPHICS_PIPELINE_STATE_DESC {
|
||||||
|
pRootSignature: windows::core::ManuallyDrop::new(&root_signature.signature),
|
||||||
|
VS: D3D12_SHADER_BYTECODE {
|
||||||
|
pShaderBytecode: vertex_dxbc.GetBufferPointer(),
|
||||||
|
BytecodeLength: vertex_dxbc.GetBufferSize(),
|
||||||
|
},
|
||||||
|
PS: D3D12_SHADER_BYTECODE {
|
||||||
|
pShaderBytecode: fragment_dxbc.GetBufferPointer(),
|
||||||
|
BytecodeLength: fragment_dxbc.GetBufferSize(),
|
||||||
|
},
|
||||||
|
StreamOutput: Default::default(),
|
||||||
|
BlendState: D3D12_BLEND_DESC {
|
||||||
|
RenderTarget: [
|
||||||
|
D3D12_RENDER_TARGET_BLEND_DESC {
|
||||||
|
BlendEnable: BOOL::from(false),
|
||||||
|
LogicOpEnable: BOOL::from(false),
|
||||||
|
SrcBlend: D3D12_BLEND_SRC_ALPHA,
|
||||||
|
DestBlend: D3D12_BLEND_INV_SRC_ALPHA,
|
||||||
|
BlendOp: D3D12_BLEND_OP_ADD,
|
||||||
|
SrcBlendAlpha: D3D12_BLEND_SRC_ALPHA,
|
||||||
|
DestBlendAlpha: D3D12_BLEND_INV_SRC_ALPHA,
|
||||||
|
BlendOpAlpha: D3D12_BLEND_OP_ADD,
|
||||||
|
LogicOp: D3D12_LOGIC_OP_NOOP,
|
||||||
|
RenderTargetWriteMask: D3D12_COLOR_WRITE_ENABLE_ALL.0 as u8,
|
||||||
|
},
|
||||||
|
Default::default(),
|
||||||
|
Default::default(),
|
||||||
|
Default::default(),
|
||||||
|
Default::default(),
|
||||||
|
Default::default(),
|
||||||
|
Default::default(),
|
||||||
|
Default::default()
|
||||||
|
],
|
||||||
|
..Default::default()
|
||||||
|
},
|
||||||
|
SampleMask: u32::MAX,
|
||||||
|
RasterizerState: D3D12_RASTERIZER_DESC {
|
||||||
|
FillMode: D3D12_FILL_MODE_SOLID,
|
||||||
|
CullMode: D3D12_CULL_MODE_NONE,
|
||||||
|
..Default::default()
|
||||||
|
},
|
||||||
|
DepthStencilState: Default::default(),
|
||||||
|
InputLayout: D3D12_INPUT_LAYOUT_DESC {
|
||||||
|
pInputElementDescs: input_element.as_ptr(),
|
||||||
|
NumElements: input_element.len() as u32,
|
||||||
|
},
|
||||||
|
PrimitiveTopologyType: D3D12_PRIMITIVE_TOPOLOGY_TYPE_TRIANGLE,
|
||||||
|
NumRenderTargets: 1,
|
||||||
|
RTVFormats: [
|
||||||
|
render_format,
|
||||||
|
DXGI_FORMAT_UNKNOWN,
|
||||||
|
DXGI_FORMAT_UNKNOWN,
|
||||||
|
DXGI_FORMAT_UNKNOWN,
|
||||||
|
DXGI_FORMAT_UNKNOWN,
|
||||||
|
DXGI_FORMAT_UNKNOWN,
|
||||||
|
DXGI_FORMAT_UNKNOWN,
|
||||||
|
DXGI_FORMAT_UNKNOWN,
|
||||||
|
],
|
||||||
|
SampleDesc: DXGI_SAMPLE_DESC {
|
||||||
|
Count: 1,
|
||||||
|
Quality: 0,
|
||||||
|
},
|
||||||
|
NodeMask: 0,
|
||||||
|
..Default::default()
|
||||||
|
};
|
||||||
|
|
||||||
|
device.CreateGraphicsPipelineState(&pipeline_desc)?
|
||||||
|
};
|
||||||
|
|
||||||
|
Ok(D3D12GraphicsPipeline {
|
||||||
|
pipeline_state,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,6 +1,6 @@
|
||||||
#![feature(const_trait_impl)]
|
#![feature(const_trait_impl)]
|
||||||
#![feature(let_chains)]
|
#![feature(let_chains)]
|
||||||
|
#![feature(type_alias_impl_trait)]
|
||||||
mod error;
|
mod error;
|
||||||
mod filter_chain;
|
mod filter_chain;
|
||||||
mod heap;
|
mod heap;
|
||||||
|
@ -9,6 +9,9 @@ mod samplers;
|
||||||
mod texture;
|
mod texture;
|
||||||
mod util;
|
mod util;
|
||||||
mod mipmap;
|
mod mipmap;
|
||||||
|
mod filter_pass;
|
||||||
|
mod quad_render;
|
||||||
|
mod graphics_pipeline;
|
||||||
|
|
||||||
#[cfg(test)]
|
#[cfg(test)]
|
||||||
mod tests {
|
mod tests {
|
||||||
|
|
120
librashader-runtime-d3d12/src/quad_render.rs
Normal file
120
librashader-runtime-d3d12/src/quad_render.rs
Normal file
|
@ -0,0 +1,120 @@
|
||||||
|
use crate::error;
|
||||||
|
use bytemuck::offset_of;
|
||||||
|
use windows::core::PCSTR;
|
||||||
|
use windows::Win32::Graphics::Direct3D::D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP;
|
||||||
|
use windows::Win32::Graphics::Direct3D11::{
|
||||||
|
ID3D11Buffer, ID3D11Device, ID3D11DeviceContext, D3D11_BIND_VERTEX_BUFFER, D3D11_BUFFER_DESC,
|
||||||
|
D3D11_INPUT_ELEMENT_DESC, D3D11_INPUT_PER_VERTEX_DATA, D3D11_SUBRESOURCE_DATA,
|
||||||
|
D3D11_USAGE_IMMUTABLE,
|
||||||
|
};
|
||||||
|
use windows::Win32::Graphics::Direct3D12::{D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA, D3D12_INPUT_ELEMENT_DESC};
|
||||||
|
use windows::Win32::Graphics::Dxgi::Common::DXGI_FORMAT_R32G32_FLOAT;
|
||||||
|
|
||||||
|
#[repr(C)]
|
||||||
|
#[derive(Debug, Copy, Clone, Default)]
|
||||||
|
struct D3D12Vertex {
|
||||||
|
position: [f32; 2],
|
||||||
|
texcoord: [f32; 2],
|
||||||
|
color: [f32; 4],
|
||||||
|
}
|
||||||
|
|
||||||
|
const CLEAR: [f32; 4] = [1.0, 1.0, 1.0, 1.0];
|
||||||
|
|
||||||
|
static QUAD_VBO_DATA: &[D3D12Vertex; 4] = &[
|
||||||
|
D3D12Vertex {
|
||||||
|
position: [0.0, 0.0],
|
||||||
|
texcoord: [0.0, 1.0],
|
||||||
|
color: CLEAR,
|
||||||
|
},
|
||||||
|
D3D12Vertex {
|
||||||
|
position: [0.0, 1.0],
|
||||||
|
texcoord: [0.0, 0.0],
|
||||||
|
color: CLEAR,
|
||||||
|
},
|
||||||
|
D3D12Vertex {
|
||||||
|
position: [1.0, 0.0],
|
||||||
|
texcoord: [1.0, 1.0],
|
||||||
|
color: CLEAR,
|
||||||
|
},
|
||||||
|
D3D12Vertex {
|
||||||
|
position: [1.0, 1.0],
|
||||||
|
texcoord: [1.0, 0.0],
|
||||||
|
color: CLEAR,
|
||||||
|
},
|
||||||
|
];
|
||||||
|
|
||||||
|
pub(crate) struct DrawQuad {
|
||||||
|
buffer: ID3D11Buffer,
|
||||||
|
context: ID3D11DeviceContext,
|
||||||
|
offset: u32,
|
||||||
|
stride: u32,
|
||||||
|
}
|
||||||
|
|
||||||
|
impl DrawQuad {
|
||||||
|
// pub fn new(device: &ID3D11Device, context: &ID3D11DeviceContext) -> error::Result<DrawQuad> {
|
||||||
|
// unsafe {
|
||||||
|
// let mut buffer = None;
|
||||||
|
// device.CreateBuffer(
|
||||||
|
// &D3D11_BUFFER_DESC {
|
||||||
|
// ByteWidth: std::mem::size_of::<[D3D11Vertex; 4]>() as u32,
|
||||||
|
// Usage: D3D11_USAGE_IMMUTABLE,
|
||||||
|
// BindFlags: D3D11_BIND_VERTEX_BUFFER,
|
||||||
|
// CPUAccessFlags: Default::default(),
|
||||||
|
// MiscFlags: Default::default(),
|
||||||
|
// StructureByteStride: 0,
|
||||||
|
// },
|
||||||
|
// Some(&D3D11_SUBRESOURCE_DATA {
|
||||||
|
// pSysMem: QUAD_VBO_DATA.as_ptr().cast(),
|
||||||
|
// SysMemPitch: 0,
|
||||||
|
// SysMemSlicePitch: 0,
|
||||||
|
// }),
|
||||||
|
// Some(&mut buffer),
|
||||||
|
// )?;
|
||||||
|
// assume_d3d11_init!(buffer, "CreateBuffer");
|
||||||
|
//
|
||||||
|
// Ok(DrawQuad {
|
||||||
|
// buffer,
|
||||||
|
// context: context.clone(),
|
||||||
|
// offset: 0,
|
||||||
|
// stride: std::mem::size_of::<D3D11Vertex>() as u32,
|
||||||
|
// })
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// pub fn bind_vertices(&self) {
|
||||||
|
// unsafe {
|
||||||
|
// self.context
|
||||||
|
// .IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP);
|
||||||
|
// self.context.IASetVertexBuffers(
|
||||||
|
// 0,
|
||||||
|
// 1,
|
||||||
|
// Some(&Some(self.buffer.clone())),
|
||||||
|
// Some(&self.stride),
|
||||||
|
// Some(&self.offset),
|
||||||
|
// );
|
||||||
|
// }
|
||||||
|
// }
|
||||||
|
|
||||||
|
pub fn get_spirv_cross_vbo_desc() -> [D3D12_INPUT_ELEMENT_DESC; 2] {
|
||||||
|
[
|
||||||
|
D3D12_INPUT_ELEMENT_DESC {
|
||||||
|
SemanticName: PCSTR(b"TEXCOORD\0".as_ptr()),
|
||||||
|
SemanticIndex: 0,
|
||||||
|
Format: DXGI_FORMAT_R32G32_FLOAT,
|
||||||
|
InputSlot: 0,
|
||||||
|
AlignedByteOffset: offset_of!(D3D12Vertex, position) as u32,
|
||||||
|
InputSlotClass: D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA,
|
||||||
|
InstanceDataStepRate: 0,
|
||||||
|
},
|
||||||
|
D3D12_INPUT_ELEMENT_DESC {
|
||||||
|
SemanticName: PCSTR(b"TEXCOORD\0".as_ptr()),
|
||||||
|
SemanticIndex: 1,
|
||||||
|
Format: DXGI_FORMAT_R32G32_FLOAT,
|
||||||
|
InputSlot: 0,
|
||||||
|
AlignedByteOffset: offset_of!(D3D12Vertex, texcoord) as u32,
|
||||||
|
InputSlotClass: D3D12_INPUT_CLASSIFICATION_PER_VERTEX_DATA,
|
||||||
|
InstanceDataStepRate: 0,
|
||||||
|
},
|
||||||
|
]
|
||||||
|
}
|
||||||
|
}
|
|
@ -116,6 +116,7 @@ pub fn d3d12_get_closest_format(
|
||||||
}
|
}
|
||||||
|
|
||||||
pub fn d3d_compile_shader(source: &[u8], entry: &[u8], version: &[u8]) -> error::Result<ID3DBlob> {
|
pub fn d3d_compile_shader(source: &[u8], entry: &[u8], version: &[u8]) -> error::Result<ID3DBlob> {
|
||||||
|
// todo: compile with dxc
|
||||||
unsafe {
|
unsafe {
|
||||||
let mut blob = None;
|
let mut blob = None;
|
||||||
D3DCompile(
|
D3DCompile(
|
||||||
|
@ -126,11 +127,12 @@ pub fn d3d_compile_shader(source: &[u8], entry: &[u8], version: &[u8]) -> error:
|
||||||
None,
|
None,
|
||||||
PCSTR(entry.as_ptr()),
|
PCSTR(entry.as_ptr()),
|
||||||
PCSTR(version.as_ptr()),
|
PCSTR(version.as_ptr()),
|
||||||
if cfg!(feature = "debug-shader") {
|
D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION,
|
||||||
D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION
|
// if cfg!(feature = "debug-shader") {
|
||||||
} else {
|
// D3DCOMPILE_DEBUG | D3DCOMPILE_SKIP_OPTIMIZATION
|
||||||
D3DCOMPILE_OPTIMIZATION_LEVEL3
|
// } else {
|
||||||
},
|
// D3DCOMPILE_OPTIMIZATION_LEVEL3
|
||||||
|
// },
|
||||||
0,
|
0,
|
||||||
&mut blob,
|
&mut blob,
|
||||||
None,
|
None,
|
||||||
|
|
Loading…
Reference in a new issue