Files
Main/support/neogeo/graphics.cpp

104 lines
3.5 KiB
C++

// Moves bytes around so that the fix graphics are stored in a way that
// takes advantage of the SDRAM 16-bit bus
// Part of Neogeo_MiSTer
// (C) 2019 Sean 'furrtek' Gonsalves
#include "graphics.h"
void spr_convert(uint8_t* buf_in, uint8_t* buf_out, unsigned int size)
{
/*
In C ROMs, a word provides two bitplanes for an 8-pixel wide line
They're used in pairs to provide 32 bits at once (all four bitplanes)
For one sprite tile, bytes are used like this: ([...] represents one 8-pixel wide line)
Even ROM Odd ROM
[ 40 41 ][ 00 01 ] [ 42 43 ][ 02 03 ]
[ 44 45 ][ 04 05 ] [ 46 47 ][ 06 07 ]
[ 48 49 ][ 08 09 ] [ 4A 4B ][ 0A 0B ]
[ 4C 4D ][ 0C 0D ] [ 4E 4F ][ 0E 0F ]
[ 50 51 ][ 10 11 ] [ 52 53 ][ 12 13 ]
... ...
The data read for a given tile line (16 pixels) is always the same, only the rendering order of the pixels can change
To take advantage of the SDRAM burst read feature, the data can be loaded so that all 16 pixels of a tile
line can be read sequentially: () are 16-bit words, [] is the 4-word burst read
[(40 41) (00 01) (42 43) (02 03)]
[(44 45) (04 05) (46 47) (06 07)]...
Word interleaving is done on the FPGA side to mix the two C ROMs data (even/odd)
In: FEDCBA9876 54321 0
Out: FEDCBA9876 15432 0
*/
for (unsigned int i = 0; i < size; i++)
buf_out[i] = buf_in[(i & 0xFFC0) | (i & 1) | ((i >> 1) & 0x1E) | (((i & 2) ^ 2) << 4)];
/*
0 <- 20
1 <- 21
2 <- 00
3 <- 01
4 <- 22
5 <- 23
6 <- 02
7 <- 03
...
00 -> 02
01 -> 03
02 -> 06
03 -> 07
...
*/
}
void spr_convert_dbl(uint8_t* buf_in, uint8_t* buf_out, unsigned int size)
{
/*
In C ROMs, a word provides two bitplanes for an 8-pixel wide line
They're used in pairs to provide 32 bits at once (all four bitplanes)
For one sprite tile, bytes are used like this: ([...] represents one 8-pixel wide line)
ROM
[ 42 43 ][ 02 03 ][ 40 41 ][ 00 01 ]
[ 46 47 ][ 06 07 ][ 44 45 ][ 04 05 ]
[ 4A 4B ][ 0A 0B ][ 48 49 ][ 08 09 ]
[ 4E 4F ][ 0E 0F ][ 4C 4D ][ 0C 0D ]
[ 52 53 ][ 12 13 ][ 50 51 ][ 10 11 ]
... ...
The data read for a given tile line (16 pixels) is always the same, only the rendering order of the pixels can change
To take advantage of the SDRAM burst read feature, the data can be loaded so that all 16 pixels of a tile
line can be read sequentially: () are 16-bit words, [] is the 4-word burst read
[(40 41) (00 01) (42 43) (02 03)]
[(44 45) (04 05) (46 47) (06 07)]...
This is consolidated version of C ROM with both parts in one.
*/
for (unsigned int i = 0; i < size; i++)
buf_out[i] = buf_in[(i & 0xFF80) | ((i ^ 2) & 3) | ((i >> 1) & 0x3C) | (((i & 4) ^ 4) << 4)];
}
void fix_convert(uint8_t* buf_in, uint8_t* buf_out, unsigned int size)
{
/*
In S ROMs, a byte provides two pixels
For one fix tile, bytes are used like this: ([...] represents a pair of pixels)
[10][18][00][08]
[11][19][01][09]
[12][1A][02][0A]
[13][1B][03][0B]
[14][1C][04][0C]
[15][1D][05][0D]
[16][1E][06][0E]
[17][1F][07][0F]
The data read for a given tile line (8 pixels) is always the same
To take advantage of the SDRAM burst read feature, the data can be loaded so that all 8 pixels of a tile
line can be read sequentially: () are 16-bit words, [] is the 2-word burst read
[(10 18) (00 08)]
[(11 19) (01 09)]...
In: FEDCBA9876543210
Out: FEDCBA9876510432
*/
for (unsigned int i = 0; i < size; i++)
buf_out[i] = buf_in[(i & 0xFFE0) | ((i >> 2) & 7) | ((i & 1) << 3) | (((i & 2) << 3) ^ 0x10)];
}