Jump to content
  • 0

Connection database l2jacis


Question

Posted

Good evening, can someone more experienced help me? Hi, I am using a code that connects to the database plus it never connects to sql in the database any code does not work if it is a single sql

5 answers to this question

Recommended Posts

  • 0
Posted
4 hours ago, l2jkain said:

Aqui para usar a versão 350, ele não guarda nada em db nem em outros códigos que eu tento colocar

https://pastebin.com/raw/v30gpeLW 

 

5 hours ago, Tryskell said:

Coloque alguns códigos, não somos Harry Potter.

 

### Eclipse Workspace Patch 1.0#P GameserverIndex: java/net/sf/l2j/gameserver/model/entity/CursedWeapon.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/CursedWeapon.java	(revision 1)+++ java/net/sf/l2j/gameserver/model/entity/CursedWeapon.java	(working copy)@@ -10,7 +10,7 @@  import net.sf.l2j.commons.concurrent.ThreadPool; import net.sf.l2j.commons.random.Rnd;-+import net.sf.l2j.Config; import net.sf.l2j.L2DatabaseFactory; import net.sf.l2j.gameserver.datatables.ItemTable; import net.sf.l2j.gameserver.datatables.SkillTable;@@ -20,6 +20,8 @@ import net.sf.l2j.gameserver.model.actor.Attackable; import net.sf.l2j.gameserver.model.actor.Character; import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.model.entity.engine.TvT; import net.sf.l2j.gameserver.model.group.Party.MessageType; import net.sf.l2j.gameserver.model.item.instance.ItemInstance; import net.sf.l2j.gameserver.network.SystemMessageId;@@ -463,7 +465,15 @@ 			player.dropItem("InvDrop", item, null, true); 			return; 		}-		++		if ((player._inEventTvT && !Config.TVT_JOIN_CURSED) || (player._inEventCTF && !Config.CTF_JOIN_CURSED))+		{+			if (player._inEventTvT)+				TvT.removePlayer(player);+			if (player._inEventCTF)+				CTF.removePlayer(player);+		}+ 		_isActivated = true; 		 		// Hold player data.Index: java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerCtf.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerCtf.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerCtf.java	(working copy)@@ -0,0 +1,92 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ * + * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ * + * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++import java.util.ArrayList;+import java.util.Calendar;+import java.util.List;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.commons.concurrent.ThreadPool;+;++/**+ * @author Boorinio+ */+public class EventHandlerCtf+{+	private static final Logger _log = Logger.getLogger(EventHandlerCtf.class.getName());+	public List<Long> datesCtf = new ArrayList<>();+	+	public void startHandler()+	{+		loadConfisCtf(false);+		getNextTimeStampCTF();+		_log.info(EventHandlerCtf.class.getSimpleName() + ": Ctf handler initiated");+	}+	+	public void loadConfisCtf(boolean NextDay)+	{+		datesCtf.clear();+		for (String times : Config.CTF_EVENT_TIMES.split(","))+		{+			String[] timesSplited = times.split(":");+			int hour = Integer.parseInt(timesSplited[0]);+			int minute = Integer.parseInt(timesSplited[1]);+			Calendar time = Calendar.getInstance();+			if (!NextDay)+			{+				time.set(Calendar.HOUR_OF_DAY, hour);+				time.set(Calendar.MINUTE, minute);+			}+			else+			{+				time.set(Calendar.DAY_OF_MONTH, Calendar.getInstance().get(Calendar.DAY_OF_MONTH) + 1);+				time.set(Calendar.HOUR_OF_DAY, hour);+				time.set(Calendar.MINUTE, minute);+			}+			datesCtf.add(time.getTimeInMillis());+		}+	}+	+	public void getNextTimeStampCTF()+	{+		boolean found = false;+		for (Long stamp : datesCtf)+		{+			if (stamp > System.currentTimeMillis())+			{+				ThreadPool.schedule(new Runnable()+				{+					@Override+					public void run()+					{+						CTF.loadData();+						CTF.autoEvent();+						getNextTimeStampCTF();+					}+				}, stamp - System.currentTimeMillis());+				found = true;+				break;+			}+		}+		if (!found)+		{+			loadConfisCtf(true);+			getNextTimeStampCTF();+		}+	}+}Index: java/net/sf/l2j/gameserver/model/L2Skill.java===================================================================--- java/net/sf/l2j/gameserver/model/L2Skill.java	(revision 3)+++ java/net/sf/l2j/gameserver/model/L2Skill.java	(working copy)@@ -6,6 +6,7 @@ import java.util.StringTokenizer; import java.util.logging.Logger; +import net.sf.l2j.Config; import net.sf.l2j.commons.util.ArraysUtil; import net.sf.l2j.gameserver.datatables.SkillTable; import net.sf.l2j.gameserver.datatables.SkillTreeTable;@@ -23,6 +24,9 @@ import net.sf.l2j.gameserver.model.actor.instance.Player; import net.sf.l2j.gameserver.model.actor.instance.Servitor; import net.sf.l2j.gameserver.model.actor.instance.SiegeFlag;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.model.entity.engine.DM;+import net.sf.l2j.gameserver.model.entity.engine.TvT; import net.sf.l2j.gameserver.model.group.Party; import net.sf.l2j.gameserver.model.holder.IntIntHolder; import net.sf.l2j.gameserver.model.item.kind.Armor;@@ -1659,6 +1663,17 @@ 								continue; 						} 						+						//check if allow interference is allowed if player is not on event but target is on event+						if (((TvT._started && !Config.TVT_ALLOW_INTERFERENCE) || (CTF._started && !Config.CTF_ALLOW_INTERFERENCE) || (DM._started && !Config.DM_ALLOW_INTERFERENCE)))+						{+							if ((obj._inEventTvT && !player._inEventTvT) || (!obj._inEventTvT && player._inEventTvT))+								continue;+							if ((obj._inEventCTF && !player._inEventCTF) || (!obj._inEventCTF && player._inEventCTF))+								continue;+							else if ((obj._inEventDM && !player._inEventDM) || (!obj._inEventDM && player._inEventDM))+								continue;+						}+						 						if (!player.checkPvpSkill(obj, this)) 							continue; 						@@ -1983,7 +1998,7 @@ 				{ 					final Summon targetSummon = (Summon) target; 					final Player summonOwner = targetSummon.getActingPlayer();-								+					 					if (activeChar instanceof Player && activeChar.getPet() != targetSummon && !targetSummon.isDead() && (summonOwner.getPvpFlag() != 0 || summonOwner.getKarma() > 0) || (summonOwner.isInsideZone(ZoneId.PVP) && activeChar.isInsideZone(ZoneId.PVP)) || (summonOwner.isInDuel() && ((Player) activeChar).isInDuel() && summonOwner.getDuelId() == ((Player) activeChar).getDuelId())) 						return new Character[] 							{Index: java/net/sf/l2j/gameserver/network/clientpackets/RequestRestart.java===================================================================--- java/net/sf/l2j/gameserver/network/clientpackets/RequestRestart.java	(revision 1)+++ java/net/sf/l2j/gameserver/network/clientpackets/RequestRestart.java	(working copy)@@ -50,7 +50,13 @@ 			sendPacket(RestartResponse.valueOf(false)); 			return; 		}-		++		if (player._inEventTvT)+		{+			player.sendMessage("You may not use an escape skill in a Event.");+			return;+		}+ 		player.removeFromBossZone(); 		 		final L2GameClient client = getClient();Index: java/net/sf/l2j/util/EventData.java===================================================================--- java/net/sf/l2j/util/EventData.java	(revision 0)+++ java/net/sf/l2j/util/EventData.java	(working copy)@@ -0,0 +1,43 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.util;++import java.util.LinkedList;++public class EventData+{+	public int eventX;+	public int eventY;+	public int eventZ;+	public int eventKarma;+	public int eventPvpKills;+	public int eventPkKills;+	public String eventTitle;+	public LinkedList<String> kills = new LinkedList<>();+	public boolean eventSitForced = false;++	public EventData(int pEventX, int pEventY, int pEventZ, int pEventkarma, int pEventpvpkills, int pEventpkkills, String pEventTitle, LinkedList<String> pKills, boolean pEventSitForced)+	{+		eventX = pEventX;+		eventY = pEventY;+		eventZ = pEventZ;+		eventKarma = pEventkarma;+		eventPvpKills = pEventpvpkills;+		eventPkKills = pEventpkkills;+		eventTitle = pEventTitle;+		kills = pKills;+		eventSitForced = pEventSitForced;+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/network/clientpackets/Logout.java===================================================================--- java/net/sf/l2j/gameserver/network/clientpackets/Logout.java	(revision 3)+++ java/net/sf/l2j/gameserver/network/clientpackets/Logout.java	(working copy)@@ -5,6 +5,7 @@ import net.sf.l2j.gameserver.model.zone.ZoneId; import net.sf.l2j.gameserver.network.SystemMessageId; import net.sf.l2j.gameserver.network.serverpackets.ActionFailed;+import net.sf.l2j.gameserver.network.serverpackets.SystemMessage; import net.sf.l2j.gameserver.taskmanager.AttackStanceTaskManager;  public final class Logout extends L2GameClientPacket@@ -47,7 +48,13 @@ 			player.sendPacket(ActionFailed.STATIC_PACKET); 			return; 		}-		++		if (player.atEvent)+		{+			player.sendPacket(SystemMessage.sendString("A superior power doesn't allow you to leave the event."));+			return;+		}+ 		player.removeFromBossZone(); 		player.logout(); 	}Index: java/net/sf/l2j/gameserver/network/clientpackets/UseItem.java===================================================================--- java/net/sf/l2j/gameserver/network/clientpackets/UseItem.java	(revision 3)+++ java/net/sf/l2j/gameserver/network/clientpackets/UseItem.java	(working copy)@@ -183,6 +183,12 @@ 				return; 			} 			+			else if (activeChar._haveFlagCTF)+			{+				activeChar.sendMessage("You can't equip an item while holding the flag");+				return;+			}+			 			switch (item.getItem().getBodyPart()) 			{ 				case Item.SLOT_LR_HAND:Index: java/net/sf/l2j/gameserver/network/L2GameClient.java===================================================================--- java/net/sf/l2j/gameserver/network/L2GameClient.java	(revision 1)+++ java/net/sf/l2j/gameserver/network/L2GameClient.java	(working copy)@@ -17,7 +17,6 @@ import net.sf.l2j.commons.mmocore.MMOClient; import net.sf.l2j.commons.mmocore.MMOConnection; import net.sf.l2j.commons.mmocore.ReceivablePacket;- import net.sf.l2j.Config; import net.sf.l2j.L2DatabaseFactory; import net.sf.l2j.gameserver.LoginServerThread;@@ -28,10 +27,12 @@ import net.sf.l2j.gameserver.model.L2Clan; import net.sf.l2j.gameserver.model.World; import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.entity.L2Event; import net.sf.l2j.gameserver.network.serverpackets.ActionFailed; import net.sf.l2j.gameserver.network.serverpackets.L2GameServerPacket; import net.sf.l2j.gameserver.network.serverpackets.ServerClose; import net.sf.l2j.gameserver.util.FloodProtectors;+import net.sf.l2j.util.EventData;  /**  * Represents a client connected on Game Server@@ -574,7 +575,16 @@ 				// we are going to manually save the char below thus we can force the cancel 				if (_autoSaveInDB != null) 					_autoSaveInDB.cancel(true);-				+				Player player = L2GameClient.this.getActiveChar();+				if (player != null) // this should only happen on connection loss+				{+					// we store all data from players who are disconnected while in an event in order to restore it in the next login+					if (player.atEvent)+					{+						EventData data = new EventData(player.eventX, player.eventY, player.eventZ, player.eventkarma, player.eventpvpkills, player.eventpkkills, player.eventTitle, player.kills, player.eventSitForced);+						L2Event.connectionLossData.put(player.getName(), data);+					}+				} 				if (getActiveChar() != null) // this should only happen on connection loss 				{ 					if (getActiveChar().isLocked())Index: java/net/sf/l2j/gameserver/model/actor/stat/PcStat.java===================================================================--- java/net/sf/l2j/gameserver/model/actor/stat/PcStat.java	(revision 1)+++ java/net/sf/l2j/gameserver/model/actor/stat/PcStat.java	(working copy)@@ -11,6 +11,9 @@ import net.sf.l2j.gameserver.model.actor.instance.Pet; import net.sf.l2j.gameserver.model.actor.instance.Player; import net.sf.l2j.gameserver.model.base.Experience;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.model.entity.engine.DM;+import net.sf.l2j.gameserver.model.entity.engine.TvT; import net.sf.l2j.gameserver.model.group.Party; import net.sf.l2j.gameserver.model.zone.ZoneId; import net.sf.l2j.gameserver.model.zone.type.L2SwampZone;@@ -192,6 +195,23 @@ 			getActiveChar().setCurrentCp(getMaxCp()); 			getActiveChar().broadcastPacket(new SocialAction(getActiveChar(), 15)); 			getActiveChar().sendPacket(SystemMessageId.YOU_INCREASED_YOUR_LEVEL);++			if (getActiveChar().isInFunEvent())+			{+				if (getActiveChar()._inEventTvT && TvT._maxlvl == getLevel() && !TvT._started)+				{+					TvT.removePlayer(getActiveChar());+				}+				if (getActiveChar()._inEventCTF && CTF._maxlvl == getLevel() && !CTF._started)+				{+					TvT.removePlayer(getActiveChar());+				}+				if (getActiveChar()._inEventDM && CTF._maxlvl == getLevel() && !DM._started)+				{+					DM.removePlayer(getActiveChar());+				}+				getActiveChar().sendMessage("Your event sign up was canceled.");+			} 		} 		 		// Give Expertise skill of this levelIndex: java/net/sf/l2j/gameserver/util/Util.java===================================================================--- java/net/sf/l2j/gameserver/util/Util.java	(revision 1)+++ java/net/sf/l2j/gameserver/util/Util.java	(working copy)@@ -171,7 +171,21 @@ 		double d = dx * dx + dy * dy; 		return d <= range * range + 2 * range * rad + rad * rad; 	}-	++	public static String reverseColor(String color)+	{+		char[] ch1 = color.toCharArray();+		char[] ch2 = new char[6];+		ch2[0] = ch1[4];+		ch2[1] = ch1[5];+		ch2[2] = ch1[2];+		ch2[3] = ch1[3];+		ch2[4] = ch1[0];+		ch2[5] = ch1[1];++		return new String(ch2);+	}+ 	/** 	 * Returns the rounded value of val to specified number of digits after the decimal point.<BR> 	 * (Based on round() in PHP)Index: java/net/sf/l2j/gameserver/model/L2Object.java===================================================================--- java/net/sf/l2j/gameserver/model/L2Object.java	(revision 1)+++ java/net/sf/l2j/gameserver/model/L2Object.java	(working copy)@@ -43,7 +43,13 @@ 	private WorldRegion _region; 	 	private boolean _isVisible;-	++	/** Engine parameters */+	public boolean _inEventTvT = false;+	public boolean _inEventCTF = false;+	public boolean _inEventVIP = false;+	public boolean _inEventDM = false;+ 	public L2Object(int objectId) 	{ 		_objectId = objectId;Index: java/net/sf/l2j/gameserver/GameServer.java===================================================================--- java/net/sf/l2j/gameserver/GameServer.java	(revision 3)+++ java/net/sf/l2j/gameserver/GameServer.java	(working copy)@@ -84,6 +84,8 @@ import net.sf.l2j.gameserver.instancemanager.games.MonsterRace; import net.sf.l2j.gameserver.model.World; import net.sf.l2j.gameserver.model.entity.Hero;+import net.sf.l2j.gameserver.model.entity.engine.EventHandlerCtf;+import net.sf.l2j.gameserver.model.entity.engine.EventHandlerTvT; import net.sf.l2j.gameserver.model.olympiad.Olympiad; import net.sf.l2j.gameserver.model.olympiad.OlympiadGameManager; import net.sf.l2j.gameserver.model.partymatching.PartyMatchRoomList;@@ -258,7 +260,16 @@ 		 		StringUtil.printSection("Events"); 		MonsterRace.getInstance();-+		if (Config.ALLOW_CTF_AUTOEVENT)+		{+			new EventHandlerCtf().startHandler();+		}+		+		if (Config.TVT_ALLOW_AUTOEVENT)+		{+			new EventHandlerTvT().startHandler();+		}+		 		if (Config.CKM_ENABLED) 		{ 			CharacterKillingManager.getInstance().init();Index: java/net/sf/l2j/gameserver/model/entity/L2Event.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/L2Event.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/L2Event.java	(working copy)@@ -0,0 +1,286 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity;++import java.io.BufferedInputStream;+import java.io.BufferedReader;+import java.io.DataInputStream;+import java.io.FileInputStream;+import java.io.IOException;+import java.io.InputStreamReader;+import java.util.HashMap;+import java.util.Iterator;+import java.util.LinkedList;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.gameserver.datatables.NpcTable;+import net.sf.l2j.gameserver.datatables.SpawnTable;+import net.sf.l2j.gameserver.model.L2Spawn;+import net.sf.l2j.gameserver.model.World;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.actor.template.NpcTemplate;+import net.sf.l2j.gameserver.network.clientpackets.Say2;+import net.sf.l2j.gameserver.network.serverpackets.CreatureSay;+import net.sf.l2j.gameserver.network.serverpackets.MagicSkillUse;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.util.EventData;++public class L2Event+{+	private static final Logger _log = Logger.getLogger(L2Event.class.getName());+	public static String eventName = "";+	public static int teamsNumber = 0;+	public static final HashMap<Integer, String> names = new HashMap<>();+	public static final LinkedList<String> participatingPlayers = new LinkedList<>();+	public static final HashMap<Integer, LinkedList<String>> players = new HashMap<>();+	public static int id = 12760;+	public static final LinkedList<String> npcs = new LinkedList<>();+	public static boolean active = false;+	public static final HashMap<String, EventData> connectionLossData = new HashMap<>();++	public static int getTeamOfPlayer(String name)+	{+		for (int i = 1; i <= players.size(); i++)+		{+			LinkedList<?> temp = players.get(i);+			Iterator<?> it = temp.iterator();+			while (it.hasNext())+			{+				if (it.next().equals(name))+					return i;+			}+		}+		return 0;+	}++	public static String[] getTopNKillers(int N)+	{ // this will return top N players sorted by kills, first element in the array will be the one with more kills+		String[] killers = new String[N];+		String playerTemp = "";+		int kills = 0;+		LinkedList<String> killersTemp = new LinkedList<>();++		for (int k = 0; k < N; k++)+		{+			kills = 0;+			for (int i = 1; i <= teamsNumber; i++)+			{+				LinkedList<?> temp = players.get(i);+				Iterator<?> it = temp.iterator();+				while (it.hasNext())+				{+					try+					{+						Player player = World.getInstance().getPlayer((String) it.next());+						if (!killersTemp.contains(player.getName()))+						{+							if (player.kills.size() > kills)+							{+								kills = player.kills.size();+								playerTemp = player.getName();+							}+						}+					}+					catch (Exception e)+					{+					}+				}+			}+			killersTemp.add(playerTemp);+		}++		for (int i = 0; i < N; i++)+		{+			kills = 0;+			Iterator<String> it = killersTemp.iterator();+			while (it.hasNext())+			{+				try+				{+					Player player = World.getInstance().getPlayer(it.next());+					if (player.kills.size() > kills)+					{+						kills = player.kills.size();+						playerTemp = player.getName();+					}+				}+				catch (Exception e)+				{+				}+			}+			killers[i] = playerTemp;+			killersTemp.remove(playerTemp);+		}+		return killers;+	}++	public static void showEventHtml(Player player, String objectid)+	{+		try (BufferedReader inbr = new BufferedReader(new InputStreamReader(new DataInputStream(new BufferedInputStream(new FileInputStream("data/events/" + eventName))))))+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+			StringBuilder replyMSG = new StringBuilder("<html><body>");+			replyMSG.append("<center><font color=\"LEVEL\">" + eventName + "</font><font color=\"FF0000\"> bY " + inbr.readLine() + "</font></center><br>");++			replyMSG.append("<br>" + inbr.readLine());+			if (L2Event.participatingPlayers.contains(player.getName()))+				replyMSG.append("<br><center>You are already in the event players list !!</center></body></html>");+			else+				replyMSG.append("<br><center><button value=\"Participate !! \" action=\"bypass -h npc_" + objectid + "_event_participate\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></center></body></html>");++			adminReply.setHtml(replyMSG.toString());+			player.sendPacket(adminReply);+			inbr.close();+		}+		catch (IOException e)+		{+			_log.warning(L2Event.class.getSimpleName() + ": failed to read line data/events/" + eventName);+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void spawn(Player target, int npcid)+	{+		NpcTemplate template1 = NpcTable.getInstance().getTemplate(npcid);++		try+		{+			// L2MonsterInstance mob = new L2MonsterInstance(template1);++			L2Spawn spawn = new L2Spawn(template1);++			spawn.setLoc(target.getX() + 50, target.getY() + 50, target.getZ(),target.getHeading());+			spawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(spawn, false);++			spawn.setRespawnState(true);+			spawn.doSpawn(false);+			spawn.getNpc().setCurrentHp(999999999);+			spawn.getNpc().setName("event inscriptor");+			spawn.getNpc().setTitle(L2Event.eventName);+			spawn.getNpc().isEventMob = true;+			spawn.getNpc().isAggressive();+			spawn.getNpc().decayMe();+			spawn.getNpc().spawnMe(spawn.getNpc().getX(), spawn.getNpc().getY(), spawn.getNpc().getZ());++			spawn.getNpc().broadcastPacket(new MagicSkillUse(spawn.getNpc(), spawn.getNpc(), 1034, 1, 1, 1));++			npcs.add(String.valueOf(spawn.getNpc().getObjectId()));+		}+		catch (Exception e)+		{+			_log.warning(L2Event.class.getSimpleName() + ": failed to spawn npcid:" + npcid);+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void announceAllPlayers(String text)+	{+		CreatureSay cs = new CreatureSay(0, Say2.ANNOUNCEMENT, "", text);++		for (Player player : World.getInstance().getPlayers())+		{+			player.sendPacket(cs);+		}+	}++	public static boolean isOnEvent(Player player)+	{+		for (int k = 0; k < L2Event.teamsNumber; k++)+		{+			Iterator<?> it = L2Event.players.get(k + 1).iterator();+			boolean temp = false;+			while (it.hasNext())+			{+				temp = player.getName().equalsIgnoreCase(it.next().toString());+				if (temp)+					return true;+			}+		}+		return false;+	}++	public static void inscribePlayer(Player player)+	{+		try+		{+			L2Event.participatingPlayers.add(player.getName());+			player.eventkarma = player.getKarma();+			player.eventX = player.getX();+			player.eventY = player.getY();+			player.eventZ = player.getZ();+			player.eventpkkills = player.getPkKills();+			player.eventpvpkills = player.getPvpKills();+			player.eventTitle = player.getTitle();+			player.kills.clear();+			player.atEvent = true;+		}+		catch (Exception e)+		{+			_log.warning(L2Event.class.getSimpleName() + ": error when signing in the event:");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void restoreChar(Player player)+	{+		try+		{+			player.eventX = connectionLossData.get(player.getName()).eventX;+			player.eventY = connectionLossData.get(player.getName()).eventY;+			player.eventZ = connectionLossData.get(player.getName()).eventZ;+			player.eventkarma = connectionLossData.get(player.getName()).eventKarma;+			player.eventpvpkills = connectionLossData.get(player.getName()).eventPvpKills;+			player.eventpkkills = connectionLossData.get(player.getName()).eventPkKills;+			player.eventTitle = connectionLossData.get(player.getName()).eventTitle;+			player.kills = connectionLossData.get(player.getName()).kills;+			player.eventSitForced = connectionLossData.get(player.getName()).eventSitForced;+			player.atEvent = true;+		}+		catch (Exception e)+		{+			_log.warning(L2Event.class.getSimpleName() + ": error when signing in the event:");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void restoreAndTeleChar(Player target)+	{+		try+		{+			restoreChar(target);+			target.setTitle(target.eventTitle);+			target.setKarma(target.eventkarma);+			target.setPvpKills(target.eventpvpkills);+			target.setPkKills(target.eventpkkills);+			target.teleToLocation(target.eventX, target.eventY, target.eventZ, 0);+			target.kills.clear();+			target.eventSitForced = false;+			target.atEvent = false;+		}+		catch (Exception e)+		{+			_log.warning(L2Event.class.getSimpleName() + ": error when restore and teleport character");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminCTFEngine.java===================================================================--- java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminCTFEngine.java	(revision 0)+++ java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminCTFEngine.java	(working copy)@@ -0,0 +1,465 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.handler.admincommandhandlers;++import net.sf.l2j.Config;+import net.sf.l2j.commons.concurrent.ThreadPool;+import net.sf.l2j.gameserver.datatables.ItemTable;+import net.sf.l2j.gameserver.handler.IAdminCommandHandler;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.util.Util;+++/**+ * @author: FBIagent / fixed by SqueezeD+ */+public class AdminCTFEngine implements IAdminCommandHandler+{+	private static final String[] ADMIN_COMMANDS =+	{/** @formatter:off */+		"admin_ctf",+		"admin_ctf_name",+		"admin_ctf_desc",+		"admin_ctf_join_loc",+		"admin_ctf_edit",+		"admin_ctf_control",+		"admin_ctf_minlvl",+		"admin_ctf_maxlvl",+		"admin_ctf_tele_npc",+		"admin_ctf_tele_team",+		"admin_ctf_tele_flag",+		"admin_ctf_npc",+		"admin_ctf_npc_pos",+		"admin_ctf_reward",+		"admin_ctf_reward_amount",+		"admin_ctf_team_add",+		"admin_ctf_team_remove",+		"admin_ctf_team_pos",+		"admin_ctf_team_color",+		"admin_ctf_team_flag",+		"admin_ctf_join",+		"admin_ctf_teleport",+		"admin_ctf_start",+		"admin_ctf_abort",+		"admin_ctf_finish",+		"admin_ctf_sit",+		"admin_ctf_dump",+		"admin_ctf_save",+		"admin_ctf_load",+		"admin_ctf_jointime",+		"admin_ctf_eventtime",+		"admin_ctf_autoevent",+		"admin_ctf_minplayers",+		"admin_ctf_maxplayers"+	};/** @formatter:on */++	@Override+	public boolean useAdminCommand(String command, Player activeChar)+	{+		try+		{+			if (command.equals("admin_ctf"))+				showMainPage(activeChar);+			else if (command.startsWith("admin_ctf_name "))+			{+				CTF._eventName = command.substring(15);+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_desc "))+			{+				CTF._eventDesc = command.substring(15);+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_minlvl "))+			{+				if (!CTF.checkMinLevel(Integer.valueOf(command.substring(17))))+					return false;+				CTF._minlvl = Integer.valueOf(command.substring(17));+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_team_flag "))+			{+				String[] params;++				params = command.split(" ");++				if (params.length != 2)+				{+					activeChar.sendMessage("Wrong usge: //ctf_team_flag <teamName>");+					return false;+				}++				CTF.setTeamFlag(params[1], activeChar);+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_edit"))+			{+				showEditPage(activeChar);+			}+			else if (command.equals("admin_ctf_control"))+			{+				showControlPage(activeChar);+			}+			else if (command.equals("admin_ctf_tele_npc"))+			{+				activeChar.teleToLocation(CTF._npcX, CTF._npcY, CTF._npcZ, 0);+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_tele_team "))+			{+				for (String t : CTF._teams)+					if (t.equals(command.substring(20)))+					{+						int index = CTF._teams.indexOf(t);+						activeChar.teleToLocation(CTF._teamsX.get(index), CTF._teamsY.get(index), CTF._teamsZ.get(index), 0);+					}+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_tele_flag "))+			{+				for (String t : CTF._teams)+					if (t.equals(command.substring(20)))+					{+						int index = CTF._teams.indexOf(t);+						activeChar.teleToLocation(CTF._flagsX.get(index), CTF._flagsY.get(index), CTF._flagsZ.get(index), 0);+					}+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_maxlvl "))+			{+				if (!CTF.checkMaxLevel(Integer.valueOf(command.substring(17))))+					return false;+				CTF._maxlvl = Integer.valueOf(command.substring(17));+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_minplayers "))+			{+				CTF._minPlayers = Integer.valueOf(command.substring(21));+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_maxplayers "))+			{+				CTF._maxPlayers = Integer.valueOf(command.substring(21));+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_join_loc "))+			{+				CTF._joiningLocationName = command.substring(19);+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_npc "))+			{+				CTF._npcId = Integer.valueOf(command.substring(14));+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_npc_pos"))+			{+				CTF.setNpcPos(activeChar);+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_reward "))+			{+				CTF._rewardId = Integer.valueOf(command.substring(17));+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_reward_amount "))+			{+				CTF._rewardAmount = Integer.valueOf(command.substring(24));+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_jointime "))+			{+				CTF._joinTime = Integer.valueOf(command.substring(19));+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_eventtime "))+			{+				CTF._eventTime = Integer.valueOf(command.substring(20));+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_team_add "))+			{+				String teamName = command.substring(19);++				CTF.addTeam(teamName);+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_team_remove "))+			{+				String teamName = command.substring(22);++				CTF.removeTeam(teamName);+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_team_pos "))+			{+				String teamName = command.substring(19);++				CTF.setTeamPos(teamName, activeChar);+				showMainPage(activeChar);+			}+			else if (command.startsWith("admin_ctf_team_color "))+			{+				String[] params;++				params = command.split(" ");++				if (params.length != 3)+				{+					activeChar.sendMessage("Wrong usege: //ctf_team_color <colorHex> <teamName>");+					return false;+				}++				CTF.setTeamColor(command.substring(params[0].length() + params[1].length() + 2), Integer.decode("0x" + Util.reverseColor(params[1])));+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_join"))+			{+				CTF.startJoin(activeChar);+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_teleport"))+			{+				CTF.teleportStart();+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_start"))+			{+				CTF.startEvent(activeChar);+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_abort"))+			{+				activeChar.sendMessage("Aborting event");+				CTF.abortEvent();+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_finish"))+			{+				CTF.finishEvent();+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_sit"))+			{+				CTF.sit();+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_load"))+			{+				CTF.loadData();+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_autoevent"))+			{+				if (CTF._joinTime > 0 && CTF._eventTime > 0)+					ThreadPool.schedule(new Runnable()+					{+						@Override+						public void run()+						{+							CTF.autoEvent();+						}+					}, 0);+				else+					activeChar.sendMessage("Wrong usege: join time or event time invallid.");+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_save"))+			{+				CTF.saveData();+				showMainPage(activeChar);+			}+			else if (command.equals("admin_ctf_dump"))+				CTF.dumpData();++			return true;+		}+		catch (Exception e)+		{+			activeChar.sendMessage("The command was not used correctly");+			return false;+		}+	}++	@Override+	public String[] getAdminCommandList()+	{+		return ADMIN_COMMANDS;+	}++	public void showEditPage(Player activeChar)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[CTF Engine by Darki699]</font></center><br><br><br>");+		replyMSG.append("<table><tr><td><edit var=\"input1\" width=\"125\"></td><td><edit var=\"input2\" width=\"125\"></td></tr></table>");+		replyMSG.append("<table border=\"0\"><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Name\" action=\"bypass -h admin_ctf_name $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Description\" action=\"bypass -h admin_ctf_desc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Join Location\" action=\"bypass -h admin_ctf_join_loc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Max lvl\" action=\"bypass -h admin_ctf_maxlvl $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Min lvl\" action=\"bypass -h admin_ctf_minlvl $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Max players\" action=\"bypass -h admin_ctf_maxplayers $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Min players\" action=\"bypass -h admin_ctf_minplayers $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"NPC\" action=\"bypass -h admin_ctf_npc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"NPC Pos\" action=\"bypass -h admin_ctf_npc_pos\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Reward\" action=\"bypass -h admin_ctf_reward $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Reward Amount\" action=\"bypass -h admin_ctf_reward_amount $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Join Time\" action=\"bypass -h admin_ctf_jointime $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Event Time\" action=\"bypass -h admin_ctf_eventtime $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Add\" action=\"bypass -h admin_ctf_team_add $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Color\" action=\"bypass -h admin_ctf_team_color $input1 $input2\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Pos\" action=\"bypass -h admin_ctf_team_pos $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Flag\" action=\"bypass -h admin_ctf_team_flag $input1 $input2\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Remove\" action=\"bypass -h admin_ctf_team_remove $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br>");+		replyMSG.append("<br><center><button value=\"Back\" action=\"bypass -h admin_ctf\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></center></body></html>");+		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}++	public void showControlPage(Player activeChar)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[CTF Engine by Darki699]</font></center><br><br><br>");+		replyMSG.append("<table border=\"0\"><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Join\" action=\"bypass -h admin_ctf_join\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Teleport\" action=\"bypass -h admin_ctf_teleport\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Start\" action=\"bypass -h admin_ctf_start\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Abort\" action=\"bypass -h admin_ctf_abort\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Finish\" action=\"bypass -h admin_ctf_finish\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Sit Force\" action=\"bypass -h admin_ctf_sit\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Dump\" action=\"bypass -h admin_ctf_dump\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Save\" action=\"bypass -h admin_ctf_save\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Load\" action=\"bypass -h admin_ctf_load\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Auto Event\" action=\"bypass -h admin_ctf_autoevent\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br>");+		replyMSG.append("<br><center><button value=\"Back\" action=\"bypass -h admin_ctf\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></center></body></html>");+		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}++	public void showMainPage(Player activeChar)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[CTF Engine by Darki699]</font></center><br><br><br>");++		replyMSG.append("<table><tr>");+		if (!CTF._joining && !CTF._started && !CTF._teleport)+			replyMSG.append("<td width=\"100\"><button value=\"Edit\" action=\"bypass -h admin_ctf_edit\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Control\" action=\"bypass -h admin_ctf_control\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br>");++		replyMSG.append("<br><font color=\"LEVEL\">Current event...</font><br1>");+		replyMSG.append("    ... name:&nbsp;<font color=\"00FF00\">" + CTF._eventName + "</font><br1>");+		replyMSG.append("    ... description:&nbsp;<font color=\"00FF00\">" + CTF._eventDesc + "</font><br1>");+		replyMSG.append("    ... joining location name:&nbsp;<font color=\"00FF00\">" + CTF._joiningLocationName + "</font><br1>");+		replyMSG.append("    ... joining NPC ID:&nbsp;<font color=\"00FF00\">" + CTF._npcId + " on pos " + CTF._npcX + "," + CTF._npcY + "," + CTF._npcZ + "</font><br1>");+		replyMSG.append("        <button value=\"Tele->NPC\" action=\"bypass -h admin_ctf_tele_npc\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"><br>");+		replyMSG.append("    ... reward ID:&nbsp;<font color=\"00FF00\">" + CTF._rewardId + "</font><br1>");+		if (ItemTable.getInstance().getTemplate(CTF._rewardId) != null)+			replyMSG.append("    ... reward Item:&nbsp;<font color=\"00FF00\">" + ItemTable.getInstance().getTemplate(CTF._rewardId).getName() + "</font><br1>");+		else+			replyMSG.append("    ... reward Item:&nbsp;<font color=\"00FF00\">(unknown)</font><br1>");+		replyMSG.append("    ... reward Amount:&nbsp;<font color=\"00FF00\">" + CTF._rewardAmount + "</font><br>");+		replyMSG.append("    ... Min lvl:&nbsp;<font color=\"00FF00\">" + CTF._minlvl + "</font><br1>");+		replyMSG.append("    ... Max lvl:&nbsp;<font color=\"00FF00\">" + CTF._maxlvl + "</font><br><br>");+		replyMSG.append("    ... Min Players:&nbsp;<font color=\"00FF00\">" + CTF._minPlayers + "</font><br1>");+		replyMSG.append("    ... Max Players:&nbsp;<font color=\"00FF00\">" + CTF._maxPlayers + "</font><br>");+		replyMSG.append("    ... Joining Time:&nbsp;<font color=\"00FF00\">" + CTF._joinTime + "</font><br1>");+		replyMSG.append("    ... Event Time:&nbsp;<font color=\"00FF00\">" + CTF._eventTime + "</font><br>");+		if (CTF._teams != null && !CTF._teams.isEmpty())+			replyMSG.append("<font color=\"LEVEL\">Current teams:</font><br1>");+		replyMSG.append("<center><table border=\"0\">");++		for (String team : CTF._teams)+		{+			replyMSG.append("<tr><td width=\"100\">Name: <font color=\"FF0000\">" + team + "</font>");++			if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+				replyMSG.append("&nbsp;(" + CTF.teamPlayersCount(team) + " joined)");+			else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+			{+				if (CTF._teleport || CTF._started)+					replyMSG.append("&nbsp;(" + CTF.teamPlayersCount(team) + " in)");+			}+			replyMSG.append("</td></tr><tr><td>");++			String c = Integer.toHexString(CTF._teamColors.get(CTF._teams.indexOf(team)));+			while (c.length() < 6)+				c = "0" + c;+			replyMSG.append("Color: <font color=\"00FF00\">0x" + c.toUpperCase() + "</font><font color=\"" + c + "\"> =) </font>");++			replyMSG.append("</td></tr><tr><td>");+			replyMSG.append("<button value=\"Tele->Team\" action=\"bypass -h admin_ctf_tele_team " + team + "\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\">");+			replyMSG.append("</td></tr><tr><td>");+			replyMSG.append(CTF._teamsX.get(CTF._teams.indexOf(team)) + ", " + CTF._teamsY.get(CTF._teams.indexOf(team)) + ", " + CTF._teamsZ.get(CTF._teams.indexOf(team)));+			replyMSG.append("</td></tr><tr><td>");+			replyMSG.append("Flag Id: <font color=\"00FF00\">" + CTF._flagIds.get(CTF._teams.indexOf(team)) + "</font>");+			replyMSG.append("</td></tr><tr><td>");+			replyMSG.append("<button value=\"Tele->Flag\" action=\"bypass -h admin_ctf_tele_flag " + team + "\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\">");+			replyMSG.append("</td></tr><tr><td>");+			replyMSG.append(CTF._flagsX.get(CTF._teams.indexOf(team)) + ", " + CTF._flagsY.get(CTF._teams.indexOf(team)) + ", " + CTF._flagsZ.get(CTF._teams.indexOf(team)) + "</td></tr>");+			if (!CTF._joining && !CTF._started && !CTF._teleport)+				replyMSG.append("<tr><td width=\"60\"><button value=\"Remove\" action=\"bypass -h admin_ctf_team_remove " + team + "\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td></tr><tr></tr>");+		}++		replyMSG.append("</table></center>");++		if (!CTF._joining && !CTF._started && !CTF._teleport)+		{+			if (CTF.startJoinOk())+			{+				replyMSG.append("<br1>");+				replyMSG.append("Event is now set up. Press JOIN to start the registration.<br1>");+				replyMSG.append("                           <button value=\"Join\" action=\"bypass -h admin_ctf_join\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"><br1>");+				replyMSG.append("<br>");+			}+			else+			{+				replyMSG.append("<br1>");+				replyMSG.append("Event is NOT set up. Press <font color=\"LEVEL\">EDIT</font> to create a new event, or <font color=\"LEVEL\">CONTROL</font> to load an existing event.<br1>");+				replyMSG.append("<br>");+			}+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && !CTF._started)+		{+			replyMSG.append("<br1>");+			replyMSG.append(CTF._playersShuffle.size() + " players participating. Waiting to shuffle in teams(done on teleport)!");+			replyMSG.append("<br><br>");+		}++		replyMSG.append("</body></html>");+		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/model/actor/instance/Player.java===================================================================--- java/net/sf/l2j/gameserver/model/actor/instance/Player.java	(revision 3)+++ java/net/sf/l2j/gameserver/model/actor/instance/Player.java	(working copy)@@ -9,6 +9,7 @@ import java.util.Collection; import java.util.HashMap; import java.util.LinkedHashMap;+import java.util.LinkedList; import java.util.List; import java.util.Map; import java.util.Set;@@ -107,8 +108,12 @@ import net.sf.l2j.gameserver.model.entity.Castle; import net.sf.l2j.gameserver.model.entity.Duel.DuelState; import net.sf.l2j.gameserver.model.entity.Hero;+import net.sf.l2j.gameserver.model.entity.L2Event; import net.sf.l2j.gameserver.model.entity.Siege; import net.sf.l2j.gameserver.model.entity.Siege.SiegeSide;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.model.entity.engine.DM;+import net.sf.l2j.gameserver.model.entity.engine.TvT; import net.sf.l2j.gameserver.model.group.CommandChannel; import net.sf.l2j.gameserver.model.group.Party; import net.sf.l2j.gameserver.model.group.Party.LootRule;@@ -504,7 +509,7 @@ 	private ScheduledFuture<?> _chargeTask; 	 	private Location _currentSkillWorldPosition;- 	+	 	private int antiAfkTime; 	 	private L2AccessLevel _accessLevel;@@ -606,6 +611,33 @@ 	 	private Door _requestedGate; 	+	/** Event parameters */+	public int eventX;+	public int eventY;+	public int eventZ;+	public int eventkarma;+	public int eventpvpkills;+	public int eventpkkills;+	public String eventTitle;+	public LinkedList<String> kills = new LinkedList<>();+	public boolean eventSitForced = false;+	public boolean atEvent = false;+	+	/** TvT Engine parameters */+	public String _teamNameTvT, _originalTitleTvT;+	public int _originalNameColorTvT, _countTvTkills, _countTvTdies, _originalKarmaTvT;+	public boolean _inEventTvT = false;+	+	/** CTF Engine parameters */+	public String _teamNameCTF, _teamNameHaveFlagCTF, _originalTitleCTF;+	public int _originalNameColorCTF, _originalKarmaCTF, _countCTFflags;+	public boolean _inEventCTF = false, _haveFlagCTF = false;+	public Future<?> _posCheckerCTF = null;+	+	/** DM Engine parameters */+	public int _originalNameColorDM, _countDMkills, _originalKarmaDM;+	public boolean _inEventDM = false;+	 	/** 	 * Constructor of L2PcInstance (use L2Character constructor). 	 * <ul>@@ -2145,8 +2177,16 @@ 	 */ 	public void standUp() 	{-		if (_isSitting && !isInStoreMode() && !isAlikeDead() && !isParalyzed())+		if (L2Event.active && eventSitForced) 		{+			sendMessage("A dark force beyond your mortal understanding makes your knees to shake when you try to stand up ...");+		}+		else if (TvT._sitForced && _inEventTvT || CTF._sitForced && _inEventCTF || DM._sitForced && _inEventDM)+		{+			sendMessage("The Admin/GM handle if you sit or stand in this match!");+		}+		else if (_isSitting && !isInStoreMode() && !isAlikeDead() && !isParalyzed())+		{ 			if (_effects.isAffected(L2EffectFlag.RELAXING)) 				stopEffects(L2EffectType.RELAXING); 			@@ -3120,7 +3160,7 @@ 							return false; 						} 						break;-					+						 					case ATTACKER: 						if (getClan().getFlag() == null) 						{@@ -3128,7 +3168,7 @@ 							return false; 						} 						break;-					+						 					default: 						sendPacket(SystemMessage.getSystemMessage(SystemMessageId.CANNOT_BE_RESURRECTED_DURING_SIEGE)); 						return false;@@ -3169,6 +3209,25 @@ 	@Override 	public void onAction(Player player) 	{+		if (((TvT._started && !Config.TVT_ALLOW_INTERFERENCE) || (CTF._started && !Config.CTF_ALLOW_INTERFERENCE) || (DM._started && !Config.DM_ALLOW_INTERFERENCE) && !player.isGM()))+		{+			if ((_inEventTvT && !player._inEventTvT) || (!_inEventTvT && player._inEventTvT))+			{+				player.sendPacket(ActionFailed.STATIC_PACKET);+				return;+			}+			+			if ((_inEventCTF && !player._inEventCTF) || (!_inEventCTF && player._inEventCTF))+			{+				player.sendPacket(ActionFailed.STATIC_PACKET);+				return;+			}+			if ((_inEventDM && !player._inEventDM) || (!_inEventDM && player._inEventDM))+			{+				player.sendPacket(ActionFailed.STATIC_PACKET);+				return;+			}+		} 		// Set the target of the player 		if (player.getTarget() != this) 			player.setTarget(this);@@ -3180,9 +3239,9 @@ 				player.getAI().setIntention(CtrlIntention.INTERACT, this); 				return; 			}-+			 			// Check if this L2PcInstance is autoAttackable-			if (isAutoAttackable(player))+			if (isAutoAttackable(player) || (player._inEventTvT && TvT._started) || (player._inEventCTF && CTF._started) || (player._inEventDM && DM._started)) 			{ 				// Player with lvl < 21 can't attack a cursed weapon holder and a cursed weapon holder can't attack players with lvl < 21 				if ((isCursedWeaponEquipped() && player.getLevel() < 21) || (player.isCursedWeaponEquipped() && getLevel() < 21))@@ -3427,11 +3486,11 @@ 				case PACKAGE_SELL: 					sendPacket(new PrivateStoreListSell(this, temp)); 					break;-				+					 				case BUY: 					sendPacket(new PrivateStoreListBuy(this, temp)); 					break;-				+					 				case MANUFACTURE: 					sendPacket(new RecipeShopSellList(this, temp)); 					break;@@ -3743,7 +3802,7 @@ 		{ 			if (oldTarget.equals(newTarget)) 				return; // no target change-				+			 			// Remove the L2PcInstance from the _statusListener of the old target if it was a L2Character 			if (oldTarget instanceof Character) 				((Character) oldTarget).removeStatusListener(this);@@ -3826,7 +3885,7 @@ 		final ItemInstance armor = getInventory().getPaperdollItem((type == ArmorType.SHIELD) ? Inventory.PAPERDOLL_LHAND : Inventory.PAPERDOLL_CHEST); 		if (armor == null) 			return type == ArmorType.NONE; // Return true if not equipped and the check was based on NONE ArmorType.-			+		 		// Test if the equipped item is an armor, then finally compare both ArmorType. 		return armor.getItemType() instanceof ArmorType && armor.getItemType() == type; 	}@@ -3936,6 +3995,125 @@ 		{ 			Player pk = killer.getActingPlayer(); 			+			if (pk != null && pk._inEventTvT && _inEventTvT)+			{+				if (TvT._teleport || TvT._started)+				{+					if (!(pk._teamNameTvT.equals(_teamNameTvT)))+					{+						QuestState ps = pk.getQuestState(null);+						ps.playSound(QuestState.SOUND_FINISH);+						+						_countTvTdies++;+						pk._countTvTkills++;+						pk.setTitle("Kills: " + pk._countTvTkills);++						TvT.setTeamKillsCount(pk._teamNameTvT, TvT.teamKillsCount(pk._teamNameTvT) + 1);+					}+					else+					{+						pk.sendMessage("You are a teamkiller! Teamkills are not allowed, you will get death penalty and your team will lose one kill!");+						+						// Give Penalty for Team-Kill:+						// 1. Death Penalty + 5+						// 2. Team will lost 1 Kill+						if (pk.getDeathPenaltyBuffLevel() < 10)+						{+							pk.setDeathPenaltyBuffLevel(pk.getDeathPenaltyBuffLevel() + 4);+							pk.getDeathPenaltyBuffLevel();+						}+						TvT.setTeamKillsCount(_teamNameTvT, TvT.teamKillsCount(_teamNameTvT) - 1);+					}+					sendMessage("You will be revived and teleported to team spot in " + Config.TVT_REVIVE_DELAY / 1000 + " seconds!");+					ThreadPool.schedule(new Runnable()+					{+						@Override+						public void run()+						{+							teleToLocation(TvT._teamsX.get(TvT._teams.indexOf(_teamNameTvT)), TvT._teamsY.get(TvT._teams.indexOf(_teamNameTvT)), TvT._teamsZ.get(TvT._teams.indexOf(_teamNameTvT)), 0);+							doRevive();+						}+					}, Config.TVT_REVIVE_DELAY);+				}+			}+			else if (_inEventTvT)+			{+				if (TvT._teleport || TvT._started)+				{+					sendMessage("You will be revived and teleported to team spot in " + Config.TVT_REVIVE_DELAY / 1000 + " seconds!");+					ThreadPool.schedule(new Runnable()+					{+						@Override+						public void run()+						{+							teleToLocation(TvT._teamsX.get(TvT._teams.indexOf(_teamNameTvT)), TvT._teamsY.get(TvT._teams.indexOf(_teamNameTvT)), TvT._teamsZ.get(TvT._teams.indexOf(_teamNameTvT)), 0);+							doRevive();+						}+					}, Config.TVT_REVIVE_DELAY);+				}+			}+			else if (_inEventCTF)+			{+				if (CTF._teleport || CTF._started)+				{+					sendMessage("You will be revived and teleported to team flag in " + Config.CTF_REVIVE_DELAY / 1000 + " seconds!");+					+					if (_haveFlagCTF)+					{+						removeCTFFlagOnDie();+					}+					+					ThreadPool.schedule(new Runnable()+					{+						@Override+						public void run()+						{+							teleToLocation(CTF._teamsX.get(CTF._teams.indexOf(_teamNameCTF)), CTF._teamsY.get(CTF._teams.indexOf(_teamNameCTF)), CTF._teamsZ.get(CTF._teams.indexOf(_teamNameCTF)), 0);+							doRevive();+						}+					}, Config.CTF_REVIVE_DELAY);+				}+			}+			else if ((killer instanceof Player && ((Player) killer)._inEventDM) && _inEventDM)+			{+				if (DM._teleport || DM._started)+				{+					((Player) killer)._countDMkills++;+					+					sendMessage("You will be revived and teleported to spot in " + Config.DM_REVIVE_DELAY / 1000 + " seconds!");+					ThreadPool.schedule(new Runnable()+					{+						@Override+						public void run()+						{+							teleToLocation(DM._playerX, DM._playerY, DM._playerZ, 0);+							doRevive();+						}+					}, Config.DM_REVIVE_DELAY);+				}+			}+			else if (_inEventDM)+			{+				if (DM._teleport || DM._started)+				{+					sendMessage("You will be revived and teleported to spot in " + Config.DM_REVIVE_DELAY / 1000 + " seconds!");+					ThreadPool.schedule(new Runnable()+					{+						@Override+						public void run()+						{+							teleToLocation(DM._playerX, DM._playerY, DM._playerZ, 0);+							doRevive();+						}+					}, Config.DM_REVIVE_DELAY);+				}+			}+			+			if (atEvent && pk != null)+			{+				pk.kills.add(getName());+			}+			 			// Clear resurrect xp calculation 			setExpBeforeDeath(0); 			@@ -3991,7 +4169,7 @@ 		for (Character character : getKnownType(Character.class)) 			if (character.getFusionSkill() != null && character.getFusionSkill().getTarget() == this) 				character.abortCast();-			+		 		// calculate death penalty buff 		calculateDeathPenaltyBuffLevel(killer); 		@@ -4062,7 +4240,7 @@ 					} 					else 						itemDropPercent = dropItem; // Item in inventory-						+					 					// NOTE: Each time an item is dropped, the chance of another item being dropped gets lesser (dropCount * 2) 					if (Rnd.get(100) < itemDropPercent) 					{@@ -4100,6 +4278,9 @@ 		if (targetPlayer == null || targetPlayer == this) 			return; 		+		if (_inEventCTF || _inEventTvT || _inEventDM)+			return;+		 		// Don't rank up the CW if it was a summon. 		if (isCursedWeaponEquipped() && target instanceof Player) 		{@@ -4110,7 +4291,7 @@ 		// If in duel and you kill (only can kill l2summon), do nothing 		if (isInDuel() && targetPlayer.isInDuel()) 			return;-+		 		// If in pvp zone, do nothing. 		if (isInsideZone(ZoneId.PVP) && targetPlayer.isInsideZone(ZoneId.PVP)) 		{@@ -4134,6 +4315,9 @@ 		{ 			if (target instanceof Player) 			{+				if ((TvT._started && _inEventTvT) || (DM._started && _inEventDM) || (CTF._started && _inEventCTF))+					return;+				 				// Add PvP point to attacker. 				setPvpKills(getPvpKills() + 1); 				@@ -4148,6 +4332,9 @@ 			if (target instanceof Player) 				setPkKills(getPkKills() + 1); 			+			if ((TvT._started && _inEventTvT) || (DM._started && _inEventDM) || (CTF._started && _inEventCTF))+				return;+			 			// Calculate new karma. 			setKarma(getKarma() + Formulas.calculateKarmaGain(getPkKills(), target instanceof Summon)); 			@@ -4156,11 +4343,19 @@ 		} 	} 	+	public boolean isInFunEvent()+	{+		return (atEvent || (TvT._started && _inEventTvT) || (DM._started && _inEventDM) || (CTF._started && _inEventCTF));+	}+	 	public void updatePvPStatus() 	{ 		if (isInsideZone(ZoneId.PVP)) 			return;-+		+		if ((TvT._started && _inEventTvT) ||(DM._started && _inEventDM) || (CTF._started && _inEventCTF))+			return;+		 		PvpFlagTaskManager.getInstance().add(this, Config.PVP_NORMAL_TIME); 		 		if (getPvpFlag() == 0)@@ -4172,7 +4367,10 @@ 		final Player player = target.getActingPlayer(); 		if (player == null) 			return;-+		+		if ((TvT._started && _inEventTvT && target._inEventTvT) || (DM._started && _inEventDM && target._inEventDM) || (CTF._started && _inEventCTF && target._inEventCTF))+			return;+		 		if (isInDuel() && player.getDuelId() == getDuelId()) 			return; 		@@ -4227,7 +4425,7 @@ 			else if (killedByPlayable) 				return; 		}-+		 		// Get the level of the L2PcInstance 		final int lvl = getLevel(); 		@@ -4246,12 +4444,12 @@ 		 		// Calculate the Experience loss 		long lostExp = 0;+		if (!atEvent && !_inEventTvT && !_inEventDM && !_inEventCTF)+			if (lvl < Experience.MAX_LEVEL)+				lostExp = Math.round((getStat().getExpForLevel(lvl + 1) - getStat().getExpForLevel(lvl)) * percentLost / 100);+			else+				lostExp = Math.round((getStat().getExpForLevel(Experience.MAX_LEVEL) - getStat().getExpForLevel(Experience.MAX_LEVEL - 1)) * percentLost / 100); 		-		if (lvl < Experience.MAX_LEVEL)-			lostExp = Math.round((getStat().getExpForLevel(lvl + 1) - getStat().getExpForLevel(lvl)) * percentLost / 100);-		else-			lostExp = Math.round((getStat().getExpForLevel(Experience.MAX_LEVEL) - getStat().getExpForLevel(Experience.MAX_LEVEL - 1)) * percentLost / 100);-		 		// Get the Experience before applying penalty 		setExpBeforeDeath(getExp()); 		@@ -4720,8 +4918,8 @@ 		if (wpn != null) 		{ 			if (wpn.getItemId() == 9999)-								return false;-							+				return false;+			 			ItemInstance[] unequipped = getInventory().unEquipItemInBodySlotAndRecord(wpn); 			InventoryUpdate iu = new InventoryUpdate(); 			for (ItemInstance itm : unequipped)@@ -5545,6 +5743,19 @@ 	} 	 	/**+	 * checks if player is same team member in TvT+	 * @param attacker +	 * @param target+	 * @return+	 */+	public static boolean isMemberOfSameTeam(Character attacker, Character target)+	{+		if ((attacker instanceof Player && ((Player) attacker)._inEventTvT && ((Player) attacker)._teamNameTvT == ((Player) target)._teamNameTvT && ((Player) target)._inEventTvT))+			return true;+		return false;+	}+	+	/** 	 * Restores secondary data for the L2PcInstance, based on the current class index. 	 */ 	private void restoreCharData()@@ -6062,7 +6273,7 @@ 				 				if (id > 9000) 					continue; // fake skills for base stats-					+				 				// Create a L2Skill object for each record 				L2Skill skill = SkillTable.getInstance().getInfo(id, level); 				@@ -6465,7 +6676,7 @@ 			// is AutoAttackable if both players are in the same duel and the duel is still going on 			if (getDuelState() == DuelState.DUELLING && getDuelId() == cha.getDuelId()) 				return true;-+			 			if (getClan() != null) 			{ 				final Siege siege = CastleManager.getInstance().getSiege(this);@@ -6544,7 +6755,7 @@ 			sendPacket(ActionFailed.STATIC_PACKET); 			return false; 		}-+		 		// Cancels the use of skills when player uses a cursed weapon or is flying. 		if ((isCursedWeaponEquipped() && !skill.isDemonicSkill()) // If CW, allow ONLY demonic skills. 			|| (getMountType() == 1 && !skill.isStriderSkill()) // If mounted, allow ONLY Strider skills.@@ -6605,7 +6816,7 @@ 			case TARGET_AURA_UNDEAD: 				target = this; 				break;-			+				 			default: // Get the first target of the list 				target = skill.getFirstOfTargetList(this); 				break;@@ -6698,6 +6909,7 @@ 		// ************************************* Check Target ******************************************* 		// Create and set a L2Object containing the target of the skill 		L2Object target = null;+		L2SkillType SkillType = skill.getSkillType(); 		SkillTargetType sklTargetType = skill.getTargetType(); 		Location worldPosition = getCurrentSkillWorldPosition(); 		@@ -6767,6 +6979,36 @@ 			} 		} 		+		if (_inEventTvT && TvT._started && !Config.TVT_ALLOW_ENEMY_HEALING)+		{+			if (target instanceof Player && skill.getSkillType() == L2SkillType.HEAL)+			{+				if (!isMemberOfSameTeam((this), (Player) target))+				{+					sendPacket(SystemMessageId.INCORRECT_TARGET);+					sendPacket(ActionFailed.STATIC_PACKET);+					return false;+				}+				+				// prevent usage of skills in same team members on TvT if tvt is on figthing period and if config is enabled+				if (_inEventTvT && TvT._started && !Config.TVT_ALLOW_TEAM_CASTING)+				{+					if (target instanceof Player && skill.getTargetType() != SkillTargetType.TARGET_SELF && skill.getSkillType() != L2SkillType.BUFF)+					{+						if (isMemberOfSameTeam((this), (Player) target))+						{+							if (skill.getSkillType() == L2SkillType.PDAM || skill.getSkillType() == L2SkillType.MDAM || (skill.getSkillType() == L2SkillType.BLOW))+							{+								sendPacket(SystemMessageId.INCORRECT_TARGET);+								sendPacket(ActionFailed.STATIC_PACKET);+								return false;+							}+						}+					}+				}+			}+		}+		 		// ************************************* Check skill availability ******************************************* 		 		// Siege summon checks. Both checks send a message to the player if it return false.@@ -6788,6 +7030,11 @@ 		 		// ************************************* Check casting conditions ******************************************* 		+		if (_inEventCTF && !Config.CTF_ALLOW_SUMMON && CTF._started && SkillType == L2SkillType.SUMMON)+		{+			sendPacket(SystemMessageId.NOTHING_HAPPENED);+		}+		 		// Check if all casting conditions are completed 		if (!skill.checkCondition(this, target, false)) 		{@@ -7154,7 +7401,7 @@ 			 			final L2Clan aClan = getClan(); 			final L2Clan tClan = targetPlayer.getClan();-+			 			if (aClan != null && tClan != null) 			{ 				if (aClan.isAtWarWith(tClan.getClanId()) && tClan.isAtWarWith(aClan.getClanId()))@@ -7174,7 +7421,7 @@ 					return false; 				} 			}-+			 			// On retail, it is impossible to debuff a "peaceful" player. 			if (targetPlayer.getPvpFlag() == 0 && targetPlayer.getKarma() == 0) 			{@@ -7226,7 +7473,7 @@ 				if (isFlying()) 					removeSkill(FrequentSkill.WYVERN_BREATH.getSkill()); 				break;-			+				 			case 2: // Flying Wyvern 				addSkill(FrequentSkill.WYVERN_BREATH.getSkill(), false); // not saved to DB 				break;@@ -7973,7 +8220,7 @@ 		else 			for (L2Skill s : SkillTable.getNobleSkills()) 				super.removeSkill(s); // Just Remove skills without deleting from Sql-				+		 		_isNoble = val; 		 		sendSkillList();@@ -8071,7 +8318,7 @@ 		{ 			if (s.getId() > 9000 && s.getId() < 9007) 				continue; // Fake skills to change base stats-				+			 			if (getClan() != null) 				isDisabled = s.isClanSkill() && getClan().getReputationScore() < 0; 			@@ -8104,7 +8351,7 @@ 	{ 		if (!_subclassLock.tryLock()) 			return false;-+		 		try 		{ 			if (_subClasses.size() == 3 || classIndex == 0 || _subClasses.containsKey(classIndex))@@ -8305,7 +8552,7 @@ 			for (Character character : getKnownType(Character.class)) 				if (character.getFusionSkill() != null && character.getFusionSkill().getTarget() == this) 					character.abortCast();-				+			 			store(); 			_reuseTimeStamps.clear(); 			@@ -8534,6 +8781,13 @@ 		if (isMounted()) 			startFeed(_mountNpcId); 		+		if ((_inEventTvT && TvT._started && Config.TVT_REVIVE_RECOVERY) || (_inEventCTF && CTF._started && Config.CTF_REVIVE_RECOVERY))+		{+			getStatus().setCurrentHp(getMaxHp());+			getStatus().setCurrentMp(getMaxMp());+			getStatus().setCurrentCp(getMaxCp());+		}+		 		// Schedule a paralyzed task to wait for the animation to finish 		ThreadPool.schedule(new Runnable() 		{@@ -8545,6 +8799,16 @@ 		}, (int) (2000 / getStat().getMovementSpeedMultiplier())); 		setIsParalyzed(true); 	}++	public void removeCTFFlagOnDie()+	{+		CTF._flagsTaken.set(CTF._teams.indexOf(_teamNameHaveFlagCTF), false);+		CTF.spawnFlag(_teamNameHaveFlagCTF);+		CTF.removeFlagFromPlayer(this);+		broadcastUserInfo();+		_haveFlagCTF = false;+		CTF.AnnounceToPlayers(false, CTF._eventName + "(CTF): " + _teamNameHaveFlagCTF + "'s flag returned.");+	} 	 	@Override 	public void doRevive(double revivePower)@@ -8675,6 +8939,29 @@ 		 		if (Config.PLAYER_SPAWN_PROTECTION > 0) 			setSpawnProtection(true);++		if (L2Event.active && L2Event.connectionLossData.containsKey(getName()) && L2Event.isOnEvent(this))+		{+			L2Event.restoreChar(this);+		}+		else if (L2Event.connectionLossData.containsKey(getName()))+		{+			L2Event.restoreAndTeleChar(this);+		}+		if (TvT._savePlayers.contains(getName()))+		{+			TvT.addDisconnectedPlayer(this);+		}++		if (CTF._savePlayers.contains(getName()))+		{+			CTF.addDisconnectedPlayer(this);+		}++		if (DM._savePlayers.contains(getName()))+		{+			DM.addDisconnectedPlayer(this);+		} 		 		// Stop toggles upon teleport. 		if (!isGM())@@ -8889,7 +9176,7 @@ 			for (Character character : getKnownType(Character.class)) 				if (character.getFusionSkill() != null && character.getFusionSkill().getTarget() == this) 					character.abortCast();-				+			 			// Stop signets & toggles effects. 			for (L2Effect effect : getAllEffects()) 			{@@ -9051,13 +9338,13 @@ 			case 7809: // yellow for beginners 			case 8486: // prize-winning for beginners 				return 0;-			+				 			case 8485: // prize-winning luminous 			case 8506: // green luminous 			case 8509: // purple luminous 			case 8512: // yellow luminous 				return 2;-			+				 			default: 				return 1; 		}@@ -9080,7 +9367,7 @@ 						else 							type = 6; 						break;-					+						 					case 7808: // purple lure, preferred by fat fish (type 4) 						if (check <= 54) 							type = 4;@@ -9089,7 +9376,7 @@ 						else 							type = 5; 						break;-					+						 					case 7809: // yellow lure, preferred by ugly fish (type 6) 						if (check <= 54) 							type = 6;@@ -9098,7 +9385,7 @@ 						else 							type = 4; 						break;-					+						 					case 8486: // prize-winning fishing lure for beginners 						if (check <= 33) 							type = 4;@@ -9109,7 +9396,7 @@ 						break; 				} 				break;-			+				 			case 1: // normal fish 				switch (_lure.getItemId()) 				{@@ -9119,7 +9406,7 @@ 					case 7613: 						type = 3; 						break;-					+						 					case 6519: // all theese lures (green) are prefered by fast-moving (nimble) fish (type 1) 					case 8505: 					case 6520:@@ -9134,7 +9421,7 @@ 						else 							type = 3; 						break;-					+						 					case 6522: // all theese lures (purple) are prefered by fat fish (type 0) 					case 8508: 					case 6523:@@ -9149,7 +9436,7 @@ 						else 							type = 3; 						break;-					+						 					case 6525: // all theese lures (yellow) are prefered by ugly fish (type 2) 					case 8511: 					case 6526:@@ -9174,7 +9461,7 @@ 						break; 				} 				break;-			+				 			case 2: // upper grade fish, luminous lure 				switch (_lure.getItemId()) 				{@@ -9186,7 +9473,7 @@ 						else 							type = 9; 						break;-					+						 					case 8509: // purple lure, preferred by fat fish (type 7) 						if (check <= 54) 							type = 7;@@ -9195,7 +9482,7 @@ 						else 							type = 8; 						break;-					+						 					case 8512: // yellow lure, preferred by ugly fish (type 9) 						if (check <= 54) 							type = 9;@@ -9204,7 +9491,7 @@ 						else 							type = 7; 						break;-					+						 					case 8485: // prize-winning fishing lure 						if (check <= 33) 							type = 7;@@ -9608,12 +9895,12 @@ 	{ 		return _punishTimer; 	}-+	 	public int getAntiAfk() 	{		 		return antiAfkTime; 	}- 	+	 	public void setAntiAfk(int antiAfk) 	{ 		antiAfkTime = antiAfk;@@ -9737,7 +10024,7 @@ 	{ 		if (_deathPenaltyBuffLevel >= 15) // maximum level reached 			return;-+		 		if ((getKarma() > 0 || Rnd.get(1, 100) <= Config.DEATH_PENALTY_CHANCE) && !(killer instanceof Player) && !isGM() && !(getCharmOfLuck() && (killer == null || killer.isRaid())) && !isPhoenixBlessed() && !(isInsideZone(ZoneId.PVP) || isInsideZone(ZoneId.SIEGE))) 		{ 			if (_deathPenaltyBuffLevel != 0)@@ -10192,7 +10479,7 @@ 			summonerChar.sendPacket(SystemMessage.getSystemMessage(SystemMessageId.S1_IN_SUMMON_BLOCKING_AREA).addCharName(targetChar)); 			return false; 		}-+		 		return true; 	} 	@@ -10445,11 +10732,11 @@ 			case PACKAGE_SELL: 				activeChar.sendPacket(new PrivateStoreMsgSell(this)); 				break;-			+				 			case BUY: 				activeChar.sendPacket(new PrivateStoreMsgBuy(this)); 				break;-			+				 			case MANUFACTURE: 				activeChar.sendPacket(new RecipeShopMsg(this)); 				break;Index: java/net/sf/l2j/gameserver/handler/AdminCommandHandler.java===================================================================--- java/net/sf/l2j/gameserver/handler/AdminCommandHandler.java	(revision 1)+++ java/net/sf/l2j/gameserver/handler/AdminCommandHandler.java	(working copy)@@ -8,11 +8,13 @@ import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminBan; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminBookmark; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminBuffs;+import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminCTFEngine; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminCache; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminCamera; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminChangeAccessLevel; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminCreateItem; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminCursedWeapons;+import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminDMEngine; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminDelete; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminDoorControl; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminEditChar;@@ -19,6 +21,7 @@ import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminEditNpc; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminEffects; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminEnchant;+import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminEventEngine; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminExpSp; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminGeoEngine; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminGm;@@ -48,6 +51,7 @@ import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminSpawn; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminTarget; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminTeleport;+import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminTvTEngine; import net.sf.l2j.gameserver.handler.admincommandhandlers.AdminZone;  public class AdminCommandHandler@@ -107,6 +111,10 @@ 		registerAdminCommandHandler(new AdminTarget()); 		registerAdminCommandHandler(new AdminTeleport()); 		registerAdminCommandHandler(new AdminZone());+		registerAdminCommandHandler(new AdminCTFEngine());+		registerAdminCommandHandler(new AdminDMEngine());+		registerAdminCommandHandler(new AdminEventEngine());+		registerAdminCommandHandler(new AdminTvTEngine()); 	} 	 	public void registerAdminCommandHandler(IAdminCommandHandler handler)Index: java/net/sf/l2j/gameserver/model/entity/engine/CTF.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/CTF.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/CTF.java	(working copy)@@ -0,0 +1,2223 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++import java.sql.Connection;+import java.sql.PreparedStatement;+import java.sql.ResultSet;+import java.sql.SQLException;+import java.util.ArrayList;+import java.util.List;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.L2DatabaseFactory;+import net.sf.l2j.commons.concurrent.ThreadPool;+import net.sf.l2j.commons.random.Rnd;+import net.sf.l2j.gameserver.datatables.ItemTable;+import net.sf.l2j.gameserver.datatables.NpcTable;+import net.sf.l2j.gameserver.datatables.SpawnTable;+import net.sf.l2j.gameserver.model.L2Effect;+import net.sf.l2j.gameserver.model.L2Radar;+import net.sf.l2j.gameserver.model.L2Spawn;+import net.sf.l2j.gameserver.model.actor.Summon;+import net.sf.l2j.gameserver.model.actor.instance.Pet;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.actor.template.NpcTemplate;+import net.sf.l2j.gameserver.model.group.Party;+import net.sf.l2j.gameserver.model.group.Party.MessageType;+import net.sf.l2j.gameserver.model.item.instance.ItemInstance;+import net.sf.l2j.gameserver.model.itemcontainer.Inventory;+import net.sf.l2j.gameserver.network.serverpackets.ActionFailed;+import net.sf.l2j.gameserver.network.serverpackets.CreatureSay;+import net.sf.l2j.gameserver.network.serverpackets.InventoryUpdate;+import net.sf.l2j.gameserver.network.serverpackets.ItemList;+import net.sf.l2j.gameserver.network.serverpackets.MagicSkillUse;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.network.serverpackets.RadarControl;+import net.sf.l2j.gameserver.network.serverpackets.SocialAction;+import net.sf.l2j.gameserver.util.Broadcast;++/**+ * @author SqueezeD & Darki699 (idea by FBIAgent)+ */+public class CTF+{+	private final static Logger _log = Logger.getLogger(CTF.class.getName());+	private static int _FlagNPC = 35062, _FLAG_IN_HAND_ITEM_ID = 6718;+	public static String _eventName = new String(), _eventDesc = new String(), _topTeam = new String(),+	_joiningLocationName = new String();+	public static List<String> _teams = new ArrayList<>(), _savePlayers = new ArrayList<>(),+			_savePlayerTeams = new ArrayList<>();+	public static List<Player> _players = new ArrayList<>(),+			_playersShuffle = new ArrayList<>();+	public static List<Integer> _teamPlayersCount = new ArrayList<>(), _teamColors = new ArrayList<>(),+			_teamsX = new ArrayList<>(), _teamsY = new ArrayList<>(), _teamsZ = new ArrayList<>();+	public static boolean _joining = false, _teleport = false, _started = false, _sitForced = false;+	public static L2Spawn _npcSpawn;+	public static int _npcId = 0, _npcX = 0, _npcY = 0, _npcZ = 0, _npcHeading = 0, _rewardId = 0, _rewardAmount = 0,+			_minlvl = 0, _maxlvl = 0, _joinTime = 0, _eventTime = 0, _minPlayers = 0, _maxPlayers = 0;+	public static List<Integer> _teamPointsCount = new ArrayList<>();+	public static List<Integer> _flagIds = new ArrayList<>(), _flagsX = new ArrayList<>(),+			_flagsY = new ArrayList<>(), _flagsZ = new ArrayList<>();+	public static List<L2Spawn> _flagSpawns = new ArrayList<>(), _throneSpawns = new ArrayList<>();+	public static List<Boolean> _flagsTaken = new ArrayList<>();+	public static int _topScore = 0, eventCenterX = 0, eventCenterY = 0, eventCenterZ = 0, eventOffset = 0;++	public static void showFlagHtml(Player eventPlayer, String objectId, String teamName)+	{+		if (eventPlayer == null)+			return;++		try+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++			StringBuilder replyMSG = new StringBuilder();++			replyMSG.append("<html><body><center>");+			replyMSG.append("CTF Flag<br><br>");+			replyMSG.append("<font color=\"00FF00\">" + teamName + "'s Flag</font><br>");+			if (eventPlayer._teamNameCTF != null && eventPlayer._teamNameCTF.equals(teamName))+				replyMSG.append("<font color=\"LEVEL\">This is your Flag</font><br>");+			else+				replyMSG.append("<font color=\"LEVEL\">Enemy Flag!</font><br>");+			if (_started)+				processInFlagRange(eventPlayer);+			else+				replyMSG.append("CTF match is not in progress yet.<br>Wait for a GM to start the event<br>");+			replyMSG.append("</center></body></html>");+			adminReply.setHtml(replyMSG.toString());+			eventPlayer.sendPacket(adminReply);+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[showEventHtlm(" + eventPlayer.getName() + ", " + objectId + ")]: exception: " + e.getStackTrace());+		}+	}++	public static void CheckRestoreFlags()+	{+		List<Integer> teamsTakenFlag = new ArrayList<>();+		try+		{+			for (Player player : _players)+			{ // if there's a player with a flag+				// add the index of the team who's FLAG WAS TAKEN to the list+				if (player != null)+				{+					if (player.isOnline() && player._haveFlagCTF)// logged off with a flag in his hands+					{+						AnnounceToPlayers(false, _eventName + "(CTF): " + player.getName() + " logged off with a CTF flag!");+						player._haveFlagCTF = false;+						if (_teams.indexOf(player._teamNameHaveFlagCTF) >= 0)+						{+							if (_flagsTaken.get(_teams.indexOf(player._teamNameHaveFlagCTF)))+							{+								_flagsTaken.set(_teams.indexOf(player._teamNameHaveFlagCTF), false);+								spawnFlag(player._teamNameHaveFlagCTF);+								AnnounceToPlayers(false, _eventName + "(CTF): " + player._teamNameHaveFlagCTF + " flag now returned to place.");+							}+						}+						removeFlagFromPlayer(player);+						player._teamNameHaveFlagCTF = null;+						return;+					}+					else if (player._haveFlagCTF)+						teamsTakenFlag.add(_teams.indexOf(player._teamNameHaveFlagCTF));+				}+			}+			// Go over the list of ALL teams+			for (String team : _teams)+			{+				if (team == null)+					continue;+				int index = _teams.indexOf(team);+				if (!teamsTakenFlag.contains(index))+				{+					if (_flagsTaken.get(index))+					{+						_flagsTaken.set(index, false);+						spawnFlag(team);+						AnnounceToPlayers(false, _eventName + "(CTF): " + team + " flag returned due to player error.");+					}+				}+			}+			// Check if a player ran away from the event holding a flag:+			for (Player player : _players)+			{+				if ((player != null) && player._haveFlagCTF)+				{+					if (isOutsideCTFArea(player))+					{+						AnnounceToPlayers(false, _eventName + "(CTF): " + player.getName() + " escaped from the event holding a flag!");+						player._haveFlagCTF = false;+						if (_teams.indexOf(player._teamNameHaveFlagCTF) >= 0)+						{+							if (_flagsTaken.get(_teams.indexOf(player._teamNameHaveFlagCTF)))+							{+								_flagsTaken.set(_teams.indexOf(player._teamNameHaveFlagCTF), false);+								spawnFlag(player._teamNameHaveFlagCTF);+								AnnounceToPlayers(false, _eventName + "(CTF): " + player._teamNameHaveFlagCTF + " flag now returned to place.");+							}+						}+						removeFlagFromPlayer(player);+						player._teamNameHaveFlagCTF = null;+						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameCTF)), _teamsY.get(_teams.indexOf(player._teamNameCTF)), _teamsZ.get(_teams.indexOf(player._teamNameCTF)), 0);+						player.sendMessage("You have been returned to your team spawn");+						return;+					}+				}+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF.restoreFlags() Error:" + e.toString());+		}+	}++	public static void kickPlayerFromCTf(Player playerToKick)+	{+		if (playerToKick == null)+			return;++		if (_joining)+		{+			_playersShuffle.remove(playerToKick);+			_players.remove(playerToKick);+			playerToKick._inEventCTF = false;+			playerToKick._teamNameCTF = new String();+		}+		if (_started || _teleport)+		{+			_playersShuffle.remove(playerToKick);+			playerToKick._inEventCTF = false;+			removePlayer(playerToKick);+			if (playerToKick.isOnline())+			{+				playerToKick.getAppearance().setNameColor(playerToKick._originalNameColorCTF);+				playerToKick.setKarma(playerToKick._originalKarmaCTF);+				playerToKick.setTitle(playerToKick._originalTitleCTF);+				playerToKick.broadcastUserInfo();+				playerToKick.sendMessage("You have been kicked from the CTF.");+				playerToKick.teleToLocation(_npcX, _npcY, _npcZ, 0);+			}+		}+	}++	public static void AnnounceToPlayers(Boolean toall, String announce)+	{+		if (toall)+			Broadcast.announceToOnlinePlayers(announce);+		else+		{+			CreatureSay cs = new CreatureSay(0, 2, "", "Announcements : " + announce);+			if (_players != null && !_players.isEmpty())+			{+				for (Player player : _players)+				{+					if (player != null && player.isOnline())+						player.sendPacket(cs);+				}+			}+		}+	}++	public static void Started(Player player)+	{+		player._teamNameHaveFlagCTF = null;+		player._haveFlagCTF = false;+	}++	public static void StartEvent()+	{+		for (Player player : _players)+		{+			if (player != null)+			{+				player._teamNameHaveFlagCTF = null;+				player._haveFlagCTF = false;+			}+		}+		AnnounceToPlayers(false, _eventName + "(CTF): Started. Go Capture the Flags!");+	}++	public static void addFlagToPlayer(Player _player)+	{+		// remove items from the player hands (right, left, both)+		// This is NOT a BUG, I don't want them to see the icon they have 8D+		ItemInstance wpn = _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_RHAND);+		if (wpn == null)+		{+			wpn = _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_LHAND);+			if (wpn != null)+				_player.getInventory().unEquipItemInSlot(Inventory.PAPERDOLL_LHAND);+		}+		else+		{+			_player.getInventory().unEquipItemInSlot(Inventory.PAPERDOLL_RHAND);+			wpn = _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_LHAND);+			if (wpn != null)+				_player.getInventory().unEquipItemInSlot(Inventory.PAPERDOLL_LHAND);+		}+		// add the flag in his hands+		_player.getInventory().equipItem(ItemTable.getInstance().createItem("", CTF._FLAG_IN_HAND_ITEM_ID, 1, _player, null));+		_player.broadcastPacket(new SocialAction(_player, 16),2000); // amazing glow+		_player._haveFlagCTF = true;+		_player.broadcastUserInfo();+		CreatureSay cs = new CreatureSay(_player.getObjectId(), 15, ":", "You got it! Run back! ::"); // 8D+		_player.sendPacket(cs);+	}++	public static void removeFlagFromPlayer(Player player)+	{+		ItemInstance wpn = player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_RHAND);+		player._haveFlagCTF = false;+		if (wpn != null)+		{+			ItemInstance[] unequiped = player.getInventory().unEquipItemInBodySlotAndRecord(wpn);+			player.getInventory().destroyItemByItemId("", CTF._FLAG_IN_HAND_ITEM_ID, 1, player, null);+			InventoryUpdate iu = new InventoryUpdate();+			for (ItemInstance element : unequiped)+				iu.addModifiedItem(element);+			player.sendPacket(iu);+			player.sendPacket(new ItemList(player, true)); // get your weapon back now ...+			player.abortAttack();+			player.broadcastUserInfo();+		}+		else+		{+			player.getInventory().destroyItemByItemId("", CTF._FLAG_IN_HAND_ITEM_ID, 1, player, null);+			player.sendPacket(new ItemList(player, true)); // get your weapon back now ...+			player.abortAttack();+			player.broadcastUserInfo();+		}+	}++	public static void setTeamFlag(String teamName, Player activeChar)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;+		addOrSet(_teams.indexOf(teamName), null, false, _FlagNPC, activeChar.getX(), activeChar.getY(), activeChar.getZ());+	}++	public static void setTeamFlag(String teamName, int x, int y, int z)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;+		addOrSet(_teams.indexOf(teamName), null, false, _FlagNPC, x, y, z);+	}++	public static void spawnAllFlags()+	{+		while (_flagSpawns.size() < _teams.size())+			_flagSpawns.add(null);+		while (_throneSpawns.size() < _teams.size())+			_throneSpawns.add(null);+		for (String team : _teams)+		{+			int index = _teams.indexOf(team);+			NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_flagIds.get(index));+			NpcTemplate throne = NpcTable.getInstance().getTemplate(32027);+			try+			{+				// spawn throne+				_throneSpawns.set(index, new L2Spawn(throne));+				_throneSpawns.get(index).setLoc(_flagsX.get(index), _flagsY.get(index), _flagsZ.get(index) - 10, 0);+				_throneSpawns.get(index).setRespawnDelay(1);+				+				SpawnTable.getInstance().addNewSpawn(_throneSpawns.get(index), false);+				+				_throneSpawns.get(index).setRespawnState(true);+				_throneSpawns.get(index).doSpawn(false);+				_throneSpawns.get(index).getNpc().getStatus().setCurrentHp(999999999);+				_throneSpawns.get(index).getNpc().decayMe();+				_throneSpawns.get(index).getNpc().spawnMe(_throneSpawns.get(index).getNpc().getX(), _throneSpawns.get(index).getNpc().getY(), _throneSpawns.get(index).getNpc().getZ());+				_throneSpawns.get(index).getNpc().setTitle(team + " Throne");+				_throneSpawns.get(index).getNpc().broadcastPacket(new MagicSkillUse(_throneSpawns.get(index).getNpc(), _throneSpawns.get(index).getNpc(), 1036, 1, 5500, 1));+				_throneSpawns.get(index).getNpc()._isCTF_throneSpawn = true;++				// spawn flag+				_flagSpawns.set(index, new L2Spawn(tmpl));+				_flagSpawns.get(index).setLoc(_flagsX.get(index), _flagsY.get(index), _flagsZ.get(index), 0);+				_flagSpawns.get(index).setRespawnDelay(1);+				+				SpawnTable.getInstance().addNewSpawn(_flagSpawns.get(index), false);+				+				_flagSpawns.get(index).setRespawnState(true);+				_flagSpawns.get(index).doSpawn(false);+				_flagSpawns.get(index).getNpc().getStatus().setCurrentHp(999999999);+				_flagSpawns.get(index).getNpc().setTitle(team + "'s Flag");+				_flagSpawns.get(index).getNpc()._CTF_FlagTeamName = team;+				_flagSpawns.get(index).getNpc().decayMe();+				_flagSpawns.get(index).getNpc().spawnMe(_flagSpawns.get(index).getNpc().getX(), _flagSpawns.get(index).getNpc().getY(), _flagSpawns.get(index).getNpc().getZ());+				_flagSpawns.get(index).getNpc()._isCTF_Flag = true;+				if (index == (_teams.size() - 1))+					calculateOutSideOfCTF(); // sets event boundaries so players don't run with the flag.+			}+			catch (Exception e)+			{+				_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[spawnAllFlags()]: exception: " + e.getStackTrace());+			}+		}+	}++	public static void processTopTeam()+	{+		_topTeam = null;+		for (String team : _teams)+		{+			if (teamPointsCount(team) == _topScore && _topScore > 0)+				_topTeam = null;+			if (teamPointsCount(team) > _topScore)+			{+				_topTeam = team;+				_topScore = teamPointsCount(team);+			}+		}+		if (_topScore <= 0)+		{+			AnnounceToPlayers(true, _eventName + "(CTF): No flags taken.");+		}+		else+		{+			if (_topTeam == null)+				AnnounceToPlayers(true, _eventName + "(CTF): Maximum flags taken : " + _topScore + " flags! No one won.");+			else+			{+				AnnounceToPlayers(true, _eventName + "(CTF): Team " + _topTeam + " wins the match, with " + _topScore + " flags taken!");+				rewardTeam(_topTeam);+			}+		}+		teleportFinish();+	}++	public static void unspawnAllFlags()+	{+		try+		{+			if ((_throneSpawns == null) || (_flagSpawns == null) || (_teams == null))+				return;+			for (String team : _teams)+			{+				int index = _teams.indexOf(team);+				if (_throneSpawns.get(index) != null)+				{+					_throneSpawns.get(index).getNpc().deleteMe();+					_throneSpawns.get(index).setRespawnState(false);+					SpawnTable.getInstance().deleteSpawn(_throneSpawns.get(index), true);+				}+				if (_flagSpawns.get(index) != null)+				{+					_flagSpawns.get(index).getNpc().deleteMe();+					_flagSpawns.get(index).setRespawnState(false);+					SpawnTable.getInstance().deleteSpawn(_flagSpawns.get(index), true);+				}+			}+			_throneSpawns.clear();+		}+		catch (Throwable t)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[unspawnAllFlags()]: exception: " + t.getStackTrace());+		}+	}++	private static void unspawnFlag(String teamName)+	{+		int index = _teams.indexOf(teamName);++		_flagSpawns.get(index).getNpc().deleteMe();+		_flagSpawns.get(index).setRespawnState(false);+		SpawnTable.getInstance().deleteSpawn(_flagSpawns.get(index), true);+	}++	public static void spawnFlag(String teamName)+	{+		int index = _teams.indexOf(teamName);+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_flagIds.get(index));++		try+		{+			_flagSpawns.set(index, new L2Spawn(tmpl));++			_flagSpawns.get(index).setLoc(_flagsX.get(index), _flagsY.get(index), _flagsZ.get(index), 0);+			_flagSpawns.get(index).setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_flagSpawns.get(index), false);++			_flagSpawns.get(index).setRespawnState(true);+			_flagSpawns.get(index).doSpawn(false);+			_flagSpawns.get(index).getNpc().getStatus().setCurrentHp(999999999);+			_flagSpawns.get(index).getNpc().setTitle(teamName + "'s Flag");+			_flagSpawns.get(index).getNpc()._CTF_FlagTeamName = teamName;+			_flagSpawns.get(index).getNpc()._isCTF_Flag = true;+			_flagSpawns.get(index).getNpc().decayMe();+			_flagSpawns.get(index).getNpc().spawnMe(_flagSpawns.get(index).getNpc().getX(), _flagSpawns.get(index).getNpc().getY(), _flagSpawns.get(index).getNpc().getZ());+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[spawnFlag(" + teamName + ")]: exception: " + e.getStackTrace());+		}+	}++	public static boolean InRangeOfFlag(Player _player, int flagIndex, int offset)+	{+		if (_player.getX() > CTF._flagsX.get(flagIndex) - offset && _player.getX() < CTF._flagsX.get(flagIndex) + offset && _player.getY() > CTF._flagsY.get(flagIndex) - offset && _player.getY() < CTF._flagsY.get(flagIndex) + offset && _player.getZ() > CTF._flagsZ.get(flagIndex) - offset && _player.getZ() < CTF._flagsZ.get(flagIndex) + offset)+			return true;+		return false;+	}++	public static void processInFlagRange(Player _player)+	{+		try+		{+			CheckRestoreFlags();+			for (String team : _teams)+			{+				if (team.equals(_player._teamNameCTF))+				{+					int indexOwn = _teams.indexOf(_player._teamNameCTF);++					// if player is near his team flag holding the enemy flag+					if (InRangeOfFlag(_player, indexOwn, 100) && !_flagsTaken.get(indexOwn) && _player._haveFlagCTF)+					{+						int indexEnemy = _teams.indexOf(_player._teamNameHaveFlagCTF);+						// return enemy flag to place+						_flagsTaken.set(indexEnemy, false);+						spawnFlag(_player._teamNameHaveFlagCTF);+						// remove the flag from this player+						_player.broadcastPacket(new SocialAction(_player, 16),2000); // amazing glow+						_player.broadcastUserInfo();+						_player.broadcastPacket(new SocialAction(_player, 3),2000); // Victory+						_player.broadcastUserInfo();+						removeFlagFromPlayer(_player);+						_teamPointsCount.set(indexOwn, teamPointsCount(team) + 1);+							+						_player.broadcastUserInfo();+						+						AnnounceToPlayers(false, _eventName + "(CTF): " + _player.getName() + " scores for " + _player._teamNameCTF + ".");+					}+				}+				else+				{+					int indexEnemy = _teams.indexOf(team);+					// if the player is near a enemy flag+					if (InRangeOfFlag(_player, indexEnemy, 100) && !_flagsTaken.get(indexEnemy) && !_player._haveFlagCTF && !_player.isDead())+					{+						if (_player.isRiding() || _player.isFlying())+						{+							_player.sendPacket(ActionFailed.STATIC_PACKET);+							break;+						}++						_flagsTaken.set(indexEnemy, true);+						unspawnFlag(team);+						_player._teamNameHaveFlagCTF = team;+						addFlagToPlayer(_player);+						_player.broadcastUserInfo();+						_player._haveFlagCTF = true;+						AnnounceToPlayers(false, _eventName + "(CTF): " + team + " flag taken by " + _player.getName() + "...");+						pointTeamTo(_player, team);+						break;+					}+				}+			}+		}+		catch (Exception e)+		{+			e.printStackTrace();+		}+	}++	public static void pointTeamTo(Player hasFlag, String ourFlag)+	{+		try+		{+			for (Player player : _players)+			{+				if (player != null && player.isOnline())+				{+					if (player._teamNameCTF.equals(ourFlag))+					{+						player.sendMessage(hasFlag.getName() + " took your flag!");+						if (player._haveFlagCTF)+						{+							player.sendMessage("You can not return the flag to headquarters, until your flag is returned to it's place.");+							player.sendPacket(new RadarControl(1, 1, player.getX(), player.getY(), player.getZ()));+						}+						else+						{+							player.sendPacket(new RadarControl(0, 1, hasFlag.getX(), hasFlag.getY(), hasFlag.getZ()));+							L2Radar rdr = new L2Radar(player);+							L2Radar.RadarOnPlayer radar = rdr.new RadarOnPlayer(hasFlag, player);+							ThreadPool.schedule(radar, 10000 + Rnd.get(30000));+						}+					}+				}+			}+		}+		catch (Throwable t)+		{+		}+	}++	public static int teamPointsCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamPointsCount.get(index);+	}++	public static void setTeamPointsCount(String teamName, int teamPointCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamPointsCount.set(index, teamPointCount);+	}++	public static int teamPlayersCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamPlayersCount.get(index);+	}++	public static void setTeamPlayersCount(String teamName, int teamPlayersCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamPlayersCount.set(index, teamPlayersCount);+	}++	public static void setNpcPos(Player activeChar)+	{+		_npcX = activeChar.getX();+		_npcY = activeChar.getY();+		_npcZ = activeChar.getZ();+		_npcHeading = activeChar.getHeading();+	}++	public static void setNpcPos(int x, int y, int z)+	{+		_npcX = x;+		_npcY = y;+		_npcZ = z;+	}++	public static void addTeam(String teamName)+	{+		if (!checkTeamOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[addTeam(" + teamName + ")]: checkTeamOk() = false");+			return;+		}++		if (teamName.equals(" "))+			return;++		_teams.add(teamName);+		_teamPlayersCount.add(0);+		_teamColors.add(0);+		_teamsX.add(0);+		_teamsY.add(0);+		_teamsZ.add(0);+		_teamPointsCount.add(0);+		addOrSet(_teams.indexOf(teamName), null, false, _FlagNPC, 0, 0, 0);+	}++	private static void addOrSet(int listSize, L2Spawn flagSpawn, boolean flagsTaken, int flagId, int flagX, int flagY, int flagZ)+	{+		while (_flagsX.size() <= listSize)+		{+			_flagSpawns.add(null);+			_flagsTaken.add(false);+			_flagIds.add(_FlagNPC);+			_flagsX.add(0);+			_flagsY.add(0);+			_flagsZ.add(0);+		}+		_flagSpawns.set(listSize, flagSpawn);+		_flagsTaken.set(listSize, flagsTaken);+		_flagIds.set(listSize, flagId);+		_flagsX.set(listSize, flagX);+		_flagsY.set(listSize, flagY);+		_flagsZ.set(listSize, flagZ);+	}++	public static boolean checkMaxLevel(int maxlvl)+	{+		if (_minlvl >= maxlvl)+			return false;++		return true;+	}++	public static boolean checkMinLevel(int minlvl)+	{+		if (_maxlvl <= minlvl)+			return false;++		return true;+	}++	/** returns true if participated players is higher or equal then minimum needed players +	 * @param players +	 * @return */+	public static boolean checkMinPlayers(int players)+	{+		if (_minPlayers <= players)+			return true;++		return false;+	}++	/** returns true if max players is higher or equal then participated players +	 * @param players +	 * @return */+	public static boolean checkMaxPlayers(int players)+	{+		if (_maxPlayers > players)+			return true;++		return false;+	}++	public static void removeTeam(String teamName)+	{+		if (!checkTeamOk() || _teams.isEmpty())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[removeTeam(" + teamName + ")]: checkTeamOk() = false");+			return;+		}++		if (teamPlayersCount(teamName) > 0)+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[removeTeam(" + teamName + ")]: teamPlayersCount(teamName) > 0");+			return;+		}++		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsZ.remove(index);+		_teamsY.remove(index);+		_teamsX.remove(index);+		_teamColors.remove(index);+		_teamPointsCount.remove(index);+		_teamPlayersCount.remove(index);+		_teams.remove(index);+		_flagSpawns.remove(index);+		_flagsTaken.remove(index);+		_flagIds.remove(index);+		_flagsX.remove(index);+		_flagsY.remove(index);+		_flagsZ.remove(index);+	}++	public static void setTeamPos(String teamName, Player activeChar)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsX.set(index, activeChar.getX());+		_teamsY.set(index, activeChar.getY());+		_teamsZ.set(index, activeChar.getZ());+	}++	public static void setTeamPos(String teamName, int x, int y, int z)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsX.set(index, x);+		_teamsY.set(index, y);+		_teamsZ.set(index, z);+	}++	public static void setTeamColor(String teamName, int color)+	{+		if (!checkTeamOk())+			return;++		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamColors.set(index, color);+	}++	public static boolean checkTeamOk()+	{+		if (_started || _teleport || _joining)+			return false;++		return true;+	}++	public static void startJoin(Player activeChar)+	{+		if (!startJoinOk())+		{+			activeChar.sendMessage("Event not setted propertly.");+			if (Config.DEBUG)+				_log.fine("CTF Engine[startJoin(" + activeChar.getName() + ")]: startJoinOk() = false");+			return;+		}++		_joining = true;+		spawnEventNpc(activeChar);+		AnnounceToPlayers(true, _eventName + " (CTF)!");+		if (Config.CTF_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Joinable in " + _joiningLocationName + "!");+	}++	public static void startJoin()+	{+		if (!startJoinOk())+		{+			_log.warning(CTF.class.getSimpleName() + ":  Event not setted propertly.");+			if (Config.DEBUG)+				_log.fine("CTF Engine[startJoin(startJoinOk() = false");+			return;+		}++		_joining = true;+		spawnEventNpc();+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Joinable in " + _joiningLocationName + "!");+		if (Config.CTF_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+	}++	public static boolean startAutoJoin()+	{+		if (!startJoinOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[startJoin]: startJoinOk() = false");+			return false;+		}++		_joining = true;+		spawnEventNpc();+		AnnounceToPlayers(true, _eventName + " (CTF)!");+		if (Config.CTF_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Joinable in " + _joiningLocationName + "!");+		return true;+	}++	public static boolean startJoinOk()+	{+		if (_started || _teleport || _joining || _teams.size() < 2 || _eventName.equals("") || _joiningLocationName.equals("") || _eventDesc.equals("") || _npcId == 0 || _npcX == 0 || _npcY == 0 || _npcZ == 0 || _rewardId == 0 || _rewardAmount == 0 || _teamsX.contains(0) || _teamsY.contains(0) || _teamsZ.contains(0))+			return false;+		try+		{+			if (_flagsX.contains(0) || _flagsY.contains(0) || _flagsZ.contains(0) || _flagIds.contains(0))+				return false;+			if (_flagsX.size() < _teams.size() || _flagsY.size() < _teams.size() || _flagsZ.size() < _teams.size() || _flagIds.size() < _teams.size())+				return false;+		}+		catch (ArrayIndexOutOfBoundsException e)+		{+			return false;+		}+		return true;+	}++	private static void spawnEventNpc(Player activeChar)+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);+			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, _npcHeading);+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobCTF = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[spawnEventNpc(" + activeChar.getName() + ")]: exception: " + e.getMessage());+		}+	}++	private static void spawnEventNpc()+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);++			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, _npcHeading);+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobCTF = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[spawnEventNpc(exception: " + e.getMessage());+		}+	}++	public static void teleportStart()+	{+		if (!_joining || _started || _teleport)+			return;++		if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && checkMinPlayers(_playersShuffle.size()))+		{+			removeOfflinePlayers();+			shuffleTeams();+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && !checkMinPlayers(_playersShuffle.size()))+		{+			AnnounceToPlayers(true, "Not enough players for event. Min Requested : " + _minPlayers + ", Participating : " + _playersShuffle.size());+			return;+		}++		_joining = false;+		AnnounceToPlayers(true, _eventName + "(CTF): Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				CTF.sit();+				CTF.spawnAllFlags();+				for (Player player : _players)+				{+					if (player != null)+					{+						if (Config.CTF_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+								Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+									if (e != null)+										e.exit();++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}++						if (Config.CTF_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}+						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameCTF)), _teamsY.get(_teams.indexOf(player._teamNameCTF)), _teamsZ.get(_teams.indexOf(player._teamNameCTF)), 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+	}++	public static boolean teleportAutoStart()+	{+		if (!_joining || _started || _teleport)+			return false;++		if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && checkMinPlayers(_playersShuffle.size()))+		{+			removeOfflinePlayers();+			shuffleTeams();+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && !checkMinPlayers(_playersShuffle.size()))+		{+			AnnounceToPlayers(true, "Not enough players for event. Min Requested : " + _minPlayers + ", Participating : " + _playersShuffle.size());+			return false;+		}++		_joining = false;+		AnnounceToPlayers(false, _eventName + "(CTF): Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				sit();+				spawnAllFlags();++				for (Player player : _players)+				{+					if (player != null)+					{+						if (Config.CTF_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+								Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+									if (e != null)+										e.exit();++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}+						if (Config.CTF_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}++						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameCTF)), _teamsY.get(_teams.indexOf(player._teamNameCTF)), _teamsZ.get(_teams.indexOf(player._teamNameCTF)), 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+		return true;+	}++	public static void startEvent(Player activeChar)+	{+		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[startEvent(" + activeChar.getName() + ")]: startEventOk() = false");+			return;+		}++		_teleport = false;+		sit();+		_started = true;+		StartEvent();+	}++	public static void setJoinTime(int time)+	{+		_joinTime = time;+	}++	public static void setEventTime(int time)+	{+		_eventTime = time;+	}++	public static boolean startAutoEvent()+	{+		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[startEvent]: startEventOk() = false");+			return false;+		}++		_teleport = false;+		sit();+		AnnounceToPlayers(true, _eventName + "(CTF): Started. Go Capture the Flags!");+		_started = true;+		return true;+	}++	public static synchronized void autoEvent()+	{+		if (startAutoJoin())+		{+			if (_joinTime > 0)+				waiter(_joinTime * 60 * 1000); // minutes for join event+			else if (_joinTime <= 0)+			{+				abortEvent();+				return;+			}+			if (teleportAutoStart())+			{+				waiter(1 * 30 * 1000); // 30 seconds wait time until start fight after teleported+				if (startAutoEvent())+				{+					waiter(_eventTime * 60 * 1000); // minutes for event time+					finishEvent();+				}+			}+			else if (!teleportAutoStart())+			{+				abortEvent();+			}+		}+	}++	private static synchronized void waiter(long interval)+	{+		long startWaiterTime = System.currentTimeMillis();+		int seconds = (int) (interval / 1000);++		while (startWaiterTime + interval > System.currentTimeMillis())+		{+			seconds--; // here because we don't want to see two time announce at the same time++			if (_joining || _started || _teleport)+			{+				switch (seconds)+				{+					case 3600: // 1 hour left+						if (_joining)+						{+							AnnounceToPlayers(true, _eventName + "(CTF): Joinable in " + _joiningLocationName + "!");+							AnnounceToPlayers(true, "CTF Event: " + seconds / 60 / 60 + " hour(s) till registration close!");+						}+						else if (_started)+							AnnounceToPlayers(false, "CTF Event: " + seconds / 60 / 60 + " hour(s) till event finish!");++					break;+					case 1800: // 30 minutes left+					case 600: // 10 minutes left+					case 180: // 3 minutes left+					case 120: // 2 minutes left+					case 60: // 1 minute left+						if (_joining)+						{+							removeOfflinePlayers();+							AnnounceToPlayers(true, _eventName + "(CTF): Joinable in " + _joiningLocationName + "!");+							AnnounceToPlayers(true, "CTF Event: " + seconds / 60 + " minute(s) till registration ends!");+						}+						else if (_started)+							AnnounceToPlayers(false, "CTF Event: " + seconds / 60 + " minute(s) till event ends!");++					break;+					case 30: // 30 seconds left+					case 10: // 10 seconds left+					case 3: // 3 seconds left+					case 2: // 2 seconds left+					case 1: // 1 seconds left+						if (_joining)+							AnnounceToPlayers(true, "CTF Event: " + seconds + " second(s) till registration close!");+						else if (_teleport)+							AnnounceToPlayers(false, "CTF Event: " + seconds + " seconds(s) till fight starts!");+						else if (_started)+							AnnounceToPlayers(false, "CTF Event: " + seconds + " second(s) till event ends!");++					break;+				}+			}++			long startOneSecondWaiterStartTime = System.currentTimeMillis();++			// only the try catch with Thread.sleep(1000) give bad countdown on high wait times+			while (startOneSecondWaiterStartTime + 1000 > System.currentTimeMillis())+			{+				try+				{+					Thread.sleep(1);+				}+				catch (InterruptedException ie)+				{+				}+			}+		}+	}++	private static boolean startEventOk()+	{+		if (_joining || !_teleport || _started)+			return false;++		if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+		{+			if (_teamPlayersCount.contains(0))+				return false;+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+		{+			List<Player> playersShuffleTemp = new ArrayList<>();+			int loopCount = 0;++			loopCount = _playersShuffle.size();++			for (int i = 0; i < loopCount; i++)+			{+				if (_playersShuffle != null)+					playersShuffleTemp.add(_playersShuffle.get(i));+			}++			_playersShuffle = playersShuffleTemp;+			playersShuffleTemp.clear();++			// if (_playersShuffle.size() < (_teams.size()*2)){+			// return false;+			// }+		}++		return true;+	}++	public static void shuffleTeams()+	{+		int teamCount = 0, playersCount = 0;++		for (;;)+		{+			if (_playersShuffle.isEmpty())+				break;++			int playerToAddIndex = Rnd.nextInt(_playersShuffle.size());+			Player player = null;+			player = _playersShuffle.get(playerToAddIndex);+			player._originalNameColorCTF = player.getAppearance().getNameColor();+			player._originalKarmaCTF = player.getKarma();++			_players.add(player);+			_players.get(playersCount)._teamNameCTF = _teams.get(teamCount);+			_savePlayers.add(_players.get(playersCount).getName());+			_savePlayerTeams.add(_teams.get(teamCount));+			playersCount++;++			if (teamCount == _teams.size() - 1)+				teamCount = 0;+			else+				teamCount++;++			_playersShuffle.remove(playerToAddIndex);+		}+	}++	public static void setUserData()+	{+		for (Player player : _players)+		{+			player.getAppearance().setNameColor(_teamColors.get(_teams.indexOf(player._teamNameCTF)));+			player.setKarma(0);+			player.broadcastUserInfo();+		}+	}++	public static void finishEvent()+	{+		if (!finishEventOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[finishEvent]: finishEventOk() = false");+			return;+		}++		_started = false;+		unspawnEventNpc();+		unspawnAllFlags();+		processTopTeam();++		if (_topScore != 0)+			playKneelAnimation(_topTeam);++		if (Config.CTF_ANNOUNCE_TEAM_STATS)+		{+			AnnounceToPlayers(true, _eventName + " Team Statistics:");+			for (String team : _teams)+			{+				int _flags_ = teamFlagCount(team);+				AnnounceToPlayers(true, "Team: " + team + " - Flags taken: " + _flags_);+			}+		}++		teleportFinish();+	}++	// show losers and winners animations+	public static void playKneelAnimation(String teamName)+	{+		for (Player player : _players)+		{+			if (player != null && player.isOnline() && player._inEventCTF == true)+			{+				if (!player._teamNameCTF.equals(teamName))+				{+					player.broadcastPacket(new SocialAction(player, 7),2000);+				}+				else if (player._teamNameCTF.equals(teamName))+				{+					player.broadcastPacket(new SocialAction(player, 3),2000);+				}+			}+		}+	}++	private static boolean finishEventOk()+	{+		if (!_started)+			return false;++		return true;+	}++	public static void rewardTeam(String teamName)+	{+		for (Player player : _players)+		{+			if (player != null)+			{+				if (player._teamNameCTF.equals(teamName))+				{+					player.addItem("CTF Event: " + _eventName, _rewardId, _rewardAmount, player, true);++					NpcHtmlMessage nhm = new NpcHtmlMessage(5);+					StringBuilder replyMSG = new StringBuilder();++					replyMSG.append("<html><body>Your team wins the event. Look in your inventory for the reward.</body></html>");++					nhm.setHtml(replyMSG.toString());+					player.sendPacket(nhm);++					// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+					player.sendPacket(ActionFailed.STATIC_PACKET);+				}+			}+		}+	}++	public static void abortEvent()+	{+		if (!_joining && !_teleport && !_started)+			return;+		if (_joining && !_teleport && !_started)+		{+			unspawnEventNpc();+			cleanCTF();+			_joining = false;+			AnnounceToPlayers(true, _eventName + "(CTF): Match aborted!");+			return;+		}+		_joining = false;+		_teleport = false;+		_started = false;+		unspawnEventNpc();+		unspawnAllFlags();+		AnnounceToPlayers(true, _eventName + "(CTF): Match aborted!");+		teleportFinish();+	}++	public static void sit()+	{+		if (_sitForced)+			_sitForced = false;+		else+			_sitForced = true;++		for (Player player : _players)+		{+			if (player != null)+			{+				if (_sitForced)+				{+					player.stopMove(null);+					player.abortAttack();+					player.abortCast();++					if (!player.isSitting())+						player.sitDown();+				}+				else+				{+					if (player.isSitting())+						player.standUp();+				}+			}+		}+	}++	public static void dumpData()+	{+		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  ");++		if (!_joining && !_teleport && !_started)+		{+			_log.warning(CTF.class.getSimpleName() + ":  <<---------------------------------->>");+			_log.warning(CTF.class.getSimpleName() + ":  >> CTF Engine infos dump (INACTIVE) <<");+			_log.warning(CTF.class.getSimpleName() + ":  <<--^----^^-----^----^^------^^----->>");+		}+		else if (_joining && !_teleport && !_started)+		{+			_log.warning(CTF.class.getSimpleName() + ":  <<--------------------------------->>");+			_log.warning(CTF.class.getSimpleName() + ":  >> CTF Engine infos dump (JOINING) <<");+			_log.warning(CTF.class.getSimpleName() + ":  <<--^----^^-----^----^^------^----->>");+		}+		else if (!_joining && _teleport && !_started)+		{+			_log.warning(CTF.class.getSimpleName() + ":  <<---------------------------------->>");+			_log.warning(CTF.class.getSimpleName() + ":  >> CTF Engine infos dump (TELEPORT) <<");+			_log.warning(CTF.class.getSimpleName() + ":  <<--^----^^-----^----^^------^^----->>");+		}+		else if (!_joining && !_teleport && _started)+		{+			_log.warning(CTF.class.getSimpleName() + ":  <<--------------------------------->>");+			_log.warning(CTF.class.getSimpleName() + ":  >> CTF Engine infos dump (STARTED) <<");+			_log.warning(CTF.class.getSimpleName() + ":  <<--^----^^-----^----^^------^----->>");+		}++		_log.warning(CTF.class.getSimpleName() + ":  Name: " + _eventName);+		_log.warning(CTF.class.getSimpleName() + ":  Desc: " + _eventDesc);+		_log.warning(CTF.class.getSimpleName() + ":  Join location: " + _joiningLocationName);+		_log.warning(CTF.class.getSimpleName() + ":  Min lvl: " + _minlvl);+		_log.warning(CTF.class.getSimpleName() + ":  Max lvl: " + _maxlvl);+		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  ##########################");+		_log.warning(CTF.class.getSimpleName() + ":  # _teams(Vector<String>) #");+		_log.warning(CTF.class.getSimpleName() + ":  ##########################");++		for (String team : _teams)+			_log.warning(CTF.class.getSimpleName() + ": " + team + " Flags Taken :" + _teamPointsCount.get(_teams.indexOf(team)));++		if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+		{+			_log.warning(CTF.class.getSimpleName() + ":  ");+			_log.warning(CTF.class.getSimpleName() + ":  #########################################");+			_log.warning(CTF.class.getSimpleName() + ":  # _playersShuffle(Vector<Player>) #");+			_log.warning(CTF.class.getSimpleName() + ":  #########################################");++			for (Player player : _playersShuffle)+			{+				if (player != null)+					_log.warning(CTF.class.getSimpleName() + ":  Name: " + player.getName());+			}+		}++		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  ##################################");+		_log.warning(CTF.class.getSimpleName() + ":  # _players(Vector<Player>) #");+		_log.warning(CTF.class.getSimpleName() + ":  ##################################");++		for (Player player : _players)+		{+			if (player != null)+				_log.warning(CTF.class.getSimpleName() + ":  Name: " + player.getName() + "   Team: " + player._teamNameCTF + "  Flags :" + player._countCTFflags);+		}++		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  #####################################################################");+		_log.warning(CTF.class.getSimpleName() + ":  # _savePlayers(Vector<String>) and _savePlayerTeams(Vector<String>) #");+		_log.warning(CTF.class.getSimpleName() + ":  #####################################################################");++		for (String player : _savePlayers)+			_log.warning(CTF.class.getSimpleName() + ":  Name: " + player + "	Team: " + _savePlayerTeams.get(_savePlayers.indexOf(player)));++		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  **********==CTF==************");+		_log.warning(CTF.class.getSimpleName() + ":  CTF._teamPointsCount:" + _teamPointsCount.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagIds:" + _flagIds.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagSpawns:" + _flagSpawns.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._throneSpawns:" + _throneSpawns.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagsTaken:" + _flagsTaken.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagsX:" + _flagsX.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagsY:" + _flagsY.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagsZ:" + _flagsZ.toString());+		_log.warning(CTF.class.getSimpleName() + ":  ************EOF**************");+		_log.warning(CTF.class.getSimpleName() + ":  ");+	}++	public static void loadData()+	{+		_eventName = new String();+		_eventDesc = new String();+		_topTeam = new String();+		_joiningLocationName = new String();+		_teams = new ArrayList<>();+		_savePlayers = new ArrayList<>();+		_savePlayerTeams = new ArrayList<>();+		_players = new ArrayList<>();+		_playersShuffle = new ArrayList<>();+		_teamPlayersCount = new ArrayList<>();+		_teamPointsCount = new ArrayList<>();+		_teamColors = new ArrayList<>();+		_teamsX = new ArrayList<>();+		_teamsY = new ArrayList<>();+		_teamsZ = new ArrayList<>();++		_throneSpawns = new ArrayList<>();+		_flagSpawns = new ArrayList<>();+		_flagsTaken = new ArrayList<>();+		_flagIds = new ArrayList<>();+		_flagsX = new ArrayList<>();+		_flagsY = new ArrayList<>();+		_flagsZ = new ArrayList<>();++		_joining = false;+		_teleport = false;+		_started = false;+		_sitForced = false;+		_npcId = 0;+		_npcX = 0;+		_npcY = 0;+		_npcZ = 0;+		_npcHeading = 0;+		_rewardId = 0;+		_rewardAmount = 0;+		_topScore = 0;+		_minlvl = 0;+		_maxlvl = 0;+		_joinTime = 0;+		_eventTime = 0;+		_minPlayers = 0;+		_maxPlayers = 0;++		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;+			ResultSet rs;++			statement = con.prepareStatement("SELECT * FROM ctf");+			rs = statement.executeQuery();++			int teams = 0;++			while (rs.next())+			{+				_eventName = rs.getString("eventName");+				_eventDesc = rs.getString("eventDesc");+				_joiningLocationName = rs.getString("joiningLocation");+				_minlvl = rs.getInt("minlvl");+				_maxlvl = rs.getInt("maxlvl");+				_npcId = rs.getInt("npcId");+				_npcX = rs.getInt("npcX");+				_npcY = rs.getInt("npcY");+				_npcZ = rs.getInt("npcZ");+				_npcHeading = rs.getInt("npcHeading");+				_rewardId = rs.getInt("rewardId");+				_rewardAmount = rs.getInt("rewardAmount");+				teams = rs.getInt("teamsCount");+				_joinTime = rs.getInt("joinTime");+				_eventTime = rs.getInt("eventTime");+				_minPlayers = rs.getInt("minPlayers");+				_maxPlayers = rs.getInt("maxPlayers");+			}+			rs.close();+			statement.close();++			int index = -1;+			if (teams > 0)+				index = 0;+			while (index < teams && index > -1)+			{+				statement = con.prepareStatement("SELECT * FROM ctf_teams WHERE teamId=?");+				statement.setInt(1, index);+				rs = statement.executeQuery();+				while (rs.next())+				{+					_teams.add(rs.getString("teamName"));+					_teamPlayersCount.add(0);+					_teamPointsCount.add(0);+					_teamColors.add(0);+					_teamsX.add(0);+					_teamsY.add(0);+					_teamsZ.add(0);+					_teamsX.set(index, rs.getInt("teamX"));+					_teamsY.set(index, rs.getInt("teamY"));+					_teamsZ.set(index, rs.getInt("teamZ"));+					_teamColors.set(index, rs.getInt("teamColor"));+					_flagsX.add(0);+					_flagsY.add(0);+					_flagsZ.add(0);+					_flagsX.set(index, rs.getInt("flagX"));+					_flagsY.set(index, rs.getInt("flagY"));+					_flagsZ.set(index, rs.getInt("flagZ"));+					_flagSpawns.add(null);+					_flagIds.add(_FlagNPC);+					_flagsTaken.add(false);++				}+				index++;+				rs.close();+				statement.close();+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  Exception: CTF.loadData(): " + e.getMessage());+		}+	}++	public static void saveData()+	{+		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;++			statement = con.prepareStatement("DELETE FROM ctf");+			statement.execute();+			statement.close();++			statement = con.prepareStatement("INSERT INTO ctf (eventName, eventDesc, joiningLocation, minlvl, maxlvl, npcId, npcX, npcY, npcZ, npcHeading, rewardId, rewardAmount, teamsCount, joinTime, eventTime, minPlayers, maxPlayers) VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)");+			statement.setString(1, _eventName);+			statement.setString(2, _eventDesc);+			statement.setString(3, _joiningLocationName);+			statement.setInt(4, _minlvl);+			statement.setInt(5, _maxlvl);+			statement.setInt(6, _npcId);+			statement.setInt(7, _npcX);+			statement.setInt(8, _npcY);+			statement.setInt(9, _npcZ);+			statement.setInt(10, _npcHeading);+			statement.setInt(11, _rewardId);+			statement.setInt(12, _rewardAmount);+			statement.setInt(13, _teams.size());+			statement.setInt(14, _joinTime);+			statement.setInt(15, _eventTime);+			statement.setInt(16, _minPlayers);+			statement.setInt(17, _maxPlayers);+			statement.execute();+			statement.close();++			statement = con.prepareStatement("DELETE FROM ctf_teams");+			statement.execute();+			statement.close();++			for (String teamName : _teams)+			{+				int index = _teams.indexOf(teamName);++				if (index == -1)+					return;+				statement = con.prepareStatement("INSERT INTO ctf_teams (teamId ,teamName, teamX, teamY, teamZ, teamColor, flagX, flagY, flagZ) VALUES (?,?,?,?,?,?,?,?,?)");+				statement.setInt(1, index);+				statement.setString(2, teamName);+				statement.setInt(3, _teamsX.get(index));+				statement.setInt(4, _teamsY.get(index));+				statement.setInt(5, _teamsZ.get(index));+				statement.setInt(6, _teamColors.get(index));+				statement.setInt(7, _flagsX.get(index));+				statement.setInt(8, _flagsY.get(index));+				statement.setInt(9, _flagsZ.get(index));+				statement.execute();+				statement.close();+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  Exception: CTF.saveData(): " + e.getMessage());+		}+	}++	public static void showEventHtml(Player eventPlayer, String objectId)+	{+		try+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+			StringBuilder replyMSG = new StringBuilder();++			replyMSG.append("<html><body>");+			replyMSG.append("CTF Match<br><br><br>");+			replyMSG.append("Current event...<br>");+			replyMSG.append("   ... description:&nbsp;<font color=\"00FF00\">" + _eventDesc + "</font><br>");+			if (Config.CTF_ANNOUNCE_REWARD)+				replyMSG.append("   ... reward: (" + _rewardAmount + ") " + ItemTable.getInstance().getTemplate(_rewardId).getName() + "<br>");++			if (!_started && !_joining)+				replyMSG.append("<center>Wait till the admin/gm start the participation.</center>");+			else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && !checkMaxPlayers(_playersShuffle.size()))+			{+				if (!CTF._started)+				{+					replyMSG.append("<font color=\"FFFF00\">The event has reached its maximum capacity.</font><br>Keep checking, someone may crit and you can steal their spot.");+				}+			}+			else if (eventPlayer.isCursedWeaponEquipped() && !Config.CTF_JOIN_CURSED)+			{+				replyMSG.append("<font color=\"FFFF00\">You can't participate in this event with a cursed Weapon.</font><br>");+			}+			else if (!_started && _joining && eventPlayer.getLevel() >= _minlvl && eventPlayer.getLevel() <= _maxlvl)+			{+				if (_players.contains(eventPlayer) || checkShufflePlayers(eventPlayer))+				{+					if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+						replyMSG.append("You are already participating in team <font color=\"LEVEL\">" + eventPlayer._teamNameCTF + "</font><br><br>");+					else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+						replyMSG.append("You are already participating!<br><br>");++					replyMSG.append("<table border=\"0\"><tr>");+					replyMSG.append("<td width=\"200\">Wait till event start or</td>");+					replyMSG.append("<td width=\"60\"><center><button value=\"remove\" action=\"bypass -h npc_" + objectId + "_ctf_player_leave\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></center></td>");+					replyMSG.append("<td width=\"100\">your participation!</td>");+					replyMSG.append("</tr></table>");+				}+				else+				{+					replyMSG.append("<td width=\"200\">Your level : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Min level : <font color=\"00FF00\">" + _minlvl + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Max level : <font color=\"00FF00\">" + _maxlvl + "</font></td><br><br>");++					if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+					{+						replyMSG.append("<center><table border=\"0\">");++						for (String team : _teams)+						{+							replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font>&nbsp;(" + teamPlayersCount(team) + " joined)</td>");+							replyMSG.append("<td width=\"60\"><button value=\"Join\" action=\"bypass -h npc_" + objectId + "_ctf_player_join " + team + "\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td></tr>");+						}++						replyMSG.append("</table></center>");+					}+					else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+					{+						replyMSG.append("<center><table border=\"0\">");++						for (String team : _teams)+							replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font></td>");++						replyMSG.append("</table></center><br>");++						replyMSG.append("<button value=\"Join\" action=\"bypass -h npc_" + objectId + "_ctf_player_join eventShuffle\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\">");+						replyMSG.append("Teams will be randomly generated!");+					}+				}+			}+			else if (_started && !_joining)+				replyMSG.append("<center>CTF match is in progress.</center>");+			else if (eventPlayer.getLevel() < _minlvl || eventPlayer.getLevel() > _maxlvl)+			{+				replyMSG.append("Your lvl : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font><br>");+				replyMSG.append("Min level : <font color=\"00FF00\">" + _minlvl + "</font><br>");+				replyMSG.append("Max level : <font color=\"00FF00\">" + _maxlvl + "</font><br><br>");+				replyMSG.append("<font color=\"FFFF00\">You can't participatein this event.</font><br>");+			}+			// Show how many players joined & how many are still needed to join+			replyMSG.append("<br>There are " + _playersShuffle.size() + " player(s) participating in this event.<br>");+			if (_joining)+			{+				if (_playersShuffle.size() < _minPlayers)+				{+					int playersNeeded = _minPlayers - _playersShuffle.size();+					replyMSG.append("The event will not start unless " + playersNeeded + " more player(s) joins!");+				}+			}++			replyMSG.append("</body></html>");+			adminReply.setHtml(replyMSG.toString());+			eventPlayer.sendPacket(adminReply);++			// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+			eventPlayer.sendPacket(ActionFailed.STATIC_PACKET);+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[showEventHtlm(" + eventPlayer.getName() + ", " + objectId + ")]: exception" + e.getMessage());+		}+	}++	public static void addPlayer(Player player, String teamName)+	{+		if (!addPlayerOk(teamName, player))+			return;++		if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+		{+			player._teamNameCTF = teamName;+			_players.add(player);+			setTeamPlayersCount(teamName, teamPlayersCount(teamName) + 1);+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+			_playersShuffle.add(player);++		player._inEventCTF = true;+		player._countCTFflags = 0;+	}++	public static synchronized void removeOfflinePlayers()+	{+		try+		{+			if (_playersShuffle == null)+				return;+			else if (_playersShuffle.isEmpty())+				return;+			else if (_playersShuffle.size() > 0)+			{+				for (Player player : _playersShuffle)+				{+					if (player == null)+						_playersShuffle.remove(player);+					else if (player.isOnline() || player.isInJail())+						removePlayer(player);+					if (_playersShuffle.size() == 0 || _playersShuffle.isEmpty())+						break;+				}+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine exception: " + e.getMessage());+			return;+		}+	}++	public static boolean checkShufflePlayers(Player eventPlayer)+	{+		try+		{+			for (Player player : _playersShuffle)+			{+				if (player == null || player.isOnline())+				{+					_playersShuffle.remove(player);+					eventPlayer._inEventCTF = false;+					continue;+				}+				else if (player.getObjectId() == eventPlayer.getObjectId())+				{+					eventPlayer._inEventCTF = true;+					eventPlayer._countCTFflags = 0;+					return true;+				}+				// this 1 is in case player got new object id after DC or reconnect+				else if (player.getName().equals(eventPlayer.getName()))+				{+					_playersShuffle.remove(player);+					_playersShuffle.add(eventPlayer);+					eventPlayer._inEventCTF = true;+					eventPlayer._countCTFflags = 0;+					return true;+				}+			}+		}+		catch (Exception e)+		{+		}+		return false;+	}++	public static boolean addPlayerOk(String teamName, Player eventPlayer)+	{+		try+		{+			if (checkShufflePlayers(eventPlayer) || eventPlayer._inEventCTF)+			{+				eventPlayer.sendMessage("You are already participating in the event!");+				return false;+			}++			for (Player player : _players)+			{+				if (player.getObjectId() == eventPlayer.getObjectId())+				{+					eventPlayer.sendMessage("You are already participating in the event!");+					return false;+				}+				else if (player.getName() == eventPlayer.getName())+				{+					eventPlayer.sendMessage("You are already participating in the event!");+					return false;+				}+			}+			if (_players.contains(eventPlayer))+			{+				eventPlayer.sendMessage("You are already participating in the event!");+				return false;+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Siege Engine exception: " + e.getMessage());+		}++		if (Config.CTF_EVEN_TEAMS.equals("NO"))+			return true;+		else if (Config.CTF_EVEN_TEAMS.equals("BALANCE"))+		{+			boolean allTeamsEqual = true;+			int countBefore = -1;++			for (int playersCount : _teamPlayersCount)+			{+				if (countBefore == -1)+					countBefore = playersCount;++				if (countBefore != playersCount)+				{+					allTeamsEqual = false;+					break;+				}++				countBefore = playersCount;+			}++			if (allTeamsEqual)+				return true;++			countBefore = Integer.MAX_VALUE;++			for (int teamPlayerCount : _teamPlayersCount)+			{+				if (teamPlayerCount < countBefore)+					countBefore = teamPlayerCount;+			}++			List<String> joinableTeams = new ArrayList<>();++			for (String team : _teams)+			{+				if (teamPlayersCount(team) == countBefore)+					joinableTeams.add(team);+			}++			if (joinableTeams.contains(teamName))+				return true;+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+			return true;++		eventPlayer.sendMessage("Too many players in team \"" + teamName + "\"");+		return false;+	}++	public static synchronized void addDisconnectedPlayer(Player player)+	{+		/*+		 * !!! CAUTION !!!+		 * Do NOT fix multiple object Ids on this event or you will ruin the flag reposition check!!!+		 * All Multiple object Ids will be collected by the Garbage Collector, after the event ends, memory sweep is made!!!+		 */++		if ((Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && (_teleport || _started)) || (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE") && (_teleport || _started)))+		{+			if (Config.CTF_ON_START_REMOVE_ALL_EFFECTS)+			{+				for (L2Effect e : player.getAllEffects())+				{+					if (e != null)+						e.exit();+				}+			}++			player._teamNameCTF = _savePlayerTeams.get(_savePlayers.indexOf(player.getName()));+			for (Player p : _players)+			{+				if (p == null)+				{+					continue;+				}+				// check by name in case player got new objectId+				else if (p.getName().equals(player.getName()))+				{+					player._originalNameColorCTF = player.getAppearance().getNameColor();+					player._originalKarmaCTF = player.getKarma();+					player._inEventCTF = true;+					player._countCTFflags = p._countCTFflags;+					_players.remove(p); // removing old object id from vector+					_players.add(player); // adding new objectId to vector+					break;+				}+			}+			player.getAppearance().setNameColor(_teamColors.get(_teams.indexOf(player._teamNameCTF)));+			player.setKarma(0);+			player.broadcastUserInfo();+			player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameCTF)), _teamsY.get(_teams.indexOf(player._teamNameCTF)), _teamsZ.get(_teams.indexOf(player._teamNameCTF)), 0);+			Started(player);+			CheckRestoreFlags();+		}+	}++	public static void removePlayer(Player player)+	{+		if (player._inEventCTF)+		{+			if (!_joining)+			{+				player.getAppearance().setNameColor(player._originalNameColorCTF);+				player.setKarma(player._originalKarmaCTF);+				player.broadcastUserInfo();+			}+			player._teamNameCTF = new String();+			player._countCTFflags = 0;+			player._inEventCTF = false;++			if ((Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE")) && _players.contains(player))+			{+				setTeamPlayersCount(player._teamNameCTF, teamPlayersCount(player._teamNameCTF) - 1);+				_players.remove(player);+			}+			else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && (!_playersShuffle.isEmpty() && _playersShuffle.contains(player)))+				_playersShuffle.remove(player);+		}+	}++	public static void cleanCTF()+	{+		_log.warning(CTF.class.getSimpleName() + ":  CTF : Cleaning players.");+		for (Player player : _players)+		{+			if (player != null)+			{+				if (player._haveFlagCTF)+					removeFlagFromPlayer(player);+				else+					player.getInventory().destroyItemByItemId("", CTF._FLAG_IN_HAND_ITEM_ID, 1, player, null);+				player._haveFlagCTF = false;+				removePlayer(player);+				if (_savePlayers.contains(player.getName()))+					_savePlayers.remove(player.getName());+				player._inEventCTF = false;+			}+		}+		if (_playersShuffle != null && !_playersShuffle.isEmpty())+		{+			for (Player player : _playersShuffle)+			{+				if (player != null)+					player._inEventCTF = false;+			}+		}+		_log.warning(CTF.class.getSimpleName() + ":  CTF : Cleaning teams and flags.");+		for (String team : _teams)+		{+			int index = _teams.indexOf(team);+			_teamPointsCount.set(index, 0);+			_flagSpawns.set(index, null);+			_flagsTaken.set(index, false);+			_teamPlayersCount.set(index, 0);+			_teamPointsCount.set(index, 0);+		}+		_topScore = 0;+		_topTeam = new String();+		_players.clear();+		_playersShuffle.clear();+		_savePlayers.clear();+		_savePlayerTeams.clear();+		_teamPointsCount.clear();+		_flagSpawns.clear();+		_flagsTaken.clear();+		_teamPlayersCount.clear();+		_log.warning(CTF.class.getSimpleName() + ":  Cleaning CTF done.");+		_log.warning(CTF.class.getSimpleName() + ":  Loading new data from MySql");+		loadData();+	}++	public static void unspawnEventNpc()+	{+		if (_npcSpawn == null)+			return;++		_npcSpawn.getNpc().deleteMe();+		_npcSpawn.setRespawnState(false);+		SpawnTable.getInstance().deleteSpawn(_npcSpawn, true);+	}++	public static void teleportFinish()+	{+		AnnounceToPlayers(false, _eventName + "(CTF): Teleport back to participation NPC in 20 seconds!");+		ThreadPool.schedule(new Runnable()+		{+			@SuppressWarnings("synthetic-access")+			@Override+			public void run()+			{+				for (Player player : _players)+				{+					if (player != null)+					{+						if (player.isOnline())+							player.teleToLocation(_npcX, _npcY, _npcZ, 0);+						else+						{+							try (Connection con = L2DatabaseFactory.getInstance().getConnection())+							{+								PreparedStatement statement = con.prepareStatement("UPDATE characters SET x=?, y=?, z=? WHERE char_name=?");+								statement.setInt(1, _npcX);+								statement.setInt(2, _npcY);+								statement.setInt(3, _npcZ);+								statement.setString(4, player.getName());+								statement.execute();+								statement.close();+							}+							catch (SQLException se)+							{+								_log.warning(CTF.class.getSimpleName() + ":  CTF Engine exception: " + se.getMessage());+							}+						}+					}+				}+				cleanCTF();+			}+		}, 20000);+	}++	public static int teamFlagCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamPointsCount.get(index);+	}++	public static void setTeamFlagCount(String teamName, int teamFlagCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamPointsCount.set(index, teamFlagCount);+	}++	/**+	 * Used to calculate the event CTF area, so that players don't run off with the flag.+	 * Essential, since a player may take the flag just so other teams can't score points.+	 * This function is Only called upon ONE time on BEGINING OF EACH EVENT right after we spawn the flags.+	 */+	private static void calculateOutSideOfCTF()+	{+		if ((_teams == null) || (_flagSpawns == null) || (_teamsX == null) || (_teamsY == null) || (_teamsZ == null))+			return;++		int division = _teams.size() * 2, pos = 0;+		int[] locX = new int[division], locY = new int[division], locZ = new int[division];+		// Get all coordinates in order to create a polygon:+		for (L2Spawn flag : _flagSpawns)+		{+			flag.setLoc(locX[pos], locY[pos], locZ[pos], pos);+			+			pos++;+			if (pos > division / 2)+				break;+		}++		for (int x = 0; x < _teams.size(); x++)+		{+			locX[pos] = _teamsX.get(x);+			locY[pos] = _teamsY.get(x);+			locZ[pos] = _teamsZ.get(x);+			pos++;+			if (pos > division)+				break;+		}++		// find the polygon center, note that it's not the mathematical center of the polygon,+		// rather than a point which centers all coordinates:+		int centerX = 0, centerY = 0, centerZ = 0;+		for (int x = 0; x < pos; x++)+		{+			centerX += (locX[x] / division);+			centerY += (locY[x] / division);+			centerZ += (locZ[x] / division);+		}++		// now let's find the farthest distance from the "center" to the egg shaped sphere+		// surrounding the polygon, size x1.5 (for maximum logical area to wander...):+		int maxX = 0, maxY = 0, maxZ = 0;+		for (int x = 0; x < pos; x++)+		{+			if (maxX < 2 * Math.abs(centerX - locX[x]))+				maxX = (2 * Math.abs(centerX - locX[x]));+			if (maxY < 2 * Math.abs(centerY - locY[x]))+				maxY = (2 * Math.abs(centerY - locY[x]));+			if (maxZ < 2 * Math.abs(centerZ - locZ[x]))+				maxZ = (2 * Math.abs(centerZ - locZ[x]));+		}++		// centerX,centerY,centerZ are the coordinates of the "event center".+		// so let's save those coordinates to check on the players:+		eventCenterX = centerX;+		eventCenterY = centerY;+		eventCenterZ = centerZ;+		eventOffset = maxX;+		if (eventOffset < maxY)+			eventOffset = maxY;+		if (eventOffset < maxZ)+			eventOffset = maxZ;+	}++	public static boolean isOutsideCTFArea(Player _player)+	{+		if ((_player == null) || (_player.isOnline()))+			return true;+		if (!(_player.getX() > eventCenterX - eventOffset && _player.getX() < eventCenterX + eventOffset && _player.getY() > eventCenterY - eventOffset && _player.getY() < eventCenterY + eventOffset && _player.getZ() > eventCenterZ - eventOffset && _player.getZ() < eventCenterZ + eventOffset))+			return true;+		return false;+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/model/entity/engine/DM.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/DM.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/DM.java	(working copy)@@ -0,0 +1,700 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++import java.sql.Connection;+import java.sql.PreparedStatement;+import java.sql.ResultSet;+import java.util.ArrayList;+import java.util.List;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.L2DatabaseFactory;+import net.sf.l2j.commons.concurrent.ThreadPool;+import net.sf.l2j.gameserver.datatables.NpcTable;+import net.sf.l2j.gameserver.datatables.SpawnTable;+import net.sf.l2j.gameserver.model.L2Effect;+import net.sf.l2j.gameserver.model.L2Spawn;+import net.sf.l2j.gameserver.model.actor.Summon;+import net.sf.l2j.gameserver.model.actor.instance.Pet;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.actor.template.NpcTemplate;+import net.sf.l2j.gameserver.model.group.Party;+import net.sf.l2j.gameserver.model.group.Party.MessageType;+import net.sf.l2j.gameserver.network.serverpackets.ActionFailed;+import net.sf.l2j.gameserver.network.serverpackets.MagicSkillUse;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.network.serverpackets.StatusUpdate;+import net.sf.l2j.gameserver.util.Broadcast;++/**+ * @author SqueezeD Edited By TheEnd+ */+public class DM+{+	private final static Logger _log = Logger.getLogger(DM.class.getName());+	public static String _eventName = new String(), _eventDesc = new String(), _joiningLocationName = new String();+	public static List<String> _savePlayers = new ArrayList<>();+	public static List<Player> _players = new ArrayList<>();+	public static boolean _joining = false, _teleport = false, _started = false, _sitForced = false;+	public static L2Spawn _npcSpawn;+	public static Player _topPlayer;+	public static int _npcId = 0, _npcX = 0, _npcY = 0, _npcZ = 0, _rewardId = 0, _rewardAmount = 0, _topKills = 0,+			_minlvl = 0, _maxlvl = 0, _playerColors = 0, _playerX = 0, _playerY = 0, _playerZ = 0;++	public static void setNpcPos(Player activeChar)+	{+		_npcX = activeChar.getX();+		_npcY = activeChar.getY();+		_npcZ = activeChar.getZ();+	}++	public static boolean checkMaxLevel(int maxlvl)+	{+		if (_minlvl >= maxlvl)+			return false;++		return true;+	}++	public static boolean checkMinLevel(int minlvl)+	{+		if (_maxlvl <= minlvl)+			return false;++		return true;+	}++	public static void setPlayersPos(Player activeChar)+	{+		_playerX = activeChar.getX();+		_playerY = activeChar.getY();+		_playerZ = activeChar.getZ();+	}++	public static boolean checkPlayerOk()+	{+		if (_started || _teleport || _joining)+			return false;++		return true;+	}++	public static void startJoin(Player activeChar)+	{+		if (!startJoinOk())+		{+			if (!Config.DEBUG)+				_log.fine("DM Engine[startJoin(" + activeChar.getName() + ")]: startJoinOk() = false");+			return;+		}++		_joining = true;+		spawnEventNpc(activeChar);+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Joinable in " + _joiningLocationName + "!");+	}++	private static boolean startJoinOk()+	{+		if (_started || _teleport || _joining || _eventName.equals("") || _joiningLocationName.equals("") || _eventDesc.equals("") || _npcId == 0 || _npcX == 0 || _npcY == 0 || _npcZ == 0 || _rewardId == 0 || _rewardAmount == 0 || _playerX == 0 || _playerY == 0 || _playerZ == 0)+			return false;++		return true;+	}++	private static void spawnEventNpc(Player activeChar)+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);+			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, activeChar.getHeading());+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobDM = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(DM.class.getSimpleName() + ":  DM Engine[spawnEventNpc(" + activeChar.getName() + ")]: exception: " + e.getMessage());+		}+	}++	public static void teleportStart()+	{+		if (!_joining || _started || _teleport)+			return;++		_joining = false;+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				DM.sit();++				for (Player player : DM._players)+				{+					if (player != null)+					{+						if (Config.DM_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+							    Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+									e.exit();++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}++						if (Config.DM_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}+						player.teleToLocation(_playerX, _playerY, _playerZ, 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+	}++	public static void startEvent(Player activeChar)+	{+		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.fine("DM Engine[startEvent(" + activeChar.getName() + ")]: startEventOk() = false");+			return;+		}++		_teleport = false;+		sit();+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Started. Go to kill your enemies!");+		_started = true;+	}++	private static boolean startEventOk()+	{+		if (_joining || !_teleport || _started)+			return false;++		return true;+	}++	public static void setUserData()+	{+		for (Player player : _players)+		{+			player._originalNameColorDM = player.getAppearance().getNameColor();+			player._originalKarmaDM = player.getKarma();+			player._inEventDM = true;+			player._countDMkills = 0;+			player.getAppearance().setNameColor(_playerColors);+			player.setKarma(0);+			player.broadcastUserInfo();+		}+	}++	public static void removeUserData()+	{+		for (Player player : _players)+		{+			player.getAppearance().setNameColor(player._originalNameColorDM);+			player.setKarma(player._originalKarmaDM);+			player._inEventDM = false;+			player._countDMkills = 0;+			player.broadcastUserInfo();+		}+	}++	public static void finishEvent(Player activeChar)+	{+		if (!finishEventOk())+		{+			if (Config.DEBUG)+				_log.fine("DM Engine[finishEvent(" + activeChar.getName() + ")]: finishEventOk() = false");+			return;+		}++		_started = false;+		unspawnEventNpc();+		processTopPlayer();++		if (_topKills == 0)+			Broadcast.announceToOnlinePlayers(_eventName + "(DM): No players win the match(nobody killed).");+		else+		{+			Broadcast.announceToOnlinePlayers(_eventName + "(DM): " + _topPlayer.getName() + " wins the match! " + _topKills + " kills.");+			rewardPlayer(activeChar);+		}++		teleportFinish();+	}++	private static boolean finishEventOk()+	{+		if (!_started)+			return false;++		return true;+	}++	public static void processTopPlayer()+	{+		for (Player player : _players)+		{+			if (player._countDMkills > _topKills)+			{+				_topPlayer = player;+				_topKills = player._countDMkills;+			}+		}+	}++	/**+	 * @param activeChar+	 */+	public static void rewardPlayer(Player activeChar)+	{+		if (_topPlayer != null)+		{+			_topPlayer.addItem("DM Event: " + _eventName, _rewardId, _rewardAmount, _topPlayer, true);++			StatusUpdate su = new StatusUpdate(_topPlayer);+			su.addAttribute(StatusUpdate.CUR_LOAD, _topPlayer.getCurrentLoad());+			_topPlayer.sendPacket(su);++			NpcHtmlMessage nhm = new NpcHtmlMessage(5);+			StringBuilder replyMSG = new StringBuilder("");++			replyMSG.append("<html><body>You won the event. Look in your inventory for the reward.</body></html>");++			nhm.setHtml(replyMSG.toString());+			_topPlayer.sendPacket(nhm);++			// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+			_topPlayer.sendPacket(ActionFailed.STATIC_PACKET);+		}+	}++	public static void abortEvent()+	{+		if (!_joining && !_teleport && !_started)+			return;++		_joining = false;+		_teleport = false;+		_started = false;+		unspawnEventNpc();+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Match aborted!");+		teleportFinish();+	}++	public static void sit()+	{+		if (_sitForced)+			_sitForced = false;+		else+			_sitForced = true;++		for (Player player : _players)+		{+			if (player != null)+			{+				if (_sitForced)+				{+					player.stopMove(null);+					player.abortAttack();+					player.abortCast();++					if (!player.isSitting())+						player.sitDown();+				}+				else+				{+					if (player.isSitting())+						player.standUp();+				}+			}+		}+	}++	public static void dumpData()+	{+		_log.info("");+		_log.info("");++		if (!_joining && !_teleport && !_started)+		{+			_log.info("<<---------------------------------->>");+			_log.info(">> DM Engine infos dump (INACTIVE) <<");+			_log.info("<<--^----^^-----^----^^------^^----->>");+		}+		else if (_joining && !_teleport && !_started)+		{+			_log.info("<<--------------------------------->>");+			_log.info(">> DM Engine infos dump (JOINING) <<");+			_log.info("<<--^----^^-----^----^^------^----->>");+		}+		else if (!_joining && _teleport && !_started)+		{+			_log.info("<<---------------------------------->>");+			_log.info(">> DM Engine infos dump (TELEPORT) <<");+			_log.info("<<--^----^^-----^----^^------^^----->>");+		}+		else if (!_joining && !_teleport && _started)+		{+			_log.info("<<--------------------------------->>");+			_log.info(">> DM Engine infos dump (STARTED) <<");+			_log.info("<<--^----^^-----^----^^------^----->>");+		}++		_log.info("Name: " + _eventName);+		_log.info("Desc: " + _eventDesc);+		_log.info("Join location: " + _joiningLocationName);+		_log.info("Min lvl: " + _minlvl);+		_log.info("Max lvl: " + _maxlvl);++		_log.info("");+		_log.info("##################################");+		_log.info("# _players(Vector<Player>) #");+		_log.info("##################################");++		_log.info("Total Players : " + _players.size());++		for (Player player : _players)+		{+			if (player != null)+				_log.info("Name: " + player.getName() + " kills :" + player._countDMkills);+		}++		_log.info("");+		_log.info("################################");+		_log.info("# _savePlayers(Vector<String>) #");+		_log.info("################################");++		for (String player : _savePlayers)+			_log.info("Name: " + player);++		_log.info("");+		_log.info("");+	}++	public static void loadData()+	{+		_eventName = new String();+		_eventDesc = new String();+		_joiningLocationName = new String();+		_savePlayers = new ArrayList<>();+		_players = new ArrayList<>();+		_topPlayer = null;+		_npcSpawn = null;+		_joining = false;+		_teleport = false;+		_started = false;+		_sitForced = false;+		_npcId = 0;+		_npcX = 0;+		_npcY = 0;+		_npcZ = 0;+		_rewardId = 0;+		_rewardAmount = 0;+		_topKills = 0;+		_minlvl = 0;+		_maxlvl = 0;+		_playerColors = 0;+		_playerX = 0;+		_playerY = 0;+		_playerZ = 0;++		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;+			ResultSet rs;++			statement = con.prepareStatement("SELECT * FROM dm");+			rs = statement.executeQuery();++			while (rs.next())+			{+				_eventName = rs.getString("eventName");+				_eventDesc = rs.getString("eventDesc");+				_joiningLocationName = rs.getString("joiningLocation");+				_minlvl = rs.getInt("minlvl");+				_maxlvl = rs.getInt("maxlvl");+				_npcId = rs.getInt("npcId");+				_npcX = rs.getInt("npcX");+				_npcY = rs.getInt("npcY");+				_npcZ = rs.getInt("npcZ");+				_rewardId = rs.getInt("rewardId");+				_rewardAmount = rs.getInt("rewardAmount");+				_playerColors = rs.getInt("color");+				_playerX = rs.getInt("playerX");+				_playerY = rs.getInt("playerY");+				_playerZ = rs.getInt("playerZ");++			}+			rs.close();+			statement.close();+		}+		catch (Exception e)+		{+			_log.warning(DM.class.getSimpleName() + ":  Exception: DM.loadData(): " + e.getMessage());+		}+	}++	public static void saveData()+	{+		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;++			statement = con.prepareStatement("DELETE FROM dm");+			statement.execute();+			statement.close();++			statement = con.prepareStatement("INSERT INTO dm (eventName, eventDesc, joiningLocation, minlvl, maxlvl, npcId, npcX, npcY, npcZ, rewardId, rewardAmount, color, playerX, playerY, playerZ ) VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)");+			statement.setString(1, _eventName);+			statement.setString(2, _eventDesc);+			statement.setString(3, _joiningLocationName);+			statement.setInt(4, _minlvl);+			statement.setInt(5, _maxlvl);+			statement.setInt(6, _npcId);+			statement.setInt(7, _npcX);+			statement.setInt(8, _npcY);+			statement.setInt(9, _npcZ);+			statement.setInt(10, _rewardId);+			statement.setInt(11, _rewardAmount);+			statement.setInt(12, _playerColors);+			statement.setInt(13, _playerX);+			statement.setInt(14, _playerY);+			statement.setInt(15, _playerZ);+			statement.execute();+			statement.close();+		}+		catch (Exception e)+		{+			_log.warning(DM.class.getSimpleName() + ":  Exception: DM.saveData(): " + e.getMessage());+		}+	}++	public static void showEventHtml(Player eventPlayer, String objectId)+	{+		try+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++			StringBuilder replyMSG = new StringBuilder("<html><body>");+			replyMSG.append("DM Match<br><br><br>");+			replyMSG.append("Current event...<br1>");+			replyMSG.append("	... name:&nbsp;<font color=\"00FF00\">" + _eventName + "</font><br1>");+			replyMSG.append("	... description:&nbsp;<font color=\"00FF00\">" + _eventDesc + "</font><br><br>");++			if (!_started && !_joining)+				replyMSG.append("<center>Wait till the admin/gm start the participation.</center>");+			else if (!_started && _joining && eventPlayer.getLevel() >= _minlvl && eventPlayer.getLevel() < _maxlvl)+			{+				if (_players.contains(eventPlayer))+				{+					replyMSG.append("You are already participating!<br><br>");++					replyMSG.append("<table border=\"0\"><tr>");+					replyMSG.append("<td width=\"200\">Wait till event start or</td>");+					replyMSG.append("<td width=\"60\"><center><button value=\"remove\" action=\"bypass -h npc_" + objectId + "_dmevent_player_leave\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></center></td>");+					replyMSG.append("<td width=\"100\">your participation!</td>");+					replyMSG.append("</tr></table>");+				}+				else+				{+					replyMSG.append("You want to participate in the event?<br><br>");+					replyMSG.append("<td width=\"200\">Admin set min lvl : <font color=\"00FF00\">" + _minlvl + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Admin set max lvl : <font color=\"00FF00\">" + _maxlvl + "</font></td><br><br>");++					replyMSG.append("<button value=\"Join\" action=\"bypass -h npc_" + objectId + "_dmevent_player_join\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\">");++				}+			}+			else if (_started && !_joining)+				replyMSG.append("<center>DM match is in progress.</center>");+			else if (eventPlayer.getLevel() < _minlvl || eventPlayer.getLevel() > _maxlvl)+			{+				replyMSG.append("Your lvl : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font><br>");+				replyMSG.append("Admin set min lvl : <font color=\"00FF00\">" + _minlvl + "</font><br>");+				replyMSG.append("Admin set max lvl : <font color=\"00FF00\">" + _maxlvl + "</font><br><br>");+				replyMSG.append("<font color=\"FFFF00\">You can't participate to this event.</font><br>");+			}++			replyMSG.append("</body></html>");+			adminReply.setHtml(replyMSG.toString());+			eventPlayer.sendPacket(adminReply);++			// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+			eventPlayer.sendPacket(ActionFailed.STATIC_PACKET);+		}+		catch (Exception e)+		{+			_log.warning(DM.class.getSimpleName() + ":  DM Engine[showEventHtlm(" + eventPlayer.getName() + ", " + objectId + ")]: exception" + e.getMessage());+		}+	}++	public static void addPlayer(Player player)+	{+		if (!addPlayerOk(player))+			return;+		_players.add(player);+		player._originalNameColorDM = player.getAppearance().getNameColor();+		player._originalKarmaDM = player.getKarma();+		player._inEventDM = true;+		player._countDMkills = 0;+		_savePlayers.add(player.getName());++	}++	public static boolean addPlayerOk(Player eventPlayer)+	{++		if (eventPlayer._inEventDM)+		{+			eventPlayer.sendMessage("You are already participating in the event!");+			return false;+		}++		return true;+	}++	public static synchronized void addDisconnectedPlayer(Player player)+	{+		if ((_teleport || _started) || _savePlayers.contains(player.getName()))+		{+			if (Config.DM_ON_START_REMOVE_ALL_EFFECTS)+			{+				for (L2Effect e : player.getAllEffects())+				{+					if (e != null)+						e.exit();+				}+			}+			for (Player p : _players)+			{+				if (p == null)+				{+					continue;+				}+				// check by name incase player got new objectId+				else if (p.getName().equals(player.getName()))+				{+					player._originalNameColorDM = player.getAppearance().getNameColor();+					player._originalKarmaDM = player.getKarma();+					player._inEventDM = true;+					player._countDMkills = p._countDMkills;+					_players.remove(p); // removing old object id from vector+					_players.add(player); // adding new objectId to vector+					break;+				}+			}++			player.getAppearance().setNameColor(_playerColors);+			player.setKarma(0);+			player.broadcastUserInfo();+			player.teleToLocation(_playerX, _playerY, _playerZ, 0);+		}+	}++	public static void removePlayer(Player player)+	{+		if (player != null)+			_players.remove(player);+	}++	public static void cleanDM()+	{+		for (Player player : _players)+		{+			removePlayer(player);+		}++		_savePlayers = new ArrayList<>();+		_topPlayer = null;+		_npcSpawn = null;+		_joining = false;+		_teleport = false;+		_started = false;+		_sitForced = false;+		_topKills = 0;+		_players = new ArrayList<>();++	}++	public static void unspawnEventNpc()+	{+		if (_npcSpawn == null)+			return;++		_npcSpawn.getNpc().deleteMe();+		_npcSpawn.setRespawnState(false);+		SpawnTable.getInstance().deleteSpawn(_npcSpawn, true);+	}++	public static void teleportFinish()+	{+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Teleport back to participation NPC in 20 seconds!");++		removeUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				for (Player player : _players)+				{+					if (player != null && player.isOnline())+						player.teleToLocation(_npcX, _npcY, _npcZ, 0);+				}+				cleanDM();+			}+		}, 20000);+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerCtf.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerCtf.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerCtf.java	(working copy)@@ -0,0 +1,92 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ * + * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ * + * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++import java.util.ArrayList;+import java.util.Calendar;+import java.util.List;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.commons.concurrent.ThreadPool;+;++/**+ * @author Boorinio+ */+public class EventHandlerCtf+{+	private static final Logger _log = Logger.getLogger(EventHandlerCtf.class.getName());+	public List<Long> datesCtf = new ArrayList<>();+	+	public void startHandler()+	{+		loadConfisCtf(false);+		getNextTimeStampCTF();+		_log.info(EventHandlerCtf.class.getSimpleName() + ": Ctf handler initiated");+	}+	+	public void loadConfisCtf(boolean NextDay)+	{+		datesCtf.clear();+		for (String times : Config.CTF_EVENT_TIMES.split(","))+		{+			String[] timesSplited = times.split(":");+			int hour = Integer.parseInt(timesSplited[0]);+			int minute = Integer.parseInt(timesSplited[1]);+			Calendar time = Calendar.getInstance();+			if (!NextDay)+			{+				time.set(Calendar.HOUR_OF_DAY, hour);+				time.set(Calendar.MINUTE, minute);+			}+			else+			{+				time.set(Calendar.DAY_OF_MONTH, Calendar.getInstance().get(Calendar.DAY_OF_MONTH) + 1);+				time.set(Calendar.HOUR_OF_DAY, hour);+				time.set(Calendar.MINUTE, minute);+			}+			datesCtf.add(time.getTimeInMillis());+		}+	}+	+	public void getNextTimeStampCTF()+	{+		boolean found = false;+		for (Long stamp : datesCtf)+		{+			if (stamp > System.currentTimeMillis())+			{+				ThreadPool.schedule(new Runnable()+				{+					@Override+					public void run()+					{+						CTF.loadData();+						CTF.autoEvent();+						getNextTimeStampCTF();+					}+				}, stamp - System.currentTimeMillis());+				found = true;+				break;+			}+		}+		if (!found)+		{+			loadConfisCtf(true);+			getNextTimeStampCTF();+		}+	}+}Index: java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerTvT.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerTvT.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerTvT.java	(working copy)@@ -0,0 +1,91 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ * + * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ * + * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++import java.util.ArrayList;+import java.util.Calendar;+import java.util.List;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.commons.concurrent.ThreadPool;++/**+ * @author Boorinio+ */+public class EventHandlerTvT+{+	private static final Logger _log = Logger.getLogger(EventHandlerTvT.class.getName());+	public List<Long> datesTvT = new ArrayList<>();+	+	public void startHandler()+	{+		loadConfisTvT(false);+		getNextTimeStampTvT();+		_log.info(EventHandlerTvT.class.getSimpleName() + ": TvT handler initiated.");+	}+	+	public void loadConfisTvT(boolean NextDay)+	{+		datesTvT.clear();+		for (String times : Config.TVT_EVENT_TIMES.split(","))+		{+			String[] timesSplited = times.split(":");+			int hour = Integer.parseInt(timesSplited[0]);+			int minute = Integer.parseInt(timesSplited[1]);+			Calendar time = Calendar.getInstance();+			if (!NextDay)+			{+				time.set(Calendar.HOUR_OF_DAY, hour);+				time.set(Calendar.MINUTE, minute);+			}+			else+			{+				time.set(Calendar.DAY_OF_MONTH, Calendar.getInstance().get(Calendar.DAY_OF_MONTH) + 1);+				time.set(Calendar.HOUR_OF_DAY, hour);+				time.set(Calendar.MINUTE, minute);+			}+			datesTvT.add(time.getTimeInMillis());+		}+	}+	+	public void getNextTimeStampTvT()+	{+		boolean found = false;+		for (Long stamp : datesTvT)+		{+			if (stamp > System.currentTimeMillis())+			{+				ThreadPool.schedule(new Runnable()+				{+					@Override+					public void run()+					{+						TvT.loadData();+						TvT.autoEvent();+						getNextTimeStampTvT();+					}+				}, stamp - System.currentTimeMillis());+				found = true;+				break;+			}+		}+		if (!found)+		{+			loadConfisTvT(true);+			getNextTimeStampTvT();+		}+	}+}Index: java/net/sf/l2j/gameserver/model/entity/engine/TvT.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/TvT.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/TvT.java	(working copy)@@ -0,0 +1,1767 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++/**+ * @author FBIagent / Fixed By l2jhellas And L2Emu Team+ */+import java.sql.Connection;+import java.sql.PreparedStatement;+import java.sql.ResultSet;+import java.sql.SQLException;+import java.util.ArrayList;+import java.util.List;+import java.util.logging.Level;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.L2DatabaseFactory;+import net.sf.l2j.commons.concurrent.ThreadPool;+import net.sf.l2j.commons.random.Rnd;+import net.sf.l2j.gameserver.datatables.DoorTable;+import net.sf.l2j.gameserver.datatables.ItemTable;+import net.sf.l2j.gameserver.datatables.NpcTable;+import net.sf.l2j.gameserver.datatables.SpawnTable;+import net.sf.l2j.gameserver.model.L2Effect;+import net.sf.l2j.gameserver.model.L2Spawn;+import net.sf.l2j.gameserver.model.actor.Summon;+import net.sf.l2j.gameserver.model.actor.instance.Pet;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.actor.template.NpcTemplate;+import net.sf.l2j.gameserver.model.group.Party;+import net.sf.l2j.gameserver.model.group.Party.MessageType;+import net.sf.l2j.gameserver.model.olympiad.OlympiadManager;+import net.sf.l2j.gameserver.network.clientpackets.Say2;+import net.sf.l2j.gameserver.network.serverpackets.ActionFailed;+import net.sf.l2j.gameserver.network.serverpackets.CreatureSay;+import net.sf.l2j.gameserver.network.serverpackets.MagicSkillUse;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.network.serverpackets.SocialAction;+import net.sf.l2j.gameserver.util.Broadcast;++public class TvT+{+	protected static final Logger _log = Logger.getLogger(TvT.class.getName());+	public static String _eventName = "";+	public static String _eventDesc = "";+	public static String _topTeam = "";+	public static String _joiningLocationName = "";+	public static List<String> _teams = new ArrayList<>();+	public static List<String> _savePlayers = new ArrayList<>();+	public static List<String> _savePlayerTeams = new ArrayList<>();++	public static List<Player> _players = new ArrayList<>();+	public static List<Player> _playersShuffle = new ArrayList<>();+	public static List<Integer> _teamPlayersCount = new ArrayList<>();+	public static List<Integer> _teamKillsCount = new ArrayList<>();+	public static List<Integer> _teamColors = new ArrayList<>();+	public static List<Integer> _teamsX = new ArrayList<>();+	public static List<Integer> _teamsY = new ArrayList<>();+	public static List<Integer> _teamsZ = new ArrayList<>();+	public static boolean _joining = false;+	public static boolean _teleport = false;+	public static boolean _started = false;+	public static boolean _sitForced = false;+	public static L2Spawn _npcSpawn;++	public static int _npcId = 0;+	public static int _npcX = 0;+	public static int _npcY = 0;+	public static int _npcZ = 0;+	public static int _npcHeading = 0;++	public static int _rewardId = 0;+	public static int _rewardAmount = 0;++	public static int _topKills = 0;+	public static int _minlvl = 0;+	public static int _maxlvl = 0;++	public static int _joinTime = 0;+	public static int _eventTime = 0;++	public static int _minPlayers = 0;+	public static int _maxPlayers = 0;++	public static int _playerWon = 0;++	public static void AnnounceToPlayers(Boolean toall, String announce)+	{+		if (toall)+			Broadcast.announceToOnlinePlayers(announce);+		else+		{+			CreatureSay cs = new CreatureSay(0, Say2.ANNOUNCEMENT, "", announce);+			if (_players != null && !_players.isEmpty())+			{+				for (Player player : _players)+				{+					if (player != null && player.isOnline())+						player.sendPacket(cs);+				}+			}+		}+	}++	public static void kickPlayerFromTvt(Player playerToKick)+	{+		if (playerToKick == null)+			return;++		if (_joining)+		{+			_playersShuffle.remove(playerToKick);+			_players.remove(playerToKick);+			playerToKick._inEventTvT = false;+			playerToKick._teamNameTvT = "";+			playerToKick._countTvTkills = 0;+		}+		if (_started || _teleport)+		{+			_playersShuffle.remove(playerToKick);+			playerToKick._inEventTvT = false;+			removePlayer(playerToKick);+			if (playerToKick.isOnline())+			{+				playerToKick.getAppearance().setNameColor(playerToKick._originalNameColorTvT);+				playerToKick.setKarma(playerToKick._originalKarmaTvT);+				playerToKick.setTitle(playerToKick._originalTitleTvT);+				playerToKick.broadcastUserInfo();+				playerToKick.sendMessage("You have been kicked from the TvT.");+				playerToKick.teleToLocation(_npcX, _npcY, _npcZ, 0);+			}+		}+	}++	public static void setNpcPos(Player activeChar)+	{+		_npcX = activeChar.getX();+		_npcY = activeChar.getY();+		_npcZ = activeChar.getZ();+		_npcHeading = activeChar.getHeading();+	}++	public static void setNpcPos(int x, int y, int z)+	{+		_npcX = x;+		_npcY = y;+		_npcZ = z;+	}++	public static void addTeam(String teamName)+	{+		if (!checkTeamOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[addTeam(" + teamName + ")]: checkTeamOk() = false");+			return;+		}++		if (teamName.equals(" "))+			return;++		_teams.add(teamName);+		_teamPlayersCount.add(0);+		_teamKillsCount.add(0);+		_teamColors.add(0);+		_teamsX.add(0);+		_teamsY.add(0);+		_teamsZ.add(0);+	}++	public static boolean checkMaxLevel(int maxlvl)+	{+		return _minlvl < maxlvl;+	}++	public static boolean checkMinLevel(int minlvl)+	{+		return _maxlvl > minlvl;+	}++	/** returns true if participated players is higher or equal then minimum needed players +	 * @param players +	 * @return */+	public static boolean checkMinPlayers(int players)+	{+		return _minPlayers <= players;+	}++	/** returns true if max players is higher or equal then participated players +	 * @param players +	 * @return */+	public static boolean checkMaxPlayers(int players)+	{+		return _maxPlayers > players;+	}++	public static void removeTeam(String teamName)+	{+		if (!checkTeamOk() || _teams.isEmpty())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[removeTeam(" + teamName + ")]: checkTeamOk() = false");+			return;+		}++		if (teamPlayersCount(teamName) > 0)+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[removeTeam(" + teamName + ")]: teamPlayersCount(teamName) > 0");+			return;+		}++		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsZ.remove(index);+		_teamsY.remove(index);+		_teamsX.remove(index);+		_teamColors.remove(index);+		_teamKillsCount.remove(index);+		_teamPlayersCount.remove(index);+		_teams.remove(index);+	}++	public static void setTeamPos(String teamName, Player activeChar)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsX.set(index, activeChar.getX());+		_teamsY.set(index, activeChar.getY());+		_teamsZ.set(index, activeChar.getZ());+	}++	public static void setTeamPos(String teamName, int x, int y, int z)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsX.set(index, x);+		_teamsY.set(index, y);+		_teamsZ.set(index, z);+	}++	public static void setTeamColor(String teamName, int color)+	{+		if (!checkTeamOk())+			return;++		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamColors.set(index, color);+	}++	public static boolean checkTeamOk()+	{+		return !(_started || _teleport || _joining);+	}++	public static void startJoin(Player activeChar)+	{+		if (!startJoinOk())+		{+			activeChar.sendMessage("Event not setted propertly.");+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startJoin(" + activeChar.getName() + ")]: startJoinOk() = false");+			return;+		}+		_joining = true;+		spawnEventNpc(activeChar);+		AnnounceToPlayers(true, _eventName);+		if (Config.TVT_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Join in " + _joiningLocationName + "!");+	}++	public static void startJoin()+	{+		if (!startJoinOk())+		{+			_log.warning(TvT.class.getSimpleName() + ":  Event not setted propertly.");+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startJoin(startJoinOk() = false");+			return;+		}+		_joining = true;+		spawnEventNpc();+		AnnounceToPlayers(true, _eventName);+		if (Config.TVT_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Join in " + _joiningLocationName + "!");+	}++	public static boolean startAutoJoin()+	{+		if (!startJoinOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startJoin]: startJoinOk() = false");+			return false;+		}++		_joining = true;+		spawnEventNpc();+		AnnounceToPlayers(true, _eventName);+		if (Config.TVT_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Join in " + _joiningLocationName + "!");+		return true;+	}++	public static boolean startJoinOk()+	{+		return !(_started || _teleport || _joining || _teams.size() < 2 || _eventName.isEmpty() || _joiningLocationName.isEmpty() || _eventDesc.isEmpty() || _npcId == 0 || _npcX == 0 || _npcY == 0 || _npcZ == 0 || _rewardId == 0 || _rewardAmount == 0 || _teamsX.contains(0) || _teamsY.contains(0) || _teamsZ.contains(0));+	}++	private static void spawnEventNpc(Player activeChar)+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);++			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, _npcHeading);+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobTvT = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  TvT Engine[spawnEventNpc(" + activeChar.getName() + ")]: exception: ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	private static void spawnEventNpc()+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);+			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, _npcHeading);+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobTvT = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  TvT Engine[spawnEventNpc(exception: ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void teleportStart()+	{+		if (!_joining || _started || _teleport)+			return;++		if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && checkMinPlayers(_playersShuffle.size()))+		{+			removeOfflinePlayers();+			shuffleTeams();+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && !checkMinPlayers(_playersShuffle.size()))+		{+			AnnounceToPlayers(true, "Not enough players for event. Min Requested : " + _minPlayers + ", Participating : " + _playersShuffle.size());+			return;+		}++		_joining = false;+		AnnounceToPlayers(false, _eventName + "Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				TvT.sit();++				for (Player player : _players)+				{+					if (player != null)+					{+						if (Config.TVT_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+								Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+								{+									if (e != null)+										e.exit();+								}++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}++						if (Config.TVT_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}++						player.setTitle("Kills: " + player._countTvTkills);+						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameTvT)), _teamsY.get(_teams.indexOf(player._teamNameTvT)), _teamsZ.get(_teams.indexOf(player._teamNameTvT)), 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+	}++	public static boolean teleportAutoStart()+	{+		if (!_joining || _started || _teleport)+			return false;++		if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && checkMinPlayers(_playersShuffle.size()))+		{+			removeOfflinePlayers();+			shuffleTeams();+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && !checkMinPlayers(_playersShuffle.size()))+		{+			AnnounceToPlayers(true, "Not enough players for event. Min Requested : " + _minPlayers + ", Participating : " + _playersShuffle.size());+			return false;+		}++		_joining = false;+		AnnounceToPlayers(false, _eventName + "Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				TvT.sit();++				for (Player player : _players)+				{+					if (player != null)+					{+						if (Config.TVT_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+								Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+								{+									if (e != null)+										e.exit();+								}++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}++						if (Config.TVT_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}+						player.setTitle("Kills: " + player._countTvTkills);+						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameTvT)), _teamsY.get(_teams.indexOf(player._teamNameTvT)), _teamsZ.get(_teams.indexOf(player._teamNameTvT)), 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+		return true;+	}++	public static void startEvent(Player activeChar)+	{+		if (_inProgress)+		{+			activeChar.sendMessage("A TvT event is already in progress, try abort.");+			return;+		}++		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startEvent(" + activeChar.getName() + ")]: startEventOk() = false");+			return;+		}++		_teleport = false;+		sit();++		if (Config.TVT_CLOSE_COLISEUM_DOORS)+			closeColiseumDoors();++		AnnounceToPlayers(false, _eventName + "Started. Go to kill your enemies!");+		_started = true;+		_inProgress = true;+	}++	public static void setJoinTime(int time)+	{+		_joinTime = time;+	}++	public static void setEventTime(int time)+	{+		_eventTime = time;+	}++	public static boolean startAutoEvent()+	{+		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startEvent]: startEventOk() = false");+			return false;+		}++		_teleport = false;+		sit();++		if (Config.TVT_CLOSE_COLISEUM_DOORS)+			closeColiseumDoors();++		AnnounceToPlayers(false, _eventName + "Started. Go to kill your enemies!");+		_started = true;+		return true;+	}++	public static synchronized void autoEvent()+	{+		_log.info("Starting TvT!");+		if (startAutoJoin())+		{+			_eventType = 2;++			if (_joinTime > 0)+				waiter(_joinTime * 60 * 1000); // minutes for join event+			else if (_joinTime <= 0)+			{+				_log.info("TvT: join time <=0 aborting event.");+				abortEvent();+				return;+			}+			if (teleportAutoStart())+			{+				waiter(30 * 1000); // 30 sec wait time untill start fight after teleported+				if (startAutoEvent())+				{+					_log.log(Level.FINER, "TvT: waiting.....minutes for event time " + TvT._eventTime);++					waiter(_eventTime * 60 * 1000); // minutes for event time+					finishEvent();++					_log.info("TvT: waiting... delay for final messages ");+					waiter(60000);// just a give a delay delay for final messages+					sendFinalMessages();+				}+			}+			else if (!teleportAutoStart())+			{+				abortEvent();+			}+		}+	}++	private synchronized static void waiter(long interval)+	{+		long startWaiterTime = System.currentTimeMillis();+		int seconds = (int) (interval / 1000);++		String npcManager = NpcTable.getInstance().getTemplate(_npcId).getName();++		while (startWaiterTime + interval > System.currentTimeMillis())+		{+			seconds--; // here because we don't want to see two time announce at the same time++			if (_joining || _started || _teleport)+			{+				switch (seconds)+				{+					case 3600: // 1 hour left+						if (_joining)+						{+							AnnounceToPlayers(true, "TvT: Joinable in " + _joiningLocationName + "!");+							AnnounceToPlayers(true, "TvT: " + seconds / 60 / 60 + " hour(s) till registration ends!");+							if (Config.TVT_ANNOUNCE_REGISTRATION_LOC_NPC)+								AnnounceToPlayers(true, "TvT: Registration Period is Active in " + _joiningLocationName + " ! at Npc " + npcManager);+						}+						else if (_started)+							AnnounceToPlayers(false, "TvT: " + seconds / 60 / 60 + " hour(s) till event ends!");++					break;+					case 1800: // 30 minutes left+					case 900: // 15 minutes left+					case 600: // 10 minutes left+					case 300: // 5 minutes left+					case 60: // 1 minute left+						if (_joining)+						{+							removeOfflinePlayers();+							AnnounceToPlayers(true, "TvT: Joinable in " + _joiningLocationName + "!");+							AnnounceToPlayers(true, "TvT: " + seconds / 60 + " minute(s) till registration ends!");+							if (Config.TVT_ANNOUNCE_REGISTRATION_LOC_NPC)+								Broadcast.announceToOnlinePlayers("TvT: Registration Period is Active in " + _joiningLocationName + " ! at Npc " + npcManager);+						}+						else if (_started)+							AnnounceToPlayers(false, "TvT: " + seconds / 60 + " minute(s) till event ends!");++					break;+					case 30: // 30 seconds left+					case 10: // 10 seconds left+					case 3: // 3 seconds left+					case 2: // 2 seconds left+					case 1: // 1 seconds left+						if (_joining)+							AnnounceToPlayers(true, "TvT: " + seconds + " second(s) till registration ends!");+						else if (_teleport)+							AnnounceToPlayers(false, "TvT: " + seconds + " seconds(s) till fight starts!");+						else if (_started)+							AnnounceToPlayers(false, "TvT: " + seconds + " second(s) till event ends!");++					break;+				}+			}++			long startOneSecondWaiterStartTime = System.currentTimeMillis();++			// only the try catch with Thread.sleep(1000) give bad countdown on high wait times+			while (startOneSecondWaiterStartTime + 1000 > System.currentTimeMillis())+			{+				try+				{+					Thread.sleep(1);+				}+				catch (InterruptedException ie)+				{++				}+			}+		}+	}++	private static boolean startEventOk()+	{+		if (_joining || !_teleport || _started)+			return false;++		if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+		{+			if (_teamPlayersCount.contains(0))+				return false;+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+		{+			List<Player> playersShuffleTemp = new ArrayList<>();+			int loopCount = 0;++			loopCount = _playersShuffle.size();++			for (int i = 0; i < loopCount; i++)+			{+				if (_playersShuffle != null)+					playersShuffleTemp.add(_playersShuffle.get(i));+			}++			_playersShuffle = playersShuffleTemp;+			playersShuffleTemp.clear();+		}++		return true;+	}++	public static void shuffleTeams()+	{+		int teamCount = 0, playersCount = 0;++		for (;;)+		{+			if (_playersShuffle.isEmpty())+				break;++			int playerToAddIndex = Rnd.nextInt(_playersShuffle.size());+			Player player = null;+			player = _playersShuffle.get(playerToAddIndex);+			player._originalNameColorTvT = player.getAppearance().getNameColor();+			player._originalTitleTvT = player.getTitle();+			player._originalKarmaTvT = player.getKarma();++			_players.add(player);+			_players.get(playersCount)._teamNameTvT = _teams.get(teamCount);+			_savePlayers.add(_players.get(playersCount).getName());+			_savePlayerTeams.add(_teams.get(teamCount));+			playersCount++;++			if (teamCount == _teams.size() - 1)+				teamCount = 0;+			else+				teamCount++;++			_playersShuffle.remove(playerToAddIndex);+		}+	}++	public static void setUserData()+	{+		for (Player player : _players)+		{+			player.getAppearance().setNameColor(_teamColors.get(_teams.indexOf(player._teamNameTvT)));+			player.setKarma(0);++			if (Config.TVT_AURA)+			{+				if (_teams.size() >= 2)+					player.setTeam(_teams.indexOf(player._teamNameTvT) + 1);+			}+			player.broadcastUserInfo();+		}+	}++	public static void finishEvent()+	{+		if (!finishEventOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[finishEvent]: finishEventOk() = false");+			return;+		}++		_started = false;+		unspawnEventNpc();+		processTopTeam();++		if (_topKills == 0)+			AnnounceToPlayers(true, _eventName + "No team wins the match(nobody killed).");+		else+		{+			AnnounceToPlayers(true, _eventName + " " + _topTeam + "'s win the match! " + _topKills + " kills.");+			rewardTeam(_topTeam);+			playKneelAnimation(_topTeam);+		}++		if (Config.TVT_ANNOUNCE_TEAM_STATS)+		{+			AnnounceToPlayers(true, _eventName + " Team Statistics:");+			for (String team : _teams)+			{+				int _kills = teamKillsCount(team);+				AnnounceToPlayers(true, "Team: " + team + " - Kills: " + _kills);+			}+		}++		teleportFinish();+	}++	// show losers and winners animations+	public static void playKneelAnimation(String teamName)+	{+		for (Player player : _players)+		{+			if (player != null)+			{+				if (!player._teamNameTvT.equals(teamName))+					player.broadcastPacket(new SocialAction(player, 7),2000);+				else if (player._teamNameTvT.equals(teamName))+					player.broadcastPacket(new SocialAction(player, 3),2000);+			}+		}+	}++	private static boolean finishEventOk()+	{+		if (!_started)+			return false;++		_inProgress = false;+		if (Config.TVT_CLOSE_COLISEUM_DOORS)+			openColiseumDoors();++		return true;+	}++	public static void processTopTeam()+	{+		for (String team : _teams)+		{+			if (teamKillsCount(team) > _topKills)+			{+				_topTeam = team;+				_topKills = teamKillsCount(team);+			}+		}+	}++	public static void rewardTeam(String teamName)+	{+		for (Player player : _players)+		{+			if (player != null && player.isOnline() && player._inEventTvT)+			{+				if (player._teamNameTvT.equals(teamName) && (player._countTvTkills > 0 || Config.TVT_PRICE_NO_KILLS))+				{+					player.addItem("TvT: " + _eventName, _rewardId, _rewardAmount, player, true);++					_playerWon = 1;++					NpcHtmlMessage nhm = new NpcHtmlMessage(5);+					StringBuilder replyMSG = new StringBuilder("");++					replyMSG.append("<html><body>Your team wins the event. Look in your inventory for the reward.</body></html>");++					nhm.setHtml(replyMSG.toString());+					player.sendPacket(nhm);++					// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+					player.sendPacket(ActionFailed.STATIC_PACKET);+				}+			}+		}+	}++	public static void abortEvent()+	{+		if (!_joining && !_teleport && !_started)+			return;+		if (_joining && !_teleport && !_started)+		{+			unspawnEventNpc();+			cleanTvT();+			_joining = false;+			AnnounceToPlayers(true, _eventName + "Match aborted!");+			return;+		}+		_joining = false;+		_teleport = false;+		_started = false;+		_inProgress = false;+		unspawnEventNpc();+		AnnounceToPlayers(true, _eventName + "Match aborted!");+		teleportFinish();+	}++	public static void sit()+	{+		_sitForced = !_sitForced;++		for (Player player : _players)+		{+			if (player != null)+			{+				if (_sitForced)+				{+					player.stopMove(null);+					player.abortAttack();+					player.abortCast();++					if (!player.isSitting())+						player.sitDown();+				}+				else+				{+					if (player.isSitting())+						player.standUp();+				}+			}+		}+	}++	public static void dumpData()+	{+		_log.info("");+		_log.info("");++		if (!_joining && !_teleport && !_started)+		{+			_log.info("<<---------------------------------->>");+			_log.info(">> TvT Engine infos dump (INACTIVE) <<");+			_log.info("<<--^----^^-----^----^^------^^----->>");+		}+		else if (_joining && !_teleport && !_started)+		{+			_log.info("<<--------------------------------->>");+			_log.info(">> TvT Engine infos dump (JOINING) <<");+			_log.info("<<--^----^^-----^----^^------^----->>");+		}+		else if (!_joining && _teleport && !_started)+		{+			_log.info("<<---------------------------------->>");+			_log.info(">> TvT Engine infos dump (TELEPORT) <<");+			_log.info("<<--^----^^-----^----^^------^^----->>");+		}+		else if (!_joining && !_teleport && _started)+		{+			_log.info("<<--------------------------------->>");+			_log.info(">> TvT Engine infos dump (STARTED) <<");+			_log.info("<<--^----^^-----^----^^------^----->>");+		}++		_log.info("Name: " + _eventName);+		_log.info("Desc: " + _eventDesc);+		_log.info("Join location: " + _joiningLocationName);+		_log.info("Min lvl: " + _minlvl);+		_log.info("Max lvl: " + _maxlvl);+		_log.info("");+		_log.info("##########################");+		_log.info("# _teams(Vector<String>) #");+		_log.info("##########################");++		for (String team : _teams)+			_log.info(team + " Kills Done :" + _teamKillsCount.get(_teams.indexOf(team)));++		if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+		{+			_log.info("");+			_log.info("#########################################");+			_log.info("# _playersShuffle(Vector<Player>) #");+			_log.info("#########################################");++			for (Player player : _playersShuffle)+			{+				if (player != null)+					_log.info("Name: " + player.getName());+			}+		}++		_log.info("");+		_log.info("##################################");+		_log.info("# _players(Vector<Player>) #");+		_log.info("##################################");++		for (Player player : _players)+		{+			if (player != null)+				_log.info("Name: " + player.getName() + "   Team: " + player._teamNameTvT + "  Kills Done:" + player._countTvTkills);+		}++		_log.info("");+		_log.info("#####################################################################");+		_log.info("# _savePlayers(Vector<String>) and _savePlayerTeams(Vector<String>) #");+		_log.info("#####################################################################");++		for (String player : _savePlayers)+			_log.info("Name: " + player + "	Team: " + _savePlayerTeams.get(_savePlayers.indexOf(player)));++		_log.info("");+		_log.info("");+	}++	public static void loadData()+	{+		_eventName = "";+		_eventDesc = "";+		_topTeam = "";+		_joiningLocationName = "";+		_teams = new ArrayList<>();+		_savePlayers = new ArrayList<>();+		_savePlayerTeams = new ArrayList<>();+		_players = new ArrayList<>();+		_playersShuffle = new ArrayList<>();+		_teamPlayersCount = new ArrayList<>();+		_teamKillsCount = new ArrayList<>();+		_teamColors = new ArrayList<>();+		_teamsX = new ArrayList<>();+		_teamsY = new ArrayList<>();+		_teamsZ = new ArrayList<>();+		_joining = false;+		_teleport = false;+		_started = false;+		_sitForced = false;+		_npcId = 0;+		_npcX = 0;+		_npcY = 0;+		_npcZ = 0;+		_npcHeading = 0;+		_rewardId = 0;+		_rewardAmount = 0;+		_topKills = 0;+		_minlvl = 0;+		_maxlvl = 0;+		_joinTime = 0;+		_eventTime = 0;+		_minPlayers = 0;+		_maxPlayers = 0;+		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;+			ResultSet rs;+			statement = con.prepareStatement("SELECT * FROM tvt");+			rs = statement.executeQuery();++			int teams = 0;++			while (rs.next())+			{+				_eventName = rs.getString("eventName");+				_eventDesc = rs.getString("eventDesc");+				_joiningLocationName = rs.getString("joiningLocation");+				_minlvl = rs.getInt("minlvl");+				_maxlvl = rs.getInt("maxlvl");+				_npcId = rs.getInt("npcId");+				_npcX = rs.getInt("npcX");+				_npcY = rs.getInt("npcY");+				_npcZ = rs.getInt("npcZ");+				_npcHeading = rs.getInt("npcHeading");+				_rewardId = rs.getInt("rewardId");+				_rewardAmount = rs.getInt("rewardAmount");+				teams = rs.getInt("teamsCount");+				_joinTime = rs.getInt("joinTime");+				_eventTime = rs.getInt("eventTime");+				_minPlayers = rs.getInt("minPlayers");+				_maxPlayers = rs.getInt("maxPlayers");+			}+			rs.close();+			statement.close();++			int index = -1;+			if (teams > 0)+				index = 0;+			while (index < teams && index > -1)+			{+				statement = con.prepareStatement("SELECT * FROM tvt_teams WHERE teamId=?");+				statement.setInt(1, index);+				rs = statement.executeQuery();+				while (rs.next())+				{+					_teams.add(rs.getString("teamName"));+					_teamPlayersCount.add(0);+					_teamKillsCount.add(0);+					_teamColors.add(0);+					_teamsX.add(0);+					_teamsY.add(0);+					_teamsZ.add(0);+					_teamsX.set(index, rs.getInt("teamX"));+					_teamsY.set(index, rs.getInt("teamY"));+					_teamsZ.set(index, rs.getInt("teamZ"));+					_teamColors.set(index, rs.getInt("teamColor"));+				}+				index++;+				rs.close();+				statement.close();+			}+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  Exception: TvT.loadData(): ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void saveData()+	{+		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;++			statement = con.prepareStatement("DELETE FROM tvt");+			statement.execute();+			statement.close();++			statement = con.prepareStatement("INSERT INTO tvt (eventName, eventDesc, joiningLocation, minlvl, maxlvl, npcId, npcX, npcY, npcZ, npcHeading, rewardId, rewardAmount, teamsCount, joinTime, eventTime, minPlayers, maxPlayers) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)");+			statement.setString(1, _eventName);+			statement.setString(2, _eventDesc);+			statement.setString(3, _joiningLocationName);+			statement.setInt(4, _minlvl);+			statement.setInt(5, _maxlvl);+			statement.setInt(6, _npcId);+			statement.setInt(7, _npcX);+			statement.setInt(8, _npcY);+			statement.setInt(9, _npcZ);+			statement.setInt(10, _npcHeading);+			statement.setInt(11, _rewardId);+			statement.setInt(12, _rewardAmount);+			statement.setInt(13, _teams.size());+			statement.setInt(14, _joinTime);+			statement.setInt(15, _eventTime);+			statement.setInt(16, _minPlayers);+			statement.setInt(17, _maxPlayers);+			statement.execute();+			statement.close();++			statement = con.prepareStatement("DELETE FROM tvt_teams");+			statement.execute();+			statement.close();++			for (String teamName : _teams)+			{+				int index = _teams.indexOf(teamName);++				if (index == -1)+					return;+				statement = con.prepareStatement("INSERT INTO tvt_teams (teamId ,teamName, teamX, teamY, teamZ, teamColor) VALUES (?, ?, ?, ?, ?, ?)");+				statement.setInt(1, index);+				statement.setString(2, teamName);+				statement.setInt(3, _teamsX.get(index));+				statement.setInt(4, _teamsY.get(index));+				statement.setInt(5, _teamsZ.get(index));+				statement.setInt(6, _teamColors.get(index));+				statement.execute();+				statement.close();+			}+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  Exception: TvT.saveData(): ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void showEventHtml(Player eventPlayer, String objectId)+	{+		try+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++			StringBuilder replyMSG = new StringBuilder("<html><body>");+			replyMSG.append("TvT Match<br><br><br>");+			replyMSG.append("Current event...<br1>");+			replyMSG.append("    ... name:&nbsp;<font color=\"00FF00\">" + _eventName + "</font><br1>");+			replyMSG.append("    ... description:&nbsp;<font color=\"00FF00\">" + _eventDesc + "</font><br>");+			if (Config.TVT_ANNOUNCE_REWARD)+				replyMSG.append("    ... reward: (" + _rewardAmount + ") " + ItemTable.getInstance().getTemplate(_rewardId).getName() + "<br>");++			if (!_started && !_joining)+				replyMSG.append("<center>Wait till the admin/gm start the participation.</center>");+			else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && !checkMaxPlayers(_playersShuffle.size()))+			{+				if (!TvT._started)+					replyMSG.append("<font color=\"FFFF00\">The event has reached its maximum capacity.</font><br>Keep checking, someone may crit and you can steal their spot.");+			}+			else if (eventPlayer.isCursedWeaponEquipped() && !Config.TVT_JOIN_CURSED)+				replyMSG.append("<font color=\"FFFF00\">You can't participate in this event with a cursed Weapon.</font><br>");+			else if (!_started && _joining && eventPlayer.getLevel() >= _minlvl && eventPlayer.getLevel() <= _maxlvl)+			{+				if (_players.contains(eventPlayer) || checkShufflePlayers(eventPlayer))+				{+					if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+						replyMSG.append("You are already participating in team <font color=\"LEVEL\">" + eventPlayer._teamNameTvT + "</font><br><br>");+					else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+						replyMSG.append("You are already participating!<br><br>");++					replyMSG.append("<table border=\"0\"><tr>");+					replyMSG.append("<td width=\"200\">Wait till event start or</td>");+					replyMSG.append("<td width=\"60\"><center><button value=\"remove\" action=\"bypass -h npc_" + objectId + "_tvt_player_leave\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></center></td>");+					replyMSG.append("<td width=\"100\">your participation!</td>");+					replyMSG.append("</tr></table>");+				}+				else+				{+					replyMSG.append("You want to participate in the event?<br><br>");+					replyMSG.append("<td width=\"200\">Your level : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Min level : <font color=\"00FF00\">" + _minlvl + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Max level : <font color=\"00FF00\">" + _maxlvl + "</font></td><br><br>");++					if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+					{+						replyMSG.append("<center><table border=\"0\">");++						for (String team : _teams)+						{+							replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font>&nbsp;(" + teamPlayersCount(team) + " joined)</td>");+							replyMSG.append("<td width=\"60\"><button value=\"Join\" action=\"bypass -h npc_" + objectId + "_tvt_player_join " + team + "\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td></tr>");+						}++						replyMSG.append("</table></center>");+					}+					else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+					{+						replyMSG.append("<center><table border=\"0\">");++						for (String team : _teams)+							replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font></td>");++						replyMSG.append("</table></center><br>");++						replyMSG.append("<button value=\"Join\" action=\"bypass -h npc_" + objectId + "_tvt_player_join eventShuffle\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\">");+						replyMSG.append("Teams will be randomly generated!");+					}+				}+			}+			else if (_started && !_joining)+				replyMSG.append("<center>TvT match is in progress.</center>");+			else if (eventPlayer.getLevel() < _minlvl || eventPlayer.getLevel() >= _maxlvl)+			{+				replyMSG.append("Your level : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font><br>");+				replyMSG.append("Min level : <font color=\"00FF00\">" + _minlvl + "</font><br>");+				replyMSG.append("Max level : <font color=\"00FF00\">" + _maxlvl + "</font><br><br>");+				replyMSG.append("<font color=\"FFFF00\">You can't participate in this event.</font><br>");+			}+			// Show how many players joined & how many are still needed to join+			replyMSG.append("<br>There are " + _playersShuffle.size() + " player(s) participating in this event.<br>");+			if (_joining)+			{+				if (_playersShuffle.size() < _minPlayers)+				{+					int playersNeeded = _minPlayers - _playersShuffle.size();+					replyMSG.append("The event will not start unless " + playersNeeded + " more player(s) joins!");+				}+			}+			replyMSG.append("</body></html>");+			adminReply.setHtml(replyMSG.toString());+			eventPlayer.sendPacket(adminReply);++			// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+			eventPlayer.sendPacket(ActionFailed.STATIC_PACKET);+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  TvT Engine[showEventHtlm(" + eventPlayer.getName() + ", " + objectId + ")]: exception");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void addPlayer(Player player, String teamName)+	{+		if (!addPlayerOk(teamName, player))+			return;++		if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+		{+			player._teamNameTvT = teamName;+			_players.add(player);+			setTeamPlayersCount(teamName, teamPlayersCount(teamName) + 1);+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+			_playersShuffle.add(player);++		player._inEventTvT = true;+		player._countTvTkills = 0;++		// notify player that he signed up in event+		NpcHtmlMessage html = new NpcHtmlMessage(1);+		html.setFile("data/html/mods/Participation.htm");+		player.sendPacket(html);++		if (Config.TVT_ANNOUNCE_SIGNUPS)+			Broadcast.announceToOnlinePlayers("Player " + player.getName() + " has Signed Up in TvT!");+	}++	public synchronized static void removeOfflinePlayers()+	{+		try+		{+			if (_playersShuffle == null || _playersShuffle.isEmpty())+				return;+			for (Player player : _playersShuffle)+			{+				if (player == null)+					_playersShuffle.remove(player);+				else if (player.isOnline() || player.isInJail())+					removePlayer(player);+				if (_playersShuffle.size() == 0 || _playersShuffle.isEmpty())+					break;+			}+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ": TVT unknown error");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static boolean checkShufflePlayers(Player eventPlayer)+	{+		try+		{+			for (Player player : _playersShuffle)+			{+				if (player == null || player.isOnline())+				{+					_playersShuffle.remove(player);+					eventPlayer._inEventTvT = false;+					continue;+				}+				else if (player.getObjectId() == eventPlayer.getObjectId())+				{+					eventPlayer._inEventTvT = true;+					eventPlayer._countTvTkills = 0;+					return true;+				}+				// this 1 is incase player got new objectid after DC or reconnect+				else if (player.getName().equals(eventPlayer.getName()))+				{+					_playersShuffle.remove(player);+					_playersShuffle.add(eventPlayer);+					eventPlayer._inEventTvT = true;+					eventPlayer._countTvTkills = 0;+					return true;+				}+			}+		}+		catch (Exception e)+		{+		}+		return false;+	}++	public static boolean addPlayerOk(String teamName, Player eventPlayer)+	{+		try+		{+			if(OlympiadManager.getInstance().isRegisteredInComp(eventPlayer) || eventPlayer.isInOlympiadMode() || eventPlayer.getOlympiadGameId() >0)+			{+				eventPlayer.sendMessage("You can't register while you are in olympiad!");+				return false;+			}+			if (checkShufflePlayers(eventPlayer) || eventPlayer._inEventTvT)+			{+				eventPlayer.sendMessage("You are already participating in the event!");+				return false;+			}+			if (eventPlayer._inEventCTF || eventPlayer._inEventDM || eventPlayer._inEventVIP)+			{+				eventPlayer.sendMessage("You are already participating in another event!");+				return false;+			}++			for (Player player : _players)+			{+				if (player.getObjectId() == eventPlayer.getObjectId())+				{+					eventPlayer.sendMessage("You are already participating in the event!");+					return false;+				}+				else if (player.getName() == eventPlayer.getName())+				{+					eventPlayer.sendMessage("You are already participating in the event!");+					return false;+				}+			}+			if (_players.contains(eventPlayer))+			{+				eventPlayer.sendMessage("You are already participating in the event!");+				return false;+			}+			if (CTF._savePlayers.contains(eventPlayer.getName()))+			{+				eventPlayer.sendMessage("You are already participating in another event!");+				return false;+			}+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  TvT Engine exception: ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}++		if (Config.TVT_EVEN_TEAMS.equals("NO"))+			return true;+		else if (Config.TVT_EVEN_TEAMS.equals("BALANCE"))+		{+			boolean allTeamsEqual = true;+			int countBefore = -1;++			for (int playersCount : _teamPlayersCount)+			{+				if (countBefore == -1)+					countBefore = playersCount;++				if (countBefore != playersCount)+				{+					allTeamsEqual = false;+					break;+				}++				countBefore = playersCount;+			}++			if (allTeamsEqual)+				return true;++			countBefore = Integer.MAX_VALUE;++			for (int teamPlayerCount : _teamPlayersCount)+			{+				if (teamPlayerCount < countBefore)+					countBefore = teamPlayerCount;+			}++			List<String> joinableTeams = new ArrayList<>();++			for (String team : _teams)+			{+				if (teamPlayersCount(team) == countBefore)+					joinableTeams.add(team);+			}++			if (joinableTeams.contains(teamName))+				return true;+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+			return true;++		eventPlayer.sendMessage("Too many players in team \"" + teamName + "\"");+		return false;+	}++	public static synchronized void addDisconnectedPlayer(Player player)+	{+		if ((Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && (_teleport || _started)) || (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE") && (_teleport || _started)))+		{+			if (Config.TVT_ON_START_REMOVE_ALL_EFFECTS)+			{+				for (L2Effect e : player.getAllEffects())+				{+					if (e != null)+						e.exit();+				}+			}++			player._teamNameTvT = _savePlayerTeams.get(_savePlayers.indexOf(player.getName()));+			for (Player p : _players)+			{+				if (p == null)+					continue;+				// check by name incase player got new objectId+				else if (p.getName().equals(player.getName()))+				{+					player._originalNameColorTvT = player.getAppearance().getNameColor();+					player._originalTitleTvT = player.getTitle();+					player._originalKarmaTvT = player.getKarma();+					player._inEventTvT = true;+					player._countTvTkills = p._countTvTkills;+					_players.remove(p); // removing old object id from vector+					_players.add(player); // adding new objectId to vector+					break;+				}+			}++			player.getAppearance().setNameColor(_teamColors.get(_teams.indexOf(player._teamNameTvT)));+			player.setKarma(0);+			if (Config.TVT_AURA)+			{+				if (_teams.size() >= 2)+					player.setTeam(_teams.indexOf(player._teamNameTvT) + 1);+			}+			player.broadcastUserInfo();+			player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameTvT)), _teamsY.get(_teams.indexOf(player._teamNameTvT)), _teamsZ.get(_teams.indexOf(player._teamNameTvT)), 0);+		}+	}++	public static void removePlayer(Player player)+	{+		if (player._inEventTvT)+		{+			if (!_joining)+			{+				player.getAppearance().setNameColor(player._originalNameColorTvT);+				player.setTitle(player._originalTitleTvT);+				player.setKarma(player._originalKarmaTvT);+				if (Config.TVT_AURA)+				{+					if (_teams.size() >= 2)+						player.setTeam(0);// clear aura :P+				}+				player.broadcastUserInfo();+			}+			player._teamNameTvT = "";+			player._countTvTkills = 0;+			player._inEventTvT = false;++			if ((Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE")) && _players.contains(player))+			{+				setTeamPlayersCount(player._teamNameTvT, teamPlayersCount(player._teamNameTvT) - 1);+				_players.remove(player);+			}+			else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && (!_playersShuffle.isEmpty() && _playersShuffle.contains(player)))+				_playersShuffle.remove(player);+		}+	}++	public static void cleanTvT()+	{+		_log.info("TvT: Cleaning players.");+		for (Player player : _players)+		{+			if (player != null)+			{+				removePlayer(player);+				if (_savePlayers.contains(player.getName()))+					_savePlayers.remove(player.getName());+				player._inEventTvT = false;+			}+		}+		if (_playersShuffle != null && !_playersShuffle.isEmpty())+		{+			for (Player player : _playersShuffle)+			{+				if (player != null)+					player._inEventTvT = false;+			}+		}+		_log.info("TvT: Cleaning teams.");+		for (String team : _teams)+		{+			int index = _teams.indexOf(team);++			_teamPlayersCount.set(index, 0);+			_teamKillsCount.set(index, 0);+		}++		_topKills = 0;+		_topTeam = "";+		_players.clear();+		_playersShuffle.clear();+		_savePlayers.clear();+		_savePlayerTeams.clear();+		_log.info("Cleaning TvT done.");+	}++	public static void unspawnEventNpc()+	{+		if (_npcSpawn == null)+			return;++		_npcSpawn.getNpc().deleteMe();+		_npcSpawn.setRespawnState(false);+		SpawnTable.getInstance().deleteSpawn(_npcSpawn, true);+	}++	public static void teleportFinish()+	{+		AnnounceToPlayers(false, _eventName + "Teleport back to participation NPC in 20 seconds!");++		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				for (Player player : _players)+				{+					if (player != null)+					{+						if (player.isOnline())+							player.teleToLocation(_npcX, _npcY, _npcZ, 0);+						else+						{+							try (Connection con = L2DatabaseFactory.getInstance().getConnection())+							{+								PreparedStatement statement = con.prepareStatement("UPDATE characters SET x=?, y=?, z=? WHERE char_name=?");+								statement.setInt(1, _npcX);+								statement.setInt(2, _npcY);+								statement.setInt(3, _npcZ);+								statement.setString(4, player.getName());+								statement.execute();+								statement.close();+							}+							catch (SQLException se)+							{+								_log.warning(TvT.class.getSimpleName() + ": " + se);+							}+						}+					}+				}+				_log.info("TvT: Teleport done.");+				cleanTvT();+			}+		}, 20000);+	}++	public static int teamKillsCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamKillsCount.get(index);+	}++	public static void setTeamKillsCount(String teamName, int teamKillsCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamKillsCount.set(index, teamKillsCount);+	}++	public static int teamPlayersCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamPlayersCount.get(index);+	}++	public static void setTeamPlayersCount(String teamName, int teamPlayersCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamPlayersCount.set(index, teamPlayersCount);+	}++	public static long _intervalBetweenMatchs = 0;++	/**+	 * The type of TvT Event+	 * 1 = Manual+	 * 2 = Automatic+	 */+	public static int _eventType = 0;++	private static boolean _inProgress = false;+	private static boolean _finished = false;+	private static boolean _aborted = false;++	/**+	 * Opens All Coliseum Doors+	 */+	private static void closeColiseumDoors()+	{+		Broadcast.announceToOnlinePlayers("Closing Coliseum Doors, TvT event has just started !");+		DoorTable.getInstance().getDoor(24190001).closeMe();// west gate out+		DoorTable.getInstance().getDoor(24190002).closeMe();// west gate in+		DoorTable.getInstance().getDoor(24190003).closeMe();// east gate out+		DoorTable.getInstance().getDoor(24190004).closeMe();// east gate in++		try+		{+			// just to give a lil delay :P+			Thread.sleep(20);+		}+		catch (InterruptedException ie)+		{+			_log.warning(TvT.class.getSimpleName() + ": Error, " + ie.getMessage());+			if (Config.DEVELOPER)+			{+				ie.printStackTrace();+			}+		}+	}++	/**+	 * Open all Coliseum Doors+	 */+	private static void openColiseumDoors()+	{+		Broadcast.announceToOnlinePlayers("Opening Coliseum Doors, TvT event has finished!");+		DoorTable.getInstance().getDoor(24190001).openMe();+		DoorTable.getInstance().getDoor(24190002).openMe();+		DoorTable.getInstance().getDoor(24190003).openMe();+		DoorTable.getInstance().getDoor(24190004).openMe();++	}+	/**+	 * Returns the event type by name.+	 * +	 * @param value+	 * @return+	 */+	public static String getEventTypeByName(int value)+	{+		String type = String.valueOf(value);++		switch (value)+		{+			case 0:+				type = ("None");+			break;++			case 1:+				type = ("Manual");+			break;++			case 2:+				type = ("Automatic");+			break;+		}+		return type;+	}+	/**+	 * just an announcer to send termination messages+	 */+	public static void sendFinalMessages()+	{+		if (_finished && !_aborted)+			Broadcast.announceToOnlinePlayers("TvT: Thank you For Participating At, " + "TVT Event.");+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/model/actor/instance/VillageMaster.java===================================================================--- java/net/sf/l2j/gameserver/model/actor/instance/VillageMaster.java	(revision 3)+++ java/net/sf/l2j/gameserver/model/actor/instance/VillageMaster.java	(working copy)@@ -325,7 +325,13 @@ 					 					if (player.getLevel() < 75) 						allowAddition = false;-					++					if (player._inEventCTF || player._inEventDM || player._inEventTvT)+					{+						player.sendMessage("You may not add a new sub class while being registered on event.");+						return;+					}+ 					if (allowAddition) 					{ 						if (!player.getSubClasses().isEmpty())@@ -349,7 +355,13 @@ 					 */ 					if (allowAddition && !Config.ALT_GAME_SUBCLASS_WITHOUT_QUESTS) 						allowAddition = checkQuests(player);-					++					if (player._inEventCTF || player._inEventDM || player._inEventTvT)+					{+						player.sendMessage("You may not add a new sub class while being registered on event.");+						return;+					}+ 					if (allowAddition && isValidNewSubClass(player, paramOne)) 					{ 						if (!player.addSubClass(paramOne, player.getSubClasses().size() + 1))Index: java/net/sf/l2j/gameserver/model/actor/Npc.java===================================================================--- java/net/sf/l2j/gameserver/model/actor/Npc.java	(revision 3)+++ java/net/sf/l2j/gameserver/model/actor/Npc.java	(working copy)@@ -40,6 +40,10 @@ import net.sf.l2j.gameserver.model.actor.template.NpcTemplate.Race; import net.sf.l2j.gameserver.model.actor.template.NpcTemplate.SkillType; import net.sf.l2j.gameserver.model.entity.Castle;+import net.sf.l2j.gameserver.model.entity.L2Event;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.model.entity.engine.DM;+import net.sf.l2j.gameserver.model.entity.engine.TvT; import net.sf.l2j.gameserver.model.item.instance.ItemInstance; import net.sf.l2j.gameserver.model.item.kind.Item; import net.sf.l2j.gameserver.model.item.kind.Weapon;@@ -103,6 +107,12 @@ 	 	private Castle _castle; 	+	/** Engine Parameters */+	public boolean isEventMob = false, _isEventMobCTF = false, _isCTF_throneSpawn = false, _isCTF_Flag = false;+	public boolean _isEventMobTvT = false;+	public boolean _isEventMobDM = false;+	public String _CTF_FlagTeamName;+	 	/** 	 * Send a packet SocialAction to all L2PcInstance in the _KnownPlayers of the L2Npc and create a new RandomAnimation Task. 	 * @param id the animation id.@@ -356,11 +366,26 @@ 					if (qlsa != null && !qlsa.isEmpty()) 						player.setLastQuestNpcObject(getObjectId()); 					-					List<Quest> qlst = getTemplate().getEventQuests(EventType.ON_FIRST_TALK);-					if (qlst != null && qlst.size() == 1)-						qlst.get(0).notifyFirstTalk(this, player);+					if (isEventMob)+						L2Event.showEventHtml(player, String.valueOf(getObjectId()));+					else if (_isEventMobTvT)+						TvT.showEventHtml(player, String.valueOf(getObjectId()));+					else if (_isEventMobDM)+						DM.showEventHtml(player, String.valueOf(getObjectId()));+					else if (_isEventMobCTF)+						CTF.showEventHtml(player, String.valueOf(getObjectId()));+					else if (_isCTF_Flag && player._inEventCTF)+						CTF.showFlagHtml(player, String.valueOf(getObjectId()), _CTF_FlagTeamName);+					else if (_isCTF_throneSpawn)+						CTF.CheckRestoreFlags(); 					else-						showChatWindow(player);+					{+						List<Quest> qlst = getTemplate().getEventQuests(EventType.ON_FIRST_TALK);+						if (qlst != null && qlst.size() == 1)+							qlst.get(0).notifyFirstTalk(this, player);+						else+							showChatWindow(player);+					} 				} 			} 		}@@ -901,7 +926,7 @@ 						player.setLoto(i, val); 						break; 					}-				+			 			// setting pusshed buttons 			count = 0; 			for (int i = 0; i < 5; i++)@@ -1206,7 +1231,7 @@ 			filename = SevenSigns.SEVEN_SIGNS_HTML_PATH + "rift/GuardianOfBorder.htm"; 		else 			filename = getHtmlPath(npcId, val);-+		 		final NpcHtmlMessage html = new NpcHtmlMessage(getObjectId()); 		html.setFile(filename); 		html.replace("%objectId%", getObjectId());@@ -1275,7 +1300,7 @@ 	{ 		if (!super.doDie(killer)) 			return false;-			+		 		// normally this wouldn't really be needed, but for those few exceptions, 		// we do need to reset the weapons back to the initial templated weapon. 		_currentLHandId = getTemplate().getLeftHand();@@ -1324,7 +1349,7 @@ 		if (quests != null) 			for (Quest quest : quests) 				quest.notifyDecay(this);-			+		 		// Remove the L2Npc from the world when the decay task is launched. 		super.onDecay(); 		Index: java/net/sf/l2j/gameserver/network/clientpackets/RequestUnEquipItem.java===================================================================--- java/net/sf/l2j/gameserver/network/clientpackets/RequestUnEquipItem.java	(revision 1)+++ java/net/sf/l2j/gameserver/network/clientpackets/RequestUnEquipItem.java	(working copy)@@ -26,7 +26,13 @@ 		final Player activeChar = getClient().getActiveChar(); 		if (activeChar == null) 			return;-		++		if (activeChar._haveFlagCTF)+		{+			activeChar.sendMessage("You can't unequip a CTF flag.");+			return;+		}+ 		ItemInstance item = activeChar.getInventory().getPaperdollItemByL2ItemId(_slot); 		if (item == null) 			return;Index: java/net/sf/l2j/gameserver/model/entity/engine/TvT.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/TvT.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/TvT.java	(working copy)@@ -0,0 +1,1767 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++/**+ * @author FBIagent / Fixed By l2jhellas And L2Emu Team+ */+import java.sql.Connection;+import java.sql.PreparedStatement;+import java.sql.ResultSet;+import java.sql.SQLException;+import java.util.ArrayList;+import java.util.List;+import java.util.logging.Level;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.L2DatabaseFactory;+import net.sf.l2j.commons.concurrent.ThreadPool;+import net.sf.l2j.commons.random.Rnd;+import net.sf.l2j.gameserver.datatables.DoorTable;+import net.sf.l2j.gameserver.datatables.ItemTable;+import net.sf.l2j.gameserver.datatables.NpcTable;+import net.sf.l2j.gameserver.datatables.SpawnTable;+import net.sf.l2j.gameserver.model.L2Effect;+import net.sf.l2j.gameserver.model.L2Spawn;+import net.sf.l2j.gameserver.model.actor.Summon;+import net.sf.l2j.gameserver.model.actor.instance.Pet;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.actor.template.NpcTemplate;+import net.sf.l2j.gameserver.model.group.Party;+import net.sf.l2j.gameserver.model.group.Party.MessageType;+import net.sf.l2j.gameserver.model.olympiad.OlympiadManager;+import net.sf.l2j.gameserver.network.clientpackets.Say2;+import net.sf.l2j.gameserver.network.serverpackets.ActionFailed;+import net.sf.l2j.gameserver.network.serverpackets.CreatureSay;+import net.sf.l2j.gameserver.network.serverpackets.MagicSkillUse;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.network.serverpackets.SocialAction;+import net.sf.l2j.gameserver.util.Broadcast;++public class TvT+{+	protected static final Logger _log = Logger.getLogger(TvT.class.getName());+	public static String _eventName = "";+	public static String _eventDesc = "";+	public static String _topTeam = "";+	public static String _joiningLocationName = "";+	public static List<String> _teams = new ArrayList<>();+	public static List<String> _savePlayers = new ArrayList<>();+	public static List<String> _savePlayerTeams = new ArrayList<>();++	public static List<Player> _players = new ArrayList<>();+	public static List<Player> _playersShuffle = new ArrayList<>();+	public static List<Integer> _teamPlayersCount = new ArrayList<>();+	public static List<Integer> _teamKillsCount = new ArrayList<>();+	public static List<Integer> _teamColors = new ArrayList<>();+	public static List<Integer> _teamsX = new ArrayList<>();+	public static List<Integer> _teamsY = new ArrayList<>();+	public static List<Integer> _teamsZ = new ArrayList<>();+	public static boolean _joining = false;+	public static boolean _teleport = false;+	public static boolean _started = false;+	public static boolean _sitForced = false;+	public static L2Spawn _npcSpawn;++	public static int _npcId = 0;+	public static int _npcX = 0;+	public static int _npcY = 0;+	public static int _npcZ = 0;+	public static int _npcHeading = 0;++	public static int _rewardId = 0;+	public static int _rewardAmount = 0;++	public static int _topKills = 0;+	public static int _minlvl = 0;+	public static int _maxlvl = 0;++	public static int _joinTime = 0;+	public static int _eventTime = 0;++	public static int _minPlayers = 0;+	public static int _maxPlayers = 0;++	public static int _playerWon = 0;++	public static void AnnounceToPlayers(Boolean toall, String announce)+	{+		if (toall)+			Broadcast.announceToOnlinePlayers(announce);+		else+		{+			CreatureSay cs = new CreatureSay(0, Say2.ANNOUNCEMENT, "", announce);+			if (_players != null && !_players.isEmpty())+			{+				for (Player player : _players)+				{+					if (player != null && player.isOnline())+						player.sendPacket(cs);+				}+			}+		}+	}++	public static void kickPlayerFromTvt(Player playerToKick)+	{+		if (playerToKick == null)+			return;++		if (_joining)+		{+			_playersShuffle.remove(playerToKick);+			_players.remove(playerToKick);+			playerToKick._inEventTvT = false;+			playerToKick._teamNameTvT = "";+			playerToKick._countTvTkills = 0;+		}+		if (_started || _teleport)+		{+			_playersShuffle.remove(playerToKick);+			playerToKick._inEventTvT = false;+			removePlayer(playerToKick);+			if (playerToKick.isOnline())+			{+				playerToKick.getAppearance().setNameColor(playerToKick._originalNameColorTvT);+				playerToKick.setKarma(playerToKick._originalKarmaTvT);+				playerToKick.setTitle(playerToKick._originalTitleTvT);+				playerToKick.broadcastUserInfo();+				playerToKick.sendMessage("You have been kicked from the TvT.");+				playerToKick.teleToLocation(_npcX, _npcY, _npcZ, 0);+			}+		}+	}++	public static void setNpcPos(Player activeChar)+	{+		_npcX = activeChar.getX();+		_npcY = activeChar.getY();+		_npcZ = activeChar.getZ();+		_npcHeading = activeChar.getHeading();+	}++	public static void setNpcPos(int x, int y, int z)+	{+		_npcX = x;+		_npcY = y;+		_npcZ = z;+	}++	public static void addTeam(String teamName)+	{+		if (!checkTeamOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[addTeam(" + teamName + ")]: checkTeamOk() = false");+			return;+		}++		if (teamName.equals(" "))+			return;++		_teams.add(teamName);+		_teamPlayersCount.add(0);+		_teamKillsCount.add(0);+		_teamColors.add(0);+		_teamsX.add(0);+		_teamsY.add(0);+		_teamsZ.add(0);+	}++	public static boolean checkMaxLevel(int maxlvl)+	{+		return _minlvl < maxlvl;+	}++	public static boolean checkMinLevel(int minlvl)+	{+		return _maxlvl > minlvl;+	}++	/** returns true if participated players is higher or equal then minimum needed players +	 * @param players +	 * @return */+	public static boolean checkMinPlayers(int players)+	{+		return _minPlayers <= players;+	}++	/** returns true if max players is higher or equal then participated players +	 * @param players +	 * @return */+	public static boolean checkMaxPlayers(int players)+	{+		return _maxPlayers > players;+	}++	public static void removeTeam(String teamName)+	{+		if (!checkTeamOk() || _teams.isEmpty())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[removeTeam(" + teamName + ")]: checkTeamOk() = false");+			return;+		}++		if (teamPlayersCount(teamName) > 0)+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[removeTeam(" + teamName + ")]: teamPlayersCount(teamName) > 0");+			return;+		}++		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsZ.remove(index);+		_teamsY.remove(index);+		_teamsX.remove(index);+		_teamColors.remove(index);+		_teamKillsCount.remove(index);+		_teamPlayersCount.remove(index);+		_teams.remove(index);+	}++	public static void setTeamPos(String teamName, Player activeChar)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsX.set(index, activeChar.getX());+		_teamsY.set(index, activeChar.getY());+		_teamsZ.set(index, activeChar.getZ());+	}++	public static void setTeamPos(String teamName, int x, int y, int z)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsX.set(index, x);+		_teamsY.set(index, y);+		_teamsZ.set(index, z);+	}++	public static void setTeamColor(String teamName, int color)+	{+		if (!checkTeamOk())+			return;++		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamColors.set(index, color);+	}++	public static boolean checkTeamOk()+	{+		return !(_started || _teleport || _joining);+	}++	public static void startJoin(Player activeChar)+	{+		if (!startJoinOk())+		{+			activeChar.sendMessage("Event not setted propertly.");+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startJoin(" + activeChar.getName() + ")]: startJoinOk() = false");+			return;+		}+		_joining = true;+		spawnEventNpc(activeChar);+		AnnounceToPlayers(true, _eventName);+		if (Config.TVT_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Join in " + _joiningLocationName + "!");+	}++	public static void startJoin()+	{+		if (!startJoinOk())+		{+			_log.warning(TvT.class.getSimpleName() + ":  Event not setted propertly.");+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startJoin(startJoinOk() = false");+			return;+		}+		_joining = true;+		spawnEventNpc();+		AnnounceToPlayers(true, _eventName);+		if (Config.TVT_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Join in " + _joiningLocationName + "!");+	}++	public static boolean startAutoJoin()+	{+		if (!startJoinOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startJoin]: startJoinOk() = false");+			return false;+		}++		_joining = true;+		spawnEventNpc();+		AnnounceToPlayers(true, _eventName);+		if (Config.TVT_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Join in " + _joiningLocationName + "!");+		return true;+	}++	public static boolean startJoinOk()+	{+		return !(_started || _teleport || _joining || _teams.size() < 2 || _eventName.isEmpty() || _joiningLocationName.isEmpty() || _eventDesc.isEmpty() || _npcId == 0 || _npcX == 0 || _npcY == 0 || _npcZ == 0 || _rewardId == 0 || _rewardAmount == 0 || _teamsX.contains(0) || _teamsY.contains(0) || _teamsZ.contains(0));+	}++	private static void spawnEventNpc(Player activeChar)+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);++			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, _npcHeading);+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobTvT = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  TvT Engine[spawnEventNpc(" + activeChar.getName() + ")]: exception: ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	private static void spawnEventNpc()+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);+			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, _npcHeading);+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobTvT = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  TvT Engine[spawnEventNpc(exception: ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void teleportStart()+	{+		if (!_joining || _started || _teleport)+			return;++		if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && checkMinPlayers(_playersShuffle.size()))+		{+			removeOfflinePlayers();+			shuffleTeams();+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && !checkMinPlayers(_playersShuffle.size()))+		{+			AnnounceToPlayers(true, "Not enough players for event. Min Requested : " + _minPlayers + ", Participating : " + _playersShuffle.size());+			return;+		}++		_joining = false;+		AnnounceToPlayers(false, _eventName + "Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				TvT.sit();++				for (Player player : _players)+				{+					if (player != null)+					{+						if (Config.TVT_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+								Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+								{+									if (e != null)+										e.exit();+								}++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}++						if (Config.TVT_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}++						player.setTitle("Kills: " + player._countTvTkills);+						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameTvT)), _teamsY.get(_teams.indexOf(player._teamNameTvT)), _teamsZ.get(_teams.indexOf(player._teamNameTvT)), 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+	}++	public static boolean teleportAutoStart()+	{+		if (!_joining || _started || _teleport)+			return false;++		if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && checkMinPlayers(_playersShuffle.size()))+		{+			removeOfflinePlayers();+			shuffleTeams();+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && !checkMinPlayers(_playersShuffle.size()))+		{+			AnnounceToPlayers(true, "Not enough players for event. Min Requested : " + _minPlayers + ", Participating : " + _playersShuffle.size());+			return false;+		}++		_joining = false;+		AnnounceToPlayers(false, _eventName + "Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				TvT.sit();++				for (Player player : _players)+				{+					if (player != null)+					{+						if (Config.TVT_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+								Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+								{+									if (e != null)+										e.exit();+								}++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}++						if (Config.TVT_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}+						player.setTitle("Kills: " + player._countTvTkills);+						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameTvT)), _teamsY.get(_teams.indexOf(player._teamNameTvT)), _teamsZ.get(_teams.indexOf(player._teamNameTvT)), 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+		return true;+	}++	public static void startEvent(Player activeChar)+	{+		if (_inProgress)+		{+			activeChar.sendMessage("A TvT event is already in progress, try abort.");+			return;+		}++		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startEvent(" + activeChar.getName() + ")]: startEventOk() = false");+			return;+		}++		_teleport = false;+		sit();++		if (Config.TVT_CLOSE_COLISEUM_DOORS)+			closeColiseumDoors();++		AnnounceToPlayers(false, _eventName + "Started. Go to kill your enemies!");+		_started = true;+		_inProgress = true;+	}++	public static void setJoinTime(int time)+	{+		_joinTime = time;+	}++	public static void setEventTime(int time)+	{+		_eventTime = time;+	}++	public static boolean startAutoEvent()+	{+		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[startEvent]: startEventOk() = false");+			return false;+		}++		_teleport = false;+		sit();++		if (Config.TVT_CLOSE_COLISEUM_DOORS)+			closeColiseumDoors();++		AnnounceToPlayers(false, _eventName + "Started. Go to kill your enemies!");+		_started = true;+		return true;+	}++	public static synchronized void autoEvent()+	{+		_log.info("Starting TvT!");+		if (startAutoJoin())+		{+			_eventType = 2;++			if (_joinTime > 0)+				waiter(_joinTime * 60 * 1000); // minutes for join event+			else if (_joinTime <= 0)+			{+				_log.info("TvT: join time <=0 aborting event.");+				abortEvent();+				return;+			}+			if (teleportAutoStart())+			{+				waiter(30 * 1000); // 30 sec wait time untill start fight after teleported+				if (startAutoEvent())+				{+					_log.log(Level.FINER, "TvT: waiting.....minutes for event time " + TvT._eventTime);++					waiter(_eventTime * 60 * 1000); // minutes for event time+					finishEvent();++					_log.info("TvT: waiting... delay for final messages ");+					waiter(60000);// just a give a delay delay for final messages+					sendFinalMessages();+				}+			}+			else if (!teleportAutoStart())+			{+				abortEvent();+			}+		}+	}++	private synchronized static void waiter(long interval)+	{+		long startWaiterTime = System.currentTimeMillis();+		int seconds = (int) (interval / 1000);++		String npcManager = NpcTable.getInstance().getTemplate(_npcId).getName();++		while (startWaiterTime + interval > System.currentTimeMillis())+		{+			seconds--; // here because we don't want to see two time announce at the same time++			if (_joining || _started || _teleport)+			{+				switch (seconds)+				{+					case 3600: // 1 hour left+						if (_joining)+						{+							AnnounceToPlayers(true, "TvT: Joinable in " + _joiningLocationName + "!");+							AnnounceToPlayers(true, "TvT: " + seconds / 60 / 60 + " hour(s) till registration ends!");+							if (Config.TVT_ANNOUNCE_REGISTRATION_LOC_NPC)+								AnnounceToPlayers(true, "TvT: Registration Period is Active in " + _joiningLocationName + " ! at Npc " + npcManager);+						}+						else if (_started)+							AnnounceToPlayers(false, "TvT: " + seconds / 60 / 60 + " hour(s) till event ends!");++					break;+					case 1800: // 30 minutes left+					case 900: // 15 minutes left+					case 600: // 10 minutes left+					case 300: // 5 minutes left+					case 60: // 1 minute left+						if (_joining)+						{+							removeOfflinePlayers();+							AnnounceToPlayers(true, "TvT: Joinable in " + _joiningLocationName + "!");+							AnnounceToPlayers(true, "TvT: " + seconds / 60 + " minute(s) till registration ends!");+							if (Config.TVT_ANNOUNCE_REGISTRATION_LOC_NPC)+								Broadcast.announceToOnlinePlayers("TvT: Registration Period is Active in " + _joiningLocationName + " ! at Npc " + npcManager);+						}+						else if (_started)+							AnnounceToPlayers(false, "TvT: " + seconds / 60 + " minute(s) till event ends!");++					break;+					case 30: // 30 seconds left+					case 10: // 10 seconds left+					case 3: // 3 seconds left+					case 2: // 2 seconds left+					case 1: // 1 seconds left+						if (_joining)+							AnnounceToPlayers(true, "TvT: " + seconds + " second(s) till registration ends!");+						else if (_teleport)+							AnnounceToPlayers(false, "TvT: " + seconds + " seconds(s) till fight starts!");+						else if (_started)+							AnnounceToPlayers(false, "TvT: " + seconds + " second(s) till event ends!");++					break;+				}+			}++			long startOneSecondWaiterStartTime = System.currentTimeMillis();++			// only the try catch with Thread.sleep(1000) give bad countdown on high wait times+			while (startOneSecondWaiterStartTime + 1000 > System.currentTimeMillis())+			{+				try+				{+					Thread.sleep(1);+				}+				catch (InterruptedException ie)+				{++				}+			}+		}+	}++	private static boolean startEventOk()+	{+		if (_joining || !_teleport || _started)+			return false;++		if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+		{+			if (_teamPlayersCount.contains(0))+				return false;+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+		{+			List<Player> playersShuffleTemp = new ArrayList<>();+			int loopCount = 0;++			loopCount = _playersShuffle.size();++			for (int i = 0; i < loopCount; i++)+			{+				if (_playersShuffle != null)+					playersShuffleTemp.add(_playersShuffle.get(i));+			}++			_playersShuffle = playersShuffleTemp;+			playersShuffleTemp.clear();+		}++		return true;+	}++	public static void shuffleTeams()+	{+		int teamCount = 0, playersCount = 0;++		for (;;)+		{+			if (_playersShuffle.isEmpty())+				break;++			int playerToAddIndex = Rnd.nextInt(_playersShuffle.size());+			Player player = null;+			player = _playersShuffle.get(playerToAddIndex);+			player._originalNameColorTvT = player.getAppearance().getNameColor();+			player._originalTitleTvT = player.getTitle();+			player._originalKarmaTvT = player.getKarma();++			_players.add(player);+			_players.get(playersCount)._teamNameTvT = _teams.get(teamCount);+			_savePlayers.add(_players.get(playersCount).getName());+			_savePlayerTeams.add(_teams.get(teamCount));+			playersCount++;++			if (teamCount == _teams.size() - 1)+				teamCount = 0;+			else+				teamCount++;++			_playersShuffle.remove(playerToAddIndex);+		}+	}++	public static void setUserData()+	{+		for (Player player : _players)+		{+			player.getAppearance().setNameColor(_teamColors.get(_teams.indexOf(player._teamNameTvT)));+			player.setKarma(0);++			if (Config.TVT_AURA)+			{+				if (_teams.size() >= 2)+					player.setTeam(_teams.indexOf(player._teamNameTvT) + 1);+			}+			player.broadcastUserInfo();+		}+	}++	public static void finishEvent()+	{+		if (!finishEventOk())+		{+			if (Config.DEBUG)+				_log.log(Level.FINER, "TvT Engine[finishEvent]: finishEventOk() = false");+			return;+		}++		_started = false;+		unspawnEventNpc();+		processTopTeam();++		if (_topKills == 0)+			AnnounceToPlayers(true, _eventName + "No team wins the match(nobody killed).");+		else+		{+			AnnounceToPlayers(true, _eventName + " " + _topTeam + "'s win the match! " + _topKills + " kills.");+			rewardTeam(_topTeam);+			playKneelAnimation(_topTeam);+		}++		if (Config.TVT_ANNOUNCE_TEAM_STATS)+		{+			AnnounceToPlayers(true, _eventName + " Team Statistics:");+			for (String team : _teams)+			{+				int _kills = teamKillsCount(team);+				AnnounceToPlayers(true, "Team: " + team + " - Kills: " + _kills);+			}+		}++		teleportFinish();+	}++	// show losers and winners animations+	public static void playKneelAnimation(String teamName)+	{+		for (Player player : _players)+		{+			if (player != null)+			{+				if (!player._teamNameTvT.equals(teamName))+					player.broadcastPacket(new SocialAction(player, 7),2000);+				else if (player._teamNameTvT.equals(teamName))+					player.broadcastPacket(new SocialAction(player, 3),2000);+			}+		}+	}++	private static boolean finishEventOk()+	{+		if (!_started)+			return false;++		_inProgress = false;+		if (Config.TVT_CLOSE_COLISEUM_DOORS)+			openColiseumDoors();++		return true;+	}++	public static void processTopTeam()+	{+		for (String team : _teams)+		{+			if (teamKillsCount(team) > _topKills)+			{+				_topTeam = team;+				_topKills = teamKillsCount(team);+			}+		}+	}++	public static void rewardTeam(String teamName)+	{+		for (Player player : _players)+		{+			if (player != null && player.isOnline() && player._inEventTvT)+			{+				if (player._teamNameTvT.equals(teamName) && (player._countTvTkills > 0 || Config.TVT_PRICE_NO_KILLS))+				{+					player.addItem("TvT: " + _eventName, _rewardId, _rewardAmount, player, true);++					_playerWon = 1;++					NpcHtmlMessage nhm = new NpcHtmlMessage(5);+					StringBuilder replyMSG = new StringBuilder("");++					replyMSG.append("<html><body>Your team wins the event. Look in your inventory for the reward.</body></html>");++					nhm.setHtml(replyMSG.toString());+					player.sendPacket(nhm);++					// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+					player.sendPacket(ActionFailed.STATIC_PACKET);+				}+			}+		}+	}++	public static void abortEvent()+	{+		if (!_joining && !_teleport && !_started)+			return;+		if (_joining && !_teleport && !_started)+		{+			unspawnEventNpc();+			cleanTvT();+			_joining = false;+			AnnounceToPlayers(true, _eventName + "Match aborted!");+			return;+		}+		_joining = false;+		_teleport = false;+		_started = false;+		_inProgress = false;+		unspawnEventNpc();+		AnnounceToPlayers(true, _eventName + "Match aborted!");+		teleportFinish();+	}++	public static void sit()+	{+		_sitForced = !_sitForced;++		for (Player player : _players)+		{+			if (player != null)+			{+				if (_sitForced)+				{+					player.stopMove(null);+					player.abortAttack();+					player.abortCast();++					if (!player.isSitting())+						player.sitDown();+				}+				else+				{+					if (player.isSitting())+						player.standUp();+				}+			}+		}+	}++	public static void dumpData()+	{+		_log.info("");+		_log.info("");++		if (!_joining && !_teleport && !_started)+		{+			_log.info("<<---------------------------------->>");+			_log.info(">> TvT Engine infos dump (INACTIVE) <<");+			_log.info("<<--^----^^-----^----^^------^^----->>");+		}+		else if (_joining && !_teleport && !_started)+		{+			_log.info("<<--------------------------------->>");+			_log.info(">> TvT Engine infos dump (JOINING) <<");+			_log.info("<<--^----^^-----^----^^------^----->>");+		}+		else if (!_joining && _teleport && !_started)+		{+			_log.info("<<---------------------------------->>");+			_log.info(">> TvT Engine infos dump (TELEPORT) <<");+			_log.info("<<--^----^^-----^----^^------^^----->>");+		}+		else if (!_joining && !_teleport && _started)+		{+			_log.info("<<--------------------------------->>");+			_log.info(">> TvT Engine infos dump (STARTED) <<");+			_log.info("<<--^----^^-----^----^^------^----->>");+		}++		_log.info("Name: " + _eventName);+		_log.info("Desc: " + _eventDesc);+		_log.info("Join location: " + _joiningLocationName);+		_log.info("Min lvl: " + _minlvl);+		_log.info("Max lvl: " + _maxlvl);+		_log.info("");+		_log.info("##########################");+		_log.info("# _teams(Vector<String>) #");+		_log.info("##########################");++		for (String team : _teams)+			_log.info(team + " Kills Done :" + _teamKillsCount.get(_teams.indexOf(team)));++		if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+		{+			_log.info("");+			_log.info("#########################################");+			_log.info("# _playersShuffle(Vector<Player>) #");+			_log.info("#########################################");++			for (Player player : _playersShuffle)+			{+				if (player != null)+					_log.info("Name: " + player.getName());+			}+		}++		_log.info("");+		_log.info("##################################");+		_log.info("# _players(Vector<Player>) #");+		_log.info("##################################");++		for (Player player : _players)+		{+			if (player != null)+				_log.info("Name: " + player.getName() + "   Team: " + player._teamNameTvT + "  Kills Done:" + player._countTvTkills);+		}++		_log.info("");+		_log.info("#####################################################################");+		_log.info("# _savePlayers(Vector<String>) and _savePlayerTeams(Vector<String>) #");+		_log.info("#####################################################################");++		for (String player : _savePlayers)+			_log.info("Name: " + player + "	Team: " + _savePlayerTeams.get(_savePlayers.indexOf(player)));++		_log.info("");+		_log.info("");+	}++	public static void loadData()+	{+		_eventName = "";+		_eventDesc = "";+		_topTeam = "";+		_joiningLocationName = "";+		_teams = new ArrayList<>();+		_savePlayers = new ArrayList<>();+		_savePlayerTeams = new ArrayList<>();+		_players = new ArrayList<>();+		_playersShuffle = new ArrayList<>();+		_teamPlayersCount = new ArrayList<>();+		_teamKillsCount = new ArrayList<>();+		_teamColors = new ArrayList<>();+		_teamsX = new ArrayList<>();+		_teamsY = new ArrayList<>();+		_teamsZ = new ArrayList<>();+		_joining = false;+		_teleport = false;+		_started = false;+		_sitForced = false;+		_npcId = 0;+		_npcX = 0;+		_npcY = 0;+		_npcZ = 0;+		_npcHeading = 0;+		_rewardId = 0;+		_rewardAmount = 0;+		_topKills = 0;+		_minlvl = 0;+		_maxlvl = 0;+		_joinTime = 0;+		_eventTime = 0;+		_minPlayers = 0;+		_maxPlayers = 0;+		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;+			ResultSet rs;+			statement = con.prepareStatement("SELECT * FROM tvt");+			rs = statement.executeQuery();++			int teams = 0;++			while (rs.next())+			{+				_eventName = rs.getString("eventName");+				_eventDesc = rs.getString("eventDesc");+				_joiningLocationName = rs.getString("joiningLocation");+				_minlvl = rs.getInt("minlvl");+				_maxlvl = rs.getInt("maxlvl");+				_npcId = rs.getInt("npcId");+				_npcX = rs.getInt("npcX");+				_npcY = rs.getInt("npcY");+				_npcZ = rs.getInt("npcZ");+				_npcHeading = rs.getInt("npcHeading");+				_rewardId = rs.getInt("rewardId");+				_rewardAmount = rs.getInt("rewardAmount");+				teams = rs.getInt("teamsCount");+				_joinTime = rs.getInt("joinTime");+				_eventTime = rs.getInt("eventTime");+				_minPlayers = rs.getInt("minPlayers");+				_maxPlayers = rs.getInt("maxPlayers");+			}+			rs.close();+			statement.close();++			int index = -1;+			if (teams > 0)+				index = 0;+			while (index < teams && index > -1)+			{+				statement = con.prepareStatement("SELECT * FROM tvt_teams WHERE teamId=?");+				statement.setInt(1, index);+				rs = statement.executeQuery();+				while (rs.next())+				{+					_teams.add(rs.getString("teamName"));+					_teamPlayersCount.add(0);+					_teamKillsCount.add(0);+					_teamColors.add(0);+					_teamsX.add(0);+					_teamsY.add(0);+					_teamsZ.add(0);+					_teamsX.set(index, rs.getInt("teamX"));+					_teamsY.set(index, rs.getInt("teamY"));+					_teamsZ.set(index, rs.getInt("teamZ"));+					_teamColors.set(index, rs.getInt("teamColor"));+				}+				index++;+				rs.close();+				statement.close();+			}+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  Exception: TvT.loadData(): ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void saveData()+	{+		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;++			statement = con.prepareStatement("DELETE FROM tvt");+			statement.execute();+			statement.close();++			statement = con.prepareStatement("INSERT INTO tvt (eventName, eventDesc, joiningLocation, minlvl, maxlvl, npcId, npcX, npcY, npcZ, npcHeading, rewardId, rewardAmount, teamsCount, joinTime, eventTime, minPlayers, maxPlayers) VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?)");+			statement.setString(1, _eventName);+			statement.setString(2, _eventDesc);+			statement.setString(3, _joiningLocationName);+			statement.setInt(4, _minlvl);+			statement.setInt(5, _maxlvl);+			statement.setInt(6, _npcId);+			statement.setInt(7, _npcX);+			statement.setInt(8, _npcY);+			statement.setInt(9, _npcZ);+			statement.setInt(10, _npcHeading);+			statement.setInt(11, _rewardId);+			statement.setInt(12, _rewardAmount);+			statement.setInt(13, _teams.size());+			statement.setInt(14, _joinTime);+			statement.setInt(15, _eventTime);+			statement.setInt(16, _minPlayers);+			statement.setInt(17, _maxPlayers);+			statement.execute();+			statement.close();++			statement = con.prepareStatement("DELETE FROM tvt_teams");+			statement.execute();+			statement.close();++			for (String teamName : _teams)+			{+				int index = _teams.indexOf(teamName);++				if (index == -1)+					return;+				statement = con.prepareStatement("INSERT INTO tvt_teams (teamId ,teamName, teamX, teamY, teamZ, teamColor) VALUES (?, ?, ?, ?, ?, ?)");+				statement.setInt(1, index);+				statement.setString(2, teamName);+				statement.setInt(3, _teamsX.get(index));+				statement.setInt(4, _teamsY.get(index));+				statement.setInt(5, _teamsZ.get(index));+				statement.setInt(6, _teamColors.get(index));+				statement.execute();+				statement.close();+			}+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  Exception: TvT.saveData(): ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void showEventHtml(Player eventPlayer, String objectId)+	{+		try+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++			StringBuilder replyMSG = new StringBuilder("<html><body>");+			replyMSG.append("TvT Match<br><br><br>");+			replyMSG.append("Current event...<br1>");+			replyMSG.append("    ... name:&nbsp;<font color=\"00FF00\">" + _eventName + "</font><br1>");+			replyMSG.append("    ... description:&nbsp;<font color=\"00FF00\">" + _eventDesc + "</font><br>");+			if (Config.TVT_ANNOUNCE_REWARD)+				replyMSG.append("    ... reward: (" + _rewardAmount + ") " + ItemTable.getInstance().getTemplate(_rewardId).getName() + "<br>");++			if (!_started && !_joining)+				replyMSG.append("<center>Wait till the admin/gm start the participation.</center>");+			else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && !checkMaxPlayers(_playersShuffle.size()))+			{+				if (!TvT._started)+					replyMSG.append("<font color=\"FFFF00\">The event has reached its maximum capacity.</font><br>Keep checking, someone may crit and you can steal their spot.");+			}+			else if (eventPlayer.isCursedWeaponEquipped() && !Config.TVT_JOIN_CURSED)+				replyMSG.append("<font color=\"FFFF00\">You can't participate in this event with a cursed Weapon.</font><br>");+			else if (!_started && _joining && eventPlayer.getLevel() >= _minlvl && eventPlayer.getLevel() <= _maxlvl)+			{+				if (_players.contains(eventPlayer) || checkShufflePlayers(eventPlayer))+				{+					if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+						replyMSG.append("You are already participating in team <font color=\"LEVEL\">" + eventPlayer._teamNameTvT + "</font><br><br>");+					else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+						replyMSG.append("You are already participating!<br><br>");++					replyMSG.append("<table border=\"0\"><tr>");+					replyMSG.append("<td width=\"200\">Wait till event start or</td>");+					replyMSG.append("<td width=\"60\"><center><button value=\"remove\" action=\"bypass -h npc_" + objectId + "_tvt_player_leave\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></center></td>");+					replyMSG.append("<td width=\"100\">your participation!</td>");+					replyMSG.append("</tr></table>");+				}+				else+				{+					replyMSG.append("You want to participate in the event?<br><br>");+					replyMSG.append("<td width=\"200\">Your level : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Min level : <font color=\"00FF00\">" + _minlvl + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Max level : <font color=\"00FF00\">" + _maxlvl + "</font></td><br><br>");++					if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+					{+						replyMSG.append("<center><table border=\"0\">");++						for (String team : _teams)+						{+							replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font>&nbsp;(" + teamPlayersCount(team) + " joined)</td>");+							replyMSG.append("<td width=\"60\"><button value=\"Join\" action=\"bypass -h npc_" + objectId + "_tvt_player_join " + team + "\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td></tr>");+						}++						replyMSG.append("</table></center>");+					}+					else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+					{+						replyMSG.append("<center><table border=\"0\">");++						for (String team : _teams)+							replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font></td>");++						replyMSG.append("</table></center><br>");++						replyMSG.append("<button value=\"Join\" action=\"bypass -h npc_" + objectId + "_tvt_player_join eventShuffle\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\">");+						replyMSG.append("Teams will be randomly generated!");+					}+				}+			}+			else if (_started && !_joining)+				replyMSG.append("<center>TvT match is in progress.</center>");+			else if (eventPlayer.getLevel() < _minlvl || eventPlayer.getLevel() >= _maxlvl)+			{+				replyMSG.append("Your level : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font><br>");+				replyMSG.append("Min level : <font color=\"00FF00\">" + _minlvl + "</font><br>");+				replyMSG.append("Max level : <font color=\"00FF00\">" + _maxlvl + "</font><br><br>");+				replyMSG.append("<font color=\"FFFF00\">You can't participate in this event.</font><br>");+			}+			// Show how many players joined & how many are still needed to join+			replyMSG.append("<br>There are " + _playersShuffle.size() + " player(s) participating in this event.<br>");+			if (_joining)+			{+				if (_playersShuffle.size() < _minPlayers)+				{+					int playersNeeded = _minPlayers - _playersShuffle.size();+					replyMSG.append("The event will not start unless " + playersNeeded + " more player(s) joins!");+				}+			}+			replyMSG.append("</body></html>");+			adminReply.setHtml(replyMSG.toString());+			eventPlayer.sendPacket(adminReply);++			// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+			eventPlayer.sendPacket(ActionFailed.STATIC_PACKET);+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  TvT Engine[showEventHtlm(" + eventPlayer.getName() + ", " + objectId + ")]: exception");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static void addPlayer(Player player, String teamName)+	{+		if (!addPlayerOk(teamName, player))+			return;++		if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+		{+			player._teamNameTvT = teamName;+			_players.add(player);+			setTeamPlayersCount(teamName, teamPlayersCount(teamName) + 1);+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+			_playersShuffle.add(player);++		player._inEventTvT = true;+		player._countTvTkills = 0;++		// notify player that he signed up in event+		NpcHtmlMessage html = new NpcHtmlMessage(1);+		html.setFile("data/html/mods/Participation.htm");+		player.sendPacket(html);++		if (Config.TVT_ANNOUNCE_SIGNUPS)+			Broadcast.announceToOnlinePlayers("Player " + player.getName() + " has Signed Up in TvT!");+	}++	public synchronized static void removeOfflinePlayers()+	{+		try+		{+			if (_playersShuffle == null || _playersShuffle.isEmpty())+				return;+			for (Player player : _playersShuffle)+			{+				if (player == null)+					_playersShuffle.remove(player);+				else if (player.isOnline() || player.isInJail())+					removePlayer(player);+				if (_playersShuffle.size() == 0 || _playersShuffle.isEmpty())+					break;+			}+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ": TVT unknown error");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}+	}++	public static boolean checkShufflePlayers(Player eventPlayer)+	{+		try+		{+			for (Player player : _playersShuffle)+			{+				if (player == null || player.isOnline())+				{+					_playersShuffle.remove(player);+					eventPlayer._inEventTvT = false;+					continue;+				}+				else if (player.getObjectId() == eventPlayer.getObjectId())+				{+					eventPlayer._inEventTvT = true;+					eventPlayer._countTvTkills = 0;+					return true;+				}+				// this 1 is incase player got new objectid after DC or reconnect+				else if (player.getName().equals(eventPlayer.getName()))+				{+					_playersShuffle.remove(player);+					_playersShuffle.add(eventPlayer);+					eventPlayer._inEventTvT = true;+					eventPlayer._countTvTkills = 0;+					return true;+				}+			}+		}+		catch (Exception e)+		{+		}+		return false;+	}++	public static boolean addPlayerOk(String teamName, Player eventPlayer)+	{+		try+		{+			if(OlympiadManager.getInstance().isRegisteredInComp(eventPlayer) || eventPlayer.isInOlympiadMode() || eventPlayer.getOlympiadGameId() >0)+			{+				eventPlayer.sendMessage("You can't register while you are in olympiad!");+				return false;+			}+			if (checkShufflePlayers(eventPlayer) || eventPlayer._inEventTvT)+			{+				eventPlayer.sendMessage("You are already participating in the event!");+				return false;+			}+			if (eventPlayer._inEventCTF || eventPlayer._inEventDM || eventPlayer._inEventVIP)+			{+				eventPlayer.sendMessage("You are already participating in another event!");+				return false;+			}++			for (Player player : _players)+			{+				if (player.getObjectId() == eventPlayer.getObjectId())+				{+					eventPlayer.sendMessage("You are already participating in the event!");+					return false;+				}+				else if (player.getName() == eventPlayer.getName())+				{+					eventPlayer.sendMessage("You are already participating in the event!");+					return false;+				}+			}+			if (_players.contains(eventPlayer))+			{+				eventPlayer.sendMessage("You are already participating in the event!");+				return false;+			}+			if (CTF._savePlayers.contains(eventPlayer.getName()))+			{+				eventPlayer.sendMessage("You are already participating in another event!");+				return false;+			}+		}+		catch (Exception e)+		{+			_log.warning(TvT.class.getSimpleName() + ":  TvT Engine exception: ");+			if (Config.DEVELOPER)+				e.printStackTrace();+		}++		if (Config.TVT_EVEN_TEAMS.equals("NO"))+			return true;+		else if (Config.TVT_EVEN_TEAMS.equals("BALANCE"))+		{+			boolean allTeamsEqual = true;+			int countBefore = -1;++			for (int playersCount : _teamPlayersCount)+			{+				if (countBefore == -1)+					countBefore = playersCount;++				if (countBefore != playersCount)+				{+					allTeamsEqual = false;+					break;+				}++				countBefore = playersCount;+			}++			if (allTeamsEqual)+				return true;++			countBefore = Integer.MAX_VALUE;++			for (int teamPlayerCount : _teamPlayersCount)+			{+				if (teamPlayerCount < countBefore)+					countBefore = teamPlayerCount;+			}++			List<String> joinableTeams = new ArrayList<>();++			for (String team : _teams)+			{+				if (teamPlayersCount(team) == countBefore)+					joinableTeams.add(team);+			}++			if (joinableTeams.contains(teamName))+				return true;+		}+		else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+			return true;++		eventPlayer.sendMessage("Too many players in team \"" + teamName + "\"");+		return false;+	}++	public static synchronized void addDisconnectedPlayer(Player player)+	{+		if ((Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && (_teleport || _started)) || (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE") && (_teleport || _started)))+		{+			if (Config.TVT_ON_START_REMOVE_ALL_EFFECTS)+			{+				for (L2Effect e : player.getAllEffects())+				{+					if (e != null)+						e.exit();+				}+			}++			player._teamNameTvT = _savePlayerTeams.get(_savePlayers.indexOf(player.getName()));+			for (Player p : _players)+			{+				if (p == null)+					continue;+				// check by name incase player got new objectId+				else if (p.getName().equals(player.getName()))+				{+					player._originalNameColorTvT = player.getAppearance().getNameColor();+					player._originalTitleTvT = player.getTitle();+					player._originalKarmaTvT = player.getKarma();+					player._inEventTvT = true;+					player._countTvTkills = p._countTvTkills;+					_players.remove(p); // removing old object id from vector+					_players.add(player); // adding new objectId to vector+					break;+				}+			}++			player.getAppearance().setNameColor(_teamColors.get(_teams.indexOf(player._teamNameTvT)));+			player.setKarma(0);+			if (Config.TVT_AURA)+			{+				if (_teams.size() >= 2)+					player.setTeam(_teams.indexOf(player._teamNameTvT) + 1);+			}+			player.broadcastUserInfo();+			player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameTvT)), _teamsY.get(_teams.indexOf(player._teamNameTvT)), _teamsZ.get(_teams.indexOf(player._teamNameTvT)), 0);+		}+	}++	public static void removePlayer(Player player)+	{+		if (player._inEventTvT)+		{+			if (!_joining)+			{+				player.getAppearance().setNameColor(player._originalNameColorTvT);+				player.setTitle(player._originalTitleTvT);+				player.setKarma(player._originalKarmaTvT);+				if (Config.TVT_AURA)+				{+					if (_teams.size() >= 2)+						player.setTeam(0);// clear aura :P+				}+				player.broadcastUserInfo();+			}+			player._teamNameTvT = "";+			player._countTvTkills = 0;+			player._inEventTvT = false;++			if ((Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE")) && _players.contains(player))+			{+				setTeamPlayersCount(player._teamNameTvT, teamPlayersCount(player._teamNameTvT) - 1);+				_players.remove(player);+			}+			else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE") && (!_playersShuffle.isEmpty() && _playersShuffle.contains(player)))+				_playersShuffle.remove(player);+		}+	}++	public static void cleanTvT()+	{+		_log.info("TvT: Cleaning players.");+		for (Player player : _players)+		{+			if (player != null)+			{+				removePlayer(player);+				if (_savePlayers.contains(player.getName()))+					_savePlayers.remove(player.getName());+				player._inEventTvT = false;+			}+		}+		if (_playersShuffle != null && !_playersShuffle.isEmpty())+		{+			for (Player player : _playersShuffle)+			{+				if (player != null)+					player._inEventTvT = false;+			}+		}+		_log.info("TvT: Cleaning teams.");+		for (String team : _teams)+		{+			int index = _teams.indexOf(team);++			_teamPlayersCount.set(index, 0);+			_teamKillsCount.set(index, 0);+		}++		_topKills = 0;+		_topTeam = "";+		_players.clear();+		_playersShuffle.clear();+		_savePlayers.clear();+		_savePlayerTeams.clear();+		_log.info("Cleaning TvT done.");+	}++	public static void unspawnEventNpc()+	{+		if (_npcSpawn == null)+			return;++		_npcSpawn.getNpc().deleteMe();+		_npcSpawn.setRespawnState(false);+		SpawnTable.getInstance().deleteSpawn(_npcSpawn, true);+	}++	public static void teleportFinish()+	{+		AnnounceToPlayers(false, _eventName + "Teleport back to participation NPC in 20 seconds!");++		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				for (Player player : _players)+				{+					if (player != null)+					{+						if (player.isOnline())+							player.teleToLocation(_npcX, _npcY, _npcZ, 0);+						else+						{+							try (Connection con = L2DatabaseFactory.getInstance().getConnection())+							{+								PreparedStatement statement = con.prepareStatement("UPDATE characters SET x=?, y=?, z=? WHERE char_name=?");+								statement.setInt(1, _npcX);+								statement.setInt(2, _npcY);+								statement.setInt(3, _npcZ);+								statement.setString(4, player.getName());+								statement.execute();+								statement.close();+							}+							catch (SQLException se)+							{+								_log.warning(TvT.class.getSimpleName() + ": " + se);+							}+						}+					}+				}+				_log.info("TvT: Teleport done.");+				cleanTvT();+			}+		}, 20000);+	}++	public static int teamKillsCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamKillsCount.get(index);+	}++	public static void setTeamKillsCount(String teamName, int teamKillsCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamKillsCount.set(index, teamKillsCount);+	}++	public static int teamPlayersCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamPlayersCount.get(index);+	}++	public static void setTeamPlayersCount(String teamName, int teamPlayersCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamPlayersCount.set(index, teamPlayersCount);+	}++	public static long _intervalBetweenMatchs = 0;++	/**+	 * The type of TvT Event+	 * 1 = Manual+	 * 2 = Automatic+	 */+	public static int _eventType = 0;++	private static boolean _inProgress = false;+	private static boolean _finished = false;+	private static boolean _aborted = false;++	/**+	 * Opens All Coliseum Doors+	 */+	private static void closeColiseumDoors()+	{+		Broadcast.announceToOnlinePlayers("Closing Coliseum Doors, TvT event has just started !");+		DoorTable.getInstance().getDoor(24190001).closeMe();// west gate out+		DoorTable.getInstance().getDoor(24190002).closeMe();// west gate in+		DoorTable.getInstance().getDoor(24190003).closeMe();// east gate out+		DoorTable.getInstance().getDoor(24190004).closeMe();// east gate in++		try+		{+			// just to give a lil delay :P+			Thread.sleep(20);+		}+		catch (InterruptedException ie)+		{+			_log.warning(TvT.class.getSimpleName() + ": Error, " + ie.getMessage());+			if (Config.DEVELOPER)+			{+				ie.printStackTrace();+			}+		}+	}++	/**+	 * Open all Coliseum Doors+	 */+	private static void openColiseumDoors()+	{+		Broadcast.announceToOnlinePlayers("Opening Coliseum Doors, TvT event has finished!");+		DoorTable.getInstance().getDoor(24190001).openMe();+		DoorTable.getInstance().getDoor(24190002).openMe();+		DoorTable.getInstance().getDoor(24190003).openMe();+		DoorTable.getInstance().getDoor(24190004).openMe();++	}+	/**+	 * Returns the event type by name.+	 * +	 * @param value+	 * @return+	 */+	public static String getEventTypeByName(int value)+	{+		String type = String.valueOf(value);++		switch (value)+		{+			case 0:+				type = ("None");+			break;++			case 1:+				type = ("Manual");+			break;++			case 2:+				type = ("Automatic");+			break;+		}+		return type;+	}+	/**+	 * just an announcer to send termination messages+	 */+	public static void sendFinalMessages()+	{+		if (_finished && !_aborted)+			Broadcast.announceToOnlinePlayers("TvT: Thank you For Participating At, " + "TVT Event.");+	}+}\ No newline at end of fileIndex: config/events.properties===================================================================--- config/events.properties	(revision 2)+++ config/events.properties	(working copy)@@ -1,3 +1,144 @@+#==================#+#    TVT Event     #+#==================#+#If yes the event will start automatically the give times+TvTAutomatedEvent = True+#What times should the event start+TvTStartUpTimes = 15:50++# Options:+# - NO = not even teams.  +# - BALANCE : Players can only join team with lowest player count.  +# - SHUFFLE : Players can only participate to the event and not direct to a team. Teams will be schuffeled in teleporting teams.  +TvTEvenTeams = SHUFFLE++# players there not participated in tvt can target tvt participants?+TvTAllowInterference = False++# tvt participants can use potions?+TvTAllowPotions = False++# tvt participants can summon by item?+TvTAllowSummon = False++# remove all effects of tvt participants on event start?+TvTOnStartRemoveAllEffects = True++# unsummon pet of tvt participants on event start?+TvTOnStartUnsummonPet = True++# on revive participants regain full hp/mp/cp ?+TvTReviveRecovery = True++# announce all team statistics+TvTAnnounceTeamStats = True++# start auto event on server boot?+TvTAutoStartUpOnBoot = False++# Only reads if "TvTAutoStartUpOnBoot = true"+# here you can set the time that server will wait for start first event on boot+# default = 10 (time in minutes)+FirstEventDelay = 5++# we must close coliseum doors on tvt start up?+TvTCloseColiseumDoors = True++# allow/disallow team1 players to heal enemy team+TvTAllowEnemyHealing = False++# Same team members can use skills each other?+TvTAllowTeamCasting = False++# Same team members can attack each other?+TvTAllowTeamAttacking = False++# if true announce to all players the loc and npc name.+TvTAnnounceLocNpc = True++# if true announce to all players who is participating.+TvTAnnounceSignUp = False++# give price with 0 kills+TvTPriceNoKills = False++# players with cursed weapon are allowed to join ?+TvTJoinWithCursedWeapon = True++# Delay on revive when dead, NOTE: 20000 equals to 20 seconds, minimum 1000 (1 second)+TVTReviveDelay = 20000++# place an aura on participants team ?+TvTAura = True++# announce reward+TvTAnnounceReward = True++#==================#+#    CTF Engine    #+#==================#+#If yes the event will start automatically the give times+CTFAutomatedEvent = True+#What times should the event start+CTFStartUpTimes = 17:00,18:00,19:00++# CTFEvenTeams = NO|BALANCE|SHUFFLE+# NO means: not even teams.+# BALANCE means: Players can only join team with lowest player count.+# SHUFFLE means: Players can only participate to the event and not direct to a team. Teams will be shuffled on teams teleport.+CTFEvenTeams = SHUFFLE++# Players that are not participating in CTF can target CTF participants?+CTFAllowInterference = False++# CTF participants can use potion's?+CTFAllowPotions = False++# CTF participants can summon by item?+CTFAllowSummon = False++# Remove all effects of CTF participants on event start?+CTFOnStartRemoveAllEffects = True++# Unsummon pet of CTF participants on event start?+CTFOnStartUnsummonPet = True++# On revive participants regain full HP/MP/CP?+CTFReviveRecovery = False++# Announce all team statistics+CTFAnnounceTeamStats = False++# Announce reward+CTFAnnounceReward = False++# Players with cursed weapon are allowed to join?+CTFJoinWithCursedWeapon = True++# Delay on revive when dead, NOTE: 20000 equals to 20 seconds, minimum 1000 (1 second)+CTFReviveDelay = 20000++#==================#+#     DM Engine    #+#==================#+# players there not participated in DM can target DM participants?+DMAllowInterference = True++# DM participants can use potion's?+DMAllowPotions = False++# DM participants can summon by item?+DMAllowSummon = False++# remove all effects of DM participants on event start?  +DMOnStartRemoveAllEffects = True++# unsummon pet of DM participants on event start?+DMOnStartUnsummonPet = True++# Delay on revive when dead, NOTE: 20000 equals to 20 seconds, minimum 1000 (1 second)+DMReviveDelay = 20000+ #============================================================= #          Character Killing Monuments (by paytaly) #=============================================================@@ -35,6 +176,10 @@ # Default: FFFFFF (white) CKMPKNpcNameColor = FFFFFF +# Reward Item Top PvP & Pk+RewardItemId = 3470+RewardAmmount = 1+  #============================================================= #                          Olympiad #=============================================================Index: java/net/sf/l2j/Config.java===================================================================--- java/net/sf/l2j/Config.java	(revision 3)+++ java/net/sf/l2j/Config.java	(working copy)@@ -42,6 +42,7 @@ 	// -------------------------------------------------- 	// RandomZone settings 	// --------------------------------------------------	+	 	public static int REFRESH; 	public static int RANDOM_RANGE; 	public static int COORDINATES_X;@@ -138,6 +139,61 @@ 	// Events settings 	// -------------------------------------------------- 	+	/** TvT Settings */+	public static boolean TVT_ALLOW_AUTOEVENT;+	public static String TVT_EVENT_TIMES;+	public static boolean TVT_ALLOW_INTERFERENCE;+	public static boolean TVT_ALLOW_POTIONS;+	public static boolean TVT_ALLOW_SUMMON;+	public static boolean TVT_ON_START_REMOVE_ALL_EFFECTS;+	public static boolean TVT_ON_START_UNSUMMON_PET;+	public static boolean TVT_REVIVE_RECOVERY;+	public static boolean TVT_ANNOUNCE_TEAM_STATS;+	public static boolean TVT_CLOSE_COLISEUM_DOORS;+	public static boolean TVT_ALLOW_ENEMY_HEALING;+	public static boolean TVT_ALLOW_TEAM_CASTING;+	public static boolean TVT_ALLOW_TEAM_ATTACKING;+	public static boolean TVT_ANNOUNCE_REGISTRATION_LOC_NPC;+	public static boolean TVT_ANNOUNCE_SIGNUPS;+	public static boolean TVT_JOIN_CURSED;+	public static boolean TVT_PRICE_NO_KILLS;+	public static boolean TVT_AURA;+	public static String TVT_EVEN_TEAMS;+	public static boolean TVT_ANNOUNCE_REWARD;+	public static int FIRST_TVT_DELAY;+	public static long TVT_REVIVE_DELAY;+	+	/**DM Settings */+	public static boolean DM_ALLOW_INTERFERENCE;+	public static boolean DM_ALLOW_POTIONS;+	public static boolean DM_ALLOW_SUMMON;+	public static boolean DM_ON_START_REMOVE_ALL_EFFECTS;+	public static boolean DM_ON_START_UNSUMMON_PET;+	public static boolean ARENA_ENABLED;+	public static int ARENA_INTERVAL;+	public static int ARENA_REWARD_ID;+	public static int ARENA_REWARD_COUNT;+	public static boolean FISHERMAN_ENABLED;+	public static int FISHERMAN_INTERVAL;+	public static int FISHERMAN_REWARD_ID;+	public static int FISHERMAN_REWARD_COUNT;+	public static long DM_REVIVE_DELAY;+	+	/** CTF Settings*/+	public static boolean ALLOW_CTF_AUTOEVENT;+	public static String CTF_EVENT_TIMES;+	public static String CTF_EVEN_TEAMS;+	public static boolean CTF_ALLOW_INTERFERENCE;+	public static boolean CTF_ALLOW_POTIONS;+	public static boolean CTF_ALLOW_SUMMON;+	public static boolean CTF_ON_START_REMOVE_ALL_EFFECTS;+	public static boolean CTF_ON_START_UNSUMMON_PET;+	public static boolean CTF_ANNOUNCE_TEAM_STATS;+	public static boolean CTF_ANNOUNCE_REWARD;+	public static boolean CTF_JOIN_CURSED;+	public static boolean CTF_REVIVE_RECOVERY;+	public static long CTF_REVIVE_DELAY;+	 	/** Character Killing Monument settings */ 	public static boolean CKM_ENABLED; 	public static long CKM_CYCLE_LENGTH;@@ -149,7 +205,7 @@ 	public static int CKM_PK_NPC_NAME_COLOR; 	public static int EVENT_MONUMENT_STATUET_REWARD_ID; 	public static int EVENT_MONUMENT_STATUET_REWARD_AMOUNT;-	 +	 	/** Olympiad */ 	public static int ALT_OLY_START_TIME; 	public static int ALT_OLY_MIN;@@ -753,7 +809,7 @@ 		} 		return result; 	}-+	 	/** 	 * Load Random Zone settings. 	 */@@ -861,6 +917,66 @@ 	private static final void loadEvents() 	{ 		final ExProperties events = initProperties(EVENTS_FILE);+		+		TVT_ALLOW_AUTOEVENT = Boolean.parseBoolean(events.getProperty("TvTAutomatedEvent", "true"));+		TVT_EVENT_TIMES= events.getProperty("TvTStartUpTimes", "17:00,18:00,19:00");+		FIRST_TVT_DELAY = Integer.parseInt(events.getProperty("FirstEventDelay", "10"));+		TVT_AURA = Boolean.parseBoolean(events.getProperty("TvTAura", "true"));+		TVT_JOIN_CURSED = Boolean.parseBoolean(events.getProperty("TvTJoinWithCursedWeapon", "true"));+		TVT_PRICE_NO_KILLS = Boolean.parseBoolean(events.getProperty("TvTPriceNoKills", "false"));+		TVT_ALLOW_ENEMY_HEALING = Boolean.parseBoolean(events.getProperty("TvTAllowEnemyHealing", "false"));+		TVT_ALLOW_TEAM_CASTING = Boolean.parseBoolean(events.getProperty("TvTAllowTeamCasting", "false"));+		TVT_ALLOW_TEAM_ATTACKING = Boolean.parseBoolean(events.getProperty("TvTAllowTeamAttacking", "false"));+		TVT_CLOSE_COLISEUM_DOORS = Boolean.parseBoolean(events.getProperty("TvTCloseColiseumDoors", "false"));+		TVT_ALLOW_INTERFERENCE = Boolean.parseBoolean(events.getProperty("TvTAllowInterference", "false"));+		TVT_ALLOW_POTIONS = Boolean.parseBoolean(events.getProperty("TvTAllowPotions", "false"));+		TVT_ALLOW_SUMMON = Boolean.parseBoolean(events.getProperty("TvTAllowSummon", "false"));+		TVT_ON_START_REMOVE_ALL_EFFECTS = Boolean.parseBoolean(events.getProperty("TvTOnStartRemoveAllEffects", "true"));+		TVT_ON_START_UNSUMMON_PET = Boolean.parseBoolean(events.getProperty("TvTOnStartUnsummonPet", "true"));+		TVT_REVIVE_RECOVERY = Boolean.parseBoolean(events.getProperty("TvTReviveRecovery", "false"));+		TVT_ANNOUNCE_TEAM_STATS = Boolean.parseBoolean(events.getProperty("TvTAnnounceTeamStats", "false"));+		TVT_EVEN_TEAMS = events.getProperty("TvTEvenTeams", "BALANCE");+		TVT_ANNOUNCE_SIGNUPS = Boolean.parseBoolean(events.getProperty("TvTAnnounceSignUp", "false"));+		TVT_ANNOUNCE_REGISTRATION_LOC_NPC = Boolean.parseBoolean(events.getProperty("TvTAnnounceLocNpc", "true"));+		TVT_ANNOUNCE_TEAM_STATS = Boolean.parseBoolean(events.getProperty("TvTAnnounceTeamStats", "false"));+		TVT_ANNOUNCE_REWARD = Boolean.parseBoolean(events.getProperty("TvTAnnounceReward", "false"));+		TVT_PRICE_NO_KILLS = Boolean.parseBoolean(events.getProperty("TvTPriceNoKills", "false"));+		TVT_JOIN_CURSED = Boolean.parseBoolean(events.getProperty("TvTJoinWithCursedWeapon", "true"));+		TVT_REVIVE_DELAY = Long.parseLong(events.getProperty("TVTReviveDelay", "20000"));+		if (TVT_REVIVE_DELAY < 1000)+		{+			TVT_REVIVE_DELAY = 1000; // can't be set less then 1 second+		}+		+		DM_ALLOW_INTERFERENCE = Boolean.parseBoolean(events.getProperty("DMAllowInterference", "false"));+		DM_ALLOW_POTIONS = Boolean.parseBoolean(events.getProperty("DMAllowPotions", "false"));+		DM_ALLOW_SUMMON = Boolean.parseBoolean(events.getProperty("DMAllowSummon", "false"));+		DM_ON_START_REMOVE_ALL_EFFECTS = Boolean.parseBoolean(events.getProperty("DMOnStartRemoveAllEffects", "true"));+		DM_ON_START_UNSUMMON_PET = Boolean.parseBoolean(events.getProperty("DMOnStartUnsummonPet", "true"));+		DM_REVIVE_DELAY = Long.parseLong(events.getProperty("DMReviveDelay", "20000"));+		if (DM_REVIVE_DELAY < 1000)+		{+			DM_REVIVE_DELAY = 1000; // can't be set less then 1 second+		}+		+		ALLOW_CTF_AUTOEVENT = Boolean.parseBoolean(events.getProperty("CTFAutomatedEvent", "true"));+		CTF_EVENT_TIMES= events.getProperty("CTFStartUpTimes", "17:00,18:00,19:00");+		CTF_EVEN_TEAMS = events.getProperty("CTFEvenTeams", "BALANCE");+		CTF_ALLOW_INTERFERENCE = Boolean.parseBoolean(events.getProperty("CTFAllowInterference", "false"));+		CTF_ALLOW_POTIONS = Boolean.parseBoolean(events.getProperty("CTFAllowPotions", "false"));+		CTF_ALLOW_SUMMON = Boolean.parseBoolean(events.getProperty("CTFAllowSummon", "false"));+		CTF_ON_START_REMOVE_ALL_EFFECTS = Boolean.parseBoolean(events.getProperty("CTFOnStartRemoveAllEffects", "true"));+		CTF_ON_START_UNSUMMON_PET = Boolean.parseBoolean(events.getProperty("CTFOnStartUnsummonPet", "true"));+		CTF_ANNOUNCE_TEAM_STATS = Boolean.parseBoolean(events.getProperty("CTFAnnounceTeamStats", "false"));+		CTF_ANNOUNCE_REWARD = Boolean.parseBoolean(events.getProperty("CTFAnnounceReward", "false"));+		CTF_JOIN_CURSED = Boolean.parseBoolean(events.getProperty("CTFJoinWithCursedWeapon", "true"));+		CTF_REVIVE_RECOVERY = Boolean.parseBoolean(events.getProperty("CTFReviveRecovery", "false"));+		CTF_REVIVE_DELAY = Long.parseLong(events.getProperty("CTFReviveDelay", "20000"));+		if (CTF_REVIVE_DELAY < 1000)+		{+			CTF_REVIVE_DELAY = 1000; // can't be set less then 1 second+		}+		 		CKM_ENABLED = events.getProperty("CKMEnabled", false); 		CKM_CYCLE_LENGTH = events.getProperty("CKMCycleLength", 86400000); 		CKM_PVP_NPC_TITLE = events.getProperty("CKMPvPNpcTitle", "%kills% PvPs in the last 24h");@@ -871,7 +987,7 @@ 		CKM_PK_NPC_NAME_COLOR = Integer.decode("0x" + events.getProperty("CKMPKNpcNameColor", "FFFFFF")); 		EVENT_MONUMENT_STATUET_REWARD_ID = Integer.parseInt(events.getProperty("RewardItemId", "57")); 		EVENT_MONUMENT_STATUET_REWARD_AMOUNT = Integer.parseInt(events.getProperty("RewardAmmount", "57"));-		 +		 		ALT_OLY_START_TIME = events.getProperty("AltOlyStartTime", 18); 		ALT_OLY_MIN = events.getProperty("AltOlyMin", 0); 		ALT_OLY_CPERIOD = events.getProperty("AltOlyCPeriod", 21600000);@@ -1445,7 +1561,7 @@ 	public static final void loadGameServer() 	{ 		_log.info("Loading gameserver configuration files.");-+		 		// randomzone settings 		loadRandomZone(); 		Index: java/net/sf/l2j/gameserver/model/entity/engine/DM.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/DM.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/DM.java	(working copy)@@ -0,0 +1,700 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++import java.sql.Connection;+import java.sql.PreparedStatement;+import java.sql.ResultSet;+import java.util.ArrayList;+import java.util.List;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.L2DatabaseFactory;+import net.sf.l2j.commons.concurrent.ThreadPool;+import net.sf.l2j.gameserver.datatables.NpcTable;+import net.sf.l2j.gameserver.datatables.SpawnTable;+import net.sf.l2j.gameserver.model.L2Effect;+import net.sf.l2j.gameserver.model.L2Spawn;+import net.sf.l2j.gameserver.model.actor.Summon;+import net.sf.l2j.gameserver.model.actor.instance.Pet;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.actor.template.NpcTemplate;+import net.sf.l2j.gameserver.model.group.Party;+import net.sf.l2j.gameserver.model.group.Party.MessageType;+import net.sf.l2j.gameserver.network.serverpackets.ActionFailed;+import net.sf.l2j.gameserver.network.serverpackets.MagicSkillUse;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.network.serverpackets.StatusUpdate;+import net.sf.l2j.gameserver.util.Broadcast;++/**+ * @author SqueezeD Edited By TheEnd+ */+public class DM+{+	private final static Logger _log = Logger.getLogger(DM.class.getName());+	public static String _eventName = new String(), _eventDesc = new String(), _joiningLocationName = new String();+	public static List<String> _savePlayers = new ArrayList<>();+	public static List<Player> _players = new ArrayList<>();+	public static boolean _joining = false, _teleport = false, _started = false, _sitForced = false;+	public static L2Spawn _npcSpawn;+	public static Player _topPlayer;+	public static int _npcId = 0, _npcX = 0, _npcY = 0, _npcZ = 0, _rewardId = 0, _rewardAmount = 0, _topKills = 0,+			_minlvl = 0, _maxlvl = 0, _playerColors = 0, _playerX = 0, _playerY = 0, _playerZ = 0;++	public static void setNpcPos(Player activeChar)+	{+		_npcX = activeChar.getX();+		_npcY = activeChar.getY();+		_npcZ = activeChar.getZ();+	}++	public static boolean checkMaxLevel(int maxlvl)+	{+		if (_minlvl >= maxlvl)+			return false;++		return true;+	}++	public static boolean checkMinLevel(int minlvl)+	{+		if (_maxlvl <= minlvl)+			return false;++		return true;+	}++	public static void setPlayersPos(Player activeChar)+	{+		_playerX = activeChar.getX();+		_playerY = activeChar.getY();+		_playerZ = activeChar.getZ();+	}++	public static boolean checkPlayerOk()+	{+		if (_started || _teleport || _joining)+			return false;++		return true;+	}++	public static void startJoin(Player activeChar)+	{+		if (!startJoinOk())+		{+			if (!Config.DEBUG)+				_log.fine("DM Engine[startJoin(" + activeChar.getName() + ")]: startJoinOk() = false");+			return;+		}++		_joining = true;+		spawnEventNpc(activeChar);+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Joinable in " + _joiningLocationName + "!");+	}++	private static boolean startJoinOk()+	{+		if (_started || _teleport || _joining || _eventName.equals("") || _joiningLocationName.equals("") || _eventDesc.equals("") || _npcId == 0 || _npcX == 0 || _npcY == 0 || _npcZ == 0 || _rewardId == 0 || _rewardAmount == 0 || _playerX == 0 || _playerY == 0 || _playerZ == 0)+			return false;++		return true;+	}++	private static void spawnEventNpc(Player activeChar)+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);+			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, activeChar.getHeading());+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobDM = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(DM.class.getSimpleName() + ":  DM Engine[spawnEventNpc(" + activeChar.getName() + ")]: exception: " + e.getMessage());+		}+	}++	public static void teleportStart()+	{+		if (!_joining || _started || _teleport)+			return;++		_joining = false;+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				DM.sit();++				for (Player player : DM._players)+				{+					if (player != null)+					{+						if (Config.DM_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+							    Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+									e.exit();++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}++						if (Config.DM_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}+						player.teleToLocation(_playerX, _playerY, _playerZ, 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+	}++	public static void startEvent(Player activeChar)+	{+		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.fine("DM Engine[startEvent(" + activeChar.getName() + ")]: startEventOk() = false");+			return;+		}++		_teleport = false;+		sit();+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Started. Go to kill your enemies!");+		_started = true;+	}++	private static boolean startEventOk()+	{+		if (_joining || !_teleport || _started)+			return false;++		return true;+	}++	public static void setUserData()+	{+		for (Player player : _players)+		{+			player._originalNameColorDM = player.getAppearance().getNameColor();+			player._originalKarmaDM = player.getKarma();+			player._inEventDM = true;+			player._countDMkills = 0;+			player.getAppearance().setNameColor(_playerColors);+			player.setKarma(0);+			player.broadcastUserInfo();+		}+	}++	public static void removeUserData()+	{+		for (Player player : _players)+		{+			player.getAppearance().setNameColor(player._originalNameColorDM);+			player.setKarma(player._originalKarmaDM);+			player._inEventDM = false;+			player._countDMkills = 0;+			player.broadcastUserInfo();+		}+	}++	public static void finishEvent(Player activeChar)+	{+		if (!finishEventOk())+		{+			if (Config.DEBUG)+				_log.fine("DM Engine[finishEvent(" + activeChar.getName() + ")]: finishEventOk() = false");+			return;+		}++		_started = false;+		unspawnEventNpc();+		processTopPlayer();++		if (_topKills == 0)+			Broadcast.announceToOnlinePlayers(_eventName + "(DM): No players win the match(nobody killed).");+		else+		{+			Broadcast.announceToOnlinePlayers(_eventName + "(DM): " + _topPlayer.getName() + " wins the match! " + _topKills + " kills.");+			rewardPlayer(activeChar);+		}++		teleportFinish();+	}++	private static boolean finishEventOk()+	{+		if (!_started)+			return false;++		return true;+	}++	public static void processTopPlayer()+	{+		for (Player player : _players)+		{+			if (player._countDMkills > _topKills)+			{+				_topPlayer = player;+				_topKills = player._countDMkills;+			}+		}+	}++	/**+	 * @param activeChar+	 */+	public static void rewardPlayer(Player activeChar)+	{+		if (_topPlayer != null)+		{+			_topPlayer.addItem("DM Event: " + _eventName, _rewardId, _rewardAmount, _topPlayer, true);++			StatusUpdate su = new StatusUpdate(_topPlayer);+			su.addAttribute(StatusUpdate.CUR_LOAD, _topPlayer.getCurrentLoad());+			_topPlayer.sendPacket(su);++			NpcHtmlMessage nhm = new NpcHtmlMessage(5);+			StringBuilder replyMSG = new StringBuilder("");++			replyMSG.append("<html><body>You won the event. Look in your inventory for the reward.</body></html>");++			nhm.setHtml(replyMSG.toString());+			_topPlayer.sendPacket(nhm);++			// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+			_topPlayer.sendPacket(ActionFailed.STATIC_PACKET);+		}+	}++	public static void abortEvent()+	{+		if (!_joining && !_teleport && !_started)+			return;++		_joining = false;+		_teleport = false;+		_started = false;+		unspawnEventNpc();+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Match aborted!");+		teleportFinish();+	}++	public static void sit()+	{+		if (_sitForced)+			_sitForced = false;+		else+			_sitForced = true;++		for (Player player : _players)+		{+			if (player != null)+			{+				if (_sitForced)+				{+					player.stopMove(null);+					player.abortAttack();+					player.abortCast();++					if (!player.isSitting())+						player.sitDown();+				}+				else+				{+					if (player.isSitting())+						player.standUp();+				}+			}+		}+	}++	public static void dumpData()+	{+		_log.info("");+		_log.info("");++		if (!_joining && !_teleport && !_started)+		{+			_log.info("<<---------------------------------->>");+			_log.info(">> DM Engine infos dump (INACTIVE) <<");+			_log.info("<<--^----^^-----^----^^------^^----->>");+		}+		else if (_joining && !_teleport && !_started)+		{+			_log.info("<<--------------------------------->>");+			_log.info(">> DM Engine infos dump (JOINING) <<");+			_log.info("<<--^----^^-----^----^^------^----->>");+		}+		else if (!_joining && _teleport && !_started)+		{+			_log.info("<<---------------------------------->>");+			_log.info(">> DM Engine infos dump (TELEPORT) <<");+			_log.info("<<--^----^^-----^----^^------^^----->>");+		}+		else if (!_joining && !_teleport && _started)+		{+			_log.info("<<--------------------------------->>");+			_log.info(">> DM Engine infos dump (STARTED) <<");+			_log.info("<<--^----^^-----^----^^------^----->>");+		}++		_log.info("Name: " + _eventName);+		_log.info("Desc: " + _eventDesc);+		_log.info("Join location: " + _joiningLocationName);+		_log.info("Min lvl: " + _minlvl);+		_log.info("Max lvl: " + _maxlvl);++		_log.info("");+		_log.info("##################################");+		_log.info("# _players(Vector<Player>) #");+		_log.info("##################################");++		_log.info("Total Players : " + _players.size());++		for (Player player : _players)+		{+			if (player != null)+				_log.info("Name: " + player.getName() + " kills :" + player._countDMkills);+		}++		_log.info("");+		_log.info("################################");+		_log.info("# _savePlayers(Vector<String>) #");+		_log.info("################################");++		for (String player : _savePlayers)+			_log.info("Name: " + player);++		_log.info("");+		_log.info("");+	}++	public static void loadData()+	{+		_eventName = new String();+		_eventDesc = new String();+		_joiningLocationName = new String();+		_savePlayers = new ArrayList<>();+		_players = new ArrayList<>();+		_topPlayer = null;+		_npcSpawn = null;+		_joining = false;+		_teleport = false;+		_started = false;+		_sitForced = false;+		_npcId = 0;+		_npcX = 0;+		_npcY = 0;+		_npcZ = 0;+		_rewardId = 0;+		_rewardAmount = 0;+		_topKills = 0;+		_minlvl = 0;+		_maxlvl = 0;+		_playerColors = 0;+		_playerX = 0;+		_playerY = 0;+		_playerZ = 0;++		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;+			ResultSet rs;++			statement = con.prepareStatement("SELECT * FROM dm");+			rs = statement.executeQuery();++			while (rs.next())+			{+				_eventName = rs.getString("eventName");+				_eventDesc = rs.getString("eventDesc");+				_joiningLocationName = rs.getString("joiningLocation");+				_minlvl = rs.getInt("minlvl");+				_maxlvl = rs.getInt("maxlvl");+				_npcId = rs.getInt("npcId");+				_npcX = rs.getInt("npcX");+				_npcY = rs.getInt("npcY");+				_npcZ = rs.getInt("npcZ");+				_rewardId = rs.getInt("rewardId");+				_rewardAmount = rs.getInt("rewardAmount");+				_playerColors = rs.getInt("color");+				_playerX = rs.getInt("playerX");+				_playerY = rs.getInt("playerY");+				_playerZ = rs.getInt("playerZ");++			}+			rs.close();+			statement.close();+		}+		catch (Exception e)+		{+			_log.warning(DM.class.getSimpleName() + ":  Exception: DM.loadData(): " + e.getMessage());+		}+	}++	public static void saveData()+	{+		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;++			statement = con.prepareStatement("DELETE FROM dm");+			statement.execute();+			statement.close();++			statement = con.prepareStatement("INSERT INTO dm (eventName, eventDesc, joiningLocation, minlvl, maxlvl, npcId, npcX, npcY, npcZ, rewardId, rewardAmount, color, playerX, playerY, playerZ ) VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)");+			statement.setString(1, _eventName);+			statement.setString(2, _eventDesc);+			statement.setString(3, _joiningLocationName);+			statement.setInt(4, _minlvl);+			statement.setInt(5, _maxlvl);+			statement.setInt(6, _npcId);+			statement.setInt(7, _npcX);+			statement.setInt(8, _npcY);+			statement.setInt(9, _npcZ);+			statement.setInt(10, _rewardId);+			statement.setInt(11, _rewardAmount);+			statement.setInt(12, _playerColors);+			statement.setInt(13, _playerX);+			statement.setInt(14, _playerY);+			statement.setInt(15, _playerZ);+			statement.execute();+			statement.close();+		}+		catch (Exception e)+		{+			_log.warning(DM.class.getSimpleName() + ":  Exception: DM.saveData(): " + e.getMessage());+		}+	}++	public static void showEventHtml(Player eventPlayer, String objectId)+	{+		try+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++			StringBuilder replyMSG = new StringBuilder("<html><body>");+			replyMSG.append("DM Match<br><br><br>");+			replyMSG.append("Current event...<br1>");+			replyMSG.append("	... name:&nbsp;<font color=\"00FF00\">" + _eventName + "</font><br1>");+			replyMSG.append("	... description:&nbsp;<font color=\"00FF00\">" + _eventDesc + "</font><br><br>");++			if (!_started && !_joining)+				replyMSG.append("<center>Wait till the admin/gm start the participation.</center>");+			else if (!_started && _joining && eventPlayer.getLevel() >= _minlvl && eventPlayer.getLevel() < _maxlvl)+			{+				if (_players.contains(eventPlayer))+				{+					replyMSG.append("You are already participating!<br><br>");++					replyMSG.append("<table border=\"0\"><tr>");+					replyMSG.append("<td width=\"200\">Wait till event start or</td>");+					replyMSG.append("<td width=\"60\"><center><button value=\"remove\" action=\"bypass -h npc_" + objectId + "_dmevent_player_leave\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></center></td>");+					replyMSG.append("<td width=\"100\">your participation!</td>");+					replyMSG.append("</tr></table>");+				}+				else+				{+					replyMSG.append("You want to participate in the event?<br><br>");+					replyMSG.append("<td width=\"200\">Admin set min lvl : <font color=\"00FF00\">" + _minlvl + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Admin set max lvl : <font color=\"00FF00\">" + _maxlvl + "</font></td><br><br>");++					replyMSG.append("<button value=\"Join\" action=\"bypass -h npc_" + objectId + "_dmevent_player_join\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\">");++				}+			}+			else if (_started && !_joining)+				replyMSG.append("<center>DM match is in progress.</center>");+			else if (eventPlayer.getLevel() < _minlvl || eventPlayer.getLevel() > _maxlvl)+			{+				replyMSG.append("Your lvl : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font><br>");+				replyMSG.append("Admin set min lvl : <font color=\"00FF00\">" + _minlvl + "</font><br>");+				replyMSG.append("Admin set max lvl : <font color=\"00FF00\">" + _maxlvl + "</font><br><br>");+				replyMSG.append("<font color=\"FFFF00\">You can't participate to this event.</font><br>");+			}++			replyMSG.append("</body></html>");+			adminReply.setHtml(replyMSG.toString());+			eventPlayer.sendPacket(adminReply);++			// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+			eventPlayer.sendPacket(ActionFailed.STATIC_PACKET);+		}+		catch (Exception e)+		{+			_log.warning(DM.class.getSimpleName() + ":  DM Engine[showEventHtlm(" + eventPlayer.getName() + ", " + objectId + ")]: exception" + e.getMessage());+		}+	}++	public static void addPlayer(Player player)+	{+		if (!addPlayerOk(player))+			return;+		_players.add(player);+		player._originalNameColorDM = player.getAppearance().getNameColor();+		player._originalKarmaDM = player.getKarma();+		player._inEventDM = true;+		player._countDMkills = 0;+		_savePlayers.add(player.getName());++	}++	public static boolean addPlayerOk(Player eventPlayer)+	{++		if (eventPlayer._inEventDM)+		{+			eventPlayer.sendMessage("You are already participating in the event!");+			return false;+		}++		return true;+	}++	public static synchronized void addDisconnectedPlayer(Player player)+	{+		if ((_teleport || _started) || _savePlayers.contains(player.getName()))+		{+			if (Config.DM_ON_START_REMOVE_ALL_EFFECTS)+			{+				for (L2Effect e : player.getAllEffects())+				{+					if (e != null)+						e.exit();+				}+			}+			for (Player p : _players)+			{+				if (p == null)+				{+					continue;+				}+				// check by name incase player got new objectId+				else if (p.getName().equals(player.getName()))+				{+					player._originalNameColorDM = player.getAppearance().getNameColor();+					player._originalKarmaDM = player.getKarma();+					player._inEventDM = true;+					player._countDMkills = p._countDMkills;+					_players.remove(p); // removing old object id from vector+					_players.add(player); // adding new objectId to vector+					break;+				}+			}++			player.getAppearance().setNameColor(_playerColors);+			player.setKarma(0);+			player.broadcastUserInfo();+			player.teleToLocation(_playerX, _playerY, _playerZ, 0);+		}+	}++	public static void removePlayer(Player player)+	{+		if (player != null)+			_players.remove(player);+	}++	public static void cleanDM()+	{+		for (Player player : _players)+		{+			removePlayer(player);+		}++		_savePlayers = new ArrayList<>();+		_topPlayer = null;+		_npcSpawn = null;+		_joining = false;+		_teleport = false;+		_started = false;+		_sitForced = false;+		_topKills = 0;+		_players = new ArrayList<>();++	}++	public static void unspawnEventNpc()+	{+		if (_npcSpawn == null)+			return;++		_npcSpawn.getNpc().deleteMe();+		_npcSpawn.setRespawnState(false);+		SpawnTable.getInstance().deleteSpawn(_npcSpawn, true);+	}++	public static void teleportFinish()+	{+		Broadcast.announceToOnlinePlayers(_eventName + "(DM): Teleport back to participation NPC in 20 seconds!");++		removeUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				for (Player player : _players)+				{+					if (player != null && player.isOnline())+						player.teleToLocation(_npcX, _npcY, _npcZ, 0);+				}+				cleanDM();+			}+		}, 20000);+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/handler/itemhandlers/SummonItems.java===================================================================--- java/net/sf/l2j/gameserver/handler/itemhandlers/SummonItems.java	(revision 1)+++ java/net/sf/l2j/gameserver/handler/itemhandlers/SummonItems.java	(working copy)@@ -2,8 +2,8 @@  import java.util.logging.Level; +import net.sf.l2j.Config; import net.sf.l2j.commons.concurrent.ThreadPool;- import net.sf.l2j.gameserver.datatables.NpcTable; import net.sf.l2j.gameserver.datatables.SummonItemsData; import net.sf.l2j.gameserver.handler.IItemHandler;@@ -16,9 +16,13 @@ import net.sf.l2j.gameserver.model.actor.instance.Pet; import net.sf.l2j.gameserver.model.actor.instance.Player; import net.sf.l2j.gameserver.model.actor.template.NpcTemplate;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.model.entity.engine.DM;+import net.sf.l2j.gameserver.model.entity.engine.TvT; import net.sf.l2j.gameserver.model.item.SummonItem; import net.sf.l2j.gameserver.model.item.instance.ItemInstance; import net.sf.l2j.gameserver.network.SystemMessageId;+import net.sf.l2j.gameserver.network.serverpackets.ActionFailed; import net.sf.l2j.gameserver.network.serverpackets.MagicSkillLaunched; import net.sf.l2j.gameserver.network.serverpackets.MagicSkillUse; import net.sf.l2j.gameserver.network.serverpackets.SetupGauge;@@ -41,7 +45,13 @@ 			activeChar.sendPacket(SystemMessageId.CANT_MOVE_SITTING); 			return; 		}-		++		if ((activeChar._inEventTvT && TvT._started && !Config.TVT_ALLOW_SUMMON) || (activeChar._inEventCTF && CTF._started && !Config.CTF_ALLOW_SUMMON) || (activeChar._inEventDM && DM._started && !Config.DM_ALLOW_SUMMON))+		{+			activeChar.sendPacket(ActionFailed.STATIC_PACKET);+			return;+		}+ 		if (activeChar.isInObserverMode()) 			return; 		Index: java/net/sf/l2j/gameserver/model/entity/engine/CTF.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/CTF.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/CTF.java	(working copy)@@ -0,0 +1,2223 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++import java.sql.Connection;+import java.sql.PreparedStatement;+import java.sql.ResultSet;+import java.sql.SQLException;+import java.util.ArrayList;+import java.util.List;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.L2DatabaseFactory;+import net.sf.l2j.commons.concurrent.ThreadPool;+import net.sf.l2j.commons.random.Rnd;+import net.sf.l2j.gameserver.datatables.ItemTable;+import net.sf.l2j.gameserver.datatables.NpcTable;+import net.sf.l2j.gameserver.datatables.SpawnTable;+import net.sf.l2j.gameserver.model.L2Effect;+import net.sf.l2j.gameserver.model.L2Radar;+import net.sf.l2j.gameserver.model.L2Spawn;+import net.sf.l2j.gameserver.model.actor.Summon;+import net.sf.l2j.gameserver.model.actor.instance.Pet;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.actor.template.NpcTemplate;+import net.sf.l2j.gameserver.model.group.Party;+import net.sf.l2j.gameserver.model.group.Party.MessageType;+import net.sf.l2j.gameserver.model.item.instance.ItemInstance;+import net.sf.l2j.gameserver.model.itemcontainer.Inventory;+import net.sf.l2j.gameserver.network.serverpackets.ActionFailed;+import net.sf.l2j.gameserver.network.serverpackets.CreatureSay;+import net.sf.l2j.gameserver.network.serverpackets.InventoryUpdate;+import net.sf.l2j.gameserver.network.serverpackets.ItemList;+import net.sf.l2j.gameserver.network.serverpackets.MagicSkillUse;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.network.serverpackets.RadarControl;+import net.sf.l2j.gameserver.network.serverpackets.SocialAction;+import net.sf.l2j.gameserver.util.Broadcast;++/**+ * @author SqueezeD & Darki699 (idea by FBIAgent)+ */+public class CTF+{+	private final static Logger _log = Logger.getLogger(CTF.class.getName());+	private static int _FlagNPC = 35062, _FLAG_IN_HAND_ITEM_ID = 6718;+	public static String _eventName = new String(), _eventDesc = new String(), _topTeam = new String(),+	_joiningLocationName = new String();+	public static List<String> _teams = new ArrayList<>(), _savePlayers = new ArrayList<>(),+			_savePlayerTeams = new ArrayList<>();+	public static List<Player> _players = new ArrayList<>(),+			_playersShuffle = new ArrayList<>();+	public static List<Integer> _teamPlayersCount = new ArrayList<>(), _teamColors = new ArrayList<>(),+			_teamsX = new ArrayList<>(), _teamsY = new ArrayList<>(), _teamsZ = new ArrayList<>();+	public static boolean _joining = false, _teleport = false, _started = false, _sitForced = false;+	public static L2Spawn _npcSpawn;+	public static int _npcId = 0, _npcX = 0, _npcY = 0, _npcZ = 0, _npcHeading = 0, _rewardId = 0, _rewardAmount = 0,+			_minlvl = 0, _maxlvl = 0, _joinTime = 0, _eventTime = 0, _minPlayers = 0, _maxPlayers = 0;+	public static List<Integer> _teamPointsCount = new ArrayList<>();+	public static List<Integer> _flagIds = new ArrayList<>(), _flagsX = new ArrayList<>(),+			_flagsY = new ArrayList<>(), _flagsZ = new ArrayList<>();+	public static List<L2Spawn> _flagSpawns = new ArrayList<>(), _throneSpawns = new ArrayList<>();+	public static List<Boolean> _flagsTaken = new ArrayList<>();+	public static int _topScore = 0, eventCenterX = 0, eventCenterY = 0, eventCenterZ = 0, eventOffset = 0;++	public static void showFlagHtml(Player eventPlayer, String objectId, String teamName)+	{+		if (eventPlayer == null)+			return;++		try+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++			StringBuilder replyMSG = new StringBuilder();++			replyMSG.append("<html><body><center>");+			replyMSG.append("CTF Flag<br><br>");+			replyMSG.append("<font color=\"00FF00\">" + teamName + "'s Flag</font><br>");+			if (eventPlayer._teamNameCTF != null && eventPlayer._teamNameCTF.equals(teamName))+				replyMSG.append("<font color=\"LEVEL\">This is your Flag</font><br>");+			else+				replyMSG.append("<font color=\"LEVEL\">Enemy Flag!</font><br>");+			if (_started)+				processInFlagRange(eventPlayer);+			else+				replyMSG.append("CTF match is not in progress yet.<br>Wait for a GM to start the event<br>");+			replyMSG.append("</center></body></html>");+			adminReply.setHtml(replyMSG.toString());+			eventPlayer.sendPacket(adminReply);+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[showEventHtlm(" + eventPlayer.getName() + ", " + objectId + ")]: exception: " + e.getStackTrace());+		}+	}++	public static void CheckRestoreFlags()+	{+		List<Integer> teamsTakenFlag = new ArrayList<>();+		try+		{+			for (Player player : _players)+			{ // if there's a player with a flag+				// add the index of the team who's FLAG WAS TAKEN to the list+				if (player != null)+				{+					if (player.isOnline() && player._haveFlagCTF)// logged off with a flag in his hands+					{+						AnnounceToPlayers(false, _eventName + "(CTF): " + player.getName() + " logged off with a CTF flag!");+						player._haveFlagCTF = false;+						if (_teams.indexOf(player._teamNameHaveFlagCTF) >= 0)+						{+							if (_flagsTaken.get(_teams.indexOf(player._teamNameHaveFlagCTF)))+							{+								_flagsTaken.set(_teams.indexOf(player._teamNameHaveFlagCTF), false);+								spawnFlag(player._teamNameHaveFlagCTF);+								AnnounceToPlayers(false, _eventName + "(CTF): " + player._teamNameHaveFlagCTF + " flag now returned to place.");+							}+						}+						removeFlagFromPlayer(player);+						player._teamNameHaveFlagCTF = null;+						return;+					}+					else if (player._haveFlagCTF)+						teamsTakenFlag.add(_teams.indexOf(player._teamNameHaveFlagCTF));+				}+			}+			// Go over the list of ALL teams+			for (String team : _teams)+			{+				if (team == null)+					continue;+				int index = _teams.indexOf(team);+				if (!teamsTakenFlag.contains(index))+				{+					if (_flagsTaken.get(index))+					{+						_flagsTaken.set(index, false);+						spawnFlag(team);+						AnnounceToPlayers(false, _eventName + "(CTF): " + team + " flag returned due to player error.");+					}+				}+			}+			// Check if a player ran away from the event holding a flag:+			for (Player player : _players)+			{+				if ((player != null) && player._haveFlagCTF)+				{+					if (isOutsideCTFArea(player))+					{+						AnnounceToPlayers(false, _eventName + "(CTF): " + player.getName() + " escaped from the event holding a flag!");+						player._haveFlagCTF = false;+						if (_teams.indexOf(player._teamNameHaveFlagCTF) >= 0)+						{+							if (_flagsTaken.get(_teams.indexOf(player._teamNameHaveFlagCTF)))+							{+								_flagsTaken.set(_teams.indexOf(player._teamNameHaveFlagCTF), false);+								spawnFlag(player._teamNameHaveFlagCTF);+								AnnounceToPlayers(false, _eventName + "(CTF): " + player._teamNameHaveFlagCTF + " flag now returned to place.");+							}+						}+						removeFlagFromPlayer(player);+						player._teamNameHaveFlagCTF = null;+						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameCTF)), _teamsY.get(_teams.indexOf(player._teamNameCTF)), _teamsZ.get(_teams.indexOf(player._teamNameCTF)), 0);+						player.sendMessage("You have been returned to your team spawn");+						return;+					}+				}+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF.restoreFlags() Error:" + e.toString());+		}+	}++	public static void kickPlayerFromCTf(Player playerToKick)+	{+		if (playerToKick == null)+			return;++		if (_joining)+		{+			_playersShuffle.remove(playerToKick);+			_players.remove(playerToKick);+			playerToKick._inEventCTF = false;+			playerToKick._teamNameCTF = new String();+		}+		if (_started || _teleport)+		{+			_playersShuffle.remove(playerToKick);+			playerToKick._inEventCTF = false;+			removePlayer(playerToKick);+			if (playerToKick.isOnline())+			{+				playerToKick.getAppearance().setNameColor(playerToKick._originalNameColorCTF);+				playerToKick.setKarma(playerToKick._originalKarmaCTF);+				playerToKick.setTitle(playerToKick._originalTitleCTF);+				playerToKick.broadcastUserInfo();+				playerToKick.sendMessage("You have been kicked from the CTF.");+				playerToKick.teleToLocation(_npcX, _npcY, _npcZ, 0);+			}+		}+	}++	public static void AnnounceToPlayers(Boolean toall, String announce)+	{+		if (toall)+			Broadcast.announceToOnlinePlayers(announce);+		else+		{+			CreatureSay cs = new CreatureSay(0, 2, "", "Announcements : " + announce);+			if (_players != null && !_players.isEmpty())+			{+				for (Player player : _players)+				{+					if (player != null && player.isOnline())+						player.sendPacket(cs);+				}+			}+		}+	}++	public static void Started(Player player)+	{+		player._teamNameHaveFlagCTF = null;+		player._haveFlagCTF = false;+	}++	public static void StartEvent()+	{+		for (Player player : _players)+		{+			if (player != null)+			{+				player._teamNameHaveFlagCTF = null;+				player._haveFlagCTF = false;+			}+		}+		AnnounceToPlayers(false, _eventName + "(CTF): Started. Go Capture the Flags!");+	}++	public static void addFlagToPlayer(Player _player)+	{+		// remove items from the player hands (right, left, both)+		// This is NOT a BUG, I don't want them to see the icon they have 8D+		ItemInstance wpn = _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_RHAND);+		if (wpn == null)+		{+			wpn = _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_LHAND);+			if (wpn != null)+				_player.getInventory().unEquipItemInSlot(Inventory.PAPERDOLL_LHAND);+		}+		else+		{+			_player.getInventory().unEquipItemInSlot(Inventory.PAPERDOLL_RHAND);+			wpn = _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_LHAND);+			if (wpn != null)+				_player.getInventory().unEquipItemInSlot(Inventory.PAPERDOLL_LHAND);+		}+		// add the flag in his hands+		_player.getInventory().equipItem(ItemTable.getInstance().createItem("", CTF._FLAG_IN_HAND_ITEM_ID, 1, _player, null));+		_player.broadcastPacket(new SocialAction(_player, 16),2000); // amazing glow+		_player._haveFlagCTF = true;+		_player.broadcastUserInfo();+		CreatureSay cs = new CreatureSay(_player.getObjectId(), 15, ":", "You got it! Run back! ::"); // 8D+		_player.sendPacket(cs);+	}++	public static void removeFlagFromPlayer(Player player)+	{+		ItemInstance wpn = player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_RHAND);+		player._haveFlagCTF = false;+		if (wpn != null)+		{+			ItemInstance[] unequiped = player.getInventory().unEquipItemInBodySlotAndRecord(wpn);+			player.getInventory().destroyItemByItemId("", CTF._FLAG_IN_HAND_ITEM_ID, 1, player, null);+			InventoryUpdate iu = new InventoryUpdate();+			for (ItemInstance element : unequiped)+				iu.addModifiedItem(element);+			player.sendPacket(iu);+			player.sendPacket(new ItemList(player, true)); // get your weapon back now ...+			player.abortAttack();+			player.broadcastUserInfo();+		}+		else+		{+			player.getInventory().destroyItemByItemId("", CTF._FLAG_IN_HAND_ITEM_ID, 1, player, null);+			player.sendPacket(new ItemList(player, true)); // get your weapon back now ...+			player.abortAttack();+			player.broadcastUserInfo();+		}+	}++	public static void setTeamFlag(String teamName, Player activeChar)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;+		addOrSet(_teams.indexOf(teamName), null, false, _FlagNPC, activeChar.getX(), activeChar.getY(), activeChar.getZ());+	}++	public static void setTeamFlag(String teamName, int x, int y, int z)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;+		addOrSet(_teams.indexOf(teamName), null, false, _FlagNPC, x, y, z);+	}++	public static void spawnAllFlags()+	{+		while (_flagSpawns.size() < _teams.size())+			_flagSpawns.add(null);+		while (_throneSpawns.size() < _teams.size())+			_throneSpawns.add(null);+		for (String team : _teams)+		{+			int index = _teams.indexOf(team);+			NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_flagIds.get(index));+			NpcTemplate throne = NpcTable.getInstance().getTemplate(32027);+			try+			{+				// spawn throne+				_throneSpawns.set(index, new L2Spawn(throne));+				_throneSpawns.get(index).setLoc(_flagsX.get(index), _flagsY.get(index), _flagsZ.get(index) - 10, 0);+				_throneSpawns.get(index).setRespawnDelay(1);+				+				SpawnTable.getInstance().addNewSpawn(_throneSpawns.get(index), false);+				+				_throneSpawns.get(index).setRespawnState(true);+				_throneSpawns.get(index).doSpawn(false);+				_throneSpawns.get(index).getNpc().getStatus().setCurrentHp(999999999);+				_throneSpawns.get(index).getNpc().decayMe();+				_throneSpawns.get(index).getNpc().spawnMe(_throneSpawns.get(index).getNpc().getX(), _throneSpawns.get(index).getNpc().getY(), _throneSpawns.get(index).getNpc().getZ());+				_throneSpawns.get(index).getNpc().setTitle(team + " Throne");+				_throneSpawns.get(index).getNpc().broadcastPacket(new MagicSkillUse(_throneSpawns.get(index).getNpc(), _throneSpawns.get(index).getNpc(), 1036, 1, 5500, 1));+				_throneSpawns.get(index).getNpc()._isCTF_throneSpawn = true;++				// spawn flag+				_flagSpawns.set(index, new L2Spawn(tmpl));+				_flagSpawns.get(index).setLoc(_flagsX.get(index), _flagsY.get(index), _flagsZ.get(index), 0);+				_flagSpawns.get(index).setRespawnDelay(1);+				+				SpawnTable.getInstance().addNewSpawn(_flagSpawns.get(index), false);+				+				_flagSpawns.get(index).setRespawnState(true);+				_flagSpawns.get(index).doSpawn(false);+				_flagSpawns.get(index).getNpc().getStatus().setCurrentHp(999999999);+				_flagSpawns.get(index).getNpc().setTitle(team + "'s Flag");+				_flagSpawns.get(index).getNpc()._CTF_FlagTeamName = team;+				_flagSpawns.get(index).getNpc().decayMe();+				_flagSpawns.get(index).getNpc().spawnMe(_flagSpawns.get(index).getNpc().getX(), _flagSpawns.get(index).getNpc().getY(), _flagSpawns.get(index).getNpc().getZ());+				_flagSpawns.get(index).getNpc()._isCTF_Flag = true;+				if (index == (_teams.size() - 1))+					calculateOutSideOfCTF(); // sets event boundaries so players don't run with the flag.+			}+			catch (Exception e)+			{+				_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[spawnAllFlags()]: exception: " + e.getStackTrace());+			}+		}+	}++	public static void processTopTeam()+	{+		_topTeam = null;+		for (String team : _teams)+		{+			if (teamPointsCount(team) == _topScore && _topScore > 0)+				_topTeam = null;+			if (teamPointsCount(team) > _topScore)+			{+				_topTeam = team;+				_topScore = teamPointsCount(team);+			}+		}+		if (_topScore <= 0)+		{+			AnnounceToPlayers(true, _eventName + "(CTF): No flags taken.");+		}+		else+		{+			if (_topTeam == null)+				AnnounceToPlayers(true, _eventName + "(CTF): Maximum flags taken : " + _topScore + " flags! No one won.");+			else+			{+				AnnounceToPlayers(true, _eventName + "(CTF): Team " + _topTeam + " wins the match, with " + _topScore + " flags taken!");+				rewardTeam(_topTeam);+			}+		}+		teleportFinish();+	}++	public static void unspawnAllFlags()+	{+		try+		{+			if ((_throneSpawns == null) || (_flagSpawns == null) || (_teams == null))+				return;+			for (String team : _teams)+			{+				int index = _teams.indexOf(team);+				if (_throneSpawns.get(index) != null)+				{+					_throneSpawns.get(index).getNpc().deleteMe();+					_throneSpawns.get(index).setRespawnState(false);+					SpawnTable.getInstance().deleteSpawn(_throneSpawns.get(index), true);+				}+				if (_flagSpawns.get(index) != null)+				{+					_flagSpawns.get(index).getNpc().deleteMe();+					_flagSpawns.get(index).setRespawnState(false);+					SpawnTable.getInstance().deleteSpawn(_flagSpawns.get(index), true);+				}+			}+			_throneSpawns.clear();+		}+		catch (Throwable t)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[unspawnAllFlags()]: exception: " + t.getStackTrace());+		}+	}++	private static void unspawnFlag(String teamName)+	{+		int index = _teams.indexOf(teamName);++		_flagSpawns.get(index).getNpc().deleteMe();+		_flagSpawns.get(index).setRespawnState(false);+		SpawnTable.getInstance().deleteSpawn(_flagSpawns.get(index), true);+	}++	public static void spawnFlag(String teamName)+	{+		int index = _teams.indexOf(teamName);+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_flagIds.get(index));++		try+		{+			_flagSpawns.set(index, new L2Spawn(tmpl));++			_flagSpawns.get(index).setLoc(_flagsX.get(index), _flagsY.get(index), _flagsZ.get(index), 0);+			_flagSpawns.get(index).setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_flagSpawns.get(index), false);++			_flagSpawns.get(index).setRespawnState(true);+			_flagSpawns.get(index).doSpawn(false);+			_flagSpawns.get(index).getNpc().getStatus().setCurrentHp(999999999);+			_flagSpawns.get(index).getNpc().setTitle(teamName + "'s Flag");+			_flagSpawns.get(index).getNpc()._CTF_FlagTeamName = teamName;+			_flagSpawns.get(index).getNpc()._isCTF_Flag = true;+			_flagSpawns.get(index).getNpc().decayMe();+			_flagSpawns.get(index).getNpc().spawnMe(_flagSpawns.get(index).getNpc().getX(), _flagSpawns.get(index).getNpc().getY(), _flagSpawns.get(index).getNpc().getZ());+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[spawnFlag(" + teamName + ")]: exception: " + e.getStackTrace());+		}+	}++	public static boolean InRangeOfFlag(Player _player, int flagIndex, int offset)+	{+		if (_player.getX() > CTF._flagsX.get(flagIndex) - offset && _player.getX() < CTF._flagsX.get(flagIndex) + offset && _player.getY() > CTF._flagsY.get(flagIndex) - offset && _player.getY() < CTF._flagsY.get(flagIndex) + offset && _player.getZ() > CTF._flagsZ.get(flagIndex) - offset && _player.getZ() < CTF._flagsZ.get(flagIndex) + offset)+			return true;+		return false;+	}++	public static void processInFlagRange(Player _player)+	{+		try+		{+			CheckRestoreFlags();+			for (String team : _teams)+			{+				if (team.equals(_player._teamNameCTF))+				{+					int indexOwn = _teams.indexOf(_player._teamNameCTF);++					// if player is near his team flag holding the enemy flag+					if (InRangeOfFlag(_player, indexOwn, 100) && !_flagsTaken.get(indexOwn) && _player._haveFlagCTF)+					{+						int indexEnemy = _teams.indexOf(_player._teamNameHaveFlagCTF);+						// return enemy flag to place+						_flagsTaken.set(indexEnemy, false);+						spawnFlag(_player._teamNameHaveFlagCTF);+						// remove the flag from this player+						_player.broadcastPacket(new SocialAction(_player, 16),2000); // amazing glow+						_player.broadcastUserInfo();+						_player.broadcastPacket(new SocialAction(_player, 3),2000); // Victory+						_player.broadcastUserInfo();+						removeFlagFromPlayer(_player);+						_teamPointsCount.set(indexOwn, teamPointsCount(team) + 1);+							+						_player.broadcastUserInfo();+						+						AnnounceToPlayers(false, _eventName + "(CTF): " + _player.getName() + " scores for " + _player._teamNameCTF + ".");+					}+				}+				else+				{+					int indexEnemy = _teams.indexOf(team);+					// if the player is near a enemy flag+					if (InRangeOfFlag(_player, indexEnemy, 100) && !_flagsTaken.get(indexEnemy) && !_player._haveFlagCTF && !_player.isDead())+					{+						if (_player.isRiding() || _player.isFlying())+						{+							_player.sendPacket(ActionFailed.STATIC_PACKET);+							break;+						}++						_flagsTaken.set(indexEnemy, true);+						unspawnFlag(team);+						_player._teamNameHaveFlagCTF = team;+						addFlagToPlayer(_player);+						_player.broadcastUserInfo();+						_player._haveFlagCTF = true;+						AnnounceToPlayers(false, _eventName + "(CTF): " + team + " flag taken by " + _player.getName() + "...");+						pointTeamTo(_player, team);+						break;+					}+				}+			}+		}+		catch (Exception e)+		{+			e.printStackTrace();+		}+	}++	public static void pointTeamTo(Player hasFlag, String ourFlag)+	{+		try+		{+			for (Player player : _players)+			{+				if (player != null && player.isOnline())+				{+					if (player._teamNameCTF.equals(ourFlag))+					{+						player.sendMessage(hasFlag.getName() + " took your flag!");+						if (player._haveFlagCTF)+						{+							player.sendMessage("You can not return the flag to headquarters, until your flag is returned to it's place.");+							player.sendPacket(new RadarControl(1, 1, player.getX(), player.getY(), player.getZ()));+						}+						else+						{+							player.sendPacket(new RadarControl(0, 1, hasFlag.getX(), hasFlag.getY(), hasFlag.getZ()));+							L2Radar rdr = new L2Radar(player);+							L2Radar.RadarOnPlayer radar = rdr.new RadarOnPlayer(hasFlag, player);+							ThreadPool.schedule(radar, 10000 + Rnd.get(30000));+						}+					}+				}+			}+		}+		catch (Throwable t)+		{+		}+	}++	public static int teamPointsCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamPointsCount.get(index);+	}++	public static void setTeamPointsCount(String teamName, int teamPointCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamPointsCount.set(index, teamPointCount);+	}++	public static int teamPlayersCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamPlayersCount.get(index);+	}++	public static void setTeamPlayersCount(String teamName, int teamPlayersCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamPlayersCount.set(index, teamPlayersCount);+	}++	public static void setNpcPos(Player activeChar)+	{+		_npcX = activeChar.getX();+		_npcY = activeChar.getY();+		_npcZ = activeChar.getZ();+		_npcHeading = activeChar.getHeading();+	}++	public static void setNpcPos(int x, int y, int z)+	{+		_npcX = x;+		_npcY = y;+		_npcZ = z;+	}++	public static void addTeam(String teamName)+	{+		if (!checkTeamOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[addTeam(" + teamName + ")]: checkTeamOk() = false");+			return;+		}++		if (teamName.equals(" "))+			return;++		_teams.add(teamName);+		_teamPlayersCount.add(0);+		_teamColors.add(0);+		_teamsX.add(0);+		_teamsY.add(0);+		_teamsZ.add(0);+		_teamPointsCount.add(0);+		addOrSet(_teams.indexOf(teamName), null, false, _FlagNPC, 0, 0, 0);+	}++	private static void addOrSet(int listSize, L2Spawn flagSpawn, boolean flagsTaken, int flagId, int flagX, int flagY, int flagZ)+	{+		while (_flagsX.size() <= listSize)+		{+			_flagSpawns.add(null);+			_flagsTaken.add(false);+			_flagIds.add(_FlagNPC);+			_flagsX.add(0);+			_flagsY.add(0);+			_flagsZ.add(0);+		}+		_flagSpawns.set(listSize, flagSpawn);+		_flagsTaken.set(listSize, flagsTaken);+		_flagIds.set(listSize, flagId);+		_flagsX.set(listSize, flagX);+		_flagsY.set(listSize, flagY);+		_flagsZ.set(listSize, flagZ);+	}++	public static boolean checkMaxLevel(int maxlvl)+	{+		if (_minlvl >= maxlvl)+			return false;++		return true;+	}++	public static boolean checkMinLevel(int minlvl)+	{+		if (_maxlvl <= minlvl)+			return false;++		return true;+	}++	/** returns true if participated players is higher or equal then minimum needed players +	 * @param players +	 * @return */+	public static boolean checkMinPlayers(int players)+	{+		if (_minPlayers <= players)+			return true;++		return false;+	}++	/** returns true if max players is higher or equal then participated players +	 * @param players +	 * @return */+	public static boolean checkMaxPlayers(int players)+	{+		if (_maxPlayers > players)+			return true;++		return false;+	}++	public static void removeTeam(String teamName)+	{+		if (!checkTeamOk() || _teams.isEmpty())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[removeTeam(" + teamName + ")]: checkTeamOk() = false");+			return;+		}++		if (teamPlayersCount(teamName) > 0)+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[removeTeam(" + teamName + ")]: teamPlayersCount(teamName) > 0");+			return;+		}++		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsZ.remove(index);+		_teamsY.remove(index);+		_teamsX.remove(index);+		_teamColors.remove(index);+		_teamPointsCount.remove(index);+		_teamPlayersCount.remove(index);+		_teams.remove(index);+		_flagSpawns.remove(index);+		_flagsTaken.remove(index);+		_flagIds.remove(index);+		_flagsX.remove(index);+		_flagsY.remove(index);+		_flagsZ.remove(index);+	}++	public static void setTeamPos(String teamName, Player activeChar)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsX.set(index, activeChar.getX());+		_teamsY.set(index, activeChar.getY());+		_teamsZ.set(index, activeChar.getZ());+	}++	public static void setTeamPos(String teamName, int x, int y, int z)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamsX.set(index, x);+		_teamsY.set(index, y);+		_teamsZ.set(index, z);+	}++	public static void setTeamColor(String teamName, int color)+	{+		if (!checkTeamOk())+			return;++		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamColors.set(index, color);+	}++	public static boolean checkTeamOk()+	{+		if (_started || _teleport || _joining)+			return false;++		return true;+	}++	public static void startJoin(Player activeChar)+	{+		if (!startJoinOk())+		{+			activeChar.sendMessage("Event not setted propertly.");+			if (Config.DEBUG)+				_log.fine("CTF Engine[startJoin(" + activeChar.getName() + ")]: startJoinOk() = false");+			return;+		}++		_joining = true;+		spawnEventNpc(activeChar);+		AnnounceToPlayers(true, _eventName + " (CTF)!");+		if (Config.CTF_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Joinable in " + _joiningLocationName + "!");+	}++	public static void startJoin()+	{+		if (!startJoinOk())+		{+			_log.warning(CTF.class.getSimpleName() + ":  Event not setted propertly.");+			if (Config.DEBUG)+				_log.fine("CTF Engine[startJoin(startJoinOk() = false");+			return;+		}++		_joining = true;+		spawnEventNpc();+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Joinable in " + _joiningLocationName + "!");+		if (Config.CTF_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+	}++	public static boolean startAutoJoin()+	{+		if (!startJoinOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[startJoin]: startJoinOk() = false");+			return false;+		}++		_joining = true;+		spawnEventNpc();+		AnnounceToPlayers(true, _eventName + " (CTF)!");+		if (Config.CTF_ANNOUNCE_REWARD)+			AnnounceToPlayers(true, "Reward: " + _rewardAmount + " " + ItemTable.getInstance().getTemplate(_rewardId).getName());+		AnnounceToPlayers(true, "Recruiting levels " + _minlvl + " to " + _maxlvl);+		AnnounceToPlayers(true, "Joinable in " + _joiningLocationName + "!");+		return true;+	}++	public static boolean startJoinOk()+	{+		if (_started || _teleport || _joining || _teams.size() < 2 || _eventName.equals("") || _joiningLocationName.equals("") || _eventDesc.equals("") || _npcId == 0 || _npcX == 0 || _npcY == 0 || _npcZ == 0 || _rewardId == 0 || _rewardAmount == 0 || _teamsX.contains(0) || _teamsY.contains(0) || _teamsZ.contains(0))+			return false;+		try+		{+			if (_flagsX.contains(0) || _flagsY.contains(0) || _flagsZ.contains(0) || _flagIds.contains(0))+				return false;+			if (_flagsX.size() < _teams.size() || _flagsY.size() < _teams.size() || _flagsZ.size() < _teams.size() || _flagIds.size() < _teams.size())+				return false;+		}+		catch (ArrayIndexOutOfBoundsException e)+		{+			return false;+		}+		return true;+	}++	private static void spawnEventNpc(Player activeChar)+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);+			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, _npcHeading);+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobCTF = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[spawnEventNpc(" + activeChar.getName() + ")]: exception: " + e.getMessage());+		}+	}++	private static void spawnEventNpc()+	{+		NpcTemplate tmpl = NpcTable.getInstance().getTemplate(_npcId);++		try+		{+			_npcSpawn = new L2Spawn(tmpl);++			_npcSpawn.setLoc(_npcX, _npcY, _npcZ, _npcHeading);+			_npcSpawn.setRespawnDelay(1);++			SpawnTable.getInstance().addNewSpawn(_npcSpawn, false);++			_npcSpawn.setRespawnState(true);+			_npcSpawn.doSpawn(false);+			_npcSpawn.getNpc().getStatus().setCurrentHp(999999999);+			_npcSpawn.getNpc().setTitle(_eventName);+			_npcSpawn.getNpc()._isEventMobCTF = true;+			_npcSpawn.getNpc().isAggressive();+			_npcSpawn.getNpc().decayMe();+			_npcSpawn.getNpc().spawnMe(_npcSpawn.getNpc().getX(), _npcSpawn.getNpc().getY(), _npcSpawn.getNpc().getZ());++			_npcSpawn.getNpc().broadcastPacket(new MagicSkillUse(_npcSpawn.getNpc(), _npcSpawn.getNpc(), 1034, 1, 1, 1));+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[spawnEventNpc(exception: " + e.getMessage());+		}+	}++	public static void teleportStart()+	{+		if (!_joining || _started || _teleport)+			return;++		if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && checkMinPlayers(_playersShuffle.size()))+		{+			removeOfflinePlayers();+			shuffleTeams();+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && !checkMinPlayers(_playersShuffle.size()))+		{+			AnnounceToPlayers(true, "Not enough players for event. Min Requested : " + _minPlayers + ", Participating : " + _playersShuffle.size());+			return;+		}++		_joining = false;+		AnnounceToPlayers(true, _eventName + "(CTF): Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				CTF.sit();+				CTF.spawnAllFlags();+				for (Player player : _players)+				{+					if (player != null)+					{+						if (Config.CTF_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+								Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+									if (e != null)+										e.exit();++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}++						if (Config.CTF_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}+						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameCTF)), _teamsY.get(_teams.indexOf(player._teamNameCTF)), _teamsZ.get(_teams.indexOf(player._teamNameCTF)), 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+	}++	public static boolean teleportAutoStart()+	{+		if (!_joining || _started || _teleport)+			return false;++		if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && checkMinPlayers(_playersShuffle.size()))+		{+			removeOfflinePlayers();+			shuffleTeams();+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && !checkMinPlayers(_playersShuffle.size()))+		{+			AnnounceToPlayers(true, "Not enough players for event. Min Requested : " + _minPlayers + ", Participating : " + _playersShuffle.size());+			return false;+		}++		_joining = false;+		AnnounceToPlayers(false, _eventName + "(CTF): Teleport to team spot in 20 seconds!");++		setUserData();+		ThreadPool.schedule(new Runnable()+		{+			@Override+			public void run()+			{+				sit();+				spawnAllFlags();++				for (Player player : _players)+				{+					if (player != null)+					{+						if (Config.CTF_ON_START_UNSUMMON_PET)+						{+							// Remove Summon's buffs+							if (player.getPet() != null)+							{+								Summon summon = player.getPet();+								for (L2Effect e : summon.getAllEffects())+									if (e != null)+										e.exit();++								if (summon instanceof Pet)+									summon.unSummon(player);+							}+						}+						if (Config.CTF_ON_START_REMOVE_ALL_EFFECTS)+						{+							for (L2Effect e : player.getAllEffects())+							{+								if (e != null)+									e.exit();+							}+						}++						// Remove player from his party+						if (player.getParty() != null)+						{+							Party party = player.getParty();+							party.removePartyMember(player, MessageType.EXPELLED);+						}++						player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameCTF)), _teamsY.get(_teams.indexOf(player._teamNameCTF)), _teamsZ.get(_teams.indexOf(player._teamNameCTF)), 0);+					}+				}+			}+		}, 20000);+		_teleport = true;+		return true;+	}++	public static void startEvent(Player activeChar)+	{+		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[startEvent(" + activeChar.getName() + ")]: startEventOk() = false");+			return;+		}++		_teleport = false;+		sit();+		_started = true;+		StartEvent();+	}++	public static void setJoinTime(int time)+	{+		_joinTime = time;+	}++	public static void setEventTime(int time)+	{+		_eventTime = time;+	}++	public static boolean startAutoEvent()+	{+		if (!startEventOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[startEvent]: startEventOk() = false");+			return false;+		}++		_teleport = false;+		sit();+		AnnounceToPlayers(true, _eventName + "(CTF): Started. Go Capture the Flags!");+		_started = true;+		return true;+	}++	public static synchronized void autoEvent()+	{+		if (startAutoJoin())+		{+			if (_joinTime > 0)+				waiter(_joinTime * 60 * 1000); // minutes for join event+			else if (_joinTime <= 0)+			{+				abortEvent();+				return;+			}+			if (teleportAutoStart())+			{+				waiter(1 * 30 * 1000); // 30 seconds wait time until start fight after teleported+				if (startAutoEvent())+				{+					waiter(_eventTime * 60 * 1000); // minutes for event time+					finishEvent();+				}+			}+			else if (!teleportAutoStart())+			{+				abortEvent();+			}+		}+	}++	private static synchronized void waiter(long interval)+	{+		long startWaiterTime = System.currentTimeMillis();+		int seconds = (int) (interval / 1000);++		while (startWaiterTime + interval > System.currentTimeMillis())+		{+			seconds--; // here because we don't want to see two time announce at the same time++			if (_joining || _started || _teleport)+			{+				switch (seconds)+				{+					case 3600: // 1 hour left+						if (_joining)+						{+							AnnounceToPlayers(true, _eventName + "(CTF): Joinable in " + _joiningLocationName + "!");+							AnnounceToPlayers(true, "CTF Event: " + seconds / 60 / 60 + " hour(s) till registration close!");+						}+						else if (_started)+							AnnounceToPlayers(false, "CTF Event: " + seconds / 60 / 60 + " hour(s) till event finish!");++					break;+					case 1800: // 30 minutes left+					case 600: // 10 minutes left+					case 180: // 3 minutes left+					case 120: // 2 minutes left+					case 60: // 1 minute left+						if (_joining)+						{+							removeOfflinePlayers();+							AnnounceToPlayers(true, _eventName + "(CTF): Joinable in " + _joiningLocationName + "!");+							AnnounceToPlayers(true, "CTF Event: " + seconds / 60 + " minute(s) till registration ends!");+						}+						else if (_started)+							AnnounceToPlayers(false, "CTF Event: " + seconds / 60 + " minute(s) till event ends!");++					break;+					case 30: // 30 seconds left+					case 10: // 10 seconds left+					case 3: // 3 seconds left+					case 2: // 2 seconds left+					case 1: // 1 seconds left+						if (_joining)+							AnnounceToPlayers(true, "CTF Event: " + seconds + " second(s) till registration close!");+						else if (_teleport)+							AnnounceToPlayers(false, "CTF Event: " + seconds + " seconds(s) till fight starts!");+						else if (_started)+							AnnounceToPlayers(false, "CTF Event: " + seconds + " second(s) till event ends!");++					break;+				}+			}++			long startOneSecondWaiterStartTime = System.currentTimeMillis();++			// only the try catch with Thread.sleep(1000) give bad countdown on high wait times+			while (startOneSecondWaiterStartTime + 1000 > System.currentTimeMillis())+			{+				try+				{+					Thread.sleep(1);+				}+				catch (InterruptedException ie)+				{+				}+			}+		}+	}++	private static boolean startEventOk()+	{+		if (_joining || !_teleport || _started)+			return false;++		if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+		{+			if (_teamPlayersCount.contains(0))+				return false;+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+		{+			List<Player> playersShuffleTemp = new ArrayList<>();+			int loopCount = 0;++			loopCount = _playersShuffle.size();++			for (int i = 0; i < loopCount; i++)+			{+				if (_playersShuffle != null)+					playersShuffleTemp.add(_playersShuffle.get(i));+			}++			_playersShuffle = playersShuffleTemp;+			playersShuffleTemp.clear();++			// if (_playersShuffle.size() < (_teams.size()*2)){+			// return false;+			// }+		}++		return true;+	}++	public static void shuffleTeams()+	{+		int teamCount = 0, playersCount = 0;++		for (;;)+		{+			if (_playersShuffle.isEmpty())+				break;++			int playerToAddIndex = Rnd.nextInt(_playersShuffle.size());+			Player player = null;+			player = _playersShuffle.get(playerToAddIndex);+			player._originalNameColorCTF = player.getAppearance().getNameColor();+			player._originalKarmaCTF = player.getKarma();++			_players.add(player);+			_players.get(playersCount)._teamNameCTF = _teams.get(teamCount);+			_savePlayers.add(_players.get(playersCount).getName());+			_savePlayerTeams.add(_teams.get(teamCount));+			playersCount++;++			if (teamCount == _teams.size() - 1)+				teamCount = 0;+			else+				teamCount++;++			_playersShuffle.remove(playerToAddIndex);+		}+	}++	public static void setUserData()+	{+		for (Player player : _players)+		{+			player.getAppearance().setNameColor(_teamColors.get(_teams.indexOf(player._teamNameCTF)));+			player.setKarma(0);+			player.broadcastUserInfo();+		}+	}++	public static void finishEvent()+	{+		if (!finishEventOk())+		{+			if (Config.DEBUG)+				_log.fine("CTF Engine[finishEvent]: finishEventOk() = false");+			return;+		}++		_started = false;+		unspawnEventNpc();+		unspawnAllFlags();+		processTopTeam();++		if (_topScore != 0)+			playKneelAnimation(_topTeam);++		if (Config.CTF_ANNOUNCE_TEAM_STATS)+		{+			AnnounceToPlayers(true, _eventName + " Team Statistics:");+			for (String team : _teams)+			{+				int _flags_ = teamFlagCount(team);+				AnnounceToPlayers(true, "Team: " + team + " - Flags taken: " + _flags_);+			}+		}++		teleportFinish();+	}++	// show losers and winners animations+	public static void playKneelAnimation(String teamName)+	{+		for (Player player : _players)+		{+			if (player != null && player.isOnline() && player._inEventCTF == true)+			{+				if (!player._teamNameCTF.equals(teamName))+				{+					player.broadcastPacket(new SocialAction(player, 7),2000);+				}+				else if (player._teamNameCTF.equals(teamName))+				{+					player.broadcastPacket(new SocialAction(player, 3),2000);+				}+			}+		}+	}++	private static boolean finishEventOk()+	{+		if (!_started)+			return false;++		return true;+	}++	public static void rewardTeam(String teamName)+	{+		for (Player player : _players)+		{+			if (player != null)+			{+				if (player._teamNameCTF.equals(teamName))+				{+					player.addItem("CTF Event: " + _eventName, _rewardId, _rewardAmount, player, true);++					NpcHtmlMessage nhm = new NpcHtmlMessage(5);+					StringBuilder replyMSG = new StringBuilder();++					replyMSG.append("<html><body>Your team wins the event. Look in your inventory for the reward.</body></html>");++					nhm.setHtml(replyMSG.toString());+					player.sendPacket(nhm);++					// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+					player.sendPacket(ActionFailed.STATIC_PACKET);+				}+			}+		}+	}++	public static void abortEvent()+	{+		if (!_joining && !_teleport && !_started)+			return;+		if (_joining && !_teleport && !_started)+		{+			unspawnEventNpc();+			cleanCTF();+			_joining = false;+			AnnounceToPlayers(true, _eventName + "(CTF): Match aborted!");+			return;+		}+		_joining = false;+		_teleport = false;+		_started = false;+		unspawnEventNpc();+		unspawnAllFlags();+		AnnounceToPlayers(true, _eventName + "(CTF): Match aborted!");+		teleportFinish();+	}++	public static void sit()+	{+		if (_sitForced)+			_sitForced = false;+		else+			_sitForced = true;++		for (Player player : _players)+		{+			if (player != null)+			{+				if (_sitForced)+				{+					player.stopMove(null);+					player.abortAttack();+					player.abortCast();++					if (!player.isSitting())+						player.sitDown();+				}+				else+				{+					if (player.isSitting())+						player.standUp();+				}+			}+		}+	}++	public static void dumpData()+	{+		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  ");++		if (!_joining && !_teleport && !_started)+		{+			_log.warning(CTF.class.getSimpleName() + ":  <<---------------------------------->>");+			_log.warning(CTF.class.getSimpleName() + ":  >> CTF Engine infos dump (INACTIVE) <<");+			_log.warning(CTF.class.getSimpleName() + ":  <<--^----^^-----^----^^------^^----->>");+		}+		else if (_joining && !_teleport && !_started)+		{+			_log.warning(CTF.class.getSimpleName() + ":  <<--------------------------------->>");+			_log.warning(CTF.class.getSimpleName() + ":  >> CTF Engine infos dump (JOINING) <<");+			_log.warning(CTF.class.getSimpleName() + ":  <<--^----^^-----^----^^------^----->>");+		}+		else if (!_joining && _teleport && !_started)+		{+			_log.warning(CTF.class.getSimpleName() + ":  <<---------------------------------->>");+			_log.warning(CTF.class.getSimpleName() + ":  >> CTF Engine infos dump (TELEPORT) <<");+			_log.warning(CTF.class.getSimpleName() + ":  <<--^----^^-----^----^^------^^----->>");+		}+		else if (!_joining && !_teleport && _started)+		{+			_log.warning(CTF.class.getSimpleName() + ":  <<--------------------------------->>");+			_log.warning(CTF.class.getSimpleName() + ":  >> CTF Engine infos dump (STARTED) <<");+			_log.warning(CTF.class.getSimpleName() + ":  <<--^----^^-----^----^^------^----->>");+		}++		_log.warning(CTF.class.getSimpleName() + ":  Name: " + _eventName);+		_log.warning(CTF.class.getSimpleName() + ":  Desc: " + _eventDesc);+		_log.warning(CTF.class.getSimpleName() + ":  Join location: " + _joiningLocationName);+		_log.warning(CTF.class.getSimpleName() + ":  Min lvl: " + _minlvl);+		_log.warning(CTF.class.getSimpleName() + ":  Max lvl: " + _maxlvl);+		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  ##########################");+		_log.warning(CTF.class.getSimpleName() + ":  # _teams(Vector<String>) #");+		_log.warning(CTF.class.getSimpleName() + ":  ##########################");++		for (String team : _teams)+			_log.warning(CTF.class.getSimpleName() + ": " + team + " Flags Taken :" + _teamPointsCount.get(_teams.indexOf(team)));++		if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+		{+			_log.warning(CTF.class.getSimpleName() + ":  ");+			_log.warning(CTF.class.getSimpleName() + ":  #########################################");+			_log.warning(CTF.class.getSimpleName() + ":  # _playersShuffle(Vector<Player>) #");+			_log.warning(CTF.class.getSimpleName() + ":  #########################################");++			for (Player player : _playersShuffle)+			{+				if (player != null)+					_log.warning(CTF.class.getSimpleName() + ":  Name: " + player.getName());+			}+		}++		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  ##################################");+		_log.warning(CTF.class.getSimpleName() + ":  # _players(Vector<Player>) #");+		_log.warning(CTF.class.getSimpleName() + ":  ##################################");++		for (Player player : _players)+		{+			if (player != null)+				_log.warning(CTF.class.getSimpleName() + ":  Name: " + player.getName() + "   Team: " + player._teamNameCTF + "  Flags :" + player._countCTFflags);+		}++		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  #####################################################################");+		_log.warning(CTF.class.getSimpleName() + ":  # _savePlayers(Vector<String>) and _savePlayerTeams(Vector<String>) #");+		_log.warning(CTF.class.getSimpleName() + ":  #####################################################################");++		for (String player : _savePlayers)+			_log.warning(CTF.class.getSimpleName() + ":  Name: " + player + "	Team: " + _savePlayerTeams.get(_savePlayers.indexOf(player)));++		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  ");+		_log.warning(CTF.class.getSimpleName() + ":  **********==CTF==************");+		_log.warning(CTF.class.getSimpleName() + ":  CTF._teamPointsCount:" + _teamPointsCount.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagIds:" + _flagIds.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagSpawns:" + _flagSpawns.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._throneSpawns:" + _throneSpawns.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagsTaken:" + _flagsTaken.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagsX:" + _flagsX.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagsY:" + _flagsY.toString());+		_log.warning(CTF.class.getSimpleName() + ":  CTF._flagsZ:" + _flagsZ.toString());+		_log.warning(CTF.class.getSimpleName() + ":  ************EOF**************");+		_log.warning(CTF.class.getSimpleName() + ":  ");+	}++	public static void loadData()+	{+		_eventName = new String();+		_eventDesc = new String();+		_topTeam = new String();+		_joiningLocationName = new String();+		_teams = new ArrayList<>();+		_savePlayers = new ArrayList<>();+		_savePlayerTeams = new ArrayList<>();+		_players = new ArrayList<>();+		_playersShuffle = new ArrayList<>();+		_teamPlayersCount = new ArrayList<>();+		_teamPointsCount = new ArrayList<>();+		_teamColors = new ArrayList<>();+		_teamsX = new ArrayList<>();+		_teamsY = new ArrayList<>();+		_teamsZ = new ArrayList<>();++		_throneSpawns = new ArrayList<>();+		_flagSpawns = new ArrayList<>();+		_flagsTaken = new ArrayList<>();+		_flagIds = new ArrayList<>();+		_flagsX = new ArrayList<>();+		_flagsY = new ArrayList<>();+		_flagsZ = new ArrayList<>();++		_joining = false;+		_teleport = false;+		_started = false;+		_sitForced = false;+		_npcId = 0;+		_npcX = 0;+		_npcY = 0;+		_npcZ = 0;+		_npcHeading = 0;+		_rewardId = 0;+		_rewardAmount = 0;+		_topScore = 0;+		_minlvl = 0;+		_maxlvl = 0;+		_joinTime = 0;+		_eventTime = 0;+		_minPlayers = 0;+		_maxPlayers = 0;++		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;+			ResultSet rs;++			statement = con.prepareStatement("SELECT * FROM ctf");+			rs = statement.executeQuery();++			int teams = 0;++			while (rs.next())+			{+				_eventName = rs.getString("eventName");+				_eventDesc = rs.getString("eventDesc");+				_joiningLocationName = rs.getString("joiningLocation");+				_minlvl = rs.getInt("minlvl");+				_maxlvl = rs.getInt("maxlvl");+				_npcId = rs.getInt("npcId");+				_npcX = rs.getInt("npcX");+				_npcY = rs.getInt("npcY");+				_npcZ = rs.getInt("npcZ");+				_npcHeading = rs.getInt("npcHeading");+				_rewardId = rs.getInt("rewardId");+				_rewardAmount = rs.getInt("rewardAmount");+				teams = rs.getInt("teamsCount");+				_joinTime = rs.getInt("joinTime");+				_eventTime = rs.getInt("eventTime");+				_minPlayers = rs.getInt("minPlayers");+				_maxPlayers = rs.getInt("maxPlayers");+			}+			rs.close();+			statement.close();++			int index = -1;+			if (teams > 0)+				index = 0;+			while (index < teams && index > -1)+			{+				statement = con.prepareStatement("SELECT * FROM ctf_teams WHERE teamId=?");+				statement.setInt(1, index);+				rs = statement.executeQuery();+				while (rs.next())+				{+					_teams.add(rs.getString("teamName"));+					_teamPlayersCount.add(0);+					_teamPointsCount.add(0);+					_teamColors.add(0);+					_teamsX.add(0);+					_teamsY.add(0);+					_teamsZ.add(0);+					_teamsX.set(index, rs.getInt("teamX"));+					_teamsY.set(index, rs.getInt("teamY"));+					_teamsZ.set(index, rs.getInt("teamZ"));+					_teamColors.set(index, rs.getInt("teamColor"));+					_flagsX.add(0);+					_flagsY.add(0);+					_flagsZ.add(0);+					_flagsX.set(index, rs.getInt("flagX"));+					_flagsY.set(index, rs.getInt("flagY"));+					_flagsZ.set(index, rs.getInt("flagZ"));+					_flagSpawns.add(null);+					_flagIds.add(_FlagNPC);+					_flagsTaken.add(false);++				}+				index++;+				rs.close();+				statement.close();+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  Exception: CTF.loadData(): " + e.getMessage());+		}+	}++	public static void saveData()+	{+		try (Connection con = L2DatabaseFactory.getInstance().getConnection())+		{+			PreparedStatement statement;++			statement = con.prepareStatement("DELETE FROM ctf");+			statement.execute();+			statement.close();++			statement = con.prepareStatement("INSERT INTO ctf (eventName, eventDesc, joiningLocation, minlvl, maxlvl, npcId, npcX, npcY, npcZ, npcHeading, rewardId, rewardAmount, teamsCount, joinTime, eventTime, minPlayers, maxPlayers) VALUES (?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?,?)");+			statement.setString(1, _eventName);+			statement.setString(2, _eventDesc);+			statement.setString(3, _joiningLocationName);+			statement.setInt(4, _minlvl);+			statement.setInt(5, _maxlvl);+			statement.setInt(6, _npcId);+			statement.setInt(7, _npcX);+			statement.setInt(8, _npcY);+			statement.setInt(9, _npcZ);+			statement.setInt(10, _npcHeading);+			statement.setInt(11, _rewardId);+			statement.setInt(12, _rewardAmount);+			statement.setInt(13, _teams.size());+			statement.setInt(14, _joinTime);+			statement.setInt(15, _eventTime);+			statement.setInt(16, _minPlayers);+			statement.setInt(17, _maxPlayers);+			statement.execute();+			statement.close();++			statement = con.prepareStatement("DELETE FROM ctf_teams");+			statement.execute();+			statement.close();++			for (String teamName : _teams)+			{+				int index = _teams.indexOf(teamName);++				if (index == -1)+					return;+				statement = con.prepareStatement("INSERT INTO ctf_teams (teamId ,teamName, teamX, teamY, teamZ, teamColor, flagX, flagY, flagZ) VALUES (?,?,?,?,?,?,?,?,?)");+				statement.setInt(1, index);+				statement.setString(2, teamName);+				statement.setInt(3, _teamsX.get(index));+				statement.setInt(4, _teamsY.get(index));+				statement.setInt(5, _teamsZ.get(index));+				statement.setInt(6, _teamColors.get(index));+				statement.setInt(7, _flagsX.get(index));+				statement.setInt(8, _flagsY.get(index));+				statement.setInt(9, _flagsZ.get(index));+				statement.execute();+				statement.close();+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  Exception: CTF.saveData(): " + e.getMessage());+		}+	}++	public static void showEventHtml(Player eventPlayer, String objectId)+	{+		try+		{+			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+			StringBuilder replyMSG = new StringBuilder();++			replyMSG.append("<html><body>");+			replyMSG.append("CTF Match<br><br><br>");+			replyMSG.append("Current event...<br>");+			replyMSG.append("   ... description:&nbsp;<font color=\"00FF00\">" + _eventDesc + "</font><br>");+			if (Config.CTF_ANNOUNCE_REWARD)+				replyMSG.append("   ... reward: (" + _rewardAmount + ") " + ItemTable.getInstance().getTemplate(_rewardId).getName() + "<br>");++			if (!_started && !_joining)+				replyMSG.append("<center>Wait till the admin/gm start the participation.</center>");+			else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && !checkMaxPlayers(_playersShuffle.size()))+			{+				if (!CTF._started)+				{+					replyMSG.append("<font color=\"FFFF00\">The event has reached its maximum capacity.</font><br>Keep checking, someone may crit and you can steal their spot.");+				}+			}+			else if (eventPlayer.isCursedWeaponEquipped() && !Config.CTF_JOIN_CURSED)+			{+				replyMSG.append("<font color=\"FFFF00\">You can't participate in this event with a cursed Weapon.</font><br>");+			}+			else if (!_started && _joining && eventPlayer.getLevel() >= _minlvl && eventPlayer.getLevel() <= _maxlvl)+			{+				if (_players.contains(eventPlayer) || checkShufflePlayers(eventPlayer))+				{+					if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+						replyMSG.append("You are already participating in team <font color=\"LEVEL\">" + eventPlayer._teamNameCTF + "</font><br><br>");+					else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+						replyMSG.append("You are already participating!<br><br>");++					replyMSG.append("<table border=\"0\"><tr>");+					replyMSG.append("<td width=\"200\">Wait till event start or</td>");+					replyMSG.append("<td width=\"60\"><center><button value=\"remove\" action=\"bypass -h npc_" + objectId + "_ctf_player_leave\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></center></td>");+					replyMSG.append("<td width=\"100\">your participation!</td>");+					replyMSG.append("</tr></table>");+				}+				else+				{+					replyMSG.append("<td width=\"200\">Your level : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Min level : <font color=\"00FF00\">" + _minlvl + "</font></td><br>");+					replyMSG.append("<td width=\"200\">Max level : <font color=\"00FF00\">" + _maxlvl + "</font></td><br><br>");++					if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+					{+						replyMSG.append("<center><table border=\"0\">");++						for (String team : _teams)+						{+							replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font>&nbsp;(" + teamPlayersCount(team) + " joined)</td>");+							replyMSG.append("<td width=\"60\"><button value=\"Join\" action=\"bypass -h npc_" + objectId + "_ctf_player_join " + team + "\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td></tr>");+						}++						replyMSG.append("</table></center>");+					}+					else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+					{+						replyMSG.append("<center><table border=\"0\">");++						for (String team : _teams)+							replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font></td>");++						replyMSG.append("</table></center><br>");++						replyMSG.append("<button value=\"Join\" action=\"bypass -h npc_" + objectId + "_ctf_player_join eventShuffle\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\">");+						replyMSG.append("Teams will be randomly generated!");+					}+				}+			}+			else if (_started && !_joining)+				replyMSG.append("<center>CTF match is in progress.</center>");+			else if (eventPlayer.getLevel() < _minlvl || eventPlayer.getLevel() > _maxlvl)+			{+				replyMSG.append("Your lvl : <font color=\"00FF00\">" + eventPlayer.getLevel() + "</font><br>");+				replyMSG.append("Min level : <font color=\"00FF00\">" + _minlvl + "</font><br>");+				replyMSG.append("Max level : <font color=\"00FF00\">" + _maxlvl + "</font><br><br>");+				replyMSG.append("<font color=\"FFFF00\">You can't participatein this event.</font><br>");+			}+			// Show how many players joined & how many are still needed to join+			replyMSG.append("<br>There are " + _playersShuffle.size() + " player(s) participating in this event.<br>");+			if (_joining)+			{+				if (_playersShuffle.size() < _minPlayers)+				{+					int playersNeeded = _minPlayers - _playersShuffle.size();+					replyMSG.append("The event will not start unless " + playersNeeded + " more player(s) joins!");+				}+			}++			replyMSG.append("</body></html>");+			adminReply.setHtml(replyMSG.toString());+			eventPlayer.sendPacket(adminReply);++			// Send a Server->Client ActionFailed to the Player in order to avoid that the client wait another packet+			eventPlayer.sendPacket(ActionFailed.STATIC_PACKET);+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine[showEventHtlm(" + eventPlayer.getName() + ", " + objectId + ")]: exception" + e.getMessage());+		}+	}++	public static void addPlayer(Player player, String teamName)+	{+		if (!addPlayerOk(teamName, player))+			return;++		if (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE"))+		{+			player._teamNameCTF = teamName;+			_players.add(player);+			setTeamPlayersCount(teamName, teamPlayersCount(teamName) + 1);+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+			_playersShuffle.add(player);++		player._inEventCTF = true;+		player._countCTFflags = 0;+	}++	public static synchronized void removeOfflinePlayers()+	{+		try+		{+			if (_playersShuffle == null)+				return;+			else if (_playersShuffle.isEmpty())+				return;+			else if (_playersShuffle.size() > 0)+			{+				for (Player player : _playersShuffle)+				{+					if (player == null)+						_playersShuffle.remove(player);+					else if (player.isOnline() || player.isInJail())+						removePlayer(player);+					if (_playersShuffle.size() == 0 || _playersShuffle.isEmpty())+						break;+				}+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Engine exception: " + e.getMessage());+			return;+		}+	}++	public static boolean checkShufflePlayers(Player eventPlayer)+	{+		try+		{+			for (Player player : _playersShuffle)+			{+				if (player == null || player.isOnline())+				{+					_playersShuffle.remove(player);+					eventPlayer._inEventCTF = false;+					continue;+				}+				else if (player.getObjectId() == eventPlayer.getObjectId())+				{+					eventPlayer._inEventCTF = true;+					eventPlayer._countCTFflags = 0;+					return true;+				}+				// this 1 is in case player got new object id after DC or reconnect+				else if (player.getName().equals(eventPlayer.getName()))+				{+					_playersShuffle.remove(player);+					_playersShuffle.add(eventPlayer);+					eventPlayer._inEventCTF = true;+					eventPlayer._countCTFflags = 0;+					return true;+				}+			}+		}+		catch (Exception e)+		{+		}+		return false;+	}++	public static boolean addPlayerOk(String teamName, Player eventPlayer)+	{+		try+		{+			if (checkShufflePlayers(eventPlayer) || eventPlayer._inEventCTF)+			{+				eventPlayer.sendMessage("You are already participating in the event!");+				return false;+			}++			for (Player player : _players)+			{+				if (player.getObjectId() == eventPlayer.getObjectId())+				{+					eventPlayer.sendMessage("You are already participating in the event!");+					return false;+				}+				else if (player.getName() == eventPlayer.getName())+				{+					eventPlayer.sendMessage("You are already participating in the event!");+					return false;+				}+			}+			if (_players.contains(eventPlayer))+			{+				eventPlayer.sendMessage("You are already participating in the event!");+				return false;+			}+		}+		catch (Exception e)+		{+			_log.warning(CTF.class.getSimpleName() + ":  CTF Siege Engine exception: " + e.getMessage());+		}++		if (Config.CTF_EVEN_TEAMS.equals("NO"))+			return true;+		else if (Config.CTF_EVEN_TEAMS.equals("BALANCE"))+		{+			boolean allTeamsEqual = true;+			int countBefore = -1;++			for (int playersCount : _teamPlayersCount)+			{+				if (countBefore == -1)+					countBefore = playersCount;++				if (countBefore != playersCount)+				{+					allTeamsEqual = false;+					break;+				}++				countBefore = playersCount;+			}++			if (allTeamsEqual)+				return true;++			countBefore = Integer.MAX_VALUE;++			for (int teamPlayerCount : _teamPlayersCount)+			{+				if (teamPlayerCount < countBefore)+					countBefore = teamPlayerCount;+			}++			List<String> joinableTeams = new ArrayList<>();++			for (String team : _teams)+			{+				if (teamPlayersCount(team) == countBefore)+					joinableTeams.add(team);+			}++			if (joinableTeams.contains(teamName))+				return true;+		}+		else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE"))+			return true;++		eventPlayer.sendMessage("Too many players in team \"" + teamName + "\"");+		return false;+	}++	public static synchronized void addDisconnectedPlayer(Player player)+	{+		/*+		 * !!! CAUTION !!!+		 * Do NOT fix multiple object Ids on this event or you will ruin the flag reposition check!!!+		 * All Multiple object Ids will be collected by the Garbage Collector, after the event ends, memory sweep is made!!!+		 */++		if ((Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && (_teleport || _started)) || (Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE") && (_teleport || _started)))+		{+			if (Config.CTF_ON_START_REMOVE_ALL_EFFECTS)+			{+				for (L2Effect e : player.getAllEffects())+				{+					if (e != null)+						e.exit();+				}+			}++			player._teamNameCTF = _savePlayerTeams.get(_savePlayers.indexOf(player.getName()));+			for (Player p : _players)+			{+				if (p == null)+				{+					continue;+				}+				// check by name in case player got new objectId+				else if (p.getName().equals(player.getName()))+				{+					player._originalNameColorCTF = player.getAppearance().getNameColor();+					player._originalKarmaCTF = player.getKarma();+					player._inEventCTF = true;+					player._countCTFflags = p._countCTFflags;+					_players.remove(p); // removing old object id from vector+					_players.add(player); // adding new objectId to vector+					break;+				}+			}+			player.getAppearance().setNameColor(_teamColors.get(_teams.indexOf(player._teamNameCTF)));+			player.setKarma(0);+			player.broadcastUserInfo();+			player.teleToLocation(_teamsX.get(_teams.indexOf(player._teamNameCTF)), _teamsY.get(_teams.indexOf(player._teamNameCTF)), _teamsZ.get(_teams.indexOf(player._teamNameCTF)), 0);+			Started(player);+			CheckRestoreFlags();+		}+	}++	public static void removePlayer(Player player)+	{+		if (player._inEventCTF)+		{+			if (!_joining)+			{+				player.getAppearance().setNameColor(player._originalNameColorCTF);+				player.setKarma(player._originalKarmaCTF);+				player.broadcastUserInfo();+			}+			player._teamNameCTF = new String();+			player._countCTFflags = 0;+			player._inEventCTF = false;++			if ((Config.CTF_EVEN_TEAMS.equals("NO") || Config.CTF_EVEN_TEAMS.equals("BALANCE")) && _players.contains(player))+			{+				setTeamPlayersCount(player._teamNameCTF, teamPlayersCount(player._teamNameCTF) - 1);+				_players.remove(player);+			}+			else if (Config.CTF_EVEN_TEAMS.equals("SHUFFLE") && (!_playersShuffle.isEmpty() && _playersShuffle.contains(player)))+				_playersShuffle.remove(player);+		}+	}++	public static void cleanCTF()+	{+		_log.warning(CTF.class.getSimpleName() + ":  CTF : Cleaning players.");+		for (Player player : _players)+		{+			if (player != null)+			{+				if (player._haveFlagCTF)+					removeFlagFromPlayer(player);+				else+					player.getInventory().destroyItemByItemId("", CTF._FLAG_IN_HAND_ITEM_ID, 1, player, null);+				player._haveFlagCTF = false;+				removePlayer(player);+				if (_savePlayers.contains(player.getName()))+					_savePlayers.remove(player.getName());+				player._inEventCTF = false;+			}+		}+		if (_playersShuffle != null && !_playersShuffle.isEmpty())+		{+			for (Player player : _playersShuffle)+			{+				if (player != null)+					player._inEventCTF = false;+			}+		}+		_log.warning(CTF.class.getSimpleName() + ":  CTF : Cleaning teams and flags.");+		for (String team : _teams)+		{+			int index = _teams.indexOf(team);+			_teamPointsCount.set(index, 0);+			_flagSpawns.set(index, null);+			_flagsTaken.set(index, false);+			_teamPlayersCount.set(index, 0);+			_teamPointsCount.set(index, 0);+		}+		_topScore = 0;+		_topTeam = new String();+		_players.clear();+		_playersShuffle.clear();+		_savePlayers.clear();+		_savePlayerTeams.clear();+		_teamPointsCount.clear();+		_flagSpawns.clear();+		_flagsTaken.clear();+		_teamPlayersCount.clear();+		_log.warning(CTF.class.getSimpleName() + ":  Cleaning CTF done.");+		_log.warning(CTF.class.getSimpleName() + ":  Loading new data from MySql");+		loadData();+	}++	public static void unspawnEventNpc()+	{+		if (_npcSpawn == null)+			return;++		_npcSpawn.getNpc().deleteMe();+		_npcSpawn.setRespawnState(false);+		SpawnTable.getInstance().deleteSpawn(_npcSpawn, true);+	}++	public static void teleportFinish()+	{+		AnnounceToPlayers(false, _eventName + "(CTF): Teleport back to participation NPC in 20 seconds!");+		ThreadPool.schedule(new Runnable()+		{+			@SuppressWarnings("synthetic-access")+			@Override+			public void run()+			{+				for (Player player : _players)+				{+					if (player != null)+					{+						if (player.isOnline())+							player.teleToLocation(_npcX, _npcY, _npcZ, 0);+						else+						{+							try (Connection con = L2DatabaseFactory.getInstance().getConnection())+							{+								PreparedStatement statement = con.prepareStatement("UPDATE characters SET x=?, y=?, z=? WHERE char_name=?");+								statement.setInt(1, _npcX);+								statement.setInt(2, _npcY);+								statement.setInt(3, _npcZ);+								statement.setString(4, player.getName());+								statement.execute();+								statement.close();+							}+							catch (SQLException se)+							{+								_log.warning(CTF.class.getSimpleName() + ":  CTF Engine exception: " + se.getMessage());+							}+						}+					}+				}+				cleanCTF();+			}+		}, 20000);+	}++	public static int teamFlagCount(String teamName)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return -1;++		return _teamPointsCount.get(index);+	}++	public static void setTeamFlagCount(String teamName, int teamFlagCount)+	{+		int index = _teams.indexOf(teamName);++		if (index == -1)+			return;++		_teamPointsCount.set(index, teamFlagCount);+	}++	/**+	 * Used to calculate the event CTF area, so that players don't run off with the flag.+	 * Essential, since a player may take the flag just so other teams can't score points.+	 * This function is Only called upon ONE time on BEGINING OF EACH EVENT right after we spawn the flags.+	 */+	private static void calculateOutSideOfCTF()+	{+		if ((_teams == null) || (_flagSpawns == null) || (_teamsX == null) || (_teamsY == null) || (_teamsZ == null))+			return;++		int division = _teams.size() * 2, pos = 0;+		int[] locX = new int[division], locY = new int[division], locZ = new int[division];+		// Get all coordinates in order to create a polygon:+		for (L2Spawn flag : _flagSpawns)+		{+			flag.setLoc(locX[pos], locY[pos], locZ[pos], pos);+			+			pos++;+			if (pos > division / 2)+				break;+		}++		for (int x = 0; x < _teams.size(); x++)+		{+			locX[pos] = _teamsX.get(x);+			locY[pos] = _teamsY.get(x);+			locZ[pos] = _teamsZ.get(x);+			pos++;+			if (pos > division)+				break;+		}++		// find the polygon center, note that it's not the mathematical center of the polygon,+		// rather than a point which centers all coordinates:+		int centerX = 0, centerY = 0, centerZ = 0;+		for (int x = 0; x < pos; x++)+		{+			centerX += (locX[x] / division);+			centerY += (locY[x] / division);+			centerZ += (locZ[x] / division);+		}++		// now let's find the farthest distance from the "center" to the egg shaped sphere+		// surrounding the polygon, size x1.5 (for maximum logical area to wander...):+		int maxX = 0, maxY = 0, maxZ = 0;+		for (int x = 0; x < pos; x++)+		{+			if (maxX < 2 * Math.abs(centerX - locX[x]))+				maxX = (2 * Math.abs(centerX - locX[x]));+			if (maxY < 2 * Math.abs(centerY - locY[x]))+				maxY = (2 * Math.abs(centerY - locY[x]));+			if (maxZ < 2 * Math.abs(centerZ - locZ[x]))+				maxZ = (2 * Math.abs(centerZ - locZ[x]));+		}++		// centerX,centerY,centerZ are the coordinates of the "event center".+		// so let's save those coordinates to check on the players:+		eventCenterX = centerX;+		eventCenterY = centerY;+		eventCenterZ = centerZ;+		eventOffset = maxX;+		if (eventOffset < maxY)+			eventOffset = maxY;+		if (eventOffset < maxZ)+			eventOffset = maxZ;+	}++	public static boolean isOutsideCTFArea(Player _player)+	{+		if ((_player == null) || (_player.isOnline()))+			return true;+		if (!(_player.getX() > eventCenterX - eventOffset && _player.getX() < eventCenterX + eventOffset && _player.getY() > eventCenterY - eventOffset && _player.getY() < eventCenterY + eventOffset && _player.getZ() > eventCenterZ - eventOffset && _player.getZ() < eventCenterZ + eventOffset))+			return true;+		return false;+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerTvT.java===================================================================--- java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerTvT.java	(revision 0)+++ java/net/sf/l2j/gameserver/model/entity/engine/EventHandlerTvT.java	(working copy)@@ -0,0 +1,91 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ * + * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ * + * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.model.entity.engine;++import java.util.ArrayList;+import java.util.Calendar;+import java.util.List;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.commons.concurrent.ThreadPool;++/**+ * @author Boorinio+ */+public class EventHandlerTvT+{+	private static final Logger _log = Logger.getLogger(EventHandlerTvT.class.getName());+	public List<Long> datesTvT = new ArrayList<>();+	+	public void startHandler()+	{+		loadConfisTvT(false);+		getNextTimeStampTvT();+		_log.info(EventHandlerTvT.class.getSimpleName() + ": TvT handler initiated.");+	}+	+	public void loadConfisTvT(boolean NextDay)+	{+		datesTvT.clear();+		for (String times : Config.TVT_EVENT_TIMES.split(","))+		{+			String[] timesSplited = times.split(":");+			int hour = Integer.parseInt(timesSplited[0]);+			int minute = Integer.parseInt(timesSplited[1]);+			Calendar time = Calendar.getInstance();+			if (!NextDay)+			{+				time.set(Calendar.HOUR_OF_DAY, hour);+				time.set(Calendar.MINUTE, minute);+			}+			else+			{+				time.set(Calendar.DAY_OF_MONTH, Calendar.getInstance().get(Calendar.DAY_OF_MONTH) + 1);+				time.set(Calendar.HOUR_OF_DAY, hour);+				time.set(Calendar.MINUTE, minute);+			}+			datesTvT.add(time.getTimeInMillis());+		}+	}+	+	public void getNextTimeStampTvT()+	{+		boolean found = false;+		for (Long stamp : datesTvT)+		{+			if (stamp > System.currentTimeMillis())+			{+				ThreadPool.schedule(new Runnable()+				{+					@Override+					public void run()+					{+						TvT.loadData();+						TvT.autoEvent();+						getNextTimeStampTvT();+					}+				}, stamp - System.currentTimeMillis());+				found = true;+				break;+			}+		}+		if (!found)+		{+			loadConfisTvT(true);+			getNextTimeStampTvT();+		}+	}+}Index: java/net/sf/l2j/gameserver/model/L2Radar.java===================================================================--- java/net/sf/l2j/gameserver/model/L2Radar.java	(revision 1)+++ java/net/sf/l2j/gameserver/model/L2Radar.java	(working copy)@@ -3,6 +3,7 @@ import java.util.ArrayList; import java.util.List; +import net.sf.l2j.commons.concurrent.ThreadPool; import net.sf.l2j.gameserver.model.actor.instance.Player; import net.sf.l2j.gameserver.network.serverpackets.RadarControl; @@ -54,6 +55,37 @@ 			_player.sendPacket(new RadarControl(0, 1, tempMarker._x, tempMarker._y, tempMarker._z)); 	} 	+	public class RadarOnPlayer implements Runnable+	{+		private final Player _myTarget, _me;+		+		public RadarOnPlayer(Player target, Player me)+		{+			_me = me;+			_myTarget = target;+		}+		+		@Override+		public void run()+		{+			try+			{+				if (_me == null || _me.isOnline())+					return;+				+				_me.sendPacket(new RadarControl(1, 1, _me.getX(), _me.getY(), _me.getZ()));+				if (_myTarget == null || _myTarget.isOnline() || !_myTarget._haveFlagCTF)+					return;+				+				_me.sendPacket(new RadarControl(0, 1, _myTarget.getX(), _myTarget.getY(), _myTarget.getZ()));+				ThreadPool.schedule(new RadarOnPlayer(_myTarget, _me), 15000);+			}+			catch (Throwable t)+			{+			}+		}+	}	+	 	public static class RadarMarker 	{ 		// Simple class to model radar points.Index: java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminEventEngine.java===================================================================--- java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminEventEngine.java	(revision 0)+++ java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminEventEngine.java	(working copy)@@ -0,0 +1,769 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.handler.admincommandhandlers;++import java.io.BufferedInputStream;+import java.io.BufferedReader;+import java.io.DataInputStream;+import java.io.File;+import java.io.FileInputStream;+import java.io.FileOutputStream;+import java.io.InputStreamReader;+import java.io.PrintStream;+import java.util.Iterator;+import java.util.LinkedList;+import java.util.StringTokenizer;+import java.util.logging.Logger;++import net.sf.l2j.Config;+import net.sf.l2j.gameserver.datatables.SpawnTable;+import net.sf.l2j.gameserver.handler.IAdminCommandHandler;+import net.sf.l2j.gameserver.model.L2Object.PolyType;+import net.sf.l2j.gameserver.model.L2Spawn;+import net.sf.l2j.gameserver.model.World;+import net.sf.l2j.gameserver.model.actor.Npc;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.entity.L2Event;+import net.sf.l2j.gameserver.network.serverpackets.CharInfo;+import net.sf.l2j.gameserver.network.serverpackets.ItemList;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.network.serverpackets.Revive;+import net.sf.l2j.gameserver.network.serverpackets.SocialAction;+import net.sf.l2j.gameserver.network.serverpackets.UserInfo;++/**+ * This class handles following admin commands:+ * - admin = shows menu+ */+public class AdminEventEngine implements IAdminCommandHandler+{+	protected static final Logger _log = Logger.getLogger(AdminEventEngine.class.getName());++	private static final String[] ADMIN_COMMANDS =+	{/** @formatter:off */+		"admin_event",+		"admin_event_new",+		"admin_event_choose",+		"admin_event_store",+		"admin_event_set",+		"admin_event_change_teams_number",+		"admin_event_announce",+		"admin_event_panel",+		"admin_event_control_begin",+		"admin_event_control_teleport",+		"admin_add",+		"admin_event_see",+		"admin_event_del",+		"admin_delete_buffer",+		"admin_event_control_sit",+		"admin_event_name",+		"admin_event_control_kill",+		"admin_event_control_res",+		"admin_event_control_poly",+		"admin_event_control_unpoly",+		"admin_event_control_prize",+		"admin_event_control_chatban",+		"admin_event_control_finish"+	};/** @formatter:off */+	private static String tempBuffer = "";+	private static String tempName = "";+	private static String tempName2 = "";+	private static boolean npcsDeleted = false;++	@Override+	public boolean useAdminCommand(String command, Player activeChar)+	{+		if (command.equals("admin_event"))+			showMainPage(activeChar);++		else if (command.equals("admin_event_new"))+		{+			showNewEventPage(activeChar);+		}+		else if (command.startsWith("admin_add"))+		{+			tempBuffer += command.substring(10);+			showNewEventPage(activeChar);++		}+		else if (command.startsWith("admin_event_see"))+		{+			String eventName = command.substring(16);+			try (DataInputStream in = new DataInputStream(new BufferedInputStream(new FileInputStream("data/events/" + eventName)));+				BufferedReader inbr = new BufferedReader(new InputStreamReader(in)))+			{+				NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+				StringBuilder replyMSG = new StringBuilder("<html><body>");+				replyMSG.append("<center><font color=\"LEVEL\">" + eventName + "</font><font color=\"FF0000\"> bY " + inbr.readLine() + "</font></center><br>");++				replyMSG.append("<br>" + inbr.readLine());+				replyMSG.append("</body></html>");+				adminReply.setHtml(replyMSG.toString());+				activeChar.sendPacket(adminReply);+			}+			catch (Exception e)+			{+				_log.warning(AdminEventEngine.class.getName() + ": Error " + eventName);+				if (Config.DEVELOPER)+					e.printStackTrace();+			}++		}+		else if (command.startsWith("admin_event_del"))+		{+			String eventName = command.substring(16);+			File file = new File("data/events/" + eventName);+			file.delete();+			showMainPage(activeChar);+		}++		else if (command.startsWith("admin_event_name"))+		{+			tempName += command.substring(17);+			showNewEventPage(activeChar);+		}++		else if (command.equalsIgnoreCase("admin_delete_buffer"))+		{+			try+			{+				tempBuffer += tempBuffer.substring(0, tempBuffer.length() - 10);+				showNewEventPage(activeChar);+			}+			catch (Exception e)+			{+				tempBuffer = "";+			}+		}++		else if (command.startsWith("admin_event_store"))+		{++			try (FileOutputStream file = new FileOutputStream("data/events/" + tempName);+				PrintStream p = new PrintStream(file))+			{+				;+				p.println(activeChar.getName());+				p.println(tempBuffer);+			}+			catch (Exception e)+			{+				_log.warning(AdminEventEngine.class.getName() + ": could not store data/events/" + tempName);+				if (Config.DEVELOPER)+					e.printStackTrace();+			}+			tempBuffer = "";+			tempName = "";+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_event_set"))+		{+			L2Event.eventName = command.substring(16);+			showEventParameters(activeChar, 2);+		}+		else if (command.startsWith("admin_event_change_teams_number"))+		{+			showEventParameters(activeChar, Integer.parseInt(command.substring(32)));+		}+		else if (command.startsWith("admin_event_panel"))+		{+			showEventControl(activeChar);+		}+		else if (command.startsWith("admin_event_control_begin"))+		{+			try+			{+				L2Event.active = true;+				L2Event.players.clear();+				L2Event.connectionLossData.clear();++				for (int j = 0; j < L2Event.teamsNumber; j++)+				{+					LinkedList<String> link = new LinkedList<>();+					L2Event.players.put(j + 1, link);++				}+				int i = 0;++				while (L2Event.participatingPlayers.size() > 0)+				{+					String target = getMaxLeveledPlayer();++					if (!target.equals(""))+					{+						L2Event.players.get(i + 1).add(target);+						i = (i + 1) % L2Event.teamsNumber;+					}+				}+				destroyEventNpcs();+				npcsDeleted = true;+			}+			catch (Exception e)+			{+				if (Config.DEVELOPER)+				{+					e.printStackTrace();+				}+			}+			showEventControl(activeChar);+		}+		else if (command.startsWith("admin_event_control_teleport"))+		{+			StringTokenizer st = new StringTokenizer(command.substring(29), "-");++			while (st.hasMoreElements())+			{+				teleportTeam(activeChar, Integer.parseInt(st.nextToken()));+			}+			showEventControl(activeChar);+		}++		else if (command.startsWith("admin_event_control_sit"))+		{+			StringTokenizer st = new StringTokenizer(command.substring(24), "-");++			while (st.hasMoreElements())+			{+				sitTeam(Integer.parseInt(st.nextToken()));+			}+			showEventControl(activeChar);+		}+		else if (command.startsWith("admin_event_control_kill"))+		{+			StringTokenizer st = new StringTokenizer(command.substring(25), "-");++			while (st.hasMoreElements())+			{+				killTeam(activeChar, Integer.parseInt(st.nextToken()));+			}+			showEventControl(activeChar);+		}+		else if (command.startsWith("admin_event_control_res"))+		{+			StringTokenizer st = new StringTokenizer(command.substring(24), "-");++			while (st.hasMoreElements())+			{+				resTeam(Integer.parseInt(st.nextToken()));+			}+			showEventControl(activeChar);+		}+		else if (command.startsWith("admin_event_control_poly"))+		{+			StringTokenizer st0 = new StringTokenizer(command.substring(25));+			StringTokenizer st = new StringTokenizer(st0.nextToken(), "-");+			String id = st0.nextToken();+			while (st.hasMoreElements())+			{+				polyTeam(Integer.parseInt(st.nextToken()), id);+			}+			showEventControl(activeChar);+		}+		else if (command.startsWith("admin_event_control_unpoly"))+		{+			StringTokenizer st = new StringTokenizer(command.substring(27), "-");++			while (st.hasMoreElements())+			{+				unpolyTeam(Integer.parseInt(st.nextToken()));+			}+			showEventControl(activeChar);+		}+		else if (command.startsWith("admin_event_control_prize"))+		{+			StringTokenizer st0 = new StringTokenizer(command.substring(26));+			StringTokenizer st = new StringTokenizer(st0.nextToken(), "-");+			String n = st0.nextToken();+			StringTokenizer st1 = new StringTokenizer(n, "*");+			n = st1.nextToken();+			String type = "";+			if (st1.hasMoreElements())+				type = st1.nextToken();++			String id = st0.nextToken();+			while (st.hasMoreElements())+			{+				regardTeam(activeChar, Integer.parseInt(st.nextToken()), Integer.parseInt(n), Integer.parseInt(id), type);+			}+			showEventControl(activeChar);+		}+		else if (command.startsWith("admin_event_control_finish"))+		{+			for (int i = 0; i < L2Event.teamsNumber; i++)+			{+				telePlayersBack(i + 1);+			}++			L2Event.eventName = "";+			L2Event.teamsNumber = 0;+			L2Event.names.clear();+			L2Event.participatingPlayers.clear();+			L2Event.players.clear();+			L2Event.id = 12760;+			L2Event.npcs.clear();+			L2Event.active = false;+			npcsDeleted = false;+		}++		else if (command.startsWith("admin_event_announce"))+		{+			StringTokenizer st = new StringTokenizer(command.substring(21));+			L2Event.id = Integer.parseInt(st.nextToken());+			L2Event.teamsNumber = Integer.parseInt(st.nextToken());+			String temp = " ";+			String temp2 = "";+			while (st.hasMoreElements())+			{+				temp += st.nextToken() + " ";+			}++			st = new StringTokenizer(temp, "-");++			Integer i = 1;++			while (st.hasMoreElements())+			{+				temp2 = st.nextToken();+				if (!temp2.equals(" "))+				{+					L2Event.names.put(i, temp2.substring(1, temp2.length() - 1));+					i++;+				}+			}++			L2Event.participatingPlayers.clear();++			muestraNpcConInfoAPlayers(activeChar, L2Event.id);++			NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++			StringBuilder replyMSG = new StringBuilder("<html><body>");++			replyMSG.append("<center><font color=\"LEVEL\">[ L2J EVENT ENGINE</font></center><br>");+			replyMSG.append("<center>The event <font color=\"LEVEL\">" + L2Event.eventName + "</font> has been announced, now you can type //event_panel to see the event panel control</center><br>");+			replyMSG.append("</body></html>");+			adminReply.setHtml(replyMSG.toString());+			activeChar.sendPacket(adminReply);+		}+		return true;+	}++	@Override+	public String[] getAdminCommandList()+	{+		return ADMIN_COMMANDS;+	}++	String showStoredEvents()+	{+		File dir = new File("data/events");+		String[] files = dir.list();+		String result = "";+		if (files == null)+		{+			result = "No 'data/events' directory!";+			return result;+		}+		for (int i = 0; i < files.length; i++)+		{++			File file = new File("data/events/" + files[i]);+			result += "<font color=\"LEVEL\">" + file.getName() + " </font><br><button value=\"select\" action=\"bypass -h admin_event_set " + file.getName() + "\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"><button value=\"ver\" action=\"bypass -h admin_event_see " + file.getName() + "\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"><button value=\"delete\" action=\"bypass -h admin_event_del " + file.getName() + "\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"><br><br>";+		}+		return result;+	}++	public void showMainPage(Player activeChar)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[ L2J EVENT ENGINE ]</font></center><br>");+		replyMSG.append("<br><center><button value=\"Create NEW event \" action=\"bypass -h admin_event_new\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\">");+		replyMSG.append("<center><br>Stored Events<br></center>");+		replyMSG.append(showStoredEvents());+		replyMSG.append("</body></html>");++		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}++	public void showNewEventPage(Player activeChar)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[ L2J EVENT ENGINE ]</font></center><br>");+		replyMSG.append("<br><center>Event's Title <br><font color=\"LEVEL\">");+		if (tempName.equals(""))+			replyMSG.append("Use //event_name text to insert a new title");+		else+			replyMSG.append(tempName);+		replyMSG.append("</font></center><br><br>Event's description<br>");+		if (tempBuffer.equals(""))+			replyMSG.append("Use //add text o //delete_buffer to modify this text field");+		else+			replyMSG.append(tempBuffer);++		if (!(tempName.equals("") && tempBuffer.equals("")))+			replyMSG.append("<br><button value=\"Crear\" action=\"bypass -h admin_event_store\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\">");++		replyMSG.append("</body></html>");++		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}++	public void showEventParameters(Player activeChar, int teamnumbers)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[ L2J EVENT ENGINE ]</font></center><br>");+		replyMSG.append("<center><font color=\"LEVEL\">" + L2Event.eventName + "</font></center><br>");+		replyMSG.append("<br><center><button value=\"Change number of teams to\" action=\"bypass -h admin_event_change_teams_number $event_teams_number\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"> <edit var=\"event_teams_number\" width=100 height=20><br><br>");+		replyMSG.append("<font color=\"LEVEL\">Team's Names</font><br>");+		for (int i = 0; i < teamnumbers; i++)+		{+			replyMSG.append((i + 1) + ".- <edit var=\"event_teams_name" + (i + 1) + "\" width=100 height=20><br>");+		}+		replyMSG.append("<br><br>Announcer NPC id<edit var=\"event_npcid\" width=100 height=20><br><br><button value=\"Announce Event!!\" action=\"bypass -h admin_event_announce $event_npcid " + teamnumbers + " ");+		for (int i = 0; i < teamnumbers; i++)+		{+			replyMSG.append("$event_teams_name" + (i + 1) + " - ");+		}+		replyMSG.append("\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\">");+		replyMSG.append("</body></html>");++		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}++	void muestraNpcConInfoAPlayers(Player activeChar, int id)+	{+		L2Event.npcs.clear();+		LinkedList<Player> temp = new LinkedList<>();+		temp.clear();+		for (Player player : World.getInstance().getPlayers())+		{++			if (!temp.contains(player))+			{+				L2Event.spawn(player, id);+				temp.add(player);+			}+			for (Player playertemp : player.getKnownType(Player.class))+			{+				if ((Math.abs(playertemp.getX() - player.getX()) < 500) && (Math.abs(playertemp.getY() - player.getY()) < 500) && (Math.abs(playertemp.getZ() - player.getZ()) < 500))+					temp.add(playertemp);+			}+		}+		L2Event.announceAllPlayers(activeChar.getName() + " wants to make an event !!! (you'll find a npc with the details around)");+	}++	void showEventControl(Player activeChar)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);++		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[ L2J EVENT ENGINE ]</font></center><br><font color=\"LEVEL\">" + L2Event.eventName + "</font><br><br><table width=200>");+		replyMSG.append("<tr><td>Apply this command to teams number </td><td><edit var=\"team_number\" width=100 height=15></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		if (!npcsDeleted)+			replyMSG.append("<tr><td><button value=\"Start\" action=\"bypass -h admin_event_control_begin\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></td><td><font color=\"LEVEL\">Destroys all event npcs so no more people can't participate now on</font></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td><button value=\"Teleport\" action=\"bypass -h admin_event_control_teleport $team_number\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></td><td><font color=\"LEVEL\">Teleports the specified team to your position</font></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td><button value=\"Sit\" action=\"bypass -h admin_event_control_sit $team_number\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></td><td><font color=\"LEVEL\">Sits/Stands up the team</font></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td><button value=\"Kill\" action=\"bypass -h admin_event_control_kill $team_number\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></td><td><font color=\"LEVEL\">Finish with the life of all the players in the selected team</font></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td><button value=\"Resurrect\" action=\"bypass -h admin_event_control_res $team_number\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></td><td><font color=\"LEVEL\">Resurrect Team's members</font></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td><button value=\"Polymorph\" action=\"bypass -h admin_event_control_poly $team_number $poly_id\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></td><td><edit var=\"poly_id\" width=100 height=15><font color=\"LEVEL\">Polymorphs the team into the NPC with the id specified</font></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td><button value=\"UnPolymorph\" action=\"bypass -h admin_event_control_unpoly $team_number\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></td><td><font color=\"LEVEL\">Unpolymorph the team</font></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td><button value=\"Give Item\" action=\"bypass -h admin_event_control_prize $team_number $n $id\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"> number <edit var=\"n\" width=100 height=15> item id <edit var=\"id\" width=100 height=15></td><td><font color=\"LEVEL\">Give the specified item id to every single member of the team, you can put 5*level, 5*kills or 5 in the number field for example</font></td></tr>");+		replyMSG.append("<tr><td>&nbsp;</td></tr>");+		replyMSG.append("<tr><td><button value=\"End\" action=\"bypass -h admin_event_control_finish\" width=90 height=15 back=\"sek.cbui94\" fore=\"sek.cbui92\"></td><td><font color=\"LEVEL\">Will finish the event teleporting back all the players</font></td></tr>");+		replyMSG.append("</table></body></html>");++		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}++	String getMaxLeveledPlayer()+	{+		Iterator<?> it = L2Event.participatingPlayers.iterator();+		Player pc = null;+		int max = 0;+		String name = "";+		while (it.hasNext())+		{+			try+			{+				tempName2 = it.next().toString();+				pc = World.getInstance().getPlayer(tempName2);+				if (max < pc.getLevel())+				{+					max = pc.getLevel();+					name = pc.getName();+				}+			}+			catch (Exception e)+			{+				try+				{+					L2Event.participatingPlayers.remove(tempName2);+				}+				catch (Exception e2)+				{++				}+			}+		}+		L2Event.participatingPlayers.remove(name);+		return name;+	}++	void destroyEventNpcs()+	{+		Npc npc;+		while (L2Event.npcs.size() > 0)+		{+			try+			{+				npc = (Npc) World.getInstance().getObject(Integer.parseInt(L2Event.npcs.getFirst()));+				L2Spawn spawn = npc.getSpawn();++				if (spawn != null)+				{+					spawn.setRespawnState(false);+					SpawnTable.getInstance().deleteSpawn(spawn, true);+				}+				npc.deleteMe();+				L2Event.npcs.removeFirst();+			}+			catch (Exception e)+			{+				L2Event.npcs.removeFirst();+			}+		}+	}++	void teleportTeam(Player activeChar, int team)+	{+		LinkedList<?> linked = L2Event.players.get(team);+		Iterator<?> it = linked.iterator();+		while (it.hasNext())+		{+			try+			{+				Player pc = World.getInstance().getPlayer(it.next().toString());+				pc.setTitle(L2Event.names.get(team));+				pc.teleToLocation(activeChar.getX(), activeChar.getY(), activeChar.getZ(), 0);+			}+			catch (Exception e)+			{++			}+		}+	}++	void sitTeam(int team)+	{+		LinkedList<?> linked = L2Event.players.get(team);+		Iterator<?> it = linked.iterator();+		while (it.hasNext())+		{+			try+			{+				Player pc = World.getInstance().getPlayer(it.next().toString());+				pc.eventSitForced = !pc.eventSitForced;+				if (pc.eventSitForced)+					pc.sitDown();+				else+					pc.standUp();+			}+			catch (Exception e)+			{+			}+		}+	}++	void killTeam(Player activeChar, int team)+	{+		LinkedList<?> linked = L2Event.players.get(team);+		Iterator<?> it = linked.iterator();+		while (it.hasNext())+		{+			try+			{+				Player target = World.getInstance().getPlayer(it.next().toString());+				target.reduceCurrentHp(target.getMaxHp() + target.getMaxCp() + 1, activeChar, null);+			}+			catch (Exception e)+			{+			}+		}+	}++	void resTeam(int team)+	{+		LinkedList<?> linked = L2Event.players.get(team);+		Iterator<?> it = linked.iterator();+		while (it.hasNext())+		{+			try+			{+				Player character = World.getInstance().getPlayer(it.next().toString());+				character.setCurrentHpMp(character.getMaxHp(), character.getMaxMp());+				character.setCurrentCp(character.getMaxCp());+				Revive revive = new Revive(character);+				SocialAction sa = new SocialAction(character, 15);+				character.broadcastPacket(sa);+				character.sendPacket(sa);+				character.sendPacket(revive);+				character.broadcastPacket(revive);+			}+			catch (Exception e)+			{+			}+		}+	}++	void polyTeam(int team, String id)+	{+		LinkedList<?> linked = L2Event.players.get(team);+		Iterator<?> it = linked.iterator();+		while (it.hasNext())+		{+			try+			{+				Player target = World.getInstance().getPlayer(it.next().toString());+				target.polymorph(null, 1);+				target.teleToLocation(target.getX(), target.getY(), target.getZ(), 0);+				+				CharInfo info1 = new CharInfo(target);+				target.broadcastPacket(info1);+				UserInfo info2 = new UserInfo(target);+				target.sendPacket(info2);+			}+			catch (Exception e)+			{+			}+		}+	}++	void unpolyTeam(int team)+	{+		LinkedList<?> linked = L2Event.players.get(team);+		Iterator<?> it = linked.iterator();+		while (it.hasNext())+		{+			try+			{+				Player target = World.getInstance().getPlayer(it.next().toString());++				if (target.getPolyType() == PolyType.NPC)+				{+					target.polymorph(null, 1);+					target.decayMe();+					target.spawnMe(target.getX(), target.getY(), target.getZ());+				}+				+				CharInfo info1 = new CharInfo(target);+				target.broadcastPacket(info1);+				UserInfo info2 = new UserInfo(target);+				target.sendPacket(info2);+			}+			catch (Exception e)+			{+			}+		}+	}++	private static void createItem(Player activeChar, Player player, int id, int num)+	{+		player.getInventory().addItem("Event", id, num, player, activeChar);+		ItemList il = new ItemList(player, true);+		player.sendPacket(il);++		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("CONGRATULATIONS, you should have a present in your inventory");+		replyMSG.append("</body></html>");++		adminReply.setHtml(replyMSG.toString());+		player.sendPacket(adminReply);+	}++	void regardTeam(Player activeChar, int team, int n, int id, String type)+	{+		LinkedList<?> linked = L2Event.players.get(team);+		int temp = n;+		Iterator<?> it = linked.iterator();+		while (it.hasNext())+		{+			try+			{+				Player target = World.getInstance().getPlayer(it.next().toString());+				if (type.equalsIgnoreCase("level"))+					temp = n * target.getLevel();+				else if (type.equalsIgnoreCase("kills"))+					temp = n * target.kills.size();+				else+					temp = n;+				createItem(activeChar, target, id, temp);+			}+			catch (Exception e)+			{+			}+		}+	}++	void telePlayersBack(int team)+	{+		resTeam(team);+		unpolyTeam(team);+		LinkedList<?> linked = L2Event.players.get(team);+		Iterator<?> it = linked.iterator();+		while (it.hasNext())+		{+			try+			{+				Player target = World.getInstance().getPlayer(it.next().toString());+				target.setTitle(target.eventTitle);+				target.setKarma(target.eventkarma);+				target.setPvpKills(target.eventpvpkills);+				target.setPkKills(target.eventpkkills);+				target.teleToLocation(target.eventX, target.eventY, target.eventZ, 0);+				target.kills.clear();+				target.eventSitForced = false;+				target.atEvent = false;+			}+			catch (Exception e)+			{+			}+		}+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/network/clientpackets/RequestJoinParty.java===================================================================--- java/net/sf/l2j/gameserver/network/clientpackets/RequestJoinParty.java	(revision 3)+++ java/net/sf/l2j/gameserver/network/clientpackets/RequestJoinParty.java	(working copy)@@ -1,8 +1,12 @@ package net.sf.l2j.gameserver.network.clientpackets; +import net.sf.l2j.Config; import net.sf.l2j.gameserver.model.BlockList; import net.sf.l2j.gameserver.model.World; import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.model.entity.engine.DM;+import net.sf.l2j.gameserver.model.entity.engine.TvT; import net.sf.l2j.gameserver.model.group.Party; import net.sf.l2j.gameserver.model.group.Party.LootRule; import net.sf.l2j.gameserver.network.SystemMessageId;@@ -27,7 +31,7 @@ 		final Player requestor = getClient().getActiveChar(); 		if (requestor == null) 			return;-+		 		final Player target = World.getInstance().getPlayer(_name); 		if (target == null) 		{@@ -46,69 +50,88 @@ 			requestor.sendPacket(SystemMessageId.YOU_HAVE_INVITED_THE_WRONG_TARGET); 			return; 		}-		-		if (target.isInParty())+	+		if (((TvT._started && !Config.TVT_ALLOW_INTERFERENCE) || (CTF._started && !Config.CTF_ALLOW_INTERFERENCE) || (DM._started && !Config.DM_ALLOW_INTERFERENCE))) 		{-			requestor.sendPacket(SystemMessage.getSystemMessage(SystemMessageId.S1_IS_ALREADY_IN_PARTY).addCharName(target));-			return;-		}-		-		if (target.getClient().isDetached())-		{-			requestor.sendMessage("The player you tried to invite is in offline mode.");-			return;-		}-		-		if (target.isInJail() || requestor.isInJail())-		{-			requestor.sendMessage("The player you tried to invite is currently jailed.");-			return;-		}-		-		if (target.isInOlympiadMode() || requestor.isInOlympiadMode())-			return;-		-		if (requestor.isProcessingRequest())-		{-			requestor.sendPacket(SystemMessageId.WAITING_FOR_ANOTHER_REPLY);-			return;-		}-		-		if (target.isProcessingRequest())-		{-			requestor.sendPacket(SystemMessage.getSystemMessage(SystemMessageId.S1_IS_BUSY_TRY_LATER).addCharName(target));-			return;-		}-		-		final Party party = requestor.getParty();-		if (party != null)-		{-			if (!party.isLeader(requestor))+			if ((target._inEventTvT && !requestor._inEventTvT) || (!target._inEventTvT && requestor._inEventTvT)) 			{-				requestor.sendPacket(SystemMessageId.ONLY_LEADER_CAN_INVITE);+				requestor.sendPacket(SystemMessageId.INCORRECT_TARGET); 				return; 			}+			if ((target._inEventCTF && !requestor._inEventCTF) || (!target._inEventCTF && requestor._inEventCTF))+			{+				requestor.sendPacket(SystemMessageId.INCORRECT_TARGET);+				return;+			}+			if ((target._inEventDM && !requestor._inEventDM) || (!target._inEventDM && requestor._inEventDM))+			{+				requestor.sendPacket(SystemMessageId.INCORRECT_TARGET);+				return;+			} 			-			if (party.getMembersCount() >= 9)+			if (target.isInParty()) 			{-				requestor.sendPacket(SystemMessageId.PARTY_FULL);+				requestor.sendPacket(SystemMessage.getSystemMessage(SystemMessageId.S1_IS_ALREADY_IN_PARTY).addCharName(target)); 				return; 			} 			-			if (party.getPendingInvitation() && !party.isInvitationRequestExpired())+			if (target.getClient().isDetached()) 			{+				requestor.sendMessage("The player you tried to invite is in offline mode.");+				return;+			}+			+			if (target.isInJail() || requestor.isInJail())+			{+				requestor.sendMessage("The player you tried to invite is currently jailed.");+				return;+			}+			+			if (target.isInOlympiadMode() || requestor.isInOlympiadMode())+				return;+			+			if (requestor.isProcessingRequest())+			{ 				requestor.sendPacket(SystemMessageId.WAITING_FOR_ANOTHER_REPLY); 				return; 			} 			-			party.setPendingInvitation(true);+			if (target.isProcessingRequest())+			{+				requestor.sendPacket(SystemMessage.getSystemMessage(SystemMessageId.S1_IS_BUSY_TRY_LATER).addCharName(target));+				return;+			}+			+			final Party party = requestor.getParty();+			if (party != null)+			{+				if (!party.isLeader(requestor))+				{+					requestor.sendPacket(SystemMessageId.ONLY_LEADER_CAN_INVITE);+					return;+				}+				+				if (party.getMembersCount() >= 9)+				{+					requestor.sendPacket(SystemMessageId.PARTY_FULL);+					return;+				}+				+				if (party.getPendingInvitation() && !party.isInvitationRequestExpired())+				{+					requestor.sendPacket(SystemMessageId.WAITING_FOR_ANOTHER_REPLY);+					return;+				}+				+				party.setPendingInvitation(true);+			}+			else+				requestor.setLootRule(LootRule.VALUES[_itemDistribution]);+			+			requestor.onTransactionRequest(target);+			requestor.sendPacket(SystemMessage.getSystemMessage(SystemMessageId.YOU_INVITED_S1_TO_PARTY).addCharName(target));+			+			target.sendPacket(new AskJoinParty(requestor.getName(), (party != null) ? party.getLootRule().ordinal() : _itemDistribution)); 		}-		else-			requestor.setLootRule(LootRule.VALUES[_itemDistribution]);-		-		requestor.onTransactionRequest(target);-		requestor.sendPacket(SystemMessage.getSystemMessage(SystemMessageId.YOU_INVITED_S1_TO_PARTY).addCharName(target));-		-		target.sendPacket(new AskJoinParty(requestor.getName(), (party != null) ? party.getLootRule().ordinal() : _itemDistribution)); 	} }\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminDMEngine.java===================================================================--- java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminDMEngine.java	(revision 0)+++ java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminDMEngine.java	(working copy)@@ -0,0 +1,238 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.handler.admincommandhandlers;++import net.sf.l2j.gameserver.handler.IAdminCommandHandler;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.entity.engine.DM;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.util.Util;++/**+ * @author SqueezeD+ */+public class AdminDMEngine implements IAdminCommandHandler+{+	private static final String[] ADMIN_COMMANDS =+	{/** @formatter:off */+		"admin_dmevent",+		"admin_dmevent_name",+		"admin_dmevent_desc",+		"admin_dmevent_join_loc",+		"admin_dmevent_minlvl",+		"admin_dmevent_maxlvl",+		"admin_dmevent_npc",+		"admin_dmevent_npc_pos",+		"admin_dmevent_reward",+		"admin_dmevent_reward_amount",+		"admin_dmevent_spawnpos",+		"admin_dmevent_color",+		"admin_dmevent_join",+		"admin_dmevent_teleport",+		"admin_dmevent_start",+		"admin_dmevent_abort",+		"admin_dmevent_finish",+		"admin_dmevent_sit",+		"admin_dmevent_dump",+		"admin_dmevent_save",+		"admin_dmevent_load"+	};/** @formatter:on */++	@Override+	public boolean useAdminCommand(String command, Player activeChar)+	{+		if (command.equals("admin_dmevent"))+			showMainPage(activeChar);+		else if (command.startsWith("admin_dmevent_name "))+		{+			DM._eventName = command.substring(19);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_dmevent_desc "))+		{+			DM._eventDesc = command.substring(19);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_dmevent_minlvl "))+		{+			if (!DM.checkMinLevel(Integer.valueOf(command.substring(21))))+				return false;+			DM._minlvl = Integer.valueOf(command.substring(21));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_dmevent_maxlvl "))+		{+			if (!DM.checkMaxLevel(Integer.valueOf(command.substring(21))))+				return false;+			DM._maxlvl = Integer.valueOf(command.substring(21));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_dmevent_join_loc "))+		{+			DM._joiningLocationName = command.substring(23);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_dmevent_npc "))+		{+			DM._npcId = Integer.valueOf(command.substring(18));+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_npc_pos"))+		{+			DM.setNpcPos(activeChar);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_dmevent_reward "))+		{+			DM._rewardId = Integer.valueOf(command.substring(21));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_dmevent_reward_amount "))+		{+			DM._rewardAmount = Integer.valueOf(command.substring(28));+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_spawnpos"))+		{+			DM.setPlayersPos(activeChar);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_dmevent_color "))+		{+			DM._playerColors = Integer.decode("0x" + Util.reverseColor(command.substring(20))); // name/title color in client is BGR, not RGB+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_join"))+		{+			DM.startJoin(activeChar);+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_teleport"))+		{+			DM.teleportStart();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_start"))+		{+			DM.startEvent(activeChar);+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_abort"))+		{+			activeChar.sendMessage("Aborting event");+			DM.abortEvent();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_finish"))+		{+			DM.finishEvent(activeChar);+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_sit"))+		{+			DM.sit();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_load"))+		{+			DM.loadData();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_save"))+		{+			DM.saveData();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_dmevent_dump"))+			DM.dumpData();++		return true;+	}++	@Override+	public String[] getAdminCommandList()+	{+		return ADMIN_COMMANDS;+	}++	public void showMainPage(Player activeChar)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[dm Engine - by SqueezeD]</font></center><br><br><br>");+		replyMSG.append("<table><tr><td><edit var=\"input1\" width=\"125\"></td><td><edit var=\"input2\" width=\"125\"></td></tr></table>");+		replyMSG.append("<table border=\"0\"><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Name\" action=\"bypass -h admin_dmevent_name $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Description\" action=\"bypass -h admin_dmevent_desc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Join Location\" action=\"bypass -h admin_dmevent_join_loc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Max lvl\" action=\"bypass -h admin_dmevent_maxlvl $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Min lvl\" action=\"bypass -h admin_dmevent_minlvl $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"NPC\" action=\"bypass -h admin_dmevent_npc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"NPC Pos\" action=\"bypass -h admin_dmevent_npc_pos\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Reward\" action=\"bypass -h admin_dmevent_reward $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Reward Amount\" action=\"bypass -h admin_dmevent_reward_amount $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"DM Color\" action=\"bypass -h admin_dmevent_color $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"DM SpawnPos\" action=\"bypass -h admin_dmevent_spawnpos\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><table><br><br><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Join\" action=\"bypass -h admin_dmevent_join\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Teleport\" action=\"bypass -h admin_dmevent_teleport\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Start\" action=\"bypass -h admin_dmevent_start\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Abort\" action=\"bypass -h admin_dmevent_abort\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Finish\" action=\"bypass -h admin_dmevent_finish\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Sit Force\" action=\"bypass -h admin_dmevent_sit\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Dump\" action=\"bypass -h admin_dmevent_dump\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Save\" action=\"bypass -h admin_dmevent_save\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Load\" action=\"bypass -h admin_dmevent_load\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><br>");+		replyMSG.append("Current event...<br1>");+		replyMSG.append("    ... name:&nbsp;<font color=\"00FF00\">" + DM._eventName + "</font><br1>");+		replyMSG.append("    ... description:&nbsp;<font color=\"00FF00\">" + DM._eventDesc + "</font><br1>");+		replyMSG.append("    ... joining location name:&nbsp;<font color=\"00FF00\">" + DM._joiningLocationName + "</font><br1>");+		replyMSG.append("    ... joining NPC ID:&nbsp;<font color=\"00FF00\">" + DM._npcId + " on pos " + DM._npcX + "," + DM._npcY + "," + DM._npcZ + "</font><br1>");+		replyMSG.append("    ... reward ID:&nbsp;<font color=\"00FF00\">" + DM._rewardId + "</font><br1>");+		replyMSG.append("    ... reward Amount:&nbsp;<font color=\"00FF00\">" + DM._rewardAmount + "</font><br><br>");+		replyMSG.append("    ... Min lvl:&nbsp;<font color=\"00FF00\">" + DM._minlvl + "</font><br>");+		replyMSG.append("    ... Max lvl:&nbsp;<font color=\"00FF00\">" + DM._maxlvl + "</font><br><br>");+		replyMSG.append("    ... Death Match Color:&nbsp;<font color=\"00FF00\">" + DM._playerColors + "</font><br>");+		replyMSG.append("    ... Death Match Spawn Pos:&nbsp;<font color=\"00FF00\">" + DM._playerX + "," + DM._playerY + "," + DM._playerZ + "</font><br><br>");+		replyMSG.append("Current players:<br1>");++		if (!DM._started)+		{+			replyMSG.append("<br1>");+			replyMSG.append(DM._players.size() + " players participating.");+			replyMSG.append("<br><br>");+		}+		else if (DM._started)+		{+			replyMSG.append("<br1>");+			replyMSG.append(DM._players.size() + " players in fighting event.");+			replyMSG.append("<br><br>");+		}++		replyMSG.append("</body></html>");+		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}+}\ No newline at end of fileIndex: java/net/sf/l2j/gameserver/network/clientpackets/RequestBypassToServer.java===================================================================--- java/net/sf/l2j/gameserver/network/clientpackets/RequestBypassToServer.java	(revision 3)+++ java/net/sf/l2j/gameserver/network/clientpackets/RequestBypassToServer.java	(working copy)@@ -14,6 +14,10 @@ import net.sf.l2j.gameserver.model.actor.instance.OlympiadManagerNpc; import net.sf.l2j.gameserver.model.actor.instance.Player; import net.sf.l2j.gameserver.model.entity.Hero;+import net.sf.l2j.gameserver.model.entity.L2Event;+import net.sf.l2j.gameserver.model.entity.engine.CTF;+import net.sf.l2j.gameserver.model.entity.engine.DM;+import net.sf.l2j.gameserver.model.entity.engine.TvT; import net.sf.l2j.gameserver.model.olympiad.OlympiadManager; import net.sf.l2j.gameserver.network.SystemMessageId; import net.sf.l2j.gameserver.network.serverpackets.ActionFailed;@@ -100,6 +104,81 @@ 					if (object != null && object instanceof Npc && endOfId > 0 && ((Npc) object).canInteract(activeChar)) 						((Npc) object).onBypassFeedback(activeChar, _command.substring(endOfId + 1)); 					+					if (_command.substring(endOfId + 1).startsWith("event_participate"))+					{+						L2Event.inscribePlayer(activeChar);+					}+					else if (_command.substring(endOfId + 1).startsWith("tvt_player_join "))+					{+						String teamName = _command.substring(endOfId + 1).substring(16);+						+						if (TvT._joining)+						{+							TvT.addPlayer(activeChar, teamName);+						}+						else+						{+							activeChar.sendMessage("The event is already started. You can not join now!");+						}+					}+					else if (_command.substring(endOfId + 1).startsWith("tvt_player_leave"))+					{+						if (TvT._joining)+						{+							TvT.removePlayer(activeChar);+						}+						else+						{+							activeChar.sendMessage("The event is already started. You can not leave now!");+						}+					}+					else if (_command.substring(endOfId + 1).startsWith("dmevent_player_join"))+					{+						if (DM._joining)+						{+							DM.addPlayer(activeChar);+						}+						else+						{+							activeChar.sendMessage("The event is already started. You can not join now!");+						}+					}+					else if (_command.substring(endOfId + 1).startsWith("dmevent_player_leave"))+					{+						if (DM._joining)+						{+							DM.removePlayer(activeChar);+						}+						else+						{+							activeChar.sendMessage("The event is already started. You can not leave now!");+						}+					}+					else if (_command.substring(endOfId + 1).startsWith("ctf_player_join "))+					{+						String teamName = _command.substring(endOfId + 1).substring(16);+						+						if (CTF._joining)+						{+							CTF.addPlayer(activeChar, teamName);+						}+						else+						{+							activeChar.sendMessage("The event is already started. You can not join now!");+						}+					}+					else if (_command.substring(endOfId + 1).startsWith("ctf_player_leave"))+					{+						if (CTF._joining)+						{+							CTF.removePlayer(activeChar);+						}+						else+						{+							activeChar.sendMessage("The event is already started. You can not leave now!");+						}+					}+					 					activeChar.sendPacket(ActionFailed.STATIC_PACKET); 				} 				catch (NumberFormatException nfe)@@ -163,7 +242,7 @@ 					activeChar.sendPacket(SystemMessageId.WHILE_YOU_ARE_ON_THE_WAITING_LIST_YOU_ARE_NOT_ALLOWED_TO_WATCH_THE_GAME); 					return; 				}-+				 				final int arenaId = Integer.parseInt(_command.substring(12).trim()); 				activeChar.enterOlympiadObserverMode(arenaId); 			}Index: java/net/sf/l2j/gameserver/model/actor/instance/BroadcastingTower.java===================================================================--- java/net/sf/l2j/gameserver/model/actor/instance/BroadcastingTower.java	(revision 1)+++ java/net/sf/l2j/gameserver/model/actor/instance/BroadcastingTower.java	(working copy)@@ -29,7 +29,13 @@ 			final int x = Integer.parseInt(st.nextToken()); 			final int y = Integer.parseInt(st.nextToken()); 			final int z = Integer.parseInt(st.nextToken());-			++			if (player._inEventTvT || player._inEventDM || player._inEventCTF)+			{+				player.sendMessage("You already participated in Event!");+				return;+			}+ 			if (command.startsWith("observeSiege") && CastleManager.getInstance().getSiege(x, y, z) == null) 			{ 				player.sendPacket(SystemMessageId.ONLY_VIEW_SIEGE);@@ -36,6 +42,12 @@ 				return; 			} 			+			if (player._inEventTvT || player._inEventDM || player._inEventCTF)+			{+				player.sendMessage("You already participated in Event!");+				return;+			}+ 			if (player.reduceAdena("Broadcast", cost, this, true)) 			{ 				player.enterObserverMode(x, y, z);Index: java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminTvTEngine.java===================================================================--- java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminTvTEngine.java	(revision 0)+++ java/net/sf/l2j/gameserver/handler/admincommandhandlers/AdminTvTEngine.java	(working copy)@@ -0,0 +1,364 @@+/*+ * This program is free software: you can redistribute it and/or modify it under+ * the terms of the GNU General Public License as published by the Free Software+ * Foundation, either version 3 of the License, or (at your option) any later+ * version.+ *+ * This program is distributed in the hope that it will be useful, but WITHOUT+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS+ * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more+ * details.+ *+ * You should have received a copy of the GNU General Public License along with+ * this program. If not, see <http://www.gnu.org/licenses/>.+ */+package net.sf.l2j.gameserver.handler.admincommandhandlers;++/**+ * @author: FBIagent / fixed by SqueezeD+ */+import java.util.StringTokenizer;++import net.sf.l2j.Config;+import net.sf.l2j.commons.concurrent.ThreadPool;+import net.sf.l2j.gameserver.handler.IAdminCommandHandler;+import net.sf.l2j.gameserver.model.World;+import net.sf.l2j.gameserver.model.actor.instance.Player;+import net.sf.l2j.gameserver.model.entity.engine.TvT;+import net.sf.l2j.gameserver.network.serverpackets.NpcHtmlMessage;+import net.sf.l2j.gameserver.util.Util;++public class AdminTvTEngine implements IAdminCommandHandler+{+	private static final String[] ADMIN_COMMANDS =+	{/** @formatter:off */+		"admin_tvt",+		"admin_tvt_name",+		"admin_tvt_desc",+		"admin_tvt_join_loc",+		"admin_tvt_minlvl",+		"admin_tvt_maxlvl",+		"admin_tvt_npc",+		"admin_tvt_npc_pos",+		"admin_tvt_reward",+		"admin_tvt_reward_amount",+		"admin_tvt_team_add",+		"admin_tvt_team_remove",+		"admin_tvt_team_pos",+		"admin_tvt_team_color",+		"admin_tvt_join",+		"admin_tvt_teleport",+		"admin_tvt_start",+		"admin_tvt_abort",+		"admin_tvt_finish",+		"admin_tvt_sit",+		"admin_tvt_dump",+		"admin_tvt_save",+		"admin_tvt_load",+		"admin_tvt_jointime",+		"admin_tvt_eventtime",+		"admin_tvt_autoevent",+		"admin_tvt_minplayers",+		"admin_tvt_maxplayers",+		"admin_tvtkick",+	};/** @formatter:on */++	@Override+	public boolean useAdminCommand(String command, Player activeChar)+	{+		if (command.equals("admin_tvt"))+			showMainPage(activeChar);+		else if (command.startsWith("admin_tvt_name "))+		{+			TvT._eventName = command.substring(15);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_desc "))+		{+			TvT._eventDesc = command.substring(15);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_minlvl "))+		{+			if (!TvT.checkMinLevel(Integer.valueOf(command.substring(17))))+				return false;+			TvT._minlvl = Integer.valueOf(command.substring(17));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_maxlvl "))+		{+			if (!TvT.checkMaxLevel(Integer.valueOf(command.substring(17))))+				return false;+			TvT._maxlvl = Integer.valueOf(command.substring(17));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_minplayers "))+		{+			TvT._minPlayers = Integer.valueOf(command.substring(21));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_maxplayers "))+		{+			TvT._maxPlayers = Integer.valueOf(command.substring(21));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_join_loc "))+		{+			TvT._joiningLocationName = command.substring(19);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_npc "))+		{+			TvT._npcId = Integer.valueOf(command.substring(14));+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_npc_pos"))+		{+			TvT.setNpcPos(activeChar);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_reward "))+		{+			TvT._rewardId = Integer.valueOf(command.substring(17));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_reward_amount "))+		{+			TvT._rewardAmount = Integer.valueOf(command.substring(24));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_jointime "))+		{+			TvT._joinTime = Integer.valueOf(command.substring(19));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_eventtime "))+		{+			TvT._eventTime = Integer.valueOf(command.substring(20));+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_team_add "))+		{+			String teamName = command.substring(19);++			TvT.addTeam(teamName);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_team_remove "))+		{+			String teamName = command.substring(22);++			TvT.removeTeam(teamName);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_team_pos "))+		{+			String teamName = command.substring(19);++			TvT.setTeamPos(teamName, activeChar);+			showMainPage(activeChar);+		}+		else if (command.startsWith("admin_tvt_team_color "))+		{+			String[] params;++			params = command.split(" ");++			if (params.length != 3)+			{+				activeChar.sendMessage("Wrong usege: //tvt_team_color <colorHex> <teamName>");+				return false;+			}++			TvT.setTeamColor(command.substring(params[0].length() + params[1].length() + 2), Integer.decode("0x" + Util.reverseColor(params[1])));+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_join"))+		{+			TvT.startJoin(activeChar);+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_teleport"))+		{+			TvT.teleportStart();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_start"))+		{+			TvT.startEvent(activeChar);+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_abort"))+		{+			activeChar.sendMessage("Aborting event");+			TvT.abortEvent();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_finish"))+		{+			TvT.finishEvent();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_sit"))+		{+			TvT.sit();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_load"))+		{+			TvT.loadData();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_autoevent"))+		{+			if (TvT._joinTime > 0 && TvT._eventTime > 0)+				ThreadPool.schedule(new Runnable()+				{+					@Override+					public void run()+					{+						TvT.autoEvent();+					}+				}, 0);+			else+				activeChar.sendMessage("Wrong usege: join time or event time invallid.");+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_save"))+		{+			TvT.saveData();+			showMainPage(activeChar);+		}+		else if (command.equals("admin_tvt_dump"))+			TvT.dumpData();+		else if (command.startsWith("admin_tvtkick"))+		{+			StringTokenizer st = new StringTokenizer(command);+			if (st.countTokens() > 1)+			{+				st.nextToken();+				String plyr = st.nextToken();+				Player playerToKick = World.getInstance().getPlayer(plyr);+				if (playerToKick != null)+				{+					TvT.kickPlayerFromTvt(playerToKick);+					activeChar.sendMessage("You kicked " + playerToKick.getName() + " from the TvT.");+				}+				else+					activeChar.sendMessage("Wrong usege: //tvtkick <player>");+			}+		}+		return true;+	}++	@Override+	public String[] getAdminCommandList()+	{+		return ADMIN_COMMANDS;+	}++	public void showMainPage(Player activeChar)+	{+		NpcHtmlMessage adminReply = new NpcHtmlMessage(5);+		StringBuilder replyMSG = new StringBuilder("<html><body>");++		replyMSG.append("<center><font color=\"LEVEL\">[TvT Engine]</font></center><br><br><br>");+		replyMSG.append("<table><tr><td><edit var=\"input1\" width=\"125\"></td><td><edit var=\"input2\" width=\"125\"></td></tr></table>");+		replyMSG.append("<table border=\"0\"><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Name\" action=\"bypass -h admin_tvt_name $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Description\" action=\"bypass -h admin_tvt_desc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Join Location\" action=\"bypass -h admin_tvt_join_loc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Max lvl\" action=\"bypass -h admin_tvt_maxlvl $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Min lvl\" action=\"bypass -h admin_tvt_minlvl $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Max players\" action=\"bypass -h admin_tvt_maxplayers $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Min players\" action=\"bypass -h admin_tvt_minplayers $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"NPC\" action=\"bypass -h admin_tvt_npc $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"NPC Pos\" action=\"bypass -h admin_tvt_npc_pos\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Reward\" action=\"bypass -h admin_tvt_reward $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Reward Amount\" action=\"bypass -h admin_tvt_reward_amount $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Join Time\" action=\"bypass -h admin_tvt_jointime $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Event Time\" action=\"bypass -h admin_tvt_eventtime $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Add\" action=\"bypass -h admin_tvt_team_add $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Color\" action=\"bypass -h admin_tvt_team_color $input1 $input2\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Pos\" action=\"bypass -h admin_tvt_team_pos $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Team Remove\" action=\"bypass -h admin_tvt_team_remove $input1\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Join\" action=\"bypass -h admin_tvt_join\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Teleport\" action=\"bypass -h admin_tvt_teleport\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Start\" action=\"bypass -h admin_tvt_start\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Abort\" action=\"bypass -h admin_tvt_abort\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Finish\" action=\"bypass -h admin_tvt_finish\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		// L2EMU_ADD+		replyMSG.append("</tr></table><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Sit Force\" action=\"bypass -h admin_tvt_sit\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Dump\" action=\"bypass -h admin_tvt_dump\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><br><table><tr>");+		replyMSG.append("<td width=\"100\"><button value=\"Save\" action=\"bypass -h admin_tvt_save\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Load\" action=\"bypass -h admin_tvt_load\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("<td width=\"100\"><button value=\"Auto Event\" action=\"bypass -h admin_tvt_autoevent\" width=90 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td>");+		replyMSG.append("</tr></table><br><br>");+		replyMSG.append("Current event...<br1>");+		// L2EMU_ADD+		replyMSG.append("    ... Event Type:&nbsp;<font color=\"00FF00\">" + TvT.getEventTypeByName(TvT._eventType) + "</font><br1>");+		// L2EMU_ADD+		replyMSG.append("    ... name:&nbsp;<font color=\"00FF00\">" + TvT._eventName + "</font><br1>");+		replyMSG.append("    ... description:&nbsp;<font color=\"00FF00\">" + TvT._eventDesc + "</font><br1>");+		replyMSG.append("    ... joining location name:&nbsp;<font color=\"00FF00\">" + TvT._joiningLocationName + "</font><br1>");+		replyMSG.append("    ... joining NPC ID:&nbsp;<font color=\"00FF00\">" + TvT._npcId + " on pos " + TvT._npcX + "," + TvT._npcY + "," + TvT._npcZ + "</font><br1>");+		replyMSG.append("    ... reward ID:&nbsp;<font color=\"00FF00\">" + TvT._rewardId + "</font><br1>");+		replyMSG.append("    ... reward Amount:&nbsp;<font color=\"00FF00\">" + TvT._rewardAmount + "</font><br><br>");+		replyMSG.append("    ... Min lvl:&nbsp;<font color=\"00FF00\">" + TvT._minlvl + "</font><br>");+		replyMSG.append("    ... Max lvl:&nbsp;<font color=\"00FF00\">" + TvT._maxlvl + "</font><br><br>");+		replyMSG.append("    ... Min Players:&nbsp;<font color=\"00FF00\">" + TvT._minPlayers + "</font><br>");+		replyMSG.append("    ... Max Players:&nbsp;<font color=\"00FF00\">" + TvT._maxPlayers + "</font><br><br>");+		replyMSG.append("    ... Joining Time:&nbsp;<font color=\"00FF00\">" + TvT._joinTime + "</font><br>");+		replyMSG.append("    ... Event Timer:&nbsp;<font color=\"00FF00\">" + TvT._eventTime + "</font><br><br>");+		replyMSG.append("Current teams:<br1>");+		replyMSG.append("<center><table border=\"0\">");++		for (String team : TvT._teams)+		{+			replyMSG.append("<tr><td width=\"100\"><font color=\"LEVEL\">" + team + "</font>");++			if (Config.TVT_EVEN_TEAMS.equals("NO") || Config.TVT_EVEN_TEAMS.equals("BALANCE"))+				replyMSG.append("&nbsp;(" + TvT.teamPlayersCount(team) + " joined)");+			else if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+			{+				if (TvT._teleport || TvT._started)+					replyMSG.append("&nbsp;(" + TvT.teamPlayersCount(team) + " in)");+			}++			replyMSG.append("</td></tr><tr><td>");+			replyMSG.append(TvT._teamColors.get(TvT._teams.indexOf(team)));+			replyMSG.append("</td></tr><tr><td>");+			replyMSG.append(TvT._teamsX.get(TvT._teams.indexOf(team)) + ", " + TvT._teamsY.get(TvT._teams.indexOf(team)) + ", " + TvT._teamsZ.get(TvT._teams.indexOf(team)));+			replyMSG.append("</td></tr><tr><td width=\"60\"><button value=\"Remove\" action=\"bypass -h admin_tvt_team_remove " + team + "\" width=50 height=15 back=\"L2UI_ct1.button_df\" fore=\"L2UI_ct1.button_df\"></td></tr>");+		}++		replyMSG.append("</table></center>");++		if (Config.TVT_EVEN_TEAMS.equals("SHUFFLE"))+		{+			if (!TvT._started)+			{+				replyMSG.append("<br1>");+				replyMSG.append(TvT._playersShuffle.size() + " players participating. Waiting to shuffle in teams(done on teleport)!");+				replyMSG.append("<br><br>");+			}+		}++		replyMSG.append("</body></html>");+		adminReply.setHtml(replyMSG.toString());+		activeChar.sendPacket(adminReply);+	}+}\ No newline at end of file#P DatapackIndex: data/xml/admin_commands_rights.xml===================================================================--- data/xml/admin_commands_rights.xml	(revision 1)+++ data/xml/admin_commands_rights.xml	(working copy)@@ -344,5 +344,119 @@ 	<!-- ZONE --> 	<aCar name="admin_zone_check" accessLevel="1" /> 	<aCar name="admin_zone_visual" accessLevel="1" />+	<!-- ADMIN EVENT ENGINE -->+	<aCar name="admin_event" accessLevel="1" />+	<aCar name="admin_event_new" accessLevel="1" />+	<aCar name="admin_event_choose" accessLevel="1" />+	<aCar name="admin_event_store" accessLevel="1" />+	<aCar name="admin_event_set" accessLevel="1" />+	<aCar name="admin_event_change_teams_number" accessLevel="1" />+	<aCar name="admin_event_announce" accessLevel="1" />+	<aCar name="admin_event_panel" accessLevel="1" />+	<aCar name="admin_event_control_begin" accessLevel="1" />+	<aCar name="admin_event_control_teleport" accessLevel="1" />+	<aCar name="admin_add" accessLevel="1" />+	<aCar name="admin_event_see" accessLevel="1" />+	<aCar name="admin_event_del" accessLevel="1" />+	<aCar name="admin_delete_buffer" accessLevel="1" />+	<aCar name="admin_event_control_sit" accessLevel="1" />+	<aCar name="admin_event_name" accessLevel="1" />+	<aCar name="admin_event_control_kill" accessLevel="1" />+	<aCar name="admin_event_control_res" accessLevel="1" />+	<aCar name="admin_event_control_poly" accessLevel="1" />+	<aCar name="admin_event_control_unpoly" accessLevel="1" />+	<aCar name="admin_event_control_prize" accessLevel="1" />+	<aCar name="admin_event_control_chatban" accessLevel="1" />+	<aCar name="admin_event_control_finish" accessLevel="1" />++	<!-- ADMIN TvT Event -->+	<aCar name="admin_tvt" accessLevel="1" />+	<aCar name="admin_tvt_name" accessLevel="1" />+	<aCar name="admin_tvt_desc" accessLevel="1" />+	<aCar name="admin_tvt_join_loc" accessLevel="1" />+	<aCar name="admin_tvt_minlvl" accessLevel="1" />+	<aCar name="admin_tvt_maxlvl" accessLevel="1" />+	<aCar name="admin_tvt_npc" accessLevel="1" />+	<aCar name="admin_tvt_npc_pos" accessLevel="1" />+	<aCar name="admin_tvt_reward" accessLevel="1" />+	<aCar name="admin_tvt_reward_amount" accessLevel="1" />+	<aCar name="admin_tvt_team_add" accessLevel="1" />+	<aCar name="admin_tvt_team_remove" accessLevel="1" />+	<aCar name="admin_tvt_team_pos" accessLevel="1" />+	<aCar name="admin_tvt_team_color" accessLevel="1" />+	<aCar name="admin_tvt_join" accessLevel="1" />+	<aCar name="admin_tvt_teleport" accessLevel="1" />+	<aCar name="admin_tvt_start" accessLevel="1" />+	<aCar name="admin_tvt_abort" accessLevel="1" />+	<aCar name="admin_tvt_finish" accessLevel="1" />+	<aCar name="admin_tvt_sit" accessLevel="1" />+	<aCar name="admin_tvt_dump" accessLevel="1" />+	<aCar name="admin_tvt_save" accessLevel="1" />+	<aCar name="admin_tvt_load" accessLevel="1" />+	<aCar name="admin_tvt_jointime" accessLevel="1" />+	<aCar name="admin_tvt_eventtime" accessLevel="1" />+	<aCar name="admin_tvt_autoevent" accessLevel="1" />+	<aCar name="admin_tvt_minplayers" accessLevel="1" />+	<aCar name="admin_tvt_maxplayers" accessLevel="1" />+	<aCar name="admin_tvtkick" accessLevel="1" />+	<aCar name="admin_tvt_interval" accessLevel="1" /> 	+	<!-- ADMIN CTF Event -->+	<aCar name="admin_ctf" accessLevel="1" />+	<aCar name="admin_ctf_name" accessLevel="1" />+	<aCar name="admin_ctf_desc" accessLevel="1" />+	<aCar name="admin_ctf_join_loc" accessLevel="1" />+	<aCar name="admin_ctf_edit" accessLevel="1" />+	<aCar name="admin_ctf_control" accessLevel="1" />+	<aCar name="admin_ctf_minlvl" accessLevel="1" />+	<aCar name="admin_ctf_maxlvl" accessLevel="1" />+	<aCar name="admin_ctf_tele_npc" accessLevel="1" />+	<aCar name="admin_ctf_tele_team" accessLevel="1" />+	<aCar name="admin_ctf_tele_flag" accessLevel="1" />+	<aCar name="admin_ctf_npc" accessLevel="1" />+	<aCar name="admin_ctf_npc_pos" accessLevel="1" />+	<aCar name="admin_ctf_reward" accessLevel="1" />+	<aCar name="admin_ctf_reward_amount" accessLevel="1" />+	<aCar name="admin_ctf_team_add" accessLevel="1" />+	<aCar name="admin_ctf_team_remove" accessLevel="1" />+	<aCar name="admin_ctf_team_pos" accessLevel="1" />+	<aCar name="admin_ctf_team_color" accessLevel="1" />+	<aCar name="admin_ctf_team_flag" accessLevel="1" />+	<aCar name="admin_ctf_join" accessLevel="1" />+	<aCar name="admin_ctf_teleport" accessLevel="1" />+	<aCar name="admin_ctf_start" accessLevel="1" />+	<aCar name="admin_ctf_abort" accessLevel="1" />+	<aCar name="admin_ctf_finish" accessLevel="1" />+	<aCar name="admin_ctf_sit" accessLevel="1" />+	<aCar name="admin_ctf_dump" accessLevel="1" />+	<aCar name="admin_ctf_save" accessLevel="1" />+	<aCar name="admin_ctf_load" accessLevel="1" />+	<aCar name="admin_ctf_jointime" accessLevel="1" />+	<aCar name="admin_ctf_eventtime" accessLevel="1" />+	<aCar name="admin_ctf_autoevent" accessLevel="1" />+	<aCar name="admin_ctf_minplayers" accessLevel="1" />+	<aCar name="admin_ctf_maxplayers" accessLevel="1" />+	+	<!-- ADMIN DM Event -->+	<aCar name="admin_dmevent" accessLevel="1" />+	<aCar name="admin_dmevent_name" accessLevel="1" />+	<aCar name="admin_dmevent_desc" accessLevel="1" />+	<aCar name="admin_dmevent_join_loc" accessLevel="1" />+	<aCar name="admin_dmevent_minlvl" accessLevel="1" />+	<aCar name="admin_dmevent_maxlvl" accessLevel="1" />+	<aCar name="admin_dmevent_npc" accessLevel="1" />+	<aCar name="admin_dmevent_npc_pos" accessLevel="1" />+	<aCar name="admin_dmevent_reward" accessLevel="1" />+	<aCar name="admin_dmevent_reward_amount" accessLevel="1" />+	<aCar name="admin_dmevent_spawnpos" accessLevel="1" />+	<aCar name="admin_dmevent_color" accessLevel="1" />+	<aCar name="admin_dmevent_join" accessLevel="1" />+	<aCar name="admin_dmevent_teleport" accessLevel="1" />+	<aCar name="admin_dmevent_start" accessLevel="1" />+	<aCar name="admin_dmevent_abort" accessLevel="1" />+	<aCar name="admin_dmevent_finish" accessLevel="1" />+	<aCar name="admin_dmevent_sit" accessLevel="1" />+	<aCar name="admin_dmevent_dump" accessLevel="1" />+	<aCar name="admin_dmevent_save" accessLevel="1" />+	<aCar name="admin_dmevent_load" accessLevel="1" /> </list>\ No newline at end of fileIndex: sql/tvt_teams.sql===================================================================--- sql/tvt_teams.sql	(revision 0)+++ sql/tvt_teams.sql	(working copy)@@ -0,0 +1,22 @@+SET FOREIGN_KEY_CHECKS=0;+-- ----------------------------+-- Table structure for `tvt_teams`+-- -----------------------------++CREATE TABLE `tvt_teams` (+  `teamId` int(4) NOT NULL DEFAULT '0',+  `teamName` varchar(255) NOT NULL DEFAULT '',+  `teamX` int(11) NOT NULL DEFAULT '0',+  `teamY` int(11) NOT NULL DEFAULT '0',+  `teamZ` int(11) NOT NULL DEFAULT '0',+  `teamColor` int(11) NOT NULL DEFAULT '0',+  PRIMARY KEY (`teamId`)+) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci ROW_FORMAT=COMPRESSED COMMENT='L2jHellas Table';++-- ----------------------------+-- Records of `tvt_teams`+-- ----------------------------+INSERT INTO `tvt_teams` VALUES +('0', 'Wolfs', '148179', '45841', '-3413', '16711680'),+('1', 'Beasts', '150787', '45822', '-3413', '255'),+('2', 'Vampires', '149496', '47826', '-3413', '26367');\ No newline at end of fileIndex: sql/ctf.sql===================================================================--- sql/ctf.sql	(revision 0)+++ sql/ctf.sql	(working copy)@@ -0,0 +1,24 @@+SET FOREIGN_KEY_CHECKS=0;+-- ----------------------------+-- Table structure for `ctf`+-- ----------------------------++CREATE TABLE `ctf` (+  `eventName` varchar(255) NOT NULL DEFAULT '',+  `eventDesc` varchar(255) NOT NULL DEFAULT '',+  `joiningLocation` varchar(255) NOT NULL DEFAULT '',+  `minlvl` int(4) NOT NULL DEFAULT '0',+  `maxlvl` int(4) NOT NULL DEFAULT '0',+  `npcId` int(11) NOT NULL DEFAULT '0',+  `npcX` int(11) NOT NULL DEFAULT '0',+  `npcY` int(11) NOT NULL DEFAULT '0',+  `npcZ` int(11) NOT NULL DEFAULT '0',+  `npcHeading` int(11) NOT NULL DEFAULT '0',+  `rewardId` int(11) NOT NULL DEFAULT '0',+  `rewardAmount` int(11) NOT NULL DEFAULT '0',+  `teamsCount` int(4) NOT NULL DEFAULT '0',+  `joinTime` int(11) NOT NULL DEFAULT '0',+  `eventTime` int(11) NOT NULL DEFAULT '0',+  `minPlayers` int(4) NOT NULL DEFAULT '0',+  `maxPlayers` int(4) NOT NULL DEFAULT '0'+) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci ROW_FORMAT=COMPRESSED COMMENT='L2jHellas Table';\ No newline at end of fileIndex: data/xml/npcs/50000-50999.xml===================================================================--- data/xml/npcs/50000-50999.xml	(revision 2)+++ data/xml/npcs/50000-50999.xml	(working copy)@@ -175,4 +175,109 @@ 		<set name="attackRange" val="40"/> 		<ai type="DEFAULT" ssCount="0" ssRate="0" spsCount="0" spsRate="0" aggro="0" canMove="true" seedable="false"/> 	</npc>+	<npc id="50011" idTemplate="31309" name="Aioria" title="TvT Manager">+		<set name="level" val="70"/>+		<set name="radius" val="8"/>+		<set name="height" val="21.5"/>+		<set name="rHand" val="0"/>+		<set name="lHand" val="0"/>+		<set name="type" val="Folk"/>+		<set name="exp" val="0"/>+		<set name="sp" val="0"/>+		<set name="hp" val="2444.46819"/>+		<set name="mp" val="1345.8"/>+		<set name="hpRegen" val="7.5"/>+		<set name="mpRegen" val="2.7"/>+		<set name="pAtk" val="688.86373"/>+		<set name="pDef" val="295.91597"/>+		<set name="mAtk" val="470.40463"/>+		<set name="mDef" val="216.53847"/>+		<set name="crit" val="4"/>+		<set name="atkSpd" val="253"/>+		<set name="str" val="40"/>+		<set name="int" val="21"/>+		<set name="dex" val="30"/>+		<set name="wit" val="20"/>+		<set name="con" val="43"/>+		<set name="men" val="20"/>+		<set name="corpseTime" val="7"/>+		<set name="walkSpd" val="50"/>+		<set name="runSpd" val="120"/>+		<set name="dropHerbGroup" val="0"/>+		<ai type="DEFAULT" ssCount="0" ssRate="0" spsCount="0" spsRate="0" aggro="0" canMove="true" seedable="false"/>+		<skills>+			<skill id="4045" level="1"/>+			<skill id="4416" level="14"/>+		</skills>+	</npc>+	<npc id="50012" idTemplate="31309" name="Leon" title="CTF Manager">+		<set name="level" val="70"/>+		<set name="radius" val="8"/>+		<set name="height" val="21.5"/>+		<set name="rHand" val="0"/>+		<set name="lHand" val="0"/>+		<set name="type" val="Folk"/>+		<set name="exp" val="0"/>+		<set name="sp" val="0"/>+		<set name="hp" val="2444.46819"/>+		<set name="mp" val="1345.8"/>+		<set name="hpRegen" val="7.5"/>+		<set name="mpRegen" val="2.7"/>+		<set name="pAtk" val="688.86373"/>+		<set name="pDef" val="295.91597"/>+		<set name="mAtk" val="470.40463"/>+		<set name="mDef" val="216.53847"/>+		<set name="crit" val="4"/>+		<set name="atkSpd" val="253"/>+		<set name="str" val="40"/>+		<set name="int" val="21"/>+		<set name="dex" val="30"/>+		<set name="wit" val="20"/>+		<set name="con" val="43"/>+		<set name="men" val="20"/>+		<set name="corpseTime" val="7"/>+		<set name="walkSpd" val="50"/>+		<set name="runSpd" val="120"/>+		<set name="dropHerbGroup" val="0"/>+		<ai type="DEFAULT" ssCount="0" ssRate="0" spsCount="0" spsRate="0" aggro="0" canMove="true" seedable="false"/>+		<skills>+			<skill id="4045" level="1"/>+			<skill id="4416" level="14"/>+		</skills>+	</npc>+	<npc id="50013" idTemplate="31309" name="Aioria" title="TvT Manager">+		<set name="level" val="70"/>+		<set name="radius" val="8"/>+		<set name="height" val="21.5"/>+		<set name="rHand" val="0"/>+		<set name="lHand" val="0"/>+		<set name="type" val="Folk"/>+		<set name="exp" val="0"/>+		<set name="sp" val="0"/>+		<set name="hp" val="2444.46819"/>+		<set name="mp" val="1345.8"/>+		<set name="hpRegen" val="7.5"/>+		<set name="mpRegen" val="2.7"/>+		<set name="pAtk" val="688.86373"/>+		<set name="pDef" val="295.91597"/>+		<set name="mAtk" val="470.40463"/>+		<set name="mDef" val="216.53847"/>+		<set name="crit" val="4"/>+		<set name="atkSpd" val="253"/>+		<set name="str" val="40"/>+		<set name="int" val="21"/>+		<set name="dex" val="30"/>+		<set name="wit" val="20"/>+		<set name="con" val="43"/>+		<set name="men" val="20"/>+		<set name="corpseTime" val="7"/>+		<set name="walkSpd" val="50"/>+		<set name="runSpd" val="120"/>+		<set name="dropHerbGroup" val="0"/>+		<ai type="DEFAULT" ssCount="0" ssRate="0" spsCount="0" spsRate="0" aggro="0" canMove="true" seedable="false"/>+		<skills>+			<skill id="4045" level="1"/>+			<skill id="4416" level="14"/>+		</skills>+	</npc> </list>\ No newline at end of fileIndex: sql/dm.sql===================================================================--- sql/dm.sql	(revision 0)+++ sql/dm.sql	(working copy)@@ -0,0 +1,22 @@+SET FOREIGN_KEY_CHECKS=0;+-- ----------------------------+-- Table structure for `dm`+-- ----------------------------++CREATE TABLE `dm` (+  `eventName` varchar(255) NOT NULL DEFAULT '',+  `eventDesc` varchar(255) NOT NULL DEFAULT '',+  `joiningLocation` varchar(255) NOT NULL DEFAULT '',+  `minlvl` int(4) NOT NULL DEFAULT '0',+  `maxlvl` int(4) NOT NULL DEFAULT '0',+  `npcId` int(8) NOT NULL DEFAULT '0',+  `npcX` int(11) NOT NULL DEFAULT '0',+  `npcY` int(11) NOT NULL DEFAULT '0',+  `npcZ` int(11) NOT NULL DEFAULT '0',+  `rewardId` int(11) NOT NULL DEFAULT '0',+  `rewardAmount` int(11) NOT NULL DEFAULT '0',+  `color` int(11) NOT NULL DEFAULT '0',+  `playerX` int(11) NOT NULL DEFAULT '0',+  `playerY` int(11) NOT NULL DEFAULT '0',+  `playerZ` int(11) NOT NULL DEFAULT '0'+) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci ROW_FORMAT=COMPRESSED COMMENT='L2jHellas Table';\ No newline at end of fileIndex: sql/tvt.sql===================================================================--- sql/tvt.sql	(revision 0)+++ sql/tvt.sql	(working copy)@@ -0,0 +1,30 @@+SET FOREIGN_KEY_CHECKS=0;+-- ----------------------------+-- Table structure for `tvt`+-- ----------------------------++CREATE TABLE `tvt` (+  `eventName` varchar(255) NOT NULL DEFAULT '',+  `eventDesc` varchar(255) NOT NULL DEFAULT '',+  `joiningLocation` varchar(255) NOT NULL DEFAULT '',+  `minlvl` int(4) NOT NULL DEFAULT '0',+  `maxlvl` int(4) NOT NULL DEFAULT '0',+  `npcId` int(8) NOT NULL DEFAULT '0',+  `npcX` int(11) NOT NULL DEFAULT '0',+  `npcY` int(11) NOT NULL DEFAULT '0',+  `npcZ` int(11) NOT NULL DEFAULT '0',+  `npcHeading` int(11) NOT NULL DEFAULT '0',+  `rewardId` int(11) NOT NULL DEFAULT '0',+  `rewardAmount` int(11) NOT NULL DEFAULT '0',+  `teamsCount` int(4) NOT NULL DEFAULT '0',+  `joinTime` int(11) NOT NULL DEFAULT '0',+  `eventTime` int(11) NOT NULL DEFAULT '0',+  `minPlayers` int(4) NOT NULL DEFAULT '0',+  `maxPlayers` int(4) NOT NULL DEFAULT '0'+) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci ROW_FORMAT=COMPRESSED COMMENT='L2jHellas Table';++-- ----------------------------+-- Records of `tvt`+-- ----------------------------+INSERT INTO `tvt` values +('TVT', 'A PvP Event', 'Giran', 1, 81, 70010, 82688, 148677, -3469, 0, 57, 100000, 2, 5, 10, 2, 50);\ No newline at end of fileIndex: data/html/mods/Participation.htm===================================================================--- data/html/mods/Participation.htm	(revision 0)+++ data/html/mods/Participation.htm	(working copy)@@ -0,0 +1,5 @@+<html><body><br><center>+Successfully, you have signed up in event!<br>+Please wait till event starts!<br><br>+<a action="bypass -h npc_%objectId%_Chat 0">Ok</a>+</center></html></body>\ No newline at end of fileIndex: sql/ctf_teams.sql===================================================================--- sql/ctf_teams.sql	(revision 0)+++ sql/ctf_teams.sql	(working copy)@@ -0,0 +1,17 @@+SET FOREIGN_KEY_CHECKS=0;+-- ----------------------------+-- Table structure for `ctf_teams`+-- ----------------------------++CREATE TABLE `ctf_teams` (+  `teamId` int(4) NOT NULL DEFAULT '0',+  `teamName` varchar(255) NOT NULL DEFAULT '',+  `teamX` int(11) NOT NULL DEFAULT '0',+  `teamY` int(11) NOT NULL DEFAULT '0',+  `teamZ` int(11) NOT NULL DEFAULT '0',+  `teamColor` int(11) NOT NULL DEFAULT '0',+  `flagX` int(11) NOT NULL DEFAULT '0',+  `flagY` int(11) NOT NULL DEFAULT '0',+  `flagZ` int(11) NOT NULL DEFAULT '0',+  PRIMARY KEY (`teamId`)+) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci ROW_FORMAT=COMPRESSED COMMENT='L2jHellas Table';\ No newline at end of file

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.
Note: Your post will require moderator approval before it will be visible.

Guest
Answer this question...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

×
×
  • Create New...