###
#
## Maps from named Wizards, unrand and fixedarts
#
# Tukima's Studio
#    threat: 6 dancing weapons, dancing weapon machine generating up to 5 more
#    loot:   the weapons, tukima's book and a scroll of acquirement
#    xp:     14400 or so
#    layout: mirrors; grey and white
#
# Eringya's Formal Garden
#    crumbling stone walls.
#    threat: centaurs, oklobs
#    loot:   a staff and four spellbooks
#    xp:     10500 or so
#    layout: formal (French) garden, flowers, crumbling stone walls
#
# Doroklohe's Tomb
#    threat: either Tomb set or demons or golems
#    loot:   either scrolls or armours or random items
#    xp:     10000+
#    layout: lots of tombs with loot and monsters inside
#    colour: yellow tombs, rest is dark, floor is randomised
#
# Wucad Mu's Monastery
#    threat: "monks", OCS
#    loot:   books, staff of wucad mu
#    xp:     9000+
#    layout: temple-esque!
#    colour: dark walls, red and orange.
#
# Cigotuvi's Fleshworks
#    threat: lumps, uglies, abominations
#    loot:   tmut. potions, books, rMut, ?oSumm, \oDeath
#    xp:     16000+
#    layout: organic, irregular, twisty, NO SQUARES, NO HARD CORNERS,
#            NOTHING THAT LOOKS PRETTY
#    colour: lightred walls, red doors, magenta floor, yellow 'glass'
#
# Iskenderun's Mystic Tower
#    threat: naga mystics, statues with IOOD and IMB, purple draconians
#    loot:   conjurations-themed randart books
#    xp:     20000+
#    layout: weird fortress tower thing with strange corners
#    colour: purple.
#
# Zonguldrok's Mausoleum
#    threat: zombies, ancient lich, skele warriors
#    loot:   scrolls, potions, spell books and zonguldrok's sword
#    xp:     20000+
#    layout: graveyard
#    colour: darkgrey, lightgrey
#
# The Roulette of Golubria
#    threat: distortion, tloc-themed monsters, Abyss monsters
#    loot:   tloc-themed consumables / rings / books, abyss escape aides, cloaks
#    xp:     20000+
#    layout: large maw shape with roulette through teeth, old-abyss-esque innards
#    colour: green floor, green/rarely cyan walls
#
## Random maps
#
# Cloud Mage's Chambers
#    threat: cloud mage (random name), vapours, air elementals
#    loot:   potions, robe of clouds, air-related spells
#    xp:     20000+
#    layout: "cloud"-esque, clouds.
#    colour: white, silver, lightblue
#
# Hellbinder's Lair:
#    threat: demons, Hellbinder
#    loot:   demonology-related items
#    xp:     15000+
#    layout: sigils, triangles and circles
#    colour: red, darkgrey
#
##
#
# TO-DO:
#
# The flavour messages for the portal vault require flavour, while the actual
# portals themselves could do with an overhaul and some new ones.
#
# *MUST* make these look awesome in tiles, too.
#
# Overall todo: random monster lists for each vault (shadows for Wucad Mu)
# (must have them or Shadow Creatures won't work)
#
##

{{
function wizlab_portal (e)
    local timeout_turns_long = crawl.random_range(2700, 3300)
    local timeout_turns_short = timeout_turns_long/10
    local messager =
        timed_msg {
            visible = true,
            -- $F{xxx} will be substituted with the 'entity' property of the timed
            -- marker, or with the desc property (if entity is not set).
            messages = time_messages(timeout_turns_short,
                            "$F{The} shimmers.",
                            "$F{The} vibrates and hums gently.",
                            "$F{The} is slightly opaque.",
                            "$F{The} is almost invisible now.")
    }

    e.lua_marker('O',
      timed_marker {
        disappear = "The portal disappears completely.",
        desc = "magical portal",
        entity = 'portal',
        dst = 'WizLab',
        overview = "magical portal",
        turns = timeout_turns_long,
        turns_short = timeout_turns_short,
        floor = "stone_arch",
        feat_tile = "dngn_portal_bazaar_gone",
        msg = messager })
    e.kfeat("O = enter_portal_vault")
    e.tile("O = no_random dngn_portal_wizard_lab")
end

-- Destinations:
function wizlab_setup (e, wizlab_desc)
    e.kfeat("< = exit_portal_vault")
    e.tile("< = no_random dngn_portal_wizard_lab")
    -- This is so that the note shows up properly.
    e.set_feature_name("exit_portal_vault", "portal leading out of here")
    if wizlab_desc ~= "Eringya's Formal Garden" then
      e.set_feature_name("stone_arch", "empty arch of stone")
    end
end

function wizlab_milestone (e, wizlab_desc)
    crawl.mark_milestone("br.enter", "entered " .. wizlab_desc .. ".", "parent")
end

function tukima_machine (data, triggerable, triggerer, marker, ev)
  if triggerer.type ~= "turn" or triggerer.sub_type ~= "countdown" then
    return
  end

  local x, y = marker:pos()
  local you_x, you_y = you.pos()

  if data.weapon_count >= 5 then
    if you.see_cell(x, y) then
      crawl.mpr("The machine makes a dull noise.")
    else
      crawl.mpr("You hear a distant, dull noise.")
    end
    return
  end

  if (you_x == x and you_y == y) then return end
  if dgn.mons_at(x, y) then return end

  dgn.apply_area_cloud(x, y, 1, 6, 1, 10, "black smoke", "other", -1)

  if (not dgn.create_monster(x, y, "generate_awake dancing weapon")) then
    return
  end

  data.weapon_count = data.weapon_count + 1

  if you.see_cell(x, y) then
    crawl.mpr("The machine hisses, and spits out a dancing weapon!")
  else
    crawl.mpr("You hear a distant hissing noise.")
  end
end

function wizlab_eringya_grow(data, triggerable, triggerer, marker, ev)
  if triggerer.type ~= "turn" or triggerer.sub_type ~= "countdown" then
    return
  end

  local count = 0

  if crawl.one_chance_in(5) then
    -- Fruit!
    for spot in iter.adjacent_iterator() do
      if not feat.is_solid(spot:xy()) and feat.has_solid_floor(spot:xy())
         and crawl.one_chance_in(3) then
        dgn.create_item(spot.x, spot.y, "pear / apple / choko / apricot / orange"
                          .. "/ banana / strawberry q:4 / lemon / rambutan "
                          .. "/ grape q:7 / sultana q:9 / lychee")
        count = count + 1
      end
    end
    if count > 0 then
      crawl.mpr("Fruit sprouts up around you!")
    end
  else
    for spot in iter.adjacent_iterator() do
      if not feat.is_solid(spot:xy()) and feat.has_solid_floor(spot:xy())
         and not crawl.one_chance_in(3) then
        dgn.create_monster(spot.x, spot.y, "toadstool")
        count = count + 1
      end
    end
    if count > 0 then
      crawl.mpr("Toadstools sprout up around you!")
    end
  end
end

function wizlab_doroklohe_convert_boxes(data, triggerable, triggerer,
                                        marker, ev)
  if triggerer.type ~= "turn" or triggerer.sub_type ~= "countdown" then
    return
  end

  if data.phase == 1 then
    data.phase = data.phase + 1
    if you.silenced() then
      crawl.mpr("The ground shakes.", "warning")
    else
      crawl.mpr("There is a faint hissing noise.", "warning")
    end
    return
  elseif data.phase == 2 then
    data.phase = data.phase + 1
    if you.silenced() then
      crawl.mpr("The ground shakes.", "warning")
    else
      crawl.mpr("There is a loud grinding noise.", "warning")
    end
    return
  elseif data.phase == 3 then
    data.phase = data.phase + 1
    crawl.mpr("The walls fall away. The entombed are set free!", "warning")
    for _, i in ipairs(dgn.find_marker_positions_by_prop("wall_drop", 1)) do
      dgn.terrain_changed(i.x, i.y, "floor", false, false, false)
      dgn.place_cloud(i.x, i.y, "black smoke", 2)
    end
    return
  else
    return
  end
end

local function spawn_zombie (x, y, spec)
    dgn.terrain_changed(x, y, "floor", false, false, false)
    local mons = dgn.create_monster(x, y, spec)
    mons.set_prop("zonguldrok", 1)
    return mons
end

function wizlab_zonguldrok_spawn_zombies(data, triggerable, triggerer,
                                         marker, ev)
    if triggerer.type ~= "turn" or triggerer.sub_type ~= "countdown" then
        return
    end

    local graves = dgn.find_markers_by_prop("grave", 1)
    local x, y
    for _, gmarker in ipairs(graves) do
        x, y = gmarker:pos()
        if (you.see_cell(x, y) and crawl.one_chance_in(3)) or
            crawl.one_chance_in(8) then
            spawn_zombie(x, y, "generate_awake human zombie")
            gmarker:remove()
        end
    end
end

function wizlab_zonguldrok_killed_zombie(data, triggerable, triggerer,
                                         marker, ev)
    if data.door_appeared then
        return
    end

    local mons = dgn.mons_from_mid(ev:arg1())
    if not mons.has_prop("zonguldrok") then
        return
    end

    data.number_killed = data.number_killed + 1
    if #dgn.find_markers_by_prop("grave", 1) < data.number_killed then
        local x, y = marker:pos()
        dgn.tile_feat_changed(x, y, nil)
        dgn.terrain_changed(x, y, "closed_door", false, false, false)
        data.door_appeared = true
        if you.see_cell(x, y) then
            crawl.mpr("A door appears!")
        else
            crawl.mpr("The walls vibrate.")
        end
    end
end

function wizlab_zonguldrok_awaken_wizard(data, triggerable,
                                         triggerer, marker, ev)
    if data.awoke == true then
        return
    end

    local pos = dgn.find_marker_positions_by_prop("wizard_grave", 1)[1]
    local lich = dgn.create_monster(pos.x, pos.y, "generate_awake ancient lich "
                 .."col:brown name:antique_lich name_replace name_descriptor"
                 .." tile:mons_zonguldrok_lich")
    if lich then
        data.awoke = true
    end
end

function wizlab_wucad_msgfn(data, triggerable, triggerer, marker, ev)
  if data.trig == true then
    return
  end

  if crawl.one_chance_in(3) then
    return
  end

  if dgn.persist.wucad_mu_died == true then
    return
  end

  if data.spot == 1 then
    crawl.mpr("Strange, shadowy figures dance through the air in front of you.", "talk_visual")
    data.trig = true
  elseif data.spot == 2 then
    crawl.mpr("This room is filled with shadowy figures, quietly meditating.", "talk_visual")
    data.trig = true
  elseif data.spot == 3 then
    crawl.mpr("Here, spectral monks perform complicated, martial routines; they fade quickly.", "talk_visual")
    data.trig = true
  elseif data.spot == 4 then
    if you.silenced() then
      return
    end
    crawl.mpr("Faint laughter comes from somewhere. Too faint to be real.", "talk_visual")
    data.trig = true
  elseif data.spot == 5 then
    if you.silenced() then
      return
    end
    crawl.mpr("There is a faint scream of pain from a crouched figure. This too fades quickly.", "talk_visual")
    data.trig = true
  elseif data.spot == 6 then
    crawl.mpr("Grey monks gather around the fountain. They do not speak, nor look at each other.", "talk_visual")
    data.trig = true
  elseif data.spot == 7 then
    crawl.mpr("A figure sits in silent meditation. It spots you, gestures wildly, and disappears.", "talk_visual")
    data.trig = true
  end
end

function wizlab_wucad_summon_monks(data, triggerable, triggerer, marker, ev)
  if triggerer.type ~= "turn" or triggerer.sub_type ~= "countdown" then
    return
  end

  if dgn.persist.wucad_mu_died == true then
    return
  end

  -- For now, no spawning during Step From Time; perhaps monks should
  -- continue to appear, just more slowly. If so, the circle_iterator below
  -- needs a different centre from (0,0).
  if you.pos() == 0 then
    return
  end

  local msp = "human name:monk n_suf col:white hd:10 dur:2 sum:shadow_creatures" ..
            " nas:old_memories tile:mons_human_monk seen / rock troll name:monk n_suf"..
            " dur:2 seen sum:shadow_creatures nas:old_memories tile:mons_rock_troll_monk" ..
            " / iron troll name:monk n_suf col:white dur:2 sum:shadow_creatures " ..
            " nas:old_memories seen tile:mons_iron_troll_monk w:5"

  local count = 0
  for point in iter.circle_iterator(3) do
    if crawl.one_chance_in(8) and count < 3 then
      if feat.is_solid(point.x, point.y) or not feat.has_solid_floor(point.x, point.y) then
      else
       local mon = dgn.create_monster(point.x, point.y, msp)
       count = count + 1
      end
    end
  end

  crawl.redraw_view()

  if count == 1 then
    crawl.mpr("One of the shadowy figures appears more solid!", "warning")
  elseif count > 1 then
    crawl.mpr("Shadows coalesce into solid form.", "warning")
  end
end

function callback.wizlab_wucad_wucad_died(data, triggerable,
                                           triggerer, marker, ev)
  dgn.persist.wucad_mu_died = true
  crawl.mpr("The shadows inhabiting this place fade forever.", "talk_visual")
end

function teleporter_golubria_switch_fn(data, triggerable, triggerer, marker, ev)
  local position = dgn.point(marker:pos())
  my_slaves = dgn.find_marker_positions_by_prop("teleport_spot",
                                                data.teleport_spot)

  if you.teleport_to(my_slaves[1].x, my_slaves[1].y, true) then
    crawl.mpr("Your surroundings suddenly seem different!")
  else
    crawl.mpr("There is a strange hissing noise.")
  end
end

}}

