/** * Calculates BLOCK chance * * @param attacker * @param attacked * @return int */ public static boolean calculatePhysicalBlockRate(Creature attacker, Creature attacked) { // check always block if (attacked.getObserveController().checkAttackStatus(AttackStatus.BLOCK)) { return true; } float accuracy = attacker.getGameStats().getMainHandPAccuracy().getCurrent(); float block = 0; if (attacked instanceof Player) { block = attacked.getGameStats().getBlock().getBonus() + getMovementModifier( attacked, StatEnum.BLOCK, attacked.getGameStats().getBlock().getBase()) + attacked.getGameStats().getStat(StatEnum.PVP_BLOCK, 0).getCurrent(); } else { block = attacked.getGameStats().getBlock().getBonus() + getMovementModifier( attacked, StatEnum.BLOCK, attacked.getGameStats().getBlock().getBase()); } float blockRate = block - accuracy; // blockRate = blockRate*0.6f+50; if (blockRate > 500) { blockRate = 500; } return Rnd.nextInt(1000) < blockRate; }
/** * Accuracy (includes evasion/parry/block formulas): Accuracy formula is based on opponents * evasion/parry/block vs your own Accuracy. If your Accuracy is 300 or more above opponents * evasion/parry/block then you can not be evaded, parried or blocked. <br> * https://docs.google.com/spreadsheet/ccc?key=0AqxBGNJV9RrzdF9tOWpwUlVLOXE5bVRWeHQtbGQxaUE&hl=en_US#gid=2 */ public static boolean calculatePhysicalEvasion(float diff, int upperCap) { diff = diff * 0.6f + 50; if (diff > upperCap) { diff = upperCap; } return Rnd.nextInt(1000) < diff; }
/** * Calculates MAGICAL CRITICAL chance * * @param attacker * @param attacke * @return boolean */ public static boolean calculateMagicalCriticalRate( Creature attacker, Creature attacked, int criticalProb) { if (attacker instanceof Servant || attacker instanceof Homing) { return false; } int critical = attacker.getGameStats().getMCritical().getCurrent(); if (attacked instanceof Player) { critical = attacked.getGameStats().getPositiveReverseStat(StatEnum.MAGICAL_CRITICAL_RESIST, critical) + attacked .getGameStats() .getPositiveReverseStat(StatEnum.PVP_MAGICAL_RESIST, critical); } else { critical = attacked .getGameStats() .getPositiveReverseStat(StatEnum.MAGICAL_CRITICAL_RESIST, critical); } // add critical Prob critical *= (float) criticalProb / 100f; double criticalRate; if (critical <= 440) { criticalRate = critical * 0.1f; } else if (critical <= 600) { criticalRate = (440 * 0.1f) + ((critical - 440) * 0.05f); } else { criticalRate = (440 * 0.1f) + (160 * 0.05f) + ((critical - 600) * 0.02f); } return Rnd.nextInt(100) < criticalRate; }
/** * Calculates CRITICAL chance * http://www.wolframalpha.com/input/?i=quadratic+fit+%7B%7B300%2C+30.97%7D%2C+%7B320%2C+31.68%7D%2C+%7B340%2C+33.30%7D%2C+%7B360%2C+36.09%7D%2C+%7B380%2C+37.81%7D%2C+%7B400%2C+40.72%7D%2C+%7B420%2C+42.12%7D%2C+%7B440%2C+44.03%7D%2C+%7B480%2C+44.66%7D%2C+%7B500%2C+45.96%7D%2C%7B604%2C+51.84%7D%2C+%7B649%2C+52.69%7D%7D * http://www.aionsource.com/topic/40542-character-stats-xp-dp-origin-gerbatorteam-july-2009/ * http://www.wolframalpha.com/input/?i=-0.000126341+x%5E2%2B0.184411+x-13.7738 * https://docs.google.com/spreadsheet/ccc?key=0AqxBGNJV9RrzdGNjbEhQNHN3S3M5bUVfUVQxRkVIT3c&hl=en_US#gid=0 * * @param attacker * @return double */ public static boolean calculatePhysicalCriticalRate( Creature attacker, Creature attacked, boolean isMainHand, int criticalProb, boolean isSkill) { if (attacker instanceof Servant || attacker instanceof Homing) { return false; } int critical; if (attacker instanceof Player && !isMainHand) { critical = ((PlayerGameStats) attacker.getGameStats()).getOffHandPCritical().getCurrent(); } else { critical = attacker.getGameStats().getMainHandPCritical().getCurrent(); } // check one time boost skill critical AttackerCriticalStatus acStatus = attacker.getObserveController().checkAttackerCriticalStatus(AttackStatus.CRITICAL, isSkill); if (acStatus.isResult()) { if (acStatus.isPercent()) { critical *= (1 + acStatus.getValue() / 100); } else { return Rnd.nextInt(1000) < acStatus.getValue(); } } critical = attacked.getGameStats().getPositiveReverseStat(StatEnum.PHYSICAL_CRITICAL_RESIST, critical) - attacker.getGameStats().getStat(StatEnum.PVP_HIT_ACCURACY, 0).getCurrent(); // add critical Prob critical *= (float) criticalProb / 100f; double criticalRate; if (critical <= 440) { criticalRate = critical * 0.1f; } else if (critical <= 600) { criticalRate = (440 * 0.1f) + ((critical - 440) * 0.05f); } else { criticalRate = (440 * 0.1f) + (160 * 0.05f) + ((critical - 600) * 0.02f); } return Rnd.nextInt(100) < criticalRate; }