mirror of
https://github.com/Creators-of-Create/Create.git
synced 2024-11-10 03:53:12 +01:00
Cull code to fix crash on mac
- A bunch of dead code removal
This commit is contained in:
parent
b071229731
commit
f1da8b8f1e
19 changed files with 3 additions and 1598 deletions
|
@ -1,10 +1,12 @@
|
|||
package com.simibubi.create.content.curiosities.bell;
|
||||
|
||||
import com.jozufozu.flywheel.backend.OptifineHandler;
|
||||
import com.mojang.blaze3d.vertex.IVertexBuilder;
|
||||
|
||||
import net.minecraft.client.particle.IAnimatedSprite;
|
||||
import net.minecraft.client.particle.SimpleAnimatedParticle;
|
||||
import net.minecraft.client.renderer.ActiveRenderInfo;
|
||||
import net.minecraft.client.renderer.LightTexture;
|
||||
import net.minecraft.client.world.ClientWorld;
|
||||
import net.minecraft.util.math.MathHelper;
|
||||
import net.minecraft.util.math.vector.Quaternion;
|
||||
|
@ -61,7 +63,7 @@ public class CustomRotationParticle extends SimpleAnimatedParticle {
|
|||
float maxU = mirror ? getMinU() : getMaxU();
|
||||
float minV = getMinV();
|
||||
float maxV = getMaxV();
|
||||
int brightness = getBrightnessForRender(partialTicks);
|
||||
int brightness = OptifineHandler.usingShaders() ? LightTexture.pack(12, 15 ) : getBrightnessForRender(partialTicks);
|
||||
builder.vertex(vertices[0].getX(), vertices[0].getY(), vertices[0].getZ()).texture(maxU, maxV).color(particleRed, particleGreen, particleBlue, particleAlpha).light(brightness).endVertex();
|
||||
builder.vertex(vertices[1].getX(), vertices[1].getY(), vertices[1].getZ()).texture(maxU, minV).color(particleRed, particleGreen, particleBlue, particleAlpha).light(brightness).endVertex();
|
||||
builder.vertex(vertices[2].getX(), vertices[2].getY(), vertices[2].getZ()).texture(minU, minV).color(particleRed, particleGreen, particleBlue, particleAlpha).light(brightness).endVertex();
|
||||
|
|
|
@ -1,63 +0,0 @@
|
|||
package com.simibubi.create.content.curiosities.projector;
|
||||
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
import com.simibubi.create.AllItems;
|
||||
import com.simibubi.create.foundation.block.ITE;
|
||||
import com.simibubi.create.foundation.gui.ScreenOpener;
|
||||
|
||||
import net.minecraft.block.Block;
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.client.entity.player.ClientPlayerEntity;
|
||||
import net.minecraft.entity.player.PlayerEntity;
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.tileentity.TileEntity;
|
||||
import net.minecraft.util.ActionResultType;
|
||||
import net.minecraft.util.Hand;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraft.util.math.BlockRayTraceResult;
|
||||
import net.minecraft.world.IBlockReader;
|
||||
import net.minecraft.world.World;
|
||||
import net.minecraftforge.api.distmarker.Dist;
|
||||
import net.minecraftforge.api.distmarker.OnlyIn;
|
||||
import net.minecraftforge.fml.DistExecutor;
|
||||
|
||||
public class ChromaticProjectorBlock extends Block implements ITE<ChromaticProjectorTileEntity> {
|
||||
public ChromaticProjectorBlock(Properties p_i48440_1_) {
|
||||
super(p_i48440_1_);
|
||||
}
|
||||
|
||||
@Override
|
||||
public ActionResultType onUse(BlockState state, World worldIn, BlockPos pos, PlayerEntity player, Hand handIn,
|
||||
BlockRayTraceResult hit) {
|
||||
ItemStack held = player.getHeldItemMainhand();
|
||||
if (AllItems.WRENCH.isIn(held))
|
||||
return ActionResultType.PASS;
|
||||
|
||||
DistExecutor.unsafeRunWhenOn(Dist.CLIENT,
|
||||
() -> () -> withTileEntityDo(worldIn, pos, te -> this.displayScreen(te, player)));
|
||||
return ActionResultType.SUCCESS;
|
||||
}
|
||||
|
||||
@OnlyIn(value = Dist.CLIENT)
|
||||
protected void displayScreen(ChromaticProjectorTileEntity te, PlayerEntity player) {
|
||||
if (player instanceof ClientPlayerEntity)
|
||||
ScreenOpener.open(new ChromaticProjectorScreen(te));
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean hasTileEntity(BlockState state) {
|
||||
return true;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public TileEntity createTileEntity(BlockState state, IBlockReader world) {
|
||||
return null;//AllTileEntities.CHROMATIC_PROJECTOR.create();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<ChromaticProjectorTileEntity> getTileEntityClass() {
|
||||
return ChromaticProjectorTileEntity.class;
|
||||
}
|
||||
}
|
|
@ -1,31 +0,0 @@
|
|||
package com.simibubi.create.content.curiosities.projector;
|
||||
|
||||
import com.jozufozu.flywheel.backend.instancing.IDynamicInstance;
|
||||
import com.jozufozu.flywheel.backend.instancing.MaterialManager;
|
||||
import com.jozufozu.flywheel.backend.instancing.tile.TileEntityInstance;
|
||||
import com.simibubi.create.foundation.render.effects.EffectsHandler;
|
||||
|
||||
public class ChromaticProjectorInstance extends TileEntityInstance<ChromaticProjectorTileEntity> implements IDynamicInstance {
|
||||
|
||||
public ChromaticProjectorInstance(MaterialManager<?> renderer, ChromaticProjectorTileEntity tile) {
|
||||
super(renderer, tile);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void beginFrame() {
|
||||
EffectsHandler instance = EffectsHandler.getInstance();
|
||||
|
||||
if (instance != null)
|
||||
instance.addSphere(tile.getFilter());
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean decreaseFramerateWithDistance() {
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void remove() {
|
||||
|
||||
}
|
||||
}
|
|
@ -1,314 +0,0 @@
|
|||
package com.simibubi.create.content.curiosities.projector;
|
||||
|
||||
import java.util.Collections;
|
||||
import java.util.Vector;
|
||||
|
||||
import com.mojang.blaze3d.matrix.MatrixStack;
|
||||
import com.simibubi.create.foundation.gui.AbstractSimiScreen;
|
||||
import com.simibubi.create.foundation.gui.AllGuiTextures;
|
||||
import com.simibubi.create.foundation.gui.AllIcons;
|
||||
import com.simibubi.create.foundation.gui.GuiGameElement;
|
||||
import com.simibubi.create.foundation.gui.widgets.IconButton;
|
||||
import com.simibubi.create.foundation.gui.widgets.ScrollInput;
|
||||
import com.simibubi.create.foundation.gui.widgets.SelectionScrollInput;
|
||||
import com.simibubi.create.foundation.networking.AllPackets;
|
||||
import com.simibubi.create.foundation.tileEntity.behaviour.scrollvalue.ScrollValueBehaviour;
|
||||
import com.simibubi.create.foundation.utility.Lang;
|
||||
|
||||
import net.minecraft.item.ItemStack;
|
||||
import net.minecraft.util.text.ITextComponent;
|
||||
import net.minecraft.util.text.StringTextComponent;
|
||||
|
||||
public class ChromaticProjectorScreen extends AbstractSimiScreen {
|
||||
|
||||
private AllGuiTextures background;
|
||||
private ChromaticProjectorTileEntity tile;
|
||||
private Vector<FilterStep> stages;
|
||||
|
||||
private ItemStack renderedItem = ItemStack.EMPTY;//AllBlocks.CHROMATIC_PROJECTOR.asStack();
|
||||
private Vector<Vector<ScrollInput>> inputs;
|
||||
|
||||
private IconButton confirmButton;
|
||||
|
||||
private ScrollInput radius;
|
||||
private ScrollInput density;
|
||||
private ScrollInput feather;
|
||||
private ScrollInput fade;
|
||||
|
||||
private IconButton blend;
|
||||
|
||||
private ScrollInput strength;
|
||||
private IconButton fieldEffect;
|
||||
|
||||
private IconButton rChannel;
|
||||
private IconButton gChannel;
|
||||
private IconButton bChannel;
|
||||
|
||||
public ChromaticProjectorScreen(ChromaticProjectorTileEntity te) {
|
||||
super(Lang.translate("gui.chromatic_projector.title"));
|
||||
background = AllGuiTextures.PROJECTOR;
|
||||
tile = te;
|
||||
stages = te.stages;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void init() {
|
||||
setWindowSize(background.width, background.height);
|
||||
setWindowOffset(-25, 0);
|
||||
super.init();
|
||||
widgets.clear();
|
||||
|
||||
int x = guiLeft;
|
||||
int y = guiTop;
|
||||
|
||||
inputs = new Vector<>(FilterStep.MAX_STEPS);
|
||||
for (int row = 0; row < inputs.capacity(); row++)
|
||||
inputs.add(new Vector<>(2));
|
||||
|
||||
for (int row = 0; row < stages.size(); row++)
|
||||
initInputsOfRow(row, x, y);
|
||||
|
||||
confirmButton =
|
||||
new IconButton(x + background.width - 33, y + background.height - 26, AllIcons.I_CONFIRM);
|
||||
widgets.add(confirmButton);
|
||||
|
||||
initEffectSettings(x, y);
|
||||
initMetaSettings(x, y);
|
||||
}
|
||||
|
||||
public void initInputsOfRow(int x, int y, int row) {
|
||||
x += 30;
|
||||
y += 18;
|
||||
int rowHeight = 22;
|
||||
|
||||
Vector<ScrollInput> rowInputs = inputs.get(row);
|
||||
rowInputs.forEach(widgets::remove);
|
||||
rowInputs.clear();
|
||||
FilterStep filter = stages.get(row);
|
||||
|
||||
final int x1 = x;
|
||||
final int y1 = y;
|
||||
ScrollInput type =
|
||||
new SelectionScrollInput(x, y + rowHeight * row, 86, 18)
|
||||
.forOptions(ColorEffect.getOptions())
|
||||
.calling(state -> stageUpdated(x1, y1, row, state))
|
||||
.setState(filter.filter.id)
|
||||
.titled(Lang.translate("gui.chromatic_projector.filter"));
|
||||
ScrollInput value =
|
||||
new ScrollInput(x + 86 + 2, y + rowHeight * row, 28, 18)
|
||||
.calling(state -> filter.value = state);
|
||||
|
||||
rowInputs.add(type);
|
||||
rowInputs.add(value);
|
||||
|
||||
widgets.addAll(rowInputs);
|
||||
updateParamsOfRow(row);
|
||||
}
|
||||
|
||||
public void updateParamsOfRow(int row) {
|
||||
FilterStep instruction = stages.get(row);
|
||||
Vector<ScrollInput> rowInputs = inputs.get(row);
|
||||
ColorEffect def = instruction.filter;
|
||||
boolean hasValue = def.hasParameter;
|
||||
|
||||
ScrollInput value = rowInputs.get(1);
|
||||
value.active = value.visible = hasValue;
|
||||
if (hasValue)
|
||||
value.withRange(def.minValue, def.maxValue + 1)
|
||||
//.titled(Lang.translate(def.parameterKey))
|
||||
.setState(instruction.value)
|
||||
.onChanged();
|
||||
|
||||
value.withStepFunction(def.step());
|
||||
}
|
||||
|
||||
private void initEffectSettings(int x, int y) {
|
||||
x += 188;
|
||||
y += 40;
|
||||
|
||||
radius = new ScrollInput(x, y, 28, 18)
|
||||
.titled(Lang.translate("gui.chromatic_projector.radius"))
|
||||
.withStepFunction(ctx -> step(ctx, 2))
|
||||
.calling(tile::setRadius)
|
||||
.withRange(0, 201)
|
||||
.setState((int) (tile.radius * 2));
|
||||
y += 22;
|
||||
feather = new ScrollInput(x, y, 28, 18)
|
||||
.titled(Lang.translate("gui.chromatic_projector.feather"))
|
||||
.withStepFunction(ctx -> step(ctx, 5))
|
||||
.calling(tile::setFeather)
|
||||
.withRange(0, 201)
|
||||
.setState((int) (tile.feather * 10));
|
||||
y += 22;
|
||||
density = new ScrollInput(x, y, 28, 18)
|
||||
.titled(Lang.translate("gui.chromatic_projector.density"))
|
||||
.withStepFunction(ctx -> step(ctx, 10))
|
||||
.calling(tile::setDensity)
|
||||
.withRange(0, 401)
|
||||
.setState((int) (tile.density * 100));
|
||||
y += 22;
|
||||
fade = new ScrollInput(x, y, 28, 18)
|
||||
.titled(Lang.translate("gui.chromatic_projector.fade"))
|
||||
.withStepFunction(ctx -> step(ctx, 1))
|
||||
.calling(tile::setFade)
|
||||
.withRange(0, 51)
|
||||
.setState((int) (tile.fade * 10));
|
||||
|
||||
Collections.addAll(widgets, radius, density, feather, fade);
|
||||
}
|
||||
|
||||
private void initMetaSettings(int x, int y) {
|
||||
y += background.height - 23;
|
||||
|
||||
blend = new IconButton(x + 16, y, AllIcons.I_FX_BLEND);
|
||||
blend.setToolTip(Lang.translate("gui.chromatic_projector.blend"));
|
||||
|
||||
int channelX = x + 39;
|
||||
rChannel = new IconButton(channelX, y, AllIcons.I_FX_BLEND);
|
||||
rChannel.setToolTip(new StringTextComponent("R"));
|
||||
channelX += 18;
|
||||
gChannel = new IconButton(channelX, y, AllIcons.I_FX_BLEND);
|
||||
gChannel.setToolTip(new StringTextComponent("G"));
|
||||
channelX += 18;
|
||||
bChannel = new IconButton(channelX, y, AllIcons.I_FX_BLEND);
|
||||
bChannel.setToolTip(new StringTextComponent("B"));
|
||||
|
||||
fieldEffect = new IconButton(x + 135, y, tile.field ? AllIcons.I_FX_FIELD_ON : AllIcons.I_FX_FIELD_OFF);
|
||||
fieldEffect.setToolTip(Lang.translate("gui.chromatic_projector.field"));
|
||||
|
||||
strength = new ScrollInput(x + 159, y, 25, 18)
|
||||
.titled(Lang.translate("gui.chromatic_projector.strength"))
|
||||
.withStepFunction(ctx -> step(ctx, 5))
|
||||
.calling(tile::setStrength)
|
||||
.withRange(-100, 101)
|
||||
.setState((int) (tile.strength * 100));
|
||||
|
||||
Collections.addAll(widgets, blend, rChannel, gChannel, bChannel, fieldEffect, strength);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void renderWindow(MatrixStack ms, int mouseX, int mouseY, float partialTicks) {
|
||||
int x = guiLeft;
|
||||
int y = guiTop;
|
||||
|
||||
background.draw(ms, this, x, y);
|
||||
|
||||
for (int row = 0; row < stages.capacity(); row++) {
|
||||
AllGuiTextures toDraw = AllGuiTextures.PROJECTOR_EMPTY;
|
||||
int yOffset = toDraw.height * row;
|
||||
if (row >= stages.size()) {
|
||||
toDraw.draw(ms, x, y + 14 + yOffset);
|
||||
continue;
|
||||
}
|
||||
|
||||
FilterStep step = stages.get(row);
|
||||
ColorEffect def = step.filter;
|
||||
def.background.draw(ms, x, y + 14 + yOffset);
|
||||
|
||||
if (def != ColorEffect.END)
|
||||
label(ms, 36, yOffset - 3, Lang.translate(def.translationKey));
|
||||
if (def.hasParameter) {
|
||||
String text = step.filter.formatValue(step.value);
|
||||
int stringWidth = textRenderer.getStringWidth(text);
|
||||
label(ms, 118 + (12 - stringWidth / 2), yOffset - 3, new StringTextComponent(text));
|
||||
}
|
||||
}
|
||||
|
||||
renderScroll(ms, radius, 2f);
|
||||
renderScroll(ms, density, 100f);
|
||||
renderScroll(ms, feather, 10f);
|
||||
renderScroll(ms, fade, 10f);
|
||||
|
||||
renderScroll(ms, strength, 100f);
|
||||
|
||||
drawCenteredText(ms, textRenderer, title, x + (background.width - 8) / 2, y + 3, 0xFFFFFF);
|
||||
|
||||
GuiGameElement.of(renderedItem)
|
||||
.scale(5)
|
||||
.at(x + background.width + 6, y + background.height - 56, -200)
|
||||
.render(ms);
|
||||
}
|
||||
|
||||
private void renderScroll(MatrixStack matrixStack, ScrollInput input, float divisor) {
|
||||
String text = String.valueOf(input.getState() / divisor);
|
||||
|
||||
// int stringWidth = textRenderer.getStringWidth(text);
|
||||
textRenderer.drawWithShadow(matrixStack, text, input.x + 2, input.y + 5, 0xFFFFEE);
|
||||
}
|
||||
|
||||
private void label(MatrixStack matrixStack, int x, int y, ITextComponent text) {
|
||||
textRenderer.drawWithShadow(matrixStack, text, guiLeft + x, guiTop + 26 + y, 0xFFFFEE);
|
||||
}
|
||||
|
||||
private static Integer step(ScrollValueBehaviour.StepContext ctx, int base) {
|
||||
if (ctx.control) return 1;
|
||||
return base * (ctx.shift ? 5 : 1) - ctx.currentValue % base;
|
||||
}
|
||||
|
||||
public void sendPacket() {
|
||||
AllPackets.channel.sendToServer(new ConfigureProjectorPacket(tile));
|
||||
}
|
||||
|
||||
@Override
|
||||
public void removed() {
|
||||
sendPacket();
|
||||
}
|
||||
|
||||
private void stageUpdated(int x, int y, int index, int state) {
|
||||
ColorEffect newValue = ColorEffect.all.get(state);
|
||||
stages.get(index).filter = newValue;
|
||||
stages.get(index).value = newValue.defaultValue;
|
||||
updateParamsOfRow(index);
|
||||
if (newValue == ColorEffect.END) {
|
||||
for (int i = stages.size() - 1; i > index; i--) {
|
||||
stages.remove(i);
|
||||
Vector<ScrollInput> rowInputs = inputs.get(i);
|
||||
rowInputs.forEach(widgets::remove);
|
||||
rowInputs.clear();
|
||||
}
|
||||
} else {
|
||||
if (index + 1 < stages.capacity() && index + 1 == stages.size()) {
|
||||
stages.add(new FilterStep(ColorEffect.END));
|
||||
initInputsOfRow(x, y, index + 1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean mouseClicked(double x, double y, int button) {
|
||||
if (confirmButton.isHovered()) {
|
||||
client.player.closeScreen();
|
||||
return true;
|
||||
}
|
||||
|
||||
if (blend.isHovered()) {
|
||||
tile.blend = !tile.blend;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (fieldEffect.isHovered()) {
|
||||
tile.field = !tile.field;
|
||||
|
||||
fieldEffect.setIcon(tile.field ? AllIcons.I_FX_FIELD_ON : AllIcons.I_FX_FIELD_OFF);
|
||||
return fieldEffect.mouseClicked(x, y, button);
|
||||
}
|
||||
|
||||
if (rChannel.isHovered()) {
|
||||
tile.rMask = !tile.rMask;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (gChannel.isHovered()) {
|
||||
tile.gMask = !tile.gMask;
|
||||
return true;
|
||||
}
|
||||
|
||||
if (bChannel.isHovered()) {
|
||||
tile.bMask = !tile.bMask;
|
||||
return true;
|
||||
}
|
||||
|
||||
return super.mouseClicked(x, y, button);
|
||||
}
|
||||
|
||||
}
|
|
@ -1,140 +0,0 @@
|
|||
package com.simibubi.create.content.curiosities.projector;
|
||||
|
||||
import java.util.Vector;
|
||||
|
||||
import com.jozufozu.flywheel.backend.instancing.IInstanceRendered;
|
||||
import com.simibubi.create.foundation.render.effects.FilterSphere;
|
||||
import com.simibubi.create.foundation.tileEntity.SyncedTileEntity;
|
||||
|
||||
import net.minecraft.block.BlockState;
|
||||
import net.minecraft.nbt.CompoundNBT;
|
||||
import net.minecraft.tileentity.TileEntityType;
|
||||
import net.minecraft.util.math.BlockPos;
|
||||
import net.minecraftforge.common.util.Constants;
|
||||
|
||||
public class ChromaticProjectorTileEntity extends SyncedTileEntity implements IInstanceRendered {
|
||||
|
||||
Vector<FilterStep> stages = FilterStep.createDefault();
|
||||
|
||||
float radius = 3f;
|
||||
|
||||
float feather = 1;
|
||||
float density = 1;
|
||||
float fade = 1;
|
||||
boolean blend = true;
|
||||
|
||||
public boolean surface = true;
|
||||
public boolean field = true;
|
||||
public float strength = 1;
|
||||
|
||||
public boolean rMask = true;
|
||||
public boolean gMask = true;
|
||||
public boolean bMask = true;
|
||||
|
||||
public ChromaticProjectorTileEntity(TileEntityType<?> te) {
|
||||
super(te);
|
||||
}
|
||||
|
||||
public FilterSphere getFilter() {
|
||||
|
||||
BlockPos pos = getPos();
|
||||
FilterSphere sphere = new FilterSphere();
|
||||
|
||||
sphere.x = (float) (pos.getX() + 0.5);
|
||||
sphere.y = (float) (pos.getY() + 0.5);
|
||||
sphere.z = (float) (pos.getZ() + 0.5);
|
||||
sphere.radius = radius;
|
||||
|
||||
sphere.feather = feather;
|
||||
sphere.density = density;
|
||||
sphere.fade = fade;
|
||||
sphere.blend = blend;
|
||||
|
||||
sphere.surface = surface;
|
||||
sphere.field = field;
|
||||
sphere.strength = strength;
|
||||
|
||||
sphere.rMask = rMask;
|
||||
sphere.gMask = gMask;
|
||||
sphere.bMask = bMask;
|
||||
|
||||
sphere.filter = FilterStep.fold(stages);
|
||||
return sphere;
|
||||
}
|
||||
|
||||
public ChromaticProjectorTileEntity setRadius(int radius) {
|
||||
this.radius = radius / 2f;
|
||||
return this;
|
||||
}
|
||||
|
||||
public ChromaticProjectorTileEntity setDensity(int density) {
|
||||
this.density = density / 100f;
|
||||
return this;
|
||||
}
|
||||
|
||||
public ChromaticProjectorTileEntity setFeather(int feather) {
|
||||
this.feather = feather / 10f;
|
||||
return this;
|
||||
}
|
||||
|
||||
public ChromaticProjectorTileEntity setFade(int fade) {
|
||||
this.fade = fade / 10f;
|
||||
return this;
|
||||
}
|
||||
|
||||
public ChromaticProjectorTileEntity setBlend(boolean blend) {
|
||||
this.blend = blend;
|
||||
return this;
|
||||
}
|
||||
|
||||
public ChromaticProjectorTileEntity setStrength(int strength) {
|
||||
this.strength = strength / 100f;
|
||||
return this;
|
||||
}
|
||||
|
||||
@Override
|
||||
public CompoundNBT write(CompoundNBT tag) {
|
||||
super.write(tag);
|
||||
|
||||
tag.put("filters", FilterStep.writeAll(stages));
|
||||
|
||||
tag.putFloat("radius", radius);
|
||||
|
||||
tag.putFloat("feather", feather);
|
||||
tag.putFloat("density", density);
|
||||
tag.putFloat("fade", fade);
|
||||
tag.putBoolean("blend", blend);
|
||||
|
||||
tag.putBoolean("surface", surface);
|
||||
tag.putBoolean("field", field);
|
||||
tag.putFloat("strength", strength);
|
||||
|
||||
tag.putBoolean("rMask", rMask);
|
||||
tag.putBoolean("gMask", gMask);
|
||||
tag.putBoolean("bMask", bMask);
|
||||
|
||||
return tag;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void fromTag(BlockState state, CompoundNBT tag) {
|
||||
super.fromTag(state, tag);
|
||||
|
||||
stages = FilterStep.readAll(tag.getList("filters", Constants.NBT.TAG_COMPOUND));
|
||||
|
||||
radius = tag.getFloat("radius");
|
||||
|
||||
feather = tag.getFloat("feather");
|
||||
density = tag.getFloat("density");
|
||||
fade = tag.getFloat("fade");
|
||||
blend = tag.getBoolean("blend");
|
||||
|
||||
surface = tag.getBoolean("surface");
|
||||
field = tag.getBoolean("field");
|
||||
strength = tag.getFloat("strength");
|
||||
|
||||
rMask = tag.getBoolean("rMask");
|
||||
gMask = tag.getBoolean("gMask");
|
||||
bMask = tag.getBoolean("bMask");
|
||||
}
|
||||
}
|
|
@ -1,113 +0,0 @@
|
|||
package com.simibubi.create.content.curiosities.projector;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import com.simibubi.create.foundation.gui.AllGuiTextures;
|
||||
import com.simibubi.create.foundation.render.effects.ColorMatrices;
|
||||
import com.simibubi.create.foundation.tileEntity.behaviour.scrollvalue.ScrollValueBehaviour;
|
||||
import com.simibubi.create.foundation.utility.Lang;
|
||||
|
||||
import net.minecraft.util.math.vector.Matrix4f;
|
||||
import net.minecraft.util.text.ITextComponent;
|
||||
|
||||
public class ColorEffect {
|
||||
static final ArrayList<ColorEffect> all = new ArrayList<>();
|
||||
static final HashMap<String, ColorEffect> lookup = new HashMap<>();
|
||||
private static int nextId = 0;
|
||||
|
||||
public static final ColorEffect SEPIA = create("sepia", ColorMatrices::sepia);
|
||||
public static final ColorEffect GRAYSCALE = create("grayscale", ColorMatrices::grayscale);
|
||||
public static final ColorEffect DARKEN = create("darken", ColorMatrices::darken).setDefaultValue(20);
|
||||
public static final ColorEffect CONTRAST = create("contrast", ColorMatrices::contrast).setRange(0, 200).setDefaultValue(100);
|
||||
public static final ColorEffect SATURATE = create("saturate", ColorMatrices::saturate).setRange(0, 200);
|
||||
public static final ColorEffect HUE_SHIFT = create("hue_shift", ColorMatrices::hueShift).setRange(0, 360).setDivisor(1f).setDefaultValue(120);
|
||||
public static final ColorEffect INVERT = create("invert", ColorMatrices::invert);
|
||||
public static final ColorEffect END = create("end", ColorMatrices::identity).setBackground(AllGuiTextures.PROJECTOR_END);
|
||||
|
||||
boolean hasParameter;
|
||||
AllGuiTextures background;
|
||||
|
||||
int defaultValue = 100;
|
||||
int minValue = 0;
|
||||
int maxValue = 100;
|
||||
float divisor = 100f;
|
||||
|
||||
final int id;
|
||||
final FilterFactory filter;
|
||||
final String name;
|
||||
final String translationKey;
|
||||
|
||||
public ColorEffect(String name, FilterFactory filter) {
|
||||
this.filter = filter;
|
||||
this.name = name;
|
||||
this.translationKey = "gui.chromatic_projector.filter." + Lang.asId(name);
|
||||
this.id = nextId++;
|
||||
|
||||
lookup.put(name, this);
|
||||
all.add(this);
|
||||
}
|
||||
|
||||
public ColorEffect setHasParameter(boolean hasParameter) {
|
||||
this.hasParameter = hasParameter;
|
||||
return setBackground(hasParameter ? AllGuiTextures.PROJECTOR_FILTER_STRENGTH : AllGuiTextures.PROJECTOR_FILTER);
|
||||
}
|
||||
|
||||
public ColorEffect setBackground(AllGuiTextures background) {
|
||||
this.background = background;
|
||||
return this;
|
||||
}
|
||||
|
||||
public ColorEffect setDefaultValue(int defaultValue) {
|
||||
this.defaultValue = defaultValue;
|
||||
return this;
|
||||
}
|
||||
|
||||
public ColorEffect setRange(int minValue, int maxValue) {
|
||||
this.minValue = minValue;
|
||||
this.maxValue = maxValue;
|
||||
return this;
|
||||
}
|
||||
|
||||
public ColorEffect setDivisor(float divisor) {
|
||||
this.divisor = divisor;
|
||||
return this;
|
||||
}
|
||||
|
||||
public Function<ScrollValueBehaviour.StepContext, Integer> step() {
|
||||
return c -> {
|
||||
if (c.control) return 1;
|
||||
if (c.shift) return 20;
|
||||
return 5;
|
||||
};
|
||||
}
|
||||
|
||||
String formatValue(int value) {
|
||||
if (this == HUE_SHIFT)
|
||||
return value + Lang.translate("generic.unit.degrees").getString();
|
||||
return "" + value;
|
||||
}
|
||||
|
||||
static List<ITextComponent> getOptions() {
|
||||
List<ITextComponent> options = new ArrayList<>();
|
||||
for (ColorEffect entry : all)
|
||||
options.add(Lang.translate(entry.translationKey));
|
||||
return options;
|
||||
}
|
||||
|
||||
@FunctionalInterface
|
||||
public interface FilterFactory {
|
||||
Matrix4f create(float param);
|
||||
}
|
||||
|
||||
public static ColorEffect create(String name, Supplier<Matrix4f> filter) {
|
||||
return new ColorEffect(name, $ -> filter.get()).setHasParameter(false);
|
||||
}
|
||||
|
||||
public static ColorEffect create(String name, FilterFactory filter) {
|
||||
return new ColorEffect(name, filter).setHasParameter(true);
|
||||
}
|
||||
}
|
|
@ -1,126 +0,0 @@
|
|||
package com.simibubi.create.content.curiosities.projector;
|
||||
|
||||
import java.util.Vector;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
import com.simibubi.create.foundation.networking.TileEntityConfigurationPacket;
|
||||
|
||||
import net.minecraft.nbt.CompoundNBT;
|
||||
import net.minecraft.network.PacketBuffer;
|
||||
|
||||
public class ConfigureProjectorPacket extends TileEntityConfigurationPacket<ChromaticProjectorTileEntity> {
|
||||
|
||||
Vector<CompoundNBT> stages;
|
||||
float radius;
|
||||
|
||||
float feather;
|
||||
float density;
|
||||
float fade;
|
||||
boolean blend;
|
||||
|
||||
public boolean surface;
|
||||
public boolean field;
|
||||
public float strength;
|
||||
|
||||
public boolean rMask;
|
||||
public boolean gMask;
|
||||
public boolean bMask;
|
||||
|
||||
public ConfigureProjectorPacket(PacketBuffer buffer) {
|
||||
super(buffer);
|
||||
}
|
||||
|
||||
public ConfigureProjectorPacket(ChromaticProjectorTileEntity tile) {
|
||||
super(tile.getPos());
|
||||
|
||||
stages = tile.stages.stream()
|
||||
.map(FilterStep::write)
|
||||
.collect(Collectors.toCollection(Vector::new));
|
||||
radius = tile.radius;
|
||||
|
||||
feather = tile.feather;
|
||||
density = tile.density;
|
||||
fade = tile.fade;
|
||||
blend = tile.blend;
|
||||
|
||||
surface = tile.surface;
|
||||
field = tile.field;
|
||||
strength = tile.strength;
|
||||
|
||||
rMask = tile.rMask;
|
||||
gMask = tile.gMask;
|
||||
bMask = tile.bMask;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void writeSettings(PacketBuffer buffer) {
|
||||
buffer.writeFloat(radius);
|
||||
|
||||
buffer.writeFloat(feather);
|
||||
buffer.writeFloat(density);
|
||||
buffer.writeFloat(fade);
|
||||
buffer.writeBoolean(blend);
|
||||
|
||||
buffer.writeBoolean(surface);
|
||||
buffer.writeBoolean(field);
|
||||
buffer.writeFloat(strength);
|
||||
|
||||
buffer.writeBoolean(rMask);
|
||||
buffer.writeBoolean(gMask);
|
||||
buffer.writeBoolean(bMask);
|
||||
|
||||
buffer.writeInt(stages.size());
|
||||
for (CompoundNBT stage : stages) {
|
||||
buffer.writeCompoundTag(stage);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void readSettings(PacketBuffer buffer) {
|
||||
radius = buffer.readFloat();
|
||||
|
||||
feather = buffer.readFloat();
|
||||
density = buffer.readFloat();
|
||||
fade = buffer.readFloat();
|
||||
blend = buffer.readBoolean();
|
||||
|
||||
surface = buffer.readBoolean();
|
||||
field = buffer.readBoolean();
|
||||
strength = buffer.readFloat();
|
||||
|
||||
rMask = buffer.readBoolean();
|
||||
gMask = buffer.readBoolean();
|
||||
bMask = buffer.readBoolean();
|
||||
|
||||
int count = buffer.readInt();
|
||||
stages = new Vector<>(FilterStep.MAX_STEPS);
|
||||
|
||||
for (int i = 0; i < count; i++) {
|
||||
stages.add(buffer.readCompoundTag());
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void applySettings(ChromaticProjectorTileEntity tile) {
|
||||
tile.stages = stages.stream()
|
||||
.map(FilterStep::new)
|
||||
.collect(Collectors.toCollection(Vector::new));
|
||||
|
||||
tile.radius = radius;
|
||||
|
||||
tile.feather = feather;
|
||||
tile.density = density;
|
||||
tile.fade = fade;
|
||||
tile.blend = blend;
|
||||
|
||||
tile.surface = surface;
|
||||
tile.field = field;
|
||||
tile.strength = strength;
|
||||
|
||||
tile.rMask = rMask;
|
||||
tile.gMask = gMask;
|
||||
tile.bMask = bMask;
|
||||
|
||||
tile.sendData();
|
||||
}
|
||||
}
|
|
@ -1,85 +0,0 @@
|
|||
package com.simibubi.create.content.curiosities.projector;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.Vector;
|
||||
|
||||
import com.simibubi.create.foundation.render.effects.ColorMatrices;
|
||||
|
||||
import net.minecraft.nbt.CompoundNBT;
|
||||
import net.minecraft.nbt.ListNBT;
|
||||
import net.minecraft.util.math.vector.Matrix4f;
|
||||
|
||||
public class FilterStep {
|
||||
|
||||
public static final int MAX_STEPS = 6;
|
||||
ColorEffect filter;
|
||||
int value;
|
||||
|
||||
public FilterStep(ColorEffect filter) {
|
||||
this.filter = filter;
|
||||
}
|
||||
|
||||
public FilterStep(ColorEffect filter, int value) {
|
||||
this.filter = filter;
|
||||
this.value = value;
|
||||
}
|
||||
|
||||
public FilterStep(CompoundNBT nbt) {
|
||||
this.filter = ColorEffect.lookup.get(nbt.getString("id"));
|
||||
this.value = nbt.getInt("value");
|
||||
}
|
||||
|
||||
public Matrix4f createFilter() {
|
||||
return filter.filter.create(value / filter.divisor);
|
||||
}
|
||||
|
||||
public CompoundNBT write() {
|
||||
CompoundNBT nbt = new CompoundNBT();
|
||||
|
||||
nbt.putString("id", filter.name);
|
||||
nbt.putInt("value", value);
|
||||
|
||||
return nbt;
|
||||
}
|
||||
|
||||
public static Vector<FilterStep> readAll(ListNBT list) {
|
||||
Vector<FilterStep> steps = new Vector<>(MAX_STEPS);
|
||||
|
||||
for (int i = 0; i < list.size(); i++) {
|
||||
steps.add(new FilterStep(list.getCompound(i)));
|
||||
}
|
||||
|
||||
return steps;
|
||||
}
|
||||
|
||||
public static ListNBT writeAll(Vector<FilterStep> filters) {
|
||||
ListNBT out = new ListNBT();
|
||||
|
||||
for (FilterStep filter : filters) {
|
||||
out.add(filter.write());
|
||||
}
|
||||
|
||||
return out;
|
||||
}
|
||||
|
||||
public static Matrix4f fold(Vector<FilterStep> filters) {
|
||||
Iterator<FilterStep> stepIterator = filters.stream().filter(it -> it != null && it.filter != ColorEffect.END).iterator();
|
||||
|
||||
if (stepIterator.hasNext()) {
|
||||
Matrix4f accum = stepIterator.next().createFilter();
|
||||
|
||||
stepIterator.forEachRemaining(filterStep -> accum.multiply(filterStep.createFilter()));
|
||||
|
||||
return accum;
|
||||
}
|
||||
|
||||
return ColorMatrices.identity();
|
||||
}
|
||||
|
||||
public static Vector<FilterStep> createDefault() {
|
||||
Vector<FilterStep> instructions = new Vector<>(MAX_STEPS);
|
||||
instructions.add(new FilterStep(ColorEffect.SEPIA, 100));
|
||||
instructions.add(new FilterStep(ColorEffect.END));
|
||||
return instructions;
|
||||
}
|
||||
}
|
|
@ -1,30 +0,0 @@
|
|||
package com.simibubi.create.foundation.mixin;
|
||||
|
||||
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;
|
||||
|
||||
import net.minecraft.entity.Entity;
|
||||
import net.minecraft.nbt.CompoundNBT;
|
||||
import net.minecraftforge.common.capabilities.CapabilityProvider;
|
||||
|
||||
@Mixin(Entity.class)
|
||||
public abstract class HeavyBootsOnEntityMixin extends CapabilityProvider<Entity> {
|
||||
|
||||
protected HeavyBootsOnEntityMixin(Class<Entity> baseClass) {
|
||||
super(baseClass);
|
||||
}
|
||||
|
||||
@Shadow
|
||||
public abstract CompoundNBT getPersistentData();
|
||||
|
||||
@Inject(at = @At("HEAD"), method = "canSwim", cancellable = true)
|
||||
public void noSwimmingWithHeavyBootsOn(CallbackInfoReturnable<Boolean> cir) {
|
||||
CompoundNBT persistentData = getPersistentData();
|
||||
if (persistentData.contains("HeavyBoots"))
|
||||
cir.setReturnValue(false);
|
||||
}
|
||||
|
||||
}
|
|
@ -22,7 +22,6 @@ import com.simibubi.create.content.contraptions.components.structureMovement.tra
|
|||
import com.simibubi.create.content.contraptions.fluids.actors.FluidSplashPacket;
|
||||
import com.simibubi.create.content.contraptions.relays.advanced.sequencer.ConfigureSequencedGearshiftPacket;
|
||||
import com.simibubi.create.content.curiosities.bell.SoulPulseEffectPacket;
|
||||
import com.simibubi.create.content.curiosities.projector.ConfigureProjectorPacket;
|
||||
import com.simibubi.create.content.curiosities.symmetry.SymmetryEffectPacket;
|
||||
import com.simibubi.create.content.curiosities.tools.BlueprintAssignCompleteRecipePacket;
|
||||
import com.simibubi.create.content.curiosities.tools.ExtendoGripInteractionPacket;
|
||||
|
@ -74,7 +73,6 @@ public enum AllPackets {
|
|||
CONFIGURE_STOCKSWITCH(ConfigureStockswitchPacket.class, ConfigureStockswitchPacket::new, PLAY_TO_SERVER),
|
||||
CONFIGURE_SEQUENCER(ConfigureSequencedGearshiftPacket.class, ConfigureSequencedGearshiftPacket::new,
|
||||
PLAY_TO_SERVER),
|
||||
CONFIGURE_PROJECTOR(ConfigureProjectorPacket.class, ConfigureProjectorPacket::new, PLAY_TO_SERVER),
|
||||
PLACE_SCHEMATIC(SchematicPlacePacket.class, SchematicPlacePacket::new, PLAY_TO_SERVER),
|
||||
UPLOAD_SCHEMATIC(SchematicUploadPacket.class, SchematicUploadPacket::new, PLAY_TO_SERVER),
|
||||
CLEAR_CONTAINER(ClearContainerPacket.class, ClearContainerPacket::new, PLAY_TO_SERVER),
|
||||
|
|
|
@ -9,7 +9,6 @@ import com.jozufozu.flywheel.backend.loading.ModelTemplate;
|
|||
import com.jozufozu.flywheel.core.WorldContext;
|
||||
import com.jozufozu.flywheel.event.GatherContextEvent;
|
||||
import com.simibubi.create.content.contraptions.components.structureMovement.render.ContraptionProgram;
|
||||
import com.simibubi.create.foundation.render.effects.EffectsContext;
|
||||
|
||||
import net.minecraft.util.ResourceLocation;
|
||||
import net.minecraftforge.api.distmarker.Dist;
|
||||
|
@ -19,7 +18,6 @@ import net.minecraftforge.api.distmarker.OnlyIn;
|
|||
public class CreateContexts {
|
||||
private static final ResourceLocation CONTRAPTION = new ResourceLocation("create", "context/contraption");
|
||||
|
||||
public static EffectsContext EFFECTS;
|
||||
public static WorldContext<ContraptionProgram> CWORLD;
|
||||
public static WorldContext<ContraptionProgram> STRUCTURE;
|
||||
|
||||
|
@ -28,7 +26,6 @@ public class CreateContexts {
|
|||
|
||||
SpecMetaRegistry.register(RainbowDebugStateProvider.INSTANCE);
|
||||
|
||||
EFFECTS = backend.register(new EffectsContext(backend));
|
||||
CWORLD = backend.register(contraptionContext(backend));
|
||||
STRUCTURE = backend.register(contraptionContext(backend)
|
||||
.withSpecStream(() -> Stream.of(AllProgramSpecs.STRUCTURE))
|
||||
|
|
|
@ -1,129 +0,0 @@
|
|||
package com.simibubi.create.foundation.render.effects;
|
||||
|
||||
import com.simibubi.create.foundation.utility.AngleHelper;
|
||||
|
||||
import net.minecraft.util.math.MathHelper;
|
||||
import net.minecraft.util.math.vector.Matrix4f;
|
||||
|
||||
public class ColorMatrices {
|
||||
|
||||
public static final float lumaR = 0.3086f;
|
||||
public static final float lumaG = 0.6094f;
|
||||
public static final float lumaB = 0.0820f;
|
||||
|
||||
public static Matrix4f invert() {
|
||||
Matrix4f invert = new Matrix4f();
|
||||
invert.a00 = -1.0F;
|
||||
invert.a11 = -1.0F;
|
||||
invert.a22 = -1.0F;
|
||||
invert.a33 = -1.0F;
|
||||
invert.a30 = 1;
|
||||
invert.a31 = 1;
|
||||
invert.a32 = 1;
|
||||
|
||||
return invert;
|
||||
}
|
||||
|
||||
public static Matrix4f grayscale() {
|
||||
Matrix4f mat = new Matrix4f();
|
||||
|
||||
mat.a00 = mat.a01 = mat.a02 = lumaR;
|
||||
mat.a10 = mat.a11 = mat.a12 = lumaG;
|
||||
mat.a20 = mat.a21 = mat.a22 = lumaB;
|
||||
mat.a33 = 1;
|
||||
|
||||
return mat;
|
||||
}
|
||||
|
||||
public static Matrix4f saturate(float s) {
|
||||
Matrix4f mat = new Matrix4f();
|
||||
|
||||
mat.a00 = (1.0f - s) * lumaR + s;
|
||||
mat.a01 = (1.0f - s) * lumaR;
|
||||
mat.a02 = (1.0f - s) * lumaR;
|
||||
mat.a10 = (1.0f - s) * lumaG;
|
||||
mat.a11 = (1.0f - s) * lumaG + s;
|
||||
mat.a12 = (1.0f - s) * lumaG;
|
||||
mat.a20 = (1.0f - s) * lumaB;
|
||||
mat.a21 = (1.0f - s) * lumaB;
|
||||
mat.a22 = (1.0f - s) * lumaB + s;
|
||||
|
||||
mat.a33 = 1;
|
||||
|
||||
return mat;
|
||||
}
|
||||
|
||||
public static Matrix4f sepia(float amount) {
|
||||
Matrix4f mat = new Matrix4f();
|
||||
|
||||
mat.a00 = (float) (0.393 + 0.607 * (1 - amount));
|
||||
mat.a10 = (float) (0.769 - 0.769 * (1 - amount));
|
||||
mat.a20 = (float) (0.189 - 0.189 * (1 - amount));
|
||||
mat.a01 = (float) (0.349 - 0.349 * (1 - amount));
|
||||
mat.a11 = (float) (0.686 + 0.314 * (1 - amount));
|
||||
mat.a21 = (float) (0.168 - 0.168 * (1 - amount));
|
||||
mat.a02 = (float) (0.272 - 0.272 * (1 - amount));
|
||||
mat.a12 = (float) (0.534 - 0.534 * (1 - amount));
|
||||
mat.a22 = (float) (0.131 + 0.869 * (1 - amount));
|
||||
|
||||
mat.a33 = 1;
|
||||
|
||||
return mat;
|
||||
}
|
||||
|
||||
// https://stackoverflow.com/a/8510751
|
||||
public static Matrix4f hueShift(float rot) {
|
||||
Matrix4f mat = new Matrix4f();
|
||||
|
||||
mat.loadIdentity();
|
||||
|
||||
float cosA = MathHelper.cos(AngleHelper.rad(rot));
|
||||
float sinA = MathHelper.sin(AngleHelper.rad(rot));
|
||||
mat.a00 = (float) (cosA + (1.0 - cosA) / 3.0);
|
||||
mat.a01 = (float) (1. / 3. * (1.0 - cosA) - MathHelper.sqrt(1. / 3.) * sinA);
|
||||
mat.a02 = (float) (1. / 3. * (1.0 - cosA) + MathHelper.sqrt(1. / 3.) * sinA);
|
||||
mat.a10 = (float) (1. / 3. * (1.0 - cosA) + MathHelper.sqrt(1. / 3.) * sinA);
|
||||
mat.a11 = (float) (cosA + 1. / 3. * (1.0 - cosA));
|
||||
mat.a12 = (float) (1. / 3. * (1.0 - cosA) - MathHelper.sqrt(1. / 3.) * sinA);
|
||||
mat.a20 = (float) (1. / 3. * (1.0 - cosA) - MathHelper.sqrt(1. / 3.) * sinA);
|
||||
mat.a21 = (float) (1. / 3. * (1.0 - cosA) + MathHelper.sqrt(1. / 3.) * sinA);
|
||||
mat.a22 = (float) (cosA + 1. / 3. * (1.0 - cosA));
|
||||
|
||||
return mat;
|
||||
}
|
||||
|
||||
public static Matrix4f darken(float amount) {
|
||||
Matrix4f mat = new Matrix4f();
|
||||
mat.loadIdentity();
|
||||
mat.multiply(1f - amount);
|
||||
return mat;
|
||||
}
|
||||
|
||||
public static Matrix4f brightness(float amount) {
|
||||
Matrix4f mat = new Matrix4f();
|
||||
mat.loadIdentity();
|
||||
mat.a03 = amount;
|
||||
mat.a13 = amount;
|
||||
mat.a23 = amount;
|
||||
return mat;
|
||||
}
|
||||
|
||||
public static Matrix4f contrast(float amount) {
|
||||
Matrix4f sub = new Matrix4f();
|
||||
sub.a00 = amount;
|
||||
sub.a11 = amount;
|
||||
sub.a22 = amount;
|
||||
sub.a33 = 1;
|
||||
sub.a30 = 0.5f - amount * 0.5f;
|
||||
sub.a31 = 0.5f - amount * 0.5f;
|
||||
sub.a32 = 0.5f - amount * 0.5f;
|
||||
|
||||
return sub;
|
||||
}
|
||||
|
||||
public static Matrix4f identity() {
|
||||
Matrix4f mat = new Matrix4f();
|
||||
mat.loadIdentity();
|
||||
return mat;
|
||||
}
|
||||
}
|
|
@ -1,38 +0,0 @@
|
|||
package com.simibubi.create.foundation.render.effects;
|
||||
|
||||
import com.jozufozu.flywheel.backend.Backend;
|
||||
import com.jozufozu.flywheel.backend.ShaderContext;
|
||||
import com.jozufozu.flywheel.backend.gl.shader.ShaderType;
|
||||
import com.jozufozu.flywheel.backend.loading.Shader;
|
||||
import com.jozufozu.flywheel.core.shader.spec.ProgramSpec;
|
||||
import com.simibubi.create.foundation.render.AllProgramSpecs;
|
||||
|
||||
import net.minecraft.util.ResourceLocation;
|
||||
|
||||
public class EffectsContext extends ShaderContext<SphereFilterProgram> {
|
||||
|
||||
public EffectsContext(Backend backend) {
|
||||
super(backend);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void load() {
|
||||
ProgramSpec programSpec = Backend.getInstance().getSpec(AllProgramSpecs.CHROMATIC);
|
||||
|
||||
try {
|
||||
programs.put(programSpec.name, new SphereFilterProgram(loadAndLink(programSpec, null)));
|
||||
|
||||
Backend.log.debug("Loaded program {}", programSpec.name);
|
||||
} catch (Exception e) {
|
||||
Backend.log.error("Program '{}': {}", programSpec.name, e);
|
||||
backend.sources.notifyError();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Shader getSource(ShaderType type, ResourceLocation name) {
|
||||
Shader source = super.getSource(type, name);
|
||||
source.processIncludes();
|
||||
return source;
|
||||
}
|
||||
}
|
|
@ -1,151 +0,0 @@
|
|||
package com.simibubi.create.foundation.render.effects;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
import javax.annotation.Nullable;
|
||||
|
||||
import org.lwjgl.opengl.GL11;
|
||||
import org.lwjgl.opengl.GL20;
|
||||
import org.lwjgl.opengl.GL30;
|
||||
|
||||
import com.jozufozu.flywheel.backend.Backend;
|
||||
import com.jozufozu.flywheel.core.FullscreenQuad;
|
||||
import com.jozufozu.flywheel.util.RenderUtil;
|
||||
import com.simibubi.create.foundation.render.AllProgramSpecs;
|
||||
import com.simibubi.create.foundation.render.CreateContexts;
|
||||
import com.simibubi.create.foundation.utility.AnimationTickHolder;
|
||||
|
||||
import net.minecraft.client.MainWindow;
|
||||
import net.minecraft.client.Minecraft;
|
||||
import net.minecraft.client.renderer.ActiveRenderInfo;
|
||||
import net.minecraft.client.renderer.GameRenderer;
|
||||
import net.minecraft.client.shader.Framebuffer;
|
||||
import net.minecraft.client.shader.FramebufferConstants;
|
||||
import net.minecraft.util.math.vector.Matrix4f;
|
||||
import net.minecraft.util.math.vector.Vector3d;
|
||||
|
||||
public class EffectsHandler {
|
||||
|
||||
private static EffectsHandler instance;
|
||||
|
||||
@Nullable
|
||||
public static EffectsHandler getInstance() {
|
||||
if (Backend.getInstance().available() && instance == null) {
|
||||
instance = new EffectsHandler(Backend.getInstance());
|
||||
}
|
||||
|
||||
if (!Backend.getInstance().available() && instance != null) {
|
||||
instance.delete();
|
||||
instance = null;
|
||||
}
|
||||
|
||||
return instance;
|
||||
}
|
||||
|
||||
public static float getNearPlane() {
|
||||
return 0.05f;
|
||||
}
|
||||
|
||||
public static float getFarPlane() {
|
||||
return Minecraft.getInstance().gameRenderer.getFarPlaneDistance() * 4;
|
||||
}
|
||||
|
||||
private final Backend backend;
|
||||
private final Framebuffer framebuffer;
|
||||
private final ArrayList<FilterSphere> spheres;
|
||||
|
||||
public EffectsHandler(Backend backend) {
|
||||
this.backend = backend;
|
||||
spheres = new ArrayList<>();
|
||||
|
||||
Framebuffer render = Minecraft.getInstance().getFramebuffer();
|
||||
framebuffer = new Framebuffer(render.framebufferWidth, render.framebufferHeight, false, Minecraft.IS_RUNNING_ON_MAC);
|
||||
|
||||
}
|
||||
|
||||
public void addSphere(FilterSphere sphere) {
|
||||
this.spheres.add(sphere);
|
||||
}
|
||||
|
||||
public void render(Matrix4f view) {
|
||||
if (spheres.size() == 0) {
|
||||
return;
|
||||
}
|
||||
|
||||
GL20.glEnable(GL20.GL_DEPTH_TEST);
|
||||
|
||||
GL20.glDepthRange(getNearPlane(), getFarPlane());
|
||||
|
||||
prepFramebufferSize();
|
||||
|
||||
Framebuffer mainBuffer = Minecraft.getInstance().getFramebuffer();
|
||||
|
||||
backend.compat.fbo.bindFramebuffer(FramebufferConstants.FRAME_BUFFER, framebuffer.framebufferObject);
|
||||
GL11.glClear(GL30.GL_COLOR_BUFFER_BIT);
|
||||
|
||||
SphereFilterProgram program = CreateContexts.EFFECTS.getProgram(AllProgramSpecs.CHROMATIC);
|
||||
program.bind();
|
||||
|
||||
program.bindColorTexture(mainBuffer.getColorAttachment());
|
||||
program.bindDepthTexture(mainBuffer.getDepthAttachment());
|
||||
|
||||
GameRenderer gameRenderer = Minecraft.getInstance().gameRenderer;
|
||||
ActiveRenderInfo activeRenderInfo = gameRenderer.getActiveRenderInfo();
|
||||
Matrix4f projection = gameRenderer.getBasicProjectionMatrix(activeRenderInfo, AnimationTickHolder.getPartialTicks(), true);
|
||||
projection.a33 = 1;
|
||||
projection.invert();
|
||||
program.bindInverseProjection(projection);
|
||||
|
||||
Matrix4f inverseView = view.copy();
|
||||
inverseView.invert();
|
||||
program.bindInverseView(inverseView);
|
||||
|
||||
Vector3d cameraPos = activeRenderInfo.getProjectedView();
|
||||
|
||||
program.setCameraPos(cameraPos.inverse());
|
||||
|
||||
for (FilterSphere sphere : spheres) {
|
||||
sphere.x -= cameraPos.x;
|
||||
sphere.y -= cameraPos.y;
|
||||
sphere.z -= cameraPos.z;
|
||||
}
|
||||
|
||||
spheres.sort((o1, o2) -> {
|
||||
double l1 = RenderUtil.length(o1.x, o1.y, o1.z);
|
||||
double l2 = RenderUtil.length(o2.x, o2.y, o2.z);
|
||||
return (int) Math.signum(l2 - l1);
|
||||
});
|
||||
|
||||
program.uploadFilters(spheres);
|
||||
|
||||
program.setFarPlane(getFarPlane());
|
||||
program.setNearPlane(getNearPlane());
|
||||
|
||||
FullscreenQuad.INSTANCE.get().draw();
|
||||
|
||||
program.bindColorTexture(0);
|
||||
program.bindDepthTexture(0);
|
||||
GL20.glActiveTexture(GL20.GL_TEXTURE0);
|
||||
|
||||
program.unbind();
|
||||
spheres.clear();
|
||||
|
||||
backend.compat.fbo.bindFramebuffer(GL30.GL_READ_FRAMEBUFFER, framebuffer.framebufferObject);
|
||||
backend.compat.fbo.bindFramebuffer(GL30.GL_DRAW_FRAMEBUFFER, mainBuffer.framebufferObject);
|
||||
backend.compat.blit.blitFramebuffer(0, 0, mainBuffer.framebufferWidth, mainBuffer.framebufferHeight, 0, 0, mainBuffer.framebufferWidth, mainBuffer.framebufferHeight, GL30.GL_COLOR_BUFFER_BIT, GL20.GL_LINEAR);
|
||||
backend.compat.fbo.bindFramebuffer(FramebufferConstants.FRAME_BUFFER, mainBuffer.framebufferObject);
|
||||
}
|
||||
|
||||
public void delete() {
|
||||
framebuffer.deleteFramebuffer();
|
||||
}
|
||||
|
||||
private void prepFramebufferSize() {
|
||||
MainWindow window = Minecraft.getInstance().getWindow();
|
||||
if (framebuffer.framebufferWidth != window.getFramebufferWidth()
|
||||
|| framebuffer.framebufferHeight != window.getFramebufferHeight()) {
|
||||
framebuffer.func_216491_a(window.getFramebufferWidth(), window.getFramebufferHeight(),
|
||||
Minecraft.IS_RUNNING_ON_MAC);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,54 +0,0 @@
|
|||
package com.simibubi.create.foundation.render.effects;
|
||||
|
||||
import com.jozufozu.flywheel.backend.gl.buffer.MappedBuffer;
|
||||
import com.jozufozu.flywheel.util.RenderUtil;
|
||||
|
||||
import net.minecraft.util.math.vector.Matrix4f;
|
||||
|
||||
public class FilterSphere {
|
||||
public float x;
|
||||
public float y;
|
||||
public float z;
|
||||
public float radius;
|
||||
|
||||
public float feather;
|
||||
public float fade;
|
||||
public float density = 2;
|
||||
public boolean blend = false;
|
||||
|
||||
public boolean surface = true;
|
||||
public boolean field = true;
|
||||
public float strength = 1;
|
||||
|
||||
public boolean rMask;
|
||||
public boolean gMask;
|
||||
public boolean bMask;
|
||||
|
||||
public Matrix4f filter;
|
||||
|
||||
public void write(MappedBuffer buf) {
|
||||
buf.putFloatArray(new float[]{
|
||||
x,
|
||||
y,
|
||||
z,
|
||||
radius,
|
||||
|
||||
feather,
|
||||
fade,
|
||||
density,
|
||||
blend ? 1 : 0,
|
||||
|
||||
surface ? 1 : 0,
|
||||
field ? 1 : 0,
|
||||
Math.abs(strength),
|
||||
strength < 0 ? 1 : 0,
|
||||
|
||||
rMask ? 1 : 0,
|
||||
gMask ? 1 : 0,
|
||||
bMask ? 1 : 0,
|
||||
0, // padding
|
||||
});
|
||||
|
||||
buf.putFloatArray(RenderUtil.writeMatrix(filter));
|
||||
}
|
||||
}
|
|
@ -1,118 +0,0 @@
|
|||
package com.simibubi.create.foundation.render.effects;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
||||
import org.lwjgl.opengl.GL20;
|
||||
import org.lwjgl.opengl.GL31;
|
||||
|
||||
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.shader.GlProgram;
|
||||
import com.jozufozu.flywheel.backend.loading.Program;
|
||||
import com.jozufozu.flywheel.core.shader.IMultiProgram;
|
||||
|
||||
import net.minecraft.util.math.vector.Matrix4f;
|
||||
import net.minecraft.util.math.vector.Vector3d;
|
||||
|
||||
public class SphereFilterProgram extends GlProgram implements IMultiProgram<SphereFilterProgram> {
|
||||
|
||||
protected static final int UBO_BINDING = 4;
|
||||
|
||||
protected static final int SPHERE_FILTER_SIZE = 24 * 4; // <vec4, float + padding, mat4>
|
||||
protected static final int MAX_FILTERS = 256; // arbitrary
|
||||
|
||||
protected static final int EXTRA_INFO = 16; // array length: int + padding
|
||||
protected static final int ALL_FILTERS_SIZE = MAX_FILTERS * SPHERE_FILTER_SIZE;
|
||||
|
||||
protected static final int BUFFER_SIZE = EXTRA_INFO + ALL_FILTERS_SIZE;
|
||||
|
||||
public final GlBuffer effectsUBO;
|
||||
|
||||
protected final int uniformBlock;
|
||||
|
||||
protected final int uDepth;
|
||||
protected final int uColor;
|
||||
|
||||
protected final int uInverseProjection;
|
||||
protected final int uInverseView;
|
||||
|
||||
protected final int uNearPlane;
|
||||
protected final int uFarPlane;
|
||||
|
||||
protected final int uCameraPos;
|
||||
|
||||
public SphereFilterProgram(Program program) {
|
||||
super(program);
|
||||
|
||||
effectsUBO = new GlBuffer(GlBufferType.UNIFORM_BUFFER);
|
||||
|
||||
uniformBlock = GL31.glGetUniformBlockIndex(program.program, "Filters");
|
||||
|
||||
GL31.glUniformBlockBinding(program.program, uniformBlock, UBO_BINDING);
|
||||
|
||||
effectsUBO.bind();
|
||||
effectsUBO.alloc(BUFFER_SIZE);
|
||||
GL31.glBindBufferBase(effectsUBO.getBufferTarget().glEnum, UBO_BINDING, effectsUBO.handle());
|
||||
effectsUBO.unbind();
|
||||
|
||||
uInverseProjection = getUniformLocation("uInverseProjection");
|
||||
uInverseView = getUniformLocation("uInverseView");
|
||||
uNearPlane = getUniformLocation("uNearPlane");
|
||||
uFarPlane = getUniformLocation("uFarPlane");
|
||||
uCameraPos = getUniformLocation("uCameraPos");
|
||||
|
||||
bind();
|
||||
uDepth = setSamplerBinding("uDepth", 8);
|
||||
uColor = setSamplerBinding("uColor", 9);
|
||||
unbind();
|
||||
}
|
||||
|
||||
public void setNearPlane(float nearPlane) {
|
||||
GL20.glUniform1f(uNearPlane, nearPlane);
|
||||
}
|
||||
|
||||
public void setFarPlane(float farPlane) {
|
||||
GL20.glUniform1f(uFarPlane, farPlane);
|
||||
}
|
||||
|
||||
public void setCameraPos(Vector3d pos) {
|
||||
GL20.glUniform3f(uCameraPos, (float) pos.x, (float) pos.y, (float) pos.z);
|
||||
}
|
||||
|
||||
public void uploadFilters(ArrayList<FilterSphere> filters) {
|
||||
effectsUBO.bind();
|
||||
MappedBuffer buffer = effectsUBO.getBuffer(0, BUFFER_SIZE)
|
||||
.putInt(filters.size())
|
||||
.position(16);
|
||||
|
||||
filters.forEach(it -> it.write(buffer));
|
||||
|
||||
buffer.flush();
|
||||
|
||||
effectsUBO.unbind();
|
||||
}
|
||||
|
||||
public void bindInverseProjection(Matrix4f mat) {
|
||||
uploadMatrixUniform(uInverseProjection, mat);
|
||||
}
|
||||
|
||||
public void bindInverseView(Matrix4f mat) {
|
||||
uploadMatrixUniform(uInverseView, mat);
|
||||
}
|
||||
|
||||
public void bindDepthTexture(int textureObject) {
|
||||
GL20.glActiveTexture(GL20.GL_TEXTURE8);
|
||||
GL20.glBindTexture(GL20.GL_TEXTURE_2D, textureObject);
|
||||
}
|
||||
|
||||
public void bindColorTexture(int textureObject) {
|
||||
GL20.glActiveTexture(GL20.GL_TEXTURE9);
|
||||
GL20.glBindTexture(GL20.GL_TEXTURE_2D, textureObject);
|
||||
}
|
||||
|
||||
@Override
|
||||
public SphereFilterProgram get() {
|
||||
return this;
|
||||
}
|
||||
}
|
|
@ -1,4 +0,0 @@
|
|||
{
|
||||
"vert": "create:area_effect.vert",
|
||||
"frag": "create:area_effect.frag"
|
||||
}
|
|
@ -1,167 +0,0 @@
|
|||
#version 140
|
||||
|
||||
#flwinclude <"flywheel:core/color.glsl">
|
||||
|
||||
in vec2 ScreenCoord;
|
||||
in vec3 WorldDir;
|
||||
|
||||
out vec4 Color;
|
||||
|
||||
// constants
|
||||
uniform sampler2D uDepth;
|
||||
uniform sampler2D uColor;
|
||||
uniform float uNearPlane = 0.15;
|
||||
uniform float uFarPlane = 1.;
|
||||
uniform vec3 uCameraPos;
|
||||
|
||||
struct SphereFilter {
|
||||
vec4 sphere;// <vec3 position, float radius>
|
||||
vec4 d1;// <float feather, float fade, float density, float blend mode>
|
||||
vec4 strength;// <float surfaceStrength, float bubbleStrength, float strength, float invert>
|
||||
vec4 channelMask;// <vec3 rgb>
|
||||
mat4 colorOp;
|
||||
};
|
||||
|
||||
#define N 256
|
||||
layout (std140) uniform Filters {
|
||||
int uCount;
|
||||
SphereFilter uSpheres[N];
|
||||
};
|
||||
|
||||
float linearizeDepth(float d, float zNear, float zFar) {
|
||||
float clipZ = 2.0 * d - 1.0;
|
||||
return zNear * zFar / (zFar + zNear - clipZ * (zFar - zNear));
|
||||
}
|
||||
|
||||
vec3 filterColor(mat4 colorOp, vec3 color) {
|
||||
// preserve alpha while transforming color
|
||||
vec4 i = vec4(color, 1.);
|
||||
i *= colorOp;
|
||||
return i.rgb;
|
||||
}
|
||||
|
||||
float getDepth() {
|
||||
float depth = texture2D(uDepth, ScreenCoord).r;
|
||||
|
||||
return linearizeDepth(depth, uNearPlane, uFarPlane);
|
||||
}
|
||||
|
||||
float surfaceFilterStrength(vec3 worldPos, vec4 sphere, float feather) {
|
||||
float distance = distance(sphere.xyz, worldPos);
|
||||
return 1 - smoothstep(sphere.w, sphere.w + feather, distance);
|
||||
}
|
||||
|
||||
vec2 raySphere(vec3 worldDir, vec3 position, float radius) {
|
||||
float rayLengthSqr = dot(worldDir, worldDir);
|
||||
float sphereDistSqr = dot(position, position);
|
||||
|
||||
const vec3 M = vec3(2., 2., 4.);
|
||||
vec3 f = M * vec3(dot(-position, worldDir), vec2(rayLengthSqr));
|
||||
|
||||
vec2 s = vec2(f.x, radius);
|
||||
vec2 s2 = s * s;
|
||||
float c = sphereDistSqr - s2.y;
|
||||
float dc = f.z * c;
|
||||
|
||||
float discriminant = s2.x - dc;
|
||||
float hitDepth = (-f.x - sqrt(discriminant)) / f.y;
|
||||
|
||||
return vec2(discriminant, hitDepth);
|
||||
}
|
||||
|
||||
// if i == 0 return s
|
||||
// if i == 1 return 1 - s
|
||||
float invert(float s, float i) {
|
||||
return i - 2*i*s + s;
|
||||
}
|
||||
|
||||
float bubbleFilterStrength(vec3 worldDir, float depth, vec4 sphere, float feather, float density) {
|
||||
vec3 position = sphere.xyz;
|
||||
|
||||
vec2 hit = raySphere(worldDir, position, sphere.w + feather);
|
||||
float hitDepth = hit.y;
|
||||
|
||||
float strength = 0.;
|
||||
|
||||
//float boo = step(0., discriminant) * step(0., hitDepth) * step(0., depth - hitDepth);
|
||||
if (hit.x > 0 && hitDepth > 0 && hitDepth < depth) {
|
||||
vec3 hitPos = worldDir * hitDepth;
|
||||
|
||||
vec3 normal = normalize(hitPos - position);
|
||||
float normalDot = dot(normal, normalize(worldDir));
|
||||
// blend into the effect based on the distance between the fragcoord and point on the sphere
|
||||
// this avoinds having hard edges
|
||||
strength += mix(0., normalDot * normalDot * density, clamp(depth - hitDepth, 0., feather + 1.));
|
||||
}
|
||||
|
||||
return clamp(strength, 0., 1.);// * boo;
|
||||
}
|
||||
|
||||
float filterStrength(vec3 worldDir, float depth, inout SphereFilter f) {
|
||||
vec4 sphere = f.sphere;
|
||||
vec4 data = f.d1;
|
||||
float feather = data.x;
|
||||
|
||||
float strength;
|
||||
// transition effect
|
||||
float transitionRadius = sphere.w + feather;
|
||||
strength = 1. - smoothstep(transitionRadius, transitionRadius + max(0.5, data.y), length(sphere.xyz));
|
||||
// bubble effect
|
||||
strength = max(strength, bubbleFilterStrength(worldDir, depth, sphere, feather, data.z));
|
||||
|
||||
strength *= f.strength.y;
|
||||
// surface effect
|
||||
strength = max(strength, surfaceFilterStrength(worldDir * depth, sphere, feather) * f.strength.x);
|
||||
|
||||
return strength * f.strength.z;
|
||||
}
|
||||
|
||||
vec3 applyFilters(vec3 worldDir, float depth, vec3 diffuse) {
|
||||
vec3 worldPos = worldDir * depth;
|
||||
|
||||
vec3 accum = vec3(diffuse);
|
||||
|
||||
for (int i = 0; i < uCount; i++) {
|
||||
SphereFilter s = uSpheres[i];
|
||||
|
||||
float strength = filterStrength(worldDir, depth, s);
|
||||
|
||||
strength = invert(strength, s.strength.w);
|
||||
|
||||
if (strength > 0) {
|
||||
const float fcon = 0.;
|
||||
|
||||
vec3 baseColor = mix(diffuse, accum, s.d1.w);
|
||||
|
||||
vec3 filtered = filterColor(s.colorOp, baseColor);
|
||||
|
||||
// vec3 baseHsv = rgb2hsv(baseColor);
|
||||
// vec3 maskHsv = rgb2hsv(s.colorMask.rgb);
|
||||
// float diff = dot(abs(baseHsv - maskHsv), vec3(1., 1.1, 0.1));
|
||||
// float colorMask = step(s.colorMask.w, diff);
|
||||
float mixing = clamp(strength, 0., 1.);
|
||||
|
||||
accum = mix(accum, filtered, mixing * s.channelMask.xyz);
|
||||
//accum = vec3(colorMask);
|
||||
}
|
||||
}
|
||||
|
||||
return accum;
|
||||
}
|
||||
|
||||
vec4 debugGrid(vec3 worldPos, vec4 diffuse) {
|
||||
vec3 fractionalCoords = fract(worldPos - uCameraPos);
|
||||
|
||||
vec3 isBonudary = step(15./16., fractionalCoords);
|
||||
|
||||
return vec4(mix(diffuse.rgb, fractionalCoords, isBonudary), 1.);
|
||||
}
|
||||
|
||||
void main() {
|
||||
float depth = getDepth();
|
||||
|
||||
vec4 diffuse = texture2D(uColor, ScreenCoord);
|
||||
|
||||
Color = vec4(applyFilters(WorldDir, depth, diffuse.rgb), diffuse.a);
|
||||
//Color = debugGrid(WorldDir * depth, Color);
|
||||
}
|
|
@ -1,29 +0,0 @@
|
|||
#version 140
|
||||
|
||||
// scaling constants
|
||||
// e - 0.99, this works well, no idea why
|
||||
#define SXY 1.7282818
|
||||
// 1.90 -> highp close, mediump far
|
||||
// 1.91 -> mediump close, highp far
|
||||
#define SZ 1.905
|
||||
|
||||
in vec4 aVertex;// <vec2 position, vec2 texCoords>
|
||||
|
||||
out vec2 ScreenCoord;
|
||||
out vec3 WorldDir;
|
||||
|
||||
uniform mat4 uInverseProjection;
|
||||
uniform mat4 uInverseView;
|
||||
|
||||
void main() {
|
||||
gl_Position = vec4(aVertex.xy, 0., 1.);
|
||||
ScreenCoord = aVertex.zw;
|
||||
|
||||
vec4 clip = vec4(aVertex.xy, 0., 1.);
|
||||
|
||||
clip *= uInverseProjection;
|
||||
|
||||
vec3 cameraDir = clip.xyz / clip.w;
|
||||
cameraDir = cameraDir * vec3(SXY, SXY, SZ);
|
||||
WorldDir = (uInverseView * vec4(cameraDir, 1.)).xyz;
|
||||
}
|
Loading…
Reference in a new issue