2013-02-02 19:32:44 -05:00
/*
Simple DirectMedia Layer
Copyright ( C ) 1997 - 2012 Sam Lantinga < slouken @ libsdl . org >
This software is provided ' as - is ' , without any express or implied
warranty . In no event will the authors be held liable for any damages
arising from the use of this software .
Permission is granted to anyone to use this software for any purpose ,
including commercial applications , and to alter it and redistribute it
freely , subject to the following restrictions :
1. The origin of this software must not be misrepresented ; you must not
claim that you wrote the original software . If you use this software
in a product , an acknowledgment in the product documentation would be
appreciated but is not required .
2. Altered source versions must be plainly marked as such , and must not be
misrepresented as being the original software .
3. This notice may not be removed or altered from any source distribution .
*/
2014-03-10 01:51:03 -07:00
# include "../../SDL_internal.h"
2013-02-02 19:32:44 -05:00
# if SDL_VIDEO_RENDER_D3D11 && !SDL_RENDER_DISABLED
2014-03-10 01:51:03 -07:00
# define COBJMACROS
2013-02-02 19:32:44 -05:00
# include "../../core/windows/SDL_windows.h"
2013-10-25 20:31:43 -04:00
# include "SDL_hints.h"
2014-03-10 01:51:03 -07:00
# include "SDL_loadso.h"
2013-02-02 19:32:44 -05:00
# include "SDL_syswm.h"
# include "../SDL_sysrender.h"
2014-03-10 17:19:19 -07:00
# include "../SDL_d3dmath.h"
2013-02-02 19:32:44 -05:00
2014-03-10 01:51:03 -07:00
# include <d3d11_1.h>
2013-02-09 11:42:17 -05:00
2013-12-25 13:13:15 -05:00
2014-03-11 12:40:31 -04:00
# ifdef __WINRT__
# include "SDL_render_d3d11_winrthelpers_cpp.h"
# if WINAPI_FAMILY == WINAPI_FAMILY_APP
# include <windows.ui.xaml.media.dxinterop.h>
/* TODO, WinRT, XAML: get the ISwapChainBackgroundPanelNative from something other than a global var */
extern ISwapChainBackgroundPanelNative * WINRT_GlobalSwapChainBackgroundPanelNative ;
# endif /* WINAPI_FAMILY == WINAPI_FAMILY_APP */
# endif /* __WINRT__ */
2014-03-10 12:49:15 -07:00
# define SAFE_RELEASE(X) if ((X)) { IUnknown_Release(SDL_static_cast(IUnknown*, X)); X = NULL; }
2013-02-02 19:32:44 -05:00
2013-11-01 22:54:39 -04:00
2013-12-25 13:13:15 -05:00
/* Vertex shader, common values */
2014-03-10 01:51:03 -07:00
typedef struct
2014-03-09 11:06:11 -07:00
{
2014-03-10 01:51:03 -07:00
Float4X4 model ;
Float4X4 projectionAndView ;
} VertexShaderConstants ;
2013-12-25 13:13:15 -05:00
/* Per-vertex data */
2014-03-10 01:51:03 -07:00
typedef struct
2014-03-09 11:06:11 -07:00
{
2014-03-10 01:51:03 -07:00
Float3 pos ;
Float2 tex ;
Float4 color ;
} VertexPositionColor ;
2013-12-25 13:13:15 -05:00
/* Per-texture data */
typedef struct
{
2014-03-10 01:51:03 -07:00
ID3D11Texture2D * mainTexture ;
ID3D11ShaderResourceView * mainTextureResourceView ;
ID3D11RenderTargetView * mainTextureRenderTargetView ;
ID3D11Texture2D * stagingTexture ;
int lockedTexturePositionX ;
int lockedTexturePositionY ;
2013-12-25 13:13:15 -05:00
D3D11_FILTER scaleMode ;
2014-03-10 05:44:34 -07:00
/* YV12 texture support */
SDL_bool yuv ;
ID3D11Texture2D * mainTextureU ;
ID3D11ShaderResourceView * mainTextureResourceViewU ;
ID3D11Texture2D * mainTextureV ;
ID3D11ShaderResourceView * mainTextureResourceViewV ;
Uint8 * pixels ;
int pitch ;
SDL_Rect locked_rect ;
2013-12-25 13:13:15 -05:00
} D3D11_TextureData ;
/* Private renderer data */
typedef struct
{
2014-03-10 12:49:15 -07:00
void * hDXGIMod ;
2014-03-10 01:51:03 -07:00
void * hD3D11Mod ;
2014-03-10 12:49:15 -07:00
IDXGIFactory2 * dxgiFactory ;
IDXGIAdapter * dxgiAdapter ;
2014-03-10 01:51:03 -07:00
ID3D11Device1 * d3dDevice ;
ID3D11DeviceContext1 * d3dContext ;
IDXGISwapChain1 * swapChain ;
DXGI_SWAP_EFFECT swapEffect ;
ID3D11RenderTargetView * mainRenderTargetView ;
ID3D11RenderTargetView * currentOffscreenRenderTargetView ;
ID3D11InputLayout * inputLayout ;
ID3D11Buffer * vertexBuffer ;
ID3D11VertexShader * vertexShader ;
ID3D11PixelShader * colorPixelShader ;
2014-03-10 05:44:34 -07:00
ID3D11PixelShader * texturePixelShader ;
ID3D11PixelShader * yuvPixelShader ;
2014-03-10 01:51:03 -07:00
ID3D11BlendState * blendModeBlend ;
ID3D11BlendState * blendModeAdd ;
ID3D11BlendState * blendModeMod ;
ID3D11SamplerState * nearestPixelSampler ;
ID3D11SamplerState * linearSampler ;
2013-12-25 13:13:15 -05:00
D3D_FEATURE_LEVEL featureLevel ;
2014-03-10 01:51:03 -07:00
/* Rasterizers */
ID3D11RasterizerState * mainRasterizer ;
ID3D11RasterizerState * clippedRasterizer ;
2013-12-26 10:18:33 -05:00
2014-03-10 01:51:03 -07:00
/* Vertex buffer constants */
2013-12-25 14:17:49 -05:00
VertexShaderConstants vertexShaderConstantsData ;
2014-03-10 01:51:03 -07:00
ID3D11Buffer * vertexShaderConstants ;
/* Cached renderer properties */
DXGI_MODE_ROTATION rotation ;
ID3D11RenderTargetView * currentRenderTargetView ;
ID3D11RasterizerState * currentRasterizerState ;
ID3D11BlendState * currentBlendState ;
ID3D11PixelShader * currentShader ;
ID3D11ShaderResourceView * currentShaderResource ;
ID3D11SamplerState * currentSampler ;
2013-12-25 13:13:15 -05:00
} D3D11_RenderData ;
2013-02-02 19:32:44 -05:00
2013-12-25 13:13:15 -05:00
2014-03-10 01:51:03 -07:00
/* Defined here so we don't have to include uuid.lib */
static const GUID IID_IDXGIFactory2 = { 0x50c83a1c , 0xe072 , 0x4c48 , { 0x87 , 0xb0 , 0x36 , 0x30 , 0xfa , 0x36 , 0xa6 , 0xd0 } } ;
static const GUID IID_IDXGIDevice1 = { 0x77db970f , 0x6276 , 0x48ba , { 0xba , 0x28 , 0x07 , 0x01 , 0x43 , 0xb4 , 0x39 , 0x2c } } ;
static const GUID IID_ID3D11Texture2D = { 0x6f15aaf2 , 0xd208 , 0x4e89 , { 0x9a , 0xb4 , 0x48 , 0x95 , 0x35 , 0xd3 , 0x4f , 0x9c } } ;
static const GUID IID_ID3D11Device1 = { 0xa04bfb29 , 0x08ef , 0x43d6 , { 0xa4 , 0x9c , 0xa9 , 0xbd , 0xbd , 0xcb , 0xe6 , 0x86 } } ;
static const GUID IID_ID3D11DeviceContext1 = { 0xbb2c6faa , 0xb5fb , 0x4082 , { 0x8e , 0x6b , 0x38 , 0x8b , 0x8c , 0xfa , 0x90 , 0xe1 } } ;
static const GUID IID_ID3D11Debug = { 0x79cf2233 , 0x7536 , 0x4948 , { 0x9d , 0x36 , 0x1e , 0x46 , 0x92 , 0xdc , 0x57 , 0x60 } } ;
2013-12-25 21:39:48 -05:00
/* Direct3D 11.x shaders
SDL ' s shaders are compiled into SDL itself , to simplify distribution .
All Direct3D 11. x shaders were compiled with the following :
2014-03-09 11:06:11 -07:00
fxc / E " main " / T " <TYPE> " / Fo " <OUTPUT FILE> " " <INPUT FILE> "
Variables :
- < TYPE > : the type of shader . A table of utilized shader types is
listed below .
- < OUTPUT FILE > : where to store compiled output
- < INPUT FILE > : where to read shader source code from
Shader types :
- ps_4_0_level_9_1 : Pixel shader for Windows 8 + , including Windows RT
- vs_4_0_level_9_1 : Vertex shader for Windows 8 + , including Windows RT
- ps_4_0_level_9_3 : Pixel shader for Windows Phone 8
- vs_4_0_level_9_3 : Vertex shader for Windows Phone 8
Shader object code was converted to a list of DWORDs via the following
* nix style command ( available separately from Windows + MSVC ) :
hexdump - v - e ' 6 / 4 " 0x%08.8x, " " \n " ' < FILE >
*/
# if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
# define D3D11_USE_SHADER_MODEL_4_0_level_9_3
# else
# define D3D11_USE_SHADER_MODEL_4_0_level_9_1
# endif
2014-03-10 05:44:34 -07:00
/* The color-only-rendering pixel shader:
- - - D3D11_PixelShader_Colors . hlsl - - -
struct PixelShaderInput
{
float4 pos : SV_POSITION ;
float2 tex : TEXCOORD0 ;
float4 color : COLOR0 ;
} ;
float4 main ( PixelShaderInput input ) : SV_TARGET
{
return input . color ;
}
*/
# if defined(D3D11_USE_SHADER_MODEL_4_0_level_9_1)
static const DWORD D3D11_PixelShader_Colors [ ] = {
0x43425844 , 0xd74c28fe , 0xa1eb8804 , 0x269d512a , 0x7699723d , 0x00000001 ,
0x00000240 , 0x00000006 , 0x00000038 , 0x00000084 , 0x000000c4 , 0x00000140 ,
0x00000198 , 0x0000020c , 0x396e6f41 , 0x00000044 , 0x00000044 , 0xffff0200 ,
0x00000020 , 0x00000024 , 0x00240000 , 0x00240000 , 0x00240000 , 0x00240000 ,
0x00240000 , 0xffff0200 , 0x0200001f , 0x80000000 , 0xb00f0001 , 0x02000001 ,
0x800f0800 , 0xb0e40001 , 0x0000ffff , 0x52444853 , 0x00000038 , 0x00000040 ,
0x0000000e , 0x03001062 , 0x001010f2 , 0x00000002 , 0x03000065 , 0x001020f2 ,
0x00000000 , 0x05000036 , 0x001020f2 , 0x00000000 , 0x00101e46 , 0x00000002 ,
0x0100003e , 0x54415453 , 0x00000074 , 0x00000002 , 0x00000000 , 0x00000000 ,
0x00000002 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000001 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000002 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x46454452 , 0x00000050 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x0000001c , 0xffff0400 , 0x00000100 , 0x0000001c , 0x7263694d ,
0x666f736f , 0x52282074 , 0x4c482029 , 0x53204c53 , 0x65646168 , 0x6f432072 ,
0x6c69706d , 0x39207265 , 0x2e30332e , 0x30303239 , 0x3336312e , 0xab003438 ,
0x4e475349 , 0x0000006c , 0x00000003 , 0x00000008 , 0x00000050 , 0x00000000 ,
0x00000001 , 0x00000003 , 0x00000000 , 0x0000000f , 0x0000005c , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000001 , 0x00000003 , 0x00000065 , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000002 , 0x00000f0f , 0x505f5653 , 0x5449534f ,
0x004e4f49 , 0x43584554 , 0x44524f4f , 0x4c4f4300 , 0xab00524f , 0x4e47534f ,
0x0000002c , 0x00000001 , 0x00000008 , 0x00000020 , 0x00000000 , 0x00000000 ,
0x00000003 , 0x00000000 , 0x0000000f , 0x545f5653 , 0x45475241 , 0xabab0054
} ;
# elif defined(D3D11_USE_SHADER_MODEL_4_0_level_9_3)
static const DWORD D3D11_PixelShader_Colors [ ] = {
0x43425844 , 0x93f6ccfc , 0x5f919270 , 0x7a11aa4f , 0x9148e931 , 0x00000001 ,
0x00000240 , 0x00000006 , 0x00000038 , 0x00000084 , 0x000000c4 , 0x00000140 ,
0x00000198 , 0x0000020c , 0x396e6f41 , 0x00000044 , 0x00000044 , 0xffff0200 ,
0x00000020 , 0x00000024 , 0x00240000 , 0x00240000 , 0x00240000 , 0x00240000 ,
0x00240000 , 0xffff0201 , 0x0200001f , 0x80000000 , 0xb00f0001 , 0x02000001 ,
0x800f0800 , 0xb0e40001 , 0x0000ffff , 0x52444853 , 0x00000038 , 0x00000040 ,
0x0000000e , 0x03001062 , 0x001010f2 , 0x00000002 , 0x03000065 , 0x001020f2 ,
0x00000000 , 0x05000036 , 0x001020f2 , 0x00000000 , 0x00101e46 , 0x00000002 ,
0x0100003e , 0x54415453 , 0x00000074 , 0x00000002 , 0x00000000 , 0x00000000 ,
0x00000002 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000001 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000002 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x46454452 , 0x00000050 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x0000001c , 0xffff0400 , 0x00000100 , 0x0000001c , 0x7263694d ,
0x666f736f , 0x52282074 , 0x4c482029 , 0x53204c53 , 0x65646168 , 0x6f432072 ,
0x6c69706d , 0x39207265 , 0x2e30332e , 0x30303239 , 0x3336312e , 0xab003438 ,
0x4e475349 , 0x0000006c , 0x00000003 , 0x00000008 , 0x00000050 , 0x00000000 ,
0x00000001 , 0x00000003 , 0x00000000 , 0x0000000f , 0x0000005c , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000001 , 0x00000003 , 0x00000065 , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000002 , 0x00000f0f , 0x505f5653 , 0x5449534f ,
0x004e4f49 , 0x43584554 , 0x44524f4f , 0x4c4f4300 , 0xab00524f , 0x4e47534f ,
0x0000002c , 0x00000001 , 0x00000008 , 0x00000020 , 0x00000000 , 0x00000000 ,
0x00000003 , 0x00000000 , 0x0000000f , 0x545f5653 , 0x45475241 , 0xabab0054
} ;
# else
# error "An appropriate 'colors' pixel shader is not defined."
# endif
2014-03-09 11:06:11 -07:00
/* The texture-rendering pixel shader:
- - - D3D11_PixelShader_Textures . hlsl - - -
Texture2D theTexture : register ( t0 ) ;
SamplerState theSampler : register ( s0 ) ;
struct PixelShaderInput
{
float4 pos : SV_POSITION ;
float2 tex : TEXCOORD0 ;
float4 color : COLOR0 ;
} ;
float4 main ( PixelShaderInput input ) : SV_TARGET
{
return theTexture . Sample ( theSampler , input . tex ) * input . color ;
}
*/
# if defined(D3D11_USE_SHADER_MODEL_4_0_level_9_1)
static const DWORD D3D11_PixelShader_Textures [ ] = {
0x43425844 , 0x6299b59f , 0x155258f2 , 0x873ab86a , 0xfcbb6dcd , 0x00000001 ,
0x00000330 , 0x00000006 , 0x00000038 , 0x000000c0 , 0x0000015c , 0x000001d8 ,
0x00000288 , 0x000002fc , 0x396e6f41 , 0x00000080 , 0x00000080 , 0xffff0200 ,
0x00000058 , 0x00000028 , 0x00280000 , 0x00280000 , 0x00280000 , 0x00240001 ,
0x00280000 , 0x00000000 , 0xffff0200 , 0x0200001f , 0x80000000 , 0xb0030000 ,
0x0200001f , 0x80000000 , 0xb00f0001 , 0x0200001f , 0x90000000 , 0xa00f0800 ,
0x03000042 , 0x800f0000 , 0xb0e40000 , 0xa0e40800 , 0x03000005 , 0x800f0000 ,
0x80e40000 , 0xb0e40001 , 0x02000001 , 0x800f0800 , 0x80e40000 , 0x0000ffff ,
0x52444853 , 0x00000094 , 0x00000040 , 0x00000025 , 0x0300005a , 0x00106000 ,
0x00000000 , 0x04001858 , 0x00107000 , 0x00000000 , 0x00005555 , 0x03001062 ,
0x00101032 , 0x00000001 , 0x03001062 , 0x001010f2 , 0x00000002 , 0x03000065 ,
0x001020f2 , 0x00000000 , 0x02000068 , 0x00000001 , 0x09000045 , 0x001000f2 ,
0x00000000 , 0x00101046 , 0x00000001 , 0x00107e46 , 0x00000000 , 0x00106000 ,
0x00000000 , 0x07000038 , 0x001020f2 , 0x00000000 , 0x00100e46 , 0x00000000 ,
0x00101e46 , 0x00000002 , 0x0100003e , 0x54415453 , 0x00000074 , 0x00000003 ,
0x00000001 , 0x00000000 , 0x00000003 , 0x00000001 , 0x00000000 , 0x00000000 ,
0x00000001 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000001 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000001 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x46454452 , 0x000000a8 ,
0x00000000 , 0x00000000 , 0x00000002 , 0x0000001c , 0xffff0400 , 0x00000100 ,
0x00000072 , 0x0000005c , 0x00000003 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000001 , 0x00000001 , 0x00000067 , 0x00000002 , 0x00000005 ,
0x00000004 , 0xffffffff , 0x00000000 , 0x00000001 , 0x0000000d , 0x53656874 ,
0x6c706d61 , 0x74007265 , 0x65546568 , 0x72757478 , 0x694d0065 , 0x736f7263 ,
0x2074666f , 0x20295228 , 0x4c534c48 , 0x61685320 , 0x20726564 , 0x706d6f43 ,
0x72656c69 , 0x332e3920 , 0x32392e30 , 0x312e3030 , 0x34383336 , 0xababab00 ,
0x4e475349 , 0x0000006c , 0x00000003 , 0x00000008 , 0x00000050 , 0x00000000 ,
0x00000001 , 0x00000003 , 0x00000000 , 0x0000000f , 0x0000005c , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000001 , 0x00000303 , 0x00000065 , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000002 , 0x00000f0f , 0x505f5653 , 0x5449534f ,
0x004e4f49 , 0x43584554 , 0x44524f4f , 0x4c4f4300 , 0xab00524f , 0x4e47534f ,
0x0000002c , 0x00000001 , 0x00000008 , 0x00000020 , 0x00000000 , 0x00000000 ,
0x00000003 , 0x00000000 , 0x0000000f , 0x545f5653 , 0x45475241 , 0xabab0054
2013-12-25 21:39:48 -05:00
} ;
# elif defined(D3D11_USE_SHADER_MODEL_4_0_level_9_3)
static const DWORD D3D11_PixelShader_Textures [ ] = {
2014-03-09 11:06:11 -07:00
0x43425844 , 0x5876569a , 0x01b6c87e , 0x8447454f , 0xc7f3ef10 , 0x00000001 ,
0x00000330 , 0x00000006 , 0x00000038 , 0x000000c0 , 0x0000015c , 0x000001d8 ,
0x00000288 , 0x000002fc , 0x396e6f41 , 0x00000080 , 0x00000080 , 0xffff0200 ,
0x00000058 , 0x00000028 , 0x00280000 , 0x00280000 , 0x00280000 , 0x00240001 ,
0x00280000 , 0x00000000 , 0xffff0201 , 0x0200001f , 0x80000000 , 0xb0030000 ,
0x0200001f , 0x80000000 , 0xb00f0001 , 0x0200001f , 0x90000000 , 0xa00f0800 ,
0x03000042 , 0x800f0000 , 0xb0e40000 , 0xa0e40800 , 0x03000005 , 0x800f0000 ,
0x80e40000 , 0xb0e40001 , 0x02000001 , 0x800f0800 , 0x80e40000 , 0x0000ffff ,
0x52444853 , 0x00000094 , 0x00000040 , 0x00000025 , 0x0300005a , 0x00106000 ,
0x00000000 , 0x04001858 , 0x00107000 , 0x00000000 , 0x00005555 , 0x03001062 ,
0x00101032 , 0x00000001 , 0x03001062 , 0x001010f2 , 0x00000002 , 0x03000065 ,
0x001020f2 , 0x00000000 , 0x02000068 , 0x00000001 , 0x09000045 , 0x001000f2 ,
0x00000000 , 0x00101046 , 0x00000001 , 0x00107e46 , 0x00000000 , 0x00106000 ,
0x00000000 , 0x07000038 , 0x001020f2 , 0x00000000 , 0x00100e46 , 0x00000000 ,
0x00101e46 , 0x00000002 , 0x0100003e , 0x54415453 , 0x00000074 , 0x00000003 ,
0x00000001 , 0x00000000 , 0x00000003 , 0x00000001 , 0x00000000 , 0x00000000 ,
0x00000001 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000001 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000001 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x46454452 , 0x000000a8 ,
0x00000000 , 0x00000000 , 0x00000002 , 0x0000001c , 0xffff0400 , 0x00000100 ,
0x00000072 , 0x0000005c , 0x00000003 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000001 , 0x00000001 , 0x00000067 , 0x00000002 , 0x00000005 ,
0x00000004 , 0xffffffff , 0x00000000 , 0x00000001 , 0x0000000d , 0x53656874 ,
0x6c706d61 , 0x74007265 , 0x65546568 , 0x72757478 , 0x694d0065 , 0x736f7263 ,
0x2074666f , 0x20295228 , 0x4c534c48 , 0x61685320 , 0x20726564 , 0x706d6f43 ,
0x72656c69 , 0x332e3920 , 0x32392e30 , 0x312e3030 , 0x34383336 , 0xababab00 ,
0x4e475349 , 0x0000006c , 0x00000003 , 0x00000008 , 0x00000050 , 0x00000000 ,
0x00000001 , 0x00000003 , 0x00000000 , 0x0000000f , 0x0000005c , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000001 , 0x00000303 , 0x00000065 , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000002 , 0x00000f0f , 0x505f5653 , 0x5449534f ,
0x004e4f49 , 0x43584554 , 0x44524f4f , 0x4c4f4300 , 0xab00524f , 0x4e47534f ,
0x0000002c , 0x00000001 , 0x00000008 , 0x00000020 , 0x00000000 , 0x00000000 ,
2013-12-25 21:39:48 -05:00
0x00000003 , 0x00000000 , 0x0000000f , 0x545f5653 , 0x45475241 , 0xabab0054
} ;
# else
# error "An appropriate 'textures' pixel shader is not defined"
# endif
2014-03-10 05:44:34 -07:00
/* The yuv-rendering pixel shader:
2013-12-25 21:39:48 -05:00
2014-03-10 05:44:34 -07:00
- - - D3D11_PixelShader_YUV . hlsl - - -
Texture2D theTextureY : register ( t0 ) ;
Texture2D theTextureU : register ( t1 ) ;
Texture2D theTextureV : register ( t2 ) ;
SamplerState theSampler : register ( s0 ) ;
struct PixelShaderInput
{
float4 pos : SV_POSITION ;
float2 tex : TEXCOORD0 ;
float4 color : COLOR0 ;
} ;
2014-03-10 12:49:15 -07:00
float4 main ( PixelShaderInput input ) : SV_TARGET
{
const float3 offset = { - 0.0625 , - 0.5 , - 0.5 } ;
const float3 Rcoeff = { 1.164 , 0.000 , 1.596 } ;
const float3 Gcoeff = { 1.164 , - 0.391 , - 0.813 } ;
const float3 Bcoeff = { 1.164 , 2.018 , 0.000 } ;
float4 Output ;
float3 yuv ;
yuv . x = theTextureY . Sample ( theSampler , input . tex ) . r ;
yuv . y = theTextureU . Sample ( theSampler , input . tex ) . r ;
yuv . z = theTextureV . Sample ( theSampler , input . tex ) . r ;
yuv + = offset ;
Output . r = dot ( yuv , Rcoeff ) ;
Output . g = dot ( yuv , Gcoeff ) ;
Output . b = dot ( yuv , Bcoeff ) ;
Output . a = 1.0f ;
return Output * input . color ;
}
2014-03-09 11:06:11 -07:00
*/
2013-12-25 21:39:48 -05:00
# if defined(D3D11_USE_SHADER_MODEL_4_0_level_9_1)
2014-03-10 05:44:34 -07:00
static const DWORD D3D11_PixelShader_YUV [ ] = {
2014-03-10 12:49:15 -07:00
0x43425844 , 0x04e69cba , 0x74ce6dd2 , 0x7fcf84cb , 0x3003d677 , 0x00000001 ,
0x000005e8 , 0x00000006 , 0x00000038 , 0x000001dc , 0x000003bc , 0x00000438 ,
0x00000540 , 0x000005b4 , 0x396e6f41 , 0x0000019c , 0x0000019c , 0xffff0200 ,
0x0000016c , 0x00000030 , 0x00300000 , 0x00300000 , 0x00300000 , 0x00240003 ,
0x00300000 , 0x00000000 , 0x00010001 , 0x00020002 , 0xffff0200 , 0x05000051 ,
0xa00f0000 , 0xbd800000 , 0xbf000000 , 0xbf000000 , 0x3f800000 , 0x05000051 ,
0xa00f0001 , 0x3f94fdf4 , 0x3fcc49ba , 0x00000000 , 0x00000000 , 0x05000051 ,
0xa00f0002 , 0x3f94fdf4 , 0xbec83127 , 0xbf5020c5 , 0x00000000 , 0x05000051 ,
0xa00f0003 , 0x3f94fdf4 , 0x400126e9 , 0x00000000 , 0x00000000 , 0x0200001f ,
0x80000000 , 0xb0030000 , 0x0200001f , 0x80000000 , 0xb00f0001 , 0x0200001f ,
0x90000000 , 0xa00f0800 , 0x0200001f , 0x90000000 , 0xa00f0801 , 0x0200001f ,
0x90000000 , 0xa00f0802 , 0x03000042 , 0x800f0000 , 0xb0e40000 , 0xa0e40800 ,
0x03000042 , 0x800f0001 , 0xb0e40000 , 0xa0e40801 , 0x03000042 , 0x800f0002 ,
0xb0e40000 , 0xa0e40802 , 0x02000001 , 0x80020000 , 0x80000001 , 0x02000001 ,
0x80040000 , 0x80000002 , 0x03000002 , 0x80070000 , 0x80e40000 , 0xa0e40000 ,
0x03000005 , 0x80080000 , 0x80000000 , 0xa0000001 , 0x04000004 , 0x80010001 ,
0x80aa0000 , 0xa0550001 , 0x80ff0000 , 0x03000008 , 0x80020001 , 0x80e40000 ,
0xa0e40002 , 0x0400005a , 0x80040001 , 0x80e40000 , 0xa0e40003 , 0xa0aa0003 ,
0x02000001 , 0x80080001 , 0xa0ff0000 , 0x03000005 , 0x800f0000 , 0x80e40001 ,
0xb0e40001 , 0x02000001 , 0x800f0800 , 0x80e40000 , 0x0000ffff , 0x52444853 ,
0x000001d8 , 0x00000040 , 0x00000076 , 0x0300005a , 0x00106000 , 0x00000000 ,
0x04001858 , 0x00107000 , 0x00000000 , 0x00005555 , 0x04001858 , 0x00107000 ,
0x00000001 , 0x00005555 , 0x04001858 , 0x00107000 , 0x00000002 , 0x00005555 ,
0x03001062 , 0x00101032 , 0x00000001 , 0x03001062 , 0x001010f2 , 0x00000002 ,
0x03000065 , 0x001020f2 , 0x00000000 , 0x02000068 , 0x00000002 , 0x09000045 ,
0x001000f2 , 0x00000000 , 0x00101046 , 0x00000001 , 0x00107e46 , 0x00000000 ,
0x00106000 , 0x00000000 , 0x09000045 , 0x001000f2 , 0x00000001 , 0x00101046 ,
0x00000001 , 0x00107e46 , 0x00000001 , 0x00106000 , 0x00000000 , 0x05000036 ,
0x00100022 , 0x00000000 , 0x0010000a , 0x00000001 , 0x09000045 , 0x001000f2 ,
0x00000001 , 0x00101046 , 0x00000001 , 0x00107e46 , 0x00000002 , 0x00106000 ,
0x00000000 , 0x05000036 , 0x00100042 , 0x00000000 , 0x0010000a , 0x00000001 ,
0x0a000000 , 0x00100072 , 0x00000000 , 0x00100246 , 0x00000000 , 0x00004002 ,
0xbd800000 , 0xbf000000 , 0xbf000000 , 0x00000000 , 0x0a00000f , 0x00100012 ,
0x00000001 , 0x00100086 , 0x00000000 , 0x00004002 , 0x3f94fdf4 , 0x3fcc49ba ,
0x00000000 , 0x00000000 , 0x0a000010 , 0x00100022 , 0x00000001 , 0x00100246 ,
0x00000000 , 0x00004002 , 0x3f94fdf4 , 0xbec83127 , 0xbf5020c5 , 0x00000000 ,
0x0a00000f , 0x00100042 , 0x00000001 , 0x00100046 , 0x00000000 , 0x00004002 ,
0x3f94fdf4 , 0x400126e9 , 0x00000000 , 0x00000000 , 0x05000036 , 0x00100082 ,
0x00000001 , 0x00004001 , 0x3f800000 , 0x07000038 , 0x001020f2 , 0x00000000 ,
0x00100e46 , 0x00000001 , 0x00101e46 , 0x00000002 , 0x0100003e , 0x54415453 ,
0x00000074 , 0x0000000c , 0x00000002 , 0x00000000 , 0x00000003 , 0x00000005 ,
0x00000000 , 0x00000000 , 0x00000001 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000003 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000003 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x46454452 , 0x00000100 , 0x00000000 , 0x00000000 , 0x00000004 , 0x0000001c ,
0xffff0400 , 0x00000100 , 0x000000cb , 0x0000009c , 0x00000003 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000001 , 0x00000001 , 0x000000a7 ,
0x00000002 , 0x00000005 , 0x00000004 , 0xffffffff , 0x00000000 , 0x00000001 ,
0x0000000d , 0x000000b3 , 0x00000002 , 0x00000005 , 0x00000004 , 0xffffffff ,
0x00000001 , 0x00000001 , 0x0000000d , 0x000000bf , 0x00000002 , 0x00000005 ,
0x00000004 , 0xffffffff , 0x00000002 , 0x00000001 , 0x0000000d , 0x53656874 ,
0x6c706d61 , 0x74007265 , 0x65546568 , 0x72757478 , 0x74005965 , 0x65546568 ,
0x72757478 , 0x74005565 , 0x65546568 , 0x72757478 , 0x4d005665 , 0x6f726369 ,
0x74666f73 , 0x29522820 , 0x534c4820 , 0x6853204c , 0x72656461 , 0x6d6f4320 ,
0x656c6970 , 0x2e362072 , 0x36392e33 , 0x312e3030 , 0x34383336 , 0xababab00 ,
0x4e475349 , 0x0000006c , 0x00000003 , 0x00000008 , 0x00000050 , 0x00000000 ,
0x00000001 , 0x00000003 , 0x00000000 , 0x0000000f , 0x0000005c , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000001 , 0x00000303 , 0x00000065 , 0x00000000 ,
0x00000000 , 0x00000003 , 0x00000002 , 0x00000f0f , 0x505f5653 , 0x5449534f ,
0x004e4f49 , 0x43584554 , 0x44524f4f , 0x4c4f4300 , 0xab00524f , 0x4e47534f ,
0x0000002c , 0x00000001 , 0x00000008 , 0x00000020 , 0x00000000 , 0x00000000 ,
2014-03-09 11:06:11 -07:00
0x00000003 , 0x00000000 , 0x0000000f , 0x545f5653 , 0x45475241 , 0xabab0054
} ;
# elif defined(D3D11_USE_SHADER_MODEL_4_0_level_9_3)
2014-03-10 05:44:34 -07:00
static const DWORD D3D11_PixelShader_YUV [ ] = {
2014-03-10 12:49:15 -07:00
0x43425844 , 0xe6d969fc , 0x63cac33c , 0xa4926502 , 0x5d788135 , 0x00000001 ,
0x000005c0 , 0x00000006 , 0x00000038 , 0x000001b4 , 0x00000394 , 0x00000410 ,
0x00000518 , 0x0000058c , 0x396e6f41 , 0x00000174 , 0x00000174 , 0xffff0200 ,
0x00000144 , 0x00000030 , 0x00300000 , 0x00300000 , 0x00300000 , 0x00240003 ,
0x00300000 , 0x00000000 , 0x00010001 , 0x00020002 , 0xffff0201 , 0x05000051 ,
0xa00f0000 , 0xbd800000 , 0xbf000000 , 0x3f800000 , 0x00000000 , 0x05000051 ,
0xa00f0001 , 0x3f94fdf4 , 0x3fcc49ba , 0x00000000 , 0x400126e9 , 0x05000051 ,
0xa00f0002 , 0x3f94fdf4 , 0xbec83127 , 0xbf5020c5 , 0x00000000 , 0x0200001f ,
0x80000000 , 0xb0030000 , 0x0200001f , 0x80000000 , 0xb00f0001 , 0x0200001f ,
0x90000000 , 0xa00f0800 , 0x0200001f , 0x90000000 , 0xa00f0801 , 0x0200001f ,
0x90000000 , 0xa00f0802 , 0x03000042 , 0x800f0000 , 0xb0e40000 , 0xa0e40801 ,
0x03000042 , 0x800f0001 , 0xb0e40000 , 0xa0e40800 , 0x02000001 , 0x80020001 ,
0x80000000 , 0x03000042 , 0x800f0000 , 0xb0e40000 , 0xa0e40802 , 0x02000001 ,
0x80040001 , 0x80000000 , 0x03000002 , 0x80070000 , 0x80e40001 , 0xa0d40000 ,
0x0400005a , 0x80010001 , 0x80e80000 , 0xa0e40001 , 0xa0aa0001 , 0x03000008 ,
0x80020001 , 0x80e40000 , 0xa0e40002 , 0x0400005a , 0x80040001 , 0x80e40000 ,
0xa0ec0001 , 0xa0aa0001 , 0x02000001 , 0x80080001 , 0xa0aa0000 , 0x03000005 ,
0x800f0000 , 0x80e40001 , 0xb0e40001 , 0x02000001 , 0x800f0800 , 0x80e40000 ,
0x0000ffff , 0x52444853 , 0x000001d8 , 0x00000040 , 0x00000076 , 0x0300005a ,
0x00106000 , 0x00000000 , 0x04001858 , 0x00107000 , 0x00000000 , 0x00005555 ,
0x04001858 , 0x00107000 , 0x00000001 , 0x00005555 , 0x04001858 , 0x00107000 ,
0x00000002 , 0x00005555 , 0x03001062 , 0x00101032 , 0x00000001 , 0x03001062 ,
0x001010f2 , 0x00000002 , 0x03000065 , 0x001020f2 , 0x00000000 , 0x02000068 ,
0x00000002 , 0x09000045 , 0x001000f2 , 0x00000000 , 0x00101046 , 0x00000001 ,
0x00107e46 , 0x00000000 , 0x00106000 , 0x00000000 , 0x09000045 , 0x001000f2 ,
0x00000001 , 0x00101046 , 0x00000001 , 0x00107e46 , 0x00000001 , 0x00106000 ,
0x00000000 , 0x05000036 , 0x00100022 , 0x00000000 , 0x0010000a , 0x00000001 ,
0x09000045 , 0x001000f2 , 0x00000001 , 0x00101046 , 0x00000001 , 0x00107e46 ,
0x00000002 , 0x00106000 , 0x00000000 , 0x05000036 , 0x00100042 , 0x00000000 ,
0x0010000a , 0x00000001 , 0x0a000000 , 0x00100072 , 0x00000000 , 0x00100246 ,
0x00000000 , 0x00004002 , 0xbd800000 , 0xbf000000 , 0xbf000000 , 0x00000000 ,
0x0a00000f , 0x00100012 , 0x00000001 , 0x00100086 , 0x00000000 , 0x00004002 ,
0x3f94fdf4 , 0x3fcc49ba , 0x00000000 , 0x00000000 , 0x0a000010 , 0x00100022 ,
0x00000001 , 0x00100246 , 0x00000000 , 0x00004002 , 0x3f94fdf4 , 0xbec83127 ,
0xbf5020c5 , 0x00000000 , 0x0a00000f , 0x00100042 , 0x00000001 , 0x00100046 ,
0x00000000 , 0x00004002 , 0x3f94fdf4 , 0x400126e9 , 0x00000000 , 0x00000000 ,
0x05000036 , 0x00100082 , 0x00000001 , 0x00004001 , 0x3f800000 , 0x07000038 ,
0x001020f2 , 0x00000000 , 0x00100e46 , 0x00000001 , 0x00101e46 , 0x00000002 ,
0x0100003e , 0x54415453 , 0x00000074 , 0x0000000c , 0x00000002 , 0x00000000 ,
0x00000003 , 0x00000005 , 0x00000000 , 0x00000000 , 0x00000001 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000003 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000003 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x46454452 , 0x00000100 , 0x00000000 , 0x00000000 ,
0x00000004 , 0x0000001c , 0xffff0400 , 0x00000100 , 0x000000cb , 0x0000009c ,
0x00000003 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000001 ,
0x00000001 , 0x000000a7 , 0x00000002 , 0x00000005 , 0x00000004 , 0xffffffff ,
0x00000000 , 0x00000001 , 0x0000000d , 0x000000b3 , 0x00000002 , 0x00000005 ,
0x00000004 , 0xffffffff , 0x00000001 , 0x00000001 , 0x0000000d , 0x000000bf ,
0x00000002 , 0x00000005 , 0x00000004 , 0xffffffff , 0x00000002 , 0x00000001 ,
0x0000000d , 0x53656874 , 0x6c706d61 , 0x74007265 , 0x65546568 , 0x72757478 ,
0x74005965 , 0x65546568 , 0x72757478 , 0x74005565 , 0x65546568 , 0x72757478 ,
0x4d005665 , 0x6f726369 , 0x74666f73 , 0x29522820 , 0x534c4820 , 0x6853204c ,
0x72656461 , 0x6d6f4320 , 0x656c6970 , 0x2e362072 , 0x36392e33 , 0x312e3030 ,
0x34383336 , 0xababab00 , 0x4e475349 , 0x0000006c , 0x00000003 , 0x00000008 ,
0x00000050 , 0x00000000 , 0x00000001 , 0x00000003 , 0x00000000 , 0x0000000f ,
0x0000005c , 0x00000000 , 0x00000000 , 0x00000003 , 0x00000001 , 0x00000303 ,
0x00000065 , 0x00000000 , 0x00000000 , 0x00000003 , 0x00000002 , 0x00000f0f ,
0x505f5653 , 0x5449534f , 0x004e4f49 , 0x43584554 , 0x44524f4f , 0x4c4f4300 ,
0xab00524f , 0x4e47534f , 0x0000002c , 0x00000001 , 0x00000008 , 0x00000020 ,
0x00000000 , 0x00000000 , 0x00000003 , 0x00000000 , 0x0000000f , 0x545f5653 ,
2014-03-10 05:44:34 -07:00
0x45475241 , 0xabab0054
2014-03-09 11:06:11 -07:00
} ;
2013-12-25 21:39:48 -05:00
# else
2014-03-10 05:44:34 -07:00
# error "An appropriate 'yuv' pixel shader is not defined."
2013-12-25 21:39:48 -05:00
# endif
/* The sole vertex shader:
- - - D3D11_VertexShader . hlsl - - -
2014-03-09 11:06:11 -07:00
# pragma pack_matrix( row_major )
cbuffer VertexShaderConstants : register ( b0 )
{
matrix model ;
matrix projectionAndView ;
} ;
struct VertexShaderInput
{
float3 pos : POSITION ;
float2 tex : TEXCOORD0 ;
float4 color : COLOR0 ;
} ;
struct VertexShaderOutput
{
float4 pos : SV_POSITION ;
float2 tex : TEXCOORD0 ;
float4 color : COLOR0 ;
} ;
VertexShaderOutput main ( VertexShaderInput input )
{
VertexShaderOutput output ;
float4 pos = float4 ( input . pos , 1.0f ) ;
// Transform the vertex position into projected space.
pos = mul ( pos , model ) ;
pos = mul ( pos , projectionAndView ) ;
output . pos = pos ;
// Pass through texture coordinates and color values without transformation
output . tex = input . tex ;
output . color = input . color ;
return output ;
}
2013-12-25 21:39:48 -05:00
*/
# if defined(D3D11_USE_SHADER_MODEL_4_0_level_9_1)
static const DWORD D3D11_VertexShader [ ] = {
2014-03-09 11:06:11 -07:00
0x43425844 , 0x62dfae5f , 0x3e8bd8df , 0x9ec97127 , 0x5044eefb , 0x00000001 ,
0x00000598 , 0x00000006 , 0x00000038 , 0x0000016c , 0x00000334 , 0x000003b0 ,
0x000004b4 , 0x00000524 , 0x396e6f41 , 0x0000012c , 0x0000012c , 0xfffe0200 ,
0x000000f8 , 0x00000034 , 0x00240001 , 0x00300000 , 0x00300000 , 0x00240000 ,
0x00300001 , 0x00000000 , 0x00010008 , 0x00000000 , 0x00000000 , 0xfffe0200 ,
0x0200001f , 0x80000005 , 0x900f0000 , 0x0200001f , 0x80010005 , 0x900f0001 ,
0x0200001f , 0x80020005 , 0x900f0002 , 0x03000005 , 0x800f0000 , 0x90550000 ,
0xa0e40002 , 0x04000004 , 0x800f0000 , 0x90000000 , 0xa0e40001 , 0x80e40000 ,
0x04000004 , 0x800f0000 , 0x90aa0000 , 0xa0e40003 , 0x80e40000 , 0x03000002 ,
0x800f0000 , 0x80e40000 , 0xa0e40004 , 0x03000005 , 0x800f0001 , 0x80550000 ,
0xa0e40006 , 0x04000004 , 0x800f0001 , 0x80000000 , 0xa0e40005 , 0x80e40001 ,
0x04000004 , 0x800f0001 , 0x80aa0000 , 0xa0e40007 , 0x80e40001 , 0x04000004 ,
0x800f0000 , 0x80ff0000 , 0xa0e40008 , 0x80e40001 , 0x04000004 , 0xc0030000 ,
0x80ff0000 , 0xa0e40000 , 0x80e40000 , 0x02000001 , 0xc00c0000 , 0x80e40000 ,
0x02000001 , 0xe0030000 , 0x90e40001 , 0x02000001 , 0xe00f0001 , 0x90e40002 ,
0x0000ffff , 0x52444853 , 0x000001c0 , 0x00010040 , 0x00000070 , 0x04000059 ,
0x00208e46 , 0x00000000 , 0x00000008 , 0x0300005f , 0x00101072 , 0x00000000 ,
0x0300005f , 0x00101032 , 0x00000001 , 0x0300005f , 0x001010f2 , 0x00000002 ,
0x04000067 , 0x001020f2 , 0x00000000 , 0x00000001 , 0x03000065 , 0x00102032 ,
0x00000001 , 0x03000065 , 0x001020f2 , 0x00000002 , 0x02000068 , 0x00000002 ,
0x08000038 , 0x001000f2 , 0x00000000 , 0x00101556 , 0x00000000 , 0x00208e46 ,
0x00000000 , 0x00000001 , 0x0a000032 , 0x001000f2 , 0x00000000 , 0x00101006 ,
0x00000000 , 0x00208e46 , 0x00000000 , 0x00000000 , 0x00100e46 , 0x00000000 ,
0x0a000032 , 0x001000f2 , 0x00000000 , 0x00101aa6 , 0x00000000 , 0x00208e46 ,
0x00000000 , 0x00000002 , 0x00100e46 , 0x00000000 , 0x08000000 , 0x001000f2 ,
0x00000000 , 0x00100e46 , 0x00000000 , 0x00208e46 , 0x00000000 , 0x00000003 ,
0x08000038 , 0x001000f2 , 0x00000001 , 0x00100556 , 0x00000000 , 0x00208e46 ,
0x00000000 , 0x00000005 , 0x0a000032 , 0x001000f2 , 0x00000001 , 0x00100006 ,
0x00000000 , 0x00208e46 , 0x00000000 , 0x00000004 , 0x00100e46 , 0x00000001 ,
0x0a000032 , 0x001000f2 , 0x00000001 , 0x00100aa6 , 0x00000000 , 0x00208e46 ,
0x00000000 , 0x00000006 , 0x00100e46 , 0x00000001 , 0x0a000032 , 0x001020f2 ,
0x00000000 , 0x00100ff6 , 0x00000000 , 0x00208e46 , 0x00000000 , 0x00000007 ,
0x00100e46 , 0x00000001 , 0x05000036 , 0x00102032 , 0x00000001 , 0x00101046 ,
0x00000001 , 0x05000036 , 0x001020f2 , 0x00000002 , 0x00101e46 , 0x00000002 ,
0x0100003e , 0x54415453 , 0x00000074 , 0x0000000b , 0x00000002 , 0x00000000 ,
0x00000006 , 0x00000003 , 0x00000000 , 0x00000000 , 0x00000001 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000003 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x46454452 , 0x000000fc , 0x00000001 , 0x00000054 ,
0x00000001 , 0x0000001c , 0xfffe0400 , 0x00000100 , 0x000000c6 , 0x0000003c ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000001 ,
0x00000001 , 0x74726556 , 0x68537865 , 0x72656461 , 0x736e6f43 , 0x746e6174 ,
0xabab0073 , 0x0000003c , 0x00000002 , 0x0000006c , 0x00000080 , 0x00000000 ,
0x00000000 , 0x0000009c , 0x00000000 , 0x00000040 , 0x00000002 , 0x000000a4 ,
0x00000000 , 0x000000b4 , 0x00000040 , 0x00000040 , 0x00000002 , 0x000000a4 ,
0x00000000 , 0x65646f6d , 0xabab006c , 0x00030002 , 0x00040004 , 0x00000000 ,
0x00000000 , 0x6a6f7270 , 0x69746365 , 0x6e416e6f , 0x65695664 , 0x694d0077 ,
0x736f7263 , 0x2074666f , 0x20295228 , 0x4c534c48 , 0x61685320 , 0x20726564 ,
0x706d6f43 , 0x72656c69 , 0x332e3920 , 0x32392e30 , 0x312e3030 , 0x34383336 ,
0xababab00 , 0x4e475349 , 0x00000068 , 0x00000003 , 0x00000008 , 0x00000050 ,
0x00000000 , 0x00000000 , 0x00000003 , 0x00000000 , 0x00000707 , 0x00000059 ,
0x00000000 , 0x00000000 , 0x00000003 , 0x00000001 , 0x00000303 , 0x00000062 ,
0x00000000 , 0x00000000 , 0x00000003 , 0x00000002 , 0x00000f0f , 0x49534f50 ,
0x4e4f4954 , 0x58455400 , 0x524f4f43 , 0x4f430044 , 0x00524f4c , 0x4e47534f ,
0x0000006c , 0x00000003 , 0x00000008 , 0x00000050 , 0x00000000 , 0x00000001 ,
0x00000003 , 0x00000000 , 0x0000000f , 0x0000005c , 0x00000000 , 0x00000000 ,
0x00000003 , 0x00000001 , 0x00000c03 , 0x00000065 , 0x00000000 , 0x00000000 ,
0x00000003 , 0x00000002 , 0x0000000f , 0x505f5653 , 0x5449534f , 0x004e4f49 ,
2013-12-26 11:03:43 -05:00
0x43584554 , 0x44524f4f , 0x4c4f4300 , 0xab00524f
2013-12-25 21:39:48 -05:00
} ;
# elif defined(D3D11_USE_SHADER_MODEL_4_0_level_9_3)
static const DWORD D3D11_VertexShader [ ] = {
2014-03-09 11:06:11 -07:00
0x43425844 , 0x01a24e41 , 0x696af551 , 0x4b2a87d1 , 0x82ea03f6 , 0x00000001 ,
0x00000598 , 0x00000006 , 0x00000038 , 0x0000016c , 0x00000334 , 0x000003b0 ,
0x000004b4 , 0x00000524 , 0x396e6f41 , 0x0000012c , 0x0000012c , 0xfffe0200 ,
0x000000f8 , 0x00000034 , 0x00240001 , 0x00300000 , 0x00300000 , 0x00240000 ,
0x00300001 , 0x00000000 , 0x00010008 , 0x00000000 , 0x00000000 , 0xfffe0201 ,
0x0200001f , 0x80000005 , 0x900f0000 , 0x0200001f , 0x80010005 , 0x900f0001 ,
0x0200001f , 0x80020005 , 0x900f0002 , 0x03000005 , 0x800f0000 , 0x90550000 ,
0xa0e40002 , 0x04000004 , 0x800f0000 , 0x90000000 , 0xa0e40001 , 0x80e40000 ,
0x04000004 , 0x800f0000 , 0x90aa0000 , 0xa0e40003 , 0x80e40000 , 0x03000002 ,
0x800f0000 , 0x80e40000 , 0xa0e40004 , 0x03000005 , 0x800f0001 , 0x80550000 ,
0xa0e40006 , 0x04000004 , 0x800f0001 , 0x80000000 , 0xa0e40005 , 0x80e40001 ,
0x04000004 , 0x800f0001 , 0x80aa0000 , 0xa0e40007 , 0x80e40001 , 0x04000004 ,
0x800f0000 , 0x80ff0000 , 0xa0e40008 , 0x80e40001 , 0x04000004 , 0xc0030000 ,
0x80ff0000 , 0xa0e40000 , 0x80e40000 , 0x02000001 , 0xc00c0000 , 0x80e40000 ,
0x02000001 , 0xe0030000 , 0x90e40001 , 0x02000001 , 0xe00f0001 , 0x90e40002 ,
0x0000ffff , 0x52444853 , 0x000001c0 , 0x00010040 , 0x00000070 , 0x04000059 ,
0x00208e46 , 0x00000000 , 0x00000008 , 0x0300005f , 0x00101072 , 0x00000000 ,
0x0300005f , 0x00101032 , 0x00000001 , 0x0300005f , 0x001010f2 , 0x00000002 ,
0x04000067 , 0x001020f2 , 0x00000000 , 0x00000001 , 0x03000065 , 0x00102032 ,
0x00000001 , 0x03000065 , 0x001020f2 , 0x00000002 , 0x02000068 , 0x00000002 ,
0x08000038 , 0x001000f2 , 0x00000000 , 0x00101556 , 0x00000000 , 0x00208e46 ,
0x00000000 , 0x00000001 , 0x0a000032 , 0x001000f2 , 0x00000000 , 0x00101006 ,
0x00000000 , 0x00208e46 , 0x00000000 , 0x00000000 , 0x00100e46 , 0x00000000 ,
0x0a000032 , 0x001000f2 , 0x00000000 , 0x00101aa6 , 0x00000000 , 0x00208e46 ,
0x00000000 , 0x00000002 , 0x00100e46 , 0x00000000 , 0x08000000 , 0x001000f2 ,
0x00000000 , 0x00100e46 , 0x00000000 , 0x00208e46 , 0x00000000 , 0x00000003 ,
0x08000038 , 0x001000f2 , 0x00000001 , 0x00100556 , 0x00000000 , 0x00208e46 ,
0x00000000 , 0x00000005 , 0x0a000032 , 0x001000f2 , 0x00000001 , 0x00100006 ,
0x00000000 , 0x00208e46 , 0x00000000 , 0x00000004 , 0x00100e46 , 0x00000001 ,
0x0a000032 , 0x001000f2 , 0x00000001 , 0x00100aa6 , 0x00000000 , 0x00208e46 ,
0x00000000 , 0x00000006 , 0x00100e46 , 0x00000001 , 0x0a000032 , 0x001020f2 ,
0x00000000 , 0x00100ff6 , 0x00000000 , 0x00208e46 , 0x00000000 , 0x00000007 ,
0x00100e46 , 0x00000001 , 0x05000036 , 0x00102032 , 0x00000001 , 0x00101046 ,
0x00000001 , 0x05000036 , 0x001020f2 , 0x00000002 , 0x00101e46 , 0x00000002 ,
0x0100003e , 0x54415453 , 0x00000074 , 0x0000000b , 0x00000002 , 0x00000000 ,
0x00000006 , 0x00000003 , 0x00000000 , 0x00000000 , 0x00000001 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000003 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 ,
0x00000000 , 0x00000000 , 0x46454452 , 0x000000fc , 0x00000001 , 0x00000054 ,
0x00000001 , 0x0000001c , 0xfffe0400 , 0x00000100 , 0x000000c6 , 0x0000003c ,
0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000000 , 0x00000001 ,
0x00000001 , 0x74726556 , 0x68537865 , 0x72656461 , 0x736e6f43 , 0x746e6174 ,
0xabab0073 , 0x0000003c , 0x00000002 , 0x0000006c , 0x00000080 , 0x00000000 ,
0x00000000 , 0x0000009c , 0x00000000 , 0x00000040 , 0x00000002 , 0x000000a4 ,
0x00000000 , 0x000000b4 , 0x00000040 , 0x00000040 , 0x00000002 , 0x000000a4 ,
0x00000000 , 0x65646f6d , 0xabab006c , 0x00030002 , 0x00040004 , 0x00000000 ,
0x00000000 , 0x6a6f7270 , 0x69746365 , 0x6e416e6f , 0x65695664 , 0x694d0077 ,
0x736f7263 , 0x2074666f , 0x20295228 , 0x4c534c48 , 0x61685320 , 0x20726564 ,
0x706d6f43 , 0x72656c69 , 0x332e3920 , 0x32392e30 , 0x312e3030 , 0x34383336 ,
0xababab00 , 0x4e475349 , 0x00000068 , 0x00000003 , 0x00000008 , 0x00000050 ,
0x00000000 , 0x00000000 , 0x00000003 , 0x00000000 , 0x00000707 , 0x00000059 ,
0x00000000 , 0x00000000 , 0x00000003 , 0x00000001 , 0x00000303 , 0x00000062 ,
0x00000000 , 0x00000000 , 0x00000003 , 0x00000002 , 0x00000f0f , 0x49534f50 ,
0x4e4f4954 , 0x58455400 , 0x524f4f43 , 0x4f430044 , 0x00524f4c , 0x4e47534f ,
0x0000006c , 0x00000003 , 0x00000008 , 0x00000050 , 0x00000000 , 0x00000001 ,
0x00000003 , 0x00000000 , 0x0000000f , 0x0000005c , 0x00000000 , 0x00000000 ,
0x00000003 , 0x00000001 , 0x00000c03 , 0x00000065 , 0x00000000 , 0x00000000 ,
0x00000003 , 0x00000002 , 0x0000000f , 0x505f5653 , 0x5449534f , 0x004e4f49 ,
0x43584554 , 0x44524f4f , 0x4c4f4300 , 0xab00524f
2013-12-25 21:39:48 -05:00
} ;
# else
# error "An appropriate vertex shader is not defined."
# endif
2014-03-10 01:51:03 -07:00
2013-12-25 13:13:15 -05:00
/* Direct3D 11.1 renderer implementation */
2013-02-02 19:32:44 -05:00
static SDL_Renderer * D3D11_CreateRenderer ( SDL_Window * window , Uint32 flags ) ;
2013-02-09 16:00:55 -05:00
static void D3D11_WindowEvent ( SDL_Renderer * renderer ,
const SDL_WindowEvent * event ) ;
2013-02-09 18:58:13 -05:00
static int D3D11_CreateTexture ( SDL_Renderer * renderer , SDL_Texture * texture ) ;
static int D3D11_UpdateTexture ( SDL_Renderer * renderer , SDL_Texture * texture ,
2013-04-13 23:03:46 -04:00
const SDL_Rect * rect , const void * srcPixels ,
int srcPitch ) ;
2014-03-10 05:44:34 -07:00
static int D3D11_UpdateTextureYUV ( SDL_Renderer * renderer , SDL_Texture * texture ,
const SDL_Rect * rect ,
const Uint8 * Yplane , int Ypitch ,
const Uint8 * Uplane , int Upitch ,
const Uint8 * Vplane , int Vpitch ) ;
2013-03-31 11:16:31 -04:00
static int D3D11_LockTexture ( SDL_Renderer * renderer , SDL_Texture * texture ,
const SDL_Rect * rect , void * * pixels , int * pitch ) ;
static void D3D11_UnlockTexture ( SDL_Renderer * renderer , SDL_Texture * texture ) ;
2013-04-13 23:03:46 -04:00
static int D3D11_SetRenderTarget ( SDL_Renderer * renderer , SDL_Texture * texture ) ;
2013-02-02 19:32:44 -05:00
static int D3D11_UpdateViewport ( SDL_Renderer * renderer ) ;
2013-08-13 20:33:15 -04:00
static int D3D11_UpdateClipRect ( SDL_Renderer * renderer ) ;
2013-02-09 18:58:13 -05:00
static int D3D11_RenderClear ( SDL_Renderer * renderer ) ;
2013-03-24 21:57:40 -04:00
static int D3D11_RenderDrawPoints ( SDL_Renderer * renderer ,
const SDL_FPoint * points , int count ) ;
2013-03-24 21:19:26 -04:00
static int D3D11_RenderDrawLines ( SDL_Renderer * renderer ,
const SDL_FPoint * points , int count ) ;
2013-02-16 09:10:43 -05:00
static int D3D11_RenderFillRects ( SDL_Renderer * renderer ,
const SDL_FRect * rects , int count ) ;
2013-02-09 18:58:13 -05:00
static int D3D11_RenderCopy ( SDL_Renderer * renderer , SDL_Texture * texture ,
const SDL_Rect * srcrect , const SDL_FRect * dstrect ) ;
2013-04-01 22:33:37 -04:00
static int D3D11_RenderCopyEx ( SDL_Renderer * renderer , SDL_Texture * texture ,
const SDL_Rect * srcrect , const SDL_FRect * dstrect ,
const double angle , const SDL_FPoint * center , const SDL_RendererFlip flip ) ;
2013-04-01 21:34:47 -04:00
static int D3D11_RenderReadPixels ( SDL_Renderer * renderer , const SDL_Rect * rect ,
Uint32 format , void * pixels , int pitch ) ;
2013-02-02 21:05:32 -05:00
static void D3D11_RenderPresent ( SDL_Renderer * renderer ) ;
2013-02-09 18:58:13 -05:00
static void D3D11_DestroyTexture ( SDL_Renderer * renderer ,
SDL_Texture * texture ) ;
2013-02-09 15:22:49 -05:00
static void D3D11_DestroyRenderer ( SDL_Renderer * renderer ) ;
2013-02-02 19:32:44 -05:00
2013-02-09 11:42:17 -05:00
/* Direct3D 11.1 Internal Functions */
2014-03-10 01:51:03 -07:00
static HRESULT D3D11_CreateDeviceResources ( SDL_Renderer * renderer ) ;
static HRESULT D3D11_CreateWindowSizeDependentResources ( SDL_Renderer * renderer ) ;
static HRESULT D3D11_UpdateForWindowSizeChange ( SDL_Renderer * renderer ) ;
static HRESULT D3D11_HandleDeviceLost ( SDL_Renderer * renderer ) ;
static void D3D11_ReleaseMainRenderTargetView ( SDL_Renderer * renderer ) ;
2013-02-02 19:32:44 -05:00
2014-03-10 01:51:03 -07:00
SDL_RenderDriver D3D11_RenderDriver = {
2013-02-02 19:32:44 -05:00
D3D11_CreateRenderer ,
{
2014-03-10 01:51:03 -07:00
" direct3d11 " ,
2013-04-13 23:03:46 -04:00
(
SDL_RENDERER_ACCELERATED |
SDL_RENDERER_PRESENTVSYNC |
SDL_RENDERER_TARGETTEXTURE
2014-03-10 01:51:03 -07:00
) , /* flags. see SDL_RendererFlags */
2014-03-10 05:44:34 -07:00
4 , /* num_texture_formats */
2014-03-10 01:51:03 -07:00
{ /* texture_formats */
2014-03-10 05:44:34 -07:00
SDL_PIXELFORMAT_ARGB8888 ,
2013-02-23 22:58:09 -05:00
SDL_PIXELFORMAT_RGB888 ,
2014-03-10 05:44:34 -07:00
SDL_PIXELFORMAT_YV12 ,
SDL_PIXELFORMAT_IYUV
2013-02-23 22:58:09 -05:00
} ,
2014-03-10 01:51:03 -07:00
0 , /* max_texture_width: will be filled in later */
0 /* max_texture_height: will be filled in later */
2013-02-23 22:58:09 -05:00
}
} ;
2013-02-02 19:32:44 -05:00
2013-04-01 21:34:47 -04:00
static Uint32
DXGIFormatToSDLPixelFormat ( DXGI_FORMAT dxgiFormat ) {
switch ( dxgiFormat ) {
case DXGI_FORMAT_B8G8R8A8_UNORM :
return SDL_PIXELFORMAT_ARGB8888 ;
case DXGI_FORMAT_B8G8R8X8_UNORM :
return SDL_PIXELFORMAT_RGB888 ;
default :
return SDL_PIXELFORMAT_UNKNOWN ;
}
}
static DXGI_FORMAT
SDLPixelFormatToDXGIFormat ( Uint32 sdlFormat )
{
2014-03-09 11:06:11 -07:00
switch ( sdlFormat ) {
case SDL_PIXELFORMAT_ARGB8888 :
return DXGI_FORMAT_B8G8R8A8_UNORM ;
case SDL_PIXELFORMAT_RGB888 :
return DXGI_FORMAT_B8G8R8X8_UNORM ;
2014-03-10 05:44:34 -07:00
case SDL_PIXELFORMAT_YV12 :
case SDL_PIXELFORMAT_IYUV :
return DXGI_FORMAT_R8_UNORM ;
2014-03-09 11:06:11 -07:00
default :
return DXGI_FORMAT_UNKNOWN ;
}
2013-12-25 23:25:25 -05:00
}
2013-02-02 19:32:44 -05:00
2014-03-09 11:06:11 -07:00
SDL_Renderer *
D3D11_CreateRenderer ( SDL_Window * window , Uint32 flags )
{
SDL_Renderer * renderer ;
D3D11_RenderData * data ;
renderer = ( SDL_Renderer * ) SDL_calloc ( 1 , sizeof ( * renderer ) ) ;
if ( ! renderer ) {
SDL_OutOfMemory ( ) ;
return NULL ;
}
2014-03-10 01:51:03 -07:00
data = ( D3D11_RenderData * ) SDL_calloc ( 1 , sizeof ( * data ) ) ;
2014-03-09 11:06:11 -07:00
if ( ! data ) {
SDL_OutOfMemory ( ) ;
return NULL ;
}
renderer - > WindowEvent = D3D11_WindowEvent ;
renderer - > CreateTexture = D3D11_CreateTexture ;
renderer - > UpdateTexture = D3D11_UpdateTexture ;
2014-03-10 05:44:34 -07:00
renderer - > UpdateTextureYUV = D3D11_UpdateTextureYUV ;
2014-03-09 11:06:11 -07:00
renderer - > LockTexture = D3D11_LockTexture ;
renderer - > UnlockTexture = D3D11_UnlockTexture ;
renderer - > SetRenderTarget = D3D11_SetRenderTarget ;
renderer - > UpdateViewport = D3D11_UpdateViewport ;
renderer - > UpdateClipRect = D3D11_UpdateClipRect ;
renderer - > RenderClear = D3D11_RenderClear ;
renderer - > RenderDrawPoints = D3D11_RenderDrawPoints ;
renderer - > RenderDrawLines = D3D11_RenderDrawLines ;
renderer - > RenderFillRects = D3D11_RenderFillRects ;
renderer - > RenderCopy = D3D11_RenderCopy ;
renderer - > RenderCopyEx = D3D11_RenderCopyEx ;
renderer - > RenderReadPixels = D3D11_RenderReadPixels ;
renderer - > RenderPresent = D3D11_RenderPresent ;
renderer - > DestroyTexture = D3D11_DestroyTexture ;
renderer - > DestroyRenderer = D3D11_DestroyRenderer ;
renderer - > info = D3D11_RenderDriver . info ;
2014-03-10 01:51:03 -07:00
renderer - > info . flags = ( SDL_RENDERER_ACCELERATED | SDL_RENDERER_TARGETTEXTURE ) ;
2014-03-09 11:06:11 -07:00
renderer - > driverdata = data ;
2014-03-10 01:51:03 -07:00
if ( ( flags & SDL_RENDERER_PRESENTVSYNC ) ) {
renderer - > info . flags | = SDL_RENDERER_PRESENTVSYNC ;
}
/* HACK: make sure the SDL_Renderer references the SDL_Window data now, in
* order to give init functions access to the underlying window handle :
*/
2014-03-09 11:06:11 -07:00
renderer - > window = window ;
/* Initialize Direct3D resources */
if ( FAILED ( D3D11_CreateDeviceResources ( renderer ) ) ) {
D3D11_DestroyRenderer ( renderer ) ;
return NULL ;
}
if ( FAILED ( D3D11_CreateWindowSizeDependentResources ( renderer ) ) ) {
D3D11_DestroyRenderer ( renderer ) ;
return NULL ;
}
return renderer ;
2013-02-02 19:32:44 -05:00
}
2013-02-09 15:22:49 -05:00
static void
D3D11_DestroyRenderer ( SDL_Renderer * renderer )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 01:51:03 -07:00
2013-02-09 15:22:49 -05:00
if ( data ) {
2014-03-10 12:49:15 -07:00
SAFE_RELEASE ( data - > dxgiFactory ) ;
SAFE_RELEASE ( data - > dxgiAdapter ) ;
2014-03-10 01:51:03 -07:00
SAFE_RELEASE ( data - > d3dDevice ) ;
SAFE_RELEASE ( data - > d3dContext ) ;
SAFE_RELEASE ( data - > swapChain ) ;
SAFE_RELEASE ( data - > mainRenderTargetView ) ;
SAFE_RELEASE ( data - > currentOffscreenRenderTargetView ) ;
SAFE_RELEASE ( data - > inputLayout ) ;
SAFE_RELEASE ( data - > vertexBuffer ) ;
SAFE_RELEASE ( data - > vertexShader ) ;
SAFE_RELEASE ( data - > colorPixelShader ) ;
2014-03-10 05:44:34 -07:00
SAFE_RELEASE ( data - > texturePixelShader ) ;
SAFE_RELEASE ( data - > yuvPixelShader ) ;
2014-03-10 01:51:03 -07:00
SAFE_RELEASE ( data - > blendModeBlend ) ;
SAFE_RELEASE ( data - > blendModeAdd ) ;
SAFE_RELEASE ( data - > blendModeMod ) ;
SAFE_RELEASE ( data - > nearestPixelSampler ) ;
SAFE_RELEASE ( data - > linearSampler ) ;
SAFE_RELEASE ( data - > mainRasterizer ) ;
SAFE_RELEASE ( data - > clippedRasterizer ) ;
SAFE_RELEASE ( data - > vertexShaderConstants ) ;
if ( data - > hD3D11Mod ) {
SDL_UnloadObject ( data - > hD3D11Mod ) ;
}
2014-03-10 12:49:15 -07:00
if ( data - > hDXGIMod ) {
SDL_UnloadObject ( data - > hDXGIMod ) ;
}
2014-03-10 01:51:03 -07:00
SDL_free ( data ) ;
2013-02-09 15:22:49 -05:00
}
2014-03-10 01:51:03 -07:00
SDL_free ( renderer ) ;
2013-02-09 15:22:49 -05:00
}
2013-02-16 16:53:06 -05:00
static HRESULT
D3D11_CreateBlendMode ( SDL_Renderer * renderer ,
BOOL enableBlending ,
D3D11_BLEND srcBlend ,
D3D11_BLEND destBlend ,
2013-12-30 11:59:04 -05:00
D3D11_BLEND srcBlendAlpha ,
D3D11_BLEND destBlendAlpha ,
2013-02-16 16:53:06 -05:00
ID3D11BlendState * * blendStateOutput )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
HRESULT result = S_OK ;
2014-03-09 11:06:11 -07:00
D3D11_BLEND_DESC blendDesc ;
2014-03-10 01:51:03 -07:00
SDL_zero ( blendDesc ) ;
2014-03-09 11:06:11 -07:00
blendDesc . AlphaToCoverageEnable = FALSE ;
blendDesc . IndependentBlendEnable = FALSE ;
blendDesc . RenderTarget [ 0 ] . BlendEnable = enableBlending ;
blendDesc . RenderTarget [ 0 ] . SrcBlend = srcBlend ;
blendDesc . RenderTarget [ 0 ] . DestBlend = destBlend ;
blendDesc . RenderTarget [ 0 ] . BlendOp = D3D11_BLEND_OP_ADD ;
blendDesc . RenderTarget [ 0 ] . SrcBlendAlpha = srcBlendAlpha ;
blendDesc . RenderTarget [ 0 ] . DestBlendAlpha = destBlendAlpha ;
blendDesc . RenderTarget [ 0 ] . BlendOpAlpha = D3D11_BLEND_OP_ADD ;
blendDesc . RenderTarget [ 0 ] . RenderTargetWriteMask = D3D11_COLOR_WRITE_ENABLE_ALL ;
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreateBlendState ( data - > d3dDevice , & blendDesc , blendStateOutput ) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateBlendState " , result ) ;
return result ;
}
return S_OK ;
2013-02-16 16:53:06 -05:00
}
2014-03-10 01:51:03 -07:00
/* Create resources that depend on the device. */
static HRESULT
2014-03-09 11:06:11 -07:00
D3D11_CreateDeviceResources ( SDL_Renderer * renderer )
2014-03-10 14:35:37 -07:00
{
2014-03-10 12:49:15 -07:00
typedef HRESULT ( WINAPI * PFN_CREATE_DXGI_FACTORY ) ( REFIID riid , void * * ppFactory ) ;
PFN_CREATE_DXGI_FACTORY CreateDXGIFactoryFunc ;
2014-03-09 11:06:11 -07:00
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 01:51:03 -07:00
PFN_D3D11_CREATE_DEVICE D3D11CreateDeviceFunc ;
2014-03-10 12:49:15 -07:00
IDXGIAdapter * d3dAdapter = NULL ;
2014-03-10 01:51:03 -07:00
ID3D11Device * d3dDevice = NULL ;
ID3D11DeviceContext * d3dContext = NULL ;
2014-03-10 12:49:15 -07:00
IDXGIDevice1 * dxgiDevice = NULL ;
2014-03-10 01:51:03 -07:00
HRESULT result = S_OK ;
2014-03-10 22:53:03 -04:00
UINT creationFlags ;
const char * hint ;
/* This array defines the set of DirectX hardware feature levels this app will support.
* Note the ordering should be preserved .
* Don ' t forget to declare your application ' s minimum required feature level in its
* description . All applications are assumed to support 9.1 unless otherwise stated .
*/
D3D_FEATURE_LEVEL featureLevels [ ] =
{
D3D_FEATURE_LEVEL_11_1 ,
D3D_FEATURE_LEVEL_11_0 ,
D3D_FEATURE_LEVEL_10_1 ,
D3D_FEATURE_LEVEL_10_0 ,
D3D_FEATURE_LEVEL_9_3 ,
D3D_FEATURE_LEVEL_9_2 ,
D3D_FEATURE_LEVEL_9_1
} ;
/* Declare how the input layout for SDL's vertex shader will be setup: */
const D3D11_INPUT_ELEMENT_DESC vertexDesc [ ] =
{
{ " POSITION " , 0 , DXGI_FORMAT_R32G32B32_FLOAT , 0 , 0 , D3D11_INPUT_PER_VERTEX_DATA , 0 } ,
{ " TEXCOORD " , 0 , DXGI_FORMAT_R32G32_FLOAT , 0 , 12 , D3D11_INPUT_PER_VERTEX_DATA , 0 } ,
{ " COLOR " , 0 , DXGI_FORMAT_R32G32B32A32_FLOAT , 0 , 20 , D3D11_INPUT_PER_VERTEX_DATA , 0 } ,
} ;
D3D11_BUFFER_DESC constantBufferDesc ;
D3D11_SAMPLER_DESC samplerDesc ;
D3D11_RASTERIZER_DESC rasterDesc ;
2014-03-09 11:06:11 -07:00
2014-03-11 12:40:31 -04:00
// TODO, WinRT, Mar 11, 2014: once SDL/WinRT is back up and running, see if D3D11 init functions are loadable (via LoadPackagedLibrary/SDL_LoadObject, etc.)
//#ifdef __WINRT__
// CreateDXGIFactoryFunc = CreateDXGIFactory;
// D3D11CreateDeviceFunc = D3D11CreateDevice;
//#else
2014-03-10 14:35:37 -07:00
data - > hDXGIMod = SDL_LoadObject ( " dxgi.dll " ) ;
2014-03-10 12:49:15 -07:00
if ( ! data - > hDXGIMod ) {
result = E_FAIL ;
goto done ;
2014-03-10 14:35:37 -07:00
}
CreateDXGIFactoryFunc = ( PFN_CREATE_DXGI_FACTORY ) SDL_LoadFunction ( data - > hDXGIMod , " CreateDXGIFactory " ) ;
2014-03-10 12:49:15 -07:00
if ( ! CreateDXGIFactoryFunc ) {
result = E_FAIL ;
goto done ;
}
2014-03-10 01:51:03 -07:00
data - > hD3D11Mod = SDL_LoadObject ( " d3d11.dll " ) ;
if ( ! data - > hD3D11Mod ) {
result = E_FAIL ;
goto done ;
}
D3D11CreateDeviceFunc = ( PFN_D3D11_CREATE_DEVICE ) SDL_LoadFunction ( data - > hD3D11Mod , " D3D11CreateDevice " ) ;
if ( ! D3D11CreateDeviceFunc ) {
result = E_FAIL ;
goto done ;
}
2014-03-11 12:40:31 -04:00
//#endif /* __WINRT__ */
2014-03-10 14:35:37 -07:00
result = CreateDXGIFactoryFunc ( & IID_IDXGIFactory2 , & data - > dxgiFactory ) ;
2014-03-10 12:49:15 -07:00
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , CreateDXGIFactory " , result ) ;
goto done ;
2014-03-10 14:35:37 -07:00
}
/* FIXME: Should we use the default adapter? */
result = IDXGIFactory2_EnumAdapters ( data - > dxgiFactory , 0 , & data - > dxgiAdapter ) ;
2014-03-10 12:49:15 -07:00
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , D3D11CreateDevice " , result ) ;
goto done ;
}
2014-03-10 01:51:03 -07:00
/* This flag adds support for surfaces with a different color channel ordering
* than the API default . It is required for compatibility with Direct2D .
*/
2014-03-10 22:53:03 -04:00
creationFlags = D3D11_CREATE_DEVICE_BGRA_SUPPORT ;
2014-03-09 11:06:11 -07:00
2014-03-10 01:51:03 -07:00
/* Make sure Direct3D's debugging feature gets used, if the app requests it. */
2014-03-10 22:53:03 -04:00
hint = SDL_GetHint ( SDL_HINT_RENDER_DIRECT3D11_DEBUG ) ;
2014-03-10 01:51:03 -07:00
if ( hint & & SDL_atoi ( hint ) > 0 ) {
creationFlags | = D3D11_CREATE_DEVICE_DEBUG ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Create the Direct3D 11 API device object and a corresponding context. */
result = D3D11CreateDeviceFunc (
2014-03-10 12:49:15 -07:00
data - > dxgiAdapter ,
D3D_DRIVER_TYPE_UNKNOWN ,
2014-03-10 01:51:03 -07:00
NULL ,
creationFlags , /* Set set debug and Direct2D compatibility flags. */
featureLevels , /* List of feature levels this app can support. */
SDL_arraysize ( featureLevels ) ,
D3D11_SDK_VERSION , /* Always set this to D3D11_SDK_VERSION for Windows Store apps. */
& d3dDevice , /* Returns the Direct3D device created. */
& data - > featureLevel , /* Returns feature level of device created. */
& d3dContext /* Returns the device immediate context. */
2014-03-09 11:06:11 -07:00
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , D3D11CreateDevice " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
result = ID3D11Device_QueryInterface ( d3dDevice , & IID_ID3D11Device1 , & data - > d3dDevice ) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device to ID3D11Device1 " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
result = ID3D11DeviceContext_QueryInterface ( d3dContext , & IID_ID3D11DeviceContext1 , & data - > d3dContext ) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11DeviceContext to ID3D11DeviceContext1 " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 12:49:15 -07:00
result = ID3D11Device_QueryInterface ( d3dDevice , & IID_IDXGIDevice1 , & dxgiDevice ) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device to IDXGIDevice1 " , result ) ;
goto done ;
}
/* Ensure that DXGI does not queue more than one frame at a time. This both reduces latency and
* ensures that the application will only render after each VSync , minimizing power consumption .
*/
result = IDXGIDevice1_SetMaximumFrameLatency ( dxgiDevice , 1 ) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGIDevice1::SetMaximumFrameLatency " , result ) ;
goto done ;
}
2014-03-10 01:51:03 -07:00
/* Make note of the maximum texture size
* Max texture sizes are documented on MSDN , at :
* http : //msdn.microsoft.com/en-us/library/windows/apps/ff476876.aspx
*/
switch ( data - > featureLevel ) {
2014-03-09 11:06:11 -07:00
case D3D_FEATURE_LEVEL_11_1 :
case D3D_FEATURE_LEVEL_11_0 :
renderer - > info . max_texture_width = renderer - > info . max_texture_height = 16384 ;
break ;
case D3D_FEATURE_LEVEL_10_1 :
case D3D_FEATURE_LEVEL_10_0 :
renderer - > info . max_texture_width = renderer - > info . max_texture_height = 8192 ;
break ;
case D3D_FEATURE_LEVEL_9_3 :
renderer - > info . max_texture_width = renderer - > info . max_texture_height = 4096 ;
break ;
case D3D_FEATURE_LEVEL_9_2 :
case D3D_FEATURE_LEVEL_9_1 :
renderer - > info . max_texture_width = renderer - > info . max_texture_height = 2048 ;
break ;
2014-03-10 01:51:03 -07:00
default :
SDL_SetError ( __FUNCTION__ " , Unexpected feature level: %d " , data - > featureLevel ) ;
result = E_FAIL ;
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Load in SDL's one and only vertex shader: */
result = ID3D11Device_CreateVertexShader ( data - > d3dDevice ,
2014-03-09 11:06:11 -07:00
D3D11_VertexShader ,
sizeof ( D3D11_VertexShader ) ,
2014-03-10 01:51:03 -07:00
NULL ,
2014-03-09 11:06:11 -07:00
& data - > vertexShader
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateVertexShader " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Create an input layout for SDL's vertex shader: */
result = ID3D11Device_CreateInputLayout ( data - > d3dDevice ,
2014-03-09 11:06:11 -07:00
vertexDesc ,
ARRAYSIZE ( vertexDesc ) ,
D3D11_VertexShader ,
sizeof ( D3D11_VertexShader ) ,
& data - > inputLayout
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateInputLayout " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Load in SDL's pixel shaders */
2014-03-10 05:44:34 -07:00
result = ID3D11Device_CreatePixelShader ( data - > d3dDevice ,
D3D11_PixelShader_Colors ,
sizeof ( D3D11_PixelShader_Colors ) ,
NULL ,
& data - > colorPixelShader
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreatePixelShader ['color' shader] " , result ) ;
goto done ;
}
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreatePixelShader ( data - > d3dDevice ,
2014-03-09 11:06:11 -07:00
D3D11_PixelShader_Textures ,
sizeof ( D3D11_PixelShader_Textures ) ,
2014-03-10 01:51:03 -07:00
NULL ,
2014-03-09 11:06:11 -07:00
& data - > texturePixelShader
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreatePixelShader ['textures' shader] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreatePixelShader ( data - > d3dDevice ,
2014-03-10 05:44:34 -07:00
D3D11_PixelShader_YUV ,
sizeof ( D3D11_PixelShader_YUV ) ,
2014-03-10 01:51:03 -07:00
NULL ,
2014-03-10 05:44:34 -07:00
& data - > yuvPixelShader
2014-03-09 11:06:11 -07:00
) ;
if ( FAILED ( result ) ) {
2014-03-10 05:44:34 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreatePixelShader ['yuv' shader] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Setup space to hold vertex shader constants: */
SDL_zero ( constantBufferDesc ) ;
constantBufferDesc . ByteWidth = sizeof ( VertexShaderConstants ) ;
constantBufferDesc . Usage = D3D11_USAGE_DEFAULT ;
constantBufferDesc . BindFlags = D3D11_BIND_CONSTANT_BUFFER ;
result = ID3D11Device_CreateBuffer ( data - > d3dDevice ,
2014-03-10 12:49:15 -07:00
& constantBufferDesc ,
NULL ,
2014-03-09 11:06:11 -07:00
& data - > vertexShaderConstants
2014-03-10 12:49:15 -07:00
) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateBuffer [vertex shader constants] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Create samplers to use when drawing textures: */
SDL_zero ( samplerDesc ) ;
samplerDesc . Filter = D3D11_FILTER_MIN_MAG_MIP_POINT ;
2014-03-09 11:06:11 -07:00
samplerDesc . AddressU = D3D11_TEXTURE_ADDRESS_CLAMP ;
samplerDesc . AddressV = D3D11_TEXTURE_ADDRESS_CLAMP ;
samplerDesc . AddressW = D3D11_TEXTURE_ADDRESS_CLAMP ;
samplerDesc . MipLODBias = 0.0f ;
samplerDesc . MaxAnisotropy = 1 ;
samplerDesc . ComparisonFunc = D3D11_COMPARISON_ALWAYS ;
samplerDesc . MinLOD = 0.0f ;
samplerDesc . MaxLOD = D3D11_FLOAT32_MAX ;
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreateSamplerState ( data - > d3dDevice ,
2014-03-09 11:06:11 -07:00
& samplerDesc ,
& data - > nearestPixelSampler
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateSamplerState [nearest-pixel filter] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
samplerDesc . Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR ;
result = ID3D11Device_CreateSamplerState ( data - > d3dDevice ,
2014-03-09 11:06:11 -07:00
& samplerDesc ,
& data - > linearSampler
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateSamplerState [linear filter] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Setup Direct3D rasterizer states */
SDL_zero ( rasterDesc ) ;
2014-03-10 12:49:15 -07:00
rasterDesc . AntialiasedLineEnable = FALSE ;
rasterDesc . CullMode = D3D11_CULL_NONE ;
rasterDesc . DepthBias = 0 ;
rasterDesc . DepthBiasClamp = 0.0f ;
rasterDesc . DepthClipEnable = TRUE ;
rasterDesc . FillMode = D3D11_FILL_SOLID ;
rasterDesc . FrontCounterClockwise = FALSE ;
2014-03-10 01:51:03 -07:00
rasterDesc . MultisampleEnable = FALSE ;
rasterDesc . ScissorEnable = FALSE ;
2014-03-10 12:49:15 -07:00
rasterDesc . SlopeScaledDepthBias = 0.0f ;
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreateRasterizerState ( data - > d3dDevice , & rasterDesc , & data - > mainRasterizer ) ;
2014-03-10 12:49:15 -07:00
if ( FAILED ( result ) ) {
2014-03-09 11:06:11 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateRasterizerState [main rasterizer] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
rasterDesc . ScissorEnable = TRUE ;
result = ID3D11Device_CreateRasterizerState ( data - > d3dDevice , & rasterDesc , & data - > clippedRasterizer ) ;
2014-03-10 12:49:15 -07:00
if ( FAILED ( result ) ) {
2014-03-09 11:06:11 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateRasterizerState [clipped rasterizer] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Create blending states: */
2014-03-09 11:06:11 -07:00
result = D3D11_CreateBlendMode (
renderer ,
TRUE ,
D3D11_BLEND_SRC_ALPHA , /* srcBlend */
D3D11_BLEND_INV_SRC_ALPHA , /* destBlend */
D3D11_BLEND_ONE , /* srcBlendAlpha */
D3D11_BLEND_INV_SRC_ALPHA , /* destBlendAlpha */
& data - > blendModeBlend ) ;
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
/* D3D11_CreateBlendMode will set the SDL error, if it fails */
goto done ;
2014-03-09 11:06:11 -07:00
}
result = D3D11_CreateBlendMode (
renderer ,
TRUE ,
D3D11_BLEND_SRC_ALPHA , /* srcBlend */
D3D11_BLEND_ONE , /* destBlend */
D3D11_BLEND_ZERO , /* srcBlendAlpha */
D3D11_BLEND_ONE , /* destBlendAlpha */
& data - > blendModeAdd ) ;
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
/* D3D11_CreateBlendMode will set the SDL error, if it fails */
goto done ;
2014-03-09 11:06:11 -07:00
}
result = D3D11_CreateBlendMode (
renderer ,
TRUE ,
D3D11_BLEND_ZERO , /* srcBlend */
D3D11_BLEND_SRC_COLOR , /* destBlend */
D3D11_BLEND_ZERO , /* srcBlendAlpha */
D3D11_BLEND_ONE , /* destBlendAlpha */
& data - > blendModeMod ) ;
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
/* D3D11_CreateBlendMode will set the SDL error, if it fails */
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 02:13:44 -07:00
/* Setup render state that doesn't change */
2014-03-10 01:51:03 -07:00
ID3D11DeviceContext_IASetInputLayout ( data - > d3dContext , data - > inputLayout ) ;
ID3D11DeviceContext_VSSetShader ( data - > d3dContext , data - > vertexShader , NULL , 0 ) ;
ID3D11DeviceContext_VSSetConstantBuffers ( data - > d3dContext , 0 , 1 , & data - > vertexShaderConstants ) ;
done :
SAFE_RELEASE ( d3dDevice ) ;
SAFE_RELEASE ( d3dContext ) ;
2014-03-10 12:49:15 -07:00
SAFE_RELEASE ( dxgiDevice ) ;
2014-03-10 01:51:03 -07:00
return result ;
2013-02-09 11:42:17 -05:00
}
2014-03-11 12:40:31 -04:00
# ifdef __WIN32__
2014-03-10 01:51:03 -07:00
static DXGI_MODE_ROTATION
D3D11_GetCurrentRotation ( )
2013-12-25 23:45:07 -05:00
{
2014-03-10 01:51:03 -07:00
/* FIXME */
return DXGI_MODE_ROTATION_IDENTITY ;
}
2014-03-11 12:40:31 -04:00
# endif /* __WIN32__ */
2014-03-10 01:51:03 -07:00
static BOOL
D3D11_IsDisplayRotated90Degrees ( DXGI_MODE_ROTATION rotation )
{
switch ( rotation ) {
2013-12-25 23:45:07 -05:00
case DXGI_MODE_ROTATION_ROTATE90 :
case DXGI_MODE_ROTATION_ROTATE270 :
2014-03-10 01:51:03 -07:00
return TRUE ;
2013-12-25 23:45:07 -05:00
default :
2014-03-10 01:51:03 -07:00
return FALSE ;
2013-12-25 23:45:07 -05:00
}
}
2013-12-26 10:18:33 -05:00
static int
D3D11_GetViewportAlignedD3DRect ( SDL_Renderer * renderer , const SDL_Rect * sdlRect , D3D11_RECT * outRect )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 01:51:03 -07:00
switch ( data - > rotation ) {
2013-12-26 10:18:33 -05:00
case DXGI_MODE_ROTATION_IDENTITY :
outRect - > left = sdlRect - > x ;
outRect - > right = sdlRect - > x + sdlRect - > w ;
outRect - > top = sdlRect - > y ;
outRect - > bottom = sdlRect - > y + sdlRect - > h ;
break ;
case DXGI_MODE_ROTATION_ROTATE270 :
2014-03-09 11:06:11 -07:00
outRect - > left = sdlRect - > y ;
outRect - > right = sdlRect - > y + sdlRect - > h ;
outRect - > top = renderer - > viewport . w - sdlRect - > x - sdlRect - > w ;
2013-12-26 10:18:33 -05:00
outRect - > bottom = renderer - > viewport . w - sdlRect - > x ;
break ;
case DXGI_MODE_ROTATION_ROTATE180 :
outRect - > left = renderer - > viewport . w - sdlRect - > x - sdlRect - > w ;
outRect - > right = renderer - > viewport . w - sdlRect - > x ;
outRect - > top = renderer - > viewport . h - sdlRect - > y - sdlRect - > h ;
outRect - > bottom = renderer - > viewport . h - sdlRect - > y ;
break ;
case DXGI_MODE_ROTATION_ROTATE90 :
outRect - > left = renderer - > viewport . h - sdlRect - > y - sdlRect - > h ;
outRect - > right = renderer - > viewport . h - sdlRect - > y ;
2014-03-09 11:06:11 -07:00
outRect - > top = sdlRect - > x ;
2013-12-26 10:18:33 -05:00
outRect - > bottom = sdlRect - > x + sdlRect - > h ;
break ;
default :
2014-03-10 01:51:03 -07:00
return SDL_SetError ( " The physical display is in an unknown or unsupported rotation " ) ;
2013-12-26 10:18:33 -05:00
}
return 0 ;
}
2014-03-10 01:51:03 -07:00
static HRESULT
D3D11_CreateSwapChain ( SDL_Renderer * renderer , int w , int h )
2014-03-09 11:06:11 -07:00
{
2014-03-10 01:51:03 -07:00
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
# ifdef __WINRT__
IUnknown * coreWindow = D3D11_GetCoreWindowFromSDLRenderer ( renderer ) ;
const BOOL usingXAML = ( coreWindow = = NULL ) ;
# else
IUnknown * coreWindow = NULL ;
const BOOL usingXAML = FALSE ;
# endif
2014-03-09 11:06:11 -07:00
HRESULT result = S_OK ;
2014-03-10 01:51:03 -07:00
/* Create a swap chain using the same adapter as the existing Direct3D device. */
DXGI_SWAP_CHAIN_DESC1 swapChainDesc ;
SDL_zero ( swapChainDesc ) ;
swapChainDesc . Width = w ;
swapChainDesc . Height = h ;
swapChainDesc . Format = DXGI_FORMAT_B8G8R8A8_UNORM ; /* This is the most common swap chain format. */
swapChainDesc . Stereo = FALSE ;
swapChainDesc . SampleDesc . Count = 1 ; /* Don't use multi-sampling. */
swapChainDesc . SampleDesc . Quality = 0 ;
swapChainDesc . BufferUsage = DXGI_USAGE_RENDER_TARGET_OUTPUT ;
swapChainDesc . BufferCount = 2 ; /* Use double-buffering to minimize latency. */
# if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
swapChainDesc . Scaling = DXGI_SCALING_STRETCH ; /* On phone, only stretch and aspect-ratio stretch scaling are allowed. */
swapChainDesc . SwapEffect = DXGI_SWAP_EFFECT_DISCARD ; /* On phone, no swap effects are supported. */
# else
if ( usingXAML ) {
swapChainDesc . Scaling = DXGI_SCALING_STRETCH ;
2014-03-09 11:06:11 -07:00
} else {
2014-03-10 01:51:03 -07:00
swapChainDesc . Scaling = DXGI_SCALING_NONE ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
swapChainDesc . SwapEffect = DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL ; /* All Windows Store apps must use this SwapEffect. */
# endif
swapChainDesc . Flags = 0 ;
2014-03-09 11:06:11 -07:00
2014-03-10 01:51:03 -07:00
if ( coreWindow ) {
2014-03-10 12:49:15 -07:00
result = IDXGIFactory2_CreateSwapChainForCoreWindow ( data - > dxgiFactory ,
2014-03-10 01:51:03 -07:00
( IUnknown * ) data - > d3dDevice ,
coreWindow ,
& swapChainDesc ,
NULL , /* Allow on all displays. */
& data - > swapChain
2014-03-09 11:06:11 -07:00
) ;
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGIFactory2::CreateSwapChainForCoreWindow " , result ) ;
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
} else if ( usingXAML ) {
2014-03-10 12:49:15 -07:00
result = IDXGIFactory2_CreateSwapChainForComposition ( data - > dxgiFactory ,
2014-03-10 01:51:03 -07:00
( IUnknown * ) data - > d3dDevice ,
& swapChainDesc ,
NULL ,
& data - > swapChain ) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGIFactory2::CreateSwapChainForComposition " , result ) ;
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
# if WINAPI_FAMILY == WINAPI_FAMILY_APP
2014-03-11 12:40:31 -04:00
result = ISwapChainBackgroundPanelNative_SetSwapChain ( WINRT_GlobalSwapChainBackgroundPanelNative , ( IDXGISwapChain * ) data - > swapChain ) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ISwapChainBackgroundPanelNative::SetSwapChain " , result ) ;
2014-03-10 12:49:15 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
# else
SDL_SetError ( __FUNCTION__ " , XAML support is not yet available for Windows Phone " ) ;
result = E_FAIL ;
goto done ;
# endif
} else {
2014-03-11 12:40:31 -04:00
# ifdef __WIN32__
2014-03-10 01:51:03 -07:00
SDL_SysWMinfo windowinfo ;
SDL_VERSION ( & windowinfo . version ) ;
SDL_GetWindowWMInfo ( renderer - > window , & windowinfo ) ;
2014-03-10 12:49:15 -07:00
result = IDXGIFactory2_CreateSwapChainForHwnd ( data - > dxgiFactory ,
2014-03-10 01:51:03 -07:00
( IUnknown * ) data - > d3dDevice ,
windowinfo . info . win . window ,
& swapChainDesc ,
NULL ,
NULL , /* Allow on all displays. */
& data - > swapChain
2014-03-09 11:06:11 -07:00
) ;
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGIFactory2::CreateSwapChainForHwnd " , result ) ;
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-11 12:40:31 -04:00
# else
SDL_SetError ( __FUNCTION__ " , Unable to find something to attach a swap chain to " ) ;
goto done ;
# endif /* ifdef __WIN32__ / else */
2014-03-10 01:51:03 -07:00
}
data - > swapEffect = swapChainDesc . SwapEffect ;
done :
SAFE_RELEASE ( coreWindow ) ;
return result ;
}
2014-03-09 11:06:11 -07:00
2014-03-10 01:51:03 -07:00
/* Initialize all resources that change when the window's size changes. */
static HRESULT
D3D11_CreateWindowSizeDependentResources ( SDL_Renderer * renderer )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
ID3D11Texture2D * backBuffer = NULL ;
HRESULT result = S_OK ;
int w , h ;
2014-03-10 22:53:03 -04:00
BOOL swapDimensions ;
2014-03-10 01:51:03 -07:00
/* Release the previous render target view */
D3D11_ReleaseMainRenderTargetView ( renderer ) ;
/* The width and height of the swap chain must be based on the window's
* landscape - oriented width and height . If the window is in a portrait
* rotation , the dimensions must be reversed .
*/
SDL_GetWindowSize ( renderer - > window , & w , & h ) ;
data - > rotation = D3D11_GetCurrentRotation ( ) ;
# if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
2014-03-10 22:53:03 -04:00
swapDimensions = FALSE ;
2014-03-09 11:06:11 -07:00
# else
2014-03-10 22:53:03 -04:00
swapDimensions = D3D11_IsDisplayRotated90Degrees ( data - > rotation ) ;
2014-03-09 11:06:11 -07:00
# endif
2014-03-10 01:51:03 -07:00
if ( swapDimensions ) {
int tmp = w ;
w = h ;
h = tmp ;
}
if ( data - > swapChain ) {
/* If the swap chain already exists, resize it. */
result = IDXGISwapChain_ResizeBuffers ( data - > swapChain ,
0 ,
w , h ,
DXGI_FORMAT_UNKNOWN ,
0
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGISwapChain::ResizeBuffers " , result ) ;
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
} else {
result = D3D11_CreateSwapChain ( renderer , w , h ) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
goto done ;
2014-03-09 11:06:11 -07:00
}
}
# if WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP
2014-03-10 01:51:03 -07:00
/* Set the proper rotation for the swap chain, and generate the
* 3 D matrix transformation for rendering to the rotated swap chain .
*
* To note , the call for this , IDXGISwapChain1 : : SetRotation , is not necessary
* on Windows Phone , nor is it supported there . It ' s only needed in Windows 8 / RT .
*/
2014-03-10 02:13:44 -07:00
if ( data - > swapEffect = = DXGI_SWAP_EFFECT_FLIP_SEQUENTIAL ) {
2014-03-10 01:51:03 -07:00
result = IDXGISwapChain1_SetRotation ( data - > swapChain , data - > rotation ) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGISwapChain1::SetRotation " , result ) ;
goto done ;
}
2014-03-09 11:06:11 -07:00
}
# endif
2014-03-10 01:51:03 -07:00
result = IDXGISwapChain_GetBuffer ( data - > swapChain ,
2014-03-09 11:06:11 -07:00
0 ,
2014-03-10 01:51:03 -07:00
& IID_ID3D11Texture2D ,
2014-03-09 11:06:11 -07:00
& backBuffer
) ;
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGISwapChain::GetBuffer [back-buffer] " , result ) ;
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
/* Create a render target view of the swap chain back buffer. */
result = ID3D11Device_CreateRenderTargetView ( data - > d3dDevice ,
( ID3D11Resource * ) backBuffer ,
NULL ,
2014-03-09 11:06:11 -07:00
& data - > mainRenderTargetView
) ;
if ( FAILED ( result ) ) {
2014-03-10 01:51:03 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device::CreateRenderTargetView " , result ) ;
goto done ;
2014-03-09 11:06:11 -07:00
}
if ( D3D11_UpdateViewport ( renderer ) ! = 0 ) {
2014-03-10 01:51:03 -07:00
/* D3D11_UpdateViewport will set the SDL error if it fails. */
result = E_FAIL ;
goto done ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 01:51:03 -07:00
done :
SAFE_RELEASE ( backBuffer ) ;
return result ;
2013-02-09 14:56:32 -05:00
}
2014-03-10 01:51:03 -07:00
/* This method is called when the window's size changes. */
static HRESULT
2014-03-09 11:06:11 -07:00
D3D11_UpdateForWindowSizeChange ( SDL_Renderer * renderer )
{
2014-03-10 01:51:03 -07:00
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
return D3D11_CreateWindowSizeDependentResources ( renderer ) ;
2013-02-09 15:43:13 -05:00
}
HRESULT
D3D11_HandleDeviceLost ( SDL_Renderer * renderer )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
HRESULT result = S_OK ;
2014-03-10 02:13:44 -07:00
/* FIXME: Need to release all resources - all textures are invalid! */
2014-03-09 11:06:11 -07:00
result = D3D11_CreateDeviceResources ( renderer ) ;
if ( FAILED ( result ) ) {
/* D3D11_CreateDeviceResources will set the SDL error */
return result ;
}
result = D3D11_UpdateForWindowSizeChange ( renderer ) ;
if ( FAILED ( result ) ) {
/* D3D11_UpdateForWindowSizeChange will set the SDL error */
return result ;
}
2013-02-09 15:43:13 -05:00
return S_OK ;
}
2013-02-09 16:00:55 -05:00
static void
D3D11_WindowEvent ( SDL_Renderer * renderer , const SDL_WindowEvent * event )
{
2014-03-09 11:06:11 -07:00
if ( event - > event = = SDL_WINDOWEVENT_SIZE_CHANGED ) {
D3D11_UpdateForWindowSizeChange ( renderer ) ;
2013-02-09 16:00:55 -05:00
}
}
2014-03-09 11:06:11 -07:00
static D3D11_FILTER
GetScaleQuality ( void )
{
const char * hint = SDL_GetHint ( SDL_HINT_RENDER_SCALE_QUALITY ) ;
if ( ! hint | | * hint = = ' 0 ' | | SDL_strcasecmp ( hint , " nearest " ) = = 0 ) {
2014-03-10 01:51:03 -07:00
return D3D11_FILTER_MIN_MAG_MIP_POINT ;
2014-03-09 11:06:11 -07:00
} else /* if (*hint == '1' || SDL_strcasecmp(hint, "linear") == 0) */ {
2014-03-10 01:51:03 -07:00
return D3D11_FILTER_MIN_MAG_MIP_LINEAR ;
2014-03-09 11:06:11 -07:00
}
2013-11-01 22:54:39 -04:00
}
2014-03-09 11:06:11 -07:00
static int
D3D11_CreateTexture ( SDL_Renderer * renderer , SDL_Texture * texture )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
D3D11_TextureData * textureData ;
HRESULT result ;
DXGI_FORMAT textureFormat = SDLPixelFormatToDXGIFormat ( texture - > format ) ;
2014-03-10 22:53:03 -04:00
D3D11_TEXTURE2D_DESC textureDesc ;
D3D11_SHADER_RESOURCE_VIEW_DESC resourceViewDesc ;
2014-03-09 11:06:11 -07:00
if ( textureFormat = = SDL_PIXELFORMAT_UNKNOWN ) {
return SDL_SetError ( " %s, An unsupported SDL pixel format (0x%x) was specified " ,
__FUNCTION__ , texture - > format ) ;
}
2014-03-10 01:51:03 -07:00
textureData = ( D3D11_TextureData * ) SDL_calloc ( 1 , sizeof ( * textureData ) ) ;
2014-03-09 11:06:11 -07:00
if ( ! textureData ) {
SDL_OutOfMemory ( ) ;
return - 1 ;
}
textureData - > scaleMode = GetScaleQuality ( ) ;
texture - > driverdata = textureData ;
2014-03-10 01:51:03 -07:00
SDL_zero ( textureDesc ) ;
2014-03-09 11:06:11 -07:00
textureDesc . Width = texture - > w ;
textureDesc . Height = texture - > h ;
textureDesc . MipLevels = 1 ;
textureDesc . ArraySize = 1 ;
textureDesc . Format = textureFormat ;
textureDesc . SampleDesc . Count = 1 ;
textureDesc . SampleDesc . Quality = 0 ;
textureDesc . MiscFlags = 0 ;
if ( texture - > access = = SDL_TEXTUREACCESS_STREAMING ) {
textureDesc . Usage = D3D11_USAGE_DYNAMIC ;
textureDesc . CPUAccessFlags = D3D11_CPU_ACCESS_WRITE ;
} else {
textureDesc . Usage = D3D11_USAGE_DEFAULT ;
textureDesc . CPUAccessFlags = 0 ;
}
if ( texture - > access = = SDL_TEXTUREACCESS_TARGET ) {
textureDesc . BindFlags = D3D11_BIND_SHADER_RESOURCE | D3D11_BIND_RENDER_TARGET ;
} else {
textureDesc . BindFlags = D3D11_BIND_SHADER_RESOURCE ;
}
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreateTexture2D ( rendererData - > d3dDevice ,
2014-03-09 11:06:11 -07:00
& textureDesc ,
2014-03-10 01:51:03 -07:00
NULL ,
2014-03-09 11:06:11 -07:00
& textureData - > mainTexture
) ;
if ( FAILED ( result ) ) {
D3D11_DestroyTexture ( renderer , texture ) ;
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateTexture2D " , result ) ;
return - 1 ;
}
2014-03-10 05:44:34 -07:00
if ( texture - > format = = SDL_PIXELFORMAT_YV12 | |
texture - > format = = SDL_PIXELFORMAT_IYUV ) {
textureData - > yuv = SDL_TRUE ;
2014-03-09 11:06:11 -07:00
2014-03-10 05:44:34 -07:00
textureDesc . Width / = 2 ;
textureDesc . Height / = 2 ;
result = ID3D11Device_CreateTexture2D ( rendererData - > d3dDevice ,
& textureDesc ,
NULL ,
& textureData - > mainTextureU
) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
D3D11_DestroyTexture ( renderer , texture ) ;
2014-03-10 05:44:34 -07:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateTexture2D " , result ) ;
return - 1 ;
}
result = ID3D11Device_CreateTexture2D ( rendererData - > d3dDevice ,
& textureDesc ,
NULL ,
& textureData - > mainTextureV
) ;
if ( FAILED ( result ) ) {
D3D11_DestroyTexture ( renderer , texture ) ;
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateTexture2D " , result ) ;
2014-03-09 11:06:11 -07:00
return - 1 ;
}
}
resourceViewDesc . Format = textureDesc . Format ;
resourceViewDesc . ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D ;
resourceViewDesc . Texture2D . MostDetailedMip = 0 ;
resourceViewDesc . Texture2D . MipLevels = textureDesc . MipLevels ;
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreateShaderResourceView ( rendererData - > d3dDevice ,
( ID3D11Resource * ) textureData - > mainTexture ,
2014-03-09 11:06:11 -07:00
& resourceViewDesc ,
& textureData - > mainTextureResourceView
) ;
if ( FAILED ( result ) ) {
D3D11_DestroyTexture ( renderer , texture ) ;
WIN_SetErrorFromHRESULT ( __FUNCTION__ " ID3D11Device1::CreateShaderResourceView " , result ) ;
return - 1 ;
}
2014-03-10 05:44:34 -07:00
if ( textureData - > yuv ) {
result = ID3D11Device_CreateShaderResourceView ( rendererData - > d3dDevice ,
( ID3D11Resource * ) textureData - > mainTextureU ,
& resourceViewDesc ,
& textureData - > mainTextureResourceViewU
) ;
if ( FAILED ( result ) ) {
D3D11_DestroyTexture ( renderer , texture ) ;
WIN_SetErrorFromHRESULT ( __FUNCTION__ " ID3D11Device1::CreateShaderResourceView " , result ) ;
return - 1 ;
}
result = ID3D11Device_CreateShaderResourceView ( rendererData - > d3dDevice ,
( ID3D11Resource * ) textureData - > mainTextureV ,
& resourceViewDesc ,
& textureData - > mainTextureResourceViewV
) ;
if ( FAILED ( result ) ) {
D3D11_DestroyTexture ( renderer , texture ) ;
WIN_SetErrorFromHRESULT ( __FUNCTION__ " ID3D11Device1::CreateShaderResourceView " , result ) ;
return - 1 ;
}
}
if ( texture - > access & SDL_TEXTUREACCESS_TARGET ) {
D3D11_RENDER_TARGET_VIEW_DESC renderTargetViewDesc ;
renderTargetViewDesc . Format = textureDesc . Format ;
renderTargetViewDesc . ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D ;
renderTargetViewDesc . Texture2D . MipSlice = 0 ;
result = ID3D11Device_CreateRenderTargetView ( rendererData - > d3dDevice ,
( ID3D11Resource * ) textureData - > mainTexture ,
& renderTargetViewDesc ,
& textureData - > mainTextureRenderTargetView ) ;
if ( FAILED ( result ) ) {
D3D11_DestroyTexture ( renderer , texture ) ;
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateRenderTargetView " , result ) ;
return - 1 ;
}
}
2014-03-09 11:06:11 -07:00
return 0 ;
2013-02-09 18:58:13 -05:00
}
static void
D3D11_DestroyTexture ( SDL_Renderer * renderer ,
SDL_Texture * texture )
{
2014-03-10 01:51:03 -07:00
D3D11_TextureData * data = ( D3D11_TextureData * ) texture - > driverdata ;
2013-02-09 18:58:13 -05:00
2014-03-10 01:51:03 -07:00
if ( ! data ) {
return ;
2013-02-09 18:58:13 -05:00
}
2014-03-10 01:51:03 -07:00
SAFE_RELEASE ( data - > mainTexture ) ;
SAFE_RELEASE ( data - > mainTextureResourceView ) ;
SAFE_RELEASE ( data - > mainTextureRenderTargetView ) ;
SAFE_RELEASE ( data - > stagingTexture ) ;
2014-03-10 05:44:34 -07:00
SAFE_RELEASE ( data - > mainTextureU ) ;
SAFE_RELEASE ( data - > mainTextureResourceViewU ) ;
SAFE_RELEASE ( data - > mainTextureV ) ;
SAFE_RELEASE ( data - > mainTextureResourceViewV ) ;
SDL_free ( data - > pixels ) ;
2014-03-10 01:51:03 -07:00
SDL_free ( data ) ;
texture - > driverdata = NULL ;
2013-02-09 18:58:13 -05:00
}
2014-03-10 05:44:34 -07:00
static int
D3D11_UpdateTextureInternal ( D3D11_RenderData * rendererData , ID3D11Texture2D * texture , Uint32 format , int x , int y , int w , int h , const void * pixels , int pitch )
{
ID3D11Texture2D * stagingTexture ;
const Uint8 * src ;
Uint8 * dst ;
int row ;
UINT length ;
HRESULT result ;
2014-03-10 22:53:03 -04:00
D3D11_TEXTURE2D_DESC stagingTextureDesc ;
D3D11_MAPPED_SUBRESOURCE textureMemory ;
2014-03-10 05:44:34 -07:00
/* Create a 'staging' texture, which will be used to write to a portion of the main texture. */
ID3D11Texture2D_GetDesc ( texture , & stagingTextureDesc ) ;
stagingTextureDesc . Width = w ;
stagingTextureDesc . Height = h ;
stagingTextureDesc . BindFlags = 0 ;
stagingTextureDesc . MiscFlags = 0 ;
stagingTextureDesc . CPUAccessFlags = D3D11_CPU_ACCESS_WRITE ;
stagingTextureDesc . Usage = D3D11_USAGE_STAGING ;
result = ID3D11Device_CreateTexture2D ( rendererData - > d3dDevice ,
& stagingTextureDesc ,
NULL ,
& stagingTexture ) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateTexture2D [create staging texture] " , result ) ;
return - 1 ;
}
/* Get a write-only pointer to data in the staging texture: */
result = ID3D11DeviceContext_Map ( rendererData - > d3dContext ,
( ID3D11Resource * ) stagingTexture ,
0 ,
D3D11_MAP_WRITE ,
0 ,
& textureMemory
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11DeviceContext1::Map [map staging texture] " , result ) ;
SAFE_RELEASE ( stagingTexture ) ;
return - 1 ;
}
src = ( const Uint8 * ) pixels ;
dst = textureMemory . pData ;
length = w * SDL_BYTESPERPIXEL ( format ) ;
if ( length = = pitch & & length = = textureMemory . RowPitch ) {
SDL_memcpy ( dst , src , length * h ) ;
} else {
if ( length > ( UINT ) pitch ) {
length = pitch ;
}
if ( length > textureMemory . RowPitch ) {
length = textureMemory . RowPitch ;
}
for ( row = 0 ; row < h ; + + row ) {
SDL_memcpy ( dst , src , length ) ;
src + = pitch ;
dst + = textureMemory . RowPitch ;
}
}
/* Commit the pixel buffer's changes back to the staging texture: */
ID3D11DeviceContext_Unmap ( rendererData - > d3dContext ,
( ID3D11Resource * ) stagingTexture ,
0 ) ;
/* Copy the staging texture's contents back to the texture: */
ID3D11DeviceContext_CopySubresourceRegion ( rendererData - > d3dContext ,
( ID3D11Resource * ) texture ,
0 ,
x ,
y ,
0 ,
( ID3D11Resource * ) stagingTexture ,
0 ,
NULL ) ;
SAFE_RELEASE ( stagingTexture ) ;
return 0 ;
}
2013-02-09 18:58:13 -05:00
static int
D3D11_UpdateTexture ( SDL_Renderer * renderer , SDL_Texture * texture ,
2013-04-13 23:03:46 -04:00
const SDL_Rect * rect , const void * srcPixels ,
int srcPitch )
2013-02-09 18:58:13 -05:00
{
2014-03-10 05:44:34 -07:00
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
D3D11_TextureData * textureData = ( D3D11_TextureData * ) texture - > driverdata ;
if ( ! textureData ) {
SDL_SetError ( " Texture is not currently available " ) ;
return - 1 ;
2014-03-09 11:06:11 -07:00
}
2014-03-10 05:44:34 -07:00
if ( D3D11_UpdateTextureInternal ( rendererData , textureData - > mainTexture , texture - > format , rect - > x , rect - > y , rect - > w , rect - > h , srcPixels , srcPitch ) < 0 ) {
return - 1 ;
}
if ( textureData - > yuv ) {
/* Skip to the correct offset into the next texture */
srcPixels = ( const void * ) ( ( const Uint8 * ) srcPixels + rect - > h * srcPitch ) ;
if ( D3D11_UpdateTextureInternal ( rendererData , texture - > format = = SDL_PIXELFORMAT_YV12 ? textureData - > mainTextureV : textureData - > mainTextureU , texture - > format , rect - > x / 2 , rect - > y / 2 , rect - > w / 2 , rect - > h / 2 , srcPixels , srcPitch / 2 ) < 0 ) {
return - 1 ;
}
2013-02-09 18:58:13 -05:00
2014-03-10 05:44:34 -07:00
/* Skip to the correct offset into the next texture */
srcPixels = ( const void * ) ( ( const Uint8 * ) srcPixels + ( rect - > h * srcPitch ) / 4 ) ;
if ( D3D11_UpdateTextureInternal ( rendererData , texture - > format = = SDL_PIXELFORMAT_YV12 ? textureData - > mainTextureU : textureData - > mainTextureV , texture - > format , rect - > x / 2 , rect - > y / 2 , rect - > w / 2 , rect - > h / 2 , srcPixels , srcPitch / 2 ) < 0 ) {
return - 1 ;
}
}
return 0 ;
}
static int
D3D11_UpdateTextureYUV ( SDL_Renderer * renderer , SDL_Texture * texture ,
const SDL_Rect * rect ,
const Uint8 * Yplane , int Ypitch ,
const Uint8 * Uplane , int Upitch ,
const Uint8 * Vplane , int Vpitch )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
D3D11_TextureData * textureData = ( D3D11_TextureData * ) texture - > driverdata ;
if ( ! textureData ) {
SDL_SetError ( " Texture is not currently available " ) ;
return - 1 ;
}
if ( D3D11_UpdateTextureInternal ( rendererData , textureData - > mainTexture , texture - > format , rect - > x , rect - > y , rect - > w , rect - > h , Yplane , Ypitch ) < 0 ) {
return - 1 ;
}
if ( D3D11_UpdateTextureInternal ( rendererData , textureData - > mainTextureU , texture - > format , rect - > x / 2 , rect - > y / 2 , rect - > w / 2 , rect - > h / 2 , Uplane , Upitch ) < 0 ) {
return - 1 ;
}
if ( D3D11_UpdateTextureInternal ( rendererData , textureData - > mainTextureV , texture - > format , rect - > x / 2 , rect - > y / 2 , rect - > w / 2 , rect - > h / 2 , Vplane , Vpitch ) < 0 ) {
return - 1 ;
}
2013-02-09 18:58:13 -05:00
return 0 ;
}
2013-03-31 11:16:31 -04:00
static int
D3D11_LockTexture ( SDL_Renderer * renderer , SDL_Texture * texture ,
const SDL_Rect * rect , void * * pixels , int * pitch )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-09 11:06:11 -07:00
D3D11_TextureData * textureData = ( D3D11_TextureData * ) texture - > driverdata ;
HRESULT result = S_OK ;
2014-03-10 22:53:03 -04:00
D3D11_TEXTURE2D_DESC stagingTextureDesc ;
D3D11_MAPPED_SUBRESOURCE textureMemory ;
2014-03-09 11:06:11 -07:00
2014-03-10 05:44:34 -07:00
if ( ! textureData ) {
SDL_SetError ( " Texture is not currently available " ) ;
return - 1 ;
}
if ( textureData - > yuv ) {
/* It's more efficient to upload directly... */
if ( ! textureData - > pixels ) {
textureData - > pitch = texture - > w ;
textureData - > pixels = ( Uint8 * ) SDL_malloc ( ( texture - > h * textureData - > pitch * 3 ) / 2 ) ;
if ( ! textureData - > pixels ) {
return SDL_OutOfMemory ( ) ;
}
}
textureData - > locked_rect = * rect ;
* pixels =
( void * ) ( ( Uint8 * ) textureData - > pixels + rect - > y * textureData - > pitch +
rect - > x * SDL_BYTESPERPIXEL ( texture - > format ) ) ;
* pitch = textureData - > pitch ;
return 0 ;
}
2013-03-31 11:16:31 -04:00
if ( textureData - > stagingTexture ) {
2013-12-25 12:52:16 -05:00
return SDL_SetError ( " texture is already locked " ) ;
2013-03-31 11:16:31 -04:00
}
2014-03-10 01:51:03 -07:00
/* Create a 'staging' texture, which will be used to write to a portion
* of the main texture . This is necessary , as Direct3D 11.1 does not
* have the ability to write a CPU - bound pixel buffer to a rectangular
* subrect of a texture . Direct3D 11.1 can , however , write a pixel
* buffer to an entire texture , hence the use of a staging texture .
*
* TODO , WinRT : consider avoiding the use of a staging texture in D3D11_LockTexture if / when the entire texture is being updated
*/
ID3D11Texture2D_GetDesc ( textureData - > mainTexture , & stagingTextureDesc ) ;
2013-03-31 11:16:31 -04:00
stagingTextureDesc . Width = rect - > w ;
stagingTextureDesc . Height = rect - > h ;
stagingTextureDesc . BindFlags = 0 ;
stagingTextureDesc . MiscFlags = 0 ;
stagingTextureDesc . CPUAccessFlags = D3D11_CPU_ACCESS_WRITE ;
stagingTextureDesc . Usage = D3D11_USAGE_STAGING ;
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreateTexture2D ( rendererData - > d3dDevice ,
2013-03-31 11:16:31 -04:00
& stagingTextureDesc ,
NULL ,
& textureData - > stagingTexture ) ;
if ( FAILED ( result ) ) {
2013-12-25 12:43:26 -05:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateTexture2D [create staging texture] " , result ) ;
2013-03-31 11:16:31 -04:00
return - 1 ;
}
2014-03-10 01:51:03 -07:00
/* Get a write-only pointer to data in the staging texture: */
result = ID3D11DeviceContext_Map ( rendererData - > d3dContext ,
( ID3D11Resource * ) textureData - > stagingTexture ,
0 ,
2014-03-09 11:06:11 -07:00
D3D11_MAP_WRITE ,
0 ,
& textureMemory
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11DeviceContext1::Map [map staging texture] " , result ) ;
2014-03-10 01:51:03 -07:00
SAFE_RELEASE ( textureData - > stagingTexture ) ;
2014-03-09 11:06:11 -07:00
return - 1 ;
2013-03-31 11:16:31 -04:00
}
2014-03-10 01:51:03 -07:00
/* Make note of where the staging texture will be written to
* ( on a call to SDL_UnlockTexture ) :
*/
textureData - > lockedTexturePositionX = rect - > x ;
textureData - > lockedTexturePositionY = rect - > y ;
2013-03-31 11:16:31 -04:00
2014-03-10 01:51:03 -07:00
/* Make sure the caller has information on the texture's pixel buffer,
* then return :
*/
2013-03-31 11:16:31 -04:00
* pixels = textureMemory . pData ;
* pitch = textureMemory . RowPitch ;
return 0 ;
}
static void
D3D11_UnlockTexture ( SDL_Renderer * renderer , SDL_Texture * texture )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
D3D11_TextureData * textureData = ( D3D11_TextureData * ) texture - > driverdata ;
2014-03-10 05:44:34 -07:00
if ( ! textureData ) {
return ;
}
if ( textureData - > yuv ) {
const SDL_Rect * rect = & textureData - > locked_rect ;
void * pixels =
( void * ) ( ( Uint8 * ) textureData - > pixels + rect - > y * textureData - > pitch +
rect - > x * SDL_BYTESPERPIXEL ( texture - > format ) ) ;
D3D11_UpdateTexture ( renderer , texture , rect , pixels , textureData - > pitch ) ;
return ;
}
2013-03-31 11:16:31 -04:00
2014-03-10 01:51:03 -07:00
/* Commit the pixel buffer's changes back to the staging texture: */
ID3D11DeviceContext_Unmap ( rendererData - > d3dContext ,
( ID3D11Resource * ) textureData - > stagingTexture ,
2013-03-31 11:16:31 -04:00
0 ) ;
2014-03-10 01:51:03 -07:00
/* Copy the staging texture's contents back to the main texture: */
ID3D11DeviceContext_CopySubresourceRegion ( rendererData - > d3dContext ,
( ID3D11Resource * ) textureData - > mainTexture ,
0 ,
textureData - > lockedTexturePositionX ,
textureData - > lockedTexturePositionY ,
0 ,
( ID3D11Resource * ) textureData - > stagingTexture ,
2013-03-31 11:16:31 -04:00
0 ,
NULL ) ;
2014-03-10 01:51:03 -07:00
SAFE_RELEASE ( textureData - > stagingTexture ) ;
2013-03-31 11:16:31 -04:00
}
2013-04-13 23:03:46 -04:00
static int
2014-03-09 11:06:11 -07:00
D3D11_SetRenderTarget ( SDL_Renderer * renderer , SDL_Texture * texture )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 22:53:03 -04:00
D3D11_TextureData * textureData = NULL ;
2014-03-09 11:06:11 -07:00
if ( texture = = NULL ) {
2014-03-10 01:51:03 -07:00
rendererData - > currentOffscreenRenderTargetView = NULL ;
2014-03-09 11:06:11 -07:00
return 0 ;
}
2014-03-10 22:53:03 -04:00
textureData = ( D3D11_TextureData * ) texture - > driverdata ;
2014-03-09 11:06:11 -07:00
if ( ! textureData - > mainTextureRenderTargetView ) {
return SDL_SetError ( " specified texture is not a render target " ) ;
}
rendererData - > currentOffscreenRenderTargetView = textureData - > mainTextureRenderTargetView ;
return 0 ;
2013-12-10 22:34:08 -05:00
}
2013-04-13 23:03:46 -04:00
2014-03-10 01:51:03 -07:00
static void
D3D11_SetModelMatrix ( SDL_Renderer * renderer , const Float4X4 * matrix )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
if ( matrix ) {
data - > vertexShaderConstantsData . model = * matrix ;
} else {
data - > vertexShaderConstantsData . model = MatrixIdentity ( ) ;
}
ID3D11DeviceContext_UpdateSubresource ( data - > d3dContext ,
( ID3D11Resource * ) data - > vertexShaderConstants ,
0 ,
NULL ,
& data - > vertexShaderConstantsData ,
0 ,
0
) ;
}
2013-02-02 19:32:44 -05:00
static int
D3D11_UpdateViewport ( SDL_Renderer * renderer )
{
2013-02-17 11:09:07 -05:00
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 22:53:03 -04:00
Float4X4 projection ;
Float4X4 view ;
SDL_FRect orientationAlignedViewport ;
BOOL swapDimensions ;
D3D11_VIEWPORT viewport ;
2013-02-17 11:09:07 -05:00
if ( renderer - > viewport . w = = 0 | | renderer - > viewport . h = = 0 ) {
2014-03-10 01:51:03 -07:00
/* If the viewport is empty, assume that it is because
* SDL_CreateRenderer is calling it , and will call it again later
* with a non - empty viewport .
*/
2013-02-17 11:09:07 -05:00
return 0 ;
}
2014-03-10 01:51:03 -07:00
/* Make sure the SDL viewport gets rotated to that of the physical display's rotation.
* Keep in mind here that the Y - axis will be been inverted ( from Direct3D ' s
* default coordinate system ) so rotations will be done in the opposite
* direction of the DXGI_MODE_ROTATION enumeration .
*/
2014-03-10 02:13:44 -07:00
switch ( data - > rotation ) {
2014-03-09 11:06:11 -07:00
case DXGI_MODE_ROTATION_IDENTITY :
2014-03-10 01:51:03 -07:00
projection = MatrixIdentity ( ) ;
2014-03-09 11:06:11 -07:00
break ;
case DXGI_MODE_ROTATION_ROTATE270 :
2014-03-10 01:51:03 -07:00
projection = MatrixRotationZ ( SDL_static_cast ( float , M_PI * 0.5f ) ) ;
2014-03-09 11:06:11 -07:00
break ;
case DXGI_MODE_ROTATION_ROTATE180 :
2014-03-10 01:51:03 -07:00
projection = MatrixRotationZ ( SDL_static_cast ( float , M_PI ) ) ;
2014-03-09 11:06:11 -07:00
break ;
case DXGI_MODE_ROTATION_ROTATE90 :
2014-03-10 01:51:03 -07:00
projection = MatrixRotationZ ( SDL_static_cast ( float , - M_PI * 0.5f ) ) ;
2014-03-09 11:06:11 -07:00
break ;
default :
return SDL_SetError ( " An unknown DisplayOrientation is being used " ) ;
}
2014-03-10 01:51:03 -07:00
/* Update the view matrix */
view . m [ 0 ] [ 0 ] = 2.0f / renderer - > viewport . w ;
view . m [ 0 ] [ 1 ] = 0.0f ;
view . m [ 0 ] [ 2 ] = 0.0f ;
view . m [ 0 ] [ 3 ] = 0.0f ;
view . m [ 1 ] [ 0 ] = 0.0f ;
view . m [ 1 ] [ 1 ] = - 2.0f / renderer - > viewport . h ;
view . m [ 1 ] [ 2 ] = 0.0f ;
view . m [ 1 ] [ 3 ] = 0.0f ;
view . m [ 2 ] [ 0 ] = 0.0f ;
view . m [ 2 ] [ 1 ] = 0.0f ;
view . m [ 2 ] [ 2 ] = 1.0f ;
view . m [ 2 ] [ 3 ] = 0.0f ;
view . m [ 3 ] [ 0 ] = - 1.0f ;
view . m [ 3 ] [ 1 ] = 1.0f ;
view . m [ 3 ] [ 2 ] = 0.0f ;
view . m [ 3 ] [ 3 ] = 1.0f ;
/* Combine the projection + view matrix together now, as both only get
* set here ( as of this writing , on Dec 26 , 2013 ) . When done , store it
* for eventual transfer to the GPU .
*/
data - > vertexShaderConstantsData . projectionAndView = MatrixMultiply (
2013-12-26 11:03:43 -05:00
view ,
2014-03-10 01:51:03 -07:00
projection ) ;
/* Reset the model matrix */
D3D11_SetModelMatrix ( renderer , NULL ) ;
/* Update the Direct3D viewport, which seems to be aligned to the
* swap buffer ' s coordinate space , which is always in either
* a landscape mode , for all Windows 8 / RT devices , or a portrait mode ,
* for Windows Phone devices .
*/
2014-03-10 22:53:03 -04:00
swapDimensions = D3D11_IsDisplayRotated90Degrees ( data - > rotation ) ;
2014-03-09 11:06:11 -07:00
if ( swapDimensions ) {
orientationAlignedViewport . x = ( float ) renderer - > viewport . y ;
orientationAlignedViewport . y = ( float ) renderer - > viewport . x ;
orientationAlignedViewport . w = ( float ) renderer - > viewport . h ;
orientationAlignedViewport . h = ( float ) renderer - > viewport . w ;
} else {
orientationAlignedViewport . x = ( float ) renderer - > viewport . x ;
orientationAlignedViewport . y = ( float ) renderer - > viewport . y ;
orientationAlignedViewport . w = ( float ) renderer - > viewport . w ;
orientationAlignedViewport . h = ( float ) renderer - > viewport . h ;
}
2014-03-10 01:51:03 -07:00
/* TODO, WinRT: get custom viewports working with non-Landscape modes (Portrait, PortraitFlipped, and LandscapeFlipped) */
2014-03-09 11:06:11 -07:00
viewport . TopLeftX = orientationAlignedViewport . x ;
viewport . TopLeftY = orientationAlignedViewport . y ;
viewport . Width = orientationAlignedViewport . w ;
viewport . Height = orientationAlignedViewport . h ;
viewport . MinDepth = 0.0f ;
viewport . MaxDepth = 1.0f ;
2014-03-10 01:51:03 -07:00
ID3D11DeviceContext_RSSetViewports ( data - > d3dContext , 1 , & viewport ) ;
2013-02-17 23:23:59 -05:00
2013-02-02 19:32:44 -05:00
return 0 ;
}
2013-08-13 20:33:15 -04:00
static int
D3D11_UpdateClipRect ( SDL_Renderer * renderer )
{
2013-12-26 10:18:33 -05:00
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
const SDL_Rect * rect = & renderer - > clip_rect ;
if ( SDL_RectEmpty ( rect ) ) {
2014-03-10 01:51:03 -07:00
ID3D11DeviceContext_RSSetScissorRects ( data - > d3dContext , 0 , NULL ) ;
2013-12-26 10:18:33 -05:00
} else {
D3D11_RECT scissorRect ;
if ( D3D11_GetViewportAlignedD3DRect ( renderer , rect , & scissorRect ) ! = 0 ) {
/* D3D11_GetViewportAlignedD3DRect will have set the SDL error */
return - 1 ;
}
2014-03-10 01:51:03 -07:00
ID3D11DeviceContext_RSSetScissorRects ( data - > d3dContext , 1 , & scissorRect ) ;
2013-12-26 10:18:33 -05:00
}
2013-08-13 20:33:15 -04:00
return 0 ;
}
2014-03-10 01:51:03 -07:00
static void
D3D11_ReleaseMainRenderTargetView ( SDL_Renderer * renderer )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
ID3D11DeviceContext_OMSetRenderTargets ( data - > d3dContext , 0 , NULL , NULL ) ;
SAFE_RELEASE ( data - > mainRenderTargetView ) ;
}
static ID3D11RenderTargetView *
2014-03-09 11:06:11 -07:00
D3D11_GetCurrentRenderTargetView ( SDL_Renderer * renderer )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
if ( data - > currentOffscreenRenderTargetView ) {
return data - > currentOffscreenRenderTargetView ;
} else {
return data - > mainRenderTargetView ;
}
2013-04-13 23:03:46 -04:00
}
2014-03-09 11:06:11 -07:00
static int
D3D11_RenderClear ( SDL_Renderer * renderer )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
const float colorRGBA [ ] = {
( renderer - > r / 255.0f ) ,
( renderer - > g / 255.0f ) ,
( renderer - > b / 255.0f ) ,
( renderer - > a / 255.0f )
} ;
2014-03-10 01:51:03 -07:00
ID3D11DeviceContext_ClearRenderTargetView ( data - > d3dContext ,
D3D11_GetCurrentRenderTargetView ( renderer ) ,
2014-03-09 11:06:11 -07:00
colorRGBA
) ;
return 0 ;
2013-02-09 18:58:13 -05:00
}
2013-02-16 09:10:43 -05:00
static int
D3D11_UpdateVertexBuffer ( SDL_Renderer * renderer ,
2013-12-22 21:13:35 -05:00
const void * vertexData , size_t dataSizeInBytes )
2013-02-09 18:58:13 -05:00
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
2013-03-24 21:19:26 -04:00
D3D11_BUFFER_DESC vertexBufferDesc ;
2014-03-10 01:51:03 -07:00
HRESULT result = S_OK ;
2014-03-10 22:53:03 -04:00
D3D11_SUBRESOURCE_DATA vertexBufferData ;
const UINT stride = sizeof ( VertexPositionColor ) ;
const UINT offset = 0 ;
2013-03-24 21:19:26 -04:00
if ( rendererData - > vertexBuffer ) {
2014-03-10 01:51:03 -07:00
ID3D11Buffer_GetDesc ( rendererData - > vertexBuffer , & vertexBufferDesc ) ;
2013-03-24 21:19:26 -04:00
} else {
2014-03-10 01:51:03 -07:00
SDL_zero ( vertexBufferDesc ) ;
2013-03-24 21:19:26 -04:00
}
2014-03-10 01:51:03 -07:00
if ( rendererData - > vertexBuffer & & vertexBufferDesc . ByteWidth > = dataSizeInBytes ) {
2014-03-09 11:06:11 -07:00
D3D11_MAPPED_SUBRESOURCE mappedResource ;
2014-03-10 01:51:03 -07:00
result = ID3D11DeviceContext_Map ( rendererData - > d3dContext ,
( ID3D11Resource * ) rendererData - > vertexBuffer ,
0 ,
D3D11_MAP_WRITE_DISCARD ,
0 ,
& mappedResource
) ;
2014-03-09 11:06:11 -07:00
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11DeviceContext1::Map [vertex buffer] " , result ) ;
return - 1 ;
}
2014-03-10 01:51:03 -07:00
SDL_memcpy ( mappedResource . pData , vertexData , dataSizeInBytes ) ;
ID3D11DeviceContext_Unmap ( rendererData - > d3dContext , ( ID3D11Resource * ) rendererData - > vertexBuffer , 0 ) ;
2014-03-09 11:06:11 -07:00
} else {
2014-03-10 01:51:03 -07:00
SAFE_RELEASE ( rendererData - > vertexBuffer ) ;
2014-03-09 11:06:11 -07:00
vertexBufferDesc . ByteWidth = dataSizeInBytes ;
vertexBufferDesc . Usage = D3D11_USAGE_DYNAMIC ;
vertexBufferDesc . BindFlags = D3D11_BIND_VERTEX_BUFFER ;
vertexBufferDesc . CPUAccessFlags = D3D11_CPU_ACCESS_WRITE ;
2014-03-10 01:51:03 -07:00
SDL_zero ( vertexBufferData ) ;
2014-03-09 11:06:11 -07:00
vertexBufferData . pSysMem = vertexData ;
vertexBufferData . SysMemPitch = 0 ;
vertexBufferData . SysMemSlicePitch = 0 ;
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreateBuffer ( rendererData - > d3dDevice ,
2014-03-09 11:06:11 -07:00
& vertexBufferDesc ,
& vertexBufferData ,
& rendererData - > vertexBuffer
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateBuffer [vertex buffer] " , result ) ;
return - 1 ;
}
2014-03-10 01:51:03 -07:00
ID3D11DeviceContext_IASetVertexBuffers ( rendererData - > d3dContext ,
0 ,
1 ,
& rendererData - > vertexBuffer ,
& stride ,
& offset
) ;
}
2013-02-16 09:10:43 -05:00
return 0 ;
}
static void
D3D11_RenderStartDrawOp ( SDL_Renderer * renderer )
{
2014-03-10 01:51:03 -07:00
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 22:53:03 -04:00
ID3D11RasterizerState * rasterizerState ;
2014-03-10 01:51:03 -07:00
ID3D11RenderTargetView * renderTargetView = D3D11_GetCurrentRenderTargetView ( renderer ) ;
if ( renderTargetView ! = rendererData - > currentRenderTargetView ) {
ID3D11DeviceContext_OMSetRenderTargets ( rendererData - > d3dContext ,
1 ,
& renderTargetView ,
NULL
) ;
rendererData - > currentRenderTargetView = renderTargetView ;
}
2013-02-16 09:10:43 -05:00
2014-03-10 01:51:03 -07:00
if ( SDL_RectEmpty ( & renderer - > clip_rect ) ) {
rasterizerState = rendererData - > mainRasterizer ;
} else {
rasterizerState = rendererData - > clippedRasterizer ;
}
if ( rasterizerState ! = rendererData - > currentRasterizerState ) {
ID3D11DeviceContext_RSSetState ( rendererData - > d3dContext , rasterizerState ) ;
rendererData - > currentRasterizerState = rasterizerState ;
}
2014-03-09 11:06:11 -07:00
}
static void
D3D11_RenderSetBlendMode ( SDL_Renderer * renderer , SDL_BlendMode blendMode )
{
2014-03-10 01:51:03 -07:00
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-11 12:40:31 -04:00
ID3D11BlendState * blendState = NULL ;
2014-03-09 11:06:11 -07:00
switch ( blendMode ) {
2014-03-10 01:51:03 -07:00
case SDL_BLENDMODE_BLEND :
blendState = rendererData - > blendModeBlend ;
break ;
case SDL_BLENDMODE_ADD :
blendState = rendererData - > blendModeAdd ;
break ;
case SDL_BLENDMODE_MOD :
blendState = rendererData - > blendModeMod ;
break ;
case SDL_BLENDMODE_NONE :
blendState = NULL ;
break ;
}
if ( blendState ! = rendererData - > currentBlendState ) {
ID3D11DeviceContext_OMSetBlendState ( rendererData - > d3dContext , blendState , 0 , 0xFFFFFFFF ) ;
rendererData - > currentBlendState = blendState ;
2014-03-09 11:06:11 -07:00
}
}
2013-02-16 09:10:43 -05:00
static void
D3D11_SetPixelShader ( SDL_Renderer * renderer ,
ID3D11PixelShader * shader ,
2014-03-10 05:44:34 -07:00
int numShaderResources ,
ID3D11ShaderResourceView * * shaderResources ,
2013-02-16 09:10:43 -05:00
ID3D11SamplerState * sampler )
{
2014-03-09 11:06:11 -07:00
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 05:44:34 -07:00
ID3D11ShaderResourceView * shaderResource ;
2014-03-10 01:51:03 -07:00
if ( shader ! = rendererData - > currentShader ) {
ID3D11DeviceContext_PSSetShader ( rendererData - > d3dContext , shader , NULL , 0 ) ;
rendererData - > currentShader = shader ;
}
2014-03-10 05:44:34 -07:00
if ( numShaderResources > 0 ) {
shaderResource = shaderResources [ 0 ] ;
} else {
shaderResource = NULL ;
}
2014-03-10 01:51:03 -07:00
if ( shaderResource ! = rendererData - > currentShaderResource ) {
2014-03-10 05:44:34 -07:00
ID3D11DeviceContext_PSSetShaderResources ( rendererData - > d3dContext , 0 , numShaderResources , shaderResources ) ;
2014-03-10 01:51:03 -07:00
rendererData - > currentShaderResource = shaderResource ;
}
if ( sampler ! = rendererData - > currentSampler ) {
ID3D11DeviceContext_PSSetSamplers ( rendererData - > d3dContext , 0 , 1 , & sampler ) ;
rendererData - > currentSampler = sampler ;
}
2013-02-16 09:10:43 -05:00
}
static void
D3D11_RenderFinishDrawOp ( SDL_Renderer * renderer ,
2013-03-24 21:19:26 -04:00
D3D11_PRIMITIVE_TOPOLOGY primitiveTopology ,
UINT vertexCount )
2013-02-16 09:10:43 -05:00
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-09 11:06:11 -07:00
2014-03-10 01:51:03 -07:00
ID3D11DeviceContext_IASetPrimitiveTopology ( rendererData - > d3dContext , primitiveTopology ) ;
ID3D11DeviceContext_Draw ( rendererData - > d3dContext , vertexCount , 0 ) ;
2013-03-24 21:19:26 -04:00
}
2013-03-24 21:57:40 -04:00
static int
D3D11_RenderDrawPoints ( SDL_Renderer * renderer ,
const SDL_FPoint * points , int count )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
float r , g , b , a ;
2014-03-10 22:53:03 -04:00
VertexPositionColor * vertices ;
int i ;
2013-03-24 21:57:40 -04:00
r = ( float ) ( renderer - > r / 255.0f ) ;
g = ( float ) ( renderer - > g / 255.0f ) ;
b = ( float ) ( renderer - > b / 255.0f ) ;
a = ( float ) ( renderer - > a / 255.0f ) ;
2014-03-10 22:53:03 -04:00
vertices = SDL_stack_alloc ( VertexPositionColor , count ) ;
for ( i = 0 ; i < min ( count , 128 ) ; + + i ) {
2014-03-10 01:51:03 -07:00
const VertexPositionColor v = { { points [ i ] . x , points [ i ] . y , 0.0f } , { 0.0f , 0.0f } , { r , g , b , a } } ;
2014-03-09 11:06:11 -07:00
vertices [ i ] = v ;
}
D3D11_RenderStartDrawOp ( renderer ) ;
D3D11_RenderSetBlendMode ( renderer , renderer - > blendMode ) ;
if ( D3D11_UpdateVertexBuffer ( renderer , vertices , ( unsigned int ) count * sizeof ( VertexPositionColor ) ) ! = 0 ) {
SDL_stack_free ( vertices ) ;
return - 1 ;
}
D3D11_SetPixelShader (
renderer ,
2014-03-10 01:51:03 -07:00
rendererData - > colorPixelShader ,
2014-03-10 05:44:34 -07:00
0 ,
2014-03-10 01:51:03 -07:00
NULL ,
NULL ) ;
2014-03-09 11:06:11 -07:00
D3D11_RenderFinishDrawOp ( renderer , D3D11_PRIMITIVE_TOPOLOGY_POINTLIST , count ) ;
2013-08-28 11:46:02 -04:00
SDL_stack_free ( vertices ) ;
2013-03-24 21:57:40 -04:00
return 0 ;
}
2013-03-24 21:19:26 -04:00
static int
D3D11_RenderDrawLines ( SDL_Renderer * renderer ,
const SDL_FPoint * points , int count )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
float r , g , b , a ;
2014-03-10 22:53:03 -04:00
VertexPositionColor * vertices ;
int i ;
2013-03-24 21:19:26 -04:00
r = ( float ) ( renderer - > r / 255.0f ) ;
g = ( float ) ( renderer - > g / 255.0f ) ;
b = ( float ) ( renderer - > b / 255.0f ) ;
a = ( float ) ( renderer - > a / 255.0f ) ;
2014-03-10 22:53:03 -04:00
vertices = SDL_stack_alloc ( VertexPositionColor , count ) ;
for ( i = 0 ; i < count ; + + i ) {
2014-03-10 01:51:03 -07:00
const VertexPositionColor v = { { points [ i ] . x , points [ i ] . y , 0.0f } , { 0.0f , 0.0f } , { r , g , b , a } } ;
2014-03-09 11:06:11 -07:00
vertices [ i ] = v ;
}
D3D11_RenderStartDrawOp ( renderer ) ;
D3D11_RenderSetBlendMode ( renderer , renderer - > blendMode ) ;
if ( D3D11_UpdateVertexBuffer ( renderer , vertices , ( unsigned int ) count * sizeof ( VertexPositionColor ) ) ! = 0 ) {
SDL_stack_free ( vertices ) ;
return - 1 ;
}
D3D11_SetPixelShader (
renderer ,
2014-03-10 01:51:03 -07:00
rendererData - > colorPixelShader ,
2014-03-10 05:44:34 -07:00
0 ,
2014-03-10 01:51:03 -07:00
NULL ,
NULL ) ;
2014-03-09 11:06:11 -07:00
D3D11_RenderFinishDrawOp ( renderer , D3D11_PRIMITIVE_TOPOLOGY_LINESTRIP , count ) ;
2013-08-28 11:46:02 -04:00
SDL_stack_free ( vertices ) ;
2013-03-24 21:19:26 -04:00
return 0 ;
2013-02-16 09:10:43 -05:00
}
static int
D3D11_RenderFillRects ( SDL_Renderer * renderer ,
const SDL_FRect * rects , int count )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
float r , g , b , a ;
2014-03-10 22:53:03 -04:00
int i ;
2013-02-16 09:10:43 -05:00
2013-02-16 16:53:06 -05:00
r = ( float ) ( renderer - > r / 255.0f ) ;
g = ( float ) ( renderer - > g / 255.0f ) ;
b = ( float ) ( renderer - > b / 255.0f ) ;
a = ( float ) ( renderer - > a / 255.0f ) ;
2013-02-16 09:10:43 -05:00
2014-03-10 22:53:03 -04:00
for ( i = 0 ; i < count ; + + i ) {
2014-03-09 11:06:11 -07:00
VertexPositionColor vertices [ ] = {
2014-03-10 01:51:03 -07:00
{ { rects [ i ] . x , rects [ i ] . y , 0.0f } , { 0.0f , 0.0f } , { r , g , b , a } } ,
{ { rects [ i ] . x , rects [ i ] . y + rects [ i ] . h , 0.0f } , { 0.0f , 0.0f } , { r , g , b , a } } ,
{ { rects [ i ] . x + rects [ i ] . w , rects [ i ] . y , 0.0f } , { 0.0f , 0.0f } , { r , g , b , a } } ,
{ { rects [ i ] . x + rects [ i ] . w , rects [ i ] . y + rects [ i ] . h , 0.0f } , { 0.0f , 0.0f } , { r , g , b , a } } ,
2014-03-09 11:06:11 -07:00
} ;
2014-03-10 22:53:03 -04:00
D3D11_RenderStartDrawOp ( renderer ) ;
D3D11_RenderSetBlendMode ( renderer , renderer - > blendMode ) ;
2014-03-09 11:06:11 -07:00
if ( D3D11_UpdateVertexBuffer ( renderer , vertices , sizeof ( vertices ) ) ! = 0 ) {
return - 1 ;
}
D3D11_SetPixelShader (
renderer ,
2014-03-10 01:51:03 -07:00
rendererData - > colorPixelShader ,
2014-03-10 05:44:34 -07:00
0 ,
2014-03-10 01:51:03 -07:00
NULL ,
NULL ) ;
2014-03-09 11:06:11 -07:00
2014-03-10 01:51:03 -07:00
D3D11_RenderFinishDrawOp ( renderer , D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP , SDL_arraysize ( vertices ) ) ;
2014-03-09 11:06:11 -07:00
}
2013-02-16 09:10:43 -05:00
return 0 ;
}
2013-11-01 22:54:39 -04:00
static ID3D11SamplerState *
D3D11_RenderGetSampler ( SDL_Renderer * renderer , SDL_Texture * texture )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
D3D11_TextureData * textureData = ( D3D11_TextureData * ) texture - > driverdata ;
switch ( textureData - > scaleMode ) {
2014-03-10 01:51:03 -07:00
case D3D11_FILTER_MIN_MAG_MIP_POINT :
return rendererData - > nearestPixelSampler ;
case D3D11_FILTER_MIN_MAG_MIP_LINEAR :
return rendererData - > linearSampler ;
default :
return NULL ;
2013-11-01 22:54:39 -04:00
}
}
2013-02-16 09:10:43 -05:00
static int
D3D11_RenderCopy ( SDL_Renderer * renderer , SDL_Texture * texture ,
const SDL_Rect * srcrect , const SDL_FRect * dstrect )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
D3D11_TextureData * textureData = ( D3D11_TextureData * ) texture - > driverdata ;
2014-03-10 22:53:03 -04:00
float minu , maxu , minv , maxv ;
Float4 color ;
VertexPositionColor vertices [ 4 ] ;
ID3D11SamplerState * textureSampler ;
2013-02-16 09:10:43 -05:00
D3D11_RenderStartDrawOp ( renderer ) ;
2013-02-23 22:58:09 -05:00
D3D11_RenderSetBlendMode ( renderer , texture - > blendMode ) ;
2013-02-24 12:27:28 -05:00
2014-03-10 22:53:03 -04:00
minu = ( float ) srcrect - > x / texture - > w ;
maxu = ( float ) ( srcrect - > x + srcrect - > w ) / texture - > w ;
minv = ( float ) srcrect - > y / texture - > h ;
maxv = ( float ) ( srcrect - > y + srcrect - > h ) / texture - > h ;
2013-04-07 22:35:58 -04:00
2014-03-10 22:53:03 -04:00
color . x = 1.0f ; /* red */
color . y = 1.0f ; /* green */
color . z = 1.0f ; /* blue */
color . w = 1.0f ; /* alpha */
2013-04-07 22:35:58 -04:00
if ( texture - > modMode & SDL_TEXTUREMODULATE_COLOR ) {
2014-03-10 22:53:03 -04:00
color . x = ( float ) ( texture - > r / 255.0f ) ; /* red */
color . y = ( float ) ( texture - > g / 255.0f ) ; /* green */
color . z = ( float ) ( texture - > b / 255.0f ) ; /* blue */
2013-04-07 22:35:58 -04:00
}
if ( texture - > modMode & SDL_TEXTUREMODULATE_ALPHA ) {
2014-03-10 22:53:03 -04:00
color . w = ( float ) ( texture - > a / 255.0f ) ; /* alpha */
}
vertices [ 0 ] . pos . x = dstrect - > x ;
vertices [ 0 ] . pos . y = dstrect - > y ;
vertices [ 0 ] . pos . z = 0.0f ;
vertices [ 0 ] . tex . x = minu ;
vertices [ 0 ] . tex . y = minv ;
vertices [ 0 ] . color = color ;
vertices [ 1 ] . pos . x = dstrect - > x ;
vertices [ 1 ] . pos . y = dstrect - > y + dstrect - > h ;
vertices [ 1 ] . pos . z = 0.0f ;
vertices [ 1 ] . tex . x = minu ;
vertices [ 1 ] . tex . y = maxv ;
vertices [ 1 ] . color = color ;
vertices [ 2 ] . pos . x = dstrect - > x + dstrect - > w ;
vertices [ 2 ] . pos . y = dstrect - > y ;
vertices [ 2 ] . pos . z = 0.0f ;
vertices [ 2 ] . tex . x = maxu ;
vertices [ 2 ] . tex . y = minv ;
vertices [ 2 ] . color = color ;
vertices [ 3 ] . pos . x = dstrect - > x + dstrect - > w ;
vertices [ 3 ] . pos . y = dstrect - > y + dstrect - > h ;
vertices [ 3 ] . pos . z = 0.0f ;
vertices [ 3 ] . tex . x = maxu ;
vertices [ 3 ] . tex . y = maxv ;
vertices [ 3 ] . color = color ;
2014-03-09 11:06:11 -07:00
if ( D3D11_UpdateVertexBuffer ( renderer , vertices , sizeof ( vertices ) ) ! = 0 ) {
return - 1 ;
}
2014-03-10 22:53:03 -04:00
textureSampler = D3D11_RenderGetSampler ( renderer , texture ) ;
2014-03-10 05:44:34 -07:00
if ( textureData - > yuv ) {
ID3D11ShaderResourceView * shaderResources [ ] = {
textureData - > mainTextureResourceView ,
textureData - > mainTextureResourceViewU ,
textureData - > mainTextureResourceViewV
} ;
D3D11_SetPixelShader (
renderer ,
rendererData - > yuvPixelShader ,
SDL_arraysize ( shaderResources ) ,
shaderResources ,
textureSampler ) ;
} else {
D3D11_SetPixelShader (
renderer ,
rendererData - > texturePixelShader ,
1 ,
& textureData - > mainTextureResourceView ,
textureSampler ) ;
}
2014-03-09 11:06:11 -07:00
D3D11_RenderFinishDrawOp ( renderer , D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP , sizeof ( vertices ) / sizeof ( VertexPositionColor ) ) ;
2013-04-01 22:33:37 -04:00
return 0 ;
}
static int
D3D11_RenderCopyEx ( SDL_Renderer * renderer , SDL_Texture * texture ,
const SDL_Rect * srcrect , const SDL_FRect * dstrect ,
const double angle , const SDL_FPoint * center , const SDL_RendererFlip flip )
{
D3D11_RenderData * rendererData = ( D3D11_RenderData * ) renderer - > driverdata ;
D3D11_TextureData * textureData = ( D3D11_TextureData * ) texture - > driverdata ;
2014-03-10 22:53:03 -04:00
float minu , maxu , minv , maxv ;
Float4 color ;
Float4X4 modelMatrix ;
float minx , maxx , miny , maxy ;
VertexPositionColor vertices [ 4 ] ;
ID3D11SamplerState * textureSampler ;
2013-04-01 22:33:37 -04:00
D3D11_RenderStartDrawOp ( renderer ) ;
D3D11_RenderSetBlendMode ( renderer , texture - > blendMode ) ;
2014-03-10 22:53:03 -04:00
minu = ( float ) srcrect - > x / texture - > w ;
maxu = ( float ) ( srcrect - > x + srcrect - > w ) / texture - > w ;
minv = ( float ) srcrect - > y / texture - > h ;
maxv = ( float ) ( srcrect - > y + srcrect - > h ) / texture - > h ;
2013-04-01 22:33:37 -04:00
2014-03-10 22:53:03 -04:00
color . x = 1.0f ; /* red */
color . y = 1.0f ; /* green */
color . z = 1.0f ; /* blue */
color . w = 1.0f ; /* alpha */
2013-04-07 22:35:58 -04:00
if ( texture - > modMode & SDL_TEXTUREMODULATE_COLOR ) {
2014-03-10 22:53:03 -04:00
color . x = ( float ) ( texture - > r / 255.0f ) ; /* red */
color . y = ( float ) ( texture - > g / 255.0f ) ; /* green */
color . z = ( float ) ( texture - > b / 255.0f ) ; /* blue */
2013-04-07 22:35:58 -04:00
}
if ( texture - > modMode & SDL_TEXTUREMODULATE_ALPHA ) {
2014-03-10 22:53:03 -04:00
color . w = ( float ) ( texture - > a / 255.0f ) ; /* alpha */
2013-04-07 22:35:58 -04:00
}
2013-04-01 22:33:37 -04:00
if ( flip & SDL_FLIP_HORIZONTAL ) {
float tmp = maxu ;
maxu = minu ;
minu = tmp ;
}
if ( flip & SDL_FLIP_VERTICAL ) {
float tmp = maxv ;
maxv = minv ;
minv = tmp ;
}
2013-04-02 00:09:49 -04:00
2014-03-10 22:53:03 -04:00
modelMatrix = MatrixMultiply (
2014-03-10 01:51:03 -07:00
MatrixRotationZ ( ( float ) ( M_PI * ( float ) angle / 180.0f ) ) ,
MatrixTranslation ( dstrect - > x + center - > x , dstrect - > y + center - > y , 0 )
) ;
2014-03-10 17:19:19 -07:00
D3D11_SetModelMatrix ( renderer , & modelMatrix ) ;
2013-04-02 00:09:49 -04:00
2014-03-10 22:53:03 -04:00
minx = - center - > x ;
maxx = dstrect - > w - center - > x ;
miny = - center - > y ;
maxy = dstrect - > h - center - > y ;
vertices [ 0 ] . pos . x = minx ;
vertices [ 0 ] . pos . y = miny ;
vertices [ 0 ] . pos . z = 0.0f ;
vertices [ 0 ] . tex . x = minu ;
vertices [ 0 ] . tex . y = minv ;
vertices [ 0 ] . color = color ;
vertices [ 1 ] . pos . x = minx ;
vertices [ 1 ] . pos . y = maxy ;
vertices [ 1 ] . pos . z = 0.0f ;
vertices [ 1 ] . tex . x = minu ;
vertices [ 1 ] . tex . y = maxv ;
vertices [ 1 ] . color = color ;
vertices [ 2 ] . pos . x = maxx ;
vertices [ 2 ] . pos . y = miny ;
vertices [ 2 ] . pos . z = 0.0f ;
vertices [ 2 ] . tex . x = maxu ;
vertices [ 2 ] . tex . y = minv ;
vertices [ 2 ] . color = color ;
vertices [ 3 ] . pos . x = maxx ;
vertices [ 3 ] . pos . y = maxy ;
vertices [ 3 ] . pos . z = 0.0f ;
vertices [ 3 ] . tex . x = maxu ;
vertices [ 3 ] . tex . y = maxv ;
vertices [ 3 ] . color = color ;
2014-03-09 11:06:11 -07:00
if ( D3D11_UpdateVertexBuffer ( renderer , vertices , sizeof ( vertices ) ) ! = 0 ) {
return - 1 ;
}
2014-03-10 22:53:03 -04:00
textureSampler = D3D11_RenderGetSampler ( renderer , texture ) ;
2014-03-10 05:44:34 -07:00
if ( textureData - > yuv ) {
ID3D11ShaderResourceView * shaderResources [ ] = {
textureData - > mainTextureResourceView ,
textureData - > mainTextureResourceViewU ,
textureData - > mainTextureResourceViewV
} ;
D3D11_SetPixelShader (
renderer ,
rendererData - > yuvPixelShader ,
SDL_arraysize ( shaderResources ) ,
shaderResources ,
textureSampler ) ;
} else {
D3D11_SetPixelShader (
renderer ,
rendererData - > texturePixelShader ,
1 ,
& textureData - > mainTextureResourceView ,
textureSampler ) ;
}
2014-03-09 11:06:11 -07:00
D3D11_RenderFinishDrawOp ( renderer , D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP , sizeof ( vertices ) / sizeof ( VertexPositionColor ) ) ;
2014-03-10 17:19:19 -07:00
D3D11_SetModelMatrix ( renderer , NULL ) ;
2013-02-09 18:58:13 -05:00
return 0 ;
}
2013-04-01 21:34:47 -04:00
static int
D3D11_RenderReadPixels ( SDL_Renderer * renderer , const SDL_Rect * rect ,
Uint32 format , void * pixels , int pitch )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 01:51:03 -07:00
ID3D11Texture2D * backBuffer = NULL ;
ID3D11Texture2D * stagingTexture = NULL ;
HRESULT result ;
int status = - 1 ;
2014-03-10 22:53:03 -04:00
D3D11_TEXTURE2D_DESC stagingTextureDesc ;
D3D11_RECT srcRect ;
D3D11_BOX srcBox ;
D3D11_MAPPED_SUBRESOURCE textureMemory ;
2013-04-01 21:34:47 -04:00
2014-03-10 01:51:03 -07:00
/* Retrieve a pointer to the back buffer: */
result = IDXGISwapChain_GetBuffer ( data - > swapChain ,
2014-03-09 11:06:11 -07:00
0 ,
2014-03-10 01:51:03 -07:00
& IID_ID3D11Texture2D ,
2014-03-09 11:06:11 -07:00
& backBuffer
) ;
if ( FAILED ( result ) ) {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGISwapChain1::GetBuffer [get back buffer] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2013-04-01 21:34:47 -04:00
}
2014-03-10 01:51:03 -07:00
/* Create a staging texture to copy the screen's data to: */
ID3D11Texture2D_GetDesc ( backBuffer , & stagingTextureDesc ) ;
2013-04-01 21:34:47 -04:00
stagingTextureDesc . Width = rect - > w ;
stagingTextureDesc . Height = rect - > h ;
stagingTextureDesc . BindFlags = 0 ;
stagingTextureDesc . MiscFlags = 0 ;
stagingTextureDesc . CPUAccessFlags = D3D11_CPU_ACCESS_READ ;
stagingTextureDesc . Usage = D3D11_USAGE_STAGING ;
2014-03-10 01:51:03 -07:00
result = ID3D11Device_CreateTexture2D ( data - > d3dDevice ,
2013-04-01 21:34:47 -04:00
& stagingTextureDesc ,
NULL ,
& stagingTexture ) ;
if ( FAILED ( result ) ) {
2013-12-25 12:43:26 -05:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11Device1::CreateTexture2D [create staging texture] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2013-04-01 21:34:47 -04:00
}
2014-03-10 01:51:03 -07:00
/* Copy the desired portion of the back buffer to the staging texture: */
2013-12-26 10:18:33 -05:00
if ( D3D11_GetViewportAlignedD3DRect ( renderer , rect , & srcRect ) ! = 0 ) {
/* D3D11_GetViewportAlignedD3DRect will have set the SDL error */
2014-03-10 01:51:03 -07:00
goto done ;
2013-12-10 22:34:08 -05:00
}
2013-12-26 10:18:33 -05:00
srcBox . left = srcRect . left ;
srcBox . right = srcRect . right ;
srcBox . top = srcRect . top ;
srcBox . bottom = srcRect . bottom ;
2013-04-01 21:34:47 -04:00
srcBox . front = 0 ;
srcBox . back = 1 ;
2014-03-10 01:51:03 -07:00
ID3D11DeviceContext_CopySubresourceRegion ( data - > d3dContext ,
( ID3D11Resource * ) stagingTexture ,
0 ,
2013-04-01 21:34:47 -04:00
0 , 0 , 0 ,
2014-03-10 01:51:03 -07:00
( ID3D11Resource * ) backBuffer ,
0 ,
2013-04-01 21:34:47 -04:00
& srcBox ) ;
2014-03-10 01:51:03 -07:00
/* Map the staging texture's data to CPU-accessible memory: */
result = ID3D11DeviceContext_Map ( data - > d3dContext ,
( ID3D11Resource * ) stagingTexture ,
0 ,
2013-04-01 21:34:47 -04:00
D3D11_MAP_READ ,
0 ,
& textureMemory ) ;
if ( FAILED ( result ) ) {
2013-12-25 12:43:26 -05:00
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , ID3D11DeviceContext1::Map [map staging texture] " , result ) ;
2014-03-10 01:51:03 -07:00
goto done ;
2013-04-01 21:34:47 -04:00
}
2014-03-10 01:51:03 -07:00
/* Copy the data into the desired buffer, converting pixels to the
* desired format at the same time :
*/
2014-03-09 11:06:11 -07:00
if ( SDL_ConvertPixels (
rect - > w , rect - > h ,
DXGIFormatToSDLPixelFormat ( stagingTextureDesc . Format ) ,
textureMemory . pData ,
textureMemory . RowPitch ,
format ,
pixels ,
2014-03-10 02:13:44 -07:00
pitch ) ! = 0 ) {
2014-03-10 01:51:03 -07:00
/* When SDL_ConvertPixels fails, it'll have already set the format.
* Get the error message , and attach some extra data to it .
*/
char errorMessage [ 1024 ] ;
SDL_snprintf ( errorMessage , sizeof ( errorMessage ) , __FUNCTION__ " , Convert Pixels failed: %s " , SDL_GetError ( ) ) ;
SDL_SetError ( errorMessage ) ;
goto done ;
}
/* Unmap the texture: */
ID3D11DeviceContext_Unmap ( data - > d3dContext ,
( ID3D11Resource * ) stagingTexture ,
0 ) ;
2014-03-09 11:06:11 -07:00
2014-03-10 01:51:03 -07:00
status = 0 ;
2014-03-09 11:06:11 -07:00
2014-03-10 01:51:03 -07:00
done :
SAFE_RELEASE ( backBuffer ) ;
SAFE_RELEASE ( stagingTexture ) ;
return status ;
2013-04-01 21:34:47 -04:00
}
2013-02-02 21:05:32 -05:00
static void
D3D11_RenderPresent ( SDL_Renderer * renderer )
{
D3D11_RenderData * data = ( D3D11_RenderData * ) renderer - > driverdata ;
2014-03-10 01:51:03 -07:00
UINT syncInterval ;
UINT presentFlags ;
2014-03-10 22:53:03 -04:00
HRESULT result ;
DXGI_PRESENT_PARAMETERS parameters ;
2014-03-10 01:51:03 -07:00
if ( renderer - > info . flags & SDL_RENDERER_PRESENTVSYNC ) {
syncInterval = 1 ;
presentFlags = 0 ;
} else {
syncInterval = 0 ;
presentFlags = DXGI_PRESENT_DO_NOT_WAIT ;
}
2013-02-02 21:05:32 -05:00
2014-03-09 11:06:11 -07:00
# if WINAPI_FAMILY == WINAPI_FAMILY_PHONE_APP
2014-03-10 22:53:03 -04:00
result = IDXGISwapChain_Present ( data - > swapChain , syncInterval , presentFlags ) ;
2014-03-09 11:06:11 -07:00
# else
2014-03-10 01:51:03 -07:00
/* The application may optionally specify "dirty" or "scroll"
* rects to improve efficiency in certain scenarios .
* This option is not available on Windows Phone 8 , to note .
*/
SDL_zero ( parameters ) ;
2014-03-10 22:53:03 -04:00
result = IDXGISwapChain1_Present1 ( data - > swapChain , syncInterval , presentFlags , & parameters ) ;
2014-03-09 11:06:11 -07:00
# endif
2014-03-10 01:51:03 -07:00
/* Discard the contents of the render target.
* This is a valid operation only when the existing contents will be entirely
* overwritten . If dirty or scroll rects are used , this call should be removed .
*/
ID3D11DeviceContext1_DiscardView ( data - > d3dContext , ( ID3D11View * ) data - > mainRenderTargetView ) ;
/* When the present flips, it unbinds the current view, so bind it again on the next draw call */
data - > currentRenderTargetView = NULL ;
if ( FAILED ( result ) & & result ! = DXGI_ERROR_WAS_STILL_DRAWING ) {
/* If the device was removed either by a disconnect or a driver upgrade, we
* must recreate all device resources .
*
* TODO , WinRT : consider throwing an exception if D3D11_RenderPresent fails , especially if there is a way to salvage debug info from users ' machines
*/
2014-03-10 15:00:59 -07:00
if ( result = = DXGI_ERROR_DEVICE_REMOVED ) {
2014-03-10 01:51:03 -07:00
D3D11_HandleDeviceLost ( renderer ) ;
2014-03-10 15:00:59 -07:00
} else if ( result = = DXGI_ERROR_INVALID_CALL ) {
/* We probably went through a fullscreen <-> windowed transition */
D3D11_CreateWindowSizeDependentResources ( renderer ) ;
2014-03-10 01:51:03 -07:00
} else {
WIN_SetErrorFromHRESULT ( __FUNCTION__ " , IDXGISwapChain::Present " , result ) ;
2014-03-09 11:06:11 -07:00
}
}
2013-02-02 21:05:32 -05:00
}
2013-12-25 23:46:19 -05:00
# endif /* SDL_VIDEO_RENDER_D3D11 && !SDL_RENDER_DISABLED */
2013-02-02 19:32:44 -05:00
/* vi: set ts=4 sw=4 expandtab: */