summaryrefslogtreecommitdiffstats
path: root/crawl-ref/source/dat/layout.des
diff options
context:
space:
mode:
authorennewalker <ennewalker@c06c8d41-db1a-0410-9941-cceddc491573>2008-05-17 03:49:50 +0000
committerennewalker <ennewalker@c06c8d41-db1a-0410-9941-cceddc491573>2008-05-17 03:49:50 +0000
commit3e02b2afba0e18c584f423ab303cbb24ba4ef313 (patch)
tree4d0b996775c7e98d7dca8e351e6cb71d92c6f7d9 /crawl-ref/source/dat/layout.des
parentad41d5694a9a1c298965910184fefe6ac3e677db (diff)
downloadcrawl-ref-3e02b2afba0e18c584f423ab303cbb24ba4ef313.tar.gz
crawl-ref-3e02b2afba0e18c584f423ab303cbb24ba4ef313.zip
Outsourced the cross and the large octagon room to the (new) layout.des file. The octagon room is especially more random now, with different types, sizes, and numbers of pillars as well as more interesting stair placement.
Vaults with the "layout" tag: 1) Aren't ever chosen as a random vault. 2) Are treated as normal level, so that other vaults can be placed over top. 3) Should probably be encompassing. 4) Currently only occur with the same frequency as the cross/octagon did. git-svn-id: https://crawl-ref.svn.sourceforge.net/svnroot/crawl-ref/trunk@5096 c06c8d41-db1a-0410-9941-cceddc491573
Diffstat (limited to 'crawl-ref/source/dat/layout.des')
-rw-r--r--crawl-ref/source/dat/layout.des303
1 files changed, 303 insertions, 0 deletions
diff --git a/crawl-ref/source/dat/layout.des b/crawl-ref/source/dat/layout.des
new file mode 100644
index 0000000000..0727074e79
--- /dev/null
+++ b/crawl-ref/source/dat/layout.des
@@ -0,0 +1,303 @@
+###############################################################################
+# layout.des: All large layout vaults go here. These are defined by having
+# both ORIENT: encompass and TAGS: layout. These are not true
+# vaults, in that the dungeon builder can add other vaults on
+# top of them.
+#
+###############################################################################
+
+lua {{
+ function fill_area(x1, y1, x2, y2, feature)
+ for x = x1, x2 do
+ for y = y1, y2 do
+ dgn.grid(x, y, feature)
+ end
+ end
+ end
+
+ function octa_room(x1, y1, x2, y2, oblique, floor)
+ local ob_temp = oblique
+
+ local rock_wall = dgn.feature_number("rock_wall")
+ local shallow_water = dgn.feature_number("shallow_water")
+
+ for x = x1, x2 do
+ for y = y1 + ob_temp, y2 - ob_temp do
+ if dgn.grid(x, y) == rock_wall then
+ dgn.grid(x, y, floor)
+ end
+ if dgn.grid(x, y) == floor and floor == shallow_water then
+ dgn.grid(x, y, shallow_water)
+ end
+ end
+
+ if x > x2 - oblique then
+ ob_temp = ob_temp + 1
+ elseif ob_temp > 0 then
+ ob_temp = ob_temp - 1
+ end
+ end
+ end
+
+ function pillars(center_x, center_y, num, flip_x, big_radius,
+ pillar_radius, pillar_routine, fill)
+ for i = 0, num - 1 do
+ local angle = i * 2 * math.pi / num
+ local x = math.floor(math.cos(angle) * big_radius * flip_x + 0.5)
+ local y = math.floor(math.sin(angle) * big_radius + 0.5)
+
+ pillar_routine(center_x + x, center_y + y, pillar_radius, fill)
+ end
+ end
+
+ -- begin pillar functions
+ function pillar_square(center_x, center_y, radius, fill)
+ for x = -radius, radius do
+ for y = -radius, radius do
+ dgn.grid(center_x + x, center_y + y, fill)
+ end
+ end
+ end
+
+ function pillar_rounded_square(center_x, center_y, radius, fill)
+ for x = -radius, radius do
+ for y = -radius, radius do
+ if math.abs(x) ~= radius or math.abs(y) ~= radius then
+ dgn.grid(center_x + x, center_y + y, fill)
+ end
+ end
+ end
+ end
+
+ function pillar_circle(center_x, center_y, radius, fill)
+ for x = -radius, radius do
+ for y = -radius, radius do
+ if x * x + y * y < radius * radius then
+ dgn.grid(center_x + x, center_y + y, fill)
+ end
+ end
+ end
+ end
+ -- end pillar functions
+
+ function select_from_weighted_table(tb)
+ local value = nil
+ local rollsize = 0
+ for temp_val, temp_weight in pairs (tb) do
+ if rollsize == 0 then
+ value = temp_val
+ rollsize = temp_weight
+ else
+ rollsize = rollsize + temp_weight
+ if crawl.random2(rollsize) < temp_weight then
+ value = temp_val
+ end
+ end
+ end
+
+ return value
+ end
+
+ -- Randomly selects a grid with feature 'search' and sets it to 'replace'
+ function replace_random(search, replace)
+ local gxm, gym = dgn.max_bounds()
+
+ local feature = nil, x, y
+ while feature ~= search do
+ x = crawl.random2(gxm)
+ y = crawl.random2(gym)
+ feature = dgn.grid(x, y)
+ end
+
+ dgn.grid(x, y, replace)
+ end
+
+ function valid(x, y)
+ local gxm, gym = dgn.max_bounds()
+ return (x >= 0 and y >= 0 and x < gxm and y < gym)
+ end
+
+ -- Walks from x, y along dx,dy until it finds 'search'
+ function replace_first(x, y, dx, dy, search, replace)
+
+ local feature = dgn.grid(x, y)
+
+ while feature ~= search and valid(x,y) do
+ x = x + dx
+ y = y + dy
+ feature = dgn.grid(x, y)
+ end
+
+ if valid(x, y) then
+ dgn.grid(x, y, replace)
+ return true
+ else
+ return false
+ end
+ end
+}}
+
+##############################################################
+# layout_cross
+#
+# This replaces dungeon.cc:_plan_2(). It creates a large cross
+# of varying width.
+#
+NAME: layout_cross
+ORIENT: encompass
+TAGS: layout allow_dup
+
+{{
+ local width = 5 - crawl.random2(5)
+ local height = 5 - crawl.random2(5)
+
+ local gxm, gym = dgn.max_bounds()
+
+ local wall = dgn.feature_number("rock_wall")
+ local floor = dgn.feature_number("floor")
+
+ -- Include a small possibility of adding windows around the cross.
+ -- This layout can get used with spotty_level, so don't make this
+ -- chance too large as lava/water prevents that from happening.
+ local window = crawl.one_chance_in(20)
+
+ if window or crawl.one_chance_in(20) then
+ if crawl.coinflip() then
+ wall = dgn.feature_number("lava")
+ else
+ wall = dgn.feature_number("deep_water")
+ end
+ end
+
+ -- fill with rock
+ fill_area(0, 0, gxm-1, gym-1, wall)
+
+ -- create window
+ if window then
+ local clear = dgn.feature_number("clear_rock_wall")
+ fill_area(10, gym/2 - height - 1, gxm - 10, gym/2 - height - 1, clear)
+ fill_area(10, gym/2 + height + 1, gxm - 10, gym/2 + height + 1, clear)
+ fill_area(gxm/2 - width - 1, 10, gxm/2 - width - 1, gym - 10, clear)
+ fill_area(gxm/2 + width + 1, 10, gxm/2 + width + 1, gym - 10, clear)
+ end
+
+ -- create a cross
+ fill_area(10, gym/2 - height, gxm - 10, gym/2 + height, floor)
+ fill_area(gxm/2 - width, 10, gxm/2 + width, gym - 10, floor)
+
+ -- TODO enne - add lua function for spotty()
+}}
+MAP
+.
+ENDMAP
+
+##############################################################
+# layout_big_octagon
+#
+# This replaces dungeon.cc:_plan_6(). It has an octagonal
+# room with some number of pillars in the middle. The stairs
+# are generally all grouped together.
+#
+
+NAME: layout_big_octagon
+ORIENT: encompass
+TAGS: layout allow_dup
+
+{{
+ local gxm, gym = dgn.max_bounds()
+ local wall = dgn.feature_number("rock_wall")
+ local floor = dgn.feature_number("floor")
+
+ local oblique = 10 + crawl.random2(20)
+
+ -- Step 1: Create octagon
+ fill_area(0, 0, gxm - 1, gym - 1, wall)
+ octa_room(10, 10, gxm - 10, gym - 10, oblique, floor)
+
+ -- Step 2: Add pillars
+
+ -- pillar types and relative weights
+ local pillar_fill = {
+ ["rock_wall"] = 15,
+ ["green_crystal_wall"] = 5,
+ ["metal_wall"] = 4,
+ ["clear_rock_wall"] = 3,
+ ["deep_water"] = 2,
+ ["lava"] = 1,
+ }
+ local fill = dgn.feature_number(select_from_weighted_table(pillar_fill))
+
+ -- Potential pillar drawing routines
+ local pillar_func = {pillar_circle, pillar_square, pillar_rounded_square}
+
+ -- Pillar size params
+ -- NOTE: Be careful about tweaking the ranges here. Pillars that are
+ -- too large, close, or large in number can entirely surround the center.
+ local type = crawl.random2(#pillar_func) + 1
+ local num = 3 + crawl.random2(9)
+ local pillar_radius = 1 + crawl.random2(3)
+ local circle_radius = 2 + crawl.random2(6) + pillar_radius * 2 + num / 2
+
+ -- beautification hack: no "circle" pillars of radius 1
+ if type == 1 and pillar_radius == 1 then
+ fill = dgn.feature_number("stone_arch")
+ end
+
+ -- Finally, make the pillars
+ pillars(gxm/2, gym/2, num, 1, circle_radius, pillar_radius,
+ pillar_func[type], fill)
+
+ -- Step 3: Create stairs
+
+ -- Potential stair locations
+ -- 0) random
+ -- 1) inside
+ -- 2) up
+ -- 3) right
+ -- 4) down
+ -- 5) left
+
+ local up_loc = crawl.random2(6)
+ local down_loc = crawl.random2(6)
+ while up_loc == down_loc do
+ down_loc = crawl.random2(6)
+ end
+
+ local up_stairs = {
+ dgn.feature_number("stone_stairs_up_i"),
+ dgn.feature_number("stone_stairs_up_ii"),
+ dgn.feature_number("stone_stairs_up_iii"),
+ }
+ local down_stairs = {
+ dgn.feature_number("stone_stairs_down_i"),
+ dgn.feature_number("stone_stairs_down_ii"),
+ dgn.feature_number("stone_stairs_down_iii"),
+ }
+ local full_stair_set = {[up_loc] = up_stairs, [down_loc] = down_stairs}
+
+ for loc, stair_list in pairs (full_stair_set) do
+ for i = 1, #stair_list do
+ local st = stair_list[i]
+ local ret = true
+
+ if loc == 0 then
+ replace_random(floor, stair_list[i])
+ elseif loc == 1 then
+ dgn.grid(gxm/2 + i - 2, gym/2 + 1 - math.abs(i - 2), st)
+ elseif loc == 2 then
+ ret = replace_first(gxm/2 + i - 2, 0, 0, 1, floor, st)
+ elseif loc == 3 then
+ ret = replace_first(gxm - 1, gym/2 + i - 2, -1, 0, floor, st)
+ elseif loc == 4 then
+ ret = replace_first(gxm/2 + i - 2, gym - 1, 0, -1, floor, st)
+ elseif loc == 5 then
+ ret = replace_first(0, gym/2 + i - 2, 1, 0, floor, st)
+ end
+
+ assert(ret)
+ end
+ end
+}}
+MAP
+.
+ENDMAP