package com.rs.game.player.content.dungeoneering;

import java.util.Arrays;

import com.rs.Settings;
import com.rs.game.WorldTile;
import com.rs.game.npc.dungeonnering.DungeonNPC;
import com.rs.game.player.Skills;
import com.rs.game.player.actions.Smelting.SmeltingBar;
import com.rs.game.player.content.dungeoneering.rooms.BossRoom;
import com.rs.game.player.content.dungeoneering.rooms.HandledPuzzleRoom;
import com.rs.game.player.content.dungeoneering.rooms.HandledRoom;
import com.rs.game.player.content.dungeoneering.rooms.NormalRoom;
import com.rs.game.player.content.dungeoneering.rooms.RoomEvent;
import com.rs.game.player.content.dungeoneering.rooms.StartRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.ColouredRecessRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.CrystalPuzzleRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.FishingFerretRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.FlipTilesRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.FlowerRootsRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.FremennikCampRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.LeverRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.PoltergeistRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.ReturnTheFlowRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.SlidingStatuesRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.SlidingTilesRoom;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.ToxinMaze;
import com.rs.game.player.content.dungeoneering.rooms.puzzles.UnhappyGhostRoom;

public class DungeonConstants {

	public static final int[] MIN_CRIT_PATH =
	{ 5, 10, 19 }, MAX_CRIT_PATH =
	{ 7, 13, 23 };

	public static final WorldTile OUTSIDE = new WorldTile(3460, 3720, 1);

	public static final int ROTATIONS_COUNT = 4;

	public static final int TINDERBOX = 17678;

	public static final int SMUGGLER = 11226;

	public static final int[] LADDERS = new int[]
	{ 49696, 49698, 49700, 53748, 55484 };

	public static final int FLOORS_COUNT = 60;

	public static final int GROUP_GATESTONE = 18829, GATESTONE = 17489;

	/*
	 * objects handling
	 */
	public static final int[] DUNGEON_DOORS = new int[]
	{ 50342, 50343, 50344, 53948, 55762 };
	public static final int[] DUNGEON_BOSS_DOORS = new int[]
	{ 50350, 50351, 50352, 53950, 55764 };

	public static final int[] DUNGEON_GUARDIAN_DOORS =
	{ 50346, 50347, 50348, 53949, 55763 };

	/*
	 * novite ores
	 */
	public static final int[] MINING_RESOURCES =
	{ 49806, 49786, 49766, 53771, 55514 };

	/*
	 * Tangle gum tree
	 */
	public static final int[] WOODCUTTING_RESOURCES =
	{ 49745, 49725, 49705, 53751, 55494 };

	/*
	 * Salve nettles
	 */
	public static final int[] FARMING_RESOURCES =
	{ 49866, 49846, 49826, 53791, 55534 };

	public static final int[] THIEF_CHEST_LOCKED =
	{ 49345, 49346, 49347, 54407, 32462 };
	public static final int[] THIEF_CHEST_OPEN =
	{ 49348, 49349, 49350, 54408, 32679 };
	public static final double[] THIEF_CHEST_XP =
	{ 25.5, 57, 115, 209, 331.5, 485, 661.5, 876, 1118, 1410.5 };

	public static final int RUSTY_COINS = 18201, BANANA = 18199;

	public static final int[] CHARMS =
	{ 18017, 18018, 18019, 18020 };

	public static final int[] ARROWS =
	{ 16427, 16432, 16437, 16442, 16447, 16452, 16457, 16462, 16467, 16472, 16477 };

	public static final int[] RUNES =
	{ 556, 555, 554, 557, 558, 559, 560, 561, 562, 563, 564, 565, 566, 9075 };

	public static final int RUNE_ESSENCE = 17776, FEATHER = 17796;

	public static final int[] DUNGEON_KEY_DOORS =
	{ 50353, 50417, 50481, 53884, 55675 };

