corregides cridades a SDL3 i migrat casi tot de int a float. Falta jail_shader

This commit is contained in:
2025-10-15 12:16:50 +02:00
parent 7c102e42cc
commit e4a08d2ec7
52 changed files with 879 additions and 823 deletions

View File

@@ -1,5 +1,6 @@
// IWYU pragma: no_include <bits/std_abs.h>
#include "surface.h"
#include <SDL3/SDL.h>
#include <algorithm> // Para min, max, copy_n, fill
@@ -177,32 +178,32 @@ void Surface::putPixel(int x, int y, Uint8 color) {
}
// Obtiene el color de un pixel de la surface_data
Uint8 Surface::getPixel(int x, int y) { return surface_data_->data.get()[x + y * surface_data_->width]; }
Uint8 Surface::getPixel(int x, int y) { return surface_data_->data.get()[x + y * static_cast<int>(surface_data_->width)]; }
// Dibuja un rectangulo relleno
void Surface::fillRect(const SDL_Rect* rect, Uint8 color) {
void Surface::fillRect(const SDL_FRect* rect, Uint8 color) {
// Limitar los valores del rectángulo al tamaño de la superficie
int x_start = std::max(0, rect->x);
int y_start = std::max(0, rect->y);
int x_end = std::min(rect->x + rect->w, static_cast<int>(surface_data_->width));
int y_end = std::min(rect->y + rect->h, static_cast<int>(surface_data_->height));
float x_start = std::max(0.0F, rect->x);
float y_start = std::max(0.0F, rect->y);
float x_end = std::min(rect->x + rect->w, surface_data_->width);
float y_end = std::min(rect->y + rect->h, surface_data_->height);
// Recorrer cada píxel dentro del rectángulo directamente
for (int y = y_start; y < y_end; ++y) {
for (int x = x_start; x < x_end; ++x) {
const int index = x + y * surface_data_->width;
surface_data_->data.get()[index] = color;
const int INDEX = x + y * surface_data_->width;
surface_data_->data.get()[INDEX] = color;
}
}
}
// Dibuja el borde de un rectangulo
void Surface::drawRectBorder(const SDL_Rect* rect, Uint8 color) {
void Surface::drawRectBorder(const SDL_FRect* rect, Uint8 color) {
// Limitar los valores del rectángulo al tamaño de la superficie
int x_start = std::max(0, rect->x);
int y_start = std::max(0, rect->y);
int x_end = std::min(rect->x + rect->w, static_cast<int>(surface_data_->width));
int y_end = std::min(rect->y + rect->h, static_cast<int>(surface_data_->height));
float x_start = std::max(0.0F, rect->x);
float y_start = std::max(0.0F, rect->y);
float x_end = std::min(rect->x + rect->w, surface_data_->width);
float y_end = std::min(rect->y + rect->h, surface_data_->height);
// Dibujar bordes horizontales
for (int x = x_start; x < x_end; ++x) {
@@ -218,31 +219,31 @@ void Surface::drawRectBorder(const SDL_Rect* rect, Uint8 color) {
// Dibujar bordes verticales
for (int y = y_start; y < y_end; ++y) {
// Borde izquierdo
const int left_index = x_start + y * surface_data_->width;
surface_data_->data.get()[left_index] = color;
const int LEFT_INDEX = x_start + y * surface_data_->width;
surface_data_->data.get()[LEFT_INDEX] = color;
// Borde derecho
const int right_index = (x_end - 1) + y * surface_data_->width;
surface_data_->data.get()[right_index] = color;
const int RIGHT_INDEX = (x_end - 1) + y * surface_data_->width;
surface_data_->data.get()[RIGHT_INDEX] = color;
}
}
// Dibuja una linea
void Surface::drawLine(int x1, int y1, int x2, int y2, Uint8 color) {
void Surface::drawLine(float x1, float y1, float x2, float y2, Uint8 color) {
// Calcula las diferencias
int dx = std::abs(x2 - x1);
int dy = std::abs(y2 - y1);
float dx = std::abs(x2 - x1);
float dy = std::abs(y2 - y1);
// Determina la dirección del incremento
int sx = (x1 < x2) ? 1 : -1;
int sy = (y1 < y2) ? 1 : -1;
float sx = (x1 < x2) ? 1 : -1;
float sy = (y1 < y2) ? 1 : -1;
int err = dx - dy;
float err = dx - dy;
while (true) {
// Asegúrate de no dibujar fuera de los límites de la superficie
if (x1 >= 0 && x1 < surface_data_->width && y1 >= 0 && y1 < surface_data_->height) {
surface_data_->data.get()[x1 + y1 * surface_data_->width] = color;
surface_data_->data.get()[static_cast<size_t>(x1 + y1 * surface_data_->width)] = color;
}
// Si alcanzamos el punto final, salimos
@@ -261,7 +262,7 @@ void Surface::drawLine(int x1, int y1, int x2, int y2, Uint8 color) {
}
}
void Surface::render(int dx, int dy, int sx, int sy, int w, int h) {
void Surface::render(float dx, float dy, float sx, float sy, float w, float h) {
auto surface_data = Screen::get()->getRendererSurface()->getSurfaceData();
// Limitar la región para evitar accesos fuera de rango en origen
@@ -280,9 +281,9 @@ void Surface::render(int dx, int dy, int sx, int sy, int w, int h) {
int src_x = sx + ix;
int src_y = sy + iy;
Uint8 color = surface_data_->data.get()[src_x + src_y * surface_data_->width];
Uint8 color = surface_data_->data.get()[static_cast<size_t>(src_x + src_y * surface_data_->width)];
if (color != transparent_color_) {
surface_data->data.get()[dest_x + dest_y * surface_data->width] = sub_palette_[color];
surface_data->data.get()[static_cast<size_t>(dest_x + dest_y * surface_data->width)] = sub_palette_[color];
}
}
}
@@ -290,14 +291,14 @@ void Surface::render(int dx, int dy, int sx, int sy, int w, int h) {
}
}
void Surface::render(int x, int y, SDL_Rect* srcRect, SDL_RendererFlip flip) {
void Surface::render(int x, int y, SDL_FRect* srcRect, SDL_FlipMode flip) {
auto surface_data_dest = Screen::get()->getRendererSurface()->getSurfaceData();
// Determina la región de origen (clip) a renderizar
int sx = (srcRect) ? srcRect->x : 0;
int sy = (srcRect) ? srcRect->y : 0;
int w = (srcRect) ? srcRect->w : surface_data_->width;
int h = (srcRect) ? srcRect->h : surface_data_->height;
float sx = (srcRect) ? srcRect->x : 0;
float sy = (srcRect) ? srcRect->y : 0;
float w = (srcRect) ? srcRect->w : surface_data_->width;
float h = (srcRect) ? srcRect->h : surface_data_->height;
// Limitar la región para evitar accesos fuera de rango en origen
w = std::min(w, surface_data_->width - sx);
@@ -323,7 +324,7 @@ void Surface::render(int x, int y, SDL_Rect* srcRect, SDL_RendererFlip flip) {
// Verificar que las coordenadas de destino están dentro de los límites
if (dest_x >= 0 && dest_x < surface_data_dest->width && dest_y >= 0 && dest_y < surface_data_dest->height) {
// Copia el píxel si no es transparente
Uint8 color = surface_data_->data.get()[src_x + src_y * surface_data_->width];
Uint8 color = surface_data_->data.get()[static_cast<size_t>(src_x + src_y * surface_data_->width)];
if (color != transparent_color_) {
surface_data_dest->data[dest_x + dest_y * surface_data_dest->width] = sub_palette_[color];
}
@@ -333,20 +334,20 @@ void Surface::render(int x, int y, SDL_Rect* srcRect, SDL_RendererFlip flip) {
}
// Copia una región de la superficie de origen a la de destino
void Surface::render(SDL_Rect* srcRect, SDL_Rect* dstRect, SDL_RendererFlip flip) {
void Surface::render(SDL_FRect* srcRect, SDL_FRect* dstRect, SDL_FlipMode flip) {
auto surface_data = Screen::get()->getRendererSurface()->getSurfaceData();
// Si srcRect es nullptr, tomar toda la superficie fuente
int sx = (srcRect) ? srcRect->x : 0;
int sy = (srcRect) ? srcRect->y : 0;
int sw = (srcRect) ? srcRect->w : surface_data_->width;
int sh = (srcRect) ? srcRect->h : surface_data_->height;
float sx = (srcRect) ? srcRect->x : 0;
float sy = (srcRect) ? srcRect->y : 0;
float sw = (srcRect) ? srcRect->w : surface_data_->width;
float sh = (srcRect) ? srcRect->h : surface_data_->height;
// Si dstRect es nullptr, asignar las mismas dimensiones que srcRect
int dx = (dstRect) ? dstRect->x : 0;
int dy = (dstRect) ? dstRect->y : 0;
int dw = (dstRect) ? dstRect->w : sw;
int dh = (dstRect) ? dstRect->h : sh;
float dx = (dstRect) ? dstRect->x : 0;
float dy = (dstRect) ? dstRect->y : 0;
float dw = (dstRect) ? dstRect->w : sw;
float dh = (dstRect) ? dstRect->h : sh;
// Asegurarse de que srcRect y dstRect tienen las mismas dimensiones
if (sw != dw || sh != dh) {
@@ -374,7 +375,7 @@ void Surface::render(SDL_Rect* srcRect, SDL_Rect* dstRect, SDL_RendererFlip flip
if (int dest_x = dx + ix; dest_x >= 0 && dest_x < surface_data->width) {
if (int dest_y = dy + iy; dest_y >= 0 && dest_y < surface_data->height) {
// Copiar el píxel si no es transparente
Uint8 color = surface_data_->data.get()[src_x + src_y * surface_data_->width];
Uint8 color = surface_data_->data.get()[static_cast<size_t>(src_x + src_y * surface_data_->width)];
if (color != transparent_color_) {
surface_data->data[dest_x + dest_y * surface_data->width] = sub_palette_[color];
}
@@ -385,14 +386,14 @@ void Surface::render(SDL_Rect* srcRect, SDL_Rect* dstRect, SDL_RendererFlip flip
}
// Copia una región de la SurfaceData de origen a la SurfaceData de destino reemplazando un color por otro
void Surface::renderWithColorReplace(int x, int y, Uint8 source_color, Uint8 target_color, SDL_Rect* srcRect, SDL_RendererFlip flip) {
void Surface::renderWithColorReplace(int x, int y, Uint8 source_color, Uint8 target_color, SDL_FRect* srcRect, SDL_FlipMode flip) {
auto surface_data = Screen::get()->getRendererSurface()->getSurfaceData();
// Determina la región de origen (clip) a renderizar
int sx = (srcRect) ? srcRect->x : 0;
int sy = (srcRect) ? srcRect->y : 0;
int w = (srcRect) ? srcRect->w : surface_data_->width;
int h = (srcRect) ? srcRect->h : surface_data_->height;
float sx = (srcRect) ? srcRect->x : 0;
float sy = (srcRect) ? srcRect->y : 0;
float w = (srcRect) ? srcRect->w : surface_data_->width;
float h = (srcRect) ? srcRect->h : surface_data_->height;
// Limitar la región para evitar accesos fuera de rango
w = std::min(w, surface_data_->width - sx);
@@ -415,7 +416,7 @@ void Surface::renderWithColorReplace(int x, int y, Uint8 source_color, Uint8 tar
}
// Copia el píxel si no es transparente
Uint8 color = surface_data_->data.get()[src_x + src_y * surface_data_->width];
Uint8 color = surface_data_->data.get()[static_cast<size_t>(src_x + src_y * surface_data_->width)];
if (color != transparent_color_) {
surface_data->data[dest_x + dest_y * surface_data->width] =
(color == source_color) ? target_color : color;
@@ -458,13 +459,13 @@ void Surface::copyToTexture(SDL_Renderer* renderer, SDL_Texture* texture) {
SDL_UnlockTexture(texture); // Desbloquea la textura
// Renderiza la textura en la pantalla completa
if (SDL_RenderCopy(renderer, texture, nullptr, nullptr) != 0) {
if (SDL_RenderTexture(renderer, texture, nullptr, nullptr) != 0) {
throw std::runtime_error("Failed to copy texture to renderer: " + std::string(SDL_GetError()));
}
}
// Vuelca la superficie a una textura
void Surface::copyToTexture(SDL_Renderer* renderer, SDL_Texture* texture, SDL_Rect* srcRect, SDL_Rect* destRect) {
void Surface::copyToTexture(SDL_Renderer* renderer, SDL_Texture* texture, SDL_FRect* srcRect, SDL_FRect* destRect) {
if (!renderer || !texture || !surface_data_) {
throw std::runtime_error("Renderer or texture is null.");
}
@@ -476,7 +477,16 @@ void Surface::copyToTexture(SDL_Renderer* renderer, SDL_Texture* texture, SDL_Re
Uint32* pixels = nullptr;
int pitch = 0;
if (SDL_LockTexture(texture, destRect, reinterpret_cast<void**>(&pixels), &pitch) != 0) {
SDL_Rect lockRect;
if (destRect) {
lockRect.x = static_cast<int>(destRect->x);
lockRect.y = static_cast<int>(destRect->y);
lockRect.w = static_cast<int>(destRect->w);
lockRect.h = static_cast<int>(destRect->h);
}
// Usa lockRect solo si destRect no es nulo
if (SDL_LockTexture(texture, destRect ? &lockRect : nullptr, reinterpret_cast<void**>(&pixels), &pitch) != 0) {
throw std::runtime_error("Failed to lock texture: " + std::string(SDL_GetError()));
}
@@ -494,7 +504,7 @@ void Surface::copyToTexture(SDL_Renderer* renderer, SDL_Texture* texture, SDL_Re
SDL_UnlockTexture(texture);
// Renderiza la textura con los rectángulos especificados
if (SDL_RenderCopy(renderer, texture, srcRect, destRect) != 0) {
if (SDL_RenderTexture(renderer, texture, srcRect, destRect) != 0) {
throw std::runtime_error("Failed to copy texture to renderer: " + std::string(SDL_GetError()));
}
}