3f45430454
gfx_blit_noclip_vflip / gfx_blit_part_noclip_vflip / gfx_blit_part_vflip. Ассемблера не потребовалось: у row-major вертикальное зеркало — это порядок строк, а он задаётся ЗНАКОМ src-страйда, который _bgi_blit_rows_raw и так принимает знаковым и патчит SMC. Даём адрес последней строки и -stride. Клип у part_vflip свой: обрезка сверху экрана съедает НИЖНИЕ строки источника, и первая строка обязана считаться от высоты ДО клипа (поймано тестом — сначала формула брала уже укороченную). tests/pageflip расширен до 8 проверок, все PASS в MAME. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
33 lines
1.7 KiB
C
33 lines
1.7 KiB
C
/*
|
|
* gfx_blit_part_noclip_vflip — под-прямоугольник картинки БЕЗ клипа,
|
|
* ЗЕРКАЛЬНО ПО ВЕРТИКАЛИ. Пара к gfx_blit_part_noclip; про механику
|
|
* зеркала (знак src-страйда) — см. gfx_blit_noclip_vflip.
|
|
*
|
|
* (sx,sy,w,h) задают кусок ИСТОЧНИКА в обычной системе координат, как у
|
|
* не-зеркального двойника: sy — верхняя строка куска. На экран этот кусок
|
|
* ложится перевёрнутым, (x,y) — левый верхний угол результата. Значит
|
|
* первой рисуется строка sy+h-1 источника.
|
|
*
|
|
* Тайловому слою это позволяет не трогать выбор куска атласа вообще:
|
|
* меняется только вызываемая функция и экранный y (его считает
|
|
* вызывающий — у него поле, у библиотеки экран).
|
|
*/
|
|
#include "../_bgi.h"
|
|
|
|
void gfx_blit_part_noclip_vflip(int x, int y, const void *img,
|
|
uint8_t sx, uint8_t sy, uint8_t w, uint8_t h)
|
|
{
|
|
const uint8_t *p = (const uint8_t *)img;
|
|
uint16_t stride = (uint16_t)(p[0] | (p[1] << 8));
|
|
const uint8_t *src;
|
|
|
|
if (!stride || !w || !h) return;
|
|
/* Стартуем с ПОСЛЕДНЕЙ строки куска и идём вверх. */
|
|
src = p + 4 + (uint16_t)(sy + h - 1) * stride + sx;
|
|
|
|
_bgi_begin();
|
|
_bgi_blit_rows_raw(src, (uint8_t *)(_gfx_addr_base + x),
|
|
w, h, -(int)stride, (uint8_t)y);
|
|
_bgi_end();
|
|
}
|