Lieutenant Scatterbrain II.

- Swich to tabs. (not everything is tabs yet)
 - Refactor light and color attributes to their own Enum.
 - Quaternion/pivot/position attribute shader.
 - Always update an instance when the WorldRenderer checks if it should rerender a block.
 - Simplify some names.
 - Remove generics in InstanceData classes.
 - Deployer Tiles now use the oriented material.
 - Press heads now correctly orient themselves.
 - ModelData buffers things faster and is simpler.
This commit is contained in:
JozsefA 2021-03-22 20:20:52 -07:00
parent f7f7b67a7d
commit 1310b88828
71 changed files with 1094 additions and 796 deletions

View file

@ -19,7 +19,6 @@ import com.simibubi.create.foundation.render.SuperByteBuffer;
import com.simibubi.create.foundation.render.backend.RenderMaterials;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import com.simibubi.create.foundation.render.backend.instancing.RenderMaterial;
import com.simibubi.create.foundation.render.backend.instancing.impl.ModelData;
import com.simibubi.create.foundation.utility.AngleHelper;
import com.simibubi.create.foundation.utility.Iterate;
@ -277,7 +276,7 @@ public class AllBlockPartials {
.unCentre();
return stack;
};
return dispatcher.getMaterial(RenderMaterials.MODELS).getModel(this, referenceState, facing, ms);
return dispatcher.getMaterial(RenderMaterials.TRANSFORMED).getModel(this, referenceState, facing, ms);
}
}

View file

