diff --git a/build.gradle b/build.gradle index 917939c..44026be 100644 --- a/build.gradle +++ b/build.gradle @@ -2,6 +2,7 @@ plugins { id 'eclipse' id 'maven-publish' id 'net.minecraftforge.gradle' version '5.1.+' + id 'org.gradle.crypto.checksum' version '1.4.0' } // Mojang ships Java 17 to end users in 1.18+, so your mod should target Java 17. @@ -22,7 +23,7 @@ minecraft { // // Use non-default mappings at your own risk. They may not always work. // Simply re-run your setup task after changing the mappings to update your workspace. - mappings channel: 'official', version: '1.19.2' + mappings channel: 'official', version: minecraft_version // accessTransformer = file('src/main/resources/META-INF/accesstransformer.cfg') // Currently, this location cannot be changed from the default. @@ -45,10 +46,10 @@ minecraft { property 'forge.logging.console.level', 'debug' // Comma-separated list of namespaces to load gametests from. Empty = all namespaces. - property 'forge.enabledGameTestNamespaces', 'pylons' + property 'forge.enabledGameTestNamespaces', mod_id mods { - pylons { + "${mod_id}" { source sourceSets.main } } @@ -62,10 +63,10 @@ minecraft { property 'forge.logging.console.level', 'debug' // Comma-separated list of namespaces to load gametests from. Empty = all namespaces. - property 'forge.enabledGameTestNamespaces', 'pylons' + property 'forge.enabledGameTestNamespaces', mod_id mods { - pylons { + "${mod_id}" { source sourceSets.main } } @@ -90,10 +91,10 @@ minecraft { property 'forge.logging.console.level', 'debug' // Comma-separated list of namespaces to load gametests from. Empty = all namespaces. - property 'forge.enabledGameTestNamespaces', 'pylons' + property 'forge.enabledGameTestNamespaces', mod_id mods { - pylons { + "${mod_id}" { source sourceSets.main } } @@ -107,10 +108,10 @@ minecraft { property 'forge.logging.console.level', 'debug' // Specify the modid for data generation, where to output the resulting resource, and where to look for existing resources. - args '--mod', 'pylons', '--all', '--output', file('src/generated/resources/'), '--existing', file('src/main/resources/') + args '--mod', mod_id, '--all', '--output', file('src/generated/resources/'), '--existing', file('src/main/resources/') mods { - pylons { + "${mod_id}" { source sourceSets.main } } @@ -122,9 +123,15 @@ minecraft { sourceSets.main.resources { srcDir 'src/generated/resources' } repositories { - maven { - url "https://www.cursemaven.com" - content { + exclusiveContent { + forRepositories(fg.repository) + forRepository { + maven { + name "CurseMaven" + url "https://www.cursemaven.com" + } + } + filter { includeGroup "curse.maven" } } @@ -134,7 +141,10 @@ dependencies { // Specify the version of Minecraft to use. If this is any group other than 'net.minecraft', it is assumed // that the dep is a ForgeGradle 'patcher' dependency, and its patches will be applied. // The userdev artifact is a special name and will get all sorts of transformations applied to it. - minecraft 'net.minecraftforge:forge:1.19.2-43.0.2' + minecraft "net.minecraftforge:forge:${minecraft_version}-${forge_version}" + + runtimeOnly fg.deobf("curse.maven:jei-238222:4615177") + compileOnly fg.deobf("curse.maven:ftb-teams-forge-404468:4611938") // runtimeOnly fg.deobf("curse.maven:jei-238222:3670018") // runtimeOnly fg.deobf("curse.maven:top-245211:3586969") @@ -147,24 +157,37 @@ dependencies { } jar { - archiveBaseName.set("${mod_id}-${mc_version}") + archiveBaseName.set("${mod_id}-${minecraft_version}") manifest { attributes([ "Specification-Title" : mod_id, "Specification-Vendor" : group, "Specification-Version" : "1", // We are version 1 of ourselves "Implementation-Title" : project.name, - "Implementation-Version" : project.jar.archiveVersion, - "Implementation-Timestamp": new Date().format("yyyy-MM-dd'T'HH:mm:ssZ"), + "Implementation-Version" : project.jar.archiveVersion ]) } + + // The settings below make sure that your build is reproducible + // More information at https://docs.gradle.org/current/userguide/working_with_files.html#sec:reproducible_archives + preserveFileTimestamps = false + reproducibleFileOrder = true + + // Example configuration to allow publishing using the maven-publish plugin + // This is the preferred method to reobfuscate your jar file + finalizedBy('reobfJar') } -// Example configuration to allow publishing using the maven-publish plugin -// This is the preferred method to reobfuscate your jar file -jar.finalizedBy('reobfJar') -// However if you are in a multi-project build, dev time needs unobfed jar files, so you can delay the obfuscation until publishing by doing -// publish.dependsOn('reobfJar') +// generate checksum for output jar +import org.gradle.crypto.checksum.Checksum +tasks.register('createChecksums', Checksum) { + dependsOn jar + + inputFiles.setFrom(jar.outputs.files) + checksumAlgorithm.set(Checksum.Algorithm.SHA512) + appendFileNameToChecksum.set(true) +} +build.finalizedBy('createChecksums') publishing { publications { diff --git a/gradle.properties b/gradle.properties index f62b34f..51ba62c 100644 --- a/gradle.properties +++ b/gradle.properties @@ -3,7 +3,8 @@ org.gradle.jvmargs=-Xmx3G org.gradle.daemon=false -mc_version=1.19.2 +minecraft_version=1.19.2 +forge_version=43.2.0 group=net.permutated mod_id=pylons -version=3.1.0 +version=3.2.0 diff --git a/src/main/java/net/permutated/pylons/ConfigManager.java b/src/main/java/net/permutated/pylons/ConfigManager.java index 11bdf8a..fdbeefe 100644 --- a/src/main/java/net/permutated/pylons/ConfigManager.java +++ b/src/main/java/net/permutated/pylons/ConfigManager.java @@ -13,6 +13,7 @@ private ConfigManager() { // nothing to do } + public static final String CATEGORY_GENERAL = "general"; public static final String CATEGORY_EXPULSION = "expulsion_pylon"; public static final String CATEGORY_INFUSION = "infusion_pylon"; public static final String CATEGORY_HARVESTER = "harvester_pylon"; @@ -28,6 +29,9 @@ private ConfigManager() { } public static class ServerConfig { + // CATEGORY_GENERAL + public final ForgeConfigSpec.BooleanValue teamSupportEnabled; + // CATEGORY_EXPULSION public final ForgeConfigSpec.ConfigValue> expulsionAllowedDimensions; public final ForgeConfigSpec.IntValue expulsionWorldSpawnRadius; @@ -49,6 +53,15 @@ public static class ServerConfig { ServerConfig(ForgeConfigSpec.Builder builder) { + // CATEGORY_GENERAL + builder.push(CATEGORY_GENERAL); + + teamSupportEnabled = builder + .comment("Whether team support is enabled if a compatible mod (FTB Teams) is installed") + .define("teamSupportEnabled", true); + + builder.pop(); + // CATEGORY_EXPULSION builder.push(CATEGORY_EXPULSION); diff --git a/src/main/java/net/permutated/pylons/Pylons.java b/src/main/java/net/permutated/pylons/Pylons.java index a0279b4..d1cddf4 100644 --- a/src/main/java/net/permutated/pylons/Pylons.java +++ b/src/main/java/net/permutated/pylons/Pylons.java @@ -12,6 +12,7 @@ import net.minecraftforge.fml.javafmlmod.FMLJavaModLoadingContext; import net.permutated.pylons.block.AbstractPylonBlock; import net.permutated.pylons.client.ClientSetup; +import net.permutated.pylons.compat.teams.TeamCompat; import net.permutated.pylons.item.MobFilterCard; import net.permutated.pylons.item.PlayerFilterCard; import net.permutated.pylons.network.NetworkDispatcher; @@ -33,6 +34,7 @@ public Pylons() { ModRegistry.register(); NetworkDispatcher.register(); + TeamCompat.init(); ModLoadingContext.get().registerConfig(ModConfig.Type.SERVER, ConfigManager.SERVER_SPEC); FMLJavaModLoadingContext.get().getModEventBus().addListener(this::onCommonSetupEvent); diff --git a/src/main/java/net/permutated/pylons/compat/teams/FTBTeamSupport.java b/src/main/java/net/permutated/pylons/compat/teams/FTBTeamSupport.java new file mode 100644 index 0000000..494f806 --- /dev/null +++ b/src/main/java/net/permutated/pylons/compat/teams/FTBTeamSupport.java @@ -0,0 +1,12 @@ +package net.permutated.pylons.compat.teams; + +import dev.ftb.mods.ftbteams.FTBTeamsAPI; + +import java.util.UUID; + +public class FTBTeamSupport implements TeamSupport { + @Override + public boolean arePlayersInSameTeam(UUID player1, UUID player2) { + return FTBTeamsAPI.arePlayersInSameTeam(player1, player2); + } +} diff --git a/src/main/java/net/permutated/pylons/compat/teams/NoTeamSupport.java b/src/main/java/net/permutated/pylons/compat/teams/NoTeamSupport.java new file mode 100644 index 0000000..ab2e7fc --- /dev/null +++ b/src/main/java/net/permutated/pylons/compat/teams/NoTeamSupport.java @@ -0,0 +1,10 @@ +package net.permutated.pylons.compat.teams; + +import java.util.UUID; + +public class NoTeamSupport implements TeamSupport { + @Override + public boolean arePlayersInSameTeam(UUID player1, UUID player2) { + return false; + } +} diff --git a/src/main/java/net/permutated/pylons/compat/teams/TeamCompat.java b/src/main/java/net/permutated/pylons/compat/teams/TeamCompat.java new file mode 100644 index 0000000..9bd83c7 --- /dev/null +++ b/src/main/java/net/permutated/pylons/compat/teams/TeamCompat.java @@ -0,0 +1,19 @@ +package net.permutated.pylons.compat.teams; + +import net.minecraftforge.fml.ModList; + +public class TeamCompat { + private TeamCompat() { + // nothing to do + } + private static TeamSupport instance = new NoTeamSupport(); + public static TeamSupport getInstance() { + return instance; + } + + public static void init() { + if (ModList.get().isLoaded("ftbteams")) { + instance = new FTBTeamSupport(); + } + } +} diff --git a/src/main/java/net/permutated/pylons/compat/teams/TeamSupport.java b/src/main/java/net/permutated/pylons/compat/teams/TeamSupport.java new file mode 100644 index 0000000..860a2da --- /dev/null +++ b/src/main/java/net/permutated/pylons/compat/teams/TeamSupport.java @@ -0,0 +1,7 @@ +package net.permutated.pylons.compat.teams; + +import java.util.UUID; + +public interface TeamSupport { + boolean arePlayersInSameTeam(UUID player1, UUID player2); +} diff --git a/src/main/java/net/permutated/pylons/data/DataGenerators.java b/src/main/java/net/permutated/pylons/data/DataGenerators.java index 7883436..2844f86 100644 --- a/src/main/java/net/permutated/pylons/data/DataGenerators.java +++ b/src/main/java/net/permutated/pylons/data/DataGenerators.java @@ -2,15 +2,18 @@ import net.minecraft.data.DataGenerator; import net.minecraftforge.common.data.ExistingFileHelper; +import net.minecraftforge.data.event.GatherDataEvent; import net.minecraftforge.eventbus.api.SubscribeEvent; import net.minecraftforge.fml.common.Mod; -import net.minecraftforge.data.event.GatherDataEvent; +import net.permutated.pylons.Pylons; import net.permutated.pylons.data.client.BlockStates; import net.permutated.pylons.data.client.ItemModels; import net.permutated.pylons.data.client.Languages; -import net.permutated.pylons.data.server.*; +import net.permutated.pylons.data.server.BlockLoot; +import net.permutated.pylons.data.server.BlockTags; +import net.permutated.pylons.data.server.CraftingRecipes; -@Mod.EventBusSubscriber(bus = Mod.EventBusSubscriber.Bus.MOD) +@Mod.EventBusSubscriber(bus = Mod.EventBusSubscriber.Bus.MOD, modid = Pylons.MODID) public final class DataGenerators { private DataGenerators() {} diff --git a/src/main/java/net/permutated/pylons/inventory/container/AbstractPylonContainer.java b/src/main/java/net/permutated/pylons/inventory/container/AbstractPylonContainer.java index 33206a1..8a6dc22 100644 --- a/src/main/java/net/permutated/pylons/inventory/container/AbstractPylonContainer.java +++ b/src/main/java/net/permutated/pylons/inventory/container/AbstractPylonContainer.java @@ -13,7 +13,7 @@ import net.minecraft.world.item.ItemStack; import net.minecraft.world.level.Level; import net.minecraft.world.level.block.Block; -import net.minecraftforge.items.CapabilityItemHandler; +import net.minecraftforge.common.capabilities.ForgeCapabilities; import net.minecraftforge.items.IItemHandler; import net.minecraftforge.items.SlotItemHandler; import net.minecraftforge.items.wrapper.InvWrapper; @@ -41,7 +41,7 @@ protected AbstractPylonContainer(@Nullable MenuType containerType, int window IItemHandler wrappedInventory = new InvWrapper(playerInventory); if (tileEntity != null) { - tileEntity.getCapability(CapabilityItemHandler.ITEM_HANDLER_CAPABILITY).ifPresent(handler -> { + tileEntity.getCapability(ForgeCapabilities.ITEM_HANDLER).ifPresent(handler -> { for (int slot = 0; slot < AbstractPylonTile.SLOTS; slot++) { addSlot(new SlotItemHandler(handler, slot, 8 + slot * 18, 54)); } diff --git a/src/main/java/net/permutated/pylons/tile/AbstractPylonTile.java b/src/main/java/net/permutated/pylons/tile/AbstractPylonTile.java index 1b31682..d0d888a 100644 --- a/src/main/java/net/permutated/pylons/tile/AbstractPylonTile.java +++ b/src/main/java/net/permutated/pylons/tile/AbstractPylonTile.java @@ -16,10 +16,12 @@ import net.minecraft.world.level.block.state.BlockState; import net.minecraftforge.common.UsernameCache; import net.minecraftforge.common.capabilities.Capability; +import net.minecraftforge.common.capabilities.ForgeCapabilities; import net.minecraftforge.common.util.LazyOptional; -import net.minecraftforge.items.CapabilityItemHandler; import net.minecraftforge.items.IItemHandler; import net.minecraftforge.items.ItemStackHandler; +import net.permutated.pylons.ConfigManager; +import net.permutated.pylons.compat.teams.TeamCompat; import net.permutated.pylons.util.ChunkManager; import net.permutated.pylons.util.Constants; import net.permutated.pylons.util.Range; @@ -57,7 +59,7 @@ protected boolean canAccessInventory() { @Nonnull @Override public LazyOptional getCapability(Capability cap, @Nullable Direction side) { - if (cap == CapabilityItemHandler.ITEM_HANDLER_CAPABILITY && (side == null || canAccessInventory())) { + if (cap == ForgeCapabilities.ITEM_HANDLER && (side == null || canAccessInventory())) { return handler.cast(); } return super.getCapability(cap, side); @@ -80,7 +82,6 @@ public void setRemoved() { } protected UUID owner = null; - protected String ownerName = null; @Nullable public UUID getOwner() { @@ -92,8 +93,13 @@ public void setOwner(UUID owner) { this.setChanged(); } + public boolean hasTeamAccess(Player player) { + return Boolean.TRUE.equals(ConfigManager.SERVER.teamSupportEnabled.get()) + && TeamCompat.getInstance().arePlayersInSameTeam(owner, player.getUUID()); + } + public boolean canAccess(Player player) { - return Objects.equals(player.getUUID(), owner) || owner == null || player.hasPermissions(2); + return Objects.equals(player.getUUID(), owner) || owner == null || player.hasPermissions(2) || hasTeamAccess(player); } private long lastTicked = 0L; diff --git a/src/main/java/net/permutated/pylons/tile/HarvesterPylonTile.java b/src/main/java/net/permutated/pylons/tile/HarvesterPylonTile.java index 5fa8487..f7f8bcb 100644 --- a/src/main/java/net/permutated/pylons/tile/HarvesterPylonTile.java +++ b/src/main/java/net/permutated/pylons/tile/HarvesterPylonTile.java @@ -11,7 +11,7 @@ import net.minecraft.world.level.block.entity.BlockEntity; import net.minecraft.world.level.block.state.BlockState; import net.minecraft.world.level.block.state.properties.IntegerProperty; -import net.minecraftforge.items.CapabilityItemHandler; +import net.minecraftforge.common.capabilities.ForgeCapabilities; import net.minecraftforge.items.IItemHandler; import net.permutated.pylons.ConfigManager; import net.permutated.pylons.ModRegistry; @@ -78,7 +78,7 @@ public void tick() { workStatus = Status.MISSING_INVENTORY; return; } - IItemHandler itemHandler = target.getCapability(CapabilityItemHandler.ITEM_HANDLER_CAPABILITY, Direction.DOWN) + IItemHandler itemHandler = target.getCapability(ForgeCapabilities.ITEM_HANDLER, Direction.DOWN) .resolve() .orElse(null); if (itemHandler == null) {