Freigeben über


Zeichnen auf dem Bildschirm

Wichtige APIs

Schließlich portieren wir den Code, der den sich drehenden Würfel auf den Bildschirm zeichnet.

In OpenGL ES 2.0 wird der Zeichnungskontext als EGLContext-Typ definiert, der die Fenster- und Oberflächenparameter sowie die Ressourcen enthält, die zum Zeichnen auf die Renderziele erforderlich sind, die zum Verfassen des endgültigen Bilds verwendet werden, das im Fenster angezeigt wird. Sie verwenden diesen Kontext, um die Grafikressourcen so zu konfigurieren, dass die Ergebnisse der Shaderpipeline auf der Anzeige ordnungsgemäß angezeigt werden. Eine der primären Ressourcen ist der "Hintergrundpuffer" (oder "Framepufferobjekt"), der die endgültigen, zusammengesetzten Renderziele enthält, die für die Präsentation bereit für die Anzeige sind.

Mit Direct3D ist der Prozess der Konfiguration der Grafikressourcen für das Zeichnen auf die Anzeige didaktischer und erfordert einige weitere APIs. (Eine Microsoft Visual Studio Direct3D-Vorlage kann diesen Vorgang jedoch erheblich vereinfachen!) Um einen Kontext (als Direct3D-Gerätekontext bezeichnet) abzurufen, müssen Sie zuerst ein ID3D11Device1-Objekt abrufen und es zum Erstellen und Konfigurieren eines ID3D11DeviceContext1-Objekts verwenden. Diese beiden Objekte werden zusammen verwendet, um die spezifischen Ressourcen zu konfigurieren, die Sie zum Zeichnen auf die Anzeige benötigen.

Kurz gesagt, die DXGI-APIs enthalten in erster Linie APIs zum Verwalten von Ressourcen, die direkt zum Grafikadapter gehören, und Direct3D enthält die APIs, mit denen Sie zwischen der GPU und Dem Hauptprogramm, das auf der CPU ausgeführt wird, schnittstellen können.

Für die Zwecke des Vergleichs in diesem Beispiel sind hier die relevanten Typen aus den einzelnen APIs:

  • ID3D11Device1: stellt eine virtuelle Darstellung des Grafikgeräts und seiner Ressourcen bereit.
  • ID3D11DeviceContext1: Stellt die Schnittstelle zum Konfigurieren von Puffern und Ausgeben von Renderingbefehlen bereit.
  • IDXGISwapChain1: Die Swapchain entspricht dem Hintergrundpuffer in OpenGL ES 2.0. Es handelt sich um den Speicherbereich auf dem Grafikkartenadapter, der die endgültigen gerenderten Bilder für die Anzeige enthält. Sie wird als "Swapchain" bezeichnet, da sie mehrere Puffer enthält, die in den Bildschirm geschrieben und "getauscht" werden können, um das neueste Rendern auf dem Bildschirm darzustellen.
  • ID3D11RenderTargetView: Dies enthält den 2D-Bitmappuffer, in den der Direct3D-Gerätekontext zeichnet und in den der Swapchain dargestellt wird. Wie bei OpenGL ES 2.0 können Sie über mehrere Renderziele verfügen, von denen einige nicht an die Swapchain gebunden sind, aber für Multi-Pass-Schattierungstechniken verwendet werden.

In der Vorlage enthält das Rendererobjekt die folgenden Felder:

Direct3D 11: Geräte- und Gerätekontextdeklarationen

Platform::Agile<Windows::UI::Core::CoreWindow>       m_window;

Microsoft::WRL::ComPtr<ID3D11Device1>                m_d3dDevice;
Microsoft::WRL::ComPtr<ID3D11DeviceContext1>          m_d3dContext;
Microsoft::WRL::ComPtr<IDXGISwapChain1>                      m_swapChainCoreWindow;
Microsoft::WRL::ComPtr<ID3D11RenderTargetView>          m_d3dRenderTargetViewWin;

Hier erfahren Sie, wie der Hintergrundpuffer als Renderziel konfiguriert und der Swapchain bereitgestellt wird.

ComPtr<ID3D11Texture2D> backBuffer;
m_swapChainCoreWindow->GetBuffer(0, IID_PPV_ARGS(backBuffer));
m_d3dDevice->CreateRenderTargetView(
  backBuffer.Get(),
  nullptr,
  &m_d3dRenderTargetViewWin);

Die Direct3D-Laufzeit erstellt implizit eine IDXGISurface1 für die ID3D11Texture2D, die die Textur als "Hintergrundpuffer" darstellt, den die Swapchain für die Anzeige verwenden kann.

Die Initialisierung und Konfiguration des Direct3D-Geräte- und Gerätekontexts sowie der Renderziele finden Sie in den benutzerdefinierten CreateDeviceResources - und CreateWindowSizeDependentResources-Methoden in der Direct3D-Vorlage.

Weitere Informationen zum Direct3D-Gerätekontext im Zusammenhang mit EGL und dem EGLContext-Typ finden Sie unter Port EGL-Code zu DXGI und Direct3D.

Anweisungen

Schritt 1: Rendern der Szene und Anzeigen der Szene