@ -115,8 +115,6 @@ import com.simibubi.create.content.schematics.block.SchematicannonRenderer;
import com.simibubi.create.content.schematics.block.SchematicannonTileEntity;
import com.simibubi.create.foundation.tileEntity.renderer.SmartTileEntityRenderer;
import com.tterrag.registrate.util.entry.TileEntityEntry;
import net.minecraftforge.api.distmarker.Dist;
import net.minecraftforge.fml.DistExecutor;
public class AllTileEntities {

View file

@ -5,10 +5,8 @@ import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexAttribSpec;
public enum KineticVertexAttributes implements IVertexAttrib {
public enum KineticAttributes implements IVertexAttrib {
INSTANCE_POSITION("aInstancePos", CommonAttributes.VEC3),
LIGHT("aLight", CommonAttributes.LIGHT),
NETWORK_COLOR("aNetworkTint", CommonAttributes.RGB),
SPEED("aSpeed", CommonAttributes.FLOAT),
OFFSET("aOffset", CommonAttributes.FLOAT),
;
@ -16,7 +14,7 @@ public enum KineticVertexAttributes implements IVertexAttrib {
private final String name;
private final VertexAttribSpec spec;
KineticVertexAttributes(String name, VertexAttribSpec spec) {
KineticAttributes(String name, VertexAttribSpec spec) {
this.name = name;
this.spec = spec;
}

View file

@ -2,23 +2,17 @@ package com.simibubi.create.content.contraptions.base;
import java.nio.ByteBuffer;
import com.simibubi.create.foundation.render.backend.instancing.InstanceData;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.impl.IFlatLight;
import com.simibubi.create.foundation.render.backend.instancing.impl.BasicData;
import com.simibubi.create.foundation.utility.ColorHelper;
import net.minecraft.client.renderer.Vector3f;
import net.minecraft.util.math.BlockPos;
public class KineticData<D extends KineticData<D>> extends InstanceData implements IFlatLight<D> {
public class KineticData extends BasicData {
private float x;
private float y;
private float z;
private byte blockLight;
private byte skyLight;
private byte r;
private byte g;
private byte b;
private float rotationalSpeed;
private float rotationOffset;
@ -26,25 +20,25 @@ public class KineticData<D extends KineticData<D>> extends InstanceData implemen
super(owner);
}
public D setTileEntity(KineticTileEntity te) {
public KineticData setTileEntity(KineticTileEntity te) {
setPosition(te.getPos());
if (te.hasSource()) {
setColor(te.network);
}else {
setColor(0xFF, 0xFF, 0x00);
}
return (D) this;
return this;
}
public D setPosition(BlockPos pos) {
public KineticData setPosition(BlockPos pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public D setPosition(Vector3f pos) {
public KineticData setPosition(Vector3f pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public D setPosition(int x, int y, int z) {
public KineticData setPosition(int x, int y, int z) {
BlockPos origin = owner.renderer.getOriginCoordinate();
return setPosition((float) (x - origin.getX()),
@ -52,75 +46,62 @@ public class KineticData<D extends KineticData<D>> extends InstanceData implemen
(float) (z - origin.getZ()));
}
public D setPosition(float x, float y, float z) {
public KineticData setPosition(float x, float y, float z) {
this.x = x;
this.y = y;
this.z = z;
return (D) this;
return this;
}
public D nudge(float x, float y, float z) {
public KineticData nudge(float x, float y, float z) {
this.x += x;
this.y += y;
this.z += z;
return (D) this;
return this;
}
@Override
public D setBlockLight(int blockLight) {
this.blockLight = (byte) ((blockLight & 0xF) << 4);
return (D) this;
}
@Override
public D setSkyLight(int skyLight) {
this.skyLight = (byte) ((skyLight & 0xF) << 4);
return (D) this;
}
public D setColor(Long l) {
public KineticData setColor(Long l) {
if (l != null)
return setColor(l.longValue());
else
return setColor(0xFF, 0xFF, 0xFF);
else {
setColor(0xFF, 0xFF, 0xFF);
return this;
}
}
private D setColor(long l) {
private KineticData setColor(long l) {
int color = ColorHelper.colorFromLong(l);
byte r = (byte) ((color >> 16) & 0xFF);
byte g = (byte) ((color >> 8) & 0xFF);
byte b = (byte) (color & 0xFF);
return setColor(r, g, b);
setColor(r, g, b);
return this;
}
public D setColor(int r, int g, int b) {
return setColor((byte) r, (byte) g, (byte) b);
}
public D setColor(byte r, byte g, byte b) {
this.r = r;
this.g = g;
this.b = b;
return (D) this;
}
public D setRotationalSpeed(float rotationalSpeed) {
public KineticData setRotationalSpeed(float rotationalSpeed) {
this.rotationalSpeed = rotationalSpeed;
return (D) this;
return this;
}
public D setRotationOffset(float rotationOffset) {
public KineticData setRotationOffset(float rotationOffset) {
this.rotationOffset = rotationOffset;
return (D) this;
return this;
}
@Override
public void write(ByteBuffer buf) {
putVec3(buf, x, y, z);
putVec2(buf, blockLight, skyLight);
putVec3(buf, r, g, b);
put(buf, rotationalSpeed);
put(buf, rotationOffset);
super.write(buf);
buf.asFloatBuffer().put(new float[] {
x,
y,
z,
rotationalSpeed,
rotationOffset
});
buf.position(buf.position() + 5 * 4);
}
}

View file

@ -1,6 +1,6 @@
package com.simibubi.create.content.contraptions.base;
import com.simibubi.create.content.contraptions.components.actors.ContraptionActorData;
import com.simibubi.create.content.contraptions.components.actors.ActorData;
import com.simibubi.create.content.contraptions.relays.belt.BeltData;
import com.simibubi.create.content.logistics.block.FlapData;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
@ -10,7 +10,7 @@ public class KineticRenderMaterials {
public static final MaterialType<InstancedModel<RotatingData>> ROTATING = new MaterialType<>();
public static final MaterialType<InstancedModel<BeltData>> BELTS = new MaterialType<>();
public static final MaterialType<InstancedModel<ContraptionActorData>> ACTORS = new MaterialType<>();
public static final MaterialType<InstancedModel<ActorData>> ACTORS = new MaterialType<>();
public static final MaterialType<InstancedModel<FlapData>> FLAPS = new MaterialType<>();
}

View file

@ -25,10 +25,10 @@ public abstract class KineticTileInstance<T extends KineticTileEntity> extends T
}
protected final void updateRotation(RotatingData key, Direction.Axis axis, float speed) {
key.setColor(tile.network)
.setRotationalSpeed(speed)
.setRotationOffset(getRotationOffset(axis))
.setRotationAxis(axis);
key.setRotationAxis(axis)
.setRotationOffset(getRotationOffset(axis))
.setRotationalSpeed(speed)
.setColor(tile.network);
}
protected final void updateRotation(RotatingData key, Direction.Axis axis) {
@ -37,12 +37,12 @@ public abstract class KineticTileInstance<T extends KineticTileEntity> extends T
protected final InstanceKey<RotatingData> setup(InstanceKey<RotatingData> key, float speed, Direction.Axis axis) {
key.getInstance()
.setBlockLight(world.getLightLevel(LightType.BLOCK, pos))
.setSkyLight(world.getLightLevel(LightType.SKY, pos))
.setTileEntity(tile)
.setRotationalSpeed(speed)
.setRotationOffset(getRotationOffset(axis))
.setRotationAxis(axis);
.setRotationAxis(axis)
.setRotationalSpeed(speed)
.setRotationOffset(getRotationOffset(axis))
.setTileEntity(tile)
.setSkyLight(world.getLightLevel(LightType.SKY, pos))
.setBlockLight(world.getLightLevel(LightType.BLOCK, pos));
return key;
}

View file

@ -5,14 +5,14 @@ import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexAttribSpec;
public enum RotatingVertexAttributes implements IVertexAttrib {
public enum RotatingAttributes implements IVertexAttrib {
AXIS("aAxis", CommonAttributes.NORMAL),
;
private final String name;
private final VertexAttribSpec spec;
RotatingVertexAttributes(String name, VertexAttribSpec spec) {
RotatingAttributes(String name, VertexAttribSpec spec) {
this.name = name;
this.spec = spec;
}

View file

@ -2,18 +2,12 @@ package com.simibubi.create.content.contraptions.base;
import java.nio.ByteBuffer;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import net.minecraft.client.renderer.Vector3f;
import net.minecraft.util.Direction;
public class RotatingData extends KineticData<RotatingData> {
public static VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(KineticVertexAttributes.class)
.addAttributes(RotatingVertexAttributes.class)
.build();
public class RotatingData extends KineticData {
private byte rotationAxisX;
private byte rotationAxisY;
private byte rotationAxisZ;

View file

@ -3,11 +3,18 @@ package com.simibubi.create.content.contraptions.base;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import com.simibubi.create.foundation.render.backend.instancing.impl.BasicAttributes;
import net.minecraft.client.renderer.BufferBuilder;
public class RotatingInstancedModel extends InstancedModel<RotatingData> {
public RotatingInstancedModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
public class RotatingModel extends InstancedModel<RotatingData> {
public static VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(BasicAttributes.class)
.addAttributes(KineticAttributes.class)
.addAttributes(RotatingAttributes.class)
.build();
public RotatingModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
super(renderer, buf);
}
@ -18,7 +25,7 @@ public class RotatingInstancedModel extends InstancedModel<RotatingData> {
@Override
protected VertexFormat getInstanceFormat() {
return RotatingData.FORMAT;
return FORMAT;
}
}

View file

@ -2,13 +2,8 @@ package com.simibubi.create.content.contraptions.base;
import com.simibubi.create.AllBlockPartials;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderRegistry;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import net.minecraft.tileentity.TileEntityType;
import net.minecraftforge.api.distmarker.Dist;
import net.minecraftforge.fml.DistExecutor;
public class ShaftlessCogInstance extends SingleRotatingInstance {
public ShaftlessCogInstance(InstancedTileRenderer<?> modelManager, KineticTileEntity tile) {

View file

@ -2,7 +2,6 @@ package com.simibubi.create.content.contraptions.components.actors;
import java.nio.ByteBuffer;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstanceData;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
@ -10,11 +9,7 @@ import net.minecraft.client.renderer.Quaternion;
import net.minecraft.client.renderer.Vector3f;
import net.minecraft.util.math.BlockPos;
public class ContraptionActorData extends InstanceData {
public static VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(ActorVertexAttributes.class)
.build();
public class ActorData extends InstanceData {
private float x;
private float y;
private float z;
@ -34,63 +29,63 @@ public class ContraptionActorData extends InstanceData {
private float speed;
protected ContraptionActorData(InstancedModel<?> owner) {
protected ActorData(InstancedModel<?> owner) {
super(owner);
}
public ContraptionActorData setPosition(BlockPos pos) {
public ActorData setPosition(BlockPos pos) {
this.x = pos.getX();
this.y = pos.getY();
this.z = pos.getZ();
return this;
}
public ContraptionActorData setBlockLight(int blockLight) {
public ActorData setBlockLight(int blockLight) {
this.blockLight = (byte) ((blockLight & 0xF) << 4);
return this;
}
public ContraptionActorData setSkyLight(int skyLight) {
public ActorData setSkyLight(int skyLight) {
this.skyLight = (byte) ((skyLight & 0xF) << 4);
return this;
}
public ContraptionActorData setRotationOffset(float rotationOffset) {
public ActorData setRotationOffset(float rotationOffset) {
this.rotationOffset = rotationOffset;
return this;
}
public ContraptionActorData setSpeed(float speed) {
public ActorData setSpeed(float speed) {
this.speed = speed;
return this;
}
public ContraptionActorData setRotationAxis(Vector3f axis) {
public ActorData setRotationAxis(Vector3f axis) {
setRotationAxis(axis.getX(), axis.getY(), axis.getZ());
return this;
}
public ContraptionActorData setRotationAxis(float rotationAxisX, float rotationAxisY, float rotationAxisZ) {
public ActorData setRotationAxis(float rotationAxisX, float rotationAxisY, float rotationAxisZ) {
this.rotationAxisX = (byte) (rotationAxisX * 127);
this.rotationAxisY = (byte) (rotationAxisY * 127);
this.rotationAxisZ = (byte) (rotationAxisZ * 127);
return this;
}
public ContraptionActorData setRotationCenter(Vector3f axis) {
public ActorData setRotationCenter(Vector3f axis) {
setRotationCenter(axis.getX(), axis.getY(), axis.getZ());
return this;
}
public ContraptionActorData setRotationCenter(float rotationCenterX, float rotationCenterY, float rotationCenterZ) {
public ActorData setRotationCenter(float rotationCenterX, float rotationCenterY, float rotationCenterZ) {
this.rotationCenterX = (byte) (rotationCenterX * 127);
this.rotationCenterY = (byte) (rotationCenterY * 127);
this.rotationCenterZ = (byte) (rotationCenterZ * 127);
return this;
}
public ContraptionActorData setLocalRotation(Quaternion q) {
public ActorData setLocalRotation(Quaternion q) {
this.qX = q.getX();
this.qY = q.getY();
this.qZ = q.getZ();

View file

@ -6,18 +6,22 @@ import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRen
import net.minecraft.client.renderer.BufferBuilder;
public class RotatingActorModel extends InstancedModel<ContraptionActorData> {
public RotatingActorModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
public class ActorModel extends InstancedModel<ActorData> {
public static VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(ActorVertexAttributes.class)
.build();
public ActorModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
super(renderer, buf);
}
@Override
protected VertexFormat getInstanceFormat() {
return ContraptionActorData.FORMAT;
return FORMAT;
}
@Override
protected ContraptionActorData newInstance() {
return new ContraptionActorData(this);
protected ActorData newInstance() {
return new ActorData(this);
}
}

View file

@ -2,7 +2,6 @@ package com.simibubi.create.content.contraptions.components.actors;
import com.simibubi.create.AllBlockPartials;
import com.simibubi.create.content.contraptions.components.structureMovement.MovementContext;
import com.simibubi.create.content.contraptions.components.structureMovement.render.ActorInstance;
import com.simibubi.create.content.contraptions.components.structureMovement.render.ContraptionKineticRenderer;
import com.simibubi.create.foundation.render.backend.instancing.InstanceKey;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
@ -13,15 +12,15 @@ import net.minecraft.block.BlockState;
import net.minecraft.client.renderer.Quaternion;
import net.minecraft.util.Direction;
public class DrillActorInstance extends ActorInstance {
public class DrillActorInstance extends com.simibubi.create.content.contraptions.components.structureMovement.render.ActorInstance {
InstanceKey<ContraptionActorData> drillHead;
InstanceKey<ActorData> drillHead;
private Direction facing;
public DrillActorInstance(ContraptionKineticRenderer modelManager, MovementContext context) {
super(modelManager, context);
RenderMaterial<?, InstancedModel<ContraptionActorData>> renderMaterial = modelManager.getActorMaterial();
RenderMaterial<?, InstancedModel<ActorData>> renderMaterial = modelManager.getActorMaterial();
BlockState state = context.state;

View file

@ -4,17 +4,7 @@ import com.simibubi.create.AllBlockPartials;
import com.simibubi.create.content.contraptions.base.KineticTileEntity;
import com.simibubi.create.content.contraptions.base.RotatingData;
import com.simibubi.create.content.contraptions.base.SingleRotatingInstance;
import com.simibubi.create.content.contraptions.components.structureMovement.MovementContext;
import com.simibubi.create.content.contraptions.components.structureMovement.render.RenderedContraption;
import com.simibubi.create.foundation.render.backend.instancing.*;
import com.simibubi.create.foundation.utility.AngleHelper;
import net.minecraft.block.BlockState;
import net.minecraft.tileentity.TileEntityType;
import net.minecraft.util.Direction;
import net.minecraft.world.LightType;
import net.minecraftforge.api.distmarker.Dist;
import net.minecraftforge.fml.DistExecutor;
public class DrillInstance extends SingleRotatingInstance {

View file

@ -36,7 +36,7 @@ public class HarvesterActorInstance extends ActorInstance {
public HarvesterActorInstance(ContraptionKineticRenderer modelManager, MovementContext context) {
super(modelManager, context);
RenderMaterial<?, InstancedModel<ModelData>> renderMaterial = modelManager.getBasicMaterial();
RenderMaterial<?, InstancedModel<ModelData>> renderMaterial = modelManager.transformMaterial();
BlockState state = context.state;

View file

@ -50,7 +50,7 @@ public class HandCrankInstance extends SingleRotatingInstance implements IDynami
.rotate(Direction.getFacingFromAxis(Direction.AxisDirection.POSITIVE, axis), angle)
.unCentre();
crank.getInstance().setTransformNoCopy(ms);
crank.getInstance().setTransform(ms);
}
@Override

View file

@ -37,7 +37,7 @@ public class DeployerActorInstance extends ActorInstance {
public DeployerActorInstance(ContraptionKineticRenderer modelManager, MovementContext context) {
super(modelManager, context);
RenderMaterial<ContraptionProgram, InstancedModel<ModelData>> mat = modelManager.getBasicMaterial();
RenderMaterial<ContraptionProgram, InstancedModel<ModelData>> mat = modelManager.transformMaterial();
BlockState state = context.state;
DeployerTileEntity.Mode mode = NBTHelper.readEnum(context.tileData, "Mode", DeployerTileEntity.Mode.class);
@ -62,9 +62,9 @@ public class DeployerActorInstance extends ActorInstance {
int blockLight = localBlockLight();
shaft.getInstance()
.setBlockLight(blockLight)
.setRotationAxis(axis)
.setPosition(context.localPos);
.setRotationAxis(axis)
.setPosition(context.localPos)
.setBlockLight(blockLight);
pole.getInstance().setBlockLight(blockLight);
hand.getInstance().setBlockLight(blockLight);
@ -91,6 +91,23 @@ public class DeployerActorInstance extends ActorInstance {
msr.translate(context.localPos)
.translate(offset);
DeployerInstance.transformModel(msr, pole, hand, yRot, zRot, zRotPole);
transformModel(msr, pole, hand, yRot, zRot, zRotPole);
}
static void transformModel(MatrixStacker msr, InstanceKey<ModelData> pole, InstanceKey<ModelData> hand, float yRot, float zRot, float zRotPole) {
msr.centre();
msr.rotate(Direction.SOUTH, (float) ((zRot) / 180 * Math.PI));
msr.rotate(Direction.UP, (float) ((yRot) / 180 * Math.PI));
msr.push();
msr.rotate(Direction.SOUTH, (float) ((zRotPole) / 180 * Math.PI));
msr.unCentre();
pole.getInstance().setTransform(msr.unwrap());
msr.pop();
msr.unCentre();
hand.getInstance().setTransform(msr.unwrap());
}
}

View file

@ -1,22 +1,24 @@
package com.simibubi.create.content.contraptions.components.deployer;
import com.mojang.blaze3d.matrix.MatrixStack;
import com.simibubi.create.AllBlockPartials;
import com.simibubi.create.content.contraptions.base.KineticTileEntity;
import com.simibubi.create.content.contraptions.relays.encased.ShaftInstance;
import com.simibubi.create.foundation.render.backend.RenderMaterials;
import com.simibubi.create.foundation.render.backend.instancing.*;
import com.simibubi.create.foundation.render.backend.instancing.impl.ModelData;
import com.simibubi.create.foundation.render.backend.instancing.impl.OrientedData;
import com.simibubi.create.foundation.utility.AngleHelper;
import com.simibubi.create.foundation.utility.AnimationTickHolder;
import com.simibubi.create.foundation.utility.MatrixStacker;
import net.minecraft.client.renderer.Quaternion;
import net.minecraft.util.Direction;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.MathHelper;
import net.minecraft.util.math.Vec3d;
import net.minecraft.util.math.Vec3i;
import static com.simibubi.create.content.contraptions.base.DirectionalAxisKineticBlock.AXIS_ALONG_FIRST_COORDINATE;
import static com.simibubi.create.content.contraptions.base.DirectionalKineticBlock.FACING;
public class DeployerInstance extends ShaftInstance implements IDynamicInstance {
public class DeployerInstance extends ShaftInstance implements IDynamicInstance, ITickableInstance {
final DeployerTileEntity tile;
final Direction facing;
@ -24,12 +26,13 @@ public class DeployerInstance extends ShaftInstance implements IDynamicInstance
final float zRot;
final float zRotPole;
protected final InstanceKey<ModelData> pole;
protected final InstanceKey<OrientedData> pole;
protected InstanceKey<ModelData> hand;
protected InstanceKey<OrientedData> hand;
AllBlockPartials currentHand;
float progress = Float.NaN;
private boolean newHand = false;
public DeployerInstance(InstancedTileRenderer<?> dispatcher, KineticTileEntity tile) {
super(dispatcher, tile);
@ -43,30 +46,41 @@ public class DeployerInstance extends ShaftInstance implements IDynamicInstance
zRot = facing == Direction.UP ? 270 : facing == Direction.DOWN ? 90 : 0;
zRotPole = rotatePole ? 90 : 0;
pole = modelManager.getBasicMaterial().getModel(AllBlockPartials.DEPLOYER_POLE, blockState).createInstance();
pole = RenderMaterials.ORIENTED.get(modelManager).getModel(AllBlockPartials.DEPLOYER_POLE, blockState).createInstance();
updateHandPose();
relight(pos, pole.getInstance());
updateRotation(pole, hand, yRot, zRot, zRotPole);
}
@Override
public void tick() {
newHand = updateHandPose();
}
@Override
public void beginFrame() {
boolean newHand = updateHandPose();
float newProgress = getProgress(AnimationTickHolder.getPartialTicks());
if (!newHand && MathHelper.epsilonEquals(newProgress, progress)) return;
progress = newProgress;
newHand = false;
MatrixStack ms = new MatrixStack();
MatrixStacker msr = MatrixStacker.of(ms);
float handLength = currentHand == AllBlockPartials.DEPLOYER_HAND_POINTING ? 0
: currentHand == AllBlockPartials.DEPLOYER_HAND_HOLDING ? 4 / 16f : 3 / 16f;
float distance = Math.min(MathHelper.clamp(progress, 0, 1) * (tile.reach + handLength), 21 / 16f);
Vec3i facingVec = facing.getDirectionVec();
BlockPos blockPos = getFloatingPos();
msr.translate(getFloatingPos())
.translate(getHandOffset());
float x = blockPos.getX() + ((float) facingVec.getX()) * distance;
float y = blockPos.getY() + ((float) facingVec.getY()) * distance;
float z = blockPos.getZ() + ((float) facingVec.getZ()) * distance;
transformModel(msr, pole, hand, yRot, zRot, zRotPole);
pole.getInstance().setPosition(x, y, z);
hand.getInstance().setPosition(x, y, z);
}
@ -93,21 +107,14 @@ public class DeployerInstance extends ShaftInstance implements IDynamicInstance
if (hand != null) hand.delete();
hand = modelManager.getBasicMaterial().getModel(currentHand, blockState).createInstance();
hand = RenderMaterials.ORIENTED.get(modelManager).getModel(currentHand, blockState).createInstance();
relight(pos, hand.getInstance());
updateRotation(pole, hand, yRot, zRot, zRotPole);
return true;
}
protected Vec3d getHandOffset() {
float handLength = tile.getHandPose() == AllBlockPartials.DEPLOYER_HAND_POINTING ? 0
: tile.getHandPose() == AllBlockPartials.DEPLOYER_HAND_HOLDING ? 4 / 16f : 3 / 16f;
float distance = Math.min(MathHelper.clamp(progress, 0, 1) * (tile.reach + handLength), 21 / 16f);
Vec3d offset = new Vec3d(facing.getDirectionVec()).scale(distance);
return offset;
}
private float getProgress(float partialTicks) {
if (tile.state == DeployerTileEntity.State.EXPANDING)
return 1 - (tile.timer - partialTicks * tile.getTimerSpeed()) / 1000f;
@ -116,20 +123,15 @@ public class DeployerInstance extends ShaftInstance implements IDynamicInstance
return 0;
}
static void transformModel(MatrixStacker msr, InstanceKey<ModelData> pole, InstanceKey<ModelData> hand, float yRot, float zRot, float zRotPole) {
static void updateRotation(InstanceKey<OrientedData> pole, InstanceKey<OrientedData> hand, float yRot, float zRot, float zRotPole) {
msr.centre();
msr.rotate(Direction.SOUTH, (float) ((zRot) / 180 * Math.PI));
msr.rotate(Direction.UP, (float) ((yRot) / 180 * Math.PI));
Quaternion q = Direction.SOUTH.getUnitVector().getDegreesQuaternion(zRot);
q.multiply(Direction.UP.getUnitVector().getDegreesQuaternion(yRot));
msr.push();
msr.rotate(Direction.SOUTH, (float) ((zRotPole) / 180 * Math.PI));
msr.unCentre();
pole.getInstance().setTransform(msr.unwrap());
msr.pop();
hand.getInstance().setRotation(q);
msr.unCentre();
q.multiply(Direction.SOUTH.getUnitVector().getDegreesQuaternion(zRotPole));
hand.getInstance().setTransform(msr.unwrap());
pole.getInstance().setRotation(q);
}
}

View file

@ -7,10 +7,8 @@ import com.simibubi.create.content.contraptions.base.IRotate;
import com.simibubi.create.content.contraptions.base.KineticTileInstance;
import com.simibubi.create.content.contraptions.base.RotatingData;
import com.simibubi.create.foundation.render.backend.instancing.InstanceKey;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import net.minecraft.client.renderer.Vector3f;
import net.minecraft.util.Direction;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.MathHelper;
@ -31,8 +29,13 @@ public class FanInstance extends KineticTileInstance<EncasedFanTileEntity> {
shaft = AllBlockPartials.SHAFT_HALF.renderOnDirectionalSouthRotating(modelManager, blockState, direction.getOpposite()).createInstance();
fan = AllBlockPartials.ENCASED_FAN_INNER.renderOnDirectionalSouthRotating(modelManager, blockState, direction.getOpposite()).createInstance();
updateRotation(shaft.getInstance().setTileEntity(tile), axis);
updateRotation(fan.getInstance().setTileEntity(tile), axis, getFanSpeed());
RotatingData shaftInstance = shaft.getInstance();
shaftInstance.setTileEntity(tile);
updateRotation(shaftInstance, axis);
RotatingData fanInstance = fan.getInstance();
fanInstance.setTileEntity(tile);
updateRotation(fanInstance, axis, getFanSpeed());
updateLight();
}

View file

@ -62,7 +62,7 @@ public class FlyWheelInstance extends KineticTileInstance<FlywheelTileEntity> im
connectorAngleMult = flipAngle ? -1 : 1;
RenderMaterial<?, InstancedModel<ModelData>> mat = modelManager.getMaterial(RenderMaterials.MODELS);
RenderMaterial<?, InstancedModel<ModelData>> mat = modelManager.getMaterial(RenderMaterials.TRANSFORMED);
upperRotating = mat.getModel(AllBlockPartials.FLYWHEEL_UPPER_ROTATING, blockState).createInstance();
lowerRotating = mat.getModel(AllBlockPartials.FLYWHEEL_LOWER_ROTATING, blockState).createInstance();
@ -125,7 +125,7 @@ public class FlyWheelInstance extends KineticTileInstance<FlywheelTileEntity> im
.rotate(Direction.getFacingFromAxis(Direction.AxisDirection.POSITIVE, facing.getAxis()), AngleHelper.rad(angle))
.unCentre();
wheel.getInstance().setTransformNoCopy(ms);
wheel.getInstance().setTransform(ms);
lastAngle = angle;
firstFrame = false;

View file

@ -30,7 +30,7 @@ public class EngineInstance extends TileEntityInstance<EngineTileEntity> {
Direction facing = blockState.get(BlockStateProperties.HORIZONTAL_FACING);
this.frame = modelManager.getMaterial(RenderMaterials.MODELS).getModel(frame, blockState).createInstance();
this.frame = modelManager.getMaterial(RenderMaterials.TRANSFORMED).getModel(frame, blockState).createInstance();
float angle = AngleHelper.rad(AngleHelper.horizontalAngle(facing));
@ -45,7 +45,7 @@ public class EngineInstance extends TileEntityInstance<EngineTileEntity> {
.translate(0, 0, -1);
this.frame.getInstance()
.setTransformNoCopy(ms);
.setTransform(ms);
updateLight();
}

View file

@ -5,13 +5,8 @@ import com.simibubi.create.content.contraptions.base.KineticTileEntity;
import com.simibubi.create.content.contraptions.base.RotatingData;
import com.simibubi.create.content.contraptions.base.SingleRotatingInstance;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderRegistry;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import net.minecraft.tileentity.TileEntityType;
import net.minecraftforge.api.distmarker.Dist;
import net.minecraftforge.fml.DistExecutor;
public class MillStoneCogInstance extends SingleRotatingInstance {
public MillStoneCogInstance(InstancedTileRenderer<?> modelManager, KineticTileEntity tile) {

View file

@ -26,7 +26,7 @@ public class MixerInstance extends ShaftlessCogInstance implements IDynamicInsta
mixerHead.getInstance()
.setRotationAxis(Direction.Axis.Y);
mixerPole = modelManager.getMaterial(RenderMaterials.MODELS)
mixerPole = modelManager.getMaterial(RenderMaterials.TRANSFORMED)
.getModel(AllBlockPartials.MECHANICAL_MIXER_POLE, blockState)
.createInstance();
@ -68,7 +68,7 @@ public class MixerInstance extends ShaftlessCogInstance implements IDynamicInsta
msr.translate(getFloatingPos());
msr.translate(0, -renderedHeadOffset, 0);
mixerPole.getInstance().setTransformNoCopy(ms);
mixerPole.getInstance().setTransform(ms);
}
private float getRenderedHeadOffset(MechanicalMixerTileEntity mixer) {

View file

@ -4,7 +4,6 @@ import com.mojang.blaze3d.matrix.MatrixStack;
import com.simibubi.create.AllBlockPartials;
import com.simibubi.create.content.contraptions.base.KineticTileEntity;
import com.simibubi.create.content.contraptions.relays.encased.ShaftInstance;
import com.simibubi.create.foundation.render.backend.RenderMaterials;
import com.simibubi.create.foundation.render.backend.instancing.IDynamicInstance;
import com.simibubi.create.foundation.render.backend.instancing.InstanceKey;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
@ -19,9 +18,7 @@ public class PressInstance extends ShaftInstance implements IDynamicInstance {
public PressInstance(InstancedTileRenderer<?> dispatcher, KineticTileEntity tile) {
super(dispatcher, tile);
pressHead = modelManager.getMaterial(RenderMaterials.MODELS)
.getModel(AllBlockPartials.MECHANICAL_PRESS_HEAD, blockState)
.createInstance();
pressHead = AllBlockPartials.MECHANICAL_PRESS_HEAD.renderOnHorizontalModel(dispatcher, blockState).createInstance();
updateLight();
transformModels((MechanicalPressTileEntity) tile);
@ -46,7 +43,7 @@ public class PressInstance extends ShaftInstance implements IDynamicInstance {
msr.translate(0, -renderedHeadOffset, 0);
pressHead.getInstance()
.setTransformNoCopy(ms);
.setTransform(ms);
}
private float getRenderedHeadOffset(MechanicalPressTileEntity press) {

View file

@ -24,7 +24,7 @@ public class StickerInstance extends TileEntityInstance<StickerTileEntity> imple
public StickerInstance(InstancedTileRenderer<?> modelManager, StickerTileEntity tile) {
super(modelManager, tile);
head = modelManager.getMaterial(RenderMaterials.MODELS).getModel(AllBlockPartials.STICKER_HEAD, blockState).createInstance();
head = modelManager.getMaterial(RenderMaterials.TRANSFORMED).getModel(AllBlockPartials.STICKER_HEAD, blockState).createInstance();
fakeWorld = tile.getWorld() != Minecraft.getInstance().world;
facing = blockState.get(StickerBlock.FACING);
@ -54,7 +54,7 @@ public class StickerInstance extends TileEntityInstance<StickerTileEntity> imple
.translate(0, (offset * offset) * 4 / 16f, 0);
head.getInstance()
.setTransformNoCopy(stack);
.setTransform(stack);
lastOffset = offset;
}

View file

@ -7,6 +7,7 @@ import com.simibubi.create.AllSoundEvents;
import com.simibubi.create.CreateClient;
import com.simibubi.create.content.contraptions.components.structureMovement.glue.SuperGlueEntity;
import com.simibubi.create.content.contraptions.components.structureMovement.glue.SuperGlueItem;
import com.simibubi.create.foundation.render.backend.FastRenderDispatcher;
import com.simibubi.create.foundation.render.backend.instancing.IInstanceRendered;
import com.simibubi.create.foundation.tileEntity.SmartTileEntity;
import com.simibubi.create.foundation.tileEntity.TileEntityBehaviour;
@ -71,7 +72,7 @@ public class StickerTileEntity extends SmartTileEntity implements IInstanceRende
DistExecutor.unsafeRunWhenOn(Dist.CLIENT, () -> () -> playSound(false));
piston.chase(target, .4f, Chaser.LINEAR);
DistExecutor.unsafeRunWhenOn(Dist.CLIENT, () -> () -> CreateClient.kineticRenderer.get(world).update(this));
DistExecutor.unsafeRunWhenOn(Dist.CLIENT, () -> () -> FastRenderDispatcher.enqueueUpdate(this));
}
public boolean isAttachedToBlock() {

View file

@ -29,7 +29,7 @@ public class GantryCarriageInstance extends ShaftInstance implements IDynamicIns
public GantryCarriageInstance(InstancedTileRenderer<?> dispatcher, KineticTileEntity tile) {
super(dispatcher, tile);
gantryCogs = modelManager.getMaterial(RenderMaterials.MODELS)
gantryCogs = modelManager.getMaterial(RenderMaterials.TRANSFORMED)
.getModel(AllBlockPartials.GANTRY_COGS, blockState)
.createInstance();
@ -72,7 +72,7 @@ public class GantryCarriageInstance extends ShaftInstance implements IDynamicIns
.translate(0, 9 / 16f, 0)
.unCentre();
gantryCogs.getInstance().setTransformNoCopy(ms);
gantryCogs.getInstance().setTransform(ms);
}
@Override

View file

@ -5,7 +5,7 @@ import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexAttribSpec;
public enum ContraptionVertexAttributes implements IVertexAttrib {
public enum ContraptionAttributes implements IVertexAttrib {
VERTEX_POSITION("aPos", CommonAttributes.VEC3),
NORMAL("aNormal", CommonAttributes.NORMAL),
TEXTURE("aTexCoords", CommonAttributes.UV),
@ -16,7 +16,7 @@ public enum ContraptionVertexAttributes implements IVertexAttrib {
private final String name;
private final VertexAttribSpec spec;
ContraptionVertexAttributes(String name, VertexAttribSpec spec) {
ContraptionAttributes(String name, VertexAttribSpec spec) {
this.name = name;
this.spec = spec;
}

View file

@ -2,18 +2,19 @@ package com.simibubi.create.content.contraptions.components.structureMovement.re
import com.simibubi.create.AllMovementBehaviours;
import com.simibubi.create.content.contraptions.base.KineticRenderMaterials;
import com.simibubi.create.content.contraptions.base.RotatingInstancedModel;
import com.simibubi.create.content.contraptions.components.actors.ContraptionActorData;
import com.simibubi.create.content.contraptions.components.actors.RotatingActorModel;
import com.simibubi.create.content.contraptions.base.RotatingModel;
import com.simibubi.create.content.contraptions.components.actors.ActorData;
import com.simibubi.create.content.contraptions.components.actors.ActorModel;
import com.simibubi.create.content.contraptions.components.structureMovement.MovementBehaviour;
import com.simibubi.create.content.contraptions.components.structureMovement.MovementContext;
import com.simibubi.create.content.contraptions.relays.belt.BeltInstancedModel;
import com.simibubi.create.content.logistics.block.FlapInstancedModel;
import com.simibubi.create.content.logistics.block.FlapModel;
import com.simibubi.create.foundation.render.AllProgramSpecs;
import com.simibubi.create.foundation.render.backend.RenderMaterials;
import com.simibubi.create.foundation.render.backend.instancing.*;
import com.simibubi.create.foundation.render.backend.instancing.impl.BasicInstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.impl.OrientedModel;
import com.simibubi.create.foundation.render.backend.instancing.impl.TransformedModel;
import net.minecraft.util.math.BlockPos;
import net.minecraft.world.gen.feature.template.Template;
import org.apache.commons.lang3.tuple.Pair;
@ -23,7 +24,7 @@ import java.util.ArrayList;
public class ContraptionKineticRenderer extends InstancedTileRenderer<ContraptionProgram> {
protected ArrayList<ActorInstance> actors = new ArrayList<>();
protected ArrayList<com.simibubi.create.content.contraptions.components.structureMovement.render.ActorInstance> actors = new ArrayList<>();
public final RenderedContraption contraption;
@ -33,35 +34,36 @@ public class ContraptionKineticRenderer extends InstancedTileRenderer<Contraptio
@Override
public void registerMaterials() {
materials.put(RenderMaterials.MODELS, new RenderMaterial<>(this, AllProgramSpecs.C_MODEL, BasicInstancedModel::new));
materials.put(RenderMaterials.TRANSFORMED, new RenderMaterial<>(this, AllProgramSpecs.C_MODEL, TransformedModel::new));
materials.put(RenderMaterials.ORIENTED, new RenderMaterial<>(this, AllProgramSpecs.C_ORIENTED, OrientedModel::new));
materials.put(KineticRenderMaterials.BELTS, new RenderMaterial<>(this, AllProgramSpecs.C_BELT, BeltInstancedModel::new));
materials.put(KineticRenderMaterials.ROTATING, new RenderMaterial<>(this, AllProgramSpecs.C_ROTATING, RotatingInstancedModel::new));
materials.put(KineticRenderMaterials.FLAPS, new RenderMaterial<>(this, AllProgramSpecs.C_FLAPS, FlapInstancedModel::new));
materials.put(KineticRenderMaterials.ACTORS, new RenderMaterial<>(this, AllProgramSpecs.C_ACTOR, RotatingActorModel::new));
materials.put(KineticRenderMaterials.ROTATING, new RenderMaterial<>(this, AllProgramSpecs.C_ROTATING, RotatingModel::new));
materials.put(KineticRenderMaterials.FLAPS, new RenderMaterial<>(this, AllProgramSpecs.C_FLAPS, FlapModel::new));
materials.put(KineticRenderMaterials.ACTORS, new RenderMaterial<>(this, AllProgramSpecs.C_ACTOR, ActorModel::new));
}
@Override
public void tick() {
actors.forEach(ActorInstance::tick);
actors.forEach(com.simibubi.create.content.contraptions.components.structureMovement.render.ActorInstance::tick);
}
@Override
public void beginFrame(double cameraX, double cameraY, double cameraZ) {
super.beginFrame(cameraX, cameraY, cameraZ);
actors.forEach(ActorInstance::beginFrame);
actors.forEach(com.simibubi.create.content.contraptions.components.structureMovement.render.ActorInstance::beginFrame);
}
@Nullable
public ActorInstance createActor(Pair<Template.BlockInfo, MovementContext> actor) {
public com.simibubi.create.content.contraptions.components.structureMovement.render.ActorInstance createActor(Pair<Template.BlockInfo, MovementContext> actor) {
Template.BlockInfo blockInfo = actor.getLeft();
MovementContext context = actor.getRight();
MovementBehaviour movementBehaviour = AllMovementBehaviours.of(blockInfo.state);
if (movementBehaviour != null && movementBehaviour.hasSpecialInstancedRendering()) {
ActorInstance instance = movementBehaviour.createInstance(this, context);
com.simibubi.create.content.contraptions.components.structureMovement.render.ActorInstance instance = movementBehaviour.createInstance(this, context);
actors.add(instance);
@ -71,7 +73,7 @@ public class ContraptionKineticRenderer extends InstancedTileRenderer<Contraptio
return null;
}
public RenderMaterial<?, InstancedModel<ContraptionActorData>> getActorMaterial() {
public RenderMaterial<?, InstancedModel<ActorData>> getActorMaterial() {
return getMaterial(KineticRenderMaterials.ACTORS);
}

View file

@ -14,7 +14,7 @@ import org.lwjgl.opengl.GL20;
public class ContraptionModel extends BufferedModel {
public static final VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(ContraptionVertexAttributes.class)
.addAttributes(ContraptionAttributes.class)
.build();
protected GlPrimitiveType eboIndexType;

View file

@ -5,22 +5,14 @@ import java.util.HashMap;
import java.util.List;
import java.util.Random;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import org.apache.commons.lang3.tuple.MutablePair;
import org.lwjgl.opengl.GL11;
import com.mojang.blaze3d.matrix.MatrixStack;
import com.simibubi.create.AllMovementBehaviours;
import com.simibubi.create.content.contraptions.base.KineticRenderMaterials;
import com.simibubi.create.content.contraptions.components.actors.ContraptionActorData;
import com.simibubi.create.content.contraptions.components.structureMovement.AbstractContraptionEntity;
import com.simibubi.create.content.contraptions.components.structureMovement.Contraption;
import com.simibubi.create.content.contraptions.components.structureMovement.ContraptionLighter;
import com.simibubi.create.content.contraptions.components.structureMovement.MovementBehaviour;
import com.simibubi.create.content.contraptions.components.structureMovement.MovementContext;
import com.simibubi.create.foundation.render.backend.Backend;
import com.simibubi.create.foundation.render.backend.instancing.IInstanceRendered;
import com.simibubi.create.foundation.render.backend.instancing.RenderMaterial;
import com.simibubi.create.foundation.render.backend.light.GridAlignedBB;
import com.simibubi.create.foundation.utility.AnimationTickHolder;
import com.simibubi.create.foundation.utility.worldWrappers.PlacementSimulationWorld;

View file

@ -5,13 +5,8 @@ import com.simibubi.create.content.contraptions.base.KineticTileEntity;
import com.simibubi.create.content.contraptions.base.RotatingData;
import com.simibubi.create.content.contraptions.base.SingleRotatingInstance;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderRegistry;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import net.minecraft.tileentity.TileEntityType;
import net.minecraftforge.api.distmarker.Dist;
import net.minecraftforge.fml.DistExecutor;
public class PumpCogInstance extends SingleRotatingInstance {
public PumpCogInstance(InstancedTileRenderer<?> modelManager, KineticTileEntity tile) {

View file

@ -37,7 +37,7 @@ public class FluidValveInstance extends ShaftInstance implements IDynamicInstanc
boolean twist = pipeAxis.isHorizontal() && shaftAxis == Direction.Axis.Z || pipeAxis.isVertical();
pointerRotationOffset = twist ? 90 : 0;
pointer = modelManager.getBasicMaterial().getModel(AllBlockPartials.FLUID_VALVE_POINTER, blockState).createInstance();
pointer = modelManager.transformMaterial().getModel(AllBlockPartials.FLUID_VALVE_POINTER, blockState).createInstance();
updateLight();
transformPointer((FluidValveTileEntity) tile);

View file

@ -5,7 +5,7 @@ import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexAttribSpec;
public enum BeltVertexAttributes implements IVertexAttrib {
public enum BeltAttributes implements IVertexAttrib {
INSTANCE_ROTATION("aInstanceRot", CommonAttributes.QUATERNION),
SOURCE_TEX("aSourceTexture", CommonAttributes.UV),
SCROLL_TEX("aScrollTexture", CommonAttributes.VEC4),
@ -15,7 +15,7 @@ public enum BeltVertexAttributes implements IVertexAttrib {
private final String name;
private final VertexAttribSpec spec;
BeltVertexAttributes(String name, VertexAttribSpec spec) {
BeltAttributes(String name, VertexAttribSpec spec) {
this.name = name;
this.spec = spec;
}

View file

@ -3,20 +3,13 @@ package com.simibubi.create.content.contraptions.relays.belt;
import java.nio.ByteBuffer;
import com.simibubi.create.content.contraptions.base.KineticData;
import com.simibubi.create.content.contraptions.base.KineticVertexAttributes;
import com.simibubi.create.foundation.block.render.SpriteShiftEntry;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import net.minecraft.client.renderer.Quaternion;
import net.minecraft.client.renderer.texture.TextureAtlasSprite;
public class BeltData extends KineticData<BeltData> {
public static VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(KineticVertexAttributes.class)
.addAttributes(BeltVertexAttributes.class)
.build();
public class BeltData extends KineticData {
private float qX;
private float qY;
private float qZ;

View file

@ -160,14 +160,14 @@ public class BeltInstance extends KineticTileInstance<BeltTileEntity> {
Quaternion q = new Quaternion(rotX, rotY, rotZ, true);
key.getInstance()
.setTileEntity(tile)
.setBlockLight(world.getLightLevel(LightType.BLOCK, pos))
.setSkyLight(world.getLightLevel(LightType.SKY, pos))
.setRotation(q)
.setRotationalSpeed(getScrollSpeed())
.setRotationOffset(bottom ? 0.5f : 0f)
.setScrollTexture(spriteShift)
.setScrollMult(diagonal ? 3f / 8f : 0.5f);
.setScrollTexture(spriteShift)
.setScrollMult(diagonal ? 3f / 8f : 0.5f)
.setRotation(q)
.setRotationalSpeed(getScrollSpeed())
.setRotationOffset(bottom ? 0.5f : 0f)
.setTileEntity(tile)
.setBlockLight(world.getLightLevel(LightType.BLOCK, pos))
.setSkyLight(world.getLightLevel(LightType.SKY, pos));
return key;
}

View file

@ -1,24 +1,32 @@
package com.simibubi.create.content.contraptions.relays.belt;
import com.simibubi.create.content.contraptions.base.KineticAttributes;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import com.simibubi.create.foundation.render.backend.instancing.impl.BasicAttributes;
import net.minecraft.client.renderer.BufferBuilder;
public class BeltInstancedModel extends InstancedModel<BeltData> {
public BeltInstancedModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
public static VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(BasicAttributes.class)
.addAttributes(KineticAttributes.class)
.addAttributes(BeltAttributes.class)
.build();
public BeltInstancedModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
super(renderer, buf);
}
@Override
protected BeltData newInstance() {
@Override
protected BeltData newInstance() {
return new BeltData(this);
}
@Override
protected VertexFormat getInstanceFormat() {
return BeltData.FORMAT;
protected VertexFormat getInstanceFormat() {
return FORMAT;
}
}

View file

@ -53,7 +53,7 @@ public class SplitShaftInstance extends KineticTileInstance<SplitShaftTileEntity
@Override
public void updateLight() {
keys.forEach(key -> relight(pos, ((InstanceKey<? extends KineticData<?>>) key).getInstance()));
keys.forEach(key -> relight(pos, ((InstanceKey<? extends KineticData>) key).getInstance()));
}
@Override
@ -66,9 +66,9 @@ public class SplitShaftInstance extends KineticTileInstance<SplitShaftTileEntity
Direction.Axis axis = dir.getAxis();
key.getInstance()
.setColor(tile.network)
.setRotationalSpeed(tile.getSpeed() * tile.getRotationSpeedModifier(dir))
.setRotationOffset(getRotationOffset(axis))
.setRotationAxis(Direction.getFacingFromAxis(Direction.AxisDirection.POSITIVE, axis).getUnitVector());
.setRotationAxis(Direction.getFacingFromAxis(Direction.AxisDirection.POSITIVE, axis).getUnitVector())
.setRotationalSpeed(tile.getSpeed() * tile.getRotationSpeedModifier(dir))
.setRotationOffset(getRotationOffset(axis))
.setColor(tile.network);
}
}

View file

@ -30,7 +30,7 @@ public abstract class GaugeInstance extends ShaftInstance implements IDynamicIns
GaugeTileEntity gaugeTile = (GaugeTileEntity) tile;
GaugeBlock gaugeBlock = (GaugeBlock) blockState.getBlock();
InstancedModel<ModelData> dialModel = modelManager.getMaterial(RenderMaterials.MODELS).getModel(AllBlockPartials.GAUGE_DIAL, blockState);
InstancedModel<ModelData> dialModel = modelManager.getMaterial(RenderMaterials.TRANSFORMED).getModel(AllBlockPartials.GAUGE_DIAL, blockState);
InstancedModel<ModelData> headModel = getHeadModel();
ms = new MatrixStack();
@ -151,7 +151,7 @@ public abstract class GaugeInstance extends ShaftInstance implements IDynamicIns
@Override
protected InstancedModel<ModelData> getHeadModel() {
return modelManager.getMaterial(RenderMaterials.MODELS).getModel(AllBlockPartials.GAUGE_HEAD_SPEED, blockState);
return modelManager.getMaterial(RenderMaterials.TRANSFORMED).getModel(AllBlockPartials.GAUGE_HEAD_SPEED, blockState);
}
}
@ -162,7 +162,7 @@ public abstract class GaugeInstance extends ShaftInstance implements IDynamicIns
@Override
protected InstancedModel<ModelData> getHeadModel() {
return modelManager.getMaterial(RenderMaterials.MODELS).getModel(AllBlockPartials.GAUGE_HEAD_STRESS, blockState);
return modelManager.getMaterial(RenderMaterials.TRANSFORMED).getModel(AllBlockPartials.GAUGE_HEAD_STRESS, blockState);
}
}
}

View file

@ -42,12 +42,12 @@ public class GearboxInstance extends KineticTileInstance<GearboxTileEntity> {
InstanceKey<RotatingData> key = shaft.createInstance();
key.getInstance()
.setBlockLight(blockLight)
.setSkyLight(skyLight)
.setRotationalSpeed(getSpeed(direction))
.setRotationOffset(getRotationOffset(axis))
.setRotationAxis(Direction.getFacingFromAxis(Direction.AxisDirection.POSITIVE, axis).getUnitVector())
.setTileEntity(tile);
.setRotationAxis(Direction.getFacingFromAxis(Direction.AxisDirection.POSITIVE, axis).getUnitVector())
.setRotationalSpeed(getSpeed(direction))
.setRotationOffset(getRotationOffset(axis))
.setTileEntity(tile)
.setBlockLight(blockLight)
.setSkyLight(skyLight);
keys.put(direction, key);
}
@ -82,11 +82,11 @@ public class GearboxInstance extends KineticTileInstance<GearboxTileEntity> {
Direction.Axis axis = direction.getAxis();
key.getValue()
.getInstance()
.setColor(tile.network)
.setRotationalSpeed(getSpeed(direction))
.setRotationOffset(getRotationOffset(axis))
.setRotationAxis(Direction.getFacingFromAxis(Direction.AxisDirection.POSITIVE, axis).getUnitVector());
.getInstance()
.setRotationAxis(Direction.getFacingFromAxis(Direction.AxisDirection.POSITIVE, axis).getUnitVector())
.setRotationalSpeed(getSpeed(direction))
.setRotationOffset(getRotationOffset(axis))
.setColor(tile.network);
}
}

View file

@ -5,7 +5,7 @@ import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexAttribSpec;
public enum FlapVertexAttributes implements IVertexAttrib {
public enum FlapAttributes implements IVertexAttrib {
INSTANCE_POSITION("aInstancePos",CommonAttributes.VEC3),
LIGHT("aLight", CommonAttributes.LIGHT),
SEGMENT_OFFSET("aSegmentOffset", CommonAttributes.VEC3),
@ -19,7 +19,7 @@ public enum FlapVertexAttributes implements IVertexAttrib {
private final String name;
private final VertexAttribSpec spec;
FlapVertexAttributes(String name, VertexAttribSpec spec) {
FlapAttributes(String name, VertexAttribSpec spec) {
this.name = name;
this.spec = spec;
}

View file

@ -1,6 +1,5 @@
package com.simibubi.create.content.logistics.block;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstanceData;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.impl.IFlatLight;
@ -11,115 +10,111 @@ import java.nio.ByteBuffer;
public class FlapData extends InstanceData implements IFlatLight<FlapData> {
public static VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(FlapVertexAttributes.class)
.build();
private float x;
private float y;
private float z;
private byte blockLight;
private byte skyLight;
private float x;
private float y;
private float z;
private byte blockLight;
private byte skyLight;
private float segmentOffsetX;
private float segmentOffsetY;
private float segmentOffsetZ;
private float segmentOffsetX;
private float segmentOffsetY;
private float segmentOffsetZ;
private float pivotX;
private float pivotY;
private float pivotZ;
private float pivotX;
private float pivotY;
private float pivotZ;
private float horizontalAngle;
private float intensity;
private float flapScale;
private float horizontalAngle;
private float intensity;
private float flapScale;
private float flapness;
private float flapness;
public FlapData(InstancedModel<?> owner) {
super(owner);
}
public FlapData(InstancedModel<?> owner) {
super(owner);
}
public FlapData setPosition(BlockPos pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public FlapData setPosition(BlockPos pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public FlapData setPosition(Vector3f pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public FlapData setPosition(Vector3f pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public FlapData setPosition(int x, int y, int z) {
BlockPos origin = owner.renderer.getOriginCoordinate();
public FlapData setPosition(int x, int y, int z) {
BlockPos origin = owner.renderer.getOriginCoordinate();
return setPosition((float) (x - origin.getX()),
(float) (y - origin.getY()),
(float) (z - origin.getZ()));
}
return setPosition((float) (x - origin.getX()),
(float) (y - origin.getY()),
(float) (z - origin.getZ()));
}
public FlapData setPosition(float x, float y, float z) {
this.x = x;
this.y = y;
this.z = z;
return this;
}
public FlapData setPosition(float x, float y, float z) {
this.x = x;
this.y = y;
this.z = z;
return this;
}
@Override
public FlapData setBlockLight(int blockLight) {
this.blockLight = (byte) ((blockLight & 0xF) << 4);
return this;
}
@Override
public FlapData setBlockLight(int blockLight) {
this.blockLight = (byte) ((blockLight & 0xF) << 4);
return this;
}
@Override
public FlapData setSkyLight(int skyLight) {
this.skyLight = (byte) ((skyLight & 0xF) << 4);
return this;
}
@Override
public FlapData setSkyLight(int skyLight) {
this.skyLight = (byte) ((skyLight & 0xF) << 4);
return this;
}
public FlapData setSegmentOffset(float x, float y, float z) {
this.segmentOffsetX = x;
this.segmentOffsetY = y;
this.segmentOffsetZ = z;
return this;
}
public FlapData setSegmentOffset(float x, float y, float z) {
this.segmentOffsetX = x;
this.segmentOffsetY = y;
this.segmentOffsetZ = z;
return this;
}
public FlapData setIntensity(float intensity) {
this.intensity = intensity;
return this;
}
public FlapData setIntensity(float intensity) {
this.intensity = intensity;
return this;
}
public FlapData setHorizontalAngle(float horizontalAngle) {
this.horizontalAngle = horizontalAngle;
return this;
}
public FlapData setHorizontalAngle(float horizontalAngle) {
this.horizontalAngle = horizontalAngle;
return this;
}
public FlapData setFlapScale(float flapScale) {
this.flapScale = flapScale;
return this;
}
public FlapData setFlapScale(float flapScale) {
this.flapScale = flapScale;
return this;
}
public FlapData setFlapness(float flapness) {
this.flapness = flapness;
return this;
}
public FlapData setFlapness(float flapness) {
this.flapness = flapness;
return this;
}
public FlapData setPivotVoxelSpace(float x, float y, float z) {
pivotX = x / 16f;
pivotY = y / 16f;
pivotZ = z / 16f;
return this;
}
public FlapData setPivotVoxelSpace(float x, float y, float z) {
pivotX = x / 16f;
pivotY = y / 16f;
pivotZ = z / 16f;
return this;
}
@Override
public void write(ByteBuffer buf) {
putVec3(buf, x, y, z);
putVec2(buf, blockLight, skyLight);
@Override
public void write(ByteBuffer buf) {
putVec3(buf, x, y, z);
putVec2(buf, blockLight, skyLight);
putVec3(buf, segmentOffsetX, segmentOffsetY, segmentOffsetZ);
putVec3(buf, pivotX, pivotY, pivotZ);
putVec3(buf, segmentOffsetX, segmentOffsetY, segmentOffsetZ);
putVec3(buf, pivotX, pivotY, pivotZ);
put(buf, horizontalAngle);
put(buf, intensity);
put(buf, flapScale);
put(buf, horizontalAngle);
put(buf, intensity);
put(buf, flapScale);
put(buf, flapness);
}
put(buf, flapness);
}
}

View file

@ -1,22 +0,0 @@
package com.simibubi.create.content.logistics.block;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import net.minecraft.client.renderer.BufferBuilder;
public class FlapInstancedModel extends InstancedModel<FlapData> {
public FlapInstancedModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
super(renderer, buf);
}
@Override
protected FlapData newInstance() {
return new FlapData(this);
}
@Override
protected VertexFormat getInstanceFormat() {
return FlapData.FORMAT;
}
}

View file

@ -0,0 +1,26 @@
package com.simibubi.create.content.logistics.block;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import net.minecraft.client.renderer.BufferBuilder;
public class FlapModel extends InstancedModel<FlapData> {
public static VertexFormat FORMAT = VertexFormat.builder()
.addAttributes(FlapAttributes.class)
.build();
public FlapModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
super(renderer, buf);
}
@Override
protected FlapData newInstance() {
return new FlapData(this);
}
@Override
protected VertexFormat getInstanceFormat() {
return FORMAT;
}
}

View file

@ -16,7 +16,7 @@ public class AdjustableRepeaterInstance extends TileEntityInstance<AdjustableRep
public AdjustableRepeaterInstance(InstancedTileRenderer<?> modelManager, AdjustableRepeaterTileEntity tile) {
super(modelManager, tile);
indicator = modelManager.getBasicMaterial().getModel(AllBlockPartials.FLEXPEATER_INDICATOR, blockState).createInstance();
indicator = modelManager.transformMaterial().getModel(AllBlockPartials.FLEXPEATER_INDICATOR, blockState).createInstance();
MatrixStack ms = new MatrixStack();
MatrixStacker.of(ms).translate(getFloatingPos());

View file

@ -24,135 +24,135 @@ import java.util.ArrayList;
public class ArmInstance extends SingleRotatingInstance implements IDynamicInstance {
final InstanceKey<ModelData> base;
final InstanceKey<ModelData> lowerBody;
final InstanceKey<ModelData> upperBody;
final InstanceKey<ModelData> head;
final InstanceKey<ModelData> claw;
private final ArrayList<InstanceKey<ModelData>> clawGrips;
final InstanceKey<ModelData> base;
final InstanceKey<ModelData> lowerBody;
final InstanceKey<ModelData> upperBody;
final InstanceKey<ModelData> head;
final InstanceKey<ModelData> claw;
private final ArrayList<InstanceKey<ModelData>> clawGrips;
private final ArrayList<InstanceKey<ModelData>> models;
private final ArrayList<InstanceKey<ModelData>> models;
private boolean firstTick = true;
private boolean firstTick = true;
public ArmInstance(InstancedTileRenderer<?> modelManager, KineticTileEntity tile) {
super(modelManager, tile);
public ArmInstance(InstancedTileRenderer<?> modelManager, KineticTileEntity tile) {
super(modelManager, tile);
RenderMaterial<?, InstancedModel<ModelData>> mat = modelManager.getMaterial(RenderMaterials.MODELS);
RenderMaterial<?, InstancedModel<ModelData>> mat = modelManager.getMaterial(RenderMaterials.TRANSFORMED);
base = mat.getModel(AllBlockPartials.ARM_BASE, blockState).createInstance();
lowerBody = mat.getModel(AllBlockPartials.ARM_LOWER_BODY, blockState).createInstance();
upperBody = mat.getModel(AllBlockPartials.ARM_UPPER_BODY, blockState).createInstance();
head = mat.getModel(AllBlockPartials.ARM_HEAD, blockState).createInstance();
claw = mat.getModel(AllBlockPartials.ARM_CLAW_BASE, blockState).createInstance();
base = mat.getModel(AllBlockPartials.ARM_BASE, blockState).createInstance();
lowerBody = mat.getModel(AllBlockPartials.ARM_LOWER_BODY, blockState).createInstance();
upperBody = mat.getModel(AllBlockPartials.ARM_UPPER_BODY, blockState).createInstance();
head = mat.getModel(AllBlockPartials.ARM_HEAD, blockState).createInstance();
claw = mat.getModel(AllBlockPartials.ARM_CLAW_BASE, blockState).createInstance();
InstancedModel<ModelData> clawHalfModel = mat.getModel(AllBlockPartials.ARM_CLAW_GRIP, blockState);
InstanceKey<ModelData> clawGrip1 = clawHalfModel.createInstance();
InstanceKey<ModelData> clawGrip2 = clawHalfModel.createInstance();
InstancedModel<ModelData> clawHalfModel = mat.getModel(AllBlockPartials.ARM_CLAW_GRIP, blockState);
InstanceKey<ModelData> clawGrip1 = clawHalfModel.createInstance();
InstanceKey<ModelData> clawGrip2 = clawHalfModel.createInstance();
clawGrips = Lists.newArrayList(clawGrip1, clawGrip2);
models = Lists.newArrayList(base, lowerBody, upperBody, head, claw, clawGrip1, clawGrip2);
clawGrips = Lists.newArrayList(clawGrip1, clawGrip2);
models = Lists.newArrayList(base, lowerBody, upperBody, head, claw, clawGrip1, clawGrip2);
updateLight();
}
updateLight();
}
@Override
public void beginFrame() {
ArmTileEntity arm = (ArmTileEntity) tile;
@Override
public void beginFrame() {
ArmTileEntity arm = (ArmTileEntity) tile;
boolean settled = arm.baseAngle.settled() && arm.lowerArmAngle.settled() && arm.upperArmAngle.settled() && arm.headAngle.settled();
boolean rave = arm.phase == ArmTileEntity.Phase.DANCING;
boolean settled = arm.baseAngle.settled() && arm.lowerArmAngle.settled() && arm.upperArmAngle.settled() && arm.headAngle.settled();
boolean rave = arm.phase == ArmTileEntity.Phase.DANCING;
if (!settled || rave || firstTick)
transformModels(arm, rave);
if (!settled || rave || firstTick)
transformModels(arm, rave);
if (settled)
firstTick = false;
}
if (settled)
firstTick = false;
}
private void transformModels(ArmTileEntity arm, boolean rave) {
float pt = AnimationTickHolder.getPartialTicks();
int color = 0xFFFFFF;
private void transformModels(ArmTileEntity arm, boolean rave) {
float pt = AnimationTickHolder.getPartialTicks();
int color = 0xFFFFFF;
float baseAngle = arm.baseAngle.get(pt);
float lowerArmAngle = arm.lowerArmAngle.get(pt) - 135;
float upperArmAngle = arm.upperArmAngle.get(pt) - 90;
float headAngle = arm.headAngle.get(pt);
float baseAngle = arm.baseAngle.get(pt);
float lowerArmAngle = arm.lowerArmAngle.get(pt) - 135;
float upperArmAngle = arm.upperArmAngle.get(pt) - 90;
float headAngle = arm.headAngle.get(pt);
if (rave) {
float renderTick = AnimationTickHolder.getRenderTime(arm.getWorld()) + (tile.hashCode() % 64);
baseAngle = (renderTick * 10) % 360;
lowerArmAngle = MathHelper.lerp((MathHelper.sin(renderTick / 4) + 1) / 2, -45, 15);
upperArmAngle = MathHelper.lerp((MathHelper.sin(renderTick / 8) + 1) / 4, -45, 95);
headAngle = -lowerArmAngle;
color = ColorHelper.rainbowColor(AnimationTickHolder.getTicks() * 100);
}
if (rave) {
float renderTick = AnimationTickHolder.getRenderTime(arm.getWorld()) + (tile.hashCode() % 64);
baseAngle = (renderTick * 10) % 360;
lowerArmAngle = MathHelper.lerp((MathHelper.sin(renderTick / 4) + 1) / 2, -45, 15);
upperArmAngle = MathHelper.lerp((MathHelper.sin(renderTick / 8) + 1) / 4, -45, 95);
headAngle = -lowerArmAngle;
color = ColorHelper.rainbowColor(AnimationTickHolder.getTicks() * 100);
}
MatrixStack msLocal = new MatrixStack();
MatrixStacker msr = MatrixStacker.of(msLocal);
msr.translate(getFloatingPos());
msr.centre();
MatrixStack msLocal = new MatrixStack();
MatrixStacker msr = MatrixStacker.of(msLocal);
msr.translate(getFloatingPos());
msr.centre();
if (blockState.get(ArmBlock.CEILING))
msr.rotateX(180);
if (blockState.get(ArmBlock.CEILING))
msr.rotateX(180);
ArmRenderer.transformBase(msr, baseAngle);
base.getInstance()
.setTransform(msLocal);
ArmRenderer.transformBase(msr, baseAngle);
base.getInstance()
.setTransform(msLocal);
ArmRenderer.transformLowerArm(msr, lowerArmAngle);
lowerBody.getInstance()
.setColor(color)
.setTransform(msLocal);
ArmRenderer.transformLowerArm(msr, lowerArmAngle);
lowerBody.getInstance()
.setTransform(msLocal)
.setColor(color);
ArmRenderer.transformUpperArm(msr, upperArmAngle);
upperBody.getInstance()
.setColor(color)
.setTransform(msLocal);
ArmRenderer.transformUpperArm(msr, upperArmAngle);
upperBody.getInstance()
.setTransform(msLocal)
.setColor(color);
ArmRenderer.transformHead(msr, headAngle);
head.getInstance()
.setTransform(msLocal);
ArmRenderer.transformHead(msr, headAngle);
head.getInstance()
.setTransform(msLocal);
ArmRenderer.transformClaw(msr);
claw.getInstance()
.setTransform(msLocal);
ArmRenderer.transformClaw(msr);
claw.getInstance()
.setTransform(msLocal);
ItemStack item = arm.heldItem;
ItemRenderer itemRenderer = Minecraft.getInstance()
.getItemRenderer();
boolean hasItem = !item.isEmpty();
boolean isBlockItem = hasItem && (item.getItem() instanceof BlockItem)
&& itemRenderer.getItemModelWithOverrides(item, Minecraft.getInstance().world, null)
.isGui3d();
ItemStack item = arm.heldItem;
ItemRenderer itemRenderer = Minecraft.getInstance()
.getItemRenderer();
boolean hasItem = !item.isEmpty();
boolean isBlockItem = hasItem && (item.getItem() instanceof BlockItem)
&& itemRenderer.getItemModelWithOverrides(item, Minecraft.getInstance().world, null)
.isGui3d();
for (int index : Iterate.zeroAndOne) {
msLocal.push();
int flip = index * 2 - 1;
ArmRenderer.transformClawHalf(msr, hasItem, isBlockItem, flip);
clawGrips.get(index)
.getInstance()
.setTransform(msLocal);
msLocal.pop();
}
}
for (int index : Iterate.zeroAndOne) {
msLocal.push();
int flip = index * 2 - 1;
ArmRenderer.transformClawHalf(msr, hasItem, isBlockItem, flip);
clawGrips.get(index)
.getInstance()
.setTransform(msLocal);
msLocal.pop();
}
}
@Override
public void updateLight() {
super.updateLight();
@Override
public void updateLight() {
super.updateLight();
relight(pos, models.stream().map(InstanceKey::getInstance));
}
relight(pos, models.stream().map(InstanceKey::getInstance));
}
@Override
protected InstancedModel<RotatingData> getModel() {
return AllBlockPartials.ARM_COG.renderOnRotating(modelManager, tile.getBlockState());
}
@Override
protected InstancedModel<RotatingData> getModel() {
return AllBlockPartials.ARM_COG.renderOnRotating(modelManager, tile.getBlockState());
}
@Override
public void remove() {
super.remove();
models.forEach(InstanceKey::delete);
}
@Override
public void remove() {
super.remove();
models.forEach(InstanceKey::delete);
}
}

View file

@ -23,7 +23,7 @@ public class AnalogLeverInstance extends TileEntityInstance<AnalogLeverTileEntit
public AnalogLeverInstance(InstancedTileRenderer<?> modelManager, AnalogLeverTileEntity tile) {
super(modelManager, tile);
RenderMaterial<?, InstancedModel<ModelData>> mat = modelManager.getMaterial(RenderMaterials.MODELS);
RenderMaterial<?, InstancedModel<ModelData>> mat = modelManager.getMaterial(RenderMaterials.TRANSFORMED);
handle = mat.getModel(AllBlockPartials.ANALOG_LEVER_HANDLE, blockState).createInstance();
indicator = mat.getModel(AllBlockPartials.ANALOG_LEVER_INDICATOR, blockState).createInstance();
@ -62,7 +62,7 @@ public class AnalogLeverInstance extends TileEntityInstance<AnalogLeverTileEntit
.translate(-1 / 2f, -1 / 16f, -1 / 2f);
handle.getInstance()
.setTransformNoCopy(ms);
.setTransform(ms);
}
@Override

View file

@ -17,7 +17,7 @@ public class SchematicannonInstance extends TileEntityInstance<SchematicannonTil
public SchematicannonInstance(InstancedTileRenderer<?> modelManager, SchematicannonTileEntity tile) {
super(modelManager, tile);
RenderMaterial<?, InstancedModel<ModelData>> mat = modelManager.getMaterial(RenderMaterials.MODELS);
RenderMaterial<?, InstancedModel<ModelData>> mat = modelManager.getMaterial(RenderMaterials.TRANSFORMED);
connector = mat.getModel(AllBlockPartials.SCHEMATICANNON_CONNECTOR, blockState).createInstance();
pipe = mat.getModel(AllBlockPartials.SCHEMATICANNON_PIPE, blockState).createInstance();
@ -54,7 +54,7 @@ public class SchematicannonInstance extends TileEntityInstance<SchematicannonTil
msr.translate(-.5f, -15 / 16f, -.5f);
msr.translate(0, -recoil / 100, 0);
pipe.getInstance().setTransformNoCopy(ms);
pipe.getInstance().setTransform(ms);
}
@Override

View file

@ -1,8 +1,11 @@
package com.simibubi.create.foundation.mixin;
import com.simibubi.create.foundation.render.KineticRenderer;
import net.minecraft.block.BlockState;
import net.minecraft.client.renderer.*;
import net.minecraft.client.renderer.texture.AtlasTexture;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Vec3d;
import org.lwjgl.opengl.GL20;
import org.spongepowered.asm.mixin.Mixin;
@ -58,6 +61,11 @@ public class RenderHooksMixin {
ContraptionRenderDispatcher.beginFrame(camX, camY, camZ);
}
@Inject(at = @At("TAIL"), method = "checkBlockRerender")
private void checkUpdate(BlockPos pos, BlockState lastState, BlockState newState, CallbackInfo ci) {
CreateClient.kineticRenderer.get(world).update(world.getTileEntity(pos));
}
@Inject(at = @At("TAIL"), method = "loadRenderers")
private void refresh(CallbackInfo ci) {
ContraptionRenderDispatcher.invalidateAll();

View file

@ -3,112 +3,137 @@ package com.simibubi.create.foundation.render;
import static com.simibubi.create.foundation.render.backend.Backend.register;
import com.simibubi.create.Create;
import com.simibubi.create.content.contraptions.base.KineticVertexAttributes;
import com.simibubi.create.content.contraptions.base.RotatingVertexAttributes;
import com.simibubi.create.content.contraptions.base.KineticAttributes;
import com.simibubi.create.content.contraptions.base.RotatingAttributes;
import com.simibubi.create.content.contraptions.components.actors.ActorVertexAttributes;
import com.simibubi.create.content.contraptions.components.structureMovement.render.ContraptionProgram;
import com.simibubi.create.content.contraptions.components.structureMovement.render.ContraptionVertexAttributes;
import com.simibubi.create.content.contraptions.relays.belt.BeltVertexAttributes;
import com.simibubi.create.content.logistics.block.FlapVertexAttributes;
import com.simibubi.create.content.contraptions.components.structureMovement.render.ContraptionAttributes;
import com.simibubi.create.content.contraptions.relays.belt.BeltAttributes;
import com.simibubi.create.content.logistics.block.FlapAttributes;
import com.simibubi.create.foundation.render.backend.gl.BasicProgram;
import com.simibubi.create.foundation.render.backend.gl.attrib.InstanceVertexAttributes;
import com.simibubi.create.foundation.render.backend.gl.attrib.ModelVertexAttributes;
import com.simibubi.create.foundation.render.backend.instancing.impl.BasicAttributes;
import com.simibubi.create.foundation.render.backend.instancing.impl.TransformAttributes;
import com.simibubi.create.foundation.render.backend.instancing.impl.ModelAttributes;
import com.simibubi.create.foundation.render.backend.instancing.impl.OrientedAttributes;
import com.simibubi.create.foundation.render.backend.gl.shader.ProgramSpec;
import com.simibubi.create.foundation.render.backend.gl.shader.ShaderConstants;
import net.minecraft.util.ResourceLocation;
public class AllProgramSpecs {
public static void init() {
// noop, make sure the static field are loaded.
}
public static void init() {
// noop, make sure the static field are loaded.
}
public static final ProgramSpec<BasicProgram> MODEL = register(ProgramSpec.builder("model", BasicProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(InstanceVertexAttributes.class)
.setVert(Locations.MODEL_VERT)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<BasicProgram> MODEL = register(ProgramSpec.builder("model", BasicProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(BasicAttributes.class)
.addAttributes(TransformAttributes.class)
.setVert(Locations.MODEL_VERT)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<BasicProgram> ROTATING = register(ProgramSpec.builder("rotating", BasicProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(KineticVertexAttributes.class)
.addAttributes(RotatingVertexAttributes.class)
.setVert(Locations.ROTATING)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<BasicProgram> ORIENTED = register(ProgramSpec.builder("oriented", BasicProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(BasicAttributes.class)
.addAttributes(OrientedAttributes.class)
.setVert(Locations.ORIENTED)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<BasicProgram> BELT = register(ProgramSpec.builder("belt", BasicProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(KineticVertexAttributes.class)
.addAttributes(BeltVertexAttributes.class)
.setVert(Locations.BELT)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<BasicProgram> ROTATING = register(ProgramSpec.builder("rotating", BasicProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(BasicAttributes.class)
.addAttributes(KineticAttributes.class)
.addAttributes(RotatingAttributes.class)
.setVert(Locations.ROTATING)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<BasicProgram> FLAPS = register(ProgramSpec.builder("flap", BasicProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(FlapVertexAttributes.class)
.setVert(Locations.FLAP)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_STRUCTURE = register(ProgramSpec.builder("contraption_structure", ContraptionProgram::new)
.addAttributes(ContraptionVertexAttributes.class)
.setVert(Locations.CONTRAPTION_STRUCTURE)
.setFrag(Locations.CONTRAPTION)
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_MODEL = register(ProgramSpec.builder("contraption_model", ContraptionProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(InstanceVertexAttributes.class)
.setVert(Locations.MODEL_VERT)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_ROTATING = register(ProgramSpec.builder("contraption_rotating", ContraptionProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(KineticVertexAttributes.class)
.addAttributes(RotatingVertexAttributes.class)
.setVert(Locations.ROTATING)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_BELT = register(ProgramSpec.builder("contraption_belt", ContraptionProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(KineticVertexAttributes.class)
.addAttributes(BeltVertexAttributes.class)
.setVert(Locations.BELT)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_FLAPS = register(ProgramSpec.builder("contraption_flap", ContraptionProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(FlapVertexAttributes.class)
.setVert(Locations.FLAP)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_ACTOR = register(ProgramSpec.builder("contraption_actor", ContraptionProgram::new)
.addAttributes(ModelVertexAttributes.class)
.addAttributes(ActorVertexAttributes.class)
.setVert(Locations.CONTRAPTION_ACTOR)
.setFrag(Locations.CONTRAPTION)
.createProgramSpec());
public static final ProgramSpec<BasicProgram> BELT = register(ProgramSpec.builder("belt", BasicProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(BasicAttributes.class)
.addAttributes(KineticAttributes.class)
.addAttributes(BeltAttributes.class)
.setVert(Locations.BELT)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<BasicProgram> FLAPS = register(ProgramSpec.builder("flap", BasicProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(FlapAttributes.class)
.setVert(Locations.FLAP)
.setFrag(Locations.MODEL_FRAG)
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_STRUCTURE = register(ProgramSpec.builder("contraption_structure", ContraptionProgram::new)
.addAttributes(ContraptionAttributes.class)
.setVert(Locations.CONTRAPTION_STRUCTURE)
.setFrag(Locations.CONTRAPTION)
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_MODEL = register(ProgramSpec.builder("contraption_model", ContraptionProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(BasicAttributes.class)
.addAttributes(TransformAttributes.class)
.setVert(Locations.MODEL_VERT)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_ORIENTED = register(ProgramSpec.builder("contraption_oriented", ContraptionProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(BasicAttributes.class)
.addAttributes(OrientedAttributes.class)
.setVert(Locations.ORIENTED)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_ROTATING = register(ProgramSpec.builder("contraption_rotating", ContraptionProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(BasicAttributes.class)
.addAttributes(KineticAttributes.class)
.addAttributes(RotatingAttributes.class)
.setVert(Locations.ROTATING)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_BELT = register(ProgramSpec.builder("contraption_belt", ContraptionProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(BasicAttributes.class)
.addAttributes(KineticAttributes.class)
.addAttributes(BeltAttributes.class)
.setVert(Locations.BELT)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_FLAPS = register(ProgramSpec.builder("contraption_flap", ContraptionProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(FlapAttributes.class)
.setVert(Locations.FLAP)
.setFrag(Locations.CONTRAPTION)
.setDefines(ShaderConstants.define("CONTRAPTION"))
.createProgramSpec());
public static final ProgramSpec<ContraptionProgram> C_ACTOR = register(ProgramSpec.builder("contraption_actor", ContraptionProgram::new)
.addAttributes(ModelAttributes.class)
.addAttributes(ActorVertexAttributes.class)
.setVert(Locations.CONTRAPTION_ACTOR)
.setFrag(Locations.CONTRAPTION)
.createProgramSpec());
public static class Locations {
public static final ResourceLocation MODEL_FRAG = loc("model.frag");
public static final ResourceLocation MODEL_VERT = loc("model.vert");
public static final ResourceLocation CONTRAPTION = loc("contraption.frag");
public static class Locations {
public static final ResourceLocation MODEL_FRAG = loc("model.frag");
public static final ResourceLocation MODEL_VERT = loc("model.vert");
public static final ResourceLocation ORIENTED = loc("oriented.vert");
public static final ResourceLocation CONTRAPTION = loc("contraption.frag");
public static final ResourceLocation ROTATING = loc("rotating.vert");
public static final ResourceLocation BELT = loc("belt.vert");
public static final ResourceLocation FLAP = loc("flap.vert");
public static final ResourceLocation CONTRAPTION_STRUCTURE = loc("contraption_structure.vert");
public static final ResourceLocation CONTRAPTION_ACTOR = loc("contraption_actor.vert");
public static final ResourceLocation ROTATING = loc("rotating.vert");
public static final ResourceLocation BELT = loc("belt.vert");
public static final ResourceLocation FLAP = loc("flap.vert");
public static final ResourceLocation CONTRAPTION_STRUCTURE = loc("contraption_structure.vert");
public static final ResourceLocation CONTRAPTION_ACTOR = loc("contraption_actor.vert");
private static ResourceLocation loc(String name) {
return new ResourceLocation(Create.ID, name);
}
}
private static ResourceLocation loc(String name) {
return new ResourceLocation(Create.ID, name);
}
}
}

View file

@ -3,20 +3,20 @@ package com.simibubi.create.foundation.render;
import java.util.ArrayList;
import com.simibubi.create.content.contraptions.base.KineticRenderMaterials;
import com.simibubi.create.content.contraptions.base.RotatingInstancedModel;
import com.simibubi.create.content.contraptions.base.RotatingModel;
import com.simibubi.create.content.contraptions.relays.belt.BeltInstancedModel;
import com.simibubi.create.content.logistics.block.FlapInstancedModel;
import com.simibubi.create.content.logistics.block.FlapModel;
import com.simibubi.create.foundation.render.backend.RenderMaterials;
import com.simibubi.create.foundation.render.backend.gl.BasicProgram;
import com.simibubi.create.foundation.render.backend.gl.shader.ShaderCallback;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import com.simibubi.create.foundation.render.backend.instancing.RenderMaterial;
import com.simibubi.create.foundation.render.backend.instancing.impl.BasicInstancedModel;
import net.minecraft.client.Minecraft;
import com.simibubi.create.foundation.render.backend.instancing.impl.OrientedModel;
import com.simibubi.create.foundation.render.backend.instancing.impl.TransformedModel;
import net.minecraft.client.renderer.Matrix4f;
import net.minecraft.client.renderer.RenderType;
import net.minecraft.entity.Entity;
import net.minecraft.tileentity.TileEntity;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.MathHelper;
@ -28,11 +28,12 @@ public class KineticRenderer extends InstancedTileRenderer<BasicProgram> {
@Override
public void registerMaterials() {
materials.put(RenderMaterials.MODELS, new RenderMaterial<>(this, AllProgramSpecs.MODEL, BasicInstancedModel::new));
materials.put(RenderMaterials.TRANSFORMED, new RenderMaterial<>(this, AllProgramSpecs.MODEL, TransformedModel::new));
materials.put(RenderMaterials.ORIENTED, new RenderMaterial<>(this, AllProgramSpecs.ORIENTED, OrientedModel::new));
materials.put(KineticRenderMaterials.BELTS, new RenderMaterial<>(this, AllProgramSpecs.BELT, BeltInstancedModel::new));
materials.put(KineticRenderMaterials.ROTATING, new RenderMaterial<>(this, AllProgramSpecs.ROTATING, RotatingInstancedModel::new));
materials.put(KineticRenderMaterials.FLAPS, new RenderMaterial<>(this, AllProgramSpecs.FLAPS, FlapInstancedModel::new));
materials.put(KineticRenderMaterials.ROTATING, new RenderMaterial<>(this, AllProgramSpecs.ROTATING, RotatingModel::new));
materials.put(KineticRenderMaterials.FLAPS, new RenderMaterial<>(this, AllProgramSpecs.FLAPS, FlapModel::new));
}
@Override

View file

@ -3,7 +3,9 @@ package com.simibubi.create.foundation.render.backend;
import com.simibubi.create.foundation.render.backend.instancing.MaterialType;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.impl.ModelData;
import com.simibubi.create.foundation.render.backend.instancing.impl.OrientedData;
public class RenderMaterials {
public static final MaterialType<InstancedModel<ModelData>> MODELS = new MaterialType<>();
public static final MaterialType<InstancedModel<ModelData>> TRANSFORMED = new MaterialType<>();
public static final MaterialType<InstancedModel<OrientedData>> ORIENTED = new MaterialType<>();
}

View file

@ -7,50 +7,45 @@ import java.nio.ByteBuffer;
import java.nio.FloatBuffer;
public class RenderUtil {
public static int nextPowerOf2(int a) {
int h = Integer.highestOneBit(a);
return (h == a) ? h : (h << 1);
}
public static int nextPowerOf2(int a) {
int h = Integer.highestOneBit(a);
return (h == a) ? h : (h << 1);
}
public static boolean isPowerOf2(int n) {
int b = n & (n - 1);
return b == 0 && n != 0;
}
public static boolean isPowerOf2(int n) {
int b = n & (n - 1);
return b == 0 && n != 0;
}
// GPUs want matrices in column major order.
// GPUs want matrices in column major order.
public static void writeMat3(ByteBuffer buf, Matrix3f mat) {
buf.putFloat(mat.a00);
buf.putFloat(mat.a10);
buf.putFloat(mat.a20);
buf.putFloat(mat.a01);
buf.putFloat(mat.a11);
buf.putFloat(mat.a21);
buf.putFloat(mat.a02);
buf.putFloat(mat.a12);
buf.putFloat(mat.a22);
}
public static void writeMat4(ByteBuffer buf, Matrix4f mat) {
buf.putFloat(mat.a00);
buf.putFloat(mat.a10);
buf.putFloat(mat.a20);
buf.putFloat(mat.a30);
buf.putFloat(mat.a01);
buf.putFloat(mat.a11);
buf.putFloat(mat.a21);
buf.putFloat(mat.a31);
buf.putFloat(mat.a02);
buf.putFloat(mat.a12);
buf.putFloat(mat.a22);
buf.putFloat(mat.a32);
buf.putFloat(mat.a03);
buf.putFloat(mat.a13);
buf.putFloat(mat.a23);
buf.putFloat(mat.a33);
}
public static float[] bufferMatrices(Matrix4f model, Matrix3f normal) {
return new float[] {
model.a00,
model.a10,
model.a20,
model.a30,
model.a01,
model.a11,
model.a21,
model.a31,
model.a02,
model.a12,
model.a22,
model.a32,
model.a03,
model.a13,
model.a23,
model.a33,
normal.a00,
normal.a10,
normal.a20,
normal.a01,
normal.a11,
normal.a21,
normal.a02,
normal.a12,
normal.a22,
};
}
}

View file

@ -1,36 +0,0 @@
package com.simibubi.create.foundation.render.backend.gl.attrib;
public enum ModelVertexAttributes implements IVertexAttrib {
VERTEX_POSITION("aPos", CommonAttributes.VEC3),
NORMAL("aNormal", CommonAttributes.NORMAL),
TEXTURE("aTexCoords", CommonAttributes.UV),
;
private final String name;
private final VertexAttribSpec spec;
ModelVertexAttributes(String name, VertexAttribSpec spec) {
this.name = name;
this.spec = spec;
}
@Override
public String attribName() {
return name;
}
@Override
public IAttribSpec attribSpec() {
return spec;
}
@Override
public int getDivisor() {
return 0;
}
@Override
public int getBufferIndex() {
return 0;
}
}

View file

@ -1,7 +1,5 @@
package com.simibubi.create.foundation.render.backend.instancing;
import java.util.function.Consumer;
public class InstanceKey<D extends InstanceData> {
public static final int INVALID = -1;

View file

@ -3,7 +3,6 @@ package com.simibubi.create.foundation.render.backend.instancing;
import java.nio.ByteBuffer;
import java.util.*;
import java.util.function.Consumer;
import com.simibubi.create.foundation.render.backend.Backend;
import com.simibubi.create.foundation.render.backend.RenderUtil;
@ -14,13 +13,13 @@ import org.lwjgl.opengl.GL20;
import com.simibubi.create.foundation.render.backend.BufferedModel;
import com.simibubi.create.foundation.render.backend.gl.GlBuffer;
import com.simibubi.create.foundation.render.backend.gl.GlVertexArray;
import com.simibubi.create.foundation.render.backend.gl.attrib.ModelVertexAttributes;
import com.simibubi.create.foundation.render.backend.instancing.impl.ModelAttributes;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import net.minecraft.client.renderer.BufferBuilder;
public abstract class InstancedModel<D extends InstanceData> extends BufferedModel {
public static final VertexFormat FORMAT = VertexFormat.builder().addAttributes(ModelVertexAttributes.class).build();
public static final VertexFormat FORMAT = VertexFormat.builder().addAttributes(ModelAttributes.class).build();
public final InstancedTileRenderer<?> renderer;

View file

@ -9,6 +9,7 @@ import com.simibubi.create.foundation.render.backend.RenderMaterials;
import com.simibubi.create.foundation.render.backend.gl.BasicProgram;
import com.simibubi.create.foundation.render.backend.gl.shader.ShaderCallback;
import com.simibubi.create.foundation.render.backend.instancing.impl.ModelData;
import com.simibubi.create.foundation.render.backend.instancing.impl.OrientedData;
import com.simibubi.create.foundation.utility.AnimationTickHolder;
import net.minecraft.client.Minecraft;
@ -52,7 +53,7 @@ public abstract class InstancedTileRenderer<P extends BasicProgram> {
public void beginFrame(double cameraX, double cameraY, double cameraZ) {
if (queuedAdditions.size() > 0) {
queuedAdditions.forEach(this::add);
queuedAdditions.forEach(this::addInternal);
queuedAdditions.clear();
}
if (dynamicInstances.size() > 0)
@ -75,33 +76,25 @@ public abstract class InstancedTileRenderer<P extends BasicProgram> {
return (RenderMaterial<P, M>) materials.get(materialType);
}
public RenderMaterial<P, InstancedModel<ModelData>> getBasicMaterial() {
return getMaterial(RenderMaterials.MODELS);
public RenderMaterial<P, InstancedModel<ModelData>> transformMaterial() {
return getMaterial(RenderMaterials.TRANSFORMED);
}
public RenderMaterial<P, InstancedModel<OrientedData>> orientedMaterial() {
return getMaterial(RenderMaterials.ORIENTED);
}
@SuppressWarnings("unchecked")
@Nullable
public <T extends TileEntity> TileEntityInstance<? super T> getInstance(T tile, boolean create) {
if (!Backend.canUseInstancing() || !canCreateInstance(tile)) return null;
if (!Backend.canUseInstancing()) return null;
TileEntityInstance<?> instance = instances.get(tile);
if (instance != null) {
return (TileEntityInstance<? super T>) instance;
} else if (create) {
TileEntityInstance<? super T> renderer = InstancedTileRenderRegistry.instance.create(this, tile);
if (renderer != null) {
instances.put(tile, renderer);
if (renderer instanceof IDynamicInstance)
dynamicInstances.put(tile, (IDynamicInstance) renderer);
if (renderer instanceof ITickableInstance)
tickableInstances.put(tile, ((ITickableInstance) renderer));
}
return renderer;
} else if (create && canCreateInstance(tile)) {
return createInternal(tile);
} else {
return null;
}
@ -122,7 +115,7 @@ public abstract class InstancedTileRenderer<P extends BasicProgram> {
if (!Backend.canUseInstancing()) return;
if (tile instanceof IInstanceRendered) {
getInstance(tile, true);
addInternal(tile);
}
}
@ -143,7 +136,7 @@ public abstract class InstancedTileRenderer<P extends BasicProgram> {
if (instance.shouldReset()) {
removeInternal(tile, instance);
getInstance(tile, true);
createInternal(tile);
} else {
instance.update();
}
@ -159,6 +152,10 @@ public abstract class InstancedTileRenderer<P extends BasicProgram> {
}
}
private void addInternal(TileEntity tile) {
getInstance(tile, true);
}
private <T extends TileEntity> void removeInternal(T tile) {
TileEntityInstance<? super T> instance = getInstance(tile, false);
@ -167,14 +164,30 @@ public abstract class InstancedTileRenderer<P extends BasicProgram> {
}
}
private <T extends TileEntity> void removeInternal(T tile, TileEntityInstance<? super T> instance) {
private void removeInternal(TileEntity tile, TileEntityInstance<?> instance) {
instance.remove();
instances.remove(tile);
dynamicInstances.remove(tile);
tickableInstances.remove(tile);
}
public void clean() {
private <T extends TileEntity> TileEntityInstance<? super T> createInternal(T tile) {
TileEntityInstance<? super T> renderer = InstancedTileRenderRegistry.instance.create(this, tile);
if (renderer != null) {
instances.put(tile, renderer);
if (renderer instanceof IDynamicInstance)
dynamicInstances.put(tile, (IDynamicInstance) renderer);
if (renderer instanceof ITickableInstance)
tickableInstances.put(tile, ((ITickableInstance) renderer));
}
return renderer;
}
private void clean() {
instances.keySet().removeIf(TileEntity::isRemoved);
}

View file

@ -1,3 +1,10 @@
package com.simibubi.create.foundation.render.backend.instancing;
public class MaterialType<M> { }
import com.simibubi.create.foundation.render.backend.gl.BasicProgram;
public class MaterialType<M extends InstancedModel<?>> {
public <P extends BasicProgram> RenderMaterial<?, M> get(InstancedTileRenderer<P> renderer) {
return renderer.getMaterial(this);
}
}

View file

@ -0,0 +1,39 @@
package com.simibubi.create.foundation.render.backend.instancing.impl;
import com.simibubi.create.foundation.render.backend.gl.attrib.CommonAttributes;
import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
public enum BasicAttributes implements IVertexAttrib {
LIGHT("aLight", CommonAttributes.LIGHT),
COLOR("aColor", CommonAttributes.RGBA),
;
private final String name;
private final IAttribSpec spec;
BasicAttributes(String name, IAttribSpec spec) {
this.name = name;
this.spec = spec;
}
@Override
public String attribName() {
return name;
}
@Override
public IAttribSpec attribSpec() {
return spec;
}
@Override
public int getDivisor() {
return 0;
}
@Override
public int getBufferIndex() {
return 0;
}
}

View file

@ -0,0 +1,73 @@
package com.simibubi.create.foundation.render.backend.instancing.impl;
import java.nio.ByteBuffer;
import com.simibubi.create.foundation.render.backend.instancing.InstanceData;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
public class BasicData extends InstanceData implements IFlatLight<BasicData> {
protected byte blockLight;
protected byte skyLight;
protected byte r = (byte) 0xFF;
protected byte g = (byte) 0xFF;
protected byte b = (byte) 0xFF;
protected byte a = (byte) 0xFF;
public BasicData(InstancedModel<?> owner) {
super(owner);
}
@Override
public BasicData setBlockLight(int blockLight) {
this.blockLight = (byte) (blockLight << 4);
return this;
}
@Override
public BasicData setSkyLight(int skyLight) {
this.skyLight = (byte) (skyLight << 4);
return this;
}
public BasicData setColor(int color) {
return setColor(color, false);
}
public BasicData setColor(int color, boolean alpha) {
byte r = (byte) ((color >> 16) & 0xFF);
byte g = (byte) ((color >> 8) & 0xFF);
byte b = (byte) (color & 0xFF);
if (alpha) {
byte a = (byte) ((color >> 24) & 0xFF);
return setColor(r, g, b, a);
} else {
return setColor(r, g, b);
}
}
public BasicData setColor(int r, int g, int b) {
return setColor((byte) r, (byte) g, (byte) b);
}
public BasicData setColor(byte r, byte g, byte b) {
this.r = r;
this.g = g;
this.b = b;
return this;
}
public BasicData setColor(byte r, byte g, byte b, byte a) {
this.r = r;
this.g = g;
this.b = b;
this.a = a;
return this;
}
@Override
public void write(ByteBuffer buf) {
buf.put(new byte[] { blockLight, skyLight, r, g, b, a });
}
}

View file

@ -0,0 +1,41 @@
package com.simibubi.create.foundation.render.backend.instancing.impl;
import com.simibubi.create.foundation.render.backend.gl.attrib.CommonAttributes;
import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexAttribSpec;
public enum ModelAttributes implements IVertexAttrib {
VERTEX_POSITION("aPos", CommonAttributes.VEC3),
NORMAL("aNormal", CommonAttributes.NORMAL),
TEXTURE("aTexCoords", CommonAttributes.UV),
;
private final String name;
private final VertexAttribSpec spec;
ModelAttributes(String name, VertexAttribSpec spec) {
this.name = name;
this.spec = spec;
}
@Override
public String attribName() {
return name;
}
@Override
public IAttribSpec attribSpec() {
return spec;
}
@Override
public int getDivisor() {
return 0;
}
@Override
public int getBufferIndex() {
return 0;
}
}

View file

@ -2,101 +2,28 @@ package com.simibubi.create.foundation.render.backend.instancing.impl;
import com.mojang.blaze3d.matrix.MatrixStack;
import com.simibubi.create.foundation.render.backend.RenderUtil;
import com.simibubi.create.foundation.render.backend.instancing.InstanceData;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import net.minecraft.client.renderer.Matrix3f;
import net.minecraft.client.renderer.Matrix4f;
import java.nio.ByteBuffer;
public class ModelData extends InstanceData implements IFlatLight<ModelData> {
private static final Matrix4f IDENT4 = new Matrix4f();
private static final Matrix3f IDENT3 = new Matrix3f();
static {
IDENT4.loadIdentity();
IDENT3.loadIdentity();
}
public class ModelData extends BasicData {
private static final float[] empty = new float[25];
private Matrix4f modelMat = IDENT4;
private Matrix3f normalMat = IDENT3;
private byte blockLight;
private byte skyLight;
private byte r = (byte) 0xFF;
private byte g = (byte) 0xFF;
private byte b = (byte) 0xFF;
private byte a = (byte) 0xFF;
private float[] matrices = empty;
public ModelData(InstancedModel<?> owner) {
super(owner);
}
public ModelData setModelMat(Matrix4f modelMat) {
this.modelMat = modelMat;
return this;
}
public ModelData setNormalMat(Matrix3f normalMat) {
this.normalMat = normalMat;
return this;
}
public ModelData setTransform(MatrixStack stack) {
this.modelMat = stack.peek().getModel().copy();
this.normalMat = stack.peek().getNormal().copy();
return this;
}
public ModelData setTransformNoCopy(MatrixStack stack) {
this.modelMat = stack.peek().getModel();
this.normalMat = stack.peek().getNormal();
return this;
}
@Override
public ModelData setBlockLight(int blockLight) {
this.blockLight = (byte) (blockLight << 4);
return this;
}
@Override
public ModelData setSkyLight(int skyLight) {
this.skyLight = (byte) (skyLight << 4);
return this;
}
public ModelData setColor(int color) {
byte a = (byte) ((color >> 24) & 0xFF);
byte r = (byte) ((color >> 16) & 0xFF);
byte g = (byte) ((color >> 8) & 0xFF);
byte b = (byte) (color & 0xFF);
return setColor(r, g, b);
}
public ModelData setColor(int r, int g, int b) {
return setColor((byte) r, (byte) g, (byte) b);
}
public ModelData setColor(byte r, byte g, byte b) {
this.r = r;
this.g = g;
this.b = b;
return this;
}
public ModelData setColor(byte r, byte g, byte b, byte a) {
this.r = r;
this.g = g;
this.b = b;
this.a = a;
matrices = RenderUtil.bufferMatrices(stack.peek().getModel(), stack.peek().getNormal());
return this;
}
@Override
public void write(ByteBuffer buf) {
RenderUtil.writeMat4(buf, modelMat);
RenderUtil.writeMat3(buf, normalMat);
buf.put(new byte[] { blockLight, skyLight, r, g, b, a });
super.write(buf);
buf.asFloatBuffer().put(matrices);
buf.position(buf.position() + matrices.length * 4);
}
}

View file

@ -0,0 +1,40 @@
package com.simibubi.create.foundation.render.backend.instancing.impl;
import com.simibubi.create.foundation.render.backend.gl.attrib.CommonAttributes;
import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
public enum OrientedAttributes implements IVertexAttrib {
INSTANCE_POS("aInstancePos", CommonAttributes.VEC3),
PIVOT("aPivot", CommonAttributes.VEC3),
ROTATION("aRotation", CommonAttributes.QUATERNION),
;
private final String name;
private final IAttribSpec spec;
OrientedAttributes(String name, IAttribSpec spec) {
this.name = name;
this.spec = spec;
}
@Override
public String attribName() {
return name;
}
@Override
public IAttribSpec attribSpec() {
return spec;
}
@Override
public int getDivisor() {
return 0;
}
@Override
public int getBufferIndex() {
return 0;
}
}

View file

@ -0,0 +1,107 @@
package com.simibubi.create.foundation.render.backend.instancing.impl;
import net.minecraft.client.renderer.Quaternion;
import net.minecraft.client.renderer.Vector3f;
import net.minecraft.util.math.BlockPos;
import net.minecraft.util.math.Vec3d;
import java.nio.ByteBuffer;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
public class OrientedData extends BasicData {
private float posX;
private float posY;
private float posZ;
private float pivotX = 0.5f;
private float pivotY = 0.5f;
private float pivotZ = 0.5f;
private float qX;
private float qY;
private float qZ;
private float qW;
public OrientedData(InstancedModel<?> owner) {
super(owner);
}
public OrientedData setPosition(BlockPos pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public OrientedData setPosition(Vector3f pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public OrientedData setPosition(int x, int y, int z) {
BlockPos origin = owner.renderer.getOriginCoordinate();
return setPosition((float) (x - origin.getX()),
(float) (y - origin.getY()),
(float) (z - origin.getZ()));
}
public OrientedData setPosition(float x, float y, float z) {
this.posX = x;
this.posY = y;
this.posZ = z;
return this;
}
public OrientedData nudge(float x, float y, float z) {
this.posX += x;
this.posY += y;
this.posZ += z;
return this;
}
public OrientedData setPivot(Vector3f pos) {
return setPosition(pos.getX(), pos.getY(), pos.getZ());
}
public OrientedData setPivot(Vec3d pos) {
return setPosition((float) pos.getX(), (float) pos.getY(), (float) pos.getZ());
}
public OrientedData setPivot(float x, float y, float z) {
this.pivotX = x;
this.pivotY = y;
this.pivotZ = z;
return this;
}
public OrientedData setRotation(Quaternion q) {
return setRotation(q.getX(), q.getY(), q.getZ(), q.getW());
}
public OrientedData setRotation(float x, float y, float z, float w) {
this.qX = x;
this.qY = y;
this.qZ = z;
this.qW = w;
return this;
}
@Override
public void write(ByteBuffer buf) {
super.write(buf);
buf.asFloatBuffer().put(new float[] {
posX,
posY,
posZ,
pivotX,
pivotY,
pivotZ,
qX,
qY,
qZ,
qW
});
buf.position(buf.position() + 10 * 4);
}
}

View file

@ -0,0 +1,28 @@
package com.simibubi.create.foundation.render.backend.instancing.impl;
import net.minecraft.client.renderer.BufferBuilder;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
public class OrientedModel extends InstancedModel<OrientedData> {
public static final VertexFormat INSTANCE_FORMAT = VertexFormat.builder()
.addAttributes(BasicAttributes.class)
.addAttributes(OrientedAttributes.class)
.build();
public OrientedModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
super(renderer, buf);
}
@Override
protected OrientedData newInstance() {
return new OrientedData(this);
}
@Override
protected VertexFormat getInstanceFormat() {
return INSTANCE_FORMAT;
}
}

View file

@ -1,16 +1,18 @@
package com.simibubi.create.foundation.render.backend.gl.attrib;
package com.simibubi.create.foundation.render.backend.instancing.impl;
public enum InstanceVertexAttributes implements IVertexAttrib {
import com.simibubi.create.foundation.render.backend.gl.attrib.IAttribSpec;
import com.simibubi.create.foundation.render.backend.gl.attrib.IVertexAttrib;
import com.simibubi.create.foundation.render.backend.gl.attrib.MatrixAttributes;
public enum TransformAttributes implements IVertexAttrib {
TRANSFORM("aTransform", MatrixAttributes.MAT4),
NORMAL_MAT("aNormalMat", MatrixAttributes.MAT3),
LIGHT("aLight", CommonAttributes.LIGHT),
COLOR("aColor", CommonAttributes.RGBA),
;
private final String name;
private final IAttribSpec spec;
InstanceVertexAttributes(String name, IAttribSpec spec) {
TransformAttributes(String name, IAttribSpec spec) {
this.name = name;
this.spec = spec;
}

View file

@ -1,15 +1,17 @@
package com.simibubi.create.foundation.render.backend.instancing.impl;
import com.simibubi.create.foundation.render.backend.gl.attrib.InstanceVertexAttributes;
import com.simibubi.create.foundation.render.backend.gl.attrib.VertexFormat;
import com.simibubi.create.foundation.render.backend.instancing.InstancedModel;
import com.simibubi.create.foundation.render.backend.instancing.InstancedTileRenderer;
import net.minecraft.client.renderer.BufferBuilder;
public class BasicInstancedModel extends InstancedModel<ModelData> {
public static final VertexFormat INSTANCE_FORMAT = VertexFormat.builder().addAttributes(InstanceVertexAttributes.class).build();
public class TransformedModel extends InstancedModel<ModelData> {
public static final VertexFormat INSTANCE_FORMAT = VertexFormat.builder()
.addAttributes(BasicAttributes.class)
.addAttributes(TransformAttributes.class)
.build();
public BasicInstancedModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
public TransformedModel(InstancedTileRenderer<?> renderer, BufferBuilder buf) {
super(renderer, buf);
}

View file

@ -9,9 +9,9 @@ attribute vec3 aPos;
attribute vec3 aNormal;
attribute vec2 aTexCoords;
attribute vec3 aInstancePos;
attribute vec2 aLight;
attribute vec3 aNetworkTint;
attribute vec4 aColor;
attribute vec3 aInstancePos;
attribute float aSpeed;
attribute float aOffset;
attribute vec4 aInstanceRot;
@ -77,7 +77,7 @@ void main() {
}
#else
if (uDebug == 1) {
Color = vec4(aNetworkTint, 1.);
Color = aColor;
} else if (uDebug == 2) {
Color = vec4(norm, 1.);
} else {

View file

@ -7,10 +7,10 @@ attribute vec3 aPos;
attribute vec3 aNormal;
attribute vec2 aTexCoords;
attribute mat4 aTransform;
attribute mat3 aNormalMat;
attribute vec2 aLight;
attribute vec4 aColor;
attribute mat4 aTransform;
attribute mat3 aNormalMat;
varying vec2 TexCoords;
varying vec4 Color;
@ -38,11 +38,11 @@ varying float FragDistance;
void main() {
vec4 worldPos = aTransform * vec4(aPos, 1.);
mat3 normalMat = aNormalMat;
vec3 norm = aNormalMat * aNormal;
#ifdef CONTRAPTION
worldPos = uModel * worldPos;
normalMat *= modelToNormal(uModel);
norm = modelToNormal(uModel) * norm;
BoxCoord = (worldPos.xyz - uLightBoxMin) / uLightBoxSize;
#if defined(USE_FOG)
@ -52,7 +52,7 @@ void main() {
FragDistance = length(worldPos.xyz - uCameraPos);
#endif
vec3 norm = normalize(normalMat * aNormal);
norm = normalize(norm);
Diffuse = diffuse(norm);
TexCoords = aTexCoords;

View file

@ -0,0 +1,63 @@
#version 110
#flwinclude <"create:core/matutils.glsl">
#flwinclude <"create:core/quaternion.glsl">
#flwinclude <"create:core/diffuse.glsl">
attribute vec3 aPos;
attribute vec3 aNormal;
attribute vec2 aTexCoords;
attribute vec2 aLight;
attribute vec4 aColor;
attribute vec3 aInstancePos;
attribute vec3 aPivot;
attribute vec4 aRotation;
varying vec2 TexCoords;
varying vec4 Color;
varying float Diffuse;
varying vec2 Light;
#if defined(CONTRAPTION)
varying vec3 BoxCoord;
uniform vec3 uLightBoxSize;
uniform vec3 uLightBoxMin;
uniform mat4 uModel;
#endif
uniform float uTime;
uniform mat4 uViewProjection;
uniform int uDebug;
uniform vec3 uCameraPos;
#if defined(USE_FOG)
varying float FragDistance;
#endif
void main() {
vec4 worldPos = vec4(rotateVertexByQuat(aPos - aPivot, aRotation) + aPivot + aInstancePos, 1.);
vec3 norm = rotateVertexByQuat(aNormal, aRotation);
#ifdef CONTRAPTION
worldPos = uModel * worldPos;
norm = normalize(modelToNormal(uModel) * norm);
BoxCoord = (worldPos.xyz - uLightBoxMin) / uLightBoxSize;
#if defined(USE_FOG)
FragDistance = length(worldPos.xyz);
#endif
#elif defined(USE_FOG)
FragDistance = length(worldPos.xyz - uCameraPos);
#endif
Diffuse = diffuse(norm);
TexCoords = aTexCoords;
Light = aLight;
gl_Position = uViewProjection * worldPos;
Color = aColor;
}

View file

@ -9,9 +9,9 @@ attribute vec3 aPos;
attribute vec3 aNormal;
attribute vec2 aTexCoords;
attribute vec3 aInstancePos;
attribute vec2 aLight;
attribute vec3 aNetworkTint;
attribute vec4 aColor;
attribute vec3 aInstancePos;
attribute float aSpeed;
attribute float aOffset;
attribute vec3 aAxis;
@ -54,7 +54,7 @@ void main() {
#ifdef CONTRAPTION
worldPos = uModel * worldPos;
norm = modelToNormal(uModel) * norm;
norm = normalize(modelToNormal(uModel) * norm);
BoxCoord = (worldPos.xyz - uLightBoxMin) / uLightBoxSize;
#if defined(USE_FOG)
@ -77,7 +77,7 @@ void main() {
}
#else
if (uDebug == 1) {
Color = vec4(aNetworkTint, 1.);
Color = aColor;
} else if (uDebug == 2) {
Color = vec4(norm, 1.);
} else {