mirror of
https://github.com/wisplite/crystalline-sky.git
synced 2026-10-30 13:32:18 -05:00
Skybox I
basic functioning on fabric
This commit is contained in:
@@ -1,4 +1,4 @@
|
||||
// 1.21.1 2026-04-16T11:05:11.823836864 Crystalline Sky/Model Definitions
|
||||
// 1.21.1 2026-04-25T02:02:19.160711408 Crystalline Sky/Model Definitions
|
||||
e832366c216102270b75085db7a7169881b853b3 assets/crystalline_sky/blockstates/sky.json
|
||||
0ac5351c3a01e0f9e76517452918e12770b3b54b assets/crystalline_sky/models/block/sky_light_14.json
|
||||
ee9cb7604922cdb2ad71d021a593ca82f0baf493 assets/crystalline_sky/models/block/sky_light_03.json
|
||||
@@ -12,6 +12,8 @@ ef9e5aca345b59cb4692a7bcfaac539aed6f6889 assets/crystalline_sky/models/block/sky
|
||||
2ce612b8445da92c6cecd07bd5364a25bcfb127f assets/crystalline_sky/models/block/sky_light_05.json
|
||||
ef5afdbcc8401a27029b6f0a29fa1117761c620d assets/crystalline_sky/models/item/sky_light.json
|
||||
59463cef438e58b137e5ce27402acf42a3a0ae87 assets/crystalline_sky/models/block/sky_light_02.json
|
||||
2763952a1919802e34f0976b023fc7b486456b91 assets/crystalline_sky/models/item/skybox_test.json
|
||||
9f63a1dc282986e15f9b22bee0ab0a2eaf4f994d assets/crystalline_sky/models/block/skybox_test.json
|
||||
c0d693e4f78ce15c238909130382909abda4c922 assets/crystalline_sky/models/block/sky_light_08.json
|
||||
008a0d0a76a34d8f375fa355452a5d0f93f9af3b assets/crystalline_sky/models/item/sky.json
|
||||
508ffb97ee711b53767b9d33659596197f69ee20 assets/crystalline_sky/models/block/weeping_sky_light.json
|
||||
@@ -31,14 +33,15 @@ fceb0c59b7f6d431200764ccf87596541bacb17f assets/crystalline_sky/models/block/sky
|
||||
e2c7bebd9eca446bb06fff866ec4d4996917e7e4 assets/crystalline_sky/models/block/sky_light_12.json
|
||||
04f1e4eba184b8e7b1669fc61006e3d00e09d164 assets/crystalline_sky/models/item/sky_light_11.json
|
||||
58349dc5dedb8016fb0bc958fcd4a9ccde13a1cd assets/crystalline_sky/models/item/sky_light_14.json
|
||||
03e2eb768bc34fbeaabffbff8ed3a2a3044a6db1 assets/crystalline_sky/blockstates/weeping_sky.json
|
||||
51fa40ff02afcec303e7a18478cbae5375dfb140 assets/crystalline_sky/models/item/sky_light_04.json
|
||||
03e2eb768bc34fbeaabffbff8ed3a2a3044a6db1 assets/crystalline_sky/blockstates/weeping_sky.json
|
||||
7c7d944714b5bcbee6a7e8014599ade8fbc5e804 assets/crystalline_sky/models/block/weeping_sky.json
|
||||
dff33a68a694de0f3ef177886c002204ffe49a8c assets/crystalline_sky/models/item/sky_light_07.json
|
||||
b29c14f77a08da7a6994cff4c6801d6f04b12ec0 assets/crystalline_sky/models/item/sky_light_03.json
|
||||
a87d8988452529a1f5af5662ad636223fdd98fec assets/crystalline_sky/models/block/sky_light_15.json
|
||||
be0be7e1d7ce1ccabed01ef09c6499a2a7f2b132 assets/crystalline_sky/models/item/weeping_sky_light.json
|
||||
d500e56057c0c2f3c948894694e2826f1726fd9e assets/crystalline_sky/models/item/sky_light_15.json
|
||||
662d2389357e6f00a3a59042d08aec47df9c2c10 assets/crystalline_sky/blockstates/skybox_test.json
|
||||
9f0d9fe5dfb05bbe18177db5c40e600c5b256858 assets/crystalline_sky/models/item/sky_light_00.json
|
||||
3183aeb9fff78d0c65f1ddd0dfb599420573e281 assets/crystalline_sky/models/block/sky_light_00.json
|
||||
04fb705807dd052f00ff861343ebe6fe0a78ca41 assets/crystalline_sky/models/block/sky.json
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
// 1.21.1 2026-04-16T11:05:11.822516104 Crystalline Sky/Tags for minecraft:block
|
||||
// 1.21.1 2026-04-25T02:02:19.159567873 Crystalline Sky/Tags for minecraft:block
|
||||
1389c0b812f7a6e4d5dd00edac1dc07beb5f9552 data/crystalline_sky/tags/block/sky_light_emitters.json
|
||||
606477607a09045ff2830cbc036e744d6a728bbd data/minecraft/tags/block/crystal_sound_blocks.json
|
||||
|
||||
@@ -1,3 +1,3 @@
|
||||
// 1.21.1 2026-04-16T11:05:11.825012592 Crystalline Sky/Block Loot Tables
|
||||
// 1.21.1 2026-04-25T02:02:19.161914767 Crystalline Sky/Block Loot Tables
|
||||
337de0acfc1b9b86adde0705e342ed1d4b5c9c4e data/crystalline_sky/loot_table/blocks/weeping_sky.json
|
||||
6a9b7a08424cbd3d699dfd3252d432517254aa45 data/crystalline_sky/loot_table/blocks/sky.json
|
||||
|
||||
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"variants": {
|
||||
"": {
|
||||
"model": "crystalline_sky:block/skybox_test"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
{
|
||||
"parent": "minecraft:block/cube_all",
|
||||
"crystalline_sky:atlas": "crystalline_sky:textures/atlas/skyboxes.png",
|
||||
"render_type": "crystalline_sky:skybox",
|
||||
"textures": {
|
||||
"all": "crystalline_sky:crystalline_sky_skybox/skybox_test"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
{
|
||||
"parent": "minecraft:item/generated",
|
||||
"textures": {
|
||||
"layer0": "crystalline_sky:block/skybox_test"
|
||||
}
|
||||
}
|
||||
+22
@@ -0,0 +1,22 @@
|
||||
package io.github.slimeistdev.crystalline_sky.mixin.client;
|
||||
|
||||
import com.google.gson.JsonObject;
|
||||
import com.llamalad7.mixinextras.injector.wrapoperation.Operation;
|
||||
import com.llamalad7.mixinextras.injector.wrapoperation.WrapOperation;
|
||||
import net.minecraft.client.renderer.block.model.BlockModel;
|
||||
import net.minecraft.resources.ResourceLocation;
|
||||
import org.objectweb.asm.Opcodes;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
|
||||
@Mixin(BlockModel.Deserializer.class)
|
||||
public class BlockModelDeserializerMixin {
|
||||
@WrapOperation(method = "getTextureMap", at = @At(value = "FIELD", target = "Lnet/minecraft/client/renderer/texture/TextureAtlas;LOCATION_BLOCKS:Lnet/minecraft/resources/ResourceLocation;", opcode = Opcodes.GETSTATIC))
|
||||
private ResourceLocation modifyAtlas(Operation<ResourceLocation> original, JsonObject json) {
|
||||
if (json.has("crystalline_sky:atlas")) {
|
||||
return ResourceLocation.parse(json.get("crystalline_sky:atlas").getAsString());
|
||||
} else {
|
||||
return original.call();
|
||||
}
|
||||
}
|
||||
}
|
||||
+50
-3
@@ -2,21 +2,42 @@ package io.github.slimeistdev.crystalline_sky.mixin.client;
|
||||
|
||||
import com.llamalad7.mixinextras.injector.wrapoperation.Operation;
|
||||
import com.llamalad7.mixinextras.injector.wrapoperation.WrapOperation;
|
||||
import com.mojang.blaze3d.vertex.DefaultVertexFormat;
|
||||
import com.mojang.datafixers.util.Pair;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.client.CrystallineShaderInstances;
|
||||
import net.minecraft.client.renderer.ShaderInstance;
|
||||
import net.minecraft.client.Camera;
|
||||
import net.minecraft.client.DeltaTracker;
|
||||
import net.minecraft.client.Minecraft;
|
||||
import net.minecraft.client.renderer.GameRenderer;
|
||||
import com.mojang.blaze3d.vertex.DefaultVertexFormat;
|
||||
import net.minecraft.client.renderer.LevelRenderer;
|
||||
import net.minecraft.client.renderer.LightTexture;
|
||||
import net.minecraft.client.renderer.ShaderInstance;
|
||||
import net.minecraft.server.packs.resources.ResourceProvider;
|
||||
import org.joml.Matrix4f;
|
||||
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 java.io.IOException;
|
||||
import java.util.List;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import static io.github.slimeistdev.crystalline_sky.util.SharedRenderVariables.invSkyboxMat;
|
||||
|
||||
@Mixin(GameRenderer.class)
|
||||
public class GameRendererMixin {
|
||||
public abstract class GameRendererMixin {
|
||||
@Shadow
|
||||
@Final
|
||||
Minecraft minecraft;
|
||||
|
||||
@Shadow
|
||||
public abstract float getDepthFar();
|
||||
|
||||
@Unique
|
||||
private static final Matrix4f crystalline_sky$scratch = new Matrix4f();
|
||||
|
||||
@WrapOperation(method = "reloadShaders", at = @At(value = "INVOKE", target = "Ljava/util/List;add(Ljava/lang/Object;)Z", ordinal = 0))
|
||||
private <E extends Pair<ShaderInstance, Consumer<ShaderInstance>>> boolean loadSkyProgram(
|
||||
List<E> instance,
|
||||
@@ -29,6 +50,32 @@ public class GameRendererMixin {
|
||||
"crystalline_sky_rendertype_sky",
|
||||
DefaultVertexFormat.BLOCK
|
||||
), (Consumer<ShaderInstance>) program -> CrystallineShaderInstances.renderTypeSkyProgram = program));
|
||||
original.call(instance, Pair.of(new ShaderInstance(
|
||||
factory,
|
||||
"crystalline_sky_rendertype_skybox",
|
||||
DefaultVertexFormat.BLOCK
|
||||
), (Consumer<ShaderInstance>) program -> CrystallineShaderInstances.renderTypeSkyboxProgram = program));
|
||||
return original.call(instance, e);
|
||||
}
|
||||
|
||||
@WrapOperation(method = "renderLevel", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/renderer/GameRenderer;getProjectionMatrix(D)Lorg/joml/Matrix4f;"))
|
||||
private Matrix4f storeInverseProjectionMatrix(GameRenderer instance, double fov, Operation<Matrix4f> original) {
|
||||
invSkyboxMat.setPerspective(
|
||||
(float)(fov * (float) (Math.PI / 180.0)),
|
||||
(float)this.minecraft.getWindow().getWidth() / this.minecraft.getWindow().getHeight(),
|
||||
0.05F,
|
||||
this.getDepthFar()
|
||||
).invert();
|
||||
// TODO: do we need inv view multiplied in here?
|
||||
return original.call(instance, fov);
|
||||
}
|
||||
|
||||
@WrapOperation(method = "renderLevel", at = @At(value = "INVOKE", target = "Lnet/minecraft/client/renderer/LevelRenderer;renderLevel(Lnet/minecraft/client/DeltaTracker;ZLnet/minecraft/client/Camera;Lnet/minecraft/client/renderer/GameRenderer;Lnet/minecraft/client/renderer/LightTexture;Lorg/joml/Matrix4f;Lorg/joml/Matrix4f;)V"))
|
||||
private void mulInvViewMat(LevelRenderer instance, DeltaTracker deltaTracker, boolean renderBlockOutline, Camera camera, GameRenderer gameRenderer, LightTexture lightTexture, Matrix4f frustumMatrix, Matrix4f projectionMatrix, Operation<Void> original) {
|
||||
// invSkyboxMat = inv(ModelViewMat) * inv(ProjMat)
|
||||
projectionMatrix.invert(invSkyboxMat);
|
||||
Matrix4f invViewMat = frustumMatrix.invert(crystalline_sky$scratch);
|
||||
invViewMat.mul(invSkyboxMat, invSkyboxMat);
|
||||
original.call(instance, deltaTracker, renderBlockOutline, camera, gameRenderer, lightTexture, frustumMatrix, projectionMatrix);
|
||||
}
|
||||
}
|
||||
|
||||
+1
@@ -134,5 +134,6 @@ public abstract class LevelRendererMixin implements LevelRenderer_Duck {
|
||||
Matrix4f matrix4f, Matrix4f positionMatrix, Operation<Void> original) {
|
||||
original.call(instance, renderLayer, x, y, z, matrix4f, positionMatrix);
|
||||
renderSectionLayer(CrystallineRenderTypes.SKY, x, y, z, matrix4f, positionMatrix);
|
||||
renderSectionLayer(CrystallineRenderTypes.SKYBOX, x, y, z, matrix4f, positionMatrix);
|
||||
}
|
||||
}
|
||||
|
||||
+1
-1
@@ -36,7 +36,7 @@ public class LevelRenderer_NoSodium_Mixin {
|
||||
RenderType renderLayer) {
|
||||
original.call(instance, drawMode, viewMatrix, projectionMatrix, window);
|
||||
|
||||
if (renderLayer == CrystallineRenderTypes.SKY
|
||||
if ((renderLayer == CrystallineRenderTypes.SKY || renderLayer == CrystallineRenderTypes.SKYBOX)
|
||||
&& instance.COLOR_MODULATOR != null
|
||||
&& minecraft.player != null
|
||||
&& (CrystallineItems.isSky(minecraft.player.getMainHandItem())
|
||||
|
||||
+13
@@ -30,10 +30,23 @@ public class DefaultMaterialsMixin {
|
||||
false
|
||||
);
|
||||
|
||||
@Unique
|
||||
@SuppressWarnings("OptionalGetWithoutIsPresent")
|
||||
private static final Material crystalline_sky$SKYBOX = new Material(
|
||||
Arrays.stream(DefaultTerrainRenderPasses.ALL)
|
||||
.filter(pass -> ((TerrainRenderPassAccessor) pass).crystalline_sky$getRenderLayer() == CrystallineRenderTypes.SKYBOX)
|
||||
.findFirst()
|
||||
.get(),
|
||||
AlphaCutoffParameter.ZERO,
|
||||
false
|
||||
);
|
||||
|
||||
@Inject(method = "forRenderLayer", at = @At(value = "NEW", target = "(Ljava/lang/String;)Ljava/lang/IllegalArgumentException;"), cancellable = true)
|
||||
private static void addCrystallineSkyMaterial(RenderType layer, CallbackInfoReturnable<Material> cir) {
|
||||
if (layer == CrystallineRenderTypes.SKY) {
|
||||
cir.setReturnValue(crystalline_sky$SKY);
|
||||
} else if (layer == CrystallineRenderTypes.SKYBOX) {
|
||||
cir.setReturnValue(crystalline_sky$SKYBOX);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+2
-1
@@ -23,9 +23,10 @@ public class DefaultTerrainRenderPassesMixin {
|
||||
|
||||
@Inject(method = "<clinit>", at = @At("RETURN"))
|
||||
private static void addCrystallineSkyPass(CallbackInfo ci) {
|
||||
var ALL$ = new TerrainRenderPass[ALL.length + 1];
|
||||
var ALL$ = new TerrainRenderPass[ALL.length + 2];
|
||||
System.arraycopy(ALL, 0, ALL$, 0, ALL.length);
|
||||
ALL$[ALL.length] = new TerrainRenderPass(CrystallineRenderTypes.SKY, false, true);
|
||||
ALL$[ALL.length + 1] = new TerrainRenderPass(CrystallineRenderTypes.SKYBOX, false, true);
|
||||
ALL = ALL$;
|
||||
}
|
||||
}
|
||||
|
||||
+4
-2
@@ -25,6 +25,8 @@ public class ShaderChunkRendererMixin {
|
||||
private GlProgram<ChunkShaderInterface> createSkyShader(ShaderChunkRenderer instance, String path, ChunkShaderOptions options, Operation<GlProgram<ChunkShaderInterface>> original) {
|
||||
if (options.pass() == DefaultMaterials.forRenderLayer(CrystallineRenderTypes.SKY).pass) {
|
||||
return original.call(instance, "sodium_compat/block_layer_sky", options);
|
||||
} else if (options.pass() == DefaultMaterials.forRenderLayer(CrystallineRenderTypes.SKYBOX).pass) {
|
||||
return original.call(instance, "sodium_compat/block_layer_skybox", options);
|
||||
}
|
||||
|
||||
return original.call(instance, path, options);
|
||||
@@ -32,7 +34,7 @@ public class ShaderChunkRendererMixin {
|
||||
|
||||
@WrapOperation(method = "createShader", at = @At(value = "INVOKE", target = "Lnet/minecraft/resources/ResourceLocation;fromNamespaceAndPath(Ljava/lang/String;Ljava/lang/String;)Lnet/minecraft/resources/ResourceLocation;"))
|
||||
private ResourceLocation redirectShaderNamespace(String namespace, String path, Operation<ResourceLocation> original, String pathArg) {
|
||||
if (pathArg.equals("sodium_compat/block_layer_sky")) {
|
||||
if (pathArg.equals("sodium_compat/block_layer_sky") || pathArg.equals("sodium_compat/block_layer_skybox")) {
|
||||
namespace = "crystalline_sky";
|
||||
}
|
||||
|
||||
@@ -41,7 +43,7 @@ public class ShaderChunkRendererMixin {
|
||||
|
||||
@WrapOperation(method = "createShader", at = @At(value = "INVOKE", target = "Lnet/caffeinemc/mods/sodium/client/gl/shader/GlProgram$Builder;link(Ljava/util/function/Function;)Lnet/caffeinemc/mods/sodium/client/gl/shader/GlProgram;"), remap = false)
|
||||
private static GlProgram<ChunkShaderInterface> useSkyShaderInterface(GlProgram.Builder instance, Function<ShaderBindingContext, ChunkShaderInterface> factory, Operation<GlProgram<ChunkShaderInterface>> original, String argPath, ChunkShaderOptions argOptions) {
|
||||
if (argPath.equals("sodium_compat/block_layer_sky")) {
|
||||
if (argPath.equals("sodium_compat/block_layer_sky") || argPath.equals("sodium_compat/block_layer_skybox")) {
|
||||
factory = (shader) -> new SkyShaderInterface(shader, argOptions);
|
||||
}
|
||||
|
||||
|
||||
+2
-2
@@ -22,8 +22,8 @@ public class SodiumWorldRendererMixin {
|
||||
|
||||
@Inject(method = "drawChunkLayer", at = @At("RETURN"))
|
||||
private void drawCrystallineLayer(RenderType renderLayer, ChunkRenderMatrices matrices, double x, double y, double z, CallbackInfo ci) {
|
||||
if (renderLayer != CrystallineRenderTypes.SKY) return;
|
||||
if (renderLayer != CrystallineRenderTypes.SKY && renderLayer != CrystallineRenderTypes.SKYBOX) return;
|
||||
|
||||
renderSectionManager.renderLayer(matrices, DefaultMaterials.forRenderLayer(CrystallineRenderTypes.SKY).pass, x, y, z);
|
||||
renderSectionManager.renderLayer(matrices, DefaultMaterials.forRenderLayer(renderLayer).pass, x, y, z);
|
||||
}
|
||||
}
|
||||
|
||||
+4
@@ -48,6 +48,10 @@ public class CrystallineBlocks {
|
||||
.initialProperties(SKY_LIGHT::value)
|
||||
.register();
|
||||
|
||||
public static final BlockHolder<SkyBlock> SKYBOX_TEST = REGISTRY.block("skybox_test", SkyBlock::new)
|
||||
.initialProperties(SKY::value)
|
||||
.register();
|
||||
|
||||
public static void init() {}
|
||||
|
||||
public static boolean isCrystallineSky(BlockState state) {
|
||||
|
||||
+6
-1
@@ -42,6 +42,10 @@ public class CrystallineItems {
|
||||
.properties(p -> p.rarity(Rarity.EPIC))
|
||||
.register();
|
||||
|
||||
public static final ItemHolder<BlockItem> SKYBOX_TEST = REGISTRY.item(CrystallineBlocks.SKYBOX_TEST)
|
||||
.properties(p -> p.rarity(Rarity.EPIC))
|
||||
.register();
|
||||
|
||||
@SuppressWarnings("SameParameterValue")
|
||||
private static ResourceKey<CreativeModeTab> tabKey(String name) {
|
||||
return ResourceKey.create(Registries.CREATIVE_MODE_TAB, ResourceLocation.withDefaultNamespace(name));
|
||||
@@ -53,6 +57,7 @@ public class CrystallineItems {
|
||||
|
||||
stacks.add(new ItemStack(SKY));
|
||||
stacks.add(new ItemStack(WEEPING_SKY));
|
||||
stacks.add(new ItemStack(SKYBOX_TEST));
|
||||
|
||||
for (int i = 15; i >= 0; i--) {
|
||||
stacks.add(SkyLightBlock.setLightOnStack(new ItemStack(SKY_LIGHT), i));
|
||||
@@ -67,6 +72,6 @@ public class CrystallineItems {
|
||||
public static void init() {}
|
||||
|
||||
public static boolean isSky(ItemStack stack) {
|
||||
return SKY.is(stack) || WEEPING_SKY.is(stack);
|
||||
return SKY.is(stack) || WEEPING_SKY.is(stack) || SKYBOX_TEST.is(stack);
|
||||
}
|
||||
}
|
||||
|
||||
+24
@@ -0,0 +1,24 @@
|
||||
package io.github.slimeistdev.crystalline_sky.registry.client;
|
||||
|
||||
import io.github.slimeistdev.crystalline_sky.CrystallineSky;
|
||||
import net.minecraft.resources.ResourceLocation;
|
||||
|
||||
import java.util.function.BiConsumer;
|
||||
|
||||
public enum CrystallineAtlases {
|
||||
SKYBOXES("skyboxes");
|
||||
|
||||
public final ResourceLocation texture;
|
||||
public final ResourceLocation info;
|
||||
|
||||
CrystallineAtlases(String name) {
|
||||
texture = CrystallineSky.id("textures/atlas/" + name + ".png");
|
||||
info = CrystallineSky.id(name);
|
||||
}
|
||||
|
||||
public static void register(BiConsumer<ResourceLocation, ResourceLocation> registrar) {
|
||||
for (CrystallineAtlases atlas : values()) {
|
||||
registrar.accept(atlas.texture, atlas.info);
|
||||
}
|
||||
}
|
||||
}
|
||||
+28
-1
@@ -5,6 +5,7 @@ import com.mojang.blaze3d.vertex.DefaultVertexFormat;
|
||||
import com.mojang.blaze3d.vertex.VertexFormat;
|
||||
import io.github.slimeistdev.crystalline_sky.mixin_ducks.client.LevelRenderer_Duck;
|
||||
import io.github.slimeistdev.crystalline_sky.mixin_ducks.client.RenderType_Duck;
|
||||
import io.github.slimeistdev.crystalline_sky.util.SharedRenderVariables;
|
||||
import net.fabricmc.api.EnvType;
|
||||
import net.fabricmc.api.Environment;
|
||||
import net.minecraft.client.Minecraft;
|
||||
@@ -15,12 +16,21 @@ import net.minecraft.client.renderer.RenderType;
|
||||
public abstract class CrystallineRenderTypes extends RenderType {
|
||||
private static final RenderStateShard.EmptyTextureStateShard SKY_TEXTURE = new SkyBufferTexture();
|
||||
private static final RenderStateShard.ShaderStateShard SKY_PROGRAM = new RenderStateShard.ShaderStateShard(CrystallineShaderInstances::getRenderTypeSkyProgram);
|
||||
private static final RenderStateShard.ShaderStateShard SKYBOX_PROGRAM = new RenderStateShard.ShaderStateShard(CrystallineShaderInstances::getRenderTypeSkyboxProgram);
|
||||
public static final RenderStateShard.TextureStateShard SKYBOX_SHEET = new RenderStateShard.TextureStateShard(CrystallineAtlases.SKYBOXES.texture, false, false);
|
||||
public static final RenderStateShard.OutputStateShard SKYBOX_MATRICES = new RenderStateShard.OutputStateShard("skybox main_target", () -> {
|
||||
MAIN_TARGET.setupRenderState();
|
||||
RenderSystem.setTextureMatrix(SharedRenderVariables.invSkyboxMat);
|
||||
}, () -> {
|
||||
RenderSystem.resetTextureMatrix();
|
||||
MAIN_TARGET.clearRenderState();
|
||||
});
|
||||
|
||||
public static final RenderType SKY = create(
|
||||
"crystalline_sky_sky",
|
||||
DefaultVertexFormat.BLOCK,
|
||||
VertexFormat.Mode.QUADS,
|
||||
4194304,
|
||||
786432,
|
||||
true,
|
||||
false,
|
||||
RenderType.CompositeState.builder()
|
||||
@@ -30,9 +40,26 @@ public abstract class CrystallineRenderTypes extends RenderType {
|
||||
.createCompositeState(true)
|
||||
);
|
||||
|
||||
public static final RenderType SKYBOX = create(
|
||||
"crystalline_sky_skybox",
|
||||
DefaultVertexFormat.BLOCK,
|
||||
VertexFormat.Mode.QUADS,
|
||||
786432,
|
||||
true,
|
||||
false,
|
||||
RenderType.CompositeState.builder()
|
||||
.setLightmapState(LIGHTMAP)
|
||||
.setShaderState(SKYBOX_PROGRAM)
|
||||
.setTextureState(SKYBOX_SHEET)
|
||||
.setOutputState(SKYBOX_MATRICES)
|
||||
.createCompositeState(true)
|
||||
);
|
||||
|
||||
static {
|
||||
//noinspection DataFlowIssue
|
||||
((RenderType_Duck) SKY).crystalline_sky$markAsBlockLayer();
|
||||
//noinspection DataFlowIssue
|
||||
((RenderType_Duck) SKYBOX).crystalline_sky$markAsBlockLayer();
|
||||
}
|
||||
|
||||
private CrystallineRenderTypes(String name, VertexFormat format, VertexFormat.Mode mode, int bufferSize, boolean affectsCrumbling, boolean sortOnUpload, Runnable setupState, Runnable clearState) {
|
||||
|
||||
+7
@@ -8,7 +8,14 @@ public class CrystallineShaderInstances {
|
||||
@ApiStatus.Internal
|
||||
public static @Nullable ShaderInstance renderTypeSkyProgram;
|
||||
|
||||
@ApiStatus.Internal
|
||||
public static @Nullable ShaderInstance renderTypeSkyboxProgram;
|
||||
|
||||
public static @Nullable ShaderInstance getRenderTypeSkyProgram() {
|
||||
return renderTypeSkyProgram;
|
||||
}
|
||||
|
||||
public static @Nullable ShaderInstance getRenderTypeSkyboxProgram() {
|
||||
return renderTypeSkyboxProgram;
|
||||
}
|
||||
}
|
||||
|
||||
+7
@@ -0,0 +1,7 @@
|
||||
package io.github.slimeistdev.crystalline_sky.util;
|
||||
|
||||
import org.joml.Matrix4f;
|
||||
|
||||
public class SharedRenderVariables {
|
||||
public static final Matrix4f invSkyboxMat = new Matrix4f();
|
||||
}
|
||||
@@ -0,0 +1,9 @@
|
||||
{
|
||||
"sources": [
|
||||
{
|
||||
"type": "directory",
|
||||
"source": "crystalline_sky_skybox",
|
||||
"prefix": "crystalline_sky_skybox/"
|
||||
}
|
||||
]
|
||||
}
|
||||
Binary file not shown.
|
After Width: | Height: | Size: 4.5 KiB |
BIN
Binary file not shown.
|
After Width: | Height: | Size: 1.2 KiB |
BIN
Binary file not shown.
+1
-2
@@ -2,8 +2,7 @@
|
||||
"vertex": "crystalline_sky_rendertype_sky",
|
||||
"fragment": "crystalline_sky_rendertype_sky",
|
||||
"samplers": [
|
||||
{ "name": "Sampler0" },
|
||||
{ "name": "Sampler2" }
|
||||
{ "name": "Sampler0" }
|
||||
],
|
||||
"uniforms": [
|
||||
{ "name": "ModelViewMat", "type": "matrix4x4", "count": 16, "values": [ 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0 ] },
|
||||
|
||||
+80
@@ -0,0 +1,80 @@
|
||||
#version 150
|
||||
|
||||
#moj_import <fog.glsl>
|
||||
|
||||
uniform sampler2D Sampler0;
|
||||
|
||||
uniform vec4 ColorModulator;
|
||||
uniform float FogStart;
|
||||
uniform float FogEnd;
|
||||
uniform vec4 FogColor;
|
||||
|
||||
in float vertexDistance;
|
||||
//in vec4 texProj0;
|
||||
in vec2 uv0;
|
||||
in vec2 uv1;
|
||||
in vec3 vPos;
|
||||
|
||||
out vec4 fragColor;
|
||||
|
||||
#ifndef BAYER_BIAS
|
||||
#define BAYER_BIAS 0.03125
|
||||
#endif
|
||||
|
||||
#ifndef SCALE
|
||||
#define SCALE 1
|
||||
#endif
|
||||
|
||||
const mat4x4 bayerMatrix4x4 = mat4x4(
|
||||
0.0, 8.0, 2.0, 10.0,
|
||||
12.0, 4.0, 14.0, 6.0,
|
||||
3.0, 11.0, 1.0, 9.0,
|
||||
15.0, 7.0, 13.0, 5.0
|
||||
) / 16.0;
|
||||
|
||||
void main() {
|
||||
int x = int(gl_FragCoord.x / SCALE) % 4;
|
||||
int y = int(gl_FragCoord.y / SCALE) % 4;
|
||||
float bayer = bayerMatrix4x4[y][x];
|
||||
|
||||
if (ColorModulator.a <= bayer + BAYER_BIAS) {
|
||||
discard;
|
||||
}
|
||||
|
||||
vec3 dir = normalize(vPos);
|
||||
vec3 dabs = abs(dir);
|
||||
float dmax = max(dabs.x, max(dabs.y, dabs.z));
|
||||
vec3 col;
|
||||
bool positive;
|
||||
vec2 uv;
|
||||
vec2 section;
|
||||
if (dabs.x == dmax) {
|
||||
col = vec3(1.0, 0.0, 0.0);
|
||||
positive = dir.x > 0;
|
||||
uv = positive ? -dir.zy : vec2(dir.z, -dir.y);
|
||||
section = vec2(positive ? 2.0 : 0.0, 1.0);
|
||||
} else if (dabs.y == dmax) {
|
||||
col = vec3(0.0, 1.0, 0.0);
|
||||
positive = dir.y > 0;
|
||||
uv = positive ? dir.xz : vec2(dir.x, -dir.z);
|
||||
section = vec2(positive ? 1.0 : 2.0, 0.0);
|
||||
} else {
|
||||
col = vec3(0.0, 0.0, 1.0);
|
||||
positive = dir.z > 0;
|
||||
uv = positive ? vec2(dir.x, -dir.y) : -dir.xy;
|
||||
section = vec2(positive ? 1.0 : 3.0, 1.0);
|
||||
}
|
||||
|
||||
uv = (uv / dmax + 1.0) / 2.0;
|
||||
uv = clamp(uv, vec2(0.0), vec2(1.0));
|
||||
uv = (uv + section) / vec2(4.0, 2.0);
|
||||
|
||||
col *= positive ? 1.0 : 0.5;
|
||||
//col = vec3(uv, 0.0);
|
||||
|
||||
vec2 uvR = uv0 + uv * (uv1 - uv0);
|
||||
|
||||
//vec4 color = vec4(col, 1.0) * vec4(ColorModulator.rgb, 1.0);
|
||||
vec4 color = texture(Sampler0, uvR) * vec4(ColorModulator.rgb, 1.0);
|
||||
fragColor = linear_fog(color, vertexDistance, FogStart, FogEnd, FogColor);
|
||||
}
|
||||
+18
@@ -0,0 +1,18 @@
|
||||
{
|
||||
"vertex": "crystalline_sky_rendertype_skybox",
|
||||
"fragment": "crystalline_sky_rendertype_skybox",
|
||||
"samplers": [
|
||||
{ "name": "Sampler0" }
|
||||
],
|
||||
"uniforms": [
|
||||
{ "name": "ModelViewMat", "type": "matrix4x4", "count": 16, "values": [ 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0 ] },
|
||||
{ "name": "ProjMat", "type": "matrix4x4", "count": 16, "values": [ 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0 ] },
|
||||
{ "name": "ChunkOffset", "type": "float", "count": 3, "values": [ 0.0, 0.0, 0.0 ] },
|
||||
{ "name": "ColorModulator", "type": "float", "count": 4, "values": [ 1.0, 1.0, 1.0, 1.0 ] },
|
||||
{ "name": "FogStart", "type": "float", "count": 1, "values": [ 0.0 ] },
|
||||
{ "name": "FogEnd", "type": "float", "count": 1, "values": [ 1.0 ] },
|
||||
{ "name": "FogColor", "type": "float", "count": 4, "values": [ 0.0, 0.0, 0.0, 0.0 ] },
|
||||
{ "name": "FogShape", "type": "int", "count": 1, "values": [ 0 ] },
|
||||
{ "name": "TextureMat", "type": "matrix4x4", "count": 16, "values": [ 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0, 0.0, 0.0, 0.0, 1.0 ] }
|
||||
]
|
||||
}
|
||||
+39
@@ -0,0 +1,39 @@
|
||||
#version 150
|
||||
|
||||
#moj_import <fog.glsl>
|
||||
|
||||
in vec3 Position;
|
||||
in vec4 Color;
|
||||
in vec2 UV0;
|
||||
in ivec2 UV2;
|
||||
in vec3 Normal;
|
||||
|
||||
uniform sampler2D Sampler2;
|
||||
|
||||
uniform mat4 ModelViewMat;
|
||||
uniform mat4 ProjMat;
|
||||
uniform mat4 TextureMat;
|
||||
uniform vec3 ChunkOffset;
|
||||
uniform int FogShape;
|
||||
|
||||
out float vertexDistance;
|
||||
out vec2 uv0;
|
||||
out vec2 uv1;
|
||||
out vec3 vPos;
|
||||
|
||||
void main() {
|
||||
vec3 pos = Position + ChunkOffset;
|
||||
gl_Position = ProjMat * ModelViewMat * vec4(pos, 1.0);
|
||||
|
||||
vertexDistance = fog_distance(pos, FogShape);
|
||||
uv0 = UV0;
|
||||
uv1 = (Color.ag * 255.0 / 256.0) + (Color.rb / 256.0);
|
||||
|
||||
// somehow this unbreaks view bobbing. No clue *how*, but it does.
|
||||
vec3 screenPos = gl_Position.xyz / gl_Position.w;
|
||||
vec4 projected4 = TextureMat * vec4(screenPos, 1.0);
|
||||
vec3 projected = projected4.xyz / projected4.w;
|
||||
vec4 projectedO4 = TextureMat * vec4(0.0, 0.0, 1.0, 0.0);
|
||||
vec3 projectedO = projectedO4.xyz / projectedO4.w;
|
||||
vPos = projected - projectedO;
|
||||
}
|
||||
@@ -16,6 +16,7 @@
|
||||
"SkyLightSectionStorageAccessor"
|
||||
],
|
||||
"client": [
|
||||
"client.BlockModelDeserializerMixin",
|
||||
"client.ClientLevelMixin",
|
||||
"client.DebugRendererMixin",
|
||||
"client.GameRendererMixin",
|
||||
|
||||
+8
@@ -1,8 +1,11 @@
|
||||
package io.github.slimeistdev.crystalline_sky.fabric;
|
||||
|
||||
import io.github.slimeistdev.crystalline_sky.CrystallineSkyClient;
|
||||
import io.github.slimeistdev.crystalline_sky.fabric.events.RegisterMaterialAtlasesEvent;
|
||||
import io.github.slimeistdev.crystalline_sky.fabric.render_tmp.SkyboxModelLoadingPlugin;
|
||||
import io.github.slimeistdev.crystalline_sky.multiloader.fabric.ItemGroupRegistrationEventImpl;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.CrystallineBlocks;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.client.CrystallineAtlases;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.client.CrystallineRenderTypes;
|
||||
import net.fabricmc.api.ClientModInitializer;
|
||||
import net.fabricmc.api.EnvType;
|
||||
@@ -23,9 +26,14 @@ public class CrystallineSkyClientImpl implements ClientModInitializer {
|
||||
ItemGroupRegistrationEventImpl.register();
|
||||
|
||||
Consumer<Block> makeSky = b -> BlockRenderLayerMap.INSTANCE.putBlock(b, CrystallineRenderTypes.SKY);
|
||||
Consumer<Block> makeSkybox = b -> BlockRenderLayerMap.INSTANCE.putBlock(b, CrystallineRenderTypes.SKYBOX);
|
||||
CrystallineBlocks.SKY.onRegistered(makeSky);
|
||||
CrystallineBlocks.WEEPING_SKY.onRegistered(makeSky);
|
||||
CrystallineBlocks.SKYBOX_TEST.onRegistered(makeSkybox);
|
||||
|
||||
ClientTickEvents.END_CLIENT_TICK.register(CrystallineSkyClient::onEndTick);
|
||||
|
||||
RegisterMaterialAtlasesEvent.EVENT.register(ctx -> CrystallineAtlases.register(ctx::addAtlas));
|
||||
SkyboxModelLoadingPlugin.register();
|
||||
}
|
||||
}
|
||||
|
||||
+31
@@ -5,8 +5,10 @@ import com.google.gson.JsonObject;
|
||||
import io.github.slimeistdev.crystalline_sky.CrystallineSky;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.CrystallineBlocks;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.CrystallineItems;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.client.CrystallineAtlases;
|
||||
import net.fabricmc.fabric.api.datagen.v1.FabricDataOutput;
|
||||
import net.fabricmc.fabric.api.datagen.v1.provider.FabricModelProvider;
|
||||
import net.minecraft.core.registries.BuiltInRegistries;
|
||||
import net.minecraft.data.models.BlockModelGenerators;
|
||||
import net.minecraft.data.models.ItemModelGenerators;
|
||||
import net.minecraft.data.models.blockstates.MultiVariantGenerator;
|
||||
@@ -24,8 +26,20 @@ import net.minecraft.world.level.block.state.properties.BlockStateProperties;
|
||||
|
||||
import java.util.Locale;
|
||||
|
||||
import static net.minecraft.data.models.model.TexturedModel.createDefault;
|
||||
|
||||
@SuppressWarnings("SameParameterValue")
|
||||
public class CrystallineSkyModelProvider extends FabricModelProvider {
|
||||
private static ResourceLocation getSkyboxBlockTexture(Block block) {
|
||||
ResourceLocation resourceLocation = BuiltInRegistries.BLOCK.getKey(block);
|
||||
return resourceLocation.withPrefix("crystalline_sky_skybox/");
|
||||
}
|
||||
|
||||
private static final TexturedModel.Provider SKYBOX_CUBE = createDefault(
|
||||
block -> TextureMapping.cube(getSkyboxBlockTexture(block)),
|
||||
ModelTemplates.CUBE_ALL
|
||||
);
|
||||
|
||||
public CrystallineSkyModelProvider(FabricDataOutput output) {
|
||||
super(output);
|
||||
}
|
||||
@@ -38,6 +52,8 @@ public class CrystallineSkyModelProvider extends FabricModelProvider {
|
||||
|
||||
gen.createAirLikeBlock(CrystallineBlocks.WEEPING_SKY_LIGHT.value(), CrystallineItems.WEEPING_SKY_LIGHT.value());
|
||||
gen.createSimpleFlatItemModel(CrystallineItems.WEEPING_SKY_LIGHT.value());
|
||||
|
||||
registerSkyboxBlock(gen, CrystallineBlocks.SKYBOX_TEST.value());
|
||||
}
|
||||
|
||||
private void registerSkyBlock(BlockModelGenerators gen, Block block) {
|
||||
@@ -54,6 +70,21 @@ public class CrystallineSkyModelProvider extends FabricModelProvider {
|
||||
gen.createSimpleFlatItemModel(block);
|
||||
}
|
||||
|
||||
private void registerSkyboxBlock(BlockModelGenerators gen, Block block) {
|
||||
gen.blockStateOutput.accept(BlockModelGenerators.createSimpleBlock(block, SKYBOX_CUBE.create(
|
||||
block,
|
||||
(id, json) -> {
|
||||
gen.modelOutput.accept(id, () -> {
|
||||
JsonObject root = json.get().getAsJsonObject();
|
||||
root.addProperty("render_type", CrystallineSky.id("skybox").toString());
|
||||
root.addProperty(CrystallineSky.id("atlas").toString(), CrystallineAtlases.SKYBOXES.texture.toString());
|
||||
return root;
|
||||
});
|
||||
}
|
||||
)));
|
||||
gen.createSimpleFlatItemModel(block);
|
||||
}
|
||||
|
||||
private void registerSkyLightBlock(BlockModelGenerators gen, Block block, Item item) {
|
||||
gen.skipAutoItemBlock(block);
|
||||
PropertyDispatch.C1<Integer> singleProperty = PropertyDispatch.property(BlockStateProperties.LEVEL);
|
||||
|
||||
+40
@@ -0,0 +1,40 @@
|
||||
package io.github.slimeistdev.crystalline_sky.fabric.events;
|
||||
|
||||
import net.fabricmc.fabric.api.event.Event;
|
||||
import net.fabricmc.fabric.api.event.EventFactory;
|
||||
import net.minecraft.resources.ResourceLocation;
|
||||
import org.jetbrains.annotations.ApiStatus;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
public interface RegisterMaterialAtlasesEvent {
|
||||
Event<RegisterMaterialAtlasesEvent> EVENT = EventFactory.createArrayBacked(RegisterMaterialAtlasesEvent.class, (callbacks) -> (context) -> {
|
||||
for (RegisterMaterialAtlasesEvent callback : callbacks) {
|
||||
callback.run(context);
|
||||
}
|
||||
});
|
||||
|
||||
@ApiStatus.Internal
|
||||
static Map<ResourceLocation, ResourceLocation> gatherMaterialAtlases(Map<ResourceLocation, ResourceLocation> vanillaAtlases) {
|
||||
Map<ResourceLocation, ResourceLocation> atlases = new HashMap<>(vanillaAtlases);
|
||||
EVENT.invoker().run(((atlasLocation, atlasInfoLocation) -> {
|
||||
ResourceLocation oldAtlasInfoLoc = atlases.putIfAbsent(atlasLocation, atlasInfoLocation);
|
||||
if (oldAtlasInfoLoc != null) {
|
||||
throw new IllegalStateException(String.format(
|
||||
"Duplicate registration of atlas: %s (old info: %s, new info: %s)",
|
||||
atlasLocation,
|
||||
oldAtlasInfoLoc,
|
||||
atlasInfoLocation));
|
||||
}
|
||||
}));
|
||||
return Map.copyOf(atlases);
|
||||
}
|
||||
|
||||
void run(Context context);
|
||||
|
||||
@FunctionalInterface
|
||||
interface Context {
|
||||
void addAtlas(ResourceLocation atlasLocation, ResourceLocation atlasInfoLocation);
|
||||
}
|
||||
}
|
||||
+21
@@ -0,0 +1,21 @@
|
||||
package io.github.slimeistdev.crystalline_sky.fabric.mixin.client;
|
||||
|
||||
import com.llamalad7.mixinextras.injector.wrapoperation.Operation;
|
||||
import com.llamalad7.mixinextras.injector.wrapoperation.WrapOperation;
|
||||
import io.github.slimeistdev.crystalline_sky.fabric.events.RegisterMaterialAtlasesEvent;
|
||||
import net.minecraft.client.renderer.texture.TextureManager;
|
||||
import net.minecraft.client.resources.model.AtlasSet;
|
||||
import net.minecraft.client.resources.model.ModelManager;
|
||||
import net.minecraft.resources.ResourceLocation;
|
||||
import org.spongepowered.asm.mixin.Mixin;
|
||||
import org.spongepowered.asm.mixin.injection.At;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
@Mixin(ModelManager.class)
|
||||
public class ModelManagerMixin {
|
||||
@WrapOperation(method = "<init>", at = @At(value = "NEW", target = "(Ljava/util/Map;Lnet/minecraft/client/renderer/texture/TextureManager;)Lnet/minecraft/client/resources/model/AtlasSet;"))
|
||||
private AtlasSet addCustomAtlases(Map<ResourceLocation, ResourceLocation> atlasMap, TextureManager textureManager, Operation<AtlasSet> original) {
|
||||
return original.call(RegisterMaterialAtlasesEvent.gatherMaterialAtlases(atlasMap), textureManager);
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -15,7 +15,7 @@ import org.spongepowered.asm.mixin.injection.callback.CallbackInfoReturnable;
|
||||
public class ChunkRenderOverrider_AxiomChunkOverrideLayerMixin {
|
||||
@Inject(method = "fromVanilla", at = @At("HEAD"), cancellable = true)
|
||||
private static void unexplodeSky(RenderType layer, CallbackInfoReturnable<ChunkRenderOverrider.AxiomChunkOverrideLayer> cir) {
|
||||
if (layer == CrystallineRenderTypes.SKY) {
|
||||
if (layer == CrystallineRenderTypes.SKY || layer == CrystallineRenderTypes.SKYBOX) {
|
||||
cir.setReturnValue(ChunkRenderOverrider.AxiomChunkOverrideLayer.CUTOUT_MIPPED);
|
||||
}
|
||||
}
|
||||
|
||||
+116
@@ -0,0 +1,116 @@
|
||||
package io.github.slimeistdev.crystalline_sky.fabric.render_tmp;
|
||||
|
||||
import net.fabricmc.fabric.api.renderer.v1.Renderer;
|
||||
import net.fabricmc.fabric.api.renderer.v1.RendererAccess;
|
||||
import net.fabricmc.fabric.api.renderer.v1.material.RenderMaterial;
|
||||
import net.fabricmc.fabric.api.renderer.v1.material.ShadeMode;
|
||||
import net.fabricmc.fabric.api.renderer.v1.mesh.QuadEmitter;
|
||||
import net.fabricmc.fabric.api.renderer.v1.model.ForwardingBakedModel;
|
||||
import net.fabricmc.fabric.api.renderer.v1.model.ModelHelper;
|
||||
import net.fabricmc.fabric.api.renderer.v1.render.RenderContext;
|
||||
import net.fabricmc.fabric.api.util.TriState;
|
||||
import net.minecraft.client.renderer.block.model.BakedQuad;
|
||||
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
|
||||
import net.minecraft.client.resources.model.BakedModel;
|
||||
import net.minecraft.core.BlockPos;
|
||||
import net.minecraft.core.Direction;
|
||||
import net.minecraft.util.RandomSource;
|
||||
import net.minecraft.world.item.ItemStack;
|
||||
import net.minecraft.world.level.BlockAndTintGetter;
|
||||
import net.minecraft.world.level.block.state.BlockState;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
public class SkyboxBakedModel extends ForwardingBakedModel {
|
||||
private static final RenderMaterial FULL_BRIGHT_MATERIAL;
|
||||
static {
|
||||
Renderer renderer = RendererAccess.INSTANCE.getRenderer();
|
||||
if (renderer == null) {
|
||||
FULL_BRIGHT_MATERIAL = null;
|
||||
} else {
|
||||
FULL_BRIGHT_MATERIAL = renderer.materialFinder()
|
||||
.shadeMode(ShadeMode.VANILLA)
|
||||
.ambientOcclusion(TriState.FALSE)
|
||||
.emissive(true)
|
||||
.disableDiffuse(true)
|
||||
.disableColorIndex(true)
|
||||
.find();
|
||||
}
|
||||
}
|
||||
|
||||
public SkyboxBakedModel(BakedModel wrapped) {
|
||||
super(wrapped);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean useAmbientOcclusion() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean usesBlockLight() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isVanillaAdapter() {
|
||||
return false;
|
||||
}
|
||||
|
||||
// copied from net.fabricmc.fabric.impl.renderer.VanillaModelEncoder.emitBlockQuads
|
||||
@Override
|
||||
public void emitBlockQuads(BlockAndTintGetter blockView, BlockState state, BlockPos pos, Supplier<RandomSource> randomSupplier, RenderContext context) {
|
||||
/*TextureAtlasSprite sprite = getParticleIcon();
|
||||
float u0 = sprite.getU0();
|
||||
float v0 = sprite.getV0();
|
||||
int u1 = (int) (sprite.getU1() * 0xffff);
|
||||
int v1 = (int) (sprite.getV1() * 0xffff);
|
||||
|
||||
int color = (u1 << 16) | v1;
|
||||
var emitter = context.getEmitter()
|
||||
.square(Direction.UP, 0, 0, 1, 1, 0)
|
||||
.material(FULLBRIGHT_MATERIAL);
|
||||
for (int i = 0; i < 4; i++) {
|
||||
emitter
|
||||
.color(i, color)
|
||||
.lightmap(i, LightTexture.FULL_BRIGHT)
|
||||
.normal(i, 0, 1, 0)
|
||||
.uv(i, u0, v0);
|
||||
}
|
||||
emitter.emit();*/
|
||||
|
||||
QuadEmitter emitter = context.getEmitter();
|
||||
|
||||
for (int i = 0; i <= ModelHelper.NULL_FACE_ID; i++) {
|
||||
final Direction cullFace = ModelHelper.faceFromIndex(i);
|
||||
|
||||
if (!context.hasTransform() && context.isFaceCulled(cullFace)) {
|
||||
// Skip entire quad list if possible
|
||||
continue;
|
||||
}
|
||||
|
||||
final List<BakedQuad> quads = getQuads(state, cullFace, randomSupplier.get());
|
||||
|
||||
for (final BakedQuad q : quads) {
|
||||
emitter.fromVanilla(q, FULL_BRIGHT_MATERIAL, cullFace); // fixme view bobbing breaks projection, use TextureMatrix to pass a view projection matrix along :)
|
||||
TextureAtlasSprite sprite = q.getSprite();
|
||||
float u0 = sprite.getU0();
|
||||
float v0 = sprite.getV0();
|
||||
int u1 = (int) (sprite.getU1() * 0xffff);
|
||||
int v1 = (int) (sprite.getV1() * 0xffff);
|
||||
int uv1 = (u1 << 16) | v1;
|
||||
for (int j = 0; j < 4; j++) {
|
||||
emitter.uv(j, u0, v0);
|
||||
emitter.color(j, uv1);
|
||||
}
|
||||
emitter.emit();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void emitItemQuads(ItemStack stack, Supplier<RandomSource> randomSupplier, RenderContext context) {
|
||||
super.emitItemQuads(stack, randomSupplier, context);
|
||||
}
|
||||
}
|
||||
+28
@@ -0,0 +1,28 @@
|
||||
package io.github.slimeistdev.crystalline_sky.fabric.render_tmp;
|
||||
|
||||
import io.github.slimeistdev.crystalline_sky.CrystallineSky;
|
||||
import net.fabricmc.fabric.api.client.model.loading.v1.ModelLoadingPlugin;
|
||||
import net.minecraft.resources.ResourceLocation;
|
||||
|
||||
public class SkyboxModelLoadingPlugin implements ModelLoadingPlugin {
|
||||
private SkyboxModelLoadingPlugin() {}
|
||||
|
||||
@Override
|
||||
public void onInitializeModelLoader(Context pluginContext) {
|
||||
pluginContext.modifyModelAfterBake().register((model, ctx) -> {
|
||||
if (model == null) return null;
|
||||
|
||||
ResourceLocation id = ctx.resourceId();
|
||||
if (id == null) {
|
||||
id = ctx.topLevelId().id();
|
||||
}
|
||||
if (!id.equals(CrystallineSky.id("block/skybox_test"))) return model;
|
||||
|
||||
return new SkyboxBakedModel(model);
|
||||
});
|
||||
}
|
||||
|
||||
public static void register() {
|
||||
ModelLoadingPlugin.register(new SkyboxModelLoadingPlugin());
|
||||
}
|
||||
}
|
||||
@@ -10,6 +10,7 @@
|
||||
"mixins": [
|
||||
],
|
||||
"client": [
|
||||
"client.ModelManagerMixin",
|
||||
"client.RenderTypeMixin",
|
||||
"client.compat.axiom.ChunkRenderOverrider_AxiomChunkOverrideLayerMixin"
|
||||
],
|
||||
|
||||
+1
-1
@@ -26,5 +26,5 @@ modVersion=0.1.2
|
||||
compatibleVersions=1.21.1
|
||||
|
||||
# mod compat
|
||||
enable_sodium=true
|
||||
enable_sodium=false
|
||||
enable_axiom=false
|
||||
|
||||
+8
@@ -4,6 +4,7 @@ import io.github.slimeistdev.crystalline_sky.CrystallineSky;
|
||||
import io.github.slimeistdev.crystalline_sky.CrystallineSkyClient;
|
||||
import io.github.slimeistdev.crystalline_sky.multiloader.neoforge.ItemGroupRegistrationEventImpl;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.CrystallineItems;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.client.CrystallineAtlases;
|
||||
import io.github.slimeistdev.crystalline_sky.registry.client.CrystallineRenderTypes;
|
||||
import net.minecraft.client.Minecraft;
|
||||
import net.minecraft.client.renderer.RenderType;
|
||||
@@ -12,6 +13,7 @@ import net.neoforged.bus.api.SubscribeEvent;
|
||||
import net.neoforged.fml.common.EventBusSubscriber;
|
||||
import net.neoforged.neoforge.client.event.ClientTickEvent;
|
||||
import net.neoforged.neoforge.client.event.RegisterKeyMappingsEvent;
|
||||
import net.neoforged.neoforge.client.event.RegisterMaterialAtlasesEvent;
|
||||
import net.neoforged.neoforge.client.event.RegisterNamedRenderTypesEvent;
|
||||
import net.neoforged.neoforge.event.BuildCreativeModeTabContentsEvent;
|
||||
|
||||
@@ -25,6 +27,7 @@ public class CrystallineSkyClientImpl {
|
||||
public static void registerNamedRenderTypes(RegisterNamedRenderTypesEvent event) {
|
||||
// NOTE: entity render type is just a placeholder, sky rendering isn't supported for entities
|
||||
event.register(CrystallineSky.id("sky"), CrystallineRenderTypes.SKY, RenderType.entitySolid(CrystallineSky.id("sky")));
|
||||
event.register(CrystallineSky.id("skybox"), CrystallineRenderTypes.SKYBOX, RenderType.entitySolid(CrystallineSky.id("skybox")));
|
||||
}
|
||||
|
||||
@SubscribeEvent
|
||||
@@ -41,4 +44,9 @@ public class CrystallineSkyClientImpl {
|
||||
public static void buildCreativeModeTabContents(BuildCreativeModeTabContentsEvent event) {
|
||||
CrystallineItems.onItemGroupRegistration(new ItemGroupRegistrationEventImpl(event));
|
||||
}
|
||||
|
||||
@SubscribeEvent
|
||||
public static void registerAtlases(RegisterMaterialAtlasesEvent event) {
|
||||
CrystallineAtlases.register(event::register);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user