default-depth: Vaults:2-7, Crypt, D:22-27, Elf:3-5

###############################################################################
# Portal entrances.
#
# Todo: more, and better.
NAME:       enter_wizlab_1
TAGS:       uniq_wizlab chance_wizlab
CHANCE:     5%
ORIENT:     float
TILE:       m = dngn_transparent_wall_green
COLOUR:     m = lightgreen
:           wizlab_portal(_G)
MAP
    wwwww
   wwwwwww
  wwbmbmbww
 wwbb...bbww
wwbm..O..mbww
 wwbb...bbww
  wwbb+bbww
   www.www
    w.@.w
ENDMAP

###############################################################################
# Basic Entrance 2 (by Mu.)
#
NAME:       enter_wizlab_2
TAGS:       uniq_wizlab no_item_gen no_monster_gen chance_wizlab
CHANCE:     5%
ORIENT:     float
SHUFFLE:    tU
TILE:       mn = dngn_transparent_wall_green
COLOUR:     mn = lightgreen
TILE:       c = wall_stone_gray
:           wizlab_portal(_G)
MAP
.................
.bbbbbbbmbbbbbbb.
.bb...b...b...bb.
.n..U...O...U..n.
.bb...b...b...bb.
.bbbbbbb+bbbbbbb.
..bb...b.b...bb..
..n..t.....t..n..
..bb...b.b...bb..
..bbbbbb+bbbbbb..
.................
......c...c......
.....ccc.ccc.....
.................
ENDMAP


###############################################################################
# Basic Entrance 3 (by Mu.)
#
NAME:       enter_wizlab_3
TAGS:       uniq_wizlab no_item_gen no_monster_gen chance_wizlab
CHANCE:     5%
ORIENT:     float
:           wizlab_portal(_G)
MARKER:     ! = lua:fog_machine { \
                 pow_max = 10, delay_min = 10, delay_max = 40, \
                 size = 2, size_buildup_amnt = 5, \
                 size_buildup_time = 25, cloud_type = "flame" \
             }
MARKER:     ? = lua:fog_machine { \
                 pow_max = 10, delay_min = 10, delay_max = 40, \
                 size = 2, size_buildup_amnt = 5, \
                 size_buildup_time = 25, cloud_type = "freezing vapour" \
             }
COLOUR:     . = red / blue
KPROP:      .?! = no_rtele_into
TILE:       n = dngn_transparent_wall_magenta
COLOUR:     n = lightmagenta
TILE:       c = wall_stone_gray
MAP
 ccccccccc
cc..!.?..cc
c?.......!c
c..nnnnn..c
c..n...n..c
c..n.O.n..c
c.?n...n!.c
c..nn.nn..c
c..nn.nn..c
cc!n.n.n?cc
 ccnn.nncc
  cc.n.cc
   cc.cc
    c@c
ENDMAP

###############################################################################
# Basic Entrance 4 (by Mu.)
#
NAME:       enter_wizlab_4
TAGS:       uniq_wizlab no_item_gen no_monster_gen chance_wizlab
CHANCE:     5%
ORIENT:     float
:           wizlab_portal(_G)
KFEAT:      ! = floor
COLOUR:     ! = magenta
FTILE:      !O = floor_rough_magenta
MAP
    xxxxx
    w!!!x
   ww!O!x
  www!!!x
 www..www
www..www
ww..www
w..www
@.www
@www
ENDMAP

###############################################################################
# Basic Entrance 5 (by Mu.)
#
NAME:       enter_wizlab_5
TAGS:       uniq_wizlab no_item_gen no_monster_gen chance_wizlab
CHANCE:     5%
ORIENT:     float
COLOUR:     U = random
COLOUR:     W = mutagenic
KFEAT:      o = granite_statue
FTILE:      WU.Oo = floor_rough_magenta
TILE:       b = dngn_crystal_magenta
:           wizlab_portal(_G)
MAP
bbbbbbbbbbb
bbbb...bbbb
bWWU.O.UWWb
bWbb...bbWb
bWWWW.WWWWb
bbbbW.Wbbbb
bbbbW.Wbbbb
bbbbW.Wbbbb
bbbbW.Wbbbb
bbbbo.obbbb
bbbb...bbbb
     @
ENDMAP

###############################################################################
# Basic Entrance 6 (by Mu.)
#
NAME:       enter_wizlab_6
TAGS:       uniq_wizlab no_item_gen no_monster_gen chance_wizlab
CHANCE:     5%
ORIENT:     float
SUBST:      x = mc.
TILE:       c = wall_stone_white
TILE:       m = dngn_transparent_wall_magenta
FTILE:      mcx.O = floor_rough_magenta
:           wizlab_portal(_G)
MAP
c.c.ccccccc
x.x.x.x..Oc
.x.x.x.x..c
x.x.x.x.x.c
.x.x.x.x.xc
x.x.x.x.x.c
.x.x.x.x.xc
x.x.x.x.x..
.x.x.x.x.xc
x.x.x.x.x..
.x.x.x.x.xc
ENDMAP

NAME:   enter_wizlab_7
TAGS:   uniq_wizlab no_item_gen no_monster_gen chance_wizlab
CHANCE: 5%
ORIENT: float
KFEAT:  abcd : floor
KFEAT:  ABCD : rock_wall
COLOUR: Aa : yellow
COLOUR: Bb : green
COLOUR: Cc : blue
COLOUR: Dd : magenta
: wizlab_portal(_G)
MAP
xxxxxxxxxxxxx
x...........@
x.xxxxxxxxxxx
xaAbbbbbbbbax
xaAcBBBBBBAax
xaAcCddddcAax
xaAcCdDDCcAax
xaAcCdOdCcAax
xaAcCDDdCcAax
xaAcddddCcAax
xaABBBBBBcAax
xabbbbbbbbAax
xxxxxxxxxxx.x
@...........x
xxxxxxxxxxxxx
ENDMAP

#
#
###############################################################################

default-depth: WizLab

###############################################################################
# And arrivals!
###############################################################################
# Firstly, we have Tukima's Dance Studio.
#
NAME:       wizlab_tukima
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
MONS:       dancing weapon
KFEAT:      M = granite_statue
TILE:       M = dngn_machine_tukima
MARKER:     M = lua:props_marker {veto_fragmentation="veto", veto_disintegrate="veto", \
                                  veto_shatter="veto", slaved_to="tukima"}
{{
local tukima_marker = TriggerableFunction:new {
    func = "tukima_machine",
    repeated = true,
    data = {weapon_count=0},
}

tukima_marker:add_triggerer(DgnTriggerer:new {
    type="turn",
    delay_min=500,
    delay_max=800
})

lua_marker('?', tukima_marker)

if crawl.coinflip() then
  subst("Y = =")
  subst("y = .")
  subst("Rr = c")
else
  subst("Y = c")
  subst("y = m")
  subst("R = .")
  subst("r = =")
end

if crawl.coinflip() then
  subst("X = =")
  subst("x = .")
  subst("Ll = c")
else
  subst("X = c")
  subst("x = m")
  subst("L = .")
  subst("l = =")
end
}}
SUBST:      ? = .
COLOUR:     =cA< = darkgrey
TILE:       c = wall_stone_dark
TILE:       V = dngn_dry_fountain_white
LFLOORTILE: floor_pebble_white
COLOUR:     mMV = silver
TILE:       m = dngn_mirror_wall
KMONS:      8 = ice statue col:silver spells:blink_other;blink_other;blink_other;\
                    blink_other;blink_other;major_healing name:strange_machine \
                    name_replace name_descriptor hd:13 hp:120 \
                    tile:mons_statue_guardian
# please make sure this is the book with Tukima's Dance
KITEM:      8 = book of enchantments
KMONS:      9 = ice statue col:silver spells:blink_other;blink_other;blink_other;\
                    blink_other;blink_other;major_healing name:strange_machine \
                    name_replace name_descriptor hd:13 hp:120 \
                    tile:mons_statue_guardian
KITEM:      9 = scroll of acquirement
:           set_feature_name("clear_rock_wall", "crystal clear mirror")
:           set_feature_name("granite_statue", "strange machine")
:           set_feature_name("dry_fountain_blue", "glistening fountain")
:           set_feature_name("stone_wall", "black marble wall")
:           set_feature_name("floor", "marble floor")
:           set_random_mon_list("dancing weapon")
:           wizlab_setup(_G, "Tukima's Studio")
epilogue{{
            wizlab_milestone(_G, "Tukima's Studio")
}}
MAP
                ccccccc
                ccmmmcc
            cccccm...mccccc
           cc...+.A.<.+...cc
          cc..cccm...mccc..cc
          cc+cccccm.mccccc+cc
          cc.cccccc+cccccc.cc
         cc...cccc...cccc...cc
         cm...mcm..1..mcm...mc
         cm...mcm.....mcm...mc
         cm.V.mcm.....mcm.V.mc
         cm...mcm.....mcm...mc
         cm...mcm..1..mcm...mc
         cc...cccc...cccc...cc
         ccc.cccccc+cccccc.ccc
          cc+ccccm...mcccc+cc
         ccm.mccm.....mccm.mcc
         cm.1..+...V...+..1.mc
        ccXm.mccm.....mccm.mYcc
      cccxccmlcccm...mcccrmccycc
      ccm.mcccLcccm.mcccRcccm.mcc
     ccm...mLLcccm...mcccRRm...mcc
    ccm..$..mcccm..?..mcccm..$..mcc
    cm..$8$..m+m...M...m+m..$9$..mc
    ccm..$..mcccm.....mcccm..$..mcc
     ccm...mcc ccm...mcc ccm...mcc
      ccmmmcc   ccmmmcc   ccmmmcc
       ccccc     ccccc     ccccc
ENDMAP