	public static enum SkillDoors {
		RUNED_DOOR(Skills.RUNECRAFTING, new int[]
		{ 50278, 50279, 50280, 53953, 55741 }, 791, 186, -1, -1, -1, -1, "You imbue the door with the wrong type of rune energy, and it reacts explosively."),
		BARRED_DOOR(Skills.STRENGTH, new int[]
		{ 50272, 50273, 50274, 53951, 55739 }, new int[]
		{ 50275, 50276, 50277, 53952, 55740 }, -1, -1, -1, -1, -1, -1, "You pull a muscle while attempting to move the plank."),
		PILE_OF_ROCKS(Skills.MINING, new int[]
		{ 50305, 50306, 50307, 53962, 55750 }, -2, -1, 13559, -1, -1, 2420, "You fail to mine the obstruction, and are harmed by falling debris."),
		FLAMMABLE_DEBRIS(Skills.FIREMAKING, new int[]
		{ 50314, 50315, 50316, 53965, 55753 }, 16700, -1, 13562, 13563, -1, -1, "The pile of debris fails to ignite. The same cannot be said for your clothes."),
		MAGICAL_BARRIER(Skills.MAGIC, new int[]
		{ 50329, 50330, 50331, 53970, 55758 }, 4411, -1, 13551, 13550, -1, -1, "You fail to dispel the barrier and take a surge of magical energy to the face."),
		DARK_SPIRIT(Skills.PRAYER, new int[]
		{ 50332, 50333, 50334, 53971, 55759 }, 645, -1, 13557, 13556, -1, -1, "The gods snub your prayer, and the dark spirit attacks you."),
		WOODEN_BARRICADE(Skills.WOODCUTTING, new int[]
		{ 50317, 50318, 50319, 53966, 55754 }, new int[]
		{ 50320, 50321, 50322, 53967, 55755 }, -3, -1, 13582, -1, -1, -1, "You swing the axe against the grain and are showered with sharp splinters of wood."),
		BROKEN_KEY_DOOR(Skills.SMITHING, new int[]
		{ 50308, 50309, 50310, 53963, 55751 }, new int[]
		{ 50311, 50312, 50313, 53964, 55752 }, 13759, -1, -1, -1, -1, -1, "You hit your hand with the hammer. Needless to say, the key is still broken."),
		BROKEN_PULLEY_DOOR(Skills.CRAFTING, new int[]
		{ 50299, 50300, 50301, 53960, 55748 }, new int[]
		{ 50302, 50303, 50304, 53961, 55749 }, 13547, -1, -1, -1, -1, -1, "The rope snaps again as you attempt to fix it, and you crush your hands in the mechanism."),
		LOCKED_DOOR(Skills.AGILITY, new int[]
		{ -1, 50288, 50289, 53956, 55744 }, new int[]
		{ 50290, 50291, 50292, 53957, 55745 }, 14550, -1, -1, -1, -1, -1, "You miss the chain, and set off the trap."),
		PADLOCKED_DOOR(Skills.THIEVING, new int[]
		{ -1, 50294, 50295, 53958, 55746 }, new int[]
		{ 50296, 50297, 50298, 53959, 55747 }, 14568, -1, -1, -1, 14569, -1, "You set off a booby trap inside the lock, and fail to pick it."),
		RAMOKEE_EXILE(Skills.SUMMONING, new int[]
		{ -1, 50327, 50328, 53969, 55757 }, 725, 1207, -1, -1, -1, -1, "You fail to dismiss the rogue familiar, and it punches you in anger."),
		LIQUID_LOCK_DOOR(Skills.HERBLORE, new int[]
		{ -1, 50336, 50337, 53972, 55760 }, new int[]
		{ 50338, 50339, 50340, 53973, 55761 }, 14568, -1, -1, -1, -1, -1, "You incorrectly mix the ingredients, making it explode."),
		VINE_COVERED_DOOR(Skills.FARMING, new int[]
		{ -1, 50324, 50325, 53968, 55756 }, 2275, -1, 13572, -1, -1, -1, "You hurt your hands on the vicious thorns covering the vines."),
		COLLAPSING_DOORFRAME(Skills.CONSTRUCTION, new int[]
		{ -1, 50282, 50283, 53954, 55742 }, new int[]
		{ 50284, 50285, 50286, 53955, 55743 }, 14566, -1, -1, -1, 14567, -1, "You dislodge some debris while attempting to fix the door, and it falls on you.");

		private SkillDoors(int skillId, int[] closedThemeObjects, int openAnim, int openGfx, int openObjectAnim, int failObjectAnim, int failAnim, int failGfx, String failMessage) {
			this(skillId, closedThemeObjects, null, openAnim, openGfx, openObjectAnim, failObjectAnim, failAnim, failGfx, failMessage);
		}

		private int skillId, openAnim, openGfx, openObjectAnim, failObjectAnim, failAnim, failGfx;
		private int[] closedThemeObjects, openThemeObjects;
		private String failMessage;

		/*
		 * set openThemeObjects if u want it to disappear after open
		 */
		private SkillDoors(int skillId, int[] closedThemeObjects, int[] openThemeObjects, int openAnim, int openGfx, int openObjectAnim, int failObjectAnim, int failAnim, int failGfx, String failMessage) {
			this.skillId = skillId;
			this.closedThemeObjects = closedThemeObjects;
			this.openThemeObjects = openThemeObjects;
			this.failMessage = failMessage;
			this.openAnim = openAnim;
			this.openGfx = openGfx;
			this.openObjectAnim = openObjectAnim;
			this.failObjectAnim = failObjectAnim;
			this.failGfx = failGfx;
			this.failAnim = failAnim;
		}

		public int getSkillId() {
			return skillId;
		}

		public int getFailGfx() {
			return failGfx;
		}

		public int getFailAnim() {
			return failAnim;
		}

		public int getFailObjectAnim() {
			return failObjectAnim;
		}

		public int getOpenObjectAnim() {
			return openObjectAnim;
		}

		public int getOpenAnim() {
			return openAnim;
		}

		public int getOpenGfx() {
			return openGfx;
		}

		public int getClosedObject(int type) {
			return closedThemeObjects[type];
		}

		public int getOpenObject(int type) {
			return openThemeObjects == null ? -1 : openThemeObjects[type];
		}

		public String getFailMessage() {
			return failMessage;
		}
	}

