So, I have a general idea of how this code should work in my head, but trying to figure out how to get it into code isn't working too well. I've been searching the forums a bit, and found this (http://www.adventuregamestudio.co.uk/forums/index.php?topic=53415.msg636533407#msg636533407) which talks about pretty much what I was thinking about. I just can't figure out how to get started. The main part I'm trying to figure out right now is getting a grid made that I can work with. I've tried using arrays, and I've messed a bit with structs, but the way I was doing that required a dynamic array within the struct, which is apparently a no-no. So if anyone has some helpful tricks, I'd greatly appreciate it.
I've been working on a procedurally generated RPG. I've put it down for now, but here's how I handle 2D arrays.
GlobalScript.ash
#define GRID_WIDTH 20
#define GRID_HEIGHT 12
GlobalScript.asc
int gridArray[];
// called when the game starts, before the first room is loaded
function game_start() {
gridArray = new int[GRID_WIDTH * GRID_HEIGHT];
}
// sets the cell in the grid to the specified value
void set_grid(int x, int y, int value) {
int i = (x + (GRID_WIDTH * y));
gridArray[i] = value;
}
// returns the value stored in the specified cell
int get_grid(int x, int y) {
int i = (x + (GRID_WIDTH * y));
return gridArray[i];
}
You can also get the xy position based on the supplied array index by:
int i = //the array index
int x = (i % GRID_WIDTH);
int y = (i / GRID_WIDTH);
This would come in useful if you wanted to loop through every cell in the grid to do stuff and things.
So I've been working from your code and came up with this. I feel it should be working, but it stays stuck in a loop. I'm thinking it might be because X_Axis isn't a float, and so can't create a remainder. If that were the case, is there a way to turn it into a float that is also a number for an array?
// main global script file
bool Ready = false;
bool RoomLoc[];
export RoomLoc;
function MazeMake(){
RoomLoc = new bool[X_Axis * Y_Axis];
RoomLoc[X_Axis/Y_Axis] = true;
RoomCount --;
while (RoomCount > 0){
int RoomCall = Random((X_Axis * Y_Axis)-1);
if (RoomLoc[RoomCall] == false){
if (RoomCall - X_Axis > 0){
if (RoomLoc[RoomCall - X_Axis] == true){
RoomLoc[RoomCall] = true;
RoomCount --;
}
}
else if (RoomCall + X_Axis < ((X_Axis * Y_Axis) - 1) ){
if (RoomLoc[RoomCall + X_Axis] == true){
RoomLoc[RoomCall] = true;
RoomCount --;
}
}
else if (RoomCall % X_Axis != 0){
if (RoomLoc[RoomCall-1] == true){
RoomLoc[RoomCall] = true;
RoomCount --;
}
}
else if ((RoomCall + 1) % X_Axis != 0){
if (RoomLoc[RoomCall+1] == true){
RoomLoc[RoomCall] = true;
RoomCount --;
}
}
}
}
while (Ready == false){
int Startit = Random((X_Axis * Y_Axis)-1);
if (RoomLoc[Startit] == true){
StartingLocal = Startit;
Ready = true;
}
}
}
I believe the command is IntToFloat or something like that...The autofiller should figure it out, or if not there's always the manual...
I'm having trouble understanding what exactly is going on in your code, especially since there's no comments.
I've quickly put something together, it's not tested. You'd have to modify it for your own variable names.
// pick a random cell in the grid, if there's a neighbour room then place one here too
void build_level {
set_grid(GRID_WIDTH/2, GRID_HEIGHT/2, true); // the starting room
#define MAX_ROOMS 10
int roomsMade = 0;
while (roomsMade < MAX_ROOMS) {
// The loop could possibly run too many times here if the program keeps choosing an invalid (no neighbours) cell.
int cell = Random((GRID_WIDTH * GRID_HEIGHT) - 1);
int x = (cell % GRID_WIDTH);
int y = (cell / GRID_WIDTH);
// Now you will want to add some array overflow checks here, eg: if we chose a cell at the bottom of the grid
// and we try to find a cell below it, that would be outside of the array.
bool foundNeighbour = get_grid(x-1, y);//left
if (foundNeighbour == false) {foundNeighbour = get_grid(x+1, y);}//right
if (foundNeighbour == false) {foundNeighbour = get_grid(x, y-1);}//up
if (foundNeighbour == false) {foundNeighbour = get_grid(x, y+1);}//down
if (foundNeighbour == true) {
set_grid(x, y, true);
roomsMade++;
}
}
}
EDIT: Just thought to avoid going off grid.
// The loop could possibly run too many times here if the program keeps choosing an invalid (no neighbours) cell.
//int cell = Random((GRID_WIDTH * GRID_HEIGHT) - 1);
//int x = (cell % GRID_WIDTH);
//int y = (cell / GRID_WIDTH);
// the edge cells on the grid are always ignored (a border of 1 cell thick)
int x = (1 + Random(GRID_WIDTH - 2));
int y = (1 + Random(GRID_HEIGHT - 2));