From b5ea5f561e2b5af2aaecbcc884a5efd3b9664a0b Mon Sep 17 00:00:00 2001 From: PepperCode1 <44146161+PepperCode1@users.noreply.github.com> Date: Tue, 12 Jul 2022 14:44:31 -0700 Subject: [PATCH 01/11] Port to 1.19 (mostly) - BufferBuilder manipulation code has not been ported --- build.gradle | 6 +- gradle.properties | 6 +- .../java/com/jozufozu/flywheel/Flywheel.java | 15 +++-- .../com/jozufozu/flywheel/backend/Loader.java | 14 ++--- .../flywheel/config/BackendTypeArgument.java | 4 +- .../jozufozu/flywheel/config/FlwCommands.java | 18 +++--- .../jozufozu/flywheel/core/PartialModel.java | 16 +++--- .../core/model/BakedModelBuilder.java | 8 +-- .../flywheel/core/model/Bufferable.java | 5 +- .../flywheel/core/model/ModelUtil.java | 9 ++- .../core/model/WorldModelBuilder.java | 27 ++++----- .../flywheel/core/source/ShaderSources.java | 17 +++--- .../flywheel/core/virtual/VirtualChunk.java | 55 ++++++++++++++++--- .../core/virtual/VirtualEmptyModelData.java | 34 ------------ .../core/virtual/VirtualRenderWorld.java | 15 ++++- .../flywheel/event/EntityWorldHandler.java | 12 ++-- .../jozufozu/flywheel/event/ForgeEvents.java | 12 ++-- .../jozufozu/flywheel/util/RenderMath.java | 6 +- 18 files changed, 144 insertions(+), 135 deletions(-) delete mode 100644 src/main/java/com/jozufozu/flywheel/core/virtual/VirtualEmptyModelData.java diff --git a/build.gradle b/build.gradle index 341b6b0e2..76127e48b 100644 --- a/build.gradle +++ b/build.gradle @@ -34,8 +34,8 @@ java.toolchain.languageVersion = JavaLanguageVersion.of(17) println('Java: ' + System.getProperty('java.version') + ' JVM: ' + System.getProperty('java.vm.version') + '(' + System.getProperty('java.vendor') + ') Arch: ' + System.getProperty('os.arch')) minecraft { - mappings channel: 'parchment', version: "${parchment_version}-${minecraft_version}" - +// mappings channel: 'parchment', version: "${parchment_version}-${minecraft_version}" + mappings channel: 'official', version: "${minecraft_version}" runs { client { @@ -199,6 +199,6 @@ curseforge { changelog = file('changelog.txt') releaseType = project.curse_type mainArtifact jar - addGameVersion '1.18.2' + addGameVersion '1.19' } } diff --git a/gradle.properties b/gradle.properties index 42e95d776..225f270f2 100644 --- a/gradle.properties +++ b/gradle.properties @@ -3,9 +3,9 @@ org.gradle.daemon = false # mod version info mod_version = 0.6.4 -mc_update_version = 1.18 -minecraft_version = 1.18.2 -forge_version = 40.1.60 +mc_update_version = 1.19 +minecraft_version = 1.19 +forge_version = 41.0.94 # build dependency versions forgegradle_version = 5.1.+ diff --git a/src/main/java/com/jozufozu/flywheel/Flywheel.java b/src/main/java/com/jozufozu/flywheel/Flywheel.java index be8be85d0..7a186371b 100644 --- a/src/main/java/com/jozufozu/flywheel/Flywheel.java +++ b/src/main/java/com/jozufozu/flywheel/Flywheel.java @@ -17,8 +17,9 @@ import com.jozufozu.flywheel.mixin.PausedPartialTickAccessor; import com.jozufozu.flywheel.vanilla.VanillaInstances; import com.mojang.logging.LogUtils; -import net.minecraft.commands.synchronization.ArgumentTypes; -import net.minecraft.commands.synchronization.EmptyArgumentSerializer; +import net.minecraft.commands.synchronization.ArgumentTypeInfos; +import net.minecraft.commands.synchronization.SingletonArgumentInfo; +import net.minecraft.core.Registry; import net.minecraft.resources.ResourceLocation; import net.minecraftforge.api.distmarker.Dist; import net.minecraftforge.common.MinecraftForge; @@ -28,9 +29,9 @@ import net.minecraftforge.fml.DistExecutor; import net.minecraftforge.fml.IExtensionPoint; import net.minecraftforge.fml.ModLoadingContext; import net.minecraftforge.fml.common.Mod; -import net.minecraftforge.fml.event.lifecycle.FMLCommonSetupEvent; import net.minecraftforge.fml.javafmlmod.FMLJavaModLoadingContext; import net.minecraftforge.network.NetworkConstants; +import net.minecraftforge.registries.RegisterEvent; @Mod(Flywheel.ID) public class Flywheel { @@ -50,7 +51,7 @@ public class Flywheel { IEventBus forgeEventBus = MinecraftForge.EVENT_BUS; IEventBus modEventBus = FMLJavaModLoadingContext.get() .getModEventBus(); - modEventBus.addListener(Flywheel::setup); + modEventBus.addListener(Flywheel::registerArgumentTypes); FlwConfig.init(); @@ -87,8 +88,10 @@ public class Flywheel { LOGGER.debug("Successfully loaded {}", PausedPartialTickAccessor.class.getName()); } - private static void setup(final FMLCommonSetupEvent event) { - ArgumentTypes.register(rl("engine").toString(), BackendTypeArgument.class, new EmptyArgumentSerializer<>(BackendTypeArgument::getInstance)); + private static void registerArgumentTypes(RegisterEvent event) { + event.register(Registry.COMMAND_ARGUMENT_TYPE_REGISTRY, rl("engine"), () -> { + return ArgumentTypeInfos.registerByClass(BackendTypeArgument.class, SingletonArgumentInfo.contextFree(BackendTypeArgument::getInstance)); + }); } public static ArtifactVersion getVersion() { diff --git a/src/main/java/com/jozufozu/flywheel/backend/Loader.java b/src/main/java/com/jozufozu/flywheel/backend/Loader.java index 94c3628cf..24a1bf048 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/Loader.java +++ b/src/main/java/com/jozufozu/flywheel/backend/Loader.java @@ -1,6 +1,6 @@ package com.jozufozu.flywheel.backend; -import java.util.Collection; +import java.io.InputStream; import java.util.HashMap; import java.util.Map; @@ -93,13 +93,11 @@ public class Loader implements ResourceManagerReloadListener { private void loadProgramSpecs(ResourceManager manager) { programs.clear(); - Collection programSpecs = manager.listResources(PROGRAM_DIR, s -> s.endsWith(".json")); + Map programSpecs = manager.listResources(PROGRAM_DIR, loc -> loc.getPath().endsWith(".json")); - for (ResourceLocation location : programSpecs) { - try { - Resource file = manager.getResource(location); - - String s = StringUtil.readToString(file.getInputStream()); + programSpecs.forEach((location, resource) -> { + try (InputStream inputStream = resource.open()) { + String s = StringUtil.readToString(inputStream); ResourceLocation specName = ResourceUtil.trim(location, PROGRAM_DIR, ".json"); @@ -119,7 +117,7 @@ public class Loader implements ResourceManagerReloadListener { } catch (Exception e) { Backend.LOGGER.error("Could not load program " + location, e); } - } + }); } } diff --git a/src/main/java/com/jozufozu/flywheel/config/BackendTypeArgument.java b/src/main/java/com/jozufozu/flywheel/config/BackendTypeArgument.java index 7f2545a3a..7187813d8 100644 --- a/src/main/java/com/jozufozu/flywheel/config/BackendTypeArgument.java +++ b/src/main/java/com/jozufozu/flywheel/config/BackendTypeArgument.java @@ -12,14 +12,14 @@ import com.mojang.brigadier.suggestion.Suggestions; import com.mojang.brigadier.suggestion.SuggestionsBuilder; import net.minecraft.commands.SharedSuggestionProvider; -import net.minecraft.network.chat.TranslatableComponent; +import net.minecraft.network.chat.Component; public enum BackendTypeArgument implements ArgumentType { INSTANCE; private static final Dynamic2CommandExceptionType INVALID = new Dynamic2CommandExceptionType((found, constants) -> { // TODO: don't steal lang - return new TranslatableComponent("commands.forge.arguments.enum.invalid", constants, found); + return Component.translatable("commands.forge.arguments.enum.invalid", constants, found); }); @Override diff --git a/src/main/java/com/jozufozu/flywheel/config/FlwCommands.java b/src/main/java/com/jozufozu/flywheel/config/FlwCommands.java index ce0ea95d7..f2e2b9d85 100644 --- a/src/main/java/com/jozufozu/flywheel/config/FlwCommands.java +++ b/src/main/java/com/jozufozu/flywheel/config/FlwCommands.java @@ -16,10 +16,8 @@ import net.minecraft.commands.CommandSourceStack; import net.minecraft.commands.Commands; import net.minecraft.network.chat.Component; import net.minecraft.network.chat.MutableComponent; -import net.minecraft.network.chat.TextComponent; import net.minecraftforge.client.event.RegisterClientCommandsEvent; import net.minecraftforge.common.ForgeConfigSpec.ConfigValue; -import net.minecraftforge.fml.ModList; public class FlwCommands { public static void registerClientCommands(RegisterClientCommandsEvent event) { @@ -56,14 +54,14 @@ public class FlwCommands { LocalPlayer player = Minecraft.getInstance().player; if (player == null) return; - Component text = new TextComponent("Normal debug mode is currently: ").append(boolToText(bool)); + Component text = Component.literal("Normal debug mode is currently: ").append(boolToText(bool)); player.displayClientMessage(text, false); }, (source, bool) -> { LocalPlayer player = Minecraft.getInstance().player; if (player == null) return; - Component text = boolToText(bool).append(new TextComponent(" normal debug mode").withStyle(ChatFormatting.WHITE)); + Component text = boolToText(bool).append(Component.literal(" normal debug mode").withStyle(ChatFormatting.WHITE)); player.displayClientMessage(text, false); } )); @@ -73,14 +71,14 @@ public class FlwCommands { LocalPlayer player = Minecraft.getInstance().player; if (player == null) return; - Component text = new TextComponent("Update limiting is currently: ").append(boolToText(bool)); + Component text = Component.literal("Update limiting is currently: ").append(boolToText(bool)); player.displayClientMessage(text, false); }, (source, bool) -> { LocalPlayer player = Minecraft.getInstance().player; if (player == null) return; - Component text = boolToText(bool).append(new TextComponent(" update limiting.").withStyle(ChatFormatting.WHITE)); + Component text = boolToText(bool).append(Component.literal(" update limiting.").withStyle(ChatFormatting.WHITE)); player.displayClientMessage(text, false); Backend.reloadWorldRenderers(); @@ -111,14 +109,14 @@ public class FlwCommands { } public static MutableComponent boolToText(boolean b) { - return b ? new TextComponent("enabled").withStyle(ChatFormatting.DARK_GREEN) : new TextComponent("disabled").withStyle(ChatFormatting.RED); + return b ? Component.literal("enabled").withStyle(ChatFormatting.DARK_GREEN) : Component.literal("disabled").withStyle(ChatFormatting.RED); } public static Component getEngineMessage(@NotNull BackendType type) { return switch (type) { - case OFF -> new TextComponent("Disabled Flywheel").withStyle(ChatFormatting.RED); - case INSTANCING -> new TextComponent("Using Instancing Engine").withStyle(ChatFormatting.GREEN); - case BATCHING -> new TextComponent("Using Batching Engine").withStyle(ChatFormatting.GREEN); + case OFF -> Component.literal("Disabled Flywheel").withStyle(ChatFormatting.RED); + case INSTANCING -> Component.literal("Using Instancing Engine").withStyle(ChatFormatting.GREEN); + case BATCHING -> Component.literal("Using Batching Engine").withStyle(ChatFormatting.GREEN); }; } diff --git a/src/main/java/com/jozufozu/flywheel/core/PartialModel.java b/src/main/java/com/jozufozu/flywheel/core/PartialModel.java index 6340e8441..526239b48 100644 --- a/src/main/java/com/jozufozu/flywheel/core/PartialModel.java +++ b/src/main/java/com/jozufozu/flywheel/core/PartialModel.java @@ -6,9 +6,7 @@ import java.util.Map; import net.minecraft.client.resources.model.BakedModel; import net.minecraft.resources.ResourceLocation; -import net.minecraftforge.client.event.ModelBakeEvent; -import net.minecraftforge.client.event.ModelRegistryEvent; -import net.minecraftforge.client.model.ForgeModelBakery; +import net.minecraftforge.client.event.ModelEvent; /** * A helper class for loading and accessing json models. @@ -30,23 +28,23 @@ public class PartialModel { protected BakedModel bakedModel; public PartialModel(ResourceLocation modelLocation) { - if (tooLate) throw new RuntimeException("PartialModel '" + modelLocation + "' loaded after ModelRegistryEvent"); + if (tooLate) throw new RuntimeException("PartialModel '" + modelLocation + "' loaded after ModelEvent.RegisterAdditional"); this.modelLocation = modelLocation; ALL.add(this); } - public static void onModelRegistry(ModelRegistryEvent event) { + public static void onModelRegistry(ModelEvent.RegisterAdditional event) { for (PartialModel partial : ALL) - ForgeModelBakery.addSpecialModel(partial.getLocation()); + event.register(partial.getLocation()); tooLate = true; } - public static void onModelBake(ModelBakeEvent event) { - Map modelRegistry = event.getModelRegistry(); + public static void onModelBake(ModelEvent.BakingCompleted event) { + Map models = event.getModels(); for (PartialModel partial : ALL) - partial.set(modelRegistry.get(partial.getLocation())); + partial.set(models.get(partial.getLocation())); } protected void set(BakedModel bakedModel) { diff --git a/src/main/java/com/jozufozu/flywheel/core/model/BakedModelBuilder.java b/src/main/java/com/jozufozu/flywheel/core/model/BakedModelBuilder.java index 70631ebea..404e69b01 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/BakedModelBuilder.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/BakedModelBuilder.java @@ -1,10 +1,7 @@ package com.jozufozu.flywheel.core.model; -import java.util.Random; - import com.jozufozu.flywheel.core.virtual.VirtualEmptyBlockGetter; -import com.jozufozu.flywheel.core.virtual.VirtualEmptyModelData; import com.mojang.blaze3d.vertex.PoseStack; import com.mojang.blaze3d.vertex.VertexConsumer; @@ -12,6 +9,7 @@ import net.minecraft.client.renderer.block.ModelBlockRenderer; import net.minecraft.client.renderer.texture.OverlayTexture; import net.minecraft.client.resources.model.BakedModel; import net.minecraft.core.BlockPos; +import net.minecraft.util.RandomSource; import net.minecraft.world.level.BlockAndTintGetter; import net.minecraft.world.level.block.Blocks; import net.minecraft.world.level.block.state.BlockState; @@ -42,7 +40,7 @@ public final class BakedModelBuilder implements Bufferable { } @Override - public void bufferInto(ModelBlockRenderer blockRenderer, VertexConsumer consumer, Random random) { - blockRenderer.tesselateBlock(renderWorld, model, referenceState, BlockPos.ZERO, poseStack, consumer, false, random, 42, OverlayTexture.NO_OVERLAY, VirtualEmptyModelData.INSTANCE); + public void bufferInto(ModelBlockRenderer blockRenderer, VertexConsumer consumer, RandomSource random) { + blockRenderer.tesselateBlock(renderWorld, model, referenceState, BlockPos.ZERO, poseStack, consumer, false, random, 42, OverlayTexture.NO_OVERLAY, ModelUtil.VIRTUAL_DATA, null); } } diff --git a/src/main/java/com/jozufozu/flywheel/core/model/Bufferable.java b/src/main/java/com/jozufozu/flywheel/core/model/Bufferable.java index ee78333ad..2c7c74a4a 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/Bufferable.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/Bufferable.java @@ -1,17 +1,16 @@ package com.jozufozu.flywheel.core.model; -import java.util.Random; - import com.mojang.blaze3d.vertex.VertexConsumer; import net.minecraft.client.renderer.block.ModelBlockRenderer; +import net.minecraft.util.RandomSource; /** * An interface for objects that can "rendered" into a BufferBuilder. */ public interface Bufferable { - void bufferInto(ModelBlockRenderer renderer, VertexConsumer consumer, Random random); + void bufferInto(ModelBlockRenderer renderer, VertexConsumer consumer, RandomSource random); default ShadeSeparatedBufferBuilder build() { return ModelUtil.getBufferBuilder(this); diff --git a/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java b/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java index 1cd4f903c..26fc5859a 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java @@ -2,7 +2,6 @@ package com.jozufozu.flywheel.core.model; import java.lang.reflect.Field; import java.util.Collection; -import java.util.Random; import java.util.function.Supplier; import com.jozufozu.flywheel.Flywheel; @@ -18,9 +17,12 @@ import net.minecraft.client.renderer.block.BlockRenderDispatcher; import net.minecraft.client.renderer.block.ModelBlockRenderer; import net.minecraft.client.resources.model.BakedModel; import net.minecraft.core.Direction; +import net.minecraft.util.RandomSource; import net.minecraft.world.level.BlockAndTintGetter; import net.minecraft.world.level.block.state.BlockState; import net.minecraft.world.level.levelgen.structure.templatesystem.StructureTemplate; +import net.minecraftforge.client.model.data.ModelData; +import net.minecraftforge.client.model.data.ModelProperty; import net.minecraftforge.fml.util.ObfuscationReflectionHelper; public class ModelUtil { @@ -30,6 +32,9 @@ public class ModelUtil { */ public static final BlockRenderDispatcher VANILLA_RENDERER = createVanillaRenderer(); + public static final ModelProperty VIRTUAL_PROPERTY = new ModelProperty<>(); + public static final ModelData VIRTUAL_DATA = ModelData.builder().with(VIRTUAL_PROPERTY, true).build(); + private static final ThreadLocal THREAD_LOCAL_OBJECTS = ThreadLocal.withInitial(ThreadLocalObjects::new); private static BlockRenderDispatcher createVanillaRenderer() { @@ -99,7 +104,7 @@ public class ModelUtil { } private static class ThreadLocalObjects { - public final Random random = new Random(); + public final RandomSource random = RandomSource.create(); public final ShadeSeparatingVertexConsumer shadeSeparatingWrapper = new ShadeSeparatingVertexConsumer(); public final ShadeSeparatedBufferBuilder separatedBufferBuilder = new ShadeSeparatedBufferBuilder(512); public final BufferBuilder unshadedBuilder = new BufferBuilder(512); diff --git a/src/main/java/com/jozufozu/flywheel/core/model/WorldModelBuilder.java b/src/main/java/com/jozufozu/flywheel/core/model/WorldModelBuilder.java index 38bda7d1c..03a145dfd 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/WorldModelBuilder.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/WorldModelBuilder.java @@ -3,30 +3,28 @@ package com.jozufozu.flywheel.core.model; import java.util.Collection; import java.util.Collections; import java.util.Map; -import java.util.Random; import com.jozufozu.flywheel.core.virtual.VirtualEmptyBlockGetter; import com.mojang.blaze3d.vertex.PoseStack; import com.mojang.blaze3d.vertex.VertexConsumer; -import net.minecraft.client.renderer.ItemBlockRenderTypes; import net.minecraft.client.renderer.RenderType; import net.minecraft.client.renderer.block.ModelBlockRenderer; import net.minecraft.client.renderer.texture.OverlayTexture; +import net.minecraft.client.resources.model.BakedModel; import net.minecraft.core.BlockPos; +import net.minecraft.util.RandomSource; import net.minecraft.world.level.BlockAndTintGetter; import net.minecraft.world.level.block.RenderShape; import net.minecraft.world.level.block.state.BlockState; import net.minecraft.world.level.levelgen.structure.templatesystem.StructureTemplate; -import net.minecraftforge.client.ForgeHooksClient; -import net.minecraftforge.client.model.data.EmptyModelData; -import net.minecraftforge.client.model.data.IModelData; +import net.minecraftforge.client.model.data.ModelData; public final class WorldModelBuilder implements Bufferable { private final RenderType layer; private PoseStack poseStack = new PoseStack(); - private Map modelData = Collections.emptyMap(); + private Map modelData = Collections.emptyMap(); private BlockAndTintGetter renderWorld = VirtualEmptyBlockGetter.INSTANCE; private Collection blocks = Collections.emptyList(); @@ -35,26 +33,25 @@ public final class WorldModelBuilder implements Bufferable { } @Override - public void bufferInto(ModelBlockRenderer modelRenderer, VertexConsumer consumer, Random random) { - ForgeHooksClient.setRenderType(this.layer); + public void bufferInto(ModelBlockRenderer modelRenderer, VertexConsumer consumer, RandomSource random) { ModelBlockRenderer.enableCaching(); for (StructureTemplate.StructureBlockInfo info : this.blocks) { BlockState state = info.state; - if (state.getRenderShape() != RenderShape.MODEL) continue; - if (!ItemBlockRenderTypes.canRenderInLayer(state, this.layer)) continue; BlockPos pos = info.pos; - - IModelData data = this.modelData.getOrDefault(pos, EmptyModelData.INSTANCE); + long randomSeed = state.getSeed(pos); + BakedModel model = ModelUtil.VANILLA_RENDERER.getBlockModel(state); + ModelData data = this.modelData.getOrDefault(pos, ModelData.EMPTY); + random.setSeed(randomSeed); + if (!model.getRenderTypes(state, random, data).contains(this.layer)) continue; poseStack.pushPose(); poseStack.translate(pos.getX(), pos.getY(), pos.getZ()); - modelRenderer.tesselateBlock(this.renderWorld, ModelUtil.VANILLA_RENDERER.getBlockModel(state), state, pos, poseStack, consumer, true, random, 42, OverlayTexture.NO_OVERLAY, data); + modelRenderer.tesselateBlock(this.renderWorld, model, state, pos, poseStack, consumer, true, random, randomSeed, OverlayTexture.NO_OVERLAY, data, this.layer); poseStack.popPose(); } ModelBlockRenderer.clearCache(); - ForgeHooksClient.setRenderType(null); } /** @@ -70,7 +67,7 @@ public final class WorldModelBuilder implements Bufferable { return this; } - public WorldModelBuilder withModelData(Map modelData) { + public WorldModelBuilder withModelData(Map modelData) { this.modelData = modelData; return this; } diff --git a/src/main/java/com/jozufozu/flywheel/core/source/ShaderSources.java b/src/main/java/com/jozufozu/flywheel/core/source/ShaderSources.java index b7e29c2a4..53e1fe5b5 100644 --- a/src/main/java/com/jozufozu/flywheel/core/source/ShaderSources.java +++ b/src/main/java/com/jozufozu/flywheel/core/source/ShaderSources.java @@ -1,8 +1,8 @@ package com.jozufozu.flywheel.core.source; import java.io.IOException; +import java.io.InputStream; import java.util.ArrayList; -import java.util.Collection; import java.util.HashMap; import java.util.Map; @@ -28,18 +28,17 @@ public class ShaderSources implements SourceFinder { public final Index index; public ShaderSources(ResourceManager manager) { - Collection allShaders = manager.listResources(SHADER_DIR, s -> { + Map allShaders = manager.listResources(SHADER_DIR, loc -> { + String path = loc.getPath(); for (String ext : EXTENSIONS) { - if (s.endsWith(ext)) return true; + if (path.endsWith(ext)) return true; } return false; }); - for (ResourceLocation location : allShaders) { - try { - Resource resource = manager.getResource(location); - - String source = StringUtil.readToString(resource.getInputStream()); + allShaders.forEach((location, resource) -> { + try (InputStream inputStream = resource.open()) { + String source = StringUtil.readToString(inputStream); ResourceLocation name = ResourceUtil.removePrefixUnchecked(location, SHADER_DIR); @@ -47,7 +46,7 @@ public class ShaderSources implements SourceFinder { } catch (IOException e) { } - } + }); index = new Index(shaderSources); } diff --git a/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualChunk.java b/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualChunk.java index eaed3e59f..32d0d9fad 100644 --- a/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualChunk.java +++ b/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualChunk.java @@ -28,7 +28,7 @@ import net.minecraft.world.level.chunk.ChunkStatus; import net.minecraft.world.level.chunk.LevelChunkSection; import net.minecraft.world.level.chunk.UpgradeData; import net.minecraft.world.level.levelgen.Heightmap; -import net.minecraft.world.level.levelgen.feature.ConfiguredStructureFeature; +import net.minecraft.world.level.levelgen.structure.Structure; import net.minecraft.world.level.levelgen.structure.StructureStart; import net.minecraft.world.level.material.Fluid; import net.minecraft.world.level.material.FluidState; @@ -192,41 +192,78 @@ public class VirtualChunk extends ChunkAccess { return null; } +// @Override +// @Nullable +// public StructureStart getStartForFeature(ConfiguredStructureFeature pStructure) { +// return null; +// } +// +// @Override +// public void setStartForFeature(ConfiguredStructureFeature pStructure, StructureStart pStart) { +// } +// +// @Override +// public Map, StructureStart> getAllStarts() { +// return Collections.emptyMap(); +// } +// +// @Override +// public void setAllStarts(Map, StructureStart> pStructureStarts) { +// } +// +// @Override +// public LongSet getReferencesForFeature(ConfiguredStructureFeature pStructure) { +// return LongSets.emptySet(); +// } +// +// @Override +// public void addReferenceForFeature(ConfiguredStructureFeature pStructure, long pReference) { +// } +// +// @Override +// public Map, LongSet> getAllReferences() { +// return Collections.emptyMap(); +// } +// +// @Override +// public void setAllReferences(Map, LongSet> pStructureReferences) { +// } + @Override @Nullable - public StructureStart getStartForFeature(ConfiguredStructureFeature pStructure) { + public StructureStart getStartForStructure(Structure structure) { return null; } @Override - public void setStartForFeature(ConfiguredStructureFeature pStructure, StructureStart pStart) { + public void setStartForStructure(Structure structure, StructureStart start) { } @Override - public Map, StructureStart> getAllStarts() { + public Map getAllStarts() { return Collections.emptyMap(); } @Override - public void setAllStarts(Map, StructureStart> pStructureStarts) { + public void setAllStarts(Map structureStarts) { } @Override - public LongSet getReferencesForFeature(ConfiguredStructureFeature pStructure) { + public LongSet getReferencesForStructure(Structure structure) { return LongSets.emptySet(); } @Override - public void addReferenceForFeature(ConfiguredStructureFeature pStructure, long pReference) { + public void addReferenceForStructure(Structure structure, long reference) { } @Override - public Map, LongSet> getAllReferences() { + public Map getAllReferences() { return Collections.emptyMap(); } @Override - public void setAllReferences(Map, LongSet> pStructureReferences) { + public void setAllReferences(Map structureReferences) { } @Override diff --git a/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualEmptyModelData.java b/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualEmptyModelData.java deleted file mode 100644 index 4a8195857..000000000 --- a/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualEmptyModelData.java +++ /dev/null @@ -1,34 +0,0 @@ -package com.jozufozu.flywheel.core.virtual; - -import net.minecraftforge.client.model.data.IModelData; -import net.minecraftforge.client.model.data.ModelProperty; - -/** - * This model data instance is passed whenever a model is rendered without - * available in-world context. IBakedModel#getModelData can react accordingly - * and avoid looking for model data itself - **/ -public enum VirtualEmptyModelData implements IModelData { - - INSTANCE; - - public static boolean is(IModelData data) { - return data == INSTANCE; - } - - @Override - public boolean hasProperty(ModelProperty prop) { - return false; - } - - @Override - public T getData(ModelProperty prop) { - return null; - } - - @Override - public T setData(ModelProperty prop, T data) { - return null; - } - -} diff --git a/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualRenderWorld.java b/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualRenderWorld.java index 39574d808..af5e7da6e 100644 --- a/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualRenderWorld.java +++ b/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualRenderWorld.java @@ -36,10 +36,12 @@ import net.minecraft.world.level.chunk.ChunkSource; import net.minecraft.world.level.chunk.LevelChunk; import net.minecraft.world.level.entity.LevelEntityGetter; import net.minecraft.world.level.gameevent.GameEvent; +import net.minecraft.world.level.gameevent.GameEvent.Context; import net.minecraft.world.level.lighting.LevelLightEngine; import net.minecraft.world.level.material.Fluid; import net.minecraft.world.level.saveddata.maps.MapItemSavedData; import net.minecraft.world.level.storage.WritableLevelData; +import net.minecraft.world.phys.Vec3; import net.minecraft.world.scores.Scoreboard; import net.minecraft.world.ticks.LevelTickAccess; @@ -68,7 +70,7 @@ public class VirtualRenderWorld extends Level implements FlywheelWorld { public VirtualRenderWorld(Level level, Vec3i biomeOffset, int height, int minBuildHeight) { super((WritableLevelData) level.getLevelData(), level.dimension(), level.dimensionTypeRegistration(), level::getProfiler, - true, false, 0); + true, false, 0, 0); this.biomeOffset = biomeOffset; this.level = level; this.height = nextMultipleOf16(height); @@ -294,6 +296,17 @@ public class VirtualRenderWorld extends Level implements FlywheelWorld { @Override public void levelEvent(@Nullable Player player, int type, BlockPos pos, int data) {} + @Override + public void gameEvent(GameEvent p_220404_, Vec3 p_220405_, Context p_220406_) {} + + @Override + public void playSeededSound(Player p_220363_, double p_220364_, double p_220365_, double p_220366_, + SoundEvent p_220367_, SoundSource p_220368_, float p_220369_, float p_220370_, long p_220371_) {} + + @Override + public void playSeededSound(Player p_220372_, Entity p_220373_, SoundEvent p_220374_, SoundSource p_220375_, + float p_220376_, float p_220377_, long p_220378_) {} + @Override public void playSound(@Nullable Player player, double x, double y, double z, SoundEvent soundIn, SoundSource category, float volume, float pitch) {} diff --git a/src/main/java/com/jozufozu/flywheel/event/EntityWorldHandler.java b/src/main/java/com/jozufozu/flywheel/event/EntityWorldHandler.java index c68054208..d6d81ae2b 100644 --- a/src/main/java/com/jozufozu/flywheel/event/EntityWorldHandler.java +++ b/src/main/java/com/jozufozu/flywheel/event/EntityWorldHandler.java @@ -4,8 +4,8 @@ import com.jozufozu.flywheel.backend.Backend; import com.jozufozu.flywheel.backend.instancing.InstancedRenderDispatcher; import net.minecraftforge.api.distmarker.Dist; -import net.minecraftforge.event.entity.EntityJoinWorldEvent; -import net.minecraftforge.event.entity.EntityLeaveWorldEvent; +import net.minecraftforge.event.entity.EntityJoinLevelEvent; +import net.minecraftforge.event.entity.EntityLeaveLevelEvent; import net.minecraftforge.eventbus.api.SubscribeEvent; import net.minecraftforge.fml.common.Mod; @@ -13,14 +13,14 @@ import net.minecraftforge.fml.common.Mod; public class EntityWorldHandler { @SubscribeEvent - public static void onEntityJoinWorld(EntityJoinWorldEvent event) { - if (event.getWorld().isClientSide && Backend.isOn()) InstancedRenderDispatcher.getEntities(event.getWorld()) + public static void onEntityJoinWorld(EntityJoinLevelEvent event) { + if (event.getLevel().isClientSide && Backend.isOn()) InstancedRenderDispatcher.getEntities(event.getLevel()) .queueAdd(event.getEntity()); } @SubscribeEvent - public static void onEntityLeaveWorld(EntityLeaveWorldEvent event) { - if (event.getWorld().isClientSide && Backend.isOn()) InstancedRenderDispatcher.getEntities(event.getWorld()) + public static void onEntityLeaveWorld(EntityLeaveLevelEvent event) { + if (event.getLevel().isClientSide && Backend.isOn()) InstancedRenderDispatcher.getEntities(event.getLevel()) .remove(event.getEntity()); } } diff --git a/src/main/java/com/jozufozu/flywheel/event/ForgeEvents.java b/src/main/java/com/jozufozu/flywheel/event/ForgeEvents.java index 056966700..c7bd0ffd3 100644 --- a/src/main/java/com/jozufozu/flywheel/event/ForgeEvents.java +++ b/src/main/java/com/jozufozu/flywheel/event/ForgeEvents.java @@ -7,9 +7,9 @@ import com.jozufozu.flywheel.util.WorldAttached; import net.minecraft.client.Minecraft; import net.minecraftforge.api.distmarker.Dist; -import net.minecraftforge.client.event.RenderGameOverlayEvent; +import net.minecraftforge.client.event.CustomizeGuiOverlayEvent; import net.minecraftforge.event.TickEvent; -import net.minecraftforge.event.world.WorldEvent; +import net.minecraftforge.event.level.LevelEvent; import net.minecraftforge.eventbus.api.SubscribeEvent; import net.minecraftforge.fml.common.Mod; @@ -17,17 +17,15 @@ import net.minecraftforge.fml.common.Mod; public class ForgeEvents { @SubscribeEvent - public static void addToDebugScreen(RenderGameOverlayEvent.Text event) { - + public static void addToDebugScreen(CustomizeGuiOverlayEvent.DebugText event) { if (Minecraft.getInstance().options.renderDebug) { - InstancedRenderDispatcher.getDebugString(event.getRight()); } } @SubscribeEvent - public static void unloadWorld(WorldEvent.Unload event) { - WorldAttached.invalidateWorld(event.getWorld()); + public static void unloadWorld(LevelEvent.Unload event) { + WorldAttached.invalidateWorld(event.getLevel()); } @SubscribeEvent diff --git a/src/main/java/com/jozufozu/flywheel/util/RenderMath.java b/src/main/java/com/jozufozu/flywheel/util/RenderMath.java index 9ee9ecddc..56febd8e9 100644 --- a/src/main/java/com/jozufozu/flywheel/util/RenderMath.java +++ b/src/main/java/com/jozufozu/flywheel/util/RenderMath.java @@ -1,6 +1,6 @@ package com.jozufozu.flywheel.util; -import net.minecraftforge.client.model.pipeline.LightUtil; +import net.minecraftforge.client.model.lighting.QuadLighter; public class RenderMath { @@ -74,13 +74,13 @@ public class RenderMath { if (!shaded) { return 1f; } - return LightUtil.diffuseLight(x, y, z); + return QuadLighter.calculateShade(x, y, z, false); } public static float diffuseLightNether(float x, float y, float z, boolean shaded) { if (!shaded) { return 0.9f; } - return Math.min(x * x * 0.6f + y * y * 0.9f + z * z * 0.8f, 1f); + return QuadLighter.calculateShade(x, y, z, true); } } From ae945f6aced1ee9614e171bf3f1d259a9fb5277e Mon Sep 17 00:00:00 2001 From: Jozufozu Date: Sat, 16 Jul 2022 21:38:22 -0400 Subject: [PATCH 02/11] Finish porting to 1.19 (mostly) - Terrible, terrible mixins to ChunkRenderDispatcher and its subclasses - Index buffers may break chunk rendering sometimes, needs debugging --- .editorconfig | 11 ++ .../backend/gl/buffer/MappedBuffer.java | 2 +- .../backend/instancing/InstanceManager.java | 11 ++ .../flywheel/backend/model/ElementBuffer.java | 6 +- .../flywheel/backend/model/IndexedModel.java | 4 +- .../flywheel/backend/model/ModelPool.java | 4 +- .../jozufozu/flywheel/core/QuadConverter.java | 177 ++++++------------ .../flywheel/core/hardcoded/ModelPart.java | 8 + .../flywheel/core/model/BlockModel.java | 74 +++++++- .../jozufozu/flywheel/core/model/Model.java | 5 +- .../model/ShadeSeparatedBufferBuilder.java | 11 +- .../flywheel/core/model/WorldModel.java | 37 ---- .../core/model/WorldModelBuilder.java | 4 +- .../core/vertex/AbstractVertexList.java | 9 - .../flywheel/core/vertex/BlockVertex.java | 13 +- .../flywheel/core/vertex/BlockVertexList.java | 15 +- .../flywheel/mixin/BufferUploaderMixin.java | 5 +- .../mixin/ChunkRebuildHooksMixin.java | 33 ---- .../ChunkRebuildHooksMixin.java | 82 ++++++++ .../ChunkRenderDispatcherAccessor.java | 14 ++ .../InstanceAddMixin.java | 2 +- .../InstanceRemoveMixin.java | 2 +- .../instancemanage/RenderChunkAccessor.java | 19 ++ .../instancemanage/RenderChunkMixin.java | 21 +++ .../flywheel/util/RenderChunkExtension.java | 7 + src/main/resources/META-INF/mods.toml | 4 +- src/main/resources/flywheel.mixins.json | 9 +- 27 files changed, 349 insertions(+), 240 deletions(-) delete mode 100644 src/main/java/com/jozufozu/flywheel/core/model/WorldModel.java delete mode 100644 src/main/java/com/jozufozu/flywheel/mixin/ChunkRebuildHooksMixin.java create mode 100644 src/main/java/com/jozufozu/flywheel/mixin/instancemanage/ChunkRebuildHooksMixin.java create mode 100644 src/main/java/com/jozufozu/flywheel/mixin/instancemanage/ChunkRenderDispatcherAccessor.java rename src/main/java/com/jozufozu/flywheel/mixin/{ => instancemanage}/InstanceAddMixin.java (95%) rename src/main/java/com/jozufozu/flywheel/mixin/{ => instancemanage}/InstanceRemoveMixin.java (96%) create mode 100644 src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkAccessor.java create mode 100644 src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkMixin.java create mode 100644 src/main/java/com/jozufozu/flywheel/util/RenderChunkExtension.java diff --git a/.editorconfig b/.editorconfig index 1eeca6433..f1abc2e0c 100644 --- a/.editorconfig +++ b/.editorconfig @@ -13,6 +13,17 @@ insert_final_newline = true [*.json] indent_style = space indent_size = 2 +max_line_length = 500 +ij_json_keep_blank_lines_in_code = 0 +ij_json_keep_indents_on_empty_lines = false +ij_json_keep_line_breaks = true +ij_json_space_after_colon = true +ij_json_space_after_comma = true +ij_json_space_before_colon = true +ij_json_space_before_comma = false +ij_json_spaces_within_braces = true +ij_json_spaces_within_brackets = false +ij_json_wrap_long_lines = false [*.java] indent_style = tab diff --git a/src/main/java/com/jozufozu/flywheel/backend/gl/buffer/MappedBuffer.java b/src/main/java/com/jozufozu/flywheel/backend/gl/buffer/MappedBuffer.java index 25155a1d0..c95a398cb 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/gl/buffer/MappedBuffer.java +++ b/src/main/java/com/jozufozu/flywheel/backend/gl/buffer/MappedBuffer.java @@ -39,7 +39,7 @@ public class MappedBuffer extends VecBuffer implements AutoCloseable { } @Override - public void close() throws Exception { + public void close() { flush(); } } diff --git a/src/main/java/com/jozufozu/flywheel/backend/instancing/InstanceManager.java b/src/main/java/com/jozufozu/flywheel/backend/instancing/InstanceManager.java index 1f8310d1e..7743fb0b8 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/instancing/InstanceManager.java +++ b/src/main/java/com/jozufozu/flywheel/backend/instancing/InstanceManager.java @@ -1,6 +1,7 @@ package com.jozufozu.flywheel.backend.instancing; import java.util.ArrayList; +import java.util.Collection; import java.util.HashMap; import java.util.HashSet; import java.util.List; @@ -359,4 +360,14 @@ public abstract class InstanceManager implements InstancingEngine.OriginShift LightUpdater.get(value.world).removeListener(value); } } + + public void queueAddAll(Collection objects) { + if (!Backend.isOn() || objects.isEmpty()) { + return; + } + + synchronized (queuedAdditions) { + queuedAdditions.addAll(objects); + } + } } diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/ElementBuffer.java b/src/main/java/com/jozufozu/flywheel/backend/model/ElementBuffer.java index 8227ad019..aba15457b 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/ElementBuffer.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/ElementBuffer.java @@ -2,14 +2,16 @@ package com.jozufozu.flywheel.backend.model; import com.jozufozu.flywheel.backend.gl.GlNumericType; import com.jozufozu.flywheel.backend.gl.buffer.GlBuffer; +import com.mojang.blaze3d.vertex.VertexBuffer; +import com.mojang.blaze3d.vertex.VertexFormat; public class ElementBuffer { private final GlBuffer buffer; public final int elementCount; - public final GlNumericType eboIndexType; + public final VertexFormat.IndexType eboIndexType; - public ElementBuffer(GlBuffer backing, int elementCount, GlNumericType indexType) { + public ElementBuffer(GlBuffer backing, int elementCount, VertexFormat.IndexType indexType) { this.buffer = backing; this.eboIndexType = indexType; this.elementCount = elementCount; diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java b/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java index 7a372b0c8..4052e569e 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java @@ -60,7 +60,7 @@ public class IndexedModel implements BufferedModel { @Override public void drawCall() { ebo.bind(); - GL20.glDrawElements(primitiveMode.glEnum, ebo.elementCount, ebo.eboIndexType.getGlEnum(), 0); + GL20.glDrawElements(primitiveMode.glEnum, ebo.elementCount, ebo.eboIndexType.asGLType, 0); } /** @@ -72,7 +72,7 @@ public class IndexedModel implements BufferedModel { ebo.bind(); - GL31.glDrawElementsInstanced(primitiveMode.glEnum, ebo.elementCount, ebo.eboIndexType.getGlEnum(), 0, instanceCount); + GL31.glDrawElementsInstanced(primitiveMode.glEnum, ebo.elementCount, ebo.eboIndexType.asGLType, 0, instanceCount); } public boolean isDeleted() { diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/ModelPool.java b/src/main/java/com/jozufozu/flywheel/backend/model/ModelPool.java index 5c1d426c7..d9ce70838 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/ModelPool.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/ModelPool.java @@ -189,7 +189,7 @@ public class ModelPool implements ModelAllocator { @Override public void drawCall() { - GL32.glDrawElementsBaseVertex(GlPrimitive.TRIANGLES.glEnum, ebo.elementCount, ebo.eboIndexType.getGlEnum(), 0, first); + GL32.glDrawElementsBaseVertex(GlPrimitive.TRIANGLES.glEnum, ebo.elementCount, ebo.eboIndexType.asGLType, 0, first); } @Override @@ -200,7 +200,7 @@ public class ModelPool implements ModelAllocator { //Backend.log.info(StringUtil.args("drawElementsInstancedBaseVertex", GlPrimitive.TRIANGLES, ebo.elementCount, ebo.eboIndexType, 0, instanceCount, first)); - GL32.glDrawElementsInstancedBaseVertex(GlPrimitive.TRIANGLES.glEnum, ebo.elementCount, ebo.eboIndexType.getGlEnum(), 0, instanceCount, first); + GL32.glDrawElementsInstancedBaseVertex(GlPrimitive.TRIANGLES.glEnum, ebo.elementCount, ebo.eboIndexType.asGLType, 0, instanceCount, first); } @Override diff --git a/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java b/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java index d1871224b..6e461b019 100644 --- a/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java +++ b/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java @@ -3,41 +3,30 @@ package com.jozufozu.flywheel.core; import java.nio.Buffer; import java.nio.ByteBuffer; import java.nio.ByteOrder; -import java.util.EnumMap; -import java.util.Map; -import javax.annotation.Nonnull; -import javax.annotation.Nullable; - -import org.lwjgl.system.MemoryStack; +import org.jetbrains.annotations.NotNull; +import org.jetbrains.annotations.Nullable; import org.lwjgl.system.MemoryUtil; import com.jozufozu.flywheel.backend.gl.GlNumericType; -import com.jozufozu.flywheel.backend.gl.buffer.GlBuffer; import com.jozufozu.flywheel.backend.gl.buffer.GlBufferType; +import com.jozufozu.flywheel.backend.gl.buffer.MappedBuffer; import com.jozufozu.flywheel.backend.gl.buffer.MappedGlBuffer; import com.jozufozu.flywheel.backend.model.ElementBuffer; import com.jozufozu.flywheel.event.ReloadRenderersEvent; - -import net.minecraftforge.api.distmarker.Dist; -import net.minecraftforge.eventbus.api.EventPriority; -import net.minecraftforge.eventbus.api.SubscribeEvent; -import net.minecraftforge.fml.common.Mod; +import com.mojang.blaze3d.vertex.VertexFormat; /** * A class to manage EBOs that index quads as triangles. */ -@Mod.EventBusSubscriber(Dist.CLIENT) public class QuadConverter { - public static final int STARTING_CAPACITY = 42; // 255 / 6 = 42 - private static QuadConverter INSTANCE; - @Nonnull + @NotNull public static QuadConverter getInstance() { if (INSTANCE == null) { - INSTANCE = new QuadConverter(STARTING_CAPACITY); + INSTANCE = new QuadConverter(); } return INSTANCE; @@ -48,130 +37,80 @@ public class QuadConverter { return INSTANCE; } - Map ebos; - int[] capacities; + private final MappedGlBuffer ebo; + private int quadCapacity; - public QuadConverter(int initialCapacity) { - this.ebos = new EnumMap<>(GlNumericType.class); - initCapacities(); - - fillBuffer(initialCapacity); + public QuadConverter() { + this.ebo = new MappedGlBuffer(GlBufferType.ELEMENT_ARRAY_BUFFER); + this.quadCapacity = 0; } public ElementBuffer quads2Tris(int quads) { int indexCount = quads * 6; - GlNumericType type = getSmallestIndexType(indexCount); - if (quads > getCapacity(type)) { - fillBuffer(quads, indexCount, type); + if (quads > quadCapacity) { + ebo.bind(); + ebo.ensureCapacity((long) indexCount * GlNumericType.UINT.getByteWidth()); + + try (MappedBuffer map = ebo.getBuffer()) { + ByteBuffer indices = map.unwrap(); + + fillBuffer(indices, quads); + } + ebo.unbind(); + + this.quadCapacity = quads; } - return new ElementBuffer(getBuffer(type), indexCount, type); - } - - private void initCapacities() { - this.capacities = new int[GlNumericType.values().length]; - } - - private int getCapacity(GlNumericType type) { - return capacities[type.ordinal()]; - } - - private void updateCapacity(GlNumericType type, int capacity) { - if (getCapacity(type) < capacity) { - capacities[type.ordinal()] = capacity; - } + return new ElementBuffer(ebo, indexCount, VertexFormat.IndexType.INT); } public void delete() { - ebos.values() - .forEach(GlBuffer::delete); - ebos.clear(); - initCapacities(); + ebo.delete(); + this.quadCapacity = 0; } - private void fillBuffer(int quads) { - int indexCount = quads * 6; + private void fillBuffer(ByteBuffer indices, int quads) { + long addr = MemoryUtil.memAddress(indices); + int numVertices = 4 * quads; + int baseVertex = 0; + while (baseVertex < numVertices) { + // writeQuadIndices(indices, baseVertex); + writeQuadIndicesUnsafe(addr, baseVertex); - fillBuffer(quads, indexCount, getSmallestIndexType(indexCount)); - } - - private void fillBuffer(int quads, int indexCount, GlNumericType type) { - MemoryStack stack = MemoryStack.stackPush(); - int bytes = indexCount * type.getByteWidth(); - - ByteBuffer indices; - if (bytes > stack.getSize()) { - indices = MemoryUtil.memAlloc(bytes); // not enough space on the preallocated stack - } else { - stack.push(); - indices = stack.malloc(bytes); + baseVertex += 4; + addr += 6 * 4; } - - indices.order(ByteOrder.nativeOrder()); - - fillBuffer(indices, type, quads); - - GlBuffer buffer = getBuffer(type); - - buffer.bind(); - buffer.upload(indices); - buffer.unbind(); - - if (bytes > stack.getSize()) { - MemoryUtil.memFree(indices); - } else { - stack.pop(); - } - - updateCapacity(type, quads); + // ((Buffer) indices).flip(); } - private void fillBuffer(ByteBuffer indices, GlNumericType type, int quads) { - for (int i = 0, max = 4 * quads; i < max; i += 4) { - // triangle a - type.castAndBuffer(indices, i); - type.castAndBuffer(indices, i + 1); - type.castAndBuffer(indices, i + 2); - // triangle b - type.castAndBuffer(indices, i); - type.castAndBuffer(indices, i + 2); - type.castAndBuffer(indices, i + 3); - } - ((Buffer) indices).flip(); + private void writeQuadIndices(ByteBuffer indices, int baseVertex) { + // triangle a + indices.putInt(baseVertex); + indices.putInt(baseVertex + 1); + indices.putInt(baseVertex + 2); + // triangle b + indices.putInt(baseVertex); + indices.putInt(baseVertex + 2); + indices.putInt(baseVertex + 3); } - private GlBuffer getBuffer(GlNumericType type) { - return ebos.computeIfAbsent(type, $ -> new MappedGlBuffer(GlBufferType.ELEMENT_ARRAY_BUFFER)); - } - - /** - * Given the needed number of indices, what is the smallest bit width type that can index everything?
- * - *
-	 * | indexCount   | type  |
-	 * |--------------|-------|
-	 * | [0, 255)     | byte  |
-	 * | [256, 65536)	| short	|
-	 * | [65537, )	| int	|
-	 * 
- */ - private static GlNumericType getSmallestIndexType(int indexCount) { -// indexCount = indexCount >>> 8; -// if (indexCount == 0) { -// return GlNumericType.UBYTE; -// } -// indexCount = indexCount >>> 8; -// if (indexCount == 0) { -// return GlNumericType.USHORT; -// } - - return GlNumericType.UINT; + private void writeQuadIndicesUnsafe(long addr, int baseVertex) { + // triangle a + MemoryUtil.memPutInt(addr, baseVertex); + MemoryUtil.memPutInt(addr + 4, baseVertex + 1); + MemoryUtil.memPutInt(addr + 8, baseVertex + 2); + // triangle b + MemoryUtil.memPutInt(addr + 12, baseVertex); + MemoryUtil.memPutInt(addr + 16, baseVertex + 2); + MemoryUtil.memPutInt(addr + 20, baseVertex + 3); } // make sure this gets reset first so it has a chance to repopulate - @SubscribeEvent(priority = EventPriority.HIGHEST) public static void onRendererReload(ReloadRenderersEvent event) { - if (INSTANCE != null) INSTANCE.delete(); + if (INSTANCE != null) { + INSTANCE.delete(); + INSTANCE = null; + } } } diff --git a/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java b/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java index 67bdeb798..d67ca22d3 100644 --- a/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java +++ b/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java @@ -3,7 +3,9 @@ package com.jozufozu.flywheel.core.hardcoded; import java.util.List; import com.jozufozu.flywheel.api.vertex.VertexList; +import com.jozufozu.flywheel.backend.model.ElementBuffer; import com.jozufozu.flywheel.core.Formats; +import com.jozufozu.flywheel.core.QuadConverter; import com.jozufozu.flywheel.core.model.Model; import com.jozufozu.flywheel.core.vertex.PosTexNormalWriterUnsafe; import com.mojang.blaze3d.platform.MemoryTracker; @@ -51,4 +53,10 @@ public class ModelPart implements Model { public VertexList getReader() { return reader; } + + @Override + public ElementBuffer createEBO() { + return QuadConverter.getInstance() + .quads2Tris(vertices / 4); + } } diff --git a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java index 8c527bea6..45b2e6f1a 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java @@ -1,8 +1,25 @@ package com.jozufozu.flywheel.core.model; +import java.lang.management.MemoryUsage; +import java.nio.ByteBuffer; +import java.util.function.Supplier; + +import org.lwjgl.system.MemoryUtil; + import com.jozufozu.flywheel.api.vertex.VertexList; +import com.jozufozu.flywheel.api.vertex.VertexType; +import com.jozufozu.flywheel.backend.gl.GlNumericType; +import com.jozufozu.flywheel.backend.gl.buffer.GlBuffer; +import com.jozufozu.flywheel.backend.gl.buffer.GlBufferType; +import com.jozufozu.flywheel.backend.gl.buffer.GlBufferUsage; +import com.jozufozu.flywheel.backend.gl.buffer.MappedGlBuffer; +import com.jozufozu.flywheel.backend.model.ElementBuffer; import com.jozufozu.flywheel.core.Formats; +import com.jozufozu.flywheel.core.QuadConverter; +import com.mojang.blaze3d.platform.MemoryTracker; +import com.mojang.blaze3d.vertex.BufferBuilder; import com.mojang.blaze3d.vertex.PoseStack; +import com.mojang.blaze3d.vertex.VertexBuffer; import net.minecraft.client.Minecraft; import net.minecraft.client.resources.model.BakedModel; @@ -12,12 +29,12 @@ import net.minecraft.world.level.block.state.BlockState; * A model of a single block. */ public class BlockModel implements Model { - private static final PoseStack IDENTITY = new PoseStack(); - private final VertexList reader; private final String name; + private final Supplier eboSupplier; + public BlockModel(BlockState state) { this(Minecraft.getInstance() .getBlockRenderer() @@ -25,12 +42,49 @@ public class BlockModel implements Model { } public BlockModel(BakedModel model, BlockState referenceState) { - this(model, referenceState, IDENTITY); + this(new BakedModelBuilder(model).withReferenceState(referenceState), referenceState.toString()); } public BlockModel(BakedModel model, BlockState referenceState, PoseStack ms) { - reader = Formats.BLOCK.createReader(ModelUtil.getBufferBuilder(model, referenceState, ms)); - name = referenceState.toString(); + this(new BakedModelBuilder(model).withReferenceState(referenceState) + .withPoseStack(ms), referenceState.toString()); + } + + public BlockModel(Bufferable bufferable, String name) { + this(bufferable.build(), name); + } + + public BlockModel(ShadeSeparatedBufferBuilder buffer, String name) { + this.name = name; + + BufferBuilder.RenderedBuffer renderedBuffer = buffer.endOrDiscardIfEmpty(); + + if (renderedBuffer == null) { + reader = null; + eboSupplier = () -> null; + return; + } + + BufferBuilder.DrawState drawState = renderedBuffer.drawState(); + + reader = Formats.BLOCK.createReader(renderedBuffer, buffer.getUnshadedStartVertex()); + + if (drawState.sequentialIndex()) { + ByteBuffer src = renderedBuffer.indexBuffer(); + ByteBuffer indexBuffer = MemoryTracker.create(src.capacity()); + MemoryUtil.memCopy(src, indexBuffer); + eboSupplier = () -> { + + MappedGlBuffer vbo = new MappedGlBuffer(GlBufferType.ELEMENT_ARRAY_BUFFER, GlBufferUsage.STATIC_DRAW); + + vbo.upload(indexBuffer); + + return new ElementBuffer(vbo, drawState.indexCount(), drawState.indexType()); + }; + } else { + eboSupplier = () -> QuadConverter.getInstance() + .quads2Tris(vertexCount() / 4); + } } @Override @@ -47,4 +101,14 @@ public class BlockModel implements Model { public VertexList getReader() { return reader; } + + @Override + public ElementBuffer createEBO() { + return eboSupplier.get(); + } + + @Override + public VertexType getType() { + return Formats.BLOCK; + } } diff --git a/src/main/java/com/jozufozu/flywheel/core/model/Model.java b/src/main/java/com/jozufozu/flywheel/core/model/Model.java index eacfd3394..c93e1df84 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/Model.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/Model.java @@ -56,10 +56,7 @@ public interface Model { *

* @return an element buffer object indexing this model's vertices. */ - default ElementBuffer createEBO() { - return QuadConverter.getInstance() - .quads2Tris(vertexCount() / 4); - } + ElementBuffer createEBO(); /** * The size in bytes that this model's data takes up. diff --git a/src/main/java/com/jozufozu/flywheel/core/model/ShadeSeparatedBufferBuilder.java b/src/main/java/com/jozufozu/flywheel/core/model/ShadeSeparatedBufferBuilder.java index 38043702b..71a05d70f 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/ShadeSeparatedBufferBuilder.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/ShadeSeparatedBufferBuilder.java @@ -14,9 +14,16 @@ public class ShadeSeparatedBufferBuilder extends BufferBuilder { } public void appendUnshadedVertices(BufferBuilder unshadedBuilder) { - Pair data = unshadedBuilder.popNextBuffer(); + RenderedBuffer renderedBuffer = unshadedBuilder.endOrDiscardIfEmpty(); + + if (renderedBuffer == null) { + return; + } + + // FIXME: Unshaded indices + ByteBuffer buffer = renderedBuffer.vertexBuffer(); unshadedStartVertex = ((BufferBuilderExtension) this).flywheel$getVertices(); - ((BufferBuilderExtension) this).flywheel$appendBufferUnsafe(data.getSecond()); + ((BufferBuilderExtension) this).flywheel$appendBufferUnsafe(buffer); } public int getUnshadedStartVertex() { diff --git a/src/main/java/com/jozufozu/flywheel/core/model/WorldModel.java b/src/main/java/com/jozufozu/flywheel/core/model/WorldModel.java deleted file mode 100644 index c144f43c6..000000000 --- a/src/main/java/com/jozufozu/flywheel/core/model/WorldModel.java +++ /dev/null @@ -1,37 +0,0 @@ -package com.jozufozu.flywheel.core.model; - -import com.jozufozu.flywheel.api.vertex.VertexList; -import com.jozufozu.flywheel.api.vertex.VertexType; -import com.jozufozu.flywheel.core.Formats; -import com.mojang.blaze3d.vertex.BufferBuilder; - -public class WorldModel implements Model { - - private final VertexList reader; - private final String name; - - public WorldModel(BufferBuilder bufferBuilder, String name) { - this.reader = Formats.BLOCK.createReader(bufferBuilder); - this.name = name; - } - - @Override - public String name() { - return name; - } - - @Override - public VertexType getType() { - return Formats.BLOCK; - } - - @Override - public int vertexCount() { - return reader.getVertexCount(); - } - - @Override - public VertexList getReader() { - return reader; - } -} diff --git a/src/main/java/com/jozufozu/flywheel/core/model/WorldModelBuilder.java b/src/main/java/com/jozufozu/flywheel/core/model/WorldModelBuilder.java index 03a145dfd..614bb0e9d 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/WorldModelBuilder.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/WorldModelBuilder.java @@ -77,7 +77,7 @@ public final class WorldModelBuilder implements Bufferable { return this; } - public WorldModel intoMesh(String name) { - return new WorldModel(ModelUtil.getBufferBuilder(this), name); + public BlockModel intoMesh(String name) { + return new BlockModel(this, name); } } diff --git a/src/main/java/com/jozufozu/flywheel/core/vertex/AbstractVertexList.java b/src/main/java/com/jozufozu/flywheel/core/vertex/AbstractVertexList.java index a68e0c943..24ec1eeab 100644 --- a/src/main/java/com/jozufozu/flywheel/core/vertex/AbstractVertexList.java +++ b/src/main/java/com/jozufozu/flywheel/core/vertex/AbstractVertexList.java @@ -22,15 +22,6 @@ public abstract class AbstractVertexList implements VertexList, AutoCloseable { init(copyFrom); } - public AbstractVertexList(BufferBuilder builder) { - var pair = builder.popNextBuffer(); - ByteBuffer copyFrom = pair.getSecond(); - this.contents = MemoryTracker.create(copyFrom.capacity()); - this.vertexCount = pair.getFirst().vertexCount(); - this.base = MemoryUtil.memAddress(this.contents); - init(copyFrom); - } - private void init(ByteBuffer copyFrom) { this.contents.order(copyFrom.order()); this.contents.put(copyFrom); diff --git a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java index d74dde894..1ac22ae94 100644 --- a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java +++ b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java @@ -62,19 +62,20 @@ Vertex FLWCreateVertex() { return new BlockVertexListUnsafe.Shaded(buffer, vertexCount, unshadedStartVertex); } - public VertexList createReader(BufferBuilder bufferBuilder) { + public VertexList createReader(BufferBuilder.RenderedBuffer renderedBuffer, int unshadedStartVertex) { + // TODO: try to avoid virtual model rendering - Pair pair = bufferBuilder.popNextBuffer(); - BufferBuilder.DrawState drawState = pair.getFirst(); + BufferBuilder.DrawState drawState = renderedBuffer.drawState(); if (drawState.format() != DefaultVertexFormat.BLOCK) { throw new RuntimeException("Cannot use BufferBuilder with " + drawState.format()); } + ByteBuffer vertexBuffer = renderedBuffer.vertexBuffer(); - if (bufferBuilder instanceof ShadeSeparatedBufferBuilder separated) { - return createReader(pair.getSecond(), drawState.vertexCount(), separated.getUnshadedStartVertex()); + if (unshadedStartVertex > 0) { + return createReader(vertexBuffer, drawState.vertexCount(), unshadedStartVertex); } else { - return createReader(pair.getSecond(), drawState.vertexCount()); + return createReader(vertexBuffer, drawState.vertexCount()); } } } diff --git a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertexList.java b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertexList.java index f84385f78..654f94865 100644 --- a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertexList.java +++ b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertexList.java @@ -1,5 +1,7 @@ package com.jozufozu.flywheel.core.vertex; +import java.nio.ByteBuffer; + import com.jozufozu.flywheel.api.vertex.ShadedVertexList; import com.jozufozu.flywheel.core.model.ShadeSeparatedBufferBuilder; import com.jozufozu.flywheel.util.RenderMath; @@ -9,10 +11,9 @@ public class BlockVertexList extends AbstractVertexList { private final int stride; - public BlockVertexList(BufferBuilder builder) { - super(builder); - this.stride = builder.getVertexFormat() - .getVertexSize(); + public BlockVertexList(ByteBuffer copyFrom, int vertexCount, int stride) { + super(copyFrom, vertexCount); + this.stride = stride; } @Override @@ -93,9 +94,9 @@ public class BlockVertexList extends AbstractVertexList { private final int unshadedStartVertex; - public Shaded(ShadeSeparatedBufferBuilder builder) { - super(builder); - unshadedStartVertex = builder.getUnshadedStartVertex(); + public Shaded(ByteBuffer copyFrom, int vertexCount, int stride, int unshadedStartVertex) { + super(copyFrom, vertexCount, stride); + this.unshadedStartVertex = unshadedStartVertex; } @Override diff --git a/src/main/java/com/jozufozu/flywheel/mixin/BufferUploaderMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/BufferUploaderMixin.java index 7cd63581c..92058feb9 100644 --- a/src/main/java/com/jozufozu/flywheel/mixin/BufferUploaderMixin.java +++ b/src/main/java/com/jozufozu/flywheel/mixin/BufferUploaderMixin.java @@ -10,6 +10,7 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; import com.jozufozu.flywheel.backend.gl.GlStateTracker; import com.mojang.blaze3d.vertex.BufferUploader; +import com.mojang.blaze3d.vertex.VertexBuffer; import com.mojang.blaze3d.vertex.VertexFormat; @Mixin(BufferUploader.class) @@ -17,13 +18,13 @@ public class BufferUploaderMixin { @Shadow @Nullable - private static VertexFormat lastFormat; + private static VertexBuffer lastImmediateBuffer; @Inject(method = "reset", at = @At("HEAD")) private static void stopBufferUploaderFromClearingBufferStateIfNothingIsBound(CallbackInfo ci) { // Trust our tracker over BufferUploader's. if (GlStateTracker.getVertexArray() == 0) { - lastFormat = null; + lastImmediateBuffer = null; } } } diff --git a/src/main/java/com/jozufozu/flywheel/mixin/ChunkRebuildHooksMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/ChunkRebuildHooksMixin.java deleted file mode 100644 index a4accbe24..000000000 --- a/src/main/java/com/jozufozu/flywheel/mixin/ChunkRebuildHooksMixin.java +++ /dev/null @@ -1,33 +0,0 @@ -package com.jozufozu.flywheel.mixin; - -import java.util.Set; - -import org.spongepowered.asm.mixin.Mixin; -import org.spongepowered.asm.mixin.injection.At; -import org.spongepowered.asm.mixin.injection.Inject; -import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; - -import com.jozufozu.flywheel.backend.Backend; -import com.jozufozu.flywheel.backend.instancing.InstancedRenderDispatcher; -import com.jozufozu.flywheel.backend.instancing.InstancedRenderRegistry; - -import net.minecraft.client.renderer.chunk.ChunkRenderDispatcher; -import net.minecraft.world.level.block.entity.BlockEntity; -import net.minecraftforge.api.distmarker.Dist; -import net.minecraftforge.api.distmarker.OnlyIn; - -@OnlyIn(Dist.CLIENT) -@Mixin(targets = "net.minecraft.client.renderer.chunk.ChunkRenderDispatcher$RenderChunk$RebuildTask") -public class ChunkRebuildHooksMixin { - - @Inject(method = "handleBlockEntity", at = @At("HEAD"), cancellable = true) - private void addAndFilterBEs(ChunkRenderDispatcher.CompiledChunk compiledChunk, Set set, E be, CallbackInfo ci) { - if (Backend.canUseInstancing(be.getLevel())) { - if (InstancedRenderRegistry.canInstance(be.getType())) - InstancedRenderDispatcher.getBlockEntities(be.getLevel()).queueAdd(be); - - if (InstancedRenderRegistry.shouldSkipRender(be)) - ci.cancel(); - } - } -} diff --git a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/ChunkRebuildHooksMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/ChunkRebuildHooksMixin.java new file mode 100644 index 000000000..599c7fc9a --- /dev/null +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/ChunkRebuildHooksMixin.java @@ -0,0 +1,82 @@ +package com.jozufozu.flywheel.mixin.instancemanage; + +import java.util.ArrayList; +import java.util.Collection; +import java.util.List; + +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.Unique; +import org.spongepowered.asm.mixin.injection.At; +import org.spongepowered.asm.mixin.injection.Inject; +import org.spongepowered.asm.mixin.injection.Redirect; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; + +import com.jozufozu.flywheel.backend.Backend; +import com.jozufozu.flywheel.backend.instancing.InstancedRenderDispatcher; +import com.jozufozu.flywheel.backend.instancing.InstancedRenderRegistry; +import com.jozufozu.flywheel.util.RenderChunkExtension; + +import net.minecraft.client.renderer.chunk.ChunkRenderDispatcher; +import net.minecraft.client.renderer.chunk.RenderChunkRegion; +import net.minecraft.world.level.ChunkPos; +import net.minecraft.world.level.Level; +import net.minecraft.world.level.block.entity.BlockEntity; +import net.minecraftforge.api.distmarker.Dist; +import net.minecraftforge.api.distmarker.OnlyIn; + +@OnlyIn(Dist.CLIENT) +@Mixin(targets = "net.minecraft.client.renderer.chunk.ChunkRenderDispatcher$RenderChunk$RebuildTask") +public abstract class ChunkRebuildHooksMixin { + @Unique + private Level flywheel$level; + + @Inject(method = "(Lnet/minecraft/client/renderer/chunk/ChunkRenderDispatcher$RenderChunk;Lnet/minecraft/world/level/ChunkPos;DLnet/minecraft/client/renderer/chunk/RenderChunkRegion;Z)V", at = @At("RETURN")) + private void setLevel(ChunkRenderDispatcher.RenderChunk this$1, ChunkPos pos, double p_194427_, RenderChunkRegion region, boolean p_194429_, CallbackInfo ci) { + flywheel$level = ((RenderChunkExtension) this$1).flywheel$getLevel(); + } + + @Redirect(method = "doTask", at = @At(value = "INVOKE", target = "Ljava/util/List;addAll(Ljava/util/Collection;)Z")) + private boolean addAndFilterBEs(List self, Collection es) { + if (!Backend.canUseInstancing(flywheel$level)) { + return self.addAll(es); + } + + boolean added = false; + var instanced = new ArrayList(); + for (E be : es) { + if (InstancedRenderRegistry.canInstance(be.getType())) { + instanced.add(be); + } + + if (!InstancedRenderRegistry.shouldSkipRender(be)) { + self.add(be); + added = true; + } + } + InstancedRenderDispatcher.getBlockEntities(flywheel$level).queueAddAll(instanced); + return added; + } + + @Redirect(method = "doTask", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/renderer/chunk/ChunkRenderDispatcher$RenderChunk;updateGlobalBlockEntities(Ljava/util/Collection;)V")) + private void addAndFilterBEs(ChunkRenderDispatcher.RenderChunk self, Collection bes) { + if (!Backend.canUseInstancing(flywheel$level)) { + ((RenderChunkAccessor) self).flywheel$updateGlobalBlockEntities(bes); + return; + } + + var global = new ArrayList(); + var instanced = new ArrayList(); + for (BlockEntity be : bes) { + if (InstancedRenderRegistry.canInstance(be.getType())) { + instanced.add(be); + } + + if (!InstancedRenderRegistry.shouldSkipRender(be)) { + global.add(be); + } + } + + InstancedRenderDispatcher.getBlockEntities(flywheel$level).queueAddAll(instanced); + ((RenderChunkAccessor) self).flywheel$updateGlobalBlockEntities(global); + } +} diff --git a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/ChunkRenderDispatcherAccessor.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/ChunkRenderDispatcherAccessor.java new file mode 100644 index 000000000..7e8e0de6d --- /dev/null +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/ChunkRenderDispatcherAccessor.java @@ -0,0 +1,14 @@ +package com.jozufozu.flywheel.mixin.instancemanage; + +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.gen.Accessor; + +import net.minecraft.client.multiplayer.ClientLevel; +import net.minecraft.client.renderer.chunk.ChunkRenderDispatcher; + +@Mixin(ChunkRenderDispatcher.class) +public interface ChunkRenderDispatcherAccessor { + + @Accessor + ClientLevel getLevel(); +} diff --git a/src/main/java/com/jozufozu/flywheel/mixin/InstanceAddMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/InstanceAddMixin.java similarity index 95% rename from src/main/java/com/jozufozu/flywheel/mixin/InstanceAddMixin.java rename to src/main/java/com/jozufozu/flywheel/mixin/instancemanage/InstanceAddMixin.java index b28fbfa84..7568c28e9 100644 --- a/src/main/java/com/jozufozu/flywheel/mixin/InstanceAddMixin.java +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/InstanceAddMixin.java @@ -1,4 +1,4 @@ -package com.jozufozu.flywheel.mixin; +package com.jozufozu.flywheel.mixin.instancemanage; import org.spongepowered.asm.mixin.Final; import org.spongepowered.asm.mixin.Mixin; diff --git a/src/main/java/com/jozufozu/flywheel/mixin/InstanceRemoveMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/InstanceRemoveMixin.java similarity index 96% rename from src/main/java/com/jozufozu/flywheel/mixin/InstanceRemoveMixin.java rename to src/main/java/com/jozufozu/flywheel/mixin/instancemanage/InstanceRemoveMixin.java index 0ee0fd088..1d115cfda 100644 --- a/src/main/java/com/jozufozu/flywheel/mixin/InstanceRemoveMixin.java +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/InstanceRemoveMixin.java @@ -1,4 +1,4 @@ -package com.jozufozu.flywheel.mixin; +package com.jozufozu.flywheel.mixin.instancemanage; import javax.annotation.Nullable; diff --git a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkAccessor.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkAccessor.java new file mode 100644 index 000000000..9bd5a2d3a --- /dev/null +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkAccessor.java @@ -0,0 +1,19 @@ +package com.jozufozu.flywheel.mixin.instancemanage; + +import java.util.Collection; + +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.gen.Invoker; + +import net.minecraft.client.renderer.chunk.ChunkRenderDispatcher; +import net.minecraft.world.level.block.entity.BlockEntity; + +/** + * For use in {@link ChunkRebuildHooksMixin#addAndFilterBEs(ChunkRenderDispatcher.RenderChunk, Collection)} + */ +@Mixin(ChunkRenderDispatcher.RenderChunk.class) +public interface RenderChunkAccessor { + + @Invoker("updateGlobalBlockEntities") + void flywheel$updateGlobalBlockEntities(Collection blockEntities); +} diff --git a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkMixin.java new file mode 100644 index 000000000..987d7e8e7 --- /dev/null +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkMixin.java @@ -0,0 +1,21 @@ +package com.jozufozu.flywheel.mixin.instancemanage; + +import org.spongepowered.asm.mixin.Final; +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.Shadow; + +import net.minecraft.client.multiplayer.ClientLevel; +import net.minecraft.client.renderer.chunk.ChunkRenderDispatcher; + +@Mixin(ChunkRenderDispatcher.RenderChunk.class) +public class RenderChunkMixin implements com.jozufozu.flywheel.util.RenderChunkExtension { + + @Shadow + @Final + private ChunkRenderDispatcher this$0; + + @Override + public ClientLevel flywheel$getLevel() { + return ((ChunkRenderDispatcherAccessor) this$0).getLevel(); + } +} diff --git a/src/main/java/com/jozufozu/flywheel/util/RenderChunkExtension.java b/src/main/java/com/jozufozu/flywheel/util/RenderChunkExtension.java new file mode 100644 index 000000000..acaa7faff --- /dev/null +++ b/src/main/java/com/jozufozu/flywheel/util/RenderChunkExtension.java @@ -0,0 +1,7 @@ +package com.jozufozu.flywheel.util; + +import net.minecraft.client.multiplayer.ClientLevel; + +public interface RenderChunkExtension { + ClientLevel flywheel$getLevel(); +} diff --git a/src/main/resources/META-INF/mods.toml b/src/main/resources/META-INF/mods.toml index 2f6649f40..4c6b69b3c 100644 --- a/src/main/resources/META-INF/mods.toml +++ b/src/main/resources/META-INF/mods.toml @@ -17,13 +17,13 @@ A modern engine for modded minecraft.''' [[dependencies.flywheel]] modId = "forge" mandatory = true -versionRange = "[40.0.0,)" +versionRange = "[41.0.0,)" ordering = "NONE" side = "CLIENT" [[dependencies.flywheel]] modId = "minecraft" mandatory = true -versionRange = "[1.18.2,1.19)" +versionRange = "[1.19,1.20)" ordering = "NONE" side = "CLIENT" diff --git a/src/main/resources/flywheel.mixins.json b/src/main/resources/flywheel.mixins.json index cccc7ef58..284039b65 100644 --- a/src/main/resources/flywheel.mixins.json +++ b/src/main/resources/flywheel.mixins.json @@ -10,17 +10,20 @@ "BufferBuilderMixin", "BufferUploaderMixin", "CameraMixin", + "instancemanage.ChunkRebuildHooksMixin", + "instancemanage.ChunkRenderDispatcherAccessor", "ClientLevelMixin", - "ChunkRebuildHooksMixin", "EntityTypeMixin", "FixFabulousDepthMixin", "FrustumMixin", "GlStateManagerMixin", - "InstanceAddMixin", - "InstanceRemoveMixin", + "instancemanage.InstanceAddMixin", + "instancemanage.InstanceRemoveMixin", "LevelRendererAccessor", "LevelRendererMixin", "PausedPartialTickAccessor", + "instancemanage.RenderChunkAccessor", + "instancemanage.RenderChunkMixin", "RenderTexturesMixin", "RenderTypeMixin", "atlas.AtlasDataMixin", From c4942ca29e80e72907397795c7b440e273cebf2a Mon Sep 17 00:00:00 2001 From: PepperCode1 <44146161+PepperCode1@users.noreply.github.com> Date: Wed, 3 Aug 2022 23:18:49 -0700 Subject: [PATCH 03/11] Buffer building changes - Remove ShadeSeparatedBufferBuilder and use Pair instead to properly support 1.19's buffer changes - Add ModelUtil#isVirtual to check if a ModelData is virtual --- .../flywheel/core/model/BlockModel.java | 13 +++--- .../flywheel/core/model/Bufferable.java | 6 ++- .../flywheel/core/model/ModelUtil.java | 44 ++++++++++++------- .../model/ShadeSeparatedBufferBuilder.java | 32 -------------- .../flywheel/core/vertex/BlockVertex.java | 9 ++-- .../flywheel/core/vertex/BlockVertexList.java | 2 - src/main/resources/META-INF/mods.toml | 2 +- src/main/resources/pack.mcmeta | 2 +- 8 files changed, 44 insertions(+), 66 deletions(-) delete mode 100644 src/main/java/com/jozufozu/flywheel/core/model/ShadeSeparatedBufferBuilder.java diff --git a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java index 45b2e6f1a..158806e7a 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java @@ -1,6 +1,5 @@ package com.jozufozu.flywheel.core.model; -import java.lang.management.MemoryUsage; import java.nio.ByteBuffer; import java.util.function.Supplier; @@ -8,18 +7,17 @@ import org.lwjgl.system.MemoryUtil; import com.jozufozu.flywheel.api.vertex.VertexList; import com.jozufozu.flywheel.api.vertex.VertexType; -import com.jozufozu.flywheel.backend.gl.GlNumericType; -import com.jozufozu.flywheel.backend.gl.buffer.GlBuffer; import com.jozufozu.flywheel.backend.gl.buffer.GlBufferType; import com.jozufozu.flywheel.backend.gl.buffer.GlBufferUsage; import com.jozufozu.flywheel.backend.gl.buffer.MappedGlBuffer; import com.jozufozu.flywheel.backend.model.ElementBuffer; import com.jozufozu.flywheel.core.Formats; import com.jozufozu.flywheel.core.QuadConverter; +import com.jozufozu.flywheel.util.Pair; import com.mojang.blaze3d.platform.MemoryTracker; import com.mojang.blaze3d.vertex.BufferBuilder; +import com.mojang.blaze3d.vertex.BufferBuilder.RenderedBuffer; import com.mojang.blaze3d.vertex.PoseStack; -import com.mojang.blaze3d.vertex.VertexBuffer; import net.minecraft.client.Minecraft; import net.minecraft.client.resources.model.BakedModel; @@ -54,11 +52,10 @@ public class BlockModel implements Model { this(bufferable.build(), name); } - public BlockModel(ShadeSeparatedBufferBuilder buffer, String name) { + public BlockModel(Pair pair, String name) { this.name = name; - BufferBuilder.RenderedBuffer renderedBuffer = buffer.endOrDiscardIfEmpty(); - + RenderedBuffer renderedBuffer = pair.first(); if (renderedBuffer == null) { reader = null; eboSupplier = () -> null; @@ -67,7 +64,7 @@ public class BlockModel implements Model { BufferBuilder.DrawState drawState = renderedBuffer.drawState(); - reader = Formats.BLOCK.createReader(renderedBuffer, buffer.getUnshadedStartVertex()); + reader = Formats.BLOCK.createReader(renderedBuffer, pair.second()); if (drawState.sequentialIndex()) { ByteBuffer src = renderedBuffer.indexBuffer(); diff --git a/src/main/java/com/jozufozu/flywheel/core/model/Bufferable.java b/src/main/java/com/jozufozu/flywheel/core/model/Bufferable.java index 2c7c74a4a..e01fecd82 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/Bufferable.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/Bufferable.java @@ -1,6 +1,8 @@ package com.jozufozu.flywheel.core.model; +import com.jozufozu.flywheel.util.Pair; +import com.mojang.blaze3d.vertex.BufferBuilder.RenderedBuffer; import com.mojang.blaze3d.vertex.VertexConsumer; import net.minecraft.client.renderer.block.ModelBlockRenderer; @@ -12,7 +14,7 @@ import net.minecraft.util.RandomSource; public interface Bufferable { void bufferInto(ModelBlockRenderer renderer, VertexConsumer consumer, RandomSource random); - default ShadeSeparatedBufferBuilder build() { - return ModelUtil.getBufferBuilder(this); + default Pair build() { + return ModelUtil.getRenderedBuffer(this); } } diff --git a/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java b/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java index 26fc5859a..57d8aaeea 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java @@ -5,8 +5,11 @@ import java.util.Collection; import java.util.function.Supplier; import com.jozufozu.flywheel.Flywheel; +import com.jozufozu.flywheel.backend.model.BufferBuilderExtension; +import com.jozufozu.flywheel.util.Pair; import com.jozufozu.flywheel.util.transform.TransformStack; import com.mojang.blaze3d.vertex.BufferBuilder; +import com.mojang.blaze3d.vertex.BufferBuilder.RenderedBuffer; import com.mojang.blaze3d.vertex.DefaultVertexFormat; import com.mojang.blaze3d.vertex.PoseStack; import com.mojang.blaze3d.vertex.VertexFormat; @@ -53,7 +56,22 @@ public class ModelUtil { return dispatcher; } - public static ShadeSeparatedBufferBuilder getBufferBuilder(Bufferable bufferable) { + public static boolean isVirtual(ModelData data) { + return data.has(ModelUtil.VIRTUAL_PROPERTY) && data.get(ModelUtil.VIRTUAL_PROPERTY); + } + + public static Pair endShadeSeparated(BufferBuilder shadedBuilder, BufferBuilder unshadedBuilder) { + int unshadedStartVertex = ((BufferBuilderExtension) shadedBuilder).flywheel$getVertices(); + RenderedBuffer unshadedBuffer = unshadedBuilder.endOrDiscardIfEmpty(); + if (unshadedBuffer != null) { + // FIXME: Unshaded indices + ((BufferBuilderExtension) shadedBuilder).flywheel$appendBufferUnsafe(unshadedBuffer.vertexBuffer()); + } + RenderedBuffer buffer = shadedBuilder.endOrDiscardIfEmpty(); + return Pair.of(buffer, unshadedStartVertex); + } + + public static Pair getRenderedBuffer(Bufferable bufferable) { ModelBlockRenderer blockRenderer = VANILLA_RENDERER.getModelRenderer(); ThreadLocalObjects objects = THREAD_LOCAL_OBJECTS.get(); @@ -61,31 +79,29 @@ public class ModelUtil { bufferable.bufferInto(blockRenderer, objects.shadeSeparatingWrapper, objects.random); - objects.end(); - - return objects.separatedBufferBuilder; + return objects.end(); } - public static ShadeSeparatedBufferBuilder getBufferBuilder(BakedModel model, BlockState referenceState, PoseStack poseStack) { + public static Pair getBufferBuilder(BakedModel model, BlockState referenceState, PoseStack poseStack) { return new BakedModelBuilder(model).withReferenceState(referenceState) .withPoseStack(poseStack) .build(); } - public static ShadeSeparatedBufferBuilder getBufferBuilder(BlockAndTintGetter renderWorld, BakedModel model, BlockState referenceState, PoseStack poseStack) { + public static Pair getBufferBuilder(BlockAndTintGetter renderWorld, BakedModel model, BlockState referenceState, PoseStack poseStack) { return new BakedModelBuilder(model).withReferenceState(referenceState) .withPoseStack(poseStack) .withRenderWorld(renderWorld) .build(); } - public static ShadeSeparatedBufferBuilder getBufferBuilderFromTemplate(BlockAndTintGetter renderWorld, RenderType layer, Collection blocks) { + public static Pair getBufferBuilderFromTemplate(BlockAndTintGetter renderWorld, RenderType layer, Collection blocks) { return new WorldModelBuilder(layer).withRenderWorld(renderWorld) .withBlocks(blocks) .build(); } - public static ShadeSeparatedBufferBuilder getBufferBuilderFromTemplate(BlockAndTintGetter renderWorld, RenderType layer, Collection blocks, PoseStack poseStack) { + public static Pair getBufferBuilderFromTemplate(BlockAndTintGetter renderWorld, RenderType layer, Collection blocks, PoseStack poseStack) { return new WorldModelBuilder(layer).withRenderWorld(renderWorld) .withBlocks(blocks) .withPoseStack(poseStack) @@ -106,20 +122,18 @@ public class ModelUtil { private static class ThreadLocalObjects { public final RandomSource random = RandomSource.create(); public final ShadeSeparatingVertexConsumer shadeSeparatingWrapper = new ShadeSeparatingVertexConsumer(); - public final ShadeSeparatedBufferBuilder separatedBufferBuilder = new ShadeSeparatedBufferBuilder(512); + public final BufferBuilder shadedBuilder = new BufferBuilder(512); public final BufferBuilder unshadedBuilder = new BufferBuilder(512); private void begin() { - this.separatedBufferBuilder.begin(VertexFormat.Mode.QUADS, DefaultVertexFormat.BLOCK); + this.shadedBuilder.begin(VertexFormat.Mode.QUADS, DefaultVertexFormat.BLOCK); this.unshadedBuilder.begin(VertexFormat.Mode.QUADS, DefaultVertexFormat.BLOCK); - this.shadeSeparatingWrapper.prepare(this.separatedBufferBuilder, this.unshadedBuilder); + this.shadeSeparatingWrapper.prepare(this.shadedBuilder, this.unshadedBuilder); } - private void end() { + private Pair end() { this.shadeSeparatingWrapper.clear(); - this.unshadedBuilder.end(); - this.separatedBufferBuilder.appendUnshadedVertices(this.unshadedBuilder); - this.separatedBufferBuilder.end(); + return ModelUtil.endShadeSeparated(shadedBuilder, unshadedBuilder); } } } diff --git a/src/main/java/com/jozufozu/flywheel/core/model/ShadeSeparatedBufferBuilder.java b/src/main/java/com/jozufozu/flywheel/core/model/ShadeSeparatedBufferBuilder.java deleted file mode 100644 index 71a05d70f..000000000 --- a/src/main/java/com/jozufozu/flywheel/core/model/ShadeSeparatedBufferBuilder.java +++ /dev/null @@ -1,32 +0,0 @@ -package com.jozufozu.flywheel.core.model; - -import java.nio.ByteBuffer; - -import com.jozufozu.flywheel.backend.model.BufferBuilderExtension; -import com.mojang.blaze3d.vertex.BufferBuilder; -import com.mojang.datafixers.util.Pair; - -public class ShadeSeparatedBufferBuilder extends BufferBuilder { - protected int unshadedStartVertex; - - public ShadeSeparatedBufferBuilder(int capacity) { - super(capacity); - } - - public void appendUnshadedVertices(BufferBuilder unshadedBuilder) { - RenderedBuffer renderedBuffer = unshadedBuilder.endOrDiscardIfEmpty(); - - if (renderedBuffer == null) { - return; - } - - // FIXME: Unshaded indices - ByteBuffer buffer = renderedBuffer.vertexBuffer(); - unshadedStartVertex = ((BufferBuilderExtension) this).flywheel$getVertices(); - ((BufferBuilderExtension) this).flywheel$appendBufferUnsafe(buffer); - } - - public int getUnshadedStartVertex() { - return unshadedStartVertex; - } -} diff --git a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java index 1ac22ae94..c9c465ca7 100644 --- a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java +++ b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java @@ -6,10 +6,8 @@ import com.jozufozu.flywheel.api.vertex.VertexList; import com.jozufozu.flywheel.api.vertex.VertexType; import com.jozufozu.flywheel.core.layout.BufferLayout; import com.jozufozu.flywheel.core.layout.CommonItems; -import com.jozufozu.flywheel.core.model.ShadeSeparatedBufferBuilder; import com.mojang.blaze3d.vertex.BufferBuilder; import com.mojang.blaze3d.vertex.DefaultVertexFormat; -import com.mojang.datafixers.util.Pair; public class BlockVertex implements VertexType { @@ -72,10 +70,11 @@ Vertex FLWCreateVertex() { } ByteBuffer vertexBuffer = renderedBuffer.vertexBuffer(); - if (unshadedStartVertex > 0) { - return createReader(vertexBuffer, drawState.vertexCount(), unshadedStartVertex); + int vertexCount = drawState.vertexCount(); + if (unshadedStartVertex > 0 && unshadedStartVertex < vertexCount) { + return createReader(vertexBuffer, vertexCount, unshadedStartVertex); } else { - return createReader(vertexBuffer, drawState.vertexCount()); + return createReader(vertexBuffer, vertexCount); } } } diff --git a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertexList.java b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertexList.java index 654f94865..ef46bdf36 100644 --- a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertexList.java +++ b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertexList.java @@ -3,9 +3,7 @@ package com.jozufozu.flywheel.core.vertex; import java.nio.ByteBuffer; import com.jozufozu.flywheel.api.vertex.ShadedVertexList; -import com.jozufozu.flywheel.core.model.ShadeSeparatedBufferBuilder; import com.jozufozu.flywheel.util.RenderMath; -import com.mojang.blaze3d.vertex.BufferBuilder; public class BlockVertexList extends AbstractVertexList { diff --git a/src/main/resources/META-INF/mods.toml b/src/main/resources/META-INF/mods.toml index b06375677..9eedd54e7 100644 --- a/src/main/resources/META-INF/mods.toml +++ b/src/main/resources/META-INF/mods.toml @@ -1,5 +1,5 @@ modLoader = "javafml" -loaderVersion = "[40,)" +loaderVersion = "[41,)" issueTrackerURL = "https://github.com/Jozufozu/Flywheel/issues" license = "MIT" diff --git a/src/main/resources/pack.mcmeta b/src/main/resources/pack.mcmeta index 2d8d4da03..79cff50a3 100644 --- a/src/main/resources/pack.mcmeta +++ b/src/main/resources/pack.mcmeta @@ -1,6 +1,6 @@ { "pack": { "description": "Flywheel resources", - "pack_format": 8 + "pack_format": 9 } } From d51c373568625fa4deb9cf56efa0bbe6589f7078 Mon Sep 17 00:00:00 2001 From: PepperCode1 <44146161+PepperCode1@users.noreply.github.com> Date: Sat, 13 Aug 2022 23:26:39 -0700 Subject: [PATCH 04/11] 1.19.2 and more fixes - Update to 1.19.2 - Unbind VAO before restoring GL state - Shift RenderLayerEvent dispatching point after vanilla VBO and VAO clean-up - Fix BlockModel's check for an index buffer being inverted - The RenderedBuffer returned from ModelUtil#endShadeSeparated is no longer nullable - Allow unshadedStartVertex to be 0 - Remove BufferUploaderMixin - Fix PartialModel javadoc referencing the old bake event - Switch back to Parchment mappings --- build.gradle | 7 ++--- gradle.properties | 8 ++--- .../flywheel/backend/gl/GlStateTracker.java | 4 +++ .../jozufozu/flywheel/core/PartialModel.java | 2 +- .../flywheel/core/model/BlockModel.java | 9 +----- .../flywheel/core/model/ModelUtil.java | 2 +- .../flywheel/core/vertex/BlockVertex.java | 2 +- .../flywheel/mixin/BufferUploaderMixin.java | 30 ------------------- .../flywheel/mixin/LevelRendererMixin.java | 4 +-- src/main/resources/META-INF/mods.toml | 6 ++-- src/main/resources/flywheel.mixins.json | 1 - 11 files changed, 19 insertions(+), 56 deletions(-) delete mode 100644 src/main/java/com/jozufozu/flywheel/mixin/BufferUploaderMixin.java diff --git a/build.gradle b/build.gradle index 7431fc5b1..b7a987060 100644 --- a/build.gradle +++ b/build.gradle @@ -33,8 +33,7 @@ java.toolchain.languageVersion = JavaLanguageVersion.of(17) println('Java: ' + System.getProperty('java.version') + ' JVM: ' + System.getProperty('java.vm.version') + '(' + System.getProperty('java.vendor') + ') Arch: ' + System.getProperty('os.arch')) minecraft { -// mappings channel: 'parchment', version: "${parchment_version}-${minecraft_version}" - mappings channel: 'official', version: "${minecraft_version}" + mappings channel: 'parchment', version: "${parchment_version}-${minecraft_version}" runs { client { @@ -114,8 +113,8 @@ dependencies { // switch to implementation for debugging compileOnly fg.deobf("maven.modrinth:starlight-forge:1.0.2+1.18.2") - compileOnly fg.deobf("maven.modrinth:rubidium:0.5.2a") - compileOnly fg.deobf("curse.maven:oculus-581495:3821406") + compileOnly fg.deobf("maven.modrinth:rubidium:0.6.1") + compileOnly fg.deobf("maven.modrinth:oculus:1.19-1.2.5a") // https://discord.com/channels/313125603924639766/725850371834118214/910619168821354497 // Prevent Mixin annotation processor from getting into IntelliJ's annotation processor settings diff --git a/gradle.properties b/gradle.properties index ac6d2dace..52eec945d 100644 --- a/gradle.properties +++ b/gradle.properties @@ -3,10 +3,10 @@ org.gradle.daemon = false # mod version info mod_version = 0.6.5 -artifact_minecraft_version = 1.19 +artifact_minecraft_version = 1.19.2 -minecraft_version = 1.19 -forge_version = 41.0.94 +minecraft_version = 1.19.2 +forge_version = 43.0.8 # build dependency versions forgegradle_version = 5.1.53 @@ -14,7 +14,7 @@ mixingradle_version = 0.7-SNAPSHOT mixin_version = 0.8.5 librarian_version = 1.+ cursegradle_version = 1.4.0 -parchment_version = 2022.07.10 +parchment_version = 2022.08.10 # curseforge info projectId = 486392 diff --git a/src/main/java/com/jozufozu/flywheel/backend/gl/GlStateTracker.java b/src/main/java/com/jozufozu/flywheel/backend/gl/GlStateTracker.java index eec0a4cf8..22e7eabff 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/gl/GlStateTracker.java +++ b/src/main/java/com/jozufozu/flywheel/backend/gl/GlStateTracker.java @@ -44,6 +44,10 @@ public class GlStateTracker { public void restore() { GlBufferType[] values = GlBufferType.values(); + if (GlStateTracker.vao != 0) { + GlStateManager._glBindVertexArray(0); + } + for (int i = 0; i < values.length; i++) { if (buffers[i] != GlStateTracker.buffers[i]) { GlStateManager._glBindBuffer(values[i].glEnum, buffers[i]); diff --git a/src/main/java/com/jozufozu/flywheel/core/PartialModel.java b/src/main/java/com/jozufozu/flywheel/core/PartialModel.java index 526239b48..846c5cfbc 100644 --- a/src/main/java/com/jozufozu/flywheel/core/PartialModel.java +++ b/src/main/java/com/jozufozu/flywheel/core/PartialModel.java @@ -14,7 +14,7 @@ import net.minecraftforge.client.event.ModelEvent; * Creating a PartialModel will make the associated modelLocation automatically load. * PartialModels must be initialized during {@link net.minecraftforge.fml.event.lifecycle.FMLClientSetupEvent FMLClientSetupEvent}. *
- * Once {@link ModelBakeEvent} finishes, all PartialModels (with valid modelLocations) + * Once {@link ModelEvent.BakingCompleted} finishes, all PartialModels (with valid modelLocations) * will have their bakedModel fields populated. *
* Attempting to create a PartialModel after ModelRegistryEvent will cause an error. diff --git a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java index 158806e7a..63054a3ef 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java @@ -56,17 +56,10 @@ public class BlockModel implements Model { this.name = name; RenderedBuffer renderedBuffer = pair.first(); - if (renderedBuffer == null) { - reader = null; - eboSupplier = () -> null; - return; - } - BufferBuilder.DrawState drawState = renderedBuffer.drawState(); - reader = Formats.BLOCK.createReader(renderedBuffer, pair.second()); - if (drawState.sequentialIndex()) { + if (!drawState.sequentialIndex()) { ByteBuffer src = renderedBuffer.indexBuffer(); ByteBuffer indexBuffer = MemoryTracker.create(src.capacity()); MemoryUtil.memCopy(src, indexBuffer); diff --git a/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java b/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java index 57d8aaeea..4b58ba1e5 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/ModelUtil.java @@ -67,7 +67,7 @@ public class ModelUtil { // FIXME: Unshaded indices ((BufferBuilderExtension) shadedBuilder).flywheel$appendBufferUnsafe(unshadedBuffer.vertexBuffer()); } - RenderedBuffer buffer = shadedBuilder.endOrDiscardIfEmpty(); + RenderedBuffer buffer = shadedBuilder.end(); return Pair.of(buffer, unshadedStartVertex); } diff --git a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java index c9c465ca7..f65c59627 100644 --- a/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java +++ b/src/main/java/com/jozufozu/flywheel/core/vertex/BlockVertex.java @@ -71,7 +71,7 @@ Vertex FLWCreateVertex() { ByteBuffer vertexBuffer = renderedBuffer.vertexBuffer(); int vertexCount = drawState.vertexCount(); - if (unshadedStartVertex > 0 && unshadedStartVertex < vertexCount) { + if (unshadedStartVertex >= 0 && unshadedStartVertex < vertexCount) { return createReader(vertexBuffer, vertexCount, unshadedStartVertex); } else { return createReader(vertexBuffer, vertexCount); diff --git a/src/main/java/com/jozufozu/flywheel/mixin/BufferUploaderMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/BufferUploaderMixin.java deleted file mode 100644 index 92058feb9..000000000 --- a/src/main/java/com/jozufozu/flywheel/mixin/BufferUploaderMixin.java +++ /dev/null @@ -1,30 +0,0 @@ -package com.jozufozu.flywheel.mixin; - -import javax.annotation.Nullable; - -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.Inject; -import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; - -import com.jozufozu.flywheel.backend.gl.GlStateTracker; -import com.mojang.blaze3d.vertex.BufferUploader; -import com.mojang.blaze3d.vertex.VertexBuffer; -import com.mojang.blaze3d.vertex.VertexFormat; - -@Mixin(BufferUploader.class) -public class BufferUploaderMixin { - - @Shadow - @Nullable - private static VertexBuffer lastImmediateBuffer; - - @Inject(method = "reset", at = @At("HEAD")) - private static void stopBufferUploaderFromClearingBufferStateIfNothingIsBound(CallbackInfo ci) { - // Trust our tracker over BufferUploader's. - if (GlStateTracker.getVertexArray() == 0) { - lastImmediateBuffer = null; - } - } -} diff --git a/src/main/java/com/jozufozu/flywheel/mixin/LevelRendererMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/LevelRendererMixin.java index 497a81ee5..2d545d55b 100644 --- a/src/main/java/com/jozufozu/flywheel/mixin/LevelRendererMixin.java +++ b/src/main/java/com/jozufozu/flywheel/mixin/LevelRendererMixin.java @@ -16,7 +16,6 @@ import com.jozufozu.flywheel.core.crumbling.CrumblingRenderer; import com.jozufozu.flywheel.event.BeginFrameEvent; import com.jozufozu.flywheel.event.ReloadRenderersEvent; import com.jozufozu.flywheel.event.RenderLayerEvent; -import com.mojang.blaze3d.vertex.BufferUploader; import com.mojang.blaze3d.vertex.PoseStack; import com.mojang.math.Matrix4f; @@ -58,7 +57,7 @@ public class LevelRendererMixin { * This only gets injected if renderChunkLayer is not Overwritten */ @Group(name = "flywheel$renderLayer", min = 1, max = 2) - @Inject(at = @At(value = "INVOKE", target = "Lnet/minecraft/client/renderer/ShaderInstance;clear()V"), method = "renderChunkLayer") + @Inject(at = @At(value = "INVOKE", target = "Lnet/minecraft/util/profiling/ProfilerFiller;pop()V", ordinal = 1), method = "renderChunkLayer") private void renderLayer(RenderType type, PoseStack stack, double camX, double camY, double camZ, Matrix4f p_172999_, CallbackInfo ci) { flywheel$renderLayer(type, stack, camX, camY, camZ); flywheel$LayerRendered = true; @@ -74,7 +73,6 @@ public class LevelRendererMixin { flywheel$renderLayer(type, stack, camX, camY, camZ); } flywheel$LayerRendered = false; - BufferUploader.reset(); } @Unique diff --git a/src/main/resources/META-INF/mods.toml b/src/main/resources/META-INF/mods.toml index 9eedd54e7..7853aae43 100644 --- a/src/main/resources/META-INF/mods.toml +++ b/src/main/resources/META-INF/mods.toml @@ -1,5 +1,5 @@ modLoader = "javafml" -loaderVersion = "[41,)" +loaderVersion = "[43,)" issueTrackerURL = "https://github.com/Jozufozu/Flywheel/issues" license = "MIT" @@ -18,13 +18,13 @@ A modern engine for modded minecraft.''' [[dependencies.flywheel]] modId = "forge" mandatory = true -versionRange = "[41.0.0,)" +versionRange = "[43.0.0,)" ordering = "NONE" side = "CLIENT" [[dependencies.flywheel]] modId = "minecraft" mandatory = true -versionRange = "[1.19,1.20)" +versionRange = "[1.19.2,1.20)" ordering = "NONE" side = "CLIENT" diff --git a/src/main/resources/flywheel.mixins.json b/src/main/resources/flywheel.mixins.json index 284039b65..265b160c7 100644 --- a/src/main/resources/flywheel.mixins.json +++ b/src/main/resources/flywheel.mixins.json @@ -8,7 +8,6 @@ "BlockEntityRenderDispatcherAccessor", "BlockEntityTypeMixin", "BufferBuilderMixin", - "BufferUploaderMixin", "CameraMixin", "instancemanage.ChunkRebuildHooksMixin", "instancemanage.ChunkRenderDispatcherAccessor", From 9b56d16f55f16be0e342ac151c71c428acf5e61d Mon Sep 17 00:00:00 2001 From: Jozufozu Date: Fri, 2 Sep 2022 22:49:18 -0700 Subject: [PATCH 05/11] AAAAAAAAAAAAMD - Fixes issue rendering models in block format while using instancing on AMD - A very hacky fix, everything will be cleaner in 1.0 - Diagonalport flw.loadRenderDoc jvm arg from 1.18/culling --- build.gradle | 1 + .../backend/model/FallbackAllocator.java | 3 +- .../flywheel/backend/model/IndexedModel.java | 11 ++++++-- .../jozufozu/flywheel/core/model/Model.java | 1 - .../flywheel/mixin/ClientMainMixin.java | 28 +++++++++++++++++++ src/main/resources/flywheel.mixins.json | 13 +++++---- 6 files changed, 47 insertions(+), 10 deletions(-) create mode 100644 src/main/java/com/jozufozu/flywheel/mixin/ClientMainMixin.java diff --git a/build.gradle b/build.gradle index b7a987060..3bcd74b6e 100644 --- a/build.gradle +++ b/build.gradle @@ -44,6 +44,7 @@ minecraft { property 'mixin.debug.export', 'true' property 'mixin.env.remapRefMap', 'true' property 'mixin.env.refMapRemappingFile', "${projectDir}/build/createSrgToMcp/output.srg" + property 'flw.loadRenderDoc', 'true' arg '-mixin.config=flywheel.mixins.json' diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/FallbackAllocator.java b/src/main/java/com/jozufozu/flywheel/backend/model/FallbackAllocator.java index 7520afff2..42d1a67df 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/FallbackAllocator.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/FallbackAllocator.java @@ -1,5 +1,6 @@ package com.jozufozu.flywheel.backend.model; +import com.jozufozu.flywheel.core.Formats; import com.jozufozu.flywheel.core.model.Model; public enum FallbackAllocator implements ModelAllocator { @@ -7,7 +8,7 @@ public enum FallbackAllocator implements ModelAllocator { @Override public BufferedModel alloc(Model model, Callback allocationCallback) { - IndexedModel out = new IndexedModel(model); + IndexedModel out = new IndexedModel(model, Formats.POS_TEX_NORMAL); allocationCallback.onAlloc(out); return out; } diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java b/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java index 4052e569e..26d3672d1 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java @@ -20,6 +20,7 @@ import com.jozufozu.flywheel.core.model.Model; */ public class IndexedModel implements BufferedModel { + protected final VertexType type; protected final Model model; protected final GlPrimitive primitiveMode; protected ElementBuffer ebo; @@ -27,6 +28,11 @@ public class IndexedModel implements BufferedModel { protected boolean deleted; public IndexedModel(Model model) { + this(model, model.getType()); + } + + public IndexedModel(Model model, VertexType type) { + this.type = type; this.model = model; this.primitiveMode = GlPrimitive.TRIANGLES; @@ -38,7 +44,8 @@ public class IndexedModel implements BufferedModel { // mirror it in system memory, so we can write to it, and upload our model. try (MappedBuffer buffer = vbo.getBuffer()) { - model.writeInto(buffer.unwrap()); + type.createWriter(buffer.unwrap()) + .writeVertexList(model.getReader()); } catch (Exception e) { Flywheel.LOGGER.error(String.format("Error uploading model '%s':", model.name()), e); } @@ -81,7 +88,7 @@ public class IndexedModel implements BufferedModel { @Override public VertexType getType() { - return model.getType(); + return type; } public int getVertexCount() { diff --git a/src/main/java/com/jozufozu/flywheel/core/model/Model.java b/src/main/java/com/jozufozu/flywheel/core/model/Model.java index c93e1df84..72692a614 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/Model.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/Model.java @@ -6,7 +6,6 @@ import com.jozufozu.flywheel.api.vertex.VertexList; import com.jozufozu.flywheel.api.vertex.VertexType; import com.jozufozu.flywheel.backend.model.ElementBuffer; import com.jozufozu.flywheel.core.Formats; -import com.jozufozu.flywheel.core.QuadConverter; /** * A model that can be rendered by flywheel. diff --git a/src/main/java/com/jozufozu/flywheel/mixin/ClientMainMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/ClientMainMixin.java new file mode 100644 index 000000000..e753a1a83 --- /dev/null +++ b/src/main/java/com/jozufozu/flywheel/mixin/ClientMainMixin.java @@ -0,0 +1,28 @@ +package com.jozufozu.flywheel.mixin; + +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.injection.At; +import org.spongepowered.asm.mixin.injection.Inject; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; + +import net.minecraft.client.main.Main; + +@Mixin(Main.class) +public class ClientMainMixin { + + @Inject(method = "main", at = @At("HEAD")) + private static void injectRenderDoc(CallbackInfo ci) { + // Only try to load RenderDoc if a system property is set. + if (System.getProperty("flw.loadRenderDoc") == null) { + return; + } + + try { + System.loadLibrary("renderdoc"); + } catch (Throwable ignored) { + // Oh well, we tried. + // On Windows, RenderDoc installs to "C:\Program Files\RenderDoc\" + System.err.println("Is RenderDoc in your PATH?"); + } + } +} diff --git a/src/main/resources/flywheel.mixins.json b/src/main/resources/flywheel.mixins.json index 265b160c7..71d3f7495 100644 --- a/src/main/resources/flywheel.mixins.json +++ b/src/main/resources/flywheel.mixins.json @@ -9,24 +9,25 @@ "BlockEntityTypeMixin", "BufferBuilderMixin", "CameraMixin", - "instancemanage.ChunkRebuildHooksMixin", - "instancemanage.ChunkRenderDispatcherAccessor", "ClientLevelMixin", + "ClientMainMixin", "EntityTypeMixin", "FixFabulousDepthMixin", "FrustumMixin", "GlStateManagerMixin", - "instancemanage.InstanceAddMixin", - "instancemanage.InstanceRemoveMixin", "LevelRendererAccessor", "LevelRendererMixin", "PausedPartialTickAccessor", - "instancemanage.RenderChunkAccessor", - "instancemanage.RenderChunkMixin", "RenderTexturesMixin", "RenderTypeMixin", "atlas.AtlasDataMixin", "atlas.SheetDataAccessor", + "instancemanage.ChunkRebuildHooksMixin", + "instancemanage.ChunkRenderDispatcherAccessor", + "instancemanage.InstanceAddMixin", + "instancemanage.InstanceRemoveMixin", + "instancemanage.RenderChunkAccessor", + "instancemanage.RenderChunkMixin", "light.LightUpdateMixin", "light.NetworkLightUpdateMixin", "matrix.Matrix3fMixin", From 377c729355f2e3a24f3989ae89a9d414c1f3f932 Mon Sep 17 00:00:00 2001 From: Jozufozu Date: Sat, 24 Sep 2022 22:44:42 -0700 Subject: [PATCH 06/11] Yeetrium - Mixin to sodium to steal block entity rendering duties - Fixes z-fighting and inconsistent BE rendering --- build.gradle | 2 +- .../flywheel/mixin/LevelRendererMixin.java | 29 +-------- .../SodiumChunkRenderDataMixin.java | 60 +++++++++++++++++++ src/main/resources/flywheel.mixins.json | 1 + 4 files changed, 63 insertions(+), 29 deletions(-) create mode 100644 src/main/java/com/jozufozu/flywheel/mixin/instancemanage/SodiumChunkRenderDataMixin.java diff --git a/build.gradle b/build.gradle index 3bcd74b6e..bc973f5da 100644 --- a/build.gradle +++ b/build.gradle @@ -112,7 +112,7 @@ dependencies { minecraft "net.minecraftforge:forge:${minecraft_version}-${forge_version}" // switch to implementation for debugging - compileOnly fg.deobf("maven.modrinth:starlight-forge:1.0.2+1.18.2") + compileOnly fg.deobf("maven.modrinth:starlight-forge:1.1.1+1.19") compileOnly fg.deobf("maven.modrinth:rubidium:0.6.1") compileOnly fg.deobf("maven.modrinth:oculus:1.19-1.2.5a") diff --git a/src/main/java/com/jozufozu/flywheel/mixin/LevelRendererMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/LevelRendererMixin.java index f3838d4bc..9daf1d971 100644 --- a/src/main/java/com/jozufozu/flywheel/mixin/LevelRendererMixin.java +++ b/src/main/java/com/jozufozu/flywheel/mixin/LevelRendererMixin.java @@ -3,9 +3,7 @@ package com.jozufozu.flywheel.mixin; import org.spongepowered.asm.mixin.Final; import org.spongepowered.asm.mixin.Mixin; import org.spongepowered.asm.mixin.Shadow; -import org.spongepowered.asm.mixin.Unique; import org.spongepowered.asm.mixin.injection.At; -import org.spongepowered.asm.mixin.injection.Group; import org.spongepowered.asm.mixin.injection.Inject; import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; @@ -48,33 +46,8 @@ public class LevelRendererMixin { MinecraftForge.EVENT_BUS.post(new BeginFrameEvent(level, camera, frustum)); } - @Unique - private boolean flywheel$LayerRendered; - - /** - * This only gets injected if renderChunkLayer is not Overwritten - */ - @Group(name = "flywheel$renderLayer", min = 1, max = 2) - @Inject(at = @At(value = "INVOKE", target = "Lnet/minecraft/util/profiling/ProfilerFiller;pop()V", ordinal = 1), method = "renderChunkLayer") - private void renderLayer(RenderType type, PoseStack stack, double camX, double camY, double camZ, Matrix4f p_172999_, CallbackInfo ci) { - flywheel$renderLayer(type, stack, camX, camY, camZ); - flywheel$LayerRendered = true; - } - - /** - * This always gets injected. - */ - @Group(name = "flywheel$renderLayer") @Inject(at = @At("TAIL"), method = "renderChunkLayer") - private void renderLayerSodium(RenderType type, PoseStack stack, double camX, double camY, double camZ, Matrix4f p_172999_, CallbackInfo ci) { - if (!flywheel$LayerRendered) { - flywheel$renderLayer(type, stack, camX, camY, camZ); - } - flywheel$LayerRendered = false; - } - - @Unique - private void flywheel$renderLayer(RenderType type, PoseStack stack, double camX, double camY, double camZ) { + private void renderLayer(RenderType type, PoseStack stack, double camX, double camY, double camZ, Matrix4f p_172999_, CallbackInfo ci) { MinecraftForge.EVENT_BUS.post(new RenderLayerEvent(level, type, stack, renderBuffers, camX, camY, camZ)); } diff --git a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/SodiumChunkRenderDataMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/SodiumChunkRenderDataMixin.java new file mode 100644 index 000000000..55e7340f2 --- /dev/null +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/SodiumChunkRenderDataMixin.java @@ -0,0 +1,60 @@ +package com.jozufozu.flywheel.mixin.instancemanage; + +import java.util.ArrayList; +import java.util.List; + +import org.spongepowered.asm.mixin.Mixin; +import org.spongepowered.asm.mixin.Unique; +import org.spongepowered.asm.mixin.injection.At; +import org.spongepowered.asm.mixin.injection.Inject; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; +import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; + +import com.jozufozu.flywheel.backend.instancing.InstancedRenderDispatcher; +import com.jozufozu.flywheel.backend.instancing.InstancedRenderRegistry; + +import me.jellysquid.mods.sodium.client.render.chunk.data.ChunkRenderData; +import net.minecraft.world.level.Level; +import net.minecraft.world.level.block.entity.BlockEntity; +import net.minecraftforge.api.distmarker.Dist; +import net.minecraftforge.api.distmarker.OnlyIn; + +@OnlyIn(Dist.CLIENT) +@Mixin(targets = "me.jellysquid.mods.sodium.client.render.chunk.data.ChunkRenderData$Builder", remap = false) +public class SodiumChunkRenderDataMixin { + + @Unique + private List flywheel$blockEntities; + @Unique + private Level flywheel$level; + + @Inject(method = "addBlockEntity", at = @At("HEAD"), cancellable = true, require = 0) + private void flywheel$onAddBlockEntity(BlockEntity be, boolean cull, CallbackInfo ci) { + if (InstancedRenderRegistry.canInstance(be.getType())) { + if (flywheel$blockEntities == null) { + flywheel$blockEntities = new ArrayList<>(); + } + + if (flywheel$level == null) { + flywheel$level = be.getLevel(); + } + + // Collect BEs in a temporary list to avoid excessive synchronization in InstancedRenderDispatcher. + flywheel$blockEntities.add(be); + } + + if (InstancedRenderRegistry.shouldSkipRender(be)) { + ci.cancel(); + } + } + + @Inject(method = "build", at = @At("HEAD")) + private void flywheel$onBuild(CallbackInfoReturnable cir) { + if (flywheel$level == null || flywheel$blockEntities == null) { + return; + } + + InstancedRenderDispatcher.getBlockEntities(flywheel$level) + .queueAddAll(flywheel$blockEntities); + } +} diff --git a/src/main/resources/flywheel.mixins.json b/src/main/resources/flywheel.mixins.json index 71d3f7495..149c7bd63 100644 --- a/src/main/resources/flywheel.mixins.json +++ b/src/main/resources/flywheel.mixins.json @@ -28,6 +28,7 @@ "instancemanage.InstanceRemoveMixin", "instancemanage.RenderChunkAccessor", "instancemanage.RenderChunkMixin", + "instancemanage.SodiumChunkRenderDataMixin", "light.LightUpdateMixin", "light.NetworkLightUpdateMixin", "matrix.Matrix3fMixin", From ccbcaf9e3ff20a0a236d085ad89a60023fb564e2 Mon Sep 17 00:00:00 2001 From: Jozufozu Date: Sun, 25 Sep 2022 17:17:57 -0700 Subject: [PATCH 07/11] Fixinum - Fix missing chunks when backend is off and sodium installed. - Fix crashes when used with iris. --- .../SodiumChunkRenderDataMixin.java | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/SodiumChunkRenderDataMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/SodiumChunkRenderDataMixin.java index 55e7340f2..d2ec94a62 100644 --- a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/SodiumChunkRenderDataMixin.java +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/SodiumChunkRenderDataMixin.java @@ -10,6 +10,7 @@ import org.spongepowered.asm.mixin.injection.Inject; import org.spongepowered.asm.mixin.injection.callback.CallbackInfo; import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable; +import com.jozufozu.flywheel.backend.Backend; import com.jozufozu.flywheel.backend.instancing.InstancedRenderDispatcher; import com.jozufozu.flywheel.backend.instancing.InstancedRenderRegistry; @@ -30,15 +31,19 @@ public class SodiumChunkRenderDataMixin { @Inject(method = "addBlockEntity", at = @At("HEAD"), cancellable = true, require = 0) private void flywheel$onAddBlockEntity(BlockEntity be, boolean cull, CallbackInfo ci) { + if (flywheel$level == null) { + flywheel$level = be.getLevel(); + } + + if (!Backend.canUseInstancing(flywheel$level)) { + return; + } + if (InstancedRenderRegistry.canInstance(be.getType())) { if (flywheel$blockEntities == null) { flywheel$blockEntities = new ArrayList<>(); } - if (flywheel$level == null) { - flywheel$level = be.getLevel(); - } - // Collect BEs in a temporary list to avoid excessive synchronization in InstancedRenderDispatcher. flywheel$blockEntities.add(be); } @@ -50,7 +55,7 @@ public class SodiumChunkRenderDataMixin { @Inject(method = "build", at = @At("HEAD")) private void flywheel$onBuild(CallbackInfoReturnable cir) { - if (flywheel$level == null || flywheel$blockEntities == null) { + if (flywheel$level == null || flywheel$blockEntities == null || !Backend.canUseInstancing(flywheel$level)) { return; } From adcb61526b2923f309cb61abf10309b9fcd62eb5 Mon Sep 17 00:00:00 2001 From: PepperCode1 <44146161+PepperCode1@users.noreply.github.com> Date: Wed, 28 Sep 2022 20:04:04 -0700 Subject: [PATCH 08/11] Fix crash with Optifine - Bump version --- gradle.properties | 2 +- .../flywheel/mixin/instancemanage/RenderChunkMixin.java | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/gradle.properties b/gradle.properties index 000483ab0..034e0c254 100644 --- a/gradle.properties +++ b/gradle.properties @@ -2,7 +2,7 @@ org.gradle.jvmargs = -Xmx3G org.gradle.daemon = false # mod version info -mod_version = 0.6.6 +mod_version = 0.6.7 artifact_minecraft_version = 1.19.2 minecraft_version = 1.19.2 diff --git a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkMixin.java b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkMixin.java index 987d7e8e7..3c42d337c 100644 --- a/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkMixin.java +++ b/src/main/java/com/jozufozu/flywheel/mixin/instancemanage/RenderChunkMixin.java @@ -10,7 +10,7 @@ import net.minecraft.client.renderer.chunk.ChunkRenderDispatcher; @Mixin(ChunkRenderDispatcher.RenderChunk.class) public class RenderChunkMixin implements com.jozufozu.flywheel.util.RenderChunkExtension { - @Shadow + @Shadow(aliases = "this$0") // Optifine does not use the obfuscated name so the mapped name must be included as an alias @Final private ChunkRenderDispatcher this$0; From 9280ae50ddb51775d66e9966c7572007d1988c51 Mon Sep 17 00:00:00 2001 From: Jozufozu Date: Sat, 22 Oct 2022 12:36:13 -0700 Subject: [PATCH 09/11] State your state - Address a few bugs with rubidium - Ignore EBOs when restoring state - ElementBuffer deals in raw gl handles - Document all state changes/restores/resets Co-authored-by: PepperCode1 <44146161+peppercode1@users.noreply.github.com> --- .../flywheel/backend/gl/GlStateTracker.java | 4 +- .../instancing/instancing/GPUInstancer.java | 5 + .../instancing/InstancedMaterialGroup.java | 23 +++-- .../instancing/InstancingEngine.java | 1 + .../flywheel/backend/model/ElementBuffer.java | 26 ++--- .../flywheel/backend/model/IndexedModel.java | 13 ++- .../flywheel/backend/model/ModelPool.java | 10 +- .../flywheel/backend/model/VBOModel.java | 1 + .../jozufozu/flywheel/core/QuadConverter.java | 94 +++++++++---------- .../core/crumbling/CrumblingGroup.java | 1 + .../core/crumbling/CrumblingRenderer.java | 5 + .../flywheel/core/model/BlockModel.java | 14 ++- .../jozufozu/flywheel/core/model/Model.java | 1 + 13 files changed, 114 insertions(+), 84 deletions(-) diff --git a/src/main/java/com/jozufozu/flywheel/backend/gl/GlStateTracker.java b/src/main/java/com/jozufozu/flywheel/backend/gl/GlStateTracker.java index e63897fc6..77749e8c7 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/gl/GlStateTracker.java +++ b/src/main/java/com/jozufozu/flywheel/backend/gl/GlStateTracker.java @@ -39,7 +39,7 @@ public class GlStateTracker { return new State(BUFFERS.clone(), vao, program); } - public static record State(int[] buffers, int vao, int program) { + public record State(int[] buffers, int vao, int program) { public void restore() { if (vao != GlStateTracker.vao) { GlStateManager._glBindVertexArray(vao); @@ -48,7 +48,7 @@ public class GlStateTracker { GlBufferType[] values = GlBufferType.values(); for (int i = 0; i < values.length; i++) { - if (buffers[i] != GlStateTracker.BUFFERS[i]) { + if (buffers[i] != GlStateTracker.BUFFERS[i] && values[i] != GlBufferType.ELEMENT_ARRAY_BUFFER) { GlStateManager._glBindBuffer(values[i].glEnum, buffers[i]); } } diff --git a/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/GPUInstancer.java b/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/GPUInstancer.java index 4b469c02f..a127b8e30 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/GPUInstancer.java +++ b/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/GPUInstancer.java @@ -45,6 +45,7 @@ public class GPUInstancer extends AbstractInstancer { public void render() { if (invalid()) return; + // XXX VAO is bound and not reset or restored vao.bind(); renderSetup(); @@ -68,12 +69,15 @@ public class GPUInstancer extends AbstractInstancer { vao = new GlVertexArray(); + // XXX Callback seems unnecessary. Remove and extract code to run after alloc call? model = modelAllocator.alloc(modelData, arenaModel -> { + // XXX VAO is bound and not reset or restored vao.bind(); arenaModel.setupState(vao); }); + // XXX VAO is already guaranteed to be bound in model callback vao.bind(); vao.enableArrays(model.getAttributeCount() + instanceFormat.getAttributeCount()); @@ -108,6 +112,7 @@ public class GPUInstancer extends AbstractInstancer { removeDeletedInstances(); } + // XXX ARRAY_BUFFER is bound and reset instanceVBO.bind(); if (!realloc()) { diff --git a/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/InstancedMaterialGroup.java b/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/InstancedMaterialGroup.java index 2bc228ed9..b132596ca 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/InstancedMaterialGroup.java +++ b/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/InstancedMaterialGroup.java @@ -68,15 +68,23 @@ public class InstancedMaterialGroup

implements MaterialG return vertexCount; } + // XXX Overriden in CrumblingGroup + // XXX Runs inside of restore state public void render(Matrix4f viewProjection, double camX, double camY, double camZ, RenderLayer layer) { type.setupRenderState(); - Textures.bindActiveTextures(); - renderAll(viewProjection, camX, camY, camZ, layer); + Textures.bindActiveTextures(); // XXX Changes active unit and bound textures + renderAll(viewProjection, camX, camY, camZ, layer); // XXX May change ARRAY_BUFFER binding (reset or not reset), VAO binding (not reset), shader binding (not reset), call Model.createEBO type.clearRenderState(); + // XXX Should texture bindings be reset or restored? + // XXX Should the active unit be reset or restored? + // XXX Should the VAO binding be reset or restored? + // XXX Should the ARRAY_BUFFER binding be reset or restored? + // XXX Should the shader binding be reset or restored? } + // XXX Internal GL state changes are inconsistent; sometimes bindings are reset to 0, sometimes not protected void renderAll(Matrix4f viewProjection, double camX, double camY, double camZ, RenderLayer layer) { - initializeInstancers(); + initializeInstancers(); // XXX May change ARRAY_BUFFER binding (reset or not reset), VAO binding (not reset), call Model.createEBO vertexCount = 0; instanceCount = 0; @@ -88,6 +96,7 @@ public class InstancedMaterialGroup

implements MaterialG P program = owner.context.getProgram(ProgramContext.create(entry.getKey() .getProgramSpec(), Formats.POS_TEX_NORMAL, layer)); + // XXX Shader is bound and not reset or restored program.bind(); program.uploadViewProjection(viewProjection); program.uploadCameraPos(camX, camY, camZ); @@ -95,7 +104,7 @@ public class InstancedMaterialGroup

implements MaterialG setup(program); for (GPUInstancer instancer : material.getAllInstancers()) { - instancer.render(); + instancer.render(); // XXX May change VAO binding (not reset), ARRAY_BUFFER binding (reset) vertexCount += instancer.getVertexCount(); instanceCount += instancer.getInstanceCount(); } @@ -103,19 +112,19 @@ public class InstancedMaterialGroup

implements MaterialG } private void initializeInstancers() { - ModelAllocator allocator = getModelAllocator(); + ModelAllocator allocator = getModelAllocator(); // XXX May change ARRAY_BUFFER binding (not reset) // initialize all uninitialized instancers... for (InstancedMaterial material : materials.values()) { for (GPUInstancer instancer : material.uninitialized) { - instancer.init(allocator); + instancer.init(allocator); // XXX May change VAO binding (not reset), ARRAY_BUFFER binding (not reset), call Model.createEBO } material.uninitialized.clear(); } if (allocator instanceof ModelPool pool) { // ...and then flush the model arena in case anything was marked for upload - pool.flush(); + pool.flush(); // XXX May change ARRAY_BUFFER binding (reset) } } diff --git a/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/InstancingEngine.java b/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/InstancingEngine.java index 5e8c30a54..2708f474d 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/InstancingEngine.java +++ b/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/InstancingEngine.java @@ -74,6 +74,7 @@ public class InstancingEngine

implements Engine { */ @Override public void render(TaskEngine taskEngine, RenderLayerEvent event) { + // XXX Restore state GlStateTracker.State restoreState = GlStateTracker.getRestoreState(); double camX; diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/ElementBuffer.java b/src/main/java/com/jozufozu/flywheel/backend/model/ElementBuffer.java index aba15457b..07ce772d3 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/ElementBuffer.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/ElementBuffer.java @@ -1,27 +1,29 @@ package com.jozufozu.flywheel.backend.model; -import com.jozufozu.flywheel.backend.gl.GlNumericType; -import com.jozufozu.flywheel.backend.gl.buffer.GlBuffer; -import com.mojang.blaze3d.vertex.VertexBuffer; +import com.jozufozu.flywheel.backend.gl.buffer.GlBufferType; import com.mojang.blaze3d.vertex.VertexFormat; public class ElementBuffer { - private final GlBuffer buffer; - public final int elementCount; - public final VertexFormat.IndexType eboIndexType; + protected final int elementCount; + protected final VertexFormat.IndexType eboIndexType; + private final int glBuffer; - public ElementBuffer(GlBuffer backing, int elementCount, VertexFormat.IndexType indexType) { - this.buffer = backing; - this.eboIndexType = indexType; + public ElementBuffer(int backing, int elementCount, VertexFormat.IndexType indexType) { this.elementCount = elementCount; + this.eboIndexType = indexType; + this.glBuffer = backing; } public void bind() { - buffer.bind(); + GlBufferType.ELEMENT_ARRAY_BUFFER.bind(glBuffer); } - public void unbind() { - buffer.unbind(); + public int getElementCount() { + return elementCount; + } + + public VertexFormat.IndexType getEboIndexType() { + return eboIndexType; } } diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java b/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java index 26d3672d1..580ded8b5 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/IndexedModel.java @@ -59,27 +59,26 @@ public class IndexedModel implements BufferedModel { * The VBO/VAO should be bound externally. */ public void setupState(GlVertexArray vao) { + // XXX ARRAY_BUFFER is bound and not reset or restored vbo.bind(); vao.enableArrays(getAttributeCount()); vao.bindAttributes(0, getType().getLayout()); + ebo.bind(); } @Override public void drawCall() { - ebo.bind(); - GL20.glDrawElements(primitiveMode.glEnum, ebo.elementCount, ebo.eboIndexType.asGLType, 0); + GL20.glDrawElements(primitiveMode.glEnum, ebo.getElementCount(), ebo.getEboIndexType().asGLType, 0); } /** - * Draws many instances of this model, assuming the appropriate state is already bound. - */ + * Draws many instances of this model, assuming the appropriate state is already bound. + */ @Override public void drawInstances(int instanceCount) { if (!valid()) return; - ebo.bind(); - - GL31.glDrawElementsInstanced(primitiveMode.glEnum, ebo.elementCount, ebo.eboIndexType.asGLType, 0, instanceCount); + GL31.glDrawElementsInstanced(primitiveMode.glEnum, ebo.getElementCount(), ebo.getEboIndexType().asGLType, 0, instanceCount); } public boolean isDeleted() { diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/ModelPool.java b/src/main/java/com/jozufozu/flywheel/backend/model/ModelPool.java index d9ce70838..3d7d330e5 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/ModelPool.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/ModelPool.java @@ -42,6 +42,7 @@ public class ModelPool implements ModelAllocator { vbo = new MappedGlBuffer(GlBufferType.ARRAY_BUFFER); + // XXX ARRAY_BUFFER is bound and not reset or restored vbo.bind(); vbo.setGrowthMargin(stride * 64); } @@ -68,6 +69,7 @@ public class ModelPool implements ModelAllocator { if (dirty) { if (anyToRemove) processDeletions(); + // XXX ARRAY_BUFFER is bound and reset vbo.bind(); if (realloc()) { uploadAll(); @@ -182,25 +184,25 @@ public class ModelPool implements ModelAllocator { @Override public void setupState(GlVertexArray vao) { + // XXX ARRAY_BUFFER is bound and not reset or restored vbo.bind(); vao.enableArrays(getAttributeCount()); vao.bindAttributes(0, vertexType.getLayout()); + ebo.bind(); } @Override public void drawCall() { - GL32.glDrawElementsBaseVertex(GlPrimitive.TRIANGLES.glEnum, ebo.elementCount, ebo.eboIndexType.asGLType, 0, first); + GL32.glDrawElementsBaseVertex(GlPrimitive.TRIANGLES.glEnum, ebo.getElementCount(), ebo.getEboIndexType().asGLType, 0, first); } @Override public void drawInstances(int instanceCount) { if (!valid()) return; - ebo.bind(); - //Backend.log.info(StringUtil.args("drawElementsInstancedBaseVertex", GlPrimitive.TRIANGLES, ebo.elementCount, ebo.eboIndexType, 0, instanceCount, first)); - GL32.glDrawElementsInstancedBaseVertex(GlPrimitive.TRIANGLES.glEnum, ebo.elementCount, ebo.eboIndexType.asGLType, 0, instanceCount, first); + GL32.glDrawElementsInstancedBaseVertex(GlPrimitive.TRIANGLES.glEnum, ebo.getElementCount(), ebo.getEboIndexType().asGLType, 0, instanceCount, first); } @Override diff --git a/src/main/java/com/jozufozu/flywheel/backend/model/VBOModel.java b/src/main/java/com/jozufozu/flywheel/backend/model/VBOModel.java index 54dccbd28..e51832a63 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/model/VBOModel.java +++ b/src/main/java/com/jozufozu/flywheel/backend/model/VBOModel.java @@ -58,6 +58,7 @@ public class VBOModel implements BufferedModel { * The VBO/VAO should be bound externally. */ public void setupState(GlVertexArray vao) { + // XXX ARRAY_BUFFER is bound and not reset or restored vbo.bind(); vao.enableArrays(getAttributeCount()); vao.bindAttributes(0, getLayout()); diff --git a/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java b/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java index 6e461b019..37ba431b7 100644 --- a/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java +++ b/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java @@ -1,21 +1,21 @@ package com.jozufozu.flywheel.core; -import java.nio.Buffer; -import java.nio.ByteBuffer; -import java.nio.ByteOrder; - import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; +import org.lwjgl.opengl.GL32; +import org.lwjgl.opengl.GL32C; import org.lwjgl.system.MemoryUtil; import com.jozufozu.flywheel.backend.gl.GlNumericType; import com.jozufozu.flywheel.backend.gl.buffer.GlBufferType; -import com.jozufozu.flywheel.backend.gl.buffer.MappedBuffer; -import com.jozufozu.flywheel.backend.gl.buffer.MappedGlBuffer; +import com.jozufozu.flywheel.backend.gl.buffer.GlBufferUsage; import com.jozufozu.flywheel.backend.model.ElementBuffer; import com.jozufozu.flywheel.event.ReloadRenderersEvent; import com.mojang.blaze3d.vertex.VertexFormat; +import it.unimi.dsi.fastutil.ints.Int2ReferenceArrayMap; +import it.unimi.dsi.fastutil.ints.Int2ReferenceMap; + /** * A class to manage EBOs that index quads as triangles. */ @@ -37,76 +37,74 @@ public class QuadConverter { return INSTANCE; } - private final MappedGlBuffer ebo; + private final Int2ReferenceMap cache = new Int2ReferenceArrayMap<>(); + private final int ebo; private int quadCapacity; public QuadConverter() { - this.ebo = new MappedGlBuffer(GlBufferType.ELEMENT_ARRAY_BUFFER); + this.ebo = GL32.glGenBuffers(); this.quadCapacity = 0; } public ElementBuffer quads2Tris(int quads) { - int indexCount = quads * 6; - if (quads > quadCapacity) { - ebo.bind(); - ebo.ensureCapacity((long) indexCount * GlNumericType.UINT.getByteWidth()); - - try (MappedBuffer map = ebo.getBuffer()) { - ByteBuffer indices = map.unwrap(); - - fillBuffer(indices, quads); - } - ebo.unbind(); - - this.quadCapacity = quads; + grow(quads * 2); } - return new ElementBuffer(ebo, indexCount, VertexFormat.IndexType.INT); + return cache.computeIfAbsent(quads, this::createElementBuffer); + } + + @NotNull + private ElementBuffer createElementBuffer(int quads) { + return new ElementBuffer(ebo, quads * 6, VertexFormat.IndexType.INT); + } + + private void grow(int quads) { + int byteSize = quads * 6 * GlNumericType.UINT.getByteWidth(); + final long ptr = MemoryUtil.nmemAlloc(byteSize); + + fillBuffer(ptr, quads); + + // XXX ARRAY_BUFFER is bound and reset + final var bufferType = GlBufferType.ARRAY_BUFFER; + final int oldBuffer = bufferType.getBoundBuffer(); + bufferType.bind(ebo); + GL32C.nglBufferData(bufferType.glEnum, byteSize, ptr, GlBufferUsage.STATIC_DRAW.glEnum); + bufferType.bind(oldBuffer); + + MemoryUtil.nmemFree(ptr); + + this.quadCapacity = quads; } public void delete() { - ebo.delete(); + GL32.glDeleteBuffers(ebo); this.quadCapacity = 0; } - private void fillBuffer(ByteBuffer indices, int quads) { - long addr = MemoryUtil.memAddress(indices); + private void fillBuffer(long ptr, int quads) { int numVertices = 4 * quads; int baseVertex = 0; while (baseVertex < numVertices) { - // writeQuadIndices(indices, baseVertex); - writeQuadIndicesUnsafe(addr, baseVertex); + writeQuadIndicesUnsafe(ptr, baseVertex); baseVertex += 4; - addr += 6 * 4; + ptr += 6 * 4; } - // ((Buffer) indices).flip(); } - private void writeQuadIndices(ByteBuffer indices, int baseVertex) { + private void writeQuadIndicesUnsafe(long ptr, int baseVertex) { // triangle a - indices.putInt(baseVertex); - indices.putInt(baseVertex + 1); - indices.putInt(baseVertex + 2); + MemoryUtil.memPutInt(ptr, baseVertex); + MemoryUtil.memPutInt(ptr + 4, baseVertex + 1); + MemoryUtil.memPutInt(ptr + 8, baseVertex + 2); // triangle b - indices.putInt(baseVertex); - indices.putInt(baseVertex + 2); - indices.putInt(baseVertex + 3); + MemoryUtil.memPutInt(ptr + 12, baseVertex); + MemoryUtil.memPutInt(ptr + 16, baseVertex + 2); + MemoryUtil.memPutInt(ptr + 20, baseVertex + 3); } - private void writeQuadIndicesUnsafe(long addr, int baseVertex) { - // triangle a - MemoryUtil.memPutInt(addr, baseVertex); - MemoryUtil.memPutInt(addr + 4, baseVertex + 1); - MemoryUtil.memPutInt(addr + 8, baseVertex + 2); - // triangle b - MemoryUtil.memPutInt(addr + 12, baseVertex); - MemoryUtil.memPutInt(addr + 16, baseVertex + 2); - MemoryUtil.memPutInt(addr + 20, baseVertex + 3); - } - - // make sure this gets reset first so it has a chance to repopulate + // make sure this gets reset first, so it has a chance to repopulate public static void onRendererReload(ReloadRenderersEvent event) { if (INSTANCE != null) { INSTANCE.delete(); diff --git a/src/main/java/com/jozufozu/flywheel/core/crumbling/CrumblingGroup.java b/src/main/java/com/jozufozu/flywheel/core/crumbling/CrumblingGroup.java index ee113de17..0378b6ee6 100644 --- a/src/main/java/com/jozufozu/flywheel/core/crumbling/CrumblingGroup.java +++ b/src/main/java/com/jozufozu/flywheel/core/crumbling/CrumblingGroup.java @@ -18,6 +18,7 @@ public class CrumblingGroup

extends InstancedMateria super(owner, type); } + // XXX See notes of overriden method @Override public void render(Matrix4f viewProjection, double camX, double camY, double camZ, RenderLayer layer) { type.setupRenderState(); diff --git a/src/main/java/com/jozufozu/flywheel/core/crumbling/CrumblingRenderer.java b/src/main/java/com/jozufozu/flywheel/core/crumbling/CrumblingRenderer.java index e15e91a4e..1455eb25e 100644 --- a/src/main/java/com/jozufozu/flywheel/core/crumbling/CrumblingRenderer.java +++ b/src/main/java/com/jozufozu/flywheel/core/crumbling/CrumblingRenderer.java @@ -65,6 +65,7 @@ public class CrumblingRenderer { Vec3 cameraPos = camera.getPosition(); + // XXX Restore state GlStateTracker.State restoreState = GlStateTracker.getRestoreState(); CrumblingRenderer.renderBreaking(activeStages, new RenderLayerEvent(level, null, stack, null, cameraPos.x, cameraPos.y, cameraPos.z)); restoreState.restore(); @@ -87,6 +88,7 @@ public class CrumblingRenderer { instanceManager.beginFrame(SerialTaskEngine.INSTANCE, info); + // XXX Each call applies another restore state even though we are already inside of a restore state materials.render(SerialTaskEngine.INSTANCE, event); instanceManager.invalidate(); @@ -94,6 +96,9 @@ public class CrumblingRenderer { } + // XXX Inconsistent GL state cleanup + // If texture binding and active unit need to be restored, store them in variables before GL state is changed + // instead of guessing that unit 0 and crumbling tex 0 are correct GlTextureUnit.T0.makeActive(); AbstractTexture breaking = textureManager.getTexture(ModelBakery.BREAKING_LOCATIONS.get(0)); if (breaking != null) RenderSystem.bindTexture(breaking.getId()); diff --git a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java index 63054a3ef..583eaeaab 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java @@ -3,13 +3,14 @@ package com.jozufozu.flywheel.core.model; import java.nio.ByteBuffer; import java.util.function.Supplier; +import org.lwjgl.opengl.GL15; +import org.lwjgl.opengl.GL32; import org.lwjgl.system.MemoryUtil; import com.jozufozu.flywheel.api.vertex.VertexList; import com.jozufozu.flywheel.api.vertex.VertexType; import com.jozufozu.flywheel.backend.gl.buffer.GlBufferType; import com.jozufozu.flywheel.backend.gl.buffer.GlBufferUsage; -import com.jozufozu.flywheel.backend.gl.buffer.MappedGlBuffer; import com.jozufozu.flywheel.backend.model.ElementBuffer; import com.jozufozu.flywheel.core.Formats; import com.jozufozu.flywheel.core.QuadConverter; @@ -64,10 +65,15 @@ public class BlockModel implements Model { ByteBuffer indexBuffer = MemoryTracker.create(src.capacity()); MemoryUtil.memCopy(src, indexBuffer); eboSupplier = () -> { + int vbo = GL32.glGenBuffers(); - MappedGlBuffer vbo = new MappedGlBuffer(GlBufferType.ELEMENT_ARRAY_BUFFER, GlBufferUsage.STATIC_DRAW); - - vbo.upload(indexBuffer); + // XXX ARRAY_BUFFER is bound and restored + var bufferType = GlBufferType.ARRAY_BUFFER; + var oldBuffer = bufferType.getBoundBuffer(); + bufferType.bind(vbo); + GL15.glBufferData(bufferType.glEnum, indexBuffer, GlBufferUsage.STATIC_DRAW.glEnum); + bufferType.bind(oldBuffer); + MemoryUtil.memFree(indexBuffer); return new ElementBuffer(vbo, drawState.indexCount(), drawState.indexType()); }; diff --git a/src/main/java/com/jozufozu/flywheel/core/model/Model.java b/src/main/java/com/jozufozu/flywheel/core/model/Model.java index 72692a614..ebe6dee47 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/Model.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/Model.java @@ -45,6 +45,7 @@ public interface Model { return Formats.POS_TEX_NORMAL; } + // XXX Since this is public API (technically) we cannot make assumptions about what GL state this method can use or modify unless a contract is established. /** * Create an element buffer object that indexes the vertices of this model. * From f47f547930f682d4d841112f1e5713dc0a40a266 Mon Sep 17 00:00:00 2001 From: PepperCode1 <44146161+PepperCode1@users.noreply.github.com> Date: Sun, 6 Nov 2022 14:00:24 -0800 Subject: [PATCH 10/11] Models are temporary - Add Model.delete - Allow BlockModel.createEBO to be called more than once for a single instance - Clear cache on QuadConverter.delete --- .../instancing/instancing/GPUInstancer.java | 3 +- .../jozufozu/flywheel/core/QuadConverter.java | 1 + .../flywheel/core/hardcoded/ModelPart.java | 11 +++ .../flywheel/core/model/BlockModel.java | 81 +++++++++++++++---- .../jozufozu/flywheel/core/model/Model.java | 2 + 5 files changed, 79 insertions(+), 19 deletions(-) diff --git a/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/GPUInstancer.java b/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/GPUInstancer.java index a127b8e30..d3522ac81 100644 --- a/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/GPUInstancer.java +++ b/src/main/java/com/jozufozu/flywheel/backend/instancing/instancing/GPUInstancer.java @@ -69,7 +69,6 @@ public class GPUInstancer extends AbstractInstancer { vao = new GlVertexArray(); - // XXX Callback seems unnecessary. Remove and extract code to run after alloc call? model = modelAllocator.alloc(modelData, arenaModel -> { // XXX VAO is bound and not reset or restored vao.bind(); @@ -77,7 +76,7 @@ public class GPUInstancer extends AbstractInstancer { arenaModel.setupState(vao); }); - // XXX VAO is already guaranteed to be bound in model callback + // XXX VAO is bound and not reset or restored vao.bind(); vao.enableArrays(model.getAttributeCount() + instanceFormat.getAttributeCount()); diff --git a/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java b/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java index 37ba431b7..266f15489 100644 --- a/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java +++ b/src/main/java/com/jozufozu/flywheel/core/QuadConverter.java @@ -79,6 +79,7 @@ public class QuadConverter { public void delete() { GL32.glDeleteBuffers(ebo); + this.cache.clear(); this.quadCapacity = 0; } diff --git a/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java b/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java index d67ca22d3..a0c8978bc 100644 --- a/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java +++ b/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java @@ -59,4 +59,15 @@ public class ModelPart implements Model { return QuadConverter.getInstance() .quads2Tris(vertices / 4); } + + @Override + public void delete() { + if (reader instanceof AutoCloseable closeable) { + try { + closeable.close(); + } catch (Exception e) { + // + } + } + } } diff --git a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java index 583eaeaab..176763966 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java @@ -19,6 +19,7 @@ import com.mojang.blaze3d.platform.MemoryTracker; import com.mojang.blaze3d.vertex.BufferBuilder; import com.mojang.blaze3d.vertex.BufferBuilder.RenderedBuffer; import com.mojang.blaze3d.vertex.PoseStack; +import com.mojang.blaze3d.vertex.VertexFormat.IndexType; import net.minecraft.client.Minecraft; import net.minecraft.client.resources.model.BakedModel; @@ -32,7 +33,7 @@ public class BlockModel implements Model { private final String name; - private final Supplier eboSupplier; + private final EBOSupplier eboSupplier; public BlockModel(BlockState state) { this(Minecraft.getInstance() @@ -61,22 +62,7 @@ public class BlockModel implements Model { reader = Formats.BLOCK.createReader(renderedBuffer, pair.second()); if (!drawState.sequentialIndex()) { - ByteBuffer src = renderedBuffer.indexBuffer(); - ByteBuffer indexBuffer = MemoryTracker.create(src.capacity()); - MemoryUtil.memCopy(src, indexBuffer); - eboSupplier = () -> { - int vbo = GL32.glGenBuffers(); - - // XXX ARRAY_BUFFER is bound and restored - var bufferType = GlBufferType.ARRAY_BUFFER; - var oldBuffer = bufferType.getBoundBuffer(); - bufferType.bind(vbo); - GL15.glBufferData(bufferType.glEnum, indexBuffer, GlBufferUsage.STATIC_DRAW.glEnum); - bufferType.bind(oldBuffer); - MemoryUtil.memFree(indexBuffer); - - return new ElementBuffer(vbo, drawState.indexCount(), drawState.indexType()); - }; + eboSupplier = new BufferEBOSupplier(renderedBuffer.indexBuffer(), drawState.indexCount(), drawState.indexType()); } else { eboSupplier = () -> QuadConverter.getInstance() .quads2Tris(vertexCount() / 4); @@ -107,4 +93,65 @@ public class BlockModel implements Model { public VertexType getType() { return Formats.BLOCK; } + + @Override + public void delete() { + if (reader instanceof AutoCloseable closeable) { + try { + closeable.close(); + } catch (Exception e) { + // + } + } + eboSupplier.delete(); + } + + private interface EBOSupplier extends Supplier { + default void delete() { + } + } + + private static class BufferEBOSupplier implements EBOSupplier { + private final ByteBuffer indexBuffer; + private final int indexCount; + private final IndexType indexType; + + private int eboName = -1; + private ElementBuffer ebo; + + public BufferEBOSupplier(ByteBuffer indexBufferSrc, int indexCount, IndexType indexType) { + indexBuffer = MemoryTracker.create(indexBufferSrc.capacity()); + MemoryUtil.memCopy(indexBufferSrc, indexBuffer); + this.indexCount = indexCount; + this.indexType = indexType; + } + + @Override + public ElementBuffer get() { + if (eboName == -1) { + eboName = createEBO(); + ebo = new ElementBuffer(eboName, indexCount, indexType); + MemoryUtil.memFree(indexBuffer); + } + + return ebo; + } + + private int createEBO() { + int vbo = GL32.glGenBuffers(); + + // XXX ARRAY_BUFFER is bound and restored + var bufferType = GlBufferType.ARRAY_BUFFER; + var oldBuffer = bufferType.getBoundBuffer(); + bufferType.bind(vbo); + GL15.glBufferData(bufferType.glEnum, indexBuffer, GlBufferUsage.STATIC_DRAW.glEnum); + bufferType.bind(oldBuffer); + return vbo; + } + + @Override + public void delete() { + GL32.glDeleteBuffers(eboName); + } + } } diff --git a/src/main/java/com/jozufozu/flywheel/core/model/Model.java b/src/main/java/com/jozufozu/flywheel/core/model/Model.java index ebe6dee47..b2e47c01d 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/Model.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/Model.java @@ -58,6 +58,8 @@ public interface Model { */ ElementBuffer createEBO(); + void delete(); + /** * The size in bytes that this model's data takes up. */ From 88135d8715d292bddc12e63511125e6e23f2efc6 Mon Sep 17 00:00:00 2001 From: PepperCode1 <44146161+PepperCode1@users.noreply.github.com> Date: Thu, 10 Nov 2022 16:56:23 -0800 Subject: [PATCH 11/11] Tiniest of discrepancies - Re-add default implementation of Model#createEBO - Remove old commented methods in VirtualChunk - Update Forge --- build.gradle | 2 +- gradle.properties | 2 +- .../flywheel/core/hardcoded/ModelPart.java | 8 ---- .../flywheel/core/model/BlockModel.java | 1 - .../jozufozu/flywheel/core/model/Model.java | 6 ++- .../flywheel/core/virtual/VirtualChunk.java | 37 ------------------- 6 files changed, 7 insertions(+), 49 deletions(-) diff --git a/build.gradle b/build.gradle index bc973f5da..50025979e 100644 --- a/build.gradle +++ b/build.gradle @@ -202,6 +202,6 @@ curseforge { changelog = file('changelog.txt') releaseType = project.curse_type mainArtifact jar - addGameVersion '1.19' + addGameVersion '1.19.2' } } diff --git a/gradle.properties b/gradle.properties index d2d98e349..f6642f3c5 100644 --- a/gradle.properties +++ b/gradle.properties @@ -6,7 +6,7 @@ mod_version = 0.6.8 artifact_minecraft_version = 1.19.2 minecraft_version = 1.19.2 -forge_version = 43.0.8 +forge_version = 43.1.23 # build dependency versions forgegradle_version = 5.1.53 diff --git a/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java b/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java index d318471cd..25546213e 100644 --- a/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java +++ b/src/main/java/com/jozufozu/flywheel/core/hardcoded/ModelPart.java @@ -4,9 +4,7 @@ import java.util.List; import com.jozufozu.flywheel.api.vertex.VertexList; import com.jozufozu.flywheel.api.vertex.VertexType; -import com.jozufozu.flywheel.backend.model.ElementBuffer; import com.jozufozu.flywheel.core.Formats; -import com.jozufozu.flywheel.core.QuadConverter; import com.jozufozu.flywheel.core.model.Model; import com.jozufozu.flywheel.core.vertex.PosTexNormalWriterUnsafe; import com.mojang.blaze3d.platform.MemoryTracker; @@ -60,12 +58,6 @@ public class ModelPart implements Model { return Formats.POS_TEX_NORMAL; } - @Override - public ElementBuffer createEBO() { - return QuadConverter.getInstance() - .quads2Tris(vertices / 4); - } - @Override public void delete() { if (reader instanceof AutoCloseable closeable) { diff --git a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java index 676913648..61df69354 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/BlockModel.java @@ -32,7 +32,6 @@ public class BlockModel implements Model { private final VertexList reader; private final String name; - private final EBOSupplier eboSupplier; public BlockModel(BlockState state) { diff --git a/src/main/java/com/jozufozu/flywheel/core/model/Model.java b/src/main/java/com/jozufozu/flywheel/core/model/Model.java index bbf320e7f..b0d31a15f 100644 --- a/src/main/java/com/jozufozu/flywheel/core/model/Model.java +++ b/src/main/java/com/jozufozu/flywheel/core/model/Model.java @@ -5,6 +5,7 @@ import java.nio.ByteBuffer; import com.jozufozu.flywheel.api.vertex.VertexList; import com.jozufozu.flywheel.api.vertex.VertexType; import com.jozufozu.flywheel.backend.model.ElementBuffer; +import com.jozufozu.flywheel.core.QuadConverter; /** * A model that can be rendered by flywheel. @@ -53,7 +54,10 @@ public interface Model { *

* @return an element buffer object indexing this model's vertices. */ - ElementBuffer createEBO(); + default ElementBuffer createEBO() { + return QuadConverter.getInstance() + .quads2Tris(vertexCount() / 4); + } void delete(); diff --git a/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualChunk.java b/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualChunk.java index 32d0d9fad..5b0027bb9 100644 --- a/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualChunk.java +++ b/src/main/java/com/jozufozu/flywheel/core/virtual/VirtualChunk.java @@ -192,43 +192,6 @@ public class VirtualChunk extends ChunkAccess { return null; } -// @Override -// @Nullable -// public StructureStart getStartForFeature(ConfiguredStructureFeature pStructure) { -// return null; -// } -// -// @Override -// public void setStartForFeature(ConfiguredStructureFeature pStructure, StructureStart pStart) { -// } -// -// @Override -// public Map, StructureStart> getAllStarts() { -// return Collections.emptyMap(); -// } -// -// @Override -// public void setAllStarts(Map, StructureStart> pStructureStarts) { -// } -// -// @Override -// public LongSet getReferencesForFeature(ConfiguredStructureFeature pStructure) { -// return LongSets.emptySet(); -// } -// -// @Override -// public void addReferenceForFeature(ConfiguredStructureFeature pStructure, long pReference) { -// } -// -// @Override -// public Map, LongSet> getAllReferences() { -// return Collections.emptyMap(); -// } -// -// @Override -// public void setAllReferences(Map, LongSet> pStructureReferences) { -// } - @Override @Nullable public StructureStart getStartForStructure(Structure structure) {