###############################################################################
# Eringya's Formal Garden
#
# Map was based on this image: http://upload.wikimedia.org/wikipedia/commons/5
#          /58/Plan_du_ch%C3%A2teau_et_des_jardins_de_Clagny_dessin%C3%A9_par_
#          Maraine_XVIIe_si%C3%A8cle.jpg (concat it back together to get the
#          full link).
#
# TODO: Needs vine-covered statues, rose-covered archway.
#       The map is too static. Some ideas by dpeg: loot behind plants or
#       bushes, so you'll have to cut/burn your way there. With catastrophic
#       effects, of course (plants turning into oklobs, fruits turning into
#       spores or (if possible) animated weapons called like the fruit etc.)
#       We could add a interesting little sub-game by having ballistos spawn
#       on their own - and these could be aggressive ballistos, too!
NAME:       wizlab_eringya
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
MONS:       centaur col:green, centaur warrior col:lightgreen
MONS:       oklob plant
MONS:       stone golem name:vine_covered name_adjective col:lightgreen \
            tile:mons_vine_golem
MONS:       toadstool
SUBST:      y = ct
COLOUR:     G = lightgrey
TILE:       G = dngn_statue_centaur
KFEAT:      / = stone_arch
KFEAT:      _ = altar_fedhas
MARKER:     A = feat:stone_arch
TILE:       c = wall_brick_vines
LROCKTILE:  wall_brick_vines
LFLOORTILE: floor_grass
ITEM:       any fixed theme book, any fixed level book, any magical staff / any rod w:2
{{

local grow_marker = TriggerableFunction:new { func = "wizlab_eringya_grow",
                                              repeated = true }

grow_marker:add_triggerer(DgnTriggerer:new { type="turn",
        delay_min=500, delay_max=800, })

lua_marker("_", grow_marker)
}}
:           set_border_fill_type("stone_wall")
:           wizlab_setup(_G, "Eringya's Formal Garden")
:           set_feature_name("stone_arch", "rose-covered archway")
:           set_feature_name("granite_statue", "vine-covered statue")
:           set_feature_name("stone_wall", "crumbling stone wall")
:           set_feature_name("floor", "the grass-covered ground")
:           set_random_mon_list ("oklob plant / centaur / centaur warrior")
epilogue{{
            wizlab_milestone(_G, "Eringya's Formal Garden")
}}
MAP
ccccccccccccccccccccccccccccccccccccccccccccc
ctttttttttttttttttttttttttttttttttttttttttttc
ctttttttt...........................ttttttttc
ctttt.....tttttttttttt.tttttttttttt.....ttttc
cttt..tt.tttttttttt.......tttttttttt.tt..tttc
ct.1.tGt............<.T.A............tGt.1.tc
cttt..tt.tttttttttt.......tttttttttt.tt..tttc
ctttt.....tttttttttttt.tttttttttttt.....ttttc
ctttttttt...........................ttttttttc
cttttttttttttttttttttt.tttttttttttttttttttttc
ctttttttttyyyttttttty...ytttttttyyytttttttttc
ctttttttty...yttttty.....yttttty...yttttttttc
cttttttt..111.........T.........111..tttttttc
ctttttt...121.tttttc.....cttttt.121...ttttttc
cttttt.tty...yttttttcc=cctttttty...ytt.tttttc
ctttt.tttty.yttttttt.....ttttttty.ytttt.ttttc
cttt.tttttt.tttttttyd232eyttttttt.tttttt.tttc
cttt.tttttt..tttttttydefyttttttt..tttttt.tttc
ctttt.tttttt..tttttttytyttttttt..tttttt.ttttc
cttttt.tttttt..ttttttttttttttt..tttttt.tttttc
ctttttt.tttttt..tttttcccttttt..tttttt.ttttttc
cttttyyy/yyyttt..ttty...yttt..tttyyy/yyyttttc
cttty...1...yttt..ty..1..yt..ttty...1...ytttc
ctty...1T1...yttt....1T1....ttty...1T1...yttc
cttty...1...yttt..ty..2..yt..ttty...1...ytttc
cttttyyy/yyyttt..ttty...yttt..tttyyy/yyyttttc
ctttttt.tttttt..tttttcccttttt..tttttt.ttttttc
cttttt.tttttt..ttttttttttttttt..tttttt.tttttc
ctttt.tttttt..ttttt.G._.G.ttttt..tttttt.ttttc
cttt.tttttt..ttttt...4.4...ttttt..tttttt.tttc
cttt.ttttt..ttttt...........ttttt..ttttt.tttc
ctttt.ttty/ytttt....cc=cc....tttty/yttt.ttttc
cttttt.ty...yttttttcc...cctttttty...yt.tttttc
ctttttt./.1./.ttttcc..2..cctttt./.1./.ttttttc
cttttttty...yt...../.1T1../....ty...ytttttttc
cttttttttyyyttttttty.....ytttttttyyyttttttttc
ctttttttttttttttttttyytyytttttttttttttttttttc
ccccccccccccccccccccccccccccccccccccccccccccc
ENDMAP

###############################################################################
# Doroklohe's Forbidden Tomb
#
# It seems as if he practised box casting. I wonder what that's good for.
# Vault by dpeg. Thanks to Enne for box_glyph and to Jude for triggers.
#
# A bleach sun settles in the smog-stained sky
# Dismembered bodies stray in disarray
# Breakfast is served in the Manchester Morgue
# The beginning of a horrifying day
#                                    Impetigo 1992
#
# TODO: Tiles.
NAME:       wizlab_doroklohe
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
LROCKCOL:   yellow
KFEAT:      ! = x
{{
function make_box(cenx, ceny, gly)
  for ox = -1, 1 do
    for oy = -1, 1 do
      local x = cenx + ox
      local y = ceny + oy
      if (x >= 1 and y >= 1 and x <= width() and y <= height()) then
        if (ox ~= 0 or oy ~= 0) then
          mapgrd[x][y] = gly;
        end
      end
    end
  end
end

function box_glyph(findgly, boxgly)
  local glyphs = {gly_points(findgly)}
  for i = 1, #glyphs, 2 do
    -- This is ugly.  gly_points should return 1-indexed coordinates.
    -- No longer ugly, as mapgrd is 0-indexed, like gly points.
    make_box(glyphs[i], glyphs[i+1], boxgly)
  end
end
}}
#           There are two layouts: round and grid.
#           Round has 19 boxes: 12 % and 6 * and 1 |
#           Grid has 21 boxes: b-u and |
#           Layout for grid can be regular or random.
#
:           local layout = crawl.random2(13)
:           if layout < 3 then
#           Preparation for the rare regular grid layout.
SUBST:      b=., c=., d=., e=., f=., g=., h=., i=., j=., k=.
SUBST:      l=., m=., n=., o=., p=., q=., r=., s=., t=., u=.
SUBST:      B=b, C=c, D=d, E=e, F=f, G=g, H=h, I=i, J=j, K=k
SUBST:      L=l, M=m, N=n, O=o, P=p, Q=q, R=r, S=s, T=t, U=u
:           end
:           if layout > 9 then
#           First the round layout...
COLOUR:     _ = darkgrey
KFEAT:      _ = stone_wall
TILE:       _ = wall_stone_black_marked / wall_stone_dark w:4 / wall_stone_black_marked
SUBST:      b=., c=., d=., e=., f=., g=., h=., i=., j=., k=.
SUBST:      l=., m=., n=., o=., p=., q=., r=., s=., t=., u=.
SUBST:      B=., C=., D=., E=., F=., G=., H=., I=., J=., K=.
SUBST:      L=., M=., N=., O=., P=., Q=., R=., S=., T=., U=.
:           else
#           ...and now the grid layout.
SUBST:      _ = .
SUBST:      *=., %=.
SUBST:      B=b, C=c, D=d, E=e, F=f, G=g, H=h, I=i, J=j, K=k
SUBST:      L=l, M=m, N=n, O=o, P=p, Q=q, R=r, S=s, T=t, U=u
NSUBST:     b = 1:b / *:.
NSUBST:     c = 1:c / *:.
NSUBST:     d = 1:d / *:.
NSUBST:     e = 1:e / *:.
NSUBST:     f = 1:f / *:.
NSUBST:     g = 1:g / *:.
NSUBST:     h = 1:h / *:.
NSUBST:     i = 1:i / *:.
NSUBST:     j = 1:j / *:.
NSUBST:     k = 1:k / *:.
NSUBST:     l = 1:l / *:.
NSUBST:     m = 1:m / *:.
NSUBST:     n = 1:n / *:.
NSUBST:     o = 1:o / *:.
NSUBST:     p = 1:p / *:.
NSUBST:     q = 1:q / *:.
NSUBST:     r = 1:r / *:.
NSUBST:     s = 1:s / *:.
NSUBST:     t = 1:t / *:.
NSUBST:     u = 1:u / *:.
#           Of the outer boxes, three are damaged.
SHUFFLE:    bcdefghijklm
:           box_glyph('b', 'X')
:           box_glyph('c', 'Y')
:           box_glyph('d', 'Z')
SUBST:      b = .
SUBST:      c = .
SUBST:      d = .
NSUBST:     X = 1=. / *=!:20 .:1
NSUBST:     Y = 1=. / *=!:30 .:1
NSUBST:     Z = 1=. / *=!:50 .:1
#           For the other boxes, prepare same setup as for the
#           round layout (i.e. six *'s)
SHUFFLE:    nqru
SUBST:      e=%, f=%, g=%, h=%, i=%, j=%, k=%, l=%, m=%, n=%
SUBST:      o=*, p=*, q=%, r=*, s=*, t=*, u=*
:           end
#           Monsters
#            0 Tomb set: zombies, mummies (weight *2)
#            1 Demons (if demons are added or reclassified, please change!)
#            2 Golems
#            TODO: 3 Holy set (for later)
:           local mrnd = crawl.random2(4)
:           if mrnd == 0 then
KMONS:      % = clay golem / wood golem / toenail golem w:2
KMONS:      * = stone golem / crystal golem / iron golem
KMONS:      | = electric golem
:           set_random_mon_list("clay golem / wood golem / toenail golem w:2 / " ..
:                               "stone golem / crystal golem / iron golem")
:           elseif mrnd == 1 then
KMONS:      % = blue devil / iron devil / ynoxinul / neqoxec / ice devil /\
                / chaos spawn / demonic crawler / hellwing / orange demon /\
                soul eater / sun demon
KMONS:      * = lorocyproca / reaper / shadow demon / tormentor / hellion
KMONS:      | = blizzard demon / green death / hell sentinel / brimstone fiend /\
                shadow fiend / ice fiend / executioner / balrug / cacodemon
:           set_random_mon_list(
:               "blue devil / iron devil / ynoxinul / neqoxec / ice devil /" ..
:               "/ chaos spawn / demonic crawler / hellwing / orange demon /" ..
:               "soul eater / sun demon / " ..
:               "lorocyproca / reaper / shadow demon / tormentor / hellion")
:           else
KMONS:      % = place:D:15 zombie / guardian mummy w:2
KMONS:      * = place:D:27 zombie / greater mummy w:5
KMONS:      | = ancient lich
:           set_random_mon_list("place:D:15 zombie / place:D:27 zombie / guardian mummy")
:           end
#           Loot.
#           0 = scrolls. 1 = armours. 2 = mixed.
:           local lrnd = crawl.random2(3)
:           if lrnd == 0 then
KITEM:      % = any scroll / any scroll q:2 w:3 / any scroll q:3 w:1
:           kitem("* = " .. dgn.good_scrolls)
KITEM:      | = scroll of acquirement / scroll of enchant weapon III q:2 /\
                scroll of blinking q:2, scroll of fog q:2, scroll of holy word q:2
