summaryrefslogtreecommitdiffstats
path: root/crawl-ref/source
diff options
context:
space:
mode:
authorzelgadis <zelgadis@c06c8d41-db1a-0410-9941-cceddc491573>2007-10-04 05:05:42 +0000
committerzelgadis <zelgadis@c06c8d41-db1a-0410-9941-cceddc491573>2007-10-04 05:05:42 +0000
commit13f47218bbda7251a2521eda0c4a858ea333bbee (patch)
treefef4d2076355461b7c64dedd1676a90351cbc23d /crawl-ref/source
parent92c238f2c7ed33f3ebffc22fe08b1c51f98814b1 (diff)
downloadcrawl-ref-13f47218bbda7251a2521eda0c4a858ea333bbee.tar.gz
crawl-ref-13f47218bbda7251a2521eda0c4a858ea333bbee.zip
Moved all of the bazaar specific logic/code to dat/bazaar (or turned the
code into Lua utility functions which can be reused by things other than bazaars). Related changes: * Portal vault entrances now work if they have destinations ("dst" property) besides "bazaar" (though it still causes an assert if no matchng maps for the destination can be found). * The floor and rock colour for a level are generated once and then stored in the save file, rather than being constantly regenerated (which means that bazaar floor colours are now truly random, rather than being tied to the depth of the bazaar entrance). * The floor and rock colour for a portal vault (or for any level containing any vault) can be set with ROCKCOL and FLOORCOL (which currently only accepts a single colour, unlike COLOUR); there are also Lua functions for querying and setting the colours. * Each portal vault level_type_name can have an associated Lua callback which is called when level generation is complete; it can be used for things like stair fixup. I also moved the Halls of Zot rock/floor colour special casing to the dat/zot.des file, since it was easy once ROCKCOL and FLOORCOL had been implemented. git-svn-id: https://crawl-ref.svn.sourceforge.net/svnroot/crawl-ref/trunk@2314 c06c8d41-db1a-0410-9941-cceddc491573
Diffstat (limited to 'crawl-ref/source')
-rw-r--r--crawl-ref/source/acr.cc31
-rw-r--r--crawl-ref/source/clua.cc3
-rw-r--r--crawl-ref/source/dat/bazaar.des65
-rw-r--r--crawl-ref/source/dat/zot.des59
-rw-r--r--crawl-ref/source/dungeon.cc181
-rw-r--r--crawl-ref/source/dungeon.h5
-rw-r--r--crawl-ref/source/luadgn.cc264
-rw-r--r--crawl-ref/source/mapdef.cc3
-rw-r--r--crawl-ref/source/mapdef.h2
-rw-r--r--crawl-ref/source/misc.cc2
-rw-r--r--crawl-ref/source/tags.cc6
-rw-r--r--crawl-ref/source/util/levcomp.lpp2
-rw-r--r--crawl-ref/source/util/levcomp.ypp21
13 files changed, 507 insertions, 137 deletions
diff --git a/crawl-ref/source/acr.cc b/crawl-ref/source/acr.cc
index 7225fb98be..d78a720368 100644
--- a/crawl-ref/source/acr.cc
+++ b/crawl-ref/source/acr.cc
@@ -734,23 +734,34 @@ static void handle_wizard_command( void )
case 'P':
{
- mpr( "Destination for portal? ", MSGCH_PROMPT );
- get_input_line( specs, sizeof( specs ) );
+ mpr( "Destination for portal (defaults to 'bazaar')? ", MSGCH_PROMPT );
+ if (cancelable_get_line( specs, sizeof( specs ) ))
+ {
+ canned_msg( MSG_OK );
+ return;
+ }
std::string dst = specs;
dst = trim_string(dst);
+ dst = replace_all(dst, " ", "_");
if (dst == "")
- canned_msg( MSG_OK );
- else
+ dst = "bazaar";
+
+ if (find_map_by_name(dst) == -1 &&
+ random_map_for_tag(dst, false) == -1)
{
- grd[you.x_pos][you.y_pos] = DNGN_ENTER_PORTAL_VAULT;
- map_wiz_props_marker
- *marker = new map_wiz_props_marker(you.pos());
- marker->set_property("dst", dst);
- marker->set_property("desc", "wizard portal, dest = " + dst);
- env.markers.add(marker);
+ mprf("No map named '%s' or tagged '%s'.",
+ dst.c_str(), dst.c_str());
+ return;
}
+
+ grd[you.x_pos][you.y_pos] = DNGN_ENTER_PORTAL_VAULT;
+ map_wiz_props_marker
+ *marker = new map_wiz_props_marker(you.pos());
+ marker->set_property("dst", dst);
+ marker->set_property("desc", "wizard portal, dest = " + dst);
+ env.markers.add(marker);
break;
}
diff --git a/crawl-ref/source/clua.cc b/crawl-ref/source/clua.cc
index 9feb395618..2527debaaa 100644
--- a/crawl-ref/source/clua.cc
+++ b/crawl-ref/source/clua.cc
@@ -742,8 +742,6 @@ LUARET1(you_see_grid, boolean,
LUARET1(you_see_grid_no_trans, boolean,
see_grid_no_trans(luaL_checkint(ls, 1), luaL_checkint(ls, 2)))
// increase by 1 because check happens on old level
-LUARET1(bzr_floor_colour, string,
- colour_to_str(bazaar_floor_colour(you.your_level + 2)))
void lua_push_floor_items(lua_State *ls);
static int you_floor_items(lua_State *ls)
@@ -824,7 +822,6 @@ static const struct luaL_reg you_lib[] =
{ "see_grid", you_see_grid },
{ "see_grid_no_trans", you_see_grid_no_trans },
- { "bazaar_floor", bzr_floor_colour },
{ NULL, NULL },
};
diff --git a/crawl-ref/source/dat/bazaar.des b/crawl-ref/source/dat/bazaar.des
index c833208cdf..4f0fa92174 100644
--- a/crawl-ref/source/dat/bazaar.des
+++ b/crawl-ref/source/dat/bazaar.des
@@ -28,6 +28,32 @@ function bazaar_message(e)
e.welcome("You enter an inter-dimensional bazaar!")
end
+function random_bazaar_colour()
+ local colours = {"blue", "red", "lightblue", "magenta", "green"}
+
+ crawl.mpr("#colours = " .. #colours)
+
+ local ret = colours[crawl.random2(#colours) + 1]
+
+ crawl.mpr("ret = " .. ret)
+
+ return ret
+end
+
+function fixup_bazaar()
+ dgn.fixup_stairs("stone_arch", "exit_portal_vault")
+ dgn.floor_halo("enter_shop", "yellow")
+
+ if (dgn.get_floor_colour() == "black") then
+ dgn.change_floor_colour(random_bazaar_colour())
+ end
+
+ if (dgn.get_rock_colour() == "black") then
+ dgn.change_rock_colour("yellow")
+ end
+end
+
+dgn.set_lt_callback("bazaar", "fixup_bazaar")
}}
default-depth: D:10-27
@@ -169,7 +195,10 @@ ENDMAP
# upstair, which will be converted into a stone arch (and on which the player
# will be placed when entering the bazaar). If there's no upstair, the player
# will arrive on a random square.
-
+#
+# You can force a particular colour for the rock walls or floor using
+# ROCKCOL and FLOORCOL directives.
+#
NAME: bazaar_general_marketplace
TAGS: bazaar allow_dup
FLAGS: no_rotate
@@ -248,10 +277,12 @@ ITEM: any jewellery / good_item any jewellery
ITEM: any book / good_item any book, any staff
SUBST: d=.d, e=.e, f=.f
# special cases for blue/red floor
-: if you.bazaar_floor() == "red" then
+: local colour = random_bazaar_colour()
+: _G.floor_colour(colour)
+: if colour == "red" then
SUBST: l = w
: else
-: if you.bazaar_floor() == "blue" then
+: if colour == "blue" then
SUBST: w = l
: end
: end
@@ -279,10 +310,12 @@ KFEAT: B = distillery shop
ITEM: any wand, ring of levitation
SHUFFLE: leAB/wdBA
# special cases for blue/red floor
-: if you.bazaar_floor() == "red" then
+: local colour = random_bazaar_colour()
+: _G.floor_colour(colour)
+: if colour == "red" then
SUBST: l = w
: else
-: if you.bazaar_floor() == "blue" then
+: if colour == "blue" then
SUBST: w = l
: end
: end
@@ -332,11 +365,13 @@ KFEAT: R = stone_arch
KFEAT: S = stone_arch
SHUFFLE: lw
# special cases for blue/red floor
-: if you.bazaar_floor() == "red" then
-SUBST: l : wWx
+: local colour = random_bazaar_colour()
+: _G.floor_colour(colour)
+: if colour == "red" then
+SUBST: l = w
: else
-: if you.bazaar_floor() == "blue" then
-SUBST: w : Wx
+: if colour == "blue" then
+SUBST: w = l
: end
: end
#
@@ -654,8 +689,10 @@ KFEAT: D = antique weapon shop
KFEAT: E = antique armour shop
KFEAT: F = scroll shop / distillery shop
: bazaar_message(_G)
-# special case for floor
-: if you.bazaar_floor() == "blue" then
+# special cases for blue floor
+: local colour = random_bazaar_colour()
+: _G.floor_colour(colour)
+: if colour == "blue" then
SUBST: w = W
: end
#
@@ -778,10 +815,12 @@ SHUFFLE: zZ
SUBST: z = ., Z = w
SHUFFLE: wl, ABCD
# special cases for blue/red floor
-: if you.bazaar_floor() == "red" then
+: local colour = random_bazaar_colour()
+: _G.floor_colour(colour)
+: if colour == "red" then
SUBST: l = w
: else
-: if you.bazaar_floor() == "blue" then
+: if colour == "blue" then
SUBST: w = l
: end
: end
diff --git a/crawl-ref/source/dat/zot.des b/crawl-ref/source/dat/zot.des
index 9edba91f88..0f060a726a 100644
--- a/crawl-ref/source/dat/zot.des
+++ b/crawl-ref/source/dat/zot.des
@@ -6,11 +6,14 @@
##############################################################################
# hall_of_Zot
-NAME: hall_of_Zot
+NAME: hall_of_Zot_5
PLACE: Zot:5
ORIENT: north
LFLAGS: no_tele_control
+FLOORCOL: magenta
+ROCKCOL: lightmagenta
+
#traps
SUBST: C = c:1000 =
KFEAT: 1 = any trap / w:20 floor
@@ -79,6 +82,60 @@ xxxxxxxxxxxcc..............ccxxxc...............cxxxcc..............ccxxxxxxxxxx
xxxxxxxxxxxxccccccccccccccccxxxxcccccccc@ccccccccxxxxccccccccccccccccxxxxxxxxxxx
ENDMAP
+################################################################
+
+# For colouring the walls and floors of the first four levels
+
+NAME: hall_of_Zot_1
+PLACE: Zot:1
+TAGS: transparent
+ORIENT: float
+
+FLOORCOL: lightgrey
+ROCKCOL: lightgrey
+
+MAP
+.
+ENDMAP
+
+###
+
+NAME: hall_of_Zot_2
+PLACE: Zot:2
+TAGS: transparent
+ORIENT: float
+
+FLOORCOL: lightgrey
+ROCKCOL: blue
+
+MAP
+.
+ENDMAP
+
+###
+NAME: hall_of_Zot_3
+PLACE: Zot:3
+TAGS: transparent
+ORIENT: float
+FLOORCOL: blue
+ROCKCOL: lightblue
+
+MAP
+.
+ENDMAP
+###
+
+NAME: hall_of_Zot_4
+PLACE: Zot:4
+TAGS: transparent
+ORIENT: float
+
+FLOORCOL: lightblue
+ROCKCOL: magenta
+
+MAP
+.
+ENDMAP
diff --git a/crawl-ref/source/dungeon.cc b/crawl-ref/source/dungeon.cc
index b07dc20008..343b4a2fe9 100644
--- a/crawl-ref/source/dungeon.cc
+++ b/crawl-ref/source/dungeon.cc
@@ -173,7 +173,7 @@ static char plan_5();
static char plan_6(int level_number);
static bool octa_room(spec_room &sr, int oblique_max,
dungeon_feature_type type_floor);
-static void bazaar_level(int level_number);
+static void portal_vault_level(int level_number);
static void labyrinth_level(int level_number);
static void box_room(int bx1, int bx2, int by1, int by2,
dungeon_feature_type wall_type);
@@ -231,6 +231,9 @@ static void place_altars();
typedef std::list<coord_def> coord_list;
+// MISC FUNCTIONS
+static void dgn_set_floor_colours();
+
//////////////////////////////////////////////////////////////////////////
// Static data
@@ -245,6 +248,9 @@ static bool use_random_maps = true;
static bool dgn_check_connectivity = false;
static int dgn_zones = 0;
+typedef std::map<std::string, std::string> callback_map;
+static callback_map level_type_post_callbacks;
+
/**********************************************************************
* builder() - kickoff for the dungeon generator.
*********************************************************************/
@@ -540,6 +546,12 @@ static void register_place(const vault_placement &place)
set_level_flags(place.map.level_flags.flags_set, true);
unset_level_flags(place.map.level_flags.flags_unset, true);
+
+ if (place.map.floor_colour != BLACK)
+ env.floor_colour = place.map.floor_colour;
+
+ if (place.map.rock_colour != BLACK)
+ env.rock_colour = place.map.rock_colour;
}
static bool ensure_vault_placed(bool vault_success)
@@ -644,6 +656,9 @@ static void reset_level()
}
else
env.level_flags = 0;
+
+ env.floor_colour = BLACK;
+ env.rock_colour = BLACK;
}
static void build_layout_skeleton(int level_number, int level_type,
@@ -836,7 +851,10 @@ static void build_dungeon_level(int level_number, int level_type)
if (you.level_type == LEVEL_LABYRINTH
|| you.level_type == LEVEL_PORTAL_VAULT
|| dgn_level_vetoed)
+ {
+ dgn_set_floor_colours();
return;
+ }
// hook up the special room (if there is one, and it hasn't
// been hooked up already in roguey_level())
@@ -922,68 +940,39 @@ static char fix_black_colour(char incol)
return incol;
}
-int bazaar_floor_colour(int curr_level)
-{
- const char floorcolours_bzr[] =
- { BLUE, RED, LIGHTBLUE, MAGENTA, GREEN };
-
- // set colour according to current level
- // randomization would reset between save/reload and after showing map
- return (floorcolours_bzr[curr_level % 5]);
-}
-
void dgn_set_colours_from_monsters()
{
env.floor_colour = fix_black_colour(mcolour[env.mons_alloc[9]]);
env.rock_colour = fix_black_colour(mcolour[env.mons_alloc[8]]);
}
-void dgn_set_floor_colours()
+static void dgn_set_floor_colours()
{
+ unsigned char old_floor_colour = env.floor_colour;
+ unsigned char old_rock_colour = env.rock_colour;
+
if (you.level_type == LEVEL_PANDEMONIUM || you.level_type == LEVEL_ABYSS)
{
dgn_set_colours_from_monsters();
}
- else if (you.level_type == LEVEL_LABYRINTH)
- {
- env.floor_colour = LIGHTGREY;
- env.rock_colour = BROWN;
- }
- else if (you.level_type == LEVEL_PORTAL_VAULT
- && you.level_type_name == "bazaar")
- {
- // bazaars get gold walls
- env.rock_colour = YELLOW;
-
- // bazaar floor is colourful
- env.floor_colour = bazaar_floor_colour(you.your_level + 1);
- }
- else
+ else if (you.level_type == LEVEL_DUNGEON)
{
// level_type == LEVEL_DUNGEON
+ // Hall of Zot colours handled in dat/zot.des
const int youbranch = you.where_are_you;
env.floor_colour = branches[youbranch].floor_colour;
env.rock_colour = branches[youbranch].rock_colour;
+ }
- // Zot is multicoloured
- if ( you.where_are_you == BRANCH_HALL_OF_ZOT )
- {
- const char floorcolours_zot[] = { LIGHTGREY, LIGHTGREY, BLUE,
- LIGHTBLUE, MAGENTA };
- const char rockcolours_zot[] = { LIGHTGREY, BLUE, LIGHTBLUE,
- MAGENTA, LIGHTMAGENTA };
-
- const int curr_subdungeon_level = player_branch_depth();
+ if (old_floor_colour != BLACK)
+ env.floor_colour = old_floor_colour;
+ if (old_rock_colour != BLACK)
+ env.rock_colour = old_rock_colour;
- if ( curr_subdungeon_level > 5 || curr_subdungeon_level < 1 )
- mpr("Odd colouring!");
- else
- {
- env.floor_colour = floorcolours_zot[curr_subdungeon_level-1];
- env.rock_colour = rockcolours_zot[curr_subdungeon_level-1];
- }
- }
- }
+ if (env.floor_colour == BLACK)
+ env.floor_colour = LIGHTGREY;
+ if (env.rock_colour == BLACK)
+ env.rock_colour = BROWN;
}
static void check_doors()
@@ -1455,14 +1444,7 @@ static builder_rc_type builder_by_type(int level_number, char level_type)
{
if (level_type == LEVEL_PORTAL_VAULT)
{
- if (you.level_type_name == "bazaar")
- bazaar_level(level_number);
- else
- {
- // Need to find encompass vault with tag matching
- // level_type_name.
- ASSERT(false);
- }
+ portal_vault_level(level_number);
return (BUILD_QUIT);
}
@@ -1535,53 +1517,25 @@ static builder_rc_type builder_by_type(int level_number, char level_type)
return BUILD_CONTINUE;
}
-static void fixup_bazaar_stairs()
+static void portal_vault_level(int level_number)
{
- for (int y = 0; y < GYM; ++y)
- {
- for (int x = 0; x < GXM; ++x)
- {
- const dungeon_feature_type feat = grd[x][y];
- if (grid_is_stone_stair(feat) || grid_is_rock_stair(feat))
- {
- if (grid_stair_direction(feat) == CMD_GO_DOWNSTAIRS)
- grd[x][y] = DNGN_EXIT_PORTAL_VAULT;
- else
- {
- grd[x][y] = DNGN_STONE_ARCH;
- env.markers.add(
- new map_feature_marker(
- coord_def(x, y),
- DNGN_STONE_ARCH));
- }
- }
-
- // colour floor squares around shops
- if (feat == DNGN_ENTER_SHOP)
- {
- for (int i=-1; i<=1; i++)
- for (int j=-1; j<=1; j++)
- {
- if (grd[x+i][y+j] == DNGN_FLOOR)
- grd[x+i][y+j] = DNGN_FLOOR_SPECIAL;
- }
- }
- }
- }
-}
+ std::string trimmed_name = trimmed_string(you.level_type_name);
+ ASSERT(trimmed_name.c_str() != "");
+
+ const char* level_name = trimmed_name.c_str();
-static void bazaar_level(int level_number)
-{
int vault = random_map_for_place(level_id::current(), false);
#ifdef WIZARD
- if (vault == -1 && you.wizard)
+ if (vault == -1 && you.wizard
+ && random_map_for_tag(level_name, false) != -1)
{
char buf[80];
do
{
- mprf(MSGCH_PROMPT, "Which bazaar (ESC or ENTER for random): ");
+ mprf(MSGCH_PROMPT, "Which %s (ESC or ENTER for random): ",
+ level_name);
if (cancelable_get_line(buf, sizeof buf))
break;
@@ -1594,35 +1548,43 @@ static void bazaar_level(int level_number)
lowercase(name);
name = replace_all(name, " ", "_");
- vault = find_map_by_name("bazaar_" + name);
+ vault = find_map_by_name(you.level_type_name + "_" + name);
if (vault == -1)
- mprf(MSGCH_DIAGNOSTICS, "No such bazaar, try again.");
+ mprf(MSGCH_DIAGNOSTICS, "No such %s, try again.",
+ level_name);
} while (vault == -1);
}
#endif
if (vault == -1)
- vault = random_map_for_tag("bazaar", false);
+ vault = random_map_for_tag(level_name, false);
if (vault != -1)
- {
ensure_vault_placed( build_vaults(level_number, vault) );
- link_items();
- fixup_bazaar_stairs();
- return;
+ else
+ {
+ plan_main(level_number, 0);
+ place_minivaults(level_name, 1, 1, true);
+
+ if (level_vaults.empty())
+ {
+ mprf(MSGCH_WARN, "No maps or tags named '%s'.",
+ level_name);
+ ASSERT(false);
+ end(-1);
+ }
}
- // No primary Bazaar vaults (ugh).
- plan_main(level_number, 0);
- place_minivaults("bazaar", 1, 1, true);
+ link_items();
- // No vaults placed yet? Place some shops of our own.
- if (level_vaults.empty())
- place_shops(level_number, random_range(5, MAX_SHOPS));
+ // TODO: Let portal vault map have arbitrary properties which can
+ // be passed onto the callback.
+ callback_map::const_iterator
+ i = level_type_post_callbacks.find(you.level_type_name);
- link_items();
- fixup_bazaar_stairs();
+ if (i != level_type_post_callbacks.end())
+ dlua.callfn(i->second.c_str(), 0, 0);
}
static int random_portal_vault(const std::string &tag)
@@ -7288,6 +7250,15 @@ coord_def dgn_find_nearby_stair(dungeon_feature_type stair_to_find,
return result;
}
+void dgn_set_lt_callback(std::string level_type_name,
+ std::string callback_name)
+{
+ ASSERT(level_type_name != "");
+ ASSERT(callback_name != "");
+
+ level_type_post_callbacks[level_type_name] = callback_name;
+}
+
////////////////////////////////////////////////////////////////////
// dgn_region
diff --git a/crawl-ref/source/dungeon.h b/crawl-ref/source/dungeon.h
index 72b3b24889..fe5d4d1fac 100644
--- a/crawl-ref/source/dungeon.h
+++ b/crawl-ref/source/dungeon.h
@@ -294,11 +294,9 @@ bool flood_find<fgrd, bound_check>::path_flood(
bool builder(int level_number, int level_type);
-int bazaar_floor_colour(int curr_level);
// Set floor/wall colour based on the mons_alloc array. Used for
// Abyss and Pan.
void dgn_set_colours_from_monsters();
-void dgn_set_floor_colours();
bool dgn_place_map(int map, bool generating_level, bool clobber);
void level_clear_vault_memory();
@@ -320,4 +318,7 @@ bool dgn_place_monster(const mons_spec &mspec,
bool set_level_flags(unsigned long flags, bool silent = false);
bool unset_level_flags(unsigned long flags, bool silent = false);
+void dgn_set_lt_callback(std::string level_type_name,
+ std::string callback_name);
+
#endif
diff --git a/crawl-ref/source/luadgn.cc b/crawl-ref/source/luadgn.cc
index 66575837c9..b72b9e4f5c 100644
--- a/crawl-ref/source/luadgn.cc
+++ b/crawl-ref/source/luadgn.cc
@@ -23,6 +23,7 @@
#include "stuff.h"
#include "tags.h"
#include "terrain.h"
+#include "view.h"
// Lua interpreter for the dungeon builder.
CLua dlua(false);
@@ -924,6 +925,139 @@ static int dgn_load_des_file(lua_State *ls)
return (0);
}
+static int dgn_floor_colour(lua_State *ls)
+{
+ MAP(ls, 1, map);
+
+ const char *s = luaL_checkstring(ls, 2);
+ int colour = str_to_colour(s);
+
+ if (colour < 0 || colour == BLACK)
+ {
+ std::string error;
+
+ if (colour == BLACK)
+ {
+ error = "Can't set floor to black.";
+ }
+ else {
+ error = "No such colour as '";
+ error += s;
+ error += "'";
+ }
+
+ luaL_argerror(ls, 2, error.c_str());
+
+ return (0);
+ }
+
+ map->floor_colour = (unsigned char) colour;
+ return (0);
+}
+
+static int dgn_rock_colour(lua_State *ls)
+{
+ MAP(ls, 1, map);
+
+ const char *s = luaL_checkstring(ls, 2);
+ int colour = str_to_colour(s);
+
+ if (colour < 0 || colour == BLACK)
+ {
+ std::string error;
+
+ if (colour == BLACK)
+ {
+ error = "Can't set rock to black.";
+ }
+ else {
+ error = "No such colour as '";
+ error += s;
+ error += "'";
+ }
+
+ luaL_argerror(ls, 2, error.c_str());
+
+ return (0);
+ }
+
+ map->rock_colour = (unsigned char) colour;
+
+ return (0);
+}
+
+static int dgn_get_floor_colour(lua_State *ls)
+{
+ PLUARET(string, colour_to_str(env.floor_colour));
+}
+
+static int dgn_get_rock_colour(lua_State *ls)
+{
+ PLUARET(string, colour_to_str(env.rock_colour));
+}
+
+static int dgn_change_floor_colour(lua_State *ls)
+{
+ const char *s = luaL_checkstring(ls, 1);
+ int colour = str_to_colour(s);
+
+ if (colour < 0 || colour == BLACK)
+ {
+ std::string error;
+
+ if (colour == BLACK)
+ {
+ error = "Can't set floor to black.";
+ }
+ else {
+ error = "No such colour as '";
+ error += s;
+ error += "'";
+ }
+
+ luaL_argerror(ls, 1, error.c_str());
+
+ return (0);
+ }
+
+ env.floor_colour = (unsigned char) colour;
+
+ viewwindow(true, false);
+
+ return (0);
+}
+
+static int dgn_change_rock_colour(lua_State *ls)
+{
+ const char *s = luaL_checkstring(ls, 1);
+ int colour = str_to_colour(s);
+
+ if (colour < 0 || colour == BLACK)
+ {
+ std::string error;
+
+ if (colour == BLACK)
+ {
+ error = "Can't set rock to black.";
+ }
+ else {
+ error = "No such colour as '";
+ error += s;
+ error += "'";
+ }
+
+ luaL_argerror(ls, 1, error.c_str());
+
+ return (0);
+ }
+
+ env.rock_colour = (unsigned char) colour;
+
+ viewwindow(true, false);
+
+ return (0);
+}
+
const char *dngn_feature_names[] =
{
"unseen", "closed_door", "secret_door", "rock_wall", "stone_wall",
@@ -1199,6 +1333,127 @@ static int dgn_mons_from_index(lua_State *ls)
return (1);
}
+static int lua_dgn_set_lt_callback(lua_State *ls)
+{
+ const char *level_type = luaL_checkstring(ls, 1);
+
+ if (level_type == NULL || strlen(level_type) == 0)
+ return (0);
+
+ const char *callback_name = luaL_checkstring(ls, 2);
+
+ if (callback_name == NULL || strlen(callback_name) == 0)
+ return (0);
+
+ dgn_set_lt_callback(level_type, callback_name);
+
+ return (0);
+}
+
+static int dgn_fixup_stairs(lua_State *ls)
+{
+ const dungeon_feature_type up_feat =
+ dungeon_feature_by_name(luaL_checkstring(ls, 1));
+
+ const dungeon_feature_type down_feat =
+ dungeon_feature_by_name(luaL_checkstring(ls, 2));
+
+ if (up_feat == DNGN_UNSEEN && down_feat == DNGN_UNSEEN)
+ return(0);
+
+ for (int y = 0; y < GYM; ++y)
+ {
+ for (int x = 0; x < GXM; ++x)
+ {
+ const dungeon_feature_type feat = grd[x][y];
+ if (grid_is_stone_stair(feat) || grid_is_rock_stair(feat))
+ {
+ dungeon_feature_type new_feat = DNGN_UNSEEN;
+
+ if (grid_stair_direction(feat) == CMD_GO_DOWNSTAIRS)
+ new_feat = down_feat;
+ else
+ new_feat = up_feat;
+
+ if (new_feat != DNGN_UNSEEN)
+ {
+ grd[x][y] = new_feat;
+ env.markers.add(
+ new map_feature_marker(
+ coord_def(x, y),
+ new_feat));
+ }
+ }
+ }
+ }
+
+ return (0);
+}
+
+static int dgn_floor_halo(lua_State *ls)
+{
+ std::string error = "";
+
+ const char* s1 = luaL_checkstring(ls, 1);
+ const dungeon_feature_type target = dungeon_feature_by_name(s1);
+
+ if (target == DNGN_UNSEEN)
+ {
+ error += "No such dungeon feature as '";
+ error += s1;
+ error += "'. ";
+ }
+
+ const char* s2 = luaL_checkstring(ls, 2);
+ unsigned char colour = str_to_colour(s2);
+
+ if (colour == -1)
+ {
+ error += "No such colour as '";
+ error += s2;
+ error += "'.";
+ }
+ else if (colour == BLACK)
+ {
+ error += "Can't set floor colour to black.";
+ }
+
+ if (error != "")
+ {
+ luaL_argerror(ls, 2, error.c_str());
+ return(0);
+ }
+
+ for (int y = 0; y < GYM; ++y)
+ {
+ for (int x = 0; x < GXM; ++x)
+ {
+ const dungeon_feature_type feat = grd[x][y];
+ if (feat == target)
+ {
+
+ for (int i=-1; i<=1; i++)
+ for (int j=-1; j<=1; j++)
+ {
+ if (!map_bounds(x+i, y+j))
+ continue;
+
+ const dungeon_feature_type feat2 = grd[x+i][y+j];
+
+ if (feat2 == DNGN_FLOOR
+ || feat2 == DNGN_UNDISCOVERED_TRAP)
+ {
+ env.grid_colours[x+i][y+j] = colour;
+ }
+ }
+ }
+ }
+ }
+
+ return (0);
+}
+
+
static const struct luaL_reg dgn_lib[] =
{
{ "default_depth", dgn_default_depth },
@@ -1218,6 +1473,8 @@ static const struct luaL_reg dgn_lib[] =
{ "subst", dgn_subst },
{ "nsubst", dgn_nsubst },
{ "colour", dgn_colour },
+ { "floor_colour", dgn_floor_colour},
+ { "rock_colour", dgn_rock_colour},
{ "subst_remove", dgn_subst_remove },
{ "map", dgn_map },
{ "mons", dgn_mons },
@@ -1249,6 +1506,13 @@ static const struct luaL_reg dgn_lib[] =
{ "mons_from_index", dgn_mons_from_index },
{ "change_level_flags", dgn_change_level_flags},
{ "change_branch_flags", dgn_change_branch_flags},
+ { "get_floor_colour", dgn_get_floor_colour},
+ { "get_rock_colour", dgn_get_rock_colour},
+ { "change_floor_colour", dgn_change_floor_colour},
+ { "change_rock_colour", dgn_change_rock_colour},
+ { "set_lt_callback", lua_dgn_set_lt_callback},
+ { "fixup_stairs", dgn_fixup_stairs},
+ { "floor_halo", dgn_floor_halo},
{ NULL, NULL }
};
diff --git a/crawl-ref/source/mapdef.cc b/crawl-ref/source/mapdef.cc
index 599ceda1b8..5444119709 100644
--- a/crawl-ref/source/mapdef.cc
+++ b/crawl-ref/source/mapdef.cc
@@ -1158,7 +1158,8 @@ map_def::map_def()
: name(), tags(), place(), depths(), orient(), chance(),
welcome_messages(), map(), mons(), items(), keyspecs(),
prelude("dlprelude"), main("dlmain"), validate("dlvalidate"),
- veto("dlveto"), index_only(false), cache_offset(0L)
+ veto("dlveto"), rock_colour(BLACK), floor_colour(BLACK),
+ index_only(false), cache_offset(0L)
{
init();
}
diff --git a/crawl-ref/source/mapdef.h b/crawl-ref/source/mapdef.h
index d364553a9a..9d2e7e2b57 100644
--- a/crawl-ref/source/mapdef.h
+++ b/crawl-ref/source/mapdef.h
@@ -581,6 +581,8 @@ public:
map_def *original;
+ unsigned char rock_colour, floor_colour;
+
private:
// This map has been loaded from an index, and not fully realised.
bool index_only;
diff --git a/crawl-ref/source/misc.cc b/crawl-ref/source/misc.cc
index 6ddf4eae07..9fa0620419 100644
--- a/crawl-ref/source/misc.cc
+++ b/crawl-ref/source/misc.cc
@@ -1216,8 +1216,6 @@ void new_level(void)
take_note(Note(NOTE_DUNGEON_LEVEL_CHANGE));
cprintf("%s", level_description_string().c_str());
- dgn_set_floor_colours();
-
clear_to_end_of_line();
#ifdef DGL_WHEREIS
whereis_record();
diff --git a/crawl-ref/source/tags.cc b/crawl-ref/source/tags.cc
index 478c53d5ad..757717c248 100644
--- a/crawl-ref/source/tags.cc
+++ b/crawl-ref/source/tags.cc
@@ -1477,6 +1477,9 @@ static void tag_read_lost_monsters(tagHeader &th, int minorVersion)
static void tag_construct_level(struct tagHeader &th)
{
+ marshallByte(th, env.floor_colour);
+ marshallByte(th, env.rock_colour);
+
marshallLong(th, env.level_flags);
marshallFloat(th, (float)you.elapsed_time);
@@ -1698,6 +1701,9 @@ void tag_construct_level_attitude(struct tagHeader &th)
static void tag_read_level( struct tagHeader &th, char minorVersion )
{
+ env.floor_colour = unmarshallByte(th);
+ env.rock_colour = unmarshallByte(th);
+
env.level_flags = (unsigned long) unmarshallLong(th);
env.elapsed_time = unmarshallFloat(th);
diff --git a/crawl-ref/source/util/levcomp.lpp b/crawl-ref/source/util/levcomp.lpp
index ffff5860f8..4d7e0278bd 100644
--- a/crawl-ref/source/util/levcomp.lpp
+++ b/crawl-ref/source/util/levcomp.lpp
@@ -199,6 +199,8 @@ BFLAGS: { BEGIN(ARGUMENT); return BFLAGS; }
SUBST: { BEGIN(ITEM_LIST); return SUBST; }
NSUBST: { BEGIN(ITEM_LIST); return NSUBST; }
COLOUR: { BEGIN(ITEM_LIST); return COLOUR; }
+FLOORCOL: { BEGIN(ARGUMENT); return FLOORCOL; }
+ROCKCOL: { BEGIN(ARGUMENT); return ROCKCOL; }
MONS: { BEGIN(MNAME); return MONS; }
ITEM: { BEGIN(ITEM_LIST); return ITEM; }
MARKER: { BEGIN(TOEOL); return MARKER; }
diff --git a/crawl-ref/source/util/levcomp.ypp b/crawl-ref/source/util/levcomp.ypp
index 98b71047b4..614a357bbc 100644
--- a/crawl-ref/source/util/levcomp.ypp
+++ b/crawl-ref/source/util/levcomp.ypp
@@ -55,6 +55,7 @@ level_range set_range(const char *s, int start, int end)
%token <i> DEFAULT_DEPTH SHUFFLE SUBST TAGS KFEAT KITEM KMONS KMASK
%token <i> NAME DEPTH ORIENT PLACE CHANCE MONS ITEM MARKER COLOUR
%token <i> PRELUDE MAIN VALIDATE VETO NSUBST WELCOME LFLAGS BFLAGS
+%token <i> FLOORCOL ROCKCOL
%token <i> COMMA INTEGER CHARACTER
@@ -159,6 +160,8 @@ metaline : place
| subst
| nsubst
| colour
+ | floorcol
+ | rockcol
| shuffle
| tags
| lflags
@@ -346,6 +349,24 @@ mspec_segment : STRING
colour : COLOUR colour_specifiers { }
;
+floorcol : FLOORCOL { }
+ | FLOORCOL STRING
+ {
+ lc_map.main.add(
+ yylineno,
+ make_stringf("floor_colour(\"%s\")",
+ quote_lua_string($2).c_str()));
+ }
+
+rockcol : ROCKCOL { }
+ | ROCKCOL STRING
+ {
+ lc_map.main.add(
+ yylineno,
+ make_stringf("rock_colour(\"%s\")",
+ quote_lua_string($2).c_str()));
+ }
+
colour_specifiers : colour_specifier { }
| colour_specifiers COMMA colour_specifier { }
;