mirror of
https://github.com/mcMMO-Dev/mcMMO.git
synced 2024-11-22 05:06:45 +01:00
Fix Blast Mining Fixes #5021
This commit is contained in:
parent
ce8464fcfe
commit
2debcbefd0
@ -1,4 +1,7 @@
|
||||
Version 2.2.017
|
||||
Fixed Blast Mining being almost completely broken
|
||||
Reworked Blast Mining to drop non-mining related blocks too
|
||||
Reworked Blast Mining to use your pickaxe when determining drops (will apply Silk Touch)
|
||||
Fixed shift-clicking ingredients into the brewing stand not working on older versions of Minecraft
|
||||
Added a setting in advanced.yml to ignore attack cooldowns (see notes)
|
||||
Fixed a bug with Mace permissions (thanks SrBedrock)
|
||||
|
@ -48,7 +48,7 @@ public class MiningCommand extends SkillCommand {
|
||||
|
||||
blastMiningRank = miningManager.getBlastMiningTier();
|
||||
bonusTNTDrops = miningManager.getDropMultiplier();
|
||||
oreBonus = percent.format(miningManager.getOreBonus() / 30.0D); // Base received in TNT is 30%
|
||||
oreBonus = percent.format(miningManager.getOreBonus()); // Base received in TNT is 30%
|
||||
// debrisReduction = percent.format(miningManager.getDebrisReduction() / 30.0D); // Base received in TNT is 30%
|
||||
blastDamageDecrease = percent.format(miningManager.getBlastDamageModifier() / 100.0D);
|
||||
blastRadiusIncrease = miningManager.getBlastRadiusModifier();
|
||||
|
@ -75,7 +75,8 @@ public class Roll extends AcrobaticsSubSkill {
|
||||
*/
|
||||
|
||||
if (canRoll(mmoPlayer)) {
|
||||
entityDamageEvent.setDamage(rollCheck(mmoPlayer, entityDamageEvent.getFinalDamage()));
|
||||
entityDamageEvent.setDamage(
|
||||
rollCheck(mmoPlayer, entityDamageEvent.getFinalDamage(), mmoPlayer.getPlayer().isSneaking()));
|
||||
|
||||
if (entityDamageEvent.getFinalDamage() == 0) {
|
||||
entityDamageEvent.setCancelled(true);
|
||||
@ -189,64 +190,24 @@ public class Roll extends AcrobaticsSubSkill {
|
||||
&& Permissions.isSubSkillEnabled(mmoPlayer.getPlayer(), SubSkillType.ACROBATICS_ROLL);
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle the damage reduction and XP gain from the Roll ability
|
||||
*
|
||||
* @param damage The amount of damage initially dealt by the event
|
||||
* @return the modified event damage if the ability was successful, the original event damage otherwise
|
||||
*/
|
||||
@VisibleForTesting
|
||||
public double rollCheck(McMMOPlayer mmoPlayer, double damage) {
|
||||
int skillLevel = mmoPlayer.getSkillLevel(getPrimarySkill());
|
||||
|
||||
if (mmoPlayer.getPlayer().isSneaking()) {
|
||||
return gracefulRollCheck(mmoPlayer, damage, skillLevel);
|
||||
}
|
||||
|
||||
double modifiedDamage = calculateModifiedRollDamage(damage, mcMMO.p.getAdvancedConfig().getRollDamageThreshold());
|
||||
|
||||
if (!isFatal(mmoPlayer, modifiedDamage)
|
||||
&& ProbabilityUtil.isSkillRNGSuccessful(SubSkillType.ACROBATICS_ROLL, mmoPlayer)) {
|
||||
NotificationManager.sendPlayerInformation(mmoPlayer.getPlayer(), NotificationType.SUBSKILL_MESSAGE, "Acrobatics.Roll.Text");
|
||||
SoundManager.sendCategorizedSound(mmoPlayer.getPlayer(), mmoPlayer.getPlayer().getLocation(), SoundType.ROLL_ACTIVATED, SoundCategory.PLAYERS);
|
||||
//mmoPlayer.getPlayer().sendMessage(LocaleLoader.getString("Acrobatics.Roll.Text"));
|
||||
|
||||
//if (!SkillUtils.cooldownExpired((long) mcMMOmmoPlayer.getPlayer().getTeleportATS(), Config.getInstance().getXPAfterTeleportCooldown())) {
|
||||
if (!isExploiting(mmoPlayer) && mmoPlayer.getAcrobaticsManager().canGainRollXP())
|
||||
SkillUtils.applyXpGain(mmoPlayer, getPrimarySkill(), calculateRollXP(mmoPlayer, damage, true), XPGainReason.PVE);
|
||||
//}
|
||||
|
||||
addFallLocation(mmoPlayer);
|
||||
return modifiedDamage;
|
||||
} else if (!isFatal(mmoPlayer, damage)) {
|
||||
//if (!SkillUtils.cooldownExpired((long) mmoPlayer.getTeleportATS(), Config.getInstance().getXPAfterTeleportCooldown())) {
|
||||
if (!isExploiting(mmoPlayer) && mmoPlayer.getAcrobaticsManager().canGainRollXP())
|
||||
SkillUtils.applyXpGain(mmoPlayer, getPrimarySkill(), calculateRollXP(mmoPlayer, damage, false), XPGainReason.PVE);
|
||||
//}
|
||||
}
|
||||
|
||||
addFallLocation(mmoPlayer);
|
||||
return damage;
|
||||
}
|
||||
|
||||
private int getActivationChance(McMMOPlayer mmoPlayer) {
|
||||
return PerksUtils.handleLuckyPerks(mmoPlayer, getPrimarySkill());
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle the damage reduction and XP gain from the Graceful Roll ability
|
||||
* Handle the damage reduction and XP gain from the Roll / Graceful Roll ability
|
||||
*
|
||||
* @param damage The amount of damage initially dealt by the event
|
||||
* @return the modified event damage if the ability was successful, the original event damage otherwise
|
||||
*/
|
||||
private double gracefulRollCheck(McMMOPlayer mmoPlayer, double damage, int skillLevel) {
|
||||
double modifiedDamage = calculateModifiedRollDamage(damage, mcMMO.p.getAdvancedConfig().getRollDamageThreshold() * 2);
|
||||
|
||||
final Probability gracefulProbability = getGracefulProbability(mmoPlayer);
|
||||
private double rollCheck(McMMOPlayer mmoPlayer, double damage, boolean isGracefulRoll) {
|
||||
final Probability probability
|
||||
= isGracefulRoll ? getGracefulProbability(mmoPlayer) : getNonGracefulProbability(mmoPlayer);
|
||||
double modifiedDamage = calculateModifiedRollDamage(damage,
|
||||
mcMMO.p.getAdvancedConfig().getRollDamageThreshold() * 2);
|
||||
|
||||
if (!isFatal(mmoPlayer, modifiedDamage)
|
||||
//TODO: Graceful isn't sending out an event
|
||||
&& ProbabilityUtil.isStaticSkillRNGSuccessful(PrimarySkillType.ACROBATICS, mmoPlayer, gracefulProbability)) {
|
||||
&& ProbabilityUtil.isStaticSkillRNGSuccessful(PrimarySkillType.ACROBATICS, mmoPlayer, probability)) {
|
||||
NotificationManager.sendPlayerInformation(mmoPlayer.getPlayer(), NotificationType.SUBSKILL_MESSAGE, "Acrobatics.Ability.Proc");
|
||||
SoundManager.sendCategorizedSound(mmoPlayer.getPlayer(), mmoPlayer.getPlayer().getLocation(), SoundType.ROLL_ACTIVATED, SoundCategory.PLAYERS,0.5F);
|
||||
if (!isExploiting(mmoPlayer) && mmoPlayer.getAcrobaticsManager().canGainRollXP())
|
||||
@ -270,6 +231,11 @@ public class Roll extends AcrobaticsSubSkill {
|
||||
return Probability.ofValue(gracefulOdds);
|
||||
}
|
||||
|
||||
public static Probability getNonGracefulProbability(McMMOPlayer mmoPlayer) {
|
||||
double gracefulOdds = ProbabilityUtil.getSubSkillProbability(SubSkillType.ACROBATICS_ROLL, mmoPlayer).getValue();
|
||||
return Probability.ofValue(gracefulOdds);
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if the player is "farming" Acrobatics XP using
|
||||
* exploits in the game.
|
||||
|
@ -756,7 +756,7 @@ public class EntityListener implements Listener {
|
||||
if (WorldBlacklist.isWorldBlacklisted(event.getEntity().getWorld()))
|
||||
return;
|
||||
|
||||
Entity entity = event.getEntity();
|
||||
final Entity entity = event.getEntity();
|
||||
|
||||
if (!(entity instanceof TNTPrimed) || !entity.hasMetadata(MetadataConstants.METADATA_KEY_TRACKED_TNT)) {
|
||||
return;
|
||||
@ -764,13 +764,14 @@ public class EntityListener implements Listener {
|
||||
|
||||
// We can make this assumption because we (should) be the only ones
|
||||
// using this exact metadata
|
||||
Player player = pluginRef.getServer().getPlayerExact(entity.getMetadata(MetadataConstants.METADATA_KEY_TRACKED_TNT).get(0).asString());
|
||||
final Player player = pluginRef.getServer().getPlayerExact(
|
||||
entity.getMetadata(MetadataConstants.METADATA_KEY_TRACKED_TNT).get(0).asString());
|
||||
|
||||
if (!UserManager.hasPlayerDataKey(player)) {
|
||||
return;
|
||||
}
|
||||
|
||||
//Profile not loaded
|
||||
// Profile is not loaded
|
||||
if (UserManager.getPlayer(player) == null) {
|
||||
return;
|
||||
}
|
||||
@ -781,7 +782,7 @@ public class EntityListener implements Listener {
|
||||
return;
|
||||
}
|
||||
|
||||
MiningManager miningManager = UserManager.getPlayer(player).getMiningManager();
|
||||
final MiningManager miningManager = UserManager.getPlayer(player).getMiningManager();
|
||||
|
||||
if (miningManager.canUseBiggerBombs()) {
|
||||
event.setRadius(miningManager.biggerBombs(event.getRadius()));
|
||||
|
@ -10,58 +10,17 @@ import org.bukkit.entity.TNTPrimed;
|
||||
import org.bukkit.event.entity.EntityDamageByEntityEvent;
|
||||
|
||||
public class BlastMining {
|
||||
// The order of the values is extremely important, a few methods depend on it to work properly
|
||||
/* public enum Tier {
|
||||
EIGHT(8),
|
||||
SEVEN(7),
|
||||
SIX(6),
|
||||
FIVE(5),
|
||||
FOUR(4),
|
||||
THREE(3),
|
||||
TWO(2),
|
||||
ONE(1);
|
||||
|
||||
int numerical;
|
||||
|
||||
private Tier(int numerical) {
|
||||
this.numerical = numerical;
|
||||
}
|
||||
|
||||
public int toNumerical() {
|
||||
return numerical;
|
||||
}
|
||||
|
||||
protected int getLevel() {
|
||||
return mcMMO.p.getAdvancedConfig().getBlastMiningRankLevel(this);
|
||||
}
|
||||
|
||||
|
||||
}*/
|
||||
|
||||
public final static int MAXIMUM_REMOTE_DETONATION_DISTANCE = 100;
|
||||
|
||||
public static double getBlastRadiusModifier(int rank) {
|
||||
return mcMMO.p.getAdvancedConfig().getBlastRadiusModifier(rank);
|
||||
}
|
||||
|
||||
|
||||
|
||||
public static double getBlastDamageDecrease(int rank) {
|
||||
return mcMMO.p.getAdvancedConfig().getBlastDamageDecrease(rank);
|
||||
}
|
||||
|
||||
|
||||
|
||||
public static int getDemolitionExpertUnlockLevel() {
|
||||
/*List<Tier> tierList = Arrays.asList(Tier.values());
|
||||
for (Tier tier : tierList) {
|
||||
if (tier.getBlastDamageDecrease() > 0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
return tier == Tier.EIGHT ? tier.getLevel() : tierList.get(tierList.indexOf(tier) - 1).getLevel();
|
||||
}*/
|
||||
|
||||
for(int i = 0; i < SubSkillType.MINING_BLAST_MINING.getNumRanks()-1; i++) {
|
||||
if (getBlastDamageDecrease(i+1) > 0)
|
||||
return RankUtils.getRankUnlockLevel(SubSkillType.MINING_BLAST_MINING, i+1);
|
||||
@ -71,15 +30,6 @@ public class BlastMining {
|
||||
}
|
||||
|
||||
public static int getBiggerBombsUnlockLevel() {
|
||||
/*List<Tier> tierList = Arrays.asList(Tier.values());
|
||||
for (Tier tier : tierList) {
|
||||
if (tier.getBlastRadiusModifier() > 1.0) {
|
||||
continue;
|
||||
}
|
||||
|
||||
return tier == Tier.EIGHT ? tier.getLevel() : tierList.get(tierList.indexOf(tier) - 1).getLevel();
|
||||
}*/
|
||||
|
||||
for(int i = 0; i < SubSkillType.MINING_BLAST_MINING.getNumRanks()-1; i++) {
|
||||
if (getBlastRadiusModifier(i+1) > 0)
|
||||
return RankUtils.getRankUnlockLevel(SubSkillType.MINING_BLAST_MINING, i+1);
|
||||
@ -104,7 +54,7 @@ public class BlastMining {
|
||||
return false;
|
||||
}
|
||||
|
||||
MiningManager miningManager = UserManager.getPlayer(defender).getMiningManager();
|
||||
final MiningManager miningManager = UserManager.getPlayer(defender).getMiningManager();
|
||||
|
||||
if (!miningManager.canUseDemolitionsExpertise()) {
|
||||
return false;
|
||||
|
@ -17,7 +17,6 @@ import com.gmail.nossr50.util.random.Probability;
|
||||
import com.gmail.nossr50.util.random.ProbabilityUtil;
|
||||
import com.gmail.nossr50.util.skills.RankUtils;
|
||||
import com.gmail.nossr50.util.skills.SkillUtils;
|
||||
import org.apache.commons.lang3.RandomUtils;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.block.Block;
|
||||
import org.bukkit.block.BlockState;
|
||||
@ -30,8 +29,11 @@ import org.bukkit.inventory.ItemStack;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import static com.gmail.nossr50.util.ItemUtils.isPickaxe;
|
||||
|
||||
public class MiningManager extends SkillManager {
|
||||
|
||||
public static final String BUDDING_AMETHYST = "budding_amethyst";
|
||||
@ -51,7 +53,7 @@ public class MiningManager extends SkillManager {
|
||||
Player player = getPlayer();
|
||||
|
||||
return canUseBlastMining() && player.isSneaking()
|
||||
&& (ItemUtils.isPickaxe(getPlayer().getInventory().getItemInMainHand()) || player.getInventory().getItemInMainHand().getType() == mcMMO.p.getGeneralConfig().getDetonatorItem())
|
||||
&& (isPickaxe(getPlayer().getInventory().getItemInMainHand()) || player.getInventory().getItemInMainHand().getType() == mcMMO.p.getGeneralConfig().getDetonatorItem())
|
||||
&& Permissions.remoteDetonation(player);
|
||||
}
|
||||
|
||||
@ -168,69 +170,76 @@ public class MiningManager extends SkillManager {
|
||||
* @param yield The % of blocks to drop
|
||||
* @param event The {@link EntityExplodeEvent}
|
||||
*/
|
||||
//TODO: Rewrite this garbage
|
||||
public void blastMiningDropProcessing(float yield, EntityExplodeEvent event) {
|
||||
if (yield == 0)
|
||||
return;
|
||||
|
||||
var increasedYieldFromBonuses = yield + (yield * getOreBonus());
|
||||
// Strip out only stuff that gives mining XP
|
||||
List<BlockState> ores = new ArrayList<>();
|
||||
|
||||
List<BlockState> notOres = new ArrayList<>();
|
||||
for (Block targetBlock : event.blockList()) {
|
||||
BlockState blockState = targetBlock.getState();
|
||||
//Containers usually have 0 XP unless someone edited their config in a very strange way
|
||||
if (ExperienceConfig.getInstance().getXp(PrimarySkillType.MINING, targetBlock) != 0
|
||||
&& !(targetBlock instanceof Container)
|
||||
&& !mcMMO.getUserBlockTracker().isIneligible(targetBlock)) {
|
||||
if (BlockUtils.isOre(blockState)) {
|
||||
|
||||
if(mcMMO.getUserBlockTracker().isIneligible(targetBlock))
|
||||
continue;
|
||||
|
||||
if (ExperienceConfig.getInstance().getXp(PrimarySkillType.MINING, targetBlock) != 0) {
|
||||
if (BlockUtils.isOre(blockState) && !(targetBlock instanceof Container)) {
|
||||
ores.add(blockState);
|
||||
}
|
||||
} else {
|
||||
notOres.add(blockState);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int xp = 0;
|
||||
|
||||
float oreBonus = (float) (getOreBonus() / 100);
|
||||
float debrisReduction = (float) (getDebrisReduction() / 100);
|
||||
int dropMultiplier = getDropMultiplier();
|
||||
float debrisYield = yield - debrisReduction;
|
||||
|
||||
//Drop "debris" based on skill modifiers
|
||||
for(BlockState blockState : notOres) {
|
||||
if (isDropIllegal(blockState.getType()))
|
||||
continue;
|
||||
|
||||
if (Probability.ofPercent(50).evaluate()) {
|
||||
ItemUtils.spawnItem(getPlayer(), Misc.getBlockCenter(blockState), new ItemStack(blockState.getType()), ItemSpawnReason.BLAST_MINING_DEBRIS_NON_ORES); // Initial block that would have been dropped
|
||||
ItemUtils.spawnItem(getPlayer(),
|
||||
Misc.getBlockCenter(blockState),
|
||||
new ItemStack(blockState.getType()),
|
||||
ItemSpawnReason.BLAST_MINING_DEBRIS_NON_ORES); // Initial block that would have been dropped
|
||||
}
|
||||
}
|
||||
|
||||
for (BlockState blockState : ores) {
|
||||
if (isDropIllegal(blockState.getType()))
|
||||
// currentOreYield only used for drop calculations for ores
|
||||
float currentOreYield = increasedYieldFromBonuses;
|
||||
|
||||
if (isDropIllegal(blockState.getType())) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (RandomUtils.nextFloat() < (yield + oreBonus)) {
|
||||
// Always give XP for every ore destroyed
|
||||
xp += Mining.getBlockXp(blockState);
|
||||
while(currentOreYield > 0) {
|
||||
if (Probability.ofValue(currentOreYield).evaluate()) {
|
||||
Collection<ItemStack> oreDrops = isPickaxe(mmoPlayer.getPlayer().getInventory().getItemInMainHand())
|
||||
? blockState.getBlock().getDrops(mmoPlayer.getPlayer().getInventory().getItemInMainHand())
|
||||
: List.of(new ItemStack(blockState.getType()));
|
||||
ItemUtils.spawnItems(getPlayer(), Misc.getBlockCenter(blockState),
|
||||
oreDrops, ItemSpawnReason.BLAST_MINING_ORES);
|
||||
|
||||
ItemUtils.spawnItem(getPlayer(), Misc.getBlockCenter(blockState), new ItemStack(blockState.getType()), ItemSpawnReason.BLAST_MINING_ORES); // Initial block that would have been dropped
|
||||
|
||||
if (mcMMO.p.getAdvancedConfig().isBlastMiningBonusDropsEnabled() && !mcMMO.getUserBlockTracker().isIneligible(blockState)) {
|
||||
if (mcMMO.p.getAdvancedConfig().isBlastMiningBonusDropsEnabled()) {
|
||||
for (int i = 1; i < dropMultiplier; i++) {
|
||||
// Bukkit.broadcastMessage("Bonus Drop on Ore: "+blockState.getType().toString());
|
||||
ItemUtils.spawnItem(getPlayer(), Misc.getBlockCenter(blockState), new ItemStack(blockState.getType()), ItemSpawnReason.BLAST_MINING_ORES_BONUS_DROP); // Initial block that would have been dropped
|
||||
ItemUtils.spawnItems(getPlayer(),
|
||||
Misc.getBlockCenter(blockState),
|
||||
oreDrops,
|
||||
ItemSpawnReason.BLAST_MINING_ORES_BONUS_DROP);
|
||||
}
|
||||
}
|
||||
}
|
||||
currentOreYield = Math.max(currentOreYield - 1, 0);
|
||||
}
|
||||
}
|
||||
|
||||
// Replace the event blocklist with the newYield list
|
||||
event.setYield(0F);
|
||||
// event.blockList().clear();
|
||||
// event.blockList().addAll(notOres);
|
||||
|
||||
applyXpGain(xp, XPGainReason.PVE);
|
||||
}
|
||||
|
||||
@ -273,10 +282,11 @@ public class MiningManager extends SkillManager {
|
||||
*
|
||||
* @return the Blast Mining tier
|
||||
*/
|
||||
public double getOreBonus() {
|
||||
return getOreBonus(getBlastMiningTier());
|
||||
public float getOreBonus() {
|
||||
return (float) (mcMMO.p.getAdvancedConfig().getOreBonus(getBlastMiningTier()) / 100F);
|
||||
}
|
||||
|
||||
@Deprecated(since = "2.2.017", forRemoval = true)
|
||||
public static double getOreBonus(int rank) {
|
||||
return mcMMO.p.getAdvancedConfig().getOreBonus(rank);
|
||||
}
|
||||
|
@ -681,6 +681,21 @@ public final class ItemUtils {
|
||||
return enchantmentWrappers.get(randomIndex);
|
||||
}
|
||||
|
||||
/**
|
||||
* Drop items at a given location.
|
||||
*
|
||||
* @param location The location to drop the items at
|
||||
* @param itemStacks The items to drop
|
||||
*/
|
||||
public static void spawnItems(@Nullable Player player,
|
||||
@NotNull Location location,
|
||||
@NotNull Collection<ItemStack> itemStacks,
|
||||
@NotNull ItemSpawnReason itemSpawnReason) {
|
||||
for (ItemStack is : itemStacks) {
|
||||
spawnItem(player, location, is, itemSpawnReason);
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Drop items at a given location.
|
||||
*
|
||||
|
@ -165,8 +165,6 @@ Alchemy.Listener=Alchemy:
|
||||
Alchemy.Ability.Locked.0=LOCKED UNTIL {0}+ SKILL (CATALYSIS)
|
||||
Alchemy.SkillName=ALCHEMY
|
||||
#ARCHERY
|
||||
|
||||
|
||||
Archery.SubSkill.SkillShot.Name=Skill Shot
|
||||
Archery.SubSkill.SkillShot.Description=Increases damage done with bows
|
||||
Archery.SubSkill.SkillShot.Stat=Skill Shot Bonus Damage
|
||||
|
Loading…
Reference in New Issue
Block a user