Files
saturnclient/stonecutter.gradle.kts
T
selimaj-devandclaude 46c7bacd04
Check / compile (pull_request) Successful in 16m19s
Build for Minecraft 26.3
Adds 26.3 as a Stonecutter version, the last step of #39.

Input: 26.3 replaces GLFW with SDL, which numbers keys (scancodes),
modifiers and mouse buttons differently. Saturn keeps GLFW's numbers,
which common uses and the config's keybinds store, so saved keybinds
stay valid. The new Keys class converts at the boundary: key events,
modifiers and mouse buttons coming into Saturn's screens, and key codes
going to InputConstants. Its table pairs GLFW's codes with 26.3's
InputConstants of the same name. Key names come from the game on 26.3,
and version-specific code uses InputConstants' key constants rather
than GLFW's.

Rendering: Blaze3D's API moved to renderpearl, which Stonecutter
replacements cover. PoseStack's quaternion mulPose became rotate, and
TextureTarget takes a depth format instead of a flag. 26.3 compiles
shaders through SPIR-V and reorders the transforms block, so glass.fsh
takes explicit locations and the new order behind defines that
GlassRenderer sets, and the unlit cosmetics pipeline declares its
color target, which 26.3 requires.

OptionsScreen no longer takes whether a world is open.

Co-Authored-By: Claude Opus 5.5 <[email protected]>
2026-09-30 22:12:50 +02:00

102 lines
4.1 KiB
Kotlin

plugins {
id("dev.kikugie.stonecutter")
}
// The version whose code is uncommented in src/. Switch with "Set active project to <v>", and run
// "Reset active project" before committing.
stonecutter active "1.21.11"
// src/ uses 1.21.11's Mojang names (the active version). These names changed in the versions given,
// so Stonecutter swaps in each version's name when it processes it.
stonecutter parameters {
for ((since, old, new) in listOf(
Triple("1.21.11", "ResourceLocation", "Identifier"),
Triple("1.21.9", "PlayerRenderer", "AvatarRenderer"),
Triple("1.21.9", "PlayerRenderState", "AvatarRenderState"),
Triple("26.1", "GuiGraphics", "GuiGraphicsExtractor"),
Triple("26.1", "net.minecraft.client.gui.render.state", "net.minecraft.client.renderer.state.gui"),
// GuiRenderState's methods
Triple("26.1", "submitGuiElement", "addGuiElement"),
Triple("26.1", "submitText", "addText"),
Triple("26.1", "submitItem", "addItem"),
Triple("26.1", "submitPicturesInPictureState", "addPicturesInPictureState"),
// 26.3 moves Blaze3D's API to renderpearl
Triple("26.3", "com.mojang.blaze3d.GpuFormat", "com.mojang.renderpearl.api.GpuFormat"),
Triple("26.3", "com.mojang.blaze3d.pipeline.RenderPipeline", "com.mojang.renderpearl.api.pipeline.RenderPipeline"),
Triple("26.3", "com.mojang.blaze3d.textures", "com.mojang.renderpearl.api.textures"),
)) {
replacements.regex(eval(current.version, ">=$since")) {
replace("\\b${Regex.escape(old)}\\b", new, "\\b${Regex.escape(new)}\\b", old)
}
}
}
subprojects {
apply(plugin = "java")
repositories {
maven("https://maven.fabricmc.net/")
maven("https://git.selimaj.dev/api/packages/selimaj-dev/maven")
maven("https://git.selimaj.dev/api/packages/saturnclientmc/maven")
mavenCentral()
}
dependencies {
"implementation"("de.javagl:obj:0.4.0")
"implementation"("com.formdev:svgSalamander:1.1.4")
"implementation"("com.fasterxml.jackson.core:jackson-databind:2.17.0")
"implementation"("com.fasterxml.jackson.core:jackson-annotations:2.17.0")
"implementation"("com.fasterxml.jackson.core:jackson-core:2.17.0")
}
}
// Every Minecraft version builds on common and ships its resources.
configure(subprojects.filter { it.name != "common" }) {
dependencies {
"implementation"(project(":common"))
}
extensions.configure<SourceSetContainer> {
named("main") {
resources.srcDir(project(":common").file("src/main/resources"))
}
}
}
// remapJar loads a whole Minecraft classpath and remaps a ~50 MB jar. Eight at once don't fit in the
// daemon's heap (org.gradle.jvmargs) and the build stalls in garbage collection, so only two run
// together. Everything else still builds in parallel.
abstract class RemapLimit : BuildService<BuildServiceParameters.None>
val remapLimit = gradle.sharedServices.registerIfAbsent("remapLimit", RemapLimit::class) {
maxParallelUsages = 2
}
subprojects {
tasks.matching { it.name == "remapJar" }.configureEach {
usesService(remapLimit)
}
}
tasks.register("buildAll") {
group = "build"
description = "Builds every Minecraft version's mod jar and collects them in build/allJars"
// The mod jar is remapJar's output for 1.21.x, and jar's for 26.1+, which isn't obfuscated.
val modJars = subprojects.filter { it.name != "common" }.flatMap { project ->
val unobfuscated = project.name.substringBefore('.').toInt() >= 26
val task = if (unobfuscated) "jar" else "remapJar"
project.tasks.matching { it.name == task }
}
dependsOn(modJars)
doLast {
val outputDir = layout.buildDirectory.dir("allJars").get().asFile
outputDir.mkdirs()
modJars.map { (it as AbstractArchiveTask).archiveFile.get().asFile }
.filter { it.exists() && !it.name.contains("sources") }
.forEach { it.copyTo(outputDir.resolve(it.name), overwrite = true) }
println("All mod jars collected in: $outputDir")
}
}