Beispiel #1
0
void StructuredBuffer::ReadFromFile(const wchar* path, ID3D11Device* device)
{
    // Open the file
    HANDLE fileHandle = CreateFile(path, GENERIC_READ, FILE_SHARE_READ, nullptr, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, nullptr);
    if(fileHandle == INVALID_HANDLE_VALUE)
        Win32Call(false);

    // Read the buffer info
    bool32 dynamic, useAsUAV, hiddenCounter, appendConsume;
    DWORD bytesRead = 0;
    Win32Call(ReadFile(fileHandle, &Size, 4, &bytesRead, nullptr));
    Win32Call(ReadFile(fileHandle, &Stride, 4, &bytesRead, nullptr));
    Win32Call(ReadFile(fileHandle, &NumElements, 4, &bytesRead, nullptr));
    Win32Call(ReadFile(fileHandle, &dynamic, 4, &bytesRead, nullptr));
    Win32Call(ReadFile(fileHandle, &useAsUAV, 4, &bytesRead, nullptr));
    Win32Call(ReadFile(fileHandle, &hiddenCounter, 4, &bytesRead, nullptr));
    Win32Call(ReadFile(fileHandle, &appendConsume, 4, &bytesRead, nullptr));

    // Read the buffer data
    UINT8* bufferData = new UINT8[Size];
    Win32Call(ReadFile(fileHandle, bufferData, Size, &bytesRead, nullptr));

    // Close the file
    Win32Call(CloseHandle(fileHandle));

    // Init
    Initialize(device, Stride, NumElements, dynamic, useAsUAV, appendConsume, hiddenCounter, bufferData);

    // Clean up
    delete [] bufferData;
}
Beispiel #2
0
Timer::Timer()
{
    // Query for the performance counter frequency
    LARGE_INTEGER largeInt;
    Win32Call(QueryPerformanceFrequency(&largeInt));
    frequency = largeInt.QuadPart;
    frequencyD = static_cast<double>(frequency);

    // Init the elapsed time
    Win32Call(QueryPerformanceCounter(&largeInt));
    startTime = largeInt.QuadPart;
    elapsed = largeInt.QuadPart - startTime;
    elapsedF = static_cast<float>(elapsed);
    elapsedSeconds = elapsed / frequency;
    elapsedSecondsD = elapsed / frequencyD;
    elapsedSecondsF = static_cast<float>(elapsedSecondsD);
    elapsedMilliseconds = static_cast<int64>(elapsedSecondsD * 1000);
    elapsedMillisecondsD = elapsedSecondsD * 1000;
    elapsedMillisecondsF = static_cast<float>(elapsedMillisecondsD);
    elapsedMicroseconds = static_cast<int64>(elapsedMillisecondsD * 1000);
    elapsedMicrosecondsD = elapsedMillisecondsD * 1000;
    elapsedMicrosecondsF = static_cast<float>(elapsedMillisecondsD);

    delta = 0;
    deltaF = 0;
    deltaMilliseconds = 0;
    deltaMillisecondsF = 0;
    deltaMicroseconds = 0;
    deltaMicrosecondsF = 0;
}
Beispiel #3
0
void File::Open(const wchar* filePath, OpenMode openMode_)
{
    Assert_(fileHandle == INVALID_HANDLE_VALUE);
    openMode = openMode_;

    if(openMode == OpenRead)
    {
        Assert_(FileExists(filePath));

        // Open the file
        fileHandle = CreateFile(filePath, GENERIC_READ, FILE_SHARE_READ, NULL, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, NULL);
        if(fileHandle == INVALID_HANDLE_VALUE)
            Win32Call(false);
    }
    else
    {
        // If the exists, delete it
        if(FileExists(filePath))
            Win32Call(DeleteFile(filePath));

        // Create the file
        fileHandle = CreateFile(filePath, GENERIC_WRITE, 0, NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, NULL);
        if(fileHandle == INVALID_HANDLE_VALUE)
            Win32Call(false);
    }
}
Beispiel #4
0
Timer::Timer()
{
    // Set the thread affinity of the calling thread so that it stays on the
    // same logical processor. QPC can give bogus results if you don't do this.
    HANDLE threadHandle = GetCurrentThread();
    Win32Call(SetThreadAffinityMask(threadHandle, 1) != 0);

    // Query for the performance counter frequency
    LARGE_INTEGER largeInt;
    Win32Call(QueryPerformanceFrequency(&largeInt));
    frequency = largeInt.QuadPart;
    frequencyD = static_cast<double>(frequency);

    // Init the elapsed time
    Win32Call(QueryPerformanceCounter(&largeInt));
    elapsed = largeInt.QuadPart;
    elapsedF = static_cast<float>(elapsed);
    elapsedSeconds = elapsed / frequency;
    elapsedSecondsD = elapsed / frequencyD;
    elapsedSecondsF = static_cast<float>(elapsedSecondsD);
    elapsedMilliseconds = static_cast<INT64>(elapsedSecondsD * 1000);
    elapsedMillisecondsD = elapsedSecondsD * 1000;
    elapsedMillisecondsF = static_cast<float>(elapsedMillisecondsD);
    elapsedMicroseconds = static_cast<INT64>(elapsedMillisecondsD * 1000);
    elapsedMicrosecondsD = elapsedMillisecondsD * 1000;
    elapsedMicrosecondsF = static_cast<float>(elapsedMillisecondsD);

    delta = 0;
    deltaF = 0;
    deltaMilliseconds = 0;
    deltaMillisecondsF = 0;
    deltaMicroseconds = 0;
    deltaMicrosecondsF = 0;
}
Beispiel #5
0
void Timer::Update()
{
    LARGE_INTEGER largeInt;
    Win32Call(QueryPerformanceCounter(&largeInt));
    int64 currentTime = largeInt.QuadPart - startTime;
    delta = currentTime - elapsed;
    deltaF = static_cast<float>(deltaF);
    deltaSeconds = delta / frequency;
    deltaSecondsD = delta / frequencyD;
    deltaSecondsF = static_cast<float>(deltaSecondsD);
    deltaMillisecondsD = deltaSecondsD * 1000;
    deltaMilliseconds = static_cast<int64>(deltaMillisecondsD);
    deltaMillisecondsF = static_cast<float>(deltaMillisecondsD);
    deltaMicrosecondsD = deltaMillisecondsD * 1000;
    deltaMicroseconds = static_cast<int64>(deltaMicrosecondsD);
    deltaMicrosecondsF = static_cast<float>(deltaMicrosecondsD);

    elapsed = currentTime;
    elapsedF = static_cast<float>(elapsed);
    elapsedSeconds = elapsed / frequency;
    elapsedSecondsD = elapsed / frequencyD;
    elapsedSecondsF = static_cast<float>(elapsedSecondsD);
    elapsedMilliseconds = static_cast<int64>(elapsedSecondsD * 1000);
    elapsedMillisecondsD = elapsedSecondsD * 1000;
    elapsedMillisecondsF = static_cast<float>(elapsedMillisecondsD);
    elapsedMicroseconds = static_cast<int64>(elapsedMillisecondsD * 1000);
    elapsedMicrosecondsD = elapsedMillisecondsD * 1000;
    elapsedMicrosecondsF = static_cast<float>(elapsedMillisecondsD);
}
Beispiel #6
0
void File::Write(uint64 size, const void* data) const
{
    Assert_(fileHandle != INVALID_HANDLE_VALUE);
    Assert_(openMode == OpenWrite);

    DWORD bytesWritten = 0;
    Win32Call(WriteFile(fileHandle, data, static_cast<DWORD>(size), &bytesWritten, NULL));
}
Beispiel #7
0
void File::Read(uint64 size, void* data) const
{
    Assert_(fileHandle != INVALID_HANDLE_VALUE);
    Assert_(openMode == OpenRead);

    DWORD bytesRead = 0;
    Win32Call(ReadFile(fileHandle, data, static_cast<DWORD>(size), &bytesRead, NULL));
}
Beispiel #8
0
// Gets the last written timestamp of the file
uint64 GetFileTimestamp(const wchar* filePath)
{
    Assert_(filePath);

    WIN32_FILE_ATTRIBUTE_DATA attributes;
    Win32Call(GetFileAttributesEx(filePath, GetFileExInfoStandard, &attributes));
    return attributes.ftLastWriteTime.dwLowDateTime | (uint64(attributes.ftLastWriteTime.dwHighDateTime) << 32);
}
Beispiel #9
0
uint64 File::Size() const
{
    Assert_(fileHandle != INVALID_HANDLE_VALUE);

    LARGE_INTEGER fileSize;
    Win32Call(GetFileSizeEx(fileHandle, &fileSize));

    return fileSize.QuadPart;
}
Beispiel #10
0
void File::Close()
{
    if(fileHandle == INVALID_HANDLE_VALUE)
        return;

    // Close the file
    Win32Call(CloseHandle(fileHandle));

    fileHandle = INVALID_HANDLE_VALUE;
}
Beispiel #11
0
void StructuredBuffer::WriteToFile(const wchar* path, ID3D11Device* device, ID3D11DeviceContext* context)
{
    Assert_(Buffer != nullptr);

    // Get the buffer info
    D3D11_BUFFER_DESC desc;
    Buffer->GetDesc(&desc);

    uint32 useAsUAV = (desc.BindFlags & D3D11_BIND_UNORDERED_ACCESS) ? 1 : 0;
	uint32 dynamic = (desc.BindFlags & D3D11_USAGE_DYNAMIC) ? 1 : 0;

    uint32 appendConsume = 0;
    uint32 hiddenCounter = 0;
    if(useAsUAV)
    {
        D3D11_UNORDERED_ACCESS_VIEW_DESC uavDesc;
        UAView->GetDesc(&uavDesc);
        appendConsume = (uavDesc.Format & D3D11_BUFFER_UAV_FLAG_APPEND) ? 1 : 0;
        hiddenCounter =(uavDesc.Format & D3D11_BUFFER_UAV_FLAG_COUNTER) ? 1 : 0;
    }

    // If the exists, delete it
    if(FileExists(path))
        Win32Call(DeleteFile(path));

    // Create the file
    HANDLE fileHandle = CreateFile(path, GENERIC_WRITE, 0, nullptr, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, nullptr);
    if(fileHandle == INVALID_HANDLE_VALUE)
        Win32Call(false);

    // Write the buffer info
    DWORD bytesWritten = 0;
    Win32Call(WriteFile(fileHandle, &Size, 4, &bytesWritten, nullptr));
    Win32Call(WriteFile(fileHandle, &Stride, 4, &bytesWritten, nullptr));
    Win32Call(WriteFile(fileHandle, &NumElements, 4, &bytesWritten, nullptr));
    Win32Call(WriteFile(fileHandle, &dynamic, 4, &bytesWritten, nullptr));
    Win32Call(WriteFile(fileHandle, &useAsUAV, 4, &bytesWritten, nullptr));
    Win32Call(WriteFile(fileHandle, &hiddenCounter, 4, &bytesWritten, nullptr));
    Win32Call(WriteFile(fileHandle, &appendConsume, 4, &bytesWritten, nullptr));

    // Get the buffer data
    StagingBuffer stagingBuffer;
    stagingBuffer.Initialize(device, Size);
    context->CopyResource(stagingBuffer.Buffer, Buffer);
    const void* bufferData= stagingBuffer.Map(context);

    // Write the data to the file
    Win32Call(WriteFile(fileHandle, bufferData, Size, &bytesWritten, nullptr));

    // Un-map the staging buffer
    stagingBuffer.Unmap(context);

    // Close the file
    Win32Call(CloseHandle(fileHandle));
}
Beispiel #12
0
static ID3DBlob* CompileShader(const wchar* path, const char* functionName, const char* profile,
                              const D3D_SHADER_MACRO* defines, bool forceOptimization,
                              vector<wstring>& filePaths)
{
    // Make a hash off the expanded shader code
    string shaderCode = GetExpandedShaderCode(path, filePaths);
    wstring cacheName = MakeShaderCacheName(shaderCode, functionName, profile, defines);

    if(FileExists(cacheName.c_str()))
    {
        File cacheFile(cacheName.c_str(), File::OpenRead);

        const uint64 shaderSize = cacheFile.Size();
        vector<uint8> compressedShader;
        compressedShader.resize(shaderSize);
        cacheFile.Read(shaderSize, compressedShader.data());

        ID3DBlob* decompressedShader[1] = { nullptr };
        uint32 indices[1] = { 0 };
        DXCall(D3DDecompressShaders(compressedShader.data(), shaderSize, 1, 0,
                                    indices, 0, decompressedShader, nullptr));

        return decompressedShader[0];
    }

    std::printf("Compiling shader %s %s %s\n", WStringToAnsi(GetFileName(path).c_str()).c_str(),
                profile, MakeDefinesString(defines).c_str());

    // Loop until we succeed, or an exception is thrown
    while(true)
    {
        UINT flags = D3DCOMPILE_WARNINGS_ARE_ERRORS;
        #ifdef _DEBUG
            flags |= D3DCOMPILE_DEBUG;
            if(forceOptimization == false)
                flags |= D3DCOMPILE_SKIP_OPTIMIZATION;
        #endif

        ID3DBlob* compiledShader;
        ID3DBlobPtr errorMessages;
        HRESULT hr = D3DCompileFromFile(path, defines, D3D_COMPILE_STANDARD_FILE_INCLUDE, functionName,
                                        profile, flags, 0, &compiledShader, &errorMessages);

        if(FAILED(hr))
        {
            if(errorMessages)
            {
                wchar message[1024] = { 0 };
                char* blobdata = reinterpret_cast<char*>(errorMessages->GetBufferPointer());

                MultiByteToWideChar(CP_ACP, 0, blobdata, static_cast<int>(errorMessages->GetBufferSize()), message, 1024);
                std::wstring fullMessage = L"Error compiling shader file \"";
                fullMessage += path;
                fullMessage += L"\" - ";
                fullMessage += message;

                // Pop up a message box allowing user to retry compilation
                int retVal = MessageBoxW(nullptr, fullMessage.c_str(), L"Shader Compilation Error", MB_RETRYCANCEL);
                if(retVal != IDRETRY)
                    throw DXException(hr, fullMessage.c_str());

                #if EnableShaderCaching_
                    shaderCode = GetExpandedShaderCode(path);
                    cacheName = MakeShaderCacheName(shaderCode, functionName, profile, defines);
                #endif
            }
            else
            {
                _ASSERT(false);
                throw DXException(hr);
            }
        }
        else
        {
            // Compress the shader
            D3D_SHADER_DATA shaderData;
            shaderData.pBytecode = compiledShader->GetBufferPointer();
            shaderData.BytecodeLength = compiledShader->GetBufferSize();
            ID3DBlobPtr compressedShader;
            DXCall(D3DCompressShaders(1, &shaderData, D3D_COMPRESS_SHADER_KEEP_ALL_PARTS, &compressedShader));

            // Create the cache directory if it doesn't exist
            if(DirectoryExists(baseCacheDir.c_str()) == false)
                Win32Call(CreateDirectory(baseCacheDir.c_str(), nullptr));

            if(DirectoryExists(cacheDir.c_str()) == false)
                Win32Call(CreateDirectory(cacheDir.c_str(), nullptr));

            File cacheFile(cacheName.c_str(), File::OpenWrite);

            // Write the compiled shader to disk
            uint64 shaderSize = compressedShader->GetBufferSize();
            cacheFile.Write(shaderSize, compressedShader->GetBufferPointer());

            return compiledShader;
        }
    }
}
Beispiel #13
0
int32 App::Run()
{
    try
    {
        if(createConsole)
        {
            Win32Call(AllocConsole());
            Win32Call(SetConsoleTitle(applicationName.c_str()));
            FILE* consoleFile = nullptr;
            freopen_s(&consoleFile, "CONOUT$", "wb", stdout);
        }

        window.SetClientArea(deviceManager.BackBufferWidth(), deviceManager.BackBufferHeight());
        deviceManager.Initialize(window);

        if(showWindow)
            window.ShowWindow();

        blendStates.Initialize(deviceManager.Device());
        rasterizerStates.Initialize(deviceManager.Device());
        depthStencilStates.Initialize(deviceManager.Device());
        samplerStates.Initialize(deviceManager.Device());

        // Create a font + SpriteRenderer
        font.Initialize(L"Arial", 18, SpriteFont::Regular, true, deviceManager.Device());
        spriteRenderer.Initialize(deviceManager.Device());

        Profiler::GlobalProfiler.Initialize(deviceManager.Device(), deviceManager.ImmediateContext());

        window.RegisterMessageCallback(WM_SIZE, OnWindowResized, this);

        // Initialize AntTweakBar
        TwCall(TwInit(TW_DIRECT3D11, deviceManager.Device()));

        // Create a tweak bar
        tweakBar = TwNewBar("Settings");
        std::string helpTextDefinition = MakeAnsiString(" GLOBAL help='%s' ", globalHelpText.c_str());
        TwCall(TwDefine(helpTextDefinition.c_str()));
        TwCall(TwDefine(" GLOBAL fontsize=3 "));

        Settings.Initialize(tweakBar);

        TwHelper::SetValuesWidth(Settings.TweakBar(), 120, false);

        AppSettings::Initialize(deviceManager.Device());

        Initialize();

        AfterReset();

        while(window.IsAlive())
        {
            if(!window.IsMinimized())
            {
                timer.Update();
                Settings.Update();

                CalculateFPS();

                AppSettings::Update();

                Update(timer);

                UpdateShaders(deviceManager.Device());

                AppSettings::UpdateCBuffer(deviceManager.ImmediateContext());

                Render(timer);

                // Render the profiler text
                spriteRenderer.Begin(deviceManager.ImmediateContext(), SpriteRenderer::Point);
                Profiler::GlobalProfiler.EndFrame(spriteRenderer, font);
                spriteRenderer.End();

                {
                    PIXEvent pixEvent(L"Ant Tweak Bar");

                    // Render the TweakBar UI
                    TwCall(TwDraw());
                }

                deviceManager.Present();
            }

            window.MessageLoop();
        }
    }
    catch(SampleFramework11::Exception exception)
    {
        exception.ShowErrorMessage();
        return -1;
    }

    ShutdownShaders();

    TwCall(TwTerminate());

    if(createConsole)
    {
        fclose(stdout);
        FreeConsole();
    }

    return returnCode;
}
static ID3DBlob* CompileShader(const wchar* path, const char* functionName, ShaderType type, ShaderProfile profile,
                              const D3D_SHADER_MACRO* defines, bool forceOptimization, GrowableList<wstring>& filePaths)
{
    if(FileExists(path) == false)
    {
        Assert_(false);
        throw Exception(L"Shader file " + std::wstring(path) + L" does not exist");
    }

    uint64 profileIdx = uint64(profile) * uint64(ShaderType::NumTypes) + uint64(type);
    Assert_(profileIdx < TotalNumProfiles);
    const char* profileString = ProfileStrings[profileIdx];

    // Make a hash off the expanded shader code
    string shaderCode = GetExpandedShaderCode(path, filePaths);
    wstring cacheName = MakeShaderCacheName(shaderCode, functionName, profileString, defines);

    if(FileExists(cacheName.c_str()))
    {
        File cacheFile(cacheName.c_str(), FileOpenMode::Read);

        const uint64 shaderSize = cacheFile.Size();
        Array<uint8> compressedShader;
        compressedShader.Init(shaderSize);
        cacheFile.Read(shaderSize, compressedShader.Data());

        ID3DBlob* decompressedShader[1] = { nullptr };
        uint32 indices[1] = { 0 };
        DXCall(D3DDecompressShaders(compressedShader.Data(), shaderSize, 1, 0,
                                    indices, 0, decompressedShader, nullptr));

        return decompressedShader[0];
    }

    WriteLog("Compiling %s shader %s_%s %s\n", TypeStrings[uint64(type)],
                WStringToAnsi(GetFileName(path).c_str()).c_str(),
                functionName, MakeDefinesString(defines).c_str());

    // Loop until we succeed, or an exception is thrown
    while(true)
    {
        UINT flags = D3DCOMPILE_WARNINGS_ARE_ERRORS;
        #ifdef _DEBUG
            flags |= D3DCOMPILE_DEBUG;
            // This is causing some shader bugs
            /*if(forceOptimization == false)
                flags |= D3DCOMPILE_SKIP_OPTIMIZATION;*/
        #endif

        ID3DBlob* compiledShader;
        ID3DBlobPtr errorMessages;
        FrameworkInclude include;
        HRESULT hr = D3DCompileFromFile(path, defines, &include, functionName,
                                        profileString, flags, 0, &compiledShader, &errorMessages);

        if(FAILED(hr))
        {
            if(errorMessages)
            {
                wchar message[1024] = { 0 };
                char* blobdata = reinterpret_cast<char*>(errorMessages->GetBufferPointer());

                MultiByteToWideChar(CP_ACP, 0, blobdata, static_cast<int>(errorMessages->GetBufferSize()), message, 1024);
                std::wstring fullMessage = L"Error compiling shader file \"";
                fullMessage += path;
                fullMessage += L"\" - ";
                fullMessage += message;

                // Pop up a message box allowing user to retry compilation
                int retVal = MessageBoxW(nullptr, fullMessage.c_str(), L"Shader Compilation Error", MB_RETRYCANCEL);
                if(retVal != IDRETRY)
                    throw DXException(hr, fullMessage.c_str());
            }
            else
            {
                Assert_(false);
                throw DXException(hr);
            }
        }
        else
        {
            // Compress the shader
            D3D_SHADER_DATA shaderData;
            shaderData.pBytecode = compiledShader->GetBufferPointer();
            shaderData.BytecodeLength = compiledShader->GetBufferSize();
            ID3DBlobPtr compressedShader;
            DXCall(D3DCompressShaders(1, &shaderData, D3D_COMPRESS_SHADER_KEEP_ALL_PARTS, &compressedShader));

            // Create the cache directory if it doesn't exist
            if(DirectoryExists(baseCacheDir.c_str()) == false)
                Win32Call(CreateDirectory(baseCacheDir.c_str(), nullptr));

            if(DirectoryExists(cacheDir.c_str()) == false)
                Win32Call(CreateDirectory(cacheDir.c_str(), nullptr));

            File cacheFile(cacheName.c_str(), FileOpenMode::Write);

            // Write the compiled shader to disk
            uint64 shaderSize = compressedShader->GetBufferSize();
            cacheFile.Write(shaderSize, compressedShader->GetBufferPointer());

            return compiledShader;
        }
    }
}