git-svn-id: https://crawl-ref.svn.sourceforge.net/svnroot/crawl-ref/trunk@6933 c06c8d41-db1a-0410-9941-cceddc491573
XPTDBTPHD5CIPPOHIPMI7HBOTQIGGJPYKDOJCHWG2ZTI7SLUHTEAC
3X2MBNOJZ24SJT2NIBQTLDOXHM3RTYRKZFZZY3MHZQGTLGTRAKUAC
RPOZZWKG5GLPHVZZ7ZKMKS64ZMV2LDCQSARBJFJ6FZOTOKCQO7FAC
K2CS6TCX2NDVL2ASEHGP4J4K4IJ6FP3ANNKTSIWVG43HPYSBX6ZQC
6ZCKL3LCJ2QYYRI6CVK7CU4VXZMIZ6RIOTFUDEM2QTM4EHKVUKMAC
B7MSPF6X2RLGWN4M6ZZF3WSOPKGYPTTD7LIJVST7DXN27DG6JHNAC
OY7KHQPESOUHPBXRZ2JSNUKPAC7DCDY73TAUHCSJG5V6TPAHBVYQC
45EMD3KLQPMERNMIKU5G76H6556XOMIW352TSBP7VLWJX2YYGS7AC
56C44YMFHZ62GXAAOLYSLLGBVGRWXB53W2VI37Q26ZECEK2XG5SQC
R5JKQLY5QE6UBG3RH3Y5ZRSX6H35CHYI2HYNDZF6ZHVRULUORXBQC
NVSFIV2ZKP44XHCSCXG6OZVGL67OIFINC34J2EMKTA4KULCERUEAC
CUNNC574MESEMTTONZ6YB6CJ2S5P6VA3V7Z3OODESWAK37GYOBPAC
PJ7HBIWAV3H23LXGZAAD2QYJ7HMOFOIR5ZJ4U2UTHI766LOTRRWQC
static void _labyrinth_colour_maze_flood(
const coord_def &c,
const std::vector<coord_def> &corder,
int colour)
{
if (colour)
env.grid_colours(c) = colour;
travel_point_distance[c.x][c.y] = 1;
if (one_chance_in(45))
colour = _labyrinth_random_colour();
for (int i = 0, size = corder.size(); i < size; ++i)
{
coord_def dp = c + corder[i];
if (map_bounds(dp) && !travel_point_distance[dp.x][dp.y]
&& grd(dp) == DNGN_ROCK_WALL)
{
_labyrinth_colour_maze_flood(dp, corder, colour);
}
}
}
static void _labyrinth_colour_maze(const coord_def &e, const dgn_region &lab)
{
coord_def start = e;
for (rectangle_iterator r(e - coord_def(1, 1), e + coord_def(1, 1));
r; ++r)
if (map_bounds(*r) && grd(*r) == DNGN_ROCK_WALL)
start = *r;
if (grd(start) != DNGN_ROCK_WALL)
return;
int colour = _labyrinth_random_colour();
std::vector<coord_def> flood_points[2];
int page = 0;
flood_points[page].push_back(start);
std::vector<coord_def> check_order;
for (int y = -1; y <= 1; ++y)
for (int x = -1; x <= 1; ++x)
if (!x != !y)
check_order.push_back(coord_def(x, y));
std::random_shuffle(check_order.begin(), check_order.end());
memset(travel_point_distance, 0, sizeof(travel_distance_grid_t));
_labyrinth_colour_maze_flood(start, check_order, colour);
}
}
static void _change_walls_from_centre(const dgn_region ®ion,
const coord_def ¢re,
bool rectangular,
unsigned mmask,
dungeon_feature_type wall,
const std::vector<dist_feat> &ldist)
{
if (ldist.empty())
return;
const coord_def &end = region.pos + region.size;
for (int y = region.pos.y; y < end.y; ++y)
for (int x = region.pos.x; x < end.x; ++x)
{
const coord_def c(x, y);
if (grd(c) != wall || !unforbidden(c, mmask))
continue;
const int distance =
rectangular? (c - centre).rdist() : (c - centre).abs();
for (int i = 0, size = ldist.size(); i < size; ++i)
{
if (distance <= ldist[i].dist)
{
grd(c) = ldist[i].feat;
break;
}
}
}
// Called as:
// change_walls_from_centre( region_affected, centre, rectangular, wall,
// dist1, feat1, dist2, feat2, ..., 0 )
// What it does:
// Examines each square in region_affected, calculates its distance from
// "centre" (the centre need not be in region_affected). If the distance is
// less than or equal to dist1, and the feature == wall, then it is replaced
// by feat1. Otherwise, if the distance <= dist2 and feature == wall, it is
// replaced by feat2, and so on. A distance of 0 indicates the end of the
// list of distances.
//
static void _change_walls_from_centre(const dgn_region ®ion,
const coord_def &c,
bool rectangular,
dungeon_feature_type wall,
...)
{
std::vector<dist_feat> ldist;
va_list args;
va_start(args, wall);
while (true)
{
const int dist = va_arg(args, int);
if (!dist)
break;
const dungeon_feature_type feat =
static_cast<dungeon_feature_type>( va_arg(args, int) );
ldist.push_back(dist_feat(dist, feat));
}
_change_walls_from_centre(region, c, rectangular, MMT_VAULT, wall, ldist);
}
// If we place any vaults, make sure they overwrite the maze
// colours where appropriate.
dgn_colour_override_manager colour_man;
if (vault != -1)
_init_minivault_placement(vault, place);
if (vault == -1 || !_build_minivaults(level_number, vault))
{
vault = -1;
_labyrinth_place_exit(end);
}
else
vault = -1;
_labyrinth_place_exit(end);
}
else
{
const vault_placement &rplace = *(Level_Vaults.end() - 1);
if (rplace.map.has_tag("generate_loot"))