/* * This file is part of aion-unique <aion-unique.com>. * * aion-emu 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. * * aion-emu 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 aion-unique. If not, see <http://www.gnu.org/licenses/>. */ package com.aionemu.gameserver.model.gameobjects.stats; import com.aionemu.commons.callbacks.EnhancedObject; import com.aionemu.gameserver.configs.main.CustomConfig; import com.aionemu.gameserver.dataholders.PlayerStatsData; import com.aionemu.gameserver.model.gameobjects.player.Player; import com.aionemu.gameserver.model.gameobjects.stats.listeners.StatChangeListener; import com.aionemu.gameserver.model.templates.stats.PlayerStatsTemplate; import com.aionemu.gameserver.network.aion.serverpackets.SM_EMOTION; import com.aionemu.gameserver.network.aion.serverpackets.SM_STATS_INFO; import com.aionemu.gameserver.utils.PacketSendUtility; /** * @author xavier * */ public class PlayerGameStats extends CreatureGameStats<Player> { /** * * @param owner */ public PlayerGameStats(Player owner) { super(owner); } /** * * @param playerStatsData * @param owner */ public PlayerGameStats(PlayerStatsData playerStatsData, final Player owner) { super(owner); PlayerStatsTemplate pst = playerStatsData.getTemplate(owner.getPlayerClass(), owner.getLevel()); initStats(pst, owner.getLevel()); log.debug("loading base game stats for player " + owner.getName() + " (id " + owner.getObjectId() + "): " + this); addRecomputeListener(owner); } /** * Adds listener that will check SPEED, FLY_SPEED or ATTACK_SPEED changes * * @param owner */ private void addRecomputeListener(final Player owner) { ((EnhancedObject)this).addCallback(new StatChangeListener(this){ private int currentRunSpeed = 0; private int currentFlySpeed = 0; private int currentAttackSpeed = 0; @Override protected void onRecompute() { int newRunSpeed = gameStats.getCurrentStat(StatEnum.SPEED); int newFlySpeed = gameStats.getCurrentStat(StatEnum.FLY_SPEED); int newAttackSpeed = gameStats.getCurrentStat(StatEnum.ATTACK_SPEED); if(newRunSpeed != currentRunSpeed || currentFlySpeed != newFlySpeed || newAttackSpeed != currentAttackSpeed) { PacketSendUtility.broadcastPacket(owner, new SM_EMOTION(owner, 30, 0, 0), true); } PacketSendUtility.sendPacket(owner, new SM_STATS_INFO(owner)); this.currentRunSpeed = newRunSpeed; this.currentFlySpeed = newFlySpeed; this.currentAttackSpeed = newAttackSpeed; } }); } /** * * @param pst * @param level */ private void initStats(PlayerStatsTemplate pst, int level) { lock.writeLock().lock(); try { this.initStats(pst.getMaxHp(), pst.getMaxMp(), pst.getPower(), pst.getHealth(), pst.getAgility(), pst .getAccuracy(), pst.getKnowledge(), pst.getWill(), pst.getMainHandAttack(), pst.getMainHandCritRate(), Math .round(pst.getAttackSpeed() * 1000), 1500, Math.round(pst.getRunSpeed() * 1000), Math.round(pst.getFlySpeed() * 1000)); setAttackCounter(1); initStat(StatEnum.PARRY, pst.getParry()); initStat(StatEnum.BLOCK, pst.getBlock()); initStat(StatEnum.EVASION, pst.getEvasion()); initStat(StatEnum.MAGICAL_ACCURACY, pst.getMagicAccuracy()); initStat(StatEnum.MAIN_HAND_ACCURACY, pst.getMainHandAccuracy()); initStat(StatEnum.FLY_TIME, CustomConfig.BASE_FLYTIME); initStat(StatEnum.REGEN_HP, level + 3); initStat(StatEnum.REGEN_MP, level + 8); initStat(StatEnum.MAXDP, 4000); } finally { lock.writeLock().unlock(); } } /** * * @param maxHp * @param maxMp * @param power * @param health * @param agility * @param accuracy * @param knowledge * @param will * @param mainHandAttack * @param mainHandCritRate * @param attackSpeed * @param attackRange * @param runSpeed * @param flySpeed */ protected void initStats(int maxHp, int maxMp, int power, int health, int agility, int accuracy, int knowledge, int will, int mainHandAttack, int mainHandCritRate, int attackSpeed, int attackRange, int runSpeed, int flySpeed) { stats.clear(); initStat(StatEnum.MAXHP, maxHp); initStat(StatEnum.MAXMP, maxMp); initStat(StatEnum.POWER, power); initStat(StatEnum.ACCURACY, accuracy); initStat(StatEnum.HEALTH, health); initStat(StatEnum.AGILITY, agility); initStat(StatEnum.KNOWLEDGE, knowledge); initStat(StatEnum.WILL, will); initStat(StatEnum.MAIN_HAND_POWER, Math.round(18 * (power * 0.01f))); initStat(StatEnum.MAIN_HAND_CRITICAL, mainHandCritRate); initStat(StatEnum.OFF_HAND_POWER, 0); initStat(StatEnum.OFF_HAND_CRITICAL, 0); initStat(StatEnum.ATTACK_SPEED, attackSpeed); initStat(StatEnum.MAIN_HAND_ATTACK_SPEED, attackSpeed); initStat(StatEnum.OFF_HAND_ATTACK_SPEED, 0); initStat(StatEnum.ATTACK_RANGE, attackRange); initStat(StatEnum.PHYSICAL_DEFENSE, 0); initStat(StatEnum.PARRY, Math.round(agility * 3.1f - 248.5f + 12.4f * (int)owner.getLevel())); initStat(StatEnum.EVASION, Math.round(agility * 3.1f - 248.5f + 12.4f * (int)owner.getLevel())); initStat(StatEnum.BLOCK, Math.round(agility * 3.1f - 248.5f + 12.4f * (int)owner.getLevel())); initStat(StatEnum.DAMAGE_REDUCE, 0); initStat(StatEnum.MAIN_HAND_ACCURACY, Math.round((accuracy * 2 - 10) + 8 * (int)owner.getLevel())); initStat(StatEnum.OFF_HAND_ACCURACY, Math.round((accuracy * 2 - 10) + 8 * (int)owner.getLevel())); initStat(StatEnum.MAGICAL_RESIST, 0); initStat(StatEnum.WIND_RESISTANCE, 0); initStat(StatEnum.FIRE_RESISTANCE, 0); initStat(StatEnum.WATER_RESISTANCE, 0); initStat(StatEnum.EARTH_RESISTANCE, 0); initStat(StatEnum.MAGICAL_ACCURACY, Math.round(14.26f * (int)owner.getLevel())); initStat(StatEnum.BOOST_MAGICAL_SKILL, 0); initStat(StatEnum.SPEED, runSpeed); initStat(StatEnum.FLY_SPEED, flySpeed); initStat(StatEnum.PVP_ATTACK_RATIO, 0); initStat(StatEnum.PVP_DEFEND_RATIO, 0); initStat(StatEnum.BOOST_CASTING_TIME, 100); initStat(StatEnum.BOOST_HATE, 100); } /** * * @param playerStatsData * @param level */ public void doLevelUpgrade() { initStats(owner.getPlayerStatsTemplate(), owner.getLevel()); recomputeStats(); } }