	/*
	 * keydoors only require the unlock objectid and itemid
	 */
	public static enum KeyDoors {
		ORANGE_TRIANGLE(0),
		ORANGE_DIAMOND(1),
		ORANGE_RECTANGLE(2),
		ORANGE_PENTAGON(3),
		ORANGE_CORNER(4),
		ORANGE_CRESCENT(5),
		ORANGE_WEDGE(6),
		ORANGE_SHIELD(7),
		SILVER_TRIANGLE(8),
		SILVER_DIAMOND(9),
		SILVER_RECTANGLE(10),
		SILVER_PENTAGON(11),
		SILVER_CORNER(12),
		SILVER_CRESCENT(13),
		SILVER_WEDGE(14),
		SILVER_SHIELD(15),
		YELLOW_TRIANGLE(16),
		YELLOW_DIAMOND(17),
		YELLOW_RECTANGLE(18),
		YELLOW_PENTAGON(19),
		YELLOW_CORNER(20),
		YELLOW_CRESCENT(21),
		YELLOW_WEDGE(22),
		YELLOW_SHIELD(23),
		GREEN_TRIANGLE(24),
		GREEN_DIAMOND(25),
		GREEN_RECTANGLE(26),
		GREEN_PENTAGON(27),
		GREEN_CORNER(28),
		GREEN_CRESCENT(29),
		GREEN_WEDGE(30),
		GREEN_SHIELD(31),
		BLUE_TRIANGLE(32),
		BLUE_DIAMOND(33),
		BLUE_RECTANGLE(34),
		BLUE_PENTAGON(35),
		BLUE_CORNER(36),
		BLUE_CRESCENT(37),
		BLUE_WEDGE(38),
		BLUE_SHIELD(39),
		PURPLE_TRIANGLE(40),
		PURPLE_DIAMOND(41),
		PURPLE_RECTANGLE(42),
		PURPLE_PENTAGON(43),
		PURPLE_CORNER(44),
		PURPLE_CRESCENT(45),
		PURPLE_WEDGE(46),
		PURPLE_SHIELD(47),
		CRIMSON_TRIANGLE(48),
		CRIMSON_DIAMOND(49),
		CRIMSON_RECTANGLE(50),
		CRIMSON_PENTAGON(51),
		CRIMSON_CORNER(52),
		CRIMSON_CRESCENT(53),
		CRIMSON_WEDGE(54),
		CRIMSON_SHIELD(55),
		GOLD_TRIANGLE(56),
		GOLD_DIAMOND(57),
		GOLD_RECTANGLE(58),
		GOLD_PENTAGON(59),
		GOLD_CORNER(60),
		GOLD_CRESCENT(61),
		GOLD_WEDGE(62),
		GOLD_SHIELD(63);
		private int index;

		private KeyDoors(int index) {
			this.index = index;
		}

		public int getObjectId() {
			return getLowestObjectId() + index;
		}

		public int getDoorId(int floorType) {
			return getLowestDoorId(floorType) + index;
		}

		public static int getLowestObjectId() {
			return 50208;
		}

		public static int getLowestDoorId(int floorType) {
			return DUNGEON_KEY_DOORS[floorType];
		}

		public static int getMaxObjectId() {
			return 50208 + KeyDoors.values().length;
		}

		public static int getMaxDoorId(int floorType) {
			return DUNGEON_KEY_DOORS[floorType] + KeyDoors.values().length;
		}

		public int getKeyId() {
			return getLowestKeyId() + (index * 2);
		}

		public static int getLowestKeyId() {
			return 18202;
		}

		public int getIndex() {
			return index;
		}
	}

	public static final int NORMAL_DOOR = 0, GUARDIAN_DOOR = 1, SKILL_DOOR = 2, CHALLENGE_DOOR = 3, KEY_DOOR = 4;

	public static final double UNBALANCED_PARTY_PENALTY = 0.4;
	public static final double[] DUNGEON_SIZE_BONUS =
	{ 0, 0.07, 0.15 };
	public static final double[] COMPLEXIYY_PENALTY_BASE =
	{ 0.32, 0.35, 0.37 };
	public static final double MAX_BONUS_ROOM = 0.13;
	public static final double[][] DUNGEON_DIFFICULTY_RATIO_BONUS =
	{
	{ 0 },
	{ -0.07, 0.05 },
	{ -0.14, 0.02, 0.1 },
	{ -0.21, -0.07, 0.06, 0.15 },
	{ -0.29, -0.12, 0.04, 0.11, 0.19 } };
	/*
	 * floor types
	 */
	public static final int FROZEN_FLOORS = 0, ABANDONED_FLOORS = 1, FURNISHED_FLOORS = 2, OCCULT_FLOORS = 3, WARPED_FLOORS = 4;

	/*
	 * dungeon sizes
	 */
	public static final int SMALL_DUNGEON = 0, MEDIUM_DUNGEON = 1, LARGE_DUNGEON = 2, TEST_DUNGEON = 3;

	// 4x4, 4x8 and 4x8, 2x1(just boss room for test)
	public static final int[][] DUNGEON_RATIO = new int[][]
	{ new int[]
	{ 4, 4 }, new int[]
	{ 4, 8 }, new int[]
	{ 8, 8 }, new int[]
	{ 2, 1 } };

	public static final int XP_RATE = 4; //4x for now

	/*
	 * door directions
	 */
	public static final int EAST_DOOR = 2, WEST_DOOR = 0, NORTH_DOOR = 1, SOUTH_DOOR = 3;

	public static final int[] START_ROOM_MUSICS = new int[]
	{ 822, 797, 765, 884, 935 };

	public static final int[][] DANGEROUS_MUSICS =
	{
	{ 832, 834, 827, 811, 824, 808, 831, 810, 833, 837 }, //frozen
		{ 779, 781, 799, 802, 794, 780, 771, 790, 775, 801 }, //abandoned
		{ 748, 769, 741, 739, 742, 753, 761, 757, 747, 756 }, //furnished
		{ 873, 882, 880, 860, 886, 872, 885, 889, 870, 864 }, //occult floor
		{ 930, 914, 917, 911, 927, 939, 938, 920, 925, 936 }, //warped floor
	};

	public static final int[][] SAFE_MUSICS =
	{
		// FROZEN_FLOORS
		{ 804, 805, 806, 807, 809, 812, 813, 814, 812, 813, 814, 821, 822 }, //frozen
		{ 772, 773, 775, 776, 777, 778, 788, 789, 791, 792, 793, 795, 796 }, //abandoned
		{ 740, 744, 745, 749, 750, 751, 752, 754, 755, 758, 760, 762, 764 }, //furnished
		{ 861, 862, 866, 867, 868, 869, 871, 874, 875, 878, 879, 881, 883 }, //occult
		{ 912, 915, 918, 919, 921, 923, 926, 928, 929, 931, 932, 933, 934 } //warped floor
	};

