Skip to content

Commit 9ed71dc

Browse files
committed
Provide emulated registries permanently
1 parent 46913ac commit 9ed71dc

File tree

2 files changed

+44
-47
lines changed

2 files changed

+44
-47
lines changed

common/src/main/java/org/embeddedt/modernfix/common/mixin/perf/dynamic_resources/ModelManagerMixin.java

Lines changed: 11 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -25,8 +25,10 @@
2525
import org.spongepowered.asm.mixin.Shadow;
2626
import org.spongepowered.asm.mixin.Unique;
2727
import org.spongepowered.asm.mixin.injection.At;
28+
import org.spongepowered.asm.mixin.injection.Inject;
2829
import org.spongepowered.asm.mixin.injection.ModifyArg;
2930
import org.spongepowered.asm.mixin.injection.Redirect;
31+
import org.spongepowered.asm.mixin.injection.callback.CallbackInfo;
3032

3133
import java.lang.ref.WeakReference;
3234
import java.util.Map;
@@ -36,7 +38,10 @@
3638
@Mixin(ModelManager.class)
3739
@ClientOnlyMixin
3840
public class ModelManagerMixin implements DynamicModelProvider.ModelManagerExtension {
39-
@Shadow private BakedModel missingModel;
41+
@Shadow private Map<ModelResourceLocation, BakedModel> bakedBlockStateModels;
42+
@Shadow private Map<ResourceLocation, ItemModel> bakedItemStackModels;
43+
@Shadow private Map<ResourceLocation, ClientItem.Properties> itemProperties;
44+
4045
@Unique
4146
private DynamicModelProvider mfix$modelProvider;
4247

@@ -79,35 +84,11 @@ private CompletableFuture<?>[] createModelProvider(CompletableFuture<?>[] cfs, @
7984
return ArrayUtils.add(cfs, makeModelProviderFuture);
8085
}
8186

82-
/**
83-
* @author embeddedt
84-
* @reason use dynamic model system
85-
*/
86-
@Overwrite
87-
public BakedModel getModel(ModelResourceLocation modelLocation) {
88-
if(this.mfix$modelProvider != null) {
89-
return this.mfix$modelProvider.getModel(modelLocation);
90-
} else {
91-
return this.missingModel;
92-
}
93-
}
94-
95-
/**
96-
* @author embeddedt
97-
* @reason use dynamic model system
98-
*/
99-
@Overwrite
100-
public ItemModel getItemModel(ResourceLocation resourceLocation) {
101-
return this.mfix$modelProvider.getItemModel(resourceLocation);
102-
}
103-
104-
/**
105-
* @author embeddedt
106-
* @reason use dynamic model system
107-
*/
108-
@Overwrite
109-
public ClientItem.Properties getItemProperties(ResourceLocation resourceLocation) {
110-
return this.mfix$modelProvider.getClientItemProperties(resourceLocation);
87+
@Inject(method = "apply", at = @At("RETURN"))
88+
private void setModelRegistries(CallbackInfo ci) {
89+
this.bakedBlockStateModels = this.mfix$modelProvider.getTopLevelEmulatedRegistry();
90+
this.bakedItemStackModels = this.mfix$modelProvider.getItemModelEmulatedRegistry();
91+
this.itemProperties = this.mfix$modelProvider.getItemPropertiesEmulatedRegistry();
11192
}
11293

11394
@Override

common/src/main/java/org/embeddedt/modernfix/dynamicresources/DynamicModelProvider.java

Lines changed: 33 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
11
package org.embeddedt.modernfix.dynamicresources;
22

3+
import com.google.common.base.Suppliers;
34
import com.google.common.cache.CacheBuilder;
45
import com.google.common.cache.CacheLoader;
56
import com.google.common.cache.LoadingCache;
7+
import com.google.common.collect.Collections2;
68
import com.google.common.collect.Iterators;
79
import com.google.common.collect.Maps;
810
import com.google.gson.JsonObject;
@@ -61,6 +63,7 @@
6163
import java.util.concurrent.TimeUnit;
6264
import java.util.function.BiFunction;
6365
import java.util.function.Function;
66+
import java.util.function.Supplier;
6467
import java.util.stream.Collectors;
6568

6669
/**
@@ -149,28 +152,32 @@ public ItemModel getMissingItemModel() {
149152
return this.missingItemModel;
150153
}
151154

152-
public Map<ModelResourceLocation, BakedModel> getTopLevelEmulatedRegistry() {
153-
Set<ModelResourceLocation> topLevelModelLocations = new HashSet<>();
155+
private static final Supplier<Set<ModelResourceLocation>> TOP_LEVEL_LOCATIONS_SUPPLIER = Suppliers.memoizeWithExpiration(() -> {
156+
Set<ModelResourceLocation> set = new HashSet<>();
154157
// Skip going through ModelLocationCache because most of the accesses will be misses
155158
BuiltInRegistries.BLOCK.entrySet().forEach(entry -> {
156159
var location = entry.getKey().location();
157160
for(BlockState state : entry.getValue().getStateDefinition().getPossibleStates()) {
158-
topLevelModelLocations.add(BlockModelShaper.stateToModelLocation(location, state));
161+
set.add(BlockModelShaper.stateToModelLocation(location, state));
159162
}
160163
});
161-
return new EmulatedRegistry<>(ModelResourceLocation.class, this.loadedBakedModels, topLevelModelLocations, this.mrlModelOverrides);
164+
return Collections.unmodifiableSet(set);
165+
}, 2, TimeUnit.MINUTES);
166+
167+
public Map<ModelResourceLocation, BakedModel> getTopLevelEmulatedRegistry() {
168+
return new EmulatedRegistry<>(ModelResourceLocation.class, this.loadedBakedModels, TOP_LEVEL_LOCATIONS_SUPPLIER, this.mrlModelOverrides);
162169
}
163170

164171
public Map<ResourceLocation, BakedModel> getStandaloneEmulatedRegistry() {
165-
return new EmulatedRegistry<>(ResourceLocation.class, this.loadedStandaloneModels, Set.of(), this.standaloneModelOverrides);
172+
return new EmulatedRegistry<>(ResourceLocation.class, this.loadedStandaloneModels, Set::of, this.standaloneModelOverrides);
166173
}
167174

168175
public Map<ResourceLocation, ItemModel> getItemModelEmulatedRegistry() {
169-
return new EmulatedRegistry<>(ResourceLocation.class, this.loadedItemModels, BuiltInRegistries.ITEM.keySet(), this.itemStackModelOverrides);
176+
return new EmulatedRegistry<>(ResourceLocation.class, this.loadedItemModels, BuiltInRegistries.ITEM::keySet, this.itemStackModelOverrides);
170177
}
171178

172179
public Map<ResourceLocation, ClientItem.Properties> getItemPropertiesEmulatedRegistry() {
173-
return Maps.transformValues(new EmulatedRegistry<>(ResourceLocation.class, this.loadedClientItemProperties, BuiltInRegistries.ITEM.keySet(), Map.of()), ClientItem::properties);
180+
return Maps.transformValues(new EmulatedRegistry<>(ResourceLocation.class, this.loadedClientItemProperties, BuiltInRegistries.ITEM::keySet, Map.of()), ClientItem::properties);
174181
}
175182

176183
private <K, V> LoadingCache<K, Optional<V>> makeLoadingCache(Function<K, Optional<V>> loadingFunction) {
@@ -189,14 +196,14 @@ public Optional<V> load(K key) {
189196

190197
private static class EmulatedRegistry<K, V> implements Map<K, V> {
191198
private final LoadingCache<K, Optional<V>> realCache;
192-
private final Set<K> keys;
199+
private final Supplier<Set<K>> keys;
193200
private final Map<K, V> overrides;
194201
private final Class<K> keyClass;
195202

196-
public EmulatedRegistry(Class<K> keyClass, LoadingCache<K, Optional<V>> realCache, Set<K> keys, Map<K, V> overrides) {
203+
public EmulatedRegistry(Class<K> keyClass, LoadingCache<K, Optional<V>> realCache, Supplier<Set<K>> keys, Map<K, V> overrides) {
197204
this.keyClass = keyClass;
198205
this.realCache = realCache;
199-
this.keys = Collections.unmodifiableSet(keys);
206+
this.keys = keys;
200207
this.overrides = overrides;
201208
}
202209

@@ -209,6 +216,15 @@ public V get(Object key) {
209216
}
210217
}
211218

219+
@Override
220+
public V getOrDefault(Object key, V defaultValue) {
221+
if (this.keyClass.isAssignableFrom(key.getClass())) {
222+
return this.realCache.getUnchecked((K)key).orElse(defaultValue);
223+
} else {
224+
return defaultValue;
225+
}
226+
}
227+
212228
@Override
213229
public V put(K key, V value) {
214230
V oldValue = this.realCache.getUnchecked(key).orElse(null);
@@ -237,17 +253,17 @@ public void clear() {
237253

238254
@Override
239255
public @NotNull Set<K> keySet() {
240-
return keys;
256+
return keys.get();
241257
}
242258

243259
@Override
244260
public @NotNull Collection<V> values() {
245-
return List.of();
261+
return Collections2.transform(this.realCache.asMap().values(), v -> v.orElse(null));
246262
}
247263

248264
@Override
249265
public int size() {
250-
return keys.size();
266+
return keys.get().size();
251267
}
252268

253269
@Override
@@ -257,7 +273,7 @@ public boolean isEmpty() {
257273

258274
@Override
259275
public boolean containsKey(Object key) {
260-
return keys.contains(key);
276+
return keys.get().contains(key);
261277
}
262278

263279
@Override
@@ -270,7 +286,7 @@ public boolean containsValue(Object value) {
270286
return new AbstractSet<>() {
271287
@Override
272288
public Iterator<Entry<K, V>> iterator() {
273-
return Iterators.transform(keys.iterator(), key -> new Entry<>() {
289+
return Iterators.transform(keys.get().iterator(), key -> new Entry<>() {
274290
@Override
275291
public K getKey() {
276292
return key;
@@ -290,14 +306,14 @@ public V setValue(V value) {
290306

291307
@Override
292308
public int size() {
293-
return keys.size();
309+
return keys.get().size();
294310
}
295311
};
296312
}
297313

298314
@Override
299315
public void replaceAll(BiFunction<? super K, ? super V, ? extends V> function) {
300-
for(K location : keys) {
316+
for(K location : keys.get()) {
301317
/*
302318
* Fetching every model is insanely slow. So we call the function with a null object first, since it
303319
* probably isn't expecting that. If we get an exception thrown, or it returns nonnull, then we know

0 commit comments

Comments
 (0)