Skip to content

Instantly share code, notes, and snippets.

@adamjs
Created December 5, 2023 02:14
Show Gist options
  • Save adamjs/aa26d62ae791279e03259baac0352067 to your computer and use it in GitHub Desktop.
Save adamjs/aa26d62ae791279e03259baac0352067 to your computer and use it in GitHub Desktop.
D3D9 Texture Streaming

In Direct3D 9, you can upload pixels to a dynamic texture via the following:

  1. Create the Texture: In D3D9 you can create the texture using the CreateTexture method. Make sure to specify the D3DUSAGE_DYNAMIC flag in the Usage parameter.

    IDirect3DTexture9* pDynamicTexture = NULL;
    HRESULT hr = pDevice->CreateTexture(width, height, 1, D3DUSAGE_DYNAMIC, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &pDynamicTexture, NULL);

    This code uses the ARGB storage format but you may need to specify an alternative based on your needs.

  2. Lock the Texture: To update the texture you'll need to lock the pixels via the LockRect method. This gives you a pointer to the texture's memory that you can manipulate.

    D3DLOCKED_RECT lockedRect;
    hr = pDynamicTexture->LockRect(0, &lockedRect, NULL, D3DLOCK_DISCARD);
  3. Copy Pixel Data: Copy your pixel data to the locked rectangle's pBits pointer. The width of the texture's pixel data (the "pitch" or "rowspan") may be larger than requested, you should use the Pitch member to calculate the proper position of the pixel when copying.

    // pBits is the destination pointer
    BYTE* pBits = static_cast<BYTE*>(lockedRect.pBits);
    int pitch = lockedRect.Pitch;
    
    for (int y = 0; y < height; ++y) {
        for (int x = 0; x < width; ++x) {
            // Assuming 32-bit pixel format (ARGB)
            DWORD* pPixel = reinterpret_cast<DWORD*>(pBits + y * pitch + x * 4);
            *pPixel = // Set your pixel value here;
        }
    }

    *Note: you can also do a line-by-line source to destination copy via memcpy()

  4. Unlock the Texture: After updating the texture data, you need to unlock it to allow Direct3D to use the updated texture.

    hr = pDynamicTexture->UnlockRect(0);
  5. Use the Texture: Finally, use the dynamic texture in your rendering pipeline.

    pDevice->SetTexture(0, pDynamicTexture);
    // Perform rendering with the dynamic texture

Remember that frequent updates to dynamic textures can impact performance, so use them judiciously. Additionally, ensure that the format and size of the dynamic texture match your application's requirements.

Please note that the code provided here is a basic example, and you might need to adapt it based on your specific use case and requirements.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment