mirror of
https://github.com/architectury/architectury-loom.git
synced 2026-03-28 04:07:01 -05:00
RenderDoc tasks (#1291)
* First pass on renderdoc support * Fixes and improvements * Fix debugging/cleaner code. * Download from fabric maven * Fix build * Revert changes to AbstractRunTask
This commit is contained in:
2
.github/workflows/publish-exp.yml
vendored
2
.github/workflows/publish-exp.yml
vendored
@@ -17,7 +17,7 @@ jobs:
|
||||
java-version: 21
|
||||
distribution: 'temurin'
|
||||
- uses: actions/checkout@v4
|
||||
- uses: gradle/wrapper-validation-action@v2
|
||||
- uses: gradle/actions/wrapper-validation@v4
|
||||
|
||||
# Generate the build number based on tags to allow per branch build numbers, not something github provides by default.
|
||||
- name: Generate build number
|
||||
|
||||
2
.github/workflows/publish.yml
vendored
2
.github/workflows/publish.yml
vendored
@@ -17,7 +17,7 @@ jobs:
|
||||
java-version: 21
|
||||
distribution: 'temurin'
|
||||
- uses: actions/checkout@v4
|
||||
- uses: gradle/wrapper-validation-action@v2
|
||||
- uses: gradle/actions/wrapper-validation@v4
|
||||
|
||||
# Generate the build number based on tags to allow per branch build numbers, not something github provides by default.
|
||||
- name: Generate build number
|
||||
|
||||
4
.github/workflows/test-push.yml
vendored
4
.github/workflows/test-push.yml
vendored
@@ -27,7 +27,7 @@ jobs:
|
||||
java-version: 21
|
||||
distribution: 'temurin'
|
||||
- uses: actions/checkout@v4
|
||||
- uses: gradle/wrapper-validation-action@v2
|
||||
- uses: gradle/actions/wrapper-validation@v4
|
||||
- run: ./gradlew build check -x test --stacktrace --warning-mode fail
|
||||
|
||||
build_windows:
|
||||
@@ -41,7 +41,7 @@ jobs:
|
||||
with:
|
||||
java-version: 21
|
||||
distribution: 'temurin'
|
||||
- uses: gradle/wrapper-validation-action@v2
|
||||
- uses: gradle/actions/wrapper-validation@v4
|
||||
- run: ./gradlew build check -x test --stacktrace --warning-mode fail
|
||||
|
||||
# This job is used to feed the test matrix of next job to allow the tests to run in parallel
|
||||
|
||||
@@ -12,6 +12,9 @@ jetbrains-annotations = "26.0.2"
|
||||
native-support = "1.0.1"
|
||||
fabric-installer = "1.0.3"
|
||||
|
||||
# Debug tools
|
||||
renderdoc = "1.37"
|
||||
|
||||
[libraries]
|
||||
# Decompilers
|
||||
fernflower = { module = "net.fabricmc:fabric-fernflower", version.ref = "fernflower" }
|
||||
@@ -24,4 +27,7 @@ dev-launch-injector = { module = "net.fabricmc:dev-launch-injector", version.ref
|
||||
terminal-console-appender = { module = "net.minecrell:terminalconsoleappender", version.ref = "terminal-console-appender" }
|
||||
jetbrains-annotations = { module = "org.jetbrains:annotations", version.ref = "jetbrains-annotations" }
|
||||
native-support = { module = "net.fabricmc:fabric-loom-native-support", version.ref = "native-support" }
|
||||
fabric-installer = { module = "net.fabricmc:fabric-installer", version.ref = "fabric-installer" }
|
||||
fabric-installer = { module = "net.fabricmc:fabric-installer", version.ref = "fabric-installer" }
|
||||
|
||||
# Debug tools
|
||||
renderdoc = { module = "org.renderdoc:renderdoc", version.ref = "renderdoc" } # Not a maven dependency
|
||||
@@ -24,13 +24,18 @@
|
||||
|
||||
package net.fabricmc.loom.task;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
import javax.inject.Inject;
|
||||
|
||||
import com.google.common.base.Preconditions;
|
||||
import org.gradle.api.Project;
|
||||
import org.gradle.api.Task;
|
||||
import org.gradle.api.file.FileCollection;
|
||||
import org.gradle.api.provider.Provider;
|
||||
import org.gradle.api.tasks.Sync;
|
||||
import org.gradle.api.tasks.TaskContainer;
|
||||
import org.gradle.api.tasks.TaskOutputs;
|
||||
import org.gradle.api.tasks.TaskProvider;
|
||||
|
||||
import net.fabricmc.loom.LoomGradleExtension;
|
||||
@@ -41,6 +46,8 @@ import net.fabricmc.loom.task.launch.GenerateDLIConfigTask;
|
||||
import net.fabricmc.loom.task.launch.GenerateLog4jConfigTask;
|
||||
import net.fabricmc.loom.task.launch.GenerateRemapClasspathTask;
|
||||
import net.fabricmc.loom.util.Constants;
|
||||
import net.fabricmc.loom.util.LoomVersions;
|
||||
import net.fabricmc.loom.util.Platform;
|
||||
import net.fabricmc.loom.util.gradle.GradleUtils;
|
||||
|
||||
public abstract class LoomTasks implements Runnable {
|
||||
@@ -132,17 +139,28 @@ public abstract class LoomTasks implements Runnable {
|
||||
|
||||
private void registerRunTasks() {
|
||||
LoomGradleExtension extension = LoomGradleExtension.get(getProject());
|
||||
final boolean renderDocSupported = RenderDocRunTask.isSupported(Platform.CURRENT);
|
||||
|
||||
Preconditions.checkArgument(extension.getRunConfigs().size() == 0, "Run configurations must not be registered before loom");
|
||||
|
||||
extension.getRunConfigs().whenObjectAdded(config -> {
|
||||
getTasks().register(getRunConfigTaskName(config), RunGameTask.class, config).configure(t -> {
|
||||
var runTask = getTasks().register(getRunConfigTaskName(config), RunGameTask.class, config);
|
||||
|
||||
runTask.configure(t -> {
|
||||
t.setDescription("Starts the '" + config.getConfigName() + "' run configuration");
|
||||
|
||||
t.dependsOn(config.getEnvironment().equals("client") ? "configureClientLaunch" : "configureLaunch");
|
||||
});
|
||||
|
||||
if (config.getName().equals("client") && renderDocSupported) {
|
||||
getTasks().register("runClientRenderDoc", RenderDocRunTask.class, config);
|
||||
}
|
||||
});
|
||||
|
||||
if (renderDocSupported) {
|
||||
configureRenderDocTasks();
|
||||
}
|
||||
|
||||
extension.getRunConfigs().whenObjectRemoved(runConfigSettings -> {
|
||||
getTasks().named(getRunConfigTaskName(runConfigSettings), task -> {
|
||||
// Disable the task so it can't be run
|
||||
@@ -170,7 +188,58 @@ public abstract class LoomTasks implements Runnable {
|
||||
return;
|
||||
}
|
||||
|
||||
extension.getRunConfigs().removeIf(settings -> settings.getName().equals(taskName));
|
||||
extension.getRunConfigs().removeIf(settings -> settings.getName().equals(taskName)
|
||||
|| settings.getName().equals(taskName + "RenderDoc"));
|
||||
});
|
||||
}
|
||||
|
||||
private void configureRenderDocTasks() {
|
||||
final Platform.OperatingSystem operatingSystem = Platform.CURRENT.getOperatingSystem();
|
||||
final String renderDocVersion = LoomVersions.RENDERDOC.version();
|
||||
final String renderDocBaseName = operatingSystem.isWindows()
|
||||
? "RenderDoc_%s_64".formatted(renderDocVersion)
|
||||
: "renderdoc_%s".formatted(renderDocVersion);
|
||||
final String renderDocFilename = operatingSystem.isWindows()
|
||||
? "%s.zip".formatted(renderDocBaseName)
|
||||
: "%s.tar.gz".formatted(renderDocBaseName);
|
||||
final String renderDocUrl = "https://maven.fabricmc.net/org/renderdoc/%s".formatted(renderDocFilename);
|
||||
final String executableExt = operatingSystem.isWindows() ? ".exe" : "";
|
||||
|
||||
var downloadRenderDoc = getTasks().register("downloadRenderDoc", DownloadTask.class, task -> {
|
||||
task.setGroup(Constants.TaskGroup.FABRIC);
|
||||
|
||||
task.getUrl().set(renderDocUrl);
|
||||
task.getOutput().set(getProject().getLayout().getBuildDirectory().file(renderDocFilename));
|
||||
});
|
||||
|
||||
var extractRenderDoc = getTasks().register("extractRenderDoc", Sync.class, task -> {
|
||||
task.setGroup(Constants.TaskGroup.FABRIC);
|
||||
|
||||
if (operatingSystem.isWindows()) {
|
||||
task.from(getProject().zipTree(downloadRenderDoc.map(DownloadTask::getOutput)));
|
||||
} else {
|
||||
task.from(getProject().tarTree(downloadRenderDoc.map(DownloadTask::getOutput)));
|
||||
}
|
||||
|
||||
task.into(getProject().getLayout().getBuildDirectory().dir("renderdoc"));
|
||||
});
|
||||
|
||||
Provider<File> renderDocDir = extractRenderDoc.map(Sync::getOutputs)
|
||||
.map(TaskOutputs::getFiles)
|
||||
.map(FileCollection::getSingleFile)
|
||||
.map(dir -> new File(dir, renderDocBaseName));
|
||||
|
||||
if (operatingSystem.isLinux()) {
|
||||
renderDocDir = renderDocDir.map(dir -> new File(dir, "bin"));
|
||||
}
|
||||
|
||||
Provider<File> renderDocCMD = renderDocDir.map(dir -> new File(dir, "renderdoccmd" + executableExt));
|
||||
Provider<File> renderDocUI = renderDocDir.map(dir -> new File(dir, "qrenderdoc" + executableExt));
|
||||
|
||||
getTasks().register("startRenderDocUI", RenderDocRunUITask.class, task -> task.getRenderDocExecutable().fileProvider(renderDocUI));
|
||||
|
||||
getTasks().withType(RenderDocRunTask.class).configureEach(task -> {
|
||||
task.getRenderDocExecutable().fileProvider(renderDocCMD);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
92
src/main/java/net/fabricmc/loom/task/RenderDocRunTask.java
Normal file
92
src/main/java/net/fabricmc/loom/task/RenderDocRunTask.java
Normal file
@@ -0,0 +1,92 @@
|
||||
/*
|
||||
* This file is part of fabric-loom, licensed under the MIT License (MIT).
|
||||
*
|
||||
* Copyright (c) 2025 FabricMC
|
||||
*
|
||||
* 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 net.fabricmc.loom.task;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
import javax.inject.Inject;
|
||||
|
||||
import org.gradle.api.file.RegularFileProperty;
|
||||
import org.gradle.api.provider.ListProperty;
|
||||
import org.gradle.api.tasks.Input;
|
||||
import org.gradle.api.tasks.InputFile;
|
||||
import org.gradle.process.CommandLineArgumentProvider;
|
||||
import org.gradle.process.ExecOperations;
|
||||
import org.gradle.process.ExecResult;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import net.fabricmc.loom.configuration.ide.RunConfigSettings;
|
||||
import net.fabricmc.loom.util.Constants;
|
||||
import net.fabricmc.loom.util.Platform;
|
||||
|
||||
public abstract class RenderDocRunTask extends RunGameTask {
|
||||
private static final Logger LOGGER = LoggerFactory.getLogger(RenderDocRunTask.class);
|
||||
|
||||
@InputFile
|
||||
public abstract RegularFileProperty getRenderDocExecutable();
|
||||
|
||||
@Input
|
||||
public abstract ListProperty<String> getRenderDocArgs();
|
||||
|
||||
@Inject
|
||||
protected abstract ExecOperations getExecOperations();
|
||||
|
||||
@Inject
|
||||
public RenderDocRunTask(RunConfigSettings settings) {
|
||||
super(settings);
|
||||
setGroup(Constants.TaskGroup.FABRIC);
|
||||
dependsOn("configureClientLaunch");
|
||||
getRenderDocArgs().addAll("capture", "--wait-for-exit", "--working-dir", getWorkingDir().getAbsolutePath());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void exec() {
|
||||
ExecResult result = getExecOperations().exec(exec -> {
|
||||
exec.workingDir(new File(getProjectDir().get(), getInternalRunDir().get()));
|
||||
exec.environment(getInternalEnvironmentVars().get());
|
||||
|
||||
exec.commandLine(getRenderDocExecutable().get().getAsFile());
|
||||
exec.args(getRenderDocArgs().get());
|
||||
exec.args(getJavaLauncher().get().getExecutablePath());
|
||||
exec.args(getJvmArgs());
|
||||
exec.args(getMainClass().get());
|
||||
|
||||
for (CommandLineArgumentProvider provider : getArgumentProviders()) {
|
||||
exec.args(provider.asArguments());
|
||||
}
|
||||
|
||||
LOGGER.info("Running command: {}", exec.getCommandLine());
|
||||
});
|
||||
result.assertNormalExitValue();
|
||||
}
|
||||
|
||||
public static boolean isSupported(Platform platform) {
|
||||
final Platform.OperatingSystem os = platform.getOperatingSystem();
|
||||
final Platform.Architecture arch = platform.getArchitecture();
|
||||
// RenderDoc does support 32-bit Windows, but I cannot be bothered to test/maintain it
|
||||
return (os.isLinux() || os.isWindows()) && arch.isX64();
|
||||
}
|
||||
}
|
||||
51
src/main/java/net/fabricmc/loom/task/RenderDocRunUITask.java
Normal file
51
src/main/java/net/fabricmc/loom/task/RenderDocRunUITask.java
Normal file
@@ -0,0 +1,51 @@
|
||||
/*
|
||||
* This file is part of fabric-loom, licensed under the MIT License (MIT).
|
||||
*
|
||||
* Copyright (c) 2025 FabricMC
|
||||
*
|
||||
* 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 net.fabricmc.loom.task;
|
||||
|
||||
import java.io.IOException;
|
||||
|
||||
import org.gradle.api.DefaultTask;
|
||||
import org.gradle.api.file.RegularFileProperty;
|
||||
import org.gradle.api.tasks.InputFile;
|
||||
import org.gradle.api.tasks.TaskAction;
|
||||
|
||||
import net.fabricmc.loom.util.Constants;
|
||||
|
||||
public abstract class RenderDocRunUITask extends DefaultTask {
|
||||
@InputFile
|
||||
public abstract RegularFileProperty getRenderDocExecutable();
|
||||
|
||||
public RenderDocRunUITask() {
|
||||
setGroup(Constants.TaskGroup.FABRIC);
|
||||
}
|
||||
|
||||
@TaskAction
|
||||
public void run() throws IOException {
|
||||
ProcessBuilder builder = new ProcessBuilder()
|
||||
.command(getRenderDocExecutable().getAsFile().get().getAbsolutePath());
|
||||
builder.start();
|
||||
// Allow to run in the background.
|
||||
}
|
||||
}
|
||||
@@ -53,6 +53,10 @@ public interface Platform {
|
||||
boolean isArm();
|
||||
|
||||
boolean isRiscV();
|
||||
|
||||
default boolean isX64() {
|
||||
return is64Bit() && !isArm() && !isRiscV();
|
||||
}
|
||||
}
|
||||
|
||||
Architecture getArchitecture();
|
||||
|
||||
Reference in New Issue
Block a user