97 lines
		
	
	
	
		
			3.1 KiB
		
	
	
	
		
			C++
		
	
	
	
	
	
			
		
		
	
	
			97 lines
		
	
	
	
		
			3.1 KiB
		
	
	
	
		
			C++
		
	
	
	
	
	
#include <renderer/dx/shader.hpp>
 | 
						|
#include <renderer/dx/shared_context.hpp>
 | 
						|
#include <renderer/dx/vertex_layout.hpp>
 | 
						|
 | 
						|
namespace lt {
 | 
						|
 | 
						|
dxVertexLayout::dxVertexLayout(
 | 
						|
    Ref<Shader> shader,
 | 
						|
    const std::vector<std::pair<std::string, VertexElementType>> &elements,
 | 
						|
    Ref<dxSharedContext> sharedContext
 | 
						|
)
 | 
						|
    : m_context(sharedContext)
 | 
						|
    , m_input_layout(nullptr)
 | 
						|
{
 | 
						|
	auto inputElementsDesc = std::vector<D3D11_INPUT_ELEMENT_DESC> {};
 | 
						|
	inputElementsDesc.reserve(elements.size());
 | 
						|
 | 
						|
	// extract elements desc
 | 
						|
	for (const auto &element : elements)
 | 
						|
	{
 | 
						|
		inputElementsDesc.emplace_back(
 | 
						|
		    D3D11_INPUT_ELEMENT_DESC { element.first.c_str(),
 | 
						|
		                               NULL,
 | 
						|
		                               get_dxgi_format(element.second),
 | 
						|
		                               0u,
 | 
						|
		                               D3D11_APPEND_ALIGNED_ELEMENT,
 | 
						|
		                               D3D11_INPUT_PER_VERTEX_DATA,
 | 
						|
		                               0u }
 | 
						|
		);
 | 
						|
	}
 | 
						|
 | 
						|
	auto dxpShader = std::dynamic_pointer_cast<dxShader>(shader);
 | 
						|
	ensure(dxpShader, "Failed to cast 'Shader' to 'dxShader'");
 | 
						|
 | 
						|
	// create input layout (vertex layout)
 | 
						|
	auto hr = HRESULT {};
 | 
						|
	dxc(m_context->get_device()->CreateInputLayout(
 | 
						|
	    &inputElementsDesc[0],
 | 
						|
	    inputElementsDesc.size(),
 | 
						|
	    dxpShader->get_vertex_blob().Get()->GetBufferPointer(),
 | 
						|
	    dxpShader->get_vertex_blob().Get()->GetBufferSize(),
 | 
						|
	    &m_input_layout
 | 
						|
	));
 | 
						|
}
 | 
						|
 | 
						|
dxVertexLayout::~dxVertexLayout()
 | 
						|
{
 | 
						|
	un_bind();
 | 
						|
}
 | 
						|
 | 
						|
void dxVertexLayout::bind()
 | 
						|
{
 | 
						|
	m_context->get_device_context()->IASetInputLayout(m_input_layout.Get());
 | 
						|
}
 | 
						|
 | 
						|
void dxVertexLayout::un_bind()
 | 
						|
{
 | 
						|
	m_context->get_device_context()->IASetInputLayout(nullptr);
 | 
						|
}
 | 
						|
 | 
						|
auto dxVertexLayout::get_dxgi_format(VertexElementType type) -> DXGI_FORMAT
 | 
						|
{
 | 
						|
	switch (type)
 | 
						|
	{
 | 
						|
	/* byte */
 | 
						|
	case lt::VertexElementType::Byte1: return DXGI_FORMAT_R8_SINT;
 | 
						|
	case lt::VertexElementType::Byte2: return DXGI_FORMAT_R8G8_SINT;
 | 
						|
	case lt::VertexElementType::Byte4: return DXGI_FORMAT_R8_SINT;
 | 
						|
 | 
						|
	/* ubyte */
 | 
						|
	case lt::VertexElementType::UByte1: return DXGI_FORMAT_R8_UINT;
 | 
						|
	case lt::VertexElementType::UByte2: return DXGI_FORMAT_R8G8_UINT;
 | 
						|
	case lt::VertexElementType::UByte4: return DXGI_FORMAT_R8G8B8A8_UINT;
 | 
						|
 | 
						|
	/* int */
 | 
						|
	case lt::VertexElementType::Int1: return DXGI_FORMAT_R32_SINT;
 | 
						|
	case lt::VertexElementType::Int2: return DXGI_FORMAT_R32G32_SINT;
 | 
						|
	case lt::VertexElementType::Int3: return DXGI_FORMAT_R32G32B32_SINT;
 | 
						|
	case lt::VertexElementType::Int4: return DXGI_FORMAT_R32G32B32A32_SINT;
 | 
						|
 | 
						|
	/* uint */
 | 
						|
	case lt::VertexElementType::UInt1: return DXGI_FORMAT_R32_UINT;
 | 
						|
	case lt::VertexElementType::UInt2: return DXGI_FORMAT_R32G32_UINT;
 | 
						|
	case lt::VertexElementType::UInt3: return DXGI_FORMAT_R32G32B32_UINT;
 | 
						|
	case lt::VertexElementType::UInt4: return DXGI_FORMAT_R32G32B32A32_UINT;
 | 
						|
 | 
						|
	/* float */
 | 
						|
	case lt::VertexElementType::Float1: return DXGI_FORMAT_R32_FLOAT;
 | 
						|
	case lt::VertexElementType::Float2: return DXGI_FORMAT_R32G32_FLOAT;
 | 
						|
	case lt::VertexElementType::Float3: return DXGI_FORMAT_R32G32B32_FLOAT;
 | 
						|
	case lt::VertexElementType::Float4: return DXGI_FORMAT_R32G32B32A32_FLOAT;
 | 
						|
 | 
						|
	default: ensure(false, "Invalid 'VertexElementType'"); return DXGI_FORMAT_UNKNOWN;
 | 
						|
	}
 | 
						|
}
 | 
						|
 | 
						|
} // namespace lt
 |