1

D3D アプリで安定した固定 60 fps を達成しようとしており、それを行うには vsync を実行します。次のようにループをセットアップしました。

while(isRunning)
            {
                ProcessMessages(window);

                renderer->context->ClearRenderTargetView(renderer->renderTarget, color);
                renderer->swapChain->Present(1, 0);

                end = GetCurrentTick();
                double ms = GetElapsedMilliseconds(start, end);
                start = end;
            }

// Function definitions

inline LONGLONG GetCurrentTick()
{
    LARGE_INTEGER count;
    QueryPerformanceCounter(&count);
    return count.QuadPart;
}

inline double GetElapsedMilliseconds(LONGLONG start, LONGLONG end)
{
    return (1000.0 * (double)(end - start)) / (double)freq.QuadPart;
}

「ms」変数は常に同じであると予想されますが、実際には約 16.1 ミリ秒から 17 ミリ秒を超えて変化しています。私が行っている間違った仮定や単純なコーディング エラーはありますか? 事前に助けてくれてありがとう。

4

1 に答える 1

0

空ループのタイミングは特に正確ではなく、簡単に混乱する可能性があるため、代わりに実際のシーンがあるものを作成する必要があります。その後、GPUViewまたは同様のツールを使用して、コード内のストールを把握できます。

ここで起こっているのは、Windows では 3 つのフレームをキューに入れ、1 つのフレームが処理されるまでスレッドをスリープ状態にしてから、再び準備を整えるということです。デフォルトのスケジューラ クォンタムは 15 ミリ秒であるため、基本的に Present キューによって保持されているこの安定した状態になると、それだけの遅延が発生します。

Present でを使用すると、コードでこの動作を検出できます。その場合、スレッドをスリープ状態にするのではなくDXGI_PRESENT_DO_NOT_WAIT、失敗コードが返されます。DXGI_ERROR_WAS_STILL_DRAWING

また、使用しているフリップ モデルについては言及していません。

于 2014-12-19T16:48:05.273 に答える