Homebrew Understanding libdns oamAllocateGfx

  • Thread starter Thread starter BluFox
  • Start date Start date
  • Views Views 1,291
  • Replies Replies 2

BluFox

New Member
Newbie
Joined
Jan 18, 2023
Messages
2
Reaction score
1
Trophies
0
Age
46
XP
72
Country
United States
Hey all, I'm getting started with libdns and the sprites system. Trying to get a good understanding on what `oamAllocateGfx` does. My understanding is that the DS has memory banks which the sprite system / oam is able to reference for drawing sprites. And that you're options are to either dma copy a whole sprite sheet in to the bank, or you can use `oamAllocateGfx` which acts like a kind of memory manager like malloc to load and unload sprites. From what I can tell, the data returned from this function is a pointer to the vram memory we can copy in to. I put together a little test program but I'm getting unexpected results.

C++:
#include <nds.h>
#include <stdio.h>

int main()
{

    videoSetModeSub(MODE_0_2D);

    consoleDemoInit();

    // initialize the sub sprite engine with 1D mapping 128 byte boundary
    // and no external palette support
    oamInit(&oamSub, SpriteMapping_Bmp_1D_128, false);

    vramSetBankD(VRAM_D_SUB_SPRITE);

    u16 *gfx = oamAllocateGfx(&oamSub, SpriteSize_32x32, SpriteColorFormat_Bmp);
    printf("pointer1 %hu\n", &gfx);
    u16 *gfx2 = oamAllocateGfx(&oamSub, SpriteSize_32x32, SpriteColorFormat_Bmp);
    printf("pointer2 %hu\n", &gfx2);

    u16 *gfx3 = oamAllocateGfx(&oamSub, SpriteSize_32x32, SpriteColorFormat_Bmp);
    printf("pointer3 %hu\n", &gfx3);

    u16 *gfx4 = oamAllocateGfx(&oamSub, SpriteSize_32x32, SpriteColorFormat_Bmp);
    printf("pointer4 %hu\n", &gfx4);

    while (1)
    {
    }

    swiWaitForVBlank();
}

This allocates a few times and prints the addresses. What confuses me is the addresses are only 4 apart , the color format and size don't change the addresses printed which I'd expect since they would need more space. Is my understanding of this correct? Should I expect the printed addresses to be spaced far enough apart that the sprite fits in the addresses between them? Also since there are multiple vram banks, how does the allocate function know which one we want to allocate to?
 
You're printing the addresses of your pointers, not their content. Using the fixed code below they're starting at 0x06600000 (the start of sub engine OAM memory) and increasing in increments of 0x800 with this size. You decide which bank is used by which bank you map at the start of OBJ VRAM, that's what mapping does. If you map multiple to the same place it'll be in all of them. (they get OR'd when mapping)

Code:
#include <nds.h>
#include <stdio.h>

int main()
{

    videoSetModeSub(MODE_0_2D);

    consoleDemoInit();

    // initialize the sub sprite engine with 1D mapping 128 byte boundary
    // and no external palette support
    oamInit(&oamSub, SpriteMapping_Bmp_1D_128, false);

    vramSetBankD(VRAM_D_SUB_SPRITE);

    u16 *gfx = oamAllocateGfx(&oamSub, SpriteSize_32x32, SpriteColorFormat_Bmp);
    printf("pointer1 %p\n", gfx); // Alternatively 0x%lx\n" (u32)gfx -- same thing
    u16 *gfx2 = oamAllocateGfx(&oamSub, SpriteSize_32x32, SpriteColorFormat_Bmp);
    printf("pointer2 %p\n", gfx2);

    u16 *gfx3 = oamAllocateGfx(&oamSub, SpriteSize_32x32, SpriteColorFormat_Bmp);
    printf("pointer3 %p\n", gfx3);

    u16 *gfx4 = oamAllocateGfx(&oamSub, SpriteSize_32x32, SpriteColorFormat_Bmp);
    printf("pointer4 %p\n", gfx4);

    while (1)
    {
    }

    swiWaitForVBlank();
}
[CODE]
[/SPOILER]
 

Site & Scene News

Popular threads in this forum