Skip to content

Commit baed23a

Browse files
committed
DTN dedicated Animation Format: Loader
1 parent eec695b commit baed23a

File tree

3 files changed

+149
-0
lines changed

3 files changed

+149
-0
lines changed

src/main/java/doggytalents/client/ClientSetup.java

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@
1717
import doggytalents.client.entity.model.FisherDogModel;
1818
import doggytalents.client.entity.model.SyncedRenderFunctionWithHeadModel;
1919
import doggytalents.client.entity.model.TorchDogModel;
20+
import doggytalents.client.entity.model.animation.DTNAnimationLoader;
2021
import doggytalents.client.entity.model.animation.DogAnimationRegistry;
2122
import doggytalents.client.entity.model.dog.DogModel;
2223
import doggytalents.client.entity.model.dog.NullDogModel;
@@ -443,5 +444,6 @@ public static void registerOverlay(RegisterGuiLayersEvent e) {
443444
public static void addClientReloadListeners(final RegisterClientReloadListenersEvent event) {
444445
event.registerReloadListener(DogTextureManager.INSTANCE);
445446
event.registerReloadListener(DogRandomNameRegistry.getInstance());
447+
event.registerReloadListener(DTNAnimationLoader.INSTANCE);
446448
}
447449
}
Lines changed: 142 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,142 @@
1+
package doggytalents.client.entity.model.animation;
2+
3+
import java.util.HashMap;
4+
import java.util.HashSet;
5+
import java.util.Locale;
6+
import java.util.Map;
7+
8+
import org.apache.logging.log4j.LogManager;
9+
import org.apache.logging.log4j.Logger;
10+
11+
import com.google.gson.Gson;
12+
import com.google.gson.JsonElement;
13+
import com.google.gson.JsonParseException;
14+
import com.mojang.serialization.Dynamic;
15+
import com.mojang.serialization.JsonOps;
16+
17+
import doggytalents.api.anim.DogAnimation;
18+
import doggytalents.common.lib.Constants;
19+
import doggytalents.common.util.Util;
20+
import net.minecraft.client.animation.AnimationDefinition;
21+
import net.minecraft.resources.ResourceLocation;
22+
import net.minecraft.server.packs.resources.ResourceManager;
23+
import net.minecraft.server.packs.resources.SimpleJsonResourceReloadListener;
24+
import net.minecraft.util.profiling.ProfilerFiller;
25+
26+
public class DTNAnimationLoader extends SimpleJsonResourceReloadListener {
27+
28+
// In charge of loading the animation files at
29+
// assets/doggytalents/doggytalents/dog_animations
30+
// Overriable via resourcepacks.
31+
32+
public static final Logger LOGGER = LogManager.getLogger(Constants.MOD_ID + "/animationLoader");
33+
34+
private final Map<ResourceLocation, DogAnimationHolder> holderMap = new HashMap<>();
35+
36+
private DTNAnimationLoader() {
37+
super(new Gson(), createRegistryPath());
38+
}
39+
40+
public static String createRegistryPath() {
41+
var registry = Util.getResource("dog_animations");
42+
return registry.getNamespace() + "/" + registry.getPath();
43+
}
44+
45+
@Override
46+
protected void apply(Map<ResourceLocation, JsonElement> contents, ResourceManager resourceManager,
47+
ProfilerFiller profiler) {
48+
49+
holderMap.values().forEach(DogAnimationHolder::invalidate);
50+
51+
var builtin_anims = new HashMap<ResourceLocation, AnimationDefinition>();
52+
for (var entry : contents.entrySet()) {
53+
final var id = entry.getKey();
54+
final var anim_json = entry.getValue();
55+
56+
//Don't load animations from different namespace for now.
57+
if (!id.getNamespace().equals(Constants.MOD_ID))
58+
continue;
59+
60+
var dynamic_data = new Dynamic<>(JsonOps.INSTANCE, anim_json);
61+
AnimationDefinition anim = null;
62+
try {
63+
anim = DTNAnimationCodec.CODEC.parse(dynamic_data)
64+
.getOrThrow(JsonParseException::new);
65+
} catch (Exception e) {
66+
LOGGER.error("Failed to load animation: {} ", id, e);
67+
}
68+
if (anim == null)
69+
continue;
70+
builtin_anims.put(id, anim);
71+
}
72+
73+
//Ensure that every DogAnimation has a sequence bound
74+
var all_dog_anim = DogAnimation.values();
75+
var updated_map = new HashMap<DogAnimation, AnimationDefinition>();
76+
var missing_set = new HashSet<String>();
77+
for (var dog_anim : all_dog_anim) {
78+
if (dog_anim.isNone())
79+
continue;
80+
var id = dog_anim.name().toLowerCase(Locale.ROOT);
81+
var sequence = builtin_anims.remove(Util.getResource(id));
82+
if (sequence == null) {
83+
missing_set.add(id);
84+
continue;
85+
}
86+
updated_map.put(dog_anim, sequence);
87+
}
88+
if (!missing_set.isEmpty()) {
89+
final int max_missing_log = 5;
90+
LOGGER.error(
91+
String.format(
92+
"Failed to load some built-in dog animation: [ %s ]",
93+
missing_set.stream().reduce((a, b) -> (a + ", " + b)).orElse("")
94+
)
95+
);
96+
} else {
97+
LOGGER.info(
98+
String.format(
99+
"All built-in animation is loaded successfully."
100+
)
101+
);
102+
}
103+
104+
DogAnimationRegistry.update(updated_map);
105+
106+
for (var entry : this.holderMap.entrySet()) {
107+
var id = entry.getKey();
108+
var holder = entry.getValue();
109+
var anim = builtin_anims.get(id);
110+
holder.update(anim);
111+
}
112+
}
113+
114+
public DogAnimationHolder getAnim(String id) {
115+
return getAnim(Util.getResource(id));
116+
}
117+
118+
public DogAnimationHolder getAnim(ResourceLocation id) {
119+
return this.holderMap.computeIfAbsent(id,
120+
k -> new DogAnimationHolder(null));
121+
}
122+
123+
public static class DogAnimationHolder {
124+
125+
private AnimationDefinition value;
126+
127+
private DogAnimationHolder(AnimationDefinition value) {
128+
this.value = value;
129+
}
130+
131+
public void update(AnimationDefinition newValue) {
132+
this.value = newValue;
133+
}
134+
135+
public void invalidate() {
136+
this.value = null;
137+
}
138+
}
139+
140+
public static final DTNAnimationLoader INSTANCE = new DTNAnimationLoader();
141+
142+
}

src/main/java/doggytalents/client/entity/model/animation/DogAnimationRegistry.java

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
package doggytalents.client.entity.model.animation;
22

3+
import java.util.HashMap;
34
import java.util.Map;
45

56
import com.google.common.collect.Maps;
@@ -16,6 +17,10 @@ public static void register(DogAnimation animation, AnimationDefinition sequence
1617
DEFINITION_MAP.putIfAbsent(animation, sequence);
1718
}
1819

20+
public static void update(Map<DogAnimation, AnimationDefinition> newMap) {
21+
DEFINITION_MAP = new HashMap<>(newMap);
22+
}
23+
1924
public static AnimationDefinition getSequence(DogAnimation animation) {
2025
return DEFINITION_MAP.get(animation);
2126
}

0 commit comments

Comments
 (0)