Directx11学习笔记【十四】 使用最新的Effect框架和SDK
由于之前一直在看directx11龙书学习,因此sdk一直用的Microsoft DirectX SDK (June 2010) 版本,最近在stackoverflow上问dx11相关问题时,一直被大神吐槽为何还用已经废弃的directx sdk,由于directx sdk现在已经和windows sdk合并到一起了,只能去下windows sdk了。为了方便索性直接换了vs 2015社区版,里面自带了(windows sdk),既然sdk换了最新的,effect框架也要换最新的啊(Effect框架已经被微软开源托管在github上,https://github.com/Microsoft/FX11/wiki)。还有stackoverflow上都推荐DirectXTK,这方面中文资料非常少,只能靠自己慢慢看文档示例学了,等看得差不多了,会考虑用DirectXTK写的。以后教程还是基本跟着龙书走,我会将龙书实现的效果用自己封装的框架写一遍,尤其是一些过时的函数方法我也会换上对应的新方法。
由于directx sdk集成在windows sdk中了,所以在建项目的时候就不用设置引用目录和库目录的路径了,只需设置链接库就可以了,还是挺方便的。由于换了sdk,一些方法参数之类的都略有不同,我又把之前的基类Dx11DemoBase重新封装了一遍,为了练习把前一个教程HillsDemo又重新写了一遍,体会一下有哪些改动。不同之处都在代码中给出了注释。
前面教程编译shader用的是两个方法D3DX11CompileFromFile和
D3DX11CreateEffectFromMemory,显得比较麻烦,在最新的FX11(Effect框架)中这两个方法已经废弃了,我们可以采用D3DX11CompileEffectFromFile来编译shader,一步到位尤为方便
//compile shader
ID3DBlob* errorBlob;
DWORD shaderFlags = D3DCOMPILE_ENABLE_STRICTNESS; #if defined _DEBUG || defined DEBUG
shaderFlags = D3DCOMPILE_DEBUG;
#endif hr = D3DX11CompileEffectFromFile(L"color.fx", nullptr, D3D_COMPILE_STANDARD_FILE_INCLUDE, shaderFlags,
, m_pd3dDevice, &m_pFx, &errorBlob);
if (FAILED(hr))
{
MessageBox(nullptr, (LPCWSTR)errorBlob->GetBufferPointer(), L"error", MB_OK);
return hr;
} m_pTechnique = m_pFx->GetTechniqueByName("ColorTech");
m_pFxWorldViewProj = m_pFx->GetVariableByName("gWorldViewProj")->AsMatrix();
下面给出改动后的HillsDemo代码(其实大体差不多),在看新的官方实例时发现代码都是c++11风格(使用nullptr代替NULL,使用c++风格类型转换static_cast/reinterpret_cast,DirectXTK中大量使用智能指针等),因此咱也尽量保持相同的风格以养成写规范代码的好习惯。此外注释我也尽量用英文写,一方面有些用汉语不太好说明,另一方面由于要经常在stackoverflow上提问老外看不懂汉语还得临时改英文挺麻烦的。
Base基类这次我们添加了depth/stencil缓冲,以便以后用到的时候不用再临时添加了。
//create depth stencil texture
D3D11_TEXTURE2D_DESC descDepth;
descDepth.Width = m_width;
descDepth.Height = m_height;
descDepth.ArraySize = ;
descDepth.MipLevels = ;
descDepth.Format = DXGI_FORMAT_D24_UNORM_S8_UINT;
descDepth.SampleDesc.Count = ;
descDepth.SampleDesc.Quality = ;
descDepth.Usage = D3D11_USAGE_DEFAULT;
descDepth.BindFlags = D3D11_BIND_DEPTH_STENCIL;
descDepth.CPUAccessFlags = ;
descDepth.MiscFlags = ;
hr = m_pd3dDevice->CreateTexture2D(&descDepth, nullptr, &m_pDepthStencilBuffer);
if (FAILED(hr))
return hr; //create the depth stencil view
D3D11_DEPTH_STENCIL_VIEW_DESC descDSV;
ZeroMemory(&descDSV, sizeof(descDSV));
descDSV.Format = descDepth.Format;
descDSV.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D;
descDSV.Texture2D.MipSlice = ;
hr = m_pd3dDevice->CreateDepthStencilView(m_pDepthStencilBuffer, &descDSV, &m_pDepthStencilView);
if (FAILED(hr))
return hr;
在实际Demo中每帧要clear一下
//clear depth/stencil view
m_pImmediateContext->ClearDepthStencilView(m_pDepthStencilView, D3D11_CLEAR_DEPTH | D3D11_CLEAR_STENCIL,
1.0f, );
Dx11DemoBase.h
#ifndef _DX11DEMOBASE_H_
#define _DX11DEMOBASE_H_ #include <string>
#include <windows.h>
#include <d3d11.h>
#include <d3dcompiler.h>
#include <DirectXMath.h>//don't use xnamath.h
#include <directxcolors.h> using namespace DirectX; class Dx11DemoBase
{
public:
Dx11DemoBase();
virtual ~Dx11DemoBase(); std::wstring m_mainWndCaption; //title
float AspectRatio() const; //width/height bool InitDirect3D(HINSTANCE hInstance, HWND hWnd); void ShutDown(); //release virtual bool LoadContent(); //init concrete content
virtual void UnLoadContent(); //release virtual void Update(float dt) = ;
virtual void Render() = ; virtual void OnMouseDown(WPARAM btnState, int x, int y) {}
virtual void OnMouseUp(WPARAM btnState, int x, int y) {}
virtual void OnMouseMove(WPARAM btnState, int x, int y) {} protected:
UINT m_width; //window width
UINT m_height; //window height
HINSTANCE m_hInstance;
HWND m_hWnd;
D3D_DRIVER_TYPE m_driverType;
D3D_FEATURE_LEVEL m_featureLevel;
ID3D11Device* m_pd3dDevice;
ID3D11DeviceContext* m_pImmediateContext;
IDXGISwapChain* m_pSwapChain;
ID3D11RenderTargetView* m_pRenderTargetView;
ID3D11Texture2D* m_pDepthStencilBuffer;
ID3D11DepthStencilView* m_pDepthStencilView;
}; #endif//_DX11DEMOBASE_H_
Dx11DemoBase.cpp
#include "Dx11DemoBase.h" Dx11DemoBase::Dx11DemoBase():
m_mainWndCaption(L"Directx11 Application"),
m_driverType(D3D_DRIVER_TYPE_HARDWARE),
m_featureLevel(D3D_FEATURE_LEVEL_11_0),
m_pd3dDevice(nullptr),
m_pImmediateContext(nullptr),
m_pRenderTargetView(nullptr),
m_pDepthStencilBuffer(nullptr),
m_pDepthStencilView(nullptr),
m_pSwapChain(nullptr),
m_hWnd(nullptr),
m_width(),
m_height()
{} Dx11DemoBase::~Dx11DemoBase()
{
ShutDown();
} float Dx11DemoBase::AspectRatio() const
{
return static_cast<float>(m_width / m_height);
} bool Dx11DemoBase::InitDirect3D(HINSTANCE hInstance, HWND hWnd)
{
HRESULT hr = S_OK;
m_hInstance = hInstance;
m_hWnd = hWnd;
RECT rc;
GetClientRect(m_hWnd, &rc);
m_width = rc.right - rc.left;
m_height = rc.bottom - rc.top; UINT createDeviceFlags = ; #ifdef _DEBUG
createDeviceFlags |= D3D11_CREATE_DEVICE_DEBUG;
#endif D3D_DRIVER_TYPE driverTypes[] =
{
D3D_DRIVER_TYPE_HARDWARE,
D3D_DRIVER_TYPE_WARP,
D3D_DRIVER_TYPE_REFERENCE
};
UINT numDriverTypes = ARRAYSIZE(driverTypes); D3D_FEATURE_LEVEL featureLevels[] =
{
D3D_FEATURE_LEVEL_11_0,
D3D_FEATURE_LEVEL_10_1,
D3D_FEATURE_LEVEL_10_0
};
UINT numFeatureLevels = ARRAYSIZE(featureLevels); DXGI_SWAP_CHAIN_DESC sd;
ZeroMemory(&sd, sizeof(sd));
sd.BufferCount = ;
sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM;
sd.BufferDesc.Width = m_width;
sd.BufferDesc.Height = m_height;
sd.BufferDesc.RefreshRate.Numerator = ;
sd.BufferDesc.RefreshRate.Denominator = ;
sd.BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT;
sd.OutputWindow = m_hWnd;
sd.SampleDesc.Count = ;
sd.SampleDesc.Quality = ;
sd.Windowed = TRUE; //create device and swapchain
for (UINT driverTypeIndex = ; driverTypeIndex < numDriverTypes; ++driverTypeIndex)
{
hr = D3D11CreateDeviceAndSwapChain(nullptr, driverTypes[driverTypeIndex], nullptr,
createDeviceFlags, featureLevels, numFeatureLevels, D3D11_SDK_VERSION, &sd, &m_pSwapChain,
&m_pd3dDevice, &m_featureLevel, &m_pImmediateContext);
if (SUCCEEDED(hr))
{
m_driverType = driverTypes[driverTypeIndex];
break;
}
}
if (FAILED(hr))
return hr; //create render target view
ID3D11Texture2D *pBackBuffer = nullptr;
hr = m_pSwapChain->GetBuffer(, __uuidof(ID3D11Texture2D), reinterpret_cast<void**>(&pBackBuffer));
if (FAILED(hr))
return hr; hr = m_pd3dDevice->CreateRenderTargetView(pBackBuffer, nullptr, &m_pRenderTargetView);
pBackBuffer->Release();
if (FAILED(hr))
return hr; m_pImmediateContext->OMSetRenderTargets(, &m_pRenderTargetView, nullptr); //create depth stencil texture
D3D11_TEXTURE2D_DESC descDepth;
descDepth.Width = m_width;
descDepth.Height = m_height;
descDepth.ArraySize = ;
descDepth.MipLevels = ;
descDepth.Format = DXGI_FORMAT_D24_UNORM_S8_UINT;
descDepth.SampleDesc.Count = ;
descDepth.SampleDesc.Quality = ;
descDepth.Usage = D3D11_USAGE_DEFAULT;
descDepth.BindFlags = D3D11_BIND_DEPTH_STENCIL;
descDepth.CPUAccessFlags = ;
descDepth.MiscFlags = ;
hr = m_pd3dDevice->CreateTexture2D(&descDepth, nullptr, &m_pDepthStencilBuffer);
if (FAILED(hr))
return hr; //create the depth stencil view
D3D11_DEPTH_STENCIL_VIEW_DESC descDSV;
ZeroMemory(&descDSV, sizeof(descDSV));
descDSV.Format = descDepth.Format;
descDSV.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D;
descDSV.Texture2D.MipSlice = ;
hr = m_pd3dDevice->CreateDepthStencilView(m_pDepthStencilBuffer, &descDSV, &m_pDepthStencilView);
if (FAILED(hr))
return hr; m_pImmediateContext->OMSetRenderTargets(, &m_pRenderTargetView, m_pDepthStencilView); //setup the viewport
D3D11_VIEWPORT vp;
vp.Width = static_cast<float>(m_width);
vp.Height = static_cast<float>(m_height);
vp.MinDepth = 0.0f;
vp.MaxDepth = 1.0f;
vp.TopLeftX = 0.0f;
vp.TopLeftY = 0.0f;
m_pImmediateContext->RSSetViewports(, &vp); return LoadContent();
} void Dx11DemoBase::ShutDown()
{
UnLoadContent();
if (m_pImmediateContext) m_pImmediateContext->ClearState(); if (m_pRenderTargetView) m_pRenderTargetView->Release();
if (m_pSwapChain) m_pSwapChain->Release();
if (m_pImmediateContext) m_pImmediateContext->Release();
if (m_pd3dDevice) m_pd3dDevice->Release();
if (m_pDepthStencilBuffer) m_pDepthStencilBuffer->Release();
if (m_pDepthStencilView) m_pDepthStencilView->Release();
} bool Dx11DemoBase::LoadContent()
{
return true;
} void Dx11DemoBase::UnLoadContent(){}
GeometryGenerator类中代码没什么改变不再给出
HillsDemo.h
#ifndef _HILLSDEMO_H_
#define _HILLSDEMO_H_ #include "Dx11DemoBase.h"
#include "d3dx11effect.h"
#include "GeometryGenerator.h" #pragma comment(lib,"d3d11.lib")
#pragma comment(lib,"Effects11.lib")
#pragma comment(lib,"d3dcompiler.lib")
#pragma comment(lib,"winmm.lib")
#pragma comment(lib,"comctl32.lib")
#pragma comment(lib,"dxguid.lib") class HillsDemo : public Dx11DemoBase
{
public:
HillsDemo();
~HillsDemo(); bool LoadContent() override;
void UnLoadContent() override; void Update(float dt) override;
void Render() override; void OnMouseDown(WPARAM btnState, int x, int y) override;
void OnMouseUp(WPARAM btnState, int x, int y) override;
void OnMouseMove(WPARAM btnState, int x, int y) override;
private:
ID3D11Buffer* m_pVertexBuffer;
ID3D11Buffer* m_pIndexBuffer;
ID3D11InputLayout* m_pInputLayout; ID3DX11Effect* m_pFx;
ID3DX11EffectTechnique* m_pTechnique;
ID3DX11EffectMatrixVariable* m_pFxWorldViewProj;
XMFLOAT4X4 m_world;
XMFLOAT4X4 m_view;
XMFLOAT4X4 m_proj; UINT m_gridIndexCount;
float m_theta;
float m_phi;
float m_radius;
POINT m_lastMousePos; float GetHeight(float x, float z)const; }; #endif//_HILLSDEMO_H_
HillsDemo.cpp
#include "HillsDemo.h" struct Vertex
{
XMFLOAT3 pos;
XMFLOAT4 color;
Vertex(XMFLOAT3 p, XMFLOAT4 c) : pos(p), color(c) {}
}; HillsDemo::HillsDemo() :m_pInputLayout(nullptr), m_pVertexBuffer(nullptr),m_pFx(nullptr), m_gridIndexCount(),
m_theta(1.5f*XM_PI), m_phi(0.1f*XM_PI), m_radius(200.0f)
{
XMMATRIX I = XMMatrixIdentity();
XMStoreFloat4x4(&m_world, I);
XMStoreFloat4x4(&m_view, I);
XMStoreFloat4x4(&m_proj, I);
} HillsDemo::~HillsDemo()
{ } bool HillsDemo::LoadContent()
{
HRESULT hr; //create vertex buffer
GeometryGenerator::MeshData grid;
GeometryGenerator geoGen;
geoGen.CreateGrid(160.0f, 160.0f, , , grid);
m_gridIndexCount = grid.indices.size(); std::vector<Vertex> vertices(grid.vertices.size(), Vertex(XMFLOAT3(, , ), XMFLOAT4(, , , )));
for (UINT i = ; i < grid.vertices.size(); ++i)
{
XMFLOAT3 p = grid.vertices[i].Position;
p.y = GetHeight(p.x, p.z); vertices[i].pos = p; //render vertex with different color according to height
if (p.y < -10.0f)
{
//sandy beach color
vertices[i].color = XMFLOAT4(1.0f, 0.96f, 0.62f, 1.0f);
}
else if (p.y < 5.0f)
{
//dark yellow-green color
vertices[i].color = XMFLOAT4(0.1f, 0.48f, 0.19f, 1.0f);
}
else if (p.y < 12.0f)
{
//light yellow-green color
vertices[i].color = XMFLOAT4(0.48f, 0.77f, 0.46f, 1.0f);
}
else if (p.y < .f)
{
//dark brown color
vertices[i].color = XMFLOAT4(0.45f, 0.39f, 0.34f, 1.0f);
}
else
{
//white snow color
vertices[i].color = XMFLOAT4(1.0f, 1.0f, 1.0f, 1.0f);
}
} D3D11_BUFFER_DESC vertexDesc;
ZeroMemory(&vertexDesc, sizeof(vertexDesc));
vertexDesc.Usage = D3D11_USAGE_IMMUTABLE;
vertexDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER;
vertexDesc.ByteWidth = sizeof(Vertex)* grid.vertices.size();
D3D11_SUBRESOURCE_DATA resourceData;
ZeroMemory(&resourceData, sizeof(resourceData));
resourceData.pSysMem = &vertices[];
hr = m_pd3dDevice->CreateBuffer(&vertexDesc, &resourceData, &m_pVertexBuffer);
if (FAILED(hr))
{
return false;
} //set vertex buffer
UINT stride = sizeof(Vertex);
UINT offset = ;
m_pImmediateContext->IASetVertexBuffers(, , &m_pVertexBuffer, &stride, &offset);
//set primitive topology
m_pImmediateContext->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST); //create index buffer
D3D11_BUFFER_DESC indexDesc;
ZeroMemory(&indexDesc, sizeof(indexDesc));
indexDesc.Usage = D3D11_USAGE_IMMUTABLE;
indexDesc.BindFlags = D3D11_BIND_INDEX_BUFFER;
indexDesc.ByteWidth = sizeof(UINT)* m_gridIndexCount; D3D11_SUBRESOURCE_DATA indexData;
ZeroMemory(&indexData, sizeof(indexData));
indexData.pSysMem = &grid.indices[];
hr = m_pd3dDevice->CreateBuffer(&indexDesc, &indexData, &m_pIndexBuffer);
if (FAILED(hr))
{
return false;
} //set index buffer
m_pImmediateContext->IASetIndexBuffer(m_pIndexBuffer, DXGI_FORMAT_R32_UINT, ); //compile shader
ID3DBlob* errorBlob;
DWORD shaderFlags = D3DCOMPILE_ENABLE_STRICTNESS; #if defined _DEBUG || defined DEBUG
shaderFlags = D3DCOMPILE_DEBUG;
#endif hr = D3DX11CompileEffectFromFile(L"color.fx", nullptr, D3D_COMPILE_STANDARD_FILE_INCLUDE, shaderFlags,
, m_pd3dDevice, &m_pFx, &errorBlob);
if (FAILED(hr))
{
MessageBox(nullptr, (LPCWSTR)errorBlob->GetBufferPointer(), L"error", MB_OK);
return hr;
} m_pTechnique = m_pFx->GetTechniqueByName("ColorTech");
m_pFxWorldViewProj = m_pFx->GetVariableByName("gWorldViewProj")->AsMatrix(); //define the input layout
D3D11_INPUT_ELEMENT_DESC colorLayout[] =
{
{ "POSITION", , DXGI_FORMAT_R32G32B32_FLOAT, , , D3D11_INPUT_PER_VERTEX_DATA, },
{ "COLOR", , DXGI_FORMAT_R32G32B32A32_FLOAT, , , D3D11_INPUT_PER_VERTEX_DATA, }
}; UINT numLayoutElements = ARRAYSIZE(colorLayout);
D3DX11_PASS_DESC passDesc;
m_pTechnique->GetPassByIndex()->GetDesc(&passDesc); //create the input layout
hr = m_pd3dDevice->CreateInputLayout(colorLayout, numLayoutElements, passDesc.pIAInputSignature,
passDesc.IAInputSignatureSize, &m_pInputLayout);
if (FAILED(hr))
return hr; //set input layout
m_pImmediateContext->IASetInputLayout(m_pInputLayout); return true;
} void HillsDemo::UnLoadContent()
{
if (m_pVertexBuffer) m_pVertexBuffer->Release();
if (m_pIndexBuffer) m_pIndexBuffer->Release();
if (m_pInputLayout) m_pInputLayout->Release();
if (m_pTechnique) m_pTechnique->Release();
} void HillsDemo::Update(float dt)
{
float x = m_radius*sinf(m_phi)*cosf(m_theta);
float z = m_radius*sinf(m_phi)*sinf(m_theta);
float y = m_radius*cosf(m_phi); XMVECTOR pos = XMVectorSet(x, y, z, 1.0f);
XMVECTOR target = XMVectorSet(0.0f, 0.0f, 0.0f, 1.0f);
XMVECTOR up = XMVectorSet(0.0f, 1.0f, 0.0f, 0.0f); XMMATRIX V = XMMatrixLookAtLH(pos, target, up);
XMStoreFloat4x4(&m_view, V);
XMMATRIX T = XMMatrixPerspectiveFovLH(XM_PIDIV4, m_width / static_cast<float>(m_height),
1.0f, 1000.0f);
XMStoreFloat4x4(&m_proj, T);
} void HillsDemo::Render()
{
if (m_pImmediateContext == )
return;
//clear render target view
float clearColor[] = { 0.0f, 0.0f, 1.0f, 1.0f };
m_pImmediateContext->ClearRenderTargetView(m_pRenderTargetView, clearColor); //clear depth/stencil view
m_pImmediateContext->ClearDepthStencilView(m_pDepthStencilView, D3D11_CLEAR_DEPTH | D3D11_CLEAR_STENCIL,
1.0f, ); //set constant buffer
XMMATRIX world = XMLoadFloat4x4(&m_world);
XMMATRIX view = XMLoadFloat4x4(&m_view);
XMMATRIX proj = XMLoadFloat4x4(&m_proj);
XMMATRIX worldViewProj = world*view*proj; D3DX11_TECHNIQUE_DESC techDesc;
m_pTechnique->GetDesc(&techDesc);
for (UINT i = ; i < techDesc.Passes; ++i)
{
m_pFxWorldViewProj->SetMatrix(reinterpret_cast<float*>(&worldViewProj));
m_pTechnique->GetPassByIndex(i)->Apply(, m_pImmediateContext);
m_pImmediateContext->DrawIndexed(m_gridIndexCount, , );
} m_pSwapChain->Present(, );
} void HillsDemo::OnMouseDown(WPARAM btnState, int x, int y)
{
m_lastMousePos.x = x;
m_lastMousePos.y = y;
SetCapture(m_hWnd);
} void HillsDemo::OnMouseUp(WPARAM btnState, int x, int y)
{
ReleaseCapture();
} //restrict the number
template<typename T>
static T Clamp(const T& x, const T& low, const T& high)
{
return x < low ? low : (x > high ? high : x);
} void HillsDemo::OnMouseMove(WPARAM btnState, int x, int y)
{
if ((btnState & MK_LBUTTON) != )
{
// make each pixel correspond to a quarter of a degree.
float dx = XMConvertToRadians(0.25f*static_cast<float>(x - m_lastMousePos.x));
float dy = XMConvertToRadians(0.25f*static_cast<float>(y - m_lastMousePos.y)); // update angles based on input to orbit camera around box.
m_theta += dx;
m_phi += dy; // restrict the angle mPhi.
m_phi = Clamp(m_phi, 0.1f, XM_PI - 0.1f);
}
else if ((btnState & MK_RBUTTON) != )
{
// make each pixel correspond to 0.2 unit in the scene.
float dx = 0.2f*static_cast<float>(x - m_lastMousePos.x);
float dy = 0.2f*static_cast<float>(y - m_lastMousePos.y); // update the camera radius based on input.
m_radius += dx - dy; // restrict the radius.
m_radius = Clamp(m_radius, 50.0f, 500.0f);
} m_lastMousePos.x = x;
m_lastMousePos.y = y;
} float HillsDemo::GetHeight(float x, float z) const
{
return 0.3f*(z*sinf(0.1f*x) + x*cosf(0.1f*z));
}
main.cpp
#include <windows.h>
#include <windowsx.h>
#include <memory>
#include "HillsDemo.h"
using namespace std; std::shared_ptr<Dx11DemoBase> demo = make_shared<HillsDemo>(); LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM); int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nShowCmd)
{
UNREFERENCED_PARAMETER(hPrevInstance);
UNREFERENCED_PARAMETER(lpCmdLine); WNDCLASSEX wcex;
wcex.cbClsExtra = ;
wcex.cbSize = sizeof(wcex);
wcex.cbWndExtra = ;
wcex.hbrBackground = (HBRUSH)(COLOR_WINDOW + );
wcex.hCursor = LoadCursor(nullptr, IDC_ARROW);
wcex.hIcon = LoadIcon(nullptr, IDI_WINLOGO);
wcex.hIconSm = wcex.hIcon;
wcex.hInstance = hInstance;
wcex.lpfnWndProc = WndProc;
wcex.lpszClassName = L"HillsDemo";
wcex.lpszMenuName = nullptr;
wcex.style = CS_HREDRAW | CS_VREDRAW; if (!RegisterClassEx(&wcex))
return ; RECT rc = { , , , };
AdjustWindowRect(&rc, WS_OVERLAPPEDWINDOW, false); HWND hwnd = CreateWindowEx(WS_EX_APPWINDOW, L"HillsDemo", L"HillsDemo", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT,
CW_USEDEFAULT, rc.right - rc.left, rc.bottom - rc.top, nullptr, nullptr, hInstance, nullptr); if (!hwnd)
return ; ShowWindow(hwnd, nShowCmd); bool result = demo->InitDirect3D(hInstance, hwnd);
if (!result)
return ; MSG msg;
ZeroMemory(&msg, sizeof(msg));
while (msg.message != WM_QUIT)
{
if (PeekMessage(&msg, nullptr, , , PM_REMOVE))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
demo->Update(0.0f);
demo->Render();
}
demo->ShutDown();
return static_cast<int>(msg.wParam);
} LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
PAINTSTRUCT paintStruct;
HDC hdc;
switch (message)
{
case WM_PAINT:
hdc = BeginPaint(hWnd, &paintStruct);
EndPaint(hWnd, &paintStruct);
break;
case WM_DESTROY:
PostQuitMessage();
break;
case WM_LBUTTONDOWN:
case WM_MBUTTONDOWN:
case WM_RBUTTONDOWN:
demo->OnMouseDown(wParam, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));
return ;
case WM_LBUTTONUP:
case WM_MBUTTONUP:
case WM_RBUTTONUP:
demo->OnMouseUp(wParam, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));
return ;
case WM_MOUSEMOVE:
demo->OnMouseMove(wParam, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));
return ;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return ;
}
好了代码就这些了,最后让我们看张图缓解下疲劳吧
Directx11学习笔记【十四】 使用最新的Effect框架和SDK的更多相关文章
- python3.4学习笔记(十四) 网络爬虫实例代码,抓取新浪爱彩双色球开奖数据实例
python3.4学习笔记(十四) 网络爬虫实例代码,抓取新浪爱彩双色球开奖数据实例 新浪爱彩双色球开奖数据URL:http://zst.aicai.com/ssq/openInfo/ 最终输出结果格 ...
- (C/C++学习笔记) 十四. 动态分配
十四. 动态分配 ● C语言实现动态数组 C语言实现动态数组,克服静态数组大小固定的缺陷 C语言中,数组长度必须在创建数组时指定,并且只能是一个常数,不能是变量.一旦定义了一个数组,系统将为它分配一个 ...
- SharpGL学习笔记(十四) 材质:十二个材质球
材质颜色 OpenGL用材料对光的红.绿.蓝三原色的反射率来近似定义材料的颜色.象光源一样,材料颜色也分成环境.漫反射和镜面反射成分,它们决定了材料对环境光.漫反射光和镜面反射光的反射程度.在进行光照 ...
- 【转】angular学习笔记(十四)-$watch(1)
本篇主要介绍$watch的基本概念: $watch是所有控制器的$scope中内置的方法: $scope.$watch(watchObj,watchCallback,ifDeep) watchObj: ...
- Directx11学习笔记【四】 封装一个简单的Dx11DemoBase
根据前面两个笔记的内容,我们来封装一个简单的基类,方便以后的使用. 代码和前面类似,没有什么新的内容,直接看代码吧(由于代码上次都注释了,这次代码就没怎么写注释o(╯□╰)o) Dx11DemoBas ...
- angular学习笔记(十四)-$watch(1)
本篇主要介绍$watch的基本概念: $watch是所有控制器的$scope中内置的方法: $scope.$watch(watchObj,watchCallback,ifDeep) watchObj: ...
- angular学习笔记(十四)-$watch(3)
同样的例子,还可以这样写: <!DOCTYPE html> <html ng-app> <head> <title>11.3$watch监控数据变化&l ...
- Java学习笔记十四:如何定义Java中的类以及使用对象的属性
如何定义Java中的类以及使用对象的属性 一:类的重要性: 所有Java程序都以类class为组织单元: 二:什么是类: 类是模子,确定对象将会拥有的特征(属性)和行为(方法): 三:类的组成: 属性 ...
- MYSQL进阶学习笔记十四:MySQL 应用程序优化!(视频序号:进阶_32)
知识点十五:MySQL 的应用程序优化(32) 一.访问数据库采用连接池 把连接当做对象或设备,统一放在‘连接池’里.凡是需要访问数据库的地方都从连接池里取连接 二.采用缓存减少对于MySQL的访问: ...
随机推荐
- Linux目录文件详解FHS标准(2013.09.05)
Linux 目录配置的依据FHS(Filesystem Hierarchy Standard)标准,将目录分成为四种交互作用的形态: 四种形态的具体解释: 可分享的:可以分享给其他系统挂载使用的目录, ...
- Android设备管理器漏洞2--禁止用户取消激活设备管理器
2013年6月,俄罗斯安全厂商卡巴斯基发现了史上最强手机木马-Obad.A.该木马利用了一个未知的Android设备管理器漏洞(ANDROID-9067882),已激活设备管理器权限的手机木马利用该漏 ...
- Android采用Application总结一下
什么是 Application Application和Activity,Service由于是android框架的一个系统组件,当android程序启动时系统会创建一个 application对象.用 ...
- SE 2014年4月3日
一 OSPF协议都支持哪些特殊区域?每种特殊区域都有什么特点. OSPF协议支持的特殊区域主要有stub区域.totally stub区域以及nssa区域,其中stub区域一般出现在末梢网络,即它的 ...
- 《软件project》课程报告 —国土资源执法监察管理信息系统建模
***********************************************声明*************************************************** ...
- 在Java中如何使用jdbc连接Sql2008数据库(转)
我们在javaEE的开发中,肯定是要用到数据库的,那么在javaEE的开发中,是如何使用代码实现和SQL2008的连接的呢?在这一篇文章中,我将讲解如何最简单的使用jdbc进行SQL2008的数据库的 ...
- CSS计数器妙用
做web的经常会遇到类似排行榜的需求, 特别是要求前n名的样式和后面人不一样. 通常大多数人对于这个需求的做法都是在后端处理好排名名次, 在前端填入内容, 然后针对前n名做特殊的样式处理. 但是这样有 ...
- dede 标签
◆织梦内容管理系统模板标签代码参考 [Arclist 标记] 这个标记是DedeCms最常用的一个标记,也叫自由列表标记,其中 hotart.coolart.likeart.artlist.imgl ...
- Linux系统部署规范v1.0
Linux系统部署规范v1.0 目的: 1.尽可能减少线上操作: 2.尽可能实现自动化部署: 3.尽可能减少安装服务和启动的服务: 4.尽可能使用安全协议提供服务: 5.尽可能让业务系统单一: 6.尽 ...
- OpenCV中的SVM參数优化
SVM(支持向量机)是机器学习算法里用得最多的一种算法.SVM最经常使用的是用于分类,只是SVM也能够用于回归,我的实验中就是用SVM来实现SVR(支持向量回归). 对于功能这么强的算法,opencv ...