diff --git a/desmume/src/GPU.c b/desmume/src/GPU.c index b76b7c7a4..e176555bf 100644 --- a/desmume/src/GPU.c +++ b/desmume/src/GPU.c @@ -24,7 +24,7 @@ #include #include - +#include #include "MMU.h" #include "GPU.h" #include "debug.h" @@ -140,11 +140,11 @@ void GPU_DeInit(GPU * gpu) void GPU_resortBGs(GPU *gpu) { - u8 i, j, prio; + int i, j, prio; struct _DISPCNT * cnt = &gpu->dispCnt.bits; itemsForPriority_t * item; - for (i=0; i<192; i++) + for (i=0; i<256; i++) memset(gpu->sprWin[i],0, 256); // we don't need to check for windows here... @@ -667,6 +667,7 @@ INLINE void renderline_textBG(GPU * gpu, u8 num, u8 * dst, u32 Y, u16 XBG, u16 Y u8 *map = gpu->BG_map_ram[num] + (tmp&31) * 64; u8 *tile, *pal, *line; + u16 color; u16 xoff = XBG; u16 yoff; u16 x = 0; @@ -711,9 +712,10 @@ INLINE void renderline_textBG(GPU * gpu, u8 num, u8 * dst, u32 Y, u16 XBG, u16 Y #define RENDERL(c,m) \ - if (c) renderline_setFinalColor(gpu,0,num,dst,T1ReadWord(pal, ((c) + (tileentry.bits.Palette* m)) << 1),x,Y) ; \ + color = T1ReadWord(pal, ((c) + (tileentry.bits.Palette* m)) << 1); \ + if (c) renderline_setFinalColor(gpu,0,num,dst,color,x,Y) ; \ dst += 2; x++; xoff++; - + if(tileentry.bits.HFlip) { line += 3 - ((xoff&7)>>1); @@ -1045,10 +1047,10 @@ void extRotBG(GPU * gpu, u8 num, u8 * DST) #define nbShow 128 #define RENDER_COND(cond) RENDER_COND_OFFSET(cond,) #define RENDER_COND_OFFSET(cond,offset) \ - if((cond)&&(prioTab[sprX offset]>=prio)) \ + if ((cond)&&(prio<=prioTab[sprX offset])) \ { \ - renderline_setFinalColor(gpu, (sprX offset) << 1,4,dst, color,(sprX offset),l); \ prioTab[sprX offset] = prio; \ + renderline_setFinalColor(gpu, (sprX offset) << 1,4,dst, color, (sprX offset) ,l); \ } /* if i understand it correct, and it fixes some sprite problems in chameleon shot */ @@ -1068,7 +1070,7 @@ INLINE void render_sprite_BMP (GPU * gpu, u16 l, u8 * dst, u16 * src, INLINE void render_sprite_256 (GPU * gpu, u16 l, u8 * dst, u8 * src, u16 * pal, u8 * prioTab, u8 prio, int lg, int sprX, int x, int xdir) { int i; u8 palette_entry; u16 color; - + prio = 0; for(i = 0; i < lg; i++, ++sprX, x+=xdir) { palette_entry = src[(x&0x7) + ((x&0xFFF8)<<3)]; @@ -1078,123 +1080,38 @@ INLINE void render_sprite_256 (GPU * gpu, u16 l, u8 * dst, u8 * src, u16 * pal, } } -INLINE void render_sprite_16 (GPU * gpu, u16 l, u8 * dst, u8 * src, u8 * pal, +INLINE void render_sprite_16 (GPU * gpu, u16 l, u8 * dst, u8 * src, u16 * pal, u8 * prioTab, u8 prio, int lg, int sprX, int x, int xdir) { int i; u8 palette, palette_entry; u16 color; - -#define BLOCK(op) \ - palette_entry = palette op; \ - color = T1ReadWord(pal, palette_entry << 1); \ - RENDER_COND(palette_entry >0) \ - ++sprX; -#if 0 - - if (xdir<0) x++; - if(x&1) + u16 x1; + for(i = 0; i < lg; i++, ++sprX, x+=xdir) { - s32 x1 = (x>>1); + x1 = x>>1; palette = src[(x1&0x3) + ((x1&0xFFFC)<<3)]; - BLOCK(>> 4) - x1 = ((x+lg-1)>>1); - palette = src[(x1&0x3) + ((x1&0xFFFC)<<3)]; - palette_entry = palette >> 4; - color = T1ReadWord(pal, palette_entry << 1); - RENDER_COND_OFFSET(palette_entry>0,+lg-1) - ++sprX; + if (x & 1) palette_entry = palette >> 4; + else palette_entry = palette & 0xF; + color = pal[palette_entry]; + // palette entry = 0 means backdrop + RENDER_COND(palette_entry>0) } - if (xdir<0) x--; - - ++sprX; - lg >>= 1; - x >>= 1; - // 16 colors - - if (xdir<0) { - for(i = 0; i < lg; ++i, x+=xdir) - { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(>> 4) - BLOCK(& 0xF) - } - } else { - for(i = 0; i < lg; ++i, x+=xdir) - { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(& 0xF) - BLOCK(>> 4) - } - } - -#else - x >>= 1; - if (xdir<0) { - if (lg&1) { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(>> 4) - x+=xdir; - } - for(i = 1; i < lg; i+=2, x+=xdir) - { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(>> 4) - BLOCK(& 0xF) - } - } else { - for(i = 1; i < lg; i+=2, x+=xdir) - { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(& 0xF) - BLOCK(>> 4) - } - if (lg&1) { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(& 0xF) - } - } -#endif -#undef BLOCK } INLINE void render_sprite_Win (GPU * gpu, u16 l, u8 * src, int col256, int lg, int sprX, int x, int xdir) { int i; u8 palette, palette_entry; + u16 x1; if (col256) { for(i = 0; i < lg; i++, sprX++,x+=xdir) gpu->sprWin[l][sprX] = (src[x])?1:0; } else { - -#define BLOCK(op) \ - palette_entry = palette op; \ - gpu->sprWin[l][sprX] = (palette_entry>0)?1:0; \ - ++sprX; - - x >>= 1; - sprX++; - if (xdir<0) { - if (lg&1) { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(>> 4) - x+=xdir; - } - for(i = 1; i < lg; i+=2, x+=xdir) - { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(>> 4) - BLOCK(& 0xF) - } - } else { - for(i = 1; i < lg; i+=2, x+=xdir) - { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(& 0xF) - BLOCK(>> 4) - } - if (lg&1) { - palette = src[(x&0x3) + ((x&0xFFFC)<<3)]; - BLOCK(& 0xF) - } + for(i = 0; i < lg; i++, ++sprX, x+=xdir) + { + x1 = x>>1; + palette = src[(x1&0x3) + ((x1&0xFFFC)<<3)]; + if (x & 1) palette_entry = palette >> 4; + else palette_entry = palette & 0xF; + gpu->sprWin[l][sprX] = (palette_entry)?1:0; } -#undef BLOCK } } @@ -1212,7 +1129,7 @@ INLINE BOOL compute_sprite_vars(_OAM_ * spriteInfo, u16 l, *lg = sprSize->x; - if (*sprY>192) + if (*sprY>=192) *sprY = (s32)((s8)(spriteInfo->Y)); // FIXME: for rot/scale, a list of entries into the sprite should be maintained, @@ -1221,7 +1138,7 @@ INLINE BOOL compute_sprite_vars(_OAM_ * spriteInfo, u16 l, if ((spriteInfo->RotScale == 2) || /* rotscale == 2 => sprite disabled */ (l<*sprY)||(l>=*sprY+sprSize->y) || /* sprite lines outside of screen */ - (*sprX==256)||(*sprX+sprSize->x<0)) /* sprite pixels outside of line */ + (*sprX==256)||(*sprX+sprSize->x<=0)) /* sprite pixels outside of line */ return FALSE; /* not to be drawn */ // sprite portion out of the screen (LEFT) @@ -1230,8 +1147,9 @@ INLINE BOOL compute_sprite_vars(_OAM_ * spriteInfo, u16 l, *lg += *sprX; *x = -(*sprX); *sprX = 0; + } // sprite portion out of the screen (RIGHT) - } else if (*sprX+sprSize->x >= 256) + if (*sprX+sprSize->x >= 256) *lg = 256 - *sprX; *y = l - *sprY; /* get the y line within sprite coords */ @@ -1274,13 +1192,12 @@ void sprite1D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab) size sprSize; s32 sprX, sprY, x, y, lg; int xdir; - u8 prio, * src, * pal; + u8 prio, * src; + u16 * pal; u16 i,j; u16 rotScaleA,rotScaleB,rotScaleC,rotScaleD; prio = spriteInfo->Priority; - - if (!compute_sprite_vars(spriteInfo, l, &sprSize, &sprX, &sprY, &x, &y, &lg, &xdir)) continue; @@ -1314,20 +1231,20 @@ void sprite1D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab) src = gpu->sprMem + (spriteInfo->TileIndex<>3)*sprSize.x*8) + ((y&0x7)*8); if (gpu->dispCnt.bits.ExOBJPalette_Enable) - pal = ARM9Mem.ObjExtPal[gpu->core][0]+(spriteInfo->PaletteIndex*0x200); + pal = (u16*)(ARM9Mem.ObjExtPal[gpu->core][0]+(spriteInfo->PaletteIndex*0x200)); else - pal = ARM9Mem.ARM9_VMEM + 0x200 + gpu->core *0x400; + pal = (u16*)(ARM9Mem.ARM9_VMEM + 0x200 + gpu->core *0x400); - render_sprite_256 (gpu, l, dst, src, (u16*)pal, + render_sprite_256 (gpu, l, dst, src, pal, prioTab, prio, lg, sprX, x, xdir); continue; } /* 16 colors */ src = gpu->sprMem + (spriteInfo->TileIndex<>3)*sprSize.x*4) + ((y&0x7)*4); - pal = ARM9Mem.ARM9_VMEM + 0x200 + gpu->core * 0x400; + pal = (u16*)(ARM9Mem.ARM9_VMEM + 0x200 + gpu->core * 0x400); - pal += (spriteInfo->PaletteIndex<<4)<<1; + pal += (spriteInfo->PaletteIndex<<4); render_sprite_16 (gpu, l, dst, src, pal, prioTab, prio, lg, sprX, x, xdir); @@ -1344,7 +1261,8 @@ void sprite2D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab) size sprSize; s32 sprX, sprY, x, y, lg; int xdir; - u8 prio, * src, * pal; + u8 prio, * src; + u16 * pal; u16 i,j; u16 rotScaleA,rotScaleB,rotScaleC,rotScaleD; int block; @@ -1384,9 +1302,9 @@ void sprite2D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab) if(spriteInfo->Depth) /* 256 colors */ { src = gpu->sprMem + ((spriteInfo->TileIndex)<<5) + ((y>>3)<<10) + ((y&0x7)*8); - pal = ARM9Mem.ARM9_VMEM + 0x200 + gpu->core *0x400; + pal = (u16*)(ARM9Mem.ARM9_VMEM + 0x200 + gpu->core *0x400); - render_sprite_256 (gpu, l, dst, src, (u16*)pal, + render_sprite_256 (gpu, l, dst, src, pal, prioTab, prio, lg, sprX, x, xdir); continue; @@ -1394,9 +1312,9 @@ void sprite2D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab) /* 16 colors */ src = gpu->sprMem + ((spriteInfo->TileIndex)<<5) + ((y>>3)<<10) + ((y&0x7)*4); - pal = ARM9Mem.ARM9_VMEM + 0x200 + gpu->core * 0x400; + pal = (u16*)(ARM9Mem.ARM9_VMEM + 0x200 + gpu->core * 0x400); - pal += (spriteInfo->PaletteIndex<<4)<<1; + pal += (spriteInfo->PaletteIndex<<4); render_sprite_16 (gpu, l, dst, src, pal, prioTab, prio, lg, sprX, x, xdir); } diff --git a/desmume/src/GPU.h b/desmume/src/GPU.h index 9eb794d25..b502c8dc3 100644 --- a/desmume/src/GPU.h +++ b/desmume/src/GPU.h @@ -391,7 +391,7 @@ struct _GPU MASTER_BRIGHT masterBright; BOOL LayersEnable[5]; itemsForPriority_t itemsForPriority[NB_PRIORITIES]; - u8 sprWin[192*2][256]; + u8 sprWin[256*2][256]; #define BGBmpBB BG_bmp_ram #define BGChBB BG_tile_ram @@ -557,16 +557,14 @@ static INLINE void GPU_ligne(Screen * screen, u16 l) c = T1ReadWord(ARM9Mem.ARM9_VMEM, gpu->core * 0x400); - c |= (c<<16); // init background color & priorities - for(i8 = 0; i8< 128; ++i8) + for(i = 0; i< 256; ++i) { - T2WriteLong(dst, i8 << 2, c); - T2WriteLong(spr, i8 << 2, c); - // we init the sprites with priority 4 (if they keep it = unprocessed) - T1WriteWord(sprPrio, i8 << 1, 0xFFFF); - T1WriteWord(gpu->sprWin[l], i8 << 1, 0); + T1WriteWord(dst, i << 1, c); + T1WriteWord(spr, i << 1, c); + sprPrio[i]=0xFF; + gpu->sprWin[l][i]=0; } // init pixels priorities @@ -583,7 +581,6 @@ static INLINE void GPU_ligne(Screen * screen, u16 l) // render 1 time, but prio 4 = isn't processed further if (prio >=4) continue; - T2WriteWord(dst, i << 1, T2ReadWord(spr, i << 1)); item = &(gpu->itemsForPriority[prio]); item->PixelsX[item->nbPixelsX]=i; @@ -613,7 +610,7 @@ static INLINE void GPU_ligne(Screen * screen, u16 l) // FIXME !!! /* capture */ capcnt = &gpu->dispCapCnt.bits; -if (0 & capcnt->Capture_Enable) +if (capcnt->Capture_Enable) { u16 * srcA, * srcB, *vram; u32 c; u8 vram_bank;