diff --git a/CHANGES b/CHANGES index ffda80576..169a69a15 100644 --- a/CHANGES +++ b/CHANGES @@ -5,6 +5,7 @@ Features: - New unlicensed GB mappers: NT (older types 1 and 2), Li Cheng, GGB-81 - Debugger: Add range watchpoints Emulation fixes: + - GB Video: Implement DMG-style sprite ordering - GBA Audio: Fix improperly deserializing GB audio registers (fixes mgba.io/i/2793) - GBA Memory: Make VRAM access stalls only apply to BG RAM - GBA SIO: Fix SIOCNT SI pin value after attaching player 2 (fixes mgba.io/i/2805) diff --git a/cinema/gb/acid/cgb-acid2/baseline_0000.png b/cinema/gb/acid/cgb-acid2/baseline_0000.png new file mode 100644 index 000000000..4baff3425 Binary files /dev/null and b/cinema/gb/acid/cgb-acid2/baseline_0000.png differ diff --git a/cinema/gb/acid/cgb-acid2/test.gbc b/cinema/gb/acid/cgb-acid2/test.gbc new file mode 100644 index 000000000..5f71bd360 Binary files /dev/null and b/cinema/gb/acid/cgb-acid2/test.gbc differ diff --git a/cinema/gb/acid/config.ini b/cinema/gb/acid/config.ini new file mode 100644 index 000000000..e6b9f2af6 --- /dev/null +++ b/cinema/gb/acid/config.ini @@ -0,0 +1,6 @@ +[testinfo] +skip=15 +frames=1 + +[ports.cinema] +sgb.borders=0 diff --git a/cinema/gb/acid/dmg-acid2/baseline_0000.png b/cinema/gb/acid/dmg-acid2/baseline_0000.png new file mode 100644 index 000000000..fde56ebc3 Binary files /dev/null and b/cinema/gb/acid/dmg-acid2/baseline_0000.png differ diff --git a/cinema/gb/acid/dmg-acid2/test.gb b/cinema/gb/acid/dmg-acid2/test.gb new file mode 100644 index 000000000..a25ef9485 Binary files /dev/null and b/cinema/gb/acid/dmg-acid2/test.gb differ diff --git a/cinema/gb/mooneye-gb/manual-only/sprite_priority/baseline_0000.png b/cinema/gb/mooneye-gb/manual-only/sprite_priority/baseline_0000.png index 64aac5965..cb3569baf 100644 Binary files a/cinema/gb/mooneye-gb/manual-only/sprite_priority/baseline_0000.png and b/cinema/gb/mooneye-gb/manual-only/sprite_priority/baseline_0000.png differ diff --git a/cinema/gb/mooneye-gb/manual-only/sprite_priority/xbaseline_0000.png b/cinema/gb/mooneye-gb/manual-only/sprite_priority/xbaseline_0000.png deleted file mode 100644 index 2201a6ac5..000000000 Binary files a/cinema/gb/mooneye-gb/manual-only/sprite_priority/xbaseline_0000.png and /dev/null differ diff --git a/src/gb/renderers/software.c b/src/gb/renderers/software.c index a5e41162f..d157920fa 100644 --- a/src/gb/renderers/software.c +++ b/src/gb/renderers/software.c @@ -571,20 +571,38 @@ static void _cleanOAM(struct GBVideoSoftwareRenderer* renderer, int y) { } int o = 0; int i; + int16_t ids[GB_VIDEO_MAX_LINE_OBJ]; for (i = 0; i < GB_VIDEO_MAX_OBJ && o < GB_VIDEO_MAX_LINE_OBJ; ++i) { uint8_t oy = renderer->d.oam->obj[i].y; if (y < oy - 16 || y >= oy - 16 + spriteHeight) { continue; } - // TODO: Sort - renderer->obj[o].obj = renderer->d.oam->obj[i]; - renderer->obj[o].index = i; + ids[o] = (renderer->d.oam->obj[i].x << 7) | i; ++o; - if (o == 10) { - break; - } } renderer->objMax = o; + if (renderer->model < GB_MODEL_CGB) { + // Terrble n^2 sort, but it's only 10 elements so it shouldn't be that bad + int16_t ids2[GB_VIDEO_MAX_LINE_OBJ]; + int min = -1; + int j; + for (i = 0; i < o; ++i) { + int min2 = 0xFFFF; + for (j = 0; j < o; ++j) { + if (ids[j] > min && ids[j] < min2) { + min2 = ids[j]; + } + } + min = min2; + ids2[i] = min; + } + memcpy(ids, ids2, sizeof(ids)); + } + for (i = 0; i < o; ++i) { + int id = ids[i] & 0x7F; + renderer->obj[i].obj = renderer->d.oam->obj[id]; + renderer->obj[i].index = id; + } } static void GBVideoSoftwareRendererDrawRange(struct GBVideoRenderer* renderer, int startX, int endX, int y) {