mirror of https://github.com/mgba-emu/mgba.git
GBA Video: OBJWIN can change blend params after OBJ is drawn (fixes #921)
This commit is contained in:
parent
24f3b5f11d
commit
65534d5dcd
1
CHANGES
1
CHANGES
|
@ -22,6 +22,7 @@ Bugfixes:
|
||||||
- GB Video: Fix loading states while in mode 3
|
- GB Video: Fix loading states while in mode 3
|
||||||
- GB Video: Only trigger STAT write IRQs when screen is on (fixes mgba.io/i/912)
|
- GB Video: Only trigger STAT write IRQs when screen is on (fixes mgba.io/i/912)
|
||||||
- GBA Cheats: Fix PARv3 slide codes (fixes mgba.io/i/919)
|
- GBA Cheats: Fix PARv3 slide codes (fixes mgba.io/i/919)
|
||||||
|
- GBA Video: OBJWIN can change blend params after OBJ is drawn (fixes mgba.io/i/921)
|
||||||
Misc:
|
Misc:
|
||||||
- GBA Timer: Use global cycles for timers
|
- GBA Timer: Use global cycles for timers
|
||||||
- GBA: Extend oddly-sized ROMs to full address space (fixes mgba.io/i/722)
|
- GBA: Extend oddly-sized ROMs to full address space (fixes mgba.io/i/722)
|
||||||
|
|
|
@ -156,26 +156,26 @@ int GBAVideoSoftwareRendererPreprocessSprite(struct GBAVideoSoftwareRenderer* re
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int objwinSlowPath = GBARegisterDISPCNTIsObjwinEnable(renderer->dispcnt) && GBAWindowControlGetBlendEnable(renderer->objwin.packed) != GBAWindowControlIsBlendEnable(renderer->currentWindow.packed);
|
||||||
int variant = renderer->target1Obj &&
|
int variant = renderer->target1Obj &&
|
||||||
GBAWindowControlIsBlendEnable(renderer->currentWindow.packed) &&
|
GBAWindowControlIsBlendEnable(renderer->currentWindow.packed) &&
|
||||||
(renderer->blendEffect == BLEND_BRIGHTEN || renderer->blendEffect == BLEND_DARKEN);
|
(renderer->blendEffect == BLEND_BRIGHTEN || renderer->blendEffect == BLEND_DARKEN);
|
||||||
if (GBAObjAttributesAGetMode(sprite->a) == OBJ_MODE_SEMITRANSPARENT) {
|
if (GBAObjAttributesAGetMode(sprite->a) == OBJ_MODE_SEMITRANSPARENT || objwinSlowPath) {
|
||||||
int target2 = renderer->target2Bd << 4;
|
int target2 = renderer->target2Bd;
|
||||||
target2 |= renderer->bg[0].target2 << (renderer->bg[0].priority);
|
target2 |= renderer->bg[0].target2;
|
||||||
target2 |= renderer->bg[1].target2 << (renderer->bg[1].priority);
|
target2 |= renderer->bg[1].target2;
|
||||||
target2 |= renderer->bg[2].target2 << (renderer->bg[2].priority);
|
target2 |= renderer->bg[2].target2;
|
||||||
target2 |= renderer->bg[3].target2 << (renderer->bg[3].priority);
|
target2 |= renderer->bg[3].target2;
|
||||||
if ((1 << GBAObjAttributesCGetPriority(sprite->c)) <= target2) {
|
if (target2) {
|
||||||
flags |= FLAG_REBLEND;
|
flags |= FLAG_REBLEND;
|
||||||
variant = 0;
|
variant = 0;
|
||||||
} else if (!target2) {
|
} else {
|
||||||
flags &= ~FLAG_TARGET_1;
|
flags &= ~FLAG_TARGET_1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
color_t* palette = &renderer->normalPalette[0x100];
|
color_t* palette = &renderer->normalPalette[0x100];
|
||||||
color_t* objwinPalette = palette;
|
color_t* objwinPalette = palette;
|
||||||
int objwinSlowPath = GBARegisterDISPCNTIsObjwinEnable(renderer->dispcnt) && GBAWindowControlGetBlendEnable(renderer->objwin.packed) != GBAWindowControlIsBlendEnable(renderer->currentWindow.packed);
|
|
||||||
|
|
||||||
if (variant) {
|
if (variant) {
|
||||||
palette = &renderer->variantPalette[0x100];
|
palette = &renderer->variantPalette[0x100];
|
||||||
|
|
|
@ -43,7 +43,7 @@ static inline void _compositeBlendObjwin(struct GBAVideoSoftwareRenderer* render
|
||||||
if (current & FLAG_TARGET_1 && color & FLAG_TARGET_2) {
|
if (current & FLAG_TARGET_1 && color & FLAG_TARGET_2) {
|
||||||
color = _mix(renderer->blda, current, renderer->bldb, color);
|
color = _mix(renderer->blda, current, renderer->bldb, color);
|
||||||
} else {
|
} else {
|
||||||
color = (current & 0x00FFFFFF) | (current & FLAG_REBLEND);
|
color = (current & 0x00FFFFFF) | (current & (FLAG_REBLEND | FLAG_OBJWIN));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
color = (color & ~FLAG_TARGET_2) | (current & FLAG_OBJWIN);
|
color = (color & ~FLAG_TARGET_2) | (current & FLAG_OBJWIN);
|
||||||
|
@ -59,7 +59,7 @@ static inline void _compositeBlendNoObjwin(struct GBAVideoSoftwareRenderer* rend
|
||||||
if (current & FLAG_TARGET_1 && color & FLAG_TARGET_2) {
|
if (current & FLAG_TARGET_1 && color & FLAG_TARGET_2) {
|
||||||
color = _mix(renderer->blda, current, renderer->bldb, color);
|
color = _mix(renderer->blda, current, renderer->bldb, color);
|
||||||
} else {
|
} else {
|
||||||
color = (current & 0x00FFFFFF) | (current & FLAG_REBLEND);
|
color = (current & 0x00FFFFFF) | (current & (FLAG_REBLEND | FLAG_OBJWIN));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
color = color & ~FLAG_TARGET_2;
|
color = color & ~FLAG_TARGET_2;
|
||||||
|
@ -73,7 +73,7 @@ static inline void _compositeNoBlendObjwin(struct GBAVideoSoftwareRenderer* rend
|
||||||
if (color < current) {
|
if (color < current) {
|
||||||
color |= (current & FLAG_OBJWIN);
|
color |= (current & FLAG_OBJWIN);
|
||||||
} else {
|
} else {
|
||||||
color = (current & 0x00FFFFFF) | (current & FLAG_REBLEND);
|
color = (current & 0x00FFFFFF) | (current & (FLAG_REBLEND | FLAG_OBJWIN));
|
||||||
}
|
}
|
||||||
*pixel = color;
|
*pixel = color;
|
||||||
}
|
}
|
||||||
|
@ -82,7 +82,7 @@ static inline void _compositeNoBlendNoObjwin(struct GBAVideoSoftwareRenderer* re
|
||||||
uint32_t current) {
|
uint32_t current) {
|
||||||
UNUSED(renderer);
|
UNUSED(renderer);
|
||||||
if (color >= current) {
|
if (color >= current) {
|
||||||
color = (current & 0x00FFFFFF) | (current & FLAG_REBLEND);
|
color = (current & 0x00FFFFFF) | (current & (FLAG_REBLEND | FLAG_OBJWIN));
|
||||||
}
|
}
|
||||||
*pixel = color;
|
*pixel = color;
|
||||||
}
|
}
|
||||||
|
|
|
@ -621,6 +621,14 @@ static void GBAVideoSoftwareRendererDrawScanline(struct GBAVideoRenderer* render
|
||||||
}
|
}
|
||||||
if (softwareRenderer->target1Obj && (softwareRenderer->blendEffect == BLEND_DARKEN || softwareRenderer->blendEffect == BLEND_BRIGHTEN)) {
|
if (softwareRenderer->target1Obj && (softwareRenderer->blendEffect == BLEND_DARKEN || softwareRenderer->blendEffect == BLEND_BRIGHTEN)) {
|
||||||
x = 0;
|
x = 0;
|
||||||
|
uint32_t mask = 0xFF000000 & ~FLAG_OBJWIN;
|
||||||
|
uint32_t match = FLAG_REBLEND;
|
||||||
|
if (GBARegisterDISPCNTIsObjwinEnable(softwareRenderer->dispcnt)) {
|
||||||
|
mask |= FLAG_OBJWIN;
|
||||||
|
if (GBAWindowControlIsBlendEnable(softwareRenderer->objwin.packed)) {
|
||||||
|
match |= FLAG_OBJWIN;
|
||||||
|
}
|
||||||
|
}
|
||||||
for (w = 0; w < softwareRenderer->nWindows; ++w) {
|
for (w = 0; w < softwareRenderer->nWindows; ++w) {
|
||||||
if (!GBAWindowControlIsBlendEnable(softwareRenderer->windows[w].control.packed)) {
|
if (!GBAWindowControlIsBlendEnable(softwareRenderer->windows[w].control.packed)) {
|
||||||
continue;
|
continue;
|
||||||
|
@ -629,14 +637,14 @@ static void GBAVideoSoftwareRendererDrawScanline(struct GBAVideoRenderer* render
|
||||||
if (softwareRenderer->blendEffect == BLEND_DARKEN) {
|
if (softwareRenderer->blendEffect == BLEND_DARKEN) {
|
||||||
for (; x < end; ++x) {
|
for (; x < end; ++x) {
|
||||||
uint32_t color = softwareRenderer->row[x];
|
uint32_t color = softwareRenderer->row[x];
|
||||||
if ((color & 0xFF000000) == FLAG_REBLEND) {
|
if ((color & mask) == match) {
|
||||||
softwareRenderer->row[x] = _darken(color, softwareRenderer->bldy);
|
softwareRenderer->row[x] = _darken(color, softwareRenderer->bldy);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} else if (softwareRenderer->blendEffect == BLEND_BRIGHTEN) {
|
} else if (softwareRenderer->blendEffect == BLEND_BRIGHTEN) {
|
||||||
for (; x < end; ++x) {
|
for (; x < end; ++x) {
|
||||||
uint32_t color = softwareRenderer->row[x];
|
uint32_t color = softwareRenderer->row[x];
|
||||||
if ((color & 0xFF000000) == FLAG_REBLEND) {
|
if ((color & mask) == match) {
|
||||||
softwareRenderer->row[x] = _brighten(color, softwareRenderer->bldy);
|
softwareRenderer->row[x] = _brighten(color, softwareRenderer->bldy);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
Binary file not shown.
After Width: | Height: | Size: 15 KiB |
Binary file not shown.
After Width: | Height: | Size: 15 KiB |
Binary file not shown.
After Width: | Height: | Size: 15 KiB |
Binary file not shown.
After Width: | Height: | Size: 15 KiB |
Binary file not shown.
Loading…
Reference in New Issue