Skip to content

Commit

Permalink
Rift Warp Menu (#10)
Browse files Browse the repository at this point in the history
* Rift Warp Menu

* Rift Warp Fixes
- Remove Config and Regular Warp Menu buttons from Rift warp menu
- Add Rift texture and some rift warps
- Require warps to have a `commandName` or `slotIndex`
- Fix `Warp#setWarpIcon` being called twice in LayoutLoader.java

* Bug Fixes
- Fix close window packet not being sent when the fancy warp menu is closed in certain situations
- Convert SkyBlockJoinListener to chat-based detection for slight performance improvement
- Settings and regular warp menu button logic fixes

* Rift update rewrite
- Rewrite GUIs for easier maintainability
- Add additional checks for determining the currently open SB menu (incomplete)
- Finish rift layout
- Fix build fail when Crowdin doesn't download any strings
- Update Gradle to 8.5

* Update DevAuth to 1.2.0

* Add stricter SkyBlock menu detection
- Detect SkyBlock menus using chest items in addition to name
- Remove Mixin

* Re-add features removed in rewrite
- Re-implement reminders to use fancy warp menu using Forge API
- Replace hacky implementation of Jerry warp with hacky implementation of Garry warp
- Fix in-game season check
- Replace existing selective warp hiding system with warp tags
- Add Garry as warp command alias

* Fix hot reload not applying new layout without re-opening warp menu
- Add warp menu background feature (has scaling issues, not ready for general use)

* Add error for Jerry's Workshop not being open yet
  • Loading branch information
ILikePlayingGames authored Feb 20, 2024
1 parent b427a39 commit d608c57
Show file tree
Hide file tree
Showing 44 changed files with 1,837 additions and 593 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -51,7 +51,7 @@ jobs:
CROWDIN_PROJECT_ID: ${{ secrets.CROWDIN_PROJECT_ID }}
CROWDIN_PERSONAL_TOKEN: ${{ secrets.CROWDIN_PERSONAL_TOKEN }}
- name: Fix ownership of Gradle build directory
run: sudo chown -R $(whoami):$(id -gn) build
run: '[ -d build ] && sudo chown -R $(whoami):$(id -gn) build || echo "Skipped, build directory does not exist."'
- name: Grant execute permission for gradlew
run: chmod +x gradlew
- name: Build with Gradle
Expand Down
22 changes: 2 additions & 20 deletions build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@ val baseGroup: String by project
val mcVersion: String by project
val modid: String by project
val version: String by project
val mixinGroup = "$baseGroup.$modid.mixin"

// Toolchains:
java {
Expand All @@ -31,9 +30,6 @@ loom {
launchConfigs {
"client" {
property("devauth.enabled", "true")
property("mixin.debug", "true")
property("asmhelper.verbose", "true")
arg("--tweakClass", "org.spongepowered.asm.launch.MixinTweaker")
}
}
runConfigs {
Expand All @@ -59,10 +55,6 @@ loom {
}
forge {
pack200Provider.set(dev.architectury.pack200.java.Pack200Adapter())
mixinConfig("mixins.$modid.json")
}
mixin {
defaultRefmapName.set("mixins.$modid.refmap.json")
}
}

Expand All @@ -82,12 +74,7 @@ dependencies {
minecraft("com.mojang:minecraft:1.8.9")
mappings("de.oceanlabs.mcp:mcp_stable:22-1.8.9")
forge("net.minecraftforge:forge:1.8.9-11.15.1.2318-1.8.9")

shadowImpl("org.spongepowered:mixin:0.7.11-SNAPSHOT") {
isTransitive = false
}
annotationProcessor("org.spongepowered:mixin:0.8.5-SNAPSHOT")
runtimeOnly("me.djtheredstoner:DevAuth-forge-legacy:1.1.2")
runtimeOnly("me.djtheredstoner:DevAuth-forge-legacy:1.2.0")
}

// Tasks:
Expand All @@ -101,10 +88,6 @@ tasks.withType(Jar::class) {
manifest.attributes.run {
this["FMLCorePluginContainsFMLMod"] = "true"
this["ForceLoadAsMod"] = "true"

// If you don't want mixins, remove these lines
this["TweakClass"] = "org.spongepowered.asm.launch.MixinTweaker"
this["MixinConfigs"] = "mixins.$modid.json"
}
}

Expand All @@ -120,9 +103,8 @@ tasks.processResources {
inputs.property("version", project.version)
inputs.property("mcversion", mcVersion)
inputs.property("modid", modid)
inputs.property("mixinGroup", mixinGroup)

filesMatching(listOf("mcmod.info", "mixins.$modid.json")) {
filesMatching("mcmod.info") {
expand(inputs.properties)
}

Expand Down
2 changes: 1 addition & 1 deletion gradle/wrapper/gradle-wrapper.properties
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-8.3-bin.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-8.5-bin.zip
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
60 changes: 29 additions & 31 deletions src/main/java/ca/tirelesstraveler/fancywarpmenu/FancyWarpMenu.java
Original file line number Diff line number Diff line change
Expand Up @@ -22,14 +22,18 @@

package ca.tirelesstraveler.fancywarpmenu;

import ca.tirelesstraveler.fancywarpmenu.commands.OpenConfigCommand;
import ca.tirelesstraveler.fancywarpmenu.data.layout.Island;
import ca.tirelesstraveler.fancywarpmenu.data.layout.Layout;
import ca.tirelesstraveler.fancywarpmenu.data.Settings;
import ca.tirelesstraveler.fancywarpmenu.listeners.ChatListener;
import ca.tirelesstraveler.fancywarpmenu.resourceloaders.LayoutLoader;
import ca.tirelesstraveler.fancywarpmenu.data.skyblockconstants.SkyBlockConstants;
import ca.tirelesstraveler.fancywarpmenu.listeners.SkyBlockJoinListener;
import ca.tirelesstraveler.fancywarpmenu.listeners.WarpMenuListener;
import ca.tirelesstraveler.fancywarpmenu.resourceloaders.SkyBlockConstantsLoader;
import ca.tirelesstraveler.fancywarpmenu.state.EnvironmentDetails;
import ca.tirelesstraveler.fancywarpmenu.state.FancyWarpMenuState;
import net.minecraft.client.Minecraft;
import net.minecraft.client.renderer.texture.TextureManager;
import net.minecraft.client.resources.IReloadableResourceManager;
Expand Down Expand Up @@ -58,10 +62,7 @@ public class FancyWarpMenu {
private static String modId;
static Logger logger;
private static ForgeVersion.CheckResult updateCheckResult;
private static Layout layout;
private static SkyBlockConstants skyBlockConstants;
private static SkyBlockJoinListener skyblockJoinListener;
private static WarpMenuListener warpMenuListener;
private static KeyBinding keyBindingOpenWarpMenu;

public static FancyWarpMenu getInstance() {
Expand All @@ -70,16 +71,18 @@ public static FancyWarpMenu getInstance() {

@Mod.EventHandler
public void preInit(FMLPreInitializationEvent event) {
ProgressManager.ProgressBar bar = ProgressManager.push("Pre-init", 4);
EnvironmentDetails.deobfuscatedEnvironment = (Boolean) Launch.blackboard.get("fml.deobfuscatedEnvironment");
ProgressManager.ProgressBar bar = ProgressManager.push("Pre-init", 5);
EnvironmentDetails.setDeobfuscatedEnvironment((Boolean) Launch.blackboard.get("fml.deobfuscatedEnvironment"));
modId = event.getModMetadata().modId;
modContainer = Loader.instance().activeModContainer();
bar.step("Initializing Listeners");
warpMenuListener = new WarpMenuListener();
WarpMenuListener warpMenuListener = new WarpMenuListener();
MinecraftForge.EVENT_BUS.register(warpMenuListener);
((IReloadableResourceManager) Minecraft.getMinecraft().getResourceManager()).registerReloadListener(warpMenuListener);
skyblockJoinListener = new SkyBlockJoinListener();
SkyBlockJoinListener skyblockJoinListener = new SkyBlockJoinListener();
MinecraftForge.EVENT_BUS.register(skyblockJoinListener);
ChatListener chatListener = new ChatListener();
MinecraftForge.EVENT_BUS.register(chatListener);
bar.step("Loading Settings");
Settings.setConfig(new Configuration(event.getSuggestedConfigurationFile(), modContainer.getVersion()));
Settings.setConfigPropertyOrder();
Expand All @@ -89,7 +92,9 @@ public void preInit(FMLPreInitializationEvent event) {
bar.step("Loading SkyBlock Constants");
skyBlockConstants = SkyBlockConstantsLoader.loadSkyBlockConstants();
bar.step("Loading Layout");
layout = LayoutLoader.loadLayout();
FancyWarpMenuState.setOverworldLayout(LayoutLoader.loadLayout(LayoutLoader.OVERWORLD_LAYOUT_LOCATION));
bar.step("Loading Rift Layout");
FancyWarpMenuState.setRiftLayout(LayoutLoader.loadLayout(LayoutLoader.RIFT_LAYOUT_LOCATION));
ProgressManager.pop(bar);
}

Expand All @@ -100,25 +105,25 @@ public void init(FMLInitializationEvent event) {
ClientRegistry.registerKeyBinding(keyBindingOpenWarpMenu);
ClientCommandHandler.instance.registerCommand(new OpenConfigCommand());

ProgressManager.ProgressBar bar = ProgressManager.push("Loading Textures", layout.getIslandList().size() + 1);
Layout overworldLayout = FancyWarpMenuState.getOverworldLayout();
ProgressManager.ProgressBar bar = ProgressManager.push("Loading Textures",
overworldLayout.getIslandList().size() + 1);
TextureManager textureManager = Minecraft.getMinecraft().getTextureManager();

for (Island island : layout.getIslandList()) {
for (Island island : overworldLayout.getIslandList()) {
bar.step(island.getName());
textureManager.bindTexture(island.getTextureLocation());
}

bar.step("Warp Icon");
textureManager.bindTexture(layout.getWarpIcon().getTextureLocation());
textureManager.bindTexture(overworldLayout.getWarpIcon().getTextureLocation());

ProgressManager.pop(bar);
}

@Mod.EventHandler
public void postInit(FMLPostInitializationEvent event) {
if (Loader.isModLoaded("patcher")) {
EnvironmentDetails.patcherInstalled = true;
}
EnvironmentDetails.setPatcherInstalled(Loader.isModLoaded("patcher"));
}

public ModContainer getModContainer() {
Expand All @@ -133,18 +138,10 @@ public static ForgeVersion.CheckResult getUpdateCheckResult() {
return updateCheckResult;
}

public WarpMenuListener getWarpMenuListener() {
return warpMenuListener;
}

public boolean isPlayerOnSkyBlock() {
return skyblockJoinListener.isOnSkyBlock();
}

public void reloadResources() {
Minecraft.getMinecraft().refreshResources();
reloadSkyBlockConstants();
reloadLayout();
reloadLayouts();
}

public void reloadSkyBlockConstants() {
Expand All @@ -156,12 +153,17 @@ public void reloadSkyBlockConstants() {
}
}

public void reloadLayout() {
Layout loadedLayout = LayoutLoader.loadLayout();
public void reloadLayouts() {
Layout loadedOverworldLayout = LayoutLoader.loadLayout(LayoutLoader.OVERWORLD_LAYOUT_LOCATION);
Layout loadedRiftLayout = LayoutLoader.loadLayout(LayoutLoader.RIFT_LAYOUT_LOCATION);

// Will be null if json syntax is wrong or layout is invalid
if (loadedLayout != null) {
FancyWarpMenu.layout = loadedLayout;
if (loadedOverworldLayout != null) {
FancyWarpMenuState.setOverworldLayout(loadedOverworldLayout);
}

if (loadedRiftLayout != null) {
FancyWarpMenuState.setRiftLayout(loadedRiftLayout);
}
}

Expand All @@ -176,10 +178,6 @@ public static KeyBinding getKeyBindingOpenWarpMenu() {
return keyBindingOpenWarpMenu;
}

public static Layout getLayout() {
return layout;
}

public static SkyBlockConstants getSkyBlockConstants() {
return skyBlockConstants;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,9 @@
* OR OTHER DEALINGS IN THE SOFTWARE.
*/

package ca.tirelesstraveler.fancywarpmenu;
package ca.tirelesstraveler.fancywarpmenu.commands;

import ca.tirelesstraveler.fancywarpmenu.state.FancyWarpMenuState;
import net.minecraft.command.CommandBase;
import net.minecraft.command.ICommandSender;

Expand All @@ -48,6 +49,6 @@ public String getCommandUsage(ICommandSender sender) {
*/
@Override
public void processCommand(ICommandSender sender, String[] args) {
FancyWarpMenu.getInstance().getWarpMenuListener().onOpenConfigMenuCommand();
FancyWarpMenuState.setOpenConfigMenuRequested(true);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@

package ca.tirelesstraveler.fancywarpmenu.data;

import ca.tirelesstraveler.fancywarpmenu.EnvironmentDetails;
import ca.tirelesstraveler.fancywarpmenu.state.EnvironmentDetails;
import ca.tirelesstraveler.fancywarpmenu.FancyWarpMenu;
import ca.tirelesstraveler.fancywarpmenu.gui.FancyWarpMenuConfigScreen;
import net.minecraft.util.EnumChatFormatting;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@
import net.minecraft.client.gui.ScaledResolution;
import net.minecraft.util.ResourceLocation;

import static ca.tirelesstraveler.fancywarpmenu.data.DataCommon.gson;
import static ca.tirelesstraveler.fancywarpmenu.resourceloaders.ResourceLoader.gson;

/**
* Class that holds the settings for drawing buttons that are not islands, like the config button.
Expand All @@ -35,19 +35,19 @@
@SuppressWarnings("unused")
public abstract class Button {

/** x-coordinate on {@link ca.tirelesstraveler.fancywarpmenu.gui.GuiFancyWarp} to draw the config button at (0-{@link Island#GRID_UNIT_WIDTH_FACTOR}) */
/** x-coordinate on {@link ca.tirelesstraveler.fancywarpmenu.gui.GuiFancyWarp} to draw the button at (0-{@link Island#GRID_UNIT_WIDTH_FACTOR}) */
private int gridX;
/** y-coordinate on {@link ca.tirelesstraveler.fancywarpmenu.gui.GuiFancyWarp} to draw the config button at (0-{@link Island#GRID_UNIT_HEIGHT_FACTOR}) */
/** y-coordinate on {@link ca.tirelesstraveler.fancywarpmenu.gui.GuiFancyWarp} to draw the button at (0-{@link Island#GRID_UNIT_HEIGHT_FACTOR}) */
private int gridY;
/** Width to render the config button texture at as a percentage of the screen width. Texture height is set automatically. */
/** Width to render the button texture at as a percentage of the screen width. Texture height is set automatically. */
private float widthPercentage;
/** Width of the warp icon texture, used to set the width of the warp button */
/** Width of the icon texture in pixels, used to set the width of the button */
private transient int textureWidth;
/** Height of the warp icon texture, used to set the height of the warp button */
/** Height of the icon texture in pixels, used to set the height of the button */
private transient int textureHeight;
/** Width of the config button */
/** Width of the button in pixels */
private transient int width;
/** Height of the config button */
/** Height of the button in pixels */
private transient int height;

Button(){}
Expand Down Expand Up @@ -75,7 +75,7 @@ public int getHeight() {
}

/**
* Initialize config button width and height.
* Initialize button width and height.
* This should be called in {@link GuiScreen#initGui()}.
*/
public void init(ScaledResolution res) {
Expand Down Expand Up @@ -103,8 +103,9 @@ public static void validateButtonIcon(Button button) throws IllegalArgumentExcep
throw new IllegalArgumentException("Button gridX must be between 0 and " + Island.GRID_UNIT_HEIGHT_FACTOR + " inclusive");
}

if (button.widthPercentage < 0 || button.widthPercentage > 1) {
throw new IllegalArgumentException("Button icon widthPercentage must be between 0 and 1");
// A button width of zero causes a stack overflow
if (button.widthPercentage <= 0 || button.widthPercentage > 1) {
throw new IllegalArgumentException("Button icon widthPercentage must be within the interval (0,1]");
}
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@
import java.io.IOException;
import java.util.List;

import static ca.tirelesstraveler.fancywarpmenu.data.DataCommon.gson;
import static ca.tirelesstraveler.fancywarpmenu.resourceloaders.ResourceLoader.gson;

/**
* Island data used to create the island buttons on the GUI
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,18 +22,33 @@

package ca.tirelesstraveler.fancywarpmenu.data.layout;

import ca.tirelesstraveler.fancywarpmenu.FancyWarpMenu;
import net.minecraft.client.Minecraft;
import net.minecraft.client.resources.IResource;
import net.minecraft.util.ResourceLocation;
import org.apache.commons.io.IOUtils;

import java.io.IOException;
import java.util.List;

import static ca.tirelesstraveler.fancywarpmenu.data.DataCommon.gson;
import static ca.tirelesstraveler.fancywarpmenu.resourceloaders.ResourceLoader.gson;

@SuppressWarnings("unused")
public class Layout {

/** Path to the texture to be shown as the background of the fancy warp menu */
private String backgroundTexturePath;
/** The islands to be shown in the fancy warp menu */
private List<Island> islandList;
/** Texture settings for the warp icon, which is drawn for all warp buttons */
private WarpIcon warpIcon;
/** Position and size settings for the button that opens the mod's settings menu */
private ConfigButton configButton;
/** Position and size settings for the button that turns off the fancy warp menu */
private RegularWarpMenuButton regularWarpMenuButton;

private transient ResourceLocation backgroundTextureLocation;

private Layout(){}

public List<Island> getIslandList() {
Expand All @@ -52,9 +67,31 @@ public RegularWarpMenuButton getRegularWarpMenuButton() {
return regularWarpMenuButton;
}

public ResourceLocation getBackgroundTextureLocation() {
return backgroundTextureLocation;
}

public void setBackgroundTextureLocation() {
if (backgroundTexturePath != null) {
backgroundTextureLocation =
new ResourceLocation(FancyWarpMenu.getInstance().getModId(), backgroundTexturePath);
}
}

public static void validateLayout(Layout layout) throws IllegalArgumentException, NullPointerException {
if (layout == null) {
throw new NullPointerException("Warp configuration cannot be null");
throw new NullPointerException("Layout cannot be null");
}

if (layout.backgroundTexturePath != null) {
ResourceLocation textureLocation =
new ResourceLocation(FancyWarpMenu.getInstance().getModId(), layout.backgroundTexturePath);
try {
IResource resource = Minecraft.getMinecraft().getResourceManager().getResource(textureLocation);
IOUtils.closeQuietly(resource.getInputStream());
} catch (IOException e) {
throw new RuntimeException(String.format("Layout background texture path not found at %s", textureLocation));
}
}

if (layout.islandList == null || layout.islandList.isEmpty()) {
Expand Down
Loading

0 comments on commit d608c57

Please sign in to comment.