diff --git a/CMakeLists.txt b/CMakeLists.txt index 9a5424c..7fdc263 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -21,6 +21,7 @@ cmake_minimum_required(VERSION 3.12.1) +option (GFX_API_DX11 "Build with DX11" ON) option (GFX_API_DX12 "Build with DX12" ON) option (GFX_API_VK "Build with Vulkan" ON) @@ -31,6 +32,8 @@ else() set_property(DIRECTORY ${CMAKE_PROJECT_DIR} PROPERTY VS_STARTUP_PROJECT ${PROJECT_NAME}) + set(GFX_API_DX11 OFF) + if(GFX_API STREQUAL DX12) set(GFX_API_DX12 ON) set(GFX_API_VK OFF) @@ -73,6 +76,7 @@ add_compile_options(/MP) add_compile_definitions($<$:USE_PIX>) # override build options in ffx-fsr2-api cmake +option (FFX_FSR2_API_DX11 "Build FSR 2.0 DX11 backend" ${GFX_API_DX11}) option (FFX_FSR2_API_DX12 "Build FSR 2.0 DX12 backend" ${GFX_API_DX12}) option (FFX_FSR2_API_VK "Build FSR 2.0 Vulkan backend" ${GFX_API_VK}) @@ -88,4 +92,7 @@ endif() if(GFX_API_DX12) add_subdirectory(src/DX12) endif() +if(GFX_API_DX11) + add_subdirectory(src/DX11) +endif() diff --git a/build/GenerateSolutionDX11.bat b/build/GenerateSolutionDX11.bat new file mode 100644 index 0000000..4ea3f9c --- /dev/null +++ b/build/GenerateSolutionDX11.bat @@ -0,0 +1,19 @@ +@echo off +setlocal enabledelayedexpansion + +echo Checking pre-requisites... + +:: Check if CMake is installed +cmake --version > nul 2>&1 +if %errorlevel% NEQ 0 ( + echo Cannot find path to cmake. Is CMake installed? Exiting... + exit /b -1 +) else ( + echo CMake - Ready. +) + +:: Call CMake +mkdir DX11 +cd DX11 +cmake -A x64 ..\.. -DGFX_API_DX11=ON -DGFX_API_DX12=OFF -DGFX_API_VK=OFF +cd .. diff --git a/build/GenerateSolutionDX11DLL.bat b/build/GenerateSolutionDX11DLL.bat new file mode 100644 index 0000000..5dbbbf9 --- /dev/null +++ b/build/GenerateSolutionDX11DLL.bat @@ -0,0 +1,19 @@ +@echo off +setlocal enabledelayedexpansion + +echo Checking pre-requisites... + +:: Check if CMake is installed +cmake --version > nul 2>&1 +if %errorlevel% NEQ 0 ( + echo Cannot find path to cmake. Is CMake installed? Exiting... + exit /b -1 +) else ( + echo CMake - Ready. +) + +:: Call CMake +mkdir DX11 +cd DX11 +cmake -A x64 ..\.. -DGFX_API_DX11=ON -DGFX_API_DX12=OFF -DGFX_API_VK=OFF -DFSR2_BUILD_AS_DLL=1 +cd .. diff --git a/media/dx11/readme.txt b/media/dx11/readme.txt new file mode 100644 index 0000000..3da072f --- /dev/null +++ b/media/dx11/readme.txt @@ -0,0 +1,6 @@ +The media files in the tank and ui subfolders are from the Microsoft DirectX SDK Samples: +https://github.com/walbourn/directx-sdk-samples + +(The files in tank are from the softparticles media folder in the Microsoft DirectX SDK Samples.) + +They are distributed under the terms of the MIT License. \ No newline at end of file diff --git a/media/dx11/tank/MIT.txt b/media/dx11/tank/MIT.txt new file mode 100644 index 0000000..a2336db --- /dev/null +++ b/media/dx11/tank/MIT.txt @@ -0,0 +1,21 @@ + The MIT License (MIT) + +Copyright (c) 2015 Microsoft Corp + +Permission is hereby granted, free of charge, to any person obtaining a copy of this +software and associated documentation files (the "Software"), to deal in the Software +without restriction, including without limitation the rights to use, copy, modify, +merge, publish, distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be included in all copies +or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, +INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A +PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF +CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE +OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + diff --git a/media/dx11/tank/TankScene.sdkmesh b/media/dx11/tank/TankScene.sdkmesh new file mode 100644 index 0000000..ba0aa09 Binary files /dev/null and b/media/dx11/tank/TankScene.sdkmesh differ diff --git a/media/dx11/tank/colorgradient.dds b/media/dx11/tank/colorgradient.dds new file mode 100644 index 0000000..130d055 Binary files /dev/null and b/media/dx11/tank/colorgradient.dds differ diff --git a/media/dx11/tank/desert_sky.dds b/media/dx11/tank/desert_sky.dds new file mode 100644 index 0000000..2c5d8dd Binary files /dev/null and b/media/dx11/tank/desert_sky.dds differ diff --git a/media/dx11/tank/desertsky.sdkmesh b/media/dx11/tank/desertsky.sdkmesh new file mode 100644 index 0000000..f0f30be Binary files /dev/null and b/media/dx11/tank/desertsky.sdkmesh differ diff --git a/media/dx11/tank/ground_diff.dds b/media/dx11/tank/ground_diff.dds new file mode 100644 index 0000000..1870df1 Binary files /dev/null and b/media/dx11/tank/ground_diff.dds differ diff --git a/media/dx11/tank/ground_norm.dds b/media/dx11/tank/ground_norm.dds new file mode 100644 index 0000000..67e9014 Binary files /dev/null and b/media/dx11/tank/ground_norm.dds differ diff --git a/media/dx11/tank/left_engine_diff.dds b/media/dx11/tank/left_engine_diff.dds new file mode 100644 index 0000000..73e5307 Binary files /dev/null and b/media/dx11/tank/left_engine_diff.dds differ diff --git a/media/dx11/tank/left_engine_norm.dds b/media/dx11/tank/left_engine_norm.dds new file mode 100644 index 0000000..bf27d49 Binary files /dev/null and b/media/dx11/tank/left_engine_norm.dds differ diff --git a/media/dx11/tank/smokevol1.dds b/media/dx11/tank/smokevol1.dds new file mode 100644 index 0000000..a9ede60 Binary files /dev/null and b/media/dx11/tank/smokevol1.dds differ diff --git a/media/dx11/tank/turret_diff.dds b/media/dx11/tank/turret_diff.dds new file mode 100644 index 0000000..c1a7299 Binary files /dev/null and b/media/dx11/tank/turret_diff.dds differ diff --git a/media/dx11/tank/turret_norm.dds b/media/dx11/tank/turret_norm.dds new file mode 100644 index 0000000..1e31e4f Binary files /dev/null and b/media/dx11/tank/turret_norm.dds differ diff --git a/media/dx11/ui/AMD_FidelityFX.dds b/media/dx11/ui/AMD_FidelityFX.dds new file mode 100644 index 0000000..c2e8366 Binary files /dev/null and b/media/dx11/ui/AMD_FidelityFX.dds differ diff --git a/media/dx11/ui/Font.dds b/media/dx11/ui/Font.dds new file mode 100644 index 0000000..37514f5 Binary files /dev/null and b/media/dx11/ui/Font.dds differ diff --git a/media/dx11/ui/MIT.txt b/media/dx11/ui/MIT.txt new file mode 100644 index 0000000..a2336db --- /dev/null +++ b/media/dx11/ui/MIT.txt @@ -0,0 +1,21 @@ + The MIT License (MIT) + +Copyright (c) 2015 Microsoft Corp + +Permission is hereby granted, free of charge, to any person obtaining a copy of this +software and associated documentation files (the "Software"), to deal in the Software +without restriction, including without limitation the rights to use, copy, modify, +merge, publish, distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be included in all copies +or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, +INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A +PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF +CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE +OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + diff --git a/media/dx11/ui/dxutcontrols.dds b/media/dx11/ui/dxutcontrols.dds new file mode 100644 index 0000000..b5f52e1 Binary files /dev/null and b/media/dx11/ui/dxutcontrols.dds differ diff --git a/src/DX11/CMakeLists.txt b/src/DX11/CMakeLists.txt new file mode 100644 index 0000000..37ff620 --- /dev/null +++ b/src/DX11/CMakeLists.txt @@ -0,0 +1,49 @@ +# This file is part of the FidelityFX SDK. +# +# Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +add_subdirectory(framework/dxut) +add_subdirectory(framework/amd_sdk) +add_subdirectory(framework/amd_lib) + +set(FSR2_Sample_DX11_SOURCES + FSR2DX11Sample.cpp + FSR2DX11Sample.h + Fsr2Wrapper.cpp + Fsr2Wrapper.h + ResourceFiles/GPUOpenIcon.rc + ResourceFiles/dpiaware.manifest +) + +set(FSR2_Sample_DX11_SHADERS + ${CMAKE_CURRENT_SOURCE_DIR}/Shaders/FSR2DX11Sample.hlsl +) +set(FSR2_Sample_DX11_CONFIG + ${CMAKE_CURRENT_SOURCE_DIR}/FSR2_Sample_DX11.json +) + +copyTargetCommand("${FSR2_Sample_DX11_SHADERS}" ${CMAKE_HOME_DIRECTORY}/bin/ShaderLibDX/dx11 dx11_sample_shaders) +copyTargetCommand("${FSR2_Sample_DX11_CONFIG}" ${CMAKE_RUNTIME_OUTPUT_DIRECTORY} dx11_sample_config) + +add_executable(FSR2_Sample_DX11 WIN32 ${FSR2_Sample_DX11_SOURCES} ${FSR2_Sample_DX11_SHADERS}) +target_link_libraries(FSR2_Sample_DX11 PUBLIC comctl32 Usp10 NJSON amd_lib_minimal amd_sdk_minimal d3dcompiler D3D11 ffx_fsr2_api_x64 ffx_fsr2_api_dx11_x64) +set_target_properties(FSR2_Sample_DX11 PROPERTIES VS_DEBUGGER_WORKING_DIRECTORY "${CMAKE_HOME_DIRECTORY}/bin" DEBUG_POSTFIX "d") +target_compile_definitions(FSR2_Sample_DX11 PRIVATE _UNICODE UNICODE) +add_dependencies(FSR2_Sample_DX11 dx11_sample_shaders dx11_sample_config) diff --git a/src/DX11/FSR2DX11Sample.cpp b/src/DX11/FSR2DX11Sample.cpp new file mode 100644 index 0000000..3756f6f --- /dev/null +++ b/src/DX11/FSR2DX11Sample.cpp @@ -0,0 +1,1332 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +// DXUT includes +#include "DXUT.h" +#include "DXUTcamera.h" +#include "DXUTgui.h" +#include "DXUTsettingsdlg.h" +#include "SDKmisc.h" + +#include "json.h" + +// AMD includes +#include "AMD_LIB.h" +#include "AMD_SDK.h" + +#include "Fsr2Wrapper.h" + +#include +#include +#include + +#include +#define _SILENCE_EXPERIMENTAL_FILESYSTEM_DEPRECATION_WARNING +#include + +#pragma warning(disable : 4201) // disable nameless struct/union warnings +#include "FSR2DX11Sample.h" + +#pragma warning(disable : 4100) // disable unreferenced formal parameter warnings +#pragma warning(disable : 4238) // disable class rvalue used as lvalue warnings + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +// UI Resources +//-------------------------------------------------------------------------------------- +CDXUTDialogResourceManager g_DialogResourceManager; // Manager for shared resources of dialogs +CDXUTTextHelper* g_pTxtHelper = NULL; + +CFirstPersonCamera g_Viewer[2]; +S_CAMERA_DESC g_ViewerData[2]; +CFirstPersonCamera* g_pCurrentCamera = &g_Viewer[0]; +CFirstPersonCamera* g_pPreviousCamera = &g_Viewer[1]; +S_CAMERA_DESC* g_pCurrentData = &g_ViewerData[0]; +S_CAMERA_DESC* g_pPreviousData = &g_ViewerData[1]; + +uint32_t g_FrameIndex = 0; + +float g_CameraArcShotAngle = 0.0f; +float g_CameraArcShotSpeed = 0.25f; +float g_CameraJitterX = 0.0f; +float g_CameraJitterY = 0.0f; + +// AMD helper classes defined here +static AMD::MagnifyTool g_MagnifyTool; +static AMD::HUD g_HUD; + +// Global boolean for HUD rendering +bool g_bRenderHUD = true; +bool g_bRotateCamera = true; +bool g_bSaveScreenShot = false; + +//-------------------------------------------------------------------------------------- +// Mesh +//-------------------------------------------------------------------------------------- +AMD::Mesh g_Model; +S_MODEL_DESC g_ModelDesc; + +#define NUM_OF_BUFFER 2 + +AMD::Texture2D g_appColorBuffer[NUM_OF_BUFFER]; +AMD::Texture2D g_appVelocityBuffer[NUM_OF_BUFFER]; +AMD::Texture2D g_appDepthBuffer[NUM_OF_BUFFER]; +AMD::Texture2D g_appUpscaledSurface; +ID3D11VertexShader* g_d3dFullScreenVS = NULL; +ID3D11PixelShader* g_d3dFullScreenPS = NULL; + +// Index for double buffer +int g_nBufferIdx = 0; + + +//-------------------------------------------------------------------------------------- +// D3D11 Model Rendering Interfaces +//-------------------------------------------------------------------------------------- +ID3D11InputLayout* g_d3dModelIL = NULL; +ID3D11VertexShader* g_d3dModelVS = NULL; +ID3D11PixelShader* g_d3dModelPS = NULL; +ID3D11Buffer* g_d3dModelCB = NULL; + + +struct CameraParameters +{ + float4 vecEye; + float4 vecAt; + float focalLength; + float focalDistance; + float sensorWidth; + float fStop; +}; + + +static const CameraParameters g_defaultCameraParameters[] = { + { { 20.2270432f, 4.19414091f, 16.7282600f }, { 19.4321709f, 4.09884357f, 16.1290131f }, 400.0f, 21.67f, 100.0f, 1.4f, }, + { { -14.7709570f, 5.55706882f, -17.5470028f }, { -14.1790190f, 5.42186546f, -16.7524414f }, 218.0f, 23.3f, 100.0f, 1.6f, }, + { { 2.34538126f, -0.0807961449f, -12.6757965f }, { 2.23687410f, 0.0531809852f, -11.6907701f }, 190.0f, 14.61f, 100.0f, 1.8f, }, + { { 25.5143566f, 5.54141998f, -20.4762344f }, { 24.8163872f, 5.42109346f, -19.7702885f }, 133.0f, 34.95f, 50.0f, 1.6f, }, + { { 5.513732f, 0.803944f, -18.025604f }, { 5.315537f, 0.848312f, -17.046444f }, 205.0f, 39.47f, 85.4f, 2.6f }, + { { -15.698505f, 6.656400f, -21.832394f }, { -15.187683f, 6.442449f, -20.999754f }, 229.0f, 11.3f, 100.00f, 3.9f }, + { { 10.018296f, 0.288034f, -1.364868f }, { 9.142344f, 0.441804f, -0.907634f }, 157.0f, 10.9f, 100.00f, 2.2f }, + { { -3.399786f, 0.948747f, -15.984277f }, { -3.114154f, 1.013084f, -15.028101f }, 366.0f, 16.8f, 100.00f, 1.4f }, + { { -14.941996f, 4.904000f, -17.381784f }, { -14.348591f, 4.798616f, -16.583803f }, 155.0f, 24.9f, 42.70f, 1.4f }, +}; + +static int g_defaultCameraParameterIndex = 0; + +float g_FocalLength = 190.0f; // in mm + +//-------------------------------------------------------------------------------------- +// D3D11 Common Rendering Interfaces +//-------------------------------------------------------------------------------------- +ID3D11Buffer* g_d3dViewerCB = NULL; + +ID3D11SamplerState* g_d3dLinearWrapSS = NULL; +ID3D11SamplerState* g_d3dPointWrapSS = NULL; +ID3D11BlendState* g_d3dOpaqueBS = NULL; +ID3D11RasterizerState* g_d3dBackCullingSolidRS = NULL; +ID3D11RasterizerState* g_d3dNoCullingSolidRS = NULL; +ID3D11DepthStencilState* g_d3dDepthLessEqualDSS = NULL; + +//-------------------------------------------------------------------------------------- +// Timing data +//-------------------------------------------------------------------------------------- +float g_FrameRenderingTime = 0.0f; +float g_SceneRenderingTime = 0.0f; +float g_Fsr2RenderingTime = 0.0f; +std::chrono::high_resolution_clock::time_point g_FrameLastTime; +float g_FrameDeltaTime = 0.0f; + +//-------------------------------------------------------------------------------------- +// FSR2 global variables +//-------------------------------------------------------------------------------------- +nlohmann::json g_JsonConfigFile; + +bool g_bStartFullscreen = false; +AMD::uint32 g_ScreenWidth = 1920; +AMD::uint32 g_ScreenHeight = 1080; +AMD::uint32 g_RenderWidth = 1920; +AMD::uint32 g_RenderHeight = 1080; + +enum Upscaling +{ + UpscalingPoint, + UpscalingLinear, + UpscalingFsr2, +}; + +enum ScaleMode +{ + ScaleModeNative, + ScaleModeQuality, + ScaleModeBalance, + ScaleModePerformance, + ScaleModeUltraPerformance, +}; + +// Upscaling +UINT g_Upscaling = UpscalingFsr2; +UINT g_ScaleMode = ScaleModePerformance; + +// Sharpening +bool g_bSharpening = false; +float g_Sharpness = 0.75f; + +bool g_bFsr2ResetCamera = true; +bool g_bResourceResizeRequired = true; + +//-------------------------------------------------------------------------------------- +// FSR2 DX11 Wrapper +//-------------------------------------------------------------------------------------- +Fsr2Wrapper g_Fsr2Wrapper; + +//-------------------------------------------------------------------------------------- +// UI control IDs +//-------------------------------------------------------------------------------------- +enum UI_IDC +{ + // Common + IDC_TOGGLE_FULLSCREEN = 1, + + IDC_STATIC_FOCAL_LENGTH, + IDC_SLIDER_FOCAL_LENGTH, + + IDC_BUTTON_SAVE_SCREEN_SHOT, + + // Upscale UI + IDC_STATIC_UPSCALING, + IDC_COMBOBOX_UPSCALING, + IDC_STATIC_SCALE_MODE, + IDC_COMBOBOX_SCALE_MODE, + IDC_CHECKBOX_SHARPENING, + IDC_STATIC_SHARPENING_STRENGTH, + IDC_SLIDER_SHARPENING_STRENGTH, + + // Camera + IDC_CHECKBOX_ROTATE_CAMERA, + IDC_STATIC_CAMERA_ROTATION_SPEED, + IDC_SLIDER_CAMERA_ROTATION_SPEED, + + // Total IDC Count + IDC_NUM_CONTROL_IDS +}; + +void ReadConfigFile() +{ + std::ifstream f("FSR2_Sample_DX11.json"); + if (!f) + { + return; + } + + try + { + f >> g_JsonConfigFile; + } + catch (nlohmann::json::parse_error) + { + // error in json file + assert(false); + exit(0); + } + + nlohmann::json globals = g_JsonConfigFile["globals"]; + + g_ScreenWidth = globals.value("width", g_ScreenWidth); + g_ScreenHeight = globals.value("height", g_ScreenHeight); + g_bStartFullscreen = globals.value("fullscreen", g_bStartFullscreen); + g_Upscaling = globals.value("upscaling_type", g_Upscaling); + g_bSharpening = globals.value("enable_sharpening", g_bSharpening); + g_Sharpness = globals.value("sharpness", g_Sharpness); + g_ScaleMode = globals.value("scale_mode", g_ScaleMode); + g_defaultCameraParameterIndex = globals.value("camera_index", g_defaultCameraParameterIndex) % (AMD_ARRAY_SIZE(g_defaultCameraParameters)); + + g_bRotateCamera = globals.value("rotate_camera", g_bRotateCamera); + g_CameraArcShotSpeed = globals.value("rotate_speed", g_CameraArcShotSpeed); +} + + +void SetCameraParameters() +{ + const CameraParameters& params = g_defaultCameraParameters[g_defaultCameraParameterIndex]; + // Setup the camera's view parameters + float4 vecEye(params.vecEye); + float4 vecAt(params.vecAt); + float4 vecDir = vecAt.v - vecEye.v; + vecDir.f[1] = 0.0f; + vecDir.v = XMVector3Normalize(vecDir.v); + g_pCurrentCamera->SetViewParams(vecEye, vecAt); + + g_FocalLength = params.focalLength; + + g_HUD.m_GUI.GetSlider(IDC_SLIDER_FOCAL_LENGTH)->SetValue((int)g_FocalLength); +} + +void ArcShotCamera() +{ + const CameraParameters& params = g_defaultCameraParameters[g_defaultCameraParameterIndex]; + float4 vecEye(params.vecEye); + vecEye.y += 10.f; + float4 vecAt(0.f, 0.f, 0.f, 1.f); + float4 vecDir = vecAt.v - vecEye.v; + + vecDir.v = XMVector4Transform(vecDir.v, XMMatrixRotationAxis({ 0.0f, 1.0f, 0.0f }, g_CameraArcShotAngle)); + //vecAt.v = vecEye.v + vecDir.v; + vecEye.v = vecAt.v - vecDir.v; + g_pCurrentCamera->SetViewParams(vecEye, vecAt); + + g_CameraArcShotAngle += g_CameraArcShotSpeed /1800.f * std::acosf(-1) * g_FrameDeltaTime; +} + +//-------------------------------------------------------------------------------------- +// Entry point to the program. Initializes everything and goes into a message processing +// loop. Idle time is used to render the scene. +//-------------------------------------------------------------------------------------- +int WINAPI wWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPWSTR lpCmdLine, int nCmdShow) +{ +// Enable run-time memory check for debug builds. +#if defined(DEBUG) || defined(_DEBUG) + _CrtSetDbgFlag(_CRTDBG_ALLOC_MEM_DF | _CRTDBG_LEAK_CHECK_DF); +#endif + + // Disable gamma correction on this sample + DXUTSetIsInGammaCorrectMode(false); + + DXUTSetCallbackDeviceChanging(ModifyDeviceSettings); + DXUTSetCallbackMsgProc(MsgProc); + DXUTSetCallbackKeyboard(OnKeyboard); + DXUTSetCallbackFrameMove(OnFrameMove); + + DXUTSetCallbackD3D11DeviceCreated(OnD3D11CreateDevice); + DXUTSetCallbackD3D11SwapChainResized(OnD3D11ResizedSwapChain); + DXUTSetCallbackD3D11FrameRender(OnD3D11FrameRender); + DXUTSetCallbackD3D11SwapChainReleasing(OnD3D11ReleasingSwapChain); + DXUTSetCallbackD3D11DeviceDestroyed(OnD3D11DestroyDevice); + + DXUTSetMediaSearchPath(L"Media\\"); + + + WCHAR windowTitle[64]; + swprintf(windowTitle, 64, L"AMD FSR 2.2 DX11 Sample"); + + ReadConfigFile(); + + InitApp(); + + DXUTInit(true, true); // Use this line instead to try to create a hardware device + + DXUTSetCursorSettings(true, true); // Show the cursor and clip it when in full screen + DXUTCreateWindow(windowTitle); + + DXUTCreateDevice(D3D_FEATURE_LEVEL_11_0, !g_bStartFullscreen, g_ScreenWidth, g_ScreenHeight); + DXUTMainLoop(); // Enter into the DXUT render loop + + return DXUTGetExitCode(); +} + +//-------------------------------------------------------------------------------------- +// Initialize the app +//-------------------------------------------------------------------------------------- +void InitApp() +{ + D3DCOLOR DlgColor = 0x88888888; // Semi-transparent background for the dialog + + g_HUD.m_GUI.Init(&g_DialogResourceManager); + + g_HUD.m_GUI.SetBackgroundColors(DlgColor); + g_HUD.m_GUI.SetCallback(OnGUIEvent); + + int iY = AMD::HUD::iElementDelta; + g_HUD.m_GUI.AddButton(IDC_TOGGLE_FULLSCREEN, L"Toggle full screen", AMD::HUD::iElementOffset, iY, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight); + iY += AMD::HUD::iElementDelta; + + g_HUD.m_GUI.AddStatic(IDC_STATIC_FOCAL_LENGTH, L"Focal Length (mm)", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight); + g_HUD.m_GUI.AddSlider(IDC_SLIDER_FOCAL_LENGTH, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, 18, 400, (int)(g_FocalLength)); + iY += AMD::HUD::iElementDelta; + + g_HUD.m_GUI.AddButton(IDC_BUTTON_SAVE_SCREEN_SHOT, L"ScreenShot", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight); + iY += AMD::HUD::iElementDelta; + + CDXUTComboBox* pComboBox = nullptr; + g_HUD.m_GUI.AddStatic(IDC_STATIC_UPSCALING, L"Upscaling", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight); + g_HUD.m_GUI.AddComboBox(IDC_COMBOBOX_UPSCALING, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, 200, 24, 0, false, &pComboBox); + pComboBox->AddItem(L"Point", nullptr); + pComboBox->AddItem(L"Linear", nullptr); + pComboBox->AddItem(L"FSR 2.2", nullptr); + pComboBox->SetSelectedByIndex(g_Upscaling); + + g_HUD.m_GUI.AddStatic(IDC_STATIC_SCALE_MODE, L"Scale Mode", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight); + g_HUD.m_GUI.AddComboBox(IDC_COMBOBOX_SCALE_MODE, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, 200, 24, 0, false, &pComboBox); + pComboBox->AddItem(L"Native 1.0x", nullptr); + pComboBox->AddItem(L"Quality 1.5x", nullptr); + pComboBox->AddItem(L"Balance 1.7x", nullptr); + pComboBox->AddItem(L"Performance 2.0x", nullptr); + pComboBox->AddItem(L"Ultra Performance 3.0x", nullptr); + pComboBox->SetSelectedByIndex(g_ScaleMode); + + wchar_t buf[64]; + g_HUD.m_GUI.AddCheckBox(IDC_CHECKBOX_SHARPENING, L"Sharpening", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, 140, 24, g_bSharpening); + swprintf(buf, 64, L"Sharpness: %.2f", g_Sharpness); + g_HUD.m_GUI.AddStatic(IDC_STATIC_SHARPENING_STRENGTH, buf, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight); + g_HUD.m_GUI.AddSlider(IDC_SLIDER_SHARPENING_STRENGTH, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, 0, 100, int(g_Sharpness * 100.0f)); + + iY += AMD::HUD::iElementDelta; + g_HUD.m_GUI.AddCheckBox(IDC_CHECKBOX_ROTATE_CAMERA, L"Rotate Camera", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, 140, 24, g_bRotateCamera); + swprintf(buf, 64, L"Speed: %.2f", g_CameraArcShotSpeed); + g_HUD.m_GUI.AddStatic(IDC_STATIC_CAMERA_ROTATION_SPEED, buf, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight); + g_HUD.m_GUI.AddSlider(IDC_SLIDER_CAMERA_ROTATION_SPEED, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, 0, 100, int(g_CameraArcShotSpeed * 100.0f)); + + iY += AMD::HUD::iElementDelta; + g_MagnifyTool.InitApp(&g_HUD.m_GUI, iY += AMD::HUD::iElementDelta); + + g_pCurrentCamera->SetRotateButtons(true, false, false); +} + + +//-------------------------------------------------------------------------------------- +// This callback function is called immediately before a device is created to allow the +// application to modify the device settings. The supplied pDeviceSettings parameter +// contains the settings that the framework has selected for the new device, and the +// application can make any desired changes directly to this structure. Note however that +// DXUT will not correct invalid device settings so care must be taken +// to return valid device settings, otherwise CreateDevice() will fail. +//-------------------------------------------------------------------------------------- +bool CALLBACK ModifyDeviceSettings(DXUTDeviceSettings* pDeviceSettings, void* pUserContext) +{ + assert(pDeviceSettings->MinimumFeatureLevel == D3D_FEATURE_LEVEL_11_0); + pDeviceSettings->d3d11.SyncInterval = 0; + + // For the first device created if it is a REF device, optionally display a warning dialog box + static bool s_bFirstTime = true; + if (s_bFirstTime) + { + s_bFirstTime = false; + if (pDeviceSettings->d3d11.DriverType == D3D_DRIVER_TYPE_REFERENCE) + { + DXUTDisplaySwitchingToREFWarning(); + } + } + return true; +} + + +//-------------------------------------------------------------------------------------- +// This callback function will be called once at the beginning of every frame. This is the +// best location for your application to handle updates to the scene, but is not +// intended to contain actual rendering calls, which should instead be placed in the +// OnFrameRender callback. +//-------------------------------------------------------------------------------------- +void CALLBACK OnFrameMove(double fTime, float fElapsedTime, void* pUserContext) +{ + // Update the camera's position based on user input + g_pCurrentCamera->FrameMove(fElapsedTime); +} + + +//-------------------------------------------------------------------------------------- +// Render stats +//-------------------------------------------------------------------------------------- +void RenderText(float frameAverage, float frameTime, float sceneAverage, float sceneTime, float fsr2Average, float fsr2Time) +{ + g_pTxtHelper->Begin(); + + g_pTxtHelper->SetInsertionPos(2, 0); + g_pTxtHelper->SetForegroundColor(XMFLOAT4(1.0f, 1.0f, 1.0f, 1.0f)); + g_pTxtHelper->DrawTextLine(DXUTGetFrameStats(DXUTIsVsyncEnabled())); + g_pTxtHelper->DrawTextLine(DXUTGetDeviceStats()); + + WCHAR szTemp[256]; + swprintf_s(szTemp, L"Screen Size %4d x %4d", g_ScreenWidth, g_ScreenHeight); + g_pTxtHelper->DrawTextLine(szTemp); + swprintf_s(szTemp, L"Render Size %4d x %4d", g_RenderWidth, g_RenderHeight); + g_pTxtHelper->DrawTextLine(szTemp); + swprintf_s(szTemp, L"Total Frame = %.3fms (%.3fms)", frameAverage, frameTime); + g_pTxtHelper->DrawTextLine(szTemp); + swprintf_s(szTemp, L" Scene = %.3fms (%.3fms)", sceneAverage, sceneTime); + g_pTxtHelper->DrawTextLine(szTemp); + swprintf_s(szTemp, L" FSR 2.2 = %.3fms (%.3fms)", fsr2Average, fsr2Time); + g_pTxtHelper->DrawTextLine(szTemp); + + g_pTxtHelper->SetInsertionPos(10, g_ScreenHeight - 170); + g_pTxtHelper->DrawTextLine(L"Camera Move : W/S/A/D/Q/E\n" + L"Camera Look : Left Mouse\n" + L"Select Upscaling : F1-F3\n" + L"Select Scale Mode : 1-5\n" + L"Toggle Sharpening : TAB\n" + L"Change Camera : C\n" + L"Toggle Rotation : R\n" + L"Toggle GUI : F11\n"); + + g_pTxtHelper->End(); +} + + +//-------------------------------------------------------------------------------------- +// Before handling window messages, DXUT passes incoming windows +// messages to the application through this callback function. If the application sets +// *pbNoFurtherProcessing to TRUE, then DXUT will not process this message. +//-------------------------------------------------------------------------------------- +LRESULT CALLBACK MsgProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, bool* pbNoFurtherProcessing, void* pUserContext) +{ + // Pass messages to dialog resource manager calls so GUI state is updated correctly + *pbNoFurtherProcessing = g_DialogResourceManager.MsgProc(hWnd, uMsg, wParam, lParam); + if (*pbNoFurtherProcessing) + { + return 0; + } + + // Give the dialogs a chance to handle the message first + *pbNoFurtherProcessing = g_HUD.m_GUI.MsgProc(hWnd, uMsg, wParam, lParam); + if (*pbNoFurtherProcessing) + { + return 0; + } + + // Pass all windows messages to camera so it can respond to user input + g_pCurrentCamera->HandleMessages(hWnd, uMsg, wParam, lParam); + + return 0; +} + + +//-------------------------------------------------------------------------------------- +// Handles the GUI events +//-------------------------------------------------------------------------------------- +void CALLBACK OnGUIEvent(UINT nEvent, int nControlID, CDXUTControl* pControl, void* pUserContext) +{ + wchar_t buf[64]; + switch (nControlID) + { + case IDC_TOGGLE_FULLSCREEN: + DXUTToggleFullScreen(); + break; + case IDC_COMBOBOX_UPSCALING: + g_Upscaling = g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_UPSCALING)->GetSelectedIndex(); + break; + case IDC_COMBOBOX_SCALE_MODE: + g_ScaleMode = g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_SCALE_MODE)->GetSelectedIndex(); + g_bResourceResizeRequired = true; + break; + case IDC_CHECKBOX_SHARPENING: + g_bSharpening = g_HUD.m_GUI.GetCheckBox(IDC_CHECKBOX_SHARPENING)->GetChecked(); + break; + case IDC_SLIDER_SHARPENING_STRENGTH: + g_Sharpness = float(g_HUD.m_GUI.GetSlider(IDC_SLIDER_SHARPENING_STRENGTH)->GetValue()) / 100.0f; + swprintf(buf, 64, L"Sharpening Strength: %.2f", g_Sharpness); + g_HUD.m_GUI.GetStatic(IDC_STATIC_SHARPENING_STRENGTH)->SetText(buf); + break; + case IDC_CHECKBOX_ROTATE_CAMERA: + g_bRotateCamera = g_HUD.m_GUI.GetCheckBox(IDC_CHECKBOX_ROTATE_CAMERA)->GetChecked(); + break; + case IDC_SLIDER_CAMERA_ROTATION_SPEED: + g_CameraArcShotSpeed = float(g_HUD.m_GUI.GetSlider(IDC_SLIDER_CAMERA_ROTATION_SPEED)->GetValue()) / 100.0f; + swprintf(buf, 64, L"Speed: %.2f", g_CameraArcShotSpeed); + g_HUD.m_GUI.GetStatic(IDC_STATIC_CAMERA_ROTATION_SPEED)->SetText(buf); + break; + case IDC_SLIDER_FOCAL_LENGTH: + g_FocalLength = float(g_HUD.m_GUI.GetSlider(IDC_SLIDER_FOCAL_LENGTH)->GetValue()); + swprintf(buf, 64, L"Focal Length: %.0f", g_FocalLength); + g_HUD.m_GUI.GetStatic(IDC_STATIC_FOCAL_LENGTH)->SetText(buf); + g_bFsr2ResetCamera = true; + break; + + case IDC_BUTTON_SAVE_SCREEN_SHOT: + g_bSaveScreenShot = true; + break; + default: + break; + } + // Call the MagnifyTool gui event handler + g_MagnifyTool.OnGUIEvent(nEvent, nControlID, pControl, pUserContext); +} + + +//-------------------------------------------------------------------------------------- +// Handle key presses +//-------------------------------------------------------------------------------------- +void CALLBACK OnKeyboard(UINT nChar, bool bKeyDown, bool bAltDown, void* pUserContext) +{ +#define VK_1 (49) +#define VK_2 (50) +#define VK_3 (51) +#define VK_4 (52) +#define VK_5 (53) +#define VK_C (67) +#define VK_R (82) + + if (bKeyDown) + { + switch (nChar) + { + case VK_F11: + g_bRenderHUD ^= true; + break; + case VK_F1: + g_Upscaling = UpscalingPoint; + g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_UPSCALING)->SetSelectedByIndex(g_Upscaling); + break; + case VK_F2: + g_Upscaling = UpscalingLinear; + g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_UPSCALING)->SetSelectedByIndex(g_Upscaling); + break; + case VK_F3: + g_Upscaling = UpscalingFsr2; + g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_UPSCALING)->SetSelectedByIndex(g_Upscaling); + g_bFsr2ResetCamera = true; + break; + case VK_1: + g_ScaleMode = ScaleModeNative; + g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_SCALE_MODE)->SetSelectedByIndex(g_ScaleMode); + g_bResourceResizeRequired = true; + break; + case VK_2: + g_ScaleMode = ScaleModeQuality; + g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_SCALE_MODE)->SetSelectedByIndex(g_ScaleMode); + g_bResourceResizeRequired = true; + break; + case VK_3: + g_ScaleMode = ScaleModeBalance; + g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_SCALE_MODE)->SetSelectedByIndex(g_ScaleMode); + g_bResourceResizeRequired = true; + break; + case VK_4: + g_ScaleMode = ScaleModePerformance; + g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_SCALE_MODE)->SetSelectedByIndex(g_ScaleMode); + g_bResourceResizeRequired = true; + break; + case VK_5: + g_ScaleMode = ScaleModeUltraPerformance; + g_HUD.m_GUI.GetComboBox(IDC_COMBOBOX_SCALE_MODE)->SetSelectedByIndex(g_ScaleMode); + g_bResourceResizeRequired = true; + break; + case VK_TAB: + g_bSharpening ^= true; + g_HUD.m_GUI.GetCheckBox(IDC_CHECKBOX_SHARPENING)->SetChecked(g_bSharpening); + break; + case VK_C: + g_defaultCameraParameterIndex = (g_defaultCameraParameterIndex + 1) % (AMD_ARRAY_SIZE(g_defaultCameraParameters)); + SetCameraParameters(); + g_bFsr2ResetCamera = true; + break; + case VK_R: + g_bRotateCamera ^= true; + g_HUD.m_GUI.GetCheckBox(IDC_CHECKBOX_ROTATE_CAMERA)->SetChecked(g_bRotateCamera); + break; + default: + break; + } + } +} + + +//-------------------------------------------------------------------------------------- +// Create any D3D11 resources that aren't dependant on the back buffer +//-------------------------------------------------------------------------------------- +HRESULT CALLBACK OnD3D11CreateDevice(ID3D11Device* pd3dDevice, const DXGI_SURFACE_DESC* pSurfaceDesc, void* pUserContext) +{ + HRESULT hr; + CD3D11_DEFAULT defaultDesc; + + g_ScreenWidth = pSurfaceDesc->Width; + g_ScreenHeight = pSurfaceDesc->Height; + + ID3D11DeviceContext* pd3dContext = DXUTGetD3D11DeviceContext(); + V_RETURN(g_DialogResourceManager.OnD3D11CreateDevice(pd3dDevice, pd3dContext)); + g_pTxtHelper = new CDXUTTextHelper(pd3dDevice, pd3dContext, &g_DialogResourceManager, 15); + + // Hooks to various AMD helper classes + V_RETURN(g_MagnifyTool.OnCreateDevice(pd3dDevice)); + V_RETURN(g_HUD.OnCreateDevice(pd3dDevice)); + + V_RETURN(CompileShaders(pd3dDevice)); + + V_RETURN(CreateMeshes(pd3dDevice)); + + + V_RETURN(SetupCamera(pd3dDevice)); + + // Create common render states (mostly these match d3d11 default state settings) + CD3D11_SAMPLER_DESC sampler_desc(defaultDesc); + sampler_desc.AddressU = D3D11_TEXTURE_ADDRESS_WRAP; + sampler_desc.AddressV = D3D11_TEXTURE_ADDRESS_WRAP; + sampler_desc.AddressW = D3D11_TEXTURE_ADDRESS_WRAP; + hr = pd3dDevice->CreateSamplerState(&sampler_desc, &g_d3dLinearWrapSS); + sampler_desc.Filter = D3D11_FILTER_MIN_MAG_MIP_POINT; + hr = pd3dDevice->CreateSamplerState(&sampler_desc, &g_d3dPointWrapSS); + + if (hr == S_OK) + { + CD3D11_BLEND_DESC blend_desc(defaultDesc); + V_RETURN(pd3dDevice->CreateBlendState(&blend_desc, &g_d3dOpaqueBS)); + } + + if (hr == S_OK) + { + CD3D11_RASTERIZER_DESC raster_desc(defaultDesc); + hr = pd3dDevice->CreateRasterizerState(&raster_desc, &g_d3dBackCullingSolidRS); + D3D11_RASTERIZER_DESC raster_desc2 = raster_desc; + raster_desc2.CullMode = D3D11_CULL_NONE; + raster_desc2.DepthClipEnable = FALSE; + V_RETURN(pd3dDevice->CreateRasterizerState(&raster_desc2, &g_d3dNoCullingSolidRS)); + } + + if (hr == S_OK) + { + CD3D11_DEPTH_STENCIL_DESC dssDesc(defaultDesc); + dssDesc.DepthFunc = D3D11_COMPARISON_LESS_EQUAL; + V_RETURN(pd3dDevice->CreateDepthStencilState(&dssDesc, &g_d3dDepthLessEqualDSS)); + } + + TIMER_Init(pd3dDevice); + + return hr; +} + + +void SetCameraProjectionParameters() +{ + float fov = 2 * atanf(50.0f / g_FocalLength); + // Setup the camera's projection parameters + FLOAT fAspectRatio = (float)g_RenderWidth / (float)g_RenderHeight; + g_pCurrentCamera->SetProjParams(fov, fAspectRatio, 0.1f, 200.0f); +} + + +//-------------------------------------------------------------------------------------- +// Resize +//-------------------------------------------------------------------------------------- +HRESULT ResizeResources(ID3D11Device* pd3dDevice) +{ + if (!g_bResourceResizeRequired) + return S_OK; + + HRESULT hr; + + if (g_ScaleMode > 0) + { + ffxFsr2GetRenderResolutionFromQualityMode(&g_RenderWidth, &g_RenderHeight, g_ScreenWidth, g_ScreenHeight, FfxFsr2QualityMode(g_ScaleMode)); + } + else + { + g_RenderWidth = g_ScreenWidth; + g_RenderHeight = g_ScreenHeight; + } + + + for (int i = 0; i < NUM_OF_BUFFER; ++i) + { + g_appColorBuffer[i].Release(); + hr = g_appColorBuffer[i].CreateSurface(pd3dDevice, g_RenderWidth, g_RenderHeight, 1, 1, 1, DXGI_FORMAT_R8G8B8A8_TYPELESS, DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, + DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, DXGI_FORMAT_UNKNOWN, DXGI_FORMAT_R8G8B8A8_UNORM, DXGI_FORMAT_UNKNOWN, D3D11_USAGE_DEFAULT, false, 0, NULL, NULL, 0); + + g_appVelocityBuffer[i].Release(); + hr = g_appVelocityBuffer[i].CreateSurface(pd3dDevice, g_RenderWidth, g_RenderHeight, 1, 1, 1, DXGI_FORMAT_R16G16_FLOAT, DXGI_FORMAT_R16G16_FLOAT, + DXGI_FORMAT_R16G16_FLOAT, DXGI_FORMAT_UNKNOWN, DXGI_FORMAT_R16G16_FLOAT, DXGI_FORMAT_UNKNOWN, D3D11_USAGE_DEFAULT, false, 0, NULL, NULL, 0); + + // scene depth buffer + g_appDepthBuffer[i].Release(); + hr = g_appDepthBuffer[i].CreateSurface(pd3dDevice, g_RenderWidth, g_RenderHeight, 1, 1, 1, DXGI_FORMAT_R32_TYPELESS, DXGI_FORMAT_R32_FLOAT, + DXGI_FORMAT_UNKNOWN, DXGI_FORMAT_D32_FLOAT, DXGI_FORMAT_UNKNOWN, DXGI_FORMAT_UNKNOWN, D3D11_USAGE_DEFAULT, false, 0, NULL, NULL, 0); + } + + g_bResourceResizeRequired = false; + g_bFsr2ResetCamera = true; + + return hr; +} + +HRESULT CALLBACK OnD3D11ResizedSwapChain(ID3D11Device* pd3dDevice, IDXGISwapChain* pSwapChain, const DXGI_SURFACE_DESC* pSurfaceDesc, void* pUserContext) +{ + HRESULT hr; + + g_ScreenWidth = pSurfaceDesc->Width; + g_ScreenHeight = pSurfaceDesc->Height; + + V_RETURN(g_DialogResourceManager.OnD3D11ResizedSwapChain(pd3dDevice, pSurfaceDesc)); + + SetCameraProjectionParameters(); + + // Set the location and size of the AMD standard HUD + g_HUD.m_GUI.SetLocation(pSurfaceDesc->Width - AMD::HUD::iDialogWidth, 0); + g_HUD.m_GUI.SetSize(AMD::HUD::iDialogWidth, pSurfaceDesc->Height); + + // Magnify tool will capture from the color buffer + g_MagnifyTool.OnResizedSwapChain(pd3dDevice, pSwapChain, pSurfaceDesc, pUserContext, pSurfaceDesc->Width - AMD::HUD::iDialogWidth, 0); + D3D11_RENDER_TARGET_VIEW_DESC RTDesc; + ID3D11Resource* pTempRTResource; + DXUTGetD3D11RenderTargetView()->GetResource(&pTempRTResource); + DXUTGetD3D11RenderTargetView()->GetDesc(&RTDesc); + g_MagnifyTool.SetSourceResources(pTempRTResource, RTDesc.Format, g_ScreenWidth, g_ScreenHeight, pSurfaceDesc->SampleDesc.Count); + g_MagnifyTool.SetPixelRegion(128); + g_MagnifyTool.SetScale(5); + SAFE_RELEASE(pTempRTResource); + + // AMD HUD hook + g_HUD.OnResizedSwapChain(pSurfaceDesc); + + // App specific resources + // scene render target + g_bResourceResizeRequired = true; + + // Upscaled Result surface + g_appUpscaledSurface.Release(); + DXGI_FORMAT appDebugFormat = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + hr = g_appUpscaledSurface.CreateSurface(pd3dDevice, g_ScreenWidth, g_ScreenHeight, pSurfaceDesc->SampleDesc.Count, 1, 1, DXGI_FORMAT_R8G8B8A8_TYPELESS, appDebugFormat, appDebugFormat, + DXGI_FORMAT_UNKNOWN, DXGI_FORMAT_R8G8B8A8_UNORM, DXGI_FORMAT_UNKNOWN, D3D11_USAGE_DEFAULT, false, 0, NULL, NULL, 0); + + if (g_Fsr2Wrapper.IsCreated()) + { + auto prevSize = g_Fsr2Wrapper.GetDisplaySize(); + if (prevSize.width != g_ScreenWidth || prevSize.height != g_ScreenHeight) + g_Fsr2Wrapper.Destroy(); + } + if (!g_Fsr2Wrapper.IsCreated()) + { + Fsr2Wrapper::ContextParameters initParams; + initParams.device = pd3dDevice; + initParams.displaySize.width = g_ScreenWidth; + initParams.displaySize.height = g_ScreenHeight; + initParams.maxRenderSize = initParams.displaySize; + g_Fsr2Wrapper.Create(initParams); + } + + g_FrameLastTime = std::chrono::high_resolution_clock::now(); + + + return S_OK; +} + +void SetCameraConstantBuffer(ID3D11DeviceContext* pd3dContext, ID3D11Buffer* pd3dCameraCB, S_CAMERA_DESC* pCameraDesc, CFirstPersonCamera* pCamera, unsigned int nCount, float jitterX, float jitterY) +{ + if (pd3dContext == NULL) + { + OutputDebugString(AMD_FUNCTION_WIDE_NAME L" received a NULL D3D11 Context pointer \n"); + return; + } + if (pd3dCameraCB == NULL) + { + OutputDebugString(AMD_FUNCTION_WIDE_NAME L" received a NULL D3D11 Constant Buffer pointer \n"); + return; + } + + D3D11_MAPPED_SUBRESOURCE MappedResource; + + for (unsigned int i = 0; i < nCount; i++) + { + CFirstPersonCamera& camera = pCamera[i]; + S_CAMERA_DESC& cameraDesc = pCameraDesc[i]; + + XMMATRIX jitter = { + 1.0f, 0.0f, 0.0f, 0.0f, + 0.0f, 1.0f, 0.0f, 0.0f, + 0.0f, 0.0f, 1.0f, 0.0f, + jitterX, jitterY, 0.0f, 1.0f + }; + + XMMATRIX view = camera.GetViewMatrix(); + XMMATRIX proj = camera.GetProjMatrix() * jitter; + XMMATRIX viewproj = view * proj; + XMMATRIX view_inv = XMMatrixInverse(&XMMatrixDeterminant(view), view); + XMMATRIX proj_inv = XMMatrixInverse(&XMMatrixDeterminant(proj), proj); + XMMATRIX viewproj_inv = XMMatrixInverse(&XMMatrixDeterminant(viewproj), viewproj); + + cameraDesc.m_View = XMMatrixTranspose(view); + cameraDesc.m_Projection = XMMatrixTranspose(proj); + cameraDesc.m_View_Inv = XMMatrixTranspose(view_inv); + cameraDesc.m_Projection_Inv = XMMatrixTranspose(proj_inv); + cameraDesc.m_ViewProjection = XMMatrixTranspose(viewproj); + cameraDesc.m_ViewProjection_Inv = XMMatrixTranspose(viewproj_inv); + cameraDesc.m_Fov = camera.GetFOV(); + cameraDesc.m_Aspect = camera.GetAspect(); + cameraDesc.m_NearPlane = camera.GetNearClip(); + cameraDesc.m_FarPlane = camera.GetFarClip(); + + memcpy(&cameraDesc.m_Position, &(camera.GetEyePt()), sizeof(cameraDesc.m_Position)); + memcpy(&cameraDesc.m_Direction, &(XMVector3Normalize(camera.GetLookAtPt() - camera.GetEyePt())), sizeof(cameraDesc.m_Direction)); + memcpy(&cameraDesc.m_Up, &(camera.GetWorldUp()), sizeof(cameraDesc.m_Position)); + } + + HRESULT hr = pd3dContext->Map(pd3dCameraCB, 0, D3D11_MAP_WRITE_DISCARD, 0, &MappedResource); + if (hr == S_OK && MappedResource.pData) + { + memcpy(MappedResource.pData, pCameraDesc, sizeof(S_CAMERA_DESC) * nCount); + pd3dContext->Unmap(pd3dCameraCB, 0); + } +} + +void SetModelConstantBuffer(ID3D11DeviceContext* pd3dContext, ID3D11Buffer* pd3dModelCB, S_MODEL_DESC* pModelDesc) +{ + if (pd3dContext == NULL) + { + OutputDebugString(AMD_FUNCTION_WIDE_NAME L" received a NULL D3D11 Context pointer \n"); + return; + } + if (pd3dModelCB == NULL) + { + OutputDebugString(AMD_FUNCTION_WIDE_NAME L" received a NULL D3D11 Constant Buffer pointer \n"); + return; + } + + D3D11_MAPPED_SUBRESOURCE MappedResource; + + S_MODEL_DESC& modelDesc = pModelDesc[0]; + + modelDesc.m_mipBias = std::log2f((float)g_RenderWidth / (float)g_ScreenWidth) - 1.0f; + + HRESULT hr = pd3dContext->Map(pd3dModelCB, 0, D3D11_MAP_WRITE_DISCARD, 0, &MappedResource); + if (hr == S_OK && MappedResource.pData) + { + memcpy(MappedResource.pData, &modelDesc, sizeof(modelDesc)); + pd3dContext->Unmap(pd3dModelCB, 0); + } +} + +//-------------------------------------------------------------------------------------- +// Render the scene (either for the main scene or the shadow map scene) +//-------------------------------------------------------------------------------------- +void RenderScene(ID3D11DeviceContext* pd3dContext, AMD::Mesh** pMesh, S_MODEL_DESC* pMeshDesc, unsigned int nMeshCount, + D3D11_VIEWPORT* pVP, // ViewPort array + unsigned int nVPCount, // Viewport count + D3D11_RECT* pSR, // Scissor Rects array + unsigned int nSRCount, // Scissor rect count + ID3D11RasterizerState* pRS, // Raster State + ID3D11BlendState* pBS, // Blend State + float* pFactorBS, // Blend state factor + ID3D11DepthStencilState* pDSS, // Depth Stencil State + unsigned int dssRef, // Depth stencil state reference value + ID3D11InputLayout* pIL, // Input Layout + ID3D11VertexShader* pVS, // Vertex Shader + ID3D11HullShader* pHS, // Hull Shader + ID3D11DomainShader* pDS, // Domain Shader + ID3D11GeometryShader* pGS, // Geometry SHader + ID3D11PixelShader* pPS, // Pixel Shader + ID3D11Buffer* pModelCB, + ID3D11Buffer** ppCB, // Constant Buffer array + unsigned int nCBStart, // First slot to attach constant buffer array + unsigned int nCBCount, // Number of constant buffers in the array + ID3D11SamplerState** ppSS, // Sampler State array + unsigned int nSSStart, // First slot to attach sampler state array + unsigned int nSSCount, // Number of sampler states in the array + ID3D11ShaderResourceView** ppSRV, // Shader Resource View array + unsigned int nSRVStart, // First slot to attach sr views array + unsigned int nSRVCount, // Number of sr views in the array + ID3D11RenderTargetView** ppRTV, // Render Target View array + unsigned int nRTVCount, // Number of rt views in the array + ID3D11DepthStencilView* pDSV, // Depth Stencil View + CFirstPersonCamera* pCamera) +{ + ID3D11RenderTargetView* const pNullRTV[8] = { 0 }; + ID3D11ShaderResourceView* const pNullSRV[128] = { 0 }; + + // Unbind anything that could be still bound on input or output + // If this doesn't happen, DX Runtime will spam with warnings + pd3dContext->OMSetRenderTargets(AMD_ARRAY_SIZE(pNullRTV), pNullRTV, NULL); + pd3dContext->CSSetShaderResources(0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV); + pd3dContext->VSSetShaderResources(0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV); + pd3dContext->HSSetShaderResources(0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV); + pd3dContext->DSSetShaderResources(0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV); + pd3dContext->GSSetShaderResources(0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV); + pd3dContext->PSSetShaderResources(0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV); + + pd3dContext->IASetInputLayout(pIL); + + pd3dContext->VSSetShader(pVS, NULL, 0); + pd3dContext->HSSetShader(pHS, NULL, 0); + pd3dContext->DSSetShader(pDS, NULL, 0); + pd3dContext->GSSetShader(pGS, NULL, 0); + pd3dContext->PSSetShader(pPS, NULL, 0); + + if (nSSCount) + { + pd3dContext->VSSetSamplers(nSSStart, nSSCount, ppSS); + pd3dContext->HSSetSamplers(nSSStart, nSSCount, ppSS); + pd3dContext->DSSetSamplers(nSSStart, nSSCount, ppSS); + pd3dContext->GSSetSamplers(nSSStart, nSSCount, ppSS); + pd3dContext->PSSetSamplers(nSSStart, nSSCount, ppSS); + } + + if (nSRVCount) + { + pd3dContext->VSSetShaderResources(nSRVStart, nSRVCount, ppSRV); + pd3dContext->HSSetShaderResources(nSRVStart, nSRVCount, ppSRV); + pd3dContext->DSSetShaderResources(nSRVStart, nSRVCount, ppSRV); + pd3dContext->GSSetShaderResources(nSRVStart, nSRVCount, ppSRV); + pd3dContext->PSSetShaderResources(nSRVStart, nSRVCount, ppSRV); + } + + if (nCBCount) + { + pd3dContext->VSSetConstantBuffers(nCBStart, nCBCount, ppCB); + pd3dContext->HSSetConstantBuffers(nCBStart, nCBCount, ppCB); + pd3dContext->DSSetConstantBuffers(nCBStart, nCBCount, ppCB); + pd3dContext->GSSetConstantBuffers(nCBStart, nCBCount, ppCB); + pd3dContext->PSSetConstantBuffers(nCBStart, nCBCount, ppCB); + } + + pd3dContext->OMSetRenderTargets(nRTVCount, ppRTV, pDSV); + pd3dContext->OMSetBlendState(pBS, pFactorBS, 0xf); + pd3dContext->OMSetDepthStencilState(pDSS, dssRef); + pd3dContext->RSSetState(pRS); + pd3dContext->RSSetScissorRects(nSRCount, pSR); + pd3dContext->RSSetViewports(nVPCount, pVP); + + for (unsigned int mesh = 0; mesh < nMeshCount; mesh++) + { + SetModelConstantBuffer(pd3dContext, pModelCB, &pMeshDesc[mesh]); + + pMesh[mesh]->Render(pd3dContext); + } +} + + +//-------------------------------------------------------------------------------------- +// Render +//-------------------------------------------------------------------------------------- +void CALLBACK OnD3D11FrameRender(ID3D11Device* pd3dDevice, ID3D11DeviceContext* pd3dContext, double fTime, float fElapsedTime, void* pUserContext) +{ + D3D11_RECT* pNullSR = NULL; + ID3D11HullShader* pNullHS = NULL; + ID3D11DomainShader* pNullDS = NULL; + ID3D11GeometryShader* pNullGS = NULL; + ID3D11ShaderResourceView* pNullSRV = NULL; + ID3D11UnorderedAccessView* pNullUAV = NULL; + + ID3D11RenderTargetView* pOriginalRTV = NULL; + ID3D11DepthStencilView* pOriginalDSV = NULL; + + static int nFrameCount = 0; + static float fAccumulatedTime = 0.0f; + static float fTimeSceneRendering = 0.0f; + static float fTimeFSR2Rendering = 0.0f; + + float4 light_blue(0.176f, 0.196f, 0.667f, 0.000f); + float4 white(1.000f, 1.000f, 1.000f, 1.000f); + float4 black(0.000f, 0.000f, 0.000f, 1.000f); + + auto frameCurrentTime = std::chrono::high_resolution_clock::now(); + g_FrameDeltaTime = (frameCurrentTime - g_FrameLastTime).count() / 1000000.0f; + g_FrameLastTime = frameCurrentTime; + + TIMER_Reset(); + + SetCameraProjectionParameters(); + + ResizeResources(pd3dDevice); + + // Store the original render target and depth buffer + pd3dContext->OMGetRenderTargets(1, &pOriginalRTV, &pOriginalDSV); + + // Clear the depth stencil & shadow map + pd3dContext->ClearRenderTargetView(pOriginalRTV, light_blue.f); + pd3dContext->ClearDepthStencilView(pOriginalDSV, D3D11_CLEAR_DEPTH, 1.0f, 0); + pd3dContext->ClearRenderTargetView(g_appColorBuffer[g_nBufferIdx]._rtv, light_blue.f); + pd3dContext->ClearRenderTargetView(g_appVelocityBuffer[g_nBufferIdx]._rtv, black.f); + pd3dContext->ClearDepthStencilView(g_appDepthBuffer[g_nBufferIdx]._dsv, D3D11_CLEAR_DEPTH, 1.0f, 0); + + // camera jitter + float jitterX = 0.f; + float jitterY = 0.f; + if (g_Upscaling == UpscalingFsr2) + { + const int32_t jitterPhaseCount = ffxFsr2GetJitterPhaseCount(g_RenderWidth, g_ScreenWidth); + ffxFsr2GetJitterOffset(&g_CameraJitterX, &g_CameraJitterY, g_FrameIndex, jitterPhaseCount); + jitterX = 2.0f * g_CameraJitterX / (float)g_RenderWidth; + jitterY = -2.0f * g_CameraJitterY / (float)g_RenderHeight; + } + + SetCameraConstantBuffer(pd3dContext, g_d3dViewerCB, g_ViewerData, g_Viewer, 2, jitterX, jitterY); + + TIMER_Begin(0, L"Scene Rendering"); + { + ID3D11Buffer* pCB[] = { g_d3dModelCB, g_d3dViewerCB }; + ID3D11SamplerState* pSS[] = { g_d3dLinearWrapSS }; + ID3D11RenderTargetView* pRTV[] = { g_appColorBuffer[g_nBufferIdx]._rtv, g_appVelocityBuffer[g_nBufferIdx]._rtv }; + + AMD::Mesh* meshes[] = { &g_Model }; + + RenderScene(pd3dContext, meshes, &g_ModelDesc, 1, &CD3D11_VIEWPORT(0.0f, 0.0f, (float)g_RenderWidth, (float)g_RenderHeight), 1, pNullSR, 0, + g_d3dBackCullingSolidRS, g_d3dOpaqueBS, white.f, g_d3dDepthLessEqualDSS, 0, g_d3dModelIL, g_d3dModelVS, pNullHS, pNullDS, + pNullGS, g_d3dModelPS, g_d3dModelCB, pCB, 0, AMD_ARRAY_SIZE(pCB), pSS, 0, AMD_ARRAY_SIZE(pSS), &pNullSRV, 1, 0, pRTV, AMD_ARRAY_SIZE(pRTV), g_appDepthBuffer[g_nBufferIdx]._dsv, + g_Viewer); + } + + TIMER_End(); + + pd3dContext->OMSetRenderTargets(0, nullptr, nullptr); + pd3dContext->CSSetUnorderedAccessViews(0, 1, &pNullUAV, NULL); + pd3dContext->CSSetShaderResources(0, 1, &pNullSRV); + + if (g_Upscaling == UpscalingFsr2) + { + Fsr2Wrapper::DrawParameters fsr2Params = { + pd3dContext, + g_appColorBuffer[g_nBufferIdx]._t2d, + g_appVelocityBuffer[g_nBufferIdx]._t2d, + g_appDepthBuffer[g_nBufferIdx]._t2d, + nullptr, + nullptr, + g_appUpscaledSurface._t2d, + g_RenderWidth, + g_RenderHeight, + g_bFsr2ResetCamera, + g_CameraJitterX, + g_CameraJitterY, + g_bSharpening, + g_Sharpness, + g_FrameDeltaTime, + g_pCurrentCamera->GetNearClip(), + g_pCurrentCamera->GetFarClip(), + g_pCurrentCamera->GetFOV(), + }; + + g_bFsr2ResetCamera = false; + + TIMER_Begin(0, L"FSR2"); + + g_Fsr2Wrapper.Draw(fsr2Params); + + TIMER_End(); + } + + CD3D11_VIEWPORT screenVP(0.0f, 0.0f, (float)g_ScreenWidth, (float)g_ScreenHeight); + pd3dContext->RSSetViewports(1, &screenVP); + + pd3dContext->OMSetRenderTargets(1, &pOriginalRTV, pOriginalDSV); + pd3dContext->VSSetShader(g_d3dFullScreenVS, NULL, 0); + pd3dContext->PSSetShader(g_d3dFullScreenPS, NULL, 0); + pd3dContext->PSSetShaderResources(0, 1, g_Upscaling == UpscalingFsr2 ? &g_appUpscaledSurface._srv : &g_appColorBuffer[g_nBufferIdx]._srv); + pd3dContext->PSSetSamplers(0, 1, g_Upscaling == UpscalingPoint ? &g_d3dPointWrapSS : &g_d3dLinearWrapSS); + pd3dContext->OMSetBlendState(g_d3dOpaqueBS, white.f, 0xf); + pd3dContext->OMSetDepthStencilState(g_d3dDepthLessEqualDSS, 0); + pd3dContext->RSSetState(g_d3dNoCullingSolidRS); + pd3dContext->Draw(6, 0); + + SAFE_RELEASE(pOriginalRTV); + SAFE_RELEASE(pOriginalDSV); + + float scene = (float)TIMER_GetTime(Gpu, L"Scene Rendering") * 1000.0f; + float fsr2 = g_Upscaling == UpscalingFsr2 ? (float)TIMER_GetTime(Gpu, L"FSR2") * 1000.0f : 0.0f; + + fTimeSceneRendering += scene; + fTimeFSR2Rendering += fsr2; + + if (g_bRenderHUD) + { + DXUT_BeginPerfEvent(DXUT_PERFEVENTCOLOR, L"HUD / Stats"); + + g_MagnifyTool.Render(); + g_HUD.OnRender(fElapsedTime); + RenderText(g_FrameRenderingTime, g_FrameDeltaTime, g_SceneRenderingTime, scene, g_Fsr2RenderingTime, fsr2); + + DXUT_EndPerfEvent(); + } + + fAccumulatedTime += g_FrameDeltaTime; + ++nFrameCount; + + if (fAccumulatedTime > 1000.f) + { + g_FrameRenderingTime = fAccumulatedTime / (float)nFrameCount; + g_SceneRenderingTime = fTimeSceneRendering / (float)nFrameCount; + g_Fsr2RenderingTime = fTimeFSR2Rendering / (float)nFrameCount; + + fAccumulatedTime = 0.0f; + fTimeSceneRendering = 0.0f; + fTimeFSR2Rendering = 0.0f; + nFrameCount = 0; + } + + ++g_FrameIndex; + + g_nBufferIdx = 1 - g_nBufferIdx; + *g_pPreviousCamera = *g_pCurrentCamera; + + if (g_bRotateCamera) + { + ArcShotCamera(); + } +} + + +//-------------------------------------------------------------------------------------- +// Release D3D11 resources created in OnD3D11CreateDevice +//-------------------------------------------------------------------------------------- +void CALLBACK OnD3D11DestroyDevice(void* pUserContext) +{ + g_Fsr2Wrapper.Destroy(); + + g_DialogResourceManager.OnD3D11DestroyDevice(); + DXUTGetGlobalResourceCache().OnDestroyDevice(); + SAFE_DELETE(g_pTxtHelper); + + g_MagnifyTool.OnDestroyDevice(); + g_HUD.OnDestroyDevice(); + + ReleaseMeshes(); + + ReleaseShaders(); + + SAFE_RELEASE(g_d3dLinearWrapSS); + SAFE_RELEASE(g_d3dPointWrapSS); + + SAFE_RELEASE(g_d3dBackCullingSolidRS); + + SAFE_RELEASE(g_d3dDepthLessEqualDSS); + SAFE_RELEASE(g_d3dOpaqueBS); + + SAFE_RELEASE(g_d3dViewerCB); + SAFE_RELEASE(g_d3dModelCB); + + for (int i = 0; i < NUM_OF_BUFFER; ++i) + { + g_appColorBuffer[i].Release(); + g_appVelocityBuffer[i].Release(); + g_appDepthBuffer[i].Release(); + } + g_appUpscaledSurface.Release(); + + SAFE_RELEASE(g_d3dNoCullingSolidRS); + + TIMER_Destroy(); +} + + +//-------------------------------------------------------------------------------------- +// Release swap chain and backbuffer associated resources +//-------------------------------------------------------------------------------------- +void CALLBACK OnD3D11ReleasingSwapChain(void* pUserContext) { g_DialogResourceManager.OnD3D11ReleasingSwapChain(); } + + +HRESULT CompileShader(const wchar_t* pFilename, const char* entryPoint, const char* target, ID3DBlob** ppCode) +{ + ID3DBlob* error_blob = NULL; + HRESULT hr = D3DCompileFromFile(pFilename, NULL, NULL, entryPoint, target, D3DCOMPILE_DEBUG, 0, ppCode, &error_blob); + if (error_blob != NULL) + { + OutputDebugStringA((LPCSTR)error_blob->GetBufferPointer()); + } + SAFE_RELEASE(error_blob); + return hr; +} + +//-------------------------------------------------------------------------------------- +// Compile shaders and create Input Layout +//-------------------------------------------------------------------------------------- +HRESULT CompileShaders(ID3D11Device* device) +{ + HRESULT hr = S_OK; + + const D3D11_INPUT_ELEMENT_DESC VSLayout[] = { + { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "NORMAL", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 24, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + }; + + ID3DBlob* code_blob = NULL; + const wchar_t pFilename[] = L"ShaderLibDX\\dx11\\FSR2DX11Sample.hlsl"; + + V_RETURN(CompileShader(pFilename, "VS_RenderModel", "vs_5_0", &code_blob)); + if (hr == S_OK) + { + device->CreateVertexShader(code_blob->GetBufferPointer(), code_blob->GetBufferSize(), NULL, &g_d3dModelVS); + device->CreateInputLayout(VSLayout, AMD_ARRAY_SIZE(VSLayout), code_blob->GetBufferPointer(), code_blob->GetBufferSize(), &g_d3dModelIL); + SAFE_RELEASE(code_blob); + } + + V_RETURN(CompileShader(pFilename, "PS_RenderModel", "ps_5_0", &code_blob)); + if (hr == S_OK) + { + device->CreatePixelShader(code_blob->GetBufferPointer(), code_blob->GetBufferSize(), NULL, &g_d3dModelPS); + SAFE_RELEASE(code_blob); + } + + AMD::CreateFullscreenPass(&g_d3dFullScreenVS, device); + AMD::CreateFullscreenPass(&g_d3dFullScreenPS, device); + + return hr; +} + +HRESULT ReleaseShaders() +{ + SAFE_RELEASE(g_d3dModelVS); + SAFE_RELEASE(g_d3dModelPS); + SAFE_RELEASE(g_d3dModelIL); + SAFE_RELEASE(g_d3dFullScreenPS); + SAFE_RELEASE(g_d3dFullScreenVS); + + return S_OK; +} + +HRESULT CreateMeshes(ID3D11Device* device) +{ + HRESULT hr = S_OK; + + // Load the meshe + hr = g_Model.Create(device, "dx11\\Tank\\", "TankScene.sdkmesh", true); + + assert(hr == S_OK); + + g_ModelDesc.m_World = XMMatrixScaling(1.0f, 1.0f, 1.0f); + g_ModelDesc.m_World_Inv = XMMatrixInverse(&XMMatrixDeterminant(g_ModelDesc.m_World), g_ModelDesc.m_World); + g_ModelDesc.m_Position = float4(0.0f, 0.0f, 0.0f, 1.0f); + g_ModelDesc.m_Orientation = float4(0.0f, 1.0f, 0.0f, 0.0f); + g_ModelDesc.m_Scale = float4(0.001f, 0.001f, 0.001f, 1); + g_ModelDesc.m_Ambient = float4(0.1f, 0.1f, 0.1f, 1.0f); + g_ModelDesc.m_Diffuse = float4(1.0f, 1.0f, 1.0f, 1.0f); + g_ModelDesc.m_Specular = float4(0.5f, 0.5f, 0.0f, 1.0f); + + + D3D11_BUFFER_DESC b1d_desc; + b1d_desc.Usage = D3D11_USAGE_DYNAMIC; + b1d_desc.BindFlags = D3D11_BIND_CONSTANT_BUFFER; + b1d_desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + b1d_desc.MiscFlags = 0; + b1d_desc.ByteWidth = sizeof(S_MODEL_DESC); + hr = device->CreateBuffer(&b1d_desc, NULL, &g_d3dModelCB); + assert(hr == S_OK); + + return hr; +} + +HRESULT ReleaseMeshes() +{ + g_Model.Release(); + + return S_OK; +} + +HRESULT SetupCamera(ID3D11Device* device) +{ + HRESULT hr = S_OK; + + SetCameraParameters(); + + D3D11_BUFFER_DESC b1d_desc; + b1d_desc.Usage = D3D11_USAGE_DYNAMIC; + b1d_desc.BindFlags = D3D11_BIND_CONSTANT_BUFFER; + b1d_desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + b1d_desc.MiscFlags = 0; + b1d_desc.ByteWidth = sizeof(S_CAMERA_DESC) * 2; + hr = device->CreateBuffer(&b1d_desc, NULL, &g_d3dViewerCB); + assert(hr == S_OK); + + return hr; +} diff --git a/src/DX11/FSR2DX11Sample.h b/src/DX11/FSR2DX11Sample.h new file mode 100644 index 0000000..7a029c5 --- /dev/null +++ b/src/DX11/FSR2DX11Sample.h @@ -0,0 +1,145 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +#include + +//-------------------------------------------------------------------------------------- +// Declare Common Sample Types +//-------------------------------------------------------------------------------------- +struct float2 +{ + union + { + struct + { + float x, y; + }; + float v[2]; + }; +}; +struct float3 +{ + union + { + struct + { + float x, y, z; + }; + float v[3]; + }; +}; + +__declspec(align(16)) struct float4 +{ + union + { + DirectX::XMVECTOR v; + float f[4]; + struct + { + float x, y, z, w; + }; + }; + + float4(float ax = 0, float ay = 0, float az = 0, float aw = 0) + { + x = ax; + y = ay; + z = az; + w = aw; + } + + float4(DirectX::XMVECTOR av) { v = av; } + float4(DirectX::XMVECTOR xyz, float aw) + { + v = xyz; + w = aw; + } + + inline operator DirectX::XMVECTOR() const { return v; } + inline operator const float*() const { return f; } +#if !defined(_XM_NO_INTRINSICS_) && defined(_XM_SSE_INTRINSICS_) + inline operator __m128i() const { return _mm_castps_si128(v); } + inline operator __m128d() const { return _mm_castps_pd(v); } +#endif +}; + +#define float4x4 DirectX::XMMATRIX + +// The declaraion of S_CAMERA_DESC matches the declaration of Camera type defined +// in AMD_Types and used throughout the libraries +__declspec(align(16)) typedef struct S_CAMERA_DESC_t +{ + float4x4 m_View; + float4x4 m_Projection; + float4x4 m_ViewProjection; + float4x4 m_View_Inv; + float4x4 m_Projection_Inv; + float4x4 m_ViewProjection_Inv; + float3 m_Position; + float m_Fov; + float3 m_Direction; + float m_FarPlane; + float3 m_Right; + float m_NearPlane; + float3 m_Up; + float m_Aspect; + float4 m_Color; +} S_CAMERA_DESC; + +// The declaraion of S_MODEL_DESC matches the declaration of Model type defined +// in AMD_Types and used throughout the libraries +__declspec(align(16)) typedef struct S_MODEL_DESC_t +{ + float4x4 m_World; + float4x4 m_World_Inv; + float4 m_Position; + float4 m_Orientation; + float4 m_Scale; + float4 m_Ambient; + float4 m_Diffuse; + float4 m_Specular; + float m_mipBias; +} S_MODEL_DESC; + + +//-------------------------------------------------------------------------------------- +// Forward declarations +//-------------------------------------------------------------------------------------- +bool CALLBACK ModifyDeviceSettings(DXUTDeviceSettings* pDeviceSettings, void* pUserContext); +void CALLBACK OnFrameMove(double fTime, float fElapsedTime, void* pUserContext); +void CALLBACK OnKeyboard(UINT nChar, bool bKeyDown, bool bAltDown, void* pUserContext); +void CALLBACK OnGUIEvent(UINT nEvent, int nControlID, CDXUTControl* pControl, void* pUserContext); +LRESULT CALLBACK MsgProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, bool* pbNoFurtherProcessing, void* pUserContext); + +HRESULT CALLBACK OnD3D11CreateDevice(ID3D11Device* pd3dDevice, const DXGI_SURFACE_DESC* pSurfaceDesc, void* pUserContext); +HRESULT CALLBACK OnD3D11ResizedSwapChain(ID3D11Device* pd3dDevice, IDXGISwapChain* pSwapChain, const DXGI_SURFACE_DESC* pSurfaceDesc, void* pUserContext); +void CALLBACK OnD3D11ReleasingSwapChain(void* pUserContext); +void CALLBACK OnD3D11DestroyDevice(void* pUserContext); +void CALLBACK OnD3D11FrameRender(ID3D11Device* pd3dDevice, ID3D11DeviceContext* pd3dContext, double fTime, float fElapsedTime, void* pUserContext); + +HRESULT CompileShaders(ID3D11Device* pd3dDevice); +HRESULT CreateMeshes(ID3D11Device* pd3dDevice); +HRESULT SetupCamera(ID3D11Device* pd3dDevice); + +void InitApp(); +HRESULT ReleaseMeshes(); +HRESULT ReleaseShaders(); diff --git a/src/DX11/FSR2_Sample_DX11.json b/src/DX11/FSR2_Sample_DX11.json new file mode 100644 index 0000000..177382d --- /dev/null +++ b/src/DX11/FSR2_Sample_DX11.json @@ -0,0 +1,11 @@ +{ + "globals": { + "width": 1920, + "height": 1080, + "fullscreen": false, + "upscaling_type": 2, + "scale_mode": 3, + "rotate_camera": true, + "rotate_speed": 0.25 + } +} \ No newline at end of file diff --git a/src/DX11/Fsr2Wrapper.cpp b/src/DX11/Fsr2Wrapper.cpp new file mode 100644 index 0000000..8561801 --- /dev/null +++ b/src/DX11/Fsr2Wrapper.cpp @@ -0,0 +1,111 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +#include "Fsr2Wrapper.h" +#include "../ffx-fsr2-api/dx11/ffx_fsr2_dx11.h" + +void Fsr2Wrapper::Create(Fsr2Wrapper::ContextParameters params) +{ + FFX_ASSERT(!m_created); + + m_contextParams = params; + + // Setup DX11 interface. + m_scratchBuffer.resize(ffxFsr2GetScratchMemorySizeDX11()); + FfxErrorCode errorCode = ffxFsr2GetInterfaceDX11(&m_contextDesc.callbacks, params.device, m_scratchBuffer.data(), m_scratchBuffer.size()); + FFX_ASSERT(errorCode == FFX_OK); + + // This adds a ref to the device. The reference will get freed in ffxFsr2ContextDestroy + m_contextDesc.device = ffxGetDeviceDX11(params.device); + m_contextDesc.maxRenderSize = params.maxRenderSize; + m_contextDesc.displaySize = params.displaySize; + + // You should config the flags you need based on your own project + m_contextDesc.flags = 0; + //FFX_FSR2_ENABLE_MOTION_VECTORS_JITTER_CANCELLATION + //| FFX_FSR2_ENABLE_HIGH_DYNAMIC_RANGE + //| FFX_FSR2_ENABLE_DEPTH_INVERTED + //| FFX_FSR2_ENABLE_AUTO_EXPOSURE; + +#if COMPILE_FROM_HLSL + // Override the shader creation so we can compile from HLSL source. + FfxFsr2Interface d3dInterface = {}; + errorCode = ffxFsr2GetInterfaceDX12(&d3dInterface, m_d3d11Device->GetDevice(), scratchBuffer, scratchBufferSize); + initializationParameters.callbacks.fpCreateRenderPass = s_bUseHLSLShaders ? createRenderPassFromSource : d3dInterface.fpCreateRenderPass; + + // copy for use by on-demand shader compile from HLSL + memcpy(&s_initializationParameters, &initializationParameters, sizeof(FfxFsr2ContextDescription)); +#endif // #if COMPILE_FROM_HLSL + + ffxFsr2ContextCreate(&m_context, &m_contextDesc); + + m_created = true; +} + +void Fsr2Wrapper::Destroy() +{ + FFX_ASSERT(m_created); + + ffxFsr2ContextDestroy(&m_context); + + m_created = false; +} + +void Fsr2Wrapper::Draw(const DrawParameters& params) +{ + FFX_ASSERT(m_created); + + FfxFsr2DispatchDescription dispatchParameters = {}; + dispatchParameters.commandList = params.deviceContext; + dispatchParameters.color = ffxGetResourceDX11(&m_context, params.unresolvedColorResource, L"FSR2_InputColor"); + dispatchParameters.depth = ffxGetResourceDX11(&m_context, params.depthbufferResource, L"FSR2_InputDepth"); + dispatchParameters.motionVectors = ffxGetResourceDX11(&m_context, params.motionvectorResource, L"FSR2_InputMotionVectors"); + dispatchParameters.exposure = ffxGetResourceDX11(&m_context, nullptr, L"FSR2_InputExposure"); + dispatchParameters.reactive = ffxGetResourceDX11(&m_context, params.reactiveMapResource, L"FSR2_InputReactiveMap"); + dispatchParameters.transparencyAndComposition = ffxGetResourceDX11(&m_context, params.transparencyAndCompositionResource, L"FSR2_TransparencyAndCompositionMap"); + dispatchParameters.output = ffxGetResourceDX11(&m_context, params.resolvedColorResource, L"FSR2_OutputUpscaledColor", FFX_RESOURCE_STATE_UNORDERED_ACCESS); + dispatchParameters.jitterOffset.x = params.cameraJitterX; + dispatchParameters.jitterOffset.y = params.cameraJitterY; + dispatchParameters.motionVectorScale.x = -(float)params.renderWidth; // adjust the x direction in motion vector to fit FSR2's requirement + dispatchParameters.motionVectorScale.y = (float)params.renderHeight; + dispatchParameters.reset = params.cameraReset; + dispatchParameters.enableSharpening = params.enableSharpening; + dispatchParameters.sharpness = params.sharpness; + dispatchParameters.frameTimeDelta = params.frameTimeDelta; + dispatchParameters.preExposure = 1.0f; + dispatchParameters.renderSize.width = params.renderWidth; + dispatchParameters.renderSize.height = params.renderHeight; + dispatchParameters.cameraFar = params.farPlane; + dispatchParameters.cameraNear = params.nearPlane;; + dispatchParameters.cameraFovAngleVertical = params.fovH; + + // EXPERIMENTAL feature, auto-generate reactive mask + // Turn it off if you don't need it + dispatchParameters.enableAutoReactive = true; + dispatchParameters.colorOpaqueOnly = ffxGetResourceDX11(&m_context, params.unresolvedColorResource, L"FSR2_InputColor"); + +#if COMPILE_FROM_HLSL + memcpy(&s_initializationParameters, &initializationParameters, sizeof(FfxFsr2ContextDescriptor)); +#endif // #if COMPILE_FROM_HLSL + + FfxErrorCode errorCode = ffxFsr2ContextDispatch(&m_context, &dispatchParameters); + FFX_ASSERT(errorCode == FFX_OK); +} diff --git a/src/DX11/Fsr2Wrapper.h b/src/DX11/Fsr2Wrapper.h new file mode 100644 index 0000000..07776e1 --- /dev/null +++ b/src/DX11/Fsr2Wrapper.h @@ -0,0 +1,92 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +#pragma once + +#include + +#include "../ffx-fsr2-api/ffx_fsr2.h" + +#include + + +class Fsr2Wrapper +{ +public: + struct ContextParameters + { + + uint32_t flags = 0; + FfxDimensions2D maxRenderSize = { 0, 0 }; + FfxDimensions2D displaySize = { 0, 0 }; + ID3D11Device* device = nullptr; + }; + + struct DrawParameters + { + ID3D11DeviceContext* deviceContext = nullptr; + + // Inputs + ID3D11Texture2D* unresolvedColorResource = nullptr; + ID3D11Texture2D* motionvectorResource = nullptr; + ID3D11Texture2D* depthbufferResource = nullptr; + ID3D11Texture2D* reactiveMapResource = nullptr; + ID3D11Texture2D* transparencyAndCompositionResource = nullptr; + + // Output + ID3D11Texture2D* resolvedColorResource = nullptr; + + // Arguments + uint32_t renderWidth = 0; + uint32_t renderHeight = 0; + + bool cameraReset = false; + float cameraJitterX = 0.f; + float cameraJitterY = 0.f; + + bool enableSharpening = true; + float sharpness = 0.f; + + float frameTimeDelta = 0.f; + + float nearPlane = 1.f; + float farPlane = 10.f; + float fovH = 90.f; + }; + +public: + void Create(ContextParameters params); + void Destroy(); + + void Draw(const DrawParameters& params); + + bool IsCreated() const { return m_created; } + FfxDimensions2D GetDisplaySize() const { return m_contextDesc.displaySize; } + +private: + bool m_created = false; + + FfxFsr2Context m_context; + FfxFsr2ContextDescription m_contextDesc; + ContextParameters m_contextParams; + + std::vector m_scratchBuffer; +}; diff --git a/src/DX11/ResourceFiles/GPUOpenChip.ico b/src/DX11/ResourceFiles/GPUOpenChip.ico new file mode 100644 index 0000000..78c5fdd Binary files /dev/null and b/src/DX11/ResourceFiles/GPUOpenChip.ico differ diff --git a/src/DX11/ResourceFiles/GpuOpenIcon.rc b/src/DX11/ResourceFiles/GpuOpenIcon.rc new file mode 100644 index 0000000..8f7816a --- /dev/null +++ b/src/DX11/ResourceFiles/GpuOpenIcon.rc @@ -0,0 +1 @@ +IDI_ICON1 ICON DISCARDABLE "GPUOpenChip.ico" \ No newline at end of file diff --git a/src/DX11/ResourceFiles/dpiaware.manifest b/src/DX11/ResourceFiles/dpiaware.manifest new file mode 100644 index 0000000..5e235e0 --- /dev/null +++ b/src/DX11/ResourceFiles/dpiaware.manifest @@ -0,0 +1,7 @@ + + + + True/PM + + + \ No newline at end of file diff --git a/src/DX11/Shaders/FSR2DX11Sample.hlsl b/src/DX11/Shaders/FSR2DX11Sample.hlsl new file mode 100644 index 0000000..69af6fd --- /dev/null +++ b/src/DX11/Shaders/FSR2DX11Sample.hlsl @@ -0,0 +1,159 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +struct S_MODEL_DESC +{ + float4x4 m_World; + float4x4 m_World_Inv; + float4 m_Position; + float4 m_Orientation; + float4 m_Scale; + float4 m_Ambient; + float4 m_Diffuse; + float4 m_Specular; + float m_mipBias; +}; + +struct S_CAMERA_DESC +{ + float4x4 m_View; + float4x4 m_Projection; + float4x4 m_ViewProjection; + float4x4 m_View_Inv; + float4x4 m_Projection_Inv; + float4x4 m_ViewProjection_Inv; + float3 m_Position; + float m_Fov; + float3 m_Direction; + float m_FarPlane; + float3 m_Right; + float m_NearPlane; + float3 m_Up; + float m_Aspect; + float4 m_Color; +}; + + +struct DirectionalLightInfo +{ + float3 direction; + float3 color; + float specPower; +}; + +static DirectionalLightInfo directionalLights[] = { + { { -0.7943764, -0.32935333, 0.5103845 }, { 1.0, 0.7, 0.6 }, 50.0 }, +}; + +cbuffer CB_MODEL_DATA : register(b0) { S_MODEL_DESC g_Model; } + +cbuffer CB_VIEWER_DATA : register(b1) { S_CAMERA_DESC g_CurrViewer; S_CAMERA_DESC g_PrevViewer; } + +//-------------------------------------------------------------------------------------- +// Buffers, Textures and Samplers +//-------------------------------------------------------------------------------------- +Texture2D g_t2dDiffuse : register(t0); + +SamplerState g_ssLinear : register(s0); + +//-------------------------------------------------------------------------------------- +// Shader structures +//-------------------------------------------------------------------------------------- + +struct VS_RenderInput +{ + float3 m_Position : POSITION; + float3 m_Normal : NORMAL; + float2 m_TexCoord : TEXCOORD; +}; + +struct PS_RenderInput +{ + float4 m_Position : SV_Position; + float4 m_CurrPos : POSITION0; + float4 m_PrevPos : POSITION1; + float3 m_worldPos : WORLDPOS; + float3 m_Normal : NORMAL; + float2 m_TexCoord : TEXCOORD; +}; + +struct PS_RenderOutput +{ + float4 m_Color : SV_Target0; + float2 m_MotionVect : SV_Target1; +}; + +//-------------------------------------------------------------------------------------- +// +//-------------------------------------------------------------------------------------- +PS_RenderInput VS_RenderModel(VS_RenderInput In) +{ + PS_RenderInput Out; + + // Transform the position from object space to homogeneous projection space + Out.m_Position = mul(float4(In.m_Position, 1.0f), mul(g_Model.m_World, g_CurrViewer.m_ViewProjection)); + Out.m_CurrPos = Out.m_Position; + Out.m_PrevPos = mul(float4(In.m_Position, 1.0f), mul(g_Model.m_World, g_PrevViewer.m_ViewProjection)); + Out.m_worldPos = mul(float4(In.m_Position, 1.0f), g_Model.m_World).xyz; + + // Transform the normal from object space to world space + Out.m_Normal = normalize(mul(In.m_Normal, (float3x3)g_Model.m_World)); + + // Pass through texture coords + Out.m_TexCoord = In.m_TexCoord; + + return Out; +} + + +void CalcDirectionalLight(in const DirectionalLightInfo light, in const float3 worldPos, in const float3 normal, in out float3 lightColor) +{ + lightColor += saturate(dot(normal, -light.direction)) * light.color * g_Model.m_Diffuse.rgb; + float3 lightReflect = normalize(reflect(light.direction, normal)); + float spec = saturate(dot(normalize(g_CurrViewer.m_Position - worldPos), lightReflect)); + float specFactor = pow(spec, light.specPower); + lightColor += specFactor * light.color * g_Model.m_Specular.rgb; +} + +//-------------------------------------------------------------------------------------- +// +//-------------------------------------------------------------------------------------- +PS_RenderOutput PS_RenderModel(PS_RenderInput In) +{ + float4 texColor = float4(1, 1, 1, 1); // + texColor = g_t2dDiffuse.SampleBias(g_ssLinear, In.m_TexCoord, g_Model.m_mipBias); + + float3 lightColor = float3(0, 0, 0); + + CalcDirectionalLight(directionalLights[0], In.m_worldPos, In.m_Normal, lightColor); + + float3 ambient = float3(0, 0, 0); + ambient += lerp(float3(0.08, 0.08, 0.05), float3(0.09, 0.1, 0.33), In.m_Normal.y * 0.5 + 0.5); + + float3 color = (lightColor + ambient); + color *= texColor.xyz; + + PS_RenderOutput Out; + Out.m_Color = float4(color, 1.0); + Out.m_MotionVect = In.m_CurrPos.xy / In.m_CurrPos.w - In.m_PrevPos.xy / In.m_PrevPos.w; + + return Out; +} diff --git a/src/DX11/framework/amd_lib/CMakeLists.txt b/src/DX11/framework/amd_lib/CMakeLists.txt new file mode 100644 index 0000000..9b080c5 --- /dev/null +++ b/src/DX11/framework/amd_lib/CMakeLists.txt @@ -0,0 +1,27 @@ +# This file is part of the FidelityFX SDK. +# +# Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +file(GLOB_RECURSE AMD_LIB_SOURCES *.cpp) +file(GLOB_RECURSE AMD_LIB_HEADERS *.h) + +add_library(amd_lib_minimal ${AMD_LIB_SOURCES} ${AMD_LIB_HEADERS}) +target_include_directories(amd_lib_minimal PUBLIC shared/common/inc PUBLIC shared/d3d11/inc) +target_compile_definitions(amd_lib_minimal PRIVATE AMD_LIB_MINIMAL _UNICODE UNICODE) \ No newline at end of file diff --git a/src/DX11/framework/amd_lib/shared/.gitattributes b/src/DX11/framework/amd_lib/shared/.gitattributes new file mode 100644 index 0000000..79f9b77 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/.gitattributes @@ -0,0 +1,30 @@ +# This is a windows-only project. Force CRLF. +* text eol=crlf + +# Explicit settings for specific file types. +*.h eol=crlf +*.hpp eol=crlf +*.inc eol=crlf +*.cpp eol=crlf +*.inl eol=crlf +*.hlsl eol=crlf +*.vcxproj eol=crlf +*.filters eol=crlf +*.props eol=crlf +*.sln eol=crlf +*.bat eol=crlf +*.txt eol=crlf +*.lua eol=crlf +*.md eol=crlf +*.pdf binary +*.ppsx binary +*.ico binary +*.png binary +*.dds binary +*.dll binary +*.exe binary + +# Ensure precompiled shader files are detected as C++. +# Otherwise, if there are a lot of them, the repo can +# get incorrectly marked as Assembly. +src/Shaders/inc/*.inc linguist-language=C++ diff --git a/src/DX11/framework/amd_lib/shared/.gitignore b/src/DX11/framework/amd_lib/shared/.gitignore new file mode 100644 index 0000000..f5da443 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/.gitignore @@ -0,0 +1,36 @@ +## Ignore Visual Studio temporary files, build results, etc. + +# User-specific files +*.suo +*.user + +# Build results +[Dd]esktop_*/ +lib/ + +# Visual Studo 2015 cache/options directory +.vs/ + +# Visual C++ cache files +ipch/ +*.aps +*.ncb +*.opensdf +*.sdf +*.cachefile + +# Visual Studio profiler +*.psess +*.vsp +*.vspx + +# Installshield output folder +[Ee]xpress/ + +# Backup & report files from converting an old project file +# to a newer Visual Studio version. Backup files are not needed, +# because we have git ;-) +_UpgradeReport_Files/ +Backup*/ +UpgradeLog*.XML +UpgradeLog*.htm diff --git a/src/DX11/framework/amd_lib/shared/LICENSE.txt b/src/DX11/framework/amd_lib/shared/LICENSE.txt new file mode 100644 index 0000000..be9c1ee --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/LICENSE.txt @@ -0,0 +1,19 @@ +Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is +furnished to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in +all copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/src/DX11/framework/amd_lib/shared/README.md b/src/DX11/framework/amd_lib/shared/README.md new file mode 100644 index 0000000..37b4571 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/README.md @@ -0,0 +1,11 @@ +# AMD LIB + +The AMD LIB project contains common code shared by [GPUOpen Effects](https://github.com/GPUOpen-Effects/) libraries. + +### Prerequisites +* AMD Radeon™ GCN-based GPU (HD 7000 series or newer) +* 64-bit Windows® 7 (SP1 with the [Platform Update](https://msdn.microsoft.com/en-us/library/windows/desktop/jj863687.aspx)), Windows® 8.1, or Windows® 10 +* Visual Studio® 2013 or Visual Studio® 2015 + +### Getting Started +* Visual Studio projects for VS2013 and VS2015 can be found in the `build` directory. diff --git a/src/DX11/framework/amd_lib/shared/common/inc/AMD_Types.h b/src/DX11/framework/amd_lib/shared/common/inc/AMD_Types.h new file mode 100644 index 0000000..dcc826a --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/common/inc/AMD_Types.h @@ -0,0 +1,176 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_TYPES_H +#define AMD_LIB_TYPES_H + +namespace AMD +{ + typedef long long int64; + typedef int int32; + typedef short int16; + typedef char int8; + typedef char byte; + + typedef long long sint64; + typedef int sint32; + typedef short sint16; + typedef char sint8; + typedef int sint; + typedef short sshort; + typedef char sbyte; + typedef char schar; + + typedef unsigned long long uint64; + typedef unsigned int uint32; + typedef unsigned short uint16; + typedef unsigned char uint8; + + typedef float real32; + typedef double real64; + + typedef unsigned long long ulong; + typedef unsigned int uint; + typedef unsigned short ushort; + typedef unsigned char ubyte; + typedef unsigned char uchar; + + template + T MIN(T a, T b) + { + return (a > b) ? b : a; + } + + template + T MAX(T a, T b) + { + return (a > b) ? a : b; + } + + // The common return codes + typedef enum RETURN_CODE_t + { + RETURN_CODE_SUCCESS, + RETURN_CODE_FAIL, + RETURN_CODE_INVALID_DEVICE, + RETURN_CODE_INVALID_DEVICE_CONTEXT, + RETURN_CODE_COUNT, + } RETURN_CODE; +} + +#ifndef AMD_DECLARE_BASIC_VECTOR_TYPE +# define AMD_DECLARE_BASIC_VECTOR_TYPE \ + struct float2 { union { struct { float x, y; }; float v[2]; }; }; \ + struct float3 { union { struct { float x, y, z; }; float v[3]; }; }; \ + struct float4 { union { struct { float x, y, z, w; }; float v[4]; }; }; \ + struct float4x4 { union { float4 r[4]; float m[16]; }; }; \ + struct uint2 { union { struct { unsigned int x, y; }; unsigned int v[2]; }; }; \ + struct uint3 { union { struct { unsigned int x, y, z; }; unsigned int v[3]; }; }; \ + struct uint4 { union { struct { unsigned int x, y, z, w; }; unsigned int v[4]; }; }; \ + struct sint2 { union { struct { int x, y; }; int v[2]; }; }; \ + struct sint3 { union { struct { int x, y, z; }; int v[3]; }; }; \ + struct sint4 { union { struct { int x, y, z, w; }; int v[4]; }; }; \ + struct sshort2 { union { struct { short x, y; }; short v[2]; }; }; \ + struct sshort3 { union { struct { short x, y, z; }; short v[3]; }; }; \ + struct sshort4 { union { struct { short x, y, z, w; }; short v[4]; }; }; \ + struct sbyte2 { union { struct { signed char x, y; }; signed char v[2]; }; }; \ + struct sbyte3 { union { struct { signed char x, y, z; }; signed char v[3]; }; }; \ + struct sbyte4 { union { struct { signed char x, y, z, w; }; signed char v[4]; }; }; +#endif // AMD_DECLARE_BASIC_VECTOR_TYPE + +#ifndef AMD_DECLARE_CAMERA_TYPE +# define AMD_DECLARE_CAMERA_TYPE \ + typedef struct Camera_t \ + { \ + float4x4 m_View; \ + float4x4 m_Projection; \ + float4x4 m_ViewProjection; \ + float4x4 m_View_Inv; \ + float4x4 m_Projection_Inv; \ + float4x4 m_ViewProjection_Inv; \ + float3 m_Position; \ + float m_Fov; \ + float3 m_Direction; \ + float m_FarPlane; \ + float3 m_Right; \ + float m_NearPlane; \ + float3 m_Up; \ + float m_Aspect; \ + float4 m_Color; \ + } Camera; +#endif // AMD_DECLARE_CAMERA_TYPE + +#ifndef AMD_DECLARE_MODEL_TYPE +# define AMD_DECLARE_MODEL_TYPE \ + typedef struct MODEL_t \ + { \ + float4x4 m_World; \ + float4x4 m_World_Inv; \ + float4x4 m_WorldView; \ + float4x4 m_WorldView_Inv; \ + float4x4 m_WorldViewProjection; \ + float4x4 m_WorldViewProjection_Inv; \ + float4 m_Position; \ + float4 m_Orientation; \ + float4 m_Scale; \ + float4 m_Ambient; \ + float4 m_Diffuse; \ + float4 m_Specular; \ + } MODEL; +#endif // AMD_DECLARE_MODEL_TYPE + +#ifndef AMD_DECLARE_RESOURCE_2D_DESC_TYPE +# define AMD_DECLARE_RESOURCE_2D_DESC_TYPE \ + typedef struct RESOURCE_2D_DESC_t \ + { \ + float2 m_Size; \ + float2 m_Size_Inv; \ + float2 m_Scale; \ + float2 m_Offset; \ + } RESOURCE_2D_DESC; +#endif // AMD_DECLARE_RESOURCE_2D_DESC_TYPE + +#ifndef AMD_SAFE_DELETE +#define AMD_SAFE_DELETE(p) { delete (p); (p) = nullptr; } +#endif +#ifndef AMD_SAFE_DELETE_ARRAY +#define AMD_SAFE_DELETE_ARRAY(p) { delete [] (p); (p) = nullptr; } +#endif +#ifndef AMD_SAFE_RELEASE +#define AMD_SAFE_RELEASE(p) { if (p) { (p)->Release(); } (p) = nullptr; } +#endif + +#define AMD_FUNCTION_WIDEN2(x) L ## x +#define AMD_FUNCTION_WIDEN(x) AMD_FUNCTION_WIDEN2(x) +#define AMD_FUNCTION_WIDE_NAME AMD_FUNCTION_WIDEN(__FUNCTION__) +#define AMD_FUNCTION_NAME __FUNCTION__ + +#define AMD_PITCHED_SIZE(x, y) ( (x+y-1) / y ) + +#define AMD_ARRAY_SIZE( arr ) ( sizeof(arr) / sizeof(arr[0]) ) + +#define AMD_PI 3.141592654f +#define AMD_ROT_ANGLE ( AMD_PI / 180.f ) + +#define AMD_COMPILE_TIME_ASSERT(condition, name) unsigned char g_AMD_CompileTimeAssertExpression ## name [ (condition) ? 1 : -1]; + +#endif //AMD_LIB_TYPES_H diff --git a/src/DX11/framework/amd_lib/shared/d3d11/inc/AMD_LIB.h b/src/DX11/framework/amd_lib/shared/d3d11/inc/AMD_LIB.h new file mode 100644 index 0000000..b67da2a --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/inc/AMD_LIB.h @@ -0,0 +1,48 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: AMD_LIB.h +// +// Library include file, to drag in all AMD LIB helper classes and functions. +//-------------------------------------------------------------------------------------- +#ifndef AMD_LIB_H +#define AMD_LIB_H + +// AMD helper classes and functions +#include "AMD_Types.h" + +#include "../src/AMD_Common.h" +#include "../src/AMD_Texture2D.h" +#include "../src/AMD_Buffer.h" +#include "../src/AMD_Rand.h" +#include "../src/AMD_SaveRestoreState.h" +#include "../src/AMD_FullscreenPass.h" +#include "../src/AMD_UnitCube.h" + +#ifdef _DEBUG +#include "../src/AMD_Serialize.h" +#include "../src/DirectXTex/DDSTextureLoader.h" +#include "../src/DirectXTex/ScreenGrab.h" +#endif + +#endif diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Buffer.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Buffer.cpp new file mode 100644 index 0000000..72028a8 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Buffer.cpp @@ -0,0 +1,160 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include "AMD_LIB.h" + +namespace AMD +{ + Buffer::Buffer() + : _b1d(NULL) + , _srv(NULL) + , _uav(NULL) + , _staging_counter_b1d(NULL) + , _staging_b1d(NULL) + , _size_in_bytes(0) + {}; + Buffer::~Buffer() + { + Release(); + } + + void Buffer::Release() + { + AMD_SAFE_RELEASE(_b1d); + AMD_SAFE_RELEASE(_srv); + AMD_SAFE_RELEASE(_uav); + AMD_SAFE_RELEASE(_staging_counter_b1d); + AMD_SAFE_RELEASE(_staging_b1d); + } + + HRESULT Buffer::CreateBuffer(ID3D11Device * device, + unsigned int uSizeInBytes, + unsigned int uSizeOfStructure, + unsigned int uCPUAccess, + unsigned int uBindFlags, + D3D11_USAGE usage, + DXGI_FORMAT SRV_Format, + DXGI_FORMAT UAV_Format, + unsigned int uUAVFlags, + unsigned int uB1DFlags, + void * data) + { + HRESULT hr = S_OK; + + if (NULL == _b1d) + { + D3D11_SUBRESOURCE_DATA subresource_data; + memset(&subresource_data, 0, sizeof(subresource_data)); + subresource_data.pSysMem = data; + + D3D11_BUFFER_DESC b1d_desc; + memset(&b1d_desc, 0, sizeof(b1d_desc)); + b1d_desc.BindFlags = uBindFlags; + b1d_desc.ByteWidth = uSizeInBytes; + b1d_desc.CPUAccessFlags = uCPUAccess; + b1d_desc.Usage = usage; + b1d_desc.StructureByteStride = (uB1DFlags & D3D11_RESOURCE_MISC_BUFFER_STRUCTURED) ? uSizeOfStructure : 0; + b1d_desc.MiscFlags = uB1DFlags; + + hr = device->CreateBuffer(&b1d_desc, data ? &subresource_data : NULL, &_b1d); + assert(S_OK == hr); + + b1d_desc.BindFlags = 0; + b1d_desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + b1d_desc.Usage = D3D11_USAGE_STAGING; + b1d_desc.MiscFlags = 0; + hr = device->CreateBuffer(&b1d_desc, NULL, &_staging_b1d); + assert(S_OK == hr); + _size_in_bytes = uSizeInBytes; + + D3D11_BUFFER_DESC staging_desc; + memset(&staging_desc, 0, sizeof(staging_desc)); + staging_desc.ByteWidth = sizeof(unsigned int); + staging_desc.Usage = D3D11_USAGE_STAGING; + staging_desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + + hr = device->CreateBuffer(&staging_desc, NULL, &_staging_counter_b1d); + assert(S_OK == hr); + } + + if (uBindFlags & D3D11_BIND_SHADER_RESOURCE) + { + AMD_SAFE_RELEASE(_srv); + + D3D11_SHADER_RESOURCE_VIEW_DESC srv_desc; + memset(&srv_desc, 0, sizeof(srv_desc)); + srv_desc.Format = SRV_Format; + srv_desc.ViewDimension = D3D11_SRV_DIMENSION_BUFFER; + srv_desc.Buffer.FirstElement = 0; + srv_desc.Buffer.NumElements = uSizeInBytes / uSizeOfStructure; + hr = device->CreateShaderResourceView(_b1d, &srv_desc, &_srv); + assert(S_OK == hr); + } + + if (uBindFlags & D3D11_BIND_UNORDERED_ACCESS) + { + AMD_SAFE_RELEASE(_uav); + + D3D11_UNORDERED_ACCESS_VIEW_DESC uav_desc; + memset(&uav_desc, 0, sizeof(D3D11_UNORDERED_ACCESS_VIEW_DESC)); + uav_desc.Format = UAV_Format; + uav_desc.ViewDimension = D3D11_UAV_DIMENSION_BUFFER; + uav_desc.Buffer.FirstElement = 0; + uav_desc.Buffer.NumElements = uSizeInBytes / uSizeOfStructure; + uav_desc.Buffer.Flags = uUAVFlags; + hr = device->CreateUnorderedAccessView(_b1d, &uav_desc, &_uav); + assert(S_OK == hr); + } + + return hr; + } + + int Buffer::UAVCounter(ID3D11DeviceContext * context) + { + int counter = 0; + + // Copy the UAV counter to a staging resource + context->CopyStructureCount(_staging_counter_b1d, 0, _uav); + + // Map the staging resource + D3D11_MAPPED_SUBRESOURCE MappedResource; + context->Map(_staging_counter_b1d, 0, D3D11_MAP_READ, 0, &MappedResource); + { + // Read the data + counter = *(int*)MappedResource.pData; + } + context->Unmap(_staging_counter_b1d, 0); + + return counter; + } + + void Buffer::ReadStgBuffer(ID3D11DeviceContext * context, void * ptr) + { + context->CopyResource(_staging_b1d, _b1d); + + D3D11_MAPPED_SUBRESOURCE subres; + context->Map(_staging_b1d, 0, D3D11_MAP_READ, 0, &subres); + memcpy(ptr, subres.pData, _size_in_bytes); + context->Unmap(_staging_b1d, 0); + } + +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Buffer.h b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Buffer.h new file mode 100644 index 0000000..01d263f --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Buffer.h @@ -0,0 +1,62 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_BUFFER_H +#define AMD_LIB_BUFFER_H + +#include +#include + +namespace AMD +{ + class Buffer + { + public: + ID3D11Buffer * _b1d; + ID3D11ShaderResourceView * _srv; + ID3D11UnorderedAccessView * _uav; + ID3D11Buffer * _staging_b1d; + ID3D11Buffer * _staging_counter_b1d; + + uint _size_in_bytes; + + Buffer(); + ~Buffer(); + void Release(); + HRESULT CreateBuffer( ID3D11Device * device, + unsigned int uSizeInBytes, + unsigned int uSizeOfStructure = 0, + unsigned int uCPUAccess = 0, + unsigned int uBindFlags = D3D11_BIND_SHADER_RESOURCE, + D3D11_USAGE usage = D3D11_USAGE_DEFAULT, + DXGI_FORMAT SRV_Format = DXGI_FORMAT_UNKNOWN, + DXGI_FORMAT UAV_Format = DXGI_FORMAT_UNKNOWN, + unsigned int uUAVFlags = 0, + unsigned int uB1DFlags = 0, + void * data = NULL); + + int UAVCounter( ID3D11DeviceContext * context ); + void ReadStgBuffer( ID3D11DeviceContext * context, void * ptr); + }; +} + +#endif // AMD_LIB_BUFFER_H diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Common.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Common.cpp new file mode 100644 index 0000000..c2e2534 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Common.cpp @@ -0,0 +1,49 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include +#include +#include +#include + +#include "AMD_LIB.h" + +#pragma warning(disable : 4100) + +namespace AMD +{ + void outputDebugString(const char * format, ...) + { +#if defined (DEBUG) || defined (_DEBUG) + assert(format != NULL); + + static char string[1024]; + + va_list argptr; + va_start(argptr, format); + vsprintf_s(string, format, argptr); + va_end(argptr); + + OutputDebugStringA(string); +#endif + } +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Common.h b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Common.h new file mode 100644 index 0000000..b0c6fe7 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Common.h @@ -0,0 +1,37 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_COMMON_H +#define AMD_LIB_COMMON_H + +namespace AMD +{ + void outputDebugString(const char * format, ...); +} + +#if defined(_DEBUG) || defined(DEBUG) +#define AMD_OUTPUT_DEBUG_STRING(format, ...) AMD::outputDebugString(format, ##__VA_ARGS__) +#else +#define AMD_OUTPUT_DEBUG_STRING(format, ...) +#endif + +#endif // AMD_LIB_COMMON_H diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_FullscreenPass.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_FullscreenPass.cpp new file mode 100644 index 0000000..8748a34 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_FullscreenPass.cpp @@ -0,0 +1,229 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include + +#include "AMD_LIB.h" + +#include "AMD_FullscreenPass.h" + +#include "Shaders\inc\VS_FULLSCREEN.inc" +#include "Shaders\inc\VS_SCREENQUAD.inc" + +#include "Shaders\inc\PS_FULLSCREEN.inc" + +#pragma warning( disable : 4100 ) // disable unreference formal parameter warnings for /W4 builds + +namespace AMD +{ + HRESULT CreateFullscreenPass(ID3D11VertexShader** ppVS, ID3D11Device* pDevice) + { + if ( pDevice == NULL || ppVS == NULL ) + { + AMD_OUTPUT_DEBUG_STRING("Invalid Device or Vertex Shader pointers in function %s\n", AMD_FUNCTION_NAME); + return E_POINTER; + } + return pDevice->CreateVertexShader(VS_FULLSCREEN_Data, sizeof(VS_FULLSCREEN_Data), NULL, ppVS); + } + + HRESULT CreateScreenQuadPass(ID3D11VertexShader** ppVS, ID3D11Device* pDevice) + { + if ( pDevice == NULL || ppVS == NULL ) + { + AMD_OUTPUT_DEBUG_STRING("Invalid Device or Vertex Shader pointers in function %s\n", AMD_FUNCTION_NAME); + return E_POINTER; + } + return pDevice->CreateVertexShader(VS_SCREENQUAD_Data, sizeof(VS_SCREENQUAD_Data), NULL, ppVS); + } + + HRESULT CreateFullscreenPass(ID3D11PixelShader** ppPS, ID3D11Device* pDevice) + { + if ( pDevice == NULL || ppPS == NULL ) + { + AMD_OUTPUT_DEBUG_STRING("Invalid Device or Vertex Shader pointers in function %s\n", AMD_FUNCTION_NAME); + return E_INVALIDARG; + } + return pDevice->CreatePixelShader(PS_FULLSCREEN_Data, sizeof(PS_FULLSCREEN_Data), NULL, ppPS); + } + + HRESULT RenderFullscreenPass( + ID3D11DeviceContext* pDeviceContext, + D3D11_VIEWPORT Viewport, + ID3D11VertexShader* pVS, + ID3D11PixelShader* pPS, + D3D11_RECT* pScissor, unsigned int uNumSR, + ID3D11Buffer** ppCB, unsigned int uNumCBs, + ID3D11SamplerState** ppSamplers, unsigned int uNumSamplers, + ID3D11ShaderResourceView** ppSRVs, unsigned int uNumSRVs, + ID3D11RenderTargetView** ppRTVs, unsigned int uNumRTVs, + ID3D11UnorderedAccessView** ppUAVs, unsigned int uStartUAV, unsigned int uNumUAVs, + ID3D11DepthStencilView* pDSV, + ID3D11DepthStencilState* pOutputDSS, unsigned int uStencilRef, + ID3D11BlendState * pOutputBS, + ID3D11RasterizerState * pOutputRS) + { + return RenderFullscreenInstancedPass(pDeviceContext, + Viewport, + pVS, NULL, pPS, + pScissor, uNumSR, + ppCB, uNumCBs, + ppSamplers, uNumSamplers, + ppSRVs, uNumSRVs, + ppRTVs, uNumRTVs, + ppUAVs, uStartUAV, uNumUAVs, + pDSV, pOutputDSS, uStencilRef, + pOutputBS, pOutputRS, 1); + } + + HRESULT RenderFullscreenInstancedPass( + ID3D11DeviceContext* pDeviceContext, + D3D11_VIEWPORT Viewport, + ID3D11VertexShader* pVS, + ID3D11GeometryShader* pGS, + ID3D11PixelShader* pPS, + D3D11_RECT* pScissor, unsigned int uNumSR, + ID3D11Buffer** ppCB, unsigned int uNumCBs, + ID3D11SamplerState** ppSamplers, unsigned int uNumSamplers, + ID3D11ShaderResourceView** ppSRVs, unsigned int uNumSRVs, + ID3D11RenderTargetView** ppRTVs, unsigned int uNumRTVs, + ID3D11UnorderedAccessView** ppUAVs, unsigned int uStartUAV, unsigned int uNumUAVs, + ID3D11DepthStencilView* pDSV, + ID3D11DepthStencilState* pOutputDSS, unsigned int uStencilRef, + ID3D11BlendState * pOutputBS, + ID3D11RasterizerState * pOutputRS, + unsigned int instanceCount) + { + float white[] = {1.0f, 1.0f, 1.0f, 1.0f}; + ID3D11ShaderResourceView* pNullSRV[8] = { NULL }; + ID3D11RenderTargetView* pNullRTV[8] = { NULL }; + ID3D11UnorderedAccessView* pNullUAV[8] = { NULL }; + ID3D11Buffer* pNullBuffer[8] = { NULL }; + uint NullStride[8] = { 0 }; + uint NullOffset[8] = { 0 }; + + if ((pDeviceContext == NULL || (pVS == NULL && pPS == NULL) || (ppRTVs == NULL && pDSV == NULL && ppUAVs == NULL))) + { + AMD_OUTPUT_DEBUG_STRING("Invalid pointer argument in function %s\n", AMD_FUNCTION_NAME); + return E_POINTER; + } + + pDeviceContext->OMSetDepthStencilState( pOutputDSS, uStencilRef ); + if (ppUAVs == NULL) + { + pDeviceContext->OMSetRenderTargets( uNumRTVs, (ID3D11RenderTargetView*const*)ppRTVs, pDSV ); + } + else + { + pDeviceContext->OMSetRenderTargetsAndUnorderedAccessViews( uNumRTVs, (ID3D11RenderTargetView*const*)ppRTVs, pDSV, uStartUAV, uNumUAVs, ppUAVs, NULL); + } + pDeviceContext->OMSetBlendState(pOutputBS, white, 0xFFFFFFFF); + + pDeviceContext->RSSetViewports( 1, &Viewport ); + pDeviceContext->RSSetScissorRects(uNumSR, pScissor); + pDeviceContext->RSSetState( pOutputRS ); + + pDeviceContext->PSSetConstantBuffers( 0, uNumCBs, ppCB); + pDeviceContext->PSSetShaderResources( 0, uNumSRVs, ppSRVs ); + pDeviceContext->PSSetSamplers( 0, uNumSamplers, ppSamplers ); + + pDeviceContext->IASetInputLayout( NULL ); + pDeviceContext->IASetVertexBuffers( 0, AMD_ARRAY_SIZE(pNullBuffer), pNullBuffer, NullStride, NullOffset ); + pDeviceContext->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST ); + + pDeviceContext->VSSetShader( pVS, NULL, 0 ); + pDeviceContext->GSSetShader( pGS, NULL, 0 ); + pDeviceContext->PSSetShader(pPS, NULL, 0); + + pDeviceContext->Draw( 3 * instanceCount, 0 ); + + // Unbind RTVs and SRVs back to NULL (otherwise D3D will throw warnings) + if (ppUAVs == NULL) + { + pDeviceContext->OMSetRenderTargets( AMD_ARRAY_SIZE(pNullRTV), pNullRTV, NULL ); + } + else + { + pDeviceContext->OMSetRenderTargetsAndUnorderedAccessViews( uNumRTVs, pNullRTV, NULL, uStartUAV, uNumUAVs, pNullUAV, NULL); + } + + pDeviceContext->PSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + + return S_OK; + } + + HRESULT RenderFullscreenAlignedQuads( + ID3D11DeviceContext* pDeviceContext, + D3D11_VIEWPORT Viewport, + ID3D11VertexShader* pVS, + ID3D11PixelShader* pPS, + D3D11_RECT* pScissor, unsigned int uNumSR, + ID3D11Buffer** ppCB, unsigned int uNumCBs, + ID3D11SamplerState** ppSamplers, unsigned int uNumSamplers, + ID3D11ShaderResourceView** ppSRVs, unsigned int uNumSRVs, + ID3D11RenderTargetView** ppRTVs, unsigned int uNumRTVs, + ID3D11DepthStencilView* pDSV, + ID3D11DepthStencilState* pOutputDSS, unsigned int uStencilRef, + ID3D11BlendState * pOutputBS, + ID3D11RasterizerState * pOutputRS, + int nCount) + { + float white[] = {1, 1, 1, 1}; + ID3D11ShaderResourceView* pNullSRV[8] = { NULL }; + ID3D11RenderTargetView* pNullRTV[8] = { NULL }; + ID3D11Buffer* pNullBuffer[8] = { NULL }; + UINT NullStride[8] = { 0 }; + UINT NullOffset[8] = { 0 }; + + if ((pDeviceContext == NULL || pVS == NULL || pPS == NULL || (ppRTVs == NULL && pDSV == NULL))) + { + AMD_OUTPUT_DEBUG_STRING("Invalid pointer argument in function %s\n", AMD_FUNCTION_NAME); + return E_POINTER; + } + + pDeviceContext->OMSetDepthStencilState( pOutputDSS, uStencilRef ); + pDeviceContext->OMSetRenderTargets( uNumRTVs, (ID3D11RenderTargetView*const*)ppRTVs, pDSV ); + pDeviceContext->OMSetBlendState(pOutputBS, white, 0xFFFFFFFF); + + pDeviceContext->RSSetViewports( 1, &Viewport ); + pDeviceContext->RSSetScissorRects(uNumSR, pScissor); + pDeviceContext->RSSetState( pOutputRS ); + + pDeviceContext->PSSetConstantBuffers( 0, uNumCBs, ppCB); + pDeviceContext->PSSetShaderResources( 0, uNumSRVs, ppSRVs ); + pDeviceContext->PSSetSamplers( 0, uNumSamplers, ppSamplers ); + + pDeviceContext->IASetInputLayout( NULL ); + pDeviceContext->IASetVertexBuffers( 0, AMD_ARRAY_SIZE(pNullBuffer), pNullBuffer, NullStride, NullOffset ); + pDeviceContext->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST ); + + pDeviceContext->VSSetShader( pVS, NULL, 0 ); + pDeviceContext->PSSetShader(pPS, NULL, 0); + + pDeviceContext->Draw( 6 * nCount, 0 ); + + // Unbind RTVs and SRVs back to NULL (otherwise D3D will throw warnings) + pDeviceContext->OMSetRenderTargets( AMD_ARRAY_SIZE(pNullRTV), pNullRTV, NULL ); + pDeviceContext->PSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + + return S_OK; + } +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_FullscreenPass.h b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_FullscreenPass.h new file mode 100644 index 0000000..0ae4a1b --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_FullscreenPass.h @@ -0,0 +1,88 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_FULLSCREEN_PASS_H +#define AMD_LIB_FULLSCREEN_PASS_H + +#include + +namespace AMD +{ + extern "C++" + { + HRESULT CreateFullscreenPass(ID3D11VertexShader** ppVS, ID3D11Device* pDevice); + HRESULT CreateScreenQuadPass(ID3D11VertexShader** ppVS, ID3D11Device* pDevice); + HRESULT CreateFullscreenPass(ID3D11PixelShader** ppPS, ID3D11Device* pDevice); + + HRESULT RenderFullscreenPass( + ID3D11DeviceContext* pDeviceContext, + D3D11_VIEWPORT Viewport, + ID3D11VertexShader* pVS, + ID3D11PixelShader* pPS, + D3D11_RECT* pScissor, unsigned int uNumSR, + ID3D11Buffer** ppCB, unsigned int uNumCBs, + ID3D11SamplerState** ppSamplers, unsigned int uNumSamplers, + ID3D11ShaderResourceView** ppSRVs, unsigned int uNumSRVs, + ID3D11RenderTargetView** ppRTVs, unsigned int uNumRTVs, + ID3D11UnorderedAccessView**ppUAVs, unsigned int uStartUAV, unsigned int uNumUAVs, + ID3D11DepthStencilView* pDSV, + ID3D11DepthStencilState* pOutputDSS, unsigned int uStencilRef, + ID3D11BlendState * pOutputBS, + ID3D11RasterizerState * pOutputRS); + + HRESULT RenderFullscreenInstancedPass( + ID3D11DeviceContext* pDeviceContext, + D3D11_VIEWPORT Viewport, + ID3D11VertexShader* pVS, + ID3D11GeometryShader* pGS, + ID3D11PixelShader* pPS, + D3D11_RECT* pScissor, unsigned int uNumSR, + ID3D11Buffer** ppCB, unsigned int uNumCBs, + ID3D11SamplerState** ppSamplers, unsigned int uNumSamplers, + ID3D11ShaderResourceView** ppSRVs, unsigned int uNumSRVs, + ID3D11RenderTargetView** ppRTVs, unsigned int uNumRTVs, + ID3D11UnorderedAccessView** ppUAVs, unsigned int uStartUAV, unsigned int uNumUAVs, + ID3D11DepthStencilView* pDSV, + ID3D11DepthStencilState* pOutputDSS, unsigned int uStencilRef, + ID3D11BlendState * pOutputBS, + ID3D11RasterizerState * pOutputRS, + unsigned int instanceCount); + + HRESULT RenderFullscreenAlignedQuads( + ID3D11DeviceContext* pDeviceContext, + D3D11_VIEWPORT Viewport, + ID3D11VertexShader* pVS, + ID3D11PixelShader* pPS, + D3D11_RECT* pScissor, unsigned int uNumSR, + ID3D11Buffer** ppCB, unsigned int uNumCBs, + ID3D11SamplerState** ppSamplers, unsigned int uNumSamplers, + ID3D11ShaderResourceView** ppSRVs, unsigned int uNumSRVs, + ID3D11RenderTargetView** ppRTVs, unsigned int uNumRTVs, + ID3D11DepthStencilView* pDSV, + ID3D11DepthStencilState* pOutputDSS, unsigned int uStencilRef, + ID3D11BlendState * pOutputBS, + ID3D11RasterizerState * pOutputRS, + int nCount); + } +} + +#endif diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Rand.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Rand.cpp new file mode 100644 index 0000000..7eff818 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Rand.cpp @@ -0,0 +1,42 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include "AMD_Types.h" +#include "AMD_Rand.h" + +#pragma warning (disable : 4996) + +namespace AMD +{ + float noise(uint x) + { + x = (x<<13) ^ x; + return ( 1.0f - ( (x * (x * x * 15731 + 789221) + 1376312589) & 0x7fffffff) / 1073741824.0f); + } + + float random_float(uint seed, float a, float b) + { + float random = noise(seed) + 1.0f; + + return a + random * 0.5f * (b - a); + } +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Rand.h b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Rand.h new file mode 100644 index 0000000..f74cc3f --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Rand.h @@ -0,0 +1,34 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_RAND_H +#define AMD_LIB_RAND_H + +#include "AMD_Types.h" + +namespace AMD +{ + float noise(uint seed); + float random_float(uint seed, float a, float b); +} + +#endif //AMD_LIB_RAND_H diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_SaveRestoreState.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_SaveRestoreState.cpp new file mode 100644 index 0000000..14130d4 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_SaveRestoreState.cpp @@ -0,0 +1,369 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include "AMD_SaveRestoreState.h" + +namespace AMD +{ + C_SaveRestore_IA::C_SaveRestore_IA(ID3D11DeviceContext * context) + : m_IAPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_UNDEFINED) + , m_pInputLayout(NULL) + , m_pIAIndexBuffer(NULL) + , m_IAIndexBufferFormat(DXGI_FORMAT_UNKNOWN) + , m_IAIndexBufferOffset(0) + , m_pContext(context) + { + if (context == NULL) { return; } + + memset(m_pIAVertexBuffers, 0, sizeof(m_pIAVertexBuffers)); + memset(m_pIAVertexBuffersStrides, 0, sizeof(m_pIAVertexBuffersStrides)); + memset(m_pIAVertexBuffersOffsets, 0, sizeof(m_pIAVertexBuffersOffsets)); + + m_pContext->IAGetInputLayout( &m_pInputLayout ); + m_pContext->IAGetIndexBuffer( &m_pIAIndexBuffer, &m_IAIndexBufferFormat, &m_IAIndexBufferOffset); + m_pContext->IAGetPrimitiveTopology( &m_IAPrimitiveTopology ); + m_pContext->IAGetVertexBuffers(0, D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT, m_pIAVertexBuffers, m_pIAVertexBuffersStrides, m_pIAVertexBuffersOffsets); + } + + C_SaveRestore_IA::~C_SaveRestore_IA() + { + if (m_pContext == NULL) { return; } + + m_pContext->IASetInputLayout( m_pInputLayout ); + m_pContext->IASetIndexBuffer( m_pIAIndexBuffer, m_IAIndexBufferFormat, m_IAIndexBufferOffset ); + m_pContext->IASetPrimitiveTopology( m_IAPrimitiveTopology ); + m_pContext->IASetVertexBuffers( 0, D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT, m_pIAVertexBuffers, m_pIAVertexBuffersStrides, m_pIAVertexBuffersOffsets ); + + if (m_pInputLayout) {m_pInputLayout->Release(); m_pInputLayout = NULL;} + if (m_pIAIndexBuffer) {m_pIAIndexBuffer->Release(); m_pIAIndexBuffer = NULL;} + for (int i = 0; i < D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT; i++ ) + { + if (m_pIAVertexBuffers[i]) {m_pIAVertexBuffers[i]->Release(); m_pIAVertexBuffers[i] = NULL;} + } + + m_pContext = NULL; + } + + C_SaveRestore_RS::C_SaveRestore_RS(ID3D11DeviceContext * context) + : m_pContext(context) + , m_pRSState(0) + , m_RSRectCount(D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE) + , m_RSViewportCount(D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE) + { + if (context == NULL) { return; } + + memset(m_RSRect, 0, sizeof(m_RSRect)); + memset(m_RSViewport, 0, sizeof(m_RSViewport)); + + m_pContext->RSGetState(&m_pRSState); + m_pContext->RSGetScissorRects(&m_RSRectCount, m_RSRect); + m_pContext->RSGetViewports(&m_RSViewportCount, m_RSViewport); + } + + C_SaveRestore_RS::~C_SaveRestore_RS() + { + if (m_pContext == NULL) { return; } + + m_pContext->RSSetState(m_pRSState); + m_pContext->RSSetScissorRects(m_RSRectCount, m_RSRect); + m_pContext->RSSetViewports(m_RSViewportCount, m_RSViewport); + + if (m_pRSState) {m_pRSState->Release(); m_pRSState = NULL;} + m_RSRectCount = D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE; + m_RSViewportCount = D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE; + m_pContext = NULL; + } + + C_SaveRestore_OM::C_SaveRestore_OM(ID3D11DeviceContext * context) + : m_pContext(context) + , m_pOMBlendState(0) + , m_OMSampleMask(0) + , m_pOMDepthStencilState(0) + , m_OMStencilRef(0) + , m_pOMDSV(0) + { + if (context == NULL) { return; } + + memset(m_OMBlendFactor, 0, sizeof(m_OMBlendFactor)); + memset(m_pOMRTV, 0, sizeof(m_pOMRTV)); + + m_pContext->OMGetBlendState(&m_pOMBlendState, m_OMBlendFactor, &m_OMSampleMask); + m_pContext->OMGetDepthStencilState(&m_pOMDepthStencilState, &m_OMStencilRef); + m_pContext->OMGetRenderTargets(D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT, m_pOMRTV, &m_pOMDSV); + } + + C_SaveRestore_OM::~C_SaveRestore_OM() + { + if (m_pContext == NULL) { return; } + + m_pContext->OMSetBlendState(m_pOMBlendState, m_OMBlendFactor, m_OMSampleMask); + m_pContext->OMSetDepthStencilState(m_pOMDepthStencilState, m_OMStencilRef); + m_pContext->OMSetRenderTargets(D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT, m_pOMRTV, m_pOMDSV); + + if (m_pOMBlendState) {m_pOMBlendState->Release(); m_pOMBlendState = NULL;} + if (m_pOMDepthStencilState) {m_pOMDepthStencilState->Release(); m_pOMDepthStencilState = NULL;} + if (m_pOMDSV) {m_pOMDSV->Release(); m_pOMDSV = NULL;} + for (int i = 0; i < D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT; i++ ) + { if (m_pOMRTV[i]) {m_pOMRTV[i]->Release(); m_pOMRTV[i] = NULL;} } + + m_pContext = NULL; + } + + C_SaveRestore_VS::C_SaveRestore_VS(ID3D11DeviceContext * context) + : m_pContext(context) + , m_pVSShader(0) + { + if (context == NULL) { return; } + + memset(m_pVSSamplers, 0, sizeof(m_pVSSamplers)); + memset(m_pVSConstantBuffer, 0, sizeof(m_pVSConstantBuffer)); + memset(m_pVSSRV, 0, sizeof(m_pVSSRV)); + + m_pContext->VSGetShader(&m_pVSShader, NULL, NULL); + m_pContext->VSGetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pVSSamplers); + m_pContext->VSGetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pVSConstantBuffer); + m_pContext->VSGetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pVSSRV); + } + + C_SaveRestore_VS::~C_SaveRestore_VS() + { + if (m_pContext == NULL) { return; } + + m_pContext->VSSetShader(m_pVSShader, NULL, NULL); + m_pContext->VSSetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pVSSamplers); + m_pContext->VSSetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pVSConstantBuffer); + m_pContext->VSSetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pVSSRV); + + if (m_pVSShader) {m_pVSShader->Release(); m_pVSShader = NULL;} + + for (int i = 0; i < D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT; i++ ) + { if (m_pVSSamplers[i]) {m_pVSSamplers[i]->Release(); m_pVSSamplers[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++ ) + { if (m_pVSConstantBuffer[i]) {m_pVSConstantBuffer[i]->Release(); m_pVSConstantBuffer[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++ ) + { if (m_pVSSRV[i]) {m_pVSSRV[i]->Release(); m_pVSSRV[i] = NULL;} } + + m_pContext = NULL; + } + + C_SaveRestore_HS::C_SaveRestore_HS(ID3D11DeviceContext * context) + : m_pContext(context) + , m_pHSShader(0) + { + if (context == NULL) { return; } + + memset(m_pHSSamplers, 0, sizeof(m_pHSSamplers)); + memset(m_pHSConstantBuffer, 0, sizeof(m_pHSConstantBuffer)); + memset(m_pHSSRV, 0, sizeof(m_pHSSRV)); + + m_pContext->HSGetShader(&m_pHSShader, NULL, NULL); + m_pContext->HSGetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pHSSamplers); + m_pContext->HSGetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pHSConstantBuffer); + m_pContext->HSGetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pHSSRV); + } + + C_SaveRestore_HS::~C_SaveRestore_HS() + { + if (m_pContext == NULL) { return; } + + m_pContext->HSSetShader(m_pHSShader, NULL, NULL); + m_pContext->HSSetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pHSSamplers); + m_pContext->HSSetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pHSConstantBuffer); + m_pContext->HSSetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pHSSRV); + + if (m_pHSShader) {m_pHSShader->Release(); m_pHSShader = NULL;} + + for (int i = 0; i < D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT; i++ ) + { if (m_pHSSamplers[i]) {m_pHSSamplers[i]->Release(); m_pHSSamplers[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++ ) + { if (m_pHSConstantBuffer[i]) {m_pHSConstantBuffer[i]->Release(); m_pHSConstantBuffer[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++ ) + { if (m_pHSSRV[i]) {m_pHSSRV[i]->Release(); m_pHSSRV[i] = NULL;} } + + m_pContext = NULL; + } + + C_SaveRestore_DS::C_SaveRestore_DS(ID3D11DeviceContext * context) + : m_pContext(context) + , m_pDSShader(0) + { + if (context == NULL) { return; } + + memset(m_pDSSamplers, 0, sizeof(m_pDSSamplers)); + memset(m_pDSConstantBuffer, 0, sizeof(m_pDSConstantBuffer)); + memset(m_pDSSRV, 0, sizeof(m_pDSSRV)); + + m_pContext->DSGetShader(&m_pDSShader, NULL, NULL); + m_pContext->DSGetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pDSSamplers); + m_pContext->DSGetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pDSConstantBuffer); + m_pContext->DSGetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pDSSRV); + } + + C_SaveRestore_DS::~C_SaveRestore_DS() + { + if (m_pContext == NULL) { return; } + + m_pContext->DSSetShader(m_pDSShader, NULL, NULL); + m_pContext->DSSetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pDSSamplers); + m_pContext->DSSetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pDSConstantBuffer); + m_pContext->DSSetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pDSSRV); + + if (m_pDSShader) {m_pDSShader->Release(); m_pDSShader = NULL;} + + for (int i = 0; i < D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT; i++ ) + { if (m_pDSSamplers[i]) {m_pDSSamplers[i]->Release(); m_pDSSamplers[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++ ) + { if (m_pDSConstantBuffer[i]) {m_pDSConstantBuffer[i]->Release(); m_pDSConstantBuffer[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++ ) + { if (m_pDSSRV[i]) {m_pDSSRV[i]->Release(); m_pDSSRV[i] = NULL;} } + + m_pContext = NULL; + } + + C_SaveRestore_GS::C_SaveRestore_GS(ID3D11DeviceContext * context) + : m_pContext(context) + , m_pGSShader(0) + { + if (context == NULL) { return; } + + memset(m_pGSSamplers, 0, sizeof(m_pGSSamplers)); + memset(m_pGSConstantBuffer, 0, sizeof(m_pGSConstantBuffer)); + memset(m_pGSSRV, 0, sizeof(m_pGSSRV)); + + m_pContext->GSGetShader(&m_pGSShader, NULL, NULL); + m_pContext->GSGetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pGSSamplers); + m_pContext->GSGetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pGSConstantBuffer); + m_pContext->GSGetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pGSSRV); + } + + C_SaveRestore_GS::~C_SaveRestore_GS() + { + if (m_pContext == NULL) { return; } + + m_pContext->GSSetShader(m_pGSShader, NULL, NULL); + m_pContext->GSSetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pGSSamplers); + m_pContext->GSSetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pGSConstantBuffer); + m_pContext->GSSetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pGSSRV); + + if (m_pGSShader) {m_pGSShader->Release(); m_pGSShader = NULL;} + + for (int i = 0; i < D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT; i++ ) + { if (m_pGSSamplers[i]) {m_pGSSamplers[i]->Release(); m_pGSSamplers[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++ ) + { if (m_pGSConstantBuffer[i]) {m_pGSConstantBuffer[i]->Release(); m_pGSConstantBuffer[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++ ) + { if (m_pGSSRV[i]) {m_pGSSRV[i]->Release(); m_pGSSRV[i] = NULL;} } + + m_pContext = NULL; + } + + C_SaveRestore_PS::C_SaveRestore_PS(ID3D11DeviceContext * context) + : m_pContext(context) + , m_pPSShader(0) + { + if (context == NULL) { return; } + + memset(m_pPSSamplers, 0, sizeof(m_pPSSamplers)); + memset(m_pPSConstantBuffer, 0, sizeof(m_pPSConstantBuffer)); + memset(m_pPSSRV, 0, sizeof(m_pPSSRV)); + + m_pContext->PSGetShader(&m_pPSShader, NULL, NULL); + m_pContext->PSGetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pPSSamplers); + m_pContext->PSGetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pPSConstantBuffer); + m_pContext->PSGetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pPSSRV); + } + + C_SaveRestore_PS::~C_SaveRestore_PS() + { + if (m_pContext == NULL) { return; } + + m_pContext->PSSetShader(m_pPSShader, NULL, NULL); + m_pContext->PSSetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pPSSamplers); + m_pContext->PSSetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pPSConstantBuffer); + m_pContext->PSSetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pPSSRV); + + if (m_pPSShader) {m_pPSShader->Release(); m_pPSShader = NULL;} + + for (int i = 0; i < D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT; i++ ) + { if (m_pPSSamplers[i]) {m_pPSSamplers[i]->Release(); m_pPSSamplers[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++ ) + { if (m_pPSConstantBuffer[i]) {m_pPSConstantBuffer[i]->Release(); m_pPSConstantBuffer[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++ ) + { if (m_pPSSRV[i]) {m_pPSSRV[i]->Release(); m_pPSSRV[i] = NULL;} } + + m_pContext= NULL; + } + + C_SaveRestore_CS::C_SaveRestore_CS(ID3D11DeviceContext * context) + : m_pContext(context) + , m_pCSShader(0) + { + if (context == NULL) { return; } + + memset(m_pCSSamplers, 0, sizeof(m_pCSSamplers)); + memset(m_pCSConstantBuffer, 0, sizeof(m_pCSConstantBuffer)); + memset(m_pCSSRV, 0, sizeof(m_pCSSRV)); + memset(m_pCSUAV, 0, sizeof(m_pCSUAV)); + + m_pContext->CSGetShader(&m_pCSShader, NULL, NULL); + m_pContext->CSGetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pCSSamplers); + m_pContext->CSGetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pCSConstantBuffer); + m_pContext->CSGetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pCSSRV); + m_pContext->CSGetUnorderedAccessViews(0, D3D11_PS_CS_UAV_REGISTER_COUNT, m_pCSUAV); + } + C_SaveRestore_CS::~C_SaveRestore_CS() + { + if (m_pContext == NULL) { return; } + + m_pContext->CSSetShader(m_pCSShader, NULL, NULL); + m_pContext->CSSetSamplers(0, D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT, m_pCSSamplers); + m_pContext->CSSetConstantBuffers(0, D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT, m_pCSConstantBuffer); + m_pContext->CSSetShaderResources(0, D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT, m_pCSSRV); + m_pContext->CSSetUnorderedAccessViews(0, D3D11_PS_CS_UAV_REGISTER_COUNT, m_pCSUAV, NULL); + + if (m_pCSShader) {m_pCSShader->Release(); m_pCSShader = NULL;} + + for (int i = 0; i < D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT; i++ ) + { if (m_pCSSamplers[i]) {m_pCSSamplers[i]->Release(); m_pCSSamplers[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT; i++ ) + { if (m_pCSConstantBuffer[i]) {m_pCSConstantBuffer[i]->Release(); m_pCSConstantBuffer[i] = NULL;} } + + for (int i = 0; i < D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT; i++ ) + { if (m_pCSSRV[i]) {m_pCSSRV[i]->Release(); m_pCSSRV[i] = NULL;} } + + for (int i = 0; i < D3D11_PS_CS_UAV_REGISTER_COUNT; i++ ) + { if (m_pCSUAV[i]) {m_pCSUAV[i]->Release(); m_pCSUAV[i] = NULL;} } + + m_pContext = NULL; + } +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_SaveRestoreState.h b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_SaveRestoreState.h new file mode 100644 index 0000000..1d17a51 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_SaveRestoreState.h @@ -0,0 +1,185 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_SAVE_RESTORE_STATE_H +#define AMD_LIB_SAVE_RESTORE_STATE_H + +#include + +namespace AMD +{ + /*=========================================================================== + INPUT ASSEMBLY STATE GUARD + ===========================================================================*/ + class C_SaveRestore_IA + { + ID3D11InputLayout * m_pInputLayout; + ID3D11Buffer* m_pIAIndexBuffer; + DXGI_FORMAT m_IAIndexBufferFormat; + UINT m_IAIndexBufferOffset; + UINT m_pIAVertexBuffersOffsets[D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT]; + UINT m_pIAVertexBuffersStrides[D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT]; + D3D11_PRIMITIVE_TOPOLOGY m_IAPrimitiveTopology; + ID3D11Buffer* m_pIAVertexBuffers[D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_IA(ID3D11DeviceContext * context); + ~C_SaveRestore_IA(); + }; + + /*=========================================================================== + RASTERIZER STATE GUARD + ===========================================================================*/ + class C_SaveRestore_RS + { + ID3D11RasterizerState * m_pRSState; + D3D11_RECT m_RSRect[D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE]; + UINT m_RSRectCount; + UINT m_RSViewportCount; + D3D11_VIEWPORT m_RSViewport[D3D11_VIEWPORT_AND_SCISSORRECT_OBJECT_COUNT_PER_PIPELINE]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_RS(ID3D11DeviceContext * context); + ~C_SaveRestore_RS(); + }; + + /*=========================================================================== + OUTPUT MERGER STATE GUARD + ===========================================================================*/ + class C_SaveRestore_OM + { + ID3D11BlendState* m_pOMBlendState; + float m_OMBlendFactor[4]; + UINT m_OMSampleMask; + ID3D11DepthStencilState* m_pOMDepthStencilState; + UINT m_OMStencilRef; + ID3D11DepthStencilView* m_pOMDSV; + ID3D11RenderTargetView* m_pOMRTV[D3D11_SIMULTANEOUS_RENDER_TARGET_COUNT]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_OM(ID3D11DeviceContext * context); + ~C_SaveRestore_OM(); + }; + + /*=========================================================================== + VERTEX SHADER STATE GUARD + ===========================================================================*/ + class C_SaveRestore_VS + { + ID3D11VertexShader* m_pVSShader; + ID3D11SamplerState* m_pVSSamplers[D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT]; + ID3D11Buffer* m_pVSConstantBuffer[D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT]; + ID3D11ShaderResourceView* m_pVSSRV[D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_VS(ID3D11DeviceContext * context); + ~C_SaveRestore_VS(); + }; + + /*=========================================================================== + HULL SHADER STATE GUARD + ===========================================================================*/ + class C_SaveRestore_HS + { + ID3D11HullShader* m_pHSShader; + ID3D11SamplerState* m_pHSSamplers[D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT]; + ID3D11Buffer* m_pHSConstantBuffer[D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT]; + ID3D11ShaderResourceView* m_pHSSRV[D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_HS(ID3D11DeviceContext * context); + ~C_SaveRestore_HS(); + }; + + /*=========================================================================== + DOMAIN SHADER STATE GUARD + ===========================================================================*/ + class C_SaveRestore_DS + { + ID3D11DomainShader* m_pDSShader; + ID3D11SamplerState* m_pDSSamplers[D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT]; + ID3D11Buffer* m_pDSConstantBuffer[D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT]; + ID3D11ShaderResourceView* m_pDSSRV[D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_DS(ID3D11DeviceContext * context); + ~C_SaveRestore_DS(); + }; + + /*=========================================================================== + GEOMETRY SHADER STATE GUARD + ===========================================================================*/ + class C_SaveRestore_GS + { + ID3D11GeometryShader* m_pGSShader; + ID3D11SamplerState* m_pGSSamplers[D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT]; + ID3D11Buffer* m_pGSConstantBuffer[D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT]; + ID3D11ShaderResourceView* m_pGSSRV[D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_GS(ID3D11DeviceContext * context); + ~C_SaveRestore_GS(); + }; + + /*=========================================================================== + PIXEL SHADER STATE GUARD + ===========================================================================*/ + class C_SaveRestore_PS + { + + ID3D11PixelShader* m_pPSShader; + ID3D11SamplerState* m_pPSSamplers[D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT]; + ID3D11Buffer* m_pPSConstantBuffer[D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT]; + ID3D11ShaderResourceView* m_pPSSRV[D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_PS(ID3D11DeviceContext * context); + ~C_SaveRestore_PS(); + }; + + /*=========================================================================== + COMPUTE SHADER STATE GUARD + ===========================================================================*/ + class C_SaveRestore_CS + { + ID3D11ComputeShader* m_pCSShader; + ID3D11SamplerState* m_pCSSamplers[D3D11_COMMONSHADER_SAMPLER_SLOT_COUNT]; + ID3D11Buffer* m_pCSConstantBuffer[D3D11_COMMONSHADER_CONSTANT_BUFFER_API_SLOT_COUNT]; + ID3D11ShaderResourceView* m_pCSSRV[D3D11_COMMONSHADER_INPUT_RESOURCE_SLOT_COUNT]; + ID3D11UnorderedAccessView* m_pCSUAV[D3D11_PS_CS_UAV_REGISTER_COUNT]; + ID3D11DeviceContext * m_pContext; + + public: + C_SaveRestore_CS(ID3D11DeviceContext * context); + ~C_SaveRestore_CS(); + }; +}; + +#endif diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Serialize.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Serialize.cpp new file mode 100644 index 0000000..bfc8e3d --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Serialize.cpp @@ -0,0 +1,194 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include +#include + +#include "AMD_Types.h" +#include "AMD_Serialize.h" + +#pragma warning (disable : 4996) + +namespace AMD +{ + AMD_COMPILE_TIME_ASSERT( sizeof(uchar) == 1, size_of_uchar); + AMD_COMPILE_TIME_ASSERT( sizeof(ushort) == 2, size_of_ushort); + AMD_COMPILE_TIME_ASSERT( sizeof(uint) == 4, size_of_uint); + AMD_COMPILE_TIME_ASSERT( sizeof(ulong) == 8, size_of_ulong); + AMD_COMPILE_TIME_ASSERT( sizeof(real32) == 4, size_of_real32); + AMD_COMPILE_TIME_ASSERT( sizeof(real64) == 8, size_of_real64); + + void serialize_string(FILE * file, char * name) + { + fprintf(file, "%s\n", name); + } + + void serialize_float(FILE * file, const char * name, float * v) + { + fprintf(file, "#%s = %.10f; \n", name, v[0]); + serialize_uint(file, name, (uint *) v); + } + + void serialize_float2(FILE * file, const char * name, float * v) + { + fprintf(file, "#%s = %.10f %.10f; \n", name, v[0], v[1]); + serialize_uint2(file, name, (uint *) v); + } + + void serialize_float3(FILE * file, const char * name, float * v) + { + fprintf(file, "#%s = %.10f %.10f %.10f; \n", name, v[0], v[1], v[2]); + serialize_uint3(file, name, (uint *) v); + } + + void serialize_float4(FILE * file, const char * name, float * v) + { + fprintf(file, "#%s = %.10f %.10f %.10f %.10f; \n", name, v[0], v[1], v[2], v[3]); + serialize_uint4(file, name, (uint *) v); + } + + void serialize_float4x4(FILE * file, const char * name, float * v) + { + std::string row_name; + row_name = std::string(name) + "[0]"; + serialize_float4(file, row_name.c_str(), &v[0]); + row_name = std::string(name) + "[1]"; + serialize_float4(file, row_name.c_str(), &v[4]); + row_name = std::string(name) + "[2]"; + serialize_float4(file, row_name.c_str(), &v[8]); + row_name = std::string(name) + "[3]"; + serialize_float4(file, row_name.c_str(), &v[12]); + } + + void serialize_uint(FILE * file, const char * name, uint32 * v) + { + fprintf(file, "%s = %X; \n", name, v[0]); + } + + void serialize_uint2(FILE * file, const char * name, uint32 * v) + { + fprintf(file, "%s = %X %X; \n", name, v[0], v[1]); + } + + void serialize_uint3(FILE * file, const char * name, uint32 * v) + { + fprintf(file, "%s = %X %X %X; \n", name, v[0], v[1], v[2]); + } + + void serialize_uint4(FILE * file, const char * name, uint32 * v) + { + fprintf(file, "%s = %X %X %X %X; \n", name, v[0], v[1], v[2], v[3]); + } + + void deserialize_string(FILE * file, char * name) + { + fscanf(file, "%s\n", name); + } + + void deserialize_float(FILE * file, char * name, float * v, bool use_float) + { + float f[4]; + fscanf(file, "#%s = %f; \n", name, &v[0]); + + if (use_float) + { + deserialize_uint(file, name, (uint *) f); + } + else + { + deserialize_uint(file, name, (uint *) v); + } + } + + void deserialize_float2(FILE * file, char * name, float * v, bool use_float) + { + float f[4]; + fscanf(file, "#%s = %f %f; \n", name, &v[0], &v[1]); + + if (use_float) + { + deserialize_uint2(file, name, (uint *) f); + } + else + { + deserialize_uint2(file, name, (uint *) v); + } + } + + void deserialize_float3(FILE * file, char * name, float * v, bool use_float) + { + float f[4]; + fscanf(file, "#%s = %f %f %f; \n", name, &v[0], &v[1], &v[2]); + + if (use_float) + { + deserialize_uint3(file, name, (uint *) f); + } + else + { + deserialize_uint3(file, name, (uint *) v); + } + } + + void deserialize_float4(FILE * file, char * name, float * v, bool use_float) + { + float f[4]; + fscanf(file, "#%s = %f %f %f %f; \n", name, &v[0], &v[1], &v[2], &v[3]); + + if (use_float) + { + deserialize_uint4(file, name, (uint *) f); + } + else + { + deserialize_uint4(file, name, (uint *) v); + } + } + + void deserialize_float4x4(FILE * file, char * name, float * v, bool use_float) + { + AMD::deserialize_float4(file, name, &v[0], use_float); + AMD::deserialize_float4(file, name, &v[4], use_float); + AMD::deserialize_float4(file, name, &v[8], use_float); + AMD::deserialize_float4(file, name, &v[12], use_float); + } + + void deserialize_uint(FILE * file, char * name, uint32 * v) + { + fscanf(file, "%s = %X; \n", name, &v[0]); + } + + void deserialize_uint2(FILE * file, char * name, uint32 * v) + { + fscanf(file, "%s = %X %X; \n", name, &v[0], &v[1]); + } + + void deserialize_uint3(FILE * file, char * name, uint32 * v) + { + fscanf(file, "%s = %X %X %X; \n", name, &v[0], &v[1], &v[2]); + } + + void deserialize_uint4(FILE * file, char * name, uint32 * v) + { + fscanf(file, "%s = %X %X %X %X; \n", name, &v[0], &v[1], &v[2], &v[3]); + } +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Serialize.h b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Serialize.h new file mode 100644 index 0000000..20766ea --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Serialize.h @@ -0,0 +1,64 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_SERIALIZE_H +#define AMD_LIB_SERIALIZE_H + +#include "AMD_Types.h" + +// forward declarations +struct _iobuf; +typedef struct _iobuf FILE; + +namespace AMD +{ + void serialize_string(FILE * file, char * name); + + void serialize_float(FILE * file, const char * name, float * v); + void serialize_float2(FILE * file, const char * name, float * v); + void serialize_float3(FILE * file, const char * name, float * v); + void serialize_float4(FILE * file, const char * name, float * v); + void serialize_uint(FILE * file, const char * name, uint32 * v); + void serialize_uint2(FILE * file, const char * name, uint32 * v); + void serialize_uint3(FILE * file, const char * name, uint32 * v); + void serialize_uint4(FILE * file, const char * name, uint32 * v); + void serialize_float4x4(FILE * file, const char * name, float * v); + + void deserialize_float(FILE * file, char * name, float * v, bool use_float = false); + void deserialize_float2(FILE * file, char * name, float * v, bool use_float = false); + void deserialize_float3(FILE * file, char * name, float * v, bool use_float = false); + void deserialize_float4(FILE * file, char * name, float * v, bool use_float = false); + void deserialize_uint(FILE * file, char * name, uint32 * v); + void deserialize_uint2(FILE * file, char * name, uint32 * v); + void deserialize_uint3(FILE * file, char * name, uint32 * v); + void deserialize_uint4(FILE * file, char * name, uint32 * v); + void deserialize_float4x4(FILE * file, char * name, float * v, bool use_float = false); + + void deserialize_string(FILE * file, char * name); +} + + +#define AMD_SERIALIZE_STRING_FLOAT_PTR(x) #x, (float *) &x +#define AMD_SERIALIZE_STRING_UINT_PTR(x) #x, (uint *) &x + + +#endif //AMD_LIB_SERIALIZE_H diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Texture2D.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Texture2D.cpp new file mode 100644 index 0000000..6005a39 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Texture2D.cpp @@ -0,0 +1,482 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include + +#include "AMD_LIB.h" + +#ifndef AMD_LIB_MINIMAL +#include "amd_ags.h" +#endif + +#pragma warning( disable : 4100 ) // disable unreferenced formal parameter warnings for /W4 builds + +namespace AMD +{ + Texture2D::Texture2D() + : _t2d(NULL) + , _srv(NULL) + , _srv_cube(NULL) + , _rtv(NULL) + , _dsv(NULL) + , _dsv_ro(NULL) + , _uav(NULL) + , _width(0) + , _height(0) + , _array(0) + , _mips(0) + , _sample(0) + { + for (int i = 0; i < 6; i++) + { + _rtv_cube[i] = NULL; + _dsv_cube[i] = NULL; + } + }; + + Texture2D::~Texture2D() + { + Release(); + } + + void Texture2D::Release() + { + _width = 0; + _height = 0; + _array = 0; + _mips = 0; + _sample = 0; + + for (int i = 0; i < 6; i++) + { + AMD_SAFE_RELEASE(_rtv_cube[i]); + AMD_SAFE_RELEASE(_dsv_cube[i]); + } + + AMD_SAFE_RELEASE(_srv_cube); + AMD_SAFE_RELEASE(_t2d); + AMD_SAFE_RELEASE(_srv); + AMD_SAFE_RELEASE(_rtv); + AMD_SAFE_RELEASE(_dsv); + AMD_SAFE_RELEASE(_uav); + AMD_SAFE_RELEASE(_dsv_ro); + } + + HRESULT Texture2D::CreateSurface(ID3D11Device * pDevice, + unsigned int uWidth, + unsigned int uHeight, + unsigned int uSampleCount, + unsigned int uArraySize, + unsigned int uMipLevels, + DXGI_FORMAT T2D_Format, + DXGI_FORMAT SRV_Format, + DXGI_FORMAT RTV_Format, + DXGI_FORMAT DSV_Format, + DXGI_FORMAT UAV_Format, + DXGI_FORMAT DSV_RO_Format, + D3D11_USAGE usage, + bool bCube, + unsigned int pitch, + void * data, + AGSContext * agsContext, + int cfxTransferType) + { + HRESULT hr = S_OK; + + if (DXGI_FORMAT_UNKNOWN != T2D_Format) + { + D3D11_TEXTURE2D_DESC t2d_desc; + memset(&t2d_desc, 0, sizeof(t2d_desc)); + + if (NULL == _t2d) + { + t2d_desc.Width = uWidth; + t2d_desc.Height = uHeight; + t2d_desc.MipLevels = 1; + t2d_desc.ArraySize = uArraySize; + t2d_desc.SampleDesc.Count = uSampleCount; + t2d_desc.SampleDesc.Quality = (uSampleCount > 1) ? (D3D11_STANDARD_MULTISAMPLE_PATTERN) : (0); + t2d_desc.Usage = usage; + t2d_desc.Format = T2D_Format; + + t2d_desc.BindFlags = 0; + if (SRV_Format != DXGI_FORMAT_UNKNOWN) { t2d_desc.BindFlags |= D3D11_BIND_SHADER_RESOURCE; } + if (RTV_Format != DXGI_FORMAT_UNKNOWN) { t2d_desc.BindFlags |= D3D11_BIND_RENDER_TARGET; } + if (DSV_Format != DXGI_FORMAT_UNKNOWN) { t2d_desc.BindFlags |= D3D11_BIND_DEPTH_STENCIL; } + if (UAV_Format != DXGI_FORMAT_UNKNOWN) { t2d_desc.BindFlags |= D3D11_BIND_UNORDERED_ACCESS; } + if (DSV_RO_Format != DXGI_FORMAT_UNKNOWN) { t2d_desc.BindFlags |= D3D11_BIND_DEPTH_STENCIL; } + + if (bCube) { t2d_desc.MiscFlags = D3D11_RESOURCE_MISC_TEXTURECUBE; } + + D3D11_SUBRESOURCE_DATA subresource_data; + memset(&subresource_data, 0, sizeof(subresource_data)); + subresource_data.pSysMem = data; + subresource_data.SysMemPitch = pitch; + +#ifndef AMD_LIB_MINIMAL + if (agsContext != NULL) + { + hr = agsDriverExtensions_CreateTexture2D(agsContext, &t2d_desc, data != NULL ? &subresource_data : NULL, &_t2d, (AGSAfrTransferType)cfxTransferType); + } + else +#endif + { + hr = pDevice->CreateTexture2D(&t2d_desc, data != NULL ? &subresource_data : NULL, &_t2d); + } + + assert(S_OK == hr); + + _width = uWidth; + _height = uHeight; + _array = uArraySize; + _mips = uMipLevels; + _sample = uSampleCount; + } + + if (DXGI_FORMAT_UNKNOWN != SRV_Format) + { + AMD_SAFE_RELEASE(_srv); + + D3D11_SHADER_RESOURCE_VIEW_DESC srv_desc; + memset(&srv_desc, 0, sizeof(srv_desc)); + srv_desc.Format = SRV_Format; + + if (uArraySize == 1) + { + if (uSampleCount == 1) + { + srv_desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + srv_desc.Texture2D.MostDetailedMip = 0; + srv_desc.Texture2D.MipLevels = _mips; + } + else + { + srv_desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DMS; + assert(_mips == 1); + } + } + else + { + if (uSampleCount == 1) + { + srv_desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY; + srv_desc.Texture2DArray.MostDetailedMip = 0; + srv_desc.Texture2DArray.MipLevels = _mips; + srv_desc.Texture2DArray.ArraySize = uArraySize; + srv_desc.Texture2DArray.FirstArraySlice = 0; + } + else + { + srv_desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DMSARRAY; + srv_desc.Texture2DMSArray.ArraySize = uArraySize; + srv_desc.Texture2DMSArray.FirstArraySlice = 0; + assert(_mips == 1); + } + } + + hr = pDevice->CreateShaderResourceView(_t2d, &srv_desc, &_srv); + assert(S_OK == hr); + } + + if (bCube && DXGI_FORMAT_UNKNOWN != SRV_Format) + { + AMD_SAFE_RELEASE(_srv_cube); + + D3D11_SHADER_RESOURCE_VIEW_DESC srv_desc; + memset(&srv_desc, 0, sizeof(srv_desc)); + srv_desc.Format = SRV_Format; + + if (uArraySize == 6) + { + if (uSampleCount == 1) + { + srv_desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE; + srv_desc.TextureCube.MostDetailedMip = 0; + srv_desc.TextureCube.MipLevels = _mips; + } + else + { + assert(0); + } + } + else + { + if (uSampleCount == 1) + { + srv_desc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBEARRAY; + srv_desc.TextureCubeArray.MostDetailedMip = 0; + srv_desc.TextureCubeArray.MipLevels = _mips; + srv_desc.TextureCubeArray.NumCubes = uArraySize / 6; + srv_desc.TextureCubeArray.First2DArrayFace = 0; + } + else + { + assert(0); + } + } + + hr = pDevice->CreateShaderResourceView(_t2d, &srv_desc, &_srv_cube); + assert(S_OK == hr); + } + + if (DXGI_FORMAT_UNKNOWN != RTV_Format) + { + AMD_SAFE_RELEASE(_rtv); + + D3D11_RENDER_TARGET_VIEW_DESC rtv_desc; + memset(&rtv_desc, 0, sizeof(rtv_desc)); + rtv_desc.Format = RTV_Format; + + if (uArraySize == 1) + { + if (uSampleCount == 1) + { + rtv_desc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2D; + rtv_desc.Texture2D.MipSlice = 0; + } + else + { + rtv_desc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DMS; + } + } + else + { + if (uSampleCount == 1) + { + rtv_desc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY; + rtv_desc.Texture2DArray.MipSlice = 0; + rtv_desc.Texture2DArray.ArraySize = uArraySize; + rtv_desc.Texture2DArray.FirstArraySlice = 0; + } + else + { + rtv_desc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DMSARRAY; + rtv_desc.Texture2DMSArray.ArraySize = uArraySize; + rtv_desc.Texture2DMSArray.FirstArraySlice = 0; + } + } + + + hr = pDevice->CreateRenderTargetView(_t2d, &rtv_desc, &_rtv); + assert(S_OK == hr); + } + + if (bCube && DXGI_FORMAT_UNKNOWN != RTV_Format) + { + for (int i = 0; i < 6; i++) + { + AMD_SAFE_RELEASE(_rtv_cube[i]); + } + + D3D11_RENDER_TARGET_VIEW_DESC rtv_desc; + memset(&rtv_desc, 0, sizeof(rtv_desc)); + rtv_desc.Format = RTV_Format; + + if (uArraySize == 6) + { + if (uSampleCount == 1) + { + + rtv_desc.ViewDimension = D3D11_RTV_DIMENSION_TEXTURE2DARRAY; + rtv_desc.Texture2DArray.MipSlice = 0; + rtv_desc.Texture2DArray.ArraySize = 1; + + for (int i = 0; i < 6; i++) + { + rtv_desc.Texture2DArray.FirstArraySlice = i; + hr = pDevice->CreateRenderTargetView(_t2d, &rtv_desc, &_rtv_cube[i]); + assert(S_OK == hr); + } + } + else // cube textures can't have MS + { + assert(0); + } + } + else // cube arrays not yet supported + { + assert(0); + } + } + + if (DXGI_FORMAT_UNKNOWN != DSV_Format) + { + AMD_SAFE_RELEASE(_dsv); + + D3D11_DEPTH_STENCIL_VIEW_DESC dsv_desc; + memset(&dsv_desc, 0, sizeof(dsv_desc)); + dsv_desc.Format = DSV_Format; + + if (uArraySize == 1) + { + if (uSampleCount == 1) + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D; + dsv_desc.Texture2D.MipSlice = 0; + } + else + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DMS; + } + } + else + { + if (uSampleCount == 1) + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DARRAY; + dsv_desc.Texture2DArray.MipSlice = 0; + dsv_desc.Texture2DArray.ArraySize = uArraySize; + dsv_desc.Texture2DArray.FirstArraySlice = 0; + } + else + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DMSARRAY; + dsv_desc.Texture2DMSArray.ArraySize = uArraySize; + dsv_desc.Texture2DMSArray.FirstArraySlice = 0; + } + } + + hr = pDevice->CreateDepthStencilView(_t2d, &dsv_desc, &_dsv); + assert(S_OK == hr); + } + + if (bCube && DXGI_FORMAT_UNKNOWN != DSV_Format) + { + for (int i = 0; i < 6; i++) + { + AMD_SAFE_RELEASE(_dsv_cube[i]); + } + + D3D11_DEPTH_STENCIL_VIEW_DESC dsv_desc; + memset(&dsv_desc, 0, sizeof(dsv_desc)); + dsv_desc.Format = DSV_Format; + + if (uArraySize == 6) + { + if (uSampleCount == 1) + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DARRAY; + dsv_desc.Texture2DArray.MipSlice = 0; + dsv_desc.Texture2DArray.ArraySize = 1; + + for (int i = 0; i < 6; i++) + { + dsv_desc.Texture2DArray.FirstArraySlice = i; + hr = pDevice->CreateDepthStencilView(_t2d, &dsv_desc, &_dsv_cube[i]); + assert(S_OK == hr); + } + } + else // cube textures can't have MS + { + assert(0); + } + } + else // cube arrays not yet supported + { + assert(0); + } + } + + if (DXGI_FORMAT_UNKNOWN != DSV_RO_Format) + { + AMD_SAFE_RELEASE(_dsv_ro); + + D3D11_DEPTH_STENCIL_VIEW_DESC dsv_desc; + memset(&dsv_desc, 0, sizeof(dsv_desc)); + dsv_desc.Format = DSV_RO_Format; + if (uArraySize == 1) + { + if (uSampleCount == 1) + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D; + dsv_desc.Texture2D.MipSlice = 0; + } + else + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DMS; + } + } + else + { + if (uSampleCount == 1) + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DARRAY; + dsv_desc.Texture2DArray.MipSlice = 0; + dsv_desc.Texture2DArray.ArraySize = uArraySize; + dsv_desc.Texture2DArray.FirstArraySlice = 0; + } + else + { + dsv_desc.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DMSARRAY; + dsv_desc.Texture2DMSArray.ArraySize = uArraySize; + dsv_desc.Texture2DMSArray.FirstArraySlice = 0; + } + } + dsv_desc.Flags = D3D11_DSV_READ_ONLY_DEPTH; + + hr = pDevice->CreateDepthStencilView(_t2d, &dsv_desc, &_dsv_ro); + assert(S_OK == hr); + } + + if (DXGI_FORMAT_UNKNOWN != UAV_Format) + { + AMD_SAFE_RELEASE(_uav); + + D3D11_UNORDERED_ACCESS_VIEW_DESC uav_desc; + memset(&uav_desc, 0, sizeof(uav_desc)); + uav_desc.Format = UAV_Format; + + if (uArraySize == 1) + { + if (uSampleCount == 1) + { + uav_desc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE2D; + uav_desc.Texture2D.MipSlice = 0; + } + else + { + assert(uSampleCount == 1); // UAV and Multisampling are incompatible + } + } + else + { + if (uSampleCount == 1) + { + uav_desc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE2DARRAY; + uav_desc.Texture2DArray.MipSlice = 0; + uav_desc.Texture2DArray.ArraySize = uArraySize; + uav_desc.Texture2DArray.FirstArraySlice = 0; + } + else + { + assert(uSampleCount == 1); // UAV and Multisampling are incompatible + } + } + + hr = pDevice->CreateUnorderedAccessView(_t2d, &uav_desc, &_uav); + assert(S_OK == hr); + } + } + + return hr; + } +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Texture2D.h b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Texture2D.h new file mode 100644 index 0000000..ae80e6e --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_Texture2D.h @@ -0,0 +1,78 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_TEXTURE_2D_H +#define AMD_LIB_TEXTURE_2D_H + +#include + +// forward declarations +struct AGSContext; + +namespace AMD +{ + class Texture2D + { + public: + ID3D11Texture2D * _t2d; + ID3D11ShaderResourceView * _srv; + ID3D11ShaderResourceView * _srv_cube; + ID3D11RenderTargetView * _rtv; + ID3D11RenderTargetView * _rtv_cube[6]; + ID3D11DepthStencilView * _dsv; + ID3D11DepthStencilView * _dsv_cube[6]; + ID3D11DepthStencilView * _dsv_ro; + ID3D11UnorderedAccessView * _uav; + + unsigned int _width; + unsigned int _height; + unsigned int _array; + unsigned int _mips; + unsigned int _sample; + + Texture2D(); + ~Texture2D(); + + void Release(); + + HRESULT CreateSurface( ID3D11Device * pDevice, + unsigned int uWidth, + unsigned int uHeight, + unsigned int uSampleCount /*= 1*/, + unsigned int uArraySize /*= 1*/, + unsigned int uMipLevels /*= 1*/, + DXGI_FORMAT T2D_Format /* = DXGI_FORMAT_UNKNOWN */, + DXGI_FORMAT SRV_Format /* = DXGI_FORMAT_UNKNOWN */, + DXGI_FORMAT RTV_Format /* = DXGI_FORMAT_UNKNOWN */, + DXGI_FORMAT DSV_Format /* = DXGI_FORMAT_UNKNOWN */, + DXGI_FORMAT UAV_Format /* = DXGI_FORMAT_UNKNOWN */, + DXGI_FORMAT DSV_RO_Format /* = DXGI_FORMAT_UNKNOWN */, + D3D11_USAGE usage /* = D3D11_USAGE_DEFAULT */, + bool bCube, + unsigned int pitch /* = 0 */, + void * data /*= NULL */, + AGSContext * agsContext /* = NULL*/, + int cfxTransferType /*= (AGSAfrTransferType)0*/); + }; +} + +#endif diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_UnitCube.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_UnitCube.cpp new file mode 100644 index 0000000..ea63673 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_UnitCube.cpp @@ -0,0 +1,162 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include "AMD_LIB.h" + +#include "Shaders\inc\VS_UNIT_CUBE.inc" +#include "Shaders\inc\VS_CLIP_SPACE_CUBE.inc" +#include "Shaders\inc\PS_UNIT_CUBE.inc" + +#pragma warning( disable : 4100 ) // disable unreference formal parameter warnings for /W4 builds + +namespace AMD +{ + HRESULT CreateUnitCube(ID3D11VertexShader ** ppVS, ID3D11Device *pDevice) + { + if (pDevice == NULL || ppVS == NULL) + { + AMD_OUTPUT_DEBUG_STRING("Invalid Device or Vertex Shader pointers in function %s\n", AMD_FUNCTION_NAME); + return E_POINTER; + } + + return pDevice->CreateVertexShader(VS_UNIT_CUBE_Data, sizeof(VS_UNIT_CUBE_Data), NULL, ppVS); + } + + + HRESULT CreateClipSpaceCube(ID3D11VertexShader** ppVS, ID3D11Device* pDevice) + { + if (pDevice == NULL || ppVS == NULL) + { + AMD_OUTPUT_DEBUG_STRING("Invalid Device or Vertex Shader pointers in function %s\n", AMD_FUNCTION_NAME); + return E_POINTER; + } + + return pDevice->CreateVertexShader(VS_CLIP_SPACE_CUBE_Data, sizeof(VS_CLIP_SPACE_CUBE_Data), NULL, ppVS); + } + + + HRESULT CreateUnitCube(ID3D11PixelShader** ppPS, ID3D11Device* pDevice) + { + if (pDevice == NULL || ppPS == NULL) + { + AMD_OUTPUT_DEBUG_STRING("Invalid Device or Vertex Shader pointers in function %s\n", AMD_FUNCTION_NAME); + return E_POINTER; + } + + return pDevice->CreatePixelShader(PS_UNIT_CUBE_Data, sizeof(PS_UNIT_CUBE_Data), NULL, ppPS); + } + + HRESULT RenderUnitCube(ID3D11DeviceContext* pd3dContext, + D3D11_VIEWPORT VP, + D3D11_RECT* pSR, unsigned int nSRCount, + ID3D11RasterizerState * pRS, + ID3D11BlendState * pBS, const float bsFactor[], + ID3D11DepthStencilState* pDSS, unsigned int stencilRef, + ID3D11VertexShader* pVS, + ID3D11HullShader* pHS, + ID3D11DomainShader* pDS, + ID3D11GeometryShader* pGS, + ID3D11PixelShader* pPS, + ID3D11Buffer** ppCB, unsigned int nCBStart, unsigned int nCBCount, + ID3D11SamplerState** ppSS, unsigned int nSSStart, unsigned int nSSCount, + ID3D11ShaderResourceView** ppSRV, unsigned int nSRVStart, unsigned int nSRVCount, + ID3D11RenderTargetView** ppRTV, unsigned int nRTVCount, + ID3D11DepthStencilView* pDSV) + { + // Useful common locals + ID3D11RenderTargetView * const pNullRTV[8] = { 0 }; + ID3D11ShaderResourceView * const pNullSRV[128] = { 0 }; + ID3D11Buffer * const pNullBuffer[8] = { 0 }; + + // Unbind anything that could be still bound on input or output + // If this doesn't happen, DX Runtime will spam with warnings + pd3dContext->OMSetRenderTargets( AMD_ARRAY_SIZE(pNullRTV), pNullRTV, NULL ); + pd3dContext->CSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + pd3dContext->VSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + pd3dContext->HSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + pd3dContext->DSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + pd3dContext->GSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + pd3dContext->PSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + + UINT NullStride[8] = { 0 }; + UINT NullOffset[8] = { 0 }; + + if ( pd3dContext == NULL || pVS == NULL || (ppRTV == NULL && pDSV == NULL) ) + { + AMD_OUTPUT_DEBUG_STRING("Invalid interface pointers in function %s\n", AMD_FUNCTION_NAME); + return E_POINTER; + } + + pd3dContext->VSSetShader( pVS, NULL, 0 ); + pd3dContext->HSSetShader( pHS, NULL, 0 ); + pd3dContext->DSSetShader( pDS, NULL, 0 ); + pd3dContext->GSSetShader( pGS, NULL, 0 ); + pd3dContext->PSSetShader( pPS, NULL, 0 ); + + if (nSSCount) + { + pd3dContext->VSSetSamplers( nSSStart, nSSCount, ppSS ); + pd3dContext->HSSetSamplers( nSSStart, nSSCount, ppSS ); + pd3dContext->DSSetSamplers( nSSStart, nSSCount, ppSS ); + pd3dContext->GSSetSamplers( nSSStart, nSSCount, ppSS ); + pd3dContext->PSSetSamplers( nSSStart, nSSCount, ppSS ); + } + + if (nSRVCount) + { + pd3dContext->VSSetShaderResources( nSRVStart, nSRVCount, ppSRV ); + pd3dContext->HSSetShaderResources( nSRVStart, nSRVCount, ppSRV ); + pd3dContext->DSSetShaderResources( nSRVStart, nSRVCount, ppSRV ); + pd3dContext->GSSetShaderResources( nSRVStart, nSRVCount, ppSRV ); + pd3dContext->PSSetShaderResources( nSRVStart, nSRVCount, ppSRV ); + } + + if (nCBCount) + { + pd3dContext->VSSetConstantBuffers( nCBStart, nCBCount, ppCB ); + pd3dContext->HSSetConstantBuffers( nCBStart, nCBCount, ppCB ); + pd3dContext->DSSetConstantBuffers( nCBStart, nCBCount, ppCB ); + pd3dContext->GSSetConstantBuffers( nCBStart, nCBCount, ppCB ); + pd3dContext->PSSetConstantBuffers( nCBStart, nCBCount, ppCB ); + } + + pd3dContext->OMSetDepthStencilState( pDSS, stencilRef ); + pd3dContext->OMSetRenderTargets( nRTVCount, (ID3D11RenderTargetView*const*)ppRTV, pDSV ); + pd3dContext->OMSetBlendState(pBS, bsFactor, 0xFFFFFFFF); + + pd3dContext->RSSetViewports( 1, &VP ); + pd3dContext->RSSetScissorRects( nSRCount, pSR ); + pd3dContext->RSSetState( pRS ); + + pd3dContext->IASetInputLayout( NULL ); + pd3dContext->IASetVertexBuffers( 0, AMD_ARRAY_SIZE(pNullBuffer), pNullBuffer, NullStride, NullOffset ); + pd3dContext->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST ); + + pd3dContext->Draw( 36, 0 ); + + // Unbind RTVs and SRVs back to NULL (otherwise D3D will throw warnings) + pd3dContext->OMSetRenderTargets( AMD_ARRAY_SIZE(pNullRTV), pNullRTV, NULL ); + pd3dContext->PSSetShaderResources( 0, AMD_ARRAY_SIZE(pNullSRV), pNullSRV ); + + return S_OK; + } +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_UnitCube.h b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_UnitCube.h new file mode 100644 index 0000000..c8eaa0f --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/AMD_UnitCube.h @@ -0,0 +1,53 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_UNIT_CUBE_H +#define AMD_LIB_UNIT_CUBE_H + +#include + +namespace AMD +{ + HRESULT CreateUnitCube(ID3D11VertexShader** ppVS, ID3D11Device* pDevice); + HRESULT CreateUnitCube(ID3D11PixelShader** ppPS, ID3D11Device* pDevice); + + HRESULT CreateClipSpaceCube(ID3D11VertexShader** ppVS, ID3D11Device* pDevice); + + HRESULT RenderUnitCube(ID3D11DeviceContext* pDeviceContext, + D3D11_VIEWPORT VP, + D3D11_RECT* pSR, unsigned int uNumSR, + ID3D11RasterizerState * pRS, + ID3D11BlendState * pBS, const float bsFactor[], + ID3D11DepthStencilState* pDSS, unsigned int stencilRef, + ID3D11VertexShader* pVS, + ID3D11HullShader* pHS, + ID3D11DomainShader* pDS, + ID3D11GeometryShader* pGS, + ID3D11PixelShader* pPS, + ID3D11Buffer** ppCB, unsigned int uStartCB, unsigned int uNumCB, + ID3D11SamplerState** ppSS, unsigned int uStartSS, unsigned int uNumSS, + ID3D11ShaderResourceView** ppSRV, unsigned int uStartSRV, unsigned int uNumSRV, + ID3D11RenderTargetView** ppRTV, unsigned int uNumRTV, + ID3D11DepthStencilView* pDSV); +} + +#endif diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/DDSTextureLoader.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/DDSTextureLoader.cpp new file mode 100644 index 0000000..f2a8bf9 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/DDSTextureLoader.cpp @@ -0,0 +1,1836 @@ +//-------------------------------------------------------------------------------------- +// File: DDSTextureLoader.cpp +// +// Functions for loading a DDS texture and creating a Direct3D 11 runtime resource for it +// +// Note these functions are useful as a light-weight runtime loader for DDS files. For +// a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#include +#include +#include + +#include "DDSTextureLoader.h" + +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) +#pragma comment(lib,"dxguid.lib") +#endif + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +// Macros +//-------------------------------------------------------------------------------------- +#ifndef MAKEFOURCC + #define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +//-------------------------------------------------------------------------------------- +// DDS file structure definitions +// +// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library +//-------------------------------------------------------------------------------------- +#pragma pack(push,1) + +const uint32_t DDS_MAGIC = 0x20534444; // "DDS " + +struct DDS_PIXELFORMAT +{ + uint32_t size; + uint32_t flags; + uint32_t fourCC; + uint32_t RGBBitCount; + uint32_t RBitMask; + uint32_t GBitMask; + uint32_t BBitMask; + uint32_t ABitMask; +}; + +#define DDS_FOURCC 0x00000004 // DDPF_FOURCC +#define DDS_RGB 0x00000040 // DDPF_RGB +#define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE +#define DDS_ALPHA 0x00000002 // DDPF_ALPHA +#define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + +#define DDS_HEADER_FLAGS_VOLUME 0x00800000 // DDSD_DEPTH + +#define DDS_HEIGHT 0x00000002 // DDSD_HEIGHT +#define DDS_WIDTH 0x00000004 // DDSD_WIDTH + +#define DDS_CUBEMAP_POSITIVEX 0x00000600 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEX +#define DDS_CUBEMAP_NEGATIVEX 0x00000a00 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEX +#define DDS_CUBEMAP_POSITIVEY 0x00001200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEY +#define DDS_CUBEMAP_NEGATIVEY 0x00002200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEY +#define DDS_CUBEMAP_POSITIVEZ 0x00004200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEZ +#define DDS_CUBEMAP_NEGATIVEZ 0x00008200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEZ + +#define DDS_CUBEMAP_ALLFACES ( DDS_CUBEMAP_POSITIVEX | DDS_CUBEMAP_NEGATIVEX |\ + DDS_CUBEMAP_POSITIVEY | DDS_CUBEMAP_NEGATIVEY |\ + DDS_CUBEMAP_POSITIVEZ | DDS_CUBEMAP_NEGATIVEZ ) + +#define DDS_CUBEMAP 0x00000200 // DDSCAPS2_CUBEMAP + +enum DDS_MISC_FLAGS2 +{ + DDS_MISC_FLAGS2_ALPHA_MODE_MASK = 0x7L, +}; + +struct DDS_HEADER +{ + uint32_t size; + uint32_t flags; + uint32_t height; + uint32_t width; + uint32_t pitchOrLinearSize; + uint32_t depth; // only if DDS_HEADER_FLAGS_VOLUME is set in flags + uint32_t mipMapCount; + uint32_t reserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t caps; + uint32_t caps2; + uint32_t caps3; + uint32_t caps4; + uint32_t reserved2; +}; + +struct DDS_HEADER_DXT10 +{ + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see D3D11_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t miscFlags2; +}; + +#pragma pack(pop) + +//-------------------------------------------------------------------------------------- +namespace +{ + +struct handle_closer { void operator()(HANDLE h) { if (h) CloseHandle(h); } }; + +typedef public std::unique_ptr ScopedHandle; + +inline HANDLE safe_handle( HANDLE h ) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + +template +inline void SetDebugObjectName(_In_ ID3D11DeviceChild* resource, _In_ const char (&name)[TNameLength]) +{ +#if defined(_DEBUG) || defined(PROFILE) + resource->SetPrivateData(WKPDID_D3DDebugObjectName, TNameLength - 1, name); +#else + UNREFERENCED_PARAMETER(resource); + UNREFERENCED_PARAMETER(name); +#endif +} + +}; + +//-------------------------------------------------------------------------------------- +static HRESULT LoadTextureDataFromFile( _In_z_ const wchar_t* fileName, + std::unique_ptr& ddsData, + DDS_HEADER** header, + uint8_t** bitData, + size_t* bitSize + ) +{ + if (!header || !bitData || !bitSize) + { + return E_POINTER; + } + + // open the file +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile( safe_handle( CreateFile2( fileName, + GENERIC_READ, + FILE_SHARE_READ, + OPEN_EXISTING, + nullptr ) ) ); +#else + ScopedHandle hFile( safe_handle( CreateFileW( fileName, + GENERIC_READ, + FILE_SHARE_READ, + nullptr, + OPEN_EXISTING, + FILE_ATTRIBUTE_NORMAL, + nullptr ) ) ); +#endif + + if ( !hFile ) + { + return HRESULT_FROM_WIN32( GetLastError() ); + } + + // Get the file size + LARGE_INTEGER FileSize = { 0 }; + +#if (_WIN32_WINNT >= _WIN32_WINNT_VISTA) + FILE_STANDARD_INFO fileInfo; + if ( !GetFileInformationByHandleEx( hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo) ) ) + { + return HRESULT_FROM_WIN32( GetLastError() ); + } + FileSize = fileInfo.EndOfFile; +#else + GetFileSizeEx( hFile.get(), &FileSize ); +#endif + + // File is too big for 32-bit allocation, so reject read + if (FileSize.HighPart > 0) + { + return E_FAIL; + } + + // Need at least enough data to fill the header and magic number to be a valid DDS + if (FileSize.LowPart < ( sizeof(DDS_HEADER) + sizeof(uint32_t) ) ) + { + return E_FAIL; + } + + // create enough space for the file data + ddsData.reset( new (std::nothrow) uint8_t[ FileSize.LowPart ] ); + if (!ddsData) + { + return E_OUTOFMEMORY; + } + + // read the data in + DWORD BytesRead = 0; + if (!ReadFile( hFile.get(), + ddsData.get(), + FileSize.LowPart, + &BytesRead, + nullptr + )) + { + return HRESULT_FROM_WIN32( GetLastError() ); + } + + if (BytesRead < FileSize.LowPart) + { + return E_FAIL; + } + + // DDS files always start with the same magic number ("DDS ") + uint32_t dwMagicNumber = *( const uint32_t* )( ddsData.get() ); + if (dwMagicNumber != DDS_MAGIC) + { + return E_FAIL; + } + + auto hdr = reinterpret_cast( ddsData.get() + sizeof( uint32_t ) ); + + // Verify header to validate DDS file + if (hdr->size != sizeof(DDS_HEADER) || + hdr->ddspf.size != sizeof(DDS_PIXELFORMAT)) + { + return E_FAIL; + } + + // Check for DX10 extension + bool bDXT10Header = false; + if ((hdr->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC( 'D', 'X', '1', '0' ) == hdr->ddspf.fourCC)) + { + // Must be long enough for both headers and magic value + if (FileSize.LowPart < ( sizeof(DDS_HEADER) + sizeof(uint32_t) + sizeof(DDS_HEADER_DXT10) ) ) + { + return E_FAIL; + } + + bDXT10Header = true; + } + + // setup the pointers in the process request + *header = hdr; + ptrdiff_t offset = sizeof( uint32_t ) + sizeof( DDS_HEADER ) + + (bDXT10Header ? sizeof( DDS_HEADER_DXT10 ) : 0); + *bitData = ddsData.get() + offset; + *bitSize = FileSize.LowPart - offset; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Return the BPP for a particular format +//-------------------------------------------------------------------------------------- +static size_t BitsPerPixel( _In_ DXGI_FORMAT fmt ) +{ + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return 8; + + default: + return 0; + } +} + + +//-------------------------------------------------------------------------------------- +// Get surface information for a particular format +//-------------------------------------------------------------------------------------- +static void GetSurfaceInfo( _In_ size_t width, + _In_ size_t height, + _In_ DXGI_FORMAT fmt, + _Out_opt_ size_t* outNumBytes, + _Out_opt_ size_t* outRowBytes, + _Out_opt_ size_t* outNumRows ) +{ + size_t numBytes = 0; + size_t rowBytes = 0; + size_t numRows = 0; + + bool bc = false; + bool packed = false; + bool planar = false; + size_t bpe = 0; + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + bc=true; + bpe = 8; + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc = true; + bpe = 16; + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + packed = true; + bpe = 4; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + packed = true; + bpe = 8; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + planar = true; + bpe = 2; + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + planar = true; + bpe = 4; + break; + } + + if (bc) + { + size_t numBlocksWide = 0; + if (width > 0) + { + numBlocksWide = std::max( 1, (width + 3) / 4 ); + } + size_t numBlocksHigh = 0; + if (height > 0) + { + numBlocksHigh = std::max( 1, (height + 3) / 4 ); + } + rowBytes = numBlocksWide * bpe; + numRows = numBlocksHigh; + numBytes = rowBytes * numBlocksHigh; + } + else if (packed) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numRows = height; + numBytes = rowBytes * height; + } + else if ( fmt == DXGI_FORMAT_NV11 ) + { + rowBytes = ( ( width + 3 ) >> 2 ) * 4; + numRows = height * 2; // Direct3D makes this simplifying assumption, although it is larger than the 4:1:1 data + numBytes = rowBytes * numRows; + } + else if (planar) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numBytes = ( rowBytes * height ) + ( ( rowBytes * height + 1 ) >> 1 ); + numRows = height + ( ( height + 1 ) >> 1 ); + } + else + { + size_t bpp = BitsPerPixel( fmt ); + rowBytes = ( width * bpp + 7 ) / 8; // round up to nearest byte + numRows = height; + numBytes = rowBytes * height; + } + + if (outNumBytes) + { + *outNumBytes = numBytes; + } + if (outRowBytes) + { + *outRowBytes = rowBytes; + } + if (outNumRows) + { + *outNumRows = numRows; + } +} + + +//-------------------------------------------------------------------------------------- +#define ISBITMASK( r,g,b,a ) ( ddpf.RBitMask == r && ddpf.GBitMask == g && ddpf.BBitMask == b && ddpf.ABitMask == a ) + +static DXGI_FORMAT GetDXGIFormat( const DDS_PIXELFORMAT& ddpf ) +{ + if (ddpf.flags & DDS_RGB) + { + // Note that sRGB formats are written using the "DX10" extended header + + switch (ddpf.RGBBitCount) + { + case 32: + if (ISBITMASK(0x000000ff,0x0000ff00,0x00ff0000,0xff000000)) + { + return DXGI_FORMAT_R8G8B8A8_UNORM; + } + + if (ISBITMASK(0x00ff0000,0x0000ff00,0x000000ff,0xff000000)) + { + return DXGI_FORMAT_B8G8R8A8_UNORM; + } + + if (ISBITMASK(0x00ff0000,0x0000ff00,0x000000ff,0x00000000)) + { + return DXGI_FORMAT_B8G8R8X8_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x000000ff,0x0000ff00,0x00ff0000,0x00000000) aka D3DFMT_X8B8G8R8 + + // Note that many common DDS reader/writers (including D3DX) swap the + // the RED/BLUE masks for 10:10:10:2 formats. We assume + // below that the 'backwards' header mask is being used since it is most + // likely written by D3DX. The more robust solution is to use the 'DX10' + // header extension and specify the DXGI_FORMAT_R10G10B10A2_UNORM format directly + + // For 'correct' writers, this should be 0x000003ff,0x000ffc00,0x3ff00000 for RGB data + if (ISBITMASK(0x3ff00000,0x000ffc00,0x000003ff,0xc0000000)) + { + return DXGI_FORMAT_R10G10B10A2_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x000003ff,0x000ffc00,0x3ff00000,0xc0000000) aka D3DFMT_A2R10G10B10 + + if (ISBITMASK(0x0000ffff,0xffff0000,0x00000000,0x00000000)) + { + return DXGI_FORMAT_R16G16_UNORM; + } + + if (ISBITMASK(0xffffffff,0x00000000,0x00000000,0x00000000)) + { + // Only 32-bit color channel format in D3D9 was R32F + return DXGI_FORMAT_R32_FLOAT; // D3DX writes this out as a FourCC of 114 + } + break; + + case 24: + // No 24bpp DXGI formats aka D3DFMT_R8G8B8 + break; + + case 16: + if (ISBITMASK(0x7c00,0x03e0,0x001f,0x8000)) + { + return DXGI_FORMAT_B5G5R5A1_UNORM; + } + if (ISBITMASK(0xf800,0x07e0,0x001f,0x0000)) + { + return DXGI_FORMAT_B5G6R5_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x7c00,0x03e0,0x001f,0x0000) aka D3DFMT_X1R5G5B5 + + if (ISBITMASK(0x0f00,0x00f0,0x000f,0xf000)) + { + return DXGI_FORMAT_B4G4R4A4_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x0f00,0x00f0,0x000f,0x0000) aka D3DFMT_X4R4G4B4 + + // No 3:3:2, 3:3:2:8, or paletted DXGI formats aka D3DFMT_A8R3G3B2, D3DFMT_R3G3B2, D3DFMT_P8, D3DFMT_A8P8, etc. + break; + } + } + else if (ddpf.flags & DDS_LUMINANCE) + { + if (8 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x000000ff,0x00000000,0x00000000,0x00000000)) + { + return DXGI_FORMAT_R8_UNORM; // D3DX10/11 writes this out as DX10 extension + } + + // No DXGI format maps to ISBITMASK(0x0f,0x00,0x00,0xf0) aka D3DFMT_A4L4 + } + + if (16 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x0000ffff,0x00000000,0x00000000,0x00000000)) + { + return DXGI_FORMAT_R16_UNORM; // D3DX10/11 writes this out as DX10 extension + } + if (ISBITMASK(0x000000ff,0x00000000,0x00000000,0x0000ff00)) + { + return DXGI_FORMAT_R8G8_UNORM; // D3DX10/11 writes this out as DX10 extension + } + } + } + else if (ddpf.flags & DDS_ALPHA) + { + if (8 == ddpf.RGBBitCount) + { + return DXGI_FORMAT_A8_UNORM; + } + } + else if (ddpf.flags & DDS_BUMPDUDV) + { + if (16 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x00ff, 0xff00, 0x0000, 0x0000)) + { + return DXGI_FORMAT_R8G8_SNORM; // D3DX10/11 writes this out as DX10 extension + } + } + + if (32 == ddpf.RGBBitCount) + { + if (ISBITMASK(0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000)) + { + return DXGI_FORMAT_R8G8B8A8_SNORM; // D3DX10/11 writes this out as DX10 extension + } + if (ISBITMASK(0x0000ffff, 0xffff0000, 0x00000000, 0x00000000)) + { + return DXGI_FORMAT_R16G16_SNORM; // D3DX10/11 writes this out as DX10 extension + } + + // No DXGI format maps to ISBITMASK(0x3ff00000, 0x000ffc00, 0x000003ff, 0xc0000000) aka D3DFMT_A2W10V10U10 + } + } + else if (ddpf.flags & DDS_FOURCC) + { + if (MAKEFOURCC( 'D', 'X', 'T', '1' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC1_UNORM; + } + if (MAKEFOURCC( 'D', 'X', 'T', '3' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC2_UNORM; + } + if (MAKEFOURCC( 'D', 'X', 'T', '5' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC3_UNORM; + } + + // While pre-multiplied alpha isn't directly supported by the DXGI formats, + // they are basically the same as these BC formats so they can be mapped + if (MAKEFOURCC( 'D', 'X', 'T', '2' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC2_UNORM; + } + if (MAKEFOURCC( 'D', 'X', 'T', '4' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC3_UNORM; + } + + if (MAKEFOURCC( 'A', 'T', 'I', '1' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_UNORM; + } + if (MAKEFOURCC( 'B', 'C', '4', 'U' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_UNORM; + } + if (MAKEFOURCC( 'B', 'C', '4', 'S' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_SNORM; + } + + if (MAKEFOURCC( 'A', 'T', 'I', '2' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_UNORM; + } + if (MAKEFOURCC( 'B', 'C', '5', 'U' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_UNORM; + } + if (MAKEFOURCC( 'B', 'C', '5', 'S' ) == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_SNORM; + } + + // BC6H and BC7 are written using the "DX10" extended header + + if (MAKEFOURCC( 'R', 'G', 'B', 'G' ) == ddpf.fourCC) + { + return DXGI_FORMAT_R8G8_B8G8_UNORM; + } + if (MAKEFOURCC( 'G', 'R', 'G', 'B' ) == ddpf.fourCC) + { + return DXGI_FORMAT_G8R8_G8B8_UNORM; + } + + if (MAKEFOURCC('Y','U','Y','2') == ddpf.fourCC) + { + return DXGI_FORMAT_YUY2; + } + + // Check for D3DFORMAT enums being set here + switch( ddpf.fourCC ) + { + case 36: // D3DFMT_A16B16G16R16 + return DXGI_FORMAT_R16G16B16A16_UNORM; + + case 110: // D3DFMT_Q16W16V16U16 + return DXGI_FORMAT_R16G16B16A16_SNORM; + + case 111: // D3DFMT_R16F + return DXGI_FORMAT_R16_FLOAT; + + case 112: // D3DFMT_G16R16F + return DXGI_FORMAT_R16G16_FLOAT; + + case 113: // D3DFMT_A16B16G16R16F + return DXGI_FORMAT_R16G16B16A16_FLOAT; + + case 114: // D3DFMT_R32F + return DXGI_FORMAT_R32_FLOAT; + + case 115: // D3DFMT_G32R32F + return DXGI_FORMAT_R32G32_FLOAT; + + case 116: // D3DFMT_A32B32G32R32F + return DXGI_FORMAT_R32G32B32A32_FLOAT; + } + } + + return DXGI_FORMAT_UNKNOWN; +} + + +//-------------------------------------------------------------------------------------- +static DXGI_FORMAT MakeSRGB( _In_ DXGI_FORMAT format ) +{ + switch( format ) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + + default: + return format; + } +} + + +//-------------------------------------------------------------------------------------- +static HRESULT FillInitData( _In_ size_t width, + _In_ size_t height, + _In_ size_t depth, + _In_ size_t mipCount, + _In_ size_t arraySize, + _In_ DXGI_FORMAT format, + _In_ size_t maxsize, + _In_ size_t bitSize, + _In_reads_bytes_(bitSize) const uint8_t* bitData, + _Out_ size_t& twidth, + _Out_ size_t& theight, + _Out_ size_t& tdepth, + _Out_ size_t& skipMip, + _Out_writes_(mipCount*arraySize) D3D11_SUBRESOURCE_DATA* initData ) +{ + if ( !bitData || !initData ) + { + return E_POINTER; + } + + skipMip = 0; + twidth = 0; + theight = 0; + tdepth = 0; + + size_t NumBytes = 0; + size_t RowBytes = 0; + const uint8_t* pSrcBits = bitData; + const uint8_t* pEndBits = bitData + bitSize; + + size_t index = 0; + for( size_t j = 0; j < arraySize; j++ ) + { + size_t w = width; + size_t h = height; + size_t d = depth; + for( size_t i = 0; i < mipCount; i++ ) + { + GetSurfaceInfo( w, + h, + format, + &NumBytes, + &RowBytes, + nullptr + ); + + if ( (mipCount <= 1) || !maxsize || (w <= maxsize && h <= maxsize && d <= maxsize) ) + { + if ( !twidth ) + { + twidth = w; + theight = h; + tdepth = d; + } + + assert(index < mipCount * arraySize); + _Analysis_assume_(index < mipCount * arraySize); + initData[index].pSysMem = ( const void* )pSrcBits; + initData[index].SysMemPitch = static_cast( RowBytes ); + initData[index].SysMemSlicePitch = static_cast( NumBytes ); + ++index; + } + else if ( !j ) + { + // Count number of skipped mipmaps (first item only) + ++skipMip; + } + + if (pSrcBits + (NumBytes*d) > pEndBits) + { + return HRESULT_FROM_WIN32( ERROR_HANDLE_EOF ); + } + + pSrcBits += NumBytes * d; + + w = w >> 1; + h = h >> 1; + d = d >> 1; + if (w == 0) + { + w = 1; + } + if (h == 0) + { + h = 1; + } + if (d == 0) + { + d = 1; + } + } + } + + return (index > 0) ? S_OK : E_FAIL; +} + + +//-------------------------------------------------------------------------------------- +static HRESULT CreateD3DResources( _In_ ID3D11Device* d3dDevice, + _In_ uint32_t resDim, + _In_ size_t width, + _In_ size_t height, + _In_ size_t depth, + _In_ size_t mipCount, + _In_ size_t arraySize, + _In_ DXGI_FORMAT format, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _In_ bool isCubeMap, + _In_reads_opt_(mipCount*arraySize) D3D11_SUBRESOURCE_DATA* initData, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView ) +{ + if ( !d3dDevice ) + return E_POINTER; + + HRESULT hr = E_FAIL; + + if ( forceSRGB ) + { + format = MakeSRGB( format ); + } + + switch ( resDim ) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + { + D3D11_TEXTURE1D_DESC desc; + desc.Width = static_cast( width ); + desc.MipLevels = static_cast( mipCount ); + desc.ArraySize = static_cast( arraySize ); + desc.Format = format; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + + ID3D11Texture1D* tex = nullptr; + hr = d3dDevice->CreateTexture1D( &desc, + initData, + &tex + ); + if (SUCCEEDED( hr ) && tex != 0) + { + if (textureView != 0) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc; + memset( &SRVDesc, 0, sizeof( SRVDesc ) ); + SRVDesc.Format = format; + + if (arraySize > 1) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1DARRAY; + SRVDesc.Texture1DArray.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + SRVDesc.Texture1DArray.ArraySize = static_cast( arraySize ); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1D; + SRVDesc.Texture1D.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + } + + hr = d3dDevice->CreateShaderResourceView( tex, + &SRVDesc, + textureView + ); + if ( FAILED(hr) ) + { + tex->Release(); + return hr; + } + } + + if (texture != 0) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + { + D3D11_TEXTURE2D_DESC desc; + desc.Width = static_cast( width ); + desc.Height = static_cast( height ); + desc.MipLevels = static_cast( mipCount ); + desc.ArraySize = static_cast( arraySize ); + desc.Format = format; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + if ( isCubeMap ) + { + desc.MiscFlags = miscFlags | D3D11_RESOURCE_MISC_TEXTURECUBE; + } + else + { + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + } + + ID3D11Texture2D* tex = nullptr; + hr = d3dDevice->CreateTexture2D( &desc, + initData, + &tex + ); + if (SUCCEEDED( hr ) && tex != 0) + { + if (textureView != 0) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc; + memset( &SRVDesc, 0, sizeof( SRVDesc ) ); + SRVDesc.Format = format; + + if ( isCubeMap ) + { + if (arraySize > 6) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBEARRAY; + SRVDesc.TextureCubeArray.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + + // Earlier we set arraySize to (NumCubes * 6) + SRVDesc.TextureCubeArray.NumCubes = static_cast( arraySize / 6 ); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE; + SRVDesc.TextureCube.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + } + } + else if (arraySize > 1) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY; + SRVDesc.Texture2DArray.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + SRVDesc.Texture2DArray.ArraySize = static_cast( arraySize ); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + SRVDesc.Texture2D.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + } + + if (SRVDesc.Format == DXGI_FORMAT_R32_TYPELESS) + { + SRVDesc.Format = DXGI_FORMAT_R32_FLOAT; + } + + hr = d3dDevice->CreateShaderResourceView( tex, + &SRVDesc, + textureView + ); + if ( FAILED(hr) ) + { + tex->Release(); + return hr; + } + } + + if (texture != 0) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + { + D3D11_TEXTURE3D_DESC desc; + desc.Width = static_cast( width ); + desc.Height = static_cast( height ); + desc.Depth = static_cast( depth ); + desc.MipLevels = static_cast( mipCount ); + desc.Format = format; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + desc.MiscFlags = miscFlags & ~D3D11_RESOURCE_MISC_TEXTURECUBE; + + ID3D11Texture3D* tex = nullptr; + hr = d3dDevice->CreateTexture3D( &desc, + initData, + &tex + ); + if (SUCCEEDED( hr ) && tex != 0) + { + if (textureView != 0) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc; + memset( &SRVDesc, 0, sizeof( SRVDesc ) ); + SRVDesc.Format = format; + + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE3D; + SRVDesc.Texture3D.MipLevels = (!mipCount) ? -1 : desc.MipLevels; + + hr = d3dDevice->CreateShaderResourceView( tex, + &SRVDesc, + textureView + ); + if ( FAILED(hr) ) + { + tex->Release(); + return hr; + } + } + + if (texture != 0) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +static HRESULT CreateTextureFromDDS( _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_ const DDS_HEADER* header, + _In_reads_bytes_(bitSize) const uint8_t* bitData, + _In_ size_t bitSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView ) +{ + HRESULT hr = S_OK; + + UINT width = header->width; + UINT height = header->height; + UINT depth = header->depth; + + uint32_t resDim = D3D11_RESOURCE_DIMENSION_UNKNOWN; + UINT arraySize = 1; + DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN; + bool isCubeMap = false; + + size_t mipCount = header->mipMapCount; + if (0 == mipCount) + { + mipCount = 1; + } + + if ((header->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC( 'D', 'X', '1', '0' ) == header->ddspf.fourCC )) + { + auto d3d10ext = reinterpret_cast( (const char*)header + sizeof(DDS_HEADER) ); + + arraySize = d3d10ext->arraySize; + if (arraySize == 0) + { + return HRESULT_FROM_WIN32( ERROR_INVALID_DATA ); + } + + switch( d3d10ext->dxgiFormat ) + { + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + + default: + if ( BitsPerPixel( d3d10ext->dxgiFormat ) == 0 ) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + } + + format = d3d10ext->dxgiFormat; + + switch ( d3d10ext->resourceDimension ) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + // D3DX writes 1D textures with a fixed Height of 1 + if ((header->flags & DDS_HEIGHT) && height != 1) + { + return HRESULT_FROM_WIN32( ERROR_INVALID_DATA ); + } + height = depth = 1; + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + if (d3d10ext->miscFlag & D3D11_RESOURCE_MISC_TEXTURECUBE) + { + arraySize *= 6; + isCubeMap = true; + } + depth = 1; + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + if (!(header->flags & DDS_HEADER_FLAGS_VOLUME)) + { + return HRESULT_FROM_WIN32( ERROR_INVALID_DATA ); + } + + if (arraySize > 1) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + break; + + default: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + + resDim = d3d10ext->resourceDimension; + } + else + { + format = GetDXGIFormat( header->ddspf ); + + if (format == DXGI_FORMAT_UNKNOWN) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + + if (header->flags & DDS_HEADER_FLAGS_VOLUME) + { + resDim = D3D11_RESOURCE_DIMENSION_TEXTURE3D; + } + else + { + if (header->caps2 & DDS_CUBEMAP) + { + // We require all six faces to be defined + if ((header->caps2 & DDS_CUBEMAP_ALLFACES ) != DDS_CUBEMAP_ALLFACES) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + + arraySize = 6; + isCubeMap = true; + } + + depth = 1; + resDim = D3D11_RESOURCE_DIMENSION_TEXTURE2D; + + // Note there's no way for a legacy Direct3D 9 DDS to express a '1D' texture + } + + assert( BitsPerPixel( format ) != 0 ); + } + + // Bound sizes (for security purposes we don't trust DDS file metadata larger than the D3D 11.x hardware requirements) + if (mipCount > D3D11_REQ_MIP_LEVELS) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + + switch ( resDim ) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + if ((arraySize > D3D11_REQ_TEXTURE1D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURE1D_U_DIMENSION) ) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + if ( isCubeMap ) + { + // This is the right bound because we set arraySize to (NumCubes*6) above + if ((arraySize > D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURECUBE_DIMENSION) || + (height > D3D11_REQ_TEXTURECUBE_DIMENSION)) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + } + else if ((arraySize > D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION) || + (height > D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION)) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + if ((arraySize > 1) || + (width > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) || + (height > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) || + (depth > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) ) + { + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + break; + + default: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + + bool autogen = false; + if ( mipCount == 1 && d3dContext != 0 && textureView != 0 ) // Must have context and shader-view to auto generate mipmaps + { + // See if format is supported for auto-gen mipmaps (varies by feature level) + UINT fmtSupport = 0; + hr = d3dDevice->CheckFormatSupport( format, &fmtSupport ); + if ( SUCCEEDED(hr) && ( fmtSupport & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN ) ) + { + // 10level9 feature levels do not support auto-gen mipgen for volume textures + if ( ( resDim != D3D11_RESOURCE_DIMENSION_TEXTURE3D ) + || ( d3dDevice->GetFeatureLevel() >= D3D_FEATURE_LEVEL_10_0 ) ) + { + autogen = true; + } + } + } + + if ( autogen ) + { + // Create texture with auto-generated mipmaps + ID3D11Resource* tex = nullptr; + hr = CreateD3DResources( d3dDevice, resDim, width, height, depth, 0, arraySize, + format, usage, + bindFlags | D3D11_BIND_RENDER_TARGET, + cpuAccessFlags, + miscFlags | D3D11_RESOURCE_MISC_GENERATE_MIPS, forceSRGB, + isCubeMap, nullptr, &tex, textureView ); + if ( SUCCEEDED(hr) ) + { + size_t numBytes = 0; + size_t rowBytes = 0; + GetSurfaceInfo( width, height, format, &numBytes, &rowBytes, nullptr ); + + if ( numBytes > bitSize ) + { + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return HRESULT_FROM_WIN32( ERROR_HANDLE_EOF ); + } + + D3D11_SHADER_RESOURCE_VIEW_DESC desc; + (*textureView)->GetDesc( &desc ); + + UINT mipLevels = 1; + + switch( desc.ViewDimension ) + { + case D3D_SRV_DIMENSION_TEXTURE1D: mipLevels = desc.Texture1D.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE1DARRAY: mipLevels = desc.Texture1DArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE2D: mipLevels = desc.Texture2D.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE2DARRAY: mipLevels = desc.Texture2DArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURECUBE: mipLevels = desc.TextureCube.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURECUBEARRAY:mipLevels = desc.TextureCubeArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE3D: mipLevels = desc.Texture3D.MipLevels; break; + default: + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return E_UNEXPECTED; + } + + if ( arraySize > 1 ) + { + const uint8_t* pSrcBits = bitData; + const uint8_t* pEndBits = bitData + bitSize; + for( UINT item = 0; item < arraySize; ++item ) + { + if ( (pSrcBits + numBytes) > pEndBits ) + { + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return HRESULT_FROM_WIN32( ERROR_HANDLE_EOF ); + } + + UINT res = D3D11CalcSubresource( 0, item, mipLevels ); + d3dContext->UpdateSubresource( tex, res, nullptr, pSrcBits, static_cast(rowBytes), static_cast(numBytes) ); + pSrcBits += numBytes; + } + } + else + { + d3dContext->UpdateSubresource( tex, 0, nullptr, bitData, static_cast(rowBytes), static_cast(numBytes) ); + } + + d3dContext->GenerateMips( *textureView ); + + if ( texture ) + { + *texture = tex; + } + else + { + tex->Release(); + } + } + } + else + { + // Create the texture + std::unique_ptr initData( new (std::nothrow) D3D11_SUBRESOURCE_DATA[ mipCount * arraySize ] ); + if ( !initData ) + { + return E_OUTOFMEMORY; + } + + size_t skipMip = 0; + size_t twidth = 0; + size_t theight = 0; + size_t tdepth = 0; + hr = FillInitData( width, height, depth, mipCount, arraySize, format, maxsize, bitSize, bitData, + twidth, theight, tdepth, skipMip, initData.get() ); + + if ( SUCCEEDED(hr) ) + { + hr = CreateD3DResources( d3dDevice, resDim, twidth, theight, tdepth, mipCount - skipMip, arraySize, + format, usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + isCubeMap, initData.get(), texture, textureView ); + + if ( FAILED(hr) && !maxsize && (mipCount > 1) ) + { + // Retry with a maxsize determined by feature level + switch( d3dDevice->GetFeatureLevel() ) + { + case D3D_FEATURE_LEVEL_9_1: + case D3D_FEATURE_LEVEL_9_2: + if ( isCubeMap ) + { + maxsize = 512 /*D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION*/; + } + else + { + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 256 /*D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 2048 /*D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + } + break; + + case D3D_FEATURE_LEVEL_9_3: + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 256 /*D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 4096 /*D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + default: // D3D_FEATURE_LEVEL_10_0 & D3D_FEATURE_LEVEL_10_1 + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 2048 /*D3D10_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 8192 /*D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + } + + hr = FillInitData( width, height, depth, mipCount, arraySize, format, maxsize, bitSize, bitData, + twidth, theight, tdepth, skipMip, initData.get() ); + if ( SUCCEEDED(hr) ) + { + hr = CreateD3DResources( d3dDevice, resDim, twidth, theight, tdepth, mipCount - skipMip, arraySize, + format, usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + isCubeMap, initData.get(), texture, textureView ); + } + } + } + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +static DDS_ALPHA_MODE GetAlphaMode( _In_ const DDS_HEADER* header ) +{ + if ( header->ddspf.flags & DDS_FOURCC ) + { + if ( MAKEFOURCC( 'D', 'X', '1', '0' ) == header->ddspf.fourCC ) + { + auto d3d10ext = reinterpret_cast( (const char*)header + sizeof(DDS_HEADER) ); + auto mode = static_cast( d3d10ext->miscFlags2 & DDS_MISC_FLAGS2_ALPHA_MODE_MASK ); + switch( mode ) + { + case DDS_ALPHA_MODE_STRAIGHT: + case DDS_ALPHA_MODE_PREMULTIPLIED: + case DDS_ALPHA_MODE_OPAQUE: + case DDS_ALPHA_MODE_CUSTOM: + return mode; + } + } + else if ( ( MAKEFOURCC( 'D', 'X', 'T', '2' ) == header->ddspf.fourCC ) + || ( MAKEFOURCC( 'D', 'X', 'T', '4' ) == header->ddspf.fourCC ) ) + { + return DDS_ALPHA_MODE_PREMULTIPLIED; + } + } + + return DDS_ALPHA_MODE_UNKNOWN; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemory( ID3D11Device* d3dDevice, + const uint8_t* ddsData, + size_t ddsDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode ) +{ + return CreateDDSTextureFromMemoryEx( d3dDevice, nullptr, ddsData, ddsDataSize, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + texture, textureView, alphaMode ); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemory( ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* ddsData, + size_t ddsDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode ) +{ + return CreateDDSTextureFromMemoryEx( d3dDevice, d3dContext, ddsData, ddsDataSize, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + texture, textureView, alphaMode ); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemoryEx( ID3D11Device* d3dDevice, + const uint8_t* ddsData, + size_t ddsDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode ) +{ + return CreateDDSTextureFromMemoryEx( d3dDevice, nullptr, ddsData, ddsDataSize, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + texture, textureView, alphaMode ); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemoryEx( ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* ddsData, + size_t ddsDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode ) +{ + if ( texture ) + { + *texture = nullptr; + } + if ( textureView ) + { + *textureView = nullptr; + } + if ( alphaMode ) + { + *alphaMode = DDS_ALPHA_MODE_UNKNOWN; + } + + if (!d3dDevice || !ddsData || (!texture && !textureView)) + { + return E_INVALIDARG; + } + + // Validate DDS file in memory + if (ddsDataSize < (sizeof(uint32_t) + sizeof(DDS_HEADER))) + { + return E_FAIL; + } + + uint32_t dwMagicNumber = *( const uint32_t* )( ddsData ); + if (dwMagicNumber != DDS_MAGIC) + { + return E_FAIL; + } + + auto header = reinterpret_cast( ddsData + sizeof( uint32_t ) ); + + // Verify header to validate DDS file + if (header->size != sizeof(DDS_HEADER) || + header->ddspf.size != sizeof(DDS_PIXELFORMAT)) + { + return E_FAIL; + } + + // Check for DX10 extension + bool bDXT10Header = false; + if ((header->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC( 'D', 'X', '1', '0' ) == header->ddspf.fourCC) ) + { + // Must be long enough for both headers and magic value + if (ddsDataSize < (sizeof(DDS_HEADER) + sizeof(uint32_t) + sizeof(DDS_HEADER_DXT10))) + { + return E_FAIL; + } + + bDXT10Header = true; + } + + ptrdiff_t offset = sizeof( uint32_t ) + + sizeof( DDS_HEADER ) + + (bDXT10Header ? sizeof( DDS_HEADER_DXT10 ) : 0); + + HRESULT hr = CreateTextureFromDDS( d3dDevice, d3dContext, header, + ddsData + offset, ddsDataSize - offset, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + texture, textureView ); + if ( SUCCEEDED(hr) ) + { + if (texture != 0 && *texture != 0) + { + SetDebugObjectName(*texture, "DDSTextureLoader"); + } + + if (textureView != 0 && *textureView != 0) + { + SetDebugObjectName(*textureView, "DDSTextureLoader"); + } + + if ( alphaMode ) + *alphaMode = GetAlphaMode( header ); + } + + return hr; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFile( ID3D11Device* d3dDevice, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode ) +{ + return CreateDDSTextureFromFileEx( d3dDevice, nullptr, fileName, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + texture, textureView, alphaMode ); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFile( ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode ) +{ + return CreateDDSTextureFromFileEx( d3dDevice, d3dContext, fileName, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, false, + texture, textureView, alphaMode ); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFileEx( ID3D11Device* d3dDevice, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode ) +{ + return CreateDDSTextureFromFileEx( d3dDevice, nullptr, fileName, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + texture, textureView, alphaMode ); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFileEx( ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode ) +{ + if ( texture ) + { + *texture = nullptr; + } + if ( textureView ) + { + *textureView = nullptr; + } + if ( alphaMode ) + { + *alphaMode = DDS_ALPHA_MODE_UNKNOWN; + } + + if (!d3dDevice || !fileName || (!texture && !textureView)) + { + return E_INVALIDARG; + } + + DDS_HEADER* header = nullptr; + uint8_t* bitData = nullptr; + size_t bitSize = 0; + + std::unique_ptr ddsData; + HRESULT hr = LoadTextureDataFromFile( fileName, + ddsData, + &header, + &bitData, + &bitSize + ); + if (FAILED(hr)) + { + return hr; + } + + hr = CreateTextureFromDDS( d3dDevice, d3dContext, header, + bitData, bitSize, maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, forceSRGB, + texture, textureView ); + + if ( SUCCEEDED(hr) ) + { +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + if (texture != 0 || textureView != 0) + { + CHAR strFileA[MAX_PATH]; + int result = WideCharToMultiByte( CP_ACP, + WC_NO_BEST_FIT_CHARS, + fileName, + -1, + strFileA, + MAX_PATH, + nullptr, + FALSE + ); + if ( result > 0 ) + { + const CHAR* pstrName = strrchr( strFileA, '\\' ); + if (!pstrName) + { + pstrName = strFileA; + } + else + { + pstrName++; + } + + if (texture != 0 && *texture != 0) + { + (*texture)->SetPrivateData( WKPDID_D3DDebugObjectName, + static_cast( strnlen_s(pstrName, MAX_PATH) ), + pstrName + ); + } + + if (textureView != 0 && *textureView != 0 ) + { + (*textureView)->SetPrivateData( WKPDID_D3DDebugObjectName, + static_cast( strnlen_s(pstrName, MAX_PATH) ), + pstrName + ); + } + } + } +#endif + + if ( alphaMode ) + *alphaMode = GetAlphaMode( header ); + } + + return hr; +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/DDSTextureLoader.h b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/DDSTextureLoader.h new file mode 100644 index 0000000..260c161 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/DDSTextureLoader.h @@ -0,0 +1,150 @@ +//-------------------------------------------------------------------------------------- +// File: DDSTextureLoader.h +// +// Functions for loading a DDS texture and creating a Direct3D 11 runtime resource for it +// +// Note these functions are useful as a light-weight runtime loader for DDS files. For +// a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#ifdef _MSC_VER +#pragma once +#endif + +#include + +#pragma warning(push) +#pragma warning(disable : 4005) +#include +#pragma warning(pop) + +#if defined(_MSC_VER) && (_MSC_VER<1610) && !defined(_In_reads_) +#define _In_reads_(exp) +#define _Out_writes_(exp) +#define _In_reads_bytes_(exp) +#define _In_reads_opt_(exp) +#define _Outptr_opt_ +#endif + +#ifndef _Use_decl_annotations_ +#define _Use_decl_annotations_ +#endif + +namespace DirectX +{ + enum DDS_ALPHA_MODE + { + DDS_ALPHA_MODE_UNKNOWN = 0, + DDS_ALPHA_MODE_STRAIGHT = 1, + DDS_ALPHA_MODE_PREMULTIPLIED = 2, + DDS_ALPHA_MODE_OPAQUE = 3, + DDS_ALPHA_MODE_CUSTOM = 4, + }; + + // Standard version + HRESULT CreateDDSTextureFromMemory( _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr + ); + + HRESULT CreateDDSTextureFromFile( _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr + ); + + // Standard version with optional auto-gen mipmap support + HRESULT CreateDDSTextureFromMemory( _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr + ); + + HRESULT CreateDDSTextureFromFile( _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr + ); + + // Extended version + HRESULT CreateDDSTextureFromMemoryEx( _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr + ); + + HRESULT CreateDDSTextureFromFileEx( _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr + ); + + // Extended version with optional auto-gen mipmap support + HRESULT CreateDDSTextureFromMemoryEx( _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr + ); + + HRESULT CreateDDSTextureFromFileEx( _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr + ); +} \ No newline at end of file diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/MIT.txt b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/MIT.txt new file mode 100644 index 0000000..a2336db --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/MIT.txt @@ -0,0 +1,21 @@ + The MIT License (MIT) + +Copyright (c) 2015 Microsoft Corp + +Permission is hereby granted, free of charge, to any person obtaining a copy of this +software and associated documentation files (the "Software"), to deal in the Software +without restriction, including without limitation the rights to use, copy, modify, +merge, publish, distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be included in all copies +or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, +INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A +PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF +CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE +OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ReadMe.txt b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ReadMe.txt new file mode 100644 index 0000000..af476bc --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ReadMe.txt @@ -0,0 +1,312 @@ +DIRECTX TEXTURE LIBRARY (DirectXTex) +------------------------------------ + +Copyright (c) Microsoft Corporation. All rights reserved. + +October 30, 2015 + +This package contains DirectXTex, a shared source library for reading and writing DDS +files, and performing various texture content processing operations including +resizing, format conversion, mip-map generation, block compression for Direct3D runtime +texture resources, and height-map to normal-map conversion. This library makes +use of the Windows Image Component (WIC) APIs. It also includes a simple .TGA reader and +writer since this image file format is commonly used for texture content processing pipelines, +but is not currently supported by a built-in WIC codec. + +The source is written for Visual Studio 2012, 2013, or 2015. It is recommended that +you make use of the Windows 8.1 SDK and Windows 7 Service Pack 1 or later. + +NOTE: DirectXTex is not supported on Windows phone 8.0 because WIC is not available on +that platform. It is available on Windows phone starting in version 8.1. + +DDSTextureLoader\ + This contains a streamlined version of the DirectX SDK sample DDSWithoutD3DX11 texture + loading code for a simple light-weight runtime DDS loader. This version only supports + Direct3D 11 and performs no runtime pixel data conversions (i.e. 24bpp legacy DDS files + always fail). This is ideal for runtime usage, and supports the full complement of + Direct3D 11 texture resources (1D, 2D, volume maps, cubemaps, mipmap levels, + texture arrays, BC formats, etc.). + +WICTextureLoader\ + This contains a Direct3D 11 2D texture loader that uses WIC to load a bitmap + (BMP, JPEG, PNG, HD Photo, or other WIC supported file container), resize if needed + based on the current feature level (or by explicit parameter), format convert to a + DXGI_FORMAT if required, and then create a 2D texture. Furthermore, if a Direct3D 11 + device context is provided and the current device supports it for the given pixel format, + it will auto-generate mipmaps. Note this does not support 1D textures, volume textures, + cubemaps, or texture arrays. DDSTextureLoader is recommended for fully "precooked" textures + for maximum performance and image quality, but this loader can be useful for creating + simple 2D texture from standard image files at runtime. + + Note: This function is not thread-safe if given a non-NULL device context for the auto-gen + mip-map support. + +DirectXTex\ + This contains the DirectXTex library. This includes a full-featured DDS reader and writer + including legacy format conversions, a TGA reader and writer, a WIC-based bitmap reader and + writer (BMP, JPEG, PNG, TIFF, and HD Photo), and various texture processing functions. This + is intended primarily for tool usage. + + Note that the majority of the header files here are intended for internal implementation + of the library only (BC.h, DDS.h, DirectXTexP.h, and scoped.h). Only DirectXTex.h is + meant as a 'public' header for the library. + +Texconv\ + This DirectXTex sample is an implementation of the "texconv" command-line texture utility + from the DirectX SDK utilizing DirectXTex rather than D3DX. + + It supports the same arguments as the Texture Conversion Tool Extended (texconvex.exe) DirectX + SDK utility. See . The primary differences + are the -10 and -11 arguments are not applicable; the filter names (POINT, LINEAR, CUBIC, + FANT or BOX, TRIANGLE, *_DITHER, *_DITHER_DIFFUSION); and support for the .TGA file format. + This also includes support for JPEG XR/HD Photo bitmap formats (see + ) + +Texassemble\ + This DirectXTex sample is a command-line utility for creating cubemaps, volume maps, or + texture arrays from a set of individual input image files. + +DDSView\ + This DirectXTex sample is a simple Direct3D 11-based viewer for DDS files. For array textures + or volume maps, the "<" and ">" keyboard keys will show different images contained in the DDS. + The "1" through "0" keys can also be used to jump to a specific image index. + +All content and source code for this package are subject to the terms of the MIT License. +. + +Documentation is available at . + +For the latest version of DirectXTex, bug reports, etc. please visit the project site. + +http://go.microsoft.com/fwlink/?LinkId=248926 + + +------------------------------------ +RELEASE NOTES + +* The alpha mode specification for DDS files was updated between the March 2013 and April 2013 releases. Any + DDS files created using the DDS_FLAGS_FORCE_DX10_EXT_MISC2 flag or the texconv -dx10 switch using the + March 2013 release should be refreshed. + +* Due to the underlying Windows BMP WIC codec, alpha channels are not supported for 16bpp or 32bpp BMP pixel format files. The Windows 8.x + version of the Windows BMP WIC codec does support 32bpp pixel formats with alpha when using the BITMAPV5HEADER file header. Note the updated + WIC is available on Windows 7 SP1 with KB 2670838 installed. + +* While DXGI 1.0 and DXGI 1.1 include 5:6:5 (DXGI_FORMAT_B5G6R5_UNORM) and 5:5:5:1 (DXGI_FORMAT_B5G5R5A1_UNORM) + pixel format enumerations, the DirectX 10.x and 11.0 Runtimes do not support these formats for use with Direct3D. The DirectX 11.1 runtime, + DXGI 1.2, and the WDDM 1.2 driver model fully support 16bpp formats (5:6:5, 5:5:5:1, and 4:4:4:4). + +* WICTextureLoader cannot load .TGA files unless the system has a 3rd party WIC codec installed. You must use the DirectXTex + library for TGA file format support without relying on an add-on WIC codec. + +* Loading of 96bpp floating-point TIFF files results in a corrupted image prior to Windows 8. This fix is available on Windows 7 SP1 with + KB 2670838 installed. + + +------------------------------------ +RELEASE HISTORY + +October 30, 2015 + DDS support for legacy bumpmap formats (V8U8, Q8W8V8U8, V16U16) + Fix for buffer overread in BC CPU compressor + Minor code cleanup + +August 18, 2015 + Added GetWICFactory and SetWICFactory + Updates for new DXGI 1.3 types + Xbox One platform updates + +July 29, 2015 + Fixed rounding problem with 32-bit RGBA/BGRA format conversions + texconv: use CPU parallel compression for BC1-BC5 (-singleproc disables) + Updated for VS 2015 and Windows 10 SDK RTM + Retired VS 2010 and Windows 8.0 Store projects + +June 18, 2015 + New BC_FLAGS_USE_3SUBSETS option for BC7 compressors; now defaults to skipping 3 subset blocks + Fixed bug with MakeTypeless and A8_UNORM + Fixed file length validation problem in LoadDDSFromFile + +March 27, 2015 + Added projects for Windows apps Technical Preview + Fixed bug with WIC-based mipmap generation for non-WIC supported formats + Fixed bug with WIC multiframe loader when resizing required + texconv: Added -nmap/-nmapamp for generating normal maps from height maps + texconv/texassemble: Updated to load multiframe WIC files (tiff, gif) + Minor code cleanup + +November 24, 2014 + Updates for Visual Studio 2015 Technical Preview + Minor code cleanup + +September 22, 2014 + Format conversion improvements and bug fixes (depth/stencil, alpha-only, float16, RGB -> 1 channel) + Fixed issue when BC decompressing non-standard compressed rowPitch images + Explicit calling-convention annotation for all 'public' functions + Code cleanup + Xbox One platform updates + +July 15, 2014 + texconv command-line tool fixes + Fixed problem with 'wide' images with CPU Compress + Updates to Xbox One platform support + +April 3, 2014 + Windows phone 8.1 platform support + +February 24, 2014 + Direct3D 11 video and Xbox One extended format support + New APIs: IsPlanar, IsPalettized, IsDepthStencil, ConvertToSinglePlane + Added 'alphaWeight' parameter to GPU Compress [breaking change] + texconv '-aw' switch to control the alpha weighting for the BC7 GPU compressor + Fixed bug with ordered dithering in non-WIC conversion codepaths + Fixed SaveToDDS* functions when using arbitrary row pitch values + +January 24, 2014 + Added sRGB flags for Compress (TEX_COMPRESS_SRGB*) + Added 'compress' flag parameter to GPU versions of Compress [breaking change] + Minor fix for potential rounding problem in GPU Compress + Code cleanup (removed DXGI_1_2_FORMATS control define; ScopedObject typedef removed) + Dropped VS 2010 support without the Windows 8.1 SDK (removed USE_XNAMATH control define) + +December 24, 2013 + texconv updated with -fl and -pow2 command-line switches + Fixed bug in Resize when doing custom filtering which occurred when exactly doubling the image size + Added move operators to ScratchImage and Blob classes + Xbox One platform support + +October 21, 2013 + Updated for Visual Studio 2013 and Windows 8.1 SDK RTM + PremultiplyAlpha updated with new 'flags' parameter and to use sRGB correct blending + Fixed colorspace conversion issue with DirectCompute compressor when compressing for BC7 SRGB + +August 13, 2013 + DirectCompute 4.0 BC6H/BC7 compressor integration + texconv utility uses DirectCompute compression by default for BC6H/BC7, -nogpu disables use of DirectCompute + +August 1, 2013 + Support for BC compression/decompression of non-power-of-2 mipmapped textures + Fixes for BC6H / BC7 codecs to better match published standard + Fix for BC4 / BC5 codecs when compressing RGB images + Minor fix for the BC1-3 codec + New optional flags for ComputeMSE to compare UNORM vs. SNORM images + New WIC loading flag added to control use of WIC metadata to return sRGB vs. non-sRGB formats + Code cleanup and /analyze fixes + Project file cleanup + Texconv utility uses parallel BC compression by default for BC6H/BC7, -singleproc disables multithreaded behavior + +July 1, 2013 + VS 2013 Preview projects added + SaveToWIC functions updated with new optional setCustomProps parameter + +June 15, 2013 + Custom filtering implementation for Resize & GenerateMipMaps(3D) - Point, Box, Linear, Cubic, and Triangle + TEX_FILTER_TRIANGLE finite low-pass triangle filter + TEX_FILTER_WRAP, TEX_FILTER_MIRROR texture semantics for custom filtering + TEX_FILTER_BOX alias for TEX_FILTER_FANT WIC + Ordered and error diffusion dithering for non-WIC conversion + sRGB gamma correct custom filtering and conversion + DDS_FLAGS_EXPAND_LUMINANCE - Reader conversion option for L8, L16, and A8L8 legacy DDS files + Added use of WIC metadata for sRGB pixel formats + Added BitsPerColor utility function + Fixed Convert threshold parameter usage + Non-power-of-2 volume map support, fixed bug with non-square volume maps + Texconv utility update with -xlum, -wrap, and -mirror options; reworked -if options for improved dithering + Texassemble utility for creating cubemaps, volume maps, and texture arrays + DDSTextureLoader and WICTextureLoader sync'd with DirectXTK versions + +April 16, 2013 + Updated alpha-mode metadata details in .DDS files + Added new control flags for Convert + Added new optional flags for ComputeMSE + Fixed conversion handling for sRGB formats + Fixed internal routines for handling R10G10B10_XR_BIAS_A2_UNORM, R9G9B9E5_SHAREDEXP, and FORMAT_R1_UNORM + Fixed WIC I/O for GUID_WICPixelFormat32bppRGBE pixel format files (HD Photo) + Fixed non-square image handling in GenerateMipMaps3D + Fixed some error handling in the DDS load code + +March 22, 2013 + Supports reading and writing alpha-mode (straight, premultiplied, etc.) metadata in .DDS files + Added build option to use WICCreateImagingFactory_Proxy instead of CoCreateInstance to obtain WIC factory + +January 29, 2013 + Added PremultiplyAlpha to DirectXTex; -pmalpha switch for texconv command-line tool + Fixed problem with forceSRGB implementation for Ex versions of CreateTexture, CreateShaderResourceView, DDSTextureLoader and WICTextureLoader + +December 11, 2012 + Ex versions of CreateTexture, CreateShaderResourceView, DDSTextureLoader and WICTextureLoader + Fixed BC2 and BC3 decompression issue for unusual color encoding case + Converted annotation to SAL2 for improved VS 2012 /analyze experience + Updated DirectXTex, DDSView, and Texconv with VS 2010 + Windows 8.0 SDK project using official 'property sheets' + +November 15, 2012 + Added support for WIC2 when available on Windows 8 and Windows 7 with KB 2670838 + Added optional targetGUID parameter to SaveWIC* APIs to influence final container pixel format choice + Fixed bug in SaveDDS* which was generating invalid DDS files for 1D dimension textures + Improved robustness of CaptureTexture when resolving MSAA source textures + Sync'd DDSTextureLoader, ScreenGrab, and WICTextureLoader standalone versions with latest DirectXTK release + +September 28, 2012 + Added ScreenGrab module for creating runtime screenshots + Renamed project files for better naming consistency + New Typeless utilities for DirectXTex + Some minor code cleanup for DirectXTex's WIC writer function + Bug fixes and new -tu/-tf options for texconv + +June 22, 2012 + Moved to using XNA Math 2.05 instead of XNA Math 2.04 for USE_XNAMATH builds + Fixed BGR vs. RGB color channel swizzle problem with 24bpp legacy .DDS files in DirectXTex + Update to DirectXTex WIC and WICTextureLoader for additional 96bpp float format handling on Windows 8 + +May 31, 2012 + Minor fix for DDSTextureLoader's retry fallback that can happen with 10level9 feature levels + Switched to use "_DEBUG" instead of "DEBUG" and cleaned up debug warnings + added Metro style application project files for DirectXTex + +April 20, 2012 + DirectTex's WIC-based writer opts-in for the Windows 8 BMP encoder option for writing 32 bpp RGBA files with the BITMAPV5HEADER + +March 30, 2012 + WICTextureLoader updated with Windows 8 WIC pixel formats + DirectXTex updated with limited non-power-of-2 texture support and TEX_FILTER_SEPARATE_ALPHA option + Texconv updated with '-sepalpha' command-line option + Added USE_XNAMATH control define to build DirectXTex using either XNAMath or DirectXMath + Added VS 2012 project files (which use DirectXMath instead of XNAMath and define DXGI_1_2_FORMATS) + +March 15, 2012 + Fix for resource leak in CreateShaderResourceView() Direct3D 11 helper function in DirectXTex + +March 5, 2012 + Fix for too much temp memory allocated by WICTextureLoader; cleaned up legacy 'min/max' macro usage in DirectXTex + +February 21, 2012 + WICTextureLoader updated to handle systems and device drivers without BGRA or 16bpp format support + +February 20, 2012 + Some code cleanup for DirectXTex and DDSTextureLoader + Fixed bug in 10:10:10:2 format fixup in the LoadDDSFromMemory function + Fixed bugs in "non-zero alpha" special-case handling in LoadTGAFromFile + Fixed bug in _SwizzleScanline when copying alpha channel for BGRA<->RGBA swizzling + +February 11, 2012 + Update of DDSTextureLoader to also build in Metro style apps; added WICTextureLoader + Added CMYK WIC pixel formats to the DirectXTex conversion table + +January 30, 2012 + Minor code-cleanup for DirectXTex to enable use of PCH through 'directxtexp.h' header + +January 24, 2011 + Some code-cleanup for DirectXTex + Added DXGI 1.2 implementation for DDSTextureLoader and DirectXTex guarded with DXGI_1_2_FORMATS compiliation define + +December 16, 2011 + Fixed x64 compilation warnings in DDSTextureLoader + +November 30, 2011 + Fixed some of the constants used in IsSupportedTexture(), + added ability to strip off top levels of mips in DDSTextureLoader, + changed DirectXTex to use CoCreateInstance rather than LoadLibrary to obtain the WIC factory, + a few minor /analyze related annotations for DirectXTex + +October 27, 2011 + Original release \ No newline at end of file diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ScreenGrab.cpp b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ScreenGrab.cpp new file mode 100644 index 0000000..b4722ac --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ScreenGrab.cpp @@ -0,0 +1,1163 @@ +//-------------------------------------------------------------------------------------- +// File: ScreenGrab.cpp +// +// Function for capturing a 2D texture and saving it to a file (aka a 'screenshot' +// when used on a Direct3D 11 Render Target). +// +// Note these functions are useful as a light-weight runtime screen grabber. For +// full-featured texture capture, DDS writer, and texture processing pipeline, +// see the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +// Does not capture 1D textures or 3D textures (volume maps) + +// Does not capture mipmap chains, only the top-most texture level is saved + +// For 2D array textures and cubemaps, it captures only the first image in the array + +#include +#include + +#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP) || (_WIN32_WINNT > _WIN32_WINNT_WIN8) + +// VS 2010's stdint.h conflicts with intsafe.h +#pragma warning(push) +#pragma warning(disable : 4005) +#include +#include +#pragma warning(pop) +#endif + +#include + +#include +#include + +#include "ScreenGrab.h" + +using Microsoft::WRL::ComPtr; + +//-------------------------------------------------------------------------------------- +// Macros +//-------------------------------------------------------------------------------------- +#ifndef MAKEFOURCC + #define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +//-------------------------------------------------------------------------------------- +// DDS file structure definitions +// +// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library +//-------------------------------------------------------------------------------------- +#pragma pack(push,1) + +#define DDS_MAGIC 0x20534444 // "DDS " + +struct DDS_PIXELFORMAT +{ + uint32_t size; + uint32_t flags; + uint32_t fourCC; + uint32_t RGBBitCount; + uint32_t RBitMask; + uint32_t GBitMask; + uint32_t BBitMask; + uint32_t ABitMask; +}; + +#define DDS_FOURCC 0x00000004 // DDPF_FOURCC +#define DDS_RGB 0x00000040 // DDPF_RGB +#define DDS_RGBA 0x00000041 // DDPF_RGB | DDPF_ALPHAPIXELS +#define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE +#define DDS_LUMINANCEA 0x00020001 // DDPF_LUMINANCE | DDPF_ALPHAPIXELS +#define DDS_ALPHA 0x00000002 // DDPF_ALPHA +#define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + +#define DDS_HEADER_FLAGS_TEXTURE 0x00001007 // DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT +#define DDS_HEADER_FLAGS_MIPMAP 0x00020000 // DDSD_MIPMAPCOUNT +#define DDS_HEADER_FLAGS_PITCH 0x00000008 // DDSD_PITCH +#define DDS_HEADER_FLAGS_LINEARSIZE 0x00080000 // DDSD_LINEARSIZE + +#define DDS_HEIGHT 0x00000002 // DDSD_HEIGHT +#define DDS_WIDTH 0x00000004 // DDSD_WIDTH + +#define DDS_SURFACE_FLAGS_TEXTURE 0x00001000 // DDSCAPS_TEXTURE + +typedef struct +{ + uint32_t size; + uint32_t flags; + uint32_t height; + uint32_t width; + uint32_t pitchOrLinearSize; + uint32_t depth; // only if DDS_HEADER_FLAGS_VOLUME is set in flags + uint32_t mipMapCount; + uint32_t reserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t caps; + uint32_t caps2; + uint32_t caps3; + uint32_t caps4; + uint32_t reserved2; +} DDS_HEADER; + +typedef struct +{ + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see D3D11_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t reserved; +} DDS_HEADER_DXT10; + +#pragma pack(pop) + +static const DDS_PIXELFORMAT DDSPF_DXT1 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','1'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_DXT3 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','3'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_DXT5 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','5'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_BC4_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','U'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_BC4_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','S'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_BC5_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','U'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_BC5_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','S'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_R8G8_B8G8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('R','G','B','G'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_G8R8_G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('G','R','G','B'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_YUY2 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('Y','U','Y','2'), 0, 0, 0, 0, 0 }; + +static const DDS_PIXELFORMAT DDSPF_A8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000 }; + +static const DDS_PIXELFORMAT DDSPF_X8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0x00000000 }; + +static const DDS_PIXELFORMAT DDSPF_A8B8G8R8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + +static const DDS_PIXELFORMAT DDSPF_G16R16 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x0000ffff, 0xffff0000, 0x00000000, 0x00000000 }; + +static const DDS_PIXELFORMAT DDSPF_R5G6B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 16, 0x0000f800, 0x000007e0, 0x0000001f, 0x00000000 }; + +static const DDS_PIXELFORMAT DDSPF_A1R5G5B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00007c00, 0x000003e0, 0x0000001f, 0x00008000 }; + +static const DDS_PIXELFORMAT DDSPF_A4R4G4B4 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x00000f00, 0x000000f0, 0x0000000f, 0x0000f000 }; + +static const DDS_PIXELFORMAT DDSPF_L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 8, 0xff, 0x00, 0x00, 0x00 }; + +static const DDS_PIXELFORMAT DDSPF_L16 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 16, 0xffff, 0x0000, 0x0000, 0x0000 }; + +static const DDS_PIXELFORMAT DDSPF_A8L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCEA, 0, 16, 0x00ff, 0x0000, 0x0000, 0xff00 }; + +static const DDS_PIXELFORMAT DDSPF_A8 = + { sizeof(DDS_PIXELFORMAT), DDS_ALPHA, 0, 8, 0x00, 0x00, 0x00, 0xff }; + +static const DDS_PIXELFORMAT DDSPF_V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 16, 0x00ff, 0xff00, 0x0000, 0x0000 }; + +static const DDS_PIXELFORMAT DDSPF_Q8W8V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + +static const DDS_PIXELFORMAT DDSPF_V16U16 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x0000ffff, 0xffff0000, 0x00000000, 0x00000000 }; + +// DXGI_FORMAT_R10G10B10A2_UNORM should be written using DX10 extension to avoid D3DX 10:10:10:2 reversal issue + +// This indicates the DDS_HEADER_DXT10 extension is present (the format is in dxgiFormat) +static const DDS_PIXELFORMAT DDSPF_DX10 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','1','0'), 0, 0, 0, 0, 0 }; + +//--------------------------------------------------------------------------------- +struct handle_closer { void operator()(HANDLE h) { if (h) CloseHandle(h); } }; + +typedef public std::unique_ptr ScopedHandle; + +inline HANDLE safe_handle( HANDLE h ) { return (h == INVALID_HANDLE_VALUE) ? 0 : h; } + + +//-------------------------------------------------------------------------------------- +// Return the BPP for a particular format +//-------------------------------------------------------------------------------------- +static size_t BitsPerPixel( _In_ DXGI_FORMAT fmt ) +{ + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return 8; + + default: + return 0; + } +} + + +//-------------------------------------------------------------------------------------- +// Determines if the format is block compressed +//-------------------------------------------------------------------------------------- +static bool IsCompressed( _In_ DXGI_FORMAT fmt ) +{ + switch ( fmt ) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return true; + + default: + return false; + } +} + + +//-------------------------------------------------------------------------------------- +// Get surface information for a particular format +//-------------------------------------------------------------------------------------- +static void GetSurfaceInfo( _In_ size_t width, + _In_ size_t height, + _In_ DXGI_FORMAT fmt, + _Out_opt_ size_t* outNumBytes, + _Out_opt_ size_t* outRowBytes, + _Out_opt_ size_t* outNumRows ) +{ + size_t numBytes = 0; + size_t rowBytes = 0; + size_t numRows = 0; + + bool bc = false; + bool packed = false; + bool planar = false; + size_t bpe = 0; + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + bc=true; + bpe = 8; + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc = true; + bpe = 16; + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + packed = true; + bpe = 4; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + packed = true; + bpe = 8; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + planar = true; + bpe = 2; + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + planar = true; + bpe = 4; + break; + } + + if (bc) + { + size_t numBlocksWide = 0; + if (width > 0) + { + numBlocksWide = std::max( 1, (width + 3) / 4 ); + } + size_t numBlocksHigh = 0; + if (height > 0) + { + numBlocksHigh = std::max( 1, (height + 3) / 4 ); + } + rowBytes = numBlocksWide * bpe; + numRows = numBlocksHigh; + numBytes = rowBytes * numBlocksHigh; + } + else if (packed) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numRows = height; + numBytes = rowBytes * height; + } + else if ( fmt == DXGI_FORMAT_NV11 ) + { + rowBytes = ( ( width + 3 ) >> 2 ) * 4; + numRows = height * 2; // Direct3D makes this simplifying assumption, although it is larger than the 4:1:1 data + numBytes = rowBytes * numRows; + } + else if (planar) + { + rowBytes = ( ( width + 1 ) >> 1 ) * bpe; + numBytes = ( rowBytes * height ) + ( ( rowBytes * height + 1 ) >> 1 ); + numRows = height + ( ( height + 1 ) >> 1 ); + } + else + { + size_t bpp = BitsPerPixel( fmt ); + rowBytes = ( width * bpp + 7 ) / 8; // round up to nearest byte + numRows = height; + numBytes = rowBytes * height; + } + + if (outNumBytes) + { + *outNumBytes = numBytes; + } + if (outRowBytes) + { + *outRowBytes = rowBytes; + } + if (outNumRows) + { + *outNumRows = numRows; + } +} + + +//-------------------------------------------------------------------------------------- +static DXGI_FORMAT EnsureNotTypeless( DXGI_FORMAT fmt ) +{ + // Assumes UNORM or FLOAT; doesn't use UINT or SINT + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: return DXGI_FORMAT_R32G32B32A32_FLOAT; + case DXGI_FORMAT_R32G32B32_TYPELESS: return DXGI_FORMAT_R32G32B32_FLOAT; + case DXGI_FORMAT_R16G16B16A16_TYPELESS: return DXGI_FORMAT_R16G16B16A16_UNORM; + case DXGI_FORMAT_R32G32_TYPELESS: return DXGI_FORMAT_R32G32_FLOAT; + case DXGI_FORMAT_R10G10B10A2_TYPELESS: return DXGI_FORMAT_R10G10B10A2_UNORM; + case DXGI_FORMAT_R8G8B8A8_TYPELESS: return DXGI_FORMAT_R8G8B8A8_UNORM; + case DXGI_FORMAT_R16G16_TYPELESS: return DXGI_FORMAT_R16G16_UNORM; + case DXGI_FORMAT_R32_TYPELESS: return DXGI_FORMAT_R32_FLOAT; + case DXGI_FORMAT_R8G8_TYPELESS: return DXGI_FORMAT_R8G8_UNORM; + case DXGI_FORMAT_R16_TYPELESS: return DXGI_FORMAT_R16_UNORM; + case DXGI_FORMAT_R8_TYPELESS: return DXGI_FORMAT_R8_UNORM; + case DXGI_FORMAT_BC1_TYPELESS: return DXGI_FORMAT_BC1_UNORM; + case DXGI_FORMAT_BC2_TYPELESS: return DXGI_FORMAT_BC2_UNORM; + case DXGI_FORMAT_BC3_TYPELESS: return DXGI_FORMAT_BC3_UNORM; + case DXGI_FORMAT_BC4_TYPELESS: return DXGI_FORMAT_BC4_UNORM; + case DXGI_FORMAT_BC5_TYPELESS: return DXGI_FORMAT_BC5_UNORM; + case DXGI_FORMAT_B8G8R8A8_TYPELESS: return DXGI_FORMAT_B8G8R8A8_UNORM; + case DXGI_FORMAT_B8G8R8X8_TYPELESS: return DXGI_FORMAT_B8G8R8X8_UNORM; + case DXGI_FORMAT_BC7_TYPELESS: return DXGI_FORMAT_BC7_UNORM; + default: return fmt; + } +} + + +//-------------------------------------------------------------------------------------- +static HRESULT CaptureTexture( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _Inout_ D3D11_TEXTURE2D_DESC& desc, + _Inout_ ComPtr& pStaging ) +{ + if ( !pContext || !pSource ) + return E_INVALIDARG; + + D3D11_RESOURCE_DIMENSION resType = D3D11_RESOURCE_DIMENSION_UNKNOWN; + pSource->GetType( &resType ); + + if ( resType != D3D11_RESOURCE_DIMENSION_TEXTURE2D ) + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + + ComPtr pTexture; + HRESULT hr = pSource->QueryInterface( __uuidof(ID3D11Texture2D), reinterpret_cast( pTexture.GetAddressOf() ) ); + if ( FAILED(hr) ) + return hr; + + assert( pTexture ); + + pTexture->GetDesc( &desc ); + + ComPtr d3dDevice; + pContext->GetDevice( d3dDevice.GetAddressOf() ); + + if ( desc.SampleDesc.Count > 1 ) + { + // MSAA content must be resolved before being copied to a staging texture + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + + ComPtr pTemp; + hr = d3dDevice->CreateTexture2D( &desc, 0, pTemp.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + assert( pTemp ); + + DXGI_FORMAT fmt = EnsureNotTypeless( desc.Format ); + + UINT support = 0; + hr = d3dDevice->CheckFormatSupport( fmt, &support ); + if ( FAILED(hr) ) + return hr; + + if ( !(support & D3D11_FORMAT_SUPPORT_MULTISAMPLE_RESOLVE) ) + return E_FAIL; + + for( UINT item = 0; item < desc.ArraySize; ++item ) + { + for( UINT level = 0; level < desc.MipLevels; ++level ) + { + UINT index = D3D11CalcSubresource( level, item, desc.MipLevels ); + pContext->ResolveSubresource( pTemp.Get(), index, pSource, index, fmt ); + } + } + + desc.BindFlags = 0; + desc.MiscFlags &= D3D11_RESOURCE_MISC_TEXTURECUBE; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = d3dDevice->CreateTexture2D( &desc, 0, pStaging.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + assert( pStaging ); + + pContext->CopyResource( pStaging.Get(), pTemp.Get() ); + } + else if ( (desc.Usage == D3D11_USAGE_STAGING) && (desc.CPUAccessFlags & D3D11_CPU_ACCESS_READ) ) + { + // Handle case where the source is already a staging texture we can use directly + pStaging = pTexture; + } + else + { + // Otherwise, create a staging texture from the non-MSAA source + desc.BindFlags = 0; + desc.MiscFlags &= D3D11_RESOURCE_MISC_TEXTURECUBE; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = d3dDevice->CreateTexture2D( &desc, 0, pStaging.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + assert( pStaging ); + + pContext->CopyResource( pStaging.Get(), pSource ); + } + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP) || (_WIN32_WINNT > _WIN32_WINNT_WIN8) + +static bool g_WIC2 = false; + +static IWICImagingFactory* _GetWIC() +{ + static IWICImagingFactory* s_Factory = nullptr; + + if ( s_Factory ) + return s_Factory; + +#if(_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + HRESULT hr = CoCreateInstance( + CLSID_WICImagingFactory2, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory2), + (LPVOID*)&s_Factory + ); + + if ( SUCCEEDED(hr) ) + { + // WIC2 is available on Windows 8 and Windows 7 SP1 with KB 2670838 installed + g_WIC2 = true; + } + else + { + hr = CoCreateInstance( + CLSID_WICImagingFactory1, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + (LPVOID*)&s_Factory + ); + + if ( FAILED(hr) ) + { + s_Factory = nullptr; + return nullptr; + } + } +#else + HRESULT hr = CoCreateInstance( + CLSID_WICImagingFactory, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + (LPVOID*)&s_Factory + ); + + if ( FAILED(hr) ) + { + s_Factory = nullptr; + return nullptr; + } +#endif + + return s_Factory; +} +#endif + + +//-------------------------------------------------------------------------------------- +HRESULT DirectX::SaveDDSTextureToFile( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_z_ LPCWSTR fileName ) +{ + if ( !fileName ) + return E_INVALIDARG; + + D3D11_TEXTURE2D_DESC desc = { 0 }; + ComPtr pStaging; + HRESULT hr = CaptureTexture( pContext, pSource, desc, pStaging ); + if ( FAILED(hr) ) + return hr; + + // Create file +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile( safe_handle( CreateFile2( fileName, GENERIC_WRITE, 0, CREATE_ALWAYS, 0 ) ) ); +#else + ScopedHandle hFile( safe_handle( CreateFileW( fileName, GENERIC_WRITE, 0, 0, CREATE_ALWAYS, 0, 0 ) ) ); +#endif + if ( !hFile ) + return HRESULT_FROM_WIN32( GetLastError() ); + + // Setup header + const size_t MAX_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10); + uint8_t fileHeader[ MAX_HEADER_SIZE ]; + + *reinterpret_cast(&fileHeader[0]) = DDS_MAGIC; + + auto header = reinterpret_cast( &fileHeader[0] + sizeof(uint32_t) ); + size_t headerSize = sizeof(uint32_t) + sizeof(DDS_HEADER); + memset( header, 0, sizeof(DDS_HEADER) ); + header->size = sizeof( DDS_HEADER ); + header->flags = DDS_HEADER_FLAGS_TEXTURE | DDS_HEADER_FLAGS_MIPMAP; + header->height = desc.Height; + header->width = desc.Width; + header->mipMapCount = 1; + header->caps = DDS_SURFACE_FLAGS_TEXTURE; + + // Try to use a legacy .DDS pixel format for better tools support, otherwise fallback to 'DX10' header extension + DDS_HEADER_DXT10* extHeader = nullptr; + switch( desc.Format ) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8B8G8R8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16G16_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_G16R16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8L8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_L16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_L8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_B8G8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_R8G8_B8G8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_G8R8_G8B8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_G8R8_G8B8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC1_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT1, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC2_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT3, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC3_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DXT5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC4_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC4_UNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC4_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC4_SNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC5_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC5_UNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_BC5_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_BC5_SNORM, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B5G6R5_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_R5G6B5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B5G5R5A1_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A1R5G5B5, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_V8U8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R8G8B8A8_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_Q8W8V8U8, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_R16G16_SNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_V16U16, sizeof(DDS_PIXELFORMAT) ); break; + case DXGI_FORMAT_B8G8R8A8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A8R8G8B8, sizeof(DDS_PIXELFORMAT) ); break; // DXGI 1.1 + case DXGI_FORMAT_B8G8R8X8_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_X8R8G8B8, sizeof(DDS_PIXELFORMAT) ); break; // DXGI 1.1 + case DXGI_FORMAT_YUY2: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_YUY2, sizeof(DDS_PIXELFORMAT) ); break; // DXGI 1.2 + case DXGI_FORMAT_B4G4R4A4_UNORM: memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_A4R4G4B4, sizeof(DDS_PIXELFORMAT) ); break; // DXGI 1.2 + + // Legacy D3DX formats using D3DFMT enum value as FourCC + case DXGI_FORMAT_R32G32B32A32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 116; break; // D3DFMT_A32B32G32R32F + case DXGI_FORMAT_R16G16B16A16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 113; break; // D3DFMT_A16B16G16R16F + case DXGI_FORMAT_R16G16B16A16_UNORM: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 36; break; // D3DFMT_A16B16G16R16 + case DXGI_FORMAT_R16G16B16A16_SNORM: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 110; break; // D3DFMT_Q16W16V16U16 + case DXGI_FORMAT_R32G32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 115; break; // D3DFMT_G32R32F + case DXGI_FORMAT_R16G16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 112; break; // D3DFMT_G16R16F + case DXGI_FORMAT_R32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 114; break; // D3DFMT_R32F + case DXGI_FORMAT_R16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 111; break; // D3DFMT_R16F + + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + + default: + memcpy_s( &header->ddspf, sizeof(header->ddspf), &DDSPF_DX10, sizeof(DDS_PIXELFORMAT) ); + + headerSize += sizeof(DDS_HEADER_DXT10); + extHeader = reinterpret_cast( reinterpret_cast(&fileHeader[0]) + sizeof(uint32_t) + sizeof(DDS_HEADER) ); + memset( extHeader, 0, sizeof(DDS_HEADER_DXT10) ); + extHeader->dxgiFormat = desc.Format; + extHeader->resourceDimension = D3D11_RESOURCE_DIMENSION_TEXTURE2D; + extHeader->arraySize = 1; + break; + } + + size_t rowPitch, slicePitch, rowCount; + GetSurfaceInfo( desc.Width, desc.Height, desc.Format, &slicePitch, &rowPitch, &rowCount ); + + if ( IsCompressed( desc.Format ) ) + { + header->flags |= DDS_HEADER_FLAGS_LINEARSIZE; + header->pitchOrLinearSize = static_cast( slicePitch ); + } + else + { + header->flags |= DDS_HEADER_FLAGS_PITCH; + header->pitchOrLinearSize = static_cast( rowPitch ); + } + + // Setup pixels + std::unique_ptr pixels( new (std::nothrow) uint8_t[ slicePitch ] ); + if (!pixels) + return E_OUTOFMEMORY; + + D3D11_MAPPED_SUBRESOURCE mapped; + hr = pContext->Map( pStaging.Get(), 0, D3D11_MAP_READ, 0, &mapped ); + if ( FAILED(hr) ) + return hr; + + auto sptr = reinterpret_cast( mapped.pData ); + if ( !sptr ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return E_POINTER; + } + + uint8_t* dptr = pixels.get(); + + size_t msize = std::min( rowPitch, mapped.RowPitch ); + for( size_t h = 0; h < rowCount; ++h ) + { + memcpy_s( dptr, rowPitch, sptr, msize ); + sptr += mapped.RowPitch; + dptr += rowPitch; + } + + pContext->Unmap( pStaging.Get(), 0 ); + + // Write header & pixels + DWORD bytesWritten; + if ( !WriteFile( hFile.get(), fileHeader, static_cast( headerSize ), &bytesWritten, 0 ) ) + return HRESULT_FROM_WIN32( GetLastError() ); + + if ( bytesWritten != headerSize ) + return E_FAIL; + + if ( !WriteFile( hFile.get(), pixels.get(), static_cast( slicePitch ), &bytesWritten, 0 ) ) + return HRESULT_FROM_WIN32( GetLastError() ); + + if ( bytesWritten != slicePitch ) + return E_FAIL; + + return S_OK; +} + +//-------------------------------------------------------------------------------------- +#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP) || (_WIN32_WINNT > _WIN32_WINNT_WIN8) + +HRESULT DirectX::SaveWICTextureToFile( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_ REFGUID guidContainerFormat, + _In_z_ LPCWSTR fileName, + _In_opt_ const GUID* targetFormat, + _In_opt_ std::function setCustomProps ) +{ + if ( !fileName ) + return E_INVALIDARG; + + D3D11_TEXTURE2D_DESC desc = { 0 }; + ComPtr pStaging; + HRESULT hr = CaptureTexture( pContext, pSource, desc, pStaging ); + if ( FAILED(hr) ) + return hr; + + // Determine source format's WIC equivalent + WICPixelFormatGUID pfGuid; + bool sRGB = false; + switch ( desc.Format ) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: pfGuid = GUID_WICPixelFormat128bppRGBAFloat; break; + case DXGI_FORMAT_R16G16B16A16_FLOAT: pfGuid = GUID_WICPixelFormat64bppRGBAHalf; break; + case DXGI_FORMAT_R16G16B16A16_UNORM: pfGuid = GUID_WICPixelFormat64bppRGBA; break; + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: pfGuid = GUID_WICPixelFormat32bppRGBA1010102XR; break; // DXGI 1.1 + case DXGI_FORMAT_R10G10B10A2_UNORM: pfGuid = GUID_WICPixelFormat32bppRGBA1010102; break; + case DXGI_FORMAT_B5G5R5A1_UNORM: pfGuid = GUID_WICPixelFormat16bppBGRA5551; break; + case DXGI_FORMAT_B5G6R5_UNORM: pfGuid = GUID_WICPixelFormat16bppBGR565; break; + case DXGI_FORMAT_R32_FLOAT: pfGuid = GUID_WICPixelFormat32bppGrayFloat; break; + case DXGI_FORMAT_R16_FLOAT: pfGuid = GUID_WICPixelFormat16bppGrayHalf; break; + case DXGI_FORMAT_R16_UNORM: pfGuid = GUID_WICPixelFormat16bppGray; break; + case DXGI_FORMAT_R8_UNORM: pfGuid = GUID_WICPixelFormat8bppGray; break; + case DXGI_FORMAT_A8_UNORM: pfGuid = GUID_WICPixelFormat8bppAlpha; break; + + case DXGI_FORMAT_R8G8B8A8_UNORM: + pfGuid = GUID_WICPixelFormat32bppRGBA; + break; + + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + pfGuid = GUID_WICPixelFormat32bppRGBA; + sRGB = true; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGRA; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGRA; + sRGB = true; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGR; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGR; + sRGB = true; + break; + + default: + return HRESULT_FROM_WIN32( ERROR_NOT_SUPPORTED ); + } + + IWICImagingFactory* pWIC = _GetWIC(); + if ( !pWIC ) + return E_NOINTERFACE; + + ComPtr stream; + hr = pWIC->CreateStream( stream.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = stream->InitializeFromFilename( fileName, GENERIC_WRITE ); + if ( FAILED(hr) ) + return hr; + + ComPtr encoder; + hr = pWIC->CreateEncoder( guidContainerFormat, 0, encoder.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + hr = encoder->Initialize( stream.Get(), WICBitmapEncoderNoCache ); + if ( FAILED(hr) ) + return hr; + + ComPtr frame; + ComPtr props; + hr = encoder->CreateNewFrame( frame.GetAddressOf(), props.GetAddressOf() ); + if ( FAILED(hr) ) + return hr; + + if ( targetFormat && memcmp( &guidContainerFormat, &GUID_ContainerFormatBmp, sizeof(WICPixelFormatGUID) ) == 0 && g_WIC2 ) + { + // Opt-in to the WIC2 support for writing 32-bit Windows BMP files with an alpha channel + PROPBAG2 option = { 0 }; + option.pstrName = L"EnableV5Header32bppBGRA"; + + VARIANT varValue; + varValue.vt = VT_BOOL; + varValue.boolVal = VARIANT_TRUE; + (void)props->Write( 1, &option, &varValue ); + } + + if ( setCustomProps ) + { + setCustomProps( props.Get() ); + } + + hr = frame->Initialize( props.Get() ); + if ( FAILED(hr) ) + return hr; + + hr = frame->SetSize( desc.Width , desc.Height ); + if ( FAILED(hr) ) + return hr; + + hr = frame->SetResolution( 72, 72 ); + if ( FAILED(hr) ) + return hr; + + // Pick a target format + WICPixelFormatGUID targetGuid; + if ( targetFormat ) + { + targetGuid = *targetFormat; + } + else + { + // Screenshots don’t typically include the alpha channel of the render target + switch ( desc.Format ) + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + if ( g_WIC2 ) + { + targetGuid = GUID_WICPixelFormat96bppRGBFloat; + } + else + { + targetGuid = GUID_WICPixelFormat24bppBGR; + } + break; +#endif + + case DXGI_FORMAT_R16G16B16A16_UNORM: targetGuid = GUID_WICPixelFormat48bppBGR; break; + case DXGI_FORMAT_B5G5R5A1_UNORM: targetGuid = GUID_WICPixelFormat16bppBGR555; break; + case DXGI_FORMAT_B5G6R5_UNORM: targetGuid = GUID_WICPixelFormat16bppBGR565; break; + + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_A8_UNORM: + targetGuid = GUID_WICPixelFormat8bppGray; + break; + + default: + targetGuid = GUID_WICPixelFormat24bppBGR; + break; + } + } + + hr = frame->SetPixelFormat( &targetGuid ); + if ( FAILED(hr) ) + return hr; + + if ( targetFormat && memcmp( targetFormat, &targetGuid, sizeof(WICPixelFormatGUID) ) != 0 ) + { + // Requested output pixel format is not supported by the WIC codec + return E_FAIL; + } + + // Encode WIC metadata + ComPtr metawriter; + if ( SUCCEEDED( frame->GetMetadataQueryWriter( metawriter.GetAddressOf() ) ) ) + { + PROPVARIANT value; + PropVariantInit( &value ); + + value.vt = VT_LPSTR; + value.pszVal = "DirectXTK"; + + if ( memcmp( &guidContainerFormat, &GUID_ContainerFormatPng, sizeof(GUID) ) == 0 ) + { + // Set Software name + (void)metawriter->SetMetadataByName( L"/tEXt/{str=Software}", &value ); + + // Set sRGB chunk + if ( sRGB ) + { + value.vt = VT_UI1; + value.bVal = 0; + (void)metawriter->SetMetadataByName( L"/sRGB/RenderingIntent", &value ); + } + } + else + { + // Set Software name + (void)metawriter->SetMetadataByName( L"System.ApplicationName", &value ); + + if ( sRGB ) + { + // Set EXIF Colorspace of sRGB + value.vt = VT_UI2; + value.uiVal = 1; + (void)metawriter->SetMetadataByName( L"System.Image.ColorSpace", &value ); + } + } + } + + D3D11_MAPPED_SUBRESOURCE mapped; + hr = pContext->Map( pStaging.Get(), 0, D3D11_MAP_READ, 0, &mapped ); + if ( FAILED(hr) ) + return hr; + + if ( memcmp( &targetGuid, &pfGuid, sizeof(WICPixelFormatGUID) ) != 0 ) + { + // Conversion required to write + ComPtr source; + hr = pWIC->CreateBitmapFromMemory( desc.Width, desc.Height, pfGuid, + mapped.RowPitch, mapped.RowPitch * desc.Height, + reinterpret_cast( mapped.pData ), source.GetAddressOf() ); + if ( FAILED(hr) ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return hr; + } + + ComPtr FC; + hr = pWIC->CreateFormatConverter( FC.GetAddressOf() ); + if ( FAILED(hr) ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return hr; + } + + BOOL canConvert = FALSE; + hr = FC->CanConvert( pfGuid, targetGuid, &canConvert ); + if ( FAILED(hr) || !canConvert ) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize( source.Get(), targetGuid, WICBitmapDitherTypeNone, 0, 0, WICBitmapPaletteTypeCustom ); + if ( FAILED(hr) ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return hr; + } + + WICRect rect = { 0, 0, static_cast( desc.Width ), static_cast( desc.Height ) }; + hr = frame->WriteSource( FC.Get(), &rect ); + if ( FAILED(hr) ) + { + pContext->Unmap( pStaging.Get(), 0 ); + return hr; + } + } + else + { + // No conversion required + hr = frame->WritePixels( desc.Height, mapped.RowPitch, mapped.RowPitch * desc.Height, reinterpret_cast( mapped.pData ) ); + if ( FAILED(hr) ) + return hr; + } + + pContext->Unmap( pStaging.Get(), 0 ); + + hr = frame->Commit(); + if ( FAILED(hr) ) + return hr; + + hr = encoder->Commit(); + if ( FAILED(hr) ) + return hr; + + return S_OK; +} + +#endif // !WINAPI_FAMILY || (WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP) || (_WIN32_WINNT > _WIN32_WINNT_WIN8) diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ScreenGrab.h b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ScreenGrab.h new file mode 100644 index 0000000..cf5d117 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/DirectXTex/ScreenGrab.h @@ -0,0 +1,53 @@ +//-------------------------------------------------------------------------------------- +// File: ScreenGrab.h +// +// Function for capturing a 2D texture and saving it to a file (aka a 'screenshot' +// when used on a Direct3D 11 Render Target). +// +// Note these functions are useful as a light-weight runtime screen grabber. For +// full-featured texture capture, DDS writer, and texture processing pipeline, +// see the 'Texconv' sample and the 'DirectXTex' library. +// +// THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF +// ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO +// THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A +// PARTICULAR PURPOSE. +// +// Copyright (c) Microsoft Corporation. All rights reserved. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#ifdef _MSC_VER +#pragma once +#endif + +#include + +#include + +#pragma warning(push) +#pragma warning(disable : 4005) +#include +#pragma warning(pop) + +#include + +namespace DirectX +{ + HRESULT SaveDDSTextureToFile( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_z_ LPCWSTR fileName ); + +#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_PHONE_APP) || (_WIN32_WINNT > _WIN32_WINNT_WIN8) + + HRESULT SaveWICTextureToFile( _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_ REFGUID guidContainerFormat, + _In_z_ LPCWSTR fileName, + _In_opt_ const GUID* targetFormat = nullptr, + _In_opt_ std::function setCustomProps = nullptr ); + +#endif +} \ No newline at end of file diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_FullscreenPass.hlsl b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_FullscreenPass.hlsl new file mode 100644 index 0000000..5930817 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_FullscreenPass.hlsl @@ -0,0 +1,119 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_FULLSCREEN_PASS_HLSL +#define AMD_LIB_FULLSCREEN_PASS_HLSL + +struct PS_FullscreenInput +{ + float4 position : SV_POSITION; + float2 texCoord : TEXCOORD0; +}; + +struct GS_FullscreenIndexRTInput +{ + float4 position : SV_POSITION; + float2 texCoord : TEXCOORD0; + uint rtIndex : RT_INDEX; +}; + +struct PS_FullscreenIndexRTInput +{ + float4 position : SV_POSITION; + float2 texCoord : TEXCOORD0; + uint rtIndex : SV_RenderTargetArrayIndex; +}; + +// The ScreenQuad shader is used to clear a subregion of a depth map +// Cleaning a rectangle in depth map is otherwise problematic +PS_FullscreenInput vsScreenQuad(uint vertexId : SV_VERTEXID) +{ + + PS_FullscreenInput vertex[6] = + { + { -1.0f, -1.0f, 1.0f, 1.0f }, { 0.0f, 1.0f }, + { -1.0f, 1.0f, 1.0f, 1.0f }, { 0.0f, 0.0f }, + { 1.0f, -1.0f, 1.0f, 1.0f }, { 1.0f, 1.0f }, + { 1.0f, -1.0f, 1.0f, 1.0f }, { 1.0f, 1.0f }, + { -1.0f, 1.0f, 1.0f, 1.0f }, { 0.0f, 0.0f }, + { 1.0f, 1.0f, 1.0f, 1.0f }, { 1.0f, 0.0f }, + }; + + return vertex[vertexId % 6]; +} + +PS_FullscreenInput vsFullscreen(uint vertexId : SV_VERTEXID) +{ + + PS_FullscreenInput vertex[3] = + { + { -1.0f, -1.0f, 0.0f, 1.0f }, { 0.0f, 1.0f }, + { -1.0f, 3.0f, 0.0f, 1.0f }, { 0.0f, -1.0f }, + { 3.0f, -1.0f, 0.0f, 1.0f }, { 2.0f, 1.0f } + }; + + return vertex[vertexId % 3]; +} + +GS_FullscreenIndexRTInput vsFullscreenIndexRT(uint indexId : SV_VERTEXID) +{ + GS_FullscreenIndexRTInput vertex[3] = + { + { -1.0f, -1.0f, 0.0f, 1.0f }, { 0.0f, 1.0f }, 0, + { -1.0f, 3.0f, 0.0f, 1.0f }, { 0.0f, -1.0f }, 0, + { 3.0f, -1.0f, 0.0f, 1.0f }, { 2.0f, 1.0f }, 0 + }; + + uint vertexId = indexId % 3; + uint instanceId = indexId / 3; + + GS_FullscreenIndexRTInput Out = vertex[vertexId]; + Out.rtIndex = instanceId; + + return Out; +} + +[maxvertexcount(3)] +void gsFullscreenIndexRT(triangle GS_FullscreenIndexRTInput In[3], inout TriangleStream OutStream) +{ + PS_FullscreenIndexRTInput Out; + + for (int i = 0; i < 3; i++) + { + PS_FullscreenIndexRTInput Out; + Out.position = In[i].position; + Out.texCoord = In[i].texCoord; + Out.rtIndex = In[i].rtIndex; + OutStream.Append(Out); + } + OutStream.RestartStrip(); +} + +SamplerState g_ssFullscreen : register(s0); +Texture2D g_t2dFullscreen : register(t0); + +float4 psFullscreen(PS_FullscreenInput In) : SV_Target0 +{ + return g_t2dFullscreen.Sample(g_ssFullscreen, In.texCoord).xyzw; +} + +#endif // AMD_LIB_FULLSCREEN_PASS_HLSL diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_Quaternion.hlsl b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_Quaternion.hlsl new file mode 100644 index 0000000..49e6b6a --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_Quaternion.hlsl @@ -0,0 +1,96 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#ifndef AMD_LIB_QUATERNION_HLSL +#define AMD_LIB_QUATERNION_HLSL + +float4 MakeQuaternion(float angle_radian, float3 axis) +{ + // create quaternion using angle and rotation axis + float4 quaternion; + float halfAngle = 0.5f * angle_radian; + float sinHalf = sin(halfAngle); + + quaternion.w = cos(halfAngle); + quaternion.xyz = sinHalf * axis.xyz; + + return quaternion; +} + +float4 InverseQuaternion(float4 q) +{ + float lengthSqr = q.x*q.x + q.y*q.y + q.z*q.z + q.w*q.w; + + if (lengthSqr < 0.001) + { + return float4(0, 0, 0, 1.0f); + } + + q.x = -q.x / lengthSqr; + q.y = -q.y / lengthSqr; + q.z = -q.z / lengthSqr; + q.w = q.w / lengthSqr; + + return q; +} + +float3 MultQuaternionAndVector(float4 q, float3 v) +{ + float3 uv, uuv; + float3 qvec = float3(q.x, q.y, q.z); + uv = cross(qvec, v); + uuv = cross(qvec, uv); + uv *= (2.0f * q.w); + uuv *= 2.0f; + + return v + uv + uuv; +} + +float4 MultQuaternionAndQuaternion(float4 qA, float4 qB) +{ + float4 q; + + q.w = qA.w * qB.w - qA.x * qB.x - qA.y * qB.y - qA.z * qB.z; + q.x = qA.w * qB.x + qA.x * qB.w + qA.y * qB.z - qA.z * qB.y; + q.y = qA.w * qB.y + qA.y * qB.w + qA.z * qB.x - qA.x * qB.z; + q.z = qA.w * qB.z + qA.z * qB.w + qA.x * qB.y - qA.y * qB.x; + + return q; +} + +float4 AngularVelocityToSpin(float4 orientation, float3 angular_veloctiy) +{ + return 0.5f * MultQuaternionAndQuaternion(float4(angular_veloctiy.xyz, 0), orientation); +} + +float3 MultWorldInertiaInvAndVector(float4 orientation, float3 inertia, float3 vec) +{ + float4 inv_orientation = float4(-orientation.xyz, orientation.w) / length(orientation); + float3 inv_inertia = 1.0f / inertia; + + float3 InertiaInv_RotT_vec = inv_inertia * MultQuaternionAndVector(inv_orientation, vec ); + float3 Rot_InertiaInv_RotT_vec = MultQuaternionAndVector(orientation, InertiaInv_RotT_vec ); + + return Rot_InertiaInv_RotT_vec; +} + +#endif // AMD_LIB_QUATERNION_HLSL diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_UnitCube.hlsl b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_UnitCube.hlsl new file mode 100644 index 0000000..abd4cd6 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/AMD_UnitCube.hlsl @@ -0,0 +1,119 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +struct PS_UnitCubeInput +{ + float4 ss_position : SV_Position; +}; + +struct UnitCubeTransform +{ + float4x4 m_tr; + float4x4 m_inverse; + float4x4 m_forward; + float4 m_color; +}; + +cbuffer CB_UNIT_CUBE_TRANSFORM : register (c0) +{ + UnitCubeTransform g_UnitCubeTransform; +} + +SamplerState g_ssUnitCube : register(s0); +Texture2D g_t2dUnitCube : register(t0); + +PS_UnitCubeInput vsClipSpaceCube( uint vertex_id : SV_VERTEXID ) +{ + float4 vertex[] = + { + { -1.0000, -1.0000, 1.0000, 1 }, + { -1.0000, -1.0000, -0.0000, 1 }, + { 1.0000, -1.0000, -0.0000, 1 }, + { 1.0000, -1.0000, 1.0000, 1 }, + { -1.0000, 1.0000, 1.0000, 1 }, + { 1.0000, 1.0000, 1.0000, 1 }, + { 1.0000, 1.0000, -0.0000, 1 }, + { -1.0000, 1.0000, -0.0000, 1 } + }; + + int index[]= + { + 1, 2, 3, + 3, 4, 1, + 5, 6, 7, + 7, 8, 5, + 1, 4, 6, + 6, 5, 1, + 4, 3, 7, + 7, 6, 4, + 3, 2, 8, + 8, 7, 3, + 2, 1, 5, + 5, 8, 2 + }; + + PS_UnitCubeInput Output; + Output.ss_position = mul (vertex[index[vertex_id] - 1], g_UnitCubeTransform.m_tr ); + + return Output; +} + +PS_UnitCubeInput vsUnitCube( uint vertex_id : SV_VERTEXID ) +{ + float4 vertex[] = + { + { -1.0000, -1.0000, 1.0000, 1 }, + { -1.0000, -1.0000, -1.0000, 1 }, + { 1.0000, -1.0000, -1.0000, 1 }, + { 1.0000, -1.0000, 1.0000, 1 }, + { -1.0000, 1.0000, 1.0000, 1 }, + { 1.0000, 1.0000, 1.0000, 1 }, + { 1.0000, 1.0000, -1.0000, 1 }, + { -1.0000, 1.0000, -1.0000, 1 } + }; + + int index[]= + { + 1, 2, 3, + 3, 4, 1, + 5, 6, 7, + 7, 8, 5, + 1, 4, 6, + 6, 5, 1, + 4, 3, 7, + 7, 6, 4, + 3, 2, 8, + 8, 7, 3, + 2, 1, 5, + 5, 8, 2 + }; + + PS_UnitCubeInput Output; + Output.ss_position = mul (vertex[index[vertex_id] - 1], g_UnitCubeTransform.m_tr ); + + return Output; +} + +float4 psUnitCube( PS_UnitCubeInput In ) : SV_Target0 +{ + return g_UnitCubeTransform.m_color; +} diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/FilterCommon.hlsl b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/FilterCommon.hlsl new file mode 100644 index 0000000..5b2dcac --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/FilterCommon.hlsl @@ -0,0 +1,170 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: FilterCommon.hlsl +// +// Common defines for separable filtering kernels +//-------------------------------------------------------------------------------------- + + +// Defines passed in at compile time +//#define LDS_PRECISION ( 8 , 16, or 32 ) +//#define USE_APPROXIMATE_FILTER ( 0, 1 ) +//#define USE_COMPUTE_SHADER +//#define KERNEL_RADIUS ( 16 ) // Must be an even number + + +// Defines that control the CS logic of the kernel +#define KERNEL_DIAMETER ( KERNEL_RADIUS * 2 + 1 ) +#define RUN_LINES ( 2 ) // Needs to match g_uRunLines in SeparableFilter11.cpp +#define RUN_SIZE ( 128 ) // Needs to match g_uRunSize in SeparableFilter11.cpp +#define KERNEL_DIAMETER_MINUS_ONE ( KERNEL_DIAMETER - 1 ) +#define RUN_SIZE_PLUS_KERNEL ( RUN_SIZE + KERNEL_DIAMETER_MINUS_ONE ) +#define PIXELS_PER_THREAD ( 4 ) +#define NUM_THREADS ( RUN_SIZE / PIXELS_PER_THREAD ) +#define SAMPLES_PER_THREAD ( RUN_SIZE_PLUS_KERNEL / NUM_THREADS ) +#define EXTRA_SAMPLES ( RUN_SIZE_PLUS_KERNEL - ( NUM_THREADS * SAMPLES_PER_THREAD ) ) + + +// The samplers +SamplerState g_PointSampler : register (s0); +SamplerState g_LinearClampSampler : register (s1); + + +// Adjusts the sampling step size if using approximate filtering +#if ( USE_APPROXIMATE_FILTER == 1 ) + + #define STEP_SIZE ( 2 ) + +#else + + #define STEP_SIZE ( 1 ) + +#endif + + +// Constant buffer used by the CS & PS +cbuffer cbSF : register( b0 ) +{ + float4 g_f4OutputSize; // x = Width, y = Height, z = Inv Width, w = Inv Height +} + + +// Input structure used by the PS +struct PS_RenderQuadInput +{ + float4 f4Position : SV_POSITION; + float2 f2TexCoord : TEXCOORD0; +}; + +#if ( REQUIRE_HDR == 1 ) + + //-------------------------------------------------------------------------------------- + // Packs a float2 to a unit + //-------------------------------------------------------------------------------------- + uint Float2ToUint( float2 f2Value ) + { + return ( f32tof16( f2Value.x ) ) + ( f32tof16( f2Value.y ) << 16 ); + } + + + //-------------------------------------------------------------------------------------- + // Unpacks a uint to a float2 + //-------------------------------------------------------------------------------------- + float2 UintToFloat2( uint uValue ) + { + return float2( f16tof32( uValue ), f16tof32( uValue >> 16 ) ); + } + +#else + + //-------------------------------------------------------------------------------------- + // Packs a float2 to a unit + //-------------------------------------------------------------------------------------- + uint Float2ToUint( float2 f2Value ) + { + return ( ( ( (uint)( f2Value.y * 65535.0f ) ) << 16 ) | + ( (uint)( f2Value.x * 65535.0f ) ) ); + } + + + //-------------------------------------------------------------------------------------- + // Unpacks a uint to a float2 + //-------------------------------------------------------------------------------------- + float2 UintToFloat2( uint uValue ) + { + return float2( ( uValue & 0x0000FFFF ) / 65535.0f, + ( ( uValue & 0xFFFF0000 ) >> 16 ) / 65535.0f ); + } + +#endif + +//-------------------------------------------------------------------------------------- +// Packs a float4 to a unit +//-------------------------------------------------------------------------------------- +uint Float4ToUint( float4 f4Value ) +{ + return ( ( ( (uint)( f4Value.w * 255.0f ) ) << 24 ) | + ( ( (uint)( f4Value.z * 255.0f ) ) << 16 ) | + ( ( (uint)( f4Value.y * 255.0f ) ) << 8 ) | + ( (uint)( f4Value.x * 255.0f ) ) ); +} + + +//-------------------------------------------------------------------------------------- +// Unpacks a uint to a float4 +//-------------------------------------------------------------------------------------- +float4 UintToFloat4( uint uValue ) +{ + return float4( ( uValue & 0x000000FF ) / 255.0f, + ( ( uValue & 0x0000FF00 ) >> 8 ) / 255.0f, + ( ( uValue & 0x00FF0000 ) >> 16 ) / 255.0f, + ( ( uValue & 0xFF000000 ) >> 24 ) / 255.0f ); +} + + +//-------------------------------------------------------------------------------------- +// Packs a float3 to a unit +//-------------------------------------------------------------------------------------- +uint Float3ToUint( float3 f3Value ) +{ + return ( ( ( (uint)( f3Value.z * 255.0f ) ) << 16 ) | + ( ( (uint)( f3Value.y * 255.0f ) ) << 8 ) | + ( (uint)( f3Value.x * 255.0f ) ) ); +} + + +//-------------------------------------------------------------------------------------- +// Unpacks a uint to a float3 +//-------------------------------------------------------------------------------------- +float3 UintToFloat3( uint uValue ) +{ + return float3( ( uValue & 0x000000FF ) / 255.0f, + ( ( uValue & 0x0000FF00 ) >> 8 ) / 255.0f, + ( ( uValue & 0x00FF0000 ) >> 16 ) / 255.0f ); +} + + +//-------------------------------------------------------------------------------------- +// EOF +//-------------------------------------------------------------------------------------- diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/FilterKernel.hlsl b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/FilterKernel.hlsl new file mode 100644 index 0000000..274e882 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/FilterKernel.hlsl @@ -0,0 +1,151 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: FilterKernel.hlsl +// +// Defines the compute kernel for a separable filter. It calls the macros defined by the +// user supplied HLSL such as GaussianFilter.hlsl and BilateralFilter.hlsl +//-------------------------------------------------------------------------------------- + + +//-------------------------------------------------------------------------------------- +// Samples from inputs defined by the SampleFromInput macro +//-------------------------------------------------------------------------------------- +RAWDataItem Sample( int2 i2Position, float2 f2Offset ) +{ + RAWDataItem RDI; + float2 f2SamplePosition = float2( i2Position ) + float2( 0.5f, 0.5f ); + + #if ( USE_APPROXIMATE_FILTER == 1 ) + + f2SamplePosition += f2Offset; + + #endif + + f2SamplePosition *= g_f4OutputSize.zw; + SAMPLE_FROM_INPUT( g_LinearClampSampler, f2SamplePosition, RDI ) + + return RDI; +} + +#if ( USE_COMPUTE_SHADER == 1 ) + + //-------------------------------------------------------------------------------------- + // Macro for caching LDS reads, this has the effect of drastically reducing reads from the + // LDS by up to 4x + //-------------------------------------------------------------------------------------- + #define CACHE_LDS_READS( _iIteration, _iLineOffset, _iPixelOffset, _RDI ) \ + /* Trickle LDS values down within the GPRs*/ \ + [unroll] for ( iPixel = 0; iPixel < PIXELS_PER_THREAD - STEP_SIZE; ++iPixel ) { \ + _RDI[iPixel] = _RDI[iPixel + STEP_SIZE]; } \ + /* Load new LDS value(s) */ \ + [unroll] for ( iPixel = 0; iPixel < STEP_SIZE; ++iPixel ) { \ + READ_FROM_LDS( _iLineOffset, ( _iPixelOffset + _iIteration + iPixel ), _RDI[(PIXELS_PER_THREAD - STEP_SIZE + iPixel)] ) } + + + //-------------------------------------------------------------------------------------- + // Defines the filter kernel logic. User supplies macro's for custom filter + //-------------------------------------------------------------------------------------- + void ComputeFilterKernel( int iPixelOffset, int iLineOffset, int2 i2Center, int2 i2Inc ) + { + CS_Output Output = (CS_Output)0; + KernelData KD[PIXELS_PER_THREAD]; + int iPixel, iIteration; + RAWDataItem RDI[PIXELS_PER_THREAD]; + + #if ( USE_APPROXIMATE_FILTER == 1 ) + + // Read the kernel center values in directly from the input surface(s), as the LDS + // values are pre-filtered, and therefore do not represent the kernel center + [unroll] + for ( iPixel = 0; iPixel < PIXELS_PER_THREAD; ++iPixel ) + { + float2 f2SamplePosition = ( float2( i2Center + ( iPixel * i2Inc ) ) + float2( 0.5f, 0.5f ) ) * g_f4OutputSize.zw; + SAMPLE_FROM_INPUT( g_PointSampler, f2SamplePosition, RDI[iPixel] ) + } + + #else + + // Read the kernel center values in from the LDS + [unroll] + for ( iPixel = 0; iPixel < PIXELS_PER_THREAD; ++iPixel ) + { + READ_FROM_LDS( iLineOffset, ( iPixelOffset + KERNEL_RADIUS + iPixel ), RDI[iPixel] ) + } + + #endif + + + // Macro defines what happens at the kernel center + KERNEL_CENTER( KD, iPixel, PIXELS_PER_THREAD, Output, RDI ) + + // Prime the GPRs for the first half of the kernel + [unroll] + for ( iPixel = 0; iPixel < PIXELS_PER_THREAD; ++iPixel ) + { + READ_FROM_LDS( iLineOffset, ( iPixelOffset + iPixel ), RDI[iPixel] ) + } + + // Increment the LDS offset by PIXELS_PER_THREAD + iPixelOffset += PIXELS_PER_THREAD; + + // First half of the kernel + [unroll] + for ( iIteration = 0; iIteration < KERNEL_RADIUS; iIteration += STEP_SIZE ) + { + // Macro defines what happens for each kernel iteration + KERNEL_ITERATION( iIteration, KD, iPixel, PIXELS_PER_THREAD, Output, RDI ) + + // Macro to cache LDS reads in GPRs + CACHE_LDS_READS( iIteration, iLineOffset, iPixelOffset, RDI ) + } + + // Prime the GPRs for the second half of the kernel + [unroll] + for ( iPixel = 0; iPixel < PIXELS_PER_THREAD; ++iPixel ) + { + READ_FROM_LDS( iLineOffset, ( iPixelOffset - PIXELS_PER_THREAD + iIteration + 1 + iPixel ), RDI[iPixel] ) + } + + // Second half of the kernel + [unroll] + for ( iIteration = KERNEL_RADIUS + 1; iIteration < KERNEL_DIAMETER; iIteration += STEP_SIZE ) + { + // Macro defines what happens for each kernel iteration + KERNEL_ITERATION( iIteration, KD, iPixel, PIXELS_PER_THREAD, Output, RDI ) + + // Macro to cache LDS reads in GPRs + CACHE_LDS_READS( iIteration, iLineOffset, iPixelOffset, RDI ) + } + + // Macros define final weighting and output + KERNEL_FINAL_WEIGHT( KD, iPixel, PIXELS_PER_THREAD, Output ) + KERNEL_OUTPUT( i2Center, i2Inc, iPixel, PIXELS_PER_THREAD, Output, KD ) + } + +#endif + + +//-------------------------------------------------------------------------------------- +// EOF +//-------------------------------------------------------------------------------------- diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/HorizontalFilter.hlsl b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/HorizontalFilter.hlsl new file mode 100644 index 0000000..a951d0d --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/HorizontalFilter.hlsl @@ -0,0 +1,134 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: HorizontalFilter.hlsl +// +// Implements the horizontal pass of the kernel. +//-------------------------------------------------------------------------------------- + + +#if ( USE_COMPUTE_SHADER == 1 ) + + //-------------------------------------------------------------------------------------- + // Compute shader implementing the horizontal pass of a separable filter + //-------------------------------------------------------------------------------------- + [numthreads( NUM_THREADS, RUN_LINES, 1 )] + void CSFilterX( uint3 Gid : SV_GroupID, uint3 GTid : SV_GroupThreadID ) + { + // Sampling and line offsets from group thread IDs + int iSampleOffset = GTid.x * SAMPLES_PER_THREAD; + int iLineOffset = GTid.y; + + // Group and pixel coords from group IDs + int2 i2GroupCoord = int2( ( Gid.x * RUN_SIZE ) - KERNEL_RADIUS, ( Gid.y * RUN_LINES ) ); + int2 i2Coord = int2( i2GroupCoord.x + iSampleOffset, i2GroupCoord.y ); + + // Sample and store to LDS + [unroll] + for ( int i = 0; i < SAMPLES_PER_THREAD; ++i ) + { + WRITE_TO_LDS( Sample( i2Coord + int2( i, GTid.y ), float2( 0.5f, 0.0f ) ), iLineOffset, iSampleOffset + i ) + } + + // Optionally load some extra texels as required by the exact kernel size + if ( GTid.x < EXTRA_SAMPLES ) + { + WRITE_TO_LDS( Sample( i2GroupCoord + int2( RUN_SIZE_PLUS_KERNEL - 1 - GTid.x, GTid.y ), float2( 0.5f, 0.0f ) ), iLineOffset, RUN_SIZE_PLUS_KERNEL - 1 - GTid.x ) + } + + // Sync threads + GroupMemoryBarrierWithGroupSync(); + + // Adjust pixel offset for computing at PIXELS_PER_THREAD + int iPixelOffset = GTid.x * PIXELS_PER_THREAD; + i2Coord = int2( i2GroupCoord.x + iPixelOffset, i2GroupCoord.y ); + + // Since we start with the first thread position, we need to increment the coord by KERNEL_RADIUS + i2Coord.x += KERNEL_RADIUS; + + // Ensure we don't compute pixels off screen + if ( i2Coord.x < g_f4OutputSize.x ) + { + int2 i2Center = i2Coord + int2( 0, GTid.y ); + int2 i2Inc = int2( 1, 0 ); + + // Compute the filter kernel using LDS values + ComputeFilterKernel( iPixelOffset, iLineOffset, i2Center, i2Inc ); + } + } + +#else // USE_COMPUTE_SHADER + + //-------------------------------------------------------------------------------------- + // Pixel shader implementing the horizontal pass of a separable filter + //-------------------------------------------------------------------------------------- + PS_Output PSFilterX( PS_RenderQuadInput I ) : SV_TARGET + { + PS_Output Output = (PS_Output)0; + RAWDataItem RDI[1]; + int iPixel, iIteration; + KernelData KD[1]; + + // Load the center sample(s) + int2 i2KernelCenter = int2( g_f4OutputSize.xy * I.f2TexCoord ); + RDI[0] = Sample( int2( i2KernelCenter.x, i2KernelCenter.y ), float2( 0.0f, 0.0f ) ); + + // Macro defines what happens at the kernel center + KERNEL_CENTER( KD, iPixel, 1, Output, RDI ) + + i2KernelCenter.x -= KERNEL_RADIUS; + + // First half of the kernel + [unroll] + for ( iIteration = 0; iIteration < KERNEL_RADIUS; iIteration += STEP_SIZE ) + { + // Load the sample(s) for this iteration + RDI[0] = Sample( int2( i2KernelCenter.x + iIteration, i2KernelCenter.y ), float2( 0.5f, 0.0f ) ); + + // Macro defines what happens for each kernel iteration + KERNEL_ITERATION( iIteration, KD, iPixel, 1, Output, RDI ) + } + + // Second half of the kernel + [unroll] + for ( iIteration = KERNEL_RADIUS + 1; iIteration < KERNEL_DIAMETER; iIteration += STEP_SIZE ) + { + // Load the sample(s) for this iteration + RDI[0] = Sample( int2( i2KernelCenter.x + iIteration, i2KernelCenter.y ), float2( 0.5f, 0.0f ) ); + + // Macro defines what happens for each kernel iteration + KERNEL_ITERATION( iIteration, KD, iPixel, 1, Output, RDI ) + } + + // Macros define final weighting + KERNEL_FINAL_WEIGHT( KD, iPixel, 1, Output ) + + return Output; + } + +#endif // USE_COMPUTE_SHADER + + +//-------------------------------------------------------------------------------------- +// EOF +//-------------------------------------------------------------------------------------- diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/VerticalFilter.hlsl b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/VerticalFilter.hlsl new file mode 100644 index 0000000..c5f023e --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/SeparableFilter/VerticalFilter.hlsl @@ -0,0 +1,134 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: VerticalFilter.hlsl +// +// Implements the vertical pass of the kernel. +//-------------------------------------------------------------------------------------- + + +#if ( USE_COMPUTE_SHADER == 1 ) + + //-------------------------------------------------------------------------------------- + // Compute shader implementing the vertical pass of a separable filter + //-------------------------------------------------------------------------------------- + [numthreads( NUM_THREADS, RUN_LINES, 1 )] + void CSFilterY( uint3 Gid : SV_GroupID, uint3 GTid : SV_GroupThreadID ) + { + // Sampling and line offsets from group thread IDs + int iSampleOffset = GTid.x * SAMPLES_PER_THREAD; + int iLineOffset = GTid.y; + + // Group and pixel coords from group IDs + int2 i2GroupCoord = int2( ( Gid.x * RUN_LINES ), ( Gid.y * RUN_SIZE ) - KERNEL_RADIUS ); + int2 i2Coord = int2( i2GroupCoord.x, i2GroupCoord.y + iSampleOffset ); + + // Sample and store to LDS + [unroll] + for ( int i = 0; i < SAMPLES_PER_THREAD; ++i ) + { + WRITE_TO_LDS( Sample( i2Coord + int2( GTid.y, i ), float2( 0.0f, 0.5f ) ), iLineOffset, iSampleOffset + i ) + } + + // Optionally load some extra texels as required by the exact kernel size + if ( GTid.x < EXTRA_SAMPLES ) + { + WRITE_TO_LDS( Sample( i2GroupCoord + int2( GTid.y, RUN_SIZE_PLUS_KERNEL - 1 - GTid.x ), float2( 0.0f, 0.5f ) ), iLineOffset, RUN_SIZE_PLUS_KERNEL - 1 - GTid.x ) + } + + // Sync threads + GroupMemoryBarrierWithGroupSync(); + + // Adjust pixel offset for computing at PIXELS_PER_THREAD + int iPixelOffset = GTid.x * PIXELS_PER_THREAD; + i2Coord = int2( i2GroupCoord.x, i2GroupCoord.y + iPixelOffset ); + + // Since we start with the first thread position, we need to increment the coord by KERNEL_RADIUS + i2Coord.y += KERNEL_RADIUS; + + // Ensure we don't compute pixels off screen + if ( i2Coord.y < g_f4OutputSize.y ) + { + int2 i2Center = i2Coord + int2( GTid.y, 0 ); + int2 i2Inc = int2( 0, 1 ); + + // Compute the filter kernel using LDS values + ComputeFilterKernel( iPixelOffset, iLineOffset, i2Center, i2Inc ); + } + } + +#else // USE_COMPUTE_SHADER + + //-------------------------------------------------------------------------------------- + // Pixel shader implementing the vertical pass of a separable filter + //-------------------------------------------------------------------------------------- + PS_Output PSFilterY( PS_RenderQuadInput I ) : SV_TARGET + { + PS_Output Output = (PS_Output)0; + RAWDataItem RDI[1]; + int iPixel, iIteration; + KernelData KD[1]; + + // Load the center sample(s) + int2 i2KernelCenter = int2( g_f4OutputSize.xy * I.f2TexCoord ); + RDI[0] = Sample( int2( i2KernelCenter.x, i2KernelCenter.y ), float2( 0.0f, 0.0f ) ); + + // Macro defines what happens at the kernel center + KERNEL_CENTER( KD, iPixel, 1, Output, RDI ) + + i2KernelCenter.y -= KERNEL_RADIUS; + + // First half of the kernel + [unroll] + for ( iIteration = 0; iIteration < KERNEL_RADIUS; iIteration += STEP_SIZE ) + { + // Load the sample(s) for this iteration + RDI[0] = Sample( int2( i2KernelCenter.x, i2KernelCenter.y + iIteration ), float2( 0.0f, 0.5f ) ); + + // Macro defines what happens for each kernel iteration + KERNEL_ITERATION( iIteration, KD, iPixel, 1, Output, RDI ) + } + + // Second half of the kernel + [unroll] + for ( iIteration = KERNEL_RADIUS + 1; iIteration < KERNEL_DIAMETER; iIteration += STEP_SIZE ) + { + // Load the sample(s) for this iteration + RDI[0] = Sample( int2( i2KernelCenter.x, i2KernelCenter.y + iIteration ), float2( 0.0f, 0.5f ) ); + + // Macro defines what happens for each kernel iteration + KERNEL_ITERATION( iIteration, KD, iPixel, 1, Output, RDI ) + } + + // Macros define final weighting + KERNEL_FINAL_WEIGHT( KD, iPixel, 1, Output ) + + return Output; + } + +#endif // USE_COMPUTE_SHADER + + +//-------------------------------------------------------------------------------------- +// EOF +//-------------------------------------------------------------------------------------- diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/GS_FULLSCREEN_INDEX_RT.inc b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/GS_FULLSCREEN_INDEX_RT.inc new file mode 100644 index 0000000..ec09943 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/GS_FULLSCREEN_INDEX_RT.inc @@ -0,0 +1,214 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 6.3.9600.16384 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_POSITION 0 xyzw 0 POS float xyzw +// TEXCOORD 0 xy 1 NONE float xy +// RT_INDEX 0 x 2 NONE uint x +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_POSITION 0 xyzw 0 POS float xyzw +// TEXCOORD 0 xy 1 NONE float xy +// SV_RenderTargetArrayIndex 0 x 2 RTINDEX uint x +// +gs_5_0 +dcl_globalFlags refactoringAllowed +dcl_input_siv v[3][0].xyzw, position +dcl_input v[3][1].xy +dcl_input v[3][2].x +dcl_temps 1 +dcl_inputprimitive triangle +dcl_stream m0 +dcl_outputtopology trianglestrip +dcl_output_siv o0.xyzw, position +dcl_output o1.xy +dcl_output_siv o2.x, rendertarget_array_index +dcl_maxout 3 +mov r0.x, l(0) +loop + ige r0.y, r0.x, l(3) + breakc_nz r0.y + mov o0.xyzw, v[r0.x + 0][0].xyzw + mov o1.xy, v[r0.x + 0][1].xyxx + mov o2.x, v[r0.x + 0][2].x + emit_stream m0 + iadd r0.x, r0.x, l(1) +endloop +cut_stream m0 +ret +// Approximately 12 instruction slots used +#endif + +const BYTE GS_FULLSCREEN_INDEX_RT_Data[] = +{ + 68, 88, 66, 67, 147, 59, + 248, 85, 248, 41, 103, 88, + 118, 46, 214, 180, 229, 33, + 62, 104, 1, 0, 0, 0, + 188, 3, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 172, 0, 0, 0, 36, 1, + 0, 0, 184, 1, 0, 0, + 32, 3, 0, 0, 82, 68, + 69, 70, 112, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 0, 0, 5, + 83, 71, 0, 1, 0, 0, + 60, 0, 0, 0, 82, 68, + 49, 49, 60, 0, 0, 0, + 24, 0, 0, 0, 32, 0, + 0, 0, 40, 0, 0, 0, + 36, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 77, 105, 99, 114, 111, 115, + 111, 102, 116, 32, 40, 82, + 41, 32, 72, 76, 83, 76, + 32, 83, 104, 97, 100, 101, + 114, 32, 67, 111, 109, 112, + 105, 108, 101, 114, 32, 54, + 46, 51, 46, 57, 54, 48, + 48, 46, 49, 54, 51, 56, + 52, 0, 171, 171, 73, 83, + 71, 78, 112, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 80, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 15, 15, + 0, 0, 92, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 3, 3, + 0, 0, 101, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 1, 1, + 0, 0, 83, 86, 95, 80, + 79, 83, 73, 84, 73, 79, + 78, 0, 84, 69, 88, 67, + 79, 79, 82, 68, 0, 82, + 84, 95, 73, 78, 68, 69, + 88, 0, 171, 171, 79, 83, + 71, 53, 140, 0, 0, 0, + 3, 0, 0, 0, 8, 0, + 0, 0, 0, 0, 0, 0, + 92, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 0, 0, 0, 0, 104, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 1, 0, 0, 0, + 3, 12, 0, 0, 0, 0, + 0, 0, 113, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 1, 0, 0, 0, + 2, 0, 0, 0, 1, 14, + 0, 0, 83, 86, 95, 80, + 79, 83, 73, 84, 73, 79, + 78, 0, 84, 69, 88, 67, + 79, 79, 82, 68, 0, 83, + 86, 95, 82, 101, 110, 100, + 101, 114, 84, 97, 114, 103, + 101, 116, 65, 114, 114, 97, + 121, 73, 110, 100, 101, 120, + 0, 171, 83, 72, 69, 88, + 96, 1, 0, 0, 80, 0, + 2, 0, 88, 0, 0, 0, + 106, 8, 0, 1, 97, 0, + 0, 5, 242, 16, 32, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 95, 0, 0, 4, 50, 16, + 32, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 95, 0, + 0, 4, 18, 16, 32, 0, + 3, 0, 0, 0, 2, 0, + 0, 0, 104, 0, 0, 2, + 1, 0, 0, 0, 93, 24, + 0, 1, 143, 0, 0, 3, + 0, 0, 17, 0, 0, 0, + 0, 0, 92, 40, 0, 1, + 103, 0, 0, 4, 242, 32, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 101, 0, + 0, 3, 50, 32, 16, 0, + 1, 0, 0, 0, 103, 0, + 0, 4, 18, 32, 16, 0, + 2, 0, 0, 0, 4, 0, + 0, 0, 94, 0, 0, 2, + 3, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 48, 0, 0, 1, 33, 0, + 0, 7, 34, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 3, 0, 4, 3, + 26, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 7, + 242, 32, 16, 0, 0, 0, + 0, 0, 70, 30, 160, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 7, 50, 32, + 16, 0, 1, 0, 0, 0, + 70, 16, 160, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 7, 18, 32, 16, 0, + 2, 0, 0, 0, 10, 16, + 160, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 117, 0, 0, 3, + 0, 0, 17, 0, 0, 0, + 0, 0, 30, 0, 0, 7, + 18, 0, 16, 0, 0, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 1, 0, 0, 0, + 22, 0, 0, 1, 118, 0, + 0, 3, 0, 0, 17, 0, + 0, 0, 0, 0, 62, 0, + 0, 1, 83, 84, 65, 84, + 148, 0, 0, 0, 12, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 5, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0 +}; diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/PS_FULLSCREEN.inc b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/PS_FULLSCREEN.inc new file mode 100644 index 0000000..b834281 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/PS_FULLSCREEN.inc @@ -0,0 +1,156 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 6.3.9600.16384 +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// g_ssFullscreen sampler NA NA 0 1 +// g_t2dFullscreen texture float4 2d 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_POSITION 0 xyzw 0 POS float +// TEXCOORD 0 xy 1 NONE float xy +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_Target 0 xyzw 0 TARGET float xyzw +// +ps_5_0 +dcl_globalFlags refactoringAllowed +dcl_sampler s0, mode_default +dcl_resource_texture2d (float,float,float,float) t0 +dcl_input_ps linear v1.xy +dcl_output o0.xyzw +sample_indexable(texture2d)(float,float,float,float) o0.xyzw, v1.xyxx, t0.xyzw, s0 +ret +// Approximately 2 instruction slots used +#endif + +const BYTE PS_FULLSCREEN_Data[] = +{ + 68, 88, 66, 67, 98, 105, + 92, 146, 115, 26, 6, 96, + 252, 230, 97, 91, 84, 225, + 134, 143, 1, 0, 0, 0, + 172, 2, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 12, 1, 0, 0, 100, 1, + 0, 0, 152, 1, 0, 0, + 16, 2, 0, 0, 82, 68, + 69, 70, 208, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 60, 0, 0, 0, 0, 5, + 255, 255, 0, 1, 0, 0, + 155, 0, 0, 0, 82, 68, + 49, 49, 60, 0, 0, 0, + 24, 0, 0, 0, 32, 0, + 0, 0, 40, 0, 0, 0, + 36, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 124, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 139, 0, 0, 0, + 2, 0, 0, 0, 5, 0, + 0, 0, 4, 0, 0, 0, + 255, 255, 255, 255, 0, 0, + 0, 0, 1, 0, 0, 0, + 13, 0, 0, 0, 103, 95, + 115, 115, 70, 117, 108, 108, + 115, 99, 114, 101, 101, 110, + 0, 103, 95, 116, 50, 100, + 70, 117, 108, 108, 115, 99, + 114, 101, 101, 110, 0, 77, + 105, 99, 114, 111, 115, 111, + 102, 116, 32, 40, 82, 41, + 32, 72, 76, 83, 76, 32, + 83, 104, 97, 100, 101, 114, + 32, 67, 111, 109, 112, 105, + 108, 101, 114, 32, 54, 46, + 51, 46, 57, 54, 48, 48, + 46, 49, 54, 51, 56, 52, + 0, 171, 171, 171, 73, 83, + 71, 78, 80, 0, 0, 0, + 2, 0, 0, 0, 8, 0, + 0, 0, 56, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 3, 0, 0, 0, + 0, 0, 0, 0, 15, 0, + 0, 0, 68, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 3, 0, 0, 0, + 1, 0, 0, 0, 3, 3, + 0, 0, 83, 86, 95, 80, + 79, 83, 73, 84, 73, 79, + 78, 0, 84, 69, 88, 67, + 79, 79, 82, 68, 0, 171, + 171, 171, 79, 83, 71, 78, + 44, 0, 0, 0, 1, 0, + 0, 0, 8, 0, 0, 0, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 83, 86, 95, 84, 97, 114, + 103, 101, 116, 0, 171, 171, + 83, 72, 69, 88, 112, 0, + 0, 0, 80, 0, 0, 0, + 28, 0, 0, 0, 106, 8, + 0, 1, 90, 0, 0, 3, + 0, 96, 16, 0, 0, 0, + 0, 0, 88, 24, 0, 4, + 0, 112, 16, 0, 0, 0, + 0, 0, 85, 85, 0, 0, + 98, 16, 0, 3, 50, 16, + 16, 0, 1, 0, 0, 0, + 101, 0, 0, 3, 242, 32, + 16, 0, 0, 0, 0, 0, + 69, 0, 0, 139, 194, 0, + 0, 128, 67, 85, 21, 0, + 242, 32, 16, 0, 0, 0, + 0, 0, 70, 16, 16, 0, + 1, 0, 0, 0, 70, 126, + 16, 0, 0, 0, 0, 0, + 0, 96, 16, 0, 0, 0, + 0, 0, 62, 0, 0, 1, + 83, 84, 65, 84, 148, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0 +}; diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/PS_UNIT_CUBE.inc b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/PS_UNIT_CUBE.inc new file mode 100644 index 0000000..63d5702 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/PS_UNIT_CUBE.inc @@ -0,0 +1,202 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 6.3.9600.16384 +// +// +// Buffer Definitions: +// +// cbuffer CB_UNIT_CUBE_TRANSFORM +// { +// +// struct UnitCubeTransform +// { +// +// float4x4 m_tr; // Offset: 0 +// float4x4 m_inverse; // Offset: 64 +// float4x4 m_forward; // Offset: 128 +// float4 m_color; // Offset: 192 +// +// } g_UnitCubeTransform; // Offset: 0 Size: 208 +// +// } +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// CB_UNIT_CUBE_TRANSFORM cbuffer NA NA 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_Position 0 xyzw 0 POS float +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_Target 0 xyzw 0 TARGET float xyzw +// +ps_5_0 +dcl_globalFlags refactoringAllowed +dcl_constantbuffer cb0[13], immediateIndexed +dcl_output o0.xyzw +mov o0.xyzw, cb0[12].xyzw +ret +// Approximately 2 instruction slots used +#endif + +const BYTE PS_UNIT_CUBE_Data[] = +{ + 68, 88, 66, 67, 222, 223, + 230, 57, 28, 194, 137, 206, + 207, 128, 38, 31, 93, 246, + 186, 96, 1, 0, 0, 0, + 104, 3, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 24, 2, 0, 0, 76, 2, + 0, 0, 128, 2, 0, 0, + 204, 2, 0, 0, 82, 68, + 69, 70, 220, 1, 0, 0, + 1, 0, 0, 0, 116, 0, + 0, 0, 1, 0, 0, 0, + 60, 0, 0, 0, 0, 5, + 255, 255, 0, 1, 0, 0, + 168, 1, 0, 0, 82, 68, + 49, 49, 60, 0, 0, 0, + 24, 0, 0, 0, 32, 0, + 0, 0, 40, 0, 0, 0, + 36, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 92, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 67, 66, 95, 85, + 78, 73, 84, 95, 67, 85, + 66, 69, 95, 84, 82, 65, + 78, 83, 70, 79, 82, 77, + 0, 171, 92, 0, 0, 0, + 1, 0, 0, 0, 140, 0, + 0, 0, 208, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 180, 0, 0, 0, + 0, 0, 0, 0, 208, 0, + 0, 0, 2, 0, 0, 0, + 132, 1, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 103, 95, 85, 110, 105, 116, + 67, 117, 98, 101, 84, 114, + 97, 110, 115, 102, 111, 114, + 109, 0, 85, 110, 105, 116, + 67, 117, 98, 101, 84, 114, + 97, 110, 115, 102, 111, 114, + 109, 0, 109, 95, 116, 114, + 0, 102, 108, 111, 97, 116, + 52, 120, 52, 0, 3, 0, + 3, 0, 4, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 223, 0, 0, 0, 109, 95, + 105, 110, 118, 101, 114, 115, + 101, 0, 109, 95, 102, 111, + 114, 119, 97, 114, 100, 0, + 109, 95, 99, 111, 108, 111, + 114, 0, 102, 108, 111, 97, + 116, 52, 0, 171, 1, 0, + 3, 0, 1, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 40, 1, 0, 0, 218, 0, + 0, 0, 232, 0, 0, 0, + 0, 0, 0, 0, 12, 1, + 0, 0, 232, 0, 0, 0, + 64, 0, 0, 0, 22, 1, + 0, 0, 232, 0, 0, 0, + 128, 0, 0, 0, 32, 1, + 0, 0, 48, 1, 0, 0, + 192, 0, 0, 0, 5, 0, + 0, 0, 1, 0, 52, 0, + 0, 0, 4, 0, 84, 1, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 200, 0, 0, 0, 77, 105, + 99, 114, 111, 115, 111, 102, + 116, 32, 40, 82, 41, 32, + 72, 76, 83, 76, 32, 83, + 104, 97, 100, 101, 114, 32, + 67, 111, 109, 112, 105, 108, + 101, 114, 32, 54, 46, 51, + 46, 57, 54, 48, 48, 46, + 49, 54, 51, 56, 52, 0, + 171, 171, 73, 83, 71, 78, + 44, 0, 0, 0, 1, 0, + 0, 0, 8, 0, 0, 0, + 32, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 83, 86, 95, 80, 111, 115, + 105, 116, 105, 111, 110, 0, + 79, 83, 71, 78, 44, 0, + 0, 0, 1, 0, 0, 0, + 8, 0, 0, 0, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 83, 86, + 95, 84, 97, 114, 103, 101, + 116, 0, 171, 171, 83, 72, + 69, 88, 68, 0, 0, 0, + 80, 0, 0, 0, 17, 0, + 0, 0, 106, 8, 0, 1, + 89, 0, 0, 4, 70, 142, + 32, 0, 0, 0, 0, 0, + 13, 0, 0, 0, 101, 0, + 0, 3, 242, 32, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 6, 242, 32, 16, 0, + 0, 0, 0, 0, 70, 142, + 32, 0, 0, 0, 0, 0, + 12, 0, 0, 0, 62, 0, + 0, 1, 83, 84, 65, 84, + 148, 0, 0, 0, 2, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0 +}; diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_CLIP_SPACE_CUBE.inc b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_CLIP_SPACE_CUBE.inc new file mode 100644 index 0000000..890fc13 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_CLIP_SPACE_CUBE.inc @@ -0,0 +1,498 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 6.3.9600.16384 +// +// +// Buffer Definitions: +// +// cbuffer CB_UNIT_CUBE_TRANSFORM +// { +// +// struct UnitCubeTransform +// { +// +// float4x4 m_tr; // Offset: 0 +// float4x4 m_inverse; // Offset: 64 +// float4x4 m_forward; // Offset: 128 +// float4 m_color; // Offset: 192 +// +// } g_UnitCubeTransform; // Offset: 0 Size: 208 +// +// } +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// CB_UNIT_CUBE_TRANSFORM cbuffer NA NA 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_VERTEXID 0 x 0 VERTID uint x +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_Position 0 xyzw 0 POS float xyzw +// +vs_5_0 +dcl_globalFlags refactoringAllowed +dcl_constantbuffer cb0[4], immediateIndexed +dcl_input_sgv v0.x, vertex_id +dcl_output_siv o0.xyzw, position +dcl_temps 1 +dcl_indexableTemp x0[8], 4 +dcl_indexableTemp x1[36], 4 +mov x0[0].xyz, l(-1.000000,-1.000000,1.000000,0) +mov x0[1].xyz, l(-1.000000,-1.000000,-0.000000,0) +mov x0[2].xyz, l(1.000000,-1.000000,-0.000000,0) +mov x0[3].xyz, l(1.000000,-1.000000,1.000000,0) +mov x0[4].xyz, l(-1.000000,1.000000,1.000000,0) +mov x0[5].xyz, l(1.000000,1.000000,1.000000,0) +mov x0[6].xyz, l(1.000000,1.000000,-0.000000,0) +mov x0[7].xyz, l(-1.000000,1.000000,-0.000000,0) +mov x1[0].x, l(1) +mov x1[1].x, l(2) +mov x1[2].x, l(3) +mov x1[3].x, l(3) +mov x1[4].x, l(4) +mov x1[5].x, l(1) +mov x1[6].x, l(5) +mov x1[7].x, l(6) +mov x1[8].x, l(7) +mov x1[9].x, l(7) +mov x1[10].x, l(8) +mov x1[11].x, l(5) +mov x1[12].x, l(1) +mov x1[13].x, l(4) +mov x1[14].x, l(6) +mov x1[15].x, l(6) +mov x1[16].x, l(5) +mov x1[17].x, l(1) +mov x1[18].x, l(4) +mov x1[19].x, l(3) +mov x1[20].x, l(7) +mov x1[21].x, l(7) +mov x1[22].x, l(6) +mov x1[23].x, l(4) +mov x1[24].x, l(3) +mov x1[25].x, l(2) +mov x1[26].x, l(8) +mov x1[27].x, l(8) +mov x1[28].x, l(7) +mov x1[29].x, l(3) +mov x1[30].x, l(2) +mov x1[31].x, l(1) +mov x1[32].x, l(5) +mov x1[33].x, l(5) +mov x1[34].x, l(8) +mov x1[35].x, l(2) +mov r0.x, v0.x +mov r0.x, x1[r0.x + 0].x +iadd r0.x, r0.x, l(-1) +mov r0.xyz, x0[r0.x + 0].xyzx +mov r0.w, l(1.000000) +dp4 o0.x, r0.xyzw, cb0[0].xyzw +dp4 o0.y, r0.xyzw, cb0[1].xyzw +dp4 o0.z, r0.xyzw, cb0[2].xyzw +dp4 o0.w, r0.xyzw, cb0[3].xyzw +ret +// Approximately 54 instruction slots used +#endif + +const BYTE VS_CLIP_SPACE_CUBE_Data[] = +{ + 68, 88, 66, 67, 14, 171, + 101, 88, 64, 235, 155, 83, + 156, 112, 95, 215, 154, 25, + 141, 72, 1, 0, 0, 0, + 8, 9, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 24, 2, 0, 0, 76, 2, + 0, 0, 128, 2, 0, 0, + 108, 8, 0, 0, 82, 68, + 69, 70, 220, 1, 0, 0, + 1, 0, 0, 0, 116, 0, + 0, 0, 1, 0, 0, 0, + 60, 0, 0, 0, 0, 5, + 254, 255, 0, 1, 0, 0, + 168, 1, 0, 0, 82, 68, + 49, 49, 60, 0, 0, 0, + 24, 0, 0, 0, 32, 0, + 0, 0, 40, 0, 0, 0, + 36, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 92, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 67, 66, 95, 85, + 78, 73, 84, 95, 67, 85, + 66, 69, 95, 84, 82, 65, + 78, 83, 70, 79, 82, 77, + 0, 171, 92, 0, 0, 0, + 1, 0, 0, 0, 140, 0, + 0, 0, 208, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 180, 0, 0, 0, + 0, 0, 0, 0, 208, 0, + 0, 0, 2, 0, 0, 0, + 132, 1, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 103, 95, 85, 110, 105, 116, + 67, 117, 98, 101, 84, 114, + 97, 110, 115, 102, 111, 114, + 109, 0, 85, 110, 105, 116, + 67, 117, 98, 101, 84, 114, + 97, 110, 115, 102, 111, 114, + 109, 0, 109, 95, 116, 114, + 0, 102, 108, 111, 97, 116, + 52, 120, 52, 0, 3, 0, + 3, 0, 4, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 223, 0, 0, 0, 109, 95, + 105, 110, 118, 101, 114, 115, + 101, 0, 109, 95, 102, 111, + 114, 119, 97, 114, 100, 0, + 109, 95, 99, 111, 108, 111, + 114, 0, 102, 108, 111, 97, + 116, 52, 0, 171, 1, 0, + 3, 0, 1, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 40, 1, 0, 0, 218, 0, + 0, 0, 232, 0, 0, 0, + 0, 0, 0, 0, 12, 1, + 0, 0, 232, 0, 0, 0, + 64, 0, 0, 0, 22, 1, + 0, 0, 232, 0, 0, 0, + 128, 0, 0, 0, 32, 1, + 0, 0, 48, 1, 0, 0, + 192, 0, 0, 0, 5, 0, + 0, 0, 1, 0, 52, 0, + 0, 0, 4, 0, 84, 1, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 200, 0, 0, 0, 77, 105, + 99, 114, 111, 115, 111, 102, + 116, 32, 40, 82, 41, 32, + 72, 76, 83, 76, 32, 83, + 104, 97, 100, 101, 114, 32, + 67, 111, 109, 112, 105, 108, + 101, 114, 32, 54, 46, 51, + 46, 57, 54, 48, 48, 46, + 49, 54, 51, 56, 52, 0, + 171, 171, 73, 83, 71, 78, + 44, 0, 0, 0, 1, 0, + 0, 0, 8, 0, 0, 0, + 32, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 1, 0, 0, + 83, 86, 95, 86, 69, 82, + 84, 69, 88, 73, 68, 0, + 79, 83, 71, 78, 44, 0, + 0, 0, 1, 0, 0, 0, + 8, 0, 0, 0, 32, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 83, 86, + 95, 80, 111, 115, 105, 116, + 105, 111, 110, 0, 83, 72, + 69, 88, 228, 5, 0, 0, + 80, 0, 1, 0, 121, 1, + 0, 0, 106, 8, 0, 1, + 89, 0, 0, 4, 70, 142, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 96, 0, + 0, 4, 18, 16, 16, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 103, 0, 0, 4, + 242, 32, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 104, 0, 0, 2, 1, 0, + 0, 0, 105, 0, 0, 4, + 0, 0, 0, 0, 8, 0, + 0, 0, 4, 0, 0, 0, + 105, 0, 0, 4, 1, 0, + 0, 0, 36, 0, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 191, 0, 0, 128, 63, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 191, 0, 0, 0, 128, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 191, 0, 0, 0, 128, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 191, 0, 0, 128, 63, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 63, 0, 0, 128, 63, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 63, 0, 0, 128, 63, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 63, 0, 0, 0, 128, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 63, 0, 0, 0, 128, + 0, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 12, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 13, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 14, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 15, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 16, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 17, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 18, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 19, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 20, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 21, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 22, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 23, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 24, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 25, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 26, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 27, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 28, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 29, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 30, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 31, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 32, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 33, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 34, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 35, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 16, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 7, 18, 0, + 16, 0, 0, 0, 0, 0, + 10, 48, 32, 4, 1, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 54, 0, 0, 7, + 114, 0, 16, 0, 0, 0, + 0, 0, 70, 50, 32, 4, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 128, 63, 17, 0, 0, 8, + 18, 32, 16, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 0, 0, 0, 0, 70, 142, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 17, 0, + 0, 8, 34, 32, 16, 0, + 0, 0, 0, 0, 70, 14, + 16, 0, 0, 0, 0, 0, + 70, 142, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 17, 0, 0, 8, 66, 32, + 16, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 0, 0, + 0, 0, 70, 142, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 17, 0, 0, 8, + 130, 32, 16, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 0, 0, 0, 0, 70, 142, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 62, 0, + 0, 1, 83, 84, 65, 84, + 148, 0, 0, 0, 54, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 44, 0, 0, 0, + 46, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0 +}; diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_FULLSCREEN.inc b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_FULLSCREEN.inc new file mode 100644 index 0000000..05fef0c --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_FULLSCREEN.inc @@ -0,0 +1,200 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 6.3.9600.16384 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_VERTEXID 0 x 0 VERTID uint x +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_POSITION 0 xyzw 0 POS float xyzw +// TEXCOORD 0 xy 1 NONE float xy +// +vs_5_0 +dcl_globalFlags refactoringAllowed +dcl_input_sgv v0.x, vertex_id +dcl_output_siv o0.xyzw, position +dcl_output o1.xy +dcl_temps 1 +dcl_indexableTemp x0[6], 4 +mov x0[0].xy, l(-1.000000,-1.000000,0,0) +mov x0[1].xy, l(0,1.000000,0,0) +mov x0[2].xy, l(-1.000000,3.000000,0,0) +mov x0[3].xy, l(0,-1.000000,0,0) +mov x0[4].xy, l(3.000000,-1.000000,0,0) +mov x0[5].xy, l(2.000000,1.000000,0,0) +udiv null, r0.x, v0.x, l(3) +ishl r0.x, r0.x, l(1) +mov o0.xy, x0[r0.x + 0].xyxx +mov o1.xy, x0[r0.x + 1].xyxx +mov o0.zw, l(0,0,0,1.000000) +ret +// Approximately 12 instruction slots used +#endif + +const BYTE VS_FULLSCREEN_Data[] = +{ + 68, 88, 66, 67, 184, 184, + 39, 104, 161, 154, 175, 221, + 215, 247, 50, 214, 127, 166, + 99, 40, 1, 0, 0, 0, + 160, 3, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 172, 0, 0, 0, 224, 0, + 0, 0, 56, 1, 0, 0, + 4, 3, 0, 0, 82, 68, + 69, 70, 112, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 0, 0, 5, + 254, 255, 0, 1, 0, 0, + 60, 0, 0, 0, 82, 68, + 49, 49, 60, 0, 0, 0, + 24, 0, 0, 0, 32, 0, + 0, 0, 40, 0, 0, 0, + 36, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 77, 105, 99, 114, 111, 115, + 111, 102, 116, 32, 40, 82, + 41, 32, 72, 76, 83, 76, + 32, 83, 104, 97, 100, 101, + 114, 32, 67, 111, 109, 112, + 105, 108, 101, 114, 32, 54, + 46, 51, 46, 57, 54, 48, + 48, 46, 49, 54, 51, 56, + 52, 0, 171, 171, 73, 83, + 71, 78, 44, 0, 0, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 32, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 1, 1, + 0, 0, 83, 86, 95, 86, + 69, 82, 84, 69, 88, 73, + 68, 0, 79, 83, 71, 78, + 80, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 56, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 68, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 3, 12, 0, 0, + 83, 86, 95, 80, 79, 83, + 73, 84, 73, 79, 78, 0, + 84, 69, 88, 67, 79, 79, + 82, 68, 0, 171, 171, 171, + 83, 72, 69, 88, 196, 1, + 0, 0, 80, 0, 1, 0, + 113, 0, 0, 0, 106, 8, + 0, 1, 96, 0, 0, 4, + 18, 16, 16, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 103, 0, 0, 4, 242, 32, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 101, 0, + 0, 3, 50, 32, 16, 0, + 1, 0, 0, 0, 104, 0, + 0, 2, 1, 0, 0, 0, + 105, 0, 0, 4, 0, 0, + 0, 0, 6, 0, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 191, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 128, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 64, 64, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 128, 191, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 64, 64, 0, 0, + 128, 191, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 64, 0, 0, + 128, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 78, 0, + 0, 8, 0, 208, 0, 0, + 18, 0, 16, 0, 0, 0, + 0, 0, 10, 16, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 7, 50, 32, 16, 0, + 0, 0, 0, 0, 70, 48, + 32, 4, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 8, + 50, 32, 16, 0, 1, 0, + 0, 0, 70, 48, 32, 6, + 0, 0, 0, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 8, 194, 32, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 128, 63, + 62, 0, 0, 1, 83, 84, + 65, 84, 148, 0, 0, 0, + 12, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 8, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0 +}; diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_FULLSCREEN_INDEX_RT.inc b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_FULLSCREEN_INDEX_RT.inc new file mode 100644 index 0000000..59934ec --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_FULLSCREEN_INDEX_RT.inc @@ -0,0 +1,221 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 6.3.9600.16384 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_VERTEXID 0 x 0 VERTID uint x +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_POSITION 0 xyzw 0 POS float xyzw +// TEXCOORD 0 xy 1 NONE float xy +// RT_INDEX 0 x 2 NONE uint x +// +vs_5_0 +dcl_globalFlags refactoringAllowed +dcl_input_sgv v0.x, vertex_id +dcl_output_siv o0.xyzw, position +dcl_output o1.xy +dcl_output o2.x +dcl_temps 1 +dcl_indexableTemp x0[8], 4 +mov x0[0].xy, l(-1.000000,-1.000000,0,0) +mov x0[1].xy, l(0,1.000000,0,0) +mov x0[2].x, l(0) +mov x0[3].xy, l(-1.000000,3.000000,0,0) +mov x0[4].xy, l(0,-1.000000,0,0) +mov x0[5].x, l(0) +mov x0[6].xy, l(3.000000,-1.000000,0,0) +mov x0[7].xy, l(2.000000,1.000000,0,0) +udiv o2.x, r0.x, v0.x, l(3) +imul null, r0.x, r0.x, l(3) +mov o0.xy, x0[r0.x + 0].xyxx +mov o1.xy, x0[r0.x + 1].xyxx +mov o0.zw, l(0,0,0,1.000000) +ret +// Approximately 14 instruction slots used +#endif + +const BYTE VS_FULLSCREEN_INDEX_RT_Data[] = +{ + 68, 88, 66, 67, 125, 128, + 239, 182, 183, 180, 20, 45, + 191, 207, 105, 92, 34, 207, + 67, 244, 1, 0, 0, 0, + 4, 4, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 172, 0, 0, 0, 224, 0, + 0, 0, 88, 1, 0, 0, + 104, 3, 0, 0, 82, 68, + 69, 70, 112, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 0, 0, 5, + 254, 255, 0, 1, 0, 0, + 60, 0, 0, 0, 82, 68, + 49, 49, 60, 0, 0, 0, + 24, 0, 0, 0, 32, 0, + 0, 0, 40, 0, 0, 0, + 36, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 77, 105, 99, 114, 111, 115, + 111, 102, 116, 32, 40, 82, + 41, 32, 72, 76, 83, 76, + 32, 83, 104, 97, 100, 101, + 114, 32, 67, 111, 109, 112, + 105, 108, 101, 114, 32, 54, + 46, 51, 46, 57, 54, 48, + 48, 46, 49, 54, 51, 56, + 52, 0, 171, 171, 73, 83, + 71, 78, 44, 0, 0, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 32, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 1, 1, + 0, 0, 83, 86, 95, 86, + 69, 82, 84, 69, 88, 73, + 68, 0, 79, 83, 71, 78, + 112, 0, 0, 0, 3, 0, + 0, 0, 8, 0, 0, 0, + 80, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 92, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 3, 12, 0, 0, + 101, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 0, + 0, 0, 1, 14, 0, 0, + 83, 86, 95, 80, 79, 83, + 73, 84, 73, 79, 78, 0, + 84, 69, 88, 67, 79, 79, + 82, 68, 0, 82, 84, 95, + 73, 78, 68, 69, 88, 0, + 171, 171, 83, 72, 69, 88, + 8, 2, 0, 0, 80, 0, + 1, 0, 130, 0, 0, 0, + 106, 8, 0, 1, 96, 0, + 0, 4, 18, 16, 16, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 103, 0, 0, 4, + 242, 32, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 101, 0, 0, 3, 50, 32, + 16, 0, 1, 0, 0, 0, + 101, 0, 0, 3, 18, 32, + 16, 0, 2, 0, 0, 0, + 104, 0, 0, 2, 1, 0, + 0, 0, 105, 0, 0, 4, + 0, 0, 0, 0, 8, 0, + 0, 0, 4, 0, 0, 0, + 54, 0, 0, 9, 50, 48, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 128, 191, + 0, 0, 128, 191, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 9, 50, 48, + 32, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 128, 63, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 2, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 9, 50, 48, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 128, 191, + 0, 0, 64, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 9, 50, 48, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 128, 191, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 6, 18, 48, + 32, 0, 0, 0, 0, 0, + 5, 0, 0, 0, 1, 64, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 9, 50, 48, + 32, 0, 0, 0, 0, 0, + 6, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 64, 64, + 0, 0, 128, 191, 0, 0, + 0, 0, 0, 0, 0, 0, + 54, 0, 0, 9, 50, 48, + 32, 0, 0, 0, 0, 0, + 7, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 64, + 0, 0, 128, 63, 0, 0, + 0, 0, 0, 0, 0, 0, + 78, 0, 0, 9, 18, 32, + 16, 0, 2, 0, 0, 0, + 18, 0, 16, 0, 0, 0, + 0, 0, 10, 16, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 3, 0, 0, 0, + 38, 0, 0, 8, 0, 208, + 0, 0, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 3, 0, + 0, 0, 54, 0, 0, 7, + 50, 32, 16, 0, 0, 0, + 0, 0, 70, 48, 32, 4, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 8, 50, 32, + 16, 0, 1, 0, 0, 0, + 70, 48, 32, 6, 0, 0, + 0, 0, 1, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 8, + 194, 32, 16, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 128, 63, 62, 0, + 0, 1, 83, 84, 65, 84, + 148, 0, 0, 0, 14, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 8, 0, 0, 0, + 10, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0 +}; diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_SCREENQUAD.inc b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_SCREENQUAD.inc new file mode 100644 index 0000000..6dea65c --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_SCREENQUAD.inc @@ -0,0 +1,242 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 6.3.9600.16384 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_VERTEXID 0 x 0 VERTID uint x +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_POSITION 0 xyzw 0 POS float xyzw +// TEXCOORD 0 xy 1 NONE float xy +// +vs_5_0 +dcl_globalFlags refactoringAllowed +dcl_input_sgv v0.x, vertex_id +dcl_output_siv o0.xyzw, position +dcl_output o1.xy +dcl_temps 1 +dcl_indexableTemp x0[12], 4 +mov x0[0].xy, l(-1.000000,-1.000000,0,0) +mov x0[1].xy, l(0,1.000000,0,0) +mov x0[2].xy, l(-1.000000,1.000000,0,0) +mov x0[3].xy, l(0,0,0,0) +mov x0[4].xy, l(1.000000,-1.000000,0,0) +mov x0[5].xy, l(1.000000,1.000000,0,0) +mov x0[6].xy, l(1.000000,-1.000000,0,0) +mov x0[7].xy, l(1.000000,1.000000,0,0) +mov x0[8].xy, l(-1.000000,1.000000,0,0) +mov x0[9].xy, l(0,0,0,0) +mov x0[10].xy, l(1.000000,1.000000,0,0) +mov x0[11].xy, l(1.000000,0,0,0) +udiv null, r0.x, v0.x, l(6) +ishl r0.x, r0.x, l(1) +mov o0.xy, x0[r0.x + 0].xyxx +mov o1.xy, x0[r0.x + 1].xyxx +mov o0.zw, l(0,0,1.000000,1.000000) +ret +// Approximately 18 instruction slots used +#endif + +const BYTE VS_SCREENQUAD_Data[] = +{ + 68, 88, 66, 67, 59, 57, + 239, 70, 173, 30, 22, 118, + 117, 75, 153, 117, 209, 230, + 219, 167, 1, 0, 0, 0, + 120, 4, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 172, 0, 0, 0, 224, 0, + 0, 0, 56, 1, 0, 0, + 220, 3, 0, 0, 82, 68, + 69, 70, 112, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 60, 0, 0, 0, 0, 5, + 254, 255, 0, 1, 0, 0, + 60, 0, 0, 0, 82, 68, + 49, 49, 60, 0, 0, 0, + 24, 0, 0, 0, 32, 0, + 0, 0, 40, 0, 0, 0, + 36, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 77, 105, 99, 114, 111, 115, + 111, 102, 116, 32, 40, 82, + 41, 32, 72, 76, 83, 76, + 32, 83, 104, 97, 100, 101, + 114, 32, 67, 111, 109, 112, + 105, 108, 101, 114, 32, 54, + 46, 51, 46, 57, 54, 48, + 48, 46, 49, 54, 51, 56, + 52, 0, 171, 171, 73, 83, + 71, 78, 44, 0, 0, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 32, 0, 0, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 1, 1, + 0, 0, 83, 86, 95, 86, + 69, 82, 84, 69, 88, 73, + 68, 0, 79, 83, 71, 78, + 80, 0, 0, 0, 2, 0, + 0, 0, 8, 0, 0, 0, + 56, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 15, 0, 0, 0, + 68, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 1, 0, + 0, 0, 3, 12, 0, 0, + 83, 86, 95, 80, 79, 83, + 73, 84, 73, 79, 78, 0, + 84, 69, 88, 67, 79, 79, + 82, 68, 0, 171, 171, 171, + 83, 72, 69, 88, 156, 2, + 0, 0, 80, 0, 1, 0, + 167, 0, 0, 0, 106, 8, + 0, 1, 96, 0, 0, 4, + 18, 16, 16, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 103, 0, 0, 4, 242, 32, + 16, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 101, 0, + 0, 3, 50, 32, 16, 0, + 1, 0, 0, 0, 104, 0, + 0, 2, 1, 0, 0, 0, + 105, 0, 0, 4, 0, 0, + 0, 0, 12, 0, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 191, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 128, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 191, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 191, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 8, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 9, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 10, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 63, 0, 0, 0, 0, + 0, 0, 0, 0, 54, 0, + 0, 9, 50, 48, 32, 0, + 0, 0, 0, 0, 11, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 78, 0, + 0, 8, 0, 208, 0, 0, + 18, 0, 16, 0, 0, 0, + 0, 0, 10, 16, 16, 0, + 0, 0, 0, 0, 1, 64, + 0, 0, 6, 0, 0, 0, + 41, 0, 0, 7, 18, 0, + 16, 0, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 7, 50, 32, 16, 0, + 0, 0, 0, 0, 70, 48, + 32, 4, 0, 0, 0, 0, + 10, 0, 16, 0, 0, 0, + 0, 0, 54, 0, 0, 8, + 50, 32, 16, 0, 1, 0, + 0, 0, 70, 48, 32, 6, + 0, 0, 0, 0, 1, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 54, 0, + 0, 8, 194, 32, 16, 0, + 0, 0, 0, 0, 2, 64, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 128, 63, 0, 0, 128, 63, + 62, 0, 0, 1, 83, 84, + 65, 84, 148, 0, 0, 0, + 18, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 12, 0, + 0, 0, 14, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0 +}; diff --git a/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_UNIT_CUBE.inc b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_UNIT_CUBE.inc new file mode 100644 index 0000000..e173ec8 --- /dev/null +++ b/src/DX11/framework/amd_lib/shared/d3d11/src/Shaders/inc/VS_UNIT_CUBE.inc @@ -0,0 +1,498 @@ +#if 0 +// +// Generated by Microsoft (R) HLSL Shader Compiler 6.3.9600.16384 +// +// +// Buffer Definitions: +// +// cbuffer CB_UNIT_CUBE_TRANSFORM +// { +// +// struct UnitCubeTransform +// { +// +// float4x4 m_tr; // Offset: 0 +// float4x4 m_inverse; // Offset: 64 +// float4x4 m_forward; // Offset: 128 +// float4 m_color; // Offset: 192 +// +// } g_UnitCubeTransform; // Offset: 0 Size: 208 +// +// } +// +// +// Resource Bindings: +// +// Name Type Format Dim Slot Elements +// ------------------------------ ---------- ------- ----------- ---- -------- +// CB_UNIT_CUBE_TRANSFORM cbuffer NA NA 0 1 +// +// +// +// Input signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_VERTEXID 0 x 0 VERTID uint x +// +// +// Output signature: +// +// Name Index Mask Register SysValue Format Used +// -------------------- ----- ------ -------- -------- ------- ------ +// SV_Position 0 xyzw 0 POS float xyzw +// +vs_5_0 +dcl_globalFlags refactoringAllowed +dcl_constantbuffer cb0[4], immediateIndexed +dcl_input_sgv v0.x, vertex_id +dcl_output_siv o0.xyzw, position +dcl_temps 1 +dcl_indexableTemp x0[8], 4 +dcl_indexableTemp x1[36], 4 +mov x0[0].xyz, l(-1.000000,-1.000000,1.000000,0) +mov x0[1].xyz, l(-1.000000,-1.000000,-1.000000,0) +mov x0[2].xyz, l(1.000000,-1.000000,-1.000000,0) +mov x0[3].xyz, l(1.000000,-1.000000,1.000000,0) +mov x0[4].xyz, l(-1.000000,1.000000,1.000000,0) +mov x0[5].xyz, l(1.000000,1.000000,1.000000,0) +mov x0[6].xyz, l(1.000000,1.000000,-1.000000,0) +mov x0[7].xyz, l(-1.000000,1.000000,-1.000000,0) +mov x1[0].x, l(1) +mov x1[1].x, l(2) +mov x1[2].x, l(3) +mov x1[3].x, l(3) +mov x1[4].x, l(4) +mov x1[5].x, l(1) +mov x1[6].x, l(5) +mov x1[7].x, l(6) +mov x1[8].x, l(7) +mov x1[9].x, l(7) +mov x1[10].x, l(8) +mov x1[11].x, l(5) +mov x1[12].x, l(1) +mov x1[13].x, l(4) +mov x1[14].x, l(6) +mov x1[15].x, l(6) +mov x1[16].x, l(5) +mov x1[17].x, l(1) +mov x1[18].x, l(4) +mov x1[19].x, l(3) +mov x1[20].x, l(7) +mov x1[21].x, l(7) +mov x1[22].x, l(6) +mov x1[23].x, l(4) +mov x1[24].x, l(3) +mov x1[25].x, l(2) +mov x1[26].x, l(8) +mov x1[27].x, l(8) +mov x1[28].x, l(7) +mov x1[29].x, l(3) +mov x1[30].x, l(2) +mov x1[31].x, l(1) +mov x1[32].x, l(5) +mov x1[33].x, l(5) +mov x1[34].x, l(8) +mov x1[35].x, l(2) +mov r0.x, v0.x +mov r0.x, x1[r0.x + 0].x +iadd r0.x, r0.x, l(-1) +mov r0.xyz, x0[r0.x + 0].xyzx +mov r0.w, l(1.000000) +dp4 o0.x, r0.xyzw, cb0[0].xyzw +dp4 o0.y, r0.xyzw, cb0[1].xyzw +dp4 o0.z, r0.xyzw, cb0[2].xyzw +dp4 o0.w, r0.xyzw, cb0[3].xyzw +ret +// Approximately 54 instruction slots used +#endif + +const BYTE VS_UNIT_CUBE_Data[] = +{ + 68, 88, 66, 67, 72, 187, + 2, 99, 129, 37, 9, 199, + 62, 25, 130, 69, 209, 161, + 214, 95, 1, 0, 0, 0, + 8, 9, 0, 0, 5, 0, + 0, 0, 52, 0, 0, 0, + 24, 2, 0, 0, 76, 2, + 0, 0, 128, 2, 0, 0, + 108, 8, 0, 0, 82, 68, + 69, 70, 220, 1, 0, 0, + 1, 0, 0, 0, 116, 0, + 0, 0, 1, 0, 0, 0, + 60, 0, 0, 0, 0, 5, + 254, 255, 0, 1, 0, 0, + 168, 1, 0, 0, 82, 68, + 49, 49, 60, 0, 0, 0, + 24, 0, 0, 0, 32, 0, + 0, 0, 40, 0, 0, 0, + 36, 0, 0, 0, 12, 0, + 0, 0, 0, 0, 0, 0, + 92, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 67, 66, 95, 85, + 78, 73, 84, 95, 67, 85, + 66, 69, 95, 84, 82, 65, + 78, 83, 70, 79, 82, 77, + 0, 171, 92, 0, 0, 0, + 1, 0, 0, 0, 140, 0, + 0, 0, 208, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 180, 0, 0, 0, + 0, 0, 0, 0, 208, 0, + 0, 0, 2, 0, 0, 0, + 132, 1, 0, 0, 0, 0, + 0, 0, 255, 255, 255, 255, + 0, 0, 0, 0, 255, 255, + 255, 255, 0, 0, 0, 0, + 103, 95, 85, 110, 105, 116, + 67, 117, 98, 101, 84, 114, + 97, 110, 115, 102, 111, 114, + 109, 0, 85, 110, 105, 116, + 67, 117, 98, 101, 84, 114, + 97, 110, 115, 102, 111, 114, + 109, 0, 109, 95, 116, 114, + 0, 102, 108, 111, 97, 116, + 52, 120, 52, 0, 3, 0, + 3, 0, 4, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 223, 0, 0, 0, 109, 95, + 105, 110, 118, 101, 114, 115, + 101, 0, 109, 95, 102, 111, + 114, 119, 97, 114, 100, 0, + 109, 95, 99, 111, 108, 111, + 114, 0, 102, 108, 111, 97, + 116, 52, 0, 171, 1, 0, + 3, 0, 1, 0, 4, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 40, 1, 0, 0, 218, 0, + 0, 0, 232, 0, 0, 0, + 0, 0, 0, 0, 12, 1, + 0, 0, 232, 0, 0, 0, + 64, 0, 0, 0, 22, 1, + 0, 0, 232, 0, 0, 0, + 128, 0, 0, 0, 32, 1, + 0, 0, 48, 1, 0, 0, + 192, 0, 0, 0, 5, 0, + 0, 0, 1, 0, 52, 0, + 0, 0, 4, 0, 84, 1, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 200, 0, 0, 0, 77, 105, + 99, 114, 111, 115, 111, 102, + 116, 32, 40, 82, 41, 32, + 72, 76, 83, 76, 32, 83, + 104, 97, 100, 101, 114, 32, + 67, 111, 109, 112, 105, 108, + 101, 114, 32, 54, 46, 51, + 46, 57, 54, 48, 48, 46, + 49, 54, 51, 56, 52, 0, + 171, 171, 73, 83, 71, 78, + 44, 0, 0, 0, 1, 0, + 0, 0, 8, 0, 0, 0, + 32, 0, 0, 0, 0, 0, + 0, 0, 6, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 1, 0, 0, + 83, 86, 95, 86, 69, 82, + 84, 69, 88, 73, 68, 0, + 79, 83, 71, 78, 44, 0, + 0, 0, 1, 0, 0, 0, + 8, 0, 0, 0, 32, 0, + 0, 0, 0, 0, 0, 0, + 1, 0, 0, 0, 3, 0, + 0, 0, 0, 0, 0, 0, + 15, 0, 0, 0, 83, 86, + 95, 80, 111, 115, 105, 116, + 105, 111, 110, 0, 83, 72, + 69, 88, 228, 5, 0, 0, + 80, 0, 1, 0, 121, 1, + 0, 0, 106, 8, 0, 1, + 89, 0, 0, 4, 70, 142, + 32, 0, 0, 0, 0, 0, + 4, 0, 0, 0, 96, 0, + 0, 4, 18, 16, 16, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 103, 0, 0, 4, + 242, 32, 16, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 104, 0, 0, 2, 1, 0, + 0, 0, 105, 0, 0, 4, + 0, 0, 0, 0, 8, 0, + 0, 0, 4, 0, 0, 0, + 105, 0, 0, 4, 1, 0, + 0, 0, 36, 0, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 191, 0, 0, 128, 63, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 1, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 191, 0, 0, 128, 191, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 191, 0, 0, 128, 191, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 3, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 191, 0, 0, 128, 63, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 4, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 63, 0, 0, 128, 63, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 5, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 63, 0, 0, 128, 63, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 6, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 63, 0, 0, + 128, 63, 0, 0, 128, 191, + 0, 0, 0, 0, 54, 0, + 0, 9, 114, 48, 32, 0, + 0, 0, 0, 0, 7, 0, + 0, 0, 2, 64, 0, 0, + 0, 0, 128, 191, 0, 0, + 128, 63, 0, 0, 128, 191, + 0, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 1, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 2, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 3, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 4, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 5, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 6, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 7, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 8, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 9, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 10, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 11, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 12, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 13, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 14, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 15, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 16, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 17, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 18, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 19, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 20, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 21, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 22, 0, + 0, 0, 1, 64, 0, 0, + 6, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 23, 0, + 0, 0, 1, 64, 0, 0, + 4, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 24, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 25, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 26, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 27, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 28, 0, + 0, 0, 1, 64, 0, 0, + 7, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 29, 0, + 0, 0, 1, 64, 0, 0, + 3, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 30, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 31, 0, + 0, 0, 1, 64, 0, 0, + 1, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 32, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 33, 0, + 0, 0, 1, 64, 0, 0, + 5, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 34, 0, + 0, 0, 1, 64, 0, 0, + 8, 0, 0, 0, 54, 0, + 0, 6, 18, 48, 32, 0, + 1, 0, 0, 0, 35, 0, + 0, 0, 1, 64, 0, 0, + 2, 0, 0, 0, 54, 0, + 0, 5, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 16, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 7, 18, 0, + 16, 0, 0, 0, 0, 0, + 10, 48, 32, 4, 1, 0, + 0, 0, 10, 0, 16, 0, + 0, 0, 0, 0, 30, 0, + 0, 7, 18, 0, 16, 0, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 255, 255, + 255, 255, 54, 0, 0, 7, + 114, 0, 16, 0, 0, 0, + 0, 0, 70, 50, 32, 4, + 0, 0, 0, 0, 10, 0, + 16, 0, 0, 0, 0, 0, + 54, 0, 0, 5, 130, 0, + 16, 0, 0, 0, 0, 0, + 1, 64, 0, 0, 0, 0, + 128, 63, 17, 0, 0, 8, + 18, 32, 16, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 0, 0, 0, 0, 70, 142, + 32, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 17, 0, + 0, 8, 34, 32, 16, 0, + 0, 0, 0, 0, 70, 14, + 16, 0, 0, 0, 0, 0, + 70, 142, 32, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 17, 0, 0, 8, 66, 32, + 16, 0, 0, 0, 0, 0, + 70, 14, 16, 0, 0, 0, + 0, 0, 70, 142, 32, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 17, 0, 0, 8, + 130, 32, 16, 0, 0, 0, + 0, 0, 70, 14, 16, 0, + 0, 0, 0, 0, 70, 142, + 32, 0, 0, 0, 0, 0, + 3, 0, 0, 0, 62, 0, + 0, 1, 83, 84, 65, 84, + 148, 0, 0, 0, 54, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 2, 0, + 0, 0, 4, 0, 0, 0, + 1, 0, 0, 0, 0, 0, + 0, 0, 1, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 44, 0, 0, 0, + 46, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 2, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, + 0, 0 +}; diff --git a/src/DX11/framework/amd_sdk/CMakeLists.txt b/src/DX11/framework/amd_sdk/CMakeLists.txt new file mode 100644 index 0000000..757af03 --- /dev/null +++ b/src/DX11/framework/amd_sdk/CMakeLists.txt @@ -0,0 +1,35 @@ +# This file is part of the FidelityFX SDK. +# +# Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +file(GLOB_RECURSE AMD_SDK_SOURCES *.cpp) +file(GLOB_RECURSE AMD_SDK_HEADERS *.h) + +set(amd_sdk_minimal_shaders + ${CMAKE_CURRENT_SOURCE_DIR}/src/Shaders/Line.hlsl + ${CMAKE_CURRENT_SOURCE_DIR}/src/Shaders/Sprite.hlsl +) + +copyCommand("${amd_sdk_minimal_shaders}" ${CMAKE_HOME_DIRECTORY}/bin/ShaderLibDX/dx11) +add_library(amd_sdk_minimal ${AMD_SDK_SOURCES} ${AMD_SDK_HEADERS} ${amd_sdk_minimal_shaders}) +target_include_directories(amd_sdk_minimal PUBLIC inc) +target_compile_definitions(amd_sdk_minimal PRIVATE AMD_SDK_MINIMAL _UNICODE UNICODE) +target_link_libraries(amd_sdk_minimal PUBLIC DXUT DXUTOpt) + diff --git a/src/DX11/framework/amd_sdk/inc/AMD_SDK.h b/src/DX11/framework/amd_sdk/inc/AMD_SDK.h new file mode 100644 index 0000000..b98b673 --- /dev/null +++ b/src/DX11/framework/amd_sdk/inc/AMD_SDK.h @@ -0,0 +1,74 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: AMD_SDK.h +// +// Library include file, to drag in all AMD SDK helper classes and functions. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_H +#define AMD_SDK_H + +#define VENDOR_ID_AMD (0x1002) +#define VENDOR_ID_NVIDIA (0x10DE) +#define VENDOR_ID_INTEL (0x8086) + +// DXUT helper code +#include "DXUT.h" +#include "DXUTmisc.h" +#include "DXUTgui.h" +#include "SDKmisc.h" +#include "SDKMesh.h" + +// AMD helper classes and functions +#include "..\\src\\Timer.h" +#include "..\\src\\ShaderCache.h" +#include "..\\src\\HelperFunctions.h" +#include "..\\src\\Sprite.h" +#include "..\\src\\Magnify.h" +#include "..\\src\\MagnifyTool.h" +#include "..\\src\\HUD.h" +#include "..\\src\\Geometry.h" +#include "..\\src\\LineRender.h" +#include "..\\src\\AMD_Mesh.h" + +#ifndef ARRAYSIZE +#define ARRAYSIZE(A) (sizeof(A)/sizeof((A)[0])) +#endif + +// Profile helpers for timing and marking up as D3D perf blocks +#define AMD_PROFILE_RED D3DCOLOR_XRGB( 255, 0, 0 ) +#define AMD_PROFILE_GREEN D3DCOLOR_XRGB( 0, 255, 0 ) +#define AMD_PROFILE_BLUE D3DCOLOR_XRGB( 0, 0, 255 ) + +#define AMDProfileBegin( col, name ) DXUT_BeginPerfEvent( col, name ); TIMER_Begin( col, name ) +#define AMDProfileEnd() TIMER_End() DXUT_EndPerfEvent(); + +struct AMDProfileEventClass +{ + AMDProfileEventClass( unsigned int col, LPCWSTR name ) { AMDProfileBegin( col, name ); } + ~AMDProfileEventClass() { AMDProfileEnd() } +}; + +#define AMDProfileEvent( col, name ) AMDProfileEventClass _amd_profile_event( col, name ) + +#endif // AMD_SDK_H diff --git a/src/DX11/framework/amd_sdk/inc/ShaderCacheSampleHelper.h b/src/DX11/framework/amd_sdk/inc/ShaderCacheSampleHelper.h new file mode 100644 index 0000000..1710277 --- /dev/null +++ b/src/DX11/framework/amd_sdk/inc/ShaderCacheSampleHelper.h @@ -0,0 +1,77 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: ShaderCacheSampleHelper.h +// +// Helpers to implement the DXUT related ShaderCache interface in samples. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_SHADER_CACHE_SAMPLE_HELPER_H +#define AMD_SDK_SHADER_CACHE_SAMPLE_HELPER_H + + +class CDXUTControl; +class CDXUTTextHelper; +typedef long HRESULT; +typedef unsigned int UINT; + +namespace AMD +{ + + class HUD; + class ShaderCache; + + //-------------------------------------------------------------------------------------- + // UI control IDs + //-------------------------------------------------------------------------------------- + extern const int g_MaxApplicationControlID; + + enum SHADER_CACHE_SAMPLE_HELPER_IDC + { + AMD_IDC_START = 0, + AMD_IDC_BUTTON_SHOW_SHADERCACHE_UI = AMD_IDC_START, + AMD_IDC_BUTTON_RECOMPILESHADERS_CHANGED, + AMD_IDC_BUTTON_RECOMPILESHADERS_GLOBAL, + AMD_IDC_BUTTON_RECREATE_SHADERS, + AMD_IDC_CHECKBOX_AUTORECOMPILE_SHADERS, + AMD_IDC_CHECKBOX_SHOW_SHADER_ERRORS, + AMD_IDC_CHECKBOX_SHOW_ISA_GPR_PRESSURE, + AMD_IDC_STATIC_TARGET_ISA, + AMD_IDC_STATIC_TARGET_ISA_INFO, + AMD_IDC_COMBOBOX_TARGET_ISA, + AMD_IDC_END + }; + + template< typename T > + T GetEnum( T i_AMDEnum ) + { + return static_cast< T > ( g_MaxApplicationControlID + i_AMDEnum ); + } + + void InitApp( ShaderCache& r_ShaderCache, HUD& r_HUD, int& iY, const bool i_bAdvancedShaderCacheGUI_VisibleByDefault = false ); + void ProcessUIChanges(); + void RenderHUDUpdates( CDXUTTextHelper* i_pTxtHelper ); + void __stdcall OnGUIEvent( UINT nEvent, int nControlID, CDXUTControl* pControl, void* pUserContext ); + +} // namespace AMD + +#endif diff --git a/src/DX11/framework/amd_sdk/media/AMD.dds b/src/DX11/framework/amd_sdk/media/AMD.dds new file mode 100644 index 0000000..2d8e012 Binary files /dev/null and b/src/DX11/framework/amd_sdk/media/AMD.dds differ diff --git a/src/DX11/framework/amd_sdk/media/AMD.ico b/src/DX11/framework/amd_sdk/media/AMD.ico new file mode 100644 index 0000000..97da20f Binary files /dev/null and b/src/DX11/framework/amd_sdk/media/AMD.ico differ diff --git a/src/DX11/framework/amd_sdk/media/AMD_FidelityFX.dds b/src/DX11/framework/amd_sdk/media/AMD_FidelityFX.dds new file mode 100644 index 0000000..c2e8366 Binary files /dev/null and b/src/DX11/framework/amd_sdk/media/AMD_FidelityFX.dds differ diff --git a/src/DX11/framework/amd_sdk/src/AMD_Mesh.cpp b/src/DX11/framework/amd_sdk/src/AMD_Mesh.cpp new file mode 100644 index 0000000..ff1edf5 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/AMD_Mesh.cpp @@ -0,0 +1,280 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +// DXUT helper code +#include "DXUT.h" +#include "DXUTmisc.h" +#include "SDKmisc.h" +#include "SDKmesh.h" + +#include "AMD_Mesh.h" + +#include + +#ifndef AMD_SDK_MINIMAL +#include "assimp/scene.h" +#include "assimp/importer.hpp" +#include "DDSTextureLoader.h" +#include "crc.h" +#endif + +#pragma warning (disable : 4996) + +namespace AMD +{ +Mesh::Mesh() + : _vertex(NULL) + , _index(NULL) + , _id(0) +{ + memcpy(_name, "default", sizeof("default")); +} + +Mesh::~Mesh() +{ + Release(); +} + +HRESULT Mesh::Create(ID3D11Device * pDevice, const char * path, const char * name, bool sdkmesh) +{ + m_isSdkMesh = sdkmesh; + + if (sdkmesh) + { + char filename[256]; + sprintf(filename, "%s%s", path, name); + std::string fname(filename); + std::wstring wfname(fname.begin(), fname.end()); + + return m_sdkMesh.Create(pDevice, wfname.c_str(), false); + } +#ifdef AMD_SDK_MINIMAL + else + { + // the minimal-dependencies version of AMD_SDK + // only supports sdkmesh + return E_FAIL; + } +#else + HRESULT hr = S_OK; + Assimp::Importer importer; + int num_vertices = 0; + int num_faces = 0; + + std::string filename = std::string(path) + std::string(name); + + aiScene* scene = (aiScene*)importer.ReadFile(filename.c_str(), 0); + + if (!scene) { return E_FAIL; } + + _id = crcFast((const unsigned char *)filename.c_str(), (int)filename.length()); + + if (scene->HasMeshes() && scene->mNumMeshes > 0) + { + for (int i = 0; i < (int)scene->mNumMeshes; i++) + { + num_vertices += scene->mMeshes[i]->mNumVertices; + num_faces += scene->mMeshes[i]->mNumFaces; + } + + if (num_vertices == 0 || num_faces == 0) { return S_OK; } + + int current_vertex = 0; + int current_face = 0; + + _material_group.resize(scene->mNumMeshes); + _vertex.resize(num_vertices); + _index.resize(num_faces * 3); + + ID3D11DeviceContext * pContext = NULL; + pDevice->GetImmediateContext(&pContext); + + for (unsigned int i = 0; i < scene->mNumMeshes; i++) + { + ID3D11Texture2D * t2d = NULL; + ID3D11ShaderResourceView * srv = NULL; + + aiMesh * mesh = scene->mMeshes[i]; + aiMaterial * material = scene->mMaterials[mesh->mMaterialIndex]; + aiString c_texture_filename; + material->Get(AI_MATKEY_TEXTURE_DIFFUSE(0), c_texture_filename); + + std::string tex_filename = std::string(path) + std::string(c_texture_filename.C_Str()); + { + WCHAR wc_texture_filename[1024]; + mbstowcs(wc_texture_filename, tex_filename.c_str(), tex_filename.length() + 1); + + unsigned int bind_flags = D3D11_BIND_SHADER_RESOURCE; + hr = DirectX::CreateDDSTextureFromFileEx(pDevice, wc_texture_filename, 0, D3D11_USAGE_DEFAULT, bind_flags, 0, 0, true, (ID3D11Resource**)&t2d, &srv); + } + + _material_group[i]._texture_index = (int)_t2d.size(); + _t2d.push_back(t2d); + _srv.push_back(srv); + + _material_group[i]._first_index = current_face; + _material_group[i]._index_count = mesh->mNumFaces * 3; + + aiVector3D * position = mesh->HasPositions() ? mesh->mVertices : NULL; + aiVector3D * normal = mesh->HasNormals() ? mesh->mNormals : NULL; + aiVector3D * uv = mesh->HasTextureCoords(0) ? mesh->mTextureCoords[0] : NULL; + + for (unsigned int j = 0; j < mesh->mNumVertices; j++) + { + if (position != NULL) + { + memcpy( &_vertex[current_vertex + j].position, &position[j], sizeof( float ) * 3 ); + } + + if (normal != NULL) + { + memcpy( &_vertex[current_vertex + j].normal, &normal[j], sizeof( float ) * 3 ); + } + + if (uv != NULL) + { + memcpy( &_vertex[current_vertex + j].uv, &uv[j], sizeof( float ) * 2 ); + } + } + + if (mesh->HasFaces()) + { + aiFace * f = mesh->mFaces; + for (unsigned int j = 0; j < mesh->mNumFaces; j++) + { + _index[current_face + j * 3 + 0] = current_vertex + f[j].mIndices[0]; + _index[current_face + j * 3 + 1] = current_vertex + f[j].mIndices[1]; + _index[current_face + j * 3 + 2] = current_vertex + f[j].mIndices[2]; + } + } + + current_face += mesh->mNumFaces * 3; + current_vertex += mesh->mNumVertices; + } + + AMD_SAFE_RELEASE(pContext); + + CD3D11_BUFFER_DESC vertexDesc, indexDesc; + vertexDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER | D3D11_BIND_SHADER_RESOURCE; + vertexDesc.ByteWidth = sizeof(Vertex) * num_vertices; + vertexDesc.CPUAccessFlags = 0; + vertexDesc.MiscFlags = 0; + vertexDesc.StructureByteStride = 0; + vertexDesc.Usage = D3D11_USAGE_IMMUTABLE; + indexDesc.BindFlags = D3D11_BIND_INDEX_BUFFER; + indexDesc.ByteWidth = sizeof(int) * num_faces * 3; + indexDesc.CPUAccessFlags = 0; + indexDesc.MiscFlags = 0; + indexDesc.StructureByteStride = 0; + indexDesc.Usage = D3D11_USAGE_IMMUTABLE; + + D3D11_SUBRESOURCE_DATA vertexData, indexData; + memset(&vertexData, 0, sizeof(vertexData)); + memset(&indexData, 0, sizeof(indexData)); + + vertexData.pSysMem = &_vertex[0]; + indexData.pSysMem = &_index[0]; + + hr = pDevice->CreateBuffer(&vertexDesc, &vertexData, &_b1d_vertex); + hr = pDevice->CreateBuffer(&indexDesc, &indexData, &_b1d_index); + } + + return hr; +#endif +} + +HRESULT Mesh::Render(ID3D11DeviceContext * pContext) +{ + if (m_isSdkMesh) + { + m_sdkMesh.Render(pContext, 0); + return S_OK; + } +#ifdef AMD_SDK_MINIMAL + else + { + // the minimal-dependencies version of AMD_SDK + // only supports sdkmesh + return E_FAIL; + } +#else + unsigned int stride = sizeof(Vertex), offset = 0; + pContext->IASetIndexBuffer(_b1d_index, DXGI_FORMAT_R32_UINT, 0); + pContext->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST); + pContext->IASetVertexBuffers(0, 1, &_b1d_vertex, &stride, &offset); + + for (unsigned int i = 0; i < _material_group.size(); i++) + { + pContext->PSSetShaderResources(0, 1, &_srv[_material_group[i]._texture_index]); + + pContext->DrawIndexed(_material_group[i]._index_count, _material_group[i]._first_index, 0); + } + + return S_OK; +#endif +} + +HRESULT Mesh::Release() +{ + if (m_isSdkMesh) + { + m_sdkMesh.Destroy(); + return S_OK; + } +#ifdef AMD_SDK_MINIMAL + else + { + // the minimal-dependencies version of AMD_SDK + // only supports sdkmesh + return E_FAIL; + } +#else + AMD_SAFE_RELEASE(_b1d_vertex); + AMD_SAFE_RELEASE(_b1d_index); + + for (unsigned int i = 0; i < _t2d.size(); i++) + { + AMD_SAFE_RELEASE(_t2d[i]); + AMD_SAFE_RELEASE(_srv[i]); + } + _t2d.clear(); + _srv.clear(); + + return S_OK; +#endif +} + +ID3D11ShaderResourceView ** Mesh::srv() +{ +#ifndef AMD_SDK_MINIMAL + if (_srv.size()) + { + return &_srv[0]; + } + else +#endif + { + return NULL; + } +} + +} // namespace AMD diff --git a/src/DX11/framework/amd_sdk/src/AMD_Mesh.h b/src/DX11/framework/amd_sdk/src/AMD_Mesh.h new file mode 100644 index 0000000..f04573b --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/AMD_Mesh.h @@ -0,0 +1,94 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: AMD_Mesh.h +// +// Convenience wrapper for loading and drawing models with Assimp or DXUT sdkmesh. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_MESH_H +#define AMD_SDK_MESH_H + +#include +#include + +#ifndef AMD_SAFE_RELEASE +#define AMD_SAFE_RELEASE(p) { if (p) { p->Release(); p = NULL; } } +#endif + +class CDXUTSDKMesh; + +namespace AMD +{ +class Mesh +{ + ID3D11Buffer * _b1d_vertex; + ID3D11Buffer * _b1d_index; + std::vector _t2d; + + struct MaterialGroup + { + int _first_index; + int _index_count; + int _texture_index; + + MaterialGroup() + : _first_index(0) + , _index_count(0) + , _texture_index(0) + {} + }; + + struct Vertex + { + float position[3]; + float normal[3]; + float uv[2]; + }; + + std::vector _material_group; + + char _name[128]; + int _id; + +public: + CDXUTSDKMesh m_sdkMesh; + bool m_isSdkMesh; + + Mesh(); + ~Mesh(); + + std::vector _vertex; + std::vector _index; + std::vector _srv; + + HRESULT Create(ID3D11Device * pDevice, const char * path, const char * name, bool sdkmesh = false); + + HRESULT Render(ID3D11DeviceContext * pContext); + HRESULT Release(); + + ID3D11ShaderResourceView ** srv(); +}; + +} // namespace AMD + +#endif diff --git a/src/DX11/framework/amd_sdk/src/Geometry.cpp b/src/DX11/framework/amd_sdk/src/Geometry.cpp new file mode 100644 index 0000000..e121f35 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Geometry.cpp @@ -0,0 +1,105 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: Geometry.cpp +// +// Classes for geometric primitives and collision and visibility testing +//-------------------------------------------------------------------------------------- +#include "DXUT.h" +#include "Geometry.h" + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +// Helper function to normalize a plane +//-------------------------------------------------------------------------------------- +static void NormalizePlane( XMFLOAT4* pPlaneEquation ) +{ + float mag; + + mag = sqrtf( pPlaneEquation->x * pPlaneEquation->x + + pPlaneEquation->y * pPlaneEquation->y + + pPlaneEquation->z * pPlaneEquation->z ); + + pPlaneEquation->x = pPlaneEquation->x / mag; + pPlaneEquation->y = pPlaneEquation->y / mag; + pPlaneEquation->z = pPlaneEquation->z / mag; + pPlaneEquation->w = pPlaneEquation->w / mag; +} + + +//-------------------------------------------------------------------------------------- +// Extract all 6 plane equations from frustum denoted by supplied matrix +//-------------------------------------------------------------------------------------- +void ExtractPlanesFromFrustum( XMFLOAT4* pPlaneEquation, const XMMATRIX* pMatrix, bool bNormalize ) +{ + XMFLOAT4X4 TempMat; + XMStoreFloat4x4( &TempMat, *pMatrix); + + // Left clipping plane + pPlaneEquation[0].x = TempMat._14 + TempMat._11; + pPlaneEquation[0].y = TempMat._24 + TempMat._21; + pPlaneEquation[0].z = TempMat._34 + TempMat._31; + pPlaneEquation[0].w = TempMat._44 + TempMat._41; + + // Right clipping plane + pPlaneEquation[1].x = TempMat._14 - TempMat._11; + pPlaneEquation[1].y = TempMat._24 - TempMat._21; + pPlaneEquation[1].z = TempMat._34 - TempMat._31; + pPlaneEquation[1].w = TempMat._44 - TempMat._41; + + // Top clipping plane + pPlaneEquation[2].x = TempMat._14 - TempMat._12; + pPlaneEquation[2].y = TempMat._24 - TempMat._22; + pPlaneEquation[2].z = TempMat._34 - TempMat._32; + pPlaneEquation[2].w = TempMat._44 - TempMat._42; + + // Bottom clipping plane + pPlaneEquation[3].x = TempMat._14 + TempMat._12; + pPlaneEquation[3].y = TempMat._24 + TempMat._22; + pPlaneEquation[3].z = TempMat._34 + TempMat._32; + pPlaneEquation[3].w = TempMat._44 + TempMat._42; + + // Near clipping plane + pPlaneEquation[4].x = TempMat._13; + pPlaneEquation[4].y = TempMat._23; + pPlaneEquation[4].z = TempMat._33; + pPlaneEquation[4].w = TempMat._43; + + // Far clipping plane + pPlaneEquation[5].x = TempMat._14 - TempMat._13; + pPlaneEquation[5].y = TempMat._24 - TempMat._23; + pPlaneEquation[5].z = TempMat._34 - TempMat._33; + pPlaneEquation[5].w = TempMat._44 - TempMat._43; + + // Normalize the plane equations, if requested + if ( bNormalize ) + { + NormalizePlane( &pPlaneEquation[0] ); + NormalizePlane( &pPlaneEquation[1] ); + NormalizePlane( &pPlaneEquation[2] ); + NormalizePlane( &pPlaneEquation[3] ); + NormalizePlane( &pPlaneEquation[4] ); + NormalizePlane( &pPlaneEquation[5] ); + } +} diff --git a/src/DX11/framework/amd_sdk/src/Geometry.h b/src/DX11/framework/amd_sdk/src/Geometry.h new file mode 100644 index 0000000..a6e9894 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Geometry.h @@ -0,0 +1,36 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: Geometry.h +// +// Classes for geometric primitives and collision and visibility testing. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_GEOMETRY_H +#define AMD_SDK_GEOMETRY_H + +namespace AMD +{ + void ExtractPlanesFromFrustum( DirectX::XMFLOAT4* pPlaneEquation, const DirectX::XMMATRIX* pMatrix, bool bNormalize = true ); +} + +#endif diff --git a/src/DX11/framework/amd_sdk/src/HUD.cpp b/src/DX11/framework/amd_sdk/src/HUD.cpp new file mode 100644 index 0000000..e145cb8 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/HUD.cpp @@ -0,0 +1,201 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: HUD.cpp +// +// Class definition for the AMD standard HUD interface. +//-------------------------------------------------------------------------------------- + +// DXUT helper code +#include "DXUT.h" +#include "DXUTmisc.h" +#include "DXUTgui.h" +#include "SDKmisc.h" +#include "DDSTextureLoader.h" + +#include "HUD.h" + +using namespace AMD; + +//-------------------------------------------------------------------------------------- +// Constructor +//-------------------------------------------------------------------------------------- +HUD::HUD() +{ + m_pLogoSRV = NULL; +} + + +//-------------------------------------------------------------------------------------- +// Destructor +//-------------------------------------------------------------------------------------- +HUD::~HUD() +{ + SAFE_RELEASE( m_pLogoSRV ); +} + + +//-------------------------------------------------------------------------------------- +// Device creation hook function, that loads the AMD logo texture, and creates a sprite +// object +//-------------------------------------------------------------------------------------- +HRESULT HUD::OnCreateDevice( ID3D11Device* pd3dDevice ) +{ + HRESULT hr; + wchar_t str[MAX_PATH]; + + m_Sprite.OnCreateDevice( pd3dDevice ); + + V_RETURN( DXUTFindDXSDKMediaFileCch( str, MAX_PATH, L"dx11\\UI\\AMD_FidelityFX.dds" ) ); + DirectX::CreateDDSTextureFromFile( pd3dDevice, str, nullptr, &m_pLogoSRV ); + DXUT_SetDebugName( m_pLogoSRV, "AMD_FidelityFX.dds" ); + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Device destruction hook function, that releases the sprite object and +//-------------------------------------------------------------------------------------- +void HUD::OnDestroyDevice() +{ + m_Sprite.OnDestroyDevice(); + + SAFE_RELEASE( m_pLogoSRV ); +} + + +//-------------------------------------------------------------------------------------- +// Resize swap chain hook function, that passes through to the sprite object +//-------------------------------------------------------------------------------------- +void HUD::OnResizedSwapChain( const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ) +{ + m_Sprite.OnResizedSwapChain( pBackBufferSurfaceDesc ); +} + + +//-------------------------------------------------------------------------------------- +// Render hook function, that calls the CDXUTDialog::OnRender method, and additionally +// renders the AMD sprite +//-------------------------------------------------------------------------------------- +void HUD::OnRender( float fElapsedTime ) +{ + m_GUI.OnRender( fElapsedTime ); + m_Sprite.RenderSprite( m_pLogoSRV, DXUTGetDXGIBackBufferSurfaceDesc()->Width - 220, DXUTGetDXGIBackBufferSurfaceDesc()->Height - 2, 200, 75, true, false ); +} + + +Slider::Slider( CDXUTDialog& dialog, int id, int& y, const wchar_t* label, int min, int max, int& value ) : +m_Value( value ), +m_szLabel( label ), +m_ValueFloat( (float &)value ) +{ + dialog.AddStatic( id + 1000000, L"", AMD::HUD::iElementOffset, y += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, false, &m_pLabel ); + dialog.AddSlider( id, AMD::HUD::iElementOffset, y += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, min, max, m_Value, false, &m_pSlider ); + + dialog.AddControl( this ); + + m_Min = min; + m_Max = max; + + m_UseFloat = false; + OnGuiEvent(); +} + + +Slider::Slider( CDXUTDialog& dialog, int id, int& y, const wchar_t* label, float min, float max, float step, float& value ) : +m_ValueFloat( value ), +m_MinFloat( min ), +m_MaxFloat( max ), +m_szLabel( label ), +m_Value( (int &)value ) +{ + m_Min = 0; + m_Max = (int)((m_MaxFloat - m_MinFloat) / step + 0.499f); + + int slider_value = (int)((m_ValueFloat - m_MinFloat) / (m_MaxFloat - m_MinFloat) * m_Max + 0.499f); + dialog.AddStatic( id + 1000000, L"", AMD::HUD::iElementOffset, y += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, false, &m_pLabel ); + dialog.AddSlider( id, AMD::HUD::iElementOffset, y += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, m_Min, m_Max, slider_value, false, &m_pSlider ); + + dialog.AddControl( this ); + + m_UseFloat = true; + OnGuiEvent(); +} + + +void Slider::OnGuiEvent() +{ + if (m_UseFloat) + { + m_ValueFloat = (m_MaxFloat - m_MinFloat) * ((float)m_pSlider->GetValue() / m_Max) + m_MinFloat; + } + else + { + m_Value = m_pSlider->GetValue(); + } + + wchar_t buff[1024]; + if (m_UseFloat) + { + swprintf_s( buff, 1024, L"%s: %f", m_szLabel, m_ValueFloat ); + } + else + { + swprintf_s( buff, 1024, L"%s: %d", m_szLabel, m_Value ); + } + + m_pLabel->SetText( buff ); +} + + +void Slider::SetEnabled( bool enable ) +{ + m_pLabel->SetEnabled( enable ); + m_pSlider->SetEnabled( enable ); +} + + +void Slider::SetVisible( bool visible ) +{ + m_pLabel->SetVisible( visible ); + m_pSlider->SetVisible( visible ); +} + + +void Slider::SetValue( int value ) +{ + if (m_UseFloat == true) { return; } + m_pSlider->SetValue( value ); + OnGuiEvent(); +} + +void Slider::SetValue( float value ) +{ + if (m_UseFloat != true) { return; } + + int slider_value = (int)((value - m_MinFloat) / (m_MaxFloat - m_MinFloat) * m_Max + 0.499f); + + m_pSlider->SetValue( (int)slider_value ); + OnGuiEvent(); +} diff --git a/src/DX11/framework/amd_sdk/src/HUD.h b/src/DX11/framework/amd_sdk/src/HUD.h new file mode 100644 index 0000000..b58ff26 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/HUD.h @@ -0,0 +1,102 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: HUD.h +// +// Class definition for the AMD standard HUD interface. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_HUD_H +#define AMD_SDK_HUD_H + +#include "Sprite.h" + +namespace AMD +{ + +class HUD +{ +public: + + // AMD standard HUD defines for GUI spacing + static const int iElementDelta = 25; + static const int iGroupDelta = ( iElementDelta * 2 ); + static const int iDialogWidth = 250; + static const int iElementHeight = 24; + static const int iElementWidth = 170; + static const int iElementOffset = ( iDialogWidth - iElementWidth ) / 2; + static const int iElementDropHeight = 35; + + // Public access to the CDXUTDialog is allowed for ease of use in the sample + CDXUTDialog m_GUI; + + // Constructor / destructor + HUD(); + ~HUD(); + + // Various hook functions + HRESULT OnCreateDevice( ID3D11Device* pd3dDevice ); + void OnDestroyDevice(); + void OnResizedSwapChain( const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ); + void OnRender( float fElapsedTime ); + +private: + + // The private AMD logo texture, and sprite object + Sprite m_Sprite; + ID3D11ShaderResourceView* m_pLogoSRV; +}; + + +class Slider : public CDXUTControl +{ +public: + + Slider( CDXUTDialog& dialog, int id, int& y, const wchar_t* label, int min, int max, int& value ); + Slider( CDXUTDialog& dialog, int id, int& y, const wchar_t* label, float min, float max, float step, float& value ); + virtual ~Slider() {} + + void OnGuiEvent(); + void SetEnabled( bool enable ); + void SetVisible( bool visible ); + void SetValue( int value ); + void SetValue( float value ); + +private: + + Slider& operator=( const Slider& ); + + int m_Min, m_Max; + float m_MinFloat, m_MaxFloat; + + bool m_UseFloat; + int& m_Value; + float& m_ValueFloat; + + const wchar_t* m_szLabel; + CDXUTSlider* m_pSlider; + CDXUTStatic* m_pLabel; +}; + +} // namespace AMD + +#endif diff --git a/src/DX11/framework/amd_sdk/src/HelperFunctions.cpp b/src/DX11/framework/amd_sdk/src/HelperFunctions.cpp new file mode 100644 index 0000000..1026736 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/HelperFunctions.cpp @@ -0,0 +1,754 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: HelperFunctions.cpp +// +// Various helper functions useful in many samples +//-------------------------------------------------------------------------------------- + + +// DXUT helper code +#include "DXUT.h" +#include "SDKmisc.h" +#include "SDKMesh.h" + +#include "HelperFunctions.h" + + +//-------------------------------------------------------------------------------------- +// Utility function that can optionally create the following objects: +// ID3D11Texture2D (only does this if the pointer is NULL) +// ID3D11ShaderResourceView +// ID3D11RenderTargetView +// ID3D11UnorderedAccessView +//-------------------------------------------------------------------------------------- +HRESULT AMD::CreateSurface( ID3D11Texture2D** ppTexture, ID3D11ShaderResourceView** ppTextureSRV, + ID3D11RenderTargetView** ppTextureRTV, ID3D11UnorderedAccessView** ppTextureUAV, + DXGI_FORMAT Format, unsigned int uWidth, unsigned int uHeight, unsigned int uSampleCount ) +{ + HRESULT hr = D3D_OK; + + if (ppTexture) + { + D3D11_TEXTURE2D_DESC Desc; + ZeroMemory( &Desc, sizeof( Desc ) ); + + if (NULL == *ppTexture) + { + Desc.Width = uWidth; + Desc.Height = uHeight; + Desc.MipLevels = 1; + Desc.ArraySize = 1; + Desc.Format = Format; + Desc.SampleDesc.Count = uSampleCount; + Desc.SampleDesc.Quality = 0;//( uSampleCount > 1 ) ? ( D3D10_STANDARD_MULTISAMPLE_PATTERN ) : ( 0 ); + Desc.Usage = D3D11_USAGE_DEFAULT; + Desc.BindFlags = D3D11_BIND_RENDER_TARGET | D3D11_BIND_SHADER_RESOURCE; + if (ppTextureUAV) + { + Desc.BindFlags |= D3D11_BIND_UNORDERED_ACCESS; + } + hr = DXUTGetD3D11Device()->CreateTexture2D( &Desc, NULL, ppTexture ); + assert( D3D_OK == hr ); + } + + if (ppTextureSRV) + { + SAFE_RELEASE( *ppTextureSRV ); + + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc; + ZeroMemory( &SRVDesc, sizeof( D3D11_SHADER_RESOURCE_VIEW_DESC ) ); + SRVDesc.Format = Format; + SRVDesc.ViewDimension = (uSampleCount > 1) ? (D3D11_SRV_DIMENSION_TEXTURE2DMS) : (D3D11_SRV_DIMENSION_TEXTURE2D); + SRVDesc.Texture2D.MostDetailedMip = 0; + SRVDesc.Texture2D.MipLevels = 1; + hr = DXUTGetD3D11Device()->CreateShaderResourceView( *ppTexture, &SRVDesc, ppTextureSRV ); + assert( D3D_OK == hr ); + } + + if (ppTextureRTV) + { + SAFE_RELEASE( *ppTextureRTV ); + + D3D11_RENDER_TARGET_VIEW_DESC RTVDesc; + ZeroMemory( &RTVDesc, sizeof( D3D11_RENDER_TARGET_VIEW_DESC ) ); + RTVDesc.Format = Format; + RTVDesc.ViewDimension = (uSampleCount > 1) ? (D3D11_RTV_DIMENSION_TEXTURE2DMS) : (D3D11_RTV_DIMENSION_TEXTURE2D); + RTVDesc.Texture2D.MipSlice = 0; + hr = DXUTGetD3D11Device()->CreateRenderTargetView( *ppTexture, &RTVDesc, ppTextureRTV ); + assert( D3D_OK == hr ); + } + + if (ppTextureUAV) + { + SAFE_RELEASE( *ppTextureUAV ); + + D3D11_UNORDERED_ACCESS_VIEW_DESC UAVDesc; + ZeroMemory( &UAVDesc, sizeof( D3D11_UNORDERED_ACCESS_VIEW_DESC ) ); + UAVDesc.Format = Format; + UAVDesc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE2D; + UAVDesc.Buffer.FirstElement = 0; + UAVDesc.Buffer.NumElements = Desc.Width * Desc.Height; + hr = DXUTGetD3D11Device()->CreateUnorderedAccessView( *ppTexture, &UAVDesc, ppTextureUAV ); + assert( D3D_OK == hr ); + } + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Creates a depth stencil surface and optionally creates the following objects: +// ID3D11ShaderResourceView +// ID3D11DepthStencilView +//-------------------------------------------------------------------------------------- +HRESULT AMD::CreateDepthStencilSurface( ID3D11Texture2D** ppDepthStencilTexture, ID3D11ShaderResourceView** ppDepthStencilSRV, + ID3D11DepthStencilView** ppDepthStencilView, DXGI_FORMAT DSFormat, DXGI_FORMAT SRVFormat, + unsigned int uWidth, unsigned int uHeight, unsigned int uSampleCount ) +{ + HRESULT hr = D3D_OK; + DXGI_FORMAT TextureFormat; + + if (ppDepthStencilTexture) + { + switch (DSFormat) + { + case DXGI_FORMAT_D32_FLOAT: + TextureFormat = DXGI_FORMAT_R32_TYPELESS; + break; + + case DXGI_FORMAT_D24_UNORM_S8_UINT: + TextureFormat = DXGI_FORMAT_R24G8_TYPELESS; + break; + + case DXGI_FORMAT_D16_UNORM: + TextureFormat = DXGI_FORMAT_R16_TYPELESS; + break; + + default: + TextureFormat = DXGI_FORMAT_UNKNOWN; + break; + } + assert( TextureFormat != DXGI_FORMAT_UNKNOWN ); + + // Create depth stencil texture + D3D11_TEXTURE2D_DESC descDepth; + descDepth.Width = uWidth; + descDepth.Height = uHeight; + descDepth.MipLevels = 1; + descDepth.ArraySize = 1; + descDepth.Format = TextureFormat; + descDepth.SampleDesc.Count = uSampleCount; + descDepth.SampleDesc.Quality = 0;//( uSampleCount > 1 ) ? ( D3D10_STANDARD_MULTISAMPLE_PATTERN ) : ( 0 ); + descDepth.Usage = D3D11_USAGE_DEFAULT; + descDepth.BindFlags = D3D11_BIND_DEPTH_STENCIL; + + if (NULL != ppDepthStencilSRV) + { + if ((descDepth.SampleDesc.Count == 1) || (DXUTGetD3D11DeviceFeatureLevel() >= D3D_FEATURE_LEVEL_10_1)) + { + descDepth.BindFlags |= D3D11_BIND_SHADER_RESOURCE; + } + } + + descDepth.CPUAccessFlags = 0; + descDepth.MiscFlags = 0; + hr = DXUTGetD3D11Device()->CreateTexture2D( &descDepth, NULL, ppDepthStencilTexture ); + assert( D3D_OK == hr ); + + if (NULL != ppDepthStencilView) + { + // Create the depth stencil view + D3D11_DEPTH_STENCIL_VIEW_DESC descDSV; + descDSV.Format = DSFormat; + if (descDepth.SampleDesc.Count > 1) + { + descDSV.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DMS; + } + else + { + descDSV.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D; + } + descDSV.Texture2D.MipSlice = 0; + descDSV.Flags = 0; + + hr = DXUTGetD3D11Device()->CreateDepthStencilView( (ID3D11Resource*)*ppDepthStencilTexture, &descDSV, ppDepthStencilView ); + assert( D3D_OK == hr ); + } + + if (NULL != ppDepthStencilSRV) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRDesc; + SRDesc.Format = SRVFormat; + SRDesc.ViewDimension = (uSampleCount > 1) ? (D3D11_SRV_DIMENSION_TEXTURE2DMS) : (D3D11_SRV_DIMENSION_TEXTURE2D); + SRDesc.Texture2D.MostDetailedMip = 0; + SRDesc.Texture2D.MipLevels = 1; + + hr = DXUTGetD3D11Device()->CreateShaderResourceView( (ID3D11Resource*)*ppDepthStencilTexture, &SRDesc, ppDepthStencilSRV ); + assert( D3D_OK == hr ); + } + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Captures a frame and dumps it to disk +//-------------------------------------------------------------------------------------- +void AMD::CaptureFrame( ID3D11Texture2D* pCaptureTexture, WCHAR* pszCaptureFileName ) +{ + assert( NULL != pCaptureTexture ); + assert( NULL != pszCaptureFileName ); + + // Retrieve RT resource + ID3D11Resource *pRTResource; + DXUTGetD3D11RenderTargetView()->GetResource( &pRTResource ); + + // Retrieve a Texture2D interface from resource + ID3D11Texture2D* RTTexture; + pRTResource->QueryInterface( __uuidof(ID3D11Texture2D), (LPVOID*)&RTTexture ); + + // Check if RT is multisampled or not + D3D11_TEXTURE2D_DESC TexDesc; + RTTexture->GetDesc( &TexDesc ); + if (TexDesc.SampleDesc.Count > 1) + { + // RT is multisampled, need resolving before dumping to disk + + // Create single-sample RT of the same type and dimensions + DXGI_SAMPLE_DESC SingleSample = { 1, 0 }; + TexDesc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + TexDesc.MipLevels = 1; + TexDesc.Usage = D3D11_USAGE_DEFAULT; + TexDesc.CPUAccessFlags = 0; + TexDesc.BindFlags = 0; + TexDesc.SampleDesc = SingleSample; + + ID3D11Texture2D *pSingleSampleTexture; + DXUTGetD3D11Device()->CreateTexture2D( &TexDesc, NULL, &pSingleSampleTexture ); + + DXUTGetD3D11DeviceContext()->ResolveSubresource( pSingleSampleTexture, 0, RTTexture, 0, TexDesc.Format ); + + // Copy RT into STAGING texture + DXUTGetD3D11DeviceContext()->CopyResource( pCaptureTexture, pSingleSampleTexture ); + + DXUTSaveTextureToFile( DXUTGetD3D11DeviceContext(), pCaptureTexture, false, pszCaptureFileName ); + + SAFE_RELEASE( pSingleSampleTexture ); + } + else + { + // Single sample case + + // Copy RT into STAGING texture + DXUTGetD3D11DeviceContext()->CopyResource( pCaptureTexture, pRTResource ); + + DXUTSaveTextureToFile( DXUTGetD3D11DeviceContext(), pCaptureTexture, false, pszCaptureFileName ); + } + + SAFE_RELEASE( RTTexture ); + + SAFE_RELEASE( pRTResource ); +} + + +//-------------------------------------------------------------------------------------- +// Allows the app to render individual meshes of an sdkmesh +// and override the primitive topology (useful for tessellated rendering of SDK meshes ) +//-------------------------------------------------------------------------------------- +void AMD::RenderMesh( CDXUTSDKMesh* pDXUTMesh, UINT uMesh, D3D11_PRIMITIVE_TOPOLOGY PrimType, + UINT uDiffuseSlot, UINT uNormalSlot, UINT uSpecularSlot ) +{ +#define MAX_D3D11_VERTEX_STREAMS D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT + + assert( NULL != pDXUTMesh ); + + SDKMESH_MESH* pMesh = pDXUTMesh->GetMesh( uMesh ); + + UINT Strides[MAX_D3D11_VERTEX_STREAMS]; + UINT Offsets[MAX_D3D11_VERTEX_STREAMS]; + ID3D11Buffer* pVB[MAX_D3D11_VERTEX_STREAMS]; + + if (pMesh->NumVertexBuffers > MAX_D3D11_VERTEX_STREAMS) + { + return; + } + + for (UINT64 i = 0; i < pMesh->NumVertexBuffers; i++) + { + pVB[i] = pDXUTMesh->GetVB11( uMesh, (UINT)i ); + Strides[i] = pDXUTMesh->GetVertexStride( uMesh, (UINT)i ); + Offsets[i] = 0; + } + + ID3D11Buffer* pIB = pDXUTMesh->GetIB11( pMesh->IndexBuffer ); + DXGI_FORMAT ibFormat = pDXUTMesh->GetIBFormat11( pMesh->IndexBuffer ); + + DXUTGetD3D11DeviceContext()->IASetVertexBuffers( 0, pMesh->NumVertexBuffers, pVB, Strides, Offsets ); + DXUTGetD3D11DeviceContext()->IASetIndexBuffer( pIB, ibFormat, 0 ); + + SDKMESH_SUBSET* pSubset = NULL; + SDKMESH_MATERIAL* pMat = NULL; + + for (UINT uSubset = 0; uSubset < pMesh->NumSubsets; uSubset++) + { + pSubset = pDXUTMesh->GetSubset( uMesh, uSubset ); + + if (D3D11_PRIMITIVE_TOPOLOGY_UNDEFINED == PrimType) + { + PrimType = pDXUTMesh->GetPrimitiveType11( (SDKMESH_PRIMITIVE_TYPE)pSubset->PrimitiveType ); + } + + DXUTGetD3D11DeviceContext()->IASetPrimitiveTopology( PrimType ); + + pMat = pDXUTMesh->GetMaterial( pSubset->MaterialID ); + if (uDiffuseSlot != INVALID_SAMPLER_SLOT && !IsErrorResource( pMat->pDiffuseRV11 )) + { + DXUTGetD3D11DeviceContext()->PSSetShaderResources( uDiffuseSlot, 1, &pMat->pDiffuseRV11 ); + } + + if (uNormalSlot != INVALID_SAMPLER_SLOT && !IsErrorResource( pMat->pNormalRV11 )) + { + DXUTGetD3D11DeviceContext()->PSSetShaderResources( uNormalSlot, 1, &pMat->pNormalRV11 ); + } + + if (uSpecularSlot != INVALID_SAMPLER_SLOT && !IsErrorResource( pMat->pSpecularRV11 )) + { + DXUTGetD3D11DeviceContext()->PSSetShaderResources( uSpecularSlot, 1, &pMat->pSpecularRV11 ); + } + + UINT IndexCount = (UINT)pSubset->IndexCount; + UINT IndexStart = (UINT)pSubset->IndexStart; + UINT VertexStart = (UINT)pSubset->VertexStart; + + DXUTGetD3D11DeviceContext()->DrawIndexed( IndexCount, IndexStart, VertexStart ); + } +} + + +//-------------------------------------------------------------------------------------- +// Debug function which copies a GPU buffer to a CPU readable buffer +//-------------------------------------------------------------------------------------- +ID3D11Buffer* AMD::CreateAndCopyToDebugBuf( ID3D11Device* pDevice, ID3D11DeviceContext* pd3dImmediateContext, ID3D11Buffer* pBuffer ) +{ + ID3D11Buffer* debugbuf = NULL; + + D3D11_BUFFER_DESC desc; + ZeroMemory( &desc, sizeof( desc ) ); + pBuffer->GetDesc( &desc ); + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + desc.BindFlags = 0; + desc.MiscFlags = 0; + pDevice->CreateBuffer( &desc, NULL, &debugbuf ); + + pd3dImmediateContext->CopyResource( debugbuf, pBuffer ); + + return debugbuf; +} + + +//-------------------------------------------------------------------------------------- +// Helper function to compile an hlsl shader from file, +// its binary compiled code is returned +//-------------------------------------------------------------------------------------- +HRESULT AMD::CompileShaderFromFile( WCHAR* szFileName, LPCSTR szEntryPoint, + LPCSTR szShaderModel, ID3DBlob** ppBlobOut, const D3D10_SHADER_MACRO* pDefines ) +{ + HRESULT hr = E_FAIL; + ID3DBlob* error = NULL; + + hr = D3DCompileFromFile( szFileName, pDefines, D3D_COMPILE_STANDARD_FILE_INCLUDE, szEntryPoint, szShaderModel, 0, 0, ppBlobOut, &error ); + if (hr != S_OK || ppBlobOut == NULL || *ppBlobOut == NULL) + { + if (error != NULL) + { + OutputDebugStringA( (const char *)error->GetBufferPointer() ); + } + else + { + char errorString[128]; + sprintf_s( errorString, "Unknown error compiling shader: (%s, %s)\n", szEntryPoint, szShaderModel ); + OutputDebugStringA( errorString ); + } + } + SAFE_RELEASE( error ); + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Helper function for command line retrieval +//-------------------------------------------------------------------------------------- +bool AMD::IsNextArg( WCHAR*& strCmdLine, WCHAR* strArg ) +{ + int nArgLen = (int)wcslen( strArg ); + int nCmdLen = (int)wcslen( strCmdLine ); + + if (nCmdLen >= nArgLen && + _wcsnicmp( strCmdLine, strArg, nArgLen ) == 0 && + (strCmdLine[nArgLen] == 0 || strCmdLine[nArgLen] == L':' || strCmdLine[nArgLen] == L'=')) + { + strCmdLine += nArgLen; + return true; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +// Helper function for command line retrieval. Updates strCmdLine and strFlag +// Example: if strCmdLine=="-width:1024 -forceref" +// then after: strCmdLine==" -forceref" and strFlag=="1024" +//-------------------------------------------------------------------------------------- +bool AMD::GetCmdParam( WCHAR*& strCmdLine, WCHAR* strFlag ) +{ + if (*strCmdLine == L':' || *strCmdLine == L'=') + { + strCmdLine++; // Skip ':' + + // Place NULL terminator in strFlag after current token + wcscpy_s( strFlag, 256, strCmdLine ); + WCHAR* strSpace = strFlag; + while (*strSpace && (*strSpace > L' ')) + { + strSpace++; + } + *strSpace = 0; + + // Update strCmdLine + strCmdLine += wcslen( strFlag ); + return true; + } + else + { + strFlag[0] = 0; + return false; + } +} + + +//-------------------------------------------------------------------------------------- +// Helper function to parse the command line +//-------------------------------------------------------------------------------------- +void AMD::ParseCommandLine( CmdLineParams* pCmdLineParams ) +{ + assert( NULL != pCmdLineParams ); + + // set some defaults + pCmdLineParams->DriverType = D3D_DRIVER_TYPE_HARDWARE; + pCmdLineParams->uWidth = 1929; + pCmdLineParams->uHeight = 1200; + pCmdLineParams->bCapture = false; + swprintf_s( pCmdLineParams->strCaptureFilename, L"FrameCapture.bmp" ); + pCmdLineParams->iExitFrame = -1; + pCmdLineParams->bRenderHUD = true; + + // Perform application-dependant command line processing + WCHAR* strCmdLine = GetCommandLine(); + WCHAR strFlag[MAX_PATH]; + int nNumArgs; + WCHAR** pstrArgList = CommandLineToArgvW( strCmdLine, &nNumArgs ); + for (int iArg = 1; iArg < nNumArgs; iArg++) + { + strCmdLine = pstrArgList[iArg]; + + // Handle flag args + if (*strCmdLine == L'/' || *strCmdLine == L'-') + { + strCmdLine++; + + if (IsNextArg( strCmdLine, L"device" )) + { + if (GetCmdParam( strCmdLine, strFlag )) + { + if ((wcscmp( strFlag, L"HAL" ) == 0) || (wcscmp( strFlag, L"TNLHAL" ) == 0)) + { + pCmdLineParams->DriverType = D3D_DRIVER_TYPE_HARDWARE; + } + else + { + pCmdLineParams->DriverType = D3D_DRIVER_TYPE_REFERENCE; + } + continue; + } + } + + if (IsNextArg( strCmdLine, L"width" )) + { + if (GetCmdParam( strCmdLine, strFlag )) + { + pCmdLineParams->uWidth = _wtoi( strFlag ); + } + continue; + } + + if (IsNextArg( strCmdLine, L"height" )) + { + if (GetCmdParam( strCmdLine, strFlag )) + { + pCmdLineParams->uHeight = _wtoi( strFlag ); + } + continue; + } + + if (IsNextArg( strCmdLine, L"capturefilename" )) + { + if (GetCmdParam( strCmdLine, strFlag )) + { + swprintf_s( pCmdLineParams->strCaptureFilename, L"%s", strFlag ); + pCmdLineParams->bCapture = true; + } + continue; + } + + if (IsNextArg( strCmdLine, L"nogui" )) + { + pCmdLineParams->bRenderHUD = false; + continue; + } + + if (IsNextArg( strCmdLine, L"exitframe" )) + { + if (GetCmdParam( strCmdLine, strFlag )) + { + pCmdLineParams->iExitFrame = _wtoi( strFlag ); + } + continue; + } + } + } +} + + +//-------------------------------------------------------------------------------------- +// Helper function to check for file existance +//-------------------------------------------------------------------------------------- +bool AMD::FileExists( WCHAR* pFileName ) +{ + assert( NULL != pFileName ); + + FILE* pFile = NULL; + _wfopen_s( &pFile, pFileName, L"rb" ); + if (pFile) + { + fclose( pFile ); + + return true; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +// Creates a cube with vertex format of +// 32x3 Position +// 32x3 Normal +// 16x2 UV +// 28 byte stride +//-------------------------------------------------------------------------------------- +void AMD::CreateCube( float fSize, ID3D11Buffer** ppVertexBuffer, ID3D11Buffer** ppIndexBuffer ) +{ + if (ppVertexBuffer) + { + struct Position + { + float x, y, z; + }; + + float x = fSize; + float y = fSize; + float z = fSize; + + const Position corners[8] = + { + { x, -y, z }, + { x, -y, -z }, + { -x, -y, z }, + { -x, -y, -z }, + { x, y, z }, + { x, y, -z }, + { -x, y, z }, + { -x, y, -z } + }; + + const DirectX::XMFLOAT3 normalDirs[] = + { + DirectX::XMFLOAT3( 0.0f, 0.0f, 1.0f ), + DirectX::XMFLOAT3( 0.0f, 0.0f, -1.0f ), + DirectX::XMFLOAT3( 1.0f, 0.0f, 0.0f ), + DirectX::XMFLOAT3( -1.0f, 0.0f, 0.0f ), + DirectX::XMFLOAT3( 0.0f, 1.0f, 0.0f ), + DirectX::XMFLOAT3( 0.0f, -1.0f, 0.0f ) + }; + + struct Vertex + { + Position position; + DirectX::XMFLOAT3 normal; + USHORT uv[2]; + }; + + Vertex vertices[24]; + + // +z + vertices[0].position = corners[4]; + vertices[1].position = corners[6]; + vertices[2].position = corners[0]; + vertices[3].position = corners[2]; + + // -z + vertices[4].position = corners[7]; + vertices[5].position = corners[5]; + vertices[6].position = corners[3]; + vertices[7].position = corners[1]; + + // +x + vertices[8].position = corners[5]; + vertices[9].position = corners[4]; + vertices[10].position = corners[1]; + vertices[11].position = corners[0]; + + // -x + vertices[12].position = corners[6]; + vertices[13].position = corners[7]; + vertices[14].position = corners[2]; + vertices[15].position = corners[3]; + + // +y + vertices[16].position = corners[7]; + vertices[17].position = corners[6]; + vertices[18].position = corners[5]; + vertices[19].position = corners[4]; + + // -y + vertices[20].position = corners[0]; + vertices[21].position = corners[2]; + vertices[22].position = corners[1]; + vertices[23].position = corners[3]; + + int f = 0; + for (int i = 0; i < 6; i++) + { + vertices[f + 0].uv[0] = 0x3C00; + vertices[f + 0].uv[1] = 0; + vertices[f + 1].uv[0] = 0; + vertices[f + 1].uv[1] = 0; + vertices[f + 2].uv[0] = 0x3C00; + vertices[f + 2].uv[1] = 0x3C00; + vertices[f + 3].uv[0] = 0; + vertices[f + 3].uv[1] = 0x3C00; + + DirectX::XMFLOAT3 normal = normalDirs[i]; + vertices[f + 0].normal = normal; + vertices[f + 1].normal = normal; + vertices[f + 2].normal = normal; + vertices[f + 3].normal = normal; + + f += 4; + } + + D3D11_BUFFER_DESC bd; + ZeroMemory( &bd, sizeof( bd ) ); + bd.Usage = D3D11_USAGE_IMMUTABLE; + bd.ByteWidth = sizeof( vertices ); + bd.BindFlags = D3D11_BIND_VERTEX_BUFFER; + + D3D11_SUBRESOURCE_DATA data; + data.pSysMem = vertices; + data.SysMemPitch = 0; + data.SysMemSlicePitch = 0; + + DXUTGetD3D11Device()->CreateBuffer( &bd, &data, ppVertexBuffer ); + } + + if (ppIndexBuffer) + { + USHORT indices[36]; + USHORT* idx = indices; + int f = 0; + for (int i = 0; i < 6; i++) + { + idx[0] = USHORT( f + 2 ); + idx[1] = USHORT( f + 0 ); + idx[2] = USHORT( f + 1 ); + idx[3] = USHORT( f + 3 ); + idx[4] = USHORT( f + 2 ); + idx[5] = USHORT( f + 1 ); + f += 4; + idx += 6; + } + + D3D11_BUFFER_DESC bd; + ZeroMemory( &bd, sizeof( bd ) ); + bd.Usage = D3D11_USAGE_IMMUTABLE; + bd.ByteWidth = sizeof( indices ); + bd.BindFlags = D3D11_BIND_INDEX_BUFFER; + + D3D11_SUBRESOURCE_DATA data; + data.pSysMem = indices; + data.SysMemPitch = 0; + data.SysMemSlicePitch = 0; + DXUTGetD3D11Device()->CreateBuffer( &bd, &data, ppIndexBuffer ); + } +} + +//-------------------------------------------------------------------------------------- +// Convert single-precision float to half-precision float, +// returned as a 16-bit unsigned value +//-------------------------------------------------------------------------------------- +unsigned short AMD::ConvertF32ToF16( float fValueToConvert ) +{ + // single precision floating point format: + // |1| 8 | 23 | + // |s|eeeeeeee|mmmmmmmmmmmmmmmmmmmmmmm| + + // half precision floating point format: + // |1| 5 | 10 | + // |s|eeeee|mmmmmmmmmm| + + unsigned int uFloatBits = (*(unsigned int *)&fValueToConvert); + + // note, this functions does not handle values that are too large (i.e. overflow), + // nor does it handle NaNs or infinity + int nExponent = (int)((uFloatBits & 0x7F800000u) >> 23) - 127 + 15; + assert( nExponent < 31 ); + + // if the resulting value would be a denorm or underflow, then just return a (signed) zero + if (nExponent <= 0) + { + return (unsigned short)((uFloatBits & 0x80000000u) >> 16); + } + + // else, exponent is in the range [1,30], and so we can represent + // the value to convert as a normalized 16-bit float (with some loss of precision, of course) + unsigned int uSignBit = (uFloatBits & 0x80000000u) >> 16; + unsigned int uExponentBits = (unsigned int)nExponent << 10; + unsigned int uMantissaBits = (uFloatBits & 0x007FFFFFu) >> 13; + + return (unsigned short)(uSignBit | uExponentBits | uMantissaBits); +} diff --git a/src/DX11/framework/amd_sdk/src/HelperFunctions.h b/src/DX11/framework/amd_sdk/src/HelperFunctions.h new file mode 100644 index 0000000..bfd6b3a --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/HelperFunctions.h @@ -0,0 +1,145 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: HelperFunctions.h +// +// Various helper functions. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_HELPER_FUNCTIONS_H +#define AMD_SDK_HELPER_FUNCTIONS_H + +namespace AMD +{ + // Cmd line params structure + typedef struct CmdLineParams_t + { + D3D_DRIVER_TYPE DriverType; + unsigned int uWidth; + unsigned int uHeight; + bool bCapture; + WCHAR strCaptureFilename[256]; + int iExitFrame; + bool bRenderHUD; + } CmdLineParams; + + +//-------------------------------------------------------------------------------------- +// Utility function that can optionally create the following objects: +// ID3D11Texture2D (only does this if the pointer is NULL) +// ID3D11ShaderResourceView +// ID3D11RenderTargetView +// ID3D11UnorderedAccessView +//-------------------------------------------------------------------------------------- +HRESULT CreateSurface( ID3D11Texture2D** ppTexture, ID3D11ShaderResourceView** ppTextureSRV, + ID3D11RenderTargetView** ppTextureRTV, ID3D11UnorderedAccessView** ppTextureUAV, + DXGI_FORMAT Format, unsigned int uWidth, unsigned int uHeight, unsigned int uSampleCount ); + + +//-------------------------------------------------------------------------------------- +// Creates a depth stencil surface and optionally creates the following objects: +// ID3D11ShaderResourceView +// ID3D11DepthStencilView +//-------------------------------------------------------------------------------------- +HRESULT CreateDepthStencilSurface( ID3D11Texture2D** ppDepthStencilTexture, ID3D11ShaderResourceView** ppDepthStencilSRV, + ID3D11DepthStencilView** ppDepthStencilView, DXGI_FORMAT DSFormat, DXGI_FORMAT SRVFormat, + unsigned int uWidth, unsigned int uHeight, unsigned int uSampleCount ); + + +//-------------------------------------------------------------------------------------- +// Capture a frame and dump it to disk +//-------------------------------------------------------------------------------------- +void CaptureFrame( ID3D11Texture2D* pCaptureTexture, WCHAR* pszCaptureFileName ); + + +//-------------------------------------------------------------------------------------- +// Allows the app to render individual meshes of an sdkmesh +// and override the primitive topology (useful for tessellated rendering of SDK meshes ) +//-------------------------------------------------------------------------------------- +void RenderMesh( CDXUTSDKMesh* pDXUTMesh, UINT uMesh, + D3D11_PRIMITIVE_TOPOLOGY PrimType = D3D11_PRIMITIVE_TOPOLOGY_UNDEFINED, + UINT uDiffuseSlot = INVALID_SAMPLER_SLOT, UINT uNormalSlot = INVALID_SAMPLER_SLOT, + UINT uSpecularSlot = INVALID_SAMPLER_SLOT ); + + +//-------------------------------------------------------------------------------------- +// Debug function which copies a GPU buffer to a CPU readable buffer +//-------------------------------------------------------------------------------------- +ID3D11Buffer* CreateAndCopyToDebugBuf( ID3D11Device* pDevice, ID3D11DeviceContext* pd3dImmediateContext, + ID3D11Buffer* pBuffer ); + + +//-------------------------------------------------------------------------------------- +// Helper function to compile an hlsl shader from file, +// its binary compiled code is returned +//-------------------------------------------------------------------------------------- +HRESULT CompileShaderFromFile( WCHAR* szFileName, LPCSTR szEntryPoint, + LPCSTR szShaderModel, ID3DBlob** ppBlobOut, const D3D10_SHADER_MACRO* pDefines ); + + +//-------------------------------------------------------------------------------------- +// Helper function for command line retrieval +//-------------------------------------------------------------------------------------- +bool IsNextArg( WCHAR*& strCmdLine, WCHAR* strArg ); + + +//-------------------------------------------------------------------------------------- +// Helper function for command line retrieval. Updates strCmdLine and strFlag +// Example: if strCmdLine=="-width:1024 -forceref" +// then after: strCmdLine==" -forceref" and strFlag=="1024" +//-------------------------------------------------------------------------------------- +bool GetCmdParam( WCHAR*& strCmdLine, WCHAR* strFlag ); + + +//-------------------------------------------------------------------------------------- +// Helper function to parse the command line +//-------------------------------------------------------------------------------------- +void ParseCommandLine( CmdLineParams* pCmdLineParams ); + + +//-------------------------------------------------------------------------------------- +// Check for file existance +//-------------------------------------------------------------------------------------- +bool FileExists( WCHAR* pFileName ); + + +//-------------------------------------------------------------------------------------- +// Creates a cube with vertex format of +// 32x3 Position +// 32x3 Normal +// 16x2 UV +// 28 byte stride +//-------------------------------------------------------------------------------------- +void CreateCube( float fSize, ID3D11Buffer** ppVertexBuffer, ID3D11Buffer** ppIndexBuffer ); + + +//-------------------------------------------------------------------------------------- +// Convert single-precision float to half-precision float, +// returned as a 16-bit unsigned value +//-------------------------------------------------------------------------------------- +unsigned short ConvertF32ToF16(float fValueToConvert); + + +} // namespace AMD + + +#endif diff --git a/src/DX11/framework/amd_sdk/src/LineRender.cpp b/src/DX11/framework/amd_sdk/src/LineRender.cpp new file mode 100644 index 0000000..e538b00 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/LineRender.cpp @@ -0,0 +1,227 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: LineRender.cpp +// +// Helper to render 3d colored lines +//-------------------------------------------------------------------------------------- + +// DXUT helper code +#include "DXUT.h" +#include "SDKMesh.h" + +#include "LineRender.h" +#include "Geometry.h" +#include "HelperFunctions.h" + +// for DirectXMath BoundingBox +#include + +AMD::LineRender::LineRender() : +m_pImmediateContext( 0 ), +m_pInputLayout( 0 ), +m_pVertexShader( 0 ), +m_pPixelShader( 0 ), +m_pConstantBuffer( 0 ), +m_pVertexBuffer( 0 ), +m_pCPUCopy( 0 ), +m_MaxLines( 0 ), +m_NumLines( 0 ) +{ +} + + +AMD::LineRender::~LineRender() +{ + assert( m_pCPUCopy == 0 ); +} + + +void AMD::LineRender::OnCreateDevice( ID3D11Device* pDevice, ID3D11DeviceContext* pImmediateContext, int nMaxLines ) +{ + assert( nMaxLines > 0 ); + assert( pDevice && pImmediateContext ); + + m_pImmediateContext = pImmediateContext; + m_MaxLines = nMaxLines; + m_NumLines = 0; + + // Create shaders + ID3DBlob* pBlob = 0; + + HRESULT hr = AMD::CompileShaderFromFile( L"..\\amd_sdk\\src\\Shaders\\Line.hlsl", "LineVS", "vs_4_0", &pBlob, 0 ); + assert( hr == S_OK ); + hr = pDevice->CreateVertexShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), 0, &m_pVertexShader ); + assert( hr == S_OK ); + + D3D11_INPUT_ELEMENT_DESC layout[] = + { + { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "COLOR", 0, DXGI_FORMAT_R8G8B8A8_UNORM, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 } + }; + hr = pDevice->CreateInputLayout( layout, ARRAYSIZE( layout ), pBlob->GetBufferPointer(), pBlob->GetBufferSize(), &m_pInputLayout ); + assert( hr == S_OK ); + SAFE_RELEASE( pBlob ); + + hr = AMD::CompileShaderFromFile( L"..\\amd_sdk\\src\\Shaders\\Line.hlsl", "LinePS", "ps_4_0", &pBlob, 0 ); + assert( hr == S_OK ); + hr = pDevice->CreatePixelShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), 0, &m_pPixelShader ); + assert( hr == S_OK ); + + // Create vertex buffer + D3D11_BUFFER_DESC desc; + ZeroMemory( &desc, sizeof( desc ) ); + desc.ByteWidth = m_MaxLines * 2 * sizeof( Vertex ); + desc.Usage = D3D11_USAGE_DYNAMIC; + desc.BindFlags = D3D11_BIND_VERTEX_BUFFER; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + pDevice->CreateBuffer( &desc, 0, &m_pVertexBuffer ); + + // Create constant buffer + desc.ByteWidth = sizeof( ConstantBuffer ); + desc.BindFlags = D3D11_BIND_CONSTANT_BUFFER; + pDevice->CreateBuffer( &desc, 0, &m_pConstantBuffer ); + + // Alloc CPU side vertex buffer + m_pCPUCopy = new Vertex[m_MaxLines * 2]; +} + + +void AMD::LineRender::OnDestroyDevice() +{ + if (m_pCPUCopy) + { + delete [] m_pCPUCopy; + m_pCPUCopy = 0; + } + + SAFE_RELEASE( m_pVertexBuffer ); + SAFE_RELEASE( m_pConstantBuffer ); + SAFE_RELEASE( m_pPixelShader ); + SAFE_RELEASE( m_pVertexShader ); + SAFE_RELEASE( m_pInputLayout ); + + m_pImmediateContext = 0; +} + + +void AMD::LineRender::AddLine( const DirectX::XMFLOAT3& p0, const DirectX::XMFLOAT3& p1, const D3DCOLOR& color ) +{ + if (m_NumLines < m_MaxLines) + { + Vertex* pVerts = &m_pCPUCopy[m_NumLines * 2]; + + pVerts[0].m_Position = p0; + pVerts[1].m_Position = p1; + + pVerts[0].m_Color = color; + pVerts[1].m_Color = color; + + m_NumLines++; + } +} + + +void AMD::LineRender::AddLines( const DirectX::XMFLOAT3* pPoints, int nNumLines, const D3DCOLOR& color ) +{ + if (m_NumLines + nNumLines <= m_MaxLines) + { + Vertex* pVerts = &m_pCPUCopy[m_NumLines * 2]; + + for (int i = 0; i < nNumLines; i++) + { + pVerts[0].m_Position = pPoints[0]; + pVerts[1].m_Position = pPoints[1]; + + pVerts[0].m_Color = color; + pVerts[1].m_Color = color; + + pVerts += 2; + pPoints += 2; + } + + m_NumLines += nNumLines; + } +} + + +void AMD::LineRender::AddBox( const DirectX::BoundingBox& box, const D3DCOLOR& color ) +{ + DirectX::XMFLOAT3 points[24]; + + DirectX::XMFLOAT3 corners[8]; + box.GetCorners( corners ); + + const int indices[24] = + { + 0, 1, 1, 3, 3, 2, 2, 0, + 4, 5, 5, 7, 7, 6, 6, 4, + 0, 4, 1, 5, 2, 6, 3, 7 + }; + + for (int i = 0; i < 24; i++) + { + points[i] = corners[indices[i]]; + } + + AddLines( points, 12, color ); +} + + +void AMD::LineRender::Render( const DirectX::XMMATRIX& viewProj ) +{ + if (m_NumLines > 0) + { + // Copy the CPU buffer into the GPU one + D3D11_MAPPED_SUBRESOURCE res; + m_pImmediateContext->Map( m_pVertexBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &res ); + memcpy( res.pData, m_pCPUCopy, sizeof( Vertex ) * m_NumLines * 2 ); + m_pImmediateContext->Unmap( m_pVertexBuffer, 0 ); + + // Update the constant buffer + m_pImmediateContext->Map( m_pConstantBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &res ); + ConstantBuffer* constants = (ConstantBuffer*)res.pData; + constants->m_ViewProj = DirectX::XMMatrixTranspose( viewProj ); + m_pImmediateContext->Unmap( m_pConstantBuffer, 0 ); + + // Set up states + m_pImmediateContext->IASetInputLayout( m_pInputLayout ); + m_pImmediateContext->VSSetShader( m_pVertexShader, 0, 0 ); + m_pImmediateContext->HSSetShader( 0, 0, 0 ); + m_pImmediateContext->DSSetShader( 0, 0, 0 ); + m_pImmediateContext->GSSetShader( 0, 0, 0 ); + m_pImmediateContext->PSSetShader( m_pPixelShader, 0, 0 ); + m_pImmediateContext->VSSetConstantBuffers( 0, 1, &m_pConstantBuffer ); + + UINT stride = sizeof( Vertex ); + UINT offset = 0; + m_pImmediateContext->IASetVertexBuffers( 0, 1, &m_pVertexBuffer, &stride, &offset ); + m_pImmediateContext->IASetPrimitiveTopology( D3D_PRIMITIVE_TOPOLOGY_LINELIST ); + + // Draw + m_pImmediateContext->Draw( m_NumLines * 2, 0 ); + + // Reset the number of lines + m_NumLines = 0; + } +} diff --git a/src/DX11/framework/amd_sdk/src/LineRender.h b/src/DX11/framework/amd_sdk/src/LineRender.h new file mode 100644 index 0000000..0b20c0a --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/LineRender.h @@ -0,0 +1,82 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: LineRender.h +// +// Helper to render 3d colored lines. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_LINE_RENDER_H +#define AMD_SDK_LINE_RENDER_H + +// forward declarations +namespace DirectX +{ + struct BoundingBox; +} + +namespace AMD +{ + + class LineRender + { + public: + + LineRender(); + ~LineRender(); + + void OnCreateDevice( ID3D11Device* pDevice, ID3D11DeviceContext* pImmediateContext, int nMaxLines ); + void OnDestroyDevice(); + + void AddLine( const DirectX::XMFLOAT3& p0, const DirectX::XMFLOAT3& p1, const D3DCOLOR& color ); + void AddLines( const DirectX::XMFLOAT3* pPoints, int nNumLines, const D3DCOLOR& color ); + void AddBox( const DirectX::BoundingBox& box, const D3DCOLOR& color ); + + void Render( const DirectX::XMMATRIX& viewProj ); + + private: + + struct Vertex + { + DirectX::XMFLOAT3 m_Position; + DWORD m_Color; + }; + + struct ConstantBuffer + { + DirectX::XMMATRIX m_ViewProj; + }; + + ID3D11DeviceContext* m_pImmediateContext; + ID3D11InputLayout* m_pInputLayout; + ID3D11VertexShader* m_pVertexShader; + ID3D11PixelShader* m_pPixelShader; + ID3D11Buffer* m_pConstantBuffer; + ID3D11Buffer* m_pVertexBuffer; + Vertex* m_pCPUCopy; + int m_MaxLines; + int m_NumLines; + }; + +} + +#endif diff --git a/src/DX11/framework/amd_sdk/src/Magnify.cpp b/src/DX11/framework/amd_sdk/src/Magnify.cpp new file mode 100644 index 0000000..b42d434 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Magnify.cpp @@ -0,0 +1,481 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: Magnify.cpp +// +// Magnify class implementation. This class magnifies a region of a given surface, and +// renders a scaled sprite at the given position on the screen. +//-------------------------------------------------------------------------------------- + + +#include "DXUT.h" +#include "Magnify.h" + +using namespace AMD; + +//-------------------------------------------------------------------------------------- +// Constructor +//-------------------------------------------------------------------------------------- +Magnify::Magnify() +{ + // Magnification settings + m_nPixelRegion = 64; + m_nHalfPixelRegion = m_nPixelRegion / 2; + m_nScale = 5; + m_nPositionX = m_nPixelRegion; + m_nPositionY = m_nPixelRegion; + m_fDepthRangeMin = 0.0f; + m_fDepthRangeMax = 0.01f; + m_nBackBufferWidth = 0; + m_nBackBufferHeight = 0; + m_nSubSampleIndex = 0; + + // Source resource data + m_pSourceResource = NULL; + m_pResolvedSourceResource = NULL; + m_pCopySourceResource = NULL; + m_pResolvedSourceResourceSRV = NULL; + m_pCopySourceResourceSRV = NULL; + m_pSourceResourceSRV1 = NULL; + m_SourceResourceFormat = DXGI_FORMAT_UNKNOWN; + m_nSourceResourceWidth = 0; + m_nSourceResourceHeight = 0; + m_nSourceResourceSamples = 0; + m_DepthFormat = DXGI_FORMAT_UNKNOWN; + m_DepthSRVFormat = DXGI_FORMAT_UNKNOWN; + m_bDepthFormat = false; +} + + +//-------------------------------------------------------------------------------------- +// Destructor +//-------------------------------------------------------------------------------------- +Magnify::~Magnify() +{ +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +HRESULT Magnify::OnCreateDevice( ID3D11Device* pd3dDevice ) +{ + HRESULT hr; + + assert( NULL != pd3dDevice ); + + hr = m_Sprite.OnCreateDevice( pd3dDevice ); + assert( S_OK == hr ); + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +void Magnify::OnDestroyDevice() +{ + m_Sprite.OnDestroyDevice(); + + SAFE_RELEASE( m_pResolvedSourceResourceSRV ); + SAFE_RELEASE( m_pCopySourceResourceSRV ); + SAFE_RELEASE( m_pSourceResourceSRV1 ); + SAFE_RELEASE( m_pResolvedSourceResource ); + SAFE_RELEASE( m_pCopySourceResource ); +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +void Magnify::OnResizedSwapChain( const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ) +{ + assert( NULL != pBackBufferSurfaceDesc ); + + m_Sprite.OnResizedSwapChain( pBackBufferSurfaceDesc ); + + m_nBackBufferWidth = pBackBufferSurfaceDesc->Width; + m_nBackBufferHeight = pBackBufferSurfaceDesc->Height; +} + + +//-------------------------------------------------------------------------------------- +// Sets the region to be captured from the source resource +//-------------------------------------------------------------------------------------- +void Magnify::Capture( POINT& Point ) +{ + RECT Rect; + ::GetWindowRect( DXUTGetHWND(), &Rect ); + + int nWidthDiff = 0; + int nHeightDiff = 0; + + if (DXUTIsWindowed()) + { + nWidthDiff = (int)(((Rect.right - Rect.left) - m_nBackBufferWidth) * (1.0f / 2.0f)); + nHeightDiff = (int)(((Rect.bottom - Rect.top) - m_nBackBufferHeight) * (4.0f / 5.0f)); + } + + SetPosition( Point.x - (Rect.left + nWidthDiff), Point.y - (Rect.top + nHeightDiff) ); + + D3D10_BOX SourceRegion; + SourceRegion.left = m_nPositionX - m_nHalfPixelRegion; + SourceRegion.right = m_nPositionX + m_nHalfPixelRegion; + SourceRegion.top = m_nPositionY - m_nHalfPixelRegion; + SourceRegion.bottom = m_nPositionY + m_nHalfPixelRegion; + SourceRegion.front = 0; + SourceRegion.back = 1; +} + + +//-------------------------------------------------------------------------------------- +// User defines the resource for capturing from +//-------------------------------------------------------------------------------------- +void Magnify::SetSourceResource( ID3D11Resource* pSourceResource, DXGI_FORMAT Format, + int nWidth, int nHeight, int nSamples ) +{ + assert( NULL != pSourceResource ); + assert( Format > DXGI_FORMAT_UNKNOWN ); + assert( nWidth > 0 ); + assert( nHeight > 0 ); + assert( nSamples > 0 ); + + m_pSourceResource = pSourceResource; + m_SourceResourceFormat = Format; + m_nSourceResourceWidth = nWidth; + m_nSourceResourceHeight = nHeight; + m_nSourceResourceSamples = nSamples; + + m_bDepthFormat = false; + + switch (m_SourceResourceFormat) + { + case DXGI_FORMAT_D32_FLOAT: + m_DepthFormat = DXGI_FORMAT_R32_TYPELESS; + m_DepthSRVFormat = DXGI_FORMAT_R32_FLOAT; + m_bDepthFormat = true; + break; + + case DXGI_FORMAT_D24_UNORM_S8_UINT: + m_DepthFormat = DXGI_FORMAT_R24G8_TYPELESS; + m_DepthSRVFormat = DXGI_FORMAT_R24_UNORM_X8_TYPELESS; + m_bDepthFormat = true; + break; + + case DXGI_FORMAT_D16_UNORM: + m_DepthFormat = DXGI_FORMAT_R16_TYPELESS; + m_DepthSRVFormat = DXGI_FORMAT_R16_UNORM; + m_bDepthFormat = true; + break; + } + + CreateInternalResources(); +} + + +//-------------------------------------------------------------------------------------- +// User defines the pixel region to be captured +//-------------------------------------------------------------------------------------- +void Magnify::SetPixelRegion( int nPixelRegion ) +{ + assert( nPixelRegion > 1 ); + + m_nPixelRegion = nPixelRegion; + m_nHalfPixelRegion = m_nPixelRegion / 2; +} + + +//-------------------------------------------------------------------------------------- +// User defines the scale of magnification +//-------------------------------------------------------------------------------------- +void Magnify::SetScale( int nScale ) +{ + assert( nScale > 1 ); + + m_nScale = nScale; +} + + +//-------------------------------------------------------------------------------------- +// User defines how to scale depth surfaces +//-------------------------------------------------------------------------------------- +void Magnify::SetDepthRangeMin( float fDepthRangeMin ) +{ + m_fDepthRangeMin = fDepthRangeMin; +} + + +//-------------------------------------------------------------------------------------- +// User defines how to scale depth surfaces +//-------------------------------------------------------------------------------------- +void Magnify::SetDepthRangeMax( float fDepthRangeMax ) +{ + m_fDepthRangeMax = fDepthRangeMax; +} + + +//-------------------------------------------------------------------------------------- +// User defines which sub-samnple to magnify for MSAA sufaces +//-------------------------------------------------------------------------------------- +void Magnify::SetSubSampleIndex( int nSubSampleIndex ) +{ + m_nSubSampleIndex = nSubSampleIndex; +} + + +//-------------------------------------------------------------------------------------- +// Renders the source resource to the screen +//-------------------------------------------------------------------------------------- +void Magnify::RenderBackground() +{ + if (m_bDepthFormat) + { + if (m_nSourceResourceSamples == 1) + { + DXUTGetD3D11DeviceContext()->CopyResource( m_pCopySourceResource, m_pSourceResource ); + } + } + else + { + if (m_nSourceResourceSamples > 1) + { + DXUTGetD3D11DeviceContext()->ResolveSubresource( m_pResolvedSourceResource, 0, + m_pSourceResource, 0, m_SourceResourceFormat ); + } + else + { + DXUTGetD3D11DeviceContext()->CopyResource( m_pCopySourceResource, m_pSourceResource ); + + } + } + + if (m_bDepthFormat) + { + if (m_nSourceResourceSamples > 1) + { + // Get the current render and depth targets, so we can later revert to these. + ID3D11RenderTargetView *pRenderTargetView; + ID3D11DepthStencilView *pDepthStencilView; + DXUTGetD3D11DeviceContext()->OMGetRenderTargets( 1, &pRenderTargetView, &pDepthStencilView ); + + // Bind our render target view to the OM stage. + DXUTGetD3D11DeviceContext()->OMSetRenderTargets( 1, (ID3D11RenderTargetView* const*)&pRenderTargetView, NULL ); + + m_Sprite.SetUVs( 0.0f, 0.0f, 1.0f, 1.0f ); + + m_Sprite.RenderSpriteAsDepthMS( m_pSourceResourceSRV1, 0, m_nBackBufferHeight, + m_nBackBufferWidth, m_nBackBufferHeight, m_nBackBufferWidth, m_nBackBufferHeight, + false, m_fDepthRangeMin, m_fDepthRangeMax, m_nSubSampleIndex ); + + // Bind back to the original render, depth target, and viewport + DXUTGetD3D11DeviceContext()->OMSetRenderTargets( 1, (ID3D11RenderTargetView* const*)&pRenderTargetView, pDepthStencilView ); + + // Decrement the counter on these resources + SAFE_RELEASE( pRenderTargetView ); + SAFE_RELEASE( pDepthStencilView ); + } + else + { + m_Sprite.SetUVs( 0.0f, 0.0f, 1.0f, 1.0f ); + + m_Sprite.RenderSpriteAsDepth( m_pCopySourceResourceSRV, 0, m_nBackBufferHeight, + m_nBackBufferWidth, m_nBackBufferHeight, false, m_fDepthRangeMin, m_fDepthRangeMax ); + } + } + else + { + m_Sprite.SetUVs( 0.0f, 0.0f, 1.0f, 1.0f ); + + if (m_nSourceResourceSamples > 1) + { + m_Sprite.RenderSprite( m_pResolvedSourceResourceSRV, 0, m_nBackBufferHeight, + m_nBackBufferWidth, m_nBackBufferHeight, false, false ); + } + else + { + m_Sprite.RenderSprite( m_pCopySourceResourceSRV, 0, m_nBackBufferHeight, + m_nBackBufferWidth, m_nBackBufferHeight, false, false ); + } + } +} + + +//-------------------------------------------------------------------------------------- +// Renders the magnified region to the screen +//-------------------------------------------------------------------------------------- +void Magnify::RenderMagnifiedRegion() +{ + m_Sprite.SetUVs( (m_nPositionX - m_nHalfPixelRegion) / (float)m_nSourceResourceWidth, + (m_nPositionY - m_nHalfPixelRegion) / (float)m_nSourceResourceHeight, + (m_nPositionX + m_nHalfPixelRegion) / (float)m_nSourceResourceWidth, + (m_nPositionY + m_nHalfPixelRegion) / (float)m_nSourceResourceHeight ); + + if (m_bDepthFormat) + { + DirectX::XMVECTOR Color = DirectX::XMVectorSet( 1.0f, 1.0f, 1.0f, 1.0f ); + m_Sprite.SetBorderColor( Color ); + + if (m_nSourceResourceSamples > 1) + { + // Get the current render and depth targets, so we can later revert to these + ID3D11RenderTargetView *pRenderTargetView; + ID3D11DepthStencilView *pDepthStencilView; + DXUTGetD3D11DeviceContext()->OMGetRenderTargets( 1, &pRenderTargetView, &pDepthStencilView ); + + // Bind our render target view to the OM stage + DXUTGetD3D11DeviceContext()->OMSetRenderTargets( 1, (ID3D11RenderTargetView* const*)&pRenderTargetView, NULL ); + + m_Sprite.RenderSpriteAsDepthMS( m_pSourceResourceSRV1, (m_nPositionX - m_nHalfPixelRegion * m_nScale), + (m_nPositionY + m_nHalfPixelRegion * m_nScale), (m_nPixelRegion * m_nScale), + (m_nPixelRegion * m_nScale), m_nSourceResourceWidth, m_nSourceResourceHeight, true, + m_fDepthRangeMin, m_fDepthRangeMax, m_nSubSampleIndex ); + + // Bind back to the original render, depth target, and viewport + DXUTGetD3D11DeviceContext()->OMSetRenderTargets( 1, (ID3D11RenderTargetView* const*)&pRenderTargetView, pDepthStencilView ); + + // Decrement the counter on these resources + SAFE_RELEASE( pRenderTargetView ); + SAFE_RELEASE( pDepthStencilView ); + } + else + { + m_Sprite.RenderSpriteAsDepth( m_pCopySourceResourceSRV, (m_nPositionX - m_nHalfPixelRegion * m_nScale), + (m_nPositionY + m_nHalfPixelRegion * m_nScale), (m_nPixelRegion * m_nScale), + (m_nPixelRegion * m_nScale), true, m_fDepthRangeMin, m_fDepthRangeMax ); + } + } + else + { + DirectX::XMVECTOR Color = DirectX::XMVectorSet( 1.0f, 0.0f, 0.0f, 0.0f ); + m_Sprite.SetBorderColor( Color ); + + if (m_nSourceResourceSamples > 1) + { + m_Sprite.RenderSprite( m_pResolvedSourceResourceSRV, (m_nPositionX - m_nHalfPixelRegion * m_nScale), + (m_nPositionY + m_nHalfPixelRegion * m_nScale), (m_nPixelRegion * m_nScale), + (m_nPixelRegion * m_nScale), false, true ); + } + else + { + m_Sprite.RenderSprite( m_pCopySourceResourceSRV, (m_nPositionX - m_nHalfPixelRegion * m_nScale), + (m_nPositionY + m_nHalfPixelRegion * m_nScale), (m_nPixelRegion * m_nScale), + (m_nPixelRegion * m_nScale), false, true ); + } + } +} + + +//-------------------------------------------------------------------------------------- +// Sets the position of capture +//-------------------------------------------------------------------------------------- +void Magnify::SetPosition( int nPositionX, int nPositionY ) +{ + m_nPositionX = nPositionX; + m_nPositionY = nPositionY; + + int nMinX = m_nPixelRegion; + int nMaxX = m_nSourceResourceWidth - m_nPixelRegion; + int nMinY = m_nPixelRegion; + int nMaxY = m_nSourceResourceHeight - m_nPixelRegion; + + m_nPositionX = (m_nPositionX < nMinX) ? (nMinX) : (m_nPositionX); + m_nPositionX = (m_nPositionX > nMaxX) ? (nMaxX) : (m_nPositionX); + + m_nPositionY = (m_nPositionY < nMinY) ? (nMinY) : (m_nPositionY); + m_nPositionY = (m_nPositionY > nMaxY) ? (nMaxY) : (m_nPositionY); +} + + +//-------------------------------------------------------------------------------------- +// Private method that creates various interanl resources +//-------------------------------------------------------------------------------------- +void Magnify::CreateInternalResources() +{ + HRESULT hr; + + SAFE_RELEASE( m_pResolvedSourceResourceSRV ); + SAFE_RELEASE( m_pCopySourceResourceSRV ); + SAFE_RELEASE( m_pSourceResourceSRV1 ); + SAFE_RELEASE( m_pResolvedSourceResource ); + SAFE_RELEASE( m_pCopySourceResource ); + + D3D11_TEXTURE2D_DESC Desc; + ZeroMemory( &Desc, sizeof( Desc ) ); + Desc.Width = m_nBackBufferWidth; + Desc.Height = m_nBackBufferHeight; + Desc.MipLevels = 1; + Desc.ArraySize = 1; + Desc.Format = (m_bDepthFormat) ? (m_DepthFormat) : (m_SourceResourceFormat); + Desc.SampleDesc.Count = 1; + Desc.Usage = D3D11_USAGE_DEFAULT; + Desc.BindFlags = D3D11_BIND_SHADER_RESOURCE; + + hr = DXUTGetD3D11Device()->CreateTexture2D( &Desc, NULL, &m_pResolvedSourceResource ); + assert( S_OK == hr ); + + Desc.SampleDesc.Count = m_nSourceResourceSamples; + + hr = DXUTGetD3D11Device()->CreateTexture2D( &Desc, NULL, &m_pCopySourceResource ); + assert( S_OK == hr ); + + if (m_bDepthFormat) + { + if (m_nSourceResourceSamples > 1) + { + if (DXUTGetD3D11DeviceFeatureLevel() >= D3D_FEATURE_LEVEL_10_1) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRDesc; + SRDesc.Format = m_DepthSRVFormat; + SRDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DMS; + + hr = DXUTGetD3D11Device()->CreateShaderResourceView( m_pSourceResource, &SRDesc, &m_pSourceResourceSRV1 ); + assert( S_OK == hr ); + } + } + else + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRDesc; + SRDesc.Format = m_DepthSRVFormat; + SRDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + SRDesc.Texture2D.MostDetailedMip = 0; + SRDesc.Texture2D.MipLevels = 1; + + hr = DXUTGetD3D11Device()->CreateShaderResourceView( m_pCopySourceResource, &SRDesc, &m_pCopySourceResourceSRV ); + assert( S_OK == hr ); + } + } + else + { + if (m_nSourceResourceSamples > 1) + { + hr = DXUTGetD3D11Device()->CreateShaderResourceView( m_pResolvedSourceResource, NULL, &m_pResolvedSourceResourceSRV ); + assert( S_OK == hr ); + } + else + { + hr = DXUTGetD3D11Device()->CreateShaderResourceView( m_pCopySourceResource, NULL, &m_pCopySourceResourceSRV ); + assert( S_OK == hr ); + } + } +} diff --git a/src/DX11/framework/amd_sdk/src/Magnify.h b/src/DX11/framework/amd_sdk/src/Magnify.h new file mode 100644 index 0000000..75a1b77 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Magnify.h @@ -0,0 +1,107 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: Magnify.h +// +// Magnify class definition. This class magnifies a region of a given surface +// and renders a scaled sprite at the given position on the screen. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_MAGNIFY_H +#define AMD_SDK_MAGNIFY_H + +#include "Sprite.h" + +namespace AMD +{ + +class Magnify +{ +public: + + // Constructor / destructor + Magnify(); + ~Magnify(); + + // Hooks for the DX SDK Framework + HRESULT OnCreateDevice( ID3D11Device* pd3dDevice ); + void OnDestroyDevice(); + void OnResizedSwapChain( const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ); + + // Set methods + void SetPixelRegion( int nPixelRegion ); + void SetScale( int nScale ); + void SetDepthRangeMin( float fDepthRangeMin ); + void SetDepthRangeMax( float fDepthRangeMax ); + void SetSourceResource( ID3D11Resource* pSourceResource, DXGI_FORMAT Format, + int nWidth, int nHeight, int nSamples ); + void SetSubSampleIndex( int nSubSampleIndex ); + + // Captures a region, at the current cursor position, for magnification + void Capture( POINT& Point ); + + // Render the magnified region, at the capture location + void RenderBackground(); + void RenderMagnifiedRegion(); + +private: + + // Private methods + void SetPosition( int nPositionX, int nPositionY ); + void CreateInternalResources(); + +private: + + // Magnification settings + int m_nPositionX; + int m_nPositionY; + int m_nPixelRegion; + int m_nHalfPixelRegion; + int m_nScale; + float m_fDepthRangeMin; + float m_fDepthRangeMax; + int m_nBackBufferWidth; + int m_nBackBufferHeight; + int m_nSubSampleIndex; + + // Helper class for plotting the magnified region + Sprite m_Sprite; + + // Source resource data + ID3D11Resource* m_pSourceResource; + ID3D11Texture2D* m_pResolvedSourceResource; + ID3D11Texture2D* m_pCopySourceResource; + ID3D11ShaderResourceView* m_pResolvedSourceResourceSRV; + ID3D11ShaderResourceView* m_pCopySourceResourceSRV; + ID3D11ShaderResourceView* m_pSourceResourceSRV1; + DXGI_FORMAT m_SourceResourceFormat; + int m_nSourceResourceWidth; + int m_nSourceResourceHeight; + int m_nSourceResourceSamples; + DXGI_FORMAT m_DepthFormat; + DXGI_FORMAT m_DepthSRVFormat; + bool m_bDepthFormat; +}; + +} // namespace AMD + +#endif // AMD_SDK_MAGNIFY_H diff --git a/src/DX11/framework/amd_sdk/src/MagnifyTool.cpp b/src/DX11/framework/amd_sdk/src/MagnifyTool.cpp new file mode 100644 index 0000000..a29e3e2 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/MagnifyTool.cpp @@ -0,0 +1,280 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: MagnifyTool.cpp +// +// MagnifyTool class implementation. This class implements a user interface based upon the +// DXUT framework, for the Magnify class. +//-------------------------------------------------------------------------------------- + +// DXUT helper code +#include "DXUT.h" +#include "DXUTgui.h" + +#include "MagnifyTool.h" +#include "HUD.h" + +#pragma warning( disable : 4100 ) // disable unreference formal parameter warnings for /W4 builds + +using namespace AMD; + + +//-------------------------------------------------------------------------------------- +// Constructor +//-------------------------------------------------------------------------------------- +MagnifyTool::MagnifyTool() +{ + m_pSourceRTResource = NULL; + m_bReleaseRTOnResize = false; + m_RTFormat = DXGI_FORMAT_UNKNOWN; + m_nWidth = 0; + m_nHeight = 0; + m_nSamples = 0; + m_pMagnifyUI = NULL; + m_bMouseDownLastFrame = false; + m_bStickyShowing = false; +} + + +//-------------------------------------------------------------------------------------- +// Destructor +//-------------------------------------------------------------------------------------- +MagnifyTool::~MagnifyTool() +{ +} + + +//-------------------------------------------------------------------------------------- +// User sets the resource to be captured from +//-------------------------------------------------------------------------------------- +void MagnifyTool::SetSourceResources( ID3D11Resource* pSourceRTResource, DXGI_FORMAT RTFormat, + int nWidth, int nHeight, int nSamples ) +{ + assert( NULL != pSourceRTResource ); + + m_pSourceRTResource = pSourceRTResource; + m_RTFormat = RTFormat; + m_nWidth = nWidth; + m_nHeight = nHeight; + m_nSamples = nSamples; + + if (NULL != pSourceRTResource) + { + m_Magnify.SetSourceResource( m_pSourceRTResource, m_RTFormat, m_nWidth, m_nHeight, m_nSamples ); + } + + EnableTool( true ); + EnableUI( true ); +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +void MagnifyTool::InitApp( CDXUTDialog* pUI, int& iStartHeight, bool bSupportStickyMode ) +{ + m_pMagnifyUI = pUI; + + int& iY = iStartHeight; + + m_pMagnifyUI->AddCheckBox( IDC_MAGNIFY_CHECKBOX_ENABLE, L"Magnify: RMouse", AMD::HUD::iElementOffset, iY, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, true ); + if (bSupportStickyMode) + { + m_pMagnifyUI->AddCheckBox( IDC_MAGNIFY_CHECKBOX_STICKY, L"Sticky Mode", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, true ); + } + + m_pMagnifyUI->AddStatic( IDC_MAGNIFY_STATIC_PIXEL_REGION, L"Magnify Region : 128", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight ); + m_pMagnifyUI->AddSlider( IDC_MAGNIFY_SLIDER_PIXEL_REGION, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, 16, 256, 128, true ); + + m_pMagnifyUI->AddStatic( IDC_MAGNIFY_STATIC_SCALE, L"Magnify Scale : 5", AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight ); + m_pMagnifyUI->AddSlider( IDC_MAGNIFY_SLIDER_SCALE, AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, 2, 10, 5, true ); + + EnableTool( false ); + EnableUI( false ); +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +HRESULT MagnifyTool::OnCreateDevice( ID3D11Device* pd3dDevice ) +{ + HRESULT hr; + + assert( NULL != pd3dDevice ); + + hr = m_Magnify.OnCreateDevice( pd3dDevice ); + assert( S_OK == hr ); + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +void MagnifyTool::OnResizedSwapChain( ID3D11Device* pd3dDevice, IDXGISwapChain *pSwapChain, + const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc, void* pUserContext, + int nPositionX, int nPositionY ) +{ + m_pMagnifyUI->SetLocation( nPositionX, nPositionY ); + m_pMagnifyUI->SetSize( AMD::HUD::iDialogWidth, pBackBufferSurfaceDesc->Height ); + + m_Magnify.OnResizedSwapChain( DXUTGetDXGIBackBufferSurfaceDesc() ); +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +void MagnifyTool::Render() +{ + if (m_pMagnifyUI->GetCheckBox( IDC_MAGNIFY_CHECKBOX_ENABLE )->GetEnabled() && + m_pMagnifyUI->GetCheckBox( IDC_MAGNIFY_CHECKBOX_ENABLE )->GetChecked()) + { + bool bRenderMagnifier = false; + POINT pt; + + m_Magnify.RenderBackground(); + + if (DXUTIsMouseButtonDown( VK_RBUTTON )) + { + if (m_pMagnifyUI->GetCheckBox( IDC_MAGNIFY_CHECKBOX_STICKY ) && m_pMagnifyUI->GetCheckBox( IDC_MAGNIFY_CHECKBOX_STICKY )->GetChecked()) + { + if (!m_bMouseDownLastFrame) + { + m_bStickyShowing ^= 1; + } + } + else + { + bRenderMagnifier = true; + } + + ::GetCursorPos( &pt ); + + if (m_bStickyShowing) + { + m_StickyPoint = pt; + } + + if (!m_bMouseDownLastFrame) + { + m_bMouseDownLastFrame = true; + } + } + else + { + if (m_bMouseDownLastFrame) + { + m_bMouseDownLastFrame = false; + } + } + + if (m_bStickyShowing) + { + bRenderMagnifier = true; + pt = m_StickyPoint; + } + + if (bRenderMagnifier) + { + m_Magnify.Capture( pt ); + m_Magnify.RenderMagnifiedRegion(); + } + } +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +void MagnifyTool::OnDestroyDevice() +{ + m_Magnify.OnDestroyDevice(); +} + + +//-------------------------------------------------------------------------------------- +// Hook function +//-------------------------------------------------------------------------------------- +void MagnifyTool::OnGUIEvent( UINT nEvent, int nControlID, CDXUTControl* pControl, void* pUserContext ) +{ + WCHAR szTemp[256]; + int nTemp; + bool bChecked; + + switch (nControlID) + { + case IDC_MAGNIFY_CHECKBOX_ENABLE: + bChecked = ((CDXUTCheckBox*)pControl)->GetChecked(); + EnableUI( bChecked ); + break; + + case IDC_MAGNIFY_CHECKBOX_STICKY: + m_bStickyShowing = false; + break; + + case IDC_MAGNIFY_SLIDER_PIXEL_REGION: + nTemp = m_pMagnifyUI->GetSlider( IDC_MAGNIFY_SLIDER_PIXEL_REGION )->GetValue(); + swprintf_s( szTemp, L"Magnify Region : %d", nTemp ); + m_pMagnifyUI->GetStatic( IDC_MAGNIFY_STATIC_PIXEL_REGION )->SetText( szTemp ); + m_Magnify.SetPixelRegion( nTemp ); + break; + + case IDC_MAGNIFY_SLIDER_SCALE: + nTemp = m_pMagnifyUI->GetSlider( IDC_MAGNIFY_SLIDER_SCALE )->GetValue(); + swprintf_s( szTemp, L"Magnify Scale : %d", nTemp ); + m_pMagnifyUI->GetStatic( IDC_MAGNIFY_STATIC_SCALE )->SetText( szTemp ); + m_Magnify.SetScale( nTemp ); + break; + } +} + +bool MagnifyTool::IsEnabled() +{ + return m_pMagnifyUI->GetCheckBox( IDC_MAGNIFY_CHECKBOX_ENABLE )->GetChecked(); +} + + +//-------------------------------------------------------------------------------------- +// Private method for UI control +//-------------------------------------------------------------------------------------- +void MagnifyTool::EnableTool( bool bEnable ) +{ + m_pMagnifyUI->GetCheckBox( IDC_MAGNIFY_CHECKBOX_ENABLE )->SetEnabled( bEnable ); +} + + +void MagnifyTool::EnableUI( bool bEnable ) +{ + if (m_pMagnifyUI->GetCheckBox( IDC_MAGNIFY_CHECKBOX_STICKY )) + { + m_pMagnifyUI->GetCheckBox( IDC_MAGNIFY_CHECKBOX_STICKY )->SetEnabled( bEnable ); + } + m_pMagnifyUI->GetStatic( IDC_MAGNIFY_STATIC_PIXEL_REGION )->SetEnabled( bEnable ); + m_pMagnifyUI->GetSlider( IDC_MAGNIFY_SLIDER_PIXEL_REGION )->SetEnabled( bEnable ); + m_pMagnifyUI->GetStatic( IDC_MAGNIFY_STATIC_SCALE )->SetEnabled( bEnable ); + m_pMagnifyUI->GetSlider( IDC_MAGNIFY_SLIDER_SCALE )->SetEnabled( bEnable ); + m_bStickyShowing = false; +} diff --git a/src/DX11/framework/amd_sdk/src/MagnifyTool.h b/src/DX11/framework/amd_sdk/src/MagnifyTool.h new file mode 100644 index 0000000..0c455cc --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/MagnifyTool.h @@ -0,0 +1,105 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: MagnifyTool.h +// +// MagnifyTool class definition. This class implements a user interface based upon +// the DXUT framework for the Magnify class. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_MAGNIFY_TOOL_H +#define AMD_SDK_MAGNIFY_TOOL_H + +#include "Magnify.h" + +namespace AMD +{ + + // GUI defines + enum MAGNIFY_TOOL_IDC + { + IDC_MAGNIFY_STATIC_CAPTION = 19 + 1024, + IDC_MAGNIFY_CHECKBOX_ENABLE, + IDC_MAGNIFY_CHECKBOX_STICKY, + IDC_MAGNIFY_STATIC_PIXEL_REGION, + IDC_MAGNIFY_SLIDER_PIXEL_REGION, + IDC_MAGNIFY_STATIC_SCALE, + IDC_MAGNIFY_SLIDER_SCALE + }; + + + class MagnifyTool + { + public: + + // Constructor / destructor + MagnifyTool(); + ~MagnifyTool(); + + // Set methods + void SetSourceResources( ID3D11Resource* pSourceRTResource, DXGI_FORMAT RTFormat, + int nWidth, int nHeight, int nSamples ); + void SetPixelRegion( int nPixelRegion ) { m_Magnify.SetPixelRegion( nPixelRegion ); } + void SetScale( int nScale ) { m_Magnify.SetScale( nScale ); } + + // Hooks for the DX SDK Framework + void InitApp( CDXUTDialog* pUI, int& iStartHeight, bool bSupportStickyMode = false ); + HRESULT OnCreateDevice( ID3D11Device* pd3dDevice ); + void OnResizedSwapChain( ID3D11Device* pd3dDevice, IDXGISwapChain *pSwapChain, + const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc, void* pUserContext, + int nPositionX, int nPositionY ); + void OnDestroyDevice(); + void OnGUIEvent( UINT nEvent, int nControlID, CDXUTControl* pControl, void* pUserContext ); + bool IsEnabled(); + + // Render + void Render(); + + private: + + // UI helper methods + void EnableTool( bool bEnable ); + void EnableUI( bool bEnable ); + + private: + + // The DXUT dialog + CDXUTDialog* m_pMagnifyUI; + + // Pointer to the Magnify class + AMD::Magnify m_Magnify; + + // The source resources + ID3D11Resource* m_pSourceRTResource; + DXGI_FORMAT m_RTFormat; + int m_nWidth; + int m_nHeight; + int m_nSamples; + bool m_bReleaseRTOnResize; + bool m_bMouseDownLastFrame; + bool m_bStickyShowing; + POINT m_StickyPoint; + }; + +} // namespace AMD + +#endif // AMD_SDK_MAGNIFY_TOOL_H diff --git a/src/DX11/framework/amd_sdk/src/ShaderCache.cpp b/src/DX11/framework/amd_sdk/src/ShaderCache.cpp new file mode 100644 index 0000000..8347953 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/ShaderCache.cpp @@ -0,0 +1,3473 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: ShaderCache.cpp +// +// Class implementation for the ShaderCache interface. Allows the user to add shaders to a list +// which is then compiled in parallel to object files. Future calls to create the shaders, +// will simply re-use the object files, making creation time very fast. The option is there, +// to force the regeneration of object files. +// +// Assumption, relies on following directory structure: +// +// SolutionDir\..\src\Shaders +//-------------------------------------------------------------------------------------- + +// DXUT helper code +#include "DXUT.h" +#include "SDKmisc.h" + +#include "ShaderCache.h" + +#include +#include +#include + +#include + +#pragma warning( disable : 4100 ) // disable unreference formal parameter warnings for /W4 builds +#pragma warning( disable : 4127 ) // disable conditional expression is constant warnings for /W4 builds +#pragma warning( disable : 4456 ) // disable declaration hides previous local declaration for /W4 builds + +using namespace AMD; + +// The done event handle +static HANDLE s_hDoneEvent = 0; + +static const wchar_t *FXC_PATH_STRING_LOCAL = L"\\src\\Shaders\\fxc.exe"; +static const wchar_t *DEV_PATH_STRING_LOCAL = L"\\src\\Shaders\\Dev.exe"; +static const wchar_t *FXC_PATH_STRING_INSTALLED_WIN_10_SDK = L"\\Windows Kits\\10\\bin\\x64\\fxc.exe"; +static const wchar_t *FXC_PATH_STRING_INSTALLED_WIN_8_1_SDK = L"\\Windows Kits\\8.1\\bin\\x64\\fxc.exe"; +static const wchar_t *FXC_PATH_STRING_INSTALLED_WIN_8_0_SDK = L"\\Windows Kits\\8.0\\bin\\x64\\fxc.exe"; +static const wchar_t *DEV_PATH_STRING_INSTALLED = L"\\Dev.exe"; + +//-------------------------------------------------------------------------------------- +// Constructor +//-------------------------------------------------------------------------------------- +ShaderCache::Shader::Shader() +{ + m_eShaderType = SHADER_TYPE_UNKNOWN; + m_ppShader = NULL; + m_ppInputLayout = NULL; + m_pInputLayoutDesc = NULL; + m_uNumDescElements = 0; + + m_bShaderUpToDate = false; + m_bGPRsUpToDate = false; + +#if AMD_SDK_INTERNAL_BUILD + m_eISATarget = DEFAULT_ISA_TARGET; + m_ISA_VGPRs = m_previous_ISA_VGPRs = 0; + m_ISA_SGPRs = m_previous_ISA_SGPRs = 0; + m_ISA_GPRPoolSize = m_previous_ISA_GPRPoolSize = 0; + m_ISA_ALUPacking = m_previous_ISA_ALUPacking = 0.0; +#endif + + memset( m_wsTarget, '\0', sizeof( wchar_t[m_uTARGET_MAX_LENGTH] ) ); + memset( m_wsEntryPoint, '\0', sizeof( wchar_t[m_uENTRY_POINT_MAX_LENGTH] ) ); + memset( m_wsSourceFile, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsCanonicalName, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + + m_uNumMacros = 0; + m_pMacros = NULL; + + memset( m_wsRawFileName, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsHashedFileName, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsObjectFile, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsErrorFile, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsAssemblyFile, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsAssemblyFileWithHashedFilename, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsISAFile, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsPreprocessFile, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsHashFile, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsCommandLine, '\0', sizeof( wchar_t[m_uCOMMAND_LINE_MAX_LENGTH] ) ); + memset( m_wsISACommandLine, '\0', sizeof( wchar_t[m_uCOMMAND_LINE_MAX_LENGTH] ) ); + memset( m_wsPreprocessCommandLine, '\0', sizeof( wchar_t[m_uCOMMAND_LINE_MAX_LENGTH] ) ); + + memset( m_wsObjectFile_with_ISA, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + memset( m_wsPreprocessFile_with_ISA, '\0', sizeof( wchar_t[m_uFILENAME_MAX_LENGTH] ) ); + + // Test that we can use paths > 255 characters with unicode file handling via \\?\ syntax + // Each section of the path needs to be <= 260 characters. + // Must first create path: + // C:\xpSnm8ixu8zR3lqGRtIbXMNOVE15oRgP7SwhsqRgkG7atxEOZbgsJmWXDLA7pCSUuQsqko9YN03e7aUw26Aoy9UpS3mSH1uekbTquhozgbB5KQwFxKzaBkSLpVmIWX8gQpoDd9mCTFLtbO0BCGdF7lF48KpxPFTjmNVgJK4sMfi5mavXhc + + FILE* pFile = NULL; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH + 1] = + { + L"\\\\?\\C:\\xpSnm8ixu8zR3lqGRtIbXMNOVE15oRgP7SwhsqRgkG7atxEOZbgs" + L"JmWXDLA7pCSUuQsqko9YN03e7aUw26Aoy9UpS3mSH1uekbTquhozgbB5KQwFxKz" + L"aBkSLpVmIWX8gQpoDd9mCTFLtbO0BCGdF7lF48KpxPFTjmNVgJK4sMfi5mavXhc" + L"\\rqgJRzfIBHlFGEcQrb3JUPcFGEt2S0ZnhetHvO2WNerlSOvqDVbBIey9bO7k0" + L"tytUih5E8ijWnbPHxF65X0jCuwikbtjkOXgoMBvoNGDlpfcrS0PVS7Ww5SJ3Ivg" + L"KdMj5VyN7qmfWkddiLoTvOybtkSchYW99uyQEgIkiPjM0mFmlCGIsTPFRDC.txt" + L"\0" + }; + + _wfopen_s( &pFile, wsShaderPathName, L"wb" ); + + if (pFile) + { + fwrite( "Hello, World!\0", 14, 1, pFile ); + fclose( pFile ); + } + + //DebugBreak(); + + + m_bBeingProcessed = false; + m_hCompileProcessHandle = NULL; + m_hCompileThreadHandle = NULL; + m_iCompileWaitCount = -1; + + m_pHash = NULL; + m_uHashLength = 0; + + m_pFilenameHash = NULL; + m_uFilenameHashLength = 0; + +} + + +//-------------------------------------------------------------------------------------- +// Destructor +//-------------------------------------------------------------------------------------- +ShaderCache::Shader::~Shader() +{ + if (NULL != m_pMacros) + { + delete [] m_pMacros; + m_pMacros = NULL; + } + + if (NULL != m_pHash) + { + free( m_pHash ); + m_pHash = NULL; + } + + if (NULL != m_pFilenameHash) + { + free( m_pFilenameHash ); + m_pFilenameHash = NULL; + } + + for (int iElement = 0; iElement < (int)m_uNumDescElements; iElement++) + { + delete [] m_pInputLayoutDesc[iElement].SemanticName; + } + delete [] m_pInputLayoutDesc; + m_pInputLayoutDesc = NULL; +} + +//-------------------------------------------------------------------------------------- +// Constructor +//-------------------------------------------------------------------------------------- +ShaderCache::ShaderCache( const SHADER_AUTO_RECOMPILE_TYPE i_keAutoRecompileTouchedShadersType, const ERROR_DISPLAY_TYPE i_keErrorDisplayType, + const GENERATE_ISA_TYPE i_keGenerateShaderISAType, const SHADER_COMPILER_EXE_TYPE i_keShaderCompilerExeType ) +{ + m_ShaderSourceList.clear(); + m_ShaderList.clear(); + m_PreprocessList.clear(); + m_HashList.clear(); + m_CompileList.clear(); + m_CompileCheckList.clear(); + m_CreateList.clear(); + m_ErrorList.clear(); + +#if AMD_SDK_INTERNAL_BUILD + m_ISATargetList.clear(); + m_ISATargetList.reserve( NUM_ISA_TARGETS ); + for (int i = 0; i < NUM_ISA_TARGETS; i++) + { + m_ISATargetList.push_back( new std::vector() ); + } +#endif + + BOOL bRet; + + InitializeCriticalSection( &m_CompileShaders_CriticalSection ); + InitializeCriticalSection( &m_GenISA_CriticalSection ); + + // the working dir we want for ShaderCache is not necessarily the current directory, + // so get the current directory and then specify our working dir relative to it + wchar_t wsWorkingDir[m_uPATHNAME_MAX_LENGTH]; + GetCurrentDirectoryW( m_uPATHNAME_MAX_LENGTH, wsWorkingDir ); + + // the safer PathCchCombine/PathCchCombineEx functions are not available in Win7, + // so just use PathCombine + PathCombine( m_wsWorkingDir, wsWorkingDir, L"..\\bin" ); + swprintf_s( m_wsUnicodeWorkingDir, L"%s%s", L"\\\\?\\", m_wsWorkingDir ); + + PathCombine( m_wsShaderSourceDir, m_wsWorkingDir, L"..\\src\\Shaders" ); + swprintf_s( m_wsUnicodeShaderSourceDir, L"%s%s", L"\\\\?\\", m_wsShaderSourceDir ); + + PathCombine( m_wsAmdSdkDir, m_wsWorkingDir, L"..\\amd_sdk" ); + + swprintf_s( m_wsBatchWorkingDir, L"%s", m_wsUnicodeWorkingDir ); + + wchar_t wsShadersDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsShadersDir, L"%s%s", m_wsWorkingDir, L"\\Shaders" ); + bRet = CreateDirectoryW( wsShadersDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + +#if AMD_SDK_INTERNAL_BUILD + swprintf_s( m_wsSCDEVWorkingDir, L"%s%s", wsShadersDir, L"\\ScDev" ); + bRet = CreateDirectoryW( m_wsSCDEVWorkingDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } +#endif + + wchar_t wsCacheDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsCacheDir, L"%s%s", wsShadersDir, L"\\Cache" ); + bRet = CreateDirectoryW( wsCacheDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsObjectDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsObjectDir, L"%s%s", wsCacheDir, L"\\Object" ); + bRet = CreateDirectoryW( wsObjectDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsObjectDebugDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsObjectDebugDir, L"%s%s", wsCacheDir, L"\\Object\\Debug" ); + bRet = CreateDirectoryW( wsObjectDebugDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsObjectReleaseDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsObjectReleaseDir, L"%s%s", wsCacheDir, L"\\Object\\Release" ); + bRet = CreateDirectoryW( wsObjectReleaseDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsErrorDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsErrorDir, L"%s%s", wsCacheDir, L"\\Error" ); + bRet = CreateDirectoryW( wsErrorDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsAssemblyDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsAssemblyDir, L"%s%s", wsCacheDir, L"\\Assembly" ); + bRet = CreateDirectoryW( wsAssemblyDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsISADir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsISADir, L"%s%s", wsCacheDir, L"\\ISA" ); + bRet = CreateDirectoryW( wsISADir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsPreprocessDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsPreprocessDir, L"%s%s", wsCacheDir, L"\\Preprocess" ); + bRet = CreateDirectoryW( wsPreprocessDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsHashDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsHashDir, L"%s%s", wsCacheDir, L"\\Hash" ); + bRet = CreateDirectoryW( wsHashDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsHashDebugDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsHashDebugDir, L"%s%s", wsCacheDir, L"\\Hash\\Debug" ); + bRet = CreateDirectoryW( wsHashDebugDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + wchar_t wsHashReleaseDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsHashReleaseDir, L"%s%s", wsCacheDir, L"\\Hash\\Release" ); + bRet = CreateDirectoryW( wsHashReleaseDir, NULL ); + if (bRet == ERROR_PATH_NOT_FOUND) + { + assert( false ); + } + + SYSTEM_INFO sysinfo; + GetSystemInfo( &sysinfo ); + m_uNumCPUCores = sysinfo.dwNumberOfProcessors; + SetMaximumCoresForShaderCompiler( MAXCORES_USE_ALL_BUT_ONE ); // Fast in Debug, no hitching + //SetMaximumCoresForShaderCompiler( MAXCORES_USE_ALL_CORES ); // Slightly faster in Release, barely any hitching + //SetMaximumCoresForShaderCompiler( MAXCORES_2X_CPU_CORES ); // Can be faster in Release, some hitching + //SetMaximumCoresForShaderCompiler( MAXCORES_NO_LIMIT ); // Can be faster in Release, a lot of hitching + + //SetMaximumCoresForShaderCompiler( MAXCORES_SINGLE_THREADED ); // Fast in Debug, no hitching + + s_hDoneEvent = CreateEvent( NULL, TRUE, FALSE, NULL ); + SetEvent( s_hDoneEvent ); + + m_CreateType = CREATE_TYPE_USE_CACHED; + + m_bShadersCreated = false; + m_bAbort = false; + m_bPrintedProgress = false; + + m_pProgressInfo = NULL; + m_uProgressCounter = 0; + + m_bForceDebugShaders = false; + + m_watchHandle = NULL; + m_waitPoolHandle = NULL; + +#if AMD_SDK_INTERNAL_BUILD + m_eTargetISA = DEFAULT_ISA_TARGET; +#endif + + m_bCreateHashDigest = true; +#if !AMD_SDK_PREBUILT_RELEASE_EXE + m_bRecompileTouchedShaders = (i_keAutoRecompileTouchedShadersType == SHADER_AUTO_RECOMPILE_ENABLED); + m_ErrorDisplayType = i_keErrorDisplayType; +#else + // the pre-built release executable ignores the passed-in construction parameters and just uses default settings + m_bRecompileTouchedShaders = false; + m_ErrorDisplayType = ERROR_DISPLAY_IN_DEBUG_OUTPUT_AND_BREAK; +#endif + m_bShowShaderErrors = (i_keErrorDisplayType == ERROR_DISPLAY_ON_SCREEN); +#if AMD_SDK_INTERNAL_BUILD +#if AMD_SDK_PREBUILT_RELEASE_EXE +#error The pre-built release exe exists specifically to release (i.e. it's external) +#endif + m_bGenerateShaderISA = (i_keGenerateShaderISAType == GENERATE_ISA_ENABLED); +#else + m_bGenerateShaderISA = false; +#endif + + m_bHasShaderErrorsToDisplay = false; + m_shaderErrorRenderedCount = 0; + + swprintf_s( m_wsLastShaderError, L"*** 0 Shader Errors ***\n" ); + +#if AMD_SDK_INTERNAL_BUILD + if (i_keShaderCompilerExeType == SHADER_COMPILER_EXE_LOCAL) + { + swprintf_s( m_wsFxcExePath, L"%s%s", m_wsAmdSdkDir, FXC_PATH_STRING_LOCAL ); + swprintf_s( m_wsDevExePath, L"%s%s", m_wsAmdSdkDir, DEV_PATH_STRING_LOCAL ); + } + else +#endif + { + // search for fxc in the win8.1 sdk. If not found, then try the 8.0 sdk. + wchar_t wsProgramFilesDir[MAX_PATH]; + SHGetSpecialFolderPath( + 0, + wsProgramFilesDir, + CSIDL_PROGRAM_FILESX86, + FALSE ); + swprintf_s( m_wsFxcExePath, L"%s%s", wsProgramFilesDir, FXC_PATH_STRING_INSTALLED_WIN_10_SDK ); + if (!CheckFXC()) + { + swprintf_s( m_wsFxcExePath, L"%s%s", wsProgramFilesDir, FXC_PATH_STRING_INSTALLED_WIN_8_1_SDK ); + if (!CheckFXC()) + { + swprintf_s( m_wsFxcExePath, L"%s%s", wsProgramFilesDir, FXC_PATH_STRING_INSTALLED_WIN_8_0_SDK ); + } + } + + // get the scdev environment variable + size_t requiredSizeForScDevEnvVar; + wchar_t wsScDevDir[MAX_PATH] = { L'\0' }; + _wgetenv_s( &requiredSizeForScDevEnvVar, wsScDevDir, MAX_PATH, L"AMD_SCDEV_DIR" ); + swprintf_s( m_wsDevExePath, L"%s%s", wsScDevDir, DEV_PATH_STRING_INSTALLED ); + } + + if (m_bGenerateShaderISA) + { + if (!CheckSCDEV()) + { + m_bGenerateShaderISA = false; + +#if !AMD_SDK_PREBUILT_RELEASE_EXE + // For SHADER_COMPILER_EXE_INSTALLED, Dev.exe is assumed to be in location specified in AMD_SCDEV_DIR environment variable + // For SHADER_COMPILER_EXE_LOCAL, Dev.exe is assumed to be in AMD_SDK\src\Shaders + DebugBreak(); +#endif + } + } + + if (!CheckFXC()) + { +#if !AMD_SDK_PREBUILT_RELEASE_EXE + // For SHADER_COMPILER_EXE_INSTALLED, fxc.exe is assumed to be in the default Win8 SDK install location + // For SHADER_COMPILER_EXE_LOCAL, fxc.exe is assumed to be in AMD_SDK\src\Shaders + DebugBreak(); +#endif + } + + m_bShowShaderISA = m_bGenerateShaderISA; + + if (m_bRecompileTouchedShaders) + { +#if defined(DEBUG) || defined(_DEBUG) + const bool watchOK = WatchDirectoryForChanges(); + assert( watchOK ); +#else + WatchDirectoryForChanges(); +#endif + } + +} + + +//-------------------------------------------------------------------------------------- +// Destructor +//-------------------------------------------------------------------------------------- +ShaderCache::~ShaderCache() +{ + WaitForSingleObject( s_hDoneEvent, INFINITE ); + CloseHandle( s_hDoneEvent ); + + for (std::list::iterator it = m_ShaderSourceList.begin(); it != m_ShaderSourceList.end(); it++) + { + Shader* pShader = *it; + delete pShader; + } + + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + delete pShader; + } + +#if AMD_SDK_INTERNAL_BUILD + for (std::vector< std::vector * >::iterator it = m_ISATargetList.begin(); it != m_ISATargetList.end(); it++) + { + std::vector * pVector = *it; + pVector->clear(); + delete pVector; + } +#endif + + m_ShaderSourceList.clear(); + m_ShaderList.clear(); + m_PreprocessList.clear(); + m_HashList.clear(); + m_CompileList.clear(); + m_CompileCheckList.clear(); + m_CreateList.clear(); + m_ErrorList.clear(); + +#if AMD_SDK_INTERNAL_BUILD + m_ISATargetList.clear(); +#endif + + if (NULL != m_pProgressInfo) + { + delete [] m_pProgressInfo; + m_pProgressInfo = NULL; + } + + if (m_waitPoolHandle) + { + UnregisterWaitEx( m_waitPoolHandle, INVALID_HANDLE_VALUE ); + m_waitPoolHandle = NULL; + } + + if (m_watchHandle) + { + FindCloseChangeNotification( m_watchHandle ); + m_watchHandle = NULL; + } + + DeleteCriticalSection( &m_GenISA_CriticalSection ); + DeleteCriticalSection( &m_CompileShaders_CriticalSection ); + + m_bRecompileTouchedShaders = false; +} + + +//-------------------------------------------------------------------------------------- +// DXUT framework hook method (flags shaders as needing creation) +//-------------------------------------------------------------------------------------- +void ShaderCache::OnDestroyDevice() +{ + m_bShadersCreated = false; + InvalidateShaders(); +} + + +//-------------------------------------------------------------------------------------- +// Called by app when WM_QUIT is posted, so that shader generation can be aborted +//-------------------------------------------------------------------------------------- +void ShaderCache::Abort() +{ + m_bAbort = true; +} + +//-------------------------------------------------------------------------------------- +// Allows the ShaderCache to add a new type of ISA Target version of all shaders to the cache +//-------------------------------------------------------------------------------------- +bool ShaderCache::CloneShaders( void ) +{ + bool bRVal = true; + +#if AMD_SDK_INTERNAL_BUILD + for (std::list::iterator it = m_ShaderSourceList.begin(); it != m_ShaderSourceList.end(); it++) + { + Shader* pShaderSource = *it; + + // check if you already have a shader for for this ISA Target + if (std::find( m_ISATargetList[m_eTargetISA]->begin(), m_ISATargetList[m_eTargetISA]->end(), pShaderSource ) == m_ISATargetList[m_eTargetISA]->end()) + { + // if not, make one + bRVal &= AddShader( NULL, + pShaderSource->m_eShaderType, + pShaderSource->m_wsTarget, + pShaderSource->m_wsEntryPoint, + pShaderSource->m_wsSourceFile, + pShaderSource->m_uNumMacros, + pShaderSource->m_pMacros, + pShaderSource->m_ppInputLayout, + pShaderSource->m_pInputLayoutDesc, + pShaderSource->m_uNumDescElements, + pShaderSource->m_wsCanonicalName, + pShaderSource->m_ISA_VGPRs, + pShaderSource->m_ISA_SGPRs, + false + ); + + // and mark in the list that you now have one for this ISA Target + m_ISATargetList[m_eTargetISA]->push_back( pShaderSource ); + } + } +#endif + + return bRVal; +} + +void ShaderCache::InsertOutputFilenameIntoCommandLine( wchar_t *pwsCommandLine, const wchar_t* pwsFileName ) const +{ + // enclose path in quotes to handle spaces in path + { + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"\"" ); + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, m_wsUnicodeWorkingDir ); + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"\\" ); + } + + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, pwsFileName ); + + // enclose path in quotes to handle spaces in path + { + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"\"" ); + } +} + +void ShaderCache::InsertInputFilenameIntoCommandLine( wchar_t *pwsCommandLine, const wchar_t* pwsFileName ) const +{ + // enclose path in quotes to handle spaces in path + { + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"\"" ); + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, m_wsUnicodeShaderSourceDir ); + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"\\" ); + } + + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, pwsFileName ); + + // enclose path in quotes to handle spaces in path + { + wcscat_s( pwsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"\"" ); + } +} + +//-------------------------------------------------------------------------------------- +// User adds a shader to the cache +//-------------------------------------------------------------------------------------- +bool ShaderCache::AddShader( ID3D11DeviceChild** ppShader, + SHADER_TYPE ShaderType, + const wchar_t* pwsTarget, + const wchar_t* pwsEntryPoint, + const wchar_t* pwsSourceFile, + unsigned int uNumMacros, + Macro* pMacros, + ID3D11InputLayout** ppInputLayout, + const D3D11_INPUT_ELEMENT_DESC* pInputLayoutDesc, + unsigned int uNumDescElements, + const wchar_t* pwsCanonicalName, + const int i_iMaxVGPR, + const int i_iMaxSGPR, + const bool i_kbIsApplicationShader + ) +{ +#if AMD_SDK_INTERNAL_BUILD + assert( (NULL != ppShader) || (!i_kbIsApplicationShader) ); +#else + assert( NULL != ppShader && i_kbIsApplicationShader); +#endif + assert( (ShaderType >= SHADER_TYPE_VERTEX) && (ShaderType <= SHADER_TYPE_COMPUTE) ); + assert( (NULL != pwsTarget) && (wcslen( pwsTarget ) <= m_uTARGET_MAX_LENGTH) ); + assert( (NULL != pwsEntryPoint) && (wcslen( pwsEntryPoint ) <= m_uENTRY_POINT_MAX_LENGTH) ); + assert( (NULL != pwsSourceFile) && (wcslen( pwsSourceFile ) <= m_uFILENAME_MAX_LENGTH) ); + if (uNumMacros > 0) + { + assert( NULL != pMacros ); + } + + if (i_kbIsApplicationShader) + { + Shader* pShaderSource = new Shader(); + pShaderSource->m_eShaderType = ShaderType; + wcscpy_s( pShaderSource->m_wsTarget, m_uTARGET_MAX_LENGTH, pwsTarget ); + wcscpy_s( pShaderSource->m_wsEntryPoint, m_uENTRY_POINT_MAX_LENGTH, pwsEntryPoint ); + wcscpy_s( pShaderSource->m_wsSourceFile, m_uFILENAME_MAX_LENGTH, pwsSourceFile ); + pShaderSource->m_uNumMacros = uNumMacros; + pShaderSource->m_uNumDescElements = uNumDescElements; + pShaderSource->m_ppInputLayout = ppInputLayout; + if (NULL != pwsCanonicalName) + { + wcscpy_s( pShaderSource->m_wsCanonicalName, m_uFILENAME_MAX_LENGTH, pwsCanonicalName ); + } +#if AMD_SDK_INTERNAL_BUILD + pShaderSource->m_ISA_VGPRs = i_iMaxVGPR; + pShaderSource->m_ISA_SGPRs = i_iMaxSGPR; +#endif + + if (pShaderSource->m_uNumMacros > 0) + { + pShaderSource->m_pMacros = new Macro[pShaderSource->m_uNumMacros]; + memcpy( pShaderSource->m_pMacros, pMacros, sizeof( Macro ) * pShaderSource->m_uNumMacros ); + } + + if (pShaderSource->m_eShaderType == SHADER_TYPE_VERTEX) + { + if (pShaderSource->m_uNumDescElements > 0) + { + assert( NULL != ppInputLayout ); + assert( NULL != pInputLayoutDesc ); + + pShaderSource->m_pInputLayoutDesc = new D3D11_INPUT_ELEMENT_DESC[pShaderSource->m_uNumDescElements]; + + memcpy( pShaderSource->m_pInputLayoutDesc, pInputLayoutDesc, sizeof( D3D11_INPUT_ELEMENT_DESC ) * pShaderSource->m_uNumDescElements ); + + for (int iElement = 0; iElement < (int)pShaderSource->m_uNumDescElements; iElement++) + { + pShaderSource->m_pInputLayoutDesc[iElement].SemanticName = new char[m_uFILENAME_MAX_LENGTH]; + strcpy_s( (char*)pShaderSource->m_pInputLayoutDesc[iElement].SemanticName, m_uFILENAME_MAX_LENGTH, (char*)pInputLayoutDesc[iElement].SemanticName ); + } + } + } + + m_ShaderSourceList.push_back( pShaderSource ); +#if AMD_SDK_INTERNAL_BUILD + m_ISATargetList[m_eTargetISA]->push_back( pShaderSource ); +#endif + } + + Shader* pShader = new Shader(); + if (i_kbIsApplicationShader) + { // Only copy this if this is an app shader; if we are cloning a shader, we won't render with it, so keep m_ppShader NULL. + pShader->m_ppShader = ppShader; + } + + pShader->m_eShaderType = ShaderType; +#if AMD_SDK_INTERNAL_BUILD + pShader->m_eISATarget = m_eTargetISA; +#endif + + if (pShader->m_eShaderType == SHADER_TYPE_VERTEX) + { + pShader->m_uNumDescElements = uNumDescElements; + + if (pShader->m_uNumDescElements > 0) + { + assert( NULL != ppInputLayout ); + assert( NULL != pInputLayoutDesc ); + + pShader->m_ppInputLayout = ppInputLayout; + + pShader->m_pInputLayoutDesc = new D3D11_INPUT_ELEMENT_DESC[pShader->m_uNumDescElements]; + + memcpy( pShader->m_pInputLayoutDesc, pInputLayoutDesc, sizeof( D3D11_INPUT_ELEMENT_DESC ) * pShader->m_uNumDescElements ); + + for (int iElement = 0; iElement < (int)pShader->m_uNumDescElements; iElement++) + { + pShader->m_pInputLayoutDesc[iElement].SemanticName = new char[m_uFILENAME_MAX_LENGTH]; + strcpy_s( (char*)pShader->m_pInputLayoutDesc[iElement].SemanticName, m_uFILENAME_MAX_LENGTH, (char*)pInputLayoutDesc[iElement].SemanticName ); + } + } + } + + wcscpy_s( pShader->m_wsTarget, m_uTARGET_MAX_LENGTH, pwsTarget ); + wcscpy_s( pShader->m_wsEntryPoint, m_uENTRY_POINT_MAX_LENGTH, pwsEntryPoint ); + wcscpy_s( pShader->m_wsSourceFile, m_uFILENAME_MAX_LENGTH, pwsSourceFile ); + if (NULL != pwsCanonicalName) + { + wcscpy_s( pShader->m_wsCanonicalName, m_uFILENAME_MAX_LENGTH, pwsCanonicalName ); + } + + pShader->m_uNumMacros = uNumMacros; + if (pShader->m_uNumMacros > 0) + { + pShader->m_pMacros = new Macro[pShader->m_uNumMacros]; + memcpy( pShader->m_pMacros, pMacros, sizeof( Macro ) * pShader->m_uNumMacros ); + } + + // Object, error, assembly, preprocess, and hash file names + wchar_t wsFileNameBody[m_uFILENAME_MAX_LENGTH] = { 0 }; +#ifdef _DEBUG + wcscat_s( pShader->m_wsObjectFile, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\Object\\Debug\\" ); + wcscat_s( pShader->m_wsHashFile, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\Hash\\Debug\\" ); +#else + wcscat_s( pShader->m_wsObjectFile, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\Object\\Release\\" ); + wcscat_s( pShader->m_wsHashFile, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\Hash\\Release\\" ); +#endif + wcscat_s( pShader->m_wsErrorFile, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\Error\\" ); + wcscat_s( pShader->m_wsAssemblyFile, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\Assembly\\" ); + wcscat_s( pShader->m_wsISAFile, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\ISA\\" ); + wcscat_s( pShader->m_wsPreprocessFile, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\Preprocess\\" ); + + if (NULL != pwsCanonicalName) + { + wcscat_s( wsFileNameBody, m_uFILENAME_MAX_LENGTH, pShader->m_wsCanonicalName ); + } + else + { + wcscpy_s( wsFileNameBody, m_uFILENAME_MAX_LENGTH, pwsEntryPoint ); + for (int iMacro = 0; iMacro < (int)pShader->m_uNumMacros; ++iMacro) + { + wchar_t wsValue[64]; + wcscat_s( wsFileNameBody, m_uFILENAME_MAX_LENGTH, L"_" ); + wcscat_s( wsFileNameBody, m_uFILENAME_MAX_LENGTH, pShader->m_pMacros[iMacro].m_wsName ); + wcscat_s( wsFileNameBody, m_uFILENAME_MAX_LENGTH, L"=" ); + _itow_s( pShader->m_pMacros[iMacro].m_iValue, wsValue, 10 ); + wcscat_s( wsFileNameBody, m_uFILENAME_MAX_LENGTH, wsValue ); + } + } + + wcscat_s( pShader->m_wsRawFileName, m_uFILENAME_MAX_LENGTH, wsFileNameBody ); + wcscat_s( pShader->m_wsObjectFile, m_uFILENAME_MAX_LENGTH, wsFileNameBody ); + wcscat_s( pShader->m_wsErrorFile, m_uFILENAME_MAX_LENGTH, wsFileNameBody ); + wcscat_s( pShader->m_wsAssemblyFile, m_uFILENAME_MAX_LENGTH, wsFileNameBody ); + wcscat_s( pShader->m_wsPreprocessFile, m_uFILENAME_MAX_LENGTH, wsFileNameBody ); + wcscat_s( pShader->m_wsHashFile, m_uFILENAME_MAX_LENGTH, wsFileNameBody ); + + wcscat_s( pShader->m_wsObjectFile, m_uFILENAME_MAX_LENGTH, L".obj" ); + wcscat_s( pShader->m_wsErrorFile, m_uFILENAME_MAX_LENGTH, L".txt" ); + wcscat_s( pShader->m_wsAssemblyFile, m_uFILENAME_MAX_LENGTH, L".asm" ); + wcscat_s( pShader->m_wsPreprocessFile, m_uFILENAME_MAX_LENGTH, L".ppf" ); + wcscat_s( pShader->m_wsHashFile, m_uFILENAME_MAX_LENGTH, L".hsh" ); + + pShader->SetupHashedFilename(); + + // Setup Hashed Assembly Filename + wcscat_s( pShader->m_wsAssemblyFileWithHashedFilename, m_uFILENAME_MAX_LENGTH, L"Shaders\\Cache\\Assembly\\" ); + wcscat_s( pShader->m_wsAssemblyFileWithHashedFilename, m_uFILENAME_MAX_LENGTH, pShader->m_wsHashedFileName ); + wcscat_s( pShader->m_wsAssemblyFileWithHashedFilename, m_uFILENAME_MAX_LENGTH, L".asm" ); + +#if AMD_SDK_INTERNAL_BUILD + // ISA File now also uses hashed filename + wcscat_s( pShader->m_wsISAFile, m_uFILENAME_MAX_LENGTH, pShader->m_wsHashedFileName ); + wcscat_s( pShader->m_wsISAFile, m_uFILENAME_MAX_LENGTH, L".asm." ); + wcscat_s( pShader->m_wsISAFile, m_uFILENAME_MAX_LENGTH, AmdTargetInfo[pShader->m_eISATarget].m_Name ); + wcscat_s( pShader->m_wsISAFile, m_uFILENAME_MAX_LENGTH, L".dump.isa" ); + + wcscat_s( pShader->m_wsObjectFile_with_ISA, m_uFILENAME_MAX_LENGTH, pShader->m_wsObjectFile ); + wcscat_s( pShader->m_wsPreprocessFile_with_ISA, m_uFILENAME_MAX_LENGTH, pShader->m_wsPreprocessFile ); + + if (m_bGenerateShaderISA) + { + wcscat_s( pShader->m_wsObjectFile_with_ISA, m_uFILENAME_MAX_LENGTH, L"." ); + wcscat_s( pShader->m_wsObjectFile_with_ISA, m_uFILENAME_MAX_LENGTH, AmdTargetInfo[pShader->m_eISATarget].m_Name ); + wcscat_s( pShader->m_wsPreprocessFile_with_ISA, m_uFILENAME_MAX_LENGTH, L"." ); + wcscat_s( pShader->m_wsPreprocessFile_with_ISA, m_uFILENAME_MAX_LENGTH, AmdTargetInfo[pShader->m_eISATarget].m_Name ); + } +#endif + + // Compilation flags based on build profile + wchar_t wsCompilationFlags[m_uFILENAME_MAX_LENGTH]; +#ifdef _DEBUG + // Best flags for shader debugging + // /Zi - Enable debugging information + // /Od - Disable optimizations + // /Gfp - Prefer flow control constructs + wcscpy_s( wsCompilationFlags, m_uFILENAME_MAX_LENGTH, L" /Zi /Od /Gfp" ); +#else + if (m_bForceDebugShaders) + { + // Best flags for shader debugging + // /Zi - Enable debugging information + // /Od - Disable optimizations + // /Gfp - Prefer flow control constructs + wcscpy_s( wsCompilationFlags, m_uFILENAME_MAX_LENGTH, L" /Od" ); + } + else + { + // Select optimization level ( 1 is default) + // /O{0,1,2,3} - Optimization Level + wcscpy_s( wsCompilationFlags, m_uFILENAME_MAX_LENGTH, L" /O1" ); + } +#endif + + // Command line + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /T " ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, pwsTarget ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, wsCompilationFlags ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /E " ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, pwsEntryPoint ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /Fo " ); + InsertOutputFilenameIntoCommandLine( pShader->m_wsCommandLine, pShader->m_wsObjectFile ); + for (int iMacro = 0; iMacro < (int)pShader->m_uNumMacros; ++iMacro) + { + wchar_t wsValue[64]; + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /D " ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, pShader->m_pMacros[iMacro].m_wsName ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"=" ); + _itow_s( pShader->m_pMacros[iMacro].m_iValue, wsValue, 10 ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, wsValue ); + } + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /Fe " ); + InsertOutputFilenameIntoCommandLine( pShader->m_wsCommandLine, pShader->m_wsErrorFile ); + /* wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /Fc " ); + InsertOutputFilenameIntoCommandLine( pShader->m_wsCommandLine, pShader->m_wsAssemblyFile );*/ + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /Fc " ); // Fx for HEX + InsertOutputFilenameIntoCommandLine( pShader->m_wsCommandLine, pShader->m_wsAssemblyFileWithHashedFilename ); + wcscat_s( pShader->m_wsCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" " ); + InsertInputFilenameIntoCommandLine( pShader->m_wsCommandLine, pShader->m_wsSourceFile ); + +#if AMD_SDK_INTERNAL_BUILD + // ISA SCDev Command line + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" -q " ); + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" -ns " ); + + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" -" ); + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, AmdTargetInfo[m_eTargetISA].m_Name ); + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" " ); + + if (i_iMaxVGPR > 0) + { + wchar_t wsValue[64]; + _itow_s( i_iMaxVGPR, wsValue, 10 ); + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" -vgprs " ); + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, wsValue ); + } + if (i_iMaxSGPR > 0) + { + wchar_t wsValue[64]; + _itow_s( i_iMaxSGPR, wsValue, 10 ); + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" -sgprs " ); + wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, wsValue ); + } + // wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" " ); + // wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"\"" ); + // wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, pShader->m_wsAssemblyFile ); + // wcscat_s( pShader->m_wsISACommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"\"" ); +#endif + + // Preprocess command line + wcscat_s( pShader->m_wsPreprocessCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /E " ); + wcscat_s( pShader->m_wsPreprocessCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, pwsEntryPoint ); + wcscat_s( pShader->m_wsPreprocessCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" " ); + InsertInputFilenameIntoCommandLine( pShader->m_wsPreprocessCommandLine, pShader->m_wsSourceFile ); + wcscat_s( pShader->m_wsPreprocessCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /P " ); + InsertOutputFilenameIntoCommandLine( pShader->m_wsPreprocessCommandLine, pShader->m_wsPreprocessFile ); + for (int iMacro = 0; iMacro < (int)pShader->m_uNumMacros; ++iMacro) + { + wchar_t wsValue[64]; + wcscat_s( pShader->m_wsPreprocessCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L" /D " ); + wcscat_s( pShader->m_wsPreprocessCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, pShader->m_pMacros[iMacro].m_wsName ); + wcscat_s( pShader->m_wsPreprocessCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, L"=" ); + _itow_s( pShader->m_pMacros[iMacro].m_iValue, wsValue, 10 ); + wcscat_s( pShader->m_wsPreprocessCommandLine, m_uCOMMAND_LINE_MAX_LENGTH, wsValue ); + } + + m_ShaderList.push_back( pShader ); + + return true; +} + + +//-------------------------------------------------------------------------------------- +// The shader thread proc, has to be public, but must not be called by user +//-------------------------------------------------------------------------------------- +DWORD WINAPI GenerateShaders_ThreadProc_( void* pParameter ) +{ + ShaderCache* pShaderCache = (ShaderCache*)pParameter; + + pShaderCache->GenerateShadersThreadProc(); + + SetEvent( s_hDoneEvent ); + + return 0; +} + + +//-------------------------------------------------------------------------------------- +// Initiates shader generation based upon the creation flags: +// CREATE_TYPE_FORCE_COMPILE, // Clean the cache, and compile all +// CREATE_TYPE_COMPILE_CHANGES, // Only compile shaders that have changed (development mode) +// CREATE_TYPE_USE_CACHED, // Use cached shaders (release mode) +//-------------------------------------------------------------------------------------- +HRESULT ShaderCache::GenerateShaders( CREATE_TYPE CreateType, const bool i_kbRecreateShaders ) +{ + DWORD dwRet = WaitForSingleObject( s_hDoneEvent, 0 ); + + if (dwRet == WAIT_OBJECT_0) + { +#if !AMD_SDK_PREBUILT_RELEASE_EXE + m_CreateType = CreateType; +#else + // ignore the CreateType parameter for the pre-built release, + // because the point of the pre-built is that it doesn't require + // the DXSDK, Win8 SDK, etc. + m_CreateType = CREATE_TYPE_USE_CACHED; +#endif + m_bShadersCreated = false; + m_bPrintedProgress = false; + + if (i_kbRecreateShaders) + { + m_CreateList.clear(); + } + + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + + if ((m_CreateType == CREATE_TYPE_COMPILE_CHANGES) || + (m_CreateType == CREATE_TYPE_FORCE_COMPILE) || + (!CheckObjectFile( pShader ))) + { + m_PreprocessList.push_back( pShader ); + } + else + { + m_CreateList.push_back( pShader ); + } + } + + if (m_PreprocessList.size()) + { + m_pProgressInfo = new ProgressInfo[m_PreprocessList.size() * 2]; + m_uProgressCounter = 0; + + ResetEvent( s_hDoneEvent ); + QueueUserWorkItem( GenerateShaders_ThreadProc_, this, WT_EXECUTELONGFUNCTION ); + } + else + { + SetEvent( s_hDoneEvent ); + } + } + + if ((m_CreateType == CREATE_TYPE_USE_CACHED) || ShadersReady()) + { + GenerateShaderGPRUsageFromISAForAllShaders(); + } + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Called by the thread proc to actaully do the work +//-------------------------------------------------------------------------------------- +void ShaderCache::GenerateShadersThreadProc() +{ + DeleteErrorFiles(); + DeleteAssemblyFiles(); + DeletePreprocessFiles(); + + if (m_CreateType == CREATE_TYPE_FORCE_COMPILE) + { + DeleteHashFiles(); + DeleteObjectFiles(); + } + + // Remove Old Shader Errors from displaying over shader recompilation + m_bHasShaderErrorsToDisplay = false; + m_shaderErrorRenderedCount = 0; + + PreprocessShaders(); + CompileShaders(); +} + +//-------------------------------------------------------------------------------------- +// Renders the progress of the shader generation process +//-------------------------------------------------------------------------------------- +void ShaderCache::RenderProgress( CDXUTTextHelper* g_pTxtHelper, int iFontHeight, DirectX::XMVECTOR FontColor ) +{ + wchar_t wsOverallProgress[m_uPATHNAME_MAX_LENGTH]; + wchar_t wsCurrentLine[m_uCOMMAND_LINE_MAX_LENGTH]; + + g_pTxtHelper->Begin(); + g_pTxtHelper->SetForegroundColor( FontColor ); + g_pTxtHelper->SetInsertionPos( 5, 5 ); + + int iNumLines = (int)((DXUTGetDXGIBackBufferSurfaceDesc()->Height - (iFontHeight)) * 0.99f / iFontHeight); + + if (!m_bPrintedProgress && !m_PreprocessList.size()) + { + swprintf_s( wsOverallProgress, L"*** Shader Cache: Creating Shaders... ***" ); + g_pTxtHelper->DrawTextLine( wsOverallProgress ); + + m_bPrintedProgress = true; + } + else + { + swprintf_s( wsOverallProgress, L"*** Shader Cache: Shaders to Preprocess = %d, Compile = %d ***", (int)m_PreprocessList.size(), (int)m_CompileList.size() ); + g_pTxtHelper->DrawTextLine( wsOverallProgress ); + } + + if (NULL != m_pProgressInfo) + { + g_pTxtHelper->SetInsertionPos( 5, 5 + iFontHeight ); + + int iCounter = m_uProgressCounter; + int iStrings = (iCounter < iNumLines) ? (iCounter) : (iNumLines); + + for (int i = iCounter - iStrings; i < iCounter; i++) + { + if (m_pProgressInfo[i].m_pShader->m_iCompileWaitCount >= 0) + { + swprintf_s( wsCurrentLine, L"%s ... [%s][%i]", m_pProgressInfo[i].m_wsFilename, m_pProgressInfo[i].m_pShader->m_wsCompileStatus, m_pProgressInfo[i].m_pShader->m_iCompileWaitCount ); + } + else + { + swprintf_s( wsCurrentLine, L"%s ... [%s]", m_pProgressInfo[i].m_wsFilename, m_pProgressInfo[i].m_pShader->m_wsCompileStatus/*m_pProgressInfo[i].m_wsStatus*/ ); + } + g_pTxtHelper->DrawTextLine( wsCurrentLine ); + } + } + + g_pTxtHelper->End(); + + if (ShowShaderErrors() && HasErrorsToDisplay()) + { + RenderShaderErrors( g_pTxtHelper, iFontHeight, FontColor ); + } +} + + +//-------------------------------------------------------------------------------------- +// boolean method to determine if the shaders are ready +//-------------------------------------------------------------------------------------- +bool ShaderCache::ShadersReady() +{ + if (TryEnterCriticalSection( &m_CompileShaders_CriticalSection )) + { + + DWORD dwRet = WaitForSingleObject( s_hDoneEvent, 0 ); + + if (dwRet == WAIT_OBJECT_0) + { + if (m_bPrintedProgress) + { + if (!m_bShadersCreated) + { + CreateShaders(); + m_bShadersCreated = true; + + if (NULL != m_pProgressInfo) + { + delete [] m_pProgressInfo; + m_pProgressInfo = NULL; + m_uProgressCounter = 0; + } + } + + LeaveCriticalSection( &m_CompileShaders_CriticalSection ); + return true; + } + } + LeaveCriticalSection( &m_CompileShaders_CriticalSection ); + + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +// public and private setter/getter methods: +//-------------------------------------------------------------------------------------- + +const bool ShaderCache::HasErrorsToDisplay( void ) const +{ + return m_bHasShaderErrorsToDisplay; +} + +const bool ShaderCache::ShowShaderErrors( void ) const +{ + return (m_ErrorDisplayType == ERROR_DISPLAY_ON_SCREEN) && m_bShowShaderErrors; +} + +const int ShaderCache::ShaderErrorDisplayType( void ) const +{ + return m_ErrorDisplayType; +} + +const bool ShaderCache::RecompileTouchedShaders( void ) const +{ + return m_bRecompileTouchedShaders; +} + +const bool ShaderCache::GenerateISAGPRPressure( void ) const +{ + return m_bGenerateShaderISA; +} + +const bool ShaderCache::ShowISAGPRPressure( void ) const +{ + return m_bShowShaderISA; +} + +void ShaderCache::SetRecompileTouchedShadersFlag( const bool i_bRecompileWhenTouched ) +{ + m_bRecompileTouchedShaders = i_bRecompileWhenTouched; + + if (m_bRecompileTouchedShaders) + { + // Create Directory Watcher + if ((m_waitPoolHandle == NULL) || (m_watchHandle == NULL)) + { +#if defined(DEBUG) || defined(_DEBUG) + const bool kb_Success = WatchDirectoryForChanges(); + assert( kb_Success ); +#else + WatchDirectoryForChanges(); +#endif + } + } +} + +void ShaderCache::SetMaximumCoresForShaderCompiler( const int ki_MaxCores ) +{ + + switch (ki_MaxCores) + { + case MAXCORES_NO_LIMIT: + m_MaxCoresType = MAXCORES_NO_LIMIT; + m_uNumCPUCoresToUse = 65536; + break; + case MAXCORES_2X_CPU_CORES: + m_MaxCoresType = MAXCORES_2X_CPU_CORES; + m_uNumCPUCoresToUse = m_uNumCPUCores * 2; + break; + case MAXCORES_USE_ALL_CORES: + m_MaxCoresType = MAXCORES_USE_ALL_CORES; + m_uNumCPUCoresToUse = m_uNumCPUCores; + break; + case MAXCORES_MULTI_THREADED: + case MAXCORES_USE_ALL_BUT_ONE: + m_MaxCoresType = MAXCORES_USE_ALL_BUT_ONE; + m_uNumCPUCoresToUse = (m_uNumCPUCores > 1) ? (m_uNumCPUCores - 1) : (1); + break; + case MAXCORES_SINGLE_THREADED: + m_MaxCoresType = MAXCORES_SINGLE_THREADED; + m_uNumCPUCoresToUse = 1; + break; + default: + m_MaxCoresType = MAXCORES_MULTI_THREADED; + m_uNumCPUCoresToUse = ki_MaxCores; + break; + }; + + return; + +} + +void ShaderCache::SetShowShaderErrorsFlag( const bool i_kbShowShaderErrors ) +{ + m_bShowShaderErrors = i_kbShowShaderErrors; +} + +void ShaderCache::SetGenerateShaderISAFlag( const bool i_kbGenerateShaderISA ) +{ + m_bGenerateShaderISA = i_kbGenerateShaderISA; +} + +void ShaderCache::SetShowShaderISAFlag( const bool i_kbShowShaderISA ) +{ + m_bShowShaderISA = i_kbShowShaderISA; +} + +#if AMD_SDK_INTERNAL_BUILD +void ShaderCache::SetTargetISA( const ISA_TARGET i_eTargetISA ) +{ + m_eTargetISA = i_eTargetISA; + assert( (i_eTargetISA >= FIRST_ISA_TARGET) && (i_eTargetISA < NUM_ISA_TARGETS) ); +} +#endif + +//-------------------------------------------------------------------------------------- +// private methods: +//-------------------------------------------------------------------------------------- + +//-------------------------------------------------------------------------------------- +// Shader Watchdog -- Recompiles shaders as they are touched (if they have changed) +//-------------------------------------------------------------------------------------- + +bool ShaderCache::WatchDirectoryForChanges( void ) +{ + assert( !m_watchHandle ); + assert( !m_waitPoolHandle ); + + if (m_waitPoolHandle) + { + UnregisterWaitEx( m_waitPoolHandle, INVALID_HANDLE_VALUE ); + m_waitPoolHandle = NULL; + } + + if (m_watchHandle) + { + FindCloseChangeNotification( m_watchHandle ); + m_watchHandle = NULL; + } + + assert( !m_watchHandle ); + assert( !m_waitPoolHandle ); + + HANDLE watchHandle = FindFirstChangeNotification( m_wsShaderSourceDir, TRUE, FILE_NOTIFY_CHANGE_LAST_WRITE | FILE_NOTIFY_CHANGE_SIZE ); + if (watchHandle == INVALID_HANDLE_VALUE) + { + wchar_t wsErrorString[m_uCOMMAND_LINE_MAX_LENGTH]; + DWORD error = GetLastError(); + swprintf_s( wsErrorString, L"\n\n*** Shader Cache: Error '%x' in FindFirstChangeNotification while attempting to watch directory '%s' ***\n\n", error, m_wsShaderSourceDir ); + OutputDebugStringW( wsErrorString ); + return false; + } + + m_watchHandle = watchHandle; + + HANDLE poolHandle; + if (!RegisterWaitForSingleObject( &poolHandle, watchHandle, onDirectoryChangeEventTriggered, (void*) this, INFINITE, WT_EXECUTEINWAITTHREAD )) + { + wchar_t wsErrorString[m_uCOMMAND_LINE_MAX_LENGTH]; + DWORD error = GetLastError(); + swprintf_s( wsErrorString, L"\n\n*** Shader Cache: Error '%x' in RegisterWaitForSingleObject while attempting to watch directory '%s' ***\n\n", error, m_wsShaderSourceDir ); + OutputDebugStringW( wsErrorString ); + return false; + } + + m_waitPoolHandle = poolHandle; + + wchar_t wsErrorString[m_uCOMMAND_LINE_MAX_LENGTH]; + swprintf_s( wsErrorString, L"\n\n*** Shader Cache: Succesfully enabled watching of directory '%s' ***\n\n", m_wsShaderSourceDir ); + OutputDebugStringW( wsErrorString ); + + return true; +} + + +void __stdcall ShaderCache::onDirectoryChangeEventTriggered( void* args, BOOLEAN /*timeout*/ ) +{ + ShaderCache* pShaderCache = reinterpret_cast(args); + + if (pShaderCache->RecompileTouchedShaders()) + { + // Don't recompile if shaders are currently compiling! + if (pShaderCache->ShadersReady()) + { + pShaderCache->GenerateShaders( AMD::ShaderCache::CREATE_TYPE_COMPILE_CHANGES, true ); + + wchar_t wsErrorString[m_uCOMMAND_LINE_MAX_LENGTH]; + swprintf_s( wsErrorString, L"\n\n*** ShaderCache::onDirectoryChangeEventTriggered! @ [%s] ***\n\n", pShaderCache->m_wsShaderSourceDir ); + OutputDebugStringW( wsErrorString ); + } + else + { + wchar_t wsErrorString[m_uCOMMAND_LINE_MAX_LENGTH]; + swprintf_s( wsErrorString, L"\n\n*** ShaderCache::onDirectoryChangeEventTriggered! @ [%s] -- SKIPPED, because shaders are already compiling. ***\n\n", pShaderCache->m_wsShaderSourceDir ); + OutputDebugStringW( wsErrorString ); + } + } + + FindNextChangeNotification( pShaderCache->m_watchHandle ); + FindNextChangeNotification( pShaderCache->m_watchHandle ); //twice +} + +//-------------------------------------------------------------------------------------- +// Methods to get AMD ISA +//-------------------------------------------------------------------------------------- + +// Methods to run SCDev to generate ISA +bool ShaderCache::GenerateISAForAllShaders() +{ + return false; +} + +bool ShaderCache::GenerateShaderISA( Shader *pShader, const bool i_kbParseGPRPressure ) +{ + + bool bSuccess = false; + if (!m_bGenerateShaderISA) + { + return bSuccess; + } + +#if AMD_SDK_INTERNAL_BUILD + //EnterCriticalSection( &m_GenISA_CriticalSection ); + + { + pShader->m_wsCompileStatus = L"ISA Compiler: Phase 1"; + + wchar_t wsASM[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsASM, L"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, m_wsUnicodeWorkingDir ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\\" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, pShader->m_wsAssemblyFileWithHashedFilename ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + + wchar_t wsISACL[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsISACL, L"%s %s", pShader->m_wsISACommandLine, wsASM ); + + wchar_t wsShaderSCDEVWorkingDir[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsShaderSCDEVWorkingDir, L"%s\\%s", m_wsSCDEVWorkingDir, AmdTargetInfo[pShader->m_eISATarget].m_Name ); +#if defined(DEBUG) || defined(_DEBUG) + const bool bRet1 = CreateDirectoryW( wsShaderSCDEVWorkingDir, NULL ) != ERROR_PATH_NOT_FOUND; assert( bRet1 ); +#else + CreateDirectoryW( wsShaderSCDEVWorkingDir, NULL ); +#endif + //swprintf_s( wsShaderSCDEVWorkingDir, L"%s\\%s\\%s", m_wsSCDEVWorkingDir, AmdTargetInfo[ pShader->m_eISATarget ].m_Name, pShader->m_wsRawFileName ); + swprintf_s( wsShaderSCDEVWorkingDir, L"%s\\%s\\%s", m_wsSCDEVWorkingDir, AmdTargetInfo[pShader->m_eISATarget].m_Name, pShader->m_wsHashedFileName ); +#if defined(DEBUG) || defined(_DEBUG) + const bool bRet2 = CreateDirectoryW( wsShaderSCDEVWorkingDir, NULL ) != ERROR_PATH_NOT_FOUND; assert( bRet2 ); +#else + CreateDirectoryW( wsShaderSCDEVWorkingDir, NULL ); +#endif + + SHELLEXECUTEINFO shExecInfo; + memset( &shExecInfo, 0, sizeof( SHELLEXECUTEINFO ) ); + shExecInfo.cbSize = sizeof( SHELLEXECUTEINFO ); + shExecInfo.fMask = SEE_MASK_NOASYNC | SEE_MASK_UNICODE; + shExecInfo.hwnd = NULL; + shExecInfo.lpFile = m_wsDevExePath; + shExecInfo.nShow = SW_HIDE; + shExecInfo.hInstApp = NULL; + shExecInfo.lpParameters = wsISACL; + shExecInfo.lpDirectory = wsShaderSCDEVWorkingDir; + bSuccess = ShellExecuteEx( &shExecInfo ) ? true : false; + assert( bSuccess ); + } + + if (bSuccess) + { + pShader->m_wsCompileStatus = L"ISA Compiler: Phase 1 ... done!"; + } + else + { + pShader->m_wsCompileStatus = L"ISA Compiler: Phase 1 ... failed!"; + } + + if (bSuccess) + { + pShader->m_wsCompileStatus = L"ISA Compiler: Phase 2"; + + wchar_t wsEXE[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsEXE, L"%s%s", m_wsAmdSdkDir, L"\\src\\Shaders\\MoveSCDevOutput.bat" ); + + wchar_t wsASM[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsASM, L"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + //wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, pShader->m_wsRawFileName ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, pShader->m_wsHashedFileName ); + //wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L".asm" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L" " ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, m_wsBatchWorkingDir ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L" " ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, AmdTargetInfo[pShader->m_eISATarget].m_Name ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L" " ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, pShader->m_wsHashedFileName ); + wcscat_s( wsASM, m_uFILENAME_MAX_LENGTH, L"\"" ); + + SHELLEXECUTEINFO shExecInfo; + memset( &shExecInfo, 0, sizeof( SHELLEXECUTEINFO ) ); + shExecInfo.cbSize = sizeof( SHELLEXECUTEINFO ); + shExecInfo.fMask = (i_kbParseGPRPressure) ? (SEE_MASK_NOASYNC | SEE_MASK_UNICODE) : SEE_MASK_ASYNCOK; // Optimization: Async if we don't plan to read this immediately + shExecInfo.hwnd = NULL; + shExecInfo.lpFile = wsEXE; + shExecInfo.nShow = SW_HIDE; + shExecInfo.hInstApp = NULL; + shExecInfo.lpParameters = wsASM; + bSuccess = ShellExecuteEx( &shExecInfo ) ? true : false; + assert( bSuccess ); + + if (bSuccess) + { + pShader->m_wsCompileStatus = L"ISA Compiler: Finished"; + } + else + { + pShader->m_wsCompileStatus = L"ISA Compiler Failed!"; + } + + pShader->m_bGPRsUpToDate = false; + } + + if (i_kbParseGPRPressure) + { + unsigned int uNumVGPR = 0; + unsigned int uNumSGPR = 0; + if (GetShaderGPRUsageFromISA( pShader, uNumVGPR, uNumSGPR )) + { + wchar_t wsGPRS[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsGPRS, L"\n\n%s::%s\nVGPRs: %u\nSGPRs: %u\n\n", pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name, uNumVGPR, uNumSGPR ); + OutputDebugStringW( wsGPRS ); + } + else + { + wchar_t wsGPRS[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsGPRS, L"\n\nFailed to determine NumVGPR and NumSGPR for %s::%s\n\n", pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name ); + OutputDebugStringW( wsGPRS ); + } + } + + //LeaveCriticalSection( &m_GenISA_CriticalSection ); +#endif + + return bSuccess; +} + +void ShaderCache::DeleteISAFiles() +{} + +void ShaderCache::DeleteISAFile( Shader *pShader ) +{} + +bool ShaderCache::GetShaderGPRUsageFromISA( Shader *pShader, unsigned int& io_uNumVGPR, unsigned int& io_uNumSGPR ) const +{ + if (!GenerateISAGPRPressure()) + { + return true; + } + +#if AMD_SDK_INTERNAL_BUILD + unsigned int io_uGPRPoolSize = 0; + float io_fALUPacking = 0.0; + + pShader->m_wsCompileStatus = L"Parsing GPR Pressure"; + + if (pShader->m_bGPRsUpToDate) + { + wchar_t wsGPRS[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsGPRS, L"\n\n%s::%s\nVGPRs: %u\nSGPRs: %u [Warning -- GetShaderGPRUsageFromISA called unnecessarily; GPRs Up To Date; Update Skipped]\n\n", + pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name, pShader->m_ISA_VGPRs, pShader->m_ISA_SGPRs ); + OutputDebugStringW( wsGPRS ); + assert( false ); + pShader->m_wsCompileStatus = L"GPRs Up-to-date!"; + return true; + } + + FILE* pFile = NULL; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + CreateFullPathFromOutputFilename( wsShaderPathName, pShader->m_wsISAFile ); + _wfopen_s( &pFile, wsShaderPathName, L"rt" ); + + io_uNumVGPR = 0; + io_uNumSGPR = 0; + io_uGPRPoolSize = 0; + io_fALUPacking = 0.0f; + + /* + NumVgprs = 27; + NumSgprs = 28; + */ + + if (pFile) + { + + wchar_t szLine[m_uCOMMAND_LINE_MAX_LENGTH]; + wchar_t* pLine = szLine; + + wchar_t szNumVgprs[32]; + wchar_t szNumSgprs[32]; + wchar_t szGPRPoolSize[32]; + wchar_t szNumGPRs[32]; + wchar_t szALUPacking[32]; + + wcscpy_s( szNumVgprs, 32, L"NumVgprs" ); // GCN Architecture (Vector GPR) + wcscpy_s( szNumSgprs, 32, L"NumSgprs" ); // GCN Architecture (Scalar GPR) + wcscpy_s( szGPRPoolSize, 32, L"GprPoolSize" ); // VLIW Architecture + wcscpy_s( szNumGPRs, 32, L"SQ_PGM_RESOURCES:NUM_GPRS" ); // VLIW Architecture + wcscpy_s( szALUPacking, 32, L";AluPacking" ); // VLIW Architecture + + + while (fgetws( pLine, m_uCOMMAND_LINE_MAX_LENGTH, pFile )) + { + wchar_t* pTemp = pLine; + while (*pTemp != L'\n') + { + + if (!wcsncmp( pTemp, szNumVgprs, wcslen( szNumVgprs ) )) + { + wchar_t *pStr = wcschr( pTemp, L'=' ); + if (pStr) + { + pStr += 2; + io_uNumVGPR = _wtoi( pStr ); + } + } + else if (!wcsncmp( pTemp, szNumSgprs, wcslen( szNumSgprs ) )) + { + wchar_t *pStr = wcschr( pTemp, L'=' ); + if (pStr) + { + pStr += 2; + io_uNumSGPR = _wtoi( pStr ); + } + } + else if (!wcsncmp( pTemp, szNumGPRs, wcslen( szNumGPRs ) )) + { + wchar_t *pStr = wcschr( pTemp, L'=' ); + if (pStr) + { + pStr += 2; + io_uNumVGPR = _wtoi( pStr ); + assert( (io_uNumSGPR == 0) || (io_uNumSGPR == (~0)) ); + io_uNumSGPR = (~0u); // Special Flag to indicate that this is a GPR Pool + } + } + else if (!wcsncmp( pTemp, szALUPacking, wcslen( szALUPacking ) )) + { + wchar_t *pStr = wcschr( pTemp, L'=' ); + if (pStr) + { + pStr += 2; + io_fALUPacking = static_cast(_wtof( pStr )); + assert( (io_uNumSGPR == 0) || (io_uNumSGPR == (~0)) ); + io_uNumSGPR = (~0u); // Special Flag to indicate that this is a GPR Pool + } + } + else if (!wcsncmp( pTemp, szGPRPoolSize, wcslen( szGPRPoolSize ) )) + { + wchar_t *pStr = wcschr( pTemp, L'=' ); + if (pStr) + { + pStr += 2; + io_uGPRPoolSize = _wtoi( pStr ); + assert( (io_uNumSGPR == 0) || (io_uNumSGPR == (~0)) ); + io_uNumSGPR = (~0u); // Special Flag to indicate that this is a GPR Pool + } + } + + if ((io_uNumVGPR > 0) && (io_uNumSGPR > 0)) + { + // Cache previous results + pShader->m_previous_ISA_VGPRs = pShader->m_ISA_VGPRs; + pShader->m_previous_ISA_SGPRs = pShader->m_ISA_SGPRs; + + pShader->m_previous_ISA_GPRPoolSize = pShader->m_ISA_GPRPoolSize; + pShader->m_previous_ISA_ALUPacking = pShader->m_ISA_ALUPacking; + + pShader->m_ISA_VGPRs = io_uNumVGPR; + pShader->m_ISA_SGPRs = io_uNumSGPR; + + pShader->m_ISA_GPRPoolSize = io_uGPRPoolSize; + pShader->m_ISA_ALUPacking = io_fALUPacking; + + pShader->m_bGPRsUpToDate = true; + fclose( pFile ); + + pShader->m_wsCompileStatus = L"GPR Pressure Updated"; + return true; + } + + ++pTemp; + } + } + + fclose( pFile ); + + } + + pShader->m_wsCompileStatus = L"Failed to read ISA"; + return false; +#else + return true; +#endif + +} + +bool ShaderCache::GenerateShaderGPRUsageFromISAForAllShaders( const bool ik_bGenerateISAOnFailure ) +{ + if (!GenerateISAGPRPressure()) + { + return true; + } + +#if AMD_SDK_INTERNAL_BUILD + bool bReturnValue = false; + + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + unsigned int VGPR = 0, SGPR = 0; + + if (pShader->m_bGPRsUpToDate) + { + wchar_t wsGPRS[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsGPRS, L"\n\n%s::%s\nVGPRs: %u\nSGPRs: %u [GPRs Up To Date; Update Skipped]\n\n", + pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name, pShader->m_ISA_VGPRs, pShader->m_ISA_SGPRs ); + OutputDebugStringW( wsGPRS ); + pShader->m_wsCompileStatus = L"GPRs Up-to-date!"; + continue; + } + + pShader->m_wsCompileStatus = L"Reading GPR Pressure"; + bool bOK = GetShaderGPRUsageFromISA( pShader, VGPR, SGPR ); + // assert( k_bOK ); + + if ((!bOK) && ik_bGenerateISAOnFailure) // Allow one single retry on failure... + { + // Possibly need to generate the Shader ISA? Try it once. + pShader->m_wsCompileStatus = L"Generating ISA"; + const bool kGenSuccess = GenerateShaderISA( pShader, false ); // Don't parse GPR pressure (prevent infinite loop) + if (kGenSuccess) + { + bOK = GetShaderGPRUsageFromISA( pShader, VGPR, SGPR ); + } + } + + const bool k_bOK = bOK; + + if (k_bOK) + { + wchar_t wsGPRS[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsGPRS, L"\n\n%s::%s\nVGPRs: %u\nSGPRs: %u\n\n", pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name, VGPR, SGPR ); + OutputDebugStringW( wsGPRS ); + } + else + { + wchar_t wsGPRS[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsGPRS, L"\n\nFailed to determine NumVGPR and NumSGPR for %s::%s\n\n", pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name ); + OutputDebugStringW( wsGPRS ); + } + + if (!k_bOK) + { + if (m_ErrorDisplayType == ERROR_DISPLAY_IN_MESSAGE_BOX) + { + wchar_t wsFailureMessage[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsFailureMessage, L"*** Could not extract GPR usage from %s ISA.\nThe ISA Shader Compiler may have failed to execute. ***", AmdTargetInfo[pShader->m_eISATarget].m_Name ); + MessageBoxW( NULL, wsFailureMessage, L"Error", MB_OK ); + } + else + { + wchar_t wsFailureMessage[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsFailureMessage, L"*** Could not extract GPR usage from %s ISA. The ISA Shader Compiler may have failed to execute. ***\n", AmdTargetInfo[pShader->m_eISATarget].m_Name ); + OutputDebugStringW( wsFailureMessage ); + if (ShowShaderErrors()) + { + const bool kbAppendToError = (wcslen( m_wsLastShaderError ) < (3 * m_uCOMMAND_LINE_MAX_LENGTH)); + swprintf_s( m_wsLastShaderError, L"%s%s", (m_bHasShaderErrorsToDisplay && kbAppendToError) ? m_wsLastShaderError : L"", wsFailureMessage ); + m_bHasShaderErrorsToDisplay = true; + m_shaderErrorRenderedCount = 0; + } + } + } + + bReturnValue |= k_bOK; + } + + return bReturnValue; +#else + return true; +#endif +} + +// Renders the GPR usage for the shaders +void ShaderCache::RenderISAInfo( CDXUTTextHelper* g_pTxtHelper, int iFontHeight, DirectX::XMVECTOR FontColor, const Shader *i_pShaderCmp, wchar_t *o_wsGPRInfo ) +{ +#if AMD_SDK_INTERNAL_BUILD + wchar_t wsOverallProgress[m_uPATHNAME_MAX_LENGTH]; + DirectX::XMVECTOR RedFontColor = DirectX::XMVectorSet( 1.0f, 0.0f, 0.0f, 1.0f ); + DirectX::XMVECTOR GreenFontColor = DirectX::XMVectorSet( 0.0f, 1.0f, 0.0f, 1.0f ); + DirectX::XMVECTOR BlueFontColor = DirectX::XMVectorSet( 0.0f, 0.0f, 1.0f, 1.0f ); + + if (!ShowISAGPRPressure()) { return; } + + if (g_pTxtHelper) + { + g_pTxtHelper->Begin(); + g_pTxtHelper->SetForegroundColor( FontColor ); + g_pTxtHelper->SetInsertionPos( 5, (m_bHasShaderErrorsToDisplay) ? 300 : 60 ); + } + + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + + if (i_pShaderCmp && (pShader != i_pShaderCmp)) { continue; } // We're trying to update GPR info for a single shader, skip the rest + + if ((pShader->m_ISA_SGPRs == 0) && (pShader->m_ISA_VGPRs == 0)) + { + // Failed to read ISA + swprintf_s( wsOverallProgress, L"%s.%s%s\t[Failed to locate ISA (try building all shaders?)]", + pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name, AmdTargetInfo[pShader->m_eISATarget].m_Info ); + } + else if (pShader->m_ISA_SGPRs == (~0)) + { + // VLIW Hardware, GPR Pool + swprintf_s( wsOverallProgress, L"%s.%s%s\t[VGPR: %u, SGPR: n/a, GPRPool: %u, ALUPacking %f]", + pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name, AmdTargetInfo[pShader->m_eISATarget].m_Info, pShader->m_ISA_VGPRs, + pShader->m_ISA_GPRPoolSize, pShader->m_ISA_ALUPacking ); + const int GPRDelta = (pShader->m_ISA_VGPRs - pShader->m_previous_ISA_VGPRs); + if ((pShader->m_previous_ISA_VGPRs != 0) && (GPRDelta != 0)) + { + if (g_pTxtHelper) + { + g_pTxtHelper->SetForegroundColor( (GPRDelta > 0) ? RedFontColor : GreenFontColor ); + } + swprintf_s( wsOverallProgress, L"%s\t[Prev VGPR: %u, Delta: %i] -- [Prev GPRPool: %u, Prev ALUPacking %f]", + wsOverallProgress, pShader->m_previous_ISA_VGPRs, GPRDelta, pShader->m_previous_ISA_GPRPoolSize, pShader->m_previous_ISA_ALUPacking ); + } + } + else + { + swprintf_s( wsOverallProgress, L"%s.%s%s\t[VGPR: %u, SGPR: %u]", + pShader->m_wsRawFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name, AmdTargetInfo[pShader->m_eISATarget].m_Info, pShader->m_ISA_VGPRs, pShader->m_ISA_SGPRs ); + const int VGPRDelta = (pShader->m_ISA_VGPRs - pShader->m_previous_ISA_VGPRs); + const int SGPRDelta = (pShader->m_ISA_SGPRs - pShader->m_previous_ISA_SGPRs); + DirectX::XMVECTOR thisColor; + if (VGPRDelta > 0) + { + if (SGPRDelta >= 0) + { + thisColor = RedFontColor; + } + else + { + thisColor = BlueFontColor; + } + } + else + { + if (SGPRDelta <= 0) + { + thisColor = GreenFontColor; + } + else + { + thisColor = BlueFontColor; + } + } + + if ((pShader->m_previous_ISA_VGPRs != 0) && (VGPRDelta != 0)) + { + if (g_pTxtHelper) + { + g_pTxtHelper->SetForegroundColor( thisColor ); + } + swprintf_s( wsOverallProgress, L"%s\t[Prev VGPR: %u, Delta: %i]", wsOverallProgress, pShader->m_previous_ISA_VGPRs, VGPRDelta ); + } + if ((pShader->m_previous_ISA_SGPRs != 0) && (SGPRDelta != 0)) + { + if (g_pTxtHelper) + { + g_pTxtHelper->SetForegroundColor( thisColor ); + } + swprintf_s( wsOverallProgress, L"%s\t[Prev SGPR: %u, Delta: %i]", wsOverallProgress, pShader->m_previous_ISA_SGPRs, SGPRDelta ); + } + } + if (g_pTxtHelper) + { + g_pTxtHelper->DrawTextLine( wsOverallProgress ); + g_pTxtHelper->SetForegroundColor( FontColor ); + } + if (o_wsGPRInfo) + { + swprintf_s( o_wsGPRInfo, m_uPATHNAME_MAX_LENGTH, L"%s", wsOverallProgress ); // Write out the progress string + } + } + + if (g_pTxtHelper) + { + g_pTxtHelper->End(); + } +#endif +} + +class HTMLWriter +{ +public: + HTMLWriter( FILE* i_pFile, const wchar_t* i_wcsTitle = NULL, const int i_ReloadRate = -1, const bool i_bUseScripts = true ) + : m_pFile( i_pFile ) + , m_wsTitle( i_wcsTitle ) + , m_bUseScripts( i_bUseScripts ) + , m_iReloadRate( i_ReloadRate ) + { + assert( i_pFile ); + WriteHTMLHeader( i_wcsTitle ); + } + + ~HTMLWriter( void ) + { + //WriteHTMLFooter(); + } + + void writeHTML( const wchar_t* i_wcsString ) + { + fwrite( i_wcsString, wcslen( i_wcsString ) * sizeof( wchar_t ), 1, m_pFile ); + } + + void StartTabTable( void ) + { + writeHTML( L"
\n" ); + writeHTML( L"
    \n" ); + } + + void AddTab( const int i_tabID, const wchar_t* i_wcsTabName ) + { + wchar_t wsTabString[AMD::ShaderCache::m_uPATHNAME_MAX_LENGTH]; + assert( wcslen( i_wcsTabName ) < AMD::ShaderCache::m_uFILENAME_MAX_LENGTH ); + swprintf_s( wsTabString, L"
  • %s
  • \n", i_tabID, i_wcsTabName ); + writeHTML( wsTabString ); + } + + void EndTabTableHeader( void ) + { + writeHTML( L"
\n" ); + } + + void AddTabBody( const int i_tabID, const wchar_t* i_wcsTabName, const wchar_t* i_wcsTabBody ) + { + wchar_t wsTabString[AMD::ShaderCache::m_uPATHNAME_MAX_LENGTH]; + assert( wcslen( i_wcsTabName ) < AMD::ShaderCache::m_uFILENAME_MAX_LENGTH ); + swprintf_s( wsTabString, L"
\n", i_tabID ); + writeHTML( wsTabString ); + writeHTML( i_wcsTabBody ); + writeHTML( L"
\n" ); + } + + void EndTabTable( void ) + { + writeHTML( L"
\n" ); + } + + void AddFileTableRow( const wchar_t* i_wcsString, const bool i_bCreateLink = true ) + { + wchar_t wsTabString[AMD::ShaderCache::m_uPATHNAME_MAX_LENGTH]; + assert( wcslen( i_wcsString ) < AMD::ShaderCache::m_uFILENAME_MAX_LENGTH ); + swprintf_s( wsTabString, L"%s", i_wcsString, i_wcsString ); + + writeHTML( L"" ); + writeHTML( (i_bCreateLink) ? wsTabString : i_wcsString ); + writeHTML( L"\n" ); + } + + void FinishHTML( void ) + { + WriteHTMLFooter(); + } + +private: + // Declare the copy constructor and assignment operator private, and don't implement them. + // That is, make HTMLWriter uncopyable. This also prevents the compiler warning (level 4) + // C4512 : assignment operator could not be generated (caused by const member variables) + HTMLWriter( const HTMLWriter& ); + HTMLWriter& operator=(const HTMLWriter&); + + void WriteHTMLHeader( const wchar_t* i_wcsTitle = NULL ) + { + writeHTML( L"\n" ); + writeHTML( L"\n" ); + writeHTML( L"\n" ); + writeHTML( L"\n" ); + writeHTML( L"\n" ); + if (m_iReloadRate > 0) + { + wchar_t wsReloadRate[AMD::ShaderCache::m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsReloadRate, L"\n", m_iReloadRate ); + writeHTML( wsReloadRate ); + } + writeHTML( L"\t" ); + writeHTML( (i_wcsTitle) ? i_wcsTitle : L"Page Generated by HTMLWriter" ); + writeHTML( L"\n" ); + if (m_bUseScripts) + { + WriteScriptHeader(); + } + WriteHTMLHeadEnding(); + } + + void WriteScriptHeader( void ) + { + writeHTML( L"\t\n" ); + writeHTML( L"\t\n" ); + writeHTML( L"\t\n" ); + writeHTML( L"\t\n" ); + writeHTML( L"\t\n" ); + } + + void WriteHTMLHeadEnding( void ) + { + writeHTML( L"\n" ); + writeHTML( L"\n" ); + } + + void WriteHTMLFooter( void ) + { + writeHTML( L"\n" ); + writeHTML( L"\n" ); + } + +private: + FILE* m_pFile; + const wchar_t* m_wsTitle; + const int m_iReloadRate; + const bool m_bUseScripts; + +}; + +//-------------------------------------------------------------------------------------- +// Creates Human-readable Hash Digest html file with hyperlinks links and plain filenames +//-------------------------------------------------------------------------------------- +bool ShaderCache::CreateHashDigest( const std::list& i_ShaderList ) +{ + FILE* pFile = NULL; + wchar_t wsPathName[m_uPATHNAME_MAX_LENGTH]; + CreateFullPathFromOutputFilename( wsPathName, L"HashDigest.html" ); + + _wfopen_s( &pFile, wsPathName, L"w+,ccs=UTF-8" ); + + if (!pFile) + { + return false; + } + + HTMLWriter html( pFile, L"AMD ShaderCache Hash Digest", 0 ); // Refresh the page every 15 seconds + + int tabID = 0; + html.StartTabTable(); + for (std::list::const_iterator it = i_ShaderList.begin(); it != i_ShaderList.end(); it++) + { + Shader* pShader = *it; + html.AddTab( ++tabID, pShader->m_wsRawFileName ); + } + html.EndTabTableHeader(); + + tabID = 0; + for (std::list::const_iterator it = i_ShaderList.begin(); it != i_ShaderList.end(); it++) + { + Shader* pShader = *it; + wchar_t wsShaderInfoHTML[16384]; + swprintf_s( wsShaderInfoHTML, L"Raw Filename: %s
\n" + L"Entry Point: %s
\n" + L"Hashed Filename: %s
\n" + L"ASM Target: %s
\n" +#if AMD_SDK_INTERNAL_BUILD + L"ISA Target: %s
\n" +#endif + L"
\n" + L"Source HLSL File: %s
\n" + L"Preprocess File: %s
\n" + L"Assembly File: %s
\n" + L"Object File: %s
\n" + L"Error File: %s
\n" + L"Hash File: %s
\n" +#if AMD_SDK_INTERNAL_BUILD + L"ISA File: %s
\n" + L"ISA Dir: Shaders\\ScDev\\%s\\%s
\n" +#endif + L"
\n" + L"Compile Status: %s
\n" + L"Compile Timing: %i
\n" + L"Processing?: %s
\n" + L"Up-to-date?: %s
\n" +#if AMD_SDK_INTERNAL_BUILD + L"ISA Generated: %s
\n" + L"
\n" + L"GPR Pressure:
\n" + L"Current VGPR: %i SGPR: %i
\n" + L"Previous VGPR: %i SGPR: %i
\n" + L"ALU Packing: %f
\n" + L"GPR Pool Size: %i
\n" + L"[Prev] ALU Packing: %f
\n" + L"[Prev] GPR Pool Size: %i
\n" +#endif + L"
\n" + L"Macros:
\n" + , + pShader->m_wsRawFileName, + pShader->m_wsEntryPoint, + pShader->m_wsHashedFileName, + pShader->m_wsTarget, +#if AMD_SDK_INTERNAL_BUILD + AmdTargetInfo[pShader->m_eISATarget].m_Name, +#endif + pShader->m_wsSourceFile, pShader->m_wsSourceFile, + pShader->m_wsPreprocessFile, pShader->m_wsPreprocessFile, + pShader->m_wsAssemblyFileWithHashedFilename, pShader->m_wsAssemblyFileWithHashedFilename, + pShader->m_wsObjectFile, pShader->m_wsObjectFile, + pShader->m_wsErrorFile, pShader->m_wsErrorFile, + pShader->m_wsHashFile, pShader->m_wsHashFile, +#if AMD_SDK_INTERNAL_BUILD + pShader->m_wsISAFile, pShader->m_wsISAFile, + AmdTargetInfo[pShader->m_eISATarget].m_Name, pShader->m_wsHashedFileName, AmdTargetInfo[pShader->m_eISATarget].m_Name, pShader->m_wsHashedFileName, +#endif + pShader->m_wsCompileStatus, + pShader->m_iCompileWaitCount, + pShader->m_bBeingProcessed ? L"yes" : L"no", + pShader->m_bShaderUpToDate ? L"yes" : L"no" +#if AMD_SDK_INTERNAL_BUILD + , pShader->m_bGPRsUpToDate ? L"yes" : L"no", + pShader->m_ISA_VGPRs, + pShader->m_ISA_SGPRs, + pShader->m_previous_ISA_VGPRs, + pShader->m_previous_ISA_SGPRs, + pShader->m_ISA_ALUPacking, + pShader->m_ISA_GPRPoolSize, + pShader->m_previous_ISA_ALUPacking, + pShader->m_previous_ISA_GPRPoolSize +#endif + ); + + // Append Macros to String + for (unsigned int i = 0; i < pShader->m_uNumMacros; ++i) + { + wchar_t* wsMacroStart = &(wsShaderInfoHTML[wcslen( wsShaderInfoHTML )]); + swprintf_s( wsMacroStart, m_uMACRO_MAX_LENGTH, L"%s: %i
\n", pShader->m_pMacros[i].m_wsName, pShader->m_pMacros[i].m_iValue ); + } + + html.AddTabBody( ++tabID, pShader->m_wsRawFileName, wsShaderInfoHTML ); + } + + html.EndTabTable(); + + // File Table: + + html.writeHTML( L"\n" ); + // Error List + + if (m_ErrorList.size() > 0) + { + html.writeHTML( L"

Error List


\n" ); + for (std::set::const_iterator it = m_ErrorList.begin(); it != m_ErrorList.end(); it++) + { + Shader* pShader = *it; + wchar_t wsShaderInfoHTML[16384]; + swprintf_s( wsShaderInfoHTML, L"%s::%s %s %s
\n", + pShader->m_wsRawFileName, pShader->m_wsEntryPoint, pShader->m_wsSourceFile, L"Source HLSL", pShader->m_wsErrorFile, L"Errors" ); + html.writeHTML( wsShaderInfoHTML ); + } + if (m_bHasShaderErrorsToDisplay) + { + html.writeHTML( L"\n" ); + std::wstring shaderErrors( m_wsLastShaderError ); + size_t offset = 0; + do + { + offset = shaderErrors.find_first_of( L'\n' ); + if (offset != shaderErrors.npos) + { + shaderErrors.replace( offset, 1, L"
" ); + } + } while (offset != shaderErrors.npos); + + html.writeHTML( shaderErrors.c_str() ); + html.writeHTML( L"
\n" ); + } + } + + html.writeHTML( L"

File Table


\n" ); + html.writeHTML( L"" ); + html.writeHTML( L"\n" ); + + for (std::list::const_iterator it = i_ShaderList.begin(); it != i_ShaderList.end(); it++) + { + Shader* pShader = *it; + html.writeHTML( L"\n\n" ); + + html.AddFileTableRow( pShader->m_wsRawFileName, false ); + html.AddFileTableRow( pShader->m_wsHashedFileName, false ); + html.AddFileTableRow( pShader->m_wsAssemblyFileWithHashedFilename ); + html.AddFileTableRow( pShader->m_wsErrorFile ); + html.AddFileTableRow( pShader->m_wsHashFile ); + html.AddFileTableRow( pShader->m_wsISAFile ); + html.AddFileTableRow( pShader->m_wsObjectFile ); + html.AddFileTableRow( pShader->m_wsPreprocessFile ); + + html.writeHTML( L"\n\n" ); + + } + + html.writeHTML( L"
Raw FilenameFilename HashAssembly FileError FileHash FileISA FileObject FilePreprocess File
\n" ); + html.writeHTML( L"
\n" ); + + html.FinishHTML(); + fclose( pFile ); + return true; +} + + +//-------------------------------------------------------------------------------------- +// Preprocesses shaders in the list, and generates a hash file, this is subsequently used to +// determine if a shader has changed +//-------------------------------------------------------------------------------------- +void ShaderCache::PreprocessShaders() +{ + Shader* pShader = NULL; + unsigned int uNumWorkThreads = 0; + + // Create Hash Digest File + bool compileStatusInitialized = false; + /*if( m_bCreateHashDigest ) + { + compileStatusInitialized = CreateHashDigest( m_PreprocessList ); + }*/ + + // Setup Progress Info and Compile Status for all shaders + for (std::list::iterator it = m_PreprocessList.begin(); it != m_PreprocessList.end(); it++) + { + pShader = *it; + pShader->m_wsCompileStatus = L"Preparing to pre-process . . ."; // Starting to Process the Shader + pShader->m_bBeingProcessed = false; + if (!compileStatusInitialized) { m_pProgressInfo[m_uProgressCounter++] = pShader; } // Add this if Hash Digest hasn't already done it! + } + + while (m_PreprocessList.size()) + { + bool bRemove = false; + + for (std::list::iterator it = m_PreprocessList.begin(); it != m_PreprocessList.end(); it++) + { + if (bRemove) + { + m_PreprocessList.remove( pShader ); + bRemove = false; + } + + pShader = *it; + + if (uNumWorkThreads < m_uNumCPUCoresToUse) + { + // LAYLAFIXED: If we have 0 worker threads, then it implies we can't be processing a shader (so when (uNumWorkThreads == 0 ) && (m_bBeingProcessed == true), we have a bug!) + assert( (pShader->m_bBeingProcessed == false) || (uNumWorkThreads > 0) ); + if ((pShader->m_bBeingProcessed == false) /*|| (uNumWorkThreads == 0)*/) + { + bRemove = true; + pShader->m_wsCompileStatus = L"Finding Shader"; // Starting to PreProcess the Shader + if (CheckShaderFile( pShader )) + { + PreprocessShader( pShader ); + pShader->m_wsCompileStatus = L"Preprocessing"; // Starting to PreProcess the Shader + //pShader->m_wsPreprocessFile_with_ISA + + pShader->m_bBeingProcessed = true; + + m_HashList.push_back( pShader ); + + uNumWorkThreads++; + } + else + { + pShader->m_wsCompileStatus = L"ERROR: Shader Not Found!"; + pShader->m_bBeingProcessed = false; + --uNumWorkThreads; + continue; + } + } + } + else + { + // else break out of the for loop, and let this batch of work finish + break; + } + + Sleep( 1 ); + } + + if (bRemove) + { + m_PreprocessList.remove( pShader ); + bRemove = false; + } + + if (m_bAbort) + { + break; + } + + // Wait for current batch of preprocessing to finish + { + HANDLE handles[MAXIMUM_WAIT_OBJECTS]; + DWORD nHandleCount = 0; + for (std::list::iterator it = m_HashList.begin(); it != m_HashList.end(); it++) + { + pShader = *it; + if (nHandleCount < MAXIMUM_WAIT_OBJECTS) + { + handles[nHandleCount++] = pShader->m_hCompileProcessHandle; + } + if (nHandleCount == MAXIMUM_WAIT_OBJECTS) + { + WaitForMultipleObjects( nHandleCount, handles, TRUE, INFINITE ); + nHandleCount = 0; + } + } + if (nHandleCount > 0) + { + WaitForMultipleObjects( nHandleCount, handles, TRUE, INFINITE ); + } + } + + // Close handles for current batch of preprocessing that is now finished + { + for (std::list::iterator it = m_HashList.begin(); it != m_HashList.end(); it++) + { + pShader = *it; + CloseHandle( pShader->m_hCompileProcessHandle ); + CloseHandle( pShader->m_hCompileThreadHandle ); + pShader->m_hCompileProcessHandle = NULL; + pShader->m_hCompileThreadHandle = NULL; + } + } + + // Hash Preprocessed Shaders + while (m_HashList.size() && (!m_bAbort)) + { + bRemove = false; + + for (std::list::iterator it = m_HashList.begin(); it != m_HashList.end(); it++) + { + if (bRemove) + { + pShader->m_iCompileWaitCount = -1; + m_HashList.remove( pShader ); + bRemove = false; + } + + pShader = *it; + + assert( pShader->m_bBeingProcessed == true ); + pShader->m_wsCompileStatus = L"Waiting for Preprocessor"; + pShader->m_iCompileWaitCount++; + + assert( pShader->m_hCompileProcessHandle == NULL ); + + /*pShader->m_iCompileWaitCount = 0; + + bool bKeepLooping = true; + while( bKeepLooping ) + { + unsigned long exitCode = 0; + int rValue = GetExitCodeProcess(pShader->m_hCompileProcessHandle, &exitCode ); + bKeepLooping = ( (rValue != 0) && (exitCode == STILL_ACTIVE) ); + pShader->m_iCompileWaitCount++; + }*/ + + if ((pShader->m_bBeingProcessed == true) && CreateHashFromPreprocessFile( pShader )) + { + // Set Status to COMPARING HASH + pShader->m_wsCompileStatus = L"Comparing Hash"; + //m_pProgressInfo[m_uProgressCounter++] = pShader; + //m_pProgressInfo[m_uProgressCounter++].m_wsFilename = pShader->m_wsPreprocessFile_with_ISA; + + if (!CompareHash( pShader )) + { + DeleteObjectFile( pShader ); + + WriteHashFile( pShader ); + + m_CompileList.push_back( pShader ); + } + else + { + if (CheckObjectFile( pShader )) + { + m_CreateList.push_back( pShader ); + } + else + { + m_CompileList.push_back( pShader ); + } + } + + // Set Status to FINISHED + pShader->m_wsCompileStatus = L"Finished Preprocessing"; + //m_pProgressInfo[m_uProgressCounter++] = pShader; + //m_pProgressInfo[m_uProgressCounter++].m_wsFilename = pShader->m_wsPreprocessFile_with_ISA; + + pShader->m_bBeingProcessed = false; + + if (uNumWorkThreads > 0) + { + uNumWorkThreads--; + } + + bRemove = true; + } + else + { + Sleep( 1 ); + } + /*else if( !bRemove ) + { + // The Preprocess File Doesn't Exist; try again? + pShader->m_bBeingProcessed = false; + + if ( uNumWorkThreads > 0 ) + uNumWorkThreads--; + + m_PreprocessList.push_back( pShader ); + + // SET STATUS TO RETRY! + pShader->m_wsCompileStatus = L"Preprocessing: RETRY"; + + bRemove = true; + //m_pProgressInfo[m_uProgressCounter++] = pShader; + //m_pProgressInfo[m_uProgressCounter++].m_wsFilename = pShader->m_wsPreprocessFile_with_ISA; + }*/ + } + + if (bRemove) + { + m_HashList.remove( pShader ); + } + + if (m_bAbort) + { + break; + } + + Sleep( 1 ); + + } + + } + +} + +// a binary predicate implemented as a function: +bool shader_duplicate_ptr( AMD::ShaderCache::Shader* pFirst, AMD::ShaderCache::Shader* pSecond ) +{ + return (pFirst == pSecond); +} + +//-------------------------------------------------------------------------------------- +// Compiles the shaders in the list +//-------------------------------------------------------------------------------------- +void ShaderCache::CompileShaders() +{ + Shader* pShader = NULL; + unsigned int uNumWorkThreads = 0; + + EnterCriticalSection( &m_CompileShaders_CriticalSection ); + + while (m_CompileList.size()) + { + bool bRemove = false; + + Sleep( 1 ); + + for (std::list::iterator it = m_CompileList.begin(); it != m_CompileList.end(); it++) + { + + Sleep( 1 ); + if (bRemove) + { + m_CompileList.remove( pShader ); + bRemove = false; + } + + pShader = *it; + + pShader->m_wsCompileStatus = L"Waiting to Compile..."; + + if (uNumWorkThreads < m_uNumCPUCoresToUse) + { + if (pShader->m_bBeingProcessed == false) + { + bRemove = true; + pShader->m_wsCompileStatus = L"Compiling Shader"; + CompileShader( pShader ); + + pShader->m_bBeingProcessed = true; + + m_CompileCheckList.push_back( pShader ); + + uNumWorkThreads++; + } + } + else + { + // else break out of the for loop, and let this batch of work finish + break; + } + } + + if (bRemove) + { + m_CompileList.remove( pShader ); + bRemove = false; + } + + if (m_bAbort) + { + break; + } + + // Wait for current batch of compiling to finish + { + HANDLE handles[MAXIMUM_WAIT_OBJECTS]; + DWORD nHandleCount = 0; + for (std::list::iterator it = m_CompileCheckList.begin(); it != m_CompileCheckList.end(); it++) + { + pShader = *it; + if (nHandleCount < MAXIMUM_WAIT_OBJECTS) + { + handles[nHandleCount++] = pShader->m_hCompileProcessHandle; + } + if (nHandleCount == MAXIMUM_WAIT_OBJECTS) + { + WaitForMultipleObjects( nHandleCount, handles, TRUE, INFINITE ); + nHandleCount = 0; + } + } + if (nHandleCount > 0) + { + WaitForMultipleObjects( nHandleCount, handles, TRUE, INFINITE ); + } + } + + // Close handles for current batch of compiling that is now finished + { + for (std::list::iterator it = m_CompileCheckList.begin(); it != m_CompileCheckList.end(); it++) + { + pShader = *it; + CloseHandle( pShader->m_hCompileProcessHandle ); + CloseHandle( pShader->m_hCompileThreadHandle ); + pShader->m_hCompileProcessHandle = NULL; + pShader->m_hCompileThreadHandle = NULL; + } + } + + // Check Compiled Shaders + while (m_CompileCheckList.size() && (!m_bAbort)) + { + bRemove = false; + + for (std::list::iterator it = m_CompileCheckList.begin(); it != m_CompileCheckList.end(); it++) + { + if (bRemove) + { + m_CompileCheckList.remove( pShader ); + bRemove = false; + } + + pShader = *it; + + bool bHasObjectFile = false; + + //pShader->m_wsCompileStatus = L"Waiting for Object File . . ."; + if (CheckObjectFile( pShader )) + { + pShader->m_wsCompileStatus = L"Found Object File"; + //m_pProgressInfo[m_uProgressCounter++].m_wsFilename = pShader->m_wsObjectFile_with_ISA; + + m_CreateList.push_back( pShader ); + + bHasObjectFile = true; + + pShader->m_bBeingProcessed = false; + + if (uNumWorkThreads > 0) + { + uNumWorkThreads--; + } + + bRemove = true; + } + + //pShader->m_wsCompileStatus = L"Checking For Errors . . ."; + bool bShaderHasCompilerError = false; + if ( /*bHasObjectFile && */CheckErrorFile( pShader, bShaderHasCompilerError )) + { + bRemove |= bShaderHasCompilerError; + + if (bHasObjectFile && !bShaderHasCompilerError) + { + if (m_bGenerateShaderISA) + { + pShader->m_wsCompileStatus = L"Generating ISA"; + pShader->m_bShaderUpToDate = false; // Shader Has Been Updated + if (GenerateShaderISA( pShader, false )) + { + pShader->m_wsCompileStatus = L"Done!"; + } + } + else + { + pShader->m_wsCompileStatus = L"Done!"; + pShader->m_bShaderUpToDate = false; // Shader Has Been Updated + } + } + else if (bShaderHasCompilerError) + { + pShader->m_bShaderUpToDate = true; + pShader->m_bGPRsUpToDate = true; + m_ErrorList.insert( pShader ); + pShader->m_wsCompileStatus = L"Compiler Error!"; + if (uNumWorkThreads > 0) + { + uNumWorkThreads--; + } + } + else + { + pShader->m_wsCompileStatus = L"Still Compiling . . ."; + } + } + else + { + Sleep( 1 ); + } + } + + if (bRemove) + { + m_CompileCheckList.remove( pShader ); + } + + if (m_bAbort) + { + break; + } + + Sleep( 1 ); + + } + } + + GenerateShaderGPRUsageFromISAForAllShaders(); // Generate GPR Usage for any shaders that still need updating + + LeaveCriticalSection( &m_CompileShaders_CriticalSection ); + + if (m_bCreateHashDigest) + { + CreateHashDigest( m_CreateList ); + } +} + + +//-------------------------------------------------------------------------------------- +// Creates the shaders in the list +//-------------------------------------------------------------------------------------- +HRESULT ShaderCache::CreateShaders() +{ + HRESULT hr = E_FAIL; + Shader* pShader = NULL; + + for (std::list::iterator it = m_CreateList.begin(); it != m_CreateList.end(); it++) + { + pShader = *it; + + if (pShader->m_ppShader) + { + if (NULL == *(pShader->m_ppShader) || (!pShader->m_bShaderUpToDate)) + { + assert( (!pShader->m_bShaderUpToDate) || (NULL != *(pShader->m_ppShader)) ); + hr = CreateShader( pShader ); + assert( S_OK == hr ); + } + } // Else, this is a cloned shader, and we won't be using it for rendering, so don't initialize it. + } + + return S_OK; +} + +//-------------------------------------------------------------------------------------- +// Invalidates the shaders in the list +//-------------------------------------------------------------------------------------- +void ShaderCache::InvalidateShaders( void ) +{ + Shader* pShader = NULL; + + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + pShader = *it; + pShader->m_bShaderUpToDate = false; + //assert( pShader->m_ppShader == NULL ); + } +} + +//-------------------------------------------------------------------------------------- +// The preprocess file generated by fxc can have the full path to the source file in it. +// Strip that out before you create the hash. +//-------------------------------------------------------------------------------------- +void ShaderCache::StripPathInfoFromPreprocessFile( Shader* pShader, FILE* pFile, char* pFileBufDst, int iFileSize ) +{ + // clear out the destination buffer + memset( pFileBufDst, '\0', iFileSize ); + + // make a plain old char version of our source filename + size_t i; + char szSourceFileWithBackSlashes[m_uFILENAME_MAX_LENGTH]; + memset( szSourceFileWithBackSlashes, '\0', sizeof( char[m_uFILENAME_MAX_LENGTH] ) ); + wcstombs_s( &i, szSourceFileWithBackSlashes, m_uFILENAME_MAX_LENGTH, pShader->m_wsSourceFile, m_uFILENAME_MAX_LENGTH ); + + // fxc accepts both forward and back slashes, so convert any forward + // slashes to back slashes for consistency + char* pForwardSlash = strchr( szSourceFileWithBackSlashes, L'/' ); + while (pForwardSlash) + { + *pForwardSlash = '\\'; + pForwardSlash = strchr( szSourceFileWithBackSlashes, L'/' ); + } + + // now that we know we have back slashes (if we have slashes at all), + // find the last one to strip off any path info + char* pFileName = strrchr( szSourceFileWithBackSlashes, '\\' ); + + // support the case where the source filename doesn't contain any path info + // (this would happen if shaders were in the project working directory instead of + // a subfolder) + if (!pFileName) + { + pFileName = szSourceFileWithBackSlashes; + } + else + { + // if there was a slash, you are now pointing to it, + // so go one past it to get just the filename + pFileName++; + } + + + char szLine[m_uCOMMAND_LINE_MAX_LENGTH]; + char* pLine = szLine; + char szFxcLineDirective[32]; + strcpy_s( szFxcLineDirective, 32, "#line" ); + + while (fgets( pLine, m_uCOMMAND_LINE_MAX_LENGTH, pFile )) + { + // check if this is a line directive + char* pStartOfFxcLineDirective = strstr( pLine, szFxcLineDirective ); + if (pStartOfFxcLineDirective) + { + // if it is, then check if the filename appears after #line + if (!strstr( pStartOfFxcLineDirective, pFileName )) + { + // if it is a line directive, but not one containing the filename, + // copy it over to the destination buffer + strcat_s( pFileBufDst, iFileSize, pLine ); + } + // else, assume it is one of the problematic #line directives + // that contains full path info, and skip it + } + else + { + // else, not a line directive, so copy it over to the destination buffer + strcat_s( pFileBufDst, iFileSize, pLine ); + } + } +} + + +//-------------------------------------------------------------------------------------- +// Creates a hash from a given shader +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::CreateHashFromPreprocessFile( Shader* pShader ) +{ + FILE* pFile = NULL; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + + CreateFullPathFromOutputFilename( wsShaderPathName, pShader->m_wsPreprocessFile ); + + const unsigned int kuMaxPath = AMD::ShaderCache::m_uPATHNAME_MAX_LENGTH; + const size_t kPathLength = wcslen( wsShaderPathName ); + if (kPathLength >= kuMaxPath) + { + wchar_t wsErrorText[m_uCOMMAND_LINE_MAX_LENGTH]; + swprintf_s( wsErrorText, L"Error: PATH LENGTH TOO LONG [%u/%u]\n\n%s", (unsigned)kPathLength, kuMaxPath, wsShaderPathName ); + MessageBoxW( NULL, wsErrorText, L"ERROR: Path Length Too Long", MB_OK ); + DebugBreak(); + } + + _wfopen_s( &pFile, wsShaderPathName, L"rt" ); + + if (pFile) + { + fseek( pFile, 0, SEEK_END ); + int iFileSize = ftell( pFile ); + rewind( pFile ); + char* pFileBuf = new char[iFileSize]; + + // Strip path info from the preprocessed file, as otherwise this causes problems + // if you move a project on disk. Without this, it triggers a full rebuild of the + // shader cache, purely because the path has changed + StripPathInfoFromPreprocessFile( pShader, pFile, pFileBuf, iFileSize ); + + if (NULL != pShader->m_pHash) + { + free( pShader->m_pHash ); + pShader->m_pHash = NULL; + pShader->m_uHashLength = 0; + } + + CreateHash( pFileBuf, iFileSize, &pShader->m_pHash, &pShader->m_uHashLength ); + + delete [] pFileBuf; + fclose( pFile ); + + return TRUE; + } + + return FALSE; +} + +//-------------------------------------------------------------------------------------- +// Creates a hash for the shader filename +//-------------------------------------------------------------------------------------- +void ShaderCache::Shader::SetupHashedFilename( void ) +{ + + if (NULL != m_pFilenameHash) + { + free( m_pFilenameHash ); + m_pFilenameHash = NULL; + m_uFilenameHashLength = 0; + } + + // TODO: Convert into URL-Safe String + // Convert filename from wchar_t to char* + size_t i; + char asciiString[m_uPATHNAME_MAX_LENGTH]; + memset( asciiString, '\0', sizeof( char[m_uPATHNAME_MAX_LENGTH] ) ); + wcstombs_s( &i, asciiString, m_uPATHNAME_MAX_LENGTH, m_wsRawFileName, m_uPATHNAME_MAX_LENGTH ); + CreateHash( asciiString, 0, &m_pFilenameHash, &m_uFilenameHashLength ); + swprintf_s( m_wsHashedFileName, L"%x", *reinterpret_cast(m_pFilenameHash) ); + assert( m_uFilenameHashLength == 16 ); + +} + + +//-------------------------------------------------------------------------------------- +// Creates the hash +//-------------------------------------------------------------------------------------- +void ShaderCache::CreateHash( const char* data, int iFileSize, BYTE** hash, long* len ) +{ + HCRYPTPROV hProv = 0; + HCRYPTHASH hHash = 0; + BYTE *pbHash = NULL; + DWORD dwHashLen = 0; + + BYTE * pbBuffer = NULL; + DWORD dwCount = 0; + DWORD i = 0; + size_t bufLen = 0; + + // DwFlags is set to zero to attempt to open an existing key container. + if (!CryptAcquireContext( &hProv, NULL, NULL, PROV_RSA_FULL, 0 )) + { + // An error occurred in acquiring the context. This could mean that + // the key container requested does not exist. In this case, the + // function can be called again to attempt to create a new key container. + if (GetLastError() == NTE_BAD_KEYSET) + { + if (!CryptAcquireContext( &hProv, NULL, NULL, PROV_RSA_FULL, CRYPT_NEWKEYSET )) + { + return; + } + } + } + if (!CryptCreateHash( hProv, CALG_MD5, 0, 0, &hHash )) + { + return; + } + + bufLen = strlen( data ); + + pbBuffer = (BYTE*)malloc( bufLen + 1 ); + memset( pbBuffer, 0, bufLen + 1 ); + + for (i = 0; i < bufLen; i++) + { + pbBuffer[i] = (BYTE)data[i]; + } + + if (!CryptHashData( hHash, pbBuffer, (DWORD)bufLen, 0 )) + { + return; + } + + dwCount = sizeof( DWORD ); + if (!CryptGetHashParam( hHash, HP_HASHSIZE, (BYTE *)&dwHashLen, &dwCount, 0 )) + { + return; + } + + if ((pbHash = (unsigned char*)malloc( dwHashLen )) == NULL) + { + return; + } + + memset( pbHash, 0, dwHashLen ); + + if (!CryptGetHashParam( hHash, HP_HASHVAL, pbHash, &dwHashLen, 0 )) + { + return; + } + + *hash = pbHash; + *len = dwHashLen; + + if (hHash) + { + CryptDestroyHash( hHash ); + } + + if (hProv) + { + CryptReleaseContext( hProv, 0 ); + } + + if (NULL != pbBuffer) + { + free( pbBuffer ); + pbBuffer = NULL; + } +} + + +//-------------------------------------------------------------------------------------- +// Writes out the hash file to disk +//-------------------------------------------------------------------------------------- +void ShaderCache::WriteHashFile( Shader* pShader ) +{ + FILE* pFile = NULL; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + + CreateFullPathFromOutputFilename( wsShaderPathName, pShader->m_wsHashFile ); + + _wfopen_s( &pFile, wsShaderPathName, L"wb" ); + + if (pFile) + { + fwrite( pShader->m_pHash, pShader->m_uHashLength, 1, pFile ); + + fclose( pFile ); + } +} + + +//-------------------------------------------------------------------------------------- +// Compares a shaders hash with the has file on disk +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::CompareHash( Shader* pShader ) +{ + FILE* pFile = NULL; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + + CreateFullPathFromOutputFilename( wsShaderPathName, pShader->m_wsHashFile ); + + _wfopen_s( &pFile, wsShaderPathName, L"rb" ); + + if (pFile) + { + fseek( pFile, 0, SEEK_END ); + int iFileSize = ftell( pFile ); + rewind( pFile ); + BYTE* pFileBuf = new BYTE[iFileSize]; + + fread( pFileBuf, 1, iFileSize, pFile ); + + fclose( pFile ); + + if (!memcmp( pShader->m_pHash, pFileBuf, pShader->m_uHashLength )) + { + delete [] pFileBuf; + return TRUE; + } + + delete [] pFileBuf; + } + + return FALSE; +} + + +//-------------------------------------------------------------------------------------- +// Creates a shader +//-------------------------------------------------------------------------------------- +HRESULT ShaderCache::CreateShader( Shader* pShader ) +{ + HRESULT hr = E_FAIL; + FILE* pFile = NULL; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + + assert( !pShader->m_bShaderUpToDate ); + ID3D11DeviceChild* pTempD3DShader = *pShader->m_ppShader; + *pShader->m_ppShader = NULL; + + CreateFullPathFromOutputFilename( wsShaderPathName, pShader->m_wsObjectFile ); + + _wfopen_s( &pFile, wsShaderPathName, L"rb" ); + + if (pFile) + { + fseek( pFile, 0, SEEK_END ); + int iFileSize = ftell( pFile ); + rewind( pFile ); + char* pFileBuf = new char[iFileSize]; + fread( pFileBuf, 1, iFileSize, pFile ); + + switch (pShader->m_eShaderType) + { + case SHADER_TYPE_VERTEX: + hr = DXUTGetD3D11Device()->CreateVertexShader( pFileBuf, iFileSize, NULL, (ID3D11VertexShader**)pShader->m_ppShader ); + assert( S_OK == hr ); + if (pShader->m_uNumDescElements && (pTempD3DShader == NULL)) + { // Only create the Input Layout if one doesn't already exist (it shouldn't change at runtime... I *think*) + hr = DXUTGetD3D11Device()->CreateInputLayout( pShader->m_pInputLayoutDesc, pShader->m_uNumDescElements, pFileBuf, iFileSize, pShader->m_ppInputLayout ); + } + break; + case SHADER_TYPE_HULL: + hr = DXUTGetD3D11Device()->CreateHullShader( pFileBuf, iFileSize, NULL, (ID3D11HullShader**)pShader->m_ppShader ); + assert( S_OK == hr ); + break; + case SHADER_TYPE_DOMAIN: + hr = DXUTGetD3D11Device()->CreateDomainShader( pFileBuf, iFileSize, NULL, (ID3D11DomainShader**)pShader->m_ppShader ); + assert( S_OK == hr ); + break; + case SHADER_TYPE_GEOMETRY: + hr = DXUTGetD3D11Device()->CreateGeometryShader( pFileBuf, iFileSize, NULL, (ID3D11GeometryShader**)pShader->m_ppShader ); + assert( S_OK == hr ); + break; + case SHADER_TYPE_PIXEL: + hr = DXUTGetD3D11Device()->CreatePixelShader( pFileBuf, iFileSize, NULL, (ID3D11PixelShader**)pShader->m_ppShader ); + assert( S_OK == hr ); + break; + case SHADER_TYPE_COMPUTE: + hr = DXUTGetD3D11Device()->CreateComputeShader( pFileBuf, iFileSize, NULL, (ID3D11ComputeShader**)pShader->m_ppShader ); + assert( S_OK == hr ); + break; + } + + delete [] pFileBuf; + fclose( pFile ); + } + + if (hr == S_OK) + { + SAFE_RELEASE( pTempD3DShader ); // Clean up Old Shader + pShader->m_bShaderUpToDate = true; + } + else + { + *pShader->m_ppShader = pTempD3DShader; // Restore last known good shader! + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Compiles a shader +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::CompileShader( Shader* pShader ) +{ + STARTUPINFO si; + PROCESS_INFORMATION pi; + + ZeroMemory( &si, sizeof( si ) ); + si.cb = sizeof( si ); + ZeroMemory( &pi, sizeof( pi ) ); + + // Start the child process. + BOOL bSuccess = CreateProcess( m_wsFxcExePath, // Application name + pShader->m_wsCommandLine, // Command line + NULL, // Process handle not inheritable + NULL, // Thread handle not inheritable + FALSE, // Set handle inheritance to FALSE + CREATE_NO_WINDOW, // Don't make a console window + NULL, // Use parent's environment block + NULL, // Use parent's starting directory + &si, // Pointer to STARTUPINFO structure + &pi ); // Pointer to PROCESS_INFORMATION structure + + assert( pShader->m_hCompileProcessHandle == NULL ); + assert( pShader->m_hCompileThreadHandle == NULL ); + pShader->m_hCompileProcessHandle = pi.hProcess; + pShader->m_hCompileThreadHandle = pi.hThread; + + return bSuccess; +} + + +//-------------------------------------------------------------------------------------- +// Preprocesses a shader +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::PreprocessShader( Shader* pShader ) +{ + STARTUPINFO si; + PROCESS_INFORMATION pi; + + ZeroMemory( &si, sizeof( si ) ); + si.cb = sizeof( si ); + ZeroMemory( &pi, sizeof( pi ) ); + + // Start the child process. + BOOL bSuccess = CreateProcess( m_wsFxcExePath, // Application name + pShader->m_wsPreprocessCommandLine, // Command line + NULL, // Process handle not inheritable + NULL, // Thread handle not inheritable + FALSE, // Set handle inheritance to FALSE + CREATE_NO_WINDOW, // Don't make a console window + NULL, // Use parent's environment block + NULL, // Use parent's starting directory + &si, // Pointer to STARTUPINFO structure + &pi ); // Pointer to PROCESS_INFORMATION structure + + assert( pShader->m_hCompileProcessHandle == NULL ); + assert( pShader->m_hCompileThreadHandle == NULL ); + pShader->m_hCompileProcessHandle = pi.hProcess; + pShader->m_hCompileThreadHandle = pi.hThread; + + return bSuccess; +} + +//-------------------------------------------------------------------------------------- +// Checks to see if the object file exists for a given shader +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::CheckShaderFile( Shader* pShader ) +{ + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + + CreateFullPathFromInputFilename( wsShaderPathName, pShader->m_wsSourceFile ); + + if (_waccess( wsShaderPathName, 00 ) != -1) + { + return TRUE; + } + else + { + wchar_t wsErrorText[m_uCOMMAND_LINE_MAX_LENGTH]; + swprintf_s( wsErrorText, L"Error: %s (FILE NOT FOUND)\n", wsShaderPathName ); + + const bool kbAppendToError = (wcslen( m_wsLastShaderError ) < (3 * m_uCOMMAND_LINE_MAX_LENGTH)); + swprintf_s( m_wsLastShaderError, L"%s%s", (m_bHasShaderErrorsToDisplay && kbAppendToError) ? m_wsLastShaderError : L"", wsErrorText ); + m_bHasShaderErrorsToDisplay = true; + m_shaderErrorRenderedCount = 0; + } + + return FALSE; +} + +//-------------------------------------------------------------------------------------- +// Checks to see if the oject file exists for a given shader +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::CheckObjectFile( Shader* pShader ) +{ + FILE* pFile = NULL; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + + CreateFullPathFromOutputFilename( wsShaderPathName, pShader->m_wsObjectFile ); + + _wfopen_s( &pFile, wsShaderPathName, L"rt" ); + + if (pFile) + { + fseek( pFile, 0, SEEK_END ); + int iFileSize = ftell( pFile ); + fclose( pFile ); + + if (iFileSize > 0) + { + return TRUE; + } + } + + return FALSE; +} + + +//-------------------------------------------------------------------------------------- +// Checks to see if FXC.exe is located correctly +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::CheckFXC() +{ + FILE* pFile = NULL; + _wfopen_s( &pFile, m_wsFxcExePath, L"rb" ); + + if (pFile) + { + fclose( pFile ); + + return TRUE; + } + + return FALSE; +} + +//-------------------------------------------------------------------------------------- +// Checks to see if Dev.exe is located correctly +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::CheckSCDEV() +{ + if (!m_bGenerateShaderISA) { return FALSE; } + + FILE* pFile = NULL; + _wfopen_s( &pFile, m_wsDevExePath, L"rb" ); + + if (pFile) + { + fclose( pFile ); + + return TRUE; + } + + return FALSE; +} + +//-------------------------------------------------------------------------------------- +// Checks to see if an error file exists, and opens it if non-zero in size +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::CheckErrorFile( Shader* pShader, bool& io_bHasShaderCompilerError ) +{ + io_bHasShaderCompilerError = false; + FILE* pFile = NULL; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + + CreateFullPathFromOutputFilename( wsShaderPathName, pShader->m_wsErrorFile ); + + _wfopen_s( &pFile, wsShaderPathName, L"rt" ); + + if (pFile) + { + fseek( pFile, 0, SEEK_END ); + int iFileSize = ftell( pFile ); + + if (iFileSize > 0) + { + rewind( pFile ); + if (IsAnError( pFile )) + { + io_bHasShaderCompilerError = true; + + { + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsShaderPathName, L"\n\n*** Shader Compiler: Errors found in [%s\\%s]\n\n", m_wsWorkingDir, pShader->m_wsErrorFile ); + OutputDebugStringW( wsShaderPathName ); + rewind( pFile ); + PrintShaderErrors( pFile ); + } + + DeleteHashFile( pShader ); + + if (m_ErrorDisplayType == ERROR_DISPLAY_IN_MESSAGE_BOX) + { + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsShaderPathName, L"*** The HLSL Shader Compiler has found the following ERROR(s) ***" ); + MessageBoxW( NULL, m_wsLastShaderError, wsShaderPathName, MB_OK ); + } + else if (m_ErrorDisplayType == ERROR_DISPLAY_IN_DEBUG_OUTPUT_AND_BREAK) + { + DebugBreak(); + } + + } + } + + fclose( pFile ); + + return TRUE; + } + + return FALSE; +} + +//-------------------------------------------------------------------------------------- +// Renders the progress of the shader generation process +//-------------------------------------------------------------------------------------- +void ShaderCache::RenderShaderErrors( CDXUTTextHelper* g_pTxtHelper, int iFontHeight, DirectX::XMVECTOR FontColor, const unsigned int ki_FrameTimeout ) +{ + wchar_t wsOverallProgress[m_uPATHNAME_MAX_LENGTH]; + + if (!m_bHasShaderErrorsToDisplay) + { + return; + } + + if (ShowShaderErrors()) + { + g_pTxtHelper->Begin(); + g_pTxtHelper->SetForegroundColor( FontColor ); + g_pTxtHelper->SetInsertionPos( 5, 60 ); + + // 2500 frames @ 500 fps = ~5 seconds + const unsigned int ki_FramesToDisplayErrorsFor = ki_FrameTimeout; + if (m_bHasShaderErrorsToDisplay && (m_shaderErrorRenderedCount < ki_FramesToDisplayErrorsFor)) + { + swprintf_s( wsOverallProgress, L"*** Shader Compiler Generated ERROR(s) -- this notification will auto-hide in %i frames ***", (ki_FramesToDisplayErrorsFor - m_shaderErrorRenderedCount) ); + g_pTxtHelper->DrawTextLine( wsOverallProgress ); + g_pTxtHelper->DrawTextLine( m_wsLastShaderError ); + ++m_shaderErrorRenderedCount; + } + else + { + // Error time limit expired (this is in frames not ms, should change to ms!) + m_bHasShaderErrorsToDisplay = false; + m_shaderErrorRenderedCount = 0; + swprintf_s( m_wsLastShaderError, L"*** ShaderCompiler: 0 Shader Errors ***\n" ); + } + + g_pTxtHelper->End(); + } + + else if (m_ErrorDisplayType == ERROR_DISPLAY_IN_MESSAGE_BOX) + { + m_bHasShaderErrorsToDisplay = false; + m_shaderErrorRenderedCount = 0; + wchar_t wsShaderPathName[m_uPATHNAME_MAX_LENGTH]; + swprintf_s( wsShaderPathName, L"*** ERROR(s) Occured ***" ); + MessageBoxW( NULL, m_wsLastShaderError, wsShaderPathName, MB_OK ); + } + + else if (m_ErrorDisplayType == ERROR_DISPLAY_IN_DEBUG_OUTPUT_AND_BREAK) + { + m_bHasShaderErrorsToDisplay = false; + m_shaderErrorRenderedCount = 0; + DebugBreak(); + } + +} + +//-------------------------------------------------------------------------------------- +// Prints the error message to debug output, and copies it to the last shader error variable +//-------------------------------------------------------------------------------------- +void ShaderCache::PrintShaderErrors( FILE* pFile ) +{ + wchar_t szLine[m_uCOMMAND_LINE_MAX_LENGTH]; + wchar_t* pLine = szLine; + wchar_t szError[32]; + wcscpy_s( szError, 32, L"error" ); + + while (fgetws( pLine, m_uCOMMAND_LINE_MAX_LENGTH, pFile )) + { + OutputDebugStringW( pLine ); + + wchar_t* pTemp = pLine; + while (*pTemp != L'\n') + { + + if (!wcsncmp( pTemp, szError, wcslen( szError ) )) + { + const bool kbAppendToError = (wcslen( m_wsLastShaderError ) < (3 * m_uCOMMAND_LINE_MAX_LENGTH)); + swprintf_s( m_wsLastShaderError, L"%s%s", (m_bHasShaderErrorsToDisplay && kbAppendToError) ? m_wsLastShaderError : L"", pLine ); + m_bHasShaderErrorsToDisplay = true; + m_shaderErrorRenderedCount = 0; + //return TRUE; + } + + ++pTemp; + } + } + + return; + +} + +//-------------------------------------------------------------------------------------- +// Checks an error file to see if there really was an error, rather than just a warning +//-------------------------------------------------------------------------------------- +BOOL ShaderCache::IsAnError( FILE* pFile ) +{ + char szLine[m_uCOMMAND_LINE_MAX_LENGTH]; + char* pLine = szLine; + char szError[32]; + strcpy_s( szError, 32, "error" ); + + while (fgets( pLine, m_uCOMMAND_LINE_MAX_LENGTH, pFile )) + { + char* pTemp = pLine; + while (*pTemp != '\n') + { + if (!strncmp( pTemp, szError, strlen( szError ) )) + { + return TRUE; + } + + pTemp++; + } + } + + return FALSE; +} + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteFileByFilename( const wchar_t* pwsFile ) const +{ + wchar_t wsPathName[m_uPATHNAME_MAX_LENGTH]; + BOOL bDeleted; + + CreateFullPathFromOutputFilename( wsPathName, pwsFile ); + + bDeleted = DeleteFile( wsPathName ); +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteErrorFiles() +{ + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + + DeleteErrorFile( pShader ); + } +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteErrorFile( Shader* pShader ) +{ + DeleteFileByFilename( pShader->m_wsErrorFile ); +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteAssemblyFiles() +{ + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + + DeleteAssemblyFile( pShader ); + } +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteAssemblyFile( Shader* pShader ) +{ + //DeleteFileByFilename( pShader->m_wsAssemblyFile ); + DeleteFileByFilename( pShader->m_wsAssemblyFileWithHashedFilename ); +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteObjectFiles() +{ + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + + DeleteObjectFile( pShader ); + } +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteObjectFile( Shader* pShader ) +{ + DeleteFileByFilename( pShader->m_wsObjectFile ); +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeletePreprocessFiles() +{ + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + + DeletePreprocessFile( pShader ); + } +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeletePreprocessFile( Shader* pShader ) +{ + DeleteFileByFilename( pShader->m_wsPreprocessFile ); +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteHashFiles() +{ + for (std::list::iterator it = m_ShaderList.begin(); it != m_ShaderList.end(); it++) + { + Shader* pShader = *it; + + DeleteHashFile( pShader ); + } +} + + +//-------------------------------------------------------------------------------------- +// Deletion utility method +//-------------------------------------------------------------------------------------- +void ShaderCache::DeleteHashFile( Shader* pShader ) +{ + DeleteFileByFilename( pShader->m_wsHashFile ); +} diff --git a/src/DX11/framework/amd_sdk/src/ShaderCache.h b/src/DX11/framework/amd_sdk/src/ShaderCache.h new file mode 100644 index 0000000..bcfff9a --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/ShaderCache.h @@ -0,0 +1,444 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: ShaderCache.h +// +// Class definition for the ShaderCache interface. Allows the user to add shaders to a list +// which is then compiled in parallel to object files. Future calls to create the shaders, +// will simply re-use the object files, making craetion time very fast. The option is there, +// to force the regeneration of object files. +// +// Assumption, relies on following directory structure: +// +// SolutionDir\..\src\Shaders +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_SHADER_CACHE_H +#define AMD_SDK_SHADER_CACHE_H + +#include +#include +#include + +// The following two defines (AMD_SDK_INTERNAL_BUILD and AMD_SDK_PREBUILT_RELEASE_EXE) are for internal AMD use. +// If you don't work for AMD, you shouldn't need to touch them. + +// AMD_SDK_INTERNAL_BUILD is used to wrap all code related to generating shader ISA and querying GPR pressure, +// so that it can be compiled out when a sample is released, as the tools necessary to make this work for GCN +// are not public (yet). Hopefully, this define can go away in the not too distant future when such tools are +// publicly available. *** This should be set to 0 before a sample is packaged for release. *** +#define AMD_SDK_INTERNAL_BUILD 0 + +// AMD_SDK_PREBUILT_RELEASE_EXE is used to build the executable that we include in a sample's release package. +// It removes the runtime dependency on the Win8.x SDK, so that a user can download a sample package and run the +// pre-built executable without needing to install the SDK. (Note, this requires a fully populated shader cache.) +// *** Set this to 1 temporarily, just long enough to build the executable to package with the sample. *** +// *** Otherwise, it should be set to 0. *** +#define AMD_SDK_PREBUILT_RELEASE_EXE 0 + +// AMD_SDK_PREBUILT_RELEASE_EXE implies that this is not an AMD_SDK_INTERNAL_BUILD +#if AMD_SDK_PREBUILT_RELEASE_EXE +#undef AMD_SDK_INTERNAL_BUILD +#define AMD_SDK_INTERNAL_BUILD 0 +#endif + +// AMD_SDK_PREBUILT_RELEASE_EXE shouldn't be used with debug builds +#if AMD_SDK_PREBUILT_RELEASE_EXE +#if defined(DEBUG) || defined(_DEBUG) +#error AMD_SDK_PREBUILT_RELEASE_EXE shouldn't be used with debug builds +#endif +#endif + +#if AMD_SDK_INTERNAL_BUILD +#include "AMD_ISA.inl" +#endif + +namespace AMD +{ + + class ShaderCache + { + public: + + // Constants used for string size limits + static const int m_uCOMMAND_LINE_MAX_LENGTH = 2048; + static const int m_uTARGET_MAX_LENGTH = 16; + static const int m_uENTRY_POINT_MAX_LENGTH = 128; + static const int m_uFILENAME_MAX_LENGTH = 256; + static const int m_uPATHNAME_MAX_LENGTH = 512; + static const int m_uMACRO_MAX_LENGTH = 64; + + // Shader type enumeration + typedef enum SHADER_TYPE_t + { + SHADER_TYPE_VERTEX, + SHADER_TYPE_HULL, + SHADER_TYPE_DOMAIN, + SHADER_TYPE_GEOMETRY, + SHADER_TYPE_PIXEL, + SHADER_TYPE_COMPUTE, + SHADER_TYPE_UNKNOWN, + SHADER_TYPE_MAX + }SHADER_TYPE; + + // Create type enumeration + typedef enum CREATE_TYPE_t + { + CREATE_TYPE_FORCE_COMPILE, // Clean the cache, and compile all + CREATE_TYPE_COMPILE_CHANGES, // Only compile shaders that have changed (development mode) + CREATE_TYPE_USE_CACHED, // Use cached shaders (release mode) + CREATE_TYPE_MAX + }CREATE_TYPE; + + // Shader auto-recompile type enumeration + typedef enum SHADER_AUTO_RECOMPILE_TYPE_t + { + SHADER_AUTO_RECOMPILE_DISABLED, // Shaders are only checked at startup + SHADER_AUTO_RECOMPILE_ENABLED, // Auto-recompile changed shaders to improve iteration times + SHADER_AUTO_RECOMPILE_MAX + }SHADER_AUTO_RECOMPILE_TYPE; + + // Shader compiler error display type enumeration + typedef enum ERROR_DISPLAY_TYPE_t + { + ERROR_DISPLAY_IN_DEBUG_OUTPUT, // Just write shader compiler errors out to debug text + ERROR_DISPLAY_ON_SCREEN, // Render shader compiler errors to the screen + ERROR_DISPLAY_IN_MESSAGE_BOX, // Pop up a message box on compiler error + ERROR_DISPLAY_IN_DEBUG_OUTPUT_AND_BREAK, // Cause a breakpoint exception on compiler error + ERROR_DISPLAY_TYPE_MAX + }ERROR_DISPLAY_TYPE; + + // ISA generation type enumeration + typedef enum GENERATE_ISA_TYPE_t + { + GENERATE_ISA_DISABLED, // Don't generate ISA (this option is required when releasing samples) + GENERATE_ISA_ENABLED, // Generate ISA and gather info on GPR pressure (requires AMD internal ScDev) + GENERATE_ISA_MAX + }GENERATE_ISA_TYPE; + + // Shader compiler exe location type enumeration + typedef enum SHADER_COMPILER_EXE_TYPE_t + { + SHADER_COMPILER_EXE_INSTALLED, // Look for shader compiler EXEs (fxc and ScDev) in their installed locations + SHADER_COMPILER_EXE_LOCAL, // Look for shader compiler EXEs (fxc and ScDev) in the AMD_SDK\src\Shaders directory + // (don't use LOCAL when releasing samples, as distributing fxc in this way violates the license) + SHADER_COMPILER_EXE_MAX + }SHADER_COMPILER_EXE_TYPE; + + // Max cores type enumeration + typedef enum MAXCORES_TYPE_t + { + MAXCORES_NO_LIMIT = -4, + MAXCORES_2X_CPU_CORES = -3, + MAXCORES_USE_ALL_CORES = -2, + MAXCORES_USE_ALL_BUT_ONE = -1, + MAXCORES_MULTI_THREADED = 0, + MAXCORES_SINGLE_THREADED = 1 + } MAXCORES_TYPE; + + // The Macro structure + class Macro + { + public: + + wchar_t m_wsName[m_uMACRO_MAX_LENGTH]; + int m_iValue; + }; + + // The shader class + class Shader + { + public: + + Shader(); + ~Shader(); + + SHADER_TYPE m_eShaderType; + ID3D11DeviceChild** m_ppShader; + ID3D11InputLayout** m_ppInputLayout; + D3D11_INPUT_ELEMENT_DESC* m_pInputLayoutDesc; + unsigned int m_uNumDescElements; + wchar_t m_wsTarget[m_uTARGET_MAX_LENGTH]; + wchar_t m_wsEntryPoint[m_uENTRY_POINT_MAX_LENGTH]; + wchar_t m_wsSourceFile[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsCanonicalName[m_uFILENAME_MAX_LENGTH]; + unsigned int m_uNumMacros; + Macro* m_pMacros; + + wchar_t m_wsRawFileName[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsHashedFileName[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsObjectFile[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsErrorFile[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsAssemblyFile[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsAssemblyFileWithHashedFilename[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsISAFile[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsPreprocessFile[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsHashFile[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsCommandLine[m_uCOMMAND_LINE_MAX_LENGTH]; + wchar_t m_wsISACommandLine[m_uCOMMAND_LINE_MAX_LENGTH]; + wchar_t m_wsPreprocessCommandLine[m_uCOMMAND_LINE_MAX_LENGTH]; + + wchar_t m_wsObjectFile_with_ISA[m_uFILENAME_MAX_LENGTH]; + wchar_t m_wsPreprocessFile_with_ISA[m_uFILENAME_MAX_LENGTH]; + +#if AMD_SDK_INTERNAL_BUILD + ISA_TARGET m_eISATarget; + unsigned int m_ISA_VGPRs; + unsigned int m_ISA_SGPRs; + unsigned int m_ISA_GPRPoolSize; + float m_ISA_ALUPacking; + unsigned int m_previous_ISA_VGPRs; + unsigned int m_previous_ISA_SGPRs; + unsigned int m_previous_ISA_GPRPoolSize; + float m_previous_ISA_ALUPacking; +#endif + + bool m_bGPRsUpToDate; + bool m_bBeingProcessed; + bool m_bShaderUpToDate; + BYTE* m_pHash; + long m_uHashLength; + + BYTE* m_pFilenameHash; + long m_uFilenameHashLength; + + const wchar_t* m_wsCompileStatus; + int m_iCompileWaitCount; + HANDLE m_hCompileProcessHandle; + HANDLE m_hCompileThreadHandle; + + void SetupHashedFilename( void ); + }; + + // Construction / destruction + ShaderCache( const SHADER_AUTO_RECOMPILE_TYPE i_keAutoRecompileTouchedShadersType = SHADER_AUTO_RECOMPILE_DISABLED, + const ERROR_DISPLAY_TYPE i_keErrorDisplayType = ERROR_DISPLAY_IN_DEBUG_OUTPUT_AND_BREAK, + const GENERATE_ISA_TYPE i_keGenerateShaderISAType = GENERATE_ISA_DISABLED, + const SHADER_COMPILER_EXE_TYPE i_keShaderCompilerExeType = SHADER_COMPILER_EXE_INSTALLED ); + ~ShaderCache(); + + // Allows the user to add a shader to the cache + bool AddShader( ID3D11DeviceChild** ppShader, + SHADER_TYPE ShaderType, + const wchar_t* pwsTarget, + const wchar_t* pwsEntryPoint, + const wchar_t* pwsSourceFile, + unsigned int uNumMacros, + Macro* pMacros, + ID3D11InputLayout** ppInputLayout, + const D3D11_INPUT_ELEMENT_DESC* pLayout, + unsigned int uNumElements, + const wchar_t* pwsCanonicalName = 0, + const int i_iMaxVGPRLimit = -1, + const int i_iMaxSGPRLimit = -1, + const bool i_kbIsApplicationShader = true ); + + // Allows the ShaderCache to add a new type of ISA Target version of all shaders to the cache + bool CloneShaders( void ); + + // Allows the user to generate shaders added to the cache + HRESULT GenerateShaders( CREATE_TYPE CreateType, const bool i_kbRecreateShaders = false ); + + const bool HasErrorsToDisplay( void ) const; + const bool ShowShaderErrors( void ) const; + const int ShaderErrorDisplayType( void ) const; + const bool RecompileTouchedShaders( void ) const; + const bool GenerateISAGPRPressure( void ) const; + const bool ShowISAGPRPressure( void ) const; + void SetMaximumCoresForShaderCompiler( const int ki_MaxCores = MAXCORES_NO_LIMIT ); + void SetRecompileTouchedShadersFlag( const bool i_bRecompileWhenTouched ); + void SetShowShaderErrorsFlag( const bool i_kbShowShaderErrors ); + void SetGenerateShaderISAFlag( const bool i_kbGenerateShaderISA ); + void SetShowShaderISAFlag( const bool i_kbShowShaderISA ); +#if AMD_SDK_INTERNAL_BUILD + void SetTargetISA( const ISA_TARGET i_eTargetISA = DEFAULT_ISA_TARGET ); +#endif + + // Renders runtime shader compiler errors from dynamically recompiled shaders + void RenderShaderErrors( CDXUTTextHelper* g_pTxtHelper, int iFontHeight, DirectX::XMVECTOR FontColor, const unsigned int ki_FrameTimeout = 2500 ); + + // Renders the progress of the shader generation + void RenderProgress( CDXUTTextHelper* g_pTxtHelper, int iFontHeight, DirectX::XMVECTOR FontColor ); + + // Renders the GPR usage for the shaders + void RenderISAInfo( CDXUTTextHelper* g_pTxtHelper, int iFontHeight, DirectX::XMVECTOR FontColor, const Shader *i_pShaderCmp = NULL, wchar_t *o_wsGPRInfo = NULL ); + + // User can enquire to see if shaders are ready + bool ShadersReady(); + + // DXUT framework hook method (flags the shaders as needing creating) + void OnDestroyDevice(); + + // Called by app when WM_QUIT is posted, so that shader generation can be aborted + void Abort(); + + // Called by the app to override optimizations when compiling shaders in release mode + void ForceDebugShaders( bool bForce ) { m_bForceDebugShaders = bForce; } + + // Do not call this function + void GenerateShadersThreadProc(); + + private: + + // Preprocessing, compilation, and creation methods + void PreprocessShaders(); + void CompileShaders(); + void InvalidateShaders(); + + HRESULT CreateShaders(); + BOOL PreprocessShader( Shader* pShader ); + BOOL CompileShader( Shader* pShader ); + HRESULT CreateShader( Shader* pShader ); + + // Hash methods + void StripPathInfoFromPreprocessFile( Shader* pShader, FILE* pFile, char* pFileBufDst, int iFileSize ); + BOOL CreateHashFromPreprocessFile( Shader* pShader ); + static void CreateHash( const char* data, int iFileSize, BYTE** hash, long* len ); + void WriteHashFile( Shader* pShader ); + BOOL CompareHash( Shader* pShader ); + bool CreateHashDigest( const std::list& i_ShaderList ); + + // Watch methods (for automatic shader recompilation when changed) + bool WatchDirectoryForChanges( void ); + static void __stdcall onDirectoryChangeEventTriggered( void* args, BOOLEAN /*timeout*/ ); + + // Check methodss + BOOL CheckFXC(); + BOOL CheckSCDEV(); + BOOL CheckShaderFile( Shader* pShader ); + BOOL CheckObjectFile( Shader* pShader ); + BOOL CheckErrorFile( Shader* pShader, bool& io_bHasShaderCompilerError ); + BOOL IsAnError( FILE* pFile ); + + // Methods to run SCDev to generate ISA + bool GenerateISAForAllShaders(); + bool GenerateShaderISA( Shader *pShader, const bool i_kbParseGPRPressure = true ); + void DeleteISAFiles(); + void DeleteISAFile( Shader *pShader ); + bool GetShaderGPRUsageFromISA( Shader *pShader, unsigned int& io_uNumVGPR, unsigned int& io_uNumSGPR ) const; + bool GenerateShaderGPRUsageFromISAForAllShaders( const bool ik_bGenerateISAOnFailure = true ); + + // Prints the error message to debug output + void PrintShaderErrors( FILE* pFile ); + + // Various delete methods + // LAYLANOTE: This code is horrid, it should be replaced by a single template function taking the type of file to delete. + void DeleteFileByFilename( const wchar_t* pwsFile ) const; + void DeleteErrorFiles(); + void DeleteErrorFile( Shader* pShader ); + void DeleteAssemblyFiles(); + void DeleteAssemblyFile( Shader* pShader ); + void DeleteObjectFiles(); + void DeleteObjectFile( Shader* pShader ); + void DeletePreprocessFiles(); + void DeletePreprocessFile( Shader* pShader ); + void DeleteHashFiles(); + void DeleteHashFile( Shader* pShader ); + + // Helpers for Long Filename Support + void InsertOutputFilenameIntoCommandLine( wchar_t *pwsCommandLine, const wchar_t* pwsFileName ) const; + void InsertInputFilenameIntoCommandLine( wchar_t *pwsCommandLine, const wchar_t* pwsFileName ) const; + template< size_t N > + void CreateFullPathFromOutputFilename( wchar_t (&pwsPath)[N], const wchar_t* pwsFileName ) const + { + swprintf_s( pwsPath, L"%s\\%s", m_wsUnicodeWorkingDir, pwsFileName ); + } + template< size_t N > + void CreateFullPathFromInputFilename( wchar_t (&pwsPath)[N], const wchar_t* pwsFileName ) const + { + swprintf_s( pwsPath, L"%s\\%s", m_wsUnicodeShaderSourceDir, pwsFileName ); + } + + // Private data + CREATE_TYPE m_CreateType; + MAXCORES_TYPE m_MaxCoresType; + unsigned int m_uNumCPUCoresToUse; + unsigned int m_uNumCPUCores; + bool m_bShadersCreated; + bool m_bAbort; + bool m_bPrintedProgress; + std::list m_ShaderSourceList; + std::list m_ShaderList; + std::list m_PreprocessList; + std::list m_HashList; + std::list m_CompileList; + std::list m_CompileCheckList; + std::list m_CreateList; + std::set m_ErrorList; +#if AMD_SDK_INTERNAL_BUILD + std::vector< std::vector * > m_ISATargetList; +#endif + + struct ProgressInfo + { + ProgressInfo( void ) + : m_wsFilename( L"No Progress Info Structure: filename unknown" ) + , m_wsStatus( L"No Status" ) + , m_pShader( NULL ) + {} + + ProgressInfo( Shader* i_pShader, const wchar_t* ki_wsStatus = L"Initializing..." ) + : m_wsFilename( (i_pShader) ? i_pShader->m_wsRawFileName : L"Invalid Progress Info Structure: filename unknown" ) + , m_wsStatus( ki_wsStatus ) + , m_pShader( i_pShader ) + {} + + wchar_t* m_wsFilename; + const wchar_t* m_wsStatus; + Shader* m_pShader; + }; + + ProgressInfo* m_pProgressInfo; + + unsigned int m_uProgressCounter; + wchar_t m_wsFxcExePath[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsDevExePath[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsAmdSdkDir[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsShaderSourceDir[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsUnicodeShaderSourceDir[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsWorkingDir[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsUnicodeWorkingDir[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsBatchWorkingDir[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsSCDEVWorkingDir[m_uPATHNAME_MAX_LENGTH]; + wchar_t m_wsLastShaderError[m_uCOMMAND_LINE_MAX_LENGTH * 4]; +#if AMD_SDK_INTERNAL_BUILD + ISA_TARGET m_eTargetISA; +#endif + CRITICAL_SECTION m_CompileShaders_CriticalSection; + CRITICAL_SECTION m_GenISA_CriticalSection; + HANDLE m_watchHandle; + HANDLE m_waitPoolHandle; + unsigned int m_shaderErrorRenderedCount; + bool m_bRecompileTouchedShaders; + bool m_bShowShaderErrors; + bool m_bHasShaderErrorsToDisplay; + bool m_bGenerateShaderISA; + bool m_bShowShaderISA; + bool m_bForceDebugShaders; + bool m_bCreateHashDigest; + + ERROR_DISPLAY_TYPE m_ErrorDisplayType; + }; + +} // namespace AMD + +#endif diff --git a/src/DX11/framework/amd_sdk/src/ShaderCacheSampleHelper.cpp b/src/DX11/framework/amd_sdk/src/ShaderCacheSampleHelper.cpp new file mode 100644 index 0000000..6f9dbd4 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/ShaderCacheSampleHelper.cpp @@ -0,0 +1,252 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: ShaderCacheSampleHelper.cpp +// +// Helpers to implement the DXUT related ShaderCache interface in samples. +//-------------------------------------------------------------------------------------- + +// DXUT helper code +#include "DXUT.h" +#include "DXUTmisc.h" +#include "DXUTgui.h" +#include "DXUTCamera.h" +#include "DXUTSettingsDlg.h" +#include "SDKmisc.h" +#include "SDKmesh.h" + +#include "..\\inc\ShaderCacheSampleHelper.h" + +#include "ShaderCache.h" +#include "Sprite.h" +#include "HUD.h" + +#pragma warning( disable : 4100 ) // disable unreference formal parameter warnings for /W4 builds + +#if !AMD_SDK_PREBUILT_RELEASE_EXE +static void SetHUDVisibility( AMD::HUD& r_HUD, const bool i_bHUDIsVisible ) +{ + using namespace AMD; + + assert( AMD_IDC_BUTTON_SHOW_SHADERCACHE_UI == AMD_IDC_START ); + for (int i = AMD_IDC_BUTTON_SHOW_SHADERCACHE_UI + 1; i < AMD_IDC_END; ++i) + { + CDXUTControl* pControl = r_HUD.m_GUI.GetControl( GetEnum( i ) ); + if (pControl) + { + pControl->SetVisible( i_bHUDIsVisible ); + } + } +} +#endif + +namespace AMD +{ + static bool g_bAdvancedShaderCacheGUI_IsVisible = false; + HUD* g_pHUD = NULL; + ShaderCache* g_pShaderCache = NULL; + + void AMD::InitApp( ShaderCache& r_ShaderCache, HUD& r_HUD, int& iY, const bool i_bAdvancedShaderCacheGUI_VisibleByDefault ) + { +#if !AMD_SDK_PREBUILT_RELEASE_EXE + g_bAdvancedShaderCacheGUI_IsVisible = i_bAdvancedShaderCacheGUI_VisibleByDefault; + + const int i_old_iY = iY; + + g_pHUD = &r_HUD; + g_pShaderCache = &r_ShaderCache; + + { + r_HUD.m_GUI.AddButton( GetEnum( AMD_IDC_BUTTON_SHOW_SHADERCACHE_UI ), L"ShaderCache HUD (F9)", + AMD::HUD::iElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, VK_F9 ); + + iY = 0; + static const int iSCElementOffset = AMD::HUD::iElementOffset - 256; + + r_HUD.m_GUI.AddButton( GetEnum( AMD_IDC_BUTTON_RECOMPILESHADERS_CHANGED ), L"Recompile shaders (F5)", + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, VK_F5 ); + +#if AMD_SDK_INTERNAL_BUILD + if (r_ShaderCache.GenerateISAGPRPressure()) + { + r_HUD.m_GUI.AddButton( GetEnum( AMD_IDC_BUTTON_RECREATE_SHADERS ), L"Gen |ISA| shaders (F6)", + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, VK_F6 ); + } +#endif + + r_HUD.m_GUI.AddButton( GetEnum( AMD_IDC_BUTTON_RECOMPILESHADERS_GLOBAL ), L"Build ALL shaders (F7)", + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, VK_F7 ); + + r_HUD.m_GUI.AddCheckBox( GetEnum( AMD_IDC_CHECKBOX_AUTORECOMPILE_SHADERS ), L"Auto Recompile Shaders", + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, r_ShaderCache.RecompileTouchedShaders() ); + + if (r_ShaderCache.ShaderErrorDisplayType() == ShaderCache::ERROR_DISPLAY_ON_SCREEN) + { + r_HUD.m_GUI.AddCheckBox( GetEnum( AMD_IDC_CHECKBOX_SHOW_SHADER_ERRORS ), L"Show Compiler Errors", + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, r_ShaderCache.ShowShaderErrors() ); + } + +#if AMD_SDK_INTERNAL_BUILD + if (r_ShaderCache.GenerateISAGPRPressure()) + { + r_HUD.m_GUI.AddCheckBox( GetEnum( AMD_IDC_CHECKBOX_SHOW_ISA_GPR_PRESSURE ), L"Show ISA GPR Pressure", + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, r_ShaderCache.ShowISAGPRPressure() ); + r_HUD.m_GUI.AddStatic( GetEnum( AMD_IDC_STATIC_TARGET_ISA ), L"Target ISA:", + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight ); + + CDXUTComboBox *pCombo; + r_HUD.m_GUI.AddComboBox( GetEnum( AMD_IDC_COMBOBOX_TARGET_ISA ), + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight, 0, true, &pCombo ); + + if (pCombo) + { + pCombo->SetDropHeight( 300 ); + for (int i = AMD::FIRST_ISA_TARGET; i < AMD::NUM_ISA_TARGETS; ++i) + { + pCombo->AddItem( AMD::AmdTargetInfo[i].m_Name, NULL ); + } + pCombo->SetSelectedByIndex( AMD::DEFAULT_ISA_TARGET ); + } + r_HUD.m_GUI.AddStatic( GetEnum( AMD_IDC_STATIC_TARGET_ISA_INFO ), L"Press (F6) to add New ISA", + iSCElementOffset, iY += AMD::HUD::iElementDelta, AMD::HUD::iElementWidth, AMD::HUD::iElementHeight ); + } +#endif + } + + SetHUDVisibility( r_HUD, i_bAdvancedShaderCacheGUI_VisibleByDefault ); + + iY = i_old_iY + AMD::HUD::iElementDelta; +#endif + } + + void AMD::ProcessUIChanges() + { +#if !AMD_SDK_PREBUILT_RELEASE_EXE + if (g_pHUD == NULL || g_pShaderCache == NULL) + { + return; + } + + ShaderCache& r_ShaderCache = *g_pShaderCache; + HUD& r_HUD = *g_pHUD; + + r_ShaderCache.SetRecompileTouchedShadersFlag( r_HUD.m_GUI.GetCheckBox( GetEnum( AMD_IDC_CHECKBOX_AUTORECOMPILE_SHADERS ) )->GetChecked() ); + if (r_ShaderCache.ShaderErrorDisplayType() == ShaderCache::ERROR_DISPLAY_ON_SCREEN) + { + r_ShaderCache.SetShowShaderErrorsFlag( r_HUD.m_GUI.GetCheckBox( GetEnum( AMD_IDC_CHECKBOX_SHOW_SHADER_ERRORS ) )->GetChecked() ); + } +#if AMD_SDK_INTERNAL_BUILD + if (r_ShaderCache.GenerateISAGPRPressure()) + { + r_ShaderCache.SetShowShaderISAFlag( r_HUD.m_GUI.GetCheckBox( GetEnum( AMD_IDC_CHECKBOX_SHOW_ISA_GPR_PRESSURE ) )->GetChecked() ); + } +#endif +#endif + } + + void AMD::RenderHUDUpdates( CDXUTTextHelper* i_pTxtHelper ) + { +#if !AMD_SDK_PREBUILT_RELEASE_EXE + if (g_pHUD == NULL || g_pShaderCache == NULL) + { + return; + } + + ShaderCache& r_ShaderCache = *g_pShaderCache; + + if (r_ShaderCache.ShadersReady() || (r_ShaderCache.ShowShaderErrors() && r_ShaderCache.HasErrorsToDisplay())) + { + assert( i_pTxtHelper ); + r_ShaderCache.RenderShaderErrors( i_pTxtHelper, 15, DirectX::XMVectorSet( 1.0f, 1.0f, 0.0f, 1.0f ) ); +#if AMD_SDK_INTERNAL_BUILD + if (r_ShaderCache.GenerateISAGPRPressure()) + { + r_ShaderCache.RenderISAInfo( i_pTxtHelper, 15, DirectX::XMVectorSet( 1.0f, 1.0f, 0.0f, 1.0f ) ); + } +#endif + } +#endif + } + + //-------------------------------------------------------------------------------------- + // Handles the GUI events + //-------------------------------------------------------------------------------------- + void __stdcall AMD::OnGUIEvent( UINT nEvent, int nControlID, CDXUTControl* pControl, void* pUserContext ) + { +#if !AMD_SDK_PREBUILT_RELEASE_EXE + if (g_pHUD == NULL || g_pShaderCache == NULL) + { + return; + } + + ShaderCache& r_ShaderCache = *g_pShaderCache; + HUD& r_HUD = *g_pHUD; + + if (nControlID == GetEnum( AMD_IDC_BUTTON_RECOMPILESHADERS_CHANGED )) + { + // Errors will post during compile, don't need them right now + const bool bOldShaderErrorsFlag = r_ShaderCache.ShowShaderErrors(); + r_ShaderCache.SetShowShaderErrorsFlag( false ); + r_ShaderCache.GenerateShaders( AMD::ShaderCache::CREATE_TYPE_COMPILE_CHANGES, true ); + r_ShaderCache.SetShowShaderErrorsFlag( bOldShaderErrorsFlag ); + } + else if (nControlID == GetEnum( AMD_IDC_BUTTON_RECOMPILESHADERS_GLOBAL )) + { + // Errors will post during compile, don't need them right now + const bool bOldShaderErrorsFlag = r_ShaderCache.ShowShaderErrors(); + r_ShaderCache.SetShowShaderErrorsFlag( false ); + r_ShaderCache.GenerateShaders( AMD::ShaderCache::CREATE_TYPE_FORCE_COMPILE, true ); + r_ShaderCache.SetShowShaderErrorsFlag( bOldShaderErrorsFlag ); + } +#if AMD_SDK_INTERNAL_BUILD + else if (nControlID == GetEnum( AMD_IDC_BUTTON_RECREATE_SHADERS )) + { + assert( r_ShaderCache.GenerateISAGPRPressure() ); // Shouldn't call this if we aren't using ISA + const bool k_bOK = r_ShaderCache.CloneShaders(); + assert( k_bOK ); + if (k_bOK) + { + // Errors won't post using this method... Should find a better one! + // Need to somehow toggle error rendering off and then on again next frame... + const bool bOldShaderErrorsFlag = r_ShaderCache.ShowShaderErrors(); + r_ShaderCache.SetShowShaderErrorsFlag( false ); + r_ShaderCache.GenerateShaders( AMD::ShaderCache::CREATE_TYPE_USE_CACHED, true ); + r_ShaderCache.SetShowShaderErrorsFlag( bOldShaderErrorsFlag ); + } + } + else if (nControlID == GetEnum( AMD_IDC_COMBOBOX_TARGET_ISA )) + { + assert( r_ShaderCache.GenerateISAGPRPressure() ); // Shouldn't call this if we aren't using ISA + r_ShaderCache.SetTargetISA( (AMD::ISA_TARGET)((CDXUTComboBox*)pControl)->GetSelectedIndex() ); + } +#endif + else if (nControlID == GetEnum( AMD_IDC_BUTTON_SHOW_SHADERCACHE_UI )) + { + // Toggle Render of ShaderCache GUI + g_bAdvancedShaderCacheGUI_IsVisible = !g_bAdvancedShaderCacheGUI_IsVisible; + SetHUDVisibility( r_HUD, g_bAdvancedShaderCacheGUI_IsVisible ); + } +#endif + } + +} // namespace AMD diff --git a/src/DX11/framework/amd_sdk/src/Shaders/Line.hlsl b/src/DX11/framework/amd_sdk/src/Shaders/Line.hlsl new file mode 100644 index 0000000..ea227aa --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Shaders/Line.hlsl @@ -0,0 +1,46 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +cbuffer Constants : register ( b0 ) +{ + matrix viewProj; +}; + + +struct VertexInput +{ + float4 pos : POSITION; + float4 color : COLOR; +}; + + +void LineVS( in VertexInput input, out float4 color : COLOR0, out float4 screenpos : SV_Position ) +{ + color = input.color; + screenpos = mul( float4( input.pos.xyz, 1 ), viewProj ); +} + + +float4 LinePS( in float4 color : COLOR0 ) : SV_Target +{ + return color; +}; diff --git a/src/DX11/framework/amd_sdk/src/Shaders/Sprite.hlsl b/src/DX11/framework/amd_sdk/src/Shaders/Sprite.hlsl new file mode 100644 index 0000000..ea61dd5 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Shaders/Sprite.hlsl @@ -0,0 +1,270 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: Sprite.hlsl +// +// Simple screen space shaders for plotting various sprite types. +//-------------------------------------------------------------------------------------- + + +//-------------------------------------------------------------------------------------- +// Structures +//-------------------------------------------------------------------------------------- + +struct VsSpriteInput +{ + float3 v3Pos : POSITION; + float2 v2Tex : TEXTURE0; +}; + +struct PsSpriteInput +{ + float4 v4Pos : SV_Position; + float2 v2Tex : TEXTURE0; +}; + +struct VsSpriteBorderInput +{ + float3 v3Pos : POSITION; +}; + +struct PsSpriteBorderInput +{ + float4 v4Pos : SV_Position; +}; + +//-------------------------------------------------------------------------------------- +// Textures and Samplers +//-------------------------------------------------------------------------------------- + +Texture2D g_SpriteTexture : register( t0 ); +Texture2DMS g_SpriteTextureMS : register( t1 ); +Texture2DMS g_SpriteDepthTextureMS : register( t2 ); + +Texture3D g_VolumeTexture : register( t0 ); + +SamplerState g_Sampler : register( s0 ); + + +//-------------------------------------------------------------------------------------- +// Constant Buffers +//-------------------------------------------------------------------------------------- + +cbuffer cbSprite +{ + float4 g_f4ViewportSize; + float4 g_f4PlotParams; + float4 g_f4TextureSize; + float4 g_f4DepthRange; + float4 g_f4SpriteColor; + float4 g_f4BorderColor; + float4 g_f4SampleIndex; +}; + + +//-------------------------------------------------------------------------------------- +// Vertex Shaders +//-------------------------------------------------------------------------------------- + +PsSpriteInput VsSprite( VsSpriteInput I ) +{ + PsSpriteInput Output = (PsSpriteInput)0; + + // Output our final position + Output.v4Pos.x = ( ( g_f4PlotParams.z * I.v3Pos.x + g_f4PlotParams.x ) / ( g_f4ViewportSize.x / 2.0f ) ) - 1.0f; + Output.v4Pos.y = -( ( g_f4PlotParams.w * I.v3Pos.y + g_f4PlotParams.y ) / ( g_f4ViewportSize.y / 2.0f ) ) + 1.0f; + Output.v4Pos.z = I.v3Pos.z; + Output.v4Pos.w = 1.0f; + + // Propogate texture coordinate + Output.v2Tex = I.v2Tex; + + return Output; +} + +PsSpriteBorderInput VsSpriteBorder( VsSpriteBorderInput I ) +{ + PsSpriteBorderInput Output = (PsSpriteBorderInput)0; + + // Output our final position + Output.v4Pos.x = ( ( g_f4PlotParams.z * I.v3Pos.x + g_f4PlotParams.x ) / ( g_f4ViewportSize.x / 2.0f ) ) - 1.0f; + Output.v4Pos.y = -( ( g_f4PlotParams.w * I.v3Pos.y + g_f4PlotParams.y ) / ( g_f4ViewportSize.y / 2.0f ) ) + 1.0f; + Output.v4Pos.z = I.v3Pos.z; + Output.v4Pos.w = 1.0f; + + return Output; +} + + +//-------------------------------------------------------------------------------------- +// Pixel Shaders +//-------------------------------------------------------------------------------------- + +float4 PsSprite( PsSpriteInput I ) : SV_Target +{ + return g_f4SpriteColor * g_SpriteTexture.Sample( g_Sampler, I.v2Tex ); +} + + +float4 PsSpriteVolume( PsSpriteInput I ) : SV_Target +{ + int3 texCoord; + texCoord.x = (int)(I.v2Tex.x * g_f4TextureSize.x); + texCoord.y = (int)(I.v2Tex.y * g_f4TextureSize.y); + texCoord.z = g_f4TextureSize.z; + float value = g_VolumeTexture.Load( int4( texCoord, 0) ); + return g_f4SpriteColor * value; +} + + +float4 PsSpriteUntextured( PsSpriteInput I ) : SV_Target +{ + return g_f4SpriteColor; +} + +float4 PsSpriteMS( PsSpriteInput I ) : SV_Target +{ + int2 n2TexCoord; + n2TexCoord.x = (int)(I.v2Tex.x * g_f4TextureSize.x); + n2TexCoord.y = (int)(I.v2Tex.y * g_f4TextureSize.y); + + float4 v4Color; + v4Color.x = 0.0f; + v4Color.y = 0.0f; + v4Color.z = 0.0f; + v4Color.w = 0.0f; + + switch ( g_f4SampleIndex.x ) + { + case 0: + v4Color = g_SpriteTextureMS.Load( n2TexCoord, 0 ); + break; + case 1: + v4Color = g_SpriteTextureMS.Load( n2TexCoord, 1 ); + break; + case 2: + v4Color = g_SpriteTextureMS.Load( n2TexCoord, 2 ); + break; + case 3: + v4Color = g_SpriteTextureMS.Load( n2TexCoord, 3 ); + break; + case 4: + v4Color = g_SpriteTextureMS.Load( n2TexCoord, 4 ); + break; + case 5: + v4Color = g_SpriteTextureMS.Load( n2TexCoord, 5 ); + break; + case 6: + v4Color = g_SpriteTextureMS.Load( n2TexCoord, 6 ); + break; + case 7: + v4Color = g_SpriteTextureMS.Load( n2TexCoord, 7 ); + break; + } + + return v4Color; +} + +float4 PsSpriteAsDepth( PsSpriteInput I ) : SV_Target +{ + float4 v4Color = g_SpriteTexture.Sample( g_Sampler, I.v2Tex ); + + v4Color.x = 1.0f - v4Color.x; + + if ( v4Color.x < g_f4DepthRange.x ) + { + v4Color.x = g_f4DepthRange.x; + } + + if ( v4Color.x > g_f4DepthRange.y ) + { + v4Color.x = g_f4DepthRange.y; + } + + float fRange = g_f4DepthRange.y - g_f4DepthRange.x; + + v4Color.x = ( v4Color.x - g_f4DepthRange.x ) / fRange; + + return v4Color.xxxw; +} + +float4 PsSpriteAsDepthMS( PsSpriteInput I ) : SV_Target +{ + int2 n2TexCoord; + n2TexCoord.x = (int)(I.v2Tex.x * g_f4TextureSize.x); + n2TexCoord.y = (int)(I.v2Tex.y * g_f4TextureSize.y); + + float fColor = 0.0f; + + switch ( g_f4SampleIndex.x ) + { + case 0: + fColor = g_SpriteDepthTextureMS.Load( n2TexCoord, 0 ).x; + break; + case 1: + fColor = g_SpriteDepthTextureMS.Load( n2TexCoord, 1 ).x; + break; + case 2: + fColor = g_SpriteDepthTextureMS.Load( n2TexCoord, 2 ).x; + break; + case 3: + fColor = g_SpriteDepthTextureMS.Load( n2TexCoord, 3 ).x; + break; + case 4: + fColor = g_SpriteDepthTextureMS.Load( n2TexCoord, 4 ).x; + break; + case 5: + fColor = g_SpriteDepthTextureMS.Load( n2TexCoord, 5 ).x; + break; + case 6: + fColor = g_SpriteDepthTextureMS.Load( n2TexCoord, 6 ).x; + break; + case 7: + fColor = g_SpriteDepthTextureMS.Load( n2TexCoord, 7 ).x; + break; + } + + fColor = 1.0f - fColor; + + if ( fColor < g_f4DepthRange.x ) + { + fColor = g_f4DepthRange.x; + } + + if ( fColor > g_f4DepthRange.y ) + { + fColor = g_f4DepthRange.y; + } + + float fRange = g_f4DepthRange.y - g_f4DepthRange.x; + + fColor = ( fColor - g_f4DepthRange.x ) / fRange; + + return fColor.xxxx; + +} + +float4 PsSpriteBorder( PsSpriteBorderInput I ) : SV_Target +{ + return g_f4BorderColor; +} diff --git a/src/DX11/framework/amd_sdk/src/Sprite.cpp b/src/DX11/framework/amd_sdk/src/Sprite.cpp new file mode 100644 index 0000000..cbf3a52 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Sprite.cpp @@ -0,0 +1,815 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: Sprite.cpp +// +// Sprite class definition. This class provides functionality to render sprites, at a +// given position and scale. +//-------------------------------------------------------------------------------------- + +// DXUT helper code +#include "DXUT.h" +#include "SDKmisc.h" +#include "SDKMesh.h" + +#include "Sprite.h" +#include "HelperFunctions.h" + +using namespace AMD; + +struct SpriteVertex +{ + DirectX::XMFLOAT3 v3Pos; + DirectX::XMFLOAT2 v2TexCoord; +}; + +struct SpriteBorderVertex +{ + DirectX::XMFLOAT3 v3Pos; +}; + +// Constant buffer layout for transfering data to the sprite HLSL functions +struct CB_SPRITE +{ + float fViewportSize[4]; + float fPlotParams[4]; + float fTextureSize[4]; + float fDepthRange[4]; + float fSpriteColor[4]; + float fBorderColor[4]; + float fSampleIndex[4]; +}; +static CB_SPRITE s_CBSprite; + + +//-------------------------------------------------------------------------------------- +// Constructor +//-------------------------------------------------------------------------------------- +Sprite::Sprite() +{ + m_pVertexLayout = NULL; + m_pVertexBuffer = NULL; + m_pcbSprite = NULL; + + memset( &s_CBSprite, 0, sizeof( CB_SPRITE ) ); + + m_pSpriteVS = NULL; + m_pSpriteBorderVS = NULL; + m_pSpritePS = NULL; + m_pSpriteMSPS = NULL; + m_pSpriteAsDepthPS = NULL; + m_pSpriteAsDepthMSPS = NULL; + m_pSpriteBorderPS = NULL; + m_pSpriteUntexturedPS = NULL; + + m_EnableScissorTest = false; + m_PointSampleMode = true; + m_pSamplePoint = NULL; + m_pSampleLinear = NULL; + m_pRasterState = NULL; + m_pRasterStateWithScissor = NULL; + m_pEnableCulling = NULL; + m_pNoBlending = NULL; + m_pSrcAlphaBlending = NULL; + m_pDisableDepthTestWrite = NULL; + m_pEnableDepthTestWrite = NULL; + + SetSpriteColor( DirectX::XMVectorSet( 1.0f, 1.0f, 1.0f, 1.0f ) ); + SetBorderColor( DirectX::XMVectorSet( 0.0f, 0.0f, 0.0f, 1.0f ) ); +} + + +//-------------------------------------------------------------------------------------- +// Destructor +//-------------------------------------------------------------------------------------- +Sprite::~Sprite() +{ +} + + +//-------------------------------------------------------------------------------------- +// Hook method +//-------------------------------------------------------------------------------------- +HRESULT Sprite::OnCreateDevice( ID3D11Device* pd3dDevice ) +{ + HRESULT hr; + + // Check we have a valid device pointer + assert( NULL != pd3dDevice ); + + // Setup shaders + ID3DBlob* pBlob = NULL; + + // VS 1 + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "VsSprite", "vs_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreateVertexShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpriteVS ); + assert( D3D_OK == hr ); + // Define the input layout + D3D11_INPUT_ELEMENT_DESC layout[] = + { + { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "TEXTURE", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + }; + hr = pd3dDevice->CreateInputLayout( layout, ARRAYSIZE( layout ), pBlob->GetBufferPointer(), + pBlob->GetBufferSize(), &m_pVertexLayout ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + // VS 2 + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "VsSpriteBorder", "vs_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreateVertexShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpriteBorderVS ); + assert( D3D_OK == hr ); + // Define the input layout + D3D11_INPUT_ELEMENT_DESC BorderLayout[] = + { + { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + }; + hr = pd3dDevice->CreateInputLayout( BorderLayout, ARRAYSIZE( BorderLayout ), pBlob->GetBufferPointer(), + pBlob->GetBufferSize(), &m_pBorderVertexLayout ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + // PS 1 + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "PsSprite", "ps_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreatePixelShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpritePS ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + // PS 2 + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "PsSpriteMS", "ps_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreatePixelShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpriteMSPS ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + // PS 3 + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "PsSpriteAsDepth", "ps_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreatePixelShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpriteAsDepthPS ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + // PS 4 + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "PsSpriteAsDepthMS", "ps_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreatePixelShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpriteAsDepthMSPS ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + // PS 5 + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "PsSpriteBorder", "ps_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreatePixelShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpriteBorderPS ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "PsSpriteUntextured", "ps_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreatePixelShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpriteUntexturedPS ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + hr = AMD::CompileShaderFromFile( L"ShaderLibDX\\dx11\\Sprite.hlsl", "PsSpriteVolume", "ps_4_0", &pBlob, NULL ); + assert( D3D_OK == hr ); + hr = pd3dDevice->CreatePixelShader( pBlob->GetBufferPointer(), pBlob->GetBufferSize(), NULL, &m_pSpriteVolumePS ); + assert( D3D_OK == hr ); + SAFE_RELEASE( pBlob ); + + /////////////////////////////////////////////////////////////////////////// + // Setup VB for the textured sprite + /////////////////////////////////////////////////////////////////////////// + + // Fill out a unit quad + SpriteVertex QuadVertices[6]; + QuadVertices[0].v3Pos = DirectX::XMFLOAT3( 0.0f, -1.0f, 0.5f ); + QuadVertices[0].v2TexCoord = DirectX::XMFLOAT2( 0.0f, 0.0f ); + QuadVertices[1].v3Pos = DirectX::XMFLOAT3( 0.0f, 0.0f, 0.5f ); + QuadVertices[1].v2TexCoord = DirectX::XMFLOAT2( 0.0f, 1.0f ); + QuadVertices[2].v3Pos = DirectX::XMFLOAT3( 1.0f, -1.0f, 0.5f ); + QuadVertices[2].v2TexCoord = DirectX::XMFLOAT2( 1.0f, 0.0f ); + QuadVertices[3].v3Pos = DirectX::XMFLOAT3( 0.0f, 0.0f, 0.5f ); + QuadVertices[3].v2TexCoord = DirectX::XMFLOAT2( 0.0f, 1.0f ); + QuadVertices[4].v3Pos = DirectX::XMFLOAT3( 1.0f, 0.0f, 0.5f ); + QuadVertices[4].v2TexCoord = DirectX::XMFLOAT2( 1.0f, 1.0f ); + QuadVertices[5].v3Pos = DirectX::XMFLOAT3( 1.0f, -1.0f, 0.5f ); + QuadVertices[5].v2TexCoord = DirectX::XMFLOAT2( 1.0f, 0.0f ); + + // Create the vertex buffer + D3D11_BUFFER_DESC BD; + ZeroMemory( &BD, sizeof( BD ) ); + BD.Usage = D3D11_USAGE_DYNAMIC; + BD.ByteWidth = sizeof( SpriteVertex ) * 6; + BD.BindFlags = D3D11_BIND_VERTEX_BUFFER; + BD.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + BD.MiscFlags = 0; + D3D11_SUBRESOURCE_DATA InitData; + InitData.pSysMem = QuadVertices; + hr = pd3dDevice->CreateBuffer( &BD, &InitData, &m_pVertexBuffer ); + assert( D3D_OK == hr ); + + /////////////////////////////////////////////////////////////////////////// + // Setup VB for the sprite border + /////////////////////////////////////////////////////////////////////////// + + // Fill out a unit quad + SpriteBorderVertex QuadBorderVertices[5]; + QuadBorderVertices[0].v3Pos = DirectX::XMFLOAT3( 0.0f, -1.0f, 0.5f ); + QuadBorderVertices[1].v3Pos = DirectX::XMFLOAT3( 0.0f, 0.0f, 0.5f ); + QuadBorderVertices[2].v3Pos = DirectX::XMFLOAT3( 1.0f, 0.0f, 0.5f ); + QuadBorderVertices[3].v3Pos = DirectX::XMFLOAT3( 1.0f, -1.0f, 0.5f ); + QuadBorderVertices[4].v3Pos = DirectX::XMFLOAT3( 0.0f, -1.0f, 0.5f ); + + // Create the vertex buffer + BD.Usage = D3D11_USAGE_DEFAULT; + BD.ByteWidth = sizeof( SpriteBorderVertex ) * 5; + BD.BindFlags = D3D11_BIND_VERTEX_BUFFER; + BD.CPUAccessFlags = 0; + BD.MiscFlags = 0; + InitData.pSysMem = QuadBorderVertices; + hr = pd3dDevice->CreateBuffer( &BD, &InitData, &m_pBorderVertexBuffer ); + assert( D3D_OK == hr ); + + // Setup constant buffer + D3D11_BUFFER_DESC Desc; + ZeroMemory( &Desc, sizeof( Desc ) ); + Desc.Usage = D3D11_USAGE_DYNAMIC; + Desc.BindFlags = D3D11_BIND_CONSTANT_BUFFER; + Desc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + Desc.MiscFlags = 0; + Desc.ByteWidth = sizeof( CB_SPRITE ); + hr = pd3dDevice->CreateBuffer( &Desc, NULL, &m_pcbSprite ); + assert( D3D_OK == hr ); + + // Create sampler states for point and linear + // Point + D3D11_SAMPLER_DESC SamDesc; + SamDesc.Filter = D3D11_FILTER_MIN_MAG_MIP_POINT; + SamDesc.AddressU = D3D11_TEXTURE_ADDRESS_CLAMP; + SamDesc.AddressV = D3D11_TEXTURE_ADDRESS_CLAMP; + SamDesc.AddressW = D3D11_TEXTURE_ADDRESS_CLAMP; + SamDesc.MipLODBias = 0.0f; + SamDesc.MaxAnisotropy = 1; + SamDesc.ComparisonFunc = D3D11_COMPARISON_ALWAYS; + SamDesc.BorderColor[0] = SamDesc.BorderColor[1] = SamDesc.BorderColor[2] = SamDesc.BorderColor[3] = 0; + SamDesc.MinLOD = 0; + SamDesc.MaxLOD = D3D11_FLOAT32_MAX; + hr = pd3dDevice->CreateSamplerState( &SamDesc, &m_pSamplePoint ); + assert( D3D_OK == hr ); + // Linear + SamDesc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR; + SamDesc.AddressU = D3D11_TEXTURE_ADDRESS_WRAP; + SamDesc.AddressV = D3D11_TEXTURE_ADDRESS_WRAP; + SamDesc.AddressW = D3D11_TEXTURE_ADDRESS_WRAP; + hr = pd3dDevice->CreateSamplerState( &SamDesc, &m_pSampleLinear ); + assert( D3D_OK == hr ); + + // Disable culling + D3D11_RASTERIZER_DESC RasterizerDesc; + RasterizerDesc.FillMode = D3D11_FILL_SOLID; + RasterizerDesc.CullMode = D3D11_CULL_NONE; + RasterizerDesc.FrontCounterClockwise = FALSE; + RasterizerDesc.DepthBias = 0; + RasterizerDesc.DepthBiasClamp = 0.0f; + RasterizerDesc.SlopeScaledDepthBias = 0.0f; + RasterizerDesc.DepthClipEnable = TRUE; + RasterizerDesc.ScissorEnable = FALSE; + RasterizerDesc.MultisampleEnable = FALSE; + RasterizerDesc.AntialiasedLineEnable = FALSE; + hr = pd3dDevice->CreateRasterizerState( &RasterizerDesc, &m_pRasterState ); + assert( D3D_OK == hr ); + + RasterizerDesc.ScissorEnable = TRUE; + hr = pd3dDevice->CreateRasterizerState( &RasterizerDesc, &m_pRasterStateWithScissor ); + assert( D3D_OK == hr ); + + // Enable culling + RasterizerDesc.ScissorEnable = FALSE; + RasterizerDesc.CullMode = D3D11_CULL_BACK; + hr = pd3dDevice->CreateRasterizerState( &RasterizerDesc, &m_pEnableCulling ); + assert( D3D_OK == hr ); + + // No Blending + D3D11_BLEND_DESC BlendDesc; + BlendDesc.AlphaToCoverageEnable = FALSE; + BlendDesc.IndependentBlendEnable = FALSE; + D3D11_RENDER_TARGET_BLEND_DESC RTBlendDesc; + RTBlendDesc.BlendEnable = FALSE; + RTBlendDesc.SrcBlend = D3D11_BLEND_ONE; + RTBlendDesc.DestBlend = D3D11_BLEND_ZERO; + RTBlendDesc.BlendOp = D3D11_BLEND_OP_ADD; + RTBlendDesc.SrcBlendAlpha = D3D11_BLEND_ONE; + RTBlendDesc.DestBlendAlpha = D3D11_BLEND_ZERO; + RTBlendDesc.BlendOpAlpha = D3D11_BLEND_OP_ADD; + RTBlendDesc.RenderTargetWriteMask = 0x0F; + BlendDesc.RenderTarget[0] = RTBlendDesc; + BlendDesc.RenderTarget[1] = RTBlendDesc; + BlendDesc.RenderTarget[2] = RTBlendDesc; + BlendDesc.RenderTarget[3] = RTBlendDesc; + BlendDesc.RenderTarget[4] = RTBlendDesc; + BlendDesc.RenderTarget[5] = RTBlendDesc; + BlendDesc.RenderTarget[6] = RTBlendDesc; + BlendDesc.RenderTarget[7] = RTBlendDesc; + hr = pd3dDevice->CreateBlendState( &BlendDesc, &m_pNoBlending ); + assert( D3D_OK == hr ); + + // SrcAlphaBlending + BlendDesc.AlphaToCoverageEnable = FALSE; + BlendDesc.IndependentBlendEnable = FALSE; + RTBlendDesc.BlendEnable = TRUE; + RTBlendDesc.SrcBlend = D3D11_BLEND_SRC_ALPHA; + RTBlendDesc.DestBlend = D3D11_BLEND_INV_SRC_ALPHA; + RTBlendDesc.BlendOp = D3D11_BLEND_OP_ADD; + RTBlendDesc.SrcBlendAlpha = D3D11_BLEND_ZERO; + RTBlendDesc.DestBlendAlpha = D3D11_BLEND_ZERO; + RTBlendDesc.BlendOpAlpha = D3D11_BLEND_OP_ADD; + RTBlendDesc.RenderTargetWriteMask = 0x0F; + BlendDesc.RenderTarget[0] = RTBlendDesc; + BlendDesc.RenderTarget[1] = RTBlendDesc; + BlendDesc.RenderTarget[2] = RTBlendDesc; + BlendDesc.RenderTarget[3] = RTBlendDesc; + BlendDesc.RenderTarget[4] = RTBlendDesc; + BlendDesc.RenderTarget[5] = RTBlendDesc; + BlendDesc.RenderTarget[6] = RTBlendDesc; + BlendDesc.RenderTarget[7] = RTBlendDesc; + hr = pd3dDevice->CreateBlendState( &BlendDesc, &m_pSrcAlphaBlending ); + assert( D3D_OK == hr ); + + // Disable depth test write + D3D11_DEPTH_STENCIL_DESC DepthStencilDesc; + DepthStencilDesc.DepthEnable = FALSE; + DepthStencilDesc.DepthWriteMask = D3D11_DEPTH_WRITE_MASK_ZERO; + DepthStencilDesc.DepthFunc = D3D11_COMPARISON_LESS; + DepthStencilDesc.StencilEnable = FALSE; + DepthStencilDesc.StencilReadMask = D3D11_DEFAULT_STENCIL_READ_MASK; + DepthStencilDesc.StencilWriteMask = D3D11_DEFAULT_STENCIL_WRITE_MASK; + hr = pd3dDevice->CreateDepthStencilState( &DepthStencilDesc, &m_pDisableDepthTestWrite ); + assert( D3D_OK == hr ); + + // Disable depth test write + DepthStencilDesc.DepthEnable = TRUE; + DepthStencilDesc.DepthWriteMask = D3D11_DEPTH_WRITE_MASK_ALL; + hr = pd3dDevice->CreateDepthStencilState( &DepthStencilDesc, &m_pEnableDepthTestWrite ); + assert( D3D_OK == hr ); + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Hook method +//-------------------------------------------------------------------------------------- +void Sprite::OnDestroyDevice() +{ + SAFE_RELEASE( m_pVertexLayout ); + SAFE_RELEASE( m_pVertexBuffer ); + SAFE_RELEASE( m_pBorderVertexLayout ); + SAFE_RELEASE( m_pBorderVertexBuffer ); + + SAFE_RELEASE( m_pcbSprite ); + + SAFE_RELEASE( m_pSpriteVS ); + SAFE_RELEASE( m_pSpriteBorderVS ); + SAFE_RELEASE( m_pSpritePS ); + SAFE_RELEASE( m_pSpriteMSPS ); + SAFE_RELEASE( m_pSpriteAsDepthPS ); + SAFE_RELEASE( m_pSpriteAsDepthMSPS ); + SAFE_RELEASE( m_pSpriteBorderPS ); + SAFE_RELEASE( m_pSpriteUntexturedPS ); + SAFE_RELEASE( m_pSpriteVolumePS ); + + SAFE_RELEASE( m_pSamplePoint ); + SAFE_RELEASE( m_pSampleLinear ); + SAFE_RELEASE( m_pRasterState ); + SAFE_RELEASE( m_pRasterStateWithScissor ); + SAFE_RELEASE( m_pEnableCulling ); + SAFE_RELEASE( m_pNoBlending ); + SAFE_RELEASE( m_pSrcAlphaBlending ); + SAFE_RELEASE( m_pDisableDepthTestWrite ); + SAFE_RELEASE( m_pEnableDepthTestWrite ); +} + + +//-------------------------------------------------------------------------------------- +// Hook method +//-------------------------------------------------------------------------------------- +void Sprite::OnResizedSwapChain( const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ) +{ + assert( NULL != pBackBufferSurfaceDesc ); + + s_CBSprite.fViewportSize[0] = (float)pBackBufferSurfaceDesc->Width; + s_CBSprite.fViewportSize[1] = (float)pBackBufferSurfaceDesc->Height; +} + + +//-------------------------------------------------------------------------------------- +// Sets the sprite color +//-------------------------------------------------------------------------------------- +void Sprite::SetSpriteColor( DirectX::XMVECTOR Color ) +{ + s_CBSprite.fSpriteColor[0] = DirectX::XMVectorGetX( Color ); + s_CBSprite.fSpriteColor[1] = DirectX::XMVectorGetY( Color ); + s_CBSprite.fSpriteColor[2] = DirectX::XMVectorGetZ( Color ); + s_CBSprite.fSpriteColor[3] = DirectX::XMVectorGetW( Color ); +} + + +//-------------------------------------------------------------------------------------- +// Sets the border color for a sprite +//-------------------------------------------------------------------------------------- +void Sprite::SetBorderColor( DirectX::XMVECTOR Color ) +{ + s_CBSprite.fBorderColor[0] = DirectX::XMVectorGetX( Color ); + s_CBSprite.fBorderColor[1] = DirectX::XMVectorGetY( Color ); + s_CBSprite.fBorderColor[2] = DirectX::XMVectorGetZ( Color ); + s_CBSprite.fBorderColor[3] = DirectX::XMVectorGetW( Color ); +} + + +//-------------------------------------------------------------------------------------- +// Set the UVs to be used for the sprite render +//-------------------------------------------------------------------------------------- +void Sprite::SetUVs( float fU1, float fV1, float fU2, float fV2 ) +{ + D3D11_MAPPED_SUBRESOURCE MappedResource; + DXUTGetD3D11DeviceContext()->Map( m_pVertexBuffer, 0, D3D11_MAP_WRITE_DISCARD, 0, &MappedResource ); + SpriteVertex* pQuadVertices = (SpriteVertex*)MappedResource.pData; + + pQuadVertices[0].v3Pos = DirectX::XMFLOAT3( 0.0f, -1.0f, 0.5f ); + pQuadVertices[0].v2TexCoord = DirectX::XMFLOAT2( fU1, fV1 ); + pQuadVertices[1].v3Pos = DirectX::XMFLOAT3( 0.0f, 0.0f, 0.5f ); + pQuadVertices[1].v2TexCoord = DirectX::XMFLOAT2( fU1, fV2 ); + pQuadVertices[2].v3Pos = DirectX::XMFLOAT3( 1.0f, -1.0f, 0.5f ); + pQuadVertices[2].v2TexCoord = DirectX::XMFLOAT2( fU2, fV1 ); + pQuadVertices[3].v3Pos = DirectX::XMFLOAT3( 0.0f, 0.0f, 0.5f ); + pQuadVertices[3].v2TexCoord = DirectX::XMFLOAT2( fU1, fV2 ); + pQuadVertices[4].v3Pos = DirectX::XMFLOAT3( 1.0f, 0.0f, 0.5f ); + pQuadVertices[4].v2TexCoord = DirectX::XMFLOAT2( fU2, fV2 ); + pQuadVertices[5].v3Pos = DirectX::XMFLOAT3( 1.0f, -1.0f, 0.5f ); + pQuadVertices[5].v2TexCoord = DirectX::XMFLOAT2( fU2, fV1 ); + + DXUTGetD3D11DeviceContext()->Unmap( m_pVertexBuffer, 0 ); +} + + +//-------------------------------------------------------------------------------------- +// Renders the sprite +//-------------------------------------------------------------------------------------- +HRESULT Sprite::RenderSprite( ID3D11ShaderResourceView* pTextureView, int nStartPosX, + int nStartPosY, int nWidth, int nHeight, bool bAlpha, bool bBordered ) +{ + ID3D11ShaderResourceView* pNULLSRV = NULL; + + s_CBSprite.fPlotParams[0] = (float)nStartPosX; + s_CBSprite.fPlotParams[1] = (float)nStartPosY; + s_CBSprite.fPlotParams[2] = (float)nWidth; + s_CBSprite.fPlotParams[3] = (float)nHeight; + + if (pTextureView) + { + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pTextureView ); + DXUTGetD3D11DeviceContext()->PSSetSamplers( 0, 1, m_PointSampleMode ? &m_pSamplePoint : &m_pSampleLinear ); + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpritePS, NULL, 0 ); + } + else + { + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteUntexturedPS, NULL, 0 ); + } + + float black[4] = { 0, 0, 0, 0 }; + if (bAlpha) + { + DXUTGetD3D11DeviceContext()->OMSetBlendState( m_pSrcAlphaBlending, black, 0xFFFFFFFF ); + } + else + { + DXUTGetD3D11DeviceContext()->OMSetBlendState( m_pNoBlending, black, 0xFFFFFFFF ); + } + + // Do the render + Render(); + + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pNULLSRV ); + + // Optionally render a border + if (bBordered) + { + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteBorderPS, NULL, 0 ); + + RenderBorder(); + } + + return D3D_OK; +} + + +//-------------------------------------------------------------------------------------- +// Renders the MS sprite +//-------------------------------------------------------------------------------------- +HRESULT Sprite::RenderSpriteMS( ID3D11ShaderResourceView* pTextureView, int nStartPosX, + int nStartPosY, int nWidth, int nHeight, int nTextureWidth, int nTextureHeight, + bool bAlpha, bool bBordered, int nSampleIndex ) +{ + ID3D11SamplerState* ppSamplerStates[2] = { m_pSamplePoint, m_pSampleLinear }; + ID3D11ShaderResourceView* pNULLSRV = NULL; + + assert( NULL != pTextureView ); + + s_CBSprite.fPlotParams[0] = (float)nStartPosX; + s_CBSprite.fPlotParams[1] = (float)nStartPosY; + s_CBSprite.fPlotParams[2] = (float)nWidth; + s_CBSprite.fPlotParams[3] = (float)nHeight; + s_CBSprite.fTextureSize[0] = (float)nTextureWidth; + s_CBSprite.fTextureSize[1] = (float)nTextureHeight; + s_CBSprite.fSampleIndex[0] = (float)nSampleIndex; + + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pTextureView ); + DXUTGetD3D11DeviceContext()->PSSetSamplers( 0, 2, ppSamplerStates ); + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteMSPS, NULL, 0 ); + + float black[4] = { 0, 0, 0, 0 }; + if (bAlpha) + { + DXUTGetD3D11DeviceContext()->OMSetBlendState( m_pSrcAlphaBlending, black, 0xFFFFFFFF ); + } + else + { + DXUTGetD3D11DeviceContext()->OMSetBlendState( m_pNoBlending, black, 0xFFFFFFFF ); + } + + // Do the render + Render(); + + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pNULLSRV ); + + // Optionally render a border + if (bBordered) + { + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteBorderPS, NULL, 0 ); + + RenderBorder(); + } + + return D3D_OK; +} + + +//-------------------------------------------------------------------------------------- +// Renders sprite as depth +//-------------------------------------------------------------------------------------- +HRESULT Sprite::RenderSpriteAsDepth( ID3D11ShaderResourceView* pTextureView, int nStartPosX, + int nStartPosY, int nWidth, int nHeight, bool bBordered, float fDepthRangeMin, + float fDepthRangeMax ) +{ + ID3D11SamplerState* ppSamplerStates[2] = { m_pSamplePoint, m_pSampleLinear }; + ID3D11ShaderResourceView* pNULLSRV = NULL; + + assert( NULL != pTextureView ); + + s_CBSprite.fPlotParams[0] = (float)nStartPosX; + s_CBSprite.fPlotParams[1] = (float)nStartPosY; + s_CBSprite.fPlotParams[2] = (float)nWidth; + s_CBSprite.fPlotParams[3] = (float)nHeight; + s_CBSprite.fDepthRange[0] = fDepthRangeMin; + s_CBSprite.fDepthRange[1] = fDepthRangeMax; + + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pTextureView ); + DXUTGetD3D11DeviceContext()->PSSetSamplers( 0, 2, ppSamplerStates ); + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteAsDepthPS, NULL, 0 ); + + float black[4] = { 0, 0, 0, 0 }; + DXUTGetD3D11DeviceContext()->OMSetBlendState( m_pNoBlending, black, 0xFFFFFFFF ); + + // Do the render + Render(); + + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pNULLSRV ); + + // Optionally render a border + if (bBordered) + { + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteBorderPS, NULL, 0 ); + RenderBorder(); + } + + return D3D_OK; +} + + +//-------------------------------------------------------------------------------------- +// Renders the sprite as MS depth +//-------------------------------------------------------------------------------------- +HRESULT Sprite::RenderSpriteAsDepthMS( ID3D11ShaderResourceView* pTextureView, int nStartPosX, + int nStartPosY, int nWidth, int nHeight, int nTextureWidth, int nTextureHeight, + bool bBordered, float fDepthRangeMin, float fDepthRangeMax, int nSampleIndex ) +{ + ID3D11SamplerState* ppSamplerStates[2] = { m_pSamplePoint, m_pSampleLinear }; + ID3D11ShaderResourceView* pNULLSRV = NULL; + + assert( NULL != pTextureView ); + + s_CBSprite.fPlotParams[0] = (float)nStartPosX; + s_CBSprite.fPlotParams[1] = (float)nStartPosY; + s_CBSprite.fPlotParams[2] = (float)nWidth; + s_CBSprite.fPlotParams[3] = (float)nHeight; + s_CBSprite.fTextureSize[0] = (float)nTextureWidth; + s_CBSprite.fTextureSize[1] = (float)nTextureHeight; + s_CBSprite.fSampleIndex[0] = (float)nSampleIndex; + s_CBSprite.fDepthRange[0] = fDepthRangeMin; + s_CBSprite.fDepthRange[1] = fDepthRangeMax; + + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pTextureView ); + DXUTGetD3D11DeviceContext()->PSSetSamplers( 0, 2, ppSamplerStates ); + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteAsDepthMSPS, NULL, 0 ); + + float black[4] = { 0, 0, 0, 0 }; + DXUTGetD3D11DeviceContext()->OMSetBlendState( m_pNoBlending, black, 0xFFFFFFFF ); + + // Do the render + Render(); + + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pNULLSRV ); + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteBorderPS, NULL, 0 ); + + // Optionally render a border + if (bBordered) + { + RenderBorder(); + } + + return D3D_OK; +} + + +HRESULT Sprite::RenderSpriteVolume( ID3D11ShaderResourceView* pTextureView, int nStartPosX, int nStartPosY, int nMaxWidth, int nSliceSize, bool bBordered ) +{ + ID3D11Texture3D* texture = 0; + pTextureView->GetResource( (ID3D11Resource**)&texture ); + D3D11_TEXTURE3D_DESC desc; + texture->GetDesc( &desc ); + texture->Release(); + + s_CBSprite.fPlotParams[2] = (float)nSliceSize; + s_CBSprite.fPlotParams[3] = (float)nSliceSize; + + s_CBSprite.fTextureSize[0] = (float)desc.Width; + s_CBSprite.fTextureSize[1] = (float)desc.Height; + + DXUTGetD3D11DeviceContext()->PSSetShaderResources( 0, 1, &pTextureView ); + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteVolumePS, NULL, 0 ); + + + /* if( bAlpha ) + { + DXUTGetD3D11DeviceContext()->OMSetBlendState( m_pSrcAlphaBlending, D3DXVECTOR4( 0.0f, 0.0f, 0.0f, 0.0f ), 0xFFFFFFFF ); + } + else*/ + { + float black[4] = { 0, 0, 0, 0 }; + DXUTGetD3D11DeviceContext()->OMSetBlendState( m_pNoBlending, black, 0xFFFFFFFF ); + } + + // Do the render + for (int j = 0; j < (bBordered ? 2 : 1); j++) + { + if (j == 1) + { + DXUTGetD3D11DeviceContext()->PSSetShader( m_pSpriteBorderPS, NULL, 0 ); + } + + float fYPos = (float)nStartPosY; + float fXPos = 0.0f; + for (UINT i = 0; i < desc.Depth; i++) + { + s_CBSprite.fPlotParams[0] = (float)nStartPosX + fXPos; + s_CBSprite.fPlotParams[1] = fYPos; + s_CBSprite.fTextureSize[2] = (float)i; + + if (j == 0) + { + Render(); + } + else + { + RenderBorder(); + } + + fXPos += (float)nSliceSize; + if (fXPos > (float)(nMaxWidth - nSliceSize)) + { + fXPos = 0.0f; + fYPos += (float)nSliceSize; + } + } + } + + return D3D_OK; +} + + +//-------------------------------------------------------------------------------------- +// Renders the border +//-------------------------------------------------------------------------------------- +void Sprite::RenderBorder() +{ + // Set states + DXUTGetD3D11DeviceContext()->RSSetState( m_EnableScissorTest ? m_pRasterStateWithScissor : m_pRasterState ); + DXUTGetD3D11DeviceContext()->OMSetDepthStencilState( m_pDisableDepthTestWrite, 0x00 ); + + // Update constant buffer + D3D11_MAPPED_SUBRESOURCE MappedResource; + DXUTGetD3D11DeviceContext()->Map( m_pcbSprite, 0, D3D11_MAP_WRITE_DISCARD, 0, &MappedResource ); + memcpy( MappedResource.pData, &s_CBSprite, sizeof( CB_SPRITE ) ); + DXUTGetD3D11DeviceContext()->Unmap( m_pcbSprite, 0 ); + DXUTGetD3D11DeviceContext()->VSSetConstantBuffers( 0, 1, &m_pcbSprite ); + DXUTGetD3D11DeviceContext()->PSSetConstantBuffers( 0, 1, &m_pcbSprite ); + + // Set vertex shader + DXUTGetD3D11DeviceContext()->VSSetShader( m_pSpriteBorderVS, NULL, 0 ); + DXUTGetD3D11DeviceContext()->HSSetShader( NULL, NULL, 0 ); + DXUTGetD3D11DeviceContext()->DSSetShader( NULL, NULL, 0 ); + DXUTGetD3D11DeviceContext()->GSSetShader( NULL, NULL, 0 ); + + // Set the input layout + DXUTGetD3D11DeviceContext()->IASetInputLayout( m_pBorderVertexLayout ); + + // Set vertex buffer + UINT Stride = sizeof( SpriteBorderVertex ); + UINT Offset = 0; + DXUTGetD3D11DeviceContext()->IASetVertexBuffers( 0, 1, &m_pBorderVertexBuffer, &Stride, &Offset ); + + // Set primitive topology + DXUTGetD3D11DeviceContext()->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_LINESTRIP ); + + // Render + DXUTGetD3D11DeviceContext()->Draw( 5, 0 ); + + // Reset states + DXUTGetD3D11DeviceContext()->RSSetState( m_pEnableCulling ); + DXUTGetD3D11DeviceContext()->OMSetDepthStencilState( m_pEnableDepthTestWrite, 0xff ); +} + + +//-------------------------------------------------------------------------------------- +// Actually does the plot +//-------------------------------------------------------------------------------------- +void Sprite::Render() +{ + // Set states + DXUTGetD3D11DeviceContext()->RSSetState( m_EnableScissorTest ? m_pRasterStateWithScissor : m_pRasterState ); + DXUTGetD3D11DeviceContext()->OMSetDepthStencilState( m_pDisableDepthTestWrite, 0x00 ); + + // Update constant buffer + D3D11_MAPPED_SUBRESOURCE MappedResource; + DXUTGetD3D11DeviceContext()->Map( m_pcbSprite, 0, D3D11_MAP_WRITE_DISCARD, 0, &MappedResource ); + memcpy( MappedResource.pData, &s_CBSprite, sizeof( CB_SPRITE ) ); + DXUTGetD3D11DeviceContext()->Unmap( m_pcbSprite, 0 ); + DXUTGetD3D11DeviceContext()->VSSetConstantBuffers( 0, 1, &m_pcbSprite ); + DXUTGetD3D11DeviceContext()->PSSetConstantBuffers( 0, 1, &m_pcbSprite ); + + // Set vertex shader + DXUTGetD3D11DeviceContext()->VSSetShader( m_pSpriteVS, NULL, 0 ); + DXUTGetD3D11DeviceContext()->HSSetShader( NULL, NULL, 0 ); + DXUTGetD3D11DeviceContext()->DSSetShader( NULL, NULL, 0 ); + DXUTGetD3D11DeviceContext()->GSSetShader( NULL, NULL, 0 ); + + // Set the input layout + DXUTGetD3D11DeviceContext()->IASetInputLayout( m_pVertexLayout ); + + // Set vertex buffer + UINT Stride = sizeof( SpriteVertex ); + UINT Offset = 0; + DXUTGetD3D11DeviceContext()->IASetVertexBuffers( 0, 1, &m_pVertexBuffer, &Stride, &Offset ); + + // Set primitive topology + DXUTGetD3D11DeviceContext()->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST ); + + // Render + DXUTGetD3D11DeviceContext()->Draw( 6, 0 ); + + // Reset states + DXUTGetD3D11DeviceContext()->RSSetState( m_pEnableCulling ); + DXUTGetD3D11DeviceContext()->OMSetDepthStencilState( m_pEnableDepthTestWrite, 0xff ); +} diff --git a/src/DX11/framework/amd_sdk/src/Sprite.h b/src/DX11/framework/amd_sdk/src/Sprite.h new file mode 100644 index 0000000..3a9693b --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Sprite.h @@ -0,0 +1,110 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +//-------------------------------------------------------------------------------------- +// File: Sprite.h +// +// Sprite class definition. This class provides functionality to render sprites, at a +// given position and scale. +//-------------------------------------------------------------------------------------- +#ifndef AMD_SDK_SPRITE_H +#define AMD_SDK_SPRITE_H + +namespace AMD +{ + + class Sprite + { + public: + + Sprite(); + ~Sprite(); + + HRESULT OnCreateDevice( ID3D11Device* pd3dDevice ); + void OnDestroyDevice(); + void OnResizedSwapChain( const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ); + + HRESULT RenderSprite( ID3D11ShaderResourceView* pTextureView, int nStartPosX, + int nStartPosY, int nWidth, int nHeight, bool bAlpha, bool bBordered ); + + HRESULT RenderSpriteMS( ID3D11ShaderResourceView* pTextureView, int nStartPosX, + int nStartPosY, int nWidth, int nHeight, int nTextureWidth, int nTextureHeight, + bool bAlpha, bool bBordered, int nSampleIndex ); + + HRESULT RenderSpriteAsDepth( ID3D11ShaderResourceView* pTextureView, int nStartPosX, + int nStartPosY, int nWidth, int nHeight, bool bBordered, float fDepthRangeMin, + float fDepthRangeMax ); + + HRESULT RenderSpriteAsDepthMS( ID3D11ShaderResourceView* pTextureView, int nStartPosX, + int nStartPosY, int nWidth, int nHeight, int nTextureWidth, int nTextureHeight, + bool bBordered, float fDepthRangeMin, float fDepthRangeMax, int nSampleIndex ); + + HRESULT RenderSpriteVolume( ID3D11ShaderResourceView* pTextureView, int nStartPosX, int nStartPosY, int nMaxWidth, int nSliceSize, bool bBordered ); + + void SetSpriteColor( DirectX::XMVECTOR Color ); + void SetBorderColor( DirectX::XMVECTOR Color ); + void SetUVs( float fU1, float fV1, float fU2, float fV2 ); + void EnableScissorTest( bool enable ) { m_EnableScissorTest = enable; } + void SetPointSample( bool pointSample ) { m_PointSampleMode = pointSample; } + + private: + + void RenderBorder(); + void Render(); + + // VBs + ID3D11InputLayout* m_pVertexLayout; + ID3D11Buffer* m_pVertexBuffer; + ID3D11InputLayout* m_pBorderVertexLayout; + ID3D11Buffer* m_pBorderVertexBuffer; + + // CB + ID3D11Buffer* m_pcbSprite; + + // Shaders + ID3D11VertexShader* m_pSpriteVS; + ID3D11VertexShader* m_pSpriteBorderVS; + ID3D11PixelShader* m_pSpritePS; + ID3D11PixelShader* m_pSpriteMSPS; + ID3D11PixelShader* m_pSpriteAsDepthPS; + ID3D11PixelShader* m_pSpriteAsDepthMSPS; + ID3D11PixelShader* m_pSpriteBorderPS; + ID3D11PixelShader* m_pSpriteUntexturedPS; + ID3D11PixelShader* m_pSpriteVolumePS; + + // States + bool m_EnableScissorTest; + bool m_PointSampleMode; + ID3D11SamplerState* m_pSamplePoint; + ID3D11SamplerState* m_pSampleLinear; + ID3D11RasterizerState* m_pRasterState; + ID3D11RasterizerState* m_pRasterStateWithScissor; + ID3D11RasterizerState* m_pEnableCulling; + ID3D11BlendState* m_pNoBlending; + ID3D11BlendState* m_pSrcAlphaBlending; + ID3D11DepthStencilState* m_pDisableDepthTestWrite; + ID3D11DepthStencilState* m_pEnableDepthTestWrite; + }; + +} // namespace AMD + +#endif // AMD_SDK_SPRITE_H diff --git a/src/DX11/framework/amd_sdk/src/Timer.cpp b/src/DX11/framework/amd_sdk/src/Timer.cpp new file mode 100644 index 0000000..b88e3a8 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Timer.cpp @@ -0,0 +1,909 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +#include "DXUT.h" +#include "Timer.h" + +//using namespace AMD; + +#if USE_RDTSC +__declspec(naked) LONGLONG __cdecl rdtsc_time(void) +{ + __asm rdtsc + __asm ret +} +#endif + +//----------------------------------------------------------------------------- +Timer::Timer() : +m_LastTime( 0.0 ), +m_SumTime( 0.0 ), +m_NumFrames( 0 ) +{ +} + +Timer::~Timer() +{ +} + +double Timer::GetTime() +{ + FinishCollection(); + + return m_LastTime; +} +double Timer::GetSumTime() +{ + return m_SumTime; +} + +double Timer::GetTimeNumFrames() +{ + return m_NumFrames; +} + +//----------------------------------------------------------------------------- + +CpuTimer::CpuTimer() : +Timer() +{ + LARGE_INTEGER freq; + QueryPerformanceFrequency( &freq ); + m_freq = static_cast(freq.QuadPart); + +#if USE_RDTSC + const double calibrationTime = 0.1; + + LONGLONG start, stop; + start = rdtsc_time(); + Delay(calibrationTime); + stop = rdtsc_time(); + + m_freqRdtsc = static_cast(stop - start) / calibrationTime; +#endif +} + +CpuTimer::~CpuTimer() +{ +} + +void CpuTimer::Reset( bool bResetSum ) +{ + m_LastTime = 0.0; + if (bResetSum) + { + m_SumTime = 0.0; + m_NumFrames = 0; + } + else + { + ++m_NumFrames; + } +} + +void CpuTimer::Start() +{ +#if USE_RDTSC + m_startTime.QuadPart = rdtsc_time(); +#else + QueryPerformanceCounter( &m_startTime ); +#endif +} + +void CpuTimer::Stop() +{ + LARGE_INTEGER t; + double freq; + +#if USE_RDTSC + t.QuadPart = rdtsc_time(); + freq = m_freqRdtsc; +#else + QueryPerformanceCounter( &t ); + freq = m_freq; +#endif + + m_LastTime += static_cast(t.QuadPart - m_startTime.QuadPart) / freq; + m_SumTime += static_cast(t.QuadPart - m_startTime.QuadPart) / freq; +} + +void CpuTimer::Delay( double sec ) +{ + LARGE_INTEGER start, stop; + double t; + + QueryPerformanceCounter( &start ); + + do + { + QueryPerformanceCounter( &stop ); + + t = static_cast(stop.QuadPart - start.QuadPart) / m_freq; + } while (t < sec); +} + +//----------------------------------------------------------------------------- + +GpuTimer::GpuTimer( ID3D11Device* pDev, UINT64 freq, UINT numTimeStamps ) : +Timer(), +m_pDevCtx( NULL ), +m_numTimeStamps( numTimeStamps ), +m_curIssueTs( m_numTimeStamps - 1 ), +m_nextRetrTs( 0 ), +m_FrameID( 0 ), + +m_CurTime( 0.0 ) +{ + HRESULT hr; + + _ASSERT( pDev != NULL ); + _ASSERT( numTimeStamps>0 ); + + pDev->GetImmediateContext( &m_pDevCtx ); + _ASSERT( m_pDevCtx != NULL ); + + D3D11_QUERY_DESC qd; + qd.MiscFlags = 0; + + m_ts = new TsRecord[m_numTimeStamps]; + for (UINT i = 0; i < m_numTimeStamps; i++) + { + qd.Query = D3D11_QUERY_TIMESTAMP_DISJOINT; + + hr = pDev->CreateQuery( &qd, &m_ts[i].pDisjointTS ); + _ASSERT( (hr == S_OK) && (m_ts[i].pDisjointTS != NULL) ); + + qd.Query = D3D11_QUERY_TIMESTAMP; + + hr = pDev->CreateQuery( &qd, &m_ts[i].pStart ); + _ASSERT( (hr == S_OK) && (m_ts[i].pStart != NULL) ); + + hr = pDev->CreateQuery( &qd, &m_ts[i].pStop ); + _ASSERT( (hr == S_OK) && (m_ts[i].pStop != NULL) ); + + m_ts[i].state.stateWord = 0; + } + m_CurTimeFrame.id = 0; + m_CurTimeFrame.invalid = 1; + + freq = 0;//prevent warning +} + +GpuTimer::~GpuTimer() +{ + for (UINT i = 0; i < m_numTimeStamps; i++) + { + SAFE_RELEASE( m_ts[i].pDisjointTS ); + SAFE_RELEASE( m_ts[i].pStart ); + SAFE_RELEASE( m_ts[i].pStop ); + } + SAFE_DELETE_ARRAY( m_ts ); + + SAFE_RELEASE( m_pDevCtx ); +} + +void GpuTimer::Reset( bool bResetSum ) +{ + FinishCollection(); + m_FrameID = (m_FrameID + 1) & 0x3FFFFFFF; + + if (bResetSum) + { + WaitIdle(); + m_CurTimeFrame.invalid = 1; + m_CurTime = 0.0; + m_LastTime = 0.0; + m_SumTime = 0.0; + m_NumFrames = 0; + } +} + +void GpuTimer::Start() +{ + if (++m_curIssueTs == m_numTimeStamps) + { + m_curIssueTs = 0; + } + + if (0 != m_ts[m_curIssueTs].state.data.startIssued) + { + _ASSERT( false && "CPU stall required! This should never happen. Please increase GpuTimer::NumTimeStamps in Timer.h" ); + CollectData( m_curIssueTs, TRUE ); + } + + m_ts[m_curIssueTs].state.data.frameID = m_FrameID; + m_ts[m_curIssueTs].state.data.startIssued = 1; + m_ts[m_curIssueTs].state.data.stopIssued = 0; + m_pDevCtx->Begin( m_ts[m_curIssueTs].pDisjointTS ); + m_pDevCtx->End( m_ts[m_curIssueTs].pStart ); +} + +void GpuTimer::Stop() +{ + // check if timestamp start has been issued but no stop yet + _ASSERT( (m_ts[m_curIssueTs].state.data.startIssued == 1) && (m_ts[m_curIssueTs].state.data.stopIssued == 0) ); + + m_ts[m_curIssueTs].state.data.stopIssued = 1; + m_pDevCtx->End( m_ts[m_curIssueTs].pStop ); + m_pDevCtx->End( m_ts[m_curIssueTs].pDisjointTS ); +} + +void GpuTimer::WaitIdle() +{ + while (m_nextRetrTs != m_curIssueTs) + { + CollectData( m_nextRetrTs, true ); + + if (++m_nextRetrTs == m_numTimeStamps) + { + m_nextRetrTs = 0; + } + } + + // retrieve the current Ts + CollectData( m_nextRetrTs, true ); + if (++m_nextRetrTs == m_numTimeStamps) + { + m_nextRetrTs = 0; + } + + if (0 == m_CurTimeFrame.invalid) + { + m_LastTime = m_CurTime; + m_SumTime += m_CurTime; + ++m_NumFrames; + } +} + +void GpuTimer::FinishCollection() +{ + // retrieve all available timestamps + while (CollectData( m_nextRetrTs )) + { + if (++m_nextRetrTs == m_numTimeStamps) + { + m_nextRetrTs = 0; + } + } +} + +bool GpuTimer::CollectData( UINT idx, BOOL stall ) +{ + if (!m_ts[idx].state.data.stopIssued) + { + return false; + } + + // start collecting data from a new frame? + if (m_ts[idx].state.data.frameID != m_CurTimeFrame.id) + { + // if frametimes collected are valid: write them into m_time + // so m_time always contains the most recent valid timing data + if (0 == m_CurTimeFrame.invalid) + { + m_LastTime = m_CurTime; + m_SumTime += m_CurTime; + ++m_NumFrames; + } + + // start collecting time data of the next frame + m_CurTime = 0.0; + m_CurTimeFrame.id = m_ts[idx].state.data.frameID; + m_CurTimeFrame.invalid = 0; + } + + // if we want to retrieve the next timing data NOW the CPU will stall + // increase NumTimeStamps in Timer.h to prevent this from happening + if (stall) + { + HRESULT hr; + UINT64 start, stop; + + D3D11_QUERY_DATA_TIMESTAMP_DISJOINT tsd; + do + { + hr = m_pDevCtx->GetData( m_ts[idx].pDisjointTS, &tsd, sizeof( D3D11_QUERY_DATA_TIMESTAMP_DISJOINT ), 0 ); + } while (hr == S_FALSE); + + _ASSERT( hr == S_OK ); + + do + { + hr = m_pDevCtx->GetData( m_ts[idx].pStart, &start, sizeof( UINT64 ), 0 ); + } while (hr == S_FALSE); + + _ASSERT( hr == S_OK ); + + do + { + hr = m_pDevCtx->GetData( m_ts[idx].pStop, &stop, sizeof( UINT64 ), 0 ); + } while (hr == S_FALSE); + + _ASSERT( hr == S_OK ); + + if (tsd.Disjoint || ((start & 0xFFFFFFFF) == 0xFFFFFFFF) || ((stop & 0xFFFFFFFF) == 0xFFFFFFFF)) + { + // mark current frametime as invalid + m_CurTimeFrame.invalid = 1; + } + else + { + m_CurTime += static_cast(stop - start) / static_cast(tsd.Frequency); + } + + m_ts[idx].state.stateWord = 0; + return true; + } + + // finally try collecting the available data, return false if it was not yet available + UINT64 start, stop; + + D3D11_QUERY_DATA_TIMESTAMP_DISJOINT tsd; + if (S_FALSE == m_pDevCtx->GetData( m_ts[idx].pDisjointTS, &tsd, sizeof( D3D11_QUERY_DATA_TIMESTAMP_DISJOINT ), 0 )) + { + return false; + } + if (S_FALSE == m_pDevCtx->GetData( m_ts[idx].pStart, &start, sizeof( UINT64 ), 0 )) + { + return false; + } + + if (S_FALSE == m_pDevCtx->GetData( m_ts[idx].pStop, &stop, sizeof( UINT64 ), 0 )) + { + return false; + } + + // all data was available, so evaluate times + if (tsd.Disjoint || ((start & 0xFFFFFFFF) == 0xFFFFFFFF) || ((stop & 0xFFFFFFFF) == 0xFFFFFFFF)) + { + // mark current frametime as invalid + m_CurTimeFrame.invalid = 1; + } + else + { + UINT64 dt = (stop - start); + m_CurTime += static_cast(dt) / static_cast(tsd.Frequency); + } + + m_ts[idx].state.stateWord = 0; + return true; +} + +//----------------------------------------------------------------------------- + +GpuCpuTimer::GpuCpuTimer( ID3D11Device* pDev ) : +CpuTimer() +{ + HRESULT hr; + + _ASSERT( pDev != NULL ); + + pDev->GetImmediateContext( &m_pDevCtx ); + _ASSERT( m_pDevCtx != NULL ); + + D3D11_QUERY_DESC qd; + qd.Query = D3D11_QUERY_EVENT; + qd.MiscFlags = 0; + + hr = pDev->CreateQuery( &qd, &m_pEvent ); + _ASSERT( (hr == S_OK) && (m_pEvent != NULL) ); +} + +GpuCpuTimer::~GpuCpuTimer() +{ + SAFE_RELEASE( m_pEvent ); + SAFE_RELEASE( m_pDevCtx ); +} + +void GpuCpuTimer::Start() +{ + WaitIdle(); + CpuTimer::Start(); +} + +void GpuCpuTimer::Stop() +{ + WaitIdle(); + CpuTimer::Stop(); +} + +void GpuCpuTimer::WaitIdle() +{ + m_pDevCtx->End( m_pEvent ); + + HRESULT hr; + BOOL data; + + do + { + hr = m_pDevCtx->GetData( m_pEvent, &data, sizeof( BOOL ), 0 ); + } while (hr == S_FALSE); + + _ASSERT( hr == S_OK ); +} + +//----------------------------------------------------------------------------- +// convenience timer functions +//----------------------------------------------------------------------------- + +TimingEvent::TimingEvent() : +m_name( NULL ), +m_nameLen( 0 ), +m_used( false ), +m_parent( NULL ), +m_firstChild( NULL ), +m_next( NULL ) +{ + m_gpu = (NULL != TimerEx::Instance().GetDevice()) ? new GpuTimer( TimerEx::Instance().GetDevice(), 0, 16 ) : NULL; +} + +TimingEvent::~TimingEvent() +{ + SAFE_DELETE( m_gpu ); + SAFE_DELETE_ARRAY( m_name ); +} + +void TimingEvent::SetName( LPCWSTR name ) +{ + size_t len_req = wcslen( name ) + 1; + if (len_req > m_nameLen) + { + SAFE_DELETE_ARRAY( m_name ); + int len_alloc = 32 + (len_req & 0xFFFFFFE0); // round up to next multiple of 32 so when reused we don't have to realloc too often + m_name = new WCHAR[len_alloc]; + m_nameLen = len_alloc; + } + wcscpy_s( m_name, m_nameLen, name ); +} + +LPCWSTR TimingEvent::GetName() +{ + return m_name; +} + +void TimingEvent::Start() +{ + m_used = true; + if (NULL != m_gpu) { m_gpu->Start(); } + m_cpu.Start(); +} + +void TimingEvent::Stop() +{ + m_cpu.Stop(); + if (NULL != m_gpu) { m_gpu->Stop(); } + m_used = true; +} + +double TimingEvent::GetTime( TimerType type, bool stall ) +{ + switch (type) + { + case ttCpu: + return m_cpu.GetTime(); + case ttGpu: + if (NULL != m_gpu) + { + if (stall) + { + m_gpu->WaitIdle(); + } + return m_gpu->GetTime(); + } + // else fallthrough + default: + return 0.0f; + } +} + +double TimingEvent::GetAvgTime( TimerType type, bool stall ) +{ + switch (type) + { + case ttCpu: + return m_cpu.GetSumTime() / m_cpu.GetTimeNumFrames(); + case ttGpu: + if (NULL != m_gpu) + { + if (stall) + { + m_gpu->WaitIdle(); + } + return m_gpu->GetSumTime() / m_gpu->GetTimeNumFrames(); + } + // else fallthrough + default: + return 0.0f; + } +} + +TimingEvent* TimingEvent::GetTimer( LPCWSTR timerId ) +{ + size_t len = wcslen( timerId ); + size_t seperator = wcscspn( timerId, L"/|\\" ); + + if (seperator < len) + { + LPWSTR idCopy = new WCHAR[len + 1]; + wcscpy_s( idCopy, len + 1, timerId ); + idCopy[seperator] = 0; + + TimingEvent* te = m_firstChild; + while (te) + { + if (!wcscmp( idCopy, te->m_name )) + { + te = te->GetTimerRec( &idCopy[seperator + 1] ); + delete [] idCopy; + return te; + } + te = te->m_next; + } + + delete [] idCopy; + } + else + { + TimingEvent* te = m_firstChild; + while (te) + { + if (!wcscmp( timerId, te->m_name )) + { + return te; + } + te = te->m_next; + } + } + return NULL; +} + +TimingEvent* TimingEvent::GetParent() +{ + return m_parent; +} + +TimingEvent* TimingEvent::GetFirstChild() +{ + return m_firstChild; +} + +TimingEvent* TimingEvent::GetNextTimer() +{ + return m_next; +} + +// when this function is called we know we're working on a copy of the name, so we can "destruct" it +TimingEvent* TimingEvent::GetTimerRec( LPWSTR timerId ) +{ + size_t len = wcslen( timerId ); + size_t seperator = wcscspn( timerId, L"/|\\" ); + if (seperator < len) + { + timerId[seperator] = 0; + } + + TimingEvent* te = m_firstChild; + while (te) + { + if (!wcscmp( timerId, te->m_name )) + { + if (seperator < len) + { + te = te->GetTimerRec( &timerId[seperator + 1] ); + } + + return te; + } + te = te->m_next; + } + + return NULL; +} + +TimingEvent* TimingEvent::FindLastChildUsed() +{ + TimingEvent* ret = NULL; + TimingEvent* te = m_firstChild; + while (te) + { + if (te->m_used) + { + ret = te; + } + te = te->m_next; + } + return ret; +} +//----------------------------------------------------------------------------- + +TimerEx::TimerEx() : +m_pDev( NULL ), +m_Current( NULL ), +m_Unused( NULL ) +{ +}; + +TimerEx::~TimerEx() +{ + _ASSERT( "Stop() not called for every Start(...)" && (m_Current == NULL) ); + + Destroy(); +} + +void TimerEx::DeleteTimerTree( TimingEvent* te ) +{ + // first delete all children + while (NULL != te) + { + DeleteTimerTree( te->m_firstChild ); + + TimingEvent* tmp = te; + te = te->m_next; + delete tmp; + } +} + +void TimerEx::Init( ID3D11Device* pDev ) +{ + m_pDev = pDev; +} + +void TimerEx::Destroy() +{ + // delete all unused + TimingEvent* te = m_Unused; + while (NULL != te) + { + TimingEvent* tmp = te; + te = te->m_next; + delete tmp; + } + m_Unused = NULL; + + // delete all used + DeleteTimerTree( m_Root ); + m_Root = NULL; + + m_pDev = NULL; +} + +void TimerEx::Reset( TimingEvent* te, bool bResetSum ) +{ + TimingEvent* prev = NULL; + while (NULL != te) + { + // recursion + Reset( te->m_firstChild, bResetSum ); + + // reset the timer event + te->m_cpu.Reset( bResetSum ); + if (NULL != te->m_gpu) { te->m_gpu->Reset( bResetSum ); } + + if (te->m_used || !bResetSum) + { + //if it was used this frame: just reset + te->m_used = false; + prev = te; + te = te->m_next; + } + else + { + if (bResetSum && !te->m_used) + { + te->m_used = false; + // if it was not used this frame + //move to unused timer list + TimingEvent* tmp = te; + te = te->m_next; + + if (NULL == prev) + { + if (NULL == tmp->m_parent) + { + m_Root = tmp->m_next; + } + else + { + tmp->m_parent->m_firstChild = tmp->m_next; + } + } + else + { + prev->m_next = tmp->m_next; + } + + tmp->m_parent = NULL; + tmp->m_next = m_Unused; + m_Unused = tmp; + } + } + } +} + +void TimerEx::Reset( bool bResetSum ) +{ + _ASSERT( "init not called or called with NULL" && (m_pDev != NULL) ); + _ASSERT( "Stop() not called for every Start(...)" && (m_Current == NULL) ); + + if (NULL != m_Root) + { + Reset( m_Root, bResetSum ); + } +} + +void TimerEx::Start( LPCWSTR timerId ) +{ + _ASSERT( "init not called or called with NULL" && (m_pDev != NULL) ); + + TimingEvent* te = (NULL == m_Current) ? GetTimer( timerId ) : m_Current->GetTimer( timerId ); + if (NULL == te) + { + // create new timer event + if (NULL == m_Unused) + { + te = new TimingEvent(); + } + else + { + te = m_Unused; + m_Unused = te->m_next; + te->m_next = NULL; + } + + te->SetName( timerId ); + te->m_parent = m_Current; + + // now look where to insert it + TimingEvent* lu = NULL; + if (NULL == m_Current) + { + TimingEvent* tmp = m_Root; + while (tmp) + { + if (tmp->m_used) + { + lu = tmp; + } + tmp = tmp->m_next; + } + } + else + { + lu = m_Current->FindLastChildUsed(); + } + + if (NULL != lu) + { + te->m_next = lu->m_next; + lu->m_next = te; + } + else + { + if (NULL == m_Current) + { + te->m_next = m_Root; + m_Root = te; + } + else + { + te->m_next = m_Current->m_firstChild; + m_Current->m_firstChild = te; + } + + } + } + + m_Current = te; + m_Current->Start(); +} + +void TimerEx::Stop() +{ + _ASSERT( "init not called or called with NULL" && (m_pDev != NULL) ); + _ASSERT( "Start(...) not called before Stop()" && (m_Current != NULL) ); + + m_Current->Stop(); + m_Current = m_Current->m_parent; +} + +double TimerEx::GetTime( TimerType type, LPCWSTR timerId, bool stall ) +{ + _ASSERT( "init not called or called with NULL" && (m_pDev != NULL) ); + + TimingEvent* te = NULL; + + if (NULL != m_Current) + { + te = m_Current->GetTimer( timerId ); + } + + if (NULL == te) + { + te = GetTimer( timerId ); + } + + return (NULL != te) ? te->GetTime( type, stall ) : 0.0; +} + +double TimerEx::GetAvgTime( TimerType type, LPCWSTR timerId, bool stall ) +{ + _ASSERT( "init not called or called with NULL" && (m_pDev != NULL) ); + + TimingEvent* te = NULL; + + if (NULL != m_Current) + { + te = m_Current->GetTimer( timerId ); + } + + if (NULL == te) + { + te = GetTimer( timerId ); + } + + return (NULL != te) ? te->GetAvgTime( type, stall ) : 0.0; +} + + +TimingEvent* TimerEx::GetTimer( LPCWSTR timerId ) +{ + if (NULL == timerId) + { + return m_Root; + } + + _ASSERT( "init not called" && (m_pDev != NULL) ); + + size_t len = wcslen( timerId ); + size_t seperator = wcscspn( timerId, L"/|\\" ); + if (seperator < len) + { + LPWSTR idCopy = new WCHAR[len + 1]; + wcscpy_s( idCopy, len + 1, timerId ); + idCopy[seperator] = 0; + TimingEvent* te = m_Root; + while (te) + { + if (!wcscmp( idCopy, te->m_name )) + { + te = te->GetTimerRec( &idCopy[seperator + 1] ); + delete [] idCopy; + return te; + } + te = te->m_next; + } + delete [] idCopy; + } + else + { + TimingEvent* te = m_Root; + while (te) + { + if (!wcscmp( timerId, te->m_name )) + { + return te; + } + te = te->m_next; + } + } + return NULL; +} diff --git a/src/DX11/framework/amd_sdk/src/Timer.h b/src/DX11/framework/amd_sdk/src/Timer.h new file mode 100644 index 0000000..2c4ace1 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/Timer.h @@ -0,0 +1,695 @@ +// +// Copyright (c) 2017 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. +// + +/*************************************************************************************** +* Purpose of Timer.cpp/Timer.h +* +* These source files provide high accuracy timer functionality to easily add profiling to +* your code. Special care was taken to ensure non-blocking behaviour of the GPU-timer and +* to make it easy to instrument your applications for both accurate CPU- and GPU- timing +* information. +* +* One side effect is that GPU timing information will only be available several frames +* later to avoid stalling the CPU waiting for GPU counter data to return. +* When profiling events that don't happen regularly (i.e. every frame when activated) you +* should not use the TimerEx class. Examples for this include texture baking, computation +* of shadow or reflection maps that get updated at low frequency. (See usage examples for details) +* +* The TimerEx class and macros have been written to enable instrumentation in your code +* similar to what is done with PIX performance counters, and to provide timing information in +* real-time within the program. +* The macros already include DXUT_BeginPerEvent/DXUT_EndPerfEvent, so if some code is already +* instrumented for DXUT adding this timer should only be search and replace operation. (See +* description and examples for more details) +* +* The additional features of TimerEx cost a bit of extra performance when compared to the basic +* Timer class. If you are using TimerEx or its macros you may want to disable it in release builds. +* +* +* Components of this code: +* ======================== +* +* Macros +* ------ +* +* TIMER_Init( device ) +* This has to be called once at initialization time to give the ID3D11Device* to the timer. +* If NULL is passed to the timer GPU timing will not be available. +* +* TIMER_Destroy( ) +* This has to be called when the ID3D11Device* gets destroyed to uninitialize the timer. +* +* TIMER_Reset( ) +* This has to be called once at the start of each frame to reset the timers +* +* TIMER_Begin( col, name ) +* This starts a new Timer (CPU and GPU if available, see TIMER_Init). +* For each TIMER_Begin a corresponding TIMER_End has to be called. +* Note that for the GPU timer to work properly the name used for a code block should be the +* same every frame. Several timers may have the same name, provided they have different parents +* (similar to a file system). If a timer with the same name is started in the same context the +* existing timer with that name will be restarted. See examples for details. +* +* TIMER_End( ) +* This ends a timer which was previously started with TIMER_Begin. +* +* TIMER_ProfileCodeBlock( col, name ) +* Convenience macro. Add this inside a code block to add profiling to it. See examples for details. +* +* TIMER_GetTime( Cpu_Gpu, name ) +* Retrieve the timing value of a timer in microseconds. +* The parameter Cpu_Gpu can either be Cpu or Gpu depending what time you want to retrieve. +* Name can be the name of a "local" timer or a name including a path to the timer in the tree +* structure. Valid path seperators are \, / or | +* See Examples for more details. +* +* TIMER_WaitForGpuAndGetTime( name ) +* This macro stalls the CPU until the result of a GPU timer is available. +* Since it forces the CPU to idle, this macro should not be used in time critical parts of your app. +* +* +* Classes +* ------- +* +* TimerExHelper +* Create an Instance of this class to automatically add profiling to a code block. +* This class starts a timer in the constructor and ends the timer in its destructor. +* +* TimerEx +* Singleton that manages the timer tree generated by TIMER_Begin and TIMER_End. +* Functions: +* - Instance : retrieve the instance of TimerEx +* - GetDevice : get the device passed to TimerEx at Init +* - Init : initialize TimerEx, pass ID3D11Device* if GPU profiling should be used +* - Destroy : uninitialize TimerEx and release resources so the ID3D11Device* can be destroyed +* - Reset : notify all timers that a new frame starts, remove unused timer events +* - Start : start a timer +* - Stop : stop a timer +* - GetTime : retrieve the timing result of a timer +* - GetTimer : retrieve a TimerEvent*. This ptr should not be kept past a reset. +* it can be used to manually iterate through the timer tree +* +* TimerEvent +* Manages one CpuTimer and one GpuTimer (if ID3D11Device is specified) plus the name of +* the timed event and the pointers of the tree structure. +* Functions: +* - GetTime : retrieve the timing result for either gpu or cpu. +* Specify if the cpu should wait to the latest gpu time to be available +* - GetTimer : retrieve a nested TimerEvent* by name or relative path +* - GetParent : retrieve the parental TimerEvent* +* - GetFirstChild : retrieve the first child-TimerEvent* +* - GetNextTimer : retrieve the next TimerEvent* with the same parent +* +* +* Timer +* Lightweight interface to instrument your code without the overhead introduced by the TimerEx class. +* The times measured by Timer will add up when starting/stopping the timer multiple times without +* resetting the timer. +* Create an instance of either of the derived classes for each event you want to profile: +* - CpuTimer : measures the time taken on the CPU to execute from Start to Stop +* - GpuTimer : measures the time taken on the GPU to execute from Start to Stop +* When using GpuTimer please note that the timing results may only be available +* several frames later, so numTimeStamps should specify enough space for at least +* numTimesTimerStartedPerFrame*maxNumFramesLag timing values. Please also keep in mind +* that Crossfire configurations are likely to increase the number of frames until a result +* is ready. +* If numTimeStamps is chosen too small this will result in the CPU stalling. +* - GpuCpuTimer : Measure the time the GPU takes to execute the commands beeing issued between Start and Stop +* by measuring the time on the CPU. +* This will stall the CPU twice, once at Start and once at Stop. +* +* +* Usage examples: +* =============== + +* Macros +* ------ +* +* *************************** +* ** EXAMPLE 1: Simple use ** +* *************************** +* +* // TIMER_Init( device ) was previously called in device creation function +* // TIMER_Destroy( ) was added to the OnD3D11DestroyDevice function +* +* For every frame: +* +* // Start of frame: reset the timer +* TIMER_Reset( ); +* +* TIMER_Begin( 0, L"Z prepass" ); +* +* TIMER_Begin( 0, L"solid" ); +* // Render solid objects in Z pre-pass +* TIMER_End( ); // "solid" + +* TIMER_Begin( 0, L"transparent" ); +* // Render transparent (alpha-tested) objects in Z pre-pass +* TIMER_End( ); // "transparent" +* +* TIMER_End( ); // "Z prepass" +* +* // Other render commands go here... +* +* // End of frame: retrieval of timing results: +* double ZPrepass_Solid_Gpu = TIMER_GetTime( Gpu, L"Z prepass|solid" ); +* double ZPrepass_Transparent_Gpu = TIMER_GetTime( Gpu, L"Z prepass|transparent" ); +* double ZPrepass_Total_Gpu = TIMER_GetTime( Gpu, L"Z prepass" ); +* +* +* ***************************** +* ** EXAMPLE 2: Advanced use ** +* ***************************** +* +* // TIMER_Init( device ) was previously called in device creation function +* // TIMER_Destroy( ) was added to the OnD3D11DestroyDevice function +* +* For every frame: +* +* // Start of frame: reset the timer +* TIMER_Reset( ); +* +* TIMER_Begin( 0, L"Render" ); +* +* TIMER_Begin( 0, L"Z prepass" ); +* +* { +* // This will automatically profile all GPU commands in the current code block +* TIMER_ProfileCodeBlock( col, L"solid" ); +* // Render solid objects in Z pre-pass +* } +* +* { +* TIMER_ProfileCodeBlock( col, L"transparent" ); +* // Render transparent trees +* } +* +* { +* TIMER_ProfileCodeBlock( col, L"transparent" ); +* // Render transparent bushes +* } +* +* TIMER_End( ); // "Z prepass" +* +* TIMER_End( ); // "Render" +* +* // Other render commands go here... +* +* // End of frame: retrieval of timing results: +* // ZPrepass_Total_Transparent_Gpu will return the total GPU time spent in "transparent" (trees and bushes GPU rendering time) +* double ZPrepass_Total_Transparent_Gpu = TIMER_GetTime( Gpu, L"Render|Z prepass|transparent" ); +* // ZPrepass_Total_Transparent_Cpu will return the total CPU time spent in "transparent" (trees and bushes CPU time) +* double ZPrepass_Total_Transparent_Cpu = TIMER_GetTime( Cpu, L"Render|Z prepass|transparent" ); +* double Render_Total_Gpu = TIMER_GetTime( Gpu, L"Render" ); +* +* +* ******************** +* ** OTHER EXAMPLES ** +* ******************** +* +* // TIMER_Init( device ) was previously called in device creation function +* // TIMER_Destroy( ) was added to the OnD3D11DestroyDevice function +* +* For every frame: +* +* // Start of frame: reset the timer +* TIMER_Reset( ); +* +* TIMER_Begin( 0, L"Render" ); +* +* TIMER_Begin( 0, L"Z prepass" ); +* +* TIMER_Begin( 0, L"solid" ); +* +* // Render solid objects in Z pre-pass +* +* // !! transparent_cpu will return 0 because "solid" has not ended yet !! +* double transparent_cpu = TIMER_GetTime( Cpu, L"Render|Z prepass|solid" ); +* +* // transparent_gpu will return the last Gpu timing available +* double transparent_gpu = TIMER_GetTime( Gpu, L"Render|Z prepass|solid" ); +* +* TIMER_End( ); // "solid" +* +* TIMER_End( ); // "Z prepass" +* +* TIMER_Begin( col, L"main" ); +* { +* TIMER_ProfileCodeBlock( col, L"solid" ); +* } +* TIMER_End( ); // "main" +* +* TIMER_End( ); // "Render" +* +* // Other render commands go here... +* +* // a little stroll through the timer tree +* TimerEvent* renderTimer = TIMER_GetTimer( L"Render" ); +* TimerEvent* zprepassTimer = renderTimer->GetFirstChild(); +* TimerEvent* mainTimer = zprepassTimer->GetNextTimer(); +* TimerEvent* solidTimer = mainTimer->GetFirstChild(); +* +* // Will retrieve the time the CPU spends during "Render|main|solid" +* double solid_cpu = solidTimer->GetTime( ttCpu ); +* +* // Will return NULL since there is no other timer at the same level as "Render|main" +* TimerEvent* willreturnnull = mainTimer->GetNextTimer(); +* +* +* **************************** +* ** IMPLEMENTATION DETAILS ** +* **************************** +* +* TimerExHelper +* ------------- +* +* // start of frame, reset timers +* TIMER_Reset( ); +* { // <-timer 0 starts here +* +* // in debug mode this would create an assert since a timer is already running +* // in release this would reset the timers but the already running timer would keep it's start time +* // TIMER_Reset( ); +* +* //some code +* TimerExHelper timer0( 0, L"timer0" ); +* // some more code +* +* for(int i = 0; i<10; ++i) +* { // <-timer 1 starts here +* TimerExHelper timer1( 0, L"timer1" ); +* +* //even more code +* +* // start a timer with a seperate name for each iteration of the loop +* // these will all be childnodes to "timer1" +* LPWSTR timerName[32]; +* swprintf( timerName,32, L"timer(i=%d)", i); +* TimerExHelper timer_i( 0, timerName ); +* }// <-timer 1 ends here +* +* // retrieve the runtime of the loop +* double timer1 = TIMER_GetTime( Cpu, L"timer1" ); +* } // <-timer 0 ends here +* +* // retrieve all timers from the immer loop +* TimerEvent* timer = TIMER_GetTimer( L"timer0|timer1" )->GetFirstChild(); +* double timer_i[10]; +* int i = 0; +* while( NULL != timer ) +* { +* timer_i[i] = timer->GetTime( ttCpu ); +* timer->GetNextTimer(); +* ++i; +* } +* +* +* TimerEx +* ------- +* Using TimerEx is just like using the macros, except the macros also include DXUT_PerfEvent-marker +* Macro: corresponding TimerEx function call: +* TIMER_Init( device ); TimerEx::Instance( ).Init( device ); +* TIMER_Destroy( ) TimerEx::Instance( ).Destroy( ); +* TIMER_Reset( ); TimerEx::Instance( ).Reset( ); +* TIMER_Begin( col, name ); TimerEx::Instance( ).Start( name ); +* TIMER_End( ); TimerEx::Instance( ).Stop( ); +* TIMER_GetTime( Gpu, name ); TimerEx::Instance( ).GetTime( ttGpu, name [optional param bool stall CPU?] ); +* TIMER_GetTime( Cpu, name ); TimerEx::Instance( ).GetTime( ttCpu, name [optional param is ignored] ); +* TIMER_GetTimer( name ); TimerEx::Instance( ).GetTimer( name ); +* +* Timer +* ----- +* The Timer class is a lightweight timing interface. It's designed to interfere with the program timing as little +* as possible. TimerEx on the other hand is written with performance in mind, but will consume some time and memory +* when used excessively and thus should not be used inside heavily used parts of time critical code. +* Especially when using GpuTimer some care must be taken, since using it is not as straight forward as the CpuTimer. +* This is due to its non blocking behaviour and the difference of up to several frames between commands beeing issued +* to the GPU und the commands having been executed and the timing result beeing available. +* +* { +* CpuTimer cpuTimer; +* Timer* gpuTimer1 = new GpuTimer( pDev ); +* GpuTimer gpuTimer2( pDev ); +* GpuTimer gpuTimer3( pDev); +* GpuTimer gpuTimer4( pDev, 0, 1 ); // <- we only need space for one event because we'll retrieve this data stalling the CPU +* // choosing the numTimeStamps too low will result in the CPU stalling +* +* gpuTimer1->Start(); +* gpuTimer3.Start(); +* cpuTimer.Start(); +* // so some stuff here +* cpuTimer.Stop(); +* gpuTimer3.Stop(); +* gpuTimer1->Stop(); +* +* // get timing results +* double timeCpu1 = cpuTimer.GetTime(); // get the CPU time required to do "some stuff" +* double timeGpu1 = gpuTimer1->GetTime(); // get the GPU time required to do "some stuff". This will be 0.0 for the first few frames +* +* cpuTimer.Reset(); // reset CPU timer +* gpuTimer3.Reset(); // try to reset GPU timer. WARNING: THIS WILL NOT WORK. We'll do it anyway and explain what happens later. +* +* gpuTimer3.Start(); +* gpuTimer2.Start(); +* cpuTimer.Start(); +* // so more stuff here +* cpuTimer.Stop(); +* gpuTimer3.Stop(); +* gpuTimer2.Stop(); +* +* // get timing results +* double timeCpu2 = cpuTimer.GetTime(); // get the CPU time required to do "more stuff" +* double timeGpu2 = gpuTimer2.GetTime(); // get the GPU time required to do "more stuff". This will be 0.0 for the first few frames +* double timeGpu3 = gpuTimer3.GetTime(); // this will get inconsistant timing info +* // the reason for this is that the timer assumes Reset() is only called once a frame and +* // a GpuTimer is only used to profile a specific part of the code taking roughly the same +* // time each frame. GetTime will return a timing value several frames old, where, in this +* // context a frame is what happened between two calls of Reset(). +* // So, if the timer is reset several times a frame this will result in GetTime randomly +* // reporting the time beeing used by "some stuff" and "more stuff" +* +* gpuTimer4.Start(); +* // so other stuff here +* gpuTimer4.Stop(); +* +* WaitIdle(); // This will work just fine, but it stalls the CPU, +* double timeGpu4 = gpuTimer4->GetTime(); // so you wouldn't want to use it in heavily used +* gpuTimer4.Reset(); // or time critical sections of your code + +* gpuTimer4.Start(); +* // so weird stuff here +* cpuTimer4.Stop(); +* WaitIdle(); +* double timeGpu4 = gpuTimer4->GetTime(); +* +* delete gpuTimer1; +* } +* +***********************************************************/ +#ifndef AMD_SDK_TIMER_H +#define AMD_SDK_TIMER_H + +//namespace AMD +//{ + +#define USE_RDTSC 0 +#define WATCH_BAD_TS_VAL 0 +#define CHECK_DISJOINT 0 + +#define ENABLE_AMD_TIMER 1 + +enum TimerType +{ + ttCpu = 1, + ttGpu = 2, + ttGpuCpu = 3, +}; + +//----------------------------------------------------------------------------- + +class Timer +{ +public: + Timer(); + virtual ~Timer(); + + virtual void Reset( bool bResetSum ) = 0; + virtual void Start() = 0; + virtual void Stop() = 0; + + double GetTime(); + double GetSumTime(); + double GetTimeNumFrames(); + +protected: + double m_LastTime; + double m_SumTime; + unsigned int m_NumFrames; + + virtual void FinishCollection() {} +}; + +//----------------------------------------------------------------------------- + +class CpuTimer : public Timer +{ +public: + CpuTimer(); + virtual ~CpuTimer(); + + virtual void Reset( bool bResetSum ); + virtual void Start(); + virtual void Stop(); + + void Delay(double sec); + +private: + LARGE_INTEGER m_startTime; + double m_freq; + +#if USE_RDTSC + double m_freqRdtsc; +#endif +}; + +//----------------------------------------------------------------------------- + +class GpuTimer : public Timer +{ +private: + struct TsRecord + { + union TsRecordState + { + struct TsRecordData + { + unsigned frameID :30; + unsigned startIssued : 1; + unsigned stopIssued : 1; + } data; + UINT stateWord; + } state; + ID3D11Query* pStart; + ID3D11Query* pStop; + ID3D11Query* pDisjointTS; + }; + +public: + GpuTimer(ID3D11Device* pDev, UINT64 freq = 27000000, UINT numTimeStamps = 8); + virtual ~GpuTimer(); + + virtual void Reset( bool bResetSum ); + virtual void Start(); + virtual void Stop(); + + void WaitIdle(); + +private: + + ID3D11DeviceContext* m_pDevCtx; + + UINT m_numTimeStamps; + TsRecord* m_ts; + + UINT m_curIssueTs; + UINT m_nextRetrTs; + UINT m_FrameID; + + struct CurTimeFrameBits + { + UINT id :30; + UINT invalid : 1; + } m_CurTimeFrame; + double m_CurTime; + + + virtual void FinishCollection(); + bool CollectData(UINT idx, BOOL stall = FALSE); +}; + +//----------------------------------------------------------------------------- + +class GpuCpuTimer : public CpuTimer +{ +public: + GpuCpuTimer(ID3D11Device* pDev); + virtual ~GpuCpuTimer(); + + virtual void Start(); + virtual void Stop(); + +private: + ID3D11DeviceContext* m_pDevCtx; + ID3D11Query* m_pEvent; + + void WaitIdle(); +}; + + +// TimingEvent: one timing event managed by TimerEx +// TimerEx: extended timer singleton to provide instrumentalization similar to PIX +// TimerExHelper: convenience class to provide easy profiling of function calls +// some MAKROS: to ease instrumenting your code +class TimingEvent +{ +public: + double GetTime ( TimerType type, bool stall = false ); + double GetAvgTime ( TimerType type, bool stall = false ); + + TimingEvent* GetTimer ( LPCWSTR timerId ); // get a child-timer by name + TimingEvent* GetParent ( ); // walk through timer tree + TimingEvent* GetFirstChild ( ); // walk through timer tree + TimingEvent* GetNextTimer ( ); // walk through timer tree + + LPCWSTR GetName ( ); + +private: + // functions only to be used by TimerEx + friend class TimerEx; + + TimingEvent( ); + virtual ~TimingEvent(); + + TimingEvent* GetTimerRec ( LPWSTR timerId ); + void Reset ( ); + void Start ( ); + void Stop ( ); + + TimingEvent* FindLastChildUsed ( ); + void SetName ( LPCWSTR timerId ); + +private: + LPWSTR m_name; + unsigned int m_nameLen; + + CpuTimer m_cpu; + GpuTimer* m_gpu; + bool m_used; + + TimingEvent* m_parent; + TimingEvent* m_firstChild; + TimingEvent* m_next; +}; + +class TimerEx +{ +public: + static TimerEx& Instance() + { + static TimerEx inst; + return inst; + } + + ID3D11Device* GetDevice() + { + return m_pDev; + } + + void Init ( ID3D11Device* pDev ); // to be called before any timing is done + void Destroy ( ); // to be called when the ID3D11Device* gets destroyed + void Reset ( bool bResetSum ); // to be called one a frame, preferably on frame switch (flip) + void Start ( LPCWSTR timerId ); // looks for the child in the tree structure, if not found adds another child + void Stop ( ); + double GetTime ( TimerType type, LPCWSTR timerId, bool stall = false ); + double GetAvgTime ( TimerType type, LPCWSTR timerId, bool stall = false ); + TimingEvent* GetTimer ( LPCWSTR timerId = NULL ); // returns the first child of root if NULL, else searches childnodes for timer with that name + +private: + TimerEx ( ); + virtual ~TimerEx ( ); + + void Reset ( TimingEvent* te, bool bResetSum ); + void DeleteTimerTree( TimingEvent* te ); + +protected: + ID3D11Device* m_pDev; + TimingEvent* m_Root; // timer tree + TimingEvent* m_Current; // current position in timer tree + TimingEvent* m_Unused; // unused timers (for faster reuse) +}; + +#if ENABLE_AMD_TIMER +#define TIMER_Init( device ) \ + TimerEx::Instance( ).Init( device ); + +#define TIMER_Destroy( ) \ + TimerEx::Instance( ).Destroy(); + +#define TIMER_Reset( ) \ + TimerEx::Instance( ).Reset( false ); + +#define TIMER_FullReset( ) \ + TimerEx::Instance( ).Reset( true ); + +#define TIMER_GetTime( Cpu_Gpu, name ) \ + TimerEx::Instance( ).GetTime( tt##Cpu_Gpu, name ) + +#define TIMER_WaitForGpuAndGetTime( name ) \ + TimerEx::Instance( ).GetTime( ttGpu, name, true ) + +#define TIMER_GetAvgTime( Cpu_Gpu, name ) \ + TimerEx::Instance( ).GetAvgTime( tt##Cpu_Gpu, name ) + +// makros, analogue to PIX +#define TIMER_Begin( col, name ) \ + TimerEx::Instance( ).Start( name ); +// DXUT_BeginPerfEvent( col, name ); +// D3DPERF_BeginEvent( col, name ); + +#define TIMER_End( ) \ + TimerEx::Instance( ).Stop( ); +// DXUT_EndPerfEvent( ); +// D3DPERF_EndEvent( ); +#else +#define TIMER_Init( device ) +#define TIMER_Destroy( ) +#define TIMER_Reset( ) +#define TIMER_GetTime( Cpu_Gpu, name ) 0 +#define TIMER_WaitForGpuAndGetTime( name ) 0 +#define TIMER_GetAvgTime( Cpu_Gpu, name ) 0 +#define TIMER_Begin( col, name ) +#define TIMER_End( ) +#endif + +class TimerExHelper +{ +public: + TimerExHelper( unsigned int col, LPCWSTR name ) + { + (void)&col; + TIMER_Begin( col, name ); + } + virtual ~TimerExHelper( ) + { + TIMER_End( ); + } +}; + +#if ENABLE_AMD_TIMER +#define TIMER_ProfileCodeBlock( col, name ) \ + TimerExHelper __codeblock_timer( col, name ); +#else +#define TIMER_ProfileCodeBlock( col, name ) +#endif +//} // namespace AMD + +#endif // AMD_SDK_TIMER_H diff --git a/src/DX11/framework/amd_sdk/src/crc.cpp b/src/DX11/framework/amd_sdk/src/crc.cpp new file mode 100644 index 0000000..7de9c4e --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/crc.cpp @@ -0,0 +1,233 @@ +/********************************************************************** + * + * Filename: crc.c + * + * Description: Slow and fast implementations of the CRC standards. + * + * Notes: The parameters for each supported CRC standard are + * defined in the header file crc.h. The implementations + * here should stand up to further additions to that list. + * + * + * Copyright (c) 2000 by Michael Barr. This software is placed into + * the public domain and may be used for any purpose. However, this + * notice must not be changed or removed and no warranty is either + * expressed or implied by its publication or distribution. + **********************************************************************/ + +#include "crc.h" + + +/* + * Derive parameters from the standard-specific parameters in crc.h. + */ +#define WIDTH (8 * sizeof(crc)) +#define TOPBIT (1 << (WIDTH - 1)) + +#if (REFLECT_DATA == TRUE) +#undef REFLECT_DATA +#define REFLECT_DATA(X) ((unsigned char) reflect((X), 8)) +#else +#undef REFLECT_DATA +#define REFLECT_DATA(X) (X) +#endif + +#if (REFLECT_REMAINDER == TRUE) +#undef REFLECT_REMAINDER +#define REFLECT_REMAINDER(X) ((crc) reflect((X), WIDTH)) +#else +#undef REFLECT_REMAINDER +#define REFLECT_REMAINDER(X) (X) +#endif + + +/********************************************************************* + * + * Function: reflect() + * + * Description: Reorder the bits of a binary sequence, by reflecting + * them about the middle position. + * + * Notes: No checking is done that nBits <= 32. + * + * Returns: The reflection of the original data. + * + *********************************************************************/ +static unsigned long +reflect(unsigned long data, unsigned char nBits) +{ + unsigned long reflection = 0x00000000; + unsigned char bit; + + /* + * Reflect the data about the center bit. + */ + for (bit = 0; bit < nBits; ++bit) + { + /* + * If the LSB bit is set, set the reflection of it. + */ + if (data & 0x01) + { + reflection |= (1 << ((nBits - 1) - bit)); + } + + data = (data >> 1); + } + + return (reflection); + +} /* reflect() */ + + +/********************************************************************* + * + * Function: crcSlow() + * + * Description: Compute the CRC of a given message. + * + * Notes: + * + * Returns: The CRC of the message. + * + *********************************************************************/ +crc +crcSlow(unsigned char const message[], int nBytes) +{ + crc remainder = INITIAL_REMAINDER; + int byte; + unsigned char bit; + + + /* + * Perform modulo-2 division, a byte at a time. + */ + for (byte = 0; byte < nBytes; ++byte) + { + /* + * Bring the next byte into the remainder. + */ + remainder ^= (REFLECT_DATA(message[byte]) << (WIDTH - 8)); + + /* + * Perform modulo-2 division, a bit at a time. + */ + for (bit = 8; bit > 0; --bit) + { + /* + * Try to divide the current data bit. + */ + if (remainder & TOPBIT) + { + remainder = (remainder << 1) ^ POLYNOMIAL; + } + else + { + remainder = (remainder << 1); + } + } + } + + /* + * The final remainder is the CRC result. + */ + return (REFLECT_REMAINDER(remainder) ^ FINAL_XOR_VALUE); + +} /* crcSlow() */ + + +crc crcTable[256]; + + +/********************************************************************* + * + * Function: crcInit() + * + * Description: Populate the partial CRC lookup table. + * + * Notes: This function must be rerun any time the CRC standard + * is changed. If desired, it can be run "offline" and + * the table results stored in an embedded system's ROM. + * + * Returns: None defined. + * + *********************************************************************/ +void +crcInit(void) +{ + crc remainder; + int dividend; + unsigned char bit; + + + /* + * Compute the remainder of each possible dividend. + */ + for (dividend = 0; dividend < 256; ++dividend) + { + /* + * Start with the dividend followed by zeros. + */ + remainder = dividend << (WIDTH - 8); + + /* + * Perform modulo-2 division, a bit at a time. + */ + for (bit = 8; bit > 0; --bit) + { + /* + * Try to divide the current data bit. + */ + if (remainder & TOPBIT) + { + remainder = (remainder << 1) ^ POLYNOMIAL; + } + else + { + remainder = (remainder << 1); + } + } + + /* + * Store the result into the table. + */ + crcTable[dividend] = remainder; + } + +} /* crcInit() */ + + +/********************************************************************* + * + * Function: crcFast() + * + * Description: Compute the CRC of a given message. + * + * Notes: crcInit() must be called first. + * + * Returns: The CRC of the message. + * + *********************************************************************/ +crc +crcFast(unsigned char const message[], int nBytes) +{ + crc remainder = INITIAL_REMAINDER; + unsigned char data; + int byte; + + + /* + * Divide the message by the polynomial, a byte at a time. + */ + for (byte = 0; byte < nBytes; ++byte) + { + data = REFLECT_DATA(message[byte]) ^ (remainder >> (WIDTH - 8)); + remainder = crcTable[data] ^ (remainder << 8); + } + + /* + * The final remainder is the CRC. + */ + return (REFLECT_REMAINDER(remainder) ^ FINAL_XOR_VALUE); + +} /* crcFast() */ diff --git a/src/DX11/framework/amd_sdk/src/crc.h b/src/DX11/framework/amd_sdk/src/crc.h new file mode 100644 index 0000000..d113113 --- /dev/null +++ b/src/DX11/framework/amd_sdk/src/crc.h @@ -0,0 +1,79 @@ +/********************************************************************** + * + * Filename: crc.h + * + * Description: A header file describing the various CRC standards. + * + * Notes: + * + * + * Copyright (c) 2000 by Michael Barr. This software is placed into + * the public domain and may be used for any purpose. However, this + * notice must not be changed or removed and no warranty is either + * expressed or implied by its publication or distribution. + **********************************************************************/ + +#ifndef _crc_h +#define _crc_h + +#ifndef FALSE +#define FALSE 0 +#endif +#ifndef TRUE +#define TRUE 1 +#endif + +/* + * Select the CRC standard from the list that follows. + */ +#define CRC32 + + +#if defined(CRC_CCITT) + +typedef unsigned short crc; + +#define CRC_NAME "CRC-CCITT" +#define POLYNOMIAL 0x1021 +#define INITIAL_REMAINDER 0xFFFF +#define FINAL_XOR_VALUE 0x0000 +#define REFLECT_DATA FALSE +#define REFLECT_REMAINDER FALSE +#define CHECK_VALUE 0x29B1 + +#elif defined(CRC16) + +typedef unsigned short crc; + +#define CRC_NAME "CRC-16" +#define POLYNOMIAL 0x8005 +#define INITIAL_REMAINDER 0x0000 +#define FINAL_XOR_VALUE 0x0000 +#define REFLECT_DATA TRUE +#define REFLECT_REMAINDER TRUE +#define CHECK_VALUE 0xBB3D + +#elif defined(CRC32) + +typedef unsigned long crc; + +#define CRC_NAME "CRC-32" +#define POLYNOMIAL 0x04C11DB7 +#define INITIAL_REMAINDER 0xFFFFFFFF +#define FINAL_XOR_VALUE 0xFFFFFFFF +#define REFLECT_DATA TRUE +#define REFLECT_REMAINDER TRUE +#define CHECK_VALUE 0xCBF43926 + +#else + +#error "One of CRC_CCITT, CRC16, or CRC32 must be #define'd." + +#endif + +void crcInit(void); +crc crcSlow(unsigned char const message[], int nBytes); +crc crcFast(unsigned char const message[], int nBytes); + + +#endif /* _crc_h */ \ No newline at end of file diff --git a/src/DX11/framework/dxut/.editorconfig b/src/DX11/framework/dxut/.editorconfig new file mode 100644 index 0000000..6a8f10a --- /dev/null +++ b/src/DX11/framework/dxut/.editorconfig @@ -0,0 +1,9 @@ +root = true + +[*.{cpp,h}] +indent_size = 4 +indent_style = space +trim_trailing_whitespace = true +insert_final_newline = true +end_of_line = crlf +charset = latin1 diff --git a/src/DX11/framework/dxut/.gitattributes b/src/DX11/framework/dxut/.gitattributes new file mode 100644 index 0000000..efb4018 --- /dev/null +++ b/src/DX11/framework/dxut/.gitattributes @@ -0,0 +1,19 @@ +# Auto detect text files and perform LF normalization +* text=auto + +# Explicitly declare code/VS files as CRLF +*.cpp eol=crlf +*.h eol=crlf +*.hlsl eol=crlf +*.hlsli eol=crlf +*.fx eol=crlf +*.fxh eol=crlf +*.inc eol=crlf +*.vcxproj eol=crlf +*.filters eol=crlf +*.sln eol=crlf +*.props eol=crlf + +# Explicitly declare resource files as binary +*.pdb binary +*.dds binary diff --git a/src/DX11/framework/dxut/.gitignore b/src/DX11/framework/dxut/.gitignore new file mode 100644 index 0000000..0e255da --- /dev/null +++ b/src/DX11/framework/dxut/.gitignore @@ -0,0 +1,23 @@ +*.psess +*.vsp +*.log +*.err +*.wrn +*.suo +*.sdf +*.user +*.i +*.vspscc +*.opensdf +*.opendb +*.ipch +*.cache +*.tlog +*.lastbuildstate +*.ilk +*.VC.db +.vs +/ipch +Bin +/wiki +/out diff --git a/src/DX11/framework/dxut/CMakeLists.txt b/src/DX11/framework/dxut/CMakeLists.txt new file mode 100644 index 0000000..f88286d --- /dev/null +++ b/src/DX11/framework/dxut/CMakeLists.txt @@ -0,0 +1,174 @@ +# Copyright (c) Microsoft Corporation. +# Licensed under the MIT License. + +cmake_minimum_required (VERSION 3.11) + +set(DXUT_VERSION 11.26) + +project (DXUT + VERSION ${DXUT_VERSION} + DESCRIPTION "DXUT for DirectX 11" + HOMEPAGE_URL "http://go.microsoft.com/fwlink/?LinkId=320437" + LANGUAGES CXX) + +option(ENABLE_CODE_ANALYSIS "Use Static Code Analysis on build" OFF) + +set(CMAKE_CXX_STANDARD 14) +set(CMAKE_CXX_STANDARD_REQUIRED ON) +set(CMAKE_CXX_EXTENSIONS OFF) + +set(CMAKE_ARCHIVE_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/bin/CMake") +set(CMAKE_LIBRARY_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/bin/CMake") +set(CMAKE_RUNTIME_OUTPUT_DIRECTORY "${CMAKE_BINARY_DIR}/bin/CMake") + +#--- Core Library +set(CORE_LIBRARY_HEADERS + Core/DDSTextureLoader.h + Core/dxerr.h + Core/DXUT.h + Core/DXUTDevice11.h + Core/DXUTmisc.h + Core/ScreenGrab.h + Core/WICTextureLoader.h +) + +set(CORE_LIBRARY_SOURCES + Core/DDSTextureLoader.cpp + Core/dxerr.cpp + Core/DXUT.cpp + Core/DXUTDevice11.cpp + Core/DXUTmisc.cpp + Core/ScreenGrab.cpp + Core/WICTextureLoader.cpp +) + +add_library(${PROJECT_NAME} STATIC ${CORE_LIBRARY_SOURCES} ${CORE_LIBRARY_HEADERS}) + +#--- Optional Library +set(OPT_LIBRARY_HEADERS + Optional/DXUTcamera.h + Optional/DXUTgui.h + Optional/DXUTguiIME.h + Optional/DXUTLockFreePipe.h + Optional/DXUTres.h + Optional/DXUTsettingsdlg.h + Optional/ImeUi.h + Optional/SDKmesh.h + Optional/SDKmisc.h +) + +set(OPT_LIBRARY_SOURCES + Optional/DXUTcamera.cpp + Optional/DXUTgui.cpp + Optional/DXUTguiIME.cpp + Optional/DXUTres.cpp + Optional/DXUTsettingsdlg.cpp + Optional/ImeUi.cpp + Optional/SDKmesh.cpp + Optional/SDKmisc.cpp +) + +add_library(${PROJECT_NAME}Opt STATIC ${OPT_LIBRARY_SOURCES} ${OPT_CORE_LIBRARY_HEADERS}) + +if (${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.16") + target_precompile_headers(${PROJECT_NAME} PRIVATE Core/DXUT.h) + target_precompile_headers(${PROJECT_NAME}Opt PRIVATE Core/DXUT.h) +endif() + +source_group(DXUT REGULAR_EXPRESSION Core/*.*) +source_group(DXUTOpt REGULAR_EXPRESSION Optional/*.*) + +target_include_directories(${PROJECT_NAME} PUBLIC + $ + $) + +target_include_directories(${PROJECT_NAME}Opt PUBLIC + $ + $ + PRIVATE Core/) + +if(MSVC) + # Use max Warning Level + string(REPLACE "/W3 " "/W4 " CMAKE_CXX_FLAGS ${CMAKE_CXX_FLAGS}) + string(REPLACE "/W3 " "/W4 " CMAKE_CXX_FLAGS_DEBUG ${CMAKE_CXX_FLAGS_DEBUG}) + string(REPLACE "/W3 " "/W4 " CMAKE_CXX_FLAGS_RELEASE ${CMAKE_CXX_FLAGS_RELEASE}) + + # Library needs /EHsc (Enable C++ exceptions) +endif() + +#--- Package +include(CMakePackageConfigHelpers) + +string(TOLOWER ${PROJECT_NAME} PACKAGE_NAME) + +write_basic_package_version_file( + ${PROJECT_BINARY_DIR}/cmake/${PACKAGE_NAME}-config-version.cmake + VERSION ${DXUT_VERSION} + COMPATIBILITY AnyNewerVersion) + +install(TARGETS ${PROJECT_NAME} + EXPORT ${PROJECT_NAME}-targets + ARCHIVE DESTINATION lib + LIBRARY DESTINATION lib + RUNTIME DESTINATION bin) + +install(TARGETS ${PROJECT_NAME}Opt + EXPORT ${PROJECT_NAME}Opt-targets + ARCHIVE DESTINATION lib + LIBRARY DESTINATION lib + RUNTIME DESTINATION bin) + +configure_package_config_file(${CMAKE_CURRENT_SOURCE_DIR}/${PROJECT_NAME}-config.cmake.in + ${PROJECT_BINARY_DIR}/cmake/${PACKAGE_NAME}-config.cmake + INSTALL_DESTINATION cmake/}) + +install(EXPORT ${PROJECT_NAME}-targets + FILE ${PROJECT_NAME}-targets.cmake + NAMESPACE Microsoft:: + DESTINATION cmake/) + +install(EXPORT ${PROJECT_NAME}Opt-targets + FILE ${PROJECT_NAME}Opt-targets.cmake + NAMESPACE Microsoft:: + DESTINATION cmake/) + +install(FILES ${CORE_LIBRARY_HEADERS} ${OPT_LIBRARY_HEADERS} + DESTINATION include/${PROJECT_NAME}) + +install(FILES + ${PROJECT_BINARY_DIR}/cmake/${PACKAGE_NAME}-config.cmake + ${PROJECT_BINARY_DIR}/cmake/${PACKAGE_NAME}-config-version.cmake + DESTINATION cmake/) + +if(MSVC) + target_compile_options(${PROJECT_NAME} PRIVATE /fp:fast) + target_compile_options(${PROJECT_NAME}Opt PRIVATE /fp:fast) + + if(ENABLE_CODE_ANALYSIS) + target_compile_options(${PROJECT_NAME} PRIVATE /analyze) + target_compile_options(${PROJECT_NAME}Opt PRIVATE /analyze) + endif() + + if (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL 19.26) + target_compile_options(${PROJECT_NAME} PRIVATE /Zc:preprocessor /wd5104 /wd5105) + target_compile_options(${PROJECT_NAME}Opt PRIVATE /Zc:preprocessor /wd5104 /wd5105) + endif() + + if (${CMAKE_SIZEOF_VOID_P} EQUAL "4") + target_compile_options(${PROJECT_NAME} PRIVATE /arch:SSE2) + target_compile_options(${PROJECT_NAME}Opt PRIVATE /arch:SSE2) + endif() +endif() + +if ( CMAKE_CXX_COMPILER_ID MATCHES "MSVC" ) + target_compile_options(${PROJECT_NAME} PRIVATE /permissive- /JMC- /Zc:__cplusplus) + target_compile_options(${PROJECT_NAME}Opt PRIVATE /permissive- /JMC- /Zc:__cplusplus) +endif() + +if(WIN32) + target_compile_definitions(${PROJECT_NAME} PRIVATE _UNICODE UNICODE) + target_compile_definitions(${PROJECT_NAME}Opt PRIVATE _UNICODE UNICODE) + + target_compile_definitions(${PROJECT_NAME} PRIVATE _WIN32_WINNT=0x0601) + target_compile_definitions(${PROJECT_NAME}Opt PRIVATE _WIN32_WINNT=0x0601) +endif() diff --git a/src/DX11/framework/dxut/Core/DDSTextureLoader.cpp b/src/DX11/framework/dxut/Core/DDSTextureLoader.cpp new file mode 100644 index 0000000..5a7e77d --- /dev/null +++ b/src/DX11/framework/dxut/Core/DDSTextureLoader.cpp @@ -0,0 +1,1992 @@ +//-------------------------------------------------------------------------------------- +// File: DDSTextureLoader.cpp +// +// Functions for loading a DDS texture and creating a Direct3D runtime resource for it +// +// Note these functions are useful as a light-weight runtime loader for DDS files. For +// a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#include "dxut.h" +#include "DDSTextureLoader.h" + +#include +#include +#include +#include + +#ifdef __clang__ +#pragma clang diagnostic ignored "-Wcovered-switch-default" +#pragma clang diagnostic ignored "-Wswitch-enum" +#endif + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +// Macros +//-------------------------------------------------------------------------------------- +#ifndef MAKEFOURCC + #define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +//-------------------------------------------------------------------------------------- +// DDS file structure definitions +// +// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library +//-------------------------------------------------------------------------------------- +#pragma pack(push,1) + +const uint32_t DDS_MAGIC = 0x20534444; // "DDS " + +struct DDS_PIXELFORMAT +{ + uint32_t size; + uint32_t flags; + uint32_t fourCC; + uint32_t RGBBitCount; + uint32_t RBitMask; + uint32_t GBitMask; + uint32_t BBitMask; + uint32_t ABitMask; +}; + +#define DDS_FOURCC 0x00000004 // DDPF_FOURCC +#define DDS_RGB 0x00000040 // DDPF_RGB +#define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE +#define DDS_ALPHA 0x00000002 // DDPF_ALPHA +#define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + +#define DDS_HEADER_FLAGS_VOLUME 0x00800000 // DDSD_DEPTH + +#define DDS_HEIGHT 0x00000002 // DDSD_HEIGHT + +#define DDS_CUBEMAP_POSITIVEX 0x00000600 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEX +#define DDS_CUBEMAP_NEGATIVEX 0x00000a00 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEX +#define DDS_CUBEMAP_POSITIVEY 0x00001200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEY +#define DDS_CUBEMAP_NEGATIVEY 0x00002200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEY +#define DDS_CUBEMAP_POSITIVEZ 0x00004200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_POSITIVEZ +#define DDS_CUBEMAP_NEGATIVEZ 0x00008200 // DDSCAPS2_CUBEMAP | DDSCAPS2_CUBEMAP_NEGATIVEZ + +#define DDS_CUBEMAP_ALLFACES ( DDS_CUBEMAP_POSITIVEX | DDS_CUBEMAP_NEGATIVEX |\ + DDS_CUBEMAP_POSITIVEY | DDS_CUBEMAP_NEGATIVEY |\ + DDS_CUBEMAP_POSITIVEZ | DDS_CUBEMAP_NEGATIVEZ ) + +#define DDS_CUBEMAP 0x00000200 // DDSCAPS2_CUBEMAP + +enum DDS_MISC_FLAGS2 +{ + DDS_MISC_FLAGS2_ALPHA_MODE_MASK = 0x7L, +}; + +struct DDS_HEADER +{ + uint32_t size; + uint32_t flags; + uint32_t height; + uint32_t width; + uint32_t pitchOrLinearSize; + uint32_t depth; // only if DDS_HEADER_FLAGS_VOLUME is set in flags + uint32_t mipMapCount; + uint32_t reserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t caps; + uint32_t caps2; + uint32_t caps3; + uint32_t caps4; + uint32_t reserved2; +}; + +struct DDS_HEADER_DXT10 +{ + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see D3D11_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t miscFlags2; +}; + +#pragma pack(pop) + +//-------------------------------------------------------------------------------------- +namespace +{ + struct handle_closer { void operator()(HANDLE h) noexcept { if (h) CloseHandle(h); } }; + + using ScopedHandle = std::unique_ptr; + + inline HANDLE safe_handle(HANDLE h) noexcept { return (h == INVALID_HANDLE_VALUE) ? nullptr : h; } + + template + inline void SetDebugObjectName(_In_ ID3D11DeviceChild* resource, _In_ const char (&name)[TNameLength]) noexcept + { + #if defined(_DEBUG) || defined(PROFILE) + resource->SetPrivateData(WKPDID_D3DDebugObjectName, TNameLength - 1, name); + #else + UNREFERENCED_PARAMETER(resource); + UNREFERENCED_PARAMETER(name); + #endif + } + + //-------------------------------------------------------------------------------------- + HRESULT LoadTextureDataFromMemory( + _In_reads_(ddsDataSize) const uint8_t* ddsData, + size_t ddsDataSize, + const DDS_HEADER** header, + const uint8_t** bitData, + size_t* bitSize) noexcept + { + if (!header || !bitData || !bitSize) + { + return E_POINTER; + } + + *bitSize = 0; + + if (ddsDataSize > UINT32_MAX) + { + return E_FAIL; + } + + if (ddsDataSize < (sizeof(uint32_t) + sizeof(DDS_HEADER))) + { + return E_FAIL; + } + + // DDS files always start with the same magic number ("DDS ") + auto dwMagicNumber = *reinterpret_cast(ddsData); + if (dwMagicNumber != DDS_MAGIC) + { + return E_FAIL; + } + + auto hdr = reinterpret_cast(ddsData + sizeof(uint32_t)); + + // Verify header to validate DDS file + if (hdr->size != sizeof(DDS_HEADER) || + hdr->ddspf.size != sizeof(DDS_PIXELFORMAT)) + { + return E_FAIL; + } + + // Check for DX10 extension + bool bDXT10Header = false; + if ((hdr->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == hdr->ddspf.fourCC)) + { + // Must be long enough for both headers and magic value + if (ddsDataSize < (sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10))) + { + return E_FAIL; + } + + bDXT10Header = true; + } + + // setup the pointers in the process request + *header = hdr; + auto offset = sizeof(uint32_t) + + sizeof(DDS_HEADER) + + (bDXT10Header ? sizeof(DDS_HEADER_DXT10) : 0); + *bitData = ddsData + offset; + *bitSize = ddsDataSize - offset; + + return S_OK; + } + + + //-------------------------------------------------------------------------------------- + HRESULT LoadTextureDataFromFile( + _In_z_ const wchar_t* fileName, + std::unique_ptr& ddsData, + const DDS_HEADER** header, + const uint8_t** bitData, + size_t* bitSize) noexcept + { + if (!header || !bitData || !bitSize) + { + return E_POINTER; + } + + *bitSize = 0; + + // open the file +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(fileName, + GENERIC_READ, + FILE_SHARE_READ, + OPEN_EXISTING, + nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(fileName, + GENERIC_READ, + FILE_SHARE_READ, + nullptr, + OPEN_EXISTING, + FILE_ATTRIBUTE_NORMAL, + nullptr))); +#endif + + if (!hFile) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // Get the file size + FILE_STANDARD_INFO fileInfo; + if (!GetFileInformationByHandleEx(hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo))) + { + return HRESULT_FROM_WIN32(GetLastError()); + } + + // File is too big for 32-bit allocation, so reject read + if (fileInfo.EndOfFile.HighPart > 0) + { + return E_FAIL; + } + + // Need at least enough data to fill the header and magic number to be a valid DDS + if (fileInfo.EndOfFile.LowPart < (sizeof(uint32_t) + sizeof(DDS_HEADER))) + { + return E_FAIL; + } + + // create enough space for the file data + ddsData.reset(new (std::nothrow) uint8_t[fileInfo.EndOfFile.LowPart]); + if (!ddsData) + { + return E_OUTOFMEMORY; + } + + // read the data in + DWORD bytesRead = 0; + if (!ReadFile(hFile.get(), + ddsData.get(), + fileInfo.EndOfFile.LowPart, + &bytesRead, + nullptr + )) + { + ddsData.reset(); + return HRESULT_FROM_WIN32(GetLastError()); + } + + if (bytesRead < fileInfo.EndOfFile.LowPart) + { + ddsData.reset(); + return E_FAIL; + } + + // DDS files always start with the same magic number ("DDS ") + auto dwMagicNumber = *reinterpret_cast(ddsData.get()); + if (dwMagicNumber != DDS_MAGIC) + { + ddsData.reset(); + return E_FAIL; + } + + auto hdr = reinterpret_cast(ddsData.get() + sizeof(uint32_t)); + + // Verify header to validate DDS file + if (hdr->size != sizeof(DDS_HEADER) || + hdr->ddspf.size != sizeof(DDS_PIXELFORMAT)) + { + ddsData.reset(); + return E_FAIL; + } + + // Check for DX10 extension + bool bDXT10Header = false; + if ((hdr->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == hdr->ddspf.fourCC)) + { + // Must be long enough for both headers and magic value + if (fileInfo.EndOfFile.LowPart < (sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10))) + { + ddsData.reset(); + return E_FAIL; + } + + bDXT10Header = true; + } + + // setup the pointers in the process request + *header = hdr; + auto offset = sizeof(uint32_t) + sizeof(DDS_HEADER) + + (bDXT10Header ? sizeof(DDS_HEADER_DXT10) : 0); + *bitData = ddsData.get() + offset; + *bitSize = fileInfo.EndOfFile.LowPart - offset; + + return S_OK; + } + + + //-------------------------------------------------------------------------------------- + // Return the BPP for a particular format + //-------------------------------------------------------------------------------------- + size_t BitsPerPixel(_In_ DXGI_FORMAT fmt) noexcept + { + switch (fmt) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + default: + return 0; + } + } + + + //-------------------------------------------------------------------------------------- + // Get surface information for a particular format + //-------------------------------------------------------------------------------------- + HRESULT GetSurfaceInfo( + _In_ size_t width, + _In_ size_t height, + _In_ DXGI_FORMAT fmt, + size_t* outNumBytes, + _Out_opt_ size_t* outRowBytes, + _Out_opt_ size_t* outNumRows) noexcept + { + uint64_t numBytes = 0; + uint64_t rowBytes = 0; + uint64_t numRows = 0; + + bool bc = false; + bool packed = false; + bool planar = false; + size_t bpe = 0; + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + bc = true; + bpe = 8; + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc = true; + bpe = 16; + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + packed = true; + bpe = 4; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + packed = true; + bpe = 8; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + planar = true; + bpe = 2; + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + planar = true; + bpe = 4; + break; + + default: + break; + } + + if (bc) + { + uint64_t numBlocksWide = 0; + if (width > 0) + { + numBlocksWide = std::max(1u, (uint64_t(width) + 3u) / 4u); + } + uint64_t numBlocksHigh = 0; + if (height > 0) + { + numBlocksHigh = std::max(1u, (uint64_t(height) + 3u) / 4u); + } + rowBytes = numBlocksWide * bpe; + numRows = numBlocksHigh; + numBytes = rowBytes * numBlocksHigh; + } + else if (packed) + { + rowBytes = ((uint64_t(width) + 1u) >> 1) * bpe; + numRows = uint64_t(height); + numBytes = rowBytes * height; + } + else if (fmt == DXGI_FORMAT_NV11) + { + rowBytes = ((uint64_t(width) + 3u) >> 2) * 4u; + numRows = uint64_t(height) * 2u; // Direct3D makes this simplifying assumption, although it is larger than the 4:1:1 data + numBytes = rowBytes * numRows; + } + else if (planar) + { + rowBytes = ((uint64_t(width) + 1u) >> 1) * bpe; + numBytes = (rowBytes * uint64_t(height)) + ((rowBytes * uint64_t(height) + 1u) >> 1); + numRows = height + ((uint64_t(height) + 1u) >> 1); + } + else + { + size_t bpp = BitsPerPixel(fmt); + if (!bpp) + return E_INVALIDARG; + + rowBytes = (uint64_t(width) * bpp + 7u) / 8u; // round up to nearest byte + numRows = uint64_t(height); + numBytes = rowBytes * height; + } + +#if defined(_M_IX86) || defined(_M_ARM) || defined(_M_HYBRID_X86_ARM64) + static_assert(sizeof(size_t) == 4, "Not a 32-bit platform!"); + if (numBytes > UINT32_MAX || rowBytes > UINT32_MAX || numRows > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW); +#else + static_assert(sizeof(size_t) == 8, "Not a 64-bit platform!"); +#endif + + if (outNumBytes) + { + *outNumBytes = static_cast(numBytes); + } + if (outRowBytes) + { + *outRowBytes = static_cast(rowBytes); + } + if (outNumRows) + { + *outNumRows = static_cast(numRows); + } + + return S_OK; + } + + + //-------------------------------------------------------------------------------------- + #define ISBITMASK( r,g,b,a ) ( ddpf.RBitMask == r && ddpf.GBitMask == g && ddpf.BBitMask == b && ddpf.ABitMask == a ) + + DXGI_FORMAT GetDXGIFormat(const DDS_PIXELFORMAT& ddpf) noexcept + { + if (ddpf.flags & DDS_RGB) + { + // Note that sRGB formats are written using the "DX10" extended header + + switch (ddpf.RGBBitCount) + { + case 32: + if (ISBITMASK(0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000)) + { + return DXGI_FORMAT_R8G8B8A8_UNORM; + } + + if (ISBITMASK(0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000)) + { + return DXGI_FORMAT_B8G8R8A8_UNORM; + } + + if (ISBITMASK(0x00ff0000, 0x0000ff00, 0x000000ff, 0)) + { + return DXGI_FORMAT_B8G8R8X8_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x000000ff,0x0000ff00,0x00ff0000,0) aka D3DFMT_X8B8G8R8 + + // Note that many common DDS reader/writers (including D3DX) swap the + // the RED/BLUE masks for 10:10:10:2 formats. We assume + // below that the 'backwards' header mask is being used since it is most + // likely written by D3DX. The more robust solution is to use the 'DX10' + // header extension and specify the DXGI_FORMAT_R10G10B10A2_UNORM format directly + + // For 'correct' writers, this should be 0x000003ff,0x000ffc00,0x3ff00000 for RGB data + if (ISBITMASK(0x3ff00000, 0x000ffc00, 0x000003ff, 0xc0000000)) + { + return DXGI_FORMAT_R10G10B10A2_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x000003ff,0x000ffc00,0x3ff00000,0xc0000000) aka D3DFMT_A2R10G10B10 + + if (ISBITMASK(0x0000ffff, 0xffff0000, 0, 0)) + { + return DXGI_FORMAT_R16G16_UNORM; + } + + if (ISBITMASK(0xffffffff, 0, 0, 0)) + { + // Only 32-bit color channel format in D3D9 was R32F + return DXGI_FORMAT_R32_FLOAT; // D3DX writes this out as a FourCC of 114 + } + break; + + case 24: + // No 24bpp DXGI formats aka D3DFMT_R8G8B8 + break; + + case 16: + if (ISBITMASK(0x7c00, 0x03e0, 0x001f, 0x8000)) + { + return DXGI_FORMAT_B5G5R5A1_UNORM; + } + if (ISBITMASK(0xf800, 0x07e0, 0x001f, 0)) + { + return DXGI_FORMAT_B5G6R5_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x7c00,0x03e0,0x001f,0) aka D3DFMT_X1R5G5B5 + + if (ISBITMASK(0x0f00, 0x00f0, 0x000f, 0xf000)) + { + return DXGI_FORMAT_B4G4R4A4_UNORM; + } + + // NVTT versions 1.x wrote this as RGB instead of LUMINANCE + if (ISBITMASK(0x00ff, 0, 0, 0xff00)) + { + return DXGI_FORMAT_R8G8_UNORM; + } + if (ISBITMASK(0xffff, 0, 0, 0)) + { + return DXGI_FORMAT_R16_UNORM; + } + + // No DXGI format maps to ISBITMASK(0x0f00,0x00f0,0x000f,0) aka D3DFMT_X4R4G4B4 + + // No 3:3:2:8 or paletted DXGI formats aka D3DFMT_A8R3G3B2, D3DFMT_A8P8, etc. + break; + + case 8: + // NVTT versions 1.x wrote this as RGB instead of LUMINANCE + if (ISBITMASK(0xff, 0, 0, 0)) + { + return DXGI_FORMAT_R8_UNORM; + } + + // No 3:3:2 or paletted DXGI formats aka D3DFMT_R3G3B2, D3DFMT_P8 + break; + } + } + else if (ddpf.flags & DDS_LUMINANCE) + { + switch (ddpf.RGBBitCount) + { + case 16: + if (ISBITMASK(0xffff, 0, 0, 0)) + { + return DXGI_FORMAT_R16_UNORM; // D3DX10/11 writes this out as DX10 extension + } + if (ISBITMASK(0x00ff, 0, 0, 0xff00)) + { + return DXGI_FORMAT_R8G8_UNORM; // D3DX10/11 writes this out as DX10 extension + } + break; + + case 8: + if (ISBITMASK(0xff, 0, 0, 0)) + { + return DXGI_FORMAT_R8_UNORM; // D3DX10/11 writes this out as DX10 extension + } + + // No DXGI format maps to ISBITMASK(0x0f,0,0,0xf0) aka D3DFMT_A4L4 + + if (ISBITMASK(0x00ff, 0, 0, 0xff00)) + { + return DXGI_FORMAT_R8G8_UNORM; // Some DDS writers assume the bitcount should be 8 instead of 16 + } + break; + } + } + else if (ddpf.flags & DDS_ALPHA) + { + if (8 == ddpf.RGBBitCount) + { + return DXGI_FORMAT_A8_UNORM; + } + } + else if (ddpf.flags & DDS_BUMPDUDV) + { + switch (ddpf.RGBBitCount) + { + case 32: + if (ISBITMASK(0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000)) + { + return DXGI_FORMAT_R8G8B8A8_SNORM; // D3DX10/11 writes this out as DX10 extension + } + if (ISBITMASK(0x0000ffff, 0xffff0000, 0, 0)) + { + return DXGI_FORMAT_R16G16_SNORM; // D3DX10/11 writes this out as DX10 extension + } + + // No DXGI format maps to ISBITMASK(0x3ff00000, 0x000ffc00, 0x000003ff, 0xc0000000) aka D3DFMT_A2W10V10U10 + break; + + case 16: + if (ISBITMASK(0x00ff, 0xff00, 0, 0)) + { + return DXGI_FORMAT_R8G8_SNORM; // D3DX10/11 writes this out as DX10 extension + } + break; + } + + // No DXGI format maps to DDPF_BUMPLUMINANCE aka D3DFMT_L6V5U5, D3DFMT_X8L8V8U8 + } + else if (ddpf.flags & DDS_FOURCC) + { + if (MAKEFOURCC('D', 'X', 'T', '1') == ddpf.fourCC) + { + return DXGI_FORMAT_BC1_UNORM; + } + if (MAKEFOURCC('D', 'X', 'T', '3') == ddpf.fourCC) + { + return DXGI_FORMAT_BC2_UNORM; + } + if (MAKEFOURCC('D', 'X', 'T', '5') == ddpf.fourCC) + { + return DXGI_FORMAT_BC3_UNORM; + } + + // While pre-multiplied alpha isn't directly supported by the DXGI formats, + // they are basically the same as these BC formats so they can be mapped + if (MAKEFOURCC('D', 'X', 'T', '2') == ddpf.fourCC) + { + return DXGI_FORMAT_BC2_UNORM; + } + if (MAKEFOURCC('D', 'X', 'T', '4') == ddpf.fourCC) + { + return DXGI_FORMAT_BC3_UNORM; + } + + if (MAKEFOURCC('A', 'T', 'I', '1') == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_UNORM; + } + if (MAKEFOURCC('B', 'C', '4', 'U') == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_UNORM; + } + if (MAKEFOURCC('B', 'C', '4', 'S') == ddpf.fourCC) + { + return DXGI_FORMAT_BC4_SNORM; + } + + if (MAKEFOURCC('A', 'T', 'I', '2') == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_UNORM; + } + if (MAKEFOURCC('B', 'C', '5', 'U') == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_UNORM; + } + if (MAKEFOURCC('B', 'C', '5', 'S') == ddpf.fourCC) + { + return DXGI_FORMAT_BC5_SNORM; + } + + // BC6H and BC7 are written using the "DX10" extended header + + if (MAKEFOURCC('R', 'G', 'B', 'G') == ddpf.fourCC) + { + return DXGI_FORMAT_R8G8_B8G8_UNORM; + } + if (MAKEFOURCC('G', 'R', 'G', 'B') == ddpf.fourCC) + { + return DXGI_FORMAT_G8R8_G8B8_UNORM; + } + + if (MAKEFOURCC('Y', 'U', 'Y', '2') == ddpf.fourCC) + { + return DXGI_FORMAT_YUY2; + } + + // Check for D3DFORMAT enums being set here + switch (ddpf.fourCC) + { + case 36: // D3DFMT_A16B16G16R16 + return DXGI_FORMAT_R16G16B16A16_UNORM; + + case 110: // D3DFMT_Q16W16V16U16 + return DXGI_FORMAT_R16G16B16A16_SNORM; + + case 111: // D3DFMT_R16F + return DXGI_FORMAT_R16_FLOAT; + + case 112: // D3DFMT_G16R16F + return DXGI_FORMAT_R16G16_FLOAT; + + case 113: // D3DFMT_A16B16G16R16F + return DXGI_FORMAT_R16G16B16A16_FLOAT; + + case 114: // D3DFMT_R32F + return DXGI_FORMAT_R32_FLOAT; + + case 115: // D3DFMT_G32R32F + return DXGI_FORMAT_R32G32_FLOAT; + + case 116: // D3DFMT_A32B32G32R32F + return DXGI_FORMAT_R32G32B32A32_FLOAT; + + // No DXGI format maps to D3DFMT_CxV8U8 + } + } + + return DXGI_FORMAT_UNKNOWN; + } + + #undef ISBITMASK + + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT MakeSRGB(_In_ DXGI_FORMAT format) noexcept + { + switch (format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + + default: + return format; + } + } + + + //-------------------------------------------------------------------------------------- + HRESULT FillInitData( + _In_ size_t width, + _In_ size_t height, + _In_ size_t depth, + _In_ size_t mipCount, + _In_ size_t arraySize, + _In_ DXGI_FORMAT format, + _In_ size_t maxsize, + _In_ size_t bitSize, + _In_reads_bytes_(bitSize) const uint8_t* bitData, + _Out_ size_t& twidth, + _Out_ size_t& theight, + _Out_ size_t& tdepth, + _Out_ size_t& skipMip, + _Out_writes_(mipCount*arraySize) D3D11_SUBRESOURCE_DATA* initData) noexcept + { + if (!bitData || !initData) + { + return E_POINTER; + } + + skipMip = 0; + twidth = 0; + theight = 0; + tdepth = 0; + + size_t NumBytes = 0; + size_t RowBytes = 0; + const uint8_t* pSrcBits = bitData; + const uint8_t* pEndBits = bitData + bitSize; + + size_t index = 0; + for (size_t j = 0; j < arraySize; j++) + { + size_t w = width; + size_t h = height; + size_t d = depth; + for (size_t i = 0; i < mipCount; i++) + { + HRESULT hr = GetSurfaceInfo(w, h, format, &NumBytes, &RowBytes, nullptr); + if (FAILED(hr)) + return hr; + + if (NumBytes > UINT32_MAX || RowBytes > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW); + + if ((mipCount <= 1) || !maxsize || (w <= maxsize && h <= maxsize && d <= maxsize)) + { + if (!twidth) + { + twidth = w; + theight = h; + tdepth = d; + } + + assert(index < mipCount * arraySize); + _Analysis_assume_(index < mipCount * arraySize); + initData[index].pSysMem = pSrcBits; + initData[index].SysMemPitch = static_cast(RowBytes); + initData[index].SysMemSlicePitch = static_cast(NumBytes); + ++index; + } + else if (!j) + { + // Count number of skipped mipmaps (first item only) + ++skipMip; + } + + if (pSrcBits + (NumBytes*d) > pEndBits) + { + return HRESULT_FROM_WIN32(ERROR_HANDLE_EOF); + } + + pSrcBits += NumBytes * d; + + w = w >> 1; + h = h >> 1; + d = d >> 1; + if (w == 0) + { + w = 1; + } + if (h == 0) + { + h = 1; + } + if (d == 0) + { + d = 1; + } + } + } + + return (index > 0) ? S_OK : E_FAIL; + } + + + //-------------------------------------------------------------------------------------- + HRESULT CreateD3DResources( + _In_ ID3D11Device* d3dDevice, + _In_ uint32_t resDim, + _In_ size_t width, + _In_ size_t height, + _In_ size_t depth, + _In_ size_t mipCount, + _In_ size_t arraySize, + _In_ DXGI_FORMAT format, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _In_ bool isCubeMap, + _In_reads_opt_(mipCount*arraySize) D3D11_SUBRESOURCE_DATA* initData, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) noexcept + { + if (!d3dDevice) + return E_POINTER; + + HRESULT hr = E_FAIL; + + if (forceSRGB) + { + format = MakeSRGB(format); + } + + switch (resDim) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + { + D3D11_TEXTURE1D_DESC desc; + desc.Width = static_cast(width); + desc.MipLevels = static_cast(mipCount); + desc.ArraySize = static_cast(arraySize); + desc.Format = format; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + desc.MiscFlags = miscFlags & ~static_cast(D3D11_RESOURCE_MISC_TEXTURECUBE); + + ID3D11Texture1D* tex = nullptr; + hr = d3dDevice->CreateTexture1D(&desc, + initData, + &tex + ); + if (SUCCEEDED(hr) && tex) + { + if (textureView) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + SRVDesc.Format = format; + + if (arraySize > 1) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1DARRAY; + SRVDesc.Texture1DArray.MipLevels = (!mipCount) ? UINT(-1) : desc.MipLevels; + SRVDesc.Texture1DArray.ArraySize = static_cast(arraySize); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1D; + SRVDesc.Texture1D.MipLevels = (!mipCount) ? UINT(-1) : desc.MipLevels; + } + + hr = d3dDevice->CreateShaderResourceView(tex, + &SRVDesc, + textureView + ); + if (FAILED(hr)) + { + tex->Release(); + return hr; + } + } + + if (texture) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + { + D3D11_TEXTURE2D_DESC desc; + desc.Width = static_cast(width); + desc.Height = static_cast(height); + desc.MipLevels = static_cast(mipCount); + desc.ArraySize = static_cast(arraySize); + desc.Format = format; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + if (isCubeMap) + { + desc.MiscFlags = miscFlags | D3D11_RESOURCE_MISC_TEXTURECUBE; + } + else + { + desc.MiscFlags = miscFlags & ~static_cast(D3D11_RESOURCE_MISC_TEXTURECUBE); + } + + ID3D11Texture2D* tex = nullptr; + hr = d3dDevice->CreateTexture2D(&desc, + initData, + &tex + ); + if (SUCCEEDED(hr) && tex) + { + if (textureView) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + SRVDesc.Format = format; + + if (isCubeMap) + { + if (arraySize > 6) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBEARRAY; + SRVDesc.TextureCubeArray.MipLevels = (!mipCount) ? UINT(-1) : desc.MipLevels; + + // Earlier we set arraySize to (NumCubes * 6) + SRVDesc.TextureCubeArray.NumCubes = static_cast(arraySize / 6); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURECUBE; + SRVDesc.TextureCube.MipLevels = (!mipCount) ? UINT(-1) : desc.MipLevels; + } + } + else if (arraySize > 1) + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2DARRAY; + SRVDesc.Texture2DArray.MipLevels = (!mipCount) ? UINT(-1) : desc.MipLevels; + SRVDesc.Texture2DArray.ArraySize = static_cast(arraySize); + } + else + { + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + SRVDesc.Texture2D.MipLevels = (!mipCount) ? UINT(-1) : desc.MipLevels; + } + + hr = d3dDevice->CreateShaderResourceView(tex, + &SRVDesc, + textureView + ); + if (FAILED(hr)) + { + tex->Release(); + return hr; + } + } + + if (texture) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + { + D3D11_TEXTURE3D_DESC desc; + desc.Width = static_cast(width); + desc.Height = static_cast(height); + desc.Depth = static_cast(depth); + desc.MipLevels = static_cast(mipCount); + desc.Format = format; + desc.Usage = usage; + desc.BindFlags = bindFlags; + desc.CPUAccessFlags = cpuAccessFlags; + desc.MiscFlags = miscFlags & ~static_cast(D3D11_RESOURCE_MISC_TEXTURECUBE); + + ID3D11Texture3D* tex = nullptr; + hr = d3dDevice->CreateTexture3D(&desc, + initData, + &tex + ); + if (SUCCEEDED(hr) && tex) + { + if (textureView) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + SRVDesc.Format = format; + + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE3D; + SRVDesc.Texture3D.MipLevels = (!mipCount) ? UINT(-1) : desc.MipLevels; + + hr = d3dDevice->CreateShaderResourceView(tex, + &SRVDesc, + textureView + ); + if (FAILED(hr)) + { + tex->Release(); + return hr; + } + } + + if (texture) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "DDSTextureLoader"); + tex->Release(); + } + } + } + break; + } + + return hr; + } + + //-------------------------------------------------------------------------------------- + HRESULT CreateTextureFromDDS( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_ const DDS_HEADER* header, + _In_reads_bytes_(bitSize) const uint8_t* bitData, + _In_ size_t bitSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) noexcept + { + HRESULT hr = S_OK; + + UINT width = header->width; + UINT height = header->height; + UINT depth = header->depth; + + uint32_t resDim = D3D11_RESOURCE_DIMENSION_UNKNOWN; + UINT arraySize = 1; + DXGI_FORMAT format = DXGI_FORMAT_UNKNOWN; + bool isCubeMap = false; + + size_t mipCount = header->mipMapCount; + if (0 == mipCount) + { + mipCount = 1; + } + + if ((header->ddspf.flags & DDS_FOURCC) && + (MAKEFOURCC('D', 'X', '1', '0') == header->ddspf.fourCC)) + { + auto d3d10ext = reinterpret_cast(reinterpret_cast(header) + sizeof(DDS_HEADER)); + + arraySize = d3d10ext->arraySize; + if (arraySize == 0) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + switch (d3d10ext->dxgiFormat) + { + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + default: + if (BitsPerPixel(d3d10ext->dxgiFormat) == 0) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + + format = d3d10ext->dxgiFormat; + + switch (d3d10ext->resourceDimension) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + // D3DX writes 1D textures with a fixed Height of 1 + if ((header->flags & DDS_HEIGHT) && height != 1) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + height = depth = 1; + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + if (d3d10ext->miscFlag & D3D11_RESOURCE_MISC_TEXTURECUBE) + { + arraySize *= 6; + isCubeMap = true; + } + depth = 1; + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + if (!(header->flags & DDS_HEADER_FLAGS_VOLUME)) + { + return HRESULT_FROM_WIN32(ERROR_INVALID_DATA); + } + + if (arraySize > 1) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + resDim = d3d10ext->resourceDimension; + } + else + { + format = GetDXGIFormat(header->ddspf); + + if (format == DXGI_FORMAT_UNKNOWN) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + if (header->flags & DDS_HEADER_FLAGS_VOLUME) + { + resDim = D3D11_RESOURCE_DIMENSION_TEXTURE3D; + } + else + { + if (header->caps2 & DDS_CUBEMAP) + { + // We require all six faces to be defined + if ((header->caps2 & DDS_CUBEMAP_ALLFACES) != DDS_CUBEMAP_ALLFACES) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + arraySize = 6; + isCubeMap = true; + } + + depth = 1; + resDim = D3D11_RESOURCE_DIMENSION_TEXTURE2D; + + // Note there's no way for a legacy Direct3D 9 DDS to express a '1D' texture + } + + assert(BitsPerPixel(format) != 0); + } + + // Bound sizes (for security purposes we don't trust DDS file metadata larger than the D3D 11.x hardware requirements) + if (mipCount > D3D11_REQ_MIP_LEVELS) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + switch (resDim) + { + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + if ((arraySize > D3D11_REQ_TEXTURE1D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURE1D_U_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + if (isCubeMap) + { + // This is the right bound because we set arraySize to (NumCubes*6) above + if ((arraySize > D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURECUBE_DIMENSION) || + (height > D3D11_REQ_TEXTURECUBE_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + } + else if ((arraySize > D3D11_REQ_TEXTURE2D_ARRAY_AXIS_DIMENSION) || + (width > D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION) || + (height > D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + if ((arraySize > 1) || + (width > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) || + (height > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION) || + (depth > D3D11_REQ_TEXTURE3D_U_V_OR_W_DIMENSION)) + { + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + bool autogen = false; + if (mipCount == 1 && d3dContext && textureView) // Must have context and shader-view to auto generate mipmaps + { + // See if format is supported for auto-gen mipmaps (varies by feature level) + UINT fmtSupport = 0; + hr = d3dDevice->CheckFormatSupport(format, &fmtSupport); + if (SUCCEEDED(hr) && (fmtSupport & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN)) + { + // 10level9 feature levels do not support auto-gen mipgen for volume textures + if ((resDim != D3D11_RESOURCE_DIMENSION_TEXTURE3D) + || (d3dDevice->GetFeatureLevel() >= D3D_FEATURE_LEVEL_10_0)) + { + autogen = true; + } + } + } + + if (autogen) + { + // Create texture with auto-generated mipmaps + ID3D11Resource* tex = nullptr; + hr = CreateD3DResources(d3dDevice, + resDim, width, height, depth, 0, arraySize, + format, + usage, + bindFlags | D3D11_BIND_RENDER_TARGET, + cpuAccessFlags, + miscFlags | D3D11_RESOURCE_MISC_GENERATE_MIPS, + forceSRGB, + isCubeMap, + nullptr, + &tex, textureView); + if (SUCCEEDED(hr)) + { + size_t numBytes = 0; + size_t rowBytes = 0; + hr = GetSurfaceInfo(width, height, format, &numBytes, &rowBytes, nullptr); + if (FAILED(hr)) + return hr; + + if (numBytes > bitSize) + { + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return HRESULT_FROM_WIN32(ERROR_HANDLE_EOF); + } + + if (numBytes > UINT32_MAX || rowBytes > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW); + + D3D11_SHADER_RESOURCE_VIEW_DESC desc; + (*textureView)->GetDesc(&desc); + + UINT mipLevels = 1; + + switch (desc.ViewDimension) + { + case D3D_SRV_DIMENSION_TEXTURE1D: mipLevels = desc.Texture1D.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE1DARRAY: mipLevels = desc.Texture1DArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE2D: mipLevels = desc.Texture2D.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE2DARRAY: mipLevels = desc.Texture2DArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURECUBE: mipLevels = desc.TextureCube.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURECUBEARRAY:mipLevels = desc.TextureCubeArray.MipLevels; break; + case D3D_SRV_DIMENSION_TEXTURE3D: mipLevels = desc.Texture3D.MipLevels; break; + default: + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return E_UNEXPECTED; + } + + if (arraySize > 1) + { + const uint8_t* pSrcBits = bitData; + const uint8_t* pEndBits = bitData + bitSize; + for (UINT item = 0; item < arraySize; ++item) + { + if ((pSrcBits + numBytes) > pEndBits) + { + (*textureView)->Release(); + *textureView = nullptr; + tex->Release(); + return HRESULT_FROM_WIN32(ERROR_HANDLE_EOF); + } + + UINT res = D3D11CalcSubresource(0, item, mipLevels); + d3dContext->UpdateSubresource(tex, res, nullptr, pSrcBits, static_cast(rowBytes), static_cast(numBytes)); + pSrcBits += numBytes; + } + } + else + { + d3dContext->UpdateSubresource(tex, 0, nullptr, bitData, static_cast(rowBytes), static_cast(numBytes)); + } + + d3dContext->GenerateMips(*textureView); + + if (texture) + { + *texture = tex; + } + else + { + tex->Release(); + } + } + } + else + { + // Create the texture + std::unique_ptr initData(new (std::nothrow) D3D11_SUBRESOURCE_DATA[mipCount * arraySize]); + if (!initData) + { + return E_OUTOFMEMORY; + } + + size_t skipMip = 0; + size_t twidth = 0; + size_t theight = 0; + size_t tdepth = 0; + hr = FillInitData(width, height, depth, mipCount, arraySize, + format, maxsize, bitSize, bitData, + twidth, theight, tdepth, skipMip, initData.get()); + + if (SUCCEEDED(hr)) + { + hr = CreateD3DResources(d3dDevice, + resDim, twidth, theight, tdepth, mipCount - skipMip, arraySize, + format, + usage, bindFlags, cpuAccessFlags, miscFlags, + forceSRGB, + isCubeMap, + initData.get(), + texture, textureView); + + if (FAILED(hr) && !maxsize && (mipCount > 1)) + { + // Retry with a maxsize determined by feature level + switch (d3dDevice->GetFeatureLevel()) + { + case D3D_FEATURE_LEVEL_9_1: + case D3D_FEATURE_LEVEL_9_2: + if (isCubeMap) + { + maxsize = 512u /*D3D_FL9_1_REQ_TEXTURECUBE_DIMENSION*/; + } + else + { + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 256u /*D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 2048u /*D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + } + break; + + case D3D_FEATURE_LEVEL_9_3: + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 256u /*D3D_FL9_1_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 4096u /*D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + default: // D3D_FEATURE_LEVEL_10_0 & D3D_FEATURE_LEVEL_10_1 + maxsize = (resDim == D3D11_RESOURCE_DIMENSION_TEXTURE3D) + ? 2048u /*D3D10_REQ_TEXTURE3D_U_V_OR_W_DIMENSION*/ + : 8192u /*D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + } + + hr = FillInitData(width, height, depth, mipCount, arraySize, format, maxsize, bitSize, bitData, + twidth, theight, tdepth, skipMip, initData.get()); + if (SUCCEEDED(hr)) + { + hr = CreateD3DResources(d3dDevice, + resDim, twidth, theight, tdepth, mipCount - skipMip, arraySize, + format, + usage, bindFlags, cpuAccessFlags, miscFlags, + forceSRGB, + isCubeMap, + initData.get(), + texture, textureView); + } + } + } + } + + return hr; + } + + + //-------------------------------------------------------------------------------------- + DDS_ALPHA_MODE GetAlphaMode(_In_ const DDS_HEADER* header) noexcept + { + if (header->ddspf.flags & DDS_FOURCC) + { + if (MAKEFOURCC('D', 'X', '1', '0') == header->ddspf.fourCC) + { + auto d3d10ext = reinterpret_cast(reinterpret_cast(header) + sizeof(DDS_HEADER)); + auto mode = static_cast(d3d10ext->miscFlags2 & DDS_MISC_FLAGS2_ALPHA_MODE_MASK); + switch (mode) + { + case DDS_ALPHA_MODE_STRAIGHT: + case DDS_ALPHA_MODE_PREMULTIPLIED: + case DDS_ALPHA_MODE_OPAQUE: + case DDS_ALPHA_MODE_CUSTOM: + return mode; + + case DDS_ALPHA_MODE_UNKNOWN: + default: + break; + } + } + else if ((MAKEFOURCC('D', 'X', 'T', '2') == header->ddspf.fourCC) + || (MAKEFOURCC('D', 'X', 'T', '4') == header->ddspf.fourCC)) + { + return DDS_ALPHA_MODE_PREMULTIPLIED; + } + } + + return DDS_ALPHA_MODE_UNKNOWN; + } + + //-------------------------------------------------------------------------------------- + void SetDebugTextureInfo( + _In_z_ const wchar_t* fileName, + _In_opt_ ID3D11Resource** texture, + _In_opt_ ID3D11ShaderResourceView** textureView) noexcept + { +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + if (texture || textureView) + { + CHAR strFileA[MAX_PATH]; + int result = WideCharToMultiByte(CP_UTF8, + WC_NO_BEST_FIT_CHARS, + fileName, + -1, + strFileA, + MAX_PATH, + nullptr, + nullptr + ); + if (result > 0) + { + const char* pstrName = strrchr(strFileA, '\\'); + if (!pstrName) + { + pstrName = strFileA; + } + else + { + pstrName++; + } + + if (texture && *texture) + { + (*texture)->SetPrivateData(WKPDID_D3DDebugObjectName, + static_cast(strnlen_s(pstrName, MAX_PATH)), + pstrName + ); + } + + if (textureView && *textureView) + { + (*textureView)->SetPrivateData(WKPDID_D3DDebugObjectName, + static_cast(strnlen_s(pstrName, MAX_PATH)), + pstrName + ); + } + } + } +#else + UNREFERENCED_PARAMETER(fileName); + UNREFERENCED_PARAMETER(texture); + UNREFERENCED_PARAMETER(textureView); +#endif + } +} // anonymous namespace + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemory( + ID3D11Device* d3dDevice, + const uint8_t* ddsData, + size_t ddsDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode) noexcept +{ + return CreateDDSTextureFromMemoryEx(d3dDevice, nullptr, + ddsData, ddsDataSize, + maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + false, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemory( + ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* ddsData, + size_t ddsDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode) noexcept +{ + return CreateDDSTextureFromMemoryEx(d3dDevice, d3dContext, + ddsData, ddsDataSize, + maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + false, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemoryEx( + ID3D11Device* d3dDevice, + const uint8_t* ddsData, + size_t ddsDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode) noexcept +{ + return CreateDDSTextureFromMemoryEx(d3dDevice, nullptr, + ddsData, ddsDataSize, + maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, + forceSRGB, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromMemoryEx( + ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* ddsData, + size_t ddsDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode) noexcept +{ + if (texture) + { + *texture = nullptr; + } + if (textureView) + { + *textureView = nullptr; + } + if (alphaMode) + { + *alphaMode = DDS_ALPHA_MODE_UNKNOWN; + } + + if (!d3dDevice || !ddsData || (!texture && !textureView)) + { + return E_INVALIDARG; + } + + if (textureView && !(bindFlags & D3D11_BIND_SHADER_RESOURCE)) + { + return E_INVALIDARG; + } + + // Validate DDS file in memory + const DDS_HEADER* header = nullptr; + const uint8_t* bitData = nullptr; + size_t bitSize = 0; + + HRESULT hr = LoadTextureDataFromMemory(ddsData, ddsDataSize, + &header, + &bitData, + &bitSize + ); + if (FAILED(hr)) + { + return hr; + } + + hr = CreateTextureFromDDS(d3dDevice, d3dContext, + header, bitData, bitSize, + maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, + forceSRGB, + texture, textureView); + if (SUCCEEDED(hr)) + { + if (texture && *texture) + { + SetDebugObjectName(*texture, "DDSTextureLoader"); + } + + if (textureView && *textureView) + { + SetDebugObjectName(*textureView, "DDSTextureLoader"); + } + + if (alphaMode) + *alphaMode = GetAlphaMode(header); + } + + return hr; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFile( + ID3D11Device* d3dDevice, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode) noexcept +{ + return CreateDDSTextureFromFileEx(d3dDevice, nullptr, + fileName, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + false, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFile( + ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize, + DDS_ALPHA_MODE* alphaMode) noexcept +{ + return CreateDDSTextureFromFileEx(d3dDevice, d3dContext, + fileName, + maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + false, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFileEx( + ID3D11Device* d3dDevice, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode) noexcept +{ + return CreateDDSTextureFromFileEx(d3dDevice, nullptr, + fileName, + maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, + forceSRGB, + texture, textureView, alphaMode); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateDDSTextureFromFileEx( + ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + bool forceSRGB, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + DDS_ALPHA_MODE* alphaMode) noexcept +{ + if (texture) + { + *texture = nullptr; + } + if (textureView) + { + *textureView = nullptr; + } + if (alphaMode) + { + *alphaMode = DDS_ALPHA_MODE_UNKNOWN; + } + + if (!d3dDevice || !fileName || (!texture && !textureView)) + { + return E_INVALIDARG; + } + + if (textureView && !(bindFlags & D3D11_BIND_SHADER_RESOURCE)) + { + return E_INVALIDARG; + } + + const DDS_HEADER* header = nullptr; + const uint8_t* bitData = nullptr; + size_t bitSize = 0; + + std::unique_ptr ddsData; + HRESULT hr = LoadTextureDataFromFile(fileName, + ddsData, + &header, + &bitData, + &bitSize + ); + if (FAILED(hr)) + { + return hr; + } + + hr = CreateTextureFromDDS(d3dDevice, d3dContext, + header, bitData, bitSize, + maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, + forceSRGB, + texture, textureView); + + if (SUCCEEDED(hr)) + { + SetDebugTextureInfo(fileName, texture, textureView); + + if (alphaMode) + *alphaMode = GetAlphaMode(header); + } + + return hr; +} diff --git a/src/DX11/framework/dxut/Core/DDSTextureLoader.h b/src/DX11/framework/dxut/Core/DDSTextureLoader.h new file mode 100644 index 0000000..a40af5e --- /dev/null +++ b/src/DX11/framework/dxut/Core/DDSTextureLoader.h @@ -0,0 +1,134 @@ +//-------------------------------------------------------------------------------------- +// File: DDSTextureLoader.h +// +// Functions for loading a DDS texture and creating a Direct3D runtime resource for it +// +// Note these functions are useful as a light-weight runtime loader for DDS files. For +// a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include + +#include +#include + + +namespace DirectX +{ +#ifndef DDS_ALPHA_MODE_DEFINED +#define DDS_ALPHA_MODE_DEFINED + enum DDS_ALPHA_MODE : uint32_t + { + DDS_ALPHA_MODE_UNKNOWN = 0, + DDS_ALPHA_MODE_STRAIGHT = 1, + DDS_ALPHA_MODE_PREMULTIPLIED = 2, + DDS_ALPHA_MODE_OPAQUE = 3, + DDS_ALPHA_MODE_CUSTOM = 4, + }; +#endif + + // Standard version + HRESULT CreateDDSTextureFromMemory( + _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr) noexcept; + + HRESULT CreateDDSTextureFromFile( + _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr) noexcept; + + // Standard version with optional auto-gen mipmap support + HRESULT CreateDDSTextureFromMemory( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr) noexcept; + + HRESULT CreateDDSTextureFromFile( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr) noexcept; + + // Extended version + HRESULT CreateDDSTextureFromMemoryEx( + _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr) noexcept; + + HRESULT CreateDDSTextureFromFileEx( + _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr) noexcept; + + // Extended version with optional auto-gen mipmap support + HRESULT CreateDDSTextureFromMemoryEx( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(ddsDataSize) const uint8_t* ddsData, + _In_ size_t ddsDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr) noexcept; + + HRESULT CreateDDSTextureFromFileEx( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ bool forceSRGB, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _Out_opt_ DDS_ALPHA_MODE* alphaMode = nullptr) noexcept; +} diff --git a/src/DX11/framework/dxut/Core/DXUT.cpp b/src/DX11/framework/dxut/Core/DXUT.cpp new file mode 100644 index 0000000..66492f7 --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT.cpp @@ -0,0 +1,4516 @@ +//-------------------------------------------------------------------------------------- +// File: DXUT.cpp +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "DXUT.h" + +#ifndef NDEBUG +#include +#endif + +#define DXUT_MIN_WINDOW_SIZE_X 200 +#define DXUT_MIN_WINDOW_SIZE_Y 200 +#define DXUT_COUNTER_STAT_LENGTH 2048 + + +//-------------------------------------------------------------------------------------- +// Thread safety +//-------------------------------------------------------------------------------------- +CRITICAL_SECTION g_cs; +bool g_bThreadSafe = true; + + +//-------------------------------------------------------------------------------------- +// Automatically enters & leaves the CS upon object creation/deletion +//-------------------------------------------------------------------------------------- +class DXUTLock +{ +public: +#pragma prefast( suppress:26166, "g_bThreadSafe controls behavior" ) + inline _Acquires_lock_(g_cs) DXUTLock() noexcept { if( g_bThreadSafe ) EnterCriticalSection( &g_cs ); } +#pragma prefast( suppress:26165, "g_bThreadSafe controls behavior" ) + inline _Releases_lock_(g_cs) ~DXUTLock() { if( g_bThreadSafe ) LeaveCriticalSection( &g_cs ); } +}; + +//-------------------------------------------------------------------------------------- +// Helper macros to build member functions that access member variables with thread safety +//-------------------------------------------------------------------------------------- +#define SET_ACCESSOR( x, y ) inline void Set##y( x t ) { DXUTLock l; m_state.m_##y = t; }; +#define GET_ACCESSOR( x, y ) inline x Get##y() { DXUTLock l; return m_state.m_##y; }; +#define GET_SET_ACCESSOR( x, y ) SET_ACCESSOR( x, y ) GET_ACCESSOR( x, y ) + +#define SETP_ACCESSOR( x, y ) inline void Set##y( x* t ) { DXUTLock l; m_state.m_##y = *t; }; +#define GETP_ACCESSOR( x, y ) inline x* Get##y() { DXUTLock l; return &m_state.m_##y; }; +#define GETP_SETP_ACCESSOR( x, y ) SETP_ACCESSOR( x, y ) GETP_ACCESSOR( x, y ) + + +//-------------------------------------------------------------------------------------- +// Stores timer callback info +//-------------------------------------------------------------------------------------- +struct DXUT_TIMER +{ + LPDXUTCALLBACKTIMER pCallbackTimer; + void* pCallbackUserContext; + float fTimeoutInSecs; + float fCountdown; + bool bEnabled; + UINT nID; +}; + + +//-------------------------------------------------------------------------------------- +// Stores DXUT state and data access is done with thread safety (if g_bThreadSafe==true) +//-------------------------------------------------------------------------------------- +class DXUTState +{ +protected: + struct STATE + { + DXUTDeviceSettings* m_CurrentDeviceSettings; // current device settings + IDXGIFactory1* m_DXGIFactory; // DXGI Factory object + IDXGIAdapter1* m_DXGIAdapter; // The DXGI adapter object for the D3D11 device + IDXGIOutput** m_DXGIOutputArray; // The array of output obj for the D3D11 adapter obj + UINT m_DXGIOutputArraySize; // Number of elements in m_D3D11OutputArray + IDXGISwapChain* m_DXGISwapChain; // the D3D11 swapchain + DXGI_SURFACE_DESC m_BackBufferSurfaceDescDXGI; // D3D11 back buffer surface description + bool m_RenderingOccluded; // Rendering is occluded by another window + bool m_DoNotStoreBufferSize; // Do not store the buffer size on WM_SIZE messages + + // D3D11 specific + ID3D11Device* m_D3D11Device; // the D3D11 rendering device + ID3D11DeviceContext* m_D3D11DeviceContext; // the D3D11 immediate device context + D3D_FEATURE_LEVEL m_D3D11FeatureLevel; // the D3D11 feature level that this device supports + ID3D11Texture2D* m_D3D11DepthStencil; // the D3D11 depth stencil texture (optional) + ID3D11DepthStencilView* m_D3D11DepthStencilView; // the D3D11 depth stencil view (optional) + ID3D11RenderTargetView* m_D3D11RenderTargetView; // the D3D11 render target view + ID3D11RasterizerState* m_D3D11RasterizerState; // the D3D11 Rasterizer state + + // D3D11.1 specific + ID3D11Device1* m_D3D11Device1; // the D3D11.1 rendering device + ID3D11DeviceContext1* m_D3D11DeviceContext1; // the D3D11.1 immediate device context + + // D3D11.2 specific + ID3D11Device2* m_D3D11Device2; // the D3D11.2 rendering device + ID3D11DeviceContext2* m_D3D11DeviceContext2; // the D3D11.2 immediate device context + +#ifdef USE_DIRECT3D11_3 + // D3D11.3 specific + ID3D11Device3* m_D3D11Device3; // the D3D11.3 rendering device + ID3D11DeviceContext3* m_D3D11DeviceContext3; // the D3D11.3 immediate device context +#endif + +#ifdef USE_DIRECT3D11_4 + // D3D11.4 specific + ID3D11Device4* m_D3D11Device4; // the D3D11.4 rendering device + ID3D11DeviceContext4* m_D3D11DeviceContext4; // the D3D11.4 immediate device context +#endif + + // General + HWND m_HWNDFocus; // the main app focus window + HWND m_HWNDDeviceFullScreen; // the main app device window in fullscreen mode + HWND m_HWNDDeviceWindowed; // the main app device window in windowed mode + HMONITOR m_AdapterMonitor; // the monitor of the adapter + HMENU m_Menu; // handle to menu + + UINT m_FullScreenBackBufferWidthAtModeChange; // back buffer size of fullscreen mode right before switching to windowed mode. Used to restore to same resolution when toggling back to fullscreen + UINT m_FullScreenBackBufferHeightAtModeChange; // back buffer size of fullscreen mode right before switching to windowed mode. Used to restore to same resolution when toggling back to fullscreen + UINT m_WindowBackBufferWidthAtModeChange; // back buffer size of windowed mode right before switching to fullscreen mode. Used to restore to same resolution when toggling back to windowed mode + UINT m_WindowBackBufferHeightAtModeChange; // back buffer size of windowed mode right before switching to fullscreen mode. Used to restore to same resolution when toggling back to windowed mode + DWORD m_WindowedStyleAtModeChange; // window style + WINDOWPLACEMENT m_WindowedPlacement;// record of windowed HWND position/show state/etc + bool m_TopmostWhileWindowed; // if true, the windowed HWND is topmost + bool m_Minimized; // if true, the HWND is minimized + bool m_Maximized; // if true, the HWND is maximized + bool m_MinimizedWhileFullscreen; // if true, the HWND is minimized due to a focus switch away when fullscreen mode + bool m_IgnoreSizeChange; // if true, DXUT won't reset the device upon HWND size change + + double m_Time; // current time in seconds + double m_AbsoluteTime; // absolute time in seconds + float m_ElapsedTime; // time elapsed since last frame + + HINSTANCE m_HInstance; // handle to the app instance + double m_LastStatsUpdateTime; // last time the stats were updated + DWORD m_LastStatsUpdateFrames; // frames count since last time the stats were updated + float m_FPS; // frames per second + int m_CurrentFrameNumber; // the current frame number + HHOOK m_KeyboardHook; // handle to keyboard hook + bool m_AllowShortcutKeysWhenFullscreen; // if true, when fullscreen enable shortcut keys (Windows keys, StickyKeys shortcut, ToggleKeys shortcut, FilterKeys shortcut) + bool m_AllowShortcutKeysWhenWindowed; // if true, when windowed enable shortcut keys (Windows keys, StickyKeys shortcut, ToggleKeys shortcut, FilterKeys shortcut) + bool m_AllowShortcutKeys; // if true, then shortcut keys are currently disabled (Windows key, etc) + bool m_CallDefWindowProc; // if true, DXUTStaticWndProc will call DefWindowProc for unhandled messages. Applications rendering to a dialog may need to set this to false. + STICKYKEYS m_StartupStickyKeys; // StickyKey settings upon startup so they can be restored later + TOGGLEKEYS m_StartupToggleKeys; // ToggleKey settings upon startup so they can be restored later + FILTERKEYS m_StartupFilterKeys; // FilterKey settings upon startup so they can be restored later + + bool m_HandleEscape; // if true, then DXUT will handle escape to quit + bool m_HandleAltEnter; // if true, then DXUT will handle alt-enter to toggle fullscreen + bool m_HandlePause; // if true, then DXUT will handle pause to toggle time pausing + bool m_ShowMsgBoxOnError; // if true, then msgboxes are displayed upon errors + bool m_NoStats; // if true, then DXUTGetFrameStats() and DXUTGetDeviceStats() will return blank strings + bool m_ClipCursorWhenFullScreen; // if true, then DXUT will keep the cursor from going outside the window when full screen + bool m_ShowCursorWhenFullScreen; // if true, then DXUT will show a cursor when full screen + bool m_ConstantFrameTime; // if true, then elapsed frame time will always be 0.05f seconds which is good for debugging or automated capture + float m_TimePerFrame; // the constant time per frame in seconds, only valid if m_ConstantFrameTime==true + bool m_WireframeMode; // if true, then D3DRS_FILLMODE==D3DFILL_WIREFRAME else D3DRS_FILLMODE==D3DFILL_SOLID + bool m_AutoChangeAdapter; // if true, then the adapter will automatically change if the window is different monitor + bool m_WindowCreatedWithDefaultPositions; // if true, then CW_USEDEFAULT was used and the window should be moved to the right adapter + int m_ExitCode; // the exit code to be returned to the command line + + bool m_DXUTInited; // if true, then DXUTInit() has succeeded + bool m_WindowCreated; // if true, then DXUTCreateWindow() or DXUTSetWindow() has succeeded + bool m_DeviceCreated; // if true, then DXUTCreateDevice() has succeeded + + bool m_DXUTInitCalled; // if true, then DXUTInit() was called + bool m_WindowCreateCalled; // if true, then DXUTCreateWindow() or DXUTSetWindow() was called + bool m_DeviceCreateCalled; // if true, then DXUTCreateDevice() was called + + bool m_DeviceObjectsCreated; // if true, then DeviceCreated callback has been called (if non-NULL) + bool m_DeviceObjectsReset; // if true, then DeviceReset callback has been called (if non-NULL) + bool m_InsideDeviceCallback; // if true, then the framework is inside an app device callback + bool m_InsideMainloop; // if true, then the framework is inside the main loop + bool m_Active; // if true, then the app is the active top level window + bool m_TimePaused; // if true, then time is paused + bool m_RenderingPaused; // if true, then rendering is paused + int m_PauseRenderingCount; // pause rendering ref count + int m_PauseTimeCount; // pause time ref count + bool m_DeviceLost; // if true, then the device is lost and needs to be reset + bool m_NotifyOnMouseMove; // if true, include WM_MOUSEMOVE in mousecallback + bool m_Automation; // if true, automation is enabled + bool m_InSizeMove; // if true, app is inside a WM_ENTERSIZEMOVE + UINT m_TimerLastID; // last ID of the DXUT timer + bool m_MessageWhenD3D11NotAvailable; + + D3D_FEATURE_LEVEL m_OverrideForceFeatureLevel; // if != -1, then overrid to use a featurelevel + WCHAR m_ScreenShotName[256]; // command line screen shot name + bool m_SaveScreenShot; // command line save screen shot + bool m_ExitAfterScreenShot; // command line exit after screen shot + + int m_OverrideAdapterOrdinal; // if != -1, then override to use this adapter ordinal + bool m_OverrideWindowed; // if true, then force to start windowed + int m_OverrideOutput; // if != -1, then override to use the particular output on the adapter + bool m_OverrideFullScreen; // if true, then force to start full screen + int m_OverrideStartX; // if != -1, then override to this X position of the window + int m_OverrideStartY; // if != -1, then override to this Y position of the window + int m_OverrideWidth; // if != 0, then override to this width + int m_OverrideHeight; // if != 0, then override to this height + bool m_OverrideForceHAL; // if true, then force to HAL device (failing if one doesn't exist) + bool m_OverrideForceREF; // if true, then force to REF device (failing if one doesn't exist) + bool m_OverrideForceWARP; // if true, then force to WARP device (failing if one doesn't exist) + bool m_OverrideConstantFrameTime; // if true, then force to constant frame time + float m_OverrideConstantTimePerFrame; // the constant time per frame in seconds if m_OverrideConstantFrameTime==true + int m_OverrideQuitAfterFrame; // if != 0, then it will force the app to quit after that frame + int m_OverrideForceVsync; // if == 0, then it will force the app to use D3DPRESENT_INTERVAL_IMMEDIATE, if == 1 force use of D3DPRESENT_INTERVAL_DEFAULT + bool m_AppCalledWasKeyPressed; // true if the app ever calls DXUTWasKeyPressed(). Allows for optimzation + bool m_ReleasingSwapChain; // if true, the app is releasing its swapchain + bool m_IsInGammaCorrectMode; // Tell DXUTRes and DXUTMisc that we are in gamma correct mode + + LPDXUTCALLBACKMODIFYDEVICESETTINGS m_ModifyDeviceSettingsFunc; // modify Direct3D device settings callback + LPDXUTCALLBACKDEVICEREMOVED m_DeviceRemovedFunc; // Direct3D device removed callback + LPDXUTCALLBACKFRAMEMOVE m_FrameMoveFunc; // frame move callback + LPDXUTCALLBACKKEYBOARD m_KeyboardFunc; // keyboard callback + LPDXUTCALLBACKMOUSE m_MouseFunc; // mouse callback + LPDXUTCALLBACKMSGPROC m_WindowMsgFunc; // window messages callback + + LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE m_IsD3D11DeviceAcceptableFunc; // D3D11 is device acceptable callback + LPDXUTCALLBACKD3D11DEVICECREATED m_D3D11DeviceCreatedFunc; // D3D11 device created callback + LPDXUTCALLBACKD3D11SWAPCHAINRESIZED m_D3D11SwapChainResizedFunc; // D3D11 SwapChain reset callback + LPDXUTCALLBACKD3D11SWAPCHAINRELEASING m_D3D11SwapChainReleasingFunc; // D3D11 SwapChain lost callback + LPDXUTCALLBACKD3D11DEVICEDESTROYED m_D3D11DeviceDestroyedFunc; // D3D11 device destroyed callback + LPDXUTCALLBACKD3D11FRAMERENDER m_D3D11FrameRenderFunc; // D3D11 frame render callback + + void* m_ModifyDeviceSettingsFuncUserContext; // user context for modify Direct3D device settings callback + void* m_DeviceRemovedFuncUserContext; // user context for Direct3D device removed callback + void* m_FrameMoveFuncUserContext; // user context for frame move callback + void* m_KeyboardFuncUserContext; // user context for keyboard callback + void* m_MouseFuncUserContext; // user context for mouse callback + void* m_WindowMsgFuncUserContext; // user context for window messages callback + + void* m_IsD3D11DeviceAcceptableFuncUserContext; // user context for is D3D11 device acceptable callback + void* m_D3D11DeviceCreatedFuncUserContext; // user context for D3D11 device created callback + void* m_D3D11SwapChainResizedFuncUserContext; // user context for D3D11 SwapChain resized callback + void* m_D3D11SwapChainReleasingFuncUserContext; // user context for D3D11 SwapChain releasing callback + void* m_D3D11DeviceDestroyedFuncUserContext; // user context for D3D11 device destroyed callback + void* m_D3D11FrameRenderFuncUserContext; // user context for D3D11 frame render callback + + bool m_Keys[256]; // array of key state + bool m_LastKeys[256]; // array of last key state + bool m_MouseButtons[5]; // array of mouse states + + std::vector* m_TimerList; // list of DXUT_TIMER structs + WCHAR m_StaticFrameStats[256]; // static part of frames stats + WCHAR m_FPSStats[64]; // fps stats + WCHAR m_FrameStats[256]; // frame stats (fps, width, etc) + WCHAR m_DeviceStats[256]; // device stats (description, device type, etc) + WCHAR m_WindowTitle[256]; // window title + }; + + STATE m_state; + +public: + DXUTState() noexcept : m_state{} + { + Create(); + } + + ~DXUTState() + { + Destroy(); + } + + void Create() + { + g_bThreadSafe = true; + (void)InitializeCriticalSectionAndSpinCount( &g_cs, 1000 ); + + ZeroMemory( &m_state, sizeof( STATE ) ); + m_state.m_OverrideStartX = -1; + m_state.m_OverrideStartY = -1; + m_state.m_OverrideForceFeatureLevel = (D3D_FEATURE_LEVEL)0; + m_state.m_ScreenShotName[0] = 0; + m_state.m_SaveScreenShot = false; + m_state.m_ExitAfterScreenShot = false; + m_state.m_OverrideAdapterOrdinal = -1; + m_state.m_OverrideOutput = -1; + m_state.m_OverrideForceVsync = -1; + m_state.m_AutoChangeAdapter = true; + m_state.m_ShowMsgBoxOnError = true; + m_state.m_AllowShortcutKeysWhenWindowed = true; + m_state.m_Active = true; + m_state.m_CallDefWindowProc = true; + m_state.m_HandleEscape = true; + m_state.m_HandleAltEnter = true; + m_state.m_HandlePause = true; + m_state.m_IsInGammaCorrectMode = true; + m_state.m_FPS = 1.0f; + m_state.m_MessageWhenD3D11NotAvailable = true; + } + + void Destroy() + { + SAFE_DELETE( m_state.m_TimerList ); + DXUTShutdown(); + DeleteCriticalSection( &g_cs ); + } + + // Macros to define access functions for thread safe access into m_state + GET_SET_ACCESSOR( DXUTDeviceSettings*, CurrentDeviceSettings ); + + // D3D11 specific + GET_SET_ACCESSOR( IDXGIFactory1*, DXGIFactory ); + GET_SET_ACCESSOR( IDXGIAdapter1*, DXGIAdapter ); + GET_SET_ACCESSOR( IDXGIOutput**, DXGIOutputArray ); + GET_SET_ACCESSOR( UINT, DXGIOutputArraySize ); + GET_SET_ACCESSOR( IDXGISwapChain*, DXGISwapChain ); + GETP_SETP_ACCESSOR( DXGI_SURFACE_DESC, BackBufferSurfaceDescDXGI ); + GET_SET_ACCESSOR( bool, RenderingOccluded ); + GET_SET_ACCESSOR( bool, DoNotStoreBufferSize ); + + GET_SET_ACCESSOR( ID3D11Device*, D3D11Device ); + GET_SET_ACCESSOR( ID3D11DeviceContext*, D3D11DeviceContext ); + GET_SET_ACCESSOR( D3D_FEATURE_LEVEL, D3D11FeatureLevel ); + GET_SET_ACCESSOR( ID3D11Texture2D*, D3D11DepthStencil ); + GET_SET_ACCESSOR( ID3D11DepthStencilView*, D3D11DepthStencilView ); + GET_SET_ACCESSOR( ID3D11RenderTargetView*, D3D11RenderTargetView ); + GET_SET_ACCESSOR( ID3D11RasterizerState*, D3D11RasterizerState ); + + GET_SET_ACCESSOR( ID3D11Device1*, D3D11Device1 ); + GET_SET_ACCESSOR( ID3D11DeviceContext1*, D3D11DeviceContext1 ); + + GET_SET_ACCESSOR(ID3D11Device2*, D3D11Device2); + GET_SET_ACCESSOR(ID3D11DeviceContext2*, D3D11DeviceContext2); + +#ifdef USE_DIRECT3D11_3 + GET_SET_ACCESSOR(ID3D11Device3*, D3D11Device3); + GET_SET_ACCESSOR(ID3D11DeviceContext3*, D3D11DeviceContext3); +#endif + +#ifdef USE_DIRECT3D11_4 + GET_SET_ACCESSOR(ID3D11Device4*, D3D11Device4); + GET_SET_ACCESSOR(ID3D11DeviceContext4*, D3D11DeviceContext4); +#endif + + GET_SET_ACCESSOR( HWND, HWNDFocus ); + GET_SET_ACCESSOR( HWND, HWNDDeviceFullScreen ); + GET_SET_ACCESSOR( HWND, HWNDDeviceWindowed ); + GET_SET_ACCESSOR( HMONITOR, AdapterMonitor ); + GET_SET_ACCESSOR( HMENU, Menu ); + + GET_SET_ACCESSOR( UINT, FullScreenBackBufferWidthAtModeChange ); + GET_SET_ACCESSOR( UINT, FullScreenBackBufferHeightAtModeChange ); + GET_SET_ACCESSOR( UINT, WindowBackBufferWidthAtModeChange ); + GET_SET_ACCESSOR( UINT, WindowBackBufferHeightAtModeChange ); + GETP_SETP_ACCESSOR( WINDOWPLACEMENT, WindowedPlacement ); + GET_SET_ACCESSOR( DWORD, WindowedStyleAtModeChange ); + GET_SET_ACCESSOR( bool, TopmostWhileWindowed ); + GET_SET_ACCESSOR( bool, Minimized ); + GET_SET_ACCESSOR( bool, Maximized ); + GET_SET_ACCESSOR( bool, MinimizedWhileFullscreen ); + GET_SET_ACCESSOR( bool, IgnoreSizeChange ); + + GET_SET_ACCESSOR( double, Time ); + GET_SET_ACCESSOR( double, AbsoluteTime ); + GET_SET_ACCESSOR( float, ElapsedTime ); + + GET_SET_ACCESSOR( HINSTANCE, HInstance ); + GET_SET_ACCESSOR( double, LastStatsUpdateTime ); + GET_SET_ACCESSOR( DWORD, LastStatsUpdateFrames ); + GET_SET_ACCESSOR( float, FPS ); + GET_SET_ACCESSOR( int, CurrentFrameNumber ); + GET_SET_ACCESSOR( HHOOK, KeyboardHook ); + GET_SET_ACCESSOR( bool, AllowShortcutKeysWhenFullscreen ); + GET_SET_ACCESSOR( bool, AllowShortcutKeysWhenWindowed ); + GET_SET_ACCESSOR( bool, AllowShortcutKeys ); + GET_SET_ACCESSOR( bool, CallDefWindowProc ); + GET_SET_ACCESSOR( STICKYKEYS, StartupStickyKeys ); + GET_SET_ACCESSOR( TOGGLEKEYS, StartupToggleKeys ); + GET_SET_ACCESSOR( FILTERKEYS, StartupFilterKeys ); + + GET_SET_ACCESSOR( bool, HandleEscape ); + GET_SET_ACCESSOR( bool, HandleAltEnter ); + GET_SET_ACCESSOR( bool, HandlePause ); + GET_SET_ACCESSOR( bool, ShowMsgBoxOnError ); + GET_SET_ACCESSOR( bool, NoStats ); + GET_SET_ACCESSOR( bool, ClipCursorWhenFullScreen ); + GET_SET_ACCESSOR( bool, ShowCursorWhenFullScreen ); + GET_SET_ACCESSOR( bool, ConstantFrameTime ); + GET_SET_ACCESSOR( float, TimePerFrame ); + GET_SET_ACCESSOR( bool, WireframeMode ); + GET_SET_ACCESSOR( bool, AutoChangeAdapter ); + GET_SET_ACCESSOR( bool, WindowCreatedWithDefaultPositions ); + GET_SET_ACCESSOR( int, ExitCode ); + + GET_SET_ACCESSOR( bool, DXUTInited ); + GET_SET_ACCESSOR( bool, WindowCreated ); + GET_SET_ACCESSOR( bool, DeviceCreated ); + GET_SET_ACCESSOR( bool, DXUTInitCalled ); + GET_SET_ACCESSOR( bool, WindowCreateCalled ); + GET_SET_ACCESSOR( bool, DeviceCreateCalled ); + GET_SET_ACCESSOR( bool, InsideDeviceCallback ); + GET_SET_ACCESSOR( bool, InsideMainloop ); + GET_SET_ACCESSOR( bool, DeviceObjectsCreated ); + GET_SET_ACCESSOR( bool, DeviceObjectsReset ); + GET_SET_ACCESSOR( bool, Active ); + GET_SET_ACCESSOR( bool, RenderingPaused ); + GET_SET_ACCESSOR( bool, TimePaused ); + GET_SET_ACCESSOR( int, PauseRenderingCount ); + GET_SET_ACCESSOR( int, PauseTimeCount ); + GET_SET_ACCESSOR( bool, DeviceLost ); + GET_SET_ACCESSOR( bool, NotifyOnMouseMove ); + GET_SET_ACCESSOR( bool, Automation ); + GET_SET_ACCESSOR( bool, InSizeMove ); + GET_SET_ACCESSOR( UINT, TimerLastID ); + GET_SET_ACCESSOR( bool, MessageWhenD3D11NotAvailable ); + GET_SET_ACCESSOR( bool, AppCalledWasKeyPressed ); + + GET_SET_ACCESSOR( D3D_FEATURE_LEVEL, OverrideForceFeatureLevel ); + GET_ACCESSOR( WCHAR*, ScreenShotName ); + GET_SET_ACCESSOR( bool, SaveScreenShot ); + GET_SET_ACCESSOR( bool, ExitAfterScreenShot ); + + GET_SET_ACCESSOR( int, OverrideAdapterOrdinal ); + GET_SET_ACCESSOR( bool, OverrideWindowed ); + GET_SET_ACCESSOR( int, OverrideOutput ); + GET_SET_ACCESSOR( bool, OverrideFullScreen ); + GET_SET_ACCESSOR( int, OverrideStartX ); + GET_SET_ACCESSOR( int, OverrideStartY ); + GET_SET_ACCESSOR( int, OverrideWidth ); + GET_SET_ACCESSOR( int, OverrideHeight ); + GET_SET_ACCESSOR( bool, OverrideForceHAL ); + GET_SET_ACCESSOR( bool, OverrideForceREF ); + GET_SET_ACCESSOR( bool, OverrideForceWARP ); + GET_SET_ACCESSOR( bool, OverrideConstantFrameTime ); + GET_SET_ACCESSOR( float, OverrideConstantTimePerFrame ); + GET_SET_ACCESSOR( int, OverrideQuitAfterFrame ); + GET_SET_ACCESSOR( int, OverrideForceVsync ); + GET_SET_ACCESSOR( bool, ReleasingSwapChain ); + GET_SET_ACCESSOR( bool, IsInGammaCorrectMode ); + + GET_SET_ACCESSOR( LPDXUTCALLBACKMODIFYDEVICESETTINGS, ModifyDeviceSettingsFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKDEVICEREMOVED, DeviceRemovedFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKFRAMEMOVE, FrameMoveFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKKEYBOARD, KeyboardFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKMOUSE, MouseFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKMSGPROC, WindowMsgFunc ); + + GET_SET_ACCESSOR( LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE, IsD3D11DeviceAcceptableFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKD3D11DEVICECREATED, D3D11DeviceCreatedFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKD3D11SWAPCHAINRESIZED, D3D11SwapChainResizedFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKD3D11SWAPCHAINRELEASING, D3D11SwapChainReleasingFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKD3D11DEVICEDESTROYED, D3D11DeviceDestroyedFunc ); + GET_SET_ACCESSOR( LPDXUTCALLBACKD3D11FRAMERENDER, D3D11FrameRenderFunc ); + + GET_SET_ACCESSOR( void*, ModifyDeviceSettingsFuncUserContext ); + GET_SET_ACCESSOR( void*, DeviceRemovedFuncUserContext ); + GET_SET_ACCESSOR( void*, FrameMoveFuncUserContext ); + GET_SET_ACCESSOR( void*, KeyboardFuncUserContext ); + GET_SET_ACCESSOR( void*, MouseFuncUserContext ); + GET_SET_ACCESSOR( void*, WindowMsgFuncUserContext ); + + GET_SET_ACCESSOR( void*, IsD3D11DeviceAcceptableFuncUserContext ); + GET_SET_ACCESSOR( void*, D3D11DeviceCreatedFuncUserContext ); + GET_SET_ACCESSOR( void*, D3D11DeviceDestroyedFuncUserContext ); + GET_SET_ACCESSOR( void*, D3D11SwapChainResizedFuncUserContext ); + GET_SET_ACCESSOR( void*, D3D11SwapChainReleasingFuncUserContext ); + GET_SET_ACCESSOR( void*, D3D11FrameRenderFuncUserContext ); + + GET_SET_ACCESSOR( std::vector*, TimerList ); + GET_ACCESSOR( bool*, Keys ); + GET_ACCESSOR( bool*, LastKeys ); + GET_ACCESSOR( bool*, MouseButtons ); + GET_ACCESSOR( WCHAR*, StaticFrameStats ); + GET_ACCESSOR( WCHAR*, FPSStats ); + GET_ACCESSOR( WCHAR*, FrameStats ); + GET_ACCESSOR( WCHAR*, DeviceStats ); + GET_ACCESSOR( WCHAR*, WindowTitle ); +}; + + +//-------------------------------------------------------------------------------------- +// Global state +//-------------------------------------------------------------------------------------- +DXUTState* g_pDXUTState = nullptr; + +HRESULT WINAPI DXUTCreateState() +{ + if( !g_pDXUTState ) + { + g_pDXUTState = new (std::nothrow) DXUTState; + if( !g_pDXUTState ) + return E_OUTOFMEMORY; + } + return S_OK; +} + +void WINAPI DXUTDestroyState() +{ + SAFE_DELETE( g_pDXUTState ); +} + +class DXUTMemoryHelper +{ +public: + DXUTMemoryHelper() noexcept { DXUTCreateState(); } + ~DXUTMemoryHelper() { DXUTDestroyState(); } +}; + +DXUTState& GetDXUTState() +{ + // This class will auto create the memory when its first accessed and delete it after the program exits WinMain. + // However the application can also call DXUTCreateState() & DXUTDestroyState() independantly if its wants + static DXUTMemoryHelper memory; + assert( g_pDXUTState ); + _Analysis_assume_( g_pDXUTState ); + return *g_pDXUTState; +} + + +//-------------------------------------------------------------------------------------- +// Internal functions forward declarations +//-------------------------------------------------------------------------------------- +void DXUTParseCommandLine( _In_z_ WCHAR* strCommandLine, + _In_ bool bIgnoreFirstCommand = true ); +bool DXUTIsNextArg( _Inout_ WCHAR*& strCmdLine, _In_ const WCHAR* strArg ); +bool DXUTGetCmdParam( _Inout_ WCHAR*& strCmdLine, _Out_cap_(cchDest) WCHAR* strFlag, _In_ int cchDest ); +void DXUTAllowShortcutKeys( _In_ bool bAllowKeys ); +void DXUTUpdateStaticFrameStats(); +void DXUTUpdateFrameStats(); + +LRESULT CALLBACK DXUTStaticWndProc( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); +void DXUTHandleTimers(); +void DXUTDisplayErrorMessage( _In_ HRESULT hr ); +int DXUTMapButtonToArrayIndex( _In_ BYTE vButton ); + +HRESULT DXUTChangeDevice( _In_ DXUTDeviceSettings* pNewDeviceSettings, + _In_ bool bClipWindowToSingleAdapter ); + +bool DXUTCanDeviceBeReset( _In_ DXUTDeviceSettings* pOldDeviceSettings, + _In_ DXUTDeviceSettings* pNewDeviceSettings, + _In_ ID3D11Device* pd3d11DeviceFromApp ); + + +HRESULT DXUTDelayLoadDXGI(); +HRESULT DXUTSnapDeviceSettingsToEnumDevice( _In_ DXUTDeviceSettings* pDeviceSettings, _In_ bool forceEnum, _In_ D3D_FEATURE_LEVEL forceFL = D3D_FEATURE_LEVEL(0) ); +void DXUTUpdateDeviceSettingsWithOverrides( _Inout_ DXUTDeviceSettings* pDeviceSettings ); +void DXUTCheckForDXGIFullScreenSwitch(); +void DXUTResizeDXGIBuffers( _In_ UINT Width, _In_ UINT Height, _In_ BOOL bFullscreen ); +void DXUTCheckForDXGIBufferChange(); +void DXUTCheckForWindowSizeChange(); +void DXUTCheckForWindowChangingMonitors(); +void DXUTCleanup3DEnvironment( _In_ bool bReleaseSettings ); +HMONITOR DXUTGetMonitorFromAdapter( _In_ DXUTDeviceSettings* pDeviceSettings ); +HRESULT DXUTGetAdapterOrdinalFromMonitor( _In_ HMONITOR hMonitor, _Out_ UINT* pAdapterOrdinal ); +HRESULT DXUTGetOutputOrdinalFromMonitor( _In_ HMONITOR hMonitor, _Out_ UINT* pOutputOrdinal ); +HRESULT DXUTHandleDeviceRemoved(); +void DXUTUpdateBackBufferDesc(); +void DXUTSetupCursor(); + +// Direct3D 11 +HRESULT DXUTCreateD3D11Views( _In_ ID3D11Device* pd3dDevice, _In_ ID3D11DeviceContext* pd3dDeviceContext, _In_ DXUTDeviceSettings* pDeviceSettings ); +HRESULT DXUTCreate3DEnvironment11(); +HRESULT DXUTReset3DEnvironment11(); +void DXUTUpdateD3D11DeviceStats( _In_ D3D_DRIVER_TYPE DeviceType, _In_ D3D_FEATURE_LEVEL featureLevel, _In_ DXGI_ADAPTER_DESC* pAdapterDesc ); + + +//-------------------------------------------------------------------------------------- +// Internal helper functions +//-------------------------------------------------------------------------------------- +UINT DXUTGetBackBufferWidthFromDS( _In_ DXUTDeviceSettings* pNewDeviceSettings ) +{ + return pNewDeviceSettings->d3d11.sd.BufferDesc.Width; +} +UINT DXUTGetBackBufferHeightFromDS( _In_ DXUTDeviceSettings* pNewDeviceSettings ) +{ + return pNewDeviceSettings->d3d11.sd.BufferDesc.Height; +} +bool DXUTGetIsWindowedFromDS( _In_ DXUTDeviceSettings* pNewDeviceSettings ) +{ + if (!pNewDeviceSettings) + return true; + + return pNewDeviceSettings->d3d11.sd.Windowed ? true : false; +} + + +//-------------------------------------------------------------------------------------- +// External state access functions +//-------------------------------------------------------------------------------------- +bool WINAPI DXUTGetMSAASwapChainCreated() +{ + DXUTDeviceSettings *psettings = GetDXUTState().GetCurrentDeviceSettings(); + if ( !psettings ) + return false; + return (psettings->d3d11.sd.SampleDesc.Count > 1); +} +D3D_FEATURE_LEVEL WINAPI DXUTGetD3D11DeviceFeatureLevel() { return GetDXUTState().GetD3D11FeatureLevel(); } +IDXGISwapChain* WINAPI DXUTGetDXGISwapChain() { return GetDXUTState().GetDXGISwapChain(); } +ID3D11RenderTargetView* WINAPI DXUTGetD3D11RenderTargetView() { return GetDXUTState().GetD3D11RenderTargetView(); } +ID3D11DepthStencilView* WINAPI DXUTGetD3D11DepthStencilView() { return GetDXUTState().GetD3D11DepthStencilView(); } +const DXGI_SURFACE_DESC* WINAPI DXUTGetDXGIBackBufferSurfaceDesc() { return GetDXUTState().GetBackBufferSurfaceDescDXGI(); } +HINSTANCE WINAPI DXUTGetHINSTANCE() { return GetDXUTState().GetHInstance(); } +HWND WINAPI DXUTGetHWND() { return DXUTIsWindowed() ? GetDXUTState().GetHWNDDeviceWindowed() : GetDXUTState().GetHWNDDeviceFullScreen(); } +HWND WINAPI DXUTGetHWNDFocus() { return GetDXUTState().GetHWNDFocus(); } +HWND WINAPI DXUTGetHWNDDeviceFullScreen() { return GetDXUTState().GetHWNDDeviceFullScreen(); } +HWND WINAPI DXUTGetHWNDDeviceWindowed() { return GetDXUTState().GetHWNDDeviceWindowed(); } +RECT WINAPI DXUTGetWindowClientRect() { RECT rc; GetClientRect( DXUTGetHWND(), &rc ); return rc; } +LONG WINAPI DXUTGetWindowWidth() { RECT rc = DXUTGetWindowClientRect(); return ((LONG)rc.right - rc.left); } +LONG WINAPI DXUTGetWindowHeight() { RECT rc = DXUTGetWindowClientRect(); return ((LONG)rc.bottom - rc.top); } +RECT WINAPI DXUTGetWindowClientRectAtModeChange() { RECT rc = { 0, 0, static_cast( GetDXUTState().GetWindowBackBufferWidthAtModeChange() ), static_cast( GetDXUTState().GetWindowBackBufferHeightAtModeChange() ) }; return rc; } +RECT WINAPI DXUTGetFullsceenClientRectAtModeChange() { RECT rc = { 0, 0, static_cast( GetDXUTState().GetFullScreenBackBufferWidthAtModeChange() ), static_cast( GetDXUTState().GetFullScreenBackBufferHeightAtModeChange() ) }; return rc; } +double WINAPI DXUTGetTime() { return GetDXUTState().GetTime(); } +float WINAPI DXUTGetElapsedTime() { return GetDXUTState().GetElapsedTime(); } +float WINAPI DXUTGetFPS() { return GetDXUTState().GetFPS(); } +LPCWSTR WINAPI DXUTGetWindowTitle() { return GetDXUTState().GetWindowTitle(); } +LPCWSTR WINAPI DXUTGetDeviceStats() { return GetDXUTState().GetDeviceStats(); } +bool WINAPI DXUTIsRenderingPaused() { return GetDXUTState().GetPauseRenderingCount() > 0; } +bool WINAPI DXUTIsTimePaused() { return GetDXUTState().GetPauseTimeCount() > 0; } +bool WINAPI DXUTIsActive() { return GetDXUTState().GetActive(); } +int WINAPI DXUTGetExitCode() { return GetDXUTState().GetExitCode(); } +bool WINAPI DXUTGetShowMsgBoxOnError() { return GetDXUTState().GetShowMsgBoxOnError(); } +bool WINAPI DXUTGetAutomation() { return GetDXUTState().GetAutomation(); } +bool WINAPI DXUTIsWindowed() { return DXUTGetIsWindowedFromDS( GetDXUTState().GetCurrentDeviceSettings() ); } +bool WINAPI DXUTIsInGammaCorrectMode() { return GetDXUTState().GetIsInGammaCorrectMode(); } +IDXGIFactory1* WINAPI DXUTGetDXGIFactory() { DXUTDelayLoadDXGI(); return GetDXUTState().GetDXGIFactory(); } + +ID3D11Device* WINAPI DXUTGetD3D11Device() { return GetDXUTState().GetD3D11Device(); } +ID3D11DeviceContext* WINAPI DXUTGetD3D11DeviceContext() { return GetDXUTState().GetD3D11DeviceContext(); } +ID3D11Device1* WINAPI DXUTGetD3D11Device1() { return GetDXUTState().GetD3D11Device1(); } +ID3D11DeviceContext1* WINAPI DXUTGetD3D11DeviceContext1() { return GetDXUTState().GetD3D11DeviceContext1(); } + +ID3D11Device2* WINAPI DXUTGetD3D11Device2() { return GetDXUTState().GetD3D11Device2(); } +ID3D11DeviceContext2* WINAPI DXUTGetD3D11DeviceContext2() { return GetDXUTState().GetD3D11DeviceContext2(); } + +#ifdef USE_DIRECT3D11_3 +ID3D11Device3* WINAPI DXUTGetD3D11Device3() { return GetDXUTState().GetD3D11Device3(); } +ID3D11DeviceContext3* WINAPI DXUTGetD3D11DeviceContext3() { return GetDXUTState().GetD3D11DeviceContext3(); } +#endif + +#ifdef USE_DIRECT3D11_4 +ID3D11Device4* WINAPI DXUTGetD3D11Device4() { return GetDXUTState().GetD3D11Device4(); } +ID3D11DeviceContext4* WINAPI DXUTGetD3D11DeviceContext4() { return GetDXUTState().GetD3D11DeviceContext4(); } +#endif + +//-------------------------------------------------------------------------------------- +// External callback setup functions +//-------------------------------------------------------------------------------------- + +// General callbacks +void WINAPI DXUTSetCallbackDeviceChanging( _In_ LPDXUTCALLBACKMODIFYDEVICESETTINGS pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetModifyDeviceSettingsFunc( pCallback ); GetDXUTState().SetModifyDeviceSettingsFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackDeviceRemoved( _In_ LPDXUTCALLBACKDEVICEREMOVED pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetDeviceRemovedFunc( pCallback ); GetDXUTState().SetDeviceRemovedFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackFrameMove( _In_ LPDXUTCALLBACKFRAMEMOVE pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetFrameMoveFunc( pCallback ); GetDXUTState().SetFrameMoveFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackKeyboard( _In_ LPDXUTCALLBACKKEYBOARD pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetKeyboardFunc( pCallback ); GetDXUTState().SetKeyboardFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackMouse( _In_ LPDXUTCALLBACKMOUSE pCallback, bool bIncludeMouseMove, _In_opt_ void* pUserContext ) { GetDXUTState().SetMouseFunc( pCallback ); GetDXUTState().SetNotifyOnMouseMove( bIncludeMouseMove ); GetDXUTState().SetMouseFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackMsgProc( _In_ LPDXUTCALLBACKMSGPROC pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetWindowMsgFunc( pCallback ); GetDXUTState().SetWindowMsgFuncUserContext( pUserContext ); } + +// Direct3D 11 callbacks +void WINAPI DXUTSetCallbackD3D11DeviceAcceptable( _In_ LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetIsD3D11DeviceAcceptableFunc( pCallback ); GetDXUTState().SetIsD3D11DeviceAcceptableFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackD3D11DeviceCreated( _In_ LPDXUTCALLBACKD3D11DEVICECREATED pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetD3D11DeviceCreatedFunc( pCallback ); GetDXUTState().SetD3D11DeviceCreatedFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackD3D11SwapChainResized( _In_ LPDXUTCALLBACKD3D11SWAPCHAINRESIZED pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetD3D11SwapChainResizedFunc( pCallback ); GetDXUTState().SetD3D11SwapChainResizedFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackD3D11FrameRender( _In_ LPDXUTCALLBACKD3D11FRAMERENDER pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetD3D11FrameRenderFunc( pCallback ); GetDXUTState().SetD3D11FrameRenderFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackD3D11SwapChainReleasing( _In_ LPDXUTCALLBACKD3D11SWAPCHAINRELEASING pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetD3D11SwapChainReleasingFunc( pCallback ); GetDXUTState().SetD3D11SwapChainReleasingFuncUserContext( pUserContext ); } +void WINAPI DXUTSetCallbackD3D11DeviceDestroyed( _In_ LPDXUTCALLBACKD3D11DEVICEDESTROYED pCallback, _In_opt_ void* pUserContext ) { GetDXUTState().SetD3D11DeviceDestroyedFunc( pCallback ); GetDXUTState().SetD3D11DeviceDestroyedFuncUserContext( pUserContext ); } +void DXUTGetCallbackD3D11DeviceAcceptable( _In_ LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE* ppCallback, _Outptr_ void** ppUserContext ) { *ppCallback = GetDXUTState().GetIsD3D11DeviceAcceptableFunc(); *ppUserContext = GetDXUTState().GetIsD3D11DeviceAcceptableFuncUserContext(); } + + +//-------------------------------------------------------------------------------------- +// Optionally parses the command line and sets if default hotkeys are handled +// +// Possible command line parameters are: +// -forcefeaturelevel:fl forces app to use a specified direct3D11 feature level +// -screenshotexit:filename save a screenshot to the filename.bmp and exit. +// -adapter:# forces app to use this adapter # (fails if the adapter doesn't exist) +// -output:# forces app to use a particular output on the adapter (fails if the output doesn't exist) +// -windowed forces app to start windowed +// -fullscreen forces app to start full screen +// -forcehal forces app to use HAL (fails if HAL doesn't exist) +// -forceref forces app to use REF (fails if REF doesn't exist) +// -forcewarp forces app to use WARP (fails if WARP doesn't exist) +// -forcevsync:# if # is 0, then vsync is disabled +// -width:# forces app to use # for width. for full screen, it will pick the closest possible supported mode +// -height:# forces app to use # for height. for full screen, it will pick the closest possible supported mode +// -startx:# forces app to use # for the x coord of the window position for windowed mode +// -starty:# forces app to use # for the y coord of the window position for windowed mode +// -constantframetime:# forces app to use constant frame time, where # is the time/frame in seconds +// -quitafterframe:x forces app to quit after # frames +// -noerrormsgboxes prevents the display of message boxes generated by the framework so the application can be run without user interaction +// -nostats prevents the display of the stats +// -automation a hint to other components that automation is active +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT WINAPI DXUTInit( bool bParseCommandLine, + bool bShowMsgBoxOnError, + WCHAR* strExtraCommandLineParams, + bool bThreadSafeDXUT ) +{ + g_bThreadSafe = bThreadSafeDXUT; + + HRESULT hr = CoInitializeEx( nullptr, COINIT_MULTITHREADED ); + if ( FAILED(hr) ) + return hr; + + GetDXUTState().SetDXUTInitCalled( true ); + + // Not always needed, but lets the app create GDI dialogs + InitCommonControls(); + + // Save the current sticky/toggle/filter key settings so DXUT can restore them later + STICKYKEYS sk = {sizeof(STICKYKEYS), 0}; + if ( !SystemParametersInfo(SPI_GETSTICKYKEYS, sizeof(STICKYKEYS), &sk, 0) ) + memset( &sk, 0, sizeof(sk) ); + GetDXUTState().SetStartupStickyKeys( sk ); + + TOGGLEKEYS tk = {sizeof(TOGGLEKEYS), 0}; + if ( !SystemParametersInfo(SPI_GETTOGGLEKEYS, sizeof(TOGGLEKEYS), &tk, 0) ) + memset( &tk, 0, sizeof(tk) ); + GetDXUTState().SetStartupToggleKeys( tk ); + + FILTERKEYS fk = {sizeof(FILTERKEYS), 0}; + if ( !SystemParametersInfo(SPI_GETFILTERKEYS, sizeof(FILTERKEYS), &fk, 0) ) + memset( &fk, 0, sizeof(fk) ); + GetDXUTState().SetStartupFilterKeys( fk ); + + GetDXUTState().SetShowMsgBoxOnError( bShowMsgBoxOnError ); + + if( bParseCommandLine ) + DXUTParseCommandLine( GetCommandLine() ); + if( strExtraCommandLineParams ) + DXUTParseCommandLine( strExtraCommandLineParams, false ); + + // Reset the timer + DXUTGetGlobalTimer()->Reset(); + + GetDXUTState().SetDXUTInited( true ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Parses the command line for parameters. See DXUTInit() for list +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DXUTParseCommandLine(WCHAR* strCommandLine, + bool bIgnoreFirstCommand ) +{ + WCHAR* strCmdLine; + WCHAR strFlag[MAX_PATH]; + + int nNumArgs; + auto pstrArgList = CommandLineToArgvW( strCommandLine, &nNumArgs ); + int iArgStart = 0; + if( bIgnoreFirstCommand ) + iArgStart = 1; + for( int iArg = iArgStart; iArg < nNumArgs; iArg++ ) + { + strCmdLine = pstrArgList[iArg]; + + // Handle flag args + if( *strCmdLine == L'/' || *strCmdLine == L'-' ) + { + strCmdLine++; + + if( DXUTIsNextArg( strCmdLine, L"forcefeaturelevel" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { +#if defined(USE_DIRECT3D11_3) || defined(USE_DIRECT3D11_4) + if (_wcsnicmp(strFlag, L"D3D_FEATURE_LEVEL_12_1", MAX_PATH) == 0) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_12_1); + } + else if (_wcsnicmp(strFlag, L"D3D_FEATURE_LEVEL_12_0", MAX_PATH) == 0) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_12_0); + } + else +#endif + if (_wcsnicmp( strFlag, L"D3D_FEATURE_LEVEL_11_1", MAX_PATH) == 0 ) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_11_1); + }else if (_wcsnicmp( strFlag, L"D3D_FEATURE_LEVEL_11_0", MAX_PATH) == 0 ) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_11_0); + }else if (_wcsnicmp( strFlag, L"D3D_FEATURE_LEVEL_10_1", MAX_PATH) == 0 ) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_10_1); + }else if (_wcsnicmp( strFlag, L"D3D_FEATURE_LEVEL_10_0", MAX_PATH) == 0 ) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_10_0); + }else if (_wcsnicmp( strFlag, L"D3D_FEATURE_LEVEL_9_3", MAX_PATH) == 0 ) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_9_3); + }else if (_wcsnicmp( strFlag, L"D3D_FEATURE_LEVEL_9_2", MAX_PATH) == 0 ) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_9_2); + }else if (_wcsnicmp( strFlag, L"D3D_FEATURE_LEVEL_9_1", MAX_PATH) == 0 ) { + GetDXUTState().SetOverrideForceFeatureLevel(D3D_FEATURE_LEVEL_9_1); + } + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"adapter" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + int nAdapter = _wtoi( strFlag ); + GetDXUTState().SetOverrideAdapterOrdinal( nAdapter ); + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"windowed" ) ) + { + GetDXUTState().SetOverrideWindowed( true ); + continue; + } + + if( DXUTIsNextArg( strCmdLine, L"output" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + int Output = _wtoi( strFlag ); + GetDXUTState().SetOverrideOutput( Output ); + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"fullscreen" ) ) + { + GetDXUTState().SetOverrideFullScreen( true ); + continue; + } + + if( DXUTIsNextArg( strCmdLine, L"forcehal" ) ) + { + GetDXUTState().SetOverrideForceHAL( true ); + continue; + } + if( DXUTIsNextArg( strCmdLine, L"screenshotexit" ) ) { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + GetDXUTState().SetExitAfterScreenShot( true ); + GetDXUTState().SetSaveScreenShot( true ); + swprintf_s( GetDXUTState().GetScreenShotName(), 256, L"%ls.bmp", strFlag ); + continue; + } + } + if( DXUTIsNextArg( strCmdLine, L"forceref" ) ) + { + GetDXUTState().SetOverrideForceREF( true ); + continue; + } + if( DXUTIsNextArg( strCmdLine, L"forcewarp" ) ) + { + GetDXUTState().SetOverrideForceWARP( true ); + continue; + } + + if( DXUTIsNextArg( strCmdLine, L"forcevsync" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + int nOn = _wtoi( strFlag ); + GetDXUTState().SetOverrideForceVsync( nOn ); + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"width" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + int nWidth = _wtoi( strFlag ); + GetDXUTState().SetOverrideWidth( nWidth ); + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"height" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + int nHeight = _wtoi( strFlag ); + GetDXUTState().SetOverrideHeight( nHeight ); + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"startx" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + int nX = _wtoi( strFlag ); + GetDXUTState().SetOverrideStartX( nX ); + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"starty" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + int nY = _wtoi( strFlag ); + GetDXUTState().SetOverrideStartY( nY ); + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"constantframetime" ) ) + { + float fTimePerFrame; + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + fTimePerFrame = ( float )wcstod( strFlag, nullptr ); + else + fTimePerFrame = 0.0333f; + GetDXUTState().SetOverrideConstantFrameTime( true ); + GetDXUTState().SetOverrideConstantTimePerFrame( fTimePerFrame ); + DXUTSetConstantFrameTime( true, fTimePerFrame ); + continue; + } + + if( DXUTIsNextArg( strCmdLine, L"quitafterframe" ) ) + { + if( DXUTGetCmdParam( strCmdLine, strFlag, MAX_PATH ) ) + { + int nFrame = _wtoi( strFlag ); + GetDXUTState().SetOverrideQuitAfterFrame( nFrame ); + continue; + } + } + + if( DXUTIsNextArg( strCmdLine, L"noerrormsgboxes" ) ) + { + GetDXUTState().SetShowMsgBoxOnError( false ); + continue; + } + + if( DXUTIsNextArg( strCmdLine, L"nostats" ) ) + { + GetDXUTState().SetNoStats( true ); + continue; + } + + if( DXUTIsNextArg( strCmdLine, L"automation" ) ) + { + GetDXUTState().SetAutomation( true ); + continue; + } + } + + // Unrecognized flag + wcscpy_s( strFlag, MAX_PATH, strCmdLine ); + WCHAR* strSpace = strFlag; + while( *strSpace && ( *strSpace > L' ' ) ) + strSpace++; + *strSpace = 0; + + DXUTOutputDebugString( L"Unrecognized flag: %ls", strFlag ); + strCmdLine += wcslen( strFlag ); + } + + LocalFree( pstrArgList ); +} + + +//-------------------------------------------------------------------------------------- +// Helper function for DXUTParseCommandLine +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DXUTIsNextArg( WCHAR*& strCmdLine, const WCHAR* strArg ) +{ + size_t nArgLen = wcslen( strArg ); + size_t nCmdLen = wcslen( strCmdLine ); + + if( nCmdLen >= nArgLen && + _wcsnicmp( strCmdLine, strArg, nArgLen ) == 0 && + ( strCmdLine[nArgLen] == 0 || strCmdLine[nArgLen] == L':' ) ) + { + strCmdLine += nArgLen; + return true; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +// Helper function for DXUTParseCommandLine. Updates strCmdLine and strFlag +// Example: if strCmdLine=="-width:1024 -forceref" +// then after: strCmdLine==" -forceref" and strFlag=="1024" +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DXUTGetCmdParam( WCHAR*& strCmdLine, WCHAR* strFlag, int cchDest ) +{ + if( *strCmdLine == L':' ) + { + strCmdLine++; // Skip ':' + + // Place nul terminator in strFlag after current token + wcscpy_s( strFlag, cchDest, strCmdLine ); + + WCHAR* strSpace = strFlag; + int count = 0; + while( *strSpace && ( *strSpace > L' ' ) && (count < cchDest) ) + { + ++strSpace; + ++count; + } + *strSpace = 0; + + // Update strCmdLine + strCmdLine += wcslen( strFlag ); + return true; + } + else + { + strFlag[0] = 0; + return false; + } +} + + +//-------------------------------------------------------------------------------------- +// Creates a window with the specified window title, icon, menu, and +// starting position. If DXUTInit() has not already been called, it will +// call it with the default parameters. Instead of calling this, you can +// call DXUTSetWindow() to use an existing window. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT WINAPI DXUTCreateWindow( const WCHAR* strWindowTitle, HINSTANCE hInstance, + HICON hIcon, HMENU hMenu, int x, int y ) +{ + HRESULT hr; + + // Not allowed to call this from inside the device callbacks + if( GetDXUTState().GetInsideDeviceCallback() ) + return DXUT_ERR_MSGBOX( L"DXUTCreateWindow", E_FAIL ); + + GetDXUTState().SetWindowCreateCalled( true ); + + if( !GetDXUTState().GetDXUTInited() ) + { + // If DXUTInit() was already called and failed, then fail. + // DXUTInit() must first succeed for this function to succeed + if( GetDXUTState().GetDXUTInitCalled() ) + return E_FAIL; + + // If DXUTInit() hasn't been called, then automatically call it + // with default params + hr = DXUTInit(); + if( FAILED( hr ) ) + return hr; + } + + if( !DXUTGetHWNDFocus() ) + { + if( !hInstance ) + hInstance = ( HINSTANCE )GetModuleHandle( nullptr ); + GetDXUTState().SetHInstance( hInstance ); + + WCHAR szExePath[MAX_PATH]; + GetModuleFileName( nullptr, szExePath, MAX_PATH ); + if( !hIcon ) // If the icon is NULL, then use the first one found in the exe + hIcon = ExtractIcon( hInstance, szExePath, 0 ); + + // Register the windows class + WNDCLASS wndClass; + wndClass.style = CS_DBLCLKS; + wndClass.lpfnWndProc = DXUTStaticWndProc; + wndClass.cbClsExtra = 0; + wndClass.cbWndExtra = 0; + wndClass.hInstance = hInstance; + wndClass.hIcon = hIcon; + wndClass.hCursor = LoadCursor( nullptr, IDC_ARROW ); + wndClass.hbrBackground = ( HBRUSH )GetStockObject( BLACK_BRUSH ); + wndClass.lpszMenuName = nullptr; + wndClass.lpszClassName = L"Direct3DWindowClass"; + + if( !RegisterClass( &wndClass ) ) + { + DWORD dwError = GetLastError(); + if( dwError != ERROR_CLASS_ALREADY_EXISTS ) + return DXUT_ERR_MSGBOX( L"RegisterClass", HRESULT_FROM_WIN32(dwError) ); + } + + // Override the window's initial & size position if there were cmd line args + if( GetDXUTState().GetOverrideStartX() != -1 ) + x = GetDXUTState().GetOverrideStartX(); + if( GetDXUTState().GetOverrideStartY() != -1 ) + y = GetDXUTState().GetOverrideStartY(); + + GetDXUTState().SetWindowCreatedWithDefaultPositions( false ); + if( x == CW_USEDEFAULT && y == CW_USEDEFAULT ) + GetDXUTState().SetWindowCreatedWithDefaultPositions( true ); + + // Find the window's initial size, but it might be changed later + int nDefaultWidth = 800; + int nDefaultHeight = 600; + if( GetDXUTState().GetOverrideWidth() != 0 ) + nDefaultWidth = GetDXUTState().GetOverrideWidth(); + if( GetDXUTState().GetOverrideHeight() != 0 ) + nDefaultHeight = GetDXUTState().GetOverrideHeight(); + + RECT rc; + SetRect( &rc, 0, 0, nDefaultWidth, nDefaultHeight ); + AdjustWindowRect( &rc, WS_OVERLAPPEDWINDOW, ( hMenu ) ? true : false ); + + WCHAR* strCachedWindowTitle = GetDXUTState().GetWindowTitle(); + wcscpy_s( strCachedWindowTitle, 256, strWindowTitle ); + + // Create the render window + HWND hWnd = CreateWindow( L"Direct3DWindowClass", strWindowTitle, WS_OVERLAPPEDWINDOW, + x, y, ( rc.right - rc.left ), ( rc.bottom - rc.top ), 0, + hMenu, hInstance, 0 ); + if( !hWnd ) + { + DWORD dwError = GetLastError(); + return DXUT_ERR_MSGBOX( L"CreateWindow", HRESULT_FROM_WIN32(dwError) ); + } + + GetDXUTState().SetWindowCreated( true ); + GetDXUTState().SetHWNDFocus( hWnd ); + GetDXUTState().SetHWNDDeviceFullScreen( hWnd ); + GetDXUTState().SetHWNDDeviceWindowed( hWnd ); + } + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Sets a previously created window for the framework to use. If DXUTInit() +// has not already been called, it will call it with the default parameters. +// Instead of calling this, you can call DXUTCreateWindow() to create a new window. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT WINAPI DXUTSetWindow( HWND hWndFocus, HWND hWndDeviceFullScreen, HWND hWndDeviceWindowed, bool bHandleMessages ) +{ + HRESULT hr; + + // Not allowed to call this from inside the device callbacks + if( GetDXUTState().GetInsideDeviceCallback() ) + return DXUT_ERR_MSGBOX( L"DXUTCreateWindow", E_FAIL ); + + GetDXUTState().SetWindowCreateCalled( true ); + + // To avoid confusion, we do not allow any HWND to be nullptr here. The + // caller must pass in valid HWND for all three parameters. The same + // HWND may be used for more than one parameter. + if( !hWndFocus || !hWndDeviceFullScreen || !hWndDeviceWindowed ) + return DXUT_ERR_MSGBOX( L"DXUTSetWindow", E_INVALIDARG ); + + // If subclassing the window, set the pointer to the local window procedure + if( bHandleMessages ) + { + // Switch window procedures + LONG_PTR nResult = SetWindowLongPtr( hWndFocus, GWLP_WNDPROC, (LONG_PTR)DXUTStaticWndProc ); + + DWORD dwError = GetLastError(); + if( nResult == 0 ) + return DXUT_ERR_MSGBOX( L"SetWindowLongPtr", HRESULT_FROM_WIN32(dwError) ); + } + + if( !GetDXUTState().GetDXUTInited() ) + { + // If DXUTInit() was already called and failed, then fail. + // DXUTInit() must first succeed for this function to succeed + if( GetDXUTState().GetDXUTInitCalled() ) + return E_FAIL; + + // If DXUTInit() hasn't been called, then automatically call it + // with default params + hr = DXUTInit(); + if( FAILED( hr ) ) + return hr; + } + + WCHAR* strCachedWindowTitle = GetDXUTState().GetWindowTitle(); + GetWindowText( hWndFocus, strCachedWindowTitle, 255 ); + strCachedWindowTitle[255] = 0; + + HINSTANCE hInstance = ( HINSTANCE )( LONG_PTR )GetWindowLongPtr( hWndFocus, GWLP_HINSTANCE ); + GetDXUTState().SetHInstance( hInstance ); + GetDXUTState().SetWindowCreatedWithDefaultPositions( false ); + GetDXUTState().SetWindowCreated( true ); + GetDXUTState().SetHWNDFocus( hWndFocus ); + GetDXUTState().SetHWNDDeviceFullScreen( hWndDeviceFullScreen ); + GetDXUTState().SetHWNDDeviceWindowed( hWndDeviceWindowed ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Handles window messages +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +LRESULT CALLBACK DXUTStaticWndProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + + // Consolidate the keyboard messages and pass them to the app's keyboard callback + if( uMsg == WM_KEYDOWN || + uMsg == WM_SYSKEYDOWN || + uMsg == WM_KEYUP || + uMsg == WM_SYSKEYUP ) + { + bool bKeyDown = ( uMsg == WM_KEYDOWN || uMsg == WM_SYSKEYDOWN ); + DWORD dwMask = ( 1 << 29 ); + bool bAltDown = ( ( lParam & dwMask ) != 0 ); + + bool* bKeys = GetDXUTState().GetKeys(); + bKeys[ ( BYTE )( wParam & 0xFF ) ] = bKeyDown; + + LPDXUTCALLBACKKEYBOARD pCallbackKeyboard = GetDXUTState().GetKeyboardFunc(); + if( pCallbackKeyboard ) + pCallbackKeyboard( ( UINT )wParam, bKeyDown, bAltDown, GetDXUTState().GetKeyboardFuncUserContext() ); + } + + // Consolidate the mouse button messages and pass them to the app's mouse callback + if( uMsg == WM_LBUTTONDOWN || + uMsg == WM_LBUTTONUP || + uMsg == WM_LBUTTONDBLCLK || + uMsg == WM_MBUTTONDOWN || + uMsg == WM_MBUTTONUP || + uMsg == WM_MBUTTONDBLCLK || + uMsg == WM_RBUTTONDOWN || + uMsg == WM_RBUTTONUP || + uMsg == WM_RBUTTONDBLCLK || + uMsg == WM_XBUTTONDOWN || + uMsg == WM_XBUTTONUP || + uMsg == WM_XBUTTONDBLCLK || + uMsg == WM_MOUSEWHEEL || + ( GetDXUTState().GetNotifyOnMouseMove() && uMsg == WM_MOUSEMOVE ) ) + { + int xPos = ( short )LOWORD( lParam ); + int yPos = ( short )HIWORD( lParam ); + + if( uMsg == WM_MOUSEWHEEL ) + { + // WM_MOUSEWHEEL passes screen mouse coords + // so convert them to client coords + POINT pt; + pt.x = xPos; pt.y = yPos; + ScreenToClient( hWnd, &pt ); + xPos = pt.x; yPos = pt.y; + } + + int nMouseWheelDelta = 0; + if( uMsg == WM_MOUSEWHEEL ) + nMouseWheelDelta = ( short )HIWORD( wParam ); + + int nMouseButtonState = LOWORD( wParam ); + bool bLeftButton = ( ( nMouseButtonState & MK_LBUTTON ) != 0 ); + bool bRightButton = ( ( nMouseButtonState & MK_RBUTTON ) != 0 ); + bool bMiddleButton = ( ( nMouseButtonState & MK_MBUTTON ) != 0 ); + bool bSideButton1 = ( ( nMouseButtonState & MK_XBUTTON1 ) != 0 ); + bool bSideButton2 = ( ( nMouseButtonState & MK_XBUTTON2 ) != 0 ); + + bool* bMouseButtons = GetDXUTState().GetMouseButtons(); + bMouseButtons[0] = bLeftButton; + bMouseButtons[1] = bMiddleButton; + bMouseButtons[2] = bRightButton; + bMouseButtons[3] = bSideButton1; + bMouseButtons[4] = bSideButton2; + + LPDXUTCALLBACKMOUSE pCallbackMouse = GetDXUTState().GetMouseFunc(); + if( pCallbackMouse ) + pCallbackMouse( bLeftButton, bRightButton, bMiddleButton, bSideButton1, bSideButton2, nMouseWheelDelta, + xPos, yPos, GetDXUTState().GetMouseFuncUserContext() ); + } + + // TODO - WM_POINTER for touch when on Windows 8.0 + + // Pass all messages to the app's MsgProc callback, and don't + // process further messages if the apps says not to. + LPDXUTCALLBACKMSGPROC pCallbackMsgProc = GetDXUTState().GetWindowMsgFunc(); + if( pCallbackMsgProc ) + { + bool bNoFurtherProcessing = false; + LRESULT nResult = pCallbackMsgProc( hWnd, uMsg, wParam, lParam, &bNoFurtherProcessing, + GetDXUTState().GetWindowMsgFuncUserContext() ); + if( bNoFurtherProcessing ) + return nResult; + } + + switch( uMsg ) + { + case WM_PAINT: + { + // Handle paint messages when the app is paused + if( DXUTIsRenderingPaused() && + GetDXUTState().GetDeviceObjectsCreated() && GetDXUTState().GetDeviceObjectsReset() ) + { + HRESULT hr; + double fTime = DXUTGetTime(); + float fElapsedTime = DXUTGetElapsedTime(); + + { + auto pd3dDevice = DXUTGetD3D11Device(); + auto pDeferred = DXUTGetD3D11DeviceContext(); + if( pd3dDevice ) + { + LPDXUTCALLBACKD3D11FRAMERENDER pCallbackFrameRender = GetDXUTState().GetD3D11FrameRenderFunc(); + if( pCallbackFrameRender && + !GetDXUTState().GetRenderingOccluded() ) + { + pCallbackFrameRender( pd3dDevice,pDeferred, fTime, fElapsedTime, + GetDXUTState().GetD3D11FrameRenderFuncUserContext() ); + } + + DWORD dwFlags = 0; + if( GetDXUTState().GetRenderingOccluded() ) + dwFlags = DXGI_PRESENT_TEST; + else + dwFlags = GetDXUTState().GetCurrentDeviceSettings()->d3d11.PresentFlags; + + auto pSwapChain = DXUTGetDXGISwapChain(); + hr = pSwapChain->Present( 0, dwFlags ); + if( DXGI_STATUS_OCCLUDED == hr ) + { + // There is a window covering our entire rendering area. + // Don't render until we're visible again. + GetDXUTState().SetRenderingOccluded( true ); + } + else if( SUCCEEDED( hr ) ) + { + if( GetDXUTState().GetRenderingOccluded() ) + { + // Now that we're no longer occluded + // allow us to render again + GetDXUTState().SetRenderingOccluded( false ); + } + } + } + } + } + break; + } + + case WM_SIZE: + + if( SIZE_MINIMIZED == wParam ) + { + DXUTPause( true, true ); // Pause while we're minimized + + GetDXUTState().SetMinimized( true ); + GetDXUTState().SetMaximized( false ); + } + else + { + RECT rcCurrentClient; + GetClientRect( DXUTGetHWND(), &rcCurrentClient ); + if( rcCurrentClient.top == 0 && rcCurrentClient.bottom == 0 ) + { + // Rapidly clicking the task bar to minimize and restore a window + // can cause a WM_SIZE message with SIZE_RESTORED when + // the window has actually become minimized due to rapid change + // so just ignore this message + } + else if( SIZE_MAXIMIZED == wParam ) + { + if( GetDXUTState().GetMinimized() ) + DXUTPause( false, false ); // Unpause since we're no longer minimized + GetDXUTState().SetMinimized( false ); + GetDXUTState().SetMaximized( true ); + DXUTCheckForWindowSizeChange(); + DXUTCheckForWindowChangingMonitors(); + } + else if( SIZE_RESTORED == wParam ) + { + //DXUTCheckForDXGIFullScreenSwitch(); + if( GetDXUTState().GetMaximized() ) + { + GetDXUTState().SetMaximized( false ); + DXUTCheckForWindowSizeChange(); + DXUTCheckForWindowChangingMonitors(); + } + else if( GetDXUTState().GetMinimized() ) + { + DXUTPause( false, false ); // Unpause since we're no longer minimized + GetDXUTState().SetMinimized( false ); + DXUTCheckForWindowSizeChange(); + DXUTCheckForWindowChangingMonitors(); + } + else if( GetDXUTState().GetInSizeMove() ) + { + // If we're neither maximized nor minimized, the window size + // is changing by the user dragging the window edges. In this + // case, we don't reset the device yet -- we wait until the + // user stops dragging, and a WM_EXITSIZEMOVE message comes. + } + else + { + // This WM_SIZE come from resizing the window via an API like SetWindowPos() so + // resize and reset the device now. + DXUTCheckForWindowSizeChange(); + DXUTCheckForWindowChangingMonitors(); + } + } + } + break; + + case WM_GETMINMAXINFO: + ( ( MINMAXINFO* )lParam )->ptMinTrackSize.x = DXUT_MIN_WINDOW_SIZE_X; + ( ( MINMAXINFO* )lParam )->ptMinTrackSize.y = DXUT_MIN_WINDOW_SIZE_Y; + break; + + case WM_ENTERSIZEMOVE: + // Halt frame movement while the app is sizing or moving + DXUTPause( true, true ); + GetDXUTState().SetInSizeMove( true ); + break; + + case WM_EXITSIZEMOVE: + DXUTPause( false, false ); + DXUTCheckForWindowSizeChange(); + DXUTCheckForWindowChangingMonitors(); + GetDXUTState().SetInSizeMove( false ); + break; + + case WM_SETCURSOR: + if( DXUTIsActive() && !DXUTIsWindowed() ) + { + if( !GetDXUTState().GetShowCursorWhenFullScreen() ) + SetCursor( nullptr ); + + return true; // prevent Windows from setting cursor to window class cursor + } + break; + + case WM_ACTIVATEAPP: + if( wParam == TRUE && !DXUTIsActive() ) // Handle only if previously not active + { + GetDXUTState().SetActive( true ); + + // Enable controller rumble & input when activating app + DXUTEnableXInput( true ); + + // The GetMinimizedWhileFullscreen() varible is used instead of !DXUTIsWindowed() + // to handle the rare case toggling to windowed mode while the fullscreen application + // is minimized and thus making the pause count wrong + if( GetDXUTState().GetMinimizedWhileFullscreen() ) + { + GetDXUTState().SetMinimizedWhileFullscreen( false ); + + DXUTToggleFullScreen(); + } + + // Upon returning to this app, potentially disable shortcut keys + // (Windows key, accessibility shortcuts) + DXUTAllowShortcutKeys( ( DXUTIsWindowed() ) ? GetDXUTState().GetAllowShortcutKeysWhenWindowed() : + GetDXUTState().GetAllowShortcutKeysWhenFullscreen() ); + + } + else if( wParam == FALSE && DXUTIsActive() ) // Handle only if previously active + { + GetDXUTState().SetActive( false ); + + // Disable any controller rumble & input when de-activating app + DXUTEnableXInput( false ); + + if( !DXUTIsWindowed() ) + { + // Going from full screen to a minimized state + ClipCursor( nullptr ); // don't limit the cursor anymore + GetDXUTState().SetMinimizedWhileFullscreen( true ); + } + + // Restore shortcut keys (Windows key, accessibility shortcuts) to original state + // + // This is important to call here if the shortcuts are disabled, + // because if this is not done then the Windows key will continue to + // be disabled while this app is running which is very bad. + // If the app crashes, the Windows key will return to normal. + DXUTAllowShortcutKeys( true ); + } + break; + + case WM_ENTERMENULOOP: + // Pause the app when menus are displayed + DXUTPause( true, true ); + break; + + case WM_EXITMENULOOP: + DXUTPause( false, false ); + break; + + case WM_MENUCHAR: + // A menu is active and the user presses a key that does not correspond to any mnemonic or accelerator key + // So just ignore and don't beep + return MAKELRESULT( 0, MNC_CLOSE ); + break; + + case WM_NCHITTEST: + // Prevent the user from selecting the menu in full screen mode + if( !DXUTIsWindowed() ) + return HTCLIENT; + break; + + case WM_POWERBROADCAST: + switch( wParam ) + { + case PBT_APMQUERYSUSPEND: + // At this point, the app should save any data for open + // network connections, files, etc., and prepare to go into + // a suspended mode. The app can use the MsgProc callback + // to handle this if desired. + return true; + + case PBT_APMRESUMESUSPEND: + // At this point, the app should recover any data, network + // connections, files, etc., and resume running from when + // the app was suspended. The app can use the MsgProc callback + // to handle this if desired. + + // QPC may lose consistency when suspending, so reset the timer + // upon resume. + DXUTGetGlobalTimer()->Reset(); + GetDXUTState().SetLastStatsUpdateTime( 0 ); + return true; + } + break; + + case WM_SYSCOMMAND: + // Prevent moving/sizing in full screen mode + switch( ( wParam & 0xFFF0 ) ) + { + case SC_MOVE: + case SC_SIZE: + case SC_MAXIMIZE: + case SC_KEYMENU: + if( !DXUTIsWindowed() ) + return 0; + break; + } + break; + + case WM_KEYDOWN: + { + switch( wParam ) + { + case VK_ESCAPE: + { + if( GetDXUTState().GetHandleEscape() ) + SendMessage( hWnd, WM_CLOSE, 0, 0 ); + break; + } + + case VK_PAUSE: + { + if( GetDXUTState().GetHandlePause() ) + { + bool bTimePaused = DXUTIsTimePaused(); + bTimePaused = !bTimePaused; + if( bTimePaused ) + DXUTPause( true, false ); + else + DXUTPause( false, false ); + } + break; + } + } + break; + } + + case WM_CLOSE: + { + HMENU hMenu; + hMenu = GetMenu( hWnd ); + if( hMenu ) + DestroyMenu( hMenu ); + DestroyWindow( hWnd ); + UnregisterClass( L"Direct3DWindowClass", nullptr ); + GetDXUTState().SetHWNDFocus( nullptr ); + GetDXUTState().SetHWNDDeviceFullScreen( nullptr ); + GetDXUTState().SetHWNDDeviceWindowed( nullptr ); + return 0; + } + + case WM_DESTROY: + PostQuitMessage( 0 ); + break; + } + + // Don't allow the F10 key to act as a shortcut to the menu bar + // by not passing these messages to the DefWindowProc only when + // there's no menu present + if( !GetDXUTState().GetCallDefWindowProc() || !GetDXUTState().GetMenu() && + ( uMsg == WM_SYSKEYDOWN || uMsg == WM_SYSKEYUP ) && wParam == VK_F10 ) + return 0; + else + return DefWindowProc( hWnd, uMsg, wParam, lParam ); +} + + +//-------------------------------------------------------------------------------------- +// Handles app's message loop and rendering when idle. If DXUTCreateDevice() +// has not already been called, it will call DXUTCreateWindow() with the default parameters. +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTMainLoop( _In_opt_ HACCEL hAccel ) +{ + HRESULT hr; + + // Not allowed to call this from inside the device callbacks or reenter + if( GetDXUTState().GetInsideDeviceCallback() || GetDXUTState().GetInsideMainloop() ) + { + if( ( GetDXUTState().GetExitCode() == 0 ) || ( GetDXUTState().GetExitCode() == 10 ) ) + GetDXUTState().SetExitCode( 1 ); + return DXUT_ERR_MSGBOX( L"DXUTMainLoop", E_FAIL ); + } + + GetDXUTState().SetInsideMainloop( true ); + + // If DXUTCreateDevice() has not already been called, + // then call DXUTCreateDevice() with the default parameters. + if( !GetDXUTState().GetDeviceCreated() ) + { + if( GetDXUTState().GetDeviceCreateCalled() ) + { + if( ( GetDXUTState().GetExitCode() == 0 ) || ( GetDXUTState().GetExitCode() == 10 ) ) + GetDXUTState().SetExitCode( 1 ); + return E_FAIL; // DXUTCreateDevice() must first succeed for this function to succeed + } + + hr = DXUTCreateDevice(D3D_FEATURE_LEVEL_10_0, true, 800, 600); + if( FAILED( hr ) ) + { + if( ( GetDXUTState().GetExitCode() == 0 ) || ( GetDXUTState().GetExitCode() == 10 ) ) + GetDXUTState().SetExitCode( 1 ); + return hr; + } + } + + HWND hWnd = DXUTGetHWND(); + + // DXUTInit() must have been called and succeeded for this function to proceed + // DXUTCreateWindow() or DXUTSetWindow() must have been called and succeeded for this function to proceed + // DXUTCreateDevice() or DXUTCreateDeviceFromSettings() must have been called and succeeded for this function to proceed + if( !GetDXUTState().GetDXUTInited() || !GetDXUTState().GetWindowCreated() || !GetDXUTState().GetDeviceCreated() ) + { + if( ( GetDXUTState().GetExitCode() == 0 ) || ( GetDXUTState().GetExitCode() == 10 ) ) + GetDXUTState().SetExitCode( 1 ); + return DXUT_ERR_MSGBOX( L"DXUTMainLoop", E_FAIL ); + } + + // Now we're ready to receive and process Windows messages. + bool bGotMsg; + MSG msg; + msg.message = WM_NULL; + PeekMessage( &msg, nullptr, 0U, 0U, PM_NOREMOVE ); + + while( WM_QUIT != msg.message ) + { + // Use PeekMessage() so we can use idle time to render the scene. + bGotMsg = ( PeekMessage( &msg, nullptr, 0U, 0U, PM_REMOVE ) != 0 ); + + if( bGotMsg ) + { + // Translate and dispatch the message + if( !hAccel || !hWnd || + 0 == TranslateAccelerator( hWnd, hAccel, &msg ) ) + { + TranslateMessage( &msg ); + DispatchMessage( &msg ); + } + } + else + { + // Render a frame during idle time (no messages are waiting) + DXUTRender3DEnvironment(); + } + } + + // Cleanup the accelerator table + if( hAccel ) + DestroyAcceleratorTable( hAccel ); + + GetDXUTState().SetInsideMainloop( false ); + + return S_OK; +} + + +//====================================================================================== +//====================================================================================== +// Direct3D section +//====================================================================================== +//====================================================================================== +_Use_decl_annotations_ +HRESULT WINAPI DXUTCreateDevice(D3D_FEATURE_LEVEL reqFL, bool bWindowed, int nSuggestedWidth, int nSuggestedHeight) +{ + HRESULT hr = S_OK; + + // Not allowed to call this from inside the device callbacks + if( GetDXUTState().GetInsideDeviceCallback() ) + return DXUT_ERR_MSGBOX( L"DXUTCreateDevice", E_FAIL ); + + GetDXUTState().SetDeviceCreateCalled( true ); + + // If DXUTCreateWindow() or DXUTSetWindow() has not already been called, + // then call DXUTCreateWindow() with the default parameters. + if( !GetDXUTState().GetWindowCreated() ) + { + // If DXUTCreateWindow() or DXUTSetWindow() was already called and failed, then fail. + // DXUTCreateWindow() or DXUTSetWindow() must first succeed for this function to succeed + if( GetDXUTState().GetWindowCreateCalled() ) + return E_FAIL; + + // If DXUTCreateWindow() or DXUTSetWindow() hasn't been called, then + // automatically call DXUTCreateWindow() with default params + hr = DXUTCreateWindow(); + if( FAILED( hr ) ) + return hr; + } + + DXUTDeviceSettings deviceSettings; + DXUTApplyDefaultDeviceSettings(&deviceSettings); + deviceSettings.MinimumFeatureLevel = reqFL; + deviceSettings.d3d11.sd.BufferDesc.Width = nSuggestedWidth; + deviceSettings.d3d11.sd.BufferDesc.Height = nSuggestedHeight; + deviceSettings.d3d11.sd.Windowed = bWindowed; + + DXUTUpdateDeviceSettingsWithOverrides(&deviceSettings); + + GetDXUTState().SetWindowBackBufferWidthAtModeChange(deviceSettings.d3d11.sd.BufferDesc.Width); + GetDXUTState().SetWindowBackBufferHeightAtModeChange(deviceSettings.d3d11.sd.BufferDesc.Height); + GetDXUTState().SetFullScreenBackBufferWidthAtModeChange(deviceSettings.d3d11.sd.BufferDesc.Width); + GetDXUTState().SetFullScreenBackBufferHeightAtModeChange(deviceSettings.d3d11.sd.BufferDesc.Height); + + // Change to a Direct3D device created from the new device settings. + // If there is an existing device, then either reset or recreated the scene + hr = DXUTChangeDevice( &deviceSettings, true ); + + if ( hr == DXUTERR_NODIRECT3D && GetDXUTState().GetMessageWhenD3D11NotAvailable() ) + { + OSVERSIONINFOEX osv; + memset( &osv, 0, sizeof(osv) ); + osv.dwOSVersionInfoSize = sizeof(osv); +#pragma warning( suppress : 4996 28159 ) + GetVersionEx( (LPOSVERSIONINFO)&osv ); + + if ( ( osv.dwMajorVersion > 6 ) + || ( osv.dwMajorVersion == 6 && osv.dwMinorVersion >= 1 ) + || ( osv.dwMajorVersion == 6 && osv.dwMinorVersion == 0 && osv.dwBuildNumber > 6002 ) ) + { + MessageBox( 0, L"Direct3D 11 components were not found.", L"Error", MB_ICONEXCLAMATION ); + // This should not happen, but is here for completeness as the system could be + // corrupted or some future OS version could pull D3D11.DLL for some reason + } + else if ( osv.dwMajorVersion == 6 && osv.dwMinorVersion == 0 && osv.dwBuildNumber == 6002 ) + { + MessageBox( 0, L"Direct3D 11 components were not found, but are available for"\ + L" this version of Windows.\n"\ + L"For details see Microsoft Knowledge Base Article #971644\n"\ + L"http://go.microsoft.com/fwlink/?LinkId=160189", L"Error", MB_ICONEXCLAMATION ); + } + else if ( osv.dwMajorVersion == 6 && osv.dwMinorVersion == 0 ) + { + MessageBox( 0, L"Direct3D 11 components were not found. Please install the latest Service Pack.\n"\ + L"For details see Microsoft Knowledge Base Article #935791\n"\ + L"http://support.microsoft.com/kb/935791/", L"Error", MB_ICONEXCLAMATION ); + } + else + { + MessageBox( 0, L"Direct3D 11 is not supported on this OS.", L"Error", MB_ICONEXCLAMATION ); + } + } + + if( FAILED( hr ) ) + return hr; + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Tells the framework to change to a device created from the passed in device settings +// If DXUTCreateWindow() has not already been called, it will call it with the +// default parameters. Instead of calling this, you can call DXUTCreateDevice() +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT WINAPI DXUTCreateDeviceFromSettings( DXUTDeviceSettings* pDeviceSettings, bool bClipWindowToSingleAdapter ) +{ + if ( !pDeviceSettings ) + return E_INVALIDARG; + + HRESULT hr; + + GetDXUTState().SetDeviceCreateCalled( true ); + + // If DXUTCreateWindow() or DXUTSetWindow() has not already been called, + // then call DXUTCreateWindow() with the default parameters. + if( !GetDXUTState().GetWindowCreated() ) + { + // If DXUTCreateWindow() or DXUTSetWindow() was already called and failed, then fail. + // DXUTCreateWindow() or DXUTSetWindow() must first succeed for this function to succeed + if( GetDXUTState().GetWindowCreateCalled() ) + return E_FAIL; + + // If DXUTCreateWindow() or DXUTSetWindow() hasn't been called, then + // automatically call DXUTCreateWindow() with default params + hr = DXUTCreateWindow(); + if( FAILED( hr ) ) + return hr; + } + + DXUTUpdateDeviceSettingsWithOverrides(pDeviceSettings); + + GetDXUTState().SetWindowBackBufferWidthAtModeChange(pDeviceSettings->d3d11.sd.BufferDesc.Width); + GetDXUTState().SetWindowBackBufferHeightAtModeChange(pDeviceSettings->d3d11.sd.BufferDesc.Height); + GetDXUTState().SetFullScreenBackBufferWidthAtModeChange(pDeviceSettings->d3d11.sd.BufferDesc.Width); + GetDXUTState().SetFullScreenBackBufferHeightAtModeChange(pDeviceSettings->d3d11.sd.BufferDesc.Height); + + // Change to a Direct3D device created from the new device settings. + // If there is an existing device, then either reset or recreate the scene + hr = DXUTChangeDevice( pDeviceSettings, bClipWindowToSingleAdapter ); + if( FAILED( hr ) ) + return hr; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// All device changes are sent to this function. It looks at the current +// device (if any) and the new device and determines the best course of action. It +// also remembers and restores the window state if toggling between windowed and fullscreen +// as well as sets the proper window and system state for switching to the new device. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DXUTChangeDevice( DXUTDeviceSettings* pNewDeviceSettings, + bool bClipWindowToSingleAdapter ) +{ + if ( GetDXUTState().GetReleasingSwapChain() ) + return S_FALSE; + + HRESULT hr = S_OK; + DXUTDeviceSettings* pOldDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + + if( !pNewDeviceSettings ) + return S_FALSE; + + hr = DXUTDelayLoadDXGI(); + + if( FAILED( hr ) ) + return hr; + + // Make a copy of the pNewDeviceSettings on the heap + DXUTDeviceSettings* pNewDeviceSettingsOnHeap = new (std::nothrow) DXUTDeviceSettings; + if( !pNewDeviceSettingsOnHeap ) + return E_OUTOFMEMORY; + memcpy( pNewDeviceSettingsOnHeap, pNewDeviceSettings, sizeof( DXUTDeviceSettings ) ); + pNewDeviceSettings = pNewDeviceSettingsOnHeap; + + GetDXUTState().SetCurrentDeviceSettings(pNewDeviceSettingsOnHeap); + hr = DXUTSnapDeviceSettingsToEnumDevice(pNewDeviceSettingsOnHeap, false); + + if( FAILED( hr ) ) // the call will fail if no valid devices were found + { + DXUTDisplayErrorMessage( hr ); + return DXUT_ERR( L"DXUTFindValidDeviceSettings", hr ); + } + + // If the ModifyDeviceSettings callback is non-NULL, then call it to let the app + // change the settings or reject the device change by returning false. + LPDXUTCALLBACKMODIFYDEVICESETTINGS pCallbackModifyDeviceSettings = GetDXUTState().GetModifyDeviceSettingsFunc(); + if( pCallbackModifyDeviceSettings ) + { + bool bContinue = pCallbackModifyDeviceSettings( pNewDeviceSettings, + GetDXUTState().GetModifyDeviceSettingsFuncUserContext() ); + if( !bContinue ) + { + // The app rejected the device change by returning false, so just use the current device if there is one. + if( !pOldDeviceSettings ) + DXUTDisplayErrorMessage( DXUTERR_NOCOMPATIBLEDEVICES ); + SAFE_DELETE( pNewDeviceSettings ); + return E_ABORT; + } + if( !GetDXUTState().GetDXGIFactory() ) // if DXUTShutdown() was called in the modify callback, just return + { + SAFE_DELETE( pNewDeviceSettings ); + return S_FALSE; + } + DXUTSnapDeviceSettingsToEnumDevice(pNewDeviceSettingsOnHeap, false); // modify the app specified settings to the closed enumerated settigns + + if( FAILED( hr ) ) // the call will fail if no valid devices were found + { + DXUTDisplayErrorMessage( hr ); + return DXUT_ERR( L"DXUTFindValidDeviceSettings", hr ); + } + + } + + GetDXUTState().SetCurrentDeviceSettings( pNewDeviceSettingsOnHeap ); + + DXUTPause( true, true ); + + // Take note if the backbuffer width & height are 0 now as they will change after pd3dDevice->Reset() + bool bKeepCurrentWindowSize = false; + if( DXUTGetBackBufferWidthFromDS( pNewDeviceSettings ) == 0 && + DXUTGetBackBufferHeightFromDS( pNewDeviceSettings ) == 0 ) + bKeepCurrentWindowSize = true; + + ////////////////////////// + // Before reset + ///////////////////////// + + if( DXUTGetIsWindowedFromDS( pNewDeviceSettings ) ) + { + // Going to windowed mode + if( pOldDeviceSettings && !DXUTGetIsWindowedFromDS( pOldDeviceSettings ) ) + { + // Going from fullscreen -> windowed + GetDXUTState().SetFullScreenBackBufferWidthAtModeChange( DXUTGetBackBufferWidthFromDS( + pOldDeviceSettings ) ); + GetDXUTState().SetFullScreenBackBufferHeightAtModeChange( DXUTGetBackBufferHeightFromDS( + pOldDeviceSettings ) ); + } + } + else + { + // Going to fullscreen mode + if( !pOldDeviceSettings || ( pOldDeviceSettings && DXUTGetIsWindowedFromDS( pOldDeviceSettings ) ) ) + { + // Transistioning to full screen mode from a standard window so + if( pOldDeviceSettings ) + { + GetDXUTState().SetWindowBackBufferWidthAtModeChange( DXUTGetBackBufferWidthFromDS( + pOldDeviceSettings ) ); + GetDXUTState().SetWindowBackBufferHeightAtModeChange( DXUTGetBackBufferHeightFromDS( + pOldDeviceSettings ) ); + } + } + } + + if( pOldDeviceSettings ) + DXUTCleanup3DEnvironment( false ); + + // Create the D3D device and call the app's device callbacks + hr = DXUTCreate3DEnvironment11(); + if( FAILED( hr ) ) + { + SAFE_DELETE( pOldDeviceSettings ); + DXUTCleanup3DEnvironment( true ); + DXUTDisplayErrorMessage( hr ); + DXUTPause( false, false ); + GetDXUTState().SetIgnoreSizeChange( false ); + return hr; + } + + // Enable/disable StickKeys shortcut, ToggleKeys shortcut, FilterKeys shortcut, and Windows key + // to prevent accidental task switching + DXUTAllowShortcutKeys( ( DXUTGetIsWindowedFromDS( pNewDeviceSettings ) ) ? + GetDXUTState().GetAllowShortcutKeysWhenWindowed() : + GetDXUTState().GetAllowShortcutKeysWhenFullscreen() ); + + HMONITOR hAdapterMonitor = DXUTGetMonitorFromAdapter( pNewDeviceSettings ); + GetDXUTState().SetAdapterMonitor( hAdapterMonitor ); + + // Update the device stats text + DXUTUpdateStaticFrameStats(); + + if( pOldDeviceSettings && !DXUTGetIsWindowedFromDS( pOldDeviceSettings ) && + DXUTGetIsWindowedFromDS( pNewDeviceSettings ) ) + { + // Going from fullscreen -> windowed + + // Restore the show state, and positions/size of the window to what it was + // It is important to adjust the window size + // after resetting the device rather than beforehand to ensure + // that the monitor resolution is correct and does not limit the size of the new window. + auto pwp = GetDXUTState().GetWindowedPlacement(); + SetWindowPlacement( DXUTGetHWNDDeviceWindowed(), pwp ); + + // Also restore the z-order of window to previous state + HWND hWndInsertAfter = GetDXUTState().GetTopmostWhileWindowed() ? HWND_TOPMOST : HWND_NOTOPMOST; + SetWindowPos( DXUTGetHWNDDeviceWindowed(), hWndInsertAfter, 0, 0, 0, 0, + SWP_NOMOVE | SWP_NOREDRAW | SWP_NOSIZE ); + } + + // Check to see if the window needs to be resized. + // Handle cases where the window is minimized and maxmimized as well. + + bool bNeedToResize = false; + if( DXUTGetIsWindowedFromDS( pNewDeviceSettings ) && // only resize if in windowed mode + !bKeepCurrentWindowSize ) // only resize if pp.BackbufferWidth/Height were not 0 + { + UINT nClientWidth; + UINT nClientHeight; + if( IsIconic( DXUTGetHWNDDeviceWindowed() ) ) + { + // Window is currently minimized. To tell if it needs to resize, + // get the client rect of window when its restored the + // hard way using GetWindowPlacement() + WINDOWPLACEMENT wp = {}; + wp.length = sizeof( WINDOWPLACEMENT ); + GetWindowPlacement( DXUTGetHWNDDeviceWindowed(), &wp ); + + if( ( wp.flags & WPF_RESTORETOMAXIMIZED ) != 0 && wp.showCmd == SW_SHOWMINIMIZED ) + { + // WPF_RESTORETOMAXIMIZED means that when the window is restored it will + // be maximized. So maximize the window temporarily to get the client rect + // when the window is maximized. GetSystemMetrics( SM_CXMAXIMIZED ) will give this + // information if the window is on the primary but this will work on multimon. + ShowWindow( DXUTGetHWNDDeviceWindowed(), SW_RESTORE ); + RECT rcClient; + GetClientRect( DXUTGetHWNDDeviceWindowed(), &rcClient ); + nClientWidth = ( UINT )( rcClient.right - rcClient.left ); + nClientHeight = ( UINT )( rcClient.bottom - rcClient.top ); + ShowWindow( DXUTGetHWNDDeviceWindowed(), SW_MINIMIZE ); + } + else + { + // Use wp.rcNormalPosition to get the client rect, but wp.rcNormalPosition + // includes the window frame so subtract it + RECT rcFrame = {}; + AdjustWindowRect( &rcFrame, GetDXUTState().GetWindowedStyleAtModeChange(), GetDXUTState().GetMenu() != 0 ); + LONG nFrameWidth = rcFrame.right - rcFrame.left; + LONG nFrameHeight = rcFrame.bottom - rcFrame.top; + nClientWidth = ( UINT )( wp.rcNormalPosition.right - wp.rcNormalPosition.left - nFrameWidth ); + nClientHeight = ( UINT )( wp.rcNormalPosition.bottom - wp.rcNormalPosition.top - nFrameHeight ); + } + } + else + { + // Window is restored or maximized so just get its client rect + RECT rcClient; + GetClientRect( DXUTGetHWNDDeviceWindowed(), &rcClient ); + nClientWidth = ( UINT )( rcClient.right - rcClient.left ); + nClientHeight = ( UINT )( rcClient.bottom - rcClient.top ); + } + + // Now that we know the client rect, compare it against the back buffer size + // to see if the client rect is already the right size + if( nClientWidth != DXUTGetBackBufferWidthFromDS( pNewDeviceSettings ) || + nClientHeight != DXUTGetBackBufferHeightFromDS( pNewDeviceSettings ) ) + { + bNeedToResize = true; + } + + if( bClipWindowToSingleAdapter && !IsIconic( DXUTGetHWNDDeviceWindowed() ) ) + { + // Get the rect of the monitor attached to the adapter + MONITORINFO miAdapter; + miAdapter.cbSize = sizeof( MONITORINFO ); + hAdapterMonitor = DXUTGetMonitorFromAdapter( pNewDeviceSettings ); + DXUTGetMonitorInfo( hAdapterMonitor, &miAdapter ); + HMONITOR hWindowMonitor = DXUTMonitorFromWindow( DXUTGetHWND(), MONITOR_DEFAULTTOPRIMARY ); + + // Get the rect of the window + RECT rcWindow; + GetWindowRect( DXUTGetHWNDDeviceWindowed(), &rcWindow ); + + // Check if the window rect is fully inside the adapter's vitural screen rect + if( ( rcWindow.left < miAdapter.rcWork.left || + rcWindow.right > miAdapter.rcWork.right || + rcWindow.top < miAdapter.rcWork.top || + rcWindow.bottom > miAdapter.rcWork.bottom ) ) + { + if( hWindowMonitor == hAdapterMonitor && IsZoomed( DXUTGetHWNDDeviceWindowed() ) ) + { + // If the window is maximized and on the same monitor as the adapter, then + // no need to clip to single adapter as the window is already clipped + // even though the rcWindow rect is outside of the miAdapter.rcWork + } + else + { + bNeedToResize = true; + } + } + } + } + + // Only resize window if needed + + if( bNeedToResize ) + { + // Need to resize, so if window is maximized or minimized then restore the window + if( IsIconic( DXUTGetHWNDDeviceWindowed() ) ) + ShowWindow( DXUTGetHWNDDeviceWindowed(), SW_RESTORE ); + if( IsZoomed( DXUTGetHWNDDeviceWindowed() ) ) // doing the IsIconic() check first also handles the WPF_RESTORETOMAXIMIZED case + ShowWindow( DXUTGetHWNDDeviceWindowed(), SW_RESTORE ); + + if( bClipWindowToSingleAdapter ) + { + // Get the rect of the monitor attached to the adapter + MONITORINFO miAdapter; + miAdapter.cbSize = sizeof( MONITORINFO ); + hAdapterMonitor = DXUTGetMonitorFromAdapter( pNewDeviceSettings ); + DXUTGetMonitorInfo( hAdapterMonitor, &miAdapter ); + + // Get the rect of the monitor attached to the window + MONITORINFO miWindow; + miWindow.cbSize = sizeof( MONITORINFO ); + DXUTGetMonitorInfo( DXUTMonitorFromWindow( DXUTGetHWND(), MONITOR_DEFAULTTOPRIMARY ), &miWindow ); + + // Do something reasonable if the BackBuffer size is greater than the monitor size + int nAdapterMonitorWidth = miAdapter.rcWork.right - miAdapter.rcWork.left; + int nAdapterMonitorHeight = miAdapter.rcWork.bottom - miAdapter.rcWork.top; + + int nClientWidth = DXUTGetBackBufferWidthFromDS( pNewDeviceSettings ); + int nClientHeight = DXUTGetBackBufferHeightFromDS( pNewDeviceSettings ); + + // Get the rect of the window + RECT rcWindow; + GetWindowRect( DXUTGetHWNDDeviceWindowed(), &rcWindow ); + + // Make a window rect with a client rect that is the same size as the backbuffer + RECT rcResizedWindow; + rcResizedWindow.left = 0; + rcResizedWindow.right = nClientWidth; + rcResizedWindow.top = 0; + rcResizedWindow.bottom = nClientHeight; + AdjustWindowRect( &rcResizedWindow, GetWindowLong( DXUTGetHWNDDeviceWindowed(), GWL_STYLE ), + GetDXUTState().GetMenu() != 0 ); + + int nWindowWidth = rcResizedWindow.right - rcResizedWindow.left; + int nWindowHeight = rcResizedWindow.bottom - rcResizedWindow.top; + + if( nWindowWidth > nAdapterMonitorWidth ) + nWindowWidth = nAdapterMonitorWidth; + if( nWindowHeight > nAdapterMonitorHeight ) + nWindowHeight = nAdapterMonitorHeight; + + if( rcResizedWindow.left < miAdapter.rcWork.left || + rcResizedWindow.top < miAdapter.rcWork.top || + rcResizedWindow.right > miAdapter.rcWork.right || + rcResizedWindow.bottom > miAdapter.rcWork.bottom ) + { + int nWindowOffsetX = ( nAdapterMonitorWidth - nWindowWidth ) / 2; + int nWindowOffsetY = ( nAdapterMonitorHeight - nWindowHeight ) / 2; + + rcResizedWindow.left = miAdapter.rcWork.left + nWindowOffsetX; + rcResizedWindow.top = miAdapter.rcWork.top + nWindowOffsetY; + rcResizedWindow.right = miAdapter.rcWork.left + nWindowOffsetX + nWindowWidth; + rcResizedWindow.bottom = miAdapter.rcWork.top + nWindowOffsetY + nWindowHeight; + } + + // Resize the window. It is important to adjust the window size + // after resetting the device rather than beforehand to ensure + // that the monitor resolution is correct and does not limit the size of the new window. + SetWindowPos( DXUTGetHWNDDeviceWindowed(), 0, rcResizedWindow.left, rcResizedWindow.top, nWindowWidth, + nWindowHeight, SWP_NOZORDER ); + } + else + { + // Make a window rect with a client rect that is the same size as the backbuffer + RECT rcWindow = {}; + rcWindow.right = (long)( DXUTGetBackBufferWidthFromDS(pNewDeviceSettings) ); + rcWindow.bottom = (long)( DXUTGetBackBufferHeightFromDS(pNewDeviceSettings) ); + AdjustWindowRect( &rcWindow, GetWindowLong( DXUTGetHWNDDeviceWindowed(), GWL_STYLE ), GetDXUTState().GetMenu() != 0 ); + + // Resize the window. It is important to adjust the window size + // after resetting the device rather than beforehand to ensure + // that the monitor resolution is correct and does not limit the size of the new window. + int cx = ( int )( rcWindow.right - rcWindow.left ); + int cy = ( int )( rcWindow.bottom - rcWindow.top ); + SetWindowPos( DXUTGetHWNDDeviceWindowed(), 0, 0, 0, cx, cy, SWP_NOZORDER | SWP_NOMOVE ); + } + + // Its possible that the new window size is not what we asked for. + // No window can be sized larger than the desktop, so see if the Windows OS resized the + // window to something smaller to fit on the desktop. Also if WM_GETMINMAXINFO + // will put a limit on the smallest/largest window size. + RECT rcClient; + GetClientRect( DXUTGetHWNDDeviceWindowed(), &rcClient ); + UINT nClientWidth = ( UINT )( rcClient.right - rcClient.left ); + UINT nClientHeight = ( UINT )( rcClient.bottom - rcClient.top ); + if( nClientWidth != DXUTGetBackBufferWidthFromDS( pNewDeviceSettings ) || + nClientHeight != DXUTGetBackBufferHeightFromDS( pNewDeviceSettings ) ) + { + // If its different, then resize the backbuffer again. This time create a backbuffer that matches the + // client rect of the current window w/o resizing the window. + auto deviceSettings = DXUTGetDeviceSettings(); + deviceSettings.d3d11.sd.BufferDesc.Width = 0; + deviceSettings.d3d11.sd.BufferDesc.Height = 0; + + hr = DXUTChangeDevice( &deviceSettings, bClipWindowToSingleAdapter ); + if( FAILED( hr ) ) + { + SAFE_DELETE( pOldDeviceSettings ); + DXUTCleanup3DEnvironment( true ); + DXUTPause( false, false ); + GetDXUTState().SetIgnoreSizeChange( false ); + return hr; + } + } + } + + //if (DXUTGetIsWindowedFromDS( pNewDeviceSettings )) { + // RECT rcFrame = {}; + // AdjustWindowRect( &rcFrame, GetDXUTState().GetWindowedStyleAtModeChange(), GetDXUTState().GetMenu() ); + // } + + // Make the window visible + if( !IsWindowVisible( DXUTGetHWND() ) ) + ShowWindow( DXUTGetHWND(), SW_SHOW ); + + // Ensure that the display doesn't power down when fullscreen but does when windowed + if( !DXUTIsWindowed() ) + SetThreadExecutionState( ES_DISPLAY_REQUIRED | ES_CONTINUOUS ); + else + SetThreadExecutionState( ES_CONTINUOUS ); + + SAFE_DELETE( pOldDeviceSettings ); + GetDXUTState().SetIgnoreSizeChange( false ); + DXUTPause( false, false ); + GetDXUTState().SetDeviceCreated( true ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Creates a DXGI factory object if one has not already been created +//-------------------------------------------------------------------------------------- +HRESULT DXUTDelayLoadDXGI() +{ + auto pDXGIFactory = GetDXUTState().GetDXGIFactory(); + if( !pDXGIFactory ) + { + HRESULT hr = DXUT_Dynamic_CreateDXGIFactory1( IID_PPV_ARGS(&pDXGIFactory) ); + if ( FAILED(hr) ) + return hr; + + GetDXUTState().SetDXGIFactory( pDXGIFactory ); + if( !pDXGIFactory ) + { + return DXUTERR_NODIRECT3D; + } + + // DXGI 1.1 implies Direct3D 11 + } + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Updates the device settings with default values.. +//-------------------------------------------------------------------------------------- +void DXUTUpdateDeviceSettingsWithOverrides( _Inout_ DXUTDeviceSettings* pDeviceSettings ) +{ + // Override with settings from the command line + if( GetDXUTState().GetOverrideWidth() != 0 ) + { + pDeviceSettings->d3d11.sd.BufferDesc.Width = GetDXUTState().GetOverrideWidth(); + } + if( GetDXUTState().GetOverrideHeight() != 0 ) + { + pDeviceSettings->d3d11.sd.BufferDesc.Height = GetDXUTState().GetOverrideHeight(); + } + + if( GetDXUTState().GetOverrideAdapterOrdinal() != -1 ) + { + pDeviceSettings->d3d11.AdapterOrdinal = GetDXUTState().GetOverrideAdapterOrdinal(); + } + + if( GetDXUTState().GetOverrideFullScreen() ) + { + pDeviceSettings->d3d11.sd.Windowed = FALSE; + } + + if( GetDXUTState().GetOverrideWindowed() ) + { + pDeviceSettings->d3d11.sd.Windowed = TRUE; + } + + if( GetDXUTState().GetOverrideForceHAL() ) + { + pDeviceSettings->d3d11.DriverType = D3D_DRIVER_TYPE_HARDWARE; + } + + if( GetDXUTState().GetOverrideForceREF() ) + { + pDeviceSettings->d3d11.DriverType = D3D_DRIVER_TYPE_REFERENCE; + } + + if( GetDXUTState().GetOverrideForceWARP() ) + { + pDeviceSettings->d3d11.DriverType = D3D_DRIVER_TYPE_WARP; + pDeviceSettings->d3d11.sd.Windowed = TRUE; + } + + if( GetDXUTState().GetOverrideForceVsync() == 0 ) + { + pDeviceSettings->d3d11.SyncInterval = 0; + } + else if( GetDXUTState().GetOverrideForceVsync() == 1 ) + { + pDeviceSettings->d3d11.SyncInterval = 1; + } + + if (GetDXUTState().GetOverrideForceFeatureLevel() != 0) + { + pDeviceSettings->d3d11.DeviceFeatureLevel = GetDXUTState().GetOverrideForceFeatureLevel(); + } +} + + +//-------------------------------------------------------------------------------------- +// Sets the viewport, render target view, and depth stencil view. +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTSetupD3D11Views( _In_ ID3D11DeviceContext* pd3dDeviceContext ) +{ + HRESULT hr = S_OK; + + // Setup the viewport to match the backbuffer + D3D11_VIEWPORT vp; + vp.Width = (FLOAT)DXUTGetDXGIBackBufferSurfaceDesc()->Width; + vp.Height = (FLOAT)DXUTGetDXGIBackBufferSurfaceDesc()->Height; + vp.MinDepth = 0; + vp.MaxDepth = 1; + vp.TopLeftX = 0; + vp.TopLeftY = 0; + pd3dDeviceContext->RSSetViewports( 1, &vp ); + + // Set the render targets + auto pRTV = GetDXUTState().GetD3D11RenderTargetView(); + auto pDSV = GetDXUTState().GetD3D11DepthStencilView(); + pd3dDeviceContext->OMSetRenderTargets( 1, &pRTV, pDSV ); + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Creates a render target view, and depth stencil texture and view. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DXUTCreateD3D11Views( ID3D11Device* pd3dDevice, ID3D11DeviceContext* pd3dImmediateContext, + DXUTDeviceSettings* pDeviceSettings ) +{ + HRESULT hr = S_OK; + auto pSwapChain = DXUTGetDXGISwapChain(); + ID3D11DepthStencilView* pDSV = nullptr; + ID3D11RenderTargetView* pRTV = nullptr; + + // Get the back buffer and desc + ID3D11Texture2D* pBackBuffer; + hr = pSwapChain->GetBuffer( 0, IID_PPV_ARGS(&pBackBuffer) ); + if( FAILED( hr ) ) + return hr; + D3D11_TEXTURE2D_DESC backBufferSurfaceDesc; + pBackBuffer->GetDesc( &backBufferSurfaceDesc ); + + // Create the render target view + hr = pd3dDevice->CreateRenderTargetView( pBackBuffer, nullptr, &pRTV ); + SAFE_RELEASE( pBackBuffer ); + if( FAILED( hr ) ) + return hr; + DXUT_SetDebugName( pRTV, "DXUT" ); + GetDXUTState().SetD3D11RenderTargetView( pRTV ); + + if( pDeviceSettings->d3d11.AutoCreateDepthStencil ) + { + // Create depth stencil texture + ID3D11Texture2D* pDepthStencil = nullptr; + D3D11_TEXTURE2D_DESC descDepth; + descDepth.Width = backBufferSurfaceDesc.Width; + descDepth.Height = backBufferSurfaceDesc.Height; + descDepth.MipLevels = 1; + descDepth.ArraySize = 1; + descDepth.Format = pDeviceSettings->d3d11.AutoDepthStencilFormat; + descDepth.SampleDesc.Count = pDeviceSettings->d3d11.sd.SampleDesc.Count; + descDepth.SampleDesc.Quality = pDeviceSettings->d3d11.sd.SampleDesc.Quality; + descDepth.Usage = D3D11_USAGE_DEFAULT; + descDepth.BindFlags = D3D11_BIND_DEPTH_STENCIL; + descDepth.CPUAccessFlags = 0; + descDepth.MiscFlags = 0; + hr = pd3dDevice->CreateTexture2D( &descDepth, nullptr, &pDepthStencil ); + if( FAILED( hr ) ) + return hr; + DXUT_SetDebugName( pDepthStencil, "DXUT" ); + GetDXUTState().SetD3D11DepthStencil( pDepthStencil ); + + // Create the depth stencil view + D3D11_DEPTH_STENCIL_VIEW_DESC descDSV; + descDSV.Format = descDepth.Format; + descDSV.Flags = 0; + if( descDepth.SampleDesc.Count > 1 ) + descDSV.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2DMS; + else + descDSV.ViewDimension = D3D11_DSV_DIMENSION_TEXTURE2D; + descDSV.Texture2D.MipSlice = 0; + hr = pd3dDevice->CreateDepthStencilView( pDepthStencil, &descDSV, &pDSV ); + if( FAILED( hr ) ) + return hr; + DXUT_SetDebugName( pDSV, "DXUT" ); + GetDXUTState().SetD3D11DepthStencilView( pDSV ); + } + + hr = DXUTSetupD3D11Views( pd3dImmediateContext ); + if( FAILED( hr ) ) + return hr; + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Creates the 3D environment +//-------------------------------------------------------------------------------------- +HRESULT DXUTCreate3DEnvironment11() +{ + HRESULT hr = S_OK; + + ID3D11Device* pd3d11Device = nullptr; + ID3D11DeviceContext* pd3dImmediateContext = nullptr; + D3D_FEATURE_LEVEL FeatureLevel = D3D_FEATURE_LEVEL_11_1; + + IDXGISwapChain* pSwapChain = nullptr; + auto pNewDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + assert( pNewDeviceSettings ); + _Analysis_assume_( pNewDeviceSettings ); + + auto pDXGIFactory = DXUTGetDXGIFactory(); + assert( pDXGIFactory ); + _Analysis_assume_( pDXGIFactory ); + hr = pDXGIFactory->MakeWindowAssociation( DXUTGetHWND(), 0 ); + + // Try to create the device with the chosen settings + IDXGIAdapter1* pAdapter = nullptr; + + hr = S_OK; + D3D_DRIVER_TYPE ddt = pNewDeviceSettings->d3d11.DriverType; + if( pNewDeviceSettings->d3d11.DriverType == D3D_DRIVER_TYPE_HARDWARE ) + { + hr = pDXGIFactory->EnumAdapters1( pNewDeviceSettings->d3d11.AdapterOrdinal, &pAdapter ); + if ( FAILED( hr) ) + { + return E_FAIL; + } + ddt = D3D_DRIVER_TYPE_UNKNOWN; + } + else if (pNewDeviceSettings->d3d11.DriverType == D3D_DRIVER_TYPE_WARP) + { + ddt = D3D_DRIVER_TYPE_WARP; + pAdapter = nullptr; + } + else if (pNewDeviceSettings->d3d11.DriverType == D3D_DRIVER_TYPE_REFERENCE) + { + ddt = D3D_DRIVER_TYPE_REFERENCE; + pAdapter = nullptr; + } + + if( SUCCEEDED( hr ) ) + { + hr = DXUT_Dynamic_D3D11CreateDevice( pAdapter, + ddt, + ( HMODULE )0, + pNewDeviceSettings->d3d11.CreateFlags, + &pNewDeviceSettings->d3d11.DeviceFeatureLevel, + 1, + D3D11_SDK_VERSION, + &pd3d11Device, + &FeatureLevel, + &pd3dImmediateContext + ); + + if ( FAILED( hr ) ) + { + pAdapter = nullptr; + // Remote desktop does not allow you to enumerate the adapter. In this case, we let D3D11 do the enumeration. + if ( ddt == D3D_DRIVER_TYPE_UNKNOWN ) + { + hr = DXUT_Dynamic_D3D11CreateDevice( pAdapter, + D3D_DRIVER_TYPE_HARDWARE, + ( HMODULE )0, + pNewDeviceSettings->d3d11.CreateFlags, + &pNewDeviceSettings->d3d11.DeviceFeatureLevel, + 1, + D3D11_SDK_VERSION, + &pd3d11Device, + &FeatureLevel, + &pd3dImmediateContext + ); + } + if ( FAILED ( hr ) ) + { + DXUT_ERR( L"D3D11CreateDevice", hr ); + return DXUTERR_CREATINGDEVICE; + } + } + } + +#ifndef NDEBUG + if( SUCCEEDED( hr ) ) + { + ID3D11Debug * d3dDebug = nullptr; + if( SUCCEEDED( pd3d11Device->QueryInterface(IID_PPV_ARGS(&d3dDebug) ) ) ) + { + ID3D11InfoQueue* infoQueue = nullptr; + if( SUCCEEDED( d3dDebug->QueryInterface( IID_PPV_ARGS(&infoQueue) ) ) ) + { + // ignore some "expected" errors + D3D11_MESSAGE_ID denied [] = + { + D3D11_MESSAGE_ID_SETPRIVATEDATA_CHANGINGPARAMS, + }; + + D3D11_INFO_QUEUE_FILTER filter; + memset( &filter, 0, sizeof(filter) ); + filter.DenyList.NumIDs = _countof(denied); + filter.DenyList.pIDList = denied; + infoQueue->AddStorageFilterEntries( &filter ); + infoQueue->Release(); + } + d3dDebug->Release(); + } + } +#endif + + if( SUCCEEDED( hr ) ) + { + IDXGIDevice1* pDXGIDev = nullptr; + hr = pd3d11Device->QueryInterface( IID_PPV_ARGS(&pDXGIDev) ); + if( SUCCEEDED( hr ) && pDXGIDev ) + { + if ( !pAdapter ) + { + IDXGIAdapter *pTempAdapter = nullptr; + V_RETURN( pDXGIDev->GetAdapter( &pTempAdapter ) ); + V_RETURN( pTempAdapter->QueryInterface( IID_PPV_ARGS(&pAdapter) ) ); + V_RETURN( pAdapter->GetParent( IID_PPV_ARGS(&pDXGIFactory) ) ); + SAFE_RELEASE ( pTempAdapter ); + if ( GetDXUTState().GetDXGIFactory() != pDXGIFactory ) + GetDXUTState().GetDXGIFactory()->Release(); + GetDXUTState().SetDXGIFactory( pDXGIFactory ); + } + } + SAFE_RELEASE( pDXGIDev ); + GetDXUTState().SetDXGIAdapter( pAdapter ); + } + + if( FAILED( hr ) ) + { + DXUT_ERR( L"D3D11CreateDevice", hr ); + return DXUTERR_CREATINGDEVICE; + } + + // set default render state to msaa enabled + D3D11_RASTERIZER_DESC drd = { + D3D11_FILL_SOLID, //D3D11_FILL_MODE FillMode; + D3D11_CULL_BACK,//D3D11_CULL_MODE CullMode; + FALSE, //BOOL FrontCounterClockwise; + 0, //INT DepthBias; + 0.0f,//FLOAT DepthBiasClamp; + 0.0f,//FLOAT SlopeScaledDepthBias; + TRUE,//BOOL DepthClipEnable; + FALSE,//BOOL ScissorEnable; + TRUE,//BOOL MultisampleEnable; + FALSE//BOOL AntialiasedLineEnable; + }; + ID3D11RasterizerState* pRS = nullptr; + hr = pd3d11Device->CreateRasterizerState(&drd, &pRS); + if ( FAILED( hr ) ) + { + DXUT_ERR( L"CreateRasterizerState", hr ); + return DXUTERR_CREATINGDEVICE; + } + DXUT_SetDebugName( pRS, "DXUT Default" ); + GetDXUTState().SetD3D11RasterizerState(pRS); + pd3dImmediateContext->RSSetState(pRS); + + // Enumerate its outputs. + UINT OutputCount, iOutput; + for( OutputCount = 0; ; ++OutputCount ) + { + IDXGIOutput* pOutput; + if( FAILED( pAdapter->EnumOutputs( OutputCount, &pOutput ) ) ) + break; + SAFE_RELEASE( pOutput ); + } + auto ppOutputArray = new (std::nothrow) IDXGIOutput*[OutputCount]; + if( !ppOutputArray ) + return E_OUTOFMEMORY; + for( iOutput = 0; iOutput < OutputCount; ++iOutput ) + pAdapter->EnumOutputs( iOutput, ppOutputArray + iOutput ); + GetDXUTState().SetDXGIOutputArray( ppOutputArray ); + GetDXUTState().SetDXGIOutputArraySize( OutputCount ); + + // Create the swapchain + hr = pDXGIFactory->CreateSwapChain( pd3d11Device, &pNewDeviceSettings->d3d11.sd, &pSwapChain ); + if( FAILED( hr ) ) + { + DXUT_ERR( L"CreateSwapChain", hr ); + return DXUTERR_CREATINGDEVICE; + } + + GetDXUTState().SetD3D11Device( pd3d11Device ); + GetDXUTState().SetD3D11DeviceContext( pd3dImmediateContext ); + GetDXUTState().SetD3D11FeatureLevel( FeatureLevel ); + GetDXUTState().SetDXGISwapChain( pSwapChain ); + + assert( pd3d11Device ); + _Analysis_assume_( pd3d11Device ); + + assert( pd3dImmediateContext ); + _Analysis_assume_( pd3dImmediateContext ); + + // Direct3D 11.1 + { + ID3D11Device1* pd3d11Device1 = nullptr; + hr = pd3d11Device->QueryInterface(IID_PPV_ARGS(&pd3d11Device1)); + if( SUCCEEDED( hr ) && pd3d11Device1 ) + { + GetDXUTState().SetD3D11Device1( pd3d11Device1 ); + + ID3D11DeviceContext1* pd3dImmediateContext1 = nullptr; + hr = pd3dImmediateContext->QueryInterface(IID_PPV_ARGS(&pd3dImmediateContext1)); + if( SUCCEEDED( hr ) && pd3dImmediateContext1 ) + { + GetDXUTState().SetD3D11DeviceContext1( pd3dImmediateContext1 ); + } + } + } + + // Direct3D 11.2 + { + ID3D11Device2* pd3d11Device2 = nullptr; + hr = pd3d11Device->QueryInterface(IID_PPV_ARGS(&pd3d11Device2)); + if (SUCCEEDED(hr) && pd3d11Device2) + { + GetDXUTState().SetD3D11Device2(pd3d11Device2); + + ID3D11DeviceContext2* pd3dImmediateContext2 = nullptr; + hr = pd3dImmediateContext->QueryInterface(IID_PPV_ARGS(&pd3dImmediateContext2)); + if (SUCCEEDED(hr) && pd3dImmediateContext2) + { + GetDXUTState().SetD3D11DeviceContext2(pd3dImmediateContext2); + } + } + } + +#ifdef USE_DIRECT3D11_3 + // Direct3D 11.3 + { + ID3D11Device3* pd3d11Device3 = nullptr; + hr = pd3d11Device->QueryInterface( IID_PPV_ARGS(&pd3d11Device3) ); + if (SUCCEEDED(hr) && pd3d11Device3) + { + GetDXUTState().SetD3D11Device3(pd3d11Device3); + + ID3D11DeviceContext3* pd3dImmediateContext3 = nullptr; + hr = pd3dImmediateContext->QueryInterface(IID_PPV_ARGS(&pd3dImmediateContext3)); + if (SUCCEEDED(hr) && pd3dImmediateContext3) + { + GetDXUTState().SetD3D11DeviceContext3(pd3dImmediateContext3); + } + } + } +#endif + +#ifdef USE_DIRECT3D11_4 + // Direct3D 11.4 + { + ID3D11Device4* pd3d11Device4 = nullptr; + hr = pd3d11Device->QueryInterface(IID_PPV_ARGS(&pd3d11Device4)); + if (SUCCEEDED(hr) && pd3d11Device4) + { + GetDXUTState().SetD3D11Device4(pd3d11Device4); + + ID3D11DeviceContext4* pd3dImmediateContext4 = nullptr; + hr = pd3dImmediateContext->QueryInterface(IID_PPV_ARGS(&pd3dImmediateContext4)); + if (SUCCEEDED(hr) && pd3dImmediateContext4) + { + GetDXUTState().SetD3D11DeviceContext4(pd3dImmediateContext4); + } + } + } +#endif + + // If switching to REF, set the exit code to 11. If switching to HAL and exit code was 11, then set it back to 0. + if( pNewDeviceSettings->d3d11.DriverType == D3D_DRIVER_TYPE_REFERENCE && GetDXUTState().GetExitCode() == 0 ) + GetDXUTState().SetExitCode( 10 ); + else if( pNewDeviceSettings->d3d11.DriverType == D3D_DRIVER_TYPE_HARDWARE && GetDXUTState().GetExitCode() == 10 ) + GetDXUTState().SetExitCode( 0 ); + + // Update back buffer desc before calling app's device callbacks + DXUTUpdateBackBufferDesc(); + + // Setup cursor based on current settings (window/fullscreen mode, show cursor state, clip cursor state) + DXUTSetupCursor(); + + // Update the device stats text + auto pd3dEnum = DXUTGetD3D11Enumeration(); + assert( pd3dEnum ); + _Analysis_assume_( pd3dEnum ); + auto pAdapterInfo = pd3dEnum->GetAdapterInfo( pNewDeviceSettings->d3d11.AdapterOrdinal ); + DXUTUpdateD3D11DeviceStats( pNewDeviceSettings->d3d11.DriverType, pNewDeviceSettings->d3d11.DeviceFeatureLevel, &pAdapterInfo->AdapterDesc ); + + // Call the app's device created callback if non-NULL + auto pBackBufferSurfaceDesc = DXUTGetDXGIBackBufferSurfaceDesc(); + GetDXUTState().SetInsideDeviceCallback( true ); + auto pCallbackDeviceCreated = GetDXUTState().GetD3D11DeviceCreatedFunc(); + hr = S_OK; + if( pCallbackDeviceCreated ) + hr = pCallbackDeviceCreated( DXUTGetD3D11Device(), pBackBufferSurfaceDesc, + GetDXUTState().GetD3D11DeviceCreatedFuncUserContext() ); + GetDXUTState().SetInsideDeviceCallback( false ); + if( !DXUTGetD3D11Device() ) // Handle DXUTShutdown from inside callback + return E_FAIL; + if( FAILED( hr ) ) + { + DXUT_ERR( L"DeviceCreated callback", hr ); + return ( hr == DXUTERR_MEDIANOTFOUND ) ? DXUTERR_MEDIANOTFOUND : DXUTERR_CREATINGDEVICEOBJECTS; + } + GetDXUTState().SetDeviceObjectsCreated( true ); + + // Setup the render target view and viewport + hr = DXUTCreateD3D11Views( pd3d11Device, pd3dImmediateContext, pNewDeviceSettings ); + if( FAILED( hr ) ) + { + DXUT_ERR( L"DXUTCreateD3D11Views", hr ); + return DXUTERR_CREATINGDEVICEOBJECTS; + } + + // Call the app's swap chain reset callback if non-NULL + GetDXUTState().SetInsideDeviceCallback( true ); + LPDXUTCALLBACKD3D11SWAPCHAINRESIZED pCallbackSwapChainResized = GetDXUTState().GetD3D11SwapChainResizedFunc(); + hr = S_OK; + if( pCallbackSwapChainResized ) + hr = pCallbackSwapChainResized( DXUTGetD3D11Device(), pSwapChain, pBackBufferSurfaceDesc, + GetDXUTState().GetD3D11SwapChainResizedFuncUserContext() ); + GetDXUTState().SetInsideDeviceCallback( false ); + if( !DXUTGetD3D11Device() ) // Handle DXUTShutdown from inside callback + return E_FAIL; + if( FAILED( hr ) ) + { + DXUT_ERR( L"DeviceReset callback", hr ); + return ( hr == DXUTERR_MEDIANOTFOUND ) ? DXUTERR_MEDIANOTFOUND : DXUTERR_RESETTINGDEVICEOBJECTS; + } + GetDXUTState().SetDeviceObjectsReset( true ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Resets the 3D environment by: +// - Calls the device lost callback +// - Resets the device +// - Stores the back buffer description +// - Sets up the full screen Direct3D cursor if requested +// - Calls the device reset callback +//-------------------------------------------------------------------------------------- +HRESULT DXUTReset3DEnvironment11() +{ + HRESULT hr; + + GetDXUTState().SetDeviceObjectsReset( false ); + DXUTPause( true, true ); + + bool bDeferredDXGIAction = false; + auto pDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + auto pSwapChain = DXUTGetDXGISwapChain(); + assert( pSwapChain ); + _Analysis_assume_( pSwapChain ); + + DXGI_SWAP_CHAIN_DESC SCDesc; + if ( FAILED( pSwapChain->GetDesc(&SCDesc)) ) + memset( &SCDesc, 0, sizeof(SCDesc) ); + + // Resize backbuffer and target of the swapchain in case they have changed. + // For windowed mode, use the client rect as the desired size. Unlike D3D9, + // we can't use 0 for width or height. Therefore, fill in the values from + // the window size. For fullscreen mode, the width and height should have + // already been filled with the desktop resolution, so don't change it. + if( pDeviceSettings->d3d11.sd.Windowed && SCDesc.Windowed ) + { + RECT rcWnd; + GetClientRect( DXUTGetHWND(), &rcWnd ); + pDeviceSettings->d3d11.sd.BufferDesc.Width = rcWnd.right - rcWnd.left; + pDeviceSettings->d3d11.sd.BufferDesc.Height = rcWnd.bottom - rcWnd.top; + } + + // If the app wants to switch from windowed to fullscreen or vice versa, + // call the swapchain's SetFullscreenState + // mode. + if( SCDesc.Windowed != pDeviceSettings->d3d11.sd.Windowed ) + { + // Set the fullscreen state + if( pDeviceSettings->d3d11.sd.Windowed ) + { + V_RETURN( pSwapChain->SetFullscreenState( FALSE, nullptr ) ); + bDeferredDXGIAction = true; + } + else + { + // Set fullscreen state by setting the display mode to fullscreen, then changing the resolution + // to the desired value. + + // SetFullscreenState causes a WM_SIZE message to be sent to the window. The WM_SIZE message calls + // DXUTCheckForDXGIBufferChange which normally stores the new height and width in + // pDeviceSettings->d3d11.sd.BufferDesc. SetDoNotStoreBufferSize tells DXUTCheckForDXGIBufferChange + // not to store the height and width so that we have the correct values when calling ResizeTarget. + + GetDXUTState().SetDoNotStoreBufferSize( true ); + V_RETURN( pSwapChain->SetFullscreenState( TRUE, nullptr ) ); + GetDXUTState().SetDoNotStoreBufferSize( false ); + + V_RETURN( pSwapChain->ResizeTarget( &pDeviceSettings->d3d11.sd.BufferDesc ) ); + bDeferredDXGIAction = true; + } + } + else + { + if( pDeviceSettings->d3d11.sd.BufferDesc.Width == SCDesc.BufferDesc.Width && + pDeviceSettings->d3d11.sd.BufferDesc.Height == SCDesc.BufferDesc.Height && + pDeviceSettings->d3d11.sd.BufferDesc.Format != SCDesc.BufferDesc.Format ) + { + DXUTResizeDXGIBuffers( 0, 0, !pDeviceSettings->d3d11.sd.Windowed ); + bDeferredDXGIAction = true; + } + else if( pDeviceSettings->d3d11.sd.BufferDesc.Width != SCDesc.BufferDesc.Width || + pDeviceSettings->d3d11.sd.BufferDesc.Height != SCDesc.BufferDesc.Height ) + { + V_RETURN( pSwapChain->ResizeTarget( &pDeviceSettings->d3d11.sd.BufferDesc ) ); + bDeferredDXGIAction = true; + } + } + + // If no deferred DXGI actions are to take place, mark the device as reset. + // If there is a deferred DXGI action, then the device isn't reset until DXGI sends us a + // window message. Only then can we mark the device as reset. + if( !bDeferredDXGIAction ) + GetDXUTState().SetDeviceObjectsReset( true ); + DXUTPause( false, false ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Render the 3D environment by: +// - Checking if the device is lost and trying to reset it if it is +// - Get the elapsed time since the last frame +// - Calling the app's framemove and render callback +// - Calling Present() +//-------------------------------------------------------------------------------------- +void WINAPI DXUTRender3DEnvironment() +{ + HRESULT hr; + + auto pd3dDevice = DXUTGetD3D11Device(); + if( !pd3dDevice ) + return; + + auto pd3dImmediateContext = DXUTGetD3D11DeviceContext(); + if( !pd3dImmediateContext ) + return; + + auto pSwapChain = DXUTGetDXGISwapChain(); + if( !pSwapChain ) + return; + + if( DXUTIsRenderingPaused() || !DXUTIsActive() || GetDXUTState().GetRenderingOccluded() ) + { + // Window is minimized/paused/occluded/or not exclusive so yield CPU time to other processes + Sleep( 50 ); + } + + // Get the app's time, in seconds. Skip rendering if no time elapsed + double fTime, fAbsTime; float fElapsedTime; + DXUTGetGlobalTimer()->GetTimeValues( &fTime, &fAbsTime, &fElapsedTime ); + + // Store the time for the app + if( GetDXUTState().GetConstantFrameTime() ) + { + fElapsedTime = GetDXUTState().GetTimePerFrame(); + fTime = DXUTGetTime() + fElapsedTime; + } + + GetDXUTState().SetTime( fTime ); + GetDXUTState().SetAbsoluteTime( fAbsTime ); + GetDXUTState().SetElapsedTime( fElapsedTime ); + + // Update the FPS stats + DXUTUpdateFrameStats(); + + DXUTHandleTimers(); + + // Animate the scene by calling the app's frame move callback + LPDXUTCALLBACKFRAMEMOVE pCallbackFrameMove = GetDXUTState().GetFrameMoveFunc(); + if( pCallbackFrameMove ) + { + pCallbackFrameMove( fTime, fElapsedTime, GetDXUTState().GetFrameMoveFuncUserContext() ); + pd3dDevice = DXUTGetD3D11Device(); + if( !pd3dDevice ) // Handle DXUTShutdown from inside callback + return; + } + + if( !GetDXUTState().GetRenderingPaused() ) + { + // Render the scene by calling the app's render callback + LPDXUTCALLBACKD3D11FRAMERENDER pCallbackFrameRender = GetDXUTState().GetD3D11FrameRenderFunc(); + if( pCallbackFrameRender && !GetDXUTState().GetRenderingOccluded() ) + { + pCallbackFrameRender( pd3dDevice, pd3dImmediateContext, fTime, fElapsedTime, + GetDXUTState().GetD3D11FrameRenderFuncUserContext() ); + + pd3dDevice = DXUTGetD3D11Device(); + if( !pd3dDevice ) // Handle DXUTShutdown from inside callback + return; + } + +#if defined(DEBUG) || defined(_DEBUG) + // The back buffer should always match the client rect + // if the Direct3D backbuffer covers the entire window + RECT rcClient; + GetClientRect( DXUTGetHWND(), &rcClient ); + if( !IsIconic( DXUTGetHWND() ) ) + { + GetClientRect( DXUTGetHWND(), &rcClient ); + + assert( DXUTGetDXGIBackBufferSurfaceDesc()->Width == (UINT)rcClient.right ); + assert( DXUTGetDXGIBackBufferSurfaceDesc()->Height == (UINT)rcClient.bottom ); + } +#endif + } + + if ( GetDXUTState().GetSaveScreenShot() ) + { + DXUTSnapD3D11Screenshot( GetDXUTState().GetScreenShotName(), false ); + } + if ( GetDXUTState().GetExitAfterScreenShot() ) + { + DXUTShutdown(); + return; + } + + DWORD dwFlags = 0; + if( GetDXUTState().GetRenderingOccluded() ) + dwFlags = DXGI_PRESENT_TEST; + else + dwFlags = GetDXUTState().GetCurrentDeviceSettings()->d3d11.PresentFlags; + UINT SyncInterval = GetDXUTState().GetCurrentDeviceSettings()->d3d11.SyncInterval; + + // Show the frame on the primary surface. + hr = pSwapChain->Present( SyncInterval, dwFlags ); + if( DXGI_STATUS_OCCLUDED == hr ) + { + // There is a window covering our entire rendering area. + // Don't render until we're visible again. + GetDXUTState().SetRenderingOccluded( true ); + } + else if( DXGI_ERROR_DEVICE_RESET == hr ) + { + // If a mode change happened, we must reset the device + if( FAILED( hr = DXUTReset3DEnvironment11() ) ) + { + if( DXUTERR_RESETTINGDEVICEOBJECTS == hr || + DXUTERR_MEDIANOTFOUND == hr ) + { + DXUTDisplayErrorMessage( hr ); + DXUTShutdown(); + return; + } + else + { + // Reset failed, but the device wasn't lost so something bad happened, + // so recreate the device to try to recover + auto pDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + if( FAILED( DXUTChangeDevice( pDeviceSettings, false ) ) ) + { + DXUTShutdown(); + return; + } + + // How to handle display orientation changes in full-screen mode? + } + } + } + else if( DXGI_ERROR_DEVICE_REMOVED == hr ) + { + // Use a callback to ask the app if it would like to find a new device. + // If no device removed callback is set, then look for a new device + if( FAILED( DXUTHandleDeviceRemoved() ) ) + { + // Perhaps get more information from pD3DDevice->GetDeviceRemovedReason()? + DXUTDisplayErrorMessage( DXUTERR_DEVICEREMOVED ); + DXUTShutdown(); + return; + } + } + else if( SUCCEEDED( hr ) ) + { + if( GetDXUTState().GetRenderingOccluded() ) + { + // Now that we're no longer occluded + // allow us to render again + GetDXUTState().SetRenderingOccluded( false ); + } + } + + // Update current frame # + int nFrame = GetDXUTState().GetCurrentFrameNumber(); + nFrame++; + GetDXUTState().SetCurrentFrameNumber( nFrame ); + + // Check to see if the app should shutdown due to cmdline + if( GetDXUTState().GetOverrideQuitAfterFrame() != 0 ) + { + if( nFrame > GetDXUTState().GetOverrideQuitAfterFrame() ) + DXUTShutdown(); + } + + return; +} + + +//-------------------------------------------------------------------------------------- +// Cleans up the 3D environment by: +// - Calls the device lost callback +// - Calls the device destroyed callback +// - Releases the D3D device +//-------------------------------------------------------------------------------------- +void DXUTCleanup3DEnvironment( _In_ bool bReleaseSettings ) +{ + auto pd3dDevice = DXUTGetD3D11Device(); + + if( pd3dDevice ) + { + if (GetDXUTState().GetD3D11RasterizerState()) + GetDXUTState().GetD3D11RasterizerState()->Release(); + + // Call the app's SwapChain lost callback + GetDXUTState().SetInsideDeviceCallback( true ); + if( GetDXUTState().GetDeviceObjectsReset() ) + { + LPDXUTCALLBACKD3D11SWAPCHAINRELEASING pCallbackSwapChainReleasing = + GetDXUTState().GetD3D11SwapChainReleasingFunc(); + if( pCallbackSwapChainReleasing ) + pCallbackSwapChainReleasing( GetDXUTState().GetD3D11SwapChainReleasingFuncUserContext() ); + GetDXUTState().SetDeviceObjectsReset( false ); + } + + // Release our old depth stencil texture and view + auto pDS = GetDXUTState().GetD3D11DepthStencil(); + SAFE_RELEASE( pDS ); + GetDXUTState().SetD3D11DepthStencil( nullptr ); + auto pDSV = GetDXUTState().GetD3D11DepthStencilView(); + SAFE_RELEASE( pDSV ); + GetDXUTState().SetD3D11DepthStencilView( nullptr ); + + // Cleanup the render target view + auto pRTV = GetDXUTState().GetD3D11RenderTargetView(); + SAFE_RELEASE( pRTV ); + GetDXUTState().SetD3D11RenderTargetView( nullptr ); + + // Call the app's device destroyed callback + if( GetDXUTState().GetDeviceObjectsCreated() ) + { + auto pCallbackDeviceDestroyed = GetDXUTState().GetD3D11DeviceDestroyedFunc(); + if( pCallbackDeviceDestroyed ) + pCallbackDeviceDestroyed( GetDXUTState().GetD3D11DeviceDestroyedFuncUserContext() ); + GetDXUTState().SetDeviceObjectsCreated( false ); + } + + GetDXUTState().SetInsideDeviceCallback( false ); + + // Release the swap chain + GetDXUTState().SetReleasingSwapChain( true ); + auto pSwapChain = DXUTGetDXGISwapChain(); + if( pSwapChain ) + { + pSwapChain->SetFullscreenState( FALSE, 0 ); + } + SAFE_RELEASE( pSwapChain ); + GetDXUTState().SetDXGISwapChain( nullptr ); + GetDXUTState().SetReleasingSwapChain( false ); + + // Release the outputs. + auto ppOutputArray = GetDXUTState().GetDXGIOutputArray(); + UINT OutputCount = GetDXUTState().GetDXGIOutputArraySize(); + for( UINT o = 0; o < OutputCount; ++o ) + SAFE_RELEASE( ppOutputArray[o] ); + delete[] ppOutputArray; + GetDXUTState().SetDXGIOutputArray( nullptr ); + GetDXUTState().SetDXGIOutputArraySize( 0 ); + + // Release the D3D adapter. + auto pAdapter = GetDXUTState().GetDXGIAdapter(); + SAFE_RELEASE( pAdapter ); + GetDXUTState().SetDXGIAdapter( nullptr ); + + // Call ClearState to avoid tons of messy debug spew telling us that we're deleting bound objects + auto pImmediateContext = DXUTGetD3D11DeviceContext(); + assert( pImmediateContext ); + pImmediateContext->ClearState(); + pImmediateContext->Flush(); + + // Release the D3D11 immediate context (if it exists) because it has a extra ref count on it + SAFE_RELEASE( pImmediateContext ); + GetDXUTState().SetD3D11DeviceContext( nullptr ); + + auto pImmediateContext1 = DXUTGetD3D11DeviceContext1(); + SAFE_RELEASE( pImmediateContext1 ); + GetDXUTState().SetD3D11DeviceContext1( nullptr ); + + auto pImmediateContext2 = DXUTGetD3D11DeviceContext2(); + SAFE_RELEASE(pImmediateContext2); + GetDXUTState().SetD3D11DeviceContext2(nullptr); + +#ifdef USE_DIRECT3D11_3 + auto pImmediateContext3 = DXUTGetD3D11DeviceContext3(); + SAFE_RELEASE(pImmediateContext3); + GetDXUTState().SetD3D11DeviceContext3(nullptr); +#endif + +#ifdef USE_DIRECT3D11_4 + auto pImmediateContext4 = DXUTGetD3D11DeviceContext4(); + SAFE_RELEASE(pImmediateContext4); + GetDXUTState().SetD3D11DeviceContext4(nullptr); +#endif + + // Report live objects + if ( pd3dDevice ) + { +#ifndef NDEBUG + ID3D11Debug * d3dDebug = nullptr; + if( SUCCEEDED( pd3dDevice->QueryInterface( IID_PPV_ARGS(&d3dDebug) ) ) ) + { + d3dDebug->ReportLiveDeviceObjects( D3D11_RLDO_SUMMARY | D3D11_RLDO_DETAIL ); + d3dDebug->Release(); + } +#endif + + auto pd3dDevice1 = DXUTGetD3D11Device1(); + SAFE_RELEASE( pd3dDevice1 ); + GetDXUTState().SetD3D11Device1(nullptr); + + auto pd3dDevice2 = DXUTGetD3D11Device2(); + SAFE_RELEASE(pd3dDevice2); + GetDXUTState().SetD3D11Device2(nullptr); + +#ifdef USE_DIRECT3D11_3 + auto pd3dDevice3 = DXUTGetD3D11Device3(); + SAFE_RELEASE(pd3dDevice3); + GetDXUTState().SetD3D11Device3(nullptr); +#endif + +#ifdef USE_DIRECT3D11_4 + auto pd3dDevice4 = DXUTGetD3D11Device4(); + SAFE_RELEASE(pd3dDevice4); + GetDXUTState().SetD3D11Device4(nullptr); +#endif + + // Release the D3D device and in debug configs, displays a message box if there + // are unrelease objects. + UINT references = pd3dDevice->Release(); + if( references > 0 ) + { + DXUTDisplayErrorMessage( DXUTERR_NONZEROREFCOUNT ); + DXUT_ERR( L"DXUTCleanup3DEnvironment", DXUTERR_NONZEROREFCOUNT ); + } + } + GetDXUTState().SetD3D11Device( nullptr ); + +#ifndef NDEBUG + { + IDXGIDebug* dxgiDebug = nullptr; + if ( SUCCEEDED( DXUT_Dynamic_DXGIGetDebugInterface( IID_IDXGIDebug, reinterpret_cast( &dxgiDebug ) ) ) ) + { + dxgiDebug->ReportLiveObjects( DXGI_DEBUG_ALL, DXGI_DEBUG_RLO_ALL ); + dxgiDebug->Release(); + } + } +#endif + + if( bReleaseSettings ) + { + auto pOldDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + SAFE_DELETE(pOldDeviceSettings); + GetDXUTState().SetCurrentDeviceSettings( nullptr ); + } + + auto pBackBufferSurfaceDesc = GetDXUTState().GetBackBufferSurfaceDescDXGI(); + ZeroMemory( pBackBufferSurfaceDesc, sizeof( DXGI_SURFACE_DESC ) ); + + GetDXUTState().SetDeviceCreated( false ); + } +} + + +//-------------------------------------------------------------------------------------- +// Low level keyboard hook to disable Windows key to prevent accidental task switching. +//-------------------------------------------------------------------------------------- +LRESULT CALLBACK DXUTLowLevelKeyboardProc( int nCode, WPARAM wParam, LPARAM lParam ) +{ + if( nCode < 0 || nCode != HC_ACTION ) // do not process message + return CallNextHookEx( GetDXUTState().GetKeyboardHook(), nCode, wParam, lParam ); + + bool bEatKeystroke = false; + auto p = reinterpret_cast( lParam ); + switch( wParam ) + { + case WM_KEYDOWN: + case WM_KEYUP: + { + bEatKeystroke = ( !GetDXUTState().GetAllowShortcutKeys() && + ( p->vkCode == VK_LWIN || p->vkCode == VK_RWIN ) ); + break; + } + } + + if( bEatKeystroke ) + return 1; + else + return CallNextHookEx( GetDXUTState().GetKeyboardHook(), nCode, wParam, lParam ); +} + + +//-------------------------------------------------------------------------------------- +// Controls how DXUT behaves when fullscreen and windowed mode with regard to +// shortcut keys (Windows keys, StickyKeys shortcut, ToggleKeys shortcut, FilterKeys shortcut) +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void WINAPI DXUTSetShortcutKeySettings( bool bAllowWhenFullscreen, bool bAllowWhenWindowed ) +{ + GetDXUTState().SetAllowShortcutKeysWhenWindowed( bAllowWhenWindowed ); + GetDXUTState().SetAllowShortcutKeysWhenFullscreen( bAllowWhenFullscreen ); + + // DXUTInit() records initial accessibility states so don't change them until then + if( GetDXUTState().GetDXUTInited() ) + { + if( DXUTIsWindowed() ) + DXUTAllowShortcutKeys( GetDXUTState().GetAllowShortcutKeysWhenWindowed() ); + else + DXUTAllowShortcutKeys( GetDXUTState().GetAllowShortcutKeysWhenFullscreen() ); + } +} + + +//-------------------------------------------------------------------------------------- +// Enables/disables Windows keys, and disables or restores the StickyKeys/ToggleKeys/FilterKeys +// shortcut to help prevent accidental task switching +//-------------------------------------------------------------------------------------- +void DXUTAllowShortcutKeys( _In_ bool bAllowKeys ) +{ + GetDXUTState().SetAllowShortcutKeys( bAllowKeys ); + + if( bAllowKeys ) + { + // Restore StickyKeys/etc to original state and enable Windows key + STICKYKEYS sk = GetDXUTState().GetStartupStickyKeys(); + TOGGLEKEYS tk = GetDXUTState().GetStartupToggleKeys(); + FILTERKEYS fk = GetDXUTState().GetStartupFilterKeys(); + + SystemParametersInfo( SPI_SETSTICKYKEYS, sizeof( STICKYKEYS ), &sk, 0 ); + SystemParametersInfo( SPI_SETTOGGLEKEYS, sizeof( TOGGLEKEYS ), &tk, 0 ); + SystemParametersInfo( SPI_SETFILTERKEYS, sizeof( FILTERKEYS ), &fk, 0 ); + + // Remove the keyboard hoook when it isn't needed to prevent any slow down of other apps + if( GetDXUTState().GetKeyboardHook() ) + { + UnhookWindowsHookEx( GetDXUTState().GetKeyboardHook() ); + GetDXUTState().SetKeyboardHook( nullptr ); + } + } + else + { + // Set low level keyboard hook if haven't already + if( !GetDXUTState().GetKeyboardHook() ) + { + // Set the low-level hook procedure. + HHOOK hKeyboardHook = SetWindowsHookEx( WH_KEYBOARD_LL, DXUTLowLevelKeyboardProc, + GetModuleHandle( nullptr ), 0 ); + GetDXUTState().SetKeyboardHook( hKeyboardHook ); + } + + // Disable StickyKeys/etc shortcuts but if the accessibility feature is on, + // then leave the settings alone as its probably being usefully used + + STICKYKEYS skOff = GetDXUTState().GetStartupStickyKeys(); + if( ( skOff.dwFlags & SKF_STICKYKEYSON ) == 0 ) + { + // Disable the hotkey and the confirmation + skOff.dwFlags &= ~SKF_HOTKEYACTIVE; + skOff.dwFlags &= ~SKF_CONFIRMHOTKEY; + + SystemParametersInfo( SPI_SETSTICKYKEYS, sizeof( STICKYKEYS ), &skOff, 0 ); + } + + TOGGLEKEYS tkOff = GetDXUTState().GetStartupToggleKeys(); + if( ( tkOff.dwFlags & TKF_TOGGLEKEYSON ) == 0 ) + { + // Disable the hotkey and the confirmation + tkOff.dwFlags &= ~TKF_HOTKEYACTIVE; + tkOff.dwFlags &= ~TKF_CONFIRMHOTKEY; + + SystemParametersInfo( SPI_SETTOGGLEKEYS, sizeof( TOGGLEKEYS ), &tkOff, 0 ); + } + + FILTERKEYS fkOff = GetDXUTState().GetStartupFilterKeys(); + if( ( fkOff.dwFlags & FKF_FILTERKEYSON ) == 0 ) + { + // Disable the hotkey and the confirmation + fkOff.dwFlags &= ~FKF_HOTKEYACTIVE; + fkOff.dwFlags &= ~FKF_CONFIRMHOTKEY; + + SystemParametersInfo( SPI_SETFILTERKEYS, sizeof( FILTERKEYS ), &fkOff, 0 ); + } + } +} + + +//-------------------------------------------------------------------------------------- +// Pauses time or rendering. Keeps a ref count so pausing can be layered +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void WINAPI DXUTPause( bool bPauseTime, bool bPauseRendering ) +{ + int nPauseTimeCount = GetDXUTState().GetPauseTimeCount(); + if( bPauseTime ) nPauseTimeCount++; + else + nPauseTimeCount--; + if( nPauseTimeCount < 0 ) nPauseTimeCount = 0; + GetDXUTState().SetPauseTimeCount( nPauseTimeCount ); + + int nPauseRenderingCount = GetDXUTState().GetPauseRenderingCount(); + if( bPauseRendering ) nPauseRenderingCount++; + else + nPauseRenderingCount--; + if( nPauseRenderingCount < 0 ) nPauseRenderingCount = 0; + GetDXUTState().SetPauseRenderingCount( nPauseRenderingCount ); + + if( nPauseTimeCount > 0 ) + { + // Stop the scene from animating + DXUTGetGlobalTimer()->Stop(); + } + else + { + // Restart the timer + DXUTGetGlobalTimer()->Start(); + } + + GetDXUTState().SetRenderingPaused( nPauseRenderingCount > 0 ); + GetDXUTState().SetTimePaused( nPauseTimeCount > 0 ); +} + + +//-------------------------------------------------------------------------------------- +// Starts a user defined timer callback +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT WINAPI DXUTSetTimer( LPDXUTCALLBACKTIMER pCallbackTimer, float fTimeoutInSecs, UINT* pnIDEvent, + void* pCallbackUserContext ) +{ + if( !pCallbackTimer ) + return DXUT_ERR_MSGBOX( L"DXUTSetTimer", E_INVALIDARG ); + + DXUT_TIMER DXUTTimer; + DXUTTimer.pCallbackTimer = pCallbackTimer; + DXUTTimer.pCallbackUserContext = pCallbackUserContext; + DXUTTimer.fTimeoutInSecs = fTimeoutInSecs; + DXUTTimer.fCountdown = fTimeoutInSecs; + DXUTTimer.bEnabled = true; + DXUTTimer.nID = GetDXUTState().GetTimerLastID() + 1; + GetDXUTState().SetTimerLastID( DXUTTimer.nID ); + + auto pTimerList = GetDXUTState().GetTimerList(); + if( !pTimerList ) + { + pTimerList = new (std::nothrow) std::vector; + if( !pTimerList ) + return E_OUTOFMEMORY; + GetDXUTState().SetTimerList( pTimerList ); + } + + pTimerList->push_back( DXUTTimer ); + + if( pnIDEvent ) + *pnIDEvent = DXUTTimer.nID; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Stops a user defined timer callback +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTKillTimer( _In_ UINT nIDEvent ) +{ + auto pTimerList = GetDXUTState().GetTimerList(); + if( !pTimerList ) + return S_FALSE; + + bool bFound = false; + + for( auto it = pTimerList->begin(); it != pTimerList->end(); ++it ) + { + DXUT_TIMER DXUTTimer = *it; + if( DXUTTimer.nID == nIDEvent ) + { + DXUTTimer.bEnabled = false; + *it = DXUTTimer; + bFound = true; + break; + } + } + + if( !bFound ) + return DXUT_ERR_MSGBOX( L"DXUTKillTimer", E_INVALIDARG ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Internal helper function to handle calling the user defined timer callbacks +//-------------------------------------------------------------------------------------- +void DXUTHandleTimers() +{ + float fElapsedTime = DXUTGetElapsedTime(); + + auto pTimerList = GetDXUTState().GetTimerList(); + if( !pTimerList ) + return; + + // Walk through the list of timer callbacks + for( auto it = pTimerList->begin(); it != pTimerList->end(); ++it ) + { + DXUT_TIMER DXUTTimer = *it; + if( DXUTTimer.bEnabled ) + { + DXUTTimer.fCountdown -= fElapsedTime; + + // Call the callback if count down expired + if( DXUTTimer.fCountdown < 0 ) + { + DXUTTimer.pCallbackTimer( DXUTTimer.nID, DXUTTimer.pCallbackUserContext ); + // The callback my have changed the timer. + DXUTTimer = *it; + DXUTTimer.fCountdown = DXUTTimer.fTimeoutInSecs; + } + *it = DXUTTimer; + } + } +} + + +//-------------------------------------------------------------------------------------- +// Display an custom error msg box +//-------------------------------------------------------------------------------------- +void DXUTDisplayErrorMessage( _In_ HRESULT hr ) +{ + WCHAR strBuffer[512]; + + int nExitCode; + bool bFound = true; + switch( hr ) + { + case DXUTERR_NODIRECT3D: + { + nExitCode = 2; + wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"Could not initialize Direct3D 11. " ); + break; + } + case DXUTERR_NOCOMPATIBLEDEVICES: + nExitCode = 3; + if( GetSystemMetrics(SM_REMOTESESSION) != 0 ) + wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"Direct3D does not work over a remote session." ); + else + wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"Could not find any compatible Direct3D devices." ); + break; + case DXUTERR_MEDIANOTFOUND: nExitCode = 4; wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"Could not find required media." ); break; + case DXUTERR_NONZEROREFCOUNT: nExitCode = 5; wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"The Direct3D device has a non-zero reference count, meaning some objects were not released." ); break; + case DXUTERR_CREATINGDEVICE: nExitCode = 6; wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"Failed creating the Direct3D device." ); break; + case DXUTERR_RESETTINGDEVICE: nExitCode = 7; wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"Failed resetting the Direct3D device." ); break; + case DXUTERR_CREATINGDEVICEOBJECTS: nExitCode = 8; wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"An error occurred in the device create callback function." ); break; + case DXUTERR_RESETTINGDEVICEOBJECTS: nExitCode = 9; wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"An error occurred in the device reset callback function." ); break; + // nExitCode 10 means the app exited using a REF device + case DXUTERR_DEVICEREMOVED: nExitCode = 11; wcscpy_s( strBuffer, ARRAYSIZE(strBuffer), L"The Direct3D device was removed." ); break; + default: bFound = false; nExitCode = 1; break; // nExitCode 1 means the API was incorrectly called + + } + + GetDXUTState().SetExitCode(nExitCode); + + bool bShowMsgBoxOnError = GetDXUTState().GetShowMsgBoxOnError(); + if( bFound && bShowMsgBoxOnError ) + { + if( DXUTGetWindowTitle()[0] == 0 ) + MessageBox( DXUTGetHWND(), strBuffer, L"DXUT Application", MB_ICONERROR | MB_OK ); + else + MessageBox( DXUTGetHWND(), strBuffer, DXUTGetWindowTitle(), MB_ICONERROR | MB_OK ); + } +} + + +//-------------------------------------------------------------------------------------- +// Internal function to map MK_* to an array index +//-------------------------------------------------------------------------------------- +int DXUTMapButtonToArrayIndex( _In_ BYTE vButton ) +{ + switch( vButton ) + { + case MK_LBUTTON: + return 0; + case VK_MBUTTON: + case MK_MBUTTON: + return 1; + case MK_RBUTTON: + return 2; + case VK_XBUTTON1: + case MK_XBUTTON1: + return 3; + case VK_XBUTTON2: + case MK_XBUTTON2: + return 4; + } + + return 0; +} + + +//-------------------------------------------------------------------------------------- +// Toggle between full screen and windowed +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTToggleFullScreen() +{ + auto deviceSettings = DXUTGetDeviceSettings(); + if ( deviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_WARP ) + { + // WARP driver type doesn't support fullscreen + return S_FALSE; + } + + auto orginalDeviceSettings = DXUTGetDeviceSettings(); + + deviceSettings.d3d11.sd.Windowed = !deviceSettings.d3d11.sd.Windowed; + + HRESULT hr; + if (!deviceSettings.d3d11.sd.Windowed) + { + DXGI_MODE_DESC adapterDesktopDisplayMode; + hr = DXUTGetD3D11AdapterDisplayMode( deviceSettings.d3d11.AdapterOrdinal, 0, &adapterDesktopDisplayMode ); + if ( FAILED(hr) ) + { + static const DXGI_MODE_DESC s_adapterDesktopDisplayMode = + { + 800, 600, { 0, 0 }, DXGI_FORMAT_R8G8B8A8_UNORM_SRGB + }; + memcpy(&adapterDesktopDisplayMode, &s_adapterDesktopDisplayMode, sizeof(DXGI_MODE_DESC)); + } + + deviceSettings.d3d11.sd.BufferDesc = adapterDesktopDisplayMode; + } + else + { + RECT r = DXUTGetWindowClientRectAtModeChange(); + deviceSettings.d3d11.sd.BufferDesc.Height = r.bottom; + deviceSettings.d3d11.sd.BufferDesc.Width = r.right; + } + + hr = DXUTChangeDevice( &deviceSettings, false ); + + // If hr == E_ABORT, this means the app rejected the device settings in the ModifySettingsCallback so nothing changed + if( FAILED( hr ) && ( hr != E_ABORT ) ) + { + // Failed creating device, try to switch back. + HRESULT hr2 = DXUTChangeDevice( &orginalDeviceSettings, false ); + if( FAILED( hr2 ) ) + { + // If this failed, then shutdown + DXUTShutdown(); + } + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Toggle between HAL/REF and WARP +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTToggleWARP () +{ + auto deviceSettings = DXUTGetDeviceSettings(); + + if ( deviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_HARDWARE || deviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_REFERENCE ) + { + if ( !deviceSettings.d3d11.sd.Windowed ) + { + // WARP driver type doesn't support fullscreen + return S_FALSE; + } + + deviceSettings.d3d11.DriverType = D3D_DRIVER_TYPE_WARP; + } + else if ( deviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_WARP ) + { + deviceSettings.d3d11.DriverType = D3D_DRIVER_TYPE_HARDWARE; + } + + HRESULT hr = DXUTSnapDeviceSettingsToEnumDevice(&deviceSettings, false); + if( SUCCEEDED( hr ) ) + { + DXUTDeviceSettings orginalDeviceSettings = DXUTGetDeviceSettings(); + + // Create a Direct3D device using the new device settings. + // If there is an existing device, then it will either reset or recreate the scene. + hr = DXUTChangeDevice( &deviceSettings, false ); + + // If hr == E_ABORT, this means the app rejected the device settings in the ModifySettingsCallback so nothing changed + if( FAILED( hr ) && ( hr != E_ABORT ) ) + { + // Failed creating device, try to switch back. + HRESULT hr2 = DXUTChangeDevice( &orginalDeviceSettings, false ); + if( FAILED( hr2 ) ) + { + // If this failed, then shutdown + DXUTShutdown(); + } + } + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Toggle between HAL/WARP and REF +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTToggleREF() +{ + auto deviceSettings = DXUTGetDeviceSettings(); + + if ( deviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_HARDWARE ) + { + deviceSettings.d3d11.DriverType = D3D_DRIVER_TYPE_REFERENCE; + } + else if ( deviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_REFERENCE ) + { + deviceSettings.d3d11.DriverType = D3D_DRIVER_TYPE_HARDWARE; + } + else if ( deviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_WARP ) + { + if ( !deviceSettings.d3d11.sd.Windowed ) + { + // WARP driver type doesn't support fullscreen + return S_FALSE; + } + + deviceSettings.d3d11.DriverType = D3D_DRIVER_TYPE_REFERENCE; + } + + HRESULT hr = DXUTSnapDeviceSettingsToEnumDevice(&deviceSettings, false); + if( SUCCEEDED( hr ) ) + { + auto orginalDeviceSettings = DXUTGetDeviceSettings(); + + // Create a Direct3D device using the new device settings. + // If there is an existing device, then it will either reset or recreate the scene. + hr = DXUTChangeDevice( &deviceSettings, false ); + + // If hr == E_ABORT, this means the app rejected the device settings in the ModifySettingsCallback so nothing changed + if( FAILED( hr ) && ( hr != E_ABORT ) ) + { + // Failed creating device, try to switch back. + HRESULT hr2 = DXUTChangeDevice( &orginalDeviceSettings, false ); + if( FAILED( hr2 ) ) + { + // If this failed, then shutdown + DXUTShutdown(); + } + } + } + + return hr; +} + +//-------------------------------------------------------------------------------------- +// Checks to see if DXGI has switched us out of fullscreen or windowed mode +//-------------------------------------------------------------------------------------- +void DXUTCheckForDXGIFullScreenSwitch() +{ + auto pDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + auto pSwapChain = DXUTGetDXGISwapChain(); + assert( pSwapChain ); + _Analysis_assume_( pSwapChain ); + DXGI_SWAP_CHAIN_DESC SCDesc; + if ( FAILED(pSwapChain->GetDesc(&SCDesc)) ) + memset( &SCDesc, 0, sizeof(SCDesc) ); + + BOOL bIsWindowed = ( BOOL )DXUTIsWindowed(); + if( bIsWindowed != SCDesc.Windowed ) + { + pDeviceSettings->d3d11.sd.Windowed = SCDesc.Windowed; + + auto deviceSettings = DXUTGetDeviceSettings(); + + if( bIsWindowed ) + { + GetDXUTState().SetWindowBackBufferWidthAtModeChange( deviceSettings.d3d11.sd.BufferDesc.Width ); + GetDXUTState().SetWindowBackBufferHeightAtModeChange( deviceSettings.d3d11.sd.BufferDesc.Height ); + } + else + { + GetDXUTState().SetFullScreenBackBufferWidthAtModeChange( deviceSettings.d3d11.sd.BufferDesc.Width ); + GetDXUTState().SetFullScreenBackBufferHeightAtModeChange( deviceSettings.d3d11.sd.BufferDesc.Height ); + } + } +} + +_Use_decl_annotations_ +void DXUTResizeDXGIBuffers( UINT Width, UINT Height, BOOL bFullScreen ) +{ + HRESULT hr = S_OK; + RECT rcCurrentClient; + GetClientRect( DXUTGetHWND(), &rcCurrentClient ); + + auto pDevSettings = GetDXUTState().GetCurrentDeviceSettings(); + assert( pDevSettings ); + _Analysis_assume_( pDevSettings ); + + auto pSwapChain = DXUTGetDXGISwapChain(); + + auto pd3dDevice = DXUTGetD3D11Device(); + assert( pd3dDevice ); + _Analysis_assume_( pd3dDevice ); + + auto pd3dImmediateContext = DXUTGetD3D11DeviceContext(); + assert( pd3dImmediateContext ); + _Analysis_assume_( pd3dImmediateContext ); + + // Determine if we're fullscreen + pDevSettings->d3d11.sd.Windowed = !bFullScreen; + + // Call releasing + GetDXUTState().SetInsideDeviceCallback( true ); + LPDXUTCALLBACKD3D11SWAPCHAINRELEASING pCallbackSwapChainReleasing = GetDXUTState().GetD3D11SwapChainReleasingFunc + (); + if( pCallbackSwapChainReleasing ) + pCallbackSwapChainReleasing( GetDXUTState().GetD3D11SwapChainResizedFuncUserContext() ); + GetDXUTState().SetInsideDeviceCallback( false ); + + // Release our old depth stencil texture and view + auto pDS = GetDXUTState().GetD3D11DepthStencil(); + SAFE_RELEASE( pDS ); + GetDXUTState().SetD3D11DepthStencil( nullptr ); + auto pDSV = GetDXUTState().GetD3D11DepthStencilView(); + SAFE_RELEASE( pDSV ); + GetDXUTState().SetD3D11DepthStencilView( nullptr ); + + // Release our old render target view + auto pRTV = GetDXUTState().GetD3D11RenderTargetView(); + SAFE_RELEASE( pRTV ); + GetDXUTState().SetD3D11RenderTargetView( nullptr ); + + // Alternate between 0 and DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH when resizing buffers. + // When in windowed mode, we want 0 since this allows the app to change to the desktop + // resolution from windowed mode during alt+enter. However, in fullscreen mode, we want + // the ability to change display modes from the Device Settings dialog. Therefore, we + // want to set the DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH flag. + UINT Flags = 0; + if( bFullScreen ) + Flags = DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH; + + // ResizeBuffers + V( pSwapChain->ResizeBuffers( pDevSettings->d3d11.sd.BufferCount, + Width, + Height, + pDevSettings->d3d11.sd.BufferDesc.Format, + Flags ) ); + + if( !GetDXUTState().GetDoNotStoreBufferSize() ) + { + pDevSettings->d3d11.sd.BufferDesc.Width = ( UINT )rcCurrentClient.right; + pDevSettings->d3d11.sd.BufferDesc.Height = ( UINT )rcCurrentClient.bottom; + } + + // Save off backbuffer desc + DXUTUpdateBackBufferDesc(); + + // Update the device stats text + DXUTUpdateStaticFrameStats(); + + // Setup the render target view and viewport + hr = DXUTCreateD3D11Views( pd3dDevice, pd3dImmediateContext, pDevSettings ); + if( FAILED( hr ) ) + { + DXUT_ERR( L"DXUTCreateD3D11Views", hr ); + return; + } + + // Setup cursor based on current settings (window/fullscreen mode, show cursor state, clip cursor state) + DXUTSetupCursor(); + + // Call the app's SwapChain reset callback + GetDXUTState().SetInsideDeviceCallback( true ); + auto pBackBufferSurfaceDesc = DXUTGetDXGIBackBufferSurfaceDesc(); + LPDXUTCALLBACKD3D11SWAPCHAINRESIZED pCallbackSwapChainResized = GetDXUTState().GetD3D11SwapChainResizedFunc(); + hr = S_OK; + if( pCallbackSwapChainResized ) + hr = pCallbackSwapChainResized( pd3dDevice, pSwapChain, pBackBufferSurfaceDesc, + GetDXUTState().GetD3D11SwapChainResizedFuncUserContext() ); + GetDXUTState().SetInsideDeviceCallback( false ); + if( FAILED( hr ) ) + { + // If callback failed, cleanup + DXUT_ERR( L"DeviceResetCallback", hr ); + if( hr != DXUTERR_MEDIANOTFOUND ) + hr = DXUTERR_RESETTINGDEVICEOBJECTS; + + GetDXUTState().SetInsideDeviceCallback( true ); + pCallbackSwapChainReleasing = + GetDXUTState().GetD3D11SwapChainReleasingFunc(); + if( pCallbackSwapChainReleasing ) + pCallbackSwapChainReleasing( GetDXUTState().GetD3D11SwapChainResizedFuncUserContext() ); + GetDXUTState().SetInsideDeviceCallback( false ); + DXUTPause( false, false ); + PostQuitMessage( 0 ); + } + else + { + GetDXUTState().SetDeviceObjectsReset( true ); + DXUTPause( false, false ); + } +} + +//-------------------------------------------------------------------------------------- +// Checks if DXGI buffers need to change +//-------------------------------------------------------------------------------------- +void DXUTCheckForDXGIBufferChange() +{ + if(DXUTGetDXGISwapChain() && !GetDXUTState().GetReleasingSwapChain() ) + { + //DXUTgetdxgi + auto pSwapChain = DXUTGetDXGISwapChain(); + assert(pSwapChain); + _Analysis_assume_(pSwapChain); + +// workaround for SAL bug in DXGI header +#pragma warning(push) +#pragma warning( disable:4616 6309 6387 ) + // Determine if we're fullscreen + BOOL bFullScreen; + if ( FAILED(pSwapChain->GetFullscreenState(&bFullScreen, nullptr)) ) + bFullScreen = FALSE; +#pragma warning(pop) + + DXUTResizeDXGIBuffers( 0, 0, bFullScreen ); + + ShowWindow( DXUTGetHWND(), SW_SHOW ); + } +} + +//-------------------------------------------------------------------------------------- +// Checks if the window client rect has changed and if it has, then reset the device +//-------------------------------------------------------------------------------------- +void DXUTCheckForWindowSizeChange() +{ + // Skip the check for various reasons + + if( GetDXUTState().GetIgnoreSizeChange() || !GetDXUTState().GetDeviceCreated() ) + return; + + DXUTCheckForDXGIBufferChange(); +} + + +//-------------------------------------------------------------------------------------- +// Checks to see if the HWND changed monitors, and if it did it creates a device +// from the monitor's adapter and recreates the scene. +//-------------------------------------------------------------------------------------- +void DXUTCheckForWindowChangingMonitors() +{ + // Skip this check for various reasons + if( !GetDXUTState().GetAutoChangeAdapter() || + GetDXUTState().GetIgnoreSizeChange() || !GetDXUTState().GetDeviceCreated() || !DXUTIsWindowed() ) + return; + + HRESULT hr; + HMONITOR hWindowMonitor = DXUTMonitorFromWindow( DXUTGetHWND(), MONITOR_DEFAULTTOPRIMARY ); + HMONITOR hAdapterMonitor = GetDXUTState().GetAdapterMonitor(); + if( hWindowMonitor != hAdapterMonitor ) + { + UINT newOrdinal; + if( SUCCEEDED( DXUTGetAdapterOrdinalFromMonitor( hWindowMonitor, &newOrdinal ) ) ) + { + // Find the closest valid device settings with the new ordinal + auto deviceSettings = DXUTGetDeviceSettings(); + deviceSettings.d3d11.AdapterOrdinal = newOrdinal; + UINT newOutput; + if( SUCCEEDED( DXUTGetOutputOrdinalFromMonitor( hWindowMonitor, &newOutput ) ) ) + deviceSettings.d3d11.Output = newOutput; + + hr = DXUTSnapDeviceSettingsToEnumDevice( &deviceSettings, false ); + if( SUCCEEDED( hr ) ) + { + // Create a Direct3D device using the new device settings. + // If there is an existing device, then it will either reset or recreate the scene. + hr = DXUTChangeDevice( &deviceSettings, false ); + + // If hr == E_ABORT, this means the app rejected the device settings in the ModifySettingsCallback + if( hr == E_ABORT ) + { + // so nothing changed and keep from attempting to switch adapters next time + GetDXUTState().SetAutoChangeAdapter( false ); + } + else if( FAILED( hr ) ) + { + DXUTShutdown(); + DXUTPause( false, false ); + return; + } + } + } + } +} + + +//-------------------------------------------------------------------------------------- +// Returns the HMONITOR attached to an adapter/output +//-------------------------------------------------------------------------------------- +HMONITOR DXUTGetMonitorFromAdapter( _In_ DXUTDeviceSettings* pDeviceSettings ) +{ + auto pD3DEnum = DXUTGetD3D11Enumeration(); + assert( pD3DEnum ); + _Analysis_assume_( pD3DEnum ); + auto pOutputInfo = pD3DEnum->GetOutputInfo( pDeviceSettings->d3d11.AdapterOrdinal, + pDeviceSettings->d3d11.Output ); + if( !pOutputInfo ) + return 0; + return DXUTMonitorFromRect( &pOutputInfo->Desc.DesktopCoordinates, MONITOR_DEFAULTTONEAREST ); +} + + +//-------------------------------------------------------------------------------------- +// Look for an adapter ordinal that is tied to a HMONITOR +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DXUTGetAdapterOrdinalFromMonitor( HMONITOR hMonitor, UINT* pAdapterOrdinal ) +{ + *pAdapterOrdinal = 0; + + // Get the monitor handle information + MONITORINFOEX mi; + mi.cbSize = sizeof( MONITORINFOEX ); + DXUTGetMonitorInfo( hMonitor, &mi ); + + // Search for this monitor in our enumeration hierarchy. + auto pd3dEnum = DXUTGetD3D11Enumeration(); + auto pAdapterList = pd3dEnum->GetAdapterInfoList(); + for( auto it = pAdapterList->cbegin(); it != pAdapterList->cend(); ++it ) + { + auto pAdapterInfo = *it; + for( auto jit = pAdapterInfo->outputInfoList.cbegin(); jit != pAdapterInfo->outputInfoList.cend(); ++jit ) + { + auto pOutputInfo = *jit; + // Convert output device name from MBCS to Unicode + if( wcsncmp( pOutputInfo->Desc.DeviceName, mi.szDevice, sizeof( mi.szDevice ) / sizeof + ( mi.szDevice[0] ) ) == 0 ) + { + *pAdapterOrdinal = pAdapterInfo->AdapterOrdinal; + return S_OK; + } + } + } + return E_FAIL; +} + + +//-------------------------------------------------------------------------------------- +// Look for a monitor ordinal that is tied to a HMONITOR (D3D11-only) +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DXUTGetOutputOrdinalFromMonitor( HMONITOR hMonitor, UINT* pOutputOrdinal ) +{ + // Get the monitor handle information + MONITORINFOEX mi; + mi.cbSize = sizeof( MONITORINFOEX ); + DXUTGetMonitorInfo( hMonitor, &mi ); + + // Search for this monitor in our enumeration hierarchy. + auto pd3dEnum = DXUTGetD3D11Enumeration(); + auto pAdapterList = pd3dEnum->GetAdapterInfoList(); + for( auto it = pAdapterList->cbegin(); it != pAdapterList->cend(); ++it ) + { + auto pAdapterInfo = *it; + for( auto jit = pAdapterInfo->outputInfoList.cbegin(); jit != pAdapterInfo->outputInfoList.cend(); ++jit ) + { + auto pOutputInfo = *jit; + DXGI_OUTPUT_DESC Desc; + if ( FAILED(pOutputInfo->m_pOutput->GetDesc(&Desc)) ) + memset( &Desc, 0, sizeof(Desc) ); + + if( hMonitor == Desc.Monitor ) + { + *pOutputOrdinal = pOutputInfo->Output; + return S_OK; + } + } + } + + return E_FAIL; +} + + +//-------------------------------------------------------------------------------------- +// This method is called when D3DERR_DEVICEREMOVED is returned from an API. DXUT +// calls the application's DeviceRemoved callback to inform it of the event. The +// application returns true if it wants DXUT to look for a closest device to run on. +// If no device is found, or the app returns false, DXUT shuts down. +//-------------------------------------------------------------------------------------- +HRESULT DXUTHandleDeviceRemoved() +{ + HRESULT hr = S_OK; + + // Device has been removed. Call the application's callback if set. If no callback + // has been set, then just look for a new device + bool bLookForNewDevice = true; + LPDXUTCALLBACKDEVICEREMOVED pDeviceRemovedFunc = GetDXUTState().GetDeviceRemovedFunc(); + if( pDeviceRemovedFunc ) + bLookForNewDevice = pDeviceRemovedFunc( GetDXUTState().GetDeviceRemovedFuncUserContext() ); + + if( bLookForNewDevice ) + { + auto pDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + + + hr = DXUTSnapDeviceSettingsToEnumDevice( pDeviceSettings, false); + if( SUCCEEDED( hr ) ) + { + // Change to a Direct3D device created from the new device settings + // that is compatible with the removed device. + hr = DXUTChangeDevice( pDeviceSettings, false ); + if( SUCCEEDED( hr ) ) + return S_OK; + } + } + + // The app does not wish to continue or continuing is not possible. + return DXUTERR_DEVICEREMOVED; +} + + +//-------------------------------------------------------------------------------------- +// Stores back buffer surface desc in GetDXUTState().GetBackBufferSurfaceDesc10() +//-------------------------------------------------------------------------------------- +void DXUTUpdateBackBufferDesc() +{ + HRESULT hr; + ID3D11Texture2D* pBackBuffer; + auto pSwapChain = GetDXUTState().GetDXGISwapChain(); + assert( pSwapChain ); + _Analysis_assume_( pSwapChain ); + hr = pSwapChain->GetBuffer( 0, IID_PPV_ARGS(&pBackBuffer) ); + auto pBBufferSurfaceDesc = GetDXUTState().GetBackBufferSurfaceDescDXGI(); + ZeroMemory( pBBufferSurfaceDesc, sizeof( DXGI_SURFACE_DESC ) ); + if( SUCCEEDED( hr ) ) + { + D3D11_TEXTURE2D_DESC TexDesc; + pBackBuffer->GetDesc( &TexDesc ); + pBBufferSurfaceDesc->Width = ( UINT )TexDesc.Width; + pBBufferSurfaceDesc->Height = ( UINT )TexDesc.Height; + pBBufferSurfaceDesc->Format = TexDesc.Format; + pBBufferSurfaceDesc->SampleDesc = TexDesc.SampleDesc; + SAFE_RELEASE( pBackBuffer ); + } +} + + +//-------------------------------------------------------------------------------------- +// Setup cursor based on current settings (window/fullscreen mode, show cursor state, clip cursor state) +//-------------------------------------------------------------------------------------- +void DXUTSetupCursor() +{ + // Clip cursor if requested + if( !DXUTIsWindowed() && GetDXUTState().GetClipCursorWhenFullScreen() ) + { + // Confine cursor to full screen window + RECT rcWindow; + GetWindowRect( DXUTGetHWNDDeviceFullScreen(), &rcWindow ); + ClipCursor( &rcWindow ); + } + else + { + ClipCursor( nullptr ); + } +} + + +//-------------------------------------------------------------------------------------- +// Updates the static part of the frame stats so it doesn't have be generated every frame +//-------------------------------------------------------------------------------------- +void DXUTUpdateStaticFrameStats() +{ + if( GetDXUTState().GetNoStats() ) + return; + + auto pDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + if( !pDeviceSettings ) + return; + + // D3D11 + auto pd3dEnum = DXUTGetD3D11Enumeration(); + if( !pd3dEnum ) + return; + + auto pDeviceSettingsCombo = pd3dEnum->GetDeviceSettingsCombo( + pDeviceSettings->d3d11.AdapterOrdinal, + pDeviceSettings->d3d11.sd.BufferDesc.Format, pDeviceSettings->d3d11.sd.Windowed ); + if( !pDeviceSettingsCombo ) + return; + + WCHAR strFmt[100]; + wcscpy_s( strFmt, 100, DXUTDXGIFormatToString( pDeviceSettingsCombo->BackBufferFormat, false ) ); + + WCHAR strMultiSample[100]; + swprintf_s( strMultiSample, 100, L" (MS%u, Q%u)", pDeviceSettings->d3d11.sd.SampleDesc.Count, + pDeviceSettings->d3d11.sd.SampleDesc.Quality ); + auto pstrStaticFrameStats = GetDXUTState().GetStaticFrameStats(); + swprintf_s( pstrStaticFrameStats, 256, L"D3D11 %%ls Vsync %ls (%ux%u), %ls%ls", + ( pDeviceSettings->d3d11.SyncInterval == 0 ) ? L"off" : L"on", + pDeviceSettings->d3d11.sd.BufferDesc.Width, pDeviceSettings->d3d11.sd.BufferDesc.Height, + strFmt, strMultiSample ); +} + + +//-------------------------------------------------------------------------------------- +// Updates the frames/sec stat once per second +//-------------------------------------------------------------------------------------- +void DXUTUpdateFrameStats() +{ + if( GetDXUTState().GetNoStats() ) + return; + + // Keep track of the frame count + double fLastTime = GetDXUTState().GetLastStatsUpdateTime(); + DWORD dwFrames = GetDXUTState().GetLastStatsUpdateFrames(); + double fAbsTime = GetDXUTState().GetAbsoluteTime(); + dwFrames++; + GetDXUTState().SetLastStatsUpdateFrames( dwFrames ); + + // Update the scene stats once per second + if( fAbsTime - fLastTime > 1.0f ) + { + float fFPS = ( float )( dwFrames / ( fAbsTime - fLastTime ) ); + GetDXUTState().SetFPS( fFPS ); + GetDXUTState().SetLastStatsUpdateTime( fAbsTime ); + GetDXUTState().SetLastStatsUpdateFrames( 0 ); + + auto pstrFPS = GetDXUTState().GetFPSStats(); + swprintf_s( pstrFPS, 64, L"%0.2f fps ", fFPS ); + } +} + + +//-------------------------------------------------------------------------------------- +// Returns a string describing the current device. If bShowFPS is true, then +// the string contains the frames/sec. If "-nostats" was used in +// the command line, the string will be blank +//-------------------------------------------------------------------------------------- +LPCWSTR WINAPI DXUTGetFrameStats( _In_ bool bShowFPS ) +{ + auto pstrFrameStats = GetDXUTState().GetFrameStats(); + const WCHAR* pstrFPS = ( bShowFPS ) ? GetDXUTState().GetFPSStats() : L""; + WCHAR* pstrStats = GetDXUTState().GetStaticFrameStats(); + swprintf_s( pstrFrameStats, 256, pstrStats, pstrFPS ); + return pstrFrameStats; +} + + +//-------------------------------------------------------------------------------------- +// Updates the string which describes the device +//-------------------------------------------------------------------------------------- +#pragma warning( suppress : 6101 ) +_Use_decl_annotations_ +void DXUTUpdateD3D11DeviceStats( D3D_DRIVER_TYPE DeviceType, D3D_FEATURE_LEVEL featureLevel, DXGI_ADAPTER_DESC* pAdapterDesc ) +{ + if( GetDXUTState().GetNoStats() ) + return; + + // Store device description + auto pstrDeviceStats = GetDXUTState().GetDeviceStats(); + if( DeviceType == D3D_DRIVER_TYPE_REFERENCE ) + wcscpy_s( pstrDeviceStats, 256, L"REFERENCE" ); + else if( DeviceType == D3D_DRIVER_TYPE_HARDWARE ) + wcscpy_s( pstrDeviceStats, 256, L"HARDWARE" ); + else if( DeviceType == D3D_DRIVER_TYPE_SOFTWARE ) + wcscpy_s( pstrDeviceStats, 256, L"SOFTWARE" ); + else if( DeviceType == D3D_DRIVER_TYPE_WARP ) + wcscpy_s( pstrDeviceStats, 256, L"WARP" ); + + if( DeviceType == D3D_DRIVER_TYPE_HARDWARE ) + { + // Be sure not to overflow m_strDeviceStats when appending the adapter + // description, since it can be long. + wcscat_s( pstrDeviceStats, 256, L": " ); + + // Try to get a unique description from the CD3D11EnumDeviceSettingsCombo + auto pDeviceSettings = GetDXUTState().GetCurrentDeviceSettings(); + if( !pDeviceSettings ) + return; + + auto pd3dEnum = DXUTGetD3D11Enumeration(); + assert( pd3dEnum ); + _Analysis_assume_( pd3dEnum ); + auto pDeviceSettingsCombo = pd3dEnum->GetDeviceSettingsCombo( + pDeviceSettings->d3d11.AdapterOrdinal, + pDeviceSettings->d3d11.sd.BufferDesc.Format, pDeviceSettings->d3d11.sd.Windowed ); + if( pDeviceSettingsCombo ) + wcscat_s( pstrDeviceStats, 256, pDeviceSettingsCombo->pAdapterInfo->szUniqueDescription ); + else + wcscat_s( pstrDeviceStats, 256, pAdapterDesc->Description ); + } + + switch( featureLevel ) + { + case D3D_FEATURE_LEVEL_9_1: + wcscat_s( pstrDeviceStats, 256, L" (FL 9.1)" ); + break; + case D3D_FEATURE_LEVEL_9_2: + wcscat_s( pstrDeviceStats, 256, L" (FL 9.2)" ); + break; + case D3D_FEATURE_LEVEL_9_3: + wcscat_s( pstrDeviceStats, 256, L" (FL 9.3)" ); + break; + case D3D_FEATURE_LEVEL_10_0: + wcscat_s( pstrDeviceStats, 256, L" (FL 10.0)" ); + break; + case D3D_FEATURE_LEVEL_10_1: + wcscat_s( pstrDeviceStats, 256, L" (FL 10.1)" ); + break; + case D3D_FEATURE_LEVEL_11_0: + wcscat_s( pstrDeviceStats, 256, L" (FL 11.0)" ); + break; + case D3D_FEATURE_LEVEL_11_1: + wcscat_s( pstrDeviceStats, 256, L" (FL 11.1)" ); + break; +#if defined(USE_DIRECT3D11_3) || defined(USE_DIRECT3D11_4) + case D3D_FEATURE_LEVEL_12_0: + wcscat_s(pstrDeviceStats, 256, L" (FL 12.0)"); + break; + case D3D_FEATURE_LEVEL_12_1: + wcscat_s(pstrDeviceStats, 256, L" (FL 12.1)"); + break; +#endif + } +} + + +//-------------------------------------------------------------------------------------- +// Misc functions +//-------------------------------------------------------------------------------------- +DXUTDeviceSettings WINAPI DXUTGetDeviceSettings() +{ + // Return a copy of device settings of the current device. If no device exists yet, then + // return a blank device settings struct + auto pDS = GetDXUTState().GetCurrentDeviceSettings(); + if( pDS ) + { + return *pDS; + } + else + { + DXUTDeviceSettings ds = {}; + return ds; + } +} + +bool WINAPI DXUTIsVsyncEnabled() +{ + auto pDS = GetDXUTState().GetCurrentDeviceSettings(); + if( pDS ) + { + return ( pDS->d3d11.SyncInterval == 0 ); + } + else + { + return true; + } +}; + +bool WINAPI DXUTIsKeyDown( _In_ BYTE vKey ) +{ + bool* bKeys = GetDXUTState().GetKeys(); + if( vKey >= 0xA0 && vKey <= 0xA5 ) // VK_LSHIFT, VK_RSHIFT, VK_LCONTROL, VK_RCONTROL, VK_LMENU, VK_RMENU + return GetAsyncKeyState( vKey ) != 0; // these keys only are tracked via GetAsyncKeyState() + else if( vKey >= 0x01 && vKey <= 0x06 && vKey != 0x03 ) // mouse buttons (VK_*BUTTON) + return DXUTIsMouseButtonDown( vKey ); + else + return bKeys[vKey]; +} + +bool WINAPI DXUTWasKeyPressed( _In_ BYTE vKey ) +{ + bool* bLastKeys = GetDXUTState().GetLastKeys(); + bool* bKeys = GetDXUTState().GetKeys(); + GetDXUTState().SetAppCalledWasKeyPressed( true ); + return ( !bLastKeys[vKey] && bKeys[vKey] ); +} + +bool WINAPI DXUTIsMouseButtonDown( _In_ BYTE vButton ) +{ + bool* bMouseButtons = GetDXUTState().GetMouseButtons(); + int nIndex = DXUTMapButtonToArrayIndex( vButton ); + return bMouseButtons[nIndex]; +} + +void WINAPI DXUTSetMultimonSettings( _In_ bool bAutoChangeAdapter ) +{ + GetDXUTState().SetAutoChangeAdapter( bAutoChangeAdapter ); +} + +_Use_decl_annotations_ +void WINAPI DXUTSetHotkeyHandling( bool bAltEnterToToggleFullscreen, bool bEscapeToQuit, bool bPauseToToggleTimePause ) +{ + GetDXUTState().SetHandleEscape( bEscapeToQuit ); + GetDXUTState().SetHandleAltEnter( bAltEnterToToggleFullscreen ); + GetDXUTState().SetHandlePause( bPauseToToggleTimePause ); +} + +_Use_decl_annotations_ +void WINAPI DXUTSetCursorSettings( bool bShowCursorWhenFullScreen, bool bClipCursorWhenFullScreen ) +{ + GetDXUTState().SetClipCursorWhenFullScreen( bClipCursorWhenFullScreen ); + GetDXUTState().SetShowCursorWhenFullScreen( bShowCursorWhenFullScreen ); + DXUTSetupCursor(); +} + +void WINAPI DXUTSetWindowSettings( _In_ bool bCallDefWindowProc ) +{ + GetDXUTState().SetCallDefWindowProc( bCallDefWindowProc ); +} + +_Use_decl_annotations_ +void WINAPI DXUTSetConstantFrameTime( bool bEnabled, float fTimePerFrame ) +{ + if( GetDXUTState().GetOverrideConstantFrameTime() ) + { + bEnabled = GetDXUTState().GetOverrideConstantFrameTime(); + fTimePerFrame = GetDXUTState().GetOverrideConstantTimePerFrame(); + } + GetDXUTState().SetConstantFrameTime( bEnabled ); + GetDXUTState().SetTimePerFrame( fTimePerFrame ); +} + + +//-------------------------------------------------------------------------------------- +// Resets the state associated with DXUT +//-------------------------------------------------------------------------------------- +void WINAPI DXUTResetFrameworkState() +{ + GetDXUTState().Destroy(); + GetDXUTState().Create(); +} + + +//-------------------------------------------------------------------------------------- +// Closes down the window. When the window closes, it will cleanup everything +//-------------------------------------------------------------------------------------- +void WINAPI DXUTShutdown( _In_ int nExitCode ) +{ + HWND hWnd = DXUTGetHWND(); + if( hWnd ) + SendMessage( hWnd, WM_CLOSE, 0, 0 ); + + GetDXUTState().SetExitCode( nExitCode ); + + DXUTCleanup3DEnvironment( true ); + + // Restore shortcut keys (Windows key, accessibility shortcuts) to original state + // This is important to call here if the shortcuts are disabled, + // because accessibility setting changes are permanent. + // This means that if this is not done then the accessibility settings + // might not be the same as when the app was started. + // If the app crashes without restoring the settings, this is also true so it + // would be wise to backup/restore the settings from a file so they can be + // restored when the crashed app is run again. + DXUTAllowShortcutKeys( true ); + + // Shutdown D3D11 + auto pDXGIFactory = GetDXUTState().GetDXGIFactory(); + SAFE_RELEASE( pDXGIFactory ); + GetDXUTState().SetDXGIFactory( nullptr ); +} + + +//-------------------------------------------------------------------------------------- +// Tells DXUT whether to operate in gamma correct mode +//-------------------------------------------------------------------------------------- +void WINAPI DXUTSetIsInGammaCorrectMode( _In_ bool bGammaCorrect ) +{ + GetDXUTState().SetIsInGammaCorrectMode( bGammaCorrect ); +} + + +//-------------------------------------------------------------------------------------- +void DXUTApplyDefaultDeviceSettings(DXUTDeviceSettings *modifySettings) +{ + ZeroMemory( modifySettings, sizeof( DXUTDeviceSettings ) ); + + modifySettings->d3d11.AdapterOrdinal = 0; + modifySettings->d3d11.AutoCreateDepthStencil = true; + modifySettings->d3d11.AutoDepthStencilFormat = DXGI_FORMAT_D24_UNORM_S8_UINT; +#if defined(DEBUG) || defined(_DEBUG) + modifySettings->d3d11.CreateFlags |= D3D11_CREATE_DEVICE_DEBUG; +#else + modifySettings->d3d11.CreateFlags = 0; +#endif + modifySettings->d3d11.DriverType = D3D_DRIVER_TYPE_HARDWARE; + modifySettings->d3d11.Output = 0; + modifySettings->d3d11.PresentFlags = 0; + modifySettings->d3d11.sd.BufferCount = 2; + modifySettings->d3d11.sd.BufferDesc.Format = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + modifySettings->d3d11.sd.BufferDesc.Height = 600; + modifySettings->d3d11.sd.BufferDesc.RefreshRate.Numerator = 0; + modifySettings->d3d11.sd.BufferDesc.RefreshRate.Denominator = 0; + modifySettings->d3d11.sd.BufferDesc.Scaling = DXGI_MODE_SCALING_UNSPECIFIED; + modifySettings->d3d11.sd.BufferDesc.ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED; + modifySettings->d3d11.sd.BufferDesc.Width = 800; + modifySettings->d3d11.sd.BufferUsage = 32; + modifySettings->d3d11.sd.Flags = DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH ; + modifySettings->d3d11.sd.OutputWindow = DXUTGetHWND(); + modifySettings->d3d11.sd.SampleDesc.Count = 1; + modifySettings->d3d11.sd.SampleDesc.Quality = 0; + modifySettings->d3d11.sd.SwapEffect = DXGI_SWAP_EFFECT_DISCARD; + modifySettings->d3d11.sd.Windowed = TRUE; + modifySettings->d3d11.SyncInterval = 0; +} + + +//-------------------------------------------------------------------------------------- +// Update settings based on what is enumeratabled +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DXUTSnapDeviceSettingsToEnumDevice( DXUTDeviceSettings* pDeviceSettings, bool forceEnum, D3D_FEATURE_LEVEL forceFL ) +{ + if( GetSystemMetrics(SM_REMOTESESSION) != 0 ) + { + pDeviceSettings->d3d11.sd.Windowed = TRUE; + } + int bestModeIndex=0; + int bestMSAAIndex=0; + + //DXUTSetDefaultDeviceSettings + CD3D11Enumeration *pEnum = DXUTGetD3D11Enumeration( forceEnum, true, forceFL); + + CD3D11EnumAdapterInfo* pAdapterInfo = nullptr; + auto pAdapterList = pEnum->GetAdapterInfoList(); + for( auto it = pAdapterList->cbegin(); it != pAdapterList->cend(); ++it ) + { + auto tempAdapterInfo = *it; + if (tempAdapterInfo->AdapterOrdinal == pDeviceSettings->d3d11.AdapterOrdinal) pAdapterInfo = tempAdapterInfo; + } + if ( !pAdapterInfo ) + { + if ( pAdapterList->empty() || pDeviceSettings->d3d11.AdapterOrdinal > 0 ) + { + return E_FAIL; // no adapters found. + } + pAdapterInfo = *pAdapterList->cbegin(); + } + CD3D11EnumDeviceSettingsCombo* pDeviceSettingsCombo = nullptr; + float biggestScore = 0; + + for( size_t iDeviceCombo = 0; iDeviceCombo < pAdapterInfo->deviceSettingsComboList.size(); iDeviceCombo++ ) + { + CD3D11EnumDeviceSettingsCombo* tempDeviceSettingsCombo = pAdapterInfo->deviceSettingsComboList[ iDeviceCombo ]; + + int bestMode; + int bestMSAA; + float score = DXUTRankD3D11DeviceCombo(tempDeviceSettingsCombo, &(pDeviceSettings->d3d11), bestMode, bestMSAA ); + if (score > biggestScore) + { + biggestScore = score; + pDeviceSettingsCombo = tempDeviceSettingsCombo; + bestModeIndex = bestMode; + bestMSAAIndex = bestMSAA; + } + } + if (!pDeviceSettingsCombo ) + { + return E_FAIL; // no settings found. + } + + pDeviceSettings->d3d11.AdapterOrdinal = pDeviceSettingsCombo->AdapterOrdinal; + pDeviceSettings->d3d11.DriverType = pDeviceSettingsCombo->DeviceType; + pDeviceSettings->d3d11.Output = pDeviceSettingsCombo->Output; + + pDeviceSettings->d3d11.sd.Windowed = pDeviceSettingsCombo->Windowed; + if( GetSystemMetrics(SM_REMOTESESSION) != 0 ) + { + pDeviceSettings->d3d11.sd.Windowed = TRUE; + } + if (pDeviceSettingsCombo->pOutputInfo) + { + auto bestDisplayMode = pDeviceSettingsCombo->pOutputInfo->displayModeList[ bestModeIndex ]; + if (!pDeviceSettingsCombo->Windowed) + { + pDeviceSettings->d3d11.sd.BufferDesc.Height = bestDisplayMode.Height; + pDeviceSettings->d3d11.sd.BufferDesc.Width = bestDisplayMode.Width; + pDeviceSettings->d3d11.sd.BufferDesc.RefreshRate.Numerator = bestDisplayMode.RefreshRate.Numerator; + pDeviceSettings->d3d11.sd.BufferDesc.RefreshRate.Denominator = bestDisplayMode.RefreshRate.Denominator; + pDeviceSettings->d3d11.sd.BufferDesc.Scaling = bestDisplayMode.Scaling; + pDeviceSettings->d3d11.sd.BufferDesc.ScanlineOrdering = bestDisplayMode.ScanlineOrdering; + } + } + if (pDeviceSettings->d3d11.DeviceFeatureLevel == 0) + pDeviceSettings->d3d11.DeviceFeatureLevel = pDeviceSettingsCombo->pDeviceInfo->SelectedLevel; + + if ( pDeviceSettings->d3d11.DriverType == D3D_DRIVER_TYPE_WARP ) + { + D3D_FEATURE_LEVEL maxWarpFL = pEnum->GetWARPFeaturevel(); + + if ( pDeviceSettings->d3d11.DeviceFeatureLevel > maxWarpFL ) + pDeviceSettings->d3d11.DeviceFeatureLevel = maxWarpFL; + } + + if ( pDeviceSettings->d3d11.DriverType == D3D_DRIVER_TYPE_REFERENCE ) + { + D3D_FEATURE_LEVEL maxRefFL = pEnum->GetREFFeaturevel(); + + if ( pDeviceSettings->d3d11.DeviceFeatureLevel > maxRefFL ) + pDeviceSettings->d3d11.DeviceFeatureLevel = maxRefFL; + } + + pDeviceSettings->d3d11.sd.SampleDesc.Count = pDeviceSettingsCombo->multiSampleCountList[ bestMSAAIndex ]; + if (pDeviceSettings->d3d11.sd.SampleDesc.Quality > pDeviceSettingsCombo->multiSampleQualityList[ bestMSAAIndex ] - 1) + pDeviceSettings->d3d11.sd.SampleDesc.Quality = pDeviceSettingsCombo->multiSampleQualityList[ bestMSAAIndex ] - 1; + + pDeviceSettings->d3d11.sd.BufferDesc.Format = pDeviceSettingsCombo->BackBufferFormat; + + return S_OK; +} diff --git a/src/DX11/framework/dxut/Core/DXUT.h b/src/DX11/framework/dxut/Core/DXUT.h new file mode 100644 index 0000000..39f97ee --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT.h @@ -0,0 +1,337 @@ +//-------------------------------------------------------------------------------------- +// File: DXUT.h +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +#ifndef UNICODE +#error "DXUT requires a Unicode build." +#endif + +#ifndef STRICT +#define STRICT +#endif + +// If app hasn't choosen, set to work with Windows Vista and beyond +#ifndef WINVER +#define WINVER 0x0600 +#endif +#ifndef _WIN32_WINDOWS +#define _WIN32_WINDOWS 0x0600 +#endif +#ifndef _WIN32_WINNT +#define _WIN32_WINNT 0x0600 +#endif + +#if defined(USE_DIRECT3D11_4) && !defined(USE_DIRECT3D11_3) +#define USE_DIRECT3D11_3 +#endif + +#if (_WIN32_WINNT >= 0x0A00) && !defined(USE_DIRECT3D11_3) +#define USE_DIRECT3D11_3 +#endif + +// #define DXUT_AUTOLIB to automatically include the libs needed for DXUT +#ifdef DXUT_AUTOLIB +#pragma comment( lib, "comctl32.lib" ) +#pragma comment( lib, "dxguid.lib" ) +#pragma comment( lib, "d3dcompiler.lib" ) +#pragma comment( lib, "ole32.lib" ) +#pragma comment( lib, "uuid.lib" ) +#endif + +#pragma warning( disable : 4481 ) + +// Standard Windows includes +#if !defined(NOMINMAX) +#define NOMINMAX +#endif + +#include +#include +#include +#include // for InitCommonControls() +#include // for ExtractIcon() +#include // for placement new +#include +#include +#include +#include + +// CRT's memory leak detection +#if defined(DEBUG) || defined(_DEBUG) +#include +#endif + +// Direct3D11 includes +#include +#include +#include +#include +#include + +#ifdef USE_DIRECT3D11_3 +#include +#endif + +#ifdef USE_DIRECT3D11_4 +#include +#endif + +// DirectXMath includes +#include +#include + +// WIC includes +#include + +// XInput includes +#include + +// HRESULT translation for Direct3D and other APIs +#include "dxerr.h" + +// STL includes +#include +#include +#include + +#if defined(DEBUG) || defined(_DEBUG) +#ifndef V +#define V(x) { hr = (x); if( FAILED(hr) ) { DXUTTrace( __FILE__, (DWORD)__LINE__, hr, L## #x, true ); } } +#endif +#ifndef V_RETURN +#define V_RETURN(x) { hr = (x); if( FAILED(hr) ) { return DXUTTrace( __FILE__, (DWORD)__LINE__, hr, L## #x, true ); } } +#endif +#else +#ifndef V +#define V(x) { hr = (x); } +#endif +#ifndef V_RETURN +#define V_RETURN(x) { hr = (x); if( FAILED(hr) ) { return hr; } } +#endif +#endif + +#ifndef SAFE_DELETE +#define SAFE_DELETE(p) { if (p) { delete (p); (p) = nullptr; } } +#endif +#ifndef SAFE_DELETE_ARRAY +#define SAFE_DELETE_ARRAY(p) { if (p) { delete[] (p); (p) = nullptr; } } +#endif +#ifndef SAFE_RELEASE +#define SAFE_RELEASE(p) { if (p) { (p)->Release(); (p) = nullptr; } } +#endif + +#ifndef D3DCOLOR_ARGB +#define D3DCOLOR_ARGB(a,r,g,b) \ + ((DWORD)((((a)&0xff)<<24)|(((r)&0xff)<<16)|(((g)&0xff)<<8)|((b)&0xff))) +#endif + +#define DXUT_VERSION 1126 + +//-------------------------------------------------------------------------------------- +// Structs +//-------------------------------------------------------------------------------------- +struct DXUTD3D11DeviceSettings +{ + UINT AdapterOrdinal; + D3D_DRIVER_TYPE DriverType; + UINT Output; + DXGI_SWAP_CHAIN_DESC sd; + UINT32 CreateFlags; + UINT32 SyncInterval; + DWORD PresentFlags; + bool AutoCreateDepthStencil; // DXUT will create the depth stencil resource and view if true + DXGI_FORMAT AutoDepthStencilFormat; + D3D_FEATURE_LEVEL DeviceFeatureLevel; +}; + +struct DXUTDeviceSettings +{ + D3D_FEATURE_LEVEL MinimumFeatureLevel; + DXUTD3D11DeviceSettings d3d11; +}; + + +//-------------------------------------------------------------------------------------- +// Error codes +//-------------------------------------------------------------------------------------- +#define DXUTERR_NODIRECT3D MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0901) +#define DXUTERR_NOCOMPATIBLEDEVICES MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0902) +#define DXUTERR_MEDIANOTFOUND MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0903) +#define DXUTERR_NONZEROREFCOUNT MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0904) +#define DXUTERR_CREATINGDEVICE MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0905) +#define DXUTERR_RESETTINGDEVICE MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0906) +#define DXUTERR_CREATINGDEVICEOBJECTS MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0907) +#define DXUTERR_RESETTINGDEVICEOBJECTS MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0908) +#define DXUTERR_DEVICEREMOVED MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x090A) + + +//-------------------------------------------------------------------------------------- +// Callback registration +//-------------------------------------------------------------------------------------- + +// General callbacks +typedef void (CALLBACK *LPDXUTCALLBACKFRAMEMOVE)( _In_ double fTime, _In_ float fElapsedTime, _In_opt_ void* pUserContext ); +typedef void (CALLBACK *LPDXUTCALLBACKKEYBOARD)( _In_ UINT nChar, _In_ bool bKeyDown, _In_ bool bAltDown, _In_opt_ void* pUserContext ); +typedef void (CALLBACK *LPDXUTCALLBACKMOUSE)( _In_ bool bLeftButtonDown, _In_ bool bRightButtonDown, _In_ bool bMiddleButtonDown, + _In_ bool bSideButton1Down, _In_ bool bSideButton2Down, _In_ int nMouseWheelDelta, + _In_ int xPos, _In_ int yPos, _In_opt_ void* pUserContext ); +typedef LRESULT (CALLBACK *LPDXUTCALLBACKMSGPROC)( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam, + _Out_ bool* pbNoFurtherProcessing, _In_opt_ void* pUserContext ); +typedef void (CALLBACK *LPDXUTCALLBACKTIMER)( _In_ UINT idEvent, _In_opt_ void* pUserContext ); +typedef bool (CALLBACK *LPDXUTCALLBACKMODIFYDEVICESETTINGS)( _In_ DXUTDeviceSettings* pDeviceSettings, _In_opt_ void* pUserContext ); +typedef bool (CALLBACK *LPDXUTCALLBACKDEVICEREMOVED)( _In_opt_ void* pUserContext ); + +class CD3D11EnumAdapterInfo; +class CD3D11EnumDeviceInfo; + +// Direct3D 11 callbacks +typedef bool (CALLBACK *LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE)( _In_ const CD3D11EnumAdapterInfo *AdapterInfo, _In_ UINT Output, _In_ const CD3D11EnumDeviceInfo *DeviceInfo, + _In_ DXGI_FORMAT BackBufferFormat, _In_ bool bWindowed, _In_opt_ void* pUserContext ); +typedef HRESULT (CALLBACK *LPDXUTCALLBACKD3D11DEVICECREATED)( _In_ ID3D11Device* pd3dDevice, _In_ const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc, _In_opt_ void* pUserContext ); +typedef HRESULT (CALLBACK *LPDXUTCALLBACKD3D11SWAPCHAINRESIZED)( _In_ ID3D11Device* pd3dDevice, _In_ IDXGISwapChain *pSwapChain, _In_ const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc, _In_opt_ void* pUserContext ); +typedef void (CALLBACK *LPDXUTCALLBACKD3D11FRAMERENDER)( _In_ ID3D11Device* pd3dDevice, _In_ ID3D11DeviceContext* pd3dImmediateContext, _In_ double fTime, _In_ float fElapsedTime, _In_opt_ void* pUserContext ); +typedef void (CALLBACK *LPDXUTCALLBACKD3D11SWAPCHAINRELEASING)( _In_opt_ void* pUserContext ); +typedef void (CALLBACK *LPDXUTCALLBACKD3D11DEVICEDESTROYED)( _In_opt_ void* pUserContext ); + +// General callbacks +void WINAPI DXUTSetCallbackFrameMove( _In_ LPDXUTCALLBACKFRAMEMOVE pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackKeyboard( _In_ LPDXUTCALLBACKKEYBOARD pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackMouse( _In_ LPDXUTCALLBACKMOUSE pCallback, bool bIncludeMouseMove = false, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackMsgProc( _In_ LPDXUTCALLBACKMSGPROC pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackDeviceChanging( _In_ LPDXUTCALLBACKMODIFYDEVICESETTINGS pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackDeviceRemoved( _In_ LPDXUTCALLBACKDEVICEREMOVED pCallback, _In_opt_ void* pUserContext = nullptr ); + +// Direct3D 11 callbacks +void WINAPI DXUTSetCallbackD3D11DeviceAcceptable( _In_ LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackD3D11DeviceCreated( _In_ LPDXUTCALLBACKD3D11DEVICECREATED pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackD3D11SwapChainResized( _In_ LPDXUTCALLBACKD3D11SWAPCHAINRESIZED pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackD3D11FrameRender( _In_ LPDXUTCALLBACKD3D11FRAMERENDER pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackD3D11SwapChainReleasing( _In_ LPDXUTCALLBACKD3D11SWAPCHAINRELEASING pCallback, _In_opt_ void* pUserContext = nullptr ); +void WINAPI DXUTSetCallbackD3D11DeviceDestroyed( _In_ LPDXUTCALLBACKD3D11DEVICEDESTROYED pCallback, _In_opt_ void* pUserContext = nullptr ); + + +//-------------------------------------------------------------------------------------- +// Initialization +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTInit( _In_ bool bParseCommandLine = true, + _In_ bool bShowMsgBoxOnError = true, + _In_opt_ WCHAR* strExtraCommandLineParams = nullptr, + _In_ bool bThreadSafeDXUT = false ); + +// Choose either DXUTCreateWindow or DXUTSetWindow. If using DXUTSetWindow, consider using DXUTStaticWndProc +HRESULT WINAPI DXUTCreateWindow( _In_z_ const WCHAR* strWindowTitle = L"Direct3D Window", + _In_opt_ HINSTANCE hInstance = nullptr, _In_opt_ HICON hIcon = nullptr, _In_opt_ HMENU hMenu = nullptr, + _In_ int x = CW_USEDEFAULT, _In_ int y = CW_USEDEFAULT ); +HRESULT WINAPI DXUTSetWindow( _In_ HWND hWndFocus, _In_ HWND hWndDeviceFullScreen, _In_ HWND hWndDeviceWindowed, _In_ bool bHandleMessages = true ); +LRESULT CALLBACK DXUTStaticWndProc( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); + +// Choose either DXUTCreateDevice or DXUTCreateD3DDeviceFromSettings + +HRESULT WINAPI DXUTCreateDevice(_In_ D3D_FEATURE_LEVEL reqFL, _In_ bool bWindowed= true, _In_ int nSuggestedWidth =0,_In_ int nSuggestedHeight =0 ); +HRESULT WINAPI DXUTCreateDeviceFromSettings( _In_ DXUTDeviceSettings* pDeviceSettings, _In_ bool bClipWindowToSingleAdapter = true ); + +// Choose either DXUTMainLoop or implement your own main loop +HRESULT WINAPI DXUTMainLoop( _In_opt_ HACCEL hAccel = nullptr ); + +// If not using DXUTMainLoop consider using DXUTRender3DEnvironment +void WINAPI DXUTRender3DEnvironment(); + + +//-------------------------------------------------------------------------------------- +// Common Tasks +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTToggleFullScreen(); +HRESULT WINAPI DXUTToggleREF(); +HRESULT WINAPI DXUTToggleWARP(); +void WINAPI DXUTPause( _In_ bool bPauseTime, _In_ bool bPauseRendering ); +void WINAPI DXUTSetConstantFrameTime( _In_ bool bConstantFrameTime, _In_ float fTimePerFrame = 0.0333f ); +void WINAPI DXUTSetCursorSettings( _In_ bool bShowCursorWhenFullScreen = false, _In_ bool bClipCursorWhenFullScreen = false ); +void WINAPI DXUTSetHotkeyHandling( _In_ bool bAltEnterToToggleFullscreen = true, _In_ bool bEscapeToQuit = true, _In_ bool bPauseToToggleTimePause = true ); +void WINAPI DXUTSetMultimonSettings( _In_ bool bAutoChangeAdapter = true ); +void WINAPI DXUTSetShortcutKeySettings( _In_ bool bAllowWhenFullscreen = false, _In_ bool bAllowWhenWindowed = true ); // Controls the Windows key, and accessibility shortcut keys +void WINAPI DXUTSetWindowSettings( _In_ bool bCallDefWindowProc = true ); +HRESULT WINAPI DXUTSetTimer( _In_ LPDXUTCALLBACKTIMER pCallbackTimer, _In_ float fTimeoutInSecs = 1.0f, _Out_opt_ UINT* pnIDEvent = nullptr, _In_opt_ void* pCallbackUserContext = nullptr ); +HRESULT WINAPI DXUTKillTimer( _In_ UINT nIDEvent ); +void WINAPI DXUTResetFrameworkState(); +void WINAPI DXUTShutdown( _In_ int nExitCode = 0 ); +void WINAPI DXUTSetIsInGammaCorrectMode( _In_ bool bGammaCorrect ); +bool WINAPI DXUTGetMSAASwapChainCreated(); + + +//-------------------------------------------------------------------------------------- +// State Retrieval +//-------------------------------------------------------------------------------------- + +// Direct3D 11.x (These do not addref unlike typical Get* APIs) +IDXGIFactory1* WINAPI DXUTGetDXGIFactory(); +IDXGISwapChain* WINAPI DXUTGetDXGISwapChain(); +const DXGI_SURFACE_DESC* WINAPI DXUTGetDXGIBackBufferSurfaceDesc(); +HRESULT WINAPI DXUTSetupD3D11Views( _In_ ID3D11DeviceContext* pd3dDeviceContext ); // Supports immediate or deferred context +D3D_FEATURE_LEVEL WINAPI DXUTGetD3D11DeviceFeatureLevel(); // Returns the D3D11 devices current feature level +ID3D11RenderTargetView* WINAPI DXUTGetD3D11RenderTargetView(); +ID3D11DepthStencilView* WINAPI DXUTGetD3D11DepthStencilView(); + +ID3D11Device* WINAPI DXUTGetD3D11Device(); +ID3D11DeviceContext* WINAPI DXUTGetD3D11DeviceContext(); + +ID3D11Device1* WINAPI DXUTGetD3D11Device1(); +ID3D11DeviceContext1* WINAPI DXUTGetD3D11DeviceContext1(); + +ID3D11Device2* WINAPI DXUTGetD3D11Device2(); +ID3D11DeviceContext2* WINAPI DXUTGetD3D11DeviceContext2(); + +#ifdef USE_DIRECT3D11_3 +ID3D11Device3* WINAPI DXUTGetD3D11Device3(); +ID3D11DeviceContext3* WINAPI DXUTGetD3D11DeviceContext3(); +#endif + +#ifdef USE_DIRECT3D11_4 +ID3D11Device4* WINAPI DXUTGetD3D11Device4(); +ID3D11DeviceContext4* WINAPI DXUTGetD3D11DeviceContext4(); +#endif + +// General +DXUTDeviceSettings WINAPI DXUTGetDeviceSettings(); +HINSTANCE WINAPI DXUTGetHINSTANCE(); +HWND WINAPI DXUTGetHWND(); +HWND WINAPI DXUTGetHWNDFocus(); +HWND WINAPI DXUTGetHWNDDeviceFullScreen(); +HWND WINAPI DXUTGetHWNDDeviceWindowed(); +RECT WINAPI DXUTGetWindowClientRect(); +LONG WINAPI DXUTGetWindowWidth(); +LONG WINAPI DXUTGetWindowHeight(); +RECT WINAPI DXUTGetWindowClientRectAtModeChange(); // Useful for returning to windowed mode with the same resolution as before toggle to full screen mode +RECT WINAPI DXUTGetFullsceenClientRectAtModeChange(); // Useful for returning to full screen mode with the same resolution as before toggle to windowed mode +double WINAPI DXUTGetTime(); +float WINAPI DXUTGetElapsedTime(); +bool WINAPI DXUTIsWindowed(); +bool WINAPI DXUTIsInGammaCorrectMode(); +float WINAPI DXUTGetFPS(); +LPCWSTR WINAPI DXUTGetWindowTitle(); +LPCWSTR WINAPI DXUTGetFrameStats( _In_ bool bIncludeFPS = false ); +LPCWSTR WINAPI DXUTGetDeviceStats(); + +bool WINAPI DXUTIsVsyncEnabled(); +bool WINAPI DXUTIsRenderingPaused(); +bool WINAPI DXUTIsTimePaused(); +bool WINAPI DXUTIsActive(); +int WINAPI DXUTGetExitCode(); +bool WINAPI DXUTGetShowMsgBoxOnError(); +bool WINAPI DXUTGetAutomation(); // Returns true if -automation parameter is used to launch the app +bool WINAPI DXUTIsKeyDown( _In_ BYTE vKey ); // Pass a virtual-key code, ex. VK_F1, 'A', VK_RETURN, VK_LSHIFT, etc +bool WINAPI DXUTWasKeyPressed( _In_ BYTE vKey ); // Like DXUTIsKeyDown() but return true only if the key was just pressed +bool WINAPI DXUTIsMouseButtonDown( _In_ BYTE vButton ); // Pass a virtual-key code: VK_LBUTTON, VK_RBUTTON, VK_MBUTTON, VK_XBUTTON1, VK_XBUTTON2 +HRESULT WINAPI DXUTCreateState(); // Optional method to create DXUT's memory. If its not called by the application it will be automatically called when needed +void WINAPI DXUTDestroyState(); // Optional method to destroy DXUT's memory. If its not called by the application it will be automatically called after the application exits WinMain + +//-------------------------------------------------------------------------------------- +// DXUT core layer includes +//-------------------------------------------------------------------------------------- +#include "DXUTmisc.h" +#include "DXUTDevice11.h" diff --git a/src/DX11/framework/dxut/Core/DXUTDevice11.cpp b/src/DX11/framework/dxut/Core/DXUTDevice11.cpp new file mode 100644 index 0000000..5e7a766 --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUTDevice11.cpp @@ -0,0 +1,1272 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTDevice11.cpp +// +// Enumerates D3D adapters, devices, modes, etc. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "DXUT.h" + +//-------------------------------------------------------------------------------------- +// Forward declarations +//-------------------------------------------------------------------------------------- +extern void DXUTGetCallbackD3D11DeviceAcceptable( LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE* ppCallbackIsDeviceAcceptable, void** ppUserContext ); + +static int __cdecl SortModesCallback( const void* arg1, const void* arg2 ); + +CD3D11Enumeration* g_pDXUTD3D11Enumeration = nullptr; + +HRESULT WINAPI DXUTCreateD3D11Enumeration() +{ + if( !g_pDXUTD3D11Enumeration ) + { + g_pDXUTD3D11Enumeration = new (std::nothrow) CD3D11Enumeration(); + if( !g_pDXUTD3D11Enumeration ) + return E_OUTOFMEMORY; + } + return S_OK; +} + +void WINAPI DXUTDestroyD3D11Enumeration() +{ + SAFE_DELETE( g_pDXUTD3D11Enumeration ); +} + +class DXUTMemoryHelperD3D11Enum +{ +public: +DXUTMemoryHelperD3D11Enum() noexcept { DXUTCreateD3D11Enumeration(); } +~DXUTMemoryHelperD3D11Enum() { DXUTDestroyD3D11Enumeration(); } +}; + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +CD3D11Enumeration* WINAPI DXUTGetD3D11Enumeration( bool bForceEnumerate, bool bEnumerateAllAdapterFormats, D3D_FEATURE_LEVEL forceFL ) +{ + // Using an static class with accessor function to allow control of the construction order + static DXUTMemoryHelperD3D11Enum d3d11enumMemory; + if( g_pDXUTD3D11Enumeration && ( !g_pDXUTD3D11Enumeration->HasEnumerated() || bForceEnumerate ) ) + { + g_pDXUTD3D11Enumeration->SetEnumerateAllAdapterFormats( bEnumerateAllAdapterFormats ); + LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE pCallbackIsDeviceAcceptable; + void* pUserContext; + DXUTGetCallbackD3D11DeviceAcceptable( &pCallbackIsDeviceAcceptable, &pUserContext ); + g_pDXUTD3D11Enumeration->SetForceFeatureLevel(forceFL); + + g_pDXUTD3D11Enumeration->Enumerate( pCallbackIsDeviceAcceptable, pUserContext ); + } + + return g_pDXUTD3D11Enumeration; +} + + +//-------------------------------------------------------------------------------------- +CD3D11Enumeration::CD3D11Enumeration() noexcept : + m_bHasEnumerated(false), + m_IsD3D11DeviceAcceptableFunc(nullptr), + m_pIsD3D11DeviceAcceptableFuncUserContext(nullptr), + m_bEnumerateAllAdapterFormats(false), + m_forceFL(D3D_FEATURE_LEVEL(0)), + m_warpFL(D3D_FEATURE_LEVEL_10_1), + m_refFL(D3D_FEATURE_LEVEL_11_0) +{ + ResetPossibleDepthStencilFormats(); +} + + +//-------------------------------------------------------------------------------------- +CD3D11Enumeration::~CD3D11Enumeration() +{ + ClearAdapterInfoList(); +} + + +//-------------------------------------------------------------------------------------- +// Enumerate for each adapter all of the supported display modes, +// device types, adapter formats, back buffer formats, window/full screen support, +// depth stencil formats, multisampling types/qualities, and presentations intervals. +// +// For each combination of device type (HAL/REF), adapter format, back buffer format, and +// IsWindowed it will call the app's ConfirmDevice callback. This allows the app +// to reject or allow that combination based on its caps/etc. It also allows the +// app to change the BehaviorFlags. The BehaviorFlags defaults non-pure HWVP +// if supported otherwise it will default to SWVP, however the app can change this +// through the ConfirmDevice callback. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CD3D11Enumeration::Enumerate( LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE IsD3D11DeviceAcceptableFunc, + void* pIsD3D11DeviceAcceptableFuncUserContext ) +{ + CDXUTPerfEventGenerator eventGenerator( DXUT_PERFEVENTCOLOR, L"DXUT D3D11 Enumeration" ); + HRESULT hr; + auto pFactory = DXUTGetDXGIFactory(); + if( !pFactory ) + return E_FAIL; + + m_bHasEnumerated = true; + m_IsD3D11DeviceAcceptableFunc = IsD3D11DeviceAcceptableFunc; + m_pIsD3D11DeviceAcceptableFuncUserContext = pIsD3D11DeviceAcceptableFuncUserContext; + + ClearAdapterInfoList(); + + for( int index = 0; ; ++index ) + { + IDXGIAdapter* pAdapter = nullptr; + hr = pFactory->EnumAdapters( index, &pAdapter ); + if( FAILED( hr ) ) // DXGIERR_NOT_FOUND is expected when the end of the list is hit + break; + + IDXGIAdapter2* pAdapter2 = nullptr; + if ( SUCCEEDED( pAdapter->QueryInterface( __uuidof(IDXGIAdapter2), ( LPVOID* )&pAdapter2 ) ) ) + { + // Succeeds on DirectX 11.1 Runtime systems + DXGI_ADAPTER_DESC2 desc; + hr = pAdapter2->GetDesc2( &desc ); + pAdapter2->Release(); + + if ( SUCCEEDED(hr) && ( desc.Flags & DXGI_ADAPTER_FLAG_SOFTWARE ) ) + { + // Skip "always there" Microsoft Basics Display Driver + pAdapter->Release(); + continue; + } + } + + auto pAdapterInfo = new (std::nothrow) CD3D11EnumAdapterInfo; + if( !pAdapterInfo ) + { + SAFE_RELEASE( pAdapter ); + return E_OUTOFMEMORY; + } + pAdapterInfo->AdapterOrdinal = index; + pAdapter->GetDesc( &pAdapterInfo->AdapterDesc ); + pAdapterInfo->m_pAdapter = pAdapter; + + // Enumerate the device driver types on the adapter. + hr = EnumerateDevices( pAdapterInfo ); + if( FAILED( hr ) ) + { + delete pAdapterInfo; + continue; + } + + hr = EnumerateOutputs( pAdapterInfo ); + if( FAILED( hr ) || pAdapterInfo->outputInfoList.empty() ) + { + delete pAdapterInfo; + continue; + } + + // Get info for each devicecombo on this device + if( FAILED( hr = EnumerateDeviceCombos( pAdapterInfo ) ) ) + { + delete pAdapterInfo; + continue; + } + + m_AdapterInfoList.push_back( pAdapterInfo ); + } + + // If we did not get an adapter then we should still enumerate WARP and Ref. + if (m_AdapterInfoList.size() == 0) + { + auto pAdapterInfo = new (std::nothrow) CD3D11EnumAdapterInfo; + if( !pAdapterInfo ) + { + return E_OUTOFMEMORY; + } + pAdapterInfo->bAdapterUnavailable = true; + + hr = EnumerateDevices( pAdapterInfo ); + + // Get info for each devicecombo on this device + if( FAILED( hr = EnumerateDeviceCombosNoAdapter( pAdapterInfo ) ) ) + { + delete pAdapterInfo; + } + + if (SUCCEEDED(hr)) m_AdapterInfoList.push_back( pAdapterInfo ); + } + + // + // Check for 2 or more adapters with the same name. Append the name + // with some instance number if that's the case to help distinguish + // them. + // + bool bUniqueDesc = true; + for( size_t i = 0; i < m_AdapterInfoList.size(); i++ ) + { + auto pAdapterInfo1 = m_AdapterInfoList[ i ]; + + for( size_t j = i + 1; j < m_AdapterInfoList.size(); j++ ) + { + auto pAdapterInfo2 = m_AdapterInfoList[ j ]; + if( wcsncmp( pAdapterInfo1->AdapterDesc.Description, + pAdapterInfo2->AdapterDesc.Description, DXGI_MAX_DEVICE_IDENTIFIER_STRING ) == 0 ) + { + bUniqueDesc = false; + break; + } + } + + if( !bUniqueDesc ) + break; + } + + for( auto it = m_AdapterInfoList.begin(); it != m_AdapterInfoList.end(); ++it ) + { + wcscpy_s((*it)->szUniqueDescription, DXGI_MAX_DEVICE_IDENTIFIER_STRING, (*it)->AdapterDesc.Description); + if( !bUniqueDesc ) + { + WCHAR sz[32]; + swprintf_s( sz, 32, L" (#%u)", (*it)->AdapterOrdinal ); + wcscat_s( (*it)->szUniqueDescription, DXGI_MAX_DEVICE_IDENTIFIER_STRING, sz ); + } + } + + // Check WARP max feature level + { + static const D3D_FEATURE_LEVEL fLvlWarp[] = + { +#if defined(USE_DIRECT3D11_3) || defined(USE_DIRECT3D11_4) + D3D_FEATURE_LEVEL_12_1, D3D_FEATURE_LEVEL_12_0, +#endif + D3D_FEATURE_LEVEL_11_1, D3D_FEATURE_LEVEL_11_0, D3D_FEATURE_LEVEL_10_1 + }; + + ID3D11Device* pDevice = nullptr; + hr = DXUT_Dynamic_D3D11CreateDevice( nullptr, D3D_DRIVER_TYPE_WARP, 0, 0, fLvlWarp, _countof(fLvlWarp), + D3D11_SDK_VERSION, &pDevice, &m_warpFL, nullptr ); + if ( hr == E_INVALIDARG ) + { +#if defined(USE_DIRECT3D11_3) || defined(USE_DIRECT3D11_4) + // DirectX 11.1 runtime will not recognize FL 12.x, so try without it + hr = DXUT_Dynamic_D3D11CreateDevice(nullptr, D3D_DRIVER_TYPE_WARP, 0, 0, &fLvlWarp[2], _countof(fLvlWarp) - 2, + D3D11_SDK_VERSION, &pDevice, &m_warpFL, nullptr); + if (hr == E_INVALIDARG) + { + // DirectX 11.0 runtime will not recognize FL 11.1+, so try without it + hr = DXUT_Dynamic_D3D11CreateDevice(nullptr, D3D_DRIVER_TYPE_WARP, 0, 0, &fLvlWarp[3], _countof(fLvlWarp) - 3, + D3D11_SDK_VERSION, &pDevice, &m_warpFL, nullptr); + } +#else + // DirectX 11.0 runtime will not recognize FL 11.1, so try without it + hr = DXUT_Dynamic_D3D11CreateDevice( nullptr, D3D_DRIVER_TYPE_WARP, 0, 0, &fLvlWarp[1], _countof(fLvlWarp) - 1, + D3D11_SDK_VERSION, &pDevice, &m_warpFL, nullptr ); +#endif + } + + if ( SUCCEEDED(hr) ) + { + pDevice->Release(); + } + else + m_warpFL = D3D_FEATURE_LEVEL_10_1; + } + + // Check REF max feature level + { + static const D3D_FEATURE_LEVEL fLvlRef[] = { D3D_FEATURE_LEVEL_11_1, D3D_FEATURE_LEVEL_11_0, D3D_FEATURE_LEVEL_10_1 }; + + ID3D11Device* pDevice = nullptr; + hr = DXUT_Dynamic_D3D11CreateDevice( nullptr, D3D_DRIVER_TYPE_REFERENCE, 0, 0, fLvlRef, _countof(fLvlRef), + D3D11_SDK_VERSION, &pDevice, &m_refFL, nullptr ); + if ( hr == E_INVALIDARG ) + { + // DirectX 11.0 runtime will not recognize FL 11.1, so try without it + hr = DXUT_Dynamic_D3D11CreateDevice( nullptr, D3D_DRIVER_TYPE_REFERENCE, 0, 0, &fLvlRef[1], _countof(fLvlRef) - 1, + D3D11_SDK_VERSION, &pDevice, &m_refFL, nullptr ); + } + + if ( SUCCEEDED(hr) ) + { + pDevice->Release(); + } + else + m_refFL = D3D_FEATURE_LEVEL_11_0; + } + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CD3D11Enumeration::EnumerateOutputs( _In_ CD3D11EnumAdapterInfo* pAdapterInfo ) +{ + HRESULT hr; + IDXGIOutput* pOutput; + + for( int iOutput = 0; ; ++iOutput ) + { + pOutput = nullptr; + hr = pAdapterInfo->m_pAdapter->EnumOutputs( iOutput, &pOutput ); + if( DXGI_ERROR_NOT_FOUND == hr ) + { + return S_OK; + } + else if( FAILED( hr ) ) + { + return hr; //Something bad happened. + } + else //Success! + { + auto pOutputInfo = new (std::nothrow) CD3D11EnumOutputInfo; + if( !pOutputInfo ) + { + SAFE_RELEASE( pOutput ); + return E_OUTOFMEMORY; + } + pOutputInfo->Output = iOutput; + pOutputInfo->m_pOutput = pOutput; + pOutput->GetDesc( &pOutputInfo->Desc ); + + EnumerateDisplayModes( pOutputInfo ); + if( pOutputInfo->displayModeList.empty() ) + { + // If this output has no valid display mode, do not save it. + delete pOutputInfo; + continue; + } + + pAdapterInfo->outputInfoList.push_back( pOutputInfo ); + } + } +} + + +//-------------------------------------------------------------------------------------- +HRESULT CD3D11Enumeration::EnumerateDisplayModes( _In_ CD3D11EnumOutputInfo* pOutputInfo ) +{ + HRESULT hr = S_OK; + DXGI_FORMAT allowedAdapterFormatArray[] = + { + DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, //This is DXUT's preferred mode + + DXGI_FORMAT_R8G8B8A8_UNORM, + DXGI_FORMAT_R16G16B16A16_FLOAT, + DXGI_FORMAT_R10G10B10A2_UNORM + }; + int allowedAdapterFormatArrayCount = sizeof( allowedAdapterFormatArray ) / sizeof( allowedAdapterFormatArray[0] ); + + // Swap perferred modes for apps running in linear space + DXGI_FORMAT RemoteMode = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + if( !DXUTIsInGammaCorrectMode() ) + { + allowedAdapterFormatArray[0] = DXGI_FORMAT_R8G8B8A8_UNORM; + allowedAdapterFormatArray[1] = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + RemoteMode = DXGI_FORMAT_R8G8B8A8_UNORM; + } + + // The fast path only enumerates R8G8B8A8_UNORM_SRGB modes + if( !m_bEnumerateAllAdapterFormats ) + allowedAdapterFormatArrayCount = 1; + + for( int f = 0; f < allowedAdapterFormatArrayCount; ++f ) + { + // Fast-path: Try to grab at least 512 modes. + // This is to avoid calling GetDisplayModeList more times than necessary. + // GetDisplayModeList is an expensive call. + UINT NumModes = 512; + auto pDesc = new (std::nothrow) DXGI_MODE_DESC[ NumModes ]; + assert( pDesc ); + if( !pDesc ) + return E_OUTOFMEMORY; + + hr = pOutputInfo->m_pOutput->GetDisplayModeList( allowedAdapterFormatArray[f], + DXGI_ENUM_MODES_SCALING, + &NumModes, + pDesc ); + if( DXGI_ERROR_NOT_FOUND == hr ) + { + SAFE_DELETE_ARRAY( pDesc ); + NumModes = 0; + break; + } + else if( MAKE_DXGI_HRESULT( 34 ) == hr && RemoteMode == allowedAdapterFormatArray[f] ) + { + // DXGI cannot enumerate display modes over a remote session. Therefore, create a fake display + // mode for the current screen resolution for the remote session. + if( 0 != GetSystemMetrics( 0x1000 ) ) // SM_REMOTESESSION + { + DEVMODE DevMode; + DevMode.dmSize = sizeof( DEVMODE ); + if( EnumDisplaySettings( nullptr, ENUM_CURRENT_SETTINGS, &DevMode ) ) + { + NumModes = 1; + pDesc[0].Width = DevMode.dmPelsWidth; + pDesc[0].Height = DevMode.dmPelsHeight; + pDesc[0].Format = DXGI_FORMAT_R8G8B8A8_UNORM; + pDesc[0].RefreshRate.Numerator = 0; + pDesc[0].RefreshRate.Denominator = 0; + pDesc[0].ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_PROGRESSIVE; + pDesc[0].Scaling = DXGI_MODE_SCALING_CENTERED; + hr = S_OK; + } + } + } + else if( DXGI_ERROR_MORE_DATA == hr ) + { + // Slow path. There were more than 512 modes. + SAFE_DELETE_ARRAY( pDesc ); + hr = pOutputInfo->m_pOutput->GetDisplayModeList( allowedAdapterFormatArray[f], + DXGI_ENUM_MODES_SCALING, + &NumModes, + nullptr ); + if( FAILED( hr ) ) + { + NumModes = 0; + break; + } + + pDesc = new (std::nothrow) DXGI_MODE_DESC[ NumModes ]; + assert( pDesc ); + if( !pDesc ) + return E_OUTOFMEMORY; + + hr = pOutputInfo->m_pOutput->GetDisplayModeList( allowedAdapterFormatArray[f], + DXGI_ENUM_MODES_SCALING, + &NumModes, + pDesc ); + if( FAILED( hr ) ) + { + SAFE_DELETE_ARRAY( pDesc ); + NumModes = 0; + break; + } + + } + + if( 0 == NumModes && 0 == f ) + { + // No R8G8B8A8_UNORM_SRGB modes! + // Abort the fast-path if we're on it + allowedAdapterFormatArrayCount = sizeof( allowedAdapterFormatArray ) / sizeof + ( allowedAdapterFormatArray[0] ); + SAFE_DELETE_ARRAY( pDesc ); + continue; + } + + if( SUCCEEDED( hr ) ) + { + for( UINT m = 0; m < NumModes; m++ ) + { +#pragma warning ( suppress : 6385 ) + pOutputInfo->displayModeList.push_back( pDesc[m] ); + } + } + + SAFE_DELETE_ARRAY( pDesc ); + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CD3D11Enumeration::EnumerateDevices( _In_ CD3D11EnumAdapterInfo* pAdapterInfo ) +{ + HRESULT hr; + auto deviceSettings = DXUTGetDeviceSettings(); + const D3D_DRIVER_TYPE devTypeArray[] = + { + D3D_DRIVER_TYPE_HARDWARE, + D3D_DRIVER_TYPE_WARP, + D3D_DRIVER_TYPE_REFERENCE + }; + const UINT devTypeArrayCount = sizeof( devTypeArray ) / sizeof( devTypeArray[0] ); + + // Enumerate each Direct3D device type + for( UINT iDeviceType = 0; iDeviceType < devTypeArrayCount; iDeviceType++ ) + { + auto pDeviceInfo = new (std::nothrow) CD3D11EnumDeviceInfo; + if( !pDeviceInfo ) + return E_OUTOFMEMORY; + + // Fill struct w/ AdapterOrdinal and D3D_DRIVER_TYPE + pDeviceInfo->AdapterOrdinal = pAdapterInfo->AdapterOrdinal; + pDeviceInfo->DeviceType = devTypeArray[iDeviceType]; + + static const D3D_FEATURE_LEVEL FeatureLevels[] = + { +#if defined(USE_DIRECT3D11_3) || defined(USE_DIRECT3D11_4) + D3D_FEATURE_LEVEL_12_1, + D3D_FEATURE_LEVEL_12_0, +#endif + 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 + }; + UINT NumFeatureLevels = ARRAYSIZE( FeatureLevels ); + + // Call D3D11CreateDevice to ensure that this is a D3D11 device. + ID3D11Device* pd3dDevice = nullptr; + ID3D11DeviceContext* pd3dDeviceContext = nullptr; + hr = DXUT_Dynamic_D3D11CreateDevice( (devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? pAdapterInfo->m_pAdapter : nullptr, + (devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? D3D_DRIVER_TYPE_UNKNOWN : devTypeArray[iDeviceType], + ( HMODULE )0, + 0, + FeatureLevels, + NumFeatureLevels, + D3D11_SDK_VERSION, + &pd3dDevice, + &pDeviceInfo->MaxLevel, + &pd3dDeviceContext ); + + if ( hr == E_INVALIDARG ) + { +#if defined(USE_DIRECT3D11_3) || defined(USE_DIRECT3D11_4) + // DirectX 11.1 runtime will not recognize FL 12.x, so try without it + hr = DXUT_Dynamic_D3D11CreateDevice((devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? pAdapterInfo->m_pAdapter : nullptr, + (devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? D3D_DRIVER_TYPE_UNKNOWN : devTypeArray[iDeviceType], + (HMODULE)0, 0, + &FeatureLevels[2], NumFeatureLevels - 2, + D3D11_SDK_VERSION, &pd3dDevice, &pDeviceInfo->MaxLevel, + &pd3dDeviceContext); + + if (hr == E_INVALIDARG) + { + // DirectX 11.0 runtime will not recognize FL 11.1, so try without it + hr = DXUT_Dynamic_D3D11CreateDevice((devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? pAdapterInfo->m_pAdapter : nullptr, + (devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? D3D_DRIVER_TYPE_UNKNOWN : devTypeArray[iDeviceType], + (HMODULE)0, 0, + &FeatureLevels[3], NumFeatureLevels - 3, + D3D11_SDK_VERSION, &pd3dDevice, &pDeviceInfo->MaxLevel, + &pd3dDeviceContext); + } +#else + // DirectX 11.0 runtime will not recognize FL 11.1, so try without it + hr = DXUT_Dynamic_D3D11CreateDevice( (devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? pAdapterInfo->m_pAdapter : nullptr, + (devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? D3D_DRIVER_TYPE_UNKNOWN : devTypeArray[iDeviceType], + ( HMODULE )0, 0, + &FeatureLevels[1], NumFeatureLevels - 1, + D3D11_SDK_VERSION, &pd3dDevice, &pDeviceInfo->MaxLevel, + &pd3dDeviceContext ); +#endif + } + + if ( FAILED(hr) ) + { + delete pDeviceInfo; + continue; + } + else if ( pDeviceInfo->MaxLevel < deviceSettings.MinimumFeatureLevel ) + { + delete pDeviceInfo; + SAFE_RELEASE( pd3dDevice ); + SAFE_RELEASE( pd3dDeviceContext ); + continue; + } + + if (m_forceFL == 0 || m_forceFL == pDeviceInfo->MaxLevel) + { + pDeviceInfo->SelectedLevel = pDeviceInfo->MaxLevel; + } + else if (m_forceFL > pDeviceInfo->MaxLevel) + { + delete pDeviceInfo; + SAFE_RELEASE( pd3dDevice ); + SAFE_RELEASE( pd3dDeviceContext ); + continue; + } + else + { + // A device was created with a higher feature level that the user-specified feature level. + SAFE_RELEASE( pd3dDevice ); + SAFE_RELEASE( pd3dDeviceContext ); + D3D_FEATURE_LEVEL rtFL; + hr = DXUT_Dynamic_D3D11CreateDevice( (devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? pAdapterInfo->m_pAdapter : nullptr, + (devTypeArray[iDeviceType] == D3D_DRIVER_TYPE_HARDWARE) ? D3D_DRIVER_TYPE_UNKNOWN : devTypeArray[iDeviceType], + ( HMODULE )0, + 0, + &m_forceFL, + 1, + D3D11_SDK_VERSION, + &pd3dDevice, + &rtFL, + &pd3dDeviceContext ); + + if( SUCCEEDED( hr ) && rtFL == m_forceFL ) + { + pDeviceInfo->SelectedLevel = m_forceFL; + } + else + { + delete pDeviceInfo; + if ( SUCCEEDED(hr) ) + { + SAFE_RELEASE( pd3dDevice ); + SAFE_RELEASE( pd3dDeviceContext ); + } + continue; + } + } + + D3D11_FEATURE_DATA_D3D10_X_HARDWARE_OPTIONS ho; + hr = pd3dDevice->CheckFeatureSupport(D3D11_FEATURE_D3D10_X_HARDWARE_OPTIONS, &ho, sizeof(ho)); + if ( FAILED(hr) ) + memset( &ho, 0, sizeof(ho) ); + + pDeviceInfo->ComputeShaders_Plus_RawAndStructuredBuffers_Via_Shader_4_x = ho.ComputeShaders_Plus_RawAndStructuredBuffers_Via_Shader_4_x; + SAFE_RELEASE( pd3dDeviceContext ); + SAFE_RELEASE( pd3dDevice ); + pAdapterInfo->deviceInfoList.push_back( pDeviceInfo ); + } + + return S_OK; +} + + +HRESULT CD3D11Enumeration::EnumerateDeviceCombosNoAdapter( _In_ CD3D11EnumAdapterInfo* pAdapterInfo ) +{ + // Iterate through each combination of device driver type, output, + // adapter format, and backbuffer format to build the adapter's device combo list. + // + + for( auto dit = pAdapterInfo->deviceInfoList.cbegin(); dit != pAdapterInfo->deviceInfoList.cend(); ++dit ) + { + DXGI_FORMAT BufferFormatArray[] = + { + DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, //This is DXUT's preferred mode + + DXGI_FORMAT_R8G8B8A8_UNORM, + DXGI_FORMAT_R16G16B16A16_FLOAT, + DXGI_FORMAT_R10G10B10A2_UNORM + }; + + // Swap perferred modes for apps running in linear space + if( !DXUTIsInGammaCorrectMode() ) + { + BufferFormatArray[0] = DXGI_FORMAT_R8G8B8A8_UNORM; + BufferFormatArray[1] = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + } + + for( UINT iBufferFormat = 0; iBufferFormat < _countof( BufferFormatArray ); iBufferFormat++ ) + { + DXGI_FORMAT BufferFormat = BufferFormatArray[iBufferFormat]; + + // determine if there are any modes for this particular format + + // If an application callback function has been provided, make sure this device + // is acceptable to the app. + if( m_IsD3D11DeviceAcceptableFunc ) + { + if( !m_IsD3D11DeviceAcceptableFunc( pAdapterInfo, + 0, + *dit, + BufferFormat, + TRUE, + m_pIsD3D11DeviceAcceptableFuncUserContext ) ) + continue; + } + + // At this point, we have an adapter/device/backbufferformat/iswindowed + // DeviceCombo that is supported by the system. We still + // need to find one or more suitable depth/stencil buffer format, + // multisample type, and present interval. + CD3D11EnumDeviceSettingsCombo* pDeviceCombo = new (std::nothrow) CD3D11EnumDeviceSettingsCombo; + if( !pDeviceCombo ) + return E_OUTOFMEMORY; + + pDeviceCombo->AdapterOrdinal = (*dit)->AdapterOrdinal; + pDeviceCombo->DeviceType = (*dit)->DeviceType; + pDeviceCombo->BackBufferFormat = BufferFormat; + pDeviceCombo->Windowed = TRUE; + pDeviceCombo->Output = 0; + pDeviceCombo->pAdapterInfo = pAdapterInfo; + pDeviceCombo->pDeviceInfo = (*dit); + pDeviceCombo->pOutputInfo = nullptr; + + BuildMultiSampleQualityList( BufferFormat, pDeviceCombo ); + + pAdapterInfo->deviceSettingsComboList.push_back( pDeviceCombo ); + } + } + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CD3D11Enumeration::EnumerateDeviceCombos( CD3D11EnumAdapterInfo* pAdapterInfo ) +{ + // Iterate through each combination of device driver type, output, + // adapter format, and backbuffer format to build the adapter's device combo list. + // + for( size_t output = 0; output < pAdapterInfo->outputInfoList.size(); ++output ) + { + auto pOutputInfo = pAdapterInfo->outputInfoList[ output ]; + + for( size_t device = 0; device < pAdapterInfo->deviceInfoList.size(); ++device ) + { + auto pDeviceInfo = pAdapterInfo->deviceInfoList[ device ]; + + DXGI_FORMAT backBufferFormatArray[] = + { + DXGI_FORMAT_R8G8B8A8_UNORM_SRGB, //This is DXUT's preferred mode + + DXGI_FORMAT_R8G8B8A8_UNORM, + DXGI_FORMAT_R16G16B16A16_FLOAT, + DXGI_FORMAT_R10G10B10A2_UNORM + }; + + // Swap perferred modes for apps running in linear space + if( !DXUTIsInGammaCorrectMode() ) + { + backBufferFormatArray[0] = DXGI_FORMAT_R8G8B8A8_UNORM; + backBufferFormatArray[1] = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + } + + for( UINT iBackBufferFormat = 0; iBackBufferFormat < _countof( backBufferFormatArray ); iBackBufferFormat++ ) + { + DXGI_FORMAT backBufferFormat = backBufferFormatArray[iBackBufferFormat]; + + for( int nWindowed = 0; nWindowed < 2; nWindowed++ ) + { + if( !nWindowed && pOutputInfo->displayModeList.size() == 0 ) + continue; + + // determine if there are any modes for this particular format + size_t iModes = 0; + for( size_t i = 0; i < pOutputInfo->displayModeList.size(); i++ ) + { + if( backBufferFormat == pOutputInfo->displayModeList[ i ].Format ) + ++iModes; + } + if( !iModes ) + continue; + + // If an application callback function has been provided, make sure this device + // is acceptable to the app. + if( m_IsD3D11DeviceAcceptableFunc ) + { + if( !m_IsD3D11DeviceAcceptableFunc( pAdapterInfo, static_cast( output ), + pDeviceInfo, backBufferFormat, + FALSE != nWindowed, + m_pIsD3D11DeviceAcceptableFuncUserContext ) ) + continue; + } + + // At this point, we have an adapter/device/backbufferformat/iswindowed + // DeviceCombo that is supported by the system. We still + // need to find one or more suitable depth/stencil buffer format, + // multisample type, and present interval. + auto pDeviceCombo = new (std::nothrow) CD3D11EnumDeviceSettingsCombo; + if( !pDeviceCombo ) + return E_OUTOFMEMORY; + + pDeviceCombo->AdapterOrdinal = pDeviceInfo->AdapterOrdinal; + pDeviceCombo->DeviceType = pDeviceInfo->DeviceType; + pDeviceCombo->BackBufferFormat = backBufferFormat; + pDeviceCombo->Windowed = ( nWindowed != 0 ); + pDeviceCombo->Output = pOutputInfo->Output; + pDeviceCombo->pAdapterInfo = pAdapterInfo; + pDeviceCombo->pDeviceInfo = pDeviceInfo; + pDeviceCombo->pOutputInfo = pOutputInfo; + + BuildMultiSampleQualityList( backBufferFormat, pDeviceCombo ); + + pAdapterInfo->deviceSettingsComboList.push_back( pDeviceCombo ); + } + } + } + } + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Release all the allocated CD3D11EnumAdapterInfo objects and empty the list +//-------------------------------------------------------------------------------------- +void CD3D11Enumeration::ClearAdapterInfoList() +{ + for( auto it = m_AdapterInfoList.begin(); it != m_AdapterInfoList.end(); ++it ) + { + auto pAdapterInfo = *it; + delete pAdapterInfo; + } + m_AdapterInfoList.clear(); +} + + +//-------------------------------------------------------------------------------------- +void CD3D11Enumeration::ResetPossibleDepthStencilFormats() +{ + m_DepthStencilPossibleList.clear(); + m_DepthStencilPossibleList.push_back( DXGI_FORMAT_D32_FLOAT_S8X24_UINT ); + m_DepthStencilPossibleList.push_back( DXGI_FORMAT_D32_FLOAT ); + m_DepthStencilPossibleList.push_back( DXGI_FORMAT_D24_UNORM_S8_UINT ); + m_DepthStencilPossibleList.push_back( DXGI_FORMAT_D16_UNORM ); +} + + +//-------------------------------------------------------------------------------------- +void CD3D11Enumeration::SetEnumerateAllAdapterFormats( _In_ bool bEnumerateAllAdapterFormats ) +{ + m_bEnumerateAllAdapterFormats = bEnumerateAllAdapterFormats; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CD3D11Enumeration::BuildMultiSampleQualityList( DXGI_FORMAT fmt, CD3D11EnumDeviceSettingsCombo* pDeviceCombo ) +{ + ID3D11Device* pd3dDevice = nullptr; + ID3D11DeviceContext* pd3dDeviceContext = nullptr; + IDXGIAdapter* pAdapter = nullptr; + + D3D_FEATURE_LEVEL *FeatureLevels = &(pDeviceCombo->pDeviceInfo->SelectedLevel); + D3D_FEATURE_LEVEL returnedFeatureLevel; + + UINT NumFeatureLevels = 1; + + HRESULT hr = DXUT_Dynamic_D3D11CreateDevice( pAdapter, + pDeviceCombo->DeviceType, + ( HMODULE )0, + 0, + FeatureLevels, + NumFeatureLevels, + D3D11_SDK_VERSION, + &pd3dDevice, + &returnedFeatureLevel, + &pd3dDeviceContext ) ; + + if( FAILED( hr)) return; + + if (returnedFeatureLevel != pDeviceCombo->pDeviceInfo->SelectedLevel) return; + + for( int i = 1; i <= D3D11_MAX_MULTISAMPLE_SAMPLE_COUNT; ++i ) + { + UINT Quality; + if( SUCCEEDED( pd3dDevice->CheckMultisampleQualityLevels( fmt, i, &Quality ) ) && Quality > 0 ) + { + //From D3D10 docs: When multisampling a texture, the number of quality levels available for an adapter is dependent on the texture + //format used and the number of samples requested. The maximum sample count is defined by + //D3D10_MAX_MULTISAMPLE_SAMPLE_COUNT in d3d10.h. If the returned value of pNumQualityLevels is 0, + //the format and sample count combination is not supported for the installed adapter. + + if (Quality != 0) { + pDeviceCombo->multiSampleCountList.push_back( i ); + pDeviceCombo->multiSampleQualityList.push_back( Quality ); + } + } + } + + SAFE_RELEASE( pAdapter ); + SAFE_RELEASE( pd3dDevice ); + SAFE_RELEASE (pd3dDeviceContext); +} + + +//-------------------------------------------------------------------------------------- +// Call GetAdapterInfoList() after Enumerate() to get a STL vector of +// CD3D11EnumAdapterInfo* +//-------------------------------------------------------------------------------------- +std::vector * CD3D11Enumeration::GetAdapterInfoList() +{ + return &m_AdapterInfoList; +} + + +//-------------------------------------------------------------------------------------- +CD3D11EnumAdapterInfo* CD3D11Enumeration::GetAdapterInfo( _In_ UINT AdapterOrdinal ) const +{ + for( auto it = m_AdapterInfoList.cbegin(); it != m_AdapterInfoList.cend(); ++it ) + { + if( (*it)->AdapterOrdinal == AdapterOrdinal ) + return *it; + } + + return nullptr; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +CD3D11EnumDeviceInfo* CD3D11Enumeration::GetDeviceInfo( UINT AdapterOrdinal, D3D_DRIVER_TYPE DeviceType ) const +{ + auto pAdapterInfo = GetAdapterInfo( AdapterOrdinal ); + if( pAdapterInfo ) + { + for( auto it = pAdapterInfo->deviceInfoList.cbegin(); it != pAdapterInfo->deviceInfoList.cend(); ++it ) + { + if( (*it)->DeviceType == DeviceType ) + return *it; + } + } + + return nullptr; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +CD3D11EnumOutputInfo* CD3D11Enumeration::GetOutputInfo( UINT AdapterOrdinal, UINT Output ) const +{ + auto pAdapterInfo = GetAdapterInfo( AdapterOrdinal ); + if( pAdapterInfo && pAdapterInfo->outputInfoList.size() > size_t( Output ) ) + { + return pAdapterInfo->outputInfoList[ Output ]; + } + + return nullptr; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +CD3D11EnumDeviceSettingsCombo* CD3D11Enumeration::GetDeviceSettingsCombo( UINT AdapterOrdinal, + DXGI_FORMAT BackBufferFormat, BOOL Windowed ) const +{ + auto pAdapterInfo = GetAdapterInfo( AdapterOrdinal ); + if( pAdapterInfo ) + { + for( size_t iDeviceCombo = 0; iDeviceCombo < pAdapterInfo->deviceSettingsComboList.size(); iDeviceCombo++ ) + { + auto pDeviceSettingsCombo = pAdapterInfo->deviceSettingsComboList[ iDeviceCombo ]; + if( pDeviceSettingsCombo->BackBufferFormat == BackBufferFormat && + pDeviceSettingsCombo->Windowed == Windowed ) + return pDeviceSettingsCombo; + } + } + + return nullptr; +} + + +//-------------------------------------------------------------------------------------- +CD3D11EnumOutputInfo::~CD3D11EnumOutputInfo() +{ + SAFE_RELEASE( m_pOutput ); + displayModeList.clear(); +} + + +//-------------------------------------------------------------------------------------- +CD3D11EnumDeviceInfo::~CD3D11EnumDeviceInfo() +{ +} + + +//-------------------------------------------------------------------------------------- +CD3D11EnumAdapterInfo::~CD3D11EnumAdapterInfo() +{ + for( size_t j = 0; j < outputInfoList.size(); ++j ) + { + auto pOutputInfo = outputInfoList[ j ]; + delete pOutputInfo; + } + outputInfoList.clear(); + + for( size_t j = 0; j < deviceInfoList.size(); ++j ) + { + auto pDeviceInfo = deviceInfoList[ j ]; + delete pDeviceInfo; + } + deviceInfoList.clear(); + + for( size_t j = 0; j < deviceSettingsComboList.size(); ++j ) + { + auto pDeviceCombo = deviceSettingsComboList[ j ]; + delete pDeviceCombo; + } + deviceSettingsComboList.clear(); + + SAFE_RELEASE( m_pAdapter ); +} + +//-------------------------------------------------------------------------------------- +// Returns the number of color channel bits in the specified DXGI_FORMAT +//-------------------------------------------------------------------------------------- +UINT WINAPI DXUTGetDXGIColorChannelBits( DXGI_FORMAT fmt ) +{ + switch( fmt ) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 32; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + return 16; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + return 10; + + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + return 8; + + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + return 5; + + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 4; + + default: + return 0; + } +} + +//-------------------------------------------------------------------------------------- +// Returns a ranking number that describes how closely this device +// combo matches the optimal combo based on the match options and the optimal device settings +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +float DXUTRankD3D11DeviceCombo( CD3D11EnumDeviceSettingsCombo* pDeviceSettingsCombo, + DXUTD3D11DeviceSettings* pOptimalDeviceSettings, + int &bestModeIndex, + int &bestMSAAIndex + ) +{ + float fCurRanking = 0.0f; + + // Arbitrary weights. Gives preference to the ordinal, device type, and windowed + const float fAdapterOrdinalWeight = 1000.0f; + const float fAdapterOutputWeight = 500.0f; + const float fDeviceTypeWeight = 100.0f; + const float fWARPOverRefWeight = 80.0f; + + const float fWindowWeight = 10.0f; + const float fResolutionWeight = 1.0f; + const float fBackBufferFormatWeight = 1.0f; + const float fMultiSampleWeight = 1.0f; + + //--------------------- + // Adapter ordinal + //--------------------- + if( pDeviceSettingsCombo->AdapterOrdinal == pOptimalDeviceSettings->AdapterOrdinal ) + fCurRanking += fAdapterOrdinalWeight; + + //--------------------- + // Adapter ordinal + //--------------------- + if( pDeviceSettingsCombo->Output == pOptimalDeviceSettings->Output ) + fCurRanking += fAdapterOutputWeight; + + //--------------------- + // Device type + //--------------------- + if( pDeviceSettingsCombo->DeviceType == pOptimalDeviceSettings->DriverType ) + fCurRanking += fDeviceTypeWeight; + else if (pDeviceSettingsCombo->DeviceType == D3D_DRIVER_TYPE_WARP && pOptimalDeviceSettings->DriverType == D3D_DRIVER_TYPE_HARDWARE) { + fCurRanking += fWARPOverRefWeight; + } + + // Slightly prefer HAL + if( pDeviceSettingsCombo->DeviceType == D3D_DRIVER_TYPE_HARDWARE ) + fCurRanking += 0.1f; + + //--------------------- + // Windowed + //--------------------- + if( pDeviceSettingsCombo->Windowed == pOptimalDeviceSettings->sd.Windowed ) + fCurRanking += fWindowWeight; + + //--------------------- + // Resolution/Refresh Rate + //--------------------- + bestModeIndex=0; + + if( pDeviceSettingsCombo->pOutputInfo ) + { + bool bResolutionFound = false; + float best = FLT_MAX; + + if ( !pDeviceSettingsCombo->Windowed + && !pOptimalDeviceSettings->sd.Windowed + && ( pOptimalDeviceSettings->sd.BufferDesc.RefreshRate.Numerator > 0 || pOptimalDeviceSettings->sd.BufferDesc.RefreshRate.Denominator > 0 ) ) + { + // Match both Resolution & Refresh Rate + for( size_t idm = 0; idm < pDeviceSettingsCombo->pOutputInfo->displayModeList.size() && !bResolutionFound; idm++ ) + { + auto displayMode = pDeviceSettingsCombo->pOutputInfo->displayModeList[ idm ]; + + float refreshDiff = fabsf( ( float( displayMode.RefreshRate.Numerator ) / float( displayMode.RefreshRate.Denominator ) ) - + ( float( pOptimalDeviceSettings->sd.BufferDesc.RefreshRate.Numerator ) / float( pOptimalDeviceSettings->sd.BufferDesc.RefreshRate.Denominator ) ) ); + + if( displayMode.Width == pOptimalDeviceSettings->sd.BufferDesc.Width + && displayMode.Height == pOptimalDeviceSettings->sd.BufferDesc.Height + && ( refreshDiff < 0.1f ) ) + { + bResolutionFound = true; + bestModeIndex = static_cast( idm ); + break; + } + + float current = refreshDiff + + fabsf( float( displayMode.Width ) - float ( pOptimalDeviceSettings->sd.BufferDesc.Width ) ) + + fabsf( float( displayMode.Height ) - float ( pOptimalDeviceSettings->sd.BufferDesc.Height ) ); + + if( current < best ) + { + best = current; + bestModeIndex = static_cast( idm ); + } + } + } + else + { + // Match just Resolution + for( size_t idm = 0; idm < pDeviceSettingsCombo->pOutputInfo->displayModeList.size() && !bResolutionFound; idm++ ) + { + auto displayMode = pDeviceSettingsCombo->pOutputInfo->displayModeList[ idm ]; + + if( displayMode.Width == pOptimalDeviceSettings->sd.BufferDesc.Width + && displayMode.Height == pOptimalDeviceSettings->sd.BufferDesc.Height ) + { + bResolutionFound = true; + bestModeIndex = static_cast( idm ); + break; + } + + float current = fabsf( float( displayMode.Width ) - float ( pOptimalDeviceSettings->sd.BufferDesc.Width ) ) + + fabsf( float( displayMode.Height ) - float ( pOptimalDeviceSettings->sd.BufferDesc.Height ) ); + + if( current < best ) + { + best = current; + bestModeIndex = static_cast( idm ); + } + } + } + + if( bResolutionFound ) + fCurRanking += fResolutionWeight; + } + + //--------------------- + // Back buffer format + //--------------------- + if( pDeviceSettingsCombo->BackBufferFormat == pOptimalDeviceSettings->sd.BufferDesc.Format ) + { + fCurRanking += fBackBufferFormatWeight; + } + else + { + int nBitDepthDelta = abs( ( long )DXUTGetDXGIColorChannelBits( pDeviceSettingsCombo->BackBufferFormat ) - + ( long )DXUTGetDXGIColorChannelBits( + pOptimalDeviceSettings->sd.BufferDesc.Format ) ); + float fScale = std::max( 0.9f - ( float )nBitDepthDelta * 0.2f, 0.0f ); + fCurRanking += fScale * fBackBufferFormatWeight; + } + + //--------------------- + // Back buffer count + //--------------------- + // No caps for the back buffer count + + //--------------------- + // Multisample + //--------------------- + bool bMultiSampleFound = false; + bestMSAAIndex = 0; + for( size_t i = 0; i < pDeviceSettingsCombo->multiSampleCountList.size(); i++ ) + { + UINT Count = pDeviceSettingsCombo->multiSampleCountList[ i ]; + + if( Count == pOptimalDeviceSettings->sd.SampleDesc.Count ) + { + bestMSAAIndex = static_cast( i ); + bMultiSampleFound = true; + break; + } + } + if( bMultiSampleFound ) + fCurRanking += fMultiSampleWeight; + + //--------------------- + // Swap effect + //--------------------- + // No caps for swap effects + + //--------------------- + // Depth stencil + //--------------------- + // No caps for swap effects + + //--------------------- + // Present flags + //--------------------- + // No caps for the present flags + + //--------------------- + // Present interval + //--------------------- + // No caps for the present flags + + return fCurRanking; +} + + +//-------------------------------------------------------------------------------------- +// Returns the DXGI_MODE_DESC struct for a given adapter and output +//-------------------------------------------------------------------------------------- +#pragma warning ( suppress : 6101 ) +_Use_decl_annotations_ +HRESULT WINAPI DXUTGetD3D11AdapterDisplayMode( UINT AdapterOrdinal, UINT nOutput, DXGI_MODE_DESC* pModeDesc ) +{ + if( !pModeDesc ) + return E_INVALIDARG; + + auto pD3DEnum = DXUTGetD3D11Enumeration(); + if ( !pD3DEnum ) + return E_POINTER; + + auto pOutputInfo = pD3DEnum->GetOutputInfo( AdapterOrdinal, nOutput ); + if( pOutputInfo ) + { + pModeDesc->Width = 800; + pModeDesc->Height = 600; + pModeDesc->RefreshRate.Numerator = 0; + pModeDesc->RefreshRate.Denominator = 0; + pModeDesc->Format = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + pModeDesc->Scaling = DXGI_MODE_SCALING_UNSPECIFIED; + pModeDesc->ScanlineOrdering = DXGI_MODE_SCANLINE_ORDER_UNSPECIFIED; + + DXGI_OUTPUT_DESC Desc; + if ( FAILED(pOutputInfo->m_pOutput->GetDesc(&Desc))) + memset( &Desc, 0, sizeof(Desc) ); + pModeDesc->Width = Desc.DesktopCoordinates.right - Desc.DesktopCoordinates.left; + pModeDesc->Height = Desc.DesktopCoordinates.bottom - Desc.DesktopCoordinates.top; + + // This should not be required with DXGI 1.1 support for BGRA... + if( pModeDesc->Format == DXGI_FORMAT_B8G8R8A8_UNORM ) + pModeDesc->Format = DXGI_FORMAT_R8G8B8A8_UNORM; + } + + return S_OK; +} diff --git a/src/DX11/framework/dxut/Core/DXUTDevice11.h b/src/DX11/framework/dxut/Core/DXUTDevice11.h new file mode 100644 index 0000000..be698d9 --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUTDevice11.h @@ -0,0 +1,221 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTDevice11.h +// +// Enumerates D3D adapters, devices, modes, etc. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +void DXUTApplyDefaultDeviceSettings(DXUTDeviceSettings *modifySettings); + +//-------------------------------------------------------------------------------------- +// Functions to get bit depth from formats +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTGetD3D11AdapterDisplayMode( _In_ UINT AdapterOrdinal, _In_ UINT Output, _Out_ DXGI_MODE_DESC* pModeDesc ); + + + + +//-------------------------------------------------------------------------------------- +// Optional memory create/destory functions. If not call, these will be called automatically +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTCreateD3D11Enumeration(); +void WINAPI DXUTDestroyD3D11Enumeration(); + + + + +//-------------------------------------------------------------------------------------- +// Forward declarations +//-------------------------------------------------------------------------------------- +class CD3D11EnumAdapterInfo; +class CD3D11EnumDeviceInfo; +class CD3D11EnumOutputInfo; +struct CD3D11EnumDeviceSettingsCombo; + + + +//-------------------------------------------------------------------------------------- +// Enumerates available Direct3D11 adapters, devices, modes, etc. +//-------------------------------------------------------------------------------------- +class CD3D11Enumeration +{ +public: + // These should be called before Enumerate(). + // + // Use these calls and the IsDeviceAcceptable to control the contents of + // the enumeration object, which affects the device selection and the device settings dialog. + void SetResolutionMinMax( _In_ UINT nMinWidth, _In_ UINT nMinHeight, _In_ UINT nMaxWidth, _In_ UINT nMaxHeight ); + void SetRefreshMinMax( _In_ UINT nMin, _In_ UINT nMax ); + void SetForceFeatureLevel( _In_ D3D_FEATURE_LEVEL forceFL) { m_forceFL = forceFL; } + void SetMultisampleQualityMax( _In_ UINT nMax ); + void ResetPossibleDepthStencilFormats(); + void SetEnumerateAllAdapterFormats( _In_ bool bEnumerateAllAdapterFormats ); + + // Call Enumerate() to enumerate available D3D11 adapters, devices, modes, etc. + bool HasEnumerated() { return m_bHasEnumerated; } + HRESULT Enumerate( _In_ LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE IsD3D11DeviceAcceptableFunc, + _In_opt_ void* pIsD3D11DeviceAcceptableFuncUserContext ); + + // These should be called after Enumerate() is called + std::vector* GetAdapterInfoList(); + CD3D11EnumAdapterInfo* GetAdapterInfo( _In_ UINT AdapterOrdinal ) const; + CD3D11EnumDeviceInfo* GetDeviceInfo( _In_ UINT AdapterOrdinal, _In_ D3D_DRIVER_TYPE DeviceType ) const; + CD3D11EnumOutputInfo* GetOutputInfo( _In_ UINT AdapterOrdinal, _In_ UINT Output ) const; + CD3D11EnumDeviceSettingsCombo* GetDeviceSettingsCombo( _In_ DXUTD3D11DeviceSettings* pDeviceSettings ) const { return GetDeviceSettingsCombo( pDeviceSettings->AdapterOrdinal, pDeviceSettings->sd.BufferDesc.Format, pDeviceSettings->sd.Windowed ); } + CD3D11EnumDeviceSettingsCombo* GetDeviceSettingsCombo( _In_ UINT AdapterOrdinal, _In_ DXGI_FORMAT BackBufferFormat, _In_ BOOL Windowed ) const; + D3D_FEATURE_LEVEL GetWARPFeaturevel() const { return m_warpFL; } + D3D_FEATURE_LEVEL GetREFFeaturevel() const { return m_refFL; } + + ~CD3D11Enumeration(); + +private: + friend HRESULT WINAPI DXUTCreateD3D11Enumeration(); + + // Use DXUTGetD3D11Enumeration() to access global instance + CD3D11Enumeration() noexcept; + + bool m_bHasEnumerated; + LPDXUTCALLBACKISD3D11DEVICEACCEPTABLE m_IsD3D11DeviceAcceptableFunc; + void* m_pIsD3D11DeviceAcceptableFuncUserContext; + + std::vector m_DepthStencilPossibleList; + + bool m_bEnumerateAllAdapterFormats; + D3D_FEATURE_LEVEL m_forceFL; + D3D_FEATURE_LEVEL m_warpFL; + D3D_FEATURE_LEVEL m_refFL; + + std::vector m_AdapterInfoList; + + HRESULT EnumerateOutputs( _In_ CD3D11EnumAdapterInfo *pAdapterInfo ); + HRESULT EnumerateDevices( _In_ CD3D11EnumAdapterInfo *pAdapterInfo ); + HRESULT EnumerateDeviceCombos( _In_ CD3D11EnumAdapterInfo* pAdapterInfo ); + HRESULT EnumerateDeviceCombosNoAdapter( _In_ CD3D11EnumAdapterInfo* pAdapterInfo ); + + HRESULT EnumerateDisplayModes( _In_ CD3D11EnumOutputInfo *pOutputInfo ); + void BuildMultiSampleQualityList( _In_ DXGI_FORMAT fmt, _In_ CD3D11EnumDeviceSettingsCombo* pDeviceCombo ); + void ClearAdapterInfoList(); +}; + +CD3D11Enumeration* WINAPI DXUTGetD3D11Enumeration(_In_ bool bForceEnumerate = false, _In_ bool EnumerateAllAdapterFormats = true, _In_ D3D_FEATURE_LEVEL forceFL = ((D3D_FEATURE_LEVEL )0) ); + + +#define DXGI_MAX_DEVICE_IDENTIFIER_STRING 128 + +//-------------------------------------------------------------------------------------- +// A class describing an adapter which contains a unique adapter ordinal +// that is installed on the system +//-------------------------------------------------------------------------------------- +class CD3D11EnumAdapterInfo +{ + const CD3D11EnumAdapterInfo &operator = ( const CD3D11EnumAdapterInfo &rhs ); + +public: + CD3D11EnumAdapterInfo() noexcept : + AdapterOrdinal( 0 ), + AdapterDesc{}, + szUniqueDescription{}, + m_pAdapter( nullptr ), + bAdapterUnavailable(false) + { + *szUniqueDescription = 0; + memset( &AdapterDesc, 0, sizeof(AdapterDesc) ); + } + ~CD3D11EnumAdapterInfo(); + + UINT AdapterOrdinal; + DXGI_ADAPTER_DESC AdapterDesc; + WCHAR szUniqueDescription[DXGI_MAX_DEVICE_IDENTIFIER_STRING]; + IDXGIAdapter *m_pAdapter; + bool bAdapterUnavailable; + + std::vector outputInfoList; // Array of CD3D11EnumOutputInfo* + std::vector deviceInfoList; // Array of CD3D11EnumDeviceInfo* + // List of CD3D11EnumDeviceSettingsCombo* with a unique set + // of BackBufferFormat, and Windowed + std::vector deviceSettingsComboList; +}; + + +class CD3D11EnumOutputInfo +{ + const CD3D11EnumOutputInfo &operator = ( const CD3D11EnumOutputInfo &rhs ); + +public: + CD3D11EnumOutputInfo() noexcept : + AdapterOrdinal(0), + Output(0), + m_pOutput(nullptr), + Desc{} + {} + ~CD3D11EnumOutputInfo(); + + UINT AdapterOrdinal; + UINT Output; + IDXGIOutput* m_pOutput; + DXGI_OUTPUT_DESC Desc; + + std::vector displayModeList; // Array of supported D3DDISPLAYMODEs +}; + + +//-------------------------------------------------------------------------------------- +// A class describing a Direct3D11 device that contains a unique supported driver type +//-------------------------------------------------------------------------------------- +class CD3D11EnumDeviceInfo +{ + const CD3D11EnumDeviceInfo& operator =( const CD3D11EnumDeviceInfo& rhs ); + +public: + ~CD3D11EnumDeviceInfo(); + + UINT AdapterOrdinal; + D3D_DRIVER_TYPE DeviceType; + D3D_FEATURE_LEVEL SelectedLevel; + D3D_FEATURE_LEVEL MaxLevel; + BOOL ComputeShaders_Plus_RawAndStructuredBuffers_Via_Shader_4_x; +}; + + +//-------------------------------------------------------------------------------------- +// A struct describing device settings that contains a unique combination of +// adapter format, back buffer format, and windowed that is compatible with a +// particular Direct3D device and the app. +//-------------------------------------------------------------------------------------- +struct CD3D11EnumDeviceSettingsCombo +{ + UINT AdapterOrdinal; + D3D_DRIVER_TYPE DeviceType; + DXGI_FORMAT BackBufferFormat; + BOOL Windowed; + UINT Output; + + std::vector multiSampleCountList; // List of valid sampling counts (multisampling) + std::vector multiSampleQualityList; // List of number of quality levels for each multisample count + + CD3D11EnumAdapterInfo* pAdapterInfo; + CD3D11EnumDeviceInfo* pDeviceInfo; + CD3D11EnumOutputInfo* pOutputInfo; + + CD3D11EnumDeviceSettingsCombo() noexcept : + AdapterOrdinal(0), + DeviceType(D3D_DRIVER_TYPE_UNKNOWN), + BackBufferFormat(DXGI_FORMAT_UNKNOWN), + Windowed(FALSE), + Output(0), + pAdapterInfo(nullptr), + pDeviceInfo(nullptr), + pOutputInfo(nullptr) + { } +}; + +float DXUTRankD3D11DeviceCombo( _In_ CD3D11EnumDeviceSettingsCombo* pDeviceSettingsCombo, + _In_ DXUTD3D11DeviceSettings* pOptimalDeviceSettings, + _Out_ int &bestModeIndex, + _Out_ int &bestMSAAIndex + ); diff --git a/src/DX11/framework/dxut/Core/DXUT_2017_Win10.vcxproj b/src/DX11/framework/dxut/Core/DXUT_2017_Win10.vcxproj new file mode 100644 index 0000000..611d4f8 --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT_2017_Win10.vcxproj @@ -0,0 +1,349 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DXUT + {85344B7F-5AA0-4e12-A065-D1333D11F6CA} + DXUT + Win32Proj + 10.0.19041.0 + + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUT + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + StreamingSIMDExtensions2 + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/DX11/framework/dxut/Core/DXUT_2017_Win10.vcxproj.filters b/src/DX11/framework/dxut/Core/DXUT_2017_Win10.vcxproj.filters new file mode 100644 index 0000000..78f1ab4 --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT_2017_Win10.vcxproj.filters @@ -0,0 +1,29 @@ + + + + +{8e114980-c1a3-4ada-ad7c-83caadf5daeb} +rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/DX11/framework/dxut/Core/DXUT_2019_Win10.vcxproj b/src/DX11/framework/dxut/Core/DXUT_2019_Win10.vcxproj new file mode 100644 index 0000000..60fe30c --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT_2019_Win10.vcxproj @@ -0,0 +1,349 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DXUT + {85344B7F-5AA0-4e12-A065-D1333D11F6CA} + DXUT + Win32Proj + 10.0 + + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + + + + + + + + + + + + + + + + + + + + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUT + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + StreamingSIMDExtensions2 + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/DX11/framework/dxut/Core/DXUT_2019_Win10.vcxproj.filters b/src/DX11/framework/dxut/Core/DXUT_2019_Win10.vcxproj.filters new file mode 100644 index 0000000..78f1ab4 --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT_2019_Win10.vcxproj.filters @@ -0,0 +1,29 @@ + + + + +{8e114980-c1a3-4ada-ad7c-83caadf5daeb} +rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2017_Win10.vcxproj b/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2017_Win10.vcxproj new file mode 100644 index 0000000..ea49ebc --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2017_Win10.vcxproj @@ -0,0 +1,349 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DXUT + {85344B7F-5AA0-4e12-A065-D1333D11F6CA} + DXUT + Win32Proj + 10.0.19041.0 + + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUT + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2017_Win10.vcxproj.filters b/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2017_Win10.vcxproj.filters new file mode 100644 index 0000000..153fbf3 --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2017_Win10.vcxproj.filters @@ -0,0 +1,23 @@ + + + + +{8e114980-c1a3-4ada-ad7c-83caadf5daeb} +rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + + + + + + + + + + diff --git a/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2019_Win10.vcxproj b/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2019_Win10.vcxproj new file mode 100644 index 0000000..ab2810f --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2019_Win10.vcxproj @@ -0,0 +1,349 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DXUT + {85344B7F-5AA0-4e12-A065-D1333D11F6CA} + DXUT + Win32Proj + 10.0 + + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + + + + + + + + + + + + + + + + + + + + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUT + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUT + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\..\DirectXTK\Inc;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2019_Win10.vcxproj.filters b/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2019_Win10.vcxproj.filters new file mode 100644 index 0000000..153fbf3 --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUT_DirectXTK_2019_Win10.vcxproj.filters @@ -0,0 +1,23 @@ + + + + +{8e114980-c1a3-4ada-ad7c-83caadf5daeb} +rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + + + + + + + + + + diff --git a/src/DX11/framework/dxut/Core/DXUTmisc.cpp b/src/DX11/framework/dxut/Core/DXUTmisc.cpp new file mode 100644 index 0000000..162510b --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUTmisc.cpp @@ -0,0 +1,1273 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTMisc.cpp +// +// Shortcut macros and functions for using DX objects +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "dxut.h" +#include + +#include "ScreenGrab.h" + + +#define DXUT_GAMEPAD_TRIGGER_THRESHOLD 30 + +CDXUTTimer* WINAPI DXUTGetGlobalTimer() +{ + // Using an accessor function gives control of the construction order + static CDXUTTimer timer; + return &timer; +} + + +//-------------------------------------------------------------------------------------- +CDXUTTimer::CDXUTTimer() noexcept : + m_bTimerStopped(true), + m_llQPFTicksPerSec{}, + m_llStopTime{}, + m_llLastElapsedTime{}, + m_llBaseTime{} +{ + // Use QueryPerformanceFrequency to get the frequency of the counter + LARGE_INTEGER qwTicksPerSec = {}; + QueryPerformanceFrequency( &qwTicksPerSec ); + m_llQPFTicksPerSec = qwTicksPerSec.QuadPart; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTTimer::Reset() +{ + LARGE_INTEGER qwTime = GetAdjustedCurrentTime(); + + m_llBaseTime = qwTime.QuadPart; + m_llLastElapsedTime = qwTime.QuadPart; + m_llStopTime = 0; + m_bTimerStopped = FALSE; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTTimer::Start() +{ + // Get the current time + LARGE_INTEGER qwTime = {}; + QueryPerformanceCounter( &qwTime ); + + if( m_bTimerStopped ) + m_llBaseTime += qwTime.QuadPart - m_llStopTime; + m_llStopTime = 0; + m_llLastElapsedTime = qwTime.QuadPart; + m_bTimerStopped = FALSE; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTTimer::Stop() +{ + if( !m_bTimerStopped ) + { + LARGE_INTEGER qwTime = {}; + QueryPerformanceCounter( &qwTime ); + m_llStopTime = qwTime.QuadPart; + m_llLastElapsedTime = qwTime.QuadPart; + m_bTimerStopped = TRUE; + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTTimer::Advance() +{ + m_llStopTime += m_llQPFTicksPerSec / 10; +} + + +//-------------------------------------------------------------------------------------- +double CDXUTTimer::GetAbsoluteTime() const +{ + LARGE_INTEGER qwTime = {}; + QueryPerformanceCounter( &qwTime ); + + double fTime = qwTime.QuadPart / ( double )m_llQPFTicksPerSec; + + return fTime; +} + + +//-------------------------------------------------------------------------------------- +double CDXUTTimer::GetTime() const +{ + LARGE_INTEGER qwTime = GetAdjustedCurrentTime(); + + double fAppTime = ( double )( qwTime.QuadPart - m_llBaseTime ) / ( double )m_llQPFTicksPerSec; + + return fAppTime; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTTimer::GetTimeValues( double* pfTime, double* pfAbsoluteTime, float* pfElapsedTime ) +{ + assert( pfTime && pfAbsoluteTime && pfElapsedTime ); + + LARGE_INTEGER qwTime = GetAdjustedCurrentTime(); + + float fElapsedTime = (float) ((double) ( qwTime.QuadPart - m_llLastElapsedTime ) / (double) m_llQPFTicksPerSec); + m_llLastElapsedTime = qwTime.QuadPart; + + // Clamp the timer to non-negative values to ensure the timer is accurate. + // fElapsedTime can be outside this range if processor goes into a + // power save mode or we somehow get shuffled to another processor. + // However, the main thread should call SetThreadAffinityMask to ensure that + // we don't get shuffled to another processor. Other worker threads should NOT call + // SetThreadAffinityMask, but use a shared copy of the timer data gathered from + // the main thread. + if( fElapsedTime < 0.0f ) + fElapsedTime = 0.0f; + + *pfAbsoluteTime = qwTime.QuadPart / ( double )m_llQPFTicksPerSec; + *pfTime = ( qwTime.QuadPart - m_llBaseTime ) / ( double )m_llQPFTicksPerSec; + *pfElapsedTime = fElapsedTime; +} + + +//-------------------------------------------------------------------------------------- +float CDXUTTimer::GetElapsedTime() +{ + LARGE_INTEGER qwTime = GetAdjustedCurrentTime(); + + double fElapsedTime = (float) ((double) ( qwTime.QuadPart - m_llLastElapsedTime ) / (double) m_llQPFTicksPerSec); + m_llLastElapsedTime = qwTime.QuadPart; + + // See the explanation about clamping in CDXUTTimer::GetTimeValues() + if( fElapsedTime < 0.0f ) + fElapsedTime = 0.0f; + + return ( float )fElapsedTime; +} + + +//-------------------------------------------------------------------------------------- +// If stopped, returns time when stopped otherwise returns current time +//-------------------------------------------------------------------------------------- +LARGE_INTEGER CDXUTTimer::GetAdjustedCurrentTime() const +{ + LARGE_INTEGER qwTime; + if( m_llStopTime != 0 ) + qwTime.QuadPart = m_llStopTime; + else + QueryPerformanceCounter( &qwTime ); + return qwTime; +} + +//-------------------------------------------------------------------------------------- +// Limit the current thread to one processor (the current one). This ensures that timing code +// runs on only one processor, and will not suffer any ill effects from power management. +// See "Game Timing and Multicore Processors" for more details +//-------------------------------------------------------------------------------------- +void CDXUTTimer::LimitThreadAffinityToCurrentProc() +{ + HANDLE hCurrentProcess = GetCurrentProcess(); + + // Get the processor affinity mask for this process + DWORD_PTR dwProcessAffinityMask = 0; + DWORD_PTR dwSystemAffinityMask = 0; + + if( GetProcessAffinityMask( hCurrentProcess, &dwProcessAffinityMask, &dwSystemAffinityMask ) != 0 && + dwProcessAffinityMask ) + { + // Find the lowest processor that our process is allows to run against + DWORD_PTR dwAffinityMask = ( dwProcessAffinityMask & ( ( ~dwProcessAffinityMask ) + 1 ) ); + + // Set this as the processor that our thread must always run against + // This must be a subset of the process affinity mask + HANDLE hCurrentThread = GetCurrentThread(); + if( INVALID_HANDLE_VALUE != hCurrentThread ) + { + SetThreadAffinityMask( hCurrentThread, dwAffinityMask ); + CloseHandle( hCurrentThread ); + } + } + + CloseHandle( hCurrentProcess ); +} + + +//-------------------------------------------------------------------------------------- +// Returns the string for the given DXGI_FORMAT. +//-------------------------------------------------------------------------------------- +#define DXUTDXGIFMTSTR( a ) case a: pstr = L## #a; break; + +_Use_decl_annotations_ +LPCWSTR WINAPI DXUTDXGIFormatToString( DXGI_FORMAT format, bool bWithPrefix ) +{ + const WCHAR* pstr = nullptr; + switch( format ) + { + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32B32A32_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32B32A32_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32B32A32_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32B32A32_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32B32_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32B32_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32B32_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32B32_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16B16A16_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16B16A16_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16B16A16_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16B16A16_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16B16A16_SNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16B16A16_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G32_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32G8X24_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_D32_FLOAT_S8X24_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_X32_TYPELESS_G8X24_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R10G10B10A2_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R10G10B10A2_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R10G10B10A2_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R11G11B10_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8B8A8_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8B8A8_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8B8A8_UNORM_SRGB) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8B8A8_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8B8A8_SNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8B8A8_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16_SNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16G16_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_D32_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R32_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R24G8_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_D24_UNORM_S8_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R24_UNORM_X8_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_X24_TYPELESS_G8_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8_SNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16_FLOAT) + DXUTDXGIFMTSTR(DXGI_FORMAT_D16_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16_SNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R16_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8_UINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8_SNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8_SINT) + DXUTDXGIFMTSTR(DXGI_FORMAT_A8_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R1_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R9G9B9E5_SHAREDEXP) + DXUTDXGIFMTSTR(DXGI_FORMAT_R8G8_B8G8_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_G8R8_G8B8_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC1_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC1_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC1_UNORM_SRGB) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC2_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC2_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC2_UNORM_SRGB) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC3_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC3_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC3_UNORM_SRGB) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC4_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC4_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC4_SNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC5_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC5_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC5_SNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_B5G6R5_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_B5G5R5A1_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_B8G8R8A8_UNORM) + + // DXGI 1.1 + DXUTDXGIFMTSTR(DXGI_FORMAT_B8G8R8X8_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_B8G8R8A8_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_B8G8R8A8_UNORM_SRGB) + DXUTDXGIFMTSTR(DXGI_FORMAT_B8G8R8X8_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_B8G8R8X8_UNORM_SRGB) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC6H_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC6H_UF16) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC6H_SF16) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC7_TYPELESS) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC7_UNORM) + DXUTDXGIFMTSTR(DXGI_FORMAT_BC7_UNORM_SRGB) + + // DXGI 1.2 + DXUTDXGIFMTSTR(DXGI_FORMAT_B4G4R4A4_UNORM) + + default: + pstr = L"Unknown format"; break; + } + if( bWithPrefix || !wcsstr( pstr, L"DXGI_FORMAT_" ) ) + return pstr; + else + return pstr + wcslen( L"DXGI_FORMAT_" ); +} + +#undef DXUTDXGIFMTSTR + + +//-------------------------------------------------------------------------------------- +// Outputs to the debug stream a formatted Unicode string with a variable-argument list. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +VOID WINAPI DXUTOutputDebugStringW( LPCWSTR strMsg, ... ) +{ +#if defined(DEBUG) || defined(_DEBUG) + WCHAR strBuffer[512]; + + va_list args; + va_start(args, strMsg); + vswprintf_s( strBuffer, 512, strMsg, args ); + strBuffer[511] = L'\0'; + va_end(args); + + OutputDebugString( strBuffer ); +#else + UNREFERENCED_PARAMETER( strMsg ); +#endif +} + + +//-------------------------------------------------------------------------------------- +// Outputs to the debug stream a formatted MBCS string with a variable-argument list. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +VOID WINAPI DXUTOutputDebugStringA( LPCSTR strMsg, ... ) +{ +#if defined(DEBUG) || defined(_DEBUG) + CHAR strBuffer[512]; + + va_list args; + va_start(args, strMsg); + sprintf_s( strBuffer, 512, strMsg, args ); + strBuffer[511] = '\0'; + va_end(args); + + OutputDebugStringA( strBuffer ); +#else + UNREFERENCED_PARAMETER( strMsg ); +#endif +} + + +//-------------------------------------------------------------------------------------- +// Direct3D dynamic linking support -- calls top-level D3D APIs with graceful +// failure if APIs are not present. +//-------------------------------------------------------------------------------------- + +// Function prototypes +typedef INT (WINAPI * LPD3DPERF_BEGINEVENT)(DWORD, LPCWSTR); +typedef INT (WINAPI * LPD3DPERF_ENDEVENT)(void); +typedef VOID (WINAPI * LPD3DPERF_SETMARKER)(DWORD, LPCWSTR); +typedef VOID (WINAPI * LPD3DPERF_SETREGION)(DWORD, LPCWSTR); +typedef BOOL (WINAPI * LPD3DPERF_QUERYREPEATFRAME)(void); +typedef VOID (WINAPI * LPD3DPERF_SETOPTIONS)( DWORD dwOptions ); +typedef DWORD (WINAPI * LPD3DPERF_GETSTATUS)(); +typedef HRESULT (WINAPI * LPCREATEDXGIFACTORY)(REFIID, void ** ); +typedef HRESULT (WINAPI * LPDXGIGETDEBUGINTERFACE)(REFIID, void ** ); + +// Module and function pointers +static HMODULE s_hModD3D9 = nullptr; +static LPD3DPERF_BEGINEVENT s_DynamicD3DPERF_BeginEvent = nullptr; +static LPD3DPERF_ENDEVENT s_DynamicD3DPERF_EndEvent = nullptr; +static LPD3DPERF_SETMARKER s_DynamicD3DPERF_SetMarker = nullptr; +static LPD3DPERF_SETREGION s_DynamicD3DPERF_SetRegion = nullptr; +static LPD3DPERF_QUERYREPEATFRAME s_DynamicD3DPERF_QueryRepeatFrame = nullptr; +static LPD3DPERF_SETOPTIONS s_DynamicD3DPERF_SetOptions = nullptr; +static LPD3DPERF_GETSTATUS s_DynamicD3DPERF_GetStatus = nullptr; +static HMODULE s_hModDXGI = nullptr; +static HMODULE s_hModDXGIDebug = nullptr; +static LPCREATEDXGIFACTORY s_DynamicCreateDXGIFactory = nullptr; +static LPDXGIGETDEBUGINTERFACE s_DynamicDXGIGetDebugInterface = nullptr; +static HMODULE s_hModD3D11 = nullptr; +static PFN_D3D11_CREATE_DEVICE s_DynamicD3D11CreateDevice = nullptr; + +// Ensure function pointers are initialized +static bool DXUT_EnsureD3D9APIs() +{ + // If the module is non-NULL, this function has already been called. Note + // that this doesn't guarantee that all ProcAddresses were found. + if( s_hModD3D9 ) + return true; + + // This could fail in theory, but not on any modern version of Windows + s_hModD3D9 = LoadLibraryEx( L"d3d9.dll", nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + if( s_hModD3D9 ) + { + // TODO - Use 11.1 perf APIs instead? + s_DynamicD3DPERF_BeginEvent = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModD3D9, "D3DPERF_BeginEvent" ) ) ); + s_DynamicD3DPERF_EndEvent = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModD3D9, "D3DPERF_EndEvent" ) ) ); + s_DynamicD3DPERF_SetMarker = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModD3D9, "D3DPERF_SetMarker" ) ) ); + s_DynamicD3DPERF_SetRegion = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModD3D9, "D3DPERF_SetRegion" ) ) ); + s_DynamicD3DPERF_QueryRepeatFrame = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModD3D9, "D3DPERF_QueryRepeatFrame" ) ) ); + s_DynamicD3DPERF_SetOptions = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModD3D9, "D3DPERF_SetOptions" ) ) ); + s_DynamicD3DPERF_GetStatus = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModD3D9, "D3DPERF_GetStatus" ) ) ); + } + + return s_hModD3D9 != nullptr; +} + +bool DXUT_EnsureD3D11APIs() +{ + // If both modules are non-NULL, this function has already been called. Note + // that this doesn't guarantee that all ProcAddresses were found. + if( s_hModD3D11 && s_hModDXGI ) + return true; + + // This may fail if Direct3D 11 isn't installed + s_hModD3D11 = LoadLibraryEx( L"d3d11.dll", nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + if( s_hModD3D11 ) + { + s_DynamicD3D11CreateDevice = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModD3D11, "D3D11CreateDevice" ) ) ); + } + + if( !s_DynamicCreateDXGIFactory ) + { + s_hModDXGI = LoadLibraryEx( L"dxgi.dll", nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + if( s_hModDXGI ) + { + s_DynamicCreateDXGIFactory = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModDXGI, "CreateDXGIFactory1" ) ) ); + } + + if ( !s_DynamicDXGIGetDebugInterface ) + { + s_hModDXGIDebug = LoadLibraryEx( L"dxgidebug.dll", nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + if ( s_hModDXGIDebug ) + { + s_DynamicDXGIGetDebugInterface = reinterpret_cast( reinterpret_cast( GetProcAddress( s_hModDXGIDebug, "DXGIGetDebugInterface" ) ) ); + } + } + + return ( s_hModDXGI ) && ( s_hModD3D11 ); + } + + return s_hModD3D11 != nullptr; +} + +int WINAPI DXUT_Dynamic_D3DPERF_BeginEvent( _In_ DWORD col, _In_z_ LPCWSTR wszName ) +{ + if( DXUT_EnsureD3D9APIs() && s_DynamicD3DPERF_BeginEvent ) + return s_DynamicD3DPERF_BeginEvent( col, wszName ); + else + return -1; +} + +int WINAPI DXUT_Dynamic_D3DPERF_EndEvent() +{ + if( DXUT_EnsureD3D9APIs() && s_DynamicD3DPERF_EndEvent ) + return s_DynamicD3DPERF_EndEvent(); + else + return -1; +} + +void WINAPI DXUT_Dynamic_D3DPERF_SetMarker( _In_ DWORD col, _In_z_ LPCWSTR wszName ) +{ + if( DXUT_EnsureD3D9APIs() && s_DynamicD3DPERF_SetMarker ) + s_DynamicD3DPERF_SetMarker( col, wszName ); +} + +void WINAPI DXUT_Dynamic_D3DPERF_SetRegion( _In_ DWORD col, _In_z_ LPCWSTR wszName ) +{ + if( DXUT_EnsureD3D9APIs() && s_DynamicD3DPERF_SetRegion ) + s_DynamicD3DPERF_SetRegion( col, wszName ); +} + +BOOL WINAPI DXUT_Dynamic_D3DPERF_QueryRepeatFrame() +{ + if( DXUT_EnsureD3D9APIs() && s_DynamicD3DPERF_QueryRepeatFrame ) + return s_DynamicD3DPERF_QueryRepeatFrame(); + else + return FALSE; +} + +void WINAPI DXUT_Dynamic_D3DPERF_SetOptions( _In_ DWORD dwOptions ) +{ + if( DXUT_EnsureD3D9APIs() && s_DynamicD3DPERF_SetOptions ) + s_DynamicD3DPERF_SetOptions( dwOptions ); +} + +DWORD WINAPI DXUT_Dynamic_D3DPERF_GetStatus() +{ + if( DXUT_EnsureD3D9APIs() && s_DynamicD3DPERF_GetStatus ) + return s_DynamicD3DPERF_GetStatus(); + else + return 0; +} + +_Use_decl_annotations_ +HRESULT WINAPI DXUT_Dynamic_CreateDXGIFactory1( REFIID rInterface, void** ppOut ) +{ + if( DXUT_EnsureD3D11APIs() && s_DynamicCreateDXGIFactory ) + return s_DynamicCreateDXGIFactory( rInterface, ppOut ); + else + return DXUTERR_NODIRECT3D; +} + +_Use_decl_annotations_ +HRESULT WINAPI DXUT_Dynamic_DXGIGetDebugInterface( REFIID rInterface, void** ppOut ) +{ + if( DXUT_EnsureD3D11APIs() && s_DynamicDXGIGetDebugInterface ) + return s_DynamicDXGIGetDebugInterface( rInterface, ppOut ); + else + return E_NOTIMPL; +} + +_Use_decl_annotations_ +HRESULT WINAPI DXUT_Dynamic_D3D11CreateDevice( IDXGIAdapter* pAdapter, + D3D_DRIVER_TYPE DriverType, + HMODULE Software, + UINT32 Flags, + const D3D_FEATURE_LEVEL* pFeatureLevels, + UINT FeatureLevels, + UINT32 SDKVersion, + ID3D11Device** ppDevice, + D3D_FEATURE_LEVEL* pFeatureLevel, + ID3D11DeviceContext** ppImmediateContext ) +{ + if( DXUT_EnsureD3D11APIs() && s_DynamicD3D11CreateDevice ) + return s_DynamicD3D11CreateDevice( pAdapter, DriverType, Software, Flags, pFeatureLevels, FeatureLevels, + SDKVersion, ppDevice, pFeatureLevel, ppImmediateContext ); + else + return DXUTERR_NODIRECT3D; +} + +#define TRACE_ID(iD) case iD: return L## #iD; + +//-------------------------------------------------------------------------------------- +const WCHAR* WINAPI DXUTTraceWindowsMessage( _In_ UINT uMsg ) +{ + switch( uMsg ) + { + TRACE_ID(WM_NULL); + TRACE_ID(WM_CREATE); + TRACE_ID(WM_DESTROY); + TRACE_ID(WM_MOVE); + TRACE_ID(WM_SIZE); + TRACE_ID(WM_ACTIVATE); + TRACE_ID(WM_SETFOCUS); + TRACE_ID(WM_KILLFOCUS); + TRACE_ID(WM_ENABLE); + TRACE_ID(WM_SETREDRAW); + TRACE_ID(WM_SETTEXT); + TRACE_ID(WM_GETTEXT); + TRACE_ID(WM_GETTEXTLENGTH); + TRACE_ID(WM_PAINT); + TRACE_ID(WM_CLOSE); + TRACE_ID(WM_QUERYENDSESSION); + TRACE_ID(WM_QUERYOPEN); + TRACE_ID(WM_ENDSESSION); + TRACE_ID(WM_QUIT); + TRACE_ID(WM_ERASEBKGND); + TRACE_ID(WM_SYSCOLORCHANGE); + TRACE_ID(WM_SHOWWINDOW); + TRACE_ID(WM_WININICHANGE); + TRACE_ID(WM_DEVMODECHANGE); + TRACE_ID(WM_ACTIVATEAPP); + TRACE_ID(WM_FONTCHANGE); + TRACE_ID(WM_TIMECHANGE); + TRACE_ID(WM_CANCELMODE); + TRACE_ID(WM_SETCURSOR); + TRACE_ID(WM_MOUSEACTIVATE); + TRACE_ID(WM_CHILDACTIVATE); + TRACE_ID(WM_QUEUESYNC); + TRACE_ID(WM_GETMINMAXINFO); + TRACE_ID(WM_PAINTICON); + TRACE_ID(WM_ICONERASEBKGND); + TRACE_ID(WM_NEXTDLGCTL); + TRACE_ID(WM_SPOOLERSTATUS); + TRACE_ID(WM_DRAWITEM); + TRACE_ID(WM_MEASUREITEM); + TRACE_ID(WM_DELETEITEM); + TRACE_ID(WM_VKEYTOITEM); + TRACE_ID(WM_CHARTOITEM); + TRACE_ID(WM_SETFONT); + TRACE_ID(WM_GETFONT); + TRACE_ID(WM_SETHOTKEY); + TRACE_ID(WM_GETHOTKEY); + TRACE_ID(WM_QUERYDRAGICON); + TRACE_ID(WM_COMPAREITEM); + TRACE_ID(WM_GETOBJECT); + TRACE_ID(WM_COMPACTING); + TRACE_ID(WM_COMMNOTIFY); + TRACE_ID(WM_WINDOWPOSCHANGING); + TRACE_ID(WM_WINDOWPOSCHANGED); + TRACE_ID(WM_POWER); + TRACE_ID(WM_COPYDATA); + TRACE_ID(WM_CANCELJOURNAL); + TRACE_ID(WM_NOTIFY); + TRACE_ID(WM_INPUTLANGCHANGEREQUEST); + TRACE_ID(WM_INPUTLANGCHANGE); + TRACE_ID(WM_TCARD); + TRACE_ID(WM_HELP); + TRACE_ID(WM_USERCHANGED); + TRACE_ID(WM_NOTIFYFORMAT); + TRACE_ID(WM_CONTEXTMENU); + TRACE_ID(WM_STYLECHANGING); + TRACE_ID(WM_STYLECHANGED); + TRACE_ID(WM_DISPLAYCHANGE); + TRACE_ID(WM_GETICON); + TRACE_ID(WM_SETICON); + TRACE_ID(WM_NCCREATE); + TRACE_ID(WM_NCDESTROY); + TRACE_ID(WM_NCCALCSIZE); + TRACE_ID(WM_NCHITTEST); + TRACE_ID(WM_NCPAINT); + TRACE_ID(WM_NCACTIVATE); + TRACE_ID(WM_GETDLGCODE); + TRACE_ID(WM_SYNCPAINT); + TRACE_ID(WM_NCMOUSEMOVE); + TRACE_ID(WM_NCLBUTTONDOWN); + TRACE_ID(WM_NCLBUTTONUP); + TRACE_ID(WM_NCLBUTTONDBLCLK); + TRACE_ID(WM_NCRBUTTONDOWN); + TRACE_ID(WM_NCRBUTTONUP); + TRACE_ID(WM_NCRBUTTONDBLCLK); + TRACE_ID(WM_NCMBUTTONDOWN); + TRACE_ID(WM_NCMBUTTONUP); + TRACE_ID(WM_NCMBUTTONDBLCLK); + TRACE_ID(WM_NCXBUTTONDOWN); + TRACE_ID(WM_NCXBUTTONUP); + TRACE_ID(WM_NCXBUTTONDBLCLK); + TRACE_ID(WM_INPUT); + TRACE_ID(WM_KEYDOWN); + TRACE_ID(WM_KEYUP); + TRACE_ID(WM_CHAR); + TRACE_ID(WM_DEADCHAR); + TRACE_ID(WM_SYSKEYDOWN); + TRACE_ID(WM_SYSKEYUP); + TRACE_ID(WM_SYSCHAR); + TRACE_ID(WM_SYSDEADCHAR); + TRACE_ID(WM_UNICHAR); + TRACE_ID(WM_IME_STARTCOMPOSITION); + TRACE_ID(WM_IME_ENDCOMPOSITION); + TRACE_ID(WM_IME_COMPOSITION); + TRACE_ID(WM_INITDIALOG); + TRACE_ID(WM_COMMAND); + TRACE_ID(WM_SYSCOMMAND); + TRACE_ID(WM_TIMER); + TRACE_ID(WM_HSCROLL); + TRACE_ID(WM_VSCROLL); + TRACE_ID(WM_INITMENU); + TRACE_ID(WM_INITMENUPOPUP); + TRACE_ID(WM_MENUSELECT); + TRACE_ID(WM_MENUCHAR); + TRACE_ID(WM_ENTERIDLE); + TRACE_ID(WM_MENURBUTTONUP); + TRACE_ID(WM_MENUDRAG); + TRACE_ID(WM_MENUGETOBJECT); + TRACE_ID(WM_UNINITMENUPOPUP); + TRACE_ID(WM_MENUCOMMAND); + TRACE_ID(WM_CHANGEUISTATE); + TRACE_ID(WM_UPDATEUISTATE); + TRACE_ID(WM_QUERYUISTATE); + TRACE_ID(WM_CTLCOLORMSGBOX); + TRACE_ID(WM_CTLCOLOREDIT); + TRACE_ID(WM_CTLCOLORLISTBOX); + TRACE_ID(WM_CTLCOLORBTN); + TRACE_ID(WM_CTLCOLORDLG); + TRACE_ID(WM_CTLCOLORSCROLLBAR); + TRACE_ID(WM_CTLCOLORSTATIC); + TRACE_ID(MN_GETHMENU); + TRACE_ID(WM_MOUSEMOVE); + TRACE_ID(WM_LBUTTONDOWN); + TRACE_ID(WM_LBUTTONUP); + TRACE_ID(WM_LBUTTONDBLCLK); + TRACE_ID(WM_RBUTTONDOWN); + TRACE_ID(WM_RBUTTONUP); + TRACE_ID(WM_RBUTTONDBLCLK); + TRACE_ID(WM_MBUTTONDOWN); + TRACE_ID(WM_MBUTTONUP); + TRACE_ID(WM_MBUTTONDBLCLK); + TRACE_ID(WM_MOUSEWHEEL); + TRACE_ID(WM_XBUTTONDOWN); + TRACE_ID(WM_XBUTTONUP); + TRACE_ID(WM_XBUTTONDBLCLK); + TRACE_ID(WM_PARENTNOTIFY); + TRACE_ID(WM_ENTERMENULOOP); + TRACE_ID(WM_EXITMENULOOP); + TRACE_ID(WM_NEXTMENU); + TRACE_ID(WM_SIZING); + TRACE_ID(WM_CAPTURECHANGED); + TRACE_ID(WM_MOVING); + TRACE_ID(WM_POWERBROADCAST); + TRACE_ID(WM_DEVICECHANGE); + TRACE_ID(WM_MDICREATE); + TRACE_ID(WM_MDIDESTROY); + TRACE_ID(WM_MDIACTIVATE); + TRACE_ID(WM_MDIRESTORE); + TRACE_ID(WM_MDINEXT); + TRACE_ID(WM_MDIMAXIMIZE); + TRACE_ID(WM_MDITILE); + TRACE_ID(WM_MDICASCADE); + TRACE_ID(WM_MDIICONARRANGE); + TRACE_ID(WM_MDIGETACTIVE); + TRACE_ID(WM_MDISETMENU); + TRACE_ID(WM_ENTERSIZEMOVE); + TRACE_ID(WM_EXITSIZEMOVE); + TRACE_ID(WM_DROPFILES); + TRACE_ID(WM_MDIREFRESHMENU); + TRACE_ID(WM_IME_SETCONTEXT); + TRACE_ID(WM_IME_NOTIFY); + TRACE_ID(WM_IME_CONTROL); + TRACE_ID(WM_IME_COMPOSITIONFULL); + TRACE_ID(WM_IME_SELECT); + TRACE_ID(WM_IME_CHAR); + TRACE_ID(WM_IME_REQUEST); + TRACE_ID(WM_IME_KEYDOWN); + TRACE_ID(WM_IME_KEYUP); + TRACE_ID(WM_MOUSEHOVER); + TRACE_ID(WM_MOUSELEAVE); + TRACE_ID(WM_NCMOUSEHOVER); + TRACE_ID(WM_NCMOUSELEAVE); + TRACE_ID(WM_WTSSESSION_CHANGE); + TRACE_ID(WM_TABLET_FIRST); + TRACE_ID(WM_TABLET_LAST); + TRACE_ID(WM_CUT); + TRACE_ID(WM_COPY); + TRACE_ID(WM_PASTE); + TRACE_ID(WM_CLEAR); + TRACE_ID(WM_UNDO); + TRACE_ID(WM_RENDERFORMAT); + TRACE_ID(WM_RENDERALLFORMATS); + TRACE_ID(WM_DESTROYCLIPBOARD); + TRACE_ID(WM_DRAWCLIPBOARD); + TRACE_ID(WM_PAINTCLIPBOARD); + TRACE_ID(WM_VSCROLLCLIPBOARD); + TRACE_ID(WM_SIZECLIPBOARD); + TRACE_ID(WM_ASKCBFORMATNAME); + TRACE_ID(WM_CHANGECBCHAIN); + TRACE_ID(WM_HSCROLLCLIPBOARD); + TRACE_ID(WM_QUERYNEWPALETTE); + TRACE_ID(WM_PALETTEISCHANGING); + TRACE_ID(WM_PALETTECHANGED); + TRACE_ID(WM_HOTKEY); + TRACE_ID(WM_PRINT); + TRACE_ID(WM_PRINTCLIENT); + TRACE_ID(WM_APPCOMMAND); + TRACE_ID(WM_THEMECHANGED); + TRACE_ID(WM_HANDHELDFIRST); + TRACE_ID(WM_HANDHELDLAST); + TRACE_ID(WM_AFXFIRST); + TRACE_ID(WM_AFXLAST); + TRACE_ID(WM_PENWINFIRST); + TRACE_ID(WM_PENWINLAST); + TRACE_ID(WM_APP); + default: + return L"Unknown"; + } +} + + +//-------------------------------------------------------------------------------------- +// Multimon API handling for OSes with or without multimon API support +//-------------------------------------------------------------------------------------- +#define DXUT_PRIMARY_MONITOR ((HMONITOR)0x12340042) +typedef HMONITOR ( WINAPI* LPMONITORFROMWINDOW )( HWND, DWORD ); +typedef BOOL ( WINAPI* LPGETMONITORINFO )( HMONITOR, LPMONITORINFO ); +typedef HMONITOR ( WINAPI* LPMONITORFROMRECT )( LPCRECT lprcScreenCoords, DWORD dwFlags ); + +#pragma warning( suppress : 6101 ) +_Use_decl_annotations_ +BOOL WINAPI DXUTGetMonitorInfo( HMONITOR hMonitor, LPMONITORINFO lpMonitorInfo ) +{ + static bool s_bInited = false; + static LPGETMONITORINFO s_pFnGetMonitorInfo = nullptr; + if( !s_bInited ) + { + s_bInited = true; + HMODULE hUser32 = GetModuleHandle( L"USER32" ); + if( hUser32 ) + { + s_pFnGetMonitorInfo = reinterpret_cast( reinterpret_cast( GetProcAddress( hUser32, "GetMonitorInfoW" ) ) ); + } + } + + if( s_pFnGetMonitorInfo ) + return s_pFnGetMonitorInfo( hMonitor, lpMonitorInfo ); + + RECT rcWork; + if( ( hMonitor == DXUT_PRIMARY_MONITOR ) && lpMonitorInfo && ( lpMonitorInfo->cbSize >= sizeof( MONITORINFO ) ) && + SystemParametersInfoA( SPI_GETWORKAREA, 0, &rcWork, 0 ) ) + { + lpMonitorInfo->rcMonitor.left = 0; + lpMonitorInfo->rcMonitor.top = 0; + lpMonitorInfo->rcMonitor.right = GetSystemMetrics( SM_CXSCREEN ); + lpMonitorInfo->rcMonitor.bottom = GetSystemMetrics( SM_CYSCREEN ); + lpMonitorInfo->rcWork = rcWork; + lpMonitorInfo->dwFlags = MONITORINFOF_PRIMARY; + return TRUE; + } + return FALSE; +} + + +_Use_decl_annotations_ +HMONITOR WINAPI DXUTMonitorFromWindow( HWND hWnd, DWORD dwFlags ) +{ + static bool s_bInited = false; + static LPMONITORFROMWINDOW s_pFnGetMonitorFromWindow = nullptr; + if( !s_bInited ) + { + s_bInited = true; + HMODULE hUser32 = GetModuleHandle( L"USER32" ); + if( hUser32 ) s_pFnGetMonitorFromWindow = reinterpret_cast( reinterpret_cast( GetProcAddress( hUser32, + "MonitorFromWindow" ) ) ); + } + + if( s_pFnGetMonitorFromWindow ) + return s_pFnGetMonitorFromWindow( hWnd, dwFlags ); + else + return DXUT_PRIMARY_MONITOR; +} + + +_Use_decl_annotations_ +HMONITOR WINAPI DXUTMonitorFromRect( LPCRECT lprcScreenCoords, DWORD dwFlags ) +{ + static bool s_bInited = false; + static LPMONITORFROMRECT s_pFnGetMonitorFromRect = nullptr; + if( !s_bInited ) + { + s_bInited = true; + HMODULE hUser32 = GetModuleHandle( L"USER32" ); + if( hUser32 ) s_pFnGetMonitorFromRect = reinterpret_cast( reinterpret_cast( GetProcAddress( hUser32, "MonitorFromRect" ) ) ); + } + + if( s_pFnGetMonitorFromRect ) + return s_pFnGetMonitorFromRect( lprcScreenCoords, dwFlags ); + else + return DXUT_PRIMARY_MONITOR; +} + + +//-------------------------------------------------------------------------------------- +// Get the desktop resolution of an adapter. This isn't the same as the current resolution +// from GetAdapterDisplayMode since the device might be fullscreen +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void WINAPI DXUTGetDesktopResolution( UINT AdapterOrdinal, UINT* pWidth, UINT* pHeight ) +{ + auto DeviceSettings = DXUTGetDeviceSettings(); + + WCHAR strDeviceName[256] = {}; + DEVMODE devMode = {}; + devMode.dmSize = sizeof( DEVMODE ); + + auto pd3dEnum = DXUTGetD3D11Enumeration(); + assert( pd3dEnum ); + _Analysis_assume_( pd3dEnum ); + auto pOutputInfo = pd3dEnum->GetOutputInfo( AdapterOrdinal, DeviceSettings.d3d11.Output ); + if( pOutputInfo ) + { + wcscpy_s( strDeviceName, 256, pOutputInfo->Desc.DeviceName ); + } + + EnumDisplaySettings( strDeviceName, ENUM_REGISTRY_SETTINGS, &devMode ); + + if( pWidth ) + *pWidth = devMode.dmPelsWidth; + if( pHeight ) + *pHeight = devMode.dmPelsHeight; +} + + +//-------------------------------------------------------------------------------------- +// Display error msg box to help debug +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT WINAPI DXUTTrace( const CHAR* strFile, DWORD dwLine, HRESULT hr, + const WCHAR* strMsg, bool bPopMsgBox ) +{ + bool bShowMsgBoxOnError = DXUTGetShowMsgBoxOnError(); + if( bPopMsgBox && bShowMsgBoxOnError == false ) + bPopMsgBox = false; + + WCHAR buff[ MAX_PATH ]; + int result = MultiByteToWideChar( CP_ACP, + MB_PRECOMPOSED, + strFile, + -1, + buff, + MAX_PATH ); + if ( !result ) + { + wcscpy_s( buff, L"*ERROR*" ); + } + + return DXTraceW( buff, dwLine, hr, strMsg, bPopMsgBox ); +} + +typedef DWORD ( WINAPI* LPXINPUTGETSTATE )( DWORD dwUserIndex, XINPUT_STATE* pState ); +typedef DWORD ( WINAPI* LPXINPUTSETSTATE )( DWORD dwUserIndex, XINPUT_VIBRATION* pVibration ); +typedef DWORD ( WINAPI* LPXINPUTGETCAPABILITIES )( DWORD dwUserIndex, DWORD dwFlags, + XINPUT_CAPABILITIES* pCapabilities ); +typedef void ( WINAPI* LPXINPUTENABLE )( BOOL bEnable ); + +//-------------------------------------------------------------------------------------- +// Does extra processing on XInput data to make it slightly more convenient to use +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DXUTGetGamepadState( DWORD dwPort, DXUT_GAMEPAD* pGamePad, bool bThumbstickDeadZone, + bool bSnapThumbstickToCardinals ) +{ + if( dwPort >= DXUT_MAX_CONTROLLERS || !pGamePad ) + return E_FAIL; + + static LPXINPUTGETSTATE s_pXInputGetState = nullptr; + static LPXINPUTGETCAPABILITIES s_pXInputGetCapabilities = nullptr; + if( !s_pXInputGetState || !s_pXInputGetCapabilities ) + { + HINSTANCE hInst = LoadLibraryEx( XINPUT_DLL, nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + if( hInst ) + { + s_pXInputGetState = reinterpret_cast( reinterpret_cast( GetProcAddress( hInst, "XInputGetState" ) ) ); + s_pXInputGetCapabilities = reinterpret_cast( reinterpret_cast( GetProcAddress( hInst, "XInputGetCapabilities" ) ) ); + } + } + if( !s_pXInputGetState ) + return E_FAIL; + + XINPUT_STATE InputState; + DWORD dwResult = s_pXInputGetState( dwPort, &InputState ); + + // Track insertion and removals + BOOL bWasConnected = pGamePad->bConnected; + pGamePad->bConnected = ( dwResult == ERROR_SUCCESS ); + pGamePad->bRemoved = ( bWasConnected && !pGamePad->bConnected ); + pGamePad->bInserted = ( !bWasConnected && pGamePad->bConnected ); + + // Don't update rest of the state if not connected + if( !pGamePad->bConnected ) + return S_OK; + + // Store the capabilities of the device + if( pGamePad->bInserted ) + { + ZeroMemory( pGamePad, sizeof( DXUT_GAMEPAD ) ); + pGamePad->bConnected = true; + pGamePad->bInserted = true; + if( s_pXInputGetCapabilities ) + s_pXInputGetCapabilities( dwPort, XINPUT_DEVTYPE_GAMEPAD, &pGamePad->caps ); + } + + // Copy gamepad to local structure (assumes that XINPUT_GAMEPAD at the front in CONTROLER_STATE) + memcpy( pGamePad, &InputState.Gamepad, sizeof( XINPUT_GAMEPAD ) ); + + if( bSnapThumbstickToCardinals ) + { + // Apply deadzone to each axis independantly to slightly snap to up/down/left/right + if( pGamePad->sThumbLX < XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE && + pGamePad->sThumbLX > -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE ) + pGamePad->sThumbLX = 0; + if( pGamePad->sThumbLY < XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE && + pGamePad->sThumbLY > -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE ) + pGamePad->sThumbLY = 0; + if( pGamePad->sThumbRX < XINPUT_GAMEPAD_RIGHT_THUMB_DEADZONE && + pGamePad->sThumbRX > -XINPUT_GAMEPAD_RIGHT_THUMB_DEADZONE ) + pGamePad->sThumbRX = 0; + if( pGamePad->sThumbRY < XINPUT_GAMEPAD_RIGHT_THUMB_DEADZONE && + pGamePad->sThumbRY > -XINPUT_GAMEPAD_RIGHT_THUMB_DEADZONE ) + pGamePad->sThumbRY = 0; + } + else if( bThumbstickDeadZone ) + { + // Apply deadzone if centered + if( ( pGamePad->sThumbLX < XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE && + pGamePad->sThumbLX > -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE ) && + ( pGamePad->sThumbLY < XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE && + pGamePad->sThumbLY > -XINPUT_GAMEPAD_LEFT_THUMB_DEADZONE ) ) + { + pGamePad->sThumbLX = 0; + pGamePad->sThumbLY = 0; + } + if( ( pGamePad->sThumbRX < XINPUT_GAMEPAD_RIGHT_THUMB_DEADZONE && + pGamePad->sThumbRX > -XINPUT_GAMEPAD_RIGHT_THUMB_DEADZONE ) && + ( pGamePad->sThumbRY < XINPUT_GAMEPAD_RIGHT_THUMB_DEADZONE && + pGamePad->sThumbRY > -XINPUT_GAMEPAD_RIGHT_THUMB_DEADZONE ) ) + { + pGamePad->sThumbRX = 0; + pGamePad->sThumbRY = 0; + } + } + + // Convert [-1,+1] range + pGamePad->fThumbLX = pGamePad->sThumbLX / 32767.0f; + pGamePad->fThumbLY = pGamePad->sThumbLY / 32767.0f; + pGamePad->fThumbRX = pGamePad->sThumbRX / 32767.0f; + pGamePad->fThumbRY = pGamePad->sThumbRY / 32767.0f; + + // Get the boolean buttons that have been pressed since the last call. + // Each button is represented by one bit. + pGamePad->wPressedButtons = ( pGamePad->wLastButtons ^ pGamePad->wButtons ) & pGamePad->wButtons; + pGamePad->wLastButtons = pGamePad->wButtons; + + // Figure out if the left trigger has been pressed or released + bool bPressed = ( pGamePad->bLeftTrigger > DXUT_GAMEPAD_TRIGGER_THRESHOLD ); + pGamePad->bPressedLeftTrigger = ( bPressed ) ? !pGamePad->bLastLeftTrigger : false; + pGamePad->bLastLeftTrigger = bPressed; + + // Figure out if the right trigger has been pressed or released + bPressed = ( pGamePad->bRightTrigger > DXUT_GAMEPAD_TRIGGER_THRESHOLD ); + pGamePad->bPressedRightTrigger = ( bPressed ) ? !pGamePad->bLastRightTrigger : false; + pGamePad->bLastRightTrigger = bPressed; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Don't pause the game or deactive the window without first stopping rumble otherwise +// the controller will continue to rumble +//-------------------------------------------------------------------------------------- +void DXUTEnableXInput( _In_ bool bEnable ) +{ + static LPXINPUTENABLE s_pXInputEnable = nullptr; + if( !s_pXInputEnable ) + { + HINSTANCE hInst = LoadLibraryEx( XINPUT_DLL, nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + if( hInst ) + s_pXInputEnable = reinterpret_cast( reinterpret_cast( GetProcAddress( hInst, "XInputEnable" ) ) ); + } + + if( s_pXInputEnable ) + s_pXInputEnable( bEnable ); +} + + +//-------------------------------------------------------------------------------------- +// Don't pause the game or deactive the window without first stopping rumble otherwise +// the controller will continue to rumble +//-------------------------------------------------------------------------------------- +HRESULT DXUTStopRumbleOnAllControllers() +{ + static LPXINPUTSETSTATE s_pXInputSetState = nullptr; + if( !s_pXInputSetState ) + { + HINSTANCE hInst = LoadLibraryEx( XINPUT_DLL, nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + if( hInst ) + s_pXInputSetState = reinterpret_cast( reinterpret_cast( GetProcAddress( hInst, "XInputSetState" ) ) ); + } + if( !s_pXInputSetState ) + return E_FAIL; + + XINPUT_VIBRATION vibration; + vibration.wLeftMotorSpeed = 0; + vibration.wRightMotorSpeed = 0; + for( int iUserIndex = 0; iUserIndex < DXUT_MAX_CONTROLLERS; iUserIndex++ ) + s_pXInputSetState( iUserIndex, &vibration ); + + return S_OK; +} + +//-------------------------------------------------------------------------------------- +// Helper functions to create SRGB formats from typeless formats and vice versa +//-------------------------------------------------------------------------------------- +DXGI_FORMAT MAKE_SRGB( _In_ DXGI_FORMAT format ) +{ + if( !DXUTIsInGammaCorrectMode() ) + return format; + + switch( format ) + { + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + }; + + return format; +} + +//-------------------------------------------------------------------------------------- +DXGI_FORMAT MAKE_TYPELESS( _In_ DXGI_FORMAT format ) +{ + switch( format ) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return DXGI_FORMAT_R32G32B32A32_TYPELESS; + + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return DXGI_FORMAT_R32G32B32_TYPELESS; + + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + return DXGI_FORMAT_R16G16B16A16_TYPELESS; + + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + return DXGI_FORMAT_R32G32_TYPELESS; + + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + return DXGI_FORMAT_R10G10B10A2_TYPELESS; + + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + return DXGI_FORMAT_R8G8B8A8_TYPELESS; + + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + return DXGI_FORMAT_R16G16_TYPELESS; + + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + return DXGI_FORMAT_R32_TYPELESS; + + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + return DXGI_FORMAT_R8G8_TYPELESS; + + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + return DXGI_FORMAT_R16_TYPELESS; + + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + return DXGI_FORMAT_R8_TYPELESS; + + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + return DXGI_FORMAT_BC1_TYPELESS; + + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + return DXGI_FORMAT_BC2_TYPELESS; + + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + return DXGI_FORMAT_BC3_TYPELESS; + + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return DXGI_FORMAT_BC4_TYPELESS; + + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + return DXGI_FORMAT_BC5_TYPELESS; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + return DXGI_FORMAT_B8G8R8A8_TYPELESS; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + return DXGI_FORMAT_B8G8R8X8_TYPELESS; + + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + return DXGI_FORMAT_BC6H_TYPELESS; + + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return DXGI_FORMAT_BC7_TYPELESS; + + default: + return format; + } +} + +//-------------------------------------------------------------------------------------- +HRESULT DXUTSnapD3D11Screenshot( _In_z_ LPCWSTR szFileName, _In_ bool usedds ) +{ + IDXGISwapChain *pSwap = DXUTGetDXGISwapChain(); + + if (!pSwap) + return E_FAIL; + + ID3D11Texture2D* pBackBuffer; + HRESULT hr = pSwap->GetBuffer( 0, __uuidof( *pBackBuffer ), ( LPVOID* )&pBackBuffer ); + if (hr != S_OK) + return hr; + + auto dc = DXUTGetD3D11DeviceContext(); + if (!dc) { + SAFE_RELEASE(pBackBuffer); + return E_FAIL; + } + + if ( usedds ) + { + hr = DirectX::SaveDDSTextureToFile( dc, pBackBuffer, szFileName ); + } + else + { + hr = DirectX::SaveWICTextureToFile( dc, pBackBuffer, GUID_ContainerFormatBmp, szFileName ); + } + + SAFE_RELEASE(pBackBuffer); + + return hr; + +} diff --git a/src/DX11/framework/dxut/Core/DXUTmisc.h b/src/DX11/framework/dxut/Core/DXUTmisc.h new file mode 100644 index 0000000..72d76dd --- /dev/null +++ b/src/DX11/framework/dxut/Core/DXUTmisc.h @@ -0,0 +1,293 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTMisc.h +// +// Helper functions for Direct3D programming. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +//-------------------------------------------------------------------------------------- +// XInput helper state/function +// This performs extra processing on XInput gamepad data to make it slightly more convenient to use +// +// Example usage: +// +// DXUT_GAMEPAD gamepad[4]; +// for( DWORD iPort=0; iPortSetPrivateData( WKPDID_D3DDebugObjectName, (UINT)strlen(pstrName), pstrName ); +} +inline void DXUT_SetDebugName( _In_ ID3D11Device* pObj, _In_z_ const CHAR* pstrName ) +{ + if ( pObj ) + pObj->SetPrivateData( WKPDID_D3DDebugObjectName, (UINT)strlen(pstrName), pstrName ); +} +inline void DXUT_SetDebugName( _In_ ID3D11DeviceChild* pObj, _In_z_ const CHAR* pstrName ) +{ + if ( pObj ) + pObj->SetPrivateData( WKPDID_D3DDebugObjectName, (UINT)strlen(pstrName), pstrName ); +} +#else +#define DXUT_SetDebugName( pObj, pstrName ) +#endif + + +//-------------------------------------------------------------------------------------- +// Some D3DPERF APIs take a color that can be used when displaying user events in +// performance analysis tools. The following constants are provided for your +// convenience, but you can use any colors you like. +//-------------------------------------------------------------------------------------- +const DWORD DXUT_PERFEVENTCOLOR = 0xFFC86464; +const DWORD DXUT_PERFEVENTCOLOR2 = 0xFF64C864; +const DWORD DXUT_PERFEVENTCOLOR3 = 0xFF6464C8; + +//-------------------------------------------------------------------------------------- +// The following macros provide a convenient way for your code to call the D3DPERF +// functions only when PROFILE is defined. If PROFILE is not defined (as for the final +// release version of a program), these macros evaluate to nothing, so no detailed event +// information is embedded in your shipping program. It is recommended that you create +// and use three build configurations for your projects: +// Debug (nonoptimized code, asserts active, PROFILE defined to assist debugging) +// Profile (optimized code, asserts disabled, PROFILE defined to assist optimization) +// Release (optimized code, asserts disabled, PROFILE not defined) +//-------------------------------------------------------------------------------------- +#ifdef PROFILE +// PROFILE is defined, so these macros call the D3DPERF functions +#define DXUT_BeginPerfEvent( color, pstrMessage ) DXUT_Dynamic_D3DPERF_BeginEvent( color, pstrMessage ) +#define DXUT_EndPerfEvent() DXUT_Dynamic_D3DPERF_EndEvent() +#define DXUT_SetPerfMarker( color, pstrMessage ) DXUT_Dynamic_D3DPERF_SetMarker( color, pstrMessage ) +#else +// PROFILE is not defined, so these macros do nothing +#define DXUT_BeginPerfEvent( color, pstrMessage ) (__noop) +#define DXUT_EndPerfEvent() (__noop) +#define DXUT_SetPerfMarker( color, pstrMessage ) (__noop) +#endif + +//-------------------------------------------------------------------------------------- +// CDXUTPerfEventGenerator is a helper class that makes it easy to attach begin and end +// events to a block of code. Simply define a CDXUTPerfEventGenerator variable anywhere +// in a block of code, and the class's constructor will call DXUT_BeginPerfEvent when +// the block of code begins, and the class's destructor will call DXUT_EndPerfEvent when +// the block ends. +//-------------------------------------------------------------------------------------- +class CDXUTPerfEventGenerator +{ +public: +CDXUTPerfEventGenerator( _In_ DWORD color, _In_z_ LPCWSTR pstrMessage ) +{ +#ifdef PROFILE + DXUT_BeginPerfEvent( color, pstrMessage ); +#else + UNREFERENCED_PARAMETER(color); + UNREFERENCED_PARAMETER(pstrMessage); +#endif +} +~CDXUTPerfEventGenerator() +{ + DXUT_EndPerfEvent(); +} +}; + + +//-------------------------------------------------------------------------------------- +// Multimon handling to support OSes with or without multimon API support. +// Purposely avoiding the use of multimon.h so DXUT.lib doesn't require +// COMPILE_MULTIMON_STUBS and cause complication with MFC or other users of multimon.h +//-------------------------------------------------------------------------------------- +#ifndef MONITOR_DEFAULTTOPRIMARY +#define MONITORINFOF_PRIMARY 0x00000001 +#define MONITOR_DEFAULTTONULL 0x00000000 +#define MONITOR_DEFAULTTOPRIMARY 0x00000001 +#define MONITOR_DEFAULTTONEAREST 0x00000002 +typedef struct tagMONITORINFO +{ + DWORD cbSize; + RECT rcMonitor; + RECT rcWork; + DWORD dwFlags; +} MONITORINFO, *LPMONITORINFO; +typedef struct tagMONITORINFOEXW : public tagMONITORINFO +{ + WCHAR szDevice[CCHDEVICENAME]; +} MONITORINFOEXW, *LPMONITORINFOEXW; +typedef MONITORINFOEXW MONITORINFOEX; +typedef LPMONITORINFOEXW LPMONITORINFOEX; +#endif + +HMONITOR WINAPI DXUTMonitorFromWindow( _In_ HWND hWnd, _In_ DWORD dwFlags ); +HMONITOR WINAPI DXUTMonitorFromRect( _In_ LPCRECT lprcScreenCoords, _In_ DWORD dwFlags ); +BOOL WINAPI DXUTGetMonitorInfo( _In_ HMONITOR hMonitor, _Out_ LPMONITORINFO lpMonitorInfo ); +void WINAPI DXUTGetDesktopResolution( _In_ UINT AdapterOrdinal, _Out_ UINT* pWidth, _Out_ UINT* pHeight ); + + +//-------------------------------------------------------------------------------------- +// Helper functions to create SRGB formats from typeless formats and vice versa +//-------------------------------------------------------------------------------------- +DXGI_FORMAT MAKE_SRGB( _In_ DXGI_FORMAT format ); +DXGI_FORMAT MAKE_TYPELESS( _In_ DXGI_FORMAT format ); diff --git a/src/DX11/framework/dxut/Core/ScreenGrab.cpp b/src/DX11/framework/dxut/Core/ScreenGrab.cpp new file mode 100644 index 0000000..b18d91e --- /dev/null +++ b/src/DX11/framework/dxut/Core/ScreenGrab.cpp @@ -0,0 +1,1251 @@ +//-------------------------------------------------------------------------------------- +// File: ScreenGrab.cpp +// +// Function for capturing a 2D texture and saving it to a file (aka a 'screenshot' +// when used on a Direct3D Render Target). +// +// Note these functions are useful as a light-weight runtime screen grabber. For +// full-featured texture capture, DDS writer, and texture processing pipeline, +// see the 'Texconv' sample and the 'DirectXTex' library. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#include "dxut.h" + +// Does not capture 1D textures or 3D textures (volume maps) + +// Does not capture mipmap chains, only the top-most texture level is saved + +// For 2D array textures and cubemaps, it captures only the first image in the array + +#include "ScreenGrab.h" + +#include +#include +#include +#include +#include +#include + +#include + +#include + +#ifdef __clang__ +#pragma clang diagnostic ignored "-Wcovered-switch-default" +#pragma clang diagnostic ignored "-Wswitch-enum" +#endif + +using Microsoft::WRL::ComPtr; + +//-------------------------------------------------------------------------------------- +// Macros +//-------------------------------------------------------------------------------------- +#ifndef MAKEFOURCC + #define MAKEFOURCC(ch0, ch1, ch2, ch3) \ + ((uint32_t)(uint8_t)(ch0) | ((uint32_t)(uint8_t)(ch1) << 8) | \ + ((uint32_t)(uint8_t)(ch2) << 16) | ((uint32_t)(uint8_t)(ch3) << 24 )) +#endif /* defined(MAKEFOURCC) */ + +//-------------------------------------------------------------------------------------- +// DDS file structure definitions +// +// See DDS.h in the 'Texconv' sample and the 'DirectXTex' library +//-------------------------------------------------------------------------------------- +namespace +{ + #pragma pack(push,1) + + #define DDS_MAGIC 0x20534444 // "DDS " + + struct DDS_PIXELFORMAT + { + uint32_t size; + uint32_t flags; + uint32_t fourCC; + uint32_t RGBBitCount; + uint32_t RBitMask; + uint32_t GBitMask; + uint32_t BBitMask; + uint32_t ABitMask; + }; + + #define DDS_FOURCC 0x00000004 // DDPF_FOURCC + #define DDS_RGB 0x00000040 // DDPF_RGB + #define DDS_RGBA 0x00000041 // DDPF_RGB | DDPF_ALPHAPIXELS + #define DDS_LUMINANCE 0x00020000 // DDPF_LUMINANCE + #define DDS_LUMINANCEA 0x00020001 // DDPF_LUMINANCE | DDPF_ALPHAPIXELS + #define DDS_ALPHA 0x00000002 // DDPF_ALPHA + #define DDS_BUMPDUDV 0x00080000 // DDPF_BUMPDUDV + + #define DDS_HEADER_FLAGS_TEXTURE 0x00001007 // DDSD_CAPS | DDSD_HEIGHT | DDSD_WIDTH | DDSD_PIXELFORMAT + #define DDS_HEADER_FLAGS_MIPMAP 0x00020000 // DDSD_MIPMAPCOUNT + #define DDS_HEADER_FLAGS_PITCH 0x00000008 // DDSD_PITCH + #define DDS_HEADER_FLAGS_LINEARSIZE 0x00080000 // DDSD_LINEARSIZE + + #define DDS_SURFACE_FLAGS_TEXTURE 0x00001000 // DDSCAPS_TEXTURE + + struct DDS_HEADER + { + uint32_t size; + uint32_t flags; + uint32_t height; + uint32_t width; + uint32_t pitchOrLinearSize; + uint32_t depth; // only if DDS_HEADER_FLAGS_VOLUME is set in flags + uint32_t mipMapCount; + uint32_t reserved1[11]; + DDS_PIXELFORMAT ddspf; + uint32_t caps; + uint32_t caps2; + uint32_t caps3; + uint32_t caps4; + uint32_t reserved2; + }; + + struct DDS_HEADER_DXT10 + { + DXGI_FORMAT dxgiFormat; + uint32_t resourceDimension; + uint32_t miscFlag; // see D3D11_RESOURCE_MISC_FLAG + uint32_t arraySize; + uint32_t reserved; + }; + + #pragma pack(pop) + + const DDS_PIXELFORMAT DDSPF_DXT1 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','1'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_DXT3 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','3'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_DXT5 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','T','5'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC4_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','U'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC4_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','4','S'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC5_UNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','U'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_BC5_SNORM = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('B','C','5','S'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_R8G8_B8G8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('R','G','B','G'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_G8R8_G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('G','R','G','B'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_YUY2 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('Y','U','Y','2'), 0, 0, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_A8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_X8R8G8B8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x00ff0000, 0x0000ff00, 0x000000ff, 0 }; + + const DDS_PIXELFORMAT DDSPF_A8B8G8R8 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_G16R16 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 32, 0x0000ffff, 0xffff0000, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_R5G6B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGB, 0, 16, 0xf800, 0x07e0, 0x001f, 0 }; + + const DDS_PIXELFORMAT DDSPF_A1R5G5B5 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x7c00, 0x03e0, 0x001f, 0x8000 }; + + const DDS_PIXELFORMAT DDSPF_A4R4G4B4 = + { sizeof(DDS_PIXELFORMAT), DDS_RGBA, 0, 16, 0x0f00, 0x00f0, 0x000f, 0xf000 }; + + const DDS_PIXELFORMAT DDSPF_L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 8, 0xff, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_L16 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCE, 0, 16, 0xffff, 0, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_A8L8 = + { sizeof(DDS_PIXELFORMAT), DDS_LUMINANCEA, 0, 16, 0x00ff, 0, 0, 0xff00 }; + + const DDS_PIXELFORMAT DDSPF_A8 = + { sizeof(DDS_PIXELFORMAT), DDS_ALPHA, 0, 8, 0, 0, 0, 0xff }; + + const DDS_PIXELFORMAT DDSPF_V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 16, 0x00ff, 0xff00, 0, 0 }; + + const DDS_PIXELFORMAT DDSPF_Q8W8V8U8 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x000000ff, 0x0000ff00, 0x00ff0000, 0xff000000 }; + + const DDS_PIXELFORMAT DDSPF_V16U16 = + { sizeof(DDS_PIXELFORMAT), DDS_BUMPDUDV, 0, 32, 0x0000ffff, 0xffff0000, 0, 0 }; + + // DXGI_FORMAT_R10G10B10A2_UNORM should be written using DX10 extension to avoid D3DX 10:10:10:2 reversal issue + + // This indicates the DDS_HEADER_DXT10 extension is present (the format is in dxgiFormat) + const DDS_PIXELFORMAT DDSPF_DX10 = + { sizeof(DDS_PIXELFORMAT), DDS_FOURCC, MAKEFOURCC('D','X','1','0'), 0, 0, 0, 0, 0 }; + + //----------------------------------------------------------------------------- + struct handle_closer { void operator()(HANDLE h) noexcept { if (h) CloseHandle(h); } }; + + using ScopedHandle = std::unique_ptr; + + inline HANDLE safe_handle(HANDLE h) noexcept { return (h == INVALID_HANDLE_VALUE) ? nullptr : h; } + + class auto_delete_file + { + public: + auto_delete_file(HANDLE hFile) noexcept : m_handle(hFile) {} + ~auto_delete_file() + { + if (m_handle) + { + FILE_DISPOSITION_INFO info = {}; + info.DeleteFile = TRUE; + (void)SetFileInformationByHandle(m_handle, FileDispositionInfo, &info, sizeof(info)); + } + } + + auto_delete_file(const auto_delete_file&) = delete; + auto_delete_file& operator=(const auto_delete_file&) = delete; + + auto_delete_file(const auto_delete_file&&) = delete; + auto_delete_file& operator=(const auto_delete_file&&) = delete; + + void clear() noexcept { m_handle = nullptr; } + + private: + HANDLE m_handle; + }; + + class auto_delete_file_wic + { + public: + auto_delete_file_wic(ComPtr& hFile, const wchar_t* szFile) noexcept : m_filename(szFile), m_handle(hFile) {} + ~auto_delete_file_wic() + { + if (m_filename) + { + m_handle.Reset(); + DeleteFileW(m_filename); + } + } + + auto_delete_file_wic(const auto_delete_file_wic&) = delete; + auto_delete_file_wic& operator=(const auto_delete_file_wic&) = delete; + + auto_delete_file_wic(const auto_delete_file_wic&&) = delete; + auto_delete_file_wic& operator=(const auto_delete_file_wic&&) = delete; + + void clear() noexcept { m_filename = nullptr; } + + private: + const wchar_t* m_filename; + ComPtr& m_handle; + }; + + //-------------------------------------------------------------------------------------- + // Return the BPP for a particular format + //-------------------------------------------------------------------------------------- + size_t BitsPerPixel(_In_ DXGI_FORMAT fmt) noexcept + { + switch (fmt) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R32G32B32A32_UINT: + case DXGI_FORMAT_R32G32B32A32_SINT: + return 128; + + case DXGI_FORMAT_R32G32B32_TYPELESS: + case DXGI_FORMAT_R32G32B32_FLOAT: + case DXGI_FORMAT_R32G32B32_UINT: + case DXGI_FORMAT_R32G32B32_SINT: + return 96; + + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + case DXGI_FORMAT_R16G16B16A16_UNORM: + case DXGI_FORMAT_R16G16B16A16_UINT: + case DXGI_FORMAT_R16G16B16A16_SNORM: + case DXGI_FORMAT_R16G16B16A16_SINT: + case DXGI_FORMAT_R32G32_TYPELESS: + case DXGI_FORMAT_R32G32_FLOAT: + case DXGI_FORMAT_R32G32_UINT: + case DXGI_FORMAT_R32G32_SINT: + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + case DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS: + case DXGI_FORMAT_X32_TYPELESS_G8X24_UINT: + case DXGI_FORMAT_Y416: + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + return 64; + + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + case DXGI_FORMAT_R10G10B10A2_UNORM: + case DXGI_FORMAT_R10G10B10A2_UINT: + case DXGI_FORMAT_R11G11B10_FLOAT: + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + case DXGI_FORMAT_R8G8B8A8_UNORM: + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + case DXGI_FORMAT_R8G8B8A8_UINT: + case DXGI_FORMAT_R8G8B8A8_SNORM: + case DXGI_FORMAT_R8G8B8A8_SINT: + case DXGI_FORMAT_R16G16_TYPELESS: + case DXGI_FORMAT_R16G16_FLOAT: + case DXGI_FORMAT_R16G16_UNORM: + case DXGI_FORMAT_R16G16_UINT: + case DXGI_FORMAT_R16G16_SNORM: + case DXGI_FORMAT_R16G16_SINT: + case DXGI_FORMAT_R32_TYPELESS: + case DXGI_FORMAT_D32_FLOAT: + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R32_UINT: + case DXGI_FORMAT_R32_SINT: + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + case DXGI_FORMAT_R24_UNORM_X8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_R9G9B9E5_SHAREDEXP: + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_B8G8R8A8_UNORM: + case DXGI_FORMAT_B8G8R8X8_UNORM: + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: + case DXGI_FORMAT_AYUV: + case DXGI_FORMAT_Y410: + case DXGI_FORMAT_YUY2: + return 32; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + return 24; + + case DXGI_FORMAT_R8G8_TYPELESS: + case DXGI_FORMAT_R8G8_UNORM: + case DXGI_FORMAT_R8G8_UINT: + case DXGI_FORMAT_R8G8_SNORM: + case DXGI_FORMAT_R8G8_SINT: + case DXGI_FORMAT_R16_TYPELESS: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_D16_UNORM: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R16_UINT: + case DXGI_FORMAT_R16_SNORM: + case DXGI_FORMAT_R16_SINT: + case DXGI_FORMAT_B5G6R5_UNORM: + case DXGI_FORMAT_B5G5R5A1_UNORM: + case DXGI_FORMAT_A8P8: + case DXGI_FORMAT_B4G4R4A4_UNORM: + return 16; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + case DXGI_FORMAT_NV11: + return 12; + + case DXGI_FORMAT_R8_TYPELESS: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_R8_UINT: + case DXGI_FORMAT_R8_SNORM: + case DXGI_FORMAT_R8_SINT: + case DXGI_FORMAT_A8_UNORM: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + return 8; + + case DXGI_FORMAT_R1_UNORM: + return 1; + + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + return 4; + + default: + return 0; + } + } + + + //-------------------------------------------------------------------------------------- + // Determines if the format is block compressed + //-------------------------------------------------------------------------------------- + bool IsCompressed(_In_ DXGI_FORMAT fmt) noexcept + { + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + return true; + + default: + return false; + } + } + + + //-------------------------------------------------------------------------------------- + // Get surface information for a particular format + //-------------------------------------------------------------------------------------- + HRESULT GetSurfaceInfo( + _In_ size_t width, + _In_ size_t height, + _In_ DXGI_FORMAT fmt, + _Out_opt_ size_t* outNumBytes, + _Out_opt_ size_t* outRowBytes, + _Out_opt_ size_t* outNumRows) noexcept + { + uint64_t numBytes = 0; + uint64_t rowBytes = 0; + uint64_t numRows = 0; + + bool bc = false; + bool packed = false; + bool planar = false; + size_t bpe = 0; + switch (fmt) + { + case DXGI_FORMAT_BC1_TYPELESS: + case DXGI_FORMAT_BC1_UNORM: + case DXGI_FORMAT_BC1_UNORM_SRGB: + case DXGI_FORMAT_BC4_TYPELESS: + case DXGI_FORMAT_BC4_UNORM: + case DXGI_FORMAT_BC4_SNORM: + bc = true; + bpe = 8; + break; + + case DXGI_FORMAT_BC2_TYPELESS: + case DXGI_FORMAT_BC2_UNORM: + case DXGI_FORMAT_BC2_UNORM_SRGB: + case DXGI_FORMAT_BC3_TYPELESS: + case DXGI_FORMAT_BC3_UNORM: + case DXGI_FORMAT_BC3_UNORM_SRGB: + case DXGI_FORMAT_BC5_TYPELESS: + case DXGI_FORMAT_BC5_UNORM: + case DXGI_FORMAT_BC5_SNORM: + case DXGI_FORMAT_BC6H_TYPELESS: + case DXGI_FORMAT_BC6H_UF16: + case DXGI_FORMAT_BC6H_SF16: + case DXGI_FORMAT_BC7_TYPELESS: + case DXGI_FORMAT_BC7_UNORM: + case DXGI_FORMAT_BC7_UNORM_SRGB: + bc = true; + bpe = 16; + break; + + case DXGI_FORMAT_R8G8_B8G8_UNORM: + case DXGI_FORMAT_G8R8_G8B8_UNORM: + case DXGI_FORMAT_YUY2: + packed = true; + bpe = 4; + break; + + case DXGI_FORMAT_Y210: + case DXGI_FORMAT_Y216: + packed = true; + bpe = 8; + break; + + case DXGI_FORMAT_NV12: + case DXGI_FORMAT_420_OPAQUE: + planar = true; + bpe = 2; + break; + + case DXGI_FORMAT_P010: + case DXGI_FORMAT_P016: + planar = true; + bpe = 4; + break; + + default: + break; + } + + if (bc) + { + uint64_t numBlocksWide = 0; + if (width > 0) + { + numBlocksWide = std::max(1u, (uint64_t(width) + 3u) / 4u); + } + uint64_t numBlocksHigh = 0; + if (height > 0) + { + numBlocksHigh = std::max(1u, (uint64_t(height) + 3u) / 4u); + } + rowBytes = numBlocksWide * bpe; + numRows = numBlocksHigh; + numBytes = rowBytes * numBlocksHigh; + } + else if (packed) + { + rowBytes = ((uint64_t(width) + 1u) >> 1) * bpe; + numRows = uint64_t(height); + numBytes = rowBytes * height; + } + else if (fmt == DXGI_FORMAT_NV11) + { + rowBytes = ((uint64_t(width) + 3u) >> 2) * 4u; + numRows = uint64_t(height) * 2u; // Direct3D makes this simplifying assumption, although it is larger than the 4:1:1 data + numBytes = rowBytes * numRows; + } + else if (planar) + { + rowBytes = ((uint64_t(width) + 1u) >> 1) * bpe; + numBytes = (rowBytes * uint64_t(height)) + ((rowBytes * uint64_t(height) + 1u) >> 1); + numRows = height + ((uint64_t(height) + 1u) >> 1); + } + else + { + size_t bpp = BitsPerPixel(fmt); + if (!bpp) + return E_INVALIDARG; + + rowBytes = (uint64_t(width) * bpp + 7u) / 8u; // round up to nearest byte + numRows = uint64_t(height); + numBytes = rowBytes * height; + } + +#if defined(_M_IX86) || defined(_M_ARM) || defined(_M_HYBRID_X86_ARM64) + static_assert(sizeof(size_t) == 4, "Not a 32-bit platform!"); + if (numBytes > UINT32_MAX || rowBytes > UINT32_MAX || numRows > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW); +#else + static_assert(sizeof(size_t) == 8, "Not a 64-bit platform!"); +#endif + + if (outNumBytes) + { + *outNumBytes = static_cast(numBytes); + } + if (outRowBytes) + { + *outRowBytes = static_cast(rowBytes); + } + if (outNumRows) + { + *outNumRows = static_cast(numRows); + } + + return S_OK; + } + + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT EnsureNotTypeless(DXGI_FORMAT fmt) noexcept + { + // Assumes UNORM or FLOAT; doesn't use UINT or SINT + switch (fmt) + { + case DXGI_FORMAT_R32G32B32A32_TYPELESS: return DXGI_FORMAT_R32G32B32A32_FLOAT; + case DXGI_FORMAT_R32G32B32_TYPELESS: return DXGI_FORMAT_R32G32B32_FLOAT; + case DXGI_FORMAT_R16G16B16A16_TYPELESS: return DXGI_FORMAT_R16G16B16A16_UNORM; + case DXGI_FORMAT_R32G32_TYPELESS: return DXGI_FORMAT_R32G32_FLOAT; + case DXGI_FORMAT_R10G10B10A2_TYPELESS: return DXGI_FORMAT_R10G10B10A2_UNORM; + case DXGI_FORMAT_R8G8B8A8_TYPELESS: return DXGI_FORMAT_R8G8B8A8_UNORM; + case DXGI_FORMAT_R16G16_TYPELESS: return DXGI_FORMAT_R16G16_UNORM; + case DXGI_FORMAT_R32_TYPELESS: return DXGI_FORMAT_R32_FLOAT; + case DXGI_FORMAT_R8G8_TYPELESS: return DXGI_FORMAT_R8G8_UNORM; + case DXGI_FORMAT_R16_TYPELESS: return DXGI_FORMAT_R16_UNORM; + case DXGI_FORMAT_R8_TYPELESS: return DXGI_FORMAT_R8_UNORM; + case DXGI_FORMAT_BC1_TYPELESS: return DXGI_FORMAT_BC1_UNORM; + case DXGI_FORMAT_BC2_TYPELESS: return DXGI_FORMAT_BC2_UNORM; + case DXGI_FORMAT_BC3_TYPELESS: return DXGI_FORMAT_BC3_UNORM; + case DXGI_FORMAT_BC4_TYPELESS: return DXGI_FORMAT_BC4_UNORM; + case DXGI_FORMAT_BC5_TYPELESS: return DXGI_FORMAT_BC5_UNORM; + case DXGI_FORMAT_B8G8R8A8_TYPELESS: return DXGI_FORMAT_B8G8R8A8_UNORM; + case DXGI_FORMAT_B8G8R8X8_TYPELESS: return DXGI_FORMAT_B8G8R8X8_UNORM; + case DXGI_FORMAT_BC7_TYPELESS: return DXGI_FORMAT_BC7_UNORM; + default: return fmt; + } + } + + + //-------------------------------------------------------------------------------------- + HRESULT CaptureTexture( + _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + D3D11_TEXTURE2D_DESC& desc, + ComPtr& pStaging) noexcept + { + if (!pContext || !pSource) + return E_INVALIDARG; + + D3D11_RESOURCE_DIMENSION resType = D3D11_RESOURCE_DIMENSION_UNKNOWN; + pSource->GetType(&resType); + + if (resType != D3D11_RESOURCE_DIMENSION_TEXTURE2D) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + ComPtr pTexture; + HRESULT hr = pSource->QueryInterface(IID_ID3D11Texture2D, reinterpret_cast(pTexture.GetAddressOf())); + if (FAILED(hr)) + return hr; + + assert(pTexture); + + pTexture->GetDesc(&desc); + + ComPtr d3dDevice; + pContext->GetDevice(d3dDevice.GetAddressOf()); + + if (desc.SampleDesc.Count > 1) + { + // MSAA content must be resolved before being copied to a staging texture + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + + ComPtr pTemp; + hr = d3dDevice->CreateTexture2D(&desc, nullptr, pTemp.GetAddressOf()); + if (FAILED(hr)) + return hr; + + assert(pTemp); + + DXGI_FORMAT fmt = EnsureNotTypeless(desc.Format); + + UINT support = 0; + hr = d3dDevice->CheckFormatSupport(fmt, &support); + if (FAILED(hr)) + return hr; + + if (!(support & D3D11_FORMAT_SUPPORT_MULTISAMPLE_RESOLVE)) + return E_FAIL; + + for (UINT item = 0; item < desc.ArraySize; ++item) + { + for (UINT level = 0; level < desc.MipLevels; ++level) + { + UINT index = D3D11CalcSubresource(level, item, desc.MipLevels); + pContext->ResolveSubresource(pTemp.Get(), index, pSource, index, fmt); + } + } + + desc.BindFlags = 0; + desc.MiscFlags &= D3D11_RESOURCE_MISC_TEXTURECUBE; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = d3dDevice->CreateTexture2D(&desc, nullptr, pStaging.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + assert(pStaging); + + pContext->CopyResource(pStaging.Get(), pTemp.Get()); + } + else if ((desc.Usage == D3D11_USAGE_STAGING) && (desc.CPUAccessFlags & D3D11_CPU_ACCESS_READ)) + { + // Handle case where the source is already a staging texture we can use directly + pStaging = pTexture; + } + else + { + // Otherwise, create a staging texture from the non-MSAA source + desc.BindFlags = 0; + desc.MiscFlags &= D3D11_RESOURCE_MISC_TEXTURECUBE; + desc.CPUAccessFlags = D3D11_CPU_ACCESS_READ; + desc.Usage = D3D11_USAGE_STAGING; + + hr = d3dDevice->CreateTexture2D(&desc, nullptr, pStaging.ReleaseAndGetAddressOf()); + if (FAILED(hr)) + return hr; + + assert(pStaging); + + pContext->CopyResource(pStaging.Get(), pSource); + } + + return S_OK; + } + + //-------------------------------------------------------------------------------------- + bool g_WIC2 = false; + + BOOL WINAPI InitializeWICFactory(PINIT_ONCE, PVOID, PVOID* ifactory) noexcept + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + HRESULT hr = CoCreateInstance( + CLSID_WICImagingFactory2, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory2), + ifactory + ); + + if (SUCCEEDED(hr)) + { + // WIC2 is available on Windows 10, Windows 8.x, and Windows 7 SP1 with KB 2670838 installed + g_WIC2 = true; + return TRUE; + } + else + { + hr = CoCreateInstance( + CLSID_WICImagingFactory1, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + ifactory + ); + return SUCCEEDED(hr) ? TRUE : FALSE; + } +#else + return SUCCEEDED(CoCreateInstance( + CLSID_WICImagingFactory, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + ifactory)) ? TRUE : FALSE; +#endif + } + + IWICImagingFactory* _GetWIC() noexcept + { + static INIT_ONCE s_initOnce = INIT_ONCE_STATIC_INIT; + + IWICImagingFactory* factory = nullptr; + if (!InitOnceExecuteOnce(&s_initOnce, + InitializeWICFactory, + nullptr, + reinterpret_cast(&factory))) + { + return nullptr; + } + + return factory; + } +} // anonymous namespace + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveDDSTextureToFile( + ID3D11DeviceContext* pContext, + ID3D11Resource* pSource, + const wchar_t* fileName) noexcept +{ + if (!fileName) + return E_INVALIDARG; + + D3D11_TEXTURE2D_DESC desc = {}; + ComPtr pStaging; + HRESULT hr = CaptureTexture(pContext, pSource, desc, pStaging); + if (FAILED(hr)) + return hr; + + // Create file +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) + ScopedHandle hFile(safe_handle(CreateFile2(fileName, + GENERIC_WRITE | DELETE, 0, CREATE_ALWAYS, nullptr))); +#else + ScopedHandle hFile(safe_handle(CreateFileW(fileName, + GENERIC_WRITE | DELETE, 0, nullptr, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, nullptr))); +#endif + if (!hFile) + return HRESULT_FROM_WIN32(GetLastError()); + + auto_delete_file delonfail(hFile.get()); + + // Setup header + const size_t MAX_HEADER_SIZE = sizeof(uint32_t) + sizeof(DDS_HEADER) + sizeof(DDS_HEADER_DXT10); + uint8_t fileHeader[MAX_HEADER_SIZE] = {}; + + *reinterpret_cast(&fileHeader[0]) = DDS_MAGIC; + + auto header = reinterpret_cast(&fileHeader[0] + sizeof(uint32_t)); + size_t headerSize = sizeof(uint32_t) + sizeof(DDS_HEADER); + header->size = sizeof(DDS_HEADER); + header->flags = DDS_HEADER_FLAGS_TEXTURE | DDS_HEADER_FLAGS_MIPMAP; + header->height = desc.Height; + header->width = desc.Width; + header->mipMapCount = 1; + header->caps = DDS_SURFACE_FLAGS_TEXTURE; + + // Try to use a legacy .DDS pixel format for better tools support, otherwise fallback to 'DX10' header extension + DDS_HEADER_DXT10* extHeader = nullptr; + switch (desc.Format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_A8B8G8R8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R16G16_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_G16R16, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8G8_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_A8L8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R16_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_L16, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_L8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_A8_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_A8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8G8_B8G8_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_R8G8_B8G8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_G8R8_G8B8_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_G8R8_G8B8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC1_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_DXT1, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC2_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_DXT3, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC3_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_DXT5, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC4_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_BC4_UNORM, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC4_SNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_BC4_SNORM, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC5_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_BC5_UNORM, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_BC5_SNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_BC5_SNORM, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_B5G6R5_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_R5G6B5, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_B5G5R5A1_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_A1R5G5B5, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8G8_SNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_V8U8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R8G8B8A8_SNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_Q8W8V8U8, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_R16G16_SNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_V16U16, sizeof(DDS_PIXELFORMAT)); break; + case DXGI_FORMAT_B8G8R8A8_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_A8R8G8B8, sizeof(DDS_PIXELFORMAT)); break; // DXGI 1.1 + case DXGI_FORMAT_B8G8R8X8_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_X8R8G8B8, sizeof(DDS_PIXELFORMAT)); break; // DXGI 1.1 + case DXGI_FORMAT_YUY2: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_YUY2, sizeof(DDS_PIXELFORMAT)); break; // DXGI 1.2 + case DXGI_FORMAT_B4G4R4A4_UNORM: memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_A4R4G4B4, sizeof(DDS_PIXELFORMAT)); break; // DXGI 1.2 + + // Legacy D3DX formats using D3DFMT enum value as FourCC + case DXGI_FORMAT_R32G32B32A32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 116; break; // D3DFMT_A32B32G32R32F + case DXGI_FORMAT_R16G16B16A16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 113; break; // D3DFMT_A16B16G16R16F + case DXGI_FORMAT_R16G16B16A16_UNORM: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 36; break; // D3DFMT_A16B16G16R16 + case DXGI_FORMAT_R16G16B16A16_SNORM: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 110; break; // D3DFMT_Q16W16V16U16 + case DXGI_FORMAT_R32G32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 115; break; // D3DFMT_G32R32F + case DXGI_FORMAT_R16G16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 112; break; // D3DFMT_G16R16F + case DXGI_FORMAT_R32_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 114; break; // D3DFMT_R32F + case DXGI_FORMAT_R16_FLOAT: header->ddspf.size = sizeof(DDS_PIXELFORMAT); header->ddspf.flags = DDS_FOURCC; header->ddspf.fourCC = 111; break; // D3DFMT_R16F + + case DXGI_FORMAT_AI44: + case DXGI_FORMAT_IA44: + case DXGI_FORMAT_P8: + case DXGI_FORMAT_A8P8: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + + default: + memcpy_s(&header->ddspf, sizeof(header->ddspf), &DDSPF_DX10, sizeof(DDS_PIXELFORMAT)); + + headerSize += sizeof(DDS_HEADER_DXT10); + extHeader = reinterpret_cast(fileHeader + sizeof(uint32_t) + sizeof(DDS_HEADER)); + extHeader->dxgiFormat = desc.Format; + extHeader->resourceDimension = D3D11_RESOURCE_DIMENSION_TEXTURE2D; + extHeader->arraySize = 1; + break; + } + + size_t rowPitch, slicePitch, rowCount; + hr = GetSurfaceInfo(desc.Width, desc.Height, desc.Format, &slicePitch, &rowPitch, &rowCount); + if (FAILED(hr)) + return hr; + + if (rowPitch > UINT32_MAX || slicePitch > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW); + + if (IsCompressed(desc.Format)) + { + header->flags |= DDS_HEADER_FLAGS_LINEARSIZE; + header->pitchOrLinearSize = static_cast(slicePitch); + } + else + { + header->flags |= DDS_HEADER_FLAGS_PITCH; + header->pitchOrLinearSize = static_cast(rowPitch); + } + + // Setup pixels + std::unique_ptr pixels(new (std::nothrow) uint8_t[slicePitch]); + if (!pixels) + return E_OUTOFMEMORY; + + D3D11_MAPPED_SUBRESOURCE mapped; + hr = pContext->Map(pStaging.Get(), 0, D3D11_MAP_READ, 0, &mapped); + if (FAILED(hr)) + return hr; + + auto sptr = static_cast(mapped.pData); + if (!sptr) + { + pContext->Unmap(pStaging.Get(), 0); + return E_POINTER; + } + + uint8_t* dptr = pixels.get(); + + size_t msize = std::min(rowPitch, mapped.RowPitch); + for (size_t h = 0; h < rowCount; ++h) + { + memcpy_s(dptr, rowPitch, sptr, msize); + sptr += mapped.RowPitch; + dptr += rowPitch; + } + + pContext->Unmap(pStaging.Get(), 0); + + // Write header & pixels + DWORD bytesWritten; + if (!WriteFile(hFile.get(), fileHeader, static_cast(headerSize), &bytesWritten, nullptr)) + return HRESULT_FROM_WIN32(GetLastError()); + + if (bytesWritten != headerSize) + return E_FAIL; + + if (!WriteFile(hFile.get(), pixels.get(), static_cast(slicePitch), &bytesWritten, nullptr)) + return HRESULT_FROM_WIN32(GetLastError()); + + if (bytesWritten != slicePitch) + return E_FAIL; + + delonfail.clear(); + + return S_OK; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::SaveWICTextureToFile( + ID3D11DeviceContext* pContext, + ID3D11Resource* pSource, + REFGUID guidContainerFormat, + const wchar_t* fileName, + const GUID* targetFormat, + std::function setCustomProps, + bool forceSRGB) +{ + if (!fileName) + return E_INVALIDARG; + + D3D11_TEXTURE2D_DESC desc = {}; + ComPtr pStaging; + HRESULT hr = CaptureTexture(pContext, pSource, desc, pStaging); + if (FAILED(hr)) + return hr; + + // Determine source format's WIC equivalent + WICPixelFormatGUID pfGuid = {}; + bool sRGB = forceSRGB; + switch (desc.Format) + { + case DXGI_FORMAT_R32G32B32A32_FLOAT: pfGuid = GUID_WICPixelFormat128bppRGBAFloat; break; + case DXGI_FORMAT_R16G16B16A16_FLOAT: pfGuid = GUID_WICPixelFormat64bppRGBAHalf; break; + case DXGI_FORMAT_R16G16B16A16_UNORM: pfGuid = GUID_WICPixelFormat64bppRGBA; break; + case DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM: pfGuid = GUID_WICPixelFormat32bppRGBA1010102XR; break; // DXGI 1.1 + case DXGI_FORMAT_R10G10B10A2_UNORM: pfGuid = GUID_WICPixelFormat32bppRGBA1010102; break; + case DXGI_FORMAT_B5G5R5A1_UNORM: pfGuid = GUID_WICPixelFormat16bppBGRA5551; break; + case DXGI_FORMAT_B5G6R5_UNORM: pfGuid = GUID_WICPixelFormat16bppBGR565; break; + case DXGI_FORMAT_R32_FLOAT: pfGuid = GUID_WICPixelFormat32bppGrayFloat; break; + case DXGI_FORMAT_R16_FLOAT: pfGuid = GUID_WICPixelFormat16bppGrayHalf; break; + case DXGI_FORMAT_R16_UNORM: pfGuid = GUID_WICPixelFormat16bppGray; break; + case DXGI_FORMAT_R8_UNORM: pfGuid = GUID_WICPixelFormat8bppGray; break; + case DXGI_FORMAT_A8_UNORM: pfGuid = GUID_WICPixelFormat8bppAlpha; break; + + case DXGI_FORMAT_R8G8B8A8_UNORM: + pfGuid = GUID_WICPixelFormat32bppRGBA; + break; + + case DXGI_FORMAT_R8G8B8A8_UNORM_SRGB: + pfGuid = GUID_WICPixelFormat32bppRGBA; + sRGB = true; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGRA; + break; + + case DXGI_FORMAT_B8G8R8A8_UNORM_SRGB: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGRA; + sRGB = true; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGR; + break; + + case DXGI_FORMAT_B8G8R8X8_UNORM_SRGB: // DXGI 1.1 + pfGuid = GUID_WICPixelFormat32bppBGR; + sRGB = true; + break; + + default: + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr stream; + hr = pWIC->CreateStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = stream->InitializeFromFilename(fileName, GENERIC_WRITE); + if (FAILED(hr)) + return hr; + + auto_delete_file_wic delonfail(stream, fileName); + + ComPtr encoder; + hr = pWIC->CreateEncoder(guidContainerFormat, nullptr, encoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = encoder->Initialize(stream.Get(), WICBitmapEncoderNoCache); + if (FAILED(hr)) + return hr; + + ComPtr frame; + ComPtr props; + hr = encoder->CreateNewFrame(frame.GetAddressOf(), props.GetAddressOf()); + if (FAILED(hr)) + return hr; + + if (targetFormat && memcmp(&guidContainerFormat, &GUID_ContainerFormatBmp, sizeof(WICPixelFormatGUID)) == 0 && g_WIC2) + { + // Opt-in to the WIC2 support for writing 32-bit Windows BMP files with an alpha channel + PROPBAG2 option = {}; + option.pstrName = const_cast(L"EnableV5Header32bppBGRA"); + + VARIANT varValue; + varValue.vt = VT_BOOL; + varValue.boolVal = VARIANT_TRUE; + (void)props->Write(1, &option, &varValue); + } + + if (setCustomProps) + { + setCustomProps(props.Get()); + } + + hr = frame->Initialize(props.Get()); + if (FAILED(hr)) + return hr; + + hr = frame->SetSize(desc.Width, desc.Height); + if (FAILED(hr)) + return hr; + + hr = frame->SetResolution(72, 72); + if (FAILED(hr)) + return hr; + + // Pick a target format + WICPixelFormatGUID targetGuid = {}; + if (targetFormat) + { + targetGuid = *targetFormat; + } + else + { + // Screenshots don't typically include the alpha channel of the render target + switch (desc.Format) + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + case DXGI_FORMAT_R32G32B32A32_FLOAT: + case DXGI_FORMAT_R16G16B16A16_FLOAT: + if (g_WIC2) + { + targetGuid = GUID_WICPixelFormat96bppRGBFloat; + } + else + { + targetGuid = GUID_WICPixelFormat24bppBGR; + } + break; +#endif + + case DXGI_FORMAT_R16G16B16A16_UNORM: targetGuid = GUID_WICPixelFormat48bppBGR; break; + case DXGI_FORMAT_B5G5R5A1_UNORM: targetGuid = GUID_WICPixelFormat16bppBGR555; break; + case DXGI_FORMAT_B5G6R5_UNORM: targetGuid = GUID_WICPixelFormat16bppBGR565; break; + + case DXGI_FORMAT_R32_FLOAT: + case DXGI_FORMAT_R16_FLOAT: + case DXGI_FORMAT_R16_UNORM: + case DXGI_FORMAT_R8_UNORM: + case DXGI_FORMAT_A8_UNORM: + targetGuid = GUID_WICPixelFormat8bppGray; + break; + + default: + targetGuid = GUID_WICPixelFormat24bppBGR; + break; + } + } + + hr = frame->SetPixelFormat(&targetGuid); + if (FAILED(hr)) + return hr; + + if (targetFormat && memcmp(targetFormat, &targetGuid, sizeof(WICPixelFormatGUID)) != 0) + { + // Requested output pixel format is not supported by the WIC codec + return E_FAIL; + } + + // Encode WIC metadata + ComPtr metawriter; + if (SUCCEEDED(frame->GetMetadataQueryWriter(metawriter.GetAddressOf()))) + { + PROPVARIANT value; + PropVariantInit(&value); + + value.vt = VT_LPSTR; + value.pszVal = const_cast("DirectXTK"); + + if (memcmp(&guidContainerFormat, &GUID_ContainerFormatPng, sizeof(GUID)) == 0) + { + // Set Software name + (void)metawriter->SetMetadataByName(L"/tEXt/{str=Software}", &value); + + // Set sRGB chunk + if (sRGB) + { + value.vt = VT_UI1; + value.bVal = 0; + (void)metawriter->SetMetadataByName(L"/sRGB/RenderingIntent", &value); + } + else + { + // add gAMA chunk with gamma 1.0 + value.vt = VT_UI4; + value.uintVal = 100000; // gama value * 100,000 -- i.e. gamma 1.0 + (void)metawriter->SetMetadataByName(L"/gAMA/ImageGamma", &value); + + // remove sRGB chunk which is added by default. + (void)metawriter->RemoveMetadataByName(L"/sRGB/RenderingIntent"); + } + } + else + { + // Set Software name + (void)metawriter->SetMetadataByName(L"System.ApplicationName", &value); + + if (sRGB) + { + // Set EXIF Colorspace of sRGB + value.vt = VT_UI2; + value.uiVal = 1; + (void)metawriter->SetMetadataByName(L"System.Image.ColorSpace", &value); + } + } + } + + D3D11_MAPPED_SUBRESOURCE mapped; + hr = pContext->Map(pStaging.Get(), 0, D3D11_MAP_READ, 0, &mapped); + if (FAILED(hr)) + return hr; + + uint64_t imageSize = uint64_t(mapped.RowPitch) * uint64_t(desc.Height); + if (imageSize > UINT32_MAX) + { + pContext->Unmap(pStaging.Get(), 0); + return HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW); + } + + if (memcmp(&targetGuid, &pfGuid, sizeof(WICPixelFormatGUID)) != 0) + { + // Conversion required to write + ComPtr source; + hr = pWIC->CreateBitmapFromMemory(desc.Width, desc.Height, + pfGuid, + mapped.RowPitch, static_cast(imageSize), + static_cast(mapped.pData), source.GetAddressOf()); + if (FAILED(hr)) + { + pContext->Unmap(pStaging.Get(), 0); + return hr; + } + + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + { + pContext->Unmap(pStaging.Get(), 0); + return hr; + } + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfGuid, targetGuid, &canConvert); + if (FAILED(hr) || !canConvert) + { + pContext->Unmap(pStaging.Get(), 0); + return E_UNEXPECTED; + } + + hr = FC->Initialize(source.Get(), targetGuid, WICBitmapDitherTypeNone, nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + { + pContext->Unmap(pStaging.Get(), 0); + return hr; + } + + WICRect rect = { 0, 0, static_cast(desc.Width), static_cast(desc.Height) }; + hr = frame->WriteSource(FC.Get(), &rect); + } + else + { + // No conversion required + hr = frame->WritePixels(desc.Height, + mapped.RowPitch, static_cast(imageSize), + static_cast(mapped.pData)); + } + + pContext->Unmap(pStaging.Get(), 0); + + if (FAILED(hr)) + return hr; + + hr = frame->Commit(); + if (FAILED(hr)) + return hr; + + hr = encoder->Commit(); + if (FAILED(hr)) + return hr; + + delonfail.clear(); + + return S_OK; +} diff --git a/src/DX11/framework/dxut/Core/ScreenGrab.h b/src/DX11/framework/dxut/Core/ScreenGrab.h new file mode 100644 index 0000000..de212b3 --- /dev/null +++ b/src/DX11/framework/dxut/Core/ScreenGrab.h @@ -0,0 +1,41 @@ +//-------------------------------------------------------------------------------------- +// File: ScreenGrab.h +// +// Function for capturing a 2D texture and saving it to a file (aka a 'screenshot' +// when used on a Direct3D 11 Render Target). +// +// Note these functions are useful as a light-weight runtime screen grabber. For +// full-featured texture capture, DDS writer, and texture processing pipeline, +// see the 'Texconv' sample and the 'DirectXTex' library. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include + +#include +#include + + +namespace DirectX +{ + HRESULT __cdecl SaveDDSTextureToFile( + _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_z_ const wchar_t* fileName) noexcept; + + HRESULT __cdecl SaveWICTextureToFile( + _In_ ID3D11DeviceContext* pContext, + _In_ ID3D11Resource* pSource, + _In_ REFGUID guidContainerFormat, + _In_z_ const wchar_t* fileName, + _In_opt_ const GUID* targetFormat = nullptr, + _In_opt_ std::function setCustomProps = nullptr, + _In_ bool forceSRGB = false); +} diff --git a/src/DX11/framework/dxut/Core/WICTextureLoader.cpp b/src/DX11/framework/dxut/Core/WICTextureLoader.cpp new file mode 100644 index 0000000..9534686 --- /dev/null +++ b/src/DX11/framework/dxut/Core/WICTextureLoader.cpp @@ -0,0 +1,1080 @@ +//-------------------------------------------------------------------------------------- +// File: WICTextureLoader.cpp +// +// Function for loading a WIC image and creating a Direct3D runtime texture for it +// (auto-generating mipmaps if possible) +// +// Note: Assumes application has already called CoInitializeEx +// +// Warning: CreateWICTexture* functions are not thread-safe if given a d3dContext instance for +// auto-gen mipmap support. +// +// Note these functions are useful for images created as simple 2D textures. For +// more complex resources, DDSTextureLoader is an excellent light-weight runtime loader. +// For a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#include "dxut.h" + +// We could load multi-frame images (TIFF/GIF) into a texture array. +// For now, we just load the first frame (note: DirectXTex supports multi-frame images) + +#include "WICTextureLoader.h" + +#include + +#include + +#include + +#include +#include +#include +#include +#include +#include + +#ifdef __clang__ +#pragma clang diagnostic ignored "-Wcovered-switch-default" +#pragma clang diagnostic ignored "-Wswitch-enum" +#endif + +using namespace DirectX; +using Microsoft::WRL::ComPtr; + +namespace +{ + //-------------------------------------------------------------------------------------- + template + inline void SetDebugObjectName(_In_ ID3D11DeviceChild* resource, _In_ const char(&name)[TNameLength]) noexcept + { +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + resource->SetPrivateData(WKPDID_D3DDebugObjectName, TNameLength - 1, name); +#else + UNREFERENCED_PARAMETER(resource); + UNREFERENCED_PARAMETER(name); +#endif + } + + //------------------------------------------------------------------------------------- + // WIC Pixel Format Translation Data + //------------------------------------------------------------------------------------- + struct WICTranslate + { + const GUID& wic; + DXGI_FORMAT format; + }; + + constexpr WICTranslate g_WICFormats[] = + { + { GUID_WICPixelFormat128bppRGBAFloat, DXGI_FORMAT_R32G32B32A32_FLOAT }, + + { GUID_WICPixelFormat64bppRGBAHalf, DXGI_FORMAT_R16G16B16A16_FLOAT }, + { GUID_WICPixelFormat64bppRGBA, DXGI_FORMAT_R16G16B16A16_UNORM }, + + { GUID_WICPixelFormat32bppRGBA, DXGI_FORMAT_R8G8B8A8_UNORM }, + { GUID_WICPixelFormat32bppBGRA, DXGI_FORMAT_B8G8R8A8_UNORM }, // DXGI 1.1 + { GUID_WICPixelFormat32bppBGR, DXGI_FORMAT_B8G8R8X8_UNORM }, // DXGI 1.1 + + { GUID_WICPixelFormat32bppRGBA1010102XR, DXGI_FORMAT_R10G10B10_XR_BIAS_A2_UNORM }, // DXGI 1.1 + { GUID_WICPixelFormat32bppRGBA1010102, DXGI_FORMAT_R10G10B10A2_UNORM }, + + { GUID_WICPixelFormat16bppBGRA5551, DXGI_FORMAT_B5G5R5A1_UNORM }, + { GUID_WICPixelFormat16bppBGR565, DXGI_FORMAT_B5G6R5_UNORM }, + + { GUID_WICPixelFormat32bppGrayFloat, DXGI_FORMAT_R32_FLOAT }, + { GUID_WICPixelFormat16bppGrayHalf, DXGI_FORMAT_R16_FLOAT }, + { GUID_WICPixelFormat16bppGray, DXGI_FORMAT_R16_UNORM }, + { GUID_WICPixelFormat8bppGray, DXGI_FORMAT_R8_UNORM }, + + { GUID_WICPixelFormat8bppAlpha, DXGI_FORMAT_A8_UNORM }, + }; + + //------------------------------------------------------------------------------------- + // WIC Pixel Format nearest conversion table + //------------------------------------------------------------------------------------- + struct WICConvert + { + const GUID& source; + const GUID& target; + }; + + constexpr WICConvert g_WICConvert [] = + { + // Note target GUID in this conversion table must be one of those directly supported formats (above). + + { GUID_WICPixelFormatBlackWhite, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + + { GUID_WICPixelFormat1bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat2bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat4bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat8bppIndexed, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + + { GUID_WICPixelFormat2bppGray, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + { GUID_WICPixelFormat4bppGray, GUID_WICPixelFormat8bppGray }, // DXGI_FORMAT_R8_UNORM + + { GUID_WICPixelFormat16bppGrayFixedPoint, GUID_WICPixelFormat16bppGrayHalf }, // DXGI_FORMAT_R16_FLOAT + { GUID_WICPixelFormat32bppGrayFixedPoint, GUID_WICPixelFormat32bppGrayFloat }, // DXGI_FORMAT_R32_FLOAT + + { GUID_WICPixelFormat16bppBGR555, GUID_WICPixelFormat16bppBGRA5551 }, // DXGI_FORMAT_B5G5R5A1_UNORM + + { GUID_WICPixelFormat32bppBGR101010, GUID_WICPixelFormat32bppRGBA1010102 }, // DXGI_FORMAT_R10G10B10A2_UNORM + + { GUID_WICPixelFormat24bppBGR, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat24bppRGB, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat32bppPBGRA, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat32bppPRGBA, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + + { GUID_WICPixelFormat48bppRGB, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat48bppBGR, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppBGRA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPRGBA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPBGRA, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + + { GUID_WICPixelFormat48bppRGBFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat48bppBGRFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBAFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppBGRAFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBFixedPoint, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat64bppRGBHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + { GUID_WICPixelFormat48bppRGBHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + + { GUID_WICPixelFormat128bppPRGBAFloat, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBFloat, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBAFixedPoint, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat128bppRGBFixedPoint, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + { GUID_WICPixelFormat32bppRGBE, GUID_WICPixelFormat128bppRGBAFloat }, // DXGI_FORMAT_R32G32B32A32_FLOAT + + { GUID_WICPixelFormat32bppCMYK, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat64bppCMYK, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat40bppCMYKAlpha, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat80bppCMYKAlpha, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + + #if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + { GUID_WICPixelFormat32bppRGB, GUID_WICPixelFormat32bppRGBA }, // DXGI_FORMAT_R8G8B8A8_UNORM + { GUID_WICPixelFormat64bppRGB, GUID_WICPixelFormat64bppRGBA }, // DXGI_FORMAT_R16G16B16A16_UNORM + { GUID_WICPixelFormat64bppPRGBAHalf, GUID_WICPixelFormat64bppRGBAHalf }, // DXGI_FORMAT_R16G16B16A16_FLOAT + #endif + + // We don't support n-channel formats + }; + + bool g_WIC2 = false; + + BOOL WINAPI InitializeWICFactory(PINIT_ONCE, PVOID, PVOID *ifactory) noexcept + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + HRESULT hr = CoCreateInstance( + CLSID_WICImagingFactory2, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory2), + ifactory + ); + + if (SUCCEEDED(hr)) + { + // WIC2 is available on Windows 10, Windows 8.x, and Windows 7 SP1 with KB 2670838 installed + g_WIC2 = true; + return TRUE; + } + else + { + hr = CoCreateInstance( + CLSID_WICImagingFactory1, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + ifactory + ); + return SUCCEEDED(hr) ? TRUE : FALSE; + } +#else + return SUCCEEDED(CoCreateInstance( + CLSID_WICImagingFactory, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof(IWICImagingFactory), + ifactory)) ? TRUE : FALSE; +#endif + } + + IWICImagingFactory* _GetWIC() noexcept + { + static INIT_ONCE s_initOnce = INIT_ONCE_STATIC_INIT; + + IWICImagingFactory* factory = nullptr; + if (!InitOnceExecuteOnce( + &s_initOnce, + InitializeWICFactory, + nullptr, + reinterpret_cast(&factory))) + { + return nullptr; + } + + return factory; + } + + //--------------------------------------------------------------------------------- + DXGI_FORMAT _WICToDXGI(const GUID& guid) noexcept + { + for (size_t i = 0; i < std::size(g_WICFormats); ++i) + { + if (memcmp(&g_WICFormats[i].wic, &guid, sizeof(GUID)) == 0) + return g_WICFormats[i].format; + } + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if (g_WIC2) + { + if (memcmp(&GUID_WICPixelFormat96bppRGBFloat, &guid, sizeof(GUID)) == 0) + return DXGI_FORMAT_R32G32B32_FLOAT; + } +#endif + + return DXGI_FORMAT_UNKNOWN; + } + + //--------------------------------------------------------------------------------- + size_t _WICBitsPerPixel(REFGUID targetGuid) noexcept + { + auto pWIC = _GetWIC(); + if (!pWIC) + return 0; + + ComPtr cinfo; + if (FAILED(pWIC->CreateComponentInfo(targetGuid, cinfo.GetAddressOf()))) + return 0; + + WICComponentType type; + if (FAILED(cinfo->GetComponentType(&type))) + return 0; + + if (type != WICPixelFormat) + return 0; + + ComPtr pfinfo; + if (FAILED(cinfo.As(&pfinfo))) + return 0; + + UINT bpp; + if (FAILED(pfinfo->GetBitsPerPixel(&bpp))) + return 0; + + return bpp; + } + + + //-------------------------------------------------------------------------------------- + DXGI_FORMAT MakeSRGB(_In_ DXGI_FORMAT format) noexcept + { + switch (format) + { + case DXGI_FORMAT_R8G8B8A8_UNORM: + return DXGI_FORMAT_R8G8B8A8_UNORM_SRGB; + + case DXGI_FORMAT_BC1_UNORM: + return DXGI_FORMAT_BC1_UNORM_SRGB; + + case DXGI_FORMAT_BC2_UNORM: + return DXGI_FORMAT_BC2_UNORM_SRGB; + + case DXGI_FORMAT_BC3_UNORM: + return DXGI_FORMAT_BC3_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8A8_UNORM: + return DXGI_FORMAT_B8G8R8A8_UNORM_SRGB; + + case DXGI_FORMAT_B8G8R8X8_UNORM: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + + case DXGI_FORMAT_BC7_UNORM: + return DXGI_FORMAT_BC7_UNORM_SRGB; + + default: + return format; + } + } + + + //--------------------------------------------------------------------------------- + void FitPowerOf2(UINT origx, UINT origy, UINT& targetx, UINT& targety, size_t maxsize) + { + float origAR = float(origx) / float(origy); + + if (origx > origy) + { + size_t x; + for (x = maxsize; x > 1; x >>= 1) { if (x <= targetx) break; } + targetx = UINT(x); + + float bestScore = FLT_MAX; + for (size_t y = maxsize; y > 0; y >>= 1) + { + float score = fabsf((float(x) / float(y)) - origAR); + if (score < bestScore) + { + bestScore = score; + targety = UINT(y); + } + } + } + else + { + size_t y; + for (y = maxsize; y > 1; y >>= 1) { if (y <= targety) break; } + targety = UINT(y); + + float bestScore = FLT_MAX; + for (size_t x = maxsize; x > 0; x >>= 1) + { + float score = fabsf((float(x) / float(y)) - origAR); + if (score < bestScore) + { + bestScore = score; + targetx = UINT(x); + } + } + } + } + + + //--------------------------------------------------------------------------------- + HRESULT CreateTextureFromWIC(_In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_ IWICBitmapFrameDecode* frame, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ WIC_LOADER_FLAGS loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) noexcept + { + UINT width, height; + HRESULT hr = frame->GetSize(&width, &height); + if (FAILED(hr)) + return hr; + + if (maxsize > UINT32_MAX) + return E_INVALIDARG; + + assert(width > 0 && height > 0); + + if (!maxsize) + { + // This is a bit conservative because the hardware could support larger textures than + // the Feature Level defined minimums, but doing it this way is much easier and more + // performant for WIC than the 'fail and retry' model used by DDSTextureLoader + + switch (d3dDevice->GetFeatureLevel()) + { + case D3D_FEATURE_LEVEL_9_1: + case D3D_FEATURE_LEVEL_9_2: + maxsize = 2048u /*D3D_FL9_1_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + case D3D_FEATURE_LEVEL_9_3: + maxsize = 4096u /*D3D_FL9_3_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + case D3D_FEATURE_LEVEL_10_0: + case D3D_FEATURE_LEVEL_10_1: + maxsize = 8192u /*D3D10_REQ_TEXTURE2D_U_OR_V_DIMENSION*/; + break; + + default: + maxsize = size_t(D3D11_REQ_TEXTURE2D_U_OR_V_DIMENSION); + break; + } + } + + assert(maxsize > 0); + + UINT twidth = width; + UINT theight = height; + if (loadFlags & WIC_LOADER_FIT_POW2) + { + FitPowerOf2(width, height, twidth, theight, maxsize); + } + else if (width > maxsize || height > maxsize) + { + float ar = static_cast(height) / static_cast(width); + if (width > height) + { + twidth = static_cast(maxsize); + theight = std::max(1, static_cast(static_cast(maxsize) * ar)); + } + else + { + theight = static_cast(maxsize); + twidth = std::max(1, static_cast(static_cast(maxsize) / ar)); + } + assert(twidth <= maxsize && theight <= maxsize); + } + + if (loadFlags & WIC_LOADER_MAKE_SQUARE) + { + twidth = std::max(twidth, theight); + theight = twidth; + } + + // Determine format + WICPixelFormatGUID pixelFormat; + hr = frame->GetPixelFormat(&pixelFormat); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID convertGUID; + memcpy_s(&convertGUID, sizeof(WICPixelFormatGUID), &pixelFormat, sizeof(GUID)); + + size_t bpp = 0; + + DXGI_FORMAT format = _WICToDXGI(pixelFormat); + if (format == DXGI_FORMAT_UNKNOWN) + { + if (memcmp(&GUID_WICPixelFormat96bppRGBFixedPoint, &pixelFormat, sizeof(WICPixelFormatGUID)) == 0) + { +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if (g_WIC2) + { + memcpy_s(&convertGUID, sizeof(WICPixelFormatGUID), &GUID_WICPixelFormat96bppRGBFloat, sizeof(GUID)); + format = DXGI_FORMAT_R32G32B32_FLOAT; + bpp = 96; + } + else +#endif + { + memcpy_s(&convertGUID, sizeof(WICPixelFormatGUID), &GUID_WICPixelFormat128bppRGBAFloat, sizeof(GUID)); + format = DXGI_FORMAT_R32G32B32A32_FLOAT; + bpp = 128; + } + } + else + { + for (size_t i = 0; i < std::size(g_WICConvert); ++i) + { + if (memcmp(&g_WICConvert[i].source, &pixelFormat, sizeof(WICPixelFormatGUID)) == 0) + { + memcpy_s(&convertGUID, sizeof(WICPixelFormatGUID), &g_WICConvert[i].target, sizeof(GUID)); + + format = _WICToDXGI(g_WICConvert[i].target); + assert(format != DXGI_FORMAT_UNKNOWN); + bpp = _WICBitsPerPixel(convertGUID); + break; + } + } + } + + if (format == DXGI_FORMAT_UNKNOWN) + return HRESULT_FROM_WIN32(ERROR_NOT_SUPPORTED); + } + else + { + bpp = _WICBitsPerPixel(pixelFormat); + } + +#if (_WIN32_WINNT >= _WIN32_WINNT_WIN8) || defined(_WIN7_PLATFORM_UPDATE) + if ((format == DXGI_FORMAT_R32G32B32_FLOAT) && d3dContext && textureView) + { + // Special case test for optional device support for autogen mipchains for R32G32B32_FLOAT + UINT fmtSupport = 0; + hr = d3dDevice->CheckFormatSupport(DXGI_FORMAT_R32G32B32_FLOAT, &fmtSupport); + if (FAILED(hr) || !(fmtSupport & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN)) + { + // Use R32G32B32A32_FLOAT instead which is required for Feature Level 10.0 and up + memcpy_s(&convertGUID, sizeof(WICPixelFormatGUID), &GUID_WICPixelFormat128bppRGBAFloat, sizeof(GUID)); + format = DXGI_FORMAT_R32G32B32A32_FLOAT; + bpp = 128; + } + } +#endif + + if (loadFlags & WIC_LOADER_FORCE_RGBA32) + { + memcpy_s(&convertGUID, sizeof(WICPixelFormatGUID), &GUID_WICPixelFormat32bppRGBA, sizeof(GUID)); + format = DXGI_FORMAT_R8G8B8A8_UNORM; + bpp = 32; + } + + if (!bpp) + return E_FAIL; + + // Handle sRGB formats + if (loadFlags & WIC_LOADER_FORCE_SRGB) + { + format = MakeSRGB(format); + } + else if (!(loadFlags & WIC_LOADER_IGNORE_SRGB)) + { + ComPtr metareader; + if (SUCCEEDED(frame->GetMetadataQueryReader(metareader.GetAddressOf()))) + { + GUID containerFormat; + if (SUCCEEDED(metareader->GetContainerFormat(&containerFormat))) + { + bool sRGB = false; + + PROPVARIANT value; + PropVariantInit(&value); + + // Check for colorspace chunks + if (memcmp(&containerFormat, &GUID_ContainerFormatPng, sizeof(GUID)) == 0) + { + if (SUCCEEDED(metareader->GetMetadataByName(L"/sRGB/RenderingIntent", &value)) && value.vt == VT_UI1) + { + sRGB = true; + } + else if (SUCCEEDED(metareader->GetMetadataByName(L"/gAMA/ImageGamma", &value)) && value.vt == VT_UI4) + { + sRGB = (value.uintVal == 45455); + } + else + { + sRGB = (loadFlags & WIC_LOADER_SRGB_DEFAULT) != 0; + } + } + else if (SUCCEEDED(metareader->GetMetadataByName(L"System.Image.ColorSpace", &value)) && value.vt == VT_UI2) + { + sRGB = (value.uiVal == 1); + } + else + { + sRGB = (loadFlags & WIC_LOADER_SRGB_DEFAULT) != 0; + } + + (void)PropVariantClear(&value); + + if (sRGB) + format = MakeSRGB(format); + } + } + } + + // Verify our target format is supported by the current device + // (handles WDDM 1.0 or WDDM 1.1 device driver cases as well as DirectX 11.0 Runtime without 16bpp format support) + UINT support = 0; + hr = d3dDevice->CheckFormatSupport(format, &support); + if (FAILED(hr) || !(support & D3D11_FORMAT_SUPPORT_TEXTURE2D)) + { + // Fallback to RGBA 32-bit format which is supported by all devices + memcpy_s(&convertGUID, sizeof(WICPixelFormatGUID), &GUID_WICPixelFormat32bppRGBA, sizeof(GUID)); + format = DXGI_FORMAT_R8G8B8A8_UNORM; + bpp = 32; + } + + // Allocate temporary memory for image + uint64_t rowBytes = (uint64_t(twidth) * uint64_t(bpp) + 7u) / 8u; + uint64_t numBytes = rowBytes * uint64_t(theight); + + if (rowBytes > UINT32_MAX || numBytes > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_ARITHMETIC_OVERFLOW); + + auto rowPitch = static_cast(rowBytes); + auto imageSize = static_cast(numBytes); + + std::unique_ptr temp(new (std::nothrow) uint8_t[imageSize]); + if (!temp) + return E_OUTOFMEMORY; + + // Load image data + if (memcmp(&convertGUID, &pixelFormat, sizeof(GUID)) == 0 + && twidth == width + && theight == height) + { + // No format conversion or resize needed + hr = frame->CopyPixels(nullptr, static_cast(rowPitch), static_cast(imageSize), temp.get()); + if (FAILED(hr)) + return hr; + } + else if (twidth != width || theight != height) + { + // Resize + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr scaler; + hr = pWIC->CreateBitmapScaler(scaler.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = scaler->Initialize(frame, twidth, theight, WICBitmapInterpolationModeFant); + if (FAILED(hr)) + return hr; + + WICPixelFormatGUID pfScaler; + hr = scaler->GetPixelFormat(&pfScaler); + if (FAILED(hr)) + return hr; + + if (memcmp(&convertGUID, &pfScaler, sizeof(GUID)) == 0) + { + // No format conversion needed + hr = scaler->CopyPixels(nullptr, static_cast(rowPitch), static_cast(imageSize), temp.get()); + if (FAILED(hr)) + return hr; + } + else + { + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pfScaler, convertGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(scaler.Get(), convertGUID, WICBitmapDitherTypeErrorDiffusion, nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(nullptr, static_cast(rowPitch), static_cast(imageSize), temp.get()); + if (FAILED(hr)) + return hr; + } + } + else + { + // Format conversion but no resize + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + ComPtr FC; + hr = pWIC->CreateFormatConverter(FC.GetAddressOf()); + if (FAILED(hr)) + return hr; + + BOOL canConvert = FALSE; + hr = FC->CanConvert(pixelFormat, convertGUID, &canConvert); + if (FAILED(hr) || !canConvert) + { + return E_UNEXPECTED; + } + + hr = FC->Initialize(frame, convertGUID, WICBitmapDitherTypeErrorDiffusion, nullptr, 0, WICBitmapPaletteTypeMedianCut); + if (FAILED(hr)) + return hr; + + hr = FC->CopyPixels(nullptr, static_cast(rowPitch), static_cast(imageSize), temp.get()); + if (FAILED(hr)) + return hr; + } + + // See if format is supported for auto-gen mipmaps (varies by feature level) + bool autogen = false; + if (d3dContext && textureView) // Must have context and shader-view to auto generate mipmaps + { + UINT fmtSupport = 0; + hr = d3dDevice->CheckFormatSupport(format, &fmtSupport); + if (SUCCEEDED(hr) && (fmtSupport & D3D11_FORMAT_SUPPORT_MIP_AUTOGEN)) + { + autogen = true; + } + } + + // Create texture + D3D11_TEXTURE2D_DESC desc = {}; + desc.Width = twidth; + desc.Height = theight; + desc.MipLevels = (autogen) ? 0u : 1u; + desc.ArraySize = 1; + desc.Format = format; + desc.SampleDesc.Count = 1; + desc.SampleDesc.Quality = 0; + desc.Usage = usage; + desc.CPUAccessFlags = cpuAccessFlags; + + if (autogen) + { + desc.BindFlags = bindFlags | D3D11_BIND_RENDER_TARGET; + desc.MiscFlags = miscFlags | D3D11_RESOURCE_MISC_GENERATE_MIPS; + } + else + { + desc.BindFlags = bindFlags; + desc.MiscFlags = miscFlags; + } + + D3D11_SUBRESOURCE_DATA initData; + initData.pSysMem = temp.get(); + initData.SysMemPitch = static_cast(rowPitch); + initData.SysMemSlicePitch = static_cast(imageSize); + + ID3D11Texture2D* tex = nullptr; + hr = d3dDevice->CreateTexture2D(&desc, (autogen) ? nullptr : &initData, &tex); + if (SUCCEEDED(hr) && tex) + { + if (textureView) + { + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc = {}; + SRVDesc.Format = desc.Format; + + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + SRVDesc.Texture2D.MipLevels = (autogen) ? unsigned(-1) : 1u; + + hr = d3dDevice->CreateShaderResourceView(tex, &SRVDesc, textureView); + if (FAILED(hr)) + { + tex->Release(); + return hr; + } + + if (autogen) + { + assert(d3dContext != nullptr); + d3dContext->UpdateSubresource(tex, 0, nullptr, temp.get(), static_cast(rowPitch), static_cast(imageSize)); + d3dContext->GenerateMips(*textureView); + } + } + + if (texture) + { + *texture = tex; + } + else + { + SetDebugObjectName(tex, "WICTextureLoader"); + tex->Release(); + } + } + + return hr; + } + + + //-------------------------------------------------------------------------------------- + void SetDebugTextureInfo( + _In_z_ const wchar_t* fileName, + _In_opt_ ID3D11Resource** texture, + _In_opt_ ID3D11ShaderResourceView** textureView) noexcept + { +#if !defined(NO_D3D11_DEBUG_NAME) && ( defined(_DEBUG) || defined(PROFILE) ) + if (texture || textureView) + { + CHAR strFileA[MAX_PATH]; + int result = WideCharToMultiByte(CP_UTF8, + WC_NO_BEST_FIT_CHARS, + fileName, + -1, + strFileA, + MAX_PATH, + nullptr, + nullptr + ); + if (result > 0) + { + const char* pstrName = strrchr(strFileA, '\\'); + if (!pstrName) + { + pstrName = strFileA; + } + else + { + pstrName++; + } + + if (texture && *texture) + { + (*texture)->SetPrivateData(WKPDID_D3DDebugObjectName, + static_cast(strnlen_s(pstrName, MAX_PATH)), + pstrName + ); + } + + if (textureView && *textureView) + { + (*textureView)->SetPrivateData(WKPDID_D3DDebugObjectName, + static_cast(strnlen_s(pstrName, MAX_PATH)), + pstrName + ); + } + } + } +#else + UNREFERENCED_PARAMETER(fileName); + UNREFERENCED_PARAMETER(texture); + UNREFERENCED_PARAMETER(textureView); +#endif + } +} // anonymous namespace + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromMemory( + ID3D11Device* d3dDevice, + const uint8_t* wicData, + size_t wicDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize) noexcept +{ + return CreateWICTextureFromMemoryEx(d3dDevice, nullptr, + wicData, wicDataSize, + maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + WIC_LOADER_DEFAULT, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromMemory( + ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* wicData, + size_t wicDataSize, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize) noexcept +{ + return CreateWICTextureFromMemoryEx(d3dDevice, d3dContext, + wicData, wicDataSize, + maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + WIC_LOADER_DEFAULT, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromMemoryEx( + ID3D11Device* d3dDevice, + const uint8_t* wicData, + size_t wicDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + WIC_LOADER_FLAGS loadFlags, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView) noexcept +{ + return CreateWICTextureFromMemoryEx(d3dDevice, nullptr, + wicData, wicDataSize, + maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, + loadFlags, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromMemoryEx( + ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const uint8_t* wicData, + size_t wicDataSize, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + WIC_LOADER_FLAGS loadFlags, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView) noexcept +{ + if (texture) + { + *texture = nullptr; + } + if (textureView) + { + *textureView = nullptr; + } + + if (!d3dDevice || !wicData || (!texture && !textureView)) + { + return E_INVALIDARG; + } + + if (textureView && !(bindFlags & D3D11_BIND_SHADER_RESOURCE)) + { + return E_INVALIDARG; + } + + if (!wicDataSize) + return E_FAIL; + + if (wicDataSize > UINT32_MAX) + return HRESULT_FROM_WIN32(ERROR_FILE_TOO_LARGE); + + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + // Create input stream for memory + ComPtr stream; + HRESULT hr = pWIC->CreateStream(stream.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = stream->InitializeFromMemory(const_cast(wicData), static_cast(wicDataSize)); + if (FAILED(hr)) + return hr; + + // Initialize WIC + ComPtr decoder; + hr = pWIC->CreateDecoderFromStream(stream.Get(), nullptr, WICDecodeMetadataCacheOnDemand, decoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr frame; + hr = decoder->GetFrame(0, frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = CreateTextureFromWIC(d3dDevice, d3dContext, + frame.Get(), + maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, + loadFlags, + texture, textureView); + if (FAILED(hr)) + return hr; + + if (texture && *texture) + { + SetDebugObjectName(*texture, "WICTextureLoader"); + } + + if (textureView && *textureView) + { + SetDebugObjectName(*textureView, "WICTextureLoader"); + } + + return hr; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromFile( + ID3D11Device* d3dDevice, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize) noexcept +{ + return CreateWICTextureFromFileEx(d3dDevice, nullptr, + fileName, maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + WIC_LOADER_DEFAULT, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromFile( + ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView, + size_t maxsize) noexcept +{ + return CreateWICTextureFromFileEx(d3dDevice, d3dContext, + fileName, + maxsize, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + WIC_LOADER_DEFAULT, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromFileEx( + ID3D11Device* d3dDevice, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + WIC_LOADER_FLAGS loadFlags, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView) noexcept +{ + return CreateWICTextureFromFileEx(d3dDevice, nullptr, + fileName, + maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, + loadFlags, + texture, textureView); +} + +_Use_decl_annotations_ +HRESULT DirectX::CreateWICTextureFromFileEx( + ID3D11Device* d3dDevice, + ID3D11DeviceContext* d3dContext, + const wchar_t* fileName, + size_t maxsize, + D3D11_USAGE usage, + unsigned int bindFlags, + unsigned int cpuAccessFlags, + unsigned int miscFlags, + WIC_LOADER_FLAGS loadFlags, + ID3D11Resource** texture, + ID3D11ShaderResourceView** textureView) noexcept +{ + if (texture) + { + *texture = nullptr; + } + if (textureView) + { + *textureView = nullptr; + } + + if (!d3dDevice || !fileName || (!texture && !textureView)) + { + return E_INVALIDARG; + } + + if (textureView && !(bindFlags & D3D11_BIND_SHADER_RESOURCE)) + { + return E_INVALIDARG; + } + + auto pWIC = _GetWIC(); + if (!pWIC) + return E_NOINTERFACE; + + // Initialize WIC + ComPtr decoder; + HRESULT hr = pWIC->CreateDecoderFromFilename(fileName, + nullptr, + GENERIC_READ, + WICDecodeMetadataCacheOnDemand, + decoder.GetAddressOf()); + if (FAILED(hr)) + return hr; + + ComPtr frame; + hr = decoder->GetFrame(0, frame.GetAddressOf()); + if (FAILED(hr)) + return hr; + + hr = CreateTextureFromWIC(d3dDevice, d3dContext, + frame.Get(), + maxsize, + usage, bindFlags, cpuAccessFlags, miscFlags, + loadFlags, + texture, textureView); + + if (SUCCEEDED(hr)) + { + SetDebugTextureInfo(fileName, texture, textureView); + } + + return hr; +} diff --git a/src/DX11/framework/dxut/Core/WICTextureLoader.h b/src/DX11/framework/dxut/Core/WICTextureLoader.h new file mode 100644 index 0000000..c0469a2 --- /dev/null +++ b/src/DX11/framework/dxut/Core/WICTextureLoader.h @@ -0,0 +1,145 @@ +//-------------------------------------------------------------------------------------- +// File: WICTextureLoader.h +// +// Function for loading a WIC image and creating a Direct3D runtime texture for it +// (auto-generating mipmaps if possible) +// +// Note: Assumes application has already called CoInitializeEx +// +// Warning: CreateWICTexture* functions are not thread-safe if given a d3dContext instance for +// auto-gen mipmap support. +// +// Note these functions are useful for images created as simple 2D textures. For +// more complex resources, DDSTextureLoader is an excellent light-weight runtime loader. +// For a full-featured DDS file reader, writer, and texture processing pipeline see +// the 'Texconv' sample and the 'DirectXTex' library. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=248926 +// http://go.microsoft.com/fwlink/?LinkId=248929 +//-------------------------------------------------------------------------------------- + +#pragma once + +#include + +#include +#include + +namespace DirectX +{ +#ifndef WIC_LOADER_FLAGS_DEFINED +#define WIC_LOADER_FLAGS_DEFINED + enum WIC_LOADER_FLAGS : uint32_t + { + WIC_LOADER_DEFAULT = 0, + WIC_LOADER_FORCE_SRGB = 0x1, + WIC_LOADER_IGNORE_SRGB = 0x2, + WIC_LOADER_SRGB_DEFAULT = 0x4, + WIC_LOADER_FIT_POW2 = 0x20, + WIC_LOADER_MAKE_SQUARE = 0x40, + WIC_LOADER_FORCE_RGBA32 = 0x80, + }; + +#ifdef __clang__ +#pragma clang diagnostic push +#pragma clang diagnostic ignored "-Wdeprecated-dynamic-exception-spec" +#endif + + DEFINE_ENUM_FLAG_OPERATORS(WIC_LOADER_FLAGS); + +#ifdef __clang__ +#pragma clang diagnostic pop +#endif +#endif + + // Standard version + HRESULT CreateWICTextureFromMemory( + _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + _In_ size_t wicDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0) noexcept; + + HRESULT CreateWICTextureFromFile( + _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0) noexcept; + + // Standard version with optional auto-gen mipmap support + HRESULT CreateWICTextureFromMemory( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + _In_ size_t wicDataSize, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0) noexcept; + + HRESULT CreateWICTextureFromFile( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView, + _In_ size_t maxsize = 0) noexcept; + + // Extended version + HRESULT CreateWICTextureFromMemoryEx( + _In_ ID3D11Device* d3dDevice, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + _In_ size_t wicDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ WIC_LOADER_FLAGS loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) noexcept; + + HRESULT CreateWICTextureFromFileEx( + _In_ ID3D11Device* d3dDevice, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ WIC_LOADER_FLAGS loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) noexcept; + + // Extended version with optional auto-gen mipmap support + HRESULT CreateWICTextureFromMemoryEx( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_reads_bytes_(wicDataSize) const uint8_t* wicData, + _In_ size_t wicDataSize, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ WIC_LOADER_FLAGS loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) noexcept; + + HRESULT CreateWICTextureFromFileEx( + _In_ ID3D11Device* d3dDevice, + _In_opt_ ID3D11DeviceContext* d3dContext, + _In_z_ const wchar_t* szFileName, + _In_ size_t maxsize, + _In_ D3D11_USAGE usage, + _In_ unsigned int bindFlags, + _In_ unsigned int cpuAccessFlags, + _In_ unsigned int miscFlags, + _In_ WIC_LOADER_FLAGS loadFlags, + _Outptr_opt_ ID3D11Resource** texture, + _Outptr_opt_ ID3D11ShaderResourceView** textureView) noexcept; +} diff --git a/src/DX11/framework/dxut/Core/dxerr.cpp b/src/DX11/framework/dxut/Core/dxerr.cpp new file mode 100644 index 0000000..28bd02a --- /dev/null +++ b/src/DX11/framework/dxut/Core/dxerr.cpp @@ -0,0 +1,3656 @@ +//-------------------------------------------------------------------------------------- +// File: DXErr.cpp +// +// DirectX Error Library +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +//-------------------------------------------------------------------------------------- +#include "dxut.h" + +// This version only supports UNICODE. + +#include "dxerr.h" + +#include + +#include +#include +#include +#include +#include +#include + +#define XAUDIO2_E_INVALID_CALL 0x88960001 +#define XAUDIO2_E_XMA_DECODER_ERROR 0x88960002 +#define XAUDIO2_E_XAPO_CREATION_FAILED 0x88960003 +#define XAUDIO2_E_DEVICE_INVALIDATED 0x88960004 + +#define XAPO_E_FORMAT_UNSUPPORTED MAKE_HRESULT(SEVERITY_ERROR, 0x897, 0x01) + +#define DXUTERR_NODIRECT3D MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0901) +#define DXUTERR_NOCOMPATIBLEDEVICES MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0902) +#define DXUTERR_MEDIANOTFOUND MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0903) +#define DXUTERR_NONZEROREFCOUNT MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0904) +#define DXUTERR_CREATINGDEVICE MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0905) +#define DXUTERR_RESETTINGDEVICE MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0906) +#define DXUTERR_CREATINGDEVICEOBJECTS MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0907) +#define DXUTERR_RESETTINGDEVICEOBJECTS MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0908) +#define DXUTERR_INCORRECTVERSION MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x0909) +#define DXUTERR_DEVICEREMOVED MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x090A) + +//----------------------------------------------------------------------------- +#define BUFFER_SIZE 3000 + +#pragma warning( disable : 6001 6221 ) + +//-------------------------------------------------------------------------------------- +#define CHK_ERR(hrchk, strOut) \ + case hrchk: \ + return L##strOut; + +#define CHK_ERRA(hrchk) \ + case hrchk: \ + return L## #hrchk; + +#define HRESULT_FROM_WIN32b(x) ((HRESULT)(x) <= 0 ? ((HRESULT)(x)) : ((HRESULT) (((x) & 0x0000FFFF) | (FACILITY_WIN32 << 16) | 0x80000000))) + +#define CHK_ERR_WIN32A(hrchk) \ + case HRESULT_FROM_WIN32b(hrchk): \ + case hrchk: \ + return L## #hrchk; + +#define CHK_ERR_WIN32_ONLY(hrchk, strOut) \ + case HRESULT_FROM_WIN32b(hrchk): \ + return L##strOut; + +//----------------------------------------------------- +const WCHAR* WINAPI DXGetErrorStringW( _In_ HRESULT hr ) +{ + switch(hr) + { +// Commmented out codes are actually alises for other codes + +// ------------------------------------------------------------- +// Common Win32 error codes +// ------------------------------------------------------------- + CHK_ERRA(S_OK) + CHK_ERRA(S_FALSE) + + CHK_ERRA(E_UNEXPECTED) + CHK_ERRA(E_NOTIMPL) + CHK_ERRA(E_OUTOFMEMORY) + CHK_ERRA(E_INVALIDARG) + CHK_ERRA(E_NOINTERFACE) + CHK_ERRA(E_POINTER) + CHK_ERRA(E_HANDLE) + CHK_ERRA(E_ABORT) + CHK_ERRA(E_FAIL) + CHK_ERRA(E_ACCESSDENIED) + CHK_ERRA(E_PENDING) + CHK_ERRA(CO_E_INIT_TLS) + CHK_ERRA(CO_E_INIT_SHARED_ALLOCATOR) + CHK_ERRA(CO_E_INIT_MEMORY_ALLOCATOR) + CHK_ERRA(CO_E_INIT_CLASS_CACHE) + CHK_ERRA(CO_E_INIT_RPC_CHANNEL) + CHK_ERRA(CO_E_INIT_TLS_SET_CHANNEL_CONTROL) + CHK_ERRA(CO_E_INIT_TLS_CHANNEL_CONTROL) + CHK_ERRA(CO_E_INIT_UNACCEPTED_USER_ALLOCATOR) + CHK_ERRA(CO_E_INIT_SCM_MUTEX_EXISTS) + CHK_ERRA(CO_E_INIT_SCM_FILE_MAPPING_EXISTS) + CHK_ERRA(CO_E_INIT_SCM_MAP_VIEW_OF_FILE) + CHK_ERRA(CO_E_INIT_SCM_EXEC_FAILURE) + CHK_ERRA(CO_E_INIT_ONLY_SINGLE_THREADED) + CHK_ERRA(CO_E_CANT_REMOTE) + CHK_ERRA(CO_E_BAD_SERVER_NAME) + CHK_ERRA(CO_E_WRONG_SERVER_IDENTITY) + CHK_ERRA(CO_E_OLE1DDE_DISABLED) + CHK_ERRA(CO_E_RUNAS_SYNTAX) + CHK_ERRA(CO_E_CREATEPROCESS_FAILURE) + CHK_ERRA(CO_E_RUNAS_CREATEPROCESS_FAILURE) + CHK_ERRA(CO_E_RUNAS_LOGON_FAILURE) + CHK_ERRA(CO_E_LAUNCH_PERMSSION_DENIED) + CHK_ERRA(CO_E_START_SERVICE_FAILURE) + CHK_ERRA(CO_E_REMOTE_COMMUNICATION_FAILURE) + CHK_ERRA(CO_E_SERVER_START_TIMEOUT) + CHK_ERRA(CO_E_CLSREG_INCONSISTENT) + CHK_ERRA(CO_E_IIDREG_INCONSISTENT) + CHK_ERRA(CO_E_NOT_SUPPORTED) + CHK_ERRA(CO_E_RELOAD_DLL) + CHK_ERRA(CO_E_MSI_ERROR) + CHK_ERRA(OLE_E_FIRST) + CHK_ERRA(OLE_E_LAST) + CHK_ERRA(OLE_S_FIRST) + CHK_ERRA(OLE_S_LAST) +// CHK_ERRA(OLE_E_OLEVERB) + CHK_ERRA(OLE_E_ADVF) + CHK_ERRA(OLE_E_ENUM_NOMORE) + CHK_ERRA(OLE_E_ADVISENOTSUPPORTED) + CHK_ERRA(OLE_E_NOCONNECTION) + CHK_ERRA(OLE_E_NOTRUNNING) + CHK_ERRA(OLE_E_NOCACHE) + CHK_ERRA(OLE_E_BLANK) + CHK_ERRA(OLE_E_CLASSDIFF) + CHK_ERRA(OLE_E_CANT_GETMONIKER) + CHK_ERRA(OLE_E_CANT_BINDTOSOURCE) + CHK_ERRA(OLE_E_STATIC) + CHK_ERRA(OLE_E_PROMPTSAVECANCELLED) + CHK_ERRA(OLE_E_INVALIDRECT) + CHK_ERRA(OLE_E_WRONGCOMPOBJ) + CHK_ERRA(OLE_E_INVALIDHWND) + CHK_ERRA(OLE_E_NOT_INPLACEACTIVE) + CHK_ERRA(OLE_E_CANTCONVERT) + CHK_ERRA(OLE_E_NOSTORAGE) + CHK_ERRA(DV_E_FORMATETC) + CHK_ERRA(DV_E_DVTARGETDEVICE) + CHK_ERRA(DV_E_STGMEDIUM) + CHK_ERRA(DV_E_STATDATA) + CHK_ERRA(DV_E_LINDEX) + CHK_ERRA(DV_E_TYMED) + CHK_ERRA(DV_E_CLIPFORMAT) + CHK_ERRA(DV_E_DVASPECT) + CHK_ERRA(DV_E_DVTARGETDEVICE_SIZE) + CHK_ERRA(DV_E_NOIVIEWOBJECT) + CHK_ERRA(DRAGDROP_E_FIRST) + CHK_ERRA(DRAGDROP_E_LAST) + CHK_ERRA(DRAGDROP_S_FIRST) + CHK_ERRA(DRAGDROP_S_LAST) +// CHK_ERRA(DRAGDROP_E_NOTREGISTERED) + CHK_ERRA(DRAGDROP_E_ALREADYREGISTERED) + CHK_ERRA(DRAGDROP_E_INVALIDHWND) + CHK_ERRA(CLASSFACTORY_E_FIRST) + CHK_ERRA(CLASSFACTORY_E_LAST) + CHK_ERRA(CLASSFACTORY_S_FIRST) + CHK_ERRA(CLASSFACTORY_S_LAST) +// CHK_ERRA(CLASS_E_NOAGGREGATION) + CHK_ERRA(CLASS_E_CLASSNOTAVAILABLE) + CHK_ERRA(CLASS_E_NOTLICENSED) + CHK_ERRA(MARSHAL_E_FIRST) + CHK_ERRA(MARSHAL_E_LAST) + CHK_ERRA(MARSHAL_S_FIRST) + CHK_ERRA(MARSHAL_S_LAST) + CHK_ERRA(DATA_E_FIRST) + CHK_ERRA(DATA_E_LAST) + CHK_ERRA(DATA_S_FIRST) + CHK_ERRA(DATA_S_LAST) + CHK_ERRA(VIEW_E_FIRST) + CHK_ERRA(VIEW_E_LAST) + CHK_ERRA(VIEW_S_FIRST) + CHK_ERRA(VIEW_S_LAST) +// CHK_ERRA(VIEW_E_DRAW) + CHK_ERRA(REGDB_E_FIRST) + CHK_ERRA(REGDB_E_LAST) + CHK_ERRA(REGDB_S_FIRST) + CHK_ERRA(REGDB_S_LAST) +// CHK_ERRA(REGDB_E_READREGDB) + CHK_ERRA(REGDB_E_WRITEREGDB) + CHK_ERRA(REGDB_E_KEYMISSING) + CHK_ERRA(REGDB_E_INVALIDVALUE) + CHK_ERRA(REGDB_E_CLASSNOTREG) + CHK_ERRA(REGDB_E_IIDNOTREG) + CHK_ERRA(CAT_E_FIRST) + CHK_ERRA(CAT_E_LAST) +// CHK_ERRA(CAT_E_CATIDNOEXIST) +// CHK_ERRA(CAT_E_NODESCRIPTION) + CHK_ERRA(CS_E_FIRST) + CHK_ERRA(CS_E_LAST) +// CHK_ERRA(CS_E_PACKAGE_NOTFOUND) + CHK_ERRA(CS_E_NOT_DELETABLE) + CHK_ERRA(CS_E_CLASS_NOTFOUND) + CHK_ERRA(CS_E_INVALID_VERSION) + CHK_ERRA(CS_E_NO_CLASSSTORE) + CHK_ERRA(CS_E_OBJECT_NOTFOUND) + CHK_ERRA(CS_E_OBJECT_ALREADY_EXISTS) + CHK_ERRA(CS_E_INVALID_PATH) + CHK_ERRA(CS_E_NETWORK_ERROR) + CHK_ERRA(CS_E_ADMIN_LIMIT_EXCEEDED) + CHK_ERRA(CS_E_SCHEMA_MISMATCH) +// CHK_ERRA(CS_E_INTERNAL_ERROR) + CHK_ERRA(CACHE_E_FIRST) + CHK_ERRA(CACHE_E_LAST) + CHK_ERRA(CACHE_S_FIRST) + CHK_ERRA(CACHE_S_LAST) +// CHK_ERRA(CACHE_E_NOCACHE_UPDATED) + CHK_ERRA(OLEOBJ_E_FIRST) + CHK_ERRA(OLEOBJ_E_LAST) + CHK_ERRA(OLEOBJ_S_FIRST) + CHK_ERRA(OLEOBJ_S_LAST) +// CHK_ERRA(OLEOBJ_E_NOVERBS) + CHK_ERRA(OLEOBJ_E_INVALIDVERB) + CHK_ERRA(CLIENTSITE_E_FIRST) + CHK_ERRA(CLIENTSITE_E_LAST) + CHK_ERRA(CLIENTSITE_S_FIRST) + CHK_ERRA(CLIENTSITE_S_LAST) + CHK_ERRA(INPLACE_E_NOTUNDOABLE) + CHK_ERRA(INPLACE_E_NOTOOLSPACE) +// CHK_ERRA(INPLACE_E_FIRST) + CHK_ERRA(INPLACE_E_LAST) + CHK_ERRA(INPLACE_S_FIRST) + CHK_ERRA(INPLACE_S_LAST) + CHK_ERRA(ENUM_E_FIRST) + CHK_ERRA(ENUM_E_LAST) + CHK_ERRA(ENUM_S_FIRST) + CHK_ERRA(ENUM_S_LAST) + CHK_ERRA(CONVERT10_E_FIRST) + CHK_ERRA(CONVERT10_E_LAST) + CHK_ERRA(CONVERT10_S_FIRST) + CHK_ERRA(CONVERT10_S_LAST) +// CHK_ERRA(CONVERT10_E_OLESTREAM_GET) + CHK_ERRA(CONVERT10_E_OLESTREAM_PUT) + CHK_ERRA(CONVERT10_E_OLESTREAM_FMT) + CHK_ERRA(CONVERT10_E_OLESTREAM_BITMAP_TO_DIB) + CHK_ERRA(CONVERT10_E_STG_FMT) + CHK_ERRA(CONVERT10_E_STG_NO_STD_STREAM) + CHK_ERRA(CONVERT10_E_STG_DIB_TO_BITMAP) + CHK_ERRA(CLIPBRD_E_FIRST) + CHK_ERRA(CLIPBRD_E_LAST) + CHK_ERRA(CLIPBRD_S_FIRST) + CHK_ERRA(CLIPBRD_S_LAST) +// CHK_ERRA(CLIPBRD_E_CANT_OPEN) + CHK_ERRA(CLIPBRD_E_CANT_EMPTY) + CHK_ERRA(CLIPBRD_E_CANT_SET) + CHK_ERRA(CLIPBRD_E_BAD_DATA) + CHK_ERRA(CLIPBRD_E_CANT_CLOSE) + CHK_ERRA(MK_E_FIRST) + CHK_ERRA(MK_E_LAST) + CHK_ERRA(MK_S_FIRST) + CHK_ERRA(MK_S_LAST) +// CHK_ERRA(MK_E_CONNECTMANUALLY) + CHK_ERRA(MK_E_EXCEEDEDDEADLINE) + CHK_ERRA(MK_E_NEEDGENERIC) + CHK_ERRA(MK_E_UNAVAILABLE) + CHK_ERRA(MK_E_SYNTAX) + CHK_ERRA(MK_E_NOOBJECT) + CHK_ERRA(MK_E_INVALIDEXTENSION) + CHK_ERRA(MK_E_INTERMEDIATEINTERFACENOTSUPPORTED) + CHK_ERRA(MK_E_NOTBINDABLE) + CHK_ERRA(MK_E_NOTBOUND) + CHK_ERRA(MK_E_CANTOPENFILE) + CHK_ERRA(MK_E_MUSTBOTHERUSER) + CHK_ERRA(MK_E_NOINVERSE) + CHK_ERRA(MK_E_NOSTORAGE) + CHK_ERRA(MK_E_NOPREFIX) +// CHK_ERRA(MK_E_ENUMERATION_FAILED) + CHK_ERRA(CO_E_NOTINITIALIZED) + CHK_ERRA(CO_E_ALREADYINITIALIZED) + CHK_ERRA(CO_E_CANTDETERMINECLASS) + CHK_ERRA(CO_E_CLASSSTRING) + CHK_ERRA(CO_E_IIDSTRING) + CHK_ERRA(CO_E_APPNOTFOUND) + CHK_ERRA(CO_E_APPSINGLEUSE) + CHK_ERRA(CO_E_ERRORINAPP) + CHK_ERRA(CO_E_DLLNOTFOUND) + CHK_ERRA(CO_E_ERRORINDLL) + CHK_ERRA(CO_E_WRONGOSFORAPP) + CHK_ERRA(CO_E_OBJNOTREG) + CHK_ERRA(CO_E_OBJISREG) + CHK_ERRA(CO_E_OBJNOTCONNECTED) + CHK_ERRA(CO_E_APPDIDNTREG) + CHK_ERRA(CO_E_RELEASED) +// CHK_ERRA(OLE_S_USEREG) + CHK_ERRA(OLE_S_STATIC) + CHK_ERRA(OLE_S_MAC_CLIPFORMAT) +// CHK_ERRA(DRAGDROP_S_DROP) + CHK_ERRA(DRAGDROP_S_CANCEL) + CHK_ERRA(DRAGDROP_S_USEDEFAULTCURSORS) +// CHK_ERRA(DATA_S_SAMEFORMATETC) +// CHK_ERRA(VIEW_S_ALREADY_FROZEN) +// CHK_ERRA(CACHE_S_FORMATETC_NOTSUPPORTED) + CHK_ERRA(CACHE_S_SAMECACHE) + CHK_ERRA(CACHE_S_SOMECACHES_NOTUPDATED) +// CHK_ERRA(OLEOBJ_S_INVALIDVERB) + CHK_ERRA(OLEOBJ_S_CANNOT_DOVERB_NOW) + CHK_ERRA(OLEOBJ_S_INVALIDHWND) +// CHK_ERRA(INPLACE_S_TRUNCATED) +// CHK_ERRA(CONVERT10_S_NO_PRESENTATION) + CHK_ERRA(MK_S_REDUCED_TO_SELF) + CHK_ERRA(MK_S_ME) + CHK_ERRA(MK_S_HIM) + CHK_ERRA(MK_S_US) + CHK_ERRA(MK_S_MONIKERALREADYREGISTERED) + CHK_ERRA(CO_E_CLASS_CREATE_FAILED) + CHK_ERRA(CO_E_SCM_ERROR) + CHK_ERRA(CO_E_SCM_RPC_FAILURE) + CHK_ERRA(CO_E_BAD_PATH) + CHK_ERRA(CO_E_SERVER_EXEC_FAILURE) + CHK_ERRA(CO_E_OBJSRV_RPC_FAILURE) + CHK_ERRA(MK_E_NO_NORMALIZED) + CHK_ERRA(CO_E_SERVER_STOPPING) + CHK_ERRA(MEM_E_INVALID_ROOT) + CHK_ERRA(MEM_E_INVALID_LINK) + CHK_ERRA(MEM_E_INVALID_SIZE) + CHK_ERRA(CO_S_NOTALLINTERFACES) + CHK_ERRA(DISP_E_UNKNOWNINTERFACE) + CHK_ERRA(DISP_E_MEMBERNOTFOUND) + CHK_ERRA(DISP_E_PARAMNOTFOUND) + CHK_ERRA(DISP_E_TYPEMISMATCH) + CHK_ERRA(DISP_E_UNKNOWNNAME) + CHK_ERRA(DISP_E_NONAMEDARGS) + CHK_ERRA(DISP_E_BADVARTYPE) + CHK_ERRA(DISP_E_EXCEPTION) + CHK_ERRA(DISP_E_OVERFLOW) + CHK_ERRA(DISP_E_BADINDEX) + CHK_ERRA(DISP_E_UNKNOWNLCID) + CHK_ERRA(DISP_E_ARRAYISLOCKED) + CHK_ERRA(DISP_E_BADPARAMCOUNT) + CHK_ERRA(DISP_E_PARAMNOTOPTIONAL) + CHK_ERRA(DISP_E_BADCALLEE) + CHK_ERRA(DISP_E_NOTACOLLECTION) + CHK_ERRA(DISP_E_DIVBYZERO) + CHK_ERRA(DISP_E_BUFFERTOOSMALL) + CHK_ERRA(TYPE_E_BUFFERTOOSMALL) + CHK_ERRA(TYPE_E_FIELDNOTFOUND) + CHK_ERRA(TYPE_E_INVDATAREAD) + CHK_ERRA(TYPE_E_UNSUPFORMAT) + CHK_ERRA(TYPE_E_REGISTRYACCESS) + CHK_ERRA(TYPE_E_LIBNOTREGISTERED) + CHK_ERRA(TYPE_E_UNDEFINEDTYPE) + CHK_ERRA(TYPE_E_QUALIFIEDNAMEDISALLOWED) + CHK_ERRA(TYPE_E_INVALIDSTATE) + CHK_ERRA(TYPE_E_WRONGTYPEKIND) + CHK_ERRA(TYPE_E_ELEMENTNOTFOUND) + CHK_ERRA(TYPE_E_AMBIGUOUSNAME) + CHK_ERRA(TYPE_E_NAMECONFLICT) + CHK_ERRA(TYPE_E_UNKNOWNLCID) + CHK_ERRA(TYPE_E_DLLFUNCTIONNOTFOUND) + CHK_ERRA(TYPE_E_BADMODULEKIND) + CHK_ERRA(TYPE_E_SIZETOOBIG) + CHK_ERRA(TYPE_E_DUPLICATEID) + CHK_ERRA(TYPE_E_INVALIDID) + CHK_ERRA(TYPE_E_TYPEMISMATCH) + CHK_ERRA(TYPE_E_OUTOFBOUNDS) + CHK_ERRA(TYPE_E_IOERROR) + CHK_ERRA(TYPE_E_CANTCREATETMPFILE) + CHK_ERRA(TYPE_E_CANTLOADLIBRARY) + CHK_ERRA(TYPE_E_INCONSISTENTPROPFUNCS) + CHK_ERRA(TYPE_E_CIRCULARTYPE) + CHK_ERRA(STG_E_INVALIDFUNCTION) + CHK_ERRA(STG_E_FILENOTFOUND) + CHK_ERRA(STG_E_PATHNOTFOUND) + CHK_ERRA(STG_E_TOOMANYOPENFILES) + CHK_ERRA(STG_E_ACCESSDENIED) + CHK_ERRA(STG_E_INVALIDHANDLE) + CHK_ERRA(STG_E_INSUFFICIENTMEMORY) + CHK_ERRA(STG_E_INVALIDPOINTER) + CHK_ERRA(STG_E_NOMOREFILES) + CHK_ERRA(STG_E_DISKISWRITEPROTECTED) + CHK_ERRA(STG_E_SEEKERROR) + CHK_ERRA(STG_E_WRITEFAULT) + CHK_ERRA(STG_E_READFAULT) + CHK_ERRA(STG_E_SHAREVIOLATION) + CHK_ERRA(STG_E_LOCKVIOLATION) + CHK_ERRA(STG_E_FILEALREADYEXISTS) + CHK_ERRA(STG_E_INVALIDPARAMETER) + CHK_ERRA(STG_E_MEDIUMFULL) + CHK_ERRA(STG_E_PROPSETMISMATCHED) + CHK_ERRA(STG_E_ABNORMALAPIEXIT) + CHK_ERRA(STG_E_INVALIDHEADER) + CHK_ERRA(STG_E_INVALIDNAME) + CHK_ERRA(STG_E_UNKNOWN) + CHK_ERRA(STG_E_UNIMPLEMENTEDFUNCTION) + CHK_ERRA(STG_E_INVALIDFLAG) + CHK_ERRA(STG_E_INUSE) + CHK_ERRA(STG_E_NOTCURRENT) + CHK_ERRA(STG_E_REVERTED) + CHK_ERRA(STG_E_CANTSAVE) + CHK_ERRA(STG_E_OLDFORMAT) + CHK_ERRA(STG_E_OLDDLL) + CHK_ERRA(STG_E_SHAREREQUIRED) + CHK_ERRA(STG_E_NOTFILEBASEDSTORAGE) + CHK_ERRA(STG_E_EXTANTMARSHALLINGS) + CHK_ERRA(STG_E_DOCFILECORRUPT) + CHK_ERRA(STG_E_BADBASEADDRESS) + CHK_ERRA(STG_E_DOCFILETOOLARGE) + CHK_ERRA(STG_E_NOTSIMPLEFORMAT) + CHK_ERRA(STG_E_INCOMPLETE) + CHK_ERRA(STG_E_TERMINATED) + CHK_ERRA(STG_S_CONVERTED) + CHK_ERRA(STG_S_BLOCK) + CHK_ERRA(STG_S_RETRYNOW) + CHK_ERRA(STG_S_MONITORING) + CHK_ERRA(STG_S_MULTIPLEOPENS) + CHK_ERRA(STG_S_CONSOLIDATIONFAILED) + CHK_ERRA(STG_S_CANNOTCONSOLIDATE) + CHK_ERRA(RPC_E_CALL_REJECTED) + CHK_ERRA(RPC_E_CALL_CANCELED) + CHK_ERRA(RPC_E_CANTPOST_INSENDCALL) + CHK_ERRA(RPC_E_CANTCALLOUT_INASYNCCALL) + CHK_ERRA(RPC_E_CANTCALLOUT_INEXTERNALCALL) + CHK_ERRA(RPC_E_CONNECTION_TERMINATED) + CHK_ERRA(RPC_E_SERVER_DIED) + CHK_ERRA(RPC_E_CLIENT_DIED) + CHK_ERRA(RPC_E_INVALID_DATAPACKET) + CHK_ERRA(RPC_E_CANTTRANSMIT_CALL) + CHK_ERRA(RPC_E_CLIENT_CANTMARSHAL_DATA) + CHK_ERRA(RPC_E_CLIENT_CANTUNMARSHAL_DATA) + CHK_ERRA(RPC_E_SERVER_CANTMARSHAL_DATA) + CHK_ERRA(RPC_E_SERVER_CANTUNMARSHAL_DATA) + CHK_ERRA(RPC_E_INVALID_DATA) + CHK_ERRA(RPC_E_INVALID_PARAMETER) + CHK_ERRA(RPC_E_CANTCALLOUT_AGAIN) + CHK_ERRA(RPC_E_SERVER_DIED_DNE) + CHK_ERRA(RPC_E_SYS_CALL_FAILED) + CHK_ERRA(RPC_E_OUT_OF_RESOURCES) + CHK_ERRA(RPC_E_ATTEMPTED_MULTITHREAD) + CHK_ERRA(RPC_E_NOT_REGISTERED) + CHK_ERRA(RPC_E_FAULT) + CHK_ERRA(RPC_E_SERVERFAULT) + CHK_ERRA(RPC_E_CHANGED_MODE) + CHK_ERRA(RPC_E_INVALIDMETHOD) + CHK_ERRA(RPC_E_DISCONNECTED) + CHK_ERRA(RPC_E_RETRY) + CHK_ERRA(RPC_E_SERVERCALL_RETRYLATER) + CHK_ERRA(RPC_E_SERVERCALL_REJECTED) + CHK_ERRA(RPC_E_INVALID_CALLDATA) + CHK_ERRA(RPC_E_CANTCALLOUT_ININPUTSYNCCALL) + CHK_ERRA(RPC_E_WRONG_THREAD) + CHK_ERRA(RPC_E_THREAD_NOT_INIT) + CHK_ERRA(RPC_E_VERSION_MISMATCH) + CHK_ERRA(RPC_E_INVALID_HEADER) + CHK_ERRA(RPC_E_INVALID_EXTENSION) + CHK_ERRA(RPC_E_INVALID_IPID) + CHK_ERRA(RPC_E_INVALID_OBJECT) + CHK_ERRA(RPC_S_CALLPENDING) + CHK_ERRA(RPC_S_WAITONTIMER) + CHK_ERRA(RPC_E_CALL_COMPLETE) + CHK_ERRA(RPC_E_UNSECURE_CALL) + CHK_ERRA(RPC_E_TOO_LATE) + CHK_ERRA(RPC_E_NO_GOOD_SECURITY_PACKAGES) + CHK_ERRA(RPC_E_ACCESS_DENIED) + CHK_ERRA(RPC_E_REMOTE_DISABLED) + CHK_ERRA(RPC_E_INVALID_OBJREF) + CHK_ERRA(RPC_E_NO_CONTEXT) + CHK_ERRA(RPC_E_TIMEOUT) + CHK_ERRA(RPC_E_NO_SYNC) + CHK_ERRA(RPC_E_FULLSIC_REQUIRED) + CHK_ERRA(RPC_E_INVALID_STD_NAME) + CHK_ERRA(CO_E_FAILEDTOIMPERSONATE) + CHK_ERRA(CO_E_FAILEDTOGETSECCTX) + CHK_ERRA(CO_E_FAILEDTOOPENTHREADTOKEN) + CHK_ERRA(CO_E_FAILEDTOGETTOKENINFO) + CHK_ERRA(CO_E_TRUSTEEDOESNTMATCHCLIENT) + CHK_ERRA(CO_E_FAILEDTOQUERYCLIENTBLANKET) + CHK_ERRA(CO_E_FAILEDTOSETDACL) + CHK_ERRA(CO_E_ACCESSCHECKFAILED) + CHK_ERRA(CO_E_NETACCESSAPIFAILED) + CHK_ERRA(CO_E_WRONGTRUSTEENAMESYNTAX) + CHK_ERRA(CO_E_INVALIDSID) + CHK_ERRA(CO_E_CONVERSIONFAILED) + CHK_ERRA(CO_E_NOMATCHINGSIDFOUND) + CHK_ERRA(CO_E_LOOKUPACCSIDFAILED) + CHK_ERRA(CO_E_NOMATCHINGNAMEFOUND) + CHK_ERRA(CO_E_LOOKUPACCNAMEFAILED) + CHK_ERRA(CO_E_SETSERLHNDLFAILED) + CHK_ERRA(CO_E_FAILEDTOGETWINDIR) + CHK_ERRA(CO_E_PATHTOOLONG) + CHK_ERRA(CO_E_FAILEDTOGENUUID) + CHK_ERRA(CO_E_FAILEDTOCREATEFILE) + CHK_ERRA(CO_E_FAILEDTOCLOSEHANDLE) + CHK_ERRA(CO_E_EXCEEDSYSACLLIMIT) + CHK_ERRA(CO_E_ACESINWRONGORDER) + CHK_ERRA(CO_E_INCOMPATIBLESTREAMVERSION) + CHK_ERRA(CO_E_FAILEDTOOPENPROCESSTOKEN) + CHK_ERRA(CO_E_DECODEFAILED) + CHK_ERRA(CO_E_ACNOTINITIALIZED) + CHK_ERRA(RPC_E_UNEXPECTED) + CHK_ERRA(NTE_BAD_UID) + CHK_ERRA(NTE_BAD_HASH) + CHK_ERRA(NTE_BAD_KEY) + CHK_ERRA(NTE_BAD_LEN) + CHK_ERRA(NTE_BAD_DATA) + CHK_ERRA(NTE_BAD_SIGNATURE) + CHK_ERRA(NTE_BAD_VER) + CHK_ERRA(NTE_BAD_ALGID) + CHK_ERRA(NTE_BAD_FLAGS) + CHK_ERRA(NTE_BAD_TYPE) + CHK_ERRA(NTE_BAD_KEY_STATE) + CHK_ERRA(NTE_BAD_HASH_STATE) + CHK_ERRA(NTE_NO_KEY) + CHK_ERRA(NTE_NO_MEMORY) + CHK_ERRA(NTE_EXISTS) + CHK_ERRA(NTE_PERM) + CHK_ERRA(NTE_NOT_FOUND) + CHK_ERRA(NTE_DOUBLE_ENCRYPT) + CHK_ERRA(NTE_BAD_PROVIDER) + CHK_ERRA(NTE_BAD_PROV_TYPE) + CHK_ERRA(NTE_BAD_PUBLIC_KEY) + CHK_ERRA(NTE_BAD_KEYSET) + CHK_ERRA(NTE_PROV_TYPE_NOT_DEF) + CHK_ERRA(NTE_PROV_TYPE_ENTRY_BAD) + CHK_ERRA(NTE_KEYSET_NOT_DEF) + CHK_ERRA(NTE_KEYSET_ENTRY_BAD) + CHK_ERRA(NTE_PROV_TYPE_NO_MATCH) + CHK_ERRA(NTE_SIGNATURE_FILE_BAD) + CHK_ERRA(NTE_PROVIDER_DLL_FAIL) + CHK_ERRA(NTE_PROV_DLL_NOT_FOUND) + CHK_ERRA(NTE_BAD_KEYSET_PARAM) + CHK_ERRA(NTE_FAIL) + CHK_ERRA(NTE_SYS_ERR) + CHK_ERRA(NTE_SILENT_CONTEXT) + CHK_ERRA(NTE_TOKEN_KEYSET_STORAGE_FULL) + CHK_ERRA(CRYPT_E_MSG_ERROR) + CHK_ERRA(CRYPT_E_UNKNOWN_ALGO) + CHK_ERRA(CRYPT_E_OID_FORMAT) + CHK_ERRA(CRYPT_E_INVALID_MSG_TYPE) + CHK_ERRA(CRYPT_E_UNEXPECTED_ENCODING) + CHK_ERRA(CRYPT_E_AUTH_ATTR_MISSING) + CHK_ERRA(CRYPT_E_HASH_VALUE) + CHK_ERRA(CRYPT_E_INVALID_INDEX) + CHK_ERRA(CRYPT_E_ALREADY_DECRYPTED) + CHK_ERRA(CRYPT_E_NOT_DECRYPTED) + CHK_ERRA(CRYPT_E_RECIPIENT_NOT_FOUND) + CHK_ERRA(CRYPT_E_CONTROL_TYPE) + CHK_ERRA(CRYPT_E_ISSUER_SERIALNUMBER) + CHK_ERRA(CRYPT_E_SIGNER_NOT_FOUND) + CHK_ERRA(CRYPT_E_ATTRIBUTES_MISSING) + CHK_ERRA(CRYPT_E_STREAM_MSG_NOT_READY) + CHK_ERRA(CRYPT_E_STREAM_INSUFFICIENT_DATA) + CHK_ERRA(CRYPT_E_BAD_LEN) + CHK_ERRA(CRYPT_E_BAD_ENCODE) + CHK_ERRA(CRYPT_E_FILE_ERROR) + CHK_ERRA(CRYPT_E_NOT_FOUND) + CHK_ERRA(CRYPT_E_EXISTS) + CHK_ERRA(CRYPT_E_NO_PROVIDER) + CHK_ERRA(CRYPT_E_SELF_SIGNED) + CHK_ERRA(CRYPT_E_DELETED_PREV) + CHK_ERRA(CRYPT_E_NO_MATCH) + CHK_ERRA(CRYPT_E_UNEXPECTED_MSG_TYPE) + CHK_ERRA(CRYPT_E_NO_KEY_PROPERTY) + CHK_ERRA(CRYPT_E_NO_DECRYPT_CERT) + CHK_ERRA(CRYPT_E_BAD_MSG) + CHK_ERRA(CRYPT_E_NO_SIGNER) + CHK_ERRA(CRYPT_E_PENDING_CLOSE) + CHK_ERRA(CRYPT_E_REVOKED) + CHK_ERRA(CRYPT_E_NO_REVOCATION_DLL) + CHK_ERRA(CRYPT_E_NO_REVOCATION_CHECK) + CHK_ERRA(CRYPT_E_REVOCATION_OFFLINE) + CHK_ERRA(CRYPT_E_NOT_IN_REVOCATION_DATABASE) + CHK_ERRA(CRYPT_E_INVALID_NUMERIC_STRING) + CHK_ERRA(CRYPT_E_INVALID_PRINTABLE_STRING) + CHK_ERRA(CRYPT_E_INVALID_IA5_STRING) + CHK_ERRA(CRYPT_E_INVALID_X500_STRING) + CHK_ERRA(CRYPT_E_NOT_CHAR_STRING) + CHK_ERRA(CRYPT_E_FILERESIZED) + CHK_ERRA(CRYPT_E_SECURITY_SETTINGS) + CHK_ERRA(CRYPT_E_NO_VERIFY_USAGE_DLL) + CHK_ERRA(CRYPT_E_NO_VERIFY_USAGE_CHECK) + CHK_ERRA(CRYPT_E_VERIFY_USAGE_OFFLINE) + CHK_ERRA(CRYPT_E_NOT_IN_CTL) + CHK_ERRA(CRYPT_E_NO_TRUSTED_SIGNER) + CHK_ERRA(CRYPT_E_OSS_ERROR) + CHK_ERRA(OSS_MORE_BUF) + CHK_ERRA(OSS_NEGATIVE_UINTEGER) + CHK_ERRA(OSS_PDU_RANGE) + CHK_ERRA(OSS_MORE_INPUT) + CHK_ERRA(OSS_DATA_ERROR) + CHK_ERRA(OSS_BAD_ARG) + CHK_ERRA(OSS_BAD_VERSION) + CHK_ERRA(OSS_OUT_MEMORY) + CHK_ERRA(OSS_PDU_MISMATCH) + CHK_ERRA(OSS_LIMITED) + CHK_ERRA(OSS_BAD_PTR) + CHK_ERRA(OSS_BAD_TIME) + CHK_ERRA(OSS_INDEFINITE_NOT_SUPPORTED) + CHK_ERRA(OSS_MEM_ERROR) + CHK_ERRA(OSS_BAD_TABLE) + CHK_ERRA(OSS_TOO_LONG) + CHK_ERRA(OSS_CONSTRAINT_VIOLATED) + CHK_ERRA(OSS_FATAL_ERROR) + CHK_ERRA(OSS_ACCESS_SERIALIZATION_ERROR) + CHK_ERRA(OSS_NULL_TBL) + CHK_ERRA(OSS_NULL_FCN) + CHK_ERRA(OSS_BAD_ENCRULES) + CHK_ERRA(OSS_UNAVAIL_ENCRULES) + CHK_ERRA(OSS_CANT_OPEN_TRACE_WINDOW) + CHK_ERRA(OSS_UNIMPLEMENTED) + CHK_ERRA(OSS_OID_DLL_NOT_LINKED) + CHK_ERRA(OSS_CANT_OPEN_TRACE_FILE) + CHK_ERRA(OSS_TRACE_FILE_ALREADY_OPEN) + CHK_ERRA(OSS_TABLE_MISMATCH) + CHK_ERRA(OSS_TYPE_NOT_SUPPORTED) + CHK_ERRA(OSS_REAL_DLL_NOT_LINKED) + CHK_ERRA(OSS_REAL_CODE_NOT_LINKED) + CHK_ERRA(OSS_OUT_OF_RANGE) + CHK_ERRA(OSS_COPIER_DLL_NOT_LINKED) + CHK_ERRA(OSS_CONSTRAINT_DLL_NOT_LINKED) + CHK_ERRA(OSS_COMPARATOR_DLL_NOT_LINKED) + CHK_ERRA(OSS_COMPARATOR_CODE_NOT_LINKED) + CHK_ERRA(OSS_MEM_MGR_DLL_NOT_LINKED) + CHK_ERRA(OSS_PDV_DLL_NOT_LINKED) + CHK_ERRA(OSS_PDV_CODE_NOT_LINKED) + CHK_ERRA(OSS_API_DLL_NOT_LINKED) + CHK_ERRA(OSS_BERDER_DLL_NOT_LINKED) + CHK_ERRA(OSS_PER_DLL_NOT_LINKED) + CHK_ERRA(OSS_OPEN_TYPE_ERROR) + CHK_ERRA(OSS_MUTEX_NOT_CREATED) + CHK_ERRA(OSS_CANT_CLOSE_TRACE_FILE) + CHK_ERRA(CERTSRV_E_BAD_REQUESTSUBJECT) + CHK_ERRA(CERTSRV_E_NO_REQUEST) + CHK_ERRA(CERTSRV_E_BAD_REQUESTSTATUS) + CHK_ERRA(CERTSRV_E_PROPERTY_EMPTY) + CHK_ERRA(CERTSRV_E_INVALID_CA_CERTIFICATE) + CHK_ERRA(CERTSRV_E_UNSUPPORTED_CERT_TYPE) + CHK_ERRA(CERTSRV_E_NO_CERT_TYPE) + CHK_ERRA(TRUST_E_SYSTEM_ERROR) + CHK_ERRA(TRUST_E_NO_SIGNER_CERT) + CHK_ERRA(TRUST_E_COUNTER_SIGNER) + CHK_ERRA(TRUST_E_CERT_SIGNATURE) + CHK_ERRA(TRUST_E_TIME_STAMP) + CHK_ERRA(TRUST_E_BAD_DIGEST) + CHK_ERRA(TRUST_E_BASIC_CONSTRAINTS) + CHK_ERRA(TRUST_E_FINANCIAL_CRITERIA) +// CHK_ERRA(NTE_OP_OK) + CHK_ERRA(TRUST_E_PROVIDER_UNKNOWN) + CHK_ERRA(TRUST_E_ACTION_UNKNOWN) + CHK_ERRA(TRUST_E_SUBJECT_FORM_UNKNOWN) + CHK_ERRA(TRUST_E_SUBJECT_NOT_TRUSTED) + CHK_ERRA(DIGSIG_E_ENCODE) + CHK_ERRA(DIGSIG_E_DECODE) + CHK_ERRA(DIGSIG_E_EXTENSIBILITY) + CHK_ERRA(DIGSIG_E_CRYPTO) + CHK_ERRA(PERSIST_E_SIZEDEFINITE) + CHK_ERRA(PERSIST_E_SIZEINDEFINITE) + CHK_ERRA(PERSIST_E_NOTSELFSIZING) + CHK_ERRA(TRUST_E_NOSIGNATURE) + CHK_ERRA(CERT_E_EXPIRED) + CHK_ERRA(CERT_E_VALIDITYPERIODNESTING) + CHK_ERRA(CERT_E_ROLE) + CHK_ERRA(CERT_E_PATHLENCONST) + CHK_ERRA(CERT_E_CRITICAL) + CHK_ERRA(CERT_E_PURPOSE) + CHK_ERRA(CERT_E_ISSUERCHAINING) + CHK_ERRA(CERT_E_MALFORMED) + CHK_ERRA(CERT_E_UNTRUSTEDROOT) + CHK_ERRA(CERT_E_CHAINING) + CHK_ERRA(TRUST_E_FAIL) + CHK_ERRA(CERT_E_REVOKED) + CHK_ERRA(CERT_E_UNTRUSTEDTESTROOT) + CHK_ERRA(CERT_E_REVOCATION_FAILURE) + CHK_ERRA(CERT_E_CN_NO_MATCH) + CHK_ERRA(CERT_E_WRONG_USAGE) + CHK_ERRA(SPAPI_E_EXPECTED_SECTION_NAME) + CHK_ERRA(SPAPI_E_BAD_SECTION_NAME_LINE) + CHK_ERRA(SPAPI_E_SECTION_NAME_TOO_LONG) + CHK_ERRA(SPAPI_E_GENERAL_SYNTAX) + CHK_ERRA(SPAPI_E_WRONG_INF_STYLE) + CHK_ERRA(SPAPI_E_SECTION_NOT_FOUND) + CHK_ERRA(SPAPI_E_LINE_NOT_FOUND) + CHK_ERRA(SPAPI_E_NO_BACKUP) + CHK_ERRA(SPAPI_E_NO_ASSOCIATED_CLASS) + CHK_ERRA(SPAPI_E_CLASS_MISMATCH) + CHK_ERRA(SPAPI_E_DUPLICATE_FOUND) + CHK_ERRA(SPAPI_E_NO_DRIVER_SELECTED) + CHK_ERRA(SPAPI_E_KEY_DOES_NOT_EXIST) + CHK_ERRA(SPAPI_E_INVALID_DEVINST_NAME) + CHK_ERRA(SPAPI_E_INVALID_CLASS) + CHK_ERRA(SPAPI_E_DEVINST_ALREADY_EXISTS) + CHK_ERRA(SPAPI_E_DEVINFO_NOT_REGISTERED) + CHK_ERRA(SPAPI_E_INVALID_REG_PROPERTY) + CHK_ERRA(SPAPI_E_NO_INF) + CHK_ERRA(SPAPI_E_NO_SUCH_DEVINST) + CHK_ERRA(SPAPI_E_CANT_LOAD_CLASS_ICON) + CHK_ERRA(SPAPI_E_INVALID_CLASS_INSTALLER) + CHK_ERRA(SPAPI_E_DI_DO_DEFAULT) + CHK_ERRA(SPAPI_E_DI_NOFILECOPY) + CHK_ERRA(SPAPI_E_INVALID_HWPROFILE) + CHK_ERRA(SPAPI_E_NO_DEVICE_SELECTED) + CHK_ERRA(SPAPI_E_DEVINFO_LIST_LOCKED) + CHK_ERRA(SPAPI_E_DEVINFO_DATA_LOCKED) + CHK_ERRA(SPAPI_E_DI_BAD_PATH) + CHK_ERRA(SPAPI_E_NO_CLASSINSTALL_PARAMS) + CHK_ERRA(SPAPI_E_FILEQUEUE_LOCKED) + CHK_ERRA(SPAPI_E_BAD_SERVICE_INSTALLSECT) + CHK_ERRA(SPAPI_E_NO_CLASS_DRIVER_LIST) + CHK_ERRA(SPAPI_E_NO_ASSOCIATED_SERVICE) + CHK_ERRA(SPAPI_E_NO_DEFAULT_DEVICE_INTERFACE) + CHK_ERRA(SPAPI_E_DEVICE_INTERFACE_ACTIVE) + CHK_ERRA(SPAPI_E_DEVICE_INTERFACE_REMOVED) + CHK_ERRA(SPAPI_E_BAD_INTERFACE_INSTALLSECT) + CHK_ERRA(SPAPI_E_NO_SUCH_INTERFACE_CLASS) + CHK_ERRA(SPAPI_E_INVALID_REFERENCE_STRING) + CHK_ERRA(SPAPI_E_INVALID_MACHINENAME) + CHK_ERRA(SPAPI_E_REMOTE_COMM_FAILURE) + CHK_ERRA(SPAPI_E_MACHINE_UNAVAILABLE) + CHK_ERRA(SPAPI_E_NO_CONFIGMGR_SERVICES) + CHK_ERRA(SPAPI_E_INVALID_PROPPAGE_PROVIDER) + CHK_ERRA(SPAPI_E_NO_SUCH_DEVICE_INTERFACE) + CHK_ERRA(SPAPI_E_DI_POSTPROCESSING_REQUIRED) + CHK_ERRA(SPAPI_E_INVALID_COINSTALLER) + CHK_ERRA(SPAPI_E_NO_COMPAT_DRIVERS) + CHK_ERRA(SPAPI_E_NO_DEVICE_ICON) + CHK_ERRA(SPAPI_E_INVALID_INF_LOGCONFIG) + CHK_ERRA(SPAPI_E_DI_DONT_INSTALL) + CHK_ERRA(SPAPI_E_INVALID_FILTER_DRIVER) + CHK_ERRA(SPAPI_E_NON_WINDOWS_NT_DRIVER) + CHK_ERRA(SPAPI_E_NON_WINDOWS_DRIVER) + CHK_ERRA(SPAPI_E_NO_CATALOG_FOR_OEM_INF) + CHK_ERRA(SPAPI_E_DEVINSTALL_QUEUE_NONNATIVE) + CHK_ERRA(SPAPI_E_ERROR_NOT_INSTALLED) +// CHK_ERRA(SCARD_S_SUCCESS) + CHK_ERRA(SCARD_F_INTERNAL_ERROR) + CHK_ERRA(SCARD_E_CANCELLED) + CHK_ERRA(SCARD_E_INVALID_HANDLE) + CHK_ERRA(SCARD_E_INVALID_PARAMETER) + CHK_ERRA(SCARD_E_INVALID_TARGET) + CHK_ERRA(SCARD_E_NO_MEMORY) + CHK_ERRA(SCARD_F_WAITED_TOO_LONG) + CHK_ERRA(SCARD_E_INSUFFICIENT_BUFFER) + CHK_ERRA(SCARD_E_UNKNOWN_READER) + CHK_ERRA(SCARD_E_TIMEOUT) + CHK_ERRA(SCARD_E_SHARING_VIOLATION) + CHK_ERRA(SCARD_E_NO_SMARTCARD) + CHK_ERRA(SCARD_E_UNKNOWN_CARD) + CHK_ERRA(SCARD_E_CANT_DISPOSE) + CHK_ERRA(SCARD_E_PROTO_MISMATCH) + CHK_ERRA(SCARD_E_NOT_READY) + CHK_ERRA(SCARD_E_INVALID_VALUE) + CHK_ERRA(SCARD_E_SYSTEM_CANCELLED) + CHK_ERRA(SCARD_F_COMM_ERROR) + CHK_ERRA(SCARD_F_UNKNOWN_ERROR) + CHK_ERRA(SCARD_E_INVALID_ATR) + CHK_ERRA(SCARD_E_NOT_TRANSACTED) + CHK_ERRA(SCARD_E_READER_UNAVAILABLE) + CHK_ERRA(SCARD_P_SHUTDOWN) + CHK_ERRA(SCARD_E_PCI_TOO_SMALL) + CHK_ERRA(SCARD_E_READER_UNSUPPORTED) + CHK_ERRA(SCARD_E_DUPLICATE_READER) + CHK_ERRA(SCARD_E_CARD_UNSUPPORTED) + CHK_ERRA(SCARD_E_NO_SERVICE) + CHK_ERRA(SCARD_E_SERVICE_STOPPED) + CHK_ERRA(SCARD_E_UNEXPECTED) + CHK_ERRA(SCARD_E_ICC_INSTALLATION) + CHK_ERRA(SCARD_E_ICC_CREATEORDER) + CHK_ERRA(SCARD_E_UNSUPPORTED_FEATURE) + CHK_ERRA(SCARD_E_DIR_NOT_FOUND) + CHK_ERRA(SCARD_E_FILE_NOT_FOUND) + CHK_ERRA(SCARD_E_NO_DIR) + CHK_ERRA(SCARD_E_NO_FILE) + CHK_ERRA(SCARD_E_NO_ACCESS) + CHK_ERRA(SCARD_E_WRITE_TOO_MANY) + CHK_ERRA(SCARD_E_BAD_SEEK) + CHK_ERRA(SCARD_E_INVALID_CHV) + CHK_ERRA(SCARD_E_UNKNOWN_RES_MNG) + CHK_ERRA(SCARD_E_NO_SUCH_CERTIFICATE) + CHK_ERRA(SCARD_E_CERTIFICATE_UNAVAILABLE) + CHK_ERRA(SCARD_E_NO_READERS_AVAILABLE) + CHK_ERRA(SCARD_E_COMM_DATA_LOST) + CHK_ERRA(SCARD_W_UNSUPPORTED_CARD) + CHK_ERRA(SCARD_W_UNRESPONSIVE_CARD) + CHK_ERRA(SCARD_W_UNPOWERED_CARD) + CHK_ERRA(SCARD_W_RESET_CARD) + CHK_ERRA(SCARD_W_REMOVED_CARD) + CHK_ERRA(SCARD_W_SECURITY_VIOLATION) + CHK_ERRA(SCARD_W_WRONG_CHV) + CHK_ERRA(SCARD_W_CHV_BLOCKED) + CHK_ERRA(SCARD_W_EOF) + CHK_ERRA(SCARD_W_CANCELLED_BY_USER) + CHK_ERR_WIN32_ONLY(ERROR_INVALID_FUNCTION, "ERROR_INVALID_FUNCTION") + CHK_ERR_WIN32A(ERROR_FILE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_PATH_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_TOO_MANY_OPEN_FILES) + CHK_ERRA(ERROR_ACCESS_DENIED) + CHK_ERRA(ERROR_INVALID_HANDLE) + CHK_ERR_WIN32A(ERROR_ARENA_TRASHED) + CHK_ERR_WIN32A(ERROR_NOT_ENOUGH_MEMORY) + CHK_ERR_WIN32A(ERROR_INVALID_BLOCK) + CHK_ERR_WIN32A(ERROR_BAD_ENVIRONMENT) + CHK_ERR_WIN32A(ERROR_BAD_FORMAT) + CHK_ERR_WIN32A(ERROR_INVALID_ACCESS) + CHK_ERR_WIN32A(ERROR_INVALID_DATA) + CHK_ERRA(ERROR_OUTOFMEMORY) + CHK_ERR_WIN32A(ERROR_INVALID_DRIVE) + CHK_ERR_WIN32A(ERROR_CURRENT_DIRECTORY) + CHK_ERR_WIN32A(ERROR_NOT_SAME_DEVICE) + CHK_ERR_WIN32A(ERROR_NO_MORE_FILES) + CHK_ERR_WIN32A(ERROR_WRITE_PROTECT) + CHK_ERR_WIN32A(ERROR_BAD_UNIT) + CHK_ERR_WIN32A(ERROR_NOT_READY) + CHK_ERR_WIN32A(ERROR_BAD_COMMAND) + CHK_ERR_WIN32A(ERROR_CRC) + CHK_ERR_WIN32A(ERROR_BAD_LENGTH) + CHK_ERR_WIN32A(ERROR_SEEK) + CHK_ERR_WIN32A(ERROR_NOT_DOS_DISK) + CHK_ERR_WIN32A(ERROR_SECTOR_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_OUT_OF_PAPER) + CHK_ERR_WIN32A(ERROR_WRITE_FAULT) + CHK_ERR_WIN32A(ERROR_READ_FAULT) + CHK_ERR_WIN32A(ERROR_GEN_FAILURE) + CHK_ERR_WIN32A(ERROR_SHARING_VIOLATION) + CHK_ERR_WIN32A(ERROR_LOCK_VIOLATION) + CHK_ERR_WIN32A(ERROR_WRONG_DISK) + CHK_ERR_WIN32A(ERROR_SHARING_BUFFER_EXCEEDED) + CHK_ERR_WIN32A(ERROR_HANDLE_EOF) + CHK_ERR_WIN32A(ERROR_HANDLE_DISK_FULL) + CHK_ERR_WIN32A(ERROR_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_REM_NOT_LIST) + CHK_ERR_WIN32A(ERROR_DUP_NAME) + CHK_ERR_WIN32A(ERROR_BAD_NETPATH) + CHK_ERR_WIN32A(ERROR_NETWORK_BUSY) + CHK_ERR_WIN32A(ERROR_DEV_NOT_EXIST) + CHK_ERR_WIN32A(ERROR_TOO_MANY_CMDS) + CHK_ERR_WIN32A(ERROR_ADAP_HDW_ERR) + CHK_ERR_WIN32A(ERROR_BAD_NET_RESP) + CHK_ERR_WIN32A(ERROR_UNEXP_NET_ERR) + CHK_ERR_WIN32A(ERROR_BAD_REM_ADAP) + CHK_ERR_WIN32A(ERROR_PRINTQ_FULL) + CHK_ERR_WIN32A(ERROR_NO_SPOOL_SPACE) + CHK_ERR_WIN32A(ERROR_PRINT_CANCELLED) + CHK_ERR_WIN32A(ERROR_NETNAME_DELETED) + CHK_ERR_WIN32A(ERROR_NETWORK_ACCESS_DENIED) + CHK_ERR_WIN32A(ERROR_BAD_DEV_TYPE) + CHK_ERR_WIN32A(ERROR_BAD_NET_NAME) + CHK_ERR_WIN32A(ERROR_TOO_MANY_NAMES) + CHK_ERR_WIN32A(ERROR_TOO_MANY_SESS) + CHK_ERR_WIN32A(ERROR_SHARING_PAUSED) + CHK_ERR_WIN32A(ERROR_REQ_NOT_ACCEP) + CHK_ERR_WIN32A(ERROR_REDIR_PAUSED) + CHK_ERR_WIN32A(ERROR_FILE_EXISTS) + CHK_ERR_WIN32A(ERROR_CANNOT_MAKE) + CHK_ERR_WIN32A(ERROR_FAIL_I24) + CHK_ERR_WIN32A(ERROR_OUT_OF_STRUCTURES) + CHK_ERR_WIN32A(ERROR_ALREADY_ASSIGNED) + CHK_ERR_WIN32A(ERROR_INVALID_PASSWORD) + CHK_ERRA(ERROR_INVALID_PARAMETER) + CHK_ERR_WIN32A(ERROR_NET_WRITE_FAULT) + CHK_ERR_WIN32A(ERROR_NO_PROC_SLOTS) + CHK_ERR_WIN32A(ERROR_TOO_MANY_SEMAPHORES) + CHK_ERR_WIN32A(ERROR_EXCL_SEM_ALREADY_OWNED) + CHK_ERR_WIN32A(ERROR_SEM_IS_SET) + CHK_ERR_WIN32A(ERROR_TOO_MANY_SEM_REQUESTS) + CHK_ERR_WIN32A(ERROR_INVALID_AT_INTERRUPT_TIME) + CHK_ERR_WIN32A(ERROR_SEM_OWNER_DIED) + CHK_ERR_WIN32A(ERROR_SEM_USER_LIMIT) + CHK_ERR_WIN32A(ERROR_DISK_CHANGE) + CHK_ERR_WIN32A(ERROR_DRIVE_LOCKED) + CHK_ERR_WIN32A(ERROR_BROKEN_PIPE) + CHK_ERR_WIN32A(ERROR_OPEN_FAILED) + CHK_ERR_WIN32A(ERROR_BUFFER_OVERFLOW) + CHK_ERR_WIN32A(ERROR_DISK_FULL) + CHK_ERR_WIN32A(ERROR_NO_MORE_SEARCH_HANDLES) + CHK_ERR_WIN32A(ERROR_INVALID_TARGET_HANDLE) + CHK_ERR_WIN32A(ERROR_INVALID_CATEGORY) + CHK_ERR_WIN32A(ERROR_INVALID_VERIFY_SWITCH) + CHK_ERR_WIN32A(ERROR_BAD_DRIVER_LEVEL) + CHK_ERR_WIN32A(ERROR_CALL_NOT_IMPLEMENTED) + CHK_ERR_WIN32A(ERROR_SEM_TIMEOUT) + CHK_ERR_WIN32A(ERROR_INSUFFICIENT_BUFFER) + CHK_ERR_WIN32A(ERROR_INVALID_NAME) + CHK_ERR_WIN32A(ERROR_INVALID_LEVEL) + CHK_ERR_WIN32A(ERROR_NO_VOLUME_LABEL) + CHK_ERR_WIN32A(ERROR_MOD_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_PROC_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_WAIT_NO_CHILDREN) + CHK_ERR_WIN32A(ERROR_CHILD_NOT_COMPLETE) + CHK_ERR_WIN32A(ERROR_DIRECT_ACCESS_HANDLE) + CHK_ERR_WIN32A(ERROR_NEGATIVE_SEEK) + CHK_ERR_WIN32A(ERROR_SEEK_ON_DEVICE) + CHK_ERR_WIN32A(ERROR_IS_JOIN_TARGET) + CHK_ERR_WIN32A(ERROR_IS_JOINED) + CHK_ERR_WIN32A(ERROR_IS_SUBSTED) + CHK_ERR_WIN32A(ERROR_NOT_JOINED) + CHK_ERR_WIN32A(ERROR_NOT_SUBSTED) + CHK_ERR_WIN32A(ERROR_JOIN_TO_JOIN) + CHK_ERR_WIN32A(ERROR_SUBST_TO_SUBST) + CHK_ERR_WIN32A(ERROR_JOIN_TO_SUBST) + CHK_ERR_WIN32A(ERROR_SUBST_TO_JOIN) + CHK_ERR_WIN32A(ERROR_BUSY_DRIVE) + CHK_ERR_WIN32A(ERROR_SAME_DRIVE) + CHK_ERR_WIN32A(ERROR_DIR_NOT_ROOT) + CHK_ERR_WIN32A(ERROR_DIR_NOT_EMPTY) + CHK_ERR_WIN32A(ERROR_IS_SUBST_PATH) + CHK_ERR_WIN32A(ERROR_IS_JOIN_PATH) + CHK_ERR_WIN32A(ERROR_PATH_BUSY) + CHK_ERR_WIN32A(ERROR_IS_SUBST_TARGET) + CHK_ERR_WIN32A(ERROR_SYSTEM_TRACE) + CHK_ERR_WIN32A(ERROR_INVALID_EVENT_COUNT) + CHK_ERR_WIN32A(ERROR_TOO_MANY_MUXWAITERS) + CHK_ERR_WIN32A(ERROR_INVALID_LIST_FORMAT) + CHK_ERR_WIN32A(ERROR_LABEL_TOO_LONG) + CHK_ERR_WIN32A(ERROR_TOO_MANY_TCBS) + CHK_ERR_WIN32A(ERROR_SIGNAL_REFUSED) + CHK_ERR_WIN32A(ERROR_DISCARDED) + CHK_ERR_WIN32A(ERROR_NOT_LOCKED) + CHK_ERR_WIN32A(ERROR_BAD_THREADID_ADDR) + CHK_ERR_WIN32A(ERROR_BAD_ARGUMENTS) + CHK_ERR_WIN32A(ERROR_BAD_PATHNAME) + CHK_ERR_WIN32A(ERROR_SIGNAL_PENDING) + CHK_ERR_WIN32A(ERROR_MAX_THRDS_REACHED) + CHK_ERR_WIN32A(ERROR_LOCK_FAILED) + CHK_ERR_WIN32A(ERROR_BUSY) + CHK_ERR_WIN32A(ERROR_CANCEL_VIOLATION) + CHK_ERR_WIN32A(ERROR_ATOMIC_LOCKS_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_INVALID_SEGMENT_NUMBER) + CHK_ERR_WIN32A(ERROR_INVALID_ORDINAL) + CHK_ERR_WIN32A(ERROR_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_INVALID_FLAG_NUMBER) + CHK_ERR_WIN32A(ERROR_SEM_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_INVALID_STARTING_CODESEG) + CHK_ERR_WIN32A(ERROR_INVALID_STACKSEG) + CHK_ERR_WIN32A(ERROR_INVALID_MODULETYPE) + CHK_ERR_WIN32A(ERROR_INVALID_EXE_SIGNATURE) + CHK_ERR_WIN32A(ERROR_EXE_MARKED_INVALID) + CHK_ERR_WIN32A(ERROR_BAD_EXE_FORMAT) + CHK_ERR_WIN32A(ERROR_ITERATED_DATA_EXCEEDS_64k) + CHK_ERR_WIN32A(ERROR_INVALID_MINALLOCSIZE) + CHK_ERR_WIN32A(ERROR_DYNLINK_FROM_INVALID_RING) + CHK_ERR_WIN32A(ERROR_IOPL_NOT_ENABLED) + CHK_ERR_WIN32A(ERROR_INVALID_SEGDPL) + CHK_ERR_WIN32A(ERROR_AUTODATASEG_EXCEEDS_64k) + CHK_ERRA(ERROR_RING2SEG_MUST_BE_MOVABLE) + CHK_ERRA(ERROR_RELOC_CHAIN_XEEDS_SEGLIM) + CHK_ERR_WIN32A(ERROR_INFLOOP_IN_RELOC_CHAIN) + CHK_ERR_WIN32A(ERROR_ENVVAR_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_NO_SIGNAL_SENT) + CHK_ERR_WIN32A(ERROR_FILENAME_EXCED_RANGE) + CHK_ERR_WIN32A(ERROR_RING2_STACK_IN_USE) + CHK_ERR_WIN32A(ERROR_META_EXPANSION_TOO_LONG) + CHK_ERR_WIN32A(ERROR_INVALID_SIGNAL_NUMBER) + CHK_ERR_WIN32A(ERROR_THREAD_1_INACTIVE) + CHK_ERR_WIN32A(ERROR_LOCKED) + CHK_ERR_WIN32A(ERROR_TOO_MANY_MODULES) + CHK_ERR_WIN32A(ERROR_NESTING_NOT_ALLOWED) + CHK_ERR_WIN32A(ERROR_EXE_MACHINE_TYPE_MISMATCH) + CHK_ERR_WIN32A(ERROR_BAD_PIPE) + CHK_ERR_WIN32A(ERROR_PIPE_BUSY) + CHK_ERR_WIN32A(ERROR_NO_DATA) + CHK_ERR_WIN32A(ERROR_PIPE_NOT_CONNECTED) + CHK_ERR_WIN32A(ERROR_MORE_DATA) + CHK_ERR_WIN32A(ERROR_VC_DISCONNECTED) + CHK_ERR_WIN32A(ERROR_INVALID_EA_NAME) + CHK_ERR_WIN32A(ERROR_EA_LIST_INCONSISTENT) + CHK_ERR_WIN32A(WAIT_TIMEOUT) + CHK_ERR_WIN32A(ERROR_NO_MORE_ITEMS) + CHK_ERR_WIN32A(ERROR_CANNOT_COPY) + CHK_ERR_WIN32A(ERROR_DIRECTORY) + CHK_ERR_WIN32A(ERROR_EAS_DIDNT_FIT) + CHK_ERR_WIN32A(ERROR_EA_FILE_CORRUPT) + CHK_ERR_WIN32A(ERROR_EA_TABLE_FULL) + CHK_ERR_WIN32A(ERROR_INVALID_EA_HANDLE) + CHK_ERR_WIN32A(ERROR_EAS_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_NOT_OWNER) + CHK_ERR_WIN32A(ERROR_TOO_MANY_POSTS) + CHK_ERR_WIN32A(ERROR_PARTIAL_COPY) + CHK_ERR_WIN32A(ERROR_OPLOCK_NOT_GRANTED) + CHK_ERR_WIN32A(ERROR_INVALID_OPLOCK_PROTOCOL) + CHK_ERR_WIN32A(ERROR_MR_MID_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_INVALID_ADDRESS) + CHK_ERR_WIN32A(ERROR_ARITHMETIC_OVERFLOW) + CHK_ERR_WIN32A(ERROR_PIPE_CONNECTED) + CHK_ERR_WIN32A(ERROR_PIPE_LISTENING) + CHK_ERR_WIN32A(ERROR_EA_ACCESS_DENIED) + CHK_ERR_WIN32A(ERROR_OPERATION_ABORTED) + CHK_ERR_WIN32A(ERROR_IO_INCOMPLETE) + CHK_ERR_WIN32A(ERROR_IO_PENDING) + CHK_ERR_WIN32A(ERROR_NOACCESS) + CHK_ERR_WIN32A(ERROR_SWAPERROR) + CHK_ERR_WIN32A(ERROR_STACK_OVERFLOW) + CHK_ERR_WIN32A(ERROR_INVALID_MESSAGE) + CHK_ERR_WIN32A(ERROR_CAN_NOT_COMPLETE) + CHK_ERR_WIN32A(ERROR_INVALID_FLAGS) + CHK_ERR_WIN32A(ERROR_UNRECOGNIZED_VOLUME) + CHK_ERR_WIN32A(ERROR_FILE_INVALID) + CHK_ERR_WIN32A(ERROR_FULLSCREEN_MODE) + CHK_ERR_WIN32A(ERROR_NO_TOKEN) + CHK_ERR_WIN32A(ERROR_BADDB) + CHK_ERR_WIN32A(ERROR_BADKEY) + CHK_ERR_WIN32A(ERROR_CANTOPEN) + CHK_ERR_WIN32A(ERROR_CANTREAD) + CHK_ERR_WIN32A(ERROR_CANTWRITE) + CHK_ERR_WIN32A(ERROR_REGISTRY_RECOVERED) + CHK_ERR_WIN32A(ERROR_REGISTRY_CORRUPT) + CHK_ERR_WIN32A(ERROR_REGISTRY_IO_FAILED) + CHK_ERR_WIN32A(ERROR_NOT_REGISTRY_FILE) + CHK_ERR_WIN32A(ERROR_KEY_DELETED) + CHK_ERR_WIN32A(ERROR_NO_LOG_SPACE) + CHK_ERR_WIN32A(ERROR_KEY_HAS_CHILDREN) + CHK_ERR_WIN32A(ERROR_CHILD_MUST_BE_VOLATILE) + CHK_ERR_WIN32A(ERROR_NOTIFY_ENUM_DIR) + CHK_ERR_WIN32A(ERROR_DEPENDENT_SERVICES_RUNNING) + CHK_ERR_WIN32A(ERROR_INVALID_SERVICE_CONTROL) + CHK_ERR_WIN32A(ERROR_SERVICE_REQUEST_TIMEOUT) + CHK_ERR_WIN32A(ERROR_SERVICE_NO_THREAD) + CHK_ERR_WIN32A(ERROR_SERVICE_DATABASE_LOCKED) + CHK_ERR_WIN32A(ERROR_SERVICE_ALREADY_RUNNING) + CHK_ERR_WIN32A(ERROR_INVALID_SERVICE_ACCOUNT) + CHK_ERR_WIN32A(ERROR_SERVICE_DISABLED) + CHK_ERR_WIN32A(ERROR_CIRCULAR_DEPENDENCY) + CHK_ERR_WIN32A(ERROR_SERVICE_DOES_NOT_EXIST) + CHK_ERR_WIN32A(ERROR_SERVICE_CANNOT_ACCEPT_CTRL) + CHK_ERR_WIN32A(ERROR_SERVICE_NOT_ACTIVE) + CHK_ERR_WIN32A(ERROR_FAILED_SERVICE_CONTROLLER_CONNECT) + CHK_ERR_WIN32A(ERROR_EXCEPTION_IN_SERVICE) + CHK_ERR_WIN32A(ERROR_DATABASE_DOES_NOT_EXIST) + CHK_ERR_WIN32A(ERROR_SERVICE_SPECIFIC_ERROR) + CHK_ERR_WIN32A(ERROR_PROCESS_ABORTED) + CHK_ERR_WIN32A(ERROR_SERVICE_DEPENDENCY_FAIL) + CHK_ERR_WIN32A(ERROR_SERVICE_LOGON_FAILED) + CHK_ERR_WIN32A(ERROR_SERVICE_START_HANG) + CHK_ERR_WIN32A(ERROR_INVALID_SERVICE_LOCK) + CHK_ERR_WIN32A(ERROR_SERVICE_MARKED_FOR_DELETE) + CHK_ERR_WIN32A(ERROR_SERVICE_EXISTS) + CHK_ERR_WIN32A(ERROR_ALREADY_RUNNING_LKG) + CHK_ERR_WIN32A(ERROR_SERVICE_DEPENDENCY_DELETED) + CHK_ERR_WIN32A(ERROR_BOOT_ALREADY_ACCEPTED) + CHK_ERR_WIN32A(ERROR_SERVICE_NEVER_STARTED) + CHK_ERR_WIN32A(ERROR_DUPLICATE_SERVICE_NAME) + CHK_ERR_WIN32A(ERROR_DIFFERENT_SERVICE_ACCOUNT) + CHK_ERR_WIN32A(ERROR_CANNOT_DETECT_DRIVER_FAILURE) + CHK_ERR_WIN32A(ERROR_CANNOT_DETECT_PROCESS_ABORT) + CHK_ERR_WIN32A(ERROR_NO_RECOVERY_PROGRAM) + CHK_ERR_WIN32A(ERROR_SERVICE_NOT_IN_EXE) + CHK_ERR_WIN32A(ERROR_END_OF_MEDIA) + CHK_ERR_WIN32A(ERROR_FILEMARK_DETECTED) + CHK_ERR_WIN32A(ERROR_BEGINNING_OF_MEDIA) + CHK_ERR_WIN32A(ERROR_SETMARK_DETECTED) + CHK_ERR_WIN32A(ERROR_NO_DATA_DETECTED) + CHK_ERR_WIN32A(ERROR_PARTITION_FAILURE) + CHK_ERR_WIN32A(ERROR_INVALID_BLOCK_LENGTH) + CHK_ERR_WIN32A(ERROR_DEVICE_NOT_PARTITIONED) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_LOCK_MEDIA) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_UNLOAD_MEDIA) + CHK_ERR_WIN32A(ERROR_MEDIA_CHANGED) + CHK_ERR_WIN32A(ERROR_BUS_RESET) + CHK_ERR_WIN32A(ERROR_NO_MEDIA_IN_DRIVE) + CHK_ERR_WIN32A(ERROR_NO_UNICODE_TRANSLATION) + CHK_ERR_WIN32A(ERROR_DLL_INIT_FAILED) + CHK_ERR_WIN32A(ERROR_SHUTDOWN_IN_PROGRESS) + CHK_ERR_WIN32A(ERROR_NO_SHUTDOWN_IN_PROGRESS) + CHK_ERR_WIN32A(ERROR_IO_DEVICE) + CHK_ERR_WIN32A(ERROR_SERIAL_NO_DEVICE) + CHK_ERR_WIN32A(ERROR_IRQ_BUSY) + CHK_ERR_WIN32A(ERROR_MORE_WRITES) + CHK_ERR_WIN32A(ERROR_COUNTER_TIMEOUT) + CHK_ERR_WIN32A(ERROR_FLOPPY_ID_MARK_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_FLOPPY_WRONG_CYLINDER) + CHK_ERR_WIN32A(ERROR_FLOPPY_UNKNOWN_ERROR) + CHK_ERR_WIN32A(ERROR_FLOPPY_BAD_REGISTERS) + CHK_ERR_WIN32A(ERROR_DISK_RECALIBRATE_FAILED) + CHK_ERR_WIN32A(ERROR_DISK_OPERATION_FAILED) + CHK_ERR_WIN32A(ERROR_DISK_RESET_FAILED) + CHK_ERR_WIN32A(ERROR_EOM_OVERFLOW) + CHK_ERR_WIN32A(ERROR_NOT_ENOUGH_SERVER_MEMORY) + CHK_ERR_WIN32A(ERROR_POSSIBLE_DEADLOCK) + CHK_ERR_WIN32A(ERROR_MAPPED_ALIGNMENT) + CHK_ERR_WIN32A(ERROR_SET_POWER_STATE_VETOED) + CHK_ERR_WIN32A(ERROR_SET_POWER_STATE_FAILED) + CHK_ERR_WIN32A(ERROR_TOO_MANY_LINKS) + CHK_ERR_WIN32A(ERROR_OLD_WIN_VERSION) + CHK_ERR_WIN32A(ERROR_APP_WRONG_OS) + CHK_ERR_WIN32A(ERROR_SINGLE_INSTANCE_APP) + CHK_ERR_WIN32A(ERROR_RMODE_APP) + CHK_ERR_WIN32A(ERROR_INVALID_DLL) + CHK_ERR_WIN32A(ERROR_NO_ASSOCIATION) + CHK_ERR_WIN32A(ERROR_DDE_FAIL) + CHK_ERR_WIN32A(ERROR_DLL_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_NO_MORE_USER_HANDLES) + CHK_ERR_WIN32A(ERROR_MESSAGE_SYNC_ONLY) + CHK_ERR_WIN32A(ERROR_SOURCE_ELEMENT_EMPTY) + CHK_ERR_WIN32A(ERROR_DESTINATION_ELEMENT_FULL) + CHK_ERR_WIN32A(ERROR_ILLEGAL_ELEMENT_ADDRESS) + CHK_ERR_WIN32A(ERROR_MAGAZINE_NOT_PRESENT) + CHK_ERR_WIN32A(ERROR_DEVICE_REINITIALIZATION_NEEDED) + CHK_ERR_WIN32A(ERROR_DEVICE_REQUIRES_CLEANING) + CHK_ERR_WIN32A(ERROR_DEVICE_DOOR_OPEN) + CHK_ERR_WIN32A(ERROR_DEVICE_NOT_CONNECTED) + CHK_ERR_WIN32A(ERROR_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_NO_MATCH) + CHK_ERR_WIN32A(ERROR_SET_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_POINT_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_NO_TRACKING_SERVICE) + CHK_ERR_WIN32A(ERROR_NO_VOLUME_ID) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_REMOVE_REPLACED) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_MOVE_REPLACEMENT) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_MOVE_REPLACEMENT_2) + CHK_ERR_WIN32A(ERROR_JOURNAL_DELETE_IN_PROGRESS) + CHK_ERR_WIN32A(ERROR_JOURNAL_NOT_ACTIVE) + CHK_ERR_WIN32A(ERROR_POTENTIAL_FILE_FOUND) + CHK_ERR_WIN32A(ERROR_BAD_DEVICE) + CHK_ERR_WIN32A(ERROR_CONNECTION_UNAVAIL) + CHK_ERR_WIN32A(ERROR_DEVICE_ALREADY_REMEMBERED) + CHK_ERR_WIN32A(ERROR_NO_NET_OR_BAD_PATH) + CHK_ERR_WIN32A(ERROR_BAD_PROVIDER) + CHK_ERR_WIN32A(ERROR_CANNOT_OPEN_PROFILE) + CHK_ERR_WIN32A(ERROR_BAD_PROFILE) + CHK_ERR_WIN32A(ERROR_NOT_CONTAINER) + CHK_ERR_WIN32A(ERROR_EXTENDED_ERROR) + CHK_ERR_WIN32A(ERROR_INVALID_GROUPNAME) + CHK_ERR_WIN32A(ERROR_INVALID_COMPUTERNAME) + CHK_ERR_WIN32A(ERROR_INVALID_EVENTNAME) + CHK_ERR_WIN32A(ERROR_INVALID_DOMAINNAME) + CHK_ERR_WIN32A(ERROR_INVALID_SERVICENAME) + CHK_ERR_WIN32A(ERROR_INVALID_NETNAME) + CHK_ERR_WIN32A(ERROR_INVALID_SHARENAME) + CHK_ERR_WIN32A(ERROR_INVALID_PASSWORDNAME) + CHK_ERR_WIN32A(ERROR_INVALID_MESSAGENAME) + CHK_ERR_WIN32A(ERROR_INVALID_MESSAGEDEST) + CHK_ERR_WIN32A(ERROR_SESSION_CREDENTIAL_CONFLICT) + CHK_ERR_WIN32A(ERROR_REMOTE_SESSION_LIMIT_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DUP_DOMAINNAME) + CHK_ERR_WIN32A(ERROR_NO_NETWORK) + CHK_ERR_WIN32A(ERROR_CANCELLED) + CHK_ERR_WIN32A(ERROR_USER_MAPPED_FILE) + CHK_ERR_WIN32A(ERROR_CONNECTION_REFUSED) + CHK_ERR_WIN32A(ERROR_GRACEFUL_DISCONNECT) + CHK_ERR_WIN32A(ERROR_ADDRESS_ALREADY_ASSOCIATED) + CHK_ERR_WIN32A(ERROR_ADDRESS_NOT_ASSOCIATED) + CHK_ERR_WIN32A(ERROR_CONNECTION_INVALID) + CHK_ERR_WIN32A(ERROR_CONNECTION_ACTIVE) + CHK_ERR_WIN32A(ERROR_NETWORK_UNREACHABLE) + CHK_ERR_WIN32A(ERROR_HOST_UNREACHABLE) + CHK_ERR_WIN32A(ERROR_PROTOCOL_UNREACHABLE) + CHK_ERR_WIN32A(ERROR_PORT_UNREACHABLE) + CHK_ERR_WIN32A(ERROR_REQUEST_ABORTED) + CHK_ERR_WIN32A(ERROR_CONNECTION_ABORTED) + CHK_ERR_WIN32A(ERROR_RETRY) + CHK_ERR_WIN32A(ERROR_CONNECTION_COUNT_LIMIT) + CHK_ERR_WIN32A(ERROR_LOGIN_TIME_RESTRICTION) + CHK_ERR_WIN32A(ERROR_LOGIN_WKSTA_RESTRICTION) + CHK_ERR_WIN32A(ERROR_INCORRECT_ADDRESS) + CHK_ERR_WIN32A(ERROR_ALREADY_REGISTERED) + CHK_ERR_WIN32A(ERROR_SERVICE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_NOT_AUTHENTICATED) + CHK_ERR_WIN32A(ERROR_NOT_LOGGED_ON) + CHK_ERR_WIN32A(ERROR_CONTINUE) + CHK_ERR_WIN32A(ERROR_ALREADY_INITIALIZED) + CHK_ERR_WIN32A(ERROR_NO_MORE_DEVICES) + CHK_ERR_WIN32A(ERROR_NO_SUCH_SITE) + CHK_ERR_WIN32A(ERROR_DOMAIN_CONTROLLER_EXISTS) + CHK_ERR_WIN32A(ERROR_NOT_ALL_ASSIGNED) + CHK_ERR_WIN32A(ERROR_SOME_NOT_MAPPED) + CHK_ERR_WIN32A(ERROR_NO_QUOTAS_FOR_ACCOUNT) + CHK_ERR_WIN32A(ERROR_LOCAL_USER_SESSION_KEY) + CHK_ERR_WIN32A(ERROR_NULL_LM_PASSWORD) + CHK_ERR_WIN32A(ERROR_UNKNOWN_REVISION) + CHK_ERR_WIN32A(ERROR_REVISION_MISMATCH) + CHK_ERR_WIN32A(ERROR_INVALID_OWNER) + CHK_ERR_WIN32A(ERROR_INVALID_PRIMARY_GROUP) + CHK_ERR_WIN32A(ERROR_NO_IMPERSONATION_TOKEN) + CHK_ERR_WIN32A(ERROR_CANT_DISABLE_MANDATORY) + CHK_ERR_WIN32A(ERROR_NO_LOGON_SERVERS) + CHK_ERR_WIN32A(ERROR_NO_SUCH_LOGON_SESSION) + CHK_ERR_WIN32A(ERROR_NO_SUCH_PRIVILEGE) + CHK_ERR_WIN32A(ERROR_PRIVILEGE_NOT_HELD) + CHK_ERR_WIN32A(ERROR_INVALID_ACCOUNT_NAME) + CHK_ERR_WIN32A(ERROR_USER_EXISTS) + CHK_ERR_WIN32A(ERROR_NO_SUCH_USER) + CHK_ERR_WIN32A(ERROR_GROUP_EXISTS) + CHK_ERR_WIN32A(ERROR_NO_SUCH_GROUP) + CHK_ERR_WIN32A(ERROR_MEMBER_IN_GROUP) + CHK_ERR_WIN32A(ERROR_MEMBER_NOT_IN_GROUP) + CHK_ERR_WIN32A(ERROR_LAST_ADMIN) + CHK_ERR_WIN32A(ERROR_WRONG_PASSWORD) + CHK_ERR_WIN32A(ERROR_ILL_FORMED_PASSWORD) + CHK_ERR_WIN32A(ERROR_PASSWORD_RESTRICTION) + CHK_ERR_WIN32A(ERROR_LOGON_FAILURE) + CHK_ERR_WIN32A(ERROR_ACCOUNT_RESTRICTION) + CHK_ERR_WIN32A(ERROR_INVALID_LOGON_HOURS) + CHK_ERR_WIN32A(ERROR_INVALID_WORKSTATION) + CHK_ERR_WIN32A(ERROR_PASSWORD_EXPIRED) + CHK_ERR_WIN32A(ERROR_ACCOUNT_DISABLED) + CHK_ERR_WIN32A(ERROR_NONE_MAPPED) + CHK_ERR_WIN32A(ERROR_TOO_MANY_LUIDS_REQUESTED) + CHK_ERR_WIN32A(ERROR_LUIDS_EXHAUSTED) + CHK_ERR_WIN32A(ERROR_INVALID_SUB_AUTHORITY) + CHK_ERR_WIN32A(ERROR_INVALID_ACL) + CHK_ERR_WIN32A(ERROR_INVALID_SID) + CHK_ERR_WIN32A(ERROR_INVALID_SECURITY_DESCR) + CHK_ERR_WIN32A(ERROR_BAD_INHERITANCE_ACL) + CHK_ERR_WIN32A(ERROR_SERVER_DISABLED) + CHK_ERR_WIN32A(ERROR_SERVER_NOT_DISABLED) + CHK_ERR_WIN32A(ERROR_INVALID_ID_AUTHORITY) + CHK_ERR_WIN32A(ERROR_ALLOTTED_SPACE_EXCEEDED) + CHK_ERR_WIN32A(ERROR_INVALID_GROUP_ATTRIBUTES) + CHK_ERR_WIN32A(ERROR_BAD_IMPERSONATION_LEVEL) + CHK_ERR_WIN32A(ERROR_CANT_OPEN_ANONYMOUS) + CHK_ERR_WIN32A(ERROR_BAD_VALIDATION_CLASS) + CHK_ERR_WIN32A(ERROR_BAD_TOKEN_TYPE) + CHK_ERR_WIN32A(ERROR_NO_SECURITY_ON_OBJECT) + CHK_ERR_WIN32A(ERROR_CANT_ACCESS_DOMAIN_INFO) + CHK_ERR_WIN32A(ERROR_INVALID_SERVER_STATE) + CHK_ERR_WIN32A(ERROR_INVALID_DOMAIN_STATE) + CHK_ERR_WIN32A(ERROR_INVALID_DOMAIN_ROLE) + CHK_ERR_WIN32A(ERROR_NO_SUCH_DOMAIN) + CHK_ERR_WIN32A(ERROR_DOMAIN_EXISTS) + CHK_ERR_WIN32A(ERROR_DOMAIN_LIMIT_EXCEEDED) + CHK_ERR_WIN32A(ERROR_INTERNAL_DB_CORRUPTION) + CHK_ERR_WIN32A(ERROR_INTERNAL_ERROR) + CHK_ERR_WIN32A(ERROR_GENERIC_NOT_MAPPED) + CHK_ERR_WIN32A(ERROR_BAD_DESCRIPTOR_FORMAT) + CHK_ERR_WIN32A(ERROR_NOT_LOGON_PROCESS) + CHK_ERR_WIN32A(ERROR_LOGON_SESSION_EXISTS) + CHK_ERR_WIN32A(ERROR_NO_SUCH_PACKAGE) + CHK_ERR_WIN32A(ERROR_BAD_LOGON_SESSION_STATE) + CHK_ERR_WIN32A(ERROR_LOGON_SESSION_COLLISION) + CHK_ERR_WIN32A(ERROR_INVALID_LOGON_TYPE) + CHK_ERR_WIN32A(ERROR_CANNOT_IMPERSONATE) + CHK_ERR_WIN32A(ERROR_RXACT_INVALID_STATE) + CHK_ERR_WIN32A(ERROR_RXACT_COMMIT_FAILURE) + CHK_ERR_WIN32A(ERROR_SPECIAL_ACCOUNT) + CHK_ERR_WIN32A(ERROR_SPECIAL_GROUP) + CHK_ERR_WIN32A(ERROR_SPECIAL_USER) + CHK_ERR_WIN32A(ERROR_MEMBERS_PRIMARY_GROUP) + CHK_ERR_WIN32A(ERROR_TOKEN_ALREADY_IN_USE) + CHK_ERR_WIN32A(ERROR_NO_SUCH_ALIAS) + CHK_ERR_WIN32A(ERROR_MEMBER_NOT_IN_ALIAS) + CHK_ERR_WIN32A(ERROR_MEMBER_IN_ALIAS) + CHK_ERR_WIN32A(ERROR_ALIAS_EXISTS) + CHK_ERR_WIN32A(ERROR_LOGON_NOT_GRANTED) + CHK_ERR_WIN32A(ERROR_TOO_MANY_SECRETS) + CHK_ERR_WIN32A(ERROR_SECRET_TOO_LONG) + CHK_ERR_WIN32A(ERROR_INTERNAL_DB_ERROR) + CHK_ERR_WIN32A(ERROR_TOO_MANY_CONTEXT_IDS) + CHK_ERR_WIN32A(ERROR_LOGON_TYPE_NOT_GRANTED) + CHK_ERR_WIN32A(ERROR_NT_CROSS_ENCRYPTION_REQUIRED) + CHK_ERR_WIN32A(ERROR_NO_SUCH_MEMBER) + CHK_ERR_WIN32A(ERROR_INVALID_MEMBER) + CHK_ERR_WIN32A(ERROR_TOO_MANY_SIDS) + CHK_ERR_WIN32A(ERROR_LM_CROSS_ENCRYPTION_REQUIRED) + CHK_ERR_WIN32A(ERROR_NO_INHERITANCE) + CHK_ERR_WIN32A(ERROR_FILE_CORRUPT) + CHK_ERR_WIN32A(ERROR_DISK_CORRUPT) + CHK_ERR_WIN32A(ERROR_NO_USER_SESSION_KEY) + CHK_ERR_WIN32A(ERROR_LICENSE_QUOTA_EXCEEDED) + CHK_ERR_WIN32A(ERROR_WRONG_TARGET_NAME) + CHK_ERR_WIN32A(ERROR_MUTUAL_AUTH_FAILED) + CHK_ERR_WIN32A(ERROR_TIME_SKEW) + CHK_ERR_WIN32A(ERROR_INVALID_WINDOW_HANDLE) + CHK_ERR_WIN32A(ERROR_INVALID_MENU_HANDLE) + CHK_ERR_WIN32A(ERROR_INVALID_CURSOR_HANDLE) + CHK_ERR_WIN32A(ERROR_INVALID_ACCEL_HANDLE) + CHK_ERR_WIN32A(ERROR_INVALID_HOOK_HANDLE) + CHK_ERR_WIN32A(ERROR_INVALID_DWP_HANDLE) + CHK_ERR_WIN32A(ERROR_TLW_WITH_WSCHILD) + CHK_ERR_WIN32A(ERROR_CANNOT_FIND_WND_CLASS) + CHK_ERR_WIN32A(ERROR_WINDOW_OF_OTHER_THREAD) + CHK_ERR_WIN32A(ERROR_HOTKEY_ALREADY_REGISTERED) + CHK_ERR_WIN32A(ERROR_CLASS_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_CLASS_DOES_NOT_EXIST) + CHK_ERR_WIN32A(ERROR_CLASS_HAS_WINDOWS) + CHK_ERR_WIN32A(ERROR_INVALID_INDEX) + CHK_ERR_WIN32A(ERROR_INVALID_ICON_HANDLE) + CHK_ERR_WIN32A(ERROR_PRIVATE_DIALOG_INDEX) + CHK_ERR_WIN32A(ERROR_LISTBOX_ID_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_NO_WILDCARD_CHARACTERS) + CHK_ERR_WIN32A(ERROR_CLIPBOARD_NOT_OPEN) + CHK_ERR_WIN32A(ERROR_HOTKEY_NOT_REGISTERED) + CHK_ERR_WIN32A(ERROR_WINDOW_NOT_DIALOG) + CHK_ERR_WIN32A(ERROR_CONTROL_ID_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_INVALID_COMBOBOX_MESSAGE) + CHK_ERR_WIN32A(ERROR_WINDOW_NOT_COMBOBOX) + CHK_ERR_WIN32A(ERROR_INVALID_EDIT_HEIGHT) + CHK_ERR_WIN32A(ERROR_DC_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_INVALID_HOOK_FILTER) + CHK_ERR_WIN32A(ERROR_INVALID_FILTER_PROC) + CHK_ERR_WIN32A(ERROR_HOOK_NEEDS_HMOD) + CHK_ERR_WIN32A(ERROR_GLOBAL_ONLY_HOOK) + CHK_ERR_WIN32A(ERROR_JOURNAL_HOOK_SET) + CHK_ERR_WIN32A(ERROR_HOOK_NOT_INSTALLED) + CHK_ERR_WIN32A(ERROR_INVALID_LB_MESSAGE) + CHK_ERR_WIN32A(ERROR_SETCOUNT_ON_BAD_LB) + CHK_ERR_WIN32A(ERROR_LB_WITHOUT_TABSTOPS) + CHK_ERR_WIN32A(ERROR_DESTROY_OBJECT_OF_OTHER_THREAD) + CHK_ERR_WIN32A(ERROR_CHILD_WINDOW_MENU) + CHK_ERR_WIN32A(ERROR_NO_SYSTEM_MENU) + CHK_ERR_WIN32A(ERROR_INVALID_MSGBOX_STYLE) + CHK_ERR_WIN32A(ERROR_INVALID_SPI_VALUE) + CHK_ERR_WIN32A(ERROR_SCREEN_ALREADY_LOCKED) + CHK_ERR_WIN32A(ERROR_HWNDS_HAVE_DIFF_PARENT) + CHK_ERR_WIN32A(ERROR_NOT_CHILD_WINDOW) + CHK_ERR_WIN32A(ERROR_INVALID_GW_COMMAND) + CHK_ERR_WIN32A(ERROR_INVALID_THREAD_ID) + CHK_ERR_WIN32A(ERROR_NON_MDICHILD_WINDOW) + CHK_ERR_WIN32A(ERROR_POPUP_ALREADY_ACTIVE) + CHK_ERR_WIN32A(ERROR_NO_SCROLLBARS) + CHK_ERR_WIN32A(ERROR_INVALID_SCROLLBAR_RANGE) + CHK_ERR_WIN32A(ERROR_INVALID_SHOWWIN_COMMAND) + CHK_ERR_WIN32A(ERROR_NO_SYSTEM_RESOURCES) + CHK_ERR_WIN32A(ERROR_NONPAGED_SYSTEM_RESOURCES) + CHK_ERR_WIN32A(ERROR_PAGED_SYSTEM_RESOURCES) + CHK_ERR_WIN32A(ERROR_WORKING_SET_QUOTA) + CHK_ERR_WIN32A(ERROR_PAGEFILE_QUOTA) + CHK_ERR_WIN32A(ERROR_COMMITMENT_LIMIT) + CHK_ERR_WIN32A(ERROR_MENU_ITEM_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_INVALID_KEYBOARD_HANDLE) + CHK_ERR_WIN32A(ERROR_HOOK_TYPE_NOT_ALLOWED) + CHK_ERR_WIN32A(ERROR_REQUIRES_INTERACTIVE_WINDOWSTATION) + CHK_ERR_WIN32A(ERROR_TIMEOUT) + CHK_ERR_WIN32A(ERROR_INVALID_MONITOR_HANDLE) + CHK_ERR_WIN32A(ERROR_EVENTLOG_FILE_CORRUPT) + CHK_ERR_WIN32A(ERROR_EVENTLOG_CANT_START) + CHK_ERR_WIN32A(ERROR_LOG_FILE_FULL) + CHK_ERR_WIN32A(ERROR_EVENTLOG_FILE_CHANGED) + CHK_ERR_WIN32A(ERROR_INSTALL_USEREXIT) + CHK_ERR_WIN32A(ERROR_INSTALL_FAILURE) + CHK_ERR_WIN32A(ERROR_INSTALL_SUSPEND) + CHK_ERR_WIN32A(ERROR_UNKNOWN_PRODUCT) + CHK_ERR_WIN32A(ERROR_UNKNOWN_FEATURE) + CHK_ERR_WIN32A(ERROR_UNKNOWN_COMPONENT) + CHK_ERR_WIN32A(ERROR_UNKNOWN_PROPERTY) + CHK_ERR_WIN32A(ERROR_INVALID_HANDLE_STATE) + CHK_ERR_WIN32A(ERROR_BAD_CONFIGURATION) + CHK_ERR_WIN32A(ERROR_INDEX_ABSENT) + CHK_ERR_WIN32A(ERROR_INSTALL_SOURCE_ABSENT) + CHK_ERR_WIN32A(ERROR_PRODUCT_UNINSTALLED) + CHK_ERR_WIN32A(ERROR_BAD_QUERY_SYNTAX) + CHK_ERR_WIN32A(ERROR_INVALID_FIELD) + CHK_ERR_WIN32A(ERROR_DEVICE_REMOVED) + CHK_ERR_WIN32A(RPC_S_INVALID_STRING_BINDING) + CHK_ERR_WIN32A(RPC_S_WRONG_KIND_OF_BINDING) + CHK_ERR_WIN32A(RPC_S_INVALID_BINDING) + CHK_ERR_WIN32A(RPC_S_PROTSEQ_NOT_SUPPORTED) + CHK_ERR_WIN32A(RPC_S_INVALID_RPC_PROTSEQ) + CHK_ERR_WIN32A(RPC_S_INVALID_STRING_UUID) + CHK_ERR_WIN32A(RPC_S_INVALID_ENDPOINT_FORMAT) + CHK_ERR_WIN32A(RPC_S_INVALID_NET_ADDR) + CHK_ERR_WIN32A(RPC_S_NO_ENDPOINT_FOUND) + CHK_ERR_WIN32A(RPC_S_INVALID_TIMEOUT) + CHK_ERR_WIN32A(RPC_S_OBJECT_NOT_FOUND) + CHK_ERR_WIN32A(RPC_S_ALREADY_REGISTERED) + CHK_ERR_WIN32A(RPC_S_TYPE_ALREADY_REGISTERED) + CHK_ERR_WIN32A(RPC_S_ALREADY_LISTENING) + CHK_ERR_WIN32A(RPC_S_NO_PROTSEQS_REGISTERED) + CHK_ERR_WIN32A(RPC_S_NOT_LISTENING) + CHK_ERR_WIN32A(RPC_S_UNKNOWN_MGR_TYPE) + CHK_ERR_WIN32A(RPC_S_UNKNOWN_IF) + CHK_ERR_WIN32A(RPC_S_NO_BINDINGS) + CHK_ERR_WIN32A(RPC_S_NO_PROTSEQS) + CHK_ERR_WIN32A(RPC_S_CANT_CREATE_ENDPOINT) + CHK_ERR_WIN32A(RPC_S_OUT_OF_RESOURCES) + CHK_ERR_WIN32A(RPC_S_SERVER_UNAVAILABLE) + CHK_ERR_WIN32A(RPC_S_SERVER_TOO_BUSY) + CHK_ERR_WIN32A(RPC_S_INVALID_NETWORK_OPTIONS) + CHK_ERR_WIN32A(RPC_S_NO_CALL_ACTIVE) + CHK_ERR_WIN32A(RPC_S_CALL_FAILED) + CHK_ERR_WIN32A(RPC_S_CALL_FAILED_DNE) + CHK_ERR_WIN32A(RPC_S_PROTOCOL_ERROR) + CHK_ERR_WIN32A(RPC_S_UNSUPPORTED_TRANS_SYN) + CHK_ERR_WIN32A(RPC_S_UNSUPPORTED_TYPE) + CHK_ERR_WIN32A(RPC_S_INVALID_TAG) + CHK_ERR_WIN32A(RPC_S_INVALID_BOUND) + CHK_ERR_WIN32A(RPC_S_NO_ENTRY_NAME) + CHK_ERR_WIN32A(RPC_S_INVALID_NAME_SYNTAX) + CHK_ERR_WIN32A(RPC_S_UNSUPPORTED_NAME_SYNTAX) + CHK_ERR_WIN32A(RPC_S_UUID_NO_ADDRESS) + CHK_ERR_WIN32A(RPC_S_DUPLICATE_ENDPOINT) + CHK_ERR_WIN32A(RPC_S_UNKNOWN_AUTHN_TYPE) + CHK_ERR_WIN32A(RPC_S_MAX_CALLS_TOO_SMALL) + CHK_ERR_WIN32A(RPC_S_STRING_TOO_LONG) + CHK_ERR_WIN32A(RPC_S_PROTSEQ_NOT_FOUND) + CHK_ERR_WIN32A(RPC_S_PROCNUM_OUT_OF_RANGE) + CHK_ERR_WIN32A(RPC_S_BINDING_HAS_NO_AUTH) + CHK_ERR_WIN32A(RPC_S_UNKNOWN_AUTHN_SERVICE) + CHK_ERR_WIN32A(RPC_S_UNKNOWN_AUTHN_LEVEL) + CHK_ERR_WIN32A(RPC_S_INVALID_AUTH_IDENTITY) + CHK_ERR_WIN32A(RPC_S_UNKNOWN_AUTHZ_SERVICE) + CHK_ERR_WIN32A(EPT_S_INVALID_ENTRY) + CHK_ERR_WIN32A(EPT_S_CANT_PERFORM_OP) + CHK_ERR_WIN32A(EPT_S_NOT_REGISTERED) + CHK_ERR_WIN32A(RPC_S_NOTHING_TO_EXPORT) + CHK_ERR_WIN32A(RPC_S_INCOMPLETE_NAME) + CHK_ERR_WIN32A(RPC_S_INVALID_VERS_OPTION) + CHK_ERR_WIN32A(RPC_S_NO_MORE_MEMBERS) + CHK_ERR_WIN32A(RPC_S_NOT_ALL_OBJS_UNEXPORTED) + CHK_ERR_WIN32A(RPC_S_INTERFACE_NOT_FOUND) + CHK_ERR_WIN32A(RPC_S_ENTRY_ALREADY_EXISTS) + CHK_ERR_WIN32A(RPC_S_ENTRY_NOT_FOUND) + CHK_ERR_WIN32A(RPC_S_NAME_SERVICE_UNAVAILABLE) + CHK_ERR_WIN32A(RPC_S_INVALID_NAF_ID) + CHK_ERR_WIN32A(RPC_S_CANNOT_SUPPORT) + CHK_ERR_WIN32A(RPC_S_NO_CONTEXT_AVAILABLE) + CHK_ERR_WIN32A(RPC_S_INTERNAL_ERROR) + CHK_ERR_WIN32A(RPC_S_ZERO_DIVIDE) + CHK_ERR_WIN32A(RPC_S_ADDRESS_ERROR) + CHK_ERR_WIN32A(RPC_S_FP_DIV_ZERO) + CHK_ERR_WIN32A(RPC_S_FP_UNDERFLOW) + CHK_ERR_WIN32A(RPC_S_FP_OVERFLOW) + CHK_ERR_WIN32A(RPC_X_NO_MORE_ENTRIES) + CHK_ERR_WIN32A(RPC_X_SS_CHAR_TRANS_OPEN_FAIL) + CHK_ERR_WIN32A(RPC_X_SS_CHAR_TRANS_SHORT_FILE) + CHK_ERR_WIN32A(RPC_X_SS_IN_NULL_CONTEXT) + CHK_ERR_WIN32A(RPC_X_SS_CONTEXT_DAMAGED) + CHK_ERR_WIN32A(RPC_X_SS_HANDLES_MISMATCH) + CHK_ERR_WIN32A(RPC_X_SS_CANNOT_GET_CALL_HANDLE) + CHK_ERR_WIN32A(RPC_X_NULL_REF_POINTER) + CHK_ERR_WIN32A(RPC_X_ENUM_VALUE_OUT_OF_RANGE) + CHK_ERR_WIN32A(RPC_X_BYTE_COUNT_TOO_SMALL) + CHK_ERR_WIN32A(RPC_X_BAD_STUB_DATA) + CHK_ERR_WIN32A(ERROR_INVALID_USER_BUFFER) + CHK_ERR_WIN32A(ERROR_UNRECOGNIZED_MEDIA) + CHK_ERR_WIN32A(ERROR_NO_TRUST_LSA_SECRET) + CHK_ERR_WIN32A(ERROR_NO_TRUST_SAM_ACCOUNT) + CHK_ERR_WIN32A(ERROR_TRUSTED_DOMAIN_FAILURE) + CHK_ERR_WIN32A(ERROR_TRUSTED_RELATIONSHIP_FAILURE) + CHK_ERR_WIN32A(ERROR_TRUST_FAILURE) + CHK_ERR_WIN32A(RPC_S_CALL_IN_PROGRESS) + CHK_ERR_WIN32A(ERROR_NETLOGON_NOT_STARTED) + CHK_ERR_WIN32A(ERROR_ACCOUNT_EXPIRED) + CHK_ERR_WIN32A(ERROR_REDIRECTOR_HAS_OPEN_HANDLES) + CHK_ERR_WIN32A(ERROR_PRINTER_DRIVER_ALREADY_INSTALLED) + CHK_ERR_WIN32A(ERROR_UNKNOWN_PORT) + CHK_ERR_WIN32A(ERROR_UNKNOWN_PRINTER_DRIVER) + CHK_ERR_WIN32A(ERROR_UNKNOWN_PRINTPROCESSOR) + CHK_ERR_WIN32A(ERROR_INVALID_SEPARATOR_FILE) + CHK_ERR_WIN32A(ERROR_INVALID_PRIORITY) + CHK_ERR_WIN32A(ERROR_INVALID_PRINTER_NAME) + CHK_ERR_WIN32A(ERROR_PRINTER_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_INVALID_PRINTER_COMMAND) + CHK_ERR_WIN32A(ERROR_INVALID_DATATYPE) + CHK_ERR_WIN32A(ERROR_INVALID_ENVIRONMENT) + CHK_ERR_WIN32A(RPC_S_NO_MORE_BINDINGS) + CHK_ERR_WIN32A(ERROR_NOLOGON_INTERDOMAIN_TRUST_ACCOUNT) + CHK_ERR_WIN32A(ERROR_NOLOGON_WORKSTATION_TRUST_ACCOUNT) + CHK_ERR_WIN32A(ERROR_NOLOGON_SERVER_TRUST_ACCOUNT) + CHK_ERR_WIN32A(ERROR_DOMAIN_TRUST_INCONSISTENT) + CHK_ERR_WIN32A(ERROR_SERVER_HAS_OPEN_HANDLES) + CHK_ERR_WIN32A(ERROR_RESOURCE_DATA_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_RESOURCE_TYPE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_RESOURCE_NAME_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_RESOURCE_LANG_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_NOT_ENOUGH_QUOTA) + CHK_ERR_WIN32A(RPC_S_NO_INTERFACES) + CHK_ERR_WIN32A(RPC_S_CALL_CANCELLED) + CHK_ERR_WIN32A(RPC_S_BINDING_INCOMPLETE) + CHK_ERR_WIN32A(RPC_S_COMM_FAILURE) + CHK_ERR_WIN32A(RPC_S_UNSUPPORTED_AUTHN_LEVEL) + CHK_ERR_WIN32A(RPC_S_NO_PRINC_NAME) + CHK_ERR_WIN32A(RPC_S_NOT_RPC_ERROR) + CHK_ERR_WIN32A(RPC_S_UUID_LOCAL_ONLY) + CHK_ERR_WIN32A(RPC_S_SEC_PKG_ERROR) + CHK_ERR_WIN32A(RPC_S_NOT_CANCELLED) + CHK_ERR_WIN32A(RPC_X_INVALID_ES_ACTION) + CHK_ERR_WIN32A(RPC_X_WRONG_ES_VERSION) + CHK_ERR_WIN32A(RPC_X_WRONG_STUB_VERSION) + CHK_ERR_WIN32A(RPC_X_INVALID_PIPE_OBJECT) + CHK_ERR_WIN32A(RPC_X_WRONG_PIPE_ORDER) + CHK_ERR_WIN32A(RPC_X_WRONG_PIPE_VERSION) + CHK_ERR_WIN32A(RPC_S_GROUP_MEMBER_NOT_FOUND) + CHK_ERR_WIN32A(EPT_S_CANT_CREATE) + CHK_ERR_WIN32A(RPC_S_INVALID_OBJECT) + CHK_ERR_WIN32A(ERROR_INVALID_TIME) + CHK_ERR_WIN32A(ERROR_INVALID_FORM_NAME) + CHK_ERR_WIN32A(ERROR_INVALID_FORM_SIZE) + CHK_ERR_WIN32A(ERROR_ALREADY_WAITING) + CHK_ERR_WIN32A(ERROR_PRINTER_DELETED) + CHK_ERR_WIN32A(ERROR_INVALID_PRINTER_STATE) + CHK_ERR_WIN32A(ERROR_PASSWORD_MUST_CHANGE) + CHK_ERR_WIN32A(ERROR_DOMAIN_CONTROLLER_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_ACCOUNT_LOCKED_OUT) + CHK_ERR_WIN32A(OR_INVALID_OXID) + CHK_ERR_WIN32A(OR_INVALID_OID) + CHK_ERR_WIN32A(OR_INVALID_SET) + CHK_ERR_WIN32A(RPC_S_SEND_INCOMPLETE) + CHK_ERR_WIN32A(RPC_S_INVALID_ASYNC_HANDLE) + CHK_ERR_WIN32A(RPC_S_INVALID_ASYNC_CALL) + CHK_ERR_WIN32A(RPC_X_PIPE_CLOSED) + CHK_ERR_WIN32A(RPC_X_PIPE_DISCIPLINE_ERROR) + CHK_ERR_WIN32A(RPC_X_PIPE_EMPTY) + CHK_ERR_WIN32A(ERROR_NO_SITENAME) + CHK_ERR_WIN32A(ERROR_CANT_ACCESS_FILE) + CHK_ERR_WIN32A(ERROR_CANT_RESOLVE_FILENAME) + CHK_ERR_WIN32A(ERROR_INVALID_PIXEL_FORMAT) + CHK_ERR_WIN32A(ERROR_BAD_DRIVER) + CHK_ERR_WIN32A(ERROR_INVALID_WINDOW_STYLE) + CHK_ERR_WIN32A(ERROR_METAFILE_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_TRANSFORM_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_CLIPPING_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_INVALID_CMM) + CHK_ERR_WIN32A(ERROR_INVALID_PROFILE) + CHK_ERR_WIN32A(ERROR_TAG_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_TAG_NOT_PRESENT) + CHK_ERR_WIN32A(ERROR_DUPLICATE_TAG) + CHK_ERR_WIN32A(ERROR_PROFILE_NOT_ASSOCIATED_WITH_DEVICE) + CHK_ERR_WIN32A(ERROR_PROFILE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_INVALID_COLORSPACE) + CHK_ERR_WIN32A(ERROR_ICM_NOT_ENABLED) + CHK_ERR_WIN32A(ERROR_DELETING_ICM_XFORM) + CHK_ERR_WIN32A(ERROR_INVALID_TRANSFORM) + CHK_ERR_WIN32A(ERROR_COLORSPACE_MISMATCH) + CHK_ERR_WIN32A(ERROR_INVALID_COLORINDEX) + CHK_ERR_WIN32A(ERROR_CONNECTED_OTHER_PASSWORD) + CHK_ERR_WIN32A(ERROR_BAD_USERNAME) + CHK_ERR_WIN32A(ERROR_NOT_CONNECTED) + CHK_ERR_WIN32A(ERROR_OPEN_FILES) + CHK_ERR_WIN32A(ERROR_ACTIVE_CONNECTIONS) + CHK_ERR_WIN32A(ERROR_DEVICE_IN_USE) + CHK_ERR_WIN32A(ERROR_UNKNOWN_PRINT_MONITOR) + CHK_ERR_WIN32A(ERROR_PRINTER_DRIVER_IN_USE) + CHK_ERR_WIN32A(ERROR_SPOOL_FILE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_SPL_NO_STARTDOC) + CHK_ERR_WIN32A(ERROR_SPL_NO_ADDJOB) + CHK_ERR_WIN32A(ERROR_PRINT_PROCESSOR_ALREADY_INSTALLED) + CHK_ERR_WIN32A(ERROR_PRINT_MONITOR_ALREADY_INSTALLED) + CHK_ERR_WIN32A(ERROR_INVALID_PRINT_MONITOR) + CHK_ERR_WIN32A(ERROR_PRINT_MONITOR_IN_USE) + CHK_ERR_WIN32A(ERROR_PRINTER_HAS_JOBS_QUEUED) + CHK_ERR_WIN32A(ERROR_SUCCESS_REBOOT_REQUIRED) + CHK_ERR_WIN32A(ERROR_SUCCESS_RESTART_REQUIRED) + CHK_ERR_WIN32A(ERROR_PRINTER_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_WINS_INTERNAL) + CHK_ERR_WIN32A(ERROR_CAN_NOT_DEL_LOCAL_WINS) + CHK_ERR_WIN32A(ERROR_STATIC_INIT) + CHK_ERR_WIN32A(ERROR_INC_BACKUP) + CHK_ERR_WIN32A(ERROR_FULL_BACKUP) + CHK_ERR_WIN32A(ERROR_REC_NON_EXISTENT) + CHK_ERR_WIN32A(ERROR_RPL_NOT_ALLOWED) + CHK_ERR_WIN32A(ERROR_DHCP_ADDRESS_CONFLICT) + CHK_ERR_WIN32A(ERROR_WMI_GUID_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_WMI_INSTANCE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_WMI_ITEMID_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_WMI_TRY_AGAIN) + CHK_ERR_WIN32A(ERROR_WMI_DP_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_WMI_UNRESOLVED_INSTANCE_REF) + CHK_ERR_WIN32A(ERROR_WMI_ALREADY_ENABLED) + CHK_ERR_WIN32A(ERROR_WMI_GUID_DISCONNECTED) + CHK_ERR_WIN32A(ERROR_WMI_SERVER_UNAVAILABLE) + CHK_ERR_WIN32A(ERROR_WMI_DP_FAILED) + CHK_ERR_WIN32A(ERROR_WMI_INVALID_MOF) + CHK_ERR_WIN32A(ERROR_WMI_INVALID_REGINFO) + CHK_ERR_WIN32A(ERROR_WMI_ALREADY_DISABLED) + CHK_ERR_WIN32A(ERROR_WMI_READ_ONLY) + CHK_ERR_WIN32A(ERROR_WMI_SET_FAILURE) + CHK_ERR_WIN32A(ERROR_INVALID_MEDIA) + CHK_ERR_WIN32A(ERROR_INVALID_LIBRARY) + CHK_ERR_WIN32A(ERROR_INVALID_MEDIA_POOL) + CHK_ERR_WIN32A(ERROR_DRIVE_MEDIA_MISMATCH) + CHK_ERR_WIN32A(ERROR_MEDIA_OFFLINE) + CHK_ERR_WIN32A(ERROR_LIBRARY_OFFLINE) + CHK_ERR_WIN32A(ERROR_EMPTY) + CHK_ERR_WIN32A(ERROR_NOT_EMPTY) + CHK_ERR_WIN32A(ERROR_MEDIA_UNAVAILABLE) + CHK_ERR_WIN32A(ERROR_RESOURCE_DISABLED) + CHK_ERR_WIN32A(ERROR_INVALID_CLEANER) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_CLEAN) + CHK_ERR_WIN32A(ERROR_OBJECT_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_DATABASE_FAILURE) + CHK_ERR_WIN32A(ERROR_DATABASE_FULL) + CHK_ERR_WIN32A(ERROR_MEDIA_INCOMPATIBLE) + CHK_ERR_WIN32A(ERROR_RESOURCE_NOT_PRESENT) + CHK_ERR_WIN32A(ERROR_INVALID_OPERATION) + CHK_ERR_WIN32A(ERROR_MEDIA_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_DEVICE_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_REQUEST_REFUSED) + CHK_ERR_WIN32A(ERROR_INVALID_DRIVE_OBJECT) + CHK_ERR_WIN32A(ERROR_LIBRARY_FULL) + CHK_ERR_WIN32A(ERROR_MEDIUM_NOT_ACCESSIBLE) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_LOAD_MEDIUM) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_INVENTORY_DRIVE) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_INVENTORY_SLOT) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_INVENTORY_TRANSPORT) + CHK_ERR_WIN32A(ERROR_TRANSPORT_FULL) + CHK_ERR_WIN32A(ERROR_CONTROLLING_IEPORT) + CHK_ERR_WIN32A(ERROR_UNABLE_TO_EJECT_MOUNTED_MEDIA) + CHK_ERR_WIN32A(ERROR_CLEANER_SLOT_SET) + CHK_ERR_WIN32A(ERROR_CLEANER_SLOT_NOT_SET) + CHK_ERR_WIN32A(ERROR_CLEANER_CARTRIDGE_SPENT) + CHK_ERR_WIN32A(ERROR_UNEXPECTED_OMID) + CHK_ERR_WIN32A(ERROR_CANT_DELETE_LAST_ITEM) + CHK_ERR_WIN32A(ERROR_MESSAGE_EXCEEDS_MAX_SIZE) + CHK_ERR_WIN32A(ERROR_FILE_OFFLINE) + CHK_ERR_WIN32A(ERROR_REMOTE_STORAGE_NOT_ACTIVE) + CHK_ERR_WIN32A(ERROR_REMOTE_STORAGE_MEDIA_ERROR) + CHK_ERR_WIN32A(ERROR_NOT_A_REPARSE_POINT) + CHK_ERR_WIN32A(ERROR_REPARSE_ATTRIBUTE_CONFLICT) + CHK_ERR_WIN32A(ERROR_INVALID_REPARSE_DATA) + CHK_ERR_WIN32A(ERROR_DEPENDENT_RESOURCE_EXISTS) + CHK_ERR_WIN32A(ERROR_DEPENDENCY_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_DEPENDENCY_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_RESOURCE_NOT_ONLINE) + CHK_ERR_WIN32A(ERROR_HOST_NODE_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_RESOURCE_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_RESOURCE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_SHUTDOWN_CLUSTER) + CHK_ERR_WIN32A(ERROR_CANT_EVICT_ACTIVE_NODE) + CHK_ERR_WIN32A(ERROR_OBJECT_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_OBJECT_IN_LIST) + CHK_ERR_WIN32A(ERROR_GROUP_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_GROUP_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_GROUP_NOT_ONLINE) + CHK_ERR_WIN32A(ERROR_HOST_NODE_NOT_RESOURCE_OWNER) + CHK_ERR_WIN32A(ERROR_HOST_NODE_NOT_GROUP_OWNER) + CHK_ERR_WIN32A(ERROR_RESMON_CREATE_FAILED) + CHK_ERR_WIN32A(ERROR_RESMON_ONLINE_FAILED) + CHK_ERR_WIN32A(ERROR_RESOURCE_ONLINE) + CHK_ERR_WIN32A(ERROR_QUORUM_RESOURCE) + CHK_ERR_WIN32A(ERROR_NOT_QUORUM_CAPABLE) + CHK_ERR_WIN32A(ERROR_CLUSTER_SHUTTING_DOWN) + CHK_ERR_WIN32A(ERROR_INVALID_STATE) + CHK_ERR_WIN32A(ERROR_RESOURCE_PROPERTIES_STORED) + CHK_ERR_WIN32A(ERROR_NOT_QUORUM_CLASS) + CHK_ERR_WIN32A(ERROR_CORE_RESOURCE) + CHK_ERR_WIN32A(ERROR_QUORUM_RESOURCE_ONLINE_FAILED) + CHK_ERR_WIN32A(ERROR_QUORUMLOG_OPEN_FAILED) + CHK_ERR_WIN32A(ERROR_CLUSTERLOG_CORRUPT) + CHK_ERR_WIN32A(ERROR_CLUSTERLOG_RECORD_EXCEEDS_MAXSIZE) + CHK_ERR_WIN32A(ERROR_CLUSTERLOG_EXCEEDS_MAXSIZE) + CHK_ERR_WIN32A(ERROR_CLUSTERLOG_CHKPOINT_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CLUSTERLOG_NOT_ENOUGH_SPACE) + CHK_ERR_WIN32A(ERROR_ENCRYPTION_FAILED) + CHK_ERR_WIN32A(ERROR_DECRYPTION_FAILED) + CHK_ERR_WIN32A(ERROR_FILE_ENCRYPTED) + CHK_ERR_WIN32A(ERROR_NO_RECOVERY_POLICY) + CHK_ERR_WIN32A(ERROR_NO_EFS) + CHK_ERR_WIN32A(ERROR_WRONG_EFS) + CHK_ERR_WIN32A(ERROR_NO_USER_KEYS) + CHK_ERR_WIN32A(ERROR_FILE_NOT_ENCRYPTED) + CHK_ERR_WIN32A(ERROR_NOT_EXPORT_FORMAT) + CHK_ERR_WIN32A(ERROR_NO_BROWSER_SERVERS_FOUND) + CHK_ERR_WIN32A(ERROR_CTX_WINSTATION_NAME_INVALID) + CHK_ERR_WIN32A(ERROR_CTX_INVALID_PD) + CHK_ERR_WIN32A(ERROR_CTX_PD_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CTX_WD_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CTX_CANNOT_MAKE_EVENTLOG_ENTRY) + CHK_ERR_WIN32A(ERROR_CTX_SERVICE_NAME_COLLISION) + CHK_ERR_WIN32A(ERROR_CTX_CLOSE_PENDING) + CHK_ERR_WIN32A(ERROR_CTX_NO_OUTBUF) + CHK_ERR_WIN32A(ERROR_CTX_MODEM_INF_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CTX_INVALID_MODEMNAME) + CHK_ERR_WIN32A(ERROR_CTX_MODEM_RESPONSE_ERROR) + CHK_ERR_WIN32A(ERROR_CTX_MODEM_RESPONSE_TIMEOUT) + CHK_ERR_WIN32A(ERROR_CTX_MODEM_RESPONSE_NO_CARRIER) + CHK_ERR_WIN32A(ERROR_CTX_MODEM_RESPONSE_NO_DIALTONE) + CHK_ERR_WIN32A(ERROR_CTX_MODEM_RESPONSE_BUSY) + CHK_ERR_WIN32A(ERROR_CTX_MODEM_RESPONSE_VOICE) + CHK_ERR_WIN32A(ERROR_CTX_TD_ERROR) + CHK_ERR_WIN32A(ERROR_CTX_WINSTATION_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CTX_WINSTATION_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_CTX_WINSTATION_BUSY) + CHK_ERR_WIN32A(ERROR_CTX_BAD_VIDEO_MODE) + CHK_ERR_WIN32A(ERROR_CTX_GRAPHICS_INVALID) + CHK_ERR_WIN32A(ERROR_CTX_LOGON_DISABLED) + CHK_ERR_WIN32A(ERROR_CTX_NOT_CONSOLE) + CHK_ERR_WIN32A(ERROR_CTX_CLIENT_QUERY_TIMEOUT) + CHK_ERR_WIN32A(ERROR_CTX_CONSOLE_DISCONNECT) + CHK_ERR_WIN32A(ERROR_CTX_CONSOLE_CONNECT) + CHK_ERR_WIN32A(ERROR_CTX_SHADOW_DENIED) + CHK_ERR_WIN32A(ERROR_CTX_WINSTATION_ACCESS_DENIED) + CHK_ERR_WIN32A(ERROR_CTX_INVALID_WD) + CHK_ERR_WIN32A(ERROR_CTX_SHADOW_INVALID) + CHK_ERR_WIN32A(ERROR_CTX_SHADOW_DISABLED) + CHK_ERR_WIN32A(FRS_ERR_INVALID_API_SEQUENCE) + CHK_ERR_WIN32A(FRS_ERR_STARTING_SERVICE) + CHK_ERR_WIN32A(FRS_ERR_STOPPING_SERVICE) + CHK_ERR_WIN32A(FRS_ERR_INTERNAL_API) + CHK_ERR_WIN32A(FRS_ERR_INTERNAL) + CHK_ERR_WIN32A(FRS_ERR_SERVICE_COMM) + CHK_ERR_WIN32A(FRS_ERR_INSUFFICIENT_PRIV) + CHK_ERR_WIN32A(FRS_ERR_AUTHENTICATION) + CHK_ERR_WIN32A(FRS_ERR_PARENT_INSUFFICIENT_PRIV) + CHK_ERR_WIN32A(FRS_ERR_PARENT_AUTHENTICATION) + CHK_ERR_WIN32A(FRS_ERR_CHILD_TO_PARENT_COMM) + CHK_ERR_WIN32A(FRS_ERR_PARENT_TO_CHILD_COMM) + CHK_ERR_WIN32A(FRS_ERR_SYSVOL_POPULATE) + CHK_ERR_WIN32A(FRS_ERR_SYSVOL_POPULATE_TIMEOUT) + CHK_ERR_WIN32A(FRS_ERR_SYSVOL_IS_BUSY) + CHK_ERR_WIN32A(FRS_ERR_SYSVOL_DEMOTE) + CHK_ERR_WIN32A(FRS_ERR_INVALID_SERVICE_PARAMETER) +// CHK_ERR_WIN32A(DS_S_SUCCESS) + CHK_ERR_WIN32A(ERROR_DS_NOT_INSTALLED) + CHK_ERR_WIN32A(ERROR_DS_MEMBERSHIP_EVALUATED_LOCALLY) + CHK_ERR_WIN32A(ERROR_DS_NO_ATTRIBUTE_OR_VALUE) + CHK_ERR_WIN32A(ERROR_DS_INVALID_ATTRIBUTE_SYNTAX) + CHK_ERR_WIN32A(ERROR_DS_ATTRIBUTE_TYPE_UNDEFINED) + CHK_ERR_WIN32A(ERROR_DS_ATTRIBUTE_OR_VALUE_EXISTS) + CHK_ERR_WIN32A(ERROR_DS_BUSY) + CHK_ERR_WIN32A(ERROR_DS_UNAVAILABLE) + CHK_ERR_WIN32A(ERROR_DS_NO_RIDS_ALLOCATED) + CHK_ERR_WIN32A(ERROR_DS_NO_MORE_RIDS) + CHK_ERR_WIN32A(ERROR_DS_INCORRECT_ROLE_OWNER) + CHK_ERR_WIN32A(ERROR_DS_RIDMGR_INIT_ERROR) + CHK_ERR_WIN32A(ERROR_DS_OBJ_CLASS_VIOLATION) + CHK_ERR_WIN32A(ERROR_DS_CANT_ON_NON_LEAF) + CHK_ERR_WIN32A(ERROR_DS_CANT_ON_RDN) + CHK_ERR_WIN32A(ERROR_DS_CANT_MOD_OBJ_CLASS) + CHK_ERR_WIN32A(ERROR_DS_CROSS_DOM_MOVE_ERROR) + CHK_ERR_WIN32A(ERROR_DS_GC_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_SHARED_POLICY) + CHK_ERR_WIN32A(ERROR_POLICY_OBJECT_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_POLICY_ONLY_IN_DS) + CHK_ERR_WIN32A(ERROR_PROMOTION_ACTIVE) + CHK_ERR_WIN32A(ERROR_NO_PROMOTION_ACTIVE) + CHK_ERR_WIN32A(ERROR_DS_OPERATIONS_ERROR) + CHK_ERR_WIN32A(ERROR_DS_PROTOCOL_ERROR) + CHK_ERR_WIN32A(ERROR_DS_TIMELIMIT_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DS_SIZELIMIT_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DS_ADMIN_LIMIT_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DS_COMPARE_FALSE) + CHK_ERR_WIN32A(ERROR_DS_COMPARE_TRUE) + CHK_ERR_WIN32A(ERROR_DS_AUTH_METHOD_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_DS_STRONG_AUTH_REQUIRED) + CHK_ERR_WIN32A(ERROR_DS_INAPPROPRIATE_AUTH) + CHK_ERR_WIN32A(ERROR_DS_AUTH_UNKNOWN) + CHK_ERR_WIN32A(ERROR_DS_REFERRAL) + CHK_ERR_WIN32A(ERROR_DS_UNAVAILABLE_CRIT_EXTENSION) + CHK_ERR_WIN32A(ERROR_DS_CONFIDENTIALITY_REQUIRED) + CHK_ERR_WIN32A(ERROR_DS_INAPPROPRIATE_MATCHING) + CHK_ERR_WIN32A(ERROR_DS_CONSTRAINT_VIOLATION) + CHK_ERR_WIN32A(ERROR_DS_NO_SUCH_OBJECT) + CHK_ERR_WIN32A(ERROR_DS_ALIAS_PROBLEM) + CHK_ERR_WIN32A(ERROR_DS_INVALID_DN_SYNTAX) + CHK_ERR_WIN32A(ERROR_DS_IS_LEAF) + CHK_ERR_WIN32A(ERROR_DS_ALIAS_DEREF_PROBLEM) + CHK_ERR_WIN32A(ERROR_DS_UNWILLING_TO_PERFORM) + CHK_ERR_WIN32A(ERROR_DS_LOOP_DETECT) + CHK_ERR_WIN32A(ERROR_DS_NAMING_VIOLATION) + CHK_ERR_WIN32A(ERROR_DS_OBJECT_RESULTS_TOO_LARGE) + CHK_ERR_WIN32A(ERROR_DS_AFFECTS_MULTIPLE_DSAS) + CHK_ERR_WIN32A(ERROR_DS_SERVER_DOWN) + CHK_ERR_WIN32A(ERROR_DS_LOCAL_ERROR) + CHK_ERR_WIN32A(ERROR_DS_ENCODING_ERROR) + CHK_ERR_WIN32A(ERROR_DS_DECODING_ERROR) + CHK_ERR_WIN32A(ERROR_DS_FILTER_UNKNOWN) + CHK_ERR_WIN32A(ERROR_DS_PARAM_ERROR) + CHK_ERR_WIN32A(ERROR_DS_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_DS_NO_RESULTS_RETURNED) + CHK_ERR_WIN32A(ERROR_DS_CONTROL_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_DS_CLIENT_LOOP) + CHK_ERR_WIN32A(ERROR_DS_REFERRAL_LIMIT_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DS_ROOT_MUST_BE_NC) + CHK_ERR_WIN32A(ERROR_DS_ADD_REPLICA_INHIBITED) + CHK_ERR_WIN32A(ERROR_DS_ATT_NOT_DEF_IN_SCHEMA) + CHK_ERR_WIN32A(ERROR_DS_MAX_OBJ_SIZE_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DS_OBJ_STRING_NAME_EXISTS) + CHK_ERR_WIN32A(ERROR_DS_NO_RDN_DEFINED_IN_SCHEMA) + CHK_ERR_WIN32A(ERROR_DS_RDN_DOESNT_MATCH_SCHEMA) + CHK_ERR_WIN32A(ERROR_DS_NO_REQUESTED_ATTS_FOUND) + CHK_ERR_WIN32A(ERROR_DS_USER_BUFFER_TO_SMALL) + CHK_ERR_WIN32A(ERROR_DS_ATT_IS_NOT_ON_OBJ) + CHK_ERR_WIN32A(ERROR_DS_ILLEGAL_MOD_OPERATION) + CHK_ERR_WIN32A(ERROR_DS_OBJ_TOO_LARGE) + CHK_ERR_WIN32A(ERROR_DS_BAD_INSTANCE_TYPE) + CHK_ERR_WIN32A(ERROR_DS_MASTERDSA_REQUIRED) + CHK_ERR_WIN32A(ERROR_DS_OBJECT_CLASS_REQUIRED) + CHK_ERR_WIN32A(ERROR_DS_MISSING_REQUIRED_ATT) + CHK_ERR_WIN32A(ERROR_DS_ATT_NOT_DEF_FOR_CLASS) + CHK_ERR_WIN32A(ERROR_DS_ATT_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_DS_CANT_ADD_ATT_VALUES) + CHK_ERR_WIN32A(ERROR_DS_SINGLE_VALUE_CONSTRAINT) + CHK_ERR_WIN32A(ERROR_DS_RANGE_CONSTRAINT) + CHK_ERR_WIN32A(ERROR_DS_ATT_VAL_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_DS_CANT_REM_MISSING_ATT) + CHK_ERR_WIN32A(ERROR_DS_CANT_REM_MISSING_ATT_VAL) + CHK_ERR_WIN32A(ERROR_DS_ROOT_CANT_BE_SUBREF) + CHK_ERR_WIN32A(ERROR_DS_NO_CHAINING) + CHK_ERR_WIN32A(ERROR_DS_NO_CHAINED_EVAL) + CHK_ERR_WIN32A(ERROR_DS_NO_PARENT_OBJECT) + CHK_ERR_WIN32A(ERROR_DS_PARENT_IS_AN_ALIAS) + CHK_ERR_WIN32A(ERROR_DS_CANT_MIX_MASTER_AND_REPS) + CHK_ERR_WIN32A(ERROR_DS_CHILDREN_EXIST) + CHK_ERR_WIN32A(ERROR_DS_OBJ_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_DS_ALIASED_OBJ_MISSING) + CHK_ERR_WIN32A(ERROR_DS_BAD_NAME_SYNTAX) + CHK_ERR_WIN32A(ERROR_DS_ALIAS_POINTS_TO_ALIAS) + CHK_ERR_WIN32A(ERROR_DS_CANT_DEREF_ALIAS) + CHK_ERR_WIN32A(ERROR_DS_OUT_OF_SCOPE) + CHK_ERR_WIN32A(ERROR_DS_CANT_DELETE_DSA_OBJ) + CHK_ERR_WIN32A(ERROR_DS_GENERIC_ERROR) + CHK_ERR_WIN32A(ERROR_DS_DSA_MUST_BE_INT_MASTER) + CHK_ERR_WIN32A(ERROR_DS_CLASS_NOT_DSA) + CHK_ERR_WIN32A(ERROR_DS_INSUFF_ACCESS_RIGHTS) + CHK_ERR_WIN32A(ERROR_DS_ILLEGAL_SUPERIOR) + CHK_ERR_WIN32A(ERROR_DS_ATTRIBUTE_OWNED_BY_SAM) + CHK_ERR_WIN32A(ERROR_DS_NAME_TOO_MANY_PARTS) + CHK_ERR_WIN32A(ERROR_DS_NAME_TOO_LONG) + CHK_ERR_WIN32A(ERROR_DS_NAME_VALUE_TOO_LONG) + CHK_ERR_WIN32A(ERROR_DS_NAME_UNPARSEABLE) + CHK_ERR_WIN32A(ERROR_DS_NAME_TYPE_UNKNOWN) + CHK_ERR_WIN32A(ERROR_DS_NOT_AN_OBJECT) + CHK_ERR_WIN32A(ERROR_DS_SEC_DESC_TOO_SHORT) + CHK_ERR_WIN32A(ERROR_DS_SEC_DESC_INVALID) + CHK_ERR_WIN32A(ERROR_DS_NO_DELETED_NAME) + CHK_ERR_WIN32A(ERROR_DS_SUBREF_MUST_HAVE_PARENT) + CHK_ERR_WIN32A(ERROR_DS_NCNAME_MUST_BE_NC) + CHK_ERR_WIN32A(ERROR_DS_CANT_ADD_SYSTEM_ONLY) + CHK_ERR_WIN32A(ERROR_DS_CLASS_MUST_BE_CONCRETE) + CHK_ERR_WIN32A(ERROR_DS_INVALID_DMD) + CHK_ERR_WIN32A(ERROR_DS_OBJ_GUID_EXISTS) + CHK_ERR_WIN32A(ERROR_DS_NOT_ON_BACKLINK) + CHK_ERR_WIN32A(ERROR_DS_NO_CROSSREF_FOR_NC) + CHK_ERR_WIN32A(ERROR_DS_SHUTTING_DOWN) + CHK_ERR_WIN32A(ERROR_DS_UNKNOWN_OPERATION) + CHK_ERR_WIN32A(ERROR_DS_INVALID_ROLE_OWNER) + CHK_ERR_WIN32A(ERROR_DS_COULDNT_CONTACT_FSMO) + CHK_ERR_WIN32A(ERROR_DS_CROSS_NC_DN_RENAME) + CHK_ERR_WIN32A(ERROR_DS_CANT_MOD_SYSTEM_ONLY) + CHK_ERR_WIN32A(ERROR_DS_REPLICATOR_ONLY) + CHK_ERR_WIN32A(ERROR_DS_OBJ_CLASS_NOT_DEFINED) + CHK_ERR_WIN32A(ERROR_DS_OBJ_CLASS_NOT_SUBCLASS) + CHK_ERR_WIN32A(ERROR_DS_NAME_REFERENCE_INVALID) + CHK_ERR_WIN32A(ERROR_DS_CROSS_REF_EXISTS) + CHK_ERR_WIN32A(ERROR_DS_CANT_DEL_MASTER_CROSSREF) + CHK_ERR_WIN32A(ERROR_DS_SUBTREE_NOTIFY_NOT_NC_HEAD) + CHK_ERR_WIN32A(ERROR_DS_NOTIFY_FILTER_TOO_COMPLEX) + CHK_ERR_WIN32A(ERROR_DS_DUP_RDN) + CHK_ERR_WIN32A(ERROR_DS_DUP_OID) + CHK_ERR_WIN32A(ERROR_DS_DUP_MAPI_ID) + CHK_ERR_WIN32A(ERROR_DS_DUP_SCHEMA_ID_GUID) + CHK_ERR_WIN32A(ERROR_DS_DUP_LDAP_DISPLAY_NAME) + CHK_ERR_WIN32A(ERROR_DS_SEMANTIC_ATT_TEST) + CHK_ERR_WIN32A(ERROR_DS_SYNTAX_MISMATCH) + CHK_ERR_WIN32A(ERROR_DS_EXISTS_IN_MUST_HAVE) + CHK_ERR_WIN32A(ERROR_DS_EXISTS_IN_MAY_HAVE) + CHK_ERR_WIN32A(ERROR_DS_NONEXISTENT_MAY_HAVE) + CHK_ERR_WIN32A(ERROR_DS_NONEXISTENT_MUST_HAVE) + CHK_ERR_WIN32A(ERROR_DS_AUX_CLS_TEST_FAIL) + CHK_ERR_WIN32A(ERROR_DS_NONEXISTENT_POSS_SUP) + CHK_ERR_WIN32A(ERROR_DS_SUB_CLS_TEST_FAIL) + CHK_ERR_WIN32A(ERROR_DS_BAD_RDN_ATT_ID_SYNTAX) + CHK_ERR_WIN32A(ERROR_DS_EXISTS_IN_AUX_CLS) + CHK_ERR_WIN32A(ERROR_DS_EXISTS_IN_SUB_CLS) + CHK_ERR_WIN32A(ERROR_DS_EXISTS_IN_POSS_SUP) + CHK_ERR_WIN32A(ERROR_DS_RECALCSCHEMA_FAILED) + CHK_ERR_WIN32A(ERROR_DS_TREE_DELETE_NOT_FINISHED) + CHK_ERR_WIN32A(ERROR_DS_CANT_DELETE) + CHK_ERR_WIN32A(ERROR_DS_ATT_SCHEMA_REQ_ID) + CHK_ERR_WIN32A(ERROR_DS_BAD_ATT_SCHEMA_SYNTAX) + CHK_ERR_WIN32A(ERROR_DS_CANT_CACHE_ATT) + CHK_ERR_WIN32A(ERROR_DS_CANT_CACHE_CLASS) + CHK_ERR_WIN32A(ERROR_DS_CANT_REMOVE_ATT_CACHE) + CHK_ERR_WIN32A(ERROR_DS_CANT_REMOVE_CLASS_CACHE) + CHK_ERR_WIN32A(ERROR_DS_CANT_RETRIEVE_DN) + CHK_ERR_WIN32A(ERROR_DS_MISSING_SUPREF) + CHK_ERR_WIN32A(ERROR_DS_CANT_RETRIEVE_INSTANCE) + CHK_ERR_WIN32A(ERROR_DS_CODE_INCONSISTENCY) + CHK_ERR_WIN32A(ERROR_DS_DATABASE_ERROR) + CHK_ERR_WIN32A(ERROR_DS_GOVERNSID_MISSING) + CHK_ERR_WIN32A(ERROR_DS_MISSING_EXPECTED_ATT) + CHK_ERR_WIN32A(ERROR_DS_NCNAME_MISSING_CR_REF) + CHK_ERR_WIN32A(ERROR_DS_SECURITY_CHECKING_ERROR) + CHK_ERR_WIN32A(ERROR_DS_SCHEMA_NOT_LOADED) + CHK_ERR_WIN32A(ERROR_DS_SCHEMA_ALLOC_FAILED) + CHK_ERR_WIN32A(ERROR_DS_ATT_SCHEMA_REQ_SYNTAX) + CHK_ERR_WIN32A(ERROR_DS_GCVERIFY_ERROR) + CHK_ERR_WIN32A(ERROR_DS_DRA_SCHEMA_MISMATCH) + CHK_ERR_WIN32A(ERROR_DS_CANT_FIND_DSA_OBJ) + CHK_ERR_WIN32A(ERROR_DS_CANT_FIND_EXPECTED_NC) + CHK_ERR_WIN32A(ERROR_DS_CANT_FIND_NC_IN_CACHE) + CHK_ERR_WIN32A(ERROR_DS_CANT_RETRIEVE_CHILD) + CHK_ERR_WIN32A(ERROR_DS_SECURITY_ILLEGAL_MODIFY) + CHK_ERR_WIN32A(ERROR_DS_CANT_REPLACE_HIDDEN_REC) + CHK_ERR_WIN32A(ERROR_DS_BAD_HIERARCHY_FILE) + CHK_ERR_WIN32A(ERROR_DS_BUILD_HIERARCHY_TABLE_FAILED) + CHK_ERR_WIN32A(ERROR_DS_CONFIG_PARAM_MISSING) + CHK_ERR_WIN32A(ERROR_DS_COUNTING_AB_INDICES_FAILED) + CHK_ERR_WIN32A(ERROR_DS_HIERARCHY_TABLE_MALLOC_FAILED) + CHK_ERR_WIN32A(ERROR_DS_INTERNAL_FAILURE) + CHK_ERR_WIN32A(ERROR_DS_UNKNOWN_ERROR) + CHK_ERR_WIN32A(ERROR_DS_ROOT_REQUIRES_CLASS_TOP) + CHK_ERR_WIN32A(ERROR_DS_REFUSING_FSMO_ROLES) + CHK_ERR_WIN32A(ERROR_DS_MISSING_FSMO_SETTINGS) + CHK_ERR_WIN32A(ERROR_DS_UNABLE_TO_SURRENDER_ROLES) + CHK_ERR_WIN32A(ERROR_DS_DRA_GENERIC) + CHK_ERR_WIN32A(ERROR_DS_DRA_INVALID_PARAMETER) + CHK_ERR_WIN32A(ERROR_DS_DRA_BUSY) + CHK_ERR_WIN32A(ERROR_DS_DRA_BAD_DN) + CHK_ERR_WIN32A(ERROR_DS_DRA_BAD_NC) + CHK_ERR_WIN32A(ERROR_DS_DRA_DN_EXISTS) + CHK_ERR_WIN32A(ERROR_DS_DRA_INTERNAL_ERROR) + CHK_ERR_WIN32A(ERROR_DS_DRA_INCONSISTENT_DIT) + CHK_ERR_WIN32A(ERROR_DS_DRA_CONNECTION_FAILED) + CHK_ERR_WIN32A(ERROR_DS_DRA_BAD_INSTANCE_TYPE) + CHK_ERR_WIN32A(ERROR_DS_DRA_OUT_OF_MEM) + CHK_ERR_WIN32A(ERROR_DS_DRA_MAIL_PROBLEM) + CHK_ERR_WIN32A(ERROR_DS_DRA_REF_ALREADY_EXISTS) + CHK_ERR_WIN32A(ERROR_DS_DRA_REF_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_DS_DRA_OBJ_IS_REP_SOURCE) + CHK_ERR_WIN32A(ERROR_DS_DRA_DB_ERROR) + CHK_ERR_WIN32A(ERROR_DS_DRA_NO_REPLICA) + CHK_ERR_WIN32A(ERROR_DS_DRA_ACCESS_DENIED) + CHK_ERR_WIN32A(ERROR_DS_DRA_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_DS_DRA_RPC_CANCELLED) + CHK_ERR_WIN32A(ERROR_DS_DRA_SOURCE_DISABLED) + CHK_ERR_WIN32A(ERROR_DS_DRA_SINK_DISABLED) + CHK_ERR_WIN32A(ERROR_DS_DRA_NAME_COLLISION) + CHK_ERR_WIN32A(ERROR_DS_DRA_SOURCE_REINSTALLED) + CHK_ERR_WIN32A(ERROR_DS_DRA_MISSING_PARENT) + CHK_ERR_WIN32A(ERROR_DS_DRA_PREEMPTED) + CHK_ERR_WIN32A(ERROR_DS_DRA_ABANDON_SYNC) + CHK_ERR_WIN32A(ERROR_DS_DRA_SHUTDOWN) + CHK_ERR_WIN32A(ERROR_DS_DRA_INCOMPATIBLE_PARTIAL_SET) + CHK_ERR_WIN32A(ERROR_DS_DRA_SOURCE_IS_PARTIAL_REPLICA) + CHK_ERR_WIN32A(ERROR_DS_DRA_EXTN_CONNECTION_FAILED) + CHK_ERR_WIN32A(ERROR_DS_INSTALL_SCHEMA_MISMATCH) + CHK_ERR_WIN32A(ERROR_DS_DUP_LINK_ID) + CHK_ERR_WIN32A(ERROR_DS_NAME_ERROR_RESOLVING) + CHK_ERR_WIN32A(ERROR_DS_NAME_ERROR_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_DS_NAME_ERROR_NOT_UNIQUE) + CHK_ERR_WIN32A(ERROR_DS_NAME_ERROR_NO_MAPPING) + CHK_ERR_WIN32A(ERROR_DS_NAME_ERROR_DOMAIN_ONLY) + CHK_ERR_WIN32A(ERROR_DS_NAME_ERROR_NO_SYNTACTICAL_MAPPING) + CHK_ERR_WIN32A(ERROR_DS_CONSTRUCTED_ATT_MOD) + CHK_ERR_WIN32A(ERROR_DS_WRONG_OM_OBJ_CLASS) + CHK_ERR_WIN32A(ERROR_DS_DRA_REPL_PENDING) + CHK_ERR_WIN32A(DNS_ERROR_RESPONSE_CODES_BASE) +// CHK_ERR_WIN32A(DNS_ERROR_MASK) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_FORMAT_ERROR) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_SERVER_FAILURE) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_NAME_ERROR) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_NOT_IMPLEMENTED) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_REFUSED) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_YXDOMAIN) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_YXRRSET) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_NXRRSET) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_NOTAUTH) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_NOTZONE) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_BADSIG) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_BADKEY) + CHK_ERR_WIN32A(DNS_ERROR_RCODE_BADTIME) + CHK_ERR_WIN32A(DNS_ERROR_PACKET_FMT_BASE) + CHK_ERR_WIN32A(DNS_INFO_NO_RECORDS) + CHK_ERR_WIN32A(DNS_ERROR_BAD_PACKET) + CHK_ERR_WIN32A(DNS_ERROR_NO_PACKET) + CHK_ERR_WIN32A(DNS_ERROR_RCODE) + CHK_ERR_WIN32A(DNS_ERROR_UNSECURE_PACKET) + CHK_ERR_WIN32A(DNS_ERROR_GENERAL_API_BASE) + CHK_ERR_WIN32A(DNS_ERROR_INVALID_TYPE) + CHK_ERR_WIN32A(DNS_ERROR_INVALID_IP_ADDRESS) + CHK_ERR_WIN32A(DNS_ERROR_INVALID_PROPERTY) + CHK_ERR_WIN32A(DNS_ERROR_TRY_AGAIN_LATER) + CHK_ERR_WIN32A(DNS_ERROR_NOT_UNIQUE) + CHK_ERR_WIN32A(DNS_ERROR_NON_RFC_NAME) + CHK_ERR_WIN32A(DNS_STATUS_FQDN) + CHK_ERR_WIN32A(DNS_STATUS_DOTTED_NAME) + CHK_ERR_WIN32A(DNS_STATUS_SINGLE_PART_NAME) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_BASE) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_DOES_NOT_EXIST) + CHK_ERR_WIN32A(DNS_ERROR_NO_ZONE_INFO) + CHK_ERR_WIN32A(DNS_ERROR_INVALID_ZONE_OPERATION) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_CONFIGURATION_ERROR) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_HAS_NO_SOA_RECORD) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_HAS_NO_NS_RECORDS) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_LOCKED) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_CREATION_FAILED) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_ALREADY_EXISTS) + CHK_ERR_WIN32A(DNS_ERROR_AUTOZONE_ALREADY_EXISTS) + CHK_ERR_WIN32A(DNS_ERROR_INVALID_ZONE_TYPE) + CHK_ERR_WIN32A(DNS_ERROR_SECONDARY_REQUIRES_MASTER_IP) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_NOT_SECONDARY) + CHK_ERR_WIN32A(DNS_ERROR_NEED_SECONDARY_ADDRESSES) + CHK_ERR_WIN32A(DNS_ERROR_WINS_INIT_FAILED) + CHK_ERR_WIN32A(DNS_ERROR_NEED_WINS_SERVERS) + CHK_ERR_WIN32A(DNS_ERROR_NBSTAT_INIT_FAILED) + CHK_ERR_WIN32A(DNS_ERROR_SOA_DELETE_INVALID) + CHK_ERR_WIN32A(DNS_ERROR_DATAFILE_BASE) + CHK_ERR_WIN32A(DNS_ERROR_PRIMARY_REQUIRES_DATAFILE) + CHK_ERR_WIN32A(DNS_ERROR_INVALID_DATAFILE_NAME) + CHK_ERR_WIN32A(DNS_ERROR_DATAFILE_OPEN_FAILURE) + CHK_ERR_WIN32A(DNS_ERROR_FILE_WRITEBACK_FAILED) + CHK_ERR_WIN32A(DNS_ERROR_DATAFILE_PARSING) + CHK_ERR_WIN32A(DNS_ERROR_DATABASE_BASE) + CHK_ERR_WIN32A(DNS_ERROR_RECORD_DOES_NOT_EXIST) + CHK_ERR_WIN32A(DNS_ERROR_RECORD_FORMAT) + CHK_ERR_WIN32A(DNS_ERROR_NODE_CREATION_FAILED) + CHK_ERR_WIN32A(DNS_ERROR_UNKNOWN_RECORD_TYPE) + CHK_ERR_WIN32A(DNS_ERROR_RECORD_TIMED_OUT) + CHK_ERR_WIN32A(DNS_ERROR_NAME_NOT_IN_ZONE) + CHK_ERR_WIN32A(DNS_ERROR_CNAME_LOOP) + CHK_ERR_WIN32A(DNS_ERROR_NODE_IS_CNAME) + CHK_ERR_WIN32A(DNS_ERROR_CNAME_COLLISION) + CHK_ERR_WIN32A(DNS_ERROR_RECORD_ONLY_AT_ZONE_ROOT) + CHK_ERR_WIN32A(DNS_ERROR_RECORD_ALREADY_EXISTS) + CHK_ERR_WIN32A(DNS_ERROR_SECONDARY_DATA) + CHK_ERR_WIN32A(DNS_ERROR_NO_CREATE_CACHE_DATA) + CHK_ERR_WIN32A(DNS_ERROR_NAME_DOES_NOT_EXIST) + CHK_ERR_WIN32A(DNS_WARNING_PTR_CREATE_FAILED) + CHK_ERR_WIN32A(DNS_WARNING_DOMAIN_UNDELETED) + CHK_ERR_WIN32A(DNS_ERROR_DS_UNAVAILABLE) + CHK_ERR_WIN32A(DNS_ERROR_DS_ZONE_ALREADY_EXISTS) + CHK_ERR_WIN32A(DNS_ERROR_NO_BOOTFILE_IF_DS_ZONE) + CHK_ERR_WIN32A(DNS_ERROR_OPERATION_BASE) + CHK_ERR_WIN32A(DNS_INFO_AXFR_COMPLETE) + CHK_ERR_WIN32A(DNS_ERROR_AXFR) + CHK_ERR_WIN32A(DNS_INFO_ADDED_LOCAL_WINS) + CHK_ERR_WIN32A(DNS_ERROR_SECURE_BASE) + CHK_ERR_WIN32A(DNS_STATUS_CONTINUE_NEEDED) + CHK_ERR_WIN32A(DNS_ERROR_SETUP_BASE) + CHK_ERR_WIN32A(DNS_ERROR_NO_TCPIP) + CHK_ERR_WIN32A(DNS_ERROR_NO_DNS_SERVERS) + CHK_ERR_WIN32A(WSABASEERR) + CHK_ERR_WIN32A(WSAEINTR) + CHK_ERR_WIN32A(WSAEBADF) + CHK_ERR_WIN32A(WSAEACCES) + CHK_ERR_WIN32A(WSAEFAULT) + CHK_ERR_WIN32A(WSAEINVAL) + CHK_ERR_WIN32A(WSAEMFILE) + CHK_ERR_WIN32A(WSAEWOULDBLOCK) + CHK_ERR_WIN32A(WSAEINPROGRESS) + CHK_ERR_WIN32A(WSAEALREADY) + CHK_ERR_WIN32A(WSAENOTSOCK) + CHK_ERR_WIN32A(WSAEDESTADDRREQ) + CHK_ERR_WIN32A(WSAEMSGSIZE) + CHK_ERR_WIN32A(WSAEPROTOTYPE) + CHK_ERR_WIN32A(WSAENOPROTOOPT) + CHK_ERR_WIN32A(WSAEPROTONOSUPPORT) + CHK_ERR_WIN32A(WSAESOCKTNOSUPPORT) + CHK_ERR_WIN32A(WSAEOPNOTSUPP) + CHK_ERR_WIN32A(WSAEPFNOSUPPORT) + CHK_ERR_WIN32A(WSAEAFNOSUPPORT) + CHK_ERR_WIN32A(WSAEADDRINUSE) + CHK_ERR_WIN32A(WSAEADDRNOTAVAIL) + CHK_ERR_WIN32A(WSAENETDOWN) + CHK_ERR_WIN32A(WSAENETUNREACH) + CHK_ERR_WIN32A(WSAENETRESET) + CHK_ERR_WIN32A(WSAECONNABORTED) + CHK_ERR_WIN32A(WSAECONNRESET) + CHK_ERR_WIN32A(WSAENOBUFS) + CHK_ERR_WIN32A(WSAEISCONN) + CHK_ERR_WIN32A(WSAENOTCONN) + CHK_ERR_WIN32A(WSAESHUTDOWN) + CHK_ERR_WIN32A(WSAETOOMANYREFS) + CHK_ERR_WIN32A(WSAETIMEDOUT) + CHK_ERR_WIN32A(WSAECONNREFUSED) + CHK_ERR_WIN32A(WSAELOOP) + CHK_ERR_WIN32A(WSAENAMETOOLONG) + CHK_ERR_WIN32A(WSAEHOSTDOWN) + CHK_ERR_WIN32A(WSAEHOSTUNREACH) + CHK_ERR_WIN32A(WSAENOTEMPTY) + CHK_ERR_WIN32A(WSAEPROCLIM) + CHK_ERR_WIN32A(WSAEUSERS) + CHK_ERR_WIN32A(WSAEDQUOT) + CHK_ERR_WIN32A(WSAESTALE) + CHK_ERR_WIN32A(WSAEREMOTE) + CHK_ERR_WIN32A(WSASYSNOTREADY) + CHK_ERR_WIN32A(WSAVERNOTSUPPORTED) + CHK_ERR_WIN32A(WSANOTINITIALISED) + CHK_ERR_WIN32A(WSAEDISCON) + CHK_ERR_WIN32A(WSAENOMORE) + CHK_ERR_WIN32A(WSAECANCELLED) + CHK_ERR_WIN32A(WSAEINVALIDPROCTABLE) + CHK_ERR_WIN32A(WSAEINVALIDPROVIDER) + CHK_ERR_WIN32A(WSAEPROVIDERFAILEDINIT) + CHK_ERR_WIN32A(WSASYSCALLFAILURE) + CHK_ERR_WIN32A(WSASERVICE_NOT_FOUND) + CHK_ERR_WIN32A(WSATYPE_NOT_FOUND) + CHK_ERR_WIN32A(WSA_E_NO_MORE) + CHK_ERR_WIN32A(WSA_E_CANCELLED) + CHK_ERR_WIN32A(WSAEREFUSED) + CHK_ERR_WIN32A(WSAHOST_NOT_FOUND) + CHK_ERR_WIN32A(WSATRY_AGAIN) + CHK_ERR_WIN32A(WSANO_RECOVERY) + CHK_ERR_WIN32A(WSANO_DATA) + CHK_ERR_WIN32A(WSA_QOS_RECEIVERS) + CHK_ERR_WIN32A(WSA_QOS_SENDERS) + CHK_ERR_WIN32A(WSA_QOS_NO_SENDERS) + CHK_ERR_WIN32A(WSA_QOS_NO_RECEIVERS) + CHK_ERR_WIN32A(WSA_QOS_REQUEST_CONFIRMED) + CHK_ERR_WIN32A(WSA_QOS_ADMISSION_FAILURE) + CHK_ERR_WIN32A(WSA_QOS_POLICY_FAILURE) + CHK_ERR_WIN32A(WSA_QOS_BAD_STYLE) + CHK_ERR_WIN32A(WSA_QOS_BAD_OBJECT) + CHK_ERR_WIN32A(WSA_QOS_TRAFFIC_CTRL_ERROR) + CHK_ERR_WIN32A(WSA_QOS_GENERIC_ERROR) + + CHK_ERRA(CO_E_ATTEMPT_TO_CREATE_OUTSIDE_CLIENT_CONTEXT) + CHK_ERRA(CO_E_SERVER_PAUSED) + CHK_ERRA(CO_E_SERVER_NOT_PAUSED) + CHK_ERRA(CO_E_CLASS_DISABLED) + CHK_ERRA(CO_E_CLRNOTAVAILABLE) + CHK_ERRA(CO_E_ASYNC_WORK_REJECTED) + CHK_ERRA(CO_E_SERVER_INIT_TIMEOUT) + CHK_ERRA(CO_E_NO_SECCTX_IN_ACTIVATE) + CHK_ERRA(CO_E_TRACKER_CONFIG) + CHK_ERRA(CO_E_THREADPOOL_CONFIG) + CHK_ERRA(CO_E_SXS_CONFIG) + CHK_ERRA(CO_E_MALFORMED_SPN) + CHK_ERRA(REGDB_E_BADTHREADINGMODEL) +// CHK_ERRA(EVENT_E_FIRST) +// CHK_ERRA(EVENT_E_LAST) +// CHK_ERRA(EVENT_S_FIRST) +// CHK_ERRA(EVENT_S_LAST) +// CHK_ERRA(EVENT_S_SOME_SUBSCRIBERS_FAILED) +// CHK_ERRA(EVENT_E_ALL_SUBSCRIBERS_FAILED) + CHK_ERRA(EVENT_S_NOSUBSCRIBERS) +// CHK_ERRA(EVENT_E_QUERYSYNTAX) +// CHK_ERRA(EVENT_E_QUERYFIELD) +// CHK_ERRA(EVENT_E_INTERNALEXCEPTION) +// CHK_ERRA(EVENT_E_INTERNALERROR) +// CHK_ERRA(EVENT_E_INVALID_PER_USER_SID) +// CHK_ERRA(EVENT_E_USER_EXCEPTION) +// CHK_ERRA(EVENT_E_TOO_MANY_METHODS) +// CHK_ERRA(EVENT_E_MISSING_EVENTCLASS) +// CHK_ERRA(EVENT_E_NOT_ALL_REMOVED) +// CHK_ERRA(EVENT_E_COMPLUS_NOT_INSTALLED) +// CHK_ERRA(EVENT_E_CANT_MODIFY_OR_DELETE_UNCONFIGURED_OBJECT) +// CHK_ERRA(EVENT_E_CANT_MODIFY_OR_DELETE_CONFIGURED_OBJECT) +// CHK_ERRA(EVENT_E_INVALID_EVENT_CLASS_PARTITION) +// CHK_ERRA(EVENT_E_PER_USER_SID_NOT_LOGGED_ON) + CHK_ERRA(CONTEXT_E_FIRST) + CHK_ERRA(CONTEXT_E_LAST) + CHK_ERRA(CONTEXT_S_FIRST) + CHK_ERRA(CONTEXT_S_LAST) + CHK_ERRA(CONTEXT_E_ABORTED) + CHK_ERRA(CONTEXT_E_ABORTING) + CHK_ERRA(CONTEXT_E_NOCONTEXT) +// CHK_ERRA(CONTEXT_E_WOULD_DEADLOCK) + CHK_ERRA(CONTEXT_E_SYNCH_TIMEOUT) + CHK_ERRA(CONTEXT_E_OLDREF) + CHK_ERRA(CONTEXT_E_ROLENOTFOUND) + CHK_ERRA(CONTEXT_E_TMNOTAVAILABLE) + CHK_ERRA(CO_E_ACTIVATIONFAILED) + CHK_ERRA(CO_E_ACTIVATIONFAILED_EVENTLOGGED) + CHK_ERRA(CO_E_ACTIVATIONFAILED_CATALOGERROR) + CHK_ERRA(CO_E_ACTIVATIONFAILED_TIMEOUT) + CHK_ERRA(CO_E_INITIALIZATIONFAILED) + CHK_ERRA(CONTEXT_E_NOJIT) + CHK_ERRA(CONTEXT_E_NOTRANSACTION) + CHK_ERRA(CO_E_THREADINGMODEL_CHANGED) + CHK_ERRA(CO_E_NOIISINTRINSICS) + CHK_ERRA(CO_E_NOCOOKIES) + CHK_ERRA(CO_E_DBERROR) + CHK_ERRA(CO_E_NOTPOOLED) + CHK_ERRA(CO_E_NOTCONSTRUCTED) + CHK_ERRA(CO_E_NOSYNCHRONIZATION) +// CHK_ERRA(CO_E_ISOLEVELMISMATCH) + CHK_ERRA(SCHED_S_TASK_READY) + CHK_ERRA(SCHED_S_TASK_RUNNING) + CHK_ERRA(SCHED_S_TASK_DISABLED) + CHK_ERRA(SCHED_S_TASK_HAS_NOT_RUN) + CHK_ERRA(SCHED_S_TASK_NO_MORE_RUNS) + CHK_ERRA(SCHED_S_TASK_NOT_SCHEDULED) + CHK_ERRA(SCHED_S_TASK_TERMINATED) + CHK_ERRA(SCHED_S_TASK_NO_VALID_TRIGGERS) + CHK_ERRA(SCHED_S_EVENT_TRIGGER) + CHK_ERRA(SCHED_E_TRIGGER_NOT_FOUND) + CHK_ERRA(SCHED_E_TASK_NOT_READY) + CHK_ERRA(SCHED_E_TASK_NOT_RUNNING) + CHK_ERRA(SCHED_E_SERVICE_NOT_INSTALLED) + CHK_ERRA(SCHED_E_CANNOT_OPEN_TASK) + CHK_ERRA(SCHED_E_INVALID_TASK) + CHK_ERRA(SCHED_E_ACCOUNT_INFORMATION_NOT_SET) + CHK_ERRA(SCHED_E_ACCOUNT_NAME_NOT_FOUND) + CHK_ERRA(SCHED_E_ACCOUNT_DBASE_CORRUPT) + CHK_ERRA(SCHED_E_NO_SECURITY_SERVICES) + CHK_ERRA(SCHED_E_UNKNOWN_OBJECT_VERSION) + CHK_ERRA(SCHED_E_UNSUPPORTED_ACCOUNT_OPTION) + CHK_ERRA(SCHED_E_SERVICE_NOT_RUNNING) + CHK_ERRA(CO_S_MACHINENAMENOTFOUND) + CHK_ERRA(STG_E_STATUS_COPY_PROTECTION_FAILURE) + CHK_ERRA(STG_E_CSS_AUTHENTICATION_FAILURE) + CHK_ERRA(STG_E_CSS_KEY_NOT_PRESENT) + CHK_ERRA(STG_E_CSS_KEY_NOT_ESTABLISHED) + CHK_ERRA(STG_E_CSS_SCRAMBLED_SECTOR) + CHK_ERRA(STG_E_CSS_REGION_MISMATCH) + CHK_ERRA(STG_E_RESETS_EXHAUSTED) + CHK_ERRA(CO_E_CANCEL_DISABLED) + CHK_ERRA(ERROR_AUDITING_DISABLED) + CHK_ERRA(ERROR_ALL_SIDS_FILTERED) + CHK_ERRA(NTE_TEMPORARY_PROFILE) + CHK_ERRA(NTE_FIXEDPARAMETER) + CHK_ERRA(SEC_E_INSUFFICIENT_MEMORY) + CHK_ERRA(SEC_E_INVALID_HANDLE) + CHK_ERRA(SEC_E_UNSUPPORTED_FUNCTION) + CHK_ERRA(SEC_E_TARGET_UNKNOWN) + CHK_ERRA(SEC_E_INTERNAL_ERROR) + CHK_ERRA(SEC_E_SECPKG_NOT_FOUND) + CHK_ERRA(SEC_E_NOT_OWNER) + CHK_ERRA(SEC_E_CANNOT_INSTALL) + CHK_ERRA(SEC_E_INVALID_TOKEN) + CHK_ERRA(SEC_E_CANNOT_PACK) + CHK_ERRA(SEC_E_QOP_NOT_SUPPORTED) + CHK_ERRA(SEC_E_NO_IMPERSONATION) + CHK_ERRA(SEC_E_LOGON_DENIED) + CHK_ERRA(SEC_E_UNKNOWN_CREDENTIALS) + CHK_ERRA(SEC_E_NO_CREDENTIALS) + CHK_ERRA(SEC_E_MESSAGE_ALTERED) + CHK_ERRA(SEC_E_OUT_OF_SEQUENCE) + CHK_ERRA(SEC_E_NO_AUTHENTICATING_AUTHORITY) + CHK_ERRA(SEC_I_CONTINUE_NEEDED) + CHK_ERRA(SEC_I_COMPLETE_NEEDED) + CHK_ERRA(SEC_I_COMPLETE_AND_CONTINUE) + CHK_ERRA(SEC_I_LOCAL_LOGON) + CHK_ERRA(SEC_E_BAD_PKGID) + CHK_ERRA(SEC_E_CONTEXT_EXPIRED) + CHK_ERRA(SEC_I_CONTEXT_EXPIRED) + CHK_ERRA(SEC_E_INCOMPLETE_MESSAGE) + CHK_ERRA(SEC_E_INCOMPLETE_CREDENTIALS) + CHK_ERRA(SEC_E_BUFFER_TOO_SMALL) + CHK_ERRA(SEC_I_INCOMPLETE_CREDENTIALS) + CHK_ERRA(SEC_I_RENEGOTIATE) + CHK_ERRA(SEC_E_WRONG_PRINCIPAL) + CHK_ERRA(SEC_I_NO_LSA_CONTEXT) + CHK_ERRA(SEC_E_TIME_SKEW) + CHK_ERRA(SEC_E_UNTRUSTED_ROOT) + CHK_ERRA(SEC_E_ILLEGAL_MESSAGE) + CHK_ERRA(SEC_E_CERT_UNKNOWN) + CHK_ERRA(SEC_E_CERT_EXPIRED) + CHK_ERRA(SEC_E_ENCRYPT_FAILURE) + CHK_ERRA(SEC_E_DECRYPT_FAILURE) + CHK_ERRA(SEC_E_ALGORITHM_MISMATCH) + CHK_ERRA(SEC_E_SECURITY_QOS_FAILED) + CHK_ERRA(SEC_E_UNFINISHED_CONTEXT_DELETED) + CHK_ERRA(SEC_E_NO_TGT_REPLY) + CHK_ERRA(SEC_E_NO_IP_ADDRESSES) + CHK_ERRA(SEC_E_WRONG_CREDENTIAL_HANDLE) + CHK_ERRA(SEC_E_CRYPTO_SYSTEM_INVALID) + CHK_ERRA(SEC_E_MAX_REFERRALS_EXCEEDED) + CHK_ERRA(SEC_E_MUST_BE_KDC) + CHK_ERRA(SEC_E_STRONG_CRYPTO_NOT_SUPPORTED) + CHK_ERRA(SEC_E_TOO_MANY_PRINCIPALS) + CHK_ERRA(SEC_E_NO_PA_DATA) + CHK_ERRA(SEC_E_PKINIT_NAME_MISMATCH) + CHK_ERRA(SEC_E_SMARTCARD_LOGON_REQUIRED) + CHK_ERRA(SEC_E_SHUTDOWN_IN_PROGRESS) + CHK_ERRA(SEC_E_KDC_INVALID_REQUEST) + CHK_ERRA(SEC_E_KDC_UNABLE_TO_REFER) + CHK_ERRA(SEC_E_KDC_UNKNOWN_ETYPE) + CHK_ERRA(SEC_E_UNSUPPORTED_PREAUTH) + CHK_ERRA(SEC_E_DELEGATION_REQUIRED) + CHK_ERRA(SEC_E_BAD_BINDINGS) + CHK_ERRA(SEC_E_MULTIPLE_ACCOUNTS) + CHK_ERRA(SEC_E_NO_KERB_KEY) +// CHK_ERRA(SEC_E_CERT_WRONG_USAGE) +// CHK_ERRA(SEC_E_DOWNGRADE_DETECTED) + CHK_ERRA(SEC_E_SMARTCARD_CERT_REVOKED) + CHK_ERRA(SEC_E_ISSUING_CA_UNTRUSTED) + CHK_ERRA(SEC_E_REVOCATION_OFFLINE_C) + CHK_ERRA(SEC_E_PKINIT_CLIENT_FAILURE) + CHK_ERRA(SEC_E_SMARTCARD_CERT_EXPIRED) +// CHK_ERRA(SEC_E_NO_SPM) +// CHK_ERRA(SEC_E_NOT_SUPPORTED) + CHK_ERRA(CRYPT_I_NEW_PROTECTION_REQUIRED) + CHK_ERRA(CRYPT_E_MISSING_PUBKEY_PARA) + CHK_ERRA(CRYPT_E_ASN1_ERROR) + CHK_ERRA(CRYPT_E_ASN1_INTERNAL) + CHK_ERRA(CRYPT_E_ASN1_EOD) + CHK_ERRA(CRYPT_E_ASN1_CORRUPT) + CHK_ERRA(CRYPT_E_ASN1_LARGE) + CHK_ERRA(CRYPT_E_ASN1_CONSTRAINT) + CHK_ERRA(CRYPT_E_ASN1_MEMORY) + CHK_ERRA(CRYPT_E_ASN1_OVERFLOW) + CHK_ERRA(CRYPT_E_ASN1_BADPDU) + CHK_ERRA(CRYPT_E_ASN1_BADARGS) + CHK_ERRA(CRYPT_E_ASN1_BADREAL) + CHK_ERRA(CRYPT_E_ASN1_BADTAG) + CHK_ERRA(CRYPT_E_ASN1_CHOICE) + CHK_ERRA(CRYPT_E_ASN1_RULE) + CHK_ERRA(CRYPT_E_ASN1_UTF8) + CHK_ERRA(CRYPT_E_ASN1_PDU_TYPE) + CHK_ERRA(CRYPT_E_ASN1_NYI) + CHK_ERRA(CRYPT_E_ASN1_EXTENDED) + CHK_ERRA(CRYPT_E_ASN1_NOEOD) + CHK_ERRA(CERTSRV_E_SERVER_SUSPENDED) + CHK_ERRA(CERTSRV_E_ENCODING_LENGTH) + CHK_ERRA(CERTSRV_E_ROLECONFLICT) + CHK_ERRA(CERTSRV_E_RESTRICTEDOFFICER) + CHK_ERRA(CERTSRV_E_KEY_ARCHIVAL_NOT_CONFIGURED) + CHK_ERRA(CERTSRV_E_NO_VALID_KRA) + CHK_ERRA(CERTSRV_E_BAD_REQUEST_KEY_ARCHIVAL) + CHK_ERRA(CERTSRV_E_NO_CAADMIN_DEFINED) + CHK_ERRA(CERTSRV_E_BAD_RENEWAL_CERT_ATTRIBUTE) + CHK_ERRA(CERTSRV_E_NO_DB_SESSIONS) + CHK_ERRA(CERTSRV_E_ALIGNMENT_FAULT) + CHK_ERRA(CERTSRV_E_ENROLL_DENIED) + CHK_ERRA(CERTSRV_E_TEMPLATE_DENIED) +// CHK_ERRA(CERTSRV_E_DOWNLEVEL_DC_SSL_OR_UPGRADE) + CHK_ERRA(CERTSRV_E_TEMPLATE_CONFLICT) + CHK_ERRA(CERTSRV_E_SUBJECT_ALT_NAME_REQUIRED) + CHK_ERRA(CERTSRV_E_ARCHIVED_KEY_REQUIRED) + CHK_ERRA(CERTSRV_E_SMIME_REQUIRED) + CHK_ERRA(CERTSRV_E_BAD_RENEWAL_SUBJECT) + CHK_ERRA(CERTSRV_E_BAD_TEMPLATE_VERSION) + CHK_ERRA(CERTSRV_E_TEMPLATE_POLICY_REQUIRED) + CHK_ERRA(CERTSRV_E_SIGNATURE_POLICY_REQUIRED) + CHK_ERRA(CERTSRV_E_SIGNATURE_COUNT) + CHK_ERRA(CERTSRV_E_SIGNATURE_REJECTED) + CHK_ERRA(CERTSRV_E_ISSUANCE_POLICY_REQUIRED) + CHK_ERRA(CERTSRV_E_SUBJECT_UPN_REQUIRED) + CHK_ERRA(CERTSRV_E_SUBJECT_DIRECTORY_GUID_REQUIRED) + CHK_ERRA(CERTSRV_E_SUBJECT_DNS_REQUIRED) + CHK_ERRA(CERTSRV_E_ARCHIVED_KEY_UNEXPECTED) + CHK_ERRA(CERTSRV_E_KEY_LENGTH) +// CHK_ERRA(CERTSRV_E_SUBJECT_EMAIL_REQUIRED) +// CHK_ERRA(CERTSRV_E_UNKNOWN_CERT_TYPE) +// CHK_ERRA(CERTSRV_E_CERT_TYPE_OVERLAP) + CHK_ERRA(XENROLL_E_KEY_NOT_EXPORTABLE) + CHK_ERRA(XENROLL_E_CANNOT_ADD_ROOT_CERT) + CHK_ERRA(XENROLL_E_RESPONSE_KA_HASH_NOT_FOUND) + CHK_ERRA(XENROLL_E_RESPONSE_UNEXPECTED_KA_HASH) + CHK_ERRA(XENROLL_E_RESPONSE_KA_HASH_MISMATCH) + CHK_ERRA(XENROLL_E_KEYSPEC_SMIME_MISMATCH) + CHK_ERRA(MSSIPOTF_E_OUTOFMEMRANGE) + CHK_ERRA(MSSIPOTF_E_CANTGETOBJECT) + CHK_ERRA(MSSIPOTF_E_NOHEADTABLE) + CHK_ERRA(MSSIPOTF_E_BAD_MAGICNUMBER) + CHK_ERRA(MSSIPOTF_E_BAD_OFFSET_TABLE) + CHK_ERRA(MSSIPOTF_E_TABLE_TAGORDER) + CHK_ERRA(MSSIPOTF_E_TABLE_LONGWORD) + CHK_ERRA(MSSIPOTF_E_BAD_FIRST_TABLE_PLACEMENT) + CHK_ERRA(MSSIPOTF_E_TABLES_OVERLAP) + CHK_ERRA(MSSIPOTF_E_TABLE_PADBYTES) + CHK_ERRA(MSSIPOTF_E_FILETOOSMALL) + CHK_ERRA(MSSIPOTF_E_TABLE_CHECKSUM) + CHK_ERRA(MSSIPOTF_E_FILE_CHECKSUM) + CHK_ERRA(MSSIPOTF_E_FAILED_POLICY) + CHK_ERRA(MSSIPOTF_E_FAILED_HINTS_CHECK) + CHK_ERRA(MSSIPOTF_E_NOT_OPENTYPE) + CHK_ERRA(MSSIPOTF_E_FILE) + CHK_ERRA(MSSIPOTF_E_CRYPT) + CHK_ERRA(MSSIPOTF_E_BADVERSION) + CHK_ERRA(MSSIPOTF_E_DSIG_STRUCTURE) + CHK_ERRA(MSSIPOTF_E_PCONST_CHECK) + CHK_ERRA(MSSIPOTF_E_STRUCTURE) + CHK_ERRA(TRUST_E_EXPLICIT_DISTRUST) + CHK_ERRA(CERT_E_UNTRUSTEDCA) + CHK_ERRA(CERT_E_INVALID_POLICY) + CHK_ERRA(CERT_E_INVALID_NAME) + CHK_ERRA(SPAPI_E_NOT_DISABLEABLE) + CHK_ERRA(SPAPI_E_CANT_REMOVE_DEVINST) + CHK_ERRA(SPAPI_E_INVALID_TARGET) + CHK_ERRA(SPAPI_E_DRIVER_NONNATIVE) + CHK_ERRA(SPAPI_E_IN_WOW64) + CHK_ERRA(SPAPI_E_SET_SYSTEM_RESTORE_POINT) + CHK_ERRA(SPAPI_E_INCORRECTLY_COPIED_INF) + CHK_ERRA(SPAPI_E_SCE_DISABLED) + CHK_ERRA(SCARD_E_NO_KEY_CONTAINER) + CHK_ERRA(SCARD_W_CARD_NOT_AUTHENTICATED) + CHK_ERRA(COMADMIN_E_OBJECTERRORS) + CHK_ERRA(COMADMIN_E_OBJECTINVALID) + CHK_ERRA(COMADMIN_E_KEYMISSING) + CHK_ERRA(COMADMIN_E_ALREADYINSTALLED) + CHK_ERRA(COMADMIN_E_APP_FILE_WRITEFAIL) + CHK_ERRA(COMADMIN_E_APP_FILE_READFAIL) + CHK_ERRA(COMADMIN_E_APP_FILE_VERSION) + CHK_ERRA(COMADMIN_E_BADPATH) + CHK_ERRA(COMADMIN_E_APPLICATIONEXISTS) + CHK_ERRA(COMADMIN_E_ROLEEXISTS) + CHK_ERRA(COMADMIN_E_CANTCOPYFILE) + CHK_ERRA(COMADMIN_E_NOUSER) + CHK_ERRA(COMADMIN_E_INVALIDUSERIDS) + CHK_ERRA(COMADMIN_E_NOREGISTRYCLSID) + CHK_ERRA(COMADMIN_E_BADREGISTRYPROGID) + CHK_ERRA(COMADMIN_E_AUTHENTICATIONLEVEL) + CHK_ERRA(COMADMIN_E_USERPASSWDNOTVALID) + CHK_ERRA(COMADMIN_E_CLSIDORIIDMISMATCH) + CHK_ERRA(COMADMIN_E_REMOTEINTERFACE) + CHK_ERRA(COMADMIN_E_DLLREGISTERSERVER) + CHK_ERRA(COMADMIN_E_NOSERVERSHARE) + CHK_ERRA(COMADMIN_E_DLLLOADFAILED) + CHK_ERRA(COMADMIN_E_BADREGISTRYLIBID) + CHK_ERRA(COMADMIN_E_APPDIRNOTFOUND) + CHK_ERRA(COMADMIN_E_REGISTRARFAILED) + CHK_ERRA(COMADMIN_E_COMPFILE_DOESNOTEXIST) + CHK_ERRA(COMADMIN_E_COMPFILE_LOADDLLFAIL) + CHK_ERRA(COMADMIN_E_COMPFILE_GETCLASSOBJ) + CHK_ERRA(COMADMIN_E_COMPFILE_CLASSNOTAVAIL) + CHK_ERRA(COMADMIN_E_COMPFILE_BADTLB) + CHK_ERRA(COMADMIN_E_COMPFILE_NOTINSTALLABLE) + CHK_ERRA(COMADMIN_E_NOTCHANGEABLE) + CHK_ERRA(COMADMIN_E_NOTDELETEABLE) + CHK_ERRA(COMADMIN_E_SESSION) + CHK_ERRA(COMADMIN_E_COMP_MOVE_LOCKED) + CHK_ERRA(COMADMIN_E_COMP_MOVE_BAD_DEST) + CHK_ERRA(COMADMIN_E_REGISTERTLB) + CHK_ERRA(COMADMIN_E_SYSTEMAPP) + CHK_ERRA(COMADMIN_E_COMPFILE_NOREGISTRAR) + CHK_ERRA(COMADMIN_E_COREQCOMPINSTALLED) + CHK_ERRA(COMADMIN_E_SERVICENOTINSTALLED) + CHK_ERRA(COMADMIN_E_PROPERTYSAVEFAILED) + CHK_ERRA(COMADMIN_E_OBJECTEXISTS) + CHK_ERRA(COMADMIN_E_COMPONENTEXISTS) + CHK_ERRA(COMADMIN_E_REGFILE_CORRUPT) + CHK_ERRA(COMADMIN_E_PROPERTY_OVERFLOW) + CHK_ERRA(COMADMIN_E_NOTINREGISTRY) + CHK_ERRA(COMADMIN_E_OBJECTNOTPOOLABLE) + CHK_ERRA(COMADMIN_E_APPLID_MATCHES_CLSID) + CHK_ERRA(COMADMIN_E_ROLE_DOES_NOT_EXIST) + CHK_ERRA(COMADMIN_E_START_APP_NEEDS_COMPONENTS) + CHK_ERRA(COMADMIN_E_REQUIRES_DIFFERENT_PLATFORM) + CHK_ERRA(COMADMIN_E_CAN_NOT_EXPORT_APP_PROXY) + CHK_ERRA(COMADMIN_E_CAN_NOT_START_APP) + CHK_ERRA(COMADMIN_E_CAN_NOT_EXPORT_SYS_APP) + CHK_ERRA(COMADMIN_E_CANT_SUBSCRIBE_TO_COMPONENT) + CHK_ERRA(COMADMIN_E_EVENTCLASS_CANT_BE_SUBSCRIBER) + CHK_ERRA(COMADMIN_E_LIB_APP_PROXY_INCOMPATIBLE) + CHK_ERRA(COMADMIN_E_BASE_PARTITION_ONLY) + CHK_ERRA(COMADMIN_E_START_APP_DISABLED) + CHK_ERRA(COMADMIN_E_CAT_DUPLICATE_PARTITION_NAME) + CHK_ERRA(COMADMIN_E_CAT_INVALID_PARTITION_NAME) + CHK_ERRA(COMADMIN_E_CAT_PARTITION_IN_USE) + CHK_ERRA(COMADMIN_E_FILE_PARTITION_DUPLICATE_FILES) + CHK_ERRA(COMADMIN_E_CAT_IMPORTED_COMPONENTS_NOT_ALLOWED) + CHK_ERRA(COMADMIN_E_AMBIGUOUS_APPLICATION_NAME) + CHK_ERRA(COMADMIN_E_AMBIGUOUS_PARTITION_NAME) + CHK_ERRA(COMADMIN_E_REGDB_NOTINITIALIZED) + CHK_ERRA(COMADMIN_E_REGDB_NOTOPEN) + CHK_ERRA(COMADMIN_E_REGDB_SYSTEMERR) + CHK_ERRA(COMADMIN_E_REGDB_ALREADYRUNNING) + CHK_ERRA(COMADMIN_E_MIG_VERSIONNOTSUPPORTED) + CHK_ERRA(COMADMIN_E_MIG_SCHEMANOTFOUND) + CHK_ERRA(COMADMIN_E_CAT_BITNESSMISMATCH) + CHK_ERRA(COMADMIN_E_CAT_UNACCEPTABLEBITNESS) + CHK_ERRA(COMADMIN_E_CAT_WRONGAPPBITNESS) + CHK_ERRA(COMADMIN_E_CAT_PAUSE_RESUME_NOT_SUPPORTED) + CHK_ERRA(COMADMIN_E_CAT_SERVERFAULT) + CHK_ERRA(COMQC_E_APPLICATION_NOT_QUEUED) + CHK_ERRA(COMQC_E_NO_QUEUEABLE_INTERFACES) + CHK_ERRA(COMQC_E_QUEUING_SERVICE_NOT_AVAILABLE) + CHK_ERRA(COMQC_E_NO_IPERSISTSTREAM) + CHK_ERRA(COMQC_E_BAD_MESSAGE) + CHK_ERRA(COMQC_E_UNAUTHENTICATED) + CHK_ERRA(COMQC_E_UNTRUSTED_ENQUEUER) + CHK_ERRA(MSDTC_E_DUPLICATE_RESOURCE) + CHK_ERRA(COMADMIN_E_OBJECT_PARENT_MISSING) + CHK_ERRA(COMADMIN_E_OBJECT_DOES_NOT_EXIST) + CHK_ERRA(COMADMIN_E_APP_NOT_RUNNING) + CHK_ERRA(COMADMIN_E_INVALID_PARTITION) + CHK_ERRA(COMADMIN_E_SVCAPP_NOT_POOLABLE_OR_RECYCLABLE) + CHK_ERRA(COMADMIN_E_USER_IN_SET) + CHK_ERRA(COMADMIN_E_CANTRECYCLELIBRARYAPPS) + CHK_ERRA(COMADMIN_E_CANTRECYCLESERVICEAPPS) + CHK_ERRA(COMADMIN_E_PROCESSALREADYRECYCLED) + CHK_ERRA(COMADMIN_E_PAUSEDPROCESSMAYNOTBERECYCLED) + CHK_ERRA(COMADMIN_E_CANTMAKEINPROCSERVICE) + CHK_ERRA(COMADMIN_E_PROGIDINUSEBYCLSID) + CHK_ERRA(COMADMIN_E_DEFAULT_PARTITION_NOT_IN_SET) + CHK_ERRA(COMADMIN_E_RECYCLEDPROCESSMAYNOTBEPAUSED) + CHK_ERRA(COMADMIN_E_PARTITION_ACCESSDENIED) + CHK_ERRA(COMADMIN_E_PARTITION_MSI_ONLY) + CHK_ERRA(COMADMIN_E_LEGACYCOMPS_NOT_ALLOWED_IN_1_0_FORMAT) + CHK_ERRA(COMADMIN_E_LEGACYCOMPS_NOT_ALLOWED_IN_NONBASE_PARTITIONS) + CHK_ERRA(COMADMIN_E_COMP_MOVE_SOURCE) + CHK_ERRA(COMADMIN_E_COMP_MOVE_DEST) + CHK_ERRA(COMADMIN_E_COMP_MOVE_PRIVATE) + CHK_ERRA(COMADMIN_E_BASEPARTITION_REQUIRED_IN_SET) + CHK_ERRA(COMADMIN_E_CANNOT_ALIAS_EVENTCLASS) + CHK_ERRA(COMADMIN_E_PRIVATE_ACCESSDENIED) + CHK_ERRA(COMADMIN_E_SAFERINVALID) + CHK_ERRA(COMADMIN_E_REGISTRY_ACCESSDENIED) +// CHK_ERRA(COMADMIN_E_PARTITIONS_DISABLED) +// CHK_ERR_WIN32A(ERROR_EXE_CANNOT_MODIFY_SIGNED_BINARY) +// CHK_ERR_WIN32A(ERROR_EXE_CANNOT_MODIFY_STRONG_SIGNED_BINARY) + CHK_ERR_WIN32A(ERROR_DISK_TOO_FRAGMENTED) + CHK_ERR_WIN32A(ERROR_DELETE_PENDING) +// CHK_ERR_WIN32A(ERROR_SCOPE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_NOT_SAFEBOOT_SERVICE) + CHK_ERR_WIN32A(ERROR_JOURNAL_ENTRY_DELETED) + CHK_ERR_WIN32A(ERROR_ONLY_IF_CONNECTED) + CHK_ERR_WIN32A(ERROR_OVERRIDE_NOCHANGES) + CHK_ERR_WIN32A(ERROR_BAD_USER_PROFILE) + CHK_ERR_WIN32A(ERROR_NOT_SUPPORTED_ON_SBS) + CHK_ERR_WIN32A(ERROR_SERVER_SHUTDOWN_IN_PROGRESS) + CHK_ERR_WIN32A(ERROR_HOST_DOWN) + CHK_ERR_WIN32A(ERROR_NON_ACCOUNT_SID) + CHK_ERR_WIN32A(ERROR_NON_DOMAIN_SID) + CHK_ERR_WIN32A(ERROR_APPHELP_BLOCK) + CHK_ERR_WIN32A(ERROR_ACCESS_DISABLED_BY_POLICY) + CHK_ERR_WIN32A(ERROR_REG_NAT_CONSUMPTION) + CHK_ERR_WIN32A(ERROR_CSCSHARE_OFFLINE) + CHK_ERR_WIN32A(ERROR_PKINIT_FAILURE) + CHK_ERR_WIN32A(ERROR_SMARTCARD_SUBSYSTEM_FAILURE) + CHK_ERR_WIN32A(ERROR_DOWNGRADE_DETECTED) + CHK_ERR_WIN32A(ERROR_MACHINE_LOCKED) + CHK_ERR_WIN32A(ERROR_CALLBACK_SUPPLIED_INVALID_DATA) + CHK_ERR_WIN32A(ERROR_SYNC_FOREGROUND_REFRESH_REQUIRED) + CHK_ERR_WIN32A(ERROR_DRIVER_BLOCKED) + CHK_ERR_WIN32A(ERROR_INVALID_IMPORT_OF_NON_DLL) +// CHK_ERR_WIN32A(ERROR_ACCESS_DISABLED_WEBBLADE) +// CHK_ERR_WIN32A(ERROR_ACCESS_DISABLED_WEBBLADE_TAMPER) +// CHK_ERR_WIN32A(ERROR_RECOVERY_FAILURE) +// CHK_ERR_WIN32A(ERROR_ALREADY_FIBER) +// CHK_ERR_WIN32A(ERROR_ALREADY_THREAD) +// CHK_ERR_WIN32A(ERROR_STACK_BUFFER_OVERRUN) +// CHK_ERR_WIN32A(ERROR_PARAMETER_QUOTA_EXCEEDED) +// CHK_ERR_WIN32A(ERROR_DEBUGGER_INACTIVE) +// CHK_ERR_WIN32A(ERROR_DELAY_LOAD_FAILED) + CHK_ERR_WIN32A(ERROR_CURRENT_DOMAIN_NOT_ALLOWED) + CHK_ERR_WIN32A(ERROR_INSTALL_SERVICE_FAILURE) + CHK_ERR_WIN32A(ERROR_INSTALL_PACKAGE_VERSION) + CHK_ERR_WIN32A(ERROR_INSTALL_ALREADY_RUNNING) + CHK_ERR_WIN32A(ERROR_INSTALL_PACKAGE_OPEN_FAILED) + CHK_ERR_WIN32A(ERROR_INSTALL_PACKAGE_INVALID) + CHK_ERR_WIN32A(ERROR_INSTALL_UI_FAILURE) + CHK_ERR_WIN32A(ERROR_INSTALL_LOG_FAILURE) + CHK_ERR_WIN32A(ERROR_INSTALL_LANGUAGE_UNSUPPORTED) + CHK_ERR_WIN32A(ERROR_INSTALL_TRANSFORM_FAILURE) + CHK_ERR_WIN32A(ERROR_INSTALL_PACKAGE_REJECTED) + CHK_ERR_WIN32A(ERROR_FUNCTION_NOT_CALLED) + CHK_ERR_WIN32A(ERROR_FUNCTION_FAILED) + CHK_ERR_WIN32A(ERROR_INVALID_TABLE) + CHK_ERR_WIN32A(ERROR_DATATYPE_MISMATCH) + CHK_ERR_WIN32A(ERROR_UNSUPPORTED_TYPE) + CHK_ERR_WIN32A(ERROR_CREATE_FAILED) + CHK_ERR_WIN32A(ERROR_INSTALL_TEMP_UNWRITABLE) + CHK_ERR_WIN32A(ERROR_INSTALL_PLATFORM_UNSUPPORTED) + CHK_ERR_WIN32A(ERROR_INSTALL_NOTUSED) + CHK_ERR_WIN32A(ERROR_PATCH_PACKAGE_OPEN_FAILED) + CHK_ERR_WIN32A(ERROR_PATCH_PACKAGE_INVALID) + CHK_ERR_WIN32A(ERROR_PATCH_PACKAGE_UNSUPPORTED) + CHK_ERR_WIN32A(ERROR_PRODUCT_VERSION) + CHK_ERR_WIN32A(ERROR_INVALID_COMMAND_LINE) + CHK_ERR_WIN32A(ERROR_INSTALL_REMOTE_DISALLOWED) + CHK_ERR_WIN32A(ERROR_SUCCESS_REBOOT_INITIATED) + CHK_ERR_WIN32A(ERROR_PATCH_TARGET_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_PATCH_PACKAGE_REJECTED) + CHK_ERR_WIN32A(ERROR_INSTALL_TRANSFORM_REJECTED) +// CHK_ERR_WIN32A(ERROR_INSTALL_REMOTE_PROHIBITED) + CHK_ERR_WIN32A(RPC_S_ENTRY_TYPE_MISMATCH) + CHK_ERR_WIN32A(RPC_S_NOT_ALL_OBJS_EXPORTED) + CHK_ERR_WIN32A(RPC_S_INTERFACE_NOT_EXPORTED) + CHK_ERR_WIN32A(RPC_S_PROFILE_NOT_ADDED) + CHK_ERR_WIN32A(RPC_S_PRF_ELT_NOT_ADDED) + CHK_ERR_WIN32A(RPC_S_PRF_ELT_NOT_REMOVED) + CHK_ERR_WIN32A(RPC_S_GRP_ELT_NOT_ADDED) + CHK_ERR_WIN32A(RPC_S_GRP_ELT_NOT_REMOVED) + CHK_ERR_WIN32A(ERROR_KM_DRIVER_BLOCKED) + CHK_ERR_WIN32A(ERROR_CONTEXT_EXPIRED) +// CHK_ERR_WIN32A(ERROR_PER_USER_TRUST_QUOTA_EXCEEDED) +// CHK_ERR_WIN32A(ERROR_ALL_USER_TRUST_QUOTA_EXCEEDED) +// CHK_ERR_WIN32A(ERROR_USER_DELETE_TRUST_QUOTA_EXCEEDED) + CHK_ERR_WIN32A(ERROR_CONNECTED_OTHER_PASSWORD_DEFAULT) + CHK_ERR_WIN32A(ERROR_PRINTER_DRIVER_WARNED) + CHK_ERR_WIN32A(ERROR_PRINTER_DRIVER_BLOCKED) + CHK_ERR_WIN32A(ERROR_VOLUME_CONTAINS_SYS_FILES) + CHK_ERR_WIN32A(ERROR_INDIGENOUS_TYPE) + CHK_ERR_WIN32A(ERROR_NO_SUPPORTING_DRIVES) + CHK_ERR_WIN32A(ERROR_CLEANER_CARTRIDGE_INSTALLED) + CHK_ERR_WIN32A(ERROR_REPARSE_TAG_INVALID) + CHK_ERR_WIN32A(ERROR_REPARSE_TAG_MISMATCH) + CHK_ERR_WIN32A(ERROR_VOLUME_NOT_SIS_ENABLED) + CHK_ERR_WIN32A(ERROR_QUORUM_OWNER_ALIVE) + CHK_ERR_WIN32A(ERROR_NETWORK_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_NODE_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_ALL_NODES_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_RESOURCE_FAILED) + CHK_ERR_WIN32A(ERROR_CLUSTER_INVALID_NODE) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_EXISTS) + CHK_ERR_WIN32A(ERROR_CLUSTER_JOIN_IN_PROGRESS) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CLUSTER_LOCAL_NODE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETWORK_EXISTS) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETWORK_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETINTERFACE_EXISTS) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETINTERFACE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CLUSTER_INVALID_REQUEST) + CHK_ERR_WIN32A(ERROR_CLUSTER_INVALID_NETWORK_PROVIDER) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_DOWN) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_UNREACHABLE) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_NOT_MEMBER) + CHK_ERR_WIN32A(ERROR_CLUSTER_JOIN_NOT_IN_PROGRESS) + CHK_ERR_WIN32A(ERROR_CLUSTER_INVALID_NETWORK) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_UP) + CHK_ERR_WIN32A(ERROR_CLUSTER_IPADDR_IN_USE) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_NOT_PAUSED) + CHK_ERR_WIN32A(ERROR_CLUSTER_NO_SECURITY_CONTEXT) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETWORK_NOT_INTERNAL) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_ALREADY_UP) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_ALREADY_DOWN) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETWORK_ALREADY_ONLINE) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETWORK_ALREADY_OFFLINE) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_ALREADY_MEMBER) + CHK_ERR_WIN32A(ERROR_CLUSTER_LAST_INTERNAL_NETWORK) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETWORK_HAS_DEPENDENTS) + CHK_ERR_WIN32A(ERROR_INVALID_OPERATION_ON_QUORUM) + CHK_ERR_WIN32A(ERROR_DEPENDENCY_NOT_ALLOWED) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_PAUSED) + CHK_ERR_WIN32A(ERROR_NODE_CANT_HOST_RESOURCE) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_NOT_READY) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_SHUTTING_DOWN) + CHK_ERR_WIN32A(ERROR_CLUSTER_JOIN_ABORTED) + CHK_ERR_WIN32A(ERROR_CLUSTER_INCOMPATIBLE_VERSIONS) + CHK_ERR_WIN32A(ERROR_CLUSTER_MAXNUM_OF_RESOURCES_EXCEEDED) + CHK_ERR_WIN32A(ERROR_CLUSTER_SYSTEM_CONFIG_CHANGED) + CHK_ERR_WIN32A(ERROR_CLUSTER_RESOURCE_TYPE_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CLUSTER_RESTYPE_NOT_SUPPORTED) + CHK_ERR_WIN32A(ERROR_CLUSTER_RESNAME_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CLUSTER_NO_RPC_PACKAGES_REGISTERED) + CHK_ERR_WIN32A(ERROR_CLUSTER_OWNER_NOT_IN_PREFLIST) + CHK_ERR_WIN32A(ERROR_CLUSTER_DATABASE_SEQMISMATCH) + CHK_ERR_WIN32A(ERROR_RESMON_INVALID_STATE) + CHK_ERR_WIN32A(ERROR_CLUSTER_GUM_NOT_LOCKER) + CHK_ERR_WIN32A(ERROR_QUORUM_DISK_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_DATABASE_BACKUP_CORRUPT) + CHK_ERR_WIN32A(ERROR_CLUSTER_NODE_ALREADY_HAS_DFS_ROOT) + CHK_ERR_WIN32A(ERROR_RESOURCE_PROPERTY_UNCHANGEABLE) + CHK_ERR_WIN32A(ERROR_CLUSTER_MEMBERSHIP_INVALID_STATE) + CHK_ERR_WIN32A(ERROR_CLUSTER_QUORUMLOG_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_CLUSTER_MEMBERSHIP_HALT) + CHK_ERR_WIN32A(ERROR_CLUSTER_INSTANCE_ID_MISMATCH) + CHK_ERR_WIN32A(ERROR_CLUSTER_NETWORK_NOT_FOUND_FOR_IP) + CHK_ERR_WIN32A(ERROR_CLUSTER_PROPERTY_DATA_TYPE_MISMATCH) + CHK_ERR_WIN32A(ERROR_CLUSTER_EVICT_WITHOUT_CLEANUP) + CHK_ERR_WIN32A(ERROR_CLUSTER_PARAMETER_MISMATCH) + CHK_ERR_WIN32A(ERROR_NODE_CANNOT_BE_CLUSTERED) + CHK_ERR_WIN32A(ERROR_CLUSTER_WRONG_OS_VERSION) + CHK_ERR_WIN32A(ERROR_CLUSTER_CANT_CREATE_DUP_CLUSTER_NAME) +// CHK_ERR_WIN32A(ERROR_CLUSCFG_ALREADY_COMMITTED) +// CHK_ERR_WIN32A(ERROR_CLUSCFG_ROLLBACK_FAILED) +// CHK_ERR_WIN32A(ERROR_CLUSCFG_SYSTEM_DISK_DRIVE_LETTER_CONFLICT) +// CHK_ERR_WIN32A(ERROR_CLUSTER_OLD_VERSION) +// CHK_ERR_WIN32A(ERROR_CLUSTER_MISMATCHED_COMPUTER_ACCT_NAME) + CHK_ERR_WIN32A(ERROR_FILE_READ_ONLY) + CHK_ERR_WIN32A(ERROR_DIR_EFS_DISALLOWED) + CHK_ERR_WIN32A(ERROR_EFS_SERVER_NOT_TRUSTED) + CHK_ERR_WIN32A(ERROR_BAD_RECOVERY_POLICY) + CHK_ERR_WIN32A(ERROR_EFS_ALG_BLOB_TOO_BIG) + CHK_ERR_WIN32A(ERROR_VOLUME_NOT_SUPPORT_EFS) + CHK_ERR_WIN32A(ERROR_EFS_DISABLED) + CHK_ERR_WIN32A(ERROR_EFS_VERSION_NOT_SUPPORT) + CHK_ERR_WIN32A(SCHED_E_SERVICE_NOT_LOCALSYSTEM) + CHK_ERR_WIN32A(ERROR_CTX_CLIENT_LICENSE_IN_USE) + CHK_ERR_WIN32A(ERROR_CTX_CLIENT_LICENSE_NOT_SET) + CHK_ERR_WIN32A(ERROR_CTX_LICENSE_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_CTX_LICENSE_CLIENT_INVALID) + CHK_ERR_WIN32A(ERROR_CTX_LICENSE_EXPIRED) + CHK_ERR_WIN32A(ERROR_CTX_SHADOW_NOT_RUNNING) + CHK_ERR_WIN32A(ERROR_CTX_SHADOW_ENDED_BY_MODE_CHANGE) +// CHK_ERR_WIN32A(ERROR_ACTIVATION_COUNT_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DS_SORT_CONTROL_MISSING) + CHK_ERR_WIN32A(ERROR_DS_OFFSET_RANGE_ERROR) + CHK_ERR_WIN32A(ERROR_DS_OBJECT_BEING_REMOVED) + CHK_ERR_WIN32A(ERROR_DS_DS_REQUIRED) + CHK_ERR_WIN32A(ERROR_DS_INVALID_LDAP_DISPLAY_NAME) + CHK_ERR_WIN32A(ERROR_DS_NON_BASE_SEARCH) + CHK_ERR_WIN32A(ERROR_DS_CANT_RETRIEVE_ATTS) + CHK_ERR_WIN32A(ERROR_DS_BACKLINK_WITHOUT_LINK) + CHK_ERR_WIN32A(ERROR_DS_EPOCH_MISMATCH) + CHK_ERR_WIN32A(ERROR_DS_SRC_NAME_MISMATCH) + CHK_ERR_WIN32A(ERROR_DS_SRC_AND_DST_NC_IDENTICAL) + CHK_ERR_WIN32A(ERROR_DS_DST_NC_MISMATCH) + CHK_ERR_WIN32A(ERROR_DS_NOT_AUTHORITIVE_FOR_DST_NC) + CHK_ERR_WIN32A(ERROR_DS_SRC_GUID_MISMATCH) + CHK_ERR_WIN32A(ERROR_DS_CANT_MOVE_DELETED_OBJECT) + CHK_ERR_WIN32A(ERROR_DS_PDC_OPERATION_IN_PROGRESS) + CHK_ERR_WIN32A(ERROR_DS_CROSS_DOMAIN_CLEANUP_REQD) + CHK_ERR_WIN32A(ERROR_DS_ILLEGAL_XDOM_MOVE_OPERATION) + CHK_ERR_WIN32A(ERROR_DS_CANT_WITH_ACCT_GROUP_MEMBERSHPS) + CHK_ERR_WIN32A(ERROR_DS_NC_MUST_HAVE_NC_PARENT) + CHK_ERR_WIN32A(ERROR_DS_CR_IMPOSSIBLE_TO_VALIDATE) + CHK_ERR_WIN32A(ERROR_DS_DST_DOMAIN_NOT_NATIVE) + CHK_ERR_WIN32A(ERROR_DS_MISSING_INFRASTRUCTURE_CONTAINER) + CHK_ERR_WIN32A(ERROR_DS_CANT_MOVE_ACCOUNT_GROUP) + CHK_ERR_WIN32A(ERROR_DS_CANT_MOVE_RESOURCE_GROUP) + CHK_ERR_WIN32A(ERROR_DS_INVALID_SEARCH_FLAG) + CHK_ERR_WIN32A(ERROR_DS_NO_TREE_DELETE_ABOVE_NC) + CHK_ERR_WIN32A(ERROR_DS_COULDNT_LOCK_TREE_FOR_DELETE) + CHK_ERR_WIN32A(ERROR_DS_COULDNT_IDENTIFY_OBJECTS_FOR_TREE_DELETE) + CHK_ERR_WIN32A(ERROR_DS_SAM_INIT_FAILURE) + CHK_ERR_WIN32A(ERROR_DS_SENSITIVE_GROUP_VIOLATION) + CHK_ERR_WIN32A(ERROR_DS_CANT_MOD_PRIMARYGROUPID) + CHK_ERR_WIN32A(ERROR_DS_ILLEGAL_BASE_SCHEMA_MOD) + CHK_ERR_WIN32A(ERROR_DS_NONSAFE_SCHEMA_CHANGE) + CHK_ERR_WIN32A(ERROR_DS_SCHEMA_UPDATE_DISALLOWED) + CHK_ERR_WIN32A(ERROR_DS_CANT_CREATE_UNDER_SCHEMA) + CHK_ERR_WIN32A(ERROR_DS_INSTALL_NO_SRC_SCH_VERSION) + CHK_ERR_WIN32A(ERROR_DS_INSTALL_NO_SCH_VERSION_IN_INIFILE) + CHK_ERR_WIN32A(ERROR_DS_INVALID_GROUP_TYPE) + CHK_ERR_WIN32A(ERROR_DS_NO_NEST_GLOBALGROUP_IN_MIXEDDOMAIN) + CHK_ERR_WIN32A(ERROR_DS_NO_NEST_LOCALGROUP_IN_MIXEDDOMAIN) + CHK_ERR_WIN32A(ERROR_DS_GLOBAL_CANT_HAVE_LOCAL_MEMBER) + CHK_ERR_WIN32A(ERROR_DS_GLOBAL_CANT_HAVE_UNIVERSAL_MEMBER) + CHK_ERR_WIN32A(ERROR_DS_UNIVERSAL_CANT_HAVE_LOCAL_MEMBER) + CHK_ERR_WIN32A(ERROR_DS_GLOBAL_CANT_HAVE_CROSSDOMAIN_MEMBER) + CHK_ERR_WIN32A(ERROR_DS_LOCAL_CANT_HAVE_CROSSDOMAIN_LOCAL_MEMBER) + CHK_ERR_WIN32A(ERROR_DS_HAVE_PRIMARY_MEMBERS) + CHK_ERR_WIN32A(ERROR_DS_STRING_SD_CONVERSION_FAILED) + CHK_ERR_WIN32A(ERROR_DS_NAMING_MASTER_GC) + CHK_ERR_WIN32A(ERROR_DS_DNS_LOOKUP_FAILURE) + CHK_ERR_WIN32A(ERROR_DS_COULDNT_UPDATE_SPNS) + CHK_ERR_WIN32A(ERROR_DS_CANT_RETRIEVE_SD) + CHK_ERR_WIN32A(ERROR_DS_KEY_NOT_UNIQUE) + CHK_ERR_WIN32A(ERROR_DS_WRONG_LINKED_ATT_SYNTAX) + CHK_ERR_WIN32A(ERROR_DS_SAM_NEED_BOOTKEY_PASSWORD) + CHK_ERR_WIN32A(ERROR_DS_SAM_NEED_BOOTKEY_FLOPPY) + CHK_ERR_WIN32A(ERROR_DS_CANT_START) + CHK_ERR_WIN32A(ERROR_DS_INIT_FAILURE) + CHK_ERR_WIN32A(ERROR_DS_NO_PKT_PRIVACY_ON_CONNECTION) + CHK_ERR_WIN32A(ERROR_DS_SOURCE_DOMAIN_IN_FOREST) + CHK_ERR_WIN32A(ERROR_DS_DESTINATION_DOMAIN_NOT_IN_FOREST) + CHK_ERR_WIN32A(ERROR_DS_DESTINATION_AUDITING_NOT_ENABLED) + CHK_ERR_WIN32A(ERROR_DS_CANT_FIND_DC_FOR_SRC_DOMAIN) + CHK_ERR_WIN32A(ERROR_DS_SRC_OBJ_NOT_GROUP_OR_USER) + CHK_ERR_WIN32A(ERROR_DS_SRC_SID_EXISTS_IN_FOREST) + CHK_ERR_WIN32A(ERROR_DS_SRC_AND_DST_OBJECT_CLASS_MISMATCH) + CHK_ERR_WIN32A(ERROR_SAM_INIT_FAILURE) + CHK_ERR_WIN32A(ERROR_DS_DRA_SCHEMA_INFO_SHIP) + CHK_ERR_WIN32A(ERROR_DS_DRA_SCHEMA_CONFLICT) + CHK_ERR_WIN32A(ERROR_DS_DRA_EARLIER_SCHEMA_CONFLICT) + CHK_ERR_WIN32A(ERROR_DS_DRA_OBJ_NC_MISMATCH) + CHK_ERR_WIN32A(ERROR_DS_NC_STILL_HAS_DSAS) + CHK_ERR_WIN32A(ERROR_DS_GC_REQUIRED) + CHK_ERR_WIN32A(ERROR_DS_LOCAL_MEMBER_OF_LOCAL_ONLY) + CHK_ERR_WIN32A(ERROR_DS_NO_FPO_IN_UNIVERSAL_GROUPS) + CHK_ERR_WIN32A(ERROR_DS_CANT_ADD_TO_GC) + CHK_ERR_WIN32A(ERROR_DS_NO_CHECKPOINT_WITH_PDC) + CHK_ERR_WIN32A(ERROR_DS_SOURCE_AUDITING_NOT_ENABLED) + CHK_ERR_WIN32A(ERROR_DS_CANT_CREATE_IN_NONDOMAIN_NC) + CHK_ERR_WIN32A(ERROR_DS_INVALID_NAME_FOR_SPN) + CHK_ERR_WIN32A(ERROR_DS_FILTER_USES_CONTRUCTED_ATTRS) + CHK_ERR_WIN32A(ERROR_DS_UNICODEPWD_NOT_IN_QUOTES) + CHK_ERR_WIN32A(ERROR_DS_MACHINE_ACCOUNT_QUOTA_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DS_MUST_BE_RUN_ON_DST_DC) + CHK_ERR_WIN32A(ERROR_DS_SRC_DC_MUST_BE_SP4_OR_GREATER) + CHK_ERR_WIN32A(ERROR_DS_CANT_TREE_DELETE_CRITICAL_OBJ) + CHK_ERR_WIN32A(ERROR_DS_INIT_FAILURE_CONSOLE) + CHK_ERR_WIN32A(ERROR_DS_SAM_INIT_FAILURE_CONSOLE) + CHK_ERR_WIN32A(ERROR_DS_FOREST_VERSION_TOO_HIGH) + CHK_ERR_WIN32A(ERROR_DS_DOMAIN_VERSION_TOO_HIGH) + CHK_ERR_WIN32A(ERROR_DS_FOREST_VERSION_TOO_LOW) + CHK_ERR_WIN32A(ERROR_DS_DOMAIN_VERSION_TOO_LOW) + CHK_ERR_WIN32A(ERROR_DS_INCOMPATIBLE_VERSION) + CHK_ERR_WIN32A(ERROR_DS_LOW_DSA_VERSION) + CHK_ERR_WIN32A(ERROR_DS_NO_BEHAVIOR_VERSION_IN_MIXEDDOMAIN) + CHK_ERR_WIN32A(ERROR_DS_NOT_SUPPORTED_SORT_ORDER) + CHK_ERR_WIN32A(ERROR_DS_NAME_NOT_UNIQUE) + CHK_ERR_WIN32A(ERROR_DS_MACHINE_ACCOUNT_CREATED_PRENT4) + CHK_ERR_WIN32A(ERROR_DS_OUT_OF_VERSION_STORE) + CHK_ERR_WIN32A(ERROR_DS_INCOMPATIBLE_CONTROLS_USED) + CHK_ERR_WIN32A(ERROR_DS_NO_REF_DOMAIN) + CHK_ERR_WIN32A(ERROR_DS_RESERVED_LINK_ID) + CHK_ERR_WIN32A(ERROR_DS_LINK_ID_NOT_AVAILABLE) + CHK_ERR_WIN32A(ERROR_DS_AG_CANT_HAVE_UNIVERSAL_MEMBER) + CHK_ERR_WIN32A(ERROR_DS_MODIFYDN_DISALLOWED_BY_INSTANCE_TYPE) + CHK_ERR_WIN32A(ERROR_DS_NO_OBJECT_MOVE_IN_SCHEMA_NC) + CHK_ERR_WIN32A(ERROR_DS_MODIFYDN_DISALLOWED_BY_FLAG) + CHK_ERR_WIN32A(ERROR_DS_MODIFYDN_WRONG_GRANDPARENT) + CHK_ERR_WIN32A(ERROR_DS_NAME_ERROR_TRUST_REFERRAL) + CHK_ERR_WIN32A(ERROR_NOT_SUPPORTED_ON_STANDARD_SERVER) + CHK_ERR_WIN32A(ERROR_DS_CANT_ACCESS_REMOTE_PART_OF_AD) + CHK_ERR_WIN32A(ERROR_DS_CR_IMPOSSIBLE_TO_VALIDATE_V2) + CHK_ERR_WIN32A(ERROR_DS_THREAD_LIMIT_EXCEEDED) + CHK_ERR_WIN32A(ERROR_DS_NOT_CLOSEST) + CHK_ERR_WIN32A(ERROR_DS_CANT_DERIVE_SPN_WITHOUT_SERVER_REF) + CHK_ERR_WIN32A(ERROR_DS_SINGLE_USER_MODE_FAILED) + CHK_ERR_WIN32A(ERROR_DS_NTDSCRIPT_SYNTAX_ERROR) + CHK_ERR_WIN32A(ERROR_DS_NTDSCRIPT_PROCESS_ERROR) + CHK_ERR_WIN32A(ERROR_DS_DIFFERENT_REPL_EPOCHS) + CHK_ERR_WIN32A(ERROR_DS_DRS_EXTENSIONS_CHANGED) + CHK_ERR_WIN32A(ERROR_DS_REPLICA_SET_CHANGE_NOT_ALLOWED_ON_DISABLED_CR) + CHK_ERR_WIN32A(ERROR_DS_NO_MSDS_INTID) + CHK_ERR_WIN32A(ERROR_DS_DUP_MSDS_INTID) + CHK_ERR_WIN32A(ERROR_DS_EXISTS_IN_RDNATTID) + CHK_ERR_WIN32A(ERROR_DS_AUTHORIZATION_FAILED) + CHK_ERR_WIN32A(ERROR_DS_INVALID_SCRIPT) + CHK_ERR_WIN32A(ERROR_DS_REMOTE_CROSSREF_OP_FAILED) +// CHK_ERR_WIN32A(ERROR_DS_CROSS_REF_BUSY) +// CHK_ERR_WIN32A(ERROR_DS_CANT_DERIVE_SPN_FOR_DELETED_DOMAIN) +// CHK_ERR_WIN32A(ERROR_DS_CANT_DEMOTE_WITH_WRITEABLE_NC) +// CHK_ERR_WIN32A(ERROR_DS_DUPLICATE_ID_FOUND) +// CHK_ERR_WIN32A(ERROR_DS_INSUFFICIENT_ATTR_TO_CREATE_OBJECT) +// CHK_ERR_WIN32A(ERROR_DS_GROUP_CONVERSION_ERROR) +// CHK_ERR_WIN32A(ERROR_DS_CANT_MOVE_APP_BASIC_GROUP) +// CHK_ERR_WIN32A(ERROR_DS_CANT_MOVE_APP_QUERY_GROUP) +// CHK_ERR_WIN32A(ERROR_DS_ROLE_NOT_VERIFIED) +// CHK_ERR_WIN32A(ERROR_DS_WKO_CONTAINER_CANNOT_BE_SPECIAL) +// CHK_ERR_WIN32A(ERROR_DS_DOMAIN_RENAME_IN_PROGRESS) +// CHK_ERR_WIN32A(ERROR_DS_EXISTING_AD_CHILD_NC) +// CHK_ERR_WIN32A(DNS_ERROR_INVALID_NAME_CHAR) +// CHK_ERR_WIN32A(DNS_ERROR_NUMERIC_NAME) +// CHK_ERR_WIN32A(DNS_ERROR_NOT_ALLOWED_ON_ROOT_SERVER) +// CHK_ERR_WIN32A(DNS_ERROR_NOT_ALLOWED_UNDER_DELEGATION) +// CHK_ERR_WIN32A(DNS_ERROR_CANNOT_FIND_ROOT_HINTS) +// CHK_ERR_WIN32A(DNS_ERROR_INCONSISTENT_ROOT_HINTS) + CHK_ERR_WIN32A(DNS_ERROR_FORWARDER_ALREADY_EXISTS) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_REQUIRES_MASTER_IP) + CHK_ERR_WIN32A(DNS_ERROR_ZONE_IS_SHUTDOWN) + CHK_ERR_WIN32A(DNS_ERROR_DP_BASE) + CHK_ERR_WIN32A(DNS_ERROR_DP_DOES_NOT_EXIST) + CHK_ERR_WIN32A(DNS_ERROR_DP_ALREADY_EXISTS) + CHK_ERR_WIN32A(DNS_ERROR_DP_NOT_ENLISTED) + CHK_ERR_WIN32A(DNS_ERROR_DP_ALREADY_ENLISTED) +// CHK_ERR_WIN32A(DNS_ERROR_DP_NOT_AVAILABLE) + CHK_ERR_WIN32A(WSA_QOS_ESERVICETYPE) + CHK_ERR_WIN32A(WSA_QOS_EFLOWSPEC) + CHK_ERR_WIN32A(WSA_QOS_EPROVSPECBUF) + CHK_ERR_WIN32A(WSA_QOS_EFILTERSTYLE) + CHK_ERR_WIN32A(WSA_QOS_EFILTERTYPE) + CHK_ERR_WIN32A(WSA_QOS_EFILTERCOUNT) + CHK_ERR_WIN32A(WSA_QOS_EOBJLENGTH) + CHK_ERR_WIN32A(WSA_QOS_EFLOWCOUNT) + CHK_ERR_WIN32A(WSA_QOS_EUNKOWNPSOBJ) + CHK_ERR_WIN32A(WSA_QOS_EPOLICYOBJ) + CHK_ERR_WIN32A(WSA_QOS_EFLOWDESC) + CHK_ERR_WIN32A(WSA_QOS_EPSFLOWSPEC) + CHK_ERR_WIN32A(WSA_QOS_EPSFILTERSPEC) + CHK_ERR_WIN32A(WSA_QOS_ESDMODEOBJ) + CHK_ERR_WIN32A(WSA_QOS_ESHAPERATEOBJ) + CHK_ERR_WIN32A(WSA_QOS_RESERVED_PETYPE) + CHK_ERR_WIN32A(ERROR_SXS_SECTION_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_SXS_CANT_GEN_ACTCTX) + CHK_ERR_WIN32A(ERROR_SXS_INVALID_ACTCTXDATA_FORMAT) + CHK_ERR_WIN32A(ERROR_SXS_ASSEMBLY_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_SXS_MANIFEST_FORMAT_ERROR) + CHK_ERR_WIN32A(ERROR_SXS_MANIFEST_PARSE_ERROR) + CHK_ERR_WIN32A(ERROR_SXS_ACTIVATION_CONTEXT_DISABLED) + CHK_ERR_WIN32A(ERROR_SXS_KEY_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_SXS_VERSION_CONFLICT) + CHK_ERR_WIN32A(ERROR_SXS_WRONG_SECTION_TYPE) + CHK_ERR_WIN32A(ERROR_SXS_THREAD_QUERIES_DISABLED) + CHK_ERR_WIN32A(ERROR_SXS_PROCESS_DEFAULT_ALREADY_SET) + CHK_ERR_WIN32A(ERROR_SXS_UNKNOWN_ENCODING_GROUP) + CHK_ERR_WIN32A(ERROR_SXS_UNKNOWN_ENCODING) + CHK_ERR_WIN32A(ERROR_SXS_INVALID_XML_NAMESPACE_URI) + CHK_ERR_WIN32A(ERROR_SXS_ROOT_MANIFEST_DEPENDENCY_NOT_INSTALLED) + CHK_ERR_WIN32A(ERROR_SXS_LEAF_MANIFEST_DEPENDENCY_NOT_INSTALLED) + CHK_ERR_WIN32A(ERROR_SXS_INVALID_ASSEMBLY_IDENTITY_ATTRIBUTE) + CHK_ERR_WIN32A(ERROR_SXS_MANIFEST_MISSING_REQUIRED_DEFAULT_NAMESPACE) + CHK_ERR_WIN32A(ERROR_SXS_MANIFEST_INVALID_REQUIRED_DEFAULT_NAMESPACE) + CHK_ERR_WIN32A(ERROR_SXS_PRIVATE_MANIFEST_CROSS_PATH_WITH_REPARSE_POINT) + CHK_ERR_WIN32A(ERROR_SXS_DUPLICATE_DLL_NAME) + CHK_ERR_WIN32A(ERROR_SXS_DUPLICATE_WINDOWCLASS_NAME) + CHK_ERR_WIN32A(ERROR_SXS_DUPLICATE_CLSID) + CHK_ERR_WIN32A(ERROR_SXS_DUPLICATE_IID) + CHK_ERR_WIN32A(ERROR_SXS_DUPLICATE_TLBID) + CHK_ERR_WIN32A(ERROR_SXS_DUPLICATE_PROGID) + CHK_ERR_WIN32A(ERROR_SXS_DUPLICATE_ASSEMBLY_NAME) + CHK_ERR_WIN32A(ERROR_SXS_FILE_HASH_MISMATCH) + CHK_ERR_WIN32A(ERROR_SXS_POLICY_PARSE_ERROR) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_MISSINGQUOTE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_COMMENTSYNTAX) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_BADSTARTNAMECHAR) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_BADNAMECHAR) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_BADCHARINSTRING) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_XMLDECLSYNTAX) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_BADCHARDATA) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_MISSINGWHITESPACE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_EXPECTINGTAGEND) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_MISSINGSEMICOLON) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNBALANCEDPAREN) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INTERNALERROR) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNEXPECTED_WHITESPACE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INCOMPLETE_ENCODING) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_MISSING_PAREN) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_EXPECTINGCLOSEQUOTE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_MULTIPLE_COLONS) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INVALID_DECIMAL) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INVALID_HEXIDECIMAL) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INVALID_UNICODE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_WHITESPACEORQUESTIONMARK) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNEXPECTEDENDTAG) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNCLOSEDTAG) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_DUPLICATEATTRIBUTE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_MULTIPLEROOTS) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INVALIDATROOTLEVEL) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_BADXMLDECL) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_MISSINGROOT) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNEXPECTEDEOF) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_BADPEREFINSUBSET) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNCLOSEDSTARTTAG) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNCLOSEDENDTAG) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNCLOSEDSTRING) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNCLOSEDCOMMENT) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNCLOSEDDECL) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNCLOSEDCDATA) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_RESERVEDNAMESPACE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INVALIDENCODING) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INVALIDSWITCH) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_BADXMLCASE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INVALID_STANDALONE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_UNEXPECTED_STANDALONE) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_INVALID_VERSION) + CHK_ERR_WIN32A(ERROR_SXS_XML_E_MISSINGEQUALS) + CHK_ERR_WIN32A(ERROR_SXS_PROTECTION_RECOVERY_FAILED) + CHK_ERR_WIN32A(ERROR_SXS_PROTECTION_PUBLIC_KEY_TOO_SHORT) + CHK_ERR_WIN32A(ERROR_SXS_PROTECTION_CATALOG_NOT_VALID) + CHK_ERR_WIN32A(ERROR_SXS_UNTRANSLATABLE_HRESULT) + CHK_ERR_WIN32A(ERROR_SXS_PROTECTION_CATALOG_FILE_MISSING) + CHK_ERR_WIN32A(ERROR_SXS_MISSING_ASSEMBLY_IDENTITY_ATTRIBUTE) + CHK_ERR_WIN32A(ERROR_SXS_INVALID_ASSEMBLY_IDENTITY_ATTRIBUTE_NAME) + CHK_ERR_WIN32A(ERROR_IPSEC_QM_POLICY_EXISTS) + CHK_ERR_WIN32A(ERROR_IPSEC_QM_POLICY_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_QM_POLICY_IN_USE) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_POLICY_EXISTS) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_POLICY_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_POLICY_IN_USE) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_FILTER_EXISTS) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_FILTER_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_TRANSPORT_FILTER_EXISTS) + CHK_ERR_WIN32A(ERROR_IPSEC_TRANSPORT_FILTER_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_AUTH_EXISTS) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_AUTH_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_AUTH_IN_USE) + CHK_ERR_WIN32A(ERROR_IPSEC_DEFAULT_MM_POLICY_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_DEFAULT_MM_AUTH_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_DEFAULT_QM_POLICY_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_TUNNEL_FILTER_EXISTS) + CHK_ERR_WIN32A(ERROR_IPSEC_TUNNEL_FILTER_NOT_FOUND) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_FILTER_PENDING_DELETION) + CHK_ERR_WIN32A(ERROR_IPSEC_TRANSPORT_FILTER_PENDING_DELETION) + CHK_ERR_WIN32A(ERROR_IPSEC_TUNNEL_FILTER_PENDING_DELETION) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_POLICY_PENDING_DELETION) + CHK_ERR_WIN32A(ERROR_IPSEC_MM_AUTH_PENDING_DELETION) + CHK_ERR_WIN32A(ERROR_IPSEC_QM_POLICY_PENDING_DELETION) +// CHK_ERR_WIN32A(WARNING_IPSEC_MM_POLICY_PRUNED) +// CHK_ERR_WIN32A(WARNING_IPSEC_QM_POLICY_PRUNED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NEG_STATUS_BEGIN) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_AUTH_FAIL) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_ATTRIB_FAIL) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NEGOTIATION_PENDING) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_GENERAL_PROCESSING_ERROR) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_TIMED_OUT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NO_CERT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_SA_DELETED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_SA_REAPED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_MM_ACQUIRE_DROP) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_QM_ACQUIRE_DROP) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_QUEUE_DROP_MM) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_QUEUE_DROP_NO_MM) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_DROP_NO_RESPONSE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_MM_DELAY_DROP) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_QM_DELAY_DROP) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_ERROR) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_CRL_FAILED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_KEY_USAGE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_CERT_TYPE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NO_PRIVATE_KEY) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_DH_FAIL) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_HEADER) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NO_POLICY) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_SIGNATURE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_KERBEROS_ERROR) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NO_PUBLIC_KEY) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_SA) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_PROP) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_TRANS) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_KE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_ID) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_CERT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_CERT_REQ) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_HASH) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_SIG) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_NONCE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_NOTIFY) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_DELETE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PROCESS_ERR_VENDOR) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_PAYLOAD) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_LOAD_SOFT_SA) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_SOFT_SA_TORN_DOWN) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_COOKIE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NO_PEER_CERT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_PEER_CRL_FAILED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_POLICY_CHANGE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NO_MM_POLICY) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NOTCBPRIV) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_SECLOADFAIL) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_FAILSSPINIT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_FAILQUERYSSP) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_SRVACQFAIL) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_SRVQUERYCRED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_GETSPIFAIL) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_FILTER) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_OUT_OF_MEMORY) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_ADD_UPDATE_KEY_FAILED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_POLICY) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_UNKNOWN_DOI) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_SITUATION) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_DH_FAILURE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_GROUP) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_ENCRYPT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_DECRYPT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_POLICY_MATCH) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_UNSUPPORTED_ID) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_HASH) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_HASH_ALG) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_HASH_SIZE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_ENCRYPT_ALG) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_AUTH_ALG) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_SIG) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_LOAD_FAILED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_RPC_DELETE) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_BENIGN_REINIT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_RESPONDER_LIFETIME_NOTIFY) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_INVALID_CERT_KEYLEN) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_MM_LIMIT) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NEGOTIATION_DISABLED) + CHK_ERR_WIN32A(ERROR_IPSEC_IKE_NEG_STATUS_END) + +// ------------------------------------------------------------- +// ddraw.h error codes +// ------------------------------------------------------------- + CHK_ERRA(DDERR_ALREADYINITIALIZED) + CHK_ERRA(DDERR_CANNOTATTACHSURFACE) + CHK_ERRA(DDERR_CANNOTDETACHSURFACE) + CHK_ERRA(DDERR_CURRENTLYNOTAVAIL) + CHK_ERRA(DDERR_EXCEPTION) +// CHK_ERRA(DDERR_GENERIC) + CHK_ERRA(DDERR_HEIGHTALIGN) + CHK_ERRA(DDERR_INCOMPATIBLEPRIMARY) + CHK_ERRA(DDERR_INVALIDCAPS) + CHK_ERRA(DDERR_INVALIDCLIPLIST) + CHK_ERRA(DDERR_INVALIDMODE) + CHK_ERRA(DDERR_INVALIDOBJECT) +// CHK_ERRA(DDERR_INVALIDPARAMS) + CHK_ERRA(DDERR_INVALIDPIXELFORMAT) + CHK_ERRA(DDERR_INVALIDRECT) + CHK_ERRA(DDERR_LOCKEDSURFACES) + CHK_ERRA(DDERR_NO3D) + CHK_ERRA(DDERR_NOALPHAHW) + CHK_ERRA(DDERR_NOSTEREOHARDWARE) + CHK_ERRA(DDERR_NOSURFACELEFT) + CHK_ERRA(DDERR_NOCLIPLIST) + CHK_ERRA(DDERR_NOCOLORCONVHW) + CHK_ERRA(DDERR_NOCOOPERATIVELEVELSET) + CHK_ERRA(DDERR_NOCOLORKEY) + CHK_ERRA(DDERR_NOCOLORKEYHW) + CHK_ERRA(DDERR_NODIRECTDRAWSUPPORT) + CHK_ERRA(DDERR_NOEXCLUSIVEMODE) + CHK_ERRA(DDERR_NOFLIPHW) + CHK_ERRA(DDERR_NOGDI) + CHK_ERRA(DDERR_NOMIRRORHW) + CHK_ERRA(DDERR_NOTFOUND) + CHK_ERRA(DDERR_NOOVERLAYHW) + CHK_ERRA(DDERR_OVERLAPPINGRECTS) + CHK_ERRA(DDERR_NORASTEROPHW) + CHK_ERRA(DDERR_NOROTATIONHW) + CHK_ERRA(DDERR_NOSTRETCHHW) + CHK_ERRA(DDERR_NOT4BITCOLOR) + CHK_ERRA(DDERR_NOT4BITCOLORINDEX) + CHK_ERRA(DDERR_NOT8BITCOLOR) + CHK_ERRA(DDERR_NOTEXTUREHW) + CHK_ERRA(DDERR_NOVSYNCHW) + CHK_ERRA(DDERR_NOZBUFFERHW) + CHK_ERRA(DDERR_NOZOVERLAYHW) + CHK_ERRA(DDERR_OUTOFCAPS) +// CHK_ERRA(DDERR_OUTOFMEMORY) +// CHK_ERRA(DDERR_OUTOFVIDEOMEMORY) + CHK_ERRA(DDERR_OVERLAYCANTCLIP) + CHK_ERRA(DDERR_OVERLAYCOLORKEYONLYONEACTIVE) + CHK_ERRA(DDERR_PALETTEBUSY) + CHK_ERRA(DDERR_COLORKEYNOTSET) + CHK_ERRA(DDERR_SURFACEALREADYATTACHED) + CHK_ERRA(DDERR_SURFACEALREADYDEPENDENT) + CHK_ERRA(DDERR_SURFACEBUSY) + CHK_ERRA(DDERR_CANTLOCKSURFACE) + CHK_ERRA(DDERR_SURFACEISOBSCURED) + CHK_ERRA(DDERR_SURFACELOST) + CHK_ERRA(DDERR_SURFACENOTATTACHED) + CHK_ERRA(DDERR_TOOBIGHEIGHT) + CHK_ERRA(DDERR_TOOBIGSIZE) + CHK_ERRA(DDERR_TOOBIGWIDTH) +// CHK_ERRA(DDERR_UNSUPPORTED) + CHK_ERRA(DDERR_UNSUPPORTEDFORMAT) + CHK_ERRA(DDERR_UNSUPPORTEDMASK) + CHK_ERRA(DDERR_INVALIDSTREAM) + CHK_ERRA(DDERR_VERTICALBLANKINPROGRESS) + CHK_ERRA(DDERR_WASSTILLDRAWING) + CHK_ERRA(DDERR_DDSCAPSCOMPLEXREQUIRED) + CHK_ERRA(DDERR_XALIGN) + CHK_ERRA(DDERR_INVALIDDIRECTDRAWGUID) + CHK_ERRA(DDERR_DIRECTDRAWALREADYCREATED) + CHK_ERRA(DDERR_NODIRECTDRAWHW) + CHK_ERRA(DDERR_PRIMARYSURFACEALREADYEXISTS) + CHK_ERRA(DDERR_NOEMULATION) + CHK_ERRA(DDERR_REGIONTOOSMALL) + CHK_ERRA(DDERR_CLIPPERISUSINGHWND) + CHK_ERRA(DDERR_NOCLIPPERATTACHED) + CHK_ERRA(DDERR_NOHWND) + CHK_ERRA(DDERR_HWNDSUBCLASSED) + CHK_ERRA(DDERR_HWNDALREADYSET) + CHK_ERRA(DDERR_NOPALETTEATTACHED) + CHK_ERRA(DDERR_NOPALETTEHW) + CHK_ERRA(DDERR_BLTFASTCANTCLIP) + CHK_ERRA(DDERR_NOBLTHW) + CHK_ERRA(DDERR_NODDROPSHW) + CHK_ERRA(DDERR_OVERLAYNOTVISIBLE) + CHK_ERRA(DDERR_NOOVERLAYDEST) + CHK_ERRA(DDERR_INVALIDPOSITION) + CHK_ERRA(DDERR_NOTAOVERLAYSURFACE) + CHK_ERRA(DDERR_EXCLUSIVEMODEALREADYSET) + CHK_ERRA(DDERR_NOTFLIPPABLE) + CHK_ERRA(DDERR_CANTDUPLICATE) + CHK_ERRA(DDERR_NOTLOCKED) + CHK_ERRA(DDERR_CANTCREATEDC) + CHK_ERRA(DDERR_NODC) + CHK_ERRA(DDERR_WRONGMODE) + CHK_ERRA(DDERR_IMPLICITLYCREATED) + CHK_ERRA(DDERR_NOTPALETTIZED) + CHK_ERRA(DDERR_UNSUPPORTEDMODE) + CHK_ERRA(DDERR_NOMIPMAPHW) + CHK_ERRA(DDERR_INVALIDSURFACETYPE) + CHK_ERRA(DDERR_NOOPTIMIZEHW) + CHK_ERRA(DDERR_NOTLOADED) + CHK_ERRA(DDERR_NOFOCUSWINDOW) + CHK_ERRA(DDERR_NOTONMIPMAPSUBLEVEL) + CHK_ERRA(DDERR_DCALREADYCREATED) + CHK_ERRA(DDERR_NONONLOCALVIDMEM) + CHK_ERRA(DDERR_CANTPAGELOCK) + CHK_ERRA(DDERR_CANTPAGEUNLOCK) + CHK_ERRA(DDERR_NOTPAGELOCKED) + CHK_ERRA(DDERR_MOREDATA) + CHK_ERRA(DDERR_EXPIRED) + CHK_ERRA(DDERR_TESTFINISHED) + CHK_ERRA(DDERR_NEWMODE) + CHK_ERRA(DDERR_D3DNOTINITIALIZED) + CHK_ERRA(DDERR_VIDEONOTACTIVE) + CHK_ERRA(DDERR_NOMONITORINFORMATION) + CHK_ERRA(DDERR_NODRIVERSUPPORT) + CHK_ERRA(DDERR_DEVICEDOESNTOWNSURFACE) + +// ------------------------------------------------------------- +// d3d10.h error codes +// ------------------------------------------------------------- + CHK_ERRA(D3D10_ERROR_TOO_MANY_UNIQUE_STATE_OBJECTS) + CHK_ERRA(D3D10_ERROR_FILE_NOT_FOUND) + +// ------------------------------------------------------------- +// dxgi.h error codes +// ------------------------------------------------------------- + CHK_ERRA(DXGI_STATUS_OCCLUDED) + CHK_ERRA(DXGI_STATUS_CLIPPED) + CHK_ERRA(DXGI_STATUS_NO_REDIRECTION) + CHK_ERRA(DXGI_STATUS_NO_DESKTOP_ACCESS) + CHK_ERRA(DXGI_STATUS_GRAPHICS_VIDPN_SOURCE_IN_USE) + CHK_ERRA(DXGI_STATUS_MODE_CHANGED) + CHK_ERRA(DXGI_STATUS_MODE_CHANGE_IN_PROGRESS) + CHK_ERRA(DXGI_ERROR_INVALID_CALL) + CHK_ERRA(DXGI_ERROR_NOT_FOUND) + CHK_ERRA(DXGI_ERROR_MORE_DATA) + CHK_ERRA(DXGI_ERROR_UNSUPPORTED) + CHK_ERRA(DXGI_ERROR_DEVICE_REMOVED) + CHK_ERRA(DXGI_ERROR_DEVICE_HUNG) + CHK_ERRA(DXGI_ERROR_DEVICE_RESET) + CHK_ERRA(DXGI_ERROR_WAS_STILL_DRAWING) + CHK_ERRA(DXGI_ERROR_FRAME_STATISTICS_DISJOINT) + CHK_ERRA(DXGI_ERROR_GRAPHICS_VIDPN_SOURCE_IN_USE) + CHK_ERRA(DXGI_ERROR_DRIVER_INTERNAL_ERROR) + CHK_ERRA(DXGI_ERROR_NONEXCLUSIVE) + CHK_ERRA(DXGI_ERROR_NOT_CURRENTLY_AVAILABLE) + CHK_ERRA(DXGI_ERROR_REMOTE_CLIENT_DISCONNECTED) + CHK_ERRA(DXGI_ERROR_REMOTE_OUTOFMEMORY) + +// ------------------------------------------------------------- +// d3d11.h error codes +// ------------------------------------------------------------- + CHK_ERRA(D3D11_ERROR_TOO_MANY_UNIQUE_STATE_OBJECTS) + CHK_ERRA(D3D11_ERROR_FILE_NOT_FOUND) + CHK_ERRA(D3D11_ERROR_TOO_MANY_UNIQUE_VIEW_OBJECTS) + CHK_ERRA(D3D11_ERROR_DEFERRED_CONTEXT_MAP_WITHOUT_INITIAL_DISCARD) + +// ------------------------------------------------------------- +// Direct2D error codes +// ------------------------------------------------------------- + CHK_ERRA(D2DERR_UNSUPPORTED_PIXEL_FORMAT) +// CHK_ERRA(D2DERR_INSUFFICIENT_BUFFER) + CHK_ERRA(D2DERR_WRONG_STATE) + CHK_ERRA(D2DERR_NOT_INITIALIZED) + CHK_ERRA(D2DERR_UNSUPPORTED_OPERATION) + CHK_ERRA(D2DERR_SCANNER_FAILED) + CHK_ERRA(D2DERR_SCREEN_ACCESS_DENIED) + CHK_ERRA(D2DERR_DISPLAY_STATE_INVALID) + CHK_ERRA(D2DERR_ZERO_VECTOR) + CHK_ERRA(D2DERR_INTERNAL_ERROR) + CHK_ERRA(D2DERR_DISPLAY_FORMAT_NOT_SUPPORTED) + CHK_ERRA(D2DERR_INVALID_CALL) + CHK_ERRA(D2DERR_NO_HARDWARE_DEVICE) + CHK_ERRA(D2DERR_RECREATE_TARGET) + CHK_ERRA(D2DERR_TOO_MANY_SHADER_ELEMENTS) + CHK_ERRA(D2DERR_SHADER_COMPILE_FAILED) + CHK_ERRA(D2DERR_MAX_TEXTURE_SIZE_EXCEEDED) + CHK_ERRA(D2DERR_UNSUPPORTED_VERSION) + CHK_ERRA(D2DERR_BAD_NUMBER) + CHK_ERRA(D2DERR_WRONG_FACTORY) + CHK_ERRA(D2DERR_LAYER_ALREADY_IN_USE) + CHK_ERRA(D2DERR_POP_CALL_DID_NOT_MATCH_PUSH) +// CHK_ERRA(D2DERR_WRONG_RESOURCE_DOMAIN) + CHK_ERRA(D2DERR_PUSH_POP_UNBALANCED) + CHK_ERRA(D2DERR_RENDER_TARGET_HAS_LAYER_OR_CLIPRECT) + CHK_ERRA(D2DERR_INCOMPATIBLE_BRUSH_TYPES) + CHK_ERRA(D2DERR_WIN32_ERROR) + CHK_ERRA(D2DERR_TARGET_NOT_GDI_COMPATIBLE) + CHK_ERRA(D2DERR_TEXT_EFFECT_IS_WRONG_TYPE) + CHK_ERRA(D2DERR_TEXT_RENDERER_NOT_RELEASED) +// CHK_ERRA(D2DERR_EXCEEDS_MAX_BITMAP_SIZE) + +// ------------------------------------------------------------- +// DirectWrite error codes +// ------------------------------------------------------------- + CHK_ERRA(DWRITE_E_FILEFORMAT) + CHK_ERRA(DWRITE_E_UNEXPECTED) + CHK_ERRA(DWRITE_E_NOFONT) + CHK_ERRA(DWRITE_E_FILENOTFOUND) + CHK_ERRA(DWRITE_E_FILEACCESS) + CHK_ERRA(DWRITE_E_FONTCOLLECTIONOBSOLETE) + CHK_ERRA(DWRITE_E_ALREADYREGISTERED) + +// ------------------------------------------------------------- +// WIC error codes +// ------------------------------------------------------------- + CHK_ERRA(WINCODEC_ERR_WRONGSTATE) + CHK_ERRA(WINCODEC_ERR_VALUEOUTOFRANGE) + CHK_ERRA(WINCODEC_ERR_UNKNOWNIMAGEFORMAT) + CHK_ERRA(WINCODEC_ERR_UNSUPPORTEDVERSION) + CHK_ERRA(WINCODEC_ERR_NOTINITIALIZED) + CHK_ERRA(WINCODEC_ERR_ALREADYLOCKED) + CHK_ERRA(WINCODEC_ERR_PROPERTYNOTFOUND) + CHK_ERRA(WINCODEC_ERR_PROPERTYNOTSUPPORTED) + CHK_ERRA(WINCODEC_ERR_PROPERTYSIZE) + CHK_ERRA(WINCODEC_ERR_CODECPRESENT) + CHK_ERRA(WINCODEC_ERR_CODECNOTHUMBNAIL) + CHK_ERRA(WINCODEC_ERR_PALETTEUNAVAILABLE) + CHK_ERRA(WINCODEC_ERR_CODECTOOMANYSCANLINES) + CHK_ERRA(WINCODEC_ERR_INTERNALERROR) + CHK_ERRA(WINCODEC_ERR_SOURCERECTDOESNOTMATCHDIMENSIONS) + CHK_ERRA(WINCODEC_ERR_COMPONENTNOTFOUND) + CHK_ERRA(WINCODEC_ERR_IMAGESIZEOUTOFRANGE) + CHK_ERRA(WINCODEC_ERR_TOOMUCHMETADATA) + CHK_ERRA(WINCODEC_ERR_BADIMAGE) + CHK_ERRA(WINCODEC_ERR_BADHEADER) + CHK_ERRA(WINCODEC_ERR_FRAMEMISSING) + CHK_ERRA(WINCODEC_ERR_BADMETADATAHEADER) + CHK_ERRA(WINCODEC_ERR_BADSTREAMDATA) + CHK_ERRA(WINCODEC_ERR_STREAMWRITE) + CHK_ERRA(WINCODEC_ERR_STREAMREAD) + CHK_ERRA(WINCODEC_ERR_STREAMNOTAVAILABLE) +// CHK_ERRA(WINCODEC_ERR_UNSUPPORTEDPIXELFORMAT) + CHK_ERRA(WINCODEC_ERR_UNSUPPORTEDOPERATION) + CHK_ERRA(WINCODEC_ERR_INVALIDREGISTRATION) + CHK_ERRA(WINCODEC_ERR_COMPONENTINITIALIZEFAILURE) + CHK_ERRA(WINCODEC_ERR_INSUFFICIENTBUFFER) + CHK_ERRA(WINCODEC_ERR_DUPLICATEMETADATAPRESENT) + CHK_ERRA(WINCODEC_ERR_PROPERTYUNEXPECTEDTYPE) + CHK_ERRA(WINCODEC_ERR_UNEXPECTEDSIZE) + CHK_ERRA(WINCODEC_ERR_INVALIDQUERYREQUEST) + CHK_ERRA(WINCODEC_ERR_UNEXPECTEDMETADATATYPE) + CHK_ERRA(WINCODEC_ERR_REQUESTONLYVALIDATMETADATAROOT) + CHK_ERRA(WINCODEC_ERR_INVALIDQUERYCHARACTER) + CHK_ERRA(WINCODEC_ERR_WIN32ERROR) + CHK_ERRA(WINCODEC_ERR_INVALIDPROGRESSIVELEVEL) + +// ------------------------------------------------------------- +// DXUT error codes +// ------------------------------------------------------------- + CHK_ERRA(DXUTERR_NODIRECT3D) + CHK_ERRA(DXUTERR_NOCOMPATIBLEDEVICES) + CHK_ERRA(DXUTERR_MEDIANOTFOUND) + CHK_ERRA(DXUTERR_NONZEROREFCOUNT) + CHK_ERRA(DXUTERR_CREATINGDEVICE) + CHK_ERRA(DXUTERR_RESETTINGDEVICE) + CHK_ERRA(DXUTERR_CREATINGDEVICEOBJECTS) + CHK_ERRA(DXUTERR_RESETTINGDEVICEOBJECTS) + CHK_ERRA(DXUTERR_INCORRECTVERSION) + CHK_ERRA(DXUTERR_DEVICEREMOVED) + +// ------------------------------------------------------------- +// xaudio2.h error codes +// ------------------------------------------------------------- + CHK_ERRA(XAUDIO2_E_INVALID_CALL) + CHK_ERRA(XAUDIO2_E_XMA_DECODER_ERROR) + CHK_ERRA(XAUDIO2_E_XAPO_CREATION_FAILED) + CHK_ERRA(XAUDIO2_E_DEVICE_INVALIDATED) + +// ------------------------------------------------------------- +// xapo.h error codes +// ------------------------------------------------------------- + CHK_ERRA(XAPO_E_FORMAT_UNSUPPORTED) + + default: return L"Unknown error."; + } +} + +//-------------------------------------------------------------------------------------- +#undef CHK_ERR +#undef CHK_ERRA +#undef HRESULT_FROM_WIN32b +#undef CHK_ERR_WIN32A +#undef CHK_ERR_WIN32_ONLY + +#define CHK_ERRA(hrchk) \ + case hrchk: \ + wcscpy_s( desc, count, L## #hrchk ); break; + +#define CHK_ERR(hrchk, strOut) \ + case hrchk: \ + wcscpy_s( desc, count, L##strOut ); break; + + +//-------------------------------------------------------------------------------------- +void WINAPI DXGetErrorDescriptionW( _In_ HRESULT hr, _Out_cap_(count) WCHAR* desc, _In_ size_t count ) +{ + if ( !count ) + return; + + *desc = 0; + + // First try to see if FormatMessage knows this hr + LPWSTR errorText = nullptr; + + DWORD result = FormatMessageW( FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS| FORMAT_MESSAGE_ALLOCATE_BUFFER, + nullptr, static_cast(hr), + MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), reinterpret_cast(&errorText), 0, nullptr ); + + if (result > 0 && errorText) + { + wcscpy_s( desc, count, errorText ); + + if ( errorText ) + LocalFree( errorText ); + + return; + } + + switch (hr) + { +// Commmented out codes are actually alises for other codes + +// ------------------------------------------------------------- +// ddraw.h error codes +// ------------------------------------------------------------- + CHK_ERR(DDERR_ALREADYINITIALIZED, "This object is already initialized") + CHK_ERR(DDERR_CANNOTATTACHSURFACE, "This surface can not be attached to the requested surface.") + CHK_ERR(DDERR_CANNOTDETACHSURFACE, "This surface can not be detached from the requested surface.") + CHK_ERR(DDERR_CURRENTLYNOTAVAIL, "Support is currently not available.") + CHK_ERR(DDERR_EXCEPTION, "An exception was encountered while performing the requested operation") +// CHK_ERR(DDERR_GENERIC, "DDERR_GENERIC") + CHK_ERR(DDERR_HEIGHTALIGN, "Height of rectangle provided is not a multiple of reqd alignment") + CHK_ERR(DDERR_INCOMPATIBLEPRIMARY, "Unable to match primary surface creation request with existing primary surface.") + CHK_ERR(DDERR_INVALIDCAPS, "One or more of the caps bits passed to the callback are incorrect.") + CHK_ERR(DDERR_INVALIDCLIPLIST, "DirectDraw does not support provided Cliplist.") + CHK_ERR(DDERR_INVALIDMODE, "DirectDraw does not support the requested mode") + CHK_ERR(DDERR_INVALIDOBJECT, "DirectDraw received a pointer that was an invalid DIRECTDRAW object.") +// CHK_ERR(DDERR_INVALIDPARAMS, "DDERR_INVALIDPARAMS") + CHK_ERR(DDERR_INVALIDPIXELFORMAT, "pixel format was invalid as specified") + CHK_ERR(DDERR_INVALIDRECT, "Rectangle provided was invalid.") + CHK_ERR(DDERR_LOCKEDSURFACES, "Operation could not be carried out because one or more surfaces are locked") + CHK_ERR(DDERR_NO3D, "There is no 3D present.") + CHK_ERR(DDERR_NOALPHAHW, "Operation could not be carried out because there is no alpha accleration hardware present or available.") + CHK_ERR(DDERR_NOSTEREOHARDWARE, "Operation could not be carried out because there is no stereo hardware present or available.") + CHK_ERR(DDERR_NOSURFACELEFT, "Operation could not be carried out because there is no hardware present which supports stereo surfaces") + CHK_ERR(DDERR_NOCLIPLIST, "no clip list available") + CHK_ERR(DDERR_NOCOLORCONVHW, "Operation could not be carried out because there is no color conversion hardware present or available.") + CHK_ERR(DDERR_NOCOOPERATIVELEVELSET, "Create function called without DirectDraw object method SetCooperativeLevel being called.") + CHK_ERR(DDERR_NOCOLORKEY, "Surface doesn't currently have a color key") + CHK_ERR(DDERR_NOCOLORKEYHW, "Operation could not be carried out because there is no hardware support of the dest color key.") + CHK_ERR(DDERR_NODIRECTDRAWSUPPORT, "No DirectDraw support possible with current display driver") + CHK_ERR(DDERR_NOEXCLUSIVEMODE, "Operation requires the application to have exclusive mode but the application does not have exclusive mode.") + CHK_ERR(DDERR_NOFLIPHW, "Flipping visible surfaces is not supported.") + CHK_ERR(DDERR_NOGDI, "There is no GDI present.") + CHK_ERR(DDERR_NOMIRRORHW, "Operation could not be carried out because there is no hardware present or available.") + CHK_ERR(DDERR_NOTFOUND, "Requested item was not found") + CHK_ERR(DDERR_NOOVERLAYHW, "Operation could not be carried out because there is no overlay hardware present or available.") + CHK_ERR(DDERR_OVERLAPPINGRECTS, "Operation could not be carried out because the source and destination rectangles are on the same surface and overlap each other.") + CHK_ERR(DDERR_NORASTEROPHW, "Operation could not be carried out because there is no appropriate raster op hardware present or available.") + CHK_ERR(DDERR_NOROTATIONHW, "Operation could not be carried out because there is no rotation hardware present or available.") + CHK_ERR(DDERR_NOSTRETCHHW, "Operation could not be carried out because there is no hardware support for stretching") + CHK_ERR(DDERR_NOT4BITCOLOR, "DirectDrawSurface is not in 4 bit color palette and the requested operation requires 4 bit color palette.") + CHK_ERR(DDERR_NOT4BITCOLORINDEX, "DirectDrawSurface is not in 4 bit color index palette and the requested operation requires 4 bit color index palette.") + CHK_ERR(DDERR_NOT8BITCOLOR, "DirectDraw Surface is not in 8 bit color mode and the requested operation requires 8 bit color.") + CHK_ERR(DDERR_NOTEXTUREHW, "Operation could not be carried out because there is no texture mapping hardware present or available.") + CHK_ERR(DDERR_NOVSYNCHW, "Operation could not be carried out because there is no hardware support for vertical blank synchronized operations.") + CHK_ERR(DDERR_NOZBUFFERHW, "Operation could not be carried out because there is no hardware support for zbuffer blting.") + CHK_ERR(DDERR_NOZOVERLAYHW, "Overlay surfaces could not be z layered based on their BltOrder because the hardware does not support z layering of overlays.") + CHK_ERR(DDERR_OUTOFCAPS, "The hardware needed for the requested operation has already been allocated.") +// CHK_ERR(DDERR_OUTOFMEMORY, "DDERR_OUTOFMEMORY") +// CHK_ERR(DDERR_OUTOFVIDEOMEMORY, "DDERR_OUTOFVIDEOMEMORY") + CHK_ERR(DDERR_OVERLAYCANTCLIP, "hardware does not support clipped overlays") + CHK_ERR(DDERR_OVERLAYCOLORKEYONLYONEACTIVE, "Can only have ony color key active at one time for overlays") + CHK_ERR(DDERR_PALETTEBUSY, "Access to this palette is being refused because the palette is already locked by another thread.") + CHK_ERR(DDERR_COLORKEYNOTSET, "No src color key specified for this operation.") + CHK_ERR(DDERR_SURFACEALREADYATTACHED, "This surface is already attached to the surface it is being attached to.") + CHK_ERR(DDERR_SURFACEALREADYDEPENDENT, "This surface is already a dependency of the surface it is being made a dependency of.") + CHK_ERR(DDERR_SURFACEBUSY, "Access to this surface is being refused because the surface is already locked by another thread.") + CHK_ERR(DDERR_CANTLOCKSURFACE, "Access to this surface is being refused because no driver exists which can supply a pointer to the surface. This is most likely to happen when attempting to lock the primary surface when no DCI provider is present. Will also happen on attempts to lock an optimized surface.") + CHK_ERR(DDERR_SURFACEISOBSCURED, "Access to Surface refused because Surface is obscured.") + CHK_ERR(DDERR_SURFACELOST, "Access to this surface is being refused because the surface is gone. The DIRECTDRAWSURFACE object representing this surface should have Restore called on it.") + CHK_ERR(DDERR_SURFACENOTATTACHED, "The requested surface is not attached.") + CHK_ERR(DDERR_TOOBIGHEIGHT, "Height requested by DirectDraw is too large.") + CHK_ERR(DDERR_TOOBIGSIZE, "Size requested by DirectDraw is too large -- The individual height and width are OK.") + CHK_ERR(DDERR_TOOBIGWIDTH, "Width requested by DirectDraw is too large.") +// CHK_ERR(DDERR_UNSUPPORTED, "DDERR_UNSUPPORTED") + CHK_ERR(DDERR_UNSUPPORTEDFORMAT, "Pixel format requested is unsupported by DirectDraw") + CHK_ERR(DDERR_UNSUPPORTEDMASK, "Bitmask in the pixel format requested is unsupported by DirectDraw") + CHK_ERR(DDERR_INVALIDSTREAM, "The specified stream contains invalid data") + CHK_ERR(DDERR_VERTICALBLANKINPROGRESS, "vertical blank is in progress") + CHK_ERR(DDERR_WASSTILLDRAWING, "Was still drawing") + CHK_ERR(DDERR_DDSCAPSCOMPLEXREQUIRED, "The specified surface type requires specification of the COMPLEX flag") + CHK_ERR(DDERR_XALIGN, "Rectangle provided was not horizontally aligned on reqd. boundary") + CHK_ERR(DDERR_INVALIDDIRECTDRAWGUID, "The GUID passed to DirectDrawCreate is not a valid DirectDraw driver identifier.") + CHK_ERR(DDERR_DIRECTDRAWALREADYCREATED, "A DirectDraw object representing this driver has already been created for this process.") + CHK_ERR(DDERR_NODIRECTDRAWHW, "A hardware only DirectDraw object creation was attempted but the driver did not support any hardware.") + CHK_ERR(DDERR_PRIMARYSURFACEALREADYEXISTS, "this process already has created a primary surface") + CHK_ERR(DDERR_NOEMULATION, "software emulation not available.") + CHK_ERR(DDERR_REGIONTOOSMALL, "region passed to Clipper::GetClipList is too small.") + CHK_ERR(DDERR_CLIPPERISUSINGHWND, "an attempt was made to set a clip list for a clipper objec that is already monitoring an hwnd.") + CHK_ERR(DDERR_NOCLIPPERATTACHED, "No clipper object attached to surface object") + CHK_ERR(DDERR_NOHWND, "Clipper notification requires an HWND or no HWND has previously been set as the CooperativeLevel HWND.") + CHK_ERR(DDERR_HWNDSUBCLASSED, "HWND used by DirectDraw CooperativeLevel has been subclassed, this prevents DirectDraw from restoring state.") + CHK_ERR(DDERR_HWNDALREADYSET, "The CooperativeLevel HWND has already been set. It can not be reset while the process has surfaces or palettes created.") + CHK_ERR(DDERR_NOPALETTEATTACHED, "No palette object attached to this surface.") + CHK_ERR(DDERR_NOPALETTEHW, "No hardware support for 16 or 256 color palettes.") + CHK_ERR(DDERR_BLTFASTCANTCLIP, "If a clipper object is attached to the source surface passed into a BltFast call.") + CHK_ERR(DDERR_NOBLTHW, "No blter.") + CHK_ERR(DDERR_NODDROPSHW, "No DirectDraw ROP hardware.") + CHK_ERR(DDERR_OVERLAYNOTVISIBLE, "returned when GetOverlayPosition is called on a hidden overlay") + CHK_ERR(DDERR_NOOVERLAYDEST, "returned when GetOverlayPosition is called on a overlay that UpdateOverlay has never been called on to establish a destionation.") + CHK_ERR(DDERR_INVALIDPOSITION, "returned when the position of the overlay on the destionation is no longer legal for that destionation.") + CHK_ERR(DDERR_NOTAOVERLAYSURFACE, "returned when an overlay member is called for a non-overlay surface") + CHK_ERR(DDERR_EXCLUSIVEMODEALREADYSET, "An attempt was made to set the cooperative level when it was already set to exclusive.") + CHK_ERR(DDERR_NOTFLIPPABLE, "An attempt has been made to flip a surface that is not flippable.") + CHK_ERR(DDERR_CANTDUPLICATE, "Can't duplicate primary & 3D surfaces, or surfaces that are implicitly created.") + CHK_ERR(DDERR_NOTLOCKED, "Surface was not locked. An attempt to unlock a surface that was not locked at all, or by this process, has been attempted.") + CHK_ERR(DDERR_CANTCREATEDC, "Windows can not create any more DCs, or a DC was requested for a paltte-indexed surface when the surface had no palette AND the display mode was not palette-indexed (in this case DirectDraw cannot select a proper palette into the DC)") + CHK_ERR(DDERR_NODC, "No DC was ever created for this surface.") + CHK_ERR(DDERR_WRONGMODE, "This surface can not be restored because it was created in a different mode.") + CHK_ERR(DDERR_IMPLICITLYCREATED, "This surface can not be restored because it is an implicitly created surface.") + CHK_ERR(DDERR_NOTPALETTIZED, "The surface being used is not a palette-based surface") + CHK_ERR(DDERR_UNSUPPORTEDMODE, "The display is currently in an unsupported mode") + CHK_ERR(DDERR_NOMIPMAPHW, "Operation could not be carried out because there is no mip-map texture mapping hardware present or available.") + CHK_ERR(DDERR_INVALIDSURFACETYPE, "The requested action could not be performed because the surface was of the wrong type.") + CHK_ERR(DDERR_NOOPTIMIZEHW, "Device does not support optimized surfaces, therefore no video memory optimized surfaces") + CHK_ERR(DDERR_NOTLOADED, "Surface is an optimized surface, but has not yet been allocated any memory") + CHK_ERR(DDERR_NOFOCUSWINDOW, "Attempt was made to create or set a device window without first setting the focus window") + CHK_ERR(DDERR_NOTONMIPMAPSUBLEVEL, "Attempt was made to set a palette on a mipmap sublevel") + CHK_ERR(DDERR_DCALREADYCREATED, "A DC has already been returned for this surface. Only one DC can be retrieved per surface.") + CHK_ERR(DDERR_NONONLOCALVIDMEM, "An attempt was made to allocate non-local video memory from a device that does not support non-local video memory.") + CHK_ERR(DDERR_CANTPAGELOCK, "The attempt to page lock a surface failed.") + CHK_ERR(DDERR_CANTPAGEUNLOCK, "The attempt to page unlock a surface failed.") + CHK_ERR(DDERR_NOTPAGELOCKED, "An attempt was made to page unlock a surface with no outstanding page locks.") + CHK_ERR(DDERR_MOREDATA, "There is more data available than the specified buffer size could hold") + CHK_ERR(DDERR_EXPIRED, "The data has expired and is therefore no longer valid.") + CHK_ERR(DDERR_TESTFINISHED, "The mode test has finished executing.") + CHK_ERR(DDERR_NEWMODE, "The mode test has switched to a new mode.") + CHK_ERR(DDERR_D3DNOTINITIALIZED, "D3D has not yet been initialized.") + CHK_ERR(DDERR_VIDEONOTACTIVE, "The video port is not active") + CHK_ERR(DDERR_NOMONITORINFORMATION, "The monitor does not have EDID data.") + CHK_ERR(DDERR_NODRIVERSUPPORT, "The driver does not enumerate display mode refresh rates.") + CHK_ERR(DDERR_DEVICEDOESNTOWNSURFACE, "Surfaces created by one direct draw device cannot be used directly by another direct draw device.") + +// ------------------------------------------------------------- +// d3d10.h error codes +// ------------------------------------------------------------- + CHK_ERR(D3D10_ERROR_TOO_MANY_UNIQUE_STATE_OBJECTS, "There are too many unique state objects.") + CHK_ERR(D3D10_ERROR_FILE_NOT_FOUND, "File not found") + +// ------------------------------------------------------------- +// dxgi.h error codes +// ------------------------------------------------------------- + CHK_ERR(DXGI_STATUS_OCCLUDED, "The target window or output has been occluded. The application should suspend rendering operations if possible.") + CHK_ERR(DXGI_STATUS_CLIPPED, "Target window is clipped.") + CHK_ERR(DXGI_STATUS_NO_REDIRECTION, "") + CHK_ERR(DXGI_STATUS_NO_DESKTOP_ACCESS, "No access to desktop.") + CHK_ERR(DXGI_STATUS_GRAPHICS_VIDPN_SOURCE_IN_USE, "") + CHK_ERR(DXGI_STATUS_MODE_CHANGED, "Display mode has changed") + CHK_ERR(DXGI_STATUS_MODE_CHANGE_IN_PROGRESS, "Display mode is changing") + CHK_ERR(DXGI_ERROR_INVALID_CALL, "The application has made an erroneous API call that it had enough information to avoid. This error is intended to denote that the application should be altered to avoid the error. Use of the debug version of the DXGI.DLL will provide run-time debug output with further information.") + CHK_ERR(DXGI_ERROR_NOT_FOUND, "The item requested was not found. For GetPrivateData calls, this means that the specified GUID had not been previously associated with the object.") + CHK_ERR(DXGI_ERROR_MORE_DATA, "The specified size of the destination buffer is too small to hold the requested data.") + CHK_ERR(DXGI_ERROR_UNSUPPORTED, "Unsupported.") + CHK_ERR(DXGI_ERROR_DEVICE_REMOVED, "Hardware device removed.") + CHK_ERR(DXGI_ERROR_DEVICE_HUNG, "Device hung due to badly formed commands.") + CHK_ERR(DXGI_ERROR_DEVICE_RESET, "Device reset due to a badly formed commant.") + CHK_ERR(DXGI_ERROR_WAS_STILL_DRAWING, "Was still drawing.") + CHK_ERR(DXGI_ERROR_FRAME_STATISTICS_DISJOINT, "The requested functionality is not supported by the device or the driver.") + CHK_ERR(DXGI_ERROR_GRAPHICS_VIDPN_SOURCE_IN_USE, "The requested functionality is not supported by the device or the driver.") + CHK_ERR(DXGI_ERROR_DRIVER_INTERNAL_ERROR, "An internal driver error occurred.") + CHK_ERR(DXGI_ERROR_NONEXCLUSIVE, "The application attempted to perform an operation on an DXGI output that is only legal after the output has been claimed for exclusive owenership.") + CHK_ERR(DXGI_ERROR_NOT_CURRENTLY_AVAILABLE, "The requested functionality is not supported by the device or the driver.") + CHK_ERR(DXGI_ERROR_REMOTE_CLIENT_DISCONNECTED, "Remote desktop client disconnected.") + CHK_ERR(DXGI_ERROR_REMOTE_OUTOFMEMORY, "Remote desktop client is out of memory.") + +// ------------------------------------------------------------- +// d3d11.h error codes +// ------------------------------------------------------------- + CHK_ERR(D3D11_ERROR_TOO_MANY_UNIQUE_STATE_OBJECTS, "There are too many unique state objects.") + CHK_ERR(D3D11_ERROR_FILE_NOT_FOUND, "File not found") + CHK_ERR(D3D11_ERROR_TOO_MANY_UNIQUE_VIEW_OBJECTS, "Therea are too many unique view objects.") + CHK_ERR(D3D11_ERROR_DEFERRED_CONTEXT_MAP_WITHOUT_INITIAL_DISCARD, "Deferred context requires Map-Discard usage pattern") + +// ------------------------------------------------------------- +// Direct2D error codes +// ------------------------------------------------------------- + CHK_ERR(D2DERR_UNSUPPORTED_PIXEL_FORMAT, "The pixel format is not supported.") +// CHK_ERR(D2DERR_INSUFFICIENT_BUFFER, "The supplied buffer was too small to accomodate the data.") + CHK_ERR(D2DERR_WRONG_STATE, "The object was not in the correct state to process the method.") + CHK_ERR(D2DERR_NOT_INITIALIZED, "The object has not yet been initialized.") + CHK_ERR(D2DERR_UNSUPPORTED_OPERATION, "The requested opertion is not supported.") + CHK_ERR(D2DERR_SCANNER_FAILED, "The geomery scanner failed to process the data.") + CHK_ERR(D2DERR_SCREEN_ACCESS_DENIED, "D2D could not access the screen.") + CHK_ERR(D2DERR_DISPLAY_STATE_INVALID, "A valid display state could not be determined.") + CHK_ERR(D2DERR_ZERO_VECTOR, "The supplied vector is zero.") + CHK_ERR(D2DERR_INTERNAL_ERROR, "An internal error (D2D bug) occurred. On checked builds, we would assert.") + CHK_ERR(D2DERR_DISPLAY_FORMAT_NOT_SUPPORTED, "The display format we need to render is not supported by the hardware device.") + CHK_ERR(D2DERR_INVALID_CALL, "A call to this method is invalid.") + CHK_ERR(D2DERR_NO_HARDWARE_DEVICE, "No HW rendering device is available for this operation.") + CHK_ERR(D2DERR_RECREATE_TARGET, "here has been a presentation error that may be recoverable. The caller needs to recreate, rerender the entire frame, and reattempt present.") + CHK_ERR(D2DERR_TOO_MANY_SHADER_ELEMENTS, "Shader construction failed because it was too complex.") + CHK_ERR(D2DERR_SHADER_COMPILE_FAILED, "Shader compilation failed.") + CHK_ERR(D2DERR_MAX_TEXTURE_SIZE_EXCEEDED, "Requested DX surface size exceeded maximum texture size.") + CHK_ERR(D2DERR_UNSUPPORTED_VERSION, "The requested D2D version is not supported.") + CHK_ERR(D2DERR_BAD_NUMBER, "Invalid number.") + CHK_ERR(D2DERR_WRONG_FACTORY, "Objects used together must be created from the same factory instance.") + CHK_ERR(D2DERR_LAYER_ALREADY_IN_USE, "A layer resource can only be in use once at any point in time.") + CHK_ERR(D2DERR_POP_CALL_DID_NOT_MATCH_PUSH, "The pop call did not match the corresponding push call") +// CHK_ERR(D2DERR_WRONG_RESOURCE_DOMAIN, "The resource was realized on the wrong render target") + CHK_ERR(D2DERR_PUSH_POP_UNBALANCED, "The push and pop calls were unbalanced") + CHK_ERR(D2DERR_RENDER_TARGET_HAS_LAYER_OR_CLIPRECT, "Attempt to copy from a render target while a layer or clip rect is applied") + CHK_ERR(D2DERR_INCOMPATIBLE_BRUSH_TYPES, "The brush types are incompatible for the call.") + CHK_ERR(D2DERR_WIN32_ERROR, "An unknown win32 failure occurred.") + CHK_ERR(D2DERR_TARGET_NOT_GDI_COMPATIBLE, "The render target is not compatible with GDI") + CHK_ERR(D2DERR_TEXT_EFFECT_IS_WRONG_TYPE, "A text client drawing effect object is of the wrong type") + CHK_ERR(D2DERR_TEXT_RENDERER_NOT_RELEASED, "The application is holding a reference to the IDWriteTextRenderer interface after the corresponding DrawText or DrawTextLayout call has returned. The IDWriteTextRenderer instance will be zombied.") +// CHK_ERR(D2DERR_EXCEEDS_MAX_BITMAP_SIZE, "The requested size is larger than the guaranteed supported texture size.") + +// ------------------------------------------------------------- +// DirectWrite error codes +// ------------------------------------------------------------- + CHK_ERR(DWRITE_E_FILEFORMAT, "Indicates an error in an input file such as a font file.") + CHK_ERR(DWRITE_E_UNEXPECTED, "Indicates an error originating in DirectWrite code, which is not expected to occur but is safe to recover from.") + CHK_ERR(DWRITE_E_NOFONT, "Indicates the specified font does not exist.") + CHK_ERR(DWRITE_E_FILENOTFOUND, "A font file could not be opened because the file, directory, network location, drive, or other storage location does not exist or is unavailable.") + CHK_ERR(DWRITE_E_FILEACCESS, "A font file exists but could not be opened due to access denied, sharing violation, or similar error.") + CHK_ERR(DWRITE_E_FONTCOLLECTIONOBSOLETE, "A font collection is obsolete due to changes in the system.") + CHK_ERR(DWRITE_E_ALREADYREGISTERED, "The given interface is already registered.") + +// ------------------------------------------------------------- +// WIC error codes +// ------------------------------------------------------------- + CHK_ERR(WINCODEC_ERR_WRONGSTATE, "WIC object in incorrect state.") + CHK_ERR(WINCODEC_ERR_VALUEOUTOFRANGE, "WIC Value out of range.") + CHK_ERR(WINCODEC_ERR_UNKNOWNIMAGEFORMAT, "Encountered unexpected value or setting in WIC image format.") + CHK_ERR(WINCODEC_ERR_UNSUPPORTEDVERSION, "Unsupported WINCODEC_SD_VERSION passed to WIC factory.") + CHK_ERR(WINCODEC_ERR_NOTINITIALIZED, "WIC component not initialized.") + CHK_ERR(WINCODEC_ERR_ALREADYLOCKED, "WIC bitmap object already locked.") + CHK_ERR(WINCODEC_ERR_PROPERTYNOTFOUND, "WIC property not found.") + CHK_ERR(WINCODEC_ERR_PROPERTYNOTSUPPORTED, "WIC property not supported.") + CHK_ERR(WINCODEC_ERR_PROPERTYSIZE, "Invalid property size") + CHK_ERRA(WINCODEC_ERR_CODECPRESENT) // not currently used by WIC + CHK_ERRA(WINCODEC_ERR_CODECNOTHUMBNAIL) // not currently used by WIC + CHK_ERR(WINCODEC_ERR_PALETTEUNAVAILABLE, "Required palette data not available.") + CHK_ERR(WINCODEC_ERR_CODECTOOMANYSCANLINES, "More scanlines requested than are available in WIC bitmap.") + CHK_ERR(WINCODEC_ERR_INTERNALERROR, "Unexpected internal error in WIC.") + CHK_ERR(WINCODEC_ERR_SOURCERECTDOESNOTMATCHDIMENSIONS, "Source WIC rectangle does not match bitmap dimensions.") + CHK_ERR(WINCODEC_ERR_COMPONENTNOTFOUND, "WIC component not found.") + CHK_ERR(WINCODEC_ERR_IMAGESIZEOUTOFRANGE, "Image size beyond expected boundaries for WIC codec." ) + CHK_ERR(WINCODEC_ERR_TOOMUCHMETADATA, "Image metadata size beyond expected boundaries for WIC codec.") + CHK_ERR(WINCODEC_ERR_BADIMAGE, "WIC image is corrupted.") + CHK_ERR(WINCODEC_ERR_BADHEADER, "Invalid header found in WIC image.") + CHK_ERR(WINCODEC_ERR_FRAMEMISSING, "Expected bitmap frame data not found in WIC image." ) + CHK_ERR(WINCODEC_ERR_BADMETADATAHEADER, "Invalid metadata header found in WIC image.") + CHK_ERR(WINCODEC_ERR_BADSTREAMDATA, "Invalid stream data found in WIC image.") + CHK_ERR(WINCODEC_ERR_STREAMWRITE, "WIC operation on write stream failed.") + CHK_ERR(WINCODEC_ERR_STREAMREAD, "WIC operation on read stream failed.") + CHK_ERR(WINCODEC_ERR_STREAMNOTAVAILABLE, "Required stream is not available." ) +// CHK_ERRA(WINCODEC_ERR_UNSUPPORTEDPIXELFORMAT) + CHK_ERR(WINCODEC_ERR_UNSUPPORTEDOPERATION, "This operation is not supported by WIC." ) + CHK_ERR(WINCODEC_ERR_INVALIDREGISTRATION, "Error occurred reading WIC codec registry keys.") + CHK_ERR(WINCODEC_ERR_COMPONENTINITIALIZEFAILURE, "Failed initializing WIC codec.") + CHK_ERR(WINCODEC_ERR_INSUFFICIENTBUFFER, "Not enough buffer space available for WIC operation.") + CHK_ERR(WINCODEC_ERR_DUPLICATEMETADATAPRESENT, "Duplicate metadata detected in WIC image.") + CHK_ERR(WINCODEC_ERR_PROPERTYUNEXPECTEDTYPE, "Unexpected property type in WIC image.") + CHK_ERR(WINCODEC_ERR_UNEXPECTEDSIZE, "Unexpected value size in WIC metadata.") + CHK_ERR(WINCODEC_ERR_INVALIDQUERYREQUEST, "Invalid metadata query.") + CHK_ERR(WINCODEC_ERR_UNEXPECTEDMETADATATYPE, "Unexpected metadata type encountered in WIC image.") + CHK_ERR(WINCODEC_ERR_REQUESTONLYVALIDATMETADATAROOT, "Operation only valid on meatadata root.") + CHK_ERR(WINCODEC_ERR_INVALIDQUERYCHARACTER, "Invalid character in WIC metadata query.") + CHK_ERR(WINCODEC_ERR_WIN32ERROR, "General Win32 error encountered during WIC operation.") + CHK_ERR(WINCODEC_ERR_INVALIDPROGRESSIVELEVEL, "Invalid level for progressive WIC image decode.") + +// ------------------------------------------------------------- +// DXUT error codes +// ------------------------------------------------------------- + CHK_ERR(DXUTERR_NODIRECT3D, "Could not initialize Direct3D.") + CHK_ERR(DXUTERR_NOCOMPATIBLEDEVICES, "No device could be found with the specified device settings.") + CHK_ERR(DXUTERR_MEDIANOTFOUND, "A media file could not be found.") + CHK_ERR(DXUTERR_NONZEROREFCOUNT, "The device interface has a non-zero reference count, meaning that some objects were not released.") + CHK_ERR(DXUTERR_CREATINGDEVICE, "An error occurred when attempting to create a device.") + CHK_ERR(DXUTERR_RESETTINGDEVICE, "An error occurred when attempting to reset a device.") + CHK_ERR(DXUTERR_CREATINGDEVICEOBJECTS, "An error occurred in the device create callback function.") + CHK_ERR(DXUTERR_RESETTINGDEVICEOBJECTS, "An error occurred in the device reset callback function.") + CHK_ERR(DXUTERR_INCORRECTVERSION, "Incorrect version of Direct3D or D3DX.") + CHK_ERR(DXUTERR_DEVICEREMOVED, "The device was removed.") + +// ------------------------------------------------------------- +// xaudio2.h error codes +// ------------------------------------------------------------- + CHK_ERR(XAUDIO2_E_INVALID_CALL, "Invalid XAudio2 API call or arguments") + CHK_ERR(XAUDIO2_E_XMA_DECODER_ERROR, "Hardware XMA decoder error") + CHK_ERR(XAUDIO2_E_XAPO_CREATION_FAILED, "Failed to create an audio effect") + CHK_ERR(XAUDIO2_E_DEVICE_INVALIDATED, "Device invalidated (unplugged, disabled, etc)") + +// ------------------------------------------------------------- +// xapo.h error codes +// ------------------------------------------------------------- + CHK_ERR(XAPO_E_FORMAT_UNSUPPORTED, "Requested audio format unsupported.") + + default: wcscpy_s( desc, count, L"Unknown error." ); break; + } +} + +//----------------------------------------------------------------------------- +HRESULT WINAPI DXTraceW( _In_z_ const WCHAR* strFile, _In_ DWORD dwLine, _In_ HRESULT hr, + _In_opt_ const WCHAR* strMsg, _In_ bool bPopMsgBox ) +{ + WCHAR strBufferLine[128]; + WCHAR strBufferError[256]; + WCHAR strBuffer[BUFFER_SIZE]; + + swprintf_s( strBufferLine, 128, L"%lu", dwLine ); + if( strFile ) + { + swprintf_s( strBuffer, BUFFER_SIZE, L"%ls(%ls): ", strFile, strBufferLine ); + OutputDebugStringW( strBuffer ); + } + + size_t nMsgLen = (strMsg) ? wcsnlen_s( strMsg, 1024 ) : 0; + if( nMsgLen > 0 ) + { + OutputDebugStringW( strMsg ); + OutputDebugStringW( L" " ); + } + + swprintf_s( strBufferError, 256, L"%ls (0x%0.8x)", DXGetErrorStringW(hr), hr ); + swprintf_s( strBuffer, BUFFER_SIZE, L"hr=%ls", strBufferError ); + OutputDebugStringW( strBuffer ); + + OutputDebugStringW( L"\n" ); + + if( bPopMsgBox ) + { + WCHAR strBufferFile[MAX_PATH]; + wcscpy_s( strBufferFile, MAX_PATH, L"" ); + if( strFile ) + wcscpy_s( strBufferFile, MAX_PATH, strFile ); + + WCHAR strBufferMsg[1024]; + wcscpy_s( strBufferMsg, 1024, L"" ); + if( nMsgLen > 0 ) + swprintf_s( strBufferMsg, 1024, L"Calling: %ls\n", strMsg ); + + swprintf_s( strBuffer, BUFFER_SIZE, L"File: %ls\nLine: %ls\nError Code: %ls\n%lsDo you want to debug the application?", + strBufferFile, strBufferLine, strBufferError, strBufferMsg ); + + int nResult = MessageBoxW( GetForegroundWindow(), strBuffer, L"Unexpected error encountered", MB_YESNO | MB_ICONERROR ); + if( nResult == IDYES ) + DebugBreak(); + } + + return hr; +} diff --git a/src/DX11/framework/dxut/Core/dxerr.h b/src/DX11/framework/dxut/Core/dxerr.h new file mode 100644 index 0000000..c5249a3 --- /dev/null +++ b/src/DX11/framework/dxut/Core/dxerr.h @@ -0,0 +1,72 @@ +//-------------------------------------------------------------------------------------- +// File: DXErr.h +// +// DirectX Error Library +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +//-------------------------------------------------------------------------------------- + +// This version only supports UNICODE. + +#pragma once + +#include +#include + +#ifdef __cplusplus +extern "C" { +#endif + +//-------------------------------------------------------------------------------------- +// DXGetErrorString +//-------------------------------------------------------------------------------------- +const WCHAR* WINAPI DXGetErrorStringW( _In_ HRESULT hr ); + +#define DXGetErrorString DXGetErrorStringW + +//-------------------------------------------------------------------------------------- +// DXGetErrorDescription has to be modified to return a copy in a buffer rather than +// the original static string. +//-------------------------------------------------------------------------------------- +void WINAPI DXGetErrorDescriptionW( _In_ HRESULT hr, _Out_cap_(count) WCHAR* desc, _In_ size_t count ); + +#define DXGetErrorDescription DXGetErrorDescriptionW + +//-------------------------------------------------------------------------------------- +// DXTrace +// +// Desc: Outputs a formatted error message to the debug stream +// +// Args: WCHAR* strFile The current file, typically passed in using the +// __FILEW__ macro. +// DWORD dwLine The current line number, typically passed in using the +// __LINE__ macro. +// HRESULT hr An HRESULT that will be traced to the debug stream. +// CHAR* strMsg A string that will be traced to the debug stream (may be NULL) +// BOOL bPopMsgBox If TRUE, then a message box will popup also containing the passed info. +// +// Return: The hr that was passed in. +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXTraceW( _In_z_ const WCHAR* strFile, _In_ DWORD dwLine, _In_ HRESULT hr, _In_opt_ const WCHAR* strMsg, _In_ bool bPopMsgBox ); + +#define DXTrace DXTraceW + +//-------------------------------------------------------------------------------------- +// +// Helper macros +// +//-------------------------------------------------------------------------------------- +#if defined(DEBUG) || defined(_DEBUG) +#define DXTRACE_MSG(str) DXTrace( __FILEW__, (DWORD)__LINE__, 0, str, false ) +#define DXTRACE_ERR(str,hr) DXTrace( __FILEW__, (DWORD)__LINE__, hr, str, false ) +#define DXTRACE_ERR_MSGBOX(str,hr) DXTrace( __FILEW__, (DWORD)__LINE__, hr, str, true ) +#else +#define DXTRACE_MSG(str) (0L) +#define DXTRACE_ERR(str,hr) (hr) +#define DXTRACE_ERR_MSGBOX(str,hr) (hr) +#endif + +#ifdef __cplusplus +} +#endif //__cplusplus diff --git a/src/DX11/framework/dxut/DXUT-config.cmake.in b/src/DX11/framework/dxut/DXUT-config.cmake.in new file mode 100644 index 0000000..fef3133 --- /dev/null +++ b/src/DX11/framework/dxut/DXUT-config.cmake.in @@ -0,0 +1,6 @@ +@PACKAGE_INIT@ + +include(${CMAKE_CURRENT_LIST_DIR}/@PROJECT_NAME@-targets.cmake) +include(${CMAKE_CURRENT_LIST_DIR}/@PROJECT_NAME@Opt-targets.cmake) + +check_required_components("@PROJECT_NAME@") diff --git a/src/DX11/framework/dxut/DXUT_2017_Win10.sln b/src/DX11/framework/dxut/DXUT_2017_Win10.sln new file mode 100644 index 0000000..10b8826 --- /dev/null +++ b/src/DX11/framework/dxut/DXUT_2017_Win10.sln @@ -0,0 +1,68 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 15 +VisualStudioVersion = 15.0.27703.2000 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DXUT", "Core\DXUT_2017_Win10.vcxproj", "{85344B7F-5AA0-4E12-A065-D1333D11F6CA}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DXUTOpt", "Optional\DXUTOpt_2017_Win10.vcxproj", "{61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{4C959E18-6969-4523-88A8-05DA5B36F168}" + ProjectSection(SolutionItems) = preProject + .editorconfig = .editorconfig + EndProjectSection +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.ActiveCfg = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.Build.0 = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.Deploy.0 = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.ActiveCfg = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.Build.0 = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.Deploy.0 = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.ActiveCfg = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.Build.0 = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.Deploy.0 = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.ActiveCfg = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.Build.0 = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.Deploy.0 = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.ActiveCfg = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.Build.0 = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.Deploy.0 = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.ActiveCfg = Release|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.Build.0 = Release|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.Deploy.0 = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.ActiveCfg = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.Build.0 = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.Deploy.0 = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.ActiveCfg = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.Build.0 = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.Deploy.0 = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.ActiveCfg = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.Build.0 = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.Deploy.0 = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.ActiveCfg = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.Build.0 = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.Deploy.0 = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.ActiveCfg = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.Build.0 = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.Deploy.0 = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.ActiveCfg = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.Build.0 = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.Deploy.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(ExtensibilityGlobals) = postSolution + SolutionGuid = {47CE266D-B0B1-44CE-A32C-E57A18C54CF3} + EndGlobalSection +EndGlobal diff --git a/src/DX11/framework/dxut/DXUT_2019_Win10.sln b/src/DX11/framework/dxut/DXUT_2019_Win10.sln new file mode 100644 index 0000000..7317732 --- /dev/null +++ b/src/DX11/framework/dxut/DXUT_2019_Win10.sln @@ -0,0 +1,68 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 16 +VisualStudioVersion = 15.0.27703.2000 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DXUT", "Core\DXUT_2019_Win10.vcxproj", "{85344B7F-5AA0-4E12-A065-D1333D11F6CA}" +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DXUTOpt", "Optional\DXUTOpt_2019_Win10.vcxproj", "{61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{4C959E18-6969-4523-88A8-05DA5B36F168}" + ProjectSection(SolutionItems) = preProject + .editorconfig = .editorconfig + EndProjectSection +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.ActiveCfg = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.Build.0 = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.Deploy.0 = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.ActiveCfg = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.Build.0 = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.Deploy.0 = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.ActiveCfg = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.Build.0 = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.Deploy.0 = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.ActiveCfg = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.Build.0 = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.Deploy.0 = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.ActiveCfg = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.Build.0 = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.Deploy.0 = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.ActiveCfg = Release|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.Build.0 = Release|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.Deploy.0 = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.ActiveCfg = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.Build.0 = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.Deploy.0 = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.ActiveCfg = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.Build.0 = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.Deploy.0 = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.ActiveCfg = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.Build.0 = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.Deploy.0 = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.ActiveCfg = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.Build.0 = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.Deploy.0 = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.ActiveCfg = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.Build.0 = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.Deploy.0 = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.ActiveCfg = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.Build.0 = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.Deploy.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(ExtensibilityGlobals) = postSolution + SolutionGuid = {47CE266D-B0B1-44CE-A32C-E57A18C54CF3} + EndGlobalSection +EndGlobal diff --git a/src/DX11/framework/dxut/DXUT_DirectXTK_2017_Win10.sln b/src/DX11/framework/dxut/DXUT_DirectXTK_2017_Win10.sln new file mode 100644 index 0000000..042ea70 --- /dev/null +++ b/src/DX11/framework/dxut/DXUT_DirectXTK_2017_Win10.sln @@ -0,0 +1,94 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 15 +VisualStudioVersion = 15.0.27703.2000 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DXUT", "Core\DXUT_DirectXTK_2017_Win10.vcxproj", "{85344B7F-5AA0-4E12-A065-D1333D11F6CA}" + ProjectSection(ProjectDependencies) = postProject + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E} = {E0B52AE7-E160-4D32-BF3F-910B785E5A8E} + EndProjectSection +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DXUTOpt", "Optional\DXUTOpt_DirectXTK_2017_Win10.vcxproj", "{61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}" + ProjectSection(ProjectDependencies) = postProject + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E} = {E0B52AE7-E160-4D32-BF3F-910B785E5A8E} + EndProjectSection +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTK_Desktop_2017", "..\DirectXTK\DirectXTK_Desktop_2017.vcxproj", "{E0B52AE7-E160-4D32-BF3F-910B785E5A8E}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{3EACA61D-02C5-45AC-AB92-6665F9022F62}" + ProjectSection(SolutionItems) = preProject + .editorconfig = .editorconfig + EndProjectSection +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.ActiveCfg = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.Build.0 = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.Deploy.0 = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.ActiveCfg = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.Build.0 = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.Deploy.0 = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.ActiveCfg = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.Build.0 = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.Deploy.0 = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.ActiveCfg = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.Build.0 = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.Deploy.0 = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.ActiveCfg = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.Build.0 = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.Deploy.0 = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.ActiveCfg = Release|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.Build.0 = Release|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.Deploy.0 = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.ActiveCfg = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.Build.0 = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.Deploy.0 = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.ActiveCfg = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.Build.0 = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.Deploy.0 = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.ActiveCfg = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.Build.0 = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.Deploy.0 = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.ActiveCfg = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.Build.0 = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.Deploy.0 = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.ActiveCfg = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.Build.0 = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.Deploy.0 = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.ActiveCfg = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.Build.0 = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.Deploy.0 = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|Win32.ActiveCfg = Debug|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|Win32.Build.0 = Debug|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|Win32.Deploy.0 = Debug|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|x64.ActiveCfg = Debug|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|x64.Build.0 = Debug|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|x64.Deploy.0 = Debug|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|Win32.ActiveCfg = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|Win32.Build.0 = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|Win32.Deploy.0 = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|x64.ActiveCfg = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|x64.Build.0 = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|x64.Deploy.0 = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|Win32.ActiveCfg = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|Win32.Build.0 = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|Win32.Deploy.0 = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|x64.ActiveCfg = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|x64.Build.0 = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|x64.Deploy.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(ExtensibilityGlobals) = postSolution + SolutionGuid = {298153E7-D73B-4B15-9824-69D4725B153C} + EndGlobalSection +EndGlobal diff --git a/src/DX11/framework/dxut/DXUT_DirectXTK_2019_Win10.sln b/src/DX11/framework/dxut/DXUT_DirectXTK_2019_Win10.sln new file mode 100644 index 0000000..602c2a4 --- /dev/null +++ b/src/DX11/framework/dxut/DXUT_DirectXTK_2019_Win10.sln @@ -0,0 +1,94 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 16 +VisualStudioVersion = 15.0.27703.2000 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DXUT", "Core\DXUT_DirectXTK_2019_Win10.vcxproj", "{85344B7F-5AA0-4E12-A065-D1333D11F6CA}" + ProjectSection(ProjectDependencies) = postProject + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E} = {E0B52AE7-E160-4D32-BF3F-910B785E5A8E} + EndProjectSection +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DXUTOpt", "Optional\DXUTOpt_DirectXTK_2019_Win10.vcxproj", "{61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}" + ProjectSection(ProjectDependencies) = postProject + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E} = {E0B52AE7-E160-4D32-BF3F-910B785E5A8E} + EndProjectSection +EndProject +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "DirectXTK_Desktop_2019", "..\DirectXTK\DirectXTK_Desktop_2019.vcxproj", "{E0B52AE7-E160-4D32-BF3F-910B785E5A8E}" +EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{3EACA61D-02C5-45AC-AB92-6665F9022F62}" + ProjectSection(SolutionItems) = preProject + .editorconfig = .editorconfig + EndProjectSection +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Debug|x64 = Debug|x64 + Profile|Win32 = Profile|Win32 + Profile|x64 = Profile|x64 + Release|Win32 = Release|Win32 + Release|x64 = Release|x64 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.ActiveCfg = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.Build.0 = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|Win32.Deploy.0 = Debug|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.ActiveCfg = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.Build.0 = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Debug|x64.Deploy.0 = Debug|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.ActiveCfg = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.Build.0 = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|Win32.Deploy.0 = Profile|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.ActiveCfg = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.Build.0 = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Profile|x64.Deploy.0 = Profile|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.ActiveCfg = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.Build.0 = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|Win32.Deploy.0 = Release|Win32 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.ActiveCfg = Release|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.Build.0 = Release|x64 + {85344B7F-5AA0-4E12-A065-D1333D11F6CA}.Release|x64.Deploy.0 = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.ActiveCfg = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.Build.0 = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|Win32.Deploy.0 = Debug|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.ActiveCfg = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.Build.0 = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Debug|x64.Deploy.0 = Debug|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.ActiveCfg = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.Build.0 = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|Win32.Deploy.0 = Profile|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.ActiveCfg = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.Build.0 = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Profile|x64.Deploy.0 = Profile|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.ActiveCfg = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.Build.0 = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|Win32.Deploy.0 = Release|Win32 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.ActiveCfg = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.Build.0 = Release|x64 + {61B333C2-C4F7-4CC1-A9BF-83F6D95588EB}.Release|x64.Deploy.0 = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|Win32.ActiveCfg = Debug|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|Win32.Build.0 = Debug|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|Win32.Deploy.0 = Debug|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|x64.ActiveCfg = Debug|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|x64.Build.0 = Debug|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Debug|x64.Deploy.0 = Debug|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|Win32.ActiveCfg = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|Win32.Build.0 = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|Win32.Deploy.0 = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|x64.ActiveCfg = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|x64.Build.0 = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Profile|x64.Deploy.0 = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|Win32.ActiveCfg = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|Win32.Build.0 = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|Win32.Deploy.0 = Release|Win32 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|x64.ActiveCfg = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|x64.Build.0 = Release|x64 + {E0B52AE7-E160-4D32-BF3F-910B785E5A8E}.Release|x64.Deploy.0 = Release|x64 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection + GlobalSection(ExtensibilityGlobals) = postSolution + SolutionGuid = {298153E7-D73B-4B15-9824-69D4725B153C} + EndGlobalSection +EndGlobal diff --git a/src/DX11/framework/dxut/HISTORY.md b/src/DX11/framework/dxut/HISTORY.md new file mode 100644 index 0000000..c0830f1 --- /dev/null +++ b/src/DX11/framework/dxut/HISTORY.md @@ -0,0 +1,134 @@ +# DXUT for Direct3D 11 + +http://go.microsoft.com/fwlink/?LinkId=320437 + +## Release History + +## December 2, 2021 +* Minor project update + +## June 2, 2021 (11.26) +* Updated DDSTextureLoader, WICTextureLoader, and ScreenGrab +* Minor code review + +## February 7, 2021 +* Added CMake project +* Removed Windows Vista support +* No code changes + +### November 17, 2020 (11.25) +* Updated DDSTextureLoader, WICTextureLoader, and ScreenGrab + +### June 3, 2020 (11.24) +* Updated DDSTextureLoader, WICTextureLoader, and ScreenGrab +* Retired VS 2015 projects + +### January 16, 2020 (11.23) +* Updated DDSTextureLoader, WICTextureLoader, and ScreenGrab + +### April 26, 2019 (11.22) +* Added VS 2019 desktop projects +* VS 2017 updated for Windows 10 October 2018 Update SDK (17763) +* Minor code cleanup + +### July 12, 2018 (11.21) +* Code cleanup + +### May 31, 2018 (11.20) +* VS 2017 updated for Windows 10 April 2018 Update SDK (17134) + +### May 11, 2018 (11.19) +* Support for Direct3D 11.2 no longer requires define ``USE_DIRECT3D11_2`` +* Retired VS 2013 projects +* Code cleanup + +### February 27, 2018 (11.18) +* Fixed array length mismatch issue with ``TOTAL_FEATURE_LEVELS`` +* Fixed optional Direct3D 11.4 support in VS 2013/2015 projects +* Minor code cleanup + +### November 2, 2017 (11.17) +* VS 2017 updated for Windows 10 Fall Creators Update SDK (16299) +* Optional support for Direct3D 11.4 (define ``USE_DIRECT3D11_4`` in projects using the 14393 or later Windows 10 SDK) + +### October 13, 2017 (11.16) +* Updated DDSTextureLoader, WICTextureLoader, and ScreenGrab +* Updated for VS 2017 update 15.1 - 15.3 and Windows 10 SDK (15063) + +### March 10, 2017 (11.15) +* Add VS 2017 projects +* Minor code cleanup + +### September 15, 2016 (11.14) +* Updated WICTextureLoader and ScreenGrab + +### August 2, 2016 (11.13) +* Updated for VS 2015 Update 3 and Windows 10 SDK (14393) + +### April 26, 2016 (11.12) +* Updated DDSTextureLoader, WICTextureLoader, and ScreenGrab +* Retired VS 2012 projects and obsolete adapter code +* Minor code and project file cleanup + +### November 30, 2015 (11.11) +* Updated DDSTextureLoader, ScreenGrab, DXERR +* Updated for VS 2015 Update 1 and Windows 10 SDK (10586) + +### July 29, 2015 (11.10) +* Updated for VS 2015 and Windows 10 SDK RTM +* Retired VS 2010 projects + +### June 16, 2015 (11.09) +* Optional support for Direct3D 11.3 (define ``USE_DIRECT3D11_3`` in VS 2015 projects) + +### April 14, 2015 (11.08) +* Fix for auto-gen of volume textures +* More updates for VS 2015 + +### November 24, 2014 (11.07) +* Minor fix for Present usage +* Minor fix for CBaseCamera::GetInput +* Minor fix for WIC usage of IWICFormatConverter +* Updates for Visual Studio 2015 Technical Preview + +### July 28, 2014 (11.06) +* Optional support for Direct3D 11.2 (define ``USE_DIRECT3D11_2`` in VS 2013 projects) +* Fixes for various UI and F2 device settings dialog issues +* Fixes for device and format enumeration +* Changed default resolution to 800x600 +* Code review fixes + +### January 24, 2014 (11.05) +* Added use of DXGI debugging when available +* Resolved CRT heap leak report +* Fixed compile bug in DXUTLockFreePipe +* Fixed bug reported in DXUT's sprite implementation +* Code cleanup (removed ``DXGI_1_2_FORMATS`` control define; ScopedObject typedef removed) + +### October 21, 2013 (11.04) +* Updated for Visual Studio 2013 and Windows 8.1 SDK RTM +* Minor fixes for systems which only have a "Microsoft Basic Renderer" device + +### September 2013 (11.03) +* Removed dependencies on the D3DX9 and D3DX11 libraries, so DXUT no longer requires the legacy DirectX SDK to build. +* It does require the d3dcompiler.h header from the Windows 8.x SDK. +* Includes standalone DDSTextureLoader, WICTexureLoader, ScreenGrab, and DxErr modules. +* Removed support for Direct3D 9 and Windows XP +* Deleted the DXUTDevice9.h/.cpp, SDKSound.h/.cpp, and SDKWaveFile.h/.cpp files +* Deleted legacy support for MCE relaunch +* General C++ code cleanups (nullptr, auto keyword, C++ style casting, Safer CRT, etc.) which are compatible with Visual C++ 2010 and 2012 +* SAL2 annotation and /analyze cleanup +* Added DXUTCompileFromFile, DXUTCreateShaderResourceViewFromFile, DXUTCreateTextureFromFile, DXUTSaveTextureToFile helpers +* Added ``-forcewarp`` command-line switch +* Added support for DXGI 1.1 and 1.2 formats +* Added Direct3D 11.1 Device/Context state +* Support Feature Level 11.1 when available + +### June 2010 (11.02) +* The DirectX SDK (June 2010) included an update to DXUT11. This is the last version to support Visual Studio 2008, Windows XP, or Direct3D 9. The source code is located in ``Samples\C++\DXUT11``. + +### February 2010 (11.01) +* An update was shipped with the DirectX SDK (February 2010). This is the last version to support Visual Studio 2005. The source code is located in ``Samples\C++\DXUT11``. + +### August 2009 (11.00) +* The initial release of DXUT11 was in DirectX SDK (August 2009). The source code is located in Samples\C++\DXUT11. This was a port of the original DXUT which supported Direct3D 10 / Direct3D 9 applications on Windows XP and Windows Vista. diff --git a/src/DX11/framework/dxut/LICENSE b/src/DX11/framework/dxut/LICENSE new file mode 100644 index 0000000..c48abe4 --- /dev/null +++ b/src/DX11/framework/dxut/LICENSE @@ -0,0 +1,21 @@ + The MIT License (MIT) + +Copyright (c) 2004-2021 Microsoft Corp + +Permission is hereby granted, free of charge, to any person obtaining a copy of this +software and associated documentation files (the "Software"), to deal in the Software +without restriction, including without limitation the rights to use, copy, modify, +merge, publish, distribute, sublicense, and/or sell copies of the Software, and to +permit persons to whom the Software is furnished to do so, subject to the following +conditions: + +The above copyright notice and this permission notice shall be included in all copies +or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, +INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A +PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT +HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF +CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE +OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + diff --git a/src/DX11/framework/dxut/Media/UI/Font.dds b/src/DX11/framework/dxut/Media/UI/Font.dds new file mode 100644 index 0000000..37514f5 Binary files /dev/null and b/src/DX11/framework/dxut/Media/UI/Font.dds differ diff --git a/src/DX11/framework/dxut/Media/UI/dxutcontrols.dds b/src/DX11/framework/dxut/Media/UI/dxutcontrols.dds new file mode 100644 index 0000000..b5f52e1 Binary files /dev/null and b/src/DX11/framework/dxut/Media/UI/dxutcontrols.dds differ diff --git a/src/DX11/framework/dxut/Optional/DXUTLockFreePipe.h b/src/DX11/framework/dxut/Optional/DXUTLockFreePipe.h new file mode 100644 index 0000000..20bdc59 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTLockFreePipe.h @@ -0,0 +1,222 @@ +//-------------------------------------------------------------------------------------- +// DXUTLockFreePipe.h +// +// See the "Lockless Programming Considerations for Xbox 360 and Microsoft Windows" +// article for more details. +// +// http://msdn.microsoft.com/en-us/library/ee418650.aspx +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +#include +#include + +#pragma pack(push) +#pragma pack(8) +#include +#pragma pack (pop) + +extern "C" + void _ReadWriteBarrier(); +#pragma intrinsic(_ReadWriteBarrier) + +// Prevent the compiler from rearranging loads +// and stores, sufficiently for read-acquire +// and write-release. This is sufficient on +// x86 and x64. +#define DXUTImportBarrier _ReadWriteBarrier +#define DXUTExportBarrier _ReadWriteBarrier + +// +// Pipe class designed for use by at most two threads: one reader, one writer. +// Access by more than two threads isn't guaranteed to be safe. +// +// In order to provide efficient access the size of the buffer is passed +// as a template parameter and restricted to powers of two less than 31. +// + +template class DXUTLockFreePipe +{ +public: + DXUTLockFreePipe() : m_readOffset( 0 ), + m_writeOffset( 0 ) + { + } + + DWORD GetBufferSize() const + { + return c_cbBufferSize; + } + + __forceinline unsigned long BytesAvailable() const + { + return m_writeOffset - m_readOffset; + } + + bool __forceinline Read( _Out_writes_(cbDest) void* pvDest, _In_ unsigned long cbDest ) + { + // Store the read and write offsets into local variables--this is + // essentially a snapshot of their values so that they stay constant + // for the duration of the function (and so we don't end up with cache + // misses due to false sharing). + DWORD readOffset = m_readOffset; + DWORD writeOffset = m_writeOffset; + + // Compare the two offsets to see if we have anything to read. + // Note that we don't do anything to synchronize the offsets here. + // Really there's not much we *can* do unless we're willing to completely + // synchronize access to the entire object. We have to assume that as we + // read, someone else may be writing, and the write offset we have now + // may be out of date by the time we read it. Fortunately that's not a + // very big deal. We might miss reading some data that was just written. + // But the assumption is that we'll be back before long to grab more data + // anyway. + // + // Note that this comparison works because we're careful to constrain + // the total buffer size to be a power of 2, which means it will divide + // evenly into ULONG_MAX+1. That, and the fact that the offsets are + // unsigned, means that the calculation returns correct results even + // when the values wrap around. + DWORD cbAvailable = writeOffset - readOffset; + if( cbDest > cbAvailable ) + { + return false; + } + + // The data has been made available, but we need to make sure + // that our view on the data is up to date -- at least as up to + // date as the control values we just read. We need to prevent + // the compiler or CPU from moving any of the data reads before + // the control value reads. This import barrier serves this + // purpose, on Xbox 360 and on Windows. + + // Reading a control value and then having a barrier is known + // as a "read-acquire." + DXUTImportBarrier(); + + unsigned char* pbDest = ( unsigned char* )pvDest; + + unsigned long actualReadOffset = readOffset & c_sizeMask; + unsigned long bytesLeft = cbDest; + + // + // Copy from the tail, then the head. Note that there's no explicit + // check to see if the write offset comes between the read offset + // and the end of the buffer--that particular condition is implicitly + // checked by the comparison with AvailableToRead(), above. If copying + // cbDest bytes off the tail would cause us to cross the write offset, + // then the previous comparison would have failed since that would imply + // that there were less than cbDest bytes available to read. + // + unsigned long cbTailBytes = std::min( bytesLeft, c_cbBufferSize - actualReadOffset ); + memcpy( pbDest, m_pbBuffer + actualReadOffset, cbTailBytes ); + bytesLeft -= cbTailBytes; + + if( bytesLeft ) + { + memcpy( pbDest + cbTailBytes, m_pbBuffer, bytesLeft ); + } + + // When we update the read offset we are, effectively, 'freeing' buffer + // memory so that the writing thread can use it. We need to make sure that + // we don't free the memory before we have finished reading it. That is, + // we need to make sure that the write to m_readOffset can't get reordered + // above the reads of the buffer data. The only way to guarantee this is to + // have an export barrier to prevent both compiler and CPU rearrangements. + DXUTExportBarrier(); + + // Advance the read offset. From the CPUs point of view this is several + // operations--read, modify, store--and we'd normally want to make sure that + // all of the operations happened atomically. But in the case of a single + // reader, only one thread updates this value and so the only operation that + // must be atomic is the store. That's lucky, because 32-bit aligned stores are + // atomic on all modern processors. + // + readOffset += cbDest; + m_readOffset = readOffset; + + return true; + } + + bool __forceinline Write( _In_reads_(cbSrc) const void* pvSrc, _In_ unsigned long cbSrc ) + { + // Reading the read offset here has the same caveats as reading + // the write offset had in the Read() function above. + DWORD readOffset = m_readOffset; + DWORD writeOffset = m_writeOffset; + + // Compute the available write size. This comparison relies on + // the fact that the buffer size is always a power of 2, and the + // offsets are unsigned integers, so that when the write pointer + // wraps around the subtraction still yields a value (assuming + // we haven't messed up somewhere else) between 0 and c_cbBufferSize - 1. + DWORD cbAvailable = c_cbBufferSize - ( writeOffset - readOffset ); + if( cbSrc > cbAvailable ) + { + return false; + } + + // It is theoretically possible for writes of the data to be reordered + // above the reads to see if the data is available. Improbable perhaps, + // but possible. This barrier guarantees that the reordering will not + // happen. + DXUTImportBarrier(); + + // Write the data + const unsigned char* pbSrc = ( const unsigned char* )pvSrc; + unsigned long actualWriteOffset = writeOffset & c_sizeMask; + unsigned long bytesLeft = cbSrc; + + // See the explanation in the Read() function as to why we don't + // explicitly check against the read offset here. + unsigned long cbTailBytes = std::min( bytesLeft, c_cbBufferSize - actualWriteOffset ); + memcpy( m_pbBuffer + actualWriteOffset, pbSrc, cbTailBytes ); + bytesLeft -= cbTailBytes; + + if( bytesLeft ) + { + memcpy( m_pbBuffer, pbSrc + cbTailBytes, bytesLeft ); + } + + // Now it's time to update the write offset, but since the updated position + // of the write offset will imply that there's data to be read, we need to + // make sure that the data all actually gets written before the update to + // the write offset. The writes could be reordered by the compiler (on any + // platform) or by the CPU (on Xbox 360). We need a barrier which prevents + // the writes from being reordered past each other. + // + // Having a barrier and then writing a control value is called "write-release." + DXUTExportBarrier(); + + // See comments in Read() as to why this operation isn't interlocked. + writeOffset += cbSrc; + m_writeOffset = writeOffset; + + return true; + } + +private: + // Values derived from the buffer size template parameter + // + static const BYTE c_cbBufferSizeLog2 = __min( cbBufferSizeLog2, 31 ); + static const DWORD c_cbBufferSize = ( 1 << c_cbBufferSizeLog2 ); + static const DWORD c_sizeMask = c_cbBufferSize - 1; + + // Leave these private and undefined to prevent their use + DXUTLockFreePipe( const DXUTLockFreePipe& ); + DXUTLockFreePipe& operator =( const DXUTLockFreePipe& ); + + // Member data + // + BYTE m_pbBuffer[c_cbBufferSize]; + // Note that these offsets are not clamped to the buffer size. + // Instead the calculations rely on wrapping at ULONG_MAX+1. + // See the comments in Read() for details. + volatile DWORD __declspec( align( 4 ) ) m_readOffset; + volatile DWORD __declspec( align( 4 ) ) m_writeOffset; +}; \ No newline at end of file diff --git a/src/DX11/framework/dxut/Optional/DXUTOpt_2017_Win10.vcxproj b/src/DX11/framework/dxut/Optional/DXUTOpt_2017_Win10.vcxproj new file mode 100644 index 0000000..0209fd5 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTOpt_2017_Win10.vcxproj @@ -0,0 +1,358 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DXUTOpt + {61B333C2-C4F7-4cc1-A9BF-83F6D95588EB} + DXUTOpt + Win32Proj + 10.0.19041.0 + + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2017_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + StreamingSIMDExtensions2 + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/DX11/framework/dxut/Optional/DXUTOpt_2017_Win10.vcxproj.filters b/src/DX11/framework/dxut/Optional/DXUTOpt_2017_Win10.vcxproj.filters new file mode 100644 index 0000000..1bdbaf9 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTOpt_2017_Win10.vcxproj.filters @@ -0,0 +1,32 @@ + + + + +{8e114980-c1a3-4ada-ad7c-83caadf5daeb} +rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/DX11/framework/dxut/Optional/DXUTOpt_2019_Win10.vcxproj b/src/DX11/framework/dxut/Optional/DXUTOpt_2019_Win10.vcxproj new file mode 100644 index 0000000..d9c708b --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTOpt_2019_Win10.vcxproj @@ -0,0 +1,358 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DXUTOpt + {61B333C2-C4F7-4cc1-A9BF-83F6D95588EB} + DXUTOpt + Win32Proj + 10.0 + + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + + + + + + + + + + + + + + + + + + + + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + Bin\Desktop_2019_Win10\$(Platform)\$(Configuration)\ + DXUTOpt + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + StreamingSIMDExtensions2 + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;_WIN32_WINNT=0x0601;_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/DX11/framework/dxut/Optional/DXUTOpt_2019_Win10.vcxproj.filters b/src/DX11/framework/dxut/Optional/DXUTOpt_2019_Win10.vcxproj.filters new file mode 100644 index 0000000..1bdbaf9 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTOpt_2019_Win10.vcxproj.filters @@ -0,0 +1,32 @@ + + + + +{8e114980-c1a3-4ada-ad7c-83caadf5daeb} +rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2017_Win10.vcxproj b/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2017_Win10.vcxproj new file mode 100644 index 0000000..4335b43 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2017_Win10.vcxproj @@ -0,0 +1,356 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DXUTOpt + {61B333C2-C4F7-4cc1-A9BF-83F6D95588EB} + DXUTOpt + Win32Proj + 10.0.19041.0 + + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + StaticLibrary + true + Unicode + v141 + + + + + + + + + + + + + + + + + + + + + + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2017\$(Platform)\$(Configuration)\ + DXUTOpt + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2017_Win10.vcxproj.filters b/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2017_Win10.vcxproj.filters new file mode 100644 index 0000000..b959c9a --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2017_Win10.vcxproj.filters @@ -0,0 +1,30 @@ + + + + +{8e114980-c1a3-4ada-ad7c-83caadf5daeb} +rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2019_Win10.vcxproj b/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2019_Win10.vcxproj new file mode 100644 index 0000000..f7b908c --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2019_Win10.vcxproj @@ -0,0 +1,356 @@ + + + + + Debug + Win32 + + + Debug + x64 + + + Profile + Win32 + + + Profile + x64 + + + Release + Win32 + + + Release + x64 + + + + DXUTOpt + {61B333C2-C4F7-4cc1-A9BF-83F6D95588EB} + DXUTOpt + Win32Proj + 10.0 + + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + StaticLibrary + true + Unicode + v142 + + + + + + + + + + + + + + + + + + + + + + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUTOpt + + + true + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + Bin\DirectXTK_2019\$(Platform)\$(Configuration)\ + DXUTOpt + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + Disabled + MultiThreadedDebugDLL + Fast + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;_DEBUG;DEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + ProgramDatabase + false + + + Windows + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + StreamingSIMDExtensions2 + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + Level4 + MaxSpeed + Fast + ..\..\DirectXTK\Inc;..\Core\;%(AdditionalIncludeDirectories) + /Zc:__cplusplus %(AdditionalOptions) + WIN32;NDEBUG;PROFILE;_WINDOWS;_LIB;USE_DIRECT3D11_4;USE_DIRECTXTK;_WIN32_WINNT=0x0601;%(PreprocessorDefinitions) + $(IntDir)$(TargetName).pdb + Use + DXUT.h + true + + + true + Windows + true + true + + + false + + + + + + + + + + + + + + + + + + + + + Create + Create + Create + Create + Create + Create + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2019_Win10.vcxproj.filters b/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2019_Win10.vcxproj.filters new file mode 100644 index 0000000..b959c9a --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTOpt_DirectXTK_2019_Win10.vcxproj.filters @@ -0,0 +1,30 @@ + + + + +{8e114980-c1a3-4ada-ad7c-83caadf5daeb} +rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/DX11/framework/dxut/Optional/DXUTcamera.cpp b/src/DX11/framework/dxut/Optional/DXUTcamera.cpp new file mode 100644 index 0000000..e20e330 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTcamera.cpp @@ -0,0 +1,1249 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTcamera.cpp +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "DXUT.h" +#include "DXUTcamera.h" +#include "DXUTres.h" + +using namespace DirectX; + +//====================================================================================== +// CD3DArcBall +//====================================================================================== + +//-------------------------------------------------------------------------------------- +CD3DArcBall::CD3DArcBall() noexcept : + m_mRotation{}, + m_mTranslation{}, + m_mTranslationDelta{}, + m_Offset{ 0, 0 }, + m_nWidth(0), + m_nHeight(0), + m_vCenter{}, + m_fRadius(0), + m_fRadiusTranslation(0), + m_qDown{}, + m_qNow{}, + m_bDrag(false), + m_ptLastMouse{}, + m_vDownPt( 0, 0, 0 ), + m_vCurrentPt( 0, 0, 0 ) +{ + Reset(); + + RECT rc; + GetClientRect( GetForegroundWindow(), &rc ); + SetWindow( rc.right, rc.bottom ); +} + + +//-------------------------------------------------------------------------------------- +void CD3DArcBall::Reset() +{ + XMVECTOR qid = XMQuaternionIdentity(); + XMStoreFloat4( &m_qDown, qid ); + XMStoreFloat4( &m_qNow, qid ); + + XMMATRIX id = XMMatrixIdentity(); + XMStoreFloat4x4( &m_mRotation, id ); + XMStoreFloat4x4( &m_mTranslation, id ); + XMStoreFloat4x4( &m_mTranslationDelta, id ); + + m_bDrag = false; + m_fRadiusTranslation = 1.0f; + m_fRadius = 1.0f; +} + + +//-------------------------------------------------------------------------------------- +void CD3DArcBall::OnBegin( _In_ int nX, _In_ int nY ) +{ + // Only enter the drag state if the click falls + // inside the click rectangle. + if( nX >= m_Offset.x && + nX < m_Offset.x + m_nWidth && + nY >= m_Offset.y && + nY < m_Offset.y + m_nHeight ) + { + m_bDrag = true; + m_qDown = m_qNow; + XMVECTOR v = ScreenToVector( float(nX), float(nY) ); + XMStoreFloat3( &m_vDownPt, v ); + } +} + + +//-------------------------------------------------------------------------------------- +void CD3DArcBall::OnMove( _In_ int nX, _In_ int nY ) +{ + if( m_bDrag ) + { + XMVECTOR curr = ScreenToVector( ( float )nX, ( float )nY ); + XMStoreFloat3( &m_vCurrentPt, curr ); + + XMVECTOR down = XMLoadFloat3( &m_vDownPt ); + XMVECTOR qdown = XMLoadFloat4( &m_qDown ); + + XMVECTOR result = XMQuaternionMultiply( qdown, QuatFromBallPoints( down, curr ) ); + XMStoreFloat4( &m_qNow, result ); + } +} + + +//-------------------------------------------------------------------------------------- +void CD3DArcBall::OnEnd() +{ + m_bDrag = false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +LRESULT CD3DArcBall::HandleMessages( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + // Current mouse position + int iMouseX = ( short )LOWORD( lParam ); + int iMouseY = ( short )HIWORD( lParam ); + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + SetCapture( hWnd ); + OnBegin( iMouseX, iMouseY ); + return TRUE; + + case WM_LBUTTONUP: + ReleaseCapture(); + OnEnd(); + return TRUE; + case WM_CAPTURECHANGED: + if( ( HWND )lParam != hWnd ) + { + ReleaseCapture(); + OnEnd(); + } + return TRUE; + + case WM_RBUTTONDOWN: + case WM_RBUTTONDBLCLK: + case WM_MBUTTONDOWN: + case WM_MBUTTONDBLCLK: + SetCapture( hWnd ); + // Store off the position of the cursor when the button is pressed + m_ptLastMouse.x = iMouseX; + m_ptLastMouse.y = iMouseY; + return TRUE; + + case WM_RBUTTONUP: + case WM_MBUTTONUP: + ReleaseCapture(); + return TRUE; + + case WM_MOUSEMOVE: + if( MK_LBUTTON & wParam ) + { + OnMove( iMouseX, iMouseY ); + } + else if( ( MK_RBUTTON & wParam ) || ( MK_MBUTTON & wParam ) ) + { + // Normalize based on size of window and bounding sphere radius + float fDeltaX = ( m_ptLastMouse.x - iMouseX ) * m_fRadiusTranslation / m_nWidth; + float fDeltaY = ( m_ptLastMouse.y - iMouseY ) * m_fRadiusTranslation / m_nHeight; + + XMMATRIX mTranslationDelta; + XMMATRIX mTranslation = XMLoadFloat4x4( &m_mTranslation ); + if( wParam & MK_RBUTTON ) + { + mTranslationDelta = XMMatrixTranslation( -2 * fDeltaX, 2 * fDeltaY, 0.0f ); + mTranslation = XMMatrixMultiply( mTranslation, mTranslationDelta ); + } + else // wParam & MK_MBUTTON + { + mTranslationDelta = XMMatrixTranslation( 0.0f, 0.0f, 5 * fDeltaY ); + mTranslation = XMMatrixMultiply( mTranslation, mTranslationDelta ); + } + + XMStoreFloat4x4( &m_mTranslationDelta, mTranslationDelta ); + XMStoreFloat4x4( &m_mTranslation, mTranslation ); + + // Store mouse coordinate + m_ptLastMouse.x = iMouseX; + m_ptLastMouse.y = iMouseY; + } + return TRUE; + } + + return FALSE; +} + + +//====================================================================================== +// CBaseCamera +//====================================================================================== + +//-------------------------------------------------------------------------------------- +// Constructor +//-------------------------------------------------------------------------------------- +CBaseCamera::CBaseCamera() noexcept : + m_mView{}, + m_mProj{}, + m_GamePad{}, + m_vGamePadLeftThumb(0,0,0), + m_vGamePadRightThumb(0,0,0), + m_GamePadLastActive{}, + m_cKeysDown(0), + m_aKeys{}, + m_vKeyboardDirection(0,0,0), + m_ptLastMousePosition{ 0, 0 }, + m_nCurrentButtonMask(0), + m_nMouseWheelDelta(0), + m_vMouseDelta(0, 0), + m_fFramesToSmoothMouseData(2.0f), + m_vDefaultEye(0, 0, 0), + m_vDefaultLookAt(0, 0, 0), + m_vEye(0, 0, 0), + m_vLookAt(0, 0, 0), + m_fCameraYawAngle(0.0f), + m_fCameraPitchAngle(0.0f), + m_rcDrag{}, + m_vVelocity(0, 0, 0), + m_vVelocityDrag(0, 0, 0), + m_fDragTimer(0.0f), + m_fTotalDragTimeToZero(0.25), + m_vRotVelocity(0, 0), + m_fFOV(0), + m_fAspect(0), + m_fNearPlane(0), + m_fFarPlane(1), + m_fRotationScaler(0.01f), + m_fMoveScaler(5.0f), + m_bMouseLButtonDown(false), + m_bMouseMButtonDown(false), + m_bMouseRButtonDown(false), + m_bMovementDrag(false), + m_bInvertPitch(false), + m_bEnablePositionMovement(true), + m_bEnableYAxisMovement(true), + m_bClipToBoundary(false), + m_bResetCursorAfterMove(false), + m_vMinBoundary(-1, -1, -1), + m_vMaxBoundary(1, 1, 1) +{ + // Setup the view matrix + SetViewParams( g_XMZero, g_XMIdentityR2 ); + + // Setup the projection matrix + SetProjParams( XM_PI / 4, 1.0f, 1.0f, 1000.0f ); + + GetCursorPos( &m_ptLastMousePosition ); + + SetRect( &m_rcDrag, LONG_MIN, LONG_MIN, LONG_MAX, LONG_MAX ); +} + + +//-------------------------------------------------------------------------------------- +// Client can call this to change the position and direction of camera +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CBaseCamera::SetViewParams( FXMVECTOR vEyePt, FXMVECTOR vLookatPt ) +{ + XMStoreFloat3( &m_vEye, vEyePt ); + XMStoreFloat3( &m_vDefaultEye, vEyePt ); + + XMStoreFloat3( &m_vLookAt, vLookatPt ); + XMStoreFloat3( &m_vDefaultLookAt , vLookatPt ); + + // Calc the view matrix + XMMATRIX mView = XMMatrixLookAtLH( vEyePt, vLookatPt, g_XMIdentityR1 ); + XMStoreFloat4x4( &m_mView, mView ); + + XMMATRIX mInvView = XMMatrixInverse( nullptr, mView ); + + // The axis basis vectors and camera position are stored inside the + // position matrix in the 4 rows of the camera's world matrix. + // To figure out the yaw/pitch of the camera, we just need the Z basis vector + XMFLOAT3 zBasis; + XMStoreFloat3( &zBasis, mInvView.r[2] ); + + m_fCameraYawAngle = atan2f( zBasis.x, zBasis.z ); + float fLen = sqrtf( zBasis.z * zBasis.z + zBasis.x * zBasis.x ); + m_fCameraPitchAngle = -atan2f( zBasis.y, fLen ); +} + + +//-------------------------------------------------------------------------------------- +// Calculates the projection matrix based on input params +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CBaseCamera::SetProjParams( float fFOV, float fAspect, float fNearPlane, float fFarPlane ) +{ + // Set attributes for the projection matrix + m_fFOV = fFOV; + m_fAspect = fAspect; + m_fNearPlane = fNearPlane; + m_fFarPlane = fFarPlane; + + XMMATRIX mProj = XMMatrixPerspectiveFovLH( fFOV, fAspect, fNearPlane, fFarPlane ); + XMStoreFloat4x4( &m_mProj, mProj ); +} + + +//-------------------------------------------------------------------------------------- +// Call this from your message proc so this class can handle window messages +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +LRESULT CBaseCamera::HandleMessages( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER( hWnd ); + UNREFERENCED_PARAMETER( lParam ); + + switch( uMsg ) + { + case WM_KEYDOWN: + { + // Map this key to a D3DUtil_CameraKeys enum and update the + // state of m_aKeys[] by adding the KEY_WAS_DOWN_MASK|KEY_IS_DOWN_MASK mask + // only if the key is not down + D3DUtil_CameraKeys mappedKey = MapKey( ( UINT )wParam ); + if( mappedKey != CAM_UNKNOWN ) + { + _Analysis_assume_( mappedKey < CAM_MAX_KEYS ); + if( FALSE == IsKeyDown( m_aKeys[mappedKey] ) ) + { + m_aKeys[ mappedKey ] = KEY_WAS_DOWN_MASK | KEY_IS_DOWN_MASK; + ++m_cKeysDown; + } + } + break; + } + + case WM_KEYUP: + { + // Map this key to a D3DUtil_CameraKeys enum and update the + // state of m_aKeys[] by removing the KEY_IS_DOWN_MASK mask. + D3DUtil_CameraKeys mappedKey = MapKey( ( UINT )wParam ); + if( mappedKey != CAM_UNKNOWN && ( DWORD )mappedKey < 8 ) + { + m_aKeys[ mappedKey ] &= ~KEY_IS_DOWN_MASK; + --m_cKeysDown; + } + break; + } + + case WM_RBUTTONDOWN: + case WM_MBUTTONDOWN: + case WM_LBUTTONDOWN: + case WM_RBUTTONDBLCLK: + case WM_MBUTTONDBLCLK: + case WM_LBUTTONDBLCLK: + { + // Compute the drag rectangle in screen coord. + POINT ptCursor = + { + ( short )LOWORD( lParam ), ( short )HIWORD( lParam ) + }; + + // Update member var state + if( ( uMsg == WM_LBUTTONDOWN || uMsg == WM_LBUTTONDBLCLK ) && PtInRect( &m_rcDrag, ptCursor ) ) + { + m_bMouseLButtonDown = true; m_nCurrentButtonMask |= MOUSE_LEFT_BUTTON; + } + if( ( uMsg == WM_MBUTTONDOWN || uMsg == WM_MBUTTONDBLCLK ) && PtInRect( &m_rcDrag, ptCursor ) ) + { + m_bMouseMButtonDown = true; m_nCurrentButtonMask |= MOUSE_MIDDLE_BUTTON; + } + if( ( uMsg == WM_RBUTTONDOWN || uMsg == WM_RBUTTONDBLCLK ) && PtInRect( &m_rcDrag, ptCursor ) ) + { + m_bMouseRButtonDown = true; m_nCurrentButtonMask |= MOUSE_RIGHT_BUTTON; + } + + // Capture the mouse, so if the mouse button is + // released outside the window, we'll get the WM_LBUTTONUP message + SetCapture( hWnd ); + GetCursorPos( &m_ptLastMousePosition ); + return TRUE; + } + + case WM_RBUTTONUP: + case WM_MBUTTONUP: + case WM_LBUTTONUP: + { + // Update member var state + if( uMsg == WM_LBUTTONUP ) + { + m_bMouseLButtonDown = false; m_nCurrentButtonMask &= ~MOUSE_LEFT_BUTTON; + } + if( uMsg == WM_MBUTTONUP ) + { + m_bMouseMButtonDown = false; m_nCurrentButtonMask &= ~MOUSE_MIDDLE_BUTTON; + } + if( uMsg == WM_RBUTTONUP ) + { + m_bMouseRButtonDown = false; m_nCurrentButtonMask &= ~MOUSE_RIGHT_BUTTON; + } + + // Release the capture if no mouse buttons down + if( !m_bMouseLButtonDown && + !m_bMouseRButtonDown && + !m_bMouseMButtonDown ) + { + ReleaseCapture(); + } + break; + } + + case WM_CAPTURECHANGED: + { + if( ( HWND )lParam != hWnd ) + { + if( ( m_nCurrentButtonMask & MOUSE_LEFT_BUTTON ) || + ( m_nCurrentButtonMask & MOUSE_MIDDLE_BUTTON ) || + ( m_nCurrentButtonMask & MOUSE_RIGHT_BUTTON ) ) + { + m_bMouseLButtonDown = false; + m_bMouseMButtonDown = false; + m_bMouseRButtonDown = false; + m_nCurrentButtonMask &= ~MOUSE_LEFT_BUTTON; + m_nCurrentButtonMask &= ~MOUSE_MIDDLE_BUTTON; + m_nCurrentButtonMask &= ~MOUSE_RIGHT_BUTTON; + ReleaseCapture(); + } + } + break; + } + + case WM_MOUSEWHEEL: + // Update member var state + m_nMouseWheelDelta += ( short )HIWORD( wParam ); + break; + } + + return FALSE; +} + + +//-------------------------------------------------------------------------------------- +// Figure out the velocity based on keyboard input & drag if any +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CBaseCamera::GetInput( bool bGetKeyboardInput, bool bGetMouseInput, bool bGetGamepadInput ) +{ + m_vKeyboardDirection = XMFLOAT3( 0, 0, 0 ); + if( bGetKeyboardInput ) + { + // Update acceleration vector based on keyboard state + if( IsKeyDown( m_aKeys[CAM_MOVE_FORWARD] ) ) + m_vKeyboardDirection.z += 1.0f; + if( IsKeyDown( m_aKeys[CAM_MOVE_BACKWARD] ) ) + m_vKeyboardDirection.z -= 1.0f; + if( m_bEnableYAxisMovement ) + { + if( IsKeyDown( m_aKeys[CAM_MOVE_UP] ) ) + m_vKeyboardDirection.y += 1.0f; + if( IsKeyDown( m_aKeys[CAM_MOVE_DOWN] ) ) + m_vKeyboardDirection.y -= 1.0f; + } + if( IsKeyDown( m_aKeys[CAM_STRAFE_RIGHT] ) ) + m_vKeyboardDirection.x += 1.0f; + if( IsKeyDown( m_aKeys[CAM_STRAFE_LEFT] ) ) + m_vKeyboardDirection.x -= 1.0f; + } + + if( bGetMouseInput ) + { + UpdateMouseDelta(); + } + + if( bGetGamepadInput ) + { + m_vGamePadLeftThumb = XMFLOAT3( 0, 0, 0 ); + m_vGamePadRightThumb = XMFLOAT3( 0, 0, 0 ); + + // Get controller state + for( DWORD iUserIndex = 0; iUserIndex < DXUT_MAX_CONTROLLERS; iUserIndex++ ) + { + DXUTGetGamepadState( iUserIndex, &m_GamePad[iUserIndex], true, true ); + + // Mark time if the controller is in a non-zero state + if( m_GamePad[iUserIndex].wButtons || + m_GamePad[iUserIndex].sThumbLX || m_GamePad[iUserIndex].sThumbLY || + m_GamePad[iUserIndex].sThumbRX || m_GamePad[iUserIndex].sThumbRY || + m_GamePad[iUserIndex].bLeftTrigger || m_GamePad[iUserIndex].bRightTrigger ) + { + m_GamePadLastActive[iUserIndex] = DXUTGetTime(); + } + } + + // Find out which controller was non-zero last + int iMostRecentlyActive = -1; + double fMostRecentlyActiveTime = 0.0f; + for( DWORD iUserIndex = 0; iUserIndex < DXUT_MAX_CONTROLLERS; iUserIndex++ ) + { + if( m_GamePadLastActive[iUserIndex] > fMostRecentlyActiveTime ) + { + fMostRecentlyActiveTime = m_GamePadLastActive[iUserIndex]; + iMostRecentlyActive = iUserIndex; + } + } + + // Use the most recent non-zero controller if its connected + if( iMostRecentlyActive >= 0 && m_GamePad[iMostRecentlyActive].bConnected ) + { + m_vGamePadLeftThumb.x = m_GamePad[iMostRecentlyActive].fThumbLX; + m_vGamePadLeftThumb.y = 0.0f; + m_vGamePadLeftThumb.z = m_GamePad[iMostRecentlyActive].fThumbLY; + + m_vGamePadRightThumb.x = m_GamePad[iMostRecentlyActive].fThumbRX; + m_vGamePadRightThumb.y = 0.0f; + m_vGamePadRightThumb.z = m_GamePad[iMostRecentlyActive].fThumbRY; + } + } +} + + +//-------------------------------------------------------------------------------------- +// Figure out the mouse delta based on mouse movement +//-------------------------------------------------------------------------------------- +void CBaseCamera::UpdateMouseDelta() +{ + // Get current position of mouse + POINT ptCurMousePos; + GetCursorPos( &ptCurMousePos ); + + // Calc how far it's moved since last frame + POINT ptCurMouseDelta; + ptCurMouseDelta.x = ptCurMousePos.x - m_ptLastMousePosition.x; + ptCurMouseDelta.y = ptCurMousePos.y - m_ptLastMousePosition.y; + + // Record current position for next time + m_ptLastMousePosition = ptCurMousePos; + + if( m_bResetCursorAfterMove && DXUTIsActive() ) + { + // Set position of camera to center of desktop, + // so it always has room to move. This is very useful + // if the cursor is hidden. If this isn't done and cursor is hidden, + // then invisible cursor will hit the edge of the screen + // and the user can't tell what happened + POINT ptCenter; + + // Get the center of the current monitor + MONITORINFO mi; + mi.cbSize = sizeof( MONITORINFO ); + DXUTGetMonitorInfo( DXUTMonitorFromWindow( DXUTGetHWND(), MONITOR_DEFAULTTONEAREST ), &mi ); + ptCenter.x = ( mi.rcMonitor.left + mi.rcMonitor.right ) / 2; + ptCenter.y = ( mi.rcMonitor.top + mi.rcMonitor.bottom ) / 2; + SetCursorPos( ptCenter.x, ptCenter.y ); + m_ptLastMousePosition = ptCenter; + } + + // Smooth the relative mouse data over a few frames so it isn't + // jerky when moving slowly at low frame rates. + float fPercentOfNew = 1.0f / m_fFramesToSmoothMouseData; + float fPercentOfOld = 1.0f - fPercentOfNew; + m_vMouseDelta.x = m_vMouseDelta.x * fPercentOfOld + ptCurMouseDelta.x * fPercentOfNew; + m_vMouseDelta.y = m_vMouseDelta.y * fPercentOfOld + ptCurMouseDelta.y * fPercentOfNew; + + m_vRotVelocity.x = m_vMouseDelta.x * m_fRotationScaler; + m_vRotVelocity.y = m_vMouseDelta.y * m_fRotationScaler; +} + + +//-------------------------------------------------------------------------------------- +// Figure out the velocity based on keyboard input & drag if any +//-------------------------------------------------------------------------------------- +void CBaseCamera::UpdateVelocity( _In_ float fElapsedTime ) +{ + XMVECTOR vGamePadRightThumb = XMVectorSet( m_vGamePadRightThumb.x, -m_vGamePadRightThumb.z, 0, 0 ); + + XMVECTOR vMouseDelta = XMLoadFloat2( &m_vMouseDelta ); + XMVECTOR vRotVelocity = vMouseDelta * m_fRotationScaler + vGamePadRightThumb * 0.02f; + + XMStoreFloat2( &m_vRotVelocity, vRotVelocity ); + + XMVECTOR vKeyboardDirection = XMLoadFloat3( &m_vKeyboardDirection ); + XMVECTOR vGamePadLeftThumb = XMLoadFloat3( &m_vGamePadLeftThumb ); + XMVECTOR vAccel = vKeyboardDirection + vGamePadLeftThumb; + + // Normalize vector so if moving 2 dirs (left & forward), + // the camera doesn't move faster than if moving in 1 dir + vAccel = XMVector3Normalize( vAccel ); + + // Scale the acceleration vector + vAccel *= m_fMoveScaler; + + if( m_bMovementDrag ) + { + // Is there any acceleration this frame? + if( XMVectorGetX( XMVector3LengthSq( vAccel ) ) > 0 ) + { + // If so, then this means the user has pressed a movement key + // so change the velocity immediately to acceleration + // upon keyboard input. This isn't normal physics + // but it will give a quick response to keyboard input + XMStoreFloat3( &m_vVelocity, vAccel ); + + m_fDragTimer = m_fTotalDragTimeToZero; + + XMStoreFloat3( &m_vVelocityDrag, vAccel / m_fDragTimer ); + } + else + { + // If no key being pressed, then slowly decrease velocity to 0 + if( m_fDragTimer > 0 ) + { + // Drag until timer is <= 0 + XMVECTOR vVelocity = XMLoadFloat3( &m_vVelocity ); + XMVECTOR vVelocityDrag = XMLoadFloat3( &m_vVelocityDrag ); + + vVelocity -= vVelocityDrag * fElapsedTime; + + XMStoreFloat3( &m_vVelocity, vVelocity ); + + m_fDragTimer -= fElapsedTime; + } + else + { + // Zero velocity + m_vVelocity = XMFLOAT3( 0, 0, 0 ); + } + } + } + else + { + // No drag, so immediately change the velocity + XMStoreFloat3( &m_vVelocity, vAccel ); + } +} + + +//-------------------------------------------------------------------------------------- +// Maps a windows virtual key to an enum +//-------------------------------------------------------------------------------------- +D3DUtil_CameraKeys CBaseCamera::MapKey( _In_ UINT nKey ) +{ + // This could be upgraded to a method that's user-definable but for + // simplicity, we'll use a hardcoded mapping. + switch( nKey ) + { + case VK_CONTROL: + return CAM_CONTROLDOWN; + case VK_LEFT: + return CAM_STRAFE_LEFT; + case VK_RIGHT: + return CAM_STRAFE_RIGHT; + case VK_UP: + return CAM_MOVE_FORWARD; + case VK_DOWN: + return CAM_MOVE_BACKWARD; + case VK_PRIOR: + return CAM_MOVE_UP; // pgup + case VK_NEXT: + return CAM_MOVE_DOWN; // pgdn + + case 'A': + return CAM_STRAFE_LEFT; + case 'D': + return CAM_STRAFE_RIGHT; + case 'W': + return CAM_MOVE_FORWARD; + case 'S': + return CAM_MOVE_BACKWARD; + case 'Q': + return CAM_MOVE_DOWN; + case 'E': + return CAM_MOVE_UP; + + case VK_NUMPAD4: + return CAM_STRAFE_LEFT; + case VK_NUMPAD6: + return CAM_STRAFE_RIGHT; + case VK_NUMPAD8: + return CAM_MOVE_FORWARD; + case VK_NUMPAD2: + return CAM_MOVE_BACKWARD; + case VK_NUMPAD9: + return CAM_MOVE_UP; + case VK_NUMPAD3: + return CAM_MOVE_DOWN; + + case VK_HOME: + return CAM_RESET; + } + + return CAM_UNKNOWN; +} + + +//-------------------------------------------------------------------------------------- +// Reset the camera's position back to the default +//-------------------------------------------------------------------------------------- +void CBaseCamera::Reset() +{ + XMVECTOR vDefaultEye = XMLoadFloat3( &m_vDefaultEye ); + XMVECTOR vDefaultLookAt = XMLoadFloat3( &m_vDefaultLookAt ); + + SetViewParams( vDefaultEye, vDefaultLookAt ); +} + + +//====================================================================================== +// CFirstPersonCamera +//====================================================================================== + +CFirstPersonCamera::CFirstPersonCamera() noexcept : + m_mCameraWorld{}, + m_nActiveButtonMask( 0x07 ), + m_bRotateWithoutButtonDown(false) +{ +} + + +//-------------------------------------------------------------------------------------- +// Update the view matrix based on user input & elapsed time +//-------------------------------------------------------------------------------------- +void CFirstPersonCamera::FrameMove( _In_ float fElapsedTime ) +{ + if( DXUTGetGlobalTimer()->IsStopped() ) + { + if (DXUTGetFPS() == 0.0f) + fElapsedTime = 0; + else + fElapsedTime = 1.0f / DXUTGetFPS(); + } + + if( IsKeyDown( m_aKeys[CAM_RESET] ) ) + { + Reset(); + } + + // Get keyboard/mouse/gamepad input + GetInput( m_bEnablePositionMovement, ( m_nActiveButtonMask & m_nCurrentButtonMask ) || m_bRotateWithoutButtonDown, true ); + + //// Get the mouse movement (if any) if the mouse button are down + //if( (m_nActiveButtonMask & m_nCurrentButtonMask) || m_bRotateWithoutButtonDown ) + // UpdateMouseDelta( fElapsedTime ); + + // Get amount of velocity based on the keyboard input and drag (if any) + UpdateVelocity( fElapsedTime ); + + // Simple euler method to calculate position delta + XMVECTOR vVelocity = XMLoadFloat3( &m_vVelocity ); + XMVECTOR vPosDelta = vVelocity * fElapsedTime; + + // If rotating the camera + if( ( m_nActiveButtonMask & m_nCurrentButtonMask ) + || m_bRotateWithoutButtonDown + || m_vGamePadRightThumb.x != 0 + || m_vGamePadRightThumb.z != 0 ) + { + // Update the pitch & yaw angle based on mouse movement + float fYawDelta = m_vRotVelocity.x; + float fPitchDelta = m_vRotVelocity.y; + + // Invert pitch if requested + if( m_bInvertPitch ) + fPitchDelta = -fPitchDelta; + + m_fCameraPitchAngle += fPitchDelta; + m_fCameraYawAngle += fYawDelta; + + // Limit pitch to straight up or straight down + m_fCameraPitchAngle = std::max( -XM_PI / 2.0f, m_fCameraPitchAngle ); + m_fCameraPitchAngle = std::min( +XM_PI / 2.0f, m_fCameraPitchAngle ); + } + + // Make a rotation matrix based on the camera's yaw & pitch + XMMATRIX mCameraRot = XMMatrixRotationRollPitchYaw( m_fCameraPitchAngle, m_fCameraYawAngle, 0 ); + + // Transform vectors based on camera's rotation matrix + XMVECTOR vWorldUp = XMVector3TransformCoord( g_XMIdentityR1, mCameraRot ); + XMVECTOR vWorldAhead = XMVector3TransformCoord( g_XMIdentityR2, mCameraRot ); + + // Transform the position delta by the camera's rotation + if( !m_bEnableYAxisMovement ) + { + // If restricting Y movement, do not include pitch + // when transforming position delta vector. + mCameraRot = XMMatrixRotationRollPitchYaw( 0.0f, m_fCameraYawAngle, 0.0f ); + } + XMVECTOR vPosDeltaWorld = XMVector3TransformCoord( vPosDelta, mCameraRot ); + + // Move the eye position + XMVECTOR vEye = XMLoadFloat3( &m_vEye ); + vEye += vPosDeltaWorld; + if( m_bClipToBoundary ) + vEye = ConstrainToBoundary( vEye ); + XMStoreFloat3( &m_vEye, vEye ); + + // Update the lookAt position based on the eye position + XMVECTOR vLookAt = vEye + vWorldAhead; + XMStoreFloat3( &m_vLookAt, vLookAt ); + + // Update the view matrix + XMMATRIX mView = XMMatrixLookAtLH( vEye, vLookAt, vWorldUp ); + XMStoreFloat4x4( &m_mView, mView ); + + XMMATRIX mCameraWorld = XMMatrixInverse( nullptr, mView ); + XMStoreFloat4x4( &m_mCameraWorld, mCameraWorld ); +} + + +//-------------------------------------------------------------------------------------- +// Enable or disable each of the mouse buttons for rotation drag. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CFirstPersonCamera::SetRotateButtons( bool bLeft, bool bMiddle, bool bRight, bool bRotateWithoutButtonDown ) +{ + m_nActiveButtonMask = ( bLeft ? MOUSE_LEFT_BUTTON : 0 ) | + ( bMiddle ? MOUSE_MIDDLE_BUTTON : 0 ) | + ( bRight ? MOUSE_RIGHT_BUTTON : 0 ); + m_bRotateWithoutButtonDown = bRotateWithoutButtonDown; +} + + + +//====================================================================================== +// CModelViewerCamera +//====================================================================================== + +CModelViewerCamera::CModelViewerCamera() noexcept : + m_nRotateModelButtonMask(MOUSE_LEFT_BUTTON), + m_nZoomButtonMask(MOUSE_WHEEL), + m_nRotateCameraButtonMask(MOUSE_RIGHT_BUTTON), + m_bAttachCameraToModel(false), + m_bLimitPitch(false), + m_bDragSinceLastUpdate(true), + m_fRadius(5.0f), + m_fDefaultRadius(5.0f), + m_fMinRadius(1.0f), + m_fMaxRadius(FLT_MAX) +{ + XMMATRIX id = XMMatrixIdentity(); + + XMStoreFloat4x4( &m_mWorld, id ); + XMStoreFloat4x4( &m_mModelRot, id ); + XMStoreFloat4x4( &m_mModelLastRot, id ); + XMStoreFloat4x4( &m_mCameraRotLast, id ); + m_vModelCenter = XMFLOAT3( 0, 0, 0 ); + + m_bEnablePositionMovement = false; +} + + +//-------------------------------------------------------------------------------------- +// Update the view matrix & the model's world matrix based +// on user input & elapsed time +//-------------------------------------------------------------------------------------- +void CModelViewerCamera::FrameMove( _In_ float fElapsedTime ) +{ + if( IsKeyDown( m_aKeys[CAM_RESET] ) ) + Reset(); + + // If no dragged has happend since last time FrameMove is called, + // and no camera key is held down, then no need to handle again. + if( !m_bDragSinceLastUpdate && 0 == m_cKeysDown ) + return; + + m_bDragSinceLastUpdate = false; + + //// If no mouse button is held down, + //// Get the mouse movement (if any) if the mouse button are down + //if( m_nCurrentButtonMask != 0 ) + // UpdateMouseDelta( fElapsedTime ); + + GetInput( m_bEnablePositionMovement, m_nCurrentButtonMask != 0, true ); + + // Get amount of velocity based on the keyboard input and drag (if any) + UpdateVelocity( fElapsedTime ); + + // Simple euler method to calculate position delta + XMVECTOR vPosDelta = XMLoadFloat3( &m_vVelocity ) * fElapsedTime; + + // Change the radius from the camera to the model based on wheel scrolling + if( m_nMouseWheelDelta && m_nZoomButtonMask == MOUSE_WHEEL ) + m_fRadius -= m_nMouseWheelDelta * m_fRadius * 0.1f / 120.0f; + m_fRadius = std::min( m_fMaxRadius, m_fRadius ); + m_fRadius = std::max( m_fMinRadius, m_fRadius ); + m_nMouseWheelDelta = 0; + + // Get the inverse of the arcball's rotation matrix + XMMATRIX mCameraRot = XMMatrixInverse( nullptr, m_ViewArcBall.GetRotationMatrix() ); + + // Transform vectors based on camera's rotation matrix + XMVECTOR vWorldUp = XMVector3TransformCoord( g_XMIdentityR1, mCameraRot ); + XMVECTOR vWorldAhead = XMVector3TransformCoord( g_XMIdentityR2, mCameraRot ); + + // Transform the position delta by the camera's rotation + XMVECTOR vPosDeltaWorld = XMVector3TransformCoord( vPosDelta, mCameraRot ); + + // Move the lookAt position + XMVECTOR vLookAt = XMLoadFloat3( &m_vLookAt ); + vLookAt += vPosDeltaWorld; + if( m_bClipToBoundary ) + vLookAt = ConstrainToBoundary( vLookAt ); + XMStoreFloat3( &m_vLookAt, vLookAt ); + + // Update the eye point based on a radius away from the lookAt position + XMVECTOR vEye = vLookAt - vWorldAhead * m_fRadius; + XMStoreFloat3( &m_vEye, vEye ); + + // Update the view matrix + XMMATRIX mView = XMMatrixLookAtLH( vEye, vLookAt, vWorldUp ); + XMStoreFloat4x4( &m_mView, mView ); + + XMMATRIX mInvView = XMMatrixInverse( nullptr, mView ); + mInvView.r[3] = XMVectorSelect( mInvView.r[3], g_XMZero, g_XMSelect1110 ); + + XMMATRIX mModelLastRot = XMLoadFloat4x4( &m_mModelLastRot ); + XMMATRIX mModelLastRotInv = XMMatrixInverse( nullptr, mModelLastRot ); + + // Accumulate the delta of the arcball's rotation in view space. + // Note that per-frame delta rotations could be problematic over long periods of time. + XMMATRIX mModelRot0 = m_WorldArcBall.GetRotationMatrix(); + XMMATRIX mModelRot = XMLoadFloat4x4( &m_mModelRot ); + mModelRot *= mView * mModelLastRotInv * mModelRot0 * mInvView; + + if( m_ViewArcBall.IsBeingDragged() && m_bAttachCameraToModel && !IsKeyDown( m_aKeys[CAM_CONTROLDOWN] ) ) + { + // Attach camera to model by inverse of the model rotation + XMMATRIX mCameraRotLast = XMLoadFloat4x4( &m_mCameraRotLast ); + XMMATRIX mCameraLastRotInv = XMMatrixInverse( nullptr, mCameraRotLast ); + XMMATRIX mCameraRotDelta = mCameraLastRotInv * mCameraRot; // local to world matrix + mModelRot *= mCameraRotDelta; + } + + XMStoreFloat4x4( &m_mModelLastRot, mModelRot0 ); + XMStoreFloat4x4( &m_mCameraRotLast, mCameraRot ); + + // Since we're accumulating delta rotations, we need to orthonormalize + // the matrix to prevent eventual matrix skew + XMVECTOR xBasis = XMVector3Normalize( mModelRot.r[0] ); + XMVECTOR yBasis = XMVector3Cross( mModelRot.r[2], xBasis ); + yBasis = XMVector3Normalize( yBasis ); + XMVECTOR zBasis = XMVector3Cross( xBasis, yBasis ); + + mModelRot.r[0] = XMVectorSelect( mModelRot.r[0], xBasis, g_XMSelect1110 ); + mModelRot.r[1] = XMVectorSelect( mModelRot.r[1], yBasis, g_XMSelect1110 ); + mModelRot.r[2] = XMVectorSelect( mModelRot.r[2], zBasis, g_XMSelect1110 ); + + // Translate the rotation matrix to the same position as the lookAt position + mModelRot.r[3] = XMVectorSelect( mModelRot.r[3], vLookAt, g_XMSelect1110 ); + + XMStoreFloat4x4( &m_mModelRot, mModelRot ); + + // Translate world matrix so its at the center of the model + XMMATRIX mTrans = XMMatrixTranslation( -m_vModelCenter.x, -m_vModelCenter.y, -m_vModelCenter.z ); + XMMATRIX mWorld = mTrans * mModelRot; + XMStoreFloat4x4( &m_mWorld, mWorld ); +} + + +//-------------------------------------------------------------------------------------- +void CModelViewerCamera::SetDragRect( _In_ const RECT& rc ) +{ + CBaseCamera::SetDragRect( rc ); + + m_WorldArcBall.SetOffset( rc.left, rc.top ); + m_ViewArcBall.SetOffset( rc.left, rc.top ); + + SetWindow( rc.right - rc.left, rc.bottom - rc.top ); +} + + +//-------------------------------------------------------------------------------------- +// Reset the camera's position back to the default +//-------------------------------------------------------------------------------------- +void CModelViewerCamera::Reset() +{ + CBaseCamera::Reset(); + + XMMATRIX id = XMMatrixIdentity(); + XMStoreFloat4x4( &m_mWorld, id ); + XMStoreFloat4x4( &m_mModelRot, id ); + XMStoreFloat4x4( &m_mModelLastRot, id ); + XMStoreFloat4x4( &m_mCameraRotLast, id ); + + m_fRadius = m_fDefaultRadius; + m_WorldArcBall.Reset(); + m_ViewArcBall.Reset(); +} + + +//-------------------------------------------------------------------------------------- +// Override for setting the view parameters +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CModelViewerCamera::SetViewParams( FXMVECTOR vEyePt, FXMVECTOR vLookatPt ) +{ + CBaseCamera::SetViewParams( vEyePt, vLookatPt ); + + // Propogate changes to the member arcball + XMMATRIX mRotation = XMMatrixLookAtLH( vEyePt, vLookatPt, g_XMIdentityR1 ); + XMVECTOR quat = XMQuaternionRotationMatrix( mRotation ); + m_ViewArcBall.SetQuatNow( quat ); + + // Set the radius according to the distance + XMVECTOR vEyeToPoint = XMVectorSubtract( vLookatPt, vEyePt ); + float len = XMVectorGetX( XMVector3Length( vEyeToPoint ) ); + SetRadius( len ); + + // View information changed. FrameMove should be called. + m_bDragSinceLastUpdate = true; +} + + +//-------------------------------------------------------------------------------------- +// Call this from your message proc so this class can handle window messages +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +LRESULT CModelViewerCamera::HandleMessages( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + CBaseCamera::HandleMessages( hWnd, uMsg, wParam, lParam ); + + if( ( ( uMsg == WM_LBUTTONDOWN || uMsg == WM_LBUTTONDBLCLK ) && m_nRotateModelButtonMask & MOUSE_LEFT_BUTTON ) || + ( ( uMsg == WM_MBUTTONDOWN || uMsg == WM_MBUTTONDBLCLK ) && m_nRotateModelButtonMask & MOUSE_MIDDLE_BUTTON ) || + ( ( uMsg == WM_RBUTTONDOWN || uMsg == WM_RBUTTONDBLCLK ) && m_nRotateModelButtonMask & MOUSE_RIGHT_BUTTON ) ) + { + int iMouseX = ( short )LOWORD( lParam ); + int iMouseY = ( short )HIWORD( lParam ); + m_WorldArcBall.OnBegin( iMouseX, iMouseY ); + } + + if( ( ( uMsg == WM_LBUTTONDOWN || uMsg == WM_LBUTTONDBLCLK ) && m_nRotateCameraButtonMask & MOUSE_LEFT_BUTTON ) || + ( ( uMsg == WM_MBUTTONDOWN || uMsg == WM_MBUTTONDBLCLK ) && + m_nRotateCameraButtonMask & MOUSE_MIDDLE_BUTTON ) || + ( ( uMsg == WM_RBUTTONDOWN || uMsg == WM_RBUTTONDBLCLK ) && m_nRotateCameraButtonMask & MOUSE_RIGHT_BUTTON ) ) + { + int iMouseX = ( short )LOWORD( lParam ); + int iMouseY = ( short )HIWORD( lParam ); + m_ViewArcBall.OnBegin( iMouseX, iMouseY ); + } + + if( uMsg == WM_MOUSEMOVE ) + { + int iMouseX = ( short )LOWORD( lParam ); + int iMouseY = ( short )HIWORD( lParam ); + m_WorldArcBall.OnMove( iMouseX, iMouseY ); + m_ViewArcBall.OnMove( iMouseX, iMouseY ); + } + + if( ( uMsg == WM_LBUTTONUP && m_nRotateModelButtonMask & MOUSE_LEFT_BUTTON ) || + ( uMsg == WM_MBUTTONUP && m_nRotateModelButtonMask & MOUSE_MIDDLE_BUTTON ) || + ( uMsg == WM_RBUTTONUP && m_nRotateModelButtonMask & MOUSE_RIGHT_BUTTON ) ) + { + m_WorldArcBall.OnEnd(); + } + + if( ( uMsg == WM_LBUTTONUP && m_nRotateCameraButtonMask & MOUSE_LEFT_BUTTON ) || + ( uMsg == WM_MBUTTONUP && m_nRotateCameraButtonMask & MOUSE_MIDDLE_BUTTON ) || + ( uMsg == WM_RBUTTONUP && m_nRotateCameraButtonMask & MOUSE_RIGHT_BUTTON ) ) + { + m_ViewArcBall.OnEnd(); + } + + if( uMsg == WM_CAPTURECHANGED ) + { + if( ( HWND )lParam != hWnd ) + { + if( ( m_nRotateModelButtonMask & MOUSE_LEFT_BUTTON ) || + ( m_nRotateModelButtonMask & MOUSE_MIDDLE_BUTTON ) || + ( m_nRotateModelButtonMask & MOUSE_RIGHT_BUTTON ) ) + { + m_WorldArcBall.OnEnd(); + } + + if( ( m_nRotateCameraButtonMask & MOUSE_LEFT_BUTTON ) || + ( m_nRotateCameraButtonMask & MOUSE_MIDDLE_BUTTON ) || + ( m_nRotateCameraButtonMask & MOUSE_RIGHT_BUTTON ) ) + { + m_ViewArcBall.OnEnd(); + } + } + } + + if( uMsg == WM_LBUTTONDOWN || + uMsg == WM_LBUTTONDBLCLK || + uMsg == WM_MBUTTONDOWN || + uMsg == WM_MBUTTONDBLCLK || + uMsg == WM_RBUTTONDOWN || + uMsg == WM_RBUTTONDBLCLK || + uMsg == WM_LBUTTONUP || + uMsg == WM_MBUTTONUP || + uMsg == WM_RBUTTONUP || + uMsg == WM_MOUSEWHEEL || + uMsg == WM_MOUSEMOVE ) + { + m_bDragSinceLastUpdate = true; + } + + return FALSE; +} + + +//====================================================================================== +// CDXUTDirectionWidget +//====================================================================================== + +CDXUTDirectionWidget::CDXUTDirectionWidget() noexcept : + m_fRadius(1.0f), + m_nRotateMask(MOUSE_RIGHT_BUTTON) +{ + m_vDefaultDir = XMFLOAT3( 0, 1, 0 ); + m_vCurrentDir = m_vDefaultDir; + + XMMATRIX id = XMMatrixIdentity(); + + XMStoreFloat4x4( &m_mView, id ); + XMStoreFloat4x4( &m_mRot, id ); + XMStoreFloat4x4( &m_mRotSnapshot, id ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +LRESULT CDXUTDirectionWidget::HandleMessages( HWND hWnd, UINT uMsg, + WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(wParam); + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_MBUTTONDOWN: + case WM_RBUTTONDOWN: + { + if( ( ( m_nRotateMask & MOUSE_LEFT_BUTTON ) != 0 && uMsg == WM_LBUTTONDOWN ) || + ( ( m_nRotateMask & MOUSE_MIDDLE_BUTTON ) != 0 && uMsg == WM_MBUTTONDOWN ) || + ( ( m_nRotateMask & MOUSE_RIGHT_BUTTON ) != 0 && uMsg == WM_RBUTTONDOWN ) ) + { + int iMouseX = ( int )( short )LOWORD( lParam ); + int iMouseY = ( int )( short )HIWORD( lParam ); + m_ArcBall.OnBegin( iMouseX, iMouseY ); + SetCapture( hWnd ); + } + return TRUE; + } + + case WM_MOUSEMOVE: + { + if( m_ArcBall.IsBeingDragged() ) + { + int iMouseX = ( int )( short )LOWORD( lParam ); + int iMouseY = ( int )( short )HIWORD( lParam ); + m_ArcBall.OnMove( iMouseX, iMouseY ); + UpdateLightDir(); + } + return TRUE; + } + + case WM_LBUTTONUP: + case WM_MBUTTONUP: + case WM_RBUTTONUP: + { + if( ( ( m_nRotateMask & MOUSE_LEFT_BUTTON ) != 0 && uMsg == WM_LBUTTONUP ) || + ( ( m_nRotateMask & MOUSE_MIDDLE_BUTTON ) != 0 && uMsg == WM_MBUTTONUP ) || + ( ( m_nRotateMask & MOUSE_RIGHT_BUTTON ) != 0 && uMsg == WM_RBUTTONUP ) ) + { + m_ArcBall.OnEnd(); + ReleaseCapture(); + } + + UpdateLightDir(); + return TRUE; + } + + case WM_CAPTURECHANGED: + { + if( ( HWND )lParam != hWnd ) + { + if( ( m_nRotateMask & MOUSE_LEFT_BUTTON ) || + ( m_nRotateMask & MOUSE_MIDDLE_BUTTON ) || + ( m_nRotateMask & MOUSE_RIGHT_BUTTON ) ) + { + m_ArcBall.OnEnd(); + ReleaseCapture(); + } + } + return TRUE; + } + } + + return 0; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTDirectionWidget::UpdateLightDir() +{ + XMMATRIX mView = XMLoadFloat4x4( &m_mView ); + + XMMATRIX mInvView = XMMatrixInverse( nullptr, mView ); + mInvView.r[3] = XMVectorSelect( mInvView.r[3], g_XMZero, g_XMSelect1110 ); + + XMMATRIX mRotSnapshot = XMLoadFloat4x4( &m_mRotSnapshot ); + XMMATRIX mLastRotInv = XMMatrixInverse( nullptr, mRotSnapshot ); + + XMMATRIX mRot0 = m_ArcBall.GetRotationMatrix(); + XMStoreFloat4x4( &m_mRotSnapshot, mRot0 ); + + // Accumulate the delta of the arcball's rotation in view space. + // Note that per-frame delta rotations could be problematic over long periods of time. + XMMATRIX mRot = XMLoadFloat4x4( &m_mRot ); + mRot *= mView * mLastRotInv * mRot0 * mInvView; + + // Since we're accumulating delta rotations, we need to orthonormalize + // the matrix to prevent eventual matrix skew + XMVECTOR xBasis = XMVector3Normalize( mRot.r[0] ); + XMVECTOR yBasis = XMVector3Cross( mRot.r[2], xBasis ); + yBasis = XMVector3Normalize( yBasis ); + XMVECTOR zBasis = XMVector3Cross( xBasis, yBasis ); + mRot.r[0] = XMVectorSelect( mRot.r[0], xBasis, g_XMSelect1110 ); + mRot.r[1] = XMVectorSelect( mRot.r[1], yBasis, g_XMSelect1110 ); + mRot.r[2] = XMVectorSelect( mRot.r[2], zBasis, g_XMSelect1110 ); + XMStoreFloat4x4( &m_mRot, mRot ); + + // Transform the default direction vector by the light's rotation matrix + XMVECTOR vDefaultDir = XMLoadFloat3( &m_vDefaultDir ); + XMVECTOR vCurrentDir = XMVector3TransformNormal( vDefaultDir, mRot ); + XMStoreFloat3( &m_vCurrentDir, vCurrentDir ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDirectionWidget::OnRender( FXMVECTOR color, CXMMATRIX mView, CXMMATRIX mProj, FXMVECTOR vEyePt ) +{ + UNREFERENCED_PARAMETER(color); + UNREFERENCED_PARAMETER(mView); + UNREFERENCED_PARAMETER(mProj); + UNREFERENCED_PARAMETER(vEyePt); + // TODO - + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDirectionWidget::StaticOnD3D11CreateDevice( ID3D11Device* pd3dDevice, ID3D11DeviceContext* pd3dImmediateContext ) +{ + UNREFERENCED_PARAMETER(pd3dDevice); + UNREFERENCED_PARAMETER(pd3dImmediateContext); + // TODO - + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDirectionWidget::StaticOnD3D11DestroyDevice() +{ + // TODO - +} diff --git a/src/DX11/framework/dxut/Optional/DXUTcamera.h b/src/DX11/framework/dxut/Optional/DXUTcamera.h new file mode 100644 index 0000000..7fff849 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTcamera.h @@ -0,0 +1,424 @@ +//-------------------------------------------------------------------------------------- +// File: Camera.h +// +// Helper functions for Direct3D programming. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +//-------------------------------------------------------------------------------------- +class CD3DArcBall +{ +public: + CD3DArcBall() noexcept; + + // Functions to change behavior + void Reset(); + void SetTranslationRadius( _In_ float fRadiusTranslation ) + { + m_fRadiusTranslation = fRadiusTranslation; + } + void SetWindow( _In_ INT nWidth, _In_ INT nHeight, _In_ float fRadius = 0.9f ) + { + m_nWidth = nWidth; + m_nHeight = nHeight; + m_fRadius = fRadius; + m_vCenter.x = float(m_nWidth) / 2.0f; + m_vCenter.y = float(m_nHeight) / 2.0f; + } + void SetOffset( _In_ INT nX, _In_ INT nY ) { m_Offset.x = nX; m_Offset.y = nY; } + + // Call these from client and use GetRotationMatrix() to read new rotation matrix + void OnBegin( _In_ int nX, _In_ int nY ); // start the rotation (pass current mouse position) + void OnMove( _In_ int nX, _In_ int nY ); // continue the rotation (pass current mouse position) + void OnEnd(); // end the rotation + + // Or call this to automatically handle left, middle, right buttons + LRESULT HandleMessages( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); + + // Functions to get/set state + DirectX::XMMATRIX GetRotationMatrix() const + { + using namespace DirectX; + XMVECTOR q = XMLoadFloat4( &m_qNow ); + return DirectX::XMMatrixRotationQuaternion( q ); + } + DirectX::XMMATRIX GetTranslationMatrix() const { return DirectX::XMLoadFloat4x4( &m_mTranslation ); } + DirectX::XMMATRIX GetTranslationDeltaMatrix() const { return DirectX::XMLoadFloat4x4( &m_mTranslationDelta ); } + bool IsBeingDragged() const { return m_bDrag; } + DirectX::XMVECTOR GetQuatNow() const { return DirectX::XMLoadFloat4( &m_qNow ); } + void SetQuatNow( _In_ DirectX::FXMVECTOR& q ) { DirectX::XMStoreFloat4( &m_qNow, q ); } + + static DirectX::XMVECTOR QuatFromBallPoints( _In_ DirectX::FXMVECTOR vFrom, _In_ DirectX::FXMVECTOR vTo ) + { + using namespace DirectX; + + XMVECTOR dot = XMVector3Dot( vFrom, vTo ); + XMVECTOR vPart = XMVector3Cross( vFrom, vTo ); + return XMVectorSelect( dot, vPart, g_XMSelect1110 ); + } + +protected: + DirectX::XMFLOAT4X4 m_mRotation; // Matrix for arc ball's orientation + DirectX::XMFLOAT4X4 m_mTranslation; // Matrix for arc ball's position + DirectX::XMFLOAT4X4 m_mTranslationDelta;// Matrix for arc ball's position + + POINT m_Offset; // window offset, or upper-left corner of window + INT m_nWidth; // arc ball's window width + INT m_nHeight; // arc ball's window height + DirectX::XMFLOAT2 m_vCenter; // center of arc ball + float m_fRadius; // arc ball's radius in screen coords + float m_fRadiusTranslation; // arc ball's radius for translating the target + + DirectX::XMFLOAT4 m_qDown; // Quaternion before button down + DirectX::XMFLOAT4 m_qNow; // Composite quaternion for current drag + bool m_bDrag; // Whether user is dragging arc ball + + POINT m_ptLastMouse; // position of last mouse point + DirectX::XMFLOAT3 m_vDownPt; // starting point of rotation arc + DirectX::XMFLOAT3 m_vCurrentPt; // current point of rotation arc + + DirectX::XMVECTOR ScreenToVector( _In_ float fScreenPtX, _In_ float fScreenPtY ) + { + // Scale to screen + float x = -( fScreenPtX - m_Offset.x - m_nWidth / 2 ) / ( m_fRadius * m_nWidth / 2 ); + float y = ( fScreenPtY - m_Offset.y - m_nHeight / 2 ) / ( m_fRadius * m_nHeight / 2 ); + + float z = 0.0f; + float mag = x * x + y * y; + + if( mag > 1.0f ) + { + float scale = 1.0f / sqrtf( mag ); + x *= scale; + y *= scale; + } + else + z = sqrtf( 1.0f - mag ); + + return DirectX::XMVectorSet( x, y, z, 0 ); + } +}; + + +//-------------------------------------------------------------------------------------- +// used by CCamera to map WM_KEYDOWN keys +//-------------------------------------------------------------------------------------- +enum D3DUtil_CameraKeys +{ + CAM_STRAFE_LEFT = 0, + CAM_STRAFE_RIGHT, + CAM_MOVE_FORWARD, + CAM_MOVE_BACKWARD, + CAM_MOVE_UP, + CAM_MOVE_DOWN, + CAM_RESET, + CAM_CONTROLDOWN, + CAM_MAX_KEYS, + CAM_UNKNOWN = 0xFF +}; + +#define KEY_WAS_DOWN_MASK 0x80 +#define KEY_IS_DOWN_MASK 0x01 + +#define MOUSE_LEFT_BUTTON 0x01 +#define MOUSE_MIDDLE_BUTTON 0x02 +#define MOUSE_RIGHT_BUTTON 0x04 +#define MOUSE_WHEEL 0x08 + + +//-------------------------------------------------------------------------------------- +// Simple base camera class that moves and rotates. The base class +// records mouse and keyboard input for use by a derived class, and +// keeps common state. +//-------------------------------------------------------------------------------------- +class CBaseCamera +{ +public: + CBaseCamera() noexcept; + + // Call these from client and use Get*Matrix() to read new matrices + virtual LRESULT HandleMessages( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); + virtual void FrameMove( _In_ float fElapsedTime ) = 0; + + // Functions to change camera matrices + virtual void Reset(); + virtual void SetViewParams( _In_ DirectX::FXMVECTOR vEyePt, _In_ DirectX::FXMVECTOR vLookatPt ); + virtual void SetProjParams( _In_ float fFOV, _In_ float fAspect, _In_ float fNearPlane, _In_ float fFarPlane ); + + // Functions to change behavior + virtual void SetDragRect( _In_ const RECT& rc ) { m_rcDrag = rc; } + void SetInvertPitch( _In_ bool bInvertPitch ) { m_bInvertPitch = bInvertPitch; } + void SetDrag( _In_ bool bMovementDrag, _In_ float fTotalDragTimeToZero = 0.25f ) + { + m_bMovementDrag = bMovementDrag; + m_fTotalDragTimeToZero = fTotalDragTimeToZero; + } + void SetEnableYAxisMovement( _In_ bool bEnableYAxisMovement ) { m_bEnableYAxisMovement = bEnableYAxisMovement; } + void SetEnablePositionMovement( _In_ bool bEnablePositionMovement ) { m_bEnablePositionMovement = bEnablePositionMovement; } + void SetClipToBoundary( _In_ bool bClipToBoundary, _In_opt_ DirectX::XMFLOAT3* pvMinBoundary, _In_opt_ DirectX::XMFLOAT3* pvMaxBoundary ) + { + m_bClipToBoundary = bClipToBoundary; + if( pvMinBoundary ) m_vMinBoundary = *pvMinBoundary; + if( pvMaxBoundary ) m_vMaxBoundary = *pvMaxBoundary; + } + void SetScalers( _In_ float fRotationScaler = 0.01f, _In_ float fMoveScaler = 5.0f ) + { + m_fRotationScaler = fRotationScaler; + m_fMoveScaler = fMoveScaler; + } + void SetNumberOfFramesToSmoothMouseData( _In_ int nFrames ) { if( nFrames > 0 ) m_fFramesToSmoothMouseData = ( float )nFrames; } + void SetResetCursorAfterMove( _In_ bool bResetCursorAfterMove ) { m_bResetCursorAfterMove = bResetCursorAfterMove; } + + // Functions to get state + DirectX::XMMATRIX GetViewMatrix() const { return DirectX::XMLoadFloat4x4( &m_mView ); } + DirectX::XMMATRIX GetProjMatrix() const { return DirectX::XMLoadFloat4x4( &m_mProj ); } + DirectX::XMVECTOR GetEyePt() const { return DirectX::XMLoadFloat3( &m_vEye ); } + DirectX::XMVECTOR GetLookAtPt() const { return DirectX::XMLoadFloat3( &m_vLookAt ); } + float GetNearClip() const { return m_fNearPlane; } + float GetFarClip() const { return m_fFarPlane; } + float GetFOV() const { return m_fFOV; } + float GetAspect() const { return m_fAspect; } + + bool IsBeingDragged() const { return ( m_bMouseLButtonDown || m_bMouseMButtonDown || m_bMouseRButtonDown ); } + bool IsMouseLButtonDown() const { return m_bMouseLButtonDown; } + bool IsMouseMButtonDown() const { return m_bMouseMButtonDown; } + bool sMouseRButtonDown() const { return m_bMouseRButtonDown; } + +protected: + // Functions to map a WM_KEYDOWN key to a D3DUtil_CameraKeys enum + virtual D3DUtil_CameraKeys MapKey( _In_ UINT nKey ); + + bool IsKeyDown( _In_ BYTE key ) const { return( ( key & KEY_IS_DOWN_MASK ) == KEY_IS_DOWN_MASK ); } + bool WasKeyDown( _In_ BYTE key ) const { return( ( key & KEY_WAS_DOWN_MASK ) == KEY_WAS_DOWN_MASK ); } + + DirectX::XMVECTOR ConstrainToBoundary( _In_ DirectX::FXMVECTOR v ) + { + using namespace DirectX; + + XMVECTOR vMin = XMLoadFloat3( &m_vMinBoundary ); + XMVECTOR vMax = XMLoadFloat3( &m_vMaxBoundary ); + + // Constrain vector to a bounding box + return XMVectorClamp( v, vMin, vMax ); + } + + void UpdateMouseDelta(); + void UpdateVelocity( _In_ float fElapsedTime ); + void GetInput( _In_ bool bGetKeyboardInput, _In_ bool bGetMouseInput, _In_ bool bGetGamepadInput ); + + DirectX::XMFLOAT4X4 m_mView; // View matrix + DirectX::XMFLOAT4X4 m_mProj; // Projection matrix + + DXUT_GAMEPAD m_GamePad[DXUT_MAX_CONTROLLERS]; // XInput controller state + DirectX::XMFLOAT3 m_vGamePadLeftThumb; + DirectX::XMFLOAT3 m_vGamePadRightThumb; + double m_GamePadLastActive[DXUT_MAX_CONTROLLERS]; + + int m_cKeysDown; // Number of camera keys that are down. + BYTE m_aKeys[CAM_MAX_KEYS]; // State of input - KEY_WAS_DOWN_MASK|KEY_IS_DOWN_MASK + DirectX::XMFLOAT3 m_vKeyboardDirection; // Direction vector of keyboard input + POINT m_ptLastMousePosition; // Last absolute position of mouse cursor + int m_nCurrentButtonMask; // mask of which buttons are down + int m_nMouseWheelDelta; // Amount of middle wheel scroll (+/-) + DirectX::XMFLOAT2 m_vMouseDelta; // Mouse relative delta smoothed over a few frames + float m_fFramesToSmoothMouseData; // Number of frames to smooth mouse data over + DirectX::XMFLOAT3 m_vDefaultEye; // Default camera eye position + DirectX::XMFLOAT3 m_vDefaultLookAt; // Default LookAt position + DirectX::XMFLOAT3 m_vEye; // Camera eye position + DirectX::XMFLOAT3 m_vLookAt; // LookAt position + float m_fCameraYawAngle; // Yaw angle of camera + float m_fCameraPitchAngle; // Pitch angle of camera + + RECT m_rcDrag; // Rectangle within which a drag can be initiated. + DirectX::XMFLOAT3 m_vVelocity; // Velocity of camera + DirectX::XMFLOAT3 m_vVelocityDrag; // Velocity drag force + float m_fDragTimer; // Countdown timer to apply drag + float m_fTotalDragTimeToZero; // Time it takes for velocity to go from full to 0 + DirectX::XMFLOAT2 m_vRotVelocity; // Velocity of camera + + float m_fFOV; // Field of view + float m_fAspect; // Aspect ratio + float m_fNearPlane; // Near plane + float m_fFarPlane; // Far plane + + float m_fRotationScaler; // Scaler for rotation + float m_fMoveScaler; // Scaler for movement + + bool m_bMouseLButtonDown; // True if left button is down + bool m_bMouseMButtonDown; // True if middle button is down + bool m_bMouseRButtonDown; // True if right button is down + bool m_bMovementDrag; // If true, then camera movement will slow to a stop otherwise movement is instant + bool m_bInvertPitch; // Invert the pitch axis + bool m_bEnablePositionMovement; // If true, then the user can translate the camera/model + bool m_bEnableYAxisMovement; // If true, then camera can move in the y-axis + bool m_bClipToBoundary; // If true, then the camera will be clipped to the boundary + bool m_bResetCursorAfterMove; // If true, the class will reset the cursor position so that the cursor always has space to move + + DirectX::XMFLOAT3 m_vMinBoundary; // Min point in clip boundary + DirectX::XMFLOAT3 m_vMaxBoundary; // Max point in clip boundary +}; + + +//-------------------------------------------------------------------------------------- +// Simple first person camera class that moves and rotates. +// It allows yaw and pitch but not roll. It uses WM_KEYDOWN and +// GetCursorPos() to respond to keyboard and mouse input and updates the +// view matrix based on input. +//-------------------------------------------------------------------------------------- +class CFirstPersonCamera : public CBaseCamera +{ +public: + CFirstPersonCamera() noexcept; + + // Call these from client and use Get*Matrix() to read new matrices + virtual void FrameMove( _In_ float fElapsedTime ) override; + + // Functions to change behavior + void SetRotateButtons( _In_ bool bLeft, _In_ bool bMiddle, _In_ bool bRight, _In_ bool bRotateWithoutButtonDown = false ); + + // Functions to get state + DirectX::XMMATRIX GetWorldMatrix() const { return DirectX::XMLoadFloat4x4( &m_mCameraWorld ); } + + DirectX::XMVECTOR GetWorldRight() const { return DirectX::XMLoadFloat3( reinterpret_cast( &m_mCameraWorld._11 ) ); } + DirectX::XMVECTOR GetWorldUp() const { return DirectX::XMLoadFloat3( reinterpret_cast( &m_mCameraWorld._21 ) ); } + DirectX::XMVECTOR GetWorldAhead() const { return DirectX::XMLoadFloat3( reinterpret_cast( &m_mCameraWorld._31 ) ); } + DirectX::XMVECTOR GetEyePt() const { return DirectX::XMLoadFloat3( reinterpret_cast( &m_mCameraWorld._41 ) ); } + +protected: + DirectX::XMFLOAT4X4 m_mCameraWorld; // World matrix of the camera (inverse of the view matrix) + + int m_nActiveButtonMask; // Mask to determine which button to enable for rotation + bool m_bRotateWithoutButtonDown; +}; + + +//-------------------------------------------------------------------------------------- +// Simple model viewing camera class that rotates around the object. +//-------------------------------------------------------------------------------------- +class CModelViewerCamera : public CBaseCamera +{ +public: + CModelViewerCamera() noexcept; + + // Call these from client and use Get*Matrix() to read new matrices + virtual LRESULT HandleMessages( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual void FrameMove( _In_ float fElapsedTime ) override; + + // Functions to change behavior + virtual void SetDragRect( _In_ const RECT& rc ) override; + virtual void Reset() override; + virtual void SetViewParams( _In_ DirectX::FXMVECTOR pvEyePt, _In_ DirectX::FXMVECTOR pvLookatPt ) override; + void SetButtonMasks( _In_ int nRotateModelButtonMask = MOUSE_LEFT_BUTTON, _In_ int nZoomButtonMask = MOUSE_WHEEL, + _In_ int nRotateCameraButtonMask = MOUSE_RIGHT_BUTTON ) + { + m_nRotateModelButtonMask = nRotateModelButtonMask, m_nZoomButtonMask = nZoomButtonMask; + m_nRotateCameraButtonMask = nRotateCameraButtonMask; + } + void SetAttachCameraToModel( _In_ bool bEnable = false ) { m_bAttachCameraToModel = bEnable; } + void SetWindow( _In_ int nWidth, _In_ int nHeight, _In_ float fArcballRadius=0.9f ) + { + m_WorldArcBall.SetWindow( nWidth, nHeight, fArcballRadius ); + m_ViewArcBall.SetWindow( nWidth, nHeight, fArcballRadius ); + } + void SetRadius( _In_ float fDefaultRadius=5.0f, _In_ float fMinRadius=1.0f, _In_ float fMaxRadius=FLT_MAX ) + { + m_fDefaultRadius = m_fRadius = fDefaultRadius; m_fMinRadius = fMinRadius; m_fMaxRadius = fMaxRadius; + m_bDragSinceLastUpdate = true; + } + void SetModelCenter( _In_ const DirectX::XMFLOAT3& vModelCenter ) { m_vModelCenter = vModelCenter; } + void SetLimitPitch( _In_ bool bLimitPitch ) { m_bLimitPitch = bLimitPitch; } + void SetViewQuat( _In_ DirectX::FXMVECTOR q ) + { + m_ViewArcBall.SetQuatNow( q ); + m_bDragSinceLastUpdate = true; + } + void SetWorldQuat( _In_ DirectX::FXMVECTOR q ) + { + m_WorldArcBall.SetQuatNow( q ); + m_bDragSinceLastUpdate = true; + } + + // Functions to get state + DirectX::XMMATRIX GetWorldMatrix() const { return DirectX::XMLoadFloat4x4( &m_mWorld ); } + void SetWorldMatrix( _In_ DirectX::CXMMATRIX mWorld ) + { + XMStoreFloat4x4( &m_mWorld, mWorld ); + m_bDragSinceLastUpdate = true; + } + +protected: + CD3DArcBall m_WorldArcBall; + CD3DArcBall m_ViewArcBall; + DirectX::XMFLOAT3 m_vModelCenter; + DirectX::XMFLOAT4X4 m_mModelLastRot; // Last arcball rotation matrix for model + DirectX::XMFLOAT4X4 m_mModelRot; // Rotation matrix of model + DirectX::XMFLOAT4X4 m_mWorld; // World matrix of model + + int m_nRotateModelButtonMask; + int m_nZoomButtonMask; + int m_nRotateCameraButtonMask; + + bool m_bAttachCameraToModel; + bool m_bLimitPitch; + bool m_bDragSinceLastUpdate; // True if mouse drag has happened since last time FrameMove is called. + float m_fRadius; // Distance from the camera to model + float m_fDefaultRadius; // Distance from the camera to model + float m_fMinRadius; // Min radius + float m_fMaxRadius; // Max radius + + DirectX::XMFLOAT4X4 m_mCameraRotLast; +}; + + +//-------------------------------------------------------------------------------------- +// Manages the mesh, direction, mouse events of a directional arrow that +// rotates around a radius controlled by an arcball +//-------------------------------------------------------------------------------------- +class CDXUTDirectionWidget +{ +public: + CDXUTDirectionWidget() noexcept; + + LRESULT HandleMessages( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); + + HRESULT OnRender( _In_ DirectX::FXMVECTOR color, _In_ DirectX::CXMMATRIX pmView, _In_ DirectX::CXMMATRIX pmProj, _In_ DirectX::FXMVECTOR vEyePt ); + + DirectX::XMVECTOR GetLightDirection() const { return DirectX::XMLoadFloat3( &m_vCurrentDir ); } + void SetLightDirection( _In_ DirectX::FXMVECTOR vDir ) + { + DirectX::XMStoreFloat3( &m_vCurrentDir, vDir ); + m_vDefaultDir = m_vCurrentDir; + } + void SetLightDirection( _In_ DirectX::XMFLOAT3 vDir ) + { + m_vDefaultDir = m_vCurrentDir = vDir; + } + void SetButtonMask( _In_ int nRotate = MOUSE_RIGHT_BUTTON ) { m_nRotateMask = nRotate; } + + float GetRadius() const { return m_fRadius; } + void SetRadius( _In_ float fRadius ) { m_fRadius = fRadius; } + + bool IsBeingDragged() { return m_ArcBall.IsBeingDragged(); } + + static HRESULT WINAPI StaticOnD3D11CreateDevice( _In_ ID3D11Device* pd3dDevice, _In_ ID3D11DeviceContext* pd3dImmediateContext ); + static void WINAPI StaticOnD3D11DestroyDevice(); + +protected: + HRESULT UpdateLightDir(); + + // TODO - need support for Direct3D 11 widget + + DirectX::XMFLOAT4X4 m_mRot; + DirectX::XMFLOAT4X4 m_mRotSnapshot; + float m_fRadius; + int m_nRotateMask; + CD3DArcBall m_ArcBall; + DirectX::XMFLOAT3 m_vDefaultDir; + DirectX::XMFLOAT3 m_vCurrentDir; + DirectX::XMFLOAT4X4 m_mView; +}; diff --git a/src/DX11/framework/dxut/Optional/DXUTgui.cpp b/src/DX11/framework/dxut/Optional/DXUTgui.cpp new file mode 100644 index 0000000..5fb4deb --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTgui.cpp @@ -0,0 +1,6683 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTgui.cpp +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "DXUT.h" +#include "DXUTgui.h" +#include "DXUTsettingsDlg.h" +#include "DXUTres.h" + +#include "SDKMisc.h" + +#include "DDSTextureLoader.h" + +using namespace DirectX; + +#ifndef WM_XBUTTONDOWN +#define WM_XBUTTONDOWN 0x020B // (not always defined) +#endif +#ifndef WM_XBUTTONUP +#define WM_XBUTTONUP 0x020C // (not always defined) +#endif +#ifndef WM_MOUSEWHEEL +#define WM_MOUSEWHEEL 0x020A // (not always defined) +#endif +#ifndef WHEEL_DELTA +#define WHEEL_DELTA 120 // (not always defined) +#endif + +// Minimum scroll bar thumb size +#define SCROLLBAR_MINTHUMBSIZE 8 + +// Delay and repeat period when clicking on the scroll bar arrows +#define SCROLLBAR_ARROWCLICK_DELAY 0.33 +#define SCROLLBAR_ARROWCLICK_REPEAT 0.05 + +#define DXUT_NEAR_BUTTON_DEPTH 0.6f +#define DXUT_FAR_BUTTON_DEPTH 0.8f + +#define DXUT_MAX_GUI_SPRITES 500 + +inline XMFLOAT4 D3DCOLOR_TO_D3DCOLORVALUE( DWORD c ) +{ + return XMFLOAT4 ( ( ( c >> 16 ) & 0xFF ) / 255.0f, + ( ( c >> 8 ) & 0xFF ) / 255.0f, + ( c & 0xFF ) / 255.0f, + ( ( c >> 24 ) & 0xFF ) / 255.0f ); +} + +#define IMM32_DLLNAME L"imm32.dll" +#define VER_DLLNAME L"version.dll" + +CHAR g_strUIEffectFile[] = \ + "Texture2D g_Texture;"\ + ""\ + "SamplerState Sampler"\ + "{"\ + " Filter = MIN_MAG_MIP_LINEAR;"\ + " AddressU = Wrap;"\ + " AddressV = Wrap;"\ + "};"\ + ""\ + "BlendState UIBlend"\ + "{"\ + " AlphaToCoverageEnable = FALSE;"\ + " BlendEnable[0] = TRUE;"\ + " SrcBlend = SRC_ALPHA;"\ + " DestBlend = INV_SRC_ALPHA;"\ + " BlendOp = ADD;"\ + " SrcBlendAlpha = ONE;"\ + " DestBlendAlpha = ZERO;"\ + " BlendOpAlpha = ADD;"\ + " RenderTargetWriteMask[0] = 0x0F;"\ + "};"\ + ""\ + "BlendState NoBlending"\ + "{"\ + " BlendEnable[0] = FALSE;"\ + " RenderTargetWriteMask[0] = 0x0F;"\ + "};"\ + ""\ + "DepthStencilState DisableDepth"\ + "{"\ + " DepthEnable = false;"\ + "};"\ + "DepthStencilState EnableDepth"\ + "{"\ + " DepthEnable = true;"\ + "};"\ + "struct VS_OUTPUT"\ + "{"\ + " float4 Pos : POSITION;"\ + " float4 Dif : COLOR;"\ + " float2 Tex : TEXCOORD;"\ + "};"\ + ""\ + "VS_OUTPUT VS( float3 vPos : POSITION,"\ + " float4 Dif : COLOR,"\ + " float2 vTexCoord0 : TEXCOORD )"\ + "{"\ + " VS_OUTPUT Output;"\ + ""\ + " Output.Pos = float4( vPos, 1.0f );"\ + " Output.Dif = Dif;"\ + " Output.Tex = vTexCoord0;"\ + ""\ + " return Output;"\ + "}"\ + ""\ + "float4 PS( VS_OUTPUT In ) : SV_Target"\ + "{"\ + " return g_Texture.Sample( Sampler, In.Tex ) * In.Dif;"\ + "}"\ + ""\ + "float4 PSUntex( VS_OUTPUT In ) : SV_Target"\ + "{"\ + " return In.Dif;"\ + "}"\ + ""\ + "technique10 RenderUI"\ + "{"\ + " pass P0"\ + " {"\ + " SetVertexShader( CompileShader( vs_4_0, VS() ) );"\ + " SetGeometryShader( NULL );"\ + " SetPixelShader( CompileShader( ps_4_0, PS() ) );"\ + " SetDepthStencilState( DisableDepth, 0 );"\ + " SetBlendState( UIBlend, float4( 0.0f, 0.0f, 0.0f, 0.0f ), 0xFFFFFFFF );"\ + " }"\ + "}"\ + "technique10 RenderUIUntex"\ + "{"\ + " pass P0"\ + " {"\ + " SetVertexShader( CompileShader( vs_4_0, VS() ) );"\ + " SetGeometryShader( NULL );"\ + " SetPixelShader( CompileShader( ps_4_0, PSUntex() ) );"\ + " SetDepthStencilState( DisableDepth, 0 );"\ + " SetBlendState( UIBlend, float4( 0.0f, 0.0f, 0.0f, 0.0f ), 0xFFFFFFFF );"\ + " }"\ + "}"\ + "technique10 RestoreState"\ + "{"\ + " pass P0"\ + " {"\ + " SetDepthStencilState( EnableDepth, 0 );"\ + " SetBlendState( NoBlending, float4( 0.0f, 0.0f, 0.0f, 0.0f ), 0xFFFFFFFF );"\ + " }"\ + "}"; +const UINT g_uUIEffectFileSize = sizeof( g_strUIEffectFile ); + + +// DXUT_MAX_EDITBOXLENGTH is the maximum string length allowed in edit boxes, +// including the nul terminator. +// +// Uniscribe does not support strings having bigger-than-16-bits length. +// This means that the string must be less than 65536 characters long, +// including the nul terminator. +#define DXUT_MAX_EDITBOXLENGTH 0xFFFF + + +double CDXUTDialog::s_fTimeRefresh = 0.0f; +CDXUTControl* CDXUTDialog::s_pControlFocus = nullptr; // The control which has focus +CDXUTControl* CDXUTDialog::s_pControlPressed = nullptr; // The control currently pressed + + +struct DXUT_SCREEN_VERTEX +{ + float x, y, z, h; + DWORD color; + float tu, tv; +}; + +struct DXUT_SCREEN_VERTEX_UNTEX +{ + float x, y, z, h; + DWORD color; +}; + +struct DXUT_SCREEN_VERTEX_10 +{ + float x, y, z; + XMFLOAT4 color; + float tu, tv; +}; + + +inline int RectWidth( RECT& rc ) +{ + return ( ( rc ).right - ( rc ).left ); +} +inline int RectHeight( RECT& rc ) +{ + return ( ( rc ).bottom - ( rc ).top ); +} + + +//====================================================================================== +// Font11 +//====================================================================================== + +ID3D11Buffer* g_pFontBuffer11 = nullptr; +UINT g_FontBufferBytes11 = 0; +std::vector g_FontVertices; +ID3D11ShaderResourceView* g_pFont11 = nullptr; +ID3D11InputLayout* g_pInputLayout11 = nullptr; + +//-------------------------------------------------------------------------------------- +HRESULT InitFont11( _In_ ID3D11Device* pd3d11Device, _In_ ID3D11InputLayout* pInputLayout ) +{ + HRESULT hr = S_OK; + WCHAR str[MAX_PATH]; + V_RETURN( DXUTFindDXSDKMediaFileCch( str, MAX_PATH, L"dx11\\UI\\Font.dds" ) ); + + V_RETURN( CreateDDSTextureFromFile( pd3d11Device, str, nullptr, &g_pFont11 ) ); + + g_pInputLayout11 = pInputLayout; + return hr; +} + + +//-------------------------------------------------------------------------------------- +void EndFont11() +{ + SAFE_RELEASE( g_pFontBuffer11 ); + g_FontBufferBytes11 = 0; + SAFE_RELEASE( g_pFont11 ); +} + + +//-------------------------------------------------------------------------------------- +void BeginText11() +{ + g_FontVertices.clear(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DrawText11DXUT( ID3D11Device* pd3dDevice, ID3D11DeviceContext* pd3d11DeviceContext, + LPCWSTR strText, const RECT& rcScreen, XMFLOAT4 vFontColor, + float fBBWidth, float fBBHeight, bool bCenter ) +{ + float fCharTexSizeX = 0.010526315f; + //float fGlyphSizeX = 14.0f / fBBWidth; + //float fGlyphSizeY = 32.0f / fBBHeight; + float fGlyphSizeX = 15.0f / fBBWidth; + float fGlyphSizeY = 42.0f / fBBHeight; + + + float fRectLeft = rcScreen.left / fBBWidth; + float fRectTop = 1.0f - rcScreen.top / fBBHeight; + + fRectLeft = fRectLeft * 2.0f - 1.0f; + fRectTop = fRectTop * 2.0f - 1.0f; + + int NumChars = (int)wcslen( strText ); + if (bCenter) { + float fRectRight = rcScreen.right / fBBWidth; + fRectRight = fRectRight * 2.0f - 1.0f; + float fRectBottom = 1.0f - rcScreen.bottom / fBBHeight; + fRectBottom = fRectBottom * 2.0f - 1.0f; + float fcenterx = ((fRectRight - fRectLeft) - (float)NumChars*fGlyphSizeX) *0.5f; + float fcentery = ((fRectTop - fRectBottom) - (float)1*fGlyphSizeY) *0.5f; + fRectLeft += fcenterx ; + fRectTop -= fcentery; + } + float fOriginalLeft = fRectLeft; + float fTexTop = 0.0f; + float fTexBottom = 1.0f; + + float fDepth = 0.5f; + for( int i=0; i 126 ) + { + continue; + } + + // Add 6 sprite vertices + DXUTSpriteVertex SpriteVertex = {}; + float fRectRight = fRectLeft + fGlyphSizeX; + float fRectBottom = fRectTop - fGlyphSizeY; + float fTexLeft = ( strText[i] - 32 ) * fCharTexSizeX; + float fTexRight = fTexLeft + fCharTexSizeX; + + // tri1 + SpriteVertex.vPos = XMFLOAT3( fRectLeft, fRectTop, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexLeft, fTexTop ); + SpriteVertex.vColor = vFontColor; + g_FontVertices.push_back( SpriteVertex ); + + SpriteVertex.vPos = XMFLOAT3( fRectRight, fRectTop, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexRight, fTexTop ); + SpriteVertex.vColor = vFontColor; + g_FontVertices.push_back( SpriteVertex ); + + SpriteVertex.vPos = XMFLOAT3( fRectLeft, fRectBottom, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexLeft, fTexBottom ); + SpriteVertex.vColor = vFontColor; + g_FontVertices.push_back( SpriteVertex ); + + // tri2 + SpriteVertex.vPos = XMFLOAT3( fRectRight, fRectTop, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexRight, fTexTop ); + SpriteVertex.vColor = vFontColor; + g_FontVertices.push_back( SpriteVertex ); + + SpriteVertex.vPos = XMFLOAT3( fRectRight, fRectBottom, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexRight, fTexBottom ); + SpriteVertex.vColor = vFontColor; + g_FontVertices.push_back( SpriteVertex ); + + SpriteVertex.vPos = XMFLOAT3( fRectLeft, fRectBottom, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexLeft, fTexBottom ); + SpriteVertex.vColor = vFontColor; + g_FontVertices.push_back( SpriteVertex ); + + fRectLeft += fGlyphSizeX; + + } + + // We have to end text after every line so that rendering order between sprites and fonts is preserved + EndText11( pd3dDevice, pd3d11DeviceContext ); +} + +_Use_decl_annotations_ +void EndText11( ID3D11Device* pd3dDevice, ID3D11DeviceContext* pd3d11DeviceContext ) +{ + if ( g_FontVertices.empty() ) + return; + + // ensure our buffer size can hold our sprites + UINT FontDataBytes = static_cast( g_FontVertices.size() * sizeof( DXUTSpriteVertex ) ); + if( g_FontBufferBytes11 < FontDataBytes ) + { + SAFE_RELEASE( g_pFontBuffer11 ); + g_FontBufferBytes11 = FontDataBytes; + + D3D11_BUFFER_DESC BufferDesc; + BufferDesc.ByteWidth = g_FontBufferBytes11; + BufferDesc.Usage = D3D11_USAGE_DYNAMIC; + BufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER; + BufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + BufferDesc.MiscFlags = 0; + + if (FAILED(pd3dDevice->CreateBuffer(&BufferDesc, nullptr, &g_pFontBuffer11))) + { + g_pFontBuffer11 = nullptr; + g_FontBufferBytes11 = 0; + return; + } + DXUT_SetDebugName( g_pFontBuffer11, "DXUT Text11" ); + } + + // Copy the sprites over + D3D11_BOX destRegion; + destRegion.left = 0; + destRegion.right = FontDataBytes; + destRegion.top = 0; + destRegion.bottom = 1; + destRegion.front = 0; + destRegion.back = 1; + D3D11_MAPPED_SUBRESOURCE MappedResource; + if ( S_OK == pd3d11DeviceContext->Map( g_pFontBuffer11, 0, D3D11_MAP_WRITE_DISCARD, 0, &MappedResource ) ) + { + memcpy( MappedResource.pData, (void*)&g_FontVertices[0], FontDataBytes ); + pd3d11DeviceContext->Unmap(g_pFontBuffer11, 0); + } + + ID3D11ShaderResourceView* pOldTexture = nullptr; + pd3d11DeviceContext->PSGetShaderResources( 0, 1, &pOldTexture ); + pd3d11DeviceContext->PSSetShaderResources( 0, 1, &g_pFont11 ); + + // Draw + UINT Stride = sizeof( DXUTSpriteVertex ); + UINT Offset = 0; + pd3d11DeviceContext->IASetVertexBuffers( 0, 1, &g_pFontBuffer11, &Stride, &Offset ); + pd3d11DeviceContext->IASetInputLayout( g_pInputLayout11 ); + pd3d11DeviceContext->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST ); + pd3d11DeviceContext->Draw( static_cast( g_FontVertices.size() ), 0 ); + + pd3d11DeviceContext->PSSetShaderResources( 0, 1, &pOldTexture ); + SAFE_RELEASE( pOldTexture ); + + g_FontVertices.clear(); +} + + +//====================================================================================== +// CDXUTDialog class +//====================================================================================== + +CDXUTDialog::CDXUTDialog() noexcept : + m_bNonUserEvents(false), + m_bKeyboardInput(false), + m_bMouseInput(true), + m_nDefaultControlID(0xffff), + m_fTimeLastRefresh(0), + m_pControlMouseOver(nullptr), + m_bVisible(true), + m_bCaption(false), + m_bMinimized(false), + m_bDrag(false), + m_wszCaption{}, + m_x( 0 ), + m_y( 0 ), + m_width( 0 ), + m_height( 0 ), + m_nCaptionHeight(18), + m_colorTopLeft(0), + m_colorTopRight(0), + m_colorBottomLeft(0), + m_colorBottomRight(0), + m_pManager( nullptr ), + m_pCallbackEvent( nullptr ), + m_pCallbackEventUserContext( nullptr ), + m_CapElement{}, + m_pNextDialog(this), + m_pPrevDialog(this) +{ +} + + +//-------------------------------------------------------------------------------------- +CDXUTDialog::~CDXUTDialog() +{ + RemoveAllControls(); + + m_Fonts.clear(); + m_Textures.clear(); + + for( auto it = m_DefaultElements.begin(); it != m_DefaultElements.end(); ++it ) + { + SAFE_DELETE( *it ); + } + + m_DefaultElements.clear(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTDialog::Init( CDXUTDialogResourceManager* pManager, bool bRegisterDialog ) +{ + m_pManager = pManager; + if( bRegisterDialog ) + pManager->RegisterDialog( this ); + + SetTexture( 0, MAKEINTRESOURCE( 0xFFFF ), ( HMODULE )0xFFFF ); + InitDefaultElements(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTDialog::Init( CDXUTDialogResourceManager* pManager, bool bRegisterDialog, LPCWSTR pszControlTextureFilename ) +{ + m_pManager = pManager; + if( bRegisterDialog ) + pManager->RegisterDialog( this ); + SetTexture( 0, pszControlTextureFilename ); + InitDefaultElements(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTDialog::Init( CDXUTDialogResourceManager* pManager, bool bRegisterDialog, + LPCWSTR szControlTextureResourceName, HMODULE hControlTextureResourceModule ) +{ + m_pManager = pManager; + if( bRegisterDialog ) + pManager->RegisterDialog( this ); + + SetTexture( 0, szControlTextureResourceName, hControlTextureResourceModule ); + InitDefaultElements(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTDialog::SetCallback( PCALLBACKDXUTGUIEVENT pCallback, void* pUserContext ) +{ + // If this assert triggers, you need to call CDXUTDialog::Init() first. This change + // was made so that the DXUT's GUI could become seperate and optional from DXUT's core. The + // creation and interfacing with CDXUTDialogResourceManager is now the responsibility + // of the application if it wishes to use DXUT's GUI. + assert( m_pManager && L"To fix call CDXUTDialog::Init() first. See comments for details." ); + + m_pCallbackEvent = pCallback; + m_pCallbackEventUserContext = pUserContext; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::RemoveControl( _In_ int ID ) +{ + for( auto it = m_Controls.begin(); it != m_Controls.end(); ++it ) + { + if( (*it)->GetID() == ID ) + { + // Clean focus first + ClearFocus(); + + // Clear references to this control + if( s_pControlFocus == (*it) ) + s_pControlFocus = nullptr; + if( s_pControlPressed == (*it) ) + s_pControlPressed = nullptr; + if( m_pControlMouseOver == (*it) ) + m_pControlMouseOver = nullptr; + + SAFE_DELETE( (*it) ); + m_Controls.erase( it ); + + return; + } + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::RemoveAllControls() +{ + if( s_pControlFocus && s_pControlFocus->m_pDialog == this ) + s_pControlFocus = nullptr; + if( s_pControlPressed && s_pControlPressed->m_pDialog == this ) + s_pControlPressed = nullptr; + m_pControlMouseOver = nullptr; + + for( auto it = m_Controls.begin(); it != m_Controls.end(); ++it ) + { + SAFE_DELETE( *it ); + } + + m_Controls.clear(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::Refresh() +{ + if( s_pControlFocus ) + s_pControlFocus->OnFocusOut(); + + if( m_pControlMouseOver ) + m_pControlMouseOver->OnMouseLeave(); + + s_pControlFocus = nullptr; + s_pControlPressed = nullptr; + m_pControlMouseOver = nullptr; + + for( auto it = m_Controls.begin(); it != m_Controls.end(); ++it ) + { + (*it)->Refresh(); + } + + if( m_bKeyboardInput ) + FocusDefaultControl(); +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTDialog::OnRender( _In_ float fElapsedTime ) +{ + // If this assert triggers, you need to call CDXUTDialogResourceManager::On*Device() from inside + // the application's device callbacks. See the SDK samples for an example of how to do this. + assert( m_pManager->GetD3D11Device() && + L"To fix hook up CDXUTDialogResourceManager to device callbacks. See comments for details" ); + + // See if the dialog needs to be refreshed + if( m_fTimeLastRefresh < s_fTimeRefresh ) + { + m_fTimeLastRefresh = DXUTGetTime(); + Refresh(); + } + + // For invisible dialog, out now. + if( !m_bVisible || + ( m_bMinimized && !m_bCaption ) ) + return S_OK; + + auto pd3dDevice = m_pManager->GetD3D11Device(); + auto pd3dDeviceContext = m_pManager->GetD3D11DeviceContext(); + + // Set up a state block here and restore it when finished drawing all the controls + m_pManager->StoreD3D11State( pd3dDeviceContext ); + + BOOL bBackgroundIsVisible = ( m_colorTopLeft | m_colorTopRight | m_colorBottomRight | m_colorBottomLeft ) & 0xff000000; + if( !m_bMinimized && bBackgroundIsVisible ) + { + // Convert the draw rectangle from screen coordinates to clip space coordinates. + float Left, Right, Top, Bottom; + Left = m_x * 2.0f / m_pManager->m_nBackBufferWidth - 1.0f; + Right = ( m_x + m_width ) * 2.0f / m_pManager->m_nBackBufferWidth - 1.0f; + Top = 1.0f - m_y * 2.0f / m_pManager->m_nBackBufferHeight; + Bottom = 1.0f - ( m_y + m_height ) * 2.0f / m_pManager->m_nBackBufferHeight; + + DXUT_SCREEN_VERTEX_10 vertices[4] = + { + Left, Top, 0.5f, D3DCOLOR_TO_D3DCOLORVALUE( m_colorTopLeft ), 0.0f, 0.0f, + Right, Top, 0.5f, D3DCOLOR_TO_D3DCOLORVALUE( m_colorTopRight ), 1.0f, 0.0f, + Left, Bottom, 0.5f, D3DCOLOR_TO_D3DCOLORVALUE( m_colorBottomLeft ), 0.0f, 1.0f, + Right, Bottom, 0.5f, D3DCOLOR_TO_D3DCOLORVALUE( m_colorBottomRight ), 1.0f, 1.0f, + }; + + //DXUT_SCREEN_VERTEX_10 *pVB; + D3D11_MAPPED_SUBRESOURCE MappedData; + if( SUCCEEDED( pd3dDeviceContext->Map( m_pManager->m_pVBScreenQuad11, 0, D3D11_MAP_WRITE_DISCARD, + 0, &MappedData ) ) ) + { + memcpy( MappedData.pData, vertices, sizeof( vertices ) ); + pd3dDeviceContext->Unmap( m_pManager->m_pVBScreenQuad11, 0 ); + } + + // Set the quad VB as current + UINT stride = sizeof( DXUT_SCREEN_VERTEX_10 ); + UINT offset = 0; + pd3dDeviceContext->IASetVertexBuffers( 0, 1, &m_pManager->m_pVBScreenQuad11, &stride, &offset ); + pd3dDeviceContext->IASetInputLayout( m_pManager->m_pInputLayout11 ); + pd3dDeviceContext->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP ); + + // Setup for rendering + m_pManager->ApplyRenderUIUntex11( pd3dDeviceContext ); + pd3dDeviceContext->Draw( 4, 0 ); + } + + auto pTextureNode = GetTexture( 0 ); + pd3dDeviceContext->PSSetShaderResources( 0, 1, &pTextureNode->pTexResView11 ); + + // Sort depth back to front + m_pManager->BeginSprites11(); + BeginText11(); + + m_pManager->ApplyRenderUI11( pd3dDeviceContext ); + + // Render the caption if it's enabled. + if( m_bCaption ) + { + // DrawSprite will offset the rect down by + // m_nCaptionHeight, so adjust the rect higher + // here to negate the effect. + RECT rc = { 0, -m_nCaptionHeight, m_width, 0 }; + DrawSprite( &m_CapElement, &rc, 0.99f ); + rc.left += 5; // Make a left margin + WCHAR wszOutput[256]; + wcscpy_s( wszOutput, 256, m_wszCaption ); + if( m_bMinimized ) + wcscat_s( wszOutput, 256, L" (Minimized)" ); + DrawText( wszOutput, &m_CapElement, &rc, true ); + } + + // If the dialog is minimized, skip rendering + // its controls. + if( !m_bMinimized ) + { + for( auto it = m_Controls.cbegin(); it != m_Controls.cend(); ++it ) + { + // Focused control is drawn last + if( *it == s_pControlFocus ) + continue; + + (*it)->Render( fElapsedTime ); + } + + if( s_pControlFocus && s_pControlFocus->m_pDialog == this ) + s_pControlFocus->Render( fElapsedTime ); + } + + // End sprites + if( m_bCaption ) + { + m_pManager->EndSprites11( pd3dDevice, pd3dDeviceContext ); + EndText11( pd3dDevice, pd3dDeviceContext ); + } + m_pManager->RestoreD3D11State( pd3dDeviceContext ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +VOID CDXUTDialog::SendEvent( UINT nEvent, bool bTriggeredByUser, CDXUTControl* pControl ) +{ + // If no callback has been registered there's nowhere to send the event to + if( !m_pCallbackEvent ) + return; + + // Discard events triggered programatically if these types of events haven't been + // enabled + if( !bTriggeredByUser && !m_bNonUserEvents ) + return; + + m_pCallbackEvent( nEvent, pControl->GetID(), pControl, m_pCallbackEventUserContext ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::SetFont( UINT index, LPCWSTR strFaceName, LONG height, LONG weight ) +{ + // If this assert triggers, you need to call CDXUTDialog::Init() first. This change + // was made so that the DXUT's GUI could become seperate and optional from DXUT's core. The + // creation and interfacing with CDXUTDialogResourceManager is now the responsibility + // of the application if it wishes to use DXUT's GUI. + assert( m_pManager && L"To fix call CDXUTDialog::Init() first. See comments for details." ); + _Analysis_assume_( m_pManager ); + + // Make sure the list is at least as large as the index being set + for( size_t i = m_Fonts.size(); i <= index; i++ ) + { + m_Fonts.push_back( -1 ); + } + + int iFont = m_pManager->AddFont( strFaceName, height, weight ); + m_Fonts[ index ] = iFont; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +DXUTFontNode* CDXUTDialog::GetFont( _In_ UINT index ) const +{ + if( !m_pManager ) + return nullptr; + return m_pManager->GetFontNode( m_Fonts[ index ] ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::SetTexture( UINT index, LPCWSTR strFilename ) +{ + // If this assert triggers, you need to call CDXUTDialog::Init() first. This change + // was made so that the DXUT's GUI could become seperate and optional from DXUT's core. The + // creation and interfacing with CDXUTDialogResourceManager is now the responsibility + // of the application if it wishes to use DXUT's GUI. + assert( m_pManager && L"To fix this, call CDXUTDialog::Init() first. See comments for details." ); + _Analysis_assume_( m_pManager ); + + // Make sure the list is at least as large as the index being set + for( size_t i = m_Textures.size(); i <= index; i++ ) + { + m_Textures.push_back( -1 ); + } + + int iTexture = m_pManager->AddTexture( strFilename ); + + m_Textures[ index] = iTexture; + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::SetTexture( UINT index, LPCWSTR strResourceName, HMODULE hResourceModule ) +{ + // If this assert triggers, you need to call CDXUTDialog::Init() first. This change + // was made so that the DXUT's GUI could become seperate and optional from DXUT's core. The + // creation and interfacing with CDXUTDialogResourceManager is now the responsibility + // of the application if it wishes to use DXUT's GUI. + assert( m_pManager && L"To fix this, call CDXUTDialog::Init() first. See comments for details." ); + _Analysis_assume_( m_pManager ); + + // Make sure the list is at least as large as the index being set + for( size_t i = m_Textures.size(); i <= index; i++ ) + { + m_Textures.push_back( -1 ); + } + + int iTexture = m_pManager->AddTexture( strResourceName, hResourceModule ); + + m_Textures[ index ] = iTexture; + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +DXUTTextureNode* CDXUTDialog::GetTexture( _In_ UINT index ) const +{ + if( !m_pManager ) + return nullptr; + return m_pManager->GetTextureNode( m_Textures[ index ] ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTDialog::MsgProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + bool bHandled = false; + + // For invisible dialog, do not handle anything. + if( !m_bVisible ) + return false; + + // If automation command-line switch is on, enable this dialog's keyboard input + // upon any key press or mouse click. + if( DXUTGetAutomation() && + ( WM_LBUTTONDOWN == uMsg || WM_LBUTTONDBLCLK == uMsg || WM_KEYDOWN == uMsg ) ) + { + m_pManager->EnableKeyboardInputForAllDialogs(); + } + + // If caption is enable, check for clicks in the caption area. + if( m_bCaption ) + { + if( uMsg == WM_LBUTTONDOWN || uMsg == WM_LBUTTONDBLCLK ) + { + POINT mousePoint = + { + short( LOWORD( lParam ) ), short( HIWORD( lParam ) ) + }; + + if( mousePoint.x >= m_x && mousePoint.x < m_x + m_width && + mousePoint.y >= m_y && mousePoint.y < m_y + m_nCaptionHeight ) + { + m_bDrag = true; + SetCapture( DXUTGetHWND() ); + return true; + } + } + else if( uMsg == WM_LBUTTONUP && m_bDrag ) + { + POINT mousePoint = + { + short( LOWORD( lParam ) ), short( HIWORD( lParam ) ) + }; + + if( mousePoint.x >= m_x && mousePoint.x < m_x + m_width && + mousePoint.y >= m_y && mousePoint.y < m_y + m_nCaptionHeight ) + { + ReleaseCapture(); + m_bDrag = false; + m_bMinimized = !m_bMinimized; + return true; + } + } + } + + // If the dialog is minimized, don't send any messages to controls. + if( m_bMinimized ) + return false; + + // If a control is in focus, it belongs to this dialog, and it's enabled, then give + // it the first chance at handling the message. + if( s_pControlFocus && + s_pControlFocus->m_pDialog == this && + s_pControlFocus->GetEnabled() ) + { + // If the control MsgProc handles it, then we don't. + if( s_pControlFocus->MsgProc( uMsg, wParam, lParam ) ) + return true; + } + + switch( uMsg ) + { + case WM_SIZE: + case WM_MOVE: + { + // Handle sizing and moving messages so that in case the mouse cursor is moved out + // of an UI control because of the window adjustment, we can properly + // unhighlight the highlighted control. + POINT pt = + { + -1, -1 + }; + OnMouseMove( pt ); + break; + } + + case WM_ACTIVATEAPP: + // Call OnFocusIn()/OnFocusOut() of the control that currently has the focus + // as the application is activated/deactivated. This matches the Windows + // behavior. + if( s_pControlFocus && + s_pControlFocus->m_pDialog == this && + s_pControlFocus->GetEnabled() ) + { + if( wParam ) + s_pControlFocus->OnFocusIn(); + else + s_pControlFocus->OnFocusOut(); + } + break; + + // Keyboard messages + case WM_KEYDOWN: + case WM_SYSKEYDOWN: + case WM_KEYUP: + case WM_SYSKEYUP: + { + // If a control is in focus, it belongs to this dialog, and it's enabled, then give + // it the first chance at handling the message. + if( s_pControlFocus && + s_pControlFocus->m_pDialog == this && + s_pControlFocus->GetEnabled() ) + for( auto it = m_Controls.cbegin(); it != m_Controls.cend(); ++it ) + { + if( s_pControlFocus->HandleKeyboard( uMsg, wParam, lParam ) ) + return true; + } + + // Not yet handled, see if this matches a control's hotkey + // Activate the hotkey if the focus doesn't belong to an + // edit box. + if( uMsg == WM_KEYDOWN && ( !s_pControlFocus || + ( s_pControlFocus->GetType() != DXUT_CONTROL_EDITBOX + && s_pControlFocus->GetType() != DXUT_CONTROL_IMEEDITBOX ) ) ) + { + for( auto it = m_Controls.begin(); it != m_Controls.end(); ++it ) + { + if( (*it)->GetHotkey() == wParam ) + { + (*it)->OnHotkey(); + return true; + } + } + } + + // Not yet handled, check for focus messages + if( uMsg == WM_KEYDOWN ) + { + // If keyboard input is not enabled, this message should be ignored + if( !m_bKeyboardInput ) + return false; + + switch( wParam ) + { + case VK_RIGHT: + case VK_DOWN: + if( s_pControlFocus ) + { + return OnCycleFocus( true ); + } + break; + + case VK_LEFT: + case VK_UP: + if( s_pControlFocus ) + { + return OnCycleFocus( false ); + } + break; + + case VK_TAB: + { + bool bShiftDown = ( ( GetKeyState( VK_SHIFT ) & 0x8000 ) != 0 ); + return OnCycleFocus( !bShiftDown ); + } + } + } + + break; + } + + + // Mouse messages + case WM_MOUSEMOVE: + case WM_LBUTTONDOWN: + case WM_LBUTTONUP: + case WM_MBUTTONDOWN: + case WM_MBUTTONUP: + case WM_RBUTTONDOWN: + case WM_RBUTTONUP: + case WM_XBUTTONDOWN: + case WM_XBUTTONUP: + case WM_LBUTTONDBLCLK: + case WM_MBUTTONDBLCLK: + case WM_RBUTTONDBLCLK: + case WM_XBUTTONDBLCLK: + case WM_MOUSEWHEEL: + { + // If not accepting mouse input, return false to indicate the message should still + // be handled by the application (usually to move the camera). + if( !m_bMouseInput ) + return false; + + POINT mousePoint = + { + short( LOWORD( lParam ) ), short( HIWORD( lParam ) ) + }; + mousePoint.x -= m_x; + mousePoint.y -= m_y; + + // If caption is enabled, offset the Y coordinate by the negative of its height. + if( m_bCaption ) + mousePoint.y -= m_nCaptionHeight; + + // If a control is in focus, it belongs to this dialog, and it's enabled, then give + // it the first chance at handling the message. + if( s_pControlFocus && + s_pControlFocus->m_pDialog == this && + s_pControlFocus->GetEnabled() ) + { + if( s_pControlFocus->HandleMouse( uMsg, mousePoint, wParam, lParam ) ) + return true; + } + + // Not yet handled, see if the mouse is over any controls + auto pControl = GetControlAtPoint( mousePoint ); + if( pControl && pControl->GetEnabled() ) + { + bHandled = pControl->HandleMouse( uMsg, mousePoint, wParam, lParam ); + if( bHandled ) + return true; + } + else + { + // Mouse not over any controls in this dialog, if there was a control + // which had focus it just lost it + if( uMsg == WM_LBUTTONDOWN && + s_pControlFocus && + s_pControlFocus->m_pDialog == this ) + { + s_pControlFocus->OnFocusOut(); + s_pControlFocus = nullptr; + } + } + + // Still not handled, hand this off to the dialog. Return false to indicate the + // message should still be handled by the application (usually to move the camera). + switch( uMsg ) + { + case WM_MOUSEMOVE: + OnMouseMove( mousePoint ); + return false; + } + + break; + } + + case WM_CAPTURECHANGED: + { + // The application has lost mouse capture. + // The dialog object may not have received + // a WM_MOUSEUP when capture changed. Reset + // m_bDrag so that the dialog does not mistakenly + // think the mouse button is still held down. + if( ( HWND )lParam != hWnd ) + m_bDrag = false; + } + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +CDXUTControl* CDXUTDialog::GetControlAtPoint( _In_ const POINT& pt ) const +{ + // Search through all child controls for the first one which + // contains the mouse point + for( auto it = m_Controls.cbegin(); it != m_Controls.cend(); ++it ) + { + if( !*it ) + { + continue; + } + + // We only return the current control if it is visible + // and enabled. Because GetControlAtPoint() is used to do mouse + // hittest, it makes sense to perform this filtering. + if( (*it)->ContainsPoint( pt ) && (*it)->GetEnabled() && (*it)->GetVisible() ) + { + return *it; + } + } + + return nullptr; +} + + +//-------------------------------------------------------------------------------------- +bool CDXUTDialog::GetControlEnabled( _In_ int ID ) const +{ + auto pControl = GetControl( ID ); + if( !pControl ) + return false; + + return pControl->GetEnabled(); +} + + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::SetControlEnabled( _In_ int ID, _In_ bool bEnabled ) +{ + auto pControl = GetControl( ID ); + if( !pControl ) + return; + + pControl->SetEnabled( bEnabled ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::OnMouseUp( _In_ const POINT& pt ) +{ + UNREFERENCED_PARAMETER(pt); + s_pControlPressed = nullptr; + m_pControlMouseOver = nullptr; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::OnMouseMove( _In_ const POINT& pt ) +{ + // Figure out which control the mouse is over now + auto pControl = GetControlAtPoint( pt ); + + // If the mouse is still over the same control, nothing needs to be done + if( pControl == m_pControlMouseOver ) + return; + + // Handle mouse leaving the old control + if( m_pControlMouseOver ) + m_pControlMouseOver->OnMouseLeave(); + + // Handle mouse entering the new control + m_pControlMouseOver = pControl; + if( pControl ) + m_pControlMouseOver->OnMouseEnter(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::SetDefaultElement( UINT nControlType, UINT iElement, CDXUTElement* pElement ) +{ + // If this Element type already exist in the list, simply update the stored Element + for( auto it = m_DefaultElements.begin(); it != m_DefaultElements.end(); ++it ) + { + if( (*it)->nControlType == nControlType && + (*it)->iElement == iElement ) + { + (*it)->Element = *pElement; + return S_OK; + } + } + + // Otherwise, add a new entry + DXUTElementHolder* pNewHolder; + pNewHolder = new (std::nothrow) DXUTElementHolder; + if( !pNewHolder ) + return E_OUTOFMEMORY; + + pNewHolder->nControlType = nControlType; + pNewHolder->iElement = iElement; + pNewHolder->Element = *pElement; + + m_DefaultElements.push_back( pNewHolder ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +CDXUTElement* CDXUTDialog::GetDefaultElement( UINT nControlType, UINT iElement ) const +{ + for( auto it = m_DefaultElements.cbegin(); it != m_DefaultElements.cend(); ++it ) + { + if( (*it)->nControlType == nControlType && + (*it)->iElement == iElement ) + { + return &(*it)->Element; + } + } + + return nullptr; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::AddStatic( int ID, LPCWSTR strText, int x, int y, int width, int height, bool bIsDefault, + CDXUTStatic** ppCreated ) +{ + HRESULT hr = S_OK; + + auto pStatic = new (std::nothrow) CDXUTStatic( this ); + + if( ppCreated ) + *ppCreated = pStatic; + + if( !pStatic ) + return E_OUTOFMEMORY; + + hr = AddControl( pStatic ); + if( FAILED( hr ) ) + return hr; + + // Set the ID and list index + pStatic->SetID( ID ); + pStatic->SetText( strText ); + pStatic->SetLocation( x, y ); + pStatic->SetSize( width, height ); + pStatic->m_bIsDefault = bIsDefault; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::AddButton( int ID, LPCWSTR strText, int x, int y, int width, int height, UINT nHotkey, + bool bIsDefault, CDXUTButton** ppCreated ) +{ + HRESULT hr = S_OK; + + auto pButton = new (std::nothrow) CDXUTButton( this ); + + if( ppCreated ) + *ppCreated = pButton; + + if( !pButton ) + return E_OUTOFMEMORY; + + hr = AddControl( pButton ); + if( FAILED( hr ) ) + return hr; + + // Set the ID and list index + pButton->SetID( ID ); + pButton->SetText( strText ); + pButton->SetLocation( x, y ); + pButton->SetSize( width, height ); + pButton->SetHotkey( nHotkey ); + pButton->m_bIsDefault = bIsDefault; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::AddCheckBox( int ID, LPCWSTR strText, int x, int y, int width, int height, bool bChecked, + UINT nHotkey, bool bIsDefault, CDXUTCheckBox** ppCreated ) +{ + HRESULT hr = S_OK; + + auto pCheckBox = new (std::nothrow) CDXUTCheckBox( this ); + + if( ppCreated ) + *ppCreated = pCheckBox; + + if( !pCheckBox ) + return E_OUTOFMEMORY; + + hr = AddControl( pCheckBox ); + if( FAILED( hr ) ) + return hr; + + // Set the ID and list index + pCheckBox->SetID( ID ); + pCheckBox->SetText( strText ); + pCheckBox->SetLocation( x, y ); + pCheckBox->SetSize( width, height ); + pCheckBox->SetHotkey( nHotkey ); + pCheckBox->m_bIsDefault = bIsDefault; + pCheckBox->SetChecked( bChecked ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::AddRadioButton( int ID, UINT nButtonGroup, LPCWSTR strText, int x, int y, int width, int height, + bool bChecked, UINT nHotkey, bool bIsDefault, CDXUTRadioButton** ppCreated ) +{ + HRESULT hr = S_OK; + + auto pRadioButton = new (std::nothrow) CDXUTRadioButton( this ); + + if( ppCreated ) + *ppCreated = pRadioButton; + + if( !pRadioButton ) + return E_OUTOFMEMORY; + + hr = AddControl( pRadioButton ); + if( FAILED( hr ) ) + return hr; + + // Set the ID and list index + pRadioButton->SetID( ID ); + pRadioButton->SetText( strText ); + pRadioButton->SetButtonGroup( nButtonGroup ); + pRadioButton->SetLocation( x, y ); + pRadioButton->SetSize( width, height ); + pRadioButton->SetHotkey( nHotkey ); + pRadioButton->SetChecked( bChecked ); + pRadioButton->m_bIsDefault = bIsDefault; + pRadioButton->SetChecked( bChecked ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::AddComboBox( int ID, int x, int y, int width, int height, UINT nHotkey, bool bIsDefault, + CDXUTComboBox** ppCreated ) +{ + HRESULT hr = S_OK; + + auto pComboBox = new (std::nothrow) CDXUTComboBox( this ); + + if( ppCreated ) + *ppCreated = pComboBox; + + if( !pComboBox ) + return E_OUTOFMEMORY; + + hr = AddControl( pComboBox ); + if( FAILED( hr ) ) + return hr; + + // Set the ID and list index + pComboBox->SetID( ID ); + pComboBox->SetLocation( x, y ); + pComboBox->SetSize( width, height ); + pComboBox->SetHotkey( nHotkey ); + pComboBox->m_bIsDefault = bIsDefault; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::AddSlider( int ID, int x, int y, int width, int height, int min, int max, int value, + bool bIsDefault, CDXUTSlider** ppCreated ) +{ + HRESULT hr = S_OK; + + auto pSlider = new (std::nothrow) CDXUTSlider( this ); + + if( ppCreated ) + *ppCreated = pSlider; + + if( !pSlider ) + return E_OUTOFMEMORY; + + hr = AddControl( pSlider ); + if( FAILED( hr ) ) + return hr; + + // Set the ID and list index + pSlider->SetID( ID ); + pSlider->SetLocation( x, y ); + pSlider->SetSize( width, height ); + pSlider->m_bIsDefault = bIsDefault; + pSlider->SetRange( min, max ); + pSlider->SetValue( value ); + pSlider->UpdateRects(); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::AddEditBox( int ID, LPCWSTR strText, int x, int y, int width, int height, bool bIsDefault, + CDXUTEditBox** ppCreated ) +{ + HRESULT hr = S_OK; + + auto pEditBox = new (std::nothrow) CDXUTEditBox( this ); + + if( ppCreated ) + *ppCreated = pEditBox; + + if( !pEditBox ) + return E_OUTOFMEMORY; + + hr = AddControl( pEditBox ); + if( FAILED( hr ) ) + return hr; + + // Set the ID and position + pEditBox->SetID( ID ); + pEditBox->SetLocation( x, y ); + pEditBox->SetSize( width, height ); + pEditBox->m_bIsDefault = bIsDefault; + + if( strText ) + pEditBox->SetText( strText ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::AddListBox( int ID, int x, int y, int width, int height, DWORD dwStyle, CDXUTListBox** ppCreated ) +{ + HRESULT hr = S_OK; + auto pListBox = new (std::nothrow) CDXUTListBox( this ); + + if( ppCreated ) + *ppCreated = pListBox; + + if( !pListBox ) + return E_OUTOFMEMORY; + + hr = AddControl( pListBox ); + if( FAILED( hr ) ) + return hr; + + // Set the ID and position + pListBox->SetID( ID ); + pListBox->SetLocation( x, y ); + pListBox->SetSize( width, height ); + pListBox->SetStyle( dwStyle ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTDialog::InitControl( _In_ CDXUTControl* pControl ) +{ + HRESULT hr; + + if( !pControl ) + return E_INVALIDARG; + + pControl->m_Index = static_cast( m_Controls.size() ); + + // Look for a default Element entries + for( auto it = m_DefaultElements.begin(); it != m_DefaultElements.end(); ++it ) + { + if( (*it)->nControlType == pControl->GetType() ) + pControl->SetElement( (*it)->iElement, &(*it)->Element ); + } + + V_RETURN( pControl->OnInit() ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTDialog::AddControl( _In_ CDXUTControl* pControl ) +{ + HRESULT hr = S_OK; + + hr = InitControl( pControl ); + if( FAILED( hr ) ) + return DXTRACE_ERR( L"CDXUTDialog::InitControl", hr ); + + // Add to the list + m_Controls.push_back( pControl ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +CDXUTControl* CDXUTDialog::GetControl( _In_ int ID ) const +{ + // Try to find the control with the given ID + for( auto it = m_Controls.cbegin(); it != m_Controls.cend(); ++it ) + { + if( (*it)->GetID() == ID ) + { + return *it; + } + } + + // Not found + return nullptr; +} + + +//-------------------------------------------------------------------------------------- +CDXUTControl* CDXUTDialog::GetControl( _In_ int ID, _In_ UINT nControlType ) const +{ + // Try to find the control with the given ID + for( auto it = m_Controls.cbegin(); it != m_Controls.cend(); ++it ) + { + if( (*it)->GetID() == ID && (*it)->GetType() == nControlType ) + { + return *it; + } + } + + // Not found + return nullptr; +} + + +//-------------------------------------------------------------------------------------- +CDXUTControl* CDXUTDialog::GetNextControl( _In_ CDXUTControl* pControl ) +{ + int index = pControl->m_Index + 1; + + auto pDialog = pControl->m_pDialog; + + // Cycle through dialogs in the loop to find the next control. Note + // that if only one control exists in all looped dialogs it will + // be the returned 'next' control. + while( index >= ( int )pDialog->m_Controls.size() ) + { + pDialog = pDialog->m_pNextDialog; + index = 0; + } + + return pDialog->m_Controls[ index ]; +} + + +//-------------------------------------------------------------------------------------- +CDXUTControl* CDXUTDialog::GetPrevControl( _In_ CDXUTControl* pControl ) +{ + int index = pControl->m_Index - 1; + + auto pDialog = pControl->m_pDialog; + + // Cycle through dialogs in the loop to find the next control. Note + // that if only one control exists in all looped dialogs it will + // be the returned 'previous' control. + while( index < 0 ) + { + pDialog = pDialog->m_pPrevDialog; + if( !pDialog ) + pDialog = pControl->m_pDialog; + + index = int( pDialog->m_Controls.size() ) - 1; + } + + return pDialog->m_Controls[ index ]; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::ClearRadioButtonGroup( _In_ UINT nButtonGroup ) +{ + // Find all radio buttons with the given group number + for( auto it = m_Controls.cbegin(); it != m_Controls.cend(); ++it ) + { + if( (*it)->GetType() == DXUT_CONTROL_RADIOBUTTON ) + { + auto pRadioButton = ( CDXUTRadioButton* )*it; + + if( pRadioButton->GetButtonGroup() == nButtonGroup ) + pRadioButton->SetChecked( false, false ); + } + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::ClearComboBox( _In_ int ID ) +{ + auto pComboBox = GetComboBox( ID ); + if( !pComboBox ) + return; + + pComboBox->RemoveAllItems(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::RequestFocus( _In_ CDXUTControl* pControl ) +{ + if( s_pControlFocus == pControl ) + return; + + if( !pControl->CanHaveFocus() ) + return; + + if( s_pControlFocus ) + s_pControlFocus->OnFocusOut(); + + pControl->OnFocusIn(); + s_pControlFocus = pControl; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::DrawRect( const RECT* pRect, DWORD color ) +{ + UNREFERENCED_PARAMETER(pRect); + UNREFERENCED_PARAMETER(color); + // TODO - + return E_FAIL; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::DrawSprite( CDXUTElement* pElement, const RECT* prcDest, float fDepth ) +{ + // No need to draw fully transparent layers + if( pElement->TextureColor.Current.w == 0 ) + return S_OK; + + RECT rcTexture = pElement->rcTexture; + + RECT rcScreen = *prcDest; + OffsetRect( &rcScreen, m_x, m_y ); + + // If caption is enabled, offset the Y position by its height. + if( m_bCaption ) + OffsetRect( &rcScreen, 0, m_nCaptionHeight ); + + auto pTextureNode = GetTexture( pElement->iTexture ); + if( !pTextureNode ) + return E_FAIL; + + float fBBWidth = ( float )m_pManager->m_nBackBufferWidth; + float fBBHeight = ( float )m_pManager->m_nBackBufferHeight; + float fTexWidth = ( float )pTextureNode->dwWidth; + float fTexHeight = ( float )pTextureNode->dwHeight; + + float fRectLeft = rcScreen.left / fBBWidth; + float fRectTop = 1.0f - rcScreen.top / fBBHeight; + float fRectRight = rcScreen.right / fBBWidth; + float fRectBottom = 1.0f - rcScreen.bottom / fBBHeight; + + fRectLeft = fRectLeft * 2.0f - 1.0f; + fRectTop = fRectTop * 2.0f - 1.0f; + fRectRight = fRectRight * 2.0f - 1.0f; + fRectBottom = fRectBottom * 2.0f - 1.0f; + + float fTexLeft = rcTexture.left / fTexWidth; + float fTexTop = rcTexture.top / fTexHeight; + float fTexRight = rcTexture.right / fTexWidth; + float fTexBottom = rcTexture.bottom / fTexHeight; + + // Add 6 sprite vertices + DXUTSpriteVertex SpriteVertex = {}; + + // tri1 + SpriteVertex.vPos = XMFLOAT3( fRectLeft, fRectTop, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexLeft, fTexTop ); + SpriteVertex.vColor = pElement->TextureColor.Current; + m_pManager->m_SpriteVertices.push_back( SpriteVertex ); + + SpriteVertex.vPos = XMFLOAT3( fRectRight, fRectTop, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexRight, fTexTop ); + SpriteVertex.vColor = pElement->TextureColor.Current; + m_pManager->m_SpriteVertices.push_back( SpriteVertex ); + + SpriteVertex.vPos = XMFLOAT3( fRectLeft, fRectBottom, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexLeft, fTexBottom ); + SpriteVertex.vColor = pElement->TextureColor.Current; + m_pManager->m_SpriteVertices.push_back( SpriteVertex ); + + // tri2 + SpriteVertex.vPos = XMFLOAT3( fRectRight, fRectTop, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexRight, fTexTop ); + SpriteVertex.vColor = pElement->TextureColor.Current; + m_pManager->m_SpriteVertices.push_back( SpriteVertex ); + + SpriteVertex.vPos = XMFLOAT3( fRectRight, fRectBottom, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexRight, fTexBottom ); + SpriteVertex.vColor = pElement->TextureColor.Current; + m_pManager->m_SpriteVertices.push_back( SpriteVertex ); + + SpriteVertex.vPos = XMFLOAT3( fRectLeft, fRectBottom, fDepth ); + SpriteVertex.vTex = XMFLOAT2( fTexLeft, fTexBottom ); + SpriteVertex.vColor = pElement->TextureColor.Current; + m_pManager->m_SpriteVertices.push_back( SpriteVertex ); + + // Why are we drawing the sprite every time? This is very inefficient, but the sprite workaround doesn't have support for sorting now, so we have to + // draw a sprite every time to keep the order correct between sprites and text. + m_pManager->EndSprites11( DXUTGetD3D11Device(), DXUTGetD3D11DeviceContext() ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::CalcTextRect( LPCWSTR strText, CDXUTElement* pElement, const RECT* prcDest, int nCount ) +{ + auto pFontNode = GetFont( pElement->iFont ); + if( !pFontNode ) + return E_FAIL; + + UNREFERENCED_PARAMETER(strText); + UNREFERENCED_PARAMETER(prcDest); + UNREFERENCED_PARAMETER(nCount); + // TODO - + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialog::DrawText( LPCWSTR strText, CDXUTElement* pElement, const RECT* prcDest, bool bShadow, bool bCenter ) +{ + // No need to draw fully transparent layers + if( pElement->FontColor.Current.w == 0 ) + return S_OK; + + RECT rcScreen = *prcDest; + OffsetRect( &rcScreen, m_x, m_y); + + // If caption is enabled, offset the Y position by its height. + if( m_bCaption ) + OffsetRect( &rcScreen, 0, m_nCaptionHeight ); + + float fBBWidth = ( float )m_pManager->m_nBackBufferWidth; + float fBBHeight = ( float )m_pManager->m_nBackBufferHeight; + + auto pd3dDevice = m_pManager->GetD3D11Device(); + auto pd3d11DeviceContext = m_pManager->GetD3D11DeviceContext(); + + if( bShadow ) + { + RECT rcShadow = rcScreen; + OffsetRect( &rcShadow, 1, 1 ); + + XMFLOAT4 vShadowColor( 0,0,0, 1.0f ); + DrawText11DXUT( pd3dDevice, pd3d11DeviceContext, + strText, rcShadow, vShadowColor, + fBBWidth, fBBHeight, bCenter ); + + } + + XMFLOAT4 vFontColor( pElement->FontColor.Current.x, pElement->FontColor.Current.y, pElement->FontColor.Current.z, 1.0f ); + DrawText11DXUT( pd3dDevice, pd3d11DeviceContext, + strText, rcScreen, vFontColor, + fBBWidth, fBBHeight, bCenter ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTDialog::SetBackgroundColors( DWORD colorTopLeft, DWORD colorTopRight, DWORD colorBottomLeft, + DWORD colorBottomRight ) +{ + m_colorTopLeft = colorTopLeft; + m_colorTopRight = colorTopRight; + m_colorBottomLeft = colorBottomLeft; + m_colorBottomRight = colorBottomRight; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::SetNextDialog( _In_ CDXUTDialog* pNextDialog ) +{ + if( !pNextDialog ) + pNextDialog = this; + + m_pNextDialog = pNextDialog; + if( pNextDialog ) + m_pNextDialog->m_pPrevDialog = this; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::ClearFocus() +{ + if( s_pControlFocus ) + { + s_pControlFocus->OnFocusOut(); + s_pControlFocus = nullptr; + } + + ReleaseCapture(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::FocusDefaultControl() +{ + // Check for default control in this dialog + for( auto it = m_Controls.cbegin(); it != m_Controls.cend(); ++it ) + { + if( (*it)->m_bIsDefault ) + { + // Remove focus from the current control + ClearFocus(); + + // Give focus to the default control + s_pControlFocus = *it; + s_pControlFocus->OnFocusIn(); + return; + } + } +} + + +//-------------------------------------------------------------------------------------- +bool CDXUTDialog::OnCycleFocus( _In_ bool bForward ) +{ + CDXUTControl* pControl = nullptr; + CDXUTDialog* pDialog = nullptr; // pDialog and pLastDialog are used to track wrapping of + CDXUTDialog* pLastDialog; // focus from first control to last or vice versa. + + if( !s_pControlFocus ) + { + // If s_pControlFocus is nullptr, we focus the first control of first dialog in + // the case that bForward is true, and focus the last control of last dialog when + // bForward is false. + // + if( bForward ) + { + // Search for the first control from the start of the dialog + // array. + for( auto it = m_pManager->m_Dialogs.cbegin(); it != m_pManager->m_Dialogs.cend(); ++it ) + { + pDialog = pLastDialog = *it; + if( pDialog && !pDialog->m_Controls.empty() ) + { + pControl = pDialog->m_Controls[ 0 ]; + break; + } + } + + if( !pDialog || !pControl ) + { + // No dialog has been registered yet or no controls have been + // added to the dialogs. Cannot proceed. + return true; + } + } + else + { + // Search for the first control from the end of the dialog + // array. + for( auto it = m_pManager->m_Dialogs.crbegin(); it != m_pManager->m_Dialogs.crend(); ++it ) + { + pDialog = pLastDialog = *it; + if( pDialog && !pDialog->m_Controls.empty() ) + { + pControl = pDialog->m_Controls[ pDialog->m_Controls.size() - 1 ]; + break; + } + } + + if( !pDialog || !pControl ) + { + // No dialog has been registered yet or no controls have been + // added to the dialogs. Cannot proceed. + return true; + } + } + } + else if( s_pControlFocus->m_pDialog != this ) + { + // If a control belonging to another dialog has focus, let that other + // dialog handle this event by returning false. + // + return false; + } + else + { + // Focused control belongs to this dialog. Cycle to the + // next/previous control. + assert( pControl != 0 ); + _Analysis_assume_( pControl != 0 ); + pLastDialog = s_pControlFocus->m_pDialog; + pControl = ( bForward ) ? GetNextControl( s_pControlFocus ) : GetPrevControl( s_pControlFocus ); + pDialog = pControl->m_pDialog; + } + + assert( pControl != 0 ); + _Analysis_assume_( pControl != 0 ); + + for( int i = 0; i < 0xffff; i++ ) + { + // If we just wrapped from last control to first or vice versa, + // set the focused control to nullptr. This state, where no control + // has focus, allows the camera to work. + int nLastDialogIndex = -1; + auto fit = std::find( m_pManager->m_Dialogs.cbegin(), m_pManager->m_Dialogs.cend(), pLastDialog ); + if ( fit != m_pManager->m_Dialogs.cend() ) + { + nLastDialogIndex = int( fit - m_pManager->m_Dialogs.begin() ); + } + + int nDialogIndex = -1; + fit = std::find( m_pManager->m_Dialogs.cbegin(), m_pManager->m_Dialogs.cend(), pDialog ); + if ( fit != m_pManager->m_Dialogs.cend() ) + { + nDialogIndex = int( fit - m_pManager->m_Dialogs.begin() ); + } + + if( ( !bForward && nLastDialogIndex < nDialogIndex ) || + ( bForward && nDialogIndex < nLastDialogIndex ) ) + { + if( s_pControlFocus ) + s_pControlFocus->OnFocusOut(); + s_pControlFocus = nullptr; + return true; + } + + // If we've gone in a full circle then focus doesn't change + if( pControl == s_pControlFocus ) + return true; + + // If the dialog accepts keybord input and the control can have focus then + // move focus + if( pControl->m_pDialog->m_bKeyboardInput && pControl->CanHaveFocus() ) + { + if( s_pControlFocus ) + s_pControlFocus->OnFocusOut(); + s_pControlFocus = pControl; + if( s_pControlFocus ) + s_pControlFocus->OnFocusIn(); + return true; + } + + pLastDialog = pDialog; + pControl = ( bForward ) ? GetNextControl( pControl ) : GetPrevControl( pControl ); + pDialog = pControl->m_pDialog; + } + + // If we reached this point, the chain of dialogs didn't form a complete loop + DXTRACE_ERR( L"CDXUTDialog: Multiple dialogs are improperly chained together", E_FAIL ); + return false; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialog::InitDefaultElements() +{ + SetFont( 0, L"Arial", 14, FW_NORMAL ); + + CDXUTElement Element; + RECT rcTexture; + + //------------------------------------- + // Element for the caption + //------------------------------------- + m_CapElement.SetFont( 0 ); + SetRect( &rcTexture, 17, 269, 241, 287 ); + m_CapElement.SetTexture( 0, &rcTexture ); + m_CapElement.TextureColor.States[ DXUT_STATE_NORMAL ] = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + m_CapElement.FontColor.States[ DXUT_STATE_NORMAL ] = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + m_CapElement.SetFont( 0, D3DCOLOR_ARGB( 255, 255, 255, 255 ), DT_LEFT | DT_VCENTER ); + // Pre-blend as we don't need to transition the state + m_CapElement.TextureColor.Blend( DXUT_STATE_NORMAL, 10.0f ); + m_CapElement.FontColor.Blend( DXUT_STATE_NORMAL, 10.0f ); + + //------------------------------------- + // CDXUTStatic + //------------------------------------- + Element.SetFont( 0 ); + Element.FontColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 200, 200, 200, 200 ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_STATIC, 0, &Element ); + + + //------------------------------------- + // CDXUTButton - Button + //------------------------------------- + SetRect( &rcTexture, 0, 0, 136, 54 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0 ); + Element.TextureColor.States[ DXUT_STATE_NORMAL ] = D3DCOLOR_ARGB( 150, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_PRESSED ] = D3DCOLOR_ARGB( 200, 255, 255, 255 ); + Element.FontColor.States[ DXUT_STATE_MOUSEOVER ] = D3DCOLOR_ARGB( 255, 0, 0, 0 ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_BUTTON, 0, &Element ); + + + //------------------------------------- + // CDXUTButton - Fill layer + //------------------------------------- + SetRect( &rcTexture, 136, 0, 252, 54 ); + Element.SetTexture( 0, &rcTexture, D3DCOLOR_ARGB( 0, 255, 255, 255 ) ); + Element.TextureColor.States[ DXUT_STATE_MOUSEOVER ] = D3DCOLOR_ARGB( 160, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_PRESSED ] = D3DCOLOR_ARGB( 60, 0, 0, 0 ); + Element.TextureColor.States[ DXUT_STATE_FOCUS ] = D3DCOLOR_ARGB( 30, 255, 255, 255 ); + + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_BUTTON, 1, &Element ); + + + //------------------------------------- + // CDXUTCheckBox - Box + //------------------------------------- + SetRect( &rcTexture, 0, 54, 27, 81 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 255, 255, 255 ), DT_LEFT | DT_VCENTER ); + Element.FontColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 200, 200, 200, 200 ); + Element.TextureColor.States[ DXUT_STATE_NORMAL ] = D3DCOLOR_ARGB( 150, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_FOCUS ] = D3DCOLOR_ARGB( 200, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_PRESSED ] = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_CHECKBOX, 0, &Element ); + + + //------------------------------------- + // CDXUTCheckBox - Check + //------------------------------------- + SetRect( &rcTexture, 27, 54, 54, 81 ); + Element.SetTexture( 0, &rcTexture ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_CHECKBOX, 1, &Element ); + + + //------------------------------------- + // CDXUTRadioButton - Box + //------------------------------------- + SetRect( &rcTexture, 54, 54, 81, 81 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 255, 255, 255 ), DT_LEFT | DT_VCENTER ); + Element.FontColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 200, 200, 200, 200 ); + Element.TextureColor.States[ DXUT_STATE_NORMAL ] = D3DCOLOR_ARGB( 150, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_FOCUS ] = D3DCOLOR_ARGB( 200, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_PRESSED ] = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_RADIOBUTTON, 0, &Element ); + + + //------------------------------------- + // CDXUTRadioButton - Check + //------------------------------------- + SetRect( &rcTexture, 81, 54, 108, 81 ); + Element.SetTexture( 0, &rcTexture ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_RADIOBUTTON, 1, &Element ); + + + //------------------------------------- + // CDXUTComboBox - Main + //------------------------------------- + SetRect( &rcTexture, 7, 81, 247, 123 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0 ); + Element.TextureColor.States[ DXUT_STATE_NORMAL ] = D3DCOLOR_ARGB( 150, 200, 200, 200 ); + Element.TextureColor.States[ DXUT_STATE_FOCUS ] = D3DCOLOR_ARGB( 170, 230, 230, 230 ); + Element.TextureColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 70, 200, 200, 200 ); + Element.FontColor.States[ DXUT_STATE_MOUSEOVER ] = D3DCOLOR_ARGB( 255, 0, 0, 0 ); + Element.FontColor.States[ DXUT_STATE_PRESSED ] = D3DCOLOR_ARGB( 255, 0, 0, 0 ); + Element.FontColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 200, 200, 200, 200 ); + + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_COMBOBOX, 0, &Element ); + + + //------------------------------------- + // CDXUTComboBox - Button + //------------------------------------- + SetRect( &rcTexture, 98, 189, 151, 238 ); + Element.SetTexture( 0, &rcTexture ); + Element.TextureColor.States[ DXUT_STATE_NORMAL ] = D3DCOLOR_ARGB( 150, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_PRESSED ] = D3DCOLOR_ARGB( 255, 150, 150, 150 ); + Element.TextureColor.States[ DXUT_STATE_FOCUS ] = D3DCOLOR_ARGB( 200, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 70, 255, 255, 255 ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_COMBOBOX, 1, &Element ); + + + //------------------------------------- + // CDXUTComboBox - Dropdown + //------------------------------------- + SetRect( &rcTexture, 13, 123, 241, 160 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 0, 0, 0 ), DT_LEFT | DT_TOP ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_COMBOBOX, 2, &Element ); + + + //------------------------------------- + // CDXUTComboBox - Selection + //------------------------------------- + SetRect( &rcTexture, 12, 163, 239, 183 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 255, 255, 255 ), DT_LEFT | DT_TOP ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_COMBOBOX, 3, &Element ); + + + //------------------------------------- + // CDXUTSlider - Track + //------------------------------------- + SetRect( &rcTexture, 1, 187, 93, 228 ); + Element.SetTexture( 0, &rcTexture ); + Element.TextureColor.States[ DXUT_STATE_NORMAL ] = D3DCOLOR_ARGB( 150, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_FOCUS ] = D3DCOLOR_ARGB( 200, 255, 255, 255 ); + Element.TextureColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 70, 255, 255, 255 ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_SLIDER, 0, &Element ); + + //------------------------------------- + // CDXUTSlider - Button + //------------------------------------- + SetRect( &rcTexture, 151, 193, 192, 234 ); + Element.SetTexture( 0, &rcTexture ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_SLIDER, 1, &Element ); + + //------------------------------------- + // CDXUTScrollBar - Track + //------------------------------------- + int nScrollBarStartX = 196; + int nScrollBarStartY = 191; + SetRect( &rcTexture, nScrollBarStartX + 0, nScrollBarStartY + 21, nScrollBarStartX + 22, nScrollBarStartY + 32 ); + Element.SetTexture( 0, &rcTexture ); + Element.TextureColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 255, 200, 200, 200 ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_SCROLLBAR, 0, &Element ); + + //------------------------------------- + // CDXUTScrollBar - Up Arrow + //------------------------------------- + SetRect( &rcTexture, nScrollBarStartX + 0, nScrollBarStartY + 1, nScrollBarStartX + 22, nScrollBarStartY + 21 ); + Element.SetTexture( 0, &rcTexture ); + Element.TextureColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 255, 200, 200, 200 ); + + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_SCROLLBAR, 1, &Element ); + + //------------------------------------- + // CDXUTScrollBar - Down Arrow + //------------------------------------- + SetRect( &rcTexture, nScrollBarStartX + 0, nScrollBarStartY + 32, nScrollBarStartX + 22, nScrollBarStartY + 53 ); + Element.SetTexture( 0, &rcTexture ); + Element.TextureColor.States[ DXUT_STATE_DISABLED ] = D3DCOLOR_ARGB( 255, 200, 200, 200 ); + + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_SCROLLBAR, 2, &Element ); + + //------------------------------------- + // CDXUTScrollBar - Button + //------------------------------------- + SetRect( &rcTexture, 220, 192, 238, 234 ); + Element.SetTexture( 0, &rcTexture ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_SCROLLBAR, 3, &Element ); + + + //------------------------------------- + // CDXUTEditBox + //------------------------------------- + // Element assignment: + // 0 - text area + // 1 - top left border + // 2 - top border + // 3 - top right border + // 4 - left border + // 5 - right border + // 6 - lower left border + // 7 - lower border + // 8 - lower right border + + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 0, 0, 0 ), DT_LEFT | DT_TOP ); + + // Assign the style + SetRect( &rcTexture, 14, 90, 241, 113 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 0, &Element ); + SetRect( &rcTexture, 8, 82, 14, 90 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 1, &Element ); + SetRect( &rcTexture, 14, 82, 241, 90 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 2, &Element ); + SetRect( &rcTexture, 241, 82, 246, 90 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 3, &Element ); + SetRect( &rcTexture, 8, 90, 14, 113 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 4, &Element ); + SetRect( &rcTexture, 241, 90, 246, 113 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 5, &Element ); + SetRect( &rcTexture, 8, 113, 14, 121 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 6, &Element ); + SetRect( &rcTexture, 14, 113, 241, 121 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 7, &Element ); + SetRect( &rcTexture, 241, 113, 246, 121 ); + Element.SetTexture( 0, &rcTexture ); + SetDefaultElement( DXUT_CONTROL_EDITBOX, 8, &Element ); + + //------------------------------------- + // CDXUTListBox - Main + //------------------------------------- + SetRect( &rcTexture, 13, 123, 241, 160 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 0, 0, 0 ), DT_LEFT | DT_TOP ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_LISTBOX, 0, &Element ); + + //------------------------------------- + // CDXUTListBox - Selection + //------------------------------------- + + SetRect( &rcTexture, 16, 166, 240, 183 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 255, 255, 255 ), DT_LEFT | DT_TOP ); + + // Assign the Element + SetDefaultElement( DXUT_CONTROL_LISTBOX, 1, &Element ); +} + + +//====================================================================================== +// CDXUTDialogResourceManager +//====================================================================================== + +//-------------------------------------------------------------------------------------- +CDXUTDialogResourceManager::CDXUTDialogResourceManager() noexcept : + m_pVSRenderUI11(nullptr), + m_pPSRenderUI11(nullptr), + m_pPSRenderUIUntex11(nullptr), + m_pDepthStencilStateUI11(nullptr), + m_pRasterizerStateUI11(nullptr), + m_pBlendStateUI11(nullptr), + m_pSamplerStateUI11(nullptr), + m_pDepthStencilStateStored11(nullptr), + m_StencilRefStored11(0), + m_pRasterizerStateStored11(nullptr), + m_pBlendStateStored11(nullptr), + m_BlendFactorStored11{}, + m_SampleMaskStored11(0), + m_pSamplerStateStored11(nullptr), + m_pInputLayout11(nullptr), + m_pVBScreenQuad11(nullptr), + m_pSpriteBuffer11(nullptr), + m_SpriteBufferBytes11(0), + m_nBackBufferWidth(0), + m_nBackBufferHeight(0), + m_pd3d11Device(nullptr), + m_pd3d11DeviceContext(nullptr) +{ +} + + +//-------------------------------------------------------------------------------------- +CDXUTDialogResourceManager::~CDXUTDialogResourceManager() +{ + for( auto it = m_FontCache.begin(); it != m_FontCache.end(); ++it ) + { + SAFE_DELETE( *it ); + } + m_FontCache.clear(); + + for( auto it = m_TextureCache.begin(); it != m_TextureCache.end(); ++it ) + { + SAFE_DELETE( *it ); + } + m_TextureCache.clear(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTDialogResourceManager::MsgProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(hWnd); + UNREFERENCED_PARAMETER(uMsg); + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + return false; +} + + +_Use_decl_annotations_ +HRESULT CDXUTDialogResourceManager::OnD3D11CreateDevice( ID3D11Device* pd3dDevice, ID3D11DeviceContext* pd3d11DeviceContext ) +{ + m_pd3d11Device = pd3dDevice; + m_pd3d11DeviceContext = pd3d11DeviceContext; + + HRESULT hr = S_OK; + + // Compile Shaders + ID3DBlob* pVSBlob = nullptr; + ID3DBlob* pPSBlob = nullptr; + ID3DBlob* pPSUntexBlob = nullptr; + V_RETURN( D3DCompile( g_strUIEffectFile, g_uUIEffectFileSize, "none", nullptr, nullptr, "VS", "vs_4_0_level_9_1", + D3D10_SHADER_ENABLE_BACKWARDS_COMPATIBILITY, 0, &pVSBlob, nullptr ) ); + V_RETURN( D3DCompile( g_strUIEffectFile, g_uUIEffectFileSize, "none", nullptr, nullptr, "PS", "ps_4_0_level_9_1", + D3D10_SHADER_ENABLE_BACKWARDS_COMPATIBILITY, 0, &pPSBlob, nullptr ) ); + V_RETURN( D3DCompile( g_strUIEffectFile, g_uUIEffectFileSize, "none", nullptr, nullptr, "PSUntex", "ps_4_0_level_9_1", + D3D10_SHADER_ENABLE_BACKWARDS_COMPATIBILITY, 0, &pPSUntexBlob, nullptr ) ); + + // Create Shaders + V_RETURN( pd3dDevice->CreateVertexShader( pVSBlob->GetBufferPointer(), pVSBlob->GetBufferSize(), nullptr, &m_pVSRenderUI11 ) ); + DXUT_SetDebugName( m_pVSRenderUI11, "CDXUTDialogResourceManager" ); + + V_RETURN( pd3dDevice->CreatePixelShader( pPSBlob->GetBufferPointer(), pPSBlob->GetBufferSize(), nullptr, &m_pPSRenderUI11 ) ); + DXUT_SetDebugName( m_pPSRenderUI11, "CDXUTDialogResourceManager" ); + + V_RETURN( pd3dDevice->CreatePixelShader( pPSUntexBlob->GetBufferPointer(), pPSUntexBlob->GetBufferSize(), nullptr, &m_pPSRenderUIUntex11 ) ); + DXUT_SetDebugName( m_pPSRenderUIUntex11, "CDXUTDialogResourceManager" ); + + // States + D3D11_DEPTH_STENCIL_DESC DSDesc = {}; + DSDesc.DepthEnable = FALSE; + DSDesc.DepthWriteMask = D3D11_DEPTH_WRITE_MASK_ALL; + DSDesc.DepthFunc = D3D11_COMPARISON_LESS; + DSDesc.StencilEnable = FALSE; + V_RETURN( pd3dDevice->CreateDepthStencilState( &DSDesc, &m_pDepthStencilStateUI11 ) ); + DXUT_SetDebugName( m_pDepthStencilStateUI11, "CDXUTDialogResourceManager" ); + + D3D11_RASTERIZER_DESC RSDesc; + RSDesc.AntialiasedLineEnable = FALSE; + RSDesc.CullMode = D3D11_CULL_BACK; + RSDesc.DepthBias = 0; + RSDesc.DepthBiasClamp = 0.0f; + RSDesc.DepthClipEnable = TRUE; + RSDesc.FillMode = D3D11_FILL_SOLID; + RSDesc.FrontCounterClockwise = FALSE; + RSDesc.MultisampleEnable = TRUE; + RSDesc.ScissorEnable = FALSE; + RSDesc.SlopeScaledDepthBias = 0.0f; + V_RETURN( pd3dDevice->CreateRasterizerState( &RSDesc, &m_pRasterizerStateUI11 ) ); + DXUT_SetDebugName( m_pRasterizerStateUI11, "CDXUTDialogResourceManager" ); + + D3D11_BLEND_DESC BSDesc = {}; + BSDesc.RenderTarget[0].BlendEnable = TRUE; + BSDesc.RenderTarget[0].SrcBlend = D3D11_BLEND_SRC_ALPHA; + BSDesc.RenderTarget[0].DestBlend = D3D11_BLEND_INV_SRC_ALPHA; + BSDesc.RenderTarget[0].BlendOp = D3D11_BLEND_OP_ADD; + BSDesc.RenderTarget[0].SrcBlendAlpha = D3D11_BLEND_ONE; + BSDesc.RenderTarget[0].DestBlendAlpha = D3D11_BLEND_ZERO; + BSDesc.RenderTarget[0].BlendOpAlpha = D3D11_BLEND_OP_ADD; + BSDesc.RenderTarget[0].RenderTargetWriteMask = 0x0F; + + V_RETURN( pd3dDevice->CreateBlendState( &BSDesc, &m_pBlendStateUI11 ) ); + DXUT_SetDebugName( m_pBlendStateUI11, "CDXUTDialogResourceManager" ); + + D3D11_SAMPLER_DESC SSDesc = {}; + SSDesc.Filter = D3D11_FILTER_ANISOTROPIC ; + SSDesc.AddressU = D3D11_TEXTURE_ADDRESS_WRAP; + SSDesc.AddressV = D3D11_TEXTURE_ADDRESS_WRAP; + SSDesc.AddressW = D3D11_TEXTURE_ADDRESS_WRAP; + SSDesc.ComparisonFunc = D3D11_COMPARISON_NEVER; + SSDesc.MaxAnisotropy = 16; + SSDesc.MinLOD = 0; + SSDesc.MaxLOD = D3D11_FLOAT32_MAX; + if ( pd3dDevice->GetFeatureLevel() < D3D_FEATURE_LEVEL_9_3 ) + { + SSDesc.Filter = D3D11_FILTER_MIN_MAG_MIP_LINEAR; + SSDesc.MaxAnisotropy = 0; + } + V_RETURN( pd3dDevice->CreateSamplerState( &SSDesc, &m_pSamplerStateUI11 ) ); + DXUT_SetDebugName( m_pSamplerStateUI11, "CDXUTDialogResourceManager" ); + + // Create the texture objects in the cache arrays. + for( size_t i = 0; i < m_TextureCache.size(); i++ ) + { + hr = CreateTexture11( static_cast( i ) ); + if( FAILED( hr ) ) + return hr; + } + + // Create input layout + const D3D11_INPUT_ELEMENT_DESC layout[] = + { + { "POSITION", 0, DXGI_FORMAT_R32G32B32_FLOAT, 0, 0, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "COLOR", 0, DXGI_FORMAT_R32G32B32A32_FLOAT, 0, 12, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + { "TEXCOORD", 0, DXGI_FORMAT_R32G32_FLOAT, 0, 28, D3D11_INPUT_PER_VERTEX_DATA, 0 }, + }; + + V_RETURN( pd3dDevice->CreateInputLayout( layout, ARRAYSIZE( layout ), pVSBlob->GetBufferPointer(), pVSBlob->GetBufferSize(), &m_pInputLayout11 ) ); + DXUT_SetDebugName( m_pInputLayout11, "CDXUTDialogResourceManager" ); + + // Release the blobs + SAFE_RELEASE( pVSBlob ); + SAFE_RELEASE( pPSBlob ); + SAFE_RELEASE( pPSUntexBlob ); + + // Create a vertex buffer quad for rendering later + D3D11_BUFFER_DESC BufDesc; + BufDesc.ByteWidth = sizeof( DXUT_SCREEN_VERTEX_10 ) * 4; + BufDesc.Usage = D3D11_USAGE_DYNAMIC; + BufDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER; + BufDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + BufDesc.MiscFlags = 0; + V_RETURN( pd3dDevice->CreateBuffer( &BufDesc, nullptr, &m_pVBScreenQuad11 ) ); + DXUT_SetDebugName( m_pVBScreenQuad11, "CDXUTDialogResourceManager" ); + + // Init the D3D11 font + InitFont11( pd3dDevice, m_pInputLayout11 ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTDialogResourceManager::OnD3D11ResizedSwapChain( ID3D11Device* pd3dDevice, + const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ) +{ + UNREFERENCED_PARAMETER(pd3dDevice); + + HRESULT hr = S_OK; + + m_nBackBufferWidth = pBackBufferSurfaceDesc->Width; + m_nBackBufferHeight = pBackBufferSurfaceDesc->Height; + + return hr; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::OnD3D11ReleasingSwapChain() +{ +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::OnD3D11DestroyDevice() +{ + // Release the resources but don't clear the cache, as these will need to be + // recreated if the device is recreated + + for( auto it = m_TextureCache.begin(); it != m_TextureCache.end(); ++it ) + { + SAFE_RELEASE( (*it)->pTexResView11 ); + SAFE_RELEASE( (*it)->pTexture11 ); + } + + // D3D11 + SAFE_RELEASE( m_pVBScreenQuad11 ); + SAFE_RELEASE( m_pSpriteBuffer11 ); + m_SpriteBufferBytes11 = 0; + SAFE_RELEASE( m_pInputLayout11 ); + + // Shaders + SAFE_RELEASE( m_pVSRenderUI11 ); + SAFE_RELEASE( m_pPSRenderUI11 ); + SAFE_RELEASE( m_pPSRenderUIUntex11 ); + + // States + SAFE_RELEASE( m_pDepthStencilStateUI11 ); + SAFE_RELEASE( m_pRasterizerStateUI11 ); + SAFE_RELEASE( m_pBlendStateUI11 ); + SAFE_RELEASE( m_pSamplerStateUI11 ); + + SAFE_RELEASE( m_pDepthStencilStateStored11 ); + SAFE_RELEASE( m_pRasterizerStateStored11 ); + SAFE_RELEASE( m_pBlendStateStored11 ); + SAFE_RELEASE( m_pSamplerStateStored11 ); + + EndFont11(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::StoreD3D11State( _In_ ID3D11DeviceContext* pd3dImmediateContext ) +{ + pd3dImmediateContext->OMGetDepthStencilState( &m_pDepthStencilStateStored11, &m_StencilRefStored11 ); + pd3dImmediateContext->RSGetState( &m_pRasterizerStateStored11 ); + pd3dImmediateContext->OMGetBlendState( &m_pBlendStateStored11, m_BlendFactorStored11, &m_SampleMaskStored11 ); + pd3dImmediateContext->PSGetSamplers( 0, 1, &m_pSamplerStateStored11 ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::RestoreD3D11State( _In_ ID3D11DeviceContext* pd3dImmediateContext ) +{ + pd3dImmediateContext->OMSetDepthStencilState( m_pDepthStencilStateStored11, m_StencilRefStored11 ); + pd3dImmediateContext->RSSetState( m_pRasterizerStateStored11 ); + pd3dImmediateContext->OMSetBlendState( m_pBlendStateStored11, m_BlendFactorStored11, m_SampleMaskStored11 ); + pd3dImmediateContext->PSSetSamplers( 0, 1, &m_pSamplerStateStored11 ); + + SAFE_RELEASE( m_pDepthStencilStateStored11 ); + SAFE_RELEASE( m_pRasterizerStateStored11 ); + SAFE_RELEASE( m_pBlendStateStored11 ); + SAFE_RELEASE( m_pSamplerStateStored11 ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::ApplyRenderUI11( _In_ ID3D11DeviceContext* pd3dImmediateContext ) +{ + // Shaders + pd3dImmediateContext->VSSetShader( m_pVSRenderUI11, nullptr, 0 ); + pd3dImmediateContext->HSSetShader( nullptr, nullptr, 0 ); + pd3dImmediateContext->DSSetShader( nullptr, nullptr, 0 ); + pd3dImmediateContext->GSSetShader( nullptr, nullptr, 0 ); + pd3dImmediateContext->PSSetShader( m_pPSRenderUI11, nullptr, 0 ); + + // States + pd3dImmediateContext->OMSetDepthStencilState( m_pDepthStencilStateUI11, 0 ); + pd3dImmediateContext->RSSetState( m_pRasterizerStateUI11 ); + float BlendFactor[4] = { 0, 0, 0, 0 }; + pd3dImmediateContext->OMSetBlendState( m_pBlendStateUI11, BlendFactor, 0xFFFFFFFF ); + pd3dImmediateContext->PSSetSamplers( 0, 1, &m_pSamplerStateUI11 ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::ApplyRenderUIUntex11( _In_ ID3D11DeviceContext* pd3dImmediateContext ) +{ + // Shaders + pd3dImmediateContext->VSSetShader( m_pVSRenderUI11, nullptr, 0 ); + pd3dImmediateContext->HSSetShader( nullptr, nullptr, 0 ); + pd3dImmediateContext->DSSetShader( nullptr, nullptr, 0 ); + pd3dImmediateContext->GSSetShader( nullptr, nullptr, 0 ); + pd3dImmediateContext->PSSetShader( m_pPSRenderUIUntex11, nullptr, 0 ); + + // States + pd3dImmediateContext->OMSetDepthStencilState( m_pDepthStencilStateUI11, 0 ); + pd3dImmediateContext->RSSetState( m_pRasterizerStateUI11 ); + float BlendFactor[4] = { 0, 0, 0, 0 }; + pd3dImmediateContext->OMSetBlendState( m_pBlendStateUI11, BlendFactor, 0xFFFFFFFF ); + pd3dImmediateContext->PSSetSamplers( 0, 1, &m_pSamplerStateUI11 ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::BeginSprites11( ) +{ + m_SpriteVertices.clear(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTDialogResourceManager::EndSprites11( ID3D11Device* pd3dDevice, ID3D11DeviceContext* pd3dImmediateContext ) +{ + + // ensure our buffer size can hold our sprites + UINT SpriteDataBytes = static_cast( m_SpriteVertices.size() * sizeof( DXUTSpriteVertex ) ); + if( m_SpriteBufferBytes11 < SpriteDataBytes ) + { + SAFE_RELEASE( m_pSpriteBuffer11 ); + m_SpriteBufferBytes11 = SpriteDataBytes; + + D3D11_BUFFER_DESC BufferDesc; + BufferDesc.ByteWidth = m_SpriteBufferBytes11; + BufferDesc.Usage = D3D11_USAGE_DYNAMIC; + BufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER; + BufferDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + BufferDesc.MiscFlags = 0; + + if ( FAILED(pd3dDevice->CreateBuffer(&BufferDesc, nullptr, &m_pSpriteBuffer11)) ) + { + m_pSpriteBuffer11 = nullptr; + m_SpriteBufferBytes11 = 0; + return; + } + DXUT_SetDebugName( m_pSpriteBuffer11, "CDXUTDialogResourceManager" ); + } + + // Copy the sprites over + D3D11_BOX destRegion; + destRegion.left = 0; + destRegion.right = SpriteDataBytes; + destRegion.top = 0; + destRegion.bottom = 1; + destRegion.front = 0; + destRegion.back = 1; + D3D11_MAPPED_SUBRESOURCE MappedResource; + if ( S_OK == pd3dImmediateContext->Map( m_pSpriteBuffer11, 0, D3D11_MAP_WRITE_DISCARD, 0, &MappedResource ) ) + { + memcpy( MappedResource.pData, (const void*)&m_SpriteVertices[0], SpriteDataBytes ); + pd3dImmediateContext->Unmap(m_pSpriteBuffer11, 0); + } + + // Draw + UINT Stride = sizeof( DXUTSpriteVertex ); + UINT Offset = 0; + pd3dImmediateContext->IASetVertexBuffers( 0, 1, &m_pSpriteBuffer11, &Stride, &Offset ); + pd3dImmediateContext->IASetInputLayout( m_pInputLayout11 ); + pd3dImmediateContext->IASetPrimitiveTopology( D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST ); + pd3dImmediateContext->Draw( static_cast( m_SpriteVertices.size() ), 0 ); + + m_SpriteVertices.clear(); +} + + +//-------------------------------------------------------------------------------------- +bool CDXUTDialogResourceManager::RegisterDialog( _In_ CDXUTDialog* pDialog ) +{ + // Check that the dialog isn't already registered. + for( auto it = m_Dialogs.cbegin(); it != m_Dialogs.cend(); ++it ) + { + if( *it == pDialog ) + return true; + } + + // Add to the list. + m_Dialogs.push_back( pDialog ); + + // Set up next and prev pointers. + if( m_Dialogs.size() > 1 ) + m_Dialogs[m_Dialogs.size() - 2]->SetNextDialog( pDialog ); + m_Dialogs[m_Dialogs.size() - 1]->SetNextDialog( m_Dialogs[0] ); + + return true; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::UnregisterDialog( _In_ CDXUTDialog* pDialog ) +{ + // Search for the dialog in the list. + for( size_t i = 0; i < m_Dialogs.size(); ++i ) + { + if( m_Dialogs[ i ] == pDialog ) + { + m_Dialogs.erase( m_Dialogs.begin() + i ); + if( !m_Dialogs.empty() ) + { + int l, r; + + if( 0 == i ) + l = int( m_Dialogs.size() - 1 ); + else + l = int(i) - 1; + + if( m_Dialogs.size() == i ) + r = 0; + else + r = int( i ); + + m_Dialogs[l]->SetNextDialog( m_Dialogs[r] ); + } + return; + } + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTDialogResourceManager::EnableKeyboardInputForAllDialogs() +{ + // Enable keyboard input for all registered dialogs + for( auto it = m_Dialogs.begin(); it != m_Dialogs.end(); ++it ) + (*it)->EnableKeyboardInput( true ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +int CDXUTDialogResourceManager::AddFont( LPCWSTR strFaceName, LONG height, LONG weight ) +{ + // See if this font already exists + for( size_t i = 0; i < m_FontCache.size(); ++i ) + { + auto pFontNode = m_FontCache[ i ]; + size_t nLen = 0; + nLen = wcsnlen( strFaceName, MAX_PATH); + if( 0 == _wcsnicmp( pFontNode->strFace, strFaceName, nLen ) && + pFontNode->nHeight == height && + pFontNode->nWeight == weight ) + { + return static_cast( i ); + } + } + + // Add a new font and try to create it + auto pNewFontNode = new (std::nothrow) DXUTFontNode; + if( !pNewFontNode ) + return -1; + + ZeroMemory( pNewFontNode, sizeof( DXUTFontNode ) ); + wcscpy_s( pNewFontNode->strFace, MAX_PATH, strFaceName ); + pNewFontNode->nHeight = height; + pNewFontNode->nWeight = weight; + m_FontCache.push_back( pNewFontNode ); + + int iFont = (int)m_FontCache.size() - 1; + + // If a device is available, try to create immediately + return iFont; +} + + +//-------------------------------------------------------------------------------------- +int CDXUTDialogResourceManager::AddTexture( _In_z_ LPCWSTR strFilename ) +{ + // See if this texture already exists + for( size_t i = 0; i < m_TextureCache.size(); ++i ) + { + auto pTextureNode = m_TextureCache[ i ]; + size_t nLen = 0; + nLen = wcsnlen( strFilename, MAX_PATH); + if( pTextureNode->bFileSource && // Sources must match + 0 == _wcsnicmp( pTextureNode->strFilename, strFilename, nLen ) ) + { + return static_cast( i ); + } + } + + // Add a new texture and try to create it + auto pNewTextureNode = new (std::nothrow) DXUTTextureNode; + if( !pNewTextureNode ) + return -1; + + ZeroMemory( pNewTextureNode, sizeof( DXUTTextureNode ) ); + pNewTextureNode->bFileSource = true; + wcscpy_s( pNewTextureNode->strFilename, MAX_PATH, strFilename ); + + m_TextureCache.push_back( pNewTextureNode ); + + int iTexture = int( m_TextureCache.size() ) - 1; + + // If a device is available, try to create immediately + + return iTexture; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +int CDXUTDialogResourceManager::AddTexture( LPCWSTR strResourceName, HMODULE hResourceModule ) +{ + // See if this texture already exists + for( size_t i = 0; i < m_TextureCache.size(); i++ ) + { + auto pTextureNode = m_TextureCache[ i ]; + if( !pTextureNode->bFileSource && // Sources must match + pTextureNode->hResourceModule == hResourceModule ) // Module handles must match + { + if( IS_INTRESOURCE( strResourceName ) ) + { + // Integer-based ID + if( ( INT_PTR )strResourceName == pTextureNode->nResourceID ) + return static_cast( i ); + } + else + { + // String-based ID + size_t nLen = 0; + nLen = wcsnlen ( strResourceName, MAX_PATH ); + if( 0 == _wcsnicmp( pTextureNode->strFilename, strResourceName, nLen ) ) + return static_cast( i ); + } + } + } + + // Add a new texture and try to create it + auto pNewTextureNode = new (std::nothrow) DXUTTextureNode; + if( !pNewTextureNode ) + return -1; + + ZeroMemory( pNewTextureNode, sizeof( DXUTTextureNode ) ); + pNewTextureNode->hResourceModule = hResourceModule; + if( IS_INTRESOURCE( strResourceName ) ) + { + pNewTextureNode->nResourceID = ( int )( size_t )strResourceName; + } + else + { + pNewTextureNode->nResourceID = 0; + wcscpy_s( pNewTextureNode->strFilename, MAX_PATH, strResourceName ); + } + + m_TextureCache.push_back( pNewTextureNode ); + + int iTexture = int( m_TextureCache.size() ) - 1; + + // If a device is available, try to create immediately + + return iTexture; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTDialogResourceManager::CreateTexture11( _In_ UINT iTexture ) +{ + HRESULT hr = S_OK; + + auto pTextureNode = m_TextureCache[ iTexture ]; + + if( !pTextureNode->bFileSource ) + { + if( pTextureNode->nResourceID == 0xFFFF && pTextureNode->hResourceModule == ( HMODULE )0xFFFF ) + { + hr = DXUTCreateGUITextureFromInternalArray( m_pd3d11Device, &pTextureNode->pTexture11 ); + if( FAILED( hr ) ) + return DXTRACE_ERR( L"DXUTCreateGUITextureFromInternalArray", hr ); + DXUT_SetDebugName( pTextureNode->pTexture11, "DXUT GUI Texture" ); + } + } + + // Store dimensions + D3D11_TEXTURE2D_DESC desc; + pTextureNode->pTexture11->GetDesc( &desc ); + pTextureNode->dwWidth = desc.Width; + pTextureNode->dwHeight = desc.Height; + + // Create resource view + D3D11_SHADER_RESOURCE_VIEW_DESC SRVDesc; + SRVDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + SRVDesc.Format = desc.Format; + SRVDesc.Texture2D.MipLevels = 1; + SRVDesc.Texture2D.MostDetailedMip = 0; + hr = m_pd3d11Device->CreateShaderResourceView( pTextureNode->pTexture11, &SRVDesc, &pTextureNode->pTexResView11 ); + if ( FAILED(hr) ) + return hr; + + DXUT_SetDebugName( pTextureNode->pTexResView11, "DXUT GUI Texture" ); + + return hr; +} + + +//====================================================================================== +// CDXUTControl class +//====================================================================================== + +CDXUTControl::CDXUTControl( _In_opt_ CDXUTDialog* pDialog ) noexcept +{ + m_Type = DXUT_CONTROL_BUTTON; + m_pDialog = pDialog; + m_ID = 0; + m_nHotkey = 0; + m_Index = 0; + m_pUserData = nullptr; + + m_bEnabled = true; + m_bVisible = true; + m_bMouseOver = false; + m_bHasFocus = false; + m_bIsDefault = false; + + m_pDialog = nullptr; + + m_x = 0; + m_y = 0; + m_width = 0; + m_height = 0; + + ZeroMemory( &m_rcBoundingBox, sizeof( m_rcBoundingBox ) ); +} + + +//-------------------------------------------------------------------------------------- +CDXUTControl::~CDXUTControl() +{ + for( auto it = m_Elements.begin(); it != m_Elements.end(); ++it ) + { + auto pElement = *it; + delete pElement; + } + m_Elements.clear(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTControl::SetTextColor( _In_ DWORD Color ) +{ + auto pElement = m_Elements[ 0 ]; + + if( pElement ) + pElement->FontColor.States[DXUT_STATE_NORMAL] = Color; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTControl::SetElement( _In_ UINT iElement, _In_ CDXUTElement* pElement ) +{ + if( !pElement ) + return E_INVALIDARG; + + // Make certain the array is this large + for( size_t i = m_Elements.size(); i <= iElement; i++ ) + { + auto pNewElement = new (std::nothrow) CDXUTElement(); + if( !pNewElement ) + return E_OUTOFMEMORY; + + m_Elements.push_back( pNewElement ); + } + + // Update the data + auto pCurElement = m_Elements[ iElement ]; + *pCurElement = *pElement; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTControl::Refresh() +{ + m_bMouseOver = false; + m_bHasFocus = false; + + for( auto it = m_Elements.begin(); it != m_Elements.end(); ++it ) + { + (*it)->Refresh(); + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTControl::UpdateRects() +{ + SetRect( &m_rcBoundingBox, m_x, m_y, m_x + m_width, m_y + m_height ); +} + + +//====================================================================================== +// CDXUTStatic class +//====================================================================================== + +//-------------------------------------------------------------------------------------- +CDXUTStatic::CDXUTStatic( _In_opt_ CDXUTDialog* pDialog ) noexcept +{ + m_Type = DXUT_CONTROL_STATIC; + m_pDialog = pDialog; + + ZeroMemory( &m_strText, sizeof( m_strText ) ); + + for( auto it = m_Elements.begin(); it != m_Elements.end(); ++it ) + { + auto pElement = *it; + SAFE_DELETE( pElement ); + } + + m_Elements.clear(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTStatic::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + + DXUT_CONTROL_STATE iState = DXUT_STATE_NORMAL; + + if( m_bEnabled == false ) + iState = DXUT_STATE_DISABLED; + + auto pElement = m_Elements[ 0 ]; + + pElement->FontColor.Blend( iState, fElapsedTime ); + + m_pDialog->DrawText( m_strText, pElement, &m_rcBoundingBox, false, false); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTStatic::GetTextCopy( LPWSTR strDest, UINT bufferCount ) const +{ + // Validate incoming parameters + if( !strDest || bufferCount == 0 ) + { + return E_INVALIDARG; + } + + // Copy the window text + wcscpy_s( strDest, bufferCount, m_strText ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTStatic::SetText( _In_z_ LPCWSTR strText ) +{ + if( !strText ) + { + m_strText[0] = 0; + return S_OK; + } + + wcscpy_s( m_strText, MAX_PATH, strText ); + return S_OK; +} + + +//====================================================================================== +// CDXUTButton class +//====================================================================================== + +CDXUTButton::CDXUTButton( _In_opt_ CDXUTDialog* pDialog ) noexcept +{ + m_Type = DXUT_CONTROL_BUTTON; + m_pDialog = pDialog; + + m_bPressed = false; + m_nHotkey = 0; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTButton::HandleKeyboard( UINT uMsg, WPARAM wParam, LPARAM lParam ) + +{ + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_KEYDOWN: + { + switch( wParam ) + { + case VK_SPACE: + m_bPressed = true; + return true; + } + } + + case WM_KEYUP: + { + switch( wParam ) + { + case VK_SPACE: + if( m_bPressed == true ) + { + m_bPressed = false; + m_pDialog->SendEvent( EVENT_BUTTON_CLICKED, true, this ); + } + return true; + } + } + } + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTButton::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + { + if( ContainsPoint( pt ) ) + { + // Pressed while inside the control + m_bPressed = true; + SetCapture( DXUTGetHWND() ); + + if( !m_bHasFocus ) + m_pDialog->RequestFocus( this ); + + return true; + } + + break; + } + + case WM_LBUTTONUP: + { + if( m_bPressed ) + { + m_bPressed = false; + ReleaseCapture(); + + if( !m_pDialog->m_bKeyboardInput ) + m_pDialog->ClearFocus(); + + // Button click + if( ContainsPoint( pt ) ) + m_pDialog->SendEvent( EVENT_BUTTON_CLICKED, true, this ); + + return true; + } + + break; + } + }; + + return false; +} + +//-------------------------------------------------------------------------------------- +void CDXUTButton::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + + int nOffsetX = 0; + int nOffsetY = 0; + + DXUT_CONTROL_STATE iState = DXUT_STATE_NORMAL; + + if( m_bVisible == false ) + { + iState = DXUT_STATE_HIDDEN; + } + else if( m_bEnabled == false ) + { + iState = DXUT_STATE_DISABLED; + } + else if( m_bPressed ) + { + iState = DXUT_STATE_PRESSED; + + nOffsetX = 1; + nOffsetY = 2; + } + else if( m_bMouseOver ) + { + iState = DXUT_STATE_MOUSEOVER; + + nOffsetX = -1; + nOffsetY = -2; + } + else if( m_bHasFocus ) + { + iState = DXUT_STATE_FOCUS; + } + + // Background fill layer + auto pElement = m_Elements[ 0 ]; + + float fBlendRate = ( iState == DXUT_STATE_PRESSED ) ? 0.0f : 0.8f; + + RECT rcWindow = m_rcBoundingBox; + OffsetRect( &rcWindow, nOffsetX, nOffsetY ); + + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + pElement->FontColor.Blend( iState, fElapsedTime, fBlendRate ); + + m_pDialog->DrawSprite( pElement, &rcWindow, DXUT_FAR_BUTTON_DEPTH ); + m_pDialog->DrawText( m_strText, pElement, &rcWindow, false, true ); + + // Main button + pElement = m_Elements[ 1 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + pElement->FontColor.Blend( iState, fElapsedTime, fBlendRate ); + + m_pDialog->DrawSprite( pElement, &rcWindow, DXUT_NEAR_BUTTON_DEPTH ); + m_pDialog->DrawText( m_strText, pElement, &rcWindow, false, true ); +} + + + +//====================================================================================== +// CDXUTCheckBox class +//====================================================================================== + +CDXUTCheckBox::CDXUTCheckBox( _In_opt_ CDXUTDialog* pDialog ) noexcept : + m_bChecked(false), + m_rcButton{}, + m_rcText{} +{ + m_Type = DXUT_CONTROL_CHECKBOX; + m_pDialog = pDialog; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTCheckBox::HandleKeyboard( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_KEYDOWN: + { + switch( wParam ) + { + case VK_SPACE: + m_bPressed = true; + return true; + } + } + + case WM_KEYUP: + { + switch( wParam ) + { + case VK_SPACE: + if( m_bPressed == true ) + { + m_bPressed = false; + SetCheckedInternal( !m_bChecked, true ); + } + return true; + } + } + } + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTCheckBox::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + { + if( ContainsPoint( pt ) ) + { + // Pressed while inside the control + m_bPressed = true; + SetCapture( DXUTGetHWND() ); + + if( !m_bHasFocus ) + m_pDialog->RequestFocus( this ); + + return true; + } + + break; + } + + case WM_LBUTTONUP: + { + if( m_bPressed ) + { + m_bPressed = false; + ReleaseCapture(); + + // Button click + if( ContainsPoint( pt ) ) + SetCheckedInternal( !m_bChecked, true ); + + return true; + } + + break; + } + }; + + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTCheckBox::SetCheckedInternal( bool bChecked, bool bFromInput ) +{ + m_bChecked = bChecked; + + m_pDialog->SendEvent( EVENT_CHECKBOX_CHANGED, bFromInput, this ); +} + + +//-------------------------------------------------------------------------------------- +bool CDXUTCheckBox::ContainsPoint( _In_ const POINT& pt ) +{ + return ( PtInRect( &m_rcBoundingBox, pt ) || + PtInRect( &m_rcButton, pt ) ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTCheckBox::UpdateRects() +{ + CDXUTButton::UpdateRects(); + + m_rcButton = m_rcBoundingBox; + m_rcButton.right = m_rcButton.left + RectHeight( m_rcButton ); + + m_rcText = m_rcBoundingBox; + m_rcText.left += ( int )( 1.25f * RectWidth( m_rcButton ) ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTCheckBox::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + DXUT_CONTROL_STATE iState = DXUT_STATE_NORMAL; + + if( m_bVisible == false ) + iState = DXUT_STATE_HIDDEN; + else if( m_bEnabled == false ) + iState = DXUT_STATE_DISABLED; + else if( m_bPressed ) + iState = DXUT_STATE_PRESSED; + else if( m_bMouseOver ) + iState = DXUT_STATE_MOUSEOVER; + else if( m_bHasFocus ) + iState = DXUT_STATE_FOCUS; + + auto pElement = m_Elements[ 0 ]; + + float fBlendRate = ( iState == DXUT_STATE_PRESSED ) ? 0.0f : 0.8f; + + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + pElement->FontColor.Blend( iState, fElapsedTime, fBlendRate ); + + m_pDialog->DrawSprite( pElement, &m_rcButton, DXUT_NEAR_BUTTON_DEPTH ); + m_pDialog->DrawText( m_strText, pElement, &m_rcText, false, false ); + + if( !m_bChecked ) + iState = DXUT_STATE_HIDDEN; + + pElement = m_Elements[ 1 ]; + + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + m_pDialog->DrawSprite( pElement, &m_rcButton, DXUT_FAR_BUTTON_DEPTH ); +} + + +//====================================================================================== +// CDXUTRadioButton class +//====================================================================================== + +CDXUTRadioButton::CDXUTRadioButton( _In_opt_ CDXUTDialog* pDialog ) noexcept : + m_nButtonGroup(0) +{ + m_Type = DXUT_CONTROL_RADIOBUTTON; + m_pDialog = pDialog; +} + + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTRadioButton::HandleKeyboard( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_KEYDOWN: + { + switch( wParam ) + { + case VK_SPACE: + m_bPressed = true; + return true; + } + } + + case WM_KEYUP: + { + switch( wParam ) + { + case VK_SPACE: + if( m_bPressed == true ) + { + m_bPressed = false; + + m_pDialog->ClearRadioButtonGroup( m_nButtonGroup ); + m_bChecked = !m_bChecked; + + m_pDialog->SendEvent( EVENT_RADIOBUTTON_CHANGED, true, this ); + } + return true; + } + } + } + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTRadioButton::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + { + if( ContainsPoint( pt ) ) + { + // Pressed while inside the control + m_bPressed = true; + SetCapture( DXUTGetHWND() ); + + if( !m_bHasFocus ) + m_pDialog->RequestFocus( this ); + + return true; + } + + break; + } + + case WM_LBUTTONUP: + { + if( m_bPressed ) + { + m_bPressed = false; + ReleaseCapture(); + + // Button click + if( ContainsPoint( pt ) ) + { + m_pDialog->ClearRadioButtonGroup( m_nButtonGroup ); + m_bChecked = !m_bChecked; + + m_pDialog->SendEvent( EVENT_RADIOBUTTON_CHANGED, true, this ); + } + + return true; + } + + break; + } + }; + + return false; +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTRadioButton::SetCheckedInternal( bool bChecked, bool bClearGroup, bool bFromInput ) +{ + if( bChecked && bClearGroup ) + m_pDialog->ClearRadioButtonGroup( m_nButtonGroup ); + + m_bChecked = bChecked; + m_pDialog->SendEvent( EVENT_RADIOBUTTON_CHANGED, bFromInput, this ); +} + + +//====================================================================================== +// CDXUTComboBox class +//====================================================================================== + +CDXUTComboBox::CDXUTComboBox( _In_opt_ CDXUTDialog* pDialog ) noexcept : + m_iSelected(-1), + m_iFocused(-1), + m_nDropHeight(100), + m_ScrollBar( pDialog ), + m_nSBWidth(16), + m_bOpened(false), + m_rcText{}, + m_rcButton{}, + m_rcDropdown{}, + m_rcDropdownText{} +{ + m_Type = DXUT_CONTROL_COMBOBOX; + m_pDialog = pDialog; +} + + +//-------------------------------------------------------------------------------------- +CDXUTComboBox::~CDXUTComboBox() +{ + RemoveAllItems(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTComboBox::SetTextColor( _In_ DWORD Color ) +{ + auto pElement = m_Elements[ 0 ]; + + if( pElement ) + pElement->FontColor.States[DXUT_STATE_NORMAL] = Color; + + pElement = m_Elements[ 2 ]; + + if( pElement ) + pElement->FontColor.States[DXUT_STATE_NORMAL] = Color; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTComboBox::UpdateRects() +{ + + CDXUTButton::UpdateRects(); + + m_rcButton = m_rcBoundingBox; + m_rcButton.left = m_rcButton.right - RectHeight( m_rcButton ); + + m_rcText = m_rcBoundingBox; + m_rcText.right = m_rcButton.left; + + m_rcDropdown = m_rcText; + OffsetRect( &m_rcDropdown, 0, static_cast( 0.90f * RectHeight( m_rcText ) ) ); + m_rcDropdown.bottom += m_nDropHeight; + m_rcDropdown.right -= m_nSBWidth; + + m_rcDropdownText = m_rcDropdown; + m_rcDropdownText.left += static_cast(0.1f * RectWidth(m_rcDropdown)); + m_rcDropdownText.right -= static_cast(0.1f * RectWidth(m_rcDropdown)); + m_rcDropdownText.top += static_cast(0.1f * RectHeight(m_rcDropdown)); + m_rcDropdownText.bottom -= static_cast(0.1f * RectHeight(m_rcDropdown)); + + // Update the scrollbar's rects + m_ScrollBar.SetLocation( m_rcDropdown.right, m_rcDropdown.top + 2 ); + m_ScrollBar.SetSize( m_nSBWidth, RectHeight( m_rcDropdown ) - 2 ); + auto pFontNode = m_pDialog->GetManager()->GetFontNode( m_Elements[ 2 ]->iFont ); + if( pFontNode && pFontNode->nHeight ) + { + m_ScrollBar.SetPageSize( RectHeight( m_rcDropdownText ) / pFontNode->nHeight ); + + // The selected item may have been scrolled off the page. + // Ensure that it is in page again. + m_ScrollBar.ShowItem( m_iSelected ); + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTComboBox::OnFocusOut() +{ + CDXUTButton::OnFocusOut(); + + m_bOpened = false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTComboBox::HandleKeyboard( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + const DWORD REPEAT_MASK = ( 0x40000000 ); + + if( !m_bEnabled || !m_bVisible ) + return false; + + // Let the scroll bar have a chance to handle it first + if( m_ScrollBar.HandleKeyboard( uMsg, wParam, lParam ) ) + return true; + + switch( uMsg ) + { + case WM_KEYDOWN: + { + switch( wParam ) + { + case VK_RETURN: + if( m_bOpened ) + { + if( m_iSelected != m_iFocused ) + { + m_iSelected = m_iFocused; + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); + } + m_bOpened = false; + + if( !m_pDialog->m_bKeyboardInput ) + m_pDialog->ClearFocus(); + + return true; + } + break; + + case VK_F4: + // Filter out auto-repeats + if( lParam & REPEAT_MASK ) + return true; + + m_bOpened = !m_bOpened; + + if( !m_bOpened ) + { + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); + + if( !m_pDialog->m_bKeyboardInput ) + m_pDialog->ClearFocus(); + } + + return true; + + case VK_LEFT: + case VK_UP: + if( m_iFocused > 0 ) + { + m_iFocused--; + m_iSelected = m_iFocused; + + if( !m_bOpened ) + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); + } + + return true; + + case VK_RIGHT: + case VK_DOWN: + if( m_iFocused + 1 < ( int )GetNumItems() ) + { + m_iFocused++; + m_iSelected = m_iFocused; + + if( !m_bOpened ) + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); + } + + return true; + } + break; + } + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTComboBox::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + if( !m_bEnabled || !m_bVisible ) + return false; + + // Let the scroll bar handle it first. + if( m_ScrollBar.HandleMouse( uMsg, pt, wParam, lParam ) ) + return true; + + switch( uMsg ) + { + case WM_MOUSEMOVE: + { + if( m_bOpened && PtInRect( &m_rcDropdown, pt ) ) + { + // Determine which item has been selected + for( size_t i = 0; i < m_Items.size(); i++ ) + { + auto pItem = m_Items[ i ]; + if( pItem->bVisible && + PtInRect( &pItem->rcActive, pt ) ) + { + m_iFocused = static_cast( i ); + } + } + return true; + } + break; + } + + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + { + if( ContainsPoint( pt ) ) + { + // Pressed while inside the control + m_bPressed = true; + SetCapture( DXUTGetHWND() ); + + if( !m_bHasFocus ) + m_pDialog->RequestFocus( this ); + + // Toggle dropdown + if( m_bHasFocus ) + { + m_bOpened = !m_bOpened; + + if( !m_bOpened ) + { + if( !m_pDialog->m_bKeyboardInput ) + m_pDialog->ClearFocus(); + } + } + + return true; + } + + // Perhaps this click is within the dropdown + if( m_bOpened && PtInRect( &m_rcDropdown, pt ) ) + { + // Determine which item has been selected + for( size_t i = m_ScrollBar.GetTrackPos(); i < m_Items.size(); i++ ) + { + auto pItem = m_Items[ i ]; + if( pItem->bVisible && + PtInRect( &pItem->rcActive, pt ) ) + { + m_iFocused = m_iSelected = static_cast( i ); + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); + m_bOpened = false; + + if( !m_pDialog->m_bKeyboardInput ) + m_pDialog->ClearFocus(); + + break; + } + } + + return true; + } + + // Mouse click not on main control or in dropdown, fire an event if needed + if( m_bOpened ) + { + m_iFocused = m_iSelected; + + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); + m_bOpened = false; + } + + // Make sure the control is no longer in a pressed state + m_bPressed = false; + + // Release focus if appropriate + if( !m_pDialog->m_bKeyboardInput ) + { + m_pDialog->ClearFocus(); + } + + break; + } + + case WM_LBUTTONUP: + { + if( m_bPressed && ContainsPoint( pt ) ) + { + // Button click + m_bPressed = false; + ReleaseCapture(); + return true; + } + + break; + } + + case WM_MOUSEWHEEL: + { + int zDelta = ( short )HIWORD( wParam ) / WHEEL_DELTA; + if( m_bOpened ) + { + UINT uLines = 0; + if ( !SystemParametersInfo(SPI_GETWHEELSCROLLLINES, 0, &uLines, 0) ) + uLines = 0; + m_ScrollBar.Scroll( -zDelta * uLines ); + } + else + { + if( zDelta > 0 ) + { + if( m_iFocused > 0 ) + { + m_iFocused--; + m_iSelected = m_iFocused; + + if( !m_bOpened ) + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); + } + } + else + { + if( m_iFocused + 1 < ( int )GetNumItems() ) + { + m_iFocused++; + m_iSelected = m_iFocused; + + if( !m_bOpened ) + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); + } + } + } + return true; + } + }; + + return false; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTComboBox::OnHotkey() +{ + if( m_bOpened ) + return; + + if( m_iSelected == -1 ) + return; + + if( m_pDialog->IsKeyboardInputEnabled() ) + m_pDialog->RequestFocus( this ); + + m_iSelected++; + + if( m_iSelected >= ( int )m_Items.size() ) + m_iSelected = 0; + + m_iFocused = m_iSelected; + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, true, this ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTComboBox::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + + DXUT_CONTROL_STATE iState = DXUT_STATE_NORMAL; + + if( !m_bOpened ) + iState = DXUT_STATE_HIDDEN; + + // Dropdown box + auto pElement = m_Elements[ 2 ]; + + // If we have not initialized the scroll bar page size, + // do that now. + static bool bSBInit; + if( !bSBInit ) + { + // Update the page size of the scroll bar + if( m_pDialog->GetManager()->GetFontNode( pElement->iFont )->nHeight ) + m_ScrollBar.SetPageSize( RectHeight( m_rcDropdownText ) / + m_pDialog->GetManager()->GetFontNode( pElement->iFont )->nHeight ); + else + m_ScrollBar.SetPageSize( RectHeight( m_rcDropdownText ) ); + bSBInit = true; + } + + // Scroll bar + if( m_bOpened ) + m_ScrollBar.Render( fElapsedTime ); + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime ); + pElement->FontColor.Blend( iState, fElapsedTime ); + + m_pDialog->DrawSprite( pElement, &m_rcDropdown, DXUT_NEAR_BUTTON_DEPTH ); + + // Selection outline + auto pSelectionElement = m_Elements[ 3 ]; + pSelectionElement->TextureColor.Current = pElement->TextureColor.Current; + pSelectionElement->FontColor.SetCurrent( pSelectionElement->FontColor.States[ DXUT_STATE_NORMAL ] ); + + auto pFont = m_pDialog->GetFont( pElement->iFont ); + if( pFont ) + { + int curY = m_rcDropdownText.top; + int nRemainingHeight = RectHeight( m_rcDropdownText ); + + for( size_t i = m_ScrollBar.GetTrackPos(); i < m_Items.size(); i++ ) + { + auto pItem = m_Items[ i ]; + + // Make sure there's room left in the dropdown + nRemainingHeight -= pFont->nHeight; + if( nRemainingHeight < 0 ) + { + pItem->bVisible = false; + continue; + } + + SetRect( &pItem->rcActive, m_rcDropdownText.left, curY, m_rcDropdownText.right, curY + pFont->nHeight ); + curY += pFont->nHeight; + + pItem->bVisible = true; + + if( m_bOpened ) + { + if( ( int )i == m_iFocused ) + { + RECT rc; + SetRect( &rc, m_rcDropdown.left, pItem->rcActive.top, m_rcDropdown.right, + pItem->rcActive.bottom + 2 ); + m_pDialog->DrawSprite( pSelectionElement, &rc, DXUT_NEAR_BUTTON_DEPTH ); + m_pDialog->DrawText( pItem->strText, pSelectionElement, &pItem->rcActive ); + } + else + { + m_pDialog->DrawText( pItem->strText, pElement, &pItem->rcActive ); + } + } + } + } + + int nOffsetX = 0; + int nOffsetY = 0; + + iState = DXUT_STATE_NORMAL; + + if( m_bVisible == false ) + iState = DXUT_STATE_HIDDEN; + else if( m_bEnabled == false ) + iState = DXUT_STATE_DISABLED; + else if( m_bPressed ) + { + iState = DXUT_STATE_PRESSED; + + nOffsetX = 1; + nOffsetY = 2; + } + else if( m_bMouseOver ) + { + iState = DXUT_STATE_MOUSEOVER; + + nOffsetX = -1; + nOffsetY = -2; + } + else if( m_bHasFocus ) + iState = DXUT_STATE_FOCUS; + + float fBlendRate = ( iState == DXUT_STATE_PRESSED ) ? 0.0f : 0.8f; + + // Button + pElement = m_Elements[ 1 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + + RECT rcWindow = m_rcButton; + OffsetRect( &rcWindow, nOffsetX, nOffsetY ); + m_pDialog->DrawSprite( pElement, &rcWindow, DXUT_FAR_BUTTON_DEPTH ); + + if( m_bOpened ) + iState = DXUT_STATE_PRESSED; + + // Main text box + pElement = m_Elements[ 0 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + pElement->FontColor.Blend( iState, fElapsedTime, fBlendRate ); + + m_pDialog->DrawSprite( pElement, &m_rcText, DXUT_NEAR_BUTTON_DEPTH ); + + if( m_iSelected >= 0 && m_iSelected < ( int )m_Items.size() ) + { + auto pItem = m_Items[ m_iSelected ]; + if( pItem ) + { + m_pDialog->DrawText( pItem->strText, pElement, &m_rcText, false, true ); + + } + } +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTComboBox::AddItem( const WCHAR* strText, void* pData ) +{ + // Validate parameters + if( !strText ) + { + return E_INVALIDARG; + } + + // Create a new item and set the data + auto pItem = new (std::nothrow) DXUTComboBoxItem; + if( !pItem ) + { + return DXTRACE_ERR_MSGBOX( L"new", E_OUTOFMEMORY ); + } + + ZeroMemory( pItem, sizeof( DXUTComboBoxItem ) ); + wcscpy_s( pItem->strText, 256, strText ); + pItem->pData = pData; + + m_Items.push_back( pItem ); + + // Update the scroll bar with new range + m_ScrollBar.SetTrackRange( 0, (int)m_Items.size() ); + + // If this is the only item in the list, it's selected + if( GetNumItems() == 1 ) + { + m_iSelected = 0; + m_iFocused = 0; + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, false, this ); + } + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTComboBox::RemoveItem( _In_ UINT index ) +{ + auto it = m_Items.begin() + index; + auto pItem = *it; + SAFE_DELETE( pItem ); + m_Items.erase( it ); + m_ScrollBar.SetTrackRange( 0, (int)m_Items.size() ); + if( m_iSelected >= (int)m_Items.size() ) + m_iSelected = (int)m_Items.size() - 1; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTComboBox::RemoveAllItems() +{ + for( auto it = m_Items.begin(); it != m_Items.end(); ++it ) + { + auto pItem = *it; + SAFE_DELETE( pItem ); + } + + m_Items.clear(); + m_ScrollBar.SetTrackRange( 0, 1 ); + m_iFocused = m_iSelected = -1; +} + + +//-------------------------------------------------------------------------------------- +bool CDXUTComboBox::ContainsItem( _In_z_ const WCHAR* strText, _In_ UINT iStart ) +{ + return ( -1 != FindItem( strText, iStart ) ); +} + + +//-------------------------------------------------------------------------------------- +int CDXUTComboBox::FindItem( _In_z_ const WCHAR* strText, _In_ UINT iStart ) const +{ + if( !strText ) + return -1; + + for( size_t i = iStart; i < m_Items.size(); i++ ) + { + auto pItem = m_Items[ i ]; + + if( 0 == wcscmp( pItem->strText, strText ) ) + { + return static_cast( i ); + } + } + + return -1; +} + + +//-------------------------------------------------------------------------------------- +void* CDXUTComboBox::GetSelectedData() const +{ + if( m_iSelected < 0 ) + return nullptr; + + auto pItem = m_Items[ m_iSelected ]; + return pItem->pData; +} + + +//-------------------------------------------------------------------------------------- +DXUTComboBoxItem* CDXUTComboBox::GetSelectedItem() const +{ + if( m_iSelected < 0 ) + return nullptr; + + return m_Items[ m_iSelected ]; +} + + +//-------------------------------------------------------------------------------------- +void* CDXUTComboBox::GetItemData( _In_z_ const WCHAR* strText ) const +{ + int index = FindItem( strText ); + if( index == -1 ) + { + return nullptr; + } + + auto pItem = m_Items[ index ]; + if( !pItem ) + { + DXTRACE_ERR( L"CDXUTComboBox::GetItemData", E_FAIL ); + return nullptr; + } + + return pItem->pData; +} + + +//-------------------------------------------------------------------------------------- +void* CDXUTComboBox::GetItemData( _In_ int nIndex ) const +{ + if( nIndex < 0 || nIndex >= (int)m_Items.size() ) + return nullptr; + + return m_Items[ nIndex ]->pData; +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTComboBox::SetSelectedByIndex( _In_ UINT index ) +{ + if( index >= GetNumItems() ) + return E_INVALIDARG; + + m_iFocused = m_iSelected = index; + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, false, this ); + + return S_OK; +} + + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTComboBox::SetSelectedByText( _In_z_ const WCHAR* strText ) +{ + if( !strText ) + return E_INVALIDARG; + + int index = FindItem( strText ); + if( index == -1 ) + return E_FAIL; + + m_iFocused = m_iSelected = index; + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, false, this ); + + return S_OK; +} + + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTComboBox::SetSelectedByData( _In_ void* pData ) +{ + for( size_t i = 0; i < m_Items.size(); i++ ) + { + auto pItem = m_Items[ i ]; + + if( pItem->pData == pData ) + { + m_iFocused = m_iSelected = static_cast( i ); + m_pDialog->SendEvent( EVENT_COMBOBOX_SELECTION_CHANGED, false, this ); + return S_OK; + } + } + + return E_FAIL; +} + + +//====================================================================================== +// CDXUTSlider class +//====================================================================================== + +CDXUTSlider::CDXUTSlider( _In_opt_ CDXUTDialog* pDialog ) noexcept : + m_nValue(50), + m_nMin(0), + m_nMax(100), + m_nDragX(0), + m_nDragOffset(0), + m_nButtonX(0), + m_bPressed(false), + m_rcButton{} +{ + m_Type = DXUT_CONTROL_SLIDER; + m_pDialog = pDialog; +} + + +//-------------------------------------------------------------------------------------- +bool CDXUTSlider::ContainsPoint( _In_ const POINT& pt ) +{ + return ( PtInRect( &m_rcBoundingBox, pt ) || + PtInRect( &m_rcButton, pt ) ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTSlider::UpdateRects() +{ + CDXUTControl::UpdateRects(); + + m_rcButton = m_rcBoundingBox; + m_rcButton.right = m_rcButton.left + RectHeight( m_rcButton ); + OffsetRect( &m_rcButton, -RectWidth( m_rcButton ) / 2, 0 ); + + m_nButtonX = ( int )( ( m_nValue - m_nMin ) * ( float )RectWidth( m_rcBoundingBox ) / ( m_nMax - m_nMin ) ); + OffsetRect( &m_rcButton, m_nButtonX, 0 ); +} + + +//-------------------------------------------------------------------------------------- +int CDXUTSlider::ValueFromPos( _In_ int x ) +{ + float fValuePerPixel = ( float )( m_nMax - m_nMin ) / RectWidth( m_rcBoundingBox ); + return ( int )( 0.5f + m_nMin + fValuePerPixel * ( x - m_rcBoundingBox.left ) ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTSlider::HandleKeyboard( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_KEYDOWN: + { + switch( wParam ) + { + case VK_HOME: + SetValueInternal( m_nMin, true ); + return true; + + case VK_END: + SetValueInternal( m_nMax, true ); + return true; + + case VK_LEFT: + case VK_DOWN: + SetValueInternal( m_nValue - 1, true ); + return true; + + case VK_RIGHT: + case VK_UP: + SetValueInternal( m_nValue + 1, true ); + return true; + + case VK_NEXT: + SetValueInternal( m_nValue - ( 10 > ( m_nMax - m_nMin ) / 10 ? 10 : ( m_nMax - m_nMin ) / 10 ), + true ); + return true; + + case VK_PRIOR: + SetValueInternal( m_nValue + ( 10 > ( m_nMax - m_nMin ) / 10 ? 10 : ( m_nMax - m_nMin ) / 10 ), + true ); + return true; + } + break; + } + } + + + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTSlider::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + { + if( PtInRect( &m_rcButton, pt ) ) + { + // Pressed while inside the control + m_bPressed = true; + SetCapture( DXUTGetHWND() ); + + m_nDragX = pt.x; + //m_nDragY = pt.y; + m_nDragOffset = m_nButtonX - m_nDragX; + + //m_nDragValue = m_nValue; + + if( !m_bHasFocus ) + m_pDialog->RequestFocus( this ); + + return true; + } + + if( PtInRect( &m_rcBoundingBox, pt ) ) + { + m_nDragX = pt.x; + m_nDragOffset = 0; + m_bPressed = true; + + if( !m_bHasFocus ) + m_pDialog->RequestFocus( this ); + + if( pt.x > m_nButtonX + m_x ) + { + SetValueInternal( m_nValue + 1, true ); + return true; + } + + if( pt.x < m_nButtonX + m_x ) + { + SetValueInternal( m_nValue - 1, true ); + return true; + } + } + + break; + } + + case WM_LBUTTONUP: + { + if( m_bPressed ) + { + m_bPressed = false; + ReleaseCapture(); + m_pDialog->SendEvent( EVENT_SLIDER_VALUE_CHANGED_UP, true, this ); + + return true; + } + + break; + } + + case WM_MOUSEMOVE: + { + if( m_bPressed ) + { + SetValueInternal( ValueFromPos( m_x + pt.x + m_nDragOffset ), true ); + return true; + } + + break; + } + + case WM_MOUSEWHEEL: + { + int nScrollAmount = int( ( short )HIWORD( wParam ) ) / WHEEL_DELTA; + SetValueInternal( m_nValue - nScrollAmount, true ); + return true; + } + }; + + return false; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTSlider::SetRange( _In_ int nMin, _In_ int nMax ) +{ + m_nMin = nMin; + m_nMax = nMax; + + SetValueInternal( m_nValue, false ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTSlider::SetValueInternal( _In_ int nValue, _In_ bool bFromInput ) +{ + // Clamp to range + nValue = std::max( m_nMin, nValue ); + nValue = std::min( m_nMax, nValue ); + + if( nValue == m_nValue ) + return; + + m_nValue = nValue; + UpdateRects(); + + m_pDialog->SendEvent( EVENT_SLIDER_VALUE_CHANGED, bFromInput, this ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTSlider::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + + int nOffsetX = 0; + int nOffsetY = 0; + + DXUT_CONTROL_STATE iState = DXUT_STATE_NORMAL; + + if( m_bVisible == false ) + { + iState = DXUT_STATE_HIDDEN; + } + else if( m_bEnabled == false ) + { + iState = DXUT_STATE_DISABLED; + } + else if( m_bPressed ) + { + iState = DXUT_STATE_PRESSED; + + nOffsetX = 1; + nOffsetY = 2; + } + else if( m_bMouseOver ) + { + iState = DXUT_STATE_MOUSEOVER; + + nOffsetX = -1; + nOffsetY = -2; + } + else if( m_bHasFocus ) + { + iState = DXUT_STATE_FOCUS; + } + + float fBlendRate = ( iState == DXUT_STATE_PRESSED ) ? 0.0f : 0.8f; + + auto pElement = m_Elements[ 0 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + m_pDialog->DrawSprite( pElement, &m_rcBoundingBox, DXUT_FAR_BUTTON_DEPTH ); + + pElement = m_Elements[ 1 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + m_pDialog->DrawSprite( pElement, &m_rcButton, DXUT_NEAR_BUTTON_DEPTH ); +} + + +//====================================================================================== +// CDXUTScrollBar class +//====================================================================================== + +CDXUTScrollBar::CDXUTScrollBar( _In_opt_ CDXUTDialog* pDialog ) noexcept : + m_bShowThumb(true), + m_bDrag(false), + m_rcUpButton{}, + m_rcDownButton{}, + m_rcTrack{}, + m_rcThumb{}, + m_nPosition(0), + m_nPageSize(1), + m_nStart(0), + m_nEnd(1), + m_LastMouse{ 0, 0 }, + m_Arrow(CLEAR), + m_dArrowTS(0.0) +{ + m_Type = DXUT_CONTROL_SCROLLBAR; + m_pDialog = pDialog; +} + + +//-------------------------------------------------------------------------------------- +CDXUTScrollBar::~CDXUTScrollBar() +{ +} + + +//-------------------------------------------------------------------------------------- +void CDXUTScrollBar::UpdateRects() +{ + CDXUTControl::UpdateRects(); + + // Make the buttons square + + SetRect( &m_rcUpButton, m_rcBoundingBox.left, m_rcBoundingBox.top, + m_rcBoundingBox.right, m_rcBoundingBox.top + RectWidth( m_rcBoundingBox ) ); + SetRect( &m_rcDownButton, m_rcBoundingBox.left, m_rcBoundingBox.bottom - RectWidth( m_rcBoundingBox ), + m_rcBoundingBox.right, m_rcBoundingBox.bottom ); + SetRect( &m_rcTrack, m_rcUpButton.left, m_rcUpButton.bottom, + m_rcDownButton.right, m_rcDownButton.top ); + m_rcThumb.left = m_rcUpButton.left; + m_rcThumb.right = m_rcUpButton.right; + + UpdateThumbRect(); +} + + +//-------------------------------------------------------------------------------------- +// Compute the dimension of the scroll thumb +void CDXUTScrollBar::UpdateThumbRect() +{ + if( m_nEnd - m_nStart > m_nPageSize ) + { + int nThumbHeight = std::max( RectHeight( m_rcTrack ) * m_nPageSize / ( m_nEnd - m_nStart ), + SCROLLBAR_MINTHUMBSIZE ); + int nMaxPosition = m_nEnd - m_nStart - m_nPageSize; + m_rcThumb.top = m_rcTrack.top + ( m_nPosition - m_nStart ) * ( RectHeight( m_rcTrack ) - nThumbHeight ) + / nMaxPosition; + m_rcThumb.bottom = m_rcThumb.top + nThumbHeight; + m_bShowThumb = true; + + } + else + { + // No content to scroll + m_rcThumb.bottom = m_rcThumb.top; + m_bShowThumb = false; + } +} + + +//-------------------------------------------------------------------------------------- +// Scroll() scrolls by nDelta items. A positive value scrolls down, while a negative +// value scrolls up. +void CDXUTScrollBar::Scroll( _In_ int nDelta ) +{ + // Perform scroll + m_nPosition += nDelta; + + // Cap position + Cap(); + + // Update thumb position + UpdateThumbRect(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTScrollBar::ShowItem( _In_ int nIndex ) +{ + // Cap the index + + if( nIndex < 0 ) + nIndex = 0; + + if( nIndex >= m_nEnd ) + nIndex = m_nEnd - 1; + + // Adjust position + + if( m_nPosition > nIndex ) + m_nPosition = nIndex; + else if( m_nPosition + m_nPageSize <= nIndex ) + m_nPosition = nIndex - m_nPageSize + 1; + + UpdateThumbRect(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTScrollBar::HandleKeyboard( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(uMsg); + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTScrollBar::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + + static int ThumbOffsetY; + + m_LastMouse = pt; + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + { + // Check for click on up button + + if( PtInRect( &m_rcUpButton, pt ) ) + { + SetCapture( DXUTGetHWND() ); + if( m_nPosition > m_nStart ) + --m_nPosition; + UpdateThumbRect(); + m_Arrow = CLICKED_UP; + m_dArrowTS = DXUTGetTime(); + return true; + } + + // Check for click on down button + + if( PtInRect( &m_rcDownButton, pt ) ) + { + SetCapture( DXUTGetHWND() ); + if( m_nPosition + m_nPageSize <= m_nEnd ) + ++m_nPosition; + UpdateThumbRect(); + m_Arrow = CLICKED_DOWN; + m_dArrowTS = DXUTGetTime(); + return true; + } + + // Check for click on thumb + + if( PtInRect( &m_rcThumb, pt ) ) + { + SetCapture( DXUTGetHWND() ); + m_bDrag = true; + ThumbOffsetY = pt.y - m_rcThumb.top; + return true; + } + + // Check for click on track + + if( m_rcThumb.left <= pt.x && + m_rcThumb.right > pt.x ) + { + SetCapture( DXUTGetHWND() ); + if( m_rcThumb.top > pt.y && + m_rcTrack.top <= pt.y ) + { + Scroll( -( m_nPageSize - 1 ) ); + return true; + } + else if( m_rcThumb.bottom <= pt.y && + m_rcTrack.bottom > pt.y ) + { + Scroll( m_nPageSize - 1 ); + return true; + } + } + + break; + } + + case WM_LBUTTONUP: + { + m_bDrag = false; + ReleaseCapture(); + UpdateThumbRect(); + m_Arrow = CLEAR; + break; + } + + case WM_MOUSEMOVE: + { + if( m_bDrag ) + { + m_rcThumb.bottom += pt.y - ThumbOffsetY - m_rcThumb.top; + m_rcThumb.top = pt.y - ThumbOffsetY; + if( m_rcThumb.top < m_rcTrack.top ) + OffsetRect( &m_rcThumb, 0, m_rcTrack.top - m_rcThumb.top ); + else if( m_rcThumb.bottom > m_rcTrack.bottom ) + OffsetRect( &m_rcThumb, 0, m_rcTrack.bottom - m_rcThumb.bottom ); + + // Compute first item index based on thumb position + + int nMaxFirstItem = m_nEnd - m_nStart - m_nPageSize + 1; // Largest possible index for first item + int nMaxThumb = RectHeight( m_rcTrack ) - RectHeight( m_rcThumb ); // Largest possible thumb position from the top + + m_nPosition = m_nStart + + ( m_rcThumb.top - m_rcTrack.top + + nMaxThumb / ( nMaxFirstItem * 2 ) ) * // Shift by half a row to avoid last row covered by only one pixel + nMaxFirstItem / nMaxThumb; + + return true; + } + + break; + } + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTScrollBar::MsgProc( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(wParam); + + if( WM_CAPTURECHANGED == uMsg ) + { + // The application just lost mouse capture. We may not have gotten + // the WM_MOUSEUP message, so reset m_bDrag here. + if( ( HWND )lParam != DXUTGetHWND() ) + m_bDrag = false; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTScrollBar::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + + // Check if the arrow button has been held for a while. + // If so, update the thumb position to simulate repeated + // scroll. + if( m_Arrow != CLEAR ) + { + double dCurrTime = DXUTGetTime(); + if( PtInRect( &m_rcUpButton, m_LastMouse ) ) + { + switch( m_Arrow ) + { + case CLICKED_UP: + if( SCROLLBAR_ARROWCLICK_DELAY < dCurrTime - m_dArrowTS ) + { + Scroll( -1 ); + m_Arrow = HELD_UP; + m_dArrowTS = dCurrTime; + } + break; + case HELD_UP: + if( SCROLLBAR_ARROWCLICK_REPEAT < dCurrTime - m_dArrowTS ) + { + Scroll( -1 ); + m_dArrowTS = dCurrTime; + } + break; + } + } + else if( PtInRect( &m_rcDownButton, m_LastMouse ) ) + { + switch( m_Arrow ) + { + case CLICKED_DOWN: + if( SCROLLBAR_ARROWCLICK_DELAY < dCurrTime - m_dArrowTS ) + { + Scroll( 1 ); + m_Arrow = HELD_DOWN; + m_dArrowTS = dCurrTime; + } + break; + case HELD_DOWN: + if( SCROLLBAR_ARROWCLICK_REPEAT < dCurrTime - m_dArrowTS ) + { + Scroll( 1 ); + m_dArrowTS = dCurrTime; + } + break; + } + } + } + + DXUT_CONTROL_STATE iState = DXUT_STATE_NORMAL; + + if( m_bVisible == false ) + iState = DXUT_STATE_HIDDEN; + else if( m_bEnabled == false || m_bShowThumb == false ) + iState = DXUT_STATE_DISABLED; + else if( m_bMouseOver ) + iState = DXUT_STATE_MOUSEOVER; + else if( m_bHasFocus ) + iState = DXUT_STATE_FOCUS; + + + float fBlendRate = ( iState == DXUT_STATE_PRESSED ) ? 0.0f : 0.8f; + + // Background track layer + auto pElement = m_Elements[ 0 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + m_pDialog->DrawSprite( pElement, &m_rcTrack, DXUT_FAR_BUTTON_DEPTH ); + + // Up Arrow + pElement = m_Elements[ 1 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + m_pDialog->DrawSprite( pElement, &m_rcUpButton, DXUT_NEAR_BUTTON_DEPTH ); + + // Down Arrow + pElement = m_Elements[ 2 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + m_pDialog->DrawSprite( pElement, &m_rcDownButton, DXUT_NEAR_BUTTON_DEPTH ); + + // Thumb button + pElement = m_Elements[ 3 ]; + + // Blend current color + pElement->TextureColor.Blend( iState, fElapsedTime, fBlendRate ); + m_pDialog->DrawSprite( pElement, &m_rcThumb, DXUT_NEAR_BUTTON_DEPTH ); + +} + + +//-------------------------------------------------------------------------------------- +void CDXUTScrollBar::SetTrackRange( _In_ int nStart, _In_ int nEnd ) +{ + m_nStart = nStart; m_nEnd = nEnd; + Cap(); + UpdateThumbRect(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTScrollBar::Cap() // Clips position at boundaries. Ensures it stays within legal range. +{ + if( m_nPosition < m_nStart || + m_nEnd - m_nStart <= m_nPageSize ) + { + m_nPosition = m_nStart; + } + else if( m_nPosition + m_nPageSize > m_nEnd ) + m_nPosition = m_nEnd - m_nPageSize + 1; +} + + +//====================================================================================== +// CDXUTListBox class +//====================================================================================== + +CDXUTListBox::CDXUTListBox( _In_opt_ CDXUTDialog* pDialog ) noexcept : + m_rcText{}, + m_rcSelection{}, + m_ScrollBar(pDialog), + m_nSBWidth(16), + m_nBorder(6), + m_nMargin(5), + m_nTextHeight(0), + m_dwStyle(0), + m_nSelected(-1), + m_nSelStart(0), + m_bDrag(false) +{ + m_Type = DXUT_CONTROL_LISTBOX; + m_pDialog = pDialog; +} + + +//-------------------------------------------------------------------------------------- +CDXUTListBox::~CDXUTListBox() +{ + RemoveAllItems(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTListBox::UpdateRects() +{ + CDXUTControl::UpdateRects(); + + m_rcSelection = m_rcBoundingBox; + m_rcSelection.right -= m_nSBWidth; + InflateRect( &m_rcSelection, -m_nBorder, -m_nBorder ); + m_rcText = m_rcSelection; + InflateRect( &m_rcText, -m_nMargin, 0 ); + + // Update the scrollbar's rects + m_ScrollBar.SetLocation( m_rcBoundingBox.right - m_nSBWidth, m_rcBoundingBox.top ); + m_ScrollBar.SetSize( m_nSBWidth, m_height ); + auto pFontNode = m_pDialog->GetManager()->GetFontNode( m_Elements[ 0 ]->iFont ); + if( pFontNode && pFontNode->nHeight ) + { + m_ScrollBar.SetPageSize( RectHeight( m_rcText ) / pFontNode->nHeight ); + + // The selected item may have been scrolled off the page. + // Ensure that it is in page again. + m_ScrollBar.ShowItem( m_nSelected ); + } +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTListBox::AddItem( const WCHAR* wszText, void* pData ) +{ + auto pNewItem = new (std::nothrow) DXUTListBoxItem; + if( !pNewItem ) + return E_OUTOFMEMORY; + + wcscpy_s( pNewItem->strText, 256, wszText ); + pNewItem->pData = pData; + SetRect( &pNewItem->rcActive, 0, 0, 0, 0 ); + pNewItem->bSelected = false; + + m_Items.push_back( pNewItem ); + m_ScrollBar.SetTrackRange( 0, (int)m_Items.size() ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTListBox::InsertItem( int nIndex, const WCHAR* wszText, void* pData ) +{ + auto pNewItem = new (std::nothrow) DXUTListBoxItem; + if( !pNewItem ) + return E_OUTOFMEMORY; + + wcscpy_s( pNewItem->strText, 256, wszText ); + pNewItem->pData = pData; + SetRect( &pNewItem->rcActive, 0, 0, 0, 0 ); + pNewItem->bSelected = false; + + m_Items[ nIndex ] = pNewItem; + m_ScrollBar.SetTrackRange( 0, (int)m_Items.size() ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTListBox::RemoveItem( _In_ int nIndex ) +{ + if( nIndex < 0 || nIndex >= ( int )m_Items.size() ) + return; + + auto it = m_Items.begin() + nIndex; + auto pItem = *it; + delete pItem; + m_Items.erase(it); + m_ScrollBar.SetTrackRange( 0, (int)m_Items.size() ); + if( m_nSelected >= ( int )m_Items.size() ) + m_nSelected = int( m_Items.size() ) - 1; + + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION, true, this ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTListBox::RemoveAllItems() +{ + for( auto it = m_Items.begin(); it != m_Items.end(); ++it ) + { + auto pItem = *it; + delete pItem; + } + + m_Items.clear(); + m_ScrollBar.SetTrackRange( 0, 1 ); +} + + +//-------------------------------------------------------------------------------------- +DXUTListBoxItem* CDXUTListBox::GetItem( _In_ int nIndex ) const +{ + if( nIndex < 0 || nIndex >= ( int )m_Items.size() ) + return nullptr; + + return m_Items[nIndex]; +} + + +//-------------------------------------------------------------------------------------- +// For single-selection listbox, returns the index of the selected item. +// For multi-selection, returns the first selected item after the nPreviousSelected position. +// To search for the first selected item, the app passes -1 for nPreviousSelected. For +// subsequent searches, the app passes the returned index back to GetSelectedIndex as. +// nPreviousSelected. +// Returns -1 on error or if no item is selected. +int CDXUTListBox::GetSelectedIndex( _In_ int nPreviousSelected ) const +{ + if( nPreviousSelected < -1 ) + return -1; + + if( m_dwStyle & MULTISELECTION ) + { + // Multiple selection enabled. Search for the next item with the selected flag. + for( int i = nPreviousSelected + 1; i < ( int )m_Items.size(); ++i ) + { + auto pItem = m_Items[ i ]; + + if( pItem->bSelected ) + return i; + } + + return -1; + } + else + { + // Single selection + return m_nSelected; + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTListBox::SelectItem( _In_ int nNewIndex ) +{ + // If no item exists, do nothing. + if( m_Items.size() == 0 ) + return; + + int nOldSelected = m_nSelected; + + // Adjust m_nSelected + m_nSelected = nNewIndex; + + // Perform capping + if( m_nSelected < 0 ) + m_nSelected = 0; + if( m_nSelected >= ( int )m_Items.size() ) + m_nSelected = int( m_Items.size() ) - 1; + + if( nOldSelected != m_nSelected ) + { + if( m_dwStyle & MULTISELECTION ) + { + m_Items[m_nSelected]->bSelected = true; + } + + // Update selection start + m_nSelStart = m_nSelected; + + // Adjust scroll bar + m_ScrollBar.ShowItem( m_nSelected ); + } + + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION, true, this ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTListBox::HandleKeyboard( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + if( !m_bEnabled || !m_bVisible ) + return false; + + // Let the scroll bar have a chance to handle it first + if( m_ScrollBar.HandleKeyboard( uMsg, wParam, lParam ) ) + return true; + + switch( uMsg ) + { + case WM_KEYDOWN: + switch( wParam ) + { + case VK_UP: + case VK_DOWN: + case VK_NEXT: + case VK_PRIOR: + case VK_HOME: + case VK_END: + { + // If no item exists, do nothing. + if( m_Items.size() == 0 ) + return true; + + int nOldSelected = m_nSelected; + + // Adjust m_nSelected + switch( wParam ) + { + case VK_UP: + --m_nSelected; break; + case VK_DOWN: + ++m_nSelected; break; + case VK_NEXT: + m_nSelected += m_ScrollBar.GetPageSize() - 1; break; + case VK_PRIOR: + m_nSelected -= m_ScrollBar.GetPageSize() - 1; break; + case VK_HOME: + m_nSelected = 0; break; + case VK_END: + m_nSelected = int( m_Items.size() ) - 1; break; + } + + // Perform capping + if( m_nSelected < 0 ) + m_nSelected = 0; + if( m_nSelected >= ( int )m_Items.size() ) + m_nSelected = int( m_Items.size() ) - 1; + + if( nOldSelected != m_nSelected ) + { + if( m_dwStyle & MULTISELECTION ) + { + // Multiple selection + + // Clear all selection + for( int i = 0; i < ( int )m_Items.size(); ++i ) + { + auto pItem = m_Items[i]; + pItem->bSelected = false; + } + + if( GetKeyState( VK_SHIFT ) < 0 ) + { + // Select all items from m_nSelStart to + // m_nSelected + int nEnd = std::max( m_nSelStart, m_nSelected ); + + for( int n = std::min( m_nSelStart, m_nSelected ); n <= nEnd; ++n ) + m_Items[n]->bSelected = true; + } + else + { + m_Items[m_nSelected]->bSelected = true; + + // Update selection start + m_nSelStart = m_nSelected; + } + } + else + m_nSelStart = m_nSelected; + + // Adjust scroll bar + + m_ScrollBar.ShowItem( m_nSelected ); + + // Send notification + + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION, true, this ); + } + return true; + } + + // Space is the hotkey for double-clicking an item. + // + case VK_SPACE: + m_pDialog->SendEvent( EVENT_LISTBOX_ITEM_DBLCLK, true, this ); + return true; + } + break; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTListBox::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + if( !m_bEnabled || !m_bVisible ) + return false; + + // First acquire focus + if( WM_LBUTTONDOWN == uMsg ) + if( !m_bHasFocus ) + m_pDialog->RequestFocus( this ); + + // Let the scroll bar handle it first. + if( m_ScrollBar.HandleMouse( uMsg, pt, wParam, lParam ) ) + return true; + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + // Check for clicks in the text area + if( !m_Items.empty() && PtInRect( &m_rcSelection, pt ) ) + { + // Compute the index of the clicked item + + int nClicked; + if( m_nTextHeight ) + nClicked = m_ScrollBar.GetTrackPos() + ( pt.y - m_rcText.top ) / m_nTextHeight; + else + nClicked = -1; + + // Only proceed if the click falls on top of an item. + + if( nClicked >= m_ScrollBar.GetTrackPos() && + nClicked < ( int )m_Items.size() && + nClicked < m_ScrollBar.GetTrackPos() + m_ScrollBar.GetPageSize() ) + { + SetCapture( DXUTGetHWND() ); + m_bDrag = true; + + // If this is a double click, fire off an event and exit + // since the first click would have taken care of the selection + // updating. + if( uMsg == WM_LBUTTONDBLCLK ) + { + m_pDialog->SendEvent( EVENT_LISTBOX_ITEM_DBLCLK, true, this ); + return true; + } + + m_nSelected = nClicked; + if( !( wParam & MK_SHIFT ) ) + m_nSelStart = m_nSelected; + + // If this is a multi-selection listbox, update per-item + // selection data. + + if( m_dwStyle & MULTISELECTION ) + { + // Determine behavior based on the state of Shift and Ctrl + + auto pSelItem = m_Items[ m_nSelected ]; + if( ( wParam & ( MK_SHIFT | MK_CONTROL ) ) == MK_CONTROL ) + { + // Control click. Reverse the selection of this item. + + pSelItem->bSelected = !pSelItem->bSelected; + } + else if( ( wParam & ( MK_SHIFT | MK_CONTROL ) ) == MK_SHIFT ) + { + // Shift click. Set the selection for all items + // from last selected item to the current item. + // Clear everything else. + + int nBegin = std::min( m_nSelStart, m_nSelected ); + int nEnd = std::max( m_nSelStart, m_nSelected ); + + for( int i = 0; i < nBegin; ++i ) + { + auto pItem = m_Items[ i ]; + pItem->bSelected = false; + } + + for( int i = nEnd + 1; i < ( int )m_Items.size(); ++i ) + { + auto pItem = m_Items[ i ]; + pItem->bSelected = false; + } + + for( int i = nBegin; i <= nEnd; ++i ) + { + auto pItem = m_Items[ i ]; + pItem->bSelected = true; + } + } + else if( ( wParam & ( MK_SHIFT | MK_CONTROL ) ) == ( MK_SHIFT | MK_CONTROL ) ) + { + // Control-Shift-click. + + // The behavior is: + // Set all items from m_nSelStart to m_nSelected to + // the same state as m_nSelStart, not including m_nSelected. + // Set m_nSelected to selected. + + int nBegin = std::min( m_nSelStart, m_nSelected ); + int nEnd = std::max( m_nSelStart, m_nSelected ); + + // The two ends do not need to be set here. + + bool bLastSelected = m_Items[ m_nSelStart ]->bSelected; + for( int i = nBegin + 1; i < nEnd; ++i ) + { + auto pItem = m_Items[ i ]; + pItem->bSelected = bLastSelected; + } + + pSelItem->bSelected = true; + + // Restore m_nSelected to the previous value + // This matches the Windows behavior + + m_nSelected = m_nSelStart; + } + else + { + // Simple click. Clear all items and select the clicked + // item. + + + for( int i = 0; i < ( int )m_Items.size(); ++i ) + { + auto pItem = m_Items[ i ]; + pItem->bSelected = false; + } + + pSelItem->bSelected = true; + } + } // End of multi-selection case + + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION, true, this ); + } + + return true; + } + break; + + case WM_LBUTTONUP: + { + ReleaseCapture(); + m_bDrag = false; + + if( m_nSelected != -1 ) + { + // Set all items between m_nSelStart and m_nSelected to + // the same state as m_nSelStart + int nEnd = std::max( m_nSelStart, m_nSelected ); + + for( int n = std::min( m_nSelStart, m_nSelected ) + 1; n < nEnd; ++n ) + m_Items[n]->bSelected = m_Items[m_nSelStart]->bSelected; + m_Items[m_nSelected]->bSelected = m_Items[m_nSelStart]->bSelected; + + // If m_nSelStart and m_nSelected are not the same, + // the user has dragged the mouse to make a selection. + // Notify the application of this. + if( m_nSelStart != m_nSelected ) + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION, true, this ); + + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION_END, true, this ); + } + return false; + } + + case WM_MOUSEMOVE: + if( m_bDrag ) + { + // Compute the index of the item below cursor + + int nItem; + if( m_nTextHeight ) + nItem = m_ScrollBar.GetTrackPos() + ( pt.y - m_rcText.top ) / m_nTextHeight; + else + nItem = -1; + + // Only proceed if the cursor is on top of an item. + + if( nItem >= ( int )m_ScrollBar.GetTrackPos() && + nItem < ( int )m_Items.size() && + nItem < m_ScrollBar.GetTrackPos() + m_ScrollBar.GetPageSize() ) + { + m_nSelected = nItem; + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION, true, this ); + } + else if( nItem < ( int )m_ScrollBar.GetTrackPos() ) + { + // User drags the mouse above window top + m_ScrollBar.Scroll( -1 ); + m_nSelected = m_ScrollBar.GetTrackPos(); + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION, true, this ); + } + else if( nItem >= m_ScrollBar.GetTrackPos() + m_ScrollBar.GetPageSize() ) + { + // User drags the mouse below window bottom + m_ScrollBar.Scroll( 1 ); + m_nSelected = std::min( ( int )m_Items.size(), m_ScrollBar.GetTrackPos() + + m_ScrollBar.GetPageSize() ) - 1; + m_pDialog->SendEvent( EVENT_LISTBOX_SELECTION, true, this ); + } + } + break; + + case WM_MOUSEWHEEL: + { + UINT uLines = 0; + if ( !SystemParametersInfo( SPI_GETWHEELSCROLLLINES, 0, &uLines, 0 ) ) + uLines = 0; + int nScrollAmount = int( ( short )HIWORD( wParam ) ) / WHEEL_DELTA * uLines; + m_ScrollBar.Scroll( -nScrollAmount ); + return true; + } + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTListBox::MsgProc( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(wParam); + + if( WM_CAPTURECHANGED == uMsg ) + { + // The application just lost mouse capture. We may not have gotten + // the WM_MOUSEUP message, so reset m_bDrag here. + if( ( HWND )lParam != DXUTGetHWND() ) + m_bDrag = false; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTListBox::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + + auto pElement = m_Elements[ 0 ]; + pElement->TextureColor.Blend( DXUT_STATE_NORMAL, fElapsedTime ); + pElement->FontColor.Blend( DXUT_STATE_NORMAL, fElapsedTime ); + + auto pSelElement = m_Elements[ 1 ]; + pSelElement->TextureColor.Blend( DXUT_STATE_NORMAL, fElapsedTime ); + pSelElement->FontColor.Blend( DXUT_STATE_NORMAL, fElapsedTime ); + + m_pDialog->DrawSprite( pElement, &m_rcBoundingBox, DXUT_FAR_BUTTON_DEPTH ); + + // Render the text + if( !m_Items.empty() ) + { + // Find out the height of a single line of text + RECT rc = m_rcText; + RECT rcSel = m_rcSelection; + rc.bottom = rc.top + m_pDialog->GetManager()->GetFontNode( pElement->iFont )->nHeight; + + // Update the line height formation + m_nTextHeight = rc.bottom - rc.top; + + static bool bSBInit; + if( !bSBInit ) + { + // Update the page size of the scroll bar + if( m_nTextHeight ) + m_ScrollBar.SetPageSize( RectHeight( m_rcText ) / m_nTextHeight ); + else + m_ScrollBar.SetPageSize( RectHeight( m_rcText ) ); + bSBInit = true; + } + + rc.right = m_rcText.right; + for( int i = m_ScrollBar.GetTrackPos(); i < ( int )m_Items.size(); ++i ) + { + if( rc.bottom > m_rcText.bottom ) + break; + + auto pItem = m_Items[ i ]; + + // Determine if we need to render this item with the + // selected element. + bool bSelectedStyle = false; + + if( !( m_dwStyle & MULTISELECTION ) && i == m_nSelected ) + bSelectedStyle = true; + else if( m_dwStyle & MULTISELECTION ) + { + if( m_bDrag && + ( ( i >= m_nSelected && i < m_nSelStart ) || + ( i <= m_nSelected && i > m_nSelStart ) ) ) + bSelectedStyle = m_Items[m_nSelStart]->bSelected; + else if( pItem->bSelected ) + bSelectedStyle = true; + } + + if( bSelectedStyle ) + { + rcSel.top = rc.top; rcSel.bottom = rc.bottom; + m_pDialog->DrawSprite( pSelElement, &rcSel, DXUT_NEAR_BUTTON_DEPTH ); + m_pDialog->DrawText( pItem->strText, pSelElement, &rc ); + } + else + m_pDialog->DrawText( pItem->strText, pElement, &rc ); + + OffsetRect( &rc, 0, m_nTextHeight ); + } + } + + // Render the scroll bar + + m_ScrollBar.Render( fElapsedTime ); +} + + +//====================================================================================== +// CDXUTEditBox class +//====================================================================================== + +// Static member initialization +bool CDXUTEditBox::s_bHideCaret; // If true, we don't render the caret. + +// When scrolling, EDITBOX_SCROLLEXTENT is reciprocal of the amount to scroll. +// If EDITBOX_SCROLLEXTENT = 4, then we scroll 1/4 of the control each time. +#define EDITBOX_SCROLLEXTENT 4 + +//-------------------------------------------------------------------------------------- +CDXUTEditBox::CDXUTEditBox( _In_opt_ CDXUTDialog* pDialog ) noexcept : + m_nBorder(5), + m_nSpacing(4), + m_rcText{}, + m_rcRender{}, + m_bCaretOn(true), + m_nCaret(0), + m_bInsertMode(true), + m_nSelStart(0), + m_nFirstVisible(0), + m_bMouseDrag(false) +{ + m_Type = DXUT_CONTROL_EDITBOX; + m_pDialog = pDialog; + + m_dfBlink = double(GetCaretBlinkTime()) * 0.001; + m_dfLastBlink = DXUTGetGlobalTimer()->GetAbsoluteTime(); + s_bHideCaret = false; + + m_TextColor = D3DCOLOR_ARGB( 255, 16, 16, 16 ); + m_SelTextColor = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + m_SelBkColor = D3DCOLOR_ARGB( 255, 40, 50, 92 ); + m_CaretColor = D3DCOLOR_ARGB( 255, 0, 0, 0 ); +} + + +//-------------------------------------------------------------------------------------- +CDXUTEditBox::~CDXUTEditBox() +{ +} + + +//-------------------------------------------------------------------------------------- +// PlaceCaret: Set the caret to a character position, and adjust the scrolling if +// necessary. +//-------------------------------------------------------------------------------------- +void CDXUTEditBox::PlaceCaret( _In_ int nCP ) +{ + assert( nCP >= 0 && nCP <= m_Buffer.GetTextSize() ); + m_nCaret = nCP; + + // Obtain the X offset of the character. + int nX1st, nX, nX2; + m_Buffer.CPtoX( m_nFirstVisible, FALSE, &nX1st ); // 1st visible char + m_Buffer.CPtoX( nCP, FALSE, &nX ); // LEAD + // If nCP is the nul terminator, get the leading edge instead of trailing. + if( nCP == m_Buffer.GetTextSize() ) + nX2 = nX; + else + m_Buffer.CPtoX( nCP, TRUE, &nX2 ); // TRAIL + + // If the left edge of the char is smaller than the left edge of the 1st visible char, + // we need to scroll left until this char is visible. + if( nX < nX1st ) + { + // Simply make the first visible character the char at the new caret position. + m_nFirstVisible = nCP; + } + else // If the right of the character is bigger than the offset of the control's + // right edge, we need to scroll right to this character. + if( nX2 > nX1st + RectWidth( m_rcText ) ) + { + // Compute the X of the new left-most pixel + int nXNewLeft = nX2 - RectWidth( m_rcText ); + + // Compute the char position of this character + int nCPNew1st, nNewTrail; + m_Buffer.XtoCP( nXNewLeft, &nCPNew1st, &nNewTrail ); + + // If this coordinate is not on a character border, + // start from the next character so that the caret + // position does not fall outside the text rectangle. + int nXNew1st; + m_Buffer.CPtoX( nCPNew1st, FALSE, &nXNew1st ); + if( nXNew1st < nXNewLeft ) + ++nCPNew1st; + + m_nFirstVisible = nCPNew1st; + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTEditBox::ClearText() +{ + m_Buffer.Clear(); + m_nFirstVisible = 0; + PlaceCaret( 0 ); + m_nSelStart = 0; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTEditBox::SetText( _In_z_ LPCWSTR wszText, _In_ bool bSelected ) +{ + assert( wszText ); + + m_Buffer.SetText( wszText ); + m_nFirstVisible = 0; + // Move the caret to the end of the text + PlaceCaret( m_Buffer.GetTextSize() ); + m_nSelStart = bSelected ? 0 : m_nCaret; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTEditBox::GetTextCopy( LPWSTR strDest, UINT bufferCount ) const +{ + assert( strDest ); + + wcscpy_s( strDest, bufferCount, m_Buffer.GetBuffer() ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTEditBox::DeleteSelectionText() +{ + int nFirst = std::min( m_nCaret, m_nSelStart ); + int nLast = std::max( m_nCaret, m_nSelStart ); + // Update caret and selection + PlaceCaret( nFirst ); + m_nSelStart = m_nCaret; + // Remove the characters + for( int i = nFirst; i < nLast; ++i ) + m_Buffer.RemoveChar( nFirst ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTEditBox::UpdateRects() +{ + CDXUTControl::UpdateRects(); + + // Update the text rectangle + m_rcText = m_rcBoundingBox; + // First inflate by m_nBorder to compute render rects + InflateRect( &m_rcText, -m_nBorder, -m_nBorder ); + + // Update the render rectangles + m_rcRender[0] = m_rcText; + SetRect( &m_rcRender[1], m_rcBoundingBox.left, m_rcBoundingBox.top, m_rcText.left, m_rcText.top ); + SetRect( &m_rcRender[2], m_rcText.left, m_rcBoundingBox.top, m_rcText.right, m_rcText.top ); + SetRect( &m_rcRender[3], m_rcText.right, m_rcBoundingBox.top, m_rcBoundingBox.right, m_rcText.top ); + SetRect( &m_rcRender[4], m_rcBoundingBox.left, m_rcText.top, m_rcText.left, m_rcText.bottom ); + SetRect( &m_rcRender[5], m_rcText.right, m_rcText.top, m_rcBoundingBox.right, m_rcText.bottom ); + SetRect( &m_rcRender[6], m_rcBoundingBox.left, m_rcText.bottom, m_rcText.left, m_rcBoundingBox.bottom ); + SetRect( &m_rcRender[7], m_rcText.left, m_rcText.bottom, m_rcText.right, m_rcBoundingBox.bottom ); + SetRect( &m_rcRender[8], m_rcText.right, m_rcText.bottom, m_rcBoundingBox.right, m_rcBoundingBox.bottom ); + + // Inflate further by m_nSpacing + InflateRect( &m_rcText, -m_nSpacing, -m_nSpacing ); +} + + +#pragma warning(push) +#pragma warning( disable : 4616 6386 ) +void CDXUTEditBox::CopyToClipboard() +{ + // Copy the selection text to the clipboard + if( m_nCaret != m_nSelStart && OpenClipboard( nullptr ) ) + { + EmptyClipboard(); + + HGLOBAL hBlock = GlobalAlloc( GMEM_MOVEABLE, sizeof( WCHAR ) * ( m_Buffer.GetTextSize() + 1 ) ); + if( hBlock ) + { + auto pwszText = reinterpret_cast( GlobalLock( hBlock ) ); + if( pwszText ) + { + int nFirst = std::min( m_nCaret, m_nSelStart ); + int nLast = std::max( m_nCaret, m_nSelStart ); + if( nLast - nFirst > 0 ) + { + memcpy( pwszText, m_Buffer.GetBuffer() + nFirst, ( nLast - nFirst ) * sizeof( WCHAR ) ); + } + pwszText[nLast - nFirst] = L'\0'; // Terminate it + GlobalUnlock( hBlock ); + } + SetClipboardData( CF_UNICODETEXT, hBlock ); + } + CloseClipboard(); + // We must not free the object until CloseClipboard is called. + if( hBlock ) + GlobalFree( hBlock ); + } +} + + +void CDXUTEditBox::PasteFromClipboard() +{ + DeleteSelectionText(); + + if( OpenClipboard( nullptr ) ) + { + HANDLE handle = GetClipboardData( CF_UNICODETEXT ); + if( handle ) + { + // Convert the ANSI string to Unicode, then + // insert to our buffer. + auto pwszText = reinterpret_cast( GlobalLock( handle ) ); + if( pwszText ) + { + // Copy all characters up to null. + if( m_Buffer.InsertString( m_nCaret, pwszText ) ) + PlaceCaret( m_nCaret + (int)wcslen( pwszText ) ); + m_nSelStart = m_nCaret; + GlobalUnlock( handle ); + } + } + CloseClipboard(); + } +} +#pragma warning(pop) + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTEditBox::HandleKeyboard( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + bool bHandled = false; + + switch( uMsg ) + { + case WM_KEYDOWN: + { + switch( wParam ) + { + case VK_TAB: + // We don't process Tab in case keyboard input is enabled and the user + // wishes to Tab to other controls. + break; + + case VK_HOME: + PlaceCaret( 0 ); + if( GetKeyState( VK_SHIFT ) >= 0 ) + // Shift is not down. Update selection + // start along with the caret. + m_nSelStart = m_nCaret; + ResetCaretBlink(); + bHandled = true; + break; + + case VK_END: + PlaceCaret( m_Buffer.GetTextSize() ); + if( GetKeyState( VK_SHIFT ) >= 0 ) + // Shift is not down. Update selection + // start along with the caret. + m_nSelStart = m_nCaret; + ResetCaretBlink(); + bHandled = true; + break; + + case VK_INSERT: + if( GetKeyState( VK_CONTROL ) < 0 ) + { + // Control Insert. Copy to clipboard + CopyToClipboard(); + } + else if( GetKeyState( VK_SHIFT ) < 0 ) + { + // Shift Insert. Paste from clipboard + PasteFromClipboard(); + } + else + { + // Toggle caret insert mode + m_bInsertMode = !m_bInsertMode; + } + break; + + case VK_DELETE: + // Check if there is a text selection. + if( m_nCaret != m_nSelStart ) + { + DeleteSelectionText(); + m_pDialog->SendEvent( EVENT_EDITBOX_CHANGE, true, this ); + } + else + { + // Deleting one character + if( m_Buffer.RemoveChar( m_nCaret ) ) + m_pDialog->SendEvent( EVENT_EDITBOX_CHANGE, true, this ); + } + ResetCaretBlink(); + bHandled = true; + break; + + case VK_LEFT: + if( GetKeyState( VK_CONTROL ) < 0 ) + { + // Control is down. Move the caret to a new item + // instead of a character. + m_Buffer.GetPriorItemPos( m_nCaret, &m_nCaret ); + PlaceCaret( m_nCaret ); + } + else if( m_nCaret > 0 ) + PlaceCaret( m_nCaret - 1 ); + if( GetKeyState( VK_SHIFT ) >= 0 ) + // Shift is not down. Update selection + // start along with the caret. + m_nSelStart = m_nCaret; + ResetCaretBlink(); + bHandled = true; + break; + + case VK_RIGHT: + if( GetKeyState( VK_CONTROL ) < 0 ) + { + // Control is down. Move the caret to a new item + // instead of a character. + m_Buffer.GetNextItemPos( m_nCaret, &m_nCaret ); + PlaceCaret( m_nCaret ); + } + else if( m_nCaret < m_Buffer.GetTextSize() ) + PlaceCaret( m_nCaret + 1 ); + if( GetKeyState( VK_SHIFT ) >= 0 ) + // Shift is not down. Update selection + // start along with the caret. + m_nSelStart = m_nCaret; + ResetCaretBlink(); + bHandled = true; + break; + + case VK_UP: + case VK_DOWN: + // Trap up and down arrows so that the dialog + // does not switch focus to another control. + bHandled = true; + break; + + default: + bHandled = wParam != VK_ESCAPE; // Let the application handle Esc. + } + } + } + return bHandled; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTEditBox::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + { + if( !m_bHasFocus ) + m_pDialog->RequestFocus( this ); + + if( !ContainsPoint( pt ) ) + return false; + + m_bMouseDrag = true; + SetCapture( DXUTGetHWND() ); + // Determine the character corresponding to the coordinates. + int nCP, nTrail, nX1st; + m_Buffer.CPtoX( m_nFirstVisible, FALSE, &nX1st ); // X offset of the 1st visible char + if( m_Buffer.XtoCP( pt.x - m_rcText.left + nX1st, &nCP, &nTrail ) ) + { + // Cap at the nul character. + if( nTrail && nCP < m_Buffer.GetTextSize() ) + PlaceCaret( nCP + 1 ); + else + PlaceCaret( nCP ); + m_nSelStart = m_nCaret; + ResetCaretBlink(); + } + return true; + } + + case WM_LBUTTONUP: + ReleaseCapture(); + m_bMouseDrag = false; + break; + + case WM_MOUSEMOVE: + if( m_bMouseDrag ) + { + // Determine the character corresponding to the coordinates. + int nCP, nTrail, nX1st; + m_Buffer.CPtoX( m_nFirstVisible, FALSE, &nX1st ); // X offset of the 1st visible char + if( m_Buffer.XtoCP( pt.x - m_rcText.left + nX1st, &nCP, &nTrail ) ) + { + // Cap at the nul character. + if( nTrail && nCP < m_Buffer.GetTextSize() ) + PlaceCaret( nCP + 1 ); + else + PlaceCaret( nCP ); + } + } + break; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTEditBox::OnFocusIn() +{ + CDXUTControl::OnFocusIn(); + + ResetCaretBlink(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTEditBox::MsgProc( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(lParam); + + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + // Make sure that while editing, the keyup and keydown messages associated with + // WM_CHAR messages don't go to any non-focused controls or cameras + case WM_KEYUP: + case WM_KEYDOWN: + return true; + + case WM_CHAR: + { + switch( ( WCHAR )wParam ) + { + // Backspace + case VK_BACK: + { + // If there's a selection, treat this + // like a delete key. + if( m_nCaret != m_nSelStart ) + { + DeleteSelectionText(); + m_pDialog->SendEvent( EVENT_EDITBOX_CHANGE, true, this ); + } + else if( m_nCaret > 0 ) + { + // Move the caret, then delete the char. + PlaceCaret( m_nCaret - 1 ); + m_nSelStart = m_nCaret; + m_Buffer.RemoveChar( m_nCaret ); + m_pDialog->SendEvent( EVENT_EDITBOX_CHANGE, true, this ); + } + ResetCaretBlink(); + break; + } + + case 24: // Ctrl-X Cut + case VK_CANCEL: // Ctrl-C Copy + { + CopyToClipboard(); + + // If the key is Ctrl-X, delete the selection too. + if( ( WCHAR )wParam == 24 ) + { + DeleteSelectionText(); + m_pDialog->SendEvent( EVENT_EDITBOX_CHANGE, true, this ); + } + + break; + } + + // Ctrl-V Paste + case 22: + { + PasteFromClipboard(); + m_pDialog->SendEvent( EVENT_EDITBOX_CHANGE, true, this ); + break; + } + + // Ctrl-A Select All + case 1: + if( m_nSelStart == m_nCaret ) + { + m_nSelStart = 0; + PlaceCaret( m_Buffer.GetTextSize() ); + } + break; + + case VK_RETURN: + // Invoke the callback when the user presses Enter. + m_pDialog->SendEvent( EVENT_EDITBOX_STRING, true, this ); + break; + + // Junk characters we don't want in the string + case 26: // Ctrl Z + case 2: // Ctrl B + case 14: // Ctrl N + case 19: // Ctrl S + case 4: // Ctrl D + case 6: // Ctrl F + case 7: // Ctrl G + case 10: // Ctrl J + case 11: // Ctrl K + case 12: // Ctrl L + case 17: // Ctrl Q + case 23: // Ctrl W + case 5: // Ctrl E + case 18: // Ctrl R + case 20: // Ctrl T + case 25: // Ctrl Y + case 21: // Ctrl U + case 9: // Ctrl I + case 15: // Ctrl O + case 16: // Ctrl P + case 27: // Ctrl [ + case 29: // Ctrl ] + case 28: // Ctrl \ + break; + + default: + { + // If there's a selection and the user + // starts to type, the selection should + // be deleted. + if( m_nCaret != m_nSelStart ) + DeleteSelectionText(); + + // If we are in overwrite mode and there is already + // a char at the caret's position, simply replace it. + // Otherwise, we insert the char as normal. + if( !m_bInsertMode && m_nCaret < m_Buffer.GetTextSize() ) + { + m_Buffer[m_nCaret] = ( WCHAR )wParam; + PlaceCaret( m_nCaret + 1 ); + m_nSelStart = m_nCaret; + } + else + { + // Insert the char + if( m_Buffer.InsertChar( m_nCaret, ( WCHAR )wParam ) ) + { + PlaceCaret( m_nCaret + 1 ); + m_nSelStart = m_nCaret; + } + } + ResetCaretBlink(); + m_pDialog->SendEvent( EVENT_EDITBOX_CHANGE, true, this ); + } + } + return true; + } + } + return false; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTEditBox::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + + int nSelStartX = 0, nCaretX = 0; // Left and right X cordinates of the selection region + + auto pElement = GetElement( 0 ); + if( pElement ) + { + m_Buffer.SetFontNode( m_pDialog->GetFont( pElement->iFont ) ); + PlaceCaret( m_nCaret ); // Call PlaceCaret now that we have the font info (node), + // so that scrolling can be handled. + } + + // Render the control graphics + for( int e = 0; e < 9; ++e ) + { + pElement = m_Elements[ e ]; + pElement->TextureColor.Blend( DXUT_STATE_NORMAL, fElapsedTime ); + + m_pDialog->DrawSprite( pElement, &m_rcRender[e], DXUT_FAR_BUTTON_DEPTH ); + } + + // + // Compute the X coordinates of the first visible character. + // + int nXFirst; + m_Buffer.CPtoX( m_nFirstVisible, FALSE, &nXFirst ); + + // + // Compute the X coordinates of the selection rectangle + // + m_Buffer.CPtoX( m_nCaret, FALSE, &nCaretX ); + if( m_nCaret != m_nSelStart ) + m_Buffer.CPtoX( m_nSelStart, FALSE, &nSelStartX ); + else + nSelStartX = nCaretX; + + // + // Render the selection rectangle + // + RECT rcSelection; // Make this available for rendering selected text + if( m_nCaret != m_nSelStart ) + { + int nSelLeftX = nCaretX, nSelRightX = nSelStartX; + // Swap if left is bigger than right + if( nSelLeftX > nSelRightX ) + { + int nTemp = nSelLeftX; nSelLeftX = nSelRightX; nSelRightX = nTemp; + } + + SetRect( &rcSelection, nSelLeftX, m_rcText.top, nSelRightX, m_rcText.bottom ); + OffsetRect( &rcSelection, m_rcText.left - nXFirst, 0 ); + IntersectRect( &rcSelection, &m_rcText, &rcSelection ); + + m_pDialog->DrawRect( &rcSelection, m_SelBkColor ); + } + + // + // Render the text + // + // Element 0 for text + m_Elements[ 0 ]->FontColor.SetCurrent( m_TextColor ); + m_pDialog->DrawText( m_Buffer.GetBuffer() + m_nFirstVisible, m_Elements[ 0 ], &m_rcText ); + + // Render the selected text + if( m_nCaret != m_nSelStart ) + { + int nFirstToRender = std::max( m_nFirstVisible, std::min( m_nSelStart, m_nCaret ) ); + m_Elements[ 0 ]->FontColor.SetCurrent( m_SelTextColor ); + m_pDialog->DrawText( m_Buffer.GetBuffer() + nFirstToRender, + m_Elements[ 0 ], &rcSelection, false ); + } + + // + // Blink the caret + // + if( DXUTGetGlobalTimer()->GetAbsoluteTime() - m_dfLastBlink >= m_dfBlink ) + { + m_bCaretOn = !m_bCaretOn; + m_dfLastBlink = DXUTGetGlobalTimer()->GetAbsoluteTime(); + } + + // + // Render the caret if this control has the focus + // + if( m_bHasFocus && m_bCaretOn && !s_bHideCaret ) + { + // Start the rectangle with insert mode caret + RECT rcCaret = + { + m_rcText.left - nXFirst + nCaretX - 1, m_rcText.top, + m_rcText.left - nXFirst + nCaretX + 1, m_rcText.bottom + }; + + // If we are in overwrite mode, adjust the caret rectangle + // to fill the entire character. + if( !m_bInsertMode ) + { + // Obtain the right edge X coord of the current character + int nRightEdgeX; + m_Buffer.CPtoX( m_nCaret, TRUE, &nRightEdgeX ); + rcCaret.right = m_rcText.left - nXFirst + nRightEdgeX; + } + + m_pDialog->DrawRect( &rcCaret, m_CaretColor ); + } +} + + +#define IN_FLOAT_CHARSET( c ) \ + ( (c) == L'-' || (c) == L'.' || ( (c) >= L'0' && (c) <= L'9' ) ) + +_Use_decl_annotations_ +void CDXUTEditBox::ParseFloatArray( float* pNumbers, int nCount ) +{ + int nWritten = 0; // Number of floats written + const WCHAR* pToken, *pEnd; + WCHAR wszToken[60]; + + pToken = m_Buffer.GetBuffer(); + while( nWritten < nCount && *pToken != L'\0' ) + { + // Skip leading spaces + while( *pToken == L' ' ) + ++pToken; + + if( *pToken == L'\0' ) + break; + + // Locate the end of number + pEnd = pToken; + while( IN_FLOAT_CHARSET( *pEnd ) ) + ++pEnd; + + // Copy the token to our buffer + int nTokenLen = std::min( sizeof( wszToken ) / sizeof( wszToken[0] ) - 1, int( pEnd - pToken ) ); + wcscpy_s( wszToken, nTokenLen, pToken ); + *pNumbers = ( float )wcstod( wszToken, nullptr ); + ++nWritten; + ++pNumbers; + pToken = pEnd; + } +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTEditBox::SetTextFloatArray( const float* pNumbers, int nCount ) +{ + WCHAR wszBuffer[512] = + { + 0 + }; + WCHAR wszTmp[64]; + + if( !pNumbers ) + return; + + for( int i = 0; i < nCount; ++i ) + { + swprintf_s( wszTmp, 64, L"%.4f ", pNumbers[i] ); + wcscat_s( wszBuffer, 512, wszTmp ); + } + + // Don't want the last space + if( nCount > 0 && wcslen( wszBuffer ) > 0 ) + wszBuffer[wcslen( wszBuffer ) - 1] = 0; + + SetText( wszBuffer ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTEditBox::ResetCaretBlink() +{ + m_bCaretOn = true; + m_dfLastBlink = DXUTGetGlobalTimer()->GetAbsoluteTime(); +} + + +//====================================================================================== +// CUniBuffer +//====================================================================================== + +//-------------------------------------------------------------------------------------- +bool CUniBuffer::SetBufferSize( _In_ int nNewSize ) +{ + // If the current size is already the maximum allowed, + // we can't possibly allocate more. + if( m_nBufferSize >= DXUT_MAX_EDITBOXLENGTH ) + return false; + + int nAllocateSize = ( nNewSize == -1 || nNewSize < m_nBufferSize * 2 ) ? ( m_nBufferSize ? m_nBufferSize * + 2 : 256 ) : nNewSize * 2; + + // Cap the buffer size at the maximum allowed. + if( nAllocateSize > DXUT_MAX_EDITBOXLENGTH ) + nAllocateSize = DXUT_MAX_EDITBOXLENGTH; + + auto pTempBuffer = new (std::nothrow) WCHAR[nAllocateSize]; + if( !pTempBuffer ) + return false; + + ZeroMemory( pTempBuffer, sizeof( WCHAR ) * nAllocateSize ); + + if( m_pwszBuffer ) + { + memcpy( pTempBuffer, m_pwszBuffer, m_nBufferSize * sizeof( WCHAR ) ); + delete[] m_pwszBuffer; + } + + m_pwszBuffer = pTempBuffer; + m_nBufferSize = nAllocateSize; + return true; +} + + +//-------------------------------------------------------------------------------------- +// Uniscribe -- Analyse() analyses the string in the buffer +//-------------------------------------------------------------------------------------- +HRESULT CUniBuffer::Analyse() +{ + if( m_Analysis ) + (void)ScriptStringFree( &m_Analysis ); + + SCRIPT_CONTROL ScriptControl = {}; // For uniscribe + SCRIPT_STATE ScriptState = {}; // For uniscribe + +#pragma warning(push) +#pragma warning(disable : 4616 6309 6387 ) + HRESULT hr = ScriptApplyDigitSubstitution( nullptr, &ScriptControl, &ScriptState ); + if ( FAILED(hr) ) + return hr; +#pragma warning(pop) + + if( !m_pFontNode ) + return E_FAIL; + + HDC hDC = nullptr; + hr = ScriptStringAnalyse( hDC, + m_pwszBuffer, + (int)wcslen( m_pwszBuffer ) + 1, // nul is also analyzed. + (int)wcslen( m_pwszBuffer ) * 3 / 2 + 16, + -1, + SSA_BREAK | SSA_GLYPHS | SSA_FALLBACK | SSA_LINK, + 0, + &ScriptControl, + &ScriptState, + nullptr, + nullptr, + nullptr, + &m_Analysis ); + if( SUCCEEDED( hr ) ) + m_bAnalyseRequired = false; // Analysis is up-to-date + return hr; +} + + +//-------------------------------------------------------------------------------------- +CUniBuffer::CUniBuffer( _In_ int nInitialSize ) noexcept +{ + m_nBufferSize = 0; + m_pwszBuffer = nullptr; + m_bAnalyseRequired = true; + m_Analysis = nullptr; + m_pFontNode = nullptr; + + if( nInitialSize > 0 ) + SetBufferSize( nInitialSize ); +} + + +//-------------------------------------------------------------------------------------- +CUniBuffer::~CUniBuffer() +{ + delete[] m_pwszBuffer; + if( m_Analysis ) + (void)ScriptStringFree( &m_Analysis ); +} + + +//-------------------------------------------------------------------------------------- +WCHAR& CUniBuffer::operator[]( _In_ int n ) // No param checking +{ + // This version of operator[] is called only + // if we are asking for write access, so + // re-analysis is required. + m_bAnalyseRequired = true; + return m_pwszBuffer[n]; +} + + +//-------------------------------------------------------------------------------------- +void CUniBuffer::Clear() +{ + *m_pwszBuffer = L'\0'; + m_bAnalyseRequired = true; +} + + +//-------------------------------------------------------------------------------------- +// Inserts the char at specified index. +// If nIndex == -1, insert to the end. +//-------------------------------------------------------------------------------------- +bool CUniBuffer::InsertChar( _In_ int nIndex, _In_ WCHAR wChar ) +{ + assert( nIndex >= 0 ); + + if( nIndex < 0 || nIndex > (int)wcslen( m_pwszBuffer ) ) + return false; // invalid index + + // Check for maximum length allowed + if( GetTextSize() + 1 >= DXUT_MAX_EDITBOXLENGTH ) + return false; + + if( (int)wcslen( m_pwszBuffer ) + 1 >= m_nBufferSize ) + { + if( !SetBufferSize( -1 ) ) + return false; // out of memory + } + + assert( m_nBufferSize >= 2 ); + + // Shift the characters after the index, start by copying the null terminator + WCHAR* dest = m_pwszBuffer + wcslen( m_pwszBuffer ) + 1; + WCHAR* stop = m_pwszBuffer + nIndex; + WCHAR* src = dest - 1; + + while( dest > stop ) + { + *dest-- = *src--; + } + + // Set new character + m_pwszBuffer[ nIndex ] = wChar; + m_bAnalyseRequired = true; + + return true; +} + + +//-------------------------------------------------------------------------------------- +// Removes the char at specified index. +// If nIndex == -1, remove the last char. +//-------------------------------------------------------------------------------------- +bool CUniBuffer::RemoveChar( _In_ int nIndex ) +{ + if( !wcslen( m_pwszBuffer ) || nIndex < 0 || nIndex >= (int)wcslen( m_pwszBuffer ) ) + return false; // Invalid index + + MoveMemory( m_pwszBuffer + nIndex, m_pwszBuffer + nIndex + 1, sizeof( WCHAR ) * + ( wcslen( m_pwszBuffer ) - nIndex ) ); + m_bAnalyseRequired = true; + return true; +} + + +//-------------------------------------------------------------------------------------- +// Inserts the first nCount characters of the string pStr at specified index. +// If nCount == -1, the entire string is inserted. +// If nIndex == -1, insert to the end. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CUniBuffer::InsertString( int nIndex, const WCHAR* pStr, int nCount ) +{ + assert( nIndex >= 0 ); + if( nIndex < 0 ) + return false; + + if( nIndex > (int)wcslen( m_pwszBuffer ) ) + return false; // invalid index + + if( -1 == nCount ) + nCount = (int)wcslen( pStr ); + + // Check for maximum length allowed + if( GetTextSize() + nCount >= DXUT_MAX_EDITBOXLENGTH ) + return false; + + if( (int)wcslen( m_pwszBuffer ) + nCount >= m_nBufferSize ) + { + if( !SetBufferSize( (int)wcslen( m_pwszBuffer ) + nCount + 1 ) ) + return false; // out of memory + } + + MoveMemory( m_pwszBuffer + nIndex + nCount, m_pwszBuffer + nIndex, sizeof( WCHAR ) * + ( wcslen( m_pwszBuffer ) - nIndex + 1 ) ); + memcpy( m_pwszBuffer + nIndex, pStr, nCount * sizeof( WCHAR ) ); + m_bAnalyseRequired = true; + + return true; +} + + +//-------------------------------------------------------------------------------------- +bool CUniBuffer::SetText( _In_z_ LPCWSTR wszText ) +{ + assert( wszText ); + + size_t nRequired = wcslen( wszText ) + 1; + + // Check for maximum length allowed + if( nRequired >= DXUT_MAX_EDITBOXLENGTH ) + return false; + + while( GetBufferSize() < nRequired ) + if( !SetBufferSize( -1 ) ) + break; + // Check again in case out of memory occurred inside while loop. + if( GetBufferSize() >= nRequired ) + { + wcscpy_s( m_pwszBuffer, GetBufferSize(), wszText ); + m_bAnalyseRequired = true; + return true; + } + else + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CUniBuffer::CPtoX( int nCP, bool bTrail, int* pX ) +{ + assert( pX ); + *pX = 0; // Default + + HRESULT hr = S_OK; + if( m_bAnalyseRequired ) + hr = Analyse(); + + if( SUCCEEDED( hr ) ) + hr = ScriptStringCPtoX( m_Analysis, nCP, bTrail, pX ); + + if ( FAILED(hr) ) + { + *pX = 0; + return false; + } + + return true; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CUniBuffer::XtoCP( int nX, int* pCP, int* pnTrail ) +{ + assert( pCP && pnTrail ); + *pCP = 0; *pnTrail = FALSE; // Default + + HRESULT hr = S_OK; + if( m_bAnalyseRequired ) + hr = Analyse(); + + if (SUCCEEDED(hr)) + { + hr = ScriptStringXtoCP( m_Analysis, nX, pCP, pnTrail ); + if (FAILED(hr)) + { + *pCP = 0; *pnTrail = FALSE; + return false; + } + } + + // If the coordinate falls outside the text region, we + // can get character positions that don't exist. We must + // filter them here and convert them to those that do exist. + if( *pCP == -1 && *pnTrail == TRUE ) + { + *pCP = 0; *pnTrail = FALSE; + } + else if( *pCP > (int)wcslen( m_pwszBuffer ) && *pnTrail == FALSE ) + { + *pCP = (int)wcslen( m_pwszBuffer ); *pnTrail = TRUE; + } + + if (FAILED(hr)) + { + *pCP = 0; *pnTrail = FALSE; + return false; + } + return true; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CUniBuffer::GetPriorItemPos( int nCP, int* pPrior ) +{ + *pPrior = nCP; // Default is the char itself + + if( m_bAnalyseRequired ) + if( FAILED( Analyse() ) ) + return; + + const SCRIPT_LOGATTR* pLogAttr = ScriptString_pLogAttr( m_Analysis ); + if( !pLogAttr ) + return; + + if( !ScriptString_pcOutChars( m_Analysis ) ) + return; + int nInitial = *ScriptString_pcOutChars( m_Analysis ); + if( nCP - 1 < nInitial ) + nInitial = nCP - 1; + for( int i = nInitial; i > 0; --i ) + if( pLogAttr[i].fWordStop || // Either the fWordStop flag is set + ( !pLogAttr[i].fWhiteSpace && // Or the previous char is whitespace but this isn't. + pLogAttr[i - 1].fWhiteSpace ) ) + { + *pPrior = i; + return; + } + // We have reached index 0. 0 is always a break point, so simply return it. + *pPrior = 0; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CUniBuffer::GetNextItemPos( int nCP, int* pPrior ) +{ + *pPrior = nCP; // Default is the char itself + + HRESULT hr = S_OK; + if( m_bAnalyseRequired ) + hr = Analyse(); + if( FAILED( hr ) ) + return; + + const SCRIPT_LOGATTR* pLogAttr = ScriptString_pLogAttr( m_Analysis ); + if( !pLogAttr ) + return; + + if( !ScriptString_pcOutChars( m_Analysis ) ) + return; + int nInitial = *ScriptString_pcOutChars( m_Analysis ); + if( nCP + 1 < nInitial ) + nInitial = nCP + 1; + + int i = nInitial; + int limit = *ScriptString_pcOutChars( m_Analysis ); + while( limit > 0 && i < limit - 1 ) + { + if( pLogAttr[i].fWordStop ) // Either the fWordStop flag is set + { + *pPrior = i; + return; + } + else if( pLogAttr[i].fWhiteSpace && // Or this whitespace but the next char isn't. + !pLogAttr[i + 1].fWhiteSpace ) + { + *pPrior = i + 1; // The next char is a word stop + return; + } + + ++i; + limit = *ScriptString_pcOutChars( m_Analysis ); + } + // We have reached the end. It's always a word stop, so simply return it. + *pPrior = *ScriptString_pcOutChars( m_Analysis ) - 1; +} + + +//====================================================================================== +// DXUTBlendColor +//====================================================================================== + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DXUTBlendColor::Init( DWORD defaultColor, DWORD disabledColor, DWORD hiddenColor ) +{ + for( int i = 0; i < MAX_CONTROL_STATES; i++ ) + { + States[ i ] = defaultColor; + } + + States[ DXUT_STATE_DISABLED ] = disabledColor; + States[ DXUT_STATE_HIDDEN ] = hiddenColor; + SetCurrent( hiddenColor ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void DXUTBlendColor::Blend( UINT iState, float fElapsedTime, float fRate ) +{ + XMFLOAT4 destColor = D3DCOLOR_TO_D3DCOLORVALUE( States[ iState ] ); + XMVECTOR clr1 = XMLoadFloat4( &destColor ); + XMVECTOR clr = XMLoadFloat4( &Current ); + clr = XMVectorLerp( clr, clr1, 1.0f - powf( fRate, 30 * fElapsedTime ) ); + XMStoreFloat4( &Current, clr ); +} + + +//-------------------------------------------------------------------------------------- +void DXUTBlendColor::SetCurrent( DWORD color ) +{ + Current = D3DCOLOR_TO_D3DCOLORVALUE( color ); +} + + +//====================================================================================== +// CDXUTElement +//====================================================================================== + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTElement::SetTexture( UINT texture, RECT* prcTexture, DWORD defaultTextureColor ) +{ + iTexture = texture; + + if( prcTexture ) + rcTexture = *prcTexture; + else + SetRectEmpty( &rcTexture ); + + TextureColor.Init( defaultTextureColor ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTElement::SetFont( UINT font, DWORD defaultFontColor, DWORD textFormat ) +{ + iFont = font; + dwTextFormat = textFormat; + + FontColor.Init( defaultFontColor ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTElement::Refresh() +{ + TextureColor.SetCurrent( TextureColor.States[ DXUT_STATE_HIDDEN ] ); + FontColor.SetCurrent( FontColor.States[ DXUT_STATE_HIDDEN ] ); +} diff --git a/src/DX11/framework/dxut/Optional/DXUTgui.h b/src/DX11/framework/dxut/Optional/DXUTgui.h new file mode 100644 index 0000000..4f38ce4 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTgui.h @@ -0,0 +1,1121 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTgui.h +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +#include +#include + +#ifdef DXUT_AUTOLIB +#pragma comment( lib, "usp10.lib" ) +#endif + +//-------------------------------------------------------------------------------------- +// Defines and macros +//-------------------------------------------------------------------------------------- +#define EVENT_BUTTON_CLICKED 0x0101 +#define EVENT_COMBOBOX_SELECTION_CHANGED 0x0201 +#define EVENT_RADIOBUTTON_CHANGED 0x0301 +#define EVENT_CHECKBOX_CHANGED 0x0401 +#define EVENT_SLIDER_VALUE_CHANGED 0x0501 +#define EVENT_SLIDER_VALUE_CHANGED_UP 0x0502 + +#define EVENT_EDITBOX_STRING 0x0601 +// EVENT_EDITBOX_CHANGE is sent when the listbox content changes +// due to user input. +#define EVENT_EDITBOX_CHANGE 0x0602 +#define EVENT_LISTBOX_ITEM_DBLCLK 0x0701 +// EVENT_LISTBOX_SELECTION is fired off when the selection changes in +// a single selection list box. +#define EVENT_LISTBOX_SELECTION 0x0702 +#define EVENT_LISTBOX_SELECTION_END 0x0703 + + +//-------------------------------------------------------------------------------------- +// Forward declarations +//-------------------------------------------------------------------------------------- +class CDXUTDialogResourceManager; +class CDXUTControl; +class CDXUTButton; +class CDXUTStatic; +class CDXUTCheckBox; +class CDXUTRadioButton; +class CDXUTComboBox; +class CDXUTSlider; +class CDXUTEditBox; +class CDXUTListBox; +class CDXUTScrollBar; +class CDXUTElement; +struct DXUTElementHolder; +struct DXUTTextureNode; +struct DXUTFontNode; +typedef void ( CALLBACK*PCALLBACKDXUTGUIEVENT )( _In_ UINT nEvent, _In_ int nControlID, _In_ CDXUTControl* pControl, + _In_opt_ void* pUserContext ); + + +//-------------------------------------------------------------------------------------- +// Enums for pre-defined control types +//-------------------------------------------------------------------------------------- +enum DXUT_CONTROL_TYPE +{ + DXUT_CONTROL_BUTTON, + DXUT_CONTROL_STATIC, + DXUT_CONTROL_CHECKBOX, + DXUT_CONTROL_RADIOBUTTON, + DXUT_CONTROL_COMBOBOX, + DXUT_CONTROL_SLIDER, + DXUT_CONTROL_EDITBOX, + DXUT_CONTROL_IMEEDITBOX, + DXUT_CONTROL_LISTBOX, + DXUT_CONTROL_SCROLLBAR, +}; + +enum DXUT_CONTROL_STATE +{ + DXUT_STATE_NORMAL = 0, + DXUT_STATE_DISABLED, + DXUT_STATE_HIDDEN, + DXUT_STATE_FOCUS, + DXUT_STATE_MOUSEOVER, + DXUT_STATE_PRESSED, +}; + +#define MAX_CONTROL_STATES 6 + +struct DXUTBlendColor +{ + void Init( _In_ DWORD defaultColor, _In_ DWORD disabledColor = D3DCOLOR_ARGB( 200, 128, 128, 128 ), _In_ DWORD hiddenColor = 0 ); + void Blend( _In_ UINT iState, _In_ float fElapsedTime, _In_ float fRate = 0.7f ); + + DWORD States[ MAX_CONTROL_STATES ]; // Modulate colors for all possible control states + DirectX::XMFLOAT4 Current; + + void SetCurrent( DWORD color ); +}; + + +//----------------------------------------------------------------------------- +// Contains all the display tweakables for a sub-control +//----------------------------------------------------------------------------- +class CDXUTElement +{ +public: + void SetTexture( _In_ UINT texture, _In_ RECT* prcTexture, _In_ DWORD defaultTextureColor = D3DCOLOR_ARGB( 255, 255, 255, 255 ) ); + void SetFont( _In_ UINT font, _In_ DWORD defaultFontColor = D3DCOLOR_ARGB( 255, 255, 255, 255 ), DWORD textFormat = DT_CENTER | DT_VCENTER ); + + void Refresh(); + + UINT iTexture; // Index of the texture for this Element + UINT iFont; // Index of the font for this Element + DWORD dwTextFormat; // The format argument to DrawText + + RECT rcTexture; // Bounding rect of this element on the composite texture + + DXUTBlendColor TextureColor; + DXUTBlendColor FontColor; +}; + + +//----------------------------------------------------------------------------- +// All controls must be assigned to a dialog, which handles +// input and rendering for the controls. +//----------------------------------------------------------------------------- +class CDXUTDialog +{ + friend class CDXUTDialogResourceManager; + +public: + CDXUTDialog() noexcept; + ~CDXUTDialog(); + + // Need to call this now + void Init( _In_ CDXUTDialogResourceManager* pManager, _In_ bool bRegisterDialog = true ); + void Init( _In_ CDXUTDialogResourceManager* pManager, _In_ bool bRegisterDialog, + _In_z_ LPCWSTR pszControlTextureFilename ); + void Init( _In_ CDXUTDialogResourceManager* pManager, _In_ bool bRegisterDialog, + _In_z_ LPCWSTR szControlTextureResourceName, _In_ HMODULE hControlTextureResourceModule ); + + // Windows message handler + bool MsgProc( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); + + // Control creation + HRESULT AddStatic( _In_ int ID, _In_z_ LPCWSTR strText, _In_ int x, _In_ int y, _In_ int width, _In_ int height, _In_ bool bIsDefault=false, + _Out_opt_ CDXUTStatic** ppCreated = nullptr ); + HRESULT AddButton( _In_ int ID, _In_z_ LPCWSTR strText, _In_ int x, _In_ int y, _In_ int width, _In_ int height, _In_ UINT nHotkey=0, + _In_ bool bIsDefault=false, _Out_opt_ CDXUTButton** ppCreated = nullptr ); + HRESULT AddCheckBox( _In_ int ID, _In_z_ LPCWSTR strText, _In_ int x, _In_ int y, _In_ int width, _In_ int height, _In_ bool bChecked=false, + _In_ UINT nHotkey=0, _In_ bool bIsDefault=false, _Out_opt_ CDXUTCheckBox** ppCreated = nullptr ); + HRESULT AddRadioButton( _In_ int ID, _In_ UINT nButtonGroup, _In_z_ LPCWSTR strText, _In_ int x, _In_ int y, _In_ int width, + _In_ int height, _In_ bool bChecked=false, _In_ UINT nHotkey=0, _In_ bool bIsDefault=false, + _Out_opt_ CDXUTRadioButton** ppCreated = nullptr ); + HRESULT AddComboBox( _In_ int ID, _In_ int x, _In_ int y, _In_ int width, _In_ int height, _In_ UINT nHotKey=0, _In_ bool bIsDefault=false, + _Out_opt_ CDXUTComboBox** ppCreated = nullptr ); + HRESULT AddSlider( _In_ int ID, _In_ int x, _In_ int y, _In_ int width, _In_ int height, _In_ int min=0, _In_ int max=100, _In_ int value=50, + _In_ bool bIsDefault=false, _Out_opt_ CDXUTSlider** ppCreated = nullptr ); + // AddIMEEditBox has been renamed into DXUTguiIME.cpp as CDXUTIMEEditBox::CreateIMEEditBox + HRESULT AddEditBox( _In_ int ID, _In_z_ LPCWSTR strText, _In_ int x, _In_ int y, _In_ int width, _In_ int height, _In_ bool bIsDefault=false, + _Out_opt_ CDXUTEditBox** ppCreated = nullptr ); + HRESULT AddListBox( _In_ int ID, _In_ int x, _In_ int y, _In_ int width, _In_ int height, _In_ DWORD dwStyle=0, + _Out_opt_ CDXUTListBox** ppCreated = nullptr ); + HRESULT AddControl( _In_ CDXUTControl* pControl ); + HRESULT InitControl( _In_ CDXUTControl* pControl ); + + // Control retrieval + CDXUTStatic* GetStatic( _In_ int ID ) const + { + return reinterpret_cast( GetControl( ID, DXUT_CONTROL_STATIC ) ); + } + CDXUTButton* GetButton( _In_ int ID ) const + { + return reinterpret_cast( GetControl(ID, DXUT_CONTROL_BUTTON) ); + } + CDXUTCheckBox* GetCheckBox( _In_ int ID ) const + { + return reinterpret_cast( GetControl(ID, DXUT_CONTROL_CHECKBOX) ); + } + CDXUTRadioButton* GetRadioButton( _In_ int ID ) const + { + return reinterpret_cast( GetControl(ID, DXUT_CONTROL_RADIOBUTTON) ); + } + CDXUTComboBox* GetComboBox( _In_ int ID ) const + { + return reinterpret_cast( GetControl(ID, DXUT_CONTROL_COMBOBOX) ); + } + CDXUTSlider* GetSlider( _In_ int ID ) const + { + return reinterpret_cast( GetControl(ID, DXUT_CONTROL_SLIDER) ); + } + CDXUTEditBox* GetEditBox( _In_ int ID ) const + { + return reinterpret_cast( GetControl(ID, DXUT_CONTROL_EDITBOX) ); + } + CDXUTListBox* GetListBox( _In_ int ID ) const + { + return reinterpret_cast( GetControl(ID, DXUT_CONTROL_LISTBOX) ); + } + + CDXUTControl* GetControl( _In_ int ID ) const; + CDXUTControl* GetControl( _In_ int ID, _In_ UINT nControlType ) const; + CDXUTControl* GetControlAtPoint( _In_ const POINT& pt ) const; + + bool GetControlEnabled( _In_ int ID ) const; + void SetControlEnabled( _In_ int ID, _In_ bool bEnabled ); + + void ClearRadioButtonGroup( _In_ UINT nGroup ); + void ClearComboBox( _In_ int ID ); + + // Access the default display Elements used when adding new controls + HRESULT SetDefaultElement( _In_ UINT nControlType, _In_ UINT iElement, _In_ CDXUTElement* pElement ); + CDXUTElement* GetDefaultElement( _In_ UINT nControlType, _In_ UINT iElement ) const; + + // Methods called by controls + void SendEvent( _In_ UINT nEvent, _In_ bool bTriggeredByUser, _In_ CDXUTControl* pControl ); + void RequestFocus( _In_ CDXUTControl* pControl ); + + // Render helpers + HRESULT DrawRect( _In_ const RECT* pRect, _In_ DWORD color ); + HRESULT DrawSprite( _In_ CDXUTElement* pElement, _In_ const RECT* prcDest, _In_ float fDepth ); + HRESULT DrawSprite11( _In_ CDXUTElement* pElement, _In_ const RECT* prcDest, _In_ float fDepth ); + HRESULT CalcTextRect( _In_z_ LPCWSTR strText, _In_ CDXUTElement* pElement, _In_ const RECT* prcDest, _In_ int nCount = -1 ); + HRESULT DrawText( _In_z_ LPCWSTR strText, _In_ CDXUTElement* pElement, _In_ const RECT* prcDest, _In_ bool bShadow = false, + _In_ bool bCenter = false ); + + // Attributes + bool GetVisible() const { return m_bVisible; } + void SetVisible( _In_ bool bVisible ) { m_bVisible = bVisible; } + bool GetMinimized() const { return m_bMinimized; } + void SetMinimized( _In_ bool bMinimized ) {m_bMinimized = bMinimized; } + void SetBackgroundColors( _In_ DWORD colorAllCorners ) { SetBackgroundColors( colorAllCorners, colorAllCorners, colorAllCorners, colorAllCorners ); } + void SetBackgroundColors( _In_ DWORD colorTopLeft, _In_ DWORD colorTopRight, _In_ DWORD colorBottomLeft, _In_ DWORD colorBottomRight ); + void EnableCaption( _In_ bool bEnable ) { m_bCaption = bEnable; } + int GetCaptionHeight() const { return m_nCaptionHeight; } + void SetCaptionHeight( _In_ int nHeight ) { m_nCaptionHeight = nHeight; } + void SetCaptionText( _In_ const WCHAR* pwszText ) { wcscpy_s( m_wszCaption, sizeof( m_wszCaption ) / sizeof( m_wszCaption[0] ), pwszText ); } + void GetLocation( _Out_ POINT& Pt ) const + { + Pt.x = m_x; + Pt.y = m_y; + } + void SetLocation( _In_ int x, _In_ int y ) + { + m_x = x; + m_y = y; + } + void SetSize( _In_ int width, _In_ int height ) + { + m_width = width; + m_height = height; + } + int GetWidth() const { return m_width; } + int GetHeight() const { return m_height; } + + static void WINAPI SetRefreshTime( _In_ float fTime ) { s_fTimeRefresh = fTime; } + + static CDXUTControl* WINAPI GetNextControl( _In_ CDXUTControl* pControl ); + static CDXUTControl* WINAPI GetPrevControl( _In_ CDXUTControl* pControl ); + + void RemoveControl( _In_ int ID ); + void RemoveAllControls(); + + // Sets the callback used to notify the app of control events + void SetCallback( _In_ PCALLBACKDXUTGUIEVENT pCallback, _In_opt_ void* pUserContext = nullptr ); + void EnableNonUserEvents( _In_ bool bEnable ) { m_bNonUserEvents = bEnable; } + void EnableKeyboardInput( _In_ bool bEnable ) { m_bKeyboardInput = bEnable; } + void EnableMouseInput( _In_ bool bEnable ) { m_bMouseInput = bEnable; } + bool IsKeyboardInputEnabled() const { return m_bKeyboardInput; } + + // Device state notification + void Refresh(); + HRESULT OnRender( _In_ float fElapsedTime ); + + // Shared resource access. Indexed fonts and textures are shared among + // all the controls. + HRESULT SetFont( _In_ UINT index, _In_z_ LPCWSTR strFaceName, _In_ LONG height, _In_ LONG weight ); + DXUTFontNode* GetFont( _In_ UINT index ) const; + + HRESULT SetTexture( _In_ UINT index, _In_z_ LPCWSTR strFilename ); + HRESULT SetTexture( _In_ UINT index, _In_z_ LPCWSTR strResourceName, _In_ HMODULE hResourceModule ); + DXUTTextureNode* GetTexture( _In_ UINT index ) const; + + CDXUTDialogResourceManager* GetManager() const { return m_pManager; } + + static void WINAPI ClearFocus(); + void FocusDefaultControl(); + + bool m_bNonUserEvents; + bool m_bKeyboardInput; + bool m_bMouseInput; + +private: + int m_nDefaultControlID; + + static double s_fTimeRefresh; + double m_fTimeLastRefresh; + + // Initialize default Elements + void InitDefaultElements(); + + // Windows message handlers + void OnMouseMove( _In_ const POINT& pt ); + void OnMouseUp( _In_ const POINT& pt ); + + void SetNextDialog( _In_ CDXUTDialog* pNextDialog ); + + // Control events + bool OnCycleFocus( _In_ bool bForward ); + + static CDXUTControl* s_pControlFocus; // The control which has focus + static CDXUTControl* s_pControlPressed; // The control currently pressed + + CDXUTControl* m_pControlMouseOver; // The control which is hovered over + + bool m_bVisible; + bool m_bCaption; + bool m_bMinimized; + bool m_bDrag; + WCHAR m_wszCaption[256]; + + int m_x; + int m_y; + int m_width; + int m_height; + int m_nCaptionHeight; + + DWORD m_colorTopLeft; + DWORD m_colorTopRight; + DWORD m_colorBottomLeft; + DWORD m_colorBottomRight; + + CDXUTDialogResourceManager* m_pManager; + PCALLBACKDXUTGUIEVENT m_pCallbackEvent; + void* m_pCallbackEventUserContext; + + std::vector m_Textures; // Index into m_TextureCache; + std::vector m_Fonts; // Index into m_FontCache; + + std::vector m_Controls; + std::vector m_DefaultElements; + + CDXUTElement m_CapElement; // Element for the caption + + CDXUTDialog* m_pNextDialog; + CDXUTDialog* m_pPrevDialog; +}; + + +//-------------------------------------------------------------------------------------- +// Structs for shared resources +//-------------------------------------------------------------------------------------- +struct DXUTTextureNode +{ + bool bFileSource; // True if this texture is loaded from a file. False if from resource. + HMODULE hResourceModule; + int nResourceID; // Resource ID. If 0, string-based ID is used and stored in strFilename. + WCHAR strFilename[MAX_PATH]; + DWORD dwWidth; + DWORD dwHeight; + ID3D11Texture2D* pTexture11; + ID3D11ShaderResourceView* pTexResView11; +}; + +struct DXUTFontNode +{ + WCHAR strFace[MAX_PATH]; + LONG nHeight; + LONG nWeight; +}; + +struct DXUTSpriteVertex +{ + DirectX::XMFLOAT3 vPos; + DirectX::XMFLOAT4 vColor; + DirectX::XMFLOAT2 vTex; +}; + + +//----------------------------------------------------------------------------- +// Manages shared resources of dialogs +//----------------------------------------------------------------------------- +class CDXUTDialogResourceManager +{ +public: + CDXUTDialogResourceManager() noexcept; + ~CDXUTDialogResourceManager(); + + bool MsgProc( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); + + // D3D11 specific + HRESULT OnD3D11CreateDevice( _In_ ID3D11Device* pd3dDevice, _In_ ID3D11DeviceContext* pd3d11DeviceContext ); + HRESULT OnD3D11ResizedSwapChain( _In_ ID3D11Device* pd3dDevice, _In_ const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ); + void OnD3D11ReleasingSwapChain(); + void OnD3D11DestroyDevice(); + void StoreD3D11State( _In_ ID3D11DeviceContext* pd3dImmediateContext ); + void RestoreD3D11State( _In_ ID3D11DeviceContext* pd3dImmediateContext ); + void ApplyRenderUI11( _In_ ID3D11DeviceContext* pd3dImmediateContext ); + void ApplyRenderUIUntex11( _In_ ID3D11DeviceContext* pd3dImmediateContext ); + void BeginSprites11( ); + void EndSprites11( _In_ ID3D11Device* pd3dDevice, _In_ ID3D11DeviceContext* pd3dImmediateContext ); + + ID3D11Device* GetD3D11Device() const { return m_pd3d11Device; } + ID3D11DeviceContext* GetD3D11DeviceContext() const { return m_pd3d11DeviceContext; } + + DXUTFontNode* GetFontNode( _In_ size_t iIndex ) const { return m_FontCache[ iIndex ]; } + DXUTTextureNode* GetTextureNode( _In_ size_t iIndex ) const { return m_TextureCache[ iIndex ]; } + + int AddFont( _In_z_ LPCWSTR strFaceName, _In_ LONG height, _In_ LONG weight ); + int AddTexture( _In_z_ LPCWSTR strFilename ); + int AddTexture( _In_z_ LPCWSTR strResourceName, _In_ HMODULE hResourceModule ); + + bool RegisterDialog( _In_ CDXUTDialog* pDialog ); + void UnregisterDialog( _In_ CDXUTDialog* pDialog ); + void EnableKeyboardInputForAllDialogs(); + + // Shared between all dialogs + + // D3D11 + // Shaders + ID3D11VertexShader* m_pVSRenderUI11; + ID3D11PixelShader* m_pPSRenderUI11; + ID3D11PixelShader* m_pPSRenderUIUntex11; + + // States + ID3D11DepthStencilState* m_pDepthStencilStateUI11; + ID3D11RasterizerState* m_pRasterizerStateUI11; + ID3D11BlendState* m_pBlendStateUI11; + ID3D11SamplerState* m_pSamplerStateUI11; + + // Stored states + ID3D11DepthStencilState* m_pDepthStencilStateStored11; + UINT m_StencilRefStored11; + ID3D11RasterizerState* m_pRasterizerStateStored11; + ID3D11BlendState* m_pBlendStateStored11; + float m_BlendFactorStored11[4]; + UINT m_SampleMaskStored11; + ID3D11SamplerState* m_pSamplerStateStored11; + + ID3D11InputLayout* m_pInputLayout11; + ID3D11Buffer* m_pVBScreenQuad11; + + // Sprite workaround + ID3D11Buffer* m_pSpriteBuffer11; + UINT m_SpriteBufferBytes11; + std::vector m_SpriteVertices; + + UINT m_nBackBufferWidth; + UINT m_nBackBufferHeight; + + std::vector m_Dialogs; // Dialogs registered + +protected: + // D3D11 specific + ID3D11Device* m_pd3d11Device; + ID3D11DeviceContext* m_pd3d11DeviceContext; + HRESULT CreateTexture11( _In_ UINT index ); + + std::vector m_TextureCache; // Shared textures + std::vector m_FontCache; // Shared fonts +}; + + +//----------------------------------------------------------------------------- +// Base class for controls +//----------------------------------------------------------------------------- +class CDXUTControl +{ +public: + CDXUTControl( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + virtual ~CDXUTControl(); + + virtual HRESULT OnInit() { return S_OK; } + virtual void Refresh(); + virtual void Render( _In_ float fElapsedTime ) { UNREFERENCED_PARAMETER(fElapsedTime); } + + // Windows message handler + virtual bool MsgProc( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) + { + UNREFERENCED_PARAMETER(uMsg); + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + return false; + } + + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) + { + UNREFERENCED_PARAMETER(uMsg); + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + return false; + } + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) + { + UNREFERENCED_PARAMETER(uMsg); + UNREFERENCED_PARAMETER(pt); + UNREFERENCED_PARAMETER(wParam); + UNREFERENCED_PARAMETER(lParam); + return false; + } + + virtual bool CanHaveFocus() { return false; } + virtual void OnFocusIn() { m_bHasFocus = true; } + virtual void OnFocusOut() { m_bHasFocus = false; } + virtual void OnMouseEnter() { m_bMouseOver = true; } + virtual void OnMouseLeave() { m_bMouseOver = false; } + virtual void OnHotkey() { } + + virtual bool ContainsPoint( _In_ const POINT& pt ) { return PtInRect( &m_rcBoundingBox, pt ) != 0; } + + virtual void SetEnabled( _In_ bool bEnabled ) { m_bEnabled = bEnabled; } + virtual bool GetEnabled() const { return m_bEnabled; } + virtual void SetVisible( _In_ bool bVisible ) { m_bVisible = bVisible; } + virtual bool GetVisible() const { return m_bVisible; } + + UINT GetType() const { return m_Type; } + + int GetID() const { return m_ID; } + void SetID( _In_ int ID ) { m_ID = ID; } + + void SetLocation( _In_ int x, _In_ int y ) + { + m_x = x; + m_y = y; + UpdateRects(); + } + void SetSize( int width, int height ) + { + m_width = width; + m_height = height; + UpdateRects(); + } + + void SetHotkey( _In_ UINT nHotkey ) { m_nHotkey = nHotkey; } + UINT GetHotkey() const { return m_nHotkey; } + + void SetUserData( _In_opt_ void* pUserData ) { m_pUserData = pUserData; } + void* GetUserData() const { return m_pUserData; } + + virtual void SetTextColor( _In_ DWORD Color ); + CDXUTElement* GetElement( _In_ UINT iElement ) const { return m_Elements[ iElement ]; } + HRESULT SetElement( _In_ UINT iElement, _In_ CDXUTElement* pElement ); + + bool m_bVisible; // Shown/hidden flag + bool m_bMouseOver; // Mouse pointer is above control + bool m_bHasFocus; // Control has input focus + bool m_bIsDefault; // Is the default control + + // Size, scale, and positioning members + int m_x, m_y; + int m_width, m_height; + + // These members are set by the container + CDXUTDialog* m_pDialog; // Parent container + UINT m_Index; // Index within the control list + + std::vector m_Elements; // All display elements + +protected: + virtual void UpdateRects(); + + int m_ID; // ID number + DXUT_CONTROL_TYPE m_Type; // Control type, set once in constructor + UINT m_nHotkey; // Virtual key code for this control's hotkey + void* m_pUserData; // Data associated with this control that is set by user. + + bool m_bEnabled; // Enabled/disabled flag + + RECT m_rcBoundingBox; // Rectangle defining the active region of the control +}; + + +//----------------------------------------------------------------------------- +// Contains all the display information for a given control type +//----------------------------------------------------------------------------- +struct DXUTElementHolder +{ + UINT nControlType; + UINT iElement; + + CDXUTElement Element; +}; + + +//----------------------------------------------------------------------------- +// Static control +//----------------------------------------------------------------------------- +class CDXUTStatic : public CDXUTControl +{ +public: + CDXUTStatic( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + + virtual void Render( _In_ float fElapsedTime ) override; + virtual bool ContainsPoint( _In_ const POINT& pt ) override + { + UNREFERENCED_PARAMETER( pt ); + return false; + } + + HRESULT GetTextCopy( _Out_writes_(bufferCount) LPWSTR strDest, _In_ UINT bufferCount ) const; + LPCWSTR GetText() const { return m_strText; } + HRESULT SetText( _In_z_ LPCWSTR strText ); + +protected: + WCHAR m_strText[MAX_PATH]; // Window text +}; + + +//----------------------------------------------------------------------------- +// Button control +//----------------------------------------------------------------------------- +class CDXUTButton : public CDXUTStatic +{ +public: + CDXUTButton( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual void OnHotkey() override + { + if( m_pDialog->IsKeyboardInputEnabled() ) m_pDialog->RequestFocus( this ); + m_pDialog->SendEvent( EVENT_BUTTON_CLICKED, true, this ); + } + + virtual bool ContainsPoint( _In_ const POINT& pt ) override + { + return PtInRect( &m_rcBoundingBox, pt ) != 0; + } + virtual bool CanHaveFocus() override + { + return ( m_bVisible && m_bEnabled ); + } + + virtual void Render( _In_ float fElapsedTime ) override; + +protected: + bool m_bPressed; +}; + + +//----------------------------------------------------------------------------- +// CheckBox control +//----------------------------------------------------------------------------- +class CDXUTCheckBox : public CDXUTButton +{ +public: + CDXUTCheckBox( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual void OnHotkey() override + { + if( m_pDialog->IsKeyboardInputEnabled() ) m_pDialog->RequestFocus( this ); + SetCheckedInternal( !m_bChecked, true ); + } + + virtual bool ContainsPoint( _In_ const POINT& pt ) override; + virtual void UpdateRects() override; + + virtual void Render( _In_ float fElapsedTime ) override; + + bool GetChecked() const { return m_bChecked; } + void SetChecked( _In_ bool bChecked ) { SetCheckedInternal( bChecked, false ); } + +protected: + virtual void SetCheckedInternal( _In_ bool bChecked, _In_ bool bFromInput ); + + bool m_bChecked; + RECT m_rcButton; + RECT m_rcText; +}; + + +//----------------------------------------------------------------------------- +// RadioButton control +//----------------------------------------------------------------------------- +class CDXUTRadioButton : public CDXUTCheckBox +{ +public: + CDXUTRadioButton( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual void OnHotkey() override + { + if( m_pDialog->IsKeyboardInputEnabled() ) m_pDialog->RequestFocus( this ); + SetCheckedInternal( true, true, true ); + } + + void SetChecked( _In_ bool bChecked, _In_ bool bClearGroup=true ) { SetCheckedInternal( bChecked, bClearGroup, false ); } + void SetButtonGroup( _In_ UINT nButtonGroup ) { m_nButtonGroup = nButtonGroup; } + UINT GetButtonGroup() const { return m_nButtonGroup; } + +protected: + virtual void SetCheckedInternal( _In_ bool bChecked, _In_ bool bClearGroup, _In_ bool bFromInput ); + UINT m_nButtonGroup; +}; + + +//----------------------------------------------------------------------------- +// Scrollbar control +//----------------------------------------------------------------------------- +class CDXUTScrollBar : public CDXUTControl +{ +public: + CDXUTScrollBar( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + virtual ~CDXUTScrollBar(); + + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool MsgProc( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + + virtual void Render( _In_ float fElapsedTime ) override; + virtual void UpdateRects() override; + + void SetTrackRange( _In_ int nStart, _In_ int nEnd ); + int GetTrackPos() const { return m_nPosition; } + void SetTrackPos( _In_ int nPosition ) + { + m_nPosition = nPosition; + Cap(); + UpdateThumbRect(); + } + int GetPageSize() const { return m_nPageSize; } + void SetPageSize( _In_ int nPageSize ) + { + m_nPageSize = nPageSize; + Cap(); + UpdateThumbRect(); + } + + void Scroll( _In_ int nDelta ); // Scroll by nDelta items (plus or minus) + void ShowItem( _In_ int nIndex ); // Ensure that item nIndex is displayed, scroll if necessary + +protected: + // ARROWSTATE indicates the state of the arrow buttons. + // CLEAR No arrow is down. + // CLICKED_UP Up arrow is clicked. + // CLICKED_DOWN Down arrow is clicked. + // HELD_UP Up arrow is held down for sustained period. + // HELD_DOWN Down arrow is held down for sustained period. + enum ARROWSTATE + { + CLEAR, + CLICKED_UP, + CLICKED_DOWN, + HELD_UP, + HELD_DOWN + }; + + void UpdateThumbRect(); + void Cap(); // Clips position at boundaries. Ensures it stays within legal range. + + bool m_bShowThumb; + bool m_bDrag; + RECT m_rcUpButton; + RECT m_rcDownButton; + RECT m_rcTrack; + RECT m_rcThumb; + int m_nPosition; // Position of the first displayed item + int m_nPageSize; // How many items are displayable in one page + int m_nStart; // First item + int m_nEnd; // The index after the last item + POINT m_LastMouse;// Last mouse position + ARROWSTATE m_Arrow; // State of the arrows + double m_dArrowTS; // Timestamp of last arrow event. +}; + + +//----------------------------------------------------------------------------- +// ListBox control +//----------------------------------------------------------------------------- +struct DXUTListBoxItem +{ + WCHAR strText[256]; + void* pData; + + RECT rcActive; + bool bSelected; +}; + +class CDXUTListBox : public CDXUTControl +{ +public: + CDXUTListBox( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + virtual ~CDXUTListBox(); + + virtual HRESULT OnInit() override + { + return m_pDialog->InitControl( &m_ScrollBar ); + } + virtual bool CanHaveFocus() override + { + return ( m_bVisible && m_bEnabled ); + } + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool MsgProc( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + + virtual void Render( _In_ float fElapsedTime ) override; + virtual void UpdateRects() override; + + DWORD GetStyle() const { return m_dwStyle; } + size_t GetSize() const { return m_Items.size(); } + void SetStyle( _In_ DWORD dwStyle ) { m_dwStyle = dwStyle; } + int GetScrollBarWidth() const{ return m_nSBWidth; } + void SetScrollBarWidth( _In_ int nWidth ) + { + m_nSBWidth = nWidth; + UpdateRects(); + } + void SetBorder( _In_ int nBorder, _In_ int nMargin ) + { + m_nBorder = nBorder; + m_nMargin = nMargin; + } + HRESULT AddItem( _In_z_ const WCHAR* wszText, _In_opt_ void* pData ); + HRESULT InsertItem( _In_ int nIndex, _In_z_ const WCHAR* wszText, _In_opt_ void* pData ); + void RemoveItem( _In_ int nIndex ); + void RemoveAllItems(); + + DXUTListBoxItem* GetItem( _In_ int nIndex ) const; + int GetSelectedIndex( _In_ int nPreviousSelected = -1 ) const; + DXUTListBoxItem* GetSelectedItem( _In_ int nPreviousSelected = -1 ) const + { + return GetItem( GetSelectedIndex( nPreviousSelected ) ); + } + void SelectItem( _In_ int nNewIndex ); + + enum STYLE + { + MULTISELECTION = 1 + }; + +protected: + RECT m_rcText; // Text rendering bound + RECT m_rcSelection; // Selection box bound + CDXUTScrollBar m_ScrollBar; + int m_nSBWidth; + int m_nBorder; + int m_nMargin; + int m_nTextHeight; // Height of a single line of text + DWORD m_dwStyle; // List box style + int m_nSelected; // Index of the selected item for single selection list box + int m_nSelStart; // Index of the item where selection starts (for handling multi-selection) + bool m_bDrag; // Whether the user is dragging the mouse to select + + std::vector m_Items; +}; + + +//----------------------------------------------------------------------------- +// ComboBox control +//----------------------------------------------------------------------------- +struct DXUTComboBoxItem +{ + WCHAR strText[256]; + void* pData; + + RECT rcActive; + bool bVisible; +}; + +class CDXUTComboBox : public CDXUTButton +{ +public: + CDXUTComboBox( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + virtual ~CDXUTComboBox(); + + virtual void SetTextColor( _In_ DWORD Color ) override; + virtual HRESULT OnInit() override + { + return m_pDialog->InitControl( &m_ScrollBar ); + } + + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual void OnHotkey() override; + + virtual bool CanHaveFocus() override + { + return ( m_bVisible && m_bEnabled ); + } + virtual void OnFocusOut() override; + virtual void Render( _In_ float fElapsedTime ) override; + + virtual void UpdateRects() override; + + HRESULT AddItem( _In_z_ const WCHAR* strText, _In_opt_ void* pData ); + void RemoveAllItems(); + void RemoveItem( _In_ UINT index ); + bool ContainsItem( _In_z_ const WCHAR* strText, _In_ UINT iStart=0 ); + int FindItem( _In_z_ const WCHAR* strText, _In_ UINT iStart=0 ) const; + void* GetItemData( _In_z_ const WCHAR* strText ) const; + void* GetItemData( _In_ int nIndex ) const; + void SetDropHeight( _In_ UINT nHeight ) + { + m_nDropHeight = nHeight; + UpdateRects(); + } + int GetScrollBarWidth() const { return m_nSBWidth; } + void SetScrollBarWidth( _In_ int nWidth ) + { + m_nSBWidth = nWidth; + UpdateRects(); + } + + int GetSelectedIndex() const { return m_iSelected; } + void* GetSelectedData() const; + DXUTComboBoxItem* GetSelectedItem() const; + + UINT GetNumItems() { return static_cast( m_Items.size() ); } + DXUTComboBoxItem* GetItem( _In_ UINT index ) { return m_Items[ index ]; } + + HRESULT SetSelectedByIndex( _In_ UINT index ); + HRESULT SetSelectedByText( _In_z_ const WCHAR* strText ); + HRESULT SetSelectedByData( _In_ void* pData ); + +protected: + int m_iSelected; + int m_iFocused; + int m_nDropHeight; + CDXUTScrollBar m_ScrollBar; + int m_nSBWidth; + + bool m_bOpened; + + RECT m_rcText; + RECT m_rcButton; + RECT m_rcDropdown; + RECT m_rcDropdownText; + + std::vector m_Items; +}; + + +//----------------------------------------------------------------------------- +// Slider control +//----------------------------------------------------------------------------- +class CDXUTSlider : public CDXUTControl +{ +public: + CDXUTSlider( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + + virtual bool ContainsPoint( _In_ const POINT& pt ) override; + virtual bool CanHaveFocus() override + { + return ( m_bVisible && m_bEnabled ); + } + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + + virtual void UpdateRects() override; + + virtual void Render( _In_ float fElapsedTime ) override; + + void SetValue( int nValue ) { SetValueInternal( nValue, false ); } + int GetValue() const { return m_nValue; } + + void GetRange( _Out_ int& nMin, _Out_ int& nMax ) const + { + nMin = m_nMin; + nMax = m_nMax; + } + void SetRange( _In_ int nMin, _In_ int nMax ); + +protected: + void SetValueInternal( _In_ int nValue, _In_ bool bFromInput ); + int ValueFromPos( _In_ int x ); + + int m_nValue; + + int m_nMin; + int m_nMax; + + int m_nDragX; // Mouse position at start of drag + int m_nDragOffset; // Drag offset from the center of the button + int m_nButtonX; + + bool m_bPressed; + RECT m_rcButton; +}; + + +//----------------------------------------------------------------------------- +// CUniBuffer class for the edit control +//----------------------------------------------------------------------------- +class CUniBuffer +{ +public: + CUniBuffer( _In_ int nInitialSize = 1 ) noexcept; + ~CUniBuffer(); + + size_t GetBufferSize() const { return m_nBufferSize; } + bool SetBufferSize( _In_ int nSize ); + int GetTextSize() const { return (int)wcslen( m_pwszBuffer ); } + const WCHAR* GetBuffer() const + { + return m_pwszBuffer; + } + const WCHAR& operator[]( _In_ int n ) const + { + return m_pwszBuffer[n]; + } + WCHAR& operator[]( _In_ int n ); + DXUTFontNode* GetFontNode() const { return m_pFontNode; } + void SetFontNode( _In_opt_ DXUTFontNode* pFontNode ) { m_pFontNode = pFontNode; } + void Clear(); + + bool InsertChar( _In_ int nIndex, _In_ WCHAR wChar ); + // Inserts the char at specified index. If nIndex == -1, insert to the end. + + bool RemoveChar( _In_ int nIndex ); + // Removes the char at specified index. If nIndex == -1, remove the last char. + + bool InsertString( _In_ int nIndex, _In_z_ const WCHAR* pStr, _In_ int nCount = -1 ); + // Inserts the first nCount characters of the string pStr at specified index. If nCount == -1, the entire string is inserted. If nIndex == -1, insert to the end. + + bool SetText( _In_z_ LPCWSTR wszText ); + + // Uniscribe + bool CPtoX( _In_ int nCP, _In_ bool bTrail, _Out_ int* pX ); + bool XtoCP( _In_ int nX, _Out_ int* pCP, _Out_ int* pnTrail ); + void GetPriorItemPos( _In_ int nCP, _Out_ int* pPrior ); + void GetNextItemPos( _In_ int nCP, _Out_ int* pPrior ); + +private: + HRESULT Analyse(); // Uniscribe -- Analyse() analyses the string in the buffer + + WCHAR* m_pwszBuffer; // Buffer to hold text + int m_nBufferSize; // Size of the buffer allocated, in characters + + // Uniscribe-specific + DXUTFontNode* m_pFontNode; // Font node for the font that this buffer uses + bool m_bAnalyseRequired; // True if the string has changed since last analysis. + SCRIPT_STRING_ANALYSIS m_Analysis; // Analysis for the current string +}; + + +//----------------------------------------------------------------------------- +// EditBox control +//----------------------------------------------------------------------------- +class CDXUTEditBox : public CDXUTControl +{ +public: + CDXUTEditBox( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + virtual ~CDXUTEditBox(); + + virtual bool HandleKeyboard( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool MsgProc( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual void UpdateRects() override; + virtual bool CanHaveFocus() override + { + return ( m_bVisible && m_bEnabled ); + } + virtual void Render( _In_ float fElapsedTime ) override; + virtual void OnFocusIn() override; + + void SetText( _In_z_ LPCWSTR wszText, _In_ bool bSelected = false ); + LPCWSTR GetText() const { return m_Buffer.GetBuffer(); } + size_t GetTextLength() const { return m_Buffer.GetTextSize(); } // Returns text length in chars excluding nul. + HRESULT GetTextCopy( _Out_writes_(bufferCount) LPWSTR strDest, _In_ UINT bufferCount ) const; + void ClearText(); + + virtual void SetTextColor( _In_ DWORD Color ) override { m_TextColor = Color; } // Text color + void SetSelectedTextColor( _In_ DWORD Color ) { m_SelTextColor = Color; } // Selected text color + void SetSelectedBackColor( _In_ DWORD Color ) { m_SelBkColor = Color; } // Selected background color + void SetCaretColor( _In_ DWORD Color ) { m_CaretColor = Color; } // Caret color + void SetBorderWidth( _In_ int nBorder ) + { + m_nBorder = nBorder; + UpdateRects(); + } // Border of the window + void SetSpacing( _In_ int nSpacing ) + { + m_nSpacing = nSpacing; + UpdateRects(); + } + void ParseFloatArray( _In_reads_(nCount) float* pNumbers, _In_ int nCount ); + void SetTextFloatArray( _In_reads_(nCount) const float* pNumbers, _In_ int nCount ); + +protected: + void PlaceCaret( _In_ int nCP ); + void DeleteSelectionText(); + void ResetCaretBlink(); + void CopyToClipboard(); + void PasteFromClipboard(); + + CUniBuffer m_Buffer; // Buffer to hold text + int m_nBorder; // Border of the window + int m_nSpacing; // Spacing between the text and the edge of border + RECT m_rcText; // Bounding rectangle for the text + RECT m_rcRender[9]; // Convenient rectangles for rendering elements + double m_dfBlink; // Caret blink time in milliseconds + double m_dfLastBlink; // Last timestamp of caret blink + bool m_bCaretOn; // Flag to indicate whether caret is currently visible + int m_nCaret; // Caret position, in characters + bool m_bInsertMode; // If true, control is in insert mode. Else, overwrite mode. + int m_nSelStart; // Starting position of the selection. The caret marks the end. + int m_nFirstVisible;// First visible character in the edit control + DWORD m_TextColor; // Text color + DWORD m_SelTextColor; // Selected text color + DWORD m_SelBkColor; // Selected background color + DWORD m_CaretColor; // Caret color + + // Mouse-specific + bool m_bMouseDrag; // True to indicate drag in progress + + // Static + static bool s_bHideCaret; // If true, we don't render the caret. +}; + + +//----------------------------------------------------------------------------- +void BeginText11(); +void DrawText11DXUT( _In_ ID3D11Device* pd3dDevice, _In_ ID3D11DeviceContext* pd3d11DeviceContext, + _In_z_ LPCWSTR strText, _In_ const RECT& rcScreen, _In_ DirectX::XMFLOAT4 vFontColor, + _In_ float fBBWidth, _In_ float fBBHeight, _In_ bool bCenter ); +void EndText11( _In_ ID3D11Device* pd3dDevice, _In_ ID3D11DeviceContext* pd3d11DeviceContext ); diff --git a/src/DX11/framework/dxut/Optional/DXUTguiIME.cpp b/src/DX11/framework/dxut/Optional/DXUTguiIME.cpp new file mode 100644 index 0000000..0684826 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTguiIME.cpp @@ -0,0 +1,999 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTguiIME.cpp +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "DXUT.h" +#include "DXUTgui.h" +#include "DXUTsettingsDlg.h" +#include "DXUTres.h" +#include "DXUTgui.h" +#include "DXUTguiIME.h" + +#define DXUT_NEAR_BUTTON_DEPTH 0.6f + + +//-------------------------------------------------------------------------------------- +// CDXUTIMEEditBox class +//-------------------------------------------------------------------------------------- +// IME constants + +POINT CDXUTIMEEditBox::s_ptCompString; // Composition string position. Updated every frame. +int CDXUTIMEEditBox::s_nFirstTargetConv; // Index of the first target converted char in comp string. If none, -1. +CUniBuffer CDXUTIMEEditBox::s_CompString = CUniBuffer( 0 ); +DWORD CDXUTIMEEditBox::s_adwCompStringClause[MAX_COMPSTRING_SIZE]; +WCHAR CDXUTIMEEditBox::s_wszReadingString[32]; +CDXUTIMEEditBox::CCandList CDXUTIMEEditBox::s_CandList; // Data relevant to the candidate list +bool CDXUTIMEEditBox::s_bImeFlag = true; + + +#if defined(DEBUG) || defined(_DEBUG) +bool CDXUTIMEEditBox::m_bIMEStaticMsgProcCalled = false; +#endif + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTIMEEditBox::CreateIMEEditBox( CDXUTDialog* pDialog, int ID, LPCWSTR strText, int x, int y, int width, + int height, bool bIsDefault, CDXUTIMEEditBox** ppCreated ) +{ + auto pEditBox = new (std::nothrow) CDXUTIMEEditBox( pDialog ); + + if( ppCreated ) + *ppCreated = pEditBox; + + if( !pEditBox ) + return E_OUTOFMEMORY; + + // Set the ID and position + pEditBox->SetID( ID ); + pEditBox->SetLocation( x, y ); + pEditBox->SetSize( width, height ); + pEditBox->m_bIsDefault = bIsDefault; + + if( strText ) + pEditBox->SetText( strText ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::InitDefaultElements( _In_ CDXUTDialog* pDialog ) +{ + //------------------------------------- + // CDXUTIMEEditBox + //------------------------------------- + + CDXUTElement Element; + RECT rcTexture; + + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 0, 0, 0 ), DT_LEFT | DT_TOP ); + + // Assign the style + SetRect( &rcTexture, 14, 90, 241, 113 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 0, &Element ); + SetRect( &rcTexture, 8, 82, 14, 90 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 1, &Element ); + SetRect( &rcTexture, 14, 82, 241, 90 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 2, &Element ); + SetRect( &rcTexture, 241, 82, 246, 90 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 3, &Element ); + SetRect( &rcTexture, 8, 90, 14, 113 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 4, &Element ); + SetRect( &rcTexture, 241, 90, 246, 113 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 5, &Element ); + SetRect( &rcTexture, 8, 113, 14, 121 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 6, &Element ); + SetRect( &rcTexture, 14, 113, 241, 121 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 7, &Element ); + SetRect( &rcTexture, 241, 113, 246, 121 ); + Element.SetTexture( 0, &rcTexture ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 8, &Element ); + // Element 9 for IME text, and indicator button + SetRect( &rcTexture, 0, 0, 136, 54 ); + Element.SetTexture( 0, &rcTexture ); + Element.SetFont( 0, D3DCOLOR_ARGB( 255, 0, 0, 0 ), DT_CENTER | DT_VCENTER ); + pDialog->SetDefaultElement( DXUT_CONTROL_IMEEDITBOX, 9, &Element ); +} + + +//-------------------------------------------------------------------------------------- +CDXUTIMEEditBox::CDXUTIMEEditBox( _In_opt_ CDXUTDialog* pDialog ) noexcept : + m_nIndicatorWidth(0), + m_rcIndicator{} +{ + m_Type = DXUT_CONTROL_IMEEDITBOX; + m_pDialog = pDialog; + + m_ReadingColor = D3DCOLOR_ARGB( 188, 255, 255, 255 ); + m_ReadingWinColor = D3DCOLOR_ARGB( 128, 0, 0, 0 ); + m_ReadingSelColor = D3DCOLOR_ARGB( 255, 255, 0, 0 ); + m_ReadingSelBkColor = D3DCOLOR_ARGB( 128, 80, 80, 80 ); + m_CandidateColor = D3DCOLOR_ARGB( 255, 200, 200, 200 ); + m_CandidateWinColor = D3DCOLOR_ARGB( 128, 0, 0, 0 ); + m_CandidateSelColor = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + m_CandidateSelBkColor = D3DCOLOR_ARGB( 128, 158, 158, 158 ); + m_CompColor = D3DCOLOR_ARGB( 255, 200, 200, 255 ); + m_CompWinColor = D3DCOLOR_ARGB( 198, 0, 0, 0 ); + m_CompCaretColor = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + m_CompTargetColor = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + m_CompTargetBkColor = D3DCOLOR_ARGB( 255, 150, 150, 150 ); + m_CompTargetNonColor = D3DCOLOR_ARGB( 255, 255, 255, 0 ); + m_CompTargetNonBkColor = D3DCOLOR_ARGB( 255, 150, 150, 150 ); + m_IndicatorImeColor = D3DCOLOR_ARGB( 255, 255, 255, 255 ); + m_IndicatorEngColor = D3DCOLOR_ARGB( 255, 0, 0, 0 ); + m_IndicatorBkColor = D3DCOLOR_ARGB( 255, 128, 128, 128 ); +} + + +//-------------------------------------------------------------------------------------- +CDXUTIMEEditBox::~CDXUTIMEEditBox() +{ +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::SendKey( _In_ BYTE nVirtKey ) +{ + keybd_event( nVirtKey, 0, 0, 0 ); + keybd_event( nVirtKey, 0, KEYEVENTF_KEYUP, 0 ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::UpdateRects() +{ + // Temporary adjust m_width so that CDXUTEditBox can compute + // the correct rects for its rendering since we need to make space + // for the indicator button + int nWidth = m_width; + m_width -= m_nIndicatorWidth + m_nBorder * 2; // Make room for the indicator button + CDXUTEditBox::UpdateRects(); + m_width = nWidth; // Restore + + // Compute the indicator button rectangle + SetRect( &m_rcIndicator, m_rcBoundingBox.right, m_rcBoundingBox.top, m_x + m_width, m_rcBoundingBox.bottom ); + // InflateRect( &m_rcIndicator, -m_nBorder, -m_nBorder ); + m_rcBoundingBox.right = m_rcBoundingBox.left + m_width; +} + + +//-------------------------------------------------------------------------------------- +// GetImeId( UINT uIndex ) +// returns +// returned value: +// 0: In the following cases +// - Non Chinese IME input locale +// - Older Chinese IME +// - Other error cases +// +// Othewise: +// When uIndex is 0 (default) +// bit 31-24: Major version +// bit 23-16: Minor version +// bit 15-0: Language ID +// When uIndex is 1 +// pVerFixedInfo->dwFileVersionLS +// +// Use IMEID_VER and IMEID_LANG macro to extract version and language information. +// + +// We define the locale-invariant ID ourselves since it doesn't exist prior to WinXP +// For more information, see the CompareString() reference. +#define LCID_INVARIANT MAKELCID(MAKELANGID(LANG_ENGLISH, SUBLANG_ENGLISH_US), SORT_DEFAULT) +//-------------------------------------------------------------------------------------- +// Enable/disable the entire IME system. When disabled, the default IME handling +// kicks in. +void CDXUTIMEEditBox::EnableImeSystem( _In_ bool bEnable ) +{ + ImeUi_EnableIme( bEnable ); +} + + +//-------------------------------------------------------------------------------------- +// Resets the composition string. +void CDXUTIMEEditBox::ResetCompositionString() +{ + s_CompString.SetText( L"" ); +} + + +//-------------------------------------------------------------------------------------- +// This function is used only briefly in CHT IME handling, +// so accelerator isn't processed. +void CDXUTIMEEditBox::PumpMessage() +{ + MSG msg; + + while( PeekMessageW( &msg, nullptr, 0, 0, PM_NOREMOVE ) ) + { + if( !GetMessageW( &msg, nullptr, 0, 0 ) ) + { + PostQuitMessage( ( int )msg.wParam ); + return; + } + TranslateMessage( &msg ); + DispatchMessageA( &msg ); + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::OnFocusIn() +{ + ImeUi_EnableIme( s_bImeFlag ); + CDXUTEditBox::OnFocusIn(); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::OnFocusOut() +{ + ImeUi_FinalizeString(); + ImeUi_EnableIme( false ); + CDXUTEditBox::OnFocusOut(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTIMEEditBox::StaticMsgProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + UNREFERENCED_PARAMETER(hWnd); + UNREFERENCED_PARAMETER(wParam); + + if( !ImeUi_IsEnabled() ) + return false; + +#if defined(DEBUG) || defined(_DEBUG) + m_bIMEStaticMsgProcCalled = true; +#endif + + switch( uMsg ) + { + case WM_INPUTLANGCHANGE: + DXUTTRACE( L"WM_INPUTLANGCHANGE\n" ); + { + } + return true; + + case WM_IME_SETCONTEXT: + DXUTTRACE( L"WM_IME_SETCONTEXT\n" ); + // + // We don't want anything to display, so we have to clear this + // + lParam = 0; + return false; + + // Handle WM_IME_STARTCOMPOSITION here since + // we do not want the default IME handler to see + // this when our fullscreen app is running. + case WM_IME_STARTCOMPOSITION: + DXUTTRACE( L"WM_IME_STARTCOMPOSITION\n" ); + ResetCompositionString(); + // Since the composition string has its own caret, we don't render + // the edit control's own caret to avoid double carets on screen. + s_bHideCaret = true; + return true; + case WM_IME_ENDCOMPOSITION: + DXUTTRACE( L"WM_IME_ENDCOMPOSITION\n" ); + s_bHideCaret = false; + return false; + case WM_IME_COMPOSITION: + DXUTTRACE( L"WM_IME_COMPOSITION\n" ); + return false; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTIMEEditBox::HandleMouse( UINT uMsg, const POINT& pt, WPARAM wParam, LPARAM lParam ) +{ + if( !m_bEnabled || !m_bVisible ) + return false; + + switch( uMsg ) + { + case WM_LBUTTONDOWN: + case WM_LBUTTONDBLCLK: + { + auto pFont = m_pDialog->GetFont( m_Elements[ 9 ]->iFont ); + + // Check if this click is on top of the composition string + int nCompStrWidth; + s_CompString.CPtoX( s_CompString.GetTextSize(), FALSE, &nCompStrWidth ); + + if( s_ptCompString.x <= pt.x && + s_ptCompString.y <= pt.y && + s_ptCompString.x + nCompStrWidth > pt.x && + s_ptCompString.y + pFont->nHeight > pt.y ) + { + int nCharBodyHit, nCharHit; + int nTrail; + + // Determine the character clicked on. + s_CompString.XtoCP( pt.x - s_ptCompString.x, &nCharBodyHit, &nTrail ); + if( nTrail && nCharBodyHit < s_CompString.GetTextSize() ) + nCharHit = nCharBodyHit + 1; + else + nCharHit = nCharBodyHit; + + + switch( GetPrimaryLanguage() ) + { + case LANG_JAPANESE: + // For Japanese, there are two cases. If s_nFirstTargetConv is + // -1, the comp string hasn't been converted yet, and we use + // s_nCompCaret. For any other value of s_nFirstTargetConv, + // the string has been converted, so we use clause information. + + if( s_nFirstTargetConv != -1 ) + { + int nClauseClicked = 0; + while( ( int )s_adwCompStringClause[nClauseClicked + 1] <= nCharBodyHit ) + ++nClauseClicked; + + int nClauseSelected = 0; + while( ( int )s_adwCompStringClause[nClauseSelected + 1] <= s_nFirstTargetConv ) + ++nClauseSelected; + + BYTE nVirtKey = nClauseClicked > nClauseSelected ? VK_RIGHT : VK_LEFT; + int nSendCount = abs( nClauseClicked - nClauseSelected ); + while( nSendCount-- > 0 ) + SendKey( nVirtKey ); + + return true; + } + + // Not converted case. Fall thru to Chinese case. + + case LANG_CHINESE: + { + // For Chinese, use s_nCompCaret. + BYTE nVirtKey = nCharHit > ( int )ImeUi_GetImeCursorChars() ? VK_RIGHT : VK_LEFT; + int nSendCount = abs( nCharHit - ( int )ImeUi_GetImeCursorChars() ); + while( nSendCount-- > 0 ) + SendKey( nVirtKey ); + break; + } + } + + return true; + } + + // Check if the click is on top of the candidate window + if( ImeUi_IsShowCandListWindow() && PtInRect( &s_CandList.rcCandidate, pt ) ) + { + if( ImeUi_IsVerticalCand() ) + { + // Vertical candidate window + + // Compute the row the click is on + int nRow = ( pt.y - s_CandList.rcCandidate.top ) / pFont->nHeight; + + if( nRow < ( int )ImeUi_GetCandidateCount() ) + { + // nRow is a valid entry. + // Now emulate keystrokes to select the candidate at this row. + switch( GetPrimaryLanguage() ) + { + case LANG_CHINESE: + case LANG_KOREAN: + // For Chinese and Korean, simply send the number keystroke. + SendKey( ( BYTE )( '0' + nRow + 1 ) ); + break; + + case LANG_JAPANESE: + // For Japanese, move the selection to the target row, + // then send Right, then send Left. + + BYTE nVirtKey; + if( nRow > ( int )ImeUi_GetCandidateSelection() ) + nVirtKey = VK_DOWN; + else + nVirtKey = VK_UP; + int nNumToHit = abs( int( nRow - ImeUi_GetCandidateSelection() ) ); + for( int nStrike = 0; nStrike < nNumToHit; ++nStrike ) + SendKey( nVirtKey ); + + // Do this to close the candidate window without ending composition. + SendKey( VK_RIGHT ); + SendKey( VK_LEFT ); + + break; + } + } + } + else + { + // Horizontal candidate window + + // Determine which the character the click has hit. + int nCharHit; + int nTrail; + s_CandList.HoriCand.XtoCP( pt.x - s_CandList.rcCandidate.left, &nCharHit, &nTrail ); + + // Determine which candidate string the character belongs to. + int nCandidate = ImeUi_GetCandidateCount() - 1; + + int nEntryStart = 0; + for( UINT i = 0; i < ImeUi_GetCandidateCount(); ++i ) + { + if( nCharHit >= nEntryStart ) + { + // Haven't found it. + nEntryStart += (int)wcslen( ImeUi_GetCandidate( i ) ) + 1; // plus space separator + } + else + { + // Found it. This entry starts at the right side of the click point, + // so the char belongs to the previous entry. + nCandidate = i - 1; + break; + } + } + + // Now emulate keystrokes to select the candidate entry. + switch( GetPrimaryLanguage() ) + { + case LANG_CHINESE: + case LANG_KOREAN: + // For Chinese and Korean, simply send the number keystroke. + SendKey( ( BYTE )( '0' + nCandidate + 1 ) ); + break; + } + } + + return true; + } + } + } + + // If we didn't care for the msg, let the parent process it. + return CDXUTEditBox::HandleMouse( uMsg, pt, wParam, lParam ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool CDXUTIMEEditBox::MsgProc( UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + if( !m_bEnabled || !m_bVisible ) + return false; + +#if defined(DEBUG) || defined(_DEBUG) + // DXUT.cpp used to call CDXUTIMEEditBox::StaticMsgProc() so that, but now + // this is the application's responsiblity. To do this, call + // CDXUTDialogResourceManager::MsgProc() before calling this function. + assert( m_bIMEStaticMsgProcCalled && L"To fix, call CDXUTDialogResourceManager::MsgProc() first" ); +#endif + switch( uMsg ) + { + case WM_DESTROY: + ImeUi_Uninitialize(); + break; + } + + bool trappedData; + bool* trapped = &trappedData; + + *trapped = false; + if( !ImeUi_IsEnabled() ) + return CDXUTEditBox::MsgProc( uMsg, wParam, lParam ); + + ImeUi_ProcessMessage( DXUTGetHWND(), uMsg, wParam, lParam, trapped ); + if( *trapped == false ) + CDXUTEditBox::MsgProc( uMsg, wParam, lParam ); + + return *trapped; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTIMEEditBox::RenderCandidateReadingWindow( bool bReading ) +{ + RECT rc; + UINT nNumEntries = bReading ? 4 : MAX_CANDLIST; + int nX, nXFirst, nXComp; + m_Buffer.CPtoX( m_nCaret, FALSE, &nX ); + m_Buffer.CPtoX( m_nFirstVisible, FALSE, &nXFirst ); + + DWORD TextColor, TextBkColor, SelTextColor, SelBkColor; + if( bReading ) + { + TextColor = m_ReadingColor; + TextBkColor = m_ReadingWinColor; + SelTextColor = m_ReadingSelColor; + SelBkColor = m_ReadingSelBkColor; + } + else + { + TextColor = m_CandidateColor; + TextBkColor = m_CandidateWinColor; + SelTextColor = m_CandidateSelColor; + SelBkColor = m_CandidateSelBkColor; + } + + // For Japanese IME, align the window with the first target converted character. + // For all other IMEs, align with the caret. This is because the caret + // does not move for Japanese IME. + if( GetLanguage() == MAKELANGID( LANG_CHINESE, SUBLANG_CHINESE_TRADITIONAL ) && !GetImeId() ) + nXComp = 0; + else if( GetPrimaryLanguage() == LANG_JAPANESE ) + s_CompString.CPtoX( s_nFirstTargetConv, FALSE, &nXComp ); + else + s_CompString.CPtoX( ImeUi_GetImeCursorChars(), FALSE, &nXComp ); + + // Compute the size of the candidate window + int nWidthRequired = 0; + int nHeightRequired = 0; + int nSingleLineHeight = 0; + + if( ( ImeUi_IsVerticalCand() && !bReading ) || + ( !ImeUi_IsHorizontalReading() && bReading ) ) + { + // Vertical window + for( UINT i = 0; i < nNumEntries; ++i ) + { + if( *( ImeUi_GetCandidate( i ) ) == L'\0' ) + break; + SetRect( &rc, 0, 0, 0, 0 ); + m_pDialog->CalcTextRect( ImeUi_GetCandidate( i ), m_Elements[ 1 ], &rc ); + nWidthRequired = std::max( nWidthRequired, rc.right - rc.left ); + nSingleLineHeight = std::max( nSingleLineHeight, rc.bottom - rc.top ); + } + nHeightRequired = nSingleLineHeight * nNumEntries; + } + else + { + // Horizontal window + SetRect( &rc, 0, 0, 0, 0 ); + if( bReading ) + m_pDialog->CalcTextRect( s_wszReadingString, m_Elements[ 1 ], &rc ); + else + { + + WCHAR wszCand[256] = L""; + + s_CandList.nFirstSelected = 0; + s_CandList.nHoriSelectedLen = 0; + for( UINT i = 0; i < MAX_CANDLIST; ++i ) + { + if( *ImeUi_GetCandidate( i ) == L'\0' ) + break; + + WCHAR wszEntry[32]; + swprintf_s( wszEntry, 32, L"%ls ", ImeUi_GetCandidate( i ) ); + // If this is the selected entry, mark its char position. + if( ImeUi_GetCandidateSelection() == i ) + { + s_CandList.nFirstSelected = (int)wcslen( wszCand ); + s_CandList.nHoriSelectedLen = (int)wcslen( wszEntry ) - 1; // Minus space + } + wcscat_s( wszCand, 256, wszEntry ); + } + wszCand[wcslen( wszCand ) - 1] = L'\0'; // Remove the last space + s_CandList.HoriCand.SetText( wszCand ); + + m_pDialog->CalcTextRect( s_CandList.HoriCand.GetBuffer(), m_Elements[ 1 ], &rc ); + } + nWidthRequired = rc.right - rc.left; + nSingleLineHeight = nHeightRequired = rc.bottom - rc.top; + } + + // Now that we have the dimension, calculate the location for the candidate window. + // We attempt to fit the window in this order: + // bottom, top, right, left. + + bool bHasPosition = false; + + // Bottom + SetRect( &rc, s_ptCompString.x + nXComp, s_ptCompString.y + m_rcText.bottom - m_rcText.top, + s_ptCompString.x + nXComp + nWidthRequired, s_ptCompString.y + m_rcText.bottom - m_rcText.top + + nHeightRequired ); + // if the right edge is cut off, move it left. + if( rc.right > m_pDialog->GetWidth() ) + { + rc.left -= rc.right - m_pDialog->GetWidth(); + rc.right = m_pDialog->GetWidth(); + } + if( rc.bottom <= m_pDialog->GetHeight() ) + bHasPosition = true; + + // Top + if( !bHasPosition ) + { + SetRect( &rc, s_ptCompString.x + nXComp, s_ptCompString.y - nHeightRequired, + s_ptCompString.x + nXComp + nWidthRequired, s_ptCompString.y ); + // if the right edge is cut off, move it left. + if( rc.right > m_pDialog->GetWidth() ) + { + rc.left -= rc.right - m_pDialog->GetWidth(); + rc.right = m_pDialog->GetWidth(); + } + if( rc.top >= 0 ) + bHasPosition = true; + } + + // Right + if( !bHasPosition ) + { + int nXCompTrail; + s_CompString.CPtoX( ImeUi_GetImeCursorChars(), TRUE, &nXCompTrail ); + SetRect( &rc, s_ptCompString.x + nXCompTrail, 0, + s_ptCompString.x + nXCompTrail + nWidthRequired, nHeightRequired ); + if( rc.right <= m_pDialog->GetWidth() ) + bHasPosition = true; + } + + // Left + if( !bHasPosition ) + { + SetRect( &rc, s_ptCompString.x + nXComp - nWidthRequired, 0, + s_ptCompString.x + nXComp, nHeightRequired ); + if( rc.right >= 0 ) + bHasPosition = true; + } + + if( !bHasPosition ) + { + // The dialog is too small for the candidate window. + // Fall back to render at 0, 0. Some part of the window + // will be cut off. + rc.left = 0; + rc.right = nWidthRequired; + } + + // If we are rendering the candidate window, save the position + // so that mouse clicks are checked properly. + if( !bReading ) + s_CandList.rcCandidate = rc; + + // Render the elements + m_pDialog->DrawRect( &rc, TextBkColor ); + if( ( ImeUi_IsVerticalCand() && !bReading ) || + ( !ImeUi_IsHorizontalReading() && bReading ) ) + { + // Vertical candidate window + for( UINT i = 0; i < nNumEntries; ++i ) + { + // Here we are rendering one line at a time + rc.bottom = rc.top + nSingleLineHeight; + // Use a different color for the selected string + if( ImeUi_GetCandidateSelection() == i ) + { + m_pDialog->DrawRect( &rc, SelBkColor ); + m_Elements[ 1 ]->FontColor.SetCurrent( SelTextColor ); + } + else + m_Elements[ 1 ]->FontColor.SetCurrent( TextColor ); + + m_pDialog->DrawText( ImeUi_GetCandidate( i ), m_Elements[ 1 ], &rc ); + + rc.top += nSingleLineHeight; + } + } + else + { + // Horizontal candidate window + m_Elements[ 1 ]->FontColor.SetCurrent( TextColor ); + if( bReading ) + m_pDialog->DrawText( s_wszReadingString, m_Elements[ 1 ], &rc ); + else + m_pDialog->DrawText( s_CandList.HoriCand.GetBuffer(), m_Elements[ 1 ], &rc ); + + // Render the selected entry differently + if( !bReading ) + { + int nXLeft, nXRight; + s_CandList.HoriCand.CPtoX( s_CandList.nFirstSelected, FALSE, &nXLeft ); + s_CandList.HoriCand.CPtoX( s_CandList.nFirstSelected + s_CandList.nHoriSelectedLen, FALSE, &nXRight ); + + rc.right = rc.left + nXRight; + rc.left += nXLeft; + m_pDialog->DrawRect( &rc, SelBkColor ); + m_Elements[ 1 ]->FontColor.SetCurrent( SelTextColor ); + m_pDialog->DrawText( s_CandList.HoriCand.GetBuffer() + s_CandList.nFirstSelected, + m_Elements[ 1 ], &rc, false ); + } + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::RenderComposition() +{ + + s_CompString.SetText( ImeUi_GetCompositionString() ); + + RECT rcCaret = + { + 0, 0, 0, 0 + }; + int nX, nXFirst; + m_Buffer.CPtoX( m_nCaret, FALSE, &nX ); + m_Buffer.CPtoX( m_nFirstVisible, FALSE, &nXFirst ); + auto pElement = m_Elements[ 1 ]; + + // Get the required width + RECT rc = + { + m_rcText.left + nX - nXFirst, m_rcText.top, + m_rcText.left + nX - nXFirst, m_rcText.bottom + }; + m_pDialog->CalcTextRect( s_CompString.GetBuffer(), pElement, &rc ); + + // If the composition string is too long to fit within + // the text area, move it to below the current line. + // This matches the behavior of the default IME. + if( rc.right > m_rcText.right ) + OffsetRect( &rc, m_rcText.left - rc.left, rc.bottom - rc.top ); + + // Save the rectangle position for processing highlighted text. + RECT rcFirst = rc; + + // Update s_ptCompString for RenderCandidateReadingWindow(). + s_ptCompString.x = rc.left; s_ptCompString.y = rc.top; + + + DWORD TextColor = m_CompColor; + // Render the window and string. + // If the string is too long, we must wrap the line. + pElement->FontColor.SetCurrent( TextColor ); + const WCHAR* pwszComp = s_CompString.GetBuffer(); + int nCharLeft = s_CompString.GetTextSize(); + for(; ; ) + { + // Find the last character that can be drawn on the same line. + int nLastInLine; + int bTrail; + s_CompString.XtoCP( m_rcText.right - rc.left, &nLastInLine, &bTrail ); + int nNumCharToDraw = std::min( nCharLeft, nLastInLine ); + m_pDialog->CalcTextRect( pwszComp, pElement, &rc, nNumCharToDraw ); + + // Draw the background + // For Korean IME, blink the composition window background as if it + // is a cursor. + if( GetPrimaryLanguage() == LANG_KOREAN ) + { + if( m_bCaretOn ) + { + m_pDialog->DrawRect( &rc, m_CompWinColor ); + } + else + { + // Not drawing composition string background. We + // use the editbox's text color for composition + // string text. + TextColor = m_Elements[ 0 ]->FontColor.States[DXUT_STATE_NORMAL]; + } + } + else + { + // Non-Korean IME. Always draw composition background. + m_pDialog->DrawRect( &rc, m_CompWinColor ); + } + + // Draw the text + pElement->FontColor.SetCurrent( TextColor ); + m_pDialog->DrawText( pwszComp, pElement, &rc, false ); + + // Advance pointer and counter + nCharLeft -= nNumCharToDraw; + pwszComp += nNumCharToDraw; + if( nCharLeft <= 0 ) + break; + + // Advance rectangle coordinates to beginning of next line + OffsetRect( &rc, m_rcText.left - rc.left, rc.bottom - rc.top ); + } + + // Load the rect for the first line again. + rc = rcFirst; + + // Inspect each character in the comp string. + // For target-converted and target-non-converted characters, + // we display a different background color so they appear highlighted. + int nCharFirst = 0; + nXFirst = 0; + s_nFirstTargetConv = -1; + BYTE* pAttr; + const WCHAR* pcComp; + for( pcComp = s_CompString.GetBuffer(), pAttr = ImeUi_GetCompStringAttr(); + *pcComp != L'\0'; ++pcComp, ++pAttr ) + { + DWORD bkColor; + + // Render a different background for this character + int nXLeft, nXRight; + s_CompString.CPtoX( int( pcComp - s_CompString.GetBuffer() ), FALSE, &nXLeft ); + s_CompString.CPtoX( int( pcComp - s_CompString.GetBuffer() ), TRUE, &nXRight ); + + // Check if this character is off the right edge and should + // be wrapped to the next line. + if( nXRight - nXFirst > m_rcText.right - rc.left ) + { + // Advance rectangle coordinates to beginning of next line + OffsetRect( &rc, m_rcText.left - rc.left, rc.bottom - rc.top ); + + // Update the line's first character information + nCharFirst = int( pcComp - s_CompString.GetBuffer() ); + s_CompString.CPtoX( nCharFirst, FALSE, &nXFirst ); + } + + // If the caret is on this character, save the coordinates + // for drawing the caret later. + if( ImeUi_GetImeCursorChars() == ( DWORD )( pcComp - s_CompString.GetBuffer() ) ) + { + rcCaret = rc; + rcCaret.left += nXLeft - nXFirst - 1; + rcCaret.right = rcCaret.left + 2; + } + + // Set up color based on the character attribute + if( *pAttr == ATTR_TARGET_CONVERTED ) + { + pElement->FontColor.SetCurrent( m_CompTargetColor ); + bkColor = m_CompTargetBkColor; + } + else if( *pAttr == ATTR_TARGET_NOTCONVERTED ) + { + pElement->FontColor.SetCurrent( m_CompTargetNonColor ); + bkColor = m_CompTargetNonBkColor; + } + else + { + continue; + } + + RECT rcTarget = + { + rc.left + nXLeft - nXFirst, rc.top, rc.left + nXRight - nXFirst, rc.bottom + }; + m_pDialog->DrawRect( &rcTarget, bkColor ); + m_pDialog->DrawText( pcComp, pElement, &rcTarget, false, 1 ); + + // Record the first target converted character's index + if( -1 == s_nFirstTargetConv ) + s_nFirstTargetConv = int( pAttr - ImeUi_GetCompStringAttr() ); + } + + // Render the composition caret + if( m_bCaretOn ) + { + // If the caret is at the very end, its position would not have + // been computed in the above loop. We compute it here. + if( ImeUi_GetImeCursorChars() == ( DWORD )s_CompString.GetTextSize() ) + { + s_CompString.CPtoX( ImeUi_GetImeCursorChars(), FALSE, &nX ); + rcCaret = rc; + rcCaret.left += nX - nXFirst - 1; + rcCaret.right = rcCaret.left + 2; + } + + m_pDialog->DrawRect( &rcCaret, m_CompCaretColor ); + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::RenderIndicator( _In_ float fElapsedTime ) +{ + auto pElement = m_Elements[ 9 ]; + pElement->TextureColor.Blend( DXUT_STATE_NORMAL, fElapsedTime ); + + m_pDialog->DrawSprite( pElement, &m_rcIndicator, DXUT_NEAR_BUTTON_DEPTH ); + RECT rc = m_rcIndicator; + InflateRect( &rc, -m_nSpacing, -m_nSpacing ); + + pElement->FontColor.SetCurrent( m_IndicatorImeColor ); + RECT rcCalc = + { + 0, 0, 0, 0 + }; + // If IME system is off, draw English indicator. + const WCHAR* pwszIndicator = ImeUi_IsEnabled() ? ImeUi_GetIndicatior() : L"En"; + + m_pDialog->CalcTextRect( pwszIndicator, pElement, &rcCalc ); + m_pDialog->DrawText( pwszIndicator, pElement, &rc ); +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::Render( _In_ float fElapsedTime ) +{ + if( m_bVisible == false ) + return; + + // If we have not computed the indicator symbol width, + // do it. + if( !m_nIndicatorWidth ) + { + RECT rc = + { + 0, 0, 0, 0 + }; + m_pDialog->CalcTextRect( L"En", m_Elements[ 9 ], &rc ); + m_nIndicatorWidth = rc.right - rc.left; + + // Update the rectangles now that we have the indicator's width + UpdateRects(); + } + + // Let the parent render first (edit control) + CDXUTEditBox::Render( fElapsedTime ); + + auto pElement = GetElement( 1 ); + if( pElement ) + { + s_CompString.SetFontNode( m_pDialog->GetFont( pElement->iFont ) ); + s_CandList.HoriCand.SetFontNode( m_pDialog->GetFont( pElement->iFont ) ); + } + + // + // Now render the IME elements + // + + ImeUi_RenderUI(); + + if( m_bHasFocus ) + { + // Render the input locale indicator + RenderIndicator( fElapsedTime ); + + // Display the composition string. + // This method should also update s_ptCompString + // for RenderCandidateReadingWindow. + RenderComposition(); + + // Display the reading/candidate window. RenderCandidateReadingWindow() + // uses s_ptCompString to position itself. s_ptCompString must have + // been filled in by RenderComposition(). + if( ImeUi_IsShowReadingWindow() ) + // Reading window + RenderCandidateReadingWindow( true ); + else if( ImeUi_IsShowCandListWindow() ) + // Candidate list window + RenderCandidateReadingWindow( false ); + } +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::SetImeEnableFlag( _In_ bool bFlag ) +{ + s_bImeFlag = bFlag; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTIMEEditBox::Initialize( _In_ HWND hWnd ) +{ + ImeUiCallback_DrawRect = nullptr; + ImeUiCallback_Malloc = malloc; + ImeUiCallback_Free = free; + ImeUiCallback_DrawFans = nullptr; + + ImeUi_Initialize( hWnd ); + + s_CompString.SetBufferSize( MAX_COMPSTRING_SIZE ); + ImeUi_EnableIme( true ); +} + + diff --git a/src/DX11/framework/dxut/Optional/DXUTguiIME.h b/src/DX11/framework/dxut/Optional/DXUTguiIME.h new file mode 100644 index 0000000..727a353 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTguiIME.h @@ -0,0 +1,143 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTguiIME.h +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +#include +#include +#include "ImeUi.h" + +//-------------------------------------------------------------------------------------- +// Forward declarations +//-------------------------------------------------------------------------------------- +class CDXUTIMEEditBox; + + +//----------------------------------------------------------------------------- +// IME-enabled EditBox control +//----------------------------------------------------------------------------- +#define MAX_COMPSTRING_SIZE 256 + + +class CDXUTIMEEditBox : public CDXUTEditBox +{ +public: + + static HRESULT CreateIMEEditBox( _In_ CDXUTDialog* pDialog, _In_ int ID, _In_z_ LPCWSTR strText, _In_ int x, _In_ int y, _In_ int width, + _In_ int height, _In_ bool bIsDefault=false, _Outptr_opt_ CDXUTIMEEditBox** ppCreated=nullptr ); + + CDXUTIMEEditBox( _In_opt_ CDXUTDialog* pDialog = nullptr ) noexcept; + virtual ~CDXUTIMEEditBox(); + + static void InitDefaultElements( _In_ CDXUTDialog* pDialog ); + + static void WINAPI Initialize( _In_ HWND hWnd ); + static void WINAPI Uninitialize(); + + static HRESULT WINAPI StaticOnCreateDevice(); + static bool WINAPI StaticMsgProc( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); + + static void WINAPI SetImeEnableFlag( _In_ bool bFlag ); + + virtual void Render( _In_ float fElapsedTime ) override; + virtual bool MsgProc( _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual bool HandleMouse( _In_ UINT uMsg, _In_ const POINT& pt, _In_ WPARAM wParam, _In_ LPARAM lParam ) override; + virtual void UpdateRects() override; + virtual void OnFocusIn() override; + virtual void OnFocusOut() override; + + void PumpMessage(); + + virtual void RenderCandidateReadingWindow( _In_ bool bReading ); + virtual void RenderComposition(); + virtual void RenderIndicator( _In_ float fElapsedTime ); + +protected: + static void WINAPI EnableImeSystem( _In_ bool bEnable ); + + static WORD WINAPI GetLanguage() + { + return ImeUi_GetLanguage(); + } + static WORD WINAPI GetPrimaryLanguage() + { + return ImeUi_GetPrimaryLanguage(); + } + static void WINAPI SendKey( _In_ BYTE nVirtKey ); + static DWORD WINAPI GetImeId( _In_ UINT uIndex = 0 ) + { + return ImeUi_GetImeId( uIndex ); + }; + static void WINAPI CheckInputLocale(); + static void WINAPI CheckToggleState(); + static void WINAPI SetupImeApi(); + static void WINAPI ResetCompositionString(); + + + static void SetupImeUiCallback(); + +protected: + enum + { + INDICATOR_NON_IME, + INDICATOR_CHS, + INDICATOR_CHT, + INDICATOR_KOREAN, + INDICATOR_JAPANESE + }; + + struct CCandList + { + CUniBuffer HoriCand; // Candidate list string (for horizontal candidate window) + int nFirstSelected; // First character position of the selected string in HoriCand + int nHoriSelectedLen; // Length of the selected string in HoriCand + RECT rcCandidate; // Candidate rectangle computed and filled each time before rendered + + CCandList() noexcept : + nFirstSelected(0), + nHoriSelectedLen(0), + rcCandidate{} + {} + }; + + static POINT s_ptCompString; // Composition string position. Updated every frame. + static int s_nFirstTargetConv; // Index of the first target converted char in comp string. If none, -1. + static CUniBuffer s_CompString; // Buffer to hold the composition string (we fix its length) + static DWORD s_adwCompStringClause[MAX_COMPSTRING_SIZE]; + static CCandList s_CandList; // Data relevant to the candidate list + static WCHAR s_wszReadingString[32];// Used only with horizontal reading window (why?) + static bool s_bImeFlag; // Is ime enabled + + // Color of various IME elements + DWORD m_ReadingColor; // Reading string color + DWORD m_ReadingWinColor; // Reading window color + DWORD m_ReadingSelColor; // Selected character in reading string + DWORD m_ReadingSelBkColor; // Background color for selected char in reading str + DWORD m_CandidateColor; // Candidate string color + DWORD m_CandidateWinColor; // Candidate window color + DWORD m_CandidateSelColor; // Selected candidate string color + DWORD m_CandidateSelBkColor; // Selected candidate background color + DWORD m_CompColor; // Composition string color + DWORD m_CompWinColor; // Composition string window color + DWORD m_CompCaretColor; // Composition string caret color + DWORD m_CompTargetColor; // Composition string target converted color + DWORD m_CompTargetBkColor; // Composition string target converted background + DWORD m_CompTargetNonColor; // Composition string target non-converted color + DWORD m_CompTargetNonBkColor;// Composition string target non-converted background + DWORD m_IndicatorImeColor; // Indicator text color for IME + DWORD m_IndicatorEngColor; // Indicator text color for English + DWORD m_IndicatorBkColor; // Indicator text background color + + // Edit-control-specific data + int m_nIndicatorWidth; // Width of the indicator symbol + RECT m_rcIndicator; // Rectangle for drawing the indicator button + +#if defined(DEBUG) || defined(_DEBUG) + static bool m_bIMEStaticMsgProcCalled; +#endif +}; diff --git a/src/DX11/framework/dxut/Optional/DXUTres.cpp b/src/DX11/framework/dxut/Optional/DXUTres.cpp new file mode 100644 index 0000000..d4f58f9 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTres.cpp @@ -0,0 +1,8311 @@ +//---------------------------------------------------------------------------- +// File: DXUTRes.cpp +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//----------------------------------------------------------------------------- +#include "DXUT.h" +#include "DXUTres.h" + +#include "DDSTextureLoader.h" + +static const DWORD g_DXUTGUITextureSrcData[] = +{ + 0x20534444, 0x0000007c, 0x00001007, 0x00000100, 0x00000100, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000020, 0x00000041, 0x00000000, 0x00000020, 0x000000ff, + 0x0000ff00, 0x00ff0000, 0xff000000, 0x00001002, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000400, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000400, 0x11000400, 0x11000400, 0x11000400, + 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000400, 0x11000400, + 0x11000000, 0x00000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000400, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000400, 0x22000400, 0x22000400, 0x22000400, + 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000400, 0x22000400, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x22000000, 0x33000000, 0x44000000, + 0x44000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x66000000, 0x66000000, + 0x66000400, 0x66000400, 0x66000400, 0x66000400, 0x66000000, 0x66000000, 0x661e1e1e, 0x771e1e1e, + 0x771e1c1e, 0x771e1c1e, 0x771e1c1e, 0x771e1c1e, 0x771e1e1e, 0x771e1e1e, 0x771e1e1e, 0x771e1e1e, + 0x771e1c1e, 0x881e1c1e, 0x881e1c1e, 0x881e1c1e, 0x88373937, 0x88373937, 0x881b1c1b, 0x881b1c1b, + 0x881e201e, 0x881e201e, 0x881e201e, 0x881e201e, 0x88313631, 0x88313631, 0x88313631, 0x88191b19, + 0x881b1f1b, 0x881b1f1b, 0x881b1f1b, 0x881b1f1b, 0x881b1e1b, 0x881b1e1b, 0x881b1e1b, 0x88373737, + 0x88313331, 0x88313331, 0x88313331, 0x88313331, 0x881b1f1b, 0x881b1f1b, 0x881b1f1b, 0x881b1f1b, + 0x881b1f1b, 0x881b1f1b, 0x881b1f1b, 0x881b1f1b, 0x88191e19, 0x88191e19, 0x88191e19, 0x77191e19, + 0x77191a19, 0x77191a19, 0x77191a19, 0x77191a19, 0x77191719, 0x77191719, 0x77191719, 0x66191719, + 0x66161616, 0x66161616, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x44000000, 0x44000000, + 0x44000000, 0x33000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x22000400, 0x22000400, 0x333c413c, 0x443c3d3f, 0x443c3d3f, 0x443c3d3f, 0x553c3d3f, + 0x66454145, 0x77454145, 0x77454145, 0x88817d81, 0x99797779, 0x99797779, 0x99797779, 0x99797779, + 0x99797979, 0xaa797979, 0xaa797979, 0xaa797979, 0xbb7e7c7e, 0xcc7e7c7e, 0xbb7e7c7e, 0xbb7e7c7e, + 0xbb7e7f7e, 0xbb7e7f7e, 0xcc7e7f7e, 0xcc7e7f7e, 0xcc7e7f7e, 0xcc7e7f7e, 0xcc7e7f7e, 0xcc7e7f7e, + 0xbb7e7c7e, 0xcc7c7b7d, 0xcc7a7879, 0xbb707071, 0xbb686869, 0xbb5d6060, 0xbb565858, 0xbb4d4f4c, + 0xcc454745, 0xcc3c3b3e, 0x77383838, 0x55393837, 0x55373737, 0x44373737, 0x33373737, 0x33373937, + 0x22000400, 0x22000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, + 0x22000000, 0x33000000, 0x44000000, 0x55000000, 0x55030303, 0x66030303, 0x66050505, 0x66080808, + 0x66101010, 0x77212021, 0x77212021, 0x77313131, 0x88373637, 0x88373637, 0x99525152, 0x99525152, + 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, + 0x995a555a, 0x995a555a, 0x995a555a, 0x995a555a, 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, + 0x995a555a, 0x995a555a, 0x995a555a, 0x995a555a, 0x99525552, 0x99525552, 0x99525552, 0x99525552, + 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, 0x994a514a, 0x994a514a, 0x994a514a, 0x994a514a, + 0x99525552, 0x99525552, 0x99525552, 0x99525552, 0x99525152, 0x99525152, 0x99525152, 0x99525152, + 0x994a4d4a, 0x994a4d4a, 0x994a4d4a, 0x994a4d4a, 0x99525552, 0x99525552, 0x99525552, 0x99525552, + 0x99525552, 0x99525552, 0x99525552, 0x99525552, 0x994a514a, 0x994a514a, 0x994a514a, 0x994a514a, + 0x994a4d4a, 0x994a4d4a, 0x994a4d4a, 0x994a4d4a, 0x994a454a, 0x994a454a, 0x994a454a, 0x994a454a, + 0x99424142, 0x99424142, 0x99424142, 0x99424142, 0x99424142, 0x99424142, 0x99424142, 0x992c2b2c, + 0x88293129, 0x881b201b, 0x771b201b, 0x771b201b, 0x66101010, 0x66101010, 0x660b0b0b, 0x66050505, + 0x66000400, 0x66000100, 0x55000100, 0x55000000, 0x55000000, 0x44000000, 0x33000000, 0x22000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080708, 0x11100d10, 0x11100d10, 0x22191419, + 0x33212324, 0x55424647, 0x66424647, 0x8863696b, 0x99737473, 0xbb737473, 0xccadaead, 0xeeadaead, + 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5b6bd, 0xffb5b6bd, 0xffb5b6bd, 0xffb5b6bd, + 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, + 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, + 0xffbdbabd, 0xffbcbabd, 0xffbcb8bc, 0xffb6b2b6, 0xffb3afb3, 0xffb0aeaf, 0xffadabaa, 0xffaaa9aa, + 0xffa9a7a8, 0xffa7a7a7, 0xffa6a6a6, 0xffa6a6a5, 0xffa6a6a5, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a2a5, + 0xffa5a2a5, 0xffa5a2a5, 0xeea5a2a5, 0xdd9c9a9c, 0xcc9c9a9c, 0xaa686768, 0x99686768, 0x885a5d5a, + 0x553c3e3c, 0x443c3e3c, 0x331e1f1e, 0x11101010, 0x11101010, 0x110b0b0b, 0x00050505, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000400, 0x33000400, 0x44000400, 0x55000400, + 0x66080808, 0x66080808, 0x663a3a3a, 0x773a3a3a, 0x885a5d5a, 0x886b6f6e, 0x996b6f6e, 0x997b8081, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99797879, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x996b716b, 0x99737773, 0x996b716b, 0x996b716b, + 0x99737173, 0x99797779, 0x99737173, 0x99737173, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x99636563, 0x99636563, 0x99636563, 0x99636563, + 0x99636163, 0x99636163, 0x99636163, 0x99636163, 0x995a5d5a, 0x995a5d5a, 0x995a5d5a, 0x995a5d5a, + 0x995a5552, 0x995a5552, 0x995a5552, 0x995a5552, 0x994a4d50, 0x994a4d50, 0x994a4d50, 0x9931353a, + 0x88313331, 0x88313331, 0x77101010, 0x66101010, 0x66080408, 0x66080408, 0x66080408, 0x55080408, + 0x55000000, 0x44000000, 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11191819, 0x22191819, 0x33191819, 0x66656465, 0x887b7d7b, 0xbba2a5a5, 0xddc8ccce, 0xffc8ccce, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd9d8d9, 0xffd6d2d6, 0xffd6d2d6, 0xffd6cece, 0xffcfcccc, 0xffc8c7c8, 0xffc6c2c3, + 0xffc4c0c2, 0xffc2c0c2, 0xffc5c2c4, 0xffc4c2c5, 0xffc5c2c5, 0xffc5c2c5, 0xffc5c2c5, 0xffbdbebd, + 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffa5a6a5, + 0xffa5a6a5, 0xffa5a6a5, 0xffa5a6a5, 0xee868a86, 0xdd868a86, 0xaa868a86, 0x885a615a, 0x55505250, + 0x33101410, 0x11101410, 0x11101410, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x44000000, 0x55000400, 0x66000400, 0x77343634, 0x77686868, + 0x886b6c6b, 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, 0x998c9294, 0x998c9294, 0x998c9294, 0x998c9294, + 0x998c8e8c, 0x99868786, 0x99868786, 0x99868786, 0x99848384, 0x99848384, 0x99848384, 0x99848384, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x997e7f7e, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x997e7c7e, 0x99848284, + 0x9984827b, 0x9984827b, 0x9984827b, 0x9984827b, 0x99848284, 0x99848284, 0x99848284, 0x997e7c7e, + 0x99848284, 0x997e7c7e, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x997b7c7b, + 0x997e7c7e, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x997b7b7b, 0x99848284, 0x99848284, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x99767776, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99737373, 0x997b797b, + 0x99737473, 0x99737473, 0x99737473, 0x99737473, 0x997b797b, 0x997b797b, 0x997b797b, 0x99707070, + 0x9970706e, 0x9970706e, 0x9970706e, 0x9970706e, 0x99636565, 0x99636565, 0x99636565, 0x99636565, + 0x99525652, 0x99525652, 0x99525652, 0x99525652, 0x99504d50, 0x882c282c, 0x772c282c, 0x77080408, + 0x66000000, 0x66000000, 0x55000000, 0x55000000, 0x44000000, 0x22000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x11000000, 0x33525452, 0x77525452, + 0xaab2afb2, 0xddfffbff, 0xfffffbff, 0xfffffbff, 0xffeff3f7, 0xffeff3f7, 0xffeff3f7, 0xffeff3f7, + 0xffefefef, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, + 0xffe1e4e1, 0xffe1e4e1, 0xffe1e4e1, 0xffe1e4e1, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe1e1e1, + 0xffe6e1e6, 0xffe6e1e6, 0xffe6e1e6, 0xffe6e1e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, + 0xffe6e3de, 0xffe6e3de, 0xffe6e3de, 0xffe6e3de, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe1dde1, + 0xffe6e3de, 0xffe6e3de, 0xffe6e3de, 0xffe6e3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, + 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3dd, 0xffdee3dd, 0xffdee1de, 0xffdee0db, + 0xffdedbd9, 0xffe2dddc, 0xffdbd9db, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd3d4d3, + 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffcbc9cb, + 0xffcbc9cb, 0xffcbc9cb, 0xffcbc9cb, 0xffb2b2b2, 0xffb2b2b2, 0xffb2b2b2, 0xffb2b2b2, 0xff8f908f, + 0xff8f908f, 0xbb8f908f, 0x88505250, 0x663c3d3c, 0x333c3d3c, 0x11000000, 0x00000000, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x44000000, 0x55000000, 0x77343234, 0x77686868, 0x999c9a9c, 0x999c9a9c, 0x999c9a9c, + 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, 0x998c9294, 0x998c9294, 0x998c9294, 0x998c9294, + 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x997e7f7e, 0x99848684, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, + 0x9984827b, 0x9984827b, 0x9984827b, 0x9984827b, 0x99848284, 0x99848284, 0x997e7c7e, 0x997e7c7e, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x997b7c7b, 0x997b7c7b, + 0x99848284, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x99848284, 0x99848284, 0x997b7b7b, 0x997b7b7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x99737973, 0x99737973, 0x99737973, 0x99737973, 0x99737173, 0x99737173, 0x99504d50, 0x99504d50, + 0x88424142, 0x88212021, 0x77212021, 0x66000000, 0x55000000, 0x55000000, 0x44000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x22000400, 0x66525452, 0xaaa5a7a5, 0xeef7fbf7, 0xfff7fbf7, + 0xfffffbff, 0xfffffbff, 0xfffffbff, 0xfffffbff, 0xffeff3f7, 0xffeff3f7, 0xffeff3f7, 0xffeff3f7, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, + 0xffe6ebe6, 0xffe6ebe6, 0xffe1e4e1, 0xffe1e4e1, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, + 0xffe6e1e6, 0xffe6e1e6, 0xffe6e1e6, 0xffefe7ef, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, + 0xffe6e3de, 0xffe6e3de, 0xffe6e3de, 0xffe6e3de, 0xffe6e3e6, 0xffe6e3e6, 0xffe1dde1, 0xffe6e3e6, + 0xffe6e3de, 0xffe6e3de, 0xffe6e3de, 0xffe6e3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, + 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdee3de, + 0xffe5e2df, 0xffe1e0dd, 0xffdcdbdc, 0xffdddfe0, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffb5b6b5, 0xdd797979, 0xaa797979, 0x663c3d3c, 0x22000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22000000, + 0x55000000, 0x77343234, 0x88686468, 0x999c969c, 0x999c9a9c, 0x999c9a9c, 0x999c9a9c, 0x999c9a9c, + 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, 0x998c9294, 0x998c9294, 0x998c9294, 0x998c9294, + 0x99868786, 0x99868786, 0x99868786, 0x99868786, 0x99848384, 0x99848384, 0x99848384, 0x99848384, + 0x997e807e, 0x997e807e, 0x997e807e, 0x997e807e, 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, + 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, + 0x997e7c79, 0x997e7c79, 0x997e7c79, 0x99797776, 0x99797779, 0x99797779, 0x997e7c7e, 0x997e7c7e, + 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997b7c7b, 0x997b7c7b, 0x99737773, 0x997b7c7b, + 0x99797779, 0x997e7c7e, 0x99797779, 0x997e7c7e, 0x997b7b7b, 0x997b7b7b, 0x997b7b7b, 0x997b7b7b, + 0x99767876, 0x99767876, 0x99767876, 0x99767876, 0x99767876, 0x99767876, 0x99767876, 0x99767876, + 0x99767776, 0x997b7d7b, 0x997b7d7b, 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99767776, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x99737973, 0x99737973, 0x99737973, 0x99737973, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99636163, 0x99636163, 0x99424142, 0x88212021, 0x77191419, 0x66000000, 0x55000000, 0x55000000, + 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x11000400, 0x66797b79, 0xccb5b6b5, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, + 0xfffffbff, 0xfffffbff, 0xfffffbff, 0xfffffbff, 0xffeff3f7, 0xffeff3f7, 0xffeff3f7, 0xffeff3f7, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, + 0xffe1e4e1, 0xffe1e4e1, 0xffe1e4e1, 0xffdbdddb, 0xffe1e1e1, 0xffe1e1e1, 0xffdbdcdb, 0xffe1e1e1, + 0xffdedcde, 0xffdedcde, 0xffdedcde, 0xffdedcde, 0xffe1dde1, 0xffe1dde1, 0xffe1dde1, 0xffe1dde1, + 0xffe1dddb, 0xffe1dddb, 0xffe1dddb, 0xffe1dddb, 0xffe1dde1, 0xffe1dde1, 0xffe1dde1, 0xffe1dde1, + 0xffe1dddb, 0xffe1dddb, 0xffe1dddb, 0xffe1dddb, 0xffdbdddb, 0xffdbdddb, 0xffdbdddb, 0xffdbdddb, + 0xffdbdddb, 0xffdbdddb, 0xffdbdddb, 0xffdbdddb, 0xffdbdcd9, 0xffdbdcd9, 0xffdcdcda, 0xffdcdbda, + 0xffdddadb, 0xffddd9dc, 0xffdad8d9, 0xffd7dadb, 0xffdbdddc, 0xffdddfdd, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xbb737973, + 0x664d524d, 0x11000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080808, 0x00080808, 0x33080808, 0x66080808, + 0x8852555a, 0x99848686, 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, 0x999c9e9c, + 0x99949294, 0x99949294, 0x99949294, 0x99898889, 0x998c8684, 0x998c8684, 0x998c8684, 0x9984807e, + 0x99848284, 0x99848284, 0x99848284, 0x997b7b7e, 0x997b7d7b, 0x997b7d7b, 0x99767876, 0x99767876, + 0x997b797b, 0x997b797b, 0x99767576, 0x99767576, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737473, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99767570, 0x99767570, 0x997b7973, 0x99767570, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99767576, 0x99767576, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7973, 0x9973706e, 0x996b6768, 0x99635d63, 0x994a4a4a, 0x77292b29, 0x66080c08, 0x66080c08, + 0x66000000, 0x33000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x333a393a, 0xbbb2b2b2, 0xeeefefef, 0xffefefef, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xfff7f7f7, 0xfff7f7f7, 0xffececec, 0xffececec, 0xffefebe6, 0xffefebe6, 0xffe6e4e1, 0xffe6e4e1, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffdedce1, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd3d7d3, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd3d7d3, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d6d6, 0xffd8d7d6, + 0xffd8d6d7, 0xffd8d3d6, 0xffd8d3d7, 0xffd9d4d8, 0xffd9d6d9, 0xffd8d7d7, 0xffd6d7d6, 0xffd3d7d3, + 0xffd3d7d3, 0xffd3d7d3, 0xffd6dbd6, 0xffd3d7d3, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbde, + 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffd6dbd6, 0xffd0d1ce, 0xffd0d1ce, 0xffc5bebd, 0xffc5c6c5, + 0xee9a9797, 0xaa6e6868, 0x3342393a, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080808, 0x33080808, 0x66080808, 0x885a595a, + 0x99848686, 0x99848686, 0x999c9e9c, 0x999c9e9c, 0x99919291, 0x99919291, 0x99919291, 0x99919291, + 0x99898889, 0x99898889, 0x99898889, 0x997e7f7e, 0x9984807e, 0x997b7b79, 0x997b7b79, 0x997b7b79, + 0x997b7b7e, 0x997b7b7e, 0x997b7b7e, 0x99737479, 0x99767876, 0x99767876, 0x99707370, 0x99707370, + 0x99767576, 0x99767576, 0x99767576, 0x99767576, 0x99737573, 0x99737573, 0x99737573, 0x99707370, + 0x99707370, 0x99707370, 0x99707370, 0x99707370, 0x99707370, 0x99707370, 0x99707370, 0x99707370, + 0x996e706e, 0x99707370, 0x99707370, 0x996e706e, 0x99707370, 0x99707370, 0x99707370, 0x996e706e, + 0x996e706e, 0x996e706e, 0x996e706e, 0x996e706e, 0x99707370, 0x996e706e, 0x99707370, 0x99707370, + 0x99737173, 0x99737473, 0x99737373, 0x99737173, 0x99737370, 0x99737370, 0x99737370, 0x99737370, + 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737373, + 0x9970716e, 0x99767570, 0x99767570, 0x99767570, 0x99737573, 0x99737370, 0x99737370, 0x99737370, + 0x99737370, 0x99737573, 0x99737370, 0x99737370, 0x99707370, 0x99707370, 0x99707370, 0x99707370, + 0x99707373, 0x99707373, 0x99707373, 0x99707373, 0x99707370, 0x99707370, 0x99707370, 0x99707370, + 0x99707370, 0x99707370, 0x99707370, 0x99707370, 0x99767576, 0x99767576, 0x99767576, 0x99767576, + 0x99767576, 0x99767576, 0x99767576, 0x99767576, 0x99767876, 0x99767876, 0x99767876, 0x99767876, + 0x997b7973, 0x997b7973, 0x997b7973, 0x9973706e, 0x996b696b, 0x994a4a4a, 0x88292b29, 0x77080c08, + 0x66000000, 0x66000000, 0x33000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x55474847, + 0xddb2b2b2, 0xffefefef, 0xffefefef, 0xffefefef, 0xfff4f3f4, 0xfff4f3f4, 0xfff4f3f4, 0xfff4f3f4, + 0xffececec, 0xffececec, 0xffe1e1e1, 0xffe1e1e1, 0xffe6e4e1, 0xffdedddb, 0xffdedddb, 0xffdedddb, + 0xffdedce1, 0xffdedce1, 0xffdedce1, 0xffd6d5db, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd3d4d3, + 0xffd9d7d9, 0xffd9d7d9, 0xffd9d7d9, 0xffd9d7d9, 0xffd3d7d3, 0xffd3d7d3, 0xffd3d7d3, 0xffd3d7d3, + 0xffd3d7d3, 0xffd3d7d3, 0xffd3d7d3, 0xffd0d2d0, 0xffd3d7d3, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, + 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, + 0xffd3d4d3, 0xffd0d1d0, 0xffd3d4d3, 0xffd0d1d0, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, + 0xffd0d4d0, 0xffd3d5d3, 0xffd0d4d0, 0xffd3d5d3, 0xffd6d4d3, 0xffd6d4d3, 0xffd6d4d3, 0xffd7d4d4, + 0xffd6d2d3, 0xffd5cfd3, 0xffd5d0d4, 0xffd5d3d4, 0xffd5d5d4, 0xffd2d5d3, 0xffd3d4d3, 0xffd3d7d3, + 0xffd3d7d3, 0xffd3d7d3, 0xffd3d7d3, 0xffd0d2d0, 0xffd3d7d3, 0xffd3d7d3, 0xffd0d2d0, 0xffd3d7d9, + 0xffd3d7d9, 0xffd3d7d9, 0xffd3d7d9, 0xffd3d4d3, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, + 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd0d1ce, 0xffc5c6c5, + 0xffc5c6c5, 0xff9a9797, 0xcc9a9797, 0x55313231, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33080808, 0x66080808, 0x995a595a, 0x99848284, + 0x99848686, 0x99848686, 0x99848686, 0x99848686, 0x99919291, 0x99868686, 0x99868686, 0x99868686, + 0x997e7f7e, 0x997e7f7e, 0x99737573, 0x99737573, 0x997b7b79, 0x997b7b79, 0x99737573, 0x99737573, + 0x99737479, 0x99737479, 0x99737479, 0x99737479, 0x99707370, 0x99707370, 0x99707370, 0x99707370, + 0x99707170, 0x99707170, 0x99707170, 0x996b6d6b, 0x996e706e, 0x996e706e, 0x996e706e, 0x996b6d6b, + 0x996e706e, 0x996e706e, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996b6d6b, 0x996e706e, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996e706e, 0x996e706e, 0x996e706e, 0x996b6d6b, 0x996e706e, 0x996e706e, 0x996e706e, 0x996e706e, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x9973706e, 0x9973706e, 0x9973706e, 0x9973706e, + 0x99737073, 0x99737073, 0x99737073, 0x99737373, 0x99737373, 0x99737073, 0x99737073, 0x99737073, + 0x9970716e, 0x9970716e, 0x9970716e, 0x9970716e, 0x9973706e, 0x99737370, 0x9973706e, 0x9973706e, + 0x9973706e, 0x9973706e, 0x99737370, 0x99737370, 0x99707370, 0x99707370, 0x996e706e, 0x996e706e, + 0x996e7073, 0x996e7073, 0x996e7073, 0x996e7073, 0x996e706e, 0x996e706e, 0x996e706e, 0x996e706e, + 0x996e706e, 0x996e706e, 0x996e706e, 0x996e706e, 0x99707170, 0x99707170, 0x99707170, 0x99707170, + 0x99707170, 0x99707170, 0x99707170, 0x99707170, 0x99707370, 0x99707370, 0x99707370, 0x99707370, + 0x997b7973, 0x9973706e, 0x9973706e, 0x9973706e, 0x996b696b, 0x996b696b, 0x994a4a4a, 0x99292b29, + 0x66101010, 0x66000000, 0x66000000, 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x66474847, 0xeed6d7d6, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xfff4f3f4, 0xffe9e7e9, 0xffe9e7e9, 0xffe9e7e9, + 0xffe1e1e1, 0xffe1e1e1, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d5db, 0xffd6d5db, 0xffd6d5db, 0xffd6d5db, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, + 0xffd3d2d3, 0xffd3d2d3, 0xffd3d2d3, 0xffcecece, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, 0xffcecece, + 0xffd0d2d0, 0xffd0d2d0, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd3d4d3, 0xffd0d1d0, 0xffd0d1d0, + 0xffced2ce, 0xffd0d4d0, 0xffd0d4d0, 0xffced2ce, 0xffd6d1d0, 0xffd6d1d0, 0xffd6d4d3, 0xffd6d2d2, + 0xffd6d2d3, 0xffd4d0d2, 0xffd4d0d3, 0xffd5d2d5, 0xffd6d3d6, 0xffd5d4d5, 0xffd3d4d3, 0xffd0d2d0, + 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d3, + 0xffd0d2d3, 0xffd0d2d3, 0xffd0d2d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, + 0xffd3d4d3, 0xffd9d9d9, 0xffd9d9d9, 0xffd6dbd6, 0xffd0d1ce, 0xffd0d1ce, 0xffd0d1ce, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xff9a9797, 0xdd949694, 0x44313231, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x66080808, 0x995a595a, 0x99848284, 0x99848284, + 0x99848686, 0x99848686, 0x99848686, 0x99848686, 0x99868686, 0x99868686, 0x99868686, 0x997b797b, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x996b6d73, 0x996b6d73, 0x996b6d73, 0x996b6d73, 0x996b6d6b, 0x996b6d6b, 0x99707370, 0x996b6d6b, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996e706e, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99736d6b, 0x9973706e, 0x9973706e, 0x9973706e, + 0x99737073, 0x99736d73, 0x99737073, 0x99737073, 0x99736d73, 0x99736d73, 0x99736d73, 0x99737073, + 0x996b6d6b, 0x9970716e, 0x9970716e, 0x996b6d6b, 0x99736d6b, 0x99736d6b, 0x99736d6b, 0x99736d6b, + 0x9973706e, 0x9973706e, 0x99736d6b, 0x9973706e, 0x996e706e, 0x99707370, 0x99707370, 0x996b6d6b, + 0x996e7073, 0x996b6d73, 0x996b6d73, 0x996e7073, 0x996e706e, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x99707170, 0x996b6d6b, 0x99707170, 0x996b6d6b, 0x99707370, 0x99707370, 0x996b6d6b, 0x996b6d6b, + 0x9973706e, 0x9973706e, 0x9973706e, 0x9973706e, 0x996b696b, 0x996b696b, 0x996b696b, 0x994a4a4a, + 0x88313131, 0x66101010, 0x66000000, 0x55000000, 0x22000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x44474847, 0xeed6d7d6, 0xffd6d7d6, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffe9e7e9, 0xffe9e7e9, 0xffe9e7e9, 0xffdedbde, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d5db, 0xffceced6, 0xffceced6, 0xffceced6, 0xffcecece, 0xffcecece, 0xffd3d4d3, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffd6d1d0, 0xffd6d1d0, 0xffd6d1d0, 0xffd7d2d2, + 0xffd7d3d5, 0xffd6d1d5, 0xffd6d1d4, 0xffd6d3d5, 0xffd5d4d5, 0xffd1d2d1, 0xffd0d1d0, 0xffd0d2d0, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffd3d4d3, 0xffcecece, 0xffd3d4d3, 0xffcecece, 0xffd3d4d3, + 0xffd3d4d3, 0xffcecece, 0xffcecece, 0xffd0d1ce, 0xffd0d1ce, 0xffd0d1ce, 0xffd0d1ce, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xff949694, 0xcc949694, 0x33313231, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x44000000, 0x884a4542, 0x99737173, 0x99737173, 0x99737173, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99737373, + 0x99737173, 0x99737173, 0x99706f70, 0x99706f70, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x99706d70, 0x99737173, 0x99706d70, 0x99706d70, 0x996b6b6b, 0x996b6c6b, 0x996b6b6b, 0x996b6b6b, + 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, 0x996b6d6b, + 0x996b6d6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, 0x996e6c6e, 0x99706f70, 0x996e6c6e, 0x99706f70, + 0x996b6f6b, 0x996b6d6b, 0x996b6f6b, 0x996b6f6b, 0x996e6d6e, 0x996e6d6e, 0x996e6d6e, 0x996e6d6e, + 0x996b7070, 0x996b6f6e, 0x996b6f6e, 0x996b6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, + 0x99736f6e, 0x99737070, 0x99737070, 0x99737070, 0x996e6f6e, 0x99737173, 0x99707070, 0x996e6f6e, + 0x9970706e, 0x9970706e, 0x9970706e, 0x9970706e, 0x996e6f6e, 0x996e6f6e, 0x99707070, 0x996e6f6e, + 0x996b6f70, 0x996b6f70, 0x996b6f70, 0x996b6f70, 0x996e6f6e, 0x99707070, 0x99707070, 0x996e6f6e, + 0x996e6f6e, 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x99707070, 0x996e6f6e, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, + 0x996b6d6b, 0x996b6d6b, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, 0x996b6d6b, 0x996b6c6b, + 0x996b6f70, 0x996b6f70, 0x996b6c6e, 0x996b6c6e, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x99686b6b, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x9963656b, 0x9963656b, 0x995d6065, 0x9952555a, + 0x994a4d4a, 0x881e1f1e, 0x66080808, 0x66080808, 0x44000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11101010, 0xccc5cac5, 0xffc5cac5, 0xffc5cac5, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedbd6, 0xffdedbd6, 0xffdedbd6, 0xffd6d5d3, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd3d0d3, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecdce, 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffcecdce, 0xffcecece, 0xffcecdce, 0xffcecdce, + 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced0d0, 0xffcecece, 0xffced0d0, + 0xffced0ce, 0xffcecece, 0xffced0ce, 0xffced0ce, 0xffd0ced0, 0xffd0ced0, 0xffd0ced0, 0xffd0ced0, + 0xffced1d3, 0xffced0d0, 0xffced0d0, 0xffced0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, + 0xffd6d0d0, 0xffd6d1d3, 0xffd6d1d3, 0xffd6d1d3, 0xffd0d0d0, 0xffd6d2d6, 0xffd3d1d3, 0xffd1d0d1, + 0xffd5d2d4, 0xffd7d3d6, 0xffd7d3d6, 0xffd6d3d5, 0xffd1d2d3, 0xffcecfce, 0xffcdcece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcbcccb, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcbcacb, 0xffc5cac5, + 0xffc0c4c0, 0xffc0c4c0, 0xffb5b6b5, 0xffa5a6a5, 0xffa5a6a5, 0xaa737473, 0x11101010, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x22000000, 0x661e1e1e, 0x99656263, 0x99737173, 0x99737173, 0x99737173, + 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99737373, 0x99737373, 0x99737373, 0x996b6c6b, + 0x996e6c6e, 0x996e6c6e, 0x99706f70, 0x99706f70, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, + 0x99706d70, 0x99706d70, 0x99706d70, 0x996e696e, 0x996b6b6b, 0x996b6b6b, 0x996b696b, 0x996b6b6b, + 0x996b696b, 0x996b6b6b, 0x996b696b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6d6b, + 0x996b6c6b, 0x996b6b6b, 0x996b6c6b, 0x996b6b6b, 0x996e6c6e, 0x996e6c6e, 0x99706f70, 0x996e6c6e, + 0x996b6f6b, 0x996b6f6b, 0x996b6f6b, 0x996b6f6b, 0x996e6d6e, 0x996e6d6e, 0x996e6d6e, 0x996e6d6e, + 0x996b6f6e, 0x996b7070, 0x996b7070, 0x996b6f6e, 0x996e6f6e, 0x99707070, 0x99707070, 0x996e6f6e, + 0x99737070, 0x99737070, 0x99736f6e, 0x99736f6e, 0x996e6f6e, 0x99707070, 0x99737173, 0x996e6f6e, + 0x996e6f68, 0x996e6f68, 0x9970706e, 0x9970706e, 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, + 0x996b6f70, 0x996b6f70, 0x996b6f70, 0x996b706e, 0x996e6f6e, 0x99707070, 0x996e6f6e, 0x996e6f6e, + 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, + 0x996b6d6b, 0x996b6c6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, + 0x996b6f70, 0x996b6c6e, 0x996b6c6e, 0x996b6c6e, 0x99686b6b, 0x99686b6b, 0x9965686b, 0x99686b6b, + 0x996b696b, 0x99686768, 0x99686768, 0x99686768, 0x9963656b, 0x995d6065, 0x995d6065, 0x9952555a, + 0x994a4d4a, 0x99343634, 0x77080808, 0x66080808, 0x66000000, 0x22000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x664d4e4d, 0xffc5cac5, 0xffc5cac5, 0xffc5cac5, + 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd6d5d3, 0xffd6d5d3, 0xffced0d0, 0xffced0d0, + 0xffd0cdd0, 0xffd0cdd0, 0xffd3d0d3, 0xffd3d0d3, 0xffcbcdcb, 0xffcbcdcb, 0xffcbcdcb, 0xffcbcdcb, + 0xffcecdce, 0xffced0ce, 0xffced0ce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecace, 0xffcecdce, + 0xffcecace, 0xffcecdce, 0xffcecace, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced0d0, 0xffcecece, + 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffd0ced0, 0xffd0ced0, 0xffd0ced0, 0xffd0ced0, + 0xffced0d0, 0xffced1d3, 0xffced1d3, 0xffced0d0, 0xffd0d0d0, 0xffd3d1d3, 0xffd3d1d3, 0xffd0d0d0, + 0xffd6d1d3, 0xffd6d1d3, 0xffd6d0d0, 0xffd6d0d0, 0xffd0d0d0, 0xffd3d1d3, 0xffd3d1d3, 0xffd0d0d0, + 0xffd5d2d3, 0xffd6d3d6, 0xffd7d2d5, 0xffd6d1d5, 0xffd6d1d5, 0xffd4cfd3, 0xffd0ced0, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffced2ce, 0xffcecace, 0xffcecece, 0xffcecece, 0xffcbcccb, + 0xffcbcccb, 0xffcbcccb, 0xffcbcccb, 0xffcbcacb, 0xffcbcacb, 0xffcbcacb, 0xffcbcacb, 0xffc5cac5, + 0xffc0c4c0, 0xffc0c4c0, 0xffb5b6b5, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a6a5, 0x66424242, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x44000000, 0x883c3b3c, 0x99656263, 0x99656263, 0x99656263, 0x99737173, + 0x99707070, 0x99707070, 0x99707070, 0x99707070, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, + 0x996b696b, 0x996b696b, 0x996e6c6e, 0x996e6c6e, 0x996b6b6b, 0x996b6b6b, 0x996b686b, 0x996b6b6b, + 0x996e696e, 0x996e696e, 0x996e696e, 0x996e696e, 0x996b696b, 0x996b696b, 0x996b6b6b, 0x996b696b, + 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, + 0x996b6b6b, 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, 0x99706f70, 0x99706f70, 0x99706f70, 0x99706f70, + 0x996b6d6b, 0x996b6f6b, 0x996b6f6b, 0x996b6f6b, 0x996e6d6e, 0x996e6d6e, 0x996e6d6e, 0x996e6d6e, + 0x996b6f6e, 0x996b6f6e, 0x996b7070, 0x996b7070, 0x99707070, 0x99707070, 0x996e6f6e, 0x99707070, + 0x99736f6e, 0x99737070, 0x99736f6e, 0x99737070, 0x99707070, 0x996e6f6e, 0x99707070, 0x99707070, + 0x9970706e, 0x9970706e, 0x9970706e, 0x9970706e, 0x99707070, 0x996e6f6e, 0x99707070, 0x996e6f6e, + 0x996b706e, 0x996b706e, 0x996b6f70, 0x996b6f70, 0x996e6f6e, 0x99737173, 0x99707070, 0x99707070, + 0x99707070, 0x996e6f6e, 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6c6b, 0x996b6d6b, 0x996b6c6b, 0x996b6c6b, + 0x996b6c6b, 0x996b6b6b, 0x996b6d6b, 0x996b6c6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, + 0x996b6c6e, 0x996b6c6e, 0x996b6c6e, 0x996b6c6e, 0x9965686b, 0x9965686b, 0x9965686b, 0x9965686b, + 0x99686768, 0x99686768, 0x99656465, 0x99656465, 0x9963656b, 0x995d6065, 0x99585a60, 0x9952555a, + 0x994a4d4a, 0x994a4d4a, 0x881e1f1e, 0x66080808, 0x66000000, 0x44000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0xddc5cac5, 0xffc5cac5, 0xffc5cac5, 0xffc5cac5, + 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffcecece, 0xffced0d0, 0xffced0d0, 0xffced0d0, 0xffc5cace, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcbcdcb, 0xffcbcdcb, 0xffc8ccc8, 0xffcbcdcb, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecdce, 0xffcecace, + 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced1d3, + 0xffcecece, 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffd0ced0, 0xffd0ced0, 0xffd0ced0, 0xffd0ced0, + 0xffced0d0, 0xffced0d0, 0xffced1d3, 0xffced1d3, 0xffd3d1d3, 0xffd6d2d6, 0xffd0d0d0, 0xffd3d1d3, + 0xffd6d0d0, 0xffd6d1d3, 0xffd6d0d0, 0xffd6d1d3, 0xffd3d1d3, 0xffd0d0d0, 0xffd3d1d3, 0xffd3d1d3, + 0xffd4d2d2, 0xffd6d2d6, 0xffd6d1d5, 0xffd5d1d5, 0xffd5d2d4, 0xffd2d1d2, 0xffcfcfcf, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcbcccb, + 0xffc8c9c8, 0xffc8c9c8, 0xffc8c9c8, 0xffcbcacb, 0xffc8c6c8, 0xffc8c6c8, 0xffc8c6c8, 0xffc0c4c0, + 0xffc0c4c0, 0xffbabdba, 0xffb5b6b5, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a6a5, 0xbb737473, 0x110e0d0e, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x55000000, 0x995a595a, 0x99656263, 0x99656263, 0x99656263, 0x99656263, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b6c6b, 0x996b6c6b, 0x99636563, 0x99636563, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b686b, 0x996b686b, 0x996b686b, 0x996b686b, + 0x996b656b, 0x996e696e, 0x996e696e, 0x996e696e, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, + 0x996b696b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, + 0x996b6b6b, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, 0x99706f70, 0x99737173, 0x99706f70, 0x99737173, + 0x996b6f6b, 0x996b6f6b, 0x996b6f6b, 0x996b706b, 0x99706d70, 0x996e6d6e, 0x996e6d6e, 0x99706d70, + 0x996b7070, 0x996b7070, 0x996b6f6e, 0x996b6f6e, 0x99707070, 0x99707070, 0x99737173, 0x99707070, + 0x99737070, 0x99737070, 0x99737173, 0x99737173, 0x99707070, 0x99737173, 0x99707070, 0x99707070, + 0x9970706e, 0x9970706e, 0x9970706e, 0x9970706e, 0x99707070, 0x99707070, 0x99707070, 0x99707070, + 0x996b706e, 0x996b706e, 0x996b706e, 0x996b706e, 0x99707070, 0x99707070, 0x99737173, 0x99737173, + 0x99737173, 0x99707070, 0x99707070, 0x996e6f6e, 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, 0x996b6d6b, + 0x996b6c6b, 0x996b6d6b, 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, + 0x996b6c6e, 0x996b696b, 0x996b696b, 0x996b696b, 0x9965686b, 0x9965686b, 0x9963656b, 0x9963656b, + 0x99656465, 0x99656465, 0x99656465, 0x99636163, 0x995d6065, 0x995d6065, 0x99585a60, 0x9952555a, + 0x994a4d4a, 0x994a4d4a, 0x99343634, 0x66080808, 0x66000000, 0x55000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x44313131, 0xffc5cac5, 0xffc5cac5, 0xffc5cac5, 0xffc5cac5, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffc5cace, 0xffc5cace, 0xffc5cace, 0xffc5cace, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffc5cac5, 0xffc5cac5, 0xffc5cac5, 0xffc5cac5, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, + 0xffcecace, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced1d3, 0xffced0d0, 0xffced1d3, + 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffced2ce, 0xffd3ced3, 0xffd0ced0, 0xffd0ced0, 0xffd3ced3, + 0xffced1d3, 0xffced1d3, 0xffced0d0, 0xffced0d0, 0xffd3d1d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd3d1d3, + 0xffd6d1d3, 0xffd6d1d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd3d1d3, 0xffd6d2d6, 0xffd3d1d3, 0xffd6d2d6, + 0xffd6d2d6, 0xffd7d2d6, 0xffd5d3d5, 0xffd5d1d5, 0xffd3d1d2, 0xffd0d0d0, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecace, 0xffcecace, 0xffcecace, 0xffc8c9c8, + 0xffc8c9c8, 0xffc8c9c8, 0xffc8c9c8, 0xffc8c6c8, 0xffc8c6c8, 0xffc8c6c8, 0xffc5c2c5, 0xffc0c4c0, + 0xffbabdba, 0xffbabdba, 0xffb5b6b5, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a6a5, 0xeea5a6a5, 0x44292829, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x22000400, 0x771e201e, 0x995a595a, 0x99525452, 0x995a5a5a, 0x99636163, 0x99636163, + 0x996b696b, 0x99656568, 0x99656568, 0x99656568, 0x99636563, 0x99636563, 0x99636563, 0x99636563, + 0x99686568, 0x99656565, 0x99656565, 0x99656565, 0x996b6765, 0x996b6765, 0x996b6868, 0x996b6765, + 0x996b676b, 0x996b686b, 0x996b676b, 0x996b686b, 0x996b696b, 0x996b696b, 0x996b6b6b, 0x996b696b, + 0x996b696b, 0x996b696b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, + 0x996e6f6e, 0x996b6d6b, 0x996b6d6b, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, + 0x99737173, 0x99737173, 0x99737173, 0x996e746e, 0x99737173, 0x99737373, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99707173, 0x996e7173, 0x99707173, 0x99707173, + 0x99707070, 0x99707070, 0x996e6f6e, 0x99707070, 0x99736f6e, 0x99737070, 0x99736f6e, 0x99737070, + 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996b6d6b, 0x996b6d6b, + 0x996b6f6e, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x99686868, 0x99656765, 0x99656765, 0x99636563, + 0x99636463, 0x99636463, 0x99636263, 0x99636163, 0x99636163, 0x995d5c5d, 0x995d5c5d, 0x995a595a, + 0x99525552, 0x993f423f, 0x993f423f, 0x77191c19, 0x77000000, 0x66000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x88737173, 0xffbdbabd, 0xffbdbabd, 0xffc5c2c5, 0xffc5c2c5, + 0xffc5cac5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, + 0xffc5c9c5, 0xffc5c8c5, 0xffc5c9c5, 0xffc5c8c5, 0xffc5c9c5, 0xffc5c9c5, 0xffc5cac5, 0xffc5c9c5, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecdce, 0xffcecace, + 0xffcecace, 0xffcecace, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffd0d0d0, 0xffcecece, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d5d0, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d4d6, + 0xffd6d4d6, 0xffd6d3d6, 0xffd7d1d5, 0xffd5d1d4, 0xffd2d0d2, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, + 0xffd0d0d0, 0xffcecece, 0xffcecece, 0xffced0d0, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecdce, 0xffcecace, 0xffcecace, 0xffc5cac5, + 0xffc5c8c5, 0xffc5c8c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c4c5, 0xffc5c4c5, 0xffc5c2bd, + 0xffc0bdbd, 0xffc0bdbd, 0xffbdbabd, 0xffb5b6b5, 0xffadadad, 0xffa5a3a5, 0xff9c9a9c, 0x77585a58, + 0x00000400, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x33000400, 0x883c3d3c, 0x995a595a, 0x99525452, 0x99525452, 0x995a5a5a, 0x99636163, + 0x99656568, 0x99656568, 0x99656568, 0x99656568, 0x99636563, 0x99636463, 0x99636463, 0x99636463, + 0x99656565, 0x99656565, 0x99656565, 0x99656565, 0x996b6765, 0x996b6765, 0x996b6765, 0x996b6765, + 0x996b676b, 0x996b686b, 0x996b686b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b6b6b, + 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, 0x996b6d6b, 0x996b6b6b, 0x996b6d6b, 0x996b6c6b, + 0x996e6f6e, 0x996b6d6b, 0x99707070, 0x99737173, 0x996e6f6e, 0x996e6f6e, 0x99707070, 0x99707070, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737373, 0x99737473, 0x99737373, 0x99737373, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737373, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737373, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99707173, 0x99737173, 0x99737173, 0x99707173, + 0x99707070, 0x99707070, 0x99707070, 0x99707070, 0x99737070, 0x99737070, 0x99737070, 0x99737070, + 0x996e6f6e, 0x99707070, 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996b6d6b, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6c6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x99686868, 0x99656765, 0x99656765, 0x99656765, + 0x99636263, 0x99636263, 0x99636263, 0x99636163, 0x99605e60, 0x99605e60, 0x995d5c5d, 0x995a595a, + 0x99525552, 0x993f423f, 0x993f423f, 0x88191c19, 0x77030303, 0x66000000, 0x22000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0xddadaaad, 0xffb5b2b5, 0xffbdbabd, 0xffbdbabd, 0xffc5c2c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c8c5, 0xffc5c8c5, 0xffc5c9c5, 0xffc5c8c5, 0xffc5c9c5, 0xffc5c9c5, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcbccc8, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecdce, + 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffd0d0d0, 0xffd0d0d0, 0xffd3d1d3, 0xffd3d1d3, 0xffd0d0d0, 0xffd0d0d0, 0xffd3d1d3, 0xffd3d1d3, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd6d4d6, + 0xffd6d2d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd6d4d6, + 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d2d6, + 0xffd6d5d6, 0xffd6d4d6, 0xffd6d1d3, 0xffd1d1d1, 0xffd3d1d3, 0xffd3d1d3, 0xffd0d0d0, 0xffd0d0d0, + 0xffd0d0d0, 0xffd0d0d0, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced0d0, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecace, 0xffcecace, 0xffcecace, 0xffc5cac5, + 0xffc5c8c5, 0xffc5c8c5, 0xffc5c8c5, 0xffc5c5c5, 0xffc5c5c5, 0xffc5c5c5, 0xffc5c4c5, 0xffc5c2bd, + 0xffc3c0bd, 0xffc0bdbd, 0xffbdbabd, 0xffb5b6b5, 0xffadadad, 0xffa5a3a5, 0xffa5a3a5, 0xaa585a58, + 0x11000400, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x44000400, 0x993c3d3c, 0x995a595a, 0x994a4d4a, 0x99525452, 0x995a5a5a, 0x99636163, + 0x99606165, 0x99606165, 0x99656568, 0x99656568, 0x99636563, 0x99636263, 0x99636263, 0x99636263, + 0x99686568, 0x99656565, 0x99656565, 0x99656565, 0x996b6765, 0x996b6563, 0x996b6765, 0x996b6868, + 0x996b686b, 0x996b686b, 0x996b686b, 0x996b696b, 0x996b696b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, + 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996e6f6e, 0x996e6f6e, 0x99707070, 0x99737173, 0x99707070, 0x99707070, 0x99707070, 0x99707070, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737573, 0x99737373, 0x99737573, + 0x99737373, 0x99737473, 0x99737373, 0x99737373, 0x99737373, 0x99737473, 0x99737173, 0x99737473, + 0x99737173, 0x99737473, 0x99737373, 0x99737373, 0x99737473, 0x99737373, 0x99737173, 0x99737173, + 0x99737373, 0x99737373, 0x99737473, 0x99737473, 0x99737173, 0x99737373, 0x99737373, 0x99737373, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99707173, 0x99707173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99707070, 0x99707070, 0x99707070, 0x996e6f6e, 0x99707070, 0x99707070, 0x996e6f6e, 0x996e6f6e, + 0x996b7070, 0x996b6f6e, 0x996b6f6e, 0x996b6d6b, 0x996b6d6b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x99656765, 0x99686868, 0x99656765, 0x99656765, + 0x99636463, 0x99636263, 0x99636263, 0x99636163, 0x99605e60, 0x995d5c5d, 0x995d5c5d, 0x995a595a, + 0x99525552, 0x99525552, 0x993f423f, 0x882c2f2c, 0x77050505, 0x66000000, 0x33000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0xffadaaad, 0xffb5b2b5, 0xffb5b2b5, 0xffbdbabd, 0xffc5c2c5, + 0xffc5c2c5, 0xffc5c2c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c5c5, 0xffc5c5c5, 0xffc5c5c5, + 0xffc5c8c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c8c5, 0xffc5c8c5, 0xffc5c6c5, 0xffc5c9c5, 0xffc5cac5, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcbccc8, 0xffcecace, 0xffcecdce, 0xffcecdce, 0xffcecece, + 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffd0d0d0, 0xffd0d0d0, 0xffd3d1d3, 0xffd6d2d6, 0xffd3d1d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd3d1d3, + 0xffd6d4d3, 0xffd6d2d6, 0xffd6d4d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d7d6, 0xffd6d4d6, 0xffd6d7d6, + 0xffd6d4d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d4d6, 0xffd6d7d6, + 0xffd6d4d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd6d4d6, + 0xffd6d5d6, 0xffd6d5d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd3d1d3, 0xffd3d1d3, 0xffd0d0d0, 0xffd3d1d3, + 0xffd3d1d3, 0xffd0d0d0, 0xffd0d0d0, 0xffced1d3, 0xffced0d0, 0xffced0d0, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecace, 0xffcecace, 0xffcecace, 0xffc5c9c5, + 0xffc5cac5, 0xffc5c8c5, 0xffc5c8c5, 0xffc5c6c5, 0xffc5c5c5, 0xffc5c4c5, 0xffc5c2c5, 0xffc5c2bd, + 0xffc0bdbd, 0xffc0bdbd, 0xffbdbabd, 0xffb5b6b5, 0xffadadad, 0xffa5a3a5, 0xffa5a3a5, 0xcc848684, + 0x22000400, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x55000400, 0x993c3d3c, 0x993c3d3c, 0x994a4d4a, 0x99525452, 0x995a5a5a, 0x995a5a5a, + 0x995a5d63, 0x99606165, 0x99606165, 0x99606165, 0x99636163, 0x99636263, 0x99636463, 0x99636263, + 0x99686568, 0x99656565, 0x99656565, 0x99656565, 0x996b6563, 0x996b6868, 0x996b6765, 0x996b6868, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b6b6b, 0x996b6c6b, 0x996b6c6b, + 0x996b6c6b, 0x996b6b6b, 0x996b6c6b, 0x996b6d6b, 0x996b6c6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x996e6f6e, 0x99707070, 0x99737173, 0x99707070, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99707370, 0x99707370, 0x99737173, 0x99707370, 0x99737373, 0x99737473, 0x99737173, 0x99737473, + 0x99737573, 0x99737573, 0x99737373, 0x99737373, 0x99737373, 0x99737473, 0x99737373, 0x99737473, + 0x99737573, 0x99737473, 0x99737473, 0x99737473, 0x99737473, 0x99737473, 0x99737473, 0x99737373, + 0x99737573, 0x99737373, 0x99737473, 0x99737473, 0x99737373, 0x99737573, 0x99737473, 0x99737473, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99707070, 0x99707070, 0x99737173, 0x99737173, 0x99737173, 0x99707070, + 0x996b7070, 0x996b6f6e, 0x996b6f6e, 0x996b6f6e, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6b6b, + 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, 0x99656765, 0x99686868, 0x99656765, + 0x99636463, 0x99636463, 0x99636263, 0x99636163, 0x99605e60, 0x99605e60, 0x995d5c5d, 0x995d5c5d, + 0x99525552, 0x99525552, 0x993f423f, 0x992c2f2c, 0x77080808, 0x77000000, 0x44000000, 0x00000000, + 0x00000000, 0x00000000, 0x443a393a, 0xffadaaad, 0xffadaaad, 0xffb5b2b5, 0xffbdbabd, 0xffbdbabd, + 0xffc5c2c5, 0xffc5c2c5, 0xffc5c2c5, 0xffc5c2c5, 0xffc5c4c5, 0xffc5c4c5, 0xffc5c6c5, 0xffc5c4c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c8c5, 0xffc5c6c5, 0xffc5cac5, 0xffc5c9c5, 0xffc5cac5, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecdce, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffd0d0d0, 0xffd3d1d3, 0xffd6d2d6, 0xffd3d1d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d4d3, 0xffd6d4d3, 0xffd6d2d6, 0xffd6d4d3, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d4d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d4d5, + 0xffd6d7d6, 0xffd6d5d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd3d1d3, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffd3d1d3, 0xffced1d3, 0xffced0d0, 0xffced0d0, 0xffced0d0, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffceccce, 0xffc5cac5, + 0xffc5c9c5, 0xffc5cac5, 0xffc5c9c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c4c5, 0xffc5c4c5, 0xffc5c2bd, + 0xffc3c0bd, 0xffc0bdbd, 0xffc0bdbd, 0xffb5b6b5, 0xffadadad, 0xffa5a3a5, 0xffa5a3a5, 0xdd848684, + 0x222c2f2c, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x55161716, 0x99424542, 0x99424542, 0x994a4c4a, 0x99525252, 0x995a595a, 0x995a595a, + 0x995d5e5d, 0x995d5e5d, 0x99606060, 0x99606060, 0x99636263, 0x99636263, 0x99636263, 0x99636463, + 0x99636563, 0x99636563, 0x99656765, 0x99636563, 0x996b686b, 0x996b676b, 0x996b686b, 0x996b696b, + 0x996b696b, 0x996b6b6b, 0x996b696b, 0x996b696b, 0x996e6c6e, 0x996e6c6e, 0x996e6c6e, 0x99706f70, + 0x996b6d6b, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x99707070, 0x996e6f6e, 0x99707070, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737373, 0x99737373, 0x99737173, + 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99767776, 0x99767776, 0x99767776, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737473, 0x99737473, 0x99737473, 0x99737373, 0x99737573, 0x99737473, 0x99737473, 0x99737373, + 0x99737373, 0x99737373, 0x99737473, 0x99737373, 0x99737373, 0x99737173, 0x99737173, 0x99737373, + 0x99737373, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99707070, 0x996e6f6e, 0x99707070, 0x996e6f6e, 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996b6d6b, + 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b696b, 0x996b6868, 0x996b6765, 0x996b6765, + 0x99656465, 0x99656465, 0x99656465, 0x99636163, 0x99636163, 0x99605e60, 0x995d5c5d, 0x995a595a, + 0x995a555a, 0x99524e52, 0x994a484a, 0x99424142, 0x770b0b0b, 0x77000000, 0x55000000, 0x00000000, + 0x00000000, 0x00000000, 0x44373737, 0xffa5a6a5, 0xffadaaad, 0xffb2b5b8, 0xffb5babd, 0xffb5babd, + 0xffbdc0c0, 0xffbdc0c0, 0xffbdc0c0, 0xffbdc2c5, 0xffc5c4c5, 0xffc5c4c5, 0xffc5c4c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c8c5, 0xffc5c6c5, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecccb, + 0xffcecace, 0xffcecdce, 0xffcecace, 0xffcecace, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced0d0, + 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd3d1d3, 0xffd0d0d0, 0xffd3d1d3, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d4d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d9, 0xffd7d7d7, 0xffd8d7d8, 0xffd6d6d6, 0xffd7d6d6, + 0xffd5d8d9, 0xffd6d8d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, + 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d1d6, 0xffd6d1d6, 0xffd6d1d6, 0xffd6d1d6, 0xffd3d1d3, + 0xffd0d0d0, 0xffd0d0d0, 0xffcecece, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffceccce, 0xffcecccb, + 0xffcec9c8, 0xffcec9c8, 0xffcec9c8, 0xffcbc8cb, 0xffcbc8cb, 0xffc8c5c8, 0xffc8c5c8, 0xffc5c2c5, + 0xffc3c0c3, 0xffc0bdc0, 0xffbdbabd, 0xffb5bab5, 0xffafb2af, 0xffaaaaaa, 0xffa5a2a5, 0xff9c9e9c, + 0x44343534, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x55161716, 0x99424542, 0x99424542, 0x99424542, 0x994a4c4a, 0x99525252, 0x995a595a, + 0x995a5d5a, 0x995d5e5d, 0x99636163, 0x99606060, 0x99636263, 0x99636263, 0x99636263, 0x99636463, + 0x99636563, 0x99636563, 0x99636563, 0x99656765, 0x996b676b, 0x996b686b, 0x996b686b, 0x996b696b, + 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996e6c6e, 0x996e6c6e, 0x99706f70, 0x99706f70, + 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x99707070, 0x99707070, 0x99707070, 0x99707070, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737373, + 0x99737373, 0x99737373, 0x99737573, 0x99737473, 0x99737473, 0x99737573, 0x99737473, 0x99737473, + 0x99737573, 0x99737573, 0x99767776, 0x99737573, 0x99737573, 0x99767776, 0x99767776, 0x99767776, + 0x99767776, 0x997b797b, 0x99797879, 0x99767776, 0x99737776, 0x99737776, 0x99737776, 0x99737776, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737473, 0x99737473, 0x99737573, 0x99737573, 0x99737473, 0x99737473, 0x99737473, + 0x99737573, 0x99737573, 0x99737473, 0x99737573, 0x99737473, 0x99737473, 0x99737373, 0x99737473, + 0x99737373, 0x99737473, 0x99737473, 0x99737173, 0x99737373, 0x99737373, 0x99737173, 0x99737173, + 0x99737173, 0x99707070, 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996b6d6b, + 0x996b6c6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b6765, + 0x99686768, 0x99656465, 0x99656465, 0x99656465, 0x99636163, 0x99605e60, 0x995d5c5d, 0x995a595a, + 0x995a555a, 0x99524e52, 0x994a484a, 0x99424142, 0x77101010, 0x77000000, 0x55000000, 0x11000000, + 0x00000000, 0x00000000, 0x55373737, 0xffa5a6a5, 0xffadaaad, 0xffafafb2, 0xffb2b5b8, 0xffb5babd, + 0xffbdbebd, 0xffbdc0c0, 0xffbdc2c5, 0xffbdc1c3, 0xffc5c4c5, 0xffc5c4c5, 0xffc5c5c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c9c5, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecccb, + 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffced0d0, 0xffced0d0, + 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffd3d1d3, 0xffd3d1d3, 0xffd6d2d6, 0xffd3d1d3, 0xffd6d2d6, + 0xffd6d4d6, 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d5d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd9d8d9, 0xffd6d7d6, 0xffd6d7d6, 0xffd9d8d6, 0xffdbd9d6, 0xffd9d8d6, + 0xffd6d7d6, 0xffd6dbde, 0xffd6d9db, 0xffd7d9dc, 0xffd9d9d9, 0xffdbd8dc, 0xffdcd8dd, 0xffd9d7da, + 0xffd5d7da, 0xffd5d7d6, 0xffd5d5d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d4d6, 0xffd6d5d6, + 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d1d6, 0xffd0d0d0, + 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffcecece, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecccb, + 0xffcecccb, 0xffcecccb, 0xffcec9c8, 0xffcbc8cb, 0xffc8c5c8, 0xffc8c5c8, 0xffc8c5c8, 0xffc5c2c5, + 0xffc3c0c3, 0xffc0bdc0, 0xffbdbabd, 0xffb5bab5, 0xffafb2af, 0xffaaaaaa, 0xffa5a2a5, 0xff9c9e9c, + 0x55343534, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x66161716, 0x99424542, 0x99424542, 0x99424542, 0x994a4c4a, 0x99525252, 0x995a595a, + 0x995a5d5a, 0x995d5e5d, 0x995d5e5d, 0x99636163, 0x99636163, 0x99636263, 0x99636463, 0x99636463, + 0x99636563, 0x99656765, 0x99656765, 0x99656765, 0x996b686b, 0x996b676b, 0x996b686b, 0x996b696b, + 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996e6c6e, 0x99706f70, 0x99737173, 0x99706f70, + 0x996e6f6e, 0x99707070, 0x99707070, 0x99707070, 0x99707070, 0x99707070, 0x99737173, 0x99737173, + 0x99737473, 0x99737573, 0x99737373, 0x99737473, 0x99737373, 0x99737373, 0x99737473, 0x99737573, + 0x99737473, 0x99737473, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99767776, 0x997b797b, 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x997b797b, + 0x99797879, 0x99767776, 0x99767776, 0x99767776, 0x99737776, 0x99737776, 0x99737776, 0x99737776, + 0x99737773, 0x99737573, 0x99737773, 0x99737773, 0x99767773, 0x99767773, 0x99767773, 0x99767773, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737373, 0x99737573, 0x99737373, 0x99737573, 0x99737373, 0x99737473, 0x99737373, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99707070, 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, + 0x996b6d6b, 0x996b6d6b, 0x996b6b6b, 0x996b6b6b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b6868, + 0x99686768, 0x99686768, 0x99656465, 0x99656465, 0x99636163, 0x99605e60, 0x995d5c5d, 0x995d5c5d, + 0x995a555a, 0x99524e52, 0x994a484a, 0x99424142, 0x77101010, 0x77000000, 0x55000000, 0x11000000, + 0x00000000, 0x00000000, 0x66373737, 0xffa5a6a5, 0xffadaaad, 0xffafafb2, 0xffb5babd, 0xffb5babd, + 0xffbdbebd, 0xffbdc0c0, 0xffbdc0c0, 0xffbdc2c5, 0xffc5c4c5, 0xffc5c4c5, 0xffc5c6c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c8c5, 0xffc5c9c5, 0xffc5c9c5, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecccb, + 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffced1d3, 0xffced0d0, + 0xffd0d0d0, 0xffd3d1d3, 0xffd3d1d3, 0xffd6d2d6, 0xffd3d1d3, 0xffd3d1d3, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d5d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d9d6, + 0xffd9d8d9, 0xffdbd9db, 0xffd9d8d9, 0xffdbd9db, 0xffdbd9d6, 0xffdbd9d6, 0xffdbd9d6, 0xffdedbd6, + 0xffd6d9db, 0xffd6d8d9, 0xffd6d9db, 0xffd7d8dc, 0xffd9dadb, 0xffdbdadc, 0xffdcd8dc, 0xffdcd8dc, + 0xffdcd7dc, 0xffdad7da, 0xffd8d8d7, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d5d6, + 0xffd6d5d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd3d1d3, + 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecdce, 0xffcecccb, + 0xffcecccb, 0xffcecccb, 0xffcec9c8, 0xffcecace, 0xffcbc8cb, 0xffcbc8cb, 0xffc8c5c8, 0xffc5c2c5, + 0xffc5c2c5, 0xffc0bdc0, 0xffc0bdc0, 0xffb5bab5, 0xffafb2af, 0xffaaaaaa, 0xffa5a2a5, 0xff9c9e9c, + 0x55343534, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x66161716, 0x99424542, 0x99424542, 0x99424542, 0x994a4c4a, 0x99525252, 0x995a595a, + 0x995a5d5a, 0x995d5e5d, 0x995d5e5d, 0x99606060, 0x99636163, 0x99636263, 0x99636263, 0x99636463, + 0x99636563, 0x99656765, 0x99686868, 0x99686868, 0x996b686b, 0x996b686b, 0x996b696b, 0x996b696b, + 0x996b6b6b, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, 0x99706f70, 0x99706f70, 0x99706f70, 0x99706f70, + 0x99707070, 0x99707070, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737473, 0x99737573, 0x99737473, 0x99737373, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99797879, 0x997b797b, 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99797879, 0x99767776, + 0x99767776, 0x99767776, 0x99767776, 0x997b797b, 0x99737776, 0x99737879, 0x99737776, 0x99737776, + 0x99737973, 0x99737773, 0x99737973, 0x99737973, 0x997b7973, 0x99767773, 0x99767773, 0x997b7973, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737573, 0x99737473, 0x99737573, 0x99737473, 0x99737573, 0x99737573, 0x99737373, 0x99737373, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99707070, 0x99707070, 0x996e6f6e, + 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6c6b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, + 0x99686768, 0x99686768, 0x99656465, 0x99656465, 0x99636163, 0x99636163, 0x995d5c5d, 0x995d5c5d, + 0x995a555a, 0x99524e52, 0x994a484a, 0x99424142, 0x77101010, 0x77000000, 0x66000000, 0x11000000, + 0x00000000, 0x00000000, 0x776e6f6e, 0xffa5a6a5, 0xffadaaad, 0xffafafb2, 0xffb2b5b8, 0xffb5babd, + 0xffbdbebd, 0xffbdc0c0, 0xffbdc0c0, 0xffbdc1c3, 0xffc5c4c5, 0xffc5c4c5, 0xffc5c5c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c8c5, 0xffc5cac5, 0xffc5cac5, 0xffcecace, 0xffcecace, 0xffcecccb, 0xffcecccb, + 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced0d0, 0xffced0d0, 0xffced1d3, 0xffced1d3, + 0xffd3d1d3, 0xffd3d1d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d5d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d8d6, + 0xffdbd9db, 0xffdedbde, 0xffdbd9db, 0xffdbd9db, 0xffdbd9d6, 0xffdbd9d6, 0xffdedbd6, 0xffdbd9d6, + 0xffd6d9db, 0xffd6d9db, 0xffd6dadb, 0xffd7dade, 0xffdadbdb, 0xffdbdadc, 0xffdbd8dc, 0xffdcd8dc, + 0xffdcdadc, 0xffd9dad9, 0xffd7d8d7, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d2d6, + 0xffd3d1d3, 0xffd3d1d3, 0xffd0d0d0, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecccb, + 0xffcecccb, 0xffcecccb, 0xffcecccb, 0xffcecace, 0xffcbc8cb, 0xffcbc8cb, 0xffc8c5c8, 0xffc5c2c5, + 0xffc5c2c5, 0xffc0bdc0, 0xffc0bdc0, 0xffb5bab5, 0xffafb2af, 0xffaaaaaa, 0xffa5a2a5, 0xff9c9e9c, + 0x66343534, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x66161616, 0x99424142, 0x99424142, 0x994a454a, 0x99504c50, 0x995a595a, 0x995a595a, + 0x995d5c5d, 0x99605e60, 0x99605e60, 0x99605e60, 0x99636163, 0x99636263, 0x99636463, 0x99636563, + 0x996b656b, 0x996b676b, 0x996b686b, 0x996b686b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b6b6b, + 0x996e6c6b, 0x996e6c6b, 0x99706f6b, 0x996e6c6b, 0x996e7070, 0x996e7070, 0x99686f6e, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737373, 0x99737473, 0x99737473, 0x99737473, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99767776, 0x99767776, 0x99767776, 0x99767776, + 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99767876, 0x99767876, 0x99767876, 0x99767876, + 0x997b7979, 0x997b7d7b, 0x997b7576, 0x997b7979, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99767876, 0x99797b79, 0x99767876, 0x99767876, + 0x997b787b, 0x997b787b, 0x997b787b, 0x997b787b, 0x99767876, 0x99767876, 0x99767876, 0x99767876, + 0x99767876, 0x99767876, 0x99767876, 0x99767876, 0x99767776, 0x99767776, 0x99767776, 0x99767776, + 0x99767776, 0x99767776, 0x99767776, 0x99737573, 0x99737776, 0x99737573, 0x99737573, 0x99737573, + 0x99737473, 0x99737373, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x996e6f6e, 0x996e6f6e, 0x996e6f6e, 0x996b6d6b, 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, 0x996b696b, + 0x99656865, 0x99656865, 0x99636563, 0x99636563, 0x99606160, 0x99606160, 0x995d5d5d, 0x995d5d5d, + 0x995a555a, 0x99524e52, 0x994a484a, 0x99424142, 0x77101410, 0x77000000, 0x66000000, 0x11000000, + 0x00000000, 0x00000000, 0x77686968, 0xff9c9e9c, 0xffa5aaa5, 0xffadb1ad, 0xffb5b7b5, 0xffb5b7b5, + 0xffbdbebd, 0xffc0c0c0, 0xffc3c1c3, 0xffc3c1c3, 0xffc5c2c5, 0xffc8c5c5, 0xffc8c5c5, 0xffcbc8c5, + 0xffc5c6c5, 0xffc8c9c8, 0xffc8c9c8, 0xffc8c9c8, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecdce, + 0xffcecece, 0xffcecece, 0xffd0d0d0, 0xffcecece, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd3d4d3, + 0xffd6d4d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d8d6, + 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd6dbd6, 0xffd6dbd6, 0xffd9dcd9, 0xffd6dbd6, + 0xffdedbde, 0xffdeddde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedcde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedade, 0xffdcdcdd, 0xffdbdbdc, 0xffdbdbdc, 0xffdbdbdc, 0xffdcdadc, + 0xffdcdadd, 0xffdcdadc, 0xffd9d9d9, 0xffd8d9db, 0xffd9d8d9, 0xffdbd9db, 0xffd9d8d9, 0xffd6d9d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d4d6, + 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d0d0, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecdd0, 0xffceccd3, 0xffcbcccb, 0xffc8c9c8, 0xffc8c9c8, 0xffc5c6c5, 0xffc5c6c5, + 0xffc3c2c3, 0xffc0bec0, 0xffc0bec0, 0xffbdbab5, 0xffb5b2af, 0xffadaaaa, 0xffa5a2a5, 0xff9c9e9c, + 0x66343734, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x66161616, 0x99424142, 0x99424142, 0x994a454a, 0x99504c50, 0x99555255, 0x995a595a, + 0x995d5c5d, 0x99605e60, 0x99605e60, 0x99636163, 0x99636263, 0x99636263, 0x99636563, 0x99636563, + 0x996b676b, 0x996b686b, 0x996b676b, 0x996b696b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, 0x996b6b6b, + 0x99706f6b, 0x996e6c6b, 0x99706f6b, 0x99706f6b, 0x996e7070, 0x996e7070, 0x996e7070, 0x996e7070, + 0x99737173, 0x99737373, 0x99737173, 0x99737473, 0x99737373, 0x99737373, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99767776, 0x99767776, 0x99767776, 0x99767776, + 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99767876, 0x99767876, 0x99767876, 0x99797b79, + 0x997b7979, 0x997b7979, 0x997b7979, 0x997b7979, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b7b7b, + 0x997b797b, 0x997b797b, 0x997b7b7b, 0x997b7c7b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99797b79, 0x99797b79, 0x99797b79, 0x99797b79, + 0x997b787b, 0x997b787b, 0x997b787b, 0x997b787b, 0x99797b79, 0x99767876, 0x99767876, 0x99797b79, + 0x99797b79, 0x99767876, 0x99767876, 0x99767876, 0x997b797b, 0x99797879, 0x997b797b, 0x99797879, + 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99737776, 0x99737776, 0x99737776, 0x99737573, + 0x99737573, 0x99737573, 0x99737473, 0x99737373, 0x99737173, 0x99737373, 0x99737173, 0x99737173, + 0x99707070, 0x99737173, 0x99707070, 0x996e6f6e, 0x996b6c6b, 0x996b6d6b, 0x996b6c6b, 0x996b6b6b, + 0x99686b68, 0x99656865, 0x99656865, 0x99636563, 0x99636563, 0x99606160, 0x99606160, 0x995a595a, + 0x995a555a, 0x99524e52, 0x994a484a, 0x99424142, 0x77101410, 0x77000000, 0x66000000, 0x11000000, + 0x00000000, 0x00000000, 0x88686968, 0xff9c9e9c, 0xffa5aaa5, 0xffadb1ad, 0xffb5b7b5, 0xffb5b7b5, + 0xffbdbebd, 0xffc0c0c0, 0xffc0c0c0, 0xffc5c2c5, 0xffc8c5c5, 0xffc8c5c5, 0xffcbc8c5, 0xffcbc8c5, + 0xffc8c9c8, 0xffc8c9c8, 0xffc8c9c8, 0xffcbcccb, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, + 0xffd0d0d0, 0xffcecece, 0xffd0d0d0, 0xffd0d0d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, + 0xffd6d2d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, + 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd6dbd6, 0xffd9dcd9, 0xffd9dcd9, 0xffd9dcd9, + 0xffdedbde, 0xffdedcde, 0xffdedcde, 0xffdedcde, 0xffdedcde, 0xffdedcde, 0xffdedbde, 0xffdeddde, + 0xffdedcde, 0xffdedcde, 0xffdddddd, 0xffdbdddd, 0xffdbdddc, 0xffdbdddc, 0xffdddbdd, 0xffdedbde, + 0xffdfdbdf, 0xffe0dbdf, 0xffdcdadc, 0xffd7dadc, 0xffd8d9d9, 0xffdad9da, 0xffdbd9db, 0xffd6d9d6, + 0xffd6d9d6, 0xffd6d8d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d4d6, + 0xffd6d5d6, 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd3d1d3, 0xffd0d0d0, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecdd0, 0xffcbcccb, 0xffcbcccb, 0xffc8c9c8, 0xffc5c6c5, 0xffc5c6c5, + 0xffc3c2c3, 0xffc3c2c3, 0xffbdbabd, 0xffbdbab5, 0xffb5b2af, 0xffadaaaa, 0xffa5a2a5, 0xff9c9e9c, + 0x66343734, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x77161616, 0x99424142, 0x99424142, 0x994a454a, 0x99504c50, 0x99555255, 0x995a595a, + 0x995d5c5d, 0x99605e60, 0x99636163, 0x99636163, 0x99636463, 0x99636563, 0x99636563, 0x99636563, + 0x996b676b, 0x996b676b, 0x996b696b, 0x996b696b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, 0x996b6d6b, + 0x99706f6b, 0x99706f6b, 0x99706f6b, 0x99706f6b, 0x996e7070, 0x996e7070, 0x99737173, 0x99737173, + 0x99737373, 0x99737373, 0x99737373, 0x99737373, 0x99737473, 0x99737473, 0x99737573, 0x99737573, + 0x99737573, 0x99737573, 0x99737773, 0x99737773, 0x99767776, 0x99767776, 0x99767776, 0x99767776, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99767876, 0x99797b79, 0x99797b79, 0x99797b79, + 0x997b7979, 0x997b7979, 0x997b7979, 0x997b7979, 0x997b797b, 0x997b7c7b, 0x997b7c7b, 0x997b7b7b, + 0x997b7b7b, 0x997b7b7b, 0x997b7b7b, 0x997b7c7b, 0x997b7b7b, 0x997b7d7b, 0x997b7c7b, 0x997b7c7b, + 0x997e7c7b, 0x997e7c7b, 0x99817f7b, 0x997e7c7b, 0x99797b79, 0x99797b79, 0x997b7d7b, 0x997b7d7b, + 0x997b7b7b, 0x997b7b7b, 0x997b7b7b, 0x997b7b7b, 0x99797b79, 0x99797b79, 0x99797b79, 0x99797b79, + 0x99797b79, 0x99767876, 0x99797b79, 0x99797b79, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x99767776, 0x99737776, 0x99737776, 0x99737776, 0x99737776, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737373, 0x99737473, 0x99737173, 0x99737173, + 0x99737173, 0x99737173, 0x99707070, 0x99707070, 0x996b6d6b, 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, + 0x99686b68, 0x99656865, 0x99656865, 0x99656865, 0x99636563, 0x99606160, 0x995d5d5d, 0x995d5d5d, + 0x995a555a, 0x99524e52, 0x994a484a, 0x99424142, 0x77101410, 0x77000000, 0x66000000, 0x11000000, + 0x00000000, 0x00000000, 0x99686968, 0xff9c9e9c, 0xffa5aaa5, 0xffadb1ad, 0xffb5b7b5, 0xffbdbebd, + 0xffbdbebd, 0xffc0c0c0, 0xffc5c2c5, 0xffc5c2c5, 0xffc8c5c5, 0xffcbc8c5, 0xffcbc8c5, 0xffcbc8c5, + 0xffc8c9c8, 0xffc8c9c8, 0xffcbcccb, 0xffcbcccb, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, + 0xffd0d0d0, 0xffd0d0d0, 0xffd3d1d3, 0xffd3d1d3, 0xffd0d1d0, 0xffd0d1d0, 0xffd3d4d3, 0xffd3d4d3, + 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, + 0xffdbdcdb, 0xffdbdcdb, 0xffdbdcdb, 0xffdbdcdb, 0xffd9dcd9, 0xffd9dcd9, 0xffd9dcd9, 0xffdbdddb, + 0xffdedcde, 0xffdeddde, 0xffdedcde, 0xffdedcde, 0xffdedcde, 0xffdedfde, 0xffdedfde, 0xffdeddde, + 0xffdeddde, 0xffdeddde, 0xffe1dee1, 0xffdfdedf, 0xffdddfdd, 0xffdddddc, 0xffdddcdd, 0xffdddfe0, + 0xffdfdedf, 0xffdfdcdf, 0xffdfdcdf, 0xffdfdbdf, 0xffdfdbde, 0xffdfdbdf, 0xffdcd9dc, 0xffd6d9d6, + 0xffd6d9d6, 0xffd6d9d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d5d6, + 0xffd6d7d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd3d1d3, 0xffd3d1d3, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecdd0, 0xffcbcccb, 0xffc8c9c8, 0xffc8c9c8, 0xffc8c9c8, 0xffc5c6c5, + 0xffc3c2c3, 0xffc3c2c3, 0xffc0bec0, 0xffbdbab5, 0xffb5b2af, 0xffadaaaa, 0xffa5a2a5, 0xff9c9e9c, + 0x66343734, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x77161616, 0x99424142, 0x99424142, 0x994a454a, 0x99504c50, 0x995a595a, 0x995a595a, + 0x99605e60, 0x99605e60, 0x99636163, 0x99636163, 0x99636563, 0x99636563, 0x99636563, 0x99636563, + 0x996b676b, 0x996b686b, 0x996b696b, 0x996b696b, 0x996b6c6b, 0x996b6b6b, 0x996b6c6b, 0x996b6d6b, + 0x99706f6b, 0x99706f6b, 0x99706f6b, 0x9973716b, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99737173, 0x99737473, 0x99737473, 0x99737473, 0x99737473, 0x99737573, 0x99737573, 0x99737573, + 0x99737773, 0x99737773, 0x99737773, 0x99737973, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99797b79, 0x99797b79, 0x99797b79, 0x997b7d7b, + 0x997b7979, 0x997b7d7b, 0x997b7979, 0x997b7d7b, 0x997b7c7b, 0x997b7c7b, 0x997b7c7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7c7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997e7c7b, 0x99817f7b, 0x99817f7b, 0x997e7c7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x99797b79, + 0x997b7d7b, 0x997b7b7b, 0x997b7d7b, 0x997b7b7b, 0x99797b79, 0x99797b79, 0x99797b79, 0x99797b79, + 0x997b7d7b, 0x99797b79, 0x997b7d7b, 0x99797b79, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x9973797b, 0x99737776, 0x99737776, 0x99737776, + 0x99737573, 0x99737573, 0x99737573, 0x99737473, 0x99737573, 0x99737473, 0x99737373, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99707070, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6b6b, + 0x996b6d6b, 0x99686b68, 0x99656865, 0x99656865, 0x99636563, 0x99606160, 0x99606160, 0x995d5d5d, + 0x995a555a, 0x99524e52, 0x994a484a, 0x99424142, 0x77101410, 0x77000000, 0x66000000, 0x11000000, + 0x00000000, 0x00000000, 0x88686968, 0xff9c9e9c, 0xffa5aaa5, 0xffadb1ad, 0xffb5b7b5, 0xffbdbebd, + 0xffc0c0c0, 0xffc0c0c0, 0xffc3c1c3, 0xffc5c2c5, 0xffc8c5c5, 0xffcbc8c5, 0xffcbc8c5, 0xffcbc8c5, + 0xffc8c9c8, 0xffc8c9c8, 0xffcbcccb, 0xffcbcccb, 0xffcecece, 0xffcecdce, 0xffcecece, 0xffcecece, + 0xffd0d0d0, 0xffd3d1d3, 0xffd0d0d0, 0xffd3d1d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, 0xffd3d4d3, + 0xffd6d4d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d9d6, + 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffdbdcdb, 0xffdbdcdb, 0xffdbdcdb, 0xffdbdcdb, 0xffd9dcd9, 0xffd9dcd9, 0xffdbdddb, 0xffdedfde, + 0xffdeddde, 0xffdedfde, 0xffdeddde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdfdee0, 0xffe1dfe1, 0xffe2dfe2, 0xffe2dfe2, 0xffe4dfe4, 0xffe2dee1, 0xffdddee2, + 0xffdedddf, 0xffdedcdf, 0xffdedcdf, 0xffdfdedf, 0xffdfdede, 0xffdedede, 0xffdedbde, 0xffd5dbd5, + 0xffd6d9d6, 0xffd6d9d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d5d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecdd0, 0xffcecece, 0xffcbcccb, 0xffcbcccb, 0xffc8c9c8, 0xffc5c6c5, + 0xffc3c2c3, 0xffc3c2c3, 0xffc0bec0, 0xffbdbab5, 0xffb5b2af, 0xffadaaaa, 0xffa5a2a5, 0xff9c9e9c, + 0x66343734, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x66161616, 0x99424142, 0x99424142, 0x994a454a, 0x99504c50, 0x99555255, 0x995a595a, + 0x995a5d5a, 0x995d605d, 0x99606260, 0x99606260, 0x99656465, 0x99686768, 0x99686768, 0x99686768, + 0x996b696b, 0x996b6b6b, 0x996b6b6b, 0x996b6c6b, 0x996b6d6b, 0x996e6f6e, 0x996b6d6b, 0x996e6f6e, + 0x99737173, 0x996e6f73, 0x99707073, 0x99707073, 0x99737373, 0x99737173, 0x99737473, 0x99737473, + 0x99737573, 0x99737573, 0x99737776, 0x99737776, 0x99767776, 0x99767776, 0x99767776, 0x99767776, + 0x997b7876, 0x997b7876, 0x997b7876, 0x997b7876, 0x997b797b, 0x997b797b, 0x997b7b7b, 0x997b797b, + 0x997b7d7b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, + 0x997e807e, 0x99818381, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997e807e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7c7b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99797b79, 0x99767876, 0x99767876, 0x99767876, + 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99737573, 0x99737573, 0x99737573, 0x99737373, + 0x99737373, 0x99737173, 0x99737173, 0x99737173, 0x99707070, 0x99707070, 0x996e6f6e, 0x996e6f6e, + 0x996b6c6b, 0x996b6b6b, 0x996b696b, 0x996b696b, 0x99636563, 0x99606160, 0x995d5d5d, 0x995d5d5d, + 0x995a5552, 0x99524e4d, 0x99424142, 0x99424142, 0x77101010, 0x77000000, 0x66000000, 0x11000000, + 0x00000400, 0x00000400, 0x886e6d6e, 0xffa5a2a5, 0xffa5aaa5, 0xffadb1ad, 0xffb5b7b5, 0xffbdbebd, + 0xffc0c1c0, 0xffc0c1c0, 0xffc3c4c3, 0xffc3c4c3, 0xffc5c6c5, 0xffc8c9c8, 0xffc8c9c8, 0xffc8c9c8, + 0xffcecace, 0xffcecdce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced0d0, + 0xffd0d1d6, 0xffd0d1d6, 0xffd0d1d6, 0xffd0d1d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, + 0xffdedbd6, 0xffdedbd6, 0xffdedcd9, 0xffdedcd9, 0xffdedcde, 0xffdedbde, 0xffdeddde, 0xffdedcde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffe1e0e1, 0xffe6e3e6, 0xffe1e0e1, 0xffdedfde, 0xffdedfde, 0xffe1e1e1, 0xffe1e1e1, 0xffdddfdd, + 0xffe1dfe1, 0xffe3e0e3, 0xffe4e1e4, 0xffe3e0e3, 0xffe4e1e4, 0xffe4dfe4, 0xffe5dfe4, 0xffe5dee5, + 0xffe6dfe5, 0xffe6dfe5, 0xffe4dfe3, 0xffe0dee0, 0xffdfdedf, 0xffdfdede, 0xffdededf, 0xffdedcdb, + 0xffdedcdb, 0xffdedcdb, 0xffdedbde, 0xffd9d8d9, 0xffdbd9db, 0xffd9d8d9, 0xffd9d8d9, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd0d1d0, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffcecece, 0xffcecdce, 0xffcecace, 0xffcecace, 0xffc5c6c5, + 0xffc5c6c5, 0xffc0c1c0, 0xffbdbebd, 0xffb5b6b5, 0xffafafaf, 0xffaaa9aa, 0xffa5a2a5, 0xff9c9a9c, + 0x55343334, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x66161616, 0x99424142, 0x99424142, 0x994a454a, 0x99504c50, 0x99555255, 0x995a595a, + 0x995a5d5a, 0x995d605d, 0x99606260, 0x99636563, 0x99656465, 0x99656465, 0x99686768, 0x996b696b, + 0x996b6b6b, 0x996b6c6b, 0x996b6c6b, 0x996b6c6b, 0x99737173, 0x99707070, 0x99707070, 0x99737173, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737373, 0x99737373, 0x99737473, 0x99737473, + 0x99737573, 0x99737573, 0x99737776, 0x99737879, 0x99797879, 0x99767776, 0x99767776, 0x99767776, + 0x997b7b79, 0x997b7876, 0x997b7876, 0x997b7876, 0x997b797b, 0x997b797b, 0x997b7c7b, 0x997b7c7b, + 0x997b797b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x99817f81, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, + 0x997e807e, 0x997e807e, 0x997b7d7b, 0x997b7d7b, 0x997e7f7e, 0x997e7f7e, 0x99818081, 0x997e7f7e, + 0x99818081, 0x99818081, 0x99848284, 0x99848284, 0x997e807e, 0x997e807e, 0x997e807e, 0x997e807e, + 0x99818081, 0x997e7f7e, 0x997e7f7e, 0x99818081, 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, + 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997b7d7b, 0x997e807e, 0x997e807e, 0x997e807e, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7c7b, 0x997b7b7b, 0x997b797b, 0x997b7b7b, 0x99797b79, 0x99797b79, 0x99767876, 0x99767876, + 0x99797879, 0x99767776, 0x99767776, 0x99767776, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737473, 0x99737173, 0x99737173, 0x99737173, 0x99707070, 0x99707070, 0x996e6f6e, 0x996e6f6e, + 0x996b6c6b, 0x996b6c6b, 0x996b6b6b, 0x996b696b, 0x99636563, 0x99636563, 0x99606160, 0x995d5d5d, + 0x995a5552, 0x99524e4d, 0x994a4847, 0x99424142, 0x77101010, 0x77000000, 0x66000000, 0x11000000, + 0x00000400, 0x00000400, 0x776e6d6e, 0xffa5a2a5, 0xffa5aaa5, 0xffadb1ad, 0xffb5b7b5, 0xffbdbebd, + 0xffc0c1c0, 0xffc0c1c0, 0xffc3c4c3, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc8c9c8, 0xffcbcccb, + 0xffceccce, 0xffcecdce, 0xffcecece, 0xffcecece, 0xffced1d3, 0xffced1d3, 0xffced1d3, 0xffced2d6, + 0xffd3d4d6, 0xffd3d4d6, 0xffd3d4d6, 0xffd3d4d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, 0xffd6d5d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6dbd6, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, + 0xffdedcd9, 0xffdedcd9, 0xffdedcd9, 0xffdedcd9, 0xffdedcde, 0xffdedcde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdee0de, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffe4e1e4, 0xffe4e1e4, 0xffe1e0e1, 0xffe1e0e1, 0xffe1e1e1, 0xffe1e1e1, 0xffe4e4e4, 0xffe0e0e0, + 0xffe3e0e3, 0xffe3e0e3, 0xffe4e1e4, 0xffe5e2e5, 0xffe4e1e4, 0xffe4dfe4, 0xffe5e0e5, 0xffe5e2e5, + 0xffe6e2e5, 0xffe6e2e5, 0xffe6dfe6, 0xffe0dedf, 0xffdfdedf, 0xffdfdedf, 0xffdfdede, 0xffdfdcdd, + 0xffdedcdb, 0xffdedcdb, 0xffdedbde, 0xffdedbde, 0xffdbd9db, 0xffd9d8d9, 0xffd9d8d9, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d2d6, 0xffd0d1d0, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecace, 0xffc5c6c5, + 0xffc5c6c5, 0xffc0c1c0, 0xffbdbebd, 0xffb5b6b5, 0xffafafaf, 0xffaaa9aa, 0xffa5a2a5, 0xff9c9a9c, + 0x55343334, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x66161616, 0x99424142, 0x99424142, 0x994a454a, 0x99504c50, 0x995a595a, 0x995a595a, + 0x995d605d, 0x99606260, 0x99606260, 0x99606260, 0x99656465, 0x99686768, 0x99686768, 0x996b696b, + 0x996b6d6b, 0x996b6d6b, 0x996b6b6b, 0x996b6c6b, 0x996e6f6e, 0x996e6f6e, 0x99707070, 0x99707070, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737373, 0x99737573, 0x99737573, 0x99737573, + 0x99737776, 0x99737776, 0x99737776, 0x9973797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b7b79, 0x997b7b79, 0x997b7b79, 0x997b7d7b, 0x997b7b7b, 0x997b7b7b, 0x997b7c7b, 0x997b7c7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x99817f81, 0x99817f81, 0x99817f81, 0x99817f81, + 0x997b7d7b, 0x997e807e, 0x997e807e, 0x997e807e, 0x99818081, 0x99818081, 0x99818081, 0x997e7f7e, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99818381, 0x997e807e, 0x99818381, 0x997e807e, + 0x99848284, 0x99818081, 0x99818081, 0x99818081, 0x99848284, 0x997e7f7e, 0x99818081, 0x99818081, + 0x99818081, 0x997e7f7e, 0x99818081, 0x99818081, 0x997e807e, 0x997e807e, 0x997e807e, 0x997e807e, + 0x997e807e, 0x997e807e, 0x997e807e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7c7b, 0x997b7c7b, 0x997b7c7b, 0x99797b79, 0x99797b79, 0x99797b79, 0x99797b79, + 0x99797879, 0x99767776, 0x99797879, 0x99767776, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737473, 0x99737473, 0x99737373, 0x99737173, 0x99737173, 0x99707070, 0x99707070, 0x996e6f6e, + 0x996b6d6b, 0x996b6d6b, 0x996b6b6b, 0x996b696b, 0x99636563, 0x99636563, 0x995d5d5d, 0x995d5d5d, + 0x995a5552, 0x99524e4d, 0x99424142, 0x99424142, 0x77101010, 0x77000000, 0x66000000, 0x11000000, + 0x00000400, 0x00000400, 0x66373937, 0xffa5a2a5, 0xffa5aaa5, 0xffadb1ad, 0xffb5b7b5, 0xffbdbebd, + 0xffc0c1c0, 0xffc3c4c3, 0xffc3c4c3, 0xffc5c6c5, 0xffc5c6c5, 0xffc8c9c8, 0xffc8c9c8, 0xffcbcccb, + 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecece, 0xffced0d0, 0xffced0d0, 0xffced1d3, 0xffced1d3, + 0xffd3d4d6, 0xffd3d4d6, 0xffd3d4d6, 0xffd3d4d6, 0xffd6d5d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, + 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6dbd6, 0xffd9d9d9, 0xffdbdcdb, 0xffdbdcdb, 0xffdbdcdb, + 0xffdedcd9, 0xffdedddb, 0xffdedcd9, 0xffdedfde, 0xffdeddde, 0xffdeddde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdee1de, 0xffdee1de, 0xffdee0de, 0xffdee1de, + 0xffe1e0e1, 0xffe6e3e6, 0xffe6e3e6, 0xffe4e1e4, 0xffe4e4e4, 0xffe3e3e4, 0xffe3e3e3, 0xffe2e3e2, + 0xffe3e3e3, 0xffe4e2e4, 0xffe4e2e4, 0xffe4e2e4, 0xffe5e2e5, 0xffe5e3e5, 0xffe5e2e5, 0xffe5e2e5, + 0xffe5e2e5, 0xffe6e2e5, 0xffe6e3e5, 0xffe3e0e3, 0xffe0dfe0, 0xffe0dfdf, 0xffe0dfdf, 0xffe0dede, + 0xffdfdddd, 0xffdedcdb, 0xffdedcdb, 0xffdedbde, 0xffdbd9db, 0xffdedbde, 0xffdbd9db, 0xffd6d9d6, + 0xffd6d8d6, 0xffd6d8d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd6d4d6, 0xffd3d4d3, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecace, 0xffc5c6c5, + 0xffc5c6c5, 0xffc0c1c0, 0xffbdbebd, 0xffb5b6b5, 0xffafafaf, 0xffa5a2a5, 0xffa5a2a5, 0xff9c9a9c, + 0x55343334, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x66161616, 0x99424142, 0x99424142, 0x994a454a, 0x99504c50, 0x99555255, 0x995a595a, + 0x995a5d5a, 0x995d605d, 0x99606260, 0x99606260, 0x99686768, 0x99656465, 0x99686768, 0x996b696b, + 0x996b6b6b, 0x996b6c6b, 0x996b6c6b, 0x996b6d6b, 0x996e6f6e, 0x99707070, 0x99737173, 0x99707070, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737776, 0x99737776, 0x99737776, 0x99737776, 0x99797879, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b7b79, 0x997b7b79, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b827b, 0x99817f81, 0x99817f81, 0x99817f81, 0x99848284, + 0x99818381, 0x99818381, 0x997e807e, 0x99818381, 0x99848284, 0x99848284, 0x99848284, 0x99848284, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99818381, 0x99818381, 0x99818381, 0x99818381, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848684, 0x99818381, 0x99848684, 0x99818381, + 0x99848684, 0x997e807e, 0x997e807e, 0x997e807e, 0x997b7f7b, 0x997b827b, 0x997b7f7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7c7b, 0x997b7c7b, 0x99797b79, 0x997b7d7b, 0x99797b79, 0x99767876, + 0x997b797b, 0x997b797b, 0x99797879, 0x99767776, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x99737473, 0x99737473, 0x99737473, 0x99737373, 0x99737173, 0x99737173, 0x99707070, 0x99707070, + 0x996b6d6b, 0x996b6c6b, 0x996b6b6b, 0x996b696b, 0x99636563, 0x99606160, 0x995d5d5d, 0x995a595a, + 0x995a5552, 0x99524e4d, 0x99424142, 0x99424142, 0x77101010, 0x77000000, 0x55000000, 0x11000000, + 0x00000400, 0x00000400, 0x66373937, 0xffa5a2a5, 0xffa5aaa5, 0xffadb1ad, 0xffb5b7b5, 0xffbdbebd, + 0xffc0c1c0, 0xffc0c1c0, 0xffc3c4c3, 0xffc5c6c5, 0xffc8c9c8, 0xffc5c6c5, 0xffc8c9c8, 0xffcbcccb, + 0xffcecdce, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced0d0, 0xffced1d3, 0xffced2d6, 0xffced2d6, + 0xffd3d4d6, 0xffd3d4d6, 0xffd3d4d6, 0xffd3d4d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, + 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffdbdcdb, 0xffdbdcdb, 0xffdbdcdb, 0xffdbdcdb, + 0xffdedddb, 0xffdedddb, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdee0de, 0xffdee1de, 0xffdee0de, 0xffdee3de, 0xffdee1de, 0xffdee1de, 0xffdee1de, 0xffdee3de, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe3e4e3, 0xffe3e4e3, 0xffe2e4e2, 0xffe3e4e3, + 0xffe4e4e3, 0xffe4e3e4, 0xffe4e3e4, 0xffe4e4e5, 0xffe5e5e4, 0xffe5e3e5, 0xffe5e3e5, 0xffe5e2e5, + 0xffe6e2e5, 0xffe6e3e5, 0xffe6e3e5, 0xffe6e1e5, 0xffe3e0e3, 0xffe2dfe2, 0xffe0dfdf, 0xffe0dedf, + 0xffe0dfdc, 0xffdedcdc, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdbd9db, 0xffd6d9d6, + 0xffd6d9d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d5d6, 0xffd3d4d3, + 0xffd3d4d3, 0xffd0d1d0, 0xffd0d1d0, 0xffcecece, 0xffcecece, 0xffcecdce, 0xffcecace, 0xffc5c6c5, + 0xffc5c6c5, 0xffc0c1c0, 0xffbdbebd, 0xffb5b6b5, 0xffafafaf, 0xffaaa9aa, 0xffa5a2a5, 0xff9c9a9c, + 0x55343334, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x66161616, 0x99424142, 0x99424142, 0x99424542, 0x994a4c4a, 0x99525252, 0x995a595a, + 0x995d5d5d, 0x99606160, 0x99606160, 0x99636563, 0x99656765, 0x99656765, 0x996b696b, 0x996b696b, + 0x996b6b6b, 0x996b6b6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d73, 0x996e7073, 0x99707373, 0x996e7073, + 0x99737373, 0x99737373, 0x99737473, 0x99737573, 0x99767776, 0x99767776, 0x99767776, 0x99767776, + 0x99767776, 0x99767776, 0x997b797b, 0x99797879, 0x997b797b, 0x997b797b, 0x997b7b7b, 0x997b7b7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997e807e, 0x997b7d7b, 0x997e807e, + 0x997e8084, 0x997e8084, 0x997e8084, 0x997e8084, 0x99848284, 0x99848284, 0x99848284, 0x99848384, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848384, 0x99848484, 0x99848484, + 0x99898484, 0x99898484, 0x99898484, 0x99898484, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99898789, 0x99868486, 0x99868486, 0x99868486, 0x99868486, 0x99868486, 0x99848284, 0x99868486, + 0x99848484, 0x99848384, 0x99848384, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848384, + 0x99848384, 0x99848384, 0x99848284, 0x99848284, 0x99818081, 0x997e7f7e, 0x997e7f7e, 0x99818081, + 0x997e7f7e, 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, 0x997b7c7b, 0x997b7c7b, 0x997b7b7b, 0x997b7c7b, + 0x997b7b7b, 0x997b797b, 0x997b797b, 0x997b797b, 0x99767876, 0x99767876, 0x99767876, 0x99737573, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737373, 0x99737373, 0x99737073, 0x99736d73, + 0x99737173, 0x99706d6e, 0x996e6968, 0x996e6968, 0x99636563, 0x99606060, 0x99606060, 0x995d5a5d, + 0x99525152, 0x99525152, 0x99454345, 0x99454345, 0x77080c08, 0x77000000, 0x55000000, 0x11000000, + 0x00000000, 0x00000000, 0x66373637, 0xffa5a2a5, 0xffadaaad, 0xffadaaad, 0xffb5b2b5, 0xffbdbabd, + 0xffc0bec0, 0xffc3c2c3, 0xffc3c2c3, 0xffc5c6c5, 0xffc8c9c8, 0xffc8c9c8, 0xffcbcccb, 0xffcbcccb, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffd0ced0, 0xffd0ced0, 0xffd3d2d3, 0xffd3d2d3, 0xffd3d2d3, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d9d6, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedcde, 0xffdedcde, 0xffdeddde, 0xffdeddde, + 0xffdedfde, 0xffdedfde, 0xffdee0e1, 0xffdedfde, 0xffdedfde, 0xffe1e1e1, 0xffe1e1e1, 0xffe1e1e1, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e5e6, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe5e3e5, 0xffe4e5e4, 0xffe3e5e3, 0xffe4e5e3, + 0xffe4e6e4, 0xffe5e5e4, 0xffe5e6e5, 0xffe5e7e5, 0xffe5e6e4, 0xffe6e6e5, 0xffe6e6e6, 0xffe6e4e6, + 0xffe6e4e6, 0xffe6e4e6, 0xffe6e4e6, 0xffe6e3e5, 0xffe6e3e5, 0xffe6e1e5, 0xffe5e2e4, 0xffdfdfde, + 0xffdfe1df, 0xffdfdede, 0xffdedfde, 0xffdeddde, 0xffdedcde, 0xffdedcde, 0xffdedbde, 0xffd9d9d9, + 0xffdbdcdb, 0xffd9d9d9, 0xffd9d9d9, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d4d6, + 0xffd6d4d6, 0xffd6d1d6, 0xffd6d1d6, 0xffced2d6, 0xffceced0, 0xffceced0, 0xffcecacb, 0xffc5c6c5, + 0xffc3c2c3, 0xffc3c2c3, 0xffc0bec0, 0xffb5b2b5, 0xffadabad, 0xffa5a5a5, 0xff9c9e9c, 0xff8c8e8c, + 0x442f322f, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x55000000, 0x99424142, 0x99424142, 0x99424542, 0x994a4c4a, 0x99525252, 0x995a595a, + 0x995d5d5d, 0x995d5d5d, 0x99606160, 0x99636563, 0x99636563, 0x99656765, 0x99686868, 0x996b696b, + 0x996b6b6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996e7073, 0x996e7073, 0x996e7073, 0x99707373, + 0x99737473, 0x99737473, 0x99737573, 0x99737573, 0x99767776, 0x99767776, 0x99767776, 0x99767776, + 0x997b797b, 0x99767776, 0x997b797b, 0x997b797b, 0x997b7b7b, 0x997b7b7b, 0x997b7c7b, 0x997b7c7b, + 0x997e7f7e, 0x997b7d7b, 0x997e7f7e, 0x997e7f7e, 0x997b7d7b, 0x997e807e, 0x997e807e, 0x99818381, + 0x997e8084, 0x997e8084, 0x99818384, 0x99818384, 0x99848384, 0x99848384, 0x99848384, 0x99848484, + 0x99868686, 0x99898a89, 0x99848284, 0x99868686, 0x99848684, 0x99848684, 0x99848684, 0x99848484, + 0x99898484, 0x99898484, 0x99898484, 0x99868784, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99898789, 0x99898789, 0x99868486, 0x99898789, 0x99898789, 0x99868486, 0x99868486, 0x99868486, + 0x99848684, 0x99848684, 0x99848484, 0x99848484, 0x99848484, 0x99848384, 0x99848484, 0x99848384, + 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99848284, 0x99818081, 0x99818081, 0x99818081, + 0x99818081, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7c7b, 0x997b7c7b, + 0x997b7b7b, 0x997b7b7b, 0x997b7b7b, 0x997b797b, 0x99767876, 0x99767876, 0x99767876, 0x99767876, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737373, 0x99737373, 0x99737373, 0x99737073, + 0x99706d6e, 0x99706d6e, 0x996e6968, 0x996e6968, 0x99636563, 0x99606060, 0x99606060, 0x995d5a5d, + 0x99525152, 0x99525152, 0x99454345, 0x99373637, 0x77050805, 0x77000000, 0x55000000, 0x00000000, + 0x00000000, 0x00000000, 0x33373637, 0xffa5a2a5, 0xffa5a2a5, 0xffadaaad, 0xffb5b2b5, 0xffbdbabd, + 0xffc0bec0, 0xffc3c2c3, 0xffc3c2c3, 0xffc5c6c5, 0xffc5c6c5, 0xffc8c9c8, 0xffcbcccb, 0xffcbcccb, + 0xffcecece, 0xffcecece, 0xffd0ced0, 0xffd3ced3, 0xffd3d2d3, 0xffd3d2d3, 0xffd3d2d3, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedcde, 0xffdeddde, 0xffdeddde, 0xffdedfde, 0xffdedfde, + 0xffdee0e1, 0xffdedfde, 0xffdee0e1, 0xffdee0e1, 0xffe1e1e1, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e4e6, 0xffe6e4e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, + 0xffe6e5e6, 0xffe6e8e6, 0xffe6e5e6, 0xffe6e8e6, 0xffe5e8e5, 0xffe4e7e4, 0xffe3e7e4, 0xffe4e5e4, + 0xffe5e6e5, 0xffe5e6e5, 0xffe5e7e5, 0xffe5e8e6, 0xffe6e7e5, 0xffe6e7e6, 0xffe6e6e6, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e4e6, 0xffe6e4e6, 0xffe6e3e6, 0xffe6e4e5, 0xffe6e3e5, 0xffe6e1e5, 0xffe4e2e3, + 0xffe1e1e1, 0xffdfdfde, 0xffdedfde, 0xffdeddde, 0xffdeddde, 0xffdeddde, 0xffdedbde, 0xffdbdcdb, + 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd6d8d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d4d6, + 0xffd6d4d6, 0xffd6d4d6, 0xffd6d1d6, 0xffceced0, 0xffceced0, 0xffceced0, 0xffcecacb, 0xffc5c6c5, + 0xffc3c2c3, 0xffc3c2c3, 0xffbdbabd, 0xffb5b2b5, 0xffadabad, 0xffa5a5a5, 0xff9c9e9c, 0xee8c8e8c, + 0x332f322f, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x44000000, 0x99424142, 0x99424142, 0x99424542, 0x994a4c4a, 0x99525252, 0x995a595a, + 0x995d5d5d, 0x995d5d5d, 0x99606160, 0x99606160, 0x99636563, 0x99656765, 0x99686868, 0x996b696b, + 0x996b6b6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996e7073, 0x996e7073, 0x996e7073, 0x99707373, + 0x99737473, 0x99737573, 0x99737573, 0x99737573, 0x99767776, 0x99767776, 0x99797879, 0x99797879, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b7c7b, 0x997b7c7b, 0x997b7c7b, 0x997b7d7b, + 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997e807e, 0x99818381, 0x99818381, 0x99818381, + 0x99818384, 0x99818384, 0x99818384, 0x99818384, 0x99848384, 0x99848684, 0x99848684, 0x99848484, + 0x99868686, 0x99868686, 0x99868686, 0x99868686, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99868784, 0x99868784, 0x99868784, 0x99868784, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99898789, 0x99898789, 0x99898789, 0x99898789, 0x998c8a8c, 0x99898789, 0x99898789, 0x99898789, + 0x99848684, 0x99848684, 0x99848684, 0x99848484, 0x99848684, 0x99848484, 0x99848484, 0x99848384, + 0x99848484, 0x99848384, 0x99848384, 0x99848484, 0x99848284, 0x99848284, 0x99818081, 0x99848284, + 0x99818081, 0x99818081, 0x997e7f7e, 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7c7b, + 0x997b7d7b, 0x997b7b7b, 0x997b7b7b, 0x997b797b, 0x99797b79, 0x99797b79, 0x99767876, 0x99767876, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737373, 0x99737373, 0x99737373, 0x99737073, + 0x99706d6e, 0x99706d6e, 0x996e6968, 0x996b6563, 0x99636563, 0x99606060, 0x995d5a5d, 0x995a555a, + 0x99525152, 0x99454345, 0x99454345, 0x88292829, 0x77030403, 0x77000000, 0x44000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0xffa5a2a5, 0xffa5a2a5, 0xffadaaad, 0xffb5b2b5, 0xffbdbabd, + 0xffc0bec0, 0xffc3c2c3, 0xffc3c2c3, 0xffc3c2c3, 0xffc5c6c5, 0xffc8c9c8, 0xffc8c9c8, 0xffcbcccb, + 0xffcecece, 0xffcecece, 0xffd0ced0, 0xffd3ced3, 0xffd3d2d3, 0xffd3d2d3, 0xffd3d2d3, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6dbd6, 0xffd6dbd6, + 0xffdedbde, 0xffdedcde, 0xffdeddde, 0xffdeddde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdee0e1, 0xffdee0e1, 0xffdee1e4, 0xffdee1e4, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, + 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e5e6, + 0xffe6e5e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe8e9e7, 0xffebeae9, 0xffeeeaed, + 0xffe9e7e8, 0xffe9e8ea, 0xffe6e8e8, 0xffe6e8e6, 0xffe6e9e6, 0xffe6e8e6, 0xffe7e9e7, 0xffe7e7e5, + 0xffe6e6e5, 0xffe7e7e6, 0xffe6e7e6, 0xffe6e4e6, 0xffe6e6e6, 0xffe6e3e5, 0xffe5e3e5, 0xffe5e1e4, + 0xffe1e1e1, 0xffdfe1df, 0xffdee0de, 0xffdedfde, 0xffdeddde, 0xffdeddde, 0xffdedcde, 0xffdbdcdb, + 0xffdbdcdb, 0xffdbdcdb, 0xffd9d9d9, 0xffd6d9d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d7d6, 0xffd6d4d6, + 0xffd6d4d6, 0xffd6d4d6, 0xffd6d4d6, 0xffceced0, 0xffceced0, 0xffceced0, 0xffcecacb, 0xffc5c6c5, + 0xffc3c2c3, 0xffc0bec0, 0xffbdbabd, 0xffb5b2b5, 0xffadabad, 0xffa5a5a5, 0xff9c9e9c, 0xdd8c8e8c, + 0x22000400, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x44000000, 0x882c2b2c, 0x99424142, 0x99424542, 0x99424542, 0x994a4c4a, 0x995a595a, + 0x995a595a, 0x995d5d5d, 0x995d5d5d, 0x99606160, 0x99636563, 0x99656765, 0x996b696b, 0x996b696b, + 0x996b6b6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996e7073, 0x996e7073, 0x99707373, 0x99707373, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99767776, 0x99767776, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997e7f7e, 0x997e7f7e, 0x99818081, 0x99848284, 0x99818381, 0x99818381, 0x99818381, 0x99818381, + 0x99818384, 0x99818384, 0x99818384, 0x99818384, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99868686, 0x99868686, 0x99868686, 0x99868686, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99848a84, 0x99868784, 0x99868784, 0x99848a84, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x998c8a8c, 0x99898789, 0x99898789, 0x998c8a8c, 0x998c8a8c, 0x99898789, 0x99898789, 0x99898789, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99848684, 0x99848684, 0x99848484, 0x99848484, 0x99848284, 0x99848284, 0x99848284, 0x99848284, + 0x997e7f7e, 0x99818081, 0x997e7f7e, 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7d7b, 0x997b7d7b, 0x997b7c7b, 0x997b7b7b, 0x99797b79, 0x99797b79, 0x99797b79, 0x99767876, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737373, 0x99737373, 0x99737073, + 0x99706d6e, 0x996e6968, 0x996e6968, 0x996b6563, 0x99606060, 0x99606060, 0x995d5a5d, 0x995a555a, + 0x99525152, 0x99454345, 0x99454345, 0x88292829, 0x77030403, 0x77000000, 0x33000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0xdda5a2a5, 0xffa5a2a5, 0xffadaaad, 0xffb5b2b5, 0xffbdbabd, + 0xffbdbabd, 0xffc0bec0, 0xffc3c2c3, 0xffc3c2c3, 0xffc5c6c5, 0xffc8c9c8, 0xffcbcccb, 0xffcbcccb, + 0xffcecece, 0xffd0ced0, 0xffd0ced0, 0xffd0ced0, 0xffd3d2d3, 0xffd3d2d3, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6dbd6, 0xffd6dbd6, + 0xffdedcde, 0xffdeddde, 0xffdeddde, 0xffdeddde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdee0e1, 0xffdee1e4, 0xffdee3e6, 0xffdee3e6, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, 0xffe6e7e6, + 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe7e9e7, 0xffe8e8e8, + 0xffeaece9, 0xffe7e9e6, 0xffe6e9e6, 0xffe6ebe6, 0xffe6e9e6, 0xffe7e9e7, 0xffe9e9e9, 0xffe7e7e6, + 0xffe6e6e6, 0xffe6e7e7, 0xffe7e4e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e4e5, 0xffe5e3e5, 0xffe4e1e4, + 0xffe2e1e2, 0xffdfe0df, 0xffdee0de, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdeddde, 0xffdedfde, + 0xffdbdcdb, 0xffdbdcdb, 0xffdbdcdb, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d4d6, 0xffd6d1d6, 0xffceced0, 0xffceced0, 0xffcecacb, 0xffcec6c5, 0xffc3c2c3, + 0xffc3c2c3, 0xffc0bec0, 0xffbdbabd, 0xffb5b2b5, 0xffadabad, 0xff9c9e9c, 0xff9c9e9c, 0xbb5d605d, + 0x22000400, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x22000000, 0x77262826, 0x993a3d3a, 0x99424142, 0x99424142, 0x994d4c4d, 0x99525152, + 0x99525452, 0x995a5a5a, 0x99636163, 0x99636163, 0x99656565, 0x99656565, 0x996b696b, 0x996b696b, + 0x996b6c6e, 0x996b6c6e, 0x996b6f70, 0x996b6f70, 0x99737173, 0x99737173, 0x99737173, 0x99737473, + 0x99737576, 0x99737576, 0x99737576, 0x99737576, 0x99767876, 0x99797b79, 0x99797b79, 0x99797b79, + 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997e7c7e, 0x997b7d7b, 0x997b7d7b, 0x997e807e, 0x997e807e, + 0x99848084, 0x99848084, 0x99848384, 0x99848384, 0x99868486, 0x99868486, 0x99868486, 0x99868486, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99868786, 0x99868786, 0x99868786, 0x99848684, + 0x99868886, 0x99868886, 0x99868886, 0x99868886, 0x99868886, 0x99868886, 0x99868886, 0x99868886, + 0x998c888c, 0x998c888c, 0x998c888c, 0x998c888c, 0x99898a89, 0x99868686, 0x99898a89, 0x99898a89, + 0x998c888c, 0x998c888c, 0x998c888c, 0x998c8b8c, 0x99898b89, 0x99868886, 0x99868886, 0x99868886, + 0x99868786, 0x99868786, 0x99868786, 0x99868786, 0x99868786, 0x99848684, 0x99848684, 0x99868786, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848284, 0x99868686, 0x99848284, 0x99848284, + 0x99848384, 0x99848384, 0x99848284, 0x99848284, 0x997e807e, 0x997e807e, 0x997e807e, 0x997b7d7b, + 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7b7b, 0x997b7b7b, 0x997b797b, 0x997b797b, + 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99737573, 0x99707370, 0x99707370, 0x996e706e, + 0x996b6d6b, 0x99686968, 0x99656565, 0x99656565, 0x99636163, 0x99636163, 0x995d5c5d, 0x99585658, + 0x994a494a, 0x994a494a, 0x994a494a, 0x77191b19, 0x77000000, 0x77000000, 0x22000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0xaa736d73, 0xff9fa29f, 0xff9fa29f, 0xffb5b6b5, 0xffb5b6b5, + 0xffbdbabd, 0xffbdbabd, 0xffc5c2c5, 0xffc5c2c5, 0xffc8c6c8, 0xffc8c6c8, 0xffcecace, 0xffcecace, + 0xffd0cdd0, 0xffd0cdd0, 0xffd3d0d3, 0xffd3d0d3, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d4d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d8d6, 0xffd6d8d6, 0xffd6d9d6, 0xffdedbde, 0xffdedcde, 0xffdedcde, 0xffdedcde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffe1e1e1, 0xffe1e1e1, 0xffe1e1e1, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e4e6, 0xffe6e4e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e8e9, 0xffe6e8e9, 0xffe6e7e6, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe6e7e6, + 0xffefebe6, 0xffefebe6, 0xffefebe6, 0xffefebe6, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, + 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffedeaed, 0xffede9ed, + 0xffeae8e9, 0xffe5e7e9, 0xffe8e7e9, 0xffe7e7e6, 0xffe6e6e6, 0xffe6e6e5, 0xffe5e6e5, 0xffe3e4e3, + 0xffe3e3e3, 0xffe1e1e1, 0xffe1e1e1, 0xffe1e0e1, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedddb, + 0xffdedddb, 0xffdedcd9, 0xffdedcd9, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd6d7d6, + 0xffd6d7d6, 0xffd3d4d3, 0xffd0d1d0, 0xffcecece, 0xffcecece, 0xffc8cacb, 0xffc3c6c8, 0xffc5c2c5, + 0xffc5c2c5, 0xffbdbcbd, 0xffb5b5b5, 0xffadaead, 0xffadaead, 0xffadaead, 0xff8f908f, 0x774a4d4a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x66131413, 0x993a3d3a, 0x99424142, 0x99424142, 0x99474647, 0x994d4c4d, + 0x99525452, 0x995a5a5a, 0x995a5a5a, 0x99636163, 0x99656565, 0x99656565, 0x99656565, 0x996b696b, + 0x996b6c6e, 0x996b6c6e, 0x996b6f70, 0x996b6f70, 0x99737173, 0x99737173, 0x99737173, 0x99737373, + 0x99737573, 0x99737576, 0x99737576, 0x99737576, 0x99767876, 0x99767876, 0x99767876, 0x99797b79, + 0x997e7c7e, 0x997e7c7e, 0x99817f81, 0x99817f81, 0x997b7d7b, 0x997e807e, 0x997e807e, 0x997e807e, + 0x99848384, 0x99848384, 0x99848384, 0x99848384, 0x99868486, 0x99868486, 0x99868486, 0x99868486, + 0x99868786, 0x99868786, 0x99868786, 0x99868786, 0x99868786, 0x99898889, 0x99868786, 0x99868786, + 0x99868886, 0x99868886, 0x99898b89, 0x99898b89, 0x99868886, 0x99898b89, 0x99898b89, 0x99898b89, + 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x99898a89, 0x99898a89, 0x99898a89, 0x99898a89, + 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x99868886, 0x99898b89, 0x99868886, 0x99868886, + 0x99898889, 0x99898889, 0x99898889, 0x99868786, 0x99868786, 0x99868786, 0x99848684, 0x99868786, + 0x99848684, 0x99868786, 0x99898889, 0x99848684, 0x99868686, 0x99848284, 0x99868686, 0x99868686, + 0x99848384, 0x99848484, 0x99848284, 0x99848384, 0x99818381, 0x997e807e, 0x997e807e, 0x997e807e, + 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, 0x997b7c7b, 0x997b7b7b, 0x997b7b7b, + 0x997b797b, 0x99797879, 0x99767776, 0x99767776, 0x99737573, 0x99707370, 0x99707370, 0x996b6d6b, + 0x99686968, 0x99686968, 0x99656565, 0x99636163, 0x99636163, 0x995d5c5d, 0x99585658, 0x99585658, + 0x994a494a, 0x994a494a, 0x99313231, 0x77000400, 0x77000000, 0x66000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x554d494d, 0xff9fa29f, 0xff9fa29f, 0xff9fa29f, 0xffb5b6b5, + 0xffb5b2b5, 0xffbdbabd, 0xffbdbabd, 0xffc5c2c5, 0xffc8c6c8, 0xffc8c6c8, 0xffc8c6c8, 0xffcecace, + 0xffd0cdd0, 0xffd0cdd0, 0xffd3d0d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d4d6, 0xffd6d5d6, + 0xffd6d7d6, 0xffd6d9d6, 0xffd6d9d6, 0xffd6d9d6, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedcde, + 0xffdedfde, 0xffdedfde, 0xffdee0de, 0xffdee0de, 0xffe1e1e1, 0xffe1e1e1, 0xffe1e1e1, 0xffe1e1e1, + 0xffe6e5e6, 0xffe6e4e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, + 0xffe6e9ec, 0xffe6e8e9, 0xffe6e9ec, 0xffe6e9ec, 0xffe9e9e9, 0xffececec, 0xffe9e9e9, 0xffe9e9e9, + 0xffefece9, 0xffefebe6, 0xffefece9, 0xffefece9, 0xffefebef, 0xffefecef, 0xffefecef, 0xffefecef, + 0xffefecef, 0xffefecef, 0xffefecef, 0xffefecef, 0xffefebef, 0xffeeecef, 0xffeeeced, 0xffede9ed, + 0xffede9ed, 0xffede7ec, 0xffece7ec, 0xffeae7ea, 0xffe7e7e7, 0xffe6e6e6, 0xffe5e6e5, 0xffe3e5e3, + 0xffe3e4e3, 0xffe4e4e4, 0xffe1e1e1, 0xffe1e0e1, 0xffe1e0e1, 0xffe1e0e1, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedddb, 0xffdedddb, 0xffdbdcdb, 0xffdbdcdb, 0xffd9d9d9, 0xffd9d9d9, 0xffd6d7d6, + 0xffd3d4d3, 0xffd3d4d3, 0xffd0d1d0, 0xffcecece, 0xffcecece, 0xffc8cacb, 0xffc3c6c8, 0xffc5c2c5, + 0xffbdbcbd, 0xffbdbcbd, 0xffb5b5b5, 0xffadaead, 0xffadaead, 0xffadaead, 0xff8f908f, 0x44313331, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x55000000, 0x993a3d3a, 0x99424142, 0x99424142, 0x99424142, 0x994d4c4d, + 0x99525452, 0x995a5a5a, 0x995a5a5a, 0x995a5a5a, 0x99606160, 0x99606160, 0x99656565, 0x996b696b, + 0x996b696b, 0x996b6c6e, 0x996b6f70, 0x996b6f70, 0x99737173, 0x99737173, 0x99737373, 0x99737373, + 0x99737573, 0x99737576, 0x99737576, 0x99737579, 0x99767876, 0x99767876, 0x99797b79, 0x997b7d7b, + 0x99817f81, 0x997e7c7e, 0x997e7c7e, 0x99817f81, 0x997e807e, 0x997e807e, 0x99818381, 0x99818381, + 0x99848384, 0x99848384, 0x99848384, 0x99848384, 0x99868486, 0x99898789, 0x99868486, 0x99898789, + 0x99868786, 0x99868786, 0x99868786, 0x99868786, 0x99898889, 0x99898889, 0x998c8a8c, 0x99898889, + 0x99898b89, 0x99898b89, 0x99898b89, 0x99898b89, 0x99898b89, 0x99898b89, 0x99898b89, 0x99898b89, + 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x998c8e8c, 0x998c8e8c, 0x99898a89, 0x998c8e8c, 0x99898a89, + 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x99898b89, 0x99898b89, 0x99898b89, 0x99868886, + 0x998c8a8c, 0x998c8a8c, 0x99898889, 0x99868786, 0x998c8a8c, 0x99898889, 0x99868786, 0x99868786, + 0x99868786, 0x99898889, 0x998c8a8c, 0x99868786, 0x99868686, 0x99868686, 0x99868686, 0x99868686, + 0x99848484, 0x99848484, 0x99848484, 0x99848384, 0x99818381, 0x997e807e, 0x997e807e, 0x997e807e, + 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7b7b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x99767776, 0x99767776, 0x99737573, 0x99707370, 0x996e706e, 0x996b6d6b, + 0x99686968, 0x99686968, 0x99656565, 0x99636163, 0x99636163, 0x995d5c5d, 0x99585658, 0x99525152, + 0x994a494a, 0x994a494a, 0x88313231, 0x77000400, 0x77000000, 0x55000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x22262426, 0xee9fa29f, 0xff9fa29f, 0xff9fa29f, 0xff9fa29f, + 0xffb5b2b5, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffc3c2c3, 0xffc3c2c3, 0xffc8c6c8, 0xffcecace, + 0xffcecace, 0xffd0cdd0, 0xffd3d0d3, 0xffd3d0d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d5d6, 0xffd6d5d6, + 0xffd6d8d6, 0xffd6d7d6, 0xffd6d9d6, 0xffd6d9d6, 0xffdedbde, 0xffdedbde, 0xffdedcde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdee0de, 0xffe1e1e1, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, + 0xffe6e4e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e7e6, 0xffe9e8e9, 0xffe6e7e6, 0xffe9e8e9, + 0xffe6e9ec, 0xffe6e9ec, 0xffe6e9ec, 0xffe6e9ec, 0xffececec, 0xffececec, 0xffececec, 0xffececec, + 0xffefedec, 0xffefece9, 0xffefece9, 0xffefece9, 0xffefecef, 0xffefecef, 0xffefedef, 0xffefecef, + 0xffefedef, 0xffefedef, 0xffefedef, 0xffefefef, 0xffefedef, 0xffefedef, 0xffeeecee, 0xffeee9ee, + 0xffede9ed, 0xffedeaec, 0xffeceaec, 0xffe9eae9, 0xffe8e7e8, 0xffe7e7e7, 0xffe7e5e7, 0xffe4e4e4, + 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e1e4, 0xffe4e1e4, 0xffe1e0e1, 0xffe1e0e1, 0xffdedfde, + 0xffdedfde, 0xffdedddb, 0xffdedcd9, 0xffdbdcdb, 0xffdbdcdb, 0xffd9d9d9, 0xffd9d9d9, 0xffd6d7d6, + 0xffd3d4d3, 0xffd0d1d0, 0xffd0d1d0, 0xffcecece, 0xffc8cacb, 0xffc3c6c8, 0xffbdc2c5, 0xffc5c2c5, + 0xffbdbcbd, 0xffb5b5b5, 0xffb5b5b5, 0xffadaead, 0xffadaead, 0xff8f908f, 0xbb707370, 0x11191a19, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x33000000, 0x77131413, 0x99424142, 0x99424142, 0x99424142, 0x99424142, + 0x994a4d4a, 0x99525452, 0x99525452, 0x995a5a5a, 0x995a5d5a, 0x99606160, 0x99656565, 0x99656565, + 0x996b696b, 0x996b6c6e, 0x996b6c6e, 0x996b6f70, 0x99737173, 0x99737173, 0x99737373, 0x99737573, + 0x99737576, 0x99737576, 0x99737576, 0x99737579, 0x99767876, 0x99797b79, 0x997b7d7b, 0x997b7d7b, + 0x99817f81, 0x997e7c7e, 0x99817f81, 0x99848284, 0x997e807e, 0x99818381, 0x99818381, 0x99818381, + 0x99848384, 0x99848684, 0x99848684, 0x99848684, 0x99898789, 0x99898789, 0x99898789, 0x998c8a8c, + 0x99898889, 0x99868786, 0x99898889, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, + 0x99898b89, 0x99898b89, 0x99898b89, 0x998c8e8c, 0x99898b89, 0x998c8e8c, 0x99898b89, 0x998c8e8c, + 0x998c8b8c, 0x998c8e8c, 0x998c8b8c, 0x998c8b8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, + 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x998c8b8c, 0x99898b89, 0x998c8e8c, 0x99898b89, 0x99898b89, + 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x99898889, 0x99898889, + 0x99898889, 0x99868786, 0x99868786, 0x99868786, 0x99898a89, 0x99868686, 0x99868686, 0x99868686, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99818381, 0x99818381, 0x99818381, 0x997e807e, + 0x99848284, 0x997e7f7e, 0x99818081, 0x997e7f7e, 0x997b7d7b, 0x997b7d7b, 0x997b7c7b, 0x997b7c7b, + 0x997b797b, 0x99797879, 0x99767776, 0x99767776, 0x99737573, 0x996e706e, 0x996b6d6b, 0x996b6d6b, + 0x99686968, 0x99656565, 0x99636163, 0x99636163, 0x995d5c5d, 0x99585658, 0x99585658, 0x99525152, + 0x994a494a, 0x994a494a, 0x77191b19, 0x77000400, 0x77000000, 0x33000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x99737973, 0xff9fa29f, 0xff9fa29f, 0xff9fa29f, + 0xffadaaad, 0xffb5b2b5, 0xffbdbabd, 0xffbdbabd, 0xffbdbebd, 0xffc3c2c3, 0xffc8c6c8, 0xffc8c6c8, + 0xffcecace, 0xffd0cdd0, 0xffd0cdd0, 0xffd3d0d3, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d5d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d8d6, 0xffd6d9d6, 0xffd6d9d6, 0xffdedbde, 0xffdeddde, 0xffdedfde, 0xffdedfde, + 0xffdee1de, 0xffdedfde, 0xffdee0de, 0xffdee3de, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, 0xffe6e7e6, + 0xffe6e5e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe9e8e9, 0xffe9e8e9, 0xffe9e8e9, 0xffefebef, + 0xffe6ebef, 0xffe6e9ec, 0xffe6ebef, 0xffe6ebef, 0xffececec, 0xffececec, 0xffececec, 0xffececec, + 0xffefedec, 0xffefedec, 0xffefefef, 0xffefefef, 0xffefedef, 0xffefefef, 0xffefedef, 0xffefefef, + 0xffefedef, 0xffefefef, 0xffefedef, 0xffefedef, 0xffefedef, 0xffefedef, 0xffeeedef, 0xffeeeded, + 0xffeeebed, 0xffece9eb, 0xffeaeaea, 0xffe8e9e8, 0xffe8e9e8, 0xffe8e9e8, 0xffe6e7e7, 0xffe6e7e6, + 0xffe6e7e6, 0xffe4e4e4, 0xffe4e4e4, 0xffe6e3e6, 0xffe4e1e4, 0xffe6e3e6, 0xffe1e0e1, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdbdcdb, 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffd6d7d6, + 0xffd3d4d3, 0xffd0d1d0, 0xffcecece, 0xffc8cacb, 0xffc3c6c8, 0xffc3c6c8, 0xffbdc2c5, 0xffbdbcbd, + 0xffbdbcbd, 0xffb5b5b5, 0xffadaead, 0xffadaead, 0xffadaead, 0xff8f908f, 0x66525552, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x55080408, 0x882c2b2c, 0x99424142, 0x99424142, 0x99424142, + 0x99424142, 0x994d4e4d, 0x99525552, 0x99525552, 0x995a5a5d, 0x99636163, 0x99636163, 0x99636163, + 0x9968686e, 0x9968686e, 0x996b6d73, 0x996b6d73, 0x99736d6b, 0x9973706e, 0x99737370, 0x99737573, + 0x99737573, 0x99767776, 0x99767776, 0x997b797b, 0x997b797b, 0x997b797b, 0x997e7c7e, 0x997e7c7e, + 0x997b7d7b, 0x997b7d7b, 0x997e807e, 0x99818381, 0x99848284, 0x99848284, 0x99848284, 0x99848284, + 0x99848684, 0x99848684, 0x99848684, 0x99868786, 0x998c8886, 0x998c8886, 0x998c8886, 0x998c8b89, + 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998f8c8f, 0x998f8c8f, 0x998c8a8c, 0x998c8a8c, + 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, + 0x998f908f, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, + 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, + 0x998f8c8f, 0x998c8a8c, 0x998f8c8f, 0x998c8a8c, 0x998c8e8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, + 0x9986888c, 0x9986888c, 0x9986888c, 0x9986888c, 0x998c8886, 0x998c8886, 0x998c8886, 0x998c8886, + 0x99868786, 0x99868786, 0x99848684, 0x99848684, 0x99848684, 0x99848484, 0x99848484, 0x99848384, + 0x99818381, 0x997e807e, 0x997e807e, 0x997e807e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x99797b79, + 0x9973797b, 0x9973797b, 0x99737779, 0x99737476, 0x99737173, 0x99737173, 0x996e6d6e, 0x99686968, + 0x9963656b, 0x9963656b, 0x99606065, 0x99606065, 0x995a5d5a, 0x995a5d5a, 0x994a4c4a, 0x994a4c4a, + 0x994a494a, 0x88343234, 0x77080408, 0x77080408, 0x66000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22000400, 0xdda5a2a5, 0xffa5a2a5, 0xffa5a2a5, + 0xffaaa9aa, 0xffafafaf, 0xffb5b6b5, 0xffb5b6b5, 0xffbdbcbd, 0xffc5c2c5, 0xffc5c2c5, 0xffc5c2c5, + 0xffc8cacb, 0xffcbced0, 0xffcbced0, 0xffcbced0, 0xffd6d1d0, 0xffd6d4d3, 0xffd6d4d3, 0xffd6d7d6, + 0xffd6d7d6, 0xffd9d9d9, 0xffd9d9d9, 0xffdbdcdb, 0xffdeddde, 0xffdeddde, 0xffdeddde, 0xffdeddde, + 0xffdedfde, 0xffe1e1e1, 0xffe1e1e1, 0xffe4e4e4, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e5e6, 0xffe6e5e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe9e9e9, 0xffefebe6, 0xffefebe6, 0xffefebe6, 0xffefece9, + 0xffefebef, 0xffefebef, 0xffefebef, 0xffefedf1, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xfff1f2f1, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xfff0efef, 0xfff3f2f2, 0xfff1efef, + 0xfff1eeef, 0xffeeebec, 0xffeeebee, 0xffebe9ea, 0xffe9e9e9, 0xffe6e7e7, 0xffe6e7e6, 0xffe6e8e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe4e4e4, 0xffe4e4e4, 0xffe1e1e1, 0xffe1e1e1, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdbdddb, 0xffd6dbde, 0xffd6dbde, 0xffd6d8db, 0xffd6d5d9, 0xffd6d7de, + 0xffd0d1d6, 0xffd0d1d6, 0xffcbccce, 0xffc5c6c5, 0xffc5c6c5, 0xffc0c2c0, 0xffc0c2c0, 0xffbdbebd, + 0xffb5b5b5, 0xffb5b5b5, 0xffadabad, 0xffa5a6a5, 0xffa5a6a5, 0xcc707170, 0x11080808, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x33000000, 0x66161616, 0x99424142, 0x99424142, 0x99424142, + 0x99424142, 0x99474847, 0x994d4e4d, 0x99525552, 0x995a5a5d, 0x995a5a5d, 0x99636163, 0x99636163, + 0x9968686e, 0x9968686e, 0x9968686e, 0x996b6d73, 0x99736d6b, 0x99737370, 0x99737573, 0x99737573, + 0x99767776, 0x99767776, 0x99767776, 0x997b797b, 0x997e7c7e, 0x99817f81, 0x997e7c7e, 0x99817f81, + 0x997e807e, 0x997e807e, 0x997e807e, 0x997e807e, 0x99848284, 0x99848686, 0x99848686, 0x99848686, + 0x99848684, 0x99868786, 0x99868786, 0x99868786, 0x998c8886, 0x998c8886, 0x998c8b89, 0x998c8b89, + 0x998c8c8f, 0x998c8c8f, 0x998c8a8c, 0x998c8c8f, 0x998f8c8f, 0x99918f91, 0x998f8c8f, 0x99918f91, + 0x998f8f8f, 0x998f8f8f, 0x998f8f8f, 0x998f8f8f, 0x998f908f, 0x998f908f, 0x998f908f, 0x998f908f, + 0x998f908f, 0x998f908f, 0x998f908f, 0x998f908f, 0x998f908f, 0x998f908f, 0x998f908f, 0x998f908f, + 0x998f908f, 0x998f908f, 0x998c8e8c, 0x998f908f, 0x998c8e8c, 0x998f908f, 0x998f908f, 0x998c8e8c, + 0x99918f91, 0x998f8c8f, 0x998f8c8f, 0x998f8c8f, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8a8c, + 0x99898b8c, 0x99898b8c, 0x99898b8c, 0x99898b8c, 0x998c8b89, 0x998c8886, 0x998c8b89, 0x998c8886, + 0x99898889, 0x99868786, 0x99868786, 0x99868786, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99818381, 0x99818381, 0x99818381, 0x997e807e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x99797b79, + 0x9973797b, 0x99737779, 0x99737779, 0x99737476, 0x99737173, 0x996e6d6e, 0x99686968, 0x99686968, + 0x9963656b, 0x9963656b, 0x99606065, 0x995d5a60, 0x995a5d5a, 0x995a5d5a, 0x994a4c4a, 0x994a4c4a, + 0x99343234, 0x771e1b1e, 0x77080408, 0x77080408, 0x33000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0x55373937, 0xeea5a2a5, 0xffa5a2a5, + 0xffa5a2a5, 0xffaaa9aa, 0xffafafaf, 0xffb5b6b5, 0xffbdbcbd, 0xffbdbcbd, 0xffc5c2c5, 0xffc5c2c5, + 0xffc8cacb, 0xffc8cacb, 0xffc8cacb, 0xffced2d6, 0xffd6d1d0, 0xffd6d4d3, 0xffd6d7d6, 0xffd6d7d6, + 0xffd9d9d9, 0xffd9d9d9, 0xffd9d9d9, 0xffdbdcdb, 0xffdeddde, 0xffdee0de, 0xffdeddde, 0xffdee0de, + 0xffe1e1e1, 0xffe1e1e1, 0xffe4e4e4, 0xffe4e4e4, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e7e6, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffefebe6, 0xffefebe6, 0xffefece9, 0xffefece9, + 0xffefedf1, 0xffefedf1, 0xffefedf1, 0xffefedf1, 0xffefefef, 0xfff1f0f1, 0xffefefef, 0xfff1f0f1, + 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, + 0xfff4f4f4, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, 0xfff4f4f4, 0xfff1f2f1, 0xfff2f2f1, 0xfff1f0f0, + 0xfff1efef, 0xffefeded, 0xffede9ed, 0xffece9ec, 0xffeae9ea, 0xffe9e9e9, 0xffe9e9e9, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdbdddb, 0xffd6dbde, 0xffd6d8db, 0xffd6d8db, 0xffd6d5d9, 0xffd0d1d6, + 0xffd0d1d6, 0xffcbccce, 0xffcbccce, 0xffc5c6c5, 0xffc5c6c5, 0xffc0c2c0, 0xffbabeba, 0xffbdbebd, + 0xffb5b5b5, 0xffb5b5b5, 0xffadabad, 0xffa5a6a5, 0xdda5a6a5, 0x443c3d3c, 0x00080808, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x55000000, 0x77161616, 0x99424142, 0x99424142, + 0x99424142, 0x99424142, 0x99474847, 0x994d4e4d, 0x99525458, 0x995a5a5d, 0x99636163, 0x99636163, + 0x99656268, 0x9968686e, 0x9968686e, 0x996b6d73, 0x9973706e, 0x99737370, 0x99737573, 0x99737573, + 0x99767776, 0x99767776, 0x997b797b, 0x997b797b, 0x99817f81, 0x99817f81, 0x99817f81, 0x99817f81, + 0x997e807e, 0x997e807e, 0x99818381, 0x99818381, 0x99848686, 0x99848686, 0x99848686, 0x99848686, + 0x99868786, 0x99868786, 0x998c8a8c, 0x998c8a8c, 0x998c8b89, 0x998c8b89, 0x998c8b89, 0x998c8b89, + 0x998c8c8f, 0x998c8c8f, 0x998c8c8f, 0x998c8f91, 0x99918f91, 0x99918f91, 0x99949294, 0x99949294, + 0x99919091, 0x99919091, 0x998f8f8f, 0x99919091, 0x998f908f, 0x99919391, 0x998f908f, 0x99919391, + 0x998f908f, 0x998f908f, 0x99919391, 0x998f908f, 0x998f908f, 0x998f908f, 0x99919391, 0x998f908f, + 0x998f908f, 0x998f908f, 0x99919391, 0x998f908f, 0x998f908f, 0x998f908f, 0x998f908f, 0x998f908f, + 0x99918f91, 0x99918f91, 0x99918f91, 0x99918f91, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, + 0x99898b8c, 0x99898b8c, 0x99898b8c, 0x99898b8c, 0x998c8b89, 0x998c8b89, 0x998c8b89, 0x998c8886, + 0x998c8a8c, 0x99868786, 0x99868786, 0x99868786, 0x99848684, 0x99848684, 0x99848684, 0x99848484, + 0x99818381, 0x99818381, 0x99818381, 0x99818381, 0x997b7d7b, 0x997b7d7b, 0x99797b79, 0x99797b79, + 0x99737779, 0x99737779, 0x99737476, 0x99737173, 0x99737173, 0x996e6d6e, 0x99686968, 0x99636563, + 0x9963656b, 0x99606065, 0x99606065, 0x995d5a60, 0x995a5d5a, 0x994a4c4a, 0x994a4c4a, 0x994a4c4a, + 0x771e1b1e, 0x77080408, 0x77080408, 0x55080408, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0x00000400, 0x886e6d6e, 0xffa5a2a5, + 0xffa5a2a5, 0xffa5a2a5, 0xffaaa9aa, 0xffafafaf, 0xffb5b5b5, 0xffbdbcbd, 0xffc5c2c5, 0xffc5c2c5, + 0xffc5c6c5, 0xffc8cacb, 0xffc8cacb, 0xffcbced0, 0xffd6d1d0, 0xffd6d4d3, 0xffd6d7d6, 0xffd6d7d6, + 0xffd9d9d9, 0xffd9d9d9, 0xffdbdcdb, 0xffdbdcdb, 0xffdee0de, 0xffdee0de, 0xffdee0de, 0xffdee0de, + 0xffe1e1e1, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, 0xffe6e5e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe9e9e9, 0xffe9e9e9, 0xffececec, 0xffececec, 0xffefedec, 0xffefece9, 0xffefedec, 0xffefedec, + 0xffefedf1, 0xffefedf1, 0xffefedf1, 0xffeff0f4, 0xfff1f0f1, 0xfff1f0f1, 0xfff4f2f4, 0xfff4f2f4, + 0xfff1f2f1, 0xfff4f4f4, 0xfff1f2f1, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, + 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff2f1f1, + 0xfff0edee, 0xffeceae9, 0xffeae8e7, 0xffeae7ea, 0xffe8e6e8, 0xffeae9ea, 0xffe9e9e9, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe4e4e4, 0xffe4e4e4, 0xffe4e4e4, 0xffdedfde, + 0xffdedfde, 0xffdbdddb, 0xffdbdddb, 0xffd6d8db, 0xffd6d8db, 0xffd6d5d9, 0xffd6d2d6, 0xffd0d1d6, + 0xffcbccce, 0xffcbccce, 0xffc5c6c5, 0xffc5c6c5, 0xffc0c2c0, 0xffbabeba, 0xffbabeba, 0xffb5b5b5, + 0xffb5b5b5, 0xffadabad, 0xffadabad, 0xeea5a6a5, 0x773c3d3c, 0x00080808, 0x00080808, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x55000000, 0x77161616, 0x99424142, + 0x99424142, 0x99424142, 0x99424142, 0x99474847, 0x994a4d52, 0x99525458, 0x995a5a5d, 0x99636163, + 0x99656268, 0x99656268, 0x9968686e, 0x9968686e, 0x99736d6b, 0x9973706e, 0x99737370, 0x99737573, + 0x99737573, 0x99767776, 0x99797879, 0x997b797b, 0x997e7c7e, 0x997e7c7e, 0x99817f81, 0x99848284, + 0x99818381, 0x99818381, 0x99818381, 0x99848684, 0x99848686, 0x99848686, 0x99848686, 0x99848a89, + 0x99898889, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8b89, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, + 0x998c8f91, 0x998c8f91, 0x998c8f91, 0x998c9294, 0x99949294, 0x99949294, 0x99949294, 0x99949294, + 0x99949294, 0x99949294, 0x99949294, 0x99949294, 0x99919391, 0x99919391, 0x99919391, 0x99919391, + 0x99919391, 0x99919391, 0x99919391, 0x99919391, 0x99919391, 0x99919391, 0x99919391, 0x99919391, + 0x99919391, 0x99919391, 0x99919391, 0x99919391, 0x99919391, 0x99919391, 0x99919391, 0x998f908f, + 0x99949294, 0x99949294, 0x99949294, 0x99949294, 0x998c928c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, + 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8b89, 0x998c8b89, 0x998c8b89, 0x998c8b89, + 0x998c8a8c, 0x998c8a8c, 0x99868786, 0x99868786, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99818381, 0x99818381, 0x997e807e, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x99797b79, 0x99767876, + 0x99737476, 0x99737476, 0x99737173, 0x99737173, 0x996e6d6e, 0x99686968, 0x99686968, 0x99636563, + 0x99606065, 0x99606065, 0x995d5a60, 0x995a555a, 0x994a4c4a, 0x994a4c4a, 0x994a4c4a, 0x77292829, + 0x77080408, 0x77080408, 0x66080408, 0x11080408, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0x00000400, 0x00000400, 0x996e6d6e, + 0xeea5a2a5, 0xffa5a2a5, 0xffa5a2a5, 0xffaaa9aa, 0xffadaead, 0xffb5b5b5, 0xffbdbcbd, 0xffc5c2c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc8cacb, 0xffcbced0, 0xffd6d1d0, 0xffd6d1d0, 0xffd6d4d3, 0xffd6d7d6, + 0xffd6d7d6, 0xffd9d9d9, 0xffdbdcdb, 0xffdbdcdb, 0xffdeddde, 0xffdeddde, 0xffdee0de, 0xffdee3de, + 0xffe4e4e4, 0xffe6e7e6, 0xffe4e4e4, 0xffe6e7e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6ebe6, + 0xffececec, 0xffececec, 0xffececec, 0xffececec, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffeff0f4, 0xffeff0f4, 0xffeff0f4, 0xffeff3f7, 0xfff7f3f7, 0xfff7f3f7, 0xfff7f3f7, 0xfff7f3f7, + 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff7f7f7, 0xfff4f4f4, 0xfff4f4f4, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff5f5f4, + 0xffefeeeb, 0xffebe8e8, 0xffe8e5e8, 0xffe7e4e8, 0xffe8e5e8, 0xffeae8ea, 0xffe9e9e9, 0xffe6e9e6, + 0xffe6e9e6, 0xffe6e7e6, 0xffe6e8e6, 0xffe6e7e6, 0xffe4e4e4, 0xffe4e4e4, 0xffe1e1e1, 0xffdedfde, + 0xffdedfde, 0xffdbdddb, 0xffd6dbd6, 0xffd6d8db, 0xffd6d5d9, 0xffd6d2d6, 0xffd6d2d6, 0xffcbccce, + 0xffcbccce, 0xffcbccce, 0xffc5c6c5, 0xffc0c2c0, 0xffc0c2c0, 0xffbabeba, 0xffb5bab5, 0xffb5b5b5, + 0xffb5b5b5, 0xffadabad, 0xeea5a2a5, 0x773c3d3c, 0x11080808, 0x00080808, 0x00080808, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22000000, 0x55000000, 0x77191419, + 0x882f2d2f, 0x99424142, 0x99424142, 0x99424142, 0x993c3b3c, 0x99525152, 0x99525152, 0x99525152, + 0x99636163, 0x99636163, 0x99636163, 0x99636163, 0x99636565, 0x996b7173, 0x996b7173, 0x996b7173, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, + 0x99868886, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998f8f8f, 0x998f8f8f, 0x998f8f8f, 0x998f8f8f, + 0x99949094, 0x99949094, 0x99949094, 0x999c969c, 0x99949694, 0x99949694, 0x99949694, 0x99949694, + 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, + 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, + 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x998f9091, + 0x99949294, 0x99949294, 0x99949294, 0x99949294, 0x998f8c8f, 0x99949294, 0x99949294, 0x99949294, + 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, + 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7973, 0x997b7973, 0x997b7973, 0x997b7973, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x99636563, 0x99636563, 0x99636563, 0x99636563, + 0x99525552, 0x99525552, 0x99525552, 0x99525552, 0x99525152, 0x88373637, 0x771b1b1b, 0x77000000, + 0x77000305, 0x66000000, 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x77686968, 0xdd9c9e9c, 0xff9c9e9c, 0xff9c9e9c, 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffadaaad, + 0xffb8b9b8, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd9dbde, 0xffdee3e6, 0xffdee3e6, 0xffdee3e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, + 0xffe9e9e9, 0xffefefef, 0xffefefef, 0xffefefef, 0xfff1f0ef, 0xfff1f0ef, 0xfff1f0ef, 0xfff1f0ef, + 0xfff1f3f1, 0xfff1f3f1, 0xfff1f3f1, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff6f6f6, + 0xffefefef, 0xffeaeae9, 0xffe6e7e7, 0xffe5e4e5, 0xffe5e3e6, 0xffece9ed, 0xffefebef, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffc8c9c8, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xff9c9e9c, + 0xff9c9e9c, 0xcc9c9e9c, 0x55343534, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22000000, 0x55000000, + 0x66080408, 0x771b181b, 0x99424142, 0x99424142, 0x993c3b3c, 0x993c3b3c, 0x99525152, 0x99525152, + 0x99555555, 0x99555555, 0x99636163, 0x99636163, 0x99636565, 0x99636565, 0x996b7173, 0x996b7173, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848384, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, + 0x998c8e8c, 0x99868886, 0x998c8e8c, 0x998c8e8c, 0x998f8f8f, 0x99949694, 0x998f8f8f, 0x998f8f8f, + 0x99949094, 0x99949094, 0x99949094, 0x99949094, 0x99949694, 0x99949694, 0x99949694, 0x99949694, + 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, + 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, + 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x998f9091, + 0x99949294, 0x99949294, 0x99949294, 0x99949294, 0x99949294, 0x99949294, 0x998f8c8f, 0x99949294, + 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x99868886, + 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x99848384, 0x99848684, 0x99848684, 0x997e7f7e, 0x997e7f7e, + 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x99767576, 0x997b7973, 0x997b7973, 0x9973706e, 0x9973706e, + 0x99737173, 0x99737173, 0x99656465, 0x99656465, 0x99636563, 0x99636563, 0x99636563, 0x99505150, + 0x99525552, 0x99525552, 0x99525552, 0x993a3b3a, 0x771b1b1b, 0x66000000, 0x77000000, 0x77000000, + 0x66000000, 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x33343534, 0x99686968, 0xee9c9e9c, 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffadaaad, + 0xffb8b9b8, 0xffb8b9b8, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c8c3, 0xffc5c8c3, 0xffced2ce, 0xffced2ce, + 0xffd0d1d0, 0xffd0d1d0, 0xffd6dbd6, 0xffd6dbd6, 0xffd9dbde, 0xffd9dbde, 0xffdee3e6, 0xffdee3e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e5e6, 0xffefebef, 0xffefebef, 0xffefebef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xfff1f0ef, 0xfff7f7f7, 0xfff1f0ef, 0xfff1f0ef, + 0xfff1f3f1, 0xfff1f3f1, 0xfff1f3f1, 0xfff1f3f1, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff6f7f6, + 0xfff2f1f1, 0xffebeaea, 0xffe4e5e5, 0xffe3e1e4, 0xffe6e4e7, 0xffedeaed, 0xffefebef, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffced0ce, 0xffd6d7d6, 0xffc8c9c8, 0xffc8c9c8, 0xffc8c9c8, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffb8b7b8, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xdd9c9e9c, + 0x88686968, 0x33343534, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, + 0x44080408, 0x66080408, 0x66080408, 0x771b181b, 0x993c3b3c, 0x993c3b3c, 0x993c3b3c, 0x993c3b3c, + 0x99474947, 0x99555555, 0x99555555, 0x99555555, 0x995a5958, 0x99636565, 0x99636565, 0x99636565, + 0x99686868, 0x996e6f6e, 0x996e6f6e, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x997e7f7e, 0x99848384, 0x99848384, 0x99848384, 0x99848384, + 0x99868886, 0x99868886, 0x99868886, 0x99868886, 0x998f8f8f, 0x99898889, 0x998f8f8f, 0x998f8f8f, + 0x99949094, 0x998c8b8c, 0x99949094, 0x99949094, 0x998f908f, 0x99949694, 0x998f908f, 0x99949694, + 0x998f908f, 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99919291, 0x99919291, 0x99919291, + 0x99949694, 0x99949694, 0x99949694, 0x99949694, 0x99919291, 0x99919291, 0x99919291, 0x99919291, + 0x99949694, 0x9991908f, 0x9991908f, 0x9991908f, 0x998f9091, 0x998f9091, 0x998f9091, 0x998f9091, + 0x998f8e8f, 0x998f8e8f, 0x998f8e8f, 0x99949294, 0x99949294, 0x998f8c8f, 0x998f8c8f, 0x998f8c8f, + 0x998c8e8c, 0x998c8e8c, 0x998c8e8c, 0x99868886, 0x99868886, 0x99868886, 0x99868886, 0x99818381, + 0x99848384, 0x99848384, 0x99848384, 0x99848384, 0x997e7f7e, 0x997e7f7e, 0x99797879, 0x99797879, + 0x99767576, 0x99767576, 0x99767576, 0x99767576, 0x9973706e, 0x9973706e, 0x996b6768, 0x996b6768, + 0x99656465, 0x99656465, 0x99656465, 0x99585658, 0x99505150, 0x99505150, 0x99505150, 0x99505150, + 0x993a3b3a, 0x993a3b3a, 0x77212221, 0x66080808, 0x77000000, 0x77000000, 0x77000000, 0x44000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x44343534, 0xaa7b797b, 0xeeadaaad, 0xffadaaad, 0xffadaaad, + 0xffaaabaa, 0xffaaabaa, 0xffb8b9b8, 0xffb8b9b8, 0xffbdbdb8, 0xffc5c8c3, 0xffc5c8c3, 0xffc5c8c3, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd3d2d6, 0xffd9dbde, 0xffd9dbde, 0xffd9dbde, + 0xffe1e0e1, 0xffe1e0e1, 0xffe1e0e1, 0xffe6e7e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, 0xffe6e5e6, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xfff1f0ef, 0xfff1f0ef, 0xfff1f0ef, 0xfff1f0ef, + 0xfff1f3f1, 0xffecefec, 0xfff1f3f1, 0xfff1f3f1, 0xfff1f3f1, 0xfff7f7f7, 0xfff1f3f1, 0xfff7f7f7, + 0xfff4f3f4, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff4f3f4, 0xfff7f7f7, 0xfff4f3f4, + 0xfff5f5f4, 0xffeeedec, 0xffe4e4e5, 0xffe1e1e2, 0xffe3e1e3, 0xffe5e4e6, 0xffe6e4e6, 0xffe1dfde, + 0xffe1dfde, 0xffe1dfde, 0xffe1dfde, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffced0ce, + 0xffced0ce, 0xffced0ce, 0xffc5c5c5, 0xffc8c9c8, 0xffc8c9c8, 0xffbabcba, 0xffbabcba, 0xffb8b7b8, + 0xffb8b7b8, 0xffb8b7b8, 0xffaaa9aa, 0xffb5b2b5, 0xeeb5b2b5, 0xdd7b7b7e, 0x997b7b7e, 0x33343534, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0x22080408, 0x55080408, 0x66080408, 0x66101010, 0x77101010, 0x88262626, 0x883c3b3c, + 0x993a3d3a, 0x993a3d3a, 0x99474947, 0x99474947, 0x99524d4a, 0x99524d4a, 0x995a5958, 0x995a5958, + 0x99636163, 0x99636163, 0x99636163, 0x99686868, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, 0x996b6d6b, + 0x99737173, 0x99737173, 0x99797879, 0x99797879, 0x99737573, 0x997b7c7b, 0x997b7c7b, 0x997b7c7b, + 0x997b7d7b, 0x997b7d7b, 0x99818381, 0x99818381, 0x99848284, 0x99848284, 0x99848284, 0x99848284, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99848684, + 0x99898b89, 0x99848684, 0x99898b89, 0x99898b89, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, + 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, 0x998c8a8c, + 0x998c8684, 0x998c8684, 0x998c8684, 0x998c8684, 0x9984868c, 0x9984868c, 0x9984868c, 0x9984868c, + 0x99848684, 0x99848684, 0x99848684, 0x99848684, 0x99898789, 0x99848284, 0x99848284, 0x99848284, + 0x99818381, 0x997b7d7b, 0x99818381, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, 0x997b7d7b, + 0x997b7c7b, 0x997b7c7b, 0x99737573, 0x99737573, 0x99737173, 0x99737173, 0x99737173, 0x99737173, + 0x99706d70, 0x99706d70, 0x996b656b, 0x996b656b, 0x99635d63, 0x99635d63, 0x99635d63, 0x99635d63, + 0x99585658, 0x99585658, 0x994a494a, 0x994a494a, 0x993c3d3c, 0x993c3d3c, 0x993c3d3c, 0x88292829, + 0x77080808, 0x66080808, 0x77080808, 0x77080808, 0x77000000, 0x55000000, 0x22000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11191819, 0x33191819, 0x664a494a, 0xbb7b797b, + 0xdd9c9e9c, 0xee9c9e9c, 0xffaaabaa, 0xffaaabaa, 0xffb5b2ad, 0xffb5b2ad, 0xffb5b2ad, 0xffbdbdb8, + 0xffc5bec5, 0xffc5bec5, 0xffcbc8cb, 0xffcbc8cb, 0xffcecace, 0xffcecace, 0xffcecace, 0xffd3d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffdbd9db, 0xffdbd9db, 0xffd6dbd6, 0xffd6dbd6, 0xffdee0de, 0xffdee0de, + 0xffdedfde, 0xffdedfde, 0xffe4e4e4, 0xffe4e4e4, 0xffe6e3de, 0xffe6e3de, 0xffece9e6, 0xffece9e6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, + 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, + 0xffefebe6, 0xffeeeae5, 0xffdedfde, 0xffddddde, 0xffdeddde, 0xffd6d7d6, 0xffd6d7d6, 0xffdbd7d6, + 0xffdbd7d6, 0xffdbd7d6, 0xffd6cece, 0xffcecece, 0xffcecece, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c5c5, + 0xffc5c5c5, 0xffc5c5c5, 0xffbdbabd, 0xffbabcba, 0xffadaead, 0xffadaead, 0xffadaead, 0xffaaa9aa, + 0xffaaa9aa, 0xee9c9a9c, 0xdd9c9a9c, 0xaa7b7b7e, 0x55424347, 0x22080c10, 0x11080c10, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x22000000, 0x44000000, 0x55030103, 0x66050305, 0x66080408, + 0x66131213, 0x77131213, 0x88262326, 0x883a353a, 0x88313131, 0x99313131, 0x994a494a, 0x994a494a, + 0x994a4d4a, 0x994a4d4a, 0x994a4d4a, 0x994a4d4a, 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, + 0x99636563, 0x99636563, 0x99636563, 0x99636563, 0x996b6d73, 0x996b6d73, 0x996b6d73, 0x996b6d73, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x997b757b, 0x997b757b, 0x997b757b, 0x997b757b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, 0x997b797b, + 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, 0x99737573, + 0x996b716b, 0x996b716b, 0x996b716b, 0x996b716b, 0x996b696b, 0x996b696b, 0x996b696b, 0x996b696b, + 0x99636563, 0x99636563, 0x99636563, 0x99636563, 0x995a595a, 0x995a595a, 0x995a595a, 0x995a595a, + 0x99525152, 0x99525152, 0x99525152, 0x99525152, 0x994a494a, 0x994a494a, 0x994a494a, 0x994a494a, + 0x99313531, 0x99313531, 0x88313531, 0x88212321, 0x77191419, 0x77100d10, 0x66080708, 0x66000000, + 0x77000000, 0x77000000, 0x66000000, 0x55000000, 0x22000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00030403, 0x11080c08, + 0x22000400, 0x442f312f, 0x885d5d5d, 0xbb8c8a8c, 0xdd9c9a9c, 0xdd9c9a9c, 0xee9c9a9c, 0xff9c9a9c, + 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcececd, 0xffcccdce, 0xffcccdcc, + 0xffcbc9cc, 0xffc9c8c9, 0xffc7c4c7, 0xffc2c1c3, 0xffbebdbf, 0xffb6babd, 0xffb5babd, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a2a5, + 0xffa5a2a5, 0xffa5a2a5, 0xffa5a2a5, 0xee9c9a9c, 0xee9c9a9c, 0xdd9c9a9c, 0xdd9c9a9c, 0xbb7b797b, + 0x77525252, 0x44292b29, 0x22000400, 0x11080c08, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x33000000, 0x44000000, + 0x55000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66191819, 0x77191819, 0x77191819, + 0x88313331, 0x88313331, 0x88313331, 0x88313331, 0x993f3d3f, 0x993f3d3f, 0x993f3d3f, 0x993f3d3f, + 0x99424342, 0x99424342, 0x99424342, 0x99424342, 0x99474a4d, 0x99474a4d, 0x99474a4d, 0x99474a4d, + 0x99504d50, 0x99504d50, 0x99504d50, 0x99504d50, 0x99555155, 0x99555155, 0x99555155, 0x99555155, + 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, + 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, + 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, + 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, 0x99555455, + 0x99505150, 0x99505150, 0x99505150, 0x99505150, 0x99505150, 0x99505150, 0x99505150, 0x99505150, + 0x994a4d4a, 0x994a4d4a, 0x994a4d4a, 0x994a4d4a, 0x99474847, 0x99474847, 0x99474847, 0x99474847, + 0x99424342, 0x99424342, 0x99424342, 0x99424342, 0x993c3b3c, 0x993c3b3c, 0x993c3b3c, 0x993c3b3c, + 0x99373737, 0x99373737, 0x88373737, 0x88373737, 0x88313131, 0x88313131, 0x77191819, 0x77191819, + 0x77101210, 0x66000000, 0x66000000, 0x66000000, 0x77000000, 0x77000000, 0x66000000, 0x55000000, + 0x44000000, 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x11000400, 0x11000400, 0x22000400, 0x44343634, 0x77686868, + 0x99797b79, 0xbb797b79, 0xcc797b79, 0xcc797b79, 0xddadaead, 0xeeadaead, 0xeeadaead, 0xeeadaead, + 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcccbcb, 0xffc8c8c9, 0xffc6c5c6, + 0xffb3b2b4, 0xffadadaf, 0xffb0b0b3, 0xffafb1b4, 0xffb1b5b9, 0xffb4b9bc, 0xffb5babd, 0xffadaead, + 0xffadaead, 0xffadaead, 0xeeadaead, 0xeea5a6a5, 0xeea5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xcca5a2a5, + 0xcca5a2a5, 0xbb6e6d6e, 0x886e6d6e, 0x66343334, 0x55343334, 0x22343334, 0x11000000, 0x11000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x22000000, 0x33000000, 0x44000000, 0x55000000, 0x55000000, 0x55000000, 0x66000000, + 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66080408, 0x66080408, 0x77080408, 0x77242024, + 0x77212221, 0x77212221, 0x77212221, 0x88212221, 0x88242726, 0x88242726, 0x88242726, 0x88242726, + 0x882c282c, 0x882c282c, 0x882c282c, 0x882c282c, 0x882f2d2f, 0x882f2d2f, 0x882f2d2f, 0x992f2d2f, + 0x882f2e2f, 0x882f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, + 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, + 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, + 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, 0x992f2e2f, + 0x992c2d2c, 0x992c2d2c, 0x992c2d2c, 0x992c2d2c, 0x992c2d2c, 0x882c2d2c, 0x882c2d2c, 0x882c2d2c, + 0x88292829, 0x88292829, 0x88292829, 0x88292829, 0x88242624, 0x88242624, 0x88242624, 0x88242624, + 0x88212221, 0x88212221, 0x88212221, 0x88212221, 0x771e1e1e, 0x771e1e1e, 0x771e1e1e, 0x771e1e1e, + 0x77000400, 0x66000400, 0x66000400, 0x66000400, 0x66000000, 0x66000000, 0x77000000, 0x77000000, + 0x77000000, 0x66000000, 0x66000000, 0x55000000, 0x44000000, 0x33000000, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x22000400, 0x443a3d3a, 0x443a3d3a, 0x663a3d3a, + 0x663c3f3c, 0x773c3f3c, 0x88797b79, 0xaa797b79, 0xbb7e7f7e, 0xbb7e7f7e, 0xbb7e7f7e, 0xbb7e7f7e, + 0xcc848684, 0xcc848684, 0xcc848684, 0xcc848684, 0xcc898889, 0xdd898889, 0xdd898889, 0xdd898889, + 0xdd8c8b8c, 0xdd8c8b8c, 0xdd8c8b8c, 0xdd8c8b8c, 0xdd8c8b8c, 0xdd8c8b8c, 0xee8c8b8c, 0xee8c8b8c, + 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, + 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8c8b8c, 0xee8b8b8b, 0xee898989, + 0xee878588, 0xee848285, 0xcc7e7d80, 0xbb7b7c7f, 0xbb797c7e, 0xbb797c7e, 0xaa797c7e, 0xaa737473, + 0x88737473, 0x77737473, 0x663a3a3a, 0x55373a37, 0x44373a37, 0x33373a37, 0x22000400, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x22000000, + 0x33000000, 0x44000000, 0x44000000, 0x55000000, 0x55080408, 0x55080408, 0x66080408, 0x66080408, + 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000400, 0x66000400, 0x66000400, 0x66000400, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66000400, 0x66000400, 0x66000400, 0x66000400, + 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, + 0x66000400, 0x66000400, 0x66000400, 0x55000400, 0x55000000, 0x44000000, 0x44000000, 0x33000000, + 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, + 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, + 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, + 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080408, 0x00080407, + 0x00080408, 0x00060308, 0x00000400, 0x00010100, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x22000000, 0x22000000, 0x22000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x44000000, + 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, + 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x55000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, + 0x44000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x22000000, 0x22000000, + 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00030403, 0x00030403, + 0x00050505, 0x00050505, 0x00050505, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00030403, 0x00030403, 0x00030403, + 0x00030303, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x22000000, 0x22000000, 0x22000000, 0x33000000, 0x33000000, + 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, + 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x22000000, 0x22000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00030403, 0x00050805, 0x11080c08, + 0x22101010, 0x22101010, 0x11101010, 0x11050505, 0x00000400, 0x00000100, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00050805, 0x11050805, 0x11080c08, 0x11080c08, + 0x11080808, 0x00030303, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, + 0x22000000, 0x22000000, 0x22000000, 0x33000000, 0x22000000, 0x22000000, 0x22000000, 0x11000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x55050705, 0xaa101410, 0xcc191819, 0xcc191819, 0xcc191819, 0xcc191819, + 0xcc191c19, 0xcc191c19, 0xcc191c19, 0xcc191c19, 0xcc191c19, 0xcc191c19, 0xcc191c19, 0xcc191c19, + 0xcc191c19, 0xcc191c19, 0xcc191c19, 0xcc191c19, 0xcc191819, 0xcc191819, 0xcc191819, 0xbb191819, + 0x66080808, 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x44050405, 0x66100c10, + 0x99101010, 0xbb191819, 0xcc191819, 0xdd191819, 0xcc191819, 0xbb191819, 0x99101010, 0x77101010, + 0x44080408, 0x22030103, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11080808, 0x55080808, 0xbb4a494a, 0xdd8c8a8c, 0xeea5a6a5, 0xeea5a6a5, 0xeea5a6a5, 0xeea5a6a5, + 0xeeadaaad, 0xeeadaaad, 0xeeadaaad, 0xeeadaaad, 0xeeadaaad, 0xeeadaaad, 0xeeadaaad, 0xeeadaaad, + 0xeeadaaad, 0xeeadaaad, 0xeeadaaad, 0xeeadaaad, 0xeea5a6a5, 0xeea5a6a5, 0xeea5a6a5, 0xee8c8e8c, + 0xbb3c3b3c, 0x77080808, 0x22080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0x00080408, 0x00080408, 0x11080408, 0x33080408, 0x88080408, 0xcc4a464a, 0xee4a464a, + 0xee8c8a8c, 0xffa7a6a7, 0xffa7a6a7, 0xffa7a6a7, 0xffafb3af, 0xff898c89, 0xee898c89, 0xee636563, + 0xcc4a494a, 0x88080408, 0x44080408, 0x22080408, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x22080808, 0xaa080808, 0xdd8c8a8c, 0xffcecace, 0xffcbcccb, 0xffcbcccb, 0xffcbcccb, 0xffcbcccb, + 0xffd3d0d3, 0xffd3d0d3, 0xffd3d0d3, 0xffd3d0d3, 0xffd3d0d3, 0xffd3d0d3, 0xffd3d0d3, 0xffd3d0d3, + 0xffd3d0d3, 0xffd3d0d3, 0xffd3d0d3, 0xffd3d0d3, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffbdbebd, + 0xeea5a2a5, 0xbb080808, 0x33080808, 0x00080808, 0x00000000, 0x110e0d0e, 0x110e0d0e, 0x331b1b1b, + 0x44212021, 0x55212021, 0x44212021, 0x22101010, 0x11100f10, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x110b0b0b, 0x110e0f0e, 0x330e0f0e, 0x441b1e1b, 0x330e0f0e, + 0x220b0b0b, 0x110b0b0b, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0x00080408, 0x11080408, 0x55080408, 0xaa4a464a, 0xee8c888c, 0xff8c888c, 0xffcecace, + 0xffc3c2c3, 0xffc3c2c3, 0xffc3c2c3, 0xffdedfde, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffafb3af, + 0xff8c8e8c, 0xee8c8e8c, 0xbb4a494a, 0x66080408, 0x22000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x22080808, 0xcc080808, 0xee8c8a8c, 0xffcecace, 0xffcbcccb, 0xffcbcccb, 0xffdedfde, 0xffdedfde, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffa5a2a5, 0xdd080808, 0x44080808, 0x00080808, 0x00000000, 0x110e0d0e, 0x331b1b1b, 0x551b1b1b, + 0x77212021, 0x88212021, 0x88212021, 0x55212021, 0x33211e21, 0x11100f10, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x110b0b0b, 0x22161616, 0x441b1e1b, 0x661b1e1b, 0x661b1e1b, 0x551b1e1b, + 0x44161616, 0x220b0b0b, 0x000b0b0b, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0x11080408, 0x66080408, 0xcc3c3b3c, 0xee8c888c, 0xffcecace, 0xffcecace, 0xffcecace, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffced2ce, 0xffced2ce, 0xee8c8e8c, 0xcc4a494a, 0x771b1a1b, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x22080808, 0xcc080808, 0xee8c8a8c, 0xffcecace, 0xffcbcccb, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffa5a2a5, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x220e0d0e, 0x551b1b1b, 0x77292829, + 0x99313131, 0xaa313131, 0xbb313131, 0xaa313131, 0x77312d31, 0x33211e21, 0x11100f10, 0x11000000, + 0x00000000, 0x110b0b0b, 0x22161616, 0x44212021, 0x88292d29, 0x99292d29, 0x99292d29, 0x77292d29, + 0x66212021, 0x33161616, 0x110b0b0b, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11080408, 0x55080408, 0xcc3c3b3c, 0xffa5aaa5, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xff8c8e8c, 0xcc524d52, 0x771b1a1b, 0x22000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9a9a9a, 0xffdedfde, 0xffd6d7d6, 0xffdedfde, 0xffdedfde, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffecedec, 0xffecedec, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, 0xffe4e5e4, 0xffe4e5e4, 0xffdedfde, 0xffdedfde, + 0xffb5b2b5, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x220e0d0e, 0x551b1b1b, 0x88292829, + 0xaa292d29, 0xbb292d29, 0xcc292d29, 0xcc212321, 0xbb2c2e2c, 0x882c2e2c, 0x442c2e2c, 0x22101010, + 0x11191419, 0x22191419, 0x44292629, 0x99292629, 0xbb292729, 0xbb313131, 0xaa313131, 0x99313131, + 0x77212421, 0x44161816, 0x110b0c0b, 0x00000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x33080808, 0xbb4a4a4a, 0xee8c8c8c, 0xffcecece, 0xffd6d7d6, 0xffd6d7d6, 0xffdeddde, 0xffdeddde, + 0xffdee3de, 0xffe6e9e6, 0xffe6e9e6, 0xffe6e9e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, + 0xffe6e7e6, 0xffdedbde, 0xffdedbde, 0xffd6ced6, 0xee8c8e8c, 0xbb4a494a, 0x55080408, 0x11080408, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080808, 0x00080808, 0x00080808, 0x00080808, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9a9a9a, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffe6e7e6, 0xffe6e7e6, + 0xffecedec, 0xffecedec, 0xfff1f4f1, 0xfff1f4f1, 0xfff1f3f1, 0xfff1f3f1, 0xfff1f3f1, 0xfff1f3f1, + 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, 0xffe9ece9, 0xffe9ece9, 0xffe4e5e4, 0xffdedfde, + 0xffb5b2b5, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x110e0d0e, 0x441b1b1b, 0x88292829, + 0xbb292d29, 0xcc212321, 0xcc212321, 0xdd191a19, 0xdd1e1f1e, 0xcc1e1f1e, 0x992c2e2c, 0x552c2e2c, + 0x33292629, 0x553a373a, 0x993a373a, 0xcc292629, 0xcc211e21, 0xcc292729, 0xbb292729, 0xbb292729, + 0x88212421, 0x33161816, 0x110b0c0b, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x11000000, + 0x88080808, 0xee8c8c8c, 0xffcecece, 0xffcecece, 0xffd6d7d6, 0xffdeddde, 0xffe6e4e6, 0xffe6e4e6, + 0xffe6e9e6, 0xffe6e9e6, 0xffeff0ef, 0xffeff0ef, 0xfff1f2f1, 0xffececec, 0xffececec, 0xffececec, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffdedbde, 0xffced2ce, 0xee8c8e8c, 0x99080408, 0x33080408, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x110e0c0e, 0x11131413, 0x22131413, 0x22131413, 0x22131413, + 0x110e120e, 0x110e120e, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9a9a9a, 0xffdedfde, 0xffdedfde, 0xffe6e7e6, 0xffe6e7e6, 0xffefefef, + 0xfff1f4f1, 0xfff1f4f1, 0xfff1f4f1, 0xfff1f4f1, 0xfff4f7f4, 0xfff4f7f4, 0xfff4f7f4, 0xfff4f7f4, + 0xfff4f6f4, 0xfff4f6f4, 0xfff4f6f4, 0xfff4f6f4, 0xffeff3ef, 0xffe9ece9, 0xffe9ece9, 0xffe4e5e4, + 0xffb5b2b5, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x000e0d0e, 0x221b1b1b, 0x55292829, + 0xaa292d29, 0xcc212321, 0xdd191a19, 0xdd191a19, 0xee101010, 0xdd101010, 0xdd1e1f1e, 0xaa3a3d3a, + 0x774a494a, 0x993a373a, 0xcc292629, 0xdd191419, 0xdd211e21, 0xdd211e21, 0xcc292729, 0xaa292729, + 0x66212421, 0x33161816, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x44050405, + 0xcc4a4a4a, 0xff8c8c8c, 0xffcecece, 0xffcecece, 0xffdeddde, 0xffe6e4e6, 0xffe6e4e6, 0xffefebef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f1, + 0xffeff3ef, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffced2ce, 0xff8c8e8c, 0xcc4a494a, 0x55080408, + 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x110e0c0e, 0x221b181b, 0x441e201e, 0x661e201e, 0x66292d29, 0x66292d29, + 0x551b1f1b, 0x331b1f1b, 0x110e120e, 0x11000400, 0x00030303, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9a9a9a, 0xffdedfde, 0xffdedfde, 0xffe6e7e6, 0xffefefef, 0xffefefef, + 0xfff1f4f1, 0xfff1f4f1, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, + 0xfff7fbf7, 0xfff7fbf7, 0xfff4f6f4, 0xfff4f6f4, 0xffeff3ef, 0xffeff3ef, 0xffe9ece9, 0xffe4e5e4, + 0xffb5b2b5, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x110e0d0e, 0x221b1b1b, + 0x66292d29, 0xbb292d29, 0xdd191a19, 0xee101010, 0xee101010, 0xee101010, 0xee101010, 0xdd1e1f1e, + 0xbb292629, 0xdd292629, 0xee191419, 0xee191419, 0xdd191419, 0xdd191419, 0xcc292729, 0x88313131, + 0x44212421, 0x330b0c0b, 0x22000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x66100c10, + 0xee4a4a4a, 0xffcecece, 0xffcecece, 0xffcecece, 0xffe6e4e6, 0xffe6e4e6, 0xffefebef, 0xffefebef, + 0xffeff0ef, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xffeff3ef, 0xffeff3ef, 0xffe6e7e6, 0xffe6e7e6, 0xffced2ce, 0xffced2ce, 0xee4a494a, 0x88080408, + 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x110e0c0e, 0x331b181b, 0x66292429, 0x88292d29, 0xaa292d29, 0xaa292d29, 0xaa292d29, + 0x99292d29, 0x77292d29, 0x551b1f1b, 0x220e120e, 0x11080808, 0x00030303, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9f9f9f, 0xffe6e7e6, 0xffe6e3e6, 0xffece9ec, 0xfff1f0f1, 0xfff1f0f1, + 0xfff7f7f7, 0xfffafafa, 0xfffcfcfc, 0xfffcfcfc, 0xfffffcff, 0xfffffcff, 0xfffffcff, 0xfffffcff, + 0xfffffcff, 0xfffffcff, 0xfffffbff, 0xfffffbff, 0xfff1f4f1, 0xfff1f4f1, 0xffecedec, 0xffe6e7e6, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00050405, 0x11100c10, + 0x33212321, 0x77313531, 0xbb313531, 0xee101210, 0xee080808, 0xee080808, 0xee080808, 0xee080808, + 0xee100c10, 0xee100c10, 0xee100c10, 0xee100c10, 0xee101010, 0xdd212021, 0xaa313131, 0x55313131, + 0x33101010, 0x33050505, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x11000000, 0x99101310, + 0xee8c8e8c, 0xffc3c4c3, 0xffdedfde, 0xffdedfde, 0xffe6e7e6, 0xffecedec, 0xffecedec, 0xfff1f4f1, + 0xfff7f7f7, 0xfff7f7f7, 0xfffafafa, 0xfffafafa, 0xfffafafa, 0xfffafafa, 0xfffafafa, 0xfff7f7f7, + 0xfffaf6fa, 0xfff4f0f4, 0xfff4f0f4, 0xffefebef, 0xffe6e7e6, 0xffe6e7e6, 0xeea2a3a2, 0xaa191c19, + 0x33000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00030303, + 0x11080808, 0x221e201e, 0x66292d29, 0xaa292d29, 0xbb292d29, 0xcc262726, 0xcc262726, 0xcc262726, + 0xcc262726, 0xbb292d29, 0x88262726, 0x55242224, 0x220b0c0b, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9f9f9f, 0xffe6e7e6, 0xffe6e3e6, 0xffece9ec, 0xfff1f0f1, 0xfff7f7f7, + 0xfff7f7f7, 0xfffcfcfc, 0xfffcfcfc, 0xffffffff, 0xfffffeff, 0xfffffeff, 0xfffffeff, 0xfffffeff, + 0xfffffeff, 0xfffffeff, 0xfffffeff, 0xfffffbff, 0xfff7fbf7, 0xfff1f4f1, 0xfff1f4f1, 0xffe6e7e6, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x11050405, + 0x11101210, 0x33212321, 0x77313531, 0xcc313531, 0xee080808, 0xee080808, 0xff080808, 0xff080808, + 0xff050705, 0xee050705, 0xee0b090b, 0xee100c10, 0xee101010, 0xbb313131, 0x77313131, 0x44212021, + 0x33050505, 0x33000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x22000000, 0xbb191c19, + 0xffa7a9a7, 0xffc3c4c3, 0xffdedfde, 0xffdedfde, 0xffe6e7e6, 0xffecedec, 0xfff1f4f1, 0xfff1f4f1, + 0xfffafafa, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffffbff, 0xfffaf6fa, 0xfff4f0f4, 0xfff4f0f4, 0xffe6e7e6, 0xffe6e7e6, 0xffa2a3a2, 0xcc191c19, + 0x44000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00050505, + 0x11131413, 0x551e201e, 0x99292d29, 0xbb292d29, 0xcc242224, 0xcc242224, 0xdd242224, 0xdd242224, + 0xdd242224, 0xcc262726, 0xbb292d29, 0x88262726, 0x33161816, 0x110b0c0b, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9f9f9f, 0xffe6e7e6, 0xffe6e3e6, 0xffece9ec, 0xfff1f0f1, 0xfff7f7f7, + 0xfffafafa, 0xfffcfcfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffeff, 0xfffffcff, 0xfff7fbf7, 0xfff1f4f1, 0xfff1f4f1, 0xffe6e7e6, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x22101210, 0x44212321, 0x88313531, 0xcc2f332f, 0xee080808, 0xff080808, 0xff080808, + 0xff050705, 0xff050705, 0xee0b090b, 0xee100c10, 0xcc212021, 0x99424142, 0x66212021, 0x44101010, + 0x33000000, 0x33000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x22000000, 0xcc191c19, + 0xffa7a9a7, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffecedec, 0xfff1f4f1, 0xfff1f4f1, 0xfff7fbf7, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xfffcfcfc, 0xfffcfcfc, + 0xfffffbff, 0xfffaf6fa, 0xfffaf6fa, 0xfff4f0f4, 0xffe6e7e6, 0xffe6e7e6, 0xffa2a3a2, 0xdd191c19, + 0x44000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080808, + 0x22131413, 0x66292d29, 0xaa292d29, 0xcc1e201e, 0xdd242224, 0xdd242224, 0xdd242224, 0xdd211c21, + 0xdd211c21, 0xcc242224, 0xbb292d29, 0x99292d29, 0x55212421, 0x220b0c0b, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9f9f9f, 0xffe6e7e6, 0xffece9ec, 0xfff1f0f1, 0xfff1f0f1, 0xfff7f7f7, + 0xfffafafa, 0xfffcfcfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffeff, 0xfffffcff, 0xfff7fbf7, 0xfff1f4f1, 0xfff1f4f1, 0xffecedec, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x22101210, 0x55313531, 0x99424942, 0xdd1b1e1b, 0xff080808, 0xff080808, + 0xff000400, 0xff050705, 0xff050705, 0xee100c10, 0xcc313131, 0x99424142, 0x66212021, 0x44101010, + 0x33050505, 0x33000000, 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x33000000, 0xdd191c19, + 0xffa7a9a7, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffecedec, 0xfff1f4f1, 0xfff1f4f1, 0xfff7fbf7, + 0xfffcfcfc, 0xfffcfcfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfffcfcfc, + 0xfffffbff, 0xfffffbff, 0xfffaf6fa, 0xfff4f0f4, 0xffe6e7e6, 0xffe6e7e6, 0xffa2a3a2, 0xdd191c19, + 0x55000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080808, + 0x33131413, 0x77292d29, 0xbb292d29, 0xcc1e201e, 0xdd211c21, 0xdd242224, 0xdd242224, 0xdd242224, + 0xdd211c21, 0xdd242224, 0xcc292d29, 0xaa292d29, 0x66212421, 0x330b0c0b, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xeea5a2a5, 0xffefebef, 0xffe6e7e6, 0xffececec, 0xfff1f2f1, 0xfff7f7f7, + 0xfff7fbf7, 0xfffafcfa, 0xfffcfefc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffeff, 0xfffffcff, 0xfff7fbf7, 0xfff4f6f4, 0xfff1f0f1, 0xffefebef, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0x11080408, 0x22191619, 0x553a393a, 0xaa424542, 0xee1b1c1b, 0xff080808, 0xff080808, + 0xff000400, 0xff000400, 0xff000400, 0xee0e100e, 0xee1e1e1e, 0xbb3a393a, 0x882c2b2c, 0x551e1e1e, + 0x440e0d0e, 0x33000000, 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x22000000, 0xcc191c19, + 0xffb8bab8, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffefefef, 0xfff1f3f1, 0xfff4f7f4, 0xfff7fbf7, + 0xfffffcff, 0xfffffeff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xfffcfbfc, 0xfffcfbfc, 0xfffaf7fa, 0xfff7f3f7, 0xffe6e7e6, 0xffe6e7e6, 0xffa2a2a2, 0xdd191819, + 0x55000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080808, + 0x22131713, 0x77292d29, 0xbb292d29, 0xcc1e221e, 0xdd242224, 0xdd242224, 0xdd211c21, 0xdd211c21, + 0xdd191c19, 0xdd1e221e, 0xcc292d29, 0xaa292d29, 0x66292429, 0x330e0c0e, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xeea5a2a5, 0xffefebef, 0xffe6e7e6, 0xffececec, 0xfff1f2f1, 0xfff7f7f7, + 0xfff7fbf7, 0xfffafcfa, 0xfffcfefc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffeff, 0xfffffcff, 0xfff7fbf7, 0xfff4f6f4, 0xfff1f0f1, 0xffefebef, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0x11080408, 0x33292729, 0x773a393a, 0xdd1b1c1b, 0xee080808, 0xff080808, 0xff080808, + 0xff000400, 0xff000400, 0xff000400, 0xee0e100e, 0xee101010, 0xdd1e1e1e, 0xbb3a393a, 0x772c2b2c, + 0x441b1b1b, 0x330e0d0e, 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x22000000, 0xbb191c19, + 0xff919291, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffefefef, 0xfff1f3f1, 0xfff4f7f4, 0xfff7fbf7, + 0xfffffeff, 0xfffffeff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xfffcfbfc, 0xfffcfbfc, 0xfffaf7fa, 0xfff7f3f7, 0xffe6e7e6, 0xffe6e7e6, 0xffa2a2a2, 0xcc191819, + 0x44000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00050505, + 0x22131713, 0x661e221e, 0xaa292d29, 0xcc292d29, 0xdd242224, 0xdd242224, 0xdd211c21, 0xdd211c21, + 0xdd1e221e, 0xdd242724, 0xcc292d29, 0x99242724, 0x551b181b, 0x330e0c0e, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xeea5a2a5, 0xffefebef, 0xffe6e7e6, 0xffececec, 0xfff1f2f1, 0xfff7f7f7, + 0xfff7fbf7, 0xfffafcfa, 0xfffcfefc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffeff, 0xfffffcff, 0xfff7fbf7, 0xfff4f6f4, 0xfff1f0f1, 0xffefebef, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x00030103, + 0x11080408, 0x22191619, 0x663a393a, 0xcc292729, 0xee080808, 0xff080808, 0xff080808, 0xff080808, + 0xee0e100e, 0xee0e100e, 0xee0e100e, 0xee0e100e, 0xee101010, 0xee101010, 0xdd1e1e1e, 0xaa2c2b2c, + 0x66292829, 0x330e0d0e, 0x220e0d0e, 0x11000000, 0x11000000, 0x00000000, 0x22000000, 0x99101310, + 0xee919291, 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffefefef, 0xfff1f3f1, 0xfff4f7f4, 0xfff7fbf7, + 0xfffffcff, 0xfffffeff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xfffcfbfc, 0xfffcfbfc, 0xfffaf7fa, 0xfff7f3f7, 0xffe6e7e6, 0xffe6e7e6, 0xeea2a2a2, 0xaa191819, + 0x44000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00030303, + 0x11080c08, 0x441e221e, 0x88292d29, 0xbb292d29, 0xcc262726, 0xdd242224, 0xdd242224, 0xdd242224, + 0xdd1e221e, 0xcc292d29, 0xbb292d29, 0x88242724, 0x441b181b, 0x330e0c0e, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xeea5a2a5, 0xffefebef, 0xffe6e7e6, 0xffececec, 0xfff1f2f1, 0xfff7f7f7, + 0xfff7fbf7, 0xfffafcfa, 0xfffcfefc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffeff, 0xfffffcff, 0xfff7fbf7, 0xfff4f6f4, 0xfff1f0f1, 0xffefebef, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00030103, 0x00080408, + 0x11191619, 0x44292729, 0xaa3a393a, 0xdd191619, 0xee080808, 0xee080808, 0xee080808, 0xee080808, + 0xdd1b1c1b, 0xdd292829, 0xee0e100e, 0xee0e100e, 0xee101010, 0xee1e1e1e, 0xdd1e1e1e, 0xcc2c2b2c, + 0x99292829, 0x55292829, 0x220e0d0e, 0x11000000, 0x11080908, 0x11000000, 0x11000000, 0x77080908, + 0xee6b696b, 0xffb8bab8, 0xffdee3de, 0xffdee3de, 0xffefefef, 0xfff1f3f1, 0xfff4f7f4, 0xfff7fbf7, + 0xfffffcff, 0xfffffeff, 0xfffffeff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xfffcfbfc, 0xfffaf7fa, 0xfffaf7fa, 0xfff7f3f7, 0xffe6e7e6, 0xffe6e7e6, 0xee5d5d5d, 0x88191819, + 0x33000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11080c08, 0x22131713, 0x661e221e, 0x99292d29, 0xbb292d29, 0xcc292d29, 0xcc262726, 0xcc292d29, + 0xcc292d29, 0xbb292d29, 0x99242724, 0x66191c19, 0x330e0c0e, 0x22000000, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9f9f9f, 0xffe6e7e6, 0xffe6e9e6, 0xffe6e9e6, 0xffeff0ef, 0xfff7f7f7, + 0xfffaf7fa, 0xfffcfbfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xfffcfcfc, 0xfff7fbf7, 0xfff1f4f1, 0xfff1f4f1, 0xffe6e7e6, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x110b0c0b, + 0x33262826, 0x88313531, 0xdd1b1c1b, 0xee101010, 0xee101010, 0xee101010, 0xee101010, 0xdd1e1e1e, + 0xaa4a454a, 0x994a454a, 0xcc312f31, 0xdd191a19, 0xee191c19, 0xdd191c19, 0xdd212321, 0xcc292a29, + 0xbb262426, 0x88262426, 0x441b181b, 0x22100c10, 0x22080c08, 0x11030403, 0x11000000, 0x44050805, + 0xcc504c50, 0xff979397, 0xffdedbde, 0xffdedbde, 0xffececec, 0xffececec, 0xfff7f7f7, 0xfff7f7f7, + 0xfffafbfa, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfffcfcfc, 0xfffcfcfc, + 0xfff7f3f7, 0xfff7f3f7, 0xfff7f3f7, 0xfff7f3f7, 0xffdee3de, 0xff979897, 0xcc504e50, 0x66080408, + 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x110b0b0b, 0x33161616, 0x66212021, 0x88292d29, 0xaa292d29, 0xbb292d29, 0xbb292d29, + 0xaa292829, 0x88292829, 0x661b1b1b, 0x440e0d0e, 0x33080408, 0x22030103, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9f9f9f, 0xffe6e7e6, 0xffdee3de, 0xffe6e9e6, 0xffeff0ef, 0xfff7f7f7, + 0xfffaf7fa, 0xfffcfbfc, 0xfffcfbfc, 0xffffffff, 0xfffcfefc, 0xfffcfefc, 0xfffcfefc, 0xfffcfefc, + 0xffffffff, 0xffffffff, 0xfffcfcfc, 0xfffcfcfc, 0xfff7fbf7, 0xfff1f4f1, 0xfff1f4f1, 0xffe6e7e6, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x110b0c0b, 0x22161816, + 0x66262826, 0xbb262826, 0xdd1b1c1b, 0xee101010, 0xee101010, 0xee101010, 0xdd1e1e1e, 0xaa3a393a, + 0x77312f31, 0x77312f31, 0x88312f31, 0xbb312f31, 0xdd212321, 0xdd212321, 0xdd292a29, 0xcc313131, + 0xbb313131, 0x99262426, 0x661b181b, 0x33100c10, 0x33080c08, 0x11030403, 0x00000000, 0x22000000, + 0x88080408, 0xee979397, 0xffdedbde, 0xffdedbde, 0xffececec, 0xffececec, 0xfff7f7f7, 0xfff7f7f7, + 0xfffafbfa, 0xfffafbfa, 0xfffafbfa, 0xfffafbfa, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfff7f3f7, 0xfff7f3f7, 0xfff7f3f7, 0xfff7f3f7, 0xffdee3de, 0xee979897, 0x99080408, 0x44080408, + 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x110b0b0b, 0x33161616, 0x441e1f1e, 0x661e1f1e, 0x77292d29, 0x771e1f1e, + 0x661b1b1b, 0x551b1b1b, 0x440e0d0e, 0x33000000, 0x22030103, 0x22000000, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9f9f9f, 0xffe6e7e6, 0xffdee3de, 0xffe6e9e6, 0xffeff0ef, 0xffeff0ef, + 0xfffaf7fa, 0xfffaf7fa, 0xfffcfbfc, 0xfffcfbfc, 0xfffafcfa, 0xfffafcfa, 0xfffafcfa, 0xfffafcfa, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffafafa, 0xfff1f4f1, 0xfff1f4f1, 0xffecedec, 0xffe6e7e6, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x00000000, 0x110b0c0b, 0x44212421, + 0x99262826, 0xcc262826, 0xdd1b1c1b, 0xdd1b1c1b, 0xdd101010, 0xdd1e1e1e, 0xbb3a393a, 0x772c2b2c, + 0x66191a19, 0x66191a19, 0x66191a19, 0x88312f31, 0xaa292a29, 0xcc292a29, 0xcc292a29, 0xbb313131, + 0xaa313131, 0x99262426, 0x77262426, 0x441b181b, 0x33050805, 0x22030403, 0x00000000, 0x11000000, + 0x44080408, 0xbb504c50, 0xee979397, 0xffdedbde, 0xffe1e1e1, 0xffececec, 0xffececec, 0xfff7f7f7, + 0xfff4f7f4, 0xfff4f7f4, 0xfffafbfa, 0xfffafbfa, 0xfffafafa, 0xfffafafa, 0xfffafafa, 0xfff7f7f7, + 0xfff7f3f7, 0xfff7f3f7, 0xfff7f3f7, 0xffe1dfe1, 0xee979897, 0xcc504e50, 0x66080408, 0x33080408, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x110b0b0b, 0x22131213, 0x33131213, 0x44131213, 0x44131213, + 0x440e0d0e, 0x330e0d0e, 0x33000000, 0x22000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33101010, 0xcc101010, 0xee9f9f9f, 0xffe6e7e6, 0xffdee3de, 0xffe6e9e6, 0xffeff0ef, 0xffeff0ef, + 0xfff7f3f7, 0xfffaf7fa, 0xfffaf7fa, 0xfffaf7fa, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, + 0xfffafafa, 0xfffafafa, 0xfff7f7f7, 0xfff7f7f7, 0xfff1f4f1, 0xfff1f4f1, 0xffecedec, 0xffe6e7e6, + 0xffbdbabd, 0xdd080808, 0x55080808, 0x00080808, 0x00000000, 0x000b0c0b, 0x22161816, 0x66212421, + 0x99262826, 0xbb262826, 0xcc262826, 0xdd1b1c1b, 0xdd1e1e1e, 0xbb2c2b2c, 0x772c2b2c, 0x551e1e1e, + 0x55000400, 0x55000400, 0x55000400, 0x55191a19, 0x66212321, 0x99292a29, 0xaa292a29, 0xaa292a29, + 0x99313131, 0x88262426, 0x661b181b, 0x441b181b, 0x22050805, 0x22030403, 0x00000000, 0x00000000, + 0x22080408, 0x66080408, 0xcc504c50, 0xff979397, 0xffd6d7d6, 0xffe1e1e1, 0xffececec, 0xffececec, + 0xffeff3ef, 0xfff4f7f4, 0xfff4f7f4, 0xfff4f7f4, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xfff7f3f7, 0xfff7f3f7, 0xffe1dfe1, 0xffb5b6b5, 0xdd504e50, 0x88080408, 0x44080408, 0x22080408, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11080408, 0x22080408, 0x22080408, 0x22080408, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33080808, 0xcc080808, 0xee919491, 0xffd6dbd6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, + 0xffa5a6a5, 0xdd080408, 0x55080408, 0x00080408, 0x00000000, 0x110b0b0b, 0x33161616, 0x66212021, + 0x88292829, 0xaa292829, 0xbb292829, 0xcc292829, 0xbb292829, 0x77292829, 0x551b1b1b, 0x550e0d0e, + 0x44030303, 0x44000000, 0x44030303, 0x44080808, 0x440b0b0b, 0x55212021, 0x77212021, 0x88212021, + 0x88212021, 0x77212021, 0x55191819, 0x44101010, 0x22080408, 0x11030103, 0x00000000, 0x00000000, + 0x00000000, 0x22000000, 0x771b1b1b, 0xcc525152, 0xee979397, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffdee3de, 0xffdee3de, 0xff979897, 0xdd504e50, 0x88101410, 0x44000000, 0x22000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x22080808, 0xbb080808, 0xee919491, 0xffd6dbd6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xffefebef, 0xffefebef, 0xffefebef, 0xffefebef, + 0xeea5a6a5, 0xcc080408, 0x44080408, 0x00080408, 0x00000000, 0x110b0b0b, 0x220b0b0b, 0x44161616, + 0x661e1e1e, 0x77292829, 0x88292829, 0x99292829, 0x77292829, 0x551b1b1b, 0x440e0d0e, 0x44000000, + 0x44000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x330b0b0b, 0x44161616, 0x66161616, + 0x66191819, 0x66191819, 0x55101010, 0x33101010, 0x22030103, 0x11030103, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x22000000, 0x771b1b1b, 0xbb504c50, 0xee979397, 0xff979397, 0xffdedbde, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xff979897, 0xee979897, 0xcc504e50, 0x88080408, 0x44000000, 0x22000000, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11080808, 0x66080808, 0xbb4d4e4d, 0xee919491, 0xeea5a7a5, 0xffa5a7a5, 0xffa5a7a5, 0xffa5a7a5, + 0xffb2b1b2, 0xffb2b1b2, 0xffb2b1b2, 0xffb2b1b2, 0xffb2b1b2, 0xffb2b1b2, 0xffb2b1b2, 0xffb2b1b2, + 0xffb2b1b2, 0xffb2b1b2, 0xffb2b1b2, 0xffb2b1b2, 0xffaaa7aa, 0xffaaa7aa, 0xeeaaa7aa, 0xeeaaa7aa, + 0xcc707070, 0x99080408, 0x33080408, 0x00080408, 0x00000000, 0x00000000, 0x110b0b0b, 0x220b0b0b, + 0x33131313, 0x441e1e1e, 0x441e1e1e, 0x441e1e1e, 0x440e0d0e, 0x440e0d0e, 0x44000000, 0x44000000, + 0x33000000, 0x33000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x220b0b0b, 0x330b0b0b, + 0x44101010, 0x44101010, 0x44080808, 0x33080808, 0x11030103, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x22000000, 0x55080408, 0x99080408, 0xcc504c50, 0xee504c50, + 0xeeaaa9aa, 0xffaaa9aa, 0xffaaa9aa, 0xffaaa9aa, 0xffa7a9a7, 0xffa7a9a7, 0xeea7a9a7, 0xee606260, + 0xcc504e50, 0x99080408, 0x66080408, 0x44080408, 0x22000000, 0x11000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080808, 0x22080808, 0x77080808, 0xbb080808, 0xdd212021, 0xdd212021, 0xdd212021, 0xdd212021, + 0xdd292429, 0xdd292429, 0xdd292429, 0xdd292429, 0xdd292429, 0xdd292429, 0xdd292429, 0xdd292429, + 0xdd292429, 0xdd292429, 0xdd292429, 0xdd292429, 0xdd212021, 0xdd212021, 0xdd212021, 0xcc212021, + 0x99080408, 0x44080408, 0x22080408, 0x00080408, 0x00000000, 0x00000000, 0x00000000, 0x110b0b0b, + 0x11080808, 0x11080808, 0x22080808, 0x22080808, 0x33000000, 0x33000000, 0x33000000, 0x33000000, + 0x33000000, 0x22000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x22000000, + 0x22080808, 0x33080808, 0x33080808, 0x22080808, 0x11000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11080408, 0x33080408, 0x55080408, 0x88080408, + 0xaa211c21, 0xcc211c21, 0xdd211c21, 0xdd211c21, 0xdd191c19, 0xcc191c19, 0xaa191c19, 0x88191c19, + 0x66080408, 0x44080408, 0x33080408, 0x22080408, 0x11000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x22000000, 0x33000000, 0x44000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x44000000, + 0x33000000, 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x11000000, 0x11000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x22000000, 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x22000000, 0x22000000, + 0x33000000, 0x44000000, 0x44000000, 0x55000000, 0x55000000, 0x44000000, 0x44000000, 0x33000000, + 0x22000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x33000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, + 0x22000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x22000000, 0x22000000, 0x33000300, 0x33000300, 0x44000400, 0x44000400, + 0x55080808, 0x55101010, 0x66101010, 0x66191819, 0x661b1e1b, 0x661b1e1b, 0x66292d29, 0x66292d29, + 0x77313531, 0x77313531, 0x77313531, 0x77313531, 0x773a3d3a, 0x773a3d3a, 0x773a3d3a, 0x773a3d3a, + 0x77424142, 0x77424142, 0x77424142, 0x77424142, 0x77424542, 0x77424542, 0x77424542, 0x77424542, + 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x88424542, 0x88424542, 0x88424542, 0x88424542, + 0x88424542, 0x88424542, 0x88424542, 0x88424542, 0x88424542, 0x88424542, 0x88424542, 0x88424542, + 0x88424142, 0x88424142, 0x88424142, 0x88424142, 0x88424142, 0x88424142, 0x88424142, 0x88424142, + 0x88424142, 0x88424142, 0x88424142, 0x88424142, 0x883a3d3a, 0x883a3d3a, 0x883a3d3a, 0x883a3d3a, + 0x883a3d3a, 0x883a3d3a, 0x883a3d3a, 0x883a3d3a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, + 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, + 0x88313531, 0x88313531, 0x88313531, 0x88313531, 0x88313131, 0x88313131, 0x88313131, 0x88313131, + 0x88313131, 0x88313131, 0x88313131, 0x88313131, 0x88312d31, 0x88312d31, 0x88312d31, 0x88312d31, + 0x88312d31, 0x88312d31, 0x88312d31, 0x88312d31, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, + 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, + 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, + 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, 0x88292d29, + 0x88312d31, 0x88312d31, 0x88312d31, 0x88312d31, 0x88312d31, 0x88312d31, 0x88312d31, 0x88312d31, + 0x88313131, 0x88313131, 0x88313131, 0x88313131, 0x88313131, 0x88313131, 0x88313131, 0x88313131, + 0x88313131, 0x88313131, 0x88313131, 0x88313131, 0x88313531, 0x88313531, 0x88313531, 0x88313531, + 0x88313531, 0x88313531, 0x88313531, 0x88313531, 0x88313531, 0x88313531, 0x88313531, 0x88313531, + 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, + 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, + 0x883a393a, 0x883a393a, 0x883a393a, 0x883a393a, 0x88313531, 0x88313531, 0x88313531, 0x88313531, + 0x88313531, 0x77313531, 0x77313531, 0x88313531, 0x88313131, 0x77313131, 0x77313131, 0x77313131, + 0x77292d29, 0x77292d29, 0x77292d29, 0x77292d29, 0x77292829, 0x77292829, 0x77292829, 0x77292829, + 0x77212021, 0x77212021, 0x77212021, 0x77212021, 0x77191819, 0x77191819, 0x77191819, 0x66101010, + 0x66101010, 0x660b0b0b, 0x660b0b0b, 0x660b0b0b, 0x55080808, 0x55080808, 0x55050505, 0x44050505, + 0x33000400, 0x33000400, 0x22000400, 0x22000300, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080408, 0x22080408, 0x44080408, 0x55080408, + 0x66191419, 0x66191419, 0x77423f42, 0x77423f42, 0x77424542, 0x77424542, 0x77606260, 0x77606260, + 0x77636163, 0x77636163, 0x88636163, 0x88636163, 0x886b696b, 0x886b696b, 0x886b696b, 0x886b696b, + 0x99737173, 0x99737173, 0x99737173, 0x99737173, 0x9973797b, 0x9973797b, 0x9973797b, 0x9973797b, + 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, + 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, + 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, + 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b797b, 0xaa7b7573, 0xaa7b7573, 0xaa7b7573, 0xaa7b7573, + 0xaa737573, 0xaa737573, 0xaa737573, 0xaa737573, 0xaa737573, 0xaa737573, 0xaa737573, 0xaa737573, + 0xaa737573, 0xaa737573, 0xaa737573, 0xaa737573, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, + 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, + 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b696b, 0xaa6b696b, 0xaa6b696b, 0xaa6b696b, + 0xaa6b696b, 0xaa6b696b, 0xaa6b696b, 0xaa6b696b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, + 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, + 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, + 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, + 0xaa736d73, 0xaa736d73, 0xaa736d73, 0xaa736d73, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa737573, 0xaa737573, 0xbb737573, 0xbb737573, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b696b, 0xaa6b696b, 0xaa6b696b, 0xaa6b696b, + 0xaa6b696b, 0xaa6b696b, 0xaa6b696b, 0xaa6b696b, 0xaa636563, 0xaa636563, 0xaa636563, 0xaa636563, + 0x995a5d5a, 0x995a5d5a, 0x995a5d5a, 0x995a5d5a, 0x99525552, 0x99525552, 0x99525552, 0x88525552, + 0x88424542, 0x88424542, 0x88424542, 0x88424542, 0x88312d31, 0x88312d31, 0x88312d31, 0x88312d31, + 0x88191c19, 0x77191c19, 0x77191c19, 0x77191c19, 0x66080c08, 0x44080c08, 0x33080c08, 0x22080c08, + 0x11080408, 0x00080408, 0x00080408, 0x00080408, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x55080408, 0x77343134, 0x88605d60, 0x88605d60, + 0x886b6b6b, 0x886b6b6b, 0x886b6b6b, 0x996b6b6b, 0x997e807e, 0x997e807e, 0xaa7e807e, 0xaa7e807e, + 0xaa898a89, 0xaa898a89, 0xaa898a89, 0xaa898a89, 0xbb8c8f8c, 0xbb8c8f8c, 0xbb8c8f8c, 0xbb8c8f8c, + 0xbb949494, 0xbb949494, 0xbb949494, 0xcc949494, 0xcc949797, 0xcc949797, 0xcc949797, 0xcc949797, + 0xcc979a97, 0xcc979a97, 0xcc979a97, 0xcc979a97, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, + 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, + 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, + 0xcc9c9d9c, 0xcc9c9d9c, 0xcc9c9d9c, 0xcc9c9d9c, 0xcc9c9b9a, 0xcc9c9b9a, 0xcc9c9b9a, 0xcc9c9b9a, + 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, + 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, + 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, + 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, + 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, + 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, + 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9d9c, 0xcc9c9d9c, 0xcc9c9d9c, 0xcc9c9d9c, + 0xcc9c9d9c, 0xcc9c9d9c, 0xcc9c9d9c, 0xcc9c9d9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, + 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, + 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, + 0xcc9c9b9c, 0xcc9c9b9c, 0xcc9c9b9c, 0xcc9c9b9c, 0xcc9c9b9c, 0xcc9c9b9c, 0xcc9c9b9c, 0xcc9c9b9c, + 0xcc9f9b9f, 0xcc9f9b9f, 0xcc9f9b9f, 0xcc9f9b9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, 0xcc9f9d9f, + 0xcc9a9d9f, 0xcc9a9d9f, 0xcc9a9d9f, 0xcc9a9d9f, 0xcc9a9a9a, 0xcc9a9a9a, 0xcc9a9a9a, 0xcc9a9a9a, + 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9b9a, 0xcc9a9a9a, 0xcc9a9a9a, 0xcc9a9a9a, 0xcc9a9a9a, + 0xcc9a979a, 0xcc9a979a, 0xcc9a979a, 0xcc9a979a, 0xcc9a979a, 0xcc9a979a, 0xcc9a979a, 0xcc9a979a, + 0xcc9a979a, 0xcc9a979a, 0xcc9a979a, 0xcc9a979a, 0xcc94979a, 0xcc94979a, 0xcc94979a, 0xcc94979a, + 0xcc979697, 0xcc979697, 0xcc979697, 0xcc979697, 0xcc919291, 0xcc919291, 0xcc919291, 0xcc919291, + 0xcc919291, 0xcc919291, 0xcc919291, 0xcc919291, 0xcc8f908f, 0xcc8f908f, 0xcc8f908f, 0xcc8f908f, + 0xcc8c8b8c, 0xcc8c8b8c, 0xcc8c8b8c, 0xcc8c8b8c, 0xbb848884, 0xbb848884, 0xbb848884, 0xbb848884, + 0xbb7e7d7e, 0xbb7e7d7e, 0xbb7e7d7e, 0xbb7e7d7e, 0xaa737073, 0xaa737073, 0xaa737073, 0xaa737073, + 0xaa6b6b6b, 0x996b6b6b, 0x99424342, 0x99424342, 0x99373937, 0x88373937, 0x77373937, 0x66080c08, + 0x66080408, 0x22080408, 0x00080408, 0x00080408, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x33000000, 0x77262626, 0x88605d60, 0x88605d60, 0x998c8a8c, 0xaa8c8a8c, + 0xaa949694, 0xaa949694, 0xbb949694, 0xbb949694, 0xbb9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, + 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9ca29c, 0xcc9ca29c, 0xdd9ca29c, 0xdd9ca29c, + 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, + 0xdda5aaa5, 0xdda5aaa5, 0xdda5aaa5, 0xdda5aaa5, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xdda5aaad, 0xdda5aaad, 0xdda5aaad, 0xdda5aaad, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, + 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, + 0xdda5a2a5, 0xdda5a2a5, 0xdda5a2a5, 0xdda5a2a5, 0xdd9ca29c, 0xdd9ca29c, 0xdd9ca29c, 0xdd9ca29c, + 0xdd9c9a9c, 0xdd9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc949294, 0xcc949294, 0xcc949294, 0xcc949294, + 0xcc949294, 0xcc949294, 0xcc949294, 0xbb6b6b6b, 0xbb656565, 0xbb656565, 0xaa656565, 0xaa656565, + 0xbb656265, 0x77373337, 0x44080408, 0x11080408, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x33000000, 0x884d4c4d, 0x99737173, 0xaa8c8a8c, 0xaa8c8a8c, 0xcc8c8a8c, 0xcc8c8a8c, + 0xcc949694, 0xcc949694, 0xdd949694, 0xdd949694, 0xdd9c9e9c, 0xdd9c9e9c, 0xdd9c9e9c, 0xdd9c9e9c, + 0xdd9c9e9c, 0xdd9c9e9c, 0xdd9c9e9c, 0xdd9c9e9c, 0xdd9ca29c, 0xdd9ca29c, 0xdd9ca29c, 0xdd9ca29c, + 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, + 0xdda5aaa5, 0xdda5aaa5, 0xdda5aaa5, 0xdda5aaa5, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xdda5aaad, 0xdda5aaad, 0xdda5aaad, 0xdda5aaad, + 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xddadaaad, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, + 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, + 0xdda5a2a5, 0xdda5a2a5, 0xdda5a2a5, 0xdda5a2a5, 0xdd9ca29c, 0xdd9ca29c, 0xdd9ca29c, 0xdd9ca29c, + 0xdd9c9a9c, 0xdd9c9a9c, 0xdd9c9a9c, 0xdd9c9a9c, 0xdd949294, 0xdd949294, 0xdd949294, 0xdd949294, + 0xdd949294, 0xdd949294, 0xdd949294, 0xdd949294, 0xdd949294, 0xcc949294, 0xcc949294, 0xcc949294, + 0xee949294, 0xbb656265, 0x99373337, 0x55080408, 0x11080808, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11100c10, 0x773c393a, 0x9994928c, 0xbb94928c, 0xcc8f908f, 0xcc8f908f, 0xdd9ca29c, 0xdd9ca29c, + 0xdda5a1a2, 0xdda5a1a2, 0xdda5a1a2, 0xdda5a1a2, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, + 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, + 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, + 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, + 0xdda7a6a7, 0xddb5b2b5, 0xddb5b2b5, 0xdda7a6a7, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddb5aead, 0xddb5aead, 0xddb5aead, 0xddb5aead, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb2b3b2, 0xddb2b3b2, 0xddb2b3b2, 0xddb2b3b2, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xdda7a6a7, + 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, + 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, + 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, + 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdd9a9a9a, 0xdd9a9a9a, 0xdd9a9a9a, + 0xdd9a9a9a, 0xdd9a9a9a, 0xdd9a9a9a, 0xdd9a9a9a, 0xdd9a979a, 0xdd9a979a, 0xdd9a979a, 0xdd9a979a, + 0xeea5a2a5, 0xdd8c8b8c, 0xbb8c8b8c, 0xaa5a5d5a, 0x662c2d2c, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x44100c10, 0x99686563, 0xbb94928c, 0xcc94928c, 0xdd9ca29c, 0xcc8f908f, 0xdd9ca29c, 0xdd9ca29c, + 0xdda5a1a2, 0xdda5a1a2, 0xdda5a1a2, 0xdda5a1a2, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, + 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, + 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, + 0xddb5b2b5, 0xddb5b2b5, 0xdda7a6a7, 0xdda7a6a7, 0xddb5b2b5, 0xdda7a6a7, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, + 0xddb5aead, 0xddb5aead, 0xddb5aead, 0xddb5aead, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb2b3b2, 0xddb2b3b2, 0xddb2b3b2, 0xddb2b3b2, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xdda7a6a7, 0xddb5b2b5, + 0xddb5b2b5, 0xddb5b2b5, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, + 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a9a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, + 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdda7a6a7, 0xdd9a9a9a, + 0xdd9a9a9a, 0xdd9a9a9a, 0xdd9a9a9a, 0xdd9a9a9a, 0xdd9a979a, 0xdd9a979a, 0xdd9a979a, 0xdd9a979a, + 0xeea5a2a5, 0xeea5a2a5, 0xdd8c8b8c, 0xcc8c8b8c, 0xbb585958, 0x332c2d2c, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00050405, + 0x773c393a, 0xbb94928c, 0xcc94928c, 0xdd94928c, 0xdd9ca29c, 0xdd817f81, 0xff736d73, 0xff817f81, + 0xff847d7b, 0xff948f8f, 0xff948f8f, 0xff948f8f, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c928c, 0xff8c928c, 0xff8c928c, 0xff8c928c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c928c, 0xff8c928c, 0xff8c928c, 0xff8c928c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8a8c, 0xff8c8a8c, 0xff8c8a8c, 0xff8c8a8c, + 0xffa5a2a5, 0xeea5a2a5, 0xdda5a2a5, 0xdda5a2a5, 0xdd848684, 0x77585958, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11100c10, + 0x88686563, 0xcc94928c, 0xdd94928c, 0xdd94928c, 0xdd9ca29c, 0xdd817f81, 0xff817f81, 0xff8f908f, + 0xffa5a1a2, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffb5aead, 0xffb5aead, 0xffb5aead, 0xffb5aead, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, + 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, + 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffbdbabd, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, + 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb5bab5, 0xffb2b3b2, 0xffb2b3b2, 0xffb2b3b2, 0xffb2b3b2, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, + 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, + 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffb5b2b5, 0xffa7a5a7, + 0xffa5a2a5, 0xeea5a2a5, 0xdda5a2a5, 0xdda5a2a5, 0xdd848684, 0xaa585958, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22191419, + 0x99636163, 0xcc898a89, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda7a6a7, 0xdd949294, 0xff949294, 0xffa7a6a7, + 0xffbdbebd, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffd0d2d0, 0xffd0d2d0, 0xffd0d2d0, 0xffbdbebd, + 0xffb2b2b2, 0xee9c9a9c, 0xdd9c9a9c, 0xdd9c9a9c, 0xdd9c9e9c, 0xbb686968, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33191419, + 0xaa636163, 0xdd898a89, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda7a6a7, 0xdd949294, 0xffa7a6a7, 0xffbababa, + 0xffd0d2d0, 0xffe4e7e4, 0xffe4e7e4, 0xffe4e7e4, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, + 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffeff0ef, 0xffe4e7e4, 0xffe4e7e4, 0xffe4e7e4, 0xffd0d2d0, + 0xffb2b2b2, 0xeea7a6a7, 0xdd9c9a9c, 0xdd9c9a9c, 0xdd9c9e9c, 0xcc686968, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33100d10, + 0xaa636163, 0xdd898a89, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda7a6a7, 0xdd949294, 0xffa7a6a7, 0xffcecece, + 0xffe4e7e4, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xffe4e7e4, + 0xffbdbebd, 0xeea7a6a7, 0xdd9c9a9c, 0xdd9c9a9c, 0xdd9c9e9c, 0xcc686968, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33100d10, + 0xaa636163, 0xdd898a89, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda7a6a7, 0xdd949294, 0xffbababa, 0xffcecece, + 0xffe4e7e4, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7fbf7, 0xfff7fbf7, 0xfff7fbf7, 0xffe4e7e4, + 0xffbdbebd, 0xeea7a6a7, 0xdd9c9a9c, 0xdd9c9a9c, 0xdd9c9e9c, 0xcc9c9e9c, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33101010, + 0xaa4a5152, 0xdd868a89, 0xdda5a6a5, 0xdda5a6a5, 0xddadadad, 0xdd9c9a9c, 0xffadadad, 0xffced2ce, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffbdbebd, 0xeea7a9a7, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda5aaa5, 0xcc6e736e, 0x00000400, 0x00000300, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22191819, + 0x994a5152, 0xdd868a89, 0xdda5a6a5, 0xdda5a6a5, 0xddadadad, 0xdd9c9a9c, 0xffadadad, 0xffced2ce, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffbdbebd, 0xeea7a9a7, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda5aaa5, 0xbb6e736e, 0x00000400, 0x00000400, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101010, + 0x994a5152, 0xcc868a89, 0xdda5a6a5, 0xdda5a6a5, 0xddadadad, 0xdd9c9a9c, 0xffadadad, 0xffced2ce, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffbdbebd, 0xeea7a9a7, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda5aaa5, 0xbb6e736e, 0x00000400, 0x00000400, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101010, + 0x994a5152, 0xcc868a89, 0xdda5a6a5, 0xdda5a6a5, 0xddadadad, 0xdd9c9a9c, 0xffadadad, 0xffced2ce, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffbdbebd, 0xeea7a9a7, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda5aaa5, 0xbb6e736e, 0x00000400, 0x00000400, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101010, + 0x884a494a, 0xcc868486, 0xdda5a2a5, 0xdda5a2a5, 0xddadaead, 0xdd9c9a9c, 0xffadaead, 0xffced7ce, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffc5c2c5, 0xeeaaaaaa, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda5aaa5, 0xaa6e716e, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11101010, + 0x884a494a, 0xcc868486, 0xdda5a2a5, 0xdda5a2a5, 0xddadaead, 0xdd9c9a9c, 0xffadaead, 0xffced7ce, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffc5c2c5, 0xeeaaaaaa, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda5aaa5, 0xaa6e716e, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101010, + 0x884a494a, 0xcca5a2a5, 0xdda5a2a5, 0xdda5a2a5, 0xddadaead, 0xdd9c9a9c, 0xffadaead, 0xffced7ce, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffc5c2c5, 0xeeaaaaaa, 0xdd9c9e9c, 0xdd9c9e9c, 0xdda5aaa5, 0xaa6e716e, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101010, + 0x994a494a, 0xcca5a2a5, 0xdda5a2a5, 0xdda5a2a5, 0xddadaead, 0xdd9c9a9c, 0xffadaead, 0xffced7ce, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffc5c2c5, 0xeeaaaaaa, 0xdd9c9e9c, 0xddaaaaaa, 0xdda5aaa5, 0xaa6e716e, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101310, + 0x995a595a, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xddafaeaf, 0xdd9c9a9c, 0xffafaeaf, 0xffd6d7d6, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffc5c2c5, 0xeeafadaf, 0xdda5a2a5, 0xdda5a2a5, 0xddb5b6b5, 0xbb797b79, 0x00000400, 0x00000400, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101310, + 0x995a595a, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xddafaeaf, 0xdd9c9a9c, 0xffafaeaf, 0xffd6d7d6, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffc5c2c5, 0xeeafadaf, 0xdda5a2a5, 0xdda5a2a5, 0xddb5b6b5, 0xbb797b79, 0x00000400, 0x00000400, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101310, + 0xaa5a595a, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xddafaeaf, 0xdd9c9a9c, 0xffafaeaf, 0xffd6d7d6, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffc5c2c5, 0xeeafadaf, 0xdda5a2a5, 0xddafadaf, 0xddb5b6b5, 0xcc797b79, 0x00000400, 0x00000400, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33101310, + 0xaa737373, 0xdda5a6a5, 0xdda5a6a5, 0xdda5a6a5, 0xddafaeaf, 0xdd9c9a9c, 0xffafaeaf, 0xffd6d7d6, + 0xffe6ebe6, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xffe6ebe6, + 0xffc5c2c5, 0xeeafadaf, 0xdda5a2a5, 0xddafadaf, 0xddb5b6b5, 0xcc797b79, 0x00000400, 0x00000400, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33101010, + 0xaa606060, 0xddada6ad, 0xddada6ad, 0xddada6ad, 0xddbab7ba, 0xdd949294, 0xffbab7ba, 0xffcecace, + 0xffeff0ef, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffeff0ef, + 0xffc5c2c5, 0xeea5aaa5, 0xdda5aaa5, 0xdda5aaa5, 0xddadaeb5, 0xcc737479, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33080808, + 0xaa606060, 0xddada6ad, 0xddada6ad, 0xddada6ad, 0xddbab7ba, 0xdd949294, 0xffbab7ba, 0xffcecace, + 0xffeff0ef, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffeff0ef, + 0xffc5c2c5, 0xeea5aaa5, 0xdda5aaa5, 0xdda5aaa5, 0xddadaeb5, 0xbb737479, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33191819, + 0x99606060, 0xccada6ad, 0xddada6ad, 0xddada6ad, 0xddbab7ba, 0xdd949294, 0xffa7a5a7, 0xffcecace, + 0xffdee1de, 0xffeff0ef, 0xffffffff, 0xffffffff, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, + 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xfff7f8f7, 0xffffffff, 0xffffffff, 0xffeff0ef, 0xffdee1de, + 0xffc5c2c5, 0xeea5aaa5, 0xdda5aaa5, 0xdda5aaa5, 0xddadaeb5, 0xbb737479, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22101010, + 0x883a3d3a, 0xbb868386, 0xddada6ad, 0xddada6ad, 0xddbab7ba, 0xdd949294, 0xffa7a5a7, 0xffbab7ba, + 0xffced2ce, 0xffdee1de, 0xffeff0ef, 0xffeff0ef, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffeff0ef, 0xffeff0ef, 0xffdee1de, 0xffced2ce, + 0xffbababa, 0xeea5aaa5, 0xdda5aaa5, 0xdda5aaa5, 0xddadaeb5, 0x99737479, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11080808, + 0x773a3a3a, 0xaa6b6c6b, 0xcc9c9e9c, 0xdd9c9e9c, 0xddadaaad, 0xdd949294, 0xff949294, 0xffadaaad, + 0xffbdbebd, 0xffcecece, 0xffcecece, 0xffcecece, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffced0ce, + 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffced1d3, 0xffced1d3, 0xffced1d3, 0xffced1d3, + 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, 0xffd0d1d0, + 0xffced1ce, 0xffced1ce, 0xffced1ce, 0xffced1ce, 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffced0ce, + 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffced0ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, + 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffced2ce, 0xffb8bcb8, + 0xffadaead, 0xeeadaead, 0xddadaead, 0xddadaead, 0xcc848a84, 0x772c2e2c, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x66080808, 0x883a3a3a, 0xaa6b6c6b, 0xcc9c9e9c, 0xddadaaad, 0xccadaaad, 0xddadaaad, 0xddadaaad, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddb2b2b2, 0xddb2b2b2, 0xddb2b2b2, 0xddb2b2b2, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddc3c2c3, 0xddc3c2c3, 0xddc3c2c3, 0xddc3c2c3, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, + 0xddc5c2c5, 0xddc5c2c5, 0xddc8c8c8, 0xddc8c8c8, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, + 0xddc5c6c5, 0xddc5c6c5, 0xddc8cac8, 0xddc8cac8, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, + 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, + 0xddd0d1d0, 0xddd3d0d3, 0xddd0d1d0, 0xddd0d1d0, 0xddd6d2d6, 0xddd6d2d6, 0xddd6d2d6, 0xddd6d2d6, + 0xddd0d4d0, 0xddd0d4d0, 0xddd0d4d0, 0xddd0d4d0, 0xddd0d4d0, 0xddd0d4d0, 0xddd6d7d6, 0xddd6d7d6, + 0xddd3d8d3, 0xddd3d8d3, 0xddd3d8d3, 0xddd3d8d3, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, + 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd3d7d3, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, + 0xddd9d8d9, 0xdddedbde, 0xddd9d8d9, 0xddd9d8d9, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, + 0xdddedbde, 0xdddedbde, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, + 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd3d8d3, 0xddd3d8d3, 0xddd3d8d3, 0xddd3d8d3, + 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd3d5d3, 0xddd3d5d3, 0xddd0d4d0, 0xddd0d4d0, 0xddd0d4d0, + 0xddd3d5d3, 0xddd3d5d3, 0xddced2ce, 0xddced2ce, 0xddd0d1d0, 0xddd0d1d0, 0xddd0d1d0, 0xddd0d1d0, + 0xddcecece, 0xddced0ce, 0xddcecece, 0xddcecece, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, + 0xddcecdce, 0xddcecdce, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, + 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, + 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, + 0xddadadad, 0xddadadad, 0xddadadad, 0xddadadad, 0xdda2a5a2, 0xdda2a5a2, 0xdda2a5a2, 0xdda2a5a2, + 0xeeadaead, 0xeeadaead, 0xcc818381, 0xbb818381, 0xaa585c58, 0x442c2e2c, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33080808, 0x883a3a3a, 0x883a3a3a, 0xaa6b6c6b, 0xcc949294, 0xbb949294, 0xccadaaad, 0xddadaaad, + 0xddadaead, 0xddadaead, 0xddadaead, 0xddadaead, 0xddb2b2b2, 0xddb2b2b2, 0xddb2b2b2, 0xddb2b2b2, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddc3c2c3, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddc3c2c3, 0xddc3c2c3, 0xddc3c2c3, 0xddc3c2c3, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc8c8c8, + 0xddc8c8c8, 0xddc8c8c8, 0xddc8c8c8, 0xddc8c8c8, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc8cac8, + 0xddc8cac8, 0xddc8cac8, 0xddc8cac8, 0xddcbcecb, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, + 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddced0d0, 0xddced0d0, 0xddced0d0, 0xddced2d6, + 0xddced2ce, 0xddd0d1d0, 0xddd0d1d0, 0xddd0d1d0, 0xddd6d2d6, 0xddd6d2d6, 0xddd6d2d6, 0xddd3d4d3, + 0xddd3d5d3, 0xddd3d5d3, 0xddd3d5d3, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, + 0xddd3d8d3, 0xddd3d8d3, 0xddd3d8d3, 0xddd6dbd6, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, + 0xddd9d8d9, 0xddd9d8d9, 0xdddedbde, 0xdddedbde, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xddd9d8d9, 0xddd9d8d9, + 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd9d8d9, 0xddd3d8d3, 0xddd6dbd6, 0xddd3d8d3, 0xddd6dbd6, + 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd3d5d3, 0xddd3d5d3, 0xddd3d5d3, + 0xddd3d5d3, 0xddd6d7d6, 0xddd3d5d3, 0xddd0d4d0, 0xddd0d1d0, 0xddd0d1d0, 0xddd0d1d0, 0xddd0d1d0, + 0xddced0ce, 0xddced0ce, 0xddced0ce, 0xddced0ce, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, + 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcec6ce, + 0xddc8cac8, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, + 0xddc8c8c8, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, + 0xddc3c5c3, 0xddbfc0bf, 0xddc2c4c2, 0xddbebfbe, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, + 0xddadadad, 0xddadadad, 0xddadadad, 0xddadadad, 0xdda2a5a2, 0xdda2a5a2, 0xdda2a5a2, 0xdda2a5a2, + 0xeeadaead, 0xdd818381, 0xbb818381, 0x99555855, 0x772c2e2c, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11080808, 0x66080808, 0x773a3a3a, 0x773a3a3a, 0x99636163, 0x997b797b, 0xbb949294, 0xbb949294, + 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcc9c9e9c, 0xcca5a2a5, 0xddb2b2b2, 0xddb2b2b2, 0xddb2b2b2, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddc3c2c3, 0xddc3c2c3, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddc3c5c3, 0xddc3c5c3, + 0xddc3c2c3, 0xddc3c2c3, 0xddc3c2c3, 0xddc3c2c3, 0xddc5c2c5, 0xddc8c8c8, 0xddc5c2c5, 0xddc8c8c8, + 0xddc8c8c8, 0xddc8c8c8, 0xddc8c8c8, 0xddc8c8c8, 0xddc8cac8, 0xddc5c6c5, 0xddc8cac8, 0xddcbcecb, + 0xddcbcecb, 0xddc8cac8, 0xddc8cac8, 0xddcbcecb, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, + 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddced0d0, 0xddced1d3, 0xddced1d3, 0xddced2d6, + 0xddced2ce, 0xddced2ce, 0xddced2ce, 0xddced2ce, 0xddd3d4d3, 0xddd3d4d3, 0xddd3d4d3, 0xddd0d5d0, + 0xddd6d7d6, 0xddd3d5d3, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, + 0xddd6dbd6, 0xddd3d8d3, 0xddd6dbd6, 0xddd6dbd6, 0xddd9d8d9, 0xdddedbde, 0xdddedbde, 0xdddedbde, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xddd9dbd9, 0xdddedfde, 0xdddedfde, 0xddd9dbd9, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xddd9dbd9, 0xddd9dbd9, 0xdddedfde, 0xdddedfde, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xddd9dbd9, 0xddd9dbd9, 0xddd9dbd9, 0xdddedfde, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, + 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xdddedbde, 0xddd6dbd6, 0xddd6dbd6, 0xddd3d8d3, 0xddd6dbd6, + 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd6d7d6, 0xddd3d5d3, 0xddd6d7d6, + 0xddd3d5d3, 0xddd6d7d6, 0xddd3d5d3, 0xddd0d4d0, 0xddd6d2d6, 0xddd6d2d6, 0xddd0d1d0, 0xddd0d1d0, + 0xddced2ce, 0xddced1ce, 0xddced0ce, 0xddced0ce, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, + 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecdce, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, + 0xddc8cac8, 0xddc5c6c5, 0xddc8cac8, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, + 0xddc8c8c8, 0xddc8c8c8, 0xddc8c8c8, 0xddc5c3c6, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, + 0xddc4c4c3, 0xddc4c4c3, 0xddc4c4c2, 0xddc1c0c1, 0xddbfc1bf, 0xddbdbebe, 0xddbdbebe, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, 0xddb5bab5, + 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddb5b2b5, 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, 0xddadb2b5, + 0xddadadad, 0xddadadad, 0xdd9c9a9c, 0xcc9c9a9c, 0xcca2a5a2, 0xcc8c8e8c, 0xcc8c8e8c, 0xcc8c8e8c, + 0xdd818381, 0xaa555855, 0x77292d29, 0x55292d29, 0x22000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x22000000, 0x77101010, 0x77313131, 0x773f3f3f, 0x773f3f3f, 0x885a5d5a, 0x995a5d5a, + 0x99737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa8c8a8c, 0xbb8c8a8c, 0xbb8c8a8c, 0xbb8c8a8c, + 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcc9c9a9c, 0xcca5a6a5, 0xcca5a6a5, 0xcca5a6a5, 0xcca5a6a5, + 0xccadaead, 0xccadaead, 0xccadaead, 0xccadaead, 0xccb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, + 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, 0xddb5b6b5, + 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbabd, 0xddbdbebd, 0xddbdbebd, 0xddbec0bf, 0xddc0c2c1, + 0xddc7cacc, 0xddc8cccd, 0xddc0c3c5, 0xddc2c6c9, 0xddc3c5c7, 0xddc3c3c4, 0xddc0c3c2, 0xddbfc2c0, + 0xddc3c2c3, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, + 0xddc5cac5, 0xddc5cac5, 0xddc5cac5, 0xddc5cac5, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, + 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, + 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, + 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, 0xddcecece, + 0xddced2ce, 0xddced2ce, 0xddced2ce, 0xddced2ce, 0xddced2ce, 0xddced2ce, 0xddced2ce, 0xddced2ce, + 0xddcecfce, 0xddcfd0cf, 0xddd2d0d0, 0xddd1d3d2, 0xddd7d9d7, 0xddd9dad8, 0xdddbdddb, 0xdddde0de, + 0xdde0e3e2, 0xdde2e2e3, 0xdde2e3e1, 0xdde3e3e4, 0xdde5e3e5, 0xdde4e3e4, 0xdde3e0e2, 0xdddfdcdf, + 0xddd3d1d0, 0xddcecece, 0xddcfd0cf, 0xddd1d0d0, 0xddd5d6d4, 0xddd5d4d5, 0xddd5d4d4, 0xddd2d1d2, + 0xddd0cdd0, 0xddcfccd0, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, 0xddcecace, + 0xddc5cace, 0xddc5cace, 0xddc5cace, 0xddc5cace, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, + 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, + 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddc5c2c5, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, 0xddbdbebd, + 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc5c6c5, 0xddc8c8c9, 0xddc9c8ca, 0xddc9cbcb, 0xddcacdcc, + 0xddc9c7c8, 0xddc8c8c9, 0xddcac8ca, 0xddc8c7c9, 0xddc6c7c6, 0xddc2c6c3, 0xddc2c3c1, 0xddc4c7c3, + 0xddb9bab9, 0xddb8b6b8, 0xddb7b7b7, 0xddbababa, 0xddbcbfbc, 0xddbcc0bc, 0xddbdc2bd, 0xddbdc2bd, + 0xddb5b6b5, 0xddb5b6b5, 0xccb5b6b5, 0xccb5b6b5, 0xccadb2ad, 0xccadb2ad, 0xccadb2ad, 0xccadb2ad, + 0xcca5a6a5, 0xcca5a6a5, 0xcca5a6a5, 0xcca5a6a5, 0xcc9c9a94, 0xcc9c9a94, 0xcc9c9a94, 0xcc9c9a94, + 0xbb84827b, 0xbb84827b, 0xbb84827b, 0xaa84827b, 0xaa6b6d6b, 0xaa6b6d6b, 0x996b6d6b, 0x99474947, + 0xbb524d52, 0x661b1a1b, 0x44000000, 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x22000000, 0x66101010, 0x77242224, 0x663f3f3f, 0x663f3f3f, 0x663f3f3f, + 0x77504e50, 0x77504e50, 0x77504e50, 0x77504e50, 0x88656565, 0x88656565, 0x88656565, 0x99656565, + 0x99767476, 0x99767476, 0x99767476, 0xaa767476, 0xaa7e7f7e, 0xaa7e7f7e, 0xaa7e7f7e, 0xaa7e7f7e, + 0xaa868786, 0xaa868786, 0xbb868786, 0xbb868786, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, + 0xbb949494, 0xbb949494, 0xbb949494, 0xbb949494, 0xcc9c989c, 0xcc9c989c, 0xcc9c989c, 0xcc9c989c, + 0xccb5b6b5, 0xccb5b6b5, 0xccb5b6b5, 0xccb5b6b5, 0xccb5b6b5, 0xccb5b6b5, 0xccb5b6b5, 0xccb5b6b5, + 0xccbdbabd, 0xccbdbabd, 0xccbdbabd, 0xccbdbabd, 0xccbdbebd, 0xccbdbebd, 0xccbcbdbc, 0xccb9baba, + 0xccb1b3b4, 0xccb2b4b4, 0xccb2b5b5, 0xccb3b5b6, 0xccb1b4b6, 0xccb3b5b6, 0xccb4b8b8, 0xccb7b9b9, + 0xccc0c0c2, 0xccc5c2c5, 0xccc5c2c5, 0xccc5c2c5, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, + 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccc5c6c5, 0xccc5c6c5, 0xccc5c6c5, 0xccc5c6c5, + 0xccc5cac5, 0xccc5cac5, 0xccc5cac5, 0xccc5cac5, 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, + 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, + 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, + 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, 0xcccecece, + 0xccced2ce, 0xccced2ce, 0xccced2ce, 0xccced2ce, 0xccced2ce, 0xccced2ce, 0xccced2ce, 0xccced2ce, + 0xcccecfce, 0xcccdcecd, 0xcccdcdcd, 0xcccbcbca, 0xccc7c8c7, 0xccc3c5c5, 0xccc3c4c4, 0xccc2c3c2, + 0xccbec1bf, 0xccbbbdbc, 0xccb7b8b6, 0xccb0b2b0, 0xccaeb1af, 0xccb0b1b0, 0xccb5b4b4, 0xccbcbabb, + 0xcca3a6a3, 0xccb8bab7, 0xccc9c9c7, 0xccc9c7c8, 0xccacacac, 0xccb5b3b7, 0xccb8b5b7, 0xccb7b5b5, + 0xccb0aeb1, 0xccb7b6b5, 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, 0xcccecace, + 0xccc5cace, 0xccc5cace, 0xccc5cace, 0xccc5cace, 0xccc5c6c5, 0xccc5c6c5, 0xccc5c6c5, 0xccc5c6c5, + 0xccc5c6c5, 0xccc5c6c5, 0xccc5c6c5, 0xccc5c6c5, 0xccc5c2c5, 0xccc5c2c5, 0xccc5c2c5, 0xccc5c2c5, + 0xccc5c2c5, 0xccc5c2c5, 0xccc5c2c5, 0xccc5c2c5, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, + 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, 0xccbdbebd, + 0xccc5c6c5, 0xccc5c6c5, 0xccabaeac, 0xcca5a6a5, 0xcca8a9a8, 0xccaeadac, 0xccaeacab, 0xccb5b5b4, + 0xccbcbdbd, 0xccb0b1b2, 0xcca9a9a9, 0xcca5a4a6, 0xcc9f9fa1, 0xcc9da09f, 0xcc9ca09e, 0xccafb3b1, + 0xccacadab, 0xcca8a9a7, 0xcca0a09f, 0xcc999a99, 0xbb939492, 0xbb8d918e, 0xbb8c908c, 0xbb8c908c, + 0xbb868686, 0xbb868686, 0xbb868686, 0xbb868686, 0xbb7b7f7b, 0xbb7b7f7b, 0xaa7b7f7b, 0xaa7b7f7b, + 0xaa737370, 0xaa737370, 0xaa737370, 0xaa737370, 0x99686763, 0x99686763, 0x99686763, 0x99686763, + 0x995a5955, 0x885a5955, 0x885a5955, 0x8831312f, 0x77242424, 0x77242424, 0x77242424, 0x66242424, + 0x661b1a1b, 0x33000000, 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x44080408, 0x66080408, 0x66242224, 0x66242224, + 0x662c2b2c, 0x662c2b2c, 0x662c2b2c, 0x662c2b2c, 0x663f413f, 0x663f413f, 0x663f413f, 0x663f413f, + 0x77504e50, 0x77504e50, 0x77504e50, 0x77504e50, 0x77585858, 0x77585858, 0x77585858, 0x77585858, + 0x88606060, 0x88606060, 0x88606060, 0x88606060, 0x88636563, 0x88636563, 0x88636563, 0x88636563, + 0x886b6b6b, 0x886b6b6b, 0x996b6b6b, 0x996b6b6b, 0x99736f73, 0x99736f73, 0x99736f73, 0x99736f73, + 0x996e6d6e, 0x996e6d6e, 0x996e6d6e, 0x996e6d6e, 0x996e706e, 0x996e706e, 0x996e706e, 0x996e706e, + 0x99707170, 0x99707170, 0x99707170, 0x99707170, 0xaa767576, 0x99767576, 0xaa767576, 0xaa767576, + 0xaa7b7c7e, 0xaa7b7c7e, 0xaa7b7c7f, 0xaa7d7e80, 0xaa7a7a7c, 0xaa7b7a7c, 0xaa787979, 0xaa777677, + 0xaa797979, 0xaa797979, 0xaa797979, 0xaa797979, 0xaa979694, 0xaa979694, 0xaa979694, 0xaa979694, + 0xaa949694, 0xaa949694, 0xaa949694, 0xaa949694, 0xaa797b79, 0xaa797b79, 0xaa797b79, 0xaa797b79, + 0xaa797979, 0xaa797979, 0xaa797979, 0xaa797979, 0xaa7b7976, 0xaa7b7976, 0xaa7b7976, 0xaa7b7976, + 0xaa767776, 0xaa767776, 0xaa767776, 0xaa767776, 0xaa767776, 0xaa767776, 0xaa767776, 0xaa767776, + 0xaa767576, 0x99767576, 0x99767576, 0x99767576, 0x99767876, 0x99767876, 0x99767876, 0x99767876, + 0x99767576, 0x99767576, 0x99767576, 0x99767576, 0x99767576, 0x99767576, 0x99767576, 0x99767576, + 0x99767776, 0x99767776, 0x99767776, 0x99767776, 0x99707770, 0x99707770, 0x99707770, 0x99707770, + 0x99707370, 0x99707370, 0x99707370, 0x99717571, 0x99787c79, 0x99787d79, 0x99787d79, 0x99797d79, + 0x99787d79, 0x99797d79, 0x99797d78, 0x99797d79, 0x99797c79, 0x99797c79, 0x99797c79, 0x99797c78, + 0x99747672, 0x99727672, 0x99727371, 0x99707371, 0x99797879, 0x99797878, 0x99797879, 0x99787879, + 0x99777577, 0xaa777676, 0xaa767476, 0xaa767476, 0xaa767476, 0xaa767476, 0xaa767476, 0xaa767476, + 0xaa6e7170, 0xaa6e7170, 0xaa6e7170, 0xaa6e7170, 0xaa737373, 0xaa737373, 0xaa737373, 0xaa737373, + 0xaa737373, 0xaa737373, 0xaa737373, 0xaa737373, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, + 0xaa737173, 0xaa737173, 0xaa737173, 0xaa737173, 0xaa707070, 0xaa707070, 0xaa707070, 0xaa707070, + 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, 0xaa6b6d6b, + 0x996e706e, 0xaa6f716f, 0x99747673, 0x99757774, 0x99767676, 0x99777876, 0x99737373, 0x99737272, + 0x99757577, 0x996e6e72, 0x996b6c70, 0x996b6c70, 0x99686c68, 0x99686c68, 0x99686c68, 0x996b6f6b, + 0x99636563, 0x995d5e5d, 0x995d5e5d, 0x995d5e5d, 0x995a5e5a, 0x885a5e5a, 0x885a5e5a, 0x885a5e5a, + 0x88585558, 0x88585558, 0x88585558, 0x88585558, 0x884a4c4a, 0x884a4c4a, 0x884a4c4a, 0x884a4c4a, + 0x77423f3c, 0x77423f3c, 0x77423f3c, 0x77423f3c, 0x77343331, 0x77343331, 0x77343331, 0x77343331, + 0x6631312f, 0x66080808, 0x66080808, 0x66080808, 0x66000000, 0x66000000, 0x55000000, 0x33000000, + 0x44000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080408, 0x11080408, 0x22080408, 0x33080408, + 0x44080808, 0x55080808, 0x55080808, 0x66080808, 0x66191c19, 0x66191c19, 0x66191c19, 0x66191c19, + 0x66292829, 0x66292829, 0x66292829, 0x66292829, 0x66313131, 0x66313131, 0x66313131, 0x66313131, + 0x663a393a, 0x663a393a, 0x663a393a, 0x663a393a, 0x663a3d3a, 0x663a3d3a, 0x663a3d3a, 0x663a3d3a, + 0x66424142, 0x66424142, 0x66424142, 0x66424142, 0x664a454a, 0x664a454a, 0x664a454a, 0x664a454a, + 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, + 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x77525152, 0x77525152, 0x77525152, 0x77525152, + 0x77525152, 0x77525152, 0x77525152, 0x77525152, 0x77525152, 0x77525152, 0x77525152, 0x77525152, + 0x77525552, 0x77525552, 0x77525552, 0x77525552, 0x774a4542, 0x774a4542, 0x774a4542, 0x774a4542, + 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x77525552, 0x77525552, 0x77525552, 0x77525552, + 0x77525152, 0x77525152, 0x77525152, 0x77525152, 0x7752514a, 0x7752514a, 0x7752514a, 0x7752514a, + 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, + 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, 0x774a4d4a, + 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, + 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x77424942, 0x77424942, 0x77424942, 0x77424942, + 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x77424942, 0x77424942, 0x77424942, 0x77424942, + 0x77424942, 0x77424942, 0x77424942, 0x77424942, 0x77424942, 0x77424942, 0x77424942, 0x77424942, + 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, + 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, + 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, + 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, + 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, 0x774a494a, + 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x77424542, + 0x77424542, 0x77424542, 0x77424542, 0x77424542, 0x77424142, 0x77424142, 0x77424142, 0x77424142, + 0x773a3d42, 0x773a3d42, 0x773a3d42, 0x773a3d42, 0x773a3d3a, 0x773a3d3a, 0x773a3d3a, 0x773a3d3a, + 0x66313531, 0x66313531, 0x66313531, 0x66313531, 0x66292d29, 0x66292d29, 0x66292d29, 0x66292d29, + 0x66292429, 0x66292429, 0x66292429, 0x66292429, 0x66191819, 0x66191819, 0x66191819, 0x66191819, + 0x66100c08, 0x66100c08, 0x66100c08, 0x66100c08, 0x66000000, 0x66000000, 0x66000000, 0x66000000, + 0x66080808, 0x66080808, 0x66080808, 0x55080808, 0x44000000, 0x22000000, 0x11000000, 0x11000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x22000000, 0x22000000, 0x33000000, 0x44000000, + 0x44000000, 0x44000000, 0x55000000, 0x55000000, 0x55000400, 0x55000400, 0x55000400, 0x55000400, + 0x55080808, 0x66080808, 0x66080808, 0x66080808, 0x662f2f2f, 0x662f2f2f, 0x662f2f2f, 0x662f2f2f, + 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, + 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, + 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, + 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, + 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, + 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, 0x66312f31, + 0x662f2f2f, 0x662f2f2f, 0x662f2f2f, 0x662f2f2f, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, 0x66080808, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080408, + 0x66080408, 0x66080408, 0x66080408, 0x66080408, 0x66080400, 0x66080400, 0x66080400, 0x66080400, + 0x66000400, 0x66000400, 0x66000400, 0x66000400, 0x66000400, 0x66000400, 0x66000400, 0x66000400, + 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x66000000, + 0x66000000, 0x66000000, 0x66000000, 0x66000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x44000000, 0x44000000, 0x33000000, 0x33000000, + 0x22000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000400, 0x11000400, 0x11000400, 0x22000400, + 0x22080808, 0x22080808, 0x22080808, 0x22080808, 0x33000000, 0x33000000, 0x33000000, 0x33000000, + 0x33000000, 0x33000000, 0x33000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, + 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, + 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x55000000, 0x44000000, 0x44000000, 0x44000000, + 0x44000000, 0x44000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55000000, + 0x55000000, 0x55000000, 0x55000000, 0x55000000, 0x55080808, 0x44080808, 0x44080808, 0x44080808, + 0x55080808, 0x44080808, 0x44080808, 0x55080808, 0x55080808, 0x44080808, 0x44080808, 0x44080808, + 0x44080808, 0x44080808, 0x44080808, 0x44080808, 0x44080808, 0x44080808, 0x44080808, 0x44080808, + 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, + 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, + 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, + 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, + 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, + 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, + 0x44080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, + 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, + 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x55080408, + 0x55080408, 0x55080408, 0x55080408, 0x55080408, 0x44080408, 0x44080408, 0x44080408, 0x44080408, + 0x44080408, 0x44080408, 0x44080408, 0x44080408, 0x44080400, 0x44080400, 0x44080400, 0x44080400, + 0x44000400, 0x44000400, 0x44000400, 0x44000400, 0x44000400, 0x44000400, 0x44000400, 0x44000400, + 0x44000000, 0x44000000, 0x44000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, + 0x33000000, 0x33000000, 0x22000000, 0x22000000, 0x22000000, 0x22000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0x00000400, 0x00000400, 0x00000400, + 0x00080808, 0x00080808, 0x00080808, 0x00080808, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11080808, 0x11080808, 0x11080808, 0x11080808, + 0x11080808, 0x11080808, 0x11080808, 0x11080808, 0x11080808, 0x11080808, 0x11080808, 0x11080808, + 0x11080808, 0x11080808, 0x11080808, 0x11080808, 0x11080808, 0x11080808, 0x11080808, 0x11080808, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080408, + 0x11080408, 0x11080408, 0x11080408, 0x11080408, 0x11080400, 0x11080400, 0x11080400, 0x11080400, + 0x11000400, 0x11000400, 0x11000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000400, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xbb4d4e4d, 0xbb737573, 0xbb737573, + 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, + 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, + 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, + 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, + 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, + 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, + 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, 0xbb948e94, + 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, + 0xbb949294, 0xbb949294, 0xbb949294, 0xbb949294, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, 0xbb8c8e8c, + 0xbb737573, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xcc737573, 0xcc737573, 0xcc737573, + 0xcca5a6a5, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, + 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xccffffff, 0xcca5a6a5, 0xcca5a6a5, + 0xcc737173, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xdd737573, 0xdd737573, 0xddadaead, + 0xdda5a6a5, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, + 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddffffff, 0xddbabcba, 0xdda5a6a5, + 0xddadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xee737573, 0xeeadaead, 0xeeadaead, + 0xeebabcba, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeeffffff, 0xeed0d1d0, 0xeebabcba, + 0xeeadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xee737573, 0xeeadaead, 0xeeadaead, + 0xeed0d1d0, 0xeefffffe, 0xeeffffff, 0xeeffffff, 0xeefefffe, 0xfffefeff, 0xeefffeff, 0xeefefeff, + 0xeefeffff, 0xeefeffff, 0xeeffffff, 0xeefeffff, 0xeeffffff, 0xeefffefe, 0xeefffefe, 0xeefeffff, + 0xfffefefe, 0xeefefffe, 0xeefffffe, 0xeeffffff, 0xfffefffe, 0xeefffefe, 0xeeffffff, 0xeefffffe, + 0xfffefffe, 0xeefffeff, 0xeefeffff, 0xeefffeff, 0xffffffff, 0xeefffffe, 0xfffffefe, 0xfffffeff, + 0xeefeffff, 0xffffffff, 0xfffffffe, 0xeefffeff, 0xeefefffe, 0xffffffff, 0xeefffeff, 0xeefefffe, + 0xeefffffe, 0xeefffeff, 0xeefeffff, 0xeefeffff, 0xeefffffe, 0xeeffffff, 0xeeffffff, 0xeeffffff, + 0xeeffffff, 0xeefffeff, 0xfffeffff, 0xeefffffe, 0xeefffeff, 0xfffefffe, 0xeefffffe, 0xeeffffff, + 0xeefffefe, 0xffffffff, 0xeeffffff, 0xeefefefe, 0xeefefefe, 0xeeffffff, 0xeefffefe, 0xeefeffff, + 0xfffffffe, 0xeefffffe, 0xeefffefe, 0xeeffffff, 0xeefefeff, 0xeefefeff, 0xfffffeff, 0xfffffeff, + 0xffffffff, 0xeefeffff, 0xeefefeff, 0xeefffeff, 0xfffeffff, 0xeefffefe, 0xffffffff, 0xeefffffe, + 0xeeffffff, 0xfffffeff, 0xeefffffe, 0xeeffffff, 0xeefeffff, 0xfffefefe, 0xeefffeff, 0xeefffffe, + 0xeefffefe, 0xeefffeff, 0xfffefefe, 0xfffffffe, 0xeefffeff, 0xeefefeff, 0xeefffefe, 0xeeffffff, + 0xeefffeff, 0xeefefeff, 0xfffefeff, 0xeefefefe, 0xfffffffe, 0xfffefeff, 0xeefefeff, 0xeeffffff, + 0xeefefefe, 0xeefffffe, 0xeefefefe, 0xeefffeff, 0xfffefffe, 0xfffefefe, 0xeefefffe, 0xeefefffe, + 0xfffffffe, 0xffffffff, 0xeefeffff, 0xfffffefe, 0xeefefefe, 0xeefffefe, 0xfffefefe, 0xeefefeff, + 0xfffeffff, 0xeeffffff, 0xfffefefe, 0xfffefefe, 0xeefeffff, 0xeefeffff, 0xfffffefe, 0xeeffffff, + 0xeefffefe, 0xeefefffe, 0xeefefffe, 0xeefffeff, 0xfffffefe, 0xeeffffff, 0xfffefeff, 0xfffffefe, + 0xeefeffff, 0xeefefeff, 0xeefefeff, 0xeefffffe, 0xfffffefe, 0xeefffeff, 0xeefefffe, 0xeefefefe, + 0xeefeffff, 0xeefefefe, 0xeefeffff, 0xeefffeff, 0xeefeffff, 0xeeffffff, 0xfffffeff, 0xeeffffff, + 0xeefefffe, 0xfffefffe, 0xfffefffe, 0xeefffeff, 0xfffffeff, 0xeefefefe, 0xeefefffe, 0xeefefffe, + 0xeefefffe, 0xeefffeff, 0xeefffeff, 0xfffeffff, 0xeefffffe, 0xeeffffff, 0xeefffefe, 0xeefefefe, + 0xeefefeff, 0xeefefefe, 0xeefefeff, 0xeeffffff, 0xeeffffff, 0xfffefffe, 0xfffeffff, 0xeefffefe, + 0xeefffffe, 0xeefefefe, 0xeefffefe, 0xeefeffff, 0xeefffffe, 0xeefefefe, 0xeefefffe, 0xeefeffff, + 0xeefffeff, 0xfffffffe, 0xeefeffff, 0xeefeffff, 0xeefffffe, 0xeefffffe, 0xeefefffe, 0xeefffeff, + 0xeefefeff, 0xfffffffe, 0xeefefeff, 0xeefefffe, 0xeeffffff, 0xeefffefe, 0xeefefeff, 0xeefffffe, + 0xeefefffe, 0xeefffeff, 0xeefefeff, 0xfffeffff, 0xeefefeff, 0xeefffeff, 0xeefffffe, 0xeefffeff, + 0xeefffefe, 0xeefefeff, 0xeefefffe, 0xeefefeff, 0xeefffeff, 0xeefffffe, 0xeefffffe, 0xeefefeff, + 0xeefefefe, 0xfffffeff, 0xeefffefe, 0xeefefeff, 0xeefefefe, 0xfffeffff, 0xeee6e7e6, 0xeed0d1d0, + 0xeeadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff848384, 0xffc5c2c5, 0xffc5c2c5, + 0xffdedfde, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefeff, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefffe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefeff, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefffe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, + 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xfffefefe, 0xffe9e9e9, 0xffdedfde, + 0xffdedfde, 0x00060306, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff848384, 0xffc5c2c5, 0xffc5c2c5, + 0xffdedfde, 0xfffefdfd, 0xfffdfdfd, 0xfffdfefd, 0xfffdfdfd, 0xfffdfdfe, 0xfffdfdfd, 0xfffefefd, + 0xfffdfefe, 0xfffdfefd, 0xfffefefd, 0xfffefefd, 0xfffefefd, 0xfffdfefd, 0xfffdfdfd, 0xfffdfdfd, + 0xfffefefe, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfe, 0xfffefdfd, 0xfffefefd, 0xfffdfefd, 0xfffdfdfd, + 0xfffdfdfd, 0xfffdfefe, 0xfffdfdfd, 0xfffdfefd, 0xfffdfefe, 0xfffefdfd, 0xfffefdfd, 0xfffdfdfe, + 0xfffdfdfd, 0xfffdfefd, 0xfffdfdfe, 0xfffdfdfd, 0xfffdfdfe, 0xfffdfefd, 0xfffefdfe, 0xfffefdfd, + 0xfffdfefd, 0xfffefdfe, 0xfffefdfd, 0xfffefefd, 0xfffefefe, 0xfffefdfe, 0xfffefefe, 0xfffdfdfd, + 0xfffdfefd, 0xfffdfefd, 0xfffdfdfd, 0xfffdfdfd, 0xfffefdfe, 0xfffdfefe, 0xfffefdfd, 0xfffdfefd, + 0xfffdfdfd, 0xfffdfefe, 0xfffdfefd, 0xfffefdfd, 0xfffdfefe, 0xfffdfdfe, 0xfffdfefd, 0xfffefdfe, + 0xfffdfefd, 0xfffefefd, 0xfffdfefd, 0xfffdfefd, 0xfffdfefd, 0xfffdfefe, 0xfffefdfe, 0xfffdfefd, + 0xfffefefe, 0xfffdfdfe, 0xfffefefd, 0xfffdfdfd, 0xfffefefd, 0xfffefdfe, 0xfffefdfd, 0xfffefefd, + 0xfffdfefd, 0xfffdfefd, 0xfffdfdfe, 0xfffdfdfd, 0xfffefdfe, 0xfffdfefe, 0xfffdfdfd, 0xfffdfefd, + 0xfffdfdfe, 0xfffefdfe, 0xfffdfdfe, 0xfffdfefe, 0xfffefefe, 0xfffefefd, 0xfffefdfe, 0xfffdfdfe, + 0xfffdfdfd, 0xfffdfefd, 0xfffefdfd, 0xfffdfdfd, 0xfffdfdfe, 0xfffdfdfd, 0xfffefefe, 0xfffefdfd, + 0xfffefdfd, 0xfffdfefe, 0xfffdfdfe, 0xfffefdfd, 0xfffefdfd, 0xfffefdfe, 0xfffdfdfd, 0xfffdfdfd, + 0xfffefefe, 0xfffdfefe, 0xfffefdfd, 0xfffefefe, 0xfffdfdfd, 0xfffefdfd, 0xfffdfdfd, 0xfffefdfd, + 0xfffefdfe, 0xfffdfefd, 0xfffdfdfd, 0xfffdfefe, 0xfffdfdfd, 0xfffdfefe, 0xfffdfdfe, 0xfffdfdfd, + 0xfffefefe, 0xfffdfefd, 0xfffdfefe, 0xfffdfdfe, 0xfffdfdfe, 0xfffefefd, 0xfffefdfe, 0xfffdfdfd, + 0xfffdfdfd, 0xfffefefe, 0xfffdfdfe, 0xfffefdfe, 0xfffdfdfd, 0xfffdfefd, 0xfffefefe, 0xfffefdfd, + 0xfffdfefe, 0xfffdfefe, 0xfffefefe, 0xfffdfdfe, 0xfffdfdfd, 0xfffefdfd, 0xfffdfdfd, 0xfffdfdfd, + 0xfffdfdfd, 0xfffdfefd, 0xfffdfdfd, 0xfffefdfd, 0xfffefefe, 0xfffdfefd, 0xfffefdfd, 0xfffdfefe, + 0xfffefdfd, 0xfffefdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffefdfe, 0xfffefdfd, 0xfffefdfd, 0xfffdfefe, + 0xfffdfefd, 0xfffdfefd, 0xfffdfdfd, 0xfffefefe, 0xfffdfefd, 0xfffefdfd, 0xfffdfdfd, 0xfffefefd, + 0xfffefefd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfefd, 0xfffdfdfe, 0xfffefdfe, 0xfffefdfd, + 0xfffdfdfd, 0xfffefefd, 0xfffefefd, 0xfffdfefd, 0xfffefefd, 0xfffefdfd, 0xfffdfefe, 0xfffdfefd, + 0xfffdfdfd, 0xfffdfdfe, 0xfffdfdfe, 0xfffdfdfd, 0xfffdfdfe, 0xfffefdfe, 0xfffefdfd, 0xfffdfefe, + 0xfffdfdfd, 0xfffefefd, 0xfffdfdfd, 0xfffefdfe, 0xfffdfefe, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfe, + 0xfffefdfe, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffefdfe, 0xfffefdfe, 0xfffdfdfd, 0xfffdfdfe, + 0xfffefefd, 0xfffdfdfd, 0xfffefefe, 0xfffdfefd, 0xfffdfdfe, 0xfffdfdfe, 0xfff4f4f4, 0xffdedfde, + 0xffdedfde, 0x00060306, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff848384, 0xffc5c2c5, 0xffc5c2c5, + 0xffe9e9e9, 0xfffdfcfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfc, 0xfffcfcfd, 0xfffdfdfd, 0xfffdfdfd, + 0xfffcfdfd, 0xfffdfdfc, 0xfffcfdfd, 0xfffcfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfcfd, 0xfffdfdfc, + 0xfffdfcfd, 0xfffdfcfd, 0xfffdfcfc, 0xfffcfcfc, 0xfffdfcfd, 0xfffdfdfd, 0xfffdfcfd, 0xfffdfdfd, + 0xfffdfdfd, 0xfffdfcfc, 0xfffdfcfd, 0xfffcfcfd, 0xfffdfdfc, 0xfffdfcfd, 0xfffdfdfc, 0xfffdfdfd, + 0xfffdfdfc, 0xfffcfdfd, 0xfffdfdfc, 0xfffdfcfd, 0xfffcfcfd, 0xfffdfdfd, 0xfffdfdfc, 0xfffdfdfd, + 0xfffdfdfd, 0xfffdfdfd, 0xfffcfcfc, 0xfffdfdfd, 0xfffcfdfd, 0xfffdfdfc, 0xfffdfdfc, 0xfffdfcfd, + 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffcfdfd, + 0xfffdfcfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffcfdfd, 0xfffcfcfc, 0xfffcfdfd, 0xfffdfdfc, 0xfffdfcfd, + 0xfffdfcfd, 0xfffdfcfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffcfdfd, 0xfffdfcfd, 0xfffdfdfd, + 0xfffdfdfd, 0xfffdfdfc, 0xfffdfdfd, 0xfffdfcfd, 0xfffcfdfd, 0xfffdfcfc, 0xfffdfcfd, 0xfffdfdfd, + 0xfffcfdfc, 0xfffdfdfd, 0xfffdfcfc, 0xfffdfcfc, 0xfffcfdfc, 0xfffcfdfd, 0xfffdfdfd, 0xfffcfcfd, + 0xfffdfcfd, 0xfffcfcfc, 0xfffdfdfc, 0xfffcfcfd, 0xfffcfdfd, 0xfffdfdfd, 0xfffcfcfd, 0xfffdfdfd, + 0xfffdfcfd, 0xfffcfdfd, 0xfffdfdfd, 0xfffdfdfc, 0xfffcfcfc, 0xfffdfcfd, 0xfffcfdfd, 0xfffdfcfc, + 0xfffcfdfc, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfc, 0xfffdfdfd, 0xfffdfdfd, 0xfffcfcfd, 0xfffdfdfd, + 0xfffdfdfc, 0xfffdfdfd, 0xfffdfdfd, 0xfffcfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfc, 0xfffdfcfd, + 0xfffdfdfd, 0xfffcfcfc, 0xfffdfcfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, + 0xfffdfcfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfcfd, 0xfffdfdfd, + 0xfffdfdfd, 0xfffcfdfd, 0xfffdfcfc, 0xfffcfdfc, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, + 0xfffdfdfd, 0xfffdfcfc, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffcfdfd, 0xfffdfcfd, 0xfffdfdfd, + 0xfffdfdfc, 0xfffdfdfc, 0xfffcfdfd, 0xfffcfdfd, 0xfffdfdfc, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfdfd, + 0xfffdfcfd, 0xfffdfdfd, 0xfffdfdfc, 0xfffdfdfc, 0xfffdfdfc, 0xfffdfdfd, 0xfffcfdfc, 0xfffdfdfd, + 0xfffdfdfd, 0xfffcfcfd, 0xfffdfcfd, 0xfffcfdfc, 0xfffdfcfd, 0xfffcfdfc, 0xfffdfdfd, 0xfffdfdfd, + 0xfffdfcfc, 0xfffdfdfd, 0xfffcfcfd, 0xfffdfdfc, 0xfffdfdfc, 0xfffdfdfc, 0xfffdfcfd, 0xfffdfdfd, + 0xfffcfdfd, 0xfffdfcfd, 0xfffdfcfd, 0xfffdfdfc, 0xfffdfdfd, 0xfffcfdfd, 0xfffdfdfd, 0xfffcfdfd, + 0xfffdfcfd, 0xfffcfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfcfd, 0xfffdfdfd, 0xfffcfdfd, 0xfffdfcfc, + 0xfffcfcfd, 0xfffdfcfd, 0xfffdfdfc, 0xfffcfdfd, 0xfffdfdfd, 0xfffdfdfd, 0xfffdfcfd, 0xfffdfdfc, + 0xfffdfdfd, 0xfffdfdfd, 0xfffdfcfc, 0xfffdfdfd, 0xfffdfcfd, 0xfffcfdfd, 0xfffcfdfc, 0xfffdfdfd, + 0xfffdfdfc, 0xfffdfdfd, 0xfffdfdfd, 0xfffcfdfd, 0xfffcfdfd, 0xfffdfcfd, 0xfff4f4f4, 0xffe9e9e9, + 0xffdedfde, 0x00060306, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff848384, 0xffc5c2c5, 0xffc5c2c5, + 0xffe9e9e9, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfbfc, + 0xfffbfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffbfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfbfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfbfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfb, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfb, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfb, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfb, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, + 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfffcfcfc, 0xfff4f4f4, 0xffe9e9e9, + 0xffdedfde, 0x00060306, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff848684, 0xffc5c6c5, 0xffc5c6c5, + 0xffe6ebe6, 0xfffbfbfb, 0xfffbfbfc, 0xfffbfbfb, 0xfffbfbfc, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, + 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfc, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffcfbfb, + 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfc, 0xfffbfbfb, + 0xfffbfcfc, 0xfffcfbfb, 0xfffcfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfc, 0xfffbfbfc, + 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffcfcfc, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfcfb, 0xfffbfbfb, + 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, + 0xfffcfbfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffcfbfb, + 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfcfc, 0xfffbfcfb, 0xfffbfcfb, + 0xfffbfcfc, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfcfb, 0xfffbfbfc, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, + 0xfffcfbfb, 0xfffcfbfb, 0xfffcfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfcfc, 0xfffbfbfb, 0xfffbfbfb, + 0xfffbfbfc, 0xfffbfbfb, 0xfffbfcfc, 0xfffcfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfcfb, + 0xfffbfbfb, 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfb, + 0xfffbfcfb, 0xfffbfcfb, 0xfffcfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfc, 0xfffcfbfb, 0xfffbfbfc, + 0xfffbfbfb, 0xfffcfbfb, 0xfffbfbfc, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, + 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfcfc, 0xfffcfbfb, + 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfc, 0xfffbfbfb, + 0xfffbfbfc, 0xfffbfbfc, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfc, 0xfffcfbfb, 0xfffbfcfb, + 0xfffbfbfb, 0xfffcfbfb, 0xfffcfbfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, + 0xfffbfbfc, 0xfffbfcfc, 0xfffcfcfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfc, 0xfffbfbfb, + 0xfffcfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfb, + 0xfffbfcfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfbfc, 0xfffbfcfc, 0xfffbfbfc, 0xfffbfbfb, 0xfffbfcfc, + 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfc, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfc, + 0xfffbfcfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffcfbfb, 0xfffbfbfc, 0xfffbfcfc, + 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfc, 0xfffcfbfb, 0xfffbfbfb, 0xfffbfbfc, 0xfffbfcfb, 0xfffbfbfb, + 0xfffbfbfb, 0xfffbfcfb, 0xfffcfbfb, 0xfffbfbfc, 0xfffbfbfb, 0xfffcfbfb, 0xfffcfbfb, 0xfffbfbfb, + 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfbfb, 0xfffbfcfb, 0xfffbfbfb, + 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffcfbfb, + 0xfffbfbfc, 0xfffbfcfb, 0xfffbfcfb, 0xfffbfbfb, 0xfffbfbfb, 0xfffbfbfc, 0xfff7f8f7, 0xffe6ebe6, + 0xffdedfde, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff848684, 0xffc5c6c5, 0xffc5c6c5, + 0xffe6ebe6, 0xfffafafb, 0xfffafafb, 0xfffafafa, 0xfffafbfa, 0xfffbfafb, 0xfffafafa, 0xfffafafa, + 0xfffafbfa, 0xfffbfafa, 0xfffbfafa, 0xfffafbfa, 0xfffbfafa, 0xfffbfafb, 0xfffafafa, 0xfffbfafa, + 0xfffafafa, 0xfffafafb, 0xfffbfafb, 0xfffafafa, 0xfffbfbfa, 0xfffafafa, 0xfffafbfb, 0xfffafbfb, + 0xfffafbfa, 0xfffafafb, 0xfffafbfa, 0xfffbfafa, 0xfffbfbfa, 0xfffafbfa, 0xfffbfafa, 0xfffafbfa, + 0xfffafafa, 0xfffbfafa, 0xfffafbfa, 0xfffbfafb, 0xfffafafb, 0xfffafafa, 0xfffafbfa, 0xfffbfbfb, + 0xfffafbfa, 0xfffbfafb, 0xfffafafa, 0xfffafbfb, 0xfffafbfa, 0xfffafafa, 0xfffafafb, 0xfffafbfb, + 0xfffbfafa, 0xfffafbfa, 0xfffafafb, 0xfffafafb, 0xfffafafb, 0xfffafafb, 0xfffbfbfb, 0xfffafafa, + 0xfffafafa, 0xfffafafb, 0xfffbfafa, 0xfffafbfa, 0xfffafbfa, 0xfffafbfa, 0xfffafafa, 0xfffbfbfa, + 0xfffafafa, 0xfffbfbfa, 0xfffbfafa, 0xfffbfafb, 0xfffafafa, 0xfffafbfa, 0xfffafafa, 0xfffafbfa, + 0xfffafafa, 0xfffafafa, 0xfffbfafb, 0xfffafafa, 0xfffafbfa, 0xfffafafa, 0xfffafafa, 0xfffafafa, + 0xfffbfbfa, 0xfffafafa, 0xfffbfafa, 0xfffafafb, 0xfffbfbfa, 0xfffafbfa, 0xfffafbfa, 0xfffafafa, + 0xfffafbfb, 0xfffbfbfa, 0xfffafafa, 0xfffafafa, 0xfffbfafb, 0xfffafafb, 0xfffafbfa, 0xfffafbfa, + 0xfffbfbfa, 0xfffbfbfb, 0xfffafbfa, 0xfffafafa, 0xfffbfbfa, 0xfffbfafa, 0xfffafbfa, 0xfffafafa, + 0xfffbfafb, 0xfffafafa, 0xfffbfafb, 0xfffbfbfb, 0xfffbfafb, 0xfffafafa, 0xfffafafa, 0xfffafbfa, + 0xfffafafa, 0xfffafafb, 0xfffafafb, 0xfffafafb, 0xfffbfafb, 0xfffbfafb, 0xfffafbfa, 0xfffbfafa, + 0xfffafafa, 0xfffafbfb, 0xfffbfafa, 0xfffafafb, 0xfffafbfb, 0xfffafbfa, 0xfffafafa, 0xfffbfbfa, + 0xfffafbfa, 0xfffafafa, 0xfffafafb, 0xfffbfafa, 0xfffafafa, 0xfffbfafa, 0xfffbfafb, 0xfffbfafb, + 0xfffafafa, 0xfffafbfa, 0xfffbfbfa, 0xfffafbfa, 0xfffbfbfa, 0xfffafbfa, 0xfffafbfb, 0xfffafbfa, + 0xfffbfbfb, 0xfffafbfb, 0xfffbfafb, 0xfffafafa, 0xfffafafa, 0xfffbfafa, 0xfffbfafa, 0xfffbfafb, + 0xfffbfbfa, 0xfffafbfa, 0xfffafafa, 0xfffafbfa, 0xfffbfafa, 0xfffafafb, 0xfffafbfa, 0xfffafafb, + 0xfffbfbfa, 0xfffbfafa, 0xfffbfbfa, 0xfffbfafb, 0xfffbfafa, 0xfffafafa, 0xfffafafa, 0xfffbfafb, + 0xfffafafa, 0xfffbfbfb, 0xfffbfafb, 0xfffafafb, 0xfffafafa, 0xfffbfafa, 0xfffbfafb, 0xfffbfafb, + 0xfffbfafa, 0xfffafafb, 0xfffbfafa, 0xfffafafb, 0xfffafafa, 0xfffafbfb, 0xfffbfbfa, 0xfffbfafa, + 0xfffafbfa, 0xfffafafa, 0xfffafbfa, 0xfffbfbfa, 0xfffafbfb, 0xfffafbfb, 0xfffbfafb, 0xfffafafa, + 0xfffafbfb, 0xfffafafb, 0xfffbfbfa, 0xfffafafa, 0xfffafafb, 0xfffafafa, 0xfffafafb, 0xfffafbfa, + 0xfffbfafa, 0xfffbfbfb, 0xfffafafb, 0xfffafbfb, 0xfffafbfb, 0xfffbfafa, 0xfffafbfb, 0xfffafafa, + 0xfffafafa, 0xfffafbfa, 0xfffbfafa, 0xfffafbfa, 0xfffbfafa, 0xfffbfafa, 0xfffafbfa, 0xfffbfafb, + 0xfffafbfa, 0xfffafafb, 0xfffbfafa, 0xfffbfafb, 0xfffafbfb, 0xfffbfbfa, 0xfff7f8f7, 0xffe6ebe6, + 0xffdedfde, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff848684, 0xffc5c6c5, 0xffc5c6c5, + 0xffe6ebe6, 0xfffafafa, 0xfff9f9fa, 0xfffaf9fa, 0xfff9faf9, 0xfff9faf9, 0xfffafafa, 0xfff9f9f9, + 0xfffaf9f9, 0xfff9f9f9, 0xfff9f9f9, 0xfffaf9f9, 0xfff9fafa, 0xfff9fafa, 0xfff9f9fa, 0xfffafaf9, + 0xfff9faf9, 0xfffafafa, 0xfff9f9fa, 0xfff9f9f9, 0xfff9f9f9, 0xfffaf9fa, 0xfffaf9fa, 0xfff9f9f9, + 0xfffafaf9, 0xfff9f9f9, 0xfff9faf9, 0xfffaf9f9, 0xfffafaf9, 0xfffaf9f9, 0xfff9f9fa, 0xfff9f9f9, + 0xfffafafa, 0xfff9faf9, 0xfff9f9f9, 0xfff9fafa, 0xfffafaf9, 0xfff9f9fa, 0xfffaf9f9, 0xfff9f9fa, + 0xfff9faf9, 0xfffafafa, 0xfffafafa, 0xfffafaf9, 0xfff9faf9, 0xfff9f9f9, 0xfff9fafa, 0xfffafaf9, + 0xfffafaf9, 0xfffafafa, 0xfff9f9fa, 0xfffaf9fa, 0xfffafaf9, 0xfff9f9f9, 0xfffaf9f9, 0xfff9fafa, + 0xfff9fafa, 0xfff9faf9, 0xfffaf9f9, 0xfffaf9fa, 0xfffaf9f9, 0xfff9f9fa, 0xfffaf9f9, 0xfff9f9f9, + 0xfff9faf9, 0xfffaf9fa, 0xfffaf9f9, 0xfffaf9f9, 0xfff9faf9, 0xfffafafa, 0xfff9f9f9, 0xfff9f9fa, + 0xfffafafa, 0xfff9f9f9, 0xfffafaf9, 0xfffaf9f9, 0xfff9faf9, 0xfff9f9f9, 0xfffafaf9, 0xfff9f9fa, + 0xfff9faf9, 0xfff9fafa, 0xfffaf9fa, 0xfffafaf9, 0xfffafaf9, 0xfffaf9fa, 0xfff9f9fa, 0xfffaf9f9, + 0xfffaf9fa, 0xfff9fafa, 0xfffaf9f9, 0xfff9f9f9, 0xfffaf9f9, 0xfff9f9fa, 0xfffafafa, 0xfff9fafa, + 0xfff9f9fa, 0xfffaf9f9, 0xfffafaf9, 0xfffafaf9, 0xfff9faf9, 0xfff9f9fa, 0xfff9fafa, 0xfffaf9fa, + 0xfff9f9fa, 0xfffaf9f9, 0xfffafafa, 0xfff9faf9, 0xfffafaf9, 0xfffaf9f9, 0xfff9faf9, 0xfffaf9fa, + 0xfffafafa, 0xfffafaf9, 0xfff9faf9, 0xfffafaf9, 0xfffafafa, 0xfffafafa, 0xfff9f9f9, 0xfff9f9fa, + 0xfffaf9fa, 0xfff9f9f9, 0xfffafaf9, 0xfffafaf9, 0xfffafaf9, 0xfffaf9f9, 0xfffafafa, 0xfff9f9fa, + 0xfff9fafa, 0xfff9faf9, 0xfffaf9f9, 0xfffaf9fa, 0xfff9f9f9, 0xfff9fafa, 0xfff9f9fa, 0xfff9f9fa, + 0xfff9f9f9, 0xfffafaf9, 0xfff9f9f9, 0xfff9faf9, 0xfff9f9fa, 0xfffaf9fa, 0xfff9faf9, 0xfffafafa, + 0xfff9f9fa, 0xfffaf9fa, 0xfffafaf9, 0xfffaf9f9, 0xfffafafa, 0xfff9f9fa, 0xfffafaf9, 0xfffaf9f9, + 0xfff9faf9, 0xfffafaf9, 0xfff9faf9, 0xfff9f9f9, 0xfff9f9f9, 0xfff9f9f9, 0xfffafaf9, 0xfffaf9fa, + 0xfff9faf9, 0xfffaf9f9, 0xfffafaf9, 0xfffafaf9, 0xfff9fafa, 0xfffafafa, 0xfffaf9f9, 0xfff9fafa, + 0xfff9f9f9, 0xfffafaf9, 0xfffaf9fa, 0xfff9f9f9, 0xfff9faf9, 0xfffafaf9, 0xfff9f9fa, 0xfff9f9fa, + 0xfffafaf9, 0xfffaf9fa, 0xfff9fafa, 0xfff9f9f9, 0xfff9faf9, 0xfff9f9f9, 0xfff9f9fa, 0xfff9fafa, + 0xfff9f9fa, 0xfffafafa, 0xfff9f9fa, 0xfffaf9fa, 0xfff9f9fa, 0xfffafaf9, 0xfff9fafa, 0xfff9f9fa, + 0xfff9faf9, 0xfff9f9fa, 0xfff9fafa, 0xfffaf9f9, 0xfff9f9f9, 0xfffafafa, 0xfff9f9f9, 0xfff9faf9, + 0xfffafaf9, 0xfff9faf9, 0xfff9f9fa, 0xfffaf9f9, 0xfffaf9fa, 0xfff9f9fa, 0xfff9f9f9, 0xfff9fafa, + 0xfffafafa, 0xfffafafa, 0xfff9f9f9, 0xfffafafa, 0xfff9f9f9, 0xfffaf9fa, 0xfff9f9f9, 0xfff9fafa, + 0xfff9f9f9, 0xfff9f9f9, 0xfffaf9fa, 0xfffaf9f9, 0xfffaf9f9, 0xfffaf9f9, 0xfff7f8f7, 0xffe6ebe6, + 0xffdedfde, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff848684, 0xffc5c6c5, 0xffc5c6c5, + 0xffe6ebe6, 0xfff8f9f9, 0xfff9f8f8, 0xfff8f9f9, 0xfff9f8f9, 0xfff8f9f9, 0xfff9f8f9, 0xfff9f8f8, + 0xfff8f8f9, 0xfff9f9f9, 0xfff8f9f9, 0xfff8f8f9, 0xfff8f8f8, 0xfff9f8f8, 0xfff9f9f9, 0xfff9f9f8, + 0xfff9f9f9, 0xfff9f8f9, 0xfff8f9f9, 0xfff8f9f9, 0xfff9f9f8, 0xfff9f8f8, 0xfff8f9f8, 0xfff8f8f9, + 0xfff9f8f9, 0xfff8f9f8, 0xfff9f8f8, 0xfff9f9f8, 0xfff9f8f8, 0xfff9f8f8, 0xfff8f9f9, 0xfff9f9f9, + 0xfff9f8f8, 0xfff8f9f9, 0xfff8f8f9, 0xfff9f8f9, 0xfff9f9f8, 0xfff9f8f8, 0xfff8f9f8, 0xfff8f8f9, + 0xfff9f9f9, 0xfff9f9f9, 0xfff8f9f9, 0xfff8f9f8, 0xfff9f8f9, 0xfff9f9f9, 0xfff8f9f9, 0xfff8f9f8, + 0xfff9f8f9, 0xfff8f8f8, 0xfff8f9f9, 0xfff9f9f9, 0xfff8f8f8, 0xfff9f8f9, 0xfff8f8f8, 0xfff9f9f9, + 0xfff8f9f9, 0xfff8f9f9, 0xfff8f9f9, 0xfff8f9f9, 0xfff8f8f9, 0xfff8f8f9, 0xfff8f9f8, 0xfff8f8f8, + 0xfff9f8f8, 0xfff8f9f9, 0xfff8f9f9, 0xfff8f9f9, 0xfff8f9f9, 0xfff9f9f9, 0xfff9f9f8, 0xfff8f8f8, + 0xfff8f8f8, 0xfff9f9f9, 0xfff9f8f8, 0xfff9f8f8, 0xfff8f8f9, 0xfff9f8f9, 0xfff9f9f9, 0xfff9f9f8, + 0xfff9f8f8, 0xfff8f8f8, 0xfff8f9f9, 0xfff9f9f9, 0xfff8f9f8, 0xfff9f9f8, 0xfff8f9f9, 0xfff8f9f9, + 0xfff9f8f8, 0xfff9f9f9, 0xfff8f8f8, 0xfff8f8f8, 0xfff9f9f8, 0xfff9f9f8, 0xfff9f9f9, 0xfff9f9f8, + 0xfff8f9f9, 0xfff9f8f8, 0xfff8f8f8, 0xfff9f9f8, 0xfff8f8f8, 0xfff8f8f9, 0xfff8f8f9, 0xfff8f9f9, + 0xfff9f9f9, 0xfff9f9f9, 0xfff8f8f9, 0xfff9f8f9, 0xfff8f8f9, 0xfff8f8f9, 0xfff9f8f8, 0xfff9f9f9, + 0xfff9f9f9, 0xfff8f9f9, 0xfff9f9f8, 0xfff9f9f9, 0xfff9f8f8, 0xfff8f8f8, 0xfff9f8f9, 0xfff8f8f8, + 0xfff9f8f9, 0xfff9f8f9, 0xfff9f9f8, 0xfff8f8f8, 0xfff8f8f9, 0xfff9f8f9, 0xfff9f8f9, 0xfff8f8f8, + 0xfff8f8f9, 0xfff9f9f9, 0xfff8f8f8, 0xfff8f9f8, 0xfff9f9f8, 0xfff9f8f8, 0xfff9f8f9, 0xfff9f9f9, + 0xfff9f9f9, 0xfff9f9f8, 0xfff9f8f8, 0xfff9f9f9, 0xfff9f9f9, 0xfff9f8f8, 0xfff8f8f9, 0xfff8f9f8, + 0xfff8f9f8, 0xfff9f8f9, 0xfff9f9f8, 0xfff9f9f8, 0xfff9f8f8, 0xfff8f9f9, 0xfff8f8f9, 0xfff8f8f9, + 0xfff9f8f8, 0xfff9f8f9, 0xfff8f8f9, 0xfff9f9f9, 0xfff9f8f9, 0xfff8f8f8, 0xfff8f9f8, 0xfff9f8f9, + 0xfff9f8f8, 0xfff9f9f9, 0xfff8f8f8, 0xfff9f8f8, 0xfff9f9f9, 0xfff8f9f9, 0xfff8f9f9, 0xfff9f8f8, + 0xfff8f9f9, 0xfff8f9f8, 0xfff8f8f9, 0xfff9f8f8, 0xfff8f8f8, 0xfff9f9f9, 0xfff8f9f8, 0xfff8f9f8, + 0xfff9f8f8, 0xfff8f9f9, 0xfff8f8f8, 0xfff9f9f8, 0xfff9f9f8, 0xfff8f9f8, 0xfff9f8f8, 0xfff8f8f8, + 0xfff9f8f8, 0xfff9f9f9, 0xfff9f9f9, 0xfff9f8f8, 0xfff9f8f8, 0xfff9f9f8, 0xfff8f9f9, 0xfff9f8f9, + 0xfff8f8f9, 0xfff9f9f9, 0xfff9f9f8, 0xfff8f9f9, 0xfff8f9f9, 0xfff9f9f8, 0xfff9f8f9, 0xfff9f9f8, + 0xfff9f9f9, 0xfff9f8f9, 0xfff9f9f9, 0xfff8f8f9, 0xfff9f9f8, 0xfff8f9f9, 0xfff9f8f9, 0xfff9f9f9, + 0xfff9f9f8, 0xfff9f8f9, 0xfff8f8f8, 0xfff9f8f8, 0xfff8f8f9, 0xfff8f9f8, 0xfff8f8f8, 0xfff8f8f9, + 0xfff8f9f9, 0xfff9f9f9, 0xfff9f9f9, 0xfff8f9f8, 0xfff9f9f9, 0xfff9f8f8, 0xfff7f8f7, 0xffe6ebe6, + 0xffdedfde, 0x00000300, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797d79, 0xffb5bab5, 0xffb5bab5, + 0xffdedbde, 0xfff7f8f7, 0xfff7f7f8, 0xfff8f8f8, 0xfff7f7f7, 0xfff8f7f8, 0xfff7f7f8, 0xfff8f8f8, + 0xfff8f8f8, 0xfff7f8f8, 0xfff7f7f8, 0xfff8f7f8, 0xfff7f8f8, 0xfff8f8f8, 0xfff8f7f7, 0xfff8f8f7, + 0xfff7f8f8, 0xfff7f7f7, 0xfff7f7f8, 0xfff8f7f8, 0xfff8f8f7, 0xfff8f7f7, 0xfff7f8f7, 0xfff8f8f8, + 0xfff8f7f7, 0xfff8f7f8, 0xfff8f7f8, 0xfff8f8f7, 0xfff8f7f7, 0xfff8f8f8, 0xfff7f8f7, 0xfff8f8f7, + 0xfff8f8f7, 0xfff7f8f8, 0xfff7f7f7, 0xfff8f7f8, 0xfff8f7f7, 0xfff7f8f8, 0xfff8f8f8, 0xfff7f7f7, + 0xfff7f8f8, 0xfff7f7f8, 0xfff7f8f8, 0xfff7f8f8, 0xfff7f8f8, 0xfff7f7f8, 0xfff8f8f8, 0xfff7f8f8, + 0xfff7f8f8, 0xfff8f8f8, 0xfff7f8f7, 0xfff8f8f7, 0xfff7f7f7, 0xfff8f8f8, 0xfff7f7f8, 0xfff8f7f7, + 0xfff7f8f7, 0xfff8f8f7, 0xfff7f8f7, 0xfff8f8f8, 0xfff7f7f7, 0xfff8f7f7, 0xfff8f8f7, 0xfff7f8f8, + 0xfff7f8f7, 0xfff8f7f8, 0xfff7f8f8, 0xfff8f8f7, 0xfff7f8f7, 0xfff8f8f7, 0xfff7f7f8, 0xfff8f7f8, + 0xfff8f8f8, 0xfff8f7f8, 0xfff7f8f8, 0xfff7f7f7, 0xfff7f8f7, 0xfff8f8f8, 0xfff7f7f8, 0xfff8f7f8, + 0xfff7f8f8, 0xfff8f8f7, 0xfff8f7f8, 0xfff8f8f8, 0xfff7f8f7, 0xfff8f7f8, 0xfff8f8f7, 0xfff7f8f8, + 0xfff7f7f8, 0xfff8f8f7, 0xfff8f8f7, 0xfff8f7f7, 0xfff7f7f7, 0xfff7f7f8, 0xfff7f8f8, 0xfff8f8f7, + 0xfff7f8f8, 0xfff8f7f8, 0xfff7f8f8, 0xfff8f8f8, 0xfff7f7f7, 0xfff7f8f7, 0xfff8f7f7, 0xfff8f7f8, + 0xfff8f8f7, 0xfff8f7f8, 0xfff8f7f7, 0xfff7f8f8, 0xfff7f7f8, 0xfff7f7f8, 0xfff8f7f8, 0xfff8f7f7, + 0xfff7f7f8, 0xfff8f8f8, 0xfff7f7f8, 0xfff7f7f7, 0xfff8f8f7, 0xfff7f8f8, 0xfff8f7f8, 0xfff7f8f8, + 0xfff8f7f7, 0xfff8f7f8, 0xfff8f8f7, 0xfff7f8f8, 0xfff8f8f7, 0xfff8f8f7, 0xfff7f8f8, 0xfff8f8f7, + 0xfff8f8f8, 0xfff7f7f8, 0xfff7f7f8, 0xfff8f8f8, 0xfff7f7f7, 0xfff8f8f7, 0xfff7f7f8, 0xfff7f8f8, + 0xfff7f7f7, 0xfff7f7f7, 0xfff7f8f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff8f8f8, 0xfff7f7f8, 0xfff8f8f8, + 0xfff7f8f8, 0xfff8f8f8, 0xfff7f8f8, 0xfff7f8f7, 0xfff8f7f8, 0xfff7f8f8, 0xfff8f7f8, 0xfff7f8f7, + 0xfff7f8f7, 0xfff8f8f7, 0xfff8f7f7, 0xfff8f7f8, 0xfff8f7f8, 0xfff7f8f8, 0xfff8f7f7, 0xfff8f8f8, + 0xfff8f7f8, 0xfff8f8f7, 0xfff8f7f8, 0xfff8f7f7, 0xfff7f8f8, 0xfff8f8f7, 0xfff8f7f7, 0xfff8f8f7, + 0xfff7f8f7, 0xfff7f8f8, 0xfff7f8f8, 0xfff8f8f8, 0xfff8f8f7, 0xfff7f8f8, 0xfff7f8f8, 0xfff7f8f7, + 0xfff8f8f8, 0xfff8f8f7, 0xfff8f8f8, 0xfff7f7f7, 0xfff7f7f8, 0xfff8f7f8, 0xfff8f8f8, 0xfff8f7f8, + 0xfff8f8f8, 0xfff7f8f7, 0xfff7f8f7, 0xfff8f7f7, 0xfff8f7f7, 0xfff8f8f8, 0xfff7f7f8, 0xfff8f7f7, + 0xfff8f8f8, 0xfff8f8f7, 0xfff8f7f7, 0xfff7f7f8, 0xfff7f8f8, 0xfff8f7f7, 0xfff8f7f7, 0xfff8f8f7, + 0xfff8f7f7, 0xfff8f8f8, 0xfff8f8f8, 0xfff8f7f7, 0xfff8f8f8, 0xfff7f8f8, 0xfff7f8f8, 0xfff7f7f8, + 0xfff7f8f7, 0xfff7f8f7, 0xfff8f8f7, 0xfff8f8f8, 0xfff8f8f8, 0xfff7f7f8, 0xfff7f8f8, 0xfff8f7f7, + 0xfff7f7f8, 0xfff8f7f7, 0xfff8f8f8, 0xfff7f8f7, 0xfff7f8f7, 0xfff8f8f8, 0xffe9e8e9, 0xffdedbde, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797d79, 0xffb5bab5, 0xffb5bab5, + 0xffdedbde, 0xfff6f7f7, 0xfff7f6f7, 0xfff7f6f7, 0xfff6f7f6, 0xfff7f6f7, 0xfff6f6f7, 0xfff6f7f7, + 0xfff6f6f7, 0xfff7f6f7, 0xfff7f7f7, 0xfff6f7f6, 0xfff7f7f7, 0xfff6f7f7, 0xfff7f6f6, 0xfff7f7f6, + 0xfff6f6f6, 0xfff7f7f7, 0xfff6f6f6, 0xfff6f7f6, 0xfff7f7f6, 0xfff7f7f7, 0xfff6f6f7, 0xfff7f7f6, + 0xfff7f7f7, 0xfff7f7f6, 0xfff6f6f6, 0xfff6f7f6, 0xfff7f7f6, 0xfff7f7f6, 0xfff7f6f7, 0xfff7f6f7, + 0xfff6f7f6, 0xfff6f6f7, 0xfff7f7f7, 0xfff6f6f6, 0xfff6f7f7, 0xfff6f6f6, 0xfff6f7f6, 0xfff6f7f7, + 0xfff7f6f7, 0xfff6f6f6, 0xfff7f7f6, 0xfff6f7f6, 0xfff6f7f7, 0xfff7f7f7, 0xfff7f7f6, 0xfff7f7f7, + 0xfff6f6f6, 0xfff6f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f6f7, 0xfff7f6f7, 0xfff7f7f7, 0xfff6f7f7, + 0xfff6f7f6, 0xfff6f6f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f6f6, 0xfff7f7f6, 0xfff7f7f7, + 0xfff7f7f6, 0xfff6f6f7, 0xfff6f6f7, 0xfff7f7f6, 0xfff7f6f7, 0xfff7f6f6, 0xfff7f7f6, 0xfff6f7f7, + 0xfff7f6f7, 0xfff7f6f7, 0xfff7f6f7, 0xfff6f6f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f6, 0xfff6f6f6, + 0xfff6f7f6, 0xfff6f6f7, 0xfff7f6f7, 0xfff7f7f6, 0xfff6f6f7, 0xfff7f7f7, 0xfff7f6f6, 0xfff7f6f7, + 0xfff6f6f6, 0xfff6f7f7, 0xfff7f6f7, 0xfff7f7f6, 0xfff7f6f7, 0xfff7f6f6, 0xfff7f6f7, 0xfff7f7f6, + 0xfff6f7f7, 0xfff7f6f6, 0xfff7f6f6, 0xfff7f6f6, 0xfff7f6f6, 0xfff6f7f7, 0xfff6f6f7, 0xfff7f6f7, + 0xfff6f7f7, 0xfff6f7f7, 0xfff6f7f6, 0xfff7f6f7, 0xfff7f7f6, 0xfff7f7f6, 0xfff6f7f7, 0xfff7f6f7, + 0xfff7f7f7, 0xfff7f7f6, 0xfff6f6f6, 0xfff7f7f7, 0xfff6f6f7, 0xfff7f7f7, 0xfff6f6f7, 0xfff6f6f6, + 0xfff6f6f7, 0xfff6f6f7, 0xfff7f6f7, 0xfff7f6f6, 0xfff7f6f6, 0xfff7f6f7, 0xfff7f7f6, 0xfff6f6f7, + 0xfff7f7f7, 0xfff6f7f6, 0xfff6f7f6, 0xfff7f7f7, 0xfff7f6f7, 0xfff6f6f6, 0xfff7f7f7, 0xfff7f6f7, + 0xfff7f7f6, 0xfff6f6f7, 0xfff7f6f7, 0xfff6f6f7, 0xfff6f7f6, 0xfff6f7f6, 0xfff6f6f7, 0xfff7f6f7, + 0xfff7f6f6, 0xfff7f6f6, 0xfff6f7f6, 0xfff7f7f7, 0xfff6f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f6f6, + 0xfff6f7f6, 0xfff7f6f6, 0xfff6f7f7, 0xfff6f6f6, 0xfff7f6f7, 0xfff6f7f7, 0xfff7f6f7, 0xfff7f7f7, + 0xfff6f6f6, 0xfff6f6f6, 0xfff6f7f6, 0xfff7f7f6, 0xfff7f6f7, 0xfff6f7f7, 0xfff6f6f6, 0xfff6f6f7, + 0xfff6f6f7, 0xfff6f7f7, 0xfff6f7f7, 0xfff6f7f7, 0xfff6f6f6, 0xfff6f7f7, 0xfff7f6f7, 0xfff7f7f7, + 0xfff6f7f7, 0xfff7f6f7, 0xfff6f6f6, 0xfff7f6f7, 0xfff6f7f6, 0xfff7f6f6, 0xfff6f7f7, 0xfff6f7f7, + 0xfff6f7f7, 0xfff6f7f6, 0xfff6f7f7, 0xfff6f7f7, 0xfff7f7f7, 0xfff7f6f6, 0xfff7f6f6, 0xfff7f6f7, + 0xfff7f7f6, 0xfff7f7f6, 0xfff7f6f7, 0xfff6f6f7, 0xfff7f6f7, 0xfff7f6f6, 0xfff7f7f7, 0xfff7f6f7, + 0xfff6f6f7, 0xfff7f7f6, 0xfff6f7f6, 0xfff6f7f6, 0xfff7f7f7, 0xfff7f6f7, 0xfff6f7f6, 0xfff7f6f6, + 0xfff6f6f7, 0xfff6f7f7, 0xfff7f6f7, 0xfff7f6f6, 0xfff6f6f7, 0xfff7f7f6, 0xfff6f6f7, 0xfff7f6f6, + 0xfff6f6f7, 0xfff6f6f7, 0xfff7f7f6, 0xfff6f7f7, 0xfff7f6f6, 0xfff7f7f7, 0xffe9e8e9, 0xffdedbde, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797d79, 0xffb5bab5, 0xffb5bab5, + 0xffdedbde, 0xfff6f6f6, 0xfff6f6f5, 0xfff6f5f6, 0xfff5f5f6, 0xfff6f5f6, 0xfff6f6f6, 0xfff5f6f5, + 0xfff6f6f5, 0xfff5f6f6, 0xfff6f6f5, 0xfff6f5f6, 0xfff6f5f5, 0xfff6f5f6, 0xfff5f6f6, 0xfff6f5f6, + 0xfff6f5f6, 0xfff5f5f6, 0xfff6f6f6, 0xfff6f5f6, 0xfff5f6f6, 0xfff6f5f5, 0xfff6f6f6, 0xfff6f5f6, + 0xfff6f5f6, 0xfff5f5f6, 0xfff6f6f5, 0xfff5f6f5, 0xfff6f6f6, 0xfff6f5f6, 0xfff6f6f6, 0xfff6f6f5, + 0xfff6f5f5, 0xfff5f5f6, 0xfff5f6f5, 0xfff5f6f5, 0xfff6f6f5, 0xfff5f5f6, 0xfff6f5f6, 0xfff6f6f6, + 0xfff5f6f6, 0xfff6f5f6, 0xfff5f5f6, 0xfff5f6f6, 0xfff5f6f5, 0xfff5f6f5, 0xfff6f6f6, 0xfff6f6f6, + 0xfff5f5f5, 0xfff5f6f6, 0xfff6f6f5, 0xfff5f5f6, 0xfff5f6f5, 0xfff6f6f6, 0xfff6f6f6, 0xfff5f6f6, + 0xfff5f5f6, 0xfff5f6f6, 0xfff5f5f6, 0xfff5f5f5, 0xfff6f5f5, 0xfff6f6f6, 0xfff5f5f5, 0xfff5f6f6, + 0xfff6f5f6, 0xfff6f6f5, 0xfff5f6f5, 0xfff5f6f5, 0xfff6f6f6, 0xfff5f6f6, 0xfff6f5f6, 0xfff5f5f5, + 0xfff6f5f6, 0xfff6f6f6, 0xfff6f6f6, 0xfff5f5f6, 0xfff6f5f6, 0xfff5f6f5, 0xfff6f5f6, 0xfff6f6f5, + 0xfff6f6f6, 0xfff6f5f6, 0xfff6f6f5, 0xfff5f6f6, 0xfff5f6f6, 0xfff5f6f5, 0xfff5f5f5, 0xfff6f6f5, + 0xfff6f6f6, 0xfff6f6f6, 0xfff5f6f5, 0xfff5f6f5, 0xfff5f5f6, 0xfff6f6f5, 0xfff6f5f5, 0xfff6f6f6, + 0xfff5f5f6, 0xfff6f5f6, 0xfff6f5f6, 0xfff6f5f6, 0xfff5f5f6, 0xfff6f6f5, 0xfff6f5f5, 0xfff6f6f5, + 0xfff6f6f6, 0xfff6f5f6, 0xfff5f6f6, 0xfff5f6f5, 0xfff6f6f6, 0xfff6f6f6, 0xfff6f5f6, 0xfff5f5f5, + 0xfff5f6f5, 0xfff5f5f6, 0xfff5f6f5, 0xfff6f6f6, 0xfff5f6f5, 0xfff6f5f5, 0xfff6f6f5, 0xfff6f6f5, + 0xfff5f6f6, 0xfff6f5f5, 0xfff6f6f6, 0xfff6f5f5, 0xfff5f5f6, 0xfff6f6f5, 0xfff5f6f6, 0xfff6f6f6, + 0xfff5f6f5, 0xfff5f5f5, 0xfff5f6f6, 0xfff6f6f6, 0xfff5f6f6, 0xfff6f6f5, 0xfff5f6f6, 0xfff5f6f5, + 0xfff6f5f6, 0xfff6f5f5, 0xfff5f6f6, 0xfff6f6f5, 0xfff5f6f5, 0xfff6f5f5, 0xfff5f5f5, 0xfff6f6f6, + 0xfff5f6f6, 0xfff5f6f5, 0xfff6f6f6, 0xfff5f6f6, 0xfff5f6f6, 0xfff6f5f6, 0xfff5f6f6, 0xfff6f6f6, + 0xfff6f5f5, 0xfff6f6f6, 0xfff6f6f6, 0xfff5f6f5, 0xfff6f6f6, 0xfff6f5f5, 0xfff6f6f5, 0xfff6f5f6, + 0xfff6f6f5, 0xfff5f6f5, 0xfff6f5f6, 0xfff5f6f5, 0xfff6f5f6, 0xfff5f6f5, 0xfff6f6f6, 0xfff6f6f5, + 0xfff6f5f6, 0xfff6f6f6, 0xfff5f6f6, 0xfff5f6f6, 0xfff6f6f5, 0xfff5f5f6, 0xfff5f6f5, 0xfff6f6f6, + 0xfff6f6f6, 0xfff6f6f5, 0xfff6f6f6, 0xfff6f5f6, 0xfff5f6f6, 0xfff5f5f6, 0xfff6f5f5, 0xfff5f6f6, + 0xfff5f6f6, 0xfff6f5f6, 0xfff5f5f5, 0xfff5f5f6, 0xfff5f6f6, 0xfff6f6f5, 0xfff6f6f6, 0xfff5f6f5, + 0xfff5f6f5, 0xfff6f5f6, 0xfff6f5f6, 0xfff6f6f6, 0xfff6f5f6, 0xfff6f6f5, 0xfff6f6f6, 0xfff6f5f6, + 0xfff6f6f5, 0xfff5f5f5, 0xfff5f6f5, 0xfff6f6f6, 0xfff6f5f6, 0xfff6f5f6, 0xfff6f6f5, 0xfff6f6f5, + 0xfff6f6f6, 0xfff5f6f5, 0xfff6f6f5, 0xfff6f6f5, 0xfff6f5f6, 0xfff6f6f6, 0xfff6f6f5, 0xfff5f6f6, + 0xfff6f6f6, 0xfff6f6f5, 0xfff6f5f5, 0xfff6f5f5, 0xfff6f6f6, 0xfff6f6f6, 0xffe9e8e9, 0xffdedbde, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797d79, 0xffb5bab5, 0xffb5bab5, + 0xffdedbde, 0xfff4f4f4, 0xfff5f5f5, 0xfff5f5f4, 0xfff5f4f5, 0xfff5f4f4, 0xfff5f4f4, 0xfff5f4f5, + 0xfff4f5f4, 0xfff4f4f5, 0xfff5f4f4, 0xfff5f4f4, 0xfff4f5f5, 0xfff5f5f4, 0xfff4f5f4, 0xfff4f4f5, + 0xfff5f4f5, 0xfff4f5f5, 0xfff5f4f4, 0xfff5f5f5, 0xfff4f5f5, 0xfff4f5f5, 0xfff4f4f5, 0xfff4f5f4, + 0xfff4f5f4, 0xfff5f5f4, 0xfff5f5f4, 0xfff4f5f4, 0xfff5f4f5, 0xfff5f5f5, 0xfff4f5f5, 0xfff4f5f5, + 0xfff5f5f4, 0xfff4f4f4, 0xfff4f5f4, 0xfff5f5f5, 0xfff5f5f5, 0xfff5f5f5, 0xfff4f5f4, 0xfff5f5f5, + 0xfff4f4f5, 0xfff5f5f5, 0xfff5f5f5, 0xfff4f4f5, 0xfff4f5f4, 0xfff5f5f4, 0xfff5f5f5, 0xfff5f4f4, + 0xfff5f4f5, 0xfff5f4f5, 0xfff4f5f4, 0xfff5f4f5, 0xfff5f5f4, 0xfff5f5f5, 0xfff4f4f5, 0xfff4f5f4, + 0xfff4f4f4, 0xfff4f5f4, 0xfff5f5f4, 0xfff5f5f4, 0xfff4f4f5, 0xfff4f5f5, 0xfff4f5f5, 0xfff4f5f4, + 0xfff5f5f5, 0xfff4f5f5, 0xfff4f5f5, 0xfff5f4f5, 0xfff4f4f5, 0xfff5f4f5, 0xfff4f5f5, 0xfff4f5f4, + 0xfff5f5f5, 0xfff5f5f5, 0xfff5f5f5, 0xfff4f5f5, 0xfff4f4f5, 0xfff4f4f4, 0xfff5f5f5, 0xfff5f5f5, + 0xfff4f5f5, 0xfff5f4f5, 0xfff4f5f5, 0xfff4f5f5, 0xfff5f4f5, 0xfff5f5f5, 0xfff5f4f5, 0xfff4f5f5, + 0xfff5f5f4, 0xfff4f4f4, 0xfff4f5f5, 0xfff4f4f4, 0xfff4f5f5, 0xfff5f5f4, 0xfff5f5f4, 0xfff4f5f5, + 0xfff4f4f4, 0xfff4f5f4, 0xfff4f5f5, 0xfff5f5f4, 0xfff4f5f5, 0xfff4f4f5, 0xfff5f5f4, 0xfff4f4f5, + 0xfff5f5f4, 0xfff4f4f5, 0xfff4f5f5, 0xfff4f5f4, 0xfff5f4f5, 0xfff5f5f5, 0xfff4f4f5, 0xfff5f4f5, + 0xfff5f5f5, 0xfff4f5f4, 0xfff5f5f5, 0xfff5f5f5, 0xfff4f5f5, 0xfff4f5f4, 0xfff4f4f5, 0xfff4f4f5, + 0xfff4f4f5, 0xfff5f4f5, 0xfff4f4f4, 0xfff5f5f5, 0xfff4f4f5, 0xfff5f5f5, 0xfff4f4f5, 0xfff5f4f4, + 0xfff4f4f4, 0xfff5f4f4, 0xfff5f5f5, 0xfff5f5f4, 0xfff5f5f5, 0xfff4f5f4, 0xfff5f5f5, 0xfff4f5f5, + 0xfff4f5f4, 0xfff5f4f4, 0xfff4f4f4, 0xfff5f5f4, 0xfff4f4f5, 0xfff5f4f5, 0xfff5f4f5, 0xfff5f4f5, + 0xfff5f5f5, 0xfff5f4f4, 0xfff4f5f4, 0xfff4f4f5, 0xfff5f5f5, 0xfff5f4f4, 0xfff5f5f5, 0xfff5f4f5, + 0xfff4f5f5, 0xfff4f5f5, 0xfff5f4f4, 0xfff5f5f5, 0xfff5f5f4, 0xfff5f4f4, 0xfff4f5f4, 0xfff5f4f4, + 0xfff5f5f4, 0xfff4f4f5, 0xfff5f4f4, 0xfff5f4f5, 0xfff4f5f5, 0xfff4f5f5, 0xfff5f5f5, 0xfff4f5f5, + 0xfff4f5f4, 0xfff4f5f5, 0xfff5f5f5, 0xfff4f4f5, 0xfff4f5f5, 0xfff4f5f5, 0xfff4f4f5, 0xfff4f5f5, + 0xfff5f4f4, 0xfff5f5f5, 0xfff4f5f4, 0xfff5f5f4, 0xfff5f4f4, 0xfff4f5f5, 0xfff4f5f5, 0xfff5f5f5, + 0xfff4f4f4, 0xfff5f5f5, 0xfff5f5f5, 0xfff4f5f5, 0xfff5f5f5, 0xfff4f4f5, 0xfff5f5f5, 0xfff4f5f5, + 0xfff4f5f4, 0xfff5f5f4, 0xfff5f5f5, 0xfff5f4f5, 0xfff5f4f4, 0xfff4f4f4, 0xfff5f5f4, 0xfff5f5f4, + 0xfff5f4f5, 0xfff5f5f4, 0xfff4f5f4, 0xfff4f5f4, 0xfff5f5f5, 0xfff4f4f5, 0xfff5f4f5, 0xfff4f5f5, + 0xfff5f5f4, 0xfff5f4f5, 0xfff5f5f5, 0xfff4f5f5, 0xfff4f4f5, 0xfff5f4f5, 0xfff4f4f5, 0xfff5f5f4, + 0xfff5f5f5, 0xfff4f5f5, 0xfff4f4f5, 0xfff5f5f5, 0xfff4f5f4, 0xfff4f5f5, 0xffe9e8e9, 0xffdedbde, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff797c79, 0xffb5bab5, 0xffb5bab5, + 0xffdedbde, 0xfff3f4f4, 0xfff4f3f3, 0xfff3f4f4, 0xfff4f4f4, 0xfff3f4f4, 0xfff3f3f4, 0xfff4f3f3, + 0xfff3f3f4, 0xfff3f3f3, 0xfff4f4f4, 0xfff4f4f3, 0xfff3f4f4, 0xfff4f3f4, 0xfff3f4f4, 0xfff3f3f4, + 0xfff3f3f3, 0xfff3f4f3, 0xfff4f4f3, 0xfff4f4f3, 0xfff4f4f4, 0xfff4f4f3, 0xfff4f4f4, 0xfff3f3f4, + 0xfff4f4f4, 0xfff3f3f3, 0xfff3f4f3, 0xfff3f4f3, 0xfff4f4f3, 0xfff3f4f4, 0xfff4f4f4, 0xfff4f4f3, + 0xfff4f4f3, 0xfff3f3f3, 0xfff3f3f4, 0xfff4f3f3, 0xfff4f4f4, 0xfff4f3f4, 0xfff3f3f3, 0xfff4f4f3, + 0xfff4f3f4, 0xfff3f4f3, 0xfff3f4f3, 0xfff4f3f4, 0xfff3f4f3, 0xfff4f4f4, 0xfff4f4f4, 0xfff4f3f4, + 0xfff4f4f4, 0xfff4f4f3, 0xfff4f3f3, 0xfff3f4f3, 0xfff3f4f3, 0xfff4f3f4, 0xfff3f4f4, 0xfff3f4f3, + 0xfff4f3f3, 0xfff4f3f4, 0xfff3f3f4, 0xfff4f4f4, 0xfff3f3f3, 0xfff4f3f3, 0xfff3f3f4, 0xfff3f3f3, + 0xfff4f3f3, 0xfff3f3f4, 0xfff4f3f3, 0xfff3f3f4, 0xfff3f4f4, 0xfff4f3f3, 0xfff3f3f3, 0xfff4f3f4, + 0xfff4f4f4, 0xfff3f4f4, 0xfff4f3f3, 0xfff3f3f4, 0xfff3f3f3, 0xfff4f4f3, 0xfff4f4f4, 0xfff4f3f3, + 0xfff3f4f4, 0xfff3f3f4, 0xfff3f3f4, 0xfff3f4f3, 0xfff3f4f3, 0xfff3f4f4, 0xfff4f3f4, 0xfff4f3f3, + 0xfff4f4f4, 0xfff4f4f4, 0xfff4f4f4, 0xfff3f4f4, 0xfff4f4f4, 0xfff3f4f3, 0xfff4f4f4, 0xfff4f3f4, + 0xfff3f3f3, 0xfff4f3f3, 0xfff4f3f3, 0xfff3f3f3, 0xfff3f4f3, 0xfff4f4f3, 0xfff3f3f3, 0xfff3f3f3, + 0xfff4f4f3, 0xfff3f3f3, 0xfff4f3f3, 0xfff4f4f4, 0xfff4f4f4, 0xfff3f3f4, 0xfff3f4f3, 0xfff4f3f4, + 0xfff4f3f4, 0xfff4f4f4, 0xfff3f3f3, 0xfff4f4f3, 0xfff4f3f3, 0xfff3f3f3, 0xfff4f4f4, 0xfff3f4f4, + 0xfff3f3f4, 0xfff3f3f4, 0xfff4f4f4, 0xfff3f4f4, 0xfff3f3f3, 0xfff4f3f4, 0xfff3f4f4, 0xfff4f4f4, + 0xfff4f4f4, 0xfff3f4f3, 0xfff3f4f4, 0xfff3f4f4, 0xfff3f4f3, 0xfff4f4f4, 0xfff4f4f3, 0xfff3f3f4, + 0xfff4f3f4, 0xfff3f3f3, 0xfff3f3f4, 0xfff4f4f4, 0xfff4f3f4, 0xfff3f3f3, 0xfff3f4f4, 0xfff3f3f3, + 0xfff4f3f4, 0xfff3f4f4, 0xfff4f3f4, 0xfff4f3f4, 0xfff4f4f4, 0xfff3f3f4, 0xfff4f3f3, 0xfff4f4f4, + 0xfff4f3f3, 0xfff3f4f4, 0xfff4f4f4, 0xfff3f4f3, 0xfff4f3f4, 0xfff4f4f4, 0xfff4f3f3, 0xfff3f3f4, + 0xfff4f3f3, 0xfff4f4f3, 0xfff3f4f3, 0xfff3f4f3, 0xfff4f4f3, 0xfff3f4f3, 0xfff4f4f4, 0xfff4f4f3, + 0xfff4f4f4, 0xfff4f4f3, 0xfff4f3f3, 0xfff4f3f4, 0xfff3f3f4, 0xfff3f4f3, 0xfff3f3f3, 0xfff4f4f4, + 0xfff3f3f4, 0xfff4f4f4, 0xfff4f3f3, 0xfff4f4f4, 0xfff4f4f3, 0xfff3f3f3, 0xfff4f4f4, 0xfff3f3f4, + 0xfff4f3f3, 0xfff4f3f3, 0xfff3f4f4, 0xfff3f4f3, 0xfff3f4f3, 0xfff4f4f4, 0xfff3f3f4, 0xfff4f4f3, + 0xfff3f3f4, 0xfff4f3f4, 0xfff3f4f4, 0xfff3f3f3, 0xfff3f3f4, 0xfff3f3f3, 0xfff4f4f4, 0xfff4f4f4, + 0xfff3f3f4, 0xfff3f4f3, 0xfff4f4f3, 0xfff3f4f3, 0xfff3f3f4, 0xfff4f4f4, 0xfff4f4f3, 0xfff3f4f4, + 0xfff3f3f3, 0xfff4f3f4, 0xfff4f3f3, 0xfff3f3f4, 0xfff4f4f3, 0xfff3f4f3, 0xfff3f3f4, 0xfff3f4f3, + 0xfff4f3f4, 0xfff4f3f4, 0xfff4f4f3, 0xfff4f3f3, 0xfff3f4f4, 0xfff3f4f3, 0xffe9e8e9, 0xffdedbde, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff797c79, 0xffb5bab5, 0xffb5bab5, + 0xffdedbde, 0xfff3f3f3, 0xfff2f3f2, 0xfff3f2f3, 0xfff2f3f2, 0xfff2f3f3, 0xfff3f2f2, 0xfff2f3f2, + 0xfff2f3f3, 0xfff3f3f2, 0xfff3f3f2, 0xfff3f2f3, 0xfff2f3f3, 0xfff3f2f3, 0xfff2f2f2, 0xfff2f3f3, + 0xfff2f3f3, 0xfff2f2f2, 0xfff2f3f2, 0xfff2f3f2, 0xfff2f2f3, 0xfff2f3f3, 0xfff2f3f2, 0xfff2f2f3, + 0xfff3f2f3, 0xfff3f2f3, 0xfff3f3f3, 0xfff2f2f2, 0xfff3f3f2, 0xfff3f2f3, 0xfff3f2f3, 0xfff2f2f3, + 0xfff2f3f3, 0xfff3f3f3, 0xfff3f2f3, 0xfff3f3f3, 0xfff2f3f2, 0xfff3f3f3, 0xfff3f2f3, 0xfff3f2f2, + 0xfff2f3f3, 0xfff2f2f3, 0xfff3f3f3, 0xfff2f2f3, 0xfff2f3f2, 0xfff2f2f3, 0xfff2f2f2, 0xfff3f2f3, + 0xfff2f2f3, 0xfff3f2f2, 0xfff2f3f2, 0xfff2f2f2, 0xfff2f3f3, 0xfff2f3f2, 0xfff2f2f3, 0xfff3f2f3, + 0xfff3f2f3, 0xfff2f3f2, 0xfff3f2f2, 0xfff3f2f3, 0xfff2f2f2, 0xfff3f2f2, 0xfff3f3f3, 0xfff3f3f2, + 0xfff2f3f3, 0xfff2f3f2, 0xfff3f3f2, 0xfff3f3f2, 0xfff2f2f2, 0xfff2f3f2, 0xfff2f3f3, 0xfff2f3f3, + 0xfff3f2f2, 0xfff3f2f2, 0xfff3f2f3, 0xfff3f3f3, 0xfff3f2f3, 0xfff2f3f2, 0xfff2f2f3, 0xfff2f2f2, + 0xfff3f3f2, 0xfff2f3f3, 0xfff2f3f3, 0xfff2f3f3, 0xfff3f2f3, 0xfff2f2f3, 0xfff2f2f3, 0xfff2f3f2, + 0xfff2f3f3, 0xfff2f3f2, 0xfff2f3f3, 0xfff3f2f2, 0xfff3f3f3, 0xfff2f2f2, 0xfff2f2f3, 0xfff2f2f3, + 0xfff3f2f2, 0xfff3f3f2, 0xfff3f3f3, 0xfff3f3f3, 0xfff3f3f2, 0xfff2f2f2, 0xfff3f3f3, 0xfff3f2f2, + 0xfff3f2f2, 0xfff2f3f3, 0xfff3f2f3, 0xfff2f3f2, 0xfff2f2f2, 0xfff2f2f2, 0xfff3f3f3, 0xfff3f2f3, + 0xfff3f2f3, 0xfff2f2f3, 0xfff3f2f2, 0xfff3f3f3, 0xfff2f3f3, 0xfff3f2f2, 0xfff3f2f3, 0xfff3f3f3, + 0xfff2f3f3, 0xfff2f2f3, 0xfff2f2f3, 0xfff2f2f2, 0xfff3f3f2, 0xfff3f2f2, 0xfff3f2f2, 0xfff2f2f3, + 0xfff2f3f2, 0xfff2f3f2, 0xfff3f2f3, 0xfff2f2f2, 0xfff3f2f3, 0xfff2f2f3, 0xfff2f3f2, 0xfff3f3f2, + 0xfff2f3f3, 0xfff3f2f3, 0xfff2f2f3, 0xfff3f3f3, 0xfff3f2f2, 0xfff2f2f3, 0xfff3f3f2, 0xfff3f2f2, + 0xfff3f2f3, 0xfff2f2f3, 0xfff3f3f2, 0xfff3f3f2, 0xfff3f2f3, 0xfff2f3f2, 0xfff2f2f2, 0xfff3f2f2, + 0xfff2f3f3, 0xfff3f2f2, 0xfff2f2f3, 0xfff3f3f2, 0xfff3f2f2, 0xfff3f2f2, 0xfff3f3f3, 0xfff2f3f2, + 0xfff2f3f3, 0xfff2f3f3, 0xfff2f3f2, 0xfff3f2f3, 0xfff2f2f2, 0xfff2f3f2, 0xfff2f2f3, 0xfff3f3f3, + 0xfff3f2f3, 0xfff2f3f2, 0xfff3f2f2, 0xfff3f2f2, 0xfff3f2f2, 0xfff3f3f3, 0xfff3f3f3, 0xfff3f3f2, + 0xfff3f3f3, 0xfff3f2f2, 0xfff2f3f2, 0xfff3f2f3, 0xfff3f2f2, 0xfff2f2f3, 0xfff3f2f2, 0xfff3f2f3, + 0xfff2f2f3, 0xfff2f3f3, 0xfff2f2f2, 0xfff2f3f3, 0xfff2f2f3, 0xfff3f3f3, 0xfff2f3f2, 0xfff3f2f2, + 0xfff2f2f2, 0xfff3f2f3, 0xfff3f2f2, 0xfff2f2f3, 0xfff2f2f3, 0xfff3f2f3, 0xfff2f2f3, 0xfff2f3f2, + 0xfff3f3f3, 0xfff3f3f3, 0xfff3f2f2, 0xfff2f2f2, 0xfff2f3f3, 0xfff3f2f3, 0xfff2f3f2, 0xfff3f3f2, + 0xfff2f2f2, 0xfff3f3f2, 0xfff2f2f2, 0xfff2f3f3, 0xfff2f2f3, 0xfff3f2f3, 0xfff3f2f3, 0xfff3f2f3, + 0xfff3f3f2, 0xfff3f3f2, 0xfff3f3f2, 0xfff3f2f3, 0xfff3f2f3, 0xfff2f3f3, 0xffe9e8e9, 0xffdedbde, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff797c79, 0xffb5bab5, 0xffb5bab5, + 0xffdedbde, 0xfff2f1f2, 0xfff1f1f1, 0xfff2f2f1, 0xfff1f2f2, 0xfff2f2f2, 0xfff1f2f1, 0xfff1f1f2, + 0xfff2f2f2, 0xfff1f2f1, 0xfff1f2f2, 0xfff1f2f2, 0xfff1f2f2, 0xfff2f1f1, 0xfff2f1f2, 0xfff1f2f1, + 0xfff2f2f1, 0xfff1f1f1, 0xfff2f2f1, 0xfff1f1f1, 0xfff2f1f1, 0xfff2f1f1, 0xfff1f1f1, 0xfff2f1f2, + 0xfff1f2f2, 0xfff2f1f1, 0xfff1f2f2, 0xfff1f1f2, 0xfff1f1f1, 0xfff1f1f2, 0xfff1f2f1, 0xfff2f1f1, + 0xfff2f2f1, 0xfff1f1f1, 0xfff1f2f2, 0xfff1f2f2, 0xfff1f1f2, 0xfff1f2f2, 0xfff1f2f1, 0xfff1f1f1, + 0xfff1f2f2, 0xfff2f1f1, 0xfff2f2f2, 0xfff1f2f2, 0xfff2f2f1, 0xfff2f1f2, 0xfff2f1f2, 0xfff1f2f1, + 0xfff1f2f2, 0xfff1f1f2, 0xfff2f2f2, 0xfff1f1f2, 0xfff2f2f1, 0xfff1f2f1, 0xfff2f2f1, 0xfff1f2f2, + 0xfff1f2f1, 0xfff2f2f2, 0xfff1f1f1, 0xfff1f1f2, 0xfff1f1f2, 0xfff2f1f2, 0xfff1f1f2, 0xfff2f1f1, + 0xfff1f2f1, 0xfff2f1f1, 0xfff1f2f1, 0xfff1f2f2, 0xfff2f1f2, 0xfff1f1f1, 0xfff2f1f1, 0xfff2f1f2, + 0xfff1f2f1, 0xfff2f2f1, 0xfff2f1f1, 0xfff1f2f2, 0xfff1f1f1, 0xfff1f1f1, 0xfff2f1f2, 0xfff2f1f2, + 0xfff1f2f2, 0xfff1f1f2, 0xfff2f2f2, 0xfff2f1f1, 0xfff2f2f1, 0xfff2f2f1, 0xfff2f1f1, 0xfff1f2f1, + 0xfff2f1f1, 0xfff1f2f1, 0xfff2f1f1, 0xfff2f2f1, 0xfff1f1f2, 0xfff2f1f1, 0xfff2f1f2, 0xfff1f1f1, + 0xfff1f2f1, 0xfff2f1f1, 0xfff1f2f2, 0xfff2f2f2, 0xfff1f1f1, 0xfff1f1f1, 0xfff1f2f1, 0xfff1f1f1, + 0xfff1f1f2, 0xfff1f2f2, 0xfff1f2f1, 0xfff2f1f1, 0xfff1f1f1, 0xfff1f2f1, 0xfff1f1f2, 0xfff1f1f2, + 0xfff2f1f1, 0xfff1f1f1, 0xfff1f2f2, 0xfff1f1f2, 0xfff2f1f1, 0xfff2f2f1, 0xfff2f2f2, 0xfff2f1f1, + 0xfff1f1f1, 0xfff1f1f2, 0xfff1f1f1, 0xfff2f1f2, 0xfff1f1f1, 0xfff1f1f2, 0xfff1f2f1, 0xfff2f1f1, + 0xfff1f2f2, 0xfff1f1f2, 0xfff2f1f2, 0xfff1f1f2, 0xfff2f1f1, 0xfff2f1f1, 0xfff2f2f1, 0xfff1f1f1, + 0xfff2f2f1, 0xfff1f1f1, 0xfff1f2f2, 0xfff2f1f2, 0xfff2f1f1, 0xfff1f1f1, 0xfff1f2f1, 0xfff1f2f1, + 0xfff2f2f1, 0xfff1f1f1, 0xfff2f1f1, 0xfff1f2f2, 0xfff1f1f1, 0xfff1f2f2, 0xfff2f2f2, 0xfff2f1f2, + 0xfff2f1f1, 0xfff2f2f1, 0xfff1f1f2, 0xfff1f2f2, 0xfff2f2f1, 0xfff2f1f2, 0xfff2f1f1, 0xfff1f2f1, + 0xfff1f2f2, 0xfff2f2f1, 0xfff2f2f1, 0xfff2f1f2, 0xfff1f1f2, 0xfff2f2f2, 0xfff1f2f2, 0xfff2f1f2, + 0xfff1f2f1, 0xfff1f2f2, 0xfff1f2f2, 0xfff1f2f1, 0xfff1f2f1, 0xfff1f2f2, 0xfff1f1f1, 0xfff2f2f2, + 0xfff1f1f2, 0xfff2f1f2, 0xfff1f1f1, 0xfff1f2f1, 0xfff1f1f1, 0xfff1f2f1, 0xfff1f2f2, 0xfff2f1f1, + 0xfff2f1f1, 0xfff1f2f2, 0xfff1f2f2, 0xfff2f1f1, 0xfff2f1f2, 0xfff1f2f2, 0xfff2f1f1, 0xfff1f1f1, + 0xfff2f1f1, 0xfff2f1f2, 0xfff2f1f1, 0xfff1f1f2, 0xfff2f2f1, 0xfff1f1f1, 0xfff1f1f2, 0xfff2f1f1, + 0xfff2f1f2, 0xfff2f2f2, 0xfff1f2f2, 0xfff2f2f2, 0xfff1f2f1, 0xfff1f1f2, 0xfff2f2f2, 0xfff1f1f1, + 0xfff1f2f2, 0xfff2f1f1, 0xfff2f1f1, 0xfff2f1f2, 0xfff1f1f2, 0xfff2f1f2, 0xfff1f1f2, 0xfff1f1f1, + 0xfff2f1f2, 0xfff1f2f2, 0xfff1f1f2, 0xfff2f1f1, 0xfff2f1f1, 0xfff2f1f2, 0xffe9e8e9, 0xffdedbde, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff797c79, 0xffb5bab5, 0xffb5bab5, + 0xffdedbde, 0xfff1f0f0, 0xfff1f1f1, 0xfff1f0f0, 0xfff0f1f0, 0xfff0f0f1, 0xfff1f0f1, 0xfff0f0f1, + 0xfff0f1f1, 0xfff0f1f0, 0xfff1f1f1, 0xfff0f1f1, 0xfff1f1f1, 0xfff1f0f0, 0xfff1f0f0, 0xfff0f1f1, + 0xfff0f0f0, 0xfff0f1f0, 0xfff0f1f0, 0xfff1f1f0, 0xfff0f0f0, 0xfff1f0f0, 0xfff0f1f1, 0xfff1f1f0, + 0xfff0f1f0, 0xfff1f0f1, 0xfff0f1f1, 0xfff1f0f0, 0xfff1f1f1, 0xfff1f0f0, 0xfff1f0f0, 0xfff1f0f1, + 0xfff0f1f1, 0xfff1f1f1, 0xfff1f1f0, 0xfff1f0f1, 0xfff0f0f0, 0xfff1f1f1, 0xfff0f0f1, 0xfff0f1f0, + 0xfff1f1f0, 0xfff0f0f0, 0xfff0f1f1, 0xfff0f1f1, 0xfff1f1f0, 0xfff0f1f1, 0xfff1f1f1, 0xfff1f0f0, + 0xfff1f0f1, 0xfff1f0f1, 0xfff0f0f1, 0xfff1f1f0, 0xfff0f0f0, 0xfff0f1f0, 0xfff1f1f0, 0xfff0f0f1, + 0xfff1f0f0, 0xfff1f1f1, 0xfff1f1f1, 0xfff0f0f0, 0xfff0f0f0, 0xfff1f1f1, 0xfff1f0f0, 0xfff0f1f1, + 0xfff1f1f0, 0xfff1f0f0, 0xfff1f0f0, 0xfff1f0f1, 0xfff0f0f1, 0xfff0f0f1, 0xfff1f0f1, 0xfff1f0f1, + 0xfff1f1f1, 0xfff0f1f1, 0xfff0f0f1, 0xfff1f0f1, 0xfff0f1f1, 0xfff0f0f0, 0xfff1f1f1, 0xfff1f1f0, + 0xfff1f1f1, 0xfff1f0f0, 0xfff0f0f0, 0xfff1f0f1, 0xfff0f0f1, 0xfff0f0f0, 0xfff1f0f1, 0xfff1f1f0, + 0xfff1f0f0, 0xfff1f0f0, 0xfff0f0f0, 0xfff1f1f0, 0xfff0f0f1, 0xfff0f0f1, 0xfff1f0f0, 0xfff1f1f1, + 0xfff1f0f1, 0xfff0f0f1, 0xfff0f0f1, 0xfff0f0f0, 0xfff1f0f0, 0xfff0f0f0, 0xfff0f0f1, 0xfff1f1f1, + 0xfff0f0f0, 0xfff0f1f0, 0xfff0f0f0, 0xfff1f0f1, 0xfff0f0f0, 0xfff0f0f0, 0xfff0f1f0, 0xfff0f1f0, + 0xfff1f1f0, 0xfff1f1f1, 0xfff0f1f1, 0xfff1f0f0, 0xfff0f0f0, 0xfff1f0f0, 0xfff0f0f0, 0xfff0f0f1, + 0xfff0f0f1, 0xfff1f1f1, 0xfff0f0f0, 0xfff0f0f0, 0xfff0f1f0, 0xfff0f1f1, 0xfff1f0f0, 0xfff1f1f1, + 0xfff0f0f0, 0xfff0f1f0, 0xfff0f1f0, 0xfff1f0f0, 0xfff1f0f0, 0xfff0f1f1, 0xfff0f0f1, 0xfff1f0f0, + 0xfff0f0f1, 0xfff0f0f1, 0xfff0f0f1, 0xfff1f1f0, 0xfff1f0f0, 0xfff1f0f0, 0xfff0f1f0, 0xfff0f0f0, + 0xfff0f1f1, 0xfff0f0f0, 0xfff0f1f1, 0xfff0f0f1, 0xfff0f1f1, 0xfff1f1f0, 0xfff1f0f0, 0xfff1f1f0, + 0xfff0f0f0, 0xfff0f0f0, 0xfff0f0f0, 0xfff0f0f1, 0xfff1f0f0, 0xfff0f0f0, 0xfff0f0f0, 0xfff0f1f0, + 0xfff0f1f0, 0xfff0f0f1, 0xfff1f0f1, 0xfff0f1f1, 0xfff1f1f0, 0xfff1f1f1, 0xfff1f0f0, 0xfff0f0f0, + 0xfff0f0f1, 0xfff0f0f0, 0xfff0f0f0, 0xfff0f1f0, 0xfff1f0f1, 0xfff0f1f0, 0xfff0f1f1, 0xfff0f0f0, + 0xfff0f0f0, 0xfff0f0f0, 0xfff1f0f0, 0xfff0f1f1, 0xfff1f1f0, 0xfff0f0f0, 0xfff0f0f0, 0xfff0f0f1, + 0xfff0f0f1, 0xfff1f0f0, 0xfff0f1f1, 0xfff0f1f1, 0xfff1f1f0, 0xfff1f1f0, 0xfff0f1f0, 0xfff1f0f1, + 0xfff0f0f1, 0xfff1f1f0, 0xfff0f0f1, 0xfff0f1f0, 0xfff0f1f1, 0xfff1f0f0, 0xfff0f0f1, 0xfff1f1f0, + 0xfff0f1f0, 0xfff0f0f0, 0xfff0f0f1, 0xfff0f1f1, 0xfff0f0f1, 0xfff1f0f1, 0xfff1f1f0, 0xfff1f0f1, + 0xfff1f0f0, 0xfff0f0f1, 0xfff0f1f0, 0xfff0f0f1, 0xfff1f0f1, 0xfff1f0f0, 0xfff1f0f0, 0xfff0f0f1, + 0xfff0f0f0, 0xfff0f0f1, 0xfff1f0f0, 0xfff0f0f0, 0xfff0f0f0, 0xfff0f1f1, 0xffe9e8e9, 0xffdedbde, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xfff0eff0, 0xffefeff0, 0xfff0f0ef, 0xfff0eff0, 0xfff0eff0, 0xffefefef, 0xffeff0f0, + 0xfff0efef, 0xffefefef, 0xffefefef, 0xfff0efef, 0xffefeff0, 0xfff0efef, 0xffeff0f0, 0xfff0efef, + 0xffefefef, 0xffefefef, 0xffeff0f0, 0xfff0efef, 0xffefefef, 0xffeff0f0, 0xffefeff0, 0xffefefef, + 0xfff0f0f0, 0xfff0eff0, 0xfff0efef, 0xfff0eff0, 0xfff0efef, 0xfff0f0ef, 0xfff0eff0, 0xfff0efef, + 0xffeff0f0, 0xffefeff0, 0xfff0efef, 0xfff0f0ef, 0xffefeff0, 0xffeff0f0, 0xfff0f0f0, 0xfff0efef, + 0xfff0f0ef, 0xffefefef, 0xffeff0f0, 0xfff0f0ef, 0xffefefef, 0xffefefef, 0xffefefef, 0xfff0eff0, + 0xffefefef, 0xffefefef, 0xfff0eff0, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xfff0efef, + 0xfff0efef, 0xfff0f0f0, 0xffeff0ef, 0xffeff0f0, 0xfff0f0f0, 0xffefefef, 0xffefefef, 0xfff0f0f0, + 0xffefefef, 0xffefefef, 0xffefefef, 0xfff0efef, 0xfff0f0f0, 0xfff0f0f0, 0xfff0efef, 0xffeff0f0, + 0xfff0efef, 0xffefeff0, 0xfff0eff0, 0xffeff0ef, 0xfff0eff0, 0xfff0eff0, 0xfff0eff0, 0xffeff0f0, + 0xffeff0ef, 0xfff0eff0, 0xffeff0f0, 0xfff0eff0, 0xffefefef, 0xfff0efef, 0xfff0f0ef, 0xffefefef, + 0xffeff0f0, 0xffeff0ef, 0xffefeff0, 0xffeff0ef, 0xffeff0ef, 0xffefeff0, 0xfff0f0f0, 0xffefefef, + 0xffefeff0, 0xfff0f0ef, 0xfff0efef, 0xfff0efef, 0xffefeff0, 0xfff0f0ef, 0xffeff0ef, 0xffefefef, + 0xfff0efef, 0xffefefef, 0xffefefef, 0xfff0f0f0, 0xfff0f0ef, 0xfff0f0ef, 0xffeff0f0, 0xfff0f0ef, + 0xffefefef, 0xfff0eff0, 0xfff0efef, 0xfff0efef, 0xffefeff0, 0xfff0efef, 0xffeff0f0, 0xfff0f0ef, + 0xffeff0f0, 0xffefefef, 0xffefeff0, 0xfff0eff0, 0xfff0efef, 0xfff0f0f0, 0xfff0efef, 0xfff0f0ef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffeff0f0, 0xfff0eff0, 0xffefeff0, 0xffeff0ef, 0xffefefef, + 0xffeff0f0, 0xffefeff0, 0xffefeff0, 0xffefeff0, 0xffeff0ef, 0xffefeff0, 0xffeff0ef, 0xfff0eff0, + 0xffeff0ef, 0xfff0eff0, 0xfff0efef, 0xfff0f0ef, 0xffeff0f0, 0xfff0efef, 0xffeff0f0, 0xfff0f0ef, + 0xfff0efef, 0xfff0efef, 0xffefefef, 0xffefeff0, 0xffefefef, 0xfff0efef, 0xffefefef, 0xfff0efef, + 0xfff0f0f0, 0xfff0f0ef, 0xfff0efef, 0xfff0eff0, 0xffefeff0, 0xffefefef, 0xffeff0ef, 0xffeff0ef, + 0xffefeff0, 0xffeff0ef, 0xfff0f0ef, 0xfff0efef, 0xffeff0ef, 0xfff0f0f0, 0xfff0f0ef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffeff0ef, 0xfff0f0ef, 0xffefeff0, 0xffefeff0, 0xffefefef, 0xffefefef, + 0xffefeff0, 0xfff0eff0, 0xffeff0f0, 0xffeff0ef, 0xffefefef, 0xffeff0ef, 0xffeff0ef, 0xfff0f0f0, + 0xfff0f0f0, 0xfff0eff0, 0xfff0efef, 0xffefefef, 0xfff0eff0, 0xffeff0f0, 0xffefeff0, 0xffefeff0, + 0xfff0f0ef, 0xfff0f0ef, 0xffefefef, 0xffefeff0, 0xfff0efef, 0xfff0f0f0, 0xfff0efef, 0xffefefef, + 0xfff0eff0, 0xffefefef, 0xffefeff0, 0xffeff0ef, 0xfff0efef, 0xffefefef, 0xffefeff0, 0xffeff0f0, + 0xffeff0ef, 0xfff0f0ef, 0xffeff0ef, 0xffefefef, 0xffefeff0, 0xffefefef, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffefeeee, 0xffeeeeee, 0xffeeefee, 0xffeeeeee, 0xffeeeeef, 0xffeeeeee, 0xffefefee, + 0xffeeefef, 0xffeeefee, 0xffefefee, 0xffefefee, 0xffefefee, 0xffeeefee, 0xffeeeeee, 0xffeeeeee, + 0xffefefef, 0xffeeeeee, 0xffeeeeee, 0xffeeeeef, 0xffefeeee, 0xffefefee, 0xffeeefee, 0xffeeeeee, + 0xffeeeeee, 0xffeeefef, 0xffeeeeee, 0xffeeefee, 0xffeeefef, 0xffefeeee, 0xffefeeee, 0xffeeeeef, + 0xffeeeeee, 0xffeeefee, 0xffeeeeef, 0xffeeeeee, 0xffeeeeef, 0xffeeefee, 0xffefeeef, 0xffefeeee, + 0xffeeefee, 0xffefeeef, 0xffefeeee, 0xffefefee, 0xffefefef, 0xffefeeef, 0xffefefef, 0xffeeeeee, + 0xffeeefee, 0xffeeefee, 0xffeeeeee, 0xffeeeeee, 0xffefeeef, 0xffeeefef, 0xffefeeee, 0xffeeefee, + 0xffeeeeee, 0xffeeefef, 0xffeeefee, 0xffefeeee, 0xffeeefef, 0xffeeeeef, 0xffeeefee, 0xffefeeef, + 0xffeeefee, 0xffefefee, 0xffeeefee, 0xffeeefee, 0xffeeefee, 0xffeeefef, 0xffefeeef, 0xffeeefee, + 0xffefefef, 0xffeeeeef, 0xffefefee, 0xffeeeeee, 0xffefefee, 0xffefeeef, 0xffefeeee, 0xffefefee, + 0xffeeefee, 0xffeeefee, 0xffeeeeef, 0xffeeeeee, 0xffefeeef, 0xffeeeeef, 0xffeeeeee, 0xffeeefee, + 0xffeeeeef, 0xffefeeef, 0xffeeeeef, 0xffeeefef, 0xffefefef, 0xffefefee, 0xffefeeef, 0xffeeeeef, + 0xffeeeeee, 0xffeeefee, 0xffefeeee, 0xffeeeeee, 0xffeeeeef, 0xffeeeeee, 0xffefefef, 0xffefeeee, + 0xffefeeee, 0xffeeefef, 0xffeeeeef, 0xffefeeee, 0xffefeeee, 0xffefeeef, 0xffeeeeee, 0xffeeeeee, + 0xffefefef, 0xffeeefef, 0xffefeeee, 0xffefefef, 0xffeeeeee, 0xffefeeee, 0xffeeeeee, 0xffeeeeee, + 0xffefeeef, 0xffeeefee, 0xffeeeeee, 0xffeeefef, 0xffeeeeee, 0xffeeefef, 0xffeeeeef, 0xffeeeeee, + 0xffefefef, 0xffeeefee, 0xffeeefef, 0xffeeeeef, 0xffeeeeef, 0xffefefee, 0xffefeeef, 0xffeeeeee, + 0xffeeeeee, 0xffefefef, 0xffeeeeef, 0xffefeeef, 0xffeeeeee, 0xffeeefee, 0xffefefef, 0xffefeeee, + 0xffeeefef, 0xffeeefef, 0xffefefef, 0xffeeeeef, 0xffeeeeee, 0xffefeeee, 0xffeeeeee, 0xffeeeeee, + 0xffeeeeee, 0xffeeefee, 0xffeeeeee, 0xffefeeee, 0xffefefef, 0xffeeefee, 0xffefeeee, 0xffeeefef, + 0xffefeeee, 0xffefeeee, 0xffeeeeee, 0xffeeeeee, 0xffefeeef, 0xffefeeee, 0xffefeeee, 0xffeeefef, + 0xffeeefee, 0xffeeefee, 0xffeeeeee, 0xffefefef, 0xffeeefee, 0xffefeeee, 0xffeeeeee, 0xffefefee, + 0xffefefee, 0xffeeeeee, 0xffeeeeee, 0xffeeeeee, 0xffeeefee, 0xffeeeeef, 0xffefeeef, 0xffefeeee, + 0xffeeeeee, 0xffefefee, 0xffefefee, 0xffeeefee, 0xffefefee, 0xffefeeee, 0xffeeefef, 0xffeeefee, + 0xffeeeeee, 0xffeeeeef, 0xffeeeeef, 0xffeeeeee, 0xffeeeeef, 0xffefeeef, 0xffefeeee, 0xffeeefef, + 0xffeeeeee, 0xffefefee, 0xffeeeeee, 0xffefeeef, 0xffeeefef, 0xffeeeeee, 0xffeeeeee, 0xffeeeeef, + 0xffefeeef, 0xffeeeeee, 0xffeeeeee, 0xffeeeeee, 0xffefeeef, 0xffefeeef, 0xffeeeeee, 0xffeeeeef, + 0xffefefee, 0xffeeeeee, 0xffefefef, 0xffeeefee, 0xffeeeeef, 0xffeeeeef, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffeeeded, 0xffeeedee, 0xffeeeded, 0xffeeeded, 0xffededed, 0xffedeeed, 0xffedeeed, + 0xffedeeee, 0xffeeeded, 0xffedeeee, 0xffedeeed, 0xffeeedee, 0xffeeeeed, 0xffededed, 0xffeeeded, + 0xffeeeded, 0xffededee, 0xffeeeded, 0xffededed, 0xffededed, 0xffedeeed, 0xffeeedee, 0xffeeeded, + 0xffededee, 0xffeeeded, 0xffededed, 0xffededee, 0xffeeeeed, 0xffededed, 0xffededed, 0xffeeedee, + 0xffeeeded, 0xffedeeed, 0xffedeeed, 0xffededed, 0xffededed, 0xffeeeded, 0xffededed, 0xffededed, + 0xffeeeeed, 0xffedeeed, 0xffededed, 0xffedeeed, 0xffededed, 0xffeeeeed, 0xffeeeded, 0xffeeeded, + 0xffeeeeed, 0xffeeedee, 0xffeeeded, 0xffeeeeee, 0xffedeeed, 0xffeeeded, 0xffedeeee, 0xffededee, + 0xffeeeded, 0xffeeedee, 0xffedeeee, 0xffededee, 0xffededed, 0xffedeeee, 0xffeeeded, 0xffeeedee, + 0xffededed, 0xffeeedee, 0xffedeeee, 0xffeeedee, 0xffeeeeee, 0xffededee, 0xffededee, 0xffeeedee, + 0xffedeeed, 0xffededed, 0xffeeeded, 0xffeeedee, 0xffededee, 0xffeeeded, 0xffededee, 0xffededed, + 0xffedeeed, 0xffedeeed, 0xffededed, 0xffededed, 0xffededed, 0xffededed, 0xffedeeee, 0xffededee, + 0xffeeeded, 0xffededed, 0xffeeeded, 0xffededed, 0xffedeeed, 0xffeeedee, 0xffededed, 0xffedeeed, + 0xffeeedee, 0xffededed, 0xffeeedee, 0xffededed, 0xffededed, 0xffeeedee, 0xffedeeed, 0xffeeeded, + 0xffedeeed, 0xffededee, 0xffeeedee, 0xffeeeeed, 0xffedeeed, 0xffeeeeed, 0xffededee, 0xffededee, + 0xffedeeed, 0xffeeeded, 0xffededed, 0xffedeeed, 0xffeeeeee, 0xffeeeded, 0xffeeeeed, 0xffeeeded, + 0xffeeedee, 0xffededed, 0xffeeeded, 0xffeeeeed, 0xffededee, 0xffeeeeee, 0xffededed, 0xffeeeeed, + 0xffeeeded, 0xffeeedee, 0xffededed, 0xffeeedee, 0xffeeeeed, 0xffedeeee, 0xffeeedee, 0xffededed, + 0xffeeeeed, 0xffededed, 0xffeeeded, 0xffededed, 0xffededee, 0xffedeeed, 0xffeeeeed, 0xffeeeeee, + 0xffedeeee, 0xffededed, 0xffeeeded, 0xffeeeeee, 0xffeeedee, 0xffededed, 0xffeeedee, 0xffedeeed, + 0xffeeeeed, 0xffededed, 0xffededed, 0xffedeeee, 0xffedeeed, 0xffedeeed, 0xffededee, 0xffeeeeee, + 0xffededed, 0xffeeeeee, 0xffedeeed, 0xffeeeded, 0xffeeeeed, 0xffeeeeee, 0xffedeeed, 0xffeeedee, + 0xffedeeee, 0xffededee, 0xffeeeded, 0xffedeeed, 0xffeeeded, 0xffedeeed, 0xffededee, 0xffededee, + 0xffeeeded, 0xffededee, 0xffededed, 0xffeeeded, 0xffedeeed, 0xffeeeeed, 0xffededee, 0xffeeedee, + 0xffededed, 0xffeeedee, 0xffeeedee, 0xffededed, 0xffedeeed, 0xffedeeee, 0xffeeeeee, 0xffededee, + 0xffededee, 0xffedeeed, 0xffeeeeed, 0xffedeeee, 0xffededed, 0xffeeeeed, 0xffedeeed, 0xffededed, + 0xffededee, 0xffeeedee, 0xffeeeeed, 0xffedeeee, 0xffeeedee, 0xffedeeee, 0xffededed, 0xffedeeed, + 0xffedeeed, 0xffededed, 0xffeeeded, 0xffedeeed, 0xffeeeded, 0xffedeeed, 0xffededed, 0xffeeeeed, + 0xffedeeed, 0xffeeeeee, 0xffedeeee, 0xffedeeed, 0xffedeeed, 0xffeeeded, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffecedec, 0xffedeced, 0xffededec, 0xffececec, 0xffedeced, 0xffeceded, 0xffedeced, + 0xffeceded, 0xffededed, 0xffedecec, 0xffecedec, 0xffececec, 0xffeceded, 0xffececec, 0xffededed, + 0xffeceded, 0xffeceded, 0xffededec, 0xffedeced, 0xffedeced, 0xffededec, 0xffedeced, 0xffedeced, + 0xffecedec, 0xffecedec, 0xffececec, 0xffecedec, 0xffededec, 0xffecedec, 0xffececec, 0xffecedec, + 0xffececed, 0xffececec, 0xffededec, 0xffececed, 0xffecedec, 0xffededec, 0xffececed, 0xffedecec, + 0xffececec, 0xffecedec, 0xffededec, 0xffecedec, 0xffeceded, 0xffedecec, 0xffedeced, 0xffececed, + 0xffecedec, 0xffedecec, 0xffeceded, 0xffececec, 0xffededed, 0xffececed, 0xffedecec, 0xffededec, + 0xffeceded, 0xffededed, 0xffededec, 0xffedecec, 0xffececec, 0xffececed, 0xffececed, 0xffeceded, + 0xffededec, 0xffececed, 0xffececec, 0xffecedec, 0xffededec, 0xffecedec, 0xffececed, 0xffededed, + 0xffececec, 0xffececed, 0xffedeced, 0xffececed, 0xffecedec, 0xffedeced, 0xffececed, 0xffecedec, + 0xffececec, 0xffececec, 0xffedecec, 0xffededed, 0xffededec, 0xffececed, 0xffececec, 0xffececed, + 0xffececec, 0xffedeced, 0xffececed, 0xffececed, 0xffececec, 0xffededed, 0xffededed, 0xffedecec, + 0xffedeced, 0xffedecec, 0xffececec, 0xffedecec, 0xffeceded, 0xffedecec, 0xffececed, 0xffeceded, + 0xffececec, 0xffececed, 0xffededec, 0xffeceded, 0xffececed, 0xffececed, 0xffeceded, 0xffededec, + 0xffececed, 0xffeceded, 0xffedecec, 0xffececed, 0xffededec, 0xffecedec, 0xffececec, 0xffedecec, + 0xffedeced, 0xffececec, 0xffedecec, 0xffececed, 0xffededec, 0xffeceded, 0xffededec, 0xffececec, + 0xffedecec, 0xffededec, 0xffededec, 0xffececec, 0xffececed, 0xffecedec, 0xffececec, 0xffecedec, + 0xffececec, 0xffededec, 0xffedeced, 0xffedecec, 0xffececec, 0xffededed, 0xffecedec, 0xffededec, + 0xffedeced, 0xffedeced, 0xffecedec, 0xffecedec, 0xffececec, 0xffececed, 0xffedecec, 0xffececec, + 0xffececec, 0xffedeced, 0xffeceded, 0xffececec, 0xffececec, 0xffececec, 0xffececec, 0xffececec, + 0xffedeced, 0xffececed, 0xffededed, 0xffedeced, 0xffededed, 0xffedecec, 0xffececed, 0xffededed, + 0xffedeced, 0xffececed, 0xffedecec, 0xffececed, 0xffededec, 0xffededed, 0xffededec, 0xffecedec, + 0xffececec, 0xffececed, 0xffececec, 0xffedeced, 0xffededec, 0xffedeced, 0xffedecec, 0xffedeced, + 0xffececed, 0xffededed, 0xffececec, 0xffedeced, 0xffececed, 0xffedeced, 0xffececec, 0xffececed, + 0xffececed, 0xffececec, 0xffededed, 0xffedecec, 0xffecedec, 0xffecedec, 0xffededec, 0xffededed, + 0xffececec, 0xffececec, 0xffedeced, 0xffededec, 0xffececed, 0xffeceded, 0xffeceded, 0xffecedec, + 0xffeceded, 0xffececec, 0xffececec, 0xffedecec, 0xffecedec, 0xffeceded, 0xffececec, 0xffedeced, + 0xffedeced, 0xffecedec, 0xffededed, 0xffededec, 0xffededed, 0xffededed, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffebebeb, 0xffebebec, 0xffecebeb, 0xffebecec, 0xffebecec, 0xffececeb, 0xffebebec, + 0xffebecec, 0xffebebeb, 0xffebecec, 0xffecebec, 0xffecebeb, 0xffebebeb, 0xffecebec, 0xffecebeb, + 0xffebeceb, 0xffebebec, 0xffecebeb, 0xffececeb, 0xffecebeb, 0xffebeceb, 0xffebebec, 0xffebecec, + 0xffebecec, 0xffecebec, 0xffecebec, 0xffecebec, 0xffecebec, 0xffecebeb, 0xffecebec, 0xffecebec, + 0xffecebeb, 0xffebebeb, 0xffebeceb, 0xffececec, 0xffecebeb, 0xffecebec, 0xffebecec, 0xffebeceb, + 0xffebebec, 0xffececec, 0xffecebeb, 0xffecebec, 0xffececeb, 0xffececeb, 0xffebeceb, 0xffebebec, + 0xffececeb, 0xffebebec, 0xffecebec, 0xffececec, 0xffececeb, 0xffebeceb, 0xffebecec, 0xffecebeb, + 0xffebecec, 0xffebecec, 0xffececec, 0xffecebeb, 0xffecebec, 0xffececec, 0xffebecec, 0xffebecec, + 0xffececec, 0xffebebeb, 0xffececeb, 0xffececeb, 0xffecebec, 0xffecebeb, 0xffececeb, 0xffebebec, + 0xffecebec, 0xffececeb, 0xffececec, 0xffebebec, 0xffebebeb, 0xffececec, 0xffebecec, 0xffebebec, + 0xffececec, 0xffebebec, 0xffebecec, 0xffecebec, 0xffebebeb, 0xffecebec, 0xffebebec, 0xffececeb, + 0xffecebeb, 0xffececec, 0xffececeb, 0xffebebeb, 0xffecebeb, 0xffebebec, 0xffebebec, 0xffececeb, + 0xffececeb, 0xffebeceb, 0xffececeb, 0xffececeb, 0xffebebeb, 0xffebebec, 0xffececeb, 0xffebebec, + 0xffececeb, 0xffecebeb, 0xffebebec, 0xffecebec, 0xffecebec, 0xffececec, 0xffebeceb, 0xffececec, + 0xffebebec, 0xffebecec, 0xffebebeb, 0xffecebeb, 0xffebebeb, 0xffececec, 0xffebecec, 0xffececeb, + 0xffececeb, 0xffebecec, 0xffecebec, 0xffececeb, 0xffebeceb, 0xffececeb, 0xffebecec, 0xffecebec, + 0xffebebec, 0xffebecec, 0xffebeceb, 0xffebebeb, 0xffebecec, 0xffecebec, 0xffecebeb, 0xffebeceb, + 0xffebeceb, 0xffecebec, 0xffececec, 0xffecebeb, 0xffececeb, 0xffececeb, 0xffecebec, 0xffecebec, + 0xffebebec, 0xffebecec, 0xffececec, 0xffebebeb, 0xffecebeb, 0xffececeb, 0xffebebec, 0xffebebec, + 0xffecebeb, 0xffebebec, 0xffebebeb, 0xffebebeb, 0xffebecec, 0xffebecec, 0xffebeceb, 0xffececec, + 0xffebeceb, 0xffecebeb, 0xffecebeb, 0xffececec, 0xffebecec, 0xffebecec, 0xffebeceb, 0xffebecec, + 0xffebecec, 0xffebecec, 0xffebebec, 0xffebeceb, 0xffebebeb, 0xffecebeb, 0xffebebec, 0xffebecec, + 0xffececeb, 0xffebebec, 0xffecebec, 0xffebebeb, 0xffececec, 0xffecebeb, 0xffebebec, 0xffebecec, + 0xffebebec, 0xffebebeb, 0xffecebec, 0xffecebeb, 0xffebebeb, 0xffecebec, 0xffebecec, 0xffebebeb, + 0xffebeceb, 0xffececec, 0xffececec, 0xffecebec, 0xffebebec, 0xffececec, 0xffecebeb, 0xffebeceb, + 0xffebebec, 0xffececeb, 0xffebebec, 0xffebecec, 0xffecebec, 0xffebeceb, 0xffebecec, 0xffecebeb, + 0xffecebec, 0xffebeceb, 0xffecebec, 0xffebecec, 0xffebeceb, 0xffebeceb, 0xffecebeb, 0xffececeb, + 0xffebebec, 0xffececec, 0xffececeb, 0xffecebec, 0xffebebeb, 0xffebebec, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffebebeb, 0xffeaebeb, 0xffeaeaea, 0xffebebeb, 0xffebeaeb, 0xffeaeaea, 0xffebeaeb, + 0xffeaebea, 0xffebebea, 0xffebeaea, 0xffeaebea, 0xffebebea, 0xffebeaeb, 0xffeaebea, 0xffebeaea, + 0xffeaebea, 0xffeaeaeb, 0xffebeaeb, 0xffeaeaea, 0xffebebea, 0xffeaebeb, 0xffebebeb, 0xffeaebeb, + 0xffebebeb, 0xffebebeb, 0xffeaebeb, 0xffebeaea, 0xffebebeb, 0xffebebeb, 0xffebebeb, 0xffeaebea, + 0xffeaeaeb, 0xffebebeb, 0xffebebea, 0xffebebeb, 0xffebeaeb, 0xffebebeb, 0xffebebea, 0xffebebeb, + 0xffebebeb, 0xffebebeb, 0xffebeaea, 0xffeaebeb, 0xffeaebea, 0xffeaeaeb, 0xffeaeaeb, 0xffebebeb, + 0xffebeaeb, 0xffebebea, 0xffeaeaeb, 0xffebebeb, 0xffebeaeb, 0xffeaebeb, 0xffebebeb, 0xffebebea, + 0xffeaeaea, 0xffeaeaeb, 0xffebeaeb, 0xffebebeb, 0xffebebea, 0xffebebea, 0xffebeaea, 0xffebebeb, + 0xffeaebeb, 0xffebebea, 0xffebebea, 0xffebeaeb, 0xffeaebea, 0xffebebea, 0xffeaeaea, 0xffeaebea, + 0xffeaebea, 0xffebebea, 0xffebeaeb, 0xffebebeb, 0xffeaebea, 0xffebebea, 0xffeaeaeb, 0xffeaebeb, + 0xffebebeb, 0xffebeaeb, 0xffebeaeb, 0xffeaebeb, 0xffebebea, 0xffeaebea, 0xffebebea, 0xffeaeaeb, + 0xffebebeb, 0xffebebeb, 0xffeaeaea, 0xffeaebeb, 0xffebeaeb, 0xffeaebeb, 0xffeaebeb, 0xffebebeb, + 0xffebebea, 0xffebebeb, 0xffeaebeb, 0xffeaebea, 0xffebebea, 0xffebebeb, 0xffebebeb, 0xffeaebeb, + 0xffebebeb, 0xffebeaeb, 0xffebeaeb, 0xffebebeb, 0xffebeaeb, 0xffeaebea, 0xffeaeaea, 0xffebebea, + 0xffeaeaea, 0xffebebeb, 0xffeaeaeb, 0xffebeaeb, 0xffebeaeb, 0xffebeaeb, 0xffeaebea, 0xffebeaea, + 0xffeaeaea, 0xffebebeb, 0xffebeaea, 0xffeaeaeb, 0xffeaebeb, 0xffeaebea, 0xffeaeaea, 0xffebebea, + 0xffeaebea, 0xffeaebea, 0xffebebeb, 0xffebeaeb, 0xffeaebeb, 0xffebebeb, 0xffebeaeb, 0xffebeaeb, + 0xffeaebeb, 0xffebebea, 0xffebebea, 0xffebebea, 0xffebebea, 0xffebebeb, 0xffeaebeb, 0xffeaebea, + 0xffebebeb, 0xffebebeb, 0xffebeaeb, 0xffeaebea, 0xffebeaeb, 0xffebebea, 0xffebebea, 0xffebebeb, + 0xffebebea, 0xffeaebeb, 0xffebeaeb, 0xffeaebeb, 0xffebeaea, 0xffeaebeb, 0xffeaebea, 0xffeaeaeb, + 0xffebebeb, 0xffebeaea, 0xffebebea, 0xffebeaeb, 0xffebebeb, 0xffebeaea, 0xffeaeaeb, 0xffebeaeb, + 0xffebebea, 0xffebebeb, 0xffebeaeb, 0xffebeaeb, 0xffebeaea, 0xffebeaea, 0xffebeaeb, 0xffebeaeb, + 0xffebeaeb, 0xffeaeaeb, 0xffebeaea, 0xffebeaeb, 0xffeaebeb, 0xffeaebeb, 0xffebebeb, 0xffebebea, + 0xffeaebea, 0xffebeaea, 0xffeaebea, 0xffebebeb, 0xffebebeb, 0xffeaebeb, 0xffebebeb, 0xffeaeaeb, + 0xffeaebeb, 0xffebebeb, 0xffebebeb, 0xffeaebea, 0xffeaebeb, 0xffeaebeb, 0xffebebeb, 0xffeaebeb, + 0xffebebea, 0xffebebeb, 0xffeaeaeb, 0xffebebeb, 0xffebebeb, 0xffebebea, 0xffeaebeb, 0xffeaebea, + 0xffeaeaeb, 0xffebebea, 0xffebeaea, 0xffebebea, 0xffebeaea, 0xffebebea, 0xffebebea, 0xffebebeb, + 0xffebebea, 0xffebebeb, 0xffebebea, 0xffebebeb, 0xffeaebeb, 0xffebebeb, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffe9eae9, 0xffeaeaea, 0xffe9eaea, + 0xffeae9ea, 0xffeaeae9, 0xffeaeae9, 0xffeae9e9, 0xffeaeaea, 0xffeaeaea, 0xffeae9ea, 0xffeaeaea, + 0xffe9eae9, 0xffeaeaea, 0xffe9e9ea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, + 0xffeaeae9, 0xffe9e9e9, 0xffe9eaea, 0xffeae9ea, 0xffeaeaea, 0xffeae9e9, 0xffeae9ea, 0xffe9e9e9, + 0xffeaeaea, 0xffeaeaea, 0xffe9e9ea, 0xffe9eaea, 0xffeaeae9, 0xffeaeaea, 0xffeae9ea, 0xffe9eaea, + 0xffe9eaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffe9eae9, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, + 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeae9ea, 0xffeaeaea, 0xffeae9ea, 0xffeae9ea, 0xffe9eaea, + 0xffeaeaea, 0xffeaeaea, 0xffeae9e9, 0xffeaeaea, 0xffeaeaea, 0xffeae9ea, 0xffeae9e9, 0xffe9eaea, + 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, 0xffeae9e9, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffe9e9ea, + 0xffeaeaea, 0xffeaeae9, 0xffeaeaea, 0xffeae9ea, 0xffe9eaea, 0xffeaeae9, 0xffeaeae9, 0xffeaeaea, + 0xffeaeaea, 0xffe9eaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, 0xffeaeaea, 0xffe9eaea, 0xffeae9ea, + 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, 0xffe9eae9, 0xffeaeaea, 0xffe9eaea, 0xffeaeaea, 0xffeaeaea, + 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, 0xffeaeae9, 0xffe9eaea, 0xffe9eaea, 0xffeaeaea, + 0xffeaeaea, 0xffeae9e9, 0xffeaeaea, 0xffeaeae9, 0xffeaeae9, 0xffeaeaea, 0xffeaeae9, 0xffeaeaea, + 0xffeaeaea, 0xffeaeae9, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, + 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, 0xffeaeaea, 0xffeaeae9, 0xffeaeaea, 0xffeaeaea, 0xffe9eaea, + 0xffeaeaea, 0xffe9eae9, 0xffeaeae9, 0xffeae9ea, 0xffeaeaea, 0xffe9eaea, 0xffe9eaea, 0xffeae9ea, + 0xffeaeae9, 0xffeaeaea, 0xffeae9e9, 0xffeaeaea, 0xffe9eaea, 0xffeae9ea, 0xffeaeaea, 0xffeaeaea, + 0xffe9eaea, 0xffeae9ea, 0xffeaeae9, 0xffeae9e9, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, + 0xffeaeaea, 0xffeaeaea, 0xffe9eaea, 0xffe9e9ea, 0xffe9eae9, 0xffeaeaea, 0xffeaeae9, 0xffeaeaea, + 0xffeaeae9, 0xffeae9ea, 0xffeaeae9, 0xffeaeae9, 0xffe9eaea, 0xffeaeaea, 0xffeaeae9, 0xffe9eaea, + 0xffeaeaea, 0xffeaeae9, 0xffeae9ea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffe9eaea, 0xffeae9ea, + 0xffeaeae9, 0xffeae9ea, 0xffe9eaea, 0xffeaeae9, 0xffeaeae9, 0xffeae9ea, 0xffeaeaea, 0xffe9eaea, + 0xffeaeaea, 0xffeaeaea, 0xffeae9ea, 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, 0xffe9eaea, 0xffe9e9ea, + 0xffeaeaea, 0xffe9e9ea, 0xffe9eaea, 0xffeae9ea, 0xffe9e9e9, 0xffeaeaea, 0xffeaeaea, 0xffeaeae9, + 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeae9ea, 0xffeaeaea, 0xffeaeaea, 0xffe9e9ea, 0xffeaeaea, + 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffeaeaea, 0xffe9eaea, + 0xffeaeaea, 0xffe9eae9, 0xffeaeaea, 0xffeae9ea, 0xffeaeae9, 0xffeaeaea, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffeae9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, + 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe9e9e9, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffe8e8e8, 0xffe8e8e9, 0xffe9e9e9, 0xffe8e8e8, 0xffe9e8e9, 0xffe8e8e9, 0xffe8e8e9, + 0xffe8e8e9, 0xffe8e8e8, 0xffe8e8e9, 0xffe8e8e9, 0xffe8e9e9, 0xffe9e8e8, 0xffe9e8e8, 0xffe8e9e8, + 0xffe8e9e9, 0xffe8e8e8, 0xffe8e8e9, 0xffe9e8e8, 0xffe8e9e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e9e9, + 0xffe9e8e8, 0xffe8e8e9, 0xffe9e8e9, 0xffe9e9e8, 0xffe9e8e8, 0xffe8e9e8, 0xffe8e9e8, 0xffe8e8e8, + 0xffe8e9e8, 0xffe8e8e9, 0xffe8e8e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e8e9, 0xffe8e9e8, 0xffe8e8e8, + 0xffe8e9e8, 0xffe8e8e8, 0xffe8e9e8, 0xffe8e9e8, 0xffe8e9e9, 0xffe8e8e8, 0xffe9e8e9, 0xffe8e8e8, + 0xffe8e9e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe9e9e8, 0xffe8e8e8, 0xffe8e9e9, 0xffe8e8e9, 0xffe8e8e8, + 0xffe8e9e8, 0xffe9e9e8, 0xffe8e8e8, 0xffe9e9e9, 0xffe8e8e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e8e9, + 0xffe8e9e8, 0xffe8e8e9, 0xffe8e9e9, 0xffe9e8e8, 0xffe8e8e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe9e8e9, + 0xffe8e8e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e9e8, 0xffe9e8e9, 0xffe8e8e8, 0xffe8e8e9, + 0xffe8e8e8, 0xffe9e9e8, 0xffe9e8e9, 0xffe8e8e9, 0xffe8e9e8, 0xffe9e8e9, 0xffe8e9e8, 0xffe8e9e9, + 0xffe8e8e8, 0xffe9e9e8, 0xffe8e9e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e8e9, 0xffe8e9e9, 0xffe8e8e8, + 0xffe8e8e8, 0xffe8e8e9, 0xffe8e9e8, 0xffe8e9e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe9e8e8, 0xffe8e8e9, + 0xffe8e9e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, + 0xffe8e8e9, 0xffe8e8e9, 0xffe8e8e8, 0xffe8e8e8, 0xffe9e9e8, 0xffe8e9e9, 0xffe8e8e8, 0xffe8e8e8, + 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe9e9e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e9e8, + 0xffe8e8e9, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e9e9, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e9e8, + 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe9e8e8, 0xffe8e8e9, 0xffe9e9e8, + 0xffe8e8e8, 0xffe9e9e8, 0xffe8e9e9, 0xffe8e9e8, 0xffe9e8e9, 0xffe8e9e8, 0xffe8e8e8, 0xffe8e8e8, + 0xffe8e8e8, 0xffe9e8e8, 0xffe9e8e8, 0xffe9e8e9, 0xffe8e8e9, 0xffe8e9e8, 0xffe9e8e8, 0xffe8e9e9, + 0xffe9e8e9, 0xffe9e8e8, 0xffe8e8e9, 0xffe9e8e8, 0xffe8e9e8, 0xffe8e9e8, 0xffe8e8e8, 0xffe9e9e8, + 0xffe8e8e8, 0xffe8e8e9, 0xffe8e9e9, 0xffe8e9e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, + 0xffe8e8e8, 0xffe8e9e8, 0xffe8e9e9, 0xffe8e8e8, 0xffe8e8e9, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e9, + 0xffe8e9e8, 0xffe8e9e8, 0xffe8e8e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e9e8, 0xffe8e8e8, 0xffe8e8e8, + 0xffe9e8e9, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e9e9, 0xffe9e8e8, 0xffe8e8e8, 0xffe9e8e8, + 0xffe9e8e8, 0xffe8e9e8, 0xffe9e8e8, 0xffe8e8e8, 0xffe8e9e8, 0xffe8e9e8, 0xffe8e8e8, 0xffe8e8e8, + 0xffe8e8e8, 0xffe8e9e8, 0xffe8e8e8, 0xffe9e8e9, 0xffe9e9e9, 0xffe8e8e8, 0xffe8e9e9, 0xffe9e8e8, + 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e9e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffe7e8e8, 0xffe8e7e8, 0xffe8e7e8, 0xffe7e8e7, 0xffe8e7e8, 0xffe7e7e8, 0xffe7e8e8, + 0xffe7e7e8, 0xffe8e7e8, 0xffe8e8e8, 0xffe7e8e7, 0xffe8e8e8, 0xffe7e8e8, 0xffe8e7e7, 0xffe8e8e7, + 0xffe7e7e7, 0xffe8e8e8, 0xffe7e7e7, 0xffe7e8e7, 0xffe8e8e7, 0xffe8e8e8, 0xffe7e7e8, 0xffe8e8e7, + 0xffe8e8e8, 0xffe8e8e7, 0xffe7e7e7, 0xffe7e8e7, 0xffe8e8e7, 0xffe8e8e7, 0xffe8e7e8, 0xffe8e7e8, + 0xffe7e8e7, 0xffe7e7e8, 0xffe8e8e8, 0xffe7e7e7, 0xffe7e8e8, 0xffe7e7e7, 0xffe7e8e7, 0xffe7e8e8, + 0xffe8e7e8, 0xffe7e7e7, 0xffe8e8e7, 0xffe7e8e7, 0xffe7e8e8, 0xffe8e8e8, 0xffe8e8e7, 0xffe8e8e8, + 0xffe7e7e7, 0xffe7e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e7e8, 0xffe8e7e8, 0xffe8e8e8, 0xffe7e8e8, + 0xffe7e8e7, 0xffe7e7e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e7e7, 0xffe8e8e7, 0xffe8e8e8, + 0xffe8e8e7, 0xffe7e7e8, 0xffe7e7e8, 0xffe8e8e7, 0xffe8e7e8, 0xffe8e7e7, 0xffe8e8e7, 0xffe7e8e8, + 0xffe8e7e8, 0xffe8e7e8, 0xffe8e7e8, 0xffe7e7e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e8e7, 0xffe7e7e7, + 0xffe7e8e7, 0xffe7e7e8, 0xffe8e7e8, 0xffe8e8e7, 0xffe7e7e8, 0xffe8e8e8, 0xffe8e7e7, 0xffe8e7e8, + 0xffe7e7e7, 0xffe7e8e8, 0xffe8e7e8, 0xffe8e8e7, 0xffe8e7e8, 0xffe8e7e7, 0xffe8e7e8, 0xffe8e8e7, + 0xffe7e8e8, 0xffe8e7e7, 0xffe8e7e7, 0xffe8e7e7, 0xffe8e7e7, 0xffe7e8e8, 0xffe7e7e8, 0xffe8e7e8, + 0xffe7e8e8, 0xffe7e8e8, 0xffe7e8e7, 0xffe8e7e8, 0xffe8e8e7, 0xffe8e8e7, 0xffe7e8e8, 0xffe8e7e8, + 0xffe8e8e8, 0xffe8e8e7, 0xffe7e7e7, 0xffe8e8e8, 0xffe7e7e8, 0xffe8e8e8, 0xffe7e7e8, 0xffe7e7e7, + 0xffe7e7e8, 0xffe7e7e8, 0xffe8e7e8, 0xffe8e7e7, 0xffe8e7e7, 0xffe8e7e8, 0xffe8e8e7, 0xffe7e7e8, + 0xffe8e8e8, 0xffe7e8e7, 0xffe7e8e7, 0xffe8e8e8, 0xffe8e7e8, 0xffe7e7e7, 0xffe8e8e8, 0xffe8e7e8, + 0xffe8e8e7, 0xffe7e7e8, 0xffe8e7e8, 0xffe7e7e8, 0xffe7e8e7, 0xffe7e8e7, 0xffe7e7e8, 0xffe8e7e7, + 0xffe8e7e7, 0xffe8e7e7, 0xffe7e8e7, 0xffe8e8e8, 0xffe7e8e8, 0xffe8e8e8, 0xffe8e8e8, 0xffe8e7e7, + 0xffe7e8e7, 0xffe8e7e7, 0xffe7e8e8, 0xffe7e7e7, 0xffe8e7e8, 0xffe7e8e8, 0xffe8e7e8, 0xffe8e8e8, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e8e7, 0xffe8e8e7, 0xffe8e7e8, 0xffe7e8e8, 0xffe7e7e7, 0xffe7e7e8, + 0xffe7e7e8, 0xffe7e8e8, 0xffe7e8e8, 0xffe7e8e8, 0xffe7e7e7, 0xffe7e8e8, 0xffe8e7e8, 0xffe8e8e8, + 0xffe7e8e8, 0xffe8e7e8, 0xffe7e7e7, 0xffe8e7e8, 0xffe7e8e7, 0xffe8e7e7, 0xffe7e8e8, 0xffe7e8e8, + 0xffe7e8e8, 0xffe7e8e7, 0xffe7e8e8, 0xffe7e8e8, 0xffe8e8e8, 0xffe8e7e7, 0xffe8e7e7, 0xffe8e7e8, + 0xffe8e8e7, 0xffe8e8e7, 0xffe8e7e8, 0xffe7e7e8, 0xffe8e7e8, 0xffe8e7e7, 0xffe8e8e8, 0xffe8e7e8, + 0xffe7e7e8, 0xffe8e8e7, 0xffe7e8e7, 0xffe7e8e7, 0xffe8e8e8, 0xffe8e7e8, 0xffe7e8e7, 0xffe8e7e7, + 0xffe7e7e8, 0xffe7e8e8, 0xffe8e7e8, 0xffe8e7e7, 0xffe7e7e8, 0xffe8e8e7, 0xffe7e7e8, 0xffe8e7e7, + 0xffe7e7e8, 0xffe7e7e8, 0xffe8e8e7, 0xffe7e8e8, 0xffe8e7e7, 0xffe8e8e8, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e6, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e6e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e6e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e6e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e6, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e6, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e6, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe6e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797b79, 0xffb5b6b5, 0xffb5b6b5, + 0xffd6dbd6, 0xffe6e6e6, 0xffe6e7e7, 0xffe6e7e6, 0xffe7e6e7, 0xffe7e6e6, 0xffe7e6e6, 0xffe6e6e7, + 0xffe6e6e6, 0xffe6e6e6, 0xffe7e6e6, 0xffe7e6e6, 0xffe6e7e7, 0xffe7e6e6, 0xffe6e7e6, 0xffe6e6e7, + 0xffe7e6e6, 0xffe6e7e7, 0xffe7e6e6, 0xffe7e7e7, 0xffe6e7e7, 0xffe6e7e7, 0xffe6e6e7, 0xffe6e7e6, + 0xffe6e7e6, 0xffe7e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e6e6, 0xffe6e7e7, 0xffe6e7e7, 0xffe6e7e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe7e7e7, 0xffe7e7e7, 0xffe6e7e6, 0xffe6e6e6, 0xffe7e7e7, + 0xffe6e6e7, 0xffe7e7e7, 0xffe7e6e7, 0xffe6e6e7, 0xffe6e7e6, 0xffe6e6e6, 0xffe7e7e7, 0xffe7e6e6, + 0xffe7e6e7, 0xffe7e6e7, 0xffe6e7e6, 0xffe6e6e7, 0xffe7e7e6, 0xffe7e7e6, 0xffe6e6e7, 0xffe6e7e6, + 0xffe6e6e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe7e6e6, 0xffe6e6e7, 0xffe6e7e7, 0xffe6e7e7, 0xffe6e7e6, + 0xffe6e6e7, 0xffe6e6e7, 0xffe6e6e7, 0xffe6e6e7, 0xffe6e6e7, 0xffe7e6e6, 0xffe6e7e6, 0xffe6e7e6, + 0xffe7e7e7, 0xffe7e7e7, 0xffe7e7e7, 0xffe6e7e7, 0xffe6e6e7, 0xffe6e6e6, 0xffe6e7e7, 0xffe7e7e7, + 0xffe6e7e7, 0xffe7e6e6, 0xffe6e6e7, 0xffe6e7e7, 0xffe7e6e7, 0xffe7e7e7, 0xffe6e6e7, 0xffe6e6e6, + 0xffe7e7e6, 0xffe6e6e6, 0xffe6e7e7, 0xffe6e6e6, 0xffe6e7e6, 0xffe7e7e6, 0xffe7e7e6, 0xffe6e7e7, + 0xffe6e6e6, 0xffe6e7e6, 0xffe6e7e7, 0xffe7e7e6, 0xffe6e7e6, 0xffe6e6e7, 0xffe7e7e6, 0xffe6e6e6, + 0xffe7e7e6, 0xffe6e6e7, 0xffe6e7e7, 0xffe6e7e6, 0xffe7e6e7, 0xffe6e7e7, 0xffe6e6e7, 0xffe7e6e7, + 0xffe6e7e7, 0xffe6e7e6, 0xffe7e7e7, 0xffe7e7e7, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e6e7, 0xffe6e6e7, + 0xffe6e6e6, 0xffe7e6e7, 0xffe6e6e6, 0xffe7e6e7, 0xffe6e6e7, 0xffe7e7e7, 0xffe6e6e7, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe7e6e6, 0xffe7e7e6, 0xffe7e7e7, 0xffe6e6e6, 0xffe7e7e7, 0xffe6e7e7, + 0xffe6e7e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe7e7e6, 0xffe6e6e7, 0xffe7e6e6, 0xffe7e6e7, 0xffe6e6e7, + 0xffe6e7e7, 0xffe7e6e6, 0xffe6e7e6, 0xffe6e6e7, 0xffe7e7e7, 0xffe7e6e6, 0xffe6e7e6, 0xffe7e6e6, + 0xffe6e7e7, 0xffe6e7e7, 0xffe6e6e6, 0xffe7e7e6, 0xffe7e6e6, 0xffe7e6e6, 0xffe6e7e6, 0xffe7e6e6, + 0xffe7e7e6, 0xffe6e6e7, 0xffe6e6e6, 0xffe6e6e7, 0xffe6e7e7, 0xffe6e7e7, 0xffe6e6e7, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e7, 0xffe7e7e7, 0xffe6e6e7, 0xffe6e7e7, 0xffe6e6e7, 0xffe6e6e7, 0xffe6e7e7, + 0xffe7e6e6, 0xffe7e6e7, 0xffe6e6e6, 0xffe7e7e6, 0xffe7e6e6, 0xffe6e7e7, 0xffe6e7e7, 0xffe7e7e7, + 0xffe6e6e6, 0xffe7e7e7, 0xffe7e7e7, 0xffe6e7e6, 0xffe7e7e7, 0xffe6e6e7, 0xffe7e7e7, 0xffe6e6e7, + 0xffe6e7e6, 0xffe7e7e6, 0xffe7e6e7, 0xffe7e6e7, 0xffe7e6e6, 0xffe6e6e6, 0xffe7e7e6, 0xffe6e7e6, + 0xffe7e6e6, 0xffe7e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e6e7, 0xffe7e6e7, 0xffe6e7e7, + 0xffe7e7e6, 0xffe7e6e7, 0xffe7e7e7, 0xffe6e6e6, 0xffe6e6e7, 0xffe7e6e6, 0xffe6e6e7, 0xffe7e7e6, + 0xffe7e7e7, 0xffe6e7e6, 0xffe6e6e7, 0xffe7e6e6, 0xffe6e7e6, 0xffe6e7e7, 0xffe6e8e6, 0xffd6dbd6, + 0xffc5c2c5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797879, 0xffb5b2b5, 0xffb5b2b5, + 0xffd9dbd9, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, + 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6e6e6, 0xffe6ebe6, 0xffd9dbd9, + 0xffbdbebd, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797879, 0xffb5b2b5, 0xffb5b2b5, + 0xffd9dbd9, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, + 0xffefefef, 0xffefefef, 0xffefefef, 0xffefefef, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffd9dbd9, + 0xffbdbebd, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff797879, 0xffb5b2b5, 0xffb5b2b5, + 0xffcbcacb, 0xffd9dbd9, 0xffe6ebe6, 0xffe6ebe6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, + 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6e8e6, 0xffe6ebe6, 0xffe6ebe6, 0xffd9dbd9, 0xffcbcacb, + 0xffbdbebd, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0x00000400, 0xff797879, 0xffb5b2b5, + 0xffbdbabd, 0xffcbcacb, 0xffd9dbd9, 0xffd9dbd9, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, + 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd9dbd9, 0xffd9dbd9, 0xffcbcacb, 0xffbdbabd, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff848284, + 0xff9c9f9c, 0xff9c9f9c, 0xff9c9f9c, 0xff9c9f9c, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, + 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xffa2a5a2, 0xff9c9e9c, 0xff9c9e9c, 0xff9c9e9c, 0x00080408, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff848284, 0xffc5c2c5, 0xffc5c2c5, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffbdbebd, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff848284, 0xff848284, 0xffc5c2c5, 0xffe6ebe6, + 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, + 0xffeff3ef, 0xffeff3ef, 0xffeff3ef, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffe6ebe6, 0xffbdbebd, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e3c, 0xffa55d5a, 0xffa55d5a, 0xffc5716b, + 0xffd07770, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd6796b, + 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6756b, + 0xffd6756b, 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd6736b, 0xffd6736b, 0xffd6736b, 0xffce7163, + 0xffce7163, 0xffce7063, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, + 0xffce6c63, 0xffce6b63, 0xffce6963, 0xffce695a, 0xffce685a, 0xffce675a, 0xffce675a, 0xffc5655a, + 0xffc5655a, 0xffc5655a, 0xffc5645a, 0xffc5645d, 0xffc56258, 0xffc56258, 0xffc56258, 0xffc56052, + 0xffc56052, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55c52, 0xffc55c52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd584a, 0xffbd564a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd544a, 0xffbd544a, 0xffbd544a, 0xffbd5142, 0xffbd5142, 0xffba5042, 0xffba5042, 0xffba4d42, + 0xffb84d42, 0xffb84d42, 0xffb84d42, 0xffb54c3f, 0xffb54a3c, 0xffb54a3c, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5463a, 0xffb5463a, 0xffb5453a, 0xffb5433a, 0xffb5433a, 0xffb5433a, 0xffb54237, + 0xffb54237, 0xffb54131, 0xffb54131, 0xffad4131, 0xffad4131, 0xffad3f31, 0xffad3f31, 0xffad3f31, + 0xffad3e31, 0xffad3e31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b2f, + 0xffad3b2f, 0xffad3b2f, 0xffad3a2c, 0xffad392f, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392f, + 0xffad392c, 0xffad392f, 0xffad392f, 0xffad3a2c, 0xffad3a2c, 0xffad3b2f, 0xffad3b2f, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, 0xffad3e31, 0xffad3f31, 0xffad3f31, + 0xffad3f31, 0xffad3f31, 0xffad4131, 0xffb54237, 0xffb54237, 0xffb54237, 0xffb54237, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54a3c, + 0xffb54a3c, 0xffb54c3f, 0xffb54c3f, 0xffb54d42, 0xffb54d42, 0xffb84e42, 0xffba5042, 0xffbd5045, + 0xffbd5142, 0xffbd5142, 0xffbd5142, 0xffbd544a, 0xffbd544a, 0xffbd544a, 0xffbd554a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd564a, 0xffc0594d, 0xffc35950, 0xffc35950, 0xffc35950, 0xffc55a52, + 0xffc55d52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc56052, 0xffc56052, 0xffc56152, 0xffc56258, + 0xffc56258, 0xffc56455, 0xffc56455, 0xffcb655a, 0xffcb655a, 0xffcb655a, 0xffcb655a, 0xffce675d, + 0xffce6860, 0xffce6860, 0xffce6963, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, 0xffce6d63, + 0xffce6f63, 0xffce6f63, 0xffce7063, 0xffd07165, 0xffd07165, 0xffd37168, 0xffd37168, 0xffd6736b, + 0xffd6736b, 0xffd6746b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6776b, + 0xffd6786b, 0xffd6796b, 0xffd6786b, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd67970, 0xffd67973, + 0xffd67973, 0xffd67973, 0xffd67973, 0xffd67973, 0xffd67973, 0xffd07770, 0xffc5716b, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e3c, 0xffa55d5a, 0xffa55d5a, 0xffc5716b, + 0xffd07770, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd6796b, + 0xffd6796b, 0xffd6796b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6746b, 0xffd6746b, 0xffd6746b, 0xffd6736b, 0xffd6716b, 0xffd6716b, 0xffd6716b, 0xffce7063, + 0xffce7063, 0xffce7063, 0xffce7063, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, + 0xffce6c63, 0xffce6b63, 0xffce6b63, 0xffce695a, 0xffce685a, 0xffce685a, 0xffce675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5645a, 0xffc56258, 0xffc56258, 0xffc56152, 0xffc56152, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55d52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd594a, 0xffbd564a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd524a, 0xffbd514a, 0xffba5042, 0xffba5042, 0xffba5042, 0xffb54d42, 0xffb84d42, + 0xffb84d42, 0xffb84d42, 0xffb84d42, 0xffb54c3f, 0xffb54a3c, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5433a, 0xffb5433a, 0xffb5423a, 0xffb54237, + 0xffb54237, 0xffb54131, 0xffb54131, 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3a2c, + 0xffad3b2f, 0xffad3a2c, 0xffad3929, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffad3929, 0xffad3a2c, 0xffad3a2c, 0xffad3b2f, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, 0xffad3f31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffb5413a, 0xffb5413a, 0xffb54237, 0xffb54237, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5493a, + 0xffb54a3c, 0xffb54c3f, 0xffb54c3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb84e42, 0xffbd4e47, + 0xffbd5045, 0xffbd5045, 0xffbd5142, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd564a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc55a52, + 0xffc55d52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc5615a, + 0xffc56258, 0xffc56258, 0xffc56455, 0xffc8655a, 0xffc8655a, 0xffcb655a, 0xffcb655a, 0xffce675d, + 0xffce6860, 0xffce6860, 0xffce6963, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6c63, 0xffce6d63, + 0xffce6f63, 0xffce6f63, 0xffce6f63, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd37168, 0xffd6716b, + 0xffd6716b, 0xffd6736b, 0xffd6736b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6776b, + 0xffd6776b, 0xffd6786b, 0xffd6786b, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd67973, + 0xffd67973, 0xffd67973, 0xffd67973, 0xffd67973, 0xffd67973, 0xffd07770, 0xffc5716b, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e3c, 0xffa55d5a, 0xffa55d5a, 0xffc5716b, + 0xffd07770, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd6796b, + 0xffd6796b, 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd6736b, 0xffd6716b, 0xffd6716b, 0xffd6716b, 0xffce7063, + 0xffce7063, 0xffce7063, 0xffce7063, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, + 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce695a, 0xffce685a, 0xffce685a, 0xffce675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5645a, 0xffc56258, 0xffc56258, 0xffc56258, 0xffc56152, 0xffc55e52, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55d52, 0xffc55c52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd594a, 0xffbd564a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd514a, 0xffbd514a, 0xffba5042, 0xffba5042, 0xffba5042, 0xffb84e42, 0xffb84d42, + 0xffb84d42, 0xffb84d42, 0xffb84d42, 0xffb54a3c, 0xffb54a3c, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5433a, 0xffb5453a, 0xffb5433a, 0xffb5433a, 0xffb54237, + 0xffb54237, 0xffb54131, 0xffb54131, 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3a2c, + 0xffad3a2c, 0xffad3a2c, 0xffad3a2c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffad3a2c, 0xffad3a2c, 0xffad3a2c, 0xffad3a2c, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, 0xffad3e31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffb54237, 0xffb54237, 0xffb54237, 0xffb54237, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5493a, 0xffb54a3c, + 0xffb54a3c, 0xffb54c3f, 0xffb54c3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffbd4e47, + 0xffbd5045, 0xffbd5045, 0xffbd5142, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd564a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc55c52, + 0xffc55c52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc56052, 0xffc5615a, + 0xffc56258, 0xffc56258, 0xffc56258, 0xffc8655a, 0xffcb655a, 0xffc8655a, 0xffcb655a, 0xffce675d, + 0xffce6860, 0xffce6963, 0xffce6963, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, 0xffce6d63, + 0xffce6f63, 0xffce6f63, 0xffce7063, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd6716b, + 0xffd6736b, 0xffd6736b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6776b, 0xffd6786b, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd67970, 0xffd67973, + 0xffd67973, 0xffd67973, 0xffd67973, 0xffd67973, 0xffd67973, 0xffd07770, 0xffc5716b, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e3c, 0xffa55d5a, 0xffa55d5a, 0xffc5716b, + 0xffd07770, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd6796e, 0xffd6796b, + 0xffd6796b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6736b, 0xffd6716b, 0xffd6736b, 0xffd6716b, 0xffd6716b, 0xffce7063, + 0xffce7063, 0xffce7063, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, + 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce695a, 0xffce695a, 0xffce675a, 0xffce675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5625a, 0xffc56258, 0xffc56258, 0xffc56152, 0xffc56152, 0xffc55e52, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55d52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd584a, 0xffbd564a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd524a, 0xffbd514a, 0xffba5042, 0xffba5042, 0xffba5042, 0xffb54d42, 0xffb84d42, + 0xffb84d42, 0xffb84d42, 0xffb84d42, 0xffb54c3f, 0xffb5493a, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5463a, 0xffb5463a, 0xffb5453a, 0xffb5433a, 0xffb5433a, 0xffb5433a, 0xffb54237, + 0xffb54237, 0xffb54131, 0xffb54131, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3a2c, + 0xffad3a2c, 0xffad3a2c, 0xffad3929, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffad3929, 0xffad3a2c, 0xffad3a2c, 0xffad3b2f, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, 0xffad3e31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffb54237, 0xffb54237, 0xffb54237, 0xffb54237, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5493a, + 0xffb54a3c, 0xffb54c3f, 0xffb54c3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb84e42, 0xffbd4e47, + 0xffbd5045, 0xffbd5045, 0xffbd5142, 0xffbd514a, 0xffbd544a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd584a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc55c52, + 0xffc55d52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc56152, 0xffc5615a, + 0xffc5615a, 0xffc56258, 0xffc56258, 0xffc8655a, 0xffc8655a, 0xffcb655a, 0xffcb655a, 0xffce675d, + 0xffce6860, 0xffce6860, 0xffce6963, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, 0xffce6f63, + 0xffce6f63, 0xffce6f63, 0xffce7063, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd37168, 0xffd6716b, + 0xffd6736b, 0xffd6736b, 0xffd6736b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6776b, 0xffd6786b, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd67973, + 0xffd67973, 0xffd67973, 0xffd67973, 0xffd67973, 0xffd67973, 0xffd07770, 0xffc5716b, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e3c, 0xffa55d5a, 0xffa55d5a, 0xffce716b, + 0xffd37770, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd6796b, + 0xffd6786b, 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd67168, 0xffd67168, 0xffd67168, 0xffd67168, 0xffce7063, + 0xffce7063, 0xffce7063, 0xffce7063, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, + 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce695a, 0xffce685a, 0xffce675a, 0xffce675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5645a, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56155, 0xffc55e52, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55c52, 0xffc55c52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd584a, 0xffbd584a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd514a, 0xffbd514a, 0xffba5042, 0xffba5042, 0xffb84e42, 0xffb84e42, 0xffb54d42, + 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54a3f, 0xffb54a3f, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5433a, 0xffb5433a, 0xffb5423a, 0xffb24137, + 0xffaf4134, 0xffaf4134, 0xffaf4134, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b2f, 0xffad3b2f, 0xffad3b2f, 0xffad3a2c, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3a2c, 0xffad3a2c, 0xffad3a2c, 0xffad3a2c, + 0xffad3b2f, 0xffad3b2f, 0xffad3b2f, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffb54131, 0xffb54131, 0xffb54234, 0xffb54337, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5493a, + 0xffb54a3c, 0xffb54c3f, 0xffb54c3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffbd4e47, + 0xffbd5045, 0xffbd5045, 0xffbd5142, 0xffbd524a, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd564a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc55c52, + 0xffc55d52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc56152, 0xffc5615a, + 0xffc56258, 0xffc56258, 0xffc56258, 0xffc8655a, 0xffc8655a, 0xffcb655a, 0xffcb655a, 0xffce685d, + 0xffce685d, 0xffce695a, 0xffce695a, 0xffce6b63, 0xffce6c63, 0xffce6c63, 0xffce6c63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd6716b, + 0xffd6716b, 0xffd6736b, 0xffd6736b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6776b, 0xffd6786b, 0xffd6796e, 0xffd6796e, 0xffd67970, 0xffd6796e, 0xffd67970, + 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd37770, 0xffce716b, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e3c, 0xffa55d5a, 0xffa55d5a, 0xffce716b, + 0xffd37770, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd6796b, + 0xffd6796b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd67168, 0xffd67168, 0xffd67168, 0xffd67165, 0xffce7063, + 0xffce7063, 0xffce7063, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, + 0xffce6c63, 0xffce6b63, 0xffce6963, 0xffce695a, 0xffce695a, 0xffce675a, 0xffce675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5625a, 0xffc56158, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc55e52, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55c52, 0xffc55c52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd584a, 0xffbd564a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd544a, 0xffbd524a, 0xffbd514a, 0xffba5042, 0xffba5042, 0xffb84e42, 0xffb54d42, 0xffb54d42, + 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54a3f, 0xffb5493a, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5463a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5433a, 0xffb5433a, 0xffb5433a, 0xffb24137, + 0xffb24137, 0xffaf4134, 0xffaf4134, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3d31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b2f, 0xffad3b2f, 0xffad3b2f, 0xffad3a2c, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3a2c, 0xffad3a2c, 0xffad3b2f, + 0xffad3b2f, 0xffad3b2f, 0xffad3b2f, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, + 0xffad3e31, 0xffad3f31, 0xffad3f31, 0xffb54131, 0xffb54234, 0xffb54234, 0xffb54337, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5493a, + 0xffb54a3c, 0xffb54c3f, 0xffb54c3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffbd4e47, + 0xffbd5045, 0xffbd5045, 0xffbd5045, 0xffbd514a, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd554a, 0xffbd564a, 0xffbd564a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc55c52, + 0xffc55c52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc5615a, + 0xffc5615a, 0xffc56258, 0xffc56258, 0xffc8655a, 0xffc8655a, 0xffcb655a, 0xffcb655a, 0xffce685d, + 0xffce685d, 0xffce695a, 0xffce685d, 0xffce6b63, 0xffce6c63, 0xffce6c63, 0xffce6d63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd37168, 0xffd6716b, + 0xffd6736b, 0xffd6736b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6786b, 0xffd6786b, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd67970, 0xffd6796e, + 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd37770, 0xffce716b, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e3c, 0xffa55d5a, 0xffa55d5a, 0xffce716b, + 0xffd37770, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6796b, + 0xffd6796b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6756b, 0xffd6746b, 0xffd67168, 0xffd67168, 0xffd67168, 0xffd67168, 0xffce7163, + 0xffce7063, 0xffce7063, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, + 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce695a, 0xffce695a, 0xffce675a, 0xffce675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5645a, 0xffc56158, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc55e52, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55c52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd584a, 0xffbd564a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd524a, 0xffbd514a, 0xffba5042, 0xffba5042, 0xffba5042, 0xffb84e42, 0xffb54d42, + 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54a3f, 0xffb54a3f, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5433a, 0xffb5433a, 0xffb5433a, 0xffb24137, + 0xffaf4134, 0xffaf4134, 0xffaf4134, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b2f, 0xffad3b2f, 0xffad3b2f, 0xffad3a2c, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3a2c, 0xffad3a2c, 0xffad3b2f, + 0xffad3b2f, 0xffad3b2f, 0xffad3b2f, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffb54131, 0xffb54234, 0xffb54234, 0xffb54337, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5493a, + 0xffb54a3c, 0xffb54a3c, 0xffb54c3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffbd5045, + 0xffbd5045, 0xffbd5045, 0xffbd5142, 0xffbd514a, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd564a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc55a52, + 0xffc55d52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc56152, 0xffc5615a, + 0xffc56258, 0xffc56258, 0xffc56455, 0xffc8655a, 0xffc8655a, 0xffcb655a, 0xffcb655a, 0xffce685d, + 0xffce685d, 0xffce695a, 0xffce695a, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd37168, 0xffd6716b, + 0xffd6716b, 0xffd6736b, 0xffd6736b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6776b, + 0xffd6756b, 0xffd6786b, 0xffd6786b, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd67970, 0xffd6796e, + 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd37770, 0xffce716b, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e3c, 0xffa55d5a, 0xffa55d5a, 0xffce716b, + 0xffd37770, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67970, 0xffd6796b, + 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6786b, 0xffd6756b, 0xffd6776b, 0xffd6756b, 0xffd6756b, + 0xffd6746b, 0xffd6746b, 0xffd6736b, 0xffd67168, 0xffd67168, 0xffd67168, 0xffd67168, 0xffce7063, + 0xffce7063, 0xffce7063, 0xffce7063, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, + 0xffce6b63, 0xffce6b63, 0xffce6963, 0xffce695a, 0xffce685a, 0xffce675a, 0xffce675a, 0xffc5655a, + 0xffc5655a, 0xffc5655a, 0xffc5645a, 0xffc56158, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55c52, 0xffc55c52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd584a, 0xffbd584a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd524a, 0xffbd514a, 0xffba5042, 0xffba5042, 0xffba5042, 0xffb54d42, 0xffb54d42, + 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54a3f, 0xffb54a3f, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5463a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5433a, 0xffb5433a, 0xffb5423a, 0xffb24137, + 0xffaf4134, 0xffaf4134, 0xffaf4134, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b2f, 0xffad3b2f, 0xffad3a2c, 0xffad3a2c, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3929, 0xffad3a2c, 0xffad3a2c, 0xffad3b2f, 0xffad3b2f, + 0xffad3b2f, 0xffad3b2f, 0xffad3b2f, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffb54131, 0xffb54131, 0xffb54234, 0xffb54234, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5493a, + 0xffb54a3c, 0xffb54a3c, 0xffb54c3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffbd4e47, + 0xffbd5045, 0xffbd5045, 0xffbd5142, 0xffbd524a, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd584a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc55a52, + 0xffc55c52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc56152, 0xffc56258, + 0xffc56258, 0xffc56258, 0xffc56455, 0xffc8655a, 0xffc8655a, 0xffcb655a, 0xffcb655a, 0xffce685d, + 0xffce685d, 0xffce695a, 0xffce695a, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd07165, 0xffd6716b, + 0xffd6716b, 0xffd6736b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6786b, 0xffd6776b, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd67970, 0xffd67970, + 0xffd67970, 0xffd67970, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd37770, 0xffce716b, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e37, 0xffa55d52, 0xffa55d52, 0xffc57163, + 0xffd0776e, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd6786b, + 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd37168, 0xffd37168, 0xffd37168, 0xffd07165, 0xffce7063, + 0xffce7063, 0xffce6f63, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c63, 0xffce6960, + 0xffce6960, 0xffce6960, 0xffce695d, 0xffcb685a, 0xffcb685a, 0xffc8675a, 0xffc8675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5625a, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55c52, 0xffc55c52, 0xffc55a52, 0xffc55952, 0xffbd594a, + 0xffbd584a, 0xffbd584a, 0xffbd564a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd514a, 0xffbd514a, 0xffb55042, 0xffb55042, 0xffb55042, 0xffb54e42, 0xffb54d42, + 0xffb54c42, 0xffb54c42, 0xffb54a42, 0xffb5493f, 0xffb5493c, 0xffb5493c, 0xffb5493c, 0xffb5483a, + 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb24137, + 0xffaf4134, 0xffaf4134, 0xffaf4134, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3d31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b31, 0xffad3a31, 0xffad3a31, 0xffad3931, 0xffad392c, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffaa3929, 0xffaa3929, 0xffa73929, 0xffaa3929, 0xffa73929, + 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad3a31, + 0xffad3a31, 0xffad3b31, 0xffad3b31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad4131, 0xffaf4234, 0xffaf4234, 0xffb24337, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54942, + 0xffb54a3c, 0xffb54a3c, 0xffb54a3c, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffba5045, + 0xffba5045, 0xffba5045, 0xffbd5142, 0xffbd514a, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd554a, 0xffbd564a, 0xffbd584a, 0xffbd594d, 0xffbd594d, 0xffbd594d, 0xffbd5950, 0xffc55a52, + 0xffc55a52, 0xffc55c52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc56052, 0xffc5615a, + 0xffc56258, 0xffc56258, 0xffc56258, 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffcb685a, + 0xffcb685a, 0xffcb685a, 0xffce695a, 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6f65, 0xffce6f65, 0xffce7068, 0xffce7068, 0xffd6716b, + 0xffd6716b, 0xffd6736b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6786b, 0xffd6786b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796e, + 0xffd6796e, 0xffd6796e, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd0776e, 0xffc57163, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e37, 0xffa55d52, 0xffa55d52, 0xffc57163, + 0xffd0776e, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd6786b, + 0xffd6786b, 0xffd6786b, 0xffd6786b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6736b, 0xffd37168, 0xffd37168, 0xffd37168, 0xffd37168, 0xffce7063, + 0xffce7063, 0xffce6f63, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6c63, 0xffce6b63, 0xffce6960, + 0xffce6960, 0xffce6960, 0xffce695d, 0xffcb685a, 0xffcb685a, 0xffcb685a, 0xffc8675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5645a, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55c52, 0xffc55a52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd584a, 0xffbd584a, 0xffbd584a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd524a, 0xffbd514a, 0xffb55042, 0xffb55042, 0xffb54e42, 0xffb54d42, 0xffb54d42, + 0xffb54c42, 0xffb54c42, 0xffb54c42, 0xffb5493f, 0xffb5493c, 0xffb5493c, 0xffb5493c, 0xffb5483a, + 0xffb5463a, 0xffb5463a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb24137, + 0xffb24137, 0xffaf4134, 0xffaf4134, 0xffad3f31, 0xffad3e31, 0xffad3f31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b31, 0xffad3a31, 0xffad3a31, 0xffad3931, 0xffad392c, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffa73929, + 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffad392c, 0xffad392c, 0xffad392f, 0xffad392c, 0xffad3a31, + 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffaf4234, 0xffaf4234, 0xffaf4234, 0xffb24337, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54942, + 0xffb54a3c, 0xffb54a3c, 0xffb54a3c, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb84e47, + 0xffba5045, 0xffba5045, 0xffbd5142, 0xffbd514a, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd564a, 0xffbd594d, 0xffbd594d, 0xffbd594d, 0xffbd5950, 0xffc55a52, + 0xffc55a52, 0xffc55c52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc56152, 0xffc5615a, + 0xffc56258, 0xffc56258, 0xffc56455, 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffcb685a, + 0xffcb685a, 0xffcb685a, 0xffce695a, 0xffce6963, 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6f65, 0xffce6f65, 0xffce7068, 0xffce7068, 0xffd6716b, + 0xffd6736b, 0xffd6736b, 0xffd6736b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6776b, + 0xffd6776b, 0xffd6786b, 0xffd6786b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796e, + 0xffd6796e, 0xffd67970, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd0776e, 0xffc57163, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e37, 0xffa55d52, 0xffa55d52, 0xffc57163, + 0xffd0776e, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6786b, + 0xffd6786b, 0xffd6786b, 0xffd6786b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd37168, 0xffd37168, 0xffd37168, 0xffd37168, 0xffce7063, + 0xffce7063, 0xffce6f63, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6c63, 0xffce6c63, 0xffce6960, + 0xffce6960, 0xffce6960, 0xffce695d, 0xffcb685a, 0xffcb685a, 0xffcb685a, 0xffc8675a, 0xffc5655a, + 0xffc5655a, 0xffc5645a, 0xffc5625a, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55c52, 0xffc55c52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd584a, 0xffbd584a, 0xffbd564a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd544a, 0xffbd524a, 0xffbd514a, 0xffb55042, 0xffb55042, 0xffb54e42, 0xffb54e42, 0xffb54d42, + 0xffb54d42, 0xffb54c42, 0xffb54a42, 0xffb5493f, 0xffb5493c, 0xffb5493c, 0xffb5493c, 0xffb5483a, + 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb24137, + 0xffaf4134, 0xffaf4134, 0xffaf4134, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b31, 0xffad3b31, 0xffad3a31, 0xffad3a31, 0xffad392c, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffaa3929, + 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffad392c, 0xffad392c, 0xffad392f, 0xffad392c, 0xffad3a31, + 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3f31, + 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad4131, 0xffaf4234, 0xffaf4234, 0xffb24337, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54942, + 0xffb54942, 0xffb54a3c, 0xffb54a3c, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb84e47, + 0xffba5045, 0xffba5045, 0xffbd5142, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd584a, 0xffbd594d, 0xffbd594d, 0xffbd594d, 0xffbd5950, 0xffc55a52, + 0xffc55c52, 0xffc55c52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc56052, 0xffc5615a, + 0xffc56258, 0xffc56258, 0xffc56455, 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc8675a, + 0xffcb685a, 0xffcb685a, 0xffce695a, 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6f65, 0xffce7068, 0xffce7068, 0xffce7068, 0xffd6716b, + 0xffd6716b, 0xffd6736b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6776b, + 0xffd6756b, 0xffd6786b, 0xffd6786b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796e, + 0xffd67970, 0xffd6796e, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd0776e, 0xffc57163, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e37, 0xffa55d52, 0xffa55d52, 0xffc57163, + 0xffd0776e, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd6786b, + 0xffd6786b, 0xffd6786b, 0xffd6786b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd37168, 0xffd37168, 0xffd37168, 0xffd37168, 0xffce7063, + 0xffce7063, 0xffce6f63, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6c63, 0xffce6c63, 0xffce6960, + 0xffce6960, 0xffce6960, 0xffce695d, 0xffcb685a, 0xffcb685a, 0xffc8675a, 0xffc8675a, 0xffc5655a, + 0xffc5655a, 0xffc5655a, 0xffc5645a, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55a52, 0xffc55a52, 0xffc55952, 0xffbd594a, + 0xffbd584a, 0xffbd584a, 0xffbd584a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd524a, 0xffbd514a, 0xffb55042, 0xffb55042, 0xffb54e42, 0xffb54e42, 0xffb54d42, + 0xffb54c42, 0xffb54c42, 0xffb54c42, 0xffb5493f, 0xffb5493f, 0xffb5493c, 0xffb5493c, 0xffb5483a, + 0xffb5483a, 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb24137, + 0xffb24137, 0xffb24137, 0xffaf4134, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b31, 0xffad3b31, 0xffad3a31, 0xffad3a31, 0xffad392f, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffaa3929, + 0xffaa3929, 0xffaa3929, 0xffaa3929, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392f, 0xffad3a31, + 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, + 0xffad3f31, 0xffad3f31, 0xffad4131, 0xffaf4234, 0xffaf4234, 0xffaf4234, 0xffaf4234, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54942, + 0xffb54942, 0xffb54a3c, 0xffb54a3c, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffba5045, + 0xffba5045, 0xffba5045, 0xffbd5142, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd584a, 0xffbd594d, 0xffbd594d, 0xffbd594d, 0xffbd5950, 0xffc55a52, + 0xffc55c52, 0xffc55c52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc56152, 0xffc5615a, + 0xffc56258, 0xffc56258, 0xffc56258, 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffcb685a, + 0xffcb685a, 0xffcb685a, 0xffce695a, 0xffce6963, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6f65, 0xffce7068, 0xffce7068, 0xffce7068, 0xffd6716b, + 0xffd6716b, 0xffd6736b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6776b, 0xffd6776b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796e, + 0xffd6796e, 0xffd67970, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd0776e, 0xffc57163, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e37, 0xffa55d52, 0xffa55d52, 0xffc57163, + 0xffd0776e, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd6786b, + 0xffd6786b, 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6736b, 0xffd6736b, 0xffd6736b, 0xffd6716b, 0xffd6716b, 0xffce7063, + 0xffce7063, 0xffce6f63, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c5d, + 0xffce6b60, 0xffce6963, 0xffce6963, 0xffcb685a, 0xffcb685a, 0xffc8675a, 0xffc8675a, 0xffc5655a, + 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc56158, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55d52, 0xffc55a52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd584d, 0xffbd584d, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd544a, 0xffbd524a, 0xffbd514a, 0xffb55042, 0xffb55042, 0xffb55042, 0xffb54e42, 0xffb54d42, + 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54a3f, 0xffb54a3f, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffaf4234, + 0xffaf4234, 0xffaf4234, 0xffad4131, 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3a31, 0xffad3a2c, + 0xffad3a2c, 0xffad3a2c, 0xffad3a2c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffad3931, 0xffad3931, 0xffad3a31, 0xffad3b31, 0xffad3a31, + 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, 0xffad3e37, + 0xffad3f34, 0xffad3f34, 0xffad3f34, 0xffad413a, 0xffad413a, 0xffaf423a, 0xffb2433a, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54a3f, + 0xffb54942, 0xffb54a3f, 0xffb54a3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffba5047, + 0xffba5047, 0xffbd5142, 0xffbd5142, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd564a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc55a52, + 0xffc55c52, 0xffc55c52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc5615a, + 0xffc5625a, 0xffc5625a, 0xffc5625a, 0xffc8655a, 0xffc8655a, 0xffc8655a, 0xffc8655a, 0xffce685d, + 0xffce685d, 0xffce685d, 0xffce685d, 0xffce6963, 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce7068, 0xffce7068, 0xffce7068, 0xffce7163, 0xffd6716b, + 0xffd6736b, 0xffd6736b, 0xffd6736b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6776b, 0xffd6786b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796e, + 0xffd67970, 0xffd6796e, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd0776e, 0xffc57163, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e37, 0xffa55d52, 0xffa55d52, 0xffc57163, + 0xffd0776e, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6796b, + 0xffd6786b, 0xffd6786b, 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd6736b, 0xffd6716b, 0xffd6716b, 0xffd6716b, 0xffce7163, + 0xffce7063, 0xffce6f63, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6b60, + 0xffce6b60, 0xffce6b60, 0xffce6963, 0xffcb685a, 0xffcb685a, 0xffcb685a, 0xffc8675a, 0xffc5655a, + 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55c52, 0xffc55a52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd584d, 0xffbd584d, 0xffbd584d, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd544a, 0xffbd524a, 0xffbd514a, 0xffb55042, 0xffb55042, 0xffb55042, 0xffb54e42, 0xffb54d42, + 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54a3f, 0xffb54a3f, 0xffb54a3f, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5463a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb24337, + 0xffaf4234, 0xffaf4234, 0xffad4131, 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad3e31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3a2c, + 0xffad3a2c, 0xffad3a2c, 0xffad3a2c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, 0xffad392c, + 0xffad392c, 0xffad392c, 0xffad392c, 0xffad3a31, 0xffad3a31, 0xffad3a31, 0xffad3b31, 0xffad3b31, + 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3d31, 0xffad3e31, 0xffad3e31, 0xffad3e31, 0xffad3f34, + 0xffad3f34, 0xffad3f34, 0xffad4131, 0xffaf423a, 0xffaf423a, 0xffaf423a, 0xffb2433a, 0xffb5453a, + 0xffb5453a, 0xffb5453a, 0xffb5463a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54942, + 0xffb54a3f, 0xffb54a3f, 0xffb54a3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffba5047, + 0xffba5047, 0xffba5047, 0xffbd5142, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd544a, 0xffbd554a, + 0xffbd564a, 0xffbd564a, 0xffbd584a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc55a52, + 0xffc55c52, 0xffc55c52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc5615a, + 0xffc5625a, 0xffc5625a, 0xffc5645a, 0xffc8655a, 0xffc8655a, 0xffc8655a, 0xffc8655a, 0xffce685d, + 0xffce685d, 0xffce685d, 0xffce695a, 0xffce6963, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce7068, 0xffce7068, 0xffce7068, 0xffce7163, 0xffd6716b, + 0xffd6736b, 0xffd6736b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6776b, 0xffd6786b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796e, + 0xffd6796e, 0xffd67970, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd0776e, 0xffc57163, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e37, 0xffa55d52, 0xffa55d52, 0xffc57163, + 0xffd0776e, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6796e, 0xffd6786b, + 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6786b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6736b, 0xffd6746b, 0xffd6716b, 0xffd6716b, 0xffd6716b, 0xffce7163, + 0xffce7063, 0xffce6f63, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6b60, + 0xffce6b60, 0xffce6b60, 0xffce6963, 0xffce695a, 0xffcb685a, 0xffcb685a, 0xffc8675a, 0xffc5655a, + 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc56158, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55d52, 0xffc55d52, 0xffc55c52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd584d, 0xffbd584d, 0xffbd584d, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd524a, 0xffbd524a, 0xffbd524a, 0xffb55042, 0xffb55042, 0xffb54e42, 0xffb54e42, 0xffb54d42, + 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54a3f, 0xffb54a3f, 0xffb5493a, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb24337, + 0xffaf4234, 0xffaf4234, 0xffad4131, 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3b2f, + 0xffad3b2f, 0xffad3a2c, 0xffad3a2c, 0xffad392c, 0xffad392f, 0xffad392c, 0xffad392c, 0xffad392f, + 0xffad392c, 0xffad392f, 0xffad392f, 0xffad3a31, 0xffad3a31, 0xffad3b31, 0xffad3b31, 0xffad3b31, + 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3d31, 0xffad3e31, 0xffad3e31, 0xffad3e31, 0xffad3f34, + 0xffad3f34, 0xffad3f34, 0xffad4131, 0xffad413a, 0xffaf423a, 0xffaf423a, 0xffb2433a, 0xffb5453a, + 0xffb5453a, 0xffb5463a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54942, + 0xffb54942, 0xffb54c3c, 0xffb54a3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffba5047, + 0xffba5047, 0xffba5047, 0xffba5047, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd544a, 0xffbd564a, + 0xffbd564a, 0xffbd564a, 0xffbd584a, 0xffc0594d, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc55a52, + 0xffc55a52, 0xffc55d52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc56152, 0xffc5625a, + 0xffc5625a, 0xffc5645a, 0xffc5645a, 0xffc8655a, 0xffc8655a, 0xffc8655a, 0xffcb655a, 0xffce685d, + 0xffce685d, 0xffce695a, 0xffce695a, 0xffce6b63, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce7068, 0xffce7068, 0xffce7068, 0xffce7068, 0xffd6716b, + 0xffd6736b, 0xffd6736b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6776b, 0xffd6776b, 0xffd6786b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796e, + 0xffd6796e, 0xffd6796e, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd0776e, 0xffc57163, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff6e3e37, 0xffa55d52, 0xffa55d52, 0xffc57163, + 0xffd0776e, 0xffd67973, 0xffd67973, 0xffd67970, 0xffd67970, 0xffd6796e, 0xffd6796e, 0xffd6796b, + 0xffd6786b, 0xffd6786b, 0xffd6786b, 0xffd6776b, 0xffd6776b, 0xffd6756b, 0xffd6756b, 0xffd6756b, + 0xffd6756b, 0xffd6746b, 0xffd6746b, 0xffd6736b, 0xffd6736b, 0xffd6716b, 0xffd6716b, 0xffce7163, + 0xffce7063, 0xffce7063, 0xffce6f63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce6c5d, + 0xffce6b60, 0xffce6b60, 0xffce6963, 0xffcb685a, 0xffcb685a, 0xffcb685a, 0xffc8675a, 0xffc5655a, + 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc56158, 0xffc56158, 0xffc56158, 0xffc56155, 0xffc56052, + 0xffc55e52, 0xffc55e52, 0xffc55e52, 0xffc55c52, 0xffc55c52, 0xffc55a52, 0xffc55a52, 0xffbd594a, + 0xffbd594a, 0xffbd584d, 0xffbd584d, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd554a, 0xffbd544a, + 0xffbd544a, 0xffbd524a, 0xffbd514a, 0xffb55142, 0xffb55042, 0xffb55042, 0xffb54e42, 0xffb54d42, + 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54a3f, 0xffb54a3f, 0xffb54a3f, 0xffb5493a, 0xffb5483a, + 0xffb5483a, 0xffb5483a, 0xffb5463a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb5453a, 0xffb24337, + 0xffaf4234, 0xffaf4234, 0xffaf4234, 0xffad4131, 0xffad3f31, 0xffad3f31, 0xffad3f31, 0xffad3d31, + 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3b31, 0xffad3a2c, + 0xffad3b2f, 0xffad3b2f, 0xffad3b2f, 0xffad392f, 0xffad392f, 0xffad392f, 0xffad392f, 0xffad392f, + 0xffad392f, 0xffad392f, 0xffad392f, 0xffad3a31, 0xffad3a31, 0xffad3b31, 0xffad3b31, 0xffad3b31, + 0xffad3b31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3d31, 0xffad3e31, 0xffad3f31, 0xffad3f34, + 0xffad3f34, 0xffad3f34, 0xffad4131, 0xffaf423a, 0xffb2433a, 0xffb2433a, 0xffb2433a, 0xffb5453a, + 0xffb5453a, 0xffb5463a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb5483a, 0xffb54942, + 0xffb54942, 0xffb54a3f, 0xffb54a3f, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffb54d42, 0xffba5047, + 0xffba5047, 0xffbd5142, 0xffbd5142, 0xffbd524a, 0xffbd544a, 0xffbd544a, 0xffbd554a, 0xffbd564a, + 0xffbd564a, 0xffbd564a, 0xffbd584a, 0xffc0594d, 0xffc0594d, 0xffc35950, 0xffc35950, 0xffc55a52, + 0xffc55c52, 0xffc55c52, 0xffc55d52, 0xffc55e52, 0xffc55e52, 0xffc56052, 0xffc56152, 0xffc5625a, + 0xffc5625a, 0xffc5625a, 0xffc5645a, 0xffc8655a, 0xffc8655a, 0xffc8655a, 0xffc8655a, 0xffce685d, + 0xffce685d, 0xffce685d, 0xffce695a, 0xffce6b63, 0xffce6b63, 0xffce6c63, 0xffce6c63, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffce7068, 0xffce7068, 0xffce7068, 0xffce7068, 0xffd6716b, + 0xffd6716b, 0xffd6746b, 0xffd6746b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6756b, 0xffd6776b, + 0xffd6776b, 0xffd6776b, 0xffd6786b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796b, 0xffd6796e, + 0xffd67970, 0xffd6796e, 0xffd67970, 0xffd67973, 0xffd67973, 0xffd0776e, 0xffc57163, 0xffb5655a, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00100400, 0xff473531, 0xff7e6563, 0xff7e6563, 0xffad655a, + 0xffad7b73, 0xffad7b73, 0xffad7b73, 0xffb57573, 0xffb57573, 0xffb57573, 0xffb57573, 0xffb5756b, + 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5716b, + 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffad716b, + 0xffad716b, 0xffad716b, 0xffad716b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, + 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffb5655a, 0xffb5655a, 0xffb5655a, 0xffb5655a, 0xffb5615a, + 0xffb5615a, 0xffb5615a, 0xffb5615a, 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffb55d52, + 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffad5952, 0xffad5952, 0xffad5952, 0xffad5952, 0xffad594a, + 0xffad594a, 0xffad594a, 0xffad594a, 0xffad554a, 0xffad554a, 0xffad554a, 0xffad554a, 0xffad514a, + 0xffad514a, 0xffad514a, 0xffad514a, 0xffa55142, 0xffa55142, 0xffa55142, 0xffa55142, 0xffa54d42, + 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54942, + 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xff9c453a, + 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c413a, + 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, + 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c3d3a, + 0xff9c3d3a, 0xff9c3d3a, 0xff9c3d3a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, + 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c453a, + 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xffa54942, + 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54d42, + 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffad514a, + 0xffad514a, 0xffad514a, 0xffad514a, 0xffad554a, 0xffad554a, 0xffad554a, 0xffad554a, 0xffad554a, + 0xffad554a, 0xffad554a, 0xffad554a, 0xffad5952, 0xffad5952, 0xffad5952, 0xffad5952, 0xffb55952, + 0xffb55952, 0xffb55952, 0xffb55952, 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffb55d5a, + 0xffb55d5a, 0xffb55d5a, 0xffb55d5a, 0xffb5615a, 0xffb5615a, 0xffb5615a, 0xffb5615a, 0xffbd655a, + 0xffbd655a, 0xffbd655a, 0xffbd655a, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, + 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad716b, 0xffad716b, 0xffad716b, 0xffad716b, 0xffb5716b, + 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5756b, + 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb57573, + 0xffb57573, 0xffb57573, 0xffb57573, 0xffad7b73, 0xffad7b73, 0xffad7b73, 0xffad655a, 0xff7e6463, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00100400, 0xff473531, 0xff7e6563, 0xff7e6563, 0xffad655a, + 0xffad7b73, 0xffad7b73, 0xffad7b73, 0xffb57573, 0xffb57573, 0xffb57573, 0xffb57573, 0xffb5756b, + 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5716b, + 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffad716b, + 0xffad716b, 0xffad716b, 0xffad716b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, + 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffb5655a, 0xffb5655a, 0xffb5655a, 0xffb5655a, 0xffb5615a, + 0xffb5615a, 0xffb5615a, 0xffb5615a, 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffb55d52, + 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffad5952, 0xffad5952, 0xffad5952, 0xffad5952, 0xffad594a, + 0xffad594a, 0xffad594a, 0xffad594a, 0xffad554a, 0xffad554a, 0xffad554a, 0xffad554a, 0xffad514a, + 0xffad514a, 0xffad514a, 0xffad514a, 0xffa55142, 0xffa55142, 0xffa55142, 0xffa55142, 0xffa54d42, + 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54942, + 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xff9c453a, + 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c413a, + 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, + 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c3d3a, + 0xff9c3d3a, 0xff9c3d3a, 0xff9c3d3a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, + 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c413a, 0xff9c453a, + 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xff9c453a, 0xffa54942, + 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54942, 0xffa54d42, + 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffa54d42, 0xffad514a, + 0xffad514a, 0xffad514a, 0xffad514a, 0xffad554a, 0xffad554a, 0xffad554a, 0xffad554a, 0xffad554a, + 0xffad554a, 0xffad554a, 0xffad554a, 0xffad5952, 0xffad5952, 0xffad5952, 0xffad5952, 0xffb55952, + 0xffb55952, 0xffb55952, 0xffb55952, 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffb55d52, 0xffb55d5a, + 0xffb55d5a, 0xffb55d5a, 0xffb55d5a, 0xffb5615a, 0xffb5615a, 0xffb5615a, 0xffb5615a, 0xffbd655a, + 0xffbd655a, 0xffbd655a, 0xffbd655a, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, + 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad716b, 0xffad716b, 0xffad716b, 0xffad716b, 0xffb5716b, + 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5756b, + 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb57573, + 0xffb57573, 0xffb57573, 0xffb57573, 0xffad7b73, 0xffad7b73, 0xffad7b73, 0xffad655a, 0xff7e6463, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00100400, 0xff7e6563, 0xff7e6563, 0xff7e6563, 0xffad655a, + 0xffad655a, 0xffad7b73, 0xffad7b73, 0xffb57573, 0xffb57573, 0xffb57573, 0xffb57573, 0xffb5756b, + 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5716b, + 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffad716b, + 0xffad716b, 0xffad716b, 0xffad716b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, + 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad7c76, 0xffad7c76, 0xffad7c76, 0xffad7c76, 0xffad7976, + 0xffad7976, 0xffad7976, 0xffad7976, 0xffad7770, 0xffad7770, 0xffad7770, 0xffad7770, 0xffad7870, + 0xffad7870, 0xffad7870, 0xffad7870, 0xffa77570, 0xffa77570, 0xffa77570, 0xffa77570, 0xffa7756b, + 0xffa7756b, 0xffa7756b, 0xffa7756b, 0xffa7736b, 0xffa7736b, 0xffa7736b, 0xffa7736b, 0xffa7706b, + 0xffa7706b, 0xffa7706b, 0xffa7706b, 0xffa27065, 0xffa27065, 0xffa27065, 0xffa27065, 0xffa26d65, + 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26b68, + 0xffa26b68, 0xffa26b68, 0xffa26b68, 0xffa26c68, 0xffa26c68, 0xffa26c68, 0xffa26c68, 0xff9c6963, + 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6763, + 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, + 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6463, + 0xff9c6463, 0xff9c6463, 0xff9c6463, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, + 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6763, 0xff9c6963, + 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xffa26c68, + 0xffa26c68, 0xffa26c68, 0xffa26c68, 0xffa26b68, 0xffa26b68, 0xffa26b68, 0xffa26b68, 0xffa26d65, + 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa26d65, 0xffa7706b, + 0xffa7706b, 0xffa7706b, 0xffa7706b, 0xffa7736b, 0xffa7736b, 0xffa7736b, 0xffa7736b, 0xffa7736b, + 0xffa7736b, 0xffa7736b, 0xffa7736b, 0xffa77570, 0xffa77570, 0xffa77570, 0xffa77570, 0xffad7570, + 0xffad7570, 0xffad7570, 0xffad7570, 0xffad7870, 0xffad7870, 0xffad7870, 0xffad7870, 0xffad7776, + 0xffad7776, 0xffad7776, 0xffad7776, 0xffad7976, 0xffad7976, 0xffad7976, 0xffad7976, 0xffaf7c76, + 0xffaf7c76, 0xffaf7c76, 0xffaf7c76, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, + 0xffad6d6b, 0xffad6d6b, 0xffad6d6b, 0xffad716b, 0xffad716b, 0xffad716b, 0xffad716b, 0xffb5716b, + 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5716b, 0xffb5756b, + 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb5756b, 0xffb57573, + 0xffb57573, 0xffb57573, 0xffb57573, 0xffad7b73, 0xffad7b73, 0xffad655a, 0xffad655a, 0xff7e6463, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00100400, 0xff7e6563, 0xffb59694, 0xffb59694, 0xffada6a5, + 0xffada6a5, 0xffada6a5, 0xffada6a5, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, + 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caead, + 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, + 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, + 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, + 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caeb5, + 0xff9caeb5, 0xff9caeb5, 0xff9caeb5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, + 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, + 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, + 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, + 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, + 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, + 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, + 0xff9cb2b5, 0xff9cb2b5, 0xff9cb2b5, 0xff9caeb5, 0xff9caeb5, 0xff9caeb5, 0xff9caeb5, 0xff9caead, + 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, + 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, + 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, + 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caaad, + 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff9caaad, 0xff94aaad, + 0xff94aaad, 0xff94aaad, 0xff94aaad, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, 0xffadaead, + 0xffadaead, 0xffadaead, 0xffadaead, 0xffada6a5, 0xffada6a5, 0xffada6a5, 0xffada6a5, 0xffbd9694, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff737473, 0xffadaead, 0xffadaead, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffb5b6b5, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, + 0x11000000, 0x22000000, 0x22000000, 0x33000000, 0x44000000, 0x55000000, 0x44000000, 0x33000000, + 0x33000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x22000000, 0x55000000, 0x88000000, 0xbb000000, + 0xdd0e0403, 0xdd0e0403, 0xee100503, 0xee100503, 0xff100503, 0xff100503, 0xff100503, 0xee100503, + 0xee100503, 0xee100503, 0xdd0e0403, 0xaa000000, 0x77000000, 0x44000000, 0x22000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff737573, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a6a5, + 0xffa5a6a5, 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffadaaad, + 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffadaaad, 0xffa5a6a5, 0xffa5a6a5, 0xffa5a6a5, + 0xffa5a6a5, 0xff737173, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x33000000, 0x880e0403, 0xcc0e0403, 0xee0e0403, 0xff1b0805, 0xff1b0805, 0xff1b0805, + 0xff1b0805, 0xff1b0805, 0xff210b05, 0xff210b05, 0xff210b05, 0xff210b05, 0xff210b05, 0xff210b05, + 0xff210b05, 0xff210b05, 0xff1b0805, 0xff1b0805, 0xff1b0805, 0xee1b0805, 0xdd0b0403, 0x880b0403, + 0x44000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xffadaaad, 0xffdbbeb8, 0xffe9dfdb, 0xffe9dfdb, + 0xffe9dfdb, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, + 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6dbd6, 0xffe6dbd6, 0xffe6dbd6, + 0xffe6dbd6, 0xffa5a6a5, 0x00000000, 0x00000000, 0x00000000, 0x00080000, 0x00080000, 0x11080000, + 0x11080000, 0x22210400, 0x22210400, 0x33210400, 0x33210400, 0x33210400, 0x33210400, 0x33210400, + 0x22210400, 0x11100400, 0x11100400, 0x00100400, 0x00100400, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22000000, 0x66080303, + 0xaa100505, 0xee190808, 0xff1b0805, 0xff1b0805, 0xff290c08, 0xff290c08, 0xff290c08, 0xff290c08, + 0xff290c08, 0xff290c08, 0xff311008, 0xff311008, 0xff311008, 0xff311008, 0xff311008, 0xff311008, + 0xff210b05, 0xff311008, 0xff290c08, 0xff290c08, 0xff290c08, 0xff290c08, 0xff210c08, 0xff210c08, + 0xee160805, 0xaa0b0403, 0x55000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11030303, 0x22030303, 0x22080808, 0x330b0b0b, 0x44101010, 0x33101010, 0x330b0b0b, 0x33080808, + 0x22050505, 0x11030303, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xffadaaad, 0xffe9dfdb, 0xfff7ffff, 0xffce9e94, + 0xffce9e94, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffce9e94, 0xffce9e94, 0xffce9e94, + 0xffce9e94, 0xffce968c, 0xffce968c, 0xffce968c, 0xffce968c, 0xffc59284, 0xffc59284, 0xfff7ffff, + 0xffe6dbd6, 0xffa5a6a5, 0x00000000, 0x00000000, 0x00000000, 0x00080000, 0x11080000, 0x22080000, + 0x33080000, 0x66210400, 0x99210400, 0xaa210400, 0xbb210400, 0xbb210400, 0xbb210400, 0xaa210400, + 0x66210400, 0x33100400, 0x22100400, 0x11100400, 0x00100400, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x66190705, 0xcc210808, 0xff340f0e, + 0xff340f0e, 0xff340f0e, 0xff3a1010, 0xff3a1010, 0xff3a1010, 0xff3a1010, 0xff3a1010, 0xff4a1613, + 0xff4a1613, 0xff3a1010, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xff3a1010, 0xff471613, + 0xff3a1010, 0xff3a1010, 0xff311010, 0xff311010, 0xff311010, 0xff311010, 0xff37100b, 0xff37100b, + 0xff290c08, 0xff290c08, 0xee160705, 0xaa160705, 0x33000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00080808, 0x00080808, 0x11080808, 0x55503a37, 0x886b494a, + 0xbb8c6160, 0xddad7976, 0xeead7976, 0xffa57479, 0xffa57479, 0xeea57479, 0xdd9c6163, 0xcc794542, + 0x99794542, 0x663c2421, 0x22000400, 0x11080400, 0x11080400, 0x00080400, 0x00080400, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xffadaaad, 0xffe9dfdb, 0xffce9e94, 0xffce9e94, + 0xffce9e94, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffce9e94, 0xffce9e94, 0xffce9e94, + 0xffce9e94, 0xffce968c, 0xffce968c, 0xffce968c, 0xffce968c, 0xffc59284, 0xffc59284, 0xffc59284, + 0xffe6dbd6, 0xffa5a6a5, 0x00000000, 0x00000000, 0x00000000, 0x11080000, 0x22080000, 0x44080000, + 0xaa080000, 0xdd55241b, 0xee894537, 0xee894537, 0xee894537, 0xee9f584d, 0xee9f584d, 0xee9f584d, + 0xdd9f584d, 0xbb100400, 0x55100400, 0x22100400, 0x11100400, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x22000000, 0x99190705, 0xee310d0b, 0xff340f0e, 0xff340f0e, + 0xff340f0e, 0xff471613, 0xff471613, 0xff471613, 0xff471613, 0xff471613, 0xff4a1613, 0xff5a1b16, + 0xff4a1613, 0xff5a1b16, 0xff501813, 0xff501813, 0xff501813, 0xff501813, 0xff551b16, 0xff471613, + 0xff471613, 0xff471613, 0xff421613, 0xff421613, 0xff421613, 0xff421613, 0xff37100b, 0xff37100b, + 0xff37100b, 0xff37100b, 0xff2c0d0b, 0xff2c0d0b, 0xcc160705, 0x44000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x33080808, 0x88503a37, 0xcc976c65, 0xffde9e94, 0xffce928c, + 0xffce928c, 0xffce928c, 0xffad7976, 0xffad878f, 0xffad878f, 0xffad878f, 0xffa57479, 0xffb56563, + 0xffb56563, 0xffb56563, 0xdd794542, 0x994a2019, 0x44080400, 0x11080400, 0x11080400, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xffadaaad, 0xffe9dfdb, 0xffce9e94, 0xffce9e94, + 0xffce9e94, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffce9e94, 0xffce9e94, 0xffce9e94, + 0xffce9e94, 0xffce968c, 0xffce968c, 0xffce968c, 0xffce968c, 0xffc59284, 0xffc59284, 0xffc59284, + 0xffe6dbd6, 0xffa5a6a5, 0x00000000, 0x00000000, 0x00000000, 0x11080000, 0x33080000, 0xaa080000, + 0xee9c3d31, 0xee894537, 0xeebd6552, 0xeebd6552, 0xeebd6552, 0xee9f584d, 0xee9f584d, 0xee9f584d, + 0xeede8273, 0xeed6c2bd, 0xbb100400, 0x33100400, 0x11100400, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x66190705, 0xdd310d0b, 0xff4a1410, 0xff4a1410, 0xff471613, 0xff471613, + 0xff471613, 0xff471613, 0xff551b16, 0xff551b16, 0xff551b16, 0xff551b16, 0xff5a1b16, 0xff5a1b16, + 0xff6b2019, 0xff5a1b16, 0xff5d1c16, 0xff5d1c16, 0xff5d1c16, 0xff5d1c16, 0xff551b16, 0xff551b16, + 0xff551b16, 0xff551b16, 0xff521b16, 0xff421613, 0xff421613, 0xff421613, 0xff45140e, 0xff45140e, + 0xff45140e, 0xff45140e, 0xff421410, 0xff421410, 0xff2c0d0b, 0xdd160705, 0x77000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x22000000, 0x884d3634, 0xdd976c65, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffce928c, + 0xffce928c, 0xffad7976, 0xffad7976, 0xffad878f, 0xffb59aa5, 0xffad878f, 0xffad878f, 0xffb56563, + 0xffb56563, 0xffb56563, 0xffb56563, 0xffce594a, 0xdd8c3d31, 0x994a2019, 0x44080400, 0x11000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00080408, 0xff979697, 0xffe6e3e6, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffce9e94, 0xffce9e94, 0xffce9a8f, 0xffce9a8f, 0xffce9a94, 0xffce9a94, 0xffce9a94, + 0xffce9a94, 0xffce968c, 0xffc88f84, 0xffc88f84, 0xffc88f84, 0xffbd8273, 0xffbd8273, 0xffbd8273, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x11000000, 0x22210400, 0x66210400, 0xdd210400, + 0xee945a52, 0xeea5615a, 0xeeaa6d68, 0xeeaa6d68, 0xeeaa6d68, 0xeead6563, 0xeead6563, 0xeeaf6c68, + 0xeeb57973, 0xeea7938f, 0xeeefdbd6, 0x77190400, 0x22190400, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x77190808, 0xee4a1410, 0xff4a1410, 0xff4a1410, 0xff4a1410, 0xff5a1c19, 0xff5a1c19, + 0xff5a1c19, 0xff5a1c19, 0xff632019, 0xff632019, 0xff632019, 0xff632019, 0xff6b2019, 0xff6b2019, + 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff632019, 0xff632019, + 0xff632019, 0xff632019, 0xff632019, 0xff521b16, 0xff521b16, 0xff521b16, 0xff521810, 0xff521810, + 0xff521810, 0xff45140e, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xee290c08, 0x66000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x554d3634, 0xbb9a6c68, 0xffe6a29c, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffce928c, + 0xffce928c, 0xffad7976, 0xffad7976, 0xffad878f, 0xffb59aa5, 0xffb59aa5, 0xffad878f, 0xffb56563, + 0xffb56563, 0xffb56563, 0xffb56563, 0xffce594a, 0xffce594a, 0xffce594a, 0xcc8c3d31, 0x77311010, + 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00080408, 0xff979697, 0xffe6e3e6, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffce9a8f, 0xffce9a8f, 0xffce9a8f, 0xffce9689, 0xffce9a94, 0xffdebab8, 0xffdebab8, + 0xffce9a94, 0xffc88f84, 0xffc88f84, 0xffc88f84, 0xffc3887b, 0xffbd8273, 0xffbd8273, 0xffbd8273, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x11000000, 0x33210400, 0x99210400, 0xee945a52, + 0xee945a52, 0xeeaa6d68, 0xeeaf7976, 0xeeaf7976, 0xeeaf7976, 0xeeaf6c68, 0xeeaf6c68, 0xeeaf6c68, + 0xeeb2736e, 0xeea7938f, 0xeeefdbd6, 0xaa190400, 0x33190400, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080000, 0x00080000, + 0x662c0c08, 0xee501810, 0xff521819, 0xff521819, 0xff521819, 0xff631e1b, 0xff631c19, 0xff631c19, + 0xff6e221b, 0xff6e221b, 0xff6b2019, 0xff76241b, 0xff76241b, 0xff76241b, 0xff732421, 0xff732421, + 0xff732421, 0xff732421, 0xff732421, 0xff732421, 0xff732421, 0xff732421, 0xff76241b, 0xff6b2019, + 0xff6b2019, 0xff6b2019, 0xff65201b, 0xff65201b, 0xff65201b, 0xff5a1c19, 0xff581c16, 0xff581c16, + 0xff581c16, 0xff4a1810, 0xff4d1813, 0xff4d1813, 0xff4d1813, 0xff421410, 0xff34120b, 0xdd1e0b05, + 0x55080400, 0x11080400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x775a413a, + 0xddb27f76, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffdb9a91, 0xffd68e8c, + 0xffc07f7e, 0xffaa7070, 0xffaa7070, 0xffaa8e97, 0xffb8a2aa, 0xffb8a2aa, 0xffaa8e97, 0xff94696b, + 0xff9c5e5d, 0xff9c5e5d, 0xffa55450, 0xffbd5142, 0xffbd5142, 0xffbd493c, 0xffbd493c, 0xeeb53929, + 0x9942160e, 0x33080400, 0x11080400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00080408, 0xff979697, 0xffe6e3e6, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffce9689, 0xffce9689, 0xffce9689, 0xffce9284, 0xffce9a94, 0xfffffbff, 0xfffffbff, + 0xffce9a94, 0xffc88f84, 0xffc3887b, 0xffc3887b, 0xffc3887b, 0xffbd8273, 0xffbd8273, 0xffbd8273, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x11000000, 0x44210400, 0xbb210400, 0xee945a52, + 0xeece867b, 0xeeaf7976, 0xeeaf7976, 0xeeaf7976, 0xeeaf7976, 0xeeb2736e, 0xeeb2736e, 0xeeaf6c68, + 0xeeb2736e, 0xeea7938f, 0xeeefdbd6, 0xcc604c47, 0x44190400, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00080000, 0x55080000, + 0xee501810, 0xff501810, 0xff631e1b, 0xff631e1b, 0xff631e1b, 0xff73231e, 0xff6e221b, 0xff6e221b, + 0xff79271e, 0xff6e221b, 0xff76241b, 0xff76241b, 0xff76241b, 0xff81281e, 0xff792721, 0xff792721, + 0xff792721, 0xff792721, 0xff7b2721, 0xff7b2721, 0xff7b2721, 0xff7b2721, 0xff76241b, 0xff76241b, + 0xff76241b, 0xff76241b, 0xff70241e, 0xff70241e, 0xff70241e, 0xff65201b, 0xff65201b, 0xff65201b, + 0xff581c16, 0xff581c16, 0xff4d1813, 0xff4d1813, 0xff4d1813, 0xff4d1813, 0xff4a1810, 0xff34120b, + 0xcc1e0b05, 0x44080400, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x7745312f, 0xeede9e94, + 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffdb9a91, 0xffd9968f, 0xffd68e8c, + 0xffc07f7e, 0xffaa7070, 0xffaa7070, 0xffaa8e97, 0xffb8a2aa, 0xffb8a2aa, 0xffaa8e97, 0xff9c5e5d, + 0xffa55450, 0xffa55450, 0xffa55450, 0xffbd5142, 0xffbd493c, 0xffbd493c, 0xffbd4137, 0xffb53929, + 0xeeb53929, 0x9942160e, 0x33080400, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00080408, 0xff979697, 0xffe6e3e6, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffce9689, 0xffce9284, 0xffce9284, 0xffce9284, 0xffdebab8, 0xfffffbff, 0xfffffbff, + 0xffefdbdb, 0xffc3887b, 0xffc3887b, 0xffc3887b, 0xffbd8273, 0xffbd8273, 0xffbd8273, 0xffbd8273, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x55210400, 0xcc210400, 0xeece867b, + 0xeece867b, 0xeeb58684, 0xeeb58684, 0xeeb58684, 0xeeaf7976, 0xeeb57973, 0xeeb57973, 0xeeb2736e, + 0xeeb57973, 0xeea7938f, 0xeea7938f, 0xdda7938f, 0x66190400, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33080000, 0xdd501810, + 0xff732419, 0xff732419, 0xff73231e, 0xff73231e, 0xff73231e, 0xff73231e, 0xff79271e, 0xff79271e, + 0xff79271e, 0xff79271e, 0xff81281e, 0xff81281e, 0xff81281e, 0xff81281e, 0xff7e2a21, 0xff7e2a21, + 0xff7e2a21, 0xff7e2a21, 0xff842a21, 0xff842a21, 0xff842a21, 0xff842a21, 0xff8c2d21, 0xff81281e, + 0xff81281e, 0xff81281e, 0xff7b2821, 0xff70241e, 0xff70241e, 0xff70241e, 0xff732421, 0xff65201b, + 0xff65201b, 0xff581c16, 0xff581c16, 0xff581c16, 0xff4d1813, 0xff4d1813, 0xff4a1810, 0xff4a1810, + 0xff34120b, 0x99080400, 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x7745312f, 0xeece928c, 0xffde9e94, + 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffdb9a91, 0xffdb9a91, 0xffd9968f, 0xffd68e8c, + 0xffc07f7e, 0xffaa7070, 0xff946163, 0xff9c7984, 0xffc5b6bd, 0xffc5b6bd, 0xff9c7984, 0xffa55450, + 0xffa55450, 0xffa55450, 0xffad4942, 0xffbd493c, 0xffbd493c, 0xffbd4137, 0xffbd3931, 0xffb53929, + 0xffb53929, 0xeeb53929, 0x9942160e, 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffce9684, 0xffce9684, + 0xffce9684, 0xffce9284, 0xffce9284, 0xffce9284, 0xffce9284, 0xfffffbf7, 0xffffffff, 0xffffffff, + 0xfffffbf7, 0xffd3aaa2, 0xffbd8273, 0xffbd8273, 0xffbd8273, 0xffad796b, 0xffad796b, 0xffad796b, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x66190000, 0xdd523331, 0xeec59a94, + 0xeec59a94, 0xeeb88e84, 0xeeb88e84, 0xeeb5867b, 0xeeb5867b, 0xeeaf7c73, 0xeead756b, 0xeead756b, + 0xeead756b, 0xee947168, 0xeecea69c, 0xeecea69c, 0x77210800, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0xaa2c0c08, 0xff732419, + 0xff732419, 0xff732419, 0xff73231e, 0xff73231e, 0xff842821, 0xff842821, 0xff79271e, 0xff842d21, + 0xff842d21, 0xff842d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff842d21, 0xff842d21, + 0xff842d21, 0xff842d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, + 0xff8c2d21, 0xff81281e, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff732421, 0xff732421, + 0xff732421, 0xff65201b, 0xff632019, 0xff581c16, 0xff581c16, 0xff581c16, 0xff4a1810, 0xff4a1810, + 0xff34120b, 0xee1e0b05, 0x66000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x5545312f, 0xddce928c, 0xffce928c, 0xffde9e94, + 0xffde9e94, 0xffde9e94, 0xffde9e94, 0xffdb9a91, 0xffdb9a91, 0xffd9968f, 0xffd6928c, 0xffd68e8c, + 0xffc07f7e, 0xffaa7070, 0xff946163, 0xff9c7984, 0xffc5b6bd, 0xffc5b6bd, 0xff9c7984, 0xffa55450, + 0xffad4942, 0xffad4942, 0xffad4942, 0xffbd493c, 0xffbd4137, 0xffbd3931, 0xffbd3931, 0xffb53929, + 0xffb53929, 0xffb53929, 0xee7b271b, 0x88290c08, 0x33000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffce9684, 0xffce9684, + 0xffce9684, 0xffce9284, 0xffce9284, 0xffce9284, 0xffefdbd6, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffe9d2d0, 0xffbd8273, 0xffbd8273, 0xffbd8273, 0xffad796b, 0xffad796b, 0xffad796b, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x77190000, 0xdd523331, 0xeec59a94, + 0xeec59a94, 0xeeba968c, 0xeeb88e84, 0xeeb88e84, 0xeeb5867b, 0xeeb2837b, 0xeeaf7c73, 0xeead756b, + 0xeead756b, 0xee947168, 0xeecea69c, 0xeecea69c, 0x77210800, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x44000000, 0xee6b2021, 0xff762421, + 0xff762421, 0xff762421, 0xff7b2421, 0xff862824, 0xff862824, 0xff912d26, 0xff943121, 0xff943121, + 0xff943121, 0xff943121, 0xff8c3129, 0xff8c3129, 0xff8c3129, 0xff8c3129, 0xff8c3529, 0xff8c3529, + 0xff8c3529, 0xff8c3529, 0xff8c3529, 0xff8c3529, 0xff8c3529, 0xff8c3529, 0xff8c3129, 0xff8c3129, + 0xff8c3129, 0xff8c3129, 0xff7b2d21, 0xff7b2d21, 0xff7b2d21, 0xff7b2d21, 0xff7b2d29, 0xff7b2d29, + 0xff7b2d29, 0xff7b2d29, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff581c16, 0xff4d1813, + 0xff4d1813, 0xff421410, 0xaa000000, 0x33000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x22191419, 0xbb976865, 0xffd6928c, 0xffd6928c, 0xffde9694, + 0xffde9694, 0xffde9694, 0xffde9694, 0xffde9694, 0xffde9694, 0xffdb908c, 0xffdb908c, 0xffd68a7b, + 0xffbd776b, 0xffa5645a, 0xff8c514a, 0xff9a7484, 0xffd6cad6, 0xffd6cad6, 0xff9a7484, 0xffad4942, + 0xffa2423a, 0xffad4942, 0xffad4942, 0xffc54131, 0xffbd3d2f, 0xffb5392c, 0xffb5392c, 0xffaa352c, + 0xffaa352c, 0xffaa352c, 0xff9f3126, 0xdd652216, 0x55080400, 0x22080400, 0x11080400, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffce9684, 0xffce9684, + 0xffce9684, 0xffce9284, 0xffce9284, 0xffdeb6ad, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xfffffbff, 0xffd3aaa2, 0xffbd8273, 0xffbd8273, 0xffad796b, 0xffad796b, 0xffad796b, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x77190000, 0xee8c6763, 0xeec59a94, + 0xeec59a94, 0xeebd9e94, 0xeeba968c, 0xeeb88e84, 0xeeb88e84, 0xeeb2837b, 0xeeb2837b, 0xeeaf7c73, + 0xeead756b, 0xee947168, 0xeecea69c, 0xeecea69c, 0x88210800, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0xaa31100e, 0xff812821, 0xff812821, + 0xff762421, 0xff812821, 0xff862824, 0xff862824, 0xff912d26, 0xff912d26, 0xff943121, 0xff9a746e, + 0xff9c9694, 0xff9c9694, 0xff978481, 0xff978481, 0xff978481, 0xff978481, 0xffa29391, 0xffa29391, + 0xffa29391, 0xffa29391, 0xffa29391, 0xffa29391, 0xffa29391, 0xffa29391, 0xffa29291, 0xffa29291, + 0xffa29291, 0xffa29291, 0xffb2aeaa, 0xffb2aeaa, 0xffb2aeaa, 0xffb2aeaa, 0xffceb6b2, 0xfff7fbf7, + 0xfff7fbf7, 0xfff7fbf7, 0xffbd9694, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff581c16, 0xff581c16, + 0xff4d1813, 0xff4d1813, 0xee2c0d0b, 0x66000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x88583e3f, 0xffd6928c, 0xffd6928c, 0xffd6928c, 0xffdb928f, + 0xffdb928f, 0xffdb928f, 0xffdb928f, 0xffdb908c, 0xffdb908c, 0xffdb908c, 0xffdb908c, 0xffd68a7b, + 0xffbd776b, 0xffa5645a, 0xff8c514a, 0xff9a7484, 0xffd6cad6, 0xffd6cad6, 0xff9a7484, 0xff973b31, + 0xffa2423a, 0xffa2423a, 0xffa2423a, 0xffbd3d2f, 0xffb5392c, 0xffb5392c, 0xffad3529, 0xffaa352c, + 0xffaa352c, 0xff9f3126, 0xff9f3126, 0xff943121, 0xaa37130b, 0x44080400, 0x11080400, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffce9684, 0xffce9684, + 0xffce9684, 0xffce9284, 0xffce9284, 0xffefdbd6, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xfffffbff, 0xfffffbff, 0xffbd8273, 0xffbd8273, 0xffad796b, 0xffad796b, 0xffad796b, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x88190000, 0xee8c6763, 0xeec59a94, + 0xeec59a94, 0xeebd9e94, 0xeeba968c, 0xeeba968c, 0xeeb88e84, 0xeeb58a84, 0xeeb2837b, 0xeeaf7c73, + 0xeead756b, 0xee947168, 0xeecea69c, 0xeecea69c, 0x99210800, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x33000000, 0xee63201b, 0xff812821, 0xff812821, + 0xff812821, 0xff8c2d21, 0xff912d26, 0xff912d26, 0xff912d26, 0xff912d26, 0xff943121, 0xff943121, + 0xff9c9694, 0xff9c9694, 0xff978481, 0xff978481, 0xff978481, 0xff9caead, 0xffa29391, 0xffa29391, + 0xffa29391, 0xffa29391, 0xffa29391, 0xffa29391, 0xffa29391, 0xffa29391, 0xffa29291, 0xffa29291, + 0xffa29291, 0xffa29291, 0xffb2aeaa, 0xffb2aeaa, 0xffb2aeaa, 0xffb2aeaa, 0xfff7fbf7, 0xfff7fbf7, + 0xfff7fbf7, 0xfff7fbf7, 0xff864842, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff581c16, 0xff581c16, + 0xff581c16, 0xff4d1813, 0xff421410, 0x99000000, 0x33000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x33211413, 0xdd976865, 0xffd6928c, 0xffd6928c, 0xffd6928c, 0xffd98e89, + 0xffd98e89, 0xffd98e89, 0xffd98e89, 0xffdb908c, 0xffdb908c, 0xffd98b84, 0xffd98b84, 0xffd68a7b, + 0xffbd776b, 0xffa5645a, 0xff8c514a, 0xff7b495a, 0xffd6cad6, 0xffd6cad6, 0xff7b495a, 0xff8c3529, + 0xff973b31, 0xff973b31, 0xff973b31, 0xffb5392c, 0xffb5392c, 0xffad3529, 0xffad3529, 0xffaa352c, + 0xff9f3126, 0xff9f3126, 0xff9f3126, 0xff943121, 0xee652216, 0x77080400, 0x33080400, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffc58a7b, 0xffc58a7b, + 0xffc58a7b, 0xffbd8273, 0xffe9d0cb, 0xfffff7f7, 0xfffff7f7, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xfff7f3f7, 0xfff7f3f7, 0xffdec9c8, 0xffad756b, 0xffa57163, 0xffa57163, 0xffa57163, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x88190000, 0xee977779, 0xeed6b2b5, + 0xeed6b2b5, 0xeec3a39f, 0xeec09d9a, 0xeebd9694, 0xeebd9694, 0xeeb58b84, 0xeeb5847b, 0xeeb57d73, + 0xeeb57d73, 0xee9a6f68, 0xeecea29c, 0xeecea29c, 0x99310800, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0xff4a464a, 0xff8c888c, 0xff8c888c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff949294, 0xff949294, 0xff9c9a9c, 0xff9c9a9c, + 0xff9c9a9c, 0xff9c9a9c, 0xff9c9a9c, 0xff9c9a9c, 0xff9c9a9c, 0xff9c9a9c, 0xff9c9a9c, 0xff9c9a9c, + 0xff9c9a9c, 0xff9c9a9c, 0xff9c9a9c, 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949694, + 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949694, + 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949694, 0xff949294, + 0xff949294, 0xff949294, 0xff949294, 0xff949294, 0xff949294, 0xff949294, 0xff949294, 0xff949294, + 0xff949294, 0xff949294, 0xff949294, 0xff949294, 0xff949294, 0xff949294, 0xff949294, 0xff948e94, + 0xff948e94, 0xff948e94, 0xff948e94, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, + 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff8c8e8c, 0xff949694, + 0xff949694, 0xff949694, 0xff737573, 0xff5d5c5d, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x7731100e, 0xff943129, 0xff8c2d21, 0xff8c2d21, + 0xff8c2d21, 0xff8c2d21, 0xff912d26, 0xff9c3129, 0xff9c3129, 0xff9c3129, 0xff943121, 0xff943121, + 0xff9a746e, 0xff9c9694, 0xff9caead, 0xff9caead, 0xff9caead, 0xff9caead, 0xffadc2c5, 0xffadc2c5, + 0xffadc2c5, 0xffadc2c5, 0xffadc2c5, 0xffadc2c5, 0xffadc2c5, 0xffadc2c5, 0xffadc2c5, 0xffadc2c5, + 0xffadc2c5, 0xffadc2c5, 0xffb2aeaa, 0xffb2aeaa, 0xffceefef, 0xffceefef, 0xfff7fbf7, 0xfff7fbf7, + 0xfff7fbf7, 0xffa5716e, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff632019, 0xff581c16, + 0xff581c16, 0xff4d1813, 0xff421410, 0xcc160705, 0x44000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x88633d3a, 0xffd6928c, 0xffd6928c, 0xffd6928c, 0xffd6928c, 0xffd98e89, + 0xffd98e89, 0xffd98e89, 0xffd68a84, 0xffd98b84, 0xffd98b84, 0xffd6867b, 0xffd6867b, 0xffbd776b, + 0xffbd776b, 0xffa5645a, 0xff8c514a, 0xff7b495a, 0xffd6cad6, 0xffd6cad6, 0xff7b495a, 0xff8c3529, + 0xff8c3529, 0xff8c3529, 0xff973b31, 0xffb5392c, 0xffad3529, 0xffad3529, 0xffad3529, 0xff9f3126, + 0xff9f3126, 0xff942d21, 0xff942d21, 0xff943121, 0xff943121, 0xbb37130b, 0x44080400, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffc58a7b, 0xffc58a7b, + 0xffc58a7b, 0xffbd8273, 0xffe9d0cb, 0xfffff7f7, 0xfffff7f7, 0xffe6d2ce, 0xffe6d2ce, 0xffe6d2ce, + 0xffe6d2ce, 0xfff7f3f7, 0xfff7f3f7, 0xffdec9c8, 0xffad756b, 0xffa57163, 0xffa57163, 0xffa57163, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x88190000, 0xee977779, 0xeed6b2b5, + 0xeed6b2b5, 0xeec5aaa5, 0xeec3a39f, 0xeebd9694, 0xeebd9694, 0xeeb58b84, 0xeeb5847b, 0xeeb5847b, + 0xeeb57d73, 0xee9a6f68, 0xeecea29c, 0xeecea29c, 0x99310800, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0xff8c888c, 0xff8c888c, 0xffcecace, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, + 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, + 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffc0c0c0, 0xffc0c0c0, 0xffced0ce, 0xffcecdce, + 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcecdce, + 0xffcecdce, 0xffcecdce, 0xffcecdce, 0xffcbc9cb, 0xffcbc9cb, 0xffcbc9cb, 0xffcbc9cb, 0xffc5c9c5, + 0xffc5c9c5, 0xffc5c9c5, 0xffc5c9c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c5c5, + 0xffc5c5c5, 0xffc5c5c5, 0xffc5c5c5, 0xffc5c2c5, 0xffc5c2c5, 0xffc5c2c5, 0xffc5c2c5, 0xffc5c2c5, + 0xffc5c2c5, 0xffc5c2c5, 0xffc5c2c5, 0xffc0c2c0, 0xffc0c2c0, 0xffc0c2c0, 0xffc0c2c0, 0xffc0bec0, + 0xffc0bec0, 0xffc0bec0, 0xffc0bec0, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, + 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xffb5b6b5, + 0xffb5b6b5, 0xffb5b6b5, 0xffb5b6b5, 0xff8c8a8c, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x11000000, 0xaa31100e, 0xff943129, 0xff8c2d21, 0xff8c2d21, + 0xff912f24, 0xff912f24, 0xff9c3129, 0xff9c3129, 0xffa23329, 0xffa23329, 0xffad3929, 0xffad3929, + 0xffad3929, 0xffb59a9c, 0xffc8b5b5, 0xffc8b5b5, 0xffc8b5b5, 0xffc8b5b5, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffdee3de, 0xffe9ece9, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffdbb9b5, 0xff942d21, 0xff812821, 0xff812821, 0xff762421, 0xff6b2021, 0xff682019, 0xff682019, + 0xff5d1c19, 0xff521819, 0xff4a1810, 0xdd190805, 0x66000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0xcc8f514d, 0xffd6867b, 0xffd6867b, 0xffd6867b, 0xffd6867b, 0xffd6827b, + 0xffd6827b, 0xffd6827b, 0xffd6827b, 0xffd6867b, 0xffd6867b, 0xffd6867b, 0xffd07970, 0xffce7573, + 0xffce7573, 0xffb25e5a, 0xff974842, 0xff632d3a, 0xffefefef, 0xffefefef, 0xff632d3a, 0xff862b1e, + 0xff9a3224, 0xff9a3224, 0xffad3929, 0xffad3529, 0xffad3529, 0xff9c3126, 0xff9c3126, 0xff943121, + 0xff892d21, 0xff892d21, 0xff892d21, 0xff7b2821, 0xff7b2821, 0xdd551b16, 0x66080000, 0x22000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffc58a7b, 0xffc58a7b, + 0xffc58a7b, 0xffbd8273, 0xffbd8273, 0xffbd8273, 0xffbd8273, 0xffb5796b, 0xffb5796b, 0xffb5796b, + 0xffb5796b, 0xffad756b, 0xffad756b, 0xffad756b, 0xffad756b, 0xffa57163, 0xffa57163, 0xffa57163, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee977779, 0xeed6b2b5, + 0xeed6b2b5, 0xeec5aaa5, 0xeec3a39f, 0xeec09d9a, 0xeebd9694, 0xeeb58b84, 0xeeb58b84, 0xeeb5847b, + 0xeeb57d73, 0xee9a6f68, 0xeecea29c, 0xeecea29c, 0xaa310800, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0xff8c888c, 0xffcecace, 0xffcecace, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffe6ebe6, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffdee3de, + 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffb5b6b5, 0xff8c8a8c, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x22000000, 0xdd63201b, 0xff943129, 0xff912f24, 0xff912f24, + 0xff912f24, 0xff912f24, 0xffa23329, 0xffa23329, 0xffa23329, 0xffa73629, 0xffad3929, 0xffad3929, + 0xffad3929, 0xffaf5950, 0xffc8b5b5, 0xffc8b5b5, 0xffd6dbde, 0xffd6dbde, 0xffe1dfe1, 0xffe1dfe1, + 0xffecebec, 0xffecebec, 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, + 0xfff1f0f1, 0xfff1f0f1, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffb8736b, 0xff942d21, 0xff8c2d21, 0xff812821, 0xff762421, 0xff762421, 0xff682019, 0xff682019, + 0xff5d1c19, 0xff521819, 0xff4a1810, 0xee31100b, 0x88000000, 0x22000000, 0x00000000, 0x00000000, + 0x00000000, 0x55472826, 0xffd67973, 0xffd37f76, 0xffd37f76, 0xffd37f76, 0xffd37f76, 0xffd6827b, + 0xffd6827b, 0xffd6827b, 0xffd6827b, 0xffd07970, 0xffd07970, 0xffd07970, 0xffd07970, 0xffce7573, + 0xffb25e5a, 0xff974842, 0xff974842, 0xff632d3a, 0xffefefef, 0xffefefef, 0xff632d3a, 0xff732419, + 0xff862b1e, 0xff9a3224, 0xff9a3224, 0xff9c3126, 0xff9c3126, 0xff9c3126, 0xff8c2d24, 0xff892d21, + 0xff892d21, 0xff7e2821, 0xff7e2821, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0x992f0d0b, 0x33000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffc58a7b, 0xffc58a7b, + 0xffc58a7b, 0xffbd8273, 0xffbd8273, 0xffbd8273, 0xffbd8273, 0xffb5796b, 0xffb5796b, 0xffb5796b, + 0xffb5796b, 0xffad756b, 0xffad756b, 0xffad756b, 0xffad756b, 0xffa57163, 0xffa57163, 0xffa57163, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee977779, 0xeed6b2b5, + 0xeed6b2b5, 0xeec5aaa5, 0xeec5aaa5, 0xeec09d9a, 0xeebd9694, 0xeeb5928c, 0xeeb58b84, 0xeeb5847b, + 0xeeb5847b, 0xee9a6f68, 0xeecea29c, 0xeecea29c, 0xaa310800, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00080408, 0xff8c888c, 0xffcecace, 0xffcecace, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffe6ebe6, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, + 0xffe6e7e6, 0xffe6e7e6, 0xffe6e7e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffe6e3e6, 0xffdee3de, + 0xffdee3de, 0xffdee3de, 0xffdee3de, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedfde, + 0xffdedfde, 0xffdedfde, 0xffdedfde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffdedbde, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6dbd6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffb5b6b5, 0xff8c8a8c, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x5531100e, 0xff943129, 0xff943129, 0xff912f24, 0xff912f24, + 0xff973226, 0xff973226, 0xffa23329, 0xffa23329, 0xffa73629, 0xffa73629, 0xffad3929, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffba8f8c, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffecebec, 0xffecebec, + 0xfff7f7f7, 0xfff7f7f7, 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, 0xfff1f0f1, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffdbb9b5, + 0xff942d21, 0xff942d21, 0xff8c2d21, 0xff812821, 0xff812821, 0xff762421, 0xff682019, 0xff682019, + 0xff682019, 0xff5d1c19, 0xff4a1810, 0xff4a1810, 0xaa000000, 0x33000000, 0x00000000, 0x00000000, + 0x00000000, 0x88472826, 0xffd67973, 0xffd07870, 0xffd07870, 0xffd07870, 0xffd07870, 0xffd37b73, + 0xffd37b73, 0xffd37b73, 0xffd0746b, 0xffd07970, 0xffcb6d65, 0xffcb6d65, 0xffcb6d65, 0xffb25e5a, + 0xffb25e5a, 0xff974842, 0xff7b3129, 0xff632d3a, 0xffefefef, 0xffefefef, 0xff632d3a, 0xff732419, + 0xff862b1e, 0xff9a3224, 0xff9a3224, 0xff9c3126, 0xff8c2d24, 0xff8c2d24, 0xff8c2d24, 0xff7e2821, + 0xff7e2821, 0xff7e2821, 0xff732421, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xbb2f0d0b, 0x44000000, + 0x22000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe9d5d0, 0xffbd8273, 0xffbd8273, + 0xffbd8273, 0xffad756b, 0xffad756b, 0xffad756b, 0xffad756b, 0xff9c6d63, 0xff9c6d63, 0xff9c6d63, + 0xff9c6d63, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6d63, 0xff9c6d63, 0xff9c6d63, + 0xffdececb, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee97827e, 0xeed6c2bd, + 0xeed6c2bd, 0xeec5b2b5, 0xeec3aaaa, 0xeec0a29f, 0xeebd9a94, 0xeeba8f86, 0xeeba8f86, 0xeeb88881, + 0xeeb5827b, 0xee976c6b, 0xeec59e9c, 0xeec59e9c, 0xaa3a0808, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0xff7e807e, 0xffbdbebd, 0xffbdbebd, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffd6d7d6, 0xffd6d7d6, + 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d7d6, 0xffd6d2d6, + 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffd6d2d6, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, + 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecece, 0xffcecace, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, 0xffcecace, + 0xffcecace, 0xffcecace, 0xffcecace, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, + 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffc5c6c5, 0xffbdbebd, + 0xffbdbebd, 0xffbdbebd, 0xffbdbebd, 0xff848284, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x7731100e, 0xff943129, 0xff943129, 0xff973226, 0xff973226, + 0xff973226, 0xff973226, 0xffa23329, 0xffa73629, 0xffa73629, 0xffa73629, 0xffad3929, 0xffad3929, + 0xffad3929, 0xffad3929, 0xffad6963, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffecebec, 0xfff7f7f7, + 0xfff7f7f7, 0xfff7f7f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xff942d21, + 0xff942d21, 0xff942d21, 0xff8c2d21, 0xff8c2d21, 0xff812821, 0xff812821, 0xff732419, 0xff682019, + 0xff682019, 0xff5d1c19, 0xff4a1810, 0xff4a1810, 0xbb190805, 0x44000000, 0x11000000, 0x00000000, + 0x11000000, 0xaa8f514d, 0xffd67973, 0xffce716b, 0xffce716b, 0xffce716b, 0xffce716b, 0xffce6d63, + 0xffce6d63, 0xffce6d63, 0xffce6d63, 0xffcb6d65, 0xffcb6d65, 0xffc5615a, 0xffc5615a, 0xffb25e5a, + 0xff974842, 0xff974842, 0xff7b3129, 0xff632d3a, 0xffefefef, 0xffefefef, 0xff632d3a, 0xff732419, + 0xff732419, 0xff862b1e, 0xff862b1e, 0xff8c2d24, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff732421, + 0xff732421, 0xff732421, 0xff732421, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xdd551b16, 0x55000000, + 0x22000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe9d5d0, 0xffbd8273, 0xffbd8273, + 0xffbd8273, 0xffad756b, 0xffad756b, 0xffad756b, 0xffad756b, 0xff9c6d63, 0xff9c6d63, 0xff9c6d63, + 0xff9c6d63, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6d63, 0xff9c6d63, 0xff9c6d63, + 0xffdececb, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee97827e, 0xeed6c2bd, + 0xeed6c2bd, 0xeec5b2b5, 0xeec3aaaa, 0xeec0a29f, 0xeebd9a94, 0xeebd968c, 0xeeba8f86, 0xeeb88881, + 0xeeb5827b, 0xee976c6b, 0xeec59e9c, 0xeec59e9c, 0xaa3a0808, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0xff3f423f, 0xff7e807e, 0xff7e807e, 0xff848484, 0xff848484, 0xff848484, 0xff848484, + 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, + 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff8f8f8f, 0xff8f8f8f, + 0xff8f8f8f, 0xff8f8f8f, 0xff8f8f8f, 0xff8f8f8f, 0xff8f8f8f, 0xff8f8f8f, 0xff8f8f8f, 0xff8f8e8f, + 0xff8f8e8f, 0xff8f8e8f, 0xff8f8e8f, 0xff8f8c8f, 0xff8f8c8f, 0xff8f8c8f, 0xff8f8c8f, 0xff898a89, + 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, + 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, 0xff898a89, 0xff898789, + 0xff898789, 0xff898789, 0xff898789, 0xff898789, 0xff898789, 0xff898789, 0xff898789, 0xff898789, + 0xff898789, 0xff898789, 0xff898789, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, + 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, + 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff848484, 0xff7e7f7e, + 0xff7e7f7e, 0xff7e7f7e, 0xff7e7f7e, 0xff585658, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x8834120e, 0xff9c3529, 0xff9c3529, 0xff9f3229, 0xff9f3229, + 0xff9f3229, 0xffa53529, 0xffaa362f, 0xffaf372c, 0xffaf372c, 0xffaf372c, 0xffb53931, 0xffb53931, + 0xffb83a2f, 0xffb53931, 0xffb53d31, 0xffcba39f, 0xffd6d7d6, 0xffd6d7d6, 0xffe6e3e6, 0xffefefef, + 0xfff7fbf7, 0xfff7fbf7, 0xfffcfcfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffd69e9c, 0xff9c3529, + 0xff9c3529, 0xff9c3529, 0xff942e21, 0xff8c2b21, 0xff8c2b21, 0xff842821, 0xff7b2421, 0xff651f1b, + 0xff651f1b, 0xff5a1c19, 0xff521810, 0xff521810, 0xcc1b0805, 0x55000000, 0x11000000, 0x00000000, + 0x11000000, 0xcc8f4c42, 0xffd67163, 0xffce6963, 0xffce6963, 0xffce6963, 0xffce6963, 0xffc5655a, + 0xffc5655a, 0xffc5655a, 0xffc5655a, 0xffc55952, 0xffc55952, 0xffc55952, 0xffc55952, 0xffbd493a, + 0xffbd493a, 0xff7e3126, 0xff7e3126, 0xff190808, 0xffffffff, 0xffffffff, 0xff190808, 0xff581b16, + 0xff842821, 0xff842821, 0xff842821, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff6b2019, + 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xff6b2019, 0xee471610, 0x55000000, + 0x22000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe9d5d0, 0xffffffff, 0xffbd8273, + 0xffbd8273, 0xffad756b, 0xffad756b, 0xffad756b, 0xffad756b, 0xff9c6d63, 0xff9c6d63, 0xff9c6d63, + 0xff9c6d63, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6963, 0xff9c6d63, 0xff9c6d63, 0xffffffff, + 0xffdececb, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee97827e, 0xeed6c2bd, + 0xeed6c2bd, 0xeec5b2b5, 0xeec3aaaa, 0xeec0a29f, 0xeebd9a94, 0xeebd968c, 0xeeba8f86, 0xeeb88881, + 0xeeb5827b, 0xee976c6b, 0xeec59e9c, 0xeec59e9c, 0xaa3a0808, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x9934120e, 0xff9c3529, 0xff9c3529, 0xff9f3229, 0xff9c3129, + 0xffa23329, 0xffa53529, 0xffaf372c, 0xffaf372c, 0xffb53929, 0xffb53929, 0xffb53931, 0xffb83a2f, + 0xffb53931, 0xffb83a2f, 0xffb53d31, 0xffb53d31, 0xffd6d7d6, 0xffd6d7d6, 0xffe6e3e6, 0xffefefef, + 0xffefefef, 0xfff7fbf7, 0xfffcfcfc, 0xfffcfcfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xff9c3529, 0xff9c3529, + 0xff9c3529, 0xff9c3529, 0xff942e21, 0xff942e21, 0xff8c2b21, 0xff842821, 0xff7b2421, 0xff70221e, + 0xff651f1b, 0xff5a1c19, 0xff521810, 0xff521810, 0xcc1b0805, 0x55000000, 0x11000000, 0x00000000, + 0x11000000, 0x22000000, 0x44000000, 0x66000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, + 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, + 0x88000000, 0x99000000, 0xaa000000, 0xcc190808, 0xffffffff, 0xffffffff, 0xbb190808, 0xaa000000, + 0x99000000, 0x88000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, + 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x77000000, 0x66000000, 0x44000000, + 0x22000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe9d5d0, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffdececb, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee97827e, 0xeed6c2bd, + 0xeed6c2bd, 0xeec5b2b5, 0xeec3aaaa, 0xeec0a29f, 0xeebd9a94, 0xeebd968c, 0xeeba8f86, 0xeeb88881, + 0xeeb5827b, 0xee976c6b, 0xeec59e9c, 0xeec59e9c, 0xaa3a0808, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000400, 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000400, + 0x00000400, 0x00000400, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0xaa34120e, 0xff9c3529, 0xff9c3529, 0xff9f3229, 0xff9f3229, + 0xffa53529, 0xffa53529, 0xffaf372c, 0xffb53929, 0xffb53929, 0xffb53929, 0xffb83a2f, 0xffb83a2f, + 0xffb83a2f, 0xffb83a2f, 0xffb53d31, 0xffb53d31, 0xffc07068, 0xffd6d7d6, 0xffded7de, 0xffe6e3e6, + 0xffefefef, 0xffefefef, 0xfffafafa, 0xfffcfcfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffc87d76, 0xff9c3529, 0xff9c3529, + 0xff9c3529, 0xff9c3529, 0xff942e21, 0xff942e21, 0xff8c2b21, 0xff842821, 0xff7b2421, 0xff70221e, + 0xff651f1b, 0xff651f1b, 0xff521810, 0xff521810, 0xdd1b0805, 0x66000000, 0x11000000, 0x00000000, + 0x00000000, 0x11000000, 0x22000000, 0x33000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, + 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, + 0x55000000, 0x66000000, 0x88000000, 0xaa190808, 0xffffffff, 0xffffffff, 0xaa190808, 0x88000000, + 0x66000000, 0x55000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, + 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x44000000, 0x33000000, 0x22000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee9c827e, 0xeedec2bd, + 0xeedec2bd, 0xeec5b6b5, 0xeec3aead, 0xeec0a6a5, 0xeebd9e9c, 0xeebd9694, 0xeeba8f8c, 0xeeb88884, + 0xeeb5827b, 0xee9c6d6b, 0xeece9e9c, 0xeece9e9c, 0xaa3a0c08, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0xbb68231b, 0xff9c3529, 0xff9c3529, 0xffa53529, 0xffa53529, + 0xffa53529, 0xffa53529, 0xffb53929, 0xffb53929, 0xffb53929, 0xffb53929, 0xffb83a2f, 0xffb83a2f, + 0xffba3b2c, 0xffb83a2f, 0xffb53d31, 0xffb53d31, 0xffb53d31, 0xffcba39f, 0xffded7de, 0xffe6e3e6, + 0xffe6e3e6, 0xffefefef, 0xfff7f7f7, 0xfffcfcfc, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffe4beba, 0xffad3d31, 0xff9c3529, 0xff9c3529, + 0xff9c3529, 0xff9c3529, 0xff9c3121, 0xff942e21, 0xff8c2b21, 0xff842821, 0xff7b2421, 0xff70221e, + 0xff651f1b, 0xff651f1b, 0xff521810, 0xff521810, 0xdd1b0805, 0x66000000, 0x22000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x22000000, 0x44000000, 0x66000000, 0x99190808, 0xffffffff, 0xffffffff, 0x88190808, 0x66000000, + 0x44000000, 0x22000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee9c827e, 0xeedec2bd, + 0xeedec2bd, 0xeec5b6b5, 0xeec3aead, 0xeec0a6a5, 0xeebd9e9c, 0xeebd9694, 0xeeba8f8c, 0xeeb88884, + 0xeeb5827b, 0xee9c6d6b, 0xeece9e9c, 0xeece9e9c, 0xaa3a0c08, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x9937120e, 0xffa53529, 0xffa53529, 0xffa53529, 0xffa53529, + 0xffa53529, 0xffaa3729, 0xffb53929, 0xffb53a2c, 0xffb53b2f, 0xffb53b2f, 0xffbd3b31, 0xffbd3b31, + 0xffbd3b31, 0xffbd3b31, 0xffbd3d31, 0xffbd3d31, 0xffbd3d31, 0xffbd6152, 0xffdedbde, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xfff7f7f7, 0xfff7f7f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffbff, 0xfffffbff, 0xffc87970, 0xffad3929, 0xffa53529, 0xffa53529, + 0xffa53529, 0xff9c3129, 0xff943129, 0xff8f2e26, 0xff892b24, 0xff842821, 0xff732421, 0xff6b221e, + 0xff631f1b, 0xff631f1b, 0xff521c10, 0xff37130b, 0xdd1b0905, 0x66000000, 0x22000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x33000000, 0x55000000, 0x88190808, 0xfffffbff, 0xfffffbff, 0x88190808, 0x55000000, + 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee9c827e, 0xeedec2bd, + 0xeedec2bd, 0xeec5b6b5, 0xeec3aead, 0xeec0a6a5, 0xeebd9e9c, 0xeebd9694, 0xeeba8f8c, 0xeeb88884, + 0xeeb5827b, 0xee9c6d6b, 0xeece9e9c, 0xeece9e9c, 0xaa3a0c08, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x8837120e, 0xffa53529, 0xffa53529, 0xffa53529, 0xffa53529, + 0xffa73629, 0xffad3929, 0xffb53a2c, 0xffb53a2c, 0xffb53a2c, 0xffb53a2c, 0xffbd3b31, 0xffbd3b31, + 0xffbd3b31, 0xffbd3b31, 0xffbd3d31, 0xffbd3d31, 0xffbd3d31, 0xffbd3d31, 0xffd3a9a7, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffefefef, 0xfff7f7f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffbff, 0xffe4bab8, 0xffad3929, 0xffad3929, 0xffa53529, 0xffa53529, + 0xffa53529, 0xff9c3129, 0xff943129, 0xff8f2e26, 0xff892b24, 0xff842821, 0xff732421, 0xff6b221e, + 0xff631f1b, 0xff5a1c19, 0xff521c10, 0xff37130b, 0xcc1b0905, 0x66000000, 0x22000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x33000000, 0x55000000, 0x88190808, 0xfffffbff, 0xfffffbff, 0x88190808, 0x55000000, + 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee9c827e, 0xeedec2bd, + 0xeedec2bd, 0xeec5b6b5, 0xeec3aead, 0xeec0a6a5, 0xeebd9e9c, 0xeebd9694, 0xeeba8f8c, 0xeeb88884, + 0xeeb5827b, 0xee9c6d6b, 0xeece9e9c, 0xeece9e9c, 0xaa3a0c08, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x7737120e, 0xffa53529, 0xffa53529, 0xffa73629, 0xffa73629, + 0xffa53529, 0xffad3929, 0xffb53929, 0xffb53a2c, 0xffb53a2c, 0xffb53b2f, 0xffbd3a31, 0xffbd3b31, + 0xffbd3b31, 0xffbd3b31, 0xffbd3d31, 0xffbd3d31, 0xffbd3d31, 0xffbd3d31, 0xffbd453a, 0xffdedbde, + 0xffdedbde, 0xffdedbde, 0xffefefef, 0xfff7f7f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xfffffbff, 0xffad3929, 0xffad3929, 0xffad3929, 0xffa53529, 0xffa53529, + 0xffa53529, 0xff9f3229, 0xff943129, 0xff8f2e26, 0xff892b24, 0xff842821, 0xff732421, 0xff6b221e, + 0xff631f1b, 0xff5a1c19, 0xff521c10, 0xff37130b, 0xcc1b0905, 0x66000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x22000000, 0x44000000, 0x66000000, 0x99190808, 0xfffffbff, 0xfffffbff, 0x99190808, 0x66000000, + 0x44000000, 0x22000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee977f79, 0xeed6beb5, + 0xeed6beb5, 0xeec5b2b5, 0xeec3abaa, 0xeec0a59f, 0xeebd9e94, 0xeebd968c, 0xeeba8f86, 0xeeb88881, + 0xeeb5827b, 0xee9a6d65, 0xeece9e94, 0xeece9e94, 0xaa310c08, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x6637120e, 0xffa53529, 0xffa53529, 0xffa53529, 0xffa53529, + 0xffa53529, 0xffaa3729, 0xffb53929, 0xffb53a2c, 0xffb53b2f, 0xffb53b2f, 0xffbd3b31, 0xffbd3b31, + 0xffbd3d31, 0xffbd3b31, 0xffbd3d31, 0xffbd3d31, 0xffbd3d31, 0xffbd3d31, 0xffbd453a, 0xffc87770, + 0xffdedbde, 0xffdedbde, 0xffe6e7e6, 0xfff7f7f7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffc87970, 0xffad3929, 0xffad3929, 0xffad3929, 0xffa53529, 0xffa53529, + 0xffa53529, 0xff9f3229, 0xff943129, 0xff8f2e26, 0xff892b24, 0xff842821, 0xff732421, 0xff6b221e, + 0xff631f1b, 0xff5a1c19, 0xff521c10, 0xff37130b, 0xbb000000, 0x55000000, 0x11000000, 0x00000000, + 0x00000000, 0x7745221e, 0xffce655a, 0xffc56152, 0xffc56152, 0xffc56152, 0xffc56152, 0xffc5594a, + 0xffc5594a, 0xffc5594a, 0xffc5594a, 0xffbd5142, 0xffbd5142, 0xffbd5142, 0xffbd5142, 0xffce4531, + 0xff892e21, 0xff892e21, 0xff892e21, 0xff190808, 0xfffffbff, 0xfffffbff, 0xff190808, 0xff581b16, + 0xff581b16, 0xff842821, 0xff842821, 0xff732419, 0xff732419, 0xff732419, 0xff732419, 0xff632019, + 0xff632019, 0xff632019, 0xff632019, 0xff632019, 0xff632019, 0xff632019, 0x88210b08, 0x22000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee977f79, 0xeed6beb5, + 0xeed6beb5, 0xeec5b2b5, 0xeec3abaa, 0xeec0a59f, 0xeebd9e94, 0xeebd968c, 0xeeba8f86, 0xeeb88881, + 0xeeb5827b, 0xee9a6d65, 0xeece9e94, 0xeece9e94, 0xaa310c08, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00080000, 0x33080000, 0xee9c3529, 0xff9c3529, 0xffa53529, 0xffa53529, + 0xffa73629, 0xffad3929, 0xffaf392c, 0xffb2392f, 0xffb2392f, 0xffb2392f, 0xffba3b2f, 0xffba3b2f, + 0xffba3b2f, 0xffba3b2f, 0xffba3b31, 0xffb83a31, 0xffba3b31, 0xffba3b31, 0xffb53931, 0xffb53931, + 0xffcba7a5, 0xffd6dfde, 0xffe6e3e6, 0xfff7f6f7, 0xffffffff, 0xffffffff, 0xfffffbff, 0xfffffbff, + 0xfffffbff, 0xfffffbff, 0xffb53d31, 0xffaf372c, 0xffaf372c, 0xffaf372c, 0xffa53529, 0xffa23329, + 0xff9f3229, 0xff9c3129, 0xff943121, 0xff8c2d21, 0xff8c2d21, 0xff842821, 0xff732421, 0xff68201b, + 0xff5d1c16, 0xff5d1c16, 0xff4a1810, 0xff31100b, 0xaa000000, 0x44000000, 0x11000000, 0x00000000, + 0x00000000, 0x55451f1b, 0xffce5d52, 0xffc5594a, 0xffc5594a, 0xffc5594a, 0xffc5594a, 0xffc5554a, + 0xffc5554a, 0xffc04c3f, 0xffc04c3f, 0xffc5453a, 0xffc5453a, 0xffba3e34, 0xffba3e34, 0xffad3529, + 0xffad3529, 0xff76271e, 0xff5a2019, 0xff5a2d3a, 0xffe6e7e6, 0xffe6e7e6, 0xff5a2d3a, 0xff4a1819, + 0xff652019, 0xff652019, 0xff732419, 0xff632019, 0xff632019, 0xff632019, 0xff632019, 0xff632019, + 0xff5d1e16, 0xff5d1e16, 0xff5d1e16, 0xff5a1c19, 0xff5a1c19, 0xff5a1c19, 0x88240908, 0x33000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee977f79, 0xeed6beb5, + 0xeed6beb5, 0xeec5b2b5, 0xeec3abaa, 0xeec0a59f, 0xeebd9e94, 0xeebd968c, 0xeeba8f86, 0xeeb88881, + 0xeeb5827b, 0xee9a6d65, 0xeece9e94, 0xeece9e94, 0xaa310c08, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00080000, 0x11080000, 0xcc6b231b, 0xff9c3529, 0xffa53529, 0xffa53529, + 0xffa53529, 0xffaa3729, 0xffaf392c, 0xffb2392f, 0xffb2392f, 0xffb2392f, 0xffb83a2c, 0xffba3b2f, + 0xffba3b2f, 0xffba3b2f, 0xffb83a31, 0xffb83a31, 0xffba3b31, 0xffba3b31, 0xffb53931, 0xffb53931, + 0xffc0706b, 0xffd6dfde, 0xffe6e3e6, 0xfff7f6f7, 0xffffffff, 0xffffffff, 0xfffffbff, 0xfffffbff, + 0xfffffbff, 0xffc87770, 0xffaf372c, 0xffaf372c, 0xffaf372c, 0xffad3529, 0xffa53529, 0xffa23329, + 0xffa23329, 0xff9c3129, 0xff943121, 0xff8c2d21, 0xff8c2d21, 0xff842821, 0xff732421, 0xff68201b, + 0xff5d1c16, 0xff5d1c16, 0xff4a1810, 0xee31100b, 0x99000000, 0x33000000, 0x00000000, 0x00000000, + 0x00000000, 0x22000000, 0xcc893e37, 0xffbd5042, 0xffbd5042, 0xffbd5042, 0xffbd5042, 0xffc04c3f, + 0xffc04c3f, 0xffba4234, 0xffba4234, 0xffba3e34, 0xffba3e34, 0xffaf372f, 0xffaf372f, 0xffad3529, + 0xff912e24, 0xff76271e, 0xff5a2019, 0xff5a2d3a, 0xffe6e7e6, 0xffe6e7e6, 0xff5a2d3a, 0xff4a1819, + 0xff581c19, 0xff652019, 0xff652019, 0xff632019, 0xff632019, 0xff5a1e16, 0xff5a1e16, 0xff581b13, + 0xff581b13, 0xff581b13, 0xff581b13, 0xff5a1c19, 0xff5a1c19, 0xdd3f1310, 0x77080000, 0x44000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x99190000, 0xee977f79, 0xeed6beb5, + 0xeed6beb5, 0xeec3abaa, 0xeec3abaa, 0xeec0a59f, 0xeebd9e94, 0xeebd968c, 0xeeba8f86, 0xeeb88881, + 0xeeb5827b, 0xee9a6d65, 0xeece9e94, 0xeece9e94, 0xaa310c08, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00080000, 0x00080000, 0x993a120e, 0xff9c3529, 0xffa53529, 0xffa53529, + 0xffa53529, 0xffa73629, 0xffaf392c, 0xffaf392c, 0xffb2392f, 0xffb2392f, 0xffb83a2c, 0xffba3b2f, + 0xffb83a2c, 0xffba3b2f, 0xffb83a31, 0xffba3b31, 0xffb83a31, 0xffba3b31, 0xffb53931, 0xffb53931, + 0xffb53931, 0xffcba7a5, 0xffe6e3e6, 0xfff7f6f7, 0xffffffff, 0xffffffff, 0xfffffbff, 0xfffffbff, + 0xffe4b9b8, 0xffad3529, 0xffaf372c, 0xffaf372c, 0xffad3529, 0xffad3529, 0xffa53529, 0xffa23329, + 0xff9f3229, 0xff9c3129, 0xff8c2d21, 0xff8c2d21, 0xff842821, 0xff7b2421, 0xff732421, 0xff68201b, + 0xff5d1c16, 0xff521810, 0xff4a1810, 0xdd190805, 0x77000000, 0x22000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x99451f1b, 0xffbd5042, 0xffb5463a, 0xffb5463a, 0xffb5463a, 0xffba4234, + 0xffba4234, 0xffb53929, 0xffb53929, 0xffaf372f, 0xffaf372f, 0xffaf372f, 0xffaf372f, 0xffad3529, + 0xff912e24, 0xff76271e, 0xff5a2019, 0xff5a2d3a, 0xffe6e7e6, 0xffe6e7e6, 0xff5a2d3a, 0xff4a1819, + 0xff4a1819, 0xff581c19, 0xff652019, 0xff5a1e16, 0xff5a1e16, 0xff521b13, 0xff521b13, 0xff581b13, + 0xff581b13, 0xff581b13, 0xff581b13, 0xff5a1c19, 0xff5a1c19, 0xcc240908, 0x77080000, 0x33000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x33000000, 0x88290400, 0xee977873, 0xeeceb2ad, + 0xeeceb2ad, 0xeec5aead, 0xeec3a6a2, 0xeec09e97, 0xeec09e97, 0xeebd928c, 0xeeba8b84, 0xeeb8847b, + 0xeeb8847b, 0xeeb58a84, 0xeeb58a84, 0xeeb58a84, 0xaa210400, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00080000, 0x00080000, 0x66080000, 0xff9c3529, 0xffa53529, 0xffa53529, + 0xffa53529, 0xffa53529, 0xffaf392c, 0xffaf392c, 0xffaf392c, 0xffb2392f, 0xffb83a2c, 0xffb83a2c, + 0xffb83a2c, 0xffb83a2c, 0xffb53931, 0xffb83a31, 0xffb83a31, 0xffb53931, 0xffb53931, 0xffb53931, + 0xffb53931, 0xffc0706b, 0xffe6e3e6, 0xffffffff, 0xffffffff, 0xffffffff, 0xfffffbff, 0xfffffbff, + 0xffc87770, 0xffad3529, 0xffaf372c, 0xffaf372c, 0xffad3529, 0xffad3529, 0xffa53529, 0xffa23329, + 0xff9c3129, 0xff9c3129, 0xff8c2d21, 0xff8c2d21, 0xff842821, 0xff7b2421, 0xff68201b, 0xff5d1c16, + 0xff521810, 0xff521810, 0xff31100b, 0xbb000000, 0x66000000, 0x22000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x44000000, 0xddad3d31, 0xffb5463a, 0xffad3d31, 0xffad3d31, 0xffb53929, + 0xffb53929, 0xffb53929, 0xffb53929, 0xffaf372f, 0xffaf372f, 0xffa53129, 0xffa53129, 0xff912e24, + 0xff912e24, 0xff5a2019, 0xff5a2019, 0xff5a2d3a, 0xffe6e7e6, 0xffe6e7e6, 0xff5a2d3a, 0xff4a1819, + 0xff4a1819, 0xff4a1819, 0xff581c19, 0xff521b13, 0xff521b13, 0xff521b13, 0xff4a1810, 0xff521810, + 0xff521810, 0xff521810, 0xff521810, 0xff5a1c19, 0xee3f1310, 0x99080000, 0x55080000, 0x22000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x88290400, 0xee977873, 0xeeceb2ad, + 0xeeceb2ad, 0xeec3a6a2, 0xeec3a6a2, 0xeec09e97, 0xeebd968c, 0xeebd928c, 0xeeba8b84, 0xeeb8847b, + 0xeeb8847b, 0xeeb58a84, 0xeeb58a84, 0xeeb58a84, 0x99210400, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x00000000, 0x22000000, 0xdd6b2019, 0xff9c3129, 0xff9c3129, + 0xff9c3129, 0xff9c3129, 0xffa23329, 0xffa73629, 0xffa73629, 0xffa73629, 0xffb53929, 0xffb53929, + 0xffb53929, 0xffb53929, 0xffaf3729, 0xffb53929, 0xffaf3729, 0xffb53929, 0xffaf3729, 0xffb53929, + 0xffaf3729, 0xffaf3729, 0xffdbb9b5, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfffff7f7, 0xffe1b7b2, + 0xffa53929, 0xffa53929, 0xffa53529, 0xffa53529, 0xffa53529, 0xffa53529, 0xff9c3129, 0xff9c3129, + 0xff9c3129, 0xff942e26, 0xff8c2d21, 0xff8c2d21, 0xff7e271e, 0xff70221b, 0xff632019, 0xff632019, + 0xff471710, 0xff471710, 0xee290c08, 0xaa000000, 0x44000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x99451710, 0xffbd3d31, 0xffbd3d31, 0xffbd3d31, 0xffad3929, + 0xffad3929, 0xffa73629, 0xffa73629, 0xffa53529, 0xffa53529, 0xff9a3126, 0xff9a3126, 0xff842d29, + 0xff762824, 0xff5a2019, 0xff5a2019, 0xff6b495a, 0xffd6cad6, 0xffd6cad6, 0xff6b495a, 0xff4d1c1e, + 0xff4a1410, 0xff4d1c1e, 0xff4d1c1e, 0xff4a1810, 0xff4a1810, 0xff4a1810, 0xff4a1810, 0xff4a1810, + 0xff4a1810, 0xff4a1810, 0xff4a1810, 0xff4a1810, 0xcc190805, 0x77000000, 0x44000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x88290400, 0xee603e3a, 0xeeceb2ad, + 0xeeceb2ad, 0xeec3a6a2, 0xeec09e97, 0xeec09e97, 0xeebd968c, 0xeebd928c, 0xeeba8b84, 0xeeb8847b, + 0xeeb57d73, 0xeeb58a84, 0xeeb58a84, 0xeeb58a84, 0x99210400, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x77240b08, 0xff9c3129, 0xff9c3129, + 0xff9c3129, 0xff9c3129, 0xffa23329, 0xffa23329, 0xffa73629, 0xffa73629, 0xffb53929, 0xffad3629, + 0xffad3629, 0xffad3629, 0xffaf3729, 0xffaf3729, 0xffaf3729, 0xffaf3729, 0xffaf3729, 0xffaf3729, + 0xffaf3729, 0xffaf3729, 0xffa53d31, 0xfff7f7f7, 0xfff7f7f7, 0xfff7f7f7, 0xfffff7f7, 0xffa53929, + 0xffa53929, 0xffa53929, 0xffa53529, 0xffa53529, 0xff9f3329, 0xff9f3329, 0xff9c3129, 0xff9c3129, + 0xff942e26, 0xff942e26, 0xff8c2d21, 0xff8c2d21, 0xff7e271e, 0xff70221b, 0xff632019, 0xff471710, + 0xff471710, 0xff471710, 0xcc0e0403, 0x88000000, 0x33000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x44080400, 0xcc812a21, 0xffbd3d31, 0xffbd3d31, 0xffa73629, + 0xffa73629, 0xffa73629, 0xffa23329, 0xff9a3126, 0xff9a3126, 0xff9a3126, 0xff8f2d24, 0xff762824, + 0xff68241e, 0xff5a2019, 0xff5a2019, 0xff6b495a, 0xffd6cad6, 0xffd6cad6, 0xff6b495a, 0xff4d1c1e, + 0xff4a1410, 0xff4a1410, 0xff4d1c1e, 0xff4a1810, 0xff4a1810, 0xff471710, 0xff471710, 0xff4a1810, + 0xff4a1810, 0xff4a1810, 0xff4a1810, 0xee31100b, 0x99000000, 0x55000000, 0x33000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x77290400, 0xee603e3a, 0xeeceb2ad, + 0xeeceb2ad, 0xeec3a6a2, 0xeec09e97, 0xeebd968c, 0xeebd968c, 0xeeba8b84, 0xeeba8b84, 0xeeb8847b, + 0xeeb57d73, 0xeeb58a84, 0xeeb58a84, 0xeeb58a84, 0x99210400, 0x33000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x22000000, 0xcc6e221e, 0xff9c3129, + 0xff9c3129, 0xff9c3129, 0xff9c3129, 0xffa23329, 0xffa23329, 0xffa73629, 0xffad3629, 0xffad3629, + 0xffad3629, 0xffad3629, 0xffaf3729, 0xffaa3629, 0xffa53529, 0xffaa3629, 0xffa53529, 0xffaf3729, + 0xffaa3629, 0xffa53529, 0xffa53d31, 0xffc07b73, 0xfff7f7f7, 0xfff7f7f7, 0xffc3786e, 0xffa53929, + 0xffa53929, 0xffa53929, 0xff9f3329, 0xff9f3329, 0xff9f3329, 0xff9a3229, 0xff9c3129, 0xff942e26, + 0xff942e26, 0xff942e26, 0xff7e271e, 0xff7e271e, 0xff70221b, 0xff70221b, 0xff632019, 0xff471710, + 0xff471710, 0xee2c0d08, 0xaa000000, 0x55000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11080400, 0x77451710, 0xee812a21, 0xffbd3d31, 0xffa73629, + 0xffa23329, 0xffa23329, 0xffa23329, 0xff9a3126, 0xff9a3126, 0xff8f2d24, 0xff8f2d24, 0xff762824, + 0xff68241e, 0xff5a2019, 0xff68241e, 0xff6b495a, 0xffb29fad, 0xffb29fad, 0xff8f7484, 0xff50242c, + 0xff4a1410, 0xff4a1410, 0xff4a1410, 0xff471710, 0xff471710, 0xff451610, 0xff451610, 0xff4a1810, + 0xff4a1810, 0xff4a1810, 0xee3c130e, 0xbb190805, 0x66000000, 0x44000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe9dfdb, 0xfff7ffff, 0xffce9e94, + 0xffce9e94, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffd6a294, 0xffd6a294, + 0xffd39e91, 0xffce9e94, 0xffce9e94, 0xffce988c, 0xffce988c, 0xffc58e7b, 0xffc58e7b, 0xfff7ffff, + 0xffe6d9d3, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x77290400, 0xdd5d3731, 0xeec59e94, + 0xeec59e94, 0xeebd9e9c, 0xeebd9e9c, 0xeeba9794, 0xeeb8908c, 0xeeb58a84, 0xeeb2837b, 0xeeaf7c73, + 0xeeaf7c73, 0xee9c7168, 0xeed6a69c, 0xee9c7168, 0x88290800, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000400, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x66100408, 0xee6e221e, + 0xff9c3129, 0xff9c3129, 0xff9c3129, 0xff9c3129, 0xff9c3129, 0xffa23329, 0xffa53329, 0xffa53329, + 0xffa53329, 0xffa53329, 0xffa53529, 0xffa53529, 0xffa53529, 0xffa53529, 0xffa53529, 0xffa53529, + 0xffa53529, 0xffa53529, 0xffa53d31, 0xffa53d31, 0xfff7f7f7, 0xfff7f7f7, 0xffa53929, 0xffa53929, + 0xffa53929, 0xffa53929, 0xff9a3229, 0xff9a3229, 0xff943129, 0xff943129, 0xff942e26, 0xff942e26, + 0xff8c2b24, 0xff842821, 0xff7e271e, 0xff70221b, 0xff70221b, 0xff631c19, 0xff471710, 0xff471710, + 0xff471710, 0xdd100400, 0x88000000, 0x33000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11080400, 0x22080400, 0x99451710, 0xee812a21, 0xffa23329, + 0xffa23329, 0xff9c3129, 0xff9c3129, 0xff8f2d24, 0xff8f2d24, 0xff8f2d24, 0xff842821, 0xff68241e, + 0xff68241e, 0xff5a2019, 0xff842d29, 0xff8f7484, 0xffb29fad, 0xffb29fad, 0xff8f7484, 0xff522d3a, + 0xff4d1c1e, 0xff4a1410, 0xff4a1410, 0xff451610, 0xff451610, 0xff451610, 0xff451610, 0xff3c130e, + 0xff3c130e, 0xff3c130e, 0xcc210808, 0x77000000, 0x44000000, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe9dfdb, 0xffce9e94, 0xffce9e94, + 0xffce9e94, 0xffd39f91, 0xffd39f91, 0xffd39f91, 0xffd39f91, 0xffd39e91, 0xffd39e91, 0xffd39e91, + 0xffd39e91, 0xffce988c, 0xffce988c, 0xffce988c, 0xffce9384, 0xffc58e7b, 0xffc58e7b, 0xffc58e7b, + 0xffe6d9d3, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x66290400, 0xdd5d3731, 0xeec59e94, + 0xeec59e94, 0xeebd9e9c, 0xeeba9794, 0xeeb8908c, 0xeeb58a84, 0xeeb58a84, 0xeeb2837b, 0xeeaf7c73, + 0xeeaf7c73, 0xee9c7168, 0xeed6a69c, 0xee9c7168, 0x77290800, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0xaa2c0f0b, + 0xff842d21, 0xff842d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff9c3129, 0xff9c3129, + 0xff9c3129, 0xff9c3129, 0xff9a3126, 0xffa53529, 0xff9a3126, 0xff9a3126, 0xff9c3129, 0xff9c3129, + 0xff9c3129, 0xff9c3129, 0xff8c2d21, 0xff8c2d21, 0xffbd6d6b, 0xffbd6d6b, 0xff9c3129, 0xff9c3129, + 0xff9c3129, 0xff9c3129, 0xff9c3121, 0xff9c3121, 0xff912d21, 0xff9c3121, 0xff842d21, 0xff842d21, + 0xff76271e, 0xff76271e, 0xff732421, 0xff732421, 0xff5d1e19, 0xff5d1e19, 0xff421410, 0xff421410, + 0xee2c0d0b, 0xaa000000, 0x55000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x33000000, 0x994a1410, 0xee942d21, + 0xff942d21, 0xff942d21, 0xff942d21, 0xff8c2d21, 0xff8c2d21, 0xff812821, 0xff812821, 0xff632019, + 0xff632019, 0xff632019, 0xff633134, 0xff846573, 0xffa596a5, 0xffa596a5, 0xff846573, 0xff5a3d42, + 0xff4a2221, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xff421410, + 0xff421410, 0xcc160705, 0x77000000, 0x55000000, 0x33000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe9dfdb, 0xffce9e94, 0xffce9e94, + 0xffce9e94, 0xffd39f91, 0xffd09d8f, 0xffd09d8f, 0xffd09d8f, 0xffd09a8f, 0xffd09a8f, 0xffd09a8f, + 0xffd09a8f, 0xffce988c, 0xffce9384, 0xffce9384, 0xffce9384, 0xffc58e7b, 0xffc58e7b, 0xffc58e7b, + 0xffe6d9d3, 0xffadaaad, 0x00000000, 0x11000000, 0x22000000, 0x55290400, 0xcc290400, 0xeec59e94, + 0xeec59e94, 0xeeba9794, 0xeeb8908c, 0xeeb8908c, 0xeeb58a84, 0xeeb2837b, 0xeeaf7c73, 0xeeaf7c73, + 0xeead756b, 0xee9c7168, 0xeed6a69c, 0xdd633d34, 0x66290800, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x22000000, + 0xbb2c0f0b, 0xff842d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8f2d26, 0xff8f2d26, + 0xff8f2d26, 0xff9c3129, 0xff8f2d24, 0xff9a3126, 0xff9a3126, 0xff9a3126, 0xff942e26, 0xff9c3129, + 0xff942e26, 0xff9c3129, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff942e26, 0xff942e26, + 0xff942e26, 0xff942e26, 0xff9c3121, 0xff912d21, 0xff912d21, 0xff912d21, 0xff842d21, 0xff76271e, + 0xff76271e, 0xff76271e, 0xff732421, 0xff5d1e19, 0xff5d1e19, 0xff471710, 0xff421410, 0xee2c0d0b, + 0xbb000000, 0x77000000, 0x33000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x33000000, 0x99370f0b, + 0xee942d21, 0xff942d21, 0xff942d21, 0xff8c2d21, 0xff812821, 0xff812821, 0xff762421, 0xff632019, + 0xff632019, 0xff632019, 0xff633942, 0xff846573, 0xffa596a5, 0xffa596a5, 0xff846573, 0xff5a3d42, + 0xff4a2221, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xee421410, + 0xcc160705, 0x77000000, 0x55000000, 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe9dfdb, 0xffce9e94, 0xffce9e94, + 0xffce9e94, 0xffd09d8f, 0xffd09d8f, 0xffd09d8f, 0xffce9a8c, 0xffd09a8f, 0xffce968c, 0xffce968c, + 0xffce968c, 0xffce9384, 0xffce9384, 0xffce8e7b, 0xffce8e7b, 0xffc58e7b, 0xffc58e7b, 0xffc58e7b, + 0xffe6d9d3, 0xffadaaad, 0x00000000, 0x00000000, 0x22000000, 0x44290400, 0xbb290400, 0xee916b63, + 0xeec59e94, 0xeeb8908c, 0xeeb8908c, 0xeeb58a84, 0xeeb58a84, 0xeeb2837b, 0xeeaf7c73, 0xeead756b, + 0xeead756b, 0xee9c7168, 0xeed6a69c, 0xcc290800, 0x55290800, 0x22000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x33000000, 0xcc2c0f0b, 0xff76241b, 0xff76241b, 0xff76241b, 0xff76241b, 0xff812824, 0xff812824, + 0xff812824, 0xff812824, 0xff8f2d24, 0xff8f2d24, 0xff8f2d24, 0xff8f2d24, 0xff8c2b24, 0xff8c2b24, + 0xff8c2b24, 0xff8c2b24, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff942e26, 0xff942e26, + 0xff942e26, 0xff942e26, 0xff912d21, 0xff912d21, 0xff862821, 0xff862821, 0xff76271e, 0xff76271e, + 0xff68221b, 0xff68221b, 0xff5d1e19, 0xff5d1e19, 0xff471710, 0xff471710, 0xff2c0d0b, 0xcc000000, + 0x88000000, 0x44000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x33080000, + 0x88370f0b, 0xdd651e16, 0xff942d21, 0xff812821, 0xff812821, 0xff762421, 0xff762421, 0xff632019, + 0xff632019, 0xff632826, 0xff633942, 0xff846573, 0xff947d8c, 0xff947d8c, 0xff846573, 0xff5a3d42, + 0xff4a2221, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xff421410, 0xee2f0d0b, 0xbb160705, + 0x77000000, 0x55000000, 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000400, 0xff949694, 0xffe6e3e6, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffce9a8c, 0xffce9a8c, 0xffce9a8c, 0xffce9a8c, 0xffce9a8c, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffc58a7b, 0xffc58a7b, 0xffc58a7b, 0xffc58a7b, 0xffb57d73, 0xffb57d73, 0xffb57d73, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x11000000, 0x33190400, 0xaa190400, 0xee91584d, + 0xeece8273, 0xeeb5867b, 0xeeb5867b, 0xeeb5867b, 0xeeb5867b, 0xeead7973, 0xeead7973, 0xeeaa6d65, + 0xeeaa6d65, 0xeeaa7d73, 0xeeefbaad, 0xbb210400, 0x44210400, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x44000000, 0xcc4a1410, 0xff76241b, 0xff76241b, 0xff76241b, 0xff732421, 0xff732421, + 0xff732421, 0xff812824, 0xff842821, 0xff842821, 0xff842821, 0xff842821, 0xff842821, 0xff842821, + 0xff8c2b24, 0xff842821, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2d21, 0xff8c2b24, 0xff8c2b24, + 0xff8c2b24, 0xff842821, 0xff862821, 0xff862821, 0xff862821, 0xff7b2421, 0xff76271e, 0xff68221b, + 0xff68221b, 0xff5a1c19, 0xff5d1e19, 0xff471710, 0xff311008, 0xff311008, 0xdd160705, 0x99000000, + 0x55000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11080000, + 0x33080000, 0x55080000, 0xaa370f0b, 0xee6b2021, 0xff812821, 0xff762421, 0xff762421, 0xff632019, + 0xff632019, 0xff632019, 0xff633134, 0xff734d5a, 0xff846573, 0xff846573, 0xff734d5a, 0xff522f31, + 0xff4a2221, 0xff421410, 0xff421410, 0xff421410, 0xee2f0d0b, 0xcc1b0705, 0x99080000, 0x66000000, + 0x44000000, 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffce9a8c, 0xffefdbd3, 0xfffffbf7, 0xfffffbf7, 0xffefddd9, 0xffefddd9, 0xffefddd9, + 0xffefddd9, 0xfffffbf7, 0xfffffbf7, 0xffecd5ce, 0xffc58a7b, 0xffb57d73, 0xffb57d73, 0xffb57d73, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x11000000, 0x22190400, 0x77190400, 0xdd552e26, + 0xeece8273, 0xeeaf7165, 0xeeaf7165, 0xeeb5867b, 0xeeaf7165, 0xeead7973, 0xeeaa6d65, 0xeeaa6d65, + 0xeeaa6d65, 0xeeaa7d73, 0xeeaa7d73, 0x88210400, 0x22210400, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x33000000, 0x99210b08, 0xee421610, 0xff632019, 0xff632019, 0xff632019, + 0xff632019, 0xff632019, 0xff732419, 0xff732419, 0xff732419, 0xff732419, 0xff6b221b, 0xff7b2821, + 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff7b2821, 0xff7b2821, + 0xff7b2821, 0xff7b2821, 0xff7b2421, 0xff7b2421, 0xff7b2421, 0xff7b2421, 0xff6b2019, 0xff6b2019, + 0xff6b2019, 0xff4a1610, 0xff421410, 0xff421410, 0xee2c0d0b, 0xcc000000, 0x99000000, 0x55000000, + 0x22000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x22000000, 0x44000000, 0x771e0908, 0xbb3c1310, 0xdd5a1c19, 0xff5a1c19, 0xff55221b, + 0xff55221b, 0xff55221b, 0xff7b3129, 0xff58373c, 0xff7b4d52, 0xff7b4d52, 0xff58373c, 0xff5a2d29, + 0xff3f1f1b, 0xff24120e, 0xee24120e, 0xcc210808, 0x990b0303, 0x77000000, 0x55000000, 0x44000000, + 0x22000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffce9a8c, 0xffefdbd3, 0xfffffbf7, 0xfffffbf7, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xfffffbf7, 0xfffffbf7, 0xffd9afa5, 0xffc58a7b, 0xffb57d73, 0xffb57d73, 0xffb57d73, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x11000000, 0x22190400, 0x44190400, 0xbb190400, + 0xee91584d, 0xeeaa5d50, 0xeeaf7165, 0xeeaf7165, 0xeeaf7165, 0xeeaa6d65, 0xeea76158, 0xeea76158, + 0xeeaa6d65, 0xeeaa7d73, 0xcc210400, 0x55210400, 0x22210400, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x11000000, 0x22000000, 0x66000000, 0xcc210b08, 0xff451610, 0xff632019, + 0xff451610, 0xff632019, 0xff5d1c13, 0xff5d1c13, 0xff5d1c13, 0xff5d1c13, 0xff6b221b, 0xff6b221b, + 0xff6b221b, 0xff6b221b, 0xff6e231b, 0xff6e231b, 0xff6e231b, 0xff6e231b, 0xff6e231b, 0xff6e231b, + 0xff6e231b, 0xff6e231b, 0xff651e1b, 0xff7b2421, 0xff651e1b, 0xff651e1b, 0xff6b2019, 0xff4a1610, + 0xff4a1610, 0xff4a1610, 0xff2c0d0b, 0xee160705, 0xbb000000, 0x88000000, 0x55000000, 0x22000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x11000000, 0x33000000, 0x44000000, 0x66000000, 0x991e0908, 0xbb2f130e, + 0xdd2f130e, 0xee55221b, 0xff55221b, 0xff58373c, 0xff58373c, 0xff58373c, 0xee342226, 0xdd3f1f1b, + 0xcc24120e, 0xaa080400, 0x88080400, 0x77000000, 0x55000000, 0x44000000, 0x33000000, 0x11000000, + 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffce9a8c, 0xffce9a8c, + 0xffce9a8c, 0xffce9a8c, 0xffce9a8c, 0xfffffbf7, 0xfffffbf7, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xfffffbf7, 0xffecd5ce, 0xffc58a7b, 0xffc58a7b, 0xffb57d73, 0xffb57d73, 0xffb57d73, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x11190400, 0x22190400, 0x77190400, + 0xcc190400, 0xeea5493a, 0xeeaa5d50, 0xeeaa5d50, 0xeeaa5d50, 0xeea76158, 0xeea76158, 0xeea76158, + 0xeea5554a, 0xcc210400, 0x77210400, 0x22210400, 0x11210400, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x44000000, 0x88080000, 0xdd260b08, + 0xee451610, 0xff451610, 0xff47140e, 0xff5d1c13, 0xff5d1c13, 0xff5d1c13, 0xff5a1b16, 0xff5a1b16, + 0xff5a1b16, 0xff5a1b16, 0xff601e16, 0xff601e16, 0xff6e231b, 0xff601e16, 0xff601e16, 0xff601e16, + 0xff601e16, 0xff601e16, 0xff651e1b, 0xff651e1b, 0xff501716, 0xff501716, 0xff4a1610, 0xff4a1610, + 0xff290b08, 0xee290b08, 0xdd000000, 0xaa000000, 0x77000000, 0x44000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x22000000, 0x33000000, 0x55080400, + 0x66080400, 0x77080400, 0x88080400, 0x88100c10, 0x99100c10, 0x99100c10, 0x88100c10, 0x8824120e, + 0x77080400, 0x66080400, 0x55080400, 0x44000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffce9284, 0xffce9284, + 0xffce9284, 0xffc58e7b, 0xffc58e7b, 0xffd9b3a7, 0xffffffff, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffffffff, 0xffcea9a2, 0xffb57d73, 0xffb57d73, 0xffad756b, 0xffad756b, 0xffad756b, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x22000000, + 0x66000000, 0x99210400, 0xaa420800, 0xbb420800, 0xbb630c00, 0xcc520c00, 0xbb520c00, 0xbb370800, + 0x991b0400, 0x66000000, 0x33000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x22080000, 0x44080000, + 0x77080000, 0xbb080000, 0xee310c08, 0xff47140e, 0xff47140e, 0xff47140e, 0xff4a1410, 0xff4a1410, + 0xff5a1b16, 0xff5a1b16, 0xff521810, 0xff521810, 0xff521810, 0xff521810, 0xff521810, 0xff521810, + 0xff521810, 0xff521810, 0xff501716, 0xff501716, 0xff501716, 0xff3a1010, 0xff290b08, 0xee290b08, + 0xcc080000, 0xaa080000, 0x88000000, 0x55000000, 0x33000000, 0x11000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x22080400, + 0x33080400, 0x33080400, 0x44080400, 0x44100c10, 0x55100c10, 0x55100c10, 0x44100c10, 0x44080400, + 0x33080400, 0x33080400, 0x22080400, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffce9284, 0xffce9284, + 0xffce9284, 0xffc58e7b, 0xffc58e7b, 0xffc58e7b, 0xffecd9d3, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffe6d4d0, 0xffb57d73, 0xffb57d73, 0xffb57d73, 0xffad756b, 0xffad756b, 0xffad756b, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, + 0x22000000, 0x22000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, 0x33000000, + 0x22000000, 0x22000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, + 0x22000000, 0x44000000, 0x66000000, 0x99000000, 0xbb080303, 0xdd190808, 0xee260b0b, 0xff3a1010, + 0xff3a1010, 0xff3a1010, 0xff3a1410, 0xff3a1410, 0xff3a1410, 0xff3a1410, 0xff4a1410, 0xff4a1410, + 0xff4a1410, 0xff4a1410, 0xff311010, 0xee210b0b, 0xdd100505, 0xcc100505, 0xbb000000, 0x99000000, + 0x77000000, 0x55000000, 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffce9284, 0xffce9284, + 0xffce9284, 0xffc58e7b, 0xffc58e7b, 0xffc58e7b, 0xffd9b3a7, 0xffffffff, 0xffffffff, 0xffffffff, + 0xffffffff, 0xffcea9a2, 0xffb57d73, 0xffb57d73, 0xffb57d73, 0xffad756b, 0xffad756b, 0xffad756b, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x11000000, 0x33000000, 0x44000000, 0x55000000, 0x77000000, 0x88000000, + 0xaa000000, 0xbb000000, 0xcc130705, 0xcc130705, 0xcc130705, 0xdd130705, 0xcc190705, 0xcc190705, + 0xcc000000, 0xbb000000, 0xbb000000, 0x99000000, 0x88000000, 0x66000000, 0x55000000, 0x44000000, + 0x33000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffce9284, 0xffce9284, + 0xffce9284, 0xffc58e7b, 0xffc58e7b, 0xffc58e7b, 0xffc58e7b, 0xffe9d7d3, 0xffffffff, 0xffffffff, + 0xffdec2bd, 0xffb57d73, 0xffb57d73, 0xffb57d73, 0xffb57d73, 0xffad756b, 0xffad756b, 0xffad756b, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x11000000, 0x11000000, 0x22000000, 0x22000000, + 0x33000000, 0x44000000, 0x55000000, 0x55000000, 0x55000000, 0x66000000, 0x66000000, 0x66000000, + 0x55000000, 0x55000000, 0x44000000, 0x44000000, 0x33000000, 0x22000000, 0x11000000, 0x11000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffc5867b, 0xffc5867b, + 0xffc5867b, 0xffc58a7b, 0xffbd8376, 0xffbd8376, 0xffbd8376, 0xffc59b8f, 0xfff7e7e6, 0xfff7e7e6, + 0xffc59b8f, 0xffb5796b, 0xffb5796b, 0xffad7568, 0xffad7568, 0xffa56d63, 0xffa56d63, 0xffa56d63, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x11000000, + 0x11000000, 0x11000000, 0x11000000, 0x11000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffc5867b, 0xffc5867b, + 0xffc5867b, 0xffbd8376, 0xffbd8376, 0xffb57c70, 0xffb57c70, 0xffad7563, 0xffdec1ba, 0xffdec1ba, + 0xffad7563, 0xffad7568, 0xffad7568, 0xffa57165, 0xffa57165, 0xffa56d63, 0xffa56d63, 0xffa56d63, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffc5867b, 0xffc5867b, + 0xffc5867b, 0xffbd8376, 0xffb57c70, 0xffb57c70, 0xffb57c70, 0xffad7563, 0xffad7563, 0xffad7563, + 0xffad7563, 0xffa57165, 0xffa57165, 0xffa57165, 0xff9c6d63, 0xffa56d63, 0xffa56d63, 0xffa56d63, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff949694, 0xffe6e3e6, 0xffc5867b, 0xffc5867b, + 0xffc5867b, 0xffb57c70, 0xffb57c70, 0xffad756b, 0xffad756b, 0xffad7563, 0xffad7563, 0xffad7563, + 0xffad7563, 0xff9c6d63, 0xff9c6d63, 0xff9c6d63, 0xff9c6d63, 0xffa56d63, 0xffa56d63, 0xffa56d63, + 0xffe6e3e6, 0xffadaaad, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff8f8f8f, 0xffded4d0, 0xffad7d73, 0xffad7d73, + 0xffad7d73, 0xffa57163, 0xffa57163, 0xffa57163, 0xffa57163, 0xff9c695a, 0xff9c695a, 0xff9c695a, + 0xff9c695a, 0xff94655a, 0xff94655a, 0xff94655a, 0xff94655a, 0xff946d63, 0xff946d63, 0xff946d63, + 0xffdbcecb, 0xffa5a6a5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff8f8f8f, 0xffded4d0, 0xfff7ffff, 0xffad7d73, + 0xffad7d73, 0xffa57163, 0xffa57163, 0xffa57163, 0xffa57163, 0xff9c695a, 0xff9c695a, 0xff9c695a, + 0xff9c695a, 0xff94655a, 0xff94655a, 0xff94655a, 0xff94655a, 0xff946d63, 0xff946d63, 0xffffffff, + 0xffdbcecb, 0xffa5a6a5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff8f8f8f, 0xffded4d0, 0xffded4d0, 0xffded4d0, + 0xffded4d0, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, + 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffd6dbde, 0xffdbcecb, 0xffdbcecb, 0xffdbcecb, + 0xffdbcecb, 0xffa5a6a5, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0xff8f8f8f, 0xffc5a9a2, 0xffc5a9a2, 0xffc5a9a2, + 0xffc5a9a2, 0xffc5b7b5, 0xffc5b7b5, 0xffc5b7b5, 0xffc5b7b5, 0xffc3b5b2, 0xffc3b5b2, 0xffc3b5b2, + 0xffc3b5b2, 0xffc0b3b2, 0xffc0b3b2, 0xffc0b3b2, 0xffc0b3b2, 0xffb89e97, 0xffb89e97, 0xffb89e97, + 0xffb89e97, 0xff6e6f6e, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, + 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000, 0x00000000 +}; + +static const UINT g_DXUTGUITextureSrcDataSizeInBytes = 262272; + +static const DWORD g_DXUTArrowMeshSrcData[] = +{ + 0x20666f78, 0x33303330, 0x70697a62, 0x32333030, 0x000030d7, 0x087930c7, 0x59ed4b43, 0xd51c6c5d, + 0x71dbbe15, 0xacbbc1d6, 0xe125d493, 0xc1024e27, 0x7133f9c1, 0xec1098ec, 0x1b1daef1, 0xc6d24eb7, + 0xc713fa10, 0x64866f59, 0xd9aecd95, 0x694304dd, 0x4485686b, 0xad2fb6a5, 0x78df44a8, 0x6cca8828, + 0x20a2895a, 0x2aaf60ef, 0x905215b5, 0x4fa9515a, 0xa45b4d45, 0xa1e09548, 0x9e94d282, 0xcf5df333, + 0x8a3acdf1, 0xec0c5368, 0xbefec6ac, 0xf77ee733, 0xdef73bdc, 0x9d667739, 0x4a65a90a, 0xf27c81a9, + 0x7040d394, 0xba2785e0, 0x7e7e38ff, 0xd5bb0be5, 0xba1f17fa, 0x56a633b0, 0x1546bf79, 0x1d7cec51, + 0x164bef39, 0x8ec9e9f3, 0xb02e0ec9, 0x1fe77ed7, 0xbf399e4f, 0x550707f2, 0x1fceceef, 0x36a1db3e, + 0xdc985b93, 0x316e794e, 0xc415a965, 0x2413551a, 0xf77d749a, 0xc2d993e5, 0x29fcb983, 0xe2d5905f, + 0x61519a86, 0x7a942488, 0x36fb0b90, 0x1df5c9ad, 0x5cc55272, 0x188e559e, 0x4288e08d, 0x1aee41e4, + 0x47c0123e, 0xae72c8b5, 0x189c29ca, 0xbebca648, 0x5a643318, 0xf91567c9, 0x90e1d964, 0x933a2f93, + 0xe963d943, 0x52685394, 0xaeaf8a1d, 0x8bcce8e4, 0x058b45b1, 0xaa87527d, 0x2afedab9, 0x642f72d5, + 0x4daeacb9, 0xfc8fd936, 0x4cc6ae0c, 0x15a5ae77, 0x2018bc05, 0x8feb9b20, 0x2bdd0e02, 0x6172b81f, + 0x50440c73, 0xbadd3f70, 0x31c0a664, 0xadf719f7, 0xf859fa15, 0x3d721e5c, 0xc62ff55f, 0x701d670c, + 0x40b14754, 0x11d86164, 0x903fbd84, 0xbd058b32, 0x97d2ddcc, 0x07f2e4cb, 0x0e711307, 0x1ffd4ffb, + 0x09963e74, 0x6121e6c2, 0x39de5391, 0xee0f8fe6, 0xc779e395, 0x6f94fac9, 0xb4e678d3, 0x664c5c13, + 0xe5244e26, 0x2cfad200, 0xcdf678ff, 0x7e4e75df, 0x20317918, 0x9f274593, 0x6f58664e, 0x8c32319f, + 0x7b94f916, 0x550533c3, 0x761ee44c, 0x300c2e88, 0x5627aea4, 0xa7527098, 0x4a3cc933, 0x4e717354, + 0xf4850ba5, 0x8e6a2d19, 0x1fb81586, 0x74e1d03a, 0x26c1c8a1, 0x06890caa, 0xb1da35be, 0x9a65dc60, + 0x3064ce14, 0x859df497, 0xd5c55639, 0xfb0b9c1f, 0xd25ef2e9, 0x46f1ae81, 0xfebf4f1f, 0x749913d3, + 0xe74c592a, 0x1c8998b2, 0x6ffdd0f0, 0x3f9bfcbc, 0xa9e868fc, 0x3fcf23f3, 0xe7f1da57, 0x3f3c31f9, + 0xcf14f5c9, 0x8fa7c81e, 0x8cc9b3a7, 0x917c919c, 0x983a7507, 0x3fb4b2f5, 0xeb6ac50a, 0xca48c6f7, + 0x07633ac9, 0xb3ea3973, 0xf58d2d2b, 0x352b3f5e, 0x8ecbab65, 0x0119b7ab, 0xf3e78c30, 0xa6af87b9, + 0xfddef7ee, 0xe5551ece, 0xafc27690, 0x65c7aaa8, 0xfbe37375, 0x6f50c91e, 0x773bf939, 0x9bc6f87c, + 0xa35729f6, 0xaef0ae99, 0x256f73b6, 0x00957ff8, 0x7d46b8f8, 0x7e7fc53e, 0x5f343232, 0x75de5ead, + 0xc1ef61ad, 0xf59d3773, 0x3950da6a, 0x35c4aa5e, 0x8a503e1e, 0x3adebfd7, 0xb2c778cb, 0x7f9dfc62, + 0x97c3d8ff, 0x8ef74db6, 0x61ecbaff, 0xd5fa7db5, 0xb2fb7024, 0xd9f6ace2, 0xab34a077, 0xece692cb, + 0x9d93d74c, 0xfe5d9cd0, 0x4757ab7a, 0xe1efef9b, 0xbf4db7f7, 0x68719a4a, 0x498126f6, 0x7c36fe33, + 0x461e3348, 0x68ce20d9, 0x5a338825, 0x568ce209, 0x95a33882, 0x2568ce20, 0x095a3388, 0x82568ce2, + 0xc44d3d38, 0x7104ad19, 0x9c412b46, 0xf4e2269e, 0xa7a71134, 0x67c93889, 0x6bf4f0fe, 0xec3ffb7d, + 0x937ab0db, 0x4e8bbc62, 0x19fabd0b, 0x5b82433a, 0x075e69b0, 0x6132f9ac, 0x9b0c23e3, 0x69b0f5e6, + 0xcd361cbe, 0xf34d83af, 0x8f34d806, 0x1479a6c0, 0x87afcd36, 0x6c18f34d, 0x6360879a, 0x9fa74cde, + 0x1d7c06ca, 0x4af0166c, 0xcd87af83, 0xf0655e02, 0xc059b00d, 0xadf8359f, 0x4dc059b0, 0x360dbf06, + 0x0673f80b, 0x059b08df, 0x6fc1837c, 0x5e02cd87, 0xd816f06d, 0x0635e02c, 0x059b04df, 0xefc1a37c, + 0xbe02cd80, 0xb0ade0c9, 0x1b37c059, 0x166c337c, 0xdf062df0, 0xdc059b02, 0x7166f068, 0xb9d2d6bf, + 0x826dce95, 0x382ede33, 0x19c136e3, 0xe33829df, 0x6e33821d, 0x4ef19c17, 0x087719c1, 0x7053b8ce, + 0x6704bbc6, 0x977825dc, 0x816b5f98, 0x1bbe0b77, 0x9592aa6d, 0x5990fe2f, 0xd25cbcf0, 0xb7df7d78, + 0x9f46a7ec, 0xe17666e9, 0x7dced644, 0xf1995cfb, 0xf6eda1e0, 0x78f667b3, 0x2607facf, 0xf479ee9f, + 0xd5e045bb, 0x6fb686e5, 0xddffb878, 0x7a707746, 0x7f4fc3c4, 0xf4cdd47f, 0xa6930f2a, 0xd0339a4b, + 0x07b34974, 0xda692e9a, 0x26932cd0, 0xd21eeaf0, 0x9369a1b4, 0x9b4d0da6, 0x60448d34, 0x33cc45ca, + 0x6515c7c2, 0x8ae9a15d, 0x83115cba, 0x8b2b622b, 0x5b45bb98, 0x5b46d16c, 0x7d16ddb4, 0xb2be8b62, + 0x98f61f45, 0x5c652f31, 0x1ed4c87b, 0xcc87b532, 0x44c87852, 0x87eedd16, 0x084ce7bd, 0x87e93f65, + 0xdea666f9, 0xb3feed9b, 0x2da69e4b, 0x5f5e2238, 0x448df95e, 0xe783dd58, 0x2758b377, 0x87573af4, + 0xb58c2c35, 0xa4d6396a, 0x513dac06, 0x8c3131ac, 0x135815cd, 0x376e6156, 0x80de8e61, 0x7306b6b9, + 0xfd8c26e6, 0xffef705b, 0xf04675df, 0x0f57b05b, 0xb2a52f7b, 0x5179b5ce, 0xced6ede0, 0xe45895bd, + 0x7c35c54d, 0xeeaea051, 0xd7b8c145, 0x85a12ddf, 0x274a972a, 0x9ec71a13, 0xa10a254f, 0x1c69b7a2, + 0xb89c3b5d, 0xe1e8ba54, 0x24b5cfb3, 0xe3274e7e, 0x08ed917f, 0x413c635d, 0xf5065cbe, 0x4eb5a4bf, + 0xdab38a87, 0xe2e941fe, 0x49fc28ec, 0x742cee63, 0x7dee6348, 0x5cef93e8, 0xc692f516, 0xf57ecfdc, + 0x7db497d3, 0xcf10b492, 0xd17b3a9c, 0xf9d225c3, 0xff8c9d05, 0xc5acfa49, 0x36f924f8, 0xb7bc1952, + 0xc62d62e9, 0xf4e3f75f, 0xc5ece870, 0x93f861f8, 0x9d04a246, 0xbdf18a31, 0x1a4faf92, 0x57a81389, + 0x6fe7db1f, 0x862f0d6d, 0x36a9636b, 0x1c1bfe96, 0xead38f56, 0x9c13f474, 0x1c8a37a3, 0xba39195d, + 0x65727232, 0xc8cae0e4, 0x639195b9, 0x56a7232b, 0x8cad0e46, 0x3919599c, 0x740dceb2, 0xe46edc4e, + 0xd45f3ac0, 0x234eef39, 0xa3f9d607, 0x8c3b79ce, 0x93e7581c, 0x44ede73a, 0x2ef9206e, 0x66e02cd8, + 0x66c17783, 0xf833af01, 0xc059b05d, 0x1bbe0deb, 0x83780b36, 0xcd86efc1, 0xe0d5be02, 0x80b3607b, + 0x3df8336f, 0x1bc059b0, 0x9b0dde0d, 0xc1bb7c05, 0x80b3607b, 0xc36e0c5b, 0x326f0166, 0x166c2f78, + 0x8f061df0, 0xb70166c3, 0x9b013c1a, 0xe0d9bc05, 0xc059b07d, 0x0fde0c5b, 0xd5bc059b, 0xb3617be0, + 0x7c19b780, 0x0679ec40, 0x7c91c7b0, 0x0681ec50, 0xfc91e7b1, 0xba27b15e, 0xc9207b17, 0x691ec487, + 0xf25b6308, 0x79de3176, 0x3a79f4bf, 0xe33820bf, 0xef19c161, 0x7ef19c13, 0x101f19c1, 0x0517f19c, + 0xc125fc67, 0x9c141f19, 0x8ce088f1, 0xf19c13ef, 0x3e3382fd, 0x07e33824, 0x65fc6704, 0x457f19c1, + 0x155fc670, 0x04d7f19c, 0x70587c67, 0x3382a3c6, 0xe338223e, 0x1f19c131, 0x52719c15, 0x7cfa24f0, + 0xd59117d1, 0xfda5d892, 0xe02969e2, 0xb71fbffd, 0xdfebfe5f, 0xe5fede67, 0xbb807a5f, 0x46c64719, + 0x5f9b96ec, 0xf1dc61ec, 0xdafda744, 0xcc66c440, 0xae3399ff, 0xc7eceba3, 0x7971cb98, 0xc98d19e0, + 0xa87daca7, 0xd2cbabac, 0xd26b577f, 0x750eb775, 0xc7573951, 0x7c233c00, 0x2baca2ca, 0x97515d34, + 0x4570622b, 0xf16e1e6c, 0x5b457663, 0x5746d15c, 0x25d75db7, 0xa58f5337, 0xcb78798e, 0xe27adff0, + 0x6fb61ccf, 0x187a67cc, 0x5eedfe1f, 0x0ba97bfb, 0x9be57e1e, 0x193e6c1b, 0x31af8db3, 0xc32e5f66, + 0x5ec16b58, 0x2ff276d6, 0x70d27f6b, 0xdcd90eb5, 0x5f27d093, 0x1a4bd757, 0x84a72f7c, 0x59fdacbd, + 0x46bceb4b, 0x4577d0a7, 0xc788aebd, 0x22ba7115, 0xcbb4577e, 0x093dedd5, 0x8dfd8e7d, 0x3f7afc87, + 0x3ffe2f4e, 0x624b5c0a, 0x2d6c496b, 0xb125ad89, 0xd3f624b5, 0xe95ec49e, 0xd638c743, 0x829fa3a9, + 0x0fb51d0f, 0x9887fe31, 0xb4bfd863, 0x621f847f, 0xdec7c59a, 0xecc3e20d, 0x7511f146, 0xa9e0f893, + 0x156e5c3f, 0xc4db201f, 0x7b8fc5c7, 0xf7e2221b, 0x0000001f +}; + +static const UINT g_DXUTArrowMeshSrcDataSizeInBytes = 2193; + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT WINAPI DXUTCreateGUITextureFromInternalArray(ID3D11Device* pd3dDevice, ID3D11Texture2D** ppTexture) +{ + if ( !ppTexture ) + return E_INVALIDARG; + + ID3D11Resource *pRes = nullptr; + HRESULT hr = DirectX::CreateDDSTextureFromMemory( pd3dDevice, + reinterpret_cast(g_DXUTGUITextureSrcData), g_DXUTGUITextureSrcDataSizeInBytes, + &pRes, nullptr ); + if ( FAILED(hr) ) + return hr; + + DXUT_SetDebugName( pRes, "DXUT" ); + + hr = pRes->QueryInterface( __uuidof( ID3D11Texture2D ), (LPVOID*)ppTexture ); + SAFE_RELEASE( pRes ); + + return hr; +} diff --git a/src/DX11/framework/dxut/Optional/DXUTres.h b/src/DX11/framework/dxut/Optional/DXUTres.h new file mode 100644 index 0000000..5cfdc8e --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTres.h @@ -0,0 +1,13 @@ +//---------------------------------------------------------------------------- +// File: dxutres.h +// +// Functions to create DXUT media from arrays in memory +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//----------------------------------------------------------------------------- +#pragma once + +HRESULT WINAPI DXUTCreateGUITextureFromInternalArray( _In_ ID3D11Device* pd3dDevice, _Outptr_ ID3D11Texture2D** ppTexture ); diff --git a/src/DX11/framework/dxut/Optional/DXUTsettingsdlg.cpp b/src/DX11/framework/dxut/Optional/DXUTsettingsdlg.cpp new file mode 100644 index 0000000..a20658b --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTsettingsdlg.cpp @@ -0,0 +1,1590 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTSettingsDlg.cpp +// +// Dialog for selection of device settings +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "DXUT.h" +#include "DXUTgui.h" +#include "DXUTsettingsDlg.h" + +//-------------------------------------------------------------------------------------- +// Internal functions forward declarations +//-------------------------------------------------------------------------------------- +const WCHAR* DXUTPresentIntervalToString( _In_ UINT pi ); +const WCHAR* DXUTDeviceTypeToString( _In_ D3D_DRIVER_TYPE devType ); +const WCHAR* DXUTVertexProcessingTypeToString( _In_ DWORD vpt ); + + +HRESULT DXUTSnapDeviceSettingsToEnumDevice( DXUTDeviceSettings* pDeviceSettings, bool forceEnum, D3D_FEATURE_LEVEL forceFL = D3D_FEATURE_LEVEL(0) ); + +//-------------------------------------------------------------------------------------- +// Global state +//-------------------------------------------------------------------------------------- +DXUTDeviceSettings g_DeviceSettings; + +CD3DSettingsDlg* WINAPI DXUTGetD3DSettingsDialog() +{ + // Using an accessor function gives control of the construction order + static CD3DSettingsDlg dlg; + return &dlg; +} + + +//-------------------------------------------------------------------------------------- +CD3DSettingsDlg::CD3DSettingsDlg() noexcept : + m_pActiveDialog(nullptr), + m_Dialog{}, + m_nRevertModeTimeout(0), + m_nIDEvent(0), + m_bActive( false ), + m_Levels{} +{ + m_Levels[0] = D3D_FEATURE_LEVEL_9_1; + m_Levels[1] = D3D_FEATURE_LEVEL_9_2; + m_Levels[2] = D3D_FEATURE_LEVEL_9_3; + m_Levels[3] = D3D_FEATURE_LEVEL_10_0; + m_Levels[4] = D3D_FEATURE_LEVEL_10_1; + m_Levels[5] = D3D_FEATURE_LEVEL_11_0; + m_Levels[6] = D3D_FEATURE_LEVEL_11_1; +#if defined(USE_DIRECT3D11_3) || defined(USE_DIRECT3D11_4) + m_Levels[7] = D3D_FEATURE_LEVEL_12_0; + m_Levels[8] = D3D_FEATURE_LEVEL_12_1; +#else + m_Levels[7] = static_cast(0xc000); + m_Levels[8] = static_cast(0xc100); +#endif +} + + +//-------------------------------------------------------------------------------------- +CD3DSettingsDlg::~CD3DSettingsDlg() +{ + // Release the memory used to hold the D3D11 refresh data in the combo box + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_REFRESH_RATE ); + if( pComboBox ) + for( UINT i = 0; i < pComboBox->GetNumItems(); ++i ) + { + auto pRate = reinterpret_cast( pComboBox->GetItemData( i ) ); + delete pRate; + } +} + + +//-------------------------------------------------------------------------------------- +void CD3DSettingsDlg::Init( _In_ CDXUTDialogResourceManager* pManager ) +{ + assert( pManager ); + m_Dialog.Init( pManager, false ); // Don't register this dialog. + m_RevertModeDialog.Init( pManager, false ); // Don't register this dialog. + m_pActiveDialog = &m_Dialog; + CreateControls(); +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CD3DSettingsDlg::Init( CDXUTDialogResourceManager* pManager, LPCWSTR szControlTextureFileName ) +{ + assert( pManager ); + m_Dialog.Init( pManager, false, szControlTextureFileName ); // Don't register this dialog. + m_RevertModeDialog.Init( pManager, false, szControlTextureFileName ); // Don't register this dialog. + m_pActiveDialog = &m_Dialog; + CreateControls(); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CD3DSettingsDlg::Init( CDXUTDialogResourceManager* pManager, LPCWSTR pszControlTextureResourcename, + HMODULE hModule ) +{ + assert( pManager ); + m_Dialog.Init( pManager, false, pszControlTextureResourcename, hModule ); // Don't register this dialog. + m_RevertModeDialog.Init( pManager, false, pszControlTextureResourcename, hModule ); // Don't register this dialog + m_pActiveDialog = &m_Dialog; + CreateControls(); +} + + +//-------------------------------------------------------------------------------------- +void CD3DSettingsDlg::CreateControls() +{ + // Set up main settings dialog + m_Dialog.EnableKeyboardInput( true ); + m_Dialog.SetFont( 0, L"Arial", 15, FW_NORMAL ); + m_Dialog.SetFont( 1, L"Arial", 28, FW_BOLD ); + + // Right-justify static controls + auto pElement = m_Dialog.GetDefaultElement( DXUT_CONTROL_STATIC, 0 ); + if( pElement ) + { + pElement->dwTextFormat = DT_VCENTER | DT_RIGHT; + + // Title + CDXUTStatic* pStatic = nullptr; + m_Dialog.AddStatic( DXUTSETTINGSDLG_STATIC, L"Direct3D Settings", 10, 5, 400, 50, false, &pStatic ); + pElement = pStatic->GetElement( 0 ); + pElement->iFont = 1; + pElement->dwTextFormat = DT_TOP | DT_LEFT; + } + + //DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL + m_Dialog.AddStatic( DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL_LABEL, L"Feature Level", 10, 60, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL, 200, 60, 400, 23 ); + m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL )->SetDropHeight( 106 ); + + // DXUTSETTINGSDLG_ADAPTER + m_Dialog.AddStatic( DXUTSETTINGSDLG_STATIC, L"Display Adapter", 10, 85, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_ADAPTER, 200, 85, 400, 23 ); + + // DXUTSETTINGSDLG_DEVICE_TYPE + m_Dialog.AddStatic( DXUTSETTINGSDLG_STATIC, L"Render Device", 10, 110, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_DEVICE_TYPE, 200, 110, 400, 23 ); + + // DXUTSETTINGSDLG_WINDOWED, DXUTSETTINGSDLG_FULLSCREEN + m_Dialog.AddRadioButton( DXUTSETTINGSDLG_WINDOWED, DXUTSETTINGSDLG_WINDOWED_GROUP, L"Windowed", + 360, 157, 100, 16 ); + m_Dialog.AddRadioButton( DXUTSETTINGSDLG_FULLSCREEN, DXUTSETTINGSDLG_WINDOWED_GROUP, L"Full Screen", + 220, 157, 100, 16 ); + + // DXUTSETTINGSDLG_RES_SHOW_ALL + m_Dialog.AddCheckBox( DXUTSETTINGSDLG_RESOLUTION_SHOW_ALL, L"Show All Aspect Ratios", 420, 200, 200, 23, false ); + + // DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT + m_Dialog.AddStatic( DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT_LABEL, L"Adapter Output", 10, 175, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT, 200, 175, 400, 23 ); + + // DXUTSETTINGSDLG_D3D11_RESOLUTION + m_Dialog.AddStatic( DXUTSETTINGSDLG_D3D11_RESOLUTION_LABEL, L"Resolution", 10, 200, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_D3D11_RESOLUTION, 200, 200, 200, 23 ); + m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_RESOLUTION )->SetDropHeight( 106 ); + + // DXUTSETTINGSDLG_D3D11_REFRESH_RATE + m_Dialog.AddStatic( DXUTSETTINGSDLG_D3D11_REFRESH_RATE_LABEL, L"Refresh Rate", 10, 225, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_D3D11_REFRESH_RATE, 200, 225, 400, 23 ); + + // DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT + m_Dialog.AddStatic( DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT_LABEL, L"Back Buffer Format", 10, 260, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT, 200, 260, 400, 23 ); + + // DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT + m_Dialog.AddStatic( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT_LABEL, L"Multisample Count", 10, 285, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT, 200, 285, 400, 23 ); + + // DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY + m_Dialog.AddStatic( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY_LABEL, L"Multisample Quality", 10, 310, 180, 23 ); + m_Dialog.AddComboBox( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY, 200, 310, 400, 23 ); + + // DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL + m_Dialog.AddStatic( DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL_LABEL, L"Vertical Sync", 10, 335, 180, 23 ); + m_Dialog.AddComboBox(DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL, 200, 335, 400, 23); + + auto pPresentIntervalComboBox = m_Dialog.GetComboBox(DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL); + if (pPresentIntervalComboBox) + { + pPresentIntervalComboBox->AddItem(L"On", ULongToPtr(1)); + pPresentIntervalComboBox->AddItem(L"Off", ULongToPtr(0)); + } + + // DXUTSETTINGSDLG_D3D11_DEBUG_DEVICE + m_Dialog.AddCheckBox( DXUTSETTINGSDLG_D3D11_DEBUG_DEVICE, L"Create Debug Device", 200, 365, 180, 23 ); + + // DXUTSETTINGSDLG_OK, DXUTSETTINGSDLG_CANCEL + m_Dialog.AddButton( DXUTSETTINGSDLG_OK, L"OK", 230, 440, 73, 31 ); + m_Dialog.AddButton( DXUTSETTINGSDLG_CANCEL, L"Cancel", 315, 440, 73, 31, 0, true ); + + // Set up mode change dialog + m_RevertModeDialog.EnableKeyboardInput( true ); + m_RevertModeDialog.EnableNonUserEvents( true ); + m_RevertModeDialog.SetFont( 0, L"Arial", 15, FW_NORMAL ); + m_RevertModeDialog.SetFont( 1, L"Arial", 28, FW_BOLD ); + + pElement = m_RevertModeDialog.GetDefaultElement( DXUT_CONTROL_STATIC, 0 ); + if( pElement ) + { + pElement->dwTextFormat = DT_VCENTER | DT_RIGHT; + + // Title + CDXUTStatic* pStatic = nullptr; + if ( SUCCEEDED(m_RevertModeDialog.AddStatic( DXUTSETTINGSDLG_STATIC, L"Do you want to keep these display settings?", 10, 5, + 640, 50, false, &pStatic ) ) ) + pElement = pStatic->GetElement( 0 ); + pElement->iFont = 1; + pElement->dwTextFormat = DT_TOP | DT_LEFT; + + // Timeout static text control + if ( SUCCEEDED(m_RevertModeDialog.AddStatic( DXUTSETTINGSDLG_STATIC_MODE_CHANGE_TIMEOUT, L"", 10, 90, 640, 30, + false, &pStatic ) ) ) + pElement = pStatic->GetElement( 0 ); + pElement->iFont = 0; + pElement->dwTextFormat = DT_TOP | DT_LEFT; + } + + // DXUTSETTINGSDLG_MODE_CHANGE_ACCEPT, DXUTSETTINGSDLG_MODE_CHANGE_REVERT + m_RevertModeDialog.AddButton( DXUTSETTINGSDLG_MODE_CHANGE_ACCEPT, L"Yes", 230, 50, 73, 31 ); + m_RevertModeDialog.AddButton( DXUTSETTINGSDLG_MODE_CHANGE_REVERT, L"No", 315, 50, 73, 31, 0, true ); +} + + +//-------------------------------------------------------------------------------------- +// Changes the UI defaults to the current device settings +//-------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::Refresh() +{ + g_DeviceSettings = DXUTGetDeviceSettings(); + + auto pD3DEnum = DXUTGetD3D11Enumeration(); + + // Fill the UI with the current settings + AddD3D11DeviceType( g_DeviceSettings.d3d11.DriverType ); + + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_WINDOWED, true ); + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_FULLSCREEN, (g_DeviceSettings.d3d11.DriverType != D3D_DRIVER_TYPE_WARP) ); + + SetWindowed( FALSE != g_DeviceSettings.d3d11.sd.Windowed ); + auto pOutputInfo = GetCurrentD3D11OutputInfo(); + AddD3D11AdapterOutput( pOutputInfo->Desc.DeviceName, g_DeviceSettings.d3d11.Output ); + + AddD3D11Resolution( g_DeviceSettings.d3d11.sd.BufferDesc.Width, + g_DeviceSettings.d3d11.sd.BufferDesc.Height ); + AddD3D11RefreshRate( g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate ); + AddD3D11BackBufferFormat( g_DeviceSettings.d3d11.sd.BufferDesc.Format ); + AddD3D11MultisampleCount( g_DeviceSettings.d3d11.sd.SampleDesc.Count ); + AddD3D11MultisampleQuality( g_DeviceSettings.d3d11.sd.SampleDesc.Quality ); + + auto pBestDeviceSettingsCombo = pD3DEnum->GetDeviceSettingsCombo( + g_DeviceSettings.d3d11.AdapterOrdinal, g_DeviceSettings.d3d11.sd.BufferDesc.Format, + ( g_DeviceSettings.d3d11.sd.Windowed != 0 ) ); + + if( !pBestDeviceSettingsCombo ) + return DXUT_ERR_MSGBOX( L"GetDeviceSettingsCombo", E_INVALIDARG ); + + CDXUTComboBox *pFeatureLevelBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL ); + pFeatureLevelBox->RemoveAllItems(); + + D3D_FEATURE_LEVEL clampFL; + if ( g_DeviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_WARP ) + clampFL = DXUTGetD3D11Enumeration()->GetWARPFeaturevel(); + else if ( g_DeviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_REFERENCE ) + clampFL = DXUTGetD3D11Enumeration()->GetREFFeaturevel(); + else + clampFL = pBestDeviceSettingsCombo->pDeviceInfo->MaxLevel; + + for (int fli = 0; fli < TOTAL_FEATURE_LEVELS; fli++) + { + if (m_Levels[fli] >= g_DeviceSettings.MinimumFeatureLevel + && m_Levels[fli] <= clampFL) + { + AddD3D11FeatureLevel( m_Levels[fli] ); + } + } + pFeatureLevelBox->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.DeviceFeatureLevel ) ); + + // Get the adapters list from CD3D11Enumeration object + auto pAdapterInfoList = pD3DEnum->GetAdapterInfoList(); + + if( pAdapterInfoList->empty() ) + return DXUT_ERR_MSGBOX( L"CD3DSettingsDlg::OnCreatedDevice", DXUTERR_NOCOMPATIBLEDEVICES ); + + auto pAdapterCombo = m_Dialog.GetComboBox( DXUTSETTINGSDLG_ADAPTER ); + pAdapterCombo->RemoveAllItems(); + + // Add adapters + for( auto it = pAdapterInfoList->cbegin(); it != pAdapterInfoList->cend(); ++it ) + { + AddAdapter( (*it)->szUniqueDescription, (*it)->AdapterOrdinal ); + } + + pAdapterCombo->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.AdapterOrdinal ) ); + + // DXUTSETTINGSDLG_D3D11_RESOLUTION + HRESULT hr = UpdateD3D11Resolutions(); + if ( FAILED(hr) ) + return hr; + + // DXUTSETTINGSDLG_D3D11_REFRESH_RATE + hr = UpdateD3D11RefreshRates(); + if ( FAILED(hr) ) + return hr; + + // Windowed mode + bool bWindowed = IsWindowed(); + + // Backbuffer Format/Driver Type + auto pAdapterInfo = GetCurrentD3D11AdapterInfo(); + if (pAdapterInfo) + { + auto pBackBufferFormatComboBox = m_Dialog.GetComboBox(DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT); + pBackBufferFormatComboBox->RemoveAllItems(); + + for (size_t idc = 0; idc < pAdapterInfo->deviceSettingsComboList.size(); idc++) + { + auto pDeviceCombo = pAdapterInfo->deviceSettingsComboList[idc]; + if ((pDeviceCombo->Windowed == TRUE) == bWindowed) + { + AddD3D11BackBufferFormat(pDeviceCombo->BackBufferFormat); + } + } + + pBackBufferFormatComboBox->SetSelectedByData( ULongToPtr(g_DeviceSettings.d3d11.sd.BufferDesc.Format) ); + + auto pDeviceTypeComboBox = m_Dialog.GetComboBox(DXUTSETTINGSDLG_DEVICE_TYPE); + pDeviceTypeComboBox->RemoveAllItems(); + + for (size_t iDeviceInfo = 0; iDeviceInfo < pAdapterInfo->deviceInfoList.size(); iDeviceInfo++) + { + auto pDeviceInfo = pAdapterInfo->deviceInfoList[iDeviceInfo]; + AddD3D11DeviceType(pDeviceInfo->DeviceType); + } + + pDeviceTypeComboBox->SetSelectedByData( ULongToPtr(g_DeviceSettings.d3d11.DriverType) ); + } + + // MSAA settings + auto pDeviceSettingsCombo = GetCurrentD3D11DeviceSettingsCombo(); + if ( pDeviceSettingsCombo ) + { + auto pMultisampleCountCombo = m_Dialog.GetComboBox(DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT); + pMultisampleCountCombo->RemoveAllItems(); + + for (auto it = pDeviceSettingsCombo->multiSampleCountList.cbegin(); it != pDeviceSettingsCombo->multiSampleCountList.cend(); ++it) + AddD3D11MultisampleCount(*it); + + pMultisampleCountCombo->SetSelectedByData( ULongToPtr(g_DeviceSettings.d3d11.sd.SampleDesc.Count) ); + + UINT MaxQuality = 0; + for (size_t iCount = 0; iCount < pDeviceSettingsCombo->multiSampleCountList.size(); iCount++) + { + UINT Count = pDeviceSettingsCombo->multiSampleCountList[iCount]; + if ( Count == g_DeviceSettings.d3d11.sd.SampleDesc.Count ) + { + MaxQuality = pDeviceSettingsCombo->multiSampleQualityList[iCount]; + break; + } + } + + auto pMultisampleQualityCombo = m_Dialog.GetComboBox(DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY); + pMultisampleQualityCombo->RemoveAllItems(); + + for (UINT iQuality = 0; iQuality < MaxQuality; iQuality++) + { + AddD3D11MultisampleQuality(iQuality); + } + + pMultisampleQualityCombo->SetSelectedByData(ULongToPtr(g_DeviceSettings.d3d11.sd.SampleDesc.Quality)); + } + + // Misc settings + auto pDebugCheckBox = m_Dialog.GetCheckBox(DXUTSETTINGSDLG_D3D11_DEBUG_DEVICE); + if ( pDebugCheckBox ) + { + pDebugCheckBox->SetChecked(0 != (g_DeviceSettings.d3d11.CreateFlags & D3D11_CREATE_DEVICE_DEBUG)); + } + + auto pPresentIntervalComboBox = m_Dialog.GetComboBox(DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL); + if ( pPresentIntervalComboBox ) + { + pPresentIntervalComboBox->SetSelectedByData(ULongToPtr(g_DeviceSettings.d3d11.SyncInterval) ); + } + + CDXUTDialog::SetRefreshTime( ( float )DXUTGetTime() ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CD3DSettingsDlg::SetSelectedD3D11RefreshRate( _In_ DXGI_RATIONAL RefreshRate ) +{ + auto pRefreshRateComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_REFRESH_RATE ); + + for( UINT i = 0; i < pRefreshRateComboBox->GetNumItems(); ++i ) + { + auto pRate = reinterpret_cast( pRefreshRateComboBox->GetItemData( i ) ); + + if( pRate && pRate->Numerator == RefreshRate.Numerator && pRate->Denominator == RefreshRate.Denominator ) + { + pRefreshRateComboBox->SetSelectedByIndex( i ); + return; + } + } +} + +//-------------------------------------------------------------------------------------- +void CD3DSettingsDlg::OnRender( _In_ float fElapsedTime ) +{ + // Render the scene + m_pActiveDialog->OnRender( fElapsedTime ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +LRESULT CD3DSettingsDlg::MsgProc( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam ) +{ + m_pActiveDialog->MsgProc( hWnd, uMsg, wParam, lParam ); + if( uMsg == WM_KEYDOWN && wParam == VK_F2 ) + SetActive( false ); + return 0; +} + +//-------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnD3D11CreateDevice( _In_ ID3D11Device* pd3dDevice ) +{ + if( !pd3dDevice ) + return DXUT_ERR_MSGBOX( L"CD3DSettingsDlg::OnCreatedDevice", E_INVALIDARG ); + + // Create the fonts/textures + m_Dialog.SetCallback( StaticOnEvent, ( void* )this ); + m_RevertModeDialog.SetCallback( StaticOnEvent, ( void* )this ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CD3DSettingsDlg::OnD3D11ResizedSwapChain( ID3D11Device* pd3dDevice, const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ) +{ + UNREFERENCED_PARAMETER(pd3dDevice); + + m_Dialog.SetLocation( 0, 0 ); + m_Dialog.SetSize( pBackBufferSurfaceDesc->Width, pBackBufferSurfaceDesc->Height ); + m_Dialog.SetBackgroundColors( D3DCOLOR_ARGB( 255, 98, 138, 206 ), + D3DCOLOR_ARGB( 255, 54, 105, 192 ), + D3DCOLOR_ARGB( 255, 54, 105, 192 ), + D3DCOLOR_ARGB( 255, 10, 73, 179 ) ); + + m_RevertModeDialog.SetLocation( 0, 0 ); + m_RevertModeDialog.SetSize( pBackBufferSurfaceDesc->Width, pBackBufferSurfaceDesc->Height ); + m_RevertModeDialog.SetBackgroundColors( D3DCOLOR_ARGB( 255, 98, 138, 206 ), + D3DCOLOR_ARGB( 255, 54, 105, 192 ), + D3DCOLOR_ARGB( 255, 54, 105, 192 ), + D3DCOLOR_ARGB( 255, 10, 73, 179 ) ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CD3DSettingsDlg::OnD3D11DestroyDevice() +{ + + +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void WINAPI CD3DSettingsDlg::StaticOnEvent( UINT nEvent, int nControlID, + CDXUTControl* pControl, void* pUserData ) +{ + auto pD3DSettings = reinterpret_cast( pUserData ); + if( pD3DSettings ) + pD3DSettings->OnEvent( nEvent, nControlID, pControl ); +} + +//-------------------------------------------------------------------------------------- +// Name: CD3DSettingsDlg::StaticOnModeChangeTimer() +// Desc: Timer callback registered by a call to DXUTSetTimer. It is called each second +// until mode change timeout limit. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void WINAPI CD3DSettingsDlg::StaticOnModeChangeTimer( UINT nIDEvent, void* pUserContext ) +{ + UNREFERENCED_PARAMETER(nIDEvent); + + auto pD3DSettings = reinterpret_cast( pUserContext ); + assert( pD3DSettings ); + _Analysis_assume_( pD3DSettings ); + assert( pD3DSettings->m_pActiveDialog == &pD3DSettings->m_RevertModeDialog ); + assert( pD3DSettings->m_nIDEvent == nIDEvent ); + + if( 0 == --pD3DSettings->m_nRevertModeTimeout ) + { + auto pControl = pD3DSettings->m_RevertModeDialog.GetControl( DXUTSETTINGSDLG_MODE_CHANGE_REVERT ); + assert( pControl ); + _Analysis_assume_( pControl ); + pD3DSettings->m_RevertModeDialog.SendEvent( EVENT_BUTTON_CLICKED, false, pControl ); + } + pD3DSettings->UpdateModeChangeTimeoutText( pD3DSettings->m_nRevertModeTimeout ); +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CD3DSettingsDlg::OnEvent( UINT nEvent, int nControlID, CDXUTControl* pControl ) +{ + UNREFERENCED_PARAMETER(nEvent); + UNREFERENCED_PARAMETER(pControl); + + switch( nControlID ) + { + case DXUTSETTINGSDLG_ADAPTER: + OnAdapterChanged(); break; + case DXUTSETTINGSDLG_DEVICE_TYPE: + OnDeviceTypeChanged(); break; + case DXUTSETTINGSDLG_WINDOWED: + OnWindowedFullScreenChanged(); break; + case DXUTSETTINGSDLG_FULLSCREEN: + OnWindowedFullScreenChanged(); break; + case DXUTSETTINGSDLG_RESOLUTION_SHOW_ALL: + OnBackBufferFormatChanged(); break; + case DXUTSETTINGSDLG_D3D11_RESOLUTION: + OnD3D11ResolutionChanged(); break; + case DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL: + OnFeatureLevelChanged(); break; + case DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT: + OnAdapterOutputChanged(); break; + case DXUTSETTINGSDLG_D3D11_REFRESH_RATE: + OnRefreshRateChanged(); break; + case DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT: + OnBackBufferFormatChanged(); break; + case DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT: + OnMultisampleTypeChanged(); break; + case DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY: + OnMultisampleQualityChanged(); break; + case DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL: + OnPresentIntervalChanged(); break; + case DXUTSETTINGSDLG_D3D11_DEBUG_DEVICE: + OnDebugDeviceChanged(); break; + + case DXUTSETTINGSDLG_OK: + { + bool bFullScreenModeChange = false; + auto currentSettings = DXUTGetDeviceSettings(); + g_DeviceSettings.MinimumFeatureLevel = currentSettings.MinimumFeatureLevel; + if( g_DeviceSettings.d3d11.sd.Windowed ) + { + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate.Denominator = + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate.Numerator = 0; + + RECT rcClient; + if( DXUTIsWindowed() ) + GetClientRect( DXUTGetHWND(), &rcClient ); + else + rcClient = DXUTGetWindowClientRectAtModeChange(); + DWORD dwWindowWidth = rcClient.right - rcClient.left; + DWORD dwWindowHeight = rcClient.bottom - rcClient.top; + + g_DeviceSettings.d3d11.sd.BufferDesc.Width = dwWindowWidth; + g_DeviceSettings.d3d11.sd.BufferDesc.Height = dwWindowHeight; + } + else + { + // Check for fullscreen mode change + bFullScreenModeChange = g_DeviceSettings.d3d11.sd.BufferDesc.Width != + currentSettings.d3d11.sd.BufferDesc.Width || + g_DeviceSettings.d3d11.sd.BufferDesc.Height != currentSettings.d3d11.sd.BufferDesc.Height || + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate.Denominator != + currentSettings.d3d11.sd.BufferDesc.RefreshRate.Denominator || + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate.Numerator != + currentSettings.d3d11.sd.BufferDesc.RefreshRate.Numerator; + } + + if( bFullScreenModeChange ) + { + // set appropriate global device settings to that of the current device + // settings. These will get set to the user-defined settings once the + // user accepts the mode change + DXUTDeviceSettings tSettings = g_DeviceSettings; + g_DeviceSettings.d3d11.sd.BufferDesc.Width = + currentSettings.d3d11.sd.BufferDesc.Width; + g_DeviceSettings.d3d11.sd.BufferDesc.Height = + currentSettings.d3d11.sd.BufferDesc.Height; + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate.Denominator = + currentSettings.d3d11.sd.BufferDesc.RefreshRate.Denominator; + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate.Numerator = + currentSettings.d3d11.sd.BufferDesc.RefreshRate.Numerator; + g_DeviceSettings.d3d11.sd.Windowed = currentSettings.d3d11.sd.Windowed; + + // apply the user-defined settings + DXUTCreateDeviceFromSettings( &tSettings ); + // create the mode change timeout dialog + m_pActiveDialog = &m_RevertModeDialog; + m_nRevertModeTimeout = 15; + UpdateModeChangeTimeoutText( m_nRevertModeTimeout ); + // activate a timer for 1-second updates + DXUTSetTimer( StaticOnModeChangeTimer, 1.0f, &m_nIDEvent, ( void* )this ); + } + else + { + DXUTCreateDeviceFromSettings( &g_DeviceSettings ); + SetActive( false ); + } + break; + } + + case DXUTSETTINGSDLG_CANCEL: + { + SetActive( false ); + break; + } + + case DXUTSETTINGSDLG_MODE_CHANGE_ACCEPT: + { + DXUTKillTimer( m_nIDEvent ); + g_DeviceSettings = DXUTGetDeviceSettings(); + m_pActiveDialog = &m_Dialog; + SetActive( false ); + break; + } + + case DXUTSETTINGSDLG_MODE_CHANGE_REVERT: + { + DXUTKillTimer( m_nIDEvent ); + m_pActiveDialog = &m_Dialog; + m_nIDEvent = 0; + m_nRevertModeTimeout = 0; + DXUTCreateDeviceFromSettings( &g_DeviceSettings ); + Refresh(); + break; + } + } +} + + +//------------------------------------------------------------------------------------- +CD3D11EnumAdapterInfo* CD3DSettingsDlg::GetCurrentD3D11AdapterInfo() const +{ + auto pD3DEnum = DXUTGetD3D11Enumeration(); + return pD3DEnum->GetAdapterInfo( g_DeviceSettings.d3d11.AdapterOrdinal ); +} + + +//------------------------------------------------------------------------------------- +CD3D11EnumDeviceInfo* CD3DSettingsDlg::GetCurrentD3D11DeviceInfo() const +{ + auto pD3DEnum = DXUTGetD3D11Enumeration(); + return pD3DEnum->GetDeviceInfo( g_DeviceSettings.d3d11.AdapterOrdinal, + g_DeviceSettings.d3d11.DriverType ); +} + + +//------------------------------------------------------------------------------------- +CD3D11EnumOutputInfo* CD3DSettingsDlg::GetCurrentD3D11OutputInfo() const +{ + auto pD3DEnum = DXUTGetD3D11Enumeration(); + return pD3DEnum->GetOutputInfo( g_DeviceSettings.d3d11.AdapterOrdinal, + g_DeviceSettings.d3d11.Output ); +} + +//------------------------------------------------------------------------------------- +CD3D11EnumDeviceSettingsCombo* CD3DSettingsDlg::GetCurrentD3D11DeviceSettingsCombo() const +{ + auto pD3DEnum = DXUTGetD3D11Enumeration(); + return pD3DEnum->GetDeviceSettingsCombo( g_DeviceSettings.d3d11.AdapterOrdinal, + g_DeviceSettings.d3d11.sd.BufferDesc.Format, + ( g_DeviceSettings.d3d11.sd.Windowed == TRUE ) ); +} + +HRESULT CD3DSettingsDlg::OnD3D11ResolutionChanged () +{ + if ( g_DeviceSettings.d3d11.sd.Windowed ) + return S_OK; + + DWORD dwWidth, dwHeight; + GetSelectedD3D11Resolution( &dwWidth, &dwHeight ); + g_DeviceSettings.d3d11.sd.BufferDesc.Width = dwWidth; + g_DeviceSettings.d3d11.sd.BufferDesc.Height = dwHeight; + + // DXUTSETTINGSDLG_D3D11_REFRESH_RATE + HRESULT hr = UpdateD3D11RefreshRates(); + if ( FAILED(hr) ) + return hr; + + return S_OK; +} + +HRESULT CD3DSettingsDlg::OnFeatureLevelChanged () +{ + HRESULT hr = E_FAIL; + + if (g_DeviceSettings.d3d11.DeviceFeatureLevel == GetSelectedFeatureLevel()) return S_OK; + + // Obtain a set of valid D3D11 device settings. + UINT CreateFlags = g_DeviceSettings.d3d11.CreateFlags; + DXGI_FORMAT BackBufferFormat = g_DeviceSettings.d3d11.sd.BufferDesc.Format; + UINT Count = g_DeviceSettings.d3d11.sd.SampleDesc.Count; + UINT Quality = g_DeviceSettings.d3d11.sd.SampleDesc.Quality; + DXGI_RATIONAL RefreshRate = g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate; + ZeroMemory(&g_DeviceSettings, sizeof(g_DeviceSettings)); + + DXUTApplyDefaultDeviceSettings(&g_DeviceSettings); + g_DeviceSettings.d3d11.CreateFlags = CreateFlags; + hr = DXUTSnapDeviceSettingsToEnumDevice(&g_DeviceSettings, true, GetSelectedFeatureLevel()); + g_DeviceSettings.d3d11.sd.BufferDesc.Format = BackBufferFormat; + g_DeviceSettings.d3d11.sd.SampleDesc.Count = Count; + g_DeviceSettings.d3d11.sd.SampleDesc.Quality = Quality; + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate = RefreshRate; + + auto pD3DEnum = DXUTGetD3D11Enumeration(); + auto pAdapterInfoList = pD3DEnum->GetAdapterInfoList(); + + // DXUTSETTINGSDLG_ADAPTER + auto pAdapterComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_ADAPTER ); + pAdapterComboBox->RemoveAllItems(); + + for( auto it = pAdapterInfoList->cbegin(); it != pAdapterInfoList->cend(); ++it ) + { + AddAdapter( (*it)->szUniqueDescription, (*it)->AdapterOrdinal ); + } + + pAdapterComboBox->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.AdapterOrdinal ) ); + + // DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT + auto pBackBufferFormatComboBox = m_Dialog.GetComboBox(DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT); + pBackBufferFormatComboBox->RemoveAllItems(); + + auto pAdapterInfo = GetCurrentD3D11AdapterInfo(); + if (!pAdapterInfo) + return E_FAIL; + + bool bWindowed = IsWindowed(); + + for (size_t idc = 0; idc < pAdapterInfo->deviceSettingsComboList.size(); idc++) + { + auto pDeviceCombo = pAdapterInfo->deviceSettingsComboList[idc]; + if ((pDeviceCombo->Windowed == TRUE) == bWindowed) + { + AddD3D11BackBufferFormat(pDeviceCombo->BackBufferFormat); + } + } + + pBackBufferFormatComboBox->SetSelectedByData( ULongToPtr(g_DeviceSettings.d3d11.sd.BufferDesc.Format) ); + + hr = OnBackBufferFormatChanged(); + if (FAILED(hr)) + return hr; + + auto pCheckBox = m_Dialog.GetCheckBox( DXUTSETTINGSDLG_D3D11_DEBUG_DEVICE ); + pCheckBox->SetChecked( 0 != ( g_DeviceSettings.d3d11.CreateFlags & D3D11_CREATE_DEVICE_DEBUG ) ); + + hr = OnAdapterChanged(); + if( FAILED( hr ) ) + return hr; + + return hr; +} + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnAdapterChanged() +{ + // Store the adapter index + g_DeviceSettings.d3d11.AdapterOrdinal = GetSelectedAdapter(); + + // DXUTSETTINGSDLG_DEVICE_TYPE + auto pDeviceTypeComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_DEVICE_TYPE ); + pDeviceTypeComboBox->RemoveAllItems(); + + auto pAdapterInfo = GetCurrentD3D11AdapterInfo(); + if( !pAdapterInfo ) + return E_FAIL; + + for( size_t iDeviceInfo = 0; iDeviceInfo < pAdapterInfo->deviceInfoList.size(); iDeviceInfo++ ) + { + auto pDeviceInfo = pAdapterInfo->deviceInfoList[ iDeviceInfo ]; + AddD3D11DeviceType( pDeviceInfo->DeviceType ); + } + + pDeviceTypeComboBox->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.DriverType ) ); + + HRESULT hr = OnDeviceTypeChanged(); + if( FAILED( hr ) ) + return hr; + + return S_OK; +} + + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnDeviceTypeChanged() +{ + HRESULT hr = S_OK; + + g_DeviceSettings.d3d11.DriverType = GetSelectedD3D11DeviceType(); + + // DXUTSETTINGSDLG_WINDOWED, DXUTSETTINGSDLG_FULLSCREEN + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_WINDOWED, true ); + if (g_DeviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_WARP ) + { + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_FULLSCREEN, false ); + g_DeviceSettings.d3d11.sd.Windowed = TRUE; + } + else + { + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_FULLSCREEN, true ); + } + + SetWindowed( g_DeviceSettings.d3d11.sd.Windowed != 0 ); + + auto pBestDeviceSettingsCombo = DXUTGetD3D11Enumeration()->GetDeviceSettingsCombo( + g_DeviceSettings.d3d11.AdapterOrdinal, g_DeviceSettings.d3d11.sd.BufferDesc.Format, + ( g_DeviceSettings.d3d11.sd.Windowed != 0 ) ); + + if( !pBestDeviceSettingsCombo ) + return DXUT_ERR_MSGBOX( L"GetDeviceSettingsCombo", E_INVALIDARG ); + + D3D_FEATURE_LEVEL clampFL; + if ( g_DeviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_WARP ) + clampFL = DXUTGetD3D11Enumeration()->GetWARPFeaturevel(); + else if ( g_DeviceSettings.d3d11.DriverType == D3D_DRIVER_TYPE_REFERENCE ) + clampFL = DXUTGetD3D11Enumeration()->GetREFFeaturevel(); + else + clampFL = pBestDeviceSettingsCombo->pDeviceInfo->MaxLevel; + + if ( g_DeviceSettings.d3d11.DeviceFeatureLevel > clampFL + || clampFL > pBestDeviceSettingsCombo->pDeviceInfo->MaxLevel ) + { + g_DeviceSettings.d3d11.DeviceFeatureLevel = std::min( g_DeviceSettings.d3d11.DeviceFeatureLevel, + clampFL ); + + CDXUTComboBox *pFeatureLevelBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL ); + pFeatureLevelBox->RemoveAllItems(); + for (int fli = 0; fli < TOTAL_FEATURE_LEVELS; fli++) + { + if (m_Levels[fli] >= g_DeviceSettings.MinimumFeatureLevel + && m_Levels[fli] <= clampFL) + { + AddD3D11FeatureLevel( m_Levels[fli] ); + } + } + pFeatureLevelBox->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.DeviceFeatureLevel ) ); + + hr = OnFeatureLevelChanged(); + if( FAILED( hr ) ) + return hr; + } + + hr = OnWindowedFullScreenChanged(); + if( FAILED( hr ) ) + return hr; + + return S_OK; +} + + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnWindowedFullScreenChanged() +{ + HRESULT hr = S_OK; + bool bWindowed = IsWindowed(); + + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT_LABEL, !bWindowed ); + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_D3D11_RESOLUTION_LABEL, !bWindowed ); + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_D3D11_REFRESH_RATE_LABEL, !bWindowed ); + + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_RESOLUTION_SHOW_ALL, !bWindowed ); + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT, !bWindowed ); + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_D3D11_RESOLUTION, !bWindowed ); + m_Dialog.SetControlEnabled( DXUTSETTINGSDLG_D3D11_REFRESH_RATE, !bWindowed ); + + g_DeviceSettings.d3d11.sd.Windowed = bWindowed; + + // Get available adapter output + auto pD3DEnum = DXUTGetD3D11Enumeration(); + + auto pOutputComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT ); + pOutputComboBox->RemoveAllItems(); + + auto pAdapterInfo = pD3DEnum->GetAdapterInfo( g_DeviceSettings.d3d11.AdapterOrdinal ); + for( size_t ioutput = 0; ioutput < pAdapterInfo->outputInfoList.size(); ++ioutput ) + { + auto pOutputInfo = pAdapterInfo->outputInfoList[ ioutput ]; + AddD3D11AdapterOutput( pOutputInfo->Desc.DeviceName, pOutputInfo->Output ); + } + + pOutputComboBox->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.Output ) ); + + hr = OnAdapterOutputChanged(); + if( FAILED( hr ) ) + return hr; + + hr = UpdateD3D11Resolutions(); + if (FAILED(hr)) + return hr; + + hr = UpdateD3D11RefreshRates(); + if ( FAILED(hr) ) + return hr; + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnAdapterOutputChanged() +{ + HRESULT hr; + + bool bWindowed = IsWindowed(); + g_DeviceSettings.d3d11.sd.Windowed = bWindowed; + + // If windowed, get the appropriate adapter format from Direct3D + if( g_DeviceSettings.d3d11.sd.Windowed ) + { + DXGI_MODE_DESC mode; + hr = DXUTGetD3D11AdapterDisplayMode( g_DeviceSettings.d3d11.AdapterOrdinal, + g_DeviceSettings.d3d11.Output, &mode ); + if( FAILED( hr ) ) + return DXTRACE_ERR( L"GetD3D11AdapterDisplayMode", hr ); + + // Default resolution to the fullscreen res that was last used + RECT rc = DXUTGetFullsceenClientRectAtModeChange(); + if( rc.right == 0 || rc.bottom == 0 ) + { + // If nothing last used, then default to the adapter desktop res + g_DeviceSettings.d3d11.sd.BufferDesc.Width = mode.Width; + g_DeviceSettings.d3d11.sd.BufferDesc.Height = mode.Height; + } + else + { + g_DeviceSettings.d3d11.sd.BufferDesc.Width = rc.right; + g_DeviceSettings.d3d11.sd.BufferDesc.Height = rc.bottom; + } + + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate.Numerator = + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate.Denominator = 0; + } + + auto pAdapterInfo = GetCurrentD3D11AdapterInfo(); + if( !pAdapterInfo ) + return E_FAIL; + + // DXUTSETTINGSDLG_D3D11_RESOLUTION + hr = UpdateD3D11Resolutions(); + if( FAILED( hr ) ) + return hr; + + // DXUTSETTINGSDLG_D3D11_REFRESH_RATE + hr = UpdateD3D11RefreshRates(); + if ( FAILED(hr) ) + return hr; + + // DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT + auto pBackBufferFormatComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT ); + pBackBufferFormatComboBox->RemoveAllItems(); + + for( size_t idc = 0; idc < pAdapterInfo->deviceSettingsComboList.size(); idc++ ) + { + auto pDeviceCombo = pAdapterInfo->deviceSettingsComboList[ idc ]; + if( ( pDeviceCombo->Windowed == TRUE ) == bWindowed ) + { + AddD3D11BackBufferFormat( pDeviceCombo->BackBufferFormat ); + } + } + + pBackBufferFormatComboBox->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.sd.BufferDesc.Format ) ); + + hr = OnBackBufferFormatChanged(); + if( FAILED( hr ) ) + return hr; + + hr = OnRefreshRateChanged(); + if( FAILED( hr ) ) + return hr; + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnRefreshRateChanged() +{ + // Set refresh rate + g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate = GetSelectedD3D11RefreshRate(); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnBackBufferFormatChanged() +{ + HRESULT hr = S_OK; + + g_DeviceSettings.d3d11.sd.BufferDesc.Format = GetSelectedD3D11BackBufferFormat(); + + DXGI_FORMAT backBufferFormat = g_DeviceSettings.d3d11.sd.BufferDesc.Format; + + auto pAdapterInfo = GetCurrentD3D11AdapterInfo(); + if( !pAdapterInfo ) + return E_FAIL; + + for( size_t idc = 0; idc < pAdapterInfo->deviceSettingsComboList.size(); idc++ ) + { + auto pDeviceCombo = pAdapterInfo->deviceSettingsComboList[ idc ]; + + if( pDeviceCombo->Windowed == ( g_DeviceSettings.d3d11.sd.Windowed == TRUE ) && + pDeviceCombo->BackBufferFormat == backBufferFormat && + pDeviceCombo->DeviceType == g_DeviceSettings.d3d11.DriverType ) + { + auto pMultisampleCountCombo = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT ); + pMultisampleCountCombo->RemoveAllItems(); + + for( auto it = pDeviceCombo->multiSampleCountList.cbegin(); it != pDeviceCombo->multiSampleCountList.cend(); ++it ) + AddD3D11MultisampleCount( *it ); + pMultisampleCountCombo->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.sd.SampleDesc.Count ) ); + + hr = OnMultisampleTypeChanged(); + if( FAILED( hr ) ) + return hr; + + auto pPresentIntervalComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL ); + pPresentIntervalComboBox->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.SyncInterval ) ); + + hr = OnPresentIntervalChanged(); + if( FAILED( hr ) ) + return hr; + + hr = UpdateD3D11Resolutions(); + if( FAILED( hr ) ) + return hr; + + hr = UpdateD3D11RefreshRates(); + if ( FAILED(hr) ) + return hr; + + break; + } + } + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnMultisampleTypeChanged() +{ + HRESULT hr = S_OK; + + UINT multisampleCount = GetSelectedD3D11MultisampleCount(); + g_DeviceSettings.d3d11.sd.SampleDesc.Count = multisampleCount; + + auto pDeviceSettingsCombo = GetCurrentD3D11DeviceSettingsCombo(); + if( !pDeviceSettingsCombo ) + return E_FAIL; + + UINT MaxQuality = 0; + for( size_t iCount = 0; iCount < pDeviceSettingsCombo->multiSampleCountList.size(); iCount++ ) + { + UINT Count = pDeviceSettingsCombo->multiSampleCountList[ iCount ]; + if( Count == multisampleCount ) + { + MaxQuality = pDeviceSettingsCombo->multiSampleQualityList[ iCount ]; + break; + } + } + + // DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY + auto pMultisampleQualityCombo = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY ); + pMultisampleQualityCombo->RemoveAllItems(); + + for( UINT iQuality = 0; iQuality < MaxQuality; iQuality++ ) + { + AddD3D11MultisampleQuality( iQuality ); + } + + pMultisampleQualityCombo->SetSelectedByData( ULongToPtr( g_DeviceSettings.d3d11.sd.SampleDesc.Quality ) ); + + hr = OnMultisampleQualityChanged(); + if( FAILED( hr ) ) + return hr; + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnMultisampleQualityChanged() +{ + g_DeviceSettings.d3d11.sd.SampleDesc.Quality = GetSelectedD3D11MultisampleQuality(); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnPresentIntervalChanged() +{ + g_DeviceSettings.d3d11.SyncInterval = GetSelectedD3D11PresentInterval(); + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::OnDebugDeviceChanged() +{ + bool bDebugDevice = GetSelectedDebugDeviceValue(); + + if( bDebugDevice ) + g_DeviceSettings.d3d11.CreateFlags |= D3D11_CREATE_DEVICE_DEBUG; + else + g_DeviceSettings.d3d11.CreateFlags &= ~D3D11_CREATE_DEVICE_DEBUG; + + return S_OK; +} + + +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::AddAdapter( _In_z_ const WCHAR* strDescription, _In_ UINT iAdapter ) +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_ADAPTER ); + + if( !pComboBox->ContainsItem( strDescription ) ) + pComboBox->AddItem( strDescription, ULongToPtr( iAdapter ) ); +} + + +//------------------------------------------------------------------------------------- +UINT CD3DSettingsDlg::GetSelectedAdapter() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_ADAPTER ); + + return PtrToUlong( pComboBox->GetSelectedData() ); +} + + +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::SetWindowed( _In_ bool bWindowed ) +{ + auto pRadioButton = m_Dialog.GetRadioButton( DXUTSETTINGSDLG_WINDOWED ); + pRadioButton->SetChecked( bWindowed ); + + pRadioButton = m_Dialog.GetRadioButton( DXUTSETTINGSDLG_FULLSCREEN ); + pRadioButton->SetChecked( !bWindowed ); + + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT_LABEL, !bWindowed); + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_D3D11_RESOLUTION_LABEL, !bWindowed); + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_D3D11_REFRESH_RATE_LABEL, !bWindowed); + + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_RESOLUTION_SHOW_ALL, !bWindowed); + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT, !bWindowed); + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_D3D11_RESOLUTION, !bWindowed); + m_Dialog.SetControlEnabled(DXUTSETTINGSDLG_D3D11_REFRESH_RATE, !bWindowed); +} + + +//------------------------------------------------------------------------------------- +bool CD3DSettingsDlg::IsWindowed() const +{ + auto pRadioButton = m_Dialog.GetRadioButton( DXUTSETTINGSDLG_WINDOWED ); + return pRadioButton->GetChecked(); +} + + +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::AddD3D11AdapterOutput( _In_z_ const WCHAR* strName, _In_ UINT Output ) +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT ); + + if( !pComboBox->ContainsItem( strName ) ) + pComboBox->AddItem( strName, ULongToPtr( Output ) ); +} + + +//------------------------------------------------------------------------------------- +UINT CD3DSettingsDlg::GetSelectedD3D11AdapterOutput() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT ); + + return PtrToUlong( pComboBox->GetSelectedData() ); +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CD3DSettingsDlg::AddD3D11Resolution( DWORD dwWidth, DWORD dwHeight ) +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_RESOLUTION ); + + DWORD dwResolutionData; + WCHAR strResolution[50]; + dwResolutionData = MAKELONG( dwWidth, dwHeight ); + swprintf_s( strResolution, 50, L"%u by %u", dwWidth, dwHeight ); + + if( !pComboBox->ContainsItem( strResolution ) ) + pComboBox->AddItem( strResolution, ULongToPtr( dwResolutionData ) ); +} + + +//------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CD3DSettingsDlg::GetSelectedD3D11Resolution( DWORD* pdwWidth, DWORD* pdwHeight ) const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_RESOLUTION ); + + DWORD dwResolution = PtrToUlong( pComboBox->GetSelectedData() ); + + *pdwWidth = LOWORD( dwResolution ); + *pdwHeight = HIWORD( dwResolution ); +} + + +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::AddD3D11FeatureLevel( _In_ D3D_FEATURE_LEVEL fl) +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL ); + switch( fl ) + { + case D3D_FEATURE_LEVEL_9_1: + { + if( !pComboBox->ContainsItem( L"D3D_FEATURE_LEVEL_9_1" ) ) + pComboBox->AddItem( L"D3D_FEATURE_LEVEL_9_1", ULongToPtr( D3D_FEATURE_LEVEL_9_1 ) ); + } + break; + case D3D_FEATURE_LEVEL_9_2: + { + if( !pComboBox->ContainsItem( L"D3D_FEATURE_LEVEL_9_2" ) ) + pComboBox->AddItem( L"D3D_FEATURE_LEVEL_9_2", ULongToPtr( D3D_FEATURE_LEVEL_9_2 ) ); + } + break; + case D3D_FEATURE_LEVEL_9_3: + { + if( !pComboBox->ContainsItem( L"D3D_FEATURE_LEVEL_9_3" ) ) + pComboBox->AddItem( L"D3D_FEATURE_LEVEL_9_3", ULongToPtr( D3D_FEATURE_LEVEL_9_3 ) ); + } + break; + case D3D_FEATURE_LEVEL_10_0: + { + if( !pComboBox->ContainsItem( L"D3D_FEATURE_LEVEL_10_0" ) ) + pComboBox->AddItem( L"D3D_FEATURE_LEVEL_10_0", ULongToPtr( D3D_FEATURE_LEVEL_10_0 ) ); + } + break; + case D3D_FEATURE_LEVEL_10_1: + { + if( !pComboBox->ContainsItem( L"D3D_FEATURE_LEVEL_10_1" ) ) + pComboBox->AddItem( L"D3D_FEATURE_LEVEL_10_1", ULongToPtr( D3D_FEATURE_LEVEL_10_1 ) ); + } + break; + case D3D_FEATURE_LEVEL_11_0: + { + if( !pComboBox->ContainsItem( L"D3D_FEATURE_LEVEL_11_0" ) ) + pComboBox->AddItem( L"D3D_FEATURE_LEVEL_11_0", ULongToPtr( D3D_FEATURE_LEVEL_11_0 ) ); + } + break; + case D3D_FEATURE_LEVEL_11_1: + { + if( !pComboBox->ContainsItem( L"D3D_FEATURE_LEVEL_11_1" ) ) + pComboBox->AddItem( L"D3D_FEATURE_LEVEL_11_1", ULongToPtr( D3D_FEATURE_LEVEL_11_1 ) ); + } + break; +#if defined(USE_DIRECT3D11_3) || defined(USE_DIRECT3D11_4) + case D3D_FEATURE_LEVEL_12_0: + { + if (!pComboBox->ContainsItem(L"D3D_FEATURE_LEVEL_12_0")) + pComboBox->AddItem(L"D3D_FEATURE_LEVEL_12_0", ULongToPtr(D3D_FEATURE_LEVEL_12_0)); + } + break; + case D3D_FEATURE_LEVEL_12_1: + { + if (!pComboBox->ContainsItem(L"D3D_FEATURE_LEVEL_12_1")) + pComboBox->AddItem(L"D3D_FEATURE_LEVEL_12_1", ULongToPtr(D3D_FEATURE_LEVEL_12_1)); + } + break; +#endif + } + +} + +D3D_FEATURE_LEVEL CD3DSettingsDlg::GetSelectedFeatureLevel() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL ); + + return (D3D_FEATURE_LEVEL)PtrToUlong( pComboBox->GetSelectedData() ); +} + + +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::AddD3D11RefreshRate( _In_ DXGI_RATIONAL RefreshRate ) +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_REFRESH_RATE ); + + WCHAR strRefreshRate[50]; + + if( RefreshRate.Numerator == 0 && RefreshRate.Denominator == 0 ) + wcscpy_s( strRefreshRate, 50, L"Default Rate" ); + else + swprintf_s( strRefreshRate, 50, L"%u Hz", RefreshRate.Numerator / RefreshRate.Denominator ); + + if( !pComboBox->ContainsItem( strRefreshRate ) ) + { + auto pNewRate = new (std::nothrow) DXGI_RATIONAL; + if( pNewRate ) + { + *pNewRate = RefreshRate; + pComboBox->AddItem( strRefreshRate, pNewRate ); + } + } +} + + +//------------------------------------------------------------------------------------- +DXGI_RATIONAL CD3DSettingsDlg::GetSelectedD3D11RefreshRate() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_REFRESH_RATE ); + return *reinterpret_cast( pComboBox->GetSelectedData() ); +} + + +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::AddD3D11BackBufferFormat( _In_ DXGI_FORMAT format ) +{ + if ( g_DeviceSettings.d3d11.DeviceFeatureLevel < D3D_FEATURE_LEVEL_10_0 ) + { + if ( (format == DXGI_FORMAT_R16G16B16A16_FLOAT) || (format == DXGI_FORMAT_R10G10B10A2_UNORM) ) + return; + } + + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT ); + + if( !pComboBox->ContainsItem( DXUTDXGIFormatToString( format, TRUE ) ) ) + pComboBox->AddItem( DXUTDXGIFormatToString( format, TRUE ), ULongToPtr( format ) ); +} + + +//------------------------------------------------------------------------------------- +DXGI_FORMAT CD3DSettingsDlg::GetSelectedD3D11BackBufferFormat() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT ); + + return ( DXGI_FORMAT )PtrToUlong( pComboBox->GetSelectedData() ); +} + + +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::AddD3D11MultisampleCount( _In_ UINT Count ) +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT ); + + WCHAR str[50]; + swprintf_s( str, 50, L"%u", Count ); + + if( !pComboBox->ContainsItem( str ) ) + pComboBox->AddItem( str, ULongToPtr( Count ) ); +} + + +//------------------------------------------------------------------------------------- +UINT CD3DSettingsDlg::GetSelectedD3D11MultisampleCount() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT ); + + return ( UINT )PtrToUlong( pComboBox->GetSelectedData() ); +} + + +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::AddD3D11MultisampleQuality( _In_ UINT Quality ) +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY ); + + WCHAR strQuality[50]; + swprintf_s( strQuality, 50, L"%u", Quality ); + + if( !pComboBox->ContainsItem( strQuality ) ) + pComboBox->AddItem( strQuality, ULongToPtr( Quality ) ); +} + + +//------------------------------------------------------------------------------------- +UINT CD3DSettingsDlg::GetSelectedD3D11MultisampleQuality() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY ); + + return ( UINT )PtrToUlong( pComboBox->GetSelectedData() ); +} + + +//------------------------------------------------------------------------------------- +DWORD CD3DSettingsDlg::GetSelectedD3D11PresentInterval() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL ); + + return PtrToUlong( pComboBox->GetSelectedData() ); +} + +//------------------------------------------------------------------------------------- +bool CD3DSettingsDlg::GetSelectedDebugDeviceValue() const +{ + auto pCheckBox = m_Dialog.GetCheckBox( DXUTSETTINGSDLG_D3D11_DEBUG_DEVICE ); + + return pCheckBox->GetChecked(); +} + + +//-------------------------------------------------------------------------------------- +// Updates the resolution list for D3D11 +//-------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::UpdateD3D11Resolutions() +{ + const DWORD dwWidth = g_DeviceSettings.d3d11.sd.BufferDesc.Width; + const DWORD dwHeight = g_DeviceSettings.d3d11.sd.BufferDesc.Height; + + // DXUTSETTINGSDLG_D3D11_RESOLUTION + auto pResolutionComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_RESOLUTION ); + pResolutionComboBox->RemoveAllItems(); + + auto pOutputInfo = GetCurrentD3D11OutputInfo(); + if( !pOutputInfo ) + return E_FAIL; + + bool bWindowed = IsWindowed(); + if ( !bWindowed ) + { + auto pShowAllCB = m_Dialog.GetCheckBox( DXUTSETTINGSDLG_RESOLUTION_SHOW_ALL ); + bool bShowAll = pShowAllCB->GetChecked(); + + // Get the desktop aspect ratio + DXGI_MODE_DESC dmDesktop; + DXUTGetDesktopResolution(g_DeviceSettings.d3d11.AdapterOrdinal, &dmDesktop.Width, &dmDesktop.Height); + float fDesktopAspectRatio = dmDesktop.Width / (float) dmDesktop.Height; + + if ( !bShowAll && !DXUTIsWindowed() ) + { + float fAspect = (float) dwWidth / (float) dwHeight; + if ( fabsf(fDesktopAspectRatio - fAspect) >= 0.05f ) + { + // Our current fullscren resolution should be listed in the combo box despite the aspect ratio + pShowAllCB->SetChecked(true); + bShowAll = true; + } + } + + for (size_t idm = 0; idm < pOutputInfo->displayModeList.size(); idm++) + { + auto DisplayMode = pOutputInfo->displayModeList[idm]; + float fAspect = (float) DisplayMode.Width / (float) DisplayMode.Height; + + if (DisplayMode.Format == g_DeviceSettings.d3d11.sd.BufferDesc.Format) + { + // If "Show All" is not checked, then hide all resolutions + // that don't match the aspect ratio of the desktop resolution + if (bShowAll || (!bShowAll && fabsf(fDesktopAspectRatio - fAspect) < 0.05f)) + { + AddD3D11Resolution(DisplayMode.Width, DisplayMode.Height); + } + } + } + } + else + { + pResolutionComboBox->RemoveAllItems(); + AddD3D11Resolution( dwWidth, dwHeight ); + } + + pResolutionComboBox->SetSelectedByData(ULongToPtr(MAKELONG(dwWidth, dwHeight))); + OnD3D11ResolutionChanged(); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// Updates the refresh list for D3D11 +//-------------------------------------------------------------------------------------- +HRESULT CD3DSettingsDlg::UpdateD3D11RefreshRates() +{ + const DWORD dwWidth = g_DeviceSettings.d3d11.sd.BufferDesc.Width; + const DWORD dwHeight = g_DeviceSettings.d3d11.sd.BufferDesc.Height; + DXGI_FORMAT backBuffer = g_DeviceSettings.d3d11.sd.BufferDesc.Format; + const DXGI_RATIONAL RefreshRate = g_DeviceSettings.d3d11.sd.BufferDesc.RefreshRate; + + auto pRefreshRateComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_D3D11_REFRESH_RATE ); + for( UINT i = 0; i < pRefreshRateComboBox->GetNumItems(); ++i ) + { + auto pRefreshRate = reinterpret_cast( pRefreshRateComboBox->GetItemData( i ) ); + delete pRefreshRate; + } + pRefreshRateComboBox->RemoveAllItems(); + + bool bWindowed = IsWindowed(); + if( bWindowed ) + { + DXGI_RATIONAL def; + def.Denominator = def.Numerator = 0; + AddD3D11RefreshRate(def); + } + else + { + auto pD3DEnum = DXUTGetD3D11Enumeration(); + if ( !pD3DEnum ) + return E_POINTER; + + auto pOutputInfo = pD3DEnum->GetOutputInfo( g_DeviceSettings.d3d11.AdapterOrdinal, g_DeviceSettings.d3d11.Output ); + if ( !pOutputInfo ) + return E_POINTER; + + for( auto it = pOutputInfo->displayModeList.cbegin(); it != pOutputInfo->displayModeList.cend(); ++it ) + { + if ( it->Width == dwWidth && it->Height == dwHeight && it->Format == backBuffer ) + AddD3D11RefreshRate( it->RefreshRate ); + } + + SetSelectedD3D11RefreshRate( RefreshRate ); + } + + return S_OK; +} + + +// +//------------------------------------------------------------------------------------- +void CD3DSettingsDlg::AddD3D11DeviceType( _In_ D3D_DRIVER_TYPE devType ) +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_DEVICE_TYPE ); + + if( !pComboBox->ContainsItem( DXUTDeviceTypeToString( devType ) ) ) + pComboBox->AddItem( DXUTDeviceTypeToString( devType ), ULongToPtr( devType ) ); +} + + +//------------------------------------------------------------------------------------- +D3D_DRIVER_TYPE CD3DSettingsDlg::GetSelectedD3D11DeviceType() const +{ + auto pComboBox = m_Dialog.GetComboBox( DXUTSETTINGSDLG_DEVICE_TYPE ); + + return ( D3D_DRIVER_TYPE )PtrToUlong( pComboBox->GetSelectedData() ); +} + + +void CD3DSettingsDlg::UpdateModeChangeTimeoutText( _In_ int nSecRemaining ) +{ + const WCHAR StrTimeout[] = L"Reverting to previous display settings in %d seconds"; + const DWORD CchBuf = sizeof( StrTimeout ) / sizeof( WCHAR ) + 16; + WCHAR buf[CchBuf]; + + swprintf_s( buf, CchBuf, StrTimeout, nSecRemaining ); + + auto pStatic = m_RevertModeDialog.GetStatic( DXUTSETTINGSDLG_STATIC_MODE_CHANGE_TIMEOUT ); + pStatic->SetText( buf ); +} + +//-------------------------------------------------------------------------------------- +// Returns the string for the given D3D_DRIVER_TYPE. +//-------------------------------------------------------------------------------------- +const WCHAR* DXUTDeviceTypeToString( _In_ D3D_DRIVER_TYPE devType ) +{ + switch( devType ) + { + case D3D_DRIVER_TYPE_HARDWARE: + return L"D3D_DRIVER_TYPE_HARDWARE"; + case D3D_DRIVER_TYPE_REFERENCE: + return L"D3D_DRIVER_TYPE_REFERENCE"; + case D3D_DRIVER_TYPE_NULL: + return L"D3D_DRIVER_TYPE_NULL"; + case D3D_DRIVER_TYPE_WARP: + return L"D3D_DRIVER_TYPE_WARP"; + default: + return L"Unknown devType"; + } +} + + diff --git a/src/DX11/framework/dxut/Optional/DXUTsettingsdlg.h b/src/DX11/framework/dxut/Optional/DXUTsettingsdlg.h new file mode 100644 index 0000000..2a22bac --- /dev/null +++ b/src/DX11/framework/dxut/Optional/DXUTsettingsdlg.h @@ -0,0 +1,165 @@ +//-------------------------------------------------------------------------------------- +// File: DXUTSettingsDlg.h +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +//-------------------------------------------------------------------------------------- +// Header Includes +//-------------------------------------------------------------------------------------- +#include "DXUTgui.h" + +//-------------------------------------------------------------------------------------- +// Control IDs +//-------------------------------------------------------------------------------------- +#define DXUTSETTINGSDLG_STATIC -1 +#define DXUTSETTINGSDLG_OK 1 +#define DXUTSETTINGSDLG_CANCEL 2 +#define DXUTSETTINGSDLG_ADAPTER 3 +#define DXUTSETTINGSDLG_DEVICE_TYPE 4 +#define DXUTSETTINGSDLG_WINDOWED 5 +#define DXUTSETTINGSDLG_FULLSCREEN 6 +#define DXUTSETTINGSDLG_RESOLUTION_SHOW_ALL 26 +#define DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT 28 +#define DXUTSETTINGSDLG_D3D11_ADAPTER_OUTPUT_LABEL 29 +#define DXUTSETTINGSDLG_D3D11_RESOLUTION 30 +#define DXUTSETTINGSDLG_D3D11_RESOLUTION_LABEL 31 +#define DXUTSETTINGSDLG_D3D11_REFRESH_RATE 32 +#define DXUTSETTINGSDLG_D3D11_REFRESH_RATE_LABEL 33 +#define DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT 34 +#define DXUTSETTINGSDLG_D3D11_BACK_BUFFER_FORMAT_LABEL 35 +#define DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT 36 +#define DXUTSETTINGSDLG_D3D11_MULTISAMPLE_COUNT_LABEL 37 +#define DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY 38 +#define DXUTSETTINGSDLG_D3D11_MULTISAMPLE_QUALITY_LABEL 39 +#define DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL 40 +#define DXUTSETTINGSDLG_D3D11_PRESENT_INTERVAL_LABEL 41 +#define DXUTSETTINGSDLG_D3D11_DEBUG_DEVICE 42 +#define DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL 43 +#define DXUTSETTINGSDLG_D3D11_FEATURE_LEVEL_LABEL 44 + +#define DXUTSETTINGSDLG_MODE_CHANGE_ACCEPT 58 +#define DXUTSETTINGSDLG_MODE_CHANGE_REVERT 59 +#define DXUTSETTINGSDLG_STATIC_MODE_CHANGE_TIMEOUT 60 +#define DXUTSETTINGSDLG_WINDOWED_GROUP 0x0100 + +#define TOTAL_FEATURE_LEVELS 9 + +//-------------------------------------------------------------------------------------- +// Dialog for selection of device settings +// Use DXUTGetD3DSettingsDialog() to access global instance +// To control the contents of the dialog, use the CD3D11Enumeration class. +//-------------------------------------------------------------------------------------- +class CD3DSettingsDlg +{ +public: + CD3DSettingsDlg() noexcept; + ~CD3DSettingsDlg(); + + void Init( _In_ CDXUTDialogResourceManager* pManager ); + void Init( _In_ CDXUTDialogResourceManager* pManager, _In_z_ LPCWSTR szControlTextureFileName ); + void Init( _In_ CDXUTDialogResourceManager* pManager, _In_z_ LPCWSTR pszControlTextureResourcename, + _In_ HMODULE hModule ); + + HRESULT Refresh(); + void OnRender( _In_ float fElapsedTime ); + + HRESULT OnD3D11CreateDevice( _In_ ID3D11Device* pd3dDevice ); + HRESULT OnD3D11ResizedSwapChain( _In_ ID3D11Device* pd3dDevice, + _In_ const DXGI_SURFACE_DESC* pBackBufferSurfaceDesc ); + void OnD3D11DestroyDevice(); + + CDXUTDialog* GetDialogControl() { return &m_Dialog; } + bool IsActive() const { return m_bActive; } + void SetActive( _In_ bool bActive ) + { + m_bActive = bActive; + if( bActive ) Refresh(); + } + + LRESULT MsgProc( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _In_ LPARAM lParam ); + +protected: + friend CD3DSettingsDlg* WINAPI DXUTGetD3DSettingsDialog(); + + void CreateControls(); + void SetSelectedD3D11RefreshRate( _In_ DXGI_RATIONAL RefreshRate ); + HRESULT UpdateD3D11Resolutions(); + HRESULT UpdateD3D11RefreshRates(); + + void OnEvent( _In_ UINT nEvent, _In_ int nControlID, _In_ CDXUTControl* pControl ); + + static void WINAPI StaticOnEvent( _In_ UINT nEvent, _In_ int nControlID, _In_ CDXUTControl* pControl, _In_opt_ void* pUserData ); + static void WINAPI StaticOnModeChangeTimer( _In_ UINT nIDEvent, _In_opt_ void* pUserContext ); + + CD3D11EnumAdapterInfo* GetCurrentD3D11AdapterInfo() const; + CD3D11EnumDeviceInfo* GetCurrentD3D11DeviceInfo() const; + CD3D11EnumOutputInfo* GetCurrentD3D11OutputInfo() const; + CD3D11EnumDeviceSettingsCombo* GetCurrentD3D11DeviceSettingsCombo() const; + + void AddAdapter( _In_z_ const WCHAR* strDescription, _In_ UINT iAdapter ); + UINT GetSelectedAdapter() const; + + void SetWindowed( _In_ bool bWindowed ); + bool IsWindowed() const; + + // D3D11 + void AddD3D11DeviceType( _In_ D3D_DRIVER_TYPE devType ); + D3D_DRIVER_TYPE GetSelectedD3D11DeviceType() const; + + void AddD3D11AdapterOutput( _In_z_ const WCHAR* strName, _In_ UINT nOutput ); + UINT GetSelectedD3D11AdapterOutput() const; + + void AddD3D11Resolution( _In_ DWORD dwWidth, _In_ DWORD dwHeight ); + void GetSelectedD3D11Resolution( _Out_ DWORD* pdwWidth, _Out_ DWORD* pdwHeight ) const; + + void AddD3D11FeatureLevel( _In_ D3D_FEATURE_LEVEL fl ); + D3D_FEATURE_LEVEL GetSelectedFeatureLevel() const; + + void AddD3D11RefreshRate( _In_ DXGI_RATIONAL RefreshRate ); + DXGI_RATIONAL GetSelectedD3D11RefreshRate() const; + + void AddD3D11BackBufferFormat( _In_ DXGI_FORMAT format ); + DXGI_FORMAT GetSelectedD3D11BackBufferFormat() const; + + void AddD3D11MultisampleCount( _In_ UINT count ); + UINT GetSelectedD3D11MultisampleCount() const; + + void AddD3D11MultisampleQuality( _In_ UINT Quality ); + UINT GetSelectedD3D11MultisampleQuality() const; + + DWORD GetSelectedD3D11PresentInterval() const; + bool GetSelectedDebugDeviceValue() const; + + HRESULT OnD3D11ResolutionChanged (); + HRESULT OnFeatureLevelChanged(); + HRESULT OnAdapterChanged(); + HRESULT OnDeviceTypeChanged(); + HRESULT OnWindowedFullScreenChanged(); + HRESULT OnAdapterOutputChanged(); + HRESULT OnRefreshRateChanged(); + HRESULT OnBackBufferFormatChanged(); + HRESULT OnMultisampleTypeChanged(); + HRESULT OnMultisampleQualityChanged(); + HRESULT OnPresentIntervalChanged(); + HRESULT OnDebugDeviceChanged(); + + void UpdateModeChangeTimeoutText( _In_ int nSecRemaining ); + + CDXUTDialog* m_pActiveDialog; + CDXUTDialog m_Dialog; + CDXUTDialog m_RevertModeDialog; + int m_nRevertModeTimeout; + UINT m_nIDEvent; + bool m_bActive; + + D3D_FEATURE_LEVEL m_Levels[TOTAL_FEATURE_LEVELS]; + +}; + + +CD3DSettingsDlg* WINAPI DXUTGetD3DSettingsDialog(); diff --git a/src/DX11/framework/dxut/Optional/ImeUi.cpp b/src/DX11/framework/dxut/Optional/ImeUi.cpp new file mode 100644 index 0000000..8d08da1 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/ImeUi.cpp @@ -0,0 +1,3246 @@ +//-------------------------------------------------------------------------------------- +// File: ImeUi.cpp +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "dxut.h" +#include "ImeUi.h" +#include +#include +#include + +// Ignore typecast warnings +#pragma warning( disable : 4312 ) +#pragma warning( disable : 4244 ) +#pragma warning( disable : 4311 ) + +#pragma prefast( disable : 28159, "GetTickCount() is fine for a blinking cursor" ) + +#define MAX_CANDIDATE_LENGTH 256 +#define COUNTOF(a) ( sizeof( a ) / sizeof( ( a )[0] ) ) +#define POSITION_UNINITIALIZED ((DWORD)-1) + +#define LANG_CHT MAKELANGID(LANG_CHINESE, SUBLANG_CHINESE_TRADITIONAL) +#define LANG_CHS MAKELANGID(LANG_CHINESE, SUBLANG_CHINESE_SIMPLIFIED) + +#define MAKEIMEVERSION(major,minor) ( (DWORD)( ( (BYTE)( major ) << 24 ) | ( (BYTE)( minor ) << 16 ) ) ) +#define IMEID_VER(dwId) ( ( dwId ) & 0xffff0000 ) +#define IMEID_LANG(dwId) ( ( dwId ) & 0x0000ffff ) + +#define _CHT_HKL_DAYI ( (HKL)0xE0060404 ) // DaYi +#define _CHT_HKL_NEW_PHONETIC ( (HKL)0xE0080404 ) // New Phonetic +#define _CHT_HKL_NEW_CHANG_JIE ( (HKL)0xE0090404 ) // New Chang Jie +#define _CHT_HKL_NEW_QUICK ( (HKL)0xE00A0404 ) // New Quick +#define _CHT_HKL_HK_CANTONESE ( (HKL)0xE00B0404 ) // Hong Kong Cantonese +#define _CHT_IMEFILENAME "TINTLGNT.IME" // New Phonetic +#define _CHT_IMEFILENAME2 "CINTLGNT.IME" // New Chang Jie +#define _CHT_IMEFILENAME3 "MSTCIPHA.IME" // Phonetic 5.1 +#define IMEID_CHT_VER42 ( LANG_CHT | MAKEIMEVERSION( 4, 2 ) ) // New(Phonetic/ChanJie)IME98 : 4.2.x.x // Win98 +#define IMEID_CHT_VER43 ( LANG_CHT | MAKEIMEVERSION( 4, 3 ) ) // New(Phonetic/ChanJie)IME98a : 4.3.x.x // Win2k +#define IMEID_CHT_VER44 ( LANG_CHT | MAKEIMEVERSION( 4, 4 ) ) // New ChanJie IME98b : 4.4.x.x // WinXP +#define IMEID_CHT_VER50 ( LANG_CHT | MAKEIMEVERSION( 5, 0 ) ) // New(Phonetic/ChanJie)IME5.0 : 5.0.x.x // WinME +#define IMEID_CHT_VER51 ( LANG_CHT | MAKEIMEVERSION( 5, 1 ) ) // New(Phonetic/ChanJie)IME5.1 : 5.1.x.x // IME2002(w/OfficeXP) +#define IMEID_CHT_VER52 ( LANG_CHT | MAKEIMEVERSION( 5, 2 ) ) // New(Phonetic/ChanJie)IME5.2 : 5.2.x.x // IME2002a(w/WinXP) +#define IMEID_CHT_VER60 ( LANG_CHT | MAKEIMEVERSION( 6, 0 ) ) // New(Phonetic/ChanJie)IME6.0 : 6.0.x.x // New IME 6.0(web download) +#define IMEID_CHT_VER_VISTA ( LANG_CHT | MAKEIMEVERSION( 7, 0 ) ) // All TSF TIP under Cicero UI-less mode: a hack to make GetImeId() return non-zero value + +#define _CHS_HKL ( (HKL)0xE00E0804 ) // MSPY +#define _CHS_IMEFILENAME "PINTLGNT.IME" // MSPY1.5/2/3 +#define _CHS_IMEFILENAME2 "MSSCIPYA.IME" // MSPY3 for OfficeXP +#define IMEID_CHS_VER41 ( LANG_CHS | MAKEIMEVERSION( 4, 1 ) ) // MSPY1.5 // SCIME97 or MSPY1.5 (w/Win98, Office97) +#define IMEID_CHS_VER42 ( LANG_CHS | MAKEIMEVERSION( 4, 2 ) ) // MSPY2 // Win2k/WinME +#define IMEID_CHS_VER53 ( LANG_CHS | MAKEIMEVERSION( 5, 3 ) ) // MSPY3 // WinXP + +static CHAR signature[] = "%%%IMEUILIB:070111%%%"; + +static IMEUI_APPEARANCE gSkinIME = +{ + 0, // symbolColor; + 0x404040, // symbolColorOff; + 0xff000000, // symbolColorText; + 24, // symbolHeight; + 0xa0, // symbolTranslucence; + 0, // symbolPlacement; + nullptr, // symbolFont; + 0xffffffff, // candColorBase; + 0xff000000, // candColorBorder; + 0, // candColorText; + 0x00ffff00, // compColorInput; + 0x000000ff, // compColorTargetConv; + 0x0000ff00, // compColorConverted; + 0x00ff0000, // compColorTargetNotConv; + 0x00ff0000, // compColorInputErr; + 0x80, // compTranslucence; + 0, // compColorText; + 2, // caretWidth; + 1, // caretYMargin; +}; + +struct _SkinCompStr +{ + DWORD colorInput; + DWORD colorTargetConv; + DWORD colorConverted; + DWORD colorTargetNotConv; + DWORD colorInputErr; +}; + +_SkinCompStr gSkinCompStr; + +// Definition from Win98DDK version of IMM.H +typedef struct +tagINPUTCONTEXT2 +{ + HWND hWnd; + BOOL fOpen; + POINT ptStatusWndPos; + POINT ptSoftKbdPos; + DWORD fdwConversion; + DWORD fdwSentence; + union + { + LOGFONTA A; + LOGFONTW W; + } lfFont; + COMPOSITIONFORM cfCompForm; + CANDIDATEFORM cfCandForm[4]; + HIMCC hCompStr; + HIMCC hCandInfo; + HIMCC hGuideLine; + HIMCC hPrivate; + DWORD dwNumMsgBuf; + HIMCC hMsgBuf; + DWORD fdwInit; + DWORD dwReserve[3]; +} +INPUTCONTEXT2, *PINPUTCONTEXT2, NEAR *NPINPUTCONTEXT2, +FAR* LPINPUTCONTEXT2; + + +// Class to disable Cicero in case ImmDisableTextFrameService() doesn't disable it completely +class CDisableCicero +{ +public: + CDisableCicero() noexcept : + m_ptim( nullptr ), + m_bComInit( false ) + {} + ~CDisableCicero() + { + Uninitialize(); + } + + void Initialize() + { + if( m_bComInit ) + { + return; + } + HRESULT hr; + hr = CoInitializeEx( nullptr, COINIT_APARTMENTTHREADED ); + if( SUCCEEDED( hr ) ) + { + m_bComInit = true; + hr = CoCreateInstance( CLSID_TF_ThreadMgr, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof( ITfThreadMgr ), + ( void** )&m_ptim ); + } + } + void Uninitialize() + { + if( m_ptim ) + { + m_ptim->Release(); + m_ptim = nullptr; + } + if( m_bComInit ) + CoUninitialize(); + m_bComInit = false; + } + + void DisableCiceroOnThisWnd( HWND hwnd ) + { + if( !m_ptim ) + return; + ITfDocumentMgr* pdimPrev; // the dim that is associated previously. + // Associate nullptr dim to the window. + // When this window gets the focus, Cicero does not work and IMM32 IME + // will be activated. + if( SUCCEEDED( m_ptim->AssociateFocus( hwnd, nullptr, &pdimPrev ) ) ) + { + if( pdimPrev ) + pdimPrev->Release(); + } + } +private: + ITfThreadMgr* m_ptim; + bool m_bComInit; +}; +static CDisableCicero g_disableCicero; + +#define _IsLeadByte(x) ( LeadByteTable[(BYTE)( x )] ) +static void _PumpMessage(); +static BYTE LeadByteTable[256]; +#define _ImmGetContext ImmGetContext +#define _ImmReleaseContext ImmReleaseContext +#define _ImmAssociateContext ImmAssociateContext +static LONG ( WINAPI* _ImmGetCompositionString )( HIMC himc, DWORD dwIndex, LPVOID lpBuf, DWORD dwBufLen ); +#define _ImmGetOpenStatus ImmGetOpenStatus +#define _ImmSetOpenStatus ImmSetOpenStatus +#define _ImmGetConversionStatus ImmGetConversionStatus +static DWORD ( WINAPI* _ImmGetCandidateList )( HIMC himc, DWORD deIndex, LPCANDIDATELIST lpCandList, DWORD dwBufLen ); +static LPINPUTCONTEXT2 ( WINAPI* _ImmLockIMC )( HIMC hIMC ); +static BOOL ( WINAPI* _ImmUnlockIMC )( HIMC hIMC ); +static LPVOID ( WINAPI* _ImmLockIMCC )( HIMCC hIMCC ); +static BOOL ( WINAPI* _ImmUnlockIMCC )( HIMCC hIMCC ); +#define _ImmGetDefaultIMEWnd ImmGetDefaultIMEWnd +#define _ImmGetIMEFileNameA ImmGetIMEFileNameA +#define _ImmGetVirtualKey ImmGetVirtualKey +#define _ImmNotifyIME ImmNotifyIME +#define _ImmSetConversionStatus ImmSetConversionStatus +#define _ImmSimulateHotKey ImmSimulateHotKey +#define _ImmIsIME ImmIsIME + +// private API provided by CHT IME. Available on version 6.0 or later. +UINT ( WINAPI*_GetReadingString )( HIMC himc, UINT uReadingBufLen, LPWSTR lpwReadingBuf, PINT pnErrorIndex, + BOOL* pfIsVertical, PUINT puMaxReadingLen ); +BOOL ( WINAPI*_ShowReadingWindow )( HIMC himc, BOOL bShow ); + +// Callbacks +void ( CALLBACK*ImeUiCallback_DrawRect )( int x1, int y1, int x2, int y2, DWORD color ); +void ( CALLBACK*ImeUiCallback_DrawFans )( const IMEUI_VERTEX* paVertex, UINT uNum ); +void* ( __cdecl*ImeUiCallback_Malloc )( size_t bytes ); +void ( __cdecl*ImeUiCallback_Free )( void* ptr ); +void ( CALLBACK*ImeUiCallback_OnChar )( WCHAR wc ); + +static void (*_SendCompString )(); +static LRESULT ( WINAPI* _SendMessage )( HWND hwnd, UINT msg, WPARAM wp, LPARAM lp ) = SendMessageA; +static DWORD (* _GetCandidateList )( HIMC himc, DWORD dwIndex, LPCANDIDATELIST* ppCandList ); + +static HWND g_hwndMain; +static HWND g_hwndCurr; +static HIMC g_himcOrg; +static bool g_bImeEnabled = false; +static TCHAR g_szCompositionString[256]; +static BYTE g_szCompAttrString[256]; +static DWORD g_IMECursorBytes = 0; +static DWORD g_IMECursorChars = 0; +static TCHAR g_szCandidate[MAX_CANDLIST][MAX_CANDIDATE_LENGTH]; +static DWORD g_dwSelection, g_dwCount; +static UINT g_uCandPageSize; +static DWORD g_bDisableImeCompletely = false; +static DWORD g_dwIMELevel; +static DWORD g_dwIMELevelSaved; +static TCHAR g_szMultiLineCompString[ 256 *( 3 - sizeof( TCHAR ) ) ]; +static bool g_bReadingWindow = false; +static bool g_bHorizontalReading = false; +static bool g_bVerticalCand = true; +static UINT g_uCaretBlinkTime = 0; +static UINT g_uCaretBlinkLast = 0; +static bool g_bCaretDraw = false; +static bool g_bChineseIME; +static bool g_bInsertMode = true; +static TCHAR g_szReadingString[32]; // Used only in case of horizontal reading window +static int g_iReadingError; // Used only in case of horizontal reading window +static UINT g_screenWidth, g_screenHeight; +static DWORD g_dwPrevFloat; +static bool bIsSendingKeyMessage = false; +static OSVERSIONINFOA g_osi; +static bool g_bInitialized = false; +static bool g_bCandList = false; +static DWORD g_dwCandX, g_dwCandY; +static DWORD g_dwCaretX, g_dwCaretY; +static DWORD g_hCompChar; +static int g_iCandListIndexBase; +static DWORD g_dwImeUiFlags = IMEUI_FLAG_SUPPORT_CARET; +static bool g_bUILessMode = false; +static HMODULE g_hImmDll = nullptr; + +#define IsNT() (g_osi.dwPlatformId == VER_PLATFORM_WIN32_NT) + +struct CompStringAttribute +{ + UINT caretX; + UINT caretY; + CImeUiFont_Base* pFont; + DWORD colorComp; + DWORD colorCand; + RECT margins; +}; + +static CompStringAttribute g_CaretInfo; +static DWORD g_dwState = IMEUI_STATE_OFF; +static DWORD swirl = 0; +static double lastSwirl; + +#define INDICATOR_NON_IME 0 +#define INDICATOR_CHS 1 +#define INDICATOR_CHT 2 +#define INDICATOR_KOREAN 3 +#define INDICATOR_JAPANESE 4 + +#define GETLANG() LOWORD(g_hklCurrent) +#define GETPRIMLANG() ((WORD)PRIMARYLANGID(GETLANG())) +#define GETSUBLANG() SUBLANGID(GETLANG()) + +#define LANG_CHS MAKELANGID(LANG_CHINESE, SUBLANG_CHINESE_SIMPLIFIED) +#define LANG_CHT MAKELANGID(LANG_CHINESE, SUBLANG_CHINESE_TRADITIONAL) + +static HKL g_hklCurrent = 0; +static UINT g_uCodePage = 0; +static LPCTSTR g_aszIndicator[] = +{ + TEXT( "A" ), + L"\x7B80", + L"\x7E41", + L"\xac00", + L"\x3042", +}; +static LPCTSTR g_pszIndicatior = g_aszIndicator[0]; + +static void GetReadingString( _In_ HWND hWnd ); +static DWORD GetImeId( _In_ UINT uIndex = 0 ); +static void CheckToggleState(); +static void DrawImeIndicator(); +static void DrawCandidateList(); +static void DrawCompositionString( _In_ bool bDrawCompAttr ); +static void GetReadingWindowOrientation( _In_ DWORD dwId ); +static void OnInputLangChangeWorker(); +static void OnInputLangChange(); +static void SetImeApi(); +static void CheckInputLocale(); +static void SetSupportLevel( _In_ DWORD dwImeLevel ); +void ImeUi_SetSupportLevel( _In_ DWORD dwImeLevel ); + + +// +// local helper functions +// +inline LRESULT SendKeyMsg( HWND hwnd, UINT msg, WPARAM wp ) +{ + bIsSendingKeyMessage = true; + LRESULT lRc = _SendMessage( hwnd, msg, wp, 1 ); + bIsSendingKeyMessage = false; + return lRc; +} +#define SendKeyMsg_DOWN(hwnd,vk) SendKeyMsg(hwnd, WM_KEYDOWN, vk) +#define SendKeyMsg_UP(hwnd,vk) SendKeyMsg(hwnd, WM_KEYUP, vk) + +/////////////////////////////////////////////////////////////////////////////// +// +// CTsfUiLessMode +// Handles IME events using Text Service Framework (TSF). Before Vista, +// IMM (Input Method Manager) API has been used to handle IME events and +// inqueries. Some IMM functions lose backward compatibility due to design +// of TSF, so we have to use new TSF interfaces. +// +/////////////////////////////////////////////////////////////////////////////// +class CTsfUiLessMode +{ +protected: + // Sink receives event notifications + class CUIElementSink : public ITfUIElementSink, + public ITfInputProcessorProfileActivationSink, + public ITfCompartmentEventSink + { + public: + CUIElementSink() noexcept; + virtual ~CUIElementSink(); + + // IUnknown + STDMETHODIMP QueryInterface( _In_ REFIID riid, _COM_Outptr_ void** ppvObj ); + STDMETHODIMP_( ULONG ) + AddRef(); + STDMETHODIMP_( ULONG ) + Release(); + + // ITfUIElementSink + // Notifications for Reading Window events. We could process candidate as well, but we'll use IMM for simplicity sake. + STDMETHODIMP BeginUIElement( DWORD dwUIElementId, BOOL* pbShow ); + STDMETHODIMP UpdateUIElement( DWORD dwUIElementId ); + STDMETHODIMP EndUIElement( DWORD dwUIElementId ); + + // ITfInputProcessorProfileActivationSink + // Notification for keyboard input locale change + STDMETHODIMP OnActivated( DWORD dwProfileType, LANGID langid, _In_ REFCLSID clsid, _In_ REFGUID catid, + _In_ REFGUID guidProfile, HKL hkl, DWORD dwFlags ); + + // ITfCompartmentEventSink + // Notification for open mode (toggle state) change + STDMETHODIMP OnChange( _In_ REFGUID rguid ); + + private: + LONG _cRef; + }; + + static void MakeReadingInformationString( ITfReadingInformationUIElement* preading ); + static void MakeCandidateStrings( ITfCandidateListUIElement* pcandidate ); + static ITfUIElement* GetUIElement( DWORD dwUIElementId ); + static BOOL GetCompartments( ITfCompartmentMgr** ppcm, ITfCompartment** ppTfOpenMode, + ITfCompartment** ppTfConvMode ); + static BOOL SetupCompartmentSinks( BOOL bResetOnly = FALSE, ITfCompartment* pTfOpenMode = nullptr, + ITfCompartment* ppTfConvMode = nullptr ); + + static ITfThreadMgrEx* m_tm; + static DWORD m_dwUIElementSinkCookie; + static DWORD m_dwAlpnSinkCookie; + static DWORD m_dwOpenModeSinkCookie; + static DWORD m_dwConvModeSinkCookie; + static CUIElementSink* m_TsfSink; + static int m_nCandidateRefCount; // Some IME shows multiple candidate lists but the Library doesn't support multiple candidate list. + // So track open / close events to make sure the candidate list opened last is shown. + CTsfUiLessMode() = default; // this class can't be instanciated + +public: + static BOOL SetupSinks(); + static void ReleaseSinks(); + static BOOL CurrentInputLocaleIsIme(); + static void UpdateImeState( BOOL bResetCompartmentEventSink = FALSE ); + static void EnableUiUpdates( bool bEnable ); +}; + +ITfThreadMgrEx* CTsfUiLessMode::m_tm; +DWORD CTsfUiLessMode::m_dwUIElementSinkCookie = TF_INVALID_COOKIE; +DWORD CTsfUiLessMode::m_dwAlpnSinkCookie = TF_INVALID_COOKIE; +DWORD CTsfUiLessMode::m_dwOpenModeSinkCookie = TF_INVALID_COOKIE; +DWORD CTsfUiLessMode::m_dwConvModeSinkCookie = TF_INVALID_COOKIE; +CTsfUiLessMode::CUIElementSink* CTsfUiLessMode::m_TsfSink = nullptr; +int CTsfUiLessMode::m_nCandidateRefCount = 0; + +static unsigned long _strtoul( LPCSTR psz, LPTSTR*, int ) +{ + if( !psz ) + return 0; + + ULONG ulRet = 0; + if( psz[0] == '0' && ( psz[1] == 'x' || psz[1] == 'X' ) ) + { + psz += 2; + ULONG ul = 0; + while( *psz ) + { + if( '0' <= *psz && *psz <= '9' ) + ul = *psz - '0'; + else if( 'A' <= *psz && *psz <= 'F' ) + ul = *psz - 'A' + 10; + else if( 'a' <= *psz && *psz <= 'f' ) + ul = *psz - 'a' + 10; + else + break; + ulRet = ulRet * 16 + ul; + psz++; + } + } + else + { + while( *psz && ( '0' <= *psz && *psz <= '9' ) ) + { + ulRet = ulRet * 10 + ( *psz - '0' ); + psz++; + } + } + return ulRet; +} + +#define GetCharCount(psz) (int)wcslen(psz) +#define GetCharCountFromBytes(psz,iBytes) (iBytes) + +static void ComposeCandidateLine( int index, LPCTSTR pszCandidate ) +{ + LPTSTR psz = g_szCandidate[index]; + *psz++ = ( TCHAR )( TEXT( '0' ) + ( ( index + g_iCandListIndexBase ) % 10 ) ); + if( g_bVerticalCand ) + { + *psz++ = TEXT( ' ' ); + } + while( *pszCandidate && ( COUNTOF(g_szCandidate[index]) > ( psz - g_szCandidate[index] ) ) ) + { + *psz++ = *pszCandidate++; + } + *psz = 0; +} + +static void SendCompString() +{ + int i, iLen = (int)wcslen( g_szCompositionString ); + if( ImeUiCallback_OnChar ) + { + LPCWSTR pwz; + pwz = g_szCompositionString; + for( i = 0; i < iLen; i++ ) + { + ImeUiCallback_OnChar( pwz[i] ); + } + return; + } + for( i = 0; i < iLen; i++ ) + { + SendKeyMsg( g_hwndCurr, WM_CHAR, + (WPARAM)g_szCompositionString[i] + ); + } +} + +static DWORD GetCandidateList( HIMC himc, DWORD dwIndex, LPCANDIDATELIST* ppCandList ) +{ + DWORD dwBufLen = _ImmGetCandidateList( himc, dwIndex, nullptr, 0 ); + if( dwBufLen ) + { + *ppCandList = ( LPCANDIDATELIST )ImeUiCallback_Malloc( dwBufLen ); + dwBufLen = _ImmGetCandidateList( himc, dwIndex, *ppCandList, dwBufLen ); + } + return dwBufLen; +} + +static void SendControlKeys( UINT vk, UINT num ) +{ + if( num == 0 ) + return; + for( UINT i = 0; i < num; i++ ) + { + SendKeyMsg_DOWN(g_hwndCurr, vk); + } + SendKeyMsg_UP(g_hwndCurr, vk); +} + +// send key messages to erase composition string. +static void CancelCompString( HWND hwnd, bool bUseBackSpace = true, int iNewStrLen = 0 ) +{ + if( g_dwIMELevel != 3 ) + return; + int cc = GetCharCount( g_szCompositionString ); + int i; + // move caret to the end of composition string + SendControlKeys( VK_RIGHT, cc - g_IMECursorChars ); + + if( bUseBackSpace || g_bInsertMode ) + iNewStrLen = 0; + + // The caller sets bUseBackSpace to false if there's possibility of sending + // new composition string to the app right after this function call. + // + // If the app is in overwriting mode and new comp string is + // shorter than current one, delete previous comp string + // till it's same long as the new one. Then move caret to the beginning of comp string. + // New comp string will overwrite old one. + if( iNewStrLen < cc ) + { + for( i = 0; i < cc - iNewStrLen; i++ ) + { + SendKeyMsg_DOWN(hwnd, VK_BACK); + SendKeyMsg( hwnd, WM_CHAR, 8 ); //Backspace character + } + SendKeyMsg_UP(hwnd, VK_BACK); + } + else + iNewStrLen = cc; + + SendControlKeys( VK_LEFT, iNewStrLen ); +} + +// initialize composition string data. +static void InitCompStringData() +{ + g_IMECursorBytes = 0; + g_IMECursorChars = 0; + memset( &g_szCompositionString, 0, sizeof( g_szCompositionString ) ); + memset( &g_szCompAttrString, 0, sizeof( g_szCompAttrString ) ); +} + +static void DrawCaret( DWORD x, DWORD y, DWORD height ) +{ + if( g_bCaretDraw && ImeUiCallback_DrawRect ) + ImeUiCallback_DrawRect( x, y + gSkinIME.caretYMargin, x + gSkinIME.caretWidth, + y + height - gSkinIME.caretYMargin, g_CaretInfo.colorComp ); +} + +// +// Apps that draw the composition string on top of composition string attribute +// in level 3 support should call this function twice in rendering a frame. +// // Draw edit box UI; +// ImeUi_RenderUI(true, false); // paint composition string attribute; +// // Draw text in the edit box; +// ImeUi_RenderUi(false, true); // paint the rest of IME UI; +// +void ImeUi_RenderUI( _In_ bool bDrawCompAttr, _In_ bool bDrawOtherUi ) +{ + if( !g_bInitialized || !g_bImeEnabled || !g_CaretInfo.pFont ) + return; + if( !bDrawCompAttr && !bDrawOtherUi ) + return; // error case + if( g_dwIMELevel == 2 ) + { + if( !bDrawOtherUi ) + return; // 1st call for level 3 support + } + + if( bDrawOtherUi ) + DrawImeIndicator(); + + DrawCompositionString( bDrawCompAttr ); + + if( bDrawOtherUi ) + DrawCandidateList(); +} + +static void DrawImeIndicator() +{ + bool bOn = g_dwState != IMEUI_STATE_OFF; + + IMEUI_VERTEX PieData[17]; + float SizeOfPie = ( float )gSkinIME.symbolHeight; + + memset( PieData, 0, sizeof( PieData ) ); + + switch( gSkinIME.symbolPlacement ) + { + case 0: // vertical centering IME indicator + { + if( SizeOfPie + g_CaretInfo.margins.right + 4 > g_screenWidth ) + { + PieData[0].sx = ( -SizeOfPie / 2 ) + g_CaretInfo.margins.left - 4; + PieData[0].sy = ( float )g_CaretInfo.margins.top + ( g_CaretInfo.margins.bottom - + g_CaretInfo.margins.top ) / 2; + } + else + { + PieData[0].sx = -( SizeOfPie / 2 ) + g_CaretInfo.margins.right + gSkinIME.symbolHeight + 4; + PieData[0].sy = ( float )g_CaretInfo.margins.top + ( g_CaretInfo.margins.bottom - + g_CaretInfo.margins.top ) / 2; + } + break; + } + case 1: // upperleft + PieData[0].sx = 4 + ( SizeOfPie / 2 ); + PieData[0].sy = 4 + ( SizeOfPie / 2 ); + break; + case 2: // upperright + PieData[0].sx = g_screenWidth - ( 4 + ( SizeOfPie / 2 ) ); + PieData[0].sy = 4 + ( SizeOfPie / 2 ); + break; + case 3: // lowerright + PieData[0].sx = g_screenWidth - ( 4 + ( SizeOfPie / 2 ) ); + PieData[0].sy = g_screenHeight - ( 4 + ( SizeOfPie / 2 ) ); + break; + case 4: // lowerleft + PieData[0].sx = 4 + ( SizeOfPie / 2 ); + PieData[0].sy = g_screenHeight - ( 4 + ( SizeOfPie / 2 ) ); + break; + } + PieData[0].rhw = 1.0f; + if( bOn ) + { + if( GetTickCount() - lastSwirl > 250 ) + { + swirl++; + lastSwirl = GetTickCount(); + if( swirl > 13 ) + swirl = 0; + } + } + else + swirl = 0; + for( int t1 = 1; t1 < 16; t1++ ) + { + float radian = 2.0f * 3.1415926f * ( t1 - 1 + ( DWORD(bOn) * swirl ) ) / 14.0f; + PieData[t1].sx = ( float )( PieData[0].sx + SizeOfPie / 2 * cos( radian ) ); + PieData[t1].sy = ( float )( PieData[0].sy + SizeOfPie / 2 * sin( radian ) ); + PieData[t1].rhw = 1.0f; + } + + PieData[0].color = 0xffffff + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + if( !gSkinIME.symbolColor && bOn ) + { + { + PieData[1].color = 0xff0000 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[2].color = 0xff3000 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[3].color = 0xff6000 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[4].color = 0xff9000 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[5].color = 0xffC000 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[6].color = 0xffff00 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[7].color = 0xC0ff00 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[8].color = 0x90ff00 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[9].color = 0x60ff00 + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[10].color = 0x30c0ff + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[11].color = 0x00a0ff + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[12].color = 0x3090ff + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[13].color = 0x6060ff + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[14].color = 0x9030ff + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + PieData[15].color = 0xc000ff + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + } + } + else + { + DWORD dwColor = bOn ? gSkinIME.symbolColor : gSkinIME.symbolColorOff; + for( int t1 = 1; t1 < 16; t1++ ) + { + PieData[t1].color = dwColor + ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ); + } + } + PieData[16] = PieData[1]; + + if( ImeUiCallback_DrawFans ) + ImeUiCallback_DrawFans( PieData, 17 ); + + float fHeight = gSkinIME.symbolHeight * 0.625f; + + // fix for Ent Gen #120 - reduce the height of character when Korean IME is on + if( GETPRIMLANG() == LANG_KOREAN && bOn ) + { + fHeight *= 0.8f; + } + + if( gSkinIME.symbolFont ) + { +#ifdef DS2 + // save the font height here since DS2 shares editbox font and indicator font + DWORD _w, _h; + g_CaretInfo.pFont->GetTextExtent( TEXT(" "), &_w, &_h ); +#endif //DS2 + + // GOS deals height in points that is 1/72nd inch and assumes display device is 96dpi. + fHeight = fHeight * 96 / 72; + gSkinIME.symbolFont->SetHeight( ( UINT )fHeight ); + gSkinIME.symbolFont->SetColor( ( ( ( DWORD )gSkinIME.symbolTranslucence ) << 24 ) | gSkinIME.symbolColorText ); + + // + // draw the proper symbol over the fan + // + DWORD w, h; + LPCTSTR cszSymbol = ( g_dwState == IMEUI_STATE_ON ) ? g_pszIndicatior : g_aszIndicator[0]; + + gSkinIME.symbolFont->GetTextExtent( cszSymbol, &w, &h ); + gSkinIME.symbolFont->SetPosition( ( int )( PieData[0].sx ) - w / 2, ( int )( PieData[0].sy ) - h / 2 ); + gSkinIME.symbolFont->DrawText( cszSymbol ); + +#ifdef DS2 + // revert the height. + g_CaretInfo.pFont->SetHeight( _h ); + + // Double-check: Confirm match by testing a range of font heights to find best fit + DWORD _h2; + g_CaretInfo.pFont->GetTextExtent( TEXT(" "), &_w, &_h2 ); + if ( _h2 < _h ) + { + for ( int i=1; _h2<_h && i<10; i++ ) + { + g_CaretInfo.pFont->SetHeight( _h+i ); + g_CaretInfo.pFont->GetTextExtent( TEXT(" "), &_w, &_h2 ); + } + } + else if ( _h2 > _h ) + { + for ( int i=1; _h2>_h && i<10; i++ ) + { + g_CaretInfo.pFont->SetHeight( _h-i ); + g_CaretInfo.pFont->GetTextExtent( TEXT(" "), &_w, &_h2 ); + } + } +#endif //DS2 + } +} + +static void DrawCompositionString( _In_ bool bDrawCompAttr ) +{ + // Process timer for caret blink + UINT uCurrentTime = GetTickCount(); + if( uCurrentTime - g_uCaretBlinkLast > g_uCaretBlinkTime ) + { + g_uCaretBlinkLast = uCurrentTime; + g_bCaretDraw = !g_bCaretDraw; + } + + int i = 0; + + g_CaretInfo.pFont->SetColor( g_CaretInfo.colorComp ); + + DWORD uDummy; + + int len = (int)wcslen( g_szCompositionString ); + + DWORD bgX = g_CaretInfo.caretX; + DWORD bgY = g_CaretInfo.caretY; + g_dwCaretX = POSITION_UNINITIALIZED; + g_dwCaretY = POSITION_UNINITIALIZED; + DWORD candX = POSITION_UNINITIALIZED; + DWORD candY = 0; + LPTSTR pszMlcs = g_szMultiLineCompString; + + DWORD wCompChar = 0; + DWORD hCompChar = 0; + g_CaretInfo.pFont->GetTextExtent( TEXT( " " ), &uDummy, &hCompChar ); + if( g_dwIMELevel == 3 && g_IMECursorBytes && g_szCompositionString[0] ) + { + // shift starting point of drawing composition string according to the current caret position. + TCHAR temp = g_szCompositionString[g_IMECursorBytes]; + g_szCompositionString[g_IMECursorBytes] = 0; + g_CaretInfo.pFont->GetTextExtent( g_szCompositionString, &wCompChar, &hCompChar ); + g_szCompositionString[g_IMECursorBytes] = temp; + bgX -= wCompChar; + } + + // + // Draw the background colors for IME text nuggets + // + bool saveCandPos = false; + DWORD cType = 1; + LPTSTR pszCurrentCompLine = g_szCompositionString; + DWORD dwCompLineStart = bgX; + DWORD bgXnext = bgX; + + if( GETPRIMLANG() != LANG_KOREAN || g_bCaretDraw ) // Korean uses composition attribute as blinking block caret + for( i = 0; i < len; i += cType ) + { + DWORD bgColor = 0x00000000; + TCHAR szChar[3]; + szChar[0] = g_szCompositionString[i]; + szChar[1] = szChar[2] = 0; + bgX = bgXnext; + TCHAR cSave = g_szCompositionString[i + cType]; + g_szCompositionString[i + cType] = 0; + g_CaretInfo.pFont->GetTextExtent( pszCurrentCompLine, &bgXnext, &hCompChar ); + g_szCompositionString[i + cType] = cSave; + bgXnext += dwCompLineStart; + wCompChar = bgXnext - bgX; + + switch( g_szCompAttrString[i] ) + { + case ATTR_INPUT: + bgColor = gSkinCompStr.colorInput; + break; + case ATTR_TARGET_CONVERTED: + bgColor = gSkinCompStr.colorTargetConv; + if( IMEID_LANG( GetImeId() ) != LANG_CHS ) + saveCandPos = true; + break; + case ATTR_CONVERTED: + bgColor = gSkinCompStr.colorConverted; + break; + case ATTR_TARGET_NOTCONVERTED: + // + // This is the one the user is working with currently + // + bgColor = gSkinCompStr.colorTargetNotConv; + break; + case ATTR_INPUT_ERROR: + bgColor = gSkinCompStr.colorInputErr; + break; + default: + // STOP( TEXT( "Attributes on IME characters are wrong" ) ); + break; + } + + if( g_dwIMELevel == 3 && bDrawCompAttr ) + { + if( ( LONG )bgX >= g_CaretInfo.margins.left && ( LONG )bgX <= g_CaretInfo.margins.right ) + { + if( g_dwImeUiFlags & IMEUI_FLAG_SUPPORT_CARET ) + { + if( ImeUiCallback_DrawRect ) + ImeUiCallback_DrawRect( bgX, bgY, bgX + wCompChar, bgY + hCompChar, bgColor ); + } + else + { + if( ImeUiCallback_DrawRect ) + ImeUiCallback_DrawRect( bgX - wCompChar, bgY, bgX, bgY + hCompChar, bgColor ); + } + } + } + else if( g_dwIMELevel == 2 ) + { + // make sure enough buffer space (possible space, NUL for current line, possible DBCS, 2 more NUL) + // are available in multiline composition string buffer + bool bWrite = ( pszMlcs - g_szMultiLineCompString < + COUNTOF( g_szMultiLineCompString ) - 5 * ( 3 - sizeof( TCHAR ) ) ); + + if( ( LONG )( bgX + wCompChar ) >= g_CaretInfo.margins.right ) + { + bgX = dwCompLineStart = bgXnext = g_CaretInfo.margins.left; + bgY = bgY + hCompChar; + pszCurrentCompLine = g_szCompositionString + i; + if( bWrite ) + { + if( pszMlcs == g_szMultiLineCompString || pszMlcs[-1] == 0 ) + *pszMlcs++ = ' '; // to avoid zero length line + *pszMlcs++ = 0; + } + } + if( ImeUiCallback_DrawRect ) + ImeUiCallback_DrawRect( bgX, bgY, bgX + wCompChar, bgY + hCompChar, bgColor ); + if( bWrite ) + { + *pszMlcs++ = g_szCompositionString[i]; + } + if( ( DWORD )i == g_IMECursorBytes ) + { + g_dwCaretX = bgX; + g_dwCaretY = bgY; + } + } + if( ( saveCandPos && candX == POSITION_UNINITIALIZED ) || + ( IMEID_LANG( GetImeId() ) == LANG_CHS && i / ( 3 - sizeof( TCHAR ) ) == ( int )g_IMECursorChars ) ) + { + candX = bgX; + candY = bgY; + } + saveCandPos = false; + } + + bgX = bgXnext; + if( g_dwIMELevel == 2 ) + { + // in case the caret in composition string is at the end of it, draw it here + if( len != 0 && ( DWORD )i == g_IMECursorBytes ) + { + g_dwCaretX = bgX; + g_dwCaretY = bgY; + } + + // Draw composition string. + //assert(pszMlcs - g_szMultiLineCompString <= + // sizeof(g_szMultiLineCompString) / sizeof(g_szMultiLineCompString[0]) - 2); + *pszMlcs++ = 0; + *pszMlcs++ = 0; + DWORD x, y; + x = g_CaretInfo.caretX; + y = g_CaretInfo.caretY; + pszMlcs = g_szMultiLineCompString; + while( *pszMlcs && + pszMlcs - g_szMultiLineCompString < sizeof( g_szMultiLineCompString ) / sizeof + ( g_szMultiLineCompString[0] ) ) + { + g_CaretInfo.pFont->SetPosition( x, y ); + g_CaretInfo.pFont->DrawText( pszMlcs ); + pszMlcs += wcslen( pszMlcs ) + 1; + x = g_CaretInfo.margins.left; + y += hCompChar; + } + } + // for changing z-order of caret + if( g_dwCaretX != POSITION_UNINITIALIZED && g_dwCaretY != POSITION_UNINITIALIZED ) + { + DrawCaret( g_dwCaretX, g_dwCaretY, hCompChar ); + } + g_dwCandX = candX; + g_dwCandY = candY; + g_hCompChar = hCompChar; +} + +static void DrawCandidateList() +{ + assert( g_CaretInfo.pFont != nullptr ); + _Analysis_assume_( g_CaretInfo.pFont != nullptr ); + DWORD candX = g_dwCandX; + DWORD candY = g_dwCandY; + DWORD hCompChar = g_hCompChar; + int i; + + // draw candidate list / reading window + if( !g_dwCount || g_szCandidate[0][0] == 0 ) + { + return; + } + + // If position of candidate list is not initialized yet, set it here. + if( candX == POSITION_UNINITIALIZED ) + { + // CHT IME in Vista doesn't have ATTR_TARGET_CONVERTED attribute while typing, + // so display the candidate list near the caret in the composition string + if( GETLANG() == LANG_CHT && GetImeId() != 0 && g_dwCaretX != POSITION_UNINITIALIZED ) + { + candX = g_dwCaretX; + candY = g_dwCaretY; + } + else + { + candX = g_CaretInfo.caretX; + candY = g_CaretInfo.caretY; + } + } + + SIZE largest = + { + 0,0 + }; + + static DWORD uDigitWidth = 0; + DWORD uSpaceWidth = 0; + static DWORD uDigitWidthList[10]; + static CImeUiFont_Base* pPrevFont = nullptr; + // find out the widest width of the digits + if( pPrevFont != g_CaretInfo.pFont ) + { + pPrevFont = g_CaretInfo.pFont; + for( int cnt = 0; cnt <= 9; cnt++ ) + { + DWORD uDW = 0; + DWORD uDH = 0; + TCHAR ss[8]; + swprintf_s( ss, COUNTOF(ss), TEXT( "%d" ), cnt ); + g_CaretInfo.pFont->GetTextExtent( ss, &uDW, &uDH ); + uDigitWidthList[cnt] = uDW; + if( uDW > uDigitWidth ) + uDigitWidth = uDW; + if( ( signed )uDH > largest.cy ) + largest.cy = uDH; + } + } + uSpaceWidth = uDigitWidth; + DWORD dwMarginX = ( uSpaceWidth + 1 ) / 2; + DWORD adwCandWidth[ MAX_CANDLIST ]; + + // Find out the widest width of the candidate strings + DWORD dwCandWidth = 0; + if( g_bReadingWindow && g_bHorizontalReading ) + g_CaretInfo.pFont->GetTextExtent( g_szReadingString, ( DWORD* )&largest.cx, ( DWORD* )&largest.cy ); + else + { + for( i = 0; g_szCandidate[i][0] && i < ( int )g_uCandPageSize; i++ ) + { + DWORD tx = 0; + DWORD ty = 0; + + if( g_bReadingWindow ) + g_CaretInfo.pFont->GetTextExtent( g_szCandidate[i], &tx, &ty ); + else + { + if( g_bVerticalCand ) + g_CaretInfo.pFont->GetTextExtent( g_szCandidate[i] + 2, &tx, &ty ); + else + g_CaretInfo.pFont->GetTextExtent( g_szCandidate[i] + 1, &tx, &ty ); + tx = tx + uDigitWidth + uSpaceWidth; + } + + if( ( signed )tx > largest.cx ) + largest.cx = tx; + if( ( signed )ty > largest.cy ) + largest.cy = ty; + adwCandWidth[ i ] = tx; + dwCandWidth += tx; + } + } + + DWORD slotsUsed; + if( g_bReadingWindow && g_dwCount < g_uCandPageSize ) + slotsUsed = g_dwCount; + else + slotsUsed = g_uCandPageSize; + + // Show candidate list above composition string if there isn't enough room below. + DWORD dwCandHeight; + if( g_bVerticalCand && !( g_bReadingWindow && g_bHorizontalReading ) ) + dwCandHeight = slotsUsed * largest.cy + 2; + else + dwCandHeight = largest.cy + 2; + if( candY + hCompChar + dwCandHeight > g_screenHeight ) + candY -= dwCandHeight; + else + candY += hCompChar; + if( ( int )candY < 0 ) + candY = 0; + + // Move candidate list horizontally to keep it inside of screen + if( !g_bReadingWindow && IMEID_LANG( GetImeId() ) == LANG_CHS ) + dwCandWidth += dwMarginX * ( slotsUsed - 1 ); + else if( g_bReadingWindow && g_bHorizontalReading ) + dwCandWidth = largest.cx + 2 + dwMarginX * 2; + else if( g_bVerticalCand || g_bReadingWindow ) + dwCandWidth = largest.cx + 2 + dwMarginX * 2; + else + dwCandWidth = slotsUsed * ( largest.cx + 1 ) + 1; + if( candX + dwCandWidth > g_screenWidth ) + candX = g_screenWidth - dwCandWidth; + if( ( int )candX < 0 ) + candX = 0; + + // Draw frame and background of candidate list / reading window + int seperateLineX = 0; + int left = candX; + int top = candY; + int right = candX + dwCandWidth; + int bottom = candY + dwCandHeight; + if( ImeUiCallback_DrawRect ) + ImeUiCallback_DrawRect( left, top, right, bottom, gSkinIME.candColorBorder ); + left++; + top++; + right--; + bottom--; + if( g_bReadingWindow || IMEID_LANG( GetImeId() ) == LANG_CHS ) + { + if( ImeUiCallback_DrawRect ) + ImeUiCallback_DrawRect( left, top, right, bottom, gSkinIME.candColorBase ); + } + else if( g_bVerticalCand ) + { + // uDigitWidth is the max width of all digits. + if( !g_bReadingWindow ) + { + seperateLineX = left + dwMarginX + uDigitWidth + uSpaceWidth / 2; + if( ImeUiCallback_DrawRect ) + { + ImeUiCallback_DrawRect( left, top, seperateLineX - 1, bottom, gSkinIME.candColorBase ); + ImeUiCallback_DrawRect( seperateLineX, top, right, bottom, gSkinIME.candColorBase ); + } + } + } + else + { + for( i = 0; ( DWORD )i < slotsUsed; i++ ) + { + if( ImeUiCallback_DrawRect ) + ImeUiCallback_DrawRect( left, top, left + largest.cx, bottom, gSkinIME.candColorBase ); + left += largest.cx + 1; + } + } + + // Draw candidates / reading strings + candX++; + candY++; + if( g_bReadingWindow && g_bHorizontalReading ) + { + int iStart = -1, iEnd = -1, iDummy; + candX += dwMarginX; + + // draw background of error character if it exists + TCHAR szTemp[COUNTOF( g_szReadingString ) ]; + if( g_iReadingError >= 0 ) + { + wcscpy_s( szTemp, COUNTOF(szTemp), g_szReadingString ); + LPTSTR psz = szTemp + g_iReadingError; + psz++; + *psz = 0; + g_CaretInfo.pFont->GetTextExtent( szTemp, ( DWORD* )&iEnd, ( DWORD* )&iDummy ); + TCHAR cSave = szTemp[ g_iReadingError ]; + szTemp[g_iReadingError] = 0; + g_CaretInfo.pFont->GetTextExtent( szTemp, ( DWORD* )&iStart, ( DWORD* )&iDummy ); + szTemp[g_iReadingError] = cSave; + if( ImeUiCallback_DrawRect ) + ImeUiCallback_DrawRect( candX + iStart, candY, candX + iEnd, candY + largest.cy, + gSkinIME.candColorBorder ); + } + + g_CaretInfo.pFont->SetPosition( candX, candY ); + g_CaretInfo.pFont->SetColor( g_CaretInfo.colorCand ); + g_CaretInfo.pFont->DrawText( g_szReadingString ); + + // draw error character if it exists + if( iStart >= 0 ) + { + g_CaretInfo.pFont->SetPosition( candX + iStart, candY ); + if( gSkinIME.candColorBase != 0xffffffff || gSkinIME.candColorBorder != 0xff000000 ) + g_CaretInfo.pFont->SetColor( g_CaretInfo.colorCand ); + else + g_CaretInfo.pFont->SetColor( 0xff000000 + ( ~( ( 0x00ffffff ) & g_CaretInfo.colorCand ) ) ); + g_CaretInfo.pFont->DrawText( szTemp + g_iReadingError ); + } + } + else + { + for( i = 0; i < ( int )g_uCandPageSize && ( DWORD )i < g_dwCount; i++ ) + { + if( g_dwSelection == ( DWORD )i ) + { + if( gSkinIME.candColorBase != 0xffffffff || gSkinIME.candColorBorder != 0xff000000 ) + g_CaretInfo.pFont->SetColor( g_CaretInfo.colorCand ); + else + g_CaretInfo.pFont->SetColor( 0xff000000 + ( ~( ( 0x00ffffff ) & g_CaretInfo.colorCand ) ) ); + + if( ImeUiCallback_DrawRect ) + { + if( g_bReadingWindow || g_bVerticalCand ) + ImeUiCallback_DrawRect( candX, candY + i * largest.cy, + candX - 1 + dwCandWidth, candY + ( i + 1 ) * largest.cy, + gSkinIME.candColorBorder ); + else + ImeUiCallback_DrawRect( candX, candY, + candX + adwCandWidth[i], candY + largest.cy, + gSkinIME.candColorBorder ); + } + } + else + g_CaretInfo.pFont->SetColor( g_CaretInfo.colorCand ); + if( g_szCandidate[i][0] != 0 ) + { + if( !g_bReadingWindow && g_bVerticalCand ) + { + TCHAR szOneDigit[2] = + { + g_szCandidate[i][0], 0 + }; + int nOneDigit = g_szCandidate[i][0] - TEXT( '0' ); + TCHAR* szCandidateBody = g_szCandidate[i] + 2; + + int dx = candX + ( seperateLineX - candX - uDigitWidthList[nOneDigit] ) / 2; + int dy = candY + largest.cy * i; + + g_CaretInfo.pFont->SetPosition( dx, dy ); + g_CaretInfo.pFont->DrawText( szOneDigit ); + g_CaretInfo.pFont->SetPosition( seperateLineX + dwMarginX, dy ); + g_CaretInfo.pFont->DrawText( szCandidateBody ); + } + else if( g_bReadingWindow ) + { + g_CaretInfo.pFont->SetPosition( dwMarginX + candX, candY + i * largest.cy ); + g_CaretInfo.pFont->DrawText( g_szCandidate[i] ); + } + else + { + g_CaretInfo.pFont->SetPosition( uSpaceWidth / 2 + candX, candY ); + g_CaretInfo.pFont->DrawText( g_szCandidate[i] ); + } + } + if( !g_bReadingWindow && !g_bVerticalCand ) + { + if( IMEID_LANG( GetImeId() ) == LANG_CHS ) + candX += adwCandWidth[i] + dwMarginX; + else + candX += largest.cx + 1; + } + } + } +} + +static void CloseCandidateList() +{ + g_bCandList = false; + if( !g_bReadingWindow ) // fix for Ent Gen #120. + { + g_dwCount = 0; + memset( &g_szCandidate, 0, sizeof( g_szCandidate ) ); + } +} + +// +// ProcessIMEMessages() +// Processes IME related messages and acquire information +// +#pragma warning(push) +#pragma warning( disable : 4616 6305 ) +_Use_decl_annotations_ +LPARAM ImeUi_ProcessMessage( HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM& lParam, bool* trapped ) +{ + HIMC himc; + int len; + static LPARAM lAlt = 0x80000000, lCtrl = 0x80000000, lShift = 0x80000000; + + *trapped = false; + if( !g_bInitialized || g_bDisableImeCompletely ) + { + return 0; + } + + switch( uMsg ) + { + // + // IME Handling + // + case WM_INPUTLANGCHANGE: + OnInputLangChange(); + break; + + case WM_IME_SETCONTEXT: + // + // We don't want anything to display, so we have to clear lParam and pass it to DefWindowProc(). + // Expecially important in Vista to receive IMN_CHANGECANDIDATE correctly. + // + lParam = 0; + break; + + case WM_IME_STARTCOMPOSITION: + InitCompStringData(); + *trapped = true; + break; + + case WM_IME_COMPOSITION: + { + LONG lRet; + TCHAR szCompStr[COUNTOF(g_szCompositionString)]; + + *trapped = true; + himc = ImmGetContext( hWnd ); + if( !himc ) + { + break; + } + + // ResultStr must be processed before composition string. + if( lParam & GCS_RESULTSTR ) + { + lRet = ( LONG )_ImmGetCompositionString( himc, GCS_RESULTSTR, szCompStr, + COUNTOF( szCompStr ) ) / sizeof( TCHAR ); + szCompStr[lRet] = 0; + CancelCompString( g_hwndCurr, false, GetCharCount( szCompStr ) ); + wcscpy_s( g_szCompositionString, COUNTOF(g_szCompositionString), szCompStr ); + _SendCompString(); + InitCompStringData(); + } + // + // Reads in the composition string. + // + if( lParam & GCS_COMPSTR ) + { + ////////////////////////////////////////////////////// + // Retrieve the latest user-selected IME candidates + lRet = ( LONG )_ImmGetCompositionString( himc, GCS_COMPSTR, szCompStr, + COUNTOF( szCompStr ) ) / sizeof( TCHAR ); + szCompStr[lRet] = 0; + // + // Remove the whole of the string + // + CancelCompString( g_hwndCurr, false, GetCharCount( szCompStr ) ); + + wcscpy_s( g_szCompositionString, COUNTOF(g_szCompositionString), szCompStr ); + lRet = _ImmGetCompositionString( himc, GCS_COMPATTR, g_szCompAttrString, + COUNTOF( g_szCompAttrString ) ); + g_szCompAttrString[lRet] = 0; + // Older CHT IME uses composition string for reading string + if( GETLANG() == LANG_CHT && !GetImeId() ) + { + int i, chars = (int)wcslen( g_szCompositionString ) / ( 3 - sizeof( TCHAR ) ); + if( chars ) + { + g_dwCount = 4; + g_dwSelection = ( DWORD )-1; // don't select any candidate + + for( i = 3; i >= 0; i-- ) + { + if( i > chars - 1 ) + g_szCandidate[i][0] = 0; + else + { + g_szCandidate[i][0] = g_szCompositionString[i]; + g_szCandidate[i][1] = 0; + } + } + g_uCandPageSize = MAX_CANDLIST; + memset( g_szCompositionString, 0, 8 ); + g_bReadingWindow = true; + GetReadingWindowOrientation( 0 ); + if( g_bHorizontalReading ) + { + g_iReadingError = -1; + g_szReadingString[0] = 0; + for( i = 0; i < ( int )g_dwCount; i++ ) + { + if( g_dwSelection == ( DWORD )i ) + g_iReadingError = (int)wcslen( g_szReadingString ); + LPCTSTR pszTmp = g_szCandidate[i]; + wcscat_s( g_szReadingString, COUNTOF(g_szReadingString), pszTmp ); + } + } + } + else + g_dwCount = 0; + } + + // get caret position in composition string + g_IMECursorBytes = _ImmGetCompositionString( himc, GCS_CURSORPOS, nullptr, 0 ); + g_IMECursorChars = GetCharCountFromBytes( g_szCompositionString, g_IMECursorBytes ); + + if( g_dwIMELevel == 3 ) + { + // send composition string via WM_CHAR + _SendCompString(); + // move caret to appropreate location + len = GetCharCount( g_szCompositionString + g_IMECursorBytes ); + SendControlKeys( VK_LEFT, len ); + } + } + _ImmReleaseContext( hWnd, himc ); + } + break; + + case WM_IME_ENDCOMPOSITION: + CancelCompString( g_hwndCurr ); + InitCompStringData(); + break; + + case WM_IME_NOTIFY: + switch( wParam ) + { + case IMN_SETCONVERSIONMODE: + { + // Disable CHT IME software keyboard. + static bool bNoReentrance = false; + if( LANG_CHT == GETLANG() && !bNoReentrance ) + { + bNoReentrance = true; + DWORD dwConvMode, dwSentMode; + _ImmGetConversionStatus( g_himcOrg, &dwConvMode, &dwSentMode ); + const DWORD dwFlag = IME_CMODE_SOFTKBD | IME_CMODE_SYMBOL; + if( dwConvMode & dwFlag ) + _ImmSetConversionStatus( g_himcOrg, dwConvMode & ~dwFlag, dwSentMode ); + } + bNoReentrance = false; + } + // fall through + case IMN_SETOPENSTATUS: + if( g_bUILessMode ) + break; + CheckToggleState(); + break; + + case IMN_OPENCANDIDATE: + case IMN_CHANGECANDIDATE: + if( g_bUILessMode ) + { + break; + } + { + g_bCandList = true; + *trapped = true; + himc = _ImmGetContext( hWnd ); + if( !himc ) + break; + + LPCANDIDATELIST lpCandList; + DWORD dwIndex, dwBufLen; + + g_bReadingWindow = false; + dwIndex = 0; + dwBufLen = _GetCandidateList( himc, dwIndex, &lpCandList ); + + if( dwBufLen ) + { + g_dwSelection = lpCandList->dwSelection; + g_dwCount = lpCandList->dwCount; + + int startOfPage = 0; + if( GETLANG() == LANG_CHS && GetImeId() ) + { + // MSPY (CHS IME) has variable number of candidates in candidate window + // find where current page starts, and the size of current page + const int maxCandChar = 18 * ( 3 - sizeof( TCHAR ) ); + UINT cChars = 0; + UINT i; + for( i = 0; i < g_dwCount; i++ ) + { + UINT uLen = (int)wcslen( + ( LPTSTR )( (UINT_PTR)lpCandList + lpCandList->dwOffset[i] ) ) + + ( 3 - sizeof( TCHAR ) ); + if( uLen + cChars > maxCandChar ) + { + if( i > g_dwSelection ) + { + break; + } + startOfPage = i; + cChars = uLen; + } + else + { + cChars += uLen; + } + } + g_uCandPageSize = i - startOfPage; + } + else + { + g_uCandPageSize = std::min( lpCandList->dwPageSize, MAX_CANDLIST ); + startOfPage = g_bUILessMode ? lpCandList->dwPageStart : + ( g_dwSelection / g_uCandPageSize ) * g_uCandPageSize; + } + + g_dwSelection = ( GETLANG() == LANG_CHS && !GetImeId() ) ? ( DWORD )-1 + : g_dwSelection - startOfPage; + + memset( &g_szCandidate, 0, sizeof( g_szCandidate ) ); + for( UINT i = startOfPage, j = 0; + ( DWORD )i < lpCandList->dwCount && j < g_uCandPageSize; + i++, j++ ) + { + ComposeCandidateLine( j, + ( LPTSTR )( (UINT_PTR)lpCandList + lpCandList->dwOffset[i] ) ); + } + ImeUiCallback_Free( ( HANDLE )lpCandList ); + _ImmReleaseContext( hWnd, himc ); + + // don't display selection in candidate list in case of Korean and old Chinese IME. + if( GETPRIMLANG() == LANG_KOREAN || + GETLANG() == LANG_CHT && !GetImeId() ) + g_dwSelection = ( DWORD )-1; + } + break; + } + + case IMN_CLOSECANDIDATE: + if( g_bUILessMode ) + { + break; + } + CloseCandidateList(); + *trapped = true; + break; + + // Jun.16,2000 05:21 by yutaka. + case IMN_PRIVATE: + { + if( !g_bCandList ) + { + GetReadingString( hWnd ); + } + // Trap some messages to hide reading window + DWORD dwId = GetImeId(); + switch( dwId ) + { + case IMEID_CHT_VER42: + case IMEID_CHT_VER43: + case IMEID_CHT_VER44: + case IMEID_CHS_VER41: + case IMEID_CHS_VER42: + if( ( lParam == 1 ) || ( lParam == 2 ) ) + { + *trapped = true; + } + break; + case IMEID_CHT_VER50: + case IMEID_CHT_VER51: + case IMEID_CHT_VER52: + case IMEID_CHT_VER60: + case IMEID_CHS_VER53: + if( ( lParam == 16 ) || ( lParam == 17 ) || ( lParam == 26 ) || ( lParam == 27 ) || + ( lParam == 28 ) ) + { + *trapped = true; + } + break; + } + } + break; + + default: + *trapped = true; + break; + } + break; + + // fix for #15386 - When Text Service Framework is installed in Win2K, Alt+Shift and Ctrl+Shift combination (to switch + // input locale / keyboard layout) doesn't send WM_KEYUP message for the key that is released first. We need to check + // if these keys are actually up whenever we receive key up message for other keys. + case WM_KEYUP: + case WM_SYSKEYUP: + if( !( lAlt & 0x80000000 ) && wParam != VK_MENU && ( GetAsyncKeyState( VK_MENU ) & 0x8000 ) == 0 ) + { + PostMessageA( GetFocus(), WM_KEYUP, ( WPARAM )VK_MENU, ( lAlt & 0x01ff0000 ) | 0xC0000001 ); + } + else if( !( lCtrl & 0x80000000 ) && wParam != VK_CONTROL && + ( GetAsyncKeyState( VK_CONTROL ) & 0x8000 ) == 0 ) + { + PostMessageA( GetFocus(), WM_KEYUP, ( WPARAM )VK_CONTROL, ( lCtrl & 0x01ff0000 ) | 0xC0000001 ); + } + else if( !( lShift & 0x80000000 ) && wParam != VK_SHIFT && ( GetAsyncKeyState( VK_SHIFT ) & 0x8000 ) == 0 ) + { + PostMessageA( GetFocus(), WM_KEYUP, ( WPARAM )VK_SHIFT, ( lShift & 0x01ff0000 ) | 0xC0000001 ); + } + // fall through WM_KEYDOWN / WM_SYSKEYDOWN + case WM_KEYDOWN: + case WM_SYSKEYDOWN: + { + switch( wParam ) + { + case VK_MENU: + lAlt = lParam; + break; + case VK_SHIFT: + lShift = lParam; + break; + case VK_CONTROL: + lCtrl = lParam; + break; + } + } + break; + } + return 0; +} +#pragma warning(pop) + +_Use_decl_annotations_ +void ImeUi_SetCaretPosition( UINT x, UINT y ) +{ + if( !g_bInitialized ) + return; + g_CaretInfo.caretX = x; + g_CaretInfo.caretY = y; +} + +_Use_decl_annotations_ +void ImeUi_SetCompStringAppearance( CImeUiFont_Base* pFont, DWORD color, const RECT* prc ) +{ + if( !g_bInitialized ) + return; + g_CaretInfo.pFont = pFont; + g_CaretInfo.margins = *prc; + + if( 0 == gSkinIME.candColorText ) + g_CaretInfo.colorCand = color; + else + g_CaretInfo.colorCand = gSkinIME.candColorText; + if( 0 == gSkinIME.compColorText ) + g_CaretInfo.colorComp = color; + else + g_CaretInfo.colorComp = gSkinIME.compColorText; +} + +void ImeUi_SetState( _In_ DWORD dwState ) +{ + if( !g_bInitialized ) + return; + HIMC himc; + if( dwState == IMEUI_STATE_ON ) + { + ImeUi_EnableIme( true ); + } + himc = _ImmGetContext( g_hwndCurr ); + if( himc ) + { + if( g_bDisableImeCompletely ) + dwState = IMEUI_STATE_OFF; + + bool bOn = dwState == IMEUI_STATE_ON; // for non-Chinese IME + switch( GETPRIMLANG() ) + { + case LANG_CHINESE: + { + // toggle Chinese IME + DWORD dwId; + DWORD dwConvMode = 0, dwSentMode = 0; + if( ( g_bChineseIME && dwState == IMEUI_STATE_OFF ) || + ( !g_bChineseIME && dwState != IMEUI_STATE_OFF ) ) + { + _ImmSimulateHotKey( g_hwndCurr, IME_THOTKEY_IME_NONIME_TOGGLE ); + _PumpMessage(); + } + if( dwState != IMEUI_STATE_OFF ) + { + dwId = GetImeId(); + if( dwId ) + { + _ImmGetConversionStatus( himc, &dwConvMode, &dwSentMode ); + dwConvMode = ( dwState == IMEUI_STATE_ON ) + ? ( dwConvMode | IME_CMODE_NATIVE ) + : ( dwConvMode & ~IME_CMODE_NATIVE ); + _ImmSetConversionStatus( himc, dwConvMode, dwSentMode ); + } + } + break; + } + case LANG_KOREAN: + // toggle Korean IME + if( ( bOn && g_dwState != IMEUI_STATE_ON ) || ( !bOn && g_dwState == IMEUI_STATE_ON ) ) + { + _ImmSimulateHotKey( g_hwndCurr, IME_KHOTKEY_ENGLISH ); + } + break; + case LANG_JAPANESE: + _ImmSetOpenStatus( himc, bOn ); + break; + } + _ImmReleaseContext( g_hwndCurr, himc ); + CheckToggleState(); + } +} + +DWORD ImeUi_GetState() +{ + if( !g_bInitialized ) + return IMEUI_STATE_OFF; + CheckToggleState(); + return g_dwState; +} + +void ImeUi_EnableIme( _In_ bool bEnable ) +{ + if( !g_bInitialized || !g_hwndCurr ) + return; + if( g_bDisableImeCompletely ) + bEnable = false; + + if( g_hwndCurr == g_hwndMain ) + { + HIMC himcDbg; + himcDbg = _ImmAssociateContext( g_hwndCurr, bEnable? g_himcOrg : nullptr ); + } + g_bImeEnabled = bEnable; + if( bEnable ) + { + CheckToggleState(); + } + CTsfUiLessMode::EnableUiUpdates( bEnable ); +} + +bool ImeUi_IsEnabled() +{ + return g_bImeEnabled; +} + +bool ImeUi_Initialize(_In_ HWND hwnd, _In_ bool bDisable ) +{ + if( g_bInitialized ) + { + return true; + } + g_hwndMain = hwnd; + g_disableCicero.Initialize(); + + g_hImmDll = LoadLibraryEx( L"imm32.dll", nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + g_bDisableImeCompletely = false; + + if( g_hImmDll ) + { + _ImmLockIMC = reinterpret_cast( reinterpret_cast( GetProcAddress( g_hImmDll, "ImmLockIMC" ) ) ); + _ImmUnlockIMC = reinterpret_cast( reinterpret_cast( GetProcAddress( g_hImmDll, "ImmUnlockIMC" ) ) ); + _ImmLockIMCC = reinterpret_cast( reinterpret_cast( GetProcAddress( g_hImmDll, "ImmLockIMCC" ) ) ); + _ImmUnlockIMCC = reinterpret_cast( reinterpret_cast( GetProcAddress( g_hImmDll, "ImmUnlockIMCC" ) ) ); + BOOL ( WINAPI* _ImmDisableTextFrameService )( DWORD ) = reinterpret_cast( reinterpret_cast( GetProcAddress( g_hImmDll, + "ImmDisableTextFrameService" ) ) ); + if( _ImmDisableTextFrameService ) + { + _ImmDisableTextFrameService( ( DWORD )-1 ); + } + } + else + { + g_bDisableImeCompletely = true; + return false; + } + _ImmGetCompositionString = ImmGetCompositionStringW; + _ImmGetCandidateList = ImmGetCandidateListW; + _GetCandidateList = GetCandidateList; + _SendCompString = SendCompString; + _SendMessage = SendMessageW; + + // turn init flag on so that subsequent calls to ImeUi functions work. + g_bInitialized = true; + + ImeUi_SetWindow( g_hwndMain ); + g_himcOrg = _ImmGetContext( g_hwndMain ); + _ImmReleaseContext( g_hwndMain, g_himcOrg ); + + if( !g_himcOrg ) + { + bDisable = true; + } + + // the following pointers to function has to be initialized before this function is called. + if( bDisable || + !ImeUiCallback_Malloc || + !ImeUiCallback_Free + ) + { + g_bDisableImeCompletely = true; + ImeUi_EnableIme( false ); + g_bInitialized = bDisable; + return false; + } + + g_uCaretBlinkTime = GetCaretBlinkTime(); + + g_CaretInfo.caretX = 0; + g_CaretInfo.caretY = 0; + g_CaretInfo.pFont = 0; + g_CaretInfo.colorComp = 0; + g_CaretInfo.colorCand = 0; + g_CaretInfo.margins.left = 0; + g_CaretInfo.margins.right = 640; + g_CaretInfo.margins.top = 0; + g_CaretInfo.margins.bottom = 480; + + CheckInputLocale(); + OnInputLangChangeWorker(); + ImeUi_SetSupportLevel( 2 ); + + // SetupTSFSinks has to be called before CheckToggleState to make it work correctly. + g_bUILessMode = CTsfUiLessMode::SetupSinks() != FALSE; + CheckToggleState(); + if( g_bUILessMode ) + { + g_bChineseIME = ( GETPRIMLANG() == LANG_CHINESE ) && CTsfUiLessMode::CurrentInputLocaleIsIme(); + CTsfUiLessMode::UpdateImeState(); + } + ImeUi_EnableIme( false ); + + return true; +} + +void ImeUi_Uninitialize() +{ + if( !g_bInitialized ) + { + return; + } + CTsfUiLessMode::ReleaseSinks(); + if( g_hwndMain ) + { + ImmAssociateContext( g_hwndMain, g_himcOrg ); + } + g_hwndMain = nullptr; + g_himcOrg = nullptr; + if( g_hImmDll ) + { + FreeLibrary( g_hImmDll ); + g_hImmDll = nullptr; + } + g_disableCicero.Uninitialize(); + g_bInitialized = false; +} + +// +// GetImeId( UINT uIndex ) +// returns +// returned value: +// 0: In the following cases +// - Non Chinese IME input locale +// - Older Chinese IME +// - Other error cases +// +// Othewise: +// When uIndex is 0 (default) +// bit 31-24: Major version +// bit 23-16: Minor version +// bit 15-0: Language ID +// When uIndex is 1 +// pVerFixedInfo->dwFileVersionLS +// +// Use IMEID_VER and IMEID_LANG macro to extract version and language information. +// +static DWORD GetImeId( _In_ UINT uIndex ) +{ + static HKL hklPrev = 0; + static DWORD dwRet[2] = + { + 0, 0 + }; + + DWORD dwVerSize; + DWORD dwVerHandle; + LPVOID lpVerBuffer; + LPVOID lpVerData; + UINT cbVerData; + char szTmp[1024]; + + if( uIndex >= sizeof( dwRet ) / sizeof( dwRet[0] ) ) + return 0; + + HKL kl = g_hklCurrent; + if( hklPrev == kl ) + { + return dwRet[uIndex]; + } + hklPrev = kl; + DWORD dwLang = ( static_cast(reinterpret_cast(kl)) & 0xffff ); + + if( g_bUILessMode && GETLANG() == LANG_CHT ) + { + // In case of Vista, artifitial value is returned so that it's not considered as older IME. + dwRet[0] = IMEID_CHT_VER_VISTA; + dwRet[1] = 0; + return dwRet[0]; + } + + if( kl != _CHT_HKL_NEW_PHONETIC && kl != _CHT_HKL_NEW_CHANG_JIE + && kl != _CHT_HKL_NEW_QUICK && kl != _CHT_HKL_HK_CANTONESE && kl != _CHS_HKL ) + { + goto error; + } + + if( _ImmGetIMEFileNameA( kl, szTmp, sizeof( szTmp ) - 1 ) <= 0 ) + { + goto error; + } + + if( !_GetReadingString ) // IME that doesn't implement private API + { +#define LCID_INVARIANT MAKELCID(MAKELANGID(LANG_ENGLISH, SUBLANG_ENGLISH_US), SORT_DEFAULT) + if( ( CompareStringA( LCID_INVARIANT, NORM_IGNORECASE, szTmp, -1, _CHT_IMEFILENAME, -1 ) != 2 ) + && ( CompareStringA( LCID_INVARIANT, NORM_IGNORECASE, szTmp, -1, _CHT_IMEFILENAME2, -1 ) != 2 ) + && ( CompareStringA( LCID_INVARIANT, NORM_IGNORECASE, szTmp, -1, _CHT_IMEFILENAME3, -1 ) != 2 ) + && ( CompareStringA( LCID_INVARIANT, NORM_IGNORECASE, szTmp, -1, _CHS_IMEFILENAME, -1 ) != 2 ) + && ( CompareStringA( LCID_INVARIANT, NORM_IGNORECASE, szTmp, -1, _CHS_IMEFILENAME2, -1 ) != 2 ) + ) + { + goto error; + } + } + + dwVerSize = GetFileVersionInfoSizeA( szTmp, &dwVerHandle ); + if( dwVerSize ) + { + lpVerBuffer = ( LPVOID )ImeUiCallback_Malloc( dwVerSize ); + if( lpVerBuffer ) + { + if( GetFileVersionInfoA( szTmp, 0, dwVerSize, lpVerBuffer ) ) + { + if( VerQueryValueA( lpVerBuffer, "\\", &lpVerData, &cbVerData ) ) + { +#define pVerFixedInfo ((VS_FIXEDFILEINFO FAR*)lpVerData) + DWORD dwVer = pVerFixedInfo->dwFileVersionMS; + dwVer = ( dwVer & 0x00ff0000 ) << 8 | ( dwVer & 0x000000ff ) << 16; + if( _GetReadingString || + dwLang == LANG_CHT && ( + dwVer == MAKEIMEVERSION(4, 2) || + dwVer == MAKEIMEVERSION(4, 3) || + dwVer == MAKEIMEVERSION(4, 4) || + dwVer == MAKEIMEVERSION(5, 0) || + dwVer == MAKEIMEVERSION(5, 1) || + dwVer == MAKEIMEVERSION(5, 2) || + dwVer == MAKEIMEVERSION(6, 0) ) + || + dwLang == LANG_CHS && ( + dwVer == MAKEIMEVERSION(4, 1) || + dwVer == MAKEIMEVERSION(4, 2) || + dwVer == MAKEIMEVERSION(5, 3) ) ) + { + dwRet[0] = dwVer | dwLang; + dwRet[1] = pVerFixedInfo->dwFileVersionLS; + ImeUiCallback_Free( lpVerBuffer ); + return dwRet[0]; + } +#undef pVerFixedInfo + } + } + ImeUiCallback_Free( lpVerBuffer ); + } + } + // The flow comes here in the following conditions + // - Non Chinese IME input locale + // - Older Chinese IME + // - Other error cases +error: + dwRet[0] = dwRet[1] = 0; + return dwRet[uIndex]; +} + +static void GetReadingString( _In_ HWND hWnd ) +{ + if( g_bUILessMode ) + { + return; + } + DWORD dwId = GetImeId(); + if( !dwId ) + { + return; + } + + HIMC himc; + himc = _ImmGetContext( hWnd ); + if( !himc ) + return; + + DWORD dwlen = 0; + DWORD dwerr = 0; + WCHAR wzBuf[16]; // We believe 16 wchars are big enough to hold reading string after having discussion with CHT IME team. + WCHAR* wstr = wzBuf; + bool unicode = FALSE; + LPINPUTCONTEXT2 lpIMC = nullptr; + + if( _GetReadingString ) + { + BOOL bVertical; + UINT uMaxUiLen; + dwlen = _GetReadingString( himc, 0, nullptr, ( PINT )&dwerr, &bVertical, &uMaxUiLen ); + if( dwlen ) + { + if( dwlen > COUNTOF(wzBuf) ) + { + dwlen = COUNTOF(wzBuf); + } + dwlen = _GetReadingString( himc, dwlen, wstr, ( PINT )&dwerr, &bVertical, &uMaxUiLen ); + } + + g_bHorizontalReading = bVertical == 0; + unicode = true; + } + else // IMEs that doesn't implement Reading String API + { + lpIMC = _ImmLockIMC( himc ); + + // *** hacking code from Michael Yang *** + + LPBYTE p = 0; + + switch( dwId ) + { + + case IMEID_CHT_VER42: // New(Phonetic/ChanJie)IME98 : 4.2.x.x // Win98 + case IMEID_CHT_VER43: // New(Phonetic/ChanJie)IME98a : 4.3.x.x // WinMe, Win2k + case IMEID_CHT_VER44: // New ChanJie IME98b : 4.4.x.x // WinXP + + p = *( LPBYTE* )( ( LPBYTE )_ImmLockIMCC( lpIMC->hPrivate ) + 24 ); + if( !p ) break; + dwlen = *( DWORD* )( p + 7 * 4 + 32 * 4 ); //m_dwInputReadStrLen + dwerr = *( DWORD* )( p + 8 * 4 + 32 * 4 ); //m_dwErrorReadStrStart + wstr = ( WCHAR* )( p + 56 ); + unicode = TRUE; + break; + + case IMEID_CHT_VER50: // 5.0.x.x // WinME + + p = *( LPBYTE* )( ( LPBYTE )_ImmLockIMCC( lpIMC->hPrivate ) + 3 * 4 ); // PCKeyCtrlManager + if( !p ) break; + p = *( LPBYTE* )( ( LPBYTE )p + 1 * 4 + 5 * 4 + 4 * 2 ); // = PCReading = &STypingInfo + if( !p ) break; + dwlen = *( DWORD* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 + 16 ); //m_dwDisplayStringLength; + dwerr = *( DWORD* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 + 16 + 1 * 4 ); //m_dwDisplayErrorStart; + wstr = ( WCHAR* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 ); + unicode = FALSE; + break; + + case IMEID_CHT_VER51: // 5.1.x.x // IME2002(w/OfficeXP) + case IMEID_CHT_VER52: // 5.2.x.x // (w/whistler) + case IMEID_CHS_VER53: // 5.3.x.x // SCIME2k or MSPY3 (w/OfficeXP and Whistler) + + p = *( LPBYTE* )( ( LPBYTE )_ImmLockIMCC( lpIMC->hPrivate ) + 4 ); // PCKeyCtrlManager + if( !p ) break; + p = *( LPBYTE* )( ( LPBYTE )p + 1 * 4 + 5 * 4 ); // = PCReading = &STypingInfo + if( !p ) break; + dwlen = *( DWORD* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 + 16 * 2 ); //m_dwDisplayStringLength; + dwerr = *( DWORD* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 + 16 * 2 + 1 * 4 ); //m_dwDisplayErrorStart; + wstr = ( WCHAR* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 ); + unicode = TRUE; + break; + + // the code tested only with Win 98 SE (MSPY 1.5/ ver 4.1.0.21) + case IMEID_CHS_VER41: + { + int offset; + offset = ( GetImeId( 1 ) >= 0x00000002 ) ? 8 : 7; + + p = *( LPBYTE* )( ( LPBYTE )_ImmLockIMCC( lpIMC->hPrivate ) + offset * 4 ); + if( !p ) break; + dwlen = *( DWORD* )( p + 7 * 4 + 16 * 2 * 4 ); + dwerr = *( DWORD* )( p + 8 * 4 + 16 * 2 * 4 ); + dwerr = std::min( dwerr, dwlen ); + wstr = ( WCHAR* )( p + 6 * 4 + 16 * 2 * 1 ); + unicode = TRUE; + break; + } + + case IMEID_CHS_VER42: // 4.2.x.x // SCIME98 or MSPY2 (w/Office2k, Win2k, WinME, etc) + { + int nTcharSize = IsNT() ? sizeof( WCHAR ) : sizeof( char ); + p = *( LPBYTE* )( ( LPBYTE )_ImmLockIMCC( lpIMC->hPrivate ) + 1 * 4 + 1 * 4 + 6 * 4 ); // = PCReading = &STypintInfo + if( !p ) break; + dwlen = *( DWORD* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 + 16 * nTcharSize ); //m_dwDisplayStringLength; + dwerr = *( DWORD* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 + 16 * nTcharSize + 1 * 4 ); //m_dwDisplayErrorStart; + wstr = ( WCHAR* )( p + 1 * 4 + ( 16 * 2 + 2 * 4 ) + 5 * 4 ); //m_tszDisplayString + unicode = IsNT() ? TRUE : FALSE; + } + } // switch + + g_szCandidate[0][0] = 0; + g_szCandidate[1][0] = 0; + g_szCandidate[2][0] = 0; + g_szCandidate[3][0] = 0; + } + g_dwCount = dwlen; + g_dwSelection = ( DWORD )-1; // do not select any char + if( unicode ) + { + int i; + for( i = 0; ( DWORD )i < dwlen; i++ ) // dwlen > 0, if known IME : yutakah + { + if( dwerr <= ( DWORD )i && g_dwSelection == ( DWORD )-1 ) + { // select error char + g_dwSelection = i; + } + g_szCandidate[i][0] = wstr[i]; + g_szCandidate[i][1] = 0; + } + g_szCandidate[i][0] = 0; + } + else + { + char* p = ( char* )wstr; + int i, j; + for( i = 0, j = 0; ( DWORD )i < dwlen; i++, j++ ) // dwlen > 0, if known IME : yutakah + { + if( dwerr <= ( DWORD )i && g_dwSelection == ( DWORD )-1 ) + { + g_dwSelection = ( DWORD )j; + } + MultiByteToWideChar( g_uCodePage, 0, p + i, 1 + ( _IsLeadByte( p[i] ) ? 1 : 0 ), + g_szCandidate[j], 1 ); + if ( _IsLeadByte( p[i] ) ) + { + i++; + } + } + g_szCandidate[j][0] = 0; + g_dwCount = j; + } + if( !_GetReadingString ) + { + _ImmUnlockIMCC( lpIMC->hPrivate ); + _ImmUnlockIMC( himc ); + GetReadingWindowOrientation( dwId ); + } + _ImmReleaseContext( hWnd, himc ); + + g_bReadingWindow = true; + if( g_bHorizontalReading ) + { + g_iReadingError = -1; + g_szReadingString[0] = 0; + for( UINT i = 0; i < g_dwCount; i++ ) + { + if( g_dwSelection == ( DWORD )i ) + g_iReadingError = (int)wcslen( g_szReadingString ); + LPCTSTR pszTmp = g_szCandidate[i]; + wcscat_s( g_szReadingString, COUNTOF(g_szReadingString), pszTmp ); + } + } + g_uCandPageSize = MAX_CANDLIST; +} + + +static struct +{ + bool m_bCtrl; + bool m_bShift; + bool m_bAlt; + UINT m_uVk; +} + aHotKeys[] = +{ + false, false, false, VK_APPS, + true, false, false, '8', + true, false, false, 'Y', + true, false, false, VK_DELETE, + true, false, false, VK_F7, + true, false, false, VK_F9, + true, false, false, VK_F10, + true, false, false, VK_F11, + true, false, false, VK_F12, + false, false, false, VK_F2, + false, false, false, VK_F3, + false, false, false, VK_F4, + false, false, false, VK_F5, + false, false, false, VK_F10, + false, true, false, VK_F6, + false, true, false, VK_F7, + false, true, false, VK_F8, + true, true, false, VK_F10, + true, true, false, VK_F11, + true, false, false, VK_CONVERT, + true, false, false, VK_SPACE, + true, false, true, 0xbc, // Alt + Ctrl + ',': SW keyboard for Trad. Chinese IME + true, false, false, VK_TAB, // ATOK2005's Ctrl+TAB +}; + +// +// Ignores specific keys when IME is on. Returns true if the message is a hot key to ignore. +// - Caller doesn't have to check whether IME is on. +// - This function must be called before TranslateMessage() is called. +// +bool ImeUi_IgnoreHotKey( _In_ const MSG* pmsg ) +{ + if( !g_bInitialized || !pmsg ) + return false; + + if( pmsg->wParam == VK_PROCESSKEY && ( pmsg->message == WM_KEYDOWN || pmsg->message == WM_SYSKEYDOWN ) ) + { + bool bCtrl, bShift, bAlt; + UINT uVkReal = _ImmGetVirtualKey( pmsg->hwnd ); + // special case #1 - VK_JUNJA toggles half/full width input mode in Korean IME. + // This VK (sent by Alt+'=' combo) is ignored regardless of the modifier state. + if( uVkReal == VK_JUNJA ) + { + return true; + } + // special case #2 - disable right arrow key that switches the candidate list to expanded mode in CHT IME. + if( uVkReal == VK_RIGHT && g_bCandList && GETLANG() == LANG_CHT ) + { + return true; + } +#ifndef ENABLE_HANJA_KEY + // special case #3 - we disable VK_HANJA key because 1. some Korean fonts don't Hanja and 2. to reduce testing cost. + if( uVkReal == VK_HANJA && GETPRIMLANG() == LANG_KOREAN ) + { + return true; + } +#endif + bCtrl = ( GetKeyState( VK_CONTROL ) & 0x8000 ) ? true : false; + bShift = ( GetKeyState( VK_SHIFT ) & 0x8000 ) ? true : false; + bAlt = ( GetKeyState( VK_MENU ) & 0x8000 ) ? true : false; + for( int i = 0; i < COUNTOF(aHotKeys); i++ ) + { + if( aHotKeys[i].m_bCtrl == bCtrl && + aHotKeys[i].m_bShift == bShift && + aHotKeys[i].m_bAlt == bAlt && + aHotKeys[i].m_uVk == uVkReal ) + return true; + } + } + return false; +} + +void ImeUi_FinalizeString( _In_ bool bSend ) +{ + HIMC himc; + static bool bProcessing = false; // to avoid infinite recursion + if( !g_bInitialized || bProcessing ) + return; + + himc = _ImmGetContext( g_hwndCurr ); + if ( !himc ) + return; + bProcessing = true; + + if( g_dwIMELevel == 2 && bSend ) + { + // Send composition string to app. + LONG lRet = (int)wcslen( g_szCompositionString ); + assert( lRet >= 2 ); + // In case of CHT IME, don't send the trailing double byte space, if it exists. + if ( GETLANG() == LANG_CHT && (lRet >= 1) + && g_szCompositionString[lRet - 1] == 0x3000 ) + { + lRet--; + } + _SendCompString(); + } + + InitCompStringData(); + // clear composition string in IME + _ImmNotifyIME( himc, NI_COMPOSITIONSTR, CPS_CANCEL, 0 ); + if( g_bUILessMode ) + { + // For some reason ImmNotifyIME doesn't work on DaYi and Array CHT IMEs. Cancel composition string by setting zero-length string. + ImmSetCompositionString( himc, SCS_SETSTR, const_cast(L""), sizeof(wchar_t), const_cast(""), sizeof(wchar_t) ); + } + // the following line is necessary as Korean IME doesn't close cand list when comp string is cancelled. + _ImmNotifyIME( himc, NI_CLOSECANDIDATE, 0, 0 ); + _ImmReleaseContext( g_hwndCurr, himc ); + // Zooty2 RAID #4759: Sometimes application doesn't receive IMN_CLOSECANDIDATE on Alt+Tab + // So the same code for IMN_CLOSECANDIDATE is replicated here. + CloseCandidateList(); + bProcessing = false; + return; +} + +static void SetCompStringColor() +{ + // change color setting according to current IME level. + DWORD dwTranslucency = ( g_dwIMELevel == 2 ) ? 0xff000000 : ( ( DWORD )gSkinIME.compTranslucence << 24 ); + gSkinCompStr.colorInput = dwTranslucency | gSkinIME.compColorInput; + gSkinCompStr.colorTargetConv = dwTranslucency | gSkinIME.compColorTargetConv; + gSkinCompStr.colorConverted = dwTranslucency | gSkinIME.compColorConverted; + gSkinCompStr.colorTargetNotConv = dwTranslucency | gSkinIME.compColorTargetNotConv; + gSkinCompStr.colorInputErr = dwTranslucency | gSkinIME.compColorInputErr; +} + +static void SetSupportLevel( _In_ DWORD dwImeLevel ) +{ + if( dwImeLevel < 2 || 3 < dwImeLevel ) + return; + if( GETPRIMLANG() == LANG_KOREAN ) + { + dwImeLevel = 3; + } + g_dwIMELevel = dwImeLevel; + // cancel current composition string. + ImeUi_FinalizeString(); + SetCompStringColor(); +} + +void ImeUi_SetSupportLevel( _In_ DWORD dwImeLevel ) +{ + if( !g_bInitialized ) + return; + g_dwIMELevelSaved = dwImeLevel; + SetSupportLevel( dwImeLevel ); +} + +void ImeUi_SetAppearance( _In_opt_ const IMEUI_APPEARANCE* pia ) +{ + if( !g_bInitialized || !pia ) + return; + gSkinIME = *pia; + gSkinIME.symbolColor &= 0xffffff; // mask translucency + gSkinIME.symbolColorOff &= 0xffffff; // mask translucency + gSkinIME.symbolColorText &= 0xffffff; // mask translucency + gSkinIME.compColorInput &= 0xffffff; // mask translucency + gSkinIME.compColorTargetConv &= 0xffffff; // mask translucency + gSkinIME.compColorConverted &= 0xffffff; // mask translucency + gSkinIME.compColorTargetNotConv &= 0xffffff; // mask translucency + gSkinIME.compColorInputErr &= 0xffffff; // mask translucency + SetCompStringColor(); +} + +void ImeUi_GetAppearance( _Out_opt_ IMEUI_APPEARANCE* pia ) +{ + if ( pia ) + { + if ( g_bInitialized ) + { + *pia = gSkinIME; + } + else + { + memset( pia, 0, sizeof(IMEUI_APPEARANCE) ); + } + } +} + +static void CheckToggleState() +{ + CheckInputLocale(); + + // In Vista, we have to use TSF since few IMM functions don't work as expected. + // WARNING: Because of timing, g_dwState and g_bChineseIME may not be updated + // immediately after the change on IME states by user. + if( g_bUILessMode ) + { + return; + } + + bool bIme = _ImmIsIME( g_hklCurrent ) != 0 + && ( ( 0xF0000000 & static_cast( reinterpret_cast( g_hklCurrent ) ) ) == 0xE0000000 ); // Hack to detect IME correctly. When IME is running as TIP, ImmIsIME() returns true for CHT US keyboard. + g_bChineseIME = ( GETPRIMLANG() == LANG_CHINESE ) && bIme; + + HIMC himc = _ImmGetContext( g_hwndCurr ); + if( himc ) + { + if( g_bChineseIME ) + { + DWORD dwConvMode, dwSentMode; + _ImmGetConversionStatus( himc, &dwConvMode, &dwSentMode ); + g_dwState = ( dwConvMode & IME_CMODE_NATIVE ) ? IMEUI_STATE_ON : IMEUI_STATE_ENGLISH; + } + else + { + g_dwState = ( bIme && _ImmGetOpenStatus( himc ) != 0 ) ? IMEUI_STATE_ON : IMEUI_STATE_OFF; + } + _ImmReleaseContext( g_hwndCurr, himc ); + } + else + g_dwState = IMEUI_STATE_OFF; +} + +void ImeUi_SetInsertMode( _In_ bool bInsert ) +{ + if( !g_bInitialized ) + return; + g_bInsertMode = bInsert; +} + +bool ImeUi_GetCaretStatus() +{ + return !g_bInitialized || !g_szCompositionString[0]; +} + +void ImeUi_SetScreenDimension( _In_ UINT width, _In_ UINT height ) +{ + if( !g_bInitialized ) + return; + g_screenWidth = width; + g_screenHeight = height; +} + +// this function is used only in brief time in CHT IME handling, so accelerator isn't processed. +static void _PumpMessage() +{ + MSG msg; + while( PeekMessageA( &msg, nullptr, 0, 0, PM_NOREMOVE ) ) + { + if( !GetMessageA( &msg, nullptr, 0, 0 ) ) + { + PostQuitMessage( msg.wParam ); + return; + } + // if (0 == TranslateAccelerator(msg.hwnd, hAccelTable, &msg)) { + TranslateMessage( &msg ); + DispatchMessageA( &msg ); + // } + } +} + +static void GetReadingWindowOrientation( _In_ DWORD dwId ) +{ + g_bHorizontalReading = ( g_hklCurrent == _CHS_HKL ) || ( g_hklCurrent == _CHT_HKL_NEW_CHANG_JIE ) || ( dwId == 0 ); + if( !g_bHorizontalReading && IMEID_LANG( dwId ) == LANG_CHT ) + { + char szRegPath[MAX_PATH]; + HKEY hkey; + DWORD dwVer = IMEID_VER( dwId ); + strcpy_s( szRegPath, COUNTOF(szRegPath), "software\\microsoft\\windows\\currentversion\\" ); + strcat_s( szRegPath, COUNTOF(szRegPath), ( dwVer >= MAKEIMEVERSION(5, 1) ) ? "MSTCIPH" : "TINTLGNT" ); + LONG lRc = RegOpenKeyExA( HKEY_CURRENT_USER, szRegPath, 0, KEY_READ, &hkey ); + if( lRc == ERROR_SUCCESS ) + { + DWORD dwSize = sizeof( DWORD ), dwMapping, dwType; + lRc = RegQueryValueExA( hkey, "keyboard mapping", nullptr, &dwType, ( PBYTE )&dwMapping, &dwSize ); + if( lRc == ERROR_SUCCESS ) + { + if( + ( dwVer <= MAKEIMEVERSION( 5, 0 ) && + ( ( BYTE )dwMapping == 0x22 || ( BYTE )dwMapping == 0x23 ) + ) || + ( ( dwVer == MAKEIMEVERSION( 5, 1 ) || dwVer == MAKEIMEVERSION( 5, 2 ) ) && + ( ( BYTE )dwMapping >= 0x22 && ( BYTE )dwMapping <= 0x24 ) + ) + ) + { + g_bHorizontalReading = true; + } + } + RegCloseKey( hkey ); + } + } +} + +void ImeUi_ToggleLanguageBar( _In_ BOOL bRestore ) +{ + static BOOL prevRestore = TRUE; + bool bCheck = ( prevRestore == TRUE || bRestore == TRUE ); + prevRestore = bRestore; + if( !bCheck ) + return; + + static int iShowStatusWindow = -1; + if( iShowStatusWindow == -1 ) + { + iShowStatusWindow = IsNT() && g_osi.dwMajorVersion >= 5 && + ( g_osi.dwMinorVersion > 1 || ( g_osi.dwMinorVersion == 1 && strlen( g_osi.szCSDVersion ) ) ) ? 1 : 0; + } + HWND hwndImeDef = _ImmGetDefaultIMEWnd( g_hwndCurr ); + if( hwndImeDef && bRestore && iShowStatusWindow ) + SendMessageA( hwndImeDef, WM_IME_CONTROL, IMC_OPENSTATUSWINDOW, 0 ); + HRESULT hr; + hr = CoInitialize( nullptr ); + if( SUCCEEDED( hr ) ) + { + ITfLangBarMgr* plbm = nullptr; + hr = CoCreateInstance( CLSID_TF_LangBarMgr, nullptr, CLSCTX_INPROC_SERVER, __uuidof( ITfLangBarMgr ), + ( void** )&plbm ); + if( SUCCEEDED( hr ) && plbm ) + { + DWORD dwCur; + ULONG uRc; + if( SUCCEEDED( hr ) ) + { + if( bRestore ) + { + if( g_dwPrevFloat ) + hr = plbm->ShowFloating( g_dwPrevFloat ); + } + else + { + hr = plbm->GetShowFloatingStatus( &dwCur ); + if( SUCCEEDED( hr ) ) + g_dwPrevFloat = dwCur; + if( !( g_dwPrevFloat & TF_SFT_DESKBAND ) ) + { + hr = plbm->ShowFloating( TF_SFT_HIDDEN ); + } + } + } + uRc = plbm->Release(); + } + CoUninitialize(); + } + if( hwndImeDef && !bRestore ) + { + // The following OPENSTATUSWINDOW is required to hide ATOK16 toolbar (FS9:#7546) + SendMessageA( hwndImeDef, WM_IME_CONTROL, IMC_OPENSTATUSWINDOW, 0 ); + SendMessageA( hwndImeDef, WM_IME_CONTROL, IMC_CLOSESTATUSWINDOW, 0 ); + } +} + +bool ImeUi_IsSendingKeyMessage() +{ + return bIsSendingKeyMessage; +} + +static void OnInputLangChangeWorker() +{ + if( !g_bUILessMode ) + { + g_iCandListIndexBase = ( g_hklCurrent == _CHT_HKL_DAYI ) ? 0 : 1; + } + SetImeApi(); +} + +static void OnInputLangChange() +{ + UINT uLang = GETPRIMLANG(); + CheckToggleState(); + OnInputLangChangeWorker(); + if( uLang != GETPRIMLANG() ) + { + // Korean IME always uses level 3 support. + // Other languages use the level that is specified by ImeUi_SetSupportLevel() + SetSupportLevel( ( GETPRIMLANG() == LANG_KOREAN ) ? 3 : g_dwIMELevelSaved ); + } + HWND hwndImeDef = _ImmGetDefaultIMEWnd( g_hwndCurr ); + if( hwndImeDef ) + { + // Fix for Zooty #3995: prevent CHT IME toobar from showing up + SendMessageA( hwndImeDef, WM_IME_CONTROL, IMC_OPENSTATUSWINDOW, 0 ); + SendMessageA( hwndImeDef, WM_IME_CONTROL, IMC_CLOSESTATUSWINDOW, 0 ); + } +} + +static void SetImeApi() +{ + _GetReadingString = nullptr; + _ShowReadingWindow = nullptr; + if( g_bUILessMode ) + return; + + char szImeFile[MAX_PATH + 1]; + HKL kl = g_hklCurrent; + if( _ImmGetIMEFileNameA( kl, szImeFile, sizeof( szImeFile ) - 1 ) <= 0 ) + return; + HMODULE hIme = LoadLibraryExA( szImeFile, nullptr, 0x00000800 /* LOAD_LIBRARY_SEARCH_SYSTEM32 */ ); + if( !hIme ) + return; + _GetReadingString = reinterpret_cast( reinterpret_cast( GetProcAddress( hIme, "GetReadingString" ) ) ); + _ShowReadingWindow = reinterpret_cast( reinterpret_cast( GetProcAddress( hIme, "ShowReadingWindow" ) ) ); + if( _ShowReadingWindow ) + { + HIMC himc = _ImmGetContext( g_hwndCurr ); + if( himc ) + { + _ShowReadingWindow( himc, false ); + _ImmReleaseContext( g_hwndCurr, himc ); + } + } +} + +static void CheckInputLocale() +{ + static HKL hklPrev = 0; + g_hklCurrent = GetKeyboardLayout( 0 ); + if( hklPrev == g_hklCurrent ) + { + return; + } + hklPrev = g_hklCurrent; + switch( GETPRIMLANG() ) + { + // Simplified Chinese + case LANG_CHINESE: + g_bVerticalCand = true; + switch( GETSUBLANG() ) + { + case SUBLANG_CHINESE_SIMPLIFIED: + g_pszIndicatior = g_aszIndicator[INDICATOR_CHS]; + //g_bVerticalCand = GetImeId() == 0; + g_bVerticalCand = false; + break; + case SUBLANG_CHINESE_TRADITIONAL: + g_pszIndicatior = g_aszIndicator[INDICATOR_CHT]; + break; + default: // unsupported sub-language + g_pszIndicatior = g_aszIndicator[INDICATOR_NON_IME]; + break; + } + break; + // Korean + case LANG_KOREAN: + g_pszIndicatior = g_aszIndicator[INDICATOR_KOREAN]; + g_bVerticalCand = false; + break; + // Japanese + case LANG_JAPANESE: + g_pszIndicatior = g_aszIndicator[INDICATOR_JAPANESE]; + g_bVerticalCand = true; + break; + default: + g_pszIndicatior = g_aszIndicator[INDICATOR_NON_IME]; + } + char szCodePage[8]; + (void)GetLocaleInfoA( MAKELCID( GETLANG(), SORT_DEFAULT ), LOCALE_IDEFAULTANSICODEPAGE, szCodePage, + COUNTOF( szCodePage ) ); + g_uCodePage = _strtoul( szCodePage, nullptr, 0 ); + for( int i = 0; i < 256; i++ ) + { + LeadByteTable[i] = ( BYTE )IsDBCSLeadByteEx( g_uCodePage, ( BYTE )i ); + } +} + +void ImeUi_SetWindow( _In_ HWND hwnd ) +{ + g_hwndCurr = hwnd; + g_disableCicero.DisableCiceroOnThisWnd( hwnd ); +} + +UINT ImeUi_GetInputCodePage() +{ + return g_uCodePage; +} + +DWORD ImeUi_GetFlags() +{ + return g_dwImeUiFlags; +} + +void ImeUi_SetFlags( _In_ DWORD dwFlags, _In_ bool bSet ) +{ + if( bSet ) + { + g_dwImeUiFlags |= dwFlags; + } + else + { + g_dwImeUiFlags &= ~dwFlags; + } +} + +/////////////////////////////////////////////////////////////////////////////// +// +// CTsfUiLessMode methods +// +/////////////////////////////////////////////////////////////////////////////// + +// +// SetupSinks() +// Set up sinks. A sink is used to receive a Text Service Framework event. +// CUIElementSink implements multiple sink interfaces to receive few different TSF events. +// +BOOL CTsfUiLessMode::SetupSinks() +{ + // ITfThreadMgrEx is available on Vista or later. + HRESULT hr; + hr = CoCreateInstance( CLSID_TF_ThreadMgr, + nullptr, + CLSCTX_INPROC_SERVER, + __uuidof( ITfThreadMgrEx ), + ( void** )&m_tm ); + + if( hr != S_OK ) + { + return FALSE; + } + + // ready to start interacting + TfClientId cid; // not used + if( FAILED( m_tm->ActivateEx( &cid, TF_TMAE_UIELEMENTENABLEDONLY ) ) ) + { + return FALSE; + } + + // Setup sinks + BOOL bRc = FALSE; + m_TsfSink = new (std::nothrow) CUIElementSink(); + if( m_TsfSink ) + { + ITfSource* srcTm; + if( SUCCEEDED( hr = m_tm->QueryInterface( __uuidof( ITfSource ), ( void** )&srcTm ) ) ) + { + // Sink for reading window change + if( SUCCEEDED( hr = srcTm->AdviseSink( __uuidof( ITfUIElementSink ), ( ITfUIElementSink* )m_TsfSink, + &m_dwUIElementSinkCookie ) ) ) + { + // Sink for input locale change + if( SUCCEEDED( hr = srcTm->AdviseSink( __uuidof( ITfInputProcessorProfileActivationSink ), + ( ITfInputProcessorProfileActivationSink* )m_TsfSink, + &m_dwAlpnSinkCookie ) ) ) + { + if( SetupCompartmentSinks() ) // Setup compartment sinks for the first time + { + bRc = TRUE; + } + } + } + srcTm->Release(); + } + } + return bRc; +} + +void CTsfUiLessMode::ReleaseSinks() +{ + HRESULT hr; + ITfSource* source; + + // Remove all sinks + if( m_tm && SUCCEEDED( m_tm->QueryInterface( __uuidof( ITfSource ), ( void** )&source ) ) ) + { + hr = source->UnadviseSink( m_dwUIElementSinkCookie ); + hr = source->UnadviseSink( m_dwAlpnSinkCookie ); + source->Release(); + SetupCompartmentSinks( TRUE ); // Remove all compartment sinks + m_tm->Deactivate(); + SAFE_RELEASE( m_tm ); + SAFE_RELEASE( m_TsfSink ); + } +} + +CTsfUiLessMode::CUIElementSink::CUIElementSink() noexcept : _cRef(1) +{ +} + + +CTsfUiLessMode::CUIElementSink::~CUIElementSink() +{ +} + +STDAPI CTsfUiLessMode::CUIElementSink::QueryInterface( _In_ REFIID riid, _COM_Outptr_ void** ppvObj ) +{ + if( !ppvObj ) + return E_INVALIDARG; + + *ppvObj = nullptr; + + if( IsEqualIID( riid, IID_IUnknown ) ) + { + *ppvObj = static_cast( static_cast( this ) ); + } + else if( IsEqualIID( riid, __uuidof( ITfUIElementSink ) ) ) + { + *ppvObj = ( ITfUIElementSink* )this; + } + else if( IsEqualIID( riid, __uuidof( ITfInputProcessorProfileActivationSink ) ) ) + { + *ppvObj = ( ITfInputProcessorProfileActivationSink* )this; + } + else if( IsEqualIID( riid, __uuidof( ITfCompartmentEventSink ) ) ) + { + *ppvObj = ( ITfCompartmentEventSink* )this; + } + + if( *ppvObj ) + { + AddRef(); + return S_OK; + } + + return E_NOINTERFACE; +} + +STDAPI_( ULONG ) +CTsfUiLessMode::CUIElementSink::AddRef() +{ + return ++_cRef; +} + +STDAPI_( ULONG ) +CTsfUiLessMode::CUIElementSink::Release() +{ + LONG cr = --_cRef; + + if( _cRef == 0 ) + { + delete this; + } + + return cr; +} + +STDAPI CTsfUiLessMode::CUIElementSink::BeginUIElement( DWORD dwUIElementId, BOOL* pbShow ) +{ + auto pElement = GetUIElement( dwUIElementId ); + if( !pElement ) + return E_INVALIDARG; + + ITfReadingInformationUIElement* preading = nullptr; + ITfCandidateListUIElement* pcandidate = nullptr; + *pbShow = FALSE; + if( !g_bCandList && SUCCEEDED( pElement->QueryInterface( __uuidof( ITfReadingInformationUIElement ), + ( void** )&preading ) ) ) + { + MakeReadingInformationString( preading ); + preading->Release(); + } + else if( SUCCEEDED( pElement->QueryInterface( __uuidof( ITfCandidateListUIElement ), + ( void** )&pcandidate ) ) ) + { + m_nCandidateRefCount++; + MakeCandidateStrings( pcandidate ); + pcandidate->Release(); + } + + pElement->Release(); + return S_OK; +} + +STDAPI CTsfUiLessMode::CUIElementSink::UpdateUIElement( DWORD dwUIElementId ) +{ + auto pElement = GetUIElement( dwUIElementId ); + if( !pElement ) + return E_INVALIDARG; + + ITfReadingInformationUIElement* preading = nullptr; + ITfCandidateListUIElement* pcandidate = nullptr; + if( !g_bCandList && SUCCEEDED( pElement->QueryInterface( __uuidof( ITfReadingInformationUIElement ), + ( void** )&preading ) ) ) + { + MakeReadingInformationString( preading ); + preading->Release(); + } + else if( SUCCEEDED( pElement->QueryInterface( __uuidof( ITfCandidateListUIElement ), + ( void** )&pcandidate ) ) ) + { + MakeCandidateStrings( pcandidate ); + pcandidate->Release(); + } + + pElement->Release(); + return S_OK; +} + +STDAPI CTsfUiLessMode::CUIElementSink::EndUIElement( DWORD dwUIElementId ) +{ + auto pElement = GetUIElement( dwUIElementId ); + if( !pElement ) + return E_INVALIDARG; + + ITfReadingInformationUIElement* preading = nullptr; + if( !g_bCandList && SUCCEEDED( pElement->QueryInterface( __uuidof( ITfReadingInformationUIElement ), + ( void** )&preading ) ) ) + { + g_dwCount = 0; + preading->Release(); + } + + ITfCandidateListUIElement* pcandidate = nullptr; + if( SUCCEEDED( pElement->QueryInterface( __uuidof( ITfCandidateListUIElement ), + ( void** )&pcandidate ) ) ) + { + m_nCandidateRefCount--; + if( m_nCandidateRefCount == 0 ) + CloseCandidateList(); + pcandidate->Release(); + } + + pElement->Release(); + return S_OK; +} + +void CTsfUiLessMode::UpdateImeState( BOOL bResetCompartmentEventSink ) +{ + ITfCompartmentMgr* pcm; + ITfCompartment* pTfOpenMode = nullptr; + ITfCompartment* pTfConvMode = nullptr; + if( GetCompartments( &pcm, &pTfOpenMode, &pTfConvMode ) ) + { + VARIANT valOpenMode; + if ( SUCCEEDED(pTfOpenMode->GetValue(&valOpenMode)) ) + { + VARIANT valConvMode; + if (SUCCEEDED(pTfConvMode->GetValue(&valConvMode))) + { + if (valOpenMode.vt == VT_I4) + { + if (g_bChineseIME) + { + g_dwState = valOpenMode.lVal != 0 && valConvMode.lVal != 0 ? IMEUI_STATE_ON : IMEUI_STATE_ENGLISH; + } + else + { + g_dwState = valOpenMode.lVal != 0 ? IMEUI_STATE_ON : IMEUI_STATE_OFF; + } + } + VariantClear(&valConvMode); + } + VariantClear(&valOpenMode); + } + + if( bResetCompartmentEventSink ) + { + SetupCompartmentSinks( FALSE, pTfOpenMode, pTfConvMode ); // Reset compartment sinks + } + pTfOpenMode->Release(); + pTfConvMode->Release(); + pcm->Release(); + } +} + +STDAPI CTsfUiLessMode::CUIElementSink::OnActivated( DWORD dwProfileType, LANGID langid, _In_ REFCLSID clsid, _In_ REFGUID catid, + _In_ REFGUID guidProfile, HKL hkl, DWORD dwFlags ) +{ + UNREFERENCED_PARAMETER(clsid); + UNREFERENCED_PARAMETER(hkl); + + static GUID s_TF_PROFILE_DAYI = + { + 0x037B2C25, 0x480C, 0x4D7F, 0xB0, 0x27, 0xD6, 0xCA, 0x6B, 0x69, 0x78, 0x8A + }; + g_iCandListIndexBase = IsEqualGUID( s_TF_PROFILE_DAYI, guidProfile ) ? 0 : 1; + if( IsEqualIID( catid, GUID_TFCAT_TIP_KEYBOARD ) && ( dwFlags & TF_IPSINK_FLAG_ACTIVE ) ) + { + g_bChineseIME = ( dwProfileType & TF_PROFILETYPE_INPUTPROCESSOR ) && langid == LANG_CHT; + if( dwProfileType & TF_PROFILETYPE_INPUTPROCESSOR ) + { + UpdateImeState( TRUE ); + } + else + g_dwState = IMEUI_STATE_OFF; + OnInputLangChange(); + } + return S_OK; +} + +STDAPI CTsfUiLessMode::CUIElementSink::OnChange( _In_ REFGUID rguid ) +{ + UNREFERENCED_PARAMETER(rguid); + UpdateImeState(); + return S_OK; +} + +void CTsfUiLessMode::MakeReadingInformationString( ITfReadingInformationUIElement* preading ) +{ + UINT cchMax; + UINT uErrorIndex = 0; + BOOL fVertical; + DWORD dwFlags; + + preading->GetUpdatedFlags( &dwFlags ); + preading->GetMaxReadingStringLength( &cchMax ); + preading->GetErrorIndex( &uErrorIndex ); // errorIndex is zero-based + preading->IsVerticalOrderPreferred( &fVertical ); + g_iReadingError = ( int )uErrorIndex; + g_bHorizontalReading = !fVertical; + g_bReadingWindow = true; + g_uCandPageSize = MAX_CANDLIST; + g_dwSelection = g_iReadingError ? g_iReadingError - 1 : ( DWORD )-1; + g_iReadingError--; // g_iReadingError is used only in horizontal window, and has to be -1 if there's no error. + + BSTR bstr; + if( SUCCEEDED( preading->GetString( &bstr ) ) ) + { + if( bstr ) + { + wcscpy_s( g_szReadingString, COUNTOF(g_szReadingString), bstr ); + g_dwCount = cchMax; + LPCTSTR pszSource = g_szReadingString; + if( fVertical ) + { + // for vertical reading window, copy each character to g_szCandidate array. + for( UINT i = 0; i < cchMax; i++ ) + { + LPTSTR pszDest = g_szCandidate[i]; + if( *pszSource ) + { + LPTSTR pszNextSrc = CharNext( pszSource ); + SIZE_T size = ( LPSTR )pszNextSrc - ( LPSTR )pszSource; + memcpy( pszDest, pszSource, size ); + pszSource = pszNextSrc; + pszDest += size; + } + *pszDest = 0; + } + } + else + { + g_szCandidate[0][0] = TEXT( ' ' ); // hack to make rendering happen + } + SysFreeString( bstr ); + } + } +} + +void CTsfUiLessMode::MakeCandidateStrings( ITfCandidateListUIElement* pcandidate ) +{ + UINT uIndex = 0; + UINT uCount = 0; + UINT uCurrentPage = 0; + UINT* IndexList = nullptr; + UINT uPageCnt = 0; + DWORD dwPageStart = 0; + DWORD dwPageSize = 0; + BSTR bstr; + + pcandidate->GetSelection( &uIndex ); + pcandidate->GetCount( &uCount ); + pcandidate->GetCurrentPage( &uCurrentPage ); + g_dwSelection = ( DWORD )uIndex; + g_dwCount = ( DWORD )uCount; + g_bCandList = true; + g_bReadingWindow = false; + + pcandidate->GetPageIndex( nullptr, 0, &uPageCnt ); + if( uPageCnt > 0 ) + { + IndexList = ( UINT* )ImeUiCallback_Malloc( sizeof( UINT ) * uPageCnt ); + if( IndexList ) + { + pcandidate->GetPageIndex( IndexList, uPageCnt, &uPageCnt ); + dwPageStart = IndexList[uCurrentPage]; + dwPageSize = ( uCurrentPage < uPageCnt - 1 ) ? + std::min( uCount, IndexList[uCurrentPage + 1] ) - dwPageStart: + uCount - dwPageStart; + } + } + + g_uCandPageSize = std::min( dwPageSize, MAX_CANDLIST ); + g_dwSelection = g_dwSelection - dwPageStart; + + memset( &g_szCandidate, 0, sizeof( g_szCandidate ) ); + for( UINT i = dwPageStart, j = 0; ( DWORD )i < g_dwCount && j < g_uCandPageSize; i++, j++ ) + { + if( SUCCEEDED( pcandidate->GetString( i, &bstr ) ) ) + { + if( bstr ) + { + ComposeCandidateLine( j, bstr ); + SysFreeString( bstr ); + } + } + } + + if( GETPRIMLANG() == LANG_KOREAN ) + { + g_dwSelection = ( DWORD )-1; + } + + if( IndexList ) + { + ImeUiCallback_Free( IndexList ); + } +} + +ITfUIElement* CTsfUiLessMode::GetUIElement( DWORD dwUIElementId ) +{ + ITfUIElementMgr* puiem; + ITfUIElement* pElement = nullptr; + + if( SUCCEEDED( m_tm->QueryInterface( __uuidof( ITfUIElementMgr ), ( void** )&puiem ) ) ) + { + puiem->GetUIElement( dwUIElementId, &pElement ); + puiem->Release(); + } + + return pElement; +} + +BOOL CTsfUiLessMode::CurrentInputLocaleIsIme() +{ + BOOL ret = FALSE; + HRESULT hr; + + ITfInputProcessorProfiles* pProfiles; + hr = CoCreateInstance( CLSID_TF_InputProcessorProfiles, nullptr, CLSCTX_INPROC_SERVER, + __uuidof( ITfInputProcessorProfiles ), ( LPVOID* )&pProfiles ); + if( SUCCEEDED( hr ) ) + { + ITfInputProcessorProfileMgr* pProfileMgr; + hr = pProfiles->QueryInterface( __uuidof( ITfInputProcessorProfileMgr ), ( LPVOID* )&pProfileMgr ); + if( SUCCEEDED( hr ) ) + { + TF_INPUTPROCESSORPROFILE tip; + hr = pProfileMgr->GetActiveProfile( GUID_TFCAT_TIP_KEYBOARD, &tip ); + if( SUCCEEDED( hr ) ) + { + ret = ( tip.dwProfileType & TF_PROFILETYPE_INPUTPROCESSOR ) != 0; + } + pProfileMgr->Release(); + } + pProfiles->Release(); + } + return ret; +} + +// Sets up or removes sink for UI element. +// UI element sink should be removed when IME is disabled, +// otherwise the sink can be triggered when a game has multiple instances of IME UI library. +void CTsfUiLessMode::EnableUiUpdates( bool bEnable ) +{ + if( !m_tm || + ( bEnable && m_dwUIElementSinkCookie != TF_INVALID_COOKIE ) || + ( !bEnable && m_dwUIElementSinkCookie == TF_INVALID_COOKIE ) ) + { + return; + } + ITfSource* srcTm = nullptr; + HRESULT hr = E_FAIL; + if( SUCCEEDED( hr = m_tm->QueryInterface( __uuidof( ITfSource ), ( void** )&srcTm ) ) ) + { + if( bEnable ) + { + hr = srcTm->AdviseSink( __uuidof( ITfUIElementSink ), ( ITfUIElementSink* )m_TsfSink, + &m_dwUIElementSinkCookie ); + } + else + { + hr = srcTm->UnadviseSink( m_dwUIElementSinkCookie ); + m_dwUIElementSinkCookie = TF_INVALID_COOKIE; + } + srcTm->Release(); + } +} + +// Returns open mode compartments and compartment manager. +// Function fails if it fails to acquire any of the objects to be returned. +BOOL CTsfUiLessMode::GetCompartments( ITfCompartmentMgr** ppcm, ITfCompartment** ppTfOpenMode, + ITfCompartment** ppTfConvMode ) +{ + ITfCompartmentMgr* pcm = nullptr; + ITfCompartment* pTfOpenMode = nullptr; + ITfCompartment* pTfConvMode = nullptr; + + static GUID _GUID_COMPARTMENT_KEYBOARD_INPUTMODE_CONVERSION = + { + 0xCCF05DD8, 0x4A87, 0x11D7, 0xA6, 0xE2, 0x00, 0x06, 0x5B, 0x84, 0x43, 0x5C + }; + + HRESULT hr; + if( SUCCEEDED( hr = m_tm->QueryInterface( IID_ITfCompartmentMgr, ( void** )&pcm ) ) ) + { + if( SUCCEEDED( hr = pcm->GetCompartment( GUID_COMPARTMENT_KEYBOARD_OPENCLOSE, &pTfOpenMode ) ) ) + { + if( SUCCEEDED( hr = pcm->GetCompartment( _GUID_COMPARTMENT_KEYBOARD_INPUTMODE_CONVERSION, + &pTfConvMode ) ) ) + { + *ppcm = pcm; + *ppTfOpenMode = pTfOpenMode; + *ppTfConvMode = pTfConvMode; + return TRUE; + } + pTfOpenMode->Release(); + } + pcm->Release(); + } + return FALSE; +} + +// There are three ways to call this function: +// SetupCompartmentSinks() : initialization +// SetupCompartmentSinks(FALSE, openmode, convmode) : Resetting sinks. This is necessary as DaYi and Array IME resets compartment on switching input locale +// SetupCompartmentSinks(TRUE) : clean up sinks +BOOL CTsfUiLessMode::SetupCompartmentSinks( BOOL bRemoveOnly, ITfCompartment* pTfOpenMode, + ITfCompartment* pTfConvMode ) +{ + bool bLocalCompartments = false; + ITfCompartmentMgr* pcm = nullptr; + BOOL bRc = FALSE; + HRESULT hr = E_FAIL; + + if( !pTfOpenMode && !pTfConvMode ) + { + bLocalCompartments = true; + GetCompartments( &pcm, &pTfOpenMode, &pTfConvMode ); + } + if( !( pTfOpenMode && pTfConvMode ) ) + { + // Invalid parameters or GetCompartments() has failed. + return FALSE; + } + ITfSource* srcOpenMode = nullptr; + if( SUCCEEDED( hr = pTfOpenMode->QueryInterface( IID_ITfSource, ( void** )&srcOpenMode ) ) ) + { + // Remove existing sink for open mode + if( m_dwOpenModeSinkCookie != TF_INVALID_COOKIE ) + { + srcOpenMode->UnadviseSink( m_dwOpenModeSinkCookie ); + m_dwOpenModeSinkCookie = TF_INVALID_COOKIE; + } + // Setup sink for open mode (toggle state) change + if( bRemoveOnly || SUCCEEDED( hr = srcOpenMode->AdviseSink( IID_ITfCompartmentEventSink, + ( ITfCompartmentEventSink* )m_TsfSink, + &m_dwOpenModeSinkCookie ) ) ) + { + ITfSource* srcConvMode = nullptr; + if( SUCCEEDED( hr = pTfConvMode->QueryInterface( IID_ITfSource, ( void** )&srcConvMode ) ) ) + { + // Remove existing sink for open mode + if( m_dwConvModeSinkCookie != TF_INVALID_COOKIE ) + { + srcConvMode->UnadviseSink( m_dwConvModeSinkCookie ); + m_dwConvModeSinkCookie = TF_INVALID_COOKIE; + } + // Setup sink for open mode (toggle state) change + if( bRemoveOnly || SUCCEEDED( hr = srcConvMode->AdviseSink( IID_ITfCompartmentEventSink, + ( ITfCompartmentEventSink* )m_TsfSink, + &m_dwConvModeSinkCookie ) ) ) + { + bRc = TRUE; + } + srcConvMode->Release(); + } + } + srcOpenMode->Release(); + } + if( bLocalCompartments ) + { + pTfOpenMode->Release(); + pTfConvMode->Release(); + pcm->Release(); + } + return bRc; +} + + +WORD ImeUi_GetPrimaryLanguage() +{ + return GETPRIMLANG(); +}; + +DWORD ImeUi_GetImeId( _In_ UINT uIndex ) +{ + return GetImeId( uIndex ); +}; + +WORD ImeUi_GetLanguage() +{ + return GETLANG(); +}; + +PCTSTR ImeUi_GetIndicatior() +{ + return g_pszIndicatior; +}; + + +bool ImeUi_IsShowReadingWindow() +{ + return g_bReadingWindow; +}; + +bool ImeUi_IsShowCandListWindow() +{ + return g_bCandList; +}; + +bool ImeUi_IsVerticalCand() +{ + return g_bVerticalCand; +}; + +bool ImeUi_IsHorizontalReading() +{ + return g_bHorizontalReading; +}; + +TCHAR* ImeUi_GetCandidate( _In_ UINT idx ) +{ + if( idx < MAX_CANDLIST ) + return g_szCandidate[idx]; + else + return g_szCandidate[0]; +} + +DWORD ImeUi_GetCandidateSelection() +{ + return g_dwSelection; +} + +DWORD ImeUi_GetCandidateCount() +{ + return g_dwCount; +} + +TCHAR* ImeUi_GetCompositionString() +{ + return g_szCompositionString; +} + +BYTE* ImeUi_GetCompStringAttr() +{ + return g_szCompAttrString; +} + +DWORD ImeUi_GetImeCursorChars() +{ + return g_IMECursorChars; +} + diff --git a/src/DX11/framework/dxut/Optional/ImeUi.h b/src/DX11/framework/dxut/Optional/ImeUi.h new file mode 100644 index 0000000..7c5866f --- /dev/null +++ b/src/DX11/framework/dxut/Optional/ImeUi.h @@ -0,0 +1,122 @@ +//-------------------------------------------------------------------------------------- +// File: ImeUi.h +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +#include + +class CImeUiFont_Base +{ +public: + virtual void SetHeight( _In_ UINT uHeight ) + { + UNREFERENCED_PARAMETER(uHeight); + }; // for backward compatibility + virtual void SetColor( _In_ DWORD color ) = 0; + virtual void SetPosition( _In_ int x, _In_ int y ) = 0; + virtual void GetTextExtent( _In_z_ LPCTSTR szText, _Out_ DWORD* puWidth, _Out_ DWORD* puHeight ) = 0; + virtual void DrawText( _In_z_ LPCTSTR pszText ) = 0; +}; + +typedef struct +{ + // symbol (Henkan-kyu) + DWORD symbolColor; + DWORD symbolColorOff; + DWORD symbolColorText; + BYTE symbolHeight; + BYTE symbolTranslucence; + BYTE symbolPlacement; + CImeUiFont_Base* symbolFont; + + // candidate list + DWORD candColorBase; + DWORD candColorBorder; + DWORD candColorText; + + // composition string + DWORD compColorInput; + DWORD compColorTargetConv; + DWORD compColorConverted; + DWORD compColorTargetNotConv; + DWORD compColorInputErr; + BYTE compTranslucence; + DWORD compColorText; + + // caret + BYTE caretWidth; + BYTE caretYMargin; +} IMEUI_APPEARANCE; + +typedef struct // D3DTLVERTEX compatible +{ + float sx; + float sy; + float sz; + float rhw; + DWORD color; + DWORD specular; + float tu; + float tv; +} IMEUI_VERTEX; + +// IME States +#define IMEUI_STATE_OFF 0 +#define IMEUI_STATE_ON 1 +#define IMEUI_STATE_ENGLISH 2 + +// IME const +#define MAX_CANDLIST 10 + +// IME Flags +#define IMEUI_FLAG_SUPPORT_CARET 0x00000001 + +bool ImeUi_Initialize( _In_ HWND hwnd, _In_ bool bDisable = false ); +void ImeUi_Uninitialize(); +void ImeUi_SetAppearance( _In_opt_ const IMEUI_APPEARANCE* pia ); +void ImeUi_GetAppearance( _Out_opt_ IMEUI_APPEARANCE* pia ); +bool ImeUi_IgnoreHotKey( _In_ const MSG* pmsg ); +LPARAM ImeUi_ProcessMessage( _In_ HWND hWnd, _In_ UINT uMsg, _In_ WPARAM wParam, _Inout_ LPARAM& lParam, _Out_ bool* trapped ); +void ImeUi_SetScreenDimension( _In_ UINT width, _In_ UINT height ); +void ImeUi_RenderUI( _In_ bool bDrawCompAttr = true, _In_ bool bDrawOtherUi = true ); +void ImeUi_SetCaretPosition( _In_ UINT x, _In_ UINT y ); +void ImeUi_SetCompStringAppearance( _In_ CImeUiFont_Base* pFont, _In_ DWORD color, _In_ const RECT* prc ); +bool ImeUi_GetCaretStatus(); +void ImeUi_SetInsertMode( _In_ bool bInsert ); +void ImeUi_SetState( _In_ DWORD dwState ); +DWORD ImeUi_GetState(); +void ImeUi_EnableIme( _In_ bool bEnable ); +bool ImeUi_IsEnabled(); +void ImeUi_FinalizeString( _In_ bool bSend = false ); +void ImeUi_ToggleLanguageBar( _In_ BOOL bRestore ); +bool ImeUi_IsSendingKeyMessage(); +void ImeUi_SetWindow( _In_ HWND hwnd ); +UINT ImeUi_GetInputCodePage(); +DWORD ImeUi_GetFlags(); +void ImeUi_SetFlags( _In_ DWORD dwFlags, _In_ bool bSet ); + +WORD ImeUi_GetPrimaryLanguage(); +DWORD ImeUi_GetImeId( _In_ UINT uIndex ); +WORD ImeUi_GetLanguage(); +LPCTSTR ImeUi_GetIndicatior(); +bool ImeUi_IsShowReadingWindow(); +bool ImeUi_IsShowCandListWindow(); +bool ImeUi_IsVerticalCand(); +bool ImeUi_IsHorizontalReading(); +TCHAR* ImeUi_GetCandidate( _In_ UINT idx ); +TCHAR* ImeUi_GetCompositionString(); +DWORD ImeUi_GetCandidateSelection(); +DWORD ImeUi_GetCandidateCount(); +BYTE* ImeUi_GetCompStringAttr(); +DWORD ImeUi_GetImeCursorChars(); + +extern void ( CALLBACK*ImeUiCallback_DrawRect )( _In_ int x1, _In_ int y1, _In_ int x2, _In_ int y2, _In_ DWORD color ); +extern void* ( __cdecl*ImeUiCallback_Malloc )( _In_ size_t bytes ); +extern void ( __cdecl*ImeUiCallback_Free )( _In_ void* ptr ); +extern void ( CALLBACK*ImeUiCallback_DrawFans )( _In_ const IMEUI_VERTEX* paVertex, _In_ UINT uNum ); +extern void ( CALLBACK*ImeUiCallback_OnChar )( _In_ WCHAR wc ); diff --git a/src/DX11/framework/dxut/Optional/SDKmesh.cpp b/src/DX11/framework/dxut/Optional/SDKmesh.cpp new file mode 100644 index 0000000..3be4809 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/SDKmesh.cpp @@ -0,0 +1,1318 @@ +//-------------------------------------------------------------------------------------- +// File: SDKMesh.cpp +// +// The SDK Mesh format (.sdkmesh) is not a recommended file format for games. +// It was designed to meet the specific needs of the SDK samples. Any real-world +// applications should avoid this file format in favor of a destination format that +// meets the specific needs of the application. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "DXUT.h" +#include "SDKMesh.h" +#include "SDKMisc.h" + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::LoadMaterials( ID3D11Device* pd3dDevice, SDKMESH_MATERIAL* pMaterials, UINT numMaterials, + SDKMESH_CALLBACKS11* pLoaderCallbacks ) +{ + char strPath[MAX_PATH]; + + if( pLoaderCallbacks && pLoaderCallbacks->pCreateTextureFromFile ) + { + for( UINT m = 0; m < numMaterials; m++ ) + { + pMaterials[m].pDiffuseTexture11 = nullptr; + pMaterials[m].pNormalTexture11 = nullptr; + pMaterials[m].pSpecularTexture11 = nullptr; + pMaterials[m].pDiffuseRV11 = nullptr; + pMaterials[m].pNormalRV11 = nullptr; + pMaterials[m].pSpecularRV11 = nullptr; + + // load textures + if( pMaterials[m].DiffuseTexture[0] != 0 ) + { + pLoaderCallbacks->pCreateTextureFromFile( pd3dDevice, + pMaterials[m].DiffuseTexture, &pMaterials[m].pDiffuseRV11, + pLoaderCallbacks->pContext ); + } + if( pMaterials[m].NormalTexture[0] != 0 ) + { + pLoaderCallbacks->pCreateTextureFromFile( pd3dDevice, + pMaterials[m].NormalTexture, &pMaterials[m].pNormalRV11, + pLoaderCallbacks->pContext ); + } + if( pMaterials[m].SpecularTexture[0] != 0 ) + { + pLoaderCallbacks->pCreateTextureFromFile( pd3dDevice, + pMaterials[m].SpecularTexture, &pMaterials[m].pSpecularRV11, + pLoaderCallbacks->pContext ); + } + } + } + else + { + for( UINT m = 0; m < numMaterials; m++ ) + { + pMaterials[m].pDiffuseTexture11 = nullptr; + pMaterials[m].pNormalTexture11 = nullptr; + pMaterials[m].pSpecularTexture11 = nullptr; + pMaterials[m].pDiffuseRV11 = nullptr; + pMaterials[m].pNormalRV11 = nullptr; + pMaterials[m].pSpecularRV11 = nullptr; + + // load textures + if( pMaterials[m].DiffuseTexture[0] != 0 ) + { + sprintf_s( strPath, MAX_PATH, "%s%s", m_strPath, pMaterials[m].DiffuseTexture ); + if( FAILED( DXUTGetGlobalResourceCache().CreateTextureFromFile( pd3dDevice, DXUTGetD3D11DeviceContext(), + strPath, &pMaterials[m].pDiffuseRV11, + true ) ) ) + pMaterials[m].pDiffuseRV11 = ( ID3D11ShaderResourceView* )ERROR_RESOURCE_VALUE; + + } + if( pMaterials[m].NormalTexture[0] != 0 ) + { + sprintf_s( strPath, MAX_PATH, "%s%s", m_strPath, pMaterials[m].NormalTexture ); + if( FAILED( DXUTGetGlobalResourceCache().CreateTextureFromFile( pd3dDevice, DXUTGetD3D11DeviceContext(), + strPath, + &pMaterials[m].pNormalRV11 ) ) ) + pMaterials[m].pNormalRV11 = ( ID3D11ShaderResourceView* )ERROR_RESOURCE_VALUE; + } + if( pMaterials[m].SpecularTexture[0] != 0 ) + { + sprintf_s( strPath, MAX_PATH, "%s%s", m_strPath, pMaterials[m].SpecularTexture ); + if( FAILED( DXUTGetGlobalResourceCache().CreateTextureFromFile( pd3dDevice, DXUTGetD3D11DeviceContext(), + strPath, + &pMaterials[m].pSpecularRV11 ) ) ) + pMaterials[m].pSpecularRV11 = ( ID3D11ShaderResourceView* )ERROR_RESOURCE_VALUE; + } + } + } +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTSDKMesh::CreateVertexBuffer( ID3D11Device* pd3dDevice, SDKMESH_VERTEX_BUFFER_HEADER* pHeader, + void* pVertices, SDKMESH_CALLBACKS11* pLoaderCallbacks ) +{ + HRESULT hr = S_OK; + pHeader->DataOffset = 0; + //Vertex Buffer + D3D11_BUFFER_DESC bufferDesc; + bufferDesc.ByteWidth = ( UINT )( pHeader->SizeBytes ); + bufferDesc.Usage = D3D11_USAGE_DEFAULT; + bufferDesc.BindFlags = D3D11_BIND_VERTEX_BUFFER; + bufferDesc.CPUAccessFlags = 0; + bufferDesc.MiscFlags = 0; + + if( pLoaderCallbacks && pLoaderCallbacks->pCreateVertexBuffer ) + { + pLoaderCallbacks->pCreateVertexBuffer( pd3dDevice, &pHeader->pVB11, bufferDesc, pVertices, + pLoaderCallbacks->pContext ); + } + else + { + D3D11_SUBRESOURCE_DATA InitData; + InitData.pSysMem = pVertices; + hr = pd3dDevice->CreateBuffer( &bufferDesc, &InitData, &pHeader->pVB11 ); + if (SUCCEEDED(hr)) + { + DXUT_SetDebugName(pHeader->pVB11, "CDXUTSDKMesh"); + } + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTSDKMesh::CreateIndexBuffer( ID3D11Device* pd3dDevice, SDKMESH_INDEX_BUFFER_HEADER* pHeader, + void* pIndices, SDKMESH_CALLBACKS11* pLoaderCallbacks ) +{ + HRESULT hr = S_OK; + pHeader->DataOffset = 0; + //Index Buffer + D3D11_BUFFER_DESC bufferDesc; + bufferDesc.ByteWidth = ( UINT )( pHeader->SizeBytes ); + bufferDesc.Usage = D3D11_USAGE_DEFAULT; + bufferDesc.BindFlags = D3D11_BIND_INDEX_BUFFER; + bufferDesc.CPUAccessFlags = 0; + bufferDesc.MiscFlags = 0; + + if( pLoaderCallbacks && pLoaderCallbacks->pCreateIndexBuffer ) + { + pLoaderCallbacks->pCreateIndexBuffer( pd3dDevice, &pHeader->pIB11, bufferDesc, pIndices, + pLoaderCallbacks->pContext ); + } + else + { + D3D11_SUBRESOURCE_DATA InitData; + InitData.pSysMem = pIndices; + hr = pd3dDevice->CreateBuffer( &bufferDesc, &InitData, &pHeader->pIB11 ); + if (SUCCEEDED(hr)) + { + DXUT_SetDebugName(pHeader->pIB11, "CDXUTSDKMesh"); + } + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTSDKMesh::CreateFromFile( ID3D11Device* pDev11, + LPCWSTR szFileName, + SDKMESH_CALLBACKS11* pLoaderCallbacks11 ) +{ + HRESULT hr = S_OK; + + // Find the path for the file + V_RETURN( DXUTFindDXSDKMediaFileCch( m_strPathW, sizeof( m_strPathW ) / sizeof( WCHAR ), szFileName ) ); + + // Open the file + m_hFile = CreateFile( m_strPathW, FILE_READ_DATA, FILE_SHARE_READ, nullptr, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, + nullptr ); + if( INVALID_HANDLE_VALUE == m_hFile ) + return DXUTERR_MEDIANOTFOUND; + + // Change the path to just the directory + WCHAR* pLastBSlash = wcsrchr( m_strPathW, L'\\' ); + if( pLastBSlash ) + *( pLastBSlash + 1 ) = L'\0'; + else + *m_strPathW = L'\0'; + + WideCharToMultiByte( CP_ACP, 0, m_strPathW, -1, m_strPath, MAX_PATH, nullptr, FALSE ); + + // Get the file size + LARGE_INTEGER FileSize; + GetFileSizeEx( m_hFile, &FileSize ); + UINT cBytes = FileSize.LowPart; + + // Allocate memory + m_pStaticMeshData = new (std::nothrow) BYTE[ cBytes ]; + if( !m_pStaticMeshData ) + { + CloseHandle( m_hFile ); + return E_OUTOFMEMORY; + } + + // Read in the file + DWORD dwBytesRead; + if( !ReadFile( m_hFile, m_pStaticMeshData, cBytes, &dwBytesRead, nullptr ) ) + hr = E_FAIL; + + CloseHandle( m_hFile ); + + if( SUCCEEDED( hr ) ) + { + hr = CreateFromMemory( pDev11, + m_pStaticMeshData, + cBytes, + false, + pLoaderCallbacks11 ); + if( FAILED( hr ) ) + delete []m_pStaticMeshData; + } + + return hr; +} + +_Use_decl_annotations_ +HRESULT CDXUTSDKMesh::CreateFromMemory( ID3D11Device* pDev11, + BYTE* pData, + size_t DataBytes, + bool bCopyStatic, + SDKMESH_CALLBACKS11* pLoaderCallbacks11 ) +{ + XMFLOAT3 lower; + XMFLOAT3 upper; + + m_pDev11 = pDev11; + + if ( DataBytes < sizeof(SDKMESH_HEADER) ) + return E_FAIL; + + // Set outstanding resources to zero + m_NumOutstandingResources = 0; + + if( bCopyStatic ) + { + auto pHeader = reinterpret_cast( pData ); + + SIZE_T StaticSize = ( SIZE_T )( pHeader->HeaderSize + pHeader->NonBufferDataSize ); + if ( DataBytes < StaticSize ) + return E_FAIL; + + m_pHeapData = new (std::nothrow) BYTE[ StaticSize ]; + if( !m_pHeapData ) + return E_OUTOFMEMORY; + + m_pStaticMeshData = m_pHeapData; + + memcpy( m_pStaticMeshData, pData, StaticSize ); + } + else + { + m_pHeapData = pData; + m_pStaticMeshData = pData; + } + + // Pointer fixup + m_pMeshHeader = reinterpret_cast( m_pStaticMeshData ); + + m_pVertexBufferArray = ( SDKMESH_VERTEX_BUFFER_HEADER* )( m_pStaticMeshData + + m_pMeshHeader->VertexStreamHeadersOffset ); + m_pIndexBufferArray = ( SDKMESH_INDEX_BUFFER_HEADER* )( m_pStaticMeshData + + m_pMeshHeader->IndexStreamHeadersOffset ); + m_pMeshArray = ( SDKMESH_MESH* )( m_pStaticMeshData + m_pMeshHeader->MeshDataOffset ); + m_pSubsetArray = ( SDKMESH_SUBSET* )( m_pStaticMeshData + m_pMeshHeader->SubsetDataOffset ); + m_pFrameArray = ( SDKMESH_FRAME* )( m_pStaticMeshData + m_pMeshHeader->FrameDataOffset ); + m_pMaterialArray = ( SDKMESH_MATERIAL* )( m_pStaticMeshData + m_pMeshHeader->MaterialDataOffset ); + + // Setup subsets + for( UINT i = 0; i < m_pMeshHeader->NumMeshes; i++ ) + { + m_pMeshArray[i].pSubsets = ( UINT* )( m_pStaticMeshData + m_pMeshArray[i].SubsetOffset ); + m_pMeshArray[i].pFrameInfluences = ( UINT* )( m_pStaticMeshData + m_pMeshArray[i].FrameInfluenceOffset ); + } + + // error condition + if( m_pMeshHeader->Version != SDKMESH_FILE_VERSION ) + { + return E_NOINTERFACE; + } + + // Setup buffer data pointer + BYTE* pBufferData = pData + m_pMeshHeader->HeaderSize + m_pMeshHeader->NonBufferDataSize; + + // Get the start of the buffer data + UINT64 BufferDataStart = m_pMeshHeader->HeaderSize + m_pMeshHeader->NonBufferDataSize; + + // Create VBs + m_ppVertices = new (std::nothrow) BYTE*[m_pMeshHeader->NumVertexBuffers]; + if ( !m_ppVertices ) + { + return E_OUTOFMEMORY; + } + for( UINT i = 0; i < m_pMeshHeader->NumVertexBuffers; i++ ) + { + BYTE* pVertices = nullptr; + pVertices = ( BYTE* )( pBufferData + ( m_pVertexBufferArray[i].DataOffset - BufferDataStart ) ); + + if( pDev11 ) + CreateVertexBuffer( pDev11, &m_pVertexBufferArray[i], pVertices, pLoaderCallbacks11 ); + + m_ppVertices[i] = pVertices; + } + + // Create IBs + m_ppIndices = new (std::nothrow) BYTE*[m_pMeshHeader->NumIndexBuffers]; + if ( !m_ppIndices ) + { + return E_OUTOFMEMORY; + } + + for( UINT i = 0; i < m_pMeshHeader->NumIndexBuffers; i++ ) + { + BYTE* pIndices = nullptr; + pIndices = ( BYTE* )( pBufferData + ( m_pIndexBufferArray[i].DataOffset - BufferDataStart ) ); + + if( pDev11 ) + CreateIndexBuffer( pDev11, &m_pIndexBufferArray[i], pIndices, pLoaderCallbacks11 ); + + m_ppIndices[i] = pIndices; + } + + // Load Materials + if( pDev11 ) + LoadMaterials( pDev11, m_pMaterialArray, m_pMeshHeader->NumMaterials, pLoaderCallbacks11 ); + + // Create a place to store our bind pose frame matrices + m_pBindPoseFrameMatrices = new (std::nothrow) XMFLOAT4X4[ m_pMeshHeader->NumFrames ]; + if( !m_pBindPoseFrameMatrices ) + { + return E_OUTOFMEMORY; + } + + // Create a place to store our transformed frame matrices + m_pTransformedFrameMatrices = new (std::nothrow) XMFLOAT4X4[ m_pMeshHeader->NumFrames ]; + if( !m_pTransformedFrameMatrices ) + { + return E_OUTOFMEMORY; + } + + m_pWorldPoseFrameMatrices = new (std::nothrow) XMFLOAT4X4[ m_pMeshHeader->NumFrames ]; + if( !m_pWorldPoseFrameMatrices ) + { + return E_OUTOFMEMORY; + } + + SDKMESH_SUBSET* pSubset = nullptr; + D3D11_PRIMITIVE_TOPOLOGY PrimType; + + // update bounding volume + SDKMESH_MESH* currentMesh = &m_pMeshArray[0]; + int tris = 0; + for (UINT meshi=0; meshi < m_pMeshHeader->NumMeshes; ++meshi) { + lower.x = FLT_MAX; lower.y = FLT_MAX; lower.z = FLT_MAX; + upper.x = -FLT_MAX; upper.y = -FLT_MAX; upper.z = -FLT_MAX; + currentMesh = GetMesh( meshi ); + INT indsize; + if (m_pIndexBufferArray[currentMesh->IndexBuffer].IndexType == IT_16BIT ) { + indsize = 2; + }else { + indsize = 4; + } + + for( UINT subset = 0; subset < currentMesh->NumSubsets; subset++ ) + { + pSubset = GetSubset( meshi, subset ); //&m_pSubsetArray[ currentMesh->pSubsets[subset] ]; + + PrimType = GetPrimitiveType11( ( SDKMESH_PRIMITIVE_TYPE )pSubset->PrimitiveType ); + assert( PrimType == D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST );// only triangle lists are handled. + + UINT IndexCount = ( UINT )pSubset->IndexCount; + UINT IndexStart = ( UINT )pSubset->IndexStart; + + /*if( bAdjacent ) + { + IndexCount *= 2; + IndexStart *= 2; + }*/ + + //BYTE* pIndices = nullptr; + //m_ppIndices[i] + UINT *ind = ( UINT * )m_ppIndices[currentMesh->IndexBuffer]; + float *verts = ( float* )m_ppVertices[currentMesh->VertexBuffers[0]]; + UINT stride = (UINT)m_pVertexBufferArray[currentMesh->VertexBuffers[0]].StrideBytes; + assert (stride % 4 == 0); + stride /=4; + for (UINT vertind = IndexStart; vertind < IndexStart + IndexCount; ++vertind) { + UINT current_ind=0; + if (indsize == 2) { + UINT ind_div2 = vertind / 2; + current_ind = ind[ind_div2]; + if (vertind %2 ==0) { + current_ind = current_ind << 16; + current_ind = current_ind >> 16; + }else { + current_ind = current_ind >> 16; + } + }else { + current_ind = ind[vertind]; + } + tris++; + XMFLOAT3 *pt = (XMFLOAT3*)&(verts[stride * current_ind]); + if (pt->x < lower.x) { + lower.x = pt->x; + } + if (pt->y < lower.y) { + lower.y = pt->y; + } + if (pt->z < lower.z) { + lower.z = pt->z; + } + if (pt->x > upper.x) { + upper.x = pt->x; + } + if (pt->y > upper.y) { + upper.y = pt->y; + } + if (pt->z > upper.z) { + upper.z = pt->z; + } + //BYTE** m_ppVertices; + //BYTE** m_ppIndices; + } + //pd3dDeviceContext->DrawIndexed( IndexCount, IndexStart, VertexStart ); + } + + XMFLOAT3 half( ( upper.x - lower.x ) * 0.5f, + ( upper.y - lower.y ) * 0.5f, + ( upper.z - lower.z ) * 0.5f ); + + currentMesh->BoundingBoxCenter.x = lower.x + half.x; + currentMesh->BoundingBoxCenter.y = lower.y + half.y; + currentMesh->BoundingBoxCenter.z = lower.z + half.z; + + currentMesh->BoundingBoxExtents = half; + + } + // Update + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +// transform bind pose frame using a recursive traversal +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::TransformBindPoseFrame( UINT iFrame, CXMMATRIX parentWorld ) +{ + if( !m_pBindPoseFrameMatrices ) + return; + + // Transform ourselves + XMMATRIX m = XMLoadFloat4x4( &m_pFrameArray[iFrame].Matrix ); + XMMATRIX mLocalWorld = XMMatrixMultiply( m, parentWorld ); + XMStoreFloat4x4( &m_pBindPoseFrameMatrices[iFrame], mLocalWorld ); + + // Transform our siblings + if( m_pFrameArray[iFrame].SiblingFrame != INVALID_FRAME ) + { + TransformBindPoseFrame( m_pFrameArray[iFrame].SiblingFrame, parentWorld ); + } + + // Transform our children + if( m_pFrameArray[iFrame].ChildFrame != INVALID_FRAME ) + { + TransformBindPoseFrame( m_pFrameArray[iFrame].ChildFrame, mLocalWorld ); + } +} + + +//-------------------------------------------------------------------------------------- +// transform frame using a recursive traversal +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::TransformFrame( UINT iFrame, CXMMATRIX parentWorld, double fTime ) +{ + // Get the tick data + XMMATRIX mLocalTransform; + + UINT iTick = GetAnimationKeyFromTime( fTime ); + + if( INVALID_ANIMATION_DATA != m_pFrameArray[iFrame].AnimationDataIndex ) + { + auto pFrameData = &m_pAnimationFrameData[ m_pFrameArray[iFrame].AnimationDataIndex ]; + auto pData = &pFrameData->pAnimationData[ iTick ]; + + // turn it into a matrix (Ignore scaling for now) + XMFLOAT3 parentPos = pData->Translation; + XMMATRIX mTranslate = XMMatrixTranslation( parentPos.x, parentPos.y, parentPos.z ); + + XMVECTOR quat = XMVectorSet( pData->Orientation.x, pData->Orientation.y, pData->Orientation.z, pData->Orientation.w ); + if ( XMVector4Equal( quat, g_XMZero ) ) + quat = XMQuaternionIdentity(); + quat = XMQuaternionNormalize( quat ); + XMMATRIX mQuat = XMMatrixRotationQuaternion( quat ); + mLocalTransform = ( mQuat * mTranslate ); + } + else + { + mLocalTransform = XMLoadFloat4x4( &m_pFrameArray[iFrame].Matrix ); + } + + // Transform ourselves + XMMATRIX mLocalWorld = XMMatrixMultiply( mLocalTransform, parentWorld ); + XMStoreFloat4x4( &m_pTransformedFrameMatrices[iFrame], mLocalWorld ); + XMStoreFloat4x4( &m_pWorldPoseFrameMatrices[iFrame], mLocalWorld ); + + // Transform our siblings + if( m_pFrameArray[iFrame].SiblingFrame != INVALID_FRAME ) + { + TransformFrame( m_pFrameArray[iFrame].SiblingFrame, parentWorld, fTime ); + } + + // Transform our children + if( m_pFrameArray[iFrame].ChildFrame != INVALID_FRAME ) + { + TransformFrame( m_pFrameArray[iFrame].ChildFrame, mLocalWorld, fTime ); + } +} + + +//-------------------------------------------------------------------------------------- +// transform frame assuming that it is an absolute transformation +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::TransformFrameAbsolute( UINT iFrame, double fTime ) +{ + UINT iTick = GetAnimationKeyFromTime( fTime ); + + if( INVALID_ANIMATION_DATA != m_pFrameArray[iFrame].AnimationDataIndex ) + { + auto pFrameData = &m_pAnimationFrameData[ m_pFrameArray[iFrame].AnimationDataIndex ]; + auto pData = &pFrameData->pAnimationData[ iTick ]; + auto pDataOrig = &pFrameData->pAnimationData[ 0 ]; + + XMMATRIX mTrans1 = XMMatrixTranslation( -pDataOrig->Translation.x, -pDataOrig->Translation.y, -pDataOrig->Translation.z ); + XMMATRIX mTrans2 = XMMatrixTranslation( pData->Translation.x, pData->Translation.y, pData->Translation.z ); + + XMVECTOR quat1 = XMVectorSet( pDataOrig->Orientation.x, pDataOrig->Orientation.y, pDataOrig->Orientation.z, pDataOrig->Orientation.w ); + quat1 = XMQuaternionInverse( quat1 ); + XMMATRIX mRot1 = XMMatrixRotationQuaternion( quat1 ); + XMMATRIX mInvTo = mTrans1 * mRot1; + + XMVECTOR quat2 = XMVectorSet( pData->Orientation.x, pData->Orientation.y, pData->Orientation.z, pData->Orientation.w ); + XMMATRIX mRot2 = XMMatrixRotationQuaternion( quat2 ); + XMMATRIX mFrom = mRot2 * mTrans2; + + XMMATRIX mOutput = mInvTo * mFrom; + XMStoreFloat4x4( &m_pTransformedFrameMatrices[iFrame], mOutput ); + } +} + +#define MAX_D3D11_VERTEX_STREAMS D3D11_IA_VERTEX_INPUT_RESOURCE_SLOT_COUNT + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::RenderMesh( UINT iMesh, + bool bAdjacent, + ID3D11DeviceContext* pd3dDeviceContext, + UINT iDiffuseSlot, + UINT iNormalSlot, + UINT iSpecularSlot ) +{ + if( 0 < GetOutstandingBufferResources() ) + return; + + auto pMesh = &m_pMeshArray[iMesh]; + + UINT Strides[MAX_D3D11_VERTEX_STREAMS]; + UINT Offsets[MAX_D3D11_VERTEX_STREAMS]; + ID3D11Buffer* pVB[MAX_D3D11_VERTEX_STREAMS]; + + if( pMesh->NumVertexBuffers > MAX_D3D11_VERTEX_STREAMS ) + return; + + for( UINT64 i = 0; i < pMesh->NumVertexBuffers; i++ ) + { + pVB[i] = m_pVertexBufferArray[ pMesh->VertexBuffers[i] ].pVB11; + Strides[i] = ( UINT )m_pVertexBufferArray[ pMesh->VertexBuffers[i] ].StrideBytes; + Offsets[i] = 0; + } + + SDKMESH_INDEX_BUFFER_HEADER* pIndexBufferArray; + if( bAdjacent ) + pIndexBufferArray = m_pAdjacencyIndexBufferArray; + else + pIndexBufferArray = m_pIndexBufferArray; + + auto pIB = pIndexBufferArray[ pMesh->IndexBuffer ].pIB11; + DXGI_FORMAT ibFormat = DXGI_FORMAT_R16_UINT; + switch( pIndexBufferArray[ pMesh->IndexBuffer ].IndexType ) + { + case IT_16BIT: + ibFormat = DXGI_FORMAT_R16_UINT; + break; + case IT_32BIT: + ibFormat = DXGI_FORMAT_R32_UINT; + break; + }; + + pd3dDeviceContext->IASetVertexBuffers( 0, pMesh->NumVertexBuffers, pVB, Strides, Offsets ); + pd3dDeviceContext->IASetIndexBuffer( pIB, ibFormat, 0 ); + + SDKMESH_SUBSET* pSubset = nullptr; + SDKMESH_MATERIAL* pMat = nullptr; + D3D11_PRIMITIVE_TOPOLOGY PrimType; + + for( UINT subset = 0; subset < pMesh->NumSubsets; subset++ ) + { + pSubset = &m_pSubsetArray[ pMesh->pSubsets[subset] ]; + + PrimType = GetPrimitiveType11( ( SDKMESH_PRIMITIVE_TYPE )pSubset->PrimitiveType ); + if( bAdjacent ) + { + switch( PrimType ) + { + case D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST: + PrimType = D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST_ADJ; + break; + case D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP: + PrimType = D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP_ADJ; + break; + case D3D11_PRIMITIVE_TOPOLOGY_LINELIST: + PrimType = D3D11_PRIMITIVE_TOPOLOGY_LINELIST_ADJ; + break; + case D3D11_PRIMITIVE_TOPOLOGY_LINESTRIP: + PrimType = D3D11_PRIMITIVE_TOPOLOGY_LINESTRIP_ADJ; + break; + } + } + + pd3dDeviceContext->IASetPrimitiveTopology( PrimType ); + + pMat = &m_pMaterialArray[ pSubset->MaterialID ]; + if( iDiffuseSlot != INVALID_SAMPLER_SLOT && !IsErrorResource( pMat->pDiffuseRV11 ) ) + pd3dDeviceContext->PSSetShaderResources( iDiffuseSlot, 1, &pMat->pDiffuseRV11 ); + if( iNormalSlot != INVALID_SAMPLER_SLOT && !IsErrorResource( pMat->pNormalRV11 ) ) + pd3dDeviceContext->PSSetShaderResources( iNormalSlot, 1, &pMat->pNormalRV11 ); + if( iSpecularSlot != INVALID_SAMPLER_SLOT && !IsErrorResource( pMat->pSpecularRV11 ) ) + pd3dDeviceContext->PSSetShaderResources( iSpecularSlot, 1, &pMat->pSpecularRV11 ); + + UINT IndexCount = ( UINT )pSubset->IndexCount; + UINT IndexStart = ( UINT )pSubset->IndexStart; + UINT VertexStart = ( UINT )pSubset->VertexStart; + if( bAdjacent ) + { + IndexCount *= 2; + IndexStart *= 2; + } + + pd3dDeviceContext->DrawIndexed( IndexCount, IndexStart, VertexStart ); + } +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::RenderFrame( UINT iFrame, + bool bAdjacent, + ID3D11DeviceContext* pd3dDeviceContext, + UINT iDiffuseSlot, + UINT iNormalSlot, + UINT iSpecularSlot ) +{ + if( !m_pStaticMeshData || !m_pFrameArray ) + return; + + if( m_pFrameArray[iFrame].Mesh != INVALID_MESH ) + { + RenderMesh( m_pFrameArray[iFrame].Mesh, + bAdjacent, + pd3dDeviceContext, + iDiffuseSlot, + iNormalSlot, + iSpecularSlot ); + } + + // Render our children + if( m_pFrameArray[iFrame].ChildFrame != INVALID_FRAME ) + RenderFrame( m_pFrameArray[iFrame].ChildFrame, bAdjacent, pd3dDeviceContext, iDiffuseSlot, + iNormalSlot, iSpecularSlot ); + + // Render our siblings + if( m_pFrameArray[iFrame].SiblingFrame != INVALID_FRAME ) + RenderFrame( m_pFrameArray[iFrame].SiblingFrame, bAdjacent, pd3dDeviceContext, iDiffuseSlot, + iNormalSlot, iSpecularSlot ); +} + +//-------------------------------------------------------------------------------------- +CDXUTSDKMesh::CDXUTSDKMesh() noexcept : + m_NumOutstandingResources(0), + m_bLoading(false), + m_hFile(0), + m_hFileMappingObject(0), + m_pDev11(nullptr), + m_pDevContext11(nullptr), + m_pStaticMeshData(nullptr), + m_pHeapData(nullptr), + m_pAnimationData(nullptr), + m_ppVertices(nullptr), + m_ppIndices(nullptr), + m_strPathW{}, + m_strPath{}, + m_pMeshHeader(nullptr), + m_pVertexBufferArray(nullptr), + m_pIndexBufferArray(nullptr), + m_pMeshArray(nullptr), + m_pSubsetArray(nullptr), + m_pFrameArray(nullptr), + m_pMaterialArray(nullptr), + m_pAdjacencyIndexBufferArray(nullptr), + m_pAnimationHeader(nullptr), + m_pAnimationFrameData(nullptr), + m_pBindPoseFrameMatrices(nullptr), + m_pTransformedFrameMatrices(nullptr), + m_pWorldPoseFrameMatrices(nullptr) +{ +} + + +//-------------------------------------------------------------------------------------- +CDXUTSDKMesh::~CDXUTSDKMesh() +{ + Destroy(); +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTSDKMesh::Create( ID3D11Device* pDev11, LPCWSTR szFileName, SDKMESH_CALLBACKS11* pLoaderCallbacks ) +{ + return CreateFromFile( pDev11, szFileName, pLoaderCallbacks ); +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTSDKMesh::Create( ID3D11Device* pDev11, BYTE* pData, size_t DataBytes, bool bCopyStatic, SDKMESH_CALLBACKS11* pLoaderCallbacks ) +{ + return CreateFromMemory( pDev11, pData, DataBytes, bCopyStatic, pLoaderCallbacks ); +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTSDKMesh::LoadAnimation( _In_z_ const WCHAR* szFileName ) +{ + HRESULT hr = E_FAIL; + DWORD dwBytesRead = 0; + LARGE_INTEGER liMove; + WCHAR strPath[MAX_PATH]; + + // Find the path for the file + V_RETURN( DXUTFindDXSDKMediaFileCch( strPath, MAX_PATH, szFileName ) ); + + // Open the file + HANDLE hFile = CreateFile( strPath, FILE_READ_DATA, FILE_SHARE_READ, nullptr, OPEN_EXISTING, + FILE_FLAG_SEQUENTIAL_SCAN, nullptr ); + if( INVALID_HANDLE_VALUE == hFile ) + return DXUTERR_MEDIANOTFOUND; + + ///////////////////////// + // Header + SDKANIMATION_FILE_HEADER fileheader; + if( !ReadFile( hFile, &fileheader, sizeof( SDKANIMATION_FILE_HEADER ), &dwBytesRead, nullptr ) ) + { + CloseHandle(hFile); + return HRESULT_FROM_WIN32(GetLastError()); + } + + //allocate + m_pAnimationData = new (std::nothrow) BYTE[ ( size_t )( sizeof( SDKANIMATION_FILE_HEADER ) + fileheader.AnimationDataSize ) ]; + if( !m_pAnimationData ) + { + CloseHandle(hFile); + return E_OUTOFMEMORY; + } + + // read it all in + liMove.QuadPart = 0; + if( !SetFilePointerEx( hFile, liMove, nullptr, FILE_BEGIN ) ) + { + CloseHandle(hFile); + return HRESULT_FROM_WIN32(GetLastError()); + } + + if( !ReadFile( hFile, m_pAnimationData, ( DWORD )( sizeof( SDKANIMATION_FILE_HEADER ) + + fileheader.AnimationDataSize ), &dwBytesRead, nullptr ) ) + { + CloseHandle(hFile); + return HRESULT_FROM_WIN32(GetLastError()); + } + + // pointer fixup + m_pAnimationHeader = ( SDKANIMATION_FILE_HEADER* )m_pAnimationData; + m_pAnimationFrameData = ( SDKANIMATION_FRAME_DATA* )( m_pAnimationData + m_pAnimationHeader->AnimationDataOffset ); + + UINT64 BaseOffset = sizeof( SDKANIMATION_FILE_HEADER ); + for( UINT i = 0; i < m_pAnimationHeader->NumFrames; i++ ) + { + m_pAnimationFrameData[i].pAnimationData = ( SDKANIMATION_DATA* )( m_pAnimationData + + m_pAnimationFrameData[i].DataOffset + + BaseOffset ); + auto pFrame = FindFrame( m_pAnimationFrameData[i].FrameName ); + if( pFrame ) + { + pFrame->AnimationDataIndex = i; + } + } + + return S_OK; +} + +//-------------------------------------------------------------------------------------- +void CDXUTSDKMesh::Destroy() +{ + if( !CheckLoadDone() ) + return; + + if( m_pStaticMeshData ) + { + if( m_pMaterialArray ) + { + for( UINT64 m = 0; m < m_pMeshHeader->NumMaterials; m++ ) + { + if( m_pDev11 ) + { + if( m_pMaterialArray[m].pDiffuseRV11 && !IsErrorResource( m_pMaterialArray[m].pDiffuseRV11 ) ) + { + //m_pMaterialArray[m].pDiffuseRV11->GetResource( &pRes ); + //SAFE_RELEASE( pRes ); + + SAFE_RELEASE( m_pMaterialArray[m].pDiffuseRV11 ); + } + if( m_pMaterialArray[m].pNormalRV11 && !IsErrorResource( m_pMaterialArray[m].pNormalRV11 ) ) + { + //m_pMaterialArray[m].pNormalRV11->GetResource( &pRes ); + //SAFE_RELEASE( pRes ); + + SAFE_RELEASE( m_pMaterialArray[m].pNormalRV11 ); + } + if( m_pMaterialArray[m].pSpecularRV11 && !IsErrorResource( m_pMaterialArray[m].pSpecularRV11 ) ) + { + //m_pMaterialArray[m].pSpecularRV11->GetResource( &pRes ); + //SAFE_RELEASE( pRes ); + + SAFE_RELEASE( m_pMaterialArray[m].pSpecularRV11 ); + } + } + } + } + for( UINT64 i = 0; i < m_pMeshHeader->NumVertexBuffers; i++ ) + { + SAFE_RELEASE( m_pVertexBufferArray[i].pVB11 ); + } + + for( UINT64 i = 0; i < m_pMeshHeader->NumIndexBuffers; i++ ) + { + SAFE_RELEASE( m_pIndexBufferArray[i].pIB11 ); + } + } + + if( m_pAdjacencyIndexBufferArray ) + { + for( UINT64 i = 0; i < m_pMeshHeader->NumIndexBuffers; i++ ) + { + SAFE_RELEASE( m_pAdjacencyIndexBufferArray[i].pIB11 ); + } + } + SAFE_DELETE_ARRAY( m_pAdjacencyIndexBufferArray ); + + SAFE_DELETE_ARRAY( m_pHeapData ); + m_pStaticMeshData = nullptr; + SAFE_DELETE_ARRAY( m_pAnimationData ); + SAFE_DELETE_ARRAY( m_pBindPoseFrameMatrices ); + SAFE_DELETE_ARRAY( m_pTransformedFrameMatrices ); + SAFE_DELETE_ARRAY( m_pWorldPoseFrameMatrices ); + + SAFE_DELETE_ARRAY( m_ppVertices ); + SAFE_DELETE_ARRAY( m_ppIndices ); + + m_pMeshHeader = nullptr; + m_pVertexBufferArray = nullptr; + m_pIndexBufferArray = nullptr; + m_pMeshArray = nullptr; + m_pSubsetArray = nullptr; + m_pFrameArray = nullptr; + m_pMaterialArray = nullptr; + + m_pAnimationHeader = nullptr; + m_pAnimationFrameData = nullptr; + +} + + +//-------------------------------------------------------------------------------------- +// transform the mesh frames according to the animation for time fTime +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::TransformMesh( CXMMATRIX world, double fTime ) +{ + if( !m_pAnimationHeader || FTT_RELATIVE == m_pAnimationHeader->FrameTransformType ) + { + TransformFrame( 0, world, fTime ); + + // For each frame, move the transform to the bind pose, then + // move it to the final position + for( UINT i = 0; i < m_pMeshHeader->NumFrames; i++ ) + { + XMMATRIX m = XMLoadFloat4x4( &m_pBindPoseFrameMatrices[i] ); + XMMATRIX mInvBindPose = XMMatrixInverse( nullptr, m ); + m = XMLoadFloat4x4( &m_pTransformedFrameMatrices[i] ); + XMMATRIX mFinal = mInvBindPose * m; + XMStoreFloat4x4( &m_pTransformedFrameMatrices[i], mFinal ); + } + } + else if( FTT_ABSOLUTE == m_pAnimationHeader->FrameTransformType ) + { + for( UINT i = 0; i < m_pAnimationHeader->NumFrames; i++ ) + TransformFrameAbsolute( i, fTime ); + } +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::Render( ID3D11DeviceContext* pd3dDeviceContext, + UINT iDiffuseSlot, + UINT iNormalSlot, + UINT iSpecularSlot ) +{ + RenderFrame( 0, false, pd3dDeviceContext, iDiffuseSlot, iNormalSlot, iSpecularSlot ); +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +void CDXUTSDKMesh::RenderAdjacent( ID3D11DeviceContext* pd3dDeviceContext, + UINT iDiffuseSlot, + UINT iNormalSlot, + UINT iSpecularSlot ) +{ + RenderFrame( 0, true, pd3dDeviceContext, iDiffuseSlot, iNormalSlot, iSpecularSlot ); +} + + +//-------------------------------------------------------------------------------------- +D3D11_PRIMITIVE_TOPOLOGY CDXUTSDKMesh::GetPrimitiveType11( _In_ SDKMESH_PRIMITIVE_TYPE PrimType ) +{ + D3D11_PRIMITIVE_TOPOLOGY retType = D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST; + + switch( PrimType ) + { + case PT_TRIANGLE_LIST: + retType = D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST; + break; + case PT_TRIANGLE_STRIP: + retType = D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP; + break; + case PT_LINE_LIST: + retType = D3D11_PRIMITIVE_TOPOLOGY_LINELIST; + break; + case PT_LINE_STRIP: + retType = D3D11_PRIMITIVE_TOPOLOGY_LINESTRIP; + break; + case PT_POINT_LIST: + retType = D3D11_PRIMITIVE_TOPOLOGY_POINTLIST; + break; + case PT_TRIANGLE_LIST_ADJ: + retType = D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST_ADJ; + break; + case PT_TRIANGLE_STRIP_ADJ: + retType = D3D11_PRIMITIVE_TOPOLOGY_TRIANGLESTRIP_ADJ; + break; + case PT_LINE_LIST_ADJ: + retType = D3D11_PRIMITIVE_TOPOLOGY_LINELIST_ADJ; + break; + case PT_LINE_STRIP_ADJ: + retType = D3D11_PRIMITIVE_TOPOLOGY_LINESTRIP_ADJ; + break; + }; + + return retType; +} + +//-------------------------------------------------------------------------------------- +DXGI_FORMAT CDXUTSDKMesh::GetIBFormat11( _In_ UINT iMesh ) const +{ + switch( m_pIndexBufferArray[ m_pMeshArray[ iMesh ].IndexBuffer ].IndexType ) + { + case IT_16BIT: + return DXGI_FORMAT_R16_UINT; + case IT_32BIT: + return DXGI_FORMAT_R32_UINT; + }; + return DXGI_FORMAT_R16_UINT; +} + +//-------------------------------------------------------------------------------------- +ID3D11Buffer* CDXUTSDKMesh::GetVB11( _In_ UINT iMesh, _In_ UINT iVB ) const +{ + return m_pVertexBufferArray[ m_pMeshArray[ iMesh ].VertexBuffers[iVB] ].pVB11; +} + +//-------------------------------------------------------------------------------------- +ID3D11Buffer* CDXUTSDKMesh::GetIB11( _In_ UINT iMesh ) const +{ + return m_pIndexBufferArray[ m_pMeshArray[ iMesh ].IndexBuffer ].pIB11; +} +SDKMESH_INDEX_TYPE CDXUTSDKMesh::GetIndexType( _In_ UINT iMesh ) const +{ + return ( SDKMESH_INDEX_TYPE ) m_pIndexBufferArray[m_pMeshArray[ iMesh ].IndexBuffer].IndexType; +} +//-------------------------------------------------------------------------------------- +ID3D11Buffer* CDXUTSDKMesh::GetAdjIB11( _In_ UINT iMesh ) const +{ + return m_pAdjacencyIndexBufferArray[ m_pMeshArray[ iMesh ].IndexBuffer ].pIB11; +} + +//-------------------------------------------------------------------------------------- +const char* CDXUTSDKMesh::GetMeshPathA() const +{ + return m_strPath; +} + +//-------------------------------------------------------------------------------------- +const WCHAR* CDXUTSDKMesh::GetMeshPathW() const +{ + return m_strPathW; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetNumMeshes() const +{ + if( !m_pMeshHeader ) + return 0; + return m_pMeshHeader->NumMeshes; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetNumMaterials() const +{ + if( !m_pMeshHeader ) + return 0; + return m_pMeshHeader->NumMaterials; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetNumVBs() const +{ + if( !m_pMeshHeader ) + return 0; + return m_pMeshHeader->NumVertexBuffers; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetNumIBs() const +{ + if( !m_pMeshHeader ) + return 0; + return m_pMeshHeader->NumIndexBuffers; +} + +//-------------------------------------------------------------------------------------- +ID3D11Buffer* CDXUTSDKMesh::GetVB11At( _In_ UINT iVB ) const +{ + return m_pVertexBufferArray[ iVB ].pVB11; +} + +//-------------------------------------------------------------------------------------- +ID3D11Buffer* CDXUTSDKMesh::GetIB11At( _In_ UINT iIB ) const +{ + return m_pIndexBufferArray[ iIB ].pIB11; +} + +//-------------------------------------------------------------------------------------- +BYTE* CDXUTSDKMesh::GetRawVerticesAt( _In_ UINT iVB ) const +{ + return m_ppVertices[iVB]; +} + +//-------------------------------------------------------------------------------------- +BYTE* CDXUTSDKMesh::GetRawIndicesAt( _In_ UINT iIB ) const +{ + return m_ppIndices[iIB]; +} + +//-------------------------------------------------------------------------------------- +SDKMESH_MATERIAL* CDXUTSDKMesh::GetMaterial( _In_ UINT iMaterial ) const +{ + return &m_pMaterialArray[ iMaterial ]; +} + +//-------------------------------------------------------------------------------------- +SDKMESH_MESH* CDXUTSDKMesh::GetMesh( _In_ UINT iMesh ) const +{ + return &m_pMeshArray[ iMesh ]; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetNumSubsets( _In_ UINT iMesh ) const +{ + return m_pMeshArray[ iMesh ].NumSubsets; +} + +//-------------------------------------------------------------------------------------- +SDKMESH_SUBSET* CDXUTSDKMesh::GetSubset( _In_ UINT iMesh, _In_ UINT iSubset ) const +{ + return &m_pSubsetArray[ m_pMeshArray[ iMesh ].pSubsets[iSubset] ]; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetVertexStride( _In_ UINT iMesh, _In_ UINT iVB ) const +{ + return ( UINT )m_pVertexBufferArray[ m_pMeshArray[ iMesh ].VertexBuffers[iVB] ].StrideBytes; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetNumFrames() const +{ + return m_pMeshHeader->NumFrames; +} + +//-------------------------------------------------------------------------------------- +SDKMESH_FRAME* CDXUTSDKMesh::GetFrame( _In_ UINT iFrame ) const +{ + assert( iFrame < m_pMeshHeader->NumFrames ); + return &m_pFrameArray[ iFrame ]; +} + +//-------------------------------------------------------------------------------------- +SDKMESH_FRAME* CDXUTSDKMesh::FindFrame( _In_z_ const char* pszName ) const +{ + for( UINT i = 0; i < m_pMeshHeader->NumFrames; i++ ) + { + if( _stricmp( m_pFrameArray[i].Name, pszName ) == 0 ) + { + return &m_pFrameArray[i]; + } + } + return nullptr; +} + +//-------------------------------------------------------------------------------------- +UINT64 CDXUTSDKMesh::GetNumVertices( _In_ UINT iMesh, _In_ UINT iVB ) const +{ + return m_pVertexBufferArray[ m_pMeshArray[ iMesh ].VertexBuffers[iVB] ].NumVertices; +} + +//-------------------------------------------------------------------------------------- +UINT64 CDXUTSDKMesh::GetNumIndices( _In_ UINT iMesh ) const +{ + return m_pIndexBufferArray[ m_pMeshArray[ iMesh ].IndexBuffer ].NumIndices; +} + +//-------------------------------------------------------------------------------------- +XMVECTOR CDXUTSDKMesh::GetMeshBBoxCenter( _In_ UINT iMesh ) const +{ + return XMLoadFloat3( &m_pMeshArray[iMesh].BoundingBoxCenter ); +} + +//-------------------------------------------------------------------------------------- +XMVECTOR CDXUTSDKMesh::GetMeshBBoxExtents( _In_ UINT iMesh ) const +{ + return XMLoadFloat3( &m_pMeshArray[iMesh].BoundingBoxExtents ); +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetOutstandingResources() const +{ + UINT outstandingResources = 0; + if( !m_pMeshHeader ) + return 1; + + outstandingResources += GetOutstandingBufferResources(); + + if( m_pDev11 ) + { + for( UINT i = 0; i < m_pMeshHeader->NumMaterials; i++ ) + { + if( m_pMaterialArray[i].DiffuseTexture[0] != 0 ) + { + if( !m_pMaterialArray[i].pDiffuseRV11 && !IsErrorResource( m_pMaterialArray[i].pDiffuseRV11 ) ) + outstandingResources ++; + } + + if( m_pMaterialArray[i].NormalTexture[0] != 0 ) + { + if( !m_pMaterialArray[i].pNormalRV11 && !IsErrorResource( m_pMaterialArray[i].pNormalRV11 ) ) + outstandingResources ++; + } + + if( m_pMaterialArray[i].SpecularTexture[0] != 0 ) + { + if( !m_pMaterialArray[i].pSpecularRV11 && !IsErrorResource( m_pMaterialArray[i].pSpecularRV11 ) ) + outstandingResources ++; + } + } + } + + return outstandingResources; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetOutstandingBufferResources() const +{ + UINT outstandingResources = 0; + if( !m_pMeshHeader ) + return 1; + + return outstandingResources; +} + +//-------------------------------------------------------------------------------------- +bool CDXUTSDKMesh::CheckLoadDone() +{ + if( 0 == GetOutstandingResources() ) + { + m_bLoading = false; + return true; + } + + return false; +} + +//-------------------------------------------------------------------------------------- +bool CDXUTSDKMesh::IsLoaded() const +{ + if( m_pStaticMeshData && !m_bLoading ) + { + return true; + } + + return false; +} + +//-------------------------------------------------------------------------------------- +bool CDXUTSDKMesh::IsLoading() const +{ + return m_bLoading; +} + +//-------------------------------------------------------------------------------------- +void CDXUTSDKMesh::SetLoading( _In_ bool bLoading ) +{ + m_bLoading = bLoading; +} + +//-------------------------------------------------------------------------------------- +BOOL CDXUTSDKMesh::HadLoadingError() const +{ + return FALSE; +} + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetNumInfluences( _In_ UINT iMesh ) const +{ + return m_pMeshArray[iMesh].NumFrameInfluences; +} + +//-------------------------------------------------------------------------------------- +XMMATRIX CDXUTSDKMesh::GetMeshInfluenceMatrix( _In_ UINT iMesh, _In_ UINT iInfluence ) const +{ + UINT iFrame = m_pMeshArray[iMesh].pFrameInfluences[ iInfluence ]; + return XMLoadFloat4x4( &m_pTransformedFrameMatrices[iFrame] ); +} + +XMMATRIX CDXUTSDKMesh::GetWorldMatrix( _In_ UINT iFrameIndex ) const +{ + return XMLoadFloat4x4( &m_pWorldPoseFrameMatrices[iFrameIndex] ); +} + +XMMATRIX CDXUTSDKMesh::GetInfluenceMatrix( _In_ UINT iFrameIndex ) const +{ + return XMLoadFloat4x4( &m_pTransformedFrameMatrices[iFrameIndex] ); +} + + +//-------------------------------------------------------------------------------------- +UINT CDXUTSDKMesh::GetAnimationKeyFromTime( _In_ double fTime ) const +{ + if( !m_pAnimationHeader ) + { + return 0; + } + + UINT iTick = ( UINT )( m_pAnimationHeader->AnimationFPS * fTime ); + + iTick = iTick % ( m_pAnimationHeader->NumAnimationKeys - 1 ); + iTick ++; + + return iTick; +} + +_Use_decl_annotations_ +bool CDXUTSDKMesh::GetAnimationProperties( UINT* pNumKeys, float* pFrameTime ) const +{ + if( !m_pAnimationHeader ) + { + *pNumKeys = 0; + *pFrameTime = 0; + return false; + } + + *pNumKeys = m_pAnimationHeader->NumAnimationKeys; + *pFrameTime = 1.0f / (float)m_pAnimationHeader->AnimationFPS; + + return true; +} diff --git a/src/DX11/framework/dxut/Optional/SDKmesh.h b/src/DX11/framework/dxut/Optional/SDKmesh.h new file mode 100644 index 0000000..4f07ad1 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/SDKmesh.h @@ -0,0 +1,456 @@ +//-------------------------------------------------------------------------------------- +// File: SDKMesh.h +// +// Disclaimer: +// The SDK Mesh format (.sdkmesh) is not a recommended file format for shipping titles. +// It was designed to meet the specific needs of the SDK samples. Any real-world +// applications should avoid this file format in favor of a destination format that +// meets the specific needs of the application. +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +#undef D3DCOLOR_ARGB +#include + +//-------------------------------------------------------------------------------------- +// Hard Defines for the various structures +//-------------------------------------------------------------------------------------- +#define SDKMESH_FILE_VERSION 101 +#define MAX_VERTEX_ELEMENTS 32 +#define MAX_VERTEX_STREAMS 16 +#define MAX_FRAME_NAME 100 +#define MAX_MESH_NAME 100 +#define MAX_SUBSET_NAME 100 +#define MAX_MATERIAL_NAME 100 +#define MAX_TEXTURE_NAME MAX_PATH +#define MAX_MATERIAL_PATH MAX_PATH +#define INVALID_FRAME ((UINT)-1) +#define INVALID_MESH ((UINT)-1) +#define INVALID_MATERIAL ((UINT)-1) +#define INVALID_SUBSET ((UINT)-1) +#define INVALID_ANIMATION_DATA ((UINT)-1) +#define INVALID_SAMPLER_SLOT ((UINT)-1) +#define ERROR_RESOURCE_VALUE 1 + +template BOOL IsErrorResource( TYPE data ) +{ + if( ( TYPE )ERROR_RESOURCE_VALUE == data ) + return TRUE; + return FALSE; +} +//-------------------------------------------------------------------------------------- +// Enumerated Types. +//-------------------------------------------------------------------------------------- +enum SDKMESH_PRIMITIVE_TYPE +{ + PT_TRIANGLE_LIST = 0, + PT_TRIANGLE_STRIP, + PT_LINE_LIST, + PT_LINE_STRIP, + PT_POINT_LIST, + PT_TRIANGLE_LIST_ADJ, + PT_TRIANGLE_STRIP_ADJ, + PT_LINE_LIST_ADJ, + PT_LINE_STRIP_ADJ, + PT_QUAD_PATCH_LIST, + PT_TRIANGLE_PATCH_LIST, +}; + +enum SDKMESH_INDEX_TYPE +{ + IT_16BIT = 0, + IT_32BIT, +}; + +enum FRAME_TRANSFORM_TYPE +{ + FTT_RELATIVE = 0, + FTT_ABSOLUTE, //This is not currently used but is here to support absolute transformations in the future +}; + +//-------------------------------------------------------------------------------------- +// Structures. Unions with pointers are forced to 64bit. +//-------------------------------------------------------------------------------------- +#pragma pack(push,8) + +struct SDKMESH_HEADER +{ + //Basic Info and sizes + UINT Version; + BYTE IsBigEndian; + UINT64 HeaderSize; + UINT64 NonBufferDataSize; + UINT64 BufferDataSize; + + //Stats + UINT NumVertexBuffers; + UINT NumIndexBuffers; + UINT NumMeshes; + UINT NumTotalSubsets; + UINT NumFrames; + UINT NumMaterials; + + //Offsets to Data + UINT64 VertexStreamHeadersOffset; + UINT64 IndexStreamHeadersOffset; + UINT64 MeshDataOffset; + UINT64 SubsetDataOffset; + UINT64 FrameDataOffset; + UINT64 MaterialDataOffset; +}; + +struct SDKMESH_VERTEX_BUFFER_HEADER +{ + UINT64 NumVertices; + UINT64 SizeBytes; + UINT64 StrideBytes; + D3DVERTEXELEMENT9 Decl[MAX_VERTEX_ELEMENTS]; + union + { + UINT64 DataOffset; //(This also forces the union to 64bits) + ID3D11Buffer* pVB11; + }; +}; + +struct SDKMESH_INDEX_BUFFER_HEADER +{ + UINT64 NumIndices; + UINT64 SizeBytes; + UINT IndexType; + union + { + UINT64 DataOffset; //(This also forces the union to 64bits) + ID3D11Buffer* pIB11; + }; +}; + +struct SDKMESH_MESH +{ + char Name[MAX_MESH_NAME]; + BYTE NumVertexBuffers; + UINT VertexBuffers[MAX_VERTEX_STREAMS]; + UINT IndexBuffer; + UINT NumSubsets; + UINT NumFrameInfluences; //aka bones + + DirectX::XMFLOAT3 BoundingBoxCenter; + DirectX::XMFLOAT3 BoundingBoxExtents; + + union + { + UINT64 SubsetOffset; //Offset to list of subsets (This also forces the union to 64bits) + UINT* pSubsets; //Pointer to list of subsets + }; + union + { + UINT64 FrameInfluenceOffset; //Offset to list of frame influences (This also forces the union to 64bits) + UINT* pFrameInfluences; //Pointer to list of frame influences + }; +}; + +struct SDKMESH_SUBSET +{ + char Name[MAX_SUBSET_NAME]; + UINT MaterialID; + UINT PrimitiveType; + UINT64 IndexStart; + UINT64 IndexCount; + UINT64 VertexStart; + UINT64 VertexCount; +}; + +struct SDKMESH_FRAME +{ + char Name[MAX_FRAME_NAME]; + UINT Mesh; + UINT ParentFrame; + UINT ChildFrame; + UINT SiblingFrame; + DirectX::XMFLOAT4X4 Matrix; + UINT AnimationDataIndex; //Used to index which set of keyframes transforms this frame +}; + +struct SDKMESH_MATERIAL +{ + char Name[MAX_MATERIAL_NAME]; + + // Use MaterialInstancePath + char MaterialInstancePath[MAX_MATERIAL_PATH]; + + // Or fall back to d3d8-type materials + char DiffuseTexture[MAX_TEXTURE_NAME]; + char NormalTexture[MAX_TEXTURE_NAME]; + char SpecularTexture[MAX_TEXTURE_NAME]; + + DirectX::XMFLOAT4 Diffuse; + DirectX::XMFLOAT4 Ambient; + DirectX::XMFLOAT4 Specular; + DirectX::XMFLOAT4 Emissive; + float Power; + + union + { + UINT64 Force64_1; //Force the union to 64bits + ID3D11Texture2D* pDiffuseTexture11; + }; + union + { + UINT64 Force64_2; //Force the union to 64bits + ID3D11Texture2D* pNormalTexture11; + }; + union + { + UINT64 Force64_3; //Force the union to 64bits + ID3D11Texture2D* pSpecularTexture11; + }; + + union + { + UINT64 Force64_4; //Force the union to 64bits + ID3D11ShaderResourceView* pDiffuseRV11; + }; + union + { + UINT64 Force64_5; //Force the union to 64bits + ID3D11ShaderResourceView* pNormalRV11; + }; + union + { + UINT64 Force64_6; //Force the union to 64bits + ID3D11ShaderResourceView* pSpecularRV11; + }; + +}; + +struct SDKANIMATION_FILE_HEADER +{ + UINT Version; + BYTE IsBigEndian; + UINT FrameTransformType; + UINT NumFrames; + UINT NumAnimationKeys; + UINT AnimationFPS; + UINT64 AnimationDataSize; + UINT64 AnimationDataOffset; +}; + +struct SDKANIMATION_DATA +{ + DirectX::XMFLOAT3 Translation; + DirectX::XMFLOAT4 Orientation; + DirectX::XMFLOAT3 Scaling; +}; + +struct SDKANIMATION_FRAME_DATA +{ + char FrameName[MAX_FRAME_NAME]; + union + { + UINT64 DataOffset; + SDKANIMATION_DATA* pAnimationData; + }; +}; + +#pragma pack(pop) + +static_assert( sizeof(D3DVERTEXELEMENT9) == 8, "Direct3D9 Decl structure size incorrect" ); +static_assert( sizeof(SDKMESH_HEADER)== 104, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKMESH_VERTEX_BUFFER_HEADER) == 288, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKMESH_INDEX_BUFFER_HEADER) == 32, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKMESH_MESH) == 224, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKMESH_SUBSET) == 144, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKMESH_FRAME) == 184, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKMESH_MATERIAL) == 1256, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKANIMATION_FILE_HEADER) == 40, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKANIMATION_DATA) == 40, "SDK Mesh structure size incorrect" ); +static_assert( sizeof(SDKANIMATION_FRAME_DATA) == 112, "SDK Mesh structure size incorrect" ); + +#ifndef _CONVERTER_APP_ + +//-------------------------------------------------------------------------------------- +// AsyncLoading callbacks +//-------------------------------------------------------------------------------------- +typedef void ( CALLBACK*LPCREATETEXTUREFROMFILE11 )( _In_ ID3D11Device* pDev, _In_z_ char* szFileName, + _Outptr_ ID3D11ShaderResourceView** ppRV, _In_opt_ void* pContext ); +typedef void ( CALLBACK*LPCREATEVERTEXBUFFER11 )( _In_ ID3D11Device* pDev, _Outptr_ ID3D11Buffer** ppBuffer, + _In_ D3D11_BUFFER_DESC BufferDesc, _In_ void* pData, _In_opt_ void* pContext ); +typedef void ( CALLBACK*LPCREATEINDEXBUFFER11 )( _In_ ID3D11Device* pDev, _Outptr_ ID3D11Buffer** ppBuffer, + _In_ D3D11_BUFFER_DESC BufferDesc, _In_ void* pData, _In_opt_ void* pContext ); +struct SDKMESH_CALLBACKS11 +{ + LPCREATETEXTUREFROMFILE11 pCreateTextureFromFile; + LPCREATEVERTEXBUFFER11 pCreateVertexBuffer; + LPCREATEINDEXBUFFER11 pCreateIndexBuffer; + void* pContext; +}; + +//-------------------------------------------------------------------------------------- +// CDXUTSDKMesh class. This class reads the sdkmesh file format for use by the samples +//-------------------------------------------------------------------------------------- +class CDXUTSDKMesh +{ +private: + UINT m_NumOutstandingResources; + bool m_bLoading; + //BYTE* m_pBufferData; + HANDLE m_hFile; + HANDLE m_hFileMappingObject; + std::vector m_MappedPointers; + ID3D11Device* m_pDev11; + ID3D11DeviceContext* m_pDevContext11; + +protected: + //These are the pointers to the two chunks of data loaded in from the mesh file + BYTE* m_pStaticMeshData; + BYTE* m_pHeapData; + BYTE* m_pAnimationData; + BYTE** m_ppVertices; + BYTE** m_ppIndices; + + //Keep track of the path + WCHAR m_strPathW[MAX_PATH]; + char m_strPath[MAX_PATH]; + + //General mesh info + SDKMESH_HEADER* m_pMeshHeader; + SDKMESH_VERTEX_BUFFER_HEADER* m_pVertexBufferArray; + SDKMESH_INDEX_BUFFER_HEADER* m_pIndexBufferArray; + SDKMESH_MESH* m_pMeshArray; + SDKMESH_SUBSET* m_pSubsetArray; + SDKMESH_FRAME* m_pFrameArray; + SDKMESH_MATERIAL* m_pMaterialArray; + + // Adjacency information (not part of the m_pStaticMeshData, so it must be created and destroyed separately ) + SDKMESH_INDEX_BUFFER_HEADER* m_pAdjacencyIndexBufferArray; + + //Animation + SDKANIMATION_FILE_HEADER* m_pAnimationHeader; + SDKANIMATION_FRAME_DATA* m_pAnimationFrameData; + DirectX::XMFLOAT4X4* m_pBindPoseFrameMatrices; + DirectX::XMFLOAT4X4* m_pTransformedFrameMatrices; + DirectX::XMFLOAT4X4* m_pWorldPoseFrameMatrices; + +protected: + void LoadMaterials( _In_ ID3D11Device* pd3dDevice, _In_reads_(NumMaterials) SDKMESH_MATERIAL* pMaterials, + _In_ UINT NumMaterials, _In_opt_ SDKMESH_CALLBACKS11* pLoaderCallbacks = nullptr ); + + HRESULT CreateVertexBuffer( _In_ ID3D11Device* pd3dDevice, + _In_ SDKMESH_VERTEX_BUFFER_HEADER* pHeader, _In_reads_(pHeader->SizeBytes) void* pVertices, + _In_opt_ SDKMESH_CALLBACKS11* pLoaderCallbacks = nullptr ); + + HRESULT CreateIndexBuffer( _In_ ID3D11Device* pd3dDevice, + _In_ SDKMESH_INDEX_BUFFER_HEADER* pHeader, _In_reads_(pHeader->SizeBytes) void* pIndices, + _In_opt_ SDKMESH_CALLBACKS11* pLoaderCallbacks = nullptr ); + + virtual HRESULT CreateFromFile( _In_opt_ ID3D11Device* pDev11, + _In_z_ LPCWSTR szFileName, + _In_opt_ SDKMESH_CALLBACKS11* pLoaderCallbacks11 = nullptr ); + + virtual HRESULT CreateFromMemory( _In_opt_ ID3D11Device* pDev11, + _In_reads_(DataBytes) BYTE* pData, + _In_ size_t DataBytes, + _In_ bool bCopyStatic, + _In_opt_ SDKMESH_CALLBACKS11* pLoaderCallbacks11 = nullptr ); + + //frame manipulation + void TransformBindPoseFrame( _In_ UINT iFrame, _In_ DirectX::CXMMATRIX parentWorld ); + void TransformFrame( _In_ UINT iFrame, _In_ DirectX::CXMMATRIX parentWorld, _In_ double fTime ); + void TransformFrameAbsolute( _In_ UINT iFrame, _In_ double fTime ); + + //Direct3D 11 rendering helpers + void RenderMesh( _In_ UINT iMesh, + _In_ bool bAdjacent, + _In_ ID3D11DeviceContext* pd3dDeviceContext, + _In_ UINT iDiffuseSlot, + _In_ UINT iNormalSlot, + _In_ UINT iSpecularSlot ); + void RenderFrame( _In_ UINT iFrame, + _In_ bool bAdjacent, + _In_ ID3D11DeviceContext* pd3dDeviceContext, + _In_ UINT iDiffuseSlot, + _In_ UINT iNormalSlot, + _In_ UINT iSpecularSlot ); + +public: + CDXUTSDKMesh() noexcept; + virtual ~CDXUTSDKMesh(); + + virtual HRESULT Create( _In_ ID3D11Device* pDev11, _In_z_ LPCWSTR szFileName, _In_opt_ SDKMESH_CALLBACKS11* pLoaderCallbacks = nullptr ); + virtual HRESULT Create( _In_ ID3D11Device* pDev11, BYTE* pData, size_t DataBytes, _In_ bool bCopyStatic=false, + _In_opt_ SDKMESH_CALLBACKS11* pLoaderCallbacks = nullptr ); + virtual HRESULT LoadAnimation( _In_z_ const WCHAR* szFileName ); + virtual void Destroy(); + + //Frame manipulation + void TransformBindPose( _In_ DirectX::CXMMATRIX world ) { TransformBindPoseFrame( 0, world ); }; + void TransformMesh( _In_ DirectX::CXMMATRIX world, _In_ double fTime ); + + //Direct3D 11 Rendering + virtual void Render( _In_ ID3D11DeviceContext* pd3dDeviceContext, + _In_ UINT iDiffuseSlot = INVALID_SAMPLER_SLOT, + _In_ UINT iNormalSlot = INVALID_SAMPLER_SLOT, + _In_ UINT iSpecularSlot = INVALID_SAMPLER_SLOT ); + virtual void RenderAdjacent( _In_ ID3D11DeviceContext* pd3dDeviceContext, + _In_ UINT iDiffuseSlot = INVALID_SAMPLER_SLOT, + _In_ UINT iNormalSlot = INVALID_SAMPLER_SLOT, + _In_ UINT iSpecularSlot = INVALID_SAMPLER_SLOT ); + + //Helpers (D3D11 specific) + static D3D11_PRIMITIVE_TOPOLOGY GetPrimitiveType11( _In_ SDKMESH_PRIMITIVE_TYPE PrimType ); + DXGI_FORMAT GetIBFormat11( _In_ UINT iMesh ) const; + ID3D11Buffer* GetVB11( _In_ UINT iMesh, _In_ UINT iVB ) const; + ID3D11Buffer* GetIB11( _In_ UINT iMesh ) const; + SDKMESH_INDEX_TYPE GetIndexType( _In_ UINT iMesh ) const; + + ID3D11Buffer* GetAdjIB11( _In_ UINT iMesh ) const; + + //Helpers (general) + const char* GetMeshPathA() const; + const WCHAR* GetMeshPathW() const; + UINT GetNumMeshes() const; + UINT GetNumMaterials() const; + UINT GetNumVBs() const; + UINT GetNumIBs() const; + + ID3D11Buffer* GetVB11At( _In_ UINT iVB ) const; + ID3D11Buffer* GetIB11At( _In_ UINT iIB ) const; + + BYTE* GetRawVerticesAt( _In_ UINT iVB ) const; + BYTE* GetRawIndicesAt( _In_ UINT iIB ) const; + + SDKMESH_MATERIAL* GetMaterial( _In_ UINT iMaterial ) const; + SDKMESH_MESH* GetMesh( _In_ UINT iMesh ) const; + UINT GetNumSubsets( _In_ UINT iMesh ) const; + SDKMESH_SUBSET* GetSubset( _In_ UINT iMesh, _In_ UINT iSubset ) const; + UINT GetVertexStride( _In_ UINT iMesh, _In_ UINT iVB ) const; + UINT GetNumFrames() const; + SDKMESH_FRAME* GetFrame( _In_ UINT iFrame ) const; + SDKMESH_FRAME* FindFrame( _In_z_ const char* pszName ) const; + UINT64 GetNumVertices( _In_ UINT iMesh, _In_ UINT iVB ) const; + UINT64 GetNumIndices( _In_ UINT iMesh ) const; + DirectX::XMVECTOR GetMeshBBoxCenter( _In_ UINT iMesh ) const; + DirectX::XMVECTOR GetMeshBBoxExtents( _In_ UINT iMesh ) const; + UINT GetOutstandingResources() const; + UINT GetOutstandingBufferResources() const; + bool CheckLoadDone(); + bool IsLoaded() const; + bool IsLoading() const; + void SetLoading( _In_ bool bLoading ); + BOOL HadLoadingError() const; + + //Animation + UINT GetNumInfluences( _In_ UINT iMesh ) const; + DirectX::XMMATRIX GetMeshInfluenceMatrix( _In_ UINT iMesh, _In_ UINT iInfluence ) const; + UINT GetAnimationKeyFromTime( _In_ double fTime ) const; + DirectX::XMMATRIX GetWorldMatrix( _In_ UINT iFrameIndex ) const; + DirectX::XMMATRIX GetInfluenceMatrix( _In_ UINT iFrameIndex ) const; + bool GetAnimationProperties( _Out_ UINT* pNumKeys, _Out_ float* pFrameTime ) const; +}; + +#endif + diff --git a/src/DX11/framework/dxut/Optional/SDKmisc.cpp b/src/DX11/framework/dxut/Optional/SDKmisc.cpp new file mode 100644 index 0000000..52a076b --- /dev/null +++ b/src/DX11/framework/dxut/Optional/SDKmisc.cpp @@ -0,0 +1,1029 @@ +//-------------------------------------------------------------------------------------- +// File: SDKmisc.cpp +// +// Various helper functionality that is shared between SDK samples +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#include "dxut.h" +#include "SDKmisc.h" +#include "DXUTres.h" + +#include "DXUTGui.h" + +#include "DDSTextureLoader.h" +#include "WICTextureLoader.h" +#include "ScreenGrab.h" + +using namespace DirectX; + +//-------------------------------------------------------------------------------------- +// Global/Static Members +//-------------------------------------------------------------------------------------- +CDXUTResourceCache& WINAPI DXUTGetGlobalResourceCache() +{ + // Using an accessor function gives control of the construction order + static CDXUTResourceCache* s_cache = nullptr; + if ( !s_cache ) + { +#if defined(DEBUG) || defined(_DEBUG) + int flag = _CrtSetDbgFlag( _CRTDBG_REPORT_FLAG ); + _CrtSetDbgFlag( flag & ~_CRTDBG_ALLOC_MEM_DF ); +#endif + s_cache = new CDXUTResourceCache; +#if defined(DEBUG) || defined(_DEBUG) + _CrtSetDbgFlag( flag ); +#endif + } + return *s_cache; +} + + +//-------------------------------------------------------------------------------------- +// Internal functions forward declarations +//-------------------------------------------------------------------------------------- +bool DXUTFindMediaSearchTypicalDirs( _Out_writes_(cchSearch) WCHAR* strSearchPath, + _In_ int cchSearch, + _In_ LPCWSTR strLeaf, + _In_ const WCHAR* strExePath, + _In_ const WCHAR* strExeName ); +bool DXUTFindMediaSearchParentDirs( _Out_writes_(cchSearch) WCHAR* strSearchPath, + _In_ int cchSearch, + _In_ const WCHAR* strStartAt, + _In_ const WCHAR* strLeafName ); + +INT_PTR CALLBACK DisplaySwitchToREFWarningProc( _In_ HWND hDlg, _In_ UINT message, _In_ WPARAM wParam, _In_ LPARAM lParam ); + + +//-------------------------------------------------------------------------------------- +// Shared code for samples to ask user if they want to use a REF device or quit +//-------------------------------------------------------------------------------------- +void WINAPI DXUTDisplaySwitchingToREFWarning() +{ + if( DXUTGetShowMsgBoxOnError() ) + { + DWORD dwSkipWarning = 0, dwRead = 0, dwWritten = 0; + HANDLE hFile = nullptr; + + // Read previous user settings + WCHAR strPath[MAX_PATH]; + if ( SUCCEEDED(SHGetFolderPath(DXUTGetHWND(), CSIDL_LOCAL_APPDATA, nullptr, SHGFP_TYPE_CURRENT, strPath)) ) + { + wcscat_s( strPath, MAX_PATH, L"\\DXUT\\SkipRefWarning.dat" ); + if( ( hFile = CreateFile( strPath, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, 0, + nullptr ) ) != INVALID_HANDLE_VALUE ) + { + (void)ReadFile( hFile, &dwSkipWarning, sizeof( DWORD ), &dwRead, nullptr ); + CloseHandle( hFile ); + } + } + + if( dwSkipWarning == 0 ) + { + // Compact code to create a custom dialog box without using a template in a resource file. + // If this dialog were in a .rc file, this would be a lot simpler but every sample calling this function would + // need a copy of the dialog in its own .rc file. Also MessageBox API could be used here instead, but + // the MessageBox API is simpler to call but it can't provide a "Don't show again" checkbox + typedef struct + { + DLGITEMTEMPLATE a; + WORD b; + WORD c; + WORD d; + WORD e; + WORD f; + } DXUT_DLG_ITEM; + typedef struct + { + DLGTEMPLATE a; + WORD b; + WORD c; + WCHAR d[2]; + WORD e; + WCHAR f[16]; + DXUT_DLG_ITEM i1; + DXUT_DLG_ITEM i2; + DXUT_DLG_ITEM i3; + DXUT_DLG_ITEM i4; + DXUT_DLG_ITEM i5; + } DXUT_DLG_DATA; + + DXUT_DLG_DATA dtp = + { + {WS_CAPTION | WS_POPUP | WS_VISIBLE | WS_SYSMENU | DS_ABSALIGN | DS_3DLOOK | DS_SETFONT | + DS_MODALFRAME | DS_CENTER,0,5,0,0,269,82},0,0,L" ",8,L"MS Shell Dlg 2", + { {WS_CHILD | WS_VISIBLE | SS_ICON | SS_CENTERIMAGE,0,7,7,24,24,0x100},0xFFFF,0x0082,0,0,0}, // icon + { {WS_CHILD | WS_VISIBLE,0,40,7,230,25,0x101},0xFFFF,0x0082,0,0,0}, // static text + { {WS_CHILD | WS_VISIBLE | WS_TABSTOP | BS_DEFPUSHBUTTON,0,80,39,50,14,IDYES},0xFFFF,0x0080,0,0,0}, // Yes button + { {WS_CHILD | WS_VISIBLE | WS_TABSTOP,0,133,39,50,14,IDNO},0xFFFF,0x0080,0,0,0}, // No button + { {WS_CHILD | WS_VISIBLE | WS_TABSTOP | BS_CHECKBOX,0,7,59,70,16,IDIGNORE},0xFFFF,0x0080,0,0,0}, // checkbox + }; + + LPARAM lParam; + lParam = 11; + int nResult = ( int )DialogBoxIndirectParam( DXUTGetHINSTANCE(), ( DLGTEMPLATE* )&dtp, DXUTGetHWND(), + DisplaySwitchToREFWarningProc, lParam ); + + if( ( nResult & 0x80 ) == 0x80 ) // "Don't show again" checkbox was checked + { + // Save user settings + dwSkipWarning = 1; + if ( SUCCEEDED(SHGetFolderPath(DXUTGetHWND(), CSIDL_LOCAL_APPDATA, nullptr, SHGFP_TYPE_CURRENT, strPath)) ) + { + wcscat_s( strPath, MAX_PATH, L"\\DXUT" ); + CreateDirectory( strPath, nullptr ); + wcscat_s( strPath, MAX_PATH, L"\\SkipRefWarning.dat" ); + if( ( hFile = CreateFile( strPath, GENERIC_WRITE, 0, nullptr, CREATE_ALWAYS, 0, + nullptr ) ) != INVALID_HANDLE_VALUE ) + { + WriteFile( hFile, &dwSkipWarning, sizeof( DWORD ), &dwWritten, nullptr ); + CloseHandle( hFile ); + } + } + } + + // User choose not to continue + if( ( nResult & 0x0F ) == IDNO ) + DXUTShutdown( 1 ); + } + } +} + + +//-------------------------------------------------------------------------------------- +// MsgProc for DXUTDisplaySwitchingToREFWarning() dialog box +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +INT_PTR CALLBACK DisplaySwitchToREFWarningProc( HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam ) +{ + switch( message ) + { + case WM_INITDIALOG: + // Easier to set text here than in the DLGITEMTEMPLATE + SetWindowText( hDlg, DXUTGetWindowTitle() ); + SendMessage( GetDlgItem( hDlg, 0x100 ), STM_SETIMAGE, IMAGE_ICON, ( LPARAM )LoadIcon( 0, IDI_QUESTION ) ); + WCHAR sz[512]; + swprintf_s( sz, 512, + L"This program needs to use the Direct3D %zu reference device. This device implements the entire Direct3D %zu feature set, but runs very slowly. Do you wish to continue?", lParam, lParam ); + SetDlgItemText( hDlg, 0x101, sz ); + SetDlgItemText( hDlg, IDYES, L"&Yes" ); + SetDlgItemText( hDlg, IDNO, L"&No" ); + SetDlgItemText( hDlg, IDIGNORE, L"&Don't show again" ); + break; + + case WM_COMMAND: + switch( LOWORD( wParam ) ) + { + case IDIGNORE: + CheckDlgButton( hDlg, IDIGNORE, ( IsDlgButtonChecked( hDlg, + IDIGNORE ) == BST_CHECKED ) ? BST_UNCHECKED : + BST_CHECKED ); + EnableWindow( GetDlgItem( hDlg, IDNO ), ( IsDlgButtonChecked( hDlg, IDIGNORE ) != BST_CHECKED ) ); + break; + case IDNO: + EndDialog( hDlg, ( IsDlgButtonChecked( hDlg, IDIGNORE ) == BST_CHECKED ) ? IDNO | 0x80 : IDNO | + 0x00 ); return TRUE; + case IDCANCEL: + case IDYES: + EndDialog( hDlg, ( IsDlgButtonChecked( hDlg, IDIGNORE ) == BST_CHECKED ) ? IDYES | 0x80 : IDYES | + 0x00 ); return TRUE; + } + break; + } + return FALSE; +} + + +//-------------------------------------------------------------------------------------- +// Returns pointer to static media search buffer +//-------------------------------------------------------------------------------------- +WCHAR* DXUTMediaSearchPath() +{ + static WCHAR s_strMediaSearchPath[MAX_PATH] = + { + 0 + }; + return s_strMediaSearchPath; + +} + + +//-------------------------------------------------------------------------------------- +LPCWSTR WINAPI DXUTGetMediaSearchPath() +{ + return DXUTMediaSearchPath(); +} + + +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTSetMediaSearchPath( _In_z_ LPCWSTR strPath ) +{ + HRESULT hr; + + WCHAR* s_strSearchPath = DXUTMediaSearchPath(); + + hr = wcscpy_s( s_strSearchPath, MAX_PATH, strPath ); + if( SUCCEEDED( hr ) ) + { + // append slash if needed + size_t ch = 0; + ch = wcsnlen( s_strSearchPath, MAX_PATH); + if( SUCCEEDED( hr ) && s_strSearchPath[ch - 1] != L'\\' ) + { + hr = wcscat_s( s_strSearchPath, MAX_PATH, L"\\" ); + } + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Tries to find the location of a SDK media file +// cchDest is the size in WCHARs of strDestPath. Be careful not to +// pass in sizeof(strDest) on UNICODE builds. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT WINAPI DXUTFindDXSDKMediaFileCch( WCHAR* strDestPath, int cchDest, + LPCWSTR strFilename ) +{ + bool bFound; + WCHAR strSearchFor[MAX_PATH]; + + if( !strFilename || strFilename[0] == 0 || !strDestPath || cchDest < 10 ) + return E_INVALIDARG; + + // Get the exe name, and exe path + WCHAR strExePath[MAX_PATH] = + { + 0 + }; + WCHAR strExeName[MAX_PATH] = + { + 0 + }; + WCHAR* strLastSlash = nullptr; + GetModuleFileName( nullptr, strExePath, MAX_PATH ); + strExePath[MAX_PATH - 1] = 0; + strLastSlash = wcsrchr( strExePath, TEXT( '\\' ) ); + if( strLastSlash ) + { + wcscpy_s( strExeName, MAX_PATH, &strLastSlash[1] ); + + // Chop the exe name from the exe path + *strLastSlash = 0; + + // Chop the .exe from the exe name + strLastSlash = wcsrchr( strExeName, TEXT( '.' ) ); + if( strLastSlash ) + *strLastSlash = 0; + } + + // Typical directories: + // .\ + // ..\ + // ..\..\ + // %EXE_DIR%\ + // %EXE_DIR%\..\ + // %EXE_DIR%\..\..\ + // %EXE_DIR%\..\%EXE_NAME% + // %EXE_DIR%\..\..\%EXE_NAME% + + // Typical directory search + bFound = DXUTFindMediaSearchTypicalDirs( strDestPath, cchDest, strFilename, strExePath, strExeName ); + if( bFound ) + return S_OK; + + // Typical directory search again, but also look in a subdir called "\media\" + swprintf_s( strSearchFor, MAX_PATH, L"media\\%ls", strFilename ); + bFound = DXUTFindMediaSearchTypicalDirs( strDestPath, cchDest, strSearchFor, strExePath, strExeName ); + if( bFound ) + return S_OK; + + WCHAR strLeafName[MAX_PATH] = + { + 0 + }; + + // Search all parent directories starting at .\ and using strFilename as the leaf name + wcscpy_s( strLeafName, MAX_PATH, strFilename ); + bFound = DXUTFindMediaSearchParentDirs( strDestPath, cchDest, L".", strLeafName ); + if( bFound ) + return S_OK; + + // Search all parent directories starting at the exe's dir and using strFilename as the leaf name + bFound = DXUTFindMediaSearchParentDirs( strDestPath, cchDest, strExePath, strLeafName ); + if( bFound ) + return S_OK; + + // Search all parent directories starting at .\ and using "media\strFilename" as the leaf name + swprintf_s( strLeafName, MAX_PATH, L"media\\%ls", strFilename ); + bFound = DXUTFindMediaSearchParentDirs( strDestPath, cchDest, L".", strLeafName ); + if( bFound ) + return S_OK; + + // Search all parent directories starting at the exe's dir and using "media\strFilename" as the leaf name + bFound = DXUTFindMediaSearchParentDirs( strDestPath, cchDest, strExePath, strLeafName ); + if( bFound ) + return S_OK; + + // On failure, return the file as the path but also return an error code + wcscpy_s( strDestPath, cchDest, strFilename ); + + return DXUTERR_MEDIANOTFOUND; +} + + +//-------------------------------------------------------------------------------------- +// Search a set of typical directories +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DXUTFindMediaSearchTypicalDirs( WCHAR* strSearchPath, int cchSearch, LPCWSTR strLeaf, + const WCHAR* strExePath, const WCHAR* strExeName ) +{ + // Typical directories: + // .\ + // ..\ + // ..\..\ + // %EXE_DIR%\ + // %EXE_DIR%\..\ + // %EXE_DIR%\..\..\ + // %EXE_DIR%\..\%EXE_NAME% + // %EXE_DIR%\..\..\%EXE_NAME% + // DXSDK media path + + // Search in .\ + wcscpy_s( strSearchPath, cchSearch, strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in ..\ + swprintf_s( strSearchPath, cchSearch, L"..\\%ls", strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in ..\..\ + swprintf_s( strSearchPath, cchSearch, L"..\\..\\%ls", strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in ..\..\ + swprintf_s( strSearchPath, cchSearch, L"..\\..\\%ls", strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in the %EXE_DIR%\ + swprintf_s( strSearchPath, cchSearch, L"%ls\\%ls", strExePath, strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in the %EXE_DIR%\..\ + swprintf_s( strSearchPath, cchSearch, L"%ls\\..\\%ls", strExePath, strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in the %EXE_DIR%\..\..\ + swprintf_s( strSearchPath, cchSearch, L"%ls\\..\\..\\%ls", strExePath, strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in "%EXE_DIR%\..\%EXE_NAME%\". This matches the DirectX SDK layout + swprintf_s( strSearchPath, cchSearch, L"%ls\\..\\%ls\\%ls", strExePath, strExeName, strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in "%EXE_DIR%\..\..\%EXE_NAME%\". This matches the DirectX SDK layout + swprintf_s( strSearchPath, cchSearch, L"%ls\\..\\..\\%ls\\%ls", strExePath, strExeName, strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + + // Search in media search dir + WCHAR* s_strSearchPath = DXUTMediaSearchPath(); + if( s_strSearchPath[0] != 0 ) + { + swprintf_s( strSearchPath, cchSearch, L"%ls%ls", s_strSearchPath, strLeaf ); + if( GetFileAttributes( strSearchPath ) != 0xFFFFFFFF ) + return true; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +// Search parent directories starting at strStartAt, and appending strLeafName +// at each parent directory. It stops at the root directory. +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +bool DXUTFindMediaSearchParentDirs( WCHAR* strSearchPath, int cchSearch, const WCHAR* strStartAt, + const WCHAR* strLeafName ) +{ + WCHAR strFullPath[MAX_PATH] = + { + 0 + }; + WCHAR strFullFileName[MAX_PATH] = + { + 0 + }; + WCHAR strSearch[MAX_PATH] = + { + 0 + }; + WCHAR* strFilePart = nullptr; + + if ( !GetFullPathName( strStartAt, MAX_PATH, strFullPath, &strFilePart ) ) + return false; + +#pragma warning( disable : 6102 ) + while( strFilePart && *strFilePart != '\0' ) + { + swprintf_s( strFullFileName, MAX_PATH, L"%ls\\%ls", strFullPath, strLeafName ); + if( GetFileAttributes( strFullFileName ) != 0xFFFFFFFF ) + { + wcscpy_s( strSearchPath, cchSearch, strFullFileName ); + return true; + } + + swprintf_s( strSearch, MAX_PATH, L"%ls\\..", strFullPath ); + if ( !GetFullPathName( strSearch, MAX_PATH, strFullPath, &strFilePart ) ) + return false; + } + + return false; +} + + +//-------------------------------------------------------------------------------------- +// Compiles HLSL shaders +//-------------------------------------------------------------------------------------- +#if D3D_COMPILER_VERSION < 46 + +namespace +{ + +struct handle_closer { void operator()(HANDLE h) { if (h) CloseHandle(h); } }; + +typedef std::unique_ptr ScopedHandle; + +inline HANDLE safe_handle( HANDLE h ) { return (h == INVALID_HANDLE_VALUE) ? nullptr : h; } + +class CIncludeHandler : public ID3DInclude + // Not as robust as D3D_COMPILE_STANDARD_FILE_INCLUDE, but it works in most cases +{ +private: + static const unsigned int MAX_INCLUDES = 9; + + struct sInclude + { + HANDLE hFile; + HANDLE hFileMap; + LARGE_INTEGER FileSize; + void *pMapData; + }; + + struct sInclude m_includeFiles[MAX_INCLUDES]; + size_t m_nIncludes; + bool m_reset; + WCHAR m_workingPath[MAX_PATH]; + +public: + CIncludeHandler() : m_nIncludes(0), m_reset(false) + { + if ( !GetCurrentDirectoryW( MAX_PATH, m_workingPath ) ) + *m_workingPath = 0; + + for ( size_t i = 0; i < MAX_INCLUDES; ++i ) + { + m_includeFiles[i].hFile = INVALID_HANDLE_VALUE; + m_includeFiles[i].hFileMap = INVALID_HANDLE_VALUE; + m_includeFiles[i].pMapData = nullptr; + } + } + virtual ~CIncludeHandler() + { + for ( size_t i = 0; i < m_nIncludes; ++i ) + { + UnmapViewOfFile( m_includeFiles[i].pMapData ); + + if ( m_includeFiles[i].hFileMap != INVALID_HANDLE_VALUE) + CloseHandle( m_includeFiles[i].hFileMap ); + + if ( m_includeFiles[i].hFile != INVALID_HANDLE_VALUE) + CloseHandle( m_includeFiles[i].hFile ); + } + + m_nIncludes = 0; + + if ( m_reset && *m_workingPath ) + { + SetCurrentDirectoryW( m_workingPath ); + } + } + + STDMETHOD(Open( D3D_INCLUDE_TYPE IncludeType, LPCSTR pFileName, LPCVOID pParentData, LPCVOID *ppData, UINT *pBytes ) ) + { + UNREFERENCED_PARAMETER(IncludeType); + UNREFERENCED_PARAMETER(pParentData); + + size_t incIndex = m_nIncludes+1; + + // Make sure we have enough room for this include file + if ( incIndex >= MAX_INCLUDES ) + return E_FAIL; + + // try to open the file + m_includeFiles[incIndex].hFile = CreateFileA( pFileName, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, FILE_FLAG_SEQUENTIAL_SCAN, nullptr ); + if( INVALID_HANDLE_VALUE == m_includeFiles[incIndex].hFile ) + { + return E_FAIL; + } + + // Get the file size + GetFileSizeEx( m_includeFiles[incIndex].hFile, &m_includeFiles[incIndex].FileSize ); + + // Use Memory Mapped File I/O for the header data + m_includeFiles[incIndex].hFileMap = CreateFileMappingA( m_includeFiles[incIndex].hFile, nullptr, PAGE_READONLY, m_includeFiles[incIndex].FileSize.HighPart, m_includeFiles[incIndex].FileSize.LowPart, pFileName); + if( !m_includeFiles[incIndex].hFileMap ) + { + if (m_includeFiles[incIndex].hFile != INVALID_HANDLE_VALUE) + CloseHandle( m_includeFiles[incIndex].hFile ); + return E_FAIL; + } + + // Create Map view + *ppData = MapViewOfFile( m_includeFiles[incIndex].hFileMap, FILE_MAP_READ, 0, 0, 0 ); + *pBytes = m_includeFiles[incIndex].FileSize.LowPart; + + // Success - Increment the include file count + m_nIncludes = incIndex; + + return S_OK; + } + + STDMETHOD(Close( LPCVOID pData )) + { + UNREFERENCED_PARAMETER(pData); + // Defer Closure until the container destructor + return S_OK; + } + + void SetCWD( LPCWSTR pFileName ) + { + WCHAR filePath[MAX_PATH]; + wcscpy_s( filePath, MAX_PATH, pFileName ); + + WCHAR *strLastSlash = wcsrchr( filePath, L'\\' ); + if( strLastSlash ) + { + // Chop the exe name from the exe path + *strLastSlash = 0; + m_reset = true; + SetCurrentDirectoryW( filePath ); + } + } +}; + +}; // namespace + +#endif + +_Use_decl_annotations_ +HRESULT WINAPI DXUTCompileFromFile( LPCWSTR pFileName, + const D3D_SHADER_MACRO* pDefines, + LPCSTR pEntrypoint, LPCSTR pTarget, + UINT Flags1, UINT Flags2, + ID3DBlob** ppCode ) +{ + HRESULT hr; + WCHAR str[MAX_PATH]; + V_RETURN( DXUTFindDXSDKMediaFileCch( str, MAX_PATH, pFileName ) ); + +#if defined( DEBUG ) || defined( _DEBUG ) + // Set the D3DCOMPILE_DEBUG flag to embed debug information in the shaders. + // Setting this flag improves the shader debugging experience, but still allows + // the shaders to be optimized and to run exactly the way they will run in + // the release configuration of this program. + Flags1 |= D3DCOMPILE_DEBUG; +#endif + + ID3DBlob* pErrorBlob = nullptr; + +#if D3D_COMPILER_VERSION >= 46 + + hr = D3DCompileFromFile( str, pDefines, D3D_COMPILE_STANDARD_FILE_INCLUDE, + pEntrypoint, pTarget, Flags1, Flags2, + ppCode, &pErrorBlob ); + +#else + + ScopedHandle hFile( safe_handle( CreateFileW( str, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, nullptr ) ) ); + + if ( !hFile ) + return HRESULT_FROM_WIN32( GetLastError() ); + + FILE_STANDARD_INFO fileInfo; + if ( !GetFileInformationByHandleEx( hFile.get(), FileStandardInfo, &fileInfo, sizeof(fileInfo) ) ) + { + return HRESULT_FROM_WIN32( GetLastError() ); + } + + if ( !fileInfo.EndOfFile.LowPart || fileInfo.EndOfFile.HighPart > 0 ) + return E_FAIL; + + std::unique_ptr fxData; + fxData.reset( new (std::nothrow) char[ fileInfo.EndOfFile.LowPart ] ); + if ( !fxData ) + return E_OUTOFMEMORY; + + DWORD BytesRead = 0; + if ( !ReadFile( hFile.get(), fxData.get(), fileInfo.EndOfFile.LowPart, &BytesRead, nullptr ) ) + return HRESULT_FROM_WIN32( GetLastError() ); + + if (BytesRead < fileInfo.EndOfFile.LowPart) + return E_FAIL; + + char pSrcName[MAX_PATH]; + int result = WideCharToMultiByte( CP_ACP, WC_NO_BEST_FIT_CHARS, str, -1, pSrcName, MAX_PATH, nullptr, FALSE ); + if ( !result ) + return E_FAIL; + + const CHAR* pstrName = strrchr( pSrcName, '\\' ); + if (!pstrName) + { + pstrName = pSrcName; + } + else + { + pstrName++; + } + + std::unique_ptr includes( new (std::nothrow) CIncludeHandler ); + if ( !includes ) + return E_OUTOFMEMORY; + + includes->SetCWD( str ); + + hr = D3DCompile( fxData.get(), BytesRead, pstrName, pDefines, includes.get(), + pEntrypoint, pTarget, Flags1, Flags2, + ppCode, &pErrorBlob ); + +#endif + +#pragma warning( suppress : 6102 ) + if ( pErrorBlob ) + { + OutputDebugStringA( reinterpret_cast( pErrorBlob->GetBufferPointer() ) ); + pErrorBlob->Release(); + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Texture utilities +//-------------------------------------------------------------------------------------- + +_Use_decl_annotations_ +HRESULT WINAPI DXUTCreateShaderResourceViewFromFile( ID3D11Device* d3dDevice, const wchar_t* szFileName, ID3D11ShaderResourceView** textureView ) +{ + if ( !d3dDevice || !szFileName || !textureView ) + return E_INVALIDARG; + + WCHAR str[MAX_PATH]; + HRESULT hr = DXUTFindDXSDKMediaFileCch( str, MAX_PATH, szFileName ); + if ( FAILED(hr) ) + return hr; + + WCHAR ext[_MAX_EXT]; + _wsplitpath_s( str, nullptr, 0, nullptr, 0, nullptr, 0, ext, _MAX_EXT ); + + if ( _wcsicmp( ext, L".dds" ) == 0 ) + { + hr = DirectX::CreateDDSTextureFromFile( d3dDevice, str, nullptr, textureView ); + } + else + { + hr = DirectX::CreateWICTextureFromFile( d3dDevice, nullptr, str, nullptr, textureView ); + } + + return hr; +} + +_Use_decl_annotations_ +HRESULT WINAPI DXUTCreateTextureFromFile( ID3D11Device* d3dDevice, const wchar_t* szFileName, ID3D11Resource** texture ) +{ + if ( !d3dDevice || !szFileName || !texture ) + return E_INVALIDARG; + + WCHAR str[MAX_PATH]; + HRESULT hr = DXUTFindDXSDKMediaFileCch( str, MAX_PATH, szFileName ); + if ( FAILED(hr) ) + return hr; + + WCHAR ext[_MAX_EXT]; + _wsplitpath_s( str, nullptr, 0, nullptr, 0, nullptr, 0, ext, _MAX_EXT ); + + if ( _wcsicmp( ext, L".dds" ) == 0 ) + { + hr = DirectX::CreateDDSTextureFromFile( d3dDevice, str, texture, nullptr ); + } + else + { + hr = DirectX::CreateWICTextureFromFile( d3dDevice, nullptr, str, texture, nullptr ); + } + + return hr; +} + +_Use_decl_annotations_ +HRESULT WINAPI DXUTSaveTextureToFile( ID3D11DeviceContext* pContext, ID3D11Resource* pSource, bool usedds, const wchar_t* szFileName ) +{ + if ( !pContext || !pSource || !szFileName ) + return E_INVALIDARG; + + HRESULT hr; + + if ( usedds ) + { + hr = DirectX::SaveDDSTextureToFile( pContext, pSource, szFileName ); + } + else + { + hr = DirectX::SaveWICTextureToFile( pContext, pSource, GUID_ContainerFormatBmp, szFileName ); + } + + return hr; +} + + +//-------------------------------------------------------------------------------------- +// Desc: Returns a view matrix for rendering to a face of a cubemap. +//-------------------------------------------------------------------------------------- +XMMATRIX WINAPI DXUTGetCubeMapViewMatrix( _In_ DWORD dwFace ) +{ + static const XMVECTORF32 s_vLookDir[] = + { + { 1.0f, 0.0f, 0.0f, 0.0f }, + { -1.0f, 0.0f, 0.0f, 0.0f }, + { 0.0f, 1.0f, 0.0f, 0.0f }, + { 0.0f, -1.0f, 0.0f, 0.0f }, + { 0.0f, 0.0f, 1.0f, 0.0f }, + { 0.0f, 0.0f, -1.0f, 0.0f }, + }; + + static const XMVECTORF32 s_vUpDir[] = + { + { 0.0f, 1.0f, 0.0f, 0.0f }, + { 0.0f, 1.0f, 0.0f, 0.0f }, + { 0.0f, 0.0f, -1.0f, 0.0f }, + { 0.0f, 0.0f, 1.0f, 0.0f }, + { 0.0f, 1.0f, 0.0f, 0.0f }, + { 0.0f, 1.0f, 0.0f, 0.0f }, + }; + + static_assert( _countof(s_vLookDir) == _countof(s_vUpDir), "arrays mismatch" ); + + if ( dwFace >= _countof(s_vLookDir) + || dwFace >= _countof(s_vUpDir) ) + return XMMatrixIdentity(); + + // Set the view transform for this cubemap surface + return XMMatrixLookAtLH( g_XMZero, s_vLookDir[ dwFace ], s_vUpDir[ dwFace ] ); +} + + +//====================================================================================== +// CDXUTResourceCache +//====================================================================================== + +CDXUTResourceCache::~CDXUTResourceCache() +{ + OnDestroyDevice(); +} + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTResourceCache::CreateTextureFromFile( ID3D11Device* pDevice, ID3D11DeviceContext *pContext, LPCWSTR pSrcFile, + ID3D11ShaderResourceView** ppOutputRV, bool bSRGB ) +{ + if ( !ppOutputRV ) + return E_INVALIDARG; + + *ppOutputRV = nullptr; + + for( auto it = m_TextureCache.cbegin(); it != m_TextureCache.cend(); ++it ) + { + if( !wcscmp( it->wszSource, pSrcFile ) + && it->bSRGB == bSRGB + && it->pSRV11 ) + { + it->pSRV11->AddRef(); + *ppOutputRV = it->pSRV11; + return S_OK; + } + } + + WCHAR ext[_MAX_EXT]; + _wsplitpath_s( pSrcFile, nullptr, 0, nullptr, 0, nullptr, 0, ext, _MAX_EXT ); + + HRESULT hr; + if ( _wcsicmp( ext, L".dds" ) == 0 ) + { + hr = DirectX::CreateDDSTextureFromFileEx( pDevice, pSrcFile, 0, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, bSRGB, + nullptr, ppOutputRV, nullptr ); + } + else + { + hr = DirectX::CreateWICTextureFromFileEx( pDevice, pContext, pSrcFile, 0, + D3D11_USAGE_DEFAULT, D3D11_BIND_SHADER_RESOURCE, 0, 0, + bSRGB ? DirectX::WIC_LOADER_FORCE_SRGB : DirectX::WIC_LOADER_DEFAULT, + nullptr, ppOutputRV ); + } + + if ( FAILED(hr) ) + return hr; + + DXUTCache_Texture entry; + wcscpy_s( entry.wszSource, MAX_PATH, pSrcFile ); + entry.bSRGB = bSRGB; + entry.pSRV11 = *ppOutputRV; + entry.pSRV11->AddRef(); + m_TextureCache.push_back( entry ); + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTResourceCache::CreateTextureFromFile( ID3D11Device* pDevice, ID3D11DeviceContext *pContext, LPCSTR pSrcFile, + ID3D11ShaderResourceView** ppOutputRV, bool bSRGB ) +{ + WCHAR szSrcFile[MAX_PATH]; + MultiByteToWideChar( CP_ACP, 0, pSrcFile, -1, szSrcFile, MAX_PATH ); + szSrcFile[MAX_PATH - 1] = 0; + + return CreateTextureFromFile( pDevice, pContext, szSrcFile, ppOutputRV, bSRGB ); +} + + +//-------------------------------------------------------------------------------------- +// Device event callbacks +//-------------------------------------------------------------------------------------- + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTResourceCache::OnDestroyDevice() +{ + // Release all resources + for( size_t j = 0; j < m_TextureCache.size(); ++j ) + { + SAFE_RELEASE( m_TextureCache[ j ].pSRV11 ); + } + m_TextureCache.clear(); + m_TextureCache.shrink_to_fit(); + + return S_OK; +} + + +//====================================================================================== +// CDXUTTextHelper +//====================================================================================== + +_Use_decl_annotations_ +CDXUTTextHelper::CDXUTTextHelper( ID3D11Device* pd3d11Device, ID3D11DeviceContext* pd3d11DeviceContext, CDXUTDialogResourceManager* pManager, int nLineHeight ) : + m_clr(0, 0, 0, 0), + m_pt{ 0, 0 }, + m_nLineHeight{}, + m_pd3d11Device(nullptr), + m_pd3d11DeviceContext(nullptr), + m_pManager(nullptr) +{ + Init( nLineHeight ); + + m_pd3d11Device = pd3d11Device; + m_pd3d11DeviceContext = pd3d11DeviceContext; + m_pManager = pManager; +} + +CDXUTTextHelper::~CDXUTTextHelper() +{ + +} + + +//-------------------------------------------------------------------------------------- +void CDXUTTextHelper::Init( _In_ int nLineHeight ) +{ + m_clr = XMFLOAT4( 1, 1, 1, 1 ); + m_pt.x = 0; + m_pt.y = 0; + m_nLineHeight = nLineHeight; + m_pd3d11Device = nullptr; + m_pd3d11DeviceContext = nullptr; + m_pManager = nullptr; + + // Create a blend state if a sprite is passed in +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTTextHelper::DrawFormattedTextLine( _In_z_ const WCHAR* strMsg, ... ) +{ + WCHAR strBuffer[512]; + + va_list args; + va_start( args, strMsg ); + vswprintf_s( strBuffer, 512, strMsg, args ); + strBuffer[511] = L'\0'; + va_end( args ); + + return DrawTextLine( strBuffer ); +} + + +//-------------------------------------------------------------------------------------- +HRESULT CDXUTTextHelper::DrawTextLine( _In_z_ const WCHAR* strMsg ) +{ + if( !m_pd3d11DeviceContext ) + return DXUT_ERR_MSGBOX( L"DrawTextLine", E_INVALIDARG ); + + HRESULT hr = S_OK; + RECT rc; + SetRect( &rc, m_pt.x, m_pt.y, 0, 0 ); + DrawText11DXUT( m_pd3d11Device, m_pd3d11DeviceContext, strMsg, rc, m_clr, + (float)m_pManager->m_nBackBufferWidth, (float)m_pManager->m_nBackBufferHeight, false ); + + if( FAILED( hr ) ) + return DXTRACE_ERR_MSGBOX( L"DrawText", hr ); + + m_pt.y += m_nLineHeight; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTTextHelper::DrawFormattedTextLine( const RECT& rc, const WCHAR* strMsg, ... ) +{ + WCHAR strBuffer[512]; + + va_list args; + va_start( args, strMsg ); + vswprintf_s( strBuffer, 512, strMsg, args ); + strBuffer[511] = L'\0'; + va_end( args ); + + return DrawTextLine( rc, strBuffer ); +} + + +//-------------------------------------------------------------------------------------- +_Use_decl_annotations_ +HRESULT CDXUTTextHelper::DrawTextLine( const RECT& rc, const WCHAR* strMsg ) +{ + if( !m_pd3d11DeviceContext ) + return DXUT_ERR_MSGBOX( L"DrawTextLine", E_INVALIDARG ); + + HRESULT hr = S_OK; + DrawText11DXUT( m_pd3d11Device, m_pd3d11DeviceContext, strMsg, rc, m_clr, + (float)m_pManager->m_nBackBufferWidth, (float)m_pManager->m_nBackBufferHeight, false ); + + if( FAILED( hr ) ) + return DXTRACE_ERR_MSGBOX( L"DrawText", hr ); + + m_pt.y += m_nLineHeight; + + return S_OK; +} + + +//-------------------------------------------------------------------------------------- +void CDXUTTextHelper::Begin() +{ + if( m_pd3d11DeviceContext ) + { + m_pManager->StoreD3D11State( m_pd3d11DeviceContext ); + m_pManager->ApplyRenderUI11( m_pd3d11DeviceContext ); + } + + +} + + +//-------------------------------------------------------------------------------------- +void CDXUTTextHelper::End() +{ + if( m_pd3d11DeviceContext ) + { + m_pManager->RestoreD3D11State( m_pd3d11DeviceContext ); + } +} diff --git a/src/DX11/framework/dxut/Optional/SDKmisc.h b/src/DX11/framework/dxut/Optional/SDKmisc.h new file mode 100644 index 0000000..a2689f7 --- /dev/null +++ b/src/DX11/framework/dxut/Optional/SDKmisc.h @@ -0,0 +1,132 @@ +//-------------------------------------------------------------------------------------- +// File: SDKMisc.h +// +// Various helper functionality that is shared between SDK samples +// +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. +// +// http://go.microsoft.com/fwlink/?LinkId=320437 +//-------------------------------------------------------------------------------------- +#pragma once + +//----------------------------------------------------------------------------- +// Resource cache for textures, fonts, meshs, and effects. +// Use DXUTGetGlobalResourceCache() to access the global cache +//----------------------------------------------------------------------------- + +struct DXUTCache_Texture +{ + WCHAR wszSource[MAX_PATH]; + bool bSRGB; + ID3D11ShaderResourceView* pSRV11; + + DXUTCache_Texture() noexcept : + wszSource{}, + bSRGB(false), + pSRV11(nullptr) + { + } +}; + + +class CDXUTResourceCache +{ +public: + ~CDXUTResourceCache(); + + HRESULT CreateTextureFromFile( _In_ ID3D11Device* pDevice, _In_ ID3D11DeviceContext *pContext, _In_z_ LPCWSTR pSrcFile, + _Outptr_ ID3D11ShaderResourceView** ppOutputRV, _In_ bool bSRGB=false ); + HRESULT CreateTextureFromFile( _In_ ID3D11Device* pDevice, _In_ ID3D11DeviceContext *pContext, _In_z_ LPCSTR pSrcFile, + _Outptr_ ID3D11ShaderResourceView** ppOutputRV, _In_ bool bSRGB=false ); +public: + HRESULT OnDestroyDevice(); + +protected: + friend CDXUTResourceCache& WINAPI DXUTGetGlobalResourceCache(); + friend HRESULT WINAPI DXUTInitialize3DEnvironment(); + friend HRESULT WINAPI DXUTReset3DEnvironment(); + friend void WINAPI DXUTCleanup3DEnvironment( bool bReleaseSettings ); + + CDXUTResourceCache() = default; + + std::vector m_TextureCache; +}; + +CDXUTResourceCache& WINAPI DXUTGetGlobalResourceCache(); + + +//-------------------------------------------------------------------------------------- +// Manages the insertion point when drawing text +//-------------------------------------------------------------------------------------- +class CDXUTDialogResourceManager; +class CDXUTTextHelper +{ +public: + CDXUTTextHelper( _In_ ID3D11Device* pd3d11Device, _In_ ID3D11DeviceContext* pd3dDeviceContext, _In_ CDXUTDialogResourceManager* pManager, _In_ int nLineHeight ); + ~CDXUTTextHelper(); + + void Init( _In_ int nLineHeight = 15 ); + + void SetInsertionPos( _In_ int x, _In_ int y ) + { + m_pt.x = x; + m_pt.y = y; + } + void SetForegroundColor( _In_ DirectX::XMFLOAT4 clr ) { m_clr = clr; } + void SetForegroundColor( _In_ DirectX::FXMVECTOR clr ) { XMStoreFloat4( &m_clr, clr ); } + + void Begin(); + HRESULT DrawFormattedTextLine( _In_z_ const WCHAR* strMsg, ... ); + HRESULT DrawTextLine( _In_z_ const WCHAR* strMsg ); + HRESULT DrawFormattedTextLine( _In_ const RECT& rc, _In_z_ const WCHAR* strMsg, ... ); + HRESULT DrawTextLine( _In_ const RECT& rc, _In_z_ const WCHAR* strMsg ); + void End(); + +protected: + DirectX::XMFLOAT4 m_clr; + POINT m_pt; + int m_nLineHeight; + + // D3D11 font + ID3D11Device* m_pd3d11Device; + ID3D11DeviceContext* m_pd3d11DeviceContext; + CDXUTDialogResourceManager* m_pManager; +}; + + +//-------------------------------------------------------------------------------------- +// Shared code for samples to ask user if they want to use a REF device or quit +//-------------------------------------------------------------------------------------- +void WINAPI DXUTDisplaySwitchingToREFWarning(); + +//-------------------------------------------------------------------------------------- +// Tries to finds a media file by searching in common locations +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTFindDXSDKMediaFileCch( _Out_writes_(cchDest) WCHAR* strDestPath, + _In_ int cchDest, + _In_z_ LPCWSTR strFilename ); +HRESULT WINAPI DXUTSetMediaSearchPath( _In_z_ LPCWSTR strPath ); +LPCWSTR WINAPI DXUTGetMediaSearchPath(); + + +//-------------------------------------------------------------------------------------- +// Compiles HLSL shaders +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTCompileFromFile( _In_z_ LPCWSTR pFileName, + _In_reads_opt_(_Inexpressible_(pDefines->Name != NULL)) const D3D_SHADER_MACRO* pDefines, + _In_z_ LPCSTR pEntrypoint, _In_z_ LPCSTR pTarget, + _In_ UINT Flags1, _In_ UINT Flags2, + _Outptr_ ID3DBlob** ppCode ); + +//-------------------------------------------------------------------------------------- +// Texture utilities +//-------------------------------------------------------------------------------------- +HRESULT WINAPI DXUTCreateShaderResourceViewFromFile( _In_ ID3D11Device* d3dDevice, _In_z_ const wchar_t* szFileName, _Outptr_ ID3D11ShaderResourceView** textureView ); +HRESULT WINAPI DXUTCreateTextureFromFile( _In_ ID3D11Device* d3dDevice, _In_z_ const wchar_t* szFileName, _Outptr_ ID3D11Resource** texture ); +HRESULT WINAPI DXUTSaveTextureToFile( _In_ ID3D11DeviceContext* pContext, _In_ ID3D11Resource* pSource, _In_ bool usedds, _In_z_ const wchar_t* szFileName ); + +//-------------------------------------------------------------------------------------- +// Returns a view matrix for rendering to a face of a cubemap. +//-------------------------------------------------------------------------------------- +DirectX::XMMATRIX WINAPI DXUTGetCubeMapViewMatrix( _In_ DWORD dwFace ); diff --git a/src/DX11/framework/dxut/Optional/directx.ico b/src/DX11/framework/dxut/Optional/directx.ico new file mode 100644 index 0000000..bc43c1b Binary files /dev/null and b/src/DX11/framework/dxut/Optional/directx.ico differ diff --git a/src/DX11/framework/dxut/README.md b/src/DX11/framework/dxut/README.md new file mode 100644 index 0000000..65d67f1 --- /dev/null +++ b/src/DX11/framework/dxut/README.md @@ -0,0 +1,62 @@ +![DirectX Logo](https://raw.githubusercontent.com/wiki/Microsoft/DXUT/Dx_logo.GIF) + +# DXUT for Direct3D 11 + +http://go.microsoft.com/fwlink/?LinkId=320437 + +Copyright (c) Microsoft Corporation. + +**December 2, 2021** + +DXUT is a "GLUT"-like framework for Direct3D 11.x Win32 desktop applications; primarily samples, demos, and prototypes. + +This code is designed to build with Visual Studio 2017 ([15.9](https://walbourn.github.io/vs-2017-15-9-update/)) or Visual Studio 2019. It is recommended that you make use of the Windows 10 May 2020 Update SDK ([19041](https://walbourn.github.io/windows-10-may-2020-update-sdk/)). + +These components are designed to work without requiring any content from the legacy DirectX SDK. For details, see [Where is the DirectX SDK?](https://aka.ms/dxsdk). + +## Documentation + +Documentation is available on the [GitHub wiki](https://github.com/Microsoft/DXUT/wiki). + +## Notices + +*This project is 'archived'. It is still available for use for legacy projects, but use of it for new projects is not recommended.* + +All content and source code for this package are subject to the terms of the [MIT License](http://opensource.org/licenses/MIT). + +## Contributing + +This project welcomes contributions and suggestions. Most contributions require you to agree to a Contributor License Agreement (CLA) declaring that you have the right to, and actually do, grant us the rights to use your contribution. For details, visit https://cla.opensource.microsoft.com. + +When you submit a pull request, a CLA bot will automatically determine whether you need to provide a CLA and decorate the PR appropriately (e.g., status check, comment). Simply follow the instructions provided by the bot. You will only need to do this once across all repos using our CLA. + +This project has adopted the [Microsoft Open Source Code of Conduct](https://opensource.microsoft.com/codeofconduct/). For more information see the [Code of Conduct FAQ](https://opensource.microsoft.com/codeofconduct/faq/) or contact [opencode@microsoft.com](mailto:opencode@microsoft.com) with any additional questions or comments. + +## Trademarks + +This project may contain trademarks or logos for projects, products, or services. Authorized use of Microsoft trademarks or logos is subject to and must follow [Microsoft's Trademark & Brand Guidelines](https://www.microsoft.com/en-us/legal/intellectualproperty/trademarks/usage/general). Use of Microsoft trademarks or logos in modified versions of this project must not cause confusion or imply Microsoft sponsorship. Any use of third-party trademarks or logos are subject to those third-party's policies. + +## Credits + +The DXUT library is the work of Shanon Drone, Jason Sandlin, and David Tuft with contributions from David Cook, Kev Gee, Matt Lee, and Chuck Walbourn. + +## Samples + +* Direct3D Tutorial08 - 10 +* BasicHLSL11, EmptyProject11, SimpleSample11 +* DXUT+DirectXTK Simple Sample + +These are hosted on [GitHub](https://github.com/walbourn/directx-sdk-samples) + +## Disclaimer + +DXUT is being provided as a porting aid for older code that makes use of the legacy DirectX SDK, the deprecated D3DX9/D3DX11 library, and the DXUT11 framework. It is a cleaned up version of the original DXUT11 that will build with the Windows 8.1 / 10 SDK and does not make use of any legacy DirectX SDK or DirectSetup deployed components. + +The DXUT framework is for use in Win32 desktop applications. It not usable for Universal Windows Platform apps, Windows Store apps, +Xbox, or Windows phone. + +This version of DXUT only supports Direct3D 11, and therefore is not compatible with Windows XP or early versions of Windows Vista. + +## Release Notes + +* The VS 2017/2019 projects make use of ``/permissive-`` for improved C++ standard conformance. Use of a Windows 10 SDK prior to the Fall Creators Update (16299) or an Xbox One XDK prior to June 2017 QFE 4 may result in failures due to problems with the system headers. You can work around these by disabling this switch in the project files which is found in the ```` elements, or in some cases adding ``/Zc:twoPhase-`` to the ```` elements. diff --git a/src/ffx-fsr2-api/CMakeLists.txt b/src/ffx-fsr2-api/CMakeLists.txt index 6195dee..47aba59 100644 --- a/src/ffx-fsr2-api/CMakeLists.txt +++ b/src/ffx-fsr2-api/CMakeLists.txt @@ -22,6 +22,7 @@ cmake_minimum_required(VERSION 3.15) set(CMAKE_DEBUG_POSTFIX d) +option (FFX_FSR2_API_DX11 "Build FSR 2.0 DX11 backend" ON) option (FFX_FSR2_API_DX12 "Build FSR 2.0 DX12 backend" ON) option (FFX_FSR2_API_VK "Build FSR 2.0 Vulkan backend" ON) @@ -97,6 +98,10 @@ else() endif() # graphics api backends +if(FFX_FSR2_API_DX11) + message("Will build FSR2 library: DX11 backend") + add_subdirectory(dx11) +endif() if(FFX_FSR2_API_DX12) message("Will build FSR2 library: DX12 backend") add_subdirectory(dx12) diff --git a/src/ffx-fsr2-api/dx11/CMakeLists.txt b/src/ffx-fsr2-api/dx11/CMakeLists.txt new file mode 100644 index 0000000..db7e37b --- /dev/null +++ b/src/ffx-fsr2-api/dx11/CMakeLists.txt @@ -0,0 +1,132 @@ +# This file is part of the FidelityFX SDK. +# +# Copyright (c) 2022-2023 Advanced Micro Devices, Inc. All rights reserved. +# +# Permission is hereby granted, free of charge, to any person obtaining a copy +# of this software and associated documentation files (the "Software"), to deal +# in the Software without restriction, including without limitation the rights +# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +# copies of the Software, and to permit persons to whom the Software is +# furnished to do so, subject to the following conditions: +# The above copyright notice and this permission notice shall be included in +# all copies or substantial portions of the Software. +# +# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +# THE SOFTWARE. + +if(NOT ${FFX_FSR2_API_DX11}) + return() +endif() + +set(FFX_SC_DX11_BASE_ARGS + -E CS -DFFX_HLSL=1 -DFFX_HLSL_5_0=1 -compiler=fxc -DSPD_NO_WAVE_OPERATIONS) + +file(GLOB SHADERS + "${CMAKE_CURRENT_SOURCE_DIR}/../shaders/*.h" + "${CMAKE_CURRENT_SOURCE_DIR}/../shaders/*.hlsl") + +set(PASS_SHADERS + ${CMAKE_CURRENT_SOURCE_DIR}/../shaders/ffx_fsr2_tcr_autogen_pass.hlsl + ${CMAKE_CURRENT_SOURCE_DIR}/../shaders/ffx_fsr2_autogen_reactive_pass.hlsl + ${CMAKE_CURRENT_SOURCE_DIR}/../shaders/ffx_fsr2_accumulate_pass.hlsl + ${CMAKE_CURRENT_SOURCE_DIR}/../shaders/ffx_fsr2_compute_luminance_pyramid_pass.hlsl + ${CMAKE_CURRENT_SOURCE_DIR}/../shaders/ffx_fsr2_depth_clip_pass.hlsl + ${CMAKE_CURRENT_SOURCE_DIR}/../shaders/ffx_fsr2_lock_pass.hlsl + ${CMAKE_CURRENT_SOURCE_DIR}/../shaders/ffx_fsr2_reconstruct_previous_depth_pass.hlsl + ${CMAKE_CURRENT_SOURCE_DIR}/../shaders/ffx_fsr2_rcas_pass.hlsl) + +file(GLOB_RECURSE DX11 + "${CMAKE_CURRENT_SOURCE_DIR}/../ffx_assert.cpp" + "${CMAKE_CURRENT_SOURCE_DIR}/*.h" + "${CMAKE_CURRENT_SOURCE_DIR}/*.cpp") + +if (FSR2_BUILD_AS_DLL) + add_library(ffx_fsr2_api_dx11_${FSR2_PLATFORM_NAME} SHARED ${DX11}) + target_link_libraries(ffx_fsr2_api_dx11_${FSR2_PLATFORM_NAME} PRIVATE dxguid) +else() + add_library(ffx_fsr2_api_dx11_${FSR2_PLATFORM_NAME} STATIC ${DX11}) +endif() + +target_include_directories(ffx_fsr2_api_dx11_${FSR2_PLATFORM_NAME} PUBLIC ${CMAKE_CURRENT_BINARY_DIR}/../shaders/dx11) + +file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/../shaders/dx11) + +if (FSR2_AUTO_COMPILE_SHADERS) + set(FFX_SC_DEPENDENT_TARGET ffx_fsr2_api_dx11_${FSR2_PLATFORM_NAME}) +else() + set(FFX_SC_DEPENDENT_TARGET ffx_fsr2_api_dx11_shaders_${FSR2_PLATFORM_NAME}) + add_custom_target(${FFX_SC_DEPENDENT_TARGET}) +endif() + +if(${CMAKE_VERSION} VERSION_GREATER_EQUAL "3.20.0") +cmake_policy(SET CMP0116 OLD) +endif() +get_filename_component(PASS_SHADER_OUTPUT_PATH ${CMAKE_CURRENT_BINARY_DIR}/../shaders/dx11 ABSOLUTE) +foreach(PASS_SHADER ${PASS_SHADERS}) + get_filename_component(PASS_SHADER_FILENAME ${PASS_SHADER} NAME_WE) + get_filename_component(PASS_SHADER_TARGET ${PASS_SHADER} NAME_WLE) + set(PERMUTATION_HEADER ${PASS_SHADER_OUTPUT_PATH}/${PASS_SHADER_TARGET}_permutations.h) + set(16BIT_PERMUTATION_HEADER ${PASS_SHADER_OUTPUT_PATH}/${PASS_SHADER_TARGET}_16bit_permutations.h) + + # combine base and permutation args + set(FFX_SC_ARGS ${FFX_SC_BASE_ARGS} ${FFX_SC_DX11_BASE_ARGS} ${FFX_SC_PERMUTATION_ARGS}) + # disable compiling optimization for rcas, as it run faster in that way + if(${PASS_SHADER_FILENAME} STREQUAL ffx_fsr2_rcas_pass) + set(FFX_SC_ARGS ${FFX_SC_ARGS} -Od) + endif() + + if (USE_DEPFILE) + add_custom_command( + OUTPUT ${PERMUTATION_HEADER} + COMMAND ${FFX_SC_EXECUTABLE} ${FFX_SC_ARGS} -name=${PASS_SHADER_FILENAME} -DFFX_HALF=0 -T cs_5_0 -I ${CMAKE_CURRENT_SOURCE_DIR}/../shaders -output=${PASS_SHADER_OUTPUT_PATH} ${PASS_SHADER} + WORKING_DIRECTORY ${CMAKE_BINARY_DIR} + DEPENDS ${PASS_SHADER} + DEPFILE ${PERMUTATION_HEADER}.d + ) + list(APPEND PERMUTATION_OUTPUTS ${PERMUTATION_HEADER}) + + # skip 16-bit permutations for the compute luminance pyramid pass + if (NOT ${PASS_SHADER_FILENAME} STREQUAL "ffx_fsr2_compute_luminance_pyramid_pass") + # 16-bit + add_custom_command( + OUTPUT ${16BIT_PERMUTATION_HEADER} + COMMAND ${FFX_SC_EXECUTABLE} ${FFX_SC_ARGS} -name=${PASS_SHADER_FILENAME}_16bit -DFFX_HALF=1 -T cs_5_0 -I ${CMAKE_CURRENT_SOURCE_DIR}/../shaders -output=${PASS_SHADER_OUTPUT_PATH} ${PASS_SHADER} + WORKING_DIRECTORY ${CMAKE_BINARY_DIR} + DEPENDS ${PASS_SHADER} + DEPFILE ${16BIT_PERMUTATION_HEADER}.d + ) + list(APPEND PERMUTATION_OUTPUTS ${16BIT_PERMUTATION_HEADER}) + endif() + else() + add_custom_command( + OUTPUT ${PERMUTATION_HEADER} + COMMAND ${FFX_SC_EXECUTABLE} ${FFX_SC_ARGS} -name=${PASS_SHADER_FILENAME} -DFFX_HALF=0 -T cs_5_0 -I ${CMAKE_CURRENT_SOURCE_DIR}/../shaders -output=${PASS_SHADER_OUTPUT_PATH} ${PASS_SHADER} + WORKING_DIRECTORY ${CMAKE_BINARY_DIR} + DEPENDS ${PASS_SHADER} + ) + list(APPEND PERMUTATION_OUTPUTS ${PERMUTATION_HEADER}) + + # skip 16-bit permutations for the compute luminance pyramid pass + if (NOT ${PASS_SHADER_FILENAME} STREQUAL "ffx_fsr2_compute_luminance_pyramid_pass") + # 16-bit + add_custom_command( + OUTPUT ${16BIT_PERMUTATION_HEADER} + COMMAND ${FFX_SC_EXECUTABLE} ${FFX_SC_ARGS} -name=${PASS_SHADER_FILENAME}_16bit -DFFX_HALF=1 -T cs_5_0 -I ${CMAKE_CURRENT_SOURCE_DIR}/../shaders -output=${PASS_SHADER_OUTPUT_PATH} ${PASS_SHADER} + WORKING_DIRECTORY ${CMAKE_BINARY_DIR} + DEPENDS ${PASS_SHADER} + ) + list(APPEND PERMUTATION_OUTPUTS ${16BIT_PERMUTATION_HEADER}) + endif() + endif() +endforeach(PASS_SHADER) + +add_custom_target(shader_permutations_dx11 DEPENDS ${PERMUTATION_OUTPUTS}) +add_dependencies(${FFX_SC_DEPENDENT_TARGET} shader_permutations_dx11) + +source_group("source" FILES ${DX11}) +source_group("shaders" FILES ${SHADERS}) \ No newline at end of file diff --git a/src/ffx-fsr2-api/dx11/ffx_fsr2_dx11.cpp b/src/ffx-fsr2-api/dx11/ffx_fsr2_dx11.cpp new file mode 100644 index 0000000..78396e2 --- /dev/null +++ b/src/ffx-fsr2-api/dx11/ffx_fsr2_dx11.cpp @@ -0,0 +1,1197 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +#include // convert string to wstring +#include +#include +#include "../ffx_fsr2.h" +#include "ffx_fsr2_dx11.h" +#include "shaders/ffx_fsr2_shaders_dx11.h" // include all the precompiled D3D11 shaders for the FSR2 passes +#include "../ffx_fsr2_private.h" + +// DX11 prototypes for functions in the backend interface +FfxErrorCode GetDeviceCapabilitiesDX11(FfxFsr2Interface* backendInterface, FfxDeviceCapabilities* deviceCapabilities, FfxDevice device); +FfxErrorCode CreateBackendContextDX11(FfxFsr2Interface* backendInterface, FfxDevice device); +FfxErrorCode DestroyBackendContextDX11(FfxFsr2Interface* backendInterface); +FfxErrorCode CreateResourceDX11(FfxFsr2Interface* backendInterface, const FfxCreateResourceDescription* createResourceDescription, FfxResourceInternal* outTexture); +FfxErrorCode RegisterResourceDX11(FfxFsr2Interface* backendInterface, const FfxResource* inResource, FfxResourceInternal* outResourceInternal); +FfxErrorCode UnregisterResourcesDX11(FfxFsr2Interface* backendInterface); +FfxResourceDescription GetResourceDescriptionDX11(FfxFsr2Interface* backendInterface, FfxResourceInternal resource); +FfxErrorCode DestroyResourceDX11(FfxFsr2Interface* backendInterface, FfxResourceInternal resource); +FfxErrorCode CreatePipelineDX11(FfxFsr2Interface* backendInterface, FfxFsr2Pass passId, const FfxPipelineDescription* desc, FfxPipelineState* outPass); +FfxErrorCode DestroyPipelineDX11(FfxFsr2Interface* backendInterface, FfxPipelineState* pipeline); +FfxErrorCode ScheduleGpuJobDX11(FfxFsr2Interface* backendInterface, const FfxGpuJobDescription* job); +FfxErrorCode ExecuteGpuJobsDX11(FfxFsr2Interface* backendInterface, FfxCommandList commandList); + +#define FSR2_MAX_QUEUED_FRAMES ( 4) +#define FSR2_MAX_RESOURCE_COUNT (64) +#define FSR2_DESC_RING_SIZE (FSR2_MAX_QUEUED_FRAMES * FFX_FSR2_PASS_COUNT * FSR2_MAX_RESOURCE_COUNT) +#define FSR2_MAX_BARRIERS (16) +#define FSR2_MAX_GPU_JOBS (32) +#define FSR2_MAX_SAMPLERS ( 2) +#define UPLOAD_JOB_COUNT (16) + +typedef struct BackendContext_DX11 { + + // store for resources and resourceViews + typedef struct Resource + { +#ifdef _DEBUG + wchar_t resourceName[64] = {}; +#endif + ID3D11Resource* resourcePtr; + FfxResourceDescription resourceDescriptor; + FfxResourceStates state; + uint32_t srvDescIndex; + uint32_t uavDescIndex; + uint32_t uavDescCount; + } Resource; + + ID3D11Device* device = nullptr; + + FfxGpuJobDescription gpuJobs[FSR2_MAX_GPU_JOBS] = {}; + uint32_t gpuJobCount; + + uint32_t nextStaticResource; + uint32_t nextDynamicResource; + Resource resources[FSR2_MAX_RESOURCE_COUNT]; + ID3D11ShaderResourceView* descHeapSrvCpu[FSR2_MAX_RESOURCE_COUNT]; + + uint32_t nextStaticUavDescriptor; + uint32_t nextDynamicUavDescriptor; + ID3D11UnorderedAccessView* descHeapUavCpu[FSR2_MAX_RESOURCE_COUNT]; + ID3D11UnorderedAccessView* descHeapUavGpu[FSR2_MAX_RESOURCE_COUNT]; + + ID3D11SamplerState* pointClampSampler = nullptr; + ID3D11SamplerState* linearClampSampler = nullptr; + + ID3D11Buffer* constantBuffers[FSR2_MAX_RESOURCE_COUNT]; + uint32_t nextConstantBuffer; + +} BackendContext_DX11; + +typedef struct Pipeline_DX11 +{ + ID3D11ComputeShader* shader; +} Pipeline_DX11; + +ID3D11SamplerState* nullSampler = nullptr; +ID3D11ShaderResourceView* nullSRV = nullptr; +ID3D11UnorderedAccessView* nullUAV = nullptr; +ID3D11Buffer* nullCB = nullptr; + +FFX_API size_t ffxFsr2GetScratchMemorySizeDX11() +{ + return FFX_ALIGN_UP(sizeof(BackendContext_DX11), sizeof(uint64_t)); +} + +// populate interface with DX11 pointers. +FfxErrorCode ffxFsr2GetInterfaceDX11( + FfxFsr2Interface* outInterface, + ID3D11Device* device, + void* scratchBuffer, + size_t scratchBufferSize) +{ + FFX_RETURN_ON_ERROR( + outInterface, + FFX_ERROR_INVALID_POINTER); + FFX_RETURN_ON_ERROR( + scratchBuffer, + FFX_ERROR_INVALID_POINTER); + FFX_RETURN_ON_ERROR( + scratchBufferSize >= ffxFsr2GetScratchMemorySizeDX11(), + FFX_ERROR_INSUFFICIENT_MEMORY); + + outInterface->fpGetDeviceCapabilities = GetDeviceCapabilitiesDX11; + outInterface->fpCreateBackendContext = CreateBackendContextDX11; + outInterface->fpDestroyBackendContext = DestroyBackendContextDX11; + outInterface->fpCreateResource = CreateResourceDX11; + outInterface->fpRegisterResource = RegisterResourceDX11; + outInterface->fpUnregisterResources = UnregisterResourcesDX11; + outInterface->fpGetResourceDescription = GetResourceDescriptionDX11; + outInterface->fpDestroyResource = DestroyResourceDX11; + outInterface->fpCreatePipeline = CreatePipelineDX11; + outInterface->fpDestroyPipeline = DestroyPipelineDX11; + outInterface->fpScheduleGpuJob = ScheduleGpuJobDX11; + outInterface->fpExecuteGpuJobs = ExecuteGpuJobsDX11; + outInterface->scratchBuffer = scratchBuffer; + outInterface->scratchBufferSize = scratchBufferSize; + + return FFX_OK; +} + +void TIF(HRESULT result) +{ + if (FAILED(result)) + { + wchar_t errorMessage[256]; + memset(errorMessage, 0, 256); + FormatMessageW(FORMAT_MESSAGE_FROM_SYSTEM, NULL, result, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), errorMessage, 255, NULL); + char errA[256]; + size_t returnSize; + wcstombs_s(&returnSize, errA, 255, errorMessage, 255); +#ifdef _DEBUG + int32_t msgboxID = MessageBoxW(NULL, errorMessage, L"Error", MB_OK); +#endif + throw 1; + } +} + +// fix up format in case resource passed to FSR2 was created as typeless +static DXGI_FORMAT convertFormat(DXGI_FORMAT format) +{ + switch (format) + { + // Handle Depth + case DXGI_FORMAT_R32G8X24_TYPELESS: + case DXGI_FORMAT_D32_FLOAT_S8X24_UINT: + return DXGI_FORMAT_R32_FLOAT_X8X24_TYPELESS; + case DXGI_FORMAT_D32_FLOAT: + return DXGI_FORMAT_R32_FLOAT; + case DXGI_FORMAT_R24G8_TYPELESS: + case DXGI_FORMAT_X24_TYPELESS_G8_UINT: + case DXGI_FORMAT_D24_UNORM_S8_UINT: + return DXGI_FORMAT_R24_UNORM_X8_TYPELESS; + case DXGI_FORMAT_D16_UNORM: + return DXGI_FORMAT_R16_UNORM; + + // Handle color: assume FLOAT for 16 and 32 bit channels, else UNORM + case DXGI_FORMAT_R32G32B32A32_TYPELESS: + return DXGI_FORMAT_R32G32B32A32_FLOAT; + case DXGI_FORMAT_R32G32B32_TYPELESS: + return DXGI_FORMAT_R32G32B32_FLOAT; + case DXGI_FORMAT_R16G16B16A16_TYPELESS: + return DXGI_FORMAT_R16G16B16A16_FLOAT; + case DXGI_FORMAT_R8G8B8A8_TYPELESS: + return DXGI_FORMAT_R8G8B8A8_UNORM; + case DXGI_FORMAT_R32G32_TYPELESS: + return DXGI_FORMAT_R32G32_FLOAT; + case DXGI_FORMAT_R16G16_TYPELESS: + return DXGI_FORMAT_R16G16_FLOAT; + case DXGI_FORMAT_R10G10B10A2_TYPELESS: + return DXGI_FORMAT_R10G10B10A2_UNORM; + case DXGI_FORMAT_B8G8R8A8_TYPELESS: + return DXGI_FORMAT_B8G8R8A8_UNORM; + case DXGI_FORMAT_B8G8R8X8_TYPELESS: + return DXGI_FORMAT_B8G8R8X8_UNORM_SRGB; + case DXGI_FORMAT_R32_TYPELESS: + return DXGI_FORMAT_R32_FLOAT; + case DXGI_FORMAT_R8G8_TYPELESS: + return DXGI_FORMAT_R8G8_UNORM; + case DXGI_FORMAT_R16_TYPELESS: + return DXGI_FORMAT_R16_FLOAT; + case DXGI_FORMAT_R8_TYPELESS: + return DXGI_FORMAT_R8_UNORM; + default: + return format; + } +} + +ID3D11Resource* getDX11ResourcePtr(BackendContext_DX11* backendContext, int32_t resourceIndex) +{ + FFX_ASSERT(NULL != backendContext); + return reinterpret_cast(backendContext->resources[resourceIndex].resourcePtr); +} + +// Create a FfxFsr2Device from a ID3D11Device* +FfxDevice ffxGetDeviceDX11(ID3D11Device* dx11Device) +{ + FFX_ASSERT(NULL != dx11Device); + return reinterpret_cast(dx11Device); +} + +DXGI_FORMAT ffxGetDX11FormatFromSurfaceFormat(FfxSurfaceFormat surfaceFormat) +{ + switch (surfaceFormat) + { + case(FFX_SURFACE_FORMAT_R32G32B32A32_TYPELESS): + return DXGI_FORMAT_R32G32B32A32_TYPELESS; + case(FFX_SURFACE_FORMAT_R32G32B32A32_FLOAT): + return DXGI_FORMAT_R32G32B32A32_FLOAT; + case(FFX_SURFACE_FORMAT_R16G16B16A16_FLOAT): + return DXGI_FORMAT_R16G16B16A16_FLOAT; + case(FFX_SURFACE_FORMAT_R16G16B16A16_UNORM): + return DXGI_FORMAT_R16G16B16A16_UNORM; + case(FFX_SURFACE_FORMAT_R32G32_FLOAT): + return DXGI_FORMAT_R32G32_FLOAT; + case(FFX_SURFACE_FORMAT_R32_UINT): + return DXGI_FORMAT_R32_UINT; + case(FFX_SURFACE_FORMAT_R8G8B8A8_TYPELESS): + return DXGI_FORMAT_R8G8B8A8_TYPELESS; + case(FFX_SURFACE_FORMAT_R8G8B8A8_UNORM): + return DXGI_FORMAT_R8G8B8A8_UNORM; + case(FFX_SURFACE_FORMAT_R11G11B10_FLOAT): + return DXGI_FORMAT_R11G11B10_FLOAT; + case(FFX_SURFACE_FORMAT_R16G16_FLOAT): + return DXGI_FORMAT_R16G16_FLOAT; + case(FFX_SURFACE_FORMAT_R16G16_UINT): + return DXGI_FORMAT_R16G16_UINT; + case(FFX_SURFACE_FORMAT_R16_FLOAT): + return DXGI_FORMAT_R16_FLOAT; + case(FFX_SURFACE_FORMAT_R16_UINT): + return DXGI_FORMAT_R16_UINT; + case(FFX_SURFACE_FORMAT_R16_UNORM): + return DXGI_FORMAT_R16_UNORM; + case(FFX_SURFACE_FORMAT_R16_SNORM): + return DXGI_FORMAT_R16_SNORM; + case(FFX_SURFACE_FORMAT_R8_UNORM): + return DXGI_FORMAT_R8_UNORM; + case(FFX_SURFACE_FORMAT_R8_UINT): + return DXGI_FORMAT_R8_UINT; + case(FFX_SURFACE_FORMAT_R8G8_UNORM): + return DXGI_FORMAT_R8G8_UNORM; + case(FFX_SURFACE_FORMAT_R32_FLOAT): + return DXGI_FORMAT_R32_FLOAT; + default: + return DXGI_FORMAT_UNKNOWN; + } +} + +UINT ffxGetDX11BindFlags(FfxResourceUsage flags) +{ + UINT dx11BindFlags = 0; + if (flags & FFX_RESOURCE_USAGE_RENDERTARGET) dx11BindFlags |= D3D11_BIND_RENDER_TARGET; + if (flags & FFX_RESOURCE_USAGE_UAV) dx11BindFlags |= D3D11_BIND_UNORDERED_ACCESS; + return dx11BindFlags; +} + +FfxSurfaceFormat ffxGetSurfaceFormatDX11(DXGI_FORMAT format) +{ + switch (format) + { + case(DXGI_FORMAT_R32G32B32A32_TYPELESS): + return FFX_SURFACE_FORMAT_R32G32B32A32_TYPELESS; + case(DXGI_FORMAT_R32G32B32A32_FLOAT): + return FFX_SURFACE_FORMAT_R32G32B32A32_FLOAT; + case(DXGI_FORMAT_R16G16B16A16_FLOAT): + return FFX_SURFACE_FORMAT_R16G16B16A16_FLOAT; + case(DXGI_FORMAT_R16G16B16A16_UNORM): + return FFX_SURFACE_FORMAT_R16G16B16A16_UNORM; + case(DXGI_FORMAT_R32G32_FLOAT): + return FFX_SURFACE_FORMAT_R32G32_FLOAT; + case(DXGI_FORMAT_R32_UINT): + return FFX_SURFACE_FORMAT_R32_UINT; + case(DXGI_FORMAT_R8G8B8A8_TYPELESS): + return FFX_SURFACE_FORMAT_R8G8B8A8_TYPELESS; + case(DXGI_FORMAT_R8G8B8A8_UNORM): + return FFX_SURFACE_FORMAT_R8G8B8A8_UNORM; + case(DXGI_FORMAT_R11G11B10_FLOAT): + return FFX_SURFACE_FORMAT_R11G11B10_FLOAT; + case(DXGI_FORMAT_R16G16_FLOAT): + return FFX_SURFACE_FORMAT_R16G16_FLOAT; + case(DXGI_FORMAT_R16G16_UINT): + return FFX_SURFACE_FORMAT_R16G16_UINT; + case(DXGI_FORMAT_R16_FLOAT): + return FFX_SURFACE_FORMAT_R16_FLOAT; + case(DXGI_FORMAT_R16_UINT): + return FFX_SURFACE_FORMAT_R16_UINT; + case(DXGI_FORMAT_R16_UNORM): + return FFX_SURFACE_FORMAT_R16_UNORM; + case(DXGI_FORMAT_R16_SNORM): + return FFX_SURFACE_FORMAT_R16_SNORM; + case(DXGI_FORMAT_R8_UNORM): + return FFX_SURFACE_FORMAT_R8_UNORM; + case(DXGI_FORMAT_R8_UINT): + return FFX_SURFACE_FORMAT_R8_UINT; + default: + return FFX_SURFACE_FORMAT_UNKNOWN; + } +} + +// register a DX11 resource to the backend +FfxResource ffxGetResourceDX11(FfxFsr2Context* context, ID3D11Resource* dx11Resource, const wchar_t* name, FfxResourceStates state) +{ + FfxResource resource = {}; + resource.resource = reinterpret_cast(dx11Resource); + resource.state = state; + resource.descriptorData = 0; + + if (dx11Resource) { + resource.description.flags = FFX_RESOURCE_FLAGS_NONE; + resource.description.width = 1; + resource.description.height = 1; + resource.description.depth = 1; + resource.description.mipCount = 1; + resource.description.format = FFX_SURFACE_FORMAT_UNKNOWN; + + D3D11_RESOURCE_DIMENSION resDimension; + dx11Resource->GetType(&resDimension); + + switch (resDimension) + { + case D3D11_RESOURCE_DIMENSION_BUFFER: + resource.description.type = FFX_RESOURCE_TYPE_BUFFER; + D3D11_BUFFER_DESC bufferDesc; + reinterpret_cast(dx11Resource)->GetDesc(&bufferDesc); + resource.description.width = bufferDesc.ByteWidth; + break; + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + resource.description.type = FFX_RESOURCE_TYPE_TEXTURE1D; + D3D11_TEXTURE1D_DESC tex1DDesc; + reinterpret_cast(dx11Resource)->GetDesc(&tex1DDesc); + resource.description.width = tex1DDesc.Width; + resource.description.mipCount = tex1DDesc.MipLevels; + resource.description.format = ffxGetSurfaceFormatDX11(tex1DDesc.Format); + break; + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + resource.description.type = FFX_RESOURCE_TYPE_TEXTURE2D; + D3D11_TEXTURE2D_DESC tex2DDesc; + reinterpret_cast(dx11Resource)->GetDesc(&tex2DDesc); + resource.description.width = tex2DDesc.Width; + resource.description.height = tex2DDesc.Height; + resource.description.mipCount = tex2DDesc.MipLevels; + resource.description.format = ffxGetSurfaceFormatDX11(tex2DDesc.Format); + break; + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + resource.description.type = FFX_RESOURCE_TYPE_TEXTURE3D; + D3D11_TEXTURE3D_DESC tex3DDesc; + reinterpret_cast(dx11Resource)->GetDesc(&tex3DDesc); + resource.description.width = tex3DDesc.Width; + resource.description.height = tex3DDesc.Height; + resource.description.depth = tex3DDesc.Depth; + resource.description.mipCount = tex3DDesc.MipLevels; + resource.description.format = ffxGetSurfaceFormatDX11(tex3DDesc.Format); + break; + default: + break; + } + } +#ifdef _DEBUG + if (name) { + wcscpy_s(resource.name, name); + } +#endif + + return resource; +} + +ID3D11Resource* ffxGetDX11ResourcePtr(FfxFsr2Context* context, uint32_t resId) +{ + FfxFsr2Context_Private* contextPrivate = (FfxFsr2Context_Private*)(context); + BackendContext_DX11* backendContext = (BackendContext_DX11*)(contextPrivate->contextDescription.callbacks.scratchBuffer); + + if (resId > FFX_FSR2_RESOURCE_IDENTIFIER_INPUT_TRANSPARENCY_AND_COMPOSITION_MASK) + return backendContext->resources[contextPrivate->uavResources[resId].internalIndex].resourcePtr; + else // Input resources are present only in srvResources array + return backendContext->resources[contextPrivate->srvResources[resId].internalIndex].resourcePtr; +} + +FfxErrorCode RegisterResourceDX11( + FfxFsr2Interface* backendInterface, + const FfxResource* inFfxResource, + FfxResourceInternal* outFfxResourceInternal +) +{ + FFX_ASSERT(NULL != backendInterface); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)(backendInterface->scratchBuffer); + ID3D11Device* dx11Device = reinterpret_cast(backendContext->device); + ID3D11Resource* dx11Resource = reinterpret_cast(inFfxResource->resource); + + FfxResourceStates state = inFfxResource->state; + + if (dx11Resource == nullptr) + { + outFfxResourceInternal->internalIndex = FFX_FSR2_RESOURCE_IDENTIFIER_NULL; + return FFX_OK; + } + + FFX_ASSERT(backendContext->nextDynamicResource > backendContext->nextStaticResource); + outFfxResourceInternal->internalIndex = backendContext->nextDynamicResource--; + + BackendContext_DX11::Resource* backendResource = &backendContext->resources[outFfxResourceInternal->internalIndex]; + backendResource->resourcePtr = dx11Resource; + backendResource->state = state; +#ifdef _DEBUG + const wchar_t* name = inFfxResource->name; + if(name) + wcscpy_s(backendResource->resourceName, name); +#endif + + // create resource views + if (dx11Resource) + { + D3D11_UNORDERED_ACCESS_VIEW_DESC uavDesc = {}; + D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc = {}; + bool allowUAV = false; + + D3D11_RESOURCE_DIMENSION resDimension; + dx11Resource->GetType(&resDimension); + switch (resDimension) + { + case D3D11_RESOURCE_DIMENSION_BUFFER: + D3D11_BUFFER_DESC bufferDesc; + reinterpret_cast(dx11Resource)->GetDesc(&bufferDesc); + uavDesc.ViewDimension = D3D11_UAV_DIMENSION_BUFFER; + srvDesc.ViewDimension = D3D11_SRV_DIMENSION_BUFFER; + backendResource->resourceDescriptor.type = FFX_RESOURCE_TYPE_BUFFER; + backendResource->resourceDescriptor.width = uint32_t(bufferDesc.ByteWidth); + allowUAV = bufferDesc.BindFlags & D3D11_BIND_UNORDERED_ACCESS; + break; + case D3D11_RESOURCE_DIMENSION_TEXTURE1D: + D3D11_TEXTURE1D_DESC tex1DDesc; + reinterpret_cast(dx11Resource)->GetDesc(&tex1DDesc); + uavDesc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE1D; + srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1D; + srvDesc.Texture1D.MipLevels = -1; + uavDesc.Format = convertFormat(tex1DDesc.Format); + srvDesc.Format = convertFormat(tex1DDesc.Format); + backendResource->resourceDescriptor.type = FFX_RESOURCE_TYPE_TEXTURE1D; + backendResource->resourceDescriptor.format = ffxGetSurfaceFormatDX11(tex1DDesc.Format); + backendResource->resourceDescriptor.width = uint32_t(tex1DDesc.Width); + backendResource->resourceDescriptor.mipCount = uint32_t(tex1DDesc.MipLevels); + allowUAV = tex1DDesc.BindFlags & D3D11_BIND_UNORDERED_ACCESS; + break; + case D3D11_RESOURCE_DIMENSION_TEXTURE2D: + D3D11_TEXTURE2D_DESC tex2DDesc; + reinterpret_cast(dx11Resource)->GetDesc(&tex2DDesc); + uavDesc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE2D; + srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + srvDesc.Texture2D.MipLevels = -1; + uavDesc.Format = convertFormat(tex2DDesc.Format); + srvDesc.Format = convertFormat(tex2DDesc.Format); + backendResource->resourceDescriptor.type = FFX_RESOURCE_TYPE_TEXTURE2D; + backendResource->resourceDescriptor.format = ffxGetSurfaceFormatDX11(tex2DDesc.Format); + backendResource->resourceDescriptor.width = uint32_t(tex2DDesc.Width); + backendResource->resourceDescriptor.height = uint32_t(tex2DDesc.Height); + backendResource->resourceDescriptor.mipCount = uint32_t(tex2DDesc.MipLevels); + allowUAV = tex2DDesc.BindFlags & D3D11_BIND_UNORDERED_ACCESS; + break; + case D3D11_RESOURCE_DIMENSION_TEXTURE3D: + D3D11_TEXTURE3D_DESC tex3DDesc; + reinterpret_cast(dx11Resource)->GetDesc(&tex3DDesc); + uavDesc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE3D; + srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE3D; + srvDesc.Texture3D.MipLevels = -1; + uavDesc.Format = convertFormat(tex3DDesc.Format); + srvDesc.Format = convertFormat(tex3DDesc.Format); + backendResource->resourceDescriptor.type = FFX_RESOURCE_TYPE_TEXTURE3D; + backendResource->resourceDescriptor.format = ffxGetSurfaceFormatDX11(tex3DDesc.Format); + backendResource->resourceDescriptor.width = uint32_t(tex3DDesc.Width); + backendResource->resourceDescriptor.height = uint32_t(tex3DDesc.Height); + backendResource->resourceDescriptor.depth = uint32_t(tex3DDesc.Depth); + backendResource->resourceDescriptor.mipCount = uint32_t(tex3DDesc.MipLevels); + allowUAV = tex3DDesc.BindFlags & D3D11_BIND_UNORDERED_ACCESS; + break; + default: + break; + } + + // set up resorce view descriptors + if (resDimension != D3D11_RESOURCE_DIMENSION_BUFFER) + { + // CPU readable + TIF(dx11Device->CreateShaderResourceView(dx11Resource, &srvDesc, &backendContext->descHeapSrvCpu[outFfxResourceInternal->internalIndex])); + + // UAV + if (allowUAV) + { + int uavDescriptorsCount = backendResource->resourceDescriptor.mipCount; + FFX_ASSERT(backendContext->nextDynamicUavDescriptor - uavDescriptorsCount + 1 > backendContext->nextStaticResource); + + backendResource->uavDescCount = uavDescriptorsCount; + backendResource->uavDescIndex = backendContext->nextDynamicUavDescriptor - uavDescriptorsCount + 1; + + for (int mip = 0; mip < uavDescriptorsCount; ++mip) + { + uavDesc.Texture2D.MipSlice = mip; + + TIF(dx11Device->CreateUnorderedAccessView(dx11Resource, &uavDesc, &backendContext->descHeapUavCpu[backendResource->uavDescIndex + mip])); + TIF(dx11Device->CreateUnorderedAccessView(dx11Resource, &uavDesc, &backendContext->descHeapUavGpu[backendResource->uavDescIndex + mip])); + } + backendContext->nextDynamicUavDescriptor -= uavDescriptorsCount; + } + } + } + return FFX_OK; +} + +// dispose dynamic resources: This should be called at the end of the frame +FfxErrorCode UnregisterResourcesDX11(FfxFsr2Interface* backendInterface) +{ + FFX_ASSERT(NULL != backendInterface); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)(backendInterface->scratchBuffer); + + ID3D11Device* dx11Device = reinterpret_cast(backendContext->device); + + for (auto i = backendContext->nextDynamicResource + 1; i < FSR2_MAX_RESOURCE_COUNT; ++i) + { + if (backendContext->descHeapSrvCpu[i]) + { + backendContext->descHeapSrvCpu[i]->Release(); + backendContext->descHeapSrvCpu[i] = nullptr; + } + } + + for (auto i = backendContext->nextDynamicUavDescriptor + 1; i < FSR2_MAX_RESOURCE_COUNT; ++i) + { + if (backendContext->descHeapUavCpu[i]) + { + backendContext->descHeapUavCpu[i]->Release(); + backendContext->descHeapUavCpu[i] = nullptr; + } + if (backendContext->descHeapUavGpu[i]) + { + backendContext->descHeapUavGpu[i]->Release(); + backendContext->descHeapUavGpu[i] = nullptr; + } + } + + backendContext->nextDynamicResource = FSR2_MAX_RESOURCE_COUNT - 1; + backendContext->nextDynamicUavDescriptor = FSR2_MAX_RESOURCE_COUNT - 1; + + return FFX_OK; +} + +// query device capabilities to select the optimal shader permutation +FfxErrorCode GetDeviceCapabilitiesDX11(FfxFsr2Interface* backendInterface, FfxDeviceCapabilities* deviceCapabilities, FfxDevice device) +{ + ID3D11Device* dx11Device = reinterpret_cast(device); + + FFX_UNUSED(backendInterface); + FFX_ASSERT(NULL != deviceCapabilities); + FFX_ASSERT(NULL != dx11Device); + + // check if we have 16bit floating point. + D3D11_FEATURE_DATA_SHADER_MIN_PRECISION_SUPPORT minPrecision = {}; + if (SUCCEEDED(dx11Device->CheckFeatureSupport(D3D11_FEATURE_SHADER_MIN_PRECISION_SUPPORT, &minPrecision, sizeof(minPrecision)))) { + + deviceCapabilities->fp16Supported = !!(minPrecision.PixelShaderMinPrecision & D3D11_SHADER_MIN_PRECISION_16_BIT); + } + + return FFX_OK; +} + +// initialize the DX11 backend +FfxErrorCode CreateBackendContextDX11(FfxFsr2Interface* backendInterface, FfxDevice device) +{ + HRESULT result = S_OK; + ID3D11Device* dx11Device = reinterpret_cast(device); + + FFX_ASSERT(NULL != backendInterface); + FFX_ASSERT(NULL != dx11Device); + + // set up some internal resources we need (space for resource views and constant buffers) + BackendContext_DX11* backendContext = (BackendContext_DX11*)backendInterface->scratchBuffer; + std::memset(backendContext, 0, sizeof(*backendContext)); + + if (dx11Device != NULL) + { + dx11Device->AddRef(); + backendContext->device = dx11Device; + } + + // init resource linked list + backendContext->nextStaticResource = 1; + backendContext->nextDynamicResource = FSR2_MAX_RESOURCE_COUNT - 1; + backendContext->nextStaticUavDescriptor = 0; + backendContext->nextDynamicUavDescriptor = FSR2_MAX_RESOURCE_COUNT - 1; + + backendContext->resources[0] = {}; + + const D3D11_SAMPLER_DESC pointClampSamplerDesc { + D3D11_FILTER_MIN_MAG_MIP_POINT, + D3D11_TEXTURE_ADDRESS_CLAMP, + D3D11_TEXTURE_ADDRESS_CLAMP, + D3D11_TEXTURE_ADDRESS_CLAMP, + 0, + 16, + D3D11_COMPARISON_NEVER, + { 1.f, 1.f, 1.f, 1.f }, + 0.f, + D3D11_FLOAT32_MAX, + }; + + const D3D11_SAMPLER_DESC linearClampSamplerDesc { + D3D11_FILTER_MIN_MAG_MIP_LINEAR, + D3D11_TEXTURE_ADDRESS_CLAMP, + D3D11_TEXTURE_ADDRESS_CLAMP, + D3D11_TEXTURE_ADDRESS_CLAMP, + 0, + 16, + D3D11_COMPARISON_NEVER, + { 1.f, 1.f, 1.f, 1.f }, + 0.f, + D3D11_FLOAT32_MAX, + }; + + dx11Device->CreateSamplerState(&pointClampSamplerDesc, &backendContext->pointClampSampler); + dx11Device->CreateSamplerState(&linearClampSamplerDesc, &backendContext->linearClampSampler); + + for (auto i = 0; i < FSR2_MAX_RESOURCE_COUNT; ++i) + { + backendContext->constantBuffers[i] = nullptr; + } + + return FFX_OK; +} + +// deinitialize the DX11 backend +FfxErrorCode DestroyBackendContextDX11(FfxFsr2Interface* backendInterface) +{ + FFX_ASSERT(NULL != backendInterface); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)backendInterface->scratchBuffer; + for (auto i = 0; i < FSR2_MAX_RESOURCE_COUNT; ++i) + { + if (backendContext->descHeapSrvCpu[i]) + backendContext->descHeapSrvCpu[i]->Release(); + if (backendContext->descHeapUavCpu[i]) + backendContext->descHeapUavCpu[i]->Release(); + if (backendContext->descHeapUavGpu[i]) + backendContext->descHeapUavGpu[i]->Release(); + } + + for (uint32_t currentStaticResourceIndex = 0; currentStaticResourceIndex < backendContext->nextStaticResource; ++currentStaticResourceIndex) + { + if (backendContext->resources[currentStaticResourceIndex].resourcePtr) + { + backendContext->resources[currentStaticResourceIndex].resourcePtr->Release(); + backendContext->resources[currentStaticResourceIndex].resourcePtr = nullptr; + } + } + backendContext->nextStaticResource = 0; + + if (backendContext->pointClampSampler) + { + backendContext->pointClampSampler->Release(); + backendContext->pointClampSampler = nullptr; + } + if (backendContext->linearClampSampler) + { + backendContext->linearClampSampler->Release(); + backendContext->linearClampSampler = nullptr; + } + + for (auto i = 0; i < FSR2_MAX_RESOURCE_COUNT; ++i) + { + if (backendContext->constantBuffers[i] != nullptr) + { + backendContext->constantBuffers[i]->Release(); + } + } + + if (backendContext->device != NULL) { + + backendContext->device->Release(); + backendContext->device = NULL; + } + + return FFX_OK; +} + +// create a internal resource that will stay alive until effect gets shut down +FfxErrorCode CreateResourceDX11( + FfxFsr2Interface* backendInterface, + const FfxCreateResourceDescription* createResourceDescription, + FfxResourceInternal* outTexture) +{ + FFX_ASSERT(NULL != backendInterface); + FFX_ASSERT(NULL != createResourceDescription); + FFX_ASSERT(NULL != outTexture); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)backendInterface->scratchBuffer; + ID3D11Device* dx11Device = backendContext->device; + + FFX_ASSERT(NULL != dx11Device); + + FFX_ASSERT(backendContext->nextStaticResource + 1 < backendContext->nextDynamicResource); + + outTexture->internalIndex = backendContext->nextStaticResource++; + BackendContext_DX11::Resource* backendResource = &backendContext->resources[outTexture->internalIndex]; + backendResource->resourceDescriptor = createResourceDescription->resourceDescription; + + // Initial data should be uploaded on resource creation for DX11, no additional upload heap type should be used + FFX_ASSERT(createResourceDescription->heapType != FFX_HEAP_TYPE_UPLOAD); + + backendResource->state = createResourceDescription->initalState; + +#ifdef _DEBUG + wcscpy_s(backendResource->resourceName, createResourceDescription->name); +#endif + + // Create SRVs and UAVs + { + D3D11_UNORDERED_ACCESS_VIEW_DESC uavDesc = {}; + D3D11_SHADER_RESOURCE_VIEW_DESC srvDesc = {}; + bool allowUAV = false; + unsigned int mipCount = 0; + + D3D11_SUBRESOURCE_DATA initData = { createResourceDescription->initData, 0, 0 }; + D3D11_SUBRESOURCE_DATA* pInitData = createResourceDescription->initData ? &initData : nullptr; + + switch (createResourceDescription->resourceDescription.type) + { + case FFX_RESOURCE_TYPE_BUFFER: + ID3D11Buffer* bufferPtr; + D3D11_BUFFER_DESC bufDesc; + bufDesc.ByteWidth = (createResourceDescription->resourceDescription.width + 15) & (~0x0F); // up to multiples of 16 + bufDesc.Usage = D3D11_USAGE_DYNAMIC; + bufDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER | ffxGetDX11BindFlags(createResourceDescription->usage); + bufDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + TIF(dx11Device->CreateBuffer(&bufDesc, pInitData, &bufferPtr)); + backendResource->resourcePtr = bufferPtr; + + uavDesc.ViewDimension = D3D11_UAV_DIMENSION_BUFFER; + srvDesc.ViewDimension = D3D11_SRV_DIMENSION_BUFFER; + + bufferPtr->SetPrivateData(WKPDID_D3DDebugObjectNameW, UINT(wcslen(createResourceDescription->name) * sizeof(wchar_t)), createResourceDescription->name); + backendResource->resourcePtr = bufferPtr; + allowUAV = bufDesc.BindFlags & D3D11_BIND_UNORDERED_ACCESS; + break; + case FFX_RESOURCE_TYPE_TEXTURE1D: + ID3D11Texture1D* tex1DPtr; + D3D11_TEXTURE1D_DESC tex1DDesc; + tex1DDesc.Width = createResourceDescription->resourceDescription.width; + tex1DDesc.MipLevels = createResourceDescription->resourceDescription.mipCount; + tex1DDesc.ArraySize = 1; + tex1DDesc.Format = ffxGetDX11FormatFromSurfaceFormat(createResourceDescription->resourceDescription.format); + tex1DDesc.Usage = D3D11_USAGE_DEFAULT; + tex1DDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE | ffxGetDX11BindFlags(createResourceDescription->usage); + tex1DDesc.CPUAccessFlags = 0; + tex1DDesc.MiscFlags = 0; + TIF(dx11Device->CreateTexture1D(&tex1DDesc, pInitData, &tex1DPtr)); + + uavDesc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE1D; + srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE1D; + srvDesc.Texture1D.MipLevels = -1; + uavDesc.Format = convertFormat(tex1DDesc.Format); + srvDesc.Format = convertFormat(tex1DDesc.Format); + + tex1DPtr->SetPrivateData(WKPDID_D3DDebugObjectNameW, UINT(wcslen(createResourceDescription->name) * sizeof(wchar_t)), createResourceDescription->name); + backendResource->resourcePtr = tex1DPtr; + tex1DPtr->GetDesc(&tex1DDesc); + mipCount = tex1DDesc.MipLevels; + allowUAV = tex1DDesc.BindFlags & D3D11_BIND_UNORDERED_ACCESS; + break; + case FFX_RESOURCE_TYPE_TEXTURE2D: + ID3D11Texture2D* tex2DPtr; + D3D11_TEXTURE2D_DESC tex2DDesc; + tex2DDesc.Width = createResourceDescription->resourceDescription.width; + tex2DDesc.Height = createResourceDescription->resourceDescription.height; + tex2DDesc.MipLevels = createResourceDescription->resourceDescription.mipCount; + tex2DDesc.ArraySize = 1; + tex2DDesc.Format = ffxGetDX11FormatFromSurfaceFormat(createResourceDescription->resourceDescription.format); + tex2DDesc.SampleDesc.Count = 1; + tex2DDesc.SampleDesc.Quality = 0; + tex2DDesc.Usage = D3D11_USAGE_DEFAULT; + tex2DDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE | ffxGetDX11BindFlags(createResourceDescription->usage); + tex2DDesc.CPUAccessFlags = 0; + tex2DDesc.MiscFlags = 0; + initData.SysMemPitch = createResourceDescription->initDataSize / createResourceDescription->resourceDescription.height; + TIF(dx11Device->CreateTexture2D(&tex2DDesc, pInitData, &tex2DPtr)); + + uavDesc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE2D; + srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE2D; + srvDesc.Texture2D.MipLevels = -1; + uavDesc.Format = convertFormat(tex2DDesc.Format); + srvDesc.Format = convertFormat(tex2DDesc.Format); + + tex2DPtr->SetPrivateData(WKPDID_D3DDebugObjectNameW, UINT(wcslen(createResourceDescription->name) * sizeof(wchar_t)), createResourceDescription->name); + backendResource->resourcePtr = tex2DPtr; + tex2DPtr->GetDesc(&tex2DDesc); + mipCount = tex2DDesc.MipLevels; + allowUAV = tex2DDesc.BindFlags & D3D11_BIND_UNORDERED_ACCESS; + break; + case FFX_RESOURCE_TYPE_TEXTURE3D: + ID3D11Texture3D* tex3DPtr; + D3D11_TEXTURE3D_DESC tex3DDesc; + tex3DDesc.Width = createResourceDescription->resourceDescription.width; + tex3DDesc.Height = createResourceDescription->resourceDescription.height; + tex3DDesc.Depth = createResourceDescription->resourceDescription.depth; + tex3DDesc.MipLevels = createResourceDescription->resourceDescription.mipCount; + tex3DDesc.Format = ffxGetDX11FormatFromSurfaceFormat(createResourceDescription->resourceDescription.format); + tex3DDesc.Usage = D3D11_USAGE_DEFAULT; + tex3DDesc.BindFlags = D3D11_BIND_SHADER_RESOURCE | ffxGetDX11BindFlags(createResourceDescription->usage); + tex3DDesc.CPUAccessFlags = 0; + tex3DDesc.MiscFlags = 0; + initData.SysMemSlicePitch = createResourceDescription->initDataSize / (createResourceDescription->resourceDescription.height * createResourceDescription->resourceDescription.depth); + initData.SysMemPitch = createResourceDescription->initDataSize / createResourceDescription->resourceDescription.depth; + TIF(dx11Device->CreateTexture3D(&tex3DDesc, pInitData, &tex3DPtr)); + + uavDesc.ViewDimension = D3D11_UAV_DIMENSION_TEXTURE3D; + srvDesc.ViewDimension = D3D11_SRV_DIMENSION_TEXTURE3D; + srvDesc.Texture3D.MipLevels = -1; + uavDesc.Format = convertFormat(tex3DDesc.Format); + srvDesc.Format = convertFormat(tex3DDesc.Format); + + tex3DPtr->SetPrivateData(WKPDID_D3DDebugObjectNameW, UINT(wcslen(createResourceDescription->name) * sizeof(wchar_t)), createResourceDescription->name); + backendResource->resourcePtr = tex3DPtr; + tex3DPtr->GetDesc(&tex3DDesc); + mipCount = tex3DDesc.MipLevels; + allowUAV = tex3DDesc.BindFlags & D3D11_BIND_UNORDERED_ACCESS; + break; + default: + break; + } + + if (createResourceDescription->resourceDescription.type != FFX_RESOURCE_TYPE_BUFFER) + { + // CPU readable + TIF(dx11Device->CreateShaderResourceView(backendResource->resourcePtr, &srvDesc, &backendContext->descHeapSrvCpu[outTexture->internalIndex])); + + // UAV + if (createResourceDescription->usage & FFX_RESOURCE_USAGE_UAV) + { + int uavDescriptorCount = mipCount; + FFX_ASSERT(backendContext->nextStaticUavDescriptor + uavDescriptorCount < backendContext->nextDynamicResource); + + backendResource->uavDescCount = uavDescriptorCount; + backendResource->uavDescIndex = backendContext->nextStaticUavDescriptor; + + for (int mip = 0; mip < uavDescriptorCount; ++mip) + { + uavDesc.Texture2D.MipSlice = mip; + + TIF(dx11Device->CreateUnorderedAccessView(backendResource->resourcePtr, &uavDesc, &backendContext->descHeapUavCpu[backendResource->uavDescIndex + mip])); + TIF(dx11Device->CreateUnorderedAccessView(backendResource->resourcePtr, &uavDesc, &backendContext->descHeapUavGpu[backendResource->uavDescIndex + mip])); + } + backendContext->nextStaticUavDescriptor += uavDescriptorCount; + } + } + } + return FFX_OK; +} + +FfxResourceDescription GetResourceDescriptionDX11( + FfxFsr2Interface* backendInterface, + FfxResourceInternal resource) +{ + FFX_ASSERT(NULL != backendInterface); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)backendInterface->scratchBuffer; + + if (resource.internalIndex != -1) + { + FfxResourceDescription desc = backendContext->resources[resource.internalIndex].resourceDescriptor; + return desc; + } + else + { + FfxResourceDescription desc = {}; + return desc; + } +} + +FfxErrorCode CreatePipelineDX11( + FfxFsr2Interface* backendInterface, + FfxFsr2Pass pass, + const FfxPipelineDescription* pipelineDescription, + FfxPipelineState* outPipeline) +{ + FFX_ASSERT(NULL != backendInterface); + FFX_ASSERT(NULL != pipelineDescription); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)backendInterface->scratchBuffer; + ID3D11Device* dx11Device = backendContext->device; + + Pipeline_DX11* pipeline = new Pipeline_DX11; + + FFX_ASSERT(pipelineDescription->rootConstantBufferCount <= FFX_MAX_NUM_CONST_BUFFERS); + size_t rootConstantsSize = pipelineDescription->rootConstantBufferCount; + + // always use LUT + bool useLut = true; + + // check if we have 16bit floating point. + bool supportedFP16 = false; + D3D11_FEATURE_DATA_SHADER_MIN_PRECISION_SUPPORT minPrecision = {}; + if (SUCCEEDED(dx11Device->CheckFeatureSupport(D3D11_FEATURE_SHADER_MIN_PRECISION_SUPPORT, &minPrecision, sizeof(minPrecision)))) { + + supportedFP16 = !!(minPrecision.PixelShaderMinPrecision & D3D11_SHADER_MIN_PRECISION_16_BIT); + } + + // work out what permutation to load. + uint32_t flags = 0; + flags |= (pipelineDescription->contextFlags & FFX_FSR2_ENABLE_HIGH_DYNAMIC_RANGE) ? FSR2_SHADER_PERMUTATION_HDR_COLOR_INPUT : 0; + flags |= (pipelineDescription->contextFlags & FFX_FSR2_ENABLE_DISPLAY_RESOLUTION_MOTION_VECTORS) ? 0 : FSR2_SHADER_PERMUTATION_LOW_RES_MOTION_VECTORS; + flags |= (pipelineDescription->contextFlags & FFX_FSR2_ENABLE_MOTION_VECTORS_JITTER_CANCELLATION) ? FSR2_SHADER_PERMUTATION_JITTER_MOTION_VECTORS : 0; + flags |= (pipelineDescription->contextFlags & FFX_FSR2_ENABLE_DEPTH_INVERTED) ? FSR2_SHADER_PERMUTATION_DEPTH_INVERTED : 0; + flags |= (pass == FFX_FSR2_PASS_ACCUMULATE_SHARPEN) ? FSR2_SHADER_PERMUTATION_ENABLE_SHARPENING : 0; + flags |= (useLut) ? FSR2_SHADER_PERMUTATION_USE_LANCZOS_TYPE : 0; + //flags |= (canForceWave64) ? FSR2_SHADER_PERMUTATION_FORCE_WAVE64 : 0; + flags |= (supportedFP16 && (pass != FFX_FSR2_PASS_RCAS)) ? FSR2_SHADER_PERMUTATION_ALLOW_FP16 : 0; + + ID3D11ComputeShader* shader = nullptr; + Fsr2ShaderBlobDX11 shaderBlob = fsr2GetPermutationBlobByIndexDX11(pass, flags); + FFX_ASSERT(shaderBlob.data && shaderBlob.size); + + if (shaderBlob.data) + { + HRESULT hr = dx11Device->CreateComputeShader(shaderBlob.data, shaderBlob.size, NULL, &shader); + FFX_ASSERT(hr == S_OK); + } + + pipeline->shader = shader; + outPipeline->pipeline = pipeline; + + // populate the pass. + outPipeline->srvCount = shaderBlob.srvCount; + outPipeline->uavCount = shaderBlob.uavCount; + outPipeline->constCount = shaderBlob.cbvCount; + std::wstring_convert> converter; + for (uint32_t srvIndex = 0; srvIndex < outPipeline->srvCount; ++srvIndex) + { + outPipeline->srvResourceBindings[srvIndex].slotIndex = shaderBlob.boundSRVResources[srvIndex]; + wcscpy_s(outPipeline->srvResourceBindings[srvIndex].name, converter.from_bytes(shaderBlob.boundSRVResourceNames[srvIndex]).c_str()); + } + for (uint32_t uavIndex = 0; uavIndex < outPipeline->uavCount; ++uavIndex) + { + outPipeline->uavResourceBindings[uavIndex].slotIndex = shaderBlob.boundUAVResources[uavIndex]; + wcscpy_s(outPipeline->uavResourceBindings[uavIndex].name, converter.from_bytes(shaderBlob.boundUAVResourceNames[uavIndex]).c_str()); + } + for (uint32_t cbIndex = 0; cbIndex < outPipeline->constCount; ++cbIndex) + { + outPipeline->cbResourceBindings[cbIndex].slotIndex = shaderBlob.boundCBVResources[cbIndex]; + wcscpy_s(outPipeline->cbResourceBindings[cbIndex].name, converter.from_bytes(shaderBlob.boundCBVResourceNames[cbIndex]).c_str()); + } + + return FFX_OK; +} + +FfxErrorCode ScheduleGpuJobDX11( + FfxFsr2Interface* backendInterface, + const FfxGpuJobDescription* job) +{ + FFX_ASSERT(NULL != backendInterface); + FFX_ASSERT(NULL != job); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)backendInterface->scratchBuffer; + + FFX_ASSERT(backendContext->gpuJobCount < FSR2_MAX_GPU_JOBS); + + backendContext->gpuJobs[backendContext->gpuJobCount] = *job; + + if (job->jobType == FFX_GPU_JOB_COMPUTE) { + + // needs to copy SRVs and UAVs in case they are on the stack only + FfxComputeJobDescription* computeJob = &backendContext->gpuJobs[backendContext->gpuJobCount].computeJobDescriptor; + const uint32_t numConstBuffers = job->computeJobDescriptor.pipeline.constCount; + for (uint32_t currentRootConstantIndex = 0; currentRootConstantIndex < numConstBuffers; ++currentRootConstantIndex) + { + computeJob->cbs[currentRootConstantIndex].uint32Size = job->computeJobDescriptor.cbs[currentRootConstantIndex].uint32Size; + memcpy(computeJob->cbs[currentRootConstantIndex].data, job->computeJobDescriptor.cbs[currentRootConstantIndex].data, computeJob->cbs[currentRootConstantIndex].uint32Size * sizeof(uint32_t)); + } + } + backendContext->gpuJobCount++; + + return FFX_OK; +} + +static FfxErrorCode executeGpuJobCompute(BackendContext_DX11* backendContext, FfxGpuJobDescription* job, ID3D11Device* dx11Device, ID3D11DeviceContext* dx11DeviceContext) +{ + Pipeline_DX11* pipeline = reinterpret_cast(job->computeJobDescriptor.pipeline.pipeline); + dx11DeviceContext->CSSetShader(pipeline->shader, nullptr, 0); + + // bind samplers + dx11DeviceContext->CSSetSamplers(0, 1, &backendContext->pointClampSampler); + dx11DeviceContext->CSSetSamplers(1, 1, &backendContext->linearClampSampler); + + // bind UAVs + for (uint32_t currentPipelineUavIndex = 0; currentPipelineUavIndex < job->computeJobDescriptor.pipeline.uavCount; ++currentPipelineUavIndex) + { + uint32_t resourceIndex = job->computeJobDescriptor.uavs[currentPipelineUavIndex].internalIndex; + uint32_t uavIndex = backendContext->resources[resourceIndex].uavDescIndex + job->computeJobDescriptor.uavMip[currentPipelineUavIndex]; + uint32_t slot = job->computeJobDescriptor.pipeline.uavResourceBindings[currentPipelineUavIndex].slotIndex; + + ID3D11UnorderedAccessView** uavs = &(backendContext->descHeapUavCpu[uavIndex]); + dx11DeviceContext->CSSetUnorderedAccessViews(slot, 1, uavs, nullptr); + } + + // bind SRVs + for (uint32_t currentPipelineSrvIndex = 0; currentPipelineSrvIndex < job->computeJobDescriptor.pipeline.srvCount; ++currentPipelineSrvIndex) + { + uint32_t resourceIndex = job->computeJobDescriptor.srvs[currentPipelineSrvIndex].internalIndex; + uint32_t slot = job->computeJobDescriptor.pipeline.srvResourceBindings[currentPipelineSrvIndex].slotIndex; + + ID3D11ShaderResourceView* srv = backendContext->descHeapSrvCpu[resourceIndex]; + dx11DeviceContext->CSSetShaderResources(slot, 1, &srv); + } + + // bind constant buffers + for (uint32_t currentRootConstantIndex = 0; currentRootConstantIndex < job->computeJobDescriptor.pipeline.constCount; ++currentRootConstantIndex) + { + int currentCbSlotIndex = job->computeJobDescriptor.pipeline.cbResourceBindings[currentRootConstantIndex].slotIndex; + + if (backendContext->constantBuffers[backendContext->nextConstantBuffer] == nullptr) + { + D3D11_BUFFER_DESC bufDesc; + bufDesc.ByteWidth = FFX_MAX_CONST_SIZE * sizeof(uint32_t); + bufDesc.Usage = D3D11_USAGE_DYNAMIC; + bufDesc.BindFlags = D3D11_BIND_CONSTANT_BUFFER; + bufDesc.CPUAccessFlags = D3D11_CPU_ACCESS_WRITE; + bufDesc.MiscFlags = 0; + TIF(dx11Device->CreateBuffer(&bufDesc, nullptr, &backendContext->constantBuffers[backendContext->nextConstantBuffer])); + } + + D3D11_MAPPED_SUBRESOURCE mapped; + TIF(dx11DeviceContext->Map(backendContext->constantBuffers[backendContext->nextConstantBuffer], 0, D3D11_MAP_WRITE_DISCARD, 0, &mapped)); + memcpy(mapped.pData, job->computeJobDescriptor.cbs[currentCbSlotIndex].data, job->computeJobDescriptor.cbs[currentCbSlotIndex].uint32Size * sizeof(uint32_t)); + dx11DeviceContext->Unmap(backendContext->constantBuffers[backendContext->nextConstantBuffer], 0); + + dx11DeviceContext->CSSetConstantBuffers(currentRootConstantIndex, 1, &backendContext->constantBuffers[backendContext->nextConstantBuffer]); + + backendContext->nextConstantBuffer++; + } + + // dispatch + dx11DeviceContext->Dispatch(job->computeJobDescriptor.dimensions[0], job->computeJobDescriptor.dimensions[1], job->computeJobDescriptor.dimensions[2]); + + // unbind samplers + dx11DeviceContext->CSSetSamplers(0, 1, &nullSampler); + dx11DeviceContext->CSSetSamplers(1, 1, &nullSampler); + + // unbind UAVs + for (uint32_t currentPipelineUavIndex = 0; currentPipelineUavIndex < job->computeJobDescriptor.pipeline.uavCount; ++currentPipelineUavIndex) + { + uint32_t resourceIndex = job->computeJobDescriptor.uavs[currentPipelineUavIndex].internalIndex; + uint32_t slot = job->computeJobDescriptor.pipeline.uavResourceBindings[currentPipelineUavIndex].slotIndex; + dx11DeviceContext->CSSetUnorderedAccessViews(slot, 1, &nullUAV, nullptr); + } + + // unbind SRVs + for (uint32_t currentPipelineSrvIndex = 0; currentPipelineSrvIndex < job->computeJobDescriptor.pipeline.srvCount; ++currentPipelineSrvIndex) + { + uint32_t slot = job->computeJobDescriptor.pipeline.srvResourceBindings[currentPipelineSrvIndex].slotIndex; + dx11DeviceContext->CSSetShaderResources(slot, 1, &nullSRV); + } + + // unbind constant buffers + for (uint32_t currentRootConstantIndex = 0; currentRootConstantIndex < job->computeJobDescriptor.pipeline.constCount; ++currentRootConstantIndex) + { + dx11DeviceContext->CSSetConstantBuffers(currentRootConstantIndex, 1, &nullCB); + } + + return FFX_OK; +} + +static FfxErrorCode executeGpuJobCopy(BackendContext_DX11* backendContext, FfxGpuJobDescription* job, ID3D11Device* dx11Device, ID3D11DeviceContext* dx11DeviceContext) +{ + ID3D11Resource* dx11ResourceSrc = getDX11ResourcePtr(backendContext, job->copyJobDescriptor.src.internalIndex); + ID3D11Resource* dx11ResourceDst = getDX11ResourcePtr(backendContext, job->copyJobDescriptor.dst.internalIndex); + + dx11DeviceContext->CopySubresourceRegion(dx11ResourceDst, 0, 0, 0, 0, dx11ResourceSrc, 0, nullptr); + + return FFX_OK; +} + +static FfxErrorCode executeGpuJobClearFloat(BackendContext_DX11* backendContext, FfxGpuJobDescription* job, ID3D11Device* dx11Device, ID3D11DeviceContext* dx11DeviceContext) +{ + uint32_t idx = job->clearJobDescriptor.target.internalIndex; + BackendContext_DX11::Resource ffxResource = backendContext->resources[idx]; + ID3D11Resource* dx11Resource = reinterpret_cast(ffxResource.resourcePtr); + uint32_t index_uav = ffxResource.uavDescIndex; + + dx11DeviceContext->ClearUnorderedAccessViewFloat(backendContext->descHeapUavGpu[index_uav], job->clearJobDescriptor.color); + + return FFX_OK; +} + +FfxErrorCode ExecuteGpuJobsDX11( + FfxFsr2Interface* backendInterface, + FfxCommandList commandList) +{ + FFX_ASSERT(NULL != backendInterface); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)backendInterface->scratchBuffer; + ID3D11DeviceContext* dx11DeviceContext = reinterpret_cast(commandList); + ID3D11Device* dx11Device = reinterpret_cast(backendContext->device); + + FfxErrorCode errorCode = FFX_OK; + + // reset in-use constant buffer pointer to top + backendContext->nextConstantBuffer = 0; + + // execute all Gpujobs + for (uint32_t currentGpuJobIndex = 0; currentGpuJobIndex < backendContext->gpuJobCount; ++currentGpuJobIndex) + { + FfxGpuJobDescription* GpuJob = &backendContext->gpuJobs[currentGpuJobIndex]; + + switch (GpuJob->jobType) + { + case FFX_GPU_JOB_CLEAR_FLOAT: + errorCode = executeGpuJobClearFloat(backendContext, GpuJob, dx11Device, dx11DeviceContext); + break; + case FFX_GPU_JOB_COPY: + errorCode = executeGpuJobCopy(backendContext, GpuJob, dx11Device, dx11DeviceContext); + break; + case FFX_GPU_JOB_COMPUTE: + errorCode = executeGpuJobCompute(backendContext, GpuJob, dx11Device, dx11DeviceContext); + break; + + default: + break; + } + } + + // check the execute function returned clearly. + FFX_RETURN_ON_ERROR( + errorCode == FFX_OK, + FFX_ERROR_BACKEND_API_ERROR); + + backendContext->gpuJobCount = 0; + + return FFX_OK; +} + +FfxErrorCode DestroyResourceDX11( + FfxFsr2Interface* backendInterface, + FfxResourceInternal resource) +{ + FFX_ASSERT(NULL != backendInterface); + + BackendContext_DX11* backendContext = (BackendContext_DX11*)backendInterface->scratchBuffer; + ID3D11Resource* dx11Resource = getDX11ResourcePtr(backendContext, resource.internalIndex); + if (dx11Resource) { + + TIF(dx11Resource->Release()); + backendContext->resources[resource.internalIndex].resourcePtr = nullptr; + //ffxDX11ReleaseResource(backendInterface, *resource); + } + + return FFX_OK; +} + +FfxErrorCode DestroyPipelineDX11( + FfxFsr2Interface* backendInterface, + FfxPipelineState* pipeline) +{ + FFX_ASSERT(backendInterface != nullptr); + if (!pipeline) + { + return FFX_OK; + } + + Pipeline_DX11* pipeline_dx11 = reinterpret_cast(pipeline->pipeline); + if (pipeline_dx11) + { + if (pipeline_dx11->shader) + { + pipeline_dx11->shader->Release(); + pipeline_dx11->shader = nullptr; + } + + delete pipeline_dx11; + } + + return FFX_OK; +} diff --git a/src/ffx-fsr2-api/dx11/ffx_fsr2_dx11.h b/src/ffx-fsr2-api/dx11/ffx_fsr2_dx11.h new file mode 100644 index 0000000..a8d4823 --- /dev/null +++ b/src/ffx-fsr2-api/dx11/ffx_fsr2_dx11.h @@ -0,0 +1,99 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +// @defgroup DX11 + +#pragma once + +#include +#include "../ffx_fsr2_interface.h" + +#if defined(__cplusplus) +extern "C" { +#endif // #if defined(__cplusplus) + +/// Query how much memory is required for the DirectX 11 backend's scratch buffer. +/// +/// @returns +/// The size (in bytes) of the required scratch memory buffer for the DX11 backend. +FFX_API size_t ffxFsr2GetScratchMemorySizeDX11(); + +/// Populate an interface with pointers for the DX11 backend. +/// +/// @param [out] fsr2Interface A pointer to a FfxFsr2Interface structure to populate with pointers. +/// @param [in] device A pointer to the DirectX11 device. +/// @param [in] scratchBuffer A pointer to a buffer of memory which can be used by the DirectX(R)11 backend. +/// @param [in] scratchBufferSize The size (in bytes) of the buffer pointed to by scratchBuffer. +/// +/// @retval +/// FFX_OK The operation completed successfully. +/// @retval +/// FFX_ERROR_CODE_INVALID_POINTER The interface pointer was NULL. +/// +/// @ingroup FSR2 DX11 +FFX_API FfxErrorCode ffxFsr2GetInterfaceDX11( + FfxFsr2Interface* fsr2Interface, + ID3D11Device* device, + void* scratchBuffer, + size_t scratchBufferSize); + +/// Create a FfxFsr2Device from a ID3D11Device. +/// +/// @param [in] device A pointer to the DirectX11 device. +/// +/// @returns +/// An abstract FidelityFX device. +/// +/// @ingroup FSR2 DX11 +FFX_API FfxDevice ffxGetDeviceDX11(ID3D11Device* device); + +/// Create a FfxResource from a ID3D11Resource. +/// +/// @param [in] fsr2Interface A pointer to a FfxFsr2Interface structure. +/// @param [in] resDx11 A pointer to the DirectX11 resource. +/// @param [in] name (optional) A name string to identify the resource in debug mode. +/// @param [in] state The state the resource is currently in. +/// +/// @returns +/// An abstract FidelityFX resources. +/// +/// @ingroup FSR2 DX11 +FFX_API FfxResource ffxGetResourceDX11( + FfxFsr2Context* context, + ID3D11Resource* resDx11, + const wchar_t* name = nullptr, + FfxResourceStates state = FFX_RESOURCE_STATE_COMPUTE_READ); + +/// Retrieve a ID3D11Resource pointer associated with a RESOURCE_IDENTIFIER. +/// Used for debug purposes when blitting internal surfaces. +/// +/// @param [in] context A pointer to a FfxFsr2Context structure. +/// @param [in] resId A resource. +/// +/// @returns +/// A ID3D11Resource pointer. +/// +/// @ingroup FSR2 DX11 +FFX_API ID3D11Resource* ffxGetDX11ResourcePtr(FfxFsr2Context* context, uint32_t resId); + +#if defined(__cplusplus) +} +#endif // #if defined(__cplusplus) diff --git a/src/ffx-fsr2-api/dx11/shaders/ffx_fsr2_shaders_dx11.cpp b/src/ffx-fsr2-api/dx11/shaders/ffx_fsr2_shaders_dx11.cpp new file mode 100644 index 0000000..63cdb34 --- /dev/null +++ b/src/ffx-fsr2-api/dx11/shaders/ffx_fsr2_shaders_dx11.cpp @@ -0,0 +1,230 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +#include "ffx_fsr2_shaders_dx11.h" +#include "../../ffx_util.h" + +#include +#include +#include +#include + +#include "ffx_fsr2_tcr_autogen_pass_permutations.h" +#include "ffx_fsr2_autogen_reactive_pass_permutations.h" +#include "ffx_fsr2_accumulate_pass_permutations.h" +#include "ffx_fsr2_compute_luminance_pyramid_pass_permutations.h" +#include "ffx_fsr2_depth_clip_pass_permutations.h" +#include "ffx_fsr2_lock_pass_permutations.h" +#include "ffx_fsr2_reconstruct_previous_depth_pass_permutations.h" +#include "ffx_fsr2_rcas_pass_permutations.h" + +#include "ffx_fsr2_tcr_autogen_pass_16bit_permutations.h" +#include "ffx_fsr2_autogen_reactive_pass_16bit_permutations.h" +#include "ffx_fsr2_accumulate_pass_16bit_permutations.h" +#include "ffx_fsr2_depth_clip_pass_16bit_permutations.h" +#include "ffx_fsr2_lock_pass_16bit_permutations.h" +#include "ffx_fsr2_reconstruct_previous_depth_pass_16bit_permutations.h" +#include "ffx_fsr2_rcas_pass_16bit_permutations.h" + +#if defined(POPULATE_PERMUTATION_KEY) +#undef POPULATE_PERMUTATION_KEY +#endif // #if defined(POPULATE_PERMUTATION_KEY) +#define POPULATE_PERMUTATION_KEY(options, key) \ +key.index = 0; \ +key.FFX_FSR2_OPTION_REPROJECT_USE_LANCZOS_TYPE = FFX_CONTAINS_FLAG(options, FSR2_SHADER_PERMUTATION_USE_LANCZOS_TYPE); \ +key.FFX_FSR2_OPTION_HDR_COLOR_INPUT = FFX_CONTAINS_FLAG(options, FSR2_SHADER_PERMUTATION_HDR_COLOR_INPUT); \ +key.FFX_FSR2_OPTION_LOW_RESOLUTION_MOTION_VECTORS = FFX_CONTAINS_FLAG(options, FSR2_SHADER_PERMUTATION_LOW_RES_MOTION_VECTORS); \ +key.FFX_FSR2_OPTION_JITTERED_MOTION_VECTORS = FFX_CONTAINS_FLAG(options, FSR2_SHADER_PERMUTATION_JITTER_MOTION_VECTORS); \ +key.FFX_FSR2_OPTION_INVERTED_DEPTH = FFX_CONTAINS_FLAG(options, FSR2_SHADER_PERMUTATION_DEPTH_INVERTED); \ +key.FFX_FSR2_OPTION_APPLY_SHARPENING = FFX_CONTAINS_FLAG(options, FSR2_SHADER_PERMUTATION_ENABLE_SHARPENING); + +#if defined(POPULATE_SHADER_BLOB) +#undef POPULATE_SHADER_BLOB +#endif // #if defined(POPULATE_SHADER_BLOB) +#define POPULATE_SHADER_BLOB(info, index) { info[index].blobData, info[index].blobSize, info[index].numUAVResources, info[index].numSRVResources, info[index].numCBVResources, info[index].uavResourceNames, info[index].uavResourceBindings, info[index].srvResourceNames, info[index].srvResourceBindings, info[index].cbvResourceNames, info[index].cbvResourceBindings } + +static Fsr2ShaderBlobDX11 fsr2GetDepthClipPassPermutationBlobByIndex(uint32_t permutationOptions, bool is16bit) +{ + ffx_fsr2_depth_clip_pass_PermutationKey key; + + POPULATE_PERMUTATION_KEY(permutationOptions, key); + + if (is16bit) + { + const int32_t tableIndex = g_ffx_fsr2_depth_clip_pass_16bit_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_depth_clip_pass_16bit_PermutationInfo, tableIndex); + } + else + { + const int32_t tableIndex = g_ffx_fsr2_depth_clip_pass_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_depth_clip_pass_PermutationInfo, tableIndex); + } +} + +static Fsr2ShaderBlobDX11 fsr2GetReconstructPreviousDepthPassPermutationBlobByIndex(uint32_t permutationOptions, bool is16bit) +{ + ffx_fsr2_reconstruct_previous_depth_pass_PermutationKey key; + + POPULATE_PERMUTATION_KEY(permutationOptions, key); + + if (is16bit) + { + const int32_t tableIndex = g_ffx_fsr2_reconstruct_previous_depth_pass_16bit_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_reconstruct_previous_depth_pass_16bit_PermutationInfo, tableIndex); + } + else + { + const int32_t tableIndex = g_ffx_fsr2_reconstruct_previous_depth_pass_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_reconstruct_previous_depth_pass_PermutationInfo, tableIndex); + } +} + +static Fsr2ShaderBlobDX11 fsr2GetLockPassPermutationBlobByIndex(uint32_t permutationOptions, bool is16bit) +{ + ffx_fsr2_lock_pass_PermutationKey key; + + POPULATE_PERMUTATION_KEY(permutationOptions, key); + + if (is16bit) + { + const int32_t tableIndex = g_ffx_fsr2_lock_pass_16bit_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_lock_pass_16bit_PermutationInfo, tableIndex); + } + else + { + const int32_t tableIndex = g_ffx_fsr2_lock_pass_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_lock_pass_PermutationInfo, tableIndex); + } +} + +static Fsr2ShaderBlobDX11 fsr2GetAccumulatePassPermutationBlobByIndex(uint32_t permutationOptions, bool is16bit) +{ + ffx_fsr2_accumulate_pass_PermutationKey key; + + POPULATE_PERMUTATION_KEY(permutationOptions, key); + + if (is16bit) + { + const int32_t tableIndex = g_ffx_fsr2_accumulate_pass_16bit_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_accumulate_pass_16bit_PermutationInfo, tableIndex); + } + else + { + const int32_t tableIndex = g_ffx_fsr2_accumulate_pass_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_accumulate_pass_PermutationInfo, tableIndex); + } +} + +static Fsr2ShaderBlobDX11 fsr2GetRCASPassPermutationBlobByIndex(uint32_t permutationOptions, bool is16bit) +{ + ffx_fsr2_rcas_pass_PermutationKey key; + + POPULATE_PERMUTATION_KEY(permutationOptions, key); + + if (is16bit) + { + const int32_t tableIndex = g_ffx_fsr2_rcas_pass_16bit_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_rcas_pass_16bit_PermutationInfo, tableIndex); + } + else + { + const int32_t tableIndex = g_ffx_fsr2_rcas_pass_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_rcas_pass_PermutationInfo, tableIndex); + } +} + +static Fsr2ShaderBlobDX11 fsr2GetComputeLuminancePyramidPassPermutationBlobByIndex(uint32_t permutationOptions, bool is16bit) +{ + ffx_fsr2_compute_luminance_pyramid_pass_PermutationKey key; + + POPULATE_PERMUTATION_KEY(permutationOptions, key); + + const int32_t tableIndex = g_ffx_fsr2_compute_luminance_pyramid_pass_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_compute_luminance_pyramid_pass_PermutationInfo, tableIndex); +} + +static Fsr2ShaderBlobDX11 fsr2GetAutogenReactivePassPermutationBlobByIndex(uint32_t permutationOptions, bool is16bit) { + + ffx_fsr2_autogen_reactive_pass_PermutationKey key; + + POPULATE_PERMUTATION_KEY(permutationOptions, key); + + if (is16bit) { + + const int32_t tableIndex = g_ffx_fsr2_autogen_reactive_pass_16bit_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_autogen_reactive_pass_16bit_PermutationInfo, tableIndex); + } + else { + + const int32_t tableIndex = g_ffx_fsr2_autogen_reactive_pass_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_autogen_reactive_pass_PermutationInfo, tableIndex); + } +} + +static Fsr2ShaderBlobDX12 fsr2GetTcrAutogeneratePassPermutationBlobByIndex(uint32_t permutationOptions, bool is16bit) { + + ffx_fsr2_autogen_reactive_pass_PermutationKey key; + + POPULATE_PERMUTATION_KEY(permutationOptions, key); + + if (is16bit) { + + const int32_t tableIndex = g_ffx_fsr2_tcr_autogen_pass_16bit_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_tcr_autogen_pass_16bit_PermutationInfo, tableIndex); + } + else { + + const int32_t tableIndex = g_ffx_fsr2_tcr_autogen_pass_IndirectionTable[key.index]; + return POPULATE_SHADER_BLOB(g_ffx_fsr2_tcr_autogen_pass_PermutationInfo, tableIndex); + } +} + +Fsr2ShaderBlobDX11 fsr2GetPermutationBlobByIndexDX11(FfxFsr2Pass passId, uint32_t permutationOptions) +{ + bool is16bit = FFX_CONTAINS_FLAG(permutationOptions, FSR2_SHADER_PERMUTATION_ALLOW_FP16); + + switch (passId) { + + case FFX_FSR2_PASS_DEPTH_CLIP: + return fsr2GetDepthClipPassPermutationBlobByIndex(permutationOptions, is16bit); + case FFX_FSR2_PASS_RECONSTRUCT_PREVIOUS_DEPTH: + return fsr2GetReconstructPreviousDepthPassPermutationBlobByIndex(permutationOptions, is16bit); + case FFX_FSR2_PASS_LOCK: + return fsr2GetLockPassPermutationBlobByIndex(permutationOptions, is16bit); + case FFX_FSR2_PASS_ACCUMULATE: + case FFX_FSR2_PASS_ACCUMULATE_SHARPEN: + return fsr2GetAccumulatePassPermutationBlobByIndex(permutationOptions, is16bit); + case FFX_FSR2_PASS_RCAS: + return fsr2GetRCASPassPermutationBlobByIndex(permutationOptions, is16bit); + case FFX_FSR2_PASS_COMPUTE_LUMINANCE_PYRAMID: + return fsr2GetComputeLuminancePyramidPassPermutationBlobByIndex(permutationOptions, is16bit); + case FFX_FSR2_PASS_GENERATE_REACTIVE: + return fsr2GetAutogenReactivePassPermutationBlobByIndex(permutationOptions, is16bit); + case FFX_FSR2_PASS_TCR_AUTOGENERATE: + return fsr2GetTcrAutogeneratePassPermutationBlobByIndex(permutationOptions, is16bit); + default: + FFX_ASSERT_FAIL("Should never reach here."); + break; + } + + Fsr2ShaderBlobDX11 emptyBlob = {}; + return emptyBlob; +} diff --git a/src/ffx-fsr2-api/dx11/shaders/ffx_fsr2_shaders_dx11.h b/src/ffx-fsr2-api/dx11/shaders/ffx_fsr2_shaders_dx11.h new file mode 100644 index 0000000..5ab7039 --- /dev/null +++ b/src/ffx-fsr2-api/dx11/shaders/ffx_fsr2_shaders_dx11.h @@ -0,0 +1,74 @@ +// This file is part of the FidelityFX SDK. +// +// Copyright (c) 2023 Advanced Micro Devices, Inc. All rights reserved. +// +// Permission is hereby granted, free of charge, to any person obtaining a copy +// of this software and associated documentation files (the "Software"), to deal +// in the Software without restriction, including without limitation the rights +// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +// copies of the Software, and to permit persons to whom the Software is +// furnished to do so, subject to the following conditions: +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +// THE SOFTWARE. + +#pragma once + +#include +#include "../../ffx_fsr2_interface.h" + +#include +#include + +#if defined(__cplusplus) +extern "C" { +#endif // #if defined(__cplusplus) + +// A single shader blob and a description of its resources. +typedef struct Fsr2ShaderBlobDX11 { + + const uint8_t* data; // A pointer to the blob + const uint32_t size; // Size in bytes. + const uint32_t uavCount; // Number of UAV. + const uint32_t srvCount; // Number of SRV. + const uint32_t cbvCount; // Number of CBs. + const char** boundUAVResourceNames; + const uint32_t* boundUAVResources; // Pointer to an array of bound UAV resources. + const char** boundSRVResourceNames; + const uint32_t* boundSRVResources; // Pointer to an array of bound SRV resources. + const char** boundCBVResourceNames; + const uint32_t* boundCBVResources; // Pointer to an array of bound ConstantBuffers. +} Fsr2ShaderBlobDX12; + +//typedef struct Fsr2ShaderBlobDX11 { +// ID3DBlob* codeBlob = nullptr; +// std::vector boundUAVResources; +// std::vector boundSRVResources; +//} Fsr2ShaderBlobDX11; + +// The different options which contribute to permutations. +typedef enum Fs2ShaderPermutationOptionsDX11 { + + FSR2_SHADER_PERMUTATION_USE_LANCZOS_TYPE = (1<<0), // FFX_FSR2_OPTION_REPROJECT_USE_LANCZOS_TYPE. Off means reference, On means LUT + FSR2_SHADER_PERMUTATION_HDR_COLOR_INPUT = (1<<1), // OPT_HDR_COLOR_INPUT + FSR2_SHADER_PERMUTATION_LOW_RES_MOTION_VECTORS = (1<<2), // OPT_LOW_RES_MOTION_VECTORS + FSR2_SHADER_PERMUTATION_JITTER_MOTION_VECTORS = (1<<3), // OPT_JITTERED_MOTION_VECTORS + FSR2_SHADER_PERMUTATION_DEPTH_INVERTED = (1<<4), // OPT_DEPTH_INVERTED + FSR2_SHADER_PERMUTATION_ENABLE_SHARPENING = (1<<5), // OPT_DO_SHARPENING + FSR2_SHADER_PERMUTATION_FORCE_WAVE64 = (1<<6), // OPT_ALLOW_FORCE_WAVE64 + FSR2_SHADER_PERMUTATION_ALLOW_FP16 = (1<<7), // FFX_USE_16BIT +} Fs2ShaderPermutationOptionsDX11; + +// Get a DX11 shader blob for the specified pass and permutation index. +Fsr2ShaderBlobDX11 fsr2GetPermutationBlobByIndexDX11(FfxFsr2Pass passId, uint32_t permutationOptions); + +#if defined(__cplusplus) +} +#endif // #if defined(__cplusplus)