mirror of
https://github.com/songoda/UltimateStacker.git
synced 2024-11-26 20:16:22 +01:00
Fix item stacking when using large numbers
This commit is contained in:
parent
86a19a520b
commit
6f77c43d97
@ -56,8 +56,6 @@ public class ItemListeners implements Listener {
|
||||
}
|
||||
}
|
||||
|
||||
//Do we need this?
|
||||
|
||||
@EventHandler
|
||||
public void onExist(ItemSpawnEvent event) {
|
||||
if (!Settings.STACK_ITEMS.getBoolean()) return;
|
||||
@ -72,16 +70,7 @@ public class ItemListeners implements Listener {
|
||||
StringUtils.substring(itemStack.getItemMeta().getDisplayName(), 0, 3).equals("***")) {
|
||||
return; //Compatibility with Shop instance: https://www.spigotmc.org/resources/shop-a-simple-intuitive-shop-instance.9628/
|
||||
}
|
||||
|
||||
StackedItemManager itemStackManager = UltimateStackerApi.getStackedItemManager();
|
||||
|
||||
if (itemStackManager.isStackedItem(event.getEntity())) {
|
||||
StackedItem stackedItem = UltimateStacker.getInstance().getStackedItemManager().getStackedItem(event.getEntity());
|
||||
stackedItem.setAmount(stackedItem.getAmount() + itemStack.getAmount());
|
||||
UltimateStackerApi.getStackedItemManager().createStack(event.getEntity(), UltimateStackerApi.getStackedItemManager().getActualItemAmount(event.getEntity()) + itemStack.getAmount());
|
||||
} else {
|
||||
UltimateStackerApi.getStackedItemManager().createStack(event.getEntity(), itemStack.getAmount());
|
||||
}
|
||||
|
||||
|
||||
UltimateStackerApi.getStackedItemManager().createStack(event.getEntity(), itemStack.getAmount());
|
||||
}
|
||||
}
|
||||
|
@ -27,6 +27,7 @@ import java.io.File;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Random;
|
||||
import java.util.concurrent.ThreadLocalRandom;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
public class LootablesManager {
|
||||
@ -36,6 +37,7 @@ public class LootablesManager {
|
||||
private final LootManager lootManager;
|
||||
|
||||
private final String lootablesDir = UltimateStacker.getInstance().getDataFolder() + File.separator + "lootables";
|
||||
private final static int MAX_INT = Integer.MAX_VALUE/2;
|
||||
|
||||
public LootablesManager() {
|
||||
this.lootables = new Lootables(lootablesDir);
|
||||
@ -121,7 +123,6 @@ public class LootablesManager {
|
||||
|
||||
double extraChance = looting / (looting + 1.0);
|
||||
|
||||
Random random = new Random();
|
||||
boolean isCharged = entity instanceof Creeper && ((Creeper) entity).isPowered();
|
||||
|
||||
//Run main loot
|
||||
@ -130,38 +131,56 @@ public class LootablesManager {
|
||||
if (loot.getOnlyDropFor().size() != 0 && loot.getOnlyDropFor().stream().noneMatch(type -> entity.getKiller() != null && type == entity.getKiller().getType())) continue;
|
||||
int finalLooting = loot.isAllowLootingEnchant() ? looting : 0;
|
||||
|
||||
int max = (int) (((loot.getMax() + finalLooting) * times) * (loot.getChance()/100));
|
||||
int min = (int) ((loot.getMin()) * times * (loot.getChance()/100));
|
||||
long max = (long) (((long) (loot.getMax() + finalLooting) * times) * (loot.getChance()/100 + (loot.isAllowLootingEnchant() ? extraChance : 0)));
|
||||
long min = (long) ((loot.getMin()) * times * (loot.getChance()/100));
|
||||
|
||||
int amount = random.nextInt((max - min) + 1) + min;
|
||||
long amount = ThreadLocalRandom.current().nextLong((max - min) + 1) + min;
|
||||
|
||||
if (amount > 0) {
|
||||
ItemStack item = entity.getFireTicks() > 0
|
||||
? loot.getBurnedMaterial() != null ? loot.getBurnedMaterial().parseItem() : loot.getMaterial().parseItem()
|
||||
: loot.getMaterial().parseItem().clone();
|
||||
item.setAmount(amount);
|
||||
: loot.getMaterial().parseItem();
|
||||
if (amount > MAX_INT) {
|
||||
while (amount > MAX_INT) {
|
||||
ItemStack loop = item.clone();
|
||||
loop.setAmount(MAX_INT);
|
||||
amount -= MAX_INT;
|
||||
toDrop.add(new Drop(loop));
|
||||
}
|
||||
}
|
||||
//Leftover
|
||||
item.setAmount((int) amount);
|
||||
toDrop.add(new Drop(item));
|
||||
}
|
||||
}
|
||||
//Run child loot
|
||||
for (Loot loot : lootable.getRegisteredLoot().stream().filter(loot -> loot.getMaterial() == null).collect(Collectors.toList())) {
|
||||
|
||||
//Run child loot //TODO: remove duplicated code
|
||||
for (Loot child : loot.getChildLoot()) {
|
||||
if (child.isRequireCharged() && !isCharged) continue;
|
||||
if (loot.getOnlyDropFor().size() != 0 && loot.getOnlyDropFor().stream().noneMatch(type -> entity.getKiller() != null && type == entity.getKiller().getType())) continue;
|
||||
if (child.getOnlyDropFor().size() != 0 && child.getOnlyDropFor().stream().noneMatch(type -> entity.getKiller() != null && type == entity.getKiller().getType())) continue;
|
||||
|
||||
int finalLooting = child.isAllowLootingEnchant() ? looting : 0;
|
||||
int choildFinalLooting = child.isAllowLootingEnchant() ? looting : 0;
|
||||
|
||||
int max = (int) (((loot.getMax() + finalLooting) * times * (loot.getChance()/100)));
|
||||
int min = (int) ((loot.getMin()) * times * (loot.getChance()/100));
|
||||
min = (int) (min - min*0.90);
|
||||
long childMax = (long) (((long) (child.getMax() + finalLooting) * times) * (child.getChance()/100 + (child.isAllowLootingEnchant() ? extraChance : 0)));
|
||||
long childmin = (long) ((child.getMin()) * times * (child.getChance()/100));
|
||||
childmin = (long) (childmin - childmin*0.90);
|
||||
|
||||
int amount = random.nextInt((max - min) + 1) + min;
|
||||
|
||||
if (amount > 0) {
|
||||
long childamount = ThreadLocalRandom.current().nextLong((childMax - childmin) + 1) + childmin;
|
||||
|
||||
if (childamount > 0) {
|
||||
ItemStack item = entity.getFireTicks() > 0
|
||||
? child.getBurnedMaterial() != null ? child.getBurnedMaterial().parseItem() : child.getMaterial().parseItem()
|
||||
: child.getMaterial().parseItem().clone();
|
||||
item.setAmount(amount);
|
||||
: child.getMaterial().parseItem();
|
||||
if (childamount > MAX_INT) {
|
||||
while (childamount > MAX_INT) {
|
||||
ItemStack loop = item.clone();
|
||||
loop.setAmount(MAX_INT);
|
||||
childamount -= MAX_INT;
|
||||
toDrop.add(new Drop(loop));
|
||||
}
|
||||
}
|
||||
//Leftover
|
||||
item.setAmount((int) childamount);
|
||||
toDrop.add(new Drop(item));
|
||||
}
|
||||
}
|
||||
|
@ -34,7 +34,7 @@ public class Settings implements com.craftaro.ultimatestacker.api.Settings {
|
||||
"The distance entities must be to each other in order to stack.");
|
||||
|
||||
public static final ConfigSetting MAX_STACK_ENTITIES = new ConfigSetting(config, "Entities.Max Stack Size", 15,
|
||||
"The max amount of entities in a single stack.");
|
||||
"The max amount of entities in a single stack. Max value is 2000000000");
|
||||
|
||||
// Note: this setting is also referenced in EpicSpawners
|
||||
public static final ConfigSetting MIN_STACK_ENTITIES = new ConfigSetting(config, "Entities.Min Stack Amount", 5,
|
||||
@ -183,7 +183,7 @@ public class Settings implements com.craftaro.ultimatestacker.api.Settings {
|
||||
"Should items that are blacklisted display holograms?");
|
||||
|
||||
public static final ConfigSetting MAX_STACK_ITEMS = new ConfigSetting(config, "Items.Max Stack Size", 512,
|
||||
"The max stack size for items.");
|
||||
"The max stack size for items. Max value is 1500000000");
|
||||
|
||||
public static final ConfigSetting NAME_FORMAT_ITEM = new ConfigSetting(config, "Items.Name Format", "&f{TYPE} &r[&6{AMT}x]",
|
||||
"The text displayed above a dropped item.");
|
||||
|
@ -1,10 +1,12 @@
|
||||
package com.craftaro.ultimatestacker.stackable.entity;
|
||||
|
||||
import com.craftaro.core.SongodaCore;
|
||||
import com.craftaro.core.compatibility.ServerVersion;
|
||||
import com.craftaro.core.lootables.loot.Drop;
|
||||
import com.craftaro.core.lootables.loot.DropUtils;
|
||||
import com.craftaro.core.utils.EntityUtils;
|
||||
import com.craftaro.ultimatestacker.UltimateStacker;
|
||||
import com.craftaro.ultimatestacker.api.UltimateStackerApi;
|
||||
import com.craftaro.ultimatestacker.api.events.entity.EntityStackKillEvent;
|
||||
import com.craftaro.ultimatestacker.api.stack.entity.EntityStack;
|
||||
import com.craftaro.ultimatestacker.settings.Settings;
|
||||
@ -12,6 +14,7 @@ import com.craftaro.ultimatestacker.utils.Async;
|
||||
import com.craftaro.ultimatestacker.utils.Methods;
|
||||
import org.bukkit.Bukkit;
|
||||
import org.bukkit.Location;
|
||||
import org.bukkit.Material;
|
||||
import org.bukkit.entity.EntityType;
|
||||
import org.bukkit.entity.ExperienceOrb;
|
||||
import org.bukkit.entity.LivingEntity;
|
||||
@ -21,6 +24,8 @@ import org.bukkit.inventory.ItemStack;
|
||||
import org.bukkit.metadata.FixedMetadataValue;
|
||||
import org.bukkit.util.Vector;
|
||||
|
||||
import java.math.BigDecimal;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
import java.util.UUID;
|
||||
|
@ -21,6 +21,8 @@ import java.util.concurrent.atomic.AtomicReference;
|
||||
|
||||
public class StackedItemManagerImpl implements StackedItemManager {
|
||||
|
||||
private final static int MAX_INT = 1500000000;
|
||||
|
||||
@Override
|
||||
public @NotNull StackedItem getStackedItem(Item item) {
|
||||
return new StackedItemImpl(item);
|
||||
@ -97,6 +99,7 @@ public class StackedItemManagerImpl implements StackedItemManager {
|
||||
}
|
||||
|
||||
int maxItemStackSize = Settings.MAX_STACK_ITEMS.getInt();
|
||||
if (maxItemStackSize > MAX_INT) maxItemStackSize = MAX_INT;
|
||||
|
||||
ItemStack fromItemStack = from.getItemStack();
|
||||
ItemStack toItemStack = to.getItemStack();
|
||||
@ -104,7 +107,7 @@ public class StackedItemManagerImpl implements StackedItemManager {
|
||||
if (fromItemStack.getType() != toItemStack.getType()) return null;
|
||||
if (!ignoreRestrictions && UltimateStacker.isMaterialBlacklisted(fromItemStack)) return null;
|
||||
|
||||
int maxSize = UltimateStacker.getInstance().getItemFile().getInt("Items." + fromItemStack.getType().name() + ".Max Stack Size");
|
||||
long maxSize = UltimateStacker.getInstance().getItemFile().getInt("Items." + fromItemStack.getType().name() + ".Max Stack Size");
|
||||
|
||||
if (maxSize <= 0) {
|
||||
maxSize = maxItemStackSize;
|
||||
@ -112,8 +115,8 @@ public class StackedItemManagerImpl implements StackedItemManager {
|
||||
maxSize = Math.min(maxSize, maxItemStackSize);
|
||||
}
|
||||
|
||||
int fromAmount = getActualItemAmount(from);
|
||||
int toAmount = getActualItemAmount(to);
|
||||
long fromAmount = getActualItemAmount(from);
|
||||
long toAmount = getActualItemAmount(to);
|
||||
|
||||
if (fromAmount + toAmount > maxSize) {
|
||||
if (callback != null) callback.accept(from, to, null);
|
||||
@ -121,7 +124,7 @@ public class StackedItemManagerImpl implements StackedItemManager {
|
||||
//merge was unsuccessful
|
||||
return null;
|
||||
} else {
|
||||
StackedItem merged = new StackedItemImpl(to, fromAmount + toAmount);
|
||||
StackedItem merged = new StackedItemImpl(to, (int) (fromAmount + toAmount));
|
||||
if (callback != null) callback.accept(null, to, merged);
|
||||
return merged;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user