Neo TeAm Forum

The 9th. NEO Project for SNES => The 9th. NEO Project for SNES Dev kit. => SNES development section => Topic started by: spinal on June 28, 2010, 03:11:49 AM

Title: How to store level data??
Post by: spinal on June 28, 2010, 03:11:49 AM
OK, currently I am storing my test levels in an array like so...

Code: [Select]
unsigned char LevelMaps[16*14 * 2] = {
1,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,
1,0,0,0,1,0,0,0,0,0,0,0,0,0,0,1,
1,0,0,1,1,0,0,0,0,0,0,0,0,0,0,1,
1,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,6,
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1,3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,

1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,
1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,
1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,
1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,1,
1,0,0,0,0,0,1,0,1,0,1,1,1,1,1,1,
1,0,0,0,0,1,0,0,1,0,0,0,0,0,0,1,
1,0,0,0,1,0,0,0,1,0,0,0,0,0,0,1,
1,0,0,1,0,0,1,0,1,0,0,0,0,0,0,1,
1,0,1,0,0,0,0,0,1,0,0,0,0,0,0,1,
6,0,0,0,0,0,1,0,0,0,0,0,0,0,0,1,
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
3,3,3,3,3,3,3,3,3,3,3,3,3,3,3,1,
1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1
};

However, this is way less than ideal. My game is [hopefully] going to be a room based game, rather than scrolling, so I will require a method of storing these rooms and loading them back. Now, if I were using a modern machine, I would simply create a binary file for each room and name it depending on its location, e.g. room_x_y.bin and then load it when the character wanted to enter that room. I assume that is out of the question on the snes.
Can any suggest a method for storing my rooms?
Title: Re: How to store level data??
Post by: ChillyWilly on June 28, 2010, 03:26:42 AM
The most common method for roms is to just keep binary files (compressed or uncompressed) and then incbin them into the game at the proper place. You can also use a rom filesystem like romfs to read the files from rom into ram, pretending the rom is a drive.
Title: Re: How to store level data??
Post by: spinal on June 28, 2010, 03:34:56 AM
Are you saying I can load the room data from separate files?
Title: Re: How to store level data??
Post by: mic_ on June 28, 2010, 04:00:52 AM
If that's how you want to organize them.
Just incbin every level and memcpy the current level to another array. If the player can't alter the level (e.g. by blowing up a wall) you don't even need to do a memcpy, you can just point to the original data.
The other part is to write the correct nametable data to VRAM based on the currently loaded level, but that should just be a simple loop.
Title: Re: How to store level data??
Post by: Conle on June 28, 2010, 11:37:29 AM
The easiest way is to use a rom filsystem like ChillyWilly suggested.  :D
(Actually i've been working on such a rom filesystem that makes things much easier but still haven't found the time to finish it.)  ::sm-03::  O0O

The next thing you can do(for the tilemaps only) is to create a binary file with all tilemaps , then ""bin2c" it" , include it as
a constant array(make sure to use mic_'s constify tool because the snesc compiler doesn't like too much consts and can put
some of them into ram section) , then , lets say you have 32tilemap layers ( (width * height) * layers):

Code: [Select]
const unsigned char map[] = //actual "file" size is (width * height)*layers
{

};

const int mapSize = ..
const int maxTilesPerLayer = (width*height)
const int maxLayers =

Then you can make a simple function to load the map:
Code: [Select]

int loadRoom(int roomIndex,.. ? )
{
if( roomIndex >= maxLayers) //or roomIndex * maxTilesPerLayer >= mapSize
return out of bounds

copyToVram((map + (roomIndex * maxTilesPerLayer)),maxTilesPerLayer)
return all ok!
}



And if you wish to define which "exit-type tile" opens which room , you can just add a few extra info on top of each map:

Code: [Select]
1Byte - number of "links"
0...links
{
           1Byte - associated_tile_x
           1Byte - associated_tile_y
           1Byte - associated_tile_which_room_index_loads
           1Byte - for padding
}

Then with a few changes , we have :
Code: [Select]
const unsigned char map[] =
{

};

const int mapSize = ..
const int maxTilesPerLayer = (width*height)
const int maxLayers =

Then you can make a simple function to load the map:
Code: [Select]

int loadRoom(int roomIndex,.. ? )
{
volatile const unsigned char* p;
short links;
short index;

if( roomIndex >= maxLayers)
return out of bounds

links = (short)*(map + (roomIndex * maxTilesPerLayer);

if(!links)
copyToVram((map + (roomIndex * maxTilesPerLayer)+1),maxTilesPerLayer)
else
{
p = (map + (roomIndex * maxTilesPerLayer)+1);

for(index = 0; index < links; index++,p += 4)
{
tileX = *(p + index);
tileY = *(p + (index+1));
roomToLoad = *(p + (index+2));

Configure here your list with those special tiles so that when player is standing on tileY,tileX will be moved to "roomToLoad"
}

copyToVram(p,maxTilesPerLayer)
}

return all ok!
}


I hope it helped you somehow  :D  :D
Title: Re: How to store level data??
Post by: mic_ on June 28, 2010, 01:05:19 PM
Quote
The next thing you can do(for the tilemaps only) is to create a binary file with all tilemaps , then ""bin2c" it" , include it as
a constant array(make sure to use mic_'s constify tool because the snesc compiler doesn't like too much consts and can put
some of them into ram section) , then , lets say you have 32tilemap layers ( (width * height) * layers)

No need for that  ;D
If he already has the maps as a set of binary files then he can just do this in an assembly file:

Code: [Select]
.include "hdr.asm"

.section ".rodata_levels" superfree

level1_data:
.incbin "level1.bin"

level2_data:
.incbin "level2.bin"

; and so on..

.ends

And then in the C code:

Code: [Select]
extern char level1_data[];  // or whatever type you want it to be
extern char level2_data[];
// ...
Title: Re: How to store level data??
Post by: Conle on June 28, 2010, 01:22:43 PM
No need for that  ;D
If he already has the maps as a set of binary files then he can just do this in an assembly file:

Code: [Select]
.include "hdr.asm"

.section ".rodata_levels" superfree

level1_data:
.incbin "level1.bin"

level2_data:
.incbin "level2.bin"

; and so on..

.ends

And then in the C code:

Code: [Select]
extern char level1_data[];  // or whatever type you want it to be
extern char level2_data[];
// ...

Yep , that's the same thing  :D .... unless he's making pc support tools to design his maps , then it would me much easier to compile all his maps into a single object :D