:           elseif lrnd == 1 then
KITEM:      % = any armour
KITEM:      * = any good_item armour
KITEM:      | = cursed robe ego:resistance / cursed gold dragon armour
:           else
KITEM:      % = any / star_item w:2
KITEM:      * = star_item / superb_item w:2
KITEM:      | = superb_item
:           end
#           Boxification:
:           box_glyph('%', '!')
:           box_glyph('*', '!')
:           box_glyph('|', '!')
#           Intentionally colouring the floor glyphs of the central room only.
#           The squares beneath the boxes are to remain uncoloured.
COLOUR:     ^ = darkgrey
TILE:       ^ = wall_stone_black_marked / wall_stone_dark w:4 / wall_stone_black_marked
COLOUR:     = = yellow
KFEAT:      ^ = stone_wall
COLOUR:     . = darkgrey / blue w:3 / cyan w:1
MARKER:     ! = lua:portal_desc {wall_drop=1}
MARKER:     = = lua:portal_desc {wall_drop=1}
TILE:       ! = dngn_stone_wall_yellow
{{
local box_marker = TriggerableFunction:new {
    func="wizlab_doroklohe_convert_boxes",
    repeated=true, data={phase=1} }

box_marker:add_triggerer(DgnTriggerer:new { type="turn",
    delay_min=500, delay_max=1000})

lua_marker("A", box_marker)
}}
:           set_feature_name("rock_wall", "strange rock wall")
:           set_feature_name("stone_wall", "highly decorated stone wall")
:           set_feature_name("floor", "rough-hewn floor")
:           wizlab_setup(_G, "Doroklohe's Tomb")
epilogue{{
            wizlab_milestone(_G, "Doroklohe's Tomb")
}}
MAP
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
^________________...........________________^
^____________...................____________^
^_________........................._________^
^_______b....cc......d%d......ee....f_______^
^_____bB.....cC%.....dDd.....%Ee.....Ff_____^
^____bb...............................ff____^
^___.....................................___^
^__........%......o*.....*p......%........__^
^__.......nnN....oO.......Pp....Qqq.......__^
^_........................................._^
^_...mm...............................gg..._^
^_...mM..%......*.....|.....*......%..Gg..._^
^_...mm...............................gg..._^
^_........................................._^
^__.......uuU....tT.......Ss....Rrr.......__^
^__........%......t*.....*s......%........__^
^___.....................................___^
^____ll...............................hh____^
^_____lL.....kK%.....jJj.....%Ii.....Hh_____^
^_______l....kk......j%j......ii....h_______^
^_________........................._________^
^____________...................____________^
^________________...........________________^
^^^^^^^^^^^^^^^^^^^^^^.^^^^^^^^^^^^^^^^^^^^^^
                ^____...____^
                ^__.......__^
                ^_...!=!..._^
                ^_.<.=A=.<._^
                ^_...!=!..._^
                ^__.......__^
                ^____...____^
                ^^^^^^^^^^^^^
ENDMAP

##############################################################################
# Cigotuvi's Fleshworks (by Mu.)
#
# Cigotuvi has mastered the art of manipulating flesh, and his lab is a
# living testament to this fact, seeming like the interior of some
# ghastly beast. The walls and floor are slick and membranous, pulsing to an
# unheard heartbeat and oozing thick, green ichor from every inch.
#
# The bulk of Cigotuvi's Fleshworks is devoted to cells that house test
# subjects in various stages of degeneration. Most are sickly humanoids; the
# others are ugly things, pulsating lumps and abominations.
#
# The central, circular chamber houses Cigotuvi's flesh golem.
# The Eastern half of his lab is dominated by a snaking passageway filled with
# pulsating lumps and the occasional ugly thing.
#
# The western half of his lab is full of abominations, including the terrible
# "Cigotuvi's Monster".
#
# TODO:     * door tile is *really* ugly, fix this?
#           * Cigotuvi's Monster needs a much bigger buff. Convert to unique?
NAME:       wizlab_cigotuvi
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
KPROP:      . = w:1 bloody / w:15 nothing
KPROP:      ' = bloody / w:5 nothing
KMONS:      a = human name:sickly dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_human / \
            human name:monstrous dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_human  / \
            human name:deformed dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_human   / \
            human name:twisted dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_human    / \
            human name:grotesque dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_human  / \
            human name:hideous dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_human    / \
            human name:febrile dbname:deformed_humanoid n_adj n_noc tile:mons_deformed_human
KMONS:      b = elf name:sickly dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_elf     / \
            elf name:monstrous dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_elf      / \
            elf name:deformed dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_elf       / \
            elf name:twisted dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_elf        / \
            elf name:grotesque dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_elf      / \
            elf name:hideous dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_elf        / \
            elf name:febrile dbname:deformed_humanoid n_adj n_spe n_noc tile:mons_deformed_elf
KMONS:      d = orc name:sickly dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_orc     / \
            orc name:monstrous dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_orc      / \
            orc name:deformed dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_orc       / \
            orc name:twisted dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_orc        / \
            orc name:grotesque dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_orc      / \
            orc name:hideous dbname:deformed_humanoid n_adj n_spe tile:mons_deformed_orc        / \
            orc name:febrile dbname:deformed_humanoid n_adj n_noc tile:mons_deformed_orc
KMONS:      u = ugly thing / w:2 very ugly thing
KMONS:      U = very ugly thing
KMONS:      J = pulsating lump
KMONS:      x = small abomination
KMONS:      X = large abomination
KMONS:      e = generate_awake giant eyeball
SUBST:      " = J:1 / .:6
KMONS:      8 = col:red clay golem name:flesh_golem name_replace \
            tile:mons_flesh_golem name_descriptor
KMONS:      M = col:mutagenic tentacled monstrosity name:Cigotuvi's_Monster \
            name_replace hp:250 tile:mons_cigotuvis_monster
MARKER:     ! = lua:fog_machine { \
                 pow_max = 15, delay_min = 10, delay_max = 40, \
                 size = 2, size_buildup_amnt = 20, \
                 size_buildup_time = 500, cloud_type = "mutagenic fog", \
                 excl_rad = -1 }
MARKER:     ? = lua:fog_machine { \
                 pow_max = 20, delay_min = 10, delay_max = 40, \
                 size = 5, size_buildup_amnt = 10, \
                 size_buildup_time = 25, cloud_type = "mutagenic fog", \
                 excl_rad = -1 }
LFLOORCOL:  magenta
LFLOORTILE: floor_nerves
LROCKTILE:  wall_flesh
TILE:       c = wall_flesh
TILE:       m = wall_transparent_flesh
TILE:       + = no_random dngn_fleshy_orifice
COLOUR:     m = yellow
COLOUR:     c+ = lightred
COLOUR:     W = green
:           set_feature_name("shallow_water", "Viscous fluid")
:           set_feature_name("stone_wall", "sinewy wall")
:           set_feature_name("clear_rock_wall", "thin membrane")
:           set_feature_name("floor", "pulsating floor")
: lua_marker('+', props_marker {
:           door_description_noun="fleshy orifice",
:           door_berserk_verb_open="You part the %s%s",
:           door_berserk_adjective="with a squelch!",
:           door_berserk_verb_close="You squeeze the %s%s closed",
:           door_noisy_verb_open="You part the %s%s with a squelch!",
:           door_noisy_verb_close="You squeeze the %s%s closed with a squelch!",
:           door_airborne_verb_open="You reach down and part the %s%s.",
:           door_airborne_verb_close="You reach down and squeeze the %s%s closed.",
:           door_verb_open="You part the %s%s.",
:           door_verb_close="You squeeze the %s%s shut."
:           })
KITEM:      $ = potion of degeneration / potion of decay / \
            potion of mutation / w:3 potion of strong poison / \
            w:2 potion of poison / w:5 potion of curing / \
            w:3 potion of heal wounds / w:1 potion of cure mutation
KITEM:      * = gold
KITEM:      % = amulet of resist mutation good_item
KITEM:      : = randbook disc:transmutation owner:Cigotuvi
KITEM:      ^ = book of morphology / randbook disc:transmutation \
                owner:Cigotuvi spell:cigotuvi's_degeneration
