🔒 Locked
Generating 2d Terrain..
Advertisement
Original Post
Well, I''m working in Visual Basic to generate terain for a Civilizationesque game. I''ve got the basics down, but adding on the "pretties" are killing me. So far I''ve got over 3 pages of If statements with 4 checks each (north south east west) to know what sorta "pretty" I need to stick on the edge of a land tile to not have that cut off look, and I''ve only made it through the very basic "pretties." Map generation time is aleadly considerably longer on my p3 500 than it was play Civilzation on my 486 66. (In the range of 3-5 seconds for an 80x80 map, i know that''s short, but like i said, i''m only at the begining)
So my question is this, is there any simpler way to do it than just repetative statements like:
If map.GetTile(iX, iY) = 2 And map.GetTile(iX - 1, iY) = 2 And map.GetTile(iX, iY - 1) = 2 And map.GetTile(iX + 1, iY) = 1 And map.GetTile(iX, iY + 1) = 1 Then
map.ChangeTile iX, iY, 12
End If
(2 being water, and 1 being land, and 12 being the pretty doodadd for having land to your right and above you)''
While writing this post I just realized that matters are actually worse than I thought. Some of the doodads are dependant on other doodad''s placed in the first cycle through, so it''s looking like I''m going to have to run a 4th for/next loop just to make sure I get them all in there.
Any suggestions VERY welcome.
So what you are trying to do with the if statements are auto-tile transitions? Just remember, whenever you find yourself stuck with repetitive code, there''s probably always an algorithm that will make it go faster using about 1% of the space the other code took up.
So what you need is a better method to do auto-transitions given you have all the transitions already drawn out in your tile set. There are only three options I can think of:
1. Create a map editor and manually put every tile you need into a map saved on your harddrive, then load the map in the game.
2. Do what is seen in this tutorial that involves using a bit of binary and partially transparent tiles (the tiles blend into nothing so they can later blend into anything).
3. Don''t draw any transitions, and let alpha masks do the work for you.
Basically, you do not have to use if statements of that nature anywhere. If you are just starting out, method #1 is perfect for you.
So what you need is a better method to do auto-transitions given you have all the transitions already drawn out in your tile set. There are only three options I can think of:
1. Create a map editor and manually put every tile you need into a map saved on your harddrive, then load the map in the game.
2. Do what is seen in this tutorial that involves using a bit of binary and partially transparent tiles (the tiles blend into nothing so they can later blend into anything).
3. Don''t draw any transitions, and let alpha masks do the work for you.
Basically, you do not have to use if statements of that nature anywhere. If you are just starting out, method #1 is perfect for you.
Ahh, another VB gamer coder! What I did was have the map editor scan through and make the modifications to my map array before writing it to the map file. As far as algorithms go, I recommend giving each terrain type a precedence. That is, each tile type has a number, grass would be higher than dirt, sand higher than water, etc. Then, scan through your map array and check the precedence number of the current tile against those around it and add the transitions. This would eliminate the lengthy IF...THEN statements since all the algorithm needs is a number.
Heh, I''d begun to think I was the only VB programer reading these boards.
I already have a sort of precidence, but It''s actually running the other way ''round right now. Heh, I guess i''ll have to re-sort my tileset. Though at current, I only have water, grass, and dirt, and dirt/water, dirt/grass transitions, cause I''m wanting to keep it simple.
The map editor is something I will do (and already know how to), however, at current I''m working on random generation of landmasses. The second option is one I thought about, and am still thinking about, but the only way I can think of to implement that is using Layers on the map. That''s something I intend to do, but I also want the water/dirt transition to be walkable. Walkability is currently based soley on tile number, using a Layer to do transition overlays wouldn''t change the base tile number, and would thus leave the water/dirt overlays unwalkable. The third solution is also unworkable, as I''m using 2D directX 7, and have absolutely no knowledge of alpha blending...
As to creating an algorythm, it sounds like a good idea, but I''m not quite sure how to go about making it know which transitions to use when. Do I need to line my tileset up so I can do it mathmatically? The idea sort of makes sense, but I don''t see how to organize my tile set to make it work with out a LOT of math.
I already have a sort of precidence, but It''s actually running the other way ''round right now. Heh, I guess i''ll have to re-sort my tileset. Though at current, I only have water, grass, and dirt, and dirt/water, dirt/grass transitions, cause I''m wanting to keep it simple.
The map editor is something I will do (and already know how to), however, at current I''m working on random generation of landmasses. The second option is one I thought about, and am still thinking about, but the only way I can think of to implement that is using Layers on the map. That''s something I intend to do, but I also want the water/dirt transition to be walkable. Walkability is currently based soley on tile number, using a Layer to do transition overlays wouldn''t change the base tile number, and would thus leave the water/dirt overlays unwalkable. The third solution is also unworkable, as I''m using 2D directX 7, and have absolutely no knowledge of alpha blending...
As to creating an algorythm, it sounds like a good idea, but I''m not quite sure how to go about making it know which transitions to use when. Do I need to line my tileset up so I can do it mathmatically? The idea sort of makes sense, but I don''t see how to organize my tile set to make it work with out a LOT of math.
I''m planning to do something similar, having a procedurally generated 2D map, and let it choose the transitions automatically. Please share any info you might find, If you wouldn''t mind.
My idea was also to use an army of if''s but maybe there is an easier way.
My idea was also to use an army of if''s but maybe there is an easier way.
It's ugly that way isn't it? Well, for the moment I'm letting that sit while idea's stew in the back of my head, and working on the UI side of things, but I did come up with an idea that would get about 70% of the doodad's applied on the the first iteration I think.
Whenever you add a new tile of land, completely surround it with the proper doodad's (Unless a doodad would replace a full land square). Now, for the purpose of land generation, you ignore these doodad's (So if you chose a square to add land to, and it already has a doodad in it, add the land anyway.) Doing this would handle all the straight edge doodad's completely, with no extra if checks. Leaving you only the corner, and tip doodad's to bruteforce into the map.
Unfortunatly, I don't think this would work nearly as well for transitions between anything but (blank)/Water, because other's might accidently modify the landmass you've created and look funky.
Hmm. Perhaps a dual approach? (Blank)/water doodad's applied like said above, and all other doodad's done via layers with transparancy?
edit: dumb mistake
[edited by - zendarva on July 1, 2003 8:33:42 AM]
Whenever you add a new tile of land, completely surround it with the proper doodad's (Unless a doodad would replace a full land square). Now, for the purpose of land generation, you ignore these doodad's (So if you chose a square to add land to, and it already has a doodad in it, add the land anyway.) Doing this would handle all the straight edge doodad's completely, with no extra if checks. Leaving you only the corner, and tip doodad's to bruteforce into the map.
Unfortunatly, I don't think this would work nearly as well for transitions between anything but (blank)/Water, because other's might accidently modify the landmass you've created and look funky.
Hmm. Perhaps a dual approach? (Blank)/water doodad's applied like said above, and all other doodad's done via layers with transparancy?
edit: dumb mistake
[edited by - zendarva on July 1, 2003 8:33:42 AM]
The algorithm would work like this:
This code only does horizontal transitions and doesn''t allow for edge tiles and so forth, but it should get across the idea. I would arrange your tileset so you can set tile programmatically, IE. have all your basic tiles arranged horizontally and their various transitions below them vertically by order of precedence. This way when you set the new tile, you simply take the current tile''s X value and add the precedence value to the Y.
For X=0 to 99
For Y=0 to 99
TilePrecedence=Map(X,Y).TilePrecedence '' Get precedence of the current tile
TilePrecedenceLeft=Map(X-1,Y).TilePrecedence '' Get precedence of the tile to the left
If TilePrecedence>TilePrecedenceLeft Then
Map(X-1,Y).Tile=5+TilePrecedent-TilePrecedentLeft '' Set the tile to the left to the transition tile
ElseIf TilePrecedenceMap(X,Y).Tile=10+TilePrecedent-TilePrecedentLeft '' Set the current tile to the transition tile
End If
Next Y
Next X
This code only does horizontal transitions and doesn''t allow for edge tiles and so forth, but it should get across the idea. I would arrange your tileset so you can set tile programmatically, IE. have all your basic tiles arranged horizontally and their various transitions below them vertically by order of precedence. This way when you set the new tile, you simply take the current tile''s X value and add the precedence value to the Y.
quote:
Original post by ZenDarva
Whenever you add a new tile of land, completely surround it with the proper doodad''s
This is roughly how Starcraft did it in the editor I seem to remember.
I''ve come up with the following:
Basically when procedurally generating the terrain, make sure it''s suitable for the transitions. a small example, # is land and ~ is water:
~#~
#~#
###
would turn into:
~~~
###
###
Please note that this is a very crude example, but say if you had all grass tiles, and you place one tile of water, the grass transitions would completely cover the water, turning it back into land, so basically, delete the tile and make it land in the first place.
If you want water, you have to place a larger quantity of it.
it would still require a huge block of really ugly if / else code, but if yu had the map suited for it in the first place, it might be easier to place the transitions.
Loop 1 you just loop through the map, deciding what tiles are unnecessary, and change them to the surrounding tile.
Loop 2 you place all transition tiles (doodad''s)
I haven''t tried this practically, but I think this was about how the Starcraft editor did it.
the problem that I ran across when generating 2d terrain was that it was well random terrain and look that way. So unless your willing to right some algothirms to make it look more realistic then random I'd stick to premade maps.
that being said if you like here is the C++ code for my map generation program.
unsigned short map[MAPSIZE][MAPSIZE];
void MapGen::generateMap()
{
srand((unsigned)time(NULL));
unsigned short T;
unsigned short L;
unsigned short R;
for(int y = 1; y < MAPSIZE-1; y++)
{
for(int x = 1; x < MAPSIZE-1; x++)
{
T=map[x][y-1];
L=map[x-1][y];
R=rand()%10;
if(T==L && R!=0)
map[x][y]=T;
if(T!=L || R==0)
map[x][y]=TRANSITION;
if(L==TRANSITION || T==TRANSITION)
while(1)
{
map[x][y]=rand()%3;
if (map[x][y]!=map[x-2][y])
break;
}
if(T!=L)
map[x][y]=TRANSITION;
}
}
}
[edited by - TechnoGoth on July 8, 2003 3:11:24 AM]
that being said if you like here is the C++ code for my map generation program.
unsigned short map[MAPSIZE][MAPSIZE];
void MapGen::generateMap()
{
srand((unsigned)time(NULL));
unsigned short T;
unsigned short L;
unsigned short R;
for(int y = 1; y < MAPSIZE-1; y++)
{
for(int x = 1; x < MAPSIZE-1; x++)
{
T=map[x][y-1];
L=map[x-1][y];
R=rand()%10;
if(T==L && R!=0)
map[x][y]=T;
if(T!=L || R==0)
map[x][y]=TRANSITION;
if(L==TRANSITION || T==TRANSITION)
while(1)
{
map[x][y]=rand()%3;
if (map[x][y]!=map[x-2][y])
break;
}
if(T!=L)
map[x][y]=TRANSITION;
}
}
}
[edited by - TechnoGoth on July 8, 2003 3:11:24 AM]
Transitions aside, a random map generator isn''t all that difficult. Here''s what you need:
- Let your generating sub-routine take a parameter that tells the procedure what type of map to generator (like Age of Kings with different types of map). Some ideas: islands, continental, artic, etc. This gives the map generator an idea of land distribution, terrain types, etc.
- An example of an island map generator:
1) Lay down water as the base terrain
2) Lay down a clump of grass at least 10 tiles by 10 tiles and less than 20 tiles by 20 tiles (choose this randomly).
3) Repeat step 2 across the map at random points
4) Add eye candy, resources, etc. randomly across land tiles
- It''s pretty simple. A useful routine to write might be one that creates an irregular clump of the terrain that it recieves as an argument. It should also take X, Y, height and width parameters. This will let you create random land masses, ponds, swamps, etc at any point on the map.
- Let your generating sub-routine take a parameter that tells the procedure what type of map to generator (like Age of Kings with different types of map). Some ideas: islands, continental, artic, etc. This gives the map generator an idea of land distribution, terrain types, etc.
- An example of an island map generator:
1) Lay down water as the base terrain
2) Lay down a clump of grass at least 10 tiles by 10 tiles and less than 20 tiles by 20 tiles (choose this randomly).
3) Repeat step 2 across the map at random points
4) Add eye candy, resources, etc. randomly across land tiles
- It''s pretty simple. A useful routine to write might be one that creates an irregular clump of the terrain that it recieves as an argument. It should also take X, Y, height and width parameters. This will let you create random land masses, ponds, swamps, etc at any point on the map.
Topic Locked
This topic has been locked by a moderator. New replies are not allowed.
Sign in to reply to this topic.
Advertisement