Compare commits
3 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| c689507982 | |||
| 417643018f | |||
| 2ed7316948 |
143
CHANGELOG.md
Normal file
143
CHANGELOG.md
Normal file
@@ -0,0 +1,143 @@
|
||||
# Changelog
|
||||
|
||||
All notable changes to JailDoctor's Dilemma are documented here.
|
||||
|
||||
---
|
||||
|
||||
## [v1.11] - 2026-03-31
|
||||
|
||||
### Novedades
|
||||
- **PaletteManager:** refactorización de `Screen`, responsabilidades de gestión de paletas extraídas a clase propia
|
||||
- **Consola 2.1:** la consola puede cambiar de paleta por nombre (`Screen` devuelve lista de paletas)
|
||||
- **Zoom configurable:** `Screen` permite establecer el nivel de zoom directamente desde consola
|
||||
- **Autocompletar en consola:** autocompletado de comandos con Tab (incluyendo soporte para armadura de lagarto)
|
||||
- Generación automática de tabla de tab-completions en la consola
|
||||
|
||||
### Correcciones
|
||||
- Fix: al entrar a GAME con la consola abierta, el jugador no tenía los inputs deshabilitados
|
||||
- Fix: al hacer restart con la música del attract mode sonando, la música no paraba al ir al logo
|
||||
- Fix: en modo debug, protección para que el jugador no caiga infinitamente si sale de pantalla
|
||||
- Corregido el case en algunas respuestas de la consola
|
||||
- Corregido Makefile
|
||||
|
||||
---
|
||||
|
||||
## [v1.10] - 2026-03-30
|
||||
|
||||
### Novedades
|
||||
- **Consola 2.0:** rediseño completo de la consola de desarrollador
|
||||
- Efecto typewriter al mostrar texto
|
||||
- Separación de líneas automática
|
||||
- Cambio de skin
|
||||
- Historial y navegación mejorada
|
||||
- Comandos para cheats, control de escena, debug, audio y shaders
|
||||
- Teclas de función operativas con la consola abierta
|
||||
- Límite de caracteres ampliado
|
||||
- La consola ya no pausa al jugador
|
||||
- Reorganización del sistema de comandos y aliases (`show info`, `hide info`, etc.)
|
||||
- **RenderInfo:** nueva clase con animación para mostrar info de renderizado en pantalla
|
||||
- **Soporte multi-shader:** comandos y teclas para manejar el nuevo diseño de shaders (SPIRV/SPIR-V)
|
||||
- **Modo kiosko:** defaults y restricciones de comandos para modo kiosk
|
||||
- **Supersampling Lanczos:** implementación de escalado Lanczos en el supersampling
|
||||
- **Driver GPU configurable:** permite elegir driver de GPU o ninguno desde consola
|
||||
- Cheats accesibles desde la consola
|
||||
- Cambio y reinicio de escena desde la consola
|
||||
- Posición e habitación inicial de debug configurables desde consola y fichero
|
||||
- `Debug` carga posición e habitación inicial desde fichero
|
||||
- Comandos de audio configurables desde consola
|
||||
- Renderizado del dispositivo GPU en info_debug
|
||||
- `Screen` optimizado (`textureToRenderer()`)
|
||||
- Eliminado soporte para argumentos de línea de comandos
|
||||
- Eliminado `Options::console`
|
||||
- Help de consola organizado
|
||||
|
||||
### Correcciones
|
||||
- Fix: vsync off no funcionaba en Wayland
|
||||
- Fix: en TITLE, la consola no bloqueaba la pulsación del 1 al 4 y entraba a opciones
|
||||
- Fix: dos logs de consola con formato incorrecto
|
||||
- Fix: lógica para abrir y entrar a la jail (ahora usa número de habitación, no nombre)
|
||||
- Corregido `compile_spirv.cmake` y la `system_folder` para shaders
|
||||
- Corregido carácter de caret que se había perdido
|
||||
- Eliminados acentos en títulos de habitaciones que causaban problemas con fuentes
|
||||
- Revisadas y corregidas traducciones
|
||||
- Corregidos ficheros `.fnt`
|
||||
- Corrección en `Screen` para `std::setprecision()` (faltaba `#include <iomanip>`)
|
||||
|
||||
---
|
||||
|
||||
## [v1.09] - 2025-03-01
|
||||
|
||||
### Novedades
|
||||
- **Refactorización a singletons:** `Screen`, `Input`, `Audio`, `Resource::Cache`, `Resource::List`, `Director`, `Cheevos`, `Debug` convertidos a singletons thread-safe
|
||||
- **Smart pointers:** uso de `std::shared_ptr` y `std::unique_ptr` para gestión de recursos y sprites
|
||||
- **Surfaces 8-bit indexadas:** nuevo sistema de renderizado con color indexado y paletas intercambiables
|
||||
- **Sistema de notificaciones rediseñado:** nuevo engine de notificaciones con control de offset
|
||||
- **Modos de vídeo mejorados:** la ventana mantiene posición al cambiar tamaño o activar borde; puede crecer según el escritorio
|
||||
- **ItemTracker:** nuevo singleton para rastrear ítems recogidos
|
||||
- **globalEvents:** nuevo sistema de eventos globales SDL
|
||||
- **Barra de progreso en carga de recursos** (actualización cada 5 ítems para mayor rendimiento con vsync)
|
||||
- **Métodos show/hide ventana:** métodos para mostrar u ocultar la ventana
|
||||
- Afinada la clase `Options`
|
||||
- Actualizada a la última versión de `jail_audio`
|
||||
- Implementados shaders
|
||||
- Nueva tipografía añadida
|
||||
- Parametros de ficheros `.ani` migrados a snake_case
|
||||
- Música de Title y attract mode restaurada
|
||||
- Eliminado sistema online completo
|
||||
|
||||
### Correcciones
|
||||
- Fix: notificaciones ya no ensucian la pantalla de carga
|
||||
- Fix: no pintaba el efecto de carga del borde en `LoadingScreen`
|
||||
- Fix: bug con el puntero a `ScoreboardData`
|
||||
- Fix: carga de opciones y recursos corregida
|
||||
- Eliminados acentos problemáticos
|
||||
|
||||
---
|
||||
|
||||
## [v1.08] - 2024-02-22
|
||||
|
||||
### Novedades
|
||||
- Posibilidad de saltar la pantalla de carga ya completada desde el menú de título
|
||||
- El `gamestate_title` puede empezar en diferentes estados
|
||||
- Pantalla de carga con fade de paleta
|
||||
- GIF loader: dibujado correcto de GIFs en pantalla
|
||||
- Añadida `paleta.cpp`/`.h` y `gif.c`
|
||||
|
||||
### Correcciones
|
||||
- Corregido bug en el fade de paleta (el canal azul no se propagaba)
|
||||
- Arreglada la separación entre el título y el fade
|
||||
- Online deshabilitado por defecto al crear el fichero de configuración
|
||||
- Tiempo de la pantalla de carga aumentado
|
||||
|
||||
---
|
||||
|
||||
## [v1.07] - 2022-12-02
|
||||
|
||||
### Novedades
|
||||
- El nombre de la habitación se pinta a partir de una textura
|
||||
- Añadido Batman a FEEL THE HEAT
|
||||
- Cielo de la Jail actualizado
|
||||
- Retocada la pantalla de título
|
||||
- Sprite de PACO modificado
|
||||
- Nombre del enemigo diskette cambiado a floppy
|
||||
- Cambios cosméticos en algunas habitaciones (BE CAREFUL WITH THE FUSE renombrado)
|
||||
- El color de fondo de la habitación se pinta en la textura del mapa
|
||||
- Optimizaciones en intro y title
|
||||
- Preparación para compatibilidad con consolas
|
||||
- Actualizado `jail_audio` a la última versión
|
||||
- Eliminados la mayor parte de accesos a `vector::at()`
|
||||
|
||||
### Correcciones
|
||||
- Corregido bug: en la jail se rellenaban las vidas mientras estaba activa la pausa
|
||||
- Corregido memory leak en `texture.cpp`
|
||||
- Corregido bug en apertura de la Jail
|
||||
|
||||
---
|
||||
|
||||
## [v1.0] - 2022-11-13
|
||||
|
||||
Versión de lanzamiento inicial.
|
||||
|
||||
---
|
||||
|
||||
*El formato de este changelog sigue [Keep a Changelog](https://keepachangelog.com/).*
|
||||
@@ -32,7 +32,7 @@ assets:
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/zx-spectrum-adjusted.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/zxarne-5-2.pal
|
||||
path: ${PREFIX}/data/palette/zxarne-5.2.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/black-and-white.pal
|
||||
- type: PALETTE
|
||||
@@ -46,15 +46,33 @@ assets:
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/pico-8.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/sweetie-16.pal
|
||||
path: ${PREFIX}/data/palette/sweetie.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/island-joy-16.pal
|
||||
path: ${PREFIX}/data/palette/island-joy.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/lost-century.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/na16.pal
|
||||
path: ${PREFIX}/data/palette/na.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/steam-lords.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/winds-seed-pc98.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/psychic-fibre.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/shido-cyberneon.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/darkseed.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/antiquity.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/bubblegum.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/vanilla-milkshake.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/aged-terracotta.pal
|
||||
- type: PALETTE
|
||||
path: ${PREFIX}/data/palette/h16da.pal
|
||||
|
||||
# LOCALE
|
||||
locale:
|
||||
|
||||
19
data/palette/aged-terracotta.pal
Normal file
19
data/palette/aged-terracotta.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
52 49 40
|
||||
80 73 57
|
||||
92 104 82
|
||||
108 116 76
|
||||
125 130 73
|
||||
163 158 85
|
||||
202 181 103
|
||||
119 63 53
|
||||
132 86 64
|
||||
160 119 84
|
||||
188 153 120
|
||||
214 193 157
|
||||
234 220 193
|
||||
247 240 221
|
||||
255 251 237
|
||||
255 255 255
|
||||
19
data/palette/antiquity.pal
Normal file
19
data/palette/antiquity.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
32 32 32
|
||||
45 33 30
|
||||
69 41 35
|
||||
109 61 41
|
||||
177 107 74
|
||||
232 159 110
|
||||
232 190 130
|
||||
93 117 87
|
||||
142 146 87
|
||||
112 123 136
|
||||
138 167 172
|
||||
229 93 77
|
||||
241 134 108
|
||||
210 103 48
|
||||
222 154 40
|
||||
232 216 165
|
||||
19
data/palette/bubblegum.pal
Normal file
19
data/palette/bubblegum.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
67 0 103
|
||||
22 23 26
|
||||
127 6 34
|
||||
0 40 89
|
||||
148 33 106
|
||||
35 73 117
|
||||
214 36 17
|
||||
255 38 116
|
||||
0 120 153
|
||||
255 132 38
|
||||
255 128 164
|
||||
104 174 212
|
||||
16 210 117
|
||||
255 209 0
|
||||
191 255 60
|
||||
250 253 255
|
||||
19
data/palette/darkseed.pal
Normal file
19
data/palette/darkseed.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
0 0 0
|
||||
0 20 24
|
||||
0 32 36
|
||||
0 44 56
|
||||
20 52 68
|
||||
68 52 68
|
||||
88 60 72
|
||||
108 76 68
|
||||
128 96 88
|
||||
108 112 108
|
||||
136 128 120
|
||||
164 148 132
|
||||
196 172 156
|
||||
216 176 168
|
||||
236 212 208
|
||||
252 252 252
|
||||
19
data/palette/h16da.pal
Normal file
19
data/palette/h16da.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
31 32 37
|
||||
46 51 77
|
||||
76 82 116
|
||||
124 143 178
|
||||
128 77 83
|
||||
191 125 133
|
||||
114 51 76
|
||||
192 165 169
|
||||
82 103 93
|
||||
108 154 154
|
||||
108 154 154
|
||||
226 217 228
|
||||
243 200 147
|
||||
229 152 125
|
||||
192 165 169
|
||||
226 217 228
|
||||
@@ -1,19 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
255 255 255
|
||||
109 247 193
|
||||
17 173 193
|
||||
96 108 129
|
||||
57 52 87
|
||||
30 136 117
|
||||
91 179 97
|
||||
161 229 90
|
||||
247 228 118
|
||||
249 146 82
|
||||
203 77 104
|
||||
106 55 113
|
||||
201 36 100
|
||||
203 77 104
|
||||
96 108 129
|
||||
30 136 117
|
||||
17 173 193
|
||||
155 156 130
|
||||
91 179 97
|
||||
249 146 82
|
||||
244 140 182
|
||||
247 182 158
|
||||
155 156 130
|
||||
161 229 90
|
||||
109 247 193
|
||||
247 228 118
|
||||
255 255 255
|
||||
@@ -1,19 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
209 177 135
|
||||
199 123 88
|
||||
174 93 64
|
||||
121 68 74
|
||||
75 61 68
|
||||
186 145 88
|
||||
146 116 65
|
||||
77 69 57
|
||||
119 116 59
|
||||
179 165 85
|
||||
210 201 165
|
||||
140 171 161
|
||||
75 114 110
|
||||
87 72 82
|
||||
121 68 74
|
||||
75 114 110
|
||||
174 93 64
|
||||
119 116 59
|
||||
146 116 65
|
||||
132 120 117
|
||||
199 123 88
|
||||
186 145 88
|
||||
171 155 142
|
||||
179 165 85
|
||||
140 171 161
|
||||
209 177 135
|
||||
210 201 165
|
||||
|
||||
@@ -1,19 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
140 143 174
|
||||
88 69 99
|
||||
62 33 55
|
||||
154 99 72
|
||||
215 155 125
|
||||
245 237 186
|
||||
192 199 65
|
||||
100 125 52
|
||||
228 148 58
|
||||
157 48 59
|
||||
210 100 113
|
||||
112 55 127
|
||||
126 196 193
|
||||
52 133 157
|
||||
23 67 75
|
||||
31 14 28
|
||||
62 33 55
|
||||
23 67 75
|
||||
157 48 59
|
||||
112 55 127
|
||||
88 69 99
|
||||
154 99 72
|
||||
100 125 52
|
||||
52 133 157
|
||||
210 100 113
|
||||
140 143 174
|
||||
228 148 58
|
||||
215 155 125
|
||||
126 196 193
|
||||
192 199 65
|
||||
245 237 186
|
||||
@@ -3,17 +3,17 @@ JASC-PAL
|
||||
16
|
||||
0 0 0
|
||||
29 43 83
|
||||
126 37 83
|
||||
0 135 81
|
||||
171 82 54
|
||||
95 87 79
|
||||
194 195 199
|
||||
255 241 232
|
||||
255 0 77
|
||||
255 163 0
|
||||
255 236 39
|
||||
0 228 54
|
||||
41 173 255
|
||||
131 118 156
|
||||
255 0 77
|
||||
171 82 54
|
||||
255 119 168
|
||||
194 195 199
|
||||
0 228 54
|
||||
0 135 81
|
||||
95 87 79
|
||||
255 241 232
|
||||
255 236 39
|
||||
255 163 0
|
||||
255 204 170
|
||||
126 37 83
|
||||
|
||||
19
data/palette/psychic-fibre.pal
Normal file
19
data/palette/psychic-fibre.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
10 8 25
|
||||
49 50 67
|
||||
69 59 70
|
||||
87 84 117
|
||||
130 105 128
|
||||
164 111 114
|
||||
185 115 113
|
||||
205 95 105
|
||||
229 76 81
|
||||
201 55 73
|
||||
144 161 168
|
||||
140 147 137
|
||||
195 150 145
|
||||
236 151 134
|
||||
235 171 145
|
||||
219 182 167
|
||||
@@ -2,18 +2,18 @@ JASC-PAL
|
||||
0100
|
||||
16
|
||||
17 17 37
|
||||
82 75 109
|
||||
176 201 196
|
||||
255 252 241
|
||||
36 34 114
|
||||
52 112 190
|
||||
159 32 98
|
||||
255 94 57
|
||||
150 58 191
|
||||
255 94 57
|
||||
159 32 98
|
||||
255 105 246
|
||||
176 201 196
|
||||
44 126 75
|
||||
160 195 95
|
||||
67 152 196
|
||||
147 255 229
|
||||
210 133 55
|
||||
254 245 107
|
||||
255 252 241
|
||||
82 75 109
|
||||
|
||||
@@ -2,18 +2,18 @@ JASC-PAL
|
||||
0100
|
||||
16
|
||||
15 11 56
|
||||
97 106 130
|
||||
173 180 183
|
||||
249 255 236
|
||||
122 87 22
|
||||
40 19 160
|
||||
74 107 255
|
||||
160 35 17
|
||||
237 23 95
|
||||
115 16 147
|
||||
238 20 181
|
||||
115 16 147
|
||||
39 139 97
|
||||
157 255 38
|
||||
27 105 167
|
||||
71 233 223
|
||||
122 87 22
|
||||
27 105 167
|
||||
247 229 77
|
||||
173 180 183
|
||||
249 255 236
|
||||
97 106 130
|
||||
|
||||
19
data/palette/shido-cyberneon.pal
Normal file
19
data/palette/shido-cyberneon.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
0 3 60
|
||||
0 82 96
|
||||
0 56 132
|
||||
42 46 121
|
||||
255 0 78
|
||||
177 5 133
|
||||
172 41 206
|
||||
255 92 255
|
||||
10 255 82
|
||||
0 157 74
|
||||
0 247 255
|
||||
0 138 197
|
||||
78 110 168
|
||||
255 255 255
|
||||
173 212 250
|
||||
96 0 136
|
||||
@@ -1,19 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
33 59 37
|
||||
58 96 74
|
||||
79 119 84
|
||||
161 159 124
|
||||
119 116 79
|
||||
119 92 79
|
||||
96 59 58
|
||||
59 33 55
|
||||
23 14 25
|
||||
47 33 59
|
||||
59 33 55
|
||||
33 59 37
|
||||
67 58 96
|
||||
96 59 58
|
||||
79 82 119
|
||||
58 96 74
|
||||
119 92 79
|
||||
79 119 84
|
||||
101 115 140
|
||||
119 116 79
|
||||
124 148 161
|
||||
161 159 124
|
||||
160 185 186
|
||||
192 209 204
|
||||
|
||||
@@ -1,19 +0,0 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
26 28 44
|
||||
93 39 93
|
||||
177 62 83
|
||||
239 125 87
|
||||
255 205 117
|
||||
167 240 112
|
||||
56 183 100
|
||||
37 113 121
|
||||
41 54 111
|
||||
59 93 201
|
||||
65 166 246
|
||||
115 239 247
|
||||
244 244 244
|
||||
148 176 194
|
||||
86 108 134
|
||||
51 60 87
|
||||
@@ -2,18 +2,18 @@ JASC-PAL
|
||||
0100
|
||||
16
|
||||
26 28 44
|
||||
41 54 111
|
||||
51 60 87
|
||||
86 108 134
|
||||
59 93 201
|
||||
37 113 121
|
||||
93 39 93
|
||||
41 54 111
|
||||
177 62 83
|
||||
239 125 87
|
||||
93 39 93
|
||||
148 176 194
|
||||
56 183 100
|
||||
167 240 112
|
||||
37 113 121
|
||||
65 166 246
|
||||
115 239 247
|
||||
239 125 87
|
||||
255 205 117
|
||||
148 176 194
|
||||
167 240 112
|
||||
244 244 244
|
||||
86 108 134
|
||||
19
data/palette/vanilla-milkshake.pal
Normal file
19
data/palette/vanilla-milkshake.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
40 40 46
|
||||
108 86 113
|
||||
217 200 191
|
||||
249 130 132
|
||||
176 169 228
|
||||
172 204 228
|
||||
179 227 218
|
||||
254 170 228
|
||||
135 168 137
|
||||
176 235 147
|
||||
233 245 157
|
||||
255 230 198
|
||||
222 163 139
|
||||
255 195 132
|
||||
255 247 160
|
||||
255 247 228
|
||||
19
data/palette/winds-seed-pc98.pal
Normal file
19
data/palette/winds-seed-pc98.pal
Normal file
@@ -0,0 +1,19 @@
|
||||
JASC-PAL
|
||||
0100
|
||||
16
|
||||
0 0 0
|
||||
50 1 50
|
||||
50 50 171
|
||||
35 103 239
|
||||
254 1 69
|
||||
119 70 2
|
||||
118 50 118
|
||||
239 152 152
|
||||
1 137 84
|
||||
1 186 152
|
||||
152 186 220
|
||||
253 253 253
|
||||
254 239 69
|
||||
186 118 84
|
||||
254 205 205
|
||||
84 1 103
|
||||
@@ -119,12 +119,12 @@ namespace GlobalInputs {
|
||||
|
||||
void handleNextPalette() {
|
||||
Screen::get()->nextPalette();
|
||||
Notifier::get()->show({Locale::get()->get("ui.palette") + " " + Options::video.palette}); // NOLINT(readability-static-accessed-through-instance)
|
||||
Notifier::get()->show({Locale::get()->get("ui.palette") + " " + toUpper(Screen::get()->getPalettePrettyName())}); // NOLINT(readability-static-accessed-through-instance)
|
||||
}
|
||||
|
||||
void handlePreviousPalette() {
|
||||
Screen::get()->previousPalette();
|
||||
Notifier::get()->show({Locale::get()->get("ui.palette") + " " + Options::video.palette}); // NOLINT(readability-static-accessed-through-instance)
|
||||
Notifier::get()->show({Locale::get()->get("ui.palette") + " " + toUpper(Screen::get()->getPalettePrettyName())}); // NOLINT(readability-static-accessed-through-instance)
|
||||
}
|
||||
|
||||
void handleToggleIntegerScale() {
|
||||
|
||||
@@ -6,6 +6,7 @@
|
||||
|
||||
#include "core/rendering/surface.hpp"
|
||||
#include "core/resources/resource_cache.hpp"
|
||||
#include "game/defaults.hpp"
|
||||
#include "game/options.hpp"
|
||||
#include "utils/utils.hpp"
|
||||
|
||||
@@ -44,9 +45,9 @@ void PaletteManager::previous() {
|
||||
}
|
||||
|
||||
auto PaletteManager::setByName(const std::string& name) -> bool {
|
||||
const std::string upper_name = toUpper(name + ".pal");
|
||||
const std::string lower_name = toLower(name + ".pal");
|
||||
for (size_t i = 0; i < palettes_.size(); ++i) {
|
||||
if (toUpper(palettes_[i]) == upper_name) {
|
||||
if (toLower(palettes_[i]) == lower_name) {
|
||||
current_ = i;
|
||||
apply();
|
||||
return true;
|
||||
@@ -62,7 +63,7 @@ auto PaletteManager::getNames() const -> std::vector<std::string> {
|
||||
std::string name = p;
|
||||
const size_t pos = name.find(".pal");
|
||||
if (pos != std::string::npos) { name.erase(pos, 4); }
|
||||
std::ranges::transform(name, name.begin(), ::toupper);
|
||||
std::ranges::transform(name, name.begin(), ::tolower);
|
||||
names.push_back(std::move(name));
|
||||
}
|
||||
return names;
|
||||
@@ -72,7 +73,13 @@ auto PaletteManager::getCurrentName() const -> std::string {
|
||||
std::string name = palettes_.at(current_);
|
||||
const size_t pos = name.find(".pal");
|
||||
if (pos != std::string::npos) { name.erase(pos, 4); }
|
||||
std::ranges::transform(name, name.begin(), ::toupper);
|
||||
std::ranges::transform(name, name.begin(), ::tolower);
|
||||
return name;
|
||||
}
|
||||
|
||||
auto PaletteManager::getPrettyName() const -> std::string {
|
||||
std::string name = getCurrentName();
|
||||
std::ranges::replace(name, '-', ' ');
|
||||
return name;
|
||||
}
|
||||
|
||||
@@ -88,9 +95,16 @@ void PaletteManager::apply() {
|
||||
}
|
||||
|
||||
auto PaletteManager::findIndex(const std::string& name) const -> size_t {
|
||||
const std::string upper_name = toUpper(name + ".pal");
|
||||
const std::string lower_name = toLower(name + ".pal");
|
||||
for (size_t i = 0; i < palettes_.size(); ++i) {
|
||||
if (toUpper(getFileName(palettes_[i])) == upper_name) {
|
||||
if (toLower(getFileName(palettes_[i])) == lower_name) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
// Fallback: buscar la paleta por defecto
|
||||
const std::string default_name = toLower(std::string(Defaults::Video::PALETTE_NAME) + ".pal");
|
||||
for (size_t i = 0; i < palettes_.size(); ++i) {
|
||||
if (toLower(getFileName(palettes_[i])) == default_name) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -21,8 +21,9 @@ class PaletteManager {
|
||||
void next(); // Avanza a la siguiente paleta
|
||||
void previous(); // Retrocede a la paleta anterior
|
||||
auto setByName(const std::string& name) -> bool; // Cambia a paleta por nombre; false si no existe
|
||||
[[nodiscard]] auto getNames() const -> std::vector<std::string>; // Nombres disponibles (mayúsculas, sin .pal)
|
||||
[[nodiscard]] auto getCurrentName() const -> std::string; // Nombre de la paleta actual (mayúsculas, sin .pal)
|
||||
[[nodiscard]] auto getNames() const -> std::vector<std::string>; // Nombres disponibles (minúsculas, sin .pal)
|
||||
[[nodiscard]] auto getCurrentName() const -> std::string; // Nombre de la paleta actual (minúsculas, sin .pal)
|
||||
[[nodiscard]] auto getPrettyName() const -> std::string; // Nombre actual con guiones sustituidos por espacios
|
||||
|
||||
private:
|
||||
void apply(); // Aplica la paleta actual a ambas surfaces
|
||||
|
||||
@@ -446,8 +446,9 @@ void Screen::renderOverlays() {
|
||||
// Cambia a una paleta por nombre (case-insensitive); devuelve false si no existe
|
||||
auto Screen::setPaletteByName(const std::string& name) -> bool { return palette_manager_->setByName(name); }
|
||||
|
||||
// Devuelve los nombres de paletas disponibles (mayúsculas, sin extensión .pal)
|
||||
// Devuelve los nombres de paletas disponibles (minúsculas, sin extensión .pal)
|
||||
auto Screen::getPaletteNames() const -> std::vector<std::string> { return palette_manager_->getNames(); }
|
||||
auto Screen::getPalettePrettyName() const -> std::string { return palette_manager_->getPrettyName(); }
|
||||
|
||||
// Limpia la game_surface_
|
||||
void Screen::clearSurface(Uint8 index) { game_surface_->clear(index); }
|
||||
|
||||
@@ -57,7 +57,8 @@ class Screen {
|
||||
void nextPalette(); // Cambia a la siguiente paleta
|
||||
void previousPalette(); // Cambia a la paleta anterior
|
||||
auto setPaletteByName(const std::string& name) -> bool; // Cambia a paleta por nombre; false si no existe
|
||||
[[nodiscard]] auto getPaletteNames() const -> std::vector<std::string>; // Nombres disponibles (mayúsculas, sin .pal)
|
||||
[[nodiscard]] auto getPaletteNames() const -> std::vector<std::string>; // Nombres disponibles (minúsculas, sin .pal)
|
||||
[[nodiscard]] auto getPalettePrettyName() const -> std::string; // Nombre actual con guiones sustituidos por espacios
|
||||
void toggleShaders(); // Activa/desactiva todos los shaders respetando current_shader
|
||||
void toggleSupersampling(); // Activa/desactiva el supersampling global
|
||||
void reloadPostFX(); // Recarga el shader del preset actual sin toggle
|
||||
|
||||
@@ -175,12 +175,12 @@ void Surface::fillRect(const SDL_FRect* rect, Uint8 color) { // NOLINT(readabil
|
||||
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;
|
||||
}
|
||||
// Rellenar fila a fila con memset (memoria contigua por fila)
|
||||
Uint8* data_ptr = surface_data_->data.get();
|
||||
const int surf_width = static_cast<int>(surface_data_->width);
|
||||
const int row_width = static_cast<int>(x_end) - static_cast<int>(x_start);
|
||||
for (int y = static_cast<int>(y_start); y < static_cast<int>(y_end); ++y) {
|
||||
std::memset(data_ptr + (y * surf_width) + static_cast<int>(x_start), color, row_width);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -192,16 +192,12 @@ void Surface::drawRectBorder(const SDL_FRect* rect, Uint8 color) { // NOLINT(re
|
||||
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) {
|
||||
// Borde superior
|
||||
const int TOP_INDEX = x + (y_start * surface_data_->width);
|
||||
surface_data_->data.get()[TOP_INDEX] = color;
|
||||
|
||||
// Borde inferior
|
||||
const int BOTTOM_INDEX = x + ((y_end - 1) * surface_data_->width);
|
||||
surface_data_->data.get()[BOTTOM_INDEX] = color;
|
||||
}
|
||||
// Dibujar bordes horizontales con memset (líneas contiguas en memoria)
|
||||
Uint8* data_ptr = surface_data_->data.get();
|
||||
const int surf_width = static_cast<int>(surface_data_->width);
|
||||
const int row_width = static_cast<int>(x_end) - static_cast<int>(x_start);
|
||||
std::memset(data_ptr + (static_cast<int>(y_start) * surf_width) + static_cast<int>(x_start), color, row_width);
|
||||
std::memset(data_ptr + ((static_cast<int>(y_end) - 1) * surf_width) + static_cast<int>(x_start), color, row_width);
|
||||
|
||||
// Dibujar bordes verticales
|
||||
for (int y = y_start; y < y_end; ++y) {
|
||||
@@ -261,6 +257,8 @@ void Surface::render(float dx, float dy, float sx, float sy, float w, float h) {
|
||||
w = std::min(w, surface_data->width - dx);
|
||||
h = std::min(h, surface_data->height - dy);
|
||||
|
||||
const Uint8* src_ptr = surface_data_->data.get();
|
||||
Uint8* dst_ptr = surface_data->data.get();
|
||||
for (int iy = 0; iy < h; ++iy) {
|
||||
for (int ix = 0; ix < w; ++ix) {
|
||||
// Verificar que las coordenadas de destino están dentro de los límites
|
||||
@@ -269,9 +267,9 @@ void Surface::render(float dx, float dy, float sx, float sy, float w, float h) {
|
||||
int src_x = sx + ix;
|
||||
int src_y = sy + iy;
|
||||
|
||||
Uint8 color = surface_data_->data.get()[static_cast<size_t>(src_x + (src_y * surface_data_->width))];
|
||||
Uint8 color = src_ptr[static_cast<size_t>(src_x + (src_y * surface_data_->width))];
|
||||
if (color != static_cast<Uint8>(transparent_color_)) {
|
||||
surface_data->data.get()[static_cast<size_t>(dest_x + (dest_y * surface_data->width))] = sub_palette_[color];
|
||||
dst_ptr[static_cast<size_t>(dest_x + (dest_y * surface_data->width))] = sub_palette_[color];
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -299,6 +297,8 @@ void Surface::render(int x, int y, SDL_FRect* src_rect, SDL_FlipMode flip) { //
|
||||
h = std::min(h, surface_data_dest->height - y);
|
||||
|
||||
// Renderiza píxel por píxel aplicando el flip si es necesario
|
||||
const Uint8* src_ptr = surface_data_->data.get();
|
||||
Uint8* dst_ptr = surface_data_dest->data.get();
|
||||
for (int iy = 0; iy < h; ++iy) {
|
||||
for (int ix = 0; ix < w; ++ix) {
|
||||
// Coordenadas de origen
|
||||
@@ -312,9 +312,9 @@ void Surface::render(int x, int y, SDL_FRect* src_rect, SDL_FlipMode 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()[static_cast<size_t>(src_x + (src_y * surface_data_->width))];
|
||||
Uint8 color = src_ptr[static_cast<size_t>(src_x + (src_y * surface_data_->width))];
|
||||
if (color != static_cast<Uint8>(transparent_color_)) {
|
||||
surface_data_dest->data[dest_x + (dest_y * surface_data_dest->width)] = sub_palette_[color];
|
||||
dst_ptr[static_cast<size_t>(dest_x + (dest_y * surface_data_dest->width))] = sub_palette_[color];
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -567,13 +567,16 @@ void Surface::copyToTexture(SDL_Renderer* renderer, SDL_Texture* texture) { //
|
||||
// Convertir `pitch` de bytes a Uint32 (asegurando alineación correcta en hardware)
|
||||
int row_stride = pitch / sizeof(Uint32);
|
||||
|
||||
for (int y = 0; y < surface_data_->height; ++y) {
|
||||
for (int x = 0; x < surface_data_->width; ++x) {
|
||||
// Calcular la posición correcta en la textura teniendo en cuenta el stride
|
||||
int texture_index = (y * row_stride) + x;
|
||||
int surface_index = (y * surface_data_->width) + x;
|
||||
|
||||
pixels[texture_index] = palette_[surface_data_->data.get()[surface_index]];
|
||||
// Cachear punteros fuera del bucle para permitir autovectorización SIMD
|
||||
const Uint8* src = surface_data_->data.get();
|
||||
const Uint32* pal = palette_.data();
|
||||
const int width = surface_data_->width;
|
||||
const int height = surface_data_->height;
|
||||
for (int y = 0; y < height; ++y) {
|
||||
const Uint8* src_row = src + (y * width);
|
||||
Uint32* dst_row = pixels + (y * row_stride);
|
||||
for (int x = 0; x < width; ++x) {
|
||||
dst_row[x] = pal[src_row[x]];
|
||||
}
|
||||
}
|
||||
|
||||
@@ -613,12 +616,16 @@ void Surface::copyToTexture(SDL_Renderer* renderer, SDL_Texture* texture, SDL_FR
|
||||
|
||||
int row_stride = pitch / sizeof(Uint32);
|
||||
|
||||
for (int y = 0; y < surface_data_->height; ++y) {
|
||||
for (int x = 0; x < surface_data_->width; ++x) {
|
||||
int texture_index = (y * row_stride) + x;
|
||||
int surface_index = (y * surface_data_->width) + x;
|
||||
|
||||
pixels[texture_index] = palette_[surface_data_->data.get()[surface_index]];
|
||||
// Cachear punteros fuera del bucle para permitir autovectorización SIMD
|
||||
const Uint8* src = surface_data_->data.get();
|
||||
const Uint32* pal = palette_.data();
|
||||
const int width = surface_data_->width;
|
||||
const int height = surface_data_->height;
|
||||
for (int y = 0; y < height; ++y) {
|
||||
const Uint8* src_row = src + (y * width);
|
||||
Uint32* dst_row = pixels + (y * row_stride);
|
||||
for (int x = 0; x < width; ++x) {
|
||||
dst_row[x] = pal[src_row[x]];
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -11,6 +11,7 @@
|
||||
#include "core/input/input_types.hpp" // Para BUTTON_TO_STRING, STRING_TO_BUTTON
|
||||
#include "external/fkyaml_node.hpp" // Para fkyaml::node
|
||||
#include "game/defaults.hpp" // Para GameDefaults::VERSION
|
||||
#include "utils/utils.hpp" // Para toLower
|
||||
|
||||
namespace Options {
|
||||
|
||||
@@ -177,24 +178,6 @@ namespace Options {
|
||||
{"LEFT_STICK_LEFT", 200},
|
||||
{"LEFT_STICK_RIGHT", 201}};
|
||||
|
||||
// Lista de paletas válidas
|
||||
const std::vector<std::string> VALID_PALETTES = {
|
||||
"black-and-white",
|
||||
"green-phosphor",
|
||||
"island-joy-16",
|
||||
"lost-century",
|
||||
"na16",
|
||||
"orange-screen",
|
||||
"pico-8",
|
||||
"ruzx-spectrum",
|
||||
"ruzx-spectrum-revision-2",
|
||||
"steam-lords",
|
||||
"sweetie-16",
|
||||
"sweetie-16_bona",
|
||||
"zx-spectrum",
|
||||
"zx-spectrum-adjusted",
|
||||
"zxarne-5-2"};
|
||||
|
||||
// Funciones helper de conversión
|
||||
auto filterToString(Screen::Filter filter) -> std::string {
|
||||
auto it = FILTER_TO_STRING.find(filter);
|
||||
@@ -257,12 +240,6 @@ namespace Options {
|
||||
}
|
||||
}
|
||||
|
||||
auto isValidPalette(const std::string& palette) -> bool {
|
||||
std::string lower_palette = palette;
|
||||
std::ranges::transform(lower_palette, lower_palette.begin(), ::tolower);
|
||||
return std::ranges::any_of(VALID_PALETTES, [&lower_palette](const auto& valid) { return valid == lower_palette; });
|
||||
}
|
||||
|
||||
// --- Funciones helper para loadFromFile() ---
|
||||
|
||||
// Carga configuración de ventana desde YAML
|
||||
@@ -309,12 +286,12 @@ namespace Options {
|
||||
}
|
||||
}
|
||||
|
||||
// Helper: carga el campo palette con validación extra
|
||||
// Helper: carga el campo palette; PaletteManager hará el fallback si el nombre no existe
|
||||
void loadPaletteFromYaml(const fkyaml::node& vid) {
|
||||
if (!vid.contains("palette")) { return; }
|
||||
try {
|
||||
auto palette_str = vid["palette"].get_value<std::string>();
|
||||
video.palette = isValidPalette(palette_str) ? palette_str : Defaults::Video::PALETTE_NAME;
|
||||
video.palette = toLower(palette_str);
|
||||
} catch (...) {
|
||||
video.palette = Defaults::Video::PALETTE_NAME;
|
||||
}
|
||||
|
||||
@@ -401,9 +401,7 @@ static const std::vector<ConsoleCommand> COMMANDS = {
|
||||
// PALETTE NEXT/PREV/<nombre> — Paleta de colores (F5/F6 o por nombre)
|
||||
{.keyword = "PALETTE", .execute = [](const std::vector<std::string>& args) -> std::string {
|
||||
const auto palName = []() -> std::string {
|
||||
std::string name = Options::video.palette;
|
||||
std::ranges::transform(name, name.begin(), ::tolower);
|
||||
return name;
|
||||
return Screen::get()->getPalettePrettyName();
|
||||
};
|
||||
if (args.empty()) { return "usage: palette [next|prev|<name>]"; }
|
||||
if (args[0] == "NEXT") {
|
||||
|
||||
125
tools/sort_palette/sort_palette.py
Normal file
125
tools/sort_palette/sort_palette.py
Normal file
@@ -0,0 +1,125 @@
|
||||
import sys
|
||||
import math
|
||||
import tempfile
|
||||
import os
|
||||
|
||||
# ------------------------------
|
||||
# Utilidades de color
|
||||
# ------------------------------
|
||||
|
||||
def luminosidad(rgb):
|
||||
r, g, b = rgb
|
||||
return 0.2126*r + 0.7152*g + 0.0722*b
|
||||
|
||||
def distancia_rgb(c1, c2):
|
||||
return math.sqrt(
|
||||
(c1[0] - c2[0])**2 +
|
||||
(c1[1] - c2[1])**2 +
|
||||
(c1[2] - c2[2])**2
|
||||
)
|
||||
|
||||
# Paleta ZX Spectrum
|
||||
PALETA_SPECTRUM = [
|
||||
(0, 0, 0),
|
||||
(0, 0, 0),
|
||||
(0, 0, 216),
|
||||
(0, 0, 255),
|
||||
(216, 0, 0),
|
||||
(255, 0, 0),
|
||||
(216, 0, 216),
|
||||
(255, 0, 255),
|
||||
(0, 216, 0),
|
||||
(0, 255, 0),
|
||||
(0, 216, 216),
|
||||
(0, 255, 255),
|
||||
(216, 216, 0),
|
||||
(255, 255, 0),
|
||||
(216, 216, 216),
|
||||
(255, 255, 255),
|
||||
]
|
||||
|
||||
# ------------------------------
|
||||
# Lectura / escritura JASC-PAL
|
||||
# ------------------------------
|
||||
|
||||
def leer_paleta_jasc(ruta):
|
||||
with open(ruta, "r") as f:
|
||||
lineas = [l.strip() for l in f.readlines()]
|
||||
|
||||
if lineas[0] != "JASC-PAL":
|
||||
raise ValueError("El fichero no es un JASC-PAL válido")
|
||||
|
||||
num_colores = int(lineas[2])
|
||||
colores = []
|
||||
|
||||
for i in range(num_colores):
|
||||
r, g, b = map(int, lineas[3 + i].split())
|
||||
colores.append((r, g, b))
|
||||
|
||||
return colores
|
||||
|
||||
def guardar_paleta_jasc(ruta, colores):
|
||||
with open(ruta, "w") as f:
|
||||
f.write("JASC-PAL\n")
|
||||
f.write("0100\n")
|
||||
f.write(f"{len(colores)}\n")
|
||||
for r, g, b in colores:
|
||||
f.write(f"{r} {g} {b}\n")
|
||||
|
||||
# ------------------------------
|
||||
# Métodos de ordenación
|
||||
# ------------------------------
|
||||
|
||||
def ordenar_por_luminosidad(colores):
|
||||
return sorted(colores, key=luminosidad)
|
||||
|
||||
def ordenar_por_similitud_spectrum(colores):
|
||||
colores_disponibles = colores.copy()
|
||||
resultado = []
|
||||
|
||||
for ref in PALETA_SPECTRUM:
|
||||
mejor = min(colores_disponibles, key=lambda c: distancia_rgb(c, ref))
|
||||
resultado.append(mejor)
|
||||
colores_disponibles.remove(mejor)
|
||||
|
||||
return resultado
|
||||
|
||||
# ------------------------------
|
||||
# Main
|
||||
# ------------------------------
|
||||
|
||||
def main():
|
||||
if len(sys.argv) < 4:
|
||||
print("Uso: python ordenar_paleta.py entrada.pal salida.pal [luminosidad|spectrum]")
|
||||
return
|
||||
|
||||
entrada = sys.argv[1]
|
||||
salida = sys.argv[2]
|
||||
modo = sys.argv[3].lower()
|
||||
|
||||
colores = leer_paleta_jasc(entrada)
|
||||
|
||||
if modo == "luminosidad":
|
||||
colores_ordenados = ordenar_por_luminosidad(colores)
|
||||
elif modo == "spectrum":
|
||||
colores_ordenados = ordenar_por_similitud_spectrum(colores)
|
||||
else:
|
||||
print(f"Modo desconocido: {modo}")
|
||||
print("Modos disponibles: luminosidad, spectrum")
|
||||
return
|
||||
|
||||
# Si salida == entrada, sobrescribimos de forma segura
|
||||
if entrada == salida:
|
||||
# Guardamos primero en un temporal para evitar corrupción si algo falla
|
||||
with tempfile.NamedTemporaryFile(delete=False) as tmp:
|
||||
temp_path = tmp.name
|
||||
guardar_paleta_jasc(temp_path, colores_ordenados)
|
||||
os.replace(temp_path, entrada)
|
||||
print(f"Paleta sobrescrita ({modo}) en {entrada}")
|
||||
else:
|
||||
guardar_paleta_jasc(salida, colores_ordenados)
|
||||
print(f"Paleta ordenada ({modo}) guardada en {salida}")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
Reference in New Issue
Block a user