KITEM:      | = staff of death
KITEM:      l = scroll of unholy creation
NSUBST:     L = 1:| / *:l
:           wizlab_setup(_G, "Cigotuvi's Fleshworks")
:           set_random_mon_list("pulsating lump / small abomination / ugly thing / very ugly thing")
epilogue{{
            wizlab_milestone(_G, "Cigotuvi's Fleshworks")
}}
MAP
ccccccccccccccccccccccccccccccccccccccccccccc
ccLLLcccc.cccccccccccAccccccccccccWWWW.U:cccc
c.....c.....ccc...ccc+cccccccccccW.....uU^ccc
c.X.........cc.u...m...m..ccccccW.......uU:cc
c.M........cc...b..m.x.m.a.cccccW..........cc
c.X........cc...d..m...m.u..ccccW.........Wcc
c..........cc.cccccm...mc...ccccc........Wccc
c.....ccc+ccccc..cccc+cccccccccccc......Wcccc
ccLLLccc..ccccuuu.cm...m..d..ccccc+cccccccccc
cccccccc..ccc..!...m.x.m.a..cccccc""ccccccccc
cc$$cccc..ccc.uuu..m...m...ccccccc""cc**%**cc
c$$$$cc...cccc....cm...m.cccWccccc""c...cee.c
c$$$$+...cccccc..cccc+cccc...Wcccc""c...c...c
c$$$$c...ccccccccc.m...m.xx...Wccc""cmm+c+mmc
cc$ccccc+cccccccc..m.x.m...u..Wccc""c.......c
ccccccc...cccc...a.m...m....x.cc.c""c.......c
cccc.........c..b..m...mc....cc..c""c...!...c
c.xJ...ccc...cc..cccc+cccc..cc...c""c......cc
c...ccccccc+cccccc.m.....ccccJJJJc""+.....ccc
cc...ccccc'''cccc..m.....uccJJJJJc""ccccccccc
cc...ccc''''''cc.!.m.....<uc.....+"""""""""cc
c..cccc''''''''cc.......cuccc....cc"""""""""c
c..ccc'''''''''cccccc+cccccccccccccccccccc""c
c..cc''''''''''ccccc...ccccccc""""""""""""""c
c..cc''''''''''ccc.......cccc""""""""""""""cc
c..c'''''''''''cc.........ccc""cccccccccccccc
c..c+c+c+c+c+ccc...........cc""""""""""""""cc
c..cXcXcXcXcXccc...........ccc""""""""""""""c
c..cccccccccccc.....c.c.....cccccccccccccc""c
c...xJ........+......?......+"""""ccc"""""""c
c...xJ........c.....c.c.....c""""""c"""""""cc
ccmmmccccmmmcccc...........cccccc""c""ccccccc
c.....cc.....cccWW.......WWcc""""""c""""""ccc
cc.JJccccuuucccccWW..8..WWcc""""""ccc""""""cc
ccJJ.cccc.a.ccccccWWWWWWWccc""ccccccccccc""cc
cc.dccccccuuccccccccWWWccccc"""""""""""""""cc
ccccccccccccccccccccccccccccc"""""""""""""ccc
ccccccccccccccccccccccccccccccccccccccccccccc
ENDMAP

###############################################################################
# Iskenderun's Mystic Tower
#
# TODO: Fix up the tiles to make them pretty. It's really quite boring. I've
#       no idea how it could be improved or made interesting, but I think that
#       a few boring maps is fine - it means that you don't know exactly what
#       you're going to get.
NAME:       wizlab_iskenderun
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup patrolling
:           wizlab_setup(_G, "Iskenderun's Mystic Tower")
MONS:       purple draconian / deep elf mage spells:iskenderun's_mystic_blast \
            / nothing
MONS:       statue tile:mons_statue_mage spells:iskenderun's_mystic_blast;orb_of\
            _destruction col:lightmagenta
KITEM:      D = star_item, star_item / superb_item, star_item
KITEM:      E = randbook disc:conjuration owner:Iskenderun spells:iskenderun's_mystic\
                _blast, randbook disc:conjuration owner:Iskenderun, any book
KITEM:      F = any book good_item, any book good_item, any book
KMONS:      DEF = purple draconian
COLOUR:     v = magenta
COLOUR:     Uc = lightmagenta
TILE:       c = wall_zot_magenta
TILE:       v = dngn_metal_wall_magenta
LFLOORTILE: floor_rough_magenta
LFLOORCOL:  magenta
MARKER:     + = lua:restrict_door()
MARKER:     R = lua:fog_machine { \
                pow_max = 10, delay_min = 10, delay_max = 40, \
                size = 15, cloud_type = "purple smoke" \
            }
SUBST:      R = .
KFEAT:      - = altar_sif_muna
KFEAT:      _ = altar_vehumet
SHUFFLE:    DEF
:           set_random_mon_list("purple draconian / deep elf mage")
epilogue{{
            wizlab_milestone(_G, "Iskenderun's Mystic Tower")
}}
MAP
ccccccccccccccccccccccccccccccccccccccccccc
cAc..c.c.c.c.c.c.c.ccRcc.c.c.c.c.c.c.cc.cRc
cc.cc<c.c.c.c.c.c.c.c.c.c.c.c.c.c.c.c.cc.cc
c.c.ccc.............c.c..............cc.c.c
c.cc...................................cccc
cc<c......2.....................2......c.cc
c.cc.............v.vv.vv.v..............c.c
cc..............vvv.1R1.vvv..............cc
c.c............v.v.1vvv1.v.v............c.c
cc............vvvv1vvEvv1vvvv............cc
c.c..........v..v1vvv+vvv1v..v..........c.c
cc..........vv.v1vv.....vv1v.vv..........cc
c.c........v.vv1vv.......vv1vv.v........c.c
cccc.......vvv1vvv.......vvv1vvv.......cccc
cR.....2......RvD+...2...+1+R......2.....Rc
cccc.......vvv1vvv.......vvv1vvv.......cccc
c.c........v.vv1vv.......vv1vv.v........c.c
cc..........vv.v1vv.....vv11.vv..........cc
c.c..........v..v1vvv+vvv1v..v..........c.c
cc............vvvv1vvFvv1vvvv............cc
c.c............v.v.1vvv1.v.v............c.c
cc..............vvv.1R1.vvv..............cc
c.c..............v.vv.vv.v..............c.c
cc.c......2.....................2......c.cc
cccc...................................cccc
c.c.cc..............c.c..............cc.c.c
cc.cc.c.c.c.c.c.c.c.c.c.c.c.c.c.c.c.c.cc.cc
cRc.cc.c.c.c.c.c.c.ccRcc.c.c.c.c.c.c.cc.cRc
ccccccccccccccccccccccccccccccccccccccccccc
ENDMAP

###############################################################################
# Zonguldrok's Shrine
NAME:       wizlab_zonguldrok
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
:           wizlab_setup(_G, "Zonguldrok's Shrine")
SUBST:      ? = txxx
SUBST:      ! = t..
SUBST:      G = G...
NSUBST:     Z = Z / .
MONS:       patrolling skeletal warrior
MONS:       generate_awake ancient lich  col:brown name:antique_lich name_replace \
            name_descriptor tile:mons_zonguldrok_lich
COLOUR:     t = darkgrey / lightgrey
TILE:       t = dngn_tree_dead
LFLOORCOL:  darkgrey
LROCKCOL:   darkgrey
NSUBST:     d = 1:e / *:d
ITEM:       any scroll / any potion / any book w:2
ITEM:       long sword unrand:sword_of_zonguldrok
{{
lua_marker("G", portal_desc { grave = 1 })
lua_marker("Z", portal_desc { wizard_grave = 1})
lua_marker("W", portal_desc { desc="Zonguldrok's gravestone",
        veto_fragmentation="veto", veto_disintegrate="veto", veto_shatter="veto" })

local zombies_appear_marker = TriggerableFunction:new {
    func = "wizlab_zonguldrok_spawn_zombies",
    repeated = true
}

local zombies_killed_marker = TriggerableFunction:new {
    data = {
        number_killed = 0,
        door_appeared = false
    },
    func = "wizlab_zonguldrok_killed_zombie",
    repeated = true
}

local wizard_appear_marker = TriggerableFunction:new {
    data = {
        awoke = false
    },
    func = "wizlab_zonguldrok_awaken_wizard",
    repeated = true,
    props = {listen_to_slaves = true, only_at_slave = true }
    }

wizard_appear_marker:add_triggerer(DgnTriggerer:new {
    type = "player_move" })

zombies_appear_marker:add_triggerer(DgnTriggerer:new {
    type = "turn",
    delay_min = 200,
    delay_max = 300
})

zombies_killed_marker:add_triggerer(DgnTriggerer:new {
    type = "monster_dies",
    target = "any"
})

lua_marker("M", zombies_appear_marker)
lua_marker("D", zombies_killed_marker)
lua_marker("L", Triggerable.synchronized_markers(wizard_appear_marker))

}}
:           set_feature_name("granite_statue", "gravestone")
:           set_feature_name("floor", "the ground")
SUBST:      M = x
SUBST:      D = c
COLOUR:     W = yellow
TILE:       W = dngn_gravestone_ornate
TILE:       G = dngn_gravestone
SUBST:      W = G
SUBST:      LZ = .
LFLOORTILE: floor_tomb
LROCKTILE:  wall_hall_darkgray
TILE:       c = wall_stone_gray
:           set_random_mon_list("human zombie / skeletal warrior")
epilogue{{
            wizlab_milestone(_G, "Zonguldrok's Shrine")
}}
MAP
M   xxxxxxxxxxxxxxxxxxx
   xx?????????????????xx
  xx?!!!!!!!!!!!!!!!!!?xx
 xx?!!.G.G.G.G.G.G.G.!!?xx
xx?!!.G.G.G.G.G.G.G.G.!!?xx
x?!!.G.G.G.G.G.G.G.G.G.!!?x
x?!.G.G.GcccccccccG.G.G.!?x
x?!G.G.G.c.ddcdd.c.G.G.G!?x
x?!.G.G.ccdd.c.ddcc.G.G.!?x
x?!G.Gcccddcc+ccddcccG.G!?x
x?!.G.c.dd.cLLLc.dd.c.G.!?x
x?!G.Gc$.ccc...ccc.$cG.G!?x
x?!.G.c$$c..ZZZ..c$$c.G.!?x
x?!G.Gcccc..ZWZ..ccccG.G!?x
x?!.G.c..+..ZZZ..+..c.G.!?x
x?!G.Gc.1ccc...ccc1.cG.G!?x
x?!.G.c..1.c...c.1..c.G.!?x
x?!G.Gccc.1ccccc1.cccG.G!?x
x?!.G.G.cc.1.c.1.cc.G.G.!?x
x?!G.G.G.c...c...c.G.G.G!?x
x?!.G.G.GccccDccccG.G.G.!?x
x?!!.G.G.G.GV.VG.G.G.G.!!?x
xx?!!.G.G.G..<..G.G.G.!!?xx
 xx?!!.G.G.G.A.G.G.G.!!?xx
  xx?!!!!!!!!!!!!!!!!!?xx
   xx?????????????????xx
    xxxxxxxxxxxxxxxxxxx
ENDMAP

###############################################################################
# Wucad Mu's Monastery
#
# TODO: I think this is done, apart from not having "alien"-esque statue tiles.
NAME:       wizlab_wucad
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
SUBST:      T = t.
KMONS:      8 = orange crystal statue name:Statue_of_Wucad_Mu n_rpl n_the \
                hd:20 hp:300 tile:mons_wucad_mu_statue
KITEM:      8 = staff unrand:staff_of_wucad_mu, book of enchantments
COLOUR:     =c = darkgrey
COLOUR:     t = lightred / red w:3
TILE:       t = dngn_tree_lightred / dngn_tree_red w:4 / dngn_tree_yellow w:4
# This used to specify dngn_statue_troll as the only middle case, but that tile
# no longer exists.
TILE:       G = dngn_granite_statue w:1 / \
                dngn_statue_angel w:1 / \
                dngn_statue_imp w:1 / \
                dngn_statue_ancient_evil w:1 / \
                dngn_statue_ancient_hero w:1
COLOUR:     AG = red
COLOUR:     < = lightred
TILE:       c = dngn_stone_dark
LFLOORTILE: floor_pebble_white
KFEAT:      ' = open_door
KFEAT:      1234567 = .
KMONS:      1234567 = nothing
LROCKCOL:   darkgrey
ITEM:       potion of experience, manual of fighting / manual of armour / manual of \
            spellcasting, manual of staves / manual of fighting / manual of dodging,\
            potion of gain dexterity / potion of gain strength / potion of gain \
            intelligence
LFLOORCOL:  white
KMONS:      F = human name:monk n_suf col:white hd:10 dur:2 sum:shadow_creatures \
            nas:old_memories tile:mons_human_monk seen / rock troll name:monk n_suf \
            dur:2 seen sum:shadow_creatures nas:old_memories tile:mons_rock_troll_monk \
            / iron troll name:monk n_suf col:white dur:2 sum:shadow_creatures \
            nas:old_memories seen tile:mons_iron_troll_monk w:5

{{
dgn.persist.wucad_mu_died = false

local function trigfn (spot)
  return Triggerable.synchronized_markers(function_at_spot(
            "wizlab_wucad_msgfn",
            { spot=spot, trig = false}, true, { only_at_slave = true,
              listen_to_slaves = true }))
end

lua_marker('1', trigfn(1))
lua_marker('2', trigfn(2))
lua_marker('3', trigfn(3))
lua_marker('4', trigfn(4))
lua_marker('5', trigfn(5))
lua_marker('6', trigfn(6))
lua_marker('7', trigfn(7))


local summon_marker = TriggerableFunction:new ({
    func="wizlab_wucad_summon_monks",
    repeated=true })

summon_marker:add_triggerer(DgnTriggerer:new {type="turn", delay_min=150,
    delay_max=400 })

local wucad_marker = TriggerableFunction:new ({
    func="callback.wizlab_wucad_wucad_died",
    repeated=false })

wucad_marker:add_triggerer(DgnTriggerer:new {type="monster_dies",
    target="Statue of Wucad Mu"})

lua_marker('A', summon_marker)
lua_marker('A', wucad_marker)

}}
MARKER:     G = lua:props_marker {veto_fragmentation="veto", veto_disintegrate="veto", \
                                  veto_shatter="veto" }
MARKER:     = = lua:props_marker {veto_fragmentation="veto", veto_disintegrate="veto", \
                                  veto_shatter="veto" }
MARKER:     + = lua:props_marker {veto_fragmentation="veto", veto_disintegrate="veto", \
                                  veto_shatter="veto" }
MARKER:     ' = lua:props_marker {veto_fragmentation="veto", veto_disintegrate="veto", \
                                  veto_shatter="veto" }
MARKER:     c = lua:props_marker {veto_fragmentation="veto", veto_disintegrate="veto", \
                                  veto_shatter="veto" }
MARKER:     t = lua:props_marker {veto_fragmentation="veto", veto_disintegrate="veto", \
                                  veto_shatter="veto", veto_fire="veto" }
:           wizlab_setup(_G, "Wucad Mu's Monastery")
:           set_border_fill_type("tree")
:           set_random_mon_list("shadow / phantom w:1 / flayed ghost w:1 / hungry ghost w:1")
:           set_feature_name("tree", "autumnal tree")
:           set_feature_name("stone_wall", "crumbled stone wall")
:           set_feature_name("granite_statue", "strange statue")
:           set_feature_name("floor", "timeless floor")
epilogue{{
            wizlab_milestone(_G, "Wucad Mu's Monastery")
}}
MAP
tttttttttttttttttttttttttttttttttttttttt
tttttttttttttttttttttttttttttttttttttttt
ttttttttttttttTTTTTTTttttttttttttttttttt
ttttttTTTTTTTT.......TTTTTTTTTTTTttttttt
tttttT.........ccccc.............Ttttttt
ttttT.........cc777cc.............Tttttt
tttT.......cccc77777cccc...........Ttttt
ttT.......cc..cc777cc..cc......ccc..Tttt
ttT......cc....cc+cc....cc....cc6cc..Ttt
ttT.....Tc....G.....G....cT..cc6U6cc.Ttt
ttT.....ccG.............Gcc...cc6cc..Ttt
ttT......+.......8.......+.....c+c...Ttt
ttT.....ccG.............Gcc..........Ttt
ttT.....Tc....G.....G....cT..........Ttt
ttT.c..cTcc.............cccT.........Ttt
ttTcc++ccccccc.......ccccccc+cc......Ttt
ttcc5555cccdeccc===cccfgccc444cc.....Ttt
ttc555555c....c.....c....c44444c....Tttt
ttc555555cc.............cc44444cc..ctttt
ttc555555ccccccccccccccccccc+cccc++ccttt
ttcc5555ccc.............ccc222cc3333cctt
tttccccccc...............+22222+33333ctt
ttttttttccc..ccc+++ccc..ccc222cc3333cctt
tttttttttcccccTT111Ttccccccccccccccccttt
ttttttttttttttT11111Tttttttttttttttttttt
tttttttttttT.........TTTTTTttttttttttttt
tttccccctttT.....G........Ttcccccttttttt
ttcc...cctT..............Ttcc...cctttttt
ttc..A..'..................'..<..ctttttt
ttcc...cctT.....TTTT.....Ttcc...cctttttt
tttccccctttT...TTttTT....Tttcccccttttttt
ttttttttttttTTTTttttTTTTTttttttttttttttt
tttttttttttttttttttttttttttttttttttttttt
tttttttttttttttttttttttttttttttttttttttt
ENDMAP

##################################################################################
# The Roulette of Golubria (by HangedMan.)
# Golubria's fascination with translocations led him to warp out a sub-realm
# of the Abyss into his own translocations playground, with some nasty and wild
# security systems built in to defend his many assorted possessions.
#
NAME:    wizlab_golubria
TAGS:    no_monster_gen no_item_gen allow_dup no_pool_fixup
ORIENT:  encompass
LFLAGS:  no_tele_control
KMONS:   1 = spatial vortex / blink frog / insubstantial wisp w:1 / nothing w:4
KMONS:   2 = deep elf summoner w:5 ; dart ego:dispersal w:20 | dart w:5 | nothing / \
             rakshasa w:5 ; dart ego:dispersal w:20 | dart w:5 | nothing / \
             boggart ; dart ego:dispersal w:20 | dart w:5 | nothing /  \
             wizard ; dart ego:dispersal w:20 | dart w:5 | nothing
KMONS:   3 = rakshasa w:5 ; staff ego:distortion | staff ego:vorpal w:6 | \
             dagger ego:distortion | dagger ego:vorpal w:6 | \
             spear ego:distortion | spear ego:vorpal w:6 . dart ego:dispersal / \
             crimson imp ; staff ego:distortion | staff ego:vorpal w:6 | \
             dagger ego:distortion | dagger ego:vorpal w:6 | \
             spear ego:distortion | spear ego:vorpal w:6 . dart ego:dispersal / \
             boggart w:5 ; staff ego:distortion | staff ego:vorpal w:6 | \
             dagger ego:distortion | dagger ego:vorpal w:6 | \
             spear ego:distortion | spear ego:vorpal w:6 . dart ego:dispersal / \
             wizard ; staff ego:distortion | staff ego:vorpal w:6 | \
             dagger ego:distortion | dagger ego:vorpal w:6 | \
             spear ego:distortion | spear ego:vorpal w:6 . dart ego:dispersal
# Disclaimer: the following three sets are all Abyss spawns.
KMONS:   04 = large abomination w:40 / small abomination w:40 / large skeleton w:30 / \
              small skeleton / chaos spawn w:5 / soul eater / hellwing / orange demon / \
              rotting devil / hell hound / red devil w:5 / lesser demon w:40 / \
              flying skull / freezing wraith / octopode w:5 / base draconian w:5 / \
              ugly thing w:30 / fire elemental w:5 / air elemental w:5
KMONS:   95 = ynoxinul / smoke demon / sun demon w:5 / sixfirhy / efreet w:5 / \
              hell knight w:5 / demonic crawler / very ugly thing w:5 / \
              unseen horror / vapour w:5 / stone golem w:5 / \
              guardian serpent / naga mage w:5 / brain worm / eidolon w:5 / \
              shadow wraith / anaconda skeleton w:5 / flaming corpse / \
              great orb of eyes w:5 / giant orange brain w:5
KMONS:   6 = executioner w:5 / balrug w:5 / cacodemon / shadow demon / hellion w:5 / \
             tormentor w:5 / lorocyproca w:5 / blizzard demon / green death / \
             reaper / lich w:5 / angel / death drake w:5 / \
             tentacled monstrosity / draconian shifter w:5 / profane servitor w:5
KMONS:   7 = eldritch tentacle
KMONS:   8 = silver statue
# Translocations items, abyss escape aides, shrouds, and an immeadiate aide.
KITEM:   d = scroll of blinking / scroll of teleportation q:2 / \
             wand of teleportation w:5 / any scroll w:1
KITEM:   e = ring of teleport control w:5 / ring of teleportation
KITEM:   f = book of spatial translocations w:5 / book of the warp w:5 / \
             manual of translocations w:5 / randbook disc:translocation numspells:5 / \
             randbook disc:translocation owner:Golubria numspells:7 \
             spells:shroud_of_golubria|passage_of_golubria
KITEM:   g = ring of levitation / potion of levitation q:2 / \
             wand of digging w:5 / lantern of shadows / \
             potion of speed w:5 / scroll of fog / potion of porridge / \
             any wand w:1 / any potion w:1 / any scroll w:1
KITEM:   h = pair of boots ego:levitation w:9 / pair of boots ego:running w:1 / \
             pair of boots ego:stealth w:9 / pair of boots w:1
KITEM:   i = cloak good_item w:75 / randart cloak w:95 / cloak unrand:cloak_of_flash / \
             cloak unrand:cloak_of_starlight / cloak unrand:cloak_of_the_thief
KITEM:   j = wand of disintegration
KITEM:   * = star_item / any w:5, any w:5 / nothing
KITEM:   % = any level:3, any level:3 / nothing
KFEAT:   - = rock_wall
KFEAT:   J = metal_wall
KFEAT:   K = green_crystal_wall
KFEAT:   m = iron_grate
KFEAT:   l = lava w:6 / deep_water w:4 / shallow_water
KFEAT:   D = permarock_wall
KFEAT:   ~ = known teleport trap
KFEAT:   8_ = altar_lugonu
KFEAT:   OPQRSTUVWXYZ&?[ = teleporter
KFEAT:   opsrtuvwxyz@!] = floor
KPROP:   "_a = no_rtele_into
MARKER:  ~ = lua:fog_machine { cloud_type = "translocational energy",  \
             pow_max = 15, delay_min = 30, delay_max = 60, size_min = 2, size_max = 3 }
SHUFFLE: qtwz / twzq / wzqt / zqtw, ypsv / vyps / svyp / psvy, ]?A}
NSUBST:  o = 1:o / 1:Q / 1:Y, p = 1:p / 1:R / 1:Z, q = 1:q / 1:S / 1:&
NSUBST:  r = 1:r / 1:T / 1:O, s = 1:s / 1:U / 1:P, t = 1:t / 1:V / 1:Q
NSUBST:  u = 1:u / 1:W / 1:R, v = 1:v / 1:X / 1:S, w = 1:w / 1:Y / 1:T
NSUBST:  x = 1:x / 1:Z / 1:U, y = 1:y / 1:& / 1:V, z = 1:z / 1:O / 1:W
NSUBST:  @ = 1:@ / 1:P / 1:X / 1:<, 4 = 4:5 / 4:4, ` = 4:d / 4:i / 1:j / 5:% / *:`
NSUBST:  a = 1:_ / 1:_" / *:a, + = 2:+ / *:c, ( = 1:! / 1:[ / *:<
NSUBST:  { = 2:< / *:d, 2 = 1:66699 / 1:66993 / 2:9 / 1:993 / 1:92 / *:2
NSUBST:  d = 2:* / 2:e / 2:f / 3:g / 1:eeggh% / 1:gg% / 3:%
NSUBST:  7 = 7 / *=7``
SUBST:   a = ':70 -:40 ncCll, F = ":70 -:40 ncCll, c = cccJK, C = cJK, B = cJKn....
SUBST:   e = de, % = %%%%g., * = **%, 4 = 444'', 5 = 5555544'', } = <
: colour("' = " .. dgn.random_colour() )
COLOUR:  OPQRSTUVWXYZ&?[ = warp
COLOUR:  opqrstuvwxyz@!] = gold
COLOUR:  D = darkgrey
FTILE:   '"GcJKaFn45_+ = floor_demonic_green
FTILE:   .012369AB{< = floor_rough_green / floor_pebble_green w:15
FTILE:   `~78m = floor_demonic_green / floor_pebble_green / floor_rough_green w:5
FTILE:   defghijk*% = floor_rough_green
LROCKTILE: wall_zot_green
TILE:    c = dngn_stone_wall_green / dngn_stone_wall_cyan w:5
TILE:    K = dngn_crystal_green / dngn_crystal_cyan w:5
TILE:    J = dngn_metal_wall_green / dngn_metal_wall_cyan w:5
TILE:    n = dngn_transparent_wall_green / dngn_transparen_wall_cyan w:5
TILE:    D = dngn_dimension_edge
FTILE:   OPQRSTUVWXYZ&?[ = floor_rough_green
TILE:    opqrstuvwxyz@!] = floor_black_cobalt

{{
-- This isn't the prettiest way of handling the teleporters, but it guarantees
-- they behave exactly the same way as in HangedMan's original version. All I've
-- done is remove some massive code duplication. [evilmike]

local teleporter_glyph = "OPQRSTUVWXYZ&?["
local teleport_spot_glyph = "opqrstuvwxyz@!]"
local tele_marker = {}

for i = 1, #teleporter_glyph do
    tele_marker[i] = TriggerableFunction:new {
                     func="teleporter_golubria_switch_fn",
                     data = {teleport_spot=i},
                     repeated=true }
    tele_marker[i]:add_triggerer(DgnTriggerer:new { type="player_move" })
    lua_marker(teleporter_glyph:sub(i,i), tele_marker[i])
    lua_marker(teleport_spot_glyph:sub(i,i), portal_desc { teleport_spot=i})
end

set_random_mon_list([[rakshasa w:15 / deep elf summoner w:15 / wizard w:15 / spatial vortex w:15 /
                    boggart w:5 / blink frog w:5 / shadow wraith w:5 / unseen horror /
                    ynoxinul / neqoxec / chaos spawn / giant orange brain /
                    large abomination w:20 / small abomination w:20 / large skeleton w:20 /
                    small skeleton w:20 / hellwing w:5 / smoke demon w:5 /
                    skeletal warrior w:5 / hell hound w:5 / very ugly thing w:5 /
                    golden eye w:5 / executioner w:2 / shadow demon w:2 / tormentor w:2 / ]])

set_border_fill_type('permarock_wall')
set_feature_name("clear_permarock_wall", "The dimension's edge")
set_feature_name("green_crystal_wall", "wall of crystal")
wizlab_setup(_G, "The Roulette of Golubria")
}}

epilogue{{
            wizlab_milestone(_G, "The Roulette of Golubria")
}}
MAP
               DDDDDDDDDD   DDDDDDDDDD
    DDDDDD    DDccccccccDDDDDccccccccDD    DDDDDD
  DDDccccDDDDDDcc..o...ccccccc...p..ccDDDDDDccccDDD
  Dccc.zcccccccco......ocaaacp......pccccccccq.cccD
 DDcz....ccaaaan........naaan........naaaacc....qcDD
 Dcc......caaa"n........n"a"n........n"aaac......ccD
 Dc....B..cnaaan...BBB..naaan..BBB...naaanc..B....cD
 Dcz..BBB..n"aac...BB2..caaac..2BB...caa"n..BBB..qcD
 Dcc...BB..ccaacc...B..0caaac0..B...ccaacc..BB...ccD
 DDcc....2.0caaacc1....ccaaacc....1ccaaac1.2....ccDD
  Dcccc...{.ccaaacc1.{.caaaaac.{.1ccaaacc1{...ccccD
  Dcaannc11..ccaaacc...caaaaac...ccaaacc...0cnnaacD
  Dcaaa"ccc...caaaacc.ccaaaaacc.ccaaaac...ccc"aaacD
  Dcaaaaaacc..cFaaaFc+cFaaaaaFc+cFaaaFc..ccaaaaaacD
 DDca"aaaaaccc+FFaFF'F'FaaaaaF'F'FaaFF+cccaaaaa"acDD
DDccnnnccaaaaFF'FFF'FFFFFF4FFFFFF'FFF'FFaaaaccnnnccDD
Dccy....ccaaaaFF'F'FFFFFF'G'FFFFFF'F'FFaaaacc....rccD
Dc.......ccaaaaFF4''FF'F'FFF'F'FF''4FFaaaacc.......cD
Dc.......1ccaaFF''GF''C'C'F'C'C''FG''FFaacc1.......cD
Dcy...BB..1ccFF'F'FFCCCCCC(CCCCCCFF'F'FFcc1..BB...rcD
Dc....BBB...cc'FFF'Cn'C~'CnC'~C'nC'FFF'cc...BBB....cD
Dc....B2..{..+FFFF'C'@C'``n``'C@'C'FFFF+..{..2B....cD
Dc..........cc'FF'CCCC`````````CCCC'FF'cc..........cD
Dccy....0ccccFFFFF'C~'`````````'~C'FFFFFcccc0....rccDDDDDDDD
DDccnnncccaaaaaFF'CC'````mmm````'CC'FFaaaaacccnnnccDDDnnnnnD
 Dcaa"aaaaaaaaFF'F'CC'``mm7mm``'CC'F'FFaaaaaaaa"aacDDDn?.}nD
 DcaaaaaaaaaaaF4GFF(nn``m787m``nn(FFG4FaaaaaaaaaaacDDDn...nD
 Dcaa"aaaaaaaaFF'F'CC'``mm7mm``'CC'F'FFaaaaaaaa"aacDDDn].AnD
DDccnnncccaaaaaFF'CC'````mmm````'CC'FFaaaaacccnnnccDDDnnnnnD
Dccx....0ccccFFFFF'C~'`````````'~C'FFFFFcccc0....sccDDDDDDDD
Dc..........cc'FF'CCCC`````````CCCC'FF'cc..........cD
Dc....B2..{..+FFF'CC'@C'`'n'`'C@'C'FFFF+..{..2B....cD
Dc....BBB...cc'FFF'Cn'C~'CnC'~C'nC'FFF'cc...BBB....cD
Dcx...BB..1ccFF'F'FFCCCCCC(CCCCCCFF'F'FFcc...BB...scD
Dc.......1ccaaFF''GF''C'C'F'C'C''FG''FFaacc1.......cD
Dc.......ccaaaaFF4''FF'F'FFF'F'FF''4FFaaaacc1......cD
Dccx....ccaaaaaF'F'FFFFFF'G'FFFFFF'F'Faaaaacc....sccD
DDccnnnccaaaaFF'FFF'FFFFFF4FFFFFF'FFF'FFaaaaccnnnccDD
 DDca"aaaaaccc+FFaFF'F'FaFFFaF'F'FaaFF+cccaaaaa"acDD
  Dcaaaaaacc..cFaaaFc+cFaaaaaFc+cFaaaFc..ccaaaaaacD
  Dcaaa"ccc...caaaacc.ccaaaaacc.ccaaaac...ccc"aaacD
  Dcaannc0...ccaaacc...caaaaac...ccaaacc..11cnnaacD
  Dcccc...{1ccaaacc1.{.caaaaac.{.1ccaaacc.{...ccccD
 DDcc....2.1caaacc1....ccaaacc....1ccaaac0.2....ccDD
 Dcc...BB..ccaacc...B..0caaac0..B...ccaacc..BB...ccD
 Dcw..BBB..n"aac...BB2..caaac..2BB...caa"n..BBB..tcD
 Dc....B..cnaaan...BBB..naaan..BBB...naaanc..B....cD
 Dcc......caaa"n........n"a"n........n"aaac......ccD
 DDcw....ccaaaan........naaan........naaaacc....tcDD
  Dccc.wccccccccv......vcaaacu......ucccccccct.cccD
  DDDccccDDDDDDcc..v...ccccccc...u..ccDDDDDDccccDDD
    DDDDDD    DDccccccccDDDDDccccccccDD    DDDDDD
               DDDDDDDDDD   DDDDDDDDDD
ENDMAP

###############################################################################
# Random and semi-random Wizard vaults
###############################################################################

###############################################################################
# Chambers of the Cloud Mage (by Mu.)
#
# TODO: Needs an "ocean of clouds" tiles, and fluffy "cotton wool" cloud tiles.
#       Most everything else is done, except redescriptions.
NAME:       wizlab_cloud
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
{{
wizname = crawl.make_name()

kmons ("    1 = patrolling Cloud Mage dbname:Cloud_Mage name:" .. string.gsub(wizname, " ", "_")
         .. " ; robe unrand:robe_of_clouds . quick blade ego:electrocution |"
         .. " quick blade ego:freezing | dagger ego:speed | dagger ego:electrocution"
         .. " | dagger ego:freezing")
}}
KMONS:      * = w:5 vapour / w:20 air elemental
SUBST:      . = .:120 *
MARKER:     ! = lua:fog_machine { \
                pow_max = 10, delay_min = 10, delay_max = 40, \
                size = 2, size_buildup_amnt = 5, \
                size_buildup_time = 25, cloud_type = "grey smoke", \
                colour = "white", name = "white fluffiness" \
            }
KITEM:      % = w:20 potion of levitation / w:20 potion of water / \
            potion of magic / potion of speed / potion of resistance / \
            gold / potion of agility / potion of brilliance
KITEM:      ? = randbook disc:air
KITEM:      $ = wand of lightning / staff of air / ring of levitation /\
            gold / scroll of silence / ring of teleport control / \
            quick blade / ring of evasion / ring of see invisible / \
            book of clouds / any book w:15 / any good_item / any w:20
KFEAT:      # = deep_water
NSUBST:     $ = 2:? / *:$
SUBST:      $ = $%
COLOUR:     +<bo = white
LFLOORCOL:  lightblue
LFLOORTILE: floor_rough_lightblue
TILE:       o = dngn_transparent_wall_white
TILE:       b = dngn_crystal_white
COLOUR:     wW# = silver
:           set_border_fill_type('open_sea')
:           set_random_mon_list("vapour / air elemental")
:           wizlab_setup(_G, "The Chambers of " .. wizname .. " the Cloud Mage")
:           set_feature_name("floor", "damp floor")
:           set_feature_name("green_crystal_wall", "wall of white crystal")
:           set_feature_name("clear_permarock_wall", "wall of transparent white crystal")

epilogue{{
            wizlab_milestone(_G, "The Chambers of " .. wizname .. " the Cloud Mage")
}}
#           Map is ugly because border_fill_type doesn't allow for (yet)
#           recolouring.
MAP
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################oooooooooooooooooooooooooooooo##################
###################ooo............................ooo################
#################ooo...wwwwwwwwwwwwwwwwwwwwwwwwww...ooo##############
################oo...wwwwwwwbbbbbbbbbbbbbbbbbbbbwww...oo#############
################o..wwwwwwwbbbbbbbbbbbbbbbbbbbbbbwwwww..o#############
###############oo.wwwwwwbbbbbbbb..b..b..b..b..bbwwwwww.oo############
###############o..wwwwwbb.....b.!............!.bwwwwww..o############
##############oo.wwwwwwbb.$$$.b................bwwwwwww.oo###########
##############o..wwwwwbbb.$$$.b................bWWWWWWW..o###########
##############o..wwwwwbbb.$$$.+...1............+.........o###########
##############o..wwwwwbbb.$$$.b................bWWWWWWW..o###########
##############oo.wwwwwwbb.$$$.b................bwwwwwww.oo###########
###############o..wwwwwbb.....b.!............!.bwwwwww..o############
###############oo.wwwwwwbbbbbbbb..b..b..b..b..bbwwwwww.oo############
################o..wwwwwwwbbbbbbbbbbbbbbbbbbbbbbwwwww..o#############
################oo...wwwwwwwbbbbbbbbbbbbbbbbbbbbwww...oo#############
#################oo....wwwwwwwwwwwwwwwwwwwwwwwwww...ooo##############
##################oooo............................ooo################
#####################bbb.......bbbbbbbbbbbbbbbbbbbb##################
#####################oo.......oo#####ooo#############################
####################oo.......oo#####oo.oo############################
###################oo.......oo#####oo.!.oo###########################
###################o!.....!ooo####oo.....ooo#########################
###################ooo.......ooo#oo........oo########################
####################oooo.......ooo..........oo#######################
#######################ooo!.....ooo..........o#######################
########################o.....!ooobb+bb......oo######################
#######################ooo......obb...bb!.....o######################
########################o......obb.....bb.....oo#####################
#######################ooo......b.......b......o#####################
#######################o.!.....ob.<.A.<.b......o#####################
#######################o.b......b.......bo...!oo#####################
#######################o.bo.....bb.....bb......o#####################
#######################b+bbbb....bb...bb!.....oo#####################
#######################o....bo...!bbbbb......oo######################
#######################o.%%.bo.............oob#######################
#######################o.%%.boo...........bbbbbbbbb##################
#######################o....b#o..........!...+....o##################
#######################ooooob#oo........ooooob.%%.o##################
###############################oo......oo####b.%%.o##################
################################oo.!..oo#####b....o##################
#################################oooooo######booooo##################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
#####################################################################
ENDMAP

###############################################################################
# Halls of the Hellbinder (by Mu.)
NAME:       wizlab_demon
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate no_hmirror no_vmirror allow_dup
LFLOORCOL:  red
LROCKCOL:   red
LFLOORTILE: floor_pebble_lightred
COLOUR:     c = darkgrey
COLOUR:     -|/\o[]CDEFGHIJKLMNOPQRSTUVWXYZu = yellow
KFEAT:      -|/\o[]CDEFGHIJKLMNOPQRSTUVWXYZu = floor
KFEAT:      _ = altar_makhleb
KPROP:      ' = bloody / nothing
KPROP:      _ = bloody
TILE:       c = wall_stone_dark
# symbols roughly corresponding to sigil shape
FTILE:      - = sigil_straight_E_W
FTILE:      | = sigil_straight_N_S
FTILE:      / = sigil_straight_NE_SW
FTILE:      \ = sigil_straight_NW_SE
FTILE:      o = sigil_circle
FTILE:      T = sigil_cross
FTILE:      Y = sigil_Y
FTILE:      ] = sigil_Y_left
FTILE:      [ = sigil_Y_right
FTILE:      O = sigil_rhombus
FTILE:      Q = sigil_algiz_left
FTILE:      R = sigil_algiz_right
FTILE:      S = sigil_sharp_E_NE
FTILE:      Z = sigil_sharp_W_SW
FTILE:      K = sigil_straight_E_NE_SW
FTILE:      X = sigil_fourway
FTILE:      Uu = sigil_Y_inverted
FTILE:      V = sigil_Y_leftleaning
FTILE:      W = sigil_Y_rightleaning
# remaining sigil patterns
FTILE:      C = sigil_curve_S_E
FTILE:      D = sigil_curve_S_W
FTILE:      E = sigil_curve_N_E
FTILE:      F = sigil_curve_N_W
FTILE:      G = sigil_straight_E_SW
FTILE:      H = sigil_straight_W_SE
FTILE:      I = sigil_straight_S_NE
FTILE:      J = sigil_straight_S_NW
FTILE:      L = sigil_straight_N_SE
FTILE:      M = sigil_straight_N_SW
FTILE:      N = sigil_straight_E_NW
FTILE:      P = sigil_straight_W_NE
RTILE:      x = wall_undead
SUBST:      u = 3
MARKER:     f = lua:fog_machine { \
                pow_max = 10, delay_min = 10, delay_max = 40, \
                size = 2, size_buildup_amnt = 5, \
                size_buildup_time = 25, cloud_type = "flame", \
                excl_rad = -1 }
KMONS:      2 = w:1 Lorocyproca / hell beast / reaper /\
            w:20 ice devil / w:20 sun demon / hellion
KMONS:      3 = blue devil / iron devil / soul eater / neqoxec /\
            w:5 tormentor / ynoxinul
KMONS:      4 = kobold demonologist / deep elf demonologist
KMONS:      5 = blizzard demon / green death / cacodemon
{{
wizname = crawl.make_name()

kmons     ("1 = patrolling Hellbinder dbname:Hellbinder name:" .. string.gsub(wizname, " ", "_"))
}}
KITEM:      $ = gold / w:1 scroll of torment / w:1 scroll of unholy creation
KITEM:      i = rod of demonology / ring of fire / ring of protection from fire /\
            amulet of conservation / scroll of torment / scroll of unholy creation /\
            demon blade w:1 / demon whip w:1 / demon trident w:1 / gold / wand of fire /\
            wand of draining / staff of summoning / any book w:30 / any good_item w:15
KITEM:      B = randbook disc:summoning
NSUBST:     i = 2:B / *:i
:           set_random_mon_list([[crimson imp / shadow imp / lemure / iron imp / quasit / white imp / ]]
:                        .. [[ufetubus / red devil / rotting devil / orange demon / ]])
:           wizlab_setup(_G, "The Hall of " .. wizname .. " the Hellbinder")
:           set_feature_name("floor", "hot floor")
:           set_feature_name("stone_wall", "black wall")
:           set_feature_name("rock_wall", "carved rock wall")
epilogue{{
            wizlab_milestone(_G, "The Hall of " .. wizname .. " the Hellbinder")
}}
MAP
cccccccccccccccccccccccccccccccccccccccccccccc
ccccccc.cccccc...................cccccc.cccccc
ccccc.....cccc.cc+ccccc+ccccc+cc.cccc.....cccc
cccc..G-H..ccc.c...cccc.cccc...c.ccc...o...ccc
ccc../...\..cc.+.A.ccc...ccc.<.+.cc..|...../cc
ccc.I...3.J.cc.c...cc.....cc...c.cc.-O-.3./.cc
cc..|..u..|....ccccc..c.c..ccccc.....|.3./...c
cc..|.3Y..|....cccc..cc.cc..cccc......3./....c
ccc.L.....M.cc.ccc.....4.....ccc.cc....K----cc
ccc..\.../..cc.cc..cccc.cccc..cc.cc.../.....cc
cccc..N-P..ccc.+...............+.ccc./.....ccc
ccccc.....cccc.ccccccccccccccccc.cccc.....cccc
ccccccc.cccccc...................cccccc.cccccc
ccccccc.cccccc.cccccccc.cccccccc.cccccc.cccccc
ccccccc.ccccccc.cccccc.c.cccccc.ccccccc.cccccc
ccccccc.cccccccc.cccc.ccc.cccc.cccccccc.cccccc
ccccccc.ccccccccc.cc.ccccc.cc.ccccccccc.cccccc
ccccccc.cccccccccc..ccccccc..cccccccccc.cccccc
ccccccc.cccc.5...................5.cccc.cccccc
ccccccc.cccc..ccccccccc.ccccccccc..cccc.cccccc
ccccccc.ccccc..cccc$$$c.c$$$cccc..ccccc.cccccc
ccccccc.cccccc..ccc$$$+.+$$$ccc..cccccc.cccccc
ccccccc.cc.cccc..cc$$$c.c$$$cc..cccc.cc.cccccc
ccccccc......ccc..ccccc.ccccc..ccc..Z...cccccc
ccccccc...o...ccc..cccc.cccc..ccc../..O.cccccc
cccccc..\.../..ccc..ccc.ccc..ccc../..OTO.ccccc
cccccc...\2/...cccc..cc.cc..cccc./2222U..ccccc
ccccc..\2CXD2/..cccc.......cccc./.........cccc
cccccc..\|2|/...ccccc.\4/.cccccS--------Zccccc
cccccc...Q.R....ccccc..Y..ccccc......../.ccccc
ccccccc..ETF....ccccc..|..ccccc......./.cccccc
cccccccc........ccccc.....ccccc......S.ccccccc
cccccccccc......cccc..ccc..cccc......ccccccccc
ccccccccccc.....ccc..ccccc..ccc.....cccccccccc
cccccccccccc.....c...ccccc...c.....ccccccccccc
cccccccccccc..\./..cc.ccc.cc..\./..ccccccccccc
ccccccccccccc..V..cccc.c.cccc..W..cccccccccccc
ccccccccccccc./...cccccfccccc...\.cccccccccccc
cccccccccccccc.....ccc.c.ccc.....ccccccccccccc
ccccccccccccccc.....c.ccc.c.....cccccccccccccc
ccccccccccccccccc.....ccc.....cccccccccccccccc
ccccccccccccccccccc.........cccccccccccccccccc
ccccccccccccccccccccc.....cccccccccccccccccccc
ccccccccccccccccccccccc+cccccccccccccccccccccc
ccccccccccccccccccccc.....cccccccccccccccccccc
ccccccccccccccccccc...G"H...cccccccccccccccccc
ccccccccccccccccc...GP...NH...cccccccccccccccc
cccccccccccccccc..G[.......]H..ccccccccccccccc
ccccccccccccccc../..N.....P..\..cccccccccccccc
ccccccccccccccc.I.............J.cccccccccccccc
cccccccccccccc..U.....G.H.....U..ccccccccccccc
cccccccccccccc.I.J.../...\...I.J.ccccccccccccc
ccccccccccccc..|..../..1..\....|..cccccccccccc
ccccccccccccc..|.../\.'''./\...|..cccccccccccc
ccccccccccccc..|../xx\'_'/xx\..|..cccccccccccc
cccccccccccc...L./..xxN'Pxx..\.M...ccccccccccc
cccccccccccci...W..G.xxxxx.H..V...iccccccccccc
ccccccccccccii...NP.........NP...iiccccccccccc
cccccccccccciii.................iiiccccccccccc
cccccccccccccccccccccccccccccccccccccccccccccc
ENDMAP

