gbadev.org forum archive

This is a read-only mirror of the content originally found on forum.gbadev.org (now offline), salvaged from Wayback machine copies. A new forum can be found here.

Graphics > help!! multiple maps won't work for me!!!

#11848 - goro - Tue Oct 21, 2003 4:45 pm

hi,

my bg1 seems to scroll perfectly, but bg2 wont budge an inch (or a pixel in this case!) and if I swap the bg numbers (in the struct-fill in main) bg2 scrolls but not bg1. There's obviously a problem with updating multiple backgrounds but I can't find it!!

here's some of my code...pleaase help!!

Code:

Bg bg1;
Bg bg2;

void EnableBackground(Bg* bg)
{
   u16 temp;
   bg->tileData = (u16*)CharBaseBlock(bg->charBaseBlock);
   bg->mapData = (u16*)ScreenBaseBlock(bg->screenBaseBlock);
   temp = bg->size | (bg->charBaseBlock<<CHAR_SHIFT) | (bg->screenBaseBlock<<SCREEN_SHIFT)
      | bg->colorMode | bg->mosaic | bg->wraparound;

   switch(bg->number)
   {
   case 0:
      {
         REG_BG0CNT = temp;
         REG_DISPCNT |= BG0_ENABLE;
      }break;
   case 1:
      {
         REG_BG1CNT = temp;
         REG_DISPCNT |= BG1_ENABLE;
      }break;
   case 2:
      {
         REG_BG2CNT = temp;
         REG_DISPCNT |= BG2_ENABLE;
      }break;
   case 3:
      {
         REG_BG3CNT = temp;
         REG_DISPCNT |= BG3_ENABLE;
      }break;

   default:break;

   }
}


void UpdateBackground(Bg* bg)
{
   switch(bg->number)
   {
   case 0:
      REG_BG0HOFS = bg->x_scroll;
      REG_BG0VOFS = bg->y_scroll;
      break;
   case 1:
      REG_BG1HOFS = bg->x_scroll;
      REG_BG1VOFS = bg->y_scroll;
      break;
   case 2:
      if(!(REG_DISPCNT & MODE_0))//it is a rot background
      {
         REG_BG2X = bg->DX;
         REG_BG2Y = bg->DY;

         REG_BG2PA = bg->PA;
         REG_BG2PB = bg->PB;
         REG_BG2PC = bg->PC;
         REG_BG2PD = bg->PD;
      }
      else  //it is a text background
      {
         REG_BG2HOFS = bg->x_scroll;
         REG_BG2VOFS = bg->y_scroll;
      }
      break;
   case 3:
      if(!(REG_DISPCNT & MODE_0))//it is a rot background
      {
         REG_BG3X = bg->DX;
         REG_BG3Y = bg->DY;

         REG_BG3PA = bg->PA;
         REG_BG3PB = bg->PB;
         REG_BG3PC = bg->PC;
         REG_BG3PD = bg->PD;
      }
      else //it is a text background
      {
         REG_BG3HOFS = bg->x_scroll;
         REG_BG3VOFS = bg->y_scroll;
      }
      break;
   default: break;
   }
}

