Método ID3D11DeviceContext::UpdateSubresource (d3d11.h)

Consulte o exemplo de holograma básico.

A CPU copia dados da memória para um sub-recurso criado na memória não aplicaível.

Sintaxe

void UpdateSubresource(
  [in]           ID3D11Resource  *pDstResource,
  [in]           UINT            DstSubresource,
  [in, optional] const D3D11_BOX *pDstBox,
  [in]           const void      *pSrcData,
  [in]           UINT            SrcRowPitch,
  [in]           UINT            SrcDepthPitch
);

Parâmetros

[in] pDstResource

Tipo: ID3D11Resource*

Um ponteiro para o recurso de destino (consulte ID3D11Resource).

[in] DstSubresource

Tipo: UINT

Um índice baseado em zero, que identifica o sub-recurso de destino. Consulte D3D11CalcSubresource para obter mais detalhes.

[in, optional] pDstBox

Tipo: const D3D11_BOX*

Um ponteiro para uma caixa que define a parte do sub-recurso de destino para a qual copiar os dados do recurso. As coordenadas estão em bytes para buffers e em texels para texturas. Se NULL, os dados serão gravados na sub-fonte de destino sem deslocamento. As dimensões da origem devem se ajustar ao destino (consulte D3D11_BOX).

Uma caixa vazia resulta em uma no-op. Uma caixa estará vazia se o valor superior for maior ou igual ao valor inferior ou o valor esquerdo for maior ou igual ao valor à direita ou o valor frontal for maior ou igual ao valor de fundo. Quando a caixa está vazia, UpdateSubresource não executa uma operação de atualização.

[in] pSrcData

Tipo: const void*

Um ponteiro para os dados de origem na memória.

[in] SrcRowPitch

Tipo: UINT

O tamanho de uma linha dos dados de origem.

[in] SrcDepthPitch

Tipo: UINT

O tamanho de uma fatia de profundidade dos dados de origem.

Valor retornado

Nenhum

Comentários

Para um buffer de constante de sombreador; defina pDstBox como NULL. Não é possível usar esse método para atualizar parcialmente um buffer de constante de sombreador.

Um recurso não poderá ser usado como destino se:

  • o recurso é criado com uso imutável ou dinâmico .
  • o recurso é criado como um recurso de estêncil de profundidade.
  • o recurso é criado com funcionalidade multisampling (consulte DXGI_SAMPLE_DESC).
Quando UpdateSubresource retorna, o aplicativo é livre para alterar ou até mesmo liberar os dados apontados por pSrcData porque o método já copiou/tirou o conteúdo original.

O desempenho do UpdateSubresource depende se há ou não contenção para o recurso de destino. Por exemplo, a contenção de um recurso de buffer de vértice ocorre quando o aplicativo executa uma chamada de Desenho e, posteriormente, chama UpdateSubresource no mesmo buffer de vértice antes que a chamada de Desenho seja realmente executada pela GPU.

  • Quando houver contenção para o recurso, UpdateSubresource executará duas cópias dos dados de origem. Primeiro, os dados são copiados pela CPU para um espaço de armazenamento temporário acessível pelo buffer de comando. Essa cópia ocorre antes que o método retorne. Em seguida, uma segunda cópia é executada pela GPU para copiar os dados de origem em memória não aplicaível. Essa segunda cópia ocorre de forma assíncrona porque é executada pela GPU quando o buffer de comando é liberado.
  • Quando não há contenção de recursos, o comportamento de UpdateSubresource depende do que é mais rápido (da perspectiva da CPU): copiar os dados para o buffer de comando e, em seguida, ter uma segunda cópia executada quando o buffer de comando é liberado ou fazer com que a CPU copie os dados para o local final do recurso. Isso depende da arquitetura do sistema subjacente.
ObservaçãoAplica-se somente ao nível do recurso 9_x hardware Se você usar UpdateSubresource ou ID3D11DeviceContext::CopySubresourceRegion para copiar de um recurso de preparo para um recurso padrão, poderá corromper o conteúdo de destino. Isso ocorrerá se você passar uma caixa de origem NULL e se o recurso de origem tiver dimensões diferentes daquelas do recurso de destino ou se você usar deslocamentos de destino (x, y e z). Nessa situação, sempre passe uma caixa de origem que tenha o tamanho total do recurso de origem.
 
Para entender melhor os parâmetros de tom de linha de origem e de profundidade de origem, a ilustração a seguir mostra uma textura de volume 3D. Ilustração de uma textura de volume 3D

Cada bloco nesse visual representa um elemento de dados e o tamanho de cada elemento depende do formato do recurso. Por exemplo, se o formato de recurso for DXGI_FORMAT_R32G32B32A32_FLOAT, o tamanho de cada elemento será de 128 bits ou 16 bytes. Essa textura de volume 3D tem uma largura de dois, uma altura de três e uma profundidade de quatro.