###############################################################################
# Incomplete and TODO work area.
#
# See git history for previous versions of Ozocubu, Alistair.
#
# PLANNING AREA:
#
# From spells:
#
# Alistair's Brewery: mutated wizards, mephitic cloud generators,
#    cupboards full of potions, confused monsters.
# Lee's Rapid Deconstructor: golems and "monk" or otherwise unarmed creatures,
#    exploding features and exploding corpses. It's a timed vault, so you have
#    to get to the loot quickly and avoid the hordes of monsters.
# Lehudib's Crystal Spire:  crystal walls and crystal golems, crystal monsters,
#    spear throwers (statues with crystal spear), possibly the unrand as the
#    loot.
# Maxwell's Forge: Maxwell employs a bunch of angels to churn out weapons;
#    stashes of hammers, flame clouds, other "smithy" styled themes, with black
#    smoke.
# Olgreb's Toxic Laboratory: poisonous clouds, a toxic radiance effect,
#    poisonous monsters, possibly even a "poison" effect that bypasses rPois,
#    potions of poison and potions dropped converting into potions of poison.
# Ozocubu's Refrigerator: simulacra, refrigeration effect, a solid stone room
#    inside of an "ice cave", freezing clouds.
#
# From unrands:
#
# Cekugob's Oubliette: a randomised maze (though not a labyrinth) with skeletal
#    guards, and with occasionally hidden. Cekugob's amulet as the loot,
#    possibly.
# Botono's Bayou: A bay-like area with small huts, wizards that cast negative
#    related spells, shadow dragons, rebranded swamp worms, wraiths, spectrals.
# Ukta's Hut: phantoms, other "ghosts", ogre mages and ogres, druidic style,
#    wooden walls set in a forest (more "earthy" than Eringya's Garden)
# The Alchemist's Tower: gold turned into things, things turned into gold.
#