	/*
	 * Creatures
	 */
	public static final int[][] GUARDIAN_CREATURES =
	{
		//ALL FLOORs
		{ 10831, 10906, 10910, 10821, 10630, 10680, 10693, 10364, 10480, 10726 }
		// FROZEN
		,
		{ 10618, 10460, 10762, 10157, 10782, 10225, 10212, 10791, 10770 }
		// ABANDONED
		,
		{ 10168, 10496, 10178, 10469, 10604, 10706, 10706 }
		// Furnished
		,
		{ 10797, 10496, 10776, 10706 }
		// Occult
		,
		{ 10744, 10722, 10496, 10754, 10718, 10188, 10492, 10815 }
		// Warped
		,
		{ 10744, 10736, 10722, 10219, 10496, 10754, 10718, 10492, 12941 } };

	public static final int[][] FORGOTTEN_WARRIORS =
	{
		//warrior
		{ 10507, 10439, 10246, 10288, 10528 },
		//mage
		{ 10560, 10570, 10575, 10580, 10585, 10590, 10595, 10600 },
		//range
		{ 10320, 10325, 10330, 10335, 10340, 10345, 10350, 10355, 10360 } };

	public static final int[] SLAYER_CREATURES =
	{ 10694, 10695, 10696, 10697, 10698, 10699, 10700, 10701, 10702, 10704, 10705 };

	/*
	 * id - lvl
	 */
	public static final int[] HUNTER_CREATURES =
	{ 11086, 11087, 11088, 11089, 11090, 11091, 11092, 11093, 11094, 11095 };

	public static final StartRoom[] START_ROOMS = new StartRoom[]
	{
		// FROZEN_FLOORS
		new StartRoom(14, 632, EAST_DOOR, WEST_DOOR, NORTH_DOOR, SOUTH_DOOR),
		new StartRoom(14, 624, SOUTH_DOOR),
		new StartRoom(14, 626, WEST_DOOR, SOUTH_DOOR),
		new StartRoom(14, 630, WEST_DOOR, NORTH_DOOR, SOUTH_DOOR) };

