Classic branch.

This commit is contained in:
MobiusDev
2017-05-01 10:49:52 +00:00
parent 304ca84360
commit 23c1374047
19872 changed files with 3745265 additions and 0 deletions

View File

@@ -0,0 +1,213 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.List;
import java.util.function.Function;
import com.l2jmobius.commons.util.Rnd;
import com.l2jmobius.gameserver.enums.Race;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.CreatureSay;
import com.l2jmobius.gameserver.network.serverpackets.IClientOutgoingPacket;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
/**
* @author Battlecruiser
*/
public abstract class AbstractPlayerGroup
{
/**
* @return a list of all members of this group
*/
public abstract List<L2PcInstance> getMembers();
/**
* @return a list of object IDs of the members of this group
*/
public List<Integer> getMembersObjectId()
{
final List<Integer> ids = new ArrayList<>();
forEachMember(m ->
{
ids.add(m.getObjectId());
return true;
});
return ids;
}
/**
* @return the leader of this group
*/
public abstract L2PcInstance getLeader();
/**
* Change the leader of this group to the specified player.
* @param leader the player to set as the new leader of this group
*/
public abstract void setLeader(L2PcInstance leader);
/**
* @return the leader's object ID
*/
public int getLeaderObjectId()
{
return getLeader().getObjectId();
}
/**
* Check if a given player is the leader of this group.
* @param player the player to check
* @return {@code true} if the specified player is the leader of this group, {@code false} otherwise
*/
public boolean isLeader(L2PcInstance player)
{
return (getLeaderObjectId() == player.getObjectId());
}
/**
* @return the count of all players in this group
*/
public int getMemberCount()
{
return getMembers().size();
}
/**
* @return the count of all player races in this group
*/
public int getRaceCount()
{
final List<Race> partyRaces = new ArrayList<>();
for (L2PcInstance member : getMembers())
{
if (!partyRaces.contains(member.getRace()))
{
partyRaces.add(member.getRace());
}
}
return partyRaces.size();
}
/**
* @return the level of this group
*/
public abstract int getLevel();
/**
* Broadcast a packet to every member of this group.
* @param packet the packet to broadcast
*/
public void broadcastPacket(IClientOutgoingPacket packet)
{
forEachMember(m ->
{
if (m != null)
{
m.sendPacket(packet);
}
return true;
});
}
/**
* Broadcast a system message to this group.
* @param message the system message to broadcast
*/
public void broadcastMessage(SystemMessageId message)
{
broadcastPacket(SystemMessage.getSystemMessage(message));
}
/**
* Broadcast a text message to this group.
* @param text to broadcast
*/
public void broadcastString(String text)
{
broadcastPacket(SystemMessage.sendString(text));
}
public void broadcastCreatureSay(CreatureSay msg, L2PcInstance broadcaster)
{
forEachMember(m ->
{
if ((m != null) && !BlockList.isBlocked(m, broadcaster))
{
m.sendPacket(msg);
}
return true;
});
}
/**
* Check if this group contains a given player.
* @param player the player to check
* @return {@code true} if this group contains the specified player, {@code false} otherwise
*/
public boolean containsPlayer(L2PcInstance player)
{
return getMembers().contains(player);
}
/**
* @return a random member of this group
*/
public L2PcInstance getRandomPlayer()
{
return getMembers().get(Rnd.get(getMemberCount()));
}
/**
* Iterates over the group and executes procedure on each member
* @param procedure the prodecure to be executed on each member.<br>
* If executing the procedure on a member returns {@code true}, the loop continues to the next member, otherwise it breaks the loop
* @return {@code true} if the procedure executed correctly, {@code false} if the loop was broken prematurely
*/
public boolean forEachMember(Function<L2PcInstance, Boolean> procedure)
{
for (L2PcInstance player : getMembers())
{
if (!procedure.apply(player))
{
return false;
}
}
return true;
}
@Override
public boolean equals(Object obj)
{
if (this == obj)
{
return true;
}
if (obj instanceof AbstractPlayerGroup)
{
if (getLeaderObjectId() == ((AbstractPlayerGroup) obj).getLeaderObjectId())
{
return true;
}
}
return false;
}
}

View File

@@ -0,0 +1,49 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* @author UnAfraid
*/
public class ActionDataHolder
{
private final int _id;
private final String _handler;
private final int _optionId;
public ActionDataHolder(StatsSet set)
{
_id = set.getInt("id");
_handler = set.getString("handler");
_optionId = set.getInt("option", 0);
}
public int getId()
{
return _id;
}
public String getHandler()
{
return _handler;
}
public int getOptionId()
{
return _optionId;
}
}

View File

@@ -0,0 +1,118 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* Action Key DTO.
* @author mrTJO, Zoey76
*/
public class ActionKey
{
private final int _cat;
private int _cmd = 0;
private int _key = 0;
private int _tgKey1 = 0;
private int _tgKey2 = 0;
private int _show = 1;
/**
* @param cat category Id
*/
public ActionKey(int cat)
{
_cat = cat;
}
/**
* L2ActionKey Initialization
* @param cat Category ID
* @param cmd Command ID
* @param key User Defined Primary Key
* @param tgKey1 1st Toggled Key (eg. Alt, Ctrl or Shift)
* @param tgKey2 2nd Toggled Key (eg. Alt, Ctrl or Shift)
* @param show Show Action in UI
*/
public ActionKey(int cat, int cmd, int key, int tgKey1, int tgKey2, int show)
{
_cat = cat;
_cmd = cmd;
_key = key;
_tgKey1 = tgKey1;
_tgKey2 = tgKey2;
_show = show;
}
public int getCategory()
{
return _cat;
}
public int getCommandId()
{
return _cmd;
}
public void setCommandId(int cmd)
{
_cmd = cmd;
}
public int getKeyId()
{
return _key;
}
public void setKeyId(int key)
{
_key = key;
}
public int getToogleKey1()
{
return _tgKey1;
}
public void setToogleKey1(int tKey1)
{
_tgKey1 = tKey1;
}
public int getToogleKey2()
{
return _tgKey2;
}
public void setToogleKey2(int tKey2)
{
_tgKey2 = tKey2;
}
public int getShowStatus()
{
return _show;
}
public void setShowStatus(int show)
{
_show = show;
}
public String getSqlSaveString(int playerId, int order)
{
return "(" + playerId + ", " + _cat + ", " + order + ", " + _cmd + "," + _key + ", " + _tgKey1 + ", " + _tgKey2 + ", " + _show + ")";
}
}

View File

@@ -0,0 +1,96 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.actor.L2Character;
/**
* @author xban1x
*/
public final class AggroInfo
{
private final L2Character _attacker;
private int _hate = 0;
private int _damage = 0;
public AggroInfo(L2Character pAttacker)
{
_attacker = pAttacker;
}
public L2Character getAttacker()
{
return _attacker;
}
public int getHate()
{
return _hate;
}
public int checkHate(L2Character owner)
{
if (_attacker.isAlikeDead() || !_attacker.isSpawned() || !owner.isInSurroundingRegion(_attacker))
{
_hate = 0;
}
return _hate;
}
public void addHate(int value)
{
_hate = (int) Math.min(_hate + (long) value, 999999999);
}
public void stopHate()
{
_hate = 0;
}
public int getDamage()
{
return _damage;
}
public void addDamage(int value)
{
_damage = (int) Math.min(_damage + (long) value, 999999999);
}
@Override
public final boolean equals(Object obj)
{
if (this == obj)
{
return true;
}
if (obj instanceof AggroInfo)
{
return (((AggroInfo) obj).getAttacker() == _attacker);
}
return false;
}
@Override
public final int hashCode()
{
return _attacker.getObjectId();
}
}

View File

@@ -0,0 +1,50 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* Holds a list of all AirShip teleports.
* @author xban1x
*/
public final class AirShipTeleportList
{
private final int _location;
private final int[] _fuel;
private final VehiclePathPoint[][] _routes;
public AirShipTeleportList(int loc, int[] f, VehiclePathPoint[][] r)
{
_location = loc;
_fuel = f;
_routes = r;
}
public int getLocation()
{
return _location;
}
public int[] getFuel()
{
return _fuel;
}
public VehiclePathPoint[][] getRoute()
{
return _routes;
}
}

View File

@@ -0,0 +1,176 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.List;
import com.l2jmobius.gameserver.instancemanager.HandysBlockCheckerManager;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.entity.BlockCheckerEngine;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.IClientOutgoingPacket;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
/**
* @author xban1x
*/
public final class ArenaParticipantsHolder
{
private final int _arena;
private final List<L2PcInstance> _redPlayers;
private final List<L2PcInstance> _bluePlayers;
private final BlockCheckerEngine _engine;
public ArenaParticipantsHolder(int arena)
{
_arena = arena;
_redPlayers = new ArrayList<>(6);
_bluePlayers = new ArrayList<>(6);
_engine = new BlockCheckerEngine(this, _arena);
}
public List<L2PcInstance> getRedPlayers()
{
return _redPlayers;
}
public List<L2PcInstance> getBluePlayers()
{
return _bluePlayers;
}
public List<L2PcInstance> getAllPlayers()
{
final List<L2PcInstance> all = new ArrayList<>(12);
all.addAll(_redPlayers);
all.addAll(_bluePlayers);
return all;
}
public void addPlayer(L2PcInstance player, int team)
{
if (team == 0)
{
_redPlayers.add(player);
}
else
{
_bluePlayers.add(player);
}
}
public void removePlayer(L2PcInstance player, int team)
{
if (team == 0)
{
_redPlayers.remove(player);
}
else
{
_bluePlayers.remove(player);
}
}
public int getPlayerTeam(L2PcInstance player)
{
if (_redPlayers.contains(player))
{
return 0;
}
else if (_bluePlayers.contains(player))
{
return 1;
}
else
{
return -1;
}
}
public int getRedTeamSize()
{
return _redPlayers.size();
}
public int getBlueTeamSize()
{
return _bluePlayers.size();
}
public void broadCastPacketToTeam(IClientOutgoingPacket packet)
{
for (L2PcInstance p : _redPlayers)
{
p.sendPacket(packet);
}
for (L2PcInstance p : _bluePlayers)
{
p.sendPacket(packet);
}
}
public void clearPlayers()
{
_redPlayers.clear();
_bluePlayers.clear();
}
public BlockCheckerEngine getEvent()
{
return _engine;
}
public void updateEvent()
{
_engine.updatePlayersOnStart(this);
}
public void checkAndShuffle()
{
final int redSize = _redPlayers.size();
final int blueSize = _bluePlayers.size();
if (redSize > (blueSize + 1))
{
broadCastPacketToTeam(SystemMessage.getSystemMessage(SystemMessageId.TEAM_MEMBERS_WERE_MODIFIED_BECAUSE_THE_TEAMS_WERE_UNBALANCED));
final int needed = redSize - (blueSize + 1);
for (int i = 0; i < (needed + 1); i++)
{
final L2PcInstance plr = _redPlayers.get(i);
if (plr == null)
{
continue;
}
HandysBlockCheckerManager.getInstance().changePlayerToTeam(plr, _arena, 1);
}
}
else if (blueSize > (redSize + 1))
{
broadCastPacketToTeam(SystemMessage.getSystemMessage(SystemMessageId.TEAM_MEMBERS_WERE_MODIFIED_BECAUSE_THE_TEAMS_WERE_UNBALANCED));
final int needed = blueSize - (redSize + 1);
for (int i = 0; i < (needed + 1); i++)
{
final L2PcInstance plr = _bluePlayers.get(i);
if (plr == null)
{
continue;
}
HandysBlockCheckerManager.getInstance().changePlayerToTeam(plr, _arena, 0);
}
}
}
}

View File

@@ -0,0 +1,272 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.commons.database.DatabaseFactory;
import com.l2jmobius.gameserver.data.sql.impl.CharNameTable;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.BlockListPacket;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
/**
* This class ...
* @version $Revision: 1.2 $ $Date: 2004/06/27 08:12:59 $
*/
public class BlockList
{
private static Logger _log = Logger.getLogger(BlockList.class.getName());
private static Map<Integer, List<Integer>> _offlineList = new ConcurrentHashMap<>();
private final L2PcInstance _owner;
private List<Integer> _blockList;
public BlockList(L2PcInstance owner)
{
_owner = owner;
_blockList = _offlineList.get(owner.getObjectId());
if (_blockList == null)
{
_blockList = loadList(_owner.getObjectId());
}
}
private void addToBlockList(int target)
{
_blockList.add(target);
updateInDB(target, true);
}
private void removeFromBlockList(int target)
{
_blockList.remove(Integer.valueOf(target));
updateInDB(target, false);
}
public void playerLogout()
{
_offlineList.put(_owner.getObjectId(), _blockList);
}
private static List<Integer> loadList(int ObjId)
{
final List<Integer> list = new ArrayList<>();
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement("SELECT friendId FROM character_friends WHERE charId=? AND relation=1"))
{
statement.setInt(1, ObjId);
try (ResultSet rset = statement.executeQuery())
{
int friendId;
while (rset.next())
{
friendId = rset.getInt("friendId");
if (friendId == ObjId)
{
continue;
}
list.add(friendId);
}
}
}
catch (Exception e)
{
_log.log(Level.WARNING, "Error found in " + ObjId + " FriendList while loading BlockList: " + e.getMessage(), e);
}
return list;
}
private void updateInDB(int targetId, boolean state)
{
try (Connection con = DatabaseFactory.getInstance().getConnection())
{
if (state) // add
{
try (PreparedStatement statement = con.prepareStatement("INSERT INTO character_friends (charId, friendId, relation) VALUES (?, ?, 1)"))
{
statement.setInt(1, _owner.getObjectId());
statement.setInt(2, targetId);
statement.execute();
}
}
else
// remove
{
try (PreparedStatement statement = con.prepareStatement("DELETE FROM character_friends WHERE charId=? AND friendId=? AND relation=1"))
{
statement.setInt(1, _owner.getObjectId());
statement.setInt(2, targetId);
statement.execute();
}
}
}
catch (Exception e)
{
_log.log(Level.WARNING, "Could not add block player: " + e.getMessage(), e);
}
}
public boolean isInBlockList(L2PcInstance target)
{
return _blockList.contains(target.getObjectId());
}
public boolean isInBlockList(int targetId)
{
return _blockList.contains(targetId);
}
public boolean isBlockAll()
{
return _owner.getMessageRefusal();
}
public static boolean isBlocked(L2PcInstance listOwner, L2PcInstance target)
{
final BlockList blockList = listOwner.getBlockList();
return blockList.isBlockAll() || blockList.isInBlockList(target);
}
public static boolean isBlocked(L2PcInstance listOwner, int targetId)
{
final BlockList blockList = listOwner.getBlockList();
return blockList.isBlockAll() || blockList.isInBlockList(targetId);
}
private void setBlockAll(boolean state)
{
_owner.setMessageRefusal(state);
}
private List<Integer> getBlockList()
{
return _blockList;
}
public static void addToBlockList(L2PcInstance listOwner, int targetId)
{
if (listOwner == null)
{
return;
}
final String charName = CharNameTable.getInstance().getNameById(targetId);
if (listOwner.getFriendList().contains(targetId))
{
final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.THIS_PLAYER_IS_ALREADY_REGISTERED_ON_YOUR_FRIENDS_LIST);
sm.addString(charName);
listOwner.sendPacket(sm);
return;
}
if (listOwner.getBlockList().getBlockList().contains(targetId))
{
listOwner.sendMessage("Already in ignore list.");
return;
}
listOwner.getBlockList().addToBlockList(targetId);
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.S1_HAS_BEEN_ADDED_TO_YOUR_IGNORE_LIST);
sm.addString(charName);
listOwner.sendPacket(sm);
final L2PcInstance player = L2World.getInstance().getPlayer(targetId);
if (player != null)
{
sm = SystemMessage.getSystemMessage(SystemMessageId.C1_HAS_PLACED_YOU_ON_HIS_HER_IGNORE_LIST);
sm.addString(listOwner.getName());
player.sendPacket(sm);
}
}
public static void removeFromBlockList(L2PcInstance listOwner, int targetId)
{
if (listOwner == null)
{
return;
}
SystemMessage sm;
final String charName = CharNameTable.getInstance().getNameById(targetId);
if (!listOwner.getBlockList().getBlockList().contains(targetId))
{
sm = SystemMessage.getSystemMessage(SystemMessageId.THAT_IS_AN_INCORRECT_TARGET);
listOwner.sendPacket(sm);
return;
}
listOwner.getBlockList().removeFromBlockList(targetId);
sm = SystemMessage.getSystemMessage(SystemMessageId.S1_HAS_BEEN_REMOVED_FROM_YOUR_IGNORE_LIST);
sm.addString(charName);
listOwner.sendPacket(sm);
}
public static boolean isInBlockList(L2PcInstance listOwner, L2PcInstance target)
{
return listOwner.getBlockList().isInBlockList(target);
}
public boolean isBlockAll(L2PcInstance listOwner)
{
return listOwner.getBlockList().isBlockAll();
}
public static void setBlockAll(L2PcInstance listOwner, boolean newValue)
{
listOwner.getBlockList().setBlockAll(newValue);
}
public static void sendListToOwner(L2PcInstance listOwner)
{
listOwner.sendPacket(new BlockListPacket(listOwner.getBlockList().getBlockList()));
}
/**
* @param ownerId object id of owner block list
* @param targetId object id of potential blocked player
* @return true if blocked
*/
public static boolean isInBlockList(int ownerId, int targetId)
{
final L2PcInstance player = L2World.getInstance().getPlayer(ownerId);
if (player != null)
{
return BlockList.isBlocked(player, targetId);
}
if (!_offlineList.containsKey(ownerId))
{
_offlineList.put(ownerId, loadList(ownerId));
}
return _offlineList.get(ownerId).contains(targetId);
}
}

View File

@@ -0,0 +1,36 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* @author UnAfraid
*/
public class ChanceLocation extends Location
{
private final double _chance;
public ChanceLocation(int x, int y, int z, int heading, double chance)
{
super(x, y, z, heading);
_chance = chance;
}
public double getChance()
{
return _chance;
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,438 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.itemcontainer.Inventory;
import com.l2jmobius.gameserver.model.itemcontainer.PcInventory;
import com.l2jmobius.gameserver.model.variables.PlayerVariables;
/**
* Used to Store data sent to Client for Character.<br>
* Selection screen.
* @version $Revision: 1.2.2.2.2.4 $ $Date: 2005/03/27 15:29:33 $
*/
public class CharSelectInfoPackage
{
private String _name;
private int _objectId = 0;
private long _exp = 0;
private long _sp = 0;
private int _clanId = 0;
private int _race = 0;
private int _classId = 0;
private int _baseClassId = 0;
private long _deleteTimer = 0L;
private long _lastAccess = 0L;
private int _face = 0;
private int _hairStyle = 0;
private int _hairColor = 0;
private int _sex = 0;
private int _level = 1;
private int _maxHp = 0;
private double _currentHp = 0;
private int _maxMp = 0;
private double _currentMp = 0;
private final int[][] _paperdoll;
private int _reputation = 0;
private int _pkKills = 0;
private int _pvpKills = 0;
private int _augmentationId = 0;
private int _x = 0;
private int _y = 0;
private int _z = 0;
private String _htmlPrefix = null;
private boolean _isGood = false;
private boolean _isEvil = false;
private int _vitalityPoints = 0;
private int _accessLevel = 0;
private boolean _isNoble;
private final PlayerVariables _vars;
/**
* Constructor for CharSelectInfoPackage.
* @param objectId character object Id.
* @param name the character's name.
*/
public CharSelectInfoPackage(int objectId, String name)
{
setObjectId(objectId);
_name = name;
_paperdoll = PcInventory.restoreVisibleInventory(objectId);
_vars = new PlayerVariables(_objectId);
}
/**
* @return the character object Id.
*/
public int getObjectId()
{
return _objectId;
}
public void setObjectId(int objectId)
{
_objectId = objectId;
}
/**
* @return the character's access level.
*/
public int getAccessLevel()
{
return _accessLevel;
}
/**
* @param level the character's access level to be set.
*/
public void setAccessLevel(int level)
{
_accessLevel = level;
}
public boolean isGood()
{
return _isGood;
}
public void setGood()
{
_isGood = true;
_isEvil = false;
}
public boolean isEvil()
{
return _isEvil;
}
public void setEvil()
{
_isGood = false;
_isEvil = true;
}
public int getClanId()
{
return _clanId;
}
public void setClanId(int clanId)
{
_clanId = clanId;
}
public int getClassId()
{
return _classId;
}
public int getBaseClassId()
{
return _baseClassId;
}
public void setClassId(int classId)
{
_classId = classId;
}
public void setBaseClassId(int baseClassId)
{
_baseClassId = baseClassId;
}
public double getCurrentHp()
{
return _currentHp;
}
public void setCurrentHp(double currentHp)
{
_currentHp = currentHp;
}
public double getCurrentMp()
{
return _currentMp;
}
public void setCurrentMp(double currentMp)
{
_currentMp = currentMp;
}
public long getDeleteTimer()
{
return _deleteTimer;
}
public void setDeleteTimer(long deleteTimer)
{
_deleteTimer = deleteTimer;
}
public long getLastAccess()
{
return _lastAccess;
}
public void setLastAccess(long lastAccess)
{
_lastAccess = lastAccess;
}
public long getExp()
{
return _exp;
}
public void setExp(long exp)
{
_exp = exp;
}
public int getFace()
{
return _vars.getInt("visualFaceId", _face);
}
public void setFace(int face)
{
_face = face;
}
public int getHairColor()
{
return _vars.getInt("visualHairColorId", _hairColor);
}
public void setHairColor(int hairColor)
{
_hairColor = hairColor;
}
public int getHairStyle()
{
return _vars.getInt("visualHairId", _hairStyle);
}
public void setHairStyle(int hairStyle)
{
_hairStyle = hairStyle;
}
public int getPaperdollObjectId(int slot)
{
return _paperdoll[slot][0];
}
public int getPaperdollItemId(int slot)
{
return _paperdoll[slot][1];
}
public int getPaperdollItemVisualId(int slot)
{
return _paperdoll[slot][3];
}
public int getLevel()
{
return _level;
}
public void setLevel(int level)
{
_level = level;
}
public int getMaxHp()
{
return _maxHp;
}
public void setMaxHp(int maxHp)
{
_maxHp = maxHp;
}
public int getMaxMp()
{
return _maxMp;
}
public void setMaxMp(int maxMp)
{
_maxMp = maxMp;
}
public String getName()
{
return _name;
}
public void setName(String name)
{
_name = name;
}
public int getRace()
{
return _race;
}
public void setRace(int race)
{
_race = race;
}
public int getSex()
{
return _sex;
}
public void setSex(int sex)
{
_sex = sex;
}
public long getSp()
{
return _sp;
}
public void setSp(long sp)
{
_sp = sp;
}
public int getEnchantEffect()
{
return _paperdoll[Inventory.PAPERDOLL_RHAND][2];
}
public void setReputation(int reputation)
{
_reputation = reputation;
}
public int getReputation()
{
return _reputation;
}
public void setAugmentationId(int augmentationId)
{
_augmentationId = augmentationId;
}
public int getAugmentationId()
{
return _augmentationId;
}
public void setPkKills(int PkKills)
{
_pkKills = PkKills;
}
public int getPkKills()
{
return _pkKills;
}
public void setPvPKills(int PvPKills)
{
_pvpKills = PvPKills;
}
public int getPvPKills()
{
return _pvpKills;
}
public int getX()
{
return _x;
}
public int getY()
{
return _y;
}
public int getZ()
{
return _z;
}
public void setX(int x)
{
_x = x;
}
public void setY(int y)
{
_y = y;
}
public void setZ(int z)
{
_z = z;
}
public String getHtmlPrefix()
{
return _htmlPrefix;
}
public void setHtmlPrefix(String s)
{
_htmlPrefix = s;
}
public void setVitalityPoints(int points)
{
_vitalityPoints = points;
}
public int getVitalityPoints()
{
return _vitalityPoints;
}
public boolean isHairAccessoryEnabled()
{
return _vars.getBoolean(PlayerVariables.HAIR_ACCESSORY_VARIABLE_NAME, true);
}
public int getVitalityItemsUsed()
{
return _vars.getInt(PlayerVariables.VITALITY_ITEMS_USED_VARIABLE_NAME, 0);
}
public boolean isNoble()
{
return _isNoble;
}
public void setNoble(boolean noble)
{
_isNoble = noble;
}
}

View File

@@ -0,0 +1,49 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* @author UnAfraid
*/
public class ClanInfo
{
private final L2Clan _clan;
private final int _total;
private final int _online;
public ClanInfo(L2Clan clan)
{
_clan = clan;
_total = clan.getMembersCount();
_online = clan.getOnlineMembersCount();
}
public L2Clan getClan()
{
return _clan;
}
public int getTotal()
{
return _total;
}
public int getOnline()
{
return _online;
}
}

View File

@@ -0,0 +1,62 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* This enum is used for clan privileges.<br>
* The ordinal of each entry is the bit index in the privilege bitmask.
* @author HorridoJoho
*/
public enum ClanPrivilege
{
/** dummy entry */
DUMMY,
/** Privilege to join clan */
CL_JOIN_CLAN,
/** Privilege to give a title */
CL_GIVE_TITLE,
/** Privilege to view warehouse content */
CL_VIEW_WAREHOUSE,
/** Privilege to manage clan ranks */
CL_MANAGE_RANKS,
CL_PLEDGE_WAR,
CL_DISMISS,
/** Privilege to register clan crest */
CL_REGISTER_CREST,
CL_APPRENTICE,
CL_TROOPS_FAME,
CL_SUMMON_AIRSHIP,
/** Privilege to open a door */
CH_OPEN_DOOR,
CH_OTHER_RIGHTS,
CH_AUCTION,
CH_DISMISS,
CH_SET_FUNCTIONS,
CS_OPEN_DOOR,
CS_MANOR_ADMIN,
CS_MANAGE_SIEGE,
CS_USE_FUNCTIONS,
CS_DISMISS,
CS_TAXES,
CS_MERCENARIES,
CS_SET_FUNCTIONS;
public int getBitmask()
{
return 1 << ordinal();
}
}

View File

@@ -0,0 +1,332 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.concurrent.Future;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicInteger;
import com.l2jmobius.Config;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.data.sql.impl.ClanTable;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.events.EventDispatcher;
import com.l2jmobius.gameserver.model.events.impl.clan.OnClanWarStart;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.SurrenderPledgeWar;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
/**
* @author Sdw
*/
public final class ClanWar
{
public static final long TIME_TO_CANCEL_NON_MUTUAL_CLAN_WAR = TimeUnit.DAYS.toMillis(7);
public static final long TIME_TO_DELETION_AFTER_CANCELLATION = TimeUnit.DAYS.toMillis(5);
public static final long TIME_TO_DELETION_AFTER_DEFEAT = TimeUnit.DAYS.toMillis(21);
private final int _attackerClanId;
private final int _attackedClanId;
private int _winnerClanId = 0;
private ClanWarState _state;
private Future<?> _cancelTask;
private final long _startTime;
private long _endTime = 0;
private final AtomicInteger _attackerKillCount = new AtomicInteger();
private final AtomicInteger _attackedKillCount = new AtomicInteger();
public ClanWar(L2Clan attacker, L2Clan attacked)
{
_attackerClanId = attacker.getId();
_attackedClanId = attacked.getId();
_startTime = System.currentTimeMillis();
_state = ClanWarState.BLOOD_DECLARATION;
_cancelTask = ThreadPoolManager.getInstance().scheduleGeneral(() ->
{
clanWarTimeout();
}, (_startTime + TIME_TO_CANCEL_NON_MUTUAL_CLAN_WAR) - System.currentTimeMillis());
attacker.addWar(attacked.getId(), this);
attacked.addWar(attacker.getId(), this);
EventDispatcher.getInstance().notifyEventAsync(new OnClanWarStart(attacker, attacked));
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.YOU_HAVE_DECLARED_A_CLAN_WAR_WITH_S1);
sm.addString(attacked.getName());
attacker.broadcastToOnlineMembers(sm);
sm = SystemMessage.getSystemMessage(SystemMessageId.S1_HAS_DECLARED_A_CLAN_WAR_THE_WAR_WILL_AUTOMATICALLY_START_IF_YOU_KILL_S1_CLAN_MEMBERS_5_TIMES_WITHIN_A_WEEK);
sm.addString(attacker.getName());
attacked.broadcastToOnlineMembers(sm);
}
public ClanWar(L2Clan attacker, L2Clan attacked, int attackerKillCount, int attackedKillCount, int winnerClan, long startTime, long endTime, ClanWarState state)
{
_attackerClanId = attacker.getId();
_attackedClanId = attacked.getId();
_startTime = startTime;
_endTime = endTime;
_state = state;
_attackerKillCount.set(attackerKillCount);
_attackedKillCount.set(attackedKillCount);
_winnerClanId = winnerClan;
if ((_startTime + TIME_TO_CANCEL_NON_MUTUAL_CLAN_WAR) > System.currentTimeMillis())
{
_cancelTask = ThreadPoolManager.getInstance().scheduleGeneral(() ->
{
clanWarTimeout();
}, (_startTime + TIME_TO_CANCEL_NON_MUTUAL_CLAN_WAR) - System.currentTimeMillis());
}
if (_endTime > 0)
{
final long endTimePeriod = _endTime + (_state == ClanWarState.TIE ? TIME_TO_DELETION_AFTER_CANCELLATION : TIME_TO_DELETION_AFTER_DEFEAT);
if (endTimePeriod > System.currentTimeMillis())
{
ClanTable.getInstance().deleteclanswars(_attackerClanId, _attackedClanId);
}
else
{
ThreadPoolManager.getInstance().scheduleGeneral(() ->
{
ClanTable.getInstance().deleteclanswars(_attackerClanId, _attackedClanId);
}, endTimePeriod);
}
}
}
public void onKill(L2PcInstance killer, L2PcInstance victim)
{
final L2Clan victimClan = victim.getClan();
final L2Clan killerClan = killer.getClan();
// Reputation increase by killing an enemy (over level 4) in a clan war under the condition of mutual war declaration
if ((victim.getLevel() > 4) && (_state == ClanWarState.MUTUAL))
{
// however, when the other side reputation score is 0 or below, your clan cannot acquire any reputation points from them.
if (victimClan.getReputationScore() > 0)
{
victimClan.takeReputationScore(Config.REPUTATION_SCORE_PER_KILL, false);
killerClan.addReputationScore(Config.REPUTATION_SCORE_PER_KILL, false);
}
// System Message notification to clan members
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.BECAUSE_C1_WAS_KILLED_BY_A_CLAN_MEMBER_OF_S2_CLAN_REPUTATION_DECREASED_BY_1);
sm.addPcName(victim);
sm.addString(killerClan.getName());
victimClan.broadcastToOtherOnlineMembers(sm, victim);
sm = SystemMessage.getSystemMessage(SystemMessageId.BECAUSE_A_CLAN_MEMBER_OF_S1_WAS_KILLED_BY_C2_CLAN_REPUTATION_INCREASED_BY_1);
sm.addString(victimClan.getName());
sm.addPcName(killer);
killerClan.broadcastToOtherOnlineMembers(sm, killer);
if (killerClan.getId() == _attackerClanId)
{
_attackerKillCount.incrementAndGet();
}
else
{
_attackedKillCount.incrementAndGet();
}
}
else if ((_state == ClanWarState.BLOOD_DECLARATION) && (victimClan.getId() == _attackerClanId))
{
final int killCount = _attackedKillCount.incrementAndGet();
if (killCount >= 5)
{
_state = ClanWarState.MUTUAL;
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.A_CLAN_WAR_WITH_CLAN_S1_HAS_STARTED_THE_CLAN_THAT_CANCELS_THE_WAR_FIRST_WILL_LOSE_5_000_CLAN_REPUTATION_ANY_CLAN_THAT_CANCELS_THE_WAR_WILL_BE_UNABLE_TO_DECLARE_A_WAR_FOR_1_WEEK_IF_YOUR_CLAN_MEMBER_GETS_KILLED_BY_THE_OTHER_CLAN_XP_DECREASES_BY_1_4_OF_THE_AMOUNT_THAT_DECREASES_IN_THE_HUNTING_GROUND);
sm.addString(victimClan.getName());
killerClan.broadcastToOnlineMembers(sm);
sm = SystemMessage.getSystemMessage(SystemMessageId.A_CLAN_WAR_WITH_CLAN_S1_HAS_STARTED_THE_CLAN_THAT_CANCELS_THE_WAR_FIRST_WILL_LOSE_5_000_CLAN_REPUTATION_ANY_CLAN_THAT_CANCELS_THE_WAR_WILL_BE_UNABLE_TO_DECLARE_A_WAR_FOR_1_WEEK_IF_YOUR_CLAN_MEMBER_GETS_KILLED_BY_THE_OTHER_CLAN_XP_DECREASES_BY_1_4_OF_THE_AMOUNT_THAT_DECREASES_IN_THE_HUNTING_GROUND);
sm.addString(killerClan.getName());
victimClan.broadcastToOnlineMembers(sm);
if (_cancelTask != null)
{
_cancelTask.cancel(true);
_cancelTask = null;
}
}
else
{
final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.A_CLAN_MEMBER_OF_S1_WAS_KILLED_BY_YOUR_CLAN_MEMBER_IF_YOUR_CLAN_KILLS_S2_MEMBERS_OF_CLAN_S1_A_CLAN_WAR_WITH_CLAN_S1_WILL_START);
sm.addString(victimClan.getName());
sm.addInt(5 - killCount);
killerClan.broadcastToOnlineMembers(sm);
}
}
}
public void cancel(L2PcInstance player, L2Clan cancelor)
{
final L2Clan winnerClan = cancelor.getId() == _attackerClanId ? ClanTable.getInstance().getClan(_attackedClanId) : ClanTable.getInstance().getClan(_attackerClanId);
if (cancelor.getReputationScore() > 5000)
{
cancelor.takeReputationScore(5000, true);
player.sendPacket(new SurrenderPledgeWar(cancelor.getName(), player.getName()));
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.THE_WAR_ENDED_BY_YOUR_DEFEAT_DECLARATION_WITH_THE_S1_CLAN);
sm.addString(winnerClan.getName());
cancelor.broadcastToOnlineMembers(sm);
sm = SystemMessage.getSystemMessage(SystemMessageId.THE_WAR_ENDED_BY_THE_S1_CLAN_S_DEFEAT_DECLARATION_YOU_HAVE_WON_THE_CLAN_WAR_OVER_THE_S1_CLAN);
sm.addString(cancelor.getName());
winnerClan.broadcastToOnlineMembers(sm);
_winnerClanId = winnerClan.getId();
_endTime = System.currentTimeMillis();
ThreadPoolManager.getInstance().scheduleGeneral(() ->
{
ClanTable.getInstance().deleteclanswars(cancelor.getId(), winnerClan.getId());
}, (_endTime + TIME_TO_DELETION_AFTER_DEFEAT) - System.currentTimeMillis());
}
}
public void clanWarTimeout()
{
final L2Clan attackerClan = ClanTable.getInstance().getClan(_attackerClanId);
final L2Clan attackedClan = ClanTable.getInstance().getClan(_attackedClanId);
if ((attackerClan != null) && (attackedClan != null))
{
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.A_CLAN_WAR_DECLARED_BY_CLAN_S1_WAS_CANCELLED);
sm.addString(attackerClan.getName());
attackedClan.broadcastToOnlineMembers(sm);
sm = SystemMessage.getSystemMessage(SystemMessageId.BECAUSE_CLAN_S1_DID_NOT_FIGHT_BACK_FOR_1_WEEK_THE_CLAN_WAR_WAS_CANCELLED);
sm.addString(attackedClan.getName());
attackerClan.broadcastToOnlineMembers(sm);
_state = ClanWarState.TIE;
_endTime = System.currentTimeMillis();
ThreadPoolManager.getInstance().scheduleGeneral(() ->
{
ClanTable.getInstance().deleteclanswars(attackerClan.getId(), attackedClan.getId());
}, (_endTime + TIME_TO_DELETION_AFTER_CANCELLATION) - System.currentTimeMillis());
}
}
public void mutualClanWarAccepted(L2Clan attacker, L2Clan attacked)
{
_state = ClanWarState.MUTUAL;
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.A_CLAN_WAR_WITH_CLAN_S1_HAS_STARTED_THE_CLAN_THAT_CANCELS_THE_WAR_FIRST_WILL_LOSE_5_000_CLAN_REPUTATION_ANY_CLAN_THAT_CANCELS_THE_WAR_WILL_BE_UNABLE_TO_DECLARE_A_WAR_FOR_1_WEEK_IF_YOUR_CLAN_MEMBER_GETS_KILLED_BY_THE_OTHER_CLAN_XP_DECREASES_BY_1_4_OF_THE_AMOUNT_THAT_DECREASES_IN_THE_HUNTING_GROUND);
sm.addString(attacker.getName());
attacked.broadcastToOnlineMembers(sm);
sm = SystemMessage.getSystemMessage(SystemMessageId.A_CLAN_WAR_WITH_CLAN_S1_HAS_STARTED_THE_CLAN_THAT_CANCELS_THE_WAR_FIRST_WILL_LOSE_5_000_CLAN_REPUTATION_ANY_CLAN_THAT_CANCELS_THE_WAR_WILL_BE_UNABLE_TO_DECLARE_A_WAR_FOR_1_WEEK_IF_YOUR_CLAN_MEMBER_GETS_KILLED_BY_THE_OTHER_CLAN_XP_DECREASES_BY_1_4_OF_THE_AMOUNT_THAT_DECREASES_IN_THE_HUNTING_GROUND);
sm.addString(attacked.getName());
attacker.broadcastToOnlineMembers(sm);
if (_cancelTask != null)
{
_cancelTask.cancel(true);
_cancelTask = null;
}
}
public int getKillDifference(L2Clan clan)
{
return _attackerClanId == clan.getId() ? _attackerKillCount.get() - _attackedKillCount.get() : _attackedKillCount.get() - _attackerKillCount.get();
}
public ClanWarState getClanWarState(L2Clan clan)
{
if (_winnerClanId > 0)
{
return _winnerClanId == clan.getId() ? ClanWarState.WIN : ClanWarState.LOSS;
}
return _state;
}
public int getAttackerClanId()
{
return _attackerClanId;
}
public int getAttackedClanId()
{
return _attackedClanId;
}
public int getAttackerKillCount()
{
return _attackerKillCount.get();
}
public int getAttackedKillCount()
{
return _attackedKillCount.get();
}
public int getWinnerClanId()
{
return _winnerClanId;
}
public long getStartTime()
{
return _startTime;
}
public long getEndTime()
{
return _endTime;
}
public ClanWarState getState()
{
return _state;
}
public int getKillToStart()
{
return _state == ClanWarState.BLOOD_DECLARATION ? 5 - _attackedKillCount.get() : 0;
}
public int getRemainingTime()
{
return (int) TimeUnit.SECONDS.convert(_startTime + TIME_TO_CANCEL_NON_MUTUAL_CLAN_WAR, TimeUnit.MILLISECONDS);
}
public L2Clan getOpposingClan(L2Clan clan)
{
return _attackerClanId == clan.getId() ? ClanTable.getInstance().getClan(_attackedClanId) : ClanTable.getInstance().getClan(_attackerClanId);
}
public enum ClanWarState
{
DECLARATION,
BLOOD_DECLARATION,
MUTUAL,
WIN,
LOSS,
TIE
}
}

View File

@@ -0,0 +1,125 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.Config;
import com.l2jmobius.gameserver.datatables.ItemTable;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.InventoryUpdate;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
public class CombatFlag
{
// private static final Logger LOGGER = Logger.getLogger(CombatFlag.class.getName());
private L2PcInstance _player = null;
private int _playerId = 0;
private L2ItemInstance _item = null;
private L2ItemInstance _itemInstance;
private final Location _location;
private final int _itemId;
@SuppressWarnings("unused")
private final int _fortId;
public CombatFlag(int fort_id, int x, int y, int z, int heading, int item_id)
{
_fortId = fort_id;
_location = new Location(x, y, z, heading);
_itemId = item_id;
}
public synchronized void spawnMe()
{
// Init the dropped L2ItemInstance and add it in the world as a visible object at the position where mob was last
_itemInstance = ItemTable.getInstance().createItem("Combat", _itemId, 1, null, null);
_itemInstance.dropMe(null, _location.getX(), _location.getY(), _location.getZ());
}
public synchronized void unSpawnMe()
{
if (_player != null)
{
dropIt();
}
if (_itemInstance != null)
{
_itemInstance.decayMe();
}
}
public boolean activate(L2PcInstance player, L2ItemInstance item)
{
if (player.isMounted())
{
player.sendPacket(SystemMessageId.YOU_DO_NOT_MEET_THE_REQUIRED_CONDITION_TO_EQUIP_THAT_ITEM);
return false;
}
// Player holding it data
_player = player;
_playerId = _player.getObjectId();
_itemInstance = null;
// Equip with the weapon
_item = item;
_player.getInventory().equipItem(_item);
final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.YOU_HAVE_EQUIPPED_YOUR_S1);
sm.addItemName(_item);
_player.sendPacket(sm);
// Refresh inventory
if (!Config.FORCE_INVENTORY_UPDATE)
{
final InventoryUpdate iu = new InventoryUpdate();
iu.addItem(_item);
_player.sendInventoryUpdate(iu);
}
else
{
_player.sendItemList(false);
}
// Refresh player stats
_player.broadcastUserInfo();
_player.setCombatFlagEquipped(true);
return true;
}
public void dropIt()
{
// Reset player stats
_player.setCombatFlagEquipped(false);
final int slot = _player.getInventory().getSlotFromItem(_item);
_player.getInventory().unEquipItemInBodySlot(slot);
_player.destroyItem("CombatFlag", _item, null, true);
_item = null;
_player.broadcastUserInfo();
_player = null;
_playerId = 0;
}
public int getPlayerObjectId()
{
return _playerId;
}
public L2ItemInstance getCombatFlagInstance()
{
return _itemInstance;
}
}

View File

@@ -0,0 +1,106 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.HashSet;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ScheduledFuture;
import java.util.function.Predicate;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.model.actor.L2Character;
import com.l2jmobius.gameserver.model.events.EventDispatcher;
import com.l2jmobius.gameserver.model.events.impl.character.OnCreatureSee;
/**
* @author UnAfraid
*/
public class CreatureContainer
{
private final Set<Integer> _seen = ConcurrentHashMap.newKeySet();
private final L2Character _owner;
private final int _range;
private ScheduledFuture<?> _task;
private Predicate<L2Character> _condition = null;
public CreatureContainer(L2Character owner, int range, Predicate<L2Character> condition)
{
_owner = owner;
_range = range;
_condition = condition;
start();
}
public L2Character getOwner()
{
return _owner;
}
public int getRange()
{
return _range;
}
/**
* Starts the task that scans for new creatures
*/
public void start()
{
if ((_task == null) || _task.isDone())
{
_task = ThreadPoolManager.getInstance().scheduleAiAtFixedRate(this::update, 1000L, 1000L);
}
}
/**
* @return {@code false} if the task could not be cancelled, typically because it has already completed normally; {@code true} otherwise
*/
public boolean stop()
{
return (_task != null) && !_task.isDone() && _task.cancel(false);
}
/**
* Resets the creatures container, all previously seen creature will be discarded and next time update method is called will notify for each creature that owner sees!
*/
public void reset()
{
_seen.clear();
}
/**
* Scans around the npc and notifies about new creature owner seen
*/
private void update()
{
final Set<Integer> verified = new HashSet<>();
L2World.getInstance().forEachVisibleObjectInRange(_owner, L2Character.class, _range, creature ->
{
if ((_condition == null) || _condition.test(creature))
{
if (_seen.add(creature.getObjectId()))
{
EventDispatcher.getInstance().notifyEventAsync(new OnCreatureSee(_owner, creature), _owner);
}
verified.add(creature.getObjectId());
}
});
_seen.retainAll(verified);
}
}

View File

@@ -0,0 +1,36 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* @author malyelfik
*/
public final class CropProcure extends SeedProduction
{
private final int _rewardType;
public CropProcure(int id, long amount, int type, long startAmount, long price)
{
super(id, amount, price, startAmount);
_rewardType = type;
}
public final int getReward()
{
return _rewardType;
}
}

View File

@@ -0,0 +1,51 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.List;
import com.l2jmobius.gameserver.model.holders.ItemChanceHolder;
/**
* @author UnAfraid
*/
public class CrystalizationData
{
private final int _id;
private final List<ItemChanceHolder> _items = new ArrayList<>();
public CrystalizationData(int id)
{
_id = id;
}
public int getId()
{
return _id;
}
public void addItem(ItemChanceHolder item)
{
_items.add(item);
}
public List<ItemChanceHolder> getItems()
{
return _items;
}
}

View File

@@ -0,0 +1,739 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.util.concurrent.ScheduledFuture;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.Config;
import com.l2jmobius.commons.database.DatabaseFactory;
import com.l2jmobius.commons.util.Rnd;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.data.xml.impl.SkillData;
import com.l2jmobius.gameserver.instancemanager.CursedWeaponsManager;
import com.l2jmobius.gameserver.model.L2Party.MessageType;
import com.l2jmobius.gameserver.model.actor.L2Attackable;
import com.l2jmobius.gameserver.model.actor.L2Character;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.interfaces.INamable;
import com.l2jmobius.gameserver.model.items.L2Item;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
import com.l2jmobius.gameserver.model.skills.CommonSkill;
import com.l2jmobius.gameserver.model.skills.Skill;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.Earthquake;
import com.l2jmobius.gameserver.network.serverpackets.ExRedSky;
import com.l2jmobius.gameserver.network.serverpackets.InventoryUpdate;
import com.l2jmobius.gameserver.network.serverpackets.SocialAction;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
import com.l2jmobius.gameserver.network.serverpackets.UserInfo;
import com.l2jmobius.gameserver.util.Broadcast;
public class CursedWeapon implements INamable
{
private static final Logger _log = Logger.getLogger(CursedWeapon.class.getName());
// _name is the name of the cursed weapon associated with its ID.
private final String _name;
// _itemId is the Item ID of the cursed weapon.
private final int _itemId;
// _skillId is the skills ID.
private final int _skillId;
private final int _skillMaxLevel;
private int _dropRate;
private int _duration;
private int _durationLost;
private int _disapearChance;
private int _stageKills;
// this should be false unless if the cursed weapon is dropped, in that case it would be true.
private boolean _isDropped = false;
// this sets the cursed weapon status to true only if a player has the cursed weapon, otherwise this should be false.
private boolean _isActivated = false;
private ScheduledFuture<?> _removeTask;
private int _nbKills = 0;
private long _endTime = 0;
private int _playerId = 0;
protected L2PcInstance _player = null;
private L2ItemInstance _item = null;
private int _playerReputation = 0;
private int _playerPkKills = 0;
protected int transformationId = 0;
public CursedWeapon(int itemId, int skillId, String name)
{
_name = name;
_itemId = itemId;
_skillId = skillId;
_skillMaxLevel = SkillData.getInstance().getMaxLevel(_skillId);
}
public void endOfLife()
{
if (_isActivated)
{
if ((_player != null) && _player.isOnline())
{
// Remove from player
_log.info(_name + " being removed online.");
_player.abortAttack();
_player.setReputation(_playerReputation);
_player.setPkKills(_playerPkKills);
_player.setCursedWeaponEquippedId(0);
removeSkill();
// Remove
_player.getInventory().unEquipItemInBodySlot(L2Item.SLOT_LR_HAND);
_player.storeMe();
// Destroy
final L2ItemInstance removedItem = _player.getInventory().destroyItemByItemId("", _itemId, 1, _player, null);
if (!Config.FORCE_INVENTORY_UPDATE)
{
final InventoryUpdate iu = new InventoryUpdate();
if (removedItem.getCount() == 0)
{
iu.addRemovedItem(removedItem);
}
else
{
iu.addModifiedItem(removedItem);
}
_player.sendInventoryUpdate(iu);
}
else
{
_player.sendItemList(false);
}
_player.broadcastUserInfo();
}
else
{
// Remove from Db
_log.info(_name + " being removed offline.");
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement del = con.prepareStatement("DELETE FROM items WHERE owner_id=? AND item_id=?");
PreparedStatement ps = con.prepareStatement("UPDATE characters SET reputation=?, pkkills=? WHERE charId=?"))
{
// Delete the item
del.setInt(1, _playerId);
del.setInt(2, _itemId);
if (del.executeUpdate() != 1)
{
_log.warning("Error while deleting itemId " + _itemId + " from userId " + _playerId);
}
// Restore the reputation
ps.setInt(1, _playerReputation);
ps.setInt(2, _playerPkKills);
ps.setInt(3, _playerId);
if (ps.executeUpdate() != 1)
{
_log.warning("Error while updating karma & pkkills for userId " + _playerId);
}
}
catch (Exception e)
{
_log.log(Level.WARNING, "Could not delete : " + e.getMessage(), e);
}
}
}
else
{
// either this cursed weapon is in the inventory of someone who has another cursed weapon equipped,
// OR this cursed weapon is on the ground.
if ((_player != null) && (_player.getInventory().getItemByItemId(_itemId) != null))
{
// Destroy
final L2ItemInstance removedItem = _player.getInventory().destroyItemByItemId("", _itemId, 1, _player, null);
if (!Config.FORCE_INVENTORY_UPDATE)
{
final InventoryUpdate iu = new InventoryUpdate();
if (removedItem.getCount() == 0)
{
iu.addRemovedItem(removedItem);
}
else
{
iu.addModifiedItem(removedItem);
}
_player.sendInventoryUpdate(iu);
}
else
{
_player.sendItemList(false);
}
_player.broadcastUserInfo();
}
// is dropped on the ground
else if (_item != null)
{
_item.decayMe();
L2World.getInstance().removeObject(_item);
_log.info(_name + " item has been removed from World.");
}
}
// Delete infos from table if any
CursedWeaponsManager.removeFromDb(_itemId);
final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.S1_HAS_DISAPPEARED);
sm.addItemName(_itemId);
CursedWeaponsManager.announce(sm);
// Reset state
cancelTask();
_isActivated = false;
_isDropped = false;
_endTime = 0;
_player = null;
_playerId = 0;
_playerReputation = 0;
_playerPkKills = 0;
_item = null;
_nbKills = 0;
}
private void cancelTask()
{
if (_removeTask != null)
{
_removeTask.cancel(true);
_removeTask = null;
}
}
private class RemoveTask implements Runnable
{
protected RemoveTask()
{
}
@Override
public void run()
{
if (System.currentTimeMillis() >= getEndTime())
{
endOfLife();
}
}
}
private void dropIt(L2Attackable attackable, L2PcInstance player)
{
dropIt(attackable, player, null, true);
}
private void dropIt(L2Attackable attackable, L2PcInstance player, L2Character killer, boolean fromMonster)
{
_isActivated = false;
if (fromMonster)
{
_item = attackable.dropItem(player, _itemId, 1);
_item.setDropTime(0); // Prevent item from being removed by ItemsAutoDestroy
// RedSky and Earthquake
final ExRedSky packet = new ExRedSky(10);
final Earthquake eq = new Earthquake(player.getX(), player.getY(), player.getZ(), 14, 3);
Broadcast.toAllOnlinePlayers(packet);
Broadcast.toAllOnlinePlayers(eq);
}
else
{
_item = _player.getInventory().getItemByItemId(_itemId);
_player.dropItem("DieDrop", _item, killer, true);
_player.setReputation(_playerReputation);
_player.setPkKills(_playerPkKills);
_player.setCursedWeaponEquippedId(0);
removeSkill();
_player.abortAttack();
// L2ItemInstance item = _player.getInventory().getItemByItemId(_itemId);
// _player.getInventory().dropItem("DieDrop", item, _player, null);
// _player.getInventory().getItemByItemId(_itemId).dropMe(_player, _player.getX(), _player.getY(), _player.getZ());
}
_isDropped = true;
final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.S2_WAS_DROPPED_IN_THE_S1_REGION);
if (player != null)
{
sm.addZoneName(player.getX(), player.getY(), player.getZ()); // Region Name
}
else if (_player != null)
{
sm.addZoneName(_player.getX(), _player.getY(), _player.getZ()); // Region Name
}
else
{
sm.addZoneName(killer.getX(), killer.getY(), killer.getZ()); // Region Name
}
sm.addItemName(_itemId);
CursedWeaponsManager.announce(sm); // in the Hot Spring region
}
public void cursedOnLogin()
{
doTransform();
giveSkill();
final SystemMessage msg = SystemMessage.getSystemMessage(SystemMessageId.S2_S_OWNER_HAS_LOGGED_INTO_THE_S1_REGION);
msg.addZoneName(_player.getX(), _player.getY(), _player.getZ());
msg.addItemName(_player.getCursedWeaponEquippedId());
CursedWeaponsManager.announce(msg);
final CursedWeapon cw = CursedWeaponsManager.getInstance().getCursedWeapon(_player.getCursedWeaponEquippedId());
final SystemMessage msg2 = SystemMessage.getSystemMessage(SystemMessageId.S1_HAS_S2_MINUTE_S_OF_USAGE_TIME_REMAINING);
final int timeLeft = (int) (cw.getTimeLeft() / 60000);
msg2.addItemName(_player.getCursedWeaponEquippedId());
msg2.addInt(timeLeft);
_player.sendPacket(msg2);
}
/**
* Yesod:<br>
* Rebind the passive skill belonging to the CursedWeapon. Invoke this method if the weapon owner switches to a subclass.
*/
public void giveSkill()
{
int level = 1 + (_nbKills / _stageKills);
if (level > _skillMaxLevel)
{
level = _skillMaxLevel;
}
final Skill skill = SkillData.getInstance().getSkill(_skillId, level);
_player.addSkill(skill, false);
// Void Burst, Void Flow
_player.addTransformSkill(CommonSkill.VOID_BURST.getSkill());
_player.addTransformSkill(CommonSkill.VOID_FLOW.getSkill());
_player.sendSkillList();
}
public void doTransform()
{
if (_itemId == 8689)
{
transformationId = 302;
}
else if (_itemId == 8190)
{
transformationId = 301;
}
if (_player.isTransformed())
{
_player.stopTransformation(true);
ThreadPoolManager.getInstance().scheduleGeneral(() -> _player.transform(transformationId, true), 500);
}
else
{
_player.transform(transformationId, true);
}
}
public void removeSkill()
{
_player.removeSkill(_skillId);
_player.untransform();
_player.sendSkillList();
}
public void reActivate()
{
_isActivated = true;
if ((_endTime - System.currentTimeMillis()) <= 0)
{
endOfLife();
}
else
{
_removeTask = ThreadPoolManager.getInstance().scheduleGeneralAtFixedRate(new RemoveTask(), _durationLost * 12000L, _durationLost * 12000L);
}
}
public boolean checkDrop(L2Attackable attackable, L2PcInstance player)
{
if (Rnd.get(100000) < _dropRate)
{
// Drop the item
dropIt(attackable, player);
// Start the Life Task
_endTime = System.currentTimeMillis() + (_duration * 60000L);
_removeTask = ThreadPoolManager.getInstance().scheduleGeneralAtFixedRate(new RemoveTask(), _durationLost * 12000L, _durationLost * 12000L);
return true;
}
return false;
}
public void activate(L2PcInstance player, L2ItemInstance item)
{
// If the player is mounted, attempt to unmount first.
// Only allow picking up the cursed weapon if unmounting is successful.
if (player.isMounted() && !player.dismount())
{
// TODO: Verify the following system message, may still be custom.
player.sendPacket(SystemMessageId.YOU_HAVE_FAILED_TO_PICK_UP_S1);
player.dropItem("InvDrop", item, null, true);
return;
}
_isActivated = true;
// Player holding it data
_player = player;
_playerId = _player.getObjectId();
_playerReputation = _player.getReputation();
_playerPkKills = _player.getPkKills();
saveData();
// Change player stats
_player.setCursedWeaponEquippedId(_itemId);
_player.setReputation(-9999999);
_player.setPkKills(0);
if (_player.isInParty())
{
_player.getParty().removePartyMember(_player, MessageType.EXPELLED);
}
// Disable All Skills
// Do Transform
doTransform();
// Add skill
giveSkill();
// Equip with the weapon
_item = item;
// L2ItemInstance[] items =
_player.getInventory().equipItem(_item);
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.YOU_HAVE_EQUIPPED_YOUR_S1);
sm.addItemName(_item);
_player.sendPacket(sm);
// Fully heal player
_player.setCurrentHpMp(_player.getMaxHp(), _player.getMaxMp());
_player.setCurrentCp(_player.getMaxCp());
// Refresh inventory
if (!Config.FORCE_INVENTORY_UPDATE)
{
final InventoryUpdate iu = new InventoryUpdate();
iu.addItem(_item);
_player.sendInventoryUpdate(iu);
}
else
{
_player.sendItemList(false);
}
// Refresh player stats
_player.broadcastUserInfo();
final SocialAction atk = new SocialAction(_player.getObjectId(), 17);
_player.broadcastPacket(atk);
sm = SystemMessage.getSystemMessage(SystemMessageId.THE_OWNER_OF_S2_HAS_APPEARED_IN_THE_S1_REGION);
sm.addZoneName(_player.getX(), _player.getY(), _player.getZ()); // Region Name
sm.addItemName(_item);
CursedWeaponsManager.announce(sm);
}
public void saveData()
{
if (Config.DEBUG)
{
_log.info("CursedWeapon: Saving data to disk.");
}
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement del = con.prepareStatement("DELETE FROM cursed_weapons WHERE itemId = ?");
PreparedStatement ps = con.prepareStatement("INSERT INTO cursed_weapons (itemId, charId, playerReputation, playerPkKills, nbKills, endTime) VALUES (?, ?, ?, ?, ?, ?)"))
{
// Delete previous datas
del.setInt(1, _itemId);
del.executeUpdate();
if (_isActivated)
{
ps.setInt(1, _itemId);
ps.setInt(2, _playerId);
ps.setInt(3, _playerReputation);
ps.setInt(4, _playerPkKills);
ps.setInt(5, _nbKills);
ps.setLong(6, _endTime);
ps.executeUpdate();
}
}
catch (SQLException e)
{
_log.log(Level.SEVERE, "CursedWeapon: Failed to save data.", e);
}
}
public void dropIt(L2Character killer)
{
if (Rnd.get(100) <= _disapearChance)
{
// Remove it
endOfLife();
}
else
{
// Unequip & Drop
dropIt(null, null, killer, false);
// Reset player stats
_player.setReputation(_playerReputation);
_player.setPkKills(_playerPkKills);
_player.setCursedWeaponEquippedId(0);
removeSkill();
_player.abortAttack();
_player.broadcastUserInfo();
}
}
public void increaseKills()
{
_nbKills++;
if ((_player != null) && _player.isOnline())
{
_player.setPkKills(_nbKills);
_player.sendPacket(new UserInfo(_player));
if (((_nbKills % _stageKills) == 0) && (_nbKills <= (_stageKills * (_skillMaxLevel - 1))))
{
giveSkill();
}
}
// Reduce time-to-live
_endTime -= _durationLost * 60000L;
saveData();
}
public void setDisapearChance(int disapearChance)
{
_disapearChance = disapearChance;
}
public void setDropRate(int dropRate)
{
_dropRate = dropRate;
}
public void setDuration(int duration)
{
_duration = duration;
}
public void setDurationLost(int durationLost)
{
_durationLost = durationLost;
}
public void setStageKills(int stageKills)
{
_stageKills = stageKills;
}
public void setNbKills(int nbKills)
{
_nbKills = nbKills;
}
public void setPlayerId(int playerId)
{
_playerId = playerId;
}
public void setPlayerReputation(int playerReputation)
{
_playerReputation = playerReputation;
}
public void setPlayerPkKills(int playerPkKills)
{
_playerPkKills = playerPkKills;
}
public void setActivated(boolean isActivated)
{
_isActivated = isActivated;
}
public void setDropped(boolean isDropped)
{
_isDropped = isDropped;
}
public void setEndTime(long endTime)
{
_endTime = endTime;
}
public void setPlayer(L2PcInstance player)
{
_player = player;
}
public void setItem(L2ItemInstance item)
{
_item = item;
}
public boolean isActivated()
{
return _isActivated;
}
public boolean isDropped()
{
return _isDropped;
}
public long getEndTime()
{
return _endTime;
}
@Override
public String getName()
{
return _name;
}
public int getItemId()
{
return _itemId;
}
public int getSkillId()
{
return _skillId;
}
public int getPlayerId()
{
return _playerId;
}
public L2PcInstance getPlayer()
{
return _player;
}
public int getPlayerReputation()
{
return _playerReputation;
}
public int getPlayerPkKills()
{
return _playerPkKills;
}
public int getNbKills()
{
return _nbKills;
}
public int getStageKills()
{
return _stageKills;
}
public boolean isActive()
{
return _isActivated || _isDropped;
}
public int getLevel()
{
if (_nbKills > (_stageKills * _skillMaxLevel))
{
return _skillMaxLevel;
}
return (_nbKills / _stageKills);
}
public long getTimeLeft()
{
return _endTime - System.currentTimeMillis();
}
public void goTo(L2PcInstance player)
{
if (player == null)
{
return;
}
if (_isActivated && (_player != null))
{
// Go to player holding the weapon
player.teleToLocation(_player.getLocation(), true);
}
else if (_isDropped && (_item != null))
{
// Go to item on the ground
player.teleToLocation(_item.getLocation(), true);
}
else
{
player.sendMessage(_name + " isn't in the World.");
}
}
public Location getWorldPosition()
{
if (_isActivated && (_player != null))
{
return _player.getLocation();
}
if (_isDropped && (_item != null))
{
return _item.getLocation();
}
return null;
}
public long getDuration()
{
return _duration;
}
}

View File

@@ -0,0 +1,122 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.List;
import java.util.function.Function;
import com.l2jmobius.gameserver.enums.DailyMissionStatus;
import com.l2jmobius.gameserver.handler.AbstractDailyMissionHandler;
import com.l2jmobius.gameserver.handler.DailyMissionHandler;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.base.ClassId;
import com.l2jmobius.gameserver.model.holders.ItemHolder;
/**
* @author Sdw
*/
public class DailyMissionDataHolder
{
private final int _id;
private final int _rewardId;
private final List<ItemHolder> _rewardsItems;
private final List<ClassId> _classRestriction;
private final int _requiredCompletions;
private final StatsSet _params;
private final boolean _isOneTime;
private final AbstractDailyMissionHandler _handler;
public DailyMissionDataHolder(StatsSet set)
{
final Function<DailyMissionDataHolder, AbstractDailyMissionHandler> handler = DailyMissionHandler.getInstance().getHandler(set.getString("handler"));
_id = set.getInt("id");
_rewardId = set.getInt("reward_id");
_requiredCompletions = set.getInt("requiredCompletion", 0);
_rewardsItems = set.getList("items", ItemHolder.class);
_classRestriction = set.getList("classRestriction", ClassId.class);
_params = set.getObject("params", StatsSet.class);
_isOneTime = set.getBoolean("isOneTime", true);
_handler = handler != null ? handler.apply(this) : null;
}
public int getId()
{
return _id;
}
public int getRewardId()
{
return _rewardId;
}
public List<ClassId> getClassRestriction()
{
return _classRestriction;
}
public List<ItemHolder> getRewards()
{
return _rewardsItems;
}
public int getRequiredCompletions()
{
return _requiredCompletions;
}
public StatsSet getParams()
{
return _params;
}
public boolean isOneTime()
{
return _isOneTime;
}
public boolean isDisplayable(L2PcInstance player)
{
return (!_isOneTime || (getStatus(player) != DailyMissionStatus.COMPLETED.getClientId())) && (_classRestriction.isEmpty() || _classRestriction.contains(player.getClassId()));
}
public void requestReward(L2PcInstance player)
{
if ((_handler != null) && isDisplayable(player))
{
_handler.requestReward(player);
}
}
public int getStatus(L2PcInstance player)
{
return _handler != null ? _handler.getStatus(player) : DailyMissionStatus.NOT_AVAILABLE.getClientId();
}
public int getProgress(L2PcInstance player)
{
return _handler != null ? _handler.getProgress(player) : DailyMissionStatus.NOT_AVAILABLE.getClientId();
}
public void reset()
{
if (_handler != null)
{
_handler.reset();
}
}
}

View File

@@ -0,0 +1,91 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.enums.DailyMissionStatus;
/**
* @author UnAfraid
*/
public class DailyMissionPlayerEntry
{
private final int _objectId;
private final int _rewardId;
private DailyMissionStatus _status = DailyMissionStatus.NOT_AVAILABLE;
private int _progress;
private long _lastCompleted;
public DailyMissionPlayerEntry(int objectId, int rewardId)
{
_objectId = objectId;
_rewardId = rewardId;
}
public DailyMissionPlayerEntry(int objectId, int rewardId, int status, int progress, long lastCompleted)
{
this(objectId, rewardId);
_status = DailyMissionStatus.valueOf(status);
_progress = progress;
_lastCompleted = lastCompleted;
}
public int getObjectId()
{
return _objectId;
}
public int getRewardId()
{
return _rewardId;
}
public DailyMissionStatus getStatus()
{
return _status;
}
public void setStatus(DailyMissionStatus status)
{
_status = status;
}
public int getProgress()
{
return _progress;
}
public void setProgress(int progress)
{
_progress = progress;
}
public int increaseProgress()
{
_progress++;
return _progress;
}
public long getLastCompleted()
{
return _lastCompleted;
}
public void setLastCompleted(long lastCompleted)
{
_lastCompleted = lastCompleted;
}
}

View File

@@ -0,0 +1,70 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
/**
* @author xban1x
*/
public final class DamageDoneInfo
{
private final L2PcInstance _attacker;
private int _damage = 0;
public DamageDoneInfo(L2PcInstance attacker)
{
_attacker = attacker;
}
public L2PcInstance getAttacker()
{
return _attacker;
}
public void addDamage(int damage)
{
_damage += damage;
}
public int getDamage()
{
return _damage;
}
@Override
public final boolean equals(Object obj)
{
if (this == obj)
{
return true;
}
if (obj instanceof DamageDoneInfo)
{
return (((DamageDoneInfo) obj).getAttacker() == _attacker);
}
return false;
}
@Override
public final int hashCode()
{
return _attacker.getObjectId();
}
}

View File

@@ -0,0 +1,108 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.concurrent.ScheduledFuture;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.actor.instance.L2PetInstance;
/**
* @author DrHouse
*/
public class DropProtection implements Runnable
{
private volatile boolean _isProtected = false;
private L2PcInstance _owner = null;
private ScheduledFuture<?> _task = null;
private static final long PROTECTED_MILLIS_TIME = 15000;
@Override
public synchronized void run()
{
_isProtected = false;
_owner = null;
_task = null;
}
public boolean isProtected()
{
return _isProtected;
}
public L2PcInstance getOwner()
{
return _owner;
}
public synchronized boolean tryPickUp(L2PcInstance actor)
{
if (!_isProtected)
{
return true;
}
if (_owner == actor)
{
return true;
}
if ((_owner.getParty() != null) && (_owner.getParty() == actor.getParty()))
{
return true;
}
/*
* if (_owner.getClan() != null && _owner.getClan() == actor.getClan()) return true;
*/
return false;
}
public boolean tryPickUp(L2PetInstance pet)
{
return tryPickUp(pet.getOwner());
}
public synchronized void unprotect()
{
if (_task != null)
{
_task.cancel(false);
}
_isProtected = false;
_owner = null;
_task = null;
}
public synchronized void protect(L2PcInstance player)
{
unprotect();
_isProtected = true;
_owner = player;
if (_owner == null)
{
throw new NullPointerException("Trying to protect dropped item to null owner");
}
_task = ThreadPoolManager.getInstance().scheduleGeneral(this, PROTECTED_MILLIS_TIME);
}
}

View File

@@ -0,0 +1,174 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.HashMap;
import java.util.Map;
public final class Elementals
{
private static final Map<Integer, ElementalItems> TABLE = new HashMap<>();
static
{
for (ElementalItems item : ElementalItems.values())
{
TABLE.put(item._itemId, item);
}
}
protected static final byte NONE = -1;
protected static final byte FIRE = 0;
protected static final byte WATER = 1;
protected static final byte WIND = 2;
protected static final byte EARTH = 3;
protected static final byte HOLY = 4;
protected static final byte DARK = 5;
public static final int FIRST_WEAPON_BONUS = 20;
public static final int NEXT_WEAPON_BONUS = 5;
public static final int ARMOR_BONUS = 6;
public static final int[] WEAPON_VALUES =
{
0, // Level 1
25, // Level 2
75, // Level 3
150, // Level 4
175, // Level 5
225, // Level 6
300, // Level 7
325, // Level 8
375, // Level 9
450, // Level 10
475, // Level 11
525, // Level 12
600, // Level 13
Integer.MAX_VALUE
// TODO: Higher stones
};
public static final int[] ARMOR_VALUES =
{
0, // Level 1
12, // Level 2
30, // Level 3
60, // Level 4
72, // Level 5
90, // Level 6
120, // Level 7
132, // Level 8
150, // Level 9
180, // Level 10
192, // Level 11
210, // Level 12
240, // Level 13
Integer.MAX_VALUE
// TODO: Higher stones
};
public enum ElementalItemType
{
Stone(3),
Roughore(3),
Crystal(6),
Jewel(9),
Energy(12);
public int _maxLevel;
ElementalItemType(int maxLvl)
{
_maxLevel = maxLvl;
}
}
public enum ElementalItems
{
fireStone(FIRE, 9546, ElementalItemType.Stone),
waterStone(WATER, 9547, ElementalItemType.Stone),
windStone(WIND, 9549, ElementalItemType.Stone),
earthStone(EARTH, 9548, ElementalItemType.Stone),
divineStone(HOLY, 9551, ElementalItemType.Stone),
darkStone(DARK, 9550, ElementalItemType.Stone),
fireRoughtore(FIRE, 10521, ElementalItemType.Roughore),
waterRoughtore(WATER, 10522, ElementalItemType.Roughore),
windRoughtore(WIND, 10524, ElementalItemType.Roughore),
earthRoughtore(EARTH, 10523, ElementalItemType.Roughore),
divineRoughtore(HOLY, 10526, ElementalItemType.Roughore),
darkRoughtore(DARK, 10525, ElementalItemType.Roughore),
fireCrystal(FIRE, 9552, ElementalItemType.Crystal),
waterCrystal(WATER, 9553, ElementalItemType.Crystal),
windCrystal(WIND, 9555, ElementalItemType.Crystal),
earthCrystal(EARTH, 9554, ElementalItemType.Crystal),
divineCrystal(HOLY, 9557, ElementalItemType.Crystal),
darkCrystal(DARK, 9556, ElementalItemType.Crystal),
fireJewel(FIRE, 9558, ElementalItemType.Jewel),
waterJewel(WATER, 9559, ElementalItemType.Jewel),
windJewel(WIND, 9561, ElementalItemType.Jewel),
earthJewel(EARTH, 9560, ElementalItemType.Jewel),
divineJewel(HOLY, 9563, ElementalItemType.Jewel),
darkJewel(DARK, 9562, ElementalItemType.Jewel),
// not yet supported by client (Freya pts)
fireEnergy(FIRE, 9564, ElementalItemType.Energy),
waterEnergy(WATER, 9565, ElementalItemType.Energy),
windEnergy(WIND, 9567, ElementalItemType.Energy),
earthEnergy(EARTH, 9566, ElementalItemType.Energy),
divineEnergy(HOLY, 9569, ElementalItemType.Energy),
darkEnergy(DARK, 9568, ElementalItemType.Energy);
public byte _element;
public int _itemId;
public ElementalItemType _type;
ElementalItems(byte element, int itemId, ElementalItemType type)
{
_element = element;
_itemId = itemId;
_type = type;
}
}
public static byte getItemElement(int itemId)
{
final ElementalItems item = TABLE.get(itemId);
if (item != null)
{
return item._element;
}
return NONE;
}
public static ElementalItems getItemElemental(int itemId)
{
return TABLE.get(itemId);
}
public static int getMaxElementLevel(int itemId)
{
final ElementalItems item = TABLE.get(itemId);
if (item != null)
{
return item._type._maxLevel;
}
return -1;
}
}

View File

@@ -0,0 +1,443 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.concurrent.ScheduledFuture;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.Config;
import com.l2jmobius.commons.util.Rnd;
import com.l2jmobius.gameserver.GeoData;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.data.xml.impl.FishingData;
import com.l2jmobius.gameserver.enums.ShotType;
import com.l2jmobius.gameserver.instancemanager.ZoneManager;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.events.EventDispatcher;
import com.l2jmobius.gameserver.model.events.impl.character.player.OnPlayerFishing;
import com.l2jmobius.gameserver.model.interfaces.ILocational;
import com.l2jmobius.gameserver.model.itemcontainer.Inventory;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
import com.l2jmobius.gameserver.model.items.type.WeaponType;
import com.l2jmobius.gameserver.model.zone.L2ZoneType;
import com.l2jmobius.gameserver.model.zone.ZoneId;
import com.l2jmobius.gameserver.model.zone.type.L2FishingZone;
import com.l2jmobius.gameserver.model.zone.type.L2WaterZone;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.ActionFailed;
import com.l2jmobius.gameserver.network.serverpackets.PlaySound;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
import com.l2jmobius.gameserver.network.serverpackets.fishing.ExFishingEnd;
import com.l2jmobius.gameserver.network.serverpackets.fishing.ExFishingEnd.FishingEndReason;
import com.l2jmobius.gameserver.network.serverpackets.fishing.ExFishingEnd.FishingEndType;
import com.l2jmobius.gameserver.network.serverpackets.fishing.ExFishingStart;
import com.l2jmobius.gameserver.network.serverpackets.fishing.ExUserInfoFishing;
import com.l2jmobius.gameserver.util.Util;
/**
* @author bit
*/
public class Fishing
{
protected static final Logger LOGGER = Logger.getLogger(Fishing.class.getName());
private volatile ILocational _baitLocation = new Location(0, 0, 0);
private final L2PcInstance _player;
private ScheduledFuture<?> _reelInTask;
private ScheduledFuture<?> _startFishingTask;
private boolean _isFishing = false;
public Fishing(L2PcInstance player)
{
_player = player;
}
public synchronized boolean isFishing()
{
return _isFishing;
}
public boolean isAtValidLocation()
{
// TODO: implement checking direction
// if (calculateBaitLocation() == null)
// {
// return false;
// }
return _player.isInsideZone(ZoneId.FISHING);
}
public boolean canFish()
{
return !_player.isDead() && !_player.isAlikeDead() && !_player.hasBlockActions() && !_player.isSitting();
}
private FishingBaitData getCurrentBaitData()
{
final L2ItemInstance bait = _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_LHAND);
return bait != null ? FishingData.getInstance().getBaitData(bait.getId()) : null;
}
private void cancelTasks()
{
if (_reelInTask != null)
{
_reelInTask.cancel(false);
_reelInTask = null;
}
if (_startFishingTask != null)
{
_startFishingTask.cancel(false);
_startFishingTask = null;
}
}
public synchronized void startFishing()
{
if (isFishing())
{
return;
}
_isFishing = true;
castLine();
}
private void castLine()
{
if (!Config.ALLOW_FISHING && !_player.canOverrideCond(PcCondOverride.ZONE_CONDITIONS))
{
_player.sendMessage("Fishing is disabled.");
_player.sendPacket(ActionFailed.STATIC_PACKET);
stopFishing(FishingEndType.ERROR);
return;
}
cancelTasks();
if (!canFish())
{
if (isFishing())
{
_player.sendPacket(SystemMessageId.YOUR_ATTEMPT_AT_FISHING_HAS_BEEN_CANCELLED);
}
stopFishing(FishingEndType.ERROR);
return;
}
final FishingBaitData baitData = getCurrentBaitData();
final int minPlayerLevel = baitData == null ? 85 : baitData.getMinPlayerLevel();
if (_player.getLevel() < minPlayerLevel)
{
if (minPlayerLevel == 85)
{
_player.sendPacket(SystemMessageId.FISHING_IS_AVAILABLE_TO_CHARACTERS_LV_85_OR_ABOVE);
}
else // In case of custom fishing level.
{
_player.sendPacket(SystemMessageId.YOU_DO_NOT_MEET_THE_FISHING_LEVEL_REQUIREMENTS);
}
_player.sendPacket(ActionFailed.STATIC_PACKET);
stopFishing(FishingEndType.ERROR);
return;
}
final L2ItemInstance rod = _player.getActiveWeaponInstance();
if ((rod == null) || (rod.getItemType() != WeaponType.FISHINGROD))
{
_player.sendPacket(SystemMessageId.YOU_DO_NOT_HAVE_A_FISHING_POLE_EQUIPPED);
_player.sendPacket(ActionFailed.STATIC_PACKET);
stopFishing(FishingEndType.ERROR);
return;
}
if (baitData == null)
{
_player.sendPacket(SystemMessageId.YOU_MUST_PUT_BAIT_ON_YOUR_HOOK_BEFORE_YOU_CAN_FISH);
_player.sendPacket(ActionFailed.STATIC_PACKET);
stopFishing(FishingEndType.ERROR);
return;
}
if (_player.isTransformed() || _player.isInBoat())
{
_player.sendPacket(SystemMessageId.YOU_CANNOT_FISH_WHEN_TRANSFORMED_OR_WHILE_RIDING_AS_A_PASSENGER_OF_A_BOAT_IT_S_AGAINST_THE_RULES);
_player.sendPacket(ActionFailed.STATIC_PACKET);
stopFishing(FishingEndType.ERROR);
return;
}
if (_player.isInCraftMode() || _player.isInStoreMode())
{
_player.sendPacket(SystemMessageId.YOU_CANNOT_FISH_WHILE_USING_A_RECIPE_BOOK_PRIVATE_WORKSHOP_OR_PRIVATE_STORE);
_player.sendPacket(ActionFailed.STATIC_PACKET);
stopFishing(FishingEndType.ERROR);
return;
}
if (_player.isInsideZone(ZoneId.WATER) || _player.isInWater())
{
_player.sendPacket(SystemMessageId.YOU_CANNOT_FISH_WHILE_UNDER_WATER);
_player.sendPacket(ActionFailed.STATIC_PACKET);
stopFishing(FishingEndType.ERROR);
return;
}
_baitLocation = calculateBaitLocation();
if (!_player.isInsideZone(ZoneId.FISHING) || (_baitLocation == null))
{
if (isFishing())
{
// _player.sendPacket(SystemMessageId.YOUR_ATTEMPT_AT_FISHING_HAS_BEEN_CANCELLED);
_player.sendPacket(ActionFailed.STATIC_PACKET);
}
else
{
_player.sendPacket(SystemMessageId.YOU_CAN_T_FISH_HERE);
_player.sendPacket(ActionFailed.STATIC_PACKET);
}
stopFishing(FishingEndType.ERROR);
return;
}
if (!_player.isChargedShot(ShotType.FISH_SOULSHOTS))
{
_player.rechargeShots(false, false, true);
}
_reelInTask = ThreadPoolManager.getInstance().scheduleGeneral(() ->
{
_player.getFishing().reelInWithReward();
_startFishingTask = ThreadPoolManager.getInstance().scheduleGeneral(() -> _player.getFishing().castLine(), Rnd.get(baitData.getWaitMin(), baitData.getWaitMax()));
}, Rnd.get(baitData.getTimeMin(), baitData.getTimeMax()));
_player.stopMove(null);
_player.broadcastPacket(new ExFishingStart(_player, -1, baitData.getLevel(), _baitLocation));
_player.sendPacket(new ExUserInfoFishing(_player, true, _baitLocation));
_player.sendPacket(new PlaySound("SF_P_01"));
_player.sendPacket(SystemMessageId.YOU_CAST_YOUR_LINE_AND_START_TO_FISH);
}
public void reelInWithReward()
{
// Fish may or may not eat the hook. If it does - it consumes fishing bait and fishing shot.
// Then player may or may not catch the fish. Using fishing shots increases chance to win.
final FishingBaitData baitData = getCurrentBaitData();
if (baitData == null)
{
reelIn(FishingEndReason.LOSE, false);
LOGGER.warning("Player " + _player + " is fishing with unhandled bait: " + _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_LHAND));
return;
}
double chance = baitData.getChance();
if (_player.isChargedShot(ShotType.FISH_SOULSHOTS))
{
chance *= 1.25; // +25 % chance to win
_player.setChargedShot(ShotType.FISH_SOULSHOTS, false);
}
if (Rnd.get(0, 100) <= chance)
{
reelIn(FishingEndReason.WIN, true);
}
else
{
reelIn(FishingEndReason.LOSE, true);
}
}
private void reelIn(FishingEndReason reason, boolean consumeBait)
{
if (!isFishing())
{
return;
}
cancelTasks();
try
{
final L2ItemInstance bait = _player.getInventory().getPaperdollItem(Inventory.PAPERDOLL_LHAND);
if (consumeBait)
{
if ((bait == null) || !_player.getInventory().updateItemCount(null, bait, -1, _player, null))
{
reason = FishingEndReason.LOSE; // no bait - no reward
return;
}
}
if ((reason == FishingEndReason.WIN) && (bait != null))
{
final FishingBaitData baitData = FishingData.getInstance().getBaitData(bait.getId());
final int numRewards = baitData.getRewards().size();
if (numRewards > 0)
{
// TODO: verify, totally guessed
final FishingData fishingData = FishingData.getInstance();
final int lvlModifier = _player.getLevel() * _player.getLevel();
_player.addExpAndSp(Rnd.get(fishingData.getExpRateMin(), fishingData.getExpRateMax()) * lvlModifier, Rnd.get(fishingData.getSpRateMin(), fishingData.getSpRateMax()) * lvlModifier, true);
final int fishId = baitData.getRewards().get(Rnd.get(0, numRewards - 1));
_player.getInventory().addItem("Fishing Reward", fishId, 1, _player, null);
final SystemMessage msg = SystemMessage.getSystemMessage(SystemMessageId.YOU_HAVE_EARNED_S1);
msg.addItemName(fishId);
_player.sendPacket(msg);
}
else
{
LOGGER.log(Level.WARNING, "Could not find fishing rewards for bait ", bait.getId());
}
}
else if (reason == FishingEndReason.LOSE)
{
_player.sendPacket(SystemMessageId.THE_BAIT_HAS_BEEN_LOST_BECAUSE_THE_FISH_GOT_AWAY);
}
if (consumeBait)
{
EventDispatcher.getInstance().notifyEventAsync(new OnPlayerFishing(_player, reason), _player);
}
}
finally
{
_player.broadcastPacket(new ExFishingEnd(_player, reason));
_player.sendPacket(new ExUserInfoFishing(_player, false));
}
}
public void stopFishing()
{
stopFishing(FishingEndType.PLAYER_STOP);
}
public synchronized void stopFishing(FishingEndType endType)
{
if (isFishing())
{
reelIn(FishingEndReason.STOP, false);
_isFishing = false;
switch (endType)
{
case PLAYER_STOP:
{
_player.sendPacket(SystemMessageId.YOU_REEL_YOUR_LINE_IN_AND_STOP_FISHING);
break;
}
case PLAYER_CANCEL:
{
_player.sendPacket(SystemMessageId.YOUR_ATTEMPT_AT_FISHING_HAS_BEEN_CANCELLED);
break;
}
}
}
}
public ILocational getBaitLocation()
{
return _baitLocation;
}
private Location calculateBaitLocation()
{
// calculate a position in front of the player with a random distance
final int distMin = FishingData.getInstance().getBaitDistanceMin();
final int distMax = FishingData.getInstance().getBaitDistanceMax();
int distance = Rnd.get(distMin, distMax);
final double angle = Util.convertHeadingToDegree(_player.getHeading());
final double radian = Math.toRadians(angle);
final double sin = Math.sin(radian);
final double cos = Math.cos(radian);
int baitX = (int) (_player.getX() + (cos * distance));
int baitY = (int) (_player.getY() + (sin * distance));
// search for fishing zone
L2FishingZone fishingZone = null;
for (L2ZoneType zone : ZoneManager.getInstance().getZones(_player))
{
if (zone instanceof L2FishingZone)
{
fishingZone = (L2FishingZone) zone;
break;
}
}
// search for water zone
L2WaterZone waterZone = null;
for (L2ZoneType zone : ZoneManager.getInstance().getZones(baitX, baitY))
{
if (zone instanceof L2WaterZone)
{
waterZone = (L2WaterZone) zone;
break;
}
}
int baitZ = computeBaitZ(_player, baitX, baitY, fishingZone, waterZone);
if (baitZ == Integer.MIN_VALUE)
{
_player.sendPacket(SystemMessageId.YOU_CAN_T_FISH_HERE);
return null;
}
return new Location(baitX, baitY, baitZ);
}
/**
* Computes the Z of the bait.
* @param player the player
* @param baitX the bait x
* @param baitY the bait y
* @param fishingZone the fishing zone
* @param waterZone the water zone
* @return the bait z or {@link Integer#MIN_VALUE} when you cannot fish here
*/
private static int computeBaitZ(L2PcInstance player, int baitX, int baitY, L2FishingZone fishingZone, L2WaterZone waterZone)
{
if ((fishingZone == null))
{
return Integer.MIN_VALUE;
}
if ((waterZone == null))
{
return Integer.MIN_VALUE;
}
// always use water zone, fishing zone high z is high in the air...
final int baitZ = waterZone.getWaterZ();
// if (!GeoData.getInstance().canSeeTarget(player.getX(), player.getY(), player.getZ(), baitX, baitY, baitZ))
//
// return Integer.MIN_VALUE;
// }
if (GeoData.getInstance().hasGeo(baitX, baitY))
{
if (GeoData.getInstance().getHeight(baitX, baitY, baitZ) > baitZ)
{
return Integer.MIN_VALUE;
}
if (GeoData.getInstance().getHeight(baitX, baitY, player.getZ()) > baitZ)
{
return Integer.MIN_VALUE;
}
}
return baitZ;
}
}

View File

@@ -0,0 +1,98 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.List;
/**
* @author bit
*/
public class FishingBaitData
{
private final int _itemId;
private final int _level;
private final int _minPlayerLevel;
private final double _chance;
private final int _timeMin;
private final int _timeMax;
private final int _waitMin;
private final int _waitMax;
private final List<Integer> _rewards = new ArrayList<>();
public FishingBaitData(int itemId, int level, int minPlayerLevel, double chance, int timeMin, int timeMax, int waitMin, int waitMax)
{
_itemId = itemId;
_level = level;
_minPlayerLevel = minPlayerLevel;
_chance = chance;
_timeMin = timeMin;
_timeMax = timeMax;
_waitMin = waitMin;
_waitMax = waitMax;
}
public int getItemId()
{
return _itemId;
}
public int getLevel()
{
return _level;
}
public int getMinPlayerLevel()
{
return _minPlayerLevel;
}
public double getChance()
{
return _chance;
}
public int getTimeMin()
{
return _timeMin;
}
public int getTimeMax()
{
return _timeMax;
}
public int getWaitMin()
{
return _waitMin;
}
public int getWaitMax()
{
return _waitMax;
}
public List<Integer> getRewards()
{
return _rewards;
}
public void addReward(int itemId)
{
_rewards.add(itemId);
}
}

View File

@@ -0,0 +1,58 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.interfaces.IIdentifiable;
/**
* Fort Siege Spawn.
* @author xban1x
*/
public final class FortSiegeSpawn extends Location implements IIdentifiable
{
private final int _npcId;
private final int _fortId;
private final int _id;
public FortSiegeSpawn(int fort_id, int x, int y, int z, int heading, int npc_id, int id)
{
super(x, y, z, heading);
_fortId = fort_id;
_npcId = npc_id;
_id = id;
}
public int getFortId()
{
return _fortId;
}
/**
* Gets the NPC ID.
* @return the NPC ID
*/
@Override
public int getId()
{
return _npcId;
}
public int getMessageId()
{
return _id;
}
}

View File

@@ -0,0 +1,84 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.enums.AttackType;
import com.l2jmobius.gameserver.model.actor.L2Character;
/**
* @author UnAfraid
*/
public class Hit
{
private final int _targetId;
private final int _damage;
private final int _ssGrade;
private int _flags = 0;
public Hit(L2Object target, int damage, boolean miss, boolean crit, byte shld, boolean soulshot, int ssGrade)
{
_targetId = target.getObjectId();
_damage = damage;
_ssGrade = ssGrade;
if (miss)
{
addMask(AttackType.MISSED);
return;
}
if (crit)
{
addMask(AttackType.CRITICAL);
}
if (soulshot)
{
addMask(AttackType.SHOT_USED);
}
if ((target.isCharacter() && ((L2Character) target).isHpBlocked()) || (shld > 0))
{
addMask(AttackType.BLOCKED);
}
}
private void addMask(AttackType type)
{
_flags |= type.getMask();
}
public int getTargetId()
{
return _targetId;
}
public int getDamage()
{
return _damage;
}
public int getFlags()
{
return _flags;
}
public int getGrade()
{
return _ssGrade;
}
}

View File

@@ -0,0 +1,427 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Collection;
import java.util.Collections;
import java.util.Objects;
import com.l2jmobius.gameserver.enums.AttributeType;
import com.l2jmobius.gameserver.model.buylist.Product;
import com.l2jmobius.gameserver.model.ensoul.EnsoulOption;
import com.l2jmobius.gameserver.model.items.L2Item;
import com.l2jmobius.gameserver.model.items.L2WarehouseItem;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
/**
* Get all information from L2ItemInstance to generate ItemInfo.
*/
public class ItemInfo
{
/** Identifier of the L2ItemInstance */
private int _objectId;
/** The L2Item template of the L2ItemInstance */
private L2Item _item;
/** The level of enchant on the L2ItemInstance */
private int _enchant;
/** The augmentation of the item */
private int _augmentation;
/** The quantity of L2ItemInstance */
private long _count;
/** The price of the L2ItemInstance */
private int _price;
/** The custom L2ItemInstance types (used loto, race tickets) */
private int _type1;
private int _type2;
/** If True the L2ItemInstance is equipped */
private int _equipped;
/** The action to do clientside (1=ADD, 2=MODIFY, 3=REMOVE) */
private int _change;
/** The mana of this item */
private int _mana;
private int _time;
private int _location;
private byte _elemAtkType = -2;
private int _elemAtkPower = 0;
private final int[] _elemDefAttr =
{
0,
0,
0,
0,
0,
0
};
private int[] _option;
private Collection<EnsoulOption> _soulCrystalOptions;
private Collection<EnsoulOption> _soulCrystalSpecialOptions;
private int _visualId;
private long _visualExpiration;
/**
* Get all information from L2ItemInstance to generate ItemInfo.
* @param item
*/
public ItemInfo(L2ItemInstance item)
{
Objects.requireNonNull(item);
// Get the Identifier of the L2ItemInstance
_objectId = item.getObjectId();
// Get the L2Item of the L2ItemInstance
_item = item.getItem();
// Get the enchant level of the L2ItemInstance
_enchant = item.getEnchantLevel();
// Get the augmentation boni
if (item.isAugmented())
{
_augmentation = item.getAugmentation().getId();
}
else
{
_augmentation = 0;
}
// Get the quantity of the L2ItemInstance
_count = item.getCount();
// Get custom item types (used loto, race tickets)
_type1 = item.getCustomType1();
_type2 = item.getCustomType2();
// Verify if the L2ItemInstance is equipped
_equipped = item.isEquipped() ? 1 : 0;
// Get the action to do clientside
switch (item.getLastChange())
{
case L2ItemInstance.ADDED:
{
_change = 1;
break;
}
case L2ItemInstance.MODIFIED:
{
_change = 2;
break;
}
case L2ItemInstance.REMOVED:
{
_change = 3;
break;
}
}
// Get shadow item mana
_mana = item.getMana();
_time = item.isTimeLimitedItem() ? (int) (item.getRemainingTime() / 1000) : -9999;
_location = item.getLocationSlot();
_elemAtkType = item.getAttackAttributeType().getClientId();
_elemAtkPower = item.getAttackAttributePower();
for (AttributeType type : AttributeType.ATTRIBUTE_TYPES)
{
_elemDefAttr[type.getClientId()] = item.getDefenceAttribute(type);
}
_option = item.getEnchantOptions();
_soulCrystalOptions = item.getSpecialAbilities();
_soulCrystalSpecialOptions = item.getAdditionalSpecialAbilities();
_visualId = item.getVisualId();
}
public ItemInfo(L2ItemInstance item, int change)
{
this(item);
_change = change;
_visualExpiration = item.getVisualLifeTime() > 0 ? (item.getVisualLifeTime() - System.currentTimeMillis()) / 1000 : 0;
}
public ItemInfo(TradeItem item)
{
if (item == null)
{
return;
}
// Get the Identifier of the L2ItemInstance
_objectId = item.getObjectId();
// Get the L2Item of the L2ItemInstance
_item = item.getItem();
// Get the enchant level of the L2ItemInstance
_enchant = item.getEnchant();
// Get the augmentation bonus
_augmentation = item.getAugmentId();
// Get the quantity of the L2ItemInstance
_count = item.getCount();
// Get custom item types (used loto, race tickets)
_type1 = item.getCustomType1();
_type2 = item.getCustomType2();
// Verify if the L2ItemInstance is equipped
_equipped = 0;
// Get the action to do clientside
_change = 0;
// Get shadow item mana
_mana = -1;
_time = -9999;
_location = item.getLocationSlot();
_elemAtkType = item.getAttackElementType();
_elemAtkPower = item.getAttackElementPower();
for (byte i = 0; i < 6; i++)
{
_elemDefAttr[i] = item.getElementDefAttr(i);
}
_option = item.getEnchantOptions();
_soulCrystalOptions = item.getSoulCrystalOptions();
_soulCrystalOptions = item.getSoulCrystalSpecialOptions();
_visualId = item.getVisualId();
}
public ItemInfo(Product item)
{
if (item == null)
{
return;
}
// Get the Identifier of the L2ItemInstance
_objectId = 0;
// Get the L2Item of the L2ItemInstance
_item = item.getItem();
// Get the enchant level of the L2ItemInstance
_enchant = 0;
// Get the augmentation boni
_augmentation = 0;
// Get the quantity of the L2ItemInstance
_count = item.getCount();
// Get custom item types (used loto, race tickets)
_type1 = item.getItem().getType1();
_type2 = item.getItem().getType2();
// Verify if the L2ItemInstance is equipped
_equipped = 0;
// Get the action to do clientside
_change = 0;
// Get shadow item mana
_mana = -1;
_time = -9999;
_location = 0;
_soulCrystalOptions = Collections.emptyList();
_soulCrystalSpecialOptions = Collections.emptyList();
}
public ItemInfo(L2WarehouseItem item)
{
if (item == null)
{
return;
}
// Get the Identifier of the L2ItemInstance
_objectId = item.getObjectId();
// Get the L2Item of the L2ItemInstance
_item = item.getItem();
// Get the enchant level of the L2ItemInstance
_enchant = item.getEnchantLevel();
// Get the augmentation boni
if (item.isAugmented())
{
_augmentation = item.getAugmentationId();
}
else
{
_augmentation = 0;
}
// Get the quantity of the L2ItemInstance
_count = item.getCount();
// Get custom item types (used loto, race tickets)
_type1 = item.getCustomType1();
_type2 = item.getCustomType2();
// Verify if the L2ItemInstance is equipped
_equipped = 0;
// Get shadow item mana
_mana = item.getMana();
_time = item.getTime();
_location = item.getLocationSlot();
_elemAtkType = item.getAttackElementType();
_elemAtkPower = item.getAttackElementPower();
for (byte i = 0; i < 6; i++)
{
_elemDefAttr[i] = item.getElementDefAttr(i);
}
_option = item.getEnchantOptions();
_soulCrystalOptions = item.getSoulCrystalOptions();
_soulCrystalOptions = item.getSoulCrystalSpecialOptions();
}
public int getObjectId()
{
return _objectId;
}
public L2Item getItem()
{
return _item;
}
public int getEnchant()
{
return _enchant;
}
public int getAugmentationBonus()
{
return _augmentation;
}
public int get1stAugmentationId()
{
return 0x0000FFFF & getAugmentationBonus();
}
public int get2ndAugmentationId()
{
return getAugmentationBonus() >> 16;
}
public long getCount()
{
return _count;
}
public int getPrice()
{
return _price;
}
public int getCustomType1()
{
return _type1;
}
public int getCustomType2()
{
return _type2;
}
public int getEquipped()
{
return _equipped;
}
public int getChange()
{
return _change;
}
public int getMana()
{
return _mana;
}
public int getTime()
{
return _time > 0 ? _time : _visualExpiration > 0 ? (int) _visualExpiration : -9999;
}
public int getLocation()
{
return _location;
}
public int getAttackElementType()
{
return _elemAtkType;
}
public int getAttackElementPower()
{
return _elemAtkPower;
}
public int getElementDefAttr(byte i)
{
return _elemDefAttr[i];
}
public int[] getEnchantOptions()
{
return _option;
}
public int getVisualId()
{
return _visualId;
}
public Collection<EnsoulOption> getSoulCrystalOptions()
{
return _soulCrystalOptions;
}
public Collection<EnsoulOption> getSoulCrystalSpecialOptions()
{
return _soulCrystalSpecialOptions;
}
public long getVisualExpiration()
{
return _visualExpiration;
}
}

View File

@@ -0,0 +1,88 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
*
*/
public class ItemRequest
{
int _objectId;
int _itemId;
long _count;
long _price;
public ItemRequest(int objectId, long count, long price)
{
_objectId = objectId;
_count = count;
_price = price;
}
public ItemRequest(int objectId, int itemId, long count, long price)
{
_objectId = objectId;
_itemId = itemId;
_count = count;
_price = price;
}
public int getObjectId()
{
return _objectId;
}
public int getItemId()
{
return _itemId;
}
public void setCount(long count)
{
_count = count;
}
public long getCount()
{
return _count;
}
public long getPrice()
{
return _price;
}
@Override
public int hashCode()
{
return _objectId;
}
@Override
public boolean equals(Object obj)
{
if (this == obj)
{
return true;
}
if (!(obj instanceof ItemRequest))
{
return false;
}
return (_objectId != ((ItemRequest) obj)._objectId);
}
}

View File

@@ -0,0 +1,44 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* @author UnAfraid
* @param <K>
* @param <V>
*/
public class KeyValuePair<K, V>
{
private final K _key;
private final V _value;
public KeyValuePair(K key, V value)
{
_key = key;
_value = value;
}
public K getKey()
{
return _key;
}
public V getValue()
{
return _value;
}
}

View File

@@ -0,0 +1,237 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.data.xml.impl.AdminData;
/**
* @author HorridoJoho
*/
public class L2AccessLevel
{
/**
* The access level<br>
*/
private int _accessLevel = 0;
/**
* The access level name<br>
*/
private String _name = null;
/** Child access levels */
L2AccessLevel _childsAccessLevel = null;
/** Child access levels */
private int _child = 0;
/**
* The name color for the access level<br>
*/
private int _nameColor = 0;
/**
* The title color for the access level<br>
*/
private int _titleColor = 0;
/**
* Flag to determine if the access level has gm access<br>
*/
private boolean _isGm = false;
/** Flag for peace zone attack */
private boolean _allowPeaceAttack = false;
/** Flag for fixed res */
private boolean _allowFixedRes = false;
/** Flag for transactions */
private boolean _allowTransaction = false;
/** Flag for AltG commands */
private boolean _allowAltG = false;
/** Flag to give damage */
private boolean _giveDamage = false;
/** Flag to take aggro */
private boolean _takeAggro = false;
/** Flag to gain exp in party */
private boolean _gainExp = false;
public L2AccessLevel(StatsSet set)
{
_accessLevel = set.getInt("level");
_name = set.getString("name");
_nameColor = Integer.decode("0x" + set.getString("nameColor", "FFFFFF"));
_titleColor = Integer.decode("0x" + set.getString("titleColor", "FFFFFF"));
_child = set.getInt("childAccess", 0);
_isGm = set.getBoolean("isGM", false);
_allowPeaceAttack = set.getBoolean("allowPeaceAttack", false);
_allowFixedRes = set.getBoolean("allowFixedRes", false);
_allowTransaction = set.getBoolean("allowTransaction", true);
_allowAltG = set.getBoolean("allowAltg", false);
_giveDamage = set.getBoolean("giveDamage", true);
_takeAggro = set.getBoolean("takeAggro", true);
_gainExp = set.getBoolean("gainExp", true);
}
public L2AccessLevel()
{
_accessLevel = 0;
_name = "User";
_nameColor = Integer.decode("0xFFFFFF");
_titleColor = Integer.decode("0xFFFFFF");
_child = 0;
_isGm = false;
_allowPeaceAttack = false;
_allowFixedRes = false;
_allowTransaction = true;
_allowAltG = false;
_giveDamage = true;
_takeAggro = true;
_gainExp = true;
}
/**
* Returns the access level<br>
* <br>
* @return int: access level<br>
*/
public int getLevel()
{
return _accessLevel;
}
/**
* Returns the access level name<br>
* <br>
* @return String: access level name<br>
*/
public String getName()
{
return _name;
}
/**
* Returns the name color of the access level<br>
* <br>
* @return int: the name color for the access level<br>
*/
public int getNameColor()
{
return _nameColor;
}
/**
* Returns the title color color of the access level<br>
* <br>
* @return int: the title color for the access level<br>
*/
public int getTitleColor()
{
return _titleColor;
}
/**
* Retuns if the access level has gm access or not<br>
* <br>
* @return boolean: true if access level have gm access, otherwise false<br>
*/
public boolean isGm()
{
return _isGm;
}
/**
* Returns if the access level is allowed to attack in peace zone or not<br>
* <br>
* @return boolean: true if the access level is allowed to attack in peace zone, otherwise false<br>
*/
public boolean allowPeaceAttack()
{
return _allowPeaceAttack;
}
/**
* Retruns if the access level is allowed to use fixed res or not<br>
* <br>
* @return true if the access level is allowed to use fixed res, otherwise false<br>
*/
public boolean allowFixedRes()
{
return _allowFixedRes;
}
/**
* Returns if the access level is allowed to perform transactions or not<br>
* <br>
* @return boolean: true if access level is allowed to perform transactions, otherwise false<br>
*/
public boolean allowTransaction()
{
return _allowTransaction;
}
/**
* Returns if the access level is allowed to use AltG commands or not<br>
* <br>
* @return boolean: true if access level is allowed to use AltG commands, otherwise false<br>
*/
public boolean allowAltG()
{
return _allowAltG;
}
/**
* Returns if the access level can give damage or not<br>
* <br>
* @return boolean: true if the access level can give damage, otherwise false<br>
*/
public boolean canGiveDamage()
{
return _giveDamage;
}
/**
* Returns if the access level can take aggro or not<br>
* <br>
* @return boolean: true if the access level can take aggro, otherwise false<br>
*/
public boolean canTakeAggro()
{
return _takeAggro;
}
/**
* Returns if the access level can gain exp or not<br>
* <br>
* @return boolean: true if the access level can gain exp, otherwise false<br>
*/
public boolean canGainExp()
{
return _gainExp;
}
/**
* Returns if the access level contains allowedAccess as child<br>
* @param accessLevel as AccessLevel<br>
* @return boolean: true if a child access level is equals to allowedAccess, otherwise false<br>
*/
public boolean hasChildAccess(L2AccessLevel accessLevel)
{
if (_childsAccessLevel == null)
{
if (_child <= 0)
{
return false;
}
_childsAccessLevel = AdminData.getInstance().getAccessLevel(_child);
}
return (_childsAccessLevel != null) && ((_childsAccessLevel.getLevel() == accessLevel.getLevel()) || _childsAccessLevel.hasChildAccess(accessLevel));
}
}

View File

@@ -0,0 +1,69 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.data.xml.impl.AdminData;
/**
* @author HorridoJoho
*/
public class L2AdminCommandAccessRight
{
private final String _adminCommand;
private final int _accessLevel;
private final boolean _requireConfirm;
public L2AdminCommandAccessRight(StatsSet set)
{
_adminCommand = set.getString("command");
_requireConfirm = set.getBoolean("confirmDlg", false);
_accessLevel = set.getInt("accessLevel", 7);
}
public L2AdminCommandAccessRight(String command, boolean confirm, int level)
{
_adminCommand = command;
_requireConfirm = confirm;
_accessLevel = level;
}
/**
* @return the admin command the access right belongs to
*/
public String getAdminCommand()
{
return _adminCommand;
}
/**
* @param characterAccessLevel
* @return {@code true} if characterAccessLevel is allowed to use the admin command which belongs to this access right, {@code false} otherwise
*/
public boolean hasAccess(L2AccessLevel characterAccessLevel)
{
final L2AccessLevel accessLevel = AdminData.getInstance().getAccessLevel(_accessLevel);
return (accessLevel != null) && ((accessLevel.getLevel() == characterAccessLevel.getLevel()) || characterAccessLevel.hasChildAccess(accessLevel));
}
/**
* @return {@code true} if admin command requires confirmation before execution, {@code false} otherwise.
*/
public boolean getRequireConfirm()
{
return _requireConfirm;
}
}

View File

@@ -0,0 +1,219 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.LinkedHashMap;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.function.Function;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.holders.ArmorsetSkillHolder;
import com.l2jmobius.gameserver.model.itemcontainer.Inventory;
import com.l2jmobius.gameserver.model.itemcontainer.PcInventory;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
import com.l2jmobius.gameserver.model.stats.BaseStats;
/**
* @author UnAfraid
*/
public final class L2ArmorSet
{
private final int _id;
private final int _minimumPieces;
private final boolean _isVisual;
private final Set<Integer> _requiredItems = new LinkedHashSet<>();
private final Set<Integer> _optionalItems = new LinkedHashSet<>();
private final List<ArmorsetSkillHolder> _skills = new ArrayList<>();
private final Map<BaseStats, Double> _stats = new LinkedHashMap<>();
private static final int[] ARMORSET_SLOTS = new int[]
{
Inventory.PAPERDOLL_CHEST,
Inventory.PAPERDOLL_LEGS,
Inventory.PAPERDOLL_HEAD,
Inventory.PAPERDOLL_GLOVES,
Inventory.PAPERDOLL_FEET
};
/**
* @param id
* @param minimumPieces
* @param isVisual
*/
public L2ArmorSet(int id, int minimumPieces, boolean isVisual)
{
_id = id;
_minimumPieces = minimumPieces;
_isVisual = isVisual;
}
public int getId()
{
return _id;
}
/**
* @return the minimum amount of pieces equipped to form a set
*/
public int getMinimumPieces()
{
return _minimumPieces;
}
/**
* @return {@code true} if the set is visual only, {@code} otherwise
*/
public boolean isVisual()
{
return _isVisual;
}
/**
* Adds an item to the set
* @param item
* @return {@code true} if item was successfully added, {@code false} in case it already exists
*/
public boolean addRequiredItem(Integer item)
{
return _requiredItems.add(item);
}
/**
* @return the set of items that can form a set
*/
public Set<Integer> getRequiredItems()
{
return _requiredItems;
}
/**
* Adds an shield to the set
* @param item
* @return {@code true} if shield was successfully added, {@code false} in case it already exists
*/
public boolean addOptionalItem(Integer item)
{
return _optionalItems.add(item);
}
/**
* @return the set of shields
*/
public Set<Integer> getOptionalItems()
{
return _optionalItems;
}
/**
* Adds an skill to the set
* @param holder
*/
public void addSkill(ArmorsetSkillHolder holder)
{
_skills.add(holder);
}
/**
* The list of skills that are activated when set reaches it's minimal equipped items condition
* @return
*/
public List<ArmorsetSkillHolder> getSkills()
{
return _skills;
}
/**
* Adds stats bonus to the set activated when set reaches it's minimal equipped items condition
* @param stat
* @param value
*/
public void addStatsBonus(BaseStats stat, double value)
{
_stats.putIfAbsent(stat, value);
}
/**
* @param stat
* @return the stats bonus value or 0 if doesn't exists
*/
public double getStatsBonus(BaseStats stat)
{
return _stats.getOrDefault(stat, 0d);
}
/**
* @param shield_id
* @return {@code true} if player has the shield of this set equipped, {@code false} in case set doesn't have a shield or player doesn't
*/
public boolean containOptionalItem(int shield_id)
{
return _optionalItems.contains(shield_id);
}
/**
* @param player
* @return true if all parts of set are enchanted to +6 or more
*/
public int getLowestSetEnchant(L2PcInstance player)
{
// Player don't have full set
if (getPiecesCount(player, L2ItemInstance::getId) < getMinimumPieces())
{
return 0;
}
final PcInventory inv = player.getInventory();
int enchantLevel = Byte.MAX_VALUE;
for (int armorSlot : ARMORSET_SLOTS)
{
final L2ItemInstance itemPart = inv.getPaperdollItem(armorSlot);
if ((itemPart != null) && _requiredItems.contains(itemPart.getId()))
{
if (enchantLevel > itemPart.getEnchantLevel())
{
enchantLevel = itemPart.getEnchantLevel();
}
}
}
if (enchantLevel == Byte.MAX_VALUE)
{
enchantLevel = 0;
}
return enchantLevel;
}
public boolean hasOptionalEquipped(L2PcInstance player, Function<L2ItemInstance, Integer> idProvider)
{
return player.getInventory().getPaperdollItems().stream().anyMatch(item -> _optionalItems.contains(idProvider.apply(item)));
}
/**
* @param player
* @param idProvider
* @return the amount of set visual items that player has equipped
*/
public long getPiecesCount(L2PcInstance player, Function<L2ItemInstance, Integer> idProvider)
{
return player.getInventory().getPaperdollItems(item -> _requiredItems.contains(idProvider.apply(item))).size();
}
}

View File

@@ -0,0 +1,107 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.List;
import java.util.logging.Logger;
import com.l2jmobius.gameserver.data.xml.impl.OptionData;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.options.Options;
/**
* Used to store an augmentation and its bonuses.
* @author durgus, UnAfraid
*/
public final class L2Augmentation
{
private static final Logger LOGGER = Logger.getLogger(L2Augmentation.class.getName());
private final List<Options> _options = new ArrayList<>();
private boolean _active;
private final int _id;
public L2Augmentation(int id)
{
_id = id;
_active = false;
final int[] stats = new int[2];
stats[0] = 0x0000FFFF & id;
stats[1] = (id >> 16);
for (int stat : stats)
{
final Options op = OptionData.getInstance().getOptions(stat);
if (op != null)
{
_options.add(op);
}
else
{
LOGGER.warning(getClass().getSimpleName() + ": Couldn't find option: " + stat);
}
}
}
/**
* Get the augmentation "id" used in serverpackets.
* @return augmentationId
*/
public int getId()
{
return _id;
}
public List<Options> getOptions()
{
return _options;
}
public void applyBonus(L2PcInstance player)
{
// make sure the bonuses are not applied twice..
if (_active)
{
return;
}
for (Options op : _options)
{
op.apply(player);
}
player.getStat().recalculateStats(true);
_active = true;
}
public void removeBonus(L2PcInstance player)
{
// make sure the bonuses are not removed twice
if (!_active)
{
return;
}
for (Options op : _options)
{
op.remove(player);
}
player.getStat().recalculateStats(true);
_active = false;
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,783 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.Config;
import com.l2jmobius.commons.database.DatabaseFactory;
import com.l2jmobius.gameserver.enums.ClanRewardType;
import com.l2jmobius.gameserver.instancemanager.SiegeManager;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.variables.PlayerVariables;
/**
* This class holds the clan members data.
*/
public class L2ClanMember
{
private static final Logger LOGGER = Logger.getLogger(L2ClanMember.class.getName());
private final L2Clan _clan;
private int _objectId;
private String _name;
private String _title;
private int _powerGrade;
private int _level;
private int _classId;
private boolean _sex;
private int _raceOrdinal;
private L2PcInstance _player;
private int _pledgeType;
private int _apprentice;
private int _sponsor;
private long _onlineTime;
/**
* Used to restore a clan member from the database.
* @param clan the clan where the clan member belongs.
* @param clanMember the clan member result set
* @throws SQLException if the columnLabel is not valid or a database error occurs
*/
public L2ClanMember(L2Clan clan, ResultSet clanMember) throws SQLException
{
if (clan == null)
{
throw new IllegalArgumentException("Cannot create a Clan Member with a null clan.");
}
_clan = clan;
_name = clanMember.getString("char_name");
_level = clanMember.getInt("level");
_classId = clanMember.getInt("classid");
_objectId = clanMember.getInt("charId");
_pledgeType = clanMember.getInt("subpledge");
_title = clanMember.getString("title");
_powerGrade = clanMember.getInt("power_grade");
_apprentice = clanMember.getInt("apprentice");
_sponsor = clanMember.getInt("sponsor");
_sex = clanMember.getInt("sex") != 0;
_raceOrdinal = clanMember.getInt("race");
}
/**
* Creates a clan member from a player instance.
* @param clan the clan where the player belongs
* @param player the player from which the clan member will be created
*/
public L2ClanMember(L2Clan clan, L2PcInstance player)
{
if (clan == null)
{
throw new IllegalArgumentException("Cannot create a Clan Member if player has a null clan.");
}
_player = player;
_clan = clan;
_name = player.getName();
_level = player.getLevel();
_classId = player.getClassId().getId();
_objectId = player.getObjectId();
_pledgeType = player.getPledgeType();
_powerGrade = player.getPowerGrade();
_title = player.getTitle();
_sponsor = 0;
_apprentice = 0;
_sex = player.getAppearance().getSex();
_raceOrdinal = player.getRace().ordinal();
}
/**
* Sets the player instance.
* @param player the new player instance
*/
public void setPlayerInstance(L2PcInstance player)
{
if ((player == null) && (_player != null))
{
// this is here to keep the data when the player logs off
_name = _player.getName();
_level = _player.getLevel();
_classId = _player.getClassId().getId();
_objectId = _player.getObjectId();
_powerGrade = _player.getPowerGrade();
_pledgeType = _player.getPledgeType();
_title = _player.getTitle();
_apprentice = _player.getApprentice();
_sponsor = _player.getSponsor();
_sex = _player.getAppearance().getSex();
_raceOrdinal = _player.getRace().ordinal();
}
if (player != null)
{
_clan.addSkillEffects(player);
if ((_clan.getLevel() > 3) && player.isClanLeader())
{
SiegeManager.getInstance().addSiegeSkills(player);
}
if (player.isClanLeader())
{
_clan.setLeader(this);
}
}
_player = player;
}
/**
* Gets the player instance.
* @return the player instance
*/
public L2PcInstance getPlayerInstance()
{
return _player;
}
/**
* Checks if is online.
* @return true, if is online
*/
public boolean isOnline()
{
if ((_player == null) || !_player.isOnline())
{
return false;
}
if ((_player.getClient() == null) || _player.getClient().isDetached())
{
return false;
}
return true;
}
/**
* Gets the class id.
* @return the classId
*/
public int getClassId()
{
return _player != null ? _player.getClassId().getId() : _classId;
}
/**
* Gets the level.
* @return the level
*/
public int getLevel()
{
return _player != null ? _player.getLevel() : _level;
}
/**
* Gets the name.
* @return the name
*/
public String getName()
{
return _player != null ? _player.getName() : _name;
}
/**
* Gets the object id.
* @return Returns the objectId.
*/
public int getObjectId()
{
return _player != null ? _player.getObjectId() : _objectId;
}
/**
* Gets the title.
* @return the title
*/
public String getTitle()
{
return _player != null ? _player.getTitle() : _title;
}
/**
* Gets the pledge type.
* @return the pledge type
*/
public int getPledgeType()
{
return _player != null ? _player.getPledgeType() : _pledgeType;
}
/**
* Sets the pledge type.
* @param pledgeType the new pledge type
*/
public void setPledgeType(int pledgeType)
{
_pledgeType = pledgeType;
if (_player != null)
{
_player.setPledgeType(pledgeType);
}
else
{
// db save if char not logged in
updatePledgeType();
}
}
/**
* Update pledge type.
*/
public void updatePledgeType()
{
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement ps = con.prepareStatement("UPDATE characters SET subpledge=? WHERE charId=?"))
{
ps.setLong(1, _pledgeType);
ps.setInt(2, getObjectId());
ps.execute();
}
catch (Exception e)
{
LOGGER.log(Level.WARNING, "Could not update pledge type: " + e.getMessage(), e);
}
}
/**
* Gets the power grade.
* @return the power grade
*/
public int getPowerGrade()
{
if (_player != null)
{
return _player.getPowerGrade();
}
return _powerGrade;
}
/**
* Sets the power grade.
* @param powerGrade the new power grade
*/
public void setPowerGrade(int powerGrade)
{
_powerGrade = powerGrade;
if (_player != null)
{
_player.setPowerGrade(powerGrade);
}
else
{
// db save if char not logged in
updatePowerGrade();
}
}
/**
* Update the characters table of the database with power grade.
*/
public void updatePowerGrade()
{
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement ps = con.prepareStatement("UPDATE characters SET power_grade=? WHERE charId=?"))
{
ps.setLong(1, _powerGrade);
ps.setInt(2, getObjectId());
ps.execute();
}
catch (Exception e)
{
LOGGER.log(Level.WARNING, "Could not update power _grade: " + e.getMessage(), e);
}
}
/**
* Sets the apprentice and sponsor.
* @param apprenticeID the apprentice id
* @param sponsorID the sponsor id
*/
public void setApprenticeAndSponsor(int apprenticeID, int sponsorID)
{
_apprentice = apprenticeID;
_sponsor = sponsorID;
}
/**
* Gets the player's race ordinal.
* @return the race ordinal
*/
public int getRaceOrdinal()
{
if (_player != null)
{
return _player.getRace().ordinal();
}
return _raceOrdinal;
}
/**
* Gets the player's sex.
* @return the sex
*/
public boolean getSex()
{
if (_player != null)
{
return _player.getAppearance().getSex();
}
return _sex;
}
/**
* Gets the sponsor.
* @return the sponsor
*/
public int getSponsor()
{
if (_player != null)
{
return _player.getSponsor();
}
return _sponsor;
}
/**
* Gets the apprentice.
* @return the apprentice
*/
public int getApprentice()
{
if (_player != null)
{
return _player.getApprentice();
}
return _apprentice;
}
/**
* Gets the apprentice or sponsor name.
* @return the apprentice or sponsor name
*/
public String getApprenticeOrSponsorName()
{
if (_player != null)
{
_apprentice = _player.getApprentice();
_sponsor = _player.getSponsor();
}
if (_apprentice != 0)
{
final L2ClanMember apprentice = _clan.getClanMember(_apprentice);
if (apprentice != null)
{
return apprentice.getName();
}
return "Error";
}
if (_sponsor != 0)
{
final L2ClanMember sponsor = _clan.getClanMember(_sponsor);
if (sponsor != null)
{
return sponsor.getName();
}
return "Error";
}
return "";
}
/**
* Gets the clan.
* @return the clan
*/
public L2Clan getClan()
{
return _clan;
}
/**
* Calculate pledge class.
* @param player the player
* @return the int
*/
public static int calculatePledgeClass(L2PcInstance player)
{
int pledgeClass = 0;
if (player == null)
{
return pledgeClass;
}
final L2Clan clan = player.getClan();
if (clan != null)
{
switch (clan.getLevel())
{
case 4:
if (player.isClanLeader())
{
pledgeClass = 3;
}
break;
case 5:
if (player.isClanLeader())
{
pledgeClass = 4;
}
else
{
pledgeClass = 2;
}
break;
case 6:
switch (player.getPledgeType())
{
case -1:
pledgeClass = 1;
break;
case 100:
case 200:
pledgeClass = 2;
break;
case 0:
if (player.isClanLeader())
{
pledgeClass = 5;
}
else
{
switch (clan.getLeaderSubPledge(player.getObjectId()))
{
case 100:
case 200:
pledgeClass = 4;
break;
case -1:
default:
pledgeClass = 3;
break;
}
}
break;
}
break;
case 7:
switch (player.getPledgeType())
{
case -1:
pledgeClass = 1;
break;
case 100:
case 200:
pledgeClass = 3;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 2;
break;
case 0:
if (player.isClanLeader())
{
pledgeClass = 7;
}
else
{
switch (clan.getLeaderSubPledge(player.getObjectId()))
{
case 100:
case 200:
pledgeClass = 6;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 5;
break;
case -1:
default:
pledgeClass = 4;
break;
}
}
break;
}
break;
case 8:
switch (player.getPledgeType())
{
case -1:
pledgeClass = 1;
break;
case 100:
case 200:
pledgeClass = 4;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 3;
break;
case 0:
if (player.isClanLeader())
{
pledgeClass = 8;
}
else
{
switch (clan.getLeaderSubPledge(player.getObjectId()))
{
case 100:
case 200:
pledgeClass = 7;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 6;
break;
case -1:
default:
pledgeClass = 5;
break;
}
}
break;
}
break;
case 9:
switch (player.getPledgeType())
{
case -1:
pledgeClass = 1;
break;
case 100:
case 200:
pledgeClass = 5;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 4;
break;
case 0:
if (player.isClanLeader())
{
pledgeClass = 9;
}
else
{
switch (clan.getLeaderSubPledge(player.getObjectId()))
{
case 100:
case 200:
pledgeClass = 8;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 7;
break;
case -1:
default:
pledgeClass = 6;
break;
}
}
break;
}
break;
case 10:
switch (player.getPledgeType())
{
case -1:
pledgeClass = 1;
break;
case 100:
case 200:
pledgeClass = 6;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 5;
break;
case 0:
if (player.isClanLeader())
{
pledgeClass = 10;
}
else
{
switch (clan.getLeaderSubPledge(player.getObjectId()))
{
case 100:
case 200:
pledgeClass = 9;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 8;
break;
case -1:
default:
pledgeClass = 7;
break;
}
}
break;
}
break;
case 11:
switch (player.getPledgeType())
{
case -1:
pledgeClass = 1;
break;
case 100:
case 200:
pledgeClass = 7;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 6;
break;
case 0:
if (player.isClanLeader())
{
pledgeClass = 11;
}
else
{
switch (clan.getLeaderSubPledge(player.getObjectId()))
{
case 100:
case 200:
pledgeClass = 10;
break;
case 1001:
case 1002:
case 2001:
case 2002:
pledgeClass = 9;
break;
case -1:
default:
pledgeClass = 8;
break;
}
}
break;
}
break;
default:
pledgeClass = 1;
break;
}
}
if (player.isNoble() && (pledgeClass < 5))
{
pledgeClass = 5;
}
if (player.isHero() && (pledgeClass < 8))
{
pledgeClass = 8;
}
return pledgeClass;
}
/**
* Save apprentice and sponsor.
* @param apprentice the apprentice
* @param sponsor the sponsor
*/
public void saveApprenticeAndSponsor(int apprentice, int sponsor)
{
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement ps = con.prepareStatement("UPDATE characters SET apprentice=?,sponsor=? WHERE charId=?"))
{
ps.setInt(1, apprentice);
ps.setInt(2, sponsor);
ps.setInt(3, getObjectId());
ps.execute();
}
catch (SQLException e)
{
LOGGER.log(Level.WARNING, "Could not save apprentice/sponsor: " + e.getMessage(), e);
}
}
public long getOnlineTime()
{
return _onlineTime;
}
public void setOnlineTime(long onlineTime)
{
_onlineTime = onlineTime;
}
public void resetBonus()
{
_onlineTime = 0;
final PlayerVariables vars = getVariables();
vars.set("CLAIMED_CLAN_REWARDS", 0);
vars.storeMe();
}
public int getOnlineStatus()
{
return !isOnline() ? 0 : _onlineTime >= (Config.ALT_CLAN_MEMBERS_TIME_FOR_BONUS) ? 2 : 1;
}
public boolean isRewardClaimed(ClanRewardType type)
{
final PlayerVariables vars = getVariables();
final int claimedRewards = vars.getInt("CLAIMED_CLAN_REWARDS", ClanRewardType.getDefaultMask());
return (claimedRewards & type.getMask()) == type.getMask();
}
public void setRewardClaimed(ClanRewardType type)
{
final PlayerVariables vars = getVariables();
int claimedRewards = vars.getInt("CLAIMED_CLAN_REWARDS", ClanRewardType.getDefaultMask());
claimedRewards |= type.getMask();
vars.set("CLAIMED_CLAN_REWARDS", claimedRewards);
vars.storeMe();
}
private PlayerVariables getVariables()
{
final L2PcInstance player = getPlayerInstance();
return player != null ? player.getVariables() : new PlayerVariables(_objectId);
}
}

View File

@@ -0,0 +1,253 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.LinkedList;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
import java.util.function.Function;
import com.l2jmobius.Config;
import com.l2jmobius.gameserver.model.actor.L2Character;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.ExCloseMPCC;
import com.l2jmobius.gameserver.network.serverpackets.ExMPCCPartyInfoUpdate;
import com.l2jmobius.gameserver.network.serverpackets.ExOpenMPCC;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
/**
* This class serves as a container for command channels.
* @author chris_00
*/
public class L2CommandChannel extends AbstractPlayerGroup
{
private final List<L2Party> _parties = new CopyOnWriteArrayList<>();
private L2PcInstance _commandLeader = null;
private int _channelLvl;
/**
* Create a new command channel and add the leader's party to it.
* @param leader the leader of this command channel
*/
public L2CommandChannel(L2PcInstance leader)
{
_commandLeader = leader;
final L2Party party = leader.getParty();
_parties.add(party);
_channelLvl = party.getLevel();
party.setCommandChannel(this);
party.broadcastMessage(SystemMessageId.THE_COMMAND_CHANNEL_HAS_BEEN_FORMED);
party.broadcastPacket(ExOpenMPCC.STATIC_PACKET);
}
/**
* Add a party to this command channel.
* @param party the party to add
*/
public void addParty(L2Party party)
{
if (party == null)
{
return;
}
// Update the CCinfo for existing players
broadcastPacket(new ExMPCCPartyInfoUpdate(party, 1));
_parties.add(party);
if (party.getLevel() > _channelLvl)
{
_channelLvl = party.getLevel();
}
party.setCommandChannel(this);
party.broadcastPacket(SystemMessage.getSystemMessage(SystemMessageId.YOU_HAVE_JOINED_THE_COMMAND_CHANNEL));
party.broadcastPacket(ExOpenMPCC.STATIC_PACKET);
}
/**
* Remove a party from this command channel.
* @param party the party to remove
*/
public void removeParty(L2Party party)
{
if (party == null)
{
return;
}
_parties.remove(party);
_channelLvl = 0;
for (L2Party pty : _parties)
{
if (pty.getLevel() > _channelLvl)
{
_channelLvl = pty.getLevel();
}
}
party.setCommandChannel(null);
party.broadcastPacket(ExCloseMPCC.STATIC_PACKET);
if (_parties.size() < 2)
{
broadcastPacket(SystemMessage.getSystemMessage(SystemMessageId.THE_COMMAND_CHANNEL_HAS_BEEN_DISBANDED));
disbandChannel();
}
else
{
// Update the CCinfo for existing players
broadcastPacket(new ExMPCCPartyInfoUpdate(party, 0));
}
}
/**
* Disband this command channel.
*/
public void disbandChannel()
{
if (_parties != null)
{
for (L2Party party : _parties)
{
if (party != null)
{
removeParty(party);
}
}
_parties.clear();
}
}
/**
* @return the total count of all members of this command channel
*/
@Override
public int getMemberCount()
{
int count = 0;
for (L2Party party : _parties)
{
if (party != null)
{
count += party.getMemberCount();
}
}
return count;
}
/**
* @return a list of all parties in this command channel
*/
public List<L2Party> getPartys()
{
return _parties;
}
/**
* @return a list of all members in this command channel
*/
@Override
public List<L2PcInstance> getMembers()
{
final List<L2PcInstance> members = new LinkedList<>();
for (L2Party party : getPartys())
{
members.addAll(party.getMembers());
}
return members;
}
/**
* @return the level of this command channel (equals the level of the highest-leveled character in this command channel)
*/
@Override
public int getLevel()
{
return _channelLvl;
}
@Override
public void setLeader(L2PcInstance leader)
{
_commandLeader = leader;
if (leader.getLevel() > _channelLvl)
{
_channelLvl = leader.getLevel();
}
}
/**
* @param obj
* @return true if proper condition for RaidWar
*/
public boolean meetRaidWarCondition(L2Object obj)
{
if (!((obj instanceof L2Character) && ((L2Character) obj).isRaid()))
{
return false;
}
return (getMemberCount() >= Config.LOOT_RAIDS_PRIVILEGE_CC_SIZE);
}
/**
* @return the leader of this command channel
*/
@Override
public L2PcInstance getLeader()
{
return _commandLeader;
}
/**
* Check if a given player is in this command channel.
* @param player the player to check
* @return {@code true} if he does, {@code false} otherwise
*/
@Override
public boolean containsPlayer(L2PcInstance player)
{
if ((_parties != null) && !_parties.isEmpty())
{
for (L2Party party : _parties)
{
if (party.containsPlayer(player))
{
return true;
}
}
}
return false;
}
/**
* Iterates over all command channel members without the need to allocate a new list
* @see com.l2jmobius.gameserver.model.AbstractPlayerGroup#forEachMember(Function)
*/
@Override
public boolean forEachMember(Function<L2PcInstance, Boolean> function)
{
if ((_parties != null) && !_parties.isEmpty())
{
for (L2Party party : _parties)
{
if (!party.forEachMember(function))
{
return false;
}
}
}
return true;
}
}

View File

@@ -0,0 +1,185 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.commons.database.DatabaseFactory;
import com.l2jmobius.gameserver.data.sql.impl.CharNameTable;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
/**
* TODO: System messages:<br>
* ADD: 3223: The previous name is being registered. Please try again later.<br>
* DEL 3219: $s1 was successfully deleted from your Contact List.<br>
* DEL 3217: The name is not currently registered.
* @author UnAfraid, mrTJO
*/
public class L2ContactList
{
private static final Logger LOGGER = Logger.getLogger(L2ContactList.class.getName());
private final L2PcInstance activeChar;
private final Set<String> _contacts = ConcurrentHashMap.newKeySet();
private static final String QUERY_ADD = "INSERT INTO character_contacts (charId, contactId) VALUES (?, ?)";
private static final String QUERY_REMOVE = "DELETE FROM character_contacts WHERE charId = ? and contactId = ?";
private static final String QUERY_LOAD = "SELECT contactId FROM character_contacts WHERE charId = ?";
public L2ContactList(L2PcInstance player)
{
activeChar = player;
restore();
}
public void restore()
{
_contacts.clear();
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement(QUERY_LOAD))
{
statement.setInt(1, activeChar.getObjectId());
try (ResultSet rset = statement.executeQuery())
{
int contactId;
String contactName;
while (rset.next())
{
contactId = rset.getInt(1);
contactName = CharNameTable.getInstance().getNameById(contactId);
if ((contactName == null) || contactName.equals(activeChar.getName()) || (contactId == activeChar.getObjectId()))
{
continue;
}
_contacts.add(contactName);
}
}
}
catch (Exception e)
{
LOGGER.log(Level.WARNING, "Error found in " + activeChar.getName() + "'s ContactsList: " + e.getMessage(), e);
}
}
public boolean add(String name)
{
SystemMessage sm;
final int contactId = CharNameTable.getInstance().getIdByName(name);
if (_contacts.contains(name))
{
activeChar.sendPacket(SystemMessageId.THE_NAME_ALREADY_EXISTS_ON_THE_ADDED_LIST);
return false;
}
else if (activeChar.getName().equals(name))
{
activeChar.sendPacket(SystemMessageId.YOU_CANNOT_ADD_YOUR_OWN_NAME);
return false;
}
else if (_contacts.size() >= 100)
{
activeChar.sendPacket(SystemMessageId.THE_MAXIMUM_NUMBER_OF_NAMES_100_HAS_BEEN_REACHED_YOU_CANNOT_REGISTER_ANY_MORE);
return false;
}
else if (contactId < 1)
{
sm = SystemMessage.getSystemMessage(SystemMessageId.THE_NAME_S1_DOESN_T_EXIST_PLEASE_TRY_ANOTHER_NAME);
sm.addString(name);
activeChar.sendPacket(sm);
return false;
}
else
{
for (String contactName : _contacts)
{
if (contactName.equalsIgnoreCase(name))
{
activeChar.sendPacket(SystemMessageId.THE_NAME_ALREADY_EXISTS_ON_THE_ADDED_LIST);
return false;
}
}
}
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement(QUERY_ADD))
{
statement.setInt(1, activeChar.getObjectId());
statement.setInt(2, contactId);
statement.execute();
_contacts.add(name);
sm = SystemMessage.getSystemMessage(SystemMessageId.S1_WAS_SUCCESSFULLY_ADDED_TO_YOUR_CONTACT_LIST);
sm.addString(name);
activeChar.sendPacket(sm);
}
catch (Exception e)
{
LOGGER.log(Level.WARNING, "Error found in " + activeChar.getName() + "'s ContactsList: " + e.getMessage(), e);
}
return true;
}
public void remove(String name)
{
final int contactId = CharNameTable.getInstance().getIdByName(name);
if (!_contacts.contains(name))
{
activeChar.sendPacket(SystemMessageId.THE_NAME_IS_NOT_CURRENTLY_REGISTERED);
return;
}
else if (contactId < 1)
{
// TODO: Message?
return;
}
_contacts.remove(name);
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement(QUERY_REMOVE))
{
statement.setInt(1, activeChar.getObjectId());
statement.setInt(2, contactId);
statement.execute();
final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.S1_WAS_SUCCESSFULLY_DELETED_FROM_YOUR_CONTACT_LIST);
sm.addString(name);
activeChar.sendPacket(sm);
}
catch (Exception e)
{
LOGGER.log(Level.WARNING, "Error found in " + activeChar.getName() + "'s ContactsList: " + e.getMessage(), e);
}
}
public Set<String> getAllContacts()
{
return _contacts;
}
}

View File

@@ -0,0 +1,138 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.Config;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.interfaces.IIdentifiable;
import com.l2jmobius.gameserver.network.serverpackets.AllyCrest;
import com.l2jmobius.gameserver.network.serverpackets.ExPledgeEmblem;
import com.l2jmobius.gameserver.network.serverpackets.PledgeCrest;
/**
* @author NosBit
*/
public final class L2Crest implements IIdentifiable
{
public enum CrestType
{
PLEDGE(1),
PLEDGE_LARGE(2),
ALLY(3);
private final int _id;
CrestType(int id)
{
_id = id;
}
public int getId()
{
return _id;
}
public static CrestType getById(int id)
{
for (CrestType crestType : values())
{
if (crestType.getId() == id)
{
return crestType;
}
}
return null;
}
}
private final int _id;
private final byte[] _data;
private final CrestType _type;
public L2Crest(int id, byte[] data, CrestType type)
{
_id = id;
_data = data;
_type = type;
}
@Override
public int getId()
{
return _id;
}
public byte[] getData()
{
return _data;
}
public CrestType getType()
{
return _type;
}
/**
* Gets the client path to crest for use in html and sends the crest to {@code L2PcInstance}
* @param activeChar the @{code L2PcInstance} where html is send to.
* @return the client path to crest
*/
public String getClientPath(L2PcInstance activeChar)
{
String path = null;
switch (getType())
{
case PLEDGE:
{
activeChar.sendPacket(new PledgeCrest(getId(), getData()));
path = "Crest.crest_" + Config.SERVER_ID + "_" + getId();
break;
}
case PLEDGE_LARGE:
{
final byte[] data = getData();
if (data != null)
{
for (int i = 0; i <= 4; i++)
{
if (i < 4)
{
final byte[] fullChunk = new byte[14336];
System.arraycopy(data, (14336 * i), fullChunk, 0, 14336);
activeChar.sendPacket(new ExPledgeEmblem(getId(), fullChunk, 0, i));
}
else
{
final byte[] lastChunk = new byte[8320];
System.arraycopy(data, (14336 * i), lastChunk, 0, 8320);
activeChar.sendPacket(new ExPledgeEmblem(getId(), lastChunk, 0, i));
}
}
}
path = "Crest.crest_" + Config.SERVER_ID + "_" + getId() + "_l";
break;
}
case ALLY:
{
activeChar.sendPacket(new AllyCrest(getId(), getData()));
path = "Crest.crest_" + Config.SERVER_ID + "_" + getId();
break;
}
}
return path;
}
}

View File

@@ -0,0 +1,79 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* @author JIV
*/
public class L2ExtractableProduct
{
private final int _id;
private final int _min;
private final int _max;
private final int _chance;
private final int _minEnchant;
private final int _maxEnchant;
/**
* Create Extractable product
* @param id create item id
* @param min item count max
* @param max item count min
* @param chance chance for creating
* @param minEnchant item min enchant
* @param maxEnchant item max enchant
*/
public L2ExtractableProduct(int id, int min, int max, double chance, int minEnchant, int maxEnchant)
{
_id = id;
_min = min;
_max = max;
_chance = (int) (chance * 1000);
_minEnchant = minEnchant;
_maxEnchant = maxEnchant;
}
public int getId()
{
return _id;
}
public int getMin()
{
return _min;
}
public int getMax()
{
return _max;
}
public int getChance()
{
return _chance;
}
public int getMinEnchant()
{
return _minEnchant;
}
public int getMaxEnchant()
{
return _maxEnchant;
}
}

View File

@@ -0,0 +1,52 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.List;
import com.l2jmobius.gameserver.model.holders.ItemHolder;
/**
* @author Zoey76
*/
public class L2ExtractableProductItem
{
private final List<ItemHolder> _items;
private final double _chance;
public L2ExtractableProductItem(List<ItemHolder> items, double chance)
{
_items = items;
_chance = chance;
}
/**
* @return the the production list.
*/
public List<ItemHolder> getItems()
{
return _items;
}
/**
* @return the chance of the production list.
*/
public double getChance()
{
return _chance;
}
}

View File

@@ -0,0 +1,91 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.logging.Level;
import com.l2jmobius.commons.util.Rnd;
import com.l2jmobius.gameserver.model.actor.L2Npc;
import com.l2jmobius.gameserver.model.actor.instance.L2ControllableMobInstance;
import com.l2jmobius.gameserver.model.actor.templates.L2NpcTemplate;
/**
* @author littlecrow A special spawn implementation to spawn controllable mob
*/
public class L2GroupSpawn extends L2Spawn
{
private final L2NpcTemplate _template;
public L2GroupSpawn(L2NpcTemplate mobTemplate) throws SecurityException, ClassNotFoundException, NoSuchMethodException
{
super(mobTemplate);
_template = mobTemplate;
setAmount(1);
}
public L2Npc doGroupSpawn()
{
try
{
if (_template.isType("L2Pet") || _template.isType("L2Minion"))
{
return null;
}
int newlocx = 0;
int newlocy = 0;
int newlocz = 0;
if ((getX() == 0) && (getY() == 0))
{
if (getLocationId() == 0)
{
return null;
}
return null;
}
newlocx = getX();
newlocy = getY();
newlocz = getZ();
final L2Npc mob = new L2ControllableMobInstance(_template);
mob.setCurrentHpMp(mob.getMaxHp(), mob.getMaxMp());
if (getHeading() == -1)
{
mob.setHeading(Rnd.nextInt(61794));
}
else
{
mob.setHeading(getHeading());
}
mob.setSpawn(this);
mob.spawnMe(newlocx, newlocy, newlocz);
return mob;
}
catch (Exception e)
{
LOGGER.log(Level.WARNING, "NPC class not found: " + e.getMessage(), e);
return null;
}
}
}

View File

@@ -0,0 +1,48 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.data.xml.impl.RecipeData;
public class L2ManufactureItem
{
private final int _recipeId;
private final long _cost;
private final boolean _isDwarven;
public L2ManufactureItem(int recipeId, long cost)
{
_recipeId = recipeId;
_cost = cost;
_isDwarven = RecipeData.getInstance().getRecipeList(_recipeId).isDwarvenRecipe();
}
public int getRecipeId()
{
return _recipeId;
}
public long getCost()
{
return _cost;
}
public boolean isDwarven()
{
return _isDwarven;
}
}

View File

@@ -0,0 +1,220 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import com.l2jmobius.Config;
import com.l2jmobius.commons.util.Rnd;
import com.l2jmobius.gameserver.enums.Race;
/**
* @author Nyaran
*/
public class L2MapRegion
{
private final String _name;
private final String _town;
private final int _locId;
private final int _castle;
private final int _bbs;
private List<int[]> _maps = null;
private List<Location> _spawnLocs = null;
private List<Location> _otherSpawnLocs = null;
private List<Location> _chaoticSpawnLocs = null;
private List<Location> _banishSpawnLocs = null;
private final Map<Race, String> _bannedRace = new HashMap<>();
public L2MapRegion(String name, String town, int locId, int castle, int bbs)
{
_name = name;
_town = town;
_locId = locId;
_castle = castle;
_bbs = bbs;
}
public final String getName()
{
return _name;
}
public final String getTown()
{
return _town;
}
public final int getLocId()
{
return _locId;
}
public final int getCastle()
{
return _castle;
}
public final int getBbs()
{
return _bbs;
}
public final void addMap(int x, int y)
{
if (_maps == null)
{
_maps = new ArrayList<>();
}
_maps.add(new int[]
{
x,
y
});
}
public final List<int[]> getMaps()
{
return _maps;
}
public final boolean isZoneInRegion(int x, int y)
{
if (_maps == null)
{
return false;
}
for (int[] map : _maps)
{
if ((map[0] == x) && (map[1] == y))
{
return true;
}
}
return false;
}
// Respawn
public final void addSpawn(int x, int y, int z)
{
if (_spawnLocs == null)
{
_spawnLocs = new ArrayList<>();
}
_spawnLocs.add(new Location(x, y, z));
}
public final void addOtherSpawn(int x, int y, int z)
{
if (_otherSpawnLocs == null)
{
_otherSpawnLocs = new ArrayList<>();
}
_otherSpawnLocs.add(new Location(x, y, z));
}
public final void addChaoticSpawn(int x, int y, int z)
{
if (_chaoticSpawnLocs == null)
{
_chaoticSpawnLocs = new ArrayList<>();
}
_chaoticSpawnLocs.add(new Location(x, y, z));
}
public final void addBanishSpawn(int x, int y, int z)
{
if (_banishSpawnLocs == null)
{
_banishSpawnLocs = new ArrayList<>();
}
_banishSpawnLocs.add(new Location(x, y, z));
}
public final List<Location> getSpawns()
{
return _spawnLocs;
}
public final Location getSpawnLoc()
{
if (Config.RANDOM_RESPAWN_IN_TOWN_ENABLED)
{
return _spawnLocs.get(Rnd.get(_spawnLocs.size()));
}
return _spawnLocs.get(0);
}
public final Location getOtherSpawnLoc()
{
if (_otherSpawnLocs != null)
{
if (Config.RANDOM_RESPAWN_IN_TOWN_ENABLED)
{
return _otherSpawnLocs.get(Rnd.get(_otherSpawnLocs.size()));
}
return _otherSpawnLocs.get(0);
}
return getSpawnLoc();
}
public final Location getChaoticSpawnLoc()
{
if (_chaoticSpawnLocs != null)
{
if (Config.RANDOM_RESPAWN_IN_TOWN_ENABLED)
{
return _chaoticSpawnLocs.get(Rnd.get(_chaoticSpawnLocs.size()));
}
return _chaoticSpawnLocs.get(0);
}
return getSpawnLoc();
}
public final Location getBanishSpawnLoc()
{
if (_banishSpawnLocs != null)
{
if (Config.RANDOM_RESPAWN_IN_TOWN_ENABLED)
{
return _banishSpawnLocs.get(Rnd.get(_banishSpawnLocs.size()));
}
return _banishSpawnLocs.get(0);
}
return getSpawnLoc();
}
public final void addBannedRace(String race, String point)
{
_bannedRace.put(Race.valueOf(race), point);
}
public final Map<Race, String> getBannedRace()
{
return _bannedRace;
}
}

View File

@@ -0,0 +1,135 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.commons.database.DatabaseFactory;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.network.serverpackets.IClientOutgoingPacket;
/**
* @author UnAfraid
*/
public class L2Mentee
{
private static final Logger _log = Logger.getLogger(L2Mentee.class.getName());
private final int _objectId;
private String _name;
private int _classId;
private int _currentLevel;
public L2Mentee(int objectId)
{
_objectId = objectId;
load();
}
public void load()
{
final L2PcInstance player = getPlayerInstance();
if (player == null) // Only if player is offline
{
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement("SELECT char_name, level, base_class FROM characters WHERE charId = ?"))
{
statement.setInt(1, getObjectId());
try (ResultSet rset = statement.executeQuery())
{
if (rset.next())
{
_name = rset.getString("char_name");
_classId = rset.getInt("base_class");
_currentLevel = rset.getInt("level");
}
}
}
catch (Exception e)
{
_log.log(Level.WARNING, e.getMessage(), e);
}
}
else
{
_name = player.getName();
_classId = player.getBaseClass();
_currentLevel = player.getLevel();
}
}
public int getObjectId()
{
return _objectId;
}
public String getName()
{
return _name;
}
public int getClassId()
{
if (isOnline())
{
if (getPlayerInstance().getClassId().getId() != _classId)
{
_classId = getPlayerInstance().getClassId().getId();
}
}
return _classId;
}
public int getLevel()
{
if (isOnline())
{
if (getPlayerInstance().getLevel() != _currentLevel)
{
_currentLevel = getPlayerInstance().getLevel();
}
}
return _currentLevel;
}
public L2PcInstance getPlayerInstance()
{
return L2World.getInstance().getPlayer(_objectId);
}
public boolean isOnline()
{
return (getPlayerInstance() != null) && (getPlayerInstance().isOnlineInt() > 0);
}
public int isOnlineInt()
{
return isOnline() ? getPlayerInstance().isOnlineInt() : 0;
}
public void sendPacket(IClientOutgoingPacket packet)
{
if (isOnline())
{
getPlayerInstance().sendPacket(packet);
}
}
}

View File

@@ -0,0 +1,64 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.network.NpcStringId;
/**
* @author Rayan RPG, JIV
* @since 927
*/
public class L2NpcWalkerNode extends Location
{
private final String _chatString;
private final NpcStringId _npcString;
private final int _delay;
private final boolean _runToLocation;
public L2NpcWalkerNode(int moveX, int moveY, int moveZ, int delay, boolean runToLocation, NpcStringId npcString, String chatText)
{
super(moveX, moveY, moveZ);
_delay = delay;
_runToLocation = runToLocation;
_npcString = npcString;
_chatString = ((chatText == null) ? "" : chatText);
}
public int getDelay()
{
return _delay;
}
public boolean runToLocation()
{
return _runToLocation;
}
public NpcStringId getNpcString()
{
return _npcString;
}
public String getChatText()
{
if (_npcString != null)
{
throw new IllegalStateException("npcString is defined for walker route!");
}
return _chatString;
}
}

View File

@@ -0,0 +1,950 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.atomic.AtomicInteger;
import com.l2jmobius.gameserver.enums.InstanceType;
import com.l2jmobius.gameserver.enums.ShotType;
import com.l2jmobius.gameserver.handler.ActionHandler;
import com.l2jmobius.gameserver.handler.ActionShiftHandler;
import com.l2jmobius.gameserver.handler.IActionHandler;
import com.l2jmobius.gameserver.handler.IActionShiftHandler;
import com.l2jmobius.gameserver.idfactory.IdFactory;
import com.l2jmobius.gameserver.instancemanager.InstanceManager;
import com.l2jmobius.gameserver.model.actor.L2Character;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.actor.poly.ObjectPoly;
import com.l2jmobius.gameserver.model.events.ListenersContainer;
import com.l2jmobius.gameserver.model.instancezone.Instance;
import com.l2jmobius.gameserver.model.interfaces.IDecayable;
import com.l2jmobius.gameserver.model.interfaces.IIdentifiable;
import com.l2jmobius.gameserver.model.interfaces.ILocational;
import com.l2jmobius.gameserver.model.interfaces.INamable;
import com.l2jmobius.gameserver.model.interfaces.IPositionable;
import com.l2jmobius.gameserver.model.interfaces.ISpawnable;
import com.l2jmobius.gameserver.model.interfaces.IUniqueId;
import com.l2jmobius.gameserver.model.zone.ZoneId;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.ActionFailed;
import com.l2jmobius.gameserver.network.serverpackets.DeleteObject;
import com.l2jmobius.gameserver.network.serverpackets.IClientOutgoingPacket;
import com.l2jmobius.gameserver.util.Util;
/**
* Base class for all interactive objects.
*/
public abstract class L2Object extends ListenersContainer implements IIdentifiable, INamable, ISpawnable, IUniqueId, IDecayable, IPositionable
{
/** Name */
private String _name;
/** Object ID */
private int _objectId;
/** World Region */
private L2WorldRegion _worldRegion;
/** Instance type */
private InstanceType _instanceType = null;
private volatile Map<String, Object> _scripts;
/** X coordinate */
private final AtomicInteger _x = new AtomicInteger(0);
/** Y coordinate */
private final AtomicInteger _y = new AtomicInteger(0);
/** Z coordinate */
private final AtomicInteger _z = new AtomicInteger(0);
/** Orientation */
private final AtomicInteger _heading = new AtomicInteger(0);
/** Instance id of object. 0 - Global */
private Instance _instance = null;
private boolean _isSpawned;
private boolean _isInvisible;
private boolean _isTargetable = true;
public L2Object(int objectId)
{
setInstanceType(InstanceType.L2Object);
_objectId = objectId;
}
/**
* Gets the instance type of object.
* @return the instance type
*/
public final InstanceType getInstanceType()
{
return _instanceType;
}
/**
* Sets the instance type.
* @param newInstanceType the instance type to set
*/
protected final void setInstanceType(InstanceType newInstanceType)
{
_instanceType = newInstanceType;
}
/**
* Verifies if object is of any given instance types.
* @param instanceTypes the instance types to verify
* @return {@code true} if object is of any given instance types, {@code false} otherwise
*/
public final boolean isInstanceTypes(InstanceType... instanceTypes)
{
return _instanceType.isTypes(instanceTypes);
}
public final void onAction(L2PcInstance player)
{
onAction(player, true);
}
public void onAction(L2PcInstance player, boolean interact)
{
final IActionHandler handler = ActionHandler.getInstance().getHandler(getInstanceType());
if (handler != null)
{
handler.action(player, this, interact);
}
player.sendPacket(ActionFailed.STATIC_PACKET);
}
public void onActionShift(L2PcInstance player)
{
final IActionShiftHandler handler = ActionShiftHandler.getInstance().getHandler(getInstanceType());
if (handler != null)
{
handler.action(player, this, true);
}
player.sendPacket(ActionFailed.STATIC_PACKET);
}
public void onForcedAttack(L2PcInstance player)
{
player.sendPacket(ActionFailed.STATIC_PACKET);
}
public void onSpawn()
{
broadcastInfo(); // Tempfix for invisible spawns.
}
@Override
public boolean decayMe()
{
final L2WorldRegion reg = getWorldRegion();
synchronized (this)
{
_isSpawned = false;
setWorldRegion(null);
}
L2World.getInstance().removeVisibleObject(this, reg);
L2World.getInstance().removeObject(this);
return true;
}
public void refreshID()
{
L2World.getInstance().removeObject(this);
IdFactory.getInstance().releaseId(getObjectId());
_objectId = IdFactory.getInstance().getNextId();
}
@Override
public final boolean spawnMe()
{
synchronized (this)
{
// Set the x,y,z position of the L2Object spawn and update its _worldregion
_isSpawned = true;
setWorldRegion(L2World.getInstance().getRegion(getLocation()));
// Add the L2Object spawn in the _allobjects of L2World
L2World.getInstance().storeObject(this);
// Add the L2Object spawn to _visibleObjects and if necessary to _allplayers of its L2WorldRegion
getWorldRegion().addVisibleObject(this);
}
// this can synchronize on others instances, so it's out of synchronized, to avoid deadlocks
// Add the L2Object spawn in the world as a visible object
L2World.getInstance().addVisibleObject(this, getWorldRegion());
onSpawn();
return true;
}
public final void spawnMe(int x, int y, int z)
{
synchronized (this)
{
if (x > L2World.MAP_MAX_X)
{
x = L2World.MAP_MAX_X - 5000;
}
if (x < L2World.MAP_MIN_X)
{
x = L2World.MAP_MIN_X + 5000;
}
if (y > L2World.MAP_MAX_Y)
{
y = L2World.MAP_MAX_Y - 5000;
}
if (y < L2World.MAP_MIN_Y)
{
y = L2World.MAP_MIN_Y + 5000;
}
if (z > L2World.MAP_MAX_Z)
{
z = L2World.MAP_MAX_Z - 1000;
}
if (z < L2World.MAP_MIN_Z)
{
z = L2World.MAP_MIN_Z + 1000;
}
// Set the x,y,z position of the WorldObject. If flagged with _isSpawned, setXYZ will automatically update world region, so avoid that.
setXYZ(x, y, z);
}
// Spawn and update its _worldregion
spawnMe();
}
/**
* Verify if object can be attacked.
* @return {@code true} if object can be attacked, {@code false} otherwise
*/
public boolean canBeAttacked()
{
return false;
}
public abstract boolean isAutoAttackable(L2Character attacker);
public final boolean isSpawned()
{
return getWorldRegion() != null;
}
public final void setSpawned(boolean value)
{
_isSpawned = value;
if (!_isSpawned)
{
setWorldRegion(null);
}
}
@Override
public String getName()
{
return _name;
}
public void setName(String value)
{
_name = value;
}
@Override
public final int getObjectId()
{
return _objectId;
}
public final ObjectPoly getPoly()
{
final ObjectPoly poly = getScript(ObjectPoly.class);
return (poly == null) ? addScript(new ObjectPoly(this)) : poly;
}
public abstract void sendInfo(L2PcInstance activeChar);
public void sendPacket(IClientOutgoingPacket... packets)
{
}
public void sendPacket(SystemMessageId id)
{
}
public L2PcInstance getActingPlayer()
{
return null;
}
/**
* Verify if object is instance of L2Attackable.
* @return {@code true} if object is instance of L2Attackable, {@code false} otherwise
*/
public boolean isAttackable()
{
return false;
}
/**
* Verify if object is instance of L2Character.
* @return {@code true} if object is instance of L2Character, {@code false} otherwise
*/
public boolean isCharacter()
{
return false;
}
/**
* Verify if object is instance of L2DoorInstance.
* @return {@code true} if object is instance of L2DoorInstance, {@code false} otherwise
*/
public boolean isDoor()
{
return false;
}
/**
* Verify if object is instance of L2MonsterInstance.
* @return {@code true} if object is instance of L2MonsterInstance, {@code false} otherwise
*/
public boolean isMonster()
{
return false;
}
/**
* Verify if object is instance of L2Npc.
* @return {@code true} if object is instance of L2Npc, {@code false} otherwise
*/
public boolean isNpc()
{
return false;
}
/**
* Verify if object is instance of L2PetInstance.
* @return {@code true} if object is instance of L2PetInstance, {@code false} otherwise
*/
public boolean isPet()
{
return false;
}
/**
* Verify if object is instance of L2PcInstance.
* @return {@code true} if object is instance of L2PcInstance, {@code false} otherwise
*/
public boolean isPlayer()
{
return false;
}
/**
* Verify if object is instance of L2Playable.
* @return {@code true} if object is instance of L2Playable, {@code false} otherwise
*/
public boolean isPlayable()
{
return false;
}
/**
* Verify if object is instance of L2ServitorInstance.
* @return {@code true} if object is instance of L2ServitorInstance, {@code false} otherwise
*/
public boolean isServitor()
{
return false;
}
/**
* Verify if object is instance of L2Summon.
* @return {@code true} if object is instance of L2Summon, {@code false} otherwise
*/
public boolean isSummon()
{
return false;
}
/**
* Verify if object is instance of L2TrapInstance.
* @return {@code true} if object is instance of L2TrapInstance, {@code false} otherwise
*/
public boolean isTrap()
{
return false;
}
/**
* Verify if object is instance of L2ItemInstance.
* @return {@code true} if object is instance of L2ItemInstance, {@code false} otherwise
*/
public boolean isItem()
{
return false;
}
/**
* Verifies if the object is a walker NPC.
* @return {@code true} if object is a walker NPC, {@code false} otherwise
*/
public boolean isWalker()
{
return false;
}
/**
* Verifies if this object is a vehicle.
* @return {@code true} if object is Vehicle, {@code false} otherwise
*/
public boolean isVehicle()
{
return false;
}
public void setTargetable(boolean targetable)
{
if (_isTargetable != targetable)
{
_isTargetable = targetable;
if (!targetable)
{
L2World.getInstance().getVisibleObjects(this, L2Character.class, creature -> this == creature.getTarget()).forEach(creature ->
{
creature.setTarget(null);
creature.abortAttack();
creature.abortCast();
});
}
}
}
/**
* @return {@code true} if the object can be targetted by other players, {@code false} otherwise.
*/
public boolean isTargetable()
{
return _isTargetable;
}
/**
* Check if the object is in the given zone Id.
* @param zone the zone Id to check
* @return {@code true} if the object is in that zone Id
*/
public boolean isInsideZone(ZoneId zone)
{
return false;
}
/**
* Check if current object has charged shot.
* @param type of the shot to be checked.
* @return {@code true} if the object has charged shot
*/
public boolean isChargedShot(ShotType type)
{
return false;
}
/**
* Charging shot into the current object.
* @param type of the shot to be charged.
* @param charged
*/
public void setChargedShot(ShotType type, boolean charged)
{
}
/**
* Try to recharge a shot.
* @param physical skill are using Soul shots.
* @param magical skill are using Spirit shots.
* @param fish
*/
public void rechargeShots(boolean physical, boolean magical, boolean fish)
{
}
/**
* @param <T>
* @param script
* @return
*/
public final <T> T addScript(T script)
{
if (_scripts == null)
{
// Double-checked locking
synchronized (this)
{
if (_scripts == null)
{
_scripts = new ConcurrentHashMap<>();
}
}
}
_scripts.put(script.getClass().getName(), script);
return script;
}
/**
* @param <T>
* @param script
* @return
*/
@SuppressWarnings("unchecked")
public final <T> T removeScript(Class<T> script)
{
if (_scripts == null)
{
return null;
}
return (T) _scripts.remove(script.getName());
}
/**
* @param <T>
* @param script
* @return
*/
@SuppressWarnings("unchecked")
public final <T> T getScript(Class<T> script)
{
if (_scripts == null)
{
return null;
}
return (T) _scripts.get(script.getName());
}
public void removeStatusListener(L2Character object)
{
}
protected void badCoords()
{
if (isCharacter())
{
decayMe();
}
else if (isPlayer())
{
((L2Character) this).teleToLocation(new Location(0, 0, 0), false);
((L2Character) this).sendMessage("Error with your coords, Please ask a GM for help!");
}
}
public final void setXYZInvisible(int x, int y, int z)
{
if (x > L2World.MAP_MAX_X)
{
x = L2World.MAP_MAX_X - 5000;
}
if (x < L2World.MAP_MIN_X)
{
x = L2World.MAP_MIN_X + 5000;
}
if (y > L2World.MAP_MAX_Y)
{
y = L2World.MAP_MAX_Y - 5000;
}
if (y < L2World.MAP_MIN_Y)
{
y = L2World.MAP_MIN_Y + 5000;
}
setXYZ(x, y, z);
setSpawned(false);
}
public final void setLocationInvisible(ILocational loc)
{
setXYZInvisible(loc.getX(), loc.getY(), loc.getZ());
}
public final L2WorldRegion getWorldRegion()
{
return _worldRegion;
}
public void setWorldRegion(L2WorldRegion value)
{
_worldRegion = value;
}
/**
* Gets the X coordinate.
* @return the X coordinate
*/
@Override
public int getX()
{
return _x.get();
}
/**
* Gets the Y coordinate.
* @return the Y coordinate
*/
@Override
public int getY()
{
return _y.get();
}
/**
* Gets the Z coordinate.
* @return the Z coordinate
*/
@Override
public int getZ()
{
return _z.get();
}
/**
* Gets the heading.
* @return the heading
*/
@Override
public int getHeading()
{
return _heading.get();
}
/**
* Gets the instance ID.
* @return the instance ID
*/
public int getInstanceId()
{
final Instance instance = _instance;
return (instance != null) ? instance.getId() : 0;
}
/**
* Check if object is inside instance world.
* @return {@code true} when object is inside any instance world, otherwise {@code false}
*/
public boolean isInInstance()
{
return _instance != null;
}
/**
* Get instance world where object is currently located.
* @return {@link Instance} if object is inside instance world, otherwise {@code null}
*/
public Instance getInstanceWorld()
{
return _instance;
}
/**
* Gets the location object.
* @return the location object
*/
@Override
public Location getLocation()
{
return new Location(getX(), getY(), getZ(), getHeading());
}
/**
* Sets the X coordinate
* @param newX the X coordinate
*/
@Override
public void setX(int newX)
{
_x.set(newX);
}
/**
* Sets the Y coordinate
* @param newY the Y coordinate
*/
@Override
public void setY(int newY)
{
_y.set(newY);
}
/**
* Sets the Z coordinate
* @param newZ the Z coordinate
*/
@Override
public void setZ(int newZ)
{
_z.set(newZ);
}
/**
* Sets the x, y, z coordinate.
* @param newX the X coordinate
* @param newY the Y coordinate
* @param newZ the Z coordinate
*/
@Override
public void setXYZ(int newX, int newY, int newZ)
{
setX(newX);
setY(newY);
setZ(newZ);
try
{
if (_isSpawned)
{
final L2WorldRegion oldRegion = getWorldRegion();
final L2WorldRegion newRegion = L2World.getInstance().getRegion(this);
if (newRegion != oldRegion)
{
if (oldRegion != null)
{
oldRegion.removeVisibleObject(this);
}
newRegion.addVisibleObject(this);
L2World.getInstance().switchRegion(this, newRegion);
setWorldRegion(newRegion);
}
}
}
catch (Exception e)
{
badCoords();
}
}
/**
* Sets the x, y, z coordinate.
* @param loc the location object
*/
@Override
public void setXYZ(ILocational loc)
{
setXYZ(loc.getX(), loc.getY(), loc.getZ());
}
/**
* Sets heading of object.
* @param newHeading the new heading
*/
@Override
public void setHeading(int newHeading)
{
_heading.set(newHeading);
}
/**
* Sets instance for current object by instance ID.<br>
* @param id ID of instance world which should be set (0 means normal world)
*/
public void setInstanceById(int id)
{
final Instance instance = InstanceManager.getInstance().getInstance(id);
if ((id != 0) && (instance == null))
{
return;
}
setInstance(instance);
}
/**
* Sets instance where current object belongs.
* @param newInstance new instance world for object
*/
public synchronized void setInstance(Instance newInstance)
{
// Check if new and old instances are identical
if (_instance == newInstance)
{
return;
}
// Leave old instance
if (_instance != null)
{
_instance.onInstanceChange(this, false);
}
// Set new instance
_instance = newInstance;
// Enter into new instance
if (newInstance != null)
{
newInstance.onInstanceChange(this, true);
}
}
/**
* Sets location of object.
* @param loc the location object
*/
@Override
public void setLocation(Location loc)
{
_x.set(loc.getX());
_y.set(loc.getY());
_z.set(loc.getZ());
_heading.set(loc.getHeading());
}
/**
* Calculates distance between this L2Object and given x, y , z.
* @param x the X coordinate
* @param y the Y coordinate
* @param z the Z coordinate
* @param includeZAxis if {@code true} Z axis will be included
* @param squared if {@code true} return will be squared
* @return distance between object and given x, y, z.
*/
public final double calculateDistance(int x, int y, int z, boolean includeZAxis, boolean squared)
{
final double distance = Math.pow(x - getX(), 2) + Math.pow(y - getY(), 2) + (includeZAxis ? Math.pow(z - getZ(), 2) : 0);
return (squared) ? distance : Math.sqrt(distance);
}
/**
* Calculates distance between this L2Object and given location.
* @param loc the location object
* @param includeZAxis if {@code true} Z axis will be included
* @param squared if {@code true} return will be squared
* @return distance between object and given location.
*/
public final double calculateDistance(ILocational loc, boolean includeZAxis, boolean squared)
{
return calculateDistance(loc.getX(), loc.getY(), loc.getZ(), includeZAxis, squared);
}
/**
* Calculates the angle in degrees from this object to the given object.<br>
* The return value can be described as how much this object has to turn<br>
* to have the given object directly in front of it.
* @param target the object to which to calculate the angle
* @return the angle this object has to turn to have the given object in front of it
*/
public final double calculateDirectionTo(ILocational target)
{
int heading = Util.calculateHeadingFrom(this, target) - getHeading();
if (heading < 0)
{
heading = 65535 + heading;
}
return Util.convertHeadingToDegree(heading);
}
/**
* @return {@code true} if this object is invisible, {@code false} otherwise.
*/
public boolean isInvisible()
{
return _isInvisible;
}
/**
* Sets this object as invisible or not
* @param invis
*/
public void setInvisible(boolean invis)
{
_isInvisible = invis;
if (invis)
{
final DeleteObject deletePacket = new DeleteObject(this);
L2World.getInstance().forEachVisibleObject(this, L2PcInstance.class, player ->
{
if (!isVisibleFor(player))
{
player.sendPacket(deletePacket);
}
});
}
// Broadcast information regarding the object to those which are suppose to see.
broadcastInfo();
}
/**
* @param player
* @return {@code true} if player can see an invisible object if it's invisible, {@code false} otherwise.
*/
public boolean isVisibleFor(L2PcInstance player)
{
return !isInvisible() || player.canOverrideCond(PcCondOverride.SEE_ALL_PLAYERS);
}
/**
* Broadcasts describing info to known players.
*/
public void broadcastInfo()
{
L2World.getInstance().forEachVisibleObject(this, L2PcInstance.class, player ->
{
if (isVisibleFor(player))
{
sendInfo(player);
}
});
}
public boolean isInvul()
{
return false;
}
public boolean isInSurroundingRegion(L2Object worldObject)
{
if (worldObject == null)
{
return false;
}
final L2WorldRegion worldRegion1 = worldObject.getWorldRegion();
if (worldRegion1 == null)
{
return false;
}
final L2WorldRegion worldRegion2 = getWorldRegion();
if (worldRegion2 == null)
{
return false;
}
return worldRegion1.isSurroundingRegion(worldRegion2);
}
@Override
public boolean equals(Object obj)
{
return ((obj instanceof L2Object) && (((L2Object) obj).getObjectId() == getObjectId()));
}
@Override
public String toString()
{
return (getClass().getSimpleName() + ":" + getName() + "[" + getObjectId() + "]");
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,271 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import com.l2jmobius.gameserver.data.xml.impl.SkillData;
import com.l2jmobius.gameserver.model.holders.SkillHolder;
/**
* Class hold information about basic pet stats which are same on each level.
* @author JIV
*/
public class L2PetData
{
private final Map<Integer, L2PetLevelData> _levelStats = new HashMap<>();
private final List<L2PetSkillLearn> _skills = new ArrayList<>();
private final int _npcId;
private final int _itemId;
private int _load = 20000;
private int _hungryLimit = 1;
private int _minlvl = Byte.MAX_VALUE;
private int _maxlvl = 0;
private boolean _syncLevel = false;
private final List<Integer> _food = new ArrayList<>();
public L2PetData(int npcId, int itemId)
{
_npcId = npcId;
_itemId = itemId;
}
/**
* @return the npc id representing this pet.
*/
public int getNpcId()
{
return _npcId;
}
/**
* @return the item id that could summon this pet.
*/
public int getItemId()
{
return _itemId;
}
/**
* @param level the pet's level.
* @param data the pet's data.
*/
public void addNewStat(int level, L2PetLevelData data)
{
if (_minlvl > level)
{
_minlvl = level;
}
if (_maxlvl < (level - 1))
{
_maxlvl = level - 1;
}
_levelStats.put(level, data);
}
/**
* @param petLevel the pet's level.
* @return the pet data associated to that pet level.
*/
public L2PetLevelData getPetLevelData(int petLevel)
{
return _levelStats.get(petLevel);
}
/**
* @return the pet's weight load.
*/
public int getLoad()
{
return _load;
}
/**
* @return the pet's hunger limit.
*/
public int getHungryLimit()
{
return _hungryLimit;
}
/**
* @return {@code true} if pet synchronizes it's level with his master's
*/
public boolean isSynchLevel()
{
return _syncLevel;
}
/**
* @return the pet's minimum level.
*/
public int getMinLevel()
{
return _minlvl;
}
/**
* @return the pet's maximum level.
*/
public int getMaxLevel()
{
return _maxlvl;
}
/**
* @return the pet's food list.
*/
public List<Integer> getFood()
{
return _food;
}
/**
* @param foodId the pet's food Id to add.
*/
public void addFood(Integer foodId)
{
_food.add(foodId);
}
/**
* @param load the weight load to set.
*/
public void setLoad(int load)
{
_load = load;
}
/**
* @param limit the hunger limit to set.
*/
public void setHungryLimit(int limit)
{
_hungryLimit = limit;
}
/**
* @param val synchronizes level with master or not.
*/
public void setSyncLevel(boolean val)
{
_syncLevel = val;
}
// SKILS
/**
* @param skillId the skill Id to add.
* @param skillLvl the skill level.
* @param petLvl the pet's level when this skill is available.
*/
public void addNewSkill(int skillId, int skillLvl, int petLvl)
{
_skills.add(new L2PetSkillLearn(skillId, skillLvl, petLvl));
}
/**
* TODO: Simplify this.
* @param skillId the skill Id.
* @param petLvl the pet level.
* @return the level of the skill for the given skill Id and pet level.
*/
public int getAvailableLevel(int skillId, int petLvl)
{
int lvl = 0;
boolean found = false;
for (L2PetSkillLearn temp : _skills)
{
if (temp.getSkillId() != skillId)
{
continue;
}
found = true;
if (temp.getSkillLevel() == 0)
{
if (petLvl < 70)
{
lvl = (petLvl / 10);
if (lvl <= 0)
{
lvl = 1;
}
}
else
{
lvl = (7 + ((petLvl - 70) / 5));
}
// formula usable for skill that have 10 or more skill levels
final int maxLvl = SkillData.getInstance().getMaxLevel(temp.getSkillId());
if (lvl > maxLvl)
{
lvl = maxLvl;
}
break;
}
else if (temp.getMinLevel() <= petLvl)
{
if (temp.getSkillLevel() > lvl)
{
lvl = temp.getSkillLevel();
}
}
}
if (found && (lvl == 0))
{
return 1;
}
return lvl;
}
/**
* @return the list with the pet's skill data.
*/
public List<L2PetSkillLearn> getAvailableSkills()
{
return _skills;
}
public static final class L2PetSkillLearn extends SkillHolder
{
private final int _minLevel;
/**
* @param id the skill Id.
* @param lvl the skill level.
* @param minLvl the minimum level when this skill is available.
*/
public L2PetSkillLearn(int id, int lvl, int minLvl)
{
super(id, lvl);
_minLevel = minLvl;
}
/**
* @return the minimum level for the pet to get the skill.
*/
public int getMinLevel()
{
return _minLevel;
}
}
}

View File

@@ -0,0 +1,218 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.stats.Stats;
/**
* Stats definition for each pet level.
* @author JIV, Zoey76
*/
public class L2PetLevelData
{
private final int _ownerExpTaken;
private final int _petFeedBattle;
private final int _petFeedNormal;
private final float _petMAtk;
private final long _petMaxExp;
private final int _petMaxFeed;
private final float _petMaxHP;
private final float _petMaxMP;
private final float _petMDef;
private final float _petPAtk;
private final float _petPDef;
private final float _petRegenHP;
private final float _petRegenMP;
private final short _petSoulShot;
private final short _petSpiritShot;
private final double _walkSpeedOnRide;
private final double _runSpeedOnRide;
private final double _slowSwimSpeedOnRide;
private final double _fastSwimSpeedOnRide;
private final double _slowFlySpeedOnRide;
private final double _fastFlySpeedOnRide;
public L2PetLevelData(StatsSet set)
{
_ownerExpTaken = set.getInt("get_exp_type");
_petMaxExp = set.getLong("exp");
_petMaxHP = set.getFloat("org_hp");
_petMaxMP = set.getFloat("org_mp");
_petPAtk = set.getFloat("org_pattack");
_petPDef = set.getFloat("org_pdefend");
_petMAtk = set.getFloat("org_mattack");
_petMDef = set.getFloat("org_mdefend");
_petMaxFeed = set.getInt("max_meal");
_petFeedBattle = set.getInt("consume_meal_in_battle");
_petFeedNormal = set.getInt("consume_meal_in_normal");
_petRegenHP = set.getFloat("org_hp_regen");
_petRegenMP = set.getFloat("org_mp_regen");
_petSoulShot = set.getShort("soulshot_count");
_petSpiritShot = set.getShort("spiritshot_count");
_walkSpeedOnRide = set.getDouble("walkSpeedOnRide", 0);
_runSpeedOnRide = set.getDouble("runSpeedOnRide", 0);
_slowSwimSpeedOnRide = set.getDouble("slowSwimSpeedOnRide", 0);
_fastSwimSpeedOnRide = set.getDouble("fastSwimSpeedOnRide", 0);
_slowFlySpeedOnRide = set.getDouble("slowFlySpeedOnRide", 0);
_fastFlySpeedOnRide = set.getDouble("fastFlySpeedOnRide", 0);
}
/**
* @return the owner's experience points consumed by the pet.
*/
public int getOwnerExpTaken()
{
return _ownerExpTaken;
}
/**
* @return the pet's food consume rate at battle state.
*/
public int getPetFeedBattle()
{
return _petFeedBattle;
}
/**
* @return the pet's food consume rate at normal state.
*/
public int getPetFeedNormal()
{
return _petFeedNormal;
}
/**
* @return the pet's Magical Attack.
*/
public float getPetMAtk()
{
return _petMAtk;
}
/**
* @return the pet's maximum experience points.
*/
public long getPetMaxExp()
{
return _petMaxExp;
}
/**
* @return the pet's maximum feed points.
*/
public int getPetMaxFeed()
{
return _petMaxFeed;
}
/**
* @return the pet's maximum HP.
*/
public float getPetMaxHP()
{
return _petMaxHP;
}
/**
* @return the pet's maximum MP.
*/
public float getPetMaxMP()
{
return _petMaxMP;
}
/**
* @return the pet's Magical Defense.
*/
public float getPetMDef()
{
return _petMDef;
}
/**
* @return the pet's Physical Attack.
*/
public float getPetPAtk()
{
return _petPAtk;
}
/**
* @return the pet's Physical Defense.
*/
public float getPetPDef()
{
return _petPDef;
}
/**
* @return the pet's HP regeneration rate.
*/
public float getPetRegenHP()
{
return _petRegenHP;
}
/**
* @return the pet's MP regeneration rate.
*/
public float getPetRegenMP()
{
return _petRegenMP;
}
/**
* @return the pet's soulshot use count.
*/
public short getPetSoulShot()
{
return _petSoulShot;
}
/**
* @return the pet's spiritshot use count.
*/
public short getPetSpiritShot()
{
return _petSpiritShot;
}
/**
* @param stat movement type
* @return the base riding speed of given movement type.
*/
public double getSpeedOnRide(Stats stat)
{
switch (stat)
{
case WALK_SPEED:
return _walkSpeedOnRide;
case RUN_SPEED:
return _runSpeedOnRide;
case SWIM_WALK_SPEED:
return _slowSwimSpeedOnRide;
case SWIM_RUN_SPEED:
return _fastSwimSpeedOnRide;
case FLY_RUN_SPEED:
return _slowFlySpeedOnRide;
case FLY_WALK_SPEED:
return _fastFlySpeedOnRide;
}
return 0;
}
}

View File

@@ -0,0 +1,54 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
** @author Gnacik
*/
public class L2PremiumItem
{
private final int _itemId;
private long _count;
private final String _sender;
public L2PremiumItem(int itemid, long count, String sender)
{
_itemId = itemid;
_count = count;
_sender = sender;
}
public void updateCount(long newcount)
{
_count = newcount;
}
public int getItemId()
{
return _itemId;
}
public long getCount()
{
return _count;
}
public String getSender()
{
return _sender;
}
}

View File

@@ -0,0 +1,132 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.network.serverpackets.RadarControl;
/**
* @author dalrond
*/
public final class L2Radar
{
private final L2PcInstance _player;
private final Set<RadarMarker> _markers = ConcurrentHashMap.newKeySet();
public L2Radar(L2PcInstance player)
{
_player = player;
}
// Add a marker to player's radar
public void addMarker(int x, int y, int z)
{
final RadarMarker newMarker = new RadarMarker(x, y, z);
_markers.add(newMarker);
_player.sendPacket(new RadarControl(2, 2, x, y, z));
_player.sendPacket(new RadarControl(0, 1, x, y, z));
}
// Remove a marker from player's radar
public void removeMarker(int x, int y, int z)
{
for (RadarMarker rm : _markers)
{
if ((rm._x == x) && (rm._y == y) && (rm._z == z))
{
_markers.remove(rm);
}
}
_player.sendPacket(new RadarControl(1, 1, x, y, z));
}
public void removeAllMarkers()
{
for (RadarMarker tempMarker : _markers)
{
_player.sendPacket(new RadarControl(2, 2, tempMarker._x, tempMarker._y, tempMarker._z));
}
_markers.clear();
}
public void loadMarkers()
{
_player.sendPacket(new RadarControl(2, 2, _player.getX(), _player.getY(), _player.getZ()));
for (RadarMarker tempMarker : _markers)
{
_player.sendPacket(new RadarControl(0, 1, tempMarker._x, tempMarker._y, tempMarker._z));
}
}
public static class RadarMarker
{
// Simple class to model radar points.
public int _type, _x, _y, _z;
public RadarMarker(int type, int x, int y, int z)
{
_type = type;
_x = x;
_y = y;
_z = z;
}
public RadarMarker(int x, int y, int z)
{
_type = 1;
_x = x;
_y = y;
_z = z;
}
@Override
public int hashCode()
{
final int prime = 31;
int result = 1;
result = (prime * result) + _type;
result = (prime * result) + _x;
result = (prime * result) + _y;
result = (prime * result) + _z;
return result;
}
@Override
public boolean equals(Object obj)
{
if (this == obj)
{
return true;
}
if (!(obj instanceof RadarMarker))
{
return false;
}
final RadarMarker other = (RadarMarker) obj;
if ((_type != other._type) || (_x != other._x) || (_y != other._y) || (_z != other._z))
{
return false;
}
return true;
}
}
}

View File

@@ -0,0 +1,57 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* This class describes a RecipeList component (1 line of the recipe : Item-Quantity needed).
*/
public class L2RecipeInstance
{
/** The Identifier of the item needed in the L2RecipeInstance */
private final int _itemId;
/** The item quantity needed in the L2RecipeInstance */
private final int _quantity;
/**
* Constructor of L2RecipeInstance (create a new line in a RecipeList).
* @param itemId
* @param quantity
*/
public L2RecipeInstance(int itemId, int quantity)
{
_itemId = itemId;
_quantity = quantity;
}
/**
* @return the Identifier of the L2RecipeInstance Item needed.
*/
public int getItemId()
{
return _itemId;
}
/**
* @return the Item quantity needed of the L2RecipeInstance.
*/
public int getQuantity()
{
return _quantity;
}
}

View File

@@ -0,0 +1,242 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* This class describes a Recipe used by Dwarf to craft Item. All L2RecipeList are made of L2RecipeInstance (1 line of the recipe : Item-Quantity needed).
*/
public class L2RecipeList
{
/** The table containing all L2RecipeInstance (1 line of the recipe : Item-Quantity needed) of the L2RecipeList */
private L2RecipeInstance[] _recipes;
/** The table containing all L2RecipeStatInstance for the statUse parameter of the L2RecipeList */
private L2RecipeStatInstance[] _statUse;
/** The table containing all L2RecipeStatInstance for the altStatChange parameter of the L2RecipeList */
private L2RecipeStatInstance[] _altStatChange;
/** The Identifier of the Instance */
private final int _id;
/** The crafting level needed to use this L2RecipeList */
private final int _level;
/** The Identifier of the L2RecipeList */
private final int _recipeId;
/** The name of the L2RecipeList */
private final String _recipeName;
/** The crafting success rate when using the L2RecipeList */
private final int _successRate;
/** The Identifier of the Item crafted with this L2RecipeList */
private final int _itemId;
/** The quantity of Item crafted when using this L2RecipeList */
private final int _count;
/** The Identifier of the Rare Item crafted with this L2RecipeList */
private int _rareItemId;
/** The quantity of Rare Item crafted when using this L2RecipeList */
private int _rareCount;
/** The chance of Rare Item crafted when using this L2RecipeList */
private int _rarity;
/** If this a common or a dwarven recipe */
private final boolean _isDwarvenRecipe;
/**
* Constructor of L2RecipeList (create a new Recipe).
* @param set
* @param haveRare
*/
public L2RecipeList(StatsSet set, boolean haveRare)
{
_recipes = new L2RecipeInstance[0];
_statUse = new L2RecipeStatInstance[0];
_altStatChange = new L2RecipeStatInstance[0];
_id = set.getInt("id");
_level = set.getInt("craftLevel");
_recipeId = set.getInt("recipeId");
_recipeName = set.getString("recipeName");
_successRate = set.getInt("successRate");
_itemId = set.getInt("itemId");
_count = set.getInt("count");
if (haveRare)
{
_rareItemId = set.getInt("rareItemId");
_rareCount = set.getInt("rareCount");
_rarity = set.getInt("rarity");
}
_isDwarvenRecipe = set.getBoolean("isDwarvenRecipe");
}
/**
* Add a L2RecipeInstance to the L2RecipeList (add a line Item-Quantity needed to the Recipe).
* @param recipe
*/
public void addRecipe(L2RecipeInstance recipe)
{
final int len = _recipes.length;
final L2RecipeInstance[] tmp = new L2RecipeInstance[len + 1];
System.arraycopy(_recipes, 0, tmp, 0, len);
tmp[len] = recipe;
_recipes = tmp;
}
/**
* Add a L2RecipeStatInstance of the statUse parameter to the L2RecipeList.
* @param statUse
*/
public void addStatUse(L2RecipeStatInstance statUse)
{
final int len = _statUse.length;
final L2RecipeStatInstance[] tmp = new L2RecipeStatInstance[len + 1];
System.arraycopy(_statUse, 0, tmp, 0, len);
tmp[len] = statUse;
_statUse = tmp;
}
/**
* Add a L2RecipeStatInstance of the altStatChange parameter to the L2RecipeList.
* @param statChange
*/
public void addAltStatChange(L2RecipeStatInstance statChange)
{
final int len = _altStatChange.length;
final L2RecipeStatInstance[] tmp = new L2RecipeStatInstance[len + 1];
System.arraycopy(_altStatChange, 0, tmp, 0, len);
tmp[len] = statChange;
_altStatChange = tmp;
}
/**
* @return the Identifier of the Instance.
*/
public int getId()
{
return _id;
}
/**
* @return the crafting level needed to use this L2RecipeList.
*/
public int getLevel()
{
return _level;
}
/**
* @return the Identifier of the L2RecipeList.
*/
public int getRecipeId()
{
return _recipeId;
}
/**
* @return the name of the L2RecipeList.
*/
public String getRecipeName()
{
return _recipeName;
}
/**
* @return the crafting success rate when using the L2RecipeList.
*/
public int getSuccessRate()
{
return _successRate;
}
/**
* @return the Identifier of the Item crafted with this L2RecipeList.
*/
public int getItemId()
{
return _itemId;
}
/**
* @return the quantity of Item crafted when using this L2RecipeList.
*/
public int getCount()
{
return _count;
}
/**
* @return the Identifier of the Rare Item crafted with this L2RecipeList.
*/
public int getRareItemId()
{
return _rareItemId;
}
/**
* @return the quantity of Rare Item crafted when using this L2RecipeList.
*/
public int getRareCount()
{
return _rareCount;
}
/**
* @return the chance of Rare Item crafted when using this L2RecipeList.
*/
public int getRarity()
{
return _rarity;
}
/**
* @return {@code true} if this a Dwarven recipe or {@code false} if its a Common recipe
*/
public boolean isDwarvenRecipe()
{
return _isDwarvenRecipe;
}
/**
* @return the table containing all L2RecipeInstance (1 line of the recipe : Item-Quantity needed) of the L2RecipeList.
*/
public L2RecipeInstance[] getRecipes()
{
return _recipes;
}
/**
* @return the table containing all L2RecipeStatInstance of the statUse parameter of the L2RecipeList.
*/
public L2RecipeStatInstance[] getStatUse()
{
return _statUse;
}
/**
* @return the table containing all L2RecipeStatInstance of the AltStatChange parameter of the L2RecipeList.
*/
public L2RecipeStatInstance[] getAltStatChange()
{
return _altStatChange;
}
}

View File

@@ -0,0 +1,59 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.enums.StatType;
/**
* This class describes a RecipeList statUse and altStatChange component.
*/
public class L2RecipeStatInstance
{
/** The Identifier of the statType */
private final StatType _type;
/** The value of the statType */
private final int _value;
/**
* Constructor of L2RecipeStatInstance.
* @param type
* @param value
*/
public L2RecipeStatInstance(String type, int value)
{
_type = Enum.valueOf(StatType.class, type);
_value = value;
}
/**
* @return the the type of the L2RecipeStatInstance.
*/
public StatType getType()
{
return _type;
}
/**
* @return the value of the L2RecipeStatInstance.
*/
public int getValue()
{
return _value;
}
}

View File

@@ -0,0 +1,148 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.clientpackets.IClientIncomingPacket;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
/**
* This class manages requests (transactions) between two L2PcInstance.
* @author kriau
*/
public class L2Request
{
private static final int REQUEST_TIMEOUT = 15; // in secs
protected L2PcInstance _player;
protected L2PcInstance _partner;
protected boolean _isRequestor;
protected boolean _isAnswerer;
protected IClientIncomingPacket _requestPacket;
public L2Request(L2PcInstance player)
{
_player = player;
}
protected void clear()
{
_partner = null;
_requestPacket = null;
_isRequestor = false;
_isAnswerer = false;
}
/**
* Set the L2PcInstance member of a transaction (ex : FriendInvite, JoinAlly, JoinParty...).
* @param partner
*/
private synchronized void setPartner(L2PcInstance partner)
{
_partner = partner;
}
/**
* @return the L2PcInstance member of a transaction (ex : FriendInvite, JoinAlly, JoinParty...).
*/
public L2PcInstance getPartner()
{
return _partner;
}
/**
* Set the packet incomed from requester.
* @param packet
*/
private synchronized void setRequestPacket(IClientIncomingPacket packet)
{
_requestPacket = packet;
}
/**
* Return the packet originally incomed from requester.
* @return
*/
public IClientIncomingPacket getRequestPacket()
{
return _requestPacket;
}
/**
* Checks if request can be made and in success case puts both PC on request state.
* @param partner
* @param packet
* @return
*/
public synchronized boolean setRequest(L2PcInstance partner, IClientIncomingPacket packet)
{
if (partner == null)
{
_player.sendPacket(SystemMessageId.YOU_HAVE_INVITED_THE_WRONG_TARGET);
return false;
}
if (partner.getRequest().isProcessingRequest())
{
final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.C1_IS_ON_ANOTHER_TASK_PLEASE_TRY_AGAIN_LATER);
sm.addString(partner.getName());
_player.sendPacket(sm);
return false;
}
if (isProcessingRequest())
{
_player.sendPacket(SystemMessageId.WAITING_FOR_ANOTHER_REPLY);
return false;
}
_partner = partner;
_requestPacket = packet;
setOnRequestTimer(true);
_partner.getRequest().setPartner(_player);
_partner.getRequest().setRequestPacket(packet);
_partner.getRequest().setOnRequestTimer(false);
return true;
}
private void setOnRequestTimer(boolean isRequestor)
{
_isRequestor = isRequestor;
_isAnswerer = !isRequestor;
ThreadPoolManager.getInstance().scheduleGeneral(() -> clear(), REQUEST_TIMEOUT * 1000);
}
/**
* Clears PC request state. Should be called after answer packet receive.
*/
public void onRequestResponse()
{
if (_partner != null)
{
_partner.getRequest().clear();
}
clear();
}
/**
* @return {@code true} if a transaction is in progress.
*/
public boolean isProcessingRequest()
{
return _partner != null;
}
}

View File

@@ -0,0 +1,137 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.Config;
import com.l2jmobius.gameserver.datatables.ItemTable;
import com.l2jmobius.gameserver.model.items.L2Item;
public final class L2Seed
{
private final int _seedId;
private final int _cropId; // crop type
private final int _level; // seed level
private final int _matureId; // mature crop type
private final int _reward1;
private final int _reward2;
private final int _castleId; // id of manor (castle id) where seed can be farmed
private final boolean _isAlternative;
private final int _limitSeeds;
private final int _limitCrops;
private final int _seedReferencePrice;
private final int _cropReferencePrice;
public L2Seed(StatsSet set)
{
_cropId = set.getInt("id");
_seedId = set.getInt("seedId");
_level = set.getInt("level");
_matureId = set.getInt("mature_Id");
_reward1 = set.getInt("reward1");
_reward2 = set.getInt("reward2");
_castleId = set.getInt("castleId");
_isAlternative = set.getBoolean("alternative");
_limitCrops = set.getInt("limit_crops");
_limitSeeds = set.getInt("limit_seed");
// Set prices
L2Item item = ItemTable.getInstance().getTemplate(_cropId);
_cropReferencePrice = (item != null) ? item.getReferencePrice() : 1;
item = ItemTable.getInstance().getTemplate(_seedId);
_seedReferencePrice = (item != null) ? item.getReferencePrice() : 1;
}
public final int getCastleId()
{
return _castleId;
}
public final int getSeedId()
{
return _seedId;
}
public final int getCropId()
{
return _cropId;
}
public final int getMatureId()
{
return _matureId;
}
public final int getReward(int type)
{
return (type == 1) ? _reward1 : _reward2;
}
public final int getLevel()
{
return _level;
}
public final boolean isAlternative()
{
return _isAlternative;
}
public final int getSeedLimit()
{
return _limitSeeds * Config.RATE_DROP_MANOR;
}
public final int getCropLimit()
{
return _limitCrops * Config.RATE_DROP_MANOR;
}
public final int getSeedReferencePrice()
{
return _seedReferencePrice;
}
public final int getSeedMaxPrice()
{
return _seedReferencePrice * 10;
}
public final int getSeedMinPrice()
{
return (int) (_seedReferencePrice * 0.6);
}
public final int getCropReferencePrice()
{
return _cropReferencePrice;
}
public final int getCropMaxPrice()
{
return _cropReferencePrice * 10;
}
public final int getCropMinPrice()
{
return (int) (_cropReferencePrice * 0.6);
}
@Override
public final String toString()
{
return "SeedData [_id=" + _seedId + ", _level=" + _level + ", _crop=" + _cropId + ", _mature=" + _matureId + ", _type1=" + _reward1 + ", _type2=" + _reward2 + ", _manorId=" + _castleId + ", _isAlternative=" + _isAlternative + ", _limitSeeds=" + _limitSeeds + ", _limitCrops=" + _limitCrops + "]";
}
}

View File

@@ -0,0 +1,86 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import com.l2jmobius.gameserver.enums.SiegeClanType;
import com.l2jmobius.gameserver.model.actor.L2Npc;
public class L2SiegeClan
{
private int _clanId = 0;
private final Set<L2Npc> _flags = ConcurrentHashMap.newKeySet();
private SiegeClanType _type;
public L2SiegeClan(int clanId, SiegeClanType type)
{
_clanId = clanId;
_type = type;
}
public int getNumFlags()
{
return _flags.size();
}
public void addFlag(L2Npc flag)
{
_flags.add(flag);
}
public boolean removeFlag(L2Npc flag)
{
if (flag == null)
{
return false;
}
flag.deleteMe();
return getFlag().remove(flag);
}
public void removeFlags()
{
for (L2Npc flag : getFlag())
{
removeFlag(flag);
}
}
public final int getClanId()
{
return _clanId;
}
public final Set<L2Npc> getFlag()
{
return _flags;
}
public SiegeClanType getType()
{
return _type;
}
public void setType(SiegeClanType setType)
{
_type = setType;
}
}

View File

@@ -0,0 +1,283 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;
import com.l2jmobius.gameserver.data.xml.impl.SkillData;
import com.l2jmobius.gameserver.enums.Race;
import com.l2jmobius.gameserver.model.base.SocialClass;
import com.l2jmobius.gameserver.model.holders.ItemHolder;
import com.l2jmobius.gameserver.model.holders.SkillHolder;
import com.l2jmobius.gameserver.model.skills.Skill;
/**
* @author Zoey76
*/
public final class L2SkillLearn
{
private final String _skillName;
private final int _skillId;
private final int _skillLvl;
private final int _getLevel;
private final int _getDualClassLevel;
private final boolean _autoGet;
private final int _levelUpSp;
private final List<ItemHolder> _requiredItems = new ArrayList<>();
private final List<Race> _races = new ArrayList<>();
private final List<SkillHolder> _preReqSkills = new ArrayList<>();
private SocialClass _socialClass;
private final boolean _residenceSkill;
private final List<Integer> _residenceIds = new ArrayList<>();
private final boolean _learnedByNpc;
private final boolean _learnedByFS;
private final Set<Integer> _removeSkills = new HashSet<>(1);
private final int _treeId;
private final int _row;
private final int _column;
private final int _pointsRequired;
/**
* Constructor for L2SkillLearn.
* @param set the set with the L2SkillLearn data.
*/
public L2SkillLearn(StatsSet set)
{
_skillName = set.getString("skillName");
_skillId = set.getInt("skillId");
_skillLvl = set.getInt("skillLvl");
_getLevel = set.getInt("getLevel");
_getDualClassLevel = set.getInt("getDualClassLevel", 0);
_autoGet = set.getBoolean("autoGet", false);
_levelUpSp = set.getInt("levelUpSp", 0);
_residenceSkill = set.getBoolean("residenceSkill", false);
_learnedByNpc = set.getBoolean("learnedByNpc", false);
_learnedByFS = set.getBoolean("learnedByFS", false);
_treeId = set.getInt("treeId", 0);
_row = set.getInt("row", 0);
_column = set.getInt("row", 0);
_pointsRequired = set.getInt("pointsRequired", 0);
}
/**
* @return the name of this skill.
*/
public String getName()
{
return _skillName;
}
/**
* @return the ID of this skill.
*/
public int getSkillId()
{
return _skillId;
}
/**
* @return the level of this skill.
*/
public int getSkillLevel()
{
return _skillLvl;
}
/**
* @return the minimum level required to acquire this skill.
*/
public int getGetLevel()
{
return _getLevel;
}
/**
* @return the minimum level of a character dual class required to acquire this skill.
*/
public int getDualClassLevel()
{
return _getDualClassLevel;
}
/**
* @return the amount of SP/Clan Reputation to acquire this skill.
*/
public int getLevelUpSp()
{
return _levelUpSp;
}
/**
* @return {@code true} if the skill is auto-get, this skill is automatically delivered.
*/
public boolean isAutoGet()
{
return _autoGet;
}
/**
* @return the list with the item holders required to acquire this skill.
*/
public List<ItemHolder> getRequiredItems()
{
return _requiredItems;
}
/**
* Adds a required item holder to learn this skill.
* @param item the required item holder.
*/
public void addRequiredItem(ItemHolder item)
{
_requiredItems.add(item);
}
/**
* @return a list with the races that can acquire this skill.
*/
public List<Race> getRaces()
{
return _races;
}
/**
* Adds a required race to learn this skill.
* @param race the required race.
*/
public void addRace(Race race)
{
_races.add(race);
}
/**
* @return the list of skill holders required to acquire this skill.
*/
public List<SkillHolder> getPreReqSkills()
{
return _preReqSkills;
}
/**
* Adds a required skill holder to learn this skill.
* @param skill the required skill holder.
*/
public void addPreReqSkill(SkillHolder skill)
{
_preReqSkills.add(skill);
}
/**
* @return the social class required to get this skill.
*/
public SocialClass getSocialClass()
{
return _socialClass;
}
/**
* Sets the social class if hasn't been set before.
* @param socialClass the social class to set.
*/
public void setSocialClass(SocialClass socialClass)
{
if (_socialClass == null)
{
_socialClass = socialClass;
}
}
/**
* @return {@code true} if this skill is a Residence skill.
*/
public boolean isResidencialSkill()
{
return _residenceSkill;
}
/**
* @return a list with the Ids where this skill is available.
*/
public List<Integer> getResidenceIds()
{
return _residenceIds;
}
/**
* Adds a required residence Id.
* @param id the residence Id to add.
*/
public void addResidenceId(Integer id)
{
_residenceIds.add(id);
}
/**
* @return {@code true} if this skill is learned from Npc.
*/
public boolean isLearnedByNpc()
{
return _learnedByNpc;
}
/**
* @return {@code true} if this skill is learned by Forgotten Scroll.
*/
public boolean isLearnedByFS()
{
return _learnedByFS;
}
public void addRemoveSkills(int skillId)
{
_removeSkills.add(skillId);
}
public Set<Integer> getRemoveSkills()
{
return _removeSkills;
}
public int getTreeId()
{
return _treeId;
}
public int getRow()
{
return _row;
}
public int getColumn()
{
return _column;
}
public int getPointsRequired()
{
return _pointsRequired;
}
@Override
public String toString()
{
final Skill skill = SkillData.getInstance().getSkill(_skillId, _skillLvl);
return "[" + skill + " treeId: " + _treeId + " row: " + _row + " column: " + _column + " pointsRequired:" + _pointsRequired + "]";
}
}

View File

@@ -0,0 +1,714 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.lang.reflect.Constructor;
import java.util.Deque;
import java.util.Objects;
import java.util.concurrent.ConcurrentLinkedDeque;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.commons.util.Rnd;
import com.l2jmobius.gameserver.GeoData;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.data.xml.impl.NpcData;
import com.l2jmobius.gameserver.model.actor.L2Npc;
import com.l2jmobius.gameserver.model.actor.instance.L2NpcInstance;
import com.l2jmobius.gameserver.model.actor.templates.L2NpcTemplate;
import com.l2jmobius.gameserver.model.instancezone.Instance;
import com.l2jmobius.gameserver.model.interfaces.IIdentifiable;
import com.l2jmobius.gameserver.model.interfaces.ILocational;
import com.l2jmobius.gameserver.model.interfaces.INamable;
import com.l2jmobius.gameserver.model.interfaces.IPositionable;
import com.l2jmobius.gameserver.model.spawns.NpcSpawnTemplate;
/**
* This class manages the spawn and respawn of a group of L2NpcInstance that are in the same are and have the same type.<br>
* <B><U>Concept</U>:</B><br>
* L2NpcInstance can be spawned either in a random position into a location area (if Lox=0 and Locy=0), either at an exact position.<br>
* The heading of the L2NpcInstance can be a random heading if not defined (value= -1) or an exact heading (ex : merchant...).
* @author Nightmare
*/
public class L2Spawn implements IPositionable, IIdentifiable, INamable
{
protected static final Logger LOGGER = Logger.getLogger(L2Spawn.class.getName());
/** String identifier of this spawn */
private String _name;
/** The link on the L2NpcTemplate object containing generic and static properties of this spawn (ex : RewardExp, RewardSP, AggroRange...) */
private L2NpcTemplate _template;
/** The maximum number of L2NpcInstance that can manage this L2Spawn */
private int _maximumCount;
/** The current number of L2NpcInstance managed by this L2Spawn */
private int _currentCount;
/** The current number of SpawnTask in progress or stand by of this L2Spawn */
protected int _scheduledCount;
/** The identifier of the location area where L2NpcInstance can be spwaned */
private int _locationId;
/** The Location of this NPC spawn. */
private Location _location = new Location(0, 0, 0, 0);
private int _instanceId = 0;
/** Minimum respawn delay */
private int _respawnMinDelay;
/** Maximum respawn delay */
private int _respawnMaxDelay;
/** The generic constructor of L2NpcInstance managed by this L2Spawn */
private Constructor<? extends L2Npc> _constructor;
/** If True a L2NpcInstance is respawned each time that another is killed */
private boolean _doRespawn;
/** If true then spawn is custom */
private final Deque<L2Npc> _spawnedNpcs = new ConcurrentLinkedDeque<>();
private boolean _randomWalk = false; // Is no random walk
private NpcSpawnTemplate _spawnTemplate;
/** The task launching the function doSpawn() */
class SpawnTask implements Runnable
{
private final L2Npc _oldNpc;
public SpawnTask(L2Npc pOldNpc)
{
_oldNpc = pOldNpc;
}
@Override
public void run()
{
try
{
// doSpawn();
respawnNpc(_oldNpc);
}
catch (Exception e)
{
LOGGER.log(Level.WARNING, "", e);
}
_scheduledCount--;
}
}
/**
* Constructor of L2Spawn.<br>
* <B><U>Concept</U>:</B><br>
* Each L2Spawn owns generic and static properties (ex : RewardExp, RewardSP, AggroRange...).<br>
* All of those properties are stored in a different L2NpcTemplate for each type of L2Spawn. Each template is loaded once in the server cache memory (reduce memory use).<br>
* When a new instance of L2Spawn is created, server just create a link between the instance and the template.<br>
* This link is stored in <B>_template</B> Each L2NpcInstance is linked to a L2Spawn that manages its spawn and respawn (delay, location...).<br>
* This link is stored in <B>_spawn</B> of the L2NpcInstance.<br>
* <B><U> Actions</U>:</B><br>
* <ul>
* <li>Set the _template of the L2Spawn</li>
* <li>Calculate the implementationName used to generate the generic constructor of L2NpcInstance managed by this L2Spawn</li>
* <li>Create the generic constructor of L2NpcInstance managed by this L2Spawn</li>
* </ul>
* @param template The L2NpcTemplate to link to this L2Spawn
* @throws SecurityException
* @throws ClassNotFoundException
* @throws NoSuchMethodException
* @throws ClassCastException when template type is not subclass of L2Npc
*/
public L2Spawn(L2NpcTemplate template) throws SecurityException, ClassNotFoundException, NoSuchMethodException, ClassCastException
{
// Set the _template of the L2Spawn
_template = template;
if (_template == null)
{
return;
}
final String className = "com.l2jmobius.gameserver.model.actor.instance." + _template.getType() + "Instance";
// Create the generic constructor of L2Npc managed by this L2Spawn
_constructor = Class.forName(className).asSubclass(L2Npc.class).getConstructor(L2NpcTemplate.class);
}
/**
* Creates a new spawn.
* @param npcId the NPC ID
* @throws SecurityException
* @throws ClassNotFoundException
* @throws NoSuchMethodException
* @throws ClassCastException
*/
public L2Spawn(int npcId) throws SecurityException, ClassNotFoundException, NoSuchMethodException, ClassCastException
{
_template = Objects.requireNonNull(NpcData.getInstance().getTemplate(npcId), "NpcTemplate not found for NPC ID: " + npcId);
final String className = "com.l2jmobius.gameserver.model.actor.instance." + _template.getType() + "Instance";
// Create the generic constructor of L2Npc managed by this L2Spawn
_constructor = Class.forName(className).asSubclass(L2Npc.class).getConstructor(L2NpcTemplate.class);
}
/**
* @return the maximum number of L2NpcInstance that this L2Spawn can manage.
*/
public int getAmount()
{
return _maximumCount;
}
/**
* @return the String Identifier of this spawn.
*/
@Override
public String getName()
{
return _name;
}
/**
* Set the String Identifier of this spawn.
* @param name
*/
public void setName(String name)
{
_name = name;
}
/**
* @return the Identifier of the location area where L2NpcInstance can be spwaned.
*/
public int getLocationId()
{
return _locationId;
}
@Override
public Location getLocation()
{
return _location;
}
/**
* @return the X position of the spawn point.
*/
@Override
public int getX()
{
return _location.getX();
}
/**
* Set the X position of the spawn point.
* @param x the x coordinate
*/
@Override
public void setX(int x)
{
_location.setX(x);
}
/**
* @return the Y position of the spawn point.
*/
@Override
public int getY()
{
return _location.getY();
}
/**
* Set the Y position of the spawn point.
* @param y the y coordinate
*/
@Override
public void setY(int y)
{
_location.setY(y);
}
/**
* @return the Z position of the spawn point.
*/
@Override
public int getZ()
{
return _location.getZ();
}
/**
* Set the Z position of the spawn point.
* @param z the z coordinate
*/
@Override
public void setZ(int z)
{
_location.setZ(z);
}
/**
* Set the x, y, z position of the spawn point.
* @param x The x coordinate.
* @param y The y coordinate.
* @param z The z coordinate.
*/
@Override
public void setXYZ(int x, int y, int z)
{
setX(x);
setY(y);
setZ(z);
}
/**
* Set the x, y, z position of the spawn point.
* @param loc The location.
*/
@Override
public void setXYZ(ILocational loc)
{
setXYZ(loc.getX(), loc.getY(), loc.getZ());
}
/**
* @return the heading of L2NpcInstance when they are spawned.
*/
@Override
public int getHeading()
{
return _location.getHeading();
}
/**
* Set the heading of L2NpcInstance when they are spawned.
* @param heading
*/
@Override
public void setHeading(int heading)
{
_location.setHeading(heading);
}
/**
* Set the XYZ position of the spawn point.
* @param loc
*/
@Override
public void setLocation(Location loc)
{
_location = loc;
}
/**
* Gets the NPC ID.
* @return the NPC ID
*/
@Override
public int getId()
{
return _template.getId();
}
/**
* @return min respawn delay.
*/
public int getRespawnMinDelay()
{
return _respawnMinDelay;
}
/**
* @return max respawn delay.
*/
public int getRespawnMaxDelay()
{
return _respawnMaxDelay;
}
/**
* Set the maximum number of L2NpcInstance that this L2Spawn can manage.
* @param amount
*/
public void setAmount(int amount)
{
_maximumCount = amount;
}
/**
* Set the Identifier of the location area where L2NpcInstance can be spawned.
* @param id
*/
public void setLocationId(int id)
{
_locationId = id;
}
/**
* Set Minimum Respawn Delay.
* @param date
*/
public void setRespawnMinDelay(int date)
{
_respawnMinDelay = date;
}
/**
* Set Maximum Respawn Delay.
* @param date
*/
public void setRespawnMaxDelay(int date)
{
_respawnMaxDelay = date;
}
/**
* Decrease the current number of L2NpcInstance of this L2Spawn and if necessary create a SpawnTask to launch after the respawn Delay. <B><U> Actions</U> :</B>
* <li>Decrease the current number of L2NpcInstance of this L2Spawn</li>
* <li>Check if respawn is possible to prevent multiple respawning caused by lag</li>
* <li>Update the current number of SpawnTask in progress or stand by of this L2Spawn</li>
* <li>Create a new SpawnTask to launch after the respawn Delay</li> <FONT COLOR=#FF0000><B> <U>Caution</U> : A respawn is possible ONLY if _doRespawn=True and _scheduledCount + _currentCount < _maximumCount</B></FONT>
* @param oldNpc
*/
public void decreaseCount(L2Npc oldNpc)
{
// sanity check
if (_currentCount <= 0)
{
return;
}
// Decrease the current number of L2NpcInstance of this L2Spawn
_currentCount--;
// Remove this NPC from list of spawned
_spawnedNpcs.remove(oldNpc);
// Check if respawn is possible to prevent multiple respawning caused by lag
if (_doRespawn && ((_scheduledCount + _currentCount) < _maximumCount))
{
// Update the current number of SpawnTask in progress or stand by of this L2Spawn
_scheduledCount++;
// Create a new SpawnTask to launch after the respawn Delay
// ClientScheduler.getInstance().scheduleLow(new SpawnTask(npcId), _respawnDelay);
ThreadPoolManager.getInstance().scheduleGeneral(new SpawnTask(oldNpc), hasRespawnRandom() ? Rnd.get(_respawnMinDelay, _respawnMaxDelay) : _respawnMinDelay);
}
}
/**
* Create the initial spawning and set _doRespawn to False, if respawn time set to 0, or set it to True otherwise.
* @return The number of L2NpcInstance that were spawned
*/
public int init()
{
while (_currentCount < _maximumCount)
{
doSpawn();
}
_doRespawn = _respawnMinDelay != 0;
return _currentCount;
}
/**
* Create a {@link L2NpcInstance} in this L2Spawn.
* @param val
* @return
*/
public L2Npc spawnOne(boolean val)
{
return doSpawn(val);
}
/**
* @return true if respawn enabled
*/
public boolean isRespawnEnabled()
{
return _doRespawn;
}
/**
* Set _doRespawn to False to stop respawn in this L2Spawn.
*/
public void stopRespawn()
{
_doRespawn = false;
}
/**
* Set _doRespawn to True to start or restart respawn in this L2Spawn.
*/
public void startRespawn()
{
_doRespawn = true;
}
public L2Npc doSpawn()
{
return doSpawn(false);
}
/**
* Create the L2NpcInstance, add it to the world and lauch its OnSpawn action.<br>
* <B><U>Concept</U>:</B><br>
* L2NpcInstance can be spawned either in a random position into a location area (if Lox=0 and Locy=0), either at an exact position.<br>
* The heading of the L2NpcInstance can be a random heading if not defined (value= -1) or an exact heading (ex : merchant...).<br>
* <B><U>Actions for an random spawn into location area</U>:<I> (if Locx=0 and Locy=0)</I></B>
* <ul>
* <li>Get L2NpcInstance Init parameters and its generate an Identifier</li>
* <li>Call the constructor of the L2NpcInstance</li>
* <li>Calculate the random position in the location area (if Locx=0 and Locy=0) or get its exact position from the L2Spawn</li>
* <li>Set the position of the L2NpcInstance</li>
* <li>Set the HP and MP of the L2NpcInstance to the max</li>
* <li>Set the heading of the L2NpcInstance (random heading if not defined : value=-1)</li>
* <li>Link the L2NpcInstance to this L2Spawn</li>
* <li>Init other values of the L2NpcInstance (ex : from its L2CharTemplate for INT, STR, DEX...) and add it in the world</li>
* <li>Launch the action OnSpawn fo the L2NpcInstance</li>
* <li>Increase the current number of L2NpcInstance managed by this L2Spawn</li>
* </ul>
* @param isSummonSpawn
* @return
*/
public L2Npc doSpawn(boolean isSummonSpawn)
{
try
{
// Check if the L2Spawn is not a L2Pet or L2Minion or L2Decoy spawn
if (_template.isType("L2Pet") || _template.isType("L2Decoy") || _template.isType("L2Trap"))
{
_currentCount++;
return null;
}
// Call the constructor of the L2Npc
final L2Npc npc = _constructor.newInstance(_template);
npc.setInstanceById(_instanceId); // Must be done before object is spawned into visible world
if (isSummonSpawn)
{
npc.setShowSummonAnimation(isSummonSpawn);
}
return initializeNpcInstance(npc);
}
catch (Exception e)
{
LOGGER.log(Level.WARNING, "Error while spawning " + _template.getId(), e);
}
return null;
}
/**
* @param npc
* @return
*/
private L2Npc initializeNpcInstance(L2Npc npc)
{
int newlocx = 0;
int newlocy = 0;
int newlocz = 0;
// If Locx and Locy are not defined, the L2NpcInstance must be spawned in an area defined by location or spawn territory
// New method
if (_spawnTemplate != null)
{
final Location loc = _spawnTemplate.getSpawnLocation();
newlocx = loc.getX();
newlocy = loc.getY();
newlocz = loc.getZ();
setLocation(loc);
}
else if ((getX() == 0) && (getY() == 0))
{
LOGGER.warning("NPC " + npc + " doesn't have spawn location!");
return null;
}
else
{
// The L2NpcInstance is spawned at the exact position (Lox, Locy, Locz)
newlocx = getX();
newlocy = getY();
newlocz = getZ();
}
// don't correct z of flying npc's
if (!npc.isFlying())
{
newlocz = GeoData.getInstance().getSpawnHeight(newlocx, newlocy, newlocz);
}
// Set is not random walk default value
npc.setRandomWalking(getRandomWalking());
// Set the heading of the L2NpcInstance (random heading if not defined)
if (getHeading() == -1)
{
npc.setHeading(Rnd.nextInt(61794));
}
else
{
npc.setHeading(getHeading());
}
// Set custom Npc server side name and title
if (npc.getTemplate().isUsingServerSideName())
{
npc.setName(npc.getTemplate().getName());
}
if (npc.getTemplate().isUsingServerSideTitle())
{
npc.setTitle(npc.getTemplate().getTitle());
}
// Reset some variables
npc.onRespawn();
// Link the L2NpcInstance to this L2Spawn
npc.setSpawn(this);
// Spawn NPC
npc.spawnMe(newlocx, newlocy, newlocz);
if (_spawnTemplate != null)
{
_spawnTemplate.notifySpawnNpc(npc);
}
_spawnedNpcs.add(npc);
_currentCount++;
return npc;
}
/**
* Set bounds for random calculation and delay for respawn
* @param delay delay in seconds
* @param randomInterval random interval in seconds
*/
public void setRespawnDelay(int delay, int randomInterval)
{
if (delay != 0)
{
if (delay < 0)
{
LOGGER.warning("respawn delay is negative for spawn:" + this);
}
final int minDelay = delay - randomInterval;
final int maxDelay = delay + randomInterval;
_respawnMinDelay = Math.max(10, minDelay) * 1000;
_respawnMaxDelay = Math.max(10, maxDelay) * 1000;
}
else
{
_respawnMinDelay = 0;
_respawnMaxDelay = 0;
}
}
public void setRespawnDelay(int delay)
{
setRespawnDelay(delay, 0);
}
public int getRespawnDelay()
{
return (_respawnMinDelay + _respawnMaxDelay) / 2;
}
public boolean hasRespawnRandom()
{
return _respawnMinDelay != _respawnMaxDelay;
}
public L2Npc getLastSpawn()
{
if (!_spawnedNpcs.isEmpty())
{
return _spawnedNpcs.peekLast();
}
return null;
}
public boolean deleteLastNpc()
{
return !_spawnedNpcs.isEmpty() && _spawnedNpcs.getLast().deleteMe();
}
public final Deque<L2Npc> getSpawnedNpcs()
{
return _spawnedNpcs;
}
/**
* @param oldNpc
*/
public void respawnNpc(L2Npc oldNpc)
{
if (_doRespawn)
{
oldNpc.refreshID();
initializeNpcInstance(oldNpc);
// Register NPC back to instance world
final Instance instance = oldNpc.getInstanceWorld();
if (instance != null)
{
instance.addNpc(oldNpc);
}
}
}
public L2NpcTemplate getTemplate()
{
return _template;
}
public int getInstanceId()
{
return _instanceId;
}
public void setInstanceId(int instanceId)
{
_instanceId = instanceId;
}
@Override
public String toString()
{
return "L2Spawn ID: " + getId() + " " + getLocation();
}
public final boolean getRandomWalking()
{
return _randomWalk;
}
public final void setRandomWalking(boolean value)
{
_randomWalk = value;
}
public void setSpawnTemplate(NpcSpawnTemplate npcSpawnTemplate)
{
_spawnTemplate = npcSpawnTemplate;
}
public NpcSpawnTemplate getNpcSpawnTemplate()
{
return _spawnTemplate;
}
}

View File

@@ -0,0 +1,144 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* This class ...
* @version $Revision: 1.2.4.1 $ $Date: 2005/03/27 15:29:32 $
*/
public class L2TeleportLocation
{
private int _teleId;
private int _locX;
private int _locY;
private int _locZ;
private int _price;
private boolean _forNoble;
private int _itemId;
/**
* @param id
*/
public void setTeleId(int id)
{
_teleId = id;
}
/**
* @param locX
*/
public void setLocX(int locX)
{
_locX = locX;
}
/**
* @param locY
*/
public void setLocY(int locY)
{
_locY = locY;
}
/**
* @param locZ
*/
public void setLocZ(int locZ)
{
_locZ = locZ;
}
/**
* @param price
*/
public void setPrice(int price)
{
_price = price;
}
/**
* @param val
*/
public void setIsForNoble(boolean val)
{
_forNoble = val;
}
/**
* @param val
*/
public void setItemId(int val)
{
_itemId = val;
}
/**
* @return
*/
public int getTeleId()
{
return _teleId;
}
/**
* @return
*/
public int getLocX()
{
return _locX;
}
/**
* @return
*/
public int getLocY()
{
return _locY;
}
/**
* @return
*/
public int getLocZ()
{
return _locZ;
}
/**
* @return
*/
public int getPrice()
{
return _price;
}
/**
* @return
*/
public boolean getIsForNoble()
{
return _forNoble;
}
/**
* @return
*/
public int getItemId()
{
return _itemId;
}
}

View File

@@ -0,0 +1,198 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.ArrayList;
import java.util.List;
import java.util.logging.Logger;
import com.l2jmobius.commons.util.Rnd;
/**
* @version 0.1, 2005-03-12
* @author Balancer
*/
public class L2Territory
{
private static Logger _log = Logger.getLogger(L2Territory.class.getName());
protected static class Point
{
protected int _x, _y, _zmin, _zmax, _proc;
Point(int x, int y, int zmin, int zmax, int proc)
{
_x = x;
_y = y;
_zmin = zmin;
_zmax = zmax;
_proc = proc;
}
}
private final List<Point> _points = new ArrayList<>();
private final int _terr;
private int _xMin;
private int _xMax;
private int _yMin;
private int _yMax;
private int _zMin;
private int _zMax;
private int _procMax;
public L2Territory(int terr)
{
_terr = terr;
_xMin = 999999;
_xMax = -999999;
_yMin = 999999;
_yMax = -999999;
_zMin = 999999;
_zMax = -999999;
_procMax = 0;
}
public void add(int x, int y, int zmin, int zmax, int proc)
{
_points.add(new Point(x, y, zmin, zmax, proc));
if (x < _xMin)
{
_xMin = x;
}
if (y < _yMin)
{
_yMin = y;
}
if (x > _xMax)
{
_xMax = x;
}
if (y > _yMax)
{
_yMax = y;
}
if (zmin < _zMin)
{
_zMin = zmin;
}
if (zmax > _zMax)
{
_zMax = zmax;
}
_procMax += proc;
}
public void print()
{
for (Point p : _points)
{
_log.info("(" + p._x + "," + p._y + ")");
}
}
public boolean isIntersect(int x, int y, Point p1, Point p2)
{
final double dy1 = p1._y - y;
final double dy2 = p2._y - y;
if (Math.abs(Math.signum(dy1) - Math.signum(dy2)) <= 1e-6)
{
return false;
}
final double dx1 = p1._x - x;
final double dx2 = p2._x - x;
if ((dx1 >= 0) && (dx2 >= 0))
{
return true;
}
if ((dx1 < 0) && (dx2 < 0))
{
return false;
}
final double dx0 = (dy1 * (p1._x - p2._x)) / (p1._y - p2._y);
return dx0 <= dx1;
}
public boolean isInside(int x, int y)
{
int intersect_count = 0;
for (int i = 0; i < _points.size(); i++)
{
final Point p1 = _points.get(i > 0 ? i - 1 : _points.size() - 1);
final Point p2 = _points.get(i);
if (isIntersect(x, y, p1, p2))
{
intersect_count++;
}
}
return (intersect_count % 2) == 1;
}
public Location getRandomPoint()
{
if (_procMax > 0)
{
int pos = 0;
final int rnd = Rnd.nextInt(_procMax);
for (Point p1 : _points)
{
pos += p1._proc;
if (rnd <= pos)
{
return new Location(p1._x, p1._y, Rnd.get(p1._zmin, p1._zmax));
}
}
}
for (int i = 0; i < 100; i++)
{
final int x = Rnd.get(_xMin, _xMax);
final int y = Rnd.get(_yMin, _yMax);
if (isInside(x, y))
{
double curdistance = 0;
int zmin = _zMin;
for (Point p1 : _points)
{
final double dx = p1._x - x;
final double dy = p1._y - y;
final double distance = Math.sqrt((dx * dx) + (dy * dy));
if ((curdistance == 0) || (distance < curdistance))
{
curdistance = distance;
zmin = p1._zmin;
}
}
return new Location(x, y, Rnd.get(zmin, _zMax));
}
}
_log.warning("Can't make point for territory " + _terr);
return null;
}
public int getProcMax()
{
return _procMax;
}
}

View File

@@ -0,0 +1,74 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.List;
/**
* @author GKR
*/
public class L2WalkRoute
{
private final String _name;
private final List<L2NpcWalkerNode> _nodeList; // List of nodes
private final boolean _repeatWalk; // Does repeat walk, after arriving into last point in list, or not
private boolean _stopAfterCycle; // Make only one cycle or endlessly
private final byte _repeatType; // Repeat style: 0 - go back, 1 - go to first point (circle style), 2 - teleport to first point (conveyor style), 3 - random walking between points
public L2WalkRoute(String name, List<L2NpcWalkerNode> route, boolean repeat, boolean once, byte repeatType)
{
_name = name;
_nodeList = route;
_repeatType = repeatType;
_repeatWalk = (_repeatType >= 0) && (_repeatType <= 2) && repeat;
}
public String getName()
{
return _name;
}
public List<L2NpcWalkerNode> getNodeList()
{
return _nodeList;
}
public L2NpcWalkerNode getLastNode()
{
return _nodeList.get(_nodeList.size() - 1);
}
public boolean repeatWalk()
{
return _repeatWalk;
}
public boolean doOnce()
{
return _stopAfterCycle;
}
public byte getRepeatType()
{
return _repeatType;
}
public int getNodesCount()
{
return _nodeList.size();
}
}

View File

@@ -0,0 +1,828 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Collection;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.function.Consumer;
import java.util.function.Predicate;
import java.util.logging.Logger;
import com.l2jmobius.Config;
import com.l2jmobius.gameserver.ai.CtrlEvent;
import com.l2jmobius.gameserver.ai.CtrlIntention;
import com.l2jmobius.gameserver.ai.L2CharacterAI;
import com.l2jmobius.gameserver.data.sql.impl.CharNameTable;
import com.l2jmobius.gameserver.model.actor.L2Character;
import com.l2jmobius.gameserver.model.actor.L2Npc;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.actor.instance.L2PetInstance;
import com.l2jmobius.gameserver.model.events.EventDispatcher;
import com.l2jmobius.gameserver.model.events.impl.character.npc.OnNpcCreatureSee;
import com.l2jmobius.gameserver.model.interfaces.ILocational;
import com.l2jmobius.gameserver.network.serverpackets.DeleteObject;
import com.l2jmobius.gameserver.util.Util;
public final class L2World
{
private static final Logger _log = Logger.getLogger(L2World.class.getName());
/** Gracia border Flying objects not allowed to the east of it. */
public static final int GRACIA_MAX_X = -166168;
public static final int GRACIA_MAX_Z = 6105;
public static final int GRACIA_MIN_Z = -895;
/** Bit shift, defines number of regions note, shifting by 15 will result in regions corresponding to map tiles shifting by 11 divides one tile to 16x16 regions. */
public static final int SHIFT_BY = 11;
public static final int SHIFT_BY_Z = 10;
public static final int TILE_SIZE = 32768;
/** Map dimensions */
public static final int TILE_X_MIN = 11;
public static final int TILE_Y_MIN = 10;
public static final int TILE_X_MAX = 28;
public static final int TILE_Y_MAX = 26;
public static final int TILE_ZERO_COORD_X = 20;
public static final int TILE_ZERO_COORD_Y = 18;
public static final int MAP_MIN_X = (TILE_X_MIN - TILE_ZERO_COORD_X) * TILE_SIZE;
public static final int MAP_MIN_Y = (TILE_Y_MIN - TILE_ZERO_COORD_Y) * TILE_SIZE;
public static final int MAP_MIN_Z = -TILE_SIZE / 2;
public static final int MAP_MAX_X = ((TILE_X_MAX - TILE_ZERO_COORD_X) + 1) * TILE_SIZE;
public static final int MAP_MAX_Y = ((TILE_Y_MAX - TILE_ZERO_COORD_Y) + 1) * TILE_SIZE;
public static final int MAP_MAX_Z = TILE_SIZE / 2;
/** calculated offset used so top left region is 0,0 */
public static final int OFFSET_X = Math.abs(MAP_MIN_X >> SHIFT_BY);
public static final int OFFSET_Y = Math.abs(MAP_MIN_Y >> SHIFT_BY);
public static final int OFFSET_Z = Math.abs(MAP_MIN_Z >> SHIFT_BY_Z);
/** number of regions */
private static final int REGIONS_X = (MAP_MAX_X >> SHIFT_BY) + OFFSET_X;
private static final int REGIONS_Y = (MAP_MAX_Y >> SHIFT_BY) + OFFSET_Y;
private static final int REGIONS_Z = (MAP_MAX_Z >> SHIFT_BY_Z) + OFFSET_Z;
public static final int REGION_MIN_DIMENSION = Math.min(TILE_SIZE / (TILE_SIZE >> SHIFT_BY_Z), TILE_SIZE / (TILE_SIZE >> SHIFT_BY));
/** Map containing all the players in game. */
private final Map<Integer, L2PcInstance> _allPlayers = new ConcurrentHashMap<>();
/** Map containing all the Good players in game. */
private static final Map<Integer, L2PcInstance> _allGoodPlayers = new ConcurrentHashMap<>();
/** Map containing all the Evil players in game. */
private static final Map<Integer, L2PcInstance> _allEvilPlayers = new ConcurrentHashMap<>();
/** Map containing all visible objects. */
private final Map<Integer, L2Object> _allObjects = new ConcurrentHashMap<>();
/** Map used for debug. */
// private final Map<Integer, String> _allObjectsDebug = new ConcurrentHashMap<>();
/** Map with the pets instances and their owner ID. */
private final Map<Integer, L2PetInstance> _petsInstance = new ConcurrentHashMap<>();
private final L2WorldRegion[][][] _worldRegions = new L2WorldRegion[REGIONS_X + 1][REGIONS_Y + 1][REGIONS_Z + 1];
/** Constructor of L2World. */
protected L2World()
{
for (int x = 0; x <= REGIONS_X; x++)
{
for (int y = 0; y <= REGIONS_Y; y++)
{
for (int z = 0; z <= REGIONS_Z; z++)
{
_worldRegions[x][y][z] = new L2WorldRegion(x, y, z);
}
}
}
_log.info(getClass().getSimpleName() + ": (" + REGIONS_X + " by " + REGIONS_Y + " by " + REGIONS_Z + ") World Region Grid set up.");
}
/**
* Adds an object to the world.<br>
* <B><U>Example of use</U>:</B>
* <ul>
* <li>Withdraw an item from the warehouse, create an item</li>
* <li>Spawn a L2Character (PC, NPC, Pet)</li>
* </ul>
* @param object
*/
public void storeObject(L2Object object)
{
if (_allObjects.containsKey(object.getObjectId()))
{
// _log.warning(getClass().getSimpleName() + ": Current object: " + object + " already exist in OID map!");
// _log.warning(CommonUtil.getTraceString(Thread.currentThread().getStackTrace()));
// _log.warning(getClass().getSimpleName() + ": Previous object: " + _allObjects.get(object.getObjectId()) + " already exist in OID map!");
// _log.warning(_allObjectsDebug.get(object.getObjectId()));
// _log.warning("---------------------- End ---------------------");
return;
}
_allObjects.put(object.getObjectId(), object);
// _allObjectsDebug.put(object.getObjectId(), CommonUtil.getTraceString(Thread.currentThread().getStackTrace()));
}
/**
* Removes an object from the world.<br>
* <B><U>Example of use</U>:</B>
* <ul>
* <li>Delete item from inventory, transfer Item from inventory to warehouse</li>
* <li>Crystallize item</li>
* <li>Remove NPC/PC/Pet from the world</li>
* </ul>
* @param object the object to remove
*/
public void removeObject(L2Object object)
{
_allObjects.remove(object.getObjectId());
// _allObjectsDebug.remove(object.getObjectId());
}
/**
* <B><U> Example of use</U>:</B>
* <ul>
* <li>Client packets : Action, AttackRequest, RequestJoinParty, RequestJoinPledge...</li>
* </ul>
* @param objectId Identifier of the L2Object
* @return the L2Object object that belongs to an ID or null if no object found.
*/
public L2Object findObject(int objectId)
{
return _allObjects.get(objectId);
}
public Collection<L2Object> getVisibleObjects()
{
return _allObjects.values();
}
/**
* Get the count of all visible objects in world.
* @return count off all L2World objects
*/
public int getVisibleObjectsCount()
{
return _allObjects.size();
}
public Collection<L2PcInstance> getPlayers()
{
return _allPlayers.values();
}
public Collection<L2PcInstance> getAllGoodPlayers()
{
return _allGoodPlayers.values();
}
public Collection<L2PcInstance> getAllEvilPlayers()
{
return _allEvilPlayers.values();
}
/**
* <B>If you have access to player objectId use {@link #getPlayer(int playerObjId)}</B>
* @param name Name of the player to get Instance
* @return the player instance corresponding to the given name.
*/
public L2PcInstance getPlayer(String name)
{
return getPlayer(CharNameTable.getInstance().getIdByName(name));
}
/**
* @param objectId of the player to get Instance
* @return the player instance corresponding to the given object ID.
*/
public L2PcInstance getPlayer(int objectId)
{
return _allPlayers.get(objectId);
}
/**
* @param ownerId ID of the owner
* @return the pet instance from the given ownerId.
*/
public L2PetInstance getPet(int ownerId)
{
return _petsInstance.get(ownerId);
}
/**
* Add the given pet instance from the given ownerId.
* @param ownerId ID of the owner
* @param pet L2PetInstance of the pet
* @return
*/
public L2PetInstance addPet(int ownerId, L2PetInstance pet)
{
return _petsInstance.put(ownerId, pet);
}
/**
* Remove the given pet instance.
* @param ownerId ID of the owner
*/
public void removePet(int ownerId)
{
_petsInstance.remove(ownerId);
}
/**
* Remove the given pet instance.
* @param pet the pet to remove
*/
public void removePet(L2PetInstance pet)
{
_petsInstance.remove(pet.getOwner().getObjectId());
}
/**
* Add a L2Object in the world. <B><U> Concept</U> :</B> L2Object (including PlayerInstance) are identified in <B>_visibleObjects</B> of his current WorldRegion and in <B>_knownObjects</B> of other surrounding L2Characters <BR>
* PlayerInstance are identified in <B>_allPlayers</B> of L2World, in <B>_allPlayers</B> of his current WorldRegion and in <B>_knownPlayer</B> of other surrounding L2Characters <B><U> Actions</U> :</B>
* <li>Add the L2Object object in _allPlayers* of L2World</li>
* <li>Add the L2Object object in _gmList** of GmListTable</li>
* <li>Add object in _knownObjects and _knownPlayer* of all surrounding WorldRegion L2Characters</li><BR>
* <li>If object is a L2Character, add all surrounding L2Object in its _knownObjects and all surrounding PlayerInstance in its _knownPlayer</li><BR>
* <I>* only if object is a PlayerInstance</I><BR>
* <I>** only if object is a GM PlayerInstance</I> <FONT COLOR=#FF0000><B> <U>Caution</U> : This method DOESN'T ADD the object in _visibleObjects and _allPlayers* of WorldRegion (need synchronisation)</B></FONT><BR>
* <FONT COLOR=#FF0000><B> <U>Caution</U> : This method DOESN'T ADD the object to _allObjects and _allPlayers* of L2World (need synchronisation)</B></FONT> <B><U> Example of use </U> :</B>
* <li>Drop an Item</li>
* <li>Spawn a L2Character</li>
* <li>Apply Death Penalty of a PlayerInstance</li>
* @param object L2object to add in the world
* @param newRegion WorldRegion in wich the object will be add (not used)
*/
public void addVisibleObject(L2Object object, L2WorldRegion newRegion)
{
// TODO: this code should be obsoleted by protection in putObject func...
if (object.isPlayer())
{
final L2PcInstance player = object.getActingPlayer();
if (!player.isTeleporting())
{
final L2PcInstance old = getPlayer(player.getObjectId());
if (old != null)
{
_log.warning(getClass().getSimpleName() + ": Duplicate character!? Closing both characters (" + player.getName() + ")");
player.logout();
old.logout();
return;
}
addPlayerToWorld(player);
}
}
if (!newRegion.isActive())
{
return;
}
forEachVisibleObject(object, L2Object.class, 1, wo ->
{
if (object.isPlayer() && wo.isVisibleFor((L2PcInstance) object))
{
wo.sendInfo((L2PcInstance) object);
if (wo.isCharacter())
{
final L2CharacterAI ai = ((L2Character) wo).getAI();
if (ai != null)
{
ai.describeStateToPlayer((L2PcInstance) object);
if (wo.isMonster())
{
if (ai.getIntention() == CtrlIntention.AI_INTENTION_IDLE)
{
ai.setIntention(CtrlIntention.AI_INTENTION_ACTIVE);
}
}
}
}
}
if (wo.isPlayer() && object.isVisibleFor((L2PcInstance) wo))
{
object.sendInfo((L2PcInstance) wo);
if (object.isCharacter())
{
final L2CharacterAI ai = ((L2Character) object).getAI();
if (ai != null)
{
ai.describeStateToPlayer((L2PcInstance) wo);
if (object.isMonster())
{
if (ai.getIntention() == CtrlIntention.AI_INTENTION_IDLE)
{
ai.setIntention(CtrlIntention.AI_INTENTION_ACTIVE);
}
}
}
}
}
if (wo.isNpc() && object.isCharacter())
{
EventDispatcher.getInstance().notifyEventAsync(new OnNpcCreatureSee((L2Npc) wo, (L2Character) object, object.isSummon()), (L2Npc) wo);
}
if (object.isNpc() && wo.isCharacter())
{
EventDispatcher.getInstance().notifyEventAsync(new OnNpcCreatureSee((L2Npc) object, (L2Character) wo, wo.isSummon()), (L2Npc) object);
}
});
}
/**
* Adds the player to the world.
* @param player the player to add
*/
public void addPlayerToWorld(L2PcInstance player)
{
_allPlayers.put(player.getObjectId(), player);
if (Config.FACTION_SYSTEM_ENABLED)
{
addFactionPlayerToWorld(player);
}
}
/**
* Remove the player from the world.
* @param player the player to remove
*/
public void removeFromAllPlayers(L2PcInstance player)
{
_allPlayers.remove(player.getObjectId());
if (Config.FACTION_SYSTEM_ENABLED)
{
if (player.isGood())
{
_allGoodPlayers.remove(player.getObjectId());
}
else if (player.isEvil())
{
_allEvilPlayers.remove(player.getObjectId());
}
}
}
public static void addFactionPlayerToWorld(L2PcInstance player)
{
if (player.isGood())
{
_allGoodPlayers.put(player.getObjectId(), player);
}
else if (player.isEvil())
{
_allEvilPlayers.put(player.getObjectId(), player);
}
}
/**
* Remove a L2Object from the world. <B><U> Concept</U> :</B> L2Object (including PlayerInstance) are identified in <B>_visibleObjects</B> of his current WorldRegion and in <B>_knownObjects</B> of other surrounding L2Characters <BR>
* PlayerInstance are identified in <B>_allPlayers</B> of L2World, in <B>_allPlayers</B> of his current WorldRegion and in <B>_knownPlayer</B> of other surrounding L2Characters <B><U> Actions</U> :</B>
* <li>Remove the L2Object object from _allPlayers* of L2World</li>
* <li>Remove the L2Object object from _visibleObjects and _allPlayers* of WorldRegion</li>
* <li>Remove the L2Object object from _gmList** of GmListTable</li>
* <li>Remove object from _knownObjects and _knownPlayer* of all surrounding WorldRegion L2Characters</li><BR>
* <li>If object is a L2Character, remove all L2Object from its _knownObjects and all PlayerInstance from its _knownPlayer</li> <FONT COLOR=#FF0000><B> <U>Caution</U> : This method DOESN'T REMOVE the object from _allObjects of L2World</B></FONT> <I>* only if object is a PlayerInstance</I><BR>
* <I>** only if object is a GM PlayerInstance</I> <B><U> Example of use </U> :</B>
* <li>Pickup an Item</li>
* <li>Decay a L2Character</li>
* @param object L2object to remove from the world
* @param oldRegion WorldRegion in which the object was before removing
*/
public void removeVisibleObject(L2Object object, L2WorldRegion oldRegion)
{
if (object == null)
{
return;
}
if (oldRegion != null)
{
oldRegion.removeVisibleObject(object);
// Go through all surrounding WorldRegion Creatures
oldRegion.forEachSurroundingRegion(w ->
{
for (L2Object wo : w.getVisibleObjects().values())
{
if (wo == object)
{
continue;
}
if (object.isCharacter())
{
final L2Character objectCreature = (L2Character) object;
final L2CharacterAI ai = objectCreature.getAI();
if (ai != null)
{
ai.notifyEvent(CtrlEvent.EVT_FORGET_OBJECT, wo);
}
if (objectCreature.getTarget() == wo)
{
objectCreature.setTarget(null);
}
if (object.isPlayer())
{
object.sendPacket(new DeleteObject(wo));
}
}
if (wo.isCharacter())
{
final L2Character woCreature = (L2Character) wo;
final L2CharacterAI ai = woCreature.getAI();
if (ai != null)
{
ai.notifyEvent(CtrlEvent.EVT_FORGET_OBJECT, object);
}
if (woCreature.getTarget() == object)
{
woCreature.setTarget(null);
}
if (wo.isPlayer())
{
wo.sendPacket(new DeleteObject(object));
}
}
}
return true;
});
if (object.isPlayer())
{
final L2PcInstance player = object.getActingPlayer();
if (!player.isTeleporting())
{
removeFromAllPlayers(player);
}
}
}
}
public void switchRegion(L2Object object, L2WorldRegion newRegion)
{
final L2WorldRegion oldRegion = object.getWorldRegion();
if ((oldRegion == null) || (oldRegion == newRegion))
{
return;
}
oldRegion.forEachSurroundingRegion(w ->
{
if (!newRegion.isSurroundingRegion(w))
{
for (L2Object wo : w.getVisibleObjects().values())
{
if (wo == object)
{
continue;
}
if (object.isCharacter())
{
final L2Character objectCreature = (L2Character) object;
final L2CharacterAI ai = objectCreature.getAI();
if (ai != null)
{
ai.notifyEvent(CtrlEvent.EVT_FORGET_OBJECT, wo);
}
if (objectCreature.getTarget() == wo)
{
objectCreature.setTarget(null);
}
if (object.isPlayer())
{
object.sendPacket(new DeleteObject(wo));
}
}
if (wo.isCharacter())
{
final L2Character woCreature = (L2Character) wo;
final L2CharacterAI ai = woCreature.getAI();
if (ai != null)
{
ai.notifyEvent(CtrlEvent.EVT_FORGET_OBJECT, object);
}
if (woCreature.getTarget() == object)
{
woCreature.setTarget(null);
}
if (wo.isPlayer())
{
wo.sendPacket(new DeleteObject(object));
}
}
}
}
return true;
});
newRegion.forEachSurroundingRegion(w ->
{
if (!oldRegion.isSurroundingRegion(w))
{
for (L2Object wo : w.getVisibleObjects().values())
{
if ((wo == object) || (wo.getInstanceWorld() != object.getInstanceWorld()))
{
continue;
}
if (object.isPlayer() && wo.isVisibleFor((L2PcInstance) object))
{
wo.sendInfo((L2PcInstance) object);
if (wo.isCharacter())
{
final L2CharacterAI ai = ((L2Character) wo).getAI();
if (ai != null)
{
ai.describeStateToPlayer((L2PcInstance) object);
if (wo.isMonster())
{
if (ai.getIntention() == CtrlIntention.AI_INTENTION_IDLE)
{
ai.setIntention(CtrlIntention.AI_INTENTION_ACTIVE);
}
}
}
}
}
if (wo.isPlayer() && object.isVisibleFor((L2PcInstance) wo))
{
object.sendInfo((L2PcInstance) wo);
if (object.isCharacter())
{
final L2CharacterAI ai = ((L2Character) object).getAI();
if (ai != null)
{
ai.describeStateToPlayer((L2PcInstance) wo);
if (object.isMonster())
{
if (ai.getIntention() == CtrlIntention.AI_INTENTION_IDLE)
{
ai.setIntention(CtrlIntention.AI_INTENTION_ACTIVE);
}
}
}
}
}
if (wo.isNpc() && object.isCharacter())
{
EventDispatcher.getInstance().notifyEventAsync(new OnNpcCreatureSee((L2Npc) wo, (L2Character) object, object.isSummon()), (L2Npc) wo);
}
if (object.isNpc() && wo.isCharacter())
{
EventDispatcher.getInstance().notifyEventAsync(new OnNpcCreatureSee((L2Npc) object, (L2Character) wo, wo.isSummon()), (L2Npc) object);
}
}
}
return true;
});
}
public <T extends L2Object> void forEachVisibleObject(L2Object object, Class<T> clazz, int depth, Consumer<T> c)
{
if (object == null)
{
return;
}
final L2WorldRegion centerWorldRegion = getRegion(object);
if (centerWorldRegion == null)
{
return;
}
for (int x = Math.max(centerWorldRegion.getRegionX() - depth, 0); x <= Math.min(centerWorldRegion.getRegionX() + depth, REGIONS_X); x++)
{
for (int y = Math.max(centerWorldRegion.getRegionY() - depth, 0); y <= Math.min(centerWorldRegion.getRegionY() + depth, REGIONS_Y); y++)
{
for (int z = Math.max(centerWorldRegion.getRegionZ() - depth, 0); z <= Math.min(centerWorldRegion.getRegionZ() + depth, REGIONS_Z); z++)
{
for (L2Object visibleObject : _worldRegions[x][y][z].getVisibleObjects().values())
{
if ((visibleObject == null) || (visibleObject == object) || !clazz.isInstance(visibleObject))
{
continue;
}
if (visibleObject.getInstanceWorld() != object.getInstanceWorld())
{
continue;
}
c.accept(clazz.cast(visibleObject));
}
}
}
}
}
public <T extends L2Object> void forEachVisibleObject(L2Object object, Class<T> clazz, Consumer<T> c)
{
forEachVisibleObject(object, clazz, 1, c);
}
public <T extends L2Object> void forEachVisibleObjectInRange(L2Object object, Class<T> clazz, int range, Consumer<T> c)
{
if (object == null)
{
return;
}
final L2WorldRegion centerWorldRegion = getRegion(object);
if (centerWorldRegion == null)
{
return;
}
final int depth = (range / REGION_MIN_DIMENSION) + 1;
for (int x = Math.max(centerWorldRegion.getRegionX() - depth, 0); x <= Math.min(centerWorldRegion.getRegionX() + depth, REGIONS_X); x++)
{
for (int y = Math.max(centerWorldRegion.getRegionY() - depth, 0); y <= Math.min(centerWorldRegion.getRegionY() + depth, REGIONS_Y); y++)
{
for (int z = Math.max(centerWorldRegion.getRegionZ() - depth, 0); z <= Math.min(centerWorldRegion.getRegionZ() + depth, REGIONS_Z); z++)
{
final int x1 = (x - OFFSET_X) << SHIFT_BY;
final int y1 = (y - OFFSET_Y) << SHIFT_BY;
final int z1 = (z - OFFSET_Z) << SHIFT_BY_Z;
final int x2 = ((x + 1) - OFFSET_X) << SHIFT_BY;
final int y2 = ((y + 1) - OFFSET_Y) << SHIFT_BY;
final int z2 = ((z + 1) - OFFSET_Z) << SHIFT_BY_Z;
if (Util.cubeIntersectsSphere(x1, y1, z1, x2, y2, z2, object.getX(), object.getY(), object.getZ(), range))
{
for (L2Object visibleObject : _worldRegions[x][y][z].getVisibleObjects().values())
{
if ((visibleObject == null) || (visibleObject == object) || !clazz.isInstance(visibleObject))
{
continue;
}
if (visibleObject.getInstanceWorld() != object.getInstanceWorld())
{
continue;
}
if (visibleObject.calculateDistance(object, true, false) <= range)
{
c.accept(clazz.cast(visibleObject));
}
}
}
}
}
}
}
public <T extends L2Object> List<T> getVisibleObjects(L2Object object, Class<T> clazz)
{
final List<T> result = new LinkedList<>();
forEachVisibleObject(object, clazz, result::add);
return result;
}
public <T extends L2Object> List<T> getVisibleObjects(L2Object object, Class<T> clazz, Predicate<T> predicate)
{
final List<T> result = new LinkedList<>();
forEachVisibleObject(object, clazz, o ->
{
if (predicate.test(o))
{
result.add(o);
}
});
return result;
}
public <T extends L2Object> List<T> getVisibleObjects(L2Object object, Class<T> clazz, int range)
{
final List<T> result = new LinkedList<>();
forEachVisibleObjectInRange(object, clazz, range, result::add);
return result;
}
public <T extends L2Object> List<T> getVisibleObjects(L2Object object, Class<T> clazz, int range, Predicate<T> predicate)
{
final List<T> result = new LinkedList<>();
forEachVisibleObjectInRange(object, clazz, range, o ->
{
if (predicate.test(o))
{
result.add(o);
}
});
return result;
}
/**
* Calculate the current WorldRegions of the object according to its position (x,y). <B><U> Example of use </U> :</B>
* <li>Set position of a new L2Object (drop, spawn...)</li>
* <li>Update position of a L2Object after a movement</li><BR>
* @param point position of the object
* @return
*/
public L2WorldRegion getRegion(ILocational point)
{
return getRegion(point.getX(), point.getY(), point.getZ());
}
public L2WorldRegion getRegion(int x, int y, int z)
{
try
{
return _worldRegions[(x >> SHIFT_BY) + OFFSET_X][(y >> SHIFT_BY) + OFFSET_Y][(z >> SHIFT_BY_Z) + OFFSET_Z];
}
catch (ArrayIndexOutOfBoundsException e)
{
_log.warning(getClass().getSimpleName() + ": Incorrect world region X: " + ((x >> SHIFT_BY) + OFFSET_X) + " Y: " + ((y >> SHIFT_BY) + OFFSET_Y) + " Z: " + ((z >> SHIFT_BY_Z) + OFFSET_Z) + " for coordinates x: " + x + " y: " + y + " z: " + z);
return null;
}
}
/**
* Returns the whole 3d array containing the world regions used by ZoneData.java to setup zones inside the world regions
* @return
*/
public L2WorldRegion[][][] getWorldRegions()
{
return _worldRegions;
}
/**
* Check if the current WorldRegions of the object is valid according to its position (x,y). <B><U> Example of use </U> :</B>
* <li>Init WorldRegions</li><BR>
* @param x X position of the object
* @param y Y position of the object
* @param z Z position of the object
* @return True if the WorldRegion is valid
*/
public static boolean validRegion(int x, int y, int z)
{
return ((x >= 0) && (x <= REGIONS_X) && (y >= 0) && (y <= REGIONS_Y)) && (z >= 0) && (z <= REGIONS_Z);
}
/**
* Deleted all spawns in the world.
*/
public void deleteVisibleNpcSpawns()
{
_log.info(getClass().getSimpleName() + ": Deleting all visible NPC's.");
for (int x = 0; x <= REGIONS_X; x++)
{
for (int y = 0; y <= REGIONS_Y; y++)
{
for (int z = 0; z <= REGIONS_Z; z++)
{
_worldRegions[x][y][z].deleteVisibleNpcSpawns();
}
}
}
_log.info(getClass().getSimpleName() + ": All visible NPC's deleted.");
}
/**
* @return the current instance of L2World
*/
public static L2World getInstance()
{
return SingletonHolder._instance;
}
private static class SingletonHolder
{
protected static final L2World _instance = new L2World();
}
}

View File

@@ -0,0 +1,388 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Collection;
import java.util.Collections;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ScheduledFuture;
import java.util.function.Predicate;
import java.util.logging.Logger;
import com.l2jmobius.Config;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.datatables.SpawnTable;
import com.l2jmobius.gameserver.model.actor.L2Attackable;
import com.l2jmobius.gameserver.model.actor.L2Npc;
import com.l2jmobius.gameserver.model.actor.L2Vehicle;
public final class L2WorldRegion
{
private static final Logger _log = Logger.getLogger(L2WorldRegion.class.getName());
/** Map containing visible objects in this world region. */
private volatile Map<Integer, L2Object> _visibleObjects;
private final int _regionX;
private final int _regionY;
private final int _regionZ;
private boolean _active = false;
private ScheduledFuture<?> _neighborsTask = null;
public L2WorldRegion(int regionX, int regionY, int regionZ)
{
_regionX = regionX;
_regionY = regionY;
_regionZ = regionZ;
// default a newly initialized region to inactive, unless always on is specified
_active = Config.GRIDS_ALWAYS_ON;
}
/** Task of AI notification */
public class NeighborsTask implements Runnable
{
private final boolean _isActivating;
public NeighborsTask(boolean isActivating)
{
_isActivating = isActivating;
}
@Override
public void run()
{
if (_isActivating)
{
// for each neighbor, if it's not active, activate.
forEachSurroundingRegion(w ->
{
w.setActive(true);
return true;
});
}
else
{
if (areNeighborsEmpty())
{
setActive(false);
}
// check and deactivate
forEachSurroundingRegion(w ->
{
if (w.areNeighborsEmpty())
{
w.setActive(false);
}
return true;
});
}
}
}
private void switchAI(boolean isOn)
{
if (_visibleObjects == null)
{
return;
}
int c = 0;
if (!isOn)
{
final Collection<L2Object> vObj = _visibleObjects.values();
for (L2Object o : vObj)
{
if (o instanceof L2Attackable)
{
c++;
final L2Attackable mob = (L2Attackable) o;
// Set target to null and cancel Attack or Cast
mob.setTarget(null);
// Stop movement
mob.stopMove(null);
// Stop all active skills effects in progress on the L2Character
mob.stopAllEffects();
mob.clearAggroList();
mob.getAttackByList().clear();
// stop the ai tasks
if (mob.hasAI())
{
mob.getAI().setIntention(com.l2jmobius.gameserver.ai.CtrlIntention.AI_INTENTION_IDLE);
mob.getAI().stopAITask();
}
}
else if (o instanceof L2Vehicle)
{
c++;
}
}
_log.finer(c + " mobs were turned off");
}
else
{
final Collection<L2Object> vObj = _visibleObjects.values();
for (L2Object o : vObj)
{
if (o instanceof L2Attackable)
{
c++;
// Start HP/MP/CP Regeneration task
((L2Attackable) o).getStatus().startHpMpRegeneration();
}
else if (o instanceof L2Npc)
{
((L2Npc) o).startRandomAnimationTask();
}
}
_log.finer(c + " mobs were turned on");
}
}
public boolean isActive()
{
return _active;
}
public boolean areNeighborsEmpty()
{
return !forEachSurroundingRegion(w ->
{
return !(w.isActive() && w.getVisibleObjects().values().stream().anyMatch(L2Object::isPlayable));
});
}
/**
* this function turns this region's AI and geodata on or off
* @param value
*/
public void setActive(boolean value)
{
if (_active == value)
{
return;
}
_active = value;
// turn the AI on or off to match the region's activation.
switchAI(value);
_log.finer((value ? "Starting" : "Stoping") + " Grid " + getName());
}
/**
* Immediately sets self as active and starts a timer to set neighbors as active this timer is to avoid turning on neighbors in the case when a person just teleported into a region and then teleported out immediately...there is no reason to activate all the neighbors in that case.
*/
private void startActivation()
{
// first set self to active and do self-tasks...
setActive(true);
// if the timer to deactivate neighbors is running, cancel it.
synchronized (this)
{
if (_neighborsTask != null)
{
_neighborsTask.cancel(true);
_neighborsTask = null;
}
// then, set a timer to activate the neighbors
_neighborsTask = ThreadPoolManager.getInstance().scheduleGeneral(new NeighborsTask(true), 1000 * Config.GRID_NEIGHBOR_TURNON_TIME);
}
}
/**
* starts a timer to set neighbors (including self) as inactive this timer is to avoid turning off neighbors in the case when a person just moved out of a region that he may very soon return to. There is no reason to turn self & neighbors off in that case.
*/
private void startDeactivation()
{
// if the timer to activate neighbors is running, cancel it.
synchronized (this)
{
if (_neighborsTask != null)
{
_neighborsTask.cancel(true);
_neighborsTask = null;
}
// start a timer to "suggest" a deactivate to self and neighbors.
// suggest means: first check if a neighbor has L2PcInstances in it. If not, deactivate.
_neighborsTask = ThreadPoolManager.getInstance().scheduleGeneral(new NeighborsTask(false), 1000 * Config.GRID_NEIGHBOR_TURNOFF_TIME);
}
}
/**
* Add the L2Object in the L2ObjectHashSet(L2Object) _visibleObjects containing L2Object visible in this L2WorldRegion <BR>
* If L2Object is a L2PcInstance, Add the L2PcInstance in the L2ObjectHashSet(L2PcInstance) _allPlayable containing L2PcInstance of all player in game in this L2WorldRegion <BR>
* Assert : object.getCurrentWorldRegion() == this
* @param object
*/
public void addVisibleObject(L2Object object)
{
if (object == null)
{
return;
}
assert object.getWorldRegion() == this;
if (_visibleObjects == null)
{
synchronized (object)
{
if (_visibleObjects == null)
{
_visibleObjects = new ConcurrentHashMap<>();
}
}
}
_visibleObjects.put(object.getObjectId(), object);
if (object.isPlayable())
{
// if this is the first player to enter the region, activate self & neighbors
if (!isActive() && (!Config.GRIDS_ALWAYS_ON))
{
startActivation();
}
}
}
/**
* Remove the L2Object from the L2ObjectHashSet(L2Object) _visibleObjects in this L2WorldRegion. If L2Object is a L2PcInstance, remove it from the L2ObjectHashSet(L2PcInstance) _allPlayable of this L2WorldRegion <BR>
* Assert : object.getCurrentWorldRegion() == this || object.getCurrentWorldRegion() == null
* @param object
*/
public void removeVisibleObject(L2Object object)
{
if (object == null)
{
return;
}
assert (object.getWorldRegion() == this) || (object.getWorldRegion() == null);
if (_visibleObjects == null)
{
return;
}
_visibleObjects.remove(object.getObjectId());
if (object.isPlayable())
{
if (areNeighborsEmpty() && !Config.GRIDS_ALWAYS_ON)
{
startDeactivation();
}
}
}
public Map<Integer, L2Object> getVisibleObjects()
{
return _visibleObjects != null ? _visibleObjects : Collections.emptyMap();
}
public String getName()
{
return "(" + _regionX + ", " + _regionY + ", " + _regionZ + ")";
}
/**
* Deleted all spawns in the world.
*/
public void deleteVisibleNpcSpawns()
{
if (_visibleObjects == null)
{
return;
}
_log.finer("Deleting all visible NPC's in Region: " + getName());
final Collection<L2Object> vNPC = _visibleObjects.values();
for (L2Object obj : vNPC)
{
if (obj instanceof L2Npc)
{
final L2Npc target = (L2Npc) obj;
target.deleteMe();
final L2Spawn spawn = target.getSpawn();
if (spawn != null)
{
spawn.stopRespawn();
SpawnTable.getInstance().deleteSpawn(spawn, false);
}
_log.finest("Removed NPC " + target.getObjectId());
}
}
_log.info("All visible NPC's deleted in Region: " + getName());
}
public boolean forEachSurroundingRegion(Predicate<L2WorldRegion> p)
{
for (int x = _regionX - 1; x <= (_regionX + 1); x++)
{
for (int y = _regionY - 1; y <= (_regionY + 1); y++)
{
for (int z = _regionZ - 1; z <= (_regionZ + 1); z++)
{
if (L2World.validRegion(x, y, z))
{
final L2WorldRegion worldRegion = L2World.getInstance().getWorldRegions()[x][y][z];
if (!p.test(worldRegion))
{
return false;
}
}
}
}
}
return true;
}
public int getRegionX()
{
return _regionX;
}
public int getRegionY()
{
return _regionY;
}
public int getRegionZ()
{
return _regionZ;
}
public boolean isSurroundingRegion(L2WorldRegion region)
{
return (region != null) && (getRegionX() >= (region.getRegionX() - 1)) && (getRegionX() <= (region.getRegionX() + 1)) && (getRegionY() >= (region.getRegionY() - 1)) && (getRegionY() <= (region.getRegionY() + 1)) && (getRegionZ() >= (region.getRegionZ() - 1)) && (getRegionZ() <= (region.getRegionZ() + 1));
}
}

View File

@@ -0,0 +1,195 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.interfaces.ILocational;
import com.l2jmobius.gameserver.model.interfaces.IPositionable;
/**
* Location data transfer object.<br>
* Contains coordinates data, heading and instance Id.
* @author Zoey76
*/
public class Location implements IPositionable
{
private int _x;
private int _y;
private int _z;
private int _heading;
public Location(int x, int y, int z)
{
this(x, y, z, 0);
}
public Location(int x, int y, int z, int heading)
{
_x = x;
_y = y;
_z = z;
_heading = heading;
}
public Location(L2Object obj)
{
this(obj.getX(), obj.getY(), obj.getZ(), obj.getHeading());
}
public Location(StatsSet set)
{
_x = set.getInt("x");
_y = set.getInt("y");
_z = set.getInt("z");
_heading = set.getInt("heading", 0);
}
/**
* Get the x coordinate.
* @return the x coordinate
*/
@Override
public int getX()
{
return _x;
}
/**
* Set the x coordinate.
* @param x the x coordinate
*/
@Override
public void setX(int x)
{
_x = x;
}
/**
* Get the y coordinate.
* @return the y coordinate
*/
@Override
public int getY()
{
return _y;
}
/**
* Set the y coordinate.
* @param y the x coordinate
*/
@Override
public void setY(int y)
{
_y = y;
}
/**
* Get the z coordinate.
* @return the z coordinate
*/
@Override
public int getZ()
{
return _z;
}
/**
* Set the z coordinate.
* @param z the z coordinate
*/
@Override
public void setZ(int z)
{
_z = z;
}
/**
* Set the x, y, z coordinates.
* @param x the x coordinate
* @param y the y coordinate
* @param z the z coordinate
*/
@Override
public void setXYZ(int x, int y, int z)
{
setX(x);
setY(y);
setZ(z);
}
/**
* Set the x, y, z coordinates.
* @param loc The location.
*/
@Override
public void setXYZ(ILocational loc)
{
setXYZ(loc.getX(), loc.getY(), loc.getZ());
}
/**
* Get the heading.
* @return the heading
*/
@Override
public int getHeading()
{
return _heading;
}
/**
* Set the heading.
* @param heading the heading
*/
@Override
public void setHeading(int heading)
{
_heading = heading;
}
@Override
public IPositionable getLocation()
{
return this;
}
@Override
public void setLocation(Location loc)
{
_x = loc.getX();
_y = loc.getY();
_z = loc.getZ();
_heading = loc.getHeading();
}
@Override
public boolean equals(Object obj)
{
if ((obj != null) && (obj instanceof Location))
{
final Location loc = (Location) obj;
return (getX() == loc.getX()) && (getY() == loc.getY()) && (getZ() == loc.getZ()) && (getHeading() == loc.getHeading());
}
return false;
}
@Override
public String toString()
{
return "[" + getClass().getSimpleName() + "] X: " + getX() + " Y: " + getY() + " Z: " + getZ() + " Heading: " + _heading;
}
}

View File

@@ -0,0 +1,116 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.List;
import com.l2jmobius.gameserver.model.interfaces.IIdentifiable;
import com.l2jmobius.gameserver.model.interfaces.INamable;
public class Macro implements IIdentifiable, INamable
{
private int _id;
private final int _icon;
private final String _name;
private final String _descr;
private final String _acronym;
private final List<MacroCmd> _commands;
/**
* Constructor for macros.
* @param id the macro ID
* @param icon the icon ID
* @param name the macro name
* @param descr the macro description
* @param acronym the macro acronym
* @param list the macro command list
*/
public Macro(int id, int icon, String name, String descr, String acronym, List<MacroCmd> list)
{
_id = id;
_icon = icon;
_name = name;
_descr = descr;
_acronym = acronym;
_commands = list;
}
/**
* Gets the marco ID.
* @returns the marco ID
*/
@Override
public int getId()
{
return _id;
}
/**
* Sets the marco ID.
* @param id the marco ID
*/
public void setId(int id)
{
_id = id;
}
/**
* Gets the macro icon ID.
* @return the icon
*/
public int getIcon()
{
return _icon;
}
/**
* Gets the macro name.
* @return the name
*/
@Override
public String getName()
{
return _name;
}
/**
* Gets the macro description.
* @return the description
*/
public String getDescr()
{
return _descr;
}
/**
* Gets the macro acronym.
* @return the acronym
*/
public String getAcronym()
{
return _acronym;
}
/**
* Gets the macro command list.
* @return the macro command list
*/
public List<MacroCmd> getCommands()
{
return _commands;
}
}

View File

@@ -0,0 +1,86 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.enums.MacroType;
/**
* Macro Cmd DTO.
* @author Zoey76
*/
public class MacroCmd
{
private final int _entry;
private final MacroType _type;
private final int _d1; // skill_id or page for shortcuts
private final int _d2; // shortcut
private final String _cmd;
public MacroCmd(int entry, MacroType type, int d1, int d2, String cmd)
{
_entry = entry;
_type = type;
_d1 = d1;
_d2 = d2;
_cmd = cmd;
}
/**
* Gets the entry index.
* @return the entry index
*/
public int getEntry()
{
return _entry;
}
/**
* Gets the macro type.
* @return the macro type
*/
public MacroType getType()
{
return _type;
}
/**
* Gets the skill ID, item ID, page ID, depending on the marco use.
* @return the first value
*/
public int getD1()
{
return _d1;
}
/**
* Gets the skill level, shortcut ID, depending on the marco use.
* @return the second value
*/
public int getD2()
{
return _d2;
}
/**
* Gets the command.
* @return the command
*/
public String getCmd()
{
return _cmd;
}
}

View File

@@ -0,0 +1,223 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.StringTokenizer;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.commons.database.DatabaseFactory;
import com.l2jmobius.gameserver.enums.MacroType;
import com.l2jmobius.gameserver.enums.MacroUpdateType;
import com.l2jmobius.gameserver.enums.ShortcutType;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.interfaces.IRestorable;
import com.l2jmobius.gameserver.network.serverpackets.SendMacroList;
public class MacroList implements IRestorable
{
private static final Logger _log = Logger.getLogger(MacroList.class.getName());
private final L2PcInstance _owner;
private int _macroId;
private final Map<Integer, Macro> _macroses = Collections.synchronizedMap(new LinkedHashMap<>());
public MacroList(L2PcInstance owner)
{
_owner = owner;
_macroId = 1000;
}
public Map<Integer, Macro> getAllMacroses()
{
return _macroses;
}
public void registerMacro(Macro macro)
{
MacroUpdateType updateType = MacroUpdateType.ADD;
if (macro.getId() == 0)
{
macro.setId(_macroId++);
while (_macroses.containsKey(macro.getId()))
{
macro.setId(_macroId++);
}
_macroses.put(macro.getId(), macro);
registerMacroInDb(macro);
}
else
{
updateType = MacroUpdateType.MODIFY;
final Macro old = _macroses.put(macro.getId(), macro);
if (old != null)
{
deleteMacroFromDb(old);
}
registerMacroInDb(macro);
}
_owner.sendPacket(new SendMacroList(1, macro, updateType));
}
public void deleteMacro(int id)
{
final Macro removed = _macroses.remove(id);
if (removed != null)
{
deleteMacroFromDb(removed);
}
final Shortcut[] allShortCuts = _owner.getAllShortCuts();
for (Shortcut sc : allShortCuts)
{
if ((sc.getId() == id) && (sc.getType() == ShortcutType.MACRO))
{
_owner.deleteShortCut(sc.getSlot(), sc.getPage());
}
}
_owner.sendPacket(new SendMacroList(0, removed, MacroUpdateType.DELETE));
}
public void sendAllMacros()
{
final Collection<Macro> allMacros = _macroses.values();
final int count = allMacros.size();
synchronized (_macroses)
{
if (allMacros.isEmpty())
{
_owner.sendPacket(new SendMacroList(0, null, MacroUpdateType.LIST));
}
else
{
for (Macro m : allMacros)
{
_owner.sendPacket(new SendMacroList(count, m, MacroUpdateType.LIST));
}
}
}
}
private void registerMacroInDb(Macro macro)
{
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement ps = con.prepareStatement("INSERT INTO character_macroses (charId,id,icon,name,descr,acronym,commands) values(?,?,?,?,?,?,?)"))
{
ps.setInt(1, _owner.getObjectId());
ps.setInt(2, macro.getId());
ps.setInt(3, macro.getIcon());
ps.setString(4, macro.getName());
ps.setString(5, macro.getDescr());
ps.setString(6, macro.getAcronym());
final StringBuilder sb = new StringBuilder(300);
for (MacroCmd cmd : macro.getCommands())
{
sb.append(cmd.getType().ordinal() + "," + cmd.getD1() + "," + cmd.getD2());
if ((cmd.getCmd() != null) && (cmd.getCmd().length() > 0))
{
sb.append("," + cmd.getCmd());
}
sb.append(';');
}
if (sb.length() > 255)
{
sb.setLength(255);
}
ps.setString(7, sb.toString());
ps.execute();
}
catch (Exception e)
{
_log.log(Level.WARNING, "could not store macro:", e);
}
}
private void deleteMacroFromDb(Macro macro)
{
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement ps = con.prepareStatement("DELETE FROM character_macroses WHERE charId=? AND id=?"))
{
ps.setInt(1, _owner.getObjectId());
ps.setInt(2, macro.getId());
ps.execute();
}
catch (Exception e)
{
_log.log(Level.WARNING, "could not delete macro:", e);
}
}
@Override
public boolean restoreMe()
{
_macroses.clear();
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement ps = con.prepareStatement("SELECT charId, id, icon, name, descr, acronym, commands FROM character_macroses WHERE charId=?"))
{
ps.setInt(1, _owner.getObjectId());
try (ResultSet rset = ps.executeQuery())
{
while (rset.next())
{
final int id = rset.getInt("id");
final int icon = rset.getInt("icon");
final String name = rset.getString("name");
final String descr = rset.getString("descr");
final String acronym = rset.getString("acronym");
final List<MacroCmd> commands = new ArrayList<>();
final StringTokenizer st1 = new StringTokenizer(rset.getString("commands"), ";");
while (st1.hasMoreTokens())
{
final StringTokenizer st = new StringTokenizer(st1.nextToken(), ",");
if (st.countTokens() < 3)
{
continue;
}
final MacroType type = MacroType.values()[Integer.parseInt(st.nextToken())];
final int d1 = Integer.parseInt(st.nextToken());
final int d2 = Integer.parseInt(st.nextToken());
String cmd = "";
if (st.hasMoreTokens())
{
cmd = st.nextToken();
}
commands.add(new MacroCmd(commands.size(), type, d1, d2, cmd));
}
_macroses.put(id, new Macro(id, icon, name, descr, acronym, commands));
}
}
}
catch (Exception e)
{
_log.log(Level.WARNING, "could not store shortcuts:", e);
return false;
}
return true;
}
}

View File

@@ -0,0 +1,409 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import com.l2jmobius.commons.util.Rnd;
import com.l2jmobius.gameserver.ai.CtrlIntention;
import com.l2jmobius.gameserver.ai.L2ControllableMobAI;
import com.l2jmobius.gameserver.datatables.SpawnTable;
import com.l2jmobius.gameserver.model.actor.L2Character;
import com.l2jmobius.gameserver.model.actor.instance.L2ControllableMobInstance;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.actor.templates.L2NpcTemplate;
/**
* @author littlecrow
*/
public final class MobGroup
{
private final L2NpcTemplate _npcTemplate;
private final int _groupId;
private final int _maxMobCount;
private Set<L2ControllableMobInstance> _mobs;
public MobGroup(int groupId, L2NpcTemplate npcTemplate, int maxMobCount)
{
_groupId = groupId;
_npcTemplate = npcTemplate;
_maxMobCount = maxMobCount;
}
public int getActiveMobCount()
{
return getMobs().size();
}
public int getGroupId()
{
return _groupId;
}
public int getMaxMobCount()
{
return _maxMobCount;
}
public Set<L2ControllableMobInstance> getMobs()
{
if (_mobs == null)
{
_mobs = ConcurrentHashMap.newKeySet();
}
return _mobs;
}
public String getStatus()
{
try
{
final L2ControllableMobAI mobGroupAI = (L2ControllableMobAI) getMobs().stream().findFirst().get().getAI();
switch (mobGroupAI.getAlternateAI())
{
case L2ControllableMobAI.AI_NORMAL:
return "Idle";
case L2ControllableMobAI.AI_FORCEATTACK:
return "Force Attacking";
case L2ControllableMobAI.AI_FOLLOW:
return "Following";
case L2ControllableMobAI.AI_CAST:
return "Casting";
case L2ControllableMobAI.AI_ATTACK_GROUP:
return "Attacking Group";
default:
return "Idle";
}
}
catch (Exception e)
{
return "Unspawned";
}
}
public L2NpcTemplate getTemplate()
{
return _npcTemplate;
}
public boolean isGroupMember(L2ControllableMobInstance mobInst)
{
for (L2ControllableMobInstance groupMember : getMobs())
{
if (groupMember == null)
{
continue;
}
if (groupMember.getObjectId() == mobInst.getObjectId())
{
return true;
}
}
return false;
}
public void spawnGroup(int x, int y, int z)
{
if (getActiveMobCount() > 0)
{
return;
}
try
{
for (int i = 0; i < getMaxMobCount(); i++)
{
final L2GroupSpawn spawn = new L2GroupSpawn(getTemplate());
final int signX = (Rnd.nextInt(2) == 0) ? -1 : 1;
final int signY = (Rnd.nextInt(2) == 0) ? -1 : 1;
final int randX = Rnd.nextInt(MobGroupTable.RANDOM_RANGE);
final int randY = Rnd.nextInt(MobGroupTable.RANDOM_RANGE);
spawn.setX(x + (signX * randX));
spawn.setY(y + (signY * randY));
spawn.setZ(z);
spawn.stopRespawn();
SpawnTable.getInstance().addNewSpawn(spawn, false);
getMobs().add((L2ControllableMobInstance) spawn.doGroupSpawn());
}
}
catch (ClassNotFoundException e)
{
}
catch (NoSuchMethodException e2)
{
}
}
public void spawnGroup(L2PcInstance activeChar)
{
spawnGroup(activeChar.getX(), activeChar.getY(), activeChar.getZ());
}
public void teleportGroup(L2PcInstance player)
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
if (!mobInst.isDead())
{
final int x = player.getX() + Rnd.nextInt(50);
final int y = player.getY() + Rnd.nextInt(50);
mobInst.teleToLocation(new Location(x, y, player.getZ()), true);
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.follow(player);
}
}
}
public L2ControllableMobInstance getRandomMob()
{
removeDead();
if (getActiveMobCount() == 0)
{
return null;
}
int choice = Rnd.nextInt(getActiveMobCount());
for (L2ControllableMobInstance mob : getMobs())
{
if (--choice == 0)
{
return mob;
}
}
return null;
}
public void unspawnGroup()
{
removeDead();
if (getActiveMobCount() == 0)
{
return;
}
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
if (!mobInst.isDead())
{
mobInst.deleteMe();
}
SpawnTable.getInstance().deleteSpawn(mobInst.getSpawn(), false);
}
getMobs().clear();
}
public void killGroup(L2PcInstance activeChar)
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
if (!mobInst.isDead())
{
mobInst.reduceCurrentHp(mobInst.getMaxHp() + 1, activeChar, null);
}
SpawnTable.getInstance().deleteSpawn(mobInst.getSpawn(), false);
}
getMobs().clear();
}
public void setAttackRandom()
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.setAlternateAI(L2ControllableMobAI.AI_NORMAL);
ai.setIntention(CtrlIntention.AI_INTENTION_ACTIVE);
}
}
public void setAttackTarget(L2Character target)
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.forceAttack(target);
}
}
public void setIdleMode()
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.stop();
}
}
public void returnGroup(L2Character activeChar)
{
setIdleMode();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
final int signX = (Rnd.nextInt(2) == 0) ? -1 : 1;
final int signY = (Rnd.nextInt(2) == 0) ? -1 : 1;
final int randX = Rnd.nextInt(MobGroupTable.RANDOM_RANGE);
final int randY = Rnd.nextInt(MobGroupTable.RANDOM_RANGE);
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.move(activeChar.getX() + (signX * randX), activeChar.getY() + (signY * randY), activeChar.getZ());
}
}
public void setFollowMode(L2Character character)
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.follow(character);
}
}
public void setCastMode()
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.setAlternateAI(L2ControllableMobAI.AI_CAST);
}
}
public void setNoMoveMode(boolean enabled)
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.setNotMoving(enabled);
}
}
protected void removeDead()
{
getMobs().removeIf(L2Character::isDead);
}
public void setInvul(boolean invulState)
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst != null)
{
mobInst.setInvul(invulState);
}
}
}
public void setAttackGroup(MobGroup otherGrp)
{
removeDead();
for (L2ControllableMobInstance mobInst : getMobs())
{
if (mobInst == null)
{
continue;
}
final L2ControllableMobAI ai = (L2ControllableMobAI) mobInst.getAI();
ai.forceAttackGroup(otherGrp);
ai.setIntention(CtrlIntention.AI_INTENTION_ACTIVE);
}
}
}

View File

@@ -0,0 +1,85 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import com.l2jmobius.gameserver.model.actor.instance.L2ControllableMobInstance;
/**
* @author littlecrow
*/
public class MobGroupTable
{
private final Map<Integer, MobGroup> _groupMap = new ConcurrentHashMap<>();
public static final int FOLLOW_RANGE = 300;
public static final int RANDOM_RANGE = 300;
protected MobGroupTable()
{
}
public static MobGroupTable getInstance()
{
return SingletonHolder._instance;
}
public void addGroup(int groupKey, MobGroup group)
{
_groupMap.put(groupKey, group);
}
public MobGroup getGroup(int groupKey)
{
return _groupMap.get(groupKey);
}
public int getGroupCount()
{
return _groupMap.size();
}
public MobGroup getGroupForMob(L2ControllableMobInstance mobInst)
{
for (MobGroup mobGroup : _groupMap.values())
{
if (mobGroup.isGroupMember(mobInst))
{
return mobGroup;
}
}
return null;
}
public MobGroup[] getGroups()
{
return _groupMap.values().toArray(new MobGroup[getGroupCount()]);
}
public boolean removeGroup(int groupKey)
{
return (_groupMap.remove(groupKey) != null);
}
private static class SingletonHolder
{
protected static final MobGroupTable _instance = new MobGroupTable();
}
}

View File

@@ -0,0 +1,75 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.concurrent.ScheduledFuture;
import java.util.concurrent.atomic.AtomicInteger;
import com.l2jmobius.Config;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.model.actor.L2Character;
import com.l2jmobius.gameserver.model.actor.L2Npc;
import com.l2jmobius.gameserver.model.actor.templates.L2NpcTemplate;
/**
* @author UnAfraid
*/
public class MpRewardTask
{
private final AtomicInteger _count;
private final double _value;
private final ScheduledFuture<?> _task;
private final L2Character _creature;
public MpRewardTask(L2Character creature, L2Npc npc)
{
final L2NpcTemplate template = npc.getTemplate();
_creature = creature;
_count = new AtomicInteger(template.getMpRewardTicks());
_value = calculateBaseValue(npc, creature);
_task = ThreadPoolManager.getInstance().scheduleEffectAtFixedRate(this::run, Config.EFFECT_TICK_RATIO, Config.EFFECT_TICK_RATIO);
}
/**
* @param npc
* @param creature
* @return
*/
private double calculateBaseValue(L2Npc npc, L2Character creature)
{
final L2NpcTemplate template = npc.getTemplate();
switch (template.getMpRewardType())
{
case PER:
{
return (creature.getMaxMp() * (template.getMpRewardValue() / 100)) / template.getMpRewardTicks();
}
}
return template.getMpRewardValue() / template.getMpRewardTicks();
}
private void run()
{
if ((_count.decrementAndGet() <= 0) || (_creature.isPlayer() && !_creature.getActingPlayer().isOnline()))
{
_task.cancel(false);
return;
}
_creature.setCurrentMp(_creature.getCurrentMp() + _value);
}
}

View File

@@ -0,0 +1,81 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* @author UnAfraid
*/
public enum PcCondOverride
{
MAX_STATS_VALUE(0, "Overrides maximum states conditions"),
ITEM_CONDITIONS(1, "Overrides item usage conditions"),
SKILL_CONDITIONS(2, "Overrides skill usage conditions"),
ZONE_CONDITIONS(3, "Overrides zone conditions"),
CASTLE_CONDITIONS(4, "Overrides castle conditions"),
FORTRESS_CONDITIONS(5, "Overrides fortress conditions"),
CLANHALL_CONDITIONS(6, "Overrides clan hall conditions"),
FLOOD_CONDITIONS(7, "Overrides floods conditions"),
CHAT_CONDITIONS(8, "Overrides chat conditions"),
INSTANCE_CONDITIONS(9, "Overrides instance conditions"),
QUEST_CONDITIONS(10, "Overrides quest conditions"),
DEATH_PENALTY(11, "Overrides death penalty conditions"),
DESTROY_ALL_ITEMS(12, "Overrides item destroy conditions"),
SEE_ALL_PLAYERS(13, "Overrides the conditions to see hidden players"),
TARGET_ALL(14, "Overrides target conditions"),
DROP_ALL_ITEMS(15, "Overrides item drop conditions");
private final int _mask;
private final String _descr;
PcCondOverride(int id, String descr)
{
_mask = 1 << id;
_descr = descr;
}
public int getMask()
{
return _mask;
}
public String getDescription()
{
return _descr;
}
public static PcCondOverride getCondOverride(int ordinal)
{
try
{
return values()[ordinal];
}
catch (Exception e)
{
return null;
}
}
public static long getAllExceptionsMask()
{
long result = 0L;
for (PcCondOverride ex : values())
{
result |= ex.getMask();
}
return result;
}
}

View File

@@ -0,0 +1,178 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.List;
import java.util.concurrent.CopyOnWriteArrayList;
import com.l2jmobius.gameserver.enums.PetitionState;
import com.l2jmobius.gameserver.enums.PetitionType;
import com.l2jmobius.gameserver.idfactory.IdFactory;
import com.l2jmobius.gameserver.instancemanager.PetitionManager;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.CreatureSay;
import com.l2jmobius.gameserver.network.serverpackets.IClientOutgoingPacket;
import com.l2jmobius.gameserver.network.serverpackets.PetitionVotePacket;
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
/**
* Petition
* @author xban1x
*/
public final class Petition
{
private final long _submitTime = System.currentTimeMillis();
private final int _id;
private final PetitionType _type;
private PetitionState _state = PetitionState.PENDING;
private final String _content;
private final List<CreatureSay> _messageLog = new CopyOnWriteArrayList<>();
private final L2PcInstance _petitioner;
private L2PcInstance _responder;
public Petition(L2PcInstance petitioner, String petitionText, int petitionType)
{
_id = IdFactory.getInstance().getNextId();
_type = PetitionType.values()[--petitionType];
_content = petitionText;
_petitioner = petitioner;
}
public boolean addLogMessage(CreatureSay cs)
{
return _messageLog.add(cs);
}
public List<CreatureSay> getLogMessages()
{
return _messageLog;
}
public boolean endPetitionConsultation(PetitionState endState)
{
setState(endState);
if ((getResponder() != null) && getResponder().isOnline())
{
if (endState == PetitionState.RESPONDER_REJECT)
{
getPetitioner().sendMessage("Your petition was rejected. Please try again later.");
}
else
{
// Ending petition consultation with <Player>.
SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.PETITION_CONSULTATION_WITH_C1_HAS_ENDED);
sm.addString(getPetitioner().getName());
getResponder().sendPacket(sm);
if (endState == PetitionState.PETITIONER_CANCEL)
{
// Receipt No. <ID> petition cancelled.
sm = SystemMessage.getSystemMessage(SystemMessageId.RECEIPT_NO_S1_PETITION_CANCELLED);
sm.addInt(getId());
getResponder().sendPacket(sm);
}
}
}
// End petition consultation and inform them, if they are still online. And if petitioner is online, enable Evaluation button
if ((getPetitioner() != null) && getPetitioner().isOnline())
{
getPetitioner().sendPacket(SystemMessageId.THIS_ENDS_THE_GM_PETITION_CONSULTATION_NPLEASE_GIVE_US_FEEDBACK_ON_THE_PETITION_SERVICE);
getPetitioner().sendPacket(PetitionVotePacket.STATIC_PACKET);
}
PetitionManager.getInstance().getCompletedPetitions().put(getId(), this);
return (PetitionManager.getInstance().getPendingPetitions().remove(getId()) != null);
}
public String getContent()
{
return _content;
}
public int getId()
{
return _id;
}
public L2PcInstance getPetitioner()
{
return _petitioner;
}
public L2PcInstance getResponder()
{
return _responder;
}
public long getSubmitTime()
{
return _submitTime;
}
public PetitionState getState()
{
return _state;
}
public String getTypeAsString()
{
return _type.toString().replace("_", " ");
}
public void sendPetitionerPacket(IClientOutgoingPacket responsePacket)
{
if ((getPetitioner() == null) || !getPetitioner().isOnline())
{
// Allows petitioners to see the results of their petition when
// they log back into the game.
// endPetitionConsultation(PetitionState.Petitioner_Missing);
return;
}
getPetitioner().sendPacket(responsePacket);
}
public void sendResponderPacket(IClientOutgoingPacket responsePacket)
{
if ((getResponder() == null) || !getResponder().isOnline())
{
endPetitionConsultation(PetitionState.RESPONDER_MISSING);
return;
}
getResponder().sendPacket(responsePacket);
}
public void setState(PetitionState state)
{
_state = state;
}
public void setResponder(L2PcInstance respondingAdmin)
{
if (getResponder() != null)
{
return;
}
_responder = respondingAdmin;
}
}

View File

@@ -0,0 +1,100 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.LinkedList;
import java.util.List;
import com.l2jmobius.gameserver.model.interfaces.ILocational;
/**
* @author UnAfraid
*/
public class SayuneEntry implements ILocational
{
private boolean _isSelector = false;
private final int _id;
private int _x;
private int _y;
private int _z;
private final List<SayuneEntry> _innerEntries = new LinkedList<>();
public SayuneEntry(int id)
{
_id = id;
}
public SayuneEntry(boolean isSelector, int id, int x, int y, int z)
{
_isSelector = isSelector;
_id = id;
_x = x;
_y = y;
_z = z;
}
public int getId()
{
return _id;
}
@Override
public int getX()
{
return _x;
}
@Override
public int getY()
{
return _y;
}
@Override
public int getZ()
{
return _z;
}
@Override
public int getHeading()
{
return 0;
}
@Override
public ILocational getLocation()
{
return new Location(_x, _y, _z);
}
public boolean isSelector()
{
return _isSelector;
}
public List<SayuneEntry> getInnerEntries()
{
return _innerEntries;
}
public SayuneEntry addInnerEntry(SayuneEntry innerEntry)
{
_innerEntries.add(innerEntry);
return innerEntry;
}
}

View File

@@ -0,0 +1,79 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.concurrent.atomic.AtomicLong;
/**
* @author xban1x
*/
public class SeedProduction
{
private final int _seedId;
private final long _price;
private final long _startAmount;
private final AtomicLong _amount;
public SeedProduction(int id, long amount, long price, long startAmount)
{
_seedId = id;
_amount = new AtomicLong(amount);
_price = price;
_startAmount = startAmount;
}
public final int getId()
{
return _seedId;
}
public final long getAmount()
{
return _amount.get();
}
public final long getPrice()
{
return _price;
}
public final long getStartAmount()
{
return _startAmount;
}
public final void setAmount(long amount)
{
_amount.set(amount);
}
public final boolean decreaseAmount(long val)
{
long current, next;
do
{
current = _amount.get();
next = current - val;
if (next < 0)
{
return false;
}
}
while (!_amount.compareAndSet(current, next));
return true;
}
}

View File

@@ -0,0 +1,245 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.Map;
import java.util.TreeMap;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.commons.database.DatabaseFactory;
import com.l2jmobius.gameserver.enums.ShortcutType;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.interfaces.IRestorable;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
import com.l2jmobius.gameserver.model.items.type.EtcItemType;
import com.l2jmobius.gameserver.network.serverpackets.ExAutoSoulShot;
import com.l2jmobius.gameserver.network.serverpackets.ShortCutInit;
import com.l2jmobius.gameserver.network.serverpackets.ShortCutRegister;
public class ShortCuts implements IRestorable
{
private static Logger _log = Logger.getLogger(ShortCuts.class.getName());
private static final int MAX_SHORTCUTS_PER_BAR = 12;
private final L2PcInstance _owner;
private final Map<Integer, Shortcut> _shortCuts = new TreeMap<>();
public ShortCuts(L2PcInstance owner)
{
_owner = owner;
}
public Shortcut[] getAllShortCuts()
{
return _shortCuts.values().toArray(new Shortcut[_shortCuts.values().size()]);
}
public Shortcut getShortCut(int slot, int page)
{
Shortcut sc = _shortCuts.get(slot + (page * MAX_SHORTCUTS_PER_BAR));
// Verify shortcut
if ((sc != null) && (sc.getType() == ShortcutType.ITEM))
{
if (_owner.getInventory().getItemByObjectId(sc.getId()) == null)
{
deleteShortCut(sc.getSlot(), sc.getPage());
sc = null;
}
}
return sc;
}
public synchronized void registerShortCut(Shortcut shortcut)
{
// Verify shortcut
if (shortcut.getType() == ShortcutType.ITEM)
{
final L2ItemInstance item = _owner.getInventory().getItemByObjectId(shortcut.getId());
if (item == null)
{
return;
}
shortcut.setSharedReuseGroup(item.getSharedReuseGroup());
}
final Shortcut oldShortCut = _shortCuts.put(shortcut.getSlot() + (shortcut.getPage() * MAX_SHORTCUTS_PER_BAR), shortcut);
registerShortCutInDb(shortcut, oldShortCut);
}
private void registerShortCutInDb(Shortcut shortcut, Shortcut oldShortCut)
{
if (oldShortCut != null)
{
deleteShortCutFromDb(oldShortCut);
}
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement("REPLACE INTO character_shortcuts (charId,slot,page,type,shortcut_id,level,sub_level,class_index) values(?,?,?,?,?,?,?,?)"))
{
statement.setInt(1, _owner.getObjectId());
statement.setInt(2, shortcut.getSlot());
statement.setInt(3, shortcut.getPage());
statement.setInt(4, shortcut.getType().ordinal());
statement.setInt(5, shortcut.getId());
statement.setInt(6, shortcut.getLevel());
statement.setInt(7, shortcut.getSubLevel());
statement.setInt(8, _owner.getClassIndex());
statement.execute();
}
catch (Exception e)
{
_log.log(Level.WARNING, "Could not store character shortcut: " + e.getMessage(), e);
}
}
/**
* @param slot
* @param page
*/
public synchronized void deleteShortCut(int slot, int page)
{
final Shortcut old = _shortCuts.remove(slot + (page * MAX_SHORTCUTS_PER_BAR));
if ((old == null) || (_owner == null))
{
return;
}
deleteShortCutFromDb(old);
if (old.getType() == ShortcutType.ITEM)
{
final L2ItemInstance item = _owner.getInventory().getItemByObjectId(old.getId());
if ((item != null) && (item.getItemType() == EtcItemType.SOULSHOT))
{
if (_owner.removeAutoSoulShot(item.getId()))
{
_owner.sendPacket(new ExAutoSoulShot(item.getId(), false, 0));
}
}
}
_owner.sendPacket(new ShortCutInit(_owner));
for (int shotId : _owner.getAutoSoulShot())
{
_owner.sendPacket(new ExAutoSoulShot(shotId, true, 0));
}
}
public synchronized void deleteShortCutByObjectId(int objectId)
{
for (Shortcut shortcut : _shortCuts.values())
{
if ((shortcut.getType() == ShortcutType.ITEM) && (shortcut.getId() == objectId))
{
deleteShortCut(shortcut.getSlot(), shortcut.getPage());
break;
}
}
}
/**
* @param shortcut
*/
private void deleteShortCutFromDb(Shortcut shortcut)
{
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement("DELETE FROM character_shortcuts WHERE charId=? AND slot=? AND page=? AND class_index=?"))
{
statement.setInt(1, _owner.getObjectId());
statement.setInt(2, shortcut.getSlot());
statement.setInt(3, shortcut.getPage());
statement.setInt(4, _owner.getClassIndex());
statement.execute();
}
catch (Exception e)
{
_log.log(Level.WARNING, "Could not delete character shortcut: " + e.getMessage(), e);
}
}
@Override
public boolean restoreMe()
{
_shortCuts.clear();
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement("SELECT charId, slot, page, type, shortcut_id, level, sub_level FROM character_shortcuts WHERE charId=? AND class_index=?"))
{
statement.setInt(1, _owner.getObjectId());
statement.setInt(2, _owner.getClassIndex());
try (ResultSet rset = statement.executeQuery())
{
while (rset.next())
{
final int slot = rset.getInt("slot");
final int page = rset.getInt("page");
final int type = rset.getInt("type");
final int id = rset.getInt("shortcut_id");
final int level = rset.getInt("level");
final int subLevel = rset.getInt("sub_level");
_shortCuts.put(slot + (page * MAX_SHORTCUTS_PER_BAR), new Shortcut(slot, page, ShortcutType.values()[type], id, level, subLevel, 1));
}
}
}
catch (Exception e)
{
_log.log(Level.WARNING, "Could not restore character shortcuts: " + e.getMessage(), e);
return false;
}
// Verify shortcuts
for (Shortcut sc : getAllShortCuts())
{
if (sc.getType() == ShortcutType.ITEM)
{
final L2ItemInstance item = _owner.getInventory().getItemByObjectId(sc.getId());
if (item == null)
{
deleteShortCut(sc.getSlot(), sc.getPage());
}
else if (item.isEtcItem())
{
sc.setSharedReuseGroup(item.getEtcItem().getSharedReuseGroup());
}
}
}
return true;
}
/**
* Updates the shortcut bars with the new skill.
* @param skillId the skill Id to search and update.
* @param skillLevel the skill level to update.
* @param skillSubLevel the skill sub level to update.
*/
public synchronized void updateShortCuts(int skillId, int skillLevel, int skillSubLevel)
{
// Update all the shortcuts for this skill
for (Shortcut sc : _shortCuts.values())
{
if ((sc.getId() == skillId) && (sc.getType() == ShortcutType.SKILL))
{
final Shortcut newsc = new Shortcut(sc.getSlot(), sc.getPage(), sc.getType(), sc.getId(), skillLevel, skillSubLevel, 1);
_owner.sendPacket(new ShortCutRegister(newsc));
_owner.registerShortCut(newsc);
}
}
}
}

View File

@@ -0,0 +1,135 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.enums.ShortcutType;
/**
* Shortcut DTO.
* @author Zoey76
*/
public class Shortcut
{
/** Slot from 0 to 11. */
private final int _slot;
/** Page from 0 to 9. */
private final int _page;
/** Type: item, skill, action, macro, recipe, bookmark. */
private final ShortcutType _type;
/** Shortcut ID. */
private final int _id;
/** Shortcut level (skills). */
private final int _level;
/** Shortcut level (skills). */
private final int _subLevel;
/** Character type: 1 player, 2 summon. */
private final int _characterType;
/** Shared reuse group. */
private int _sharedReuseGroup = -1;
public Shortcut(int slot, int page, ShortcutType type, int id, int level, int subLevel, int characterType)
{
_slot = slot;
_page = page;
_type = type;
_id = id;
_level = level;
_subLevel = subLevel;
_characterType = characterType;
}
/**
* Gets the shortcut ID.
* @return the ID
*/
public int getId()
{
return _id;
}
/**
* Gets the shortcut level.
* @return the level
*/
public int getLevel()
{
return _level;
}
/**
* Gets the shortcut level.
* @return the level
*/
public int getSubLevel()
{
return _subLevel;
}
/**
* Gets the shortcut page.
* @return the page
*/
public int getPage()
{
return _page;
}
/**
* Gets the shortcut slot.
* @return the slot
*/
public int getSlot()
{
return _slot;
}
/**
* Gets the shortcut type.
* @return the type
*/
public ShortcutType getType()
{
return _type;
}
/**
* Gets the shortcut character type.
* @return the character type
*/
public int getCharacterType()
{
return _characterType;
}
/**
* Gets the shared reuse group.
* @return the shared reuse group
*/
public int getSharedReuseGroup()
{
return _sharedReuseGroup;
}
/**
* Sets the shared reuse group.
* @param sharedReuseGroup the shared reuse group to set
*/
public void setSharedReuseGroup(int sharedReuseGroup)
{
_sharedReuseGroup = sharedReuseGroup;
}
}

View File

@@ -0,0 +1,51 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Calendar;
/**
* @author UnAfraid
*/
public class SiegeScheduleDate
{
private final int _day;
private final int _hour;
private final int _maxConcurrent;
public SiegeScheduleDate(StatsSet set)
{
_day = set.getInt("day", Calendar.SUNDAY);
_hour = set.getInt("hour", 16);
_maxConcurrent = set.getInt("maxConcurrent", 5);
}
public int getDay()
{
return _day;
}
public int getHour()
{
return _hour;
}
public int getMaxConcurrent()
{
return _maxConcurrent;
}
}

View File

@@ -0,0 +1,28 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.actor.L2Npc;
/**
* This class ...
* @version $Revision: 1.2 $ $Date: 2004/06/27 08:12:59 $
*/
public interface SpawnListener
{
void npcSpawned(L2Npc npc);
}

View File

@@ -0,0 +1,957 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.time.Duration;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import java.util.Map;
import java.util.Objects;
import java.util.concurrent.ConcurrentHashMap;
import java.util.function.Supplier;
import java.util.logging.Level;
import java.util.logging.Logger;
import java.util.stream.Collectors;
import com.l2jmobius.commons.util.TimeUtil;
import com.l2jmobius.gameserver.model.holders.MinionHolder;
import com.l2jmobius.gameserver.model.holders.SkillHolder;
import com.l2jmobius.gameserver.model.interfaces.IParserAdvUtils;
import com.l2jmobius.gameserver.util.Util;
/**
* This class is meant to hold a set of (key,value) pairs.<br>
* They are stored as object but can be retrieved in any type wanted. As long as cast is available.<br>
* @author mkizub
*/
public class StatsSet implements IParserAdvUtils
{
private static final Logger LOGGER = Logger.getLogger(StatsSet.class.getName());
/** Static empty immutable map, used to avoid multiple null checks over the source. */
public static final StatsSet EMPTY_STATSET = new StatsSet(Collections.emptyMap());
private final Map<String, Object> _set;
public StatsSet()
{
this(ConcurrentHashMap::new);
}
public StatsSet(Supplier<Map<String, Object>> mapFactory)
{
this(mapFactory.get());
}
public StatsSet(Map<String, Object> map)
{
_set = map;
}
/**
* Returns the set of values
* @return HashMap
*/
public final Map<String, Object> getSet()
{
return _set;
}
/**
* Add a set of couple values in the current set
* @param newSet : StatsSet pointing out the list of couples to add in the current set
*/
public void merge(StatsSet newSet)
{
_set.putAll(newSet.getSet());
}
/**
* Verifies if the stat set is empty.
* @return {@code true} if the stat set is empty, {@code false} otherwise
*/
public boolean isEmpty()
{
return _set.isEmpty();
}
/**
* Return the boolean value associated with key.
* @param key : String designating the key in the set
* @return boolean : value associated to the key
* @throws IllegalArgumentException : If value is not set or value is not boolean
*/
@Override
public boolean getBoolean(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Boolean value required, but not specified");
}
if (val instanceof Boolean)
{
return ((Boolean) val).booleanValue();
}
try
{
return Boolean.parseBoolean((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Boolean value required, but found: " + val);
}
}
/**
* Return the boolean value associated with key.<br>
* If no value is associated with key, or type of value is wrong, returns defaultValue.
* @param key : String designating the key in the entry set
* @return boolean : value associated to the key
*/
@Override
public boolean getBoolean(String key, boolean defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
if (val instanceof Boolean)
{
return ((Boolean) val).booleanValue();
}
try
{
return Boolean.parseBoolean((String) val);
}
catch (Exception e)
{
return defaultValue;
}
}
@Override
public byte getByte(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Byte value required, but not specified");
}
if (val instanceof Number)
{
return ((Number) val).byteValue();
}
try
{
return Byte.parseByte((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Byte value required, but found: " + val);
}
}
@Override
public byte getByte(String key, byte defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
if (val instanceof Number)
{
return ((Number) val).byteValue();
}
try
{
return Byte.parseByte((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Byte value required, but found: " + val);
}
}
public short increaseByte(String key, byte increaseWith)
{
final byte newValue = (byte) (getByte(key) + increaseWith);
set(key, newValue);
return newValue;
}
public short increaseByte(String key, byte defaultValue, byte increaseWith)
{
final byte newValue = (byte) (getByte(key, defaultValue) + increaseWith);
set(key, newValue);
return newValue;
}
public byte[] getByteArray(String key, String splitOn)
{
Objects.requireNonNull(key);
Objects.requireNonNull(splitOn);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Byte value required, but not specified");
}
if (val instanceof Number)
{
return new byte[]
{
((Number) val).byteValue()
};
}
int c = 0;
final String[] vals = ((String) val).split(splitOn);
final byte[] result = new byte[vals.length];
for (String v : vals)
{
try
{
result[c++] = Byte.parseByte(v);
}
catch (Exception e)
{
throw new IllegalArgumentException("Byte value required, but found: " + val);
}
}
return result;
}
public List<Byte> getByteList(String key, String splitOn)
{
Objects.requireNonNull(key);
Objects.requireNonNull(splitOn);
final List<Byte> result = new ArrayList<>();
for (Byte i : getByteArray(key, splitOn))
{
result.add(i);
}
return result;
}
@Override
public short getShort(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Short value required, but not specified");
}
if (val instanceof Number)
{
return ((Number) val).shortValue();
}
try
{
return Short.parseShort((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Short value required, but found: " + val);
}
}
@Override
public short getShort(String key, short defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
if (val instanceof Number)
{
return ((Number) val).shortValue();
}
try
{
return Short.parseShort((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Short value required, but found: " + val);
}
}
public short increaseShort(String key, short increaseWith)
{
final short newValue = (short) (getShort(key) + increaseWith);
set(key, newValue);
return newValue;
}
public short increaseShort(String key, short defaultValue, short increaseWith)
{
final short newValue = (short) (getShort(key, defaultValue) + increaseWith);
set(key, newValue);
return newValue;
}
@Override
public int getInt(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Integer value required, but not specified: " + key + "!");
}
if (val instanceof Number)
{
return ((Number) val).intValue();
}
try
{
return Integer.parseInt((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Integer value required, but found: " + val + "!");
}
}
@Override
public int getInt(String key, int defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
if (val instanceof Number)
{
return ((Number) val).intValue();
}
try
{
return Integer.parseInt((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Integer value required, but found: " + val);
}
}
public int increaseInt(String key, int increaseWith)
{
final int newValue = getInt(key) + increaseWith;
set(key, newValue);
return newValue;
}
public int increaseInt(String key, int defaultValue, int increaseWith)
{
final int newValue = getInt(key, defaultValue) + increaseWith;
set(key, newValue);
return newValue;
}
public int[] getIntArray(String key, String splitOn)
{
Objects.requireNonNull(key);
Objects.requireNonNull(splitOn);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Integer value required, but not specified");
}
if (val instanceof Number)
{
return new int[]
{
((Number) val).intValue()
};
}
int c = 0;
final String[] vals = ((String) val).split(splitOn);
final int[] result = new int[vals.length];
for (String v : vals)
{
try
{
result[c++] = Integer.parseInt(v);
}
catch (Exception e)
{
throw new IllegalArgumentException("Integer value required, but found: " + val);
}
}
return result;
}
public List<Integer> getIntegerList(String key, String splitOn)
{
Objects.requireNonNull(key);
Objects.requireNonNull(splitOn);
final List<Integer> result = new ArrayList<>();
for (int i : getIntArray(key, splitOn))
{
result.add(i);
}
return result;
}
@Override
public long getLong(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Long value required, but not specified");
}
if (val instanceof Number)
{
return ((Number) val).longValue();
}
try
{
return Long.parseLong((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Long value required, but found: " + val);
}
}
@Override
public long getLong(String key, long defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
if (val instanceof Number)
{
return ((Number) val).longValue();
}
try
{
return Long.parseLong((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Long value required, but found: " + val);
}
}
public long increaseLong(String key, long increaseWith)
{
final long newValue = getLong(key) + increaseWith;
set(key, newValue);
return newValue;
}
public long increaseLong(String key, long defaultValue, long increaseWith)
{
final long newValue = getLong(key, defaultValue) + increaseWith;
set(key, newValue);
return newValue;
}
@Override
public float getFloat(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Float value required, but not specified");
}
if (val instanceof Number)
{
return ((Number) val).floatValue();
}
try
{
return Float.parseFloat((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Float value required, but found: " + val);
}
}
@Override
public float getFloat(String key, float defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
if (val instanceof Number)
{
return ((Number) val).floatValue();
}
try
{
return Float.parseFloat((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Float value required, but found: " + val);
}
}
public float increaseFloat(String key, float increaseWith)
{
final float newValue = getFloat(key) + increaseWith;
set(key, newValue);
return newValue;
}
public float increaseFloat(String key, float defaultValue, float increaseWith)
{
final float newValue = getFloat(key, defaultValue) + increaseWith;
set(key, newValue);
return newValue;
}
@Override
public double getDouble(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Double value required, but not specified");
}
if (val instanceof Number)
{
return ((Number) val).doubleValue();
}
try
{
return Double.parseDouble((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Double value required, but found: " + val);
}
}
@Override
public double getDouble(String key, double defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
if (val instanceof Number)
{
return ((Number) val).doubleValue();
}
try
{
return Double.parseDouble((String) val);
}
catch (Exception e)
{
throw new IllegalArgumentException("Double value required, but found: " + val);
}
}
public double increaseDouble(String key, double increaseWith)
{
final double newValue = getDouble(key) + increaseWith;
set(key, newValue);
return newValue;
}
public double increaseDouble(String key, double defaultValue, double increaseWith)
{
final double newValue = getDouble(key, defaultValue) + increaseWith;
set(key, newValue);
return newValue;
}
@Override
public String getString(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("String value required, but not specified");
}
return String.valueOf(val);
}
@Override
public String getString(String key, String defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
return String.valueOf(val);
}
@Override
public Duration getDuration(String key)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("String value required, but not specified");
}
return TimeUtil.parseDuration(String.valueOf(val));
}
@Override
public Duration getDuration(String key, Duration defaultValue)
{
Objects.requireNonNull(key);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
return TimeUtil.parseDuration(String.valueOf(val));
}
@Override
@SuppressWarnings("unchecked")
public <T extends Enum<T>> T getEnum(String key, Class<T> enumClass)
{
Objects.requireNonNull(key);
Objects.requireNonNull(enumClass);
final Object val = _set.get(key);
if (val == null)
{
throw new IllegalArgumentException("Enum value of type " + enumClass.getName() + " required, but not specified");
}
if (enumClass.isInstance(val))
{
return (T) val;
}
try
{
return Enum.valueOf(enumClass, String.valueOf(val));
}
catch (Exception e)
{
throw new IllegalArgumentException("Enum value of type " + enumClass.getName() + " required, but found: " + val);
}
}
@Override
@SuppressWarnings("unchecked")
public <T extends Enum<T>> T getEnum(String key, Class<T> enumClass, T defaultValue)
{
Objects.requireNonNull(key);
Objects.requireNonNull(enumClass);
final Object val = _set.get(key);
if (val == null)
{
return defaultValue;
}
if (enumClass.isInstance(val))
{
return (T) val;
}
try
{
return Enum.valueOf(enumClass, String.valueOf(val));
}
catch (Exception e)
{
throw new IllegalArgumentException("Enum value of type " + enumClass.getName() + " required, but found: " + val);
}
}
@SuppressWarnings("unchecked")
public final <A> A getObject(String name, Class<A> type)
{
Objects.requireNonNull(name);
Objects.requireNonNull(type);
final Object obj = _set.get(name);
if ((obj == null) || !type.isAssignableFrom(obj.getClass()))
{
return null;
}
return (A) obj;
}
public SkillHolder getSkillHolder(String key)
{
Objects.requireNonNull(key);
final Object obj = _set.get(key);
if ((obj == null) || !(obj instanceof SkillHolder))
{
return null;
}
return (SkillHolder) obj;
}
public Location getLocation(String key)
{
Objects.requireNonNull(key);
final Object obj = _set.get(key);
if ((obj == null) || !(obj instanceof Location))
{
return null;
}
return (Location) obj;
}
@SuppressWarnings("unchecked")
public List<MinionHolder> getMinionList(String key)
{
Objects.requireNonNull(key);
final Object obj = _set.get(key);
if ((obj == null) || !(obj instanceof List<?>))
{
return Collections.emptyList();
}
return (List<MinionHolder>) obj;
}
@SuppressWarnings("unchecked")
public <T> List<T> getList(String key, Class<T> clazz)
{
Objects.requireNonNull(key);
Objects.requireNonNull(clazz);
final Object obj = _set.get(key);
if ((obj == null) || !(obj instanceof List<?>))
{
return null;
}
final List<Object> originalList = (List<Object>) obj;
if (!originalList.isEmpty() && !originalList.stream().allMatch(clazz::isInstance))
{
if (clazz.getSuperclass() == Enum.class)
{
throw new IllegalAccessError("Please use getEnumList if you want to get list of Enums!");
}
// Attempt to convert the list
final List<T> convertedList = convertList(originalList, clazz);
if (convertedList == null)
{
LOGGER.log(Level.WARNING, "getList(\"" + key + "\", " + clazz.getSimpleName() + ") requested with wrong generic type: " + obj.getClass().getGenericInterfaces()[0] + "!", new ClassNotFoundException());
return null;
}
// Overwrite the existing list with proper generic type
_set.put(key, convertedList);
return convertedList;
}
return (List<T>) obj;
}
public <T> List<T> getList(String key, Class<T> clazz, List<T> defaultValue)
{
final List<T> list = getList(key, clazz);
return list == null ? defaultValue : list;
}
@SuppressWarnings("unchecked")
public <T extends Enum<T>> List<T> getEnumList(String key, Class<T> clazz)
{
final Object obj = _set.get(key);
if ((obj == null) || !(obj instanceof List<?>))
{
return null;
}
final List<Object> originalList = (List<Object>) obj;
if (!originalList.isEmpty() && (obj.getClass().getGenericInterfaces()[0] != clazz) && originalList.stream().allMatch(name -> Util.isEnum(name.toString(), clazz)))
{
final List<T> convertedList = originalList.stream().map(Object::toString).map(name -> Enum.valueOf(clazz, name)).map(clazz::cast).collect(Collectors.toList());
// Overwrite the existing list with proper generic type
_set.put(key, convertedList);
return convertedList;
}
return (List<T>) obj;
}
/**
* @param <T>
* @param originalList
* @param clazz
* @return
*/
private <T> List<T> convertList(List<Object> originalList, Class<T> clazz)
{
if (clazz == Integer.class)
{
if (originalList.stream().map(Object::toString).allMatch(Util::isInteger))
{
return originalList.stream().map(Object::toString).map(Integer::valueOf).map(clazz::cast).collect(Collectors.toList());
}
}
else if (clazz == Float.class)
{
if (originalList.stream().map(Object::toString).allMatch(Util::isFloat))
{
return originalList.stream().map(Object::toString).map(Float::valueOf).map(clazz::cast).collect(Collectors.toList());
}
}
else if (clazz == Double.class)
{
if (originalList.stream().map(Object::toString).allMatch(Util::isDouble))
{
return originalList.stream().map(Object::toString).map(Double::valueOf).map(clazz::cast).collect(Collectors.toList());
}
}
return null;
}
@SuppressWarnings("unchecked")
public <K, V> Map<K, V> getMap(String key, Class<K> keyClass, Class<V> valueClass)
{
final Object obj = _set.get(key);
if ((obj == null) || !(obj instanceof Map<?, ?>))
{
return null;
}
final Map<?, ?> originalList = (Map<?, ?>) obj;
if (!originalList.isEmpty())
{
if ((!originalList.keySet().stream().allMatch(keyClass::isInstance)) || (!originalList.values().stream().allMatch(valueClass::isInstance)))
{
LOGGER.log(Level.WARNING, "getMap(\"" + key + "\", " + keyClass.getSimpleName() + ", " + valueClass.getSimpleName() + ") requested with wrong generic type: " + obj.getClass().getGenericInterfaces()[0] + "!", new ClassNotFoundException());
}
}
return (Map<K, V>) obj;
}
public StatsSet set(String name, Object value)
{
if (value == null)
{
return this;
}
_set.put(name, value);
return this;
}
public StatsSet set(String key, boolean value)
{
_set.put(key, value);
return this;
}
public StatsSet set(String key, byte value)
{
_set.put(key, value);
return this;
}
public StatsSet set(String key, short value)
{
_set.put(key, value);
return this;
}
public StatsSet set(String key, int value)
{
_set.put(key, value);
return this;
}
public StatsSet set(String key, long value)
{
_set.put(key, value);
return this;
}
public StatsSet set(String key, float value)
{
_set.put(key, value);
return this;
}
public StatsSet set(String key, double value)
{
_set.put(key, value);
return this;
}
public StatsSet set(String key, String value)
{
if (value == null)
{
return this;
}
_set.put(key, value);
return this;
}
public StatsSet set(String key, Enum<?> value)
{
if (value == null)
{
return this;
}
_set.put(key, value);
return this;
}
public static StatsSet valueOf(String key, Object value)
{
final StatsSet set = new StatsSet();
set.set(key, value);
return set;
}
public void remove(String key)
{
_set.remove(key);
}
public boolean contains(String name)
{
return _set.containsKey(name);
}
@Override
public String toString()
{
return "StatsSet{_set=" + _set + '}';
}
}

View File

@@ -0,0 +1,71 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* @author UnAfraid
*/
public class TeleportBookmark extends Location
{
private final int _id;
private int _icon;
private String _name, _tag;
public TeleportBookmark(int id, int x, int y, int z, int icon, String tag, String name)
{
super(x, y, z);
_id = id;
_icon = icon;
_name = name;
_tag = tag;
}
public String getName()
{
return _name;
}
public void setName(String name)
{
_name = name;
}
public int getId()
{
return _id;
}
public int getIcon()
{
return _icon;
}
public void setIcon(int icon)
{
_icon = icon;
}
public String getTag()
{
return _tag;
}
public void setTag(String tag)
{
_tag = tag;
}
}

View File

@@ -0,0 +1,30 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
/**
* All teleport types.
* @author xban1x
*/
public enum TeleportWhereType
{
CASTLE,
CLANHALL,
SIEGEFLAG,
TOWN,
FORTRESS
}

View File

@@ -0,0 +1,83 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
/**
* Class explanation:<br>
* For item counting or checking purposes. When you don't want to modify inventory<br>
* class contains itemId, quantity, ownerId, referencePrice, but not objectId<br>
* is stored, this will be only "list" of items with it's owner
*/
public final class TempItem
{
private final int _itemId;
private int _quantity;
private final int _referencePrice;
private final String _itemName;
/**
* @param item
* @param quantity of that item
*/
public TempItem(L2ItemInstance item, int quantity)
{
super();
_itemId = item.getId();
_quantity = quantity;
_itemName = item.getItem().getName();
_referencePrice = item.getReferencePrice();
}
/**
* @return the quantity.
*/
public int getQuantity()
{
return _quantity;
}
/**
* @param quantity The quantity to set.
*/
public void setQuantity(int quantity)
{
_quantity = quantity;
}
public int getReferencePrice()
{
return _referencePrice;
}
/**
* @return the itemId.
*/
public int getItemId()
{
return _itemId;
}
/**
* @return the itemName.
*/
public String getItemName()
{
return _itemName;
}
}

View File

@@ -0,0 +1,165 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
import com.l2jmobius.gameserver.model.skills.Skill;
/**
* Simple class containing all necessary information to maintain<br>
* valid time stamps and reuse for skills and items reuse upon re-login.<br>
* <b>Filter this carefully as it becomes redundant to store reuse for small delays.</b>
* @author Yesod, Zoey76
*/
public class TimeStamp
{
/** Item or skill ID. */
private final int _id1;
/** Item object ID or skill level. */
private final int _id2;
/** Skill level. */
private final int _id3;
/** Item or skill reuse time. */
private final long _reuse;
/** Time stamp. */
private final long _stamp;
/** Shared reuse group. */
private final int _group;
/**
* Skill time stamp constructor.
* @param skill the skill upon the stamp will be created.
* @param reuse the reuse time for this skill.
* @param systime overrides the system time with a customized one.
*/
public TimeStamp(Skill skill, long reuse, long systime)
{
_id1 = skill.getId();
_id2 = skill.getLevel();
_id3 = skill.getSubLevel();
_reuse = reuse;
_stamp = systime > 0 ? systime : System.currentTimeMillis() + reuse;
_group = -1;
}
/**
* Item time stamp constructor.
* @param item the item upon the stamp will be created.
* @param reuse the reuse time for this item.
* @param systime overrides the system time with a customized one.
*/
public TimeStamp(L2ItemInstance item, long reuse, long systime)
{
_id1 = item.getId();
_id2 = item.getObjectId();
_id3 = 0;
_reuse = reuse;
_stamp = systime > 0 ? systime : System.currentTimeMillis() + reuse;
_group = item.getSharedReuseGroup();
}
/**
* Gets the time stamp.
* @return the time stamp, either the system time where this time stamp was created or the custom time assigned
*/
public long getStamp()
{
return _stamp;
}
/**
* Gets the item ID.
* @return the item ID
*/
public int getItemId()
{
return _id1;
}
/**
* Gets the item object ID.
* @return the item object ID
*/
public int getItemObjectId()
{
return _id2;
}
/**
* Gets the skill ID.
* @return the skill ID
*/
public int getSkillId()
{
return _id1;
}
/**
* Gets the skill level.
* @return the skill level
*/
public int getSkillLvl()
{
return _id2;
}
/**
* Gets the skill sub level.
* @return the skill level
*/
public int getSkillSubLvl()
{
return _id3;
}
/**
* Gets the reuse.
* @return the reuse
*/
public long getReuse()
{
return _reuse;
}
/**
* Get the shared reuse group.<br>
* Only used on items.
* @return the shared reuse group
*/
public int getSharedReuseGroup()
{
return _group;
}
/**
* Gets the remaining time.
* @return the remaining time for this time stamp to expire
*/
public long getRemaining()
{
return Math.max(_stamp - System.currentTimeMillis(), 0);
}
/**
* Verifies if the reuse delay has passed.
* @return {@code true} if this time stamp has expired, {@code false} otherwise
*/
public boolean hasNotPassed()
{
return System.currentTimeMillis() < _stamp;
}
}

View File

@@ -0,0 +1,75 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.List;
import com.l2jmobius.gameserver.model.interfaces.IIdentifiable;
/**
* @author malyelfik
*/
public class TowerSpawn implements IIdentifiable
{
private final int _npcId;
private final Location _location;
private List<Integer> _zoneList = null;
private int _upgradeLevel = 0;
public TowerSpawn(int npcId, Location location)
{
_location = location;
_npcId = npcId;
}
public TowerSpawn(int npcId, Location location, List<Integer> zoneList)
{
_location = location;
_npcId = npcId;
_zoneList = zoneList;
}
/**
* Gets the NPC ID.
* @return the NPC ID
*/
@Override
public int getId()
{
return _npcId;
}
public Location getLocation()
{
return _location;
}
public List<Integer> getZoneList()
{
return _zoneList;
}
public void setUpgradeLevel(int level)
{
_upgradeLevel = level;
}
public int getUpgradeLevel()
{
return _upgradeLevel;
}
}

View File

@@ -0,0 +1,227 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.Collection;
import java.util.Collections;
import java.util.Objects;
import com.l2jmobius.gameserver.enums.AttributeType;
import com.l2jmobius.gameserver.model.ensoul.EnsoulOption;
import com.l2jmobius.gameserver.model.items.L2Item;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
public class TradeItem
{
private int _objectId;
private final L2Item _item;
private final int _location;
private int _enchant;
private final int _type1;
private final int _type2;
private long _count;
private long _storeCount;
private long _price;
private final byte _elemAtkType;
private final int _elemAtkPower;
private final int[] _elemDefAttr =
{
0,
0,
0,
0,
0,
0
};
private final int[] _enchantOptions;
private final Collection<EnsoulOption> _soulCrystalOptions;
private final Collection<EnsoulOption> _soulCrystalSpecialOptions;
private int _visualId;
private int _augmentId;
public TradeItem(L2ItemInstance item, long count, long price)
{
Objects.requireNonNull(item);
_objectId = item.getObjectId();
_item = item.getItem();
_location = item.getLocationSlot();
_enchant = item.getEnchantLevel();
_type1 = item.getCustomType1();
_type2 = item.getCustomType2();
_count = count;
_price = price;
_elemAtkType = item.getAttackAttributeType().getClientId();
_elemAtkPower = item.getAttackAttributePower();
for (AttributeType type : AttributeType.ATTRIBUTE_TYPES)
{
_elemDefAttr[type.getClientId()] = item.getDefenceAttribute(type);
}
_enchantOptions = item.getEnchantOptions();
_soulCrystalOptions = item.getSpecialAbilities();
_soulCrystalSpecialOptions = item.getAdditionalSpecialAbilities();
_visualId = item.getVisualId();
_augmentId = item.isAugmented() ? item.getAugmentation().getId() : 0;
}
public TradeItem(L2Item item, long count, long price)
{
Objects.requireNonNull(item);
_objectId = 0;
_item = item;
_location = 0;
_enchant = 0;
_type1 = 0;
_type2 = 0;
_count = count;
_storeCount = count;
_price = price;
_elemAtkType = Elementals.NONE;
_elemAtkPower = 0;
_enchantOptions = L2ItemInstance.DEFAULT_ENCHANT_OPTIONS;
_soulCrystalOptions = Collections.emptyList();
_soulCrystalSpecialOptions = Collections.emptyList();
}
public TradeItem(TradeItem item, long count, long price)
{
Objects.requireNonNull(item);
_objectId = item.getObjectId();
_item = item.getItem();
_location = item.getLocationSlot();
_enchant = item.getEnchant();
_type1 = item.getCustomType1();
_type2 = item.getCustomType2();
_count = count;
_storeCount = count;
_price = price;
_elemAtkType = item.getAttackElementType();
_elemAtkPower = item.getAttackElementPower();
for (byte i = 0; i < 6; i++)
{
_elemDefAttr[i] = item.getElementDefAttr(i);
}
_enchantOptions = item.getEnchantOptions();
_soulCrystalOptions = item.getSoulCrystalOptions();
_soulCrystalSpecialOptions = item.getSoulCrystalSpecialOptions();
_visualId = item.getVisualId();
}
public void setObjectId(int objectId)
{
_objectId = objectId;
}
public int getObjectId()
{
return _objectId;
}
public L2Item getItem()
{
return _item;
}
public int getLocationSlot()
{
return _location;
}
public void setEnchant(int enchant)
{
_enchant = enchant;
}
public int getEnchant()
{
return _enchant;
}
public int getCustomType1()
{
return _type1;
}
public int getCustomType2()
{
return _type2;
}
public void setCount(long count)
{
_count = count;
}
public long getCount()
{
return _count;
}
public long getStoreCount()
{
return _storeCount;
}
public void setPrice(long price)
{
_price = price;
}
public long getPrice()
{
return _price;
}
public byte getAttackElementType()
{
return _elemAtkType;
}
public int getAttackElementPower()
{
return _elemAtkPower;
}
public int getElementDefAttr(byte i)
{
return _elemDefAttr[i];
}
public int[] getEnchantOptions()
{
return _enchantOptions;
}
public Collection<EnsoulOption> getSoulCrystalOptions()
{
return _soulCrystalOptions;
}
public Collection<EnsoulOption> getSoulCrystalSpecialOptions()
{
return _soulCrystalSpecialOptions;
}
public int getAugmentId()
{
return _augmentId;
}
public int getVisualId()
{
return _visualId;
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,213 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.logging.Level;
import java.util.logging.Logger;
import com.l2jmobius.commons.database.DatabaseFactory;
import com.l2jmobius.gameserver.data.xml.impl.UIData;
/**
* UI Keys Settings class.
* @author mrTJO, Zoey76
*/
public class UIKeysSettings
{
private static final Logger _log = Logger.getLogger(UIKeysSettings.class.getName());
private final int _playerObjId;
private Map<Integer, List<ActionKey>> _storedKeys;
private Map<Integer, List<Integer>> _storedCategories;
private boolean _saved = true;
public UIKeysSettings(int playerObjId)
{
_playerObjId = playerObjId;
loadFromDB();
}
public void storeAll(Map<Integer, List<Integer>> catMap, Map<Integer, List<ActionKey>> keyMap)
{
_saved = false;
_storedCategories = catMap;
_storedKeys = keyMap;
}
public void storeCategories(Map<Integer, List<Integer>> catMap)
{
_saved = false;
_storedCategories = catMap;
}
public Map<Integer, List<Integer>> getCategories()
{
return _storedCategories;
}
public void storeKeys(Map<Integer, List<ActionKey>> keyMap)
{
_saved = false;
_storedKeys = keyMap;
}
public Map<Integer, List<ActionKey>> getKeys()
{
return _storedKeys;
}
public void loadFromDB()
{
getCatsFromDB();
getKeysFromDB();
}
/**
* Save Categories and Mapped Keys into GameServer DataBase
*/
public void saveInDB()
{
String query;
if (_saved)
{
return;
}
query = "REPLACE INTO character_ui_categories (`charId`, `catId`, `order`, `cmdId`) VALUES ";
for (int category : _storedCategories.keySet())
{
int order = 0;
for (int key : _storedCategories.get(category))
{
query += "(" + _playerObjId + ", " + category + ", " + (order++) + ", " + key + "),";
}
}
query = query.substring(0, query.length() - 1) + "; ";
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement(query))
{
statement.execute();
}
catch (Exception e)
{
_log.log(Level.WARNING, "Exception: saveInDB(): " + e.getMessage(), e);
}
query = "REPLACE INTO character_ui_actions (`charId`, `cat`, `order`, `cmd`, `key`, `tgKey1`, `tgKey2`, `show`) VALUES";
for (List<ActionKey> keyLst : _storedKeys.values())
{
int order = 0;
for (ActionKey key : keyLst)
{
query += key.getSqlSaveString(_playerObjId, order++) + ",";
}
}
query = query.substring(0, query.length() - 1) + ";";
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement statement = con.prepareStatement(query))
{
statement.execute();
}
catch (Exception e)
{
_log.log(Level.WARNING, "Exception: saveInDB(): " + e.getMessage(), e);
}
_saved = true;
}
public void getCatsFromDB()
{
if (_storedCategories != null)
{
return;
}
_storedCategories = new HashMap<>();
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement stmt = con.prepareStatement("SELECT * FROM character_ui_categories WHERE `charId` = ? ORDER BY `catId`, `order`"))
{
stmt.setInt(1, _playerObjId);
try (ResultSet rs = stmt.executeQuery())
{
while (rs.next())
{
UIData.addCategory(_storedCategories, rs.getInt("catId"), rs.getInt("cmdId"));
}
}
}
catch (Exception e)
{
_log.log(Level.WARNING, "Exception: getCatsFromDB(): " + e.getMessage(), e);
}
if (_storedCategories.isEmpty())
{
_storedCategories = UIData.getInstance().getCategories();
}
}
public void getKeysFromDB()
{
if (_storedKeys != null)
{
return;
}
_storedKeys = new HashMap<>();
try (Connection con = DatabaseFactory.getInstance().getConnection();
PreparedStatement stmt = con.prepareStatement("SELECT * FROM character_ui_actions WHERE `charId` = ? ORDER BY `cat`, `order`"))
{
stmt.setInt(1, _playerObjId);
try (ResultSet rs = stmt.executeQuery())
{
while (rs.next())
{
final int cat = rs.getInt("cat");
final int cmd = rs.getInt("cmd");
final int key = rs.getInt("key");
final int tgKey1 = rs.getInt("tgKey1");
final int tgKey2 = rs.getInt("tgKey2");
final int show = rs.getInt("show");
UIData.addKey(_storedKeys, cat, new ActionKey(cat, cmd, key, tgKey1, tgKey2, show));
}
}
}
catch (Exception e)
{
_log.log(Level.WARNING, "Exception: getKeysFromDB(): " + e.getMessage(), e);
}
if (_storedKeys.isEmpty())
{
_storedKeys = UIData.getInstance().getKeys();
}
}
public boolean isSaved()
{
return _saved;
}
}

View File

@@ -0,0 +1,52 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
public final class VehiclePathPoint extends Location
{
private final int _moveSpeed;
private final int _rotationSpeed;
public VehiclePathPoint(Location loc)
{
this(loc.getX(), loc.getY(), loc.getZ());
}
public VehiclePathPoint(int x, int y, int z)
{
super(x, y, z);
_moveSpeed = 350;
_rotationSpeed = 4000;
}
public VehiclePathPoint(int x, int y, int z, int moveSpeed, int rotationSpeed)
{
super(x, y, z);
_moveSpeed = moveSpeed;
_rotationSpeed = rotationSpeed;
}
public int getMoveSpeed()
{
return _moveSpeed;
}
public int getRotationSpeed()
{
return _rotationSpeed;
}
}

View File

@@ -0,0 +1,227 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model;
import java.util.concurrent.ScheduledFuture;
import com.l2jmobius.commons.util.Rnd;
import com.l2jmobius.gameserver.instancemanager.WalkingManager;
import com.l2jmobius.gameserver.model.actor.L2Npc;
import com.l2jmobius.gameserver.model.events.EventDispatcher;
import com.l2jmobius.gameserver.model.events.impl.character.npc.OnNpcMoveRouteFinished;
/**
* Holds info about current walk progress.
* @author GKR, UnAfraid
*/
public class WalkInfo
{
private final String _routeName;
private ScheduledFuture<?> _walkCheckTask;
private boolean _blocked = false;
private boolean _suspended = false;
private boolean _stoppedByAttack = false;
private int _currentNode = 0;
private boolean _forward = true; // Determines first --> last or first <-- last direction
private long _lastActionTime; // Debug field
public WalkInfo(String routeName)
{
_routeName = routeName;
}
/**
* @return name of route of this WalkInfo.
*/
public L2WalkRoute getRoute()
{
return WalkingManager.getInstance().getRoute(_routeName);
}
/**
* @return current node of this WalkInfo.
*/
public L2NpcWalkerNode getCurrentNode()
{
return getRoute().getNodeList().get(_currentNode);
}
/**
* Calculate next node for this WalkInfo and send debug message from given npc
* @param npc NPC to debug message to be sent from
*/
public synchronized void calculateNextNode(L2Npc npc)
{
// Check this first, within the bounds of random moving, we have no conception of "first" or "last" node
if (getRoute().getRepeatType() == WalkingManager.REPEAT_RANDOM)
{
int newNode = _currentNode;
while (newNode == _currentNode)
{
newNode = Rnd.get(getRoute().getNodesCount());
}
_currentNode = newNode;
npc.sendDebugMessage("Route: " + getRoute().getName() + ", next random node is " + _currentNode);
}
else
{
if (_forward)
{
_currentNode++;
}
else
{
_currentNode--;
}
if (_currentNode == getRoute().getNodesCount()) // Last node arrived
{
// Notify quest
EventDispatcher.getInstance().notifyEventAsync(new OnNpcMoveRouteFinished(npc), npc);
npc.sendDebugMessage("Route: " + getRoute().getName() + ", last node arrived");
if (!getRoute().repeatWalk())
{
WalkingManager.getInstance().cancelMoving(npc);
return;
}
switch (getRoute().getRepeatType())
{
case WalkingManager.REPEAT_GO_BACK:
{
_forward = false;
_currentNode -= 2;
break;
}
case WalkingManager.REPEAT_GO_FIRST:
{
_currentNode = 0;
break;
}
case WalkingManager.REPEAT_TELE_FIRST:
{
npc.teleToLocation(npc.getSpawn().getLocation());
_currentNode = 0;
break;
}
}
}
else if (_currentNode == WalkingManager.NO_REPEAT) // First node arrived, when direction is first <-- last
{
_currentNode = 1;
_forward = true;
}
}
}
/**
* @return {@code true} if walking task is blocked, {@code false} otherwise,
*/
public boolean isBlocked()
{
return _blocked;
}
/**
* @param val
*/
public void setBlocked(boolean val)
{
_blocked = val;
}
/**
* @return {@code true} if walking task is suspended, {@code false} otherwise,
*/
public boolean isSuspended()
{
return _suspended;
}
/**
* @param val
*/
public void setSuspended(boolean val)
{
_suspended = val;
}
/**
* @return {@code true} if walking task shall be stopped by attack, {@code false} otherwise,
*/
public boolean isStoppedByAttack()
{
return _stoppedByAttack;
}
/**
* @param val
*/
public void setStoppedByAttack(boolean val)
{
_stoppedByAttack = val;
}
/**
* @return the id of the current node in this walking task.
*/
public int getCurrentNodeId()
{
return _currentNode;
}
/**
* @return {@code long} last action time used only for debugging.
*/
public long getLastAction()
{
return _lastActionTime;
}
/**
* @param val
*/
public void setLastAction(long val)
{
_lastActionTime = val;
}
/**
* @return walking check task.
*/
public ScheduledFuture<?> getWalkCheckTask()
{
return _walkCheckTask;
}
/**
* @param val walking check task.
*/
public void setWalkCheckTask(ScheduledFuture<?> val)
{
_walkCheckTask = val;
}
@Override
public String toString()
{
return "WalkInfo [_routeName=" + _routeName + ", _walkCheckTask=" + _walkCheckTask + ", _blocked=" + _blocked + ", _suspended=" + _suspended + ", _stoppedByAttack=" + _stoppedByAttack + ", _currentNode=" + _currentNode + ", _forward=" + _forward + ", _lastActionTime=" + _lastActionTime + "]";
}
}

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,323 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model.actor;
import com.l2jmobius.gameserver.ai.CtrlEvent;
import com.l2jmobius.gameserver.enums.InstanceType;
import com.l2jmobius.gameserver.instancemanager.ZoneManager;
import com.l2jmobius.gameserver.model.L2Clan;
import com.l2jmobius.gameserver.model.L2Object;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.actor.stat.PlayableStat;
import com.l2jmobius.gameserver.model.actor.status.PlayableStatus;
import com.l2jmobius.gameserver.model.actor.templates.L2CharTemplate;
import com.l2jmobius.gameserver.model.effects.EffectFlag;
import com.l2jmobius.gameserver.model.events.EventDispatcher;
import com.l2jmobius.gameserver.model.events.impl.character.OnCreatureDeath;
import com.l2jmobius.gameserver.model.events.returns.TerminateReturn;
import com.l2jmobius.gameserver.model.instancezone.Instance;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
import com.l2jmobius.gameserver.model.quest.QuestState;
import com.l2jmobius.gameserver.model.skills.Skill;
import com.l2jmobius.gameserver.network.serverpackets.EtcStatusUpdate;
/**
* This class represents all Playable characters in the world.<br>
* L2Playable:
* <ul>
* <li>L2PcInstance</li>
* <li>L2Summon</li>
* </ul>
*/
public abstract class L2Playable extends L2Character
{
private L2Character _lockedTarget = null;
private L2PcInstance transferDmgTo = null;
/**
* Constructor of L2Playable.<br>
* <B><U> Actions</U> :</B>
* <ul>
* <li>Call the L2Character constructor to create an empty _skills slot and link copy basic Calculator set to this L2Playable</li>
* </ul>
* @param objectId the object id
* @param template The L2CharTemplate to apply to the L2Playable
*/
public L2Playable(int objectId, L2CharTemplate template)
{
super(objectId, template);
setInstanceType(InstanceType.L2Playable);
setIsInvul(false);
}
public L2Playable(L2CharTemplate template)
{
super(template);
setInstanceType(InstanceType.L2Playable);
setIsInvul(false);
}
@Override
public PlayableStat getStat()
{
return (PlayableStat) super.getStat();
}
@Override
public void initCharStat()
{
setStat(new PlayableStat(this));
}
@Override
public PlayableStatus getStatus()
{
return (PlayableStatus) super.getStatus();
}
@Override
public void initCharStatus()
{
setStatus(new PlayableStatus(this));
}
@Override
public boolean doDie(L2Character killer)
{
final TerminateReturn returnBack = EventDispatcher.getInstance().notifyEvent(new OnCreatureDeath(killer, this), this, TerminateReturn.class);
if ((returnBack != null) && returnBack.terminate())
{
return false;
}
// killing is only possible one time
synchronized (this)
{
if (isDead())
{
return false;
}
// now reset currentHp to zero
setCurrentHp(0);
setIsDead(true);
}
abortAttack();
abortCast();
// Set target to null and cancel Attack or Cast
setTarget(null);
// Stop movement
stopMove(null);
// Stop HP/MP/CP Regeneration task
getStatus().stopHpMpRegeneration();
boolean deleteBuffs = true;
if (isNoblesseBlessedAffected())
{
stopEffects(EffectFlag.NOBLESS_BLESSING);
deleteBuffs = false;
}
if (isResurrectSpecialAffected())
{
stopEffects(EffectFlag.RESURRECTION_SPECIAL);
deleteBuffs = false;
}
if (isPlayer())
{
final L2PcInstance activeChar = getActingPlayer();
if (activeChar.hasCharmOfCourage())
{
if (activeChar.isInSiege())
{
getActingPlayer().reviveRequest(getActingPlayer(), null, false, 0);
}
activeChar.setCharmOfCourage(false);
activeChar.sendPacket(new EtcStatusUpdate(activeChar));
}
}
if (deleteBuffs)
{
stopAllEffectsExceptThoseThatLastThroughDeath();
}
// Send the Server->Client packet StatusUpdate with current HP and MP to all other L2PcInstance to inform
broadcastStatusUpdate();
ZoneManager.getInstance().getRegion(this).onDeath(this);
// Notify Quest of L2Playable's death
final L2PcInstance actingPlayer = getActingPlayer();
if (!actingPlayer.isNotifyQuestOfDeathEmpty())
{
for (QuestState qs : actingPlayer.getNotifyQuestOfDeath())
{
qs.getQuest().notifyDeath((killer == null ? this : killer), this, qs);
}
}
// Notify instance
if (isPlayer())
{
final Instance instance = getInstanceWorld();
if (instance != null)
{
instance.onDeath(getActingPlayer());
}
}
if (killer != null)
{
final L2PcInstance killerPlayer = killer.getActingPlayer();
if ((killerPlayer != null) && isPlayable())
{
killerPlayer.onPlayerKill(this);
}
}
// Notify L2Character AI
getAI().notifyEvent(CtrlEvent.EVT_DEAD);
super.updateEffectIcons();
return true;
}
public boolean checkIfPvP(L2PcInstance target)
{
final L2PcInstance player = getActingPlayer();
if ((player == null) || (target == null) || (player == target))
{
return true;
}
if (target.isOnDarkSide())
{
return true;
}
else if (target.getReputation() < 0)
{
return true;
}
else if ((player.getPvpFlag() > 0) && (target.getPvpFlag() > 0))
{
return true;
}
final L2Clan playerClan = player.getClan();
final L2Clan targetClan = target.getClan();
if ((playerClan != null) && (targetClan != null) && playerClan.isAtWarWith(targetClan) && targetClan.isAtWarWith(playerClan))
{
return (player.getPledgeType() != L2Clan.SUBUNIT_ACADEMY) && (target.getPledgeType() != L2Clan.SUBUNIT_ACADEMY);
}
return false;
}
/**
* Return True.
*/
@Override
public boolean canBeAttacked()
{
return true;
}
// Support for Noblesse Blessing skill, where buffs are retained after resurrect
public final boolean isNoblesseBlessedAffected()
{
return isAffected(EffectFlag.NOBLESS_BLESSING);
}
/**
* @return {@code true} if char can resurrect by himself, {@code false} otherwise
*/
public final boolean isResurrectSpecialAffected()
{
return isAffected(EffectFlag.RESURRECTION_SPECIAL);
}
/**
* @return {@code true} if the Silent Moving mode is active, {@code false} otherwise
*/
public boolean isSilentMovingAffected()
{
return isAffected(EffectFlag.SILENT_MOVE);
}
/**
* For Newbie Protection Blessing skill, keeps you safe from an attack by a chaotic character >= 10 levels apart from you.
* @return
*/
public final boolean isProtectionBlessingAffected()
{
return isAffected(EffectFlag.PROTECTION_BLESSING);
}
@Override
public void updateEffectIcons(boolean partyOnly)
{
getEffectList().updateEffectIcons(partyOnly);
}
public boolean isLockedTarget()
{
return _lockedTarget != null;
}
public L2Character getLockedTarget()
{
return _lockedTarget;
}
public void setLockedTarget(L2Character cha)
{
_lockedTarget = cha;
}
public void setTransferDamageTo(L2PcInstance val)
{
transferDmgTo = val;
}
public L2PcInstance getTransferingDamageTo()
{
return transferDmgTo;
}
public abstract void doPickupItem(L2Object object);
public abstract int getReputation();
public abstract boolean useMagic(Skill skill, L2ItemInstance item, boolean forceUse, boolean dontMove);
public abstract void storeMe();
public abstract void storeEffect(boolean storeEffects);
public abstract void restoreEffects();
@Override
public boolean isPlayable()
{
return true;
}
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,81 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model.actor;
import com.l2jmobius.gameserver.GeoData;
import com.l2jmobius.gameserver.ai.CtrlIntention;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.actor.templates.L2NpcTemplate;
import com.l2jmobius.gameserver.network.serverpackets.ActionFailed;
/**
* This class is a super-class for L2ControlTowerInstance and L2FlameTowerInstance.
* @author Zoey76
*/
public abstract class L2Tower extends L2Npc
{
public L2Tower(L2NpcTemplate template)
{
super(template);
setIsInvul(false);
}
@Override
public boolean canBeAttacked()
{
// Attackable during siege by attacker only
return ((getCastle() != null) && (getCastle().getResidenceId() > 0) && getCastle().getSiege().isInProgress());
}
@Override
public boolean isAutoAttackable(L2Character attacker)
{
// Attackable during siege by attacker only
return ((attacker != null) && attacker.isPlayer() && (getCastle() != null) && (getCastle().getResidenceId() > 0) && getCastle().getSiege().isInProgress() && getCastle().getSiege().checkIsAttacker(attacker.getClan()));
}
@Override
public void onAction(L2PcInstance player, boolean interact)
{
if (!canTarget(player))
{
return;
}
if (this != player.getTarget())
{
// Set the target of the L2PcInstance player
player.setTarget(this);
}
else if (interact)
{
if (isAutoAttackable(player) && (Math.abs(player.getZ() - getZ()) < 100) && GeoData.getInstance().canSeeTarget(player, this))
{
// Notify the L2PcInstance AI with AI_INTENTION_INTERACT
player.getAI().setIntention(CtrlIntention.AI_INTENTION_ATTACK, this);
}
}
// Send a Server->Client ActionFailed to the L2PcInstance in order to avoid that the client wait another packet
player.sendPacket(ActionFailed.STATIC_PACKET);
}
@Override
public void onForcedAttack(L2PcInstance player)
{
onAction(player);
}
}

View File

@@ -0,0 +1,482 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model.actor;
import java.util.Iterator;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.logging.Level;
import com.l2jmobius.gameserver.GameTimeController;
import com.l2jmobius.gameserver.ThreadPoolManager;
import com.l2jmobius.gameserver.ai.CtrlIntention;
import com.l2jmobius.gameserver.enums.InstanceType;
import com.l2jmobius.gameserver.instancemanager.MapRegionManager;
import com.l2jmobius.gameserver.instancemanager.ZoneManager;
import com.l2jmobius.gameserver.model.L2World;
import com.l2jmobius.gameserver.model.Location;
import com.l2jmobius.gameserver.model.TeleportWhereType;
import com.l2jmobius.gameserver.model.VehiclePathPoint;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
import com.l2jmobius.gameserver.model.actor.stat.VehicleStat;
import com.l2jmobius.gameserver.model.actor.templates.L2CharTemplate;
import com.l2jmobius.gameserver.model.interfaces.ILocational;
import com.l2jmobius.gameserver.model.items.L2Weapon;
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
import com.l2jmobius.gameserver.model.zone.ZoneRegion;
import com.l2jmobius.gameserver.network.SystemMessageId;
import com.l2jmobius.gameserver.network.serverpackets.IClientOutgoingPacket;
import com.l2jmobius.gameserver.network.serverpackets.InventoryUpdate;
import com.l2jmobius.gameserver.util.Util;
/**
* @author DS
*/
public abstract class L2Vehicle extends L2Character
{
protected int _dockId = 0;
protected final Set<L2PcInstance> _passengers = ConcurrentHashMap.newKeySet();
protected Location _oustLoc = null;
private Runnable _engine = null;
protected VehiclePathPoint[] _currentPath = null;
protected int _runState = 0;
public L2Vehicle(L2CharTemplate template)
{
super(template);
setInstanceType(InstanceType.L2Vehicle);
setIsFlying(true);
}
public boolean isBoat()
{
return false;
}
public boolean isAirShip()
{
return false;
}
public boolean canBeControlled()
{
return _engine == null;
}
public void registerEngine(Runnable r)
{
_engine = r;
}
public void runEngine(int delay)
{
if (_engine != null)
{
ThreadPoolManager.getInstance().scheduleGeneral(_engine, delay);
}
}
public void executePath(VehiclePathPoint[] path)
{
_runState = 0;
_currentPath = path;
if ((_currentPath != null) && (_currentPath.length > 0))
{
final VehiclePathPoint point = _currentPath[0];
if (point.getMoveSpeed() > 0)
{
getStat().setMoveSpeed(point.getMoveSpeed());
}
if (point.getRotationSpeed() > 0)
{
getStat().setRotationSpeed(point.getRotationSpeed());
}
getAI().setIntention(CtrlIntention.AI_INTENTION_MOVE_TO, new Location(point.getX(), point.getY(), point.getZ(), 0));
return;
}
getAI().setIntention(CtrlIntention.AI_INTENTION_ACTIVE);
}
@Override
public boolean moveToNextRoutePoint()
{
_move = null;
if (_currentPath != null)
{
_runState++;
if (_runState < _currentPath.length)
{
final VehiclePathPoint point = _currentPath[_runState];
if (!isMovementDisabled())
{
if (point.getMoveSpeed() == 0)
{
point.setHeading(point.getRotationSpeed());
teleToLocation(point, false);
_currentPath = null;
}
else
{
if (point.getMoveSpeed() > 0)
{
getStat().setMoveSpeed(point.getMoveSpeed());
}
if (point.getRotationSpeed() > 0)
{
getStat().setRotationSpeed(point.getRotationSpeed());
}
final MoveData m = new MoveData();
m.disregardingGeodata = false;
m.onGeodataPathIndex = -1;
m._xDestination = point.getX();
m._yDestination = point.getY();
m._zDestination = point.getZ();
m._heading = 0;
final double dx = point.getX() - getX();
final double dy = point.getY() - getY();
final double distance = Math.sqrt((dx * dx) + (dy * dy));
if (distance > 1)
{
setHeading(Util.calculateHeadingFrom(getX(), getY(), point.getX(), point.getY()));
}
m._moveStartTime = GameTimeController.getInstance().getGameTicks();
_move = m;
GameTimeController.getInstance().registerMovingObject(this);
return true;
}
}
}
else
{
_currentPath = null;
}
}
runEngine(10);
return false;
}
@Override
public VehicleStat getStat()
{
return (VehicleStat) super.getStat();
}
@Override
public void initCharStat()
{
setStat(new VehicleStat(this));
}
public boolean isInDock()
{
return _dockId > 0;
}
public int getDockId()
{
return _dockId;
}
public void setInDock(int d)
{
_dockId = d;
}
public void setOustLoc(Location loc)
{
_oustLoc = loc;
}
public Location getOustLoc()
{
return _oustLoc != null ? _oustLoc : MapRegionManager.getInstance().getTeleToLocation(this, TeleportWhereType.TOWN);
}
public void oustPlayers()
{
L2PcInstance player;
// Use iterator because oustPlayer will try to remove player from _passengers
final Iterator<L2PcInstance> iter = _passengers.iterator();
while (iter.hasNext())
{
player = iter.next();
iter.remove();
if (player != null)
{
oustPlayer(player);
}
}
}
public void oustPlayer(L2PcInstance player)
{
player.setVehicle(null);
player.setInVehiclePosition(null);
removePassenger(player);
}
public boolean addPassenger(L2PcInstance player)
{
if ((player == null) || _passengers.contains(player))
{
return false;
}
// already in other vehicle
if ((player.getVehicle() != null) && (player.getVehicle() != this))
{
return false;
}
_passengers.add(player);
return true;
}
public void removePassenger(L2PcInstance player)
{
try
{
_passengers.remove(player);
}
catch (Exception e)
{
}
}
public boolean isEmpty()
{
return _passengers.isEmpty();
}
public Set<L2PcInstance> getPassengers()
{
return _passengers;
}
public void broadcastToPassengers(IClientOutgoingPacket sm)
{
for (L2PcInstance player : _passengers)
{
if (player != null)
{
player.sendPacket(sm);
}
}
}
/**
* Consume ticket(s) and teleport player from boat if no correct ticket
* @param itemId Ticket itemId
* @param count Ticket count
* @param oustX
* @param oustY
* @param oustZ
*/
public void payForRide(int itemId, int count, int oustX, int oustY, int oustZ)
{
L2World.getInstance().forEachVisibleObjectInRange(this, L2PcInstance.class, 1000, player ->
{
if (player.isInBoat() && (player.getBoat() == this))
{
if (itemId > 0)
{
final L2ItemInstance ticket = player.getInventory().getItemByItemId(itemId);
if ((ticket == null) || (player.getInventory().destroyItem("Boat", ticket, count, player, this) == null))
{
player.sendPacket(SystemMessageId.YOU_DO_NOT_POSSESS_THE_CORRECT_TICKET_TO_BOARD_THE_BOAT);
player.teleToLocation(new Location(oustX, oustY, oustZ), true);
return;
}
final InventoryUpdate iu = new InventoryUpdate();
iu.addModifiedItem(ticket);
player.sendInventoryUpdate(iu);
}
addPassenger(player);
}
});
}
@Override
public boolean updatePosition()
{
final boolean result = super.updatePosition();
for (L2PcInstance player : _passengers)
{
if ((player != null) && (player.getVehicle() == this))
{
player.setXYZ(getX(), getY(), getZ());
player.revalidateZone(false);
}
}
return result;
}
@Override
public void teleToLocation(ILocational loc, boolean allowRandomOffset)
{
if (isMoving())
{
stopMove(null);
}
setIsTeleporting(true);
getAI().setIntention(CtrlIntention.AI_INTENTION_ACTIVE);
for (L2PcInstance player : _passengers)
{
if (player != null)
{
player.teleToLocation(loc, false);
}
}
decayMe();
setXYZ(loc);
// temporary fix for heading on teleports
if (loc.getHeading() != 0)
{
setHeading(loc.getHeading());
}
onTeleported();
revalidateZone(true);
}
@Override
public void stopMove(Location loc)
{
_move = null;
if (loc != null)
{
setXYZ(loc);
setHeading(loc.getHeading());
revalidateZone(true);
}
}
@Override
public boolean deleteMe()
{
_engine = null;
try
{
if (isMoving())
{
stopMove(null);
}
}
catch (Exception e)
{
_log.log(Level.SEVERE, "Failed stopMove().", e);
}
try
{
oustPlayers();
}
catch (Exception e)
{
_log.log(Level.SEVERE, "Failed oustPlayers().", e);
}
final ZoneRegion oldZoneRegion = ZoneManager.getInstance().getRegion(this);
try
{
decayMe();
}
catch (Exception e)
{
_log.log(Level.SEVERE, "Failed decayMe().", e);
}
oldZoneRegion.removeFromZones(this);
// Remove L2Object object from _allObjects of World
L2World.getInstance().removeObject(this);
return super.deleteMe();
}
@Override
public void updateAbnormalVisualEffects()
{
}
@Override
public L2ItemInstance getActiveWeaponInstance()
{
return null;
}
@Override
public L2Weapon getActiveWeaponItem()
{
return null;
}
@Override
public L2ItemInstance getSecondaryWeaponInstance()
{
return null;
}
@Override
public L2Weapon getSecondaryWeaponItem()
{
return null;
}
@Override
public int getLevel()
{
return 0;
}
@Override
public boolean isAutoAttackable(L2Character attacker)
{
return false;
}
@Override
public void detachAI()
{
}
@Override
public boolean isVehicle()
{
return true;
}
}

View File

@@ -0,0 +1,254 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model.actor.appearance;
import com.l2jmobius.gameserver.enums.Sex;
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
public class PcAppearance
{
public static final int DEFAULT_TITLE_COLOR = 0xECF9A2;
private L2PcInstance _owner;
private byte _face;
private byte _hairColor;
private byte _hairStyle;
private boolean _sex; // Female true(1)
/** The current visible name of this player, not necessarily the real one */
private String _visibleName;
/** The current visible title of this player, not necessarily the real one */
private String _visibleTitle;
/** The default name color is 0xFFFFFF. */
private int _nameColor = 0xFFFFFF;
/** The default title color is 0xECF9A2. */
private int _titleColor = DEFAULT_TITLE_COLOR;
private int _visibleClanId = -1;
private int _visibleClanCrestId = -1;
private int _visibleClanLargeCrestId = -1;
private int _visibleAllyId = -1;
private int _visibleAllyCrestId = -1;
public PcAppearance(byte face, byte hColor, byte hStyle, boolean sex)
{
_face = face;
_hairColor = hColor;
_hairStyle = hStyle;
_sex = sex;
}
/**
* @param visibleName The visibleName to set.
*/
public final void setVisibleName(String visibleName)
{
_visibleName = visibleName;
}
/**
* @return Returns the visibleName.
*/
public final String getVisibleName()
{
if (_visibleName == null)
{
return getOwner().getName();
}
return _visibleName;
}
/**
* @param visibleTitle The visibleTitle to set.
*/
public final void setVisibleTitle(String visibleTitle)
{
_visibleTitle = visibleTitle;
}
/**
* @return Returns the visibleTitle.
*/
public final String getVisibleTitle()
{
if (_visibleTitle == null)
{
return getOwner().getTitle();
}
return _visibleTitle;
}
public final byte getFace()
{
return _face;
}
/**
* @param value
*/
public final void setFace(int value)
{
_face = (byte) value;
}
public final byte getHairColor()
{
return _hairColor;
}
/**
* @param value
*/
public final void setHairColor(int value)
{
_hairColor = (byte) value;
}
public final byte getHairStyle()
{
return _hairStyle;
}
/**
* @param value
*/
public final void setHairStyle(int value)
{
_hairStyle = (byte) value;
}
/**
* @return true if char is female
*/
public final boolean getSex()
{
return _sex;
}
/**
* @return Sex of the char
*/
public Sex getSexType()
{
return _sex ? Sex.FEMALE : Sex.MALE;
}
/**
* @param isfemale
*/
public final void setSex(boolean isfemale)
{
_sex = isfemale;
}
public int getNameColor()
{
return _nameColor;
}
public void setNameColor(int nameColor)
{
if (nameColor < 0)
{
return;
}
_nameColor = nameColor;
}
public void setNameColor(int red, int green, int blue)
{
_nameColor = (red & 0xFF) + ((green & 0xFF) << 8) + ((blue & 0xFF) << 16);
}
public int getTitleColor()
{
return _titleColor;
}
public void setTitleColor(int titleColor)
{
if (titleColor < 0)
{
return;
}
_titleColor = titleColor;
}
public void setTitleColor(int red, int green, int blue)
{
_titleColor = (red & 0xFF) + ((green & 0xFF) << 8) + ((blue & 0xFF) << 16);
}
/**
* @param owner The owner to set.
*/
public void setOwner(L2PcInstance owner)
{
_owner = owner;
}
/**
* @return Returns the owner.
*/
public L2PcInstance getOwner()
{
return _owner;
}
public int getVisibleClanId()
{
return _visibleClanId != -1 ? _visibleClanId : getOwner().isCursedWeaponEquipped() ? 0 : getOwner().getClanId();
}
public int getVisibleClanCrestId()
{
return _visibleClanCrestId != -1 ? _visibleClanCrestId : getOwner().isCursedWeaponEquipped() ? 0 : getOwner().getClanCrestId();
}
public int getVisibleClanLargeCrestId()
{
return _visibleClanLargeCrestId != -1 ? _visibleClanLargeCrestId : getOwner().isCursedWeaponEquipped() ? 0 : getOwner().getClanCrestLargeId();
}
public int getVisibleAllyId()
{
return _visibleAllyId != -1 ? _visibleAllyId : getOwner().isCursedWeaponEquipped() ? 0 : getOwner().getAllyId();
}
public int getVisibleAllyCrestId()
{
return _visibleAllyCrestId != -1 ? _visibleAllyCrestId : getOwner().isCursedWeaponEquipped() ? 0 : getOwner().getAllyCrestId();
}
public void setVisibleClanData(int clanId, int clanCrestId, int clanLargeCrestId, int allyId, int allyCrestId)
{
_visibleClanId = clanId;
_visibleClanCrestId = clanCrestId;
_visibleClanLargeCrestId = clanLargeCrestId;
_visibleAllyId = allyId;
_visibleAllyCrestId = allyCrestId;
}
}

View File

@@ -0,0 +1,59 @@
/*
* This file is part of the L2J Mobius project.
*
* 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 com.l2jmobius.gameserver.model.actor.instance;
import com.l2jmobius.gameserver.enums.InstanceType;
import com.l2jmobius.gameserver.model.actor.L2Character;
import com.l2jmobius.gameserver.model.actor.L2Npc;
import com.l2jmobius.gameserver.model.actor.templates.L2NpcTemplate;
import com.l2jmobius.gameserver.network.serverpackets.commission.ExShowCommission;
/**
* @author NosBit
*/
public class CommissionManagerInstance extends L2Npc
{
public CommissionManagerInstance(L2NpcTemplate template)
{
super(template);
setInstanceType(InstanceType.CommissionManagerInstance);
}
@Override
public boolean isAutoAttackable(L2Character attacker)
{
if (attacker.isMonster())
{
return true;
}
return super.isAutoAttackable(attacker);
}
@Override
public void onBypassFeedback(L2PcInstance player, String command)
{
if (command.equalsIgnoreCase("show_commission"))
{
player.sendPacket(ExShowCommission.STATIC_PACKET);
}
else
{
super.onBypassFeedback(player, command);
}
}
}

Some files were not shown because too many files have changed in this diff Show More