feat: Add render mode options for image display in gsplash
This commit is contained in:
@@ -7,6 +7,7 @@
|
||||
#include <stdarg.h>
|
||||
#include <errno.h>
|
||||
#include <string.h>
|
||||
#include <math.h>
|
||||
|
||||
static void log_info(const char *fmt, ...)
|
||||
{
|
||||
@@ -30,15 +31,53 @@ static void log_error(const char *fmt, ...)
|
||||
fflush(stderr);
|
||||
}
|
||||
|
||||
typedef enum RenderMode
|
||||
{
|
||||
RENDER_STRETCH = 0,
|
||||
RENDER_CENTER,
|
||||
RENDER_CROP
|
||||
} RenderMode;
|
||||
|
||||
static RenderMode parse_render_mode(const char *value)
|
||||
{
|
||||
if (strcmp(value, "center") == 0)
|
||||
{
|
||||
return RENDER_CENTER;
|
||||
}
|
||||
if (strcmp(value, "crop") == 0)
|
||||
{
|
||||
return RENDER_CROP;
|
||||
}
|
||||
return RENDER_STRETCH;
|
||||
}
|
||||
|
||||
int main(int argc, char *argv[])
|
||||
{
|
||||
if (argc < 3)
|
||||
RenderMode render_mode = RENDER_CENTER;
|
||||
int arg_index = 1;
|
||||
|
||||
if (argc >= 3 && strncmp(argv[1], "--mode=", 7) == 0)
|
||||
{
|
||||
log_error("Usage: %s <image_path> <game_executable> [args...]", argv[0]);
|
||||
render_mode = parse_render_mode(argv[1] + 7);
|
||||
arg_index += 1;
|
||||
}
|
||||
else if (argc >= 4 && strcmp(argv[1], "-m") == 0)
|
||||
{
|
||||
render_mode = parse_render_mode(argv[2]);
|
||||
arg_index += 2;
|
||||
}
|
||||
|
||||
if (argc - arg_index < 2)
|
||||
{
|
||||
log_error("Usage: %s [--mode=stretch|center|crop] <image_path> <game_executable> [args...]", argv[0]);
|
||||
log_error(" %s -m stretch|center|crop <image_path> <game_executable> [args...]", argv[0]);
|
||||
return 1;
|
||||
}
|
||||
|
||||
log_info("Starting splash: image='%s', game='%s'", argv[1], argv[2]);
|
||||
const char *image_path = argv[arg_index];
|
||||
const char *game_path = argv[arg_index + 1];
|
||||
|
||||
log_info("Starting splash: image='%s', game='%s'", image_path, game_path);
|
||||
|
||||
// Initialize SDL2 Video subsystems
|
||||
if (SDL_Init(SDL_INIT_VIDEO) < 0)
|
||||
@@ -81,11 +120,11 @@ int main(int argc, char *argv[])
|
||||
{
|
||||
log_info("Renderer created (accelerated)");
|
||||
}
|
||||
SDL_Texture *texture = IMG_LoadTexture(renderer, argv[1]);
|
||||
SDL_Texture *texture = IMG_LoadTexture(renderer, image_path);
|
||||
|
||||
if (!texture)
|
||||
{
|
||||
log_error("Failed to load splash image '%s': %s; showing black screen", argv[1], IMG_GetError());
|
||||
log_error("Failed to load splash image '%s': %s; showing black screen", image_path, IMG_GetError());
|
||||
// Fallback: Clear to solid black if image file is broken
|
||||
SDL_SetRenderDrawColor(renderer, 0, 0, 0, 255);
|
||||
SDL_RenderClear(renderer);
|
||||
@@ -95,8 +134,48 @@ int main(int argc, char *argv[])
|
||||
{
|
||||
log_info("Splash image loaded");
|
||||
SDL_RenderClear(renderer);
|
||||
// Automatically scales your image to perfectly match the monitor aspect ratio
|
||||
SDL_RenderCopy(renderer, texture, NULL, NULL);
|
||||
|
||||
SDL_Rect dst_rect = {0, 0, 0, 0};
|
||||
int tex_w = 0;
|
||||
int tex_h = 0;
|
||||
int out_w = 0;
|
||||
int out_h = 0;
|
||||
|
||||
if (SDL_QueryTexture(texture, NULL, NULL, &tex_w, &tex_h) == 0 &&
|
||||
SDL_GetRendererOutputSize(renderer, &out_w, &out_h) == 0 &&
|
||||
tex_w > 0 && tex_h > 0 && out_w > 0 && out_h > 0)
|
||||
{
|
||||
if (render_mode == RENDER_CENTER)
|
||||
{
|
||||
float scale = fminf((float)out_w / (float)tex_w, (float)out_h / (float)tex_h);
|
||||
dst_rect.w = (int)(tex_w * scale);
|
||||
dst_rect.h = (int)(tex_h * scale);
|
||||
dst_rect.x = (out_w - dst_rect.w) / 2;
|
||||
dst_rect.y = (out_h - dst_rect.h) / 2;
|
||||
}
|
||||
else if (render_mode == RENDER_CROP)
|
||||
{
|
||||
float scale = fmaxf((float)out_w / (float)tex_w, (float)out_h / (float)tex_h);
|
||||
dst_rect.w = (int)(tex_w * scale);
|
||||
dst_rect.h = (int)(tex_h * scale);
|
||||
dst_rect.x = (out_w - dst_rect.w) / 2;
|
||||
dst_rect.y = (out_h - dst_rect.h) / 2;
|
||||
}
|
||||
else
|
||||
{
|
||||
dst_rect.w = out_w;
|
||||
dst_rect.h = out_h;
|
||||
}
|
||||
}
|
||||
|
||||
if (dst_rect.w > 0 && dst_rect.h > 0)
|
||||
{
|
||||
SDL_RenderCopy(renderer, texture, NULL, &dst_rect);
|
||||
}
|
||||
else
|
||||
{
|
||||
SDL_RenderCopy(renderer, texture, NULL, NULL);
|
||||
}
|
||||
SDL_RenderPresent(renderer);
|
||||
}
|
||||
|
||||
@@ -106,9 +185,9 @@ int main(int argc, char *argv[])
|
||||
if (pid == 0)
|
||||
{
|
||||
// Inside Child Process: Hand over execution directly to the game binary
|
||||
log_info("Execing game: %s", argv[2]);
|
||||
execvp(argv[2], &argv[2]);
|
||||
log_error("Failed to launch target game executable '%s': %s", argv[2], strerror(errno));
|
||||
log_info("Execing game: %s", game_path);
|
||||
execvp(game_path, &argv[arg_index + 1]);
|
||||
log_error("Failed to launch target game executable '%s': %s", game_path, strerror(errno));
|
||||
_exit(1);
|
||||
}
|
||||
else if (pid < 0)
|
||||
|
||||
Reference in New Issue
Block a user