proc/GenMap(var/x,var/y,var/z,var/floortype,var/walltype,var/iterations)
GenRect(rand(-10,-5)+x,rand(-10,-5)+y,rand(10,5)+x,rand(10,5)+y,z,floortype)
var/list/turf/posswalls=FindValidWalls(z,walltype,floortype)
var/xsize
var/ysize
var/turf/t
var/x1
var/y1
var/x2
var/y2
var/n
for(var/i=1 to iterations)
n=0
while(!n)
t=pick(posswalls)
xsize=rand(1,10)
ysize=rand(1,10)
switch(rand(1,4))
if(1)
x1=t.x-0.5*xsize
x2=t.x+0.5*xsize
y1=t.y+1
y2=t.y+1+ysize
if(2)
x1=t.x-0.5*xsize
x2=t.x+0.5*xsize
y1=t.y-1
y2=t.y-1-ysize
if(3)
x1=t.x+1
x2=t.x+1+xsize
y1=t.y-0.5*ysize
y2=t.y+0.5*ysize
if(4)
x1=t.x-1
x2=t.x-1-xsize
y1=t.y-0.5*ysize
y2=t.y+0.5*ysize
if(IsValidRect(x1,y1,x2,y2,z,walltype)) n=1
GenRect(x1,y1,x2,y2,z,floortype)
new floortype (locate(t.x,t.y,z))
posswalls=FindValidWalls(z,walltype,floortype)
proc/GenRect(var/x1,var/y1,var/x2,var/y2,var/z,var/type)
for(var/turf/t in block(locate(x1,y1,z),locate(x2,y2,z))) new type(t)
proc/FindValidWalls(var/z,var/floortype,var/walltype)
var/list/results=list()
for(var/turf/t in block(locate(1,1,z),locate(world.maxx,world.maxy,z))) if(t.type==walltype) for(var/turf/t2 in range(t,1)) if(t2.type==floortype)
results+=t
break
return results
proc/IsValidRect(var/x1,var/y1,var/x2,var/y2,var/z,var/walltype)
if((x1<1||x2<1||y1<1||y2<1)||(x1>world.maxx||x2>world.maxx||y1>world.maxy||y2>world.maxy)) return 0
for(var/turf/t in block(locate(x1,y1,z),locate(x2,y2,z))) if(t.type!=walltype) return 0
else return 1
Problem description:
Okay, I haven't tested that, but as far as I know it works.
My problem is thus: How do I make that more elegant? It's an ugly, ugly algorithm currently. I'll run through what it's supposed to do:
1 - Generate a room on the centre of the Z-level being created.
2 - Find every wall with a floor square next to it.
3 - Pick one of those walls at random.
4 - Pick a feature at random
5 - Check if there's enough space to generate 'feature' at 'wall'
6 - If yes, generate the feature and go to 2
7 - If no, go to 2.
8 - Repeat until bored.
A secondary problem - What would be a good way to encode a room layout so that I can have non-rectangle features? It would be fairly easy to write a proc to draw hexagons, crosses, etc., but surely there's a way of defining a sort of 'room mask' of turfs to draw. The only thing I can come up with is a multidimensional list, but that's going to be very, very ugly.
Something like that, I dunno.
Or, you can just place objects directly on the template maps and delete them after you are done using them.
Just friendly ideas.