Skip to content

Commit 36ef225

Browse files
committed
Merge PR EssentialsX#5321: Add item group for sell sign
# Conflicts: # Essentials/src/main/java/com/earth2me/essentials/Essentials.java
2 parents 2c8b25a + 295c462 commit 36ef225

9 files changed

Lines changed: 242 additions & 8 deletions

File tree

‎Essentials/src/main/java/com/earth2me/essentials/Essentials.java‎

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -192,6 +192,7 @@ public class Essentials extends JavaPlugin implements net.ess3.api.IEssentials {
192192
private transient EssentialsTimer timer;
193193
private transient ProviderListener recipeBookEventProvider;
194194
private transient Kits kits;
195+
private transient ItemGroups itemGroups;
195196
private transient RandomTeleport randomTeleport;
196197
private transient UpdateChecker updateChecker;
197198
private transient AdventureFacet adventureFacet;
@@ -339,6 +340,10 @@ public void onEnable() {
339340
confList.add(jails);
340341
execTimer.mark("Init(Jails)");
341342

343+
itemGroups = new ItemGroups(this);
344+
confList.add(itemGroups);
345+
execTimer.mark("Init(ItemGroups)");
346+
342347
// Spawner item provider only uses one, but it's here for legacy...
343348
providerFactory.registerProvider(BlockMetaSpawnerItemProvider.class);
344349

Lines changed: 43 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
package com.earth2me.essentials;
2+
3+
import net.ess3.api.IEssentials;
4+
import org.bukkit.Bukkit;
5+
import org.bukkit.Material;
6+
import org.bukkit.NamespacedKey;
7+
import org.bukkit.Tag;
8+
9+
public class ItemGroupQuery {
10+
11+
private final String itemGroup;
12+
private final int amount;
13+
14+
public ItemGroupQuery(String group, int quantity) {
15+
this.itemGroup = group;
16+
this.amount = quantity;
17+
}
18+
19+
public boolean contains(IEssentials ess, Material item){
20+
Tag<Material> tag = Bukkit.getTag(Tag.REGISTRY_ITEMS, NamespacedKey.minecraft(itemGroup), Material.class);
21+
if (tag != null && tag.isTagged(item)) {
22+
return true;
23+
}
24+
final ItemGroups groupsConfig = new ItemGroups(ess);
25+
return groupsConfig.getItemGroup(itemGroup).contains(item);
26+
}
27+
28+
public String getItemGroup() {
29+
return itemGroup;
30+
}
31+
32+
public int getAmount() {
33+
return amount;
34+
}
35+
36+
@Override
37+
public String toString() {
38+
return "ItemGroupQuery{" +
39+
"itemGroup='" + itemGroup + '\'' +
40+
", quantity=" + amount +
41+
'}';
42+
}
43+
}
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
package com.earth2me.essentials;
2+
3+
import com.earth2me.essentials.config.EssentialsConfiguration;
4+
import net.ess3.api.IEssentials;
5+
import net.ess3.api.IItemGroups;
6+
import org.bukkit.Material;
7+
8+
import java.io.File;
9+
import java.util.Collections;
10+
import java.util.HashMap;
11+
import java.util.List;
12+
import java.util.Map;
13+
import java.util.Set;
14+
import java.util.stream.Collectors;
15+
16+
public class ItemGroups implements IItemGroups {
17+
18+
private final EssentialsConfiguration config;
19+
private final Map<String, List<Material>> itemGroups = new HashMap<>();
20+
21+
public ItemGroups(final IEssentials ess) {
22+
this.config = new EssentialsConfiguration(new File(ess.getDataFolder(), "groups.yml"));
23+
reloadConfig();
24+
}
25+
26+
@Override
27+
public void reloadConfig() {
28+
synchronized (itemGroups) {
29+
config.load();
30+
itemGroups.clear();
31+
32+
for (String id : config.getKeys()) {
33+
final List<String> list = config.getList(id, String.class);
34+
itemGroups.put(id, list.stream().map(Material::matchMaterial).collect(Collectors.toList()));
35+
}
36+
}
37+
}
38+
39+
@Override
40+
public List<Material> getItemGroup(String group) {
41+
return itemGroups.getOrDefault(group, Collections.emptyList());
42+
}
43+
44+
@Override
45+
public Set<String> getItemGroups() {
46+
return itemGroups.keySet();
47+
}
48+
}

‎Essentials/src/main/java/com/earth2me/essentials/Trade.java‎

Lines changed: 28 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -31,39 +31,45 @@ public class Trade {
3131
private final transient Trade fallbackTrade;
3232
private final transient BigDecimal money;
3333
private final transient ItemStack itemStack;
34+
private final transient ItemGroupQuery itemGroupQuery;
3435
private final transient Integer exp;
3536
private final transient IEssentials ess;
3637

3738
public Trade(final String command, final IEssentials ess) {
38-
this(command, null, null, null, null, ess);
39+
this(command, null, null, null, null, null, ess);
3940
}
4041

4142
public Trade(final String command, final Trade fallback, final IEssentials ess) {
42-
this(command, fallback, null, null, null, ess);
43+
this(command, fallback, null, null, null, null, ess);
4344
}
4445

4546
@Deprecated
4647
public Trade(final double money, final com.earth2me.essentials.IEssentials ess) {
47-
this(null, null, BigDecimal.valueOf(money), null, null, (IEssentials) ess);
48+
this(null, null, BigDecimal.valueOf(money), null, null, null, (IEssentials) ess);
4849
}
4950

5051
public Trade(final BigDecimal money, final IEssentials ess) {
51-
this(null, null, money, null, null, ess);
52+
this(null, null, money, null, null, null, ess);
5253
}
5354

5455
public Trade(final ItemStack items, final IEssentials ess) {
55-
this(null, null, null, items, null, ess);
56+
this(null, null, null, items, null, null, ess);
5657
}
5758

5859
public Trade(final int exp, final IEssentials ess) {
59-
this(null, null, null, null, exp, ess);
60+
this(null, null, null, null, null, exp, ess);
6061
}
6162

62-
private Trade(final String command, final Trade fallback, final BigDecimal money, final ItemStack item, final Integer exp, final IEssentials ess) {
63+
public Trade(final ItemGroupQuery query, final IEssentials ess){
64+
this(null, null, null, null, query, null, ess);
65+
}
66+
67+
private Trade(final String command, final Trade fallback, final BigDecimal money, final ItemStack item, final ItemGroupQuery groupQuery, final Integer exp, final IEssentials ess) {
6368
this.command = command;
6469
this.fallbackTrade = fallback;
6570
this.money = money;
6671
this.itemStack = item;
72+
this.itemGroupQuery = groupQuery;
6773
this.exp = exp;
6874
this.ess = ess;
6975
}
@@ -317,6 +323,17 @@ public void charge(final IUser user, final CompletableFuture<Boolean> future) {
317323
Inventories.removeItemAmount(user.getBase(), getItemStack(), getItemStack().getAmount());
318324
user.getBase().updateInventory();
319325
}
326+
if(getItemGroupQuery() != null){
327+
if(ess.getSettings().isDebug()) {
328+
ess.getLogger().log(Level.INFO, "charging user " + user.getName() + " itemgroup " +getItemGroupQuery().toString());
329+
}
330+
if (!Inventories.containsAtLeast(user.getBase(), ess, getItemGroupQuery())) {
331+
future.completeExceptionally(new ChargeException(tl("missingItems", getItemGroupQuery().getAmount(), "~"+getItemGroupQuery().getItemGroup().toLowerCase(Locale.ENGLISH).replace("_", " "))));
332+
return;
333+
}
334+
Inventories.removeItemAmount(user.getBase(), ess, getItemGroupQuery());
335+
user.getBase().updateInventory();
336+
}
320337
if (command != null) {
321338
final BigDecimal cost = getCommandCost(user);
322339
if (!user.canAfford(cost) && cost.signum() > 0) {
@@ -349,6 +366,10 @@ public ItemStack getItemStack() {
349366
return itemStack;
350367
}
351368

369+
public ItemGroupQuery getItemGroupQuery() {
370+
return itemGroupQuery;
371+
}
372+
352373
public Integer getExperience() {
353374
return exp;
354375
}

‎Essentials/src/main/java/com/earth2me/essentials/craftbukkit/Inventories.java‎

Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,10 @@
11
package com.earth2me.essentials.craftbukkit;
22

3+
import com.earth2me.essentials.ItemGroupQuery;
4+
import com.earth2me.essentials.ItemGroups;
35
import com.earth2me.essentials.utils.MaterialUtil;
46
import com.earth2me.essentials.utils.VersionUtil;
7+
import net.ess3.api.IEssentials;
58
import org.bukkit.entity.Player;
69
import org.bukkit.inventory.EntityEquipment;
710
import org.bukkit.inventory.Inventory;
@@ -87,6 +90,22 @@ public static boolean containsAtLeast(final Player player, final ItemStack item,
8790
return false;
8891
}
8992

93+
public static boolean containsAtLeast(final Player player, IEssentials ess, final ItemGroupQuery query) {
94+
int amount = query.getAmount();
95+
for (final ItemStack invItem : player.getInventory().getContents()) {
96+
if (isEmpty(invItem)) {
97+
continue;
98+
}
99+
if (query.contains(ess, invItem.getType())) {
100+
amount -= invItem.getAmount();
101+
if (amount <= 0) {
102+
return true;
103+
}
104+
}
105+
}
106+
return false;
107+
}
108+
90109
public static boolean hasSpace(final Player player, final int maxStack, final boolean includeArmor, ItemStack... items) {
91110
items = normalizeItems(cloneItems(items));
92111
final InventoryData inventoryData = parseInventoryData(player.getInventory(), items, maxStack, includeArmor);
@@ -319,6 +338,41 @@ public static boolean removeItemAmount(final Player player, final ItemStack toRe
319338
return false;
320339
}
321340

341+
public static boolean removeItemAmount(final Player player, final IEssentials ess, final ItemGroupQuery query) {
342+
final List<Integer> clearSlots = new ArrayList<>();
343+
final ItemStack[] items = player.getInventory().getContents();
344+
345+
int amount = query.getAmount();
346+
for (int i = 0; i < items.length; i++) {
347+
final ItemStack item = items[i];
348+
if (isEmpty(item)) {
349+
continue;
350+
}
351+
352+
if (query.contains(ess, item.getType())) {
353+
if (item.getAmount() >= amount) {
354+
item.setAmount(item.getAmount() - amount);
355+
player.getInventory().setItem(i, item);
356+
for (final int slot : clearSlots) {
357+
clearSlot(player, slot);
358+
}
359+
return true;
360+
} else {
361+
amount -= item.getAmount();
362+
clearSlots.add(i);
363+
}
364+
365+
if (amount == 0) {
366+
for (final int slot : clearSlots) {
367+
clearSlot(player, slot);
368+
}
369+
return true;
370+
}
371+
}
372+
}
373+
return false;
374+
}
375+
322376
public static void clearSlot(final Player player, final int slot) {
323377
final ItemStack item = player.getInventory().getItem(slot);
324378
if (!isEmpty(item)) {

‎Essentials/src/main/java/com/earth2me/essentials/signs/EssentialsSign.java‎

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
import com.earth2me.essentials.ChargeException;
44
import com.earth2me.essentials.CommandSource;
5+
import com.earth2me.essentials.ItemGroupQuery;
56
import com.earth2me.essentials.MetaItemStack;
67
import com.earth2me.essentials.Trade;
78
import com.earth2me.essentials.User;
@@ -345,6 +346,12 @@ protected final void validateTrade(final ISign sign, final int amountIndex, fina
345346
sign.setLine(itemIndex, "exp");
346347
return;
347348
}
349+
if(itemType.startsWith("~")){
350+
final int amount = getIntegerPositive(getSignText(sign, amountIndex));
351+
sign.setLine(amountIndex, Integer.toString(amount));
352+
sign.setLine(itemIndex, "§6~§r"+itemType.substring(1));
353+
return;
354+
}
348355
final Trade trade = getTrade(sign, amountIndex, itemIndex, player, ess);
349356
final ItemStack item = trade.getItemStack();
350357
sign.setLine(amountIndex, Integer.toString(item.getAmount()));
@@ -361,6 +368,11 @@ protected final Trade getTrade(final ISign sign, final int amountIndex, final in
361368
final int amount = getIntegerPositive(getSignText(sign, amountIndex));
362369
return new Trade(amount, ess);
363370
}
371+
if(itemType.startsWith("§6~§r")){
372+
final int amount = Math.min(getIntegerPositive(getSignText(sign, amountIndex)), 64 * player.getBase().getInventory().getSize());
373+
final ItemGroupQuery query = new ItemGroupQuery(itemType.substring(5), amount);
374+
return new Trade(query, ess);
375+
}
364376
final ItemStack item = getItemStack(itemType, 1, allowId, ess);
365377
final int amount = Math.min(getIntegerPositive(getSignText(sign, amountIndex)), item.getType().getMaxStackSize() * player.getBase().getInventory().getSize());
366378
if (item.getType() == Material.AIR || amount < 1) {

‎Essentials/src/main/java/com/earth2me/essentials/signs/SignSell.java‎

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
package com.earth2me.essentials.signs;
22

33
import com.earth2me.essentials.ChargeException;
4+
import com.earth2me.essentials.ItemGroupQuery;
45
import com.earth2me.essentials.Trade;
56
import com.earth2me.essentials.Trade.OverflowType;
67
import com.earth2me.essentials.User;
@@ -31,7 +32,7 @@ protected boolean onSignInteract(final ISign sign, final User player, final Stri
3132
// Check if the player is trying to sell in bulk.
3233
if (ess.getSettings().isAllowBulkBuySell() && player.getBase().isSneaking()) {
3334
final ItemStack heldItem = player.getItemInHand();
34-
if (charge.getItemStack().isSimilar(heldItem)) {
35+
if (charge.getItemStack() != null && charge.getItemStack().isSimilar(heldItem)) {
3536
final int initialItemAmount = charge.getItemStack().getAmount();
3637
final int newItemAmount = heldItem.getAmount();
3738
final ItemStack item = charge.getItemStack();
@@ -44,6 +45,17 @@ protected boolean onSignInteract(final ISign sign, final User player, final Stri
4445
pricePerSingleItem = pricePerSingleItem.multiply(new BigDecimal(newItemAmount));
4546
pricePerSingleItem = pricePerSingleItem.multiply(ess.getSettings().getMultiplier(player));
4647
money = new Trade(pricePerSingleItem, ess);
48+
}else if(charge.getItemGroupQuery() != null && charge.getItemGroupQuery().contains(ess, heldItem.getType())){
49+
final ItemGroupQuery groupQuery = charge.getItemGroupQuery();
50+
final int initialItemAmount = groupQuery.getAmount();
51+
final int newItemAmount = heldItem.getAmount();
52+
charge = new Trade(new ItemGroupQuery(groupQuery.getItemGroup(), newItemAmount), ess);
53+
54+
final BigDecimal chargeAmount = money.getMoney();
55+
//noinspection BigDecimalMethodWithoutRoundingCalled
56+
BigDecimal pricePerSingleItem = chargeAmount.divide(new BigDecimal(initialItemAmount));
57+
pricePerSingleItem = pricePerSingleItem.multiply(new BigDecimal(newItemAmount));
58+
money = new Trade(pricePerSingleItem, ess);
4759
}
4860
}
4961

Lines changed: 26 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
package net.ess3.api;
2+
3+
import com.earth2me.essentials.IConf;
4+
import org.bukkit.Material;
5+
6+
import java.util.List;
7+
import java.util.Set;
8+
9+
/**
10+
* Provides access to the storage of item groups. Maintainers should add methods to <i>this interface</i>.
11+
*/
12+
public interface IItemGroups extends IConf {
13+
14+
/**
15+
* Gets the set of saved item groups from config file
16+
* @return the set of item groups
17+
*/
18+
Set<String> getItemGroups();
19+
20+
/**
21+
* Gets the list of item materials inside an item group
22+
* @param group the item group
23+
* @return a list of items in the item group
24+
*/
25+
List<Material> getItemGroup(String group);
26+
}
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
#EssentialsX item group configuration
2+
#Item groups are currently used only by sell sign
3+
#By creating a group here and using ~[group_id] on the sign
4+
#Any player will be able to sell items with one of the types written here
5+
6+
#You can use minecraft tags as groups, for reference https://minecraft.fandom.com/wiki/Tag#Item_tags
7+
#Example
8+
#dirt:
9+
# - DIRT
10+
# - GRASS
11+
# - PODZOL
12+
# - COARSE_DIRT
13+
# - ROOTED_DIRT

0 commit comments

Comments
 (0)