diff --git a/src/main/java/io/wispforest/owo/mixin/registry/RegistryEntryMixin.java b/src/main/java/io/wispforest/owo/mixin/registry/RegistryEntryMixin.java new file mode 100644 index 00000000..cef4cc26 --- /dev/null +++ b/src/main/java/io/wispforest/owo/mixin/registry/RegistryEntryMixin.java @@ -0,0 +1,19 @@ +package io.wispforest.owo.mixin.registry; + +import io.wispforest.owo.util.pond.OwoInjectedSupplier; +import net.minecraft.registry.entry.RegistryEntry; +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.Shadow; + +import java.util.function.Supplier; + +@Mixin(RegistryEntry.class) +public interface RegistryEntryMixin extends OwoInjectedSupplier { + + @Shadow T value(); + + @Override + default T get() { + return this.value(); + } +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/AutoRegistryContainer.java b/src/main/java/io/wispforest/owo/registration/reflect/AutoRegistryContainer.java index 23d0b00d..29839d3d 100644 --- a/src/main/java/io/wispforest/owo/registration/reflect/AutoRegistryContainer.java +++ b/src/main/java/io/wispforest/owo/registration/reflect/AutoRegistryContainer.java @@ -1,9 +1,13 @@ package io.wispforest.owo.registration.reflect; import io.wispforest.owo.registration.annotations.AssignedName; +import io.wispforest.owo.registration.reflect.entry.MemoizedEntry; +import io.wispforest.owo.registration.reflect.entry.TypedRegistryEntry; import net.minecraft.registry.Registry; +import net.minecraft.registry.entry.RegistryEntry; import java.lang.reflect.Field; +import java.util.function.Supplier; /** * A special version of {@link FieldProcessingSubject} that contains fields which should @@ -14,12 +18,12 @@ * * @param The type of objects to register, same as the Registry's type parameter */ -public interface AutoRegistryContainer extends FieldProcessingSubject { +public abstract class AutoRegistryContainer implements FieldProcessingSubject { /** * @return The registry the fields of this class should be registered into */ - Registry getRegistry(); + public abstract Registry getRegistry(); /** * Called after the given field has been registered @@ -29,17 +33,25 @@ public interface AutoRegistryContainer extends FieldProcessingSubject { * @param identifier The identifier the field was assigned, possibly overridden by an {@link AssignedName} * annotation and always fully lowercase */ - default void postProcessField(String namespace, T value, String identifier, Field field) {} + public void postProcessField(String namespace, T value, String identifier, Field field) {} /** * Convenience-alias for {@link FieldRegistrationHandler#register(Class, String, boolean)} */ - static void register(Class> container, String namespace, boolean recurse) { + public static void register(Class> container, String namespace, boolean recurse) { FieldRegistrationHandler.register(container, namespace, recurse); } @SuppressWarnings({"unchecked"}) - static Class conform(Class input) { + protected static Class conform(Class input) { return (Class) input; } + + public static RegistryEntry entry(Supplier supplier) { + return MemoizedEntry.ofEntry(supplier); + } + + public static TypedRegistryEntry typedEntry(Supplier supplier) { + return MemoizedEntry.ofTypedEntry(supplier); + } } diff --git a/src/main/java/io/wispforest/owo/registration/reflect/BlockEntityRegistryContainer.java b/src/main/java/io/wispforest/owo/registration/reflect/BlockEntityRegistryContainer.java deleted file mode 100644 index 0ee286ba..00000000 --- a/src/main/java/io/wispforest/owo/registration/reflect/BlockEntityRegistryContainer.java +++ /dev/null @@ -1,18 +0,0 @@ -package io.wispforest.owo.registration.reflect; - -import net.minecraft.block.entity.BlockEntityType; -import net.minecraft.registry.Registries; -import net.minecraft.registry.Registry; - -public interface BlockEntityRegistryContainer extends AutoRegistryContainer> { - - @Override - default Registry> getRegistry() { - return Registries.BLOCK_ENTITY_TYPE; - } - - @Override - default Class> getTargetFieldType() { - return AutoRegistryContainer.conform(BlockEntityType.class); - } -} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/EntityRegistryContainer.java b/src/main/java/io/wispforest/owo/registration/reflect/EntityRegistryContainer.java deleted file mode 100644 index a18bf10f..00000000 --- a/src/main/java/io/wispforest/owo/registration/reflect/EntityRegistryContainer.java +++ /dev/null @@ -1,18 +0,0 @@ -package io.wispforest.owo.registration.reflect; - -import net.minecraft.entity.EntityType; -import net.minecraft.registry.Registries; -import net.minecraft.registry.Registry; - -public interface EntityRegistryContainer extends AutoRegistryContainer> { - - @Override - default Registry> getRegistry() { - return Registries.ENTITY_TYPE; - } - - @Override - default Class> getTargetFieldType() { - return AutoRegistryContainer.conform(EntityType.class); - } -} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/FieldRegistrationHandler.java b/src/main/java/io/wispforest/owo/registration/reflect/FieldRegistrationHandler.java index 83739920..107ae618 100644 --- a/src/main/java/io/wispforest/owo/registration/reflect/FieldRegistrationHandler.java +++ b/src/main/java/io/wispforest/owo/registration/reflect/FieldRegistrationHandler.java @@ -1,10 +1,17 @@ package io.wispforest.owo.registration.reflect; +import io.wispforest.owo.registration.annotations.IterationIgnored; import io.wispforest.owo.registration.annotations.RegistryNamespace; +import io.wispforest.owo.registration.reflect.entry.MemoizedEntry; +import io.wispforest.owo.registration.reflect.entry.MemoizedRegistryEntry; import io.wispforest.owo.util.ReflectionUtils; import net.minecraft.registry.Registry; import net.minecraft.util.Identifier; +import java.lang.reflect.Modifier; +import java.lang.reflect.ParameterizedType; +import java.util.function.Supplier; + /** * Main hub for all interactions with implementations of * {@link FieldProcessingSubject} @@ -24,7 +31,7 @@ private FieldRegistrationHandler() {} */ public static void process(Class> clazz, ReflectionUtils.FieldConsumer processor, boolean recurseIntoInnerClasses) { var handler = ReflectionUtils.tryInstantiateWithNoArgs(clazz); - ReflectionUtils.iterateAccessibleStaticFields(clazz, handler.getTargetFieldType(), createProcessor(processor, handler)); + iterateAccessibleStaticFieldsAllowingMemorizedSuppliers(clazz, handler.getTargetFieldType(), createProcessor(processor, handler)); if (recurseIntoInnerClasses) { ReflectionUtils.forApplicableSubclasses(clazz, FieldProcessingSubject.class, @@ -44,7 +51,7 @@ public static void process(Class> clazz, */ public static void processSimple(Class> clazz, boolean recurseIntoInnerClasses) { var handler = ReflectionUtils.tryInstantiateWithNoArgs(clazz); - ReflectionUtils.iterateAccessibleStaticFields(clazz, handler.getTargetFieldType(), createProcessor(handler::processField, handler)); + iterateAccessibleStaticFieldsAllowingMemorizedSuppliers(clazz, handler.getTargetFieldType(), createProcessor(handler::processField, handler)); if (recurseIntoInnerClasses) { ReflectionUtils.forApplicableSubclasses(clazz, SimpleFieldProcessingSubject.class, @@ -65,8 +72,19 @@ public static void processSimple(Class void register(Class> clazz, String namespace, boolean recurseIntoInnerClasses) { AutoRegistryContainer container = ReflectionUtils.tryInstantiateWithNoArgs(clazz); - ReflectionUtils.iterateAccessibleStaticFields(clazz, container.getTargetFieldType(), createProcessor((fieldValue, identifier, field) -> { - Registry.register(container.getRegistry(), Identifier.of(namespace, identifier), fieldValue); + iterateAccessibleStaticFieldsAllowingMemorizedSuppliers(clazz, container.getTargetFieldType(), createProcessor((fieldValue, identifier, field) -> { + var reference = Registry.registerReference(container.getRegistry(), Identifier.of(namespace, identifier), fieldValue); + + try { + var object = field.get(null); + + if(object instanceof MemoizedRegistryEntry memorizedRegistryEntry) { + memorizedRegistryEntry.setEntry(reference); + } + } catch (IllegalArgumentException | IllegalAccessException e) { + throw new RuntimeException(e); + } + container.postProcessField(namespace, fieldValue, identifier, field); }, container)); @@ -88,4 +106,49 @@ private static ReflectionUtils.FieldConsumer createProcessor(ReflectionUt }; } + private static void iterateAccessibleStaticFieldsAllowingMemorizedSuppliers(Class clazz, Class targetFieldType, ReflectionUtils.FieldConsumer fieldConsumer) { + for (var field : clazz.getDeclaredFields()) { + if (!Modifier.isStatic(field.getModifiers())) continue; + if (field.isAnnotationPresent(IterationIgnored.class)) continue; + + Object fieldValue; + try { + fieldValue = field.get(null); + } catch (IllegalAccessException e) { + continue; + } + + if(fieldValue == null) continue; + + var valueType = fieldValue.getClass(); + + F finalValue = null; + + if (!targetFieldType.isAssignableFrom(valueType)) { + boolean isValid = false; + + if(Supplier.class.isAssignableFrom(field.getType()) && field.getGenericType() instanceof ParameterizedType parameterizedType) { + var genericType = parameterizedType.getActualTypeArguments()[0]; + + if (genericType instanceof Class genericClass && targetFieldType.isAssignableFrom(genericClass)) { + if(!(fieldValue instanceof MemoizedEntry)) { + throw new IllegalStateException("A given Supplier object must be of a memoized variant or problems may occur! [Field: " + field.getName() + "]"); + } + + finalValue = (F) ((Supplier) fieldValue).get(); + + + isValid = true; + } + } + + if(!isValid) continue; + } else { + finalValue = (F) fieldValue; + } + + fieldConsumer.accept(finalValue, ReflectionUtils.getFieldName(field), field); + } + } + } diff --git a/src/main/java/io/wispforest/owo/registration/reflect/ItemRegistryContainer.java b/src/main/java/io/wispforest/owo/registration/reflect/ItemRegistryContainer.java deleted file mode 100644 index 6e7aedbf..00000000 --- a/src/main/java/io/wispforest/owo/registration/reflect/ItemRegistryContainer.java +++ /dev/null @@ -1,17 +0,0 @@ -package io.wispforest.owo.registration.reflect; - -import net.minecraft.item.Item; -import net.minecraft.registry.Registries; -import net.minecraft.registry.Registry; - -public interface ItemRegistryContainer extends AutoRegistryContainer { - @Override - default Registry getRegistry() { - return Registries.ITEM; - } - - @Override - default Class getTargetFieldType() { - return Item.class; - } -} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/BlockRegistryContainer.java b/src/main/java/io/wispforest/owo/registration/reflect/block/BlockRegistryContainer.java similarity index 68% rename from src/main/java/io/wispforest/owo/registration/reflect/BlockRegistryContainer.java rename to src/main/java/io/wispforest/owo/registration/reflect/block/BlockRegistryContainer.java index 21f87efd..71cec67a 100644 --- a/src/main/java/io/wispforest/owo/registration/reflect/BlockRegistryContainer.java +++ b/src/main/java/io/wispforest/owo/registration/reflect/block/BlockRegistryContainer.java @@ -1,6 +1,7 @@ -package io.wispforest.owo.registration.reflect; +package io.wispforest.owo.registration.reflect.block; import io.wispforest.owo.registration.annotations.AssignedName; +import io.wispforest.owo.registration.reflect.AutoRegistryContainer; import net.minecraft.block.Block; import net.minecraft.item.BlockItem; import net.minecraft.item.Item; @@ -13,25 +14,30 @@ import java.lang.annotation.RetentionPolicy; import java.lang.annotation.Target; import java.lang.reflect.Field; +import java.util.function.Supplier; -public interface BlockRegistryContainer extends AutoRegistryContainer { +public abstract class BlockRegistryContainer extends AutoRegistryContainer { @Override - default Registry getRegistry() { + public final Registry getRegistry() { return Registries.BLOCK; } @Override - default Class getTargetFieldType() { + public final Class getTargetFieldType() { return Block.class; } @Override - default void postProcessField(String namespace, Block value, String identifier, Field field) { + public void postProcessField(String namespace, Block value, String identifier, Field field) { if (field.isAnnotationPresent(NoBlockItem.class)) return; Registry.register(Registries.ITEM, Identifier.of(namespace, identifier), createBlockItem(value, identifier)); } + public static BlockRegistryEntry block(Supplier supplier) { + return new BlockRegistryEntry<>(supplier); + } + /** * Creates a block item for the given block * @@ -40,7 +46,7 @@ default void postProcessField(String namespace, Block value, String identifier, * annotation and always fully lowercase * @return The created BlockItem instance */ - default BlockItem createBlockItem(Block block, String identifier) { + public BlockItem createBlockItem(Block block, String identifier) { return new BlockItem(block, new Item.Settings()); } diff --git a/src/main/java/io/wispforest/owo/registration/reflect/block/BlockRegistryEntry.java b/src/main/java/io/wispforest/owo/registration/reflect/block/BlockRegistryEntry.java new file mode 100644 index 00000000..70401e31 --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/block/BlockRegistryEntry.java @@ -0,0 +1,19 @@ +package io.wispforest.owo.registration.reflect.block; + +import io.wispforest.owo.registration.reflect.entry.MemoizedRegistryEntry; +import net.minecraft.block.Block; +import net.minecraft.item.Item; +import net.minecraft.item.ItemConvertible; + +import java.util.function.Supplier; + +public final class BlockRegistryEntry extends MemoizedRegistryEntry implements ItemConvertible { + public BlockRegistryEntry(Supplier factory) { + super(factory); + } + + @Override + public Item asItem() { + return this.value().asItem(); + } +} \ No newline at end of file diff --git a/src/main/java/io/wispforest/owo/registration/reflect/blockentity/BlockEntityRegistryContainer.java b/src/main/java/io/wispforest/owo/registration/reflect/blockentity/BlockEntityRegistryContainer.java new file mode 100644 index 00000000..7df9327f --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/blockentity/BlockEntityRegistryContainer.java @@ -0,0 +1,29 @@ +package io.wispforest.owo.registration.reflect.blockentity; + +import io.wispforest.owo.registration.reflect.AutoRegistryContainer; +import io.wispforest.owo.registration.reflect.entity.EntityRegistryEntry; +import net.minecraft.block.entity.BlockEntity; +import net.minecraft.block.entity.BlockEntityType; +import net.minecraft.entity.Entity; +import net.minecraft.entity.EntityType; +import net.minecraft.registry.Registries; +import net.minecraft.registry.Registry; + +import java.util.function.Supplier; + +public abstract class BlockEntityRegistryContainer extends AutoRegistryContainer> { + + @Override + public final Registry> getRegistry() { + return Registries.BLOCK_ENTITY_TYPE; + } + + @Override + public final Class> getTargetFieldType() { + return AutoRegistryContainer.conform(BlockEntityType.class); + } + + public static BlockEntityRegistryEntry blockEntity(Supplier> supplier) { + return new BlockEntityRegistryEntry<>(supplier); + } +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/blockentity/BlockEntityRegistryEntry.java b/src/main/java/io/wispforest/owo/registration/reflect/blockentity/BlockEntityRegistryEntry.java new file mode 100644 index 00000000..3d92b989 --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/blockentity/BlockEntityRegistryEntry.java @@ -0,0 +1,14 @@ +package io.wispforest.owo.registration.reflect.blockentity; + +import io.wispforest.owo.registration.reflect.entry.MemoizedRegistryEntry; +import net.minecraft.block.entity.BlockEntity; +import net.minecraft.block.entity.BlockEntityType; +import net.minecraft.entity.Entity; + +import java.util.function.Supplier; + +public class BlockEntityRegistryEntry extends MemoizedRegistryEntry, BlockEntityType> { + public BlockEntityRegistryEntry(Supplier> factory) { + super(factory); + } +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/entity/EntityRegistryContainer.java b/src/main/java/io/wispforest/owo/registration/reflect/entity/EntityRegistryContainer.java new file mode 100644 index 00000000..9dc285cd --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/entity/EntityRegistryContainer.java @@ -0,0 +1,26 @@ +package io.wispforest.owo.registration.reflect.entity; + +import io.wispforest.owo.registration.reflect.AutoRegistryContainer; +import net.minecraft.entity.Entity; +import net.minecraft.entity.EntityType; +import net.minecraft.registry.Registries; +import net.minecraft.registry.Registry; + +import java.util.function.Supplier; + +public abstract class EntityRegistryContainer extends AutoRegistryContainer> { + + @Override + public final Registry> getRegistry() { + return Registries.ENTITY_TYPE; + } + + @Override + public final Class> getTargetFieldType() { + return AutoRegistryContainer.conform(EntityType.class); + } + + public static EntityRegistryEntry entity(Supplier> supplier) { + return new EntityRegistryEntry<>(supplier); + } +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/entity/EntityRegistryEntry.java b/src/main/java/io/wispforest/owo/registration/reflect/entity/EntityRegistryEntry.java new file mode 100644 index 00000000..4ebb1dea --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/entity/EntityRegistryEntry.java @@ -0,0 +1,13 @@ +package io.wispforest.owo.registration.reflect.entity; + +import io.wispforest.owo.registration.reflect.entry.MemoizedRegistryEntry; +import net.minecraft.entity.Entity; +import net.minecraft.entity.EntityType; + +import java.util.function.Supplier; + +public class EntityRegistryEntry extends MemoizedRegistryEntry, EntityType> { + public EntityRegistryEntry(Supplier> factory) { + super(factory); + } +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/entry/MemoizedEntry.java b/src/main/java/io/wispforest/owo/registration/reflect/entry/MemoizedEntry.java new file mode 100644 index 00000000..66c1e770 --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/entry/MemoizedEntry.java @@ -0,0 +1,51 @@ +package io.wispforest.owo.registration.reflect.entry; + +import net.minecraft.registry.entry.RegistryEntry; +import org.jetbrains.annotations.Nullable; + +import java.util.function.Supplier; + +public class MemoizedEntry implements Supplier { + + private final Supplier factory; + + @Nullable + private T object = null; + + protected MemoizedEntry(Supplier factory) { + this.factory = factory; + } + + public static MemoizedEntry of(Supplier supplier) { + if(supplier instanceof MemoizedEntry memoizedSupplier) return memoizedSupplier; + + return new MemoizedEntry<>(supplier); + } + + public static TypedRegistryEntry ofTypedEntry(Supplier supplier) { + if(supplier instanceof MemoizedRegistryEntry memorizedRegistryEntry) { + return memorizedRegistryEntry; + } else if(supplier instanceof MemoizedEntry memoizedSupplier) { + supplier = memoizedSupplier.factory; + } + + return new MemoizedRegistryEntry<>(supplier); + } + + public static RegistryEntry ofEntry(Supplier supplier) { + if(supplier instanceof MemoizedRegistryEntry memorizedRegistryEntry) { + return memorizedRegistryEntry; + } else if(supplier instanceof MemoizedEntry memoizedSupplier) { + supplier = memoizedSupplier.factory; + } + + return new MemoizedRegistryEntry<>(supplier); + } + + @Override + public T get() { + if(this.object == null) this.object = factory.get(); + + return object; + } +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/entry/MemoizedRegistryEntry.java b/src/main/java/io/wispforest/owo/registration/reflect/entry/MemoizedRegistryEntry.java new file mode 100644 index 00000000..40662329 --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/entry/MemoizedRegistryEntry.java @@ -0,0 +1,102 @@ +package io.wispforest.owo.registration.reflect.entry; + +import com.mojang.datafixers.util.Either; +import net.minecraft.registry.RegistryKey; +import net.minecraft.registry.entry.RegistryEntry; +import net.minecraft.registry.entry.RegistryEntryOwner; +import net.minecraft.registry.tag.TagKey; +import net.minecraft.util.Identifier; +import org.jetbrains.annotations.ApiStatus; +import org.jetbrains.annotations.Nullable; + +import java.util.Optional; +import java.util.function.Predicate; +import java.util.function.Supplier; +import java.util.stream.Stream; + +public class MemoizedRegistryEntry extends MemoizedEntry implements TypedRegistryEntry { + + @Nullable + private RegistryEntry registryEntry = null; + + protected MemoizedRegistryEntry(Supplier factory) { + super(factory::get); + } + + @ApiStatus.Internal + public final void setEntry(RegistryEntry registryEntry) { + this.registryEntry = registryEntry; + } + + private RegistryEntry getTypedEntry() { + if(this.registryEntry == null) { + throw new IllegalStateException("Unable to get the wrapped registry entry as it has not been set yet!"); + } + + return registryEntry; + } + + public final RegistryEntry getBaseEntry() { + return (RegistryEntry) getTypedEntry(); + } + + @Override + public T value() { + return this.getTypedEntry().value(); + } + + @Override + public boolean hasKeyAndValue() { + return this.getBaseEntry().hasKeyAndValue(); + } + + @Override + public boolean matchesId(Identifier id) { + return this.getBaseEntry().matchesId(id); + } + + @Override + public boolean matchesKey(RegistryKey key) { + return this.getBaseEntry().matchesKey(key); + } + + @Override + public boolean matches(Predicate> predicate) { + return this.getBaseEntry().matches(predicate); + } + + @Override + public boolean isIn(TagKey tag) { + return this.getBaseEntry().isIn(tag); + } + + @Override + public boolean matches(RegistryEntry entry) { + return this.getBaseEntry().matches(entry); + } + + @Override + public Stream> streamTags() { + return this.getBaseEntry().streamTags(); + } + + @Override + public Either, B> getKeyOrValue() { + return this.getBaseEntry().getKeyOrValue(); + } + + @Override + public Optional> getKey() { + return this.getBaseEntry().getKey(); + } + + @Override + public Type getType() { + return this.getBaseEntry().getType(); + } + + @Override + public boolean ownerEquals(RegistryEntryOwner owner) { + return this.getBaseEntry().ownerEquals(owner); + } +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/entry/TypedRegistryEntry.java b/src/main/java/io/wispforest/owo/registration/reflect/entry/TypedRegistryEntry.java new file mode 100644 index 00000000..7105b7e6 --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/entry/TypedRegistryEntry.java @@ -0,0 +1,9 @@ +package io.wispforest.owo.registration.reflect.entry; + +import net.minecraft.registry.entry.RegistryEntry; + +public interface TypedRegistryEntry extends RegistryEntry { + + @Override + T value(); +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/item/ItemRegistryContainer.java b/src/main/java/io/wispforest/owo/registration/reflect/item/ItemRegistryContainer.java new file mode 100644 index 00000000..aa537eca --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/item/ItemRegistryContainer.java @@ -0,0 +1,25 @@ +package io.wispforest.owo.registration.reflect.item; + +import io.wispforest.owo.registration.reflect.AutoRegistryContainer; +import net.minecraft.item.Item; +import net.minecraft.registry.Registries; +import net.minecraft.registry.Registry; + +import java.util.function.Supplier; + +public abstract class ItemRegistryContainer extends AutoRegistryContainer { + + @Override + public final Registry getRegistry() { + return Registries.ITEM; + } + + @Override + public final Class getTargetFieldType() { + return Item.class; + } + + public static ItemRegistryEntry item(Supplier supplier) { + return new ItemRegistryEntry<>(supplier); + } +} diff --git a/src/main/java/io/wispforest/owo/registration/reflect/item/ItemRegistryEntry.java b/src/main/java/io/wispforest/owo/registration/reflect/item/ItemRegistryEntry.java new file mode 100644 index 00000000..507f4bb4 --- /dev/null +++ b/src/main/java/io/wispforest/owo/registration/reflect/item/ItemRegistryEntry.java @@ -0,0 +1,18 @@ +package io.wispforest.owo.registration.reflect.item; + +import io.wispforest.owo.registration.reflect.entry.MemoizedRegistryEntry; +import net.minecraft.item.Item; +import net.minecraft.item.ItemConvertible; + +import java.util.function.Supplier; + +public final class ItemRegistryEntry extends MemoizedRegistryEntry implements ItemConvertible { + public ItemRegistryEntry(Supplier factory) { + super(factory); + } + + @Override + public Item asItem() { + return this.value(); + } +} diff --git a/src/main/java/io/wispforest/owo/util/ReflectionUtils.java b/src/main/java/io/wispforest/owo/util/ReflectionUtils.java index f430d603..a6262e78 100644 --- a/src/main/java/io/wispforest/owo/util/ReflectionUtils.java +++ b/src/main/java/io/wispforest/owo/util/ReflectionUtils.java @@ -82,6 +82,7 @@ public static Constructor getNoArgsConstructor(Class clazz) { public static void iterateAccessibleStaticFields(Class clazz, Class targetFieldType, FieldConsumer fieldConsumer) { for (var field : clazz.getDeclaredFields()) { if (!Modifier.isStatic(field.getModifiers())) continue; + if (field.isAnnotationPresent(IterationIgnored.class)) continue; F value; try { @@ -91,7 +92,6 @@ public static void iterateAccessibleStaticFields(Class clazz, Class } if (value == null || !targetFieldType.isAssignableFrom(value.getClass())) continue; - if (field.isAnnotationPresent(IterationIgnored.class)) continue; fieldConsumer.accept(value, getFieldName(field), field); } diff --git a/src/main/java/io/wispforest/owo/util/pond/OwoInjectedSupplier.java b/src/main/java/io/wispforest/owo/util/pond/OwoInjectedSupplier.java new file mode 100644 index 00000000..3cbd110c --- /dev/null +++ b/src/main/java/io/wispforest/owo/util/pond/OwoInjectedSupplier.java @@ -0,0 +1,9 @@ +package io.wispforest.owo.util.pond; + +import java.util.function.Supplier; + +public interface OwoInjectedSupplier extends Supplier { + default T get() { + throw new IllegalStateException("Injected Supplier interface has yet to be override!"); + } +} diff --git a/src/main/resources/fabric.mod.json b/src/main/resources/fabric.mod.json index 51f25f24..9d05384b 100644 --- a/src/main/resources/fabric.mod.json +++ b/src/main/resources/fabric.mod.json @@ -76,6 +76,9 @@ ], "net/minecraft/class_9331\u0024class_9332": [ "io/wispforest/owo/serialization/OwoComponentTypeBuilder" + ], + "net/minecraft/class_6880": [ + "io/wispforest/owo/util/pond/OwoInjectedSupplier" ] } } diff --git a/src/main/resources/owo.mixins.json b/src/main/resources/owo.mixins.json index 4f60f67d..e77b81a9 100644 --- a/src/main/resources/owo.mixins.json +++ b/src/main/resources/owo.mixins.json @@ -39,7 +39,8 @@ "ui.SimpleRegistryAccessor", "ui.SlotAccessor", "ui.SlotMixin", - "ui.access.BlockEntityAccessor" + "ui.access.BlockEntityAccessor", + "registry.RegistryEntryMixin" ], "client": [ "ClientConfigurationNetworkHandlerMixin", diff --git a/src/testmod/java/io/wispforest/uwu/items/UwuItems.java b/src/testmod/java/io/wispforest/uwu/items/UwuItems.java index 635c75dd..ceabc0aa 100644 --- a/src/testmod/java/io/wispforest/uwu/items/UwuItems.java +++ b/src/testmod/java/io/wispforest/uwu/items/UwuItems.java @@ -3,20 +3,24 @@ import io.wispforest.owo.itemgroup.OwoItemSettings; import io.wispforest.owo.registration.annotations.AssignedName; import io.wispforest.owo.registration.annotations.RegistryNamespace; -import io.wispforest.owo.registration.reflect.ItemRegistryContainer; +import io.wispforest.owo.registration.reflect.item.ItemRegistryContainer; +import io.wispforest.owo.registration.reflect.item.ItemRegistryEntry; +import io.wispforest.owo.registration.reflect.entry.TypedRegistryEntry; import io.wispforest.uwu.Uwu; import net.fabricmc.loader.api.FabricLoader; +import net.minecraft.component.type.FoodComponents; import net.minecraft.item.Item; +import net.minecraft.registry.entry.RegistryEntry; import java.lang.reflect.Field; -public class UwuItems implements ItemRegistryContainer { +public class UwuItems extends ItemRegistryContainer { - public static final Item TEST_STICK = new UwuTestStickItem(); + public static final ItemRegistryEntry TEST_STICK = item(UwuTestStickItem::new); public static final Item SCREEN_SHARD = new UwuScreenShardItem(); @RegistryNamespace("uowou") - public static class OwoCompatItems implements ItemRegistryContainer { + public static class OwoCompatItems extends ItemRegistryContainer { @AssignedName("owo_ingot") public static final Item OWO_COMPAT_ITEM = new Item(new OwoItemSettings().group(Uwu.FOUR_TAB_GROUP).tab(2)); @@ -27,4 +31,11 @@ public boolean shouldProcessField(Item value, String identifier, Field field) { } } + @RegistryNamespace("supplied") + public static class OwoTestingSuppliers extends ItemRegistryContainer { + public static final TypedRegistryEntry RANDOM_1 = typedEntry(() -> new Item(new Item.Settings().fireproof().maxCount(1))); + public static final RegistryEntry RANDOM_2 = entry(() -> new Item(new Item.Settings().food(FoodComponents.APPLE).maxCount(65))); + public static final RegistryEntry RANDOM_3 = entry(() -> new Item(new Item.Settings().food(FoodComponents.APPLE).maxCount(65))); + public static final RegistryEntry RANDOM_4 = entry(() -> new Item(new Item.Settings().food(FoodComponents.APPLE).maxCount(65))); + } } diff --git a/src/testmod/java/io/wispforest/uwu/items/UwuTestStickItem.java b/src/testmod/java/io/wispforest/uwu/items/UwuTestStickItem.java index 9b761ded..0c6cb091 100644 --- a/src/testmod/java/io/wispforest/uwu/items/UwuTestStickItem.java +++ b/src/testmod/java/io/wispforest/uwu/items/UwuTestStickItem.java @@ -29,6 +29,8 @@ import net.minecraft.registry.Registry; import net.minecraft.registry.RegistryKeys; import net.minecraft.registry.RegistryOps; +import net.minecraft.registry.entry.RegistryEntry; +import net.minecraft.registry.tag.ItemTags; import net.minecraft.server.network.ServerPlayerEntity; import net.minecraft.text.MutableText; import net.minecraft.text.Text; @@ -83,6 +85,7 @@ public UwuTestStickItem() { @Override public TypedActionResult use(World world, PlayerEntity user, Hand hand) { + test(UwuItems.TEST_STICK); if (user.isSneaking()) { if (world.isClient) return TypedActionResult.success(user.getStackInHand(hand)); @@ -106,6 +109,10 @@ public TypedActionResult use(World world, PlayerEntity user, Hand han } } + public void test(RegistryEntry entry) { + System.out.println(entry.value()); + } + @Override public ActionResult useOnBlock(ItemUsageContext context) { if (!context.getPlayer().isSneaking()) {