Code:
if(!(*KEYS & KEY_RIGHT))
   {
      
      if ( bg1.x_scroll < 1792 ) // stop scrolling at far right.
      {         
         if (hero_posx < 100)
         {
            hero_posx++;
            // other stuff
         }
         else
         {
         bg2.x_scroll++;
         bg1.x_scroll++;
         ScrollBg();
         
         // other stuff
         }
      }
      else
      {
         hero_posx++;
         // other stuff      }
      
   }


Code:
int main(void)
{
   
   u16 loop;
   
   // Bg initialisation
   SetMode( MODE_0 | BG1_ENABLE | BG2_ENABLE | OBJ_MAP_1D | OBJ_ENABLE);

   bg1.charBaseBlock = 0;
   bg1.colorMode = BG_COLOR16;
   bg1.mosaic = 0;
   bg1.screenBaseBlock = 28;
   bg1.size = TEXTBG_SIZE_256x256;
   bg1.x_scroll = 8;
   bg1.y_scroll = 80;
   bg1.number = 1;

   bg2.charBaseBlock = 16;
   bg2.colorMode = BG_COLOR16;
   bg2.mosaic = 0;
   bg2.screenBaseBlock = 30;
   bg2.size = TEXTBG_SIZE_256x256;
   bg2.x_scroll = 8;
   bg2.y_scroll =80;
   bg2.number = 2;

   EnableBackground(&bg1);
   EnableBackground(&bg2);

Code:
while(1)
   {
      
      GetInput();    //check for input
      WaitForVblank();

      //waits for the screen to stop drawing
      UpdateBackground(&bg2); //make sure registers are updated if anything changes e.g. scrolling
      UpdateBackground(&bg1);
      
      CopyOAM();// Update sprite stuff
      

            
      }


Last edited by goro on Wed Oct 22, 2003 1:28 pm; edited 1 time in total

#11851 - sajiimori - Tue Oct 21, 2003 6:23 pm

Quote:

if(!(REG_DISPCNT & MODE_0))//it is a rot background

That expression is actually true when you're in mode 0, because MODE_0 is defined as 0 (assuming your defines are the same as everybody else's), and anything bitwise-and'ed with 0 is still 0.

You probably wanted this:
Quote:

#define MODE_FIELD 7
if(REG_DISPCNT & MODE_FIELD != MODE_0)

#11865 - goro - Wed Oct 22, 2003 1:35 pm

MODE_FIELD?

that is not defined in my gba.h file. I need to define it where?

I don't think that's the answer because my bg1 scrolls with that code but bg2 will not.

-(I'm trying to create multi-paralax scrolling.)

PLEASE HELP!!!

#11869 - niltsair - Wed Oct 22, 2003 3:19 pm

Yes this is the problem.

BG1 Scroll because it's doesn't evaluate that predicate. BG2 don't because it evaluate that predicate that always return false the way you setup it.

MODE_0 = 0 thus making and AND with this value, will yield 0 with everything.

MODE_FIELD is just a name sajiimori came up with to represent all video mode but Mode_0. Give it another meaningfull name if you want. As fo rthe define, it's right on top of where he's using the value. Just define it wherever you feel like.

Or, if you already you won't be using any other video mode but 0, thne just remove the would 'if xxxxxxxxxxxxxx' predicate.

Code:
if(!(REG_DISPCNT & MODE_0))//it is a rot background
      {
         REG_BG2X = bg->DX;
         REG_BG2Y = bg->DY;

         REG_BG2PA = bg->PA;
         REG_BG2PB = bg->PB;
         REG_BG2PC = bg->PC;
         REG_BG2PD = bg->PD;
      }
      else  //it is a text background
      {
         REG_BG2HOFS = bg->x_scroll;
         REG_BG2VOFS = bg->y_scroll;
      }

TO
         REG_BG2HOFS = bg->x_scroll;
         REG_BG2VOFS = bg->y_scroll; 


*edit* I didn't paid enough attention, and left the wrong part in the code, changed it to be ok.
_________________
-Inside every large program is a small program struggling to get out. (Hoare's Law of Large Programs)
-The man who can smile when things go wrong has thought of someone he can blame it on. (Nixon's Theorem)


Last edited by niltsair on Wed Oct 22, 2003 6:42 pm; edited 1 time in total

#11874 - sajiimori - Wed Oct 22, 2003 6:26 pm

Quote:

that is not defined in my gba.h file. I need to define it where?

Anywhere before you use it. You could simply add it to your gba.h.
Quote:

I don't think that's the answer because my bg1 scrolls with that code but bg2 will not.

Perhaps there is another problem as well, but maybe you should actually try to fix this bug before you come back asking for more help.
Quote:

MODE_FIELD is just a name sajiimori came up with to represent all video mode but Mode_0.

Actually, it's a mask to isolate the bits that specify the video mode (including mode 0). We're isolating the low 3 bits, so its value in binary is 111 (or 7 in decimal).
Quote:

Or, if you already you won't be using any other video mode but 0, thne just remove the would 'if xxxxxxxxxxxxxx' predicate.

True, but only if you erase the right part of the code. The part you left in your example was for modes other than 0. ;-)

#11895 - goro - Thu Oct 23, 2003 8:44 am

Thanks.

It wuz exactly what you guys said.

- Those GBA Junkie tutorials are just so full of bugs!!!

-But I am a newbie so I guess I should accept some responsibility for not noticing them...


Thanks again guys!!!