A code example has been added below.
Basically what the code does is:
- Initialize SDL
- Create the SDL window
- Create the SDL renderer, with render-to-texture functionality enabled
- Create an empty SDL texture, which will be used as a render target
- In the render loop, set the render target texture as the current render target
- Clear it to some color (optionally)
- Render whatever object(s) that should be rendered
- Reset the render target back to the default render target
- Render the actual render target texture to the default render target (i.e the window/screen)
- Repeat process 5-9 every frame
Note that I haven’t done any error checking whatsoever in the code, to reduce code length, and normally this should always be made.
Code example
#include <SDL.h>
#define WINDOW_WIDTH (800)
#define WINDOW_HEIGHT (600)
#define RENDER_TARGET_WIDTH (320)
#define RENDER_TARGET_HEIGHT (240)
SDL_Window* pWindow = nullptr;
SDL_Renderer* pRenderer = nullptr;
SDL_Texture* pRenderTarget = nullptr;
SDL_Event Event;
bool Running = true;
void Update (void);
void Render (void);
int main(int argc, char *argv[])
{
SDL_Init(SDL_INIT_EVERYTHING);
pWindow = SDL_CreateWindow("SDL - render to texture", SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, WINDOW_WIDTH, WINDOW_HEIGHT, SDL_WINDOW_SHOWN);
// Note the SDL_RENDERER_TARGETTEXTURE flag, which enables render-to-texture functionality
pRenderer = SDL_CreateRenderer(pWindow, -1, SDL_RENDERER_ACCELERATED | SDL_RENDERER_TARGETTEXTURE);
/*
Create a blank texture which will be used as a render target
Note the SDL_TEXTUREACCESS_TARGET flag, which means the texture can be used as a render target
*/
pRenderTarget = SDL_CreateTexture(pRenderer, SDL_PIXELFORMAT_RGBA8888, SDL_TEXTUREACCESS_TARGET, RENDER_TARGET_WIDTH, RENDER_TARGET_HEIGHT);
// Set the texture as the current render target and clear the whole render target texture to black
SDL_SetRenderTarget(pRenderer, pRenderTarget);
SDL_SetRenderDrawColor(pRenderer, 0, 0, 0, 255);
SDL_RenderClear(pRenderer);
// And reset back to the default render target (i.e, the window/screen)
SDL_SetRenderTarget(pRenderer, nullptr);
while(Running)
{
Update();
Render();
}
SDL_DestroyTexture(pRenderTarget);
SDL_DestroyRenderer(pRenderer);
SDL_DestroyWindow(pWindow);
SDL_Quit();
return 0;
}
void Update(void)
{
HandleSDLEvents();
}
void Render(void)
{
// Set the render target texture as the current render target
SDL_SetRenderTarget(pRenderer, pRenderTarget);
/*
Note: everything from now on will be rendered to the render target texture,
until the render target are reset back to the default render target
*/
// Clear the render target texture to black
SDL_SetRenderDrawColor(pRenderer, 0, 0, 0, 255);
SDL_RenderClear(pRenderer);
// Render a red quad/square to the render target texture
SDL_SetRenderDrawColor(pRenderer, 255, 0, 0, 255);
const SDL_Rect Quad = {20, 20, 60, 60};
SDL_RenderFillRect(pRenderer, &Quad);
// Render a diagonal yellow line to the render target texture
SDL_SetRenderDrawColor(pRenderer, 255, 255, 0, 255);
SDL_RenderDrawLine(pRenderer, 20, 100, 180, 180);
// Reset the render target back to the default render target
SDL_SetRenderTarget(pRenderer, nullptr);
//////////////////////////////////////////////////////////////////////////
// Clear the default render target to white
SDL_SetRenderDrawColor(pRenderer, 255, 255, 255, 255);
SDL_RenderClear(pRenderer);
const SDL_Rect SrcQuad = { 0, 0, RENDER_TARGET_WIDTH, RENDER_TARGET_HEIGHT};
const SDL_Rect DstQuad = {50, 50, RENDER_TARGET_WIDTH, RENDER_TARGET_HEIGHT};
// Render the actual render target texture to the default render target
SDL_RenderCopy(pRenderer, pRenderTarget, &SrcQuad, &DstQuad);
// And update the window/screen
SDL_RenderPresent(pRenderer);
}