Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Add support for oredict item predicates in advancements, and add a re…
…gistry for item predicates (#4188)
- Loading branch information
1 parent
82d735e
commit ee449e4
Showing
5 changed files
with
337 additions
and
0 deletions.
There are no files selected for viewing
16 changes: 16 additions & 0 deletions
16
patches/minecraft/net/minecraft/advancements/critereon/ItemPredicate.java.patch
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
--- ../src-base/minecraft/net/minecraft/advancements/critereon/ItemPredicate.java | ||
+++ ../src-work/minecraft/net/minecraft/advancements/critereon/ItemPredicate.java | ||
@@ -104,6 +104,7 @@ | ||
if (p_192492_0_ != null && !p_192492_0_.isJsonNull()) | ||
{ | ||
JsonObject jsonobject = JsonUtils.func_151210_l(p_192492_0_, "item"); | ||
+ if (jsonobject.has("type")) | ||
+ { | ||
+ final ResourceLocation rl = new ResourceLocation(JsonUtils.func_151200_h(jsonobject, "type")); | ||
+ final Map<ResourceLocation, java.util.function.Function<JsonObject, ItemPredicate>> map = net.minecraftforge.advancements.critereon.ItemPredicates.getPredicates(); | ||
+ if (map.containsKey(rl)) return map.get(rl).apply(jsonobject); | ||
+ else throw new JsonSyntaxException("There is no ItemPredicate of type "+rl); | ||
+ } | ||
MinMaxBounds minmaxbounds = MinMaxBounds.func_192515_a(jsonobject.get("count")); | ||
MinMaxBounds minmaxbounds1 = MinMaxBounds.func_192515_a(jsonobject.get("durability")); | ||
Integer integer = jsonobject.has("data") ? JsonUtils.func_151203_m(jsonobject, "data") : null; |
49 changes: 49 additions & 0 deletions
49
src/main/java/net/minecraftforge/advancements/critereon/ItemPredicates.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
/* | ||
* Minecraft Forge | ||
* Copyright (c) 2016. | ||
* | ||
* This library is free software; you can redistribute it and/or | ||
* modify it under the terms of the GNU Lesser General Public | ||
* License as published by the Free Software Foundation version 2.1 | ||
* of the License. | ||
* | ||
* This library is distributed in the hope that it will be useful, | ||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
* Lesser General Public License for more details. | ||
* | ||
* You should have received a copy of the GNU Lesser General Public | ||
* License along with this library; if not, write to the Free Software | ||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
*/ | ||
|
||
package net.minecraftforge.advancements.critereon; | ||
|
||
import com.google.gson.JsonObject; | ||
import gnu.trove.map.hash.THashMap; | ||
import net.minecraft.advancements.critereon.ItemPredicate; | ||
import net.minecraft.util.ResourceLocation; | ||
|
||
import java.util.Collections; | ||
import java.util.Map; | ||
import java.util.function.Function; | ||
|
||
public class ItemPredicates | ||
{ | ||
private static final Map<ResourceLocation, Function<JsonObject, ItemPredicate>> predicates = new THashMap<>(); | ||
|
||
static | ||
{ | ||
register(new ResourceLocation("forge:ore_dict"), OredictItemPredicate::new); | ||
} | ||
|
||
public static void register(ResourceLocation rl, Function<JsonObject, ItemPredicate> jsonToPredicate) | ||
{ | ||
predicates.put(rl, jsonToPredicate); | ||
} | ||
|
||
public static Map<ResourceLocation, Function<JsonObject, ItemPredicate>> getPredicates() | ||
{ | ||
return Collections.unmodifiableMap(predicates); | ||
} | ||
} |
50 changes: 50 additions & 0 deletions
50
src/main/java/net/minecraftforge/advancements/critereon/OredictItemPredicate.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
/* | ||
* Minecraft Forge | ||
* Copyright (c) 2016. | ||
* | ||
* This library is free software; you can redistribute it and/or | ||
* modify it under the terms of the GNU Lesser General Public | ||
* License as published by the Free Software Foundation version 2.1 | ||
* of the License. | ||
* | ||
* This library is distributed in the hope that it will be useful, | ||
* but WITHOUT ANY WARRANTY; without even the implied warranty of | ||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | ||
* Lesser General Public License for more details. | ||
* | ||
* You should have received a copy of the GNU Lesser General Public | ||
* License along with this library; if not, write to the Free Software | ||
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA | ||
*/ | ||
|
||
package net.minecraftforge.advancements.critereon; | ||
|
||
|
||
import com.google.gson.JsonObject; | ||
import net.minecraft.util.JsonUtils; | ||
import org.apache.commons.lang3.ArrayUtils; | ||
|
||
import net.minecraft.advancements.critereon.ItemPredicate; | ||
import net.minecraft.item.ItemStack; | ||
import net.minecraftforge.oredict.OreDictionary; | ||
|
||
/** | ||
* An {@link ItemPredicate} that matches oredicts. | ||
*/ | ||
public class OredictItemPredicate extends ItemPredicate | ||
{ | ||
private final String ore; | ||
|
||
public OredictItemPredicate(String ore) | ||
{ | ||
this.ore = ore; | ||
} | ||
|
||
public OredictItemPredicate(JsonObject jsonObject) { this(JsonUtils.getString(jsonObject, "ore")); } | ||
|
||
@Override | ||
public boolean test(ItemStack stack) | ||
{ | ||
return !stack.isEmpty() && ArrayUtils.contains(OreDictionary.getOreIDs(stack), OreDictionary.getOreID(ore)); | ||
} | ||
} |
198 changes: 198 additions & 0 deletions
198
src/test/java/net/minecraftforge/debug/OredictItemPredicateTest.java
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,198 @@ | ||
package net.minecraftforge.debug; | ||
|
||
import com.google.gson.JsonDeserializationContext; | ||
import com.google.gson.JsonObject; | ||
import net.minecraft.advancements.CriteriaTriggers; | ||
import net.minecraft.advancements.ICriterionTrigger; | ||
import net.minecraft.advancements.PlayerAdvancements; | ||
import net.minecraft.advancements.critereon.AbstractCriterionInstance; | ||
import net.minecraft.entity.player.EntityPlayerMP; | ||
import net.minecraft.entity.player.InventoryPlayer; | ||
import net.minecraft.util.ResourceLocation; | ||
import net.minecraftforge.event.entity.EntityJoinWorldEvent; | ||
import net.minecraftforge.fml.common.Mod; | ||
import net.minecraftforge.fml.common.eventhandler.SubscribeEvent; | ||
|
||
import java.lang.invoke.MethodHandle; | ||
import java.lang.invoke.MethodHandles; | ||
import java.lang.reflect.Method; | ||
import java.util.ArrayList; | ||
import java.util.HashMap; | ||
import java.util.HashSet; | ||
import java.util.List; | ||
import java.util.Map; | ||
import java.util.Set; | ||
|
||
/** | ||
* Most of the real work is in the advancements directory of this mod. | ||
* This mod tests ore-dict advancement triggers. | ||
*/ | ||
@Mod.EventBusSubscriber | ||
@Mod(modid = OredictItemPredicateTest.MODID, name = "Oredict Item Predicate Test", version = "1.0", acceptableRemoteVersions = "*") | ||
public class OredictItemPredicateTest | ||
{ | ||
public static final String MODID = "oredict_predicate"; | ||
|
||
static final boolean ENABLED = false; | ||
|
||
private static final MethodHandle ctRegister; | ||
static | ||
{ | ||
try | ||
{ | ||
final Method tmp = CriteriaTriggers.class.getDeclaredMethod("register"/* func_192118_a */, ICriterionTrigger.class); | ||
tmp.setAccessible(true); | ||
ctRegister = MethodHandles.lookup().unreflect(tmp); | ||
} | ||
catch (Throwable e) | ||
{ | ||
throw new RuntimeException(e); | ||
} | ||
} | ||
|
||
public static final EnabledTrigger ENABLED_TRIGGER; | ||
static | ||
{ | ||
try | ||
{ | ||
ENABLED_TRIGGER = (EnabledTrigger)(ICriterionTrigger)ctRegister.invokeExact((ICriterionTrigger)new EnabledTrigger()); | ||
} | ||
catch (Throwable e) | ||
{ | ||
throw new RuntimeException(e); | ||
} | ||
} | ||
|
||
// trigger the enabled advancement on player entry | ||
@SubscribeEvent | ||
public static void triggerAdv(EntityJoinWorldEvent event) | ||
{ | ||
if (event.getEntity() instanceof EntityPlayerMP) | ||
{ | ||
final EntityPlayerMP player = (EntityPlayerMP)event.getEntity(); | ||
ENABLED_TRIGGER.trigger(player, player.inventory); | ||
} | ||
} | ||
|
||
|
||
/** | ||
* Far more work than expected…oh well. | ||
*/ | ||
public static class EnabledTrigger implements ICriterionTrigger<EnabledTrigger.Instance> | ||
{ | ||
public static final ResourceLocation ID = new ResourceLocation(MODID, "is_enabled"); | ||
private final Map<PlayerAdvancements, Listeners> listeners = new HashMap<>(); | ||
|
||
@Override | ||
public ResourceLocation getId() | ||
{ | ||
return ID; | ||
} | ||
|
||
@Override | ||
public void addListener(PlayerAdvancements playerAdvancementsIn, Listener<Instance> listener) | ||
{ | ||
Listeners listeners = this.listeners.computeIfAbsent(playerAdvancementsIn, Listeners::new); | ||
|
||
listeners.add(listener); | ||
} | ||
|
||
@Override | ||
public void removeListener(PlayerAdvancements playerAdvancementsIn, Listener<Instance> listener) | ||
{ | ||
Listeners listeners = this.listeners.get(playerAdvancementsIn); | ||
|
||
if (listeners != null) | ||
{ | ||
listeners.remove(listener); | ||
|
||
if (listeners.isEmpty()) | ||
{ | ||
this.listeners.remove(playerAdvancementsIn); | ||
} | ||
} | ||
} | ||
|
||
@Override | ||
public void removeAllListeners(PlayerAdvancements playerAdvancementsIn) | ||
{ | ||
this.listeners.remove(playerAdvancementsIn); | ||
} | ||
|
||
@Override | ||
public Instance deserializeInstance(JsonObject json, JsonDeserializationContext context) | ||
{ | ||
return new Instance(); | ||
} | ||
|
||
public void trigger(EntityPlayerMP player, InventoryPlayer inventory) | ||
{ | ||
Listeners listeners = this.listeners.get(player.getAdvancements()); | ||
|
||
if (listeners != null) | ||
{ | ||
listeners.trigger(inventory); | ||
} | ||
} | ||
|
||
public static class Instance extends AbstractCriterionInstance | ||
{ | ||
public Instance() | ||
{ | ||
super(ID); | ||
} | ||
} | ||
|
||
static class Listeners | ||
{ | ||
private final PlayerAdvancements playerAdvancements; | ||
private final Set<Listener<Instance>> listeners = new HashSet<>(); | ||
|
||
public Listeners(PlayerAdvancements playerAdvancementsIn) | ||
{ | ||
this.playerAdvancements = playerAdvancementsIn; | ||
} | ||
|
||
public boolean isEmpty() | ||
{ | ||
return this.listeners.isEmpty(); | ||
} | ||
|
||
public void add(ICriterionTrigger.Listener<Instance> listener) | ||
{ | ||
this.listeners.add(listener); | ||
} | ||
|
||
public void remove(ICriterionTrigger.Listener<Instance> listener) | ||
{ | ||
this.listeners.remove(listener); | ||
} | ||
|
||
public void trigger(InventoryPlayer inventory) | ||
{ | ||
List<Listener<Instance>> list = null; | ||
|
||
for (ICriterionTrigger.Listener<Instance> listener : this.listeners) | ||
{ | ||
if (ENABLED) | ||
{ | ||
if (list == null) | ||
{ | ||
list = new ArrayList<>(); | ||
} | ||
|
||
list.add(listener); | ||
} | ||
} | ||
|
||
if (list != null) | ||
{ | ||
for (ICriterionTrigger.Listener<Instance> listener1 : list) | ||
{ | ||
listener1.grantCriterion(this.playerAdvancements); | ||
} | ||
} | ||
} | ||
} | ||
} | ||
} |
24 changes: 24 additions & 0 deletions
24
src/test/resources/assets/oredict_predicate/advancements/recipes/wood_unlock_tnt.json
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,24 @@ | ||
{ | ||
"parent": "minecraft:recipes/root", | ||
"rewards": { | ||
"recipes": [ "minecraft:tnt" ] | ||
}, | ||
"criteria": { | ||
"has_wood": { | ||
"trigger": "minecraft:inventory_changed", | ||
"conditions": { | ||
"items": [ | ||
{ | ||
"type": "forge:ore_dict", | ||
"ore": "plankWood" | ||
} | ||
] | ||
} | ||
}, | ||
"mod_enabled": { | ||
"trigger": "oredict_predicate:is_enabled", | ||
"conditions": {} | ||
} | ||
}, | ||
"requirements": [["has_wood"], ["mod_enabled"]] | ||
} |