	public static final NormalRoom[] NORMAL_ROOMS = new NormalRoom[]
	{
		new NormalRoom(8, 240, spot(3, 7), SOUTH_DOOR),
		new NormalRoom(8, 242, spot(3, 12), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(8, 244, spot(3, 12), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(8, 246, spot(4, 13), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(8, 248, spot(3, 12), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(8, 256, spot(12, 12), SOUTH_DOOR),
		new NormalRoom(8, 258, spot(12, 12), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(8, 260, spot(11, 6), SOUTH_DOOR, NORTH_DOOR),
		new NormalRoom(8, 262, spot(12, 6), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR),
		new NormalRoom(8, 264, spot(12, 12), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(10, 240, spot(3, 3), SOUTH_DOOR),
		new NormalRoom(10, 242, spot(7, 12), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(10, 244, spot(2, 4), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(10, 246, spot(2, 12), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(10, 248, spot(2, 12), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(10, 256, spot(8, 12), SOUTH_DOOR),
		new NormalRoom(10, 258, spot(12, 2), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(10, 260, spot(3, 4), SOUTH_DOOR, NORTH_DOOR),
		new NormalRoom(10, 262, spot(7, 8), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR),
		new NormalRoom(10, 264, spot(5, 10), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(12, 240, spot(3, 7), SOUTH_DOOR),
		new NormalRoom(12, 242, spot(11, 7), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(12, 244, spot(3, 12), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(12, 246, spot(10, 7), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(12, 248, spot(10, 7), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(12, 256, spot(9, 7), SOUTH_DOOR),
		new NormalRoom(12, 258, spot(3, 6), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(12, 260, spot(4, 10), SOUTH_DOOR, NORTH_DOOR),
		new NormalRoom(12, 262, spot(9, 7), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR),
		new NormalRoom(12, 264, spot(3, 6), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(14, 240, spot(7, 10), SOUTH_DOOR),

		new NormalRoom(14, 256, spot(4, 13), SOUTH_DOOR),
		new NormalRoom(14, 258, spot(12, 9), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(14, 260, spot(12, 13), SOUTH_DOOR, NORTH_DOOR),
		new NormalRoom(14, 262, spot(7, 7), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR),
		new NormalRoom(14, 264, spot(11, 13), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(16, 240, spot(7, 10), SOUTH_DOOR),

		new NormalRoom(16, 256, spot(4, 12), SOUTH_DOOR),
		new NormalRoom(16, 258, spot(7, 11), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(16, 260, spot(4, 3), SOUTH_DOOR, NORTH_DOOR),
		new NormalRoom(16, 262, spot(7, 8), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR),
		new NormalRoom(16, 264, spot(7, 7), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(18, 240, spot(7, 10), SOUTH_DOOR),
		new NormalRoom(18, 260, spot(5, 12), SOUTH_DOOR, NORTH_DOOR),
		new NormalRoom(18, 264, spot(3, 12), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(20, 240, spot(9, 13), SOUTH_DOOR),

		new NormalRoom(20, 258, spot(11, 9), SOUTH_DOOR, WEST_DOOR),

		new NormalRoom(22, 240, spot(8, 9), SOUTH_DOOR),

		new NormalRoom(22, 256, spot(7, 10), SOUTH_DOOR),
		new NormalRoom(22, 258, spot(11, 10), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(22, 260, spot(7, 8), SOUTH_DOOR, NORTH_DOOR),
		new NormalRoom(22, 262, spot(7, 7), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR),
		new NormalRoom(22, 264, spot(7, 7), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(24, 242, spot(7, 7), SOUTH_DOOR, WEST_DOOR),

		new NormalRoom(24, 258, spot(12, 10), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(24, 264, spot(7, 7), SOUTH_DOOR, NORTH_DOOR, WEST_DOOR, EAST_DOOR),

		new NormalRoom(26, 242, spot(9, 9), SOUTH_DOOR, WEST_DOOR),

		new NormalRoom(28, 246, spot(11, 8), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(30, 244, spot(3, 6), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(32, 244, spot(3, 12), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(34, 242, spot(12, 12), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(36, 248, spot(2, 13), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),
		new NormalRoom(38, 246, spot(12, 10), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(40, 244, spot(3, 12), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(42, 244, spot(7, 7), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(44, 244, spot(7, 7), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(46, 244, spot(7, 7), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(48, 244, spot(7, 7), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(50, 244, spot(7, 7), NORTH_DOOR, SOUTH_DOOR),

		new NormalRoom(52, 240, spot(7, 11), SOUTH_DOOR),
		new NormalRoom(54, 240, spot(8, 11), SOUTH_DOOR),
		new NormalRoom(56, 240, spot(3, 10), SOUTH_DOOR),
		new NormalRoom(58, 240, spot(3, 12), SOUTH_DOOR),
		new NormalRoom(60, 240, spot(9, 12), SOUTH_DOOR),
		new NormalRoom(62, 240, spot(12, 12), SOUTH_DOOR),
		new NormalRoom(64, 240, spot(2, 12), SOUTH_DOOR),
		new NormalRoom(66, 240, spot(8, 10), SOUTH_DOOR),
		new NormalRoom(68, 240, spot(3, 7), SOUTH_DOOR),
		new NormalRoom(70, 240, spot(8, 12), SOUTH_DOOR),
		new NormalRoom(72, 240, spot(12, 7), SOUTH_DOOR),
		new NormalRoom(74, 240, spot(4, 10), SOUTH_DOOR),
		new NormalRoom(76, 240, spot(8, 7), SOUTH_DOOR),
		new NormalRoom(78, 240, spot(3, 4), SOUTH_DOOR),

		new NormalRoom(62, 242, spot(13, 11), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(62, 244, spot(2, 3), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(62, 246, spot(13, 11), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(62, 248, spot(2, 3), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),
		new NormalRoom(64, 242, spot(7, 12), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(64, 244, spot(13, 12), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(64, 246, spot(7, 7), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(64, 248, spot(7, 7), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),
		new NormalRoom(66, 242, spot(12, 12), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(66, 244, spot(3, 4), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(66, 246, spot(12, 12), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(66, 248, spot(3, 3), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),
		new NormalRoom(68, 242, spot(12, 8), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(68, 244, spot(5, 8), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(68, 246, spot(5, 8), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(70, 242, spot(11, 10), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(70, 244, spot(8, 7), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(70, 246, spot(8, 7), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(72, 242, spot(9, 12), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(72, 244, spot(10, 8), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(72, 246, spot(11, 8), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(72, 248, spot(8, 5), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),
		new NormalRoom(74, 242, spot(3, 6), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(74, 244, spot(7, 5), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(74, 246, spot(3, 7), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(74, 248, spot(2, 6), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),
		new NormalRoom(76, 242, spot(11, 9), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(76, 244, spot(7, 7), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(76, 246, spot(7, 7), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(76, 248, spot(7, 11), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),
		new NormalRoom(78, 242, spot(12, 12), SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(78, 244, spot(12, 12), NORTH_DOOR, SOUTH_DOOR),
		new NormalRoom(78, 246, spot(12, 3), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR),
		new NormalRoom(78, 248, spot(2, 3), NORTH_DOOR, SOUTH_DOOR, WEST_DOOR, EAST_DOOR), };

	public static enum MapRoomIcon {

		MAP_1(2791, true, SOUTH_DOOR),
		MAP_2(2792, true, WEST_DOOR),
		MAP_3(2793, true, NORTH_DOOR),
		MAP_4(2794, true, EAST_DOOR),
		MAP_5(2795, true, WEST_DOOR, SOUTH_DOOR),
		MAP_6(2796, true, WEST_DOOR, NORTH_DOOR),
		MAP_7(2797, true, NORTH_DOOR, EAST_DOOR),
		MAP_8(2798, true, SOUTH_DOOR, EAST_DOOR),
		MAP_9(2799, true, SOUTH_DOOR, WEST_DOOR, NORTH_DOOR),
		MAP_10(2800, true, WEST_DOOR, NORTH_DOOR, EAST_DOOR),
		MAP_11(2801, true, SOUTH_DOOR, NORTH_DOOR, EAST_DOOR),
		MAP_12(2802, true, SOUTH_DOOR, WEST_DOOR, EAST_DOOR),
		MAP_13(2803, true, SOUTH_DOOR, NORTH_DOOR, EAST_DOOR, WEST_DOOR),
		MAP_14(2804, true, SOUTH_DOOR, NORTH_DOOR),
		MAP_15(2805, true, WEST_DOOR, EAST_DOOR),
		MAP_16(2787, false, SOUTH_DOOR),
		MAP_17(2788, false, WEST_DOOR),
		MAP_18(2789, false, NORTH_DOOR),
		MAP_19(2790, false, EAST_DOOR);

		private int[] doorsDirections;
		private int spriteId;
		private boolean open;

		private MapRoomIcon(int spriteId, boolean open, int... doorsDirections) {
			this.doorsDirections = doorsDirections;
			this.open = open;
			this.spriteId = spriteId;
		}

		public int[] getDoorDirections() {
			return doorsDirections;
		}

		public boolean hasSouthDoor() {
			return hasDoor(SOUTH_DOOR);
		}

		public boolean hasNorthDoor() {
			return hasDoor(NORTH_DOOR);
		}

		public boolean hasWestDoor() {
			return hasDoor(WEST_DOOR);
		}

		public boolean hasEastDoor() {
			return hasDoor(EAST_DOOR);
		}

		public boolean hasDoor(int direction) {
			for (int dir : doorsDirections)
				if (dir == direction)
					return true;
			return false;
		}

		public int getSpriteId() {
			return spriteId;
		}

		public boolean isOpen() {
			return open;
		}
	}

	public static final int[][] PUZZLE_DOOR_ORDER = new int[][]
	{
	{ SOUTH_DOOR, WEST_DOOR },
	{ SOUTH_DOOR, EAST_DOOR },
	{ SOUTH_DOOR, NORTH_DOOR },
	{ SOUTH_DOOR, NORTH_DOOR, WEST_DOOR },
	{ SOUTH_DOOR, EAST_DOOR, WEST_DOOR },
	{ SOUTH_DOOR, EAST_DOOR, NORTH_DOOR },
	{ SOUTH_DOOR, EAST_DOOR, NORTH_DOOR, WEST_DOOR }, };

	public static final HandledRoom[] PUZZLE_ROOMS;

	public static enum Puzzle {

		CRYSTAL_PUZZLE(12, CrystalPuzzleRoom.class, all(spot(13, 5))),
		TOXIN_MAZE(20, ToxinMaze.class, all(spot(7, 8)), false),
		FLIP_TILES(24, FlipTilesRoom.class, list(spot(1, 3), spot(1, 12), spot(1, 3), spot(14, 11), spot(14, 11), spot(1, 9), spot(1, 3))),
		FREMENNIK_CAMP(26, FremennikCampRoom.class, list(spot(6, 14), spot(10, 2), spot(14, 6), spot(5, 12), spot(13, 10), spot(3, 5), spot(13, 10))),
		FISHING_FERRET(32, FishingFerretRoom.class, all(spot(2, 1)), false),
		LEVERS(38, LeverRoom.class, list(spot(1, 5), spot(10, 14), spot(1, 5), spot(10, 14), spot(1, 5), spot(10, 14), spot(1, 5))),
		SLIDING_STATUES(42, SlidingStatuesRoom.class, all(spot(1, 3)), false),
		FLOWER_ROOTS(50, FlowerRootsRoom.class, list(spot(9, 10), spot(6, 7), spot(13, 12), spot(12, 12), spot(3, 6), spot(2, 11), spot(3, 11)), false),
		POLTERGEIST(52, PoltergeistRoom.class, list(spot(1, 10), spot(2, 10), spot(3, 5), spot(2, 4), spot(13, 4), spot(2, 12), spot(3, 4))),
		UNHAPPY_GHOST(60, UnhappyGhostRoom.class, list(spot(2, 3), spot(3, 5), spot(3, 5), spot(2, 2), spot(3, 3), spot(2, 2), spot(4, 3)), false),
		RETURN_THE_FLOW(66, ReturnTheFlowRoom.class, list(spot(3, 3), spot(2, 12), spot(2, 2), spot(4, 2), spot(3, 3), spot(2, 2), spot(2, 2))),
		COLOURED_RECESS(68, ColouredRecessRoom.class, list(spot(2, 3), spot(2, 3), spot(2, 3), spot(2, 3), spot(2, 3), spot(2, 5), spot(2, 3)), false),
		SLIDING_TILES(76, SlidingTilesRoom.class, list(spot(1, 2), spot(13, 7), spot(1, 2), spot(13, 7), spot(1, 2), spot(13, 7), spot(1, 2)));

		private int chunkX;
		private Class<? extends VisibleRoom> clazz;
		private boolean allowResources;
		private int[][] keys;

		private Puzzle(int chunkX, Class<? extends VisibleRoom> clazz) {
			this(chunkX, clazz, null);
		}

		private Puzzle(int chunkX, Class<? extends VisibleRoom> clazz, int[][] key) {
			this(chunkX, clazz, key, true);
		}

		private Puzzle(int chunkX, Class<? extends VisibleRoom> clazz, int[][] keys, boolean allowResources) {
			this.chunkX = chunkX;
			this.clazz = clazz;
			this.keys = keys;
			this.allowResources = allowResources;
		}

		public int getChunkX() {
			return chunkX;
		}

		public VisibleRoom newInstance() {
			try {
				return clazz.newInstance();
			} catch (InstantiationException | IllegalAccessException e) {
				e.printStackTrace();
				System.err.println("error creating puzzle instance");
				return null;
			}
		}

		public boolean isAvailableOnFloorType(int floorType) {
			//I think constructor args are uglier because some are exclude and some are include
			if (this == POLTERGEIST && floorType == 0) {
				return false;
			}
			if (this == FLOWER_ROOTS && floorType == 0) {
				return false;
			}
			//if(this == ICY_PRESSURE_PAD && floorType != 0) {
			//return false;
			//}
			return true;
		}

		public boolean allowResources() {
			return allowResources;
		}

		public int[] getKeySpot(int i) {
			if (keys == null || i >= keys.length) {
				return null;
			}
			return keys[i];
		}

		private static int[][] all(int[] spot) {
			return new int[][]
			{ spot, spot, spot, spot, spot, spot, spot };
		}

		private static int[][] list(int[]... list) {
			if (list.length != 7) {
				System.err.println("Error in key list " + Arrays.toString(list));
				return null;
			}
			return list;
		}

	}

	private static int[] spot(int x, int y) {
		return new int[]
		{ x, y };
	}

	static {

		int ptr = 0;
		PUZZLE_ROOMS = new HandledRoom[Puzzle.values().length * PUZZLE_DOOR_ORDER.length];
		for (Puzzle puzzle : Puzzle.values()) {
			//Force puzzle
			if (!Settings.HOSTED) {
				puzzle = Puzzle.SLIDING_STATUES;
			}/* else if(puzzle == Puzzle.COLOURED_RECESS) {
				//don't use in progress one on live instead replace it with last added one (more bug testers!)
				puzzle = Puzzle.SLIDING_STATUES;
			}*/
			for (int i = 0; i < PUZZLE_DOOR_ORDER.length; i++) {
				PUZZLE_ROOMS[ptr++] = new HandledPuzzleRoom(i, puzzle);
			}
		}

		//8 Monolith spot
		//(4,4),(4,4),(4,4),(4,4),(4,4),(4,4),(4,5)
		//10 Collapsing room (7, 1)
		//14 Ghosts (3, 10) in small one,	(3, 3)
		//(1,2),(3,10),(1,3),(1,3),(1,3),(1,3),(3,3)
		//16 Three statue weapon (Combat triangle statues) (8, 7) + chisel too
		//18 Follow the leader (Emotes) (7, 6) 
		//22 	Frozen: Icy Pressure Pad,
		//		(8, 1), (8, 1), (8, 1), (1, 8), (14, 8), (14, 8), (8, 14)
		//	Aba: Seeker Sentinel, //where no door else entrance? (8, 2) south (13, 7) east (7, 13)
		//		(), (), (), (), (), (), ()
		//	Furnished: Sleeping guards,
		//		(8, 10),all
		//	Occcult: Coloured bookcases,
		//		(8, 11), (14, 3), (4, 3), (10, 11), (5, 1), (7, 2), (3, 3)
		//	Warped: Portal maze
		//		(13, 6), all
		//28 Ten statue weapon (was 2-3 pairs on 1:1 on rs) (7, 8) on chisel
		//30 Lodestone power //east of crystal? (10, 1) (14, 4)
		//34 Suspicious grooves (11, 11) usually or opposite side
		//(5, 12 or 10,12
		//36 Agility Maze (4, 2) start always
		//40 Barrel puzzle (6, 11) barrel part at (7, 11) or (9, 2)
		//42 Sliding statues (1, 3)
		//1,3 or 3,1
		//44 Hunter ferret (8, 8) key ferret on (7, 8)
		//ferrets: (8, 7), (8, 7), (7, 7), (8, 7), (7, 8), (8, 7), (8, 7)
		//keys:    (7, 7), (8, 7), (7, 7), (7, 7), (7, 8), (7, 7), (8, 6)
		//46 Magical Construct (8, 6)
		//(), (), (), (), (), (), ()
		//48 Enigmatic Hoardstalker (Riddles) (NOT ON FROZEN) (7, 8)
		//(), (), (), (), (), (), ()
		//54 Keystone bridge (NOT ON FROZEN)
		//(9, 7), ??, (10,2) crit or (5, 13) bonus, (6, 2), (6, 2), (6, 2), (9, 2)
		//56 Grapple tightrope
		//(6, 2), (2, 2), (5, 1), (7, 2), (6, 1), (13, 1), (6, 1)
		//58 Pondskaters
		//(2, 2) or (13, 10), (<), (14, 8), (1, 6), (13, 7), (2,2 or 13,7), (13, 2)
		//60 Unhappy ghost
		//(2, 3), (3, 5), (3, 5), (2, 2), (3, 3), (2, 2), (4, 3)
		//62 Broken plank bridge
		//(6, 1), (6, 1), (6, 1), (6, 1), (7, 2), (6, 1), (6, 1)
		//64 Statue bridge
		//(13, 2), (9, 2), (4, 1), (6, 1), (9, 2), (8, 2), (9, 1)
		//68 Coloured recess 
		//(2, 3), (2, 3), (2, 3), (2, 3), (2, 3), (2, 5), (2, 3)
		//70 Winch bridge (6, 1), (1, 3), (9, 1), (9, 2), (8, 2), (6, 1), (8, 2)
		//72 Mercenary leader (combat) (12, 13), (3, 11), (2, 13), (4, 4), (4 , 2), (3, 4), (2, 3)
		//74 Ramokee familiars (combat) (4, 2), (3, 12), (2, 3), (2, 3), (2, 12), (3, 12), (5, 2)
		//78 Coloured ferrets (1, 3), (14, 4), (2, 13), (2, 2), (3, 5), (2, 2), (1, 6)
	}

	public static final BossRoom[][] BOSS_ROOMS =
	{
		// FROZEN_FLOORS
		{

			//To'Kash The Blood Chiller
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 10024, 5, 10, false, BOSS_NPC);
				}
			}, 820, 9, 26, 626)

			//Plane-freezer Lakhrahnaz
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					DungeonNPC npc = dungeon.spawnNPC(reference, 9929, 7, 11, false, BOSS_NPC);
					npc.setCantSetTargetAutoRelatio(true);
				}
			}, 819, 6, 26, 624)

			//Luminscent Icefiend
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 9912, 7, 11, false, BOSS_NPC);
				}
			}, 818, 3, 26, 626)

			//Icy Bones

			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 10040, 7, 11, false, BOSS_NPC);
				}
			}, 815, 1, 24, 626)

			// Gluttonous behemoth

			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 9948, 5, 10, false, BOSS_NPC);
					dungeon.spawnObject(reference, 49283, 10, 3, 0, 11);
					if (dungeon.getParty().getTeam().size() >= 2)
						dungeon.spawnObject(reference, 49283, 10, 0, 11, 11);
				}
			}, 817, 1, 28, 624),

			// Astea Frostweb
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 9965, 8, 12, false, BOSS_NPC);
				}
			}, 816, 1, 30, 624) },
		//ABANDONED BOSSES
		{
			//Bal'Lak The Pummeler
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 10128, 6, 8, false, BOSS_NPC);
				}
			}, 786, 33, 26, 642),

			//Shadow-forger Ihlakhizan
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 10143, 6, 6, false, BOSS_NPC);
				}
			}, 783, 30, 28, 640),

			//Unholy cursebearer
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 10111, 6, 8, false, BOSS_NPC);
				}
			}, 784, 15, 26, 640),

			//Bulwark beast
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 10073, 5, 10, false, BOSS_NPC);
				}
			}, 785, 12, 24, 642),

			//Hobgoblin Geomancer
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 10059, 6, 8, false, BOSS_NPC);
				}
			}, 787, 12, 24, 640)

			//Divine Skinweaver
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 10058, 5, 2, false, BOSS_NPC);
				}
			}, 782, 12, 30, 640) },
		//FURNISHED BOSSES
		{

			//Night-gazer Khighorahk
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 9725, 6, 6, false, BOSS_NPC);
				}
			}, 759, 26, 24, 656)

			//Sagittare
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 9753, 6, 6, false, BOSS_NPC);
				}
			}, 768, 23, 24, 658)

			//Lexicus Runewright
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 9842, 8, 7, false, BOSS_NPC);
				}
			}, 738, 20, 26, 658)

			//Lakk The Rift Splitter
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 9898, 6, 6, false, BOSS_NPC);
				}
			}, 767, 18, 28, 656)