Nach dem Aktualisieren der Cubedaten (in diesem Fall durch eine geringfügige Drehung um die Y-Achse) legt die Render-Methode den Viewport auf die Dimensionen des Zeichnungskontexts (EGLContext) fest. Dieser Kontext enthält den Farbpuffer, der mithilfe der konfigurierten Anzeige (EGLDisplay) auf der Fensteroberfläche (EGLSurface) angezeigt wird. Zu diesem Zeitpunkt aktualisiert das Beispiel die Vertexdatenattribute, bindet den Indexpuffer erneut, zeichnet den Würfel und wechselt in Farbpuffer, der von der Schattierungspipeline auf die Anzeigeoberfläche gezeichnet wird.

OpenGL ES 2.0: Rendern eines Frames für die Anzeige

void Render(GraphicsContext *drawContext)
{
  Renderer *renderer = drawContext->renderer;

  int loc;
   
  // Set the viewport
  glViewport ( 0, 0, drawContext->width, drawContext->height );
   
   
  // Clear the color buffer
  glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
  glEnable(GL_DEPTH_TEST);


  // Use the program object
  glUseProgram (renderer->programObject);

  // Load the a_position attribute with the vertex position portion of a vertex buffer element
  loc = glGetAttribLocation(renderer->programObject, "a_position");
  glVertexAttribPointer(loc, 3, GL_FLOAT, GL_FALSE, 
      sizeof(Vertex), 0);
  glEnableVertexAttribArray(loc);

  // Load the a_color attribute with the color position portion of a vertex buffer element
  loc = glGetAttribLocation(renderer->programObject, "a_color");
  glVertexAttribPointer(loc, 4, GL_FLOAT, GL_FALSE, 
      sizeof(Vertex), (GLvoid*) (sizeof(float) * 3));
  glEnableVertexAttribArray(loc);

  // Bind the index buffer
  glBindBuffer(GL_ELEMENT_ARRAY_BUFFER, renderer->indexBuffer);

  // Load the MVP matrix
  glUniformMatrix4fv(renderer->mvpLoc, 1, GL_FALSE, (GLfloat*) &renderer->mvpMatrix.m[0][0]);

  // Draw the cube
  glDrawElements(GL_TRIANGLES, renderer->numIndices, GL_UNSIGNED_INT, 0);

  eglSwapBuffers(drawContext->eglDisplay, drawContext->eglSurface);
}

In Direct3D 11 ist der Prozess sehr ähnlich. (Es wird davon ausgegangen, dass Sie die Viewport- und Renderzielkonfiguration aus der Direct3D-Vorlage verwenden.

Direct3D 11: Rendern eines Frames für die Anzeige

void RenderObject::Render()
{
  // ...

  // Only update shader resources that have changed since the last frame.
  m_d3dContext->UpdateSubresource(
    m_constantBuffer.Get(),
    0,
    NULL,
    &m_constantBufferData,
    0,
    0);

  // Set up the IA stage corresponding to the current draw operation.
  UINT stride = sizeof(VertexPositionColor);
  UINT offset = 0;
  m_d3dContext->IASetVertexBuffers(
    0,
    1,
    m_vertexBuffer.GetAddressOf(),
    &stride,
    &offset);

  m_d3dContext->IASetIndexBuffer(
    m_indexBuffer.Get(),
    DXGI_FORMAT_R16_UINT,
    0);

  m_d3dContext->IASetPrimitiveTopology(D3D11_PRIMITIVE_TOPOLOGY_TRIANGLELIST);
  m_d3dContext->IASetInputLayout(m_inputLayout.Get());

  // Set up the vertex shader corresponding to the current draw operation.
  m_d3dContext->VSSetShader(
    m_vertexShader.Get(),
    nullptr,
    0);

  m_d3dContext->VSSetConstantBuffers(
    0,
    1,
    m_constantBuffer.GetAddressOf());

  // Set up the pixel shader corresponding to the current draw operation.
  m_d3dContext->PSSetShader(
    m_pixelShader.Get(),
    nullptr,
    0);

  m_d3dContext->DrawIndexed(
    m_indexCount,
    0,
    0);

    // ...

  m_swapChainCoreWindow->Present1(1, 0, &parameters);
}

Sobald IDXGISwapChain1::P resent1 aufgerufen wird, wird Ihr Frame an die konfigurierte Anzeige ausgegeben.

Vorheriger Schritt

Port the GLSL

Hinweise

Dieses Beispiel glänzt über einen Großteil der Komplexität, die in die Konfiguration von Geräteressourcen geht, insbesondere für Universelle Windows-Plattform (UWP)-DirectX-Apps. Es wird empfohlen, den vollständigen Vorlagencode zu überprüfen, insbesondere die Teile, die die Einrichtung und Verwaltung von Fenster- und Geräteressourcen ausführen. UWP-Apps müssen Drehungsereignisse sowie Anhalte-/Fortsetzungsereignisse unterstützen, und die Vorlage veranschaulicht bewährte Methoden zum Behandeln des Verlusts einer Schnittstelle oder einer Änderung der Anzeigeparameter.