all repos — mgba @ f34f45257a6c52ea2e96e8ba75e8f7bfe8d5e245

mGBA Game Boy Advance Emulator

GBA Video: Fix out-of-order OBJWIN
Jeffrey Pfau jeffrey@endrift.com
Sun, 11 Sep 2016 00:51:29 -0700
commit

f34f45257a6c52ea2e96e8ba75e8f7bfe8d5e245

parent

2155a3017296fbe9de76a6db4ca69515ef113506

3 files changed, 30 insertions(+), 4 deletions(-)

jump to
M CHANGESCHANGES

@@ -39,6 +39,7 @@ - GBA: Fix filehandle leak with savegames

- GBA: Timer 0 cannot be count up - Qt: Fix being unable to pause manually when using auto-pausing - GBA Memory: Fix ldm {pc} + - GBA Video: Fix out-of-order OBJWIN Misc: - 3DS: Use blip_add_delta_fast for a small speed improvement - OpenGL: Log shader compilation failure
M src/gba/renderers/video-software.csrc/gba/renderers/video-software.c

@@ -455,6 +455,7 @@

static void _cleanOAM(struct GBAVideoSoftwareRenderer* renderer) { int i; int oamMax = 0; + int objwinMax = 0; for (i = 0; i < 128; ++i) { struct GBAObj obj; LOAD_16(obj.a, 0, &renderer->d.oam->obj[i].a);

@@ -466,14 +467,22 @@ if (GBAObjAttributesAIsTransformed(obj.a)) {

height <<= GBAObjAttributesAGetDoubleSize(obj.a); } if (GBAObjAttributesAGetY(obj.a) < VIDEO_VERTICAL_PIXELS || GBAObjAttributesAGetY(obj.a) + height >= VIDEO_VERTICAL_TOTAL_PIXELS) { - renderer->sprites[oamMax].y = GBAObjAttributesAGetY(obj.a); - renderer->sprites[oamMax].endY = GBAObjAttributesAGetY(obj.a) + height; - renderer->sprites[oamMax].obj = obj; - ++oamMax; + if (GBAObjAttributesAGetMode(obj.a) == OBJ_MODE_OBJWIN) { + renderer->objwinSprites[objwinMax].y = GBAObjAttributesAGetY(obj.a); + renderer->objwinSprites[objwinMax].endY = GBAObjAttributesAGetY(obj.a) + height; + renderer->objwinSprites[objwinMax].obj = obj; + ++objwinMax; + } else { + renderer->sprites[oamMax].y = GBAObjAttributesAGetY(obj.a); + renderer->sprites[oamMax].endY = GBAObjAttributesAGetY(obj.a) + height; + renderer->sprites[oamMax].obj = obj; + ++oamMax; + } } } } renderer->oamMax = oamMax; + renderer->objwinMax = objwinMax; renderer->oamDirty = 0; }

@@ -773,6 +782,20 @@ continue;

} int i; int drawn; + for (i = 0; i < renderer->objwinMax; ++i) { + int localY = y; + if (renderer->spriteCyclesRemaining <= 0) { + break; + } + struct GBAVideoSoftwareSprite* sprite = &renderer->objwinSprites[i]; + if (GBAObjAttributesAIsMosaic(sprite->obj.a)) { + localY = mosaicY; + } + if ((localY < sprite->y && (sprite->endY - 256 < 0 || localY >= sprite->endY - 256)) || localY >= sprite->endY) { + continue; + } + drawn = GBAVideoSoftwareRendererPreprocessSprite(renderer, &sprite->obj, localY); + } for (i = 0; i < renderer->oamMax; ++i) { int localY = y; if (renderer->spriteCyclesRemaining <= 0) {
M src/gba/renderers/video-software.hsrc/gba/renderers/video-software.h

@@ -152,7 +152,9 @@ struct GBAVideoSoftwareBackground bg[4];

int oamDirty; int oamMax; + int objwinMax; struct GBAVideoSoftwareSprite sprites[128]; + struct GBAVideoSoftwareSprite objwinSprites[128]; int start; int end;