###############################################################################
# Alistair's Brewery
#
# TODO: Do.
NAME:       wizlab_alistair
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Alistair's Brewery")
epilogue{{
            wizlab_milestone(_G, "Alistair's Brewery")
}}
MAP
ENDMAP

###############################################################################
# Lee's Rapid Deconstructor
#
# TODO: Do.
NAME:       wizlab_lee
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Lee's Rapid Deconstructor")
epilogue{{
            wizlab_milestone(_G, "Lee's Rapid Deconstructor")
}}
MAP
ENDMAP

###############################################################################
# Lehudib's Crystal Spire
#
# TODO: Do.
NAME:       wizlab_lehudib
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Lehudib's Crystal Spire")
epilogue{{
            wizlab_milestone(_G, "Lehudib's Crystal Spire")
}}
MAP
ENDMAP

###############################################################################
# Maxwell's Forge
#
# TODO: Do.
NAME:       wizlab_maxwell
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Maxwell's Forge")
epilogue{{
            wizlab_milestone(_G, "Maxwell's Forge")
}}
MAP
ENDMAP

###############################################################################
# Olgreb's Toxic Laboratory
#
# TODO: Do.
NAME:       wizlab_olgreb
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Olgreb's Toxic Laboratory")
epilogue{{
            wizlab_milestone(_G, "Olgreb's Toxic Laboratory")
}}
MAP
ENDMAP

