Displaying the same image multiple times in different positions on the screen is a common requirement in many applications, especially games.
In SDL2, we can achieve this by using the same source surface or texture and blitting it to different positions on the destination surface. Here's how you can do it:
#include <SDL.h>
#include <iostream>
#include <vector>
class Image {
public:
Image(const char* file) : surface{
SDL_LoadBMP(file)} {
if (!surface) {
std::cerr << "Failed to load image: " <<
SDL_GetError() << '\n';
}
}
void RenderMultiple(SDL_Surface* destSurface,
const std::vector<
SDL_Point>& positions) {
if (!surface || !destSurface) return;
SDL_Rect srcRect{
0, 0, surface->w, surface->h};
for (const auto& pos : positions) {
SDL_Rect destRect{
pos.x, pos.y, surface->w, surface->h};
SDL_BlitSurface(surface, &srcRect,
destSurface, &destRect);
}
}
~Image() {
if (surface) SDL_FreeSurface(surface);
}
private:
SDL_Surface* surface;
};
int main() {
SDL_Init(SDL_INIT_VIDEO);
SDL_Window* window =
SDL_CreateWindow("Multiple Images",
SDL_WINDOWPOS_UNDEFINED,
SDL_WINDOWPOS_UNDEFINED,
640, 480, 0);
SDL_Surface* screenSurface =
SDL_GetWindowSurface(window);
Image img{"example.bmp"};
// Define positions for multiple instances of the image
std::vector<SDL_Point> positions = {
{50, 50}, // Top-left
{500, 50}, // Top-right
{50, 350}, // Bottom-left
{500, 350}, // Bottom-right
{275, 200} // Center
};
img.RenderMultiple(screenSurface, positions);
SDL_UpdateWindowSurface(window);
SDL_Delay(3000); // Display for 3 seconds
SDL_DestroyWindow(window);
SDL_Quit();
return 0;
}
In this example, we've added a RenderMultiple()
method to our Image
class. This method takes a vector of SDL_Point
structures, each representing a position where we want to render the image.
The key part is the loop inside RenderMultiple()
:
for (const auto& pos : positions) {
SDL_Rect destRect{
pos.x, pos.y, surface->w, surface->h};
SDL_BlitSurface(
surface, &srcRect, destSurface, &destRect);
}
This loop iterates through all the positions and blits the image to each one.
In the main()
function, we define a vector of positions where we want our image to appear:
std::vector<SDL_Point> positions = {
{50, 50}, // Top-left
{500, 50}, // Top-right
{50, 350}, // Bottom-left
{500, 350}, // Bottom-right
{275, 200} // Center
};
Then we call RenderMultiple()
with these positions.
This approach is efficient because we only load the image once, but we can display it in multiple locations. It's particularly useful for things like:
Remember to handle potential errors, such as failing to load the image or create the window. Also, in a real application, you'd typically render in a loop rather than using SDL_Delay()
.
Answers to questions are automatically generated and may not have been reviewed.
Learn to precisely control image display using source and destination rectangles.