From 67171a5ff24ed77e6c4cc889543e8dfb543e8fe5 Mon Sep 17 00:00:00 2001 From: shedaniel Date: Sun, 20 Dec 2020 19:59:49 +0800 Subject: wip more Signed-off-by: shedaniel --- .../me/shedaniel/rei/plugin/DefaultPlugin.java | 444 +++++++++++++++++++++ .../plugin/DefaultPotionEffectExclusionZones.java | 64 +++ .../plugin/DefaultRecipeBookExclusionZones.java | 58 +++ .../rei/plugin/DefaultServerContainerPlugin.java | 40 ++ .../autocrafting/DefaultRecipeBookHandler.java | 104 +++++ .../beacon/base/DefaultBeaconBaseCategory.java | 187 +++++++++ .../beacon/base/DefaultBeaconBaseDisplay.java | 65 +++ .../payment/DefaultBeaconPaymentCategory.java | 183 +++++++++ .../payment/DefaultBeaconPaymentDisplay.java | 66 +++ .../plugin/blasting/DefaultBlastingDisplay.java | 44 ++ .../rei/plugin/brewing/BrewingRecipe.java | 39 ++ .../rei/plugin/brewing/DefaultBrewingCategory.java | 85 ++++ .../rei/plugin/brewing/DefaultBrewingDisplay.java | 98 +++++ .../plugin/brewing/RegisteredBrewingRecipe.java | 39 ++ .../plugin/campfire/DefaultCampfireCategory.java | 81 ++++ .../plugin/campfire/DefaultCampfireDisplay.java | 91 +++++ .../composting/DefaultCompostingCategory.java | 121 ++++++ .../composting/DefaultCompostingDisplay.java | 91 +++++ .../containers/CraftingContainerInfoWrapper.java | 77 ++++ .../rei/plugin/cooking/DefaultCookingCategory.java | 110 +++++ .../rei/plugin/cooking/DefaultCookingDisplay.java | 105 +++++ .../plugin/crafting/DefaultCraftingCategory.java | 116 ++++++ .../plugin/crafting/DefaultCraftingDisplay.java | 73 ++++ .../rei/plugin/crafting/DefaultCustomDisplay.java | 114 ++++++ .../rei/plugin/crafting/DefaultShapedDisplay.java | 86 ++++ .../plugin/crafting/DefaultShapelessDisplay.java | 90 +++++ .../shedaniel/rei/plugin/favorites/Animator.java | 97 +++++ .../plugin/favorites/GameModeFavoriteEntry.java | 276 +++++++++++++ .../rei/plugin/favorites/WeatherFavoriteEntry.java | 323 +++++++++++++++ .../rei/plugin/fuel/DefaultFuelCategory.java | 119 ++++++ .../rei/plugin/fuel/DefaultFuelDisplay.java | 64 +++ .../information/DefaultInformationCategory.java | 219 ++++++++++ .../information/DefaultInformationDisplay.java | 102 +++++ .../rei/plugin/pathing/DefaultPathingCategory.java | 75 ++++ .../rei/plugin/pathing/DefaultPathingDisplay.java | 80 ++++ .../rei/plugin/pathing/DummyShovelItem.java | 41 ++ .../plugin/smelting/DefaultSmeltingDisplay.java | 44 ++ .../plugin/smithing/DefaultSmithingCategory.java | 75 ++++ .../plugin/smithing/DefaultSmithingDisplay.java | 93 +++++ .../rei/plugin/smoking/DefaultSmokingDisplay.java | 41 ++ .../stonecutting/DefaultStoneCuttingCategory.java | 75 ++++ .../stonecutting/DefaultStoneCuttingDisplay.java | 84 ++++ .../plugin/stripping/DefaultStrippingCategory.java | 76 ++++ .../plugin/stripping/DefaultStrippingDisplay.java | 80 ++++ .../rei/plugin/stripping/DummyAxeItem.java | 40 ++ .../rei/plugin/tilling/DefaultTillingCategory.java | 75 ++++ .../rei/plugin/tilling/DefaultTillingDisplay.java | 80 ++++ .../shedaniel/rei/plugin/tilling/DummyHoeItem.java | 41 ++ default-plugin/src/main/resources/fabric.mod.json | 29 ++ default-plugin/src/main/resources/icon.png | Bin 0 -> 27270 bytes ...roughlyenoughitems-default-plugin.accessWidener | 21 + 51 files changed, 4921 insertions(+) create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultPlugin.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultPotionEffectExclusionZones.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultRecipeBookExclusionZones.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultServerContainerPlugin.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/autocrafting/DefaultRecipeBookHandler.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/base/DefaultBeaconBaseCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/base/DefaultBeaconBaseDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/payment/DefaultBeaconPaymentCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/payment/DefaultBeaconPaymentDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/blasting/DefaultBlastingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/brewing/BrewingRecipe.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/brewing/DefaultBrewingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/brewing/DefaultBrewingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/brewing/RegisteredBrewingRecipe.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/campfire/DefaultCampfireCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/campfire/DefaultCampfireDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/composting/DefaultCompostingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/composting/DefaultCompostingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/containers/CraftingContainerInfoWrapper.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/cooking/DefaultCookingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/cooking/DefaultCookingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/crafting/DefaultCraftingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/crafting/DefaultCraftingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/crafting/DefaultCustomDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/crafting/DefaultShapedDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/crafting/DefaultShapelessDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/favorites/Animator.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/favorites/GameModeFavoriteEntry.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/favorites/WeatherFavoriteEntry.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/fuel/DefaultFuelCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/fuel/DefaultFuelDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/information/DefaultInformationCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/information/DefaultInformationDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/pathing/DefaultPathingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/pathing/DefaultPathingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/pathing/DummyShovelItem.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/smelting/DefaultSmeltingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/smithing/DefaultSmithingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/smithing/DefaultSmithingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/smoking/DefaultSmokingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/stonecutting/DefaultStoneCuttingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/stonecutting/DefaultStoneCuttingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/stripping/DefaultStrippingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/stripping/DefaultStrippingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/stripping/DummyAxeItem.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/tilling/DefaultTillingCategory.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/tilling/DefaultTillingDisplay.java create mode 100644 default-plugin/src/main/java/me/shedaniel/rei/plugin/tilling/DummyHoeItem.java create mode 100644 default-plugin/src/main/resources/fabric.mod.json create mode 100644 default-plugin/src/main/resources/icon.png create mode 100644 default-plugin/src/main/resources/roughlyenoughitems-default-plugin.accessWidener (limited to 'default-plugin/src') diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultPlugin.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultPlugin.java new file mode 100644 index 000000000..ccb568637 --- /dev/null +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultPlugin.java @@ -0,0 +1,444 @@ +/* + * This file is licensed under the MIT License, part of Roughly Enough Items. + * Copyright (c) 2018, 2019, 2020 shedaniel + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package me.shedaniel.rei.plugin; + +import com.google.common.collect.Iterators; +import com.google.common.collect.Lists; +import com.google.common.collect.Sets; +import it.unimi.dsi.fastutil.objects.Object2FloatMap; +import it.unimi.dsi.fastutil.objects.ReferenceOpenHashSet; +import it.unimi.dsi.fastutil.objects.ReferenceSet; +import me.shedaniel.architectury.hooks.FluidStackHooks; +import me.shedaniel.math.Rectangle; +import me.shedaniel.rei.api.*; +import me.shedaniel.rei.api.entry.EntryStacks; +import me.shedaniel.rei.api.favorites.FavoriteEntry; +import me.shedaniel.rei.api.favorites.FavoriteEntryType; +import me.shedaniel.rei.api.fluid.FluidSupportProvider; +import me.shedaniel.rei.api.plugins.REIPluginV0; +import me.shedaniel.rei.plugin.autocrafting.DefaultRecipeBookHandler; +import me.shedaniel.rei.plugin.beacon.base.DefaultBeaconBaseCategory; +import me.shedaniel.rei.plugin.beacon.base.DefaultBeaconBaseDisplay; +import me.shedaniel.rei.plugin.beacon.payment.DefaultBeaconPaymentCategory; +import me.shedaniel.rei.plugin.beacon.payment.DefaultBeaconPaymentDisplay; +import me.shedaniel.rei.plugin.blasting.DefaultBlastingDisplay; +import me.shedaniel.rei.plugin.brewing.DefaultBrewingCategory; +import me.shedaniel.rei.plugin.brewing.DefaultBrewingDisplay; +import me.shedaniel.rei.plugin.brewing.RegisteredBrewingRecipe; +import me.shedaniel.rei.plugin.campfire.DefaultCampfireCategory; +import me.shedaniel.rei.plugin.campfire.DefaultCampfireDisplay; +import me.shedaniel.rei.plugin.composting.DefaultCompostingCategory; +import me.shedaniel.rei.plugin.composting.DefaultCompostingDisplay; +import me.shedaniel.rei.plugin.cooking.DefaultCookingCategory; +import me.shedaniel.rei.plugin.crafting.DefaultCraftingCategory; +import me.shedaniel.rei.plugin.crafting.DefaultCustomDisplay; +import me.shedaniel.rei.plugin.crafting.DefaultShapedDisplay; +import me.shedaniel.rei.plugin.crafting.DefaultShapelessDisplay; +import me.shedaniel.rei.plugin.favorites.GameModeFavoriteEntry; +import me.shedaniel.rei.plugin.favorites.WeatherFavoriteEntry; +import me.shedaniel.rei.plugin.fuel.DefaultFuelCategory; +import me.shedaniel.rei.plugin.fuel.DefaultFuelDisplay; +import me.shedaniel.rei.plugin.information.DefaultInformationCategory; +import me.shedaniel.rei.plugin.information.DefaultInformationDisplay; +import me.shedaniel.rei.plugin.pathing.DefaultPathingCategory; +import me.shedaniel.rei.plugin.pathing.DefaultPathingDisplay; +import me.shedaniel.rei.plugin.pathing.DummyShovelItem; +import me.shedaniel.rei.plugin.smelting.DefaultSmeltingDisplay; +import me.shedaniel.rei.plugin.smithing.DefaultSmithingCategory; +import me.shedaniel.rei.plugin.smithing.DefaultSmithingDisplay; +import me.shedaniel.rei.plugin.smoking.DefaultSmokingDisplay; +import me.shedaniel.rei.plugin.stonecutting.DefaultStoneCuttingCategory; +import me.shedaniel.rei.plugin.stonecutting.DefaultStoneCuttingDisplay; +import me.shedaniel.rei.plugin.stripping.DefaultStrippingCategory; +import me.shedaniel.rei.plugin.stripping.DefaultStrippingDisplay; +import me.shedaniel.rei.plugin.stripping.DummyAxeItem; +import me.shedaniel.rei.plugin.tilling.DefaultTillingCategory; +import me.shedaniel.rei.plugin.tilling.DefaultTillingDisplay; +import me.shedaniel.rei.plugin.tilling.DummyHoeItem; +import me.shedaniel.rei.utils.CollectionUtils; +import me.shedaniel.rei.utils.EntryStackCompoundList; +import net.fabricmc.api.EnvType; +import net.fabricmc.api.Environment; +import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.screens.inventory.*; +import net.minecraft.client.gui.screens.recipebook.RecipeUpdateListener; +import net.minecraft.core.Registry; +import net.minecraft.network.chat.Component; +import net.minecraft.network.chat.TranslatableComponent; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.tags.BlockTags; +import net.minecraft.tags.ItemTags; +import net.minecraft.tags.Tag; +import net.minecraft.world.InteractionResultHolder; +import net.minecraft.world.item.*; +import net.minecraft.world.item.alchemy.Potion; +import net.minecraft.world.item.alchemy.PotionBrewing; +import net.minecraft.world.item.alchemy.PotionUtils; +import net.minecraft.world.item.crafting.*; +import net.minecraft.world.item.enchantment.Enchantment; +import net.minecraft.world.item.enchantment.EnchantmentHelper; +import net.minecraft.world.level.GameType; +import net.minecraft.world.level.ItemLike; +import net.minecraft.world.level.block.ComposterBlock; +import net.minecraft.world.level.block.entity.AbstractFurnaceBlockEntity; +import net.minecraft.world.level.material.Fluid; +import org.apache.logging.log4j.LogManager; +import org.apache.logging.log4j.Logger; +import org.jetbrains.annotations.ApiStatus; + +import java.util.*; +import java.util.function.IntConsumer; +import java.util.function.UnaryOperator; +import java.util.stream.Stream; + +import static me.shedaniel.rei.impl.Internals.attachInstance; + +@Environment(EnvType.CLIENT) +@ApiStatus.Internal +public class DefaultPlugin implements REIPluginV0, BuiltinPlugin { + private static final Logger LOGGER = LogManager.getFormatterLogger("REI/DefaultPlugin"); + public static final ResourceLocation CRAFTING = BuiltinPlugin.CRAFTING; + public static final ResourceLocation SMELTING = BuiltinPlugin.SMELTING; + public static final ResourceLocation SMOKING = BuiltinPlugin.SMOKING; + public static final ResourceLocation BLASTING = BuiltinPlugin.BLASTING; + public static final ResourceLocation CAMPFIRE = BuiltinPlugin.CAMPFIRE; + public static final ResourceLocation STONE_CUTTING = BuiltinPlugin.STONE_CUTTING; + public static final ResourceLocation STRIPPING = BuiltinPlugin.STRIPPING; + public static final ResourceLocation BREWING = BuiltinPlugin.BREWING; + public static final ResourceLocation PLUGIN = BuiltinPlugin.PLUGIN; + public static final ResourceLocation COMPOSTING = BuiltinPlugin.COMPOSTING; + public static final ResourceLocation FUEL = BuiltinPlugin.FUEL; + public static final ResourceLocation SMITHING = BuiltinPlugin.SMITHING; + public static final ResourceLocation BEACON = BuiltinPlugin.BEACON; + public static final ResourceLocation BEACON_PAYMENT = BuiltinPlugin.BEACON_PAYMENT; + public static final ResourceLocation TILLING = BuiltinPlugin.TILLING; + public static final ResourceLocation PATHING = BuiltinPlugin.PATHING; + public static final ResourceLocation INFO = BuiltinPlugin.INFO; + private static final ResourceLocation DISPLAY_TEXTURE = new ResourceLocation("roughlyenoughitems", "textures/gui/display.png"); + private static final ResourceLocation DISPLAY_TEXTURE_DARK = new ResourceLocation("roughlyenoughitems", "textures/gui/display_dark.png"); + + public static ResourceLocation getDisplayTexture() { + return REIHelper.getInstance().getDefaultDisplayTexture(); + } + + public DefaultPlugin() { + attachInstance(this, BuiltinPlugin.class); + } + + public static void registerBrewingRecipe(RegisteredBrewingRecipe recipe) { + RecipeHelper.getInstance().registerDisplay(new DefaultBrewingDisplay(recipe.input, recipe.ingredient, recipe.output)); + } + + public static void registerInfoDisplay(DefaultInformationDisplay display) { + RecipeHelper.getInstance().registerDisplay(display); + } + + @Override + public void registerBrewingRecipe(Ingredient input, Ingredient ingredient, ItemStack output) { + registerBrewingRecipe(new RegisteredBrewingRecipe(input, ingredient, output)); + } + + @Override + public void registerInformation(List> entryStacks, Component name, UnaryOperator> textBuilder) { + registerInfoDisplay(DefaultInformationDisplay.createFromEntries(entryStacks, name).lines(textBuilder.apply(Lists.newArrayList()))); + } + + @Override + public ResourceLocation getPluginIdentifier() { + return PLUGIN; + } + + @Override + public void registerEntries(EntryRegistry entryRegistry) { + for (Item item : Registry.ITEM) { + List stacks = null; + try { + stacks = entryRegistry.appendStacksForItem(item); + } catch (Exception ignored) { + } + if (stacks != null) { + for (ItemStack stack : entryRegistry.appendStacksForItem(item)) { + entryRegistry.registerEntry(EntryStacks.of(stack)); + } + } else + entryRegistry.registerEntry(EntryStacks.of(item)); + } + EntryStack stack = EntryStacks.of(Items.ENCHANTED_BOOK); + List> enchantments = new ArrayList<>(); + for (Enchantment enchantment : Registry.ENCHANTMENT) { + IntConsumer consumer = level -> { + Map map = new HashMap<>(); + map.put(enchantment, level); + ItemStack itemStack = new ItemStack(Items.ENCHANTED_BOOK); + EnchantmentHelper.setEnchantments(map, itemStack); + enchantments.add(EntryStacks.of(itemStack).setting(EntryStack.Settings.CHECK_TAGS, EntryStack.Settings.TRUE)); + }; + if (enchantment.getMaxLevel() - enchantment.getMinLevel() >= 10) { + consumer.accept(enchantment.getMinLevel()); + consumer.accept(enchantment.getMaxLevel()); + } else { + for (int i = enchantment.getMinLevel(); i <= enchantment.getMaxLevel(); i++) consumer.accept(i); + } + } + entryRegistry.registerEntriesAfter(stack, enchantments); + for (Fluid fluid : Registry.FLUID) { + if (!fluid.defaultFluidState().isEmpty() && fluid.defaultFluidState().isSource()) + entryRegistry.registerEntry(EntryStacks.of(fluid)); + } + } + + @Override + public void registerPluginCategories(RecipeHelper recipeHelper) { + recipeHelper.registerCategories( + new DefaultCraftingCategory(), + new DefaultCookingCategory(SMELTING, EntryStacks.of(Items.FURNACE), "category.rei.smelting"), + new DefaultCookingCategory(SMOKING, EntryStacks.of(Items.SMOKER), "category.rei.smoking"), + new DefaultCookingCategory(BLASTING, EntryStacks.of(Items.BLAST_FURNACE), "category.rei.blasting"), new DefaultCampfireCategory(), + new DefaultStoneCuttingCategory(), + new DefaultFuelCategory(), + new DefaultBrewingCategory(), + new DefaultCompostingCategory(), + new DefaultStrippingCategory(), + new DefaultSmithingCategory(), + new DefaultBeaconBaseCategory(), + new DefaultBeaconPaymentCategory(), + new DefaultTillingCategory(), + new DefaultPathingCategory(), + new DefaultInformationCategory() + ); + } + + @Override + public void registerRecipeDisplays(RecipeHelper recipeHelper) { + recipeHelper.registerRecipes(CRAFTING, ShapelessRecipe.class, DefaultShapelessDisplay::new); + recipeHelper.registerRecipes(CRAFTING, ShapedRecipe.class, DefaultShapedDisplay::new); + recipeHelper.registerRecipes(SMELTING, SmeltingRecipe.class, DefaultSmeltingDisplay::new); + recipeHelper.registerRecipes(SMOKING, SmokingRecipe.class, DefaultSmokingDisplay::new); + recipeHelper.registerRecipes(BLASTING, BlastingRecipe.class, DefaultBlastingDisplay::new); + recipeHelper.registerRecipes(CAMPFIRE, CampfireCookingRecipe.class, DefaultCampfireDisplay::new); + recipeHelper.registerRecipes(STONE_CUTTING, StonecutterRecipe.class, DefaultStoneCuttingDisplay::new); + recipeHelper.registerRecipes(SMITHING, UpgradeRecipe.class, DefaultSmithingDisplay::new); + for (Map.Entry entry : AbstractFurnaceBlockEntity.getFuel().entrySet()) { + recipeHelper.registerDisplay(new DefaultFuelDisplay(EntryStacks.of(entry.getKey()), entry.getValue())); + } + List> arrowStack = Collections.singletonList(EntryStacks.of(Items.ARROW)); + ReferenceSet registeredPotions = new ReferenceOpenHashSet<>(); + EntryRegistry.getInstance().getEntryStacks().filter(entry -> entry.getValue() == Items.LINGERING_POTION).forEach(entry -> { + ItemStack itemStack = (ItemStack) entry.getValue(); + Potion potion = PotionUtils.getPotion(itemStack); + if (registeredPotions.add(potion)) { + EntryStackCompoundList input = new EntryStackCompoundList(); + for (int i = 0; i < 4; i++) + input.add(arrowStack); + input.add(Collections.singletonList(EntryStacks.of(itemStack))); + for (int i = 0; i < 4; i++) + input.add(arrowStack); + ItemStack outputStack = new ItemStack(Items.TIPPED_ARROW, 8); + PotionUtils.setPotion(outputStack, potion); + PotionUtils.setCustomEffects(outputStack, PotionUtils.getCustomEffects(itemStack)); + List> output = Collections.singletonList(EntryStacks.of(outputStack).setting(EntryStack.Settings.CHECK_TAGS, EntryStack.Settings.TRUE)); + recipeHelper.registerDisplay(new DefaultCustomDisplay(null, input, output)); + } + }); + if (ComposterBlock.COMPOSTABLES.isEmpty()) + ComposterBlock.bootStrap(); + Object2FloatMap compostables = ComposterBlock.COMPOSTABLES; + int i = 0; + Iterator>> iterator = Iterators.partition(compostables.object2FloatEntrySet().stream().sorted(Map.Entry.comparingByValue()).iterator(), 48); + while (iterator.hasNext()) { + List> entries = iterator.next(); + recipeHelper.registerDisplay(new DefaultCompostingDisplay(i, entries, compostables, new ItemStack(Items.BONE_MEAL))); + i++; + } + DummyAxeItem.getStrippedBlocksMap().entrySet().stream().sorted(Comparator.comparing(b -> Registry.BLOCK.getKey(b.getKey()))).forEach(set -> { + recipeHelper.registerDisplay(new DefaultStrippingDisplay(EntryStacks.of(set.getKey()), EntryStacks.of(set.getValue()))); + }); + DummyHoeItem.getTilledBlocksMap().entrySet().stream().sorted(Comparator.comparing(b -> Registry.BLOCK.getKey(b.getKey()))).forEach(set -> { + recipeHelper.registerDisplay(new DefaultTillingDisplay(EntryStacks.of(set.getKey()), EntryStacks.of(set.getValue().getBlock()))); + }); + DummyShovelItem.getPathBlocksMap().entrySet().stream().sorted(Comparator.comparing(b -> Registry.BLOCK.getKey(b.getKey()))).forEach(set -> { + recipeHelper.registerDisplay(new DefaultPathingDisplay(EntryStacks.of(set.getKey()), EntryStacks.of(set.getValue().getBlock()))); + }); + recipeHelper.registerDisplay(new DefaultBeaconBaseDisplay(CollectionUtils.map(Lists.newArrayList(BlockTags.BEACON_BASE_BLOCKS.getValues()), ItemStack::new))); + recipeHelper.registerDisplay(new DefaultBeaconPaymentDisplay(CollectionUtils.map(Lists.newArrayList(ItemTags.BEACON_PAYMENT_ITEMS.getValues()), ItemStack::new))); + Set potions = Sets.newLinkedHashSet(); + for (Ingredient container : PotionBrewing.ALLOWED_CONTAINERS) { + for (PotionBrewing.Mix mix : PotionBrewing.POTION_MIXES) { + Potion from = mix.from; + Ingredient ingredient = mix.ingredient; + Potion to = mix.to; + Ingredient base = Ingredient.of(Arrays.stream(container.getItems()) + .map(ItemStack::copy) + .map(stack -> PotionUtils.setPotion(stack, from))); + ItemStack output = Arrays.stream(container.getItems()) + .map(ItemStack::copy) + .map(stack -> PotionUtils.setPotion(stack, to)) + .findFirst().orElse(ItemStack.EMPTY); + registerBrewingRecipe(base, ingredient, output); + potions.add(from); + potions.add(to); + } + } + for (Potion potion : potions) { + for (PotionBrewing.Mix mix : PotionBrewing.CONTAINER_MIXES) { + Item from = mix.from; + Ingredient ingredient = mix.ingredient; + Item to = mix.to; + Ingredient base = Ingredient.of(PotionUtils.setPotion(new ItemStack(from), potion)); + ItemStack output = PotionUtils.setPotion(new ItemStack(to), potion); + registerBrewingRecipe(base, ingredient, output); + } + } + } + + @Override + public void postRegister() { + // TODO Turn this into an API + // Sit tight! This will be a fast journey! + long time = System.currentTimeMillis(); + EntryRegistry.getInstance().getEntryStacks().forEach(this::applyPotionTransformer); + for (List displays : RecipeHelper.getInstance().getAllRecipesNoHandlers().values()) { + for (RecipeDisplay display : displays) { + for (List> entries : display.getInputEntries()) + for (EntryStack stack : entries) + applyPotionTransformer(stack); + for (List> entries : display.getResultingEntries()) + for (EntryStack stack : entries) + applyPotionTransformer(stack); + } + } + time = System.currentTimeMillis() - time; + LOGGER.info("Applied Check Tags for potion in %dms.", time); + } + + private void applyPotionTransformer(EntryStack stack) { + if (stack.getValue() instanceof PotionItem) + stack.setting(EntryStack.Settings.CHECK_TAGS, EntryStack.Settings.TRUE); + } + + @Override + public void registerBounds(DisplayHelper displayHelper) { + BaseBoundsHandler baseBoundsHandler = BaseBoundsHandler.getInstance(); + baseBoundsHandler.registerExclusionZones(EffectRenderingInventoryScreen.class, new DefaultPotionEffectExclusionZones()); + baseBoundsHandler.registerExclusionZones(RecipeUpdateListener.class, new DefaultRecipeBookExclusionZones()); + displayHelper.registerProvider(new DisplayHelper.DisplayBoundsProvider>() { + @Override + public Rectangle getScreenBounds(AbstractContainerScreen screen) { + return new Rectangle(screen.leftPos, screen.topPos, screen.imageWidth, screen.imageHeight); + } + + @Override + public Class getBaseSupportedClass() { + return AbstractContainerScreen.class; + } + }); + } + + @Override + public void registerOthers(RecipeHelper recipeHelper) { + recipeHelper.registerAutoCraftingHandler(new DefaultRecipeBookHandler()); + + recipeHelper.registerWorkingStations(CRAFTING, EntryStacks.of(Items.CRAFTING_TABLE)); + recipeHelper.registerWorkingStations(SMELTING, EntryStacks.of(Items.FURNACE)); + recipeHelper.registerWorkingStations(SMOKING, EntryStacks.of(Items.SMOKER)); + recipeHelper.registerWorkingStations(BLASTING, EntryStacks.of(Items.BLAST_FURNACE)); + recipeHelper.registerWorkingStations(CAMPFIRE, EntryStacks.of(Items.CAMPFIRE), EntryStacks.of(Items.SOUL_CAMPFIRE)); + recipeHelper.registerWorkingStations(FUEL, EntryStacks.of(Items.FURNACE), EntryStacks.of(Items.SMOKER), EntryStacks.of(Items.BLAST_FURNACE)); + recipeHelper.registerWorkingStations(BREWING, EntryStacks.of(Items.BREWING_STAND)); + recipeHelper.registerWorkingStations(STONE_CUTTING, EntryStacks.of(Items.STONECUTTER)); + recipeHelper.registerWorkingStations(COMPOSTING, EntryStacks.of(Items.COMPOSTER)); + recipeHelper.registerWorkingStations(SMITHING, EntryStacks.of(Items.SMITHING_TABLE)); + recipeHelper.registerWorkingStations(BEACON, EntryStacks.of(Items.BEACON)); + recipeHelper.registerWorkingStations(BEACON_PAYMENT, EntryStacks.of(Items.BEACON)); + Set axes = Sets.newHashSet(), hoes = Sets.newHashSet(), shovels = Sets.newHashSet(); + EntryRegistry.getInstance().getEntryStacks().filter(stack -> stack.getValueType() == ItemStack.class).map(stack -> ((ItemStack) stack.getValue()).getItem()).forEach(item -> { + if (item instanceof AxeItem && axes.add(item)) { + recipeHelper.registerWorkingStations(STRIPPING, EntryStacks.of(item)); + } + if (item instanceof HoeItem && hoes.add(item)) { + recipeHelper.registerWorkingStations(TILLING, EntryStacks.of(item)); + } + if (item instanceof ShovelItem && shovels.add(item)) { + recipeHelper.registerWorkingStations(PATHING, EntryStacks.of(item)); + } + }); + Tag axesTag = Minecraft.getInstance().getConnection().getTags().getItems().getTag(new ResourceLocation("c", "axes")); + if (axesTag != null) { + for (Item item : axesTag.getValues()) { + if (axes.add(item)) recipeHelper.registerWorkingStations(STRIPPING, EntryStacks.of(item)); + } + } + Tag hoesTag = Minecraft.getInstance().getConnection().getTags().getItems().getTag(new ResourceLocation("c", "hoes")); + if (hoesTag != null) { + for (Item item : hoesTag.getValues()) { + if (hoes.add(item)) recipeHelper.registerWorkingStations(TILLING, EntryStacks.of(item)); + } + } + Tag shovelsTag = Minecraft.getInstance().getConnection().getTags().getItems().getTag(new ResourceLocation("c", "shovels")); + if (shovelsTag != null) { + for (Item item : shovelsTag.getValues()) { + if (shovels.add(item)) recipeHelper.registerWorkingStations(PATHING, EntryStacks.of(item)); + } + } + recipeHelper.removeAutoCraftButton(FUEL); + recipeHelper.removeAutoCraftButton(COMPOSTING); + recipeHelper.removeAutoCraftButton(BEACON); + recipeHelper.removeAutoCraftButton(BEACON_PAYMENT); + recipeHelper.removeAutoCraftButton(INFO); + recipeHelper.registerContainerClickArea(new Rectangle(88, 32, 28, 23), CraftingScreen.class, CRAFTING); + recipeHelper.registerContainerClickArea(new Rectangle(137, 29, 10, 13), InventoryScreen.class, CRAFTING); + recipeHelper.registerContainerClickArea(new Rectangle(97, 16, 14, 30), BrewingStandScreen.class, BREWING); + recipeHelper.registerContainerClickArea(new Rectangle(78, 32, 28, 23), FurnaceScreen.class, SMELTING); + recipeHelper.registerContainerClickArea(new Rectangle(78, 32, 28, 23), SmokerScreen.class, SMOKING); + recipeHelper.registerContainerClickArea(new Rectangle(78, 32, 28, 23), BlastFurnaceScreen.class, BLASTING); + FluidSupportProvider.getInstance().registerProvider(entry -> { + ItemStack stack = entry.getValue(); + if (stack.getItem() instanceof BucketItem) + return InteractionResultHolder.success(Stream.of(EntryStacks.of(((BucketItem) stack.getItem()).content, FluidStackHooks.bucketAmount()))); + return InteractionResultHolder.pass(null); + }); +// SubsetsRegistry subsetsRegistry = SubsetsRegistry.INSTANCE; +// subsetsRegistry.registerPathEntry("roughlyenoughitems:food", EntryStacks.of(Items.MILK_BUCKET)); +// subsetsRegistry.registerPathEntry("roughlyenoughitems:food/roughlyenoughitems:cookies", EntryStacks.of(Items.COOKIE)); + + FavoriteEntryType.registry().register(GameModeFavoriteEntry.ID, GameModeFavoriteEntry.Type.INSTANCE); + FavoriteEntryType.registry().getOrCrateSection(new TranslatableComponent(GameModeFavoriteEntry.TRANSLATION_KEY)) + .add(Stream.concat( + Arrays.stream(GameType.values()), + Stream.of((GameType) null) + ).map(GameModeFavoriteEntry.Type.INSTANCE::fromArgs).toArray(FavoriteEntry[]::new)); + FavoriteEntryType.registry().register(WeatherFavoriteEntry.ID, WeatherFavoriteEntry.Type.INSTANCE); + FavoriteEntryType.registry().getOrCrateSection(new TranslatableComponent(WeatherFavoriteEntry.TRANSLATION_KEY)) + .add(Stream.concat( + Arrays.stream(WeatherFavoriteEntry.Weather.values()), + Stream.of((WeatherFavoriteEntry.Weather) null) + ).map(WeatherFavoriteEntry.Type.INSTANCE::fromArgs).toArray(FavoriteEntry[]::new)); + } + + @Override + public int getPriority() { + return -1; + } + +} diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultPotionEffectExclusionZones.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultPotionEffectExclusionZones.java new file mode 100644 index 000000000..9fd033af6 --- /dev/null +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultPotionEffectExclusionZones.java @@ -0,0 +1,64 @@ +/* + * This file is licensed under the MIT License, part of Roughly Enough Items. + * Copyright (c) 2018, 2019, 2020 shedaniel + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package me.shedaniel.rei.plugin; + +import com.google.common.collect.Ordering; +import me.shedaniel.math.Rectangle; +import me.shedaniel.rei.api.REIHelper; +import net.fabricmc.api.EnvType; +import net.fabricmc.api.Environment; +import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.screens.inventory.AbstractContainerScreen; +import net.minecraft.client.gui.screens.inventory.EffectRenderingInventoryScreen; +import net.minecraft.world.effect.MobEffectInstance; + +import java.util.ArrayList; +import java.util.Collection; +import java.util.Collections; +import java.util.List; +import java.util.function.Supplier; + +@Environment(EnvType.CLIENT) +public class DefaultPotionEffectExclusionZones implements Supplier> { + @Override + public List get() { + if (!(REIHelper.getInstance().getPreviousContainerScreen() instanceof EffectRenderingInventoryScreen) || !((EffectRenderingInventoryScreen) REIHelper.getInstance().getPreviousContainerScreen()).doRenderEffects) + return Collections.emptyList(); + Collection activePotionEffects = Minecraft.getInstance().player.getActiveEffects(); + if (activePotionEffects.isEmpty()) + return Collections.emptyList(); + AbstractContainerScreen containerScreen = REIHelper.getInstance().getPreviousContainerScreen(); + List list = new ArrayList<>(); + int x = containerScreen.leftPos - 124; + int y = containerScreen.topPos; + int height = 33; + if (activePotionEffects.size() > 5) + height = 132 / (activePotionEffects.size() - 1); + for (MobEffectInstance instance : Ordering.natural().sortedCopy(activePotionEffects)) { + list.add(new Rectangle(x, y, 166, height)); + y += height; + } + return list; + } +} diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultRecipeBookExclusionZones.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultRecipeBookExclusionZones.java new file mode 100644 index 000000000..bde75067d --- /dev/null +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultRecipeBookExclusionZones.java @@ -0,0 +1,58 @@ +/* + * This file is licensed under the MIT License, part of Roughly Enough Items. + * Copyright (c) 2018, 2019, 2020 shedaniel + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package me.shedaniel.rei.plugin; + +import com.google.common.collect.Lists; +import me.shedaniel.math.Rectangle; +import me.shedaniel.rei.api.REIHelper; +import net.fabricmc.api.EnvType; +import net.fabricmc.api.Environment; +import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.screens.inventory.AbstractContainerScreen; +import net.minecraft.client.gui.screens.recipebook.RecipeBookComponent; +import net.minecraft.client.gui.screens.recipebook.RecipeUpdateListener; +import net.minecraft.world.inventory.RecipeBookMenu; + +import java.util.Collections; +import java.util.List; +import java.util.function.Supplier; + +@Environment(EnvType.CLIENT) +public class DefaultRecipeBookExclusionZones implements Supplier> { + + @Override + public List get() { + if (!(Minecraft.getInstance().screen instanceof RecipeUpdateListener) || !(REIHelper.getInstance().getPreviousContainerScreen().getMenu() instanceof RecipeBookMenu) || + !Minecraft.getInstance().player.getRecipeBook().isOpen(((RecipeBookMenu) REIHelper.getInstance().getPreviousContainerScreen().getMenu()).getRecipeBookType())) + return Collections.emptyList(); + RecipeBookComponent recipeBookWidget = ((RecipeUpdateListener) Minecraft.getInstance().screen).getRecipeBookComponent(); + AbstractContainerScreen containerScreen = REIHelper.getInstance().getPreviousContainerScreen(); + List l = Lists.newArrayList(new Rectangle(containerScreen.leftPos - 4 - 145, containerScreen.topPos, 4 + 145 + 30, containerScreen.imageHeight)); + int size = recipeBookWidget.tabButtons.size(); + if (size > 0) + l.add(new Rectangle(containerScreen.leftPos - 4 - 145 - 30, containerScreen.topPos, 30, size * 27)); + return l; + } + +} diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultServerContainerPlugin.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultServerContainerPlugin.java new file mode 100644 index 000000000..f0b9c978c --- /dev/null +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/DefaultServerContainerPlugin.java @@ -0,0 +1,40 @@ +/* + * This file is licensed under the MIT License, part of Roughly Enough Items. + * Copyright (c) 2018, 2019, 2020 shedaniel + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package me.shedaniel.rei.plugin; + +import me.shedaniel.rei.plugin.containers.CraftingContainerInfoWrapper; +import me.shedaniel.rei.server.ContainerInfoHandler; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.world.inventory.*; + +public class DefaultServerContainerPlugin implements Runnable { + @Override + public void run() { + ContainerInfoHandler.registerContainerInfo(new ResourceLocation("minecraft", "plugins/crafting"), CraftingContainerInfoWrapper.create(CraftingMenu.class)); + ContainerInfoHandler.registerContainerInfo(new ResourceLocation("minecraft", "plugins/crafting"), CraftingContainerInfoWrapper.create(InventoryMenu.class)); + ContainerInfoHandler.registerContainerInfo(new ResourceLocation("minecraft", "plugins/smelting"), CraftingContainerInfoWrapper.create(FurnaceMenu.class)); + ContainerInfoHandler.registerContainerInfo(new ResourceLocation("minecraft", "plugins/smoking"), CraftingContainerInfoWrapper.create(SmokerMenu.class)); + ContainerInfoHandler.registerContainerInfo(new ResourceLocation("minecraft", "plugins/blasting"), CraftingContainerInfoWrapper.create(BlastFurnaceMenu.class)); + } +} diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/autocrafting/DefaultRecipeBookHandler.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/autocrafting/DefaultRecipeBookHandler.java new file mode 100644 index 000000000..80ee0196a --- /dev/null +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/autocrafting/DefaultRecipeBookHandler.java @@ -0,0 +1,104 @@ +/* + * This file is licensed under the MIT License, part of Roughly Enough Items. + * Copyright (c) 2018, 2019, 2020 shedaniel + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package me.shedaniel.rei.plugin.autocrafting; + +import me.shedaniel.rei.api.AutoTransferHandler; +import me.shedaniel.rei.api.ClientHelper; +import me.shedaniel.rei.api.RecipeDisplay; +import me.shedaniel.rei.api.TransferRecipeDisplay; +import me.shedaniel.rei.plugin.cooking.DefaultCookingDisplay; +import me.shedaniel.rei.plugin.crafting.DefaultCraftingDisplay; +import net.fabricmc.api.EnvType; +import net.fabricmc.api.Environment; +import net.minecraft.client.gui.screens.Screen; +import net.minecraft.client.gui.screens.recipebook.RecipeUpdateListener; +import net.minecraft.client.resources.language.I18n; +import net.minecraft.world.inventory.CraftingMenu; +import net.minecraft.world.inventory.InventoryMenu; +import net.minecraft.world.inventory.RecipeBookMenu; +import net.minecraft.world.item.crafting.Recipe; +import org.jetbrains.annotations.NotNull; + +@Environment(EnvType.CLIENT) +public class DefaultRecipeBookHandler implements AutoTransferHandler { + @NotNull + @Override + public Result handle(@NotNull Context context) { + if (context.getRecipe() instanceof TransferRecipeDisplay && ClientHelper.getInstance().canUseMovePackets()) + return Result.createNotApplicable(); + RecipeDisplay display = context.getRecipe(); + if (!(context.getContainer() instanceof RecipeBookMenu)) + return Result.createNotApplicable(); + RecipeBookMenu container = (RecipeBookMenu) context.getContainer(); + if (container == null) + return Result.createNotApplicable(); + if (display instanceof DefaultCraftingDisplay) { + DefaultCraftingDisplay craftingDisplay = (DefaultCraftingDisplay) display; + if (craftingDisplay.getOptionalRecipe().isPresent()) { + int h = -1, w = -1; + if (container instanceof CraftingMenu) { + h = 3; + w = 3; + } else if (container instanceof InventoryMenu) { + h = 2; + w = 2; + } + if (h == -1 || w == -1) + return Result.createNotApplicable(); + Recipe recipe = (craftingDisplay).getOptionalRecipe().get(); + if (craftingDisplay.getHeight() > h || craftingDisplay.getWidth() > w) + return Result.createFailed(I18n.get("error.rei.transfer.too_small", h, w)); + if (!context.getMinecraft().player.getRecipeBook().contains(recipe)) + return Result.createFailed(I18n.get("error.rei.recipe.not.unlocked")); + if (!context.isActuallyCrafting()) + return Result.createSuccessful(); + context.getMinecraft().setScreen(context.getContainerScreen()); + if (context.getContainerScreen() instanceof RecipeUpdateListener) + ((RecipeUpdateListener) context.getContainerScreen()).getRecipeBookComponent().ghostRecipe.clear(); + context.getMinecraft().gameMode.handlePlaceRecipe(container.containerId, recipe, Screen.hasShiftDown()); + return Result.createSuccessful(); + } + } else if (display instanceof DefaultCookingDisplay) { + DefaultCookingDisplay defaultDisplay = (DefaultCookingDisplay) display; + if (defaultDisplay.getOptionalRecipe().isPresent()) { + Recipe recipe = (defaultDisplay).getOptionalRecipe().get(); + if (!context.getMinecraft().player.getRecipeBook().contains(recipe)) + return Result.createFailed(I18n.get("error.rei.recipe.not.unlocked")); + if (!context.isActuallyCrafting()) + return Result.createSuccessful(); + context.getMinecraft().setScreen(context.getContainerScreen()); + if (context.getContainerScreen() instanceof RecipeUpdateListener) + ((RecipeUpdateListener) context.getContainerScreen()).getRecipeBookComponent().ghostRecipe.clear(); + context.getMinecraft().gameMode.handlePlaceRecipe(container.containerId, recipe, Screen.hasShiftDown()); + return Result.createSuccessful(); + } + } + return Result.createNotApplicable(); + } + + @Override + public double getPriority() { + return -20; + } +} diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/base/DefaultBeaconBaseCategory.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/base/DefaultBeaconBaseCategory.java new file mode 100644 index 000000000..08ad35567 --- /dev/null +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/base/DefaultBeaconBaseCategory.java @@ -0,0 +1,187 @@ +/* + * This file is licensed under the MIT License, part of Roughly Enough Items. + * Copyright (c) 2018, 2019, 2020 shedaniel + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package me.shedaniel.rei.plugin.beacon.base; + +import com.google.common.collect.Lists; +import com.mojang.blaze3d.vertex.PoseStack; +import me.shedaniel.clothconfig2.ClothConfigInitializer; +import me.shedaniel.clothconfig2.api.ScissorsHandler; +import me.shedaniel.clothconfig2.api.ScrollingContainer; +import me.shedaniel.math.Point; +import me.shedaniel.math.Rectangle; +import me.shedaniel.rei.api.REIHelper; +import me.shedaniel.rei.api.RecipeCategory; +import me.shedaniel.rei.api.Renderer; +import me.shedaniel.rei.api.entry.EntryStacks; +import me.shedaniel.rei.api.widgets.Slot; +import me.shedaniel.rei.api.widgets.Tooltip; +import me.shedaniel.rei.api.widgets.Widgets; +import me.shedaniel.rei.gui.entries.RecipeRenderer; +import me.shedaniel.rei.gui.widget.Widget; +import me.shedaniel.rei.gui.widget.WidgetWithBounds; +import me.shedaniel.rei.plugin.DefaultPlugin; +import me.shedaniel.rei.utils.CollectionUtils; +import net.minecraft.client.Minecraft; +import net.minecraft.client.gui.components.events.GuiEventListener; +import net.minecraft.client.resources.language.I18n; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.util.Mth; +import net.minecraft.world.level.block.Blocks; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; + +import java.util.List; +import java.util.Objects; + +public class DefaultBeaconBaseCategory implements RecipeCategory { + @Override + public @NotNull ResourceLocation getIdentifier() { + return DefaultPlugin.BEACON; + } + + @Override + @NotNull + public String getCategoryName() { + return I18n.get("category.rei.beacon_base"); + } + + @Override + @NotNull + public Renderer getLogo() { + return EntryStacks.of(Blocks.BEACON); + } + + @Override + public @NotNull RecipeRenderer getSimpleRenderer(DefaultBeaconBaseDisplay recipe) { + String name = getCategoryName(); + return new RecipeRenderer() { + @Override + public int getHeight() { + return 10 + Minecraft.getInstance().font.lineHeight; + } + + @Override + public void render(PoseStack matrices, Rectangle rectangle, int mouseX, int mouseY, float delta) { + Minecraft.getInstance().font.draw(matrices, name, rectangle.x + 5, rectangle.y + 6, -1); + } + }; + } + + @Override + public @NotNull List setupDisplay(DefaultBeaconBaseDisplay display, Rectangle bounds) { + List widgets = Lists.newArrayList(); + widgets.add(Widgets.createSlot(new Point(bounds.getCenterX() - 8, bounds.y + 3)).entry(EntryStacks.of(Blocks.BEACON))); + Rectangle rectangle = new Rectangle(bounds.getCenterX() - (bounds.width / 2) - 1, bounds.y + 23, bounds.width + 2, bounds.height - 28); + widgets.add(Widgets.createSlotBase(rectangle)); + widgets.add(new ScrollableSlotsWidget(rectangle, CollectionUtils.map(display.getEntries(), t -> Widgets.createSlot(new Point(0, 0)).disableBackground().entry(t)))); + return widgets; + } + + @Override + public int getDisplayHeight() { + return 140; + } + + @Override + public int getFixedRecipesPerPage() { + return 1; + } + + private static class ScrollableSlotsWidget extends WidgetWithBounds { + private Rectangle bounds; + private List widgets; + private final ScrollingContainer scrolling = new ScrollingContainer() { + @Override + public Rectangle getBounds() { + Rectangle bounds = ScrollableSlotsWidget.this.getBounds(); + return new Rectangle(bounds.x + 1, bounds.y + 1, bounds.width - 2, bounds.height - 2); + } + + @Override + public int getMaxScrollHeight() { + return Mth.ceil(widgets.size() / 8f) * 18; + } + }; + + public ScrollableSlotsWidget(Rectangle bounds, List widgets) { + this.bounds = Objects.requireNonNull(bounds); + this.widgets = Lists.newArrayList(widgets); + } + + @Override + public boolean mouseScrolled(double double_1, double double_2, double double_3) { + if (containsMouse(double_1, double_2)) { + scrolling.offset(ClothConfigInitializer.getScrollStep() * -double_3, true); + return true; + } + return false; + } + + @NotNull + @Override + public Rectangle getBounds() { + return bounds; + } + + @Override + public boolean mouseClicked(double mouseX, double mouseY, int button) { + if (scrolling.updateDraggingState(mouseX, mouseY, button)) + return true; + return super.mouseClicked(mouseX, mouseY, button); + } + + @Override + public boolean mouseDragged(double mouseX, double mouseY, int button, double deltaX, double deltaY) { + if (scrolling.mouseDragged(mouseX, mouseY, button, deltaX, deltaY)) + return true; + return super.mouseDragged(mouseX, mouseY, button, deltaX, deltaY); + } + + @Override + public void render(PoseStack matrices, int mouseX, int mouseY, float delta) { + scrolling.updatePosition(delta); + Rectangle innerBounds = scrolling.getScissorBounds(); + ScissorsHandler.INSTANCE.scissor(innerBounds); + for (int y = 0; y < Mth.ceil(widgets.size() / 8f); y++) { + for (int x = 0; x < 8; x++) { + int index = y * 8 + x; + if (widgets.size() <= index) + break; + Slot widget = widgets.get(index); + widget.getBounds().setLocation(bounds.x + 1 + x * 18, (int) (bounds.y + 1 + y * 18 - scrolling.scrollAmount)); + widget.render(matrices, mouseX, mouseY, delta); + } + } + ScissorsHandler.INSTANCE.removeLastScissor(); + ScissorsHandler.INSTANCE.scissor(scrolling.getBounds()); + scrolling.renderScrollBar(0xff000000, 1, REIHelper.getInstance().isDarkThemeEnabled() ? 0.8f : 1f); + ScissorsHandler.INSTANCE.removeLastScissor(); + } + + @Override + public List children() { + return widgets; + } + } +} diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/base/DefaultBeaconBaseDisplay.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/base/DefaultBeaconBaseDisplay.java new file mode 100644 index 000000000..0ddbd7e09 --- /dev/null +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/base/DefaultBeaconBaseDisplay.java @@ -0,0 +1,65 @@ +/* + * This file is licensed under the MIT License, part of Roughly Enough Items. + * Copyright (c) 2018, 2019, 2020 shedaniel + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package me.shedaniel.rei.plugin.beacon.base; + +import me.shedaniel.rei.api.EntryStack; +import me.shedaniel.rei.api.RecipeDisplay; +import me.shedaniel.rei.api.entry.EntryStacks; +import me.shedaniel.rei.plugin.DefaultPlugin; +import net.fabricmc.api.EnvType; +import net.fabricmc.api.Environment; +import net.minecraft.resources.ResourceLocation; +import net.minecraft.world.item.ItemStack; +import org.jetbrains.annotations.NotNull; + +import java.util.Collections; +import java.util.List; + +@Environment(EnvType.CLIENT) +public class DefaultBeaconBaseDisplay implements RecipeDisplay { + private List> entries; + + public DefaultBeaconBaseDisplay(List entries) { + this.entries = EntryStacks.ofItemStacks(entries); + } + + @Override + public @NotNull List>> getInputEntries() { + return Collections.singletonList(entries); + } + + public List> getEntries() { + return entries; + } + + @Override + public @NotNull List>> getResultingEntries() { + return Collections.emptyList(); + } + + @Override + public @NotNull ResourceLocation getRecipeCategory() { + return DefaultPlugin.BEACON; + } +} diff --git a/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/payment/DefaultBeaconPaymentCategory.java b/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/payment/DefaultBeaconPaymentCategory.java new file mode 100644 index 000000000..bba02c60c --- /dev/null +++ b/default-plugin/src/main/java/me/shedaniel/rei/plugin/beacon/payment/DefaultBeaconPaymentCategory.java @@ -0,0 +1,183 @@ +/* + * This file is licensed under the MIT License, part of Roughly Enough Items. + * Copyright (c) 2018, 2019, 2020 shedaniel + * + * Permission is hereby granted, free of charge, to any person obtaining a copy + * of this software and associated documentation files (the "Software"), to deal + * in the Software without restriction, including without limitation the rights + * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell + * copies of the Software, and to permit persons to whom the Software is + * furnished to do so, subject to the following conditions: + * + * The above copyright notice and this permission notice shall be included in all + * copies or substantial portions of the Software. + * + * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR + * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, + * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE + * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER + * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, + * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE + * SOFTWARE. + */ + +package me.shedaniel.rei.plugin.beacon.payment; + +import com.google.common.collect.Lists; +import com.mojang.blaze3d.vertex.PoseStack; +import me.shedaniel.clothconfig2.ClothConfigInitializer; +import me.shedaniel.clothconfig2.api.ScissorsHandler; +import me.shedaniel.clothconfig2.api.ScrollingContainer; +import me.shedaniel.math.Point; +import me.shedaniel.math.Rectangle; +import me.shedaniel.rei.api.REIHelper; +import me.shedaniel.rei.api.RecipeCategory; +import me.shedaniel.rei.api.Renderer; +import me.shedaniel.rei.api.entry.EntryStacks; +import me.shedaniel.rei.api.widgets.Slot; +import me.shedaniel.rei.api.widgets.Widgets; +import me.shedaniel.rei.gui.entries.RecipeRenderer; +import me.shedaniel.rei.gui.widget.Widget; +import me.shedaniel.rei.gui.widget.WidgetWithBounds; +import me.shedaniel.rei.plugin.DefaultPlugin; +import me.shedaniel.rei.utils.CollectionUtils; +import net.minecraft.clien