Project update.
This commit is contained in:
@@ -0,0 +1,112 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.holders.RangeAbilityPointsHolder;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public final class AbilityPointsData implements IXmlReader
|
||||
{
|
||||
private final List<RangeAbilityPointsHolder> _points = new ArrayList<>();
|
||||
|
||||
protected AbilityPointsData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_points.clear();
|
||||
parseFile(new File("config/AbilityPoints.xml"));
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _points.size() + " range fees.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("points".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
final int from = parseInteger(attrs, "from");
|
||||
final int to = parseInteger(attrs, "to");
|
||||
final int costs = parseInteger(attrs, "costs");
|
||||
_points.add(new RangeAbilityPointsHolder(from, to, costs));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public RangeAbilityPointsHolder getHolder(int points)
|
||||
{
|
||||
for (RangeAbilityPointsHolder holder : _points)
|
||||
{
|
||||
if ((holder.getMin() <= points) && (holder.getMax() >= points))
|
||||
{
|
||||
return holder;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public long getPrice(int points)
|
||||
{
|
||||
points++; // for next point
|
||||
final RangeAbilityPointsHolder holder = getHolder(points);
|
||||
if (holder == null)
|
||||
{
|
||||
final RangeAbilityPointsHolder prevHolder = getHolder(points - 1);
|
||||
if (prevHolder != null)
|
||||
{
|
||||
return prevHolder.getSP();
|
||||
}
|
||||
|
||||
// No data found
|
||||
return points >= 13 ? 1_000_000_000 : points >= 9 ? 750_000_000 : points >= 5 ? 500_000_000 : 250_000_000;
|
||||
}
|
||||
return holder.getSP();
|
||||
}
|
||||
|
||||
public static final AbilityPointsData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final AbilityPointsData _instance = new AbilityPointsData();
|
||||
}
|
||||
}
|
352
trunk/java/com/l2jmobius/gameserver/data/xml/impl/AdminData.java
Normal file
352
trunk/java/com/l2jmobius/gameserver/data/xml/impl/AdminData.java
Normal file
@@ -0,0 +1,352 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Map.Entry;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.L2AccessLevel;
|
||||
import com.l2jmobius.gameserver.model.L2AdminCommandAccessRight;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
|
||||
import com.l2jmobius.gameserver.network.SystemMessageId;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.L2GameServerPacket;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Loads administrator access levels and commands.
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public final class AdminData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2AccessLevel> _accessLevels = new HashMap<>();
|
||||
private final Map<String, L2AdminCommandAccessRight> _adminCommandAccessRights = new HashMap<>();
|
||||
private final Map<L2PcInstance, Boolean> _gmList = new ConcurrentHashMap<>();
|
||||
private int _highestLevel = 0;
|
||||
|
||||
protected AdminData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_accessLevels.clear();
|
||||
_adminCommandAccessRights.clear();
|
||||
parseDatapackFile("../config/accessLevels.xml");
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _accessLevels.size() + " Access Levels.");
|
||||
parseDatapackFile("../config/adminCommands.xml");
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _adminCommandAccessRights.size() + " Access Commands.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
NamedNodeMap attrs;
|
||||
Node attr;
|
||||
StatsSet set;
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("access".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
set = new StatsSet();
|
||||
attrs = d.getAttributes();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
attr = attrs.item(i);
|
||||
set.set(attr.getNodeName(), attr.getNodeValue());
|
||||
}
|
||||
final L2AccessLevel level = new L2AccessLevel(set);
|
||||
if (level.getLevel() > _highestLevel)
|
||||
{
|
||||
_highestLevel = level.getLevel();
|
||||
}
|
||||
_accessLevels.put(level.getLevel(), level);
|
||||
}
|
||||
else if ("admin".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
set = new StatsSet();
|
||||
attrs = d.getAttributes();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
attr = attrs.item(i);
|
||||
set.set(attr.getNodeName(), attr.getNodeValue());
|
||||
}
|
||||
final L2AdminCommandAccessRight command = new L2AdminCommandAccessRight(set);
|
||||
_adminCommandAccessRights.put(command.getAdminCommand(), command);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the access level by characterAccessLevel.
|
||||
* @param accessLevelNum as int
|
||||
* @return the access level instance by char access level
|
||||
*/
|
||||
public L2AccessLevel getAccessLevel(int accessLevelNum)
|
||||
{
|
||||
if (accessLevelNum < 0)
|
||||
{
|
||||
return _accessLevels.get(-1);
|
||||
}
|
||||
else if (!_accessLevels.containsKey(accessLevelNum))
|
||||
{
|
||||
_accessLevels.put(accessLevelNum, new L2AccessLevel());
|
||||
}
|
||||
return _accessLevels.get(accessLevelNum);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the master access level.
|
||||
* @return the master access level
|
||||
*/
|
||||
public L2AccessLevel getMasterAccessLevel()
|
||||
{
|
||||
return _accessLevels.get(_highestLevel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks for access level.
|
||||
* @param id the id
|
||||
* @return {@code true}, if successful, {@code false} otherwise
|
||||
*/
|
||||
public boolean hasAccessLevel(int id)
|
||||
{
|
||||
return _accessLevels.containsKey(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks for access.
|
||||
* @param adminCommand the admin command
|
||||
* @param accessLevel the access level
|
||||
* @return {@code true}, if successful, {@code false} otherwise
|
||||
*/
|
||||
public boolean hasAccess(String adminCommand, L2AccessLevel accessLevel)
|
||||
{
|
||||
L2AdminCommandAccessRight acar = _adminCommandAccessRights.get(adminCommand);
|
||||
if (acar == null)
|
||||
{
|
||||
// Trying to avoid the spam for next time when the gm would try to use the same command
|
||||
if ((accessLevel.getLevel() > 0) && (accessLevel.getLevel() == _highestLevel))
|
||||
{
|
||||
acar = new L2AdminCommandAccessRight(adminCommand, true, accessLevel.getLevel());
|
||||
_adminCommandAccessRights.put(adminCommand, acar);
|
||||
LOGGER.info(getClass().getSimpleName() + ": No rights defined for admin command " + adminCommand + " auto setting accesslevel: " + accessLevel.getLevel() + " !");
|
||||
}
|
||||
else
|
||||
{
|
||||
LOGGER.info(getClass().getSimpleName() + ": No rights defined for admin command " + adminCommand + " !");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
return acar.hasAccess(accessLevel);
|
||||
}
|
||||
|
||||
/**
|
||||
* Require confirm.
|
||||
* @param command the command
|
||||
* @return {@code true}, if the command require confirmation, {@code false} otherwise
|
||||
*/
|
||||
public boolean requireConfirm(String command)
|
||||
{
|
||||
final L2AdminCommandAccessRight acar = _adminCommandAccessRights.get(command);
|
||||
if (acar == null)
|
||||
{
|
||||
LOGGER.info(getClass().getSimpleName() + ": No rights defined for admin command " + command + ".");
|
||||
return false;
|
||||
}
|
||||
return acar.getRequireConfirm();
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the all GMs.
|
||||
* @param includeHidden the include hidden
|
||||
* @return the all GMs
|
||||
*/
|
||||
public List<L2PcInstance> getAllGms(boolean includeHidden)
|
||||
{
|
||||
final List<L2PcInstance> tmpGmList = new ArrayList<>();
|
||||
for (Entry<L2PcInstance, Boolean> entry : _gmList.entrySet())
|
||||
{
|
||||
if (includeHidden || !entry.getValue())
|
||||
{
|
||||
tmpGmList.add(entry.getKey());
|
||||
}
|
||||
}
|
||||
return tmpGmList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the all GM names.
|
||||
* @param includeHidden the include hidden
|
||||
* @return the all GM names
|
||||
*/
|
||||
public List<String> getAllGmNames(boolean includeHidden)
|
||||
{
|
||||
final List<String> tmpGmList = new ArrayList<>();
|
||||
for (Entry<L2PcInstance, Boolean> entry : _gmList.entrySet())
|
||||
{
|
||||
if (!entry.getValue())
|
||||
{
|
||||
tmpGmList.add(entry.getKey().getName());
|
||||
}
|
||||
else if (includeHidden)
|
||||
{
|
||||
tmpGmList.add(entry.getKey().getName() + " (invis)");
|
||||
}
|
||||
}
|
||||
return tmpGmList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a L2PcInstance player to the Set _gmList.
|
||||
* @param player the player
|
||||
* @param hidden the hidden
|
||||
*/
|
||||
public void addGm(L2PcInstance player, boolean hidden)
|
||||
{
|
||||
_gmList.put(player, hidden);
|
||||
}
|
||||
|
||||
/**
|
||||
* Delete a GM.
|
||||
* @param player the player
|
||||
*/
|
||||
public void deleteGm(L2PcInstance player)
|
||||
{
|
||||
_gmList.remove(player);
|
||||
}
|
||||
|
||||
/**
|
||||
* GM will be displayed on clients GM list.
|
||||
* @param player the player
|
||||
*/
|
||||
public void showGm(L2PcInstance player)
|
||||
{
|
||||
if (_gmList.containsKey(player))
|
||||
{
|
||||
_gmList.put(player, false);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* GM will no longer be displayed on clients GM list.
|
||||
* @param player the player
|
||||
*/
|
||||
public void hideGm(L2PcInstance player)
|
||||
{
|
||||
if (_gmList.containsKey(player))
|
||||
{
|
||||
_gmList.put(player, true);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if is GM online.
|
||||
* @param includeHidden the include hidden
|
||||
* @return true, if is GM online
|
||||
*/
|
||||
public boolean isGmOnline(boolean includeHidden)
|
||||
{
|
||||
for (Entry<L2PcInstance, Boolean> entry : _gmList.entrySet())
|
||||
{
|
||||
if (includeHidden || !entry.getValue())
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Send list to player.
|
||||
* @param player the player
|
||||
*/
|
||||
public void sendListToPlayer(L2PcInstance player)
|
||||
{
|
||||
if (isGmOnline(player.isGM()))
|
||||
{
|
||||
player.sendPacket(SystemMessageId.GM_LIST);
|
||||
|
||||
for (String name : getAllGmNames(player.isGM()))
|
||||
{
|
||||
final SystemMessage sm = SystemMessage.getSystemMessage(SystemMessageId.GM_C1);
|
||||
sm.addString(name);
|
||||
player.sendPacket(sm);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
player.sendPacket(SystemMessageId.THERE_ARE_NO_GMS_CURRENTLY_VISIBLE_IN_THE_PUBLIC_LIST_AS_THEY_MAY_BE_PERFORMING_OTHER_FUNCTIONS_AT_THE_MOMENT);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Broadcast to GMs.
|
||||
* @param packet the packet
|
||||
*/
|
||||
public void broadcastToGMs(L2GameServerPacket packet)
|
||||
{
|
||||
for (L2PcInstance gm : getAllGms(true))
|
||||
{
|
||||
gm.sendPacket(packet);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Broadcast message to GMs.
|
||||
* @param message the message
|
||||
*/
|
||||
public void broadcastMessageToGMs(String message)
|
||||
{
|
||||
for (L2PcInstance gm : getAllGms(true))
|
||||
{
|
||||
gm.sendMessage(message);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of AdminTable.
|
||||
* @return AccessLevels: the one and only instance of this class<br>
|
||||
*/
|
||||
public static AdminData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final AdminData _instance = new AdminData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,153 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.datatables.ItemTable;
|
||||
import com.l2jmobius.gameserver.enums.Race;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.items.appearance.AppearanceStone;
|
||||
import com.l2jmobius.gameserver.model.items.appearance.AppearanceTargetType;
|
||||
import com.l2jmobius.gameserver.model.items.type.CrystalType;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public class AppearanceItemData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, AppearanceStone> _stones = new HashMap<>();
|
||||
|
||||
protected AppearanceItemData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
parseDatapackFile("AppearanceStones.xml");
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _stones.size() + " Stones");
|
||||
|
||||
//@formatter:off
|
||||
/*
|
||||
for (L2Item item : ItemTable.getInstance().getAllItems())
|
||||
{
|
||||
if ((item == null) || !item.getName().contains("Appearance Stone"))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
if (item.getName().contains("Pack") || _stones.containsKey(item.getId()))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
System.out.println("Unhandled appearance stone: " + item);
|
||||
}
|
||||
*/
|
||||
//@formatter:on
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("appearance_stone".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
final StatsSet set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
|
||||
final AppearanceStone stone = new AppearanceStone(set);
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
switch (c.getNodeName())
|
||||
{
|
||||
case "grade":
|
||||
{
|
||||
final CrystalType type = CrystalType.valueOf(c.getTextContent());
|
||||
stone.addCrystalType(type);
|
||||
break;
|
||||
}
|
||||
case "targetType":
|
||||
{
|
||||
final AppearanceTargetType type = AppearanceTargetType.valueOf(c.getTextContent());
|
||||
stone.addTargetType(type);
|
||||
break;
|
||||
}
|
||||
case "bodyPart":
|
||||
{
|
||||
final int part = ItemTable.SLOTS.get(c.getTextContent());
|
||||
stone.addBodyPart(part);
|
||||
break;
|
||||
}
|
||||
case "race":
|
||||
{
|
||||
final Race race = Race.valueOf(c.getTextContent());
|
||||
stone.addRace(race);
|
||||
break;
|
||||
}
|
||||
case "raceNot":
|
||||
{
|
||||
final Race raceNot = Race.valueOf(c.getTextContent());
|
||||
stone.addRaceNot(raceNot);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
_stones.put(stone.getId(), stone);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public AppearanceStone getStone(int stone)
|
||||
{
|
||||
return _stones.get(stone);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of AppearanceItemData.
|
||||
* @return single instance of AppearanceItemData
|
||||
*/
|
||||
public static final AppearanceItemData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final AppearanceItemData _instance = new AppearanceItemData();
|
||||
}
|
||||
}
|
@@ -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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.L2ArmorSet;
|
||||
import com.l2jmobius.gameserver.model.holders.ArmorsetSkillHolder;
|
||||
import com.l2jmobius.gameserver.model.holders.SkillHolder;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Loads armor set bonuses.
|
||||
* @author godson, Luno, UnAfraid
|
||||
*/
|
||||
public final class ArmorSetsData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2ArmorSet> _armorSets = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new armor sets data.
|
||||
*/
|
||||
protected ArmorSetsData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_armorSets.clear();
|
||||
parseDatapackDirectory("stats/armorsets", false);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _armorSets.size() + " Armor sets.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("set".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final L2ArmorSet set = new L2ArmorSet();
|
||||
set.setIsVisual(parseBoolean(d.getAttributes(), "visual", false));
|
||||
set.setMinimumPieces(parseInteger(d.getAttributes(), "minimumPieces"));
|
||||
|
||||
for (Node a = d.getFirstChild(); a != null; a = a.getNextSibling())
|
||||
{
|
||||
final NamedNodeMap attrs = a.getAttributes();
|
||||
switch (a.getNodeName())
|
||||
{
|
||||
case "chest":
|
||||
{
|
||||
set.addChest(parseInteger(attrs, "id"));
|
||||
break;
|
||||
}
|
||||
case "feet":
|
||||
{
|
||||
set.addFeet(parseInteger(attrs, "id"));
|
||||
break;
|
||||
}
|
||||
case "gloves":
|
||||
{
|
||||
set.addGloves(parseInteger(attrs, "id"));
|
||||
break;
|
||||
}
|
||||
case "head":
|
||||
{
|
||||
set.addHead(parseInteger(attrs, "id"));
|
||||
break;
|
||||
}
|
||||
case "legs":
|
||||
{
|
||||
set.addLegs(parseInteger(attrs, "id"));
|
||||
break;
|
||||
}
|
||||
case "shield":
|
||||
{
|
||||
set.addShield(parseInteger(attrs, "id"));
|
||||
break;
|
||||
}
|
||||
case "skill":
|
||||
{
|
||||
final int skillId = parseInteger(attrs, "id");
|
||||
final int skillLevel = parseInteger(attrs, "level");
|
||||
final int minimumPieces = parseInteger(attrs, "minimumPieces", set.getMinimumPieces());
|
||||
set.addSkill(new ArmorsetSkillHolder(skillId, skillLevel, minimumPieces));
|
||||
break;
|
||||
}
|
||||
case "shield_skill":
|
||||
{
|
||||
final int skillId = parseInteger(attrs, "id");
|
||||
final int skillLevel = parseInteger(attrs, "level");
|
||||
set.addShieldSkill(new SkillHolder(skillId, skillLevel));
|
||||
break;
|
||||
}
|
||||
case "enchant6skill":
|
||||
{
|
||||
final int skillId = parseInteger(attrs, "id");
|
||||
final int skillLevel = parseInteger(attrs, "level");
|
||||
final int minimumEnchant = parseInteger(attrs, "minimumEnchant", 6);
|
||||
set.addEnchantSkill(new ArmorsetSkillHolder(skillId, skillLevel, minimumEnchant));
|
||||
break;
|
||||
}
|
||||
case "enchant7skill":
|
||||
{
|
||||
final int skillId = parseInteger(attrs, "id");
|
||||
final int skillLevel = parseInteger(attrs, "level");
|
||||
final int minimumEnchant = parseInteger(attrs, "minimumEnchant", 7);
|
||||
set.addEnchantSkill(new ArmorsetSkillHolder(skillId, skillLevel, minimumEnchant));
|
||||
break;
|
||||
}
|
||||
case "enchant8skill":
|
||||
{
|
||||
final int skillId = parseInteger(attrs, "id");
|
||||
final int skillLevel = parseInteger(attrs, "level");
|
||||
final int minimumEnchant = parseInteger(attrs, "minimumEnchant", 8);
|
||||
set.addEnchantSkill(new ArmorsetSkillHolder(skillId, skillLevel, minimumEnchant));
|
||||
break;
|
||||
}
|
||||
case "con":
|
||||
{
|
||||
set.addCon(parseInteger(attrs, "val"));
|
||||
break;
|
||||
}
|
||||
case "dex":
|
||||
{
|
||||
set.addDex(parseInteger(attrs, "val"));
|
||||
break;
|
||||
}
|
||||
case "str":
|
||||
{
|
||||
set.addStr(parseInteger(attrs, "val"));
|
||||
break;
|
||||
}
|
||||
case "men":
|
||||
{
|
||||
set.addMen(parseInteger(attrs, "val"));
|
||||
break;
|
||||
}
|
||||
case "wit":
|
||||
{
|
||||
set.addWit(parseInteger(attrs, "val"));
|
||||
break;
|
||||
}
|
||||
case "int":
|
||||
{
|
||||
set.addInt(parseInteger(attrs, "val"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (int chestId : set.getChests())
|
||||
{
|
||||
_armorSets.put(chestId, set);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if is armor set.
|
||||
* @param chestId the chest Id to verify.
|
||||
* @return {@code true} if the chest Id belongs to a registered armor set, {@code false} otherwise.
|
||||
*/
|
||||
public boolean isArmorSet(int chestId)
|
||||
{
|
||||
return _armorSets.containsKey(chestId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the sets the.
|
||||
* @param chestId the chest Id identifying the armor set.
|
||||
* @return the armor set associated to the give chest Id.
|
||||
*/
|
||||
public L2ArmorSet getSet(int chestId)
|
||||
{
|
||||
return _armorSets.get(chestId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of ArmorSetsData.
|
||||
* @return single instance of ArmorSetsData
|
||||
*/
|
||||
public static ArmorSetsData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final ArmorSetsData _instance = new ArmorSetsData();
|
||||
}
|
||||
}
|
@@ -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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.enums.Race;
|
||||
import com.l2jmobius.gameserver.enums.Sex;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.beautyshop.BeautyData;
|
||||
import com.l2jmobius.gameserver.model.beautyshop.BeautyItem;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author Sdw
|
||||
*/
|
||||
public final class BeautyShopData implements IXmlReader
|
||||
{
|
||||
private final Map<Race, Map<Sex, BeautyData>> _beautyList = new HashMap<>();
|
||||
private final Map<Sex, BeautyData> _beautyData = new HashMap<>();
|
||||
|
||||
protected BeautyShopData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_beautyList.clear();
|
||||
_beautyData.clear();
|
||||
parseDatapackFile("BeautyShop.xml");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
NamedNodeMap attrs;
|
||||
StatsSet set;
|
||||
Node att;
|
||||
Race race = null;
|
||||
Sex sex = null;
|
||||
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("race".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
att = d.getAttributes().getNamedItem("type");
|
||||
if (att != null)
|
||||
{
|
||||
race = parseEnum(att, Race.class);
|
||||
}
|
||||
|
||||
for (Node b = d.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("sex".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
att = b.getAttributes().getNamedItem("type");
|
||||
if (att != null)
|
||||
{
|
||||
sex = parseEnum(att, Sex.class);
|
||||
}
|
||||
|
||||
final BeautyData beautyData = new BeautyData();
|
||||
|
||||
for (Node a = b.getFirstChild(); a != null; a = a.getNextSibling())
|
||||
{
|
||||
if ("hair".equalsIgnoreCase(a.getNodeName()))
|
||||
{
|
||||
attrs = a.getAttributes();
|
||||
set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
final BeautyItem hair = new BeautyItem(set);
|
||||
|
||||
for (Node g = a.getFirstChild(); g != null; g = g.getNextSibling())
|
||||
{
|
||||
if ("color".equalsIgnoreCase(g.getNodeName()))
|
||||
{
|
||||
attrs = g.getAttributes();
|
||||
set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
hair.addColor(set);
|
||||
}
|
||||
}
|
||||
beautyData.addHair(hair);
|
||||
}
|
||||
else if ("face".equalsIgnoreCase(a.getNodeName()))
|
||||
{
|
||||
attrs = a.getAttributes();
|
||||
set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
final BeautyItem face = new BeautyItem(set);
|
||||
beautyData.addFace(face);
|
||||
}
|
||||
}
|
||||
|
||||
_beautyData.put(sex, beautyData);
|
||||
}
|
||||
}
|
||||
_beautyList.put(race, _beautyData);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public boolean hasBeautyData(Race race, Sex sex)
|
||||
{
|
||||
return _beautyList.containsKey(race) && _beautyList.get(race).containsKey(sex);
|
||||
}
|
||||
|
||||
public BeautyData getBeautyData(Race race, Sex sex)
|
||||
{
|
||||
if (_beautyList.containsKey(race))
|
||||
{
|
||||
return _beautyList.get(race).get(sex);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public static BeautyShopData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final BeautyShopData _instance = new BeautyShopData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,192 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileFilter;
|
||||
import java.sql.Connection;
|
||||
import java.sql.ResultSet;
|
||||
import java.sql.Statement;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.commons.database.pool.impl.ConnectionFactory;
|
||||
import com.l2jmobius.gameserver.datatables.ItemTable;
|
||||
import com.l2jmobius.gameserver.model.buylist.L2BuyList;
|
||||
import com.l2jmobius.gameserver.model.buylist.Product;
|
||||
import com.l2jmobius.gameserver.model.items.L2Item;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
import com.l2jmobius.util.file.filter.NumericNameFilter;
|
||||
|
||||
/**
|
||||
* Loads buy lists for NPCs.
|
||||
* @author NosBit
|
||||
*/
|
||||
public final class BuyListData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2BuyList> _buyLists = new HashMap<>();
|
||||
private static final FileFilter NUMERIC_FILTER = new NumericNameFilter();
|
||||
|
||||
protected BuyListData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_buyLists.clear();
|
||||
parseDatapackDirectory("buylists", false);
|
||||
if (Config.CUSTOM_BUYLIST_LOAD)
|
||||
{
|
||||
parseDatapackDirectory("buylists/custom", false);
|
||||
}
|
||||
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _buyLists.size() + " BuyLists.");
|
||||
|
||||
try (Connection con = ConnectionFactory.getInstance().getConnection();
|
||||
Statement statement = con.createStatement();
|
||||
ResultSet rs = statement.executeQuery("SELECT * FROM `buylists`"))
|
||||
{
|
||||
while (rs.next())
|
||||
{
|
||||
final int buyListId = rs.getInt("buylist_id");
|
||||
final int itemId = rs.getInt("item_id");
|
||||
final long count = rs.getLong("count");
|
||||
final long nextRestockTime = rs.getLong("next_restock_time");
|
||||
final L2BuyList buyList = getBuyList(buyListId);
|
||||
if (buyList == null)
|
||||
{
|
||||
LOGGER.warning("BuyList found in database but not loaded from xml! BuyListId: " + buyListId);
|
||||
continue;
|
||||
}
|
||||
final Product product = buyList.getProductByItemId(itemId);
|
||||
if (product == null)
|
||||
{
|
||||
LOGGER.warning("ItemId found in database but not loaded from xml! BuyListId: " + buyListId + " ItemId: " + itemId);
|
||||
continue;
|
||||
}
|
||||
if (count < product.getMaxCount())
|
||||
{
|
||||
product.setCount(count);
|
||||
product.restartRestockTask(nextRestockTime);
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, "Failed to load buyList data from database.", e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc, File f)
|
||||
{
|
||||
try
|
||||
{
|
||||
final int buyListId = Integer.parseInt(f.getName().replaceAll(".xml", ""));
|
||||
|
||||
for (Node node = doc.getFirstChild(); node != null; node = node.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(node.getNodeName()))
|
||||
{
|
||||
final L2BuyList buyList = new L2BuyList(buyListId);
|
||||
for (Node list_node = node.getFirstChild(); list_node != null; list_node = list_node.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
int itemId = -1;
|
||||
long price = -1;
|
||||
long restockDelay = -1;
|
||||
long count = -1;
|
||||
final NamedNodeMap attrs = list_node.getAttributes();
|
||||
Node attr = attrs.getNamedItem("id");
|
||||
itemId = Integer.parseInt(attr.getNodeValue());
|
||||
attr = attrs.getNamedItem("price");
|
||||
if (attr != null)
|
||||
{
|
||||
price = Long.parseLong(attr.getNodeValue());
|
||||
}
|
||||
attr = attrs.getNamedItem("restock_delay");
|
||||
if (attr != null)
|
||||
{
|
||||
restockDelay = Long.parseLong(attr.getNodeValue());
|
||||
}
|
||||
attr = attrs.getNamedItem("count");
|
||||
if (attr != null)
|
||||
{
|
||||
count = Long.parseLong(attr.getNodeValue());
|
||||
}
|
||||
final L2Item item = ItemTable.getInstance().getTemplate(itemId);
|
||||
if (item != null)
|
||||
{
|
||||
buyList.addProduct(new Product(buyList.getListId(), item, price, restockDelay, count));
|
||||
}
|
||||
else
|
||||
{
|
||||
LOGGER.warning("Item not found. BuyList:" + buyList.getListId() + " ItemID:" + itemId + " File:" + f.getName());
|
||||
}
|
||||
}
|
||||
else if ("npcs".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
for (Node npcs_node = list_node.getFirstChild(); npcs_node != null; npcs_node = npcs_node.getNextSibling())
|
||||
{
|
||||
if ("npc".equalsIgnoreCase(npcs_node.getNodeName()))
|
||||
{
|
||||
final int npcId = Integer.parseInt(npcs_node.getTextContent());
|
||||
buyList.addAllowedNpc(npcId);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_buyLists.put(buyList.getListId(), buyList);
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, "Failed to load buyList data from xml File:" + f.getName(), e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public FileFilter getCurrentFileFilter()
|
||||
{
|
||||
return NUMERIC_FILTER;
|
||||
}
|
||||
|
||||
public L2BuyList getBuyList(int listId)
|
||||
{
|
||||
return _buyLists.get(listId);
|
||||
}
|
||||
|
||||
public static BuyListData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final BuyListData _instance = new BuyListData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,113 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.enums.CastleSide;
|
||||
import com.l2jmobius.gameserver.model.holders.CastleSpawnHolder;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author St3eT
|
||||
*/
|
||||
public final class CastleData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, List<CastleSpawnHolder>> _castles = new HashMap<>();
|
||||
|
||||
protected CastleData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_castles.clear();
|
||||
parseDatapackDirectory("/castles", true);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node listNode = doc.getFirstChild(); listNode != null; listNode = listNode.getNextSibling())
|
||||
{
|
||||
if ("list".equals(listNode.getNodeName()))
|
||||
{
|
||||
for (Node castleNode = listNode.getFirstChild(); castleNode != null; castleNode = castleNode.getNextSibling())
|
||||
{
|
||||
if ("castle".equals(castleNode.getNodeName()))
|
||||
{
|
||||
final int castleId = parseInteger(castleNode.getAttributes(), "id");
|
||||
final List<CastleSpawnHolder> spawns = new ArrayList<>();
|
||||
|
||||
for (Node tpNode = castleNode.getFirstChild(); tpNode != null; tpNode = tpNode.getNextSibling())
|
||||
{
|
||||
if ("spawn".equals(tpNode.getNodeName()))
|
||||
{
|
||||
final CastleSide side = parseEnum(tpNode.getAttributes(), CastleSide.class, "castleSide", CastleSide.NEUTRAL);
|
||||
for (Node npcNode = tpNode.getFirstChild(); npcNode != null; npcNode = npcNode.getNextSibling())
|
||||
{
|
||||
if ("npc".equals(npcNode.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap np = npcNode.getAttributes();
|
||||
final int npcId = parseInteger(np, "id");
|
||||
final int x = parseInteger(np, "x");
|
||||
final int y = parseInteger(np, "y");
|
||||
final int z = parseInteger(np, "z");
|
||||
final int heading = parseInteger(np, "heading");
|
||||
|
||||
spawns.add(new CastleSpawnHolder(npcId, side, x, y, z, heading));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_castles.put(castleId, spawns);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public final List<CastleSpawnHolder> getSpawnsForSide(int castleId, CastleSide side)
|
||||
{
|
||||
return _castles.getOrDefault(castleId, Collections.emptyList()).stream().filter(s -> s.getSide() == side).collect(Collectors.toList());
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of TeleportersData.
|
||||
* @return single instance of TeleportersData
|
||||
*/
|
||||
public static CastleData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final CastleData _instance = new CastleData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,126 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.logging.Level;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.enums.CategoryType;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Loads the category data with Class or NPC IDs.
|
||||
* @author NosBit, xban1x
|
||||
*/
|
||||
public final class CategoryData implements IXmlReader
|
||||
{
|
||||
private static final Logger LOGGER = Logger.getLogger(CategoryData.class.getName());
|
||||
|
||||
private final Map<CategoryType, Set<Integer>> _categories = new HashMap<>();
|
||||
|
||||
protected CategoryData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_categories.clear();
|
||||
parseDatapackFile("categoryData.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _categories.size() + " Categories.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node node = doc.getFirstChild(); node != null; node = node.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(node.getNodeName()))
|
||||
{
|
||||
for (Node list_node = node.getFirstChild(); list_node != null; list_node = list_node.getNextSibling())
|
||||
{
|
||||
if ("category".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = list_node.getAttributes();
|
||||
final CategoryType categoryType = CategoryType.findByName(attrs.getNamedItem("name").getNodeValue());
|
||||
if (categoryType == null)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, getClass().getSimpleName() + ": Can't find category by name :" + attrs.getNamedItem("name").getNodeValue());
|
||||
continue;
|
||||
}
|
||||
|
||||
final Set<Integer> ids = new HashSet<>();
|
||||
for (Node category_node = list_node.getFirstChild(); category_node != null; category_node = category_node.getNextSibling())
|
||||
{
|
||||
if ("id".equalsIgnoreCase(category_node.getNodeName()))
|
||||
{
|
||||
ids.add(Integer.parseInt(category_node.getTextContent()));
|
||||
}
|
||||
}
|
||||
_categories.put(categoryType, ids);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if ID is in category.
|
||||
* @param type The category type
|
||||
* @param id The id to be checked
|
||||
* @return {@code true} if id is in category, {@code false} if id is not in category or category was not found
|
||||
*/
|
||||
public boolean isInCategory(CategoryType type, int id)
|
||||
{
|
||||
final Set<Integer> category = getCategoryByType(type);
|
||||
if (category == null)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, getClass().getSimpleName() + ": Can't find category type :" + type);
|
||||
return false;
|
||||
}
|
||||
return category.contains(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the category by category type.
|
||||
* @param type The category type
|
||||
* @return A {@code Set} containing all the IDs in category if category is found, {@code null} if category was not found
|
||||
*/
|
||||
public Set<Integer> getCategoryByType(CategoryType type)
|
||||
{
|
||||
return _categories.get(type);
|
||||
}
|
||||
|
||||
public static CategoryData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final CategoryData _instance = new CategoryData();
|
||||
}
|
||||
}
|
@@ -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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.base.ClassId;
|
||||
import com.l2jmobius.gameserver.model.base.ClassInfo;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Loads the the list of classes and it's info.
|
||||
* @author Zoey76
|
||||
*/
|
||||
public final class ClassListData implements IXmlReader
|
||||
{
|
||||
private final Map<ClassId, ClassInfo> _classData = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new class list data.
|
||||
*/
|
||||
protected ClassListData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_classData.clear();
|
||||
parseDatapackFile("stats/chars/classList.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _classData.size() + " Class data.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equals(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
if ("class".equals(d.getNodeName()))
|
||||
{
|
||||
Node attr = attrs.getNamedItem("classId");
|
||||
final ClassId classId = ClassId.getClassId(parseInteger(attr));
|
||||
attr = attrs.getNamedItem("name");
|
||||
final String className = attr.getNodeValue();
|
||||
attr = attrs.getNamedItem("parentClassId");
|
||||
final ClassId parentClassId = (attr != null) ? ClassId.getClassId(parseInteger(attr)) : null;
|
||||
_classData.put(classId, new ClassInfo(classId, className, parentClassId));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the class list.
|
||||
* @return the complete class list
|
||||
*/
|
||||
public Map<ClassId, ClassInfo> getClassList()
|
||||
{
|
||||
return _classData;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the class info.
|
||||
* @param classId the class ID
|
||||
* @return the class info related to the given {@code classId}
|
||||
*/
|
||||
public ClassInfo getClass(ClassId classId)
|
||||
{
|
||||
return _classData.get(classId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the class info.
|
||||
* @param classId the class Id as integer
|
||||
* @return the class info related to the given {@code classId}
|
||||
*/
|
||||
public ClassInfo getClass(int classId)
|
||||
{
|
||||
final ClassId id = ClassId.getClassId(classId);
|
||||
return (id != null) ? _classData.get(id) : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of ClassListData.
|
||||
* @return single instance of ClassListData
|
||||
*/
|
||||
public static ClassListData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final ClassListData _instance = new ClassListData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,265 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
|
||||
import com.l2jmobius.gameserver.model.base.ClassId;
|
||||
import com.l2jmobius.gameserver.model.holders.DailyMissionHolder;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.dailymission.ExOneDayReceiveRewardList;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* The Class DailyMissionData.
|
||||
* @author Mobius
|
||||
*/
|
||||
public class DailyMissionData implements IXmlReader
|
||||
{
|
||||
private final List<DailyMissionHolder> _dailyMissions = new ArrayList<>();
|
||||
private final List<DailyMissionHolder> _dailyLevelUpMissions = new ArrayList<>();
|
||||
|
||||
/**
|
||||
* Instantiates new daily mission data.
|
||||
*/
|
||||
protected DailyMissionData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_dailyMissions.clear();
|
||||
_dailyLevelUpMissions.clear();
|
||||
parseDatapackFile("dailyMissions.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _dailyMissions.size() + " daily missions.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
int id;
|
||||
int clientId;
|
||||
String type;
|
||||
int level;
|
||||
List<Integer> classesList;
|
||||
Map<Integer, Integer> rewards;
|
||||
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("mission".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
Node att;
|
||||
id = -1;
|
||||
clientId = 0;
|
||||
type = "";
|
||||
level = 1;
|
||||
classesList = new ArrayList<>();
|
||||
rewards = new HashMap<>();
|
||||
|
||||
att = attrs.getNamedItem("id");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing id for daily mission, skipping");
|
||||
continue;
|
||||
}
|
||||
id = Integer.parseInt(att.getNodeValue());
|
||||
|
||||
att = attrs.getNamedItem("clientId");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing clientId for daily mission id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
clientId = Integer.parseInt(att.getNodeValue());
|
||||
|
||||
att = attrs.getNamedItem("type");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing type for daily mission id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
type = att.getNodeValue();
|
||||
|
||||
att = attrs.getNamedItem("level");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing level for daily mission id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
level = Integer.parseInt(att.getNodeValue());
|
||||
|
||||
att = attrs.getNamedItem("classes");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing classes for daily mission id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
if (att.getNodeValue().equalsIgnoreCase("ALL"))
|
||||
{
|
||||
for (ClassId cid : ClassId.values())
|
||||
{
|
||||
classesList.add(cid.getId());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
final String[] s = att.getNodeValue().split(",");
|
||||
for (String element : s)
|
||||
{
|
||||
classesList.add(Integer.parseInt(element));
|
||||
}
|
||||
}
|
||||
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("reward".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
final int itemId = Integer.parseInt(c.getAttributes().getNamedItem("item").getNodeValue());
|
||||
final int itemCount = Integer.parseInt(c.getAttributes().getNamedItem("count").getNodeValue());
|
||||
rewards.put(itemId, itemCount);
|
||||
}
|
||||
}
|
||||
|
||||
if (type.equalsIgnoreCase("LEVEL"))
|
||||
{
|
||||
_dailyLevelUpMissions.add(new DailyMissionHolder(id, clientId, type, level, classesList, rewards));
|
||||
}
|
||||
_dailyMissions.add(new DailyMissionHolder(id, clientId, type, level, classesList, rewards));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param id int
|
||||
* @param player L2PcInstance
|
||||
* @return int
|
||||
*/
|
||||
public int RewardStatus(int id, L2PcInstance player)
|
||||
{
|
||||
if (player.getLevel() < _dailyMissions.get(id - 1).getLevel())
|
||||
{
|
||||
return 2; // Not Available
|
||||
}
|
||||
if (player.getVariables().getString("DailyMission" + id, null) != null)
|
||||
{
|
||||
return 3; // Complete
|
||||
}
|
||||
return 1; // Available
|
||||
}
|
||||
|
||||
/**
|
||||
* @param rewardId1 int
|
||||
* @param player L2PcInstance
|
||||
*/
|
||||
public void rewardPlayer(int rewardId1, L2PcInstance player)
|
||||
{
|
||||
for (DailyMissionHolder mission : _dailyMissions)
|
||||
{
|
||||
if ((mission.getClientId() == rewardId1) && (RewardStatus(mission.getId(), player) == 1))
|
||||
{
|
||||
for (int classId : mission.getAvailableClasses())
|
||||
{
|
||||
if (player.getClassId().getId() == classId)
|
||||
{
|
||||
for (int itemId : mission.getRewards().keySet())
|
||||
{
|
||||
player.addItem("DailyMission", itemId, mission.getRewards().get(itemId), player, true);
|
||||
}
|
||||
for (DailyMissionHolder m : _dailyMissions)
|
||||
{
|
||||
if (mission.getClientId() == m.getClientId())
|
||||
{
|
||||
player.getVariables().set("DailyMission" + m.getId(), System.currentTimeMillis());
|
||||
}
|
||||
}
|
||||
player.sendPacket(new ExOneDayReceiveRewardList(player));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the daily missions.
|
||||
* @param classId int
|
||||
* @return the daily missions
|
||||
*/
|
||||
public List<DailyMissionHolder> getDailyMissions(int classId)
|
||||
{
|
||||
final List<DailyMissionHolder> missions = new ArrayList<>();
|
||||
for (DailyMissionHolder mission : _dailyMissions)
|
||||
{
|
||||
if (mission.getAvailableClasses().contains(classId))
|
||||
{
|
||||
missions.add(mission);
|
||||
}
|
||||
}
|
||||
return missions;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the daily level up missions.
|
||||
* @param classId int
|
||||
* @return the daily level up missions
|
||||
*/
|
||||
public List<DailyMissionHolder> getDailyLevelUpMissions(int classId)
|
||||
{
|
||||
final List<DailyMissionHolder> missions = new ArrayList<>();
|
||||
for (DailyMissionHolder mission : _dailyLevelUpMissions)
|
||||
{
|
||||
if (mission.getAvailableClasses().contains(classId))
|
||||
{
|
||||
missions.add(mission);
|
||||
}
|
||||
}
|
||||
return missions;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of DailyMissionData.
|
||||
* @return single instance of DailyMissionData
|
||||
*/
|
||||
public static DailyMissionData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
/**
|
||||
* The Class SingletonHolder.
|
||||
*/
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final DailyMissionData _instance = new DailyMissionData();
|
||||
}
|
||||
}
|
257
trunk/java/com/l2jmobius/gameserver/data/xml/impl/DoorData.java
Normal file
257
trunk/java/com/l2jmobius/gameserver/data/xml/impl/DoorData.java
Normal file
@@ -0,0 +1,257 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.instancemanager.InstanceManager;
|
||||
import com.l2jmobius.gameserver.instancemanager.MapRegionManager;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2DoorInstance;
|
||||
import com.l2jmobius.gameserver.model.actor.templates.L2DoorTemplate;
|
||||
import com.l2jmobius.gameserver.pathfinding.AbstractNodeLoc;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Loads doors.
|
||||
* @author JIV, GodKratos, UnAfraid
|
||||
*/
|
||||
public class DoorData implements IXmlReader
|
||||
{
|
||||
private static final Map<String, Set<Integer>> _groups = new HashMap<>();
|
||||
private final Map<Integer, L2DoorInstance> _doors = new HashMap<>();
|
||||
private final Map<Integer, StatsSet> _templates = new HashMap<>();
|
||||
private final Map<Integer, List<L2DoorInstance>> _regions = new HashMap<>();
|
||||
|
||||
protected DoorData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_doors.clear();
|
||||
_groups.clear();
|
||||
_regions.clear();
|
||||
parseDatapackFile("doors.xml");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node a = doc.getFirstChild(); a != null; a = a.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(a.getNodeName()))
|
||||
{
|
||||
for (Node b = a.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("door".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = b.getAttributes();
|
||||
final StatsSet set = new StatsSet();
|
||||
set.set("baseHpMax", 1); // Avoid doors without HP value created dead due to default value 0 in L2CharTemplate
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
makeDoor(set);
|
||||
_templates.put(set.getInt("id"), set);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _doors.size() + " Door Templates for " + _regions.size() + " regions.");
|
||||
}
|
||||
|
||||
public void insertCollisionData(StatsSet set)
|
||||
{
|
||||
int posX, posY, nodeX, nodeY, height;
|
||||
height = set.getInt("height");
|
||||
String[] pos = set.getString("node1").split(",");
|
||||
nodeX = Integer.parseInt(pos[0]);
|
||||
nodeY = Integer.parseInt(pos[1]);
|
||||
pos = set.getString("node2").split(",");
|
||||
posX = Integer.parseInt(pos[0]);
|
||||
posY = Integer.parseInt(pos[1]);
|
||||
int collisionRadius; // (max) radius for movement checks
|
||||
collisionRadius = Math.min(Math.abs(nodeX - posX), Math.abs(nodeY - posY));
|
||||
if (collisionRadius < 20)
|
||||
{
|
||||
collisionRadius = 20;
|
||||
}
|
||||
|
||||
set.set("collisionRadius", collisionRadius);
|
||||
set.set("collisionHeight", height);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param set
|
||||
*/
|
||||
private void makeDoor(StatsSet set)
|
||||
{
|
||||
insertCollisionData(set);
|
||||
final L2DoorTemplate template = new L2DoorTemplate(set);
|
||||
final L2DoorInstance door = new L2DoorInstance(template);
|
||||
door.setCurrentHp(door.getMaxHp());
|
||||
door.spawnMe(template.getX(), template.getY(), template.getZ());
|
||||
putDoor(door, MapRegionManager.getInstance().getMapRegionLocId(door));
|
||||
}
|
||||
|
||||
public StatsSet getDoorTemplate(int doorId)
|
||||
{
|
||||
return _templates.get(doorId);
|
||||
}
|
||||
|
||||
public L2DoorInstance getDoor(int doorId)
|
||||
{
|
||||
return _doors.get(doorId);
|
||||
}
|
||||
|
||||
public void putDoor(L2DoorInstance door, int region)
|
||||
{
|
||||
_doors.put(door.getId(), door);
|
||||
|
||||
if (!_regions.containsKey(region))
|
||||
{
|
||||
_regions.put(region, new ArrayList<L2DoorInstance>());
|
||||
}
|
||||
_regions.get(region).add(door);
|
||||
}
|
||||
|
||||
public static void addDoorGroup(String groupName, int doorId)
|
||||
{
|
||||
Set<Integer> set = _groups.get(groupName);
|
||||
if (set == null)
|
||||
{
|
||||
set = new HashSet<>();
|
||||
_groups.put(groupName, set);
|
||||
}
|
||||
set.add(doorId);
|
||||
}
|
||||
|
||||
public static Set<Integer> getDoorsByGroup(String groupName)
|
||||
{
|
||||
return _groups.get(groupName);
|
||||
}
|
||||
|
||||
public Collection<L2DoorInstance> getDoors()
|
||||
{
|
||||
return _doors.values();
|
||||
}
|
||||
|
||||
public boolean checkIfDoorsBetween(AbstractNodeLoc start, AbstractNodeLoc end, int instanceId)
|
||||
{
|
||||
return checkIfDoorsBetween(start.getX(), start.getY(), start.getZ(), end.getX(), end.getY(), end.getZ(), instanceId);
|
||||
}
|
||||
|
||||
public boolean checkIfDoorsBetween(int x, int y, int z, int tx, int ty, int tz, int instanceId)
|
||||
{
|
||||
return checkIfDoorsBetween(x, y, z, tx, ty, tz, instanceId, false);
|
||||
}
|
||||
|
||||
/**
|
||||
* GodKratos: TODO: remove GeoData checks from door table and convert door nodes to Geo zones
|
||||
* @param x
|
||||
* @param y
|
||||
* @param z
|
||||
* @param tx
|
||||
* @param ty
|
||||
* @param tz
|
||||
* @param instanceId
|
||||
* @param doubleFaceCheck
|
||||
* @return {@code boolean}
|
||||
*/
|
||||
public boolean checkIfDoorsBetween(int x, int y, int z, int tx, int ty, int tz, int instanceId, boolean doubleFaceCheck)
|
||||
{
|
||||
Collection<L2DoorInstance> allDoors;
|
||||
if ((instanceId > 0) && (InstanceManager.getInstance().getInstance(instanceId) != null))
|
||||
{
|
||||
allDoors = InstanceManager.getInstance().getInstance(instanceId).getDoors();
|
||||
}
|
||||
else
|
||||
{
|
||||
allDoors = _regions.get(MapRegionManager.getInstance().getMapRegionLocId(x, y));
|
||||
}
|
||||
|
||||
if (allDoors == null)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
for (L2DoorInstance doorInst : allDoors)
|
||||
{
|
||||
// check dead and open
|
||||
if (doorInst.isDead() || doorInst.getOpen() || !doorInst.checkCollision() || (doorInst.getX(0) == 0))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
boolean intersectFace = false;
|
||||
for (int i = 0; i < 4; i++)
|
||||
{
|
||||
final int j = (i + 1) < 4 ? i + 1 : 0;
|
||||
// lower part of the multiplier fraction, if it is 0 we avoid an error and also know that the lines are parallel
|
||||
final int denominator = ((ty - y) * (doorInst.getX(i) - doorInst.getX(j))) - ((tx - x) * (doorInst.getY(i) - doorInst.getY(j)));
|
||||
if (denominator == 0)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
// multipliers to the equations of the lines. If they are lower than 0 or bigger than 1, we know that segments don't intersect
|
||||
final float multiplier1 = (float) (((doorInst.getX(j) - doorInst.getX(i)) * (y - doorInst.getY(i))) - ((doorInst.getY(j) - doorInst.getY(i)) * (x - doorInst.getX(i)))) / denominator;
|
||||
final float multiplier2 = (float) (((tx - x) * (y - doorInst.getY(i))) - ((ty - y) * (x - doorInst.getX(i)))) / denominator;
|
||||
if ((multiplier1 >= 0) && (multiplier1 <= 1) && (multiplier2 >= 0) && (multiplier2 <= 1))
|
||||
{
|
||||
final int intersectZ = Math.round(z + (multiplier1 * (tz - z)));
|
||||
// now checking if the resulting point is between door's min and max z
|
||||
if ((intersectZ > doorInst.getZMin()) && (intersectZ < doorInst.getZMax()))
|
||||
{
|
||||
if (!doubleFaceCheck || intersectFace)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
intersectFace = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public static DoorData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final DoorData _instance = new DoorData();
|
||||
}
|
||||
}
|
@@ -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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.items.enchant.EnchantScroll;
|
||||
import com.l2jmobius.gameserver.model.items.enchant.EnchantSupportItem;
|
||||
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Loads item enchant data.
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public class EnchantItemData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, EnchantScroll> _scrolls = new HashMap<>();
|
||||
private final Map<Integer, EnchantSupportItem> _supports = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new enchant item data.
|
||||
*/
|
||||
public EnchantItemData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_scrolls.clear();
|
||||
_supports.clear();
|
||||
parseDatapackFile("enchantItemData.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _scrolls.size() + " Enchant Scrolls.");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _supports.size() + " Support Items.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
StatsSet set;
|
||||
Node att;
|
||||
NamedNodeMap attrs;
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("enchant".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
attrs = d.getAttributes();
|
||||
set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
final EnchantScroll item = new EnchantScroll(set);
|
||||
for (Node cd = d.getFirstChild(); cd != null; cd = cd.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(cd.getNodeName()))
|
||||
{
|
||||
item.addItem(parseInteger(cd.getAttributes(), "id"));
|
||||
}
|
||||
}
|
||||
_scrolls.put(item.getId(), item);
|
||||
}
|
||||
catch (NullPointerException e)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, getClass().getSimpleName() + ": Unexistent enchant scroll: " + set.getString("id") + " defined in enchant data!");
|
||||
}
|
||||
catch (IllegalAccessError e)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, getClass().getSimpleName() + ": Wrong enchant scroll item type: " + set.getString("id") + " defined in enchant data!");
|
||||
}
|
||||
}
|
||||
else if ("support".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
attrs = d.getAttributes();
|
||||
set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
|
||||
try
|
||||
{
|
||||
final EnchantSupportItem item = new EnchantSupportItem(set);
|
||||
_supports.put(item.getId(), item);
|
||||
}
|
||||
catch (NullPointerException e)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, getClass().getSimpleName() + ": Unexistent enchant support item: " + set.getString("id") + " defined in enchant data!");
|
||||
}
|
||||
catch (IllegalAccessError e)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, getClass().getSimpleName() + ": Wrong enchant support item type: " + set.getString("id") + " defined in enchant data!");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the enchant scroll.
|
||||
* @param scroll the scroll
|
||||
* @return enchant template for scroll
|
||||
*/
|
||||
public final EnchantScroll getEnchantScroll(L2ItemInstance scroll)
|
||||
{
|
||||
return _scrolls.get(scroll.getId());
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the support item.
|
||||
* @param item the item
|
||||
* @return enchant template for support item
|
||||
*/
|
||||
public final EnchantSupportItem getSupportItem(L2ItemInstance item)
|
||||
{
|
||||
return _supports.get(item.getId());
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of EnchantItemData.
|
||||
* @return single instance of EnchantItemData
|
||||
*/
|
||||
public static final EnchantItemData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final EnchantItemData _instance = new EnchantItemData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,166 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.datatables.ItemTable;
|
||||
import com.l2jmobius.gameserver.model.holders.RangeChanceHolder;
|
||||
import com.l2jmobius.gameserver.model.items.L2Item;
|
||||
import com.l2jmobius.gameserver.model.items.enchant.EnchantItemGroup;
|
||||
import com.l2jmobius.gameserver.model.items.enchant.EnchantRateItem;
|
||||
import com.l2jmobius.gameserver.model.items.enchant.EnchantScrollGroup;
|
||||
import com.l2jmobius.gameserver.util.Util;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public final class EnchantItemGroupsData implements IXmlReader
|
||||
{
|
||||
private final Map<String, EnchantItemGroup> _itemGroups = new HashMap<>();
|
||||
private final Map<Integer, EnchantScrollGroup> _scrollGroups = new HashMap<>();
|
||||
|
||||
protected EnchantItemGroupsData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_itemGroups.clear();
|
||||
_scrollGroups.clear();
|
||||
parseDatapackFile("enchantItemGroups.xml");
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _itemGroups.size() + " item group templates.");
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _scrollGroups.size() + " scroll group templates.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("enchantRateGroup".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final String name = parseString(d.getAttributes(), "name");
|
||||
final EnchantItemGroup group = new EnchantItemGroup(name);
|
||||
for (Node cd = d.getFirstChild(); cd != null; cd = cd.getNextSibling())
|
||||
{
|
||||
if ("current".equalsIgnoreCase(cd.getNodeName()))
|
||||
{
|
||||
final String range = parseString(cd.getAttributes(), "enchant");
|
||||
final double chance = parseDouble(cd.getAttributes(), "chance");
|
||||
int min = -1;
|
||||
int max = 0;
|
||||
if (range.contains("-"))
|
||||
{
|
||||
final String[] split = range.split("-");
|
||||
if ((split.length == 2) && Util.isDigit(split[0]) && Util.isDigit(split[1]))
|
||||
{
|
||||
min = Integer.parseInt(split[0]);
|
||||
max = Integer.parseInt(split[1]);
|
||||
}
|
||||
}
|
||||
else if (Util.isDigit(range))
|
||||
{
|
||||
min = Integer.parseInt(range);
|
||||
max = min;
|
||||
}
|
||||
if ((min > -1) && (max > 0))
|
||||
{
|
||||
group.addChance(new RangeChanceHolder(min, max, chance));
|
||||
}
|
||||
}
|
||||
}
|
||||
_itemGroups.put(name, group);
|
||||
}
|
||||
else if ("enchantScrollGroup".equals(d.getNodeName()))
|
||||
{
|
||||
final int id = parseInteger(d.getAttributes(), "id");
|
||||
final EnchantScrollGroup group = new EnchantScrollGroup(id);
|
||||
for (Node cd = d.getFirstChild(); cd != null; cd = cd.getNextSibling())
|
||||
{
|
||||
if ("enchantRate".equalsIgnoreCase(cd.getNodeName()))
|
||||
{
|
||||
final EnchantRateItem rateGroup = new EnchantRateItem(parseString(cd.getAttributes(), "group"));
|
||||
for (Node z = cd.getFirstChild(); z != null; z = z.getNextSibling())
|
||||
{
|
||||
if ("item".equals(z.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = z.getAttributes();
|
||||
if (attrs.getNamedItem("slot") != null)
|
||||
{
|
||||
rateGroup.addSlot(ItemTable.SLOTS.get(parseString(attrs, "slot")));
|
||||
}
|
||||
if (attrs.getNamedItem("magicWeapon") != null)
|
||||
{
|
||||
rateGroup.setMagicWeapon(parseBoolean(attrs, "magicWeapon"));
|
||||
}
|
||||
if (attrs.getNamedItem("id") != null)
|
||||
{
|
||||
rateGroup.setItemId(parseInteger(attrs, "id"));
|
||||
}
|
||||
}
|
||||
}
|
||||
group.addRateGroup(rateGroup);
|
||||
}
|
||||
}
|
||||
_scrollGroups.put(id, group);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public EnchantItemGroup getItemGroup(L2Item item, int scrollGroup)
|
||||
{
|
||||
final EnchantScrollGroup group = _scrollGroups.get(scrollGroup);
|
||||
final EnchantRateItem rateGroup = group.getRateGroup(item);
|
||||
return rateGroup != null ? _itemGroups.get(rateGroup.getName()) : null;
|
||||
}
|
||||
|
||||
public EnchantItemGroup getItemGroup(String name)
|
||||
{
|
||||
return _itemGroups.get(name);
|
||||
}
|
||||
|
||||
public EnchantScrollGroup getScrollGroup(int id)
|
||||
{
|
||||
return _scrollGroups.get(id);
|
||||
}
|
||||
|
||||
public static EnchantItemGroupsData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final EnchantItemGroupsData _instance = new EnchantItemGroupsData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,158 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.EnumMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.datatables.ItemTable;
|
||||
import com.l2jmobius.gameserver.enums.StatFunction;
|
||||
import com.l2jmobius.gameserver.model.items.L2Item;
|
||||
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
|
||||
import com.l2jmobius.gameserver.model.items.type.CrystalType;
|
||||
import com.l2jmobius.gameserver.model.stats.Stats;
|
||||
import com.l2jmobius.gameserver.model.stats.functions.FuncTemplate;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Enchant HP Bonus Data.
|
||||
* @author MrPoke, Zoey76
|
||||
*/
|
||||
public class EnchantItemHPBonusData implements IXmlReader
|
||||
{
|
||||
private final Map<CrystalType, List<Integer>> _armorHPBonuses = new EnumMap<>(CrystalType.class);
|
||||
|
||||
private static final float FULL_ARMOR_MODIFIER = 1.5f; // TODO: Move it to config!
|
||||
|
||||
/**
|
||||
* Instantiates a new enchant hp bonus data.
|
||||
*/
|
||||
protected EnchantItemHPBonusData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_armorHPBonuses.clear();
|
||||
parseDatapackFile("stats/enchantHPBonus.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _armorHPBonuses.size() + " Enchant HP Bonuses.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("enchantHP".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final List<Integer> bonuses = new ArrayList<>(12);
|
||||
for (Node e = d.getFirstChild(); e != null; e = e.getNextSibling())
|
||||
{
|
||||
if ("bonus".equalsIgnoreCase(e.getNodeName()))
|
||||
{
|
||||
bonuses.add(Integer.parseInt(e.getTextContent()));
|
||||
}
|
||||
}
|
||||
_armorHPBonuses.put(parseEnum(d.getAttributes(), CrystalType.class, "grade"), bonuses);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!_armorHPBonuses.isEmpty())
|
||||
{
|
||||
final ItemTable it = ItemTable.getInstance();
|
||||
// Armors
|
||||
final Collection<Integer> armorIds = it.getAllArmorsId();
|
||||
for (Integer itemId : armorIds)
|
||||
{
|
||||
final L2Item item = it.getTemplate(itemId);
|
||||
if ((item != null) && (item.getCrystalType() != CrystalType.NONE))
|
||||
{
|
||||
switch (item.getBodyPart())
|
||||
{
|
||||
case L2Item.SLOT_CHEST:
|
||||
case L2Item.SLOT_FEET:
|
||||
case L2Item.SLOT_GLOVES:
|
||||
case L2Item.SLOT_HEAD:
|
||||
case L2Item.SLOT_LEGS:
|
||||
case L2Item.SLOT_BACK:
|
||||
case L2Item.SLOT_FULL_ARMOR:
|
||||
case L2Item.SLOT_UNDERWEAR:
|
||||
case L2Item.SLOT_L_HAND:
|
||||
case L2Item.SLOT_BELT:
|
||||
{
|
||||
item.attach(new FuncTemplate(null, null, StatFunction.ENCHANTHP.getName(), -1, Stats.MAX_HP, 0));
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the HP bonus.
|
||||
* @param item the item
|
||||
* @return the HP bonus
|
||||
*/
|
||||
public final int getHPBonus(L2ItemInstance item)
|
||||
{
|
||||
final List<Integer> values = _armorHPBonuses.get(item.getItem().getCrystalTypePlus());
|
||||
if ((values == null) || values.isEmpty() || (item.getOlyEnchantLevel() <= 0))
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
final int bonus = values.get(Math.min(item.getOlyEnchantLevel(), values.size()) - 1);
|
||||
if (item.getItem().getBodyPart() == L2Item.SLOT_FULL_ARMOR)
|
||||
{
|
||||
return (int) (bonus * FULL_ARMOR_MODIFIER);
|
||||
}
|
||||
return bonus;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of EnchantHPBonusData.
|
||||
* @return single instance of EnchantHPBonusData
|
||||
*/
|
||||
public static final EnchantItemHPBonusData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final EnchantItemHPBonusData _instance = new EnchantItemHPBonusData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,128 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
|
||||
import com.l2jmobius.gameserver.model.options.EnchantOptions;
|
||||
import com.l2jmobius.gameserver.util.Util;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public class EnchantItemOptionsData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, Map<Integer, EnchantOptions>> _data = new HashMap<>();
|
||||
|
||||
protected EnchantItemOptionsData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_data.clear();
|
||||
parseDatapackFile("enchantItemOptions.xml");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
int counter = 0;
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final int itemId = parseInteger(d.getAttributes(), "id");
|
||||
if (!_data.containsKey(itemId))
|
||||
{
|
||||
_data.put(itemId, new HashMap<Integer, EnchantOptions>());
|
||||
}
|
||||
for (Node cd = d.getFirstChild(); cd != null; cd = cd.getNextSibling())
|
||||
{
|
||||
if ("options".equalsIgnoreCase(cd.getNodeName()))
|
||||
{
|
||||
final EnchantOptions op = new EnchantOptions(parseInteger(cd.getAttributes(), "level"));
|
||||
_data.get(itemId).put(op.getLevel(), op);
|
||||
|
||||
for (byte i = 0; i < 3; i++)
|
||||
{
|
||||
final Node att = cd.getAttributes().getNamedItem("option" + (i + 1));
|
||||
if ((att != null) && Util.isDigit(att.getNodeValue()))
|
||||
{
|
||||
op.setOption(i, parseInteger(att));
|
||||
}
|
||||
}
|
||||
counter++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _data.size() + " Items and " + counter + " Options.");
|
||||
}
|
||||
|
||||
/**
|
||||
* @param itemId
|
||||
* @param enchantLevel
|
||||
* @return enchant effects information.
|
||||
*/
|
||||
public EnchantOptions getOptions(int itemId, int enchantLevel)
|
||||
{
|
||||
if (!_data.containsKey(itemId) || !_data.get(itemId).containsKey(enchantLevel))
|
||||
{
|
||||
return null;
|
||||
}
|
||||
return _data.get(itemId).get(enchantLevel);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param item
|
||||
* @return enchant effects information.
|
||||
*/
|
||||
public EnchantOptions getOptions(L2ItemInstance item)
|
||||
{
|
||||
return item != null ? getOptions(item.getId(), item.getEnchantLevel()) : null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of EnchantOptionsData.
|
||||
* @return single instance of EnchantOptionsData
|
||||
*/
|
||||
public static final EnchantItemOptionsData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final EnchantItemOptionsData _instance = new EnchantItemOptionsData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,262 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.gameserver.model.L2EnchantSkillGroup;
|
||||
import com.l2jmobius.gameserver.model.L2EnchantSkillGroup.EnchantSkillHolder;
|
||||
import com.l2jmobius.gameserver.model.L2EnchantSkillLearn;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
|
||||
import com.l2jmobius.gameserver.model.skills.Skill;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Enchant Groups information.
|
||||
* @author Micr0
|
||||
*/
|
||||
public class EnchantSkillGroupsData implements IXmlReader
|
||||
{
|
||||
public static final int NORMAL_ENCHANT_COST_MULTIPLIER = Config.NORMAL_ENCHANT_COST_MULTIPLIER;
|
||||
public static final int SAFE_ENCHANT_COST_MULTIPLIER = Config.SAFE_ENCHANT_COST_MULTIPLIER;
|
||||
|
||||
public static final int NORMAL_ENCHANT_BOOK_OLD = 6622;
|
||||
public static final int SAFE_ENCHANT_BOOK_OLD = 9627;
|
||||
public static final int CHANGE_ENCHANT_BOOK_OLD = 9626;
|
||||
public static final int UNTRAIN_ENCHANT_BOOK_OLD = 9625;
|
||||
public static final int NORMAL_ENCHANT_BOOK = 30297;
|
||||
public static final int SAFE_ENCHANT_BOOK = 30298;
|
||||
public static final int CHANGE_ENCHANT_BOOK = 30299;
|
||||
public static final int UNTRAIN_ENCHANT_BOOK = 30300;
|
||||
public static final int IMMORTAL_SCROLL = 37044;
|
||||
public static final int NORMAL_ENCHANT_BOOK_V2 = 46150;
|
||||
public static final int SAFE_ENCHANT_BOOK_V2 = 46151;
|
||||
public static final int CHANGE_ENCHANT_BOOK_V2 = 46152;
|
||||
public static final int IMMORTAL_SCROLL_V2 = 46153;
|
||||
public static final int NORMAL_ENCHANT_BOOK_V3 = 46154;
|
||||
public static final int SAFE_ENCHANT_BOOK_V3 = 46155;
|
||||
public static final int CHANGE_ENCHANT_BOOK_V3 = 46156;
|
||||
public static final int IMMORTAL_SCROLL_V3 = 46157;
|
||||
|
||||
private final Map<Integer, L2EnchantSkillGroup> _enchantSkillGroups = new HashMap<>();
|
||||
private final Map<Integer, L2EnchantSkillLearn> _enchantSkillTrees = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new enchant groups table.
|
||||
*/
|
||||
protected EnchantSkillGroupsData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_enchantSkillGroups.clear();
|
||||
_enchantSkillTrees.clear();
|
||||
parseDatapackFile("enchantSkillGroups.xml");
|
||||
int routes = 0;
|
||||
for (L2EnchantSkillGroup group : _enchantSkillGroups.values())
|
||||
{
|
||||
routes += group.getEnchantGroupDetails().size();
|
||||
}
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _enchantSkillGroups.size() + " groups and " + routes + " routes.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("group".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
NamedNodeMap attrs = d.getAttributes();
|
||||
final int id = parseInteger(attrs, "id");
|
||||
L2EnchantSkillGroup group = _enchantSkillGroups.get(id);
|
||||
if (group == null)
|
||||
{
|
||||
group = new L2EnchantSkillGroup(id);
|
||||
_enchantSkillGroups.put(id, group);
|
||||
}
|
||||
|
||||
for (Node b = d.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("enchant".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
attrs = b.getAttributes();
|
||||
final StatsSet set = new StatsSet();
|
||||
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
group.addEnchantDetail(new EnchantSkillHolder(set));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds the new route for skill.
|
||||
* @param skillId the skill id
|
||||
* @param maxLvL the max lvl
|
||||
* @param route the route
|
||||
* @param group the group
|
||||
* @return the int
|
||||
*/
|
||||
public int addNewRouteForSkill(int skillId, int maxLvL, int route, int group)
|
||||
{
|
||||
L2EnchantSkillLearn enchantableSkill = _enchantSkillTrees.get(skillId);
|
||||
if (enchantableSkill == null)
|
||||
{
|
||||
enchantableSkill = new L2EnchantSkillLearn(skillId, maxLvL);
|
||||
_enchantSkillTrees.put(skillId, enchantableSkill);
|
||||
}
|
||||
if (_enchantSkillGroups.containsKey(group))
|
||||
{
|
||||
enchantableSkill.addNewEnchantRoute(route, group);
|
||||
|
||||
return _enchantSkillGroups.get(group).getEnchantGroupDetails().size();
|
||||
}
|
||||
LOGGER.log(Level.SEVERE, getClass().getSimpleName() + ": Error while loading generating enchant skill id: " + skillId + "; route: " + route + "; missing group: " + group);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the skill enchantment for skill.
|
||||
* @param skill the skill
|
||||
* @return the skill enchantment for skill
|
||||
*/
|
||||
public L2EnchantSkillLearn getSkillEnchantmentForSkill(Skill skill)
|
||||
{
|
||||
// there is enchantment for this skill and we have the required level of it
|
||||
final L2EnchantSkillLearn esl = getSkillEnchantmentBySkillId(skill.getId());
|
||||
if ((esl != null) && (skill.getLevel() >= esl.getBaseLevel()))
|
||||
{
|
||||
return esl;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the skill enchantment by skill id.
|
||||
* @param skillId the skill id
|
||||
* @return the skill enchantment by skill id
|
||||
*/
|
||||
public L2EnchantSkillLearn getSkillEnchantmentBySkillId(int skillId)
|
||||
{
|
||||
return _enchantSkillTrees.get(skillId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the enchant skill group by id.
|
||||
* @param id the id
|
||||
* @return the enchant skill group by id
|
||||
*/
|
||||
public L2EnchantSkillGroup getEnchantSkillGroupById(int id)
|
||||
{
|
||||
return _enchantSkillGroups.get(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the enchant skill sp cost.
|
||||
* @param skill the skill
|
||||
* @return the enchant skill sp cost
|
||||
*/
|
||||
public int getEnchantSkillSpCost(Skill skill)
|
||||
{
|
||||
final L2EnchantSkillLearn enchantSkillLearn = _enchantSkillTrees.get(skill.getId());
|
||||
if (enchantSkillLearn != null)
|
||||
{
|
||||
final EnchantSkillHolder esh = enchantSkillLearn.getEnchantSkillHolder(skill.getLevel());
|
||||
if (esh != null)
|
||||
{
|
||||
return esh.getSpCost();
|
||||
}
|
||||
}
|
||||
return Integer.MAX_VALUE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the enchant skill Adena cost.
|
||||
* @param skill the skill
|
||||
* @return the enchant skill Adena cost
|
||||
*/
|
||||
public int getEnchantSkillAdenaCost(Skill skill)
|
||||
{
|
||||
final L2EnchantSkillLearn enchantSkillLearn = _enchantSkillTrees.get(skill.getId());
|
||||
if (enchantSkillLearn != null)
|
||||
{
|
||||
final EnchantSkillHolder esh = enchantSkillLearn.getEnchantSkillHolder(skill.getLevel());
|
||||
if (esh != null)
|
||||
{
|
||||
return esh.getAdenaCost();
|
||||
}
|
||||
}
|
||||
return Integer.MAX_VALUE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the enchant skill rate.
|
||||
* @param player the player
|
||||
* @param skill the skill
|
||||
* @return the enchant skill rate
|
||||
*/
|
||||
public byte getEnchantSkillRate(L2PcInstance player, Skill skill)
|
||||
{
|
||||
final L2EnchantSkillLearn enchantSkillLearn = _enchantSkillTrees.get(skill.getId());
|
||||
if (enchantSkillLearn != null)
|
||||
{
|
||||
final EnchantSkillHolder esh = enchantSkillLearn.getEnchantSkillHolder(skill.getLevel());
|
||||
if (esh != null)
|
||||
{
|
||||
return esh.getRate(player);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of EnchantGroupsData.
|
||||
* @return single instance of EnchantGroupsData
|
||||
*/
|
||||
public static EnchantSkillGroupsData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final EnchantSkillGroupsData _instance = new EnchantSkillGroupsData();
|
||||
}
|
||||
}
|
@@ -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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Experience points for each level for players and pets.
|
||||
* @author mrTJO
|
||||
*/
|
||||
public final class ExperienceData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, Long> _expTable = new HashMap<>();
|
||||
|
||||
private byte MAX_LEVEL;
|
||||
private byte MAX_PET_LEVEL;
|
||||
|
||||
/**
|
||||
* Instantiates a new experience table.
|
||||
*/
|
||||
protected ExperienceData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_expTable.clear();
|
||||
parseDatapackFile("stats/experience.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + (_expTable.size() - 1) + " levels.");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Max Player Level is: " + (MAX_LEVEL - 1));
|
||||
LOGGER.info(getClass().getSimpleName() + ": Max Pet Level is: " + (MAX_PET_LEVEL - 1));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
final Node table = doc.getFirstChild();
|
||||
final NamedNodeMap tableAttr = table.getAttributes();
|
||||
|
||||
MAX_LEVEL = (byte) (Byte.parseByte(tableAttr.getNamedItem("maxLevel").getNodeValue()) + 1);
|
||||
MAX_PET_LEVEL = (byte) (Byte.parseByte(tableAttr.getNamedItem("maxPetLevel").getNodeValue()) + 1);
|
||||
|
||||
if (MAX_LEVEL > Config.PLAYER_MAXIMUM_LEVEL)
|
||||
{
|
||||
MAX_LEVEL = Config.PLAYER_MAXIMUM_LEVEL;
|
||||
}
|
||||
if (MAX_PET_LEVEL > MAX_LEVEL)
|
||||
{
|
||||
MAX_PET_LEVEL = MAX_LEVEL; // Pet level should not exceed owner level.
|
||||
}
|
||||
|
||||
int maxLevel = 0;
|
||||
for (Node n = table.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("experience".equals(n.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = n.getAttributes();
|
||||
maxLevel = parseInteger(attrs, "level");
|
||||
if (maxLevel > Config.PLAYER_MAXIMUM_LEVEL)
|
||||
{
|
||||
break;
|
||||
}
|
||||
_expTable.put(maxLevel, parseLong(attrs, "tolevel"));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the exp for level.
|
||||
* @param level the level required.
|
||||
* @return the experience points required to reach the given level.
|
||||
*/
|
||||
public long getExpForLevel(int level)
|
||||
{
|
||||
if (level > Config.PLAYER_MAXIMUM_LEVEL)
|
||||
{
|
||||
level = Config.PLAYER_MAXIMUM_LEVEL;
|
||||
}
|
||||
return _expTable.get(level);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the max level.
|
||||
* @return the maximum level acquirable by a player.
|
||||
*/
|
||||
public byte getMaxLevel()
|
||||
{
|
||||
return MAX_LEVEL;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the max pet level.
|
||||
* @return the maximum level acquirable by a pet.
|
||||
*/
|
||||
public byte getMaxPetLevel()
|
||||
{
|
||||
return MAX_PET_LEVEL;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of ExperienceTable.
|
||||
* @return single instance of ExperienceTable
|
||||
*/
|
||||
public static ExperienceData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final ExperienceData _instance = new ExperienceData();
|
||||
}
|
||||
}
|
169
trunk/java/com/l2jmobius/gameserver/data/xml/impl/FishData.java
Normal file
169
trunk/java/com/l2jmobius/gameserver/data/xml/impl/FishData.java
Normal file
@@ -0,0 +1,169 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.fishing.L2Fish;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Fish information.
|
||||
* @author nonom
|
||||
*/
|
||||
public final class FishData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2Fish> _fishNormal = new HashMap<>();
|
||||
private final Map<Integer, L2Fish> _fishEasy = new HashMap<>();
|
||||
private final Map<Integer, L2Fish> _fishHard = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new fish data.
|
||||
*/
|
||||
protected FishData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_fishEasy.clear();
|
||||
_fishNormal.clear();
|
||||
_fishHard.clear();
|
||||
parseDatapackFile("stats/fishing/fishes.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + (_fishEasy.size() + _fishNormal.size() + _fishHard.size()) + " Fishes.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("fish".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
|
||||
final StatsSet set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
|
||||
final L2Fish fish = new L2Fish(set);
|
||||
switch (fish.getFishGrade())
|
||||
{
|
||||
case 0:
|
||||
{
|
||||
_fishEasy.put(fish.getFishId(), fish);
|
||||
break;
|
||||
}
|
||||
case 1:
|
||||
{
|
||||
_fishNormal.put(fish.getFishId(), fish);
|
||||
break;
|
||||
}
|
||||
case 2:
|
||||
{
|
||||
_fishHard.put(fish.getFishId(), fish);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the fish.
|
||||
* @param level the fish Level
|
||||
* @param group the fish Group
|
||||
* @param grade the fish Grade
|
||||
* @return List of Fish that can be fished
|
||||
*/
|
||||
public List<L2Fish> getFish(int level, int group, int grade)
|
||||
{
|
||||
final ArrayList<L2Fish> result = new ArrayList<>();
|
||||
Map<Integer, L2Fish> fish = null;
|
||||
switch (grade)
|
||||
{
|
||||
case 0:
|
||||
{
|
||||
fish = _fishEasy;
|
||||
break;
|
||||
}
|
||||
case 1:
|
||||
{
|
||||
fish = _fishNormal;
|
||||
break;
|
||||
}
|
||||
case 2:
|
||||
{
|
||||
fish = _fishHard;
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
LOGGER.warning(getClass().getSimpleName() + ": Unmanaged fish grade!");
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
for (L2Fish f : fish.values())
|
||||
{
|
||||
if ((f.getFishLevel() != level) || (f.getFishGroup() != group))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
result.add(f);
|
||||
}
|
||||
|
||||
if (result.isEmpty())
|
||||
{
|
||||
LOGGER.warning(getClass().getSimpleName() + ": Cannot find any fish for level: " + level + " group: " + group + " and grade: " + grade + "!");
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of FishData.
|
||||
* @return single instance of FishData
|
||||
*/
|
||||
public static FishData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final FishData _instance = new FishData();
|
||||
}
|
||||
}
|
@@ -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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.fishing.L2FishingMonster;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Fishing Monsters information.
|
||||
* @author nonom
|
||||
*/
|
||||
public final class FishingMonstersData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2FishingMonster> _fishingMonstersData = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new fishing monsters data.
|
||||
*/
|
||||
protected FishingMonstersData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_fishingMonstersData.clear();
|
||||
parseDatapackFile("stats/fishing/fishingMonsters.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _fishingMonstersData.size() + " Fishing Monsters.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("fishingMonster".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
final StatsSet set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
|
||||
final L2FishingMonster fishingMonster = new L2FishingMonster(set);
|
||||
_fishingMonstersData.put(fishingMonster.getFishingMonsterId(), fishingMonster);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the fishing monster.
|
||||
* @param lvl the fisherman level
|
||||
* @return a fishing monster given the fisherman level
|
||||
*/
|
||||
public L2FishingMonster getFishingMonster(int lvl)
|
||||
{
|
||||
for (L2FishingMonster fishingMonster : _fishingMonstersData.values())
|
||||
{
|
||||
if ((lvl >= fishingMonster.getUserMinLevel()) && (lvl <= fishingMonster.getUserMaxLevel()))
|
||||
{
|
||||
return fishingMonster;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the fishing monster by Id.
|
||||
* @param id the fishing monster Id
|
||||
* @return the fishing monster by Id
|
||||
*/
|
||||
public L2FishingMonster getFishingMonsterById(int id)
|
||||
{
|
||||
if (_fishingMonstersData.containsKey(id))
|
||||
{
|
||||
return _fishingMonstersData.get(id);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of FishingMonsterData.
|
||||
* @return single instance of FishingMonsterData
|
||||
*/
|
||||
public static FishingMonstersData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final FishingMonstersData _instance = new FishingMonstersData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,104 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.fishing.L2FishingRod;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Fishing Rods information.
|
||||
* @author nonom
|
||||
*/
|
||||
public final class FishingRodsData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2FishingRod> _fishingRods = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new fishing rods data.
|
||||
*/
|
||||
protected FishingRodsData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_fishingRods.clear();
|
||||
parseDatapackFile("stats/fishing/fishingRods.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _fishingRods.size() + " Fishing Rods.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("fishingRod".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
final StatsSet set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
|
||||
final L2FishingRod fishingRod = new L2FishingRod(set);
|
||||
_fishingRods.put(fishingRod.getFishingRodItemId(), fishingRod);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the fishing rod.
|
||||
* @param itemId the item id
|
||||
* @return A fishing Rod by Item Id
|
||||
*/
|
||||
public L2FishingRod getFishingRod(int itemId)
|
||||
{
|
||||
return _fishingRods.get(itemId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of FishingRodsData.
|
||||
* @return single instance of FishingRodsData
|
||||
*/
|
||||
public static FishingRodsData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final FishingRodsData _instance = new FishingRodsData();
|
||||
}
|
||||
}
|
194
trunk/java/com/l2jmobius/gameserver/data/xml/impl/HennaData.java
Normal file
194
trunk/java/com/l2jmobius/gameserver/data/xml/impl/HennaData.java
Normal file
@@ -0,0 +1,194 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.base.ClassId;
|
||||
import com.l2jmobius.gameserver.model.holders.SkillHolder;
|
||||
import com.l2jmobius.gameserver.model.items.L2Henna;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the henna related information.<br>
|
||||
* Cost and required amount to add the henna to the player.<br>
|
||||
* Cost and retrieved amount for removing the henna from the player.<br>
|
||||
* Allowed classes to wear each henna.
|
||||
* @author Zoey76
|
||||
*/
|
||||
public final class HennaData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2Henna> _hennaList = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new henna data.
|
||||
*/
|
||||
protected HennaData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_hennaList.clear();
|
||||
parseDatapackFile("stats/hennaList.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _hennaList.size() + " Henna data.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equals(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("henna".equals(d.getNodeName()))
|
||||
{
|
||||
parseHenna(d);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses the henna.
|
||||
* @param d the d
|
||||
*/
|
||||
private void parseHenna(Node d)
|
||||
{
|
||||
final StatsSet set = new StatsSet();
|
||||
final List<ClassId> wearClassIds = new ArrayList<>();
|
||||
final List<SkillHolder> skills = new ArrayList<>();
|
||||
NamedNodeMap attrs = d.getAttributes();
|
||||
Node attr;
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
attr = attrs.item(i);
|
||||
set.set(attr.getNodeName(), attr.getNodeValue());
|
||||
}
|
||||
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
final String name = c.getNodeName();
|
||||
attrs = c.getAttributes();
|
||||
switch (name)
|
||||
{
|
||||
case "stats":
|
||||
{
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
attr = attrs.item(i);
|
||||
set.set(attr.getNodeName(), attr.getNodeValue());
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "wear":
|
||||
{
|
||||
attr = attrs.getNamedItem("count");
|
||||
set.set("wear_count", attr.getNodeValue());
|
||||
attr = attrs.getNamedItem("fee");
|
||||
set.set("wear_fee", attr.getNodeValue());
|
||||
break;
|
||||
}
|
||||
case "cancel":
|
||||
{
|
||||
attr = attrs.getNamedItem("count");
|
||||
set.set("cancel_count", attr.getNodeValue());
|
||||
attr = attrs.getNamedItem("fee");
|
||||
set.set("cancel_fee", attr.getNodeValue());
|
||||
break;
|
||||
}
|
||||
case "skills":
|
||||
{
|
||||
for (Node i = c.getFirstChild(); i != null; i = i.getNextSibling())
|
||||
{
|
||||
if ("skill".equals(i.getNodeName()))
|
||||
{
|
||||
final int skillId = Integer.parseInt(i.getAttributes().getNamedItem("id").getNodeValue());
|
||||
final int skillLevel = Integer.parseInt(i.getAttributes().getNamedItem("level").getNodeValue());
|
||||
skills.add(new SkillHolder(skillId, skillLevel));
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "classId":
|
||||
{
|
||||
wearClassIds.add(ClassId.getClassId(Integer.parseInt(c.getTextContent())));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
final L2Henna henna = new L2Henna(set);
|
||||
henna.setWearClassIds(wearClassIds);
|
||||
henna.setSkills(skills);
|
||||
_hennaList.put(henna.getDyeId(), henna);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the henna.
|
||||
* @param id of the dye.
|
||||
* @return the dye with that id.
|
||||
*/
|
||||
public L2Henna getHenna(int id)
|
||||
{
|
||||
return _hennaList.get(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the henna list.
|
||||
* @param classId the player's class Id.
|
||||
* @return the list with all the allowed dyes.
|
||||
*/
|
||||
public List<L2Henna> getHennaList(ClassId classId)
|
||||
{
|
||||
final List<L2Henna> list = new ArrayList<>();
|
||||
for (L2Henna henna : _hennaList.values())
|
||||
{
|
||||
if (henna.isAllowedClass(classId))
|
||||
{
|
||||
list.add(henna);
|
||||
}
|
||||
}
|
||||
return list;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of HennaData.
|
||||
* @return single instance of HennaData
|
||||
*/
|
||||
public static HennaData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final HennaData _instance = new HennaData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,172 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.gameserver.GameTimeController;
|
||||
import com.l2jmobius.gameserver.model.actor.L2Character;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class load, holds and calculates the hit condition bonuses.
|
||||
* @author Nik
|
||||
*/
|
||||
public final class HitConditionBonusData implements IXmlReader
|
||||
{
|
||||
private int frontBonus = 0;
|
||||
private int sideBonus = 0;
|
||||
private int backBonus = 0;
|
||||
private int highBonus = 0;
|
||||
private int lowBonus = 0;
|
||||
private int darkBonus = 0;
|
||||
private int rainBonus = 0;
|
||||
|
||||
/**
|
||||
* Instantiates a new hit condition bonus.
|
||||
*/
|
||||
protected HitConditionBonusData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
parseDatapackFile("stats/hitConditionBonus.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded Hit Condition bonuses.");
|
||||
if (Config.DEBUG)
|
||||
{
|
||||
LOGGER.info(getClass().getSimpleName() + ": Front bonus: " + frontBonus);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Side bonus: " + sideBonus);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Back bonus: " + backBonus);
|
||||
LOGGER.info(getClass().getSimpleName() + ": High bonus: " + highBonus);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Low bonus: " + lowBonus);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Dark bonus: " + darkBonus);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Rain bonus: " + rainBonus);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node d = doc.getFirstChild().getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
switch (d.getNodeName())
|
||||
{
|
||||
case "front":
|
||||
{
|
||||
frontBonus = parseInteger(attrs, "val");
|
||||
break;
|
||||
}
|
||||
case "side":
|
||||
{
|
||||
sideBonus = parseInteger(attrs, "val");
|
||||
break;
|
||||
}
|
||||
case "back":
|
||||
{
|
||||
backBonus = parseInteger(attrs, "val");
|
||||
break;
|
||||
}
|
||||
case "high":
|
||||
{
|
||||
highBonus = parseInteger(attrs, "val");
|
||||
break;
|
||||
}
|
||||
case "low":
|
||||
{
|
||||
lowBonus = parseInteger(attrs, "val");
|
||||
break;
|
||||
}
|
||||
case "dark":
|
||||
{
|
||||
darkBonus = parseInteger(attrs, "val");
|
||||
break;
|
||||
}
|
||||
case "rain":
|
||||
{
|
||||
rainBonus = parseInteger(attrs, "val");
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the condition bonus.
|
||||
* @param attacker the attacking character.
|
||||
* @param target the attacked character.
|
||||
* @return the bonus of the attacker against the target.
|
||||
*/
|
||||
public double getConditionBonus(L2Character attacker, L2Character target)
|
||||
{
|
||||
double mod = 100;
|
||||
// Get high or low bonus
|
||||
if ((attacker.getZ() - target.getZ()) > 50)
|
||||
{
|
||||
mod += highBonus;
|
||||
}
|
||||
else if ((attacker.getZ() - target.getZ()) < -50)
|
||||
{
|
||||
mod += lowBonus;
|
||||
}
|
||||
|
||||
// Get weather bonus
|
||||
if (GameTimeController.getInstance().isNight())
|
||||
{
|
||||
mod += darkBonus;
|
||||
// else if () No rain support yet.
|
||||
// chance += hitConditionBonus.rainBonus;
|
||||
}
|
||||
|
||||
// Get side bonus
|
||||
if (attacker.isBehindTarget())
|
||||
{
|
||||
mod += backBonus;
|
||||
}
|
||||
else if (attacker.isInFrontOfTarget())
|
||||
{
|
||||
mod += frontBonus;
|
||||
}
|
||||
else
|
||||
{
|
||||
mod += sideBonus;
|
||||
}
|
||||
|
||||
// If (mod / 100) is less than 0, return 0, because we can't lower more than 100%.
|
||||
return Math.max(mod / 100, 0);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of HitConditionBonus.
|
||||
* @return single instance of HitConditionBonus
|
||||
*/
|
||||
public static HitConditionBonusData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final HitConditionBonusData _instance = new HitConditionBonusData();
|
||||
}
|
||||
}
|
@@ -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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.base.ClassId;
|
||||
import com.l2jmobius.gameserver.model.items.PcItemTemplate;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Initial Equipment information.<br>
|
||||
* What items get each newly created character and if this item is equipped upon creation (<b>Requires the item to be equippable</b>).
|
||||
* @author Zoey76
|
||||
*/
|
||||
public final class InitialEquipmentData implements IXmlReader
|
||||
{
|
||||
private final Map<ClassId, List<PcItemTemplate>> _initialEquipmentList = new HashMap<>();
|
||||
private static final String NORMAL = "stats/initialEquipment.xml";
|
||||
private static final String EVENT = "stats/initialEquipmentEvent.xml";
|
||||
|
||||
/**
|
||||
* Instantiates a new initial equipment data.
|
||||
*/
|
||||
protected InitialEquipmentData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_initialEquipmentList.clear();
|
||||
parseDatapackFile(Config.INITIAL_EQUIPMENT_EVENT ? EVENT : NORMAL);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _initialEquipmentList.size() + " Initial Equipment data.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("equipment".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
parseEquipment(d);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses the equipment.
|
||||
* @param d parse an initial equipment and add it to {@link #_initialEquipmentList}
|
||||
*/
|
||||
private void parseEquipment(Node d)
|
||||
{
|
||||
NamedNodeMap attrs = d.getAttributes();
|
||||
final ClassId classId = ClassId.getClassId(Integer.parseInt(attrs.getNamedItem("classId").getNodeValue()));
|
||||
final List<PcItemTemplate> equipList = new ArrayList<>();
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
final StatsSet set = new StatsSet();
|
||||
attrs = c.getAttributes();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node attr = attrs.item(i);
|
||||
set.set(attr.getNodeName(), attr.getNodeValue());
|
||||
}
|
||||
equipList.add(new PcItemTemplate(set));
|
||||
}
|
||||
}
|
||||
_initialEquipmentList.put(classId, equipList);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the equipment list.
|
||||
* @param cId the class Id for the required initial equipment.
|
||||
* @return the initial equipment for the given class Id.
|
||||
*/
|
||||
public List<PcItemTemplate> getEquipmentList(ClassId cId)
|
||||
{
|
||||
return _initialEquipmentList.get(cId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the equipment list.
|
||||
* @param cId the class Id for the required initial equipment.
|
||||
* @return the initial equipment for the given class Id.
|
||||
*/
|
||||
public List<PcItemTemplate> getEquipmentList(int cId)
|
||||
{
|
||||
return _initialEquipmentList.get(ClassId.getClassId(cId));
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of InitialEquipmentData.
|
||||
* @return single instance of InitialEquipmentData
|
||||
*/
|
||||
public static InitialEquipmentData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final InitialEquipmentData _instance = new InitialEquipmentData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,367 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.enums.MacroType;
|
||||
import com.l2jmobius.gameserver.enums.ShortcutType;
|
||||
import com.l2jmobius.gameserver.model.Macro;
|
||||
import com.l2jmobius.gameserver.model.MacroCmd;
|
||||
import com.l2jmobius.gameserver.model.Shortcut;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
|
||||
import com.l2jmobius.gameserver.model.base.ClassId;
|
||||
import com.l2jmobius.gameserver.model.items.instance.L2ItemInstance;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.ShortCutRegister;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Initial Shortcuts information.<br>
|
||||
* What shortcuts get each newly created character.
|
||||
* @author Zoey76
|
||||
*/
|
||||
public final class InitialShortcutData implements IXmlReader
|
||||
{
|
||||
private final Map<ClassId, List<Shortcut>> _initialShortcutData = new HashMap<>();
|
||||
private final List<Shortcut> _initialGlobalShortcutList = new ArrayList<>();
|
||||
private final Map<Integer, Macro> _macroPresets = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new initial shortcuts data.
|
||||
*/
|
||||
protected InitialShortcutData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_initialShortcutData.clear();
|
||||
_initialGlobalShortcutList.clear();
|
||||
|
||||
parseDatapackFile("stats/initialShortcuts.xml");
|
||||
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _initialGlobalShortcutList.size() + " Initial Global Shortcuts data.");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _initialShortcutData.size() + " Initial Shortcuts data.");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _macroPresets.size() + " Macros presets.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equals(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
switch (d.getNodeName())
|
||||
{
|
||||
case "shortcuts":
|
||||
{
|
||||
parseShortcuts(d);
|
||||
break;
|
||||
}
|
||||
case "macros":
|
||||
{
|
||||
parseMacros(d);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses a shortcut.
|
||||
* @param d the node
|
||||
*/
|
||||
private void parseShortcuts(Node d)
|
||||
{
|
||||
NamedNodeMap attrs = d.getAttributes();
|
||||
final Node classIdNode = attrs.getNamedItem("classId");
|
||||
final List<Shortcut> list = new ArrayList<>();
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("page".equals(c.getNodeName()))
|
||||
{
|
||||
attrs = c.getAttributes();
|
||||
final int pageId = parseInteger(attrs, "pageId");
|
||||
for (Node b = c.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("slot".equals(b.getNodeName()))
|
||||
{
|
||||
list.add(createShortcut(pageId, b));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (classIdNode != null)
|
||||
{
|
||||
_initialShortcutData.put(ClassId.getClassId(Integer.parseInt(classIdNode.getNodeValue())), list);
|
||||
}
|
||||
else
|
||||
{
|
||||
_initialGlobalShortcutList.addAll(list);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses a macro.
|
||||
* @param d the node
|
||||
*/
|
||||
private void parseMacros(Node d)
|
||||
{
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("macro".equals(c.getNodeName()))
|
||||
{
|
||||
NamedNodeMap attrs = c.getAttributes();
|
||||
if (!parseBoolean(attrs, "enabled", true))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
final int macroId = parseInteger(attrs, "macroId");
|
||||
final int icon = parseInteger(attrs, "icon");
|
||||
final String name = parseString(attrs, "name");
|
||||
final String description = parseString(attrs, "description");
|
||||
final String acronym = parseString(attrs, "acronym");
|
||||
final List<MacroCmd> commands = new ArrayList<>(1);
|
||||
int entry = 0;
|
||||
for (Node b = c.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("command".equals(b.getNodeName()))
|
||||
{
|
||||
attrs = b.getAttributes();
|
||||
final MacroType type = parseEnum(attrs, MacroType.class, "type");
|
||||
int d1 = 0;
|
||||
int d2 = 0;
|
||||
final String cmd = b.getTextContent();
|
||||
switch (type)
|
||||
{
|
||||
case SKILL:
|
||||
{
|
||||
d1 = parseInteger(attrs, "skillId"); // Skill ID
|
||||
d2 = parseInteger(attrs, "skillLvl", 0); // Skill level
|
||||
break;
|
||||
}
|
||||
case ACTION:
|
||||
{
|
||||
// Not handled by client.
|
||||
d1 = parseInteger(attrs, "actionId");
|
||||
break;
|
||||
}
|
||||
case TEXT:
|
||||
{
|
||||
// Doesn't have numeric parameters.
|
||||
break;
|
||||
}
|
||||
case SHORTCUT:
|
||||
{
|
||||
d1 = parseInteger(attrs, "page"); // Page
|
||||
d2 = parseInteger(attrs, "slot", 0); // Slot
|
||||
break;
|
||||
}
|
||||
case ITEM:
|
||||
{
|
||||
// Not handled by client.
|
||||
d1 = parseInteger(attrs, "itemId");
|
||||
break;
|
||||
}
|
||||
case DELAY:
|
||||
{
|
||||
d1 = parseInteger(attrs, "delay"); // Delay in seconds
|
||||
break;
|
||||
}
|
||||
}
|
||||
commands.add(new MacroCmd(entry++, type, d1, d2, cmd));
|
||||
}
|
||||
}
|
||||
_macroPresets.put(macroId, new Macro(macroId, icon, name, description, acronym, commands));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Parses a node an create a shortcut from it.
|
||||
* @param pageId the page ID
|
||||
* @param b the node to parse
|
||||
* @return the new shortcut
|
||||
*/
|
||||
private Shortcut createShortcut(int pageId, Node b)
|
||||
{
|
||||
final NamedNodeMap attrs = b.getAttributes();
|
||||
final int slotId = parseInteger(attrs, "slotId");
|
||||
final ShortcutType shortcutType = parseEnum(attrs, ShortcutType.class, "shortcutType");
|
||||
final int shortcutId = parseInteger(attrs, "shortcutId");
|
||||
final int shortcutLevel = parseInteger(attrs, "shortcutLevel", 0);
|
||||
final int characterType = parseInteger(attrs, "characterType", 0);
|
||||
return new Shortcut(slotId, pageId, shortcutType, shortcutId, shortcutLevel, characterType);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the shortcut list.
|
||||
* @param cId the class ID for the shortcut list
|
||||
* @return the shortcut list for the give class ID
|
||||
*/
|
||||
public List<Shortcut> getShortcutList(ClassId cId)
|
||||
{
|
||||
return _initialShortcutData.get(cId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the shortcut list.
|
||||
* @param cId the class ID for the shortcut list
|
||||
* @return the shortcut list for the give class ID
|
||||
*/
|
||||
public List<Shortcut> getShortcutList(int cId)
|
||||
{
|
||||
return _initialShortcutData.get(ClassId.getClassId(cId));
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the global shortcut list.
|
||||
* @return the global shortcut list
|
||||
*/
|
||||
public List<Shortcut> getGlobalMacroList()
|
||||
{
|
||||
return _initialGlobalShortcutList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Register all the available shortcuts for the given player.
|
||||
* @param player the player
|
||||
*/
|
||||
public void registerAllShortcuts(L2PcInstance player)
|
||||
{
|
||||
if (player == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
// Register global shortcuts.
|
||||
for (Shortcut shortcut : _initialGlobalShortcutList)
|
||||
{
|
||||
int shortcutId = shortcut.getId();
|
||||
switch (shortcut.getType())
|
||||
{
|
||||
case ITEM:
|
||||
{
|
||||
final L2ItemInstance item = player.getInventory().getItemByItemId(shortcutId);
|
||||
if (item == null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
shortcutId = item.getObjectId();
|
||||
break;
|
||||
}
|
||||
case SKILL:
|
||||
{
|
||||
if (!player.getSkills().containsKey(shortcutId))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case MACRO:
|
||||
{
|
||||
final Macro macro = _macroPresets.get(shortcutId);
|
||||
if (macro == null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
player.registerMacro(macro);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Register shortcut
|
||||
final Shortcut newShortcut = new Shortcut(shortcut.getSlot(), shortcut.getPage(), shortcut.getType(), shortcutId, shortcut.getLevel(), shortcut.getCharacterType());
|
||||
player.sendPacket(new ShortCutRegister(newShortcut));
|
||||
player.registerShortCut(newShortcut);
|
||||
}
|
||||
|
||||
// Register class specific shortcuts.
|
||||
if (_initialShortcutData.containsKey(player.getClassId()))
|
||||
{
|
||||
for (Shortcut shortcut : _initialShortcutData.get(player.getClassId()))
|
||||
{
|
||||
int shortcutId = shortcut.getId();
|
||||
switch (shortcut.getType())
|
||||
{
|
||||
case ITEM:
|
||||
{
|
||||
final L2ItemInstance item = player.getInventory().getItemByItemId(shortcutId);
|
||||
if (item == null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
shortcutId = item.getObjectId();
|
||||
break;
|
||||
}
|
||||
case SKILL:
|
||||
{
|
||||
if (!player.getSkills().containsKey(shortcut.getId()))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
break;
|
||||
}
|
||||
case MACRO:
|
||||
{
|
||||
final Macro macro = _macroPresets.get(shortcutId);
|
||||
if (macro == null)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
player.registerMacro(macro);
|
||||
break;
|
||||
}
|
||||
}
|
||||
// Register shortcut
|
||||
final Shortcut newShortcut = new Shortcut(shortcut.getSlot(), shortcut.getPage(), shortcut.getType(), shortcutId, shortcut.getLevel(), shortcut.getCharacterType());
|
||||
player.sendPacket(new ShortCutRegister(newShortcut));
|
||||
player.registerShortCut(newShortcut);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of InitialEquipmentData.
|
||||
* @return single instance of InitialEquipmentData
|
||||
*/
|
||||
public static InitialShortcutData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final InitialShortcutData _instance = new InitialShortcutData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,99 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.CrystalizationData;
|
||||
import com.l2jmobius.gameserver.model.holders.ItemChanceHolder;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public final class ItemCrystalizationData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, CrystalizationData> _items = new HashMap<>();
|
||||
|
||||
protected ItemCrystalizationData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
parseDatapackFile("CrystalizableItems.xml");
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _items.size() + " Items");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("crystalizable_item".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final int id = parseInteger(d.getAttributes(), "id");
|
||||
final CrystalizationData data = new CrystalizationData(id);
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = c.getAttributes();
|
||||
final int itemId = parseInteger(attrs, "id");
|
||||
final long itemCount = parseLong(attrs, "count");
|
||||
final double itemChance = parseDouble(attrs, "chance");
|
||||
data.addItem(new ItemChanceHolder(itemId, itemChance, itemCount));
|
||||
}
|
||||
}
|
||||
_items.put(id, data);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public CrystalizationData getCrystalization(int itemId)
|
||||
{
|
||||
return _items.get(itemId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of ItemCrystalizationData.
|
||||
* @return single instance of ItemCrystalizationData
|
||||
*/
|
||||
public static final ItemCrystalizationData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final ItemCrystalizationData _instance = new ItemCrystalizationData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,97 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Karma data.
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public class KarmaData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, Double> _karmaTable = new HashMap<>();
|
||||
|
||||
public KarmaData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_karmaTable.clear();
|
||||
parseDatapackFile("stats/chars/pcKarmaIncrease.xml");
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded " + _karmaTable.size() + " karma modifiers.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("pcKarmaIncrease".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("increase".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
final int level = parseInteger(attrs, "lvl");
|
||||
if (level >= Config.PLAYER_MAXIMUM_LEVEL)
|
||||
{
|
||||
break;
|
||||
}
|
||||
_karmaTable.put(level, parseDouble(attrs, "val"));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param level
|
||||
* @return {@code double} modifier used to calculate karma lost upon death.
|
||||
*/
|
||||
public double getMultiplier(int level)
|
||||
{
|
||||
return _karmaTable.get(level);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of KarmaData.
|
||||
* @return single instance of KarmaData
|
||||
*/
|
||||
public static KarmaData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final KarmaData _instance = new KarmaData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,164 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.holders.ItemHolder;
|
||||
import com.l2jmobius.util.Rnd;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author Mathael
|
||||
*/
|
||||
public class LuckyGameData implements IXmlReader
|
||||
{
|
||||
private static final List<ItemHolder> _fortuneReadingTicketRewards = new ArrayList<>();
|
||||
private static final List<ItemHolder> _luxuryFortuneReadingTicketRewards = new ArrayList<>();
|
||||
private static final List<ItemHolder> _rareLuxuryFortuneReadingTicketRewards = new ArrayList<>();
|
||||
|
||||
protected LuckyGameData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_fortuneReadingTicketRewards.clear();
|
||||
_luxuryFortuneReadingTicketRewards.clear();
|
||||
_rareLuxuryFortuneReadingTicketRewards.clear();
|
||||
|
||||
parseDatapackFile("LuckyGameData.xml");
|
||||
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _fortuneReadingTicketRewards.size() + " Normal item rewards.");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _luxuryFortuneReadingTicketRewards.size() + " Luxury item rewards.");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _rareLuxuryFortuneReadingTicketRewards.size() + " Rare item rewards.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap at = n.getAttributes();
|
||||
final Node attribute = at.getNamedItem("enabled");
|
||||
if ((attribute != null) && Boolean.parseBoolean(attribute.getNodeValue())) // <list enabled="true"
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("fortuneReadingTicketRewards".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
for (Node b = d.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = b.getAttributes();
|
||||
|
||||
final int itemId = parseInteger(attrs, "id");
|
||||
final int count = parseInteger(attrs, "count");
|
||||
|
||||
if ((itemId == 0) || (count == 0))
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": itemId: [" + itemId + "] count: [" + count + "] cannot be zero.");
|
||||
return;
|
||||
}
|
||||
|
||||
_fortuneReadingTicketRewards.add(new ItemHolder(itemId, count));
|
||||
}
|
||||
}
|
||||
}
|
||||
else if ("luxuryFortuneReadingTicketRewards".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
for (Node b = d.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = b.getAttributes();
|
||||
|
||||
final int itemId = parseInteger(attrs, "id");
|
||||
final int count = parseInteger(attrs, "count");
|
||||
|
||||
if ((itemId == 0) || (count == 0))
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": itemId: [" + itemId + "] count: [" + count + "] cannot be zero.");
|
||||
return;
|
||||
}
|
||||
|
||||
_luxuryFortuneReadingTicketRewards.add(new ItemHolder(itemId, count));
|
||||
}
|
||||
}
|
||||
}
|
||||
else if ("rareLuxuryFortuneReadingTicketRewards".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
for (Node b = d.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = b.getAttributes();
|
||||
|
||||
final int itemId = parseInteger(attrs, "id");
|
||||
final int count = parseInteger(attrs, "count");
|
||||
|
||||
if ((itemId == 0) || (count == 0))
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": itemId: [" + itemId + "] count: [" + count + "] cannot be zero.");
|
||||
return;
|
||||
}
|
||||
|
||||
_rareLuxuryFortuneReadingTicketRewards.add(new ItemHolder(itemId, count));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static ItemHolder getRandomNormalReward()
|
||||
{
|
||||
return _fortuneReadingTicketRewards.get(Rnd.get(_fortuneReadingTicketRewards.size()));
|
||||
}
|
||||
|
||||
public static ItemHolder getRandomLuxuryReward()
|
||||
{
|
||||
return _luxuryFortuneReadingTicketRewards.get(Rnd.get(_luxuryFortuneReadingTicketRewards.size()));
|
||||
}
|
||||
|
||||
public static ItemHolder getRandomRareReward()
|
||||
{
|
||||
return _rareLuxuryFortuneReadingTicketRewards.get(Rnd.get(_rareLuxuryFortuneReadingTicketRewards.size()));
|
||||
}
|
||||
|
||||
public static LuckyGameData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final LuckyGameData _instance = new LuckyGameData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,448 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileFilter;
|
||||
import java.util.HashMap;
|
||||
import java.util.Iterator;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.DOMException;
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.L2Npc;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
|
||||
import com.l2jmobius.gameserver.model.multisell.Entry;
|
||||
import com.l2jmobius.gameserver.model.multisell.Ingredient;
|
||||
import com.l2jmobius.gameserver.model.multisell.ListContainer;
|
||||
import com.l2jmobius.gameserver.model.multisell.PreparedListContainer;
|
||||
import com.l2jmobius.gameserver.network.SystemMessageId;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.ExPCCafePointInfo;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.MultiSellList;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.SystemMessage;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.UserInfo;
|
||||
import com.l2jmobius.gameserver.util.Util;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
import com.l2jmobius.util.file.filter.NumericNameFilter;
|
||||
|
||||
public final class MultisellData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, ListContainer> _entries = new HashMap<>();
|
||||
|
||||
public static final int PAGE_SIZE = 40;
|
||||
// Special IDs.
|
||||
public static final int PC_BANG_POINTS = -100;
|
||||
public static final int CLAN_REPUTATION = -200;
|
||||
public static final int FAME = -300;
|
||||
public static final int RAID_POINTS = -500;
|
||||
// Misc
|
||||
private static final FileFilter NUMERIC_FILTER = new NumericNameFilter();
|
||||
|
||||
protected MultisellData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_entries.clear();
|
||||
parseDatapackDirectory("multisell", false);
|
||||
if (Config.CUSTOM_MULTISELL_LOAD)
|
||||
{
|
||||
parseDatapackDirectory("multisell/custom", false);
|
||||
}
|
||||
|
||||
verify();
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded " + _entries.size() + " multisell lists.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc, File f)
|
||||
{
|
||||
try
|
||||
{
|
||||
final int id = Integer.parseInt(f.getName().replaceAll(".xml", ""));
|
||||
int entryId = 1;
|
||||
Node att;
|
||||
final ListContainer list = new ListContainer(id);
|
||||
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
list.setApplyTaxes(parseBoolean(n.getAttributes(), "applyTaxes", false));
|
||||
list.setNewMultisell(parseBoolean(n.getAttributes(), "isNewMultisell", false));
|
||||
list.setMaintainEnchantment(parseBoolean(n.getAttributes(), "maintainEnchantment", false));
|
||||
|
||||
att = n.getAttributes().getNamedItem("useRate");
|
||||
if (att != null)
|
||||
{
|
||||
try
|
||||
{
|
||||
|
||||
list.setUseRate(Double.valueOf(att.getNodeValue()));
|
||||
if (list.getUseRate() <= 1e-6)
|
||||
{
|
||||
throw new NumberFormatException("The value cannot be 0"); // threat 0 as invalid value
|
||||
}
|
||||
}
|
||||
catch (NumberFormatException e)
|
||||
{
|
||||
try
|
||||
{
|
||||
list.setUseRate(Config.class.getField(att.getNodeValue()).getDouble(Config.class));
|
||||
}
|
||||
catch (Exception e1)
|
||||
{
|
||||
LOGGER.warning(e1.getMessage() + doc.getLocalName());
|
||||
list.setUseRate(1.0);
|
||||
}
|
||||
}
|
||||
catch (DOMException e)
|
||||
{
|
||||
LOGGER.warning(e.getMessage() + doc.getLocalName());
|
||||
}
|
||||
}
|
||||
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final Entry e = parseEntry(d, entryId++, list);
|
||||
list.getEntries().add(e);
|
||||
}
|
||||
else if ("npcs".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
for (Node b = d.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("npc".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
if (Util.isDigit(b.getTextContent()))
|
||||
{
|
||||
list.allowNpc(Integer.parseInt(b.getTextContent()));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_entries.put(id, list);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
LOGGER.log(Level.SEVERE, getClass().getSimpleName() + ": Error in file " + f, e);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public FileFilter getCurrentFileFilter()
|
||||
{
|
||||
return NUMERIC_FILTER;
|
||||
}
|
||||
|
||||
private final Entry parseEntry(Node n, int entryId, ListContainer list)
|
||||
{
|
||||
final Node first = n.getFirstChild();
|
||||
final Entry entry = new Entry(entryId);
|
||||
|
||||
NamedNodeMap attrs;
|
||||
Node att;
|
||||
StatsSet set;
|
||||
|
||||
for (n = first; n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("ingredient".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
attrs = n.getAttributes();
|
||||
set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
entry.addIngredient(new Ingredient(set));
|
||||
}
|
||||
else if ("production".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
attrs = n.getAttributes();
|
||||
set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
entry.addProduct(new Ingredient(set));
|
||||
}
|
||||
}
|
||||
|
||||
return entry;
|
||||
}
|
||||
|
||||
/**
|
||||
* This will generate the multisell list for the items.<br>
|
||||
* There exist various parameters in multisells that affect the way they will appear:
|
||||
* <ol>
|
||||
* <li>Inventory only:
|
||||
* <ul>
|
||||
* <li>If true, only show items of the multisell for which the "primary" ingredients are already in the player's inventory. By "primary" ingredients we mean weapon and armor.</li>
|
||||
* <li>If false, show the entire list.</li>
|
||||
* </ul>
|
||||
* </li>
|
||||
* <li>Maintain enchantment: presumably, only lists with "inventory only" set to true should sometimes have this as true. This makes no sense otherwise...
|
||||
* <ul>
|
||||
* <li>If true, then the product will match the enchantment level of the ingredient.<br>
|
||||
* If the player has multiple items that match the ingredient list but the enchantment levels differ, then the entries need to be duplicated to show the products and ingredients for each enchantment level.<br>
|
||||
* For example: If the player has a crystal staff +1 and a crystal staff +3 and goes to exchange it at the mammon, the list should have all exchange possibilities for the +1 staff, followed by all possibilities for the +3 staff.</li>
|
||||
* <li>If false, then any level ingredient will be considered equal and product will always be at +0</li>
|
||||
* </ul>
|
||||
* </li>
|
||||
* <li>Apply taxes: Uses the "taxIngredient" entry in order to add a certain amount of adena to the ingredients.
|
||||
* <li>
|
||||
* <li>Additional product and ingredient multipliers.</li>
|
||||
* </ol>
|
||||
* @param listId
|
||||
* @param player
|
||||
* @param npc
|
||||
* @param inventoryOnly
|
||||
* @param productMultiplier
|
||||
* @param ingredientMultiplier
|
||||
*/
|
||||
public final void separateAndSend(int listId, L2PcInstance player, L2Npc npc, boolean inventoryOnly, double productMultiplier, double ingredientMultiplier)
|
||||
{
|
||||
final ListContainer template = _entries.get(listId);
|
||||
if (template == null)
|
||||
{
|
||||
LOGGER.warning(getClass().getSimpleName() + ": Cannot find list ID: " + listId + " requested by player: " + player.getName() + ", NPC ID:" + (npc != null ? npc.getId() : 0));
|
||||
return;
|
||||
}
|
||||
|
||||
if (!template.isNpcAllowed(-1) && (((npc != null) && !template.isNpcAllowed(npc.getId())) || ((npc == null) && template.isNpcOnly())))
|
||||
{
|
||||
LOGGER.warning(getClass().getSimpleName() + ": Player " + player + " attempted to open multisell " + listId + " from npc " + npc + " which is not allowed!");
|
||||
return;
|
||||
}
|
||||
|
||||
final PreparedListContainer list = new PreparedListContainer(template, inventoryOnly, player, npc);
|
||||
|
||||
// Pass through this only when multipliers are different from 1
|
||||
if ((productMultiplier != 1) || (ingredientMultiplier != 1))
|
||||
{
|
||||
list.getEntries().forEach(entry ->
|
||||
{
|
||||
// Math.max used here to avoid dropping count to 0
|
||||
entry.getProducts().forEach(product -> product.setItemCount((long) Math.max(product.getItemCount() * productMultiplier, 1)));
|
||||
|
||||
// Math.max used here to avoid dropping count to 0
|
||||
entry.getIngredients().forEach(ingredient -> ingredient.setItemCount((long) Math.max(ingredient.getItemCount() * ingredientMultiplier, 1)));
|
||||
});
|
||||
}
|
||||
int index = 0;
|
||||
do
|
||||
{
|
||||
// send list at least once even if size = 0
|
||||
player.sendPacket(new MultiSellList(list, index));
|
||||
index += PAGE_SIZE;
|
||||
}
|
||||
while (index < list.getEntries().size());
|
||||
|
||||
player.setMultiSell(list);
|
||||
}
|
||||
|
||||
public final void separateAndSend(int listId, L2PcInstance player, L2Npc npc, boolean inventoryOnly)
|
||||
{
|
||||
separateAndSend(listId, player, npc, inventoryOnly, 1, 1);
|
||||
}
|
||||
|
||||
public static final boolean hasSpecialIngredient(int id, long amount, L2PcInstance player)
|
||||
{
|
||||
switch (id)
|
||||
{
|
||||
case PC_BANG_POINTS:
|
||||
{
|
||||
if (player.getPcBangPoints() < amount)
|
||||
{
|
||||
player.sendPacket(SystemMessage.getSystemMessage(SystemMessageId.YOU_ARE_SHORT_OF_PC_POINTS));
|
||||
break;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
case CLAN_REPUTATION:
|
||||
{
|
||||
if (player.getClan() == null)
|
||||
{
|
||||
player.sendPacket(SystemMessageId.YOU_ARE_NOT_A_CLAN_MEMBER_AND_CANNOT_PERFORM_THIS_ACTION);
|
||||
break;
|
||||
}
|
||||
if (!player.isClanLeader())
|
||||
{
|
||||
player.sendPacket(SystemMessageId.ONLY_THE_CLAN_LEADER_IS_ENABLED);
|
||||
break;
|
||||
}
|
||||
if (player.getClan().getReputationScore() < amount)
|
||||
{
|
||||
player.sendPacket(SystemMessageId.THE_CLAN_REPUTATION_IS_TOO_LOW);
|
||||
break;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
case FAME:
|
||||
{
|
||||
if (player.getFame() < amount)
|
||||
{
|
||||
player.sendPacket(SystemMessageId.YOU_DON_T_HAVE_ENOUGH_FAME_TO_DO_THAT);
|
||||
break;
|
||||
}
|
||||
}
|
||||
case RAID_POINTS:
|
||||
{
|
||||
if (player.getRaidPoints() < amount)
|
||||
{
|
||||
player.sendPacket(SystemMessageId.NOT_ENOUGH_RAID_POINTS);
|
||||
break;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public static final boolean takeSpecialIngredient(int id, long amount, L2PcInstance player)
|
||||
{
|
||||
switch (id)
|
||||
{
|
||||
case PC_BANG_POINTS: // PcBang points
|
||||
{
|
||||
final int cost = player.getPcBangPoints() - (int) (amount);
|
||||
player.setPcBangPoints(cost);
|
||||
final SystemMessage smsgpc = SystemMessage.getSystemMessage(SystemMessageId.YOU_ARE_USING_S1_POINT);
|
||||
smsgpc.addLong((int) amount);
|
||||
player.sendPacket(smsgpc);
|
||||
player.sendPacket(new ExPCCafePointInfo(player.getPcBangPoints(), (int) amount, 1));
|
||||
return true;
|
||||
}
|
||||
case CLAN_REPUTATION:
|
||||
{
|
||||
player.getClan().takeReputationScore((int) amount, true);
|
||||
final SystemMessage smsg = SystemMessage.getSystemMessage(SystemMessageId.S1_POINT_S_HAVE_BEEN_DEDUCTED_FROM_THE_CLAN_S_REPUTATION);
|
||||
smsg.addLong(amount);
|
||||
player.sendPacket(smsg);
|
||||
return true;
|
||||
}
|
||||
case FAME:
|
||||
{
|
||||
player.setFame(player.getFame() - (int) amount);
|
||||
player.sendPacket(new UserInfo(player));
|
||||
return true;
|
||||
}
|
||||
case RAID_POINTS:
|
||||
{
|
||||
player.setRaidPoints(player.getRaidPoints() - (int) amount);
|
||||
player.sendPacket(new UserInfo(player));
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public static final void giveSpecialProduct(int id, long amount, L2PcInstance player)
|
||||
{
|
||||
switch (id)
|
||||
{
|
||||
case CLAN_REPUTATION:
|
||||
{
|
||||
player.getClan().addReputationScore((int) amount, true);
|
||||
break;
|
||||
}
|
||||
case FAME:
|
||||
{
|
||||
player.setFame((int) (player.getFame() + amount));
|
||||
player.sendPacket(new UserInfo(player));
|
||||
break;
|
||||
}
|
||||
case RAID_POINTS:
|
||||
{
|
||||
player.setRaidPoints((int) (player.getRaidPoints() + amount));
|
||||
player.sendPacket(new UserInfo(player));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private final void verify()
|
||||
{
|
||||
ListContainer list;
|
||||
final Iterator<ListContainer> iter = _entries.values().iterator();
|
||||
while (iter.hasNext())
|
||||
{
|
||||
list = iter.next();
|
||||
|
||||
for (Entry ent : list.getEntries())
|
||||
{
|
||||
for (Ingredient ing : ent.getIngredients())
|
||||
{
|
||||
if (!verifyIngredient(ing))
|
||||
{
|
||||
LOGGER.warning(getClass().getSimpleName() + ": Cannot find ingredient with item ID: " + ing.getItemId() + " in list: " + list.getListId());
|
||||
}
|
||||
}
|
||||
for (Ingredient ing : ent.getProducts())
|
||||
{
|
||||
if (!verifyIngredient(ing))
|
||||
{
|
||||
LOGGER.warning(getClass().getSimpleName() + ": Cannot find product with item ID: " + ing.getItemId() + " in list: " + list.getListId());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private final boolean verifyIngredient(Ingredient ing)
|
||||
{
|
||||
switch (ing.getItemId())
|
||||
{
|
||||
case PC_BANG_POINTS:
|
||||
case CLAN_REPUTATION:
|
||||
case FAME:
|
||||
case RAID_POINTS:
|
||||
{
|
||||
return true;
|
||||
}
|
||||
default:
|
||||
{
|
||||
return ing.getTemplate() != null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static MultisellData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final MultisellData _instance = new MultisellData();
|
||||
}
|
||||
}
|
894
trunk/java/com/l2jmobius/gameserver/data/xml/impl/NpcData.java
Normal file
894
trunk/java/com/l2jmobius/gameserver/data/xml/impl/NpcData.java
Normal file
@@ -0,0 +1,894 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.EnumMap;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Set;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
import java.util.function.Predicate;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.gameserver.datatables.SkillData;
|
||||
import com.l2jmobius.gameserver.enums.AISkillScope;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.templates.L2NpcTemplate;
|
||||
import com.l2jmobius.gameserver.model.base.ClassId;
|
||||
import com.l2jmobius.gameserver.model.drops.DropListScope;
|
||||
import com.l2jmobius.gameserver.model.drops.GeneralDropItem;
|
||||
import com.l2jmobius.gameserver.model.drops.GroupedGeneralDropItem;
|
||||
import com.l2jmobius.gameserver.model.drops.IDropItem;
|
||||
import com.l2jmobius.gameserver.model.effects.L2EffectType;
|
||||
import com.l2jmobius.gameserver.model.holders.MinionHolder;
|
||||
import com.l2jmobius.gameserver.model.holders.SkillHolder;
|
||||
import com.l2jmobius.gameserver.model.skills.Skill;
|
||||
import com.l2jmobius.gameserver.util.Util;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* NPC data parser.
|
||||
* @author NosBit
|
||||
*/
|
||||
public class NpcData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2NpcTemplate> _npcs = new ConcurrentHashMap<>();
|
||||
private final Map<String, Integer> _clans = new ConcurrentHashMap<>();
|
||||
private MinionData _minionData;
|
||||
|
||||
protected NpcData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_minionData = new MinionData();
|
||||
|
||||
parseDatapackDirectory("stats/npcs", false);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _npcs.size() + " NPCs.");
|
||||
|
||||
if (Config.CUSTOM_NPC_DATA)
|
||||
{
|
||||
final int npcCount = _npcs.size();
|
||||
parseDatapackDirectory("stats/npcs/custom", true);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + (_npcs.size() - npcCount) + " Custom NPCs.");
|
||||
}
|
||||
|
||||
_minionData = null;
|
||||
loadNpcsSkillLearn();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc, File f)
|
||||
{
|
||||
for (Node node = doc.getFirstChild(); node != null; node = node.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(node.getNodeName()))
|
||||
{
|
||||
for (Node listNode = node.getFirstChild(); listNode != null; listNode = listNode.getNextSibling())
|
||||
{
|
||||
if ("npc".equalsIgnoreCase(listNode.getNodeName()))
|
||||
{
|
||||
NamedNodeMap attrs = listNode.getAttributes();
|
||||
final StatsSet set = new StatsSet();
|
||||
final int npcId = parseInteger(attrs, "id");
|
||||
Map<String, Object> parameters = null;
|
||||
Map<Integer, Skill> skills = null;
|
||||
Set<Integer> clans = null;
|
||||
Set<Integer> ignoreClanNpcIds = null;
|
||||
Map<DropListScope, List<IDropItem>> dropLists = null;
|
||||
set.set("id", npcId);
|
||||
set.set("displayId", parseInteger(attrs, "displayId"));
|
||||
set.set("level", parseByte(attrs, "level"));
|
||||
set.set("type", parseString(attrs, "type"));
|
||||
set.set("name", parseString(attrs, "name"));
|
||||
set.set("usingServerSideName", parseBoolean(attrs, "usingServerSideName"));
|
||||
set.set("title", parseString(attrs, "title"));
|
||||
set.set("usingServerSideTitle", parseBoolean(attrs, "usingServerSideTitle"));
|
||||
for (Node npcNode = listNode.getFirstChild(); npcNode != null; npcNode = npcNode.getNextSibling())
|
||||
{
|
||||
attrs = npcNode.getAttributes();
|
||||
switch (npcNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "parameters":
|
||||
{
|
||||
if (parameters == null)
|
||||
{
|
||||
parameters = new HashMap<>();
|
||||
}
|
||||
|
||||
for (Node parametersNode = npcNode.getFirstChild(); parametersNode != null; parametersNode = parametersNode.getNextSibling())
|
||||
{
|
||||
attrs = parametersNode.getAttributes();
|
||||
switch (parametersNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "param":
|
||||
{
|
||||
parameters.put(parseString(attrs, "name"), parseString(attrs, "value"));
|
||||
break;
|
||||
}
|
||||
case "skill":
|
||||
{
|
||||
parameters.put(parseString(attrs, "name"), new SkillHolder(parseInteger(attrs, "id"), parseInteger(attrs, "level")));
|
||||
break;
|
||||
}
|
||||
case "minions":
|
||||
{
|
||||
final List<MinionHolder> minions = new ArrayList<>(1);
|
||||
for (Node minionsNode = parametersNode.getFirstChild(); minionsNode != null; minionsNode = minionsNode.getNextSibling())
|
||||
{
|
||||
if (minionsNode.getNodeName().equalsIgnoreCase("npc"))
|
||||
{
|
||||
attrs = minionsNode.getAttributes();
|
||||
minions.add(new MinionHolder(parseInteger(attrs, "id"), parseInteger(attrs, "count"), parseInteger(attrs, "respawnTime"), parseInteger(attrs, "weightPoint")));
|
||||
}
|
||||
}
|
||||
|
||||
if (!minions.isEmpty())
|
||||
{
|
||||
parameters.put(parseString(parametersNode.getAttributes(), "name"), minions);
|
||||
}
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "race":
|
||||
case "sex":
|
||||
{
|
||||
set.set(npcNode.getNodeName(), npcNode.getTextContent().toUpperCase());
|
||||
break;
|
||||
}
|
||||
case "equipment":
|
||||
{
|
||||
set.set("chestId", parseInteger(attrs, "chest"));
|
||||
set.set("rhandId", parseInteger(attrs, "rhand"));
|
||||
set.set("lhandId", parseInteger(attrs, "lhand"));
|
||||
set.set("weaponEnchant", parseInteger(attrs, "weaponEnchant"));
|
||||
break;
|
||||
}
|
||||
case "acquire":
|
||||
{
|
||||
set.set("exp", parseDouble(attrs, "exp"));
|
||||
set.set("sp", parseDouble(attrs, "sp"));
|
||||
set.set("raidPoints", parseDouble(attrs, "raidPoints"));
|
||||
break;
|
||||
}
|
||||
case "stats":
|
||||
{
|
||||
set.set("baseSTR", parseInteger(attrs, "str"));
|
||||
set.set("baseINT", parseInteger(attrs, "int"));
|
||||
set.set("baseDEX", parseInteger(attrs, "dex"));
|
||||
set.set("baseWIT", parseInteger(attrs, "wit"));
|
||||
set.set("baseCON", parseInteger(attrs, "con"));
|
||||
set.set("baseMEN", parseInteger(attrs, "men"));
|
||||
for (Node statsNode = npcNode.getFirstChild(); statsNode != null; statsNode = statsNode.getNextSibling())
|
||||
{
|
||||
attrs = statsNode.getAttributes();
|
||||
switch (statsNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "vitals":
|
||||
{
|
||||
set.set("baseHpMax", parseDouble(attrs, "hp"));
|
||||
set.set("baseHpReg", parseDouble(attrs, "hpRegen"));
|
||||
set.set("baseMpMax", parseDouble(attrs, "mp"));
|
||||
set.set("baseMpReg", parseDouble(attrs, "mpRegen"));
|
||||
break;
|
||||
}
|
||||
case "attack":
|
||||
{
|
||||
set.set("basePAtk", parseDouble(attrs, "physical"));
|
||||
set.set("baseMAtk", parseDouble(attrs, "magical"));
|
||||
set.set("baseRndDam", parseInteger(attrs, "random"));
|
||||
set.set("baseCritRate", parseInteger(attrs, "critical"));
|
||||
set.set("accuracy", parseDouble(attrs, "accuracy"));// TODO: Implement me
|
||||
set.set("basePAtkSpd", parseInteger(attrs, "attackSpeed"));
|
||||
set.set("reuseDelay", parseInteger(attrs, "reuseDelay"));// TODO: Implement me
|
||||
set.set("baseAtkType", parseString(attrs, "type"));
|
||||
set.set("baseAtkRange", parseInteger(attrs, "range"));
|
||||
set.set("distance", parseInteger(attrs, "distance"));// TODO: Implement me
|
||||
set.set("width", parseInteger(attrs, "width"));// TODO: Implement me
|
||||
break;
|
||||
}
|
||||
case "defence":
|
||||
{
|
||||
set.set("basePDef", parseDouble(attrs, "physical"));
|
||||
set.set("baseMDef", parseDouble(attrs, "magical"));
|
||||
set.set("evasion", parseInteger(attrs, "evasion"));// TODO: Implement me
|
||||
set.set("baseShldDef", parseInteger(attrs, "shield"));
|
||||
set.set("baseShldRate", parseInteger(attrs, "shieldRate"));
|
||||
break;
|
||||
}
|
||||
case "attribute":
|
||||
{
|
||||
for (Node attributeNode = statsNode.getFirstChild(); attributeNode != null; attributeNode = attributeNode.getNextSibling())
|
||||
{
|
||||
attrs = attributeNode.getAttributes();
|
||||
switch (attributeNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "attack":
|
||||
{
|
||||
final String attackAttributeType = parseString(attrs, "type");
|
||||
switch (attackAttributeType.toUpperCase())
|
||||
{
|
||||
case "FIRE":
|
||||
{
|
||||
set.set("baseFire", parseInteger(attrs, "value"));
|
||||
break;
|
||||
}
|
||||
case "WATER":
|
||||
{
|
||||
set.set("baseWater", parseInteger(attrs, "value"));
|
||||
break;
|
||||
}
|
||||
case "WIND":
|
||||
{
|
||||
set.set("baseWind", parseInteger(attrs, "value"));
|
||||
break;
|
||||
}
|
||||
case "EARTH":
|
||||
{
|
||||
set.set("baseEarth", parseInteger(attrs, "value"));
|
||||
break;
|
||||
}
|
||||
case "DARK":
|
||||
{
|
||||
set.set("baseDark", parseInteger(attrs, "value"));
|
||||
break;
|
||||
}
|
||||
case "HOLY":
|
||||
{
|
||||
set.set("baseHoly", parseInteger(attrs, "value"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "defence":
|
||||
{
|
||||
set.set("baseFireRes", parseInteger(attrs, "fire"));
|
||||
set.set("baseWaterRes", parseInteger(attrs, "water"));
|
||||
set.set("baseWindRes", parseInteger(attrs, "wind"));
|
||||
set.set("baseEarthRes", parseInteger(attrs, "earth"));
|
||||
set.set("baseHolyRes", parseInteger(attrs, "holy"));
|
||||
set.set("baseDarkRes", parseInteger(attrs, "dark"));
|
||||
set.set("baseElementRes", parseInteger(attrs, "default"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "speed":
|
||||
{
|
||||
{
|
||||
for (Node speedNode = statsNode.getFirstChild(); speedNode != null; speedNode = speedNode.getNextSibling())
|
||||
{
|
||||
attrs = speedNode.getAttributes();
|
||||
switch (speedNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "walk":
|
||||
{
|
||||
set.set("baseWalkSpd", parseDouble(attrs, "ground"));
|
||||
set.set("baseSwimWalkSpd", parseDouble(attrs, "swim"));
|
||||
set.set("baseFlyWalkSpd", parseDouble(attrs, "fly"));
|
||||
break;
|
||||
}
|
||||
case "run":
|
||||
{
|
||||
set.set("baseRunSpd", parseDouble(attrs, "ground"));
|
||||
set.set("baseSwimRunSpd", parseDouble(attrs, "swim"));
|
||||
set.set("baseFlyRunSpd", parseDouble(attrs, "fly"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
case "hitTime":
|
||||
{
|
||||
set.set("hitTime", npcNode.getTextContent());// TODO: Implement me default 600 (value in ms)
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "status":
|
||||
{
|
||||
set.set("unique", parseBoolean(attrs, "unique"));
|
||||
set.set("attackable", parseBoolean(attrs, "attackable"));
|
||||
set.set("targetable", parseBoolean(attrs, "targetable"));
|
||||
set.set("talkable", parseBoolean(attrs, "talkable"));
|
||||
set.set("undying", parseBoolean(attrs, "undying"));
|
||||
set.set("showName", parseBoolean(attrs, "showName"));
|
||||
set.set("flying", parseBoolean(attrs, "flying"));
|
||||
set.set("canMove", parseBoolean(attrs, "canMove"));
|
||||
set.set("noSleepMode", parseBoolean(attrs, "noSleepMode"));
|
||||
set.set("passableDoor", parseBoolean(attrs, "passableDoor"));
|
||||
set.set("hasSummoner", parseBoolean(attrs, "hasSummoner"));
|
||||
set.set("canBeSown", parseBoolean(attrs, "canBeSown"));
|
||||
break;
|
||||
}
|
||||
case "skilllist":
|
||||
{
|
||||
skills = new HashMap<>();
|
||||
for (Node skillListNode = npcNode.getFirstChild(); skillListNode != null; skillListNode = skillListNode.getNextSibling())
|
||||
{
|
||||
if ("skill".equalsIgnoreCase(skillListNode.getNodeName()))
|
||||
{
|
||||
attrs = skillListNode.getAttributes();
|
||||
final int skillId = parseInteger(attrs, "id");
|
||||
final int skillLevel = parseInteger(attrs, "level");
|
||||
final Skill skill = SkillData.getInstance().getSkill(skillId, skillLevel);
|
||||
if (skill != null)
|
||||
{
|
||||
skills.put(skill.getId(), skill);
|
||||
}
|
||||
else
|
||||
{
|
||||
LOGGER.warning("[" + f.getName() + "] skill not found. NPC ID: " + npcId + " Skill ID:" + skillId + " Skill Level: " + skillLevel);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "shots":
|
||||
{
|
||||
set.set("soulShot", parseInteger(attrs, "soul"));
|
||||
set.set("spiritShot", parseInteger(attrs, "spirit"));
|
||||
set.set("shotShotChance", parseInteger(attrs, "shotChance"));
|
||||
set.set("spiritShotChance", parseInteger(attrs, "spiritChance"));
|
||||
break;
|
||||
}
|
||||
case "corpsetime":
|
||||
{
|
||||
set.set("corpseTime", npcNode.getTextContent());
|
||||
break;
|
||||
}
|
||||
case "excrteffect":
|
||||
{
|
||||
set.set("exCrtEffect", npcNode.getTextContent()); // TODO: Implement me default ? type boolean
|
||||
break;
|
||||
}
|
||||
case "snpcprophprate":
|
||||
{
|
||||
set.set("sNpcPropHpRate", npcNode.getTextContent()); // TODO: Implement me default 1 type double
|
||||
break;
|
||||
}
|
||||
case "ai":
|
||||
{
|
||||
set.set("aiType", parseString(attrs, "type"));
|
||||
set.set("aggroRange", parseInteger(attrs, "aggroRange"));
|
||||
set.set("clanHelpRange", parseInteger(attrs, "clanHelpRange"));
|
||||
set.set("dodge", parseInteger(attrs, "dodge"));
|
||||
set.set("isChaos", parseBoolean(attrs, "isChaos"));
|
||||
set.set("isAggressive", parseBoolean(attrs, "isAggressive"));
|
||||
for (Node aiNode = npcNode.getFirstChild(); aiNode != null; aiNode = aiNode.getNextSibling())
|
||||
{
|
||||
attrs = aiNode.getAttributes();
|
||||
switch (aiNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "skill":
|
||||
{
|
||||
set.set("minSkillChance", parseInteger(attrs, "minChance"));
|
||||
set.set("maxSkillChance", parseInteger(attrs, "maxChance"));
|
||||
set.set("primarySkillId", parseInteger(attrs, "primaryId"));
|
||||
set.set("shortRangeSkillId", parseInteger(attrs, "shortRangeId"));
|
||||
set.set("shortRangeSkillChance", parseInteger(attrs, "shortRangeChance"));
|
||||
set.set("longRangeSkillId", parseInteger(attrs, "longRangeId"));
|
||||
set.set("longRangeSkillChance", parseInteger(attrs, "longRangeChance"));
|
||||
break;
|
||||
}
|
||||
case "clanList":
|
||||
{
|
||||
for (Node clanListNode = aiNode.getFirstChild(); clanListNode != null; clanListNode = clanListNode.getNextSibling())
|
||||
{
|
||||
attrs = clanListNode.getAttributes();
|
||||
switch (clanListNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "clan":
|
||||
{
|
||||
if (clans == null)
|
||||
{
|
||||
clans = new HashSet<>(1);
|
||||
}
|
||||
clans.add(getOrCreateClanId(clanListNode.getTextContent()));
|
||||
break;
|
||||
}
|
||||
case "ignoreNpcId":
|
||||
{
|
||||
if (ignoreClanNpcIds == null)
|
||||
{
|
||||
ignoreClanNpcIds = new HashSet<>(1);
|
||||
}
|
||||
ignoreClanNpcIds.add(Integer.parseInt(clanListNode.getTextContent()));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "droplists":
|
||||
{
|
||||
for (Node dropListsNode = npcNode.getFirstChild(); dropListsNode != null; dropListsNode = dropListsNode.getNextSibling())
|
||||
{
|
||||
DropListScope dropListScope = null;
|
||||
|
||||
try
|
||||
{
|
||||
dropListScope = Enum.valueOf(DropListScope.class, dropListsNode.getNodeName().toUpperCase());
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
}
|
||||
|
||||
if (dropListScope != null)
|
||||
{
|
||||
if (dropLists == null)
|
||||
{
|
||||
dropLists = new EnumMap<>(DropListScope.class);
|
||||
}
|
||||
|
||||
final List<IDropItem> dropList = new ArrayList<>();
|
||||
parseDropList(f, dropListsNode, dropListScope, dropList);
|
||||
dropLists.put(dropListScope, Collections.unmodifiableList(dropList));
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "collision":
|
||||
{
|
||||
for (Node collisionNode = npcNode.getFirstChild(); collisionNode != null; collisionNode = collisionNode.getNextSibling())
|
||||
{
|
||||
attrs = collisionNode.getAttributes();
|
||||
switch (collisionNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "radius":
|
||||
{
|
||||
set.set("collisionRadius", parseDouble(attrs, "normal"));
|
||||
set.set("collisionRadiusGrown", parseDouble(attrs, "grown"));
|
||||
break;
|
||||
}
|
||||
case "height":
|
||||
{
|
||||
set.set("collisionHeight", parseDouble(attrs, "normal"));
|
||||
set.set("collisionHeightGrown", parseDouble(attrs, "grown"));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
L2NpcTemplate template = _npcs.get(npcId);
|
||||
if (template == null)
|
||||
{
|
||||
template = new L2NpcTemplate(set);
|
||||
_npcs.put(template.getId(), template);
|
||||
}
|
||||
else
|
||||
{
|
||||
template.set(set);
|
||||
}
|
||||
|
||||
if (_minionData._tempMinions.containsKey(npcId))
|
||||
{
|
||||
if (parameters == null)
|
||||
{
|
||||
parameters = new HashMap<>();
|
||||
}
|
||||
parameters.putIfAbsent("Privates", _minionData._tempMinions.get(npcId));
|
||||
}
|
||||
|
||||
if (parameters != null)
|
||||
{
|
||||
// Using unmodifiable map parameters of template are not meant to be changed at runtime.
|
||||
template.setParameters(new StatsSet(Collections.unmodifiableMap(parameters)));
|
||||
}
|
||||
else
|
||||
{
|
||||
template.setParameters(StatsSet.EMPTY_STATSET);
|
||||
}
|
||||
|
||||
if (skills != null)
|
||||
{
|
||||
Map<AISkillScope, List<Skill>> aiSkillLists = null;
|
||||
for (Skill skill : skills.values())
|
||||
{
|
||||
if (skill.isPassive())
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (aiSkillLists == null)
|
||||
{
|
||||
aiSkillLists = new EnumMap<>(AISkillScope.class);
|
||||
}
|
||||
|
||||
final List<AISkillScope> aiSkillScopes = new ArrayList<>();
|
||||
final AISkillScope shortOrLongRangeScope = skill.getCastRange() <= 150 ? AISkillScope.SHORT_RANGE : AISkillScope.LONG_RANGE;
|
||||
if (skill.isSuicideAttack())
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.SUICIDE);
|
||||
}
|
||||
else
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.GENERAL);
|
||||
|
||||
if (skill.isContinuous())
|
||||
{
|
||||
if (!skill.isDebuff())
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.BUFF);
|
||||
}
|
||||
else
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.DEBUFF);
|
||||
aiSkillScopes.add(AISkillScope.COT);
|
||||
aiSkillScopes.add(shortOrLongRangeScope);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (skill.hasEffectType(L2EffectType.DISPEL, L2EffectType.DISPEL_BY_SLOT))
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.NEGATIVE);
|
||||
aiSkillScopes.add(shortOrLongRangeScope);
|
||||
}
|
||||
else if (skill.hasEffectType(L2EffectType.HEAL))
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.HEAL);
|
||||
}
|
||||
else if (skill.hasEffectType(L2EffectType.PHYSICAL_ATTACK, L2EffectType.PHYSICAL_ATTACK_HP_LINK, L2EffectType.MAGICAL_ATTACK, L2EffectType.DEATH_LINK, L2EffectType.HP_DRAIN))
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.ATTACK);
|
||||
aiSkillScopes.add(AISkillScope.UNIVERSAL);
|
||||
aiSkillScopes.add(shortOrLongRangeScope);
|
||||
}
|
||||
else if (skill.hasEffectType(L2EffectType.SLEEP))
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.IMMOBILIZE);
|
||||
}
|
||||
else if (skill.hasEffectType(L2EffectType.STUN, L2EffectType.ROOT))
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.IMMOBILIZE);
|
||||
aiSkillScopes.add(shortOrLongRangeScope);
|
||||
}
|
||||
else if (skill.hasEffectType(L2EffectType.MUTE, L2EffectType.FEAR))
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.COT);
|
||||
aiSkillScopes.add(shortOrLongRangeScope);
|
||||
}
|
||||
else if (skill.hasEffectType(L2EffectType.PARALYZE))
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.IMMOBILIZE);
|
||||
aiSkillScopes.add(shortOrLongRangeScope);
|
||||
}
|
||||
else if (skill.hasEffectType(L2EffectType.DMG_OVER_TIME, L2EffectType.DMG_OVER_TIME_PERCENT))
|
||||
{
|
||||
aiSkillScopes.add(shortOrLongRangeScope);
|
||||
}
|
||||
else if (skill.hasEffectType(L2EffectType.RESURRECTION))
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.RES);
|
||||
}
|
||||
else
|
||||
{
|
||||
aiSkillScopes.add(AISkillScope.UNIVERSAL);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for (AISkillScope aiSkillScope : aiSkillScopes)
|
||||
{
|
||||
List<Skill> aiSkills = aiSkillLists.get(aiSkillScope);
|
||||
if (aiSkills == null)
|
||||
{
|
||||
aiSkills = new ArrayList<>();
|
||||
aiSkillLists.put(aiSkillScope, aiSkills);
|
||||
}
|
||||
|
||||
aiSkills.add(skill);
|
||||
}
|
||||
}
|
||||
|
||||
template.setSkills(skills);
|
||||
template.setAISkillLists(aiSkillLists);
|
||||
}
|
||||
else
|
||||
{
|
||||
template.setSkills(null);
|
||||
template.setAISkillLists(null);
|
||||
}
|
||||
|
||||
template.setClans(clans);
|
||||
template.setIgnoreClanNpcIds(ignoreClanNpcIds);
|
||||
|
||||
template.setDropLists(dropLists);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void parseDropList(File f, Node dropListNode, DropListScope dropListScope, List<IDropItem> drops)
|
||||
{
|
||||
for (Node dropNode = dropListNode.getFirstChild(); dropNode != null; dropNode = dropNode.getNextSibling())
|
||||
{
|
||||
final NamedNodeMap attrs = dropNode.getAttributes();
|
||||
switch (dropNode.getNodeName().toLowerCase())
|
||||
{
|
||||
case "group":
|
||||
{
|
||||
final GroupedGeneralDropItem dropItem = dropListScope.newGroupedDropItem(parseDouble(attrs, "chance"));
|
||||
final List<IDropItem> groupedDropList = new ArrayList<>(2);
|
||||
for (Node groupNode = dropNode.getFirstChild(); groupNode != null; groupNode = groupNode.getNextSibling())
|
||||
{
|
||||
parseDropListItem(groupNode, dropListScope, groupedDropList);
|
||||
}
|
||||
|
||||
final List<GeneralDropItem> items = new ArrayList<>(groupedDropList.size());
|
||||
for (IDropItem item : groupedDropList)
|
||||
{
|
||||
if (item instanceof GeneralDropItem)
|
||||
{
|
||||
items.add((GeneralDropItem) item);
|
||||
}
|
||||
else
|
||||
{
|
||||
LOGGER.warning("[" + f + "] grouped general drop item supports only general drop item.");
|
||||
}
|
||||
}
|
||||
dropItem.setItems(items);
|
||||
|
||||
drops.add(dropItem);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
parseDropListItem(dropNode, dropListScope, drops);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void parseDropListItem(Node dropListItem, DropListScope dropListScope, List<IDropItem> drops)
|
||||
{
|
||||
final NamedNodeMap attrs = dropListItem.getAttributes();
|
||||
switch (dropListItem.getNodeName().toLowerCase())
|
||||
{
|
||||
case "item":
|
||||
{
|
||||
final IDropItem dropItem = dropListScope.newDropItem(parseInteger(attrs, "id"), parseLong(attrs, "min"), parseLong(attrs, "max"), parseDouble(attrs, "chance"));
|
||||
if (dropItem != null)
|
||||
{
|
||||
drops.add(dropItem);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets or creates a clan id if it doesnt exists.
|
||||
* @param clanName the clan name to get or create its id
|
||||
* @return the clan id for the given clan name
|
||||
*/
|
||||
private int getOrCreateClanId(String clanName)
|
||||
{
|
||||
Integer id = _clans.get(clanName.toUpperCase());
|
||||
if (id == null)
|
||||
{
|
||||
id = _clans.size();
|
||||
_clans.put(clanName.toUpperCase(), id);
|
||||
}
|
||||
return id;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the clan id
|
||||
* @param clanName the clan name to get its id
|
||||
* @return the clan id for the given clan name if it exists, -1 otherwise
|
||||
*/
|
||||
public int getClanId(String clanName)
|
||||
{
|
||||
final Integer id = _clans.get(clanName.toUpperCase());
|
||||
return id != null ? id : -1;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the template.
|
||||
* @param id the template Id to get.
|
||||
* @return the template for the given id.
|
||||
*/
|
||||
public L2NpcTemplate getTemplate(int id)
|
||||
{
|
||||
return _npcs.get(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the template by name.
|
||||
* @param name of the template to get.
|
||||
* @return the template for the given name.
|
||||
*/
|
||||
public L2NpcTemplate getTemplateByName(String name)
|
||||
{
|
||||
for (L2NpcTemplate npcTemplate : _npcs.values())
|
||||
{
|
||||
if (npcTemplate.getName().equalsIgnoreCase(name))
|
||||
{
|
||||
return npcTemplate;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets all templates matching the filter.
|
||||
* @param filter
|
||||
* @return the template list for the given filter
|
||||
*/
|
||||
public List<L2NpcTemplate> getTemplates(Predicate<L2NpcTemplate> filter)
|
||||
{
|
||||
//@formatter:off
|
||||
return _npcs.values().stream()
|
||||
.filter(filter)
|
||||
.collect(Collectors.toList());
|
||||
//@formatter:on
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the all of level.
|
||||
* @param lvls of all the templates to get.
|
||||
* @return the template list for the given level.
|
||||
*/
|
||||
public List<L2NpcTemplate> getAllOfLevel(int... lvls)
|
||||
{
|
||||
return getTemplates(template -> Util.contains(lvls, template.getLevel()));
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the all monsters of level.
|
||||
* @param lvls of all the monster templates to get.
|
||||
* @return the template list for the given level.
|
||||
*/
|
||||
public List<L2NpcTemplate> getAllMonstersOfLevel(int... lvls)
|
||||
{
|
||||
return getTemplates(template -> Util.contains(lvls, template.getLevel()) && template.isType("L2Monster"));
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the all npc starting with.
|
||||
* @param text of all the NPC templates which its name start with.
|
||||
* @return the template list for the given letter.
|
||||
*/
|
||||
public List<L2NpcTemplate> getAllNpcStartingWith(String text)
|
||||
{
|
||||
return getTemplates(template -> template.isType("L2Npc") && template.getName().startsWith(text));
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the all npc of class type.
|
||||
* @param classTypes of all the templates to get.
|
||||
* @return the template list for the given class type.
|
||||
*/
|
||||
public List<L2NpcTemplate> getAllNpcOfClassType(String... classTypes)
|
||||
{
|
||||
return getTemplates(template -> Util.contains(classTypes, template.getType(), true));
|
||||
}
|
||||
|
||||
public void loadNpcsSkillLearn()
|
||||
{
|
||||
_npcs.values().forEach(template ->
|
||||
{
|
||||
final List<ClassId> teachInfo = SkillLearnData.getInstance().getSkillLearnData(template.getId());
|
||||
if (teachInfo != null)
|
||||
{
|
||||
template.addTeachInfo(teachInfo);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* This class handles minions from Spawn System<br>
|
||||
* Once Spawn System gets reworked delete this class<br>
|
||||
* @author Zealar
|
||||
*/
|
||||
private final class MinionData implements IXmlReader
|
||||
{
|
||||
public final Map<Integer, List<MinionHolder>> _tempMinions = new HashMap<>();
|
||||
|
||||
protected MinionData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_tempMinions.clear();
|
||||
parseDatapackFile("minionData.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _tempMinions.size() + " minions data.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node node = doc.getFirstChild(); node != null; node = node.getNextSibling())
|
||||
{
|
||||
if ("list".equals(node.getNodeName()))
|
||||
{
|
||||
for (Node listNode = node.getFirstChild(); listNode != null; listNode = listNode.getNextSibling())
|
||||
{
|
||||
if ("npc".equals(listNode.getNodeName()))
|
||||
{
|
||||
final List<MinionHolder> minions = new ArrayList<>(1);
|
||||
NamedNodeMap attrs = listNode.getAttributes();
|
||||
final int id = parseInteger(attrs, "id");
|
||||
for (Node npcNode = listNode.getFirstChild(); npcNode != null; npcNode = npcNode.getNextSibling())
|
||||
{
|
||||
if ("minion".equals(npcNode.getNodeName()))
|
||||
{
|
||||
attrs = npcNode.getAttributes();
|
||||
minions.add(new MinionHolder(parseInteger(attrs, "id"), parseInteger(attrs, "count"), parseInteger(attrs, "respawnTime"), 0));
|
||||
}
|
||||
}
|
||||
_tempMinions.put(id, minions);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of NpcData.
|
||||
* @return single instance of NpcData
|
||||
*/
|
||||
public static NpcData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final NpcData _instance = new NpcData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,161 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.holders.SkillHolder;
|
||||
import com.l2jmobius.gameserver.model.options.Options;
|
||||
import com.l2jmobius.gameserver.model.options.OptionsSkillHolder;
|
||||
import com.l2jmobius.gameserver.model.options.OptionsSkillType;
|
||||
import com.l2jmobius.gameserver.model.stats.Stats;
|
||||
import com.l2jmobius.gameserver.model.stats.functions.FuncTemplate;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Item Option data.
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public class OptionData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, Options> _optionData = new HashMap<>();
|
||||
|
||||
protected OptionData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_optionData.clear();
|
||||
parseDatapackDirectory("stats/options", false);
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _optionData.size() + " Options.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("option".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final int id = parseInteger(d.getAttributes(), "id");
|
||||
final Options op = new Options(id);
|
||||
|
||||
for (Node cd = d.getFirstChild(); cd != null; cd = cd.getNextSibling())
|
||||
{
|
||||
switch (cd.getNodeName())
|
||||
{
|
||||
case "for":
|
||||
{
|
||||
for (Node fd = cd.getFirstChild(); fd != null; fd = fd.getNextSibling())
|
||||
{
|
||||
switch (fd.getNodeName())
|
||||
{
|
||||
case "add":
|
||||
case "sub":
|
||||
case "mul":
|
||||
case "div":
|
||||
case "set":
|
||||
case "share":
|
||||
case "enchant":
|
||||
case "enchanthp":
|
||||
{
|
||||
parseFuncs(fd.getAttributes(), fd.getNodeName(), op);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "active_skill":
|
||||
{
|
||||
op.setActiveSkill(new SkillHolder(parseInteger(cd.getAttributes(), "id"), parseInteger(cd.getAttributes(), "level")));
|
||||
break;
|
||||
}
|
||||
case "passive_skill":
|
||||
{
|
||||
op.setPassiveSkill(new SkillHolder(parseInteger(cd.getAttributes(), "id"), parseInteger(cd.getAttributes(), "level")));
|
||||
break;
|
||||
}
|
||||
case "attack_skill":
|
||||
{
|
||||
op.addActivationSkill(new OptionsSkillHolder(parseInteger(cd.getAttributes(), "id"), parseInteger(cd.getAttributes(), "level"), parseDouble(cd.getAttributes(), "chance"), OptionsSkillType.ATTACK));
|
||||
break;
|
||||
}
|
||||
case "magic_skill":
|
||||
{
|
||||
op.addActivationSkill(new OptionsSkillHolder(parseInteger(cd.getAttributes(), "id"), parseInteger(cd.getAttributes(), "level"), parseDouble(cd.getAttributes(), "chance"), OptionsSkillType.MAGIC));
|
||||
break;
|
||||
}
|
||||
case "critical_skill":
|
||||
{
|
||||
op.addActivationSkill(new OptionsSkillHolder(parseInteger(cd.getAttributes(), "id"), parseInteger(cd.getAttributes(), "level"), parseDouble(cd.getAttributes(), "chance"), OptionsSkillType.CRITICAL));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
_optionData.put(op.getId(), op);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void parseFuncs(NamedNodeMap attrs, String functionName, Options op)
|
||||
{
|
||||
final Stats stat = Stats.valueOfXml(parseString(attrs, "stat"));
|
||||
final double val = parseDouble(attrs, "val");
|
||||
int order = -1;
|
||||
final Node orderNode = attrs.getNamedItem("order");
|
||||
if (orderNode != null)
|
||||
{
|
||||
order = Integer.parseInt(orderNode.getNodeValue());
|
||||
}
|
||||
op.addFunc(new FuncTemplate(null, null, functionName, order, stat, val));
|
||||
}
|
||||
|
||||
public Options getOptions(int id)
|
||||
{
|
||||
return _optionData.get(id);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of OptionsData.
|
||||
* @return single instance of OptionsData
|
||||
*/
|
||||
public static final OptionData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final OptionData _instance = new OptionData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,241 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.enums.MountType;
|
||||
import com.l2jmobius.gameserver.model.L2PetData;
|
||||
import com.l2jmobius.gameserver.model.L2PetLevelData;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class parse and hold all pet parameters.<br>
|
||||
* TODO: load and use all pet parameters.
|
||||
* @author Zoey76 (rework)
|
||||
*/
|
||||
public final class PetDataTable implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2PetData> _pets = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new pet data table.
|
||||
*/
|
||||
protected PetDataTable()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_pets.clear();
|
||||
parseDatapackDirectory("stats/pets", false);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _pets.size() + " Pets.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
NamedNodeMap attrs;
|
||||
final Node n = doc.getFirstChild();
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if (d.getNodeName().equals("pet"))
|
||||
{
|
||||
final int npcId = parseInteger(d.getAttributes(), "id");
|
||||
final int itemId = parseInteger(d.getAttributes(), "itemId");
|
||||
// index ignored for now
|
||||
final L2PetData data = new L2PetData(npcId, itemId);
|
||||
for (Node p = d.getFirstChild(); p != null; p = p.getNextSibling())
|
||||
{
|
||||
if (p.getNodeName().equals("set"))
|
||||
{
|
||||
attrs = p.getAttributes();
|
||||
final String type = attrs.getNamedItem("name").getNodeValue();
|
||||
if ("food".equals(type))
|
||||
{
|
||||
for (String foodId : attrs.getNamedItem("val").getNodeValue().split(";"))
|
||||
{
|
||||
data.addFood(Integer.valueOf(foodId));
|
||||
}
|
||||
}
|
||||
else if ("load".equals(type))
|
||||
{
|
||||
data.setLoad(parseInteger(attrs, "val"));
|
||||
}
|
||||
else if ("hungry_limit".equals(type))
|
||||
{
|
||||
data.setHungryLimit(parseInteger(attrs, "val"));
|
||||
}
|
||||
else if ("sync_level".equals(type))
|
||||
{
|
||||
data.setSyncLevel(parseInteger(attrs, "val") == 1);
|
||||
}
|
||||
// evolve ignored
|
||||
}
|
||||
else if (p.getNodeName().equals("skills"))
|
||||
{
|
||||
for (Node s = p.getFirstChild(); s != null; s = s.getNextSibling())
|
||||
{
|
||||
if (s.getNodeName().equals("skill"))
|
||||
{
|
||||
attrs = s.getAttributes();
|
||||
data.addNewSkill(parseInteger(attrs, "skillId"), parseInteger(attrs, "skillLvl"), parseInteger(attrs, "minLvl"));
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (p.getNodeName().equals("stats"))
|
||||
{
|
||||
for (Node s = p.getFirstChild(); s != null; s = s.getNextSibling())
|
||||
{
|
||||
if (s.getNodeName().equals("stat"))
|
||||
{
|
||||
final int level = Integer.parseInt(s.getAttributes().getNamedItem("level").getNodeValue());
|
||||
final StatsSet set = new StatsSet();
|
||||
for (Node bean = s.getFirstChild(); bean != null; bean = bean.getNextSibling())
|
||||
{
|
||||
if (bean.getNodeName().equals("set"))
|
||||
{
|
||||
attrs = bean.getAttributes();
|
||||
if (attrs.getNamedItem("name").getNodeValue().equals("speed_on_ride"))
|
||||
{
|
||||
set.set("walkSpeedOnRide", attrs.getNamedItem("walk").getNodeValue());
|
||||
set.set("runSpeedOnRide", attrs.getNamedItem("run").getNodeValue());
|
||||
set.set("slowSwimSpeedOnRide", attrs.getNamedItem("slowSwim").getNodeValue());
|
||||
set.set("fastSwimSpeedOnRide", attrs.getNamedItem("fastSwim").getNodeValue());
|
||||
if (attrs.getNamedItem("slowFly") != null)
|
||||
{
|
||||
set.set("slowFlySpeedOnRide", attrs.getNamedItem("slowFly").getNodeValue());
|
||||
}
|
||||
if (attrs.getNamedItem("fastFly") != null)
|
||||
{
|
||||
set.set("fastFlySpeedOnRide", attrs.getNamedItem("fastFly").getNodeValue());
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
set.set(attrs.getNamedItem("name").getNodeValue(), attrs.getNamedItem("val").getNodeValue());
|
||||
}
|
||||
}
|
||||
}
|
||||
data.addNewStat(level, new L2PetLevelData(set));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_pets.put(npcId, data);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param itemId
|
||||
* @return
|
||||
*/
|
||||
public L2PetData getPetDataByItemId(int itemId)
|
||||
{
|
||||
for (L2PetData data : _pets.values())
|
||||
{
|
||||
if (data.getItemId() == itemId)
|
||||
{
|
||||
return data;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the pet level data.
|
||||
* @param petId the pet Id.
|
||||
* @param petLevel the pet level.
|
||||
* @return the pet's parameters for the given Id and level.
|
||||
*/
|
||||
public L2PetLevelData getPetLevelData(int petId, int petLevel)
|
||||
{
|
||||
final L2PetData pd = getPetData(petId);
|
||||
if (pd != null)
|
||||
{
|
||||
return pd.getPetLevelData(petLevel);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the pet data.
|
||||
* @param petId the pet Id.
|
||||
* @return the pet data
|
||||
*/
|
||||
public L2PetData getPetData(int petId)
|
||||
{
|
||||
if (!_pets.containsKey(petId))
|
||||
{
|
||||
LOGGER.info(getClass().getSimpleName() + ": Missing pet data for npcid: " + petId);
|
||||
}
|
||||
return _pets.get(petId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the pet min level.
|
||||
* @param petId the pet Id.
|
||||
* @return the pet min level
|
||||
*/
|
||||
public int getPetMinLevel(int petId)
|
||||
{
|
||||
return _pets.get(petId).getMinLevel();
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the pet items by npc.
|
||||
* @param npcId the NPC ID to get its summoning item
|
||||
* @return summoning item for the given NPC ID
|
||||
*/
|
||||
public int getPetItemsByNpc(int npcId)
|
||||
{
|
||||
return _pets.get(npcId).getItemId();
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if is mountable.
|
||||
* @param npcId the NPC Id to verify.
|
||||
* @return {@code true} if the given Id is from a mountable pet, {@code false} otherwise.
|
||||
*/
|
||||
public static boolean isMountable(int npcId)
|
||||
{
|
||||
return MountType.findByNpcId(npcId) != MountType.NONE;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of PetDataTable.
|
||||
* @return this class unique instance.
|
||||
*/
|
||||
public static PetDataTable getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final PetDataTable _instance = new PetDataTable();
|
||||
}
|
||||
}
|
@@ -0,0 +1,192 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.Config;
|
||||
import com.l2jmobius.gameserver.model.Location;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.templates.L2PcTemplate;
|
||||
import com.l2jmobius.gameserver.model.base.ClassId;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Loads player's base stats.
|
||||
* @author Forsaiken, Zoey76, GKR
|
||||
*/
|
||||
public final class PlayerTemplateData implements IXmlReader
|
||||
{
|
||||
private static final Logger LOGGER = Logger.getLogger(PlayerTemplateData.class.getName());
|
||||
|
||||
private final Map<ClassId, L2PcTemplate> _playerTemplates = new HashMap<>();
|
||||
|
||||
private int _dataCount = 0;
|
||||
|
||||
protected PlayerTemplateData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_playerTemplates.clear();
|
||||
parseDatapackDirectory("stats/chars/baseStats", false);
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _playerTemplates.size() + " character templates.");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _dataCount + " level up gain records.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
NamedNodeMap attrs;
|
||||
int classId = 0;
|
||||
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("classId".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
classId = Integer.parseInt(d.getTextContent());
|
||||
}
|
||||
else if ("staticData".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final StatsSet set = new StatsSet();
|
||||
set.set("classId", classId);
|
||||
final List<Location> creationPoints = new ArrayList<>();
|
||||
|
||||
for (Node nd = d.getFirstChild(); nd != null; nd = nd.getNextSibling())
|
||||
{
|
||||
// Skip odd nodes
|
||||
if (nd.getNodeName().equals("#text"))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (nd.getChildNodes().getLength() > 1)
|
||||
{
|
||||
for (Node cnd = nd.getFirstChild(); cnd != null; cnd = cnd.getNextSibling())
|
||||
{
|
||||
// use L2CharTemplate(superclass) fields for male collision height and collision radius
|
||||
if (nd.getNodeName().equalsIgnoreCase("collisionMale"))
|
||||
{
|
||||
if (cnd.getNodeName().equalsIgnoreCase("radius"))
|
||||
{
|
||||
set.set("collisionRadius", cnd.getTextContent());
|
||||
}
|
||||
else if (cnd.getNodeName().equalsIgnoreCase("height"))
|
||||
{
|
||||
set.set("collisionHeight", cnd.getTextContent());
|
||||
}
|
||||
}
|
||||
if ("node".equalsIgnoreCase(cnd.getNodeName()))
|
||||
{
|
||||
attrs = cnd.getAttributes();
|
||||
creationPoints.add(new Location(parseInteger(attrs, "x"), parseInteger(attrs, "y"), parseInteger(attrs, "z")));
|
||||
}
|
||||
else if ("walk".equalsIgnoreCase(cnd.getNodeName()))
|
||||
{
|
||||
set.set("baseWalkSpd", cnd.getTextContent());
|
||||
}
|
||||
else if ("run".equalsIgnoreCase(cnd.getNodeName()))
|
||||
{
|
||||
set.set("baseRunSpd", cnd.getTextContent());
|
||||
}
|
||||
else if ("slowSwim".equals(cnd.getNodeName()))
|
||||
{
|
||||
set.set("baseSwimWalkSpd", cnd.getTextContent());
|
||||
}
|
||||
else if ("fastSwim".equals(cnd.getNodeName()))
|
||||
{
|
||||
set.set("baseSwimRunSpd", cnd.getTextContent());
|
||||
}
|
||||
else if (!cnd.getNodeName().equals("#text"))
|
||||
{
|
||||
set.set((nd.getNodeName() + cnd.getNodeName()), cnd.getTextContent());
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
set.set(nd.getNodeName(), nd.getTextContent());
|
||||
}
|
||||
}
|
||||
// calculate total pdef and mdef from parts
|
||||
set.set("basePDef", (set.getInt("basePDefchest", 0) + set.getInt("basePDeflegs", 0) + set.getInt("basePDefhead", 0) + set.getInt("basePDeffeet", 0) + set.getInt("basePDefgloves", 0) + set.getInt("basePDefunderwear", 0) + set.getInt("basePDefcloak", 0)));
|
||||
set.set("baseMDef", (set.getInt("baseMDefrear", 0) + set.getInt("baseMDeflear", 0) + set.getInt("baseMDefrfinger", 0) + set.getInt("baseMDefrfinger", 0) + set.getInt("baseMDefneck", 0)));
|
||||
|
||||
_playerTemplates.put(ClassId.getClassId(classId), new L2PcTemplate(set, creationPoints));
|
||||
}
|
||||
else if ("lvlUpgainData".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
for (Node lvlNode = d.getFirstChild(); lvlNode != null; lvlNode = lvlNode.getNextSibling())
|
||||
{
|
||||
if ("level".equalsIgnoreCase(lvlNode.getNodeName()))
|
||||
{
|
||||
attrs = lvlNode.getAttributes();
|
||||
final int level = parseInteger(attrs, "val");
|
||||
for (Node valNode = lvlNode.getFirstChild(); valNode != null; valNode = valNode.getNextSibling())
|
||||
{
|
||||
final String nodeName = valNode.getNodeName();
|
||||
|
||||
if ((level < Config.PLAYER_MAXIMUM_LEVEL) && (nodeName.startsWith("hp") || nodeName.startsWith("mp") || nodeName.startsWith("cp")) && _playerTemplates.containsKey(ClassId.getClassId(classId)))
|
||||
{
|
||||
_playerTemplates.get(ClassId.getClassId(classId)).setUpgainValue(nodeName, level, Double.parseDouble(valNode.getTextContent()));
|
||||
_dataCount++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
// TODO: Generate stats automatically.
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public L2PcTemplate getTemplate(ClassId classId)
|
||||
{
|
||||
return _playerTemplates.get(classId);
|
||||
}
|
||||
|
||||
public L2PcTemplate getTemplate(int classId)
|
||||
{
|
||||
return _playerTemplates.get(ClassId.getClassId(classId));
|
||||
}
|
||||
|
||||
public static final PlayerTemplateData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final PlayerTemplateData _instance = new PlayerTemplateData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,95 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.Arrays;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class holds the Player Xp Percent Lost Data for each level for players.
|
||||
* @author Zealar
|
||||
*/
|
||||
public final class PlayerXpPercentLostData implements IXmlReader
|
||||
{
|
||||
private final int _maxlevel = ExperienceData.getInstance().getMaxLevel();
|
||||
private final double[] _playerXpPercentLost = new double[_maxlevel + 1];
|
||||
|
||||
protected PlayerXpPercentLostData()
|
||||
{
|
||||
Arrays.fill(_playerXpPercentLost, 1.);
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
parseDatapackFile("stats/chars/playerXpPercentLost.xml");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("xpLost".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
final Integer level = parseInteger(attrs, "level");
|
||||
if (level > _maxlevel)
|
||||
{
|
||||
break;
|
||||
}
|
||||
_playerXpPercentLost[level] = parseDouble(attrs, "val");
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public double getXpPercent(final int level)
|
||||
{
|
||||
if (level > _maxlevel)
|
||||
{
|
||||
LOGGER.warning("Require to high level inside PlayerXpPercentLostData (" + level + ")");
|
||||
return _playerXpPercentLost[_maxlevel];
|
||||
}
|
||||
return _playerXpPercentLost[level];
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of PlayerXpPercentLostData.
|
||||
* @return single instance of PlayerXpPercentLostData.
|
||||
*/
|
||||
public static PlayerXpPercentLostData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final PlayerXpPercentLostData _instance = new PlayerXpPercentLostData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,149 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.datatables.ItemTable;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
|
||||
import com.l2jmobius.gameserver.model.items.L2Item;
|
||||
import com.l2jmobius.gameserver.model.primeshop.PrimeShopGroup;
|
||||
import com.l2jmobius.gameserver.model.primeshop.PrimeShopItem;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.primeshop.ExBRProductInfo;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author Gnacik, UnAfraid
|
||||
*/
|
||||
public class PrimeShopData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, PrimeShopGroup> _primeItems = new LinkedHashMap<>();
|
||||
|
||||
protected PrimeShopData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_primeItems.clear();
|
||||
parseDatapackFile("PrimeShop.xml");
|
||||
|
||||
if (_primeItems.size() > 0)
|
||||
{
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _primeItems.size() + " items");
|
||||
}
|
||||
else
|
||||
{
|
||||
LOGGER.info(getClass().getSimpleName() + ": System is disabled.");
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap at = n.getAttributes();
|
||||
final Node attribute = at.getNamedItem("enabled");
|
||||
if ((attribute != null) && Boolean.parseBoolean(attribute.getNodeValue()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
NamedNodeMap attrs = d.getAttributes();
|
||||
Node att;
|
||||
final StatsSet set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
|
||||
final List<PrimeShopItem> items = new ArrayList<>();
|
||||
for (Node b = d.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
attrs = b.getAttributes();
|
||||
|
||||
final int itemId = parseInteger(attrs, "itemId");
|
||||
final int count = parseInteger(attrs, "count");
|
||||
|
||||
final L2Item item = ItemTable.getInstance().getTemplate(itemId);
|
||||
if (item == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Item template null for itemId: " + itemId + " brId: " + set.getInt("id"));
|
||||
return;
|
||||
}
|
||||
|
||||
items.add(new PrimeShopItem(itemId, count, item.getWeight(), item.isTradeable() ? 1 : 0));
|
||||
}
|
||||
}
|
||||
|
||||
_primeItems.put(set.getInt("id"), new PrimeShopGroup(set, items));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void showProductInfo(L2PcInstance player, int brId)
|
||||
{
|
||||
final PrimeShopGroup item = _primeItems.get(brId);
|
||||
|
||||
if ((player == null) || (item == null))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
player.sendPacket(new ExBRProductInfo(item));
|
||||
}
|
||||
|
||||
public PrimeShopGroup getItem(int brId)
|
||||
{
|
||||
return _primeItems.get(brId);
|
||||
}
|
||||
|
||||
public Map<Integer, PrimeShopGroup> getPrimeItems()
|
||||
{
|
||||
return _primeItems;
|
||||
}
|
||||
|
||||
public static PrimeShopData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final PrimeShopData _instance = new PrimeShopData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,279 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.L2RecipeInstance;
|
||||
import com.l2jmobius.gameserver.model.L2RecipeList;
|
||||
import com.l2jmobius.gameserver.model.L2RecipeStatInstance;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* The Class RecipeData.
|
||||
* @author Zoey76
|
||||
*/
|
||||
public class RecipeData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2RecipeList> _recipes = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new recipe data.
|
||||
*/
|
||||
protected RecipeData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_recipes.clear();
|
||||
parseDatapackFile("recipes.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _recipes.size() + " recipes.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
// TODO: Cleanup checks enforced by XSD.
|
||||
final List<L2RecipeInstance> recipePartList = new ArrayList<>();
|
||||
final List<L2RecipeStatInstance> recipeStatUseList = new ArrayList<>();
|
||||
final List<L2RecipeStatInstance> recipeAltStatChangeList = new ArrayList<>();
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
RECIPES_FILE: for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("item".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
recipePartList.clear();
|
||||
recipeStatUseList.clear();
|
||||
recipeAltStatChangeList.clear();
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
Node att;
|
||||
int id = -1;
|
||||
boolean haveRare = false;
|
||||
final StatsSet set = new StatsSet();
|
||||
|
||||
att = attrs.getNamedItem("id");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing id for recipe item, skipping");
|
||||
continue;
|
||||
}
|
||||
id = Integer.parseInt(att.getNodeValue());
|
||||
set.set("id", id);
|
||||
|
||||
att = attrs.getNamedItem("recipeId");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing recipeId for recipe item id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
set.set("recipeId", Integer.parseInt(att.getNodeValue()));
|
||||
|
||||
att = attrs.getNamedItem("name");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing name for recipe item id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
set.set("recipeName", att.getNodeValue());
|
||||
|
||||
att = attrs.getNamedItem("craftLevel");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing level for recipe item id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
set.set("craftLevel", Integer.parseInt(att.getNodeValue()));
|
||||
|
||||
att = attrs.getNamedItem("type");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing type for recipe item id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
set.set("isDwarvenRecipe", att.getNodeValue().equalsIgnoreCase("dwarven"));
|
||||
|
||||
att = attrs.getNamedItem("successRate");
|
||||
if (att == null)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Missing successRate for recipe item id: " + id + ", skipping");
|
||||
continue;
|
||||
}
|
||||
set.set("successRate", Integer.parseInt(att.getNodeValue()));
|
||||
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("statUse".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
final String statName = c.getAttributes().getNamedItem("name").getNodeValue();
|
||||
final int value = Integer.parseInt(c.getAttributes().getNamedItem("value").getNodeValue());
|
||||
try
|
||||
{
|
||||
recipeStatUseList.add(new L2RecipeStatInstance(statName, value));
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Error in StatUse parameter for recipe item id: " + id + ", skipping");
|
||||
continue RECIPES_FILE;
|
||||
}
|
||||
}
|
||||
else if ("altStatChange".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
final String statName = c.getAttributes().getNamedItem("name").getNodeValue();
|
||||
final int value = Integer.parseInt(c.getAttributes().getNamedItem("value").getNodeValue());
|
||||
try
|
||||
{
|
||||
recipeAltStatChangeList.add(new L2RecipeStatInstance(statName, value));
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
LOGGER.severe(getClass().getSimpleName() + ": Error in AltStatChange parameter for recipe item id: " + id + ", skipping");
|
||||
continue RECIPES_FILE;
|
||||
}
|
||||
}
|
||||
else if ("ingredient".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
final int ingId = Integer.parseInt(c.getAttributes().getNamedItem("id").getNodeValue());
|
||||
final int ingCount = Integer.parseInt(c.getAttributes().getNamedItem("count").getNodeValue());
|
||||
recipePartList.add(new L2RecipeInstance(ingId, ingCount));
|
||||
}
|
||||
else if ("production".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
set.set("itemId", Integer.parseInt(c.getAttributes().getNamedItem("id").getNodeValue()));
|
||||
set.set("count", Integer.parseInt(c.getAttributes().getNamedItem("count").getNodeValue()));
|
||||
}
|
||||
else if ("productionRare".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
set.set("rareItemId", Integer.parseInt(c.getAttributes().getNamedItem("id").getNodeValue()));
|
||||
set.set("rareCount", Integer.parseInt(c.getAttributes().getNamedItem("count").getNodeValue()));
|
||||
set.set("rarity", Integer.parseInt(c.getAttributes().getNamedItem("rarity").getNodeValue()));
|
||||
haveRare = true;
|
||||
}
|
||||
}
|
||||
|
||||
final L2RecipeList recipeList = new L2RecipeList(set, haveRare);
|
||||
for (L2RecipeInstance recipePart : recipePartList)
|
||||
{
|
||||
recipeList.addRecipe(recipePart);
|
||||
}
|
||||
for (L2RecipeStatInstance recipeStatUse : recipeStatUseList)
|
||||
{
|
||||
recipeList.addStatUse(recipeStatUse);
|
||||
}
|
||||
for (L2RecipeStatInstance recipeAltStatChange : recipeAltStatChangeList)
|
||||
{
|
||||
recipeList.addAltStatChange(recipeAltStatChange);
|
||||
}
|
||||
|
||||
_recipes.put(id, recipeList);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the recipe list.
|
||||
* @param listId the list id
|
||||
* @return the recipe list
|
||||
*/
|
||||
public L2RecipeList getRecipeList(int listId)
|
||||
{
|
||||
return _recipes.get(listId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the recipe by item id.
|
||||
* @param itemId the item id
|
||||
* @return the recipe by item id
|
||||
*/
|
||||
public L2RecipeList getRecipeByItemId(int itemId)
|
||||
{
|
||||
for (L2RecipeList find : _recipes.values())
|
||||
{
|
||||
if (find.getRecipeId() == itemId)
|
||||
{
|
||||
return find;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the all item ids.
|
||||
* @return the all item ids
|
||||
*/
|
||||
public int[] getAllItemIds()
|
||||
{
|
||||
final int[] idList = new int[_recipes.size()];
|
||||
int i = 0;
|
||||
for (L2RecipeList rec : _recipes.values())
|
||||
{
|
||||
idList[i++] = rec.getRecipeId();
|
||||
}
|
||||
return idList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the valid recipe list.
|
||||
* @param player the player
|
||||
* @param id the recipe list id
|
||||
* @return the valid recipe list
|
||||
*/
|
||||
public L2RecipeList getValidRecipeList(L2PcInstance player, int id)
|
||||
{
|
||||
final L2RecipeList recipeList = _recipes.get(id);
|
||||
if ((recipeList == null) || (recipeList.getRecipes().length == 0))
|
||||
{
|
||||
player.sendMessage(getClass().getSimpleName() + ": No recipe for: " + id);
|
||||
player.isInCraftMode(false);
|
||||
return null;
|
||||
}
|
||||
return recipeList;
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of RecipeData.
|
||||
* @return single instance of RecipeData
|
||||
*/
|
||||
public static RecipeData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
/**
|
||||
* The Class SingletonHolder.
|
||||
*/
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final RecipeData _instance = new RecipeData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,140 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.io.File;
|
||||
import java.util.HashSet;
|
||||
import java.util.Set;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Secondary Auth data.
|
||||
* @author NosBit
|
||||
*/
|
||||
public class SecondaryAuthData implements IXmlReader
|
||||
{
|
||||
private final Set<String> _forbiddenPasswords = new HashSet<>();
|
||||
private boolean _enabled = false;
|
||||
private int _maxAttempts = 5;
|
||||
private int _banTime = 480;
|
||||
private String _recoveryLink = "";
|
||||
|
||||
protected SecondaryAuthData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_forbiddenPasswords.clear();
|
||||
parseFile(new File("config/SecondaryAuth.xml"));
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _forbiddenPasswords.size() + " forbidden passwords.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
try
|
||||
{
|
||||
for (Node node = doc.getFirstChild(); node != null; node = node.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(node.getNodeName()))
|
||||
{
|
||||
for (Node list_node = node.getFirstChild(); list_node != null; list_node = list_node.getNextSibling())
|
||||
{
|
||||
if ("enabled".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
_enabled = Boolean.parseBoolean(list_node.getTextContent());
|
||||
}
|
||||
else if ("maxAttempts".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
_maxAttempts = Integer.parseInt(list_node.getTextContent());
|
||||
}
|
||||
else if ("banTime".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
_banTime = Integer.parseInt(list_node.getTextContent());
|
||||
}
|
||||
else if ("recoveryLink".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
_recoveryLink = list_node.getTextContent();
|
||||
}
|
||||
else if ("forbiddenPasswords".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
for (Node forbiddenPasswords_node = list_node.getFirstChild(); forbiddenPasswords_node != null; forbiddenPasswords_node = forbiddenPasswords_node.getNextSibling())
|
||||
{
|
||||
if ("password".equalsIgnoreCase(forbiddenPasswords_node.getNodeName()))
|
||||
{
|
||||
_forbiddenPasswords.add(forbiddenPasswords_node.getTextContent());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, "Failed to load secondary auth data from xml.", e);
|
||||
}
|
||||
}
|
||||
|
||||
public boolean isEnabled()
|
||||
{
|
||||
return _enabled;
|
||||
}
|
||||
|
||||
public int getMaxAttempts()
|
||||
{
|
||||
return _maxAttempts;
|
||||
}
|
||||
|
||||
public int getBanTime()
|
||||
{
|
||||
return _banTime;
|
||||
}
|
||||
|
||||
public String getRecoveryLink()
|
||||
{
|
||||
return _recoveryLink;
|
||||
}
|
||||
|
||||
public Set<String> getForbiddenPasswords()
|
||||
{
|
||||
return _forbiddenPasswords;
|
||||
}
|
||||
|
||||
public boolean isForbiddenPassword(String password)
|
||||
{
|
||||
return _forbiddenPasswords.contains(password);
|
||||
}
|
||||
|
||||
public static SecondaryAuthData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final SecondaryAuthData _instance = new SecondaryAuthData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,199 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.Location;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.VehiclePathPoint;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2ShuttleInstance;
|
||||
import com.l2jmobius.gameserver.model.actor.templates.L2CharTemplate;
|
||||
import com.l2jmobius.gameserver.model.shuttle.L2ShuttleData;
|
||||
import com.l2jmobius.gameserver.model.shuttle.L2ShuttleEngine;
|
||||
import com.l2jmobius.gameserver.model.shuttle.L2ShuttleStop;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public final class ShuttleData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2ShuttleData> _shuttles = new HashMap<>();
|
||||
private final Map<Integer, L2ShuttleInstance> _shuttleInstances = new HashMap<>();
|
||||
|
||||
protected ShuttleData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
if (!_shuttleInstances.isEmpty())
|
||||
{
|
||||
for (L2ShuttleInstance shuttle : _shuttleInstances.values())
|
||||
{
|
||||
shuttle.deleteMe();
|
||||
}
|
||||
_shuttleInstances.clear();
|
||||
}
|
||||
parseDatapackFile("shuttledata.xml");
|
||||
init();
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _shuttles.size() + " Shuttles.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
NamedNodeMap attrs;
|
||||
StatsSet set;
|
||||
Node att;
|
||||
L2ShuttleData data;
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("shuttle".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
attrs = d.getAttributes();
|
||||
set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
data = new L2ShuttleData(set);
|
||||
for (Node b = d.getFirstChild(); b != null; b = b.getNextSibling())
|
||||
{
|
||||
if ("doors".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
for (Node a = b.getFirstChild(); a != null; a = a.getNextSibling())
|
||||
{
|
||||
if ("door".equalsIgnoreCase(a.getNodeName()))
|
||||
{
|
||||
attrs = a.getAttributes();
|
||||
data.addDoor(parseInteger(attrs, "id"));
|
||||
}
|
||||
}
|
||||
}
|
||||
else if ("stops".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
for (Node a = b.getFirstChild(); a != null; a = a.getNextSibling())
|
||||
{
|
||||
if ("stop".equalsIgnoreCase(a.getNodeName()))
|
||||
{
|
||||
attrs = a.getAttributes();
|
||||
final L2ShuttleStop stop = new L2ShuttleStop(parseInteger(attrs, "id"));
|
||||
|
||||
for (Node z = a.getFirstChild(); z != null; z = z.getNextSibling())
|
||||
{
|
||||
if ("dimension".equalsIgnoreCase(z.getNodeName()))
|
||||
{
|
||||
attrs = z.getAttributes();
|
||||
stop.addDimension(new Location(parseInteger(attrs, "x"), parseInteger(attrs, "y"), parseInteger(attrs, "z")));
|
||||
}
|
||||
}
|
||||
data.addStop(stop);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if ("routes".equalsIgnoreCase(b.getNodeName()))
|
||||
{
|
||||
for (Node a = b.getFirstChild(); a != null; a = a.getNextSibling())
|
||||
{
|
||||
if ("route".equalsIgnoreCase(a.getNodeName()))
|
||||
{
|
||||
attrs = a.getAttributes();
|
||||
final List<Location> locs = new ArrayList<>();
|
||||
for (Node z = a.getFirstChild(); z != null; z = z.getNextSibling())
|
||||
{
|
||||
if ("loc".equalsIgnoreCase(z.getNodeName()))
|
||||
{
|
||||
attrs = z.getAttributes();
|
||||
locs.add(new Location(parseInteger(attrs, "x"), parseInteger(attrs, "y"), parseInteger(attrs, "z")));
|
||||
}
|
||||
}
|
||||
|
||||
final VehiclePathPoint[] route = new VehiclePathPoint[locs.size()];
|
||||
int i = 0;
|
||||
for (Location loc : locs)
|
||||
{
|
||||
route[i++] = new VehiclePathPoint(loc);
|
||||
}
|
||||
data.addRoute(route);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_shuttles.put(data.getId(), data);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void init()
|
||||
{
|
||||
for (L2ShuttleData data : _shuttles.values())
|
||||
{
|
||||
final L2ShuttleInstance shuttle = new L2ShuttleInstance(new L2CharTemplate(new StatsSet()));
|
||||
shuttle.setData(data);
|
||||
shuttle.setHeading(data.getLocation().getHeading());
|
||||
shuttle.setLocationInvisible(data.getLocation());
|
||||
shuttle.spawnMe();
|
||||
shuttle.getStat().setMoveSpeed(300);
|
||||
shuttle.getStat().setRotationSpeed(0);
|
||||
shuttle.registerEngine(new L2ShuttleEngine(data, shuttle));
|
||||
shuttle.runEngine(1000);
|
||||
_shuttleInstances.put(shuttle.getObjectId(), shuttle);
|
||||
}
|
||||
}
|
||||
|
||||
public L2ShuttleInstance getShuttle(int id)
|
||||
{
|
||||
for (L2ShuttleInstance shuttle : _shuttleInstances.values())
|
||||
{
|
||||
if ((shuttle.getObjectId() == id) || (shuttle.getId() == id))
|
||||
{
|
||||
return shuttle;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public static ShuttleData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final ShuttleData _instance = new ShuttleData();
|
||||
}
|
||||
}
|
@@ -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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Calendar;
|
||||
import java.util.List;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.SiegeScheduleDate;
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.util.Util;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Siege Schedule data.
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public class SiegeScheduleData implements IXmlReader
|
||||
{
|
||||
private final List<SiegeScheduleDate> _scheduleData = new ArrayList<>();
|
||||
|
||||
protected SiegeScheduleData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_scheduleData.clear();
|
||||
parseDatapackFile("../config/SiegeSchedule.xml");
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _scheduleData.size() + " siege schedulers.");
|
||||
if (_scheduleData.isEmpty())
|
||||
{
|
||||
_scheduleData.add(new SiegeScheduleDate(new StatsSet()));
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Emergency Loaded: " + _scheduleData.size() + " default siege schedulers.");
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node cd = n.getFirstChild(); cd != null; cd = cd.getNextSibling())
|
||||
{
|
||||
switch (cd.getNodeName())
|
||||
{
|
||||
case "schedule":
|
||||
{
|
||||
final StatsSet set = new StatsSet();
|
||||
final NamedNodeMap attrs = cd.getAttributes();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node node = attrs.item(i);
|
||||
final String key = node.getNodeName();
|
||||
String val = node.getNodeValue();
|
||||
if ("day".equals(key))
|
||||
{
|
||||
if (!Util.isDigit(val))
|
||||
{
|
||||
val = Integer.toString(getValueForField(val));
|
||||
}
|
||||
}
|
||||
set.set(key, val);
|
||||
}
|
||||
_scheduleData.add(new SiegeScheduleDate(set));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private int getValueForField(String field)
|
||||
{
|
||||
try
|
||||
{
|
||||
return Calendar.class.getField(field).getInt(Calendar.class);
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
LOGGER.log(Level.WARNING, "", e);
|
||||
return -1;
|
||||
}
|
||||
}
|
||||
|
||||
public List<SiegeScheduleDate> getScheduleDates()
|
||||
{
|
||||
return _scheduleData;
|
||||
}
|
||||
|
||||
public static final SiegeScheduleData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final SiegeScheduleData _instance = new SiegeScheduleData();
|
||||
}
|
||||
|
||||
}
|
@@ -0,0 +1,99 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.base.ClassId;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Holds all skill learn data for all NPCs.
|
||||
* @author xban1x
|
||||
*/
|
||||
public final class SkillLearnData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, List<ClassId>> _skillLearn = new HashMap<>();
|
||||
|
||||
protected SkillLearnData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_skillLearn.clear();
|
||||
parseDatapackFile("skillLearn.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _skillLearn.size() + " Skill Learn data.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node node = doc.getFirstChild(); node != null; node = node.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(node.getNodeName()))
|
||||
{
|
||||
for (Node list_node = node.getFirstChild(); list_node != null; list_node = list_node.getNextSibling())
|
||||
{
|
||||
if ("npc".equalsIgnoreCase(list_node.getNodeName()))
|
||||
{
|
||||
final List<ClassId> classIds = new ArrayList<>();
|
||||
for (Node c = list_node.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("classId".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
classIds.add(ClassId.getClassId(Integer.parseInt(c.getTextContent())));
|
||||
}
|
||||
}
|
||||
_skillLearn.put(parseInteger(list_node.getAttributes(), "id"), classIds);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @param npcId
|
||||
* @return {@link List} of {@link ClassId}'s that this npcId can teach.
|
||||
*/
|
||||
public List<ClassId> getSkillLearnData(int npcId)
|
||||
{
|
||||
return _skillLearn.get(npcId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of SkillLearnData.
|
||||
* @return single instance of SkillLearnData
|
||||
*/
|
||||
public static SkillLearnData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final SkillLearnData _instance = new SkillLearnData();
|
||||
}
|
||||
}
|
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,117 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2StaticObjectInstance;
|
||||
import com.l2jmobius.gameserver.model.actor.templates.L2CharTemplate;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* This class loads and holds all static object data.
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public final class StaticObjectData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, L2StaticObjectInstance> _staticObjects = new HashMap<>();
|
||||
|
||||
/**
|
||||
* Instantiates a new static objects.
|
||||
*/
|
||||
protected StaticObjectData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_staticObjects.clear();
|
||||
parseDatapackFile("staticObjects.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _staticObjects.size() + " static object templates.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("object".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = d.getAttributes();
|
||||
final StatsSet set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
addObject(set);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Initialize an static object based on the stats set and add it to the map.
|
||||
* @param set the stats set to add.
|
||||
*/
|
||||
private void addObject(StatsSet set)
|
||||
{
|
||||
final L2StaticObjectInstance obj = new L2StaticObjectInstance(new L2CharTemplate(new StatsSet()), set.getInt("id"));
|
||||
obj.setType(set.getInt("type", 0));
|
||||
obj.setName(set.getString("name"));
|
||||
obj.setMap(set.getString("texture", "none"), set.getInt("map_x", 0), set.getInt("map_y", 0));
|
||||
obj.spawnMe(set.getInt("x"), set.getInt("y"), set.getInt("z"));
|
||||
_staticObjects.put(obj.getObjectId(), obj);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the static objects.
|
||||
* @return a collection of static objects.
|
||||
*/
|
||||
public Collection<L2StaticObjectInstance> getStaticObjects()
|
||||
{
|
||||
return _staticObjects.values();
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of StaticObjects.
|
||||
* @return single instance of StaticObjects
|
||||
*/
|
||||
public static StaticObjectData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final StaticObjectData _instance = new StaticObjectData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,113 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.teleporter.TeleportHolder;
|
||||
import com.l2jmobius.gameserver.model.teleporter.TeleportLocation;
|
||||
import com.l2jmobius.gameserver.model.teleporter.TeleportType;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public class TeleportersData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, TeleportHolder> _teleporters = new HashMap<>();
|
||||
|
||||
protected TeleportersData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_teleporters.clear();
|
||||
parseDatapackDirectory("teleporters", true);
|
||||
LOGGER.log(Level.INFO, "Loaded: " + _teleporters.size() + " npc teleporters.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node listNode = doc.getFirstChild(); listNode != null; listNode = listNode.getNextSibling())
|
||||
{
|
||||
if ("list".equals(listNode.getNodeName()))
|
||||
{
|
||||
for (Node npcNode = listNode.getFirstChild(); npcNode != null; npcNode = npcNode.getNextSibling())
|
||||
{
|
||||
if ("npc".equals(npcNode.getNodeName()))
|
||||
{
|
||||
final int id = parseInteger(npcNode.getAttributes(), "id");
|
||||
final TeleportHolder holder = new TeleportHolder(id);
|
||||
for (Node tpNode = npcNode.getFirstChild(); tpNode != null; tpNode = tpNode.getNextSibling())
|
||||
{
|
||||
if ("teleport".equals(tpNode.getNodeName()))
|
||||
{
|
||||
final TeleportType type = parseEnum(tpNode.getAttributes(), TeleportType.class, "type", TeleportType.NORMAL);
|
||||
for (Node locNode = tpNode.getFirstChild(); locNode != null; locNode = locNode.getNextSibling())
|
||||
{
|
||||
if ("location".equals(locNode.getNodeName()))
|
||||
{
|
||||
final NamedNodeMap attrs = locNode.getAttributes();
|
||||
final int nextId = holder.getLocations(type).size() + 1;
|
||||
final StatsSet set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node locationNode = attrs.item(i);
|
||||
set.set(locationNode.getNodeName(), locationNode.getNodeValue());
|
||||
}
|
||||
holder.addLocation(type, new TeleportLocation(nextId, set));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_teleporters.put(id, holder);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public TeleportHolder getHolder(int npcId)
|
||||
{
|
||||
return _teleporters.get(npcId);
|
||||
}
|
||||
|
||||
/**
|
||||
* Gets the single instance of TeleportersData.
|
||||
* @return single instance of TeleportersData
|
||||
*/
|
||||
public static TeleportersData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final TeleportersData _instance = new TeleportersData();
|
||||
}
|
||||
}
|
@@ -0,0 +1,244 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Level;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.NamedNodeMap;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.StatsSet;
|
||||
import com.l2jmobius.gameserver.model.actor.instance.L2PcInstance;
|
||||
import com.l2jmobius.gameserver.model.actor.transform.Transform;
|
||||
import com.l2jmobius.gameserver.model.actor.transform.TransformLevelData;
|
||||
import com.l2jmobius.gameserver.model.actor.transform.TransformTemplate;
|
||||
import com.l2jmobius.gameserver.model.holders.AdditionalItemHolder;
|
||||
import com.l2jmobius.gameserver.model.holders.AdditionalSkillHolder;
|
||||
import com.l2jmobius.gameserver.model.holders.SkillHolder;
|
||||
import com.l2jmobius.gameserver.network.serverpackets.ExBasicActionList;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* Transformation data.
|
||||
* @author UnAfraid
|
||||
*/
|
||||
public final class TransformData implements IXmlReader
|
||||
{
|
||||
private final Map<Integer, Transform> _transformData = new HashMap<>();
|
||||
|
||||
protected TransformData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public synchronized void load()
|
||||
{
|
||||
_transformData.clear();
|
||||
parseDatapackDirectory("stats/transformations", false);
|
||||
LOGGER.log(Level.INFO, getClass().getSimpleName() + ": Loaded: " + _transformData.size() + " transform templates.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("transform".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
NamedNodeMap attrs = d.getAttributes();
|
||||
final StatsSet set = new StatsSet();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
final Transform transform = new Transform(set);
|
||||
for (Node cd = d.getFirstChild(); cd != null; cd = cd.getNextSibling())
|
||||
{
|
||||
final boolean isMale = "Male".equalsIgnoreCase(cd.getNodeName());
|
||||
if ("Male".equalsIgnoreCase(cd.getNodeName()) || "Female".equalsIgnoreCase(cd.getNodeName()))
|
||||
{
|
||||
TransformTemplate templateData = null;
|
||||
for (Node z = cd.getFirstChild(); z != null; z = z.getNextSibling())
|
||||
{
|
||||
switch (z.getNodeName())
|
||||
{
|
||||
case "common":
|
||||
{
|
||||
for (Node s = z.getFirstChild(); s != null; s = s.getNextSibling())
|
||||
{
|
||||
switch (s.getNodeName())
|
||||
{
|
||||
case "base":
|
||||
case "stats":
|
||||
case "defense":
|
||||
case "magicDefense":
|
||||
case "collision":
|
||||
case "moving":
|
||||
{
|
||||
attrs = s.getAttributes();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
set.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
templateData = new TransformTemplate(set);
|
||||
transform.setTemplate(isMale, templateData);
|
||||
break;
|
||||
}
|
||||
case "skills":
|
||||
{
|
||||
if (templateData == null)
|
||||
{
|
||||
templateData = new TransformTemplate(set);
|
||||
transform.setTemplate(isMale, templateData);
|
||||
}
|
||||
for (Node s = z.getFirstChild(); s != null; s = s.getNextSibling())
|
||||
{
|
||||
if ("skill".equals(s.getNodeName()))
|
||||
{
|
||||
attrs = s.getAttributes();
|
||||
final int skillId = parseInteger(attrs, "id");
|
||||
final int skillLevel = parseInteger(attrs, "level");
|
||||
templateData.addSkill(new SkillHolder(skillId, skillLevel));
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "actions":
|
||||
{
|
||||
if (templateData == null)
|
||||
{
|
||||
templateData = new TransformTemplate(set);
|
||||
transform.setTemplate(isMale, templateData);
|
||||
}
|
||||
set.set("actions", z.getTextContent());
|
||||
final int[] actions = set.getIntArray("actions", " ");
|
||||
templateData.setBasicActionList(new ExBasicActionList(actions));
|
||||
break;
|
||||
}
|
||||
case "additionalSkills":
|
||||
{
|
||||
if (templateData == null)
|
||||
{
|
||||
templateData = new TransformTemplate(set);
|
||||
transform.setTemplate(isMale, templateData);
|
||||
}
|
||||
for (Node s = z.getFirstChild(); s != null; s = s.getNextSibling())
|
||||
{
|
||||
if ("skill".equals(s.getNodeName()))
|
||||
{
|
||||
attrs = s.getAttributes();
|
||||
final int skillId = parseInteger(attrs, "id");
|
||||
final int skillLevel = parseInteger(attrs, "level");
|
||||
final int minLevel = parseInteger(attrs, "minLevel");
|
||||
templateData.addAdditionalSkill(new AdditionalSkillHolder(skillId, skillLevel, minLevel));
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "items":
|
||||
{
|
||||
if (templateData == null)
|
||||
{
|
||||
templateData = new TransformTemplate(set);
|
||||
transform.setTemplate(isMale, templateData);
|
||||
}
|
||||
for (Node s = z.getFirstChild(); s != null; s = s.getNextSibling())
|
||||
{
|
||||
if ("item".equals(s.getNodeName()))
|
||||
{
|
||||
attrs = s.getAttributes();
|
||||
final int itemId = parseInteger(attrs, "id");
|
||||
final boolean allowed = parseBoolean(attrs, "allowed");
|
||||
templateData.addAdditionalItem(new AdditionalItemHolder(itemId, allowed));
|
||||
}
|
||||
}
|
||||
break;
|
||||
}
|
||||
case "levels":
|
||||
{
|
||||
if (templateData == null)
|
||||
{
|
||||
templateData = new TransformTemplate(set);
|
||||
transform.setTemplate(isMale, templateData);
|
||||
}
|
||||
|
||||
final StatsSet levelsSet = new StatsSet();
|
||||
for (Node s = z.getFirstChild(); s != null; s = s.getNextSibling())
|
||||
{
|
||||
if ("level".equals(s.getNodeName()))
|
||||
{
|
||||
attrs = s.getAttributes();
|
||||
for (int i = 0; i < attrs.getLength(); i++)
|
||||
{
|
||||
final Node att = attrs.item(i);
|
||||
levelsSet.set(att.getNodeName(), att.getNodeValue());
|
||||
}
|
||||
}
|
||||
}
|
||||
templateData.addLevelData(new TransformLevelData(levelsSet));
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_transformData.put(transform.getId(), transform);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public Transform getTransform(int id)
|
||||
{
|
||||
return _transformData.get(id);
|
||||
}
|
||||
|
||||
public boolean transformPlayer(int id, L2PcInstance player)
|
||||
{
|
||||
final Transform transform = getTransform(id);
|
||||
if (transform != null)
|
||||
{
|
||||
player.transform(transform);
|
||||
}
|
||||
return transform != null;
|
||||
}
|
||||
|
||||
public static TransformData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final TransformData _instance = new TransformData();
|
||||
}
|
||||
}
|
193
trunk/java/com/l2jmobius/gameserver/data/xml/impl/UIData.java
Normal file
193
trunk/java/com/l2jmobius/gameserver/data/xml/impl/UIData.java
Normal file
@@ -0,0 +1,193 @@
|
||||
/*
|
||||
* 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.data.xml.impl;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.logging.Logger;
|
||||
|
||||
import org.w3c.dom.Document;
|
||||
import org.w3c.dom.Node;
|
||||
|
||||
import com.l2jmobius.gameserver.model.ActionKey;
|
||||
import com.l2jmobius.util.data.xml.IXmlReader;
|
||||
|
||||
/**
|
||||
* UI Data parser.
|
||||
* @author Zoey76
|
||||
*/
|
||||
public class UIData implements IXmlReader
|
||||
{
|
||||
private static final Logger LOGGER = Logger.getLogger(UIData.class.getName());
|
||||
|
||||
private final Map<Integer, List<ActionKey>> _storedKeys = new HashMap<>();
|
||||
private final Map<Integer, List<Integer>> _storedCategories = new HashMap<>();
|
||||
|
||||
protected UIData()
|
||||
{
|
||||
load();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load()
|
||||
{
|
||||
_storedKeys.clear();
|
||||
_storedCategories.clear();
|
||||
parseDatapackFile("ui/ui_en.xml");
|
||||
LOGGER.info(getClass().getSimpleName() + ": Loaded " + _storedKeys.size() + " keys " + _storedCategories.size() + " categories.");
|
||||
}
|
||||
|
||||
@Override
|
||||
public void parseDocument(Document doc)
|
||||
{
|
||||
for (Node n = doc.getFirstChild(); n != null; n = n.getNextSibling())
|
||||
{
|
||||
if ("list".equalsIgnoreCase(n.getNodeName()))
|
||||
{
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("category".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
parseCategory(d);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void parseCategory(Node n)
|
||||
{
|
||||
final int cat = parseInteger(n.getAttributes(), "id");
|
||||
for (Node d = n.getFirstChild(); d != null; d = d.getNextSibling())
|
||||
{
|
||||
if ("commands".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
parseCommands(cat, d);
|
||||
}
|
||||
else if ("keys".equalsIgnoreCase(d.getNodeName()))
|
||||
{
|
||||
parseKeys(cat, d);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void parseCommands(int cat, Node d)
|
||||
{
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("cmd".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
addCategory(_storedCategories, cat, Integer.parseInt(c.getTextContent()));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private void parseKeys(int cat, Node d)
|
||||
{
|
||||
for (Node c = d.getFirstChild(); c != null; c = c.getNextSibling())
|
||||
{
|
||||
if ("key".equalsIgnoreCase(c.getNodeName()))
|
||||
{
|
||||
final ActionKey akey = new ActionKey(cat);
|
||||
for (int i = 0; i < c.getAttributes().getLength(); i++)
|
||||
{
|
||||
final Node att = c.getAttributes().item(i);
|
||||
final int val = Integer.parseInt(att.getNodeValue());
|
||||
switch (att.getNodeName())
|
||||
{
|
||||
case "cmd":
|
||||
{
|
||||
akey.setCommandId(val);
|
||||
break;
|
||||
}
|
||||
case "key":
|
||||
{
|
||||
akey.setKeyId(val);
|
||||
break;
|
||||
}
|
||||
case "toggleKey1":
|
||||
{
|
||||
akey.setToogleKey1(val);
|
||||
break;
|
||||
}
|
||||
case "toggleKey2":
|
||||
{
|
||||
akey.setToogleKey2(val);
|
||||
break;
|
||||
}
|
||||
case "showType":
|
||||
{
|
||||
akey.setShowStatus(val);
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
addKey(_storedKeys, cat, akey);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Add a category to the stored categories.
|
||||
* @param map the map to store the category
|
||||
* @param cat the category
|
||||
* @param cmd the command
|
||||
*/
|
||||
public static void addCategory(Map<Integer, List<Integer>> map, int cat, int cmd)
|
||||
{
|
||||
map.computeIfAbsent(cat, k -> new ArrayList<>()).add(cmd);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create and insert an Action Key into the stored keys.
|
||||
* @param map the map to store the key
|
||||
* @param cat the category
|
||||
* @param akey the action key
|
||||
*/
|
||||
public static void addKey(Map<Integer, List<ActionKey>> map, int cat, ActionKey akey)
|
||||
{
|
||||
map.computeIfAbsent(cat, k -> new ArrayList<>()).add(akey);
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the categories
|
||||
*/
|
||||
public Map<Integer, List<Integer>> getCategories()
|
||||
{
|
||||
return _storedCategories;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return the keys
|
||||
*/
|
||||
public Map<Integer, List<ActionKey>> getKeys()
|
||||
{
|
||||
return _storedKeys;
|
||||
}
|
||||
|
||||
public static UIData getInstance()
|
||||
{
|
||||
return SingletonHolder._instance;
|
||||
}
|
||||
|
||||
private static class SingletonHolder
|
||||
{
|
||||
protected static final UIData _instance = new UIData();
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user