Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,15 @@

## Not yet usable or functional, don't try.

Rewrite of the previous rewrite, targeting NeoForge/MC 1.21.5.
Rewrite of the previous rewrite, targeting NeoForge/MC 1.21.6.

This Minecraft mod extends Minecraft height and depth to be nearly infinite (at least a million blocks).

For the most up-to-date information about this mod and its related mods, as well as the newest downloads, please join us on the [**Cubic Chunks Discord**](https://discord.gg/kMfWg9m).

### Cubic Chunks (CC) - Links:

Github - [Cubic Chunks - 1.21.5 and above](https://github.com/OpenCubicChunks/CubicChunks3)
Github - [Cubic Chunks - 1.21.6 and above](https://github.com/OpenCubicChunks/CubicChunks3)
Github - [Cubic Chunks - 1.12.2 and lower](https://github.com/OpenCubicChunks/CubicChunks)

### Cloning the repository
Expand Down
10 changes: 5 additions & 5 deletions gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -6,20 +6,20 @@ org.gradle.debug=false
## Environment Properties
# You can find the latest versions here: https://projects.neoforged.net/neoforged/neoforge
# The Minecraft version must agree with the Neo version to get a valid artifact
minecraft_version=1.21.5
minecraft_version=1.21.6
# The Minecraft version range can use any release version of Minecraft as bounds.
# Snapshots, pre-releases, and release candidates are not guaranteed to sort properly
# as they do not follow standard versioning conventions.
minecraft_version_range=[1.21.5,1.21.6)
minecraft_version_range=[1.21.6,1.21.7)
# The Neo version must agree with the Minecraft version to get a valid artifact
neo_version=21.5.75
neo_version=21.6.4-beta
# The Neo version range can use any version of Neo as bounds
neo_version_range=[21.5,)
neo_version_range=[21.6,)
# The loader version range can only use the major version of FML as bounds
loader_version_range=[4,)

parchment_minecraft_version=1.21.5
parchment_mappings_version=2025.04.19
parchment_mappings_version=2025.06.15

## Mod Properties

Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package io.github.opencubicchunks.cubicchunks.client.renderer.chunk;

import io.github.notstirred.dasm.api.annotations.Dasm;
import io.github.opencubicchunks.cubicchunks.mixin.dasmsets.ChunkToCubeSet;
import io.github.opencubicchunks.cubicchunks.util.asm.FactoryFromConstructor;
import io.github.opencubicchunks.cubicchunks.world.level.cube.LevelCube;
import net.minecraft.client.renderer.chunk.SectionCopy;

@Dasm(ChunkToCubeSet.class)
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Don't need the @dasm, maybe remove or leave as @Dasm({})?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

oh yep, forgot to remove when switching to @FactoryFromConstructor

public interface CCSectionCopy {
// Factory method for constructor that's added to SectionCopy by DASM
@FactoryFromConstructor
static SectionCopy cc_create(LevelCube wrapped, int sectionIndex) {
throw new IllegalStateException("FactoryFromConstructor failed to apply");
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
@ParametersAreNonnullByDefault
@MethodsReturnNonnullByDefault
package io.github.opencubicchunks.cubicchunks.client.renderer.cube;
package io.github.opencubicchunks.cubicchunks.client.renderer.chunk;

import javax.annotation.ParametersAreNonnullByDefault;

Expand Down

This file was deleted.

This file was deleted.

This file was deleted.

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
package io.github.opencubicchunks.cubicchunks.mixin.core.client.renderer.chunk;

import io.github.opencubicchunks.cubicchunks.client.renderer.chunk.CCSectionCopy;
import org.spongepowered.asm.mixin.Mixin;

// Needed for FactoryFromConstructor to apply
@Mixin(CCSectionCopy.class)
public interface MixinCCSectionCopy {}
Original file line number Diff line number Diff line change
@@ -1,73 +1,41 @@
package io.github.opencubicchunks.cubicchunks.mixin.core.client.renderer.chunk;

import javax.annotation.Nullable;

import io.github.opencubicchunks.cc_core.api.CubePos;
import io.github.opencubicchunks.cc_core.utils.Coords;
import io.github.opencubicchunks.cubicchunks.client.renderer.cube.CubicRenderRegionCache;
import io.github.opencubicchunks.cubicchunks.client.renderer.cube.RenderCube;
import io.github.opencubicchunks.cubicchunks.client.renderer.cube.RenderCubeRegion;
import io.github.opencubicchunks.cubicchunks.client.renderer.cube.RenderRegionCacheCubeInfo;
import io.github.opencubicchunks.cubicchunks.CanBeCubic;
import io.github.opencubicchunks.cubicchunks.client.renderer.chunk.CCSectionCopy;
import io.github.opencubicchunks.cubicchunks.world.level.CubicLevel;
import io.github.opencubicchunks.cubicchunks.world.level.cube.LevelCube;
import it.unimi.dsi.fastutil.longs.Long2ObjectMap;
import it.unimi.dsi.fastutil.longs.Long2ObjectOpenHashMap;
import net.minecraft.client.renderer.chunk.RenderChunk;
import net.minecraft.client.renderer.chunk.RenderChunkRegion;
import net.minecraft.client.renderer.chunk.RenderRegionCache;
import net.minecraft.client.renderer.chunk.RenderSectionRegion;
import net.minecraft.client.renderer.chunk.SectionCopy;
import net.minecraft.client.renderer.chunk.SectionRenderDispatcher;
import net.minecraft.core.SectionPos;
import net.minecraft.world.level.Level;
import net.minecraft.world.level.chunk.LevelChunk;
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.CallbackInfoReturnable;

// TODO rewrite javadoc for 1.21.6
/**
* The vanilla {@link RenderRegionCache} caches {@link LevelChunk}s and {@link RenderChunk}s while rebuilding
* The vanilla {@link RenderRegionCache} caches {@link SectionCopy}s while rebuilding
* {@link SectionRenderDispatcher.RenderSection}s
* and has a method for creating a {@link RenderChunkRegion} for a given {@link SectionPos}.
* and has a method for creating a {@link RenderSectionRegion} for a given {@link SectionPos}.
* <p/>
* We modify it by additionally caching {@link LevelCube}s and {@link RenderCube}s, and adding an equivalent method to create a
* {@link RenderCubeRegion} for a given {@link SectionPos}.
* We simply modify it to get section data from cubes instead of chunks in cubic levels.
*/
@Mixin(RenderRegionCache.class)
public abstract class MixinRenderRegionCache implements CubicRenderRegionCache {
@Shadow private final Long2ObjectMap<RenderRegionCacheCubeInfo> chunkInfoCache = new Long2ObjectOpenHashMap<>();

// TODO can we possibly do this with DASM + mixin? probably not?
@Override public @Nullable RenderCubeRegion cc_createRegion(Level level, SectionPos sectionPos, boolean nullForEmpty) {
int centerCubeX = Coords.sectionToCube(sectionPos.getX());
int centerCubeY = Coords.sectionToCube(sectionPos.getY());
int centerCubeZ = Coords.sectionToCube(sectionPos.getZ());
var centerCubeInfo = this.cc_getChunkInfo(level, centerCubeX, centerCubeY, centerCubeZ);
// if (nullForEmpty && centerCubeInfo.cube().isSectionEmpty(sectionPos.y())) { // TODO need a proper isSectionEmpty on CubeAccess
// return null;
// }
int cubeStartX = centerCubeX - 1;
int cubeStartY = centerCubeY - 1;
int cubeStartZ = centerCubeZ - 1;
int cubeEndX = centerCubeX + 1;
int cubeEndY = centerCubeY + 1;
int cubeEndZ = centerCubeZ + 1;
RenderCube[] renderCubes = new RenderCube[RenderCubeRegion.CUBE_COUNT];

for (int cubeX = cubeStartX; cubeX <= cubeEndX; ++cubeX) {
for (int cubeY = cubeStartY; cubeY <= cubeEndY; ++cubeY) {
for (int cubeZ = cubeStartZ; cubeZ <= cubeEndZ; ++cubeZ) {
int cubeIndex = RenderCubeRegion.index(cubeStartX, cubeStartY, cubeStartZ, cubeX, cubeY, cubeZ);
var cubeInfo = cubeX == centerCubeX && cubeY == centerCubeY && cubeZ == centerCubeZ ? centerCubeInfo
: this.cc_getChunkInfo(level, cubeX, cubeY, cubeZ);
renderCubes[cubeIndex] = cubeInfo.renderCube();
}
}
public abstract class MixinRenderRegionCache {
// Note the order of the individual sectionPos axes is weird (x,z,y) due to it being based on usage order within the vanilla lambda
// To avoid brittleness we ignore these parameters and use the captured sectionPos long instead.
@Inject(method = "lambda$getSectionDataCopy$0", at = @At("HEAD"), cancellable = true)
private static void cc_onGetSectionDataCopy(
Level level, int unusedSectionX, int unusedSectionZ, int unusedSectionY, long sectionPosLong, CallbackInfoReturnable<SectionCopy> cir
) {
if (((CanBeCubic) level).cc_isCubic()) {
var sectionPos = SectionPos.of(sectionPosLong);
var cube = ((CubicLevel) level).cc_getCube(Coords.sectionToCube(sectionPos.getX()), Coords.sectionToCube(sectionPos.getY()),
Coords.sectionToCube(sectionPos.getZ()));
cir.setReturnValue(CCSectionCopy.cc_create(cube, Coords.sectionToIndex(sectionPos.getX(), sectionPos.getY(), sectionPos.getZ())));
}

var modelDataManager = level.getModelDataManager().snapshotSectionRegion(cubeStartX, cubeStartY, cubeStartZ, cubeEndX, cubeEndY, cubeEndZ);
return new RenderCubeRegion(level, cubeStartX, cubeStartY, cubeStartZ, renderCubes, modelDataManager);
}

private RenderRegionCacheCubeInfo cc_getChunkInfo(Level level, int cubeX, int cubeY, int cubeZ) {
return this.chunkInfoCache.computeIfAbsent(CubePos.asLong(cubeX, cubeY, cubeZ), cubePosLong -> new RenderRegionCacheCubeInfo(
((CubicLevel) level).cc_getCube(CubePos.extractX(cubePosLong), CubePos.extractY(cubePosLong), CubePos.extractZ(cubePosLong))));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
package io.github.opencubicchunks.cubicchunks.mixin.core.client.renderer.chunk;

import io.github.notstirred.dasm.api.annotations.Dasm;
import io.github.notstirred.dasm.api.annotations.redirect.redirects.AddFieldToSets;
import io.github.notstirred.dasm.api.annotations.redirect.redirects.AddTransformToSets;
import io.github.notstirred.dasm.api.annotations.selector.FieldSig;
import io.github.notstirred.dasm.api.annotations.selector.MethodSig;
import io.github.notstirred.dasm.api.annotations.selector.Ref;
import io.github.notstirred.dasm.api.annotations.transform.TransformFromMethod;
import io.github.opencubicchunks.cubicchunks.exception.DasmFailedToApply;
import io.github.opencubicchunks.cubicchunks.mixin.dasmsets.ChunkToCubeSet;
import io.github.opencubicchunks.cubicchunks.world.level.cube.LevelCube;
import net.minecraft.client.renderer.chunk.SectionCopy;
import net.minecraft.world.level.chunk.LevelChunk;
import net.minecraft.world.level.chunk.LevelChunkSection;
import org.spongepowered.asm.mixin.Mixin;

/**
* The vanilla {@link SectionCopy} stores block data of a {@link LevelChunkSection} and is used for rendering that section.
* We simply add a constructor that creates the {@code SectionCopy} from a cube instead of a chunk.
*/
@Dasm(value = ChunkToCubeSet.class, target = @Ref(SectionCopy.class))
@Mixin(SectionCopy.class)
public class MixinSectionCopy {
// TODO is this field on the vanilla class actually used anywhere? based on snowblower output not having it, it seems like neoforge is adding it?
@AddFieldToSets(containers = ChunkToCubeSet.SectionCopy_redirects.class, field = @FieldSig(type = @Ref(LevelChunk.class), name = "wrapped"))
final LevelCube cc_wrapped;

@AddTransformToSets(ChunkToCubeSet.SectionCopy_redirects.class)
@TransformFromMethod(@MethodSig("<init>(Lnet/minecraft/world/level/chunk/LevelChunk;I)V"))
public MixinSectionCopy(LevelCube wrapped, int sectionIndex) {
throw new DasmFailedToApply();
}
}
Loading