Para calcular o tom de linha de origem e o tom de profundidade de origem para um determinado recurso, use as seguintes fórmulas:

  • Pitch de Linha de Origem = [tamanho de um elemento em bytes] * [número de elementos em uma linha]
  • Arremesso de Profundidade de Origem = [Campo de Linha de Origem] * [número de linhas (altura)]
No caso deste exemplo de textura de volume 3D em que o tamanho de cada elemento é de 16 bytes, as fórmulas são as seguintes:
  • Campo de linha de origem = 16 * 2 = 32
  • Arremesso de Profundidade de Origem = 16 * 2 * 3 = 96
A ilustração a seguir mostra o recurso conforme ele é disposto na memória. Ilustração de uma textura de volume 3D disposta na memória

Por exemplo, o snippet de código a seguir mostra como especificar uma região de destino em uma textura 2D. Suponha que a textura de destino seja 512x512 e a operação copiará os dados apontados por pData para [(120,100).. (200.220)] na textura de destino. Suponha também que rowPitch tenha sido inicializado com o valor adequado (conforme explicado acima). front e back são definidos como 0 e 1, respectivamente, porque por ter frente igual a back, a caixa está tecnicamente vazia.


D3D11_BOX destRegion;
destRegion.left = 120;
destRegion.right = 200;
destRegion.top = 100;
destRegion.bottom = 220;
destRegion.front = 0;
destRegion.back = 1;

pd3dDeviceContext->UpdateSubresource( pDestTexture, 0, &destRegion, pData, rowPitch, 0 );

O caso 1D é semelhante. O snippet a seguir mostra como especificar uma região de destino em uma textura 1D. Use as mesmas suposições que acima, exceto que a textura tem 512 de comprimento.


D3D11_BOX destRegion;
destRegion.left = 120;
destRegion.right = 200;
destRegion.top = 0;
destRegion.bottom = 1;
destRegion.front = 0;
destRegion.back = 1;

pd3dDeviceContext->UpdateSubresource( pDestTexture, 0, &destRegion, pData, rowPitch, 0 );

Para obter informações sobre vários tipos de recursos e como UpdateSubresource pode funcionar com cada tipo de recurso, consulte Introdução a um recurso no Direct3D 11.

Chamando UpdateSubresource em um contexto adiado

Se o aplicativo chamar UpdateSubresource em um contexto adiado com uma caixa de destino, para a qual pDstBox aponta, que tem um deslocamento não (0,0,0) e, se o driver não der suporte a listas de comandos, UpdateSubresource aplicará inadequadamente esse deslocamento de caixa de destino ao parâmetro pSrcData . Para contornar esse comportamento, use o seguinte código:

HRESULT UpdateSubresource_Workaround(
  ID3D11Device *pDevice,
  ID3D11DeviceContext *pDeviceContext,
  ID3D11Resource *pDstResource,
  UINT dstSubresource,
  const D3D11_BOX *pDstBox,
  const void *pSrcData,
  UINT srcBytesPerElement,
  UINT srcRowPitch,
  UINT srcDepthPitch,
  bool* pDidWorkAround )
{
     HRESULT hr = S_OK;
     bool needWorkaround = false;
     D3D11_DEVICE_CONTEXT_TYPE contextType = pDeviceContext->GetType();

     if( pDstBox && (D3D11_DEVICE_CONTEXT_DEFERRED == contextType) )
     {
          D3D11_FEATURE_DATA_THREADING threadingCaps = { FALSE, FALSE };

          hr = pDevice->CheckFeatureSupport( D3D11_FEATURE_THREADING, &threadingCaps, sizeof(threadingCaps) );
          if( SUCCEEDED(hr) )
          {
               if( !threadingCaps.DriverCommandLists )
               {
                    needWorkaround = true;
               }
          }
     }

     const void* pAdjustedSrcData = pSrcData;

     if( needWorkaround )
     {
          D3D11_BOX alignedBox = *pDstBox;
		
          // convert from pixels to blocks
          if( m_bBC )
          {
               alignedBox.left     /= 4;
               alignedBox.right    /= 4;
               alignedBox.top      /= 4;
               alignedBox.bottom   /= 4;
          }

          pAdjustedSrcData = ((const BYTE*)pSrcData) - (alignedBox.front * srcDepthPitch) - (alignedBox.top * srcRowPitch) - (alignedBox.left * srcBytesPerElement);
     }

     pDeviceContext->UpdateSubresource( pDstResource, dstSubresource, pDstBox, pAdjustedSrcData, srcRowPitch, srcDepthPitch );

     if( pDidWorkAround )
     {
          *pDidWorkAround = needWorkaround;
     }

     return hr;
}

Requisitos

   
Plataforma de Destino Windows
Cabeçalho d3d11.h
Biblioteca D3D11.lib

Confira também

ID3D11DeviceContext

ID3D11Resource

Exemplo básico de holograma