Begin CTM refactor. Submaps working, lighting not so much

This commit is contained in:
tterrag1098 committed 2015-02-18 15:27:57 -05:00
1 parent ba3f7eb57a
commit 3f2e39ceb8
12 files changed
+638 -427

No files matched your search

@@ -31,16 +31,20 @@ public class CarvingUtils {
}
private static Field _chisel;
private static boolean errored = false;
private static boolean registryErrored = false;
private static final String CARVING_CLASS = "com.cricketcraft.chisel.carving.Carving";
private static Class<ICarvableHelper> _carvableHelper;
private static boolean helperErrored = false;
private static final String CARVABLE_HELPER_CLASS = "com.cricketcraft.carving.CarvableHelper";
/**
* @return The instance of the chisel carving registry from the chisel mod.
* <p>
* If chisel is not installed or some other error occurs this will return null.
*/
public static ICarvingRegistry getChiselRegistry() {
if (errored) {
if (registryErrored) {
return null;
}
@@ -51,8 +55,31 @@ public class CarvingUtils {
return (ICarvingRegistry) _chisel.get(null);
} catch (Exception e) {
e.printStackTrace();
errored = true;
registryErrored = true;
return getChiselRegistry();
}
}
/**
* @return An instance of an {@link ICarvableHelper}.
* <p>
* If chisel is not installed or some other error occurs this will return null.
*/
@SuppressWarnings("unchecked")
public static ICarvableHelper getCarvableHelperInstance() {
if (helperErrored) {
return null;
}
try {
if (_carvableHelper == null) {
_carvableHelper = (Class<ICarvableHelper>) Class.forName(CARVABLE_HELPER_CLASS);
}
return _carvableHelper.newInstance();
} catch (Exception e) {
e.printStackTrace();
helperErrored = true;
return getCarvableHelperInstance();
}
}
}
@@ -0,0 +1,6 @@
package com.cricketcraft.chisel.api.carving;
public interface ICarvableHelper {
}
@@ -8,6 +8,7 @@ import com.cricketcraft.chisel.compat.FMPIntegration;
import com.cricketcraft.chisel.config.Configurations;
import com.cricketcraft.chisel.item.ItemCarvable;
import com.cricketcraft.chisel.utils.GeneralClient;
import cpw.mods.fml.common.registry.GameRegistry;
import net.minecraft.block.Block;
import net.minecraft.block.BlockPane;
@@ -23,20 +24,288 @@ import java.util.*;
public class CarvableHelper {
public static final int NORMAL = 0;
public static final int TOPSIDE = 1;
public static final int TOPBOTSIDE = 2;
public static final int CTM3 = 3;
public static final int CTMV = 4;
public static final int CTMH = 5;
public static final int V9 = 6;
public static final int V4 = 7;
public static final int CTMX = 8;
public static final int R16 = 9;
public static final int R9 = 10;
public static final int R4 = 11;
public interface ISubmapManager {
private static final Random rand = new Random();
IIcon getIcon(int side, int meta);
IIcon getIcon(IBlockAccess world, int x, int y, int z, int side);
void registerIcons(String modName, Block block, IIconRegister register);
}
public enum TextureType implements ISubmapManager {
TOPSIDE("top", "side") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
TOPBOTSIDE("top", "bottom", "side") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
CTM3("ctm1", "ctm2", "ctm3") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
CTMV("ctmv", "top") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
CTMH("ctmh", "top") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
V9("v9") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
V4("v4") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
CTMX("", "ctm") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
R16("r16") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
R9("r9") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
R4("r4") {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
},
NORMAL {
@Override
public IIcon getIcon(int side, int meta) {
// TODO Auto-generated method stub
return null;
}
@Override
public IIcon getIcon(IBlockAccess world, int x, int y, int z, int side) {
// TODO Auto-generated method stub
return null;
}
@Override
public void registerIcons(String modName, Block block, IIconRegister register) {
// TODO Auto-generated method stub
}
};
private String[] suffixes;
private TextureType(String... suffixes) {
this.suffixes = suffixes.length == 0 ? new String[] { "" } : suffixes;
}
public static ISubmapManager getManagerFor(String path) {
for (TextureType t : values()) {
boolean matches = true;
for (String s : t.suffixes) {
String res = "".equals(s) ? path + ".png" : path + "-" + s + ".png";
if (Chisel.class.getResource(res) == null) {
matches = false;
}
}
if (matches) {
return t;
}
}
return null;
}
@Override
public abstract IIcon getIcon(int side, int meta);
@Override
public abstract IIcon getIcon(IBlockAccess world, int x, int y, int z, int side);
}
private static final Random rand = new Random();
public ArrayList<CarvableVariation> variations = new ArrayList<CarvableVariation>();
CarvableVariation[] map = new CarvableVariation[16];
@@ -75,53 +344,11 @@ public class CarvableHelper {
if (texture != null) {
variation.texture = texture;
String path = "/assets/" + Chisel.MOD_ID + "/textures/blocks/" + variation.texture;
boolean any = Chisel.class.getResource(path + ".png") != null;
boolean ctm3 = Chisel.class.getResource(path + "-ctm1.png") != null && Chisel.class.getResource(path + "-ctm2.png") != null && Chisel.class.getResource(path + "-ctm3.png") != null;
boolean ctmv = Chisel.class.getResource(path + "-ctmv.png") != null;
boolean ctmh = Chisel.class.getResource(path + "-ctmh.png") != null;
boolean side = Chisel.class.getResource(path + "-side.png") != null;
boolean top = Chisel.class.getResource(path + "-top.png") != null;
boolean bot = Chisel.class.getResource(path + "-bottom.png") != null;
boolean v9 = Chisel.class.getResource(path + "-v9.png") != null;
boolean v4 = Chisel.class.getResource(path + "-v4.png") != null;
boolean ctmx = Chisel.class.getResource(path + "-ctm.png") != null;
boolean r16 = Chisel.class.getResource(path + "-r16.png") != null;
boolean r9 = Chisel.class.getResource(path + "-r9.png") != null;
boolean r4 = Chisel.class.getResource(path + "-r4.png") != null;
if (ctm3) {
variation.kind = 3;
} else if (ctmh && top) {
variation.kind = 5;
} else if (ctmv && top) {
variation.kind = CTMV;
} else if (bot && top && side) {
variation.kind = 2;
} else if (top && side) {
variation.kind = 1;
} else if (v9) {
variation.kind = V9;
} else if (v4) {
variation.kind = V4;
} else if (any && ctmx && !Configurations.disableCTM) {
variation.kind = CTMX;
} else if (r16) {
variation.kind = R16;
} else if (r9) {
variation.kind = R9;
} else if (r4) {
variation.kind = R4;
} else if (any) {
variation.kind = 0;
} else {
throw new RuntimeException("No valid textures found for chisel block variation '" + description + "' (" + variation.texture + ")");
}
variation.type = (TextureType) TextureType.getManagerFor(path);
} else {
variation.block = block;
variation.kind = 2;
variation.type = TextureType.TOPBOTSIDE;
variation.blockMeta = blockMeta;
}
@@ -148,45 +375,45 @@ public class CarvableHelper {
if (variation == null)
return GeneralClient.getMissingIcon();
switch (variation.kind) {
case NORMAL:
return variation.icon;
case TOPSIDE:
if (side == 0 || side == 1)
return variation.iconTop;
else
return variation.icon;
case TOPBOTSIDE:
if (side == 1)
return variation.iconTop;
else if (side == 0)
return variation.iconBot;
else
return variation.icon;
case CTM3:
return variation.ctm.seams[0].icons[0];
case CTMV:
if (side < 2)
return variation.iconTop;
else
return variation.seamsCtmVert.icons[0];
case CTMH:
if (side < 2)
return variation.iconTop;
else
return variation.seamsCtmVert.icons[0];
case V9:
return variation.variations9.icons[4];
case V4:
return variation.variations9.icons[0];
case CTMX:
return variation.icon;
case R16:
return variation.variations9.icons[5];
case R9:
return variation.variations9.icons[4];
case R4:
return variation.variations9.icons[0];
switch (variation.type) {
case NORMAL:
return variation.icon;
case TOPSIDE:
if (side == 0 || side == 1)
return variation.iconTop;
else
return variation.icon;
case TOPBOTSIDE:
if (side == 1)
return variation.iconTop;
else if (side == 0)
return variation.iconBot;
else
return variation.icon;
case CTM3:
return variation.ctm.seams[0].icons[0];
case CTMV:
if (side < 2)
return variation.iconTop;
else
return variation.seamsCtmVert.icons[0];
case CTMH:
if (side < 2)
return variation.iconTop;
else
return variation.seamsCtmVert.icons[0];
case V9:
return variation.variations9.icons[4];
case V4:
return variation.variations9.icons[0];
case CTMX:
return variation.icon;
case R16:
return variation.variations9.icons[5];
case R9:
return variation.variations9.icons[4];
case R4:
return variation.variations9.icons[0];
}
return GeneralClient.getMissingIcon();
@@ -202,7 +429,7 @@ public class CarvableHelper {
if (variation == null)
return GeneralClient.getMissingIcon();
switch (variation.kind) {
switch (variation.type) {
case NORMAL:
case TOPSIDE:
case TOPBOTSIDE:
@@ -255,61 +482,59 @@ public class CarvableHelper {
else if (n)
return variation.seamsCtmVert.icons[reverse ? 3 : 2];
return variation.seamsCtmVert.icons[0];
case V9:
case V4:
int variationSize = (variation.kind == V9) ? 3 : 2;
case V9:
case V4:
int variationSize = (variation.type == TextureType.V9) ? 3 : 2;
int xModulus = x % variationSize;
int zModulus = z % variationSize;
//This ensures that blocks placed near 0,0 or it's axis' do not misbehave
int textureX = (xModulus < 0) ? (xModulus + variationSize) : xModulus;
int textureZ = (zModulus < 0) ? (zModulus + variationSize) : zModulus;
//Always invert the y index
int textureY = (variationSize - (y % variationSize) - 1);
int xModulus = x % variationSize;
int zModulus = z % variationSize;
// This ensures that blocks placed near 0,0 or it's axis' do not misbehave
int textureX = (xModulus < 0) ? (xModulus + variationSize) : xModulus;
int textureZ = (zModulus < 0) ? (zModulus + variationSize) : zModulus;
// Always invert the y index
int textureY = (variationSize - (y % variationSize) - 1);
if (side == 2 || side == 5) {
//For WEST, SOUTH reverse the indexes for both X and Z
textureX = (variationSize - textureX - 1);
textureZ = (variationSize - textureZ - 1);
} else if (side == 0) {
//For DOWN, reverse the indexes for only Z
textureZ = (variationSize - textureZ - 1);
}
if (side == 2 || side == 5) {
// For WEST, SOUTH reverse the indexes for both X and Z
textureX = (variationSize - textureX - 1);
textureZ = (variationSize - textureZ - 1);
} else if (side == 0) {
// For DOWN, reverse the indexes for only Z
textureZ = (variationSize - textureZ - 1);
}
int index;
if (side == 0 || side == 1) {
// DOWN || UP
index = textureX + textureZ * variationSize;
} else if (side == 2 || side == 3) {
// NORTH || SOUTH
index = textureX + textureY * variationSize;
} else {
// WEST || EAST
index = textureZ + textureY * variationSize;
}
int index;
if (side == 0 || side == 1) {
// DOWN || UP
index = textureX + textureZ * variationSize;
} else if (side == 2 || side == 3) {
// NORTH || SOUTH
index = textureX + textureY * variationSize;
} else {
// WEST || EAST
index = textureZ + textureY * variationSize;
}
return variation.variations9.icons[index];
return variation.variations9.icons[index];
case CTMX:
return variation.icon;
case R16:
case R9:
case R4:
case R16:
case R9:
case R4:
int indexRan = x + y + z;
if ((side==2)||(side==5)) {
indexRan = -indexRan;
}
while (indexRan < 0) {
indexRan = indexRan+10000;
}
int indexRan = x + y + z;
if ((side == 2) || (side == 5)) {
indexRan = -indexRan;
}
while (indexRan < 0) {
indexRan = indexRan + 10000;
}
//rand.setSeed(indexRan); // Broken
// rand.setSeed(indexRan); // Broken
return variation.variations9.icons[ /*rand*/ indexRan % ((variation.kind == R9) ? 9 : 4)];
return variation.variations9.icons[ /* rand */indexRan % ((variation.type == TextureType.R9) ? 9 : 4)];
}
return GeneralClient.getMissingIcon();
}
@@ -360,7 +585,7 @@ public class CarvableHelper {
variation.iconBot = ((BlockPane) variation.block).getBlockTextureFromSide(0);
} else {
switch (variation.kind) {
switch (variation.type) {
case NORMAL:
variation.icon = variation.block.getIcon(2, variation.blockMeta);
break;
@@ -376,7 +601,7 @@ public class CarvableHelper {
}
}
} else {
switch (variation.kind) {
switch (variation.type) {
case NORMAL:
variation.icon = register.registerIcon(modName + ":" + variation.texture);
break;
@@ -415,15 +640,15 @@ public class CarvableHelper {
variation.submap = new TextureSubmap(register.registerIcon(modName + ":" + variation.texture + "-ctm"), 4, 4);
variation.submapSmall = new TextureSubmap(variation.icon, 2, 2);
break;
case R16:
variation.variations9 = new TextureSubmap(register.registerIcon(modName + ":" + variation.texture + "-r16"), 4, 4);
break;
case R9:
variation.variations9 = new TextureSubmap(register.registerIcon(modName + ":" + variation.texture + "-r9"), 3, 3);
break;
case R4:
variation.variations9 = new TextureSubmap(register.registerIcon(modName + ":" + variation.texture + "-r4"), 2, 2);
break;
case R16:
variation.variations9 = new TextureSubmap(register.registerIcon(modName + ":" + variation.texture + "-r16"), 4, 4);
break;
case R9:
variation.variations9 = new TextureSubmap(register.registerIcon(modName + ":" + variation.texture + "-r9"), 3, 3);
break;
case R4:
variation.variations9 = new TextureSubmap(register.registerIcon(modName + ":" + variation.texture + "-r4"), 2, 2);
break;
}
}
}
@@ -436,12 +661,7 @@ public class CarvableHelper {
}
public void setChiselBlockName(String name) {
blockName = name;
}
public static Set<Block> getChiselBlockSet() {
HashSet<Block> tools = new HashSet<Block>();
return tools;
blockName = name;
}
public void registerOre(String ore) {
@@ -4,6 +4,7 @@ import net.minecraft.block.Block;
import net.minecraft.client.resources.I18n;
import net.minecraft.util.IIcon;
import com.cricketcraft.chisel.carving.CarvableHelper.TextureType;
import com.cricketcraft.chisel.client.render.TextureSubmap;
public class CarvableVariation {
@@ -11,7 +12,7 @@ public class CarvableVariation {
public String blockName;
public String descriptionUnloc;
public int metadata;
public int kind;
public TextureType type = TextureType.NORMAL;
public Block block;
public int blockMeta;
@@ -19,8 +20,8 @@ public class CarvableVariation {
public String texture;
public IIcon icon;
public IIcon iconTop;
public IIcon iconBot;
public IIcon iconTop;
public CarvableVariationCTM ctm;
public TextureSubmap seamsCtmVert;
@@ -0,0 +1,6 @@
package com.cricketcraft.chisel.carving;
public interface ITextureVariation {
}
@@ -9,6 +9,7 @@ import org.lwjgl.opengl.GL11;
import com.cricketcraft.chisel.Chisel;
import com.cricketcraft.chisel.api.ICarvable;
import com.cricketcraft.chisel.carving.CarvableHelper;
import com.cricketcraft.chisel.carving.CarvableHelper.TextureType;
import com.cricketcraft.chisel.carving.CarvableVariation;
import com.cricketcraft.chisel.utils.Drawing;
@@ -45,8 +46,8 @@ public class BlockAdvancedMarbleRenderer implements ISimpleBlockRenderingHandler
return true;
}
switch (var == null ? 0 : var.kind) {
case CarvableHelper.CTMX:
switch (var == null ? TextureType.NORMAL : var.type) {
case CTMX:
rendererCTM.blockAccess = world;
rendererCTM.renderMaxX = 1.0;
rendererCTM.renderMaxY = 1.0;
@@ -58,7 +59,7 @@ public class BlockAdvancedMarbleRenderer implements ISimpleBlockRenderingHandler
rendererCTM.rendererOld = rendererOld;
return rendererCTM.renderStandardBlock(block, x, y, z);
case CarvableHelper.CTMV:
case CTMV:
rendererColumn.blockAccess = world;
rendererColumn.renderMaxX = 1.0;
rendererColumn.renderMaxY = 1.0;
@@ -10,6 +10,7 @@ import com.cricketcraft.chisel.Chisel;
import com.cricketcraft.chisel.api.ICarvable;
import com.cricketcraft.chisel.carving.CarvableHelper;
import com.cricketcraft.chisel.carving.CarvableVariation;
import com.cricketcraft.chisel.carving.CarvableHelper.TextureType;
import com.cricketcraft.chisel.utils.Drawing;
import cpw.mods.fml.client.registry.ISimpleBlockRenderingHandler;
@@ -40,8 +41,7 @@ public class BlockCTMNoLightRenderer implements ISimpleBlockRenderingHandler {
CarvableVariation var = ((ICarvable) block).getVariation(world, x, y, z, meta);
switch (var == null ? 0 : var.kind) {
case CarvableHelper.CTMX:
if (var != null && var.type == TextureType.CTMX) {
rendererCTMNoLight.blockAccess = world;
rendererCTMNoLight.renderMaxX = 1.0;
rendererCTMNoLight.renderMaxY = 1.0;
@@ -53,7 +53,7 @@ public class BlockCTMNoLightRenderer implements ISimpleBlockRenderingHandler {
rendererCTMNoLight.rendererOld = rendererOld;
return rendererCTMNoLight.renderStandardBlock(block, x, y, z);
default:
} else {
return rendererOld.renderStandardBlock(block, x, y, z);
}
}
@@ -8,6 +8,7 @@ import org.lwjgl.opengl.GL11;
import com.cricketcraft.chisel.block.BlockCarvablePillar;
import com.cricketcraft.chisel.carving.CarvableHelper;
import com.cricketcraft.chisel.carving.CarvableHelper.TextureType;
import com.cricketcraft.chisel.utils.Drawing;
import cpw.mods.fml.client.registry.ISimpleBlockRenderingHandler;
@@ -54,7 +55,7 @@ public class BlockMarblePillarRenderer implements ISimpleBlockRenderingHandler {
metadata = block.carverHelper.variations.size() - 1;
}
else {
if (block.carverHelper.variations.get(metadata).kind != CarvableHelper.CTMV) {
if (block.carverHelper.variations.get(metadata).type != TextureType.CTMV) {
block.sides[0] = block.carverHelper.getIcon(0, metadata);
block.sides[1] = block.carverHelper.getIcon(1, metadata);
block.sides[2] = block.carverHelper.getIcon(2, metadata);
@@ -5,8 +5,96 @@ import net.minecraft.client.renderer.RenderBlocks;
import net.minecraft.client.renderer.Tessellator;
import net.minecraft.util.IIcon;
import org.apache.commons.lang3.tuple.Triple;
import static com.cricketcraft.chisel.client.render.RenderBlocksCTM.Vert.*;
import static com.cricketcraft.chisel.client.render.RenderBlocksCTM.SubSide.*;
public class RenderBlocksCTM extends RenderBlocks {
/**
* An enum for all possible 26 sub-side vertices.
* <p>
* The naming scheme is as follows:
* <ul>
* <li>ZERO and ONE are special cases, they are the absolute min and absolute max of the block.</li>
* <li>X, Y, Z, or any combination means that the axes listed in the name are at 1.</li>
* <li>X, Y, Z, or any combination followed by HALF means that those axes are at 0.5.</li>
* <li>X, Y, Z, or any combination after a HALF means those axes are at 1.</li>
* </ul>
*/
enum Vert {
ZERO(0, 0, 0),
ONE(1, 1, 1),
X(1, 0, 0),
Y(0, 1, 0),
Z(0, 0, 1),
XY(1, 1, 0),
YZ(0, 1, 1),
XZ(1, 0, 1),
X_HALF(0.5, 0, 0),
Y_HALF(0, 0.5, 0),
Z_HALF(0, 0, 0.5),
XY_HALF(0.5, 0.5, 0),
YZ_HALF(0, 0.5, 0.5),
XZ_HALF(0.5, 0, 0.5),
X_HALF_Y(0.5, 1, 0),
X_HALF_Z(0.5, 0, 1),
Y_HALF_X(1, 0.5, 0),
Y_HALF_Z(0, 0.5, 1),
Z_HALF_X(1, 0, 0.5),
Z_HALF_Y(0, 1, 0.5),
X_HALF_YZ(0.5, 1, 1),
Y_HALF_XZ(1, 0.5, 1),
Z_HALF_XY(1, 1, 0.5),
XY_HALF_Z(0.5, 0.5, 1),
YZ_HALF_X(1, 0.5, 0.5),
XZ_HALF_Y(0.5, 1, 0.5);
private double x, y, z;
private Vert(double x, double y, double z) {
this.x = x;
this.y = y;
this.z = z;
}
void render(RenderBlocksCTM inst, int cacheID) {
if (inst.enableAO) {
// inst.tessellator.setColorOpaque_F(inst.redCache[cacheID], inst.greenCache[cacheID], inst.blueCache[cacheID]);
inst.tessellator.setBrightness(inst.lightingCache[cacheID]);
}
inst.tessellator.addVertexWithUV(x, y, z, inst.uCache[cacheID], inst.vCache[cacheID]);
}
}
/**
* Each side is divided into 4 sub-sides. LB(left bottom), RB(right bottom), LT(right top), and RT(right top).
* <p>
* Each sub-side contains 4 {@link Vert} objects representing its position on the block.
*/
enum SubSide {
XNEG_LB(ZERO, Z_HALF, YZ_HALF, Y_HALF), XNEG_RB(Z_HALF, Z, Y_HALF_Z, YZ_HALF), XNEG_LT(Y_HALF, YZ_HALF, Z_HALF_Y, Y), XNEG_RT(YZ_HALF, Y_HALF_Z, YZ, Z_HALF_Y);
private Vert xmin, xmax, ymin, ymax;
SubSide(Vert xmin, Vert ymin, Vert ymax, Vert xmax) {
this.xmin = xmin;
this.ymin = ymin;
this.ymax = ymax;
this.xmax = xmax;
}
void render(RenderBlocksCTM inst) {
xmin.render(inst, 0);
ymin.render(inst, 1);
ymax.render(inst, 2);
xmax.render(inst, 3);
}
}
// globals added to save the JVM some trouble. No need to constantly create
// and destroy ints if we don't have to
int blockLightBitChannel = 0;
@@ -17,20 +105,15 @@ public class RenderBlocksCTM extends RenderBlocks {
RenderBlocksCTM() {
super();
resetVertices();
}
Tessellator tessellator;
double[] X = new double[26];
double[] Y = new double[26];
double[] Z = new double[26];
double[] U = new double[26];
double[] V = new double[26];
int[] L = new int[26];
float[] R = new float[26];
float[] G = new float[26];
float[] B = new float[26];
double[] uCache = new double[4];
double[] vCache = new double[4];
int[] lightingCache = new int[4];
float[] redCache = new float[4];
float[] greenCache = new float[4];
float[] blueCache = new float[4];
TextureSubmap submap;
TextureSubmap submapSmall;
RenderBlocks rendererOld;
@@ -55,66 +138,60 @@ public class RenderBlocksCTM extends RenderBlocks {
return res;
}
void setupSides(int a, int b, int c, int d, int xa, int xb, int xc, int xd, int e) {
L[a] = brightnessBottomLeft;
L[b] = brightnessBottomRight;
L[c] = brightnessTopRight;
L[d] = brightnessTopLeft;
void updateLighting() {
lightingCache[0] = brightnessBottomLeft;
lightingCache[1] = brightnessBottomRight;
lightingCache[2] = brightnessTopRight;
lightingCache[3] = brightnessTopLeft;
// Updated to safely average light and color channels
L[e] = averageBrightnessChannels(brightnessBottomLeft, brightnessTopLeft, brightnessTopRight, brightnessBottomRight);
L[xa] = averageBrightnessChannels(L[a], L[b]);
L[xb] = averageBrightnessChannels(L[b], L[c]);
L[xc] = averageBrightnessChannels(L[c], L[d]);
L[xd] = averageBrightnessChannels(L[d], L[a]);
R[a] = colorRedBottomLeft;
R[b] = colorRedBottomRight;
R[c] = colorRedTopRight;
R[d] = colorRedTopLeft;
R[e] = (colorRedBottomLeft + colorRedTopLeft + colorRedTopRight + colorRedBottomRight) / 4;
R[xa] = (R[a] + R[b]) / 2;
R[xb] = (R[b] + R[c]) / 2;
R[xc] = (R[c] + R[d]) / 2;
R[xd] = (R[d] + R[a]) / 2;
G[a] = colorGreenBottomLeft;
G[b] = colorGreenBottomRight;
G[c] = colorGreenTopRight;
G[d] = colorGreenTopLeft;
G[e] = (colorGreenBottomLeft + colorGreenTopLeft + colorGreenTopRight + colorGreenBottomRight) / 4;
G[xa] = (G[a] + G[b]) / 2;
G[xb] = (G[b] + G[c]) / 2;
G[xc] = (G[c] + G[d]) / 2;
G[xd] = (G[d] + G[a]) / 2;
B[a] = colorBlueBottomLeft;
B[b] = colorBlueBottomRight;
B[c] = colorBlueTopRight;
B[d] = colorBlueTopLeft;
B[e] = (colorBlueBottomLeft + colorBlueTopLeft + colorBlueTopRight + colorBlueBottomRight) / 4;
B[xa] = (B[a] + B[b]) / 2;
B[xb] = (B[b] + B[c]) / 2;
B[xc] = (B[c] + B[d]) / 2;
B[xd] = (B[d] + B[a]) / 2;
// // Updated to safely average light and color channels
// L[e] = averageBrightnessChannels(brightnessBottomLeft, brightnessTopLeft, brightnessTopRight, brightnessBottomRight);
// L[xa] = averageBrightnessChannels(L[a], L[b]);
// L[xb] = averageBrightnessChannels(L[b], L[c]);
// L[xc] = averageBrightnessChannels(L[c], L[d]);
// L[xd] = averageBrightnessChannels(L[d], L[a]);
//
// Rcache[a] = colorRedBottomLeft;
// Rcache[b] = colorRedBottomRight;
// Rcache[c] = colorRedTopRight;
// Rcache[d] = colorRedTopLeft;
// Rcache[e] = (colorRedBottomLeft + colorRedTopLeft + colorRedTopRight + colorRedBottomRight) / 4;
// Rcache[xa] = (Rcache[a] + Rcache[b]) / 2;
// Rcache[xb] = (Rcache[b] + Rcache[c]) / 2;
// Rcache[xc] = (Rcache[c] + Rcache[d]) / 2;
// Rcache[xd] = (Rcache[d] + Rcache[a]) / 2;
//
// Gcache[a] = colorGreenBottomLeft;
// Gcache[b] = colorGreenBottomRight;
// Gcache[c] = colorGreenTopRight;
// Gcache[d] = colorGreenTopLeft;
// Gcache[e] = (colorGreenBottomLeft + colorGreenTopLeft + colorGreenTopRight + colorGreenBottomRight) / 4;
// Gcache[xa] = (Gcache[a] + Gcache[b]) / 2;
// Gcache[xb] = (Gcache[b] + Gcache[c]) / 2;
// Gcache[xc] = (Gcache[c] + Gcache[d]) / 2;
// Gcache[xd] = (Gcache[d] + Gcache[a]) / 2;
//
// Bcache[a] = colorBlueBottomLeft;
// Bcache[b] = colorBlueBottomRight;
// Bcache[c] = colorBlueTopRight;
// Bcache[d] = colorBlueTopLeft;
// Bcache[e] = (colorBlueBottomLeft + colorBlueTopLeft + colorBlueTopRight + colorBlueBottomRight) / 4;
// Bcache[xa] = (Bcache[a] + Bcache[b]) / 2;
// Bcache[xb] = (Bcache[b] + Bcache[c]) / 2;
// Bcache[xc] = (Bcache[c] + Bcache[d]) / 2;
// Bcache[xd] = (Bcache[d] + Bcache[a]) / 2;
}
/*
* Takes in a variable number of packed light-integers, and computes the
* average value of each 4 bit channel
/**
* Takes in a variable number of packed light-integers, and computes the average value of each 4 bit channel
*
* For vanilla, these look like: (S = skylight and L = block light) 0000
* 0000 SSSS 0000 0000 0000 LLLL 0000 With the Colored Light Core installed,
* these look like: (B = Blue, G = Green, R = Red) 0000 0000 SSSS BBBB GGGG
* RRRR LLLL 0000
* For vanilla, these look like: (S = skylight and L = block light) 0000 0000 SSSS 0000 0000 0000 LLLL 0000 With the Colored Light Core installed, these look like: (B = Blue, G = Green, R = Red)
* 0000 0000 SSSS BBBB GGGG RRRR LLLL 0000
*
* This method will average all of the values appropriately for the more
* complex case, by separating each color channel into a running total, then
* it will combine the final results together using integer division and a
* lot of bit-cramming.
* This method will average all of the values appropriately for the more complex case, by separating each color channel into a running total, then it will combine the final results together using
* integer division and a lot of bit-cramming.
*
* While slightly more complex, the runtime should not be drastically
* effected, and the averaging routine remains compatible with vanilla.
* While slightly more complex, the runtime should not be drastically effected, and the averaging routine remains compatible with vanilla.
*
* Authored: CptSpaceToaster - 12/19/2014
*/
@@ -137,37 +214,25 @@ public class RenderBlocksCTM extends RenderBlocks {
| ((blueBitChannel / lightVals.length) & 0xF0000) | ((sunlightBitChannel / lightVals.length) & 0xF00000);
}
void side(int a, int b, int c, int d, int iconIndex, boolean flip) {
void side(SubSide side, int iconIndex, boolean flip) {
IIcon icon = iconIndex >= 16 ? submapSmall.icons[iconIndex - 16] : submap.icons[iconIndex];
double u0 = icon.getMaxU();
double u1 = icon.getMinU();
double v0 = icon.getMaxV();
double v1 = icon.getMinV();
double umax = icon.getMaxU();
double umin = icon.getMinU();
double vmax = icon.getMaxV();
double vmin = icon.getMinV();
U[a] = flip ? u1 : u1;
U[b] = flip ? u0 : u1;
U[c] = flip ? u0 : u0;
U[d] = flip ? u1 : u0;
uCache[0] = flip ? umax : umin;
uCache[1] = umax;
uCache[2] = flip ? umin : umax;
uCache[3] = umin;
V[a] = flip ? v1 : v1;
V[b] = flip ? v1 : v0;
V[c] = flip ? v0 : v0;
V[d] = flip ? v0 : v1;
vCache[0] = flip ? vmin : vmax;
vCache[1] = vmax;
vCache[2] = flip ? vmax : vmin;
vCache[3] = vmin;
vert(a);
vert(b);
vert(c);
vert(d);
}
void vert(int index) {
if (enableAO) {
tessellator.setColorOpaque_F(R[index], G[index], B[index]);
tessellator.setBrightness(L[index]);
}
tessellator.addVertexWithUV(X[index], Y[index], Z[index], U[index], V[index]);
side.render(this);
}
@Override
@@ -182,11 +247,11 @@ public class RenderBlocksCTM extends RenderBlocks {
} else {
int tex[] = CTM.getSubmapIndices(blockAccess, bx, by, bz, 4);
setupSides(1, 0, 4, 5, 14, 19, 17, 23, 9);
side(1, 14, 9, 23, tex[0], false);
side(23, 9, 17, 5, tex[1], false);
side(9, 19, 4, 17, tex[3], false);
side(14, 0, 19, 9, tex[2], false);
updateLighting();
side(XNEG_LB, tex[2], false);
side(XNEG_RB, tex[3], false);
side(XNEG_RT, tex[1], false);
side(XNEG_LT, tex[0], false);
}
}
@@ -202,11 +267,11 @@ public class RenderBlocksCTM extends RenderBlocks {
} else {
int tex[] = CTM.getSubmapIndices(blockAccess, bx, by, bz, 5);
setupSides(3, 2, 6, 7, 15, 25, 16, 21, 11);
side(11, 21, 3, 15, tex[3], false);
side(16, 7, 21, 11, tex[2], false);
side(25, 11, 15, 2, tex[1], false);
side(6, 16, 11, 25, tex[0], false);
updateLighting();
// side(11, 21, 3, 15, tex[3], false);
// side(16, 7, 21, 11, tex[2], false);
// side(25, 11, 15, 2, tex[1], false);
// side(6, 16, 11, 25, tex[0], false);
}
}
@@ -222,11 +287,11 @@ public class RenderBlocksCTM extends RenderBlocks {
} else {
int tex[] = CTM.getSubmapIndices(blockAccess, bx, by, bz, 2);
setupSides(2, 3, 0, 1, 15, 18, 14, 22, 8);
side(2, 15, 8, 22, tex[0], false);
side(15, 3, 18, 8, tex[2], false);
side(8, 18, 0, 14, tex[3], false);
side(22, 8, 14, 1, tex[1], false);
updateLighting();
// side(2, 15, 8, 22, tex[0], false);
// side(15, 3, 18, 8, tex[2], false);
// side(8, 18, 0, 14, tex[3], false);
// side(22, 8, 14, 1, tex[1], false);
}
}
@@ -242,11 +307,11 @@ public class RenderBlocksCTM extends RenderBlocks {
} else {
int tex[] = CTM.getSubmapIndices(blockAccess, bx, by, bz, 3);
setupSides(4, 7, 6, 5, 20, 16, 24, 17, 10);
side(17, 4, 20, 10, tex[2], false);
side(5, 17, 10, 24, tex[0], false);
side(24, 10, 16, 6, tex[1], false);
side(10, 20, 7, 16, tex[3], false);
updateLighting();
// side(17, 4, 20, 10, tex[2], false);
// side(5, 17, 10, 24, tex[0], false);
// side(24, 10, 16, 6, tex[1], false);
// side(10, 20, 7, 16, tex[3], false);
}
}
@@ -262,11 +327,11 @@ public class RenderBlocksCTM extends RenderBlocks {
} else {
int tex[] = CTM.getSubmapIndices(blockAccess, bx, by, bz, 0);
setupSides(0, 3, 7, 4, 18, 21, 20, 19, 13);
side(13, 21, 7, 20, tex[3], true);
side(19, 13, 20, 4, tex[2], true);
side(0, 18, 13, 19, tex[0], true);
side(18, 3, 21, 13, tex[1], true);
updateLighting();
// side(13, 21, 7, 20, tex[3], true);
// side(19, 13, 20, 4, tex[2], true);
// side(0, 18, 13, 19, tex[0], true);
// side(18, 3, 21, 13, tex[1], true);
}
}
@@ -282,117 +347,12 @@ public class RenderBlocksCTM extends RenderBlocks {
} else {
int tex[] = CTM.getSubmapIndices(blockAccess, bx, by, bz, 1);
setupSides(2, 1, 5, 6, 22, 23, 24, 25, 12);
side(12, 24, 6, 25, tex[3], false);
side(22, 12, 25, 2, tex[1], false);
side(1, 23, 12, 22, tex[0], false);
side(23, 5, 24, 12, tex[2], false);
updateLighting();
// side(12, 24, 6, 25, tex[3], false);
// side(22, 12, 25, 2, tex[1], false);
// side(1, 23, 12, 22, tex[0], false);
// side(23, 5, 24, 12, tex[2], false);
}
}
void resetVertices() {
X[0] = 0;
Z[0] = 0;
Y[0] = 0;
X[1] = 0;
Z[1] = 0;
Y[1] = 1;
X[2] = 1;
Z[2] = 0;
Y[2] = 1;
X[3] = 1;
Z[3] = 0;
Y[3] = 0;
X[4] = 0;
Z[4] = 1;
Y[4] = 0;
X[5] = 0;
Z[5] = 1;
Y[5] = 1;
X[6] = 1;
Z[6] = 1;
Y[6] = 1;
X[7] = 1;
Z[7] = 1;
Y[7] = 0;
X[8] = 0.5;
Z[8] = 0;
Y[8] = 0.5;
X[9] = 0;
Z[9] = 0.5;
Y[9] = 0.5;
X[10] = 0.5;
Z[10] = 1;
Y[10] = 0.5;
X[11] = 1;
Z[11] = 0.5;
Y[11] = 0.5;
X[12] = 0.5;
Z[12] = 0.5;
Y[12] = 1;
X[13] = 0.5;
Z[13] = 0.5;
Y[13] = 0;
X[14] = 0;
Z[14] = 0;
Y[14] = 0.5;
X[15] = 1;
Z[15] = 0;
Y[15] = 0.5;
X[16] = 1;
Z[16] = 1;
Y[16] = 0.5;
X[17] = 0;
Z[17] = 1;
Y[17] = 0.5;
X[18] = 0.5;
Z[18] = 0;
Y[18] = 0;
X[19] = 0;
Z[19] = 0.5;
Y[19] = 0;
X[20] = 0.5;
Z[20] = 1;
Y[20] = 0;
X[21] = 1;
Z[21] = 0.5;
Y[21] = 0;
X[22] = 0.5;
Z[22] = 0;
Y[22] = 1;
X[23] = 0;
Z[23] = 0.5;
Y[23] = 1;
X[24] = 0.5;
Z[24] = 1;
Y[24] = 1;
X[25] = 1;
Z[25] = 0.5;
Y[25] = 1;
}
}
@@ -9,15 +9,6 @@ public class RenderBlocksCTMCarpet extends RenderBlocksCTM {
super();
}
@Override
void resetVertices() {
super.resetVertices();
for (int i = 0; i < Y.length; i++) {
Y[i] /= 16;
}
}
@Override
public void renderFaceXNeg(Block block, double x, double y, double z, IIcon icon) {
rendererOld.renderFaceXNeg(block, 0, 0, 0, submapSmall.icon);
@@ -29,5 +29,4 @@ public class TextureSubmap {
}
}
}
}
@@ -6,59 +6,59 @@ import cpw.mods.fml.relauncher.SideOnly;
public class TextureVirtual implements IIcon {
int ox, oy;
float u0, u1, v0, v1;
String name;
IIcon icon;
private int width, height;
private float umin, umax, vmin, vmax;
private String name;
private IIcon parentIcon;
TextureVirtual(IIcon parent, int w, int h, int x, int y) {
icon = parent;
parentIcon = parent;
u0 = icon.getInterpolatedU(16.0 * (x) / w);
u1 = icon.getInterpolatedU(16.0 * (x + 1) / w);
v0 = icon.getInterpolatedV(16.0 * (y) / h);
v1 = icon.getInterpolatedV(16.0 * (y + 1) / h);
umin = parentIcon.getInterpolatedU(16.0 * (x) / w);
umax = parentIcon.getInterpolatedU(16.0 * (x + 1) / w);
vmin = parentIcon.getInterpolatedV(16.0 * (y) / h);
vmax = parentIcon.getInterpolatedV(16.0 * (y + 1) / h);
name = icon.getIconName() + "|" + x + "." + y;
name = parentIcon.getIconName() + "|" + x + "." + y;
ox = icon.getIconWidth();
oy = icon.getIconHeight();
width = parentIcon.getIconWidth();
height = parentIcon.getIconHeight();
}
@Override
@SideOnly(Side.CLIENT)
public float getMinU() {
return u0;
return umin;
}
@Override
@SideOnly(Side.CLIENT)
public float getMaxU() {
return u1;
return umax;
}
@Override
@SideOnly(Side.CLIENT)
public float getInterpolatedU(double d0) {
return (float) (u0 + (u1 - u0) * d0 / 16.0);
return (float) (umin + (umax - umin) * d0 / 16.0);
}
@Override
@SideOnly(Side.CLIENT)
public float getMinV() {
return v0;
return vmin;
}
@Override
@SideOnly(Side.CLIENT)
public float getMaxV() {
return v1;
return vmax;
}
@Override
@SideOnly(Side.CLIENT)
public float getInterpolatedV(double d0) {
return (float) (v0 + (v1 - v0) * d0 / 16.0);
return (float) (vmin + (vmax - vmin) * d0 / 16.0);
}
@Override
@@ -70,13 +70,12 @@ public class TextureVirtual implements IIcon {
@Override
@SideOnly(Side.CLIENT)
public int getIconWidth() {
return ox;
return width;
}
@Override
@SideOnly(Side.CLIENT)
public int getIconHeight() {
return oy;
return height;
}
}