diff --git a/common-files/src/main/resources/translations/en.yml b/common-files/src/main/resources/translations/en.yml index 13f426037..93b5e5c72 100644 --- a/common-files/src/main/resources/translations/en.yml +++ b/common-files/src/main/resources/translations/en.yml @@ -374,6 +374,7 @@ warning.config.loot_table.function.apply_bonus.missing_enchantment: "Iss warning.config.loot_table.function.apply_bonus.missing_formula: "Issue found in file - '' has a misconfigured loot table, function 'apply_bonus' is missing the required 'formula' argument." warning.config.loot_table.function.drop_exp.missing_count: "Issue found in file - '' has a misconfigured loot table, function 'drop_exp' is missing the required 'count' argument." warning.config.loot_table.function.set_count.missing_count: "Issue found in file - '' has a misconfigured loot table, function 'set_count' is missing the required 'count' argument." +warning.config.loot_table.function.apply_data.missing_data: "Issue found in file - '' has a misconfigured loot table, function 'apply_data' is missing the required 'data' argument." warning.config.loot_table.entry.missing_type: "Issue found in file - '' has a misconfigured loot table, one of the entries is missing the required 'type' argument." warning.config.loot_table.entry.invalid_type: "Issue found in file - '' has a misconfigured loot table, one of the entries is using an invalid entry type ''." warning.config.loot_table.entry.exp.missing_count: "Issue found in file - '' has a misconfigured loot table, entry 'exp' is missing the required 'count' argument." diff --git a/core/src/main/java/net/momirealms/craftengine/core/item/context/UseOnContext.java b/core/src/main/java/net/momirealms/craftengine/core/item/context/UseOnContext.java index dc59e38aa..21a4ae92e 100644 --- a/core/src/main/java/net/momirealms/craftengine/core/item/context/UseOnContext.java +++ b/core/src/main/java/net/momirealms/craftengine/core/item/context/UseOnContext.java @@ -73,6 +73,10 @@ public class UseOnContext { return this.level; } + public World getWorld() { + return this.level; + } + public Direction getHorizontalDirection() { return this.player == null ? Direction.NORTH : this.player.getDirection(); } diff --git a/core/src/main/java/net/momirealms/craftengine/core/loot/function/ApplyDataFunction.java b/core/src/main/java/net/momirealms/craftengine/core/loot/function/ApplyDataFunction.java new file mode 100644 index 000000000..168d9e6fa --- /dev/null +++ b/core/src/main/java/net/momirealms/craftengine/core/loot/function/ApplyDataFunction.java @@ -0,0 +1,58 @@ +package net.momirealms.craftengine.core.loot.function; + +import net.momirealms.craftengine.core.item.Item; +import net.momirealms.craftengine.core.item.ItemBuildContext; +import net.momirealms.craftengine.core.item.modifier.ItemDataModifier; +import net.momirealms.craftengine.core.item.recipe.result.ApplyItemDataPostProcessor; +import net.momirealms.craftengine.core.loot.LootConditions; +import net.momirealms.craftengine.core.loot.LootContext; +import net.momirealms.craftengine.core.plugin.context.Condition; +import net.momirealms.craftengine.core.plugin.context.number.NumberProvider; +import net.momirealms.craftengine.core.plugin.context.number.NumberProviders; +import net.momirealms.craftengine.core.registry.BuiltInRegistries; +import net.momirealms.craftengine.core.util.Key; +import net.momirealms.craftengine.core.util.ResourceConfigUtils; + +import java.util.*; + +public class ApplyDataFunction extends AbstractLootConditionalFunction { + public static final Factory FACTORY = new Factory<>(); + private final ItemDataModifier[] modifiers; + + public ApplyDataFunction(List> conditions, ItemDataModifier[] modifiers) { + super(conditions); + this.modifiers = modifiers; + } + + @Override + public Key type() { + return LootFunctions.APPLY_DATA; + } + + @SuppressWarnings({"unchecked", "rawtypes"}) + @Override + protected Item applyInternal(Item item, LootContext context) { + ItemBuildContext ctx = ItemBuildContext.of(context.player()); + for (ItemDataModifier modifier : this.modifiers) { + item = modifier.apply(item, ctx); + } + return item; + } + + public static class Factory implements LootFunctionFactory { + @SuppressWarnings("unchecked") + @Override + public LootFunction create(Map arguments) { + List> modifiers = new ArrayList<>(); + Map data = ResourceConfigUtils.getAsMap(ResourceConfigUtils.requireNonNullOrThrow(arguments.get("data"), "warning.config.loot_table.function.apply_data.missing_data"), "data"); + for (Map.Entry entry : data.entrySet()) { + Optional.ofNullable(BuiltInRegistries.ITEM_DATA_MODIFIER_FACTORY.getValue(Key.withDefaultNamespace(entry.getKey(), Key.DEFAULT_NAMESPACE))) + .ifPresent(factory -> modifiers.add(factory.create(entry.getValue()))); + } + List> conditions = Optional.ofNullable(arguments.get("conditions")) + .map(it -> LootConditions.fromMapList((List>) it)) + .orElse(Collections.emptyList()); + return new ApplyDataFunction<>(conditions, modifiers.toArray(new ItemDataModifier[0])); + } + } +} diff --git a/core/src/main/java/net/momirealms/craftengine/core/loot/function/LootFunctions.java b/core/src/main/java/net/momirealms/craftengine/core/loot/function/LootFunctions.java index c9d221c95..854e741e1 100644 --- a/core/src/main/java/net/momirealms/craftengine/core/loot/function/LootFunctions.java +++ b/core/src/main/java/net/momirealms/craftengine/core/loot/function/LootFunctions.java @@ -17,6 +17,7 @@ import java.util.function.BiFunction; public class LootFunctions { public static final Key APPLY_BONUS = Key.from("craftengine:apply_bonus"); + public static final Key APPLY_DATA = Key.from("craftengine:apply_data"); public static final Key SET_COUNT = Key.from("craftengine:set_count"); public static final Key EXPLOSION_DECAY = Key.from("craftengine:explosion_decay"); public static final Key DROP_EXP = Key.from("craftengine:drop_exp"); @@ -24,6 +25,7 @@ public class LootFunctions { static { register(SET_COUNT, SetCountFunction.FACTORY); + register(APPLY_DATA, ApplyDataFunction.FACTORY); register(EXPLOSION_DECAY, ExplosionDecayFunction.FACTORY); register(APPLY_BONUS, ApplyBonusCountFunction.FACTORY); register(DROP_EXP, DropExpFunction.FACTORY);