Skip to content
Open
76 changes: 54 additions & 22 deletions build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,8 @@ import net.modificationstation.stationapi.gradle.SubprojectHelpers.addDependency

plugins {
id("maven-publish")
id("fabric-loom") version "1.9-SNAPSHOT"
id("babric-loom-extension") version "1.9.2"
id("net.fabricmc.fabric-loom-remap") version "1.15.+"
id("ploceus") version "1.15-SNAPSHOT"
}

// https://stackoverflow.com/a/40101046 - Even with kotlin, gradle can't get it's shit together.
Expand All @@ -15,18 +15,38 @@ inline fun <reified C> Project.configure(name: String, configuration: C.() -> Un
}

allprojects {
apply(plugin = "maven-publish")
apply(plugin = "fabric-loom")
apply(plugin = "babric-loom-extension")
if (project != rootProject) {
apply(plugin = "maven-publish")
apply(plugin = "net.fabricmc.fabric-loom-remap")
apply(plugin = "ploceus")
}

pluginManager.withPlugin("ploceus") {
val ploceus = extensions.getByName<net.ornithemc.ploceus.api.PloceusGradleExtensionApi>("ploceus")
ploceus.setIntermediaryGeneration(2)

dependencies {
"minecraft"("com.mojang:minecraft:${project.properties["minecraft_version"]}")
"mappings"(ploceus.mappings("net.glasslauncher:biny-ornithe:b1.7.3+build.${project.properties["biny_mappings"]}:mergedv2"))
"clientExceptions"(ploceus.raven(project.properties["client_raven_build"].toString(), "client"))
"serverExceptions"(ploceus.raven(project.properties["server_raven_build"].toString(), "server"))
"clientSignatures"(ploceus.sparrow(project.properties["client_sparrow_build"].toString(), "client"))
"serverSignatures"(ploceus.sparrow(project.properties["server_sparrow_build"].toString(), "server"))
"clientNests"("net.glasslauncher:biny-nests:b1.7.3-client+build.2")
"serverNests"("net.glasslauncher:biny-nests:b1.7.3-server+build.2")
"modImplementation"("net.fabricmc:fabric-loader:${project.properties["loader_version"]}")
}
}

java.sourceCompatibility = JavaVersion.VERSION_17
java.targetCompatibility = JavaVersion.VERSION_17
java.sourceCompatibility = JavaVersion.VERSION_21
java.targetCompatibility = JavaVersion.VERSION_21

repositories {
maven(url = "https://maven.minecraftforge.net/")
maven(url = "https://maven.glass-launcher.net/babric")
maven(url = "https://maven.glass-launcher.net/snapshots")
maven(url = "https://maven.glass-launcher.net/releases")
maven(url = "https://maven.glass-launcher.net/snapshots")
maven(url = "https://mvn.devos.one/releases")
maven(url = "https://maven.wispforest.io")
maven(url = "https://jitpack.io/")
mavenCentral()
exclusiveContent {
Expand All @@ -47,24 +67,28 @@ allprojects {
all {
exclude(group = "org.ow2.asm", module = "asm-debug-all")
exclude(group = "org.ow2.asm", module = "asm-all")
exclude(group = "babric")
// Force correct Guava version to avoid conflicts
resolutionStrategy {
force("com.google.guava:guava:31.1-jre")
}
}
}

dependencies {
implementation("org.slf4j:slf4j-api:1.8.0-beta4")
implementation("org.apache.logging.log4j:log4j-slf4j18-impl:2.17.2")

implementation("org.apache.logging.log4j:log4j-core:2.17.2")
implementation("com.google.guava:guava:33.2.1-jre")
implementation("org.apache.logging.log4j:log4j-core:2.17.2") {
exclude(group = "com.google.guava", module = "guava")
}
implementation("net.ornithemc:logger-config:1.0.0") {
exclude(group = "com.google.guava", module = "guava")
}
implementation("com.google.guava:guava:31.1-jre")
implementation("com.google.code.gson:gson:2.9.0")

//to change the versions see the gradle.properties file
minecraft("com.mojang:minecraft:${project.properties["minecraft_version"]}")

mappings("net.glasslauncher:biny:${project.properties["yarn_mappings"]}:v2")

modImplementation("net.fabricmc:fabric-loader:${project.properties["loader_version"]}")
//minecraft and mappings are added in the ploceus withPlugin block above

"transitiveImplementation"(implementation("org.apache.commons:commons-lang3:3.12.0") as Dependency)
"transitiveImplementation"(implementation("commons-io:commons-io:2.11.0") as Dependency)
Expand All @@ -77,7 +101,7 @@ allprojects {
"transitiveImplementation"(implementation("me.carleslc:Simple-Yaml:1.8.4") as Dependency)

// not a runtime dependency unless we use something outside its events.
modImplementation("net.glasslauncher.mods:GlassConfigAPI:${project.properties["gcapi_version"]}")
modImplementation("net.glasslauncher.mods:GlassConfigAPI:${project.properties["gcapi_version"]}+gen2")

// convenience stuff
// adds some useful annotations for data classes. does not add any dependencies
Expand All @@ -89,15 +113,16 @@ allprojects {
// adds some useful annotations for miscellaneous uses. does not add any dependencies, though people without the lib will be missing some useful context hints.
implementation("org.jetbrains:annotations:23.0.0")

modLocalRuntime("net.glasslauncher.mods:ModMenu:${project.properties["modmenu_version"]}")
modLocalRuntime("maven.modrinth:retrocommands:${project.properties["rc_version"]}") {
isTransitive = false
}
// modLocalRuntime("net.glasslauncher.mods:ModMenu:${project.properties["modmenu_version"]}")
// modLocalRuntime("maven.modrinth:retrocommands:${project.properties["rc_version"]}") {
// isTransitive = false
// }

annotationProcessor("io.github.llamalad7:mixinextras-fabric:0.4.1")

// Optional bugfix mod for testing qol. Remove the // to enable.
//modLocalRuntime "maven.modrinth:mojangfix:${project.properties["mojangfix_version"]}"

}

sourceSets {
Expand Down Expand Up @@ -255,6 +280,8 @@ dependencies {
include("com.github.ben-manes.caffeine:caffeine:${project.properties["caffeine_version"]}")
include("com.mojang:datafixerupper:${project.properties["dfu_version"]}")
include("maven.modrinth:spasm:${project.properties["spasm_version"]}")
include("com.google.guava:guava:31.1-jre")
include("org.apache.commons:commons-lang3:3.12.0")
}

// Makes java shut up
Expand All @@ -264,6 +291,11 @@ configure<JavaCompile>("compileTestJava") {
options.forkOptions.executable = System.getProperty("java.home") + "/bin/javac" + (if (System.getProperty("os.name").startsWith("Windows")) ".exe" else "")
}

// Don't fail test task when no tests are discovered (these are mod test classes, not unit tests)
tasks.withType<Test> {
failOnNoDiscoveredTests = false
}

publishing {
publications {
getByName("mavenJava", MavenPublication::class) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,7 @@
package net.fabricmc.loom.util;

import groovy.util.Node;
import groovy.xml.QName;
import groovy.namespace.QName;

public final class GroovyXmlUtil {
private GroovyXmlUtil() { }
Expand All @@ -49,11 +49,6 @@ private static boolean isSameName(Object nodeName, String givenName) {
return qName.matches(givenName);
}

// New groovy 3 (gradle 7) class
if (nodeName instanceof groovy.namespace.QName qName) {
return qName.matches(givenName);
}

throw new UnsupportedOperationException("Cannot determine if " + nodeName.getClass() + " is the same as a String");
}
}
10 changes: 8 additions & 2 deletions gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -10,9 +10,15 @@ fabric.loom.multiProjectOptimisation=true
# Fabric Properties
# check these on https://fabricmc.net/use
minecraft_version = b1.7.3
yarn_mappings = b1.7.3+e1fe071
biny_mappings = 9859f76
loader_version = 0.16.9

# Ploceus Properties
client_raven_build = 2
server_raven_build = 2
client_sparrow_build = 2
server_sparrow_build = 2

# Library Properties
typetools_version = 0.8.3
unsafeevents_version = e31096e
Expand All @@ -27,6 +33,6 @@ fabric.loom.multiProjectOptimisation=true
archives_base_name = StationAPI

# Test properties
gcapi_version = 3.2.5
gcapi_version = 3.3.0
modmenu_version = 1.8.5-beta.11
rc_version = 0.5.4
2 changes: 1 addition & 1 deletion gradle/wrapper/gradle-wrapper.properties
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
distributionUrl=https\://services.gradle.org/distributions/gradle-8.12.1-bin.zip
distributionUrl=https\://services.gradle.org/distributions/gradle-9.3.0-bin.zip
networkTimeout=10000
validateDistributionUrl=true
zipStoreBase=GRADLE_USER_HOME
Expand Down
17 changes: 13 additions & 4 deletions settings.gradle.kts
Original file line number Diff line number Diff line change
@@ -1,9 +1,18 @@
pluginManagement {
repositories {
maven(url = "https://maven.glass-launcher.net/babric")
maven(url = "https://maven.fabricmc.net/")
maven(url = "https://jitpack.io/")
mavenCentral()
maven {
name = "Fabric"
url = uri("https://maven.fabricmc.net/")
}
maven {
name = "Ornithe Releases"
url = uri("https://maven.ornithemc.net/releases")
}
maven {
name = "Ornithe Snapshots"
url = uri("https://maven.ornithemc.net/snapshots")
}
mavenLocal()
gradlePluginPortal()
}
}
Expand Down
2 changes: 1 addition & 1 deletion src/main/resources/fabric.mod.json
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
"environment": "*",

"depends": {
"java": ">=17",
"java": ">=21",
"fabricloader": "*",
"minecraft": "1.0.0-beta.7.3",
"station-api-configuration": "*",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@

@Mixin(World.class)
public abstract class MixinLevel {
@Shadow public abstract BiomeSource method_1781();
@Shadow public abstract BiomeSource getBiomeSource();

/*@Inject(
method = "<init>(Lnet/minecraft/level/dimension/DimensionData;Ljava/lang/String;J)V",
Expand All @@ -27,7 +27,7 @@ private void onInit(WorldStorage string, String l, long par3, CallbackInfo ci) {
int[] pixels = ((DataBufferInt) buffer.getRaster().getDataBuffer()).getData();

int start = -(side >> 1);
BiomeSource biomeSource = method_1781();
BiomeSource biomeSource = getBiomeSource();
Biome[] biomes = biomeSource.getBiomesInArea(new Biome[side * side], start, start, side, side);

for (int i = 0; i < pixels.length; i++) {
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
package net.modificationstation.stationapi.impl.recipe;

import java.util.Comparator;

/**
* Fixed comparator that properly implements the comparison contract.
* Sorts recipes with shaped recipes first, then by size (smaller first).
*
* This fixes the buggy comparator in CraftingRecipeManager that violates
* the general contract and causes IllegalArgumentException in Java 17+.
*/
public class CraftingRecipeComparator implements Comparator {
@Override
public int compare(Object o1, Object o2) {
if (o1 == o2) return 0;

try {
// Get class names to determine recipe type
String o1Class = o1.getClass().getSimpleName();
String o2Class = o2.getClass().getSimpleName();

// Determine recipe types
boolean o1Shapeless = o1Class.contains("Shapeless");
boolean o2Shapeless = o2Class.contains("Shapeless");

// Different types: Shaped comes before Shapeless
if (o1Shapeless != o2Shapeless) {
return o1Shapeless ? 1 : -1;
}

// Same type: compare by size (smaller first)
try {
int o1Size = (Integer) o1.getClass().getMethod("getSize").invoke(o1);
int o2Size = (Integer) o2.getClass().getMethod("getSize").invoke(o2);
return Integer.compare(o1Size, o2Size);
} catch (Exception e) {
// If we can't get sizes, maintain order
return 0;
}
} catch (Exception e) {
// Fallback: maintain original order
return 0;
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
package net.modificationstation.stationapi.mixin;

import java.util.Collections;
import java.util.Comparator;
import java.util.List;

import net.minecraft.recipe.CraftingRecipe;
import net.modificationstation.stationapi.impl.recipe.CraftingRecipeComparator;
import org.spongepowered.asm.mixin.Mixin;
import org.spongepowered.asm.mixin.Shadow;
import org.spongepowered.asm.mixin.injection.At;
import org.spongepowered.asm.mixin.injection.Redirect;

@Mixin(targets = "net.minecraft.recipe.CraftingRecipeManager")
public class CraftingRecipeManagerMixin {
@Shadow
private List recipes;

@Redirect(method = "<init>", at = @At(value = "INVOKE", target = "Ljava/util/Collections;sort(Ljava/util/List;Ljava/util/Comparator;)V"))
void resort(List<CraftingRecipe> list, Comparator<? super CraftingRecipe> c) {
// Skip the buggy sort and use our fixed comparator instead
Collections.sort(this.recipes, new CraftingRecipeComparator());
}
}
3 changes: 3 additions & 0 deletions station-api-base/src/main/resources/fabric.mod.json
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,9 @@
"icon": "assets/station-api-base/icon.png",

"environment": "*",
"mixins": [
"station-api-base.mixins.json"
],
"entrypoints": {
"preLaunch": [
"net.modificationstation.stationapi.api.StationAPI"
Expand Down
11 changes: 11 additions & 0 deletions station-api-base/src/main/resources/station-api-base.mixins.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
{
"required": true,
"minVersion": "0.8",
"package": "net.modificationstation.stationapi.mixin",
"compatibilityLevel": "JAVA_17",
"mixins": [
],
"injectors": {
"defaultRequire": 1
}
}
7 changes: 1 addition & 6 deletions station-blockitems-v0/src/main/resources/fabric.mod.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,6 @@
"schemaVersion": 1,
"id": "station-blockitems-v0",
"version": "${version}",

"name": "Station BlockItems (v0)",
"description": "API for custom block items.",
"authors": [
Expand All @@ -13,10 +12,8 @@
"sources": "https://github.com/ModificationStation/StationAPI",
"issues": "https://github.com/ModificationStation/StationAPI/issues"
},

"license": "MIT",
"icon": "assets/station-blockitems-v0/icon.png",

"environment": "*",
"entrypoints": {
"stationapi:event_bus": [
Expand All @@ -29,16 +26,14 @@
"mixins": [
"station-blockitems-v0.mixins.json"
],

"depends": {
"fabricloader": "*",
"minecraft": "1.0.0-beta.7.3"
},

"custom": {
"modmenu:api": true,
"loom:injected_interfaces": {
"net/minecraft/class_17": [
"net/minecraft/unmapped/C_81592558": [
"net/modificationstation/stationapi/api/block/StationBlockItemsBlock"
]
}
Expand Down
Loading