reorganized some code

fixed a bug in gtk-glade ui where checkbox to en/disable OBJ was not
taken into account
This commit is contained in:
damdoum 2007-01-22 14:21:41 +00:00
parent 6446581624
commit dd4d72faf9
3 changed files with 97 additions and 138 deletions

View File

@ -302,19 +302,18 @@ void GPU_setBGProp(GPU * gpu, u16 num, u16 p)
void GPU_remove(GPU * gpu, u8 num) void GPU_remove(GPU * gpu, u8 num)
{ {
gpu->dispBG[num] = 0; if (num == 4) gpu->dispOBJ = 0;
else gpu->dispBG[num] = 0;
GPU_resortBGs(gpu); GPU_resortBGs(gpu);
} }
void GPU_addBack(GPU * gpu, u8 num) void GPU_addBack(GPU * gpu, u8 num)
{ {
gpu->dispBG[num] = 1; if (num == 4) gpu->dispOBJ = 1;
else gpu->dispBG[num] = 1;
GPU_resortBGs(gpu); GPU_resortBGs(gpu);
} }
void GPU_toggleOBJ(GPU * gpu, u8 disp) {
gpu->dispOBJ = disp;
}
void GPU_scrollX(GPU * gpu, u8 num, u16 v) void GPU_scrollX(GPU * gpu, u8 num, u16 v)
{ {
@ -1245,6 +1244,71 @@ INLINE void render_sprite_Win (GPU * gpu, u16 l, u8 * src,
} }
} }
// return val means if the sprite is to be drawn or not
INLINE BOOL compute_sprite_vars(_OAM_ * spriteInfo, u16 l,
size *sprSize, s32 *sprX, s32 *sprY, s32 *x, s32 *y, s32 *lg, int *xdir) {
*x = 0;
// get sprite location and size
*sprX = (spriteInfo->X<<23)>>23;
*sprY = spriteInfo->Y;
*sprSize = sprSizeTab[spriteInfo->Size][spriteInfo->Shape];
*lg = sprSize->x;
if (*sprY>192)
*sprY = (s32)((s8)(spriteInfo->Y));
// FIXME: for rot/scale, a list of entries into the sprite should be maintained,
// that tells us where the first pixel of a screenline starts in the sprite,
// and how a step to the right in a screenline translates within the sprite
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 */
return FALSE; /* not to be drawn */
// sprite portion out of the screen (LEFT)
if(*sprX<0)
{
*lg += *sprX;
*x = -(*sprX);
*sprX = 0;
// sprite portion out of the screen (RIGHT)
} else if (*sprX+sprSize->x >= 256)
*lg = 256 - *sprX;
*y = l - *sprY; /* get the y line within sprite coords */
// switch TOP<-->BOTTOM
if (spriteInfo->VFlip)
*y = sprSize->y - *y -1;
// switch LEFT<-->RIGHT
if (spriteInfo->HFlip) {
*x = sprSize->x - *x -1;
*xdir = -1;
} else {
*xdir = 1;
}
return TRUE;
}
INLINE void compute_sprite_rotoscale(GPU * gpu, _OAM_ * spriteInfo,
u16 * rotScaleA, u16 * rotScaleB, u16 * rotScaleC, u16 * rotScaleD) {
u16 rotScaleIndex;
// index from 0 to 31
rotScaleIndex = spriteInfo->RotScalIndex + (spriteInfo->HFlip<<1) + (spriteInfo->VFlip << 2);
/* if we need to do rotscale, gather its parameters */
/* http://nocash.emubase.de/gbatek.htm#lcdobjoamrotationscalingparameters */
*rotScaleA = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x06),0) ;
*rotScaleB = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x0E),0) ;
*rotScaleC = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x16),0) ;
*rotScaleD = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x1E),0) ;
}
void sprite1D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab) void sprite1D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab)
{ {
_OAM_ * spriteInfo = (_OAM_ *)(gpu->oam + (nbShow-1));// + 127; _OAM_ * spriteInfo = (_OAM_ *)(gpu->oam + (nbShow-1));// + 127;
@ -1253,76 +1317,23 @@ void sprite1D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab)
for(i = 0; i<nbShow; ++i, --spriteInfo) /* check all sprites */ for(i = 0; i<nbShow; ++i, --spriteInfo) /* check all sprites */
{ {
s32 sprX;
s32 sprY;
s32 x = 0;
u32 lg;
size sprSize; size sprSize;
s32 y; s32 sprX, sprY, x, y, lg;
u8 prio;
u8 * src;
u8 * pal;
u16 i,j , rotScaleIndex;
int xdir; int xdir;
u8 prio, * src, * pal;
u16 i,j;
u16 rotScaleA,rotScaleB,rotScaleC,rotScaleD;
u16 rotScaleA,rotScaleB,rotScaleC,rotScaleD ;
// get sprite location and size
sprX = (spriteInfo->X<<23)>>23;
sprY = spriteInfo->Y;
sprSize = sprSizeTab[spriteInfo->Size][spriteInfo->Shape];
lg = sprSize.x;
if(sprY>192)
sprY = (s32)((s8)(spriteInfo->Y));
/* FIXME: for rot/scale, a list of entries into the sprite should be maintained, that tells us where the first pixel */
/* of a screenline starts in the sprite, and how a step to the right in a screenline translates within the sprite */
if( (spriteInfo->RotScale == 2) || /* rotscale == 2 => sprite disabled */
(l<sprY)||(l>=sprY+sprSize.y) || /* sprite occupies only lines outside the current drawn line */
(sprX==256) ) /* sprite is outside our line */
continue; /* for all these problems, continue with the next sprite */
// sprite portion out of the screen (LEFT)
if(sprX<0)
{
if(sprX+sprSize.x<0) continue; // fully out of screen
lg += sprX;
x = -sprX;
sprX = 0;
// sprite portion out of the screen (RIGHT)
} else if(sprX+sprSize.x >= 256)
lg = 256 - sprX;
y = l - sprY; /* get the y line within sprite coords */
prio = spriteInfo->Priority; prio = spriteInfo->Priority;
// switch TOP<-->BOTTOM
if (spriteInfo->VFlip)
y = sprSize.y - y -1;
// switch LEFT<-->RIGHT
if (spriteInfo->HFlip) {
x = sprSize.x -x -1;
xdir = -1;
} else {
xdir = 1;
}
if (spriteInfo->RotScale & 1) {
// index from 0 to 31
rotScaleIndex = spriteInfo->RotScalIndex + (spriteInfo->HFlip<<1) + (spriteInfo->VFlip << 2);
/* if we need to do rotscale, gather its parameters */
/* http://nocash.emubase.de/gbatek.htm#lcdobjoamrotationscalingparameters */
rotScaleA = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x06),0) ;
rotScaleB = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x0E),0) ;
rotScaleC = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x16),0) ;
rotScaleD = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x1E),0) ;
}
#if 1
if (!compute_sprite_vars(spriteInfo, l, &sprSize, &sprX, &sprY, &x, &y, &lg, &xdir))
continue;
if (spriteInfo->RotScale & 1)
compute_sprite_rotoscale(gpu, spriteInfo,
&rotScaleA, &rotScaleB, &rotScaleC, &rotScaleD);
if (spriteInfo->Mode == 2) { if (spriteInfo->Mode == 2) {
if (spriteInfo->Depth) if (spriteInfo->Depth)
src = gpu->sprMem + (spriteInfo->TileIndex<<block) + ((y>>3)*sprSize.x*8) + ((y&0x7)*8); src = gpu->sprMem + (spriteInfo->TileIndex<<block) + ((y>>3)*sprSize.x*8) + ((y&0x7)*8);
@ -1332,7 +1343,7 @@ void sprite1D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab)
spriteInfo->Depth, lg, sprX, x, xdir); spriteInfo->Depth, lg, sprX, x, xdir);
continue; continue;
} }
#endif
if (spriteInfo->Mode == 3) /* sprite is in BMP format */ if (spriteInfo->Mode == 3) /* sprite is in BMP format */
{ {
/* sprMemory + sprBoundary + 16Bytes per line (8pixels a 2 bytes) */ /* sprMemory + sprBoundary + 16Bytes per line (8pixels a 2 bytes) */
@ -1376,72 +1387,23 @@ void sprite2D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab)
for(i = 0; i<nbShow; ++i, --spriteInfo) for(i = 0; i<nbShow; ++i, --spriteInfo)
{ {
s32 sprX;
s32 sprY;
s32 x = 0;
u32 lg;
size sprSize; size sprSize;
s32 y; s32 sprX, sprY, x, y, lg;
u8 prio; int xdir;
u8 * src; u8 prio, * src, * pal;
u8 * pal; u16 i,j;
u16 i, j; u16 rotScaleA,rotScaleB,rotScaleC,rotScaleD;
int xdir, block; int block;
u16 rotScaleA,rotScaleB,rotScaleC,rotScaleD, rotScaleIndex ;
sprX = (spriteInfo->X<<23)>>23; prio = spriteInfo->Priority;
sprY = spriteInfo->Y;
sprSize = sprSizeTab[spriteInfo->Size][spriteInfo->Shape];
lg = sprSize.x;
if(sprY>192) if (!compute_sprite_vars(spriteInfo, l, &sprSize, &sprX, &sprY, &x, &y, &lg, &xdir))
sprY = (s32)((s8)(spriteInfo->Y));
if( (spriteInfo->RotScale == 2) ||
(l<sprY)||(l>=sprY+sprSize.y) ||
(sprX==256) )
continue; continue;
// sprite portion out of the screen (LEFT) if (spriteInfo->RotScale & 1)
if(sprX<0) compute_sprite_rotoscale(gpu, spriteInfo,
{ &rotScaleA, &rotScaleB, &rotScaleC, &rotScaleD);
if(sprX+sprSize.x<0) continue; // fully out of screen
lg += sprX;
x = -sprX;
sprX = 0;
// sprite portion out of the screen (RIGHT)
} else if(sprX+sprSize.x >= 256)
lg = 256 - sprX;
y = l - sprY;
prio = spriteInfo->Priority;
if (spriteInfo->RotScale & 1) {
// index from 0 to 31
rotScaleIndex = spriteInfo->RotScalIndex + (spriteInfo->HFlip<<1) + (spriteInfo->VFlip << 2);
/* if we need to do rotscale, gather its parameters */
/* http://nocash.emubase.de/gbatek.htm#lcdobjoamrotationscalingparameters */
rotScaleA = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x06),0) ;
rotScaleB = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x0E),0) ;
rotScaleC = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x16),0) ;
rotScaleD = T1ReadWord((u8*)(gpu->oam + rotScaleIndex*0x20 + 0x1E),0) ;
}
// switch TOP<-->BOTTOM
if (spriteInfo->VFlip)
y = sprSize.y - y -1;
// switch LEFT<-->RIGHT
if (spriteInfo->HFlip) {
x = sprSize.x -x -1;
xdir = -1;
} else {
xdir = 1;
}
#if 1
if (spriteInfo->Mode == 2) { if (spriteInfo->Mode == 2) {
if (spriteInfo->Depth) if (spriteInfo->Depth)
src = gpu->sprMem + ((spriteInfo->TileIndex)<<5) + ((y>>3)<<10) + ((y&0x7)*8); src = gpu->sprMem + ((spriteInfo->TileIndex)<<5) + ((y>>3)<<10) + ((y&0x7)*8);
@ -1451,7 +1413,7 @@ void sprite2D(GPU * gpu, u16 l, u8 * dst, u8 * prioTab)
spriteInfo->Depth, lg, sprX, x, xdir); spriteInfo->Depth, lg, sprX, x, xdir);
continue; continue;
} }
#endif
if (spriteInfo->Mode == 3) /* sprite is in BMP format */ if (spriteInfo->Mode == 3) /* sprite is in BMP format */
{ {
if (gpu->dispCnt.bits.OBJ_BMP_2D_dim) // 256*256 if (gpu->dispCnt.bits.OBJ_BMP_2D_dim) // 256*256

View File

@ -852,7 +852,6 @@ void GPU_setMASTER_BRIGHT (GPU *gpu, u16 v);
void GPU_remove(GPU *, u8 num); void GPU_remove(GPU *, u8 num);
void GPU_addBack(GPU *, u8 num); void GPU_addBack(GPU *, u8 num);
void GPU_toggleOBJ(GPU *, u8 disp);
int GPU_ChangeGraphicsCore(int coreid); int GPU_ChangeGraphicsCore(int coreid);

View File

@ -353,9 +353,7 @@ void change_bgx_layer(int layer, gboolean state, Screen scr) {
} }
//fprintf(stderr,"Changed Layer %s to %d\n",layer,state); //fprintf(stderr,"Changed Layer %s to %d\n",layer,state);
} }
void change_obj_layer(gboolean state, Screen scr) {
GPU_toggleOBJ(scr.gpu, state);
}
/* LAYERS MAIN SCREEN ***** ***** ***** ***** */ /* LAYERS MAIN SCREEN ***** ***** ***** ***** */
void on_wc_1_BG0_toggled (GtkToggleButton *togglebutton, gpointer user_data) { void on_wc_1_BG0_toggled (GtkToggleButton *togglebutton, gpointer user_data) {
@ -367,7 +365,7 @@ void on_wc_1_BG2_toggled (GtkToggleButton *togglebutton, gpointer user_data) {
void on_wc_1_BG3_toggled (GtkToggleButton *togglebutton, gpointer user_data) { void on_wc_1_BG3_toggled (GtkToggleButton *togglebutton, gpointer user_data) {
change_bgx_layer(3, gtk_toggle_button_get_active(togglebutton), MainScreen); } change_bgx_layer(3, gtk_toggle_button_get_active(togglebutton), MainScreen); }
void on_wc_1_OBJ_toggled (GtkToggleButton *togglebutton, gpointer user_data) { void on_wc_1_OBJ_toggled (GtkToggleButton *togglebutton, gpointer user_data) {
change_obj_layer(gtk_toggle_button_get_active(togglebutton), MainScreen); } change_bgx_layer(4, gtk_toggle_button_get_active(togglebutton), MainScreen); }
/* LAYERS SECOND SCREEN ***** ***** ***** ***** */ /* LAYERS SECOND SCREEN ***** ***** ***** ***** */
void on_wc_2b_BG0_toggled (GtkToggleButton *togglebutton, gpointer user_data) { void on_wc_2b_BG0_toggled (GtkToggleButton *togglebutton, gpointer user_data) {
@ -379,4 +377,4 @@ void on_wc_2b_BG2_toggled (GtkToggleButton *togglebutton, gpointer user_data)
void on_wc_2b_BG3_toggled (GtkToggleButton *togglebutton, gpointer user_data) { void on_wc_2b_BG3_toggled (GtkToggleButton *togglebutton, gpointer user_data) {
change_bgx_layer(3, gtk_toggle_button_get_active(togglebutton), SubScreen); } change_bgx_layer(3, gtk_toggle_button_get_active(togglebutton), SubScreen); }
void on_wc_2b_OBJ_toggled (GtkToggleButton *togglebutton, gpointer user_data) { void on_wc_2b_OBJ_toggled (GtkToggleButton *togglebutton, gpointer user_data) {
change_obj_layer(gtk_toggle_button_get_active(togglebutton), SubScreen); } change_bgx_layer(4, gtk_toggle_button_get_active(togglebutton), SubScreen); }