minecraft-source/src/net/minecraft/advancements/Advancement.java

367 lines
15 KiB
Java

package net.minecraft.advancements;
import org.apache.commons.lang3.ArrayUtils;
import com.google.gson.JsonSyntaxException;
import net.minecraft.util.GsonHelper;
import com.google.gson.JsonDeserializationContext;
import net.minecraft.network.FriendlyByteBuf;
import java.util.Iterator;
import com.google.gson.JsonArray;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import java.util.function.Consumer;
import java.util.Collection;
import java.util.function.Function;
import net.minecraft.world.level.ItemLike;
import net.minecraft.world.item.ItemStack;
import com.google.common.collect.Maps;
import net.minecraft.network.chat.Style;
import java.util.Arrays;
import net.minecraft.ChatFormatting;
import net.minecraft.network.chat.HoverEvent;
import net.minecraft.network.chat.TextComponent;
import com.google.common.collect.ImmutableMap;
import com.google.common.collect.Sets;
import javax.annotation.Nullable;
import net.minecraft.network.chat.Component;
import java.util.Set;
import java.util.Map;
import net.minecraft.resources.ResourceLocation;
public class Advancement {
private final Advancement parent;
private final DisplayInfo display;
private final AdvancementRewards rewards;
private final ResourceLocation id;
private final Map<String, Criterion> criteria;
private final String[][] requirements;
private final Set<Advancement> children;
private final Component chatComponent;
public Advancement(final ResourceLocation sm, @Nullable final Advancement u, @Nullable final DisplayInfo ad, final AdvancementRewards x, final Map<String, Criterion> map, final String[][] arr) {
this.children = Sets.newLinkedHashSet();
this.id = sm;
this.display = ad;
this.criteria = ImmutableMap.copyOf(map);
this.parent = u;
this.rewards = x;
this.requirements = arr;
if (u != null) {
u.addChild(this);
}
if (ad == null) {
this.chatComponent = new TextComponent(sm.toString());
}
else {
final Component lf8 = ad.getTitle();
final ChatFormatting g9 = ad.getFrame().getChatColor();
final Component lf9 = lf8.deepCopy().withStyle(g9).append("\n").append(ad.getDescription());
final Component lf10 = lf8.deepCopy().withStyle(ln -> ln.setHoverEvent(new HoverEvent(HoverEvent.Action.SHOW_TEXT, lf9)));
this.chatComponent = new TextComponent("[").append(lf10).append("]").withStyle(g9);
}
}
public Builder deconstruct() {
return new Builder((this.parent == null) ? null : this.parent.getId(), this.display, this.rewards, (Map)this.criteria, this.requirements);
}
@Nullable
public Advancement getParent() {
return this.parent;
}
@Nullable
public DisplayInfo getDisplay() {
return this.display;
}
public AdvancementRewards getRewards() {
return this.rewards;
}
@Override
public String toString() {
return "SimpleAdvancement{id=" + this.getId() + ", parent=" + ((this.parent == null) ? "null" : this.parent.getId()) + ", display=" + this.display + ", rewards=" + this.rewards + ", criteria=" + this.criteria + ", requirements=" + Arrays.deepToString(this.requirements) + '}';
}
public Iterable<Advancement> getChildren() {
return this.children;
}
public Map<String, Criterion> getCriteria() {
return this.criteria;
}
public int getMaxCriteraRequired() {
return this.requirements.length;
}
public void addChild(final Advancement u) {
this.children.add(u);
}
public ResourceLocation getId() {
return this.id;
}
@Override
public boolean equals(final Object object) {
if (this == object) {
return true;
}
if (!(object instanceof Advancement)) {
return false;
}
final Advancement u3 = (Advancement)object;
return this.id.equals(u3.id);
}
@Override
public int hashCode() {
return this.id.hashCode();
}
public String[][] getRequirements() {
return this.requirements;
}
public Component getChatComponent() {
return this.chatComponent;
}
public static class Builder {
private ResourceLocation parentId;
private Advancement parent;
private DisplayInfo display;
private AdvancementRewards rewards;
private Map<String, Criterion> criteria;
private String[][] requirements;
private RequirementsStrategy requirementsStrategy;
private Builder(@Nullable final ResourceLocation sm, @Nullable final DisplayInfo ad, final AdvancementRewards x, final Map<String, Criterion> map, final String[][] arr) {
this.rewards = AdvancementRewards.EMPTY;
this.criteria = Maps.newLinkedHashMap();
this.requirementsStrategy = RequirementsStrategy.AND;
this.parentId = sm;
this.display = ad;
this.rewards = x;
this.criteria = map;
this.requirements = arr;
}
private Builder() {
this.rewards = AdvancementRewards.EMPTY;
this.criteria = Maps.newLinkedHashMap();
this.requirementsStrategy = RequirementsStrategy.AND;
}
public static Builder advancement() {
return new Builder();
}
public Builder parent(final Advancement u) {
this.parent = u;
return this;
}
public Builder parent(final ResourceLocation sm) {
this.parentId = sm;
return this;
}
public Builder display(final ItemStack ben, final Component lf2, final Component lf3, @Nullable final ResourceLocation sm, final FrameType ae, final boolean boolean6, final boolean boolean7, final boolean boolean8) {
return this.display(new DisplayInfo(ben, lf2, lf3, sm, ae, boolean6, boolean7, boolean8));
}
public Builder display(final ItemLike bjv, final Component lf2, final Component lf3, @Nullable final ResourceLocation sm, final FrameType ae, final boolean boolean6, final boolean boolean7, final boolean boolean8) {
return this.display(new DisplayInfo(new ItemStack(bjv.asItem()), lf2, lf3, sm, ae, boolean6, boolean7, boolean8));
}
public Builder display(final DisplayInfo ad) {
this.display = ad;
return this;
}
public Builder rewards(final AdvancementRewards.Builder a) {
return this.rewards(a.build());
}
public Builder rewards(final AdvancementRewards x) {
this.rewards = x;
return this;
}
public Builder addCriterion(final String string, final CriterionTriggerInstance ac) {
return this.addCriterion(string, new Criterion(ac));
}
public Builder addCriterion(final String string, final Criterion z) {
if (this.criteria.containsKey(string)) {
throw new IllegalArgumentException("Duplicate criterion " + string);
}
this.criteria.put(string, z);
return this;
}
public Builder requirements(final RequirementsStrategy af) {
this.requirementsStrategy = af;
return this;
}
public boolean canBuild(final Function<ResourceLocation, Advancement> function) {
if (this.parentId == null) {
return true;
}
if (this.parent == null) {
this.parent = function.apply(this.parentId);
}
return this.parent != null;
}
public Advancement build(final ResourceLocation sm) {
if (!this.canBuild(sm -> null)) {
throw new IllegalStateException("Tried to build incomplete advancement!");
}
if (this.requirements == null) {
this.requirements = this.requirementsStrategy.createRequirements(this.criteria.keySet());
}
return new Advancement(sm, this.parent, this.display, this.rewards, this.criteria, this.requirements);
}
public Advancement save(final Consumer<Advancement> consumer, final String string) {
final Advancement u4 = this.build(new ResourceLocation(string));
consumer.accept(u4);
return u4;
}
public JsonObject serializeToJson() {
if (this.requirements == null) {
this.requirements = this.requirementsStrategy.createRequirements(this.criteria.keySet());
}
final JsonObject jsonObject2 = new JsonObject();
if (this.parent != null) {
jsonObject2.addProperty("parent", this.parent.getId().toString());
}
else if (this.parentId != null) {
jsonObject2.addProperty("parent", this.parentId.toString());
}
if (this.display != null) {
jsonObject2.add("display", this.display.serializeToJson());
}
jsonObject2.add("rewards", this.rewards.serializeToJson());
final JsonObject jsonObject3 = new JsonObject();
for (final Map.Entry<String, Criterion> entry5 : this.criteria.entrySet()) {
jsonObject3.add(entry5.getKey(), entry5.getValue().serializeToJson());
}
jsonObject2.add("criteria", jsonObject3);
final JsonArray jsonArray4 = new JsonArray();
for (final String[] arr8 : this.requirements) {
final JsonArray jsonArray5 = new JsonArray();
for (final String string13 : arr8) {
jsonArray5.add(string13);
}
jsonArray4.add(jsonArray5);
}
jsonObject2.add("requirements", jsonArray4);
return jsonObject2;
}
public void serializeToNetwork(final FriendlyByteBuf kv) {
if (this.parentId == null) {
kv.writeBoolean(false);
}
else {
kv.writeBoolean(true);
kv.writeResourceLocation(this.parentId);
}
if (this.display == null) {
kv.writeBoolean(false);
}
else {
kv.writeBoolean(true);
this.display.serializeToNetwork(kv);
}
Criterion.serializeToNetwork(this.criteria, kv);
kv.writeVarInt(this.requirements.length);
for (final String[] arr6 : this.requirements) {
kv.writeVarInt(arr6.length);
for (final String string10 : arr6) {
kv.writeUtf(string10);
}
}
}
@Override
public String toString() {
return "Task Advancement{parentId=" + this.parentId + ", display=" + this.display + ", rewards=" + this.rewards + ", criteria=" + this.criteria + ", requirements=" + Arrays.deepToString(this.requirements) + '}';
}
public static Builder fromJson(final JsonObject jsonObject, final JsonDeserializationContext jsonDeserializationContext) {
final ResourceLocation sm3 = jsonObject.has("parent") ? new ResourceLocation(GsonHelper.getAsString(jsonObject, "parent")) : null;
final DisplayInfo ad4 = jsonObject.has("display") ? DisplayInfo.fromJson(GsonHelper.getAsJsonObject(jsonObject, "display"), jsonDeserializationContext) : null;
final AdvancementRewards x5 = GsonHelper.<AdvancementRewards>getAsObject(jsonObject, "rewards", AdvancementRewards.EMPTY, jsonDeserializationContext, AdvancementRewards.class);
final Map<String, Criterion> map6 = Criterion.criteriaFromJson(GsonHelper.getAsJsonObject(jsonObject, "criteria"), jsonDeserializationContext);
if (map6.isEmpty()) {
throw new JsonSyntaxException("Advancement criteria cannot be empty");
}
final JsonArray jsonArray7 = GsonHelper.getAsJsonArray(jsonObject, "requirements", new JsonArray());
String[][] arr8 = new String[jsonArray7.size()][];
for (int integer9 = 0; integer9 < jsonArray7.size(); ++integer9) {
final JsonArray jsonArray8 = GsonHelper.convertToJsonArray(jsonArray7.get(integer9), "requirements[" + integer9 + "]");
arr8[integer9] = new String[jsonArray8.size()];
for (int integer10 = 0; integer10 < jsonArray8.size(); ++integer10) {
arr8[integer9][integer10] = GsonHelper.convertToString(jsonArray8.get(integer10), "requirements[" + integer9 + "][" + integer10 + "]");
}
}
if (arr8.length == 0) {
arr8 = new String[map6.size()][];
int integer9 = 0;
for (final String string11 : map6.keySet()) {
arr8[integer9++] = new String[] { string11 };
}
}
for (final String[] arr9 : arr8) {
if (arr9.length == 0 && map6.isEmpty()) {
throw new JsonSyntaxException("Requirement entry cannot be empty");
}
for (final String string12 : arr9) {
if (!map6.containsKey(string12)) {
throw new JsonSyntaxException("Unknown required criterion '" + string12 + "'");
}
}
}
for (final String string13 : map6.keySet()) {
boolean boolean11 = false;
for (final String[] arr10 : arr8) {
if (ArrayUtils.contains((Object[])arr10, string13)) {
boolean11 = true;
break;
}
}
if (!boolean11) {
throw new JsonSyntaxException("Criterion '" + string13 + "' isn't a requirement for completion. This isn't supported behaviour, all criteria must be required.");
}
}
return new Builder(sm3, ad4, x5, map6, arr8);
}
public static Builder fromNetwork(final FriendlyByteBuf kv) {
final ResourceLocation sm2 = kv.readBoolean() ? kv.readResourceLocation() : null;
final DisplayInfo ad3 = kv.readBoolean() ? DisplayInfo.fromNetwork(kv) : null;
final Map<String, Criterion> map4 = Criterion.criteriaFromNetwork(kv);
final String[][] arr5 = new String[kv.readVarInt()][];
for (int integer6 = 0; integer6 < arr5.length; ++integer6) {
arr5[integer6] = new String[kv.readVarInt()];
for (int integer7 = 0; integer7 < arr5[integer6].length; ++integer7) {
arr5[integer6][integer7] = kv.readUtf(32767);
}
}
return new Builder(sm2, ad3, AdvancementRewards.EMPTY, map4, arr5);
}
public Map<String, Criterion> getCriteria() {
return this.criteria;
}
}
}