			//Stomp
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 9782, 6, 9, false, BOSS_NPC);
				}
			}, 743, 18, 30, 656)

			//Rammernaut
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					//this one appears at middle of arena instead
					dungeon.spawnNPC(reference, 9767, 7, 7, false, BOSS_NPC);
				}
			}, 746, 18, 26, 656)

		},

		{

			//Yk'lagoor the thunderous
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 11872, 5, 5, false, BOSS_NPC);
				}

			}, 890, 45, 26, 672)

			//Flesh-spoiler Haasghenahk
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 11925, 8, 7, false, BOSS_NPC);
				}

			}, 892, 42, 24, 674)

			//Necro Lord
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 11737, 7, 10, false, BOSS_NPC);
				}

			}, 876, 39, 30, 672)

			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 11708, 5, 5, false, BOSS_NPC);
				}

			}, 891, 36, 28, 672)

			//Runebound Behemoth
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 11812, 6, 8, false, BOSS_NPC);
				}

			}, 877, 36, 26, 674)

			//Skeletal Trio
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 11940, 5, 6, false, BOSS_NPC, 0.5D);
					dungeon.spawnNPC(reference, 12044, 7, 9, false, BOSS_NPC, 0.5D);
					dungeon.spawnNPC(reference, 11999, 7, 6, false, BOSS_NPC, 0.5D);
				}

			}, 865, 36, 24, 672)

		},

		//201 5513 0 for blink
		{

			//Warmonger
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 12752, 6, 9, false, BOSS_NPC);
				}

			}, 924, 57, 24, 690)

			//World Gorger
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 12478, 5, 6, false, BOSS_NPC);
				}

			}, 937, 54, 26, 690)

			//Hope Devourer
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 12886, 8, 6, false, BOSS_NPC);
				}

			}, 916, 51, 30, 688)

			//Blink
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 12865, 5, 6, false, BOSS_NPC);
				}

			}, 940, 48, 24, 688)

			//Dreadnaut
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 12848, 7, 5, false, BOSS_NPC);
				}

			}, 913, 48, 28, 688)

			//Warped Gulega
			,
			new BossRoom(new RoomEvent() {
				@Override
				public void openRoom(DungeonManager dungeon, RoomReference reference) {
					dungeon.spawnNPC(reference, 12737, 8, 8, false, BOSS_NPC);
				}

			}, 922, 48, 26, 688) }

	};

	public static final int[][] WALL_BASE_X_Y =
	{
	{ 14, 1, 0, 14 },
	{ 1, 1, 14, 0 },
	{ 1, 1, 0, 14 },
	{ 1, 14, 14, 0 } };

	public static final int SET_RESOURCES_MAX_TRY = 300;

	public static final int FISH_SPOT_OBJECT_ID = 49922, FISH_SPOT_NPC_ID = 2859;

	public static final long[] FARMING_CYCLES =
	{ 0, 30000, 60000, Integer.MAX_VALUE };
	public static final int FARMING_PATCH_BEGINING = 50040, FARMING_PATCH_END = 50189;
	public static final int EMPTY_FARMING_PATCH = 50038;

	public static final int ESSENCE = 17776;

	public static final int NORMAL_NPC = 0, GUARDIAN_NPC = 1, FISH_SPOT_NPC = 2, BOSS_NPC = 3, FORGOTTEN_WARRIOR = 4, SLAYER_NPC = 5, HUNTER_NPC = 6, PUZZLE_NPC = 7;

	public static SmeltingBar[] SMELTING_BARS = new SmeltingBar[]
	{
		SmeltingBar.NOVITE,
		SmeltingBar.BATHUS,
		SmeltingBar.MARMAROS,
		SmeltingBar.KRATONITE,
		SmeltingBar.FRACTITE,
		SmeltingBar.ZEPHYRIUM,
		SmeltingBar.ARGONITE,
		SmeltingBar.KATAGON,
		SmeltingBar.GORGONITE,
		SmeltingBar.PROMETHIUM };

	public static int[] GROUP_GATESTONE_RUNES =
	{ 17792, 3 };

	public static final int[][] HOARDSTALKER_ITEMS =
	{
	{ 17630, 17424, 17682, 17448, 17797 },
	{ 17632, 17426, 17684, 17450, 17799 },
	{ 17634, 17428, 17686, 17452, 17801 },
	{ 17636, 17430, 17688, 17454, 17803 },
	{ 17638, 17432, 17700, 17456, 17805 },
	{ 17640, 17434, 17702, 17458, 17807 },
	{ 17642, 17436, 17704, 17460, 17809 },
	{ 17644, 17438, 17706, 17462, 17811 },
	{ 17646, 17440, 17708, 17464, 17813 },
	{ 17648, 17442, 17710, 17466, 17815 }, };

	public static final int[] SLAYER_LEVELS =
	{ 5, 10, 17, 30, 41, 52, 63, 71, 80, 90, 99 };

}