###############################################################################
# Ozocubu's Refrigerator
#
# TODO: Do.
NAME:       wizlab_ozocubu
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Ozocubu's Refrigerator")
epilogue{{
            wizlab_milestone(_G, "Ozocubu's Refrigerator")
}}
MAP
ENDMAP

###############################################################################
# Cekugob's Oubliette
#
# TODO: Do.
NAME:       wizlab_cekugob
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Cekugob's Oubliette")
epilogue{{
            wizlab_milestone(_G, "Cekugob's Oubliette")
}}
MAP
ENDMAP

###############################################################################
# Botono's Bayou
#
# TODO: Do.
NAME:       wizlab_botono
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Botono's Bayou")
epilogue{{
            wizlab_milestone(_G, "Botono's Bayou")
}}
MAP
ENDMAP

###############################################################################
# Ukta's Hut
#
# TODO: Do.
NAME:       wizlab_ukta
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "Ukta's Hut")
epilogue{{
            wizlab_milestone(_G, "Ukta's Hut")
}}
MAP
ENDMAP

###############################################################################
# The Alchemist's Tower
#
# TODO: Do.
NAME:       wizlab_alchemist
ORIENT:     encompass
TAGS:       no_item_gen no_monster_gen no_rotate allow_dup
WEIGHT:     0
:           wizlab_setup(_G, "The Alchemist's Tower")
epilogue{{
            wizlab_milestone(_G, "The Alchemist's Tower")
}}
MAP
ENDMAP
