Transparent texture rendering handling.

origin
Joshua Sigona 3 years ago
parent 057ef44afb
commit 5d6c8de3b5
  1. BIN
      SigRenderer-0-jar-with-dependencies.jar
  2. 24
      cube.obj
  3. 6
      pom.xml
  4. 42
      src/sig/Block.java
  5. 24
      src/sig/Panel.java
  6. 30
      src/sig/SigRenderer.java
  7. 10
      src/sig/Texture.java
  8. 1
      src/sig/Triangle.java
  9. 22
      src/sig/utils/DrawUtils.java

@ -12,15 +12,15 @@ vt 0 1 #2
vt 1 0 #3
vt 1 1 #4
f 1/2 3/1 7/3 #South
f 1/2 7/3 5/4
f 5/2 7/1 8/3 #East
f 5/2 8/3 6/4
f 6/2 8/1 4/3 #North
f 6/2 4/3 2/4
f 2/2 4/1 3/3 #West
f 2/2 3/3 1/4
f 3/2 4/1 8/3 #Top
f 3/2 8/3 7/4
f 6/2 2/1 1/3 #Bottom
f 6/2 1/3 5/4
f 1/2 3/1 7/3 #South/0
f 1/2 7/3 5/4 #1
f 5/2 7/1 8/3 #East/2
f 5/2 8/3 6/4 #3
f 6/2 8/1 4/3 #North/4
f 6/2 4/3 2/4 #5
f 2/2 4/1 3/3 #West/6
f 2/2 3/3 1/4 #7
f 3/2 4/1 8/3 #Top/8
f 3/2 8/3 7/4 #9
f 6/2 2/1 1/3 #Bottom/10
f 6/2 1/3 5/4 #11

@ -17,12 +17,6 @@
</properties>
<dependencies>
<!-- https://mvnrepository.com/artifact/org.jogamp.jogl/jogl-all-main -->
<dependency>
<groupId>org.jogamp.jogl</groupId>
<artifactId>jogl-all-main</artifactId>
<version>2.3.2</version>
</dependency>
</dependencies>
<build>

@ -21,27 +21,57 @@ public class Block {
public void updateFaces() {
if (SigRenderer.blockGrid.containsKey(pos.x+"_"+(pos.y+1)+"_"+pos.z)) {
neighbors.UP=true;
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y+1)+"_"+pos.z).neighbors.DOWN=true;
if (block.triangles.get(Texture.TOP).tex.hasTransparency==SigRenderer.blockGrid.get(pos.x+"_"+(pos.y+1)+"_"+pos.z).block.triangles.get(Texture.BOTTOM).tex.hasTransparency) {
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y+1)+"_"+pos.z).neighbors.DOWN=true;
} else
if (block.triangles.get(Texture.TOP).tex.hasTransparency&&!SigRenderer.blockGrid.get(pos.x+"_"+(pos.y+1)+"_"+pos.z).block.triangles.get(Texture.BOTTOM).tex.hasTransparency) {
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y+1)+"_"+pos.z).neighbors.DOWN=false;
}
}
if (SigRenderer.blockGrid.containsKey(pos.x+"_"+(pos.y-1)+"_"+pos.z)) {
neighbors.DOWN=true;
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y-1)+"_"+pos.z).neighbors.UP=true;
if (block.triangles.get(Texture.BOTTOM).tex.hasTransparency==SigRenderer.blockGrid.get(pos.x+"_"+(pos.y-1)+"_"+pos.z).block.triangles.get(Texture.TOP).tex.hasTransparency) {
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y-1)+"_"+pos.z).neighbors.UP=true;
} else
if (block.triangles.get(Texture.BOTTOM).tex.hasTransparency&&!SigRenderer.blockGrid.get(pos.x+"_"+(pos.y-1)+"_"+pos.z).block.triangles.get(Texture.TOP).tex.hasTransparency) {
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y-1)+"_"+pos.z).neighbors.UP=false;
}
}
if (SigRenderer.blockGrid.containsKey((pos.x-1)+"_"+(pos.y)+"_"+pos.z)) {
neighbors.LEFT=true;
SigRenderer.blockGrid.get((pos.x-1)+"_"+(pos.y)+"_"+pos.z).neighbors.RIGHT=true;
if (block.triangles.get(Texture.WEST).tex.hasTransparency==SigRenderer.blockGrid.get((pos.x-1)+"_"+(pos.y)+"_"+pos.z).block.triangles.get(Texture.EAST).tex.hasTransparency) {
SigRenderer.blockGrid.get((pos.x-1)+"_"+(pos.y)+"_"+pos.z).neighbors.RIGHT=true;
} else
if (block.triangles.get(Texture.WEST).tex.hasTransparency&&!SigRenderer.blockGrid.get((pos.x-1)+"_"+(pos.y)+"_"+pos.z).block.triangles.get(Texture.EAST).tex.hasTransparency) {
SigRenderer.blockGrid.get((pos.x-1)+"_"+(pos.y)+"_"+pos.z).neighbors.RIGHT=false;
}
}
if (SigRenderer.blockGrid.containsKey((pos.x+1)+"_"+(pos.y)+"_"+pos.z)) {
neighbors.RIGHT=true;
SigRenderer.blockGrid.get((pos.x+1)+"_"+(pos.y)+"_"+pos.z).neighbors.LEFT=true;
if (block.triangles.get(Texture.EAST).tex.hasTransparency==SigRenderer.blockGrid.get((pos.x+1)+"_"+(pos.y)+"_"+pos.z).block.triangles.get(Texture.WEST).tex.hasTransparency) {
SigRenderer.blockGrid.get((pos.x+1)+"_"+(pos.y)+"_"+pos.z).neighbors.LEFT=true;
} else
if (block.triangles.get(Texture.EAST).tex.hasTransparency&&!SigRenderer.blockGrid.get((pos.x+1)+"_"+(pos.y)+"_"+pos.z).block.triangles.get(Texture.WEST).tex.hasTransparency) {
SigRenderer.blockGrid.get((pos.x+1)+"_"+(pos.y)+"_"+pos.z).neighbors.LEFT=false;
}
}
if (SigRenderer.blockGrid.containsKey(pos.x+"_"+(pos.y)+"_"+(pos.z+1))) {
neighbors.FORWARD=true;
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z+1)).neighbors.BACKWARD=true;
if (block.triangles.get(Texture.SOUTH).tex.hasTransparency==SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z+1)).block.triangles.get(Texture.NORTH).tex.hasTransparency) {
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z+1)).neighbors.BACKWARD=true;
} else
if (block.triangles.get(Texture.SOUTH).tex.hasTransparency&&!SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z+1)).block.triangles.get(Texture.NORTH).tex.hasTransparency) {
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z+1)).neighbors.BACKWARD=false;
}
}
if (SigRenderer.blockGrid.containsKey(pos.x+"_"+(pos.y)+"_"+(pos.z-1))) {
neighbors.BACKWARD=true;
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z-1)).neighbors.FORWARD=true;
if (block.triangles.get(Texture.NORTH).tex.hasTransparency==SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z-1)).block.triangles.get(Texture.SOUTH).tex.hasTransparency) {
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z-1)).neighbors.FORWARD=true;
} else
if (block.triangles.get(Texture.NORTH).tex.hasTransparency&&!SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z-1)).block.triangles.get(Texture.SOUTH).tex.hasTransparency) {
SigRenderer.blockGrid.get(pos.x+"_"+(pos.y)+"_"+(pos.z-1)).neighbors.FORWARD=false;
}
}
}
@Override

@ -9,6 +9,7 @@ import java.awt.Color;
import java.awt.Image;
import java.awt.image.MemoryImageSource;
import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.concurrent.ConcurrentLinkedQueue;
@ -176,7 +177,12 @@ public class Panel extends JPanel implements Runnable {
SigRenderer.tempAnswer=null;
long totalTime=0;
long startTime2=0;
ConcurrentLinkedQueue<Triangle> currentRender = (renderFirst)?accumulatedTris1:accumulatedTris2;
Collection<Triangle> currentRender = (renderFirst)?accumulatedTris1:accumulatedTris2;
List<Triangle> newTris = new ArrayList<>();
for (Triangle t:currentRender) {
prepareTriForRender(matWorld, matView, t.unmodifiedTri, newTris, true);
}
currentRender=newTris;
for (Triangle t : currentRender) {
Triangle[] clipped = new Triangle[]{new Triangle(),new Triangle()};
List<Triangle> triList = new ArrayList<>();
@ -206,7 +212,11 @@ public class Panel extends JPanel implements Runnable {
}
for (Triangle tt : triList) {
if (tt.tex!=null) {
//tt.unmodifiedTri.nextRenderTime=System.currentTimeMillis()+200;
if (renderFirst) {
tt.unmodifiedTri.nextRenderTime=System.currentTimeMillis()+200;
} else {
tt.unmodifiedTri.nextRenderTime2=System.currentTimeMillis()+200;
}
DrawUtils.TexturedTriangle(p,
(int)tt.A.x,(int)tt.A.y,tt.T.u,tt.T.v,tt.T.w,
(int)tt.B.x,(int)tt.B.y,tt.U.u,tt.U.v,tt.U.w,
@ -228,7 +238,7 @@ public class Panel extends JPanel implements Runnable {
for (int y=0;y<SigRenderer.SCREEN_HEIGHT;y++) {
Triangle t = SigRenderer.depthBuffer_tri[x+y*SigRenderer.SCREEN_WIDTH];
if (t!=null) {
t.nextRenderTime=-1;
t.nextRenderTime=t.nextRenderTime2=-1;
}
}
}
@ -239,8 +249,12 @@ public class Panel extends JPanel implements Runnable {
}
}
private void prepareTriForRender(Matrix matWorld, Matrix matView, Triangle t, ConcurrentLinkedQueue<Triangle> accumulatedTris) {
if (t.nextRenderTime<=System.currentTimeMillis()) {
private void prepareTriForRender(Matrix matWorld, Matrix matView, Triangle t, Collection<Triangle> accumulatedTris) {
prepareTriForRender(matWorld,matView,t,accumulatedTris,false);
}
private void prepareTriForRender(Matrix matWorld, Matrix matView, Triangle t, Collection<Triangle> accumulatedTris, boolean buffer) {
if (!buffer||(buffer&&t.nextRenderTime<=System.currentTimeMillis())) {
Triangle triProjected = new Triangle(),triTransformed=new Triangle(),triViewed=new Triangle();
if (t.b!=null) {

@ -2,8 +2,6 @@ package sig;
import javax.imageio.ImageIO;
import javax.swing.JFrame;
import sig.utils.OBJReader;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
@ -13,14 +11,10 @@ import java.io.File;
import java.io.IOException;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.ConcurrentLinkedQueue;
import java.awt.Toolkit;
import java.awt.BorderLayout;
@ -110,13 +104,21 @@ public class SigRenderer implements KeyListener,MouseListener,MouseMotionListene
SigRenderer(JFrame f) {
//cube = new Mesh(OBJReader.ReadOBJFile("teapot.obj",false));
Random r = new Random(438107);
for (int x=0;x<256;x++) {
for (int z=0;z<256;z++) {
for (int x=0;x<64;x++) {
for (int z=0;z<64;z++) {
addBlock(new Vector(x,0,z),BlockType.DIRT);
/*
if (Math.random()<=0.5) {
addBlock(new Vector(x,0,z),BlockType.DIRT);
addBlock(new Vector(x,y,z),BlockType.GLASS);
} else {
addBlock(new Vector(x,0,z),BlockType.SNOW_DIRT);
}
addBlock(new Vector(x,y,z),BlockType.SNOW_DIRT);
}*/
}
}
for (int x=0;x<64;x++) {
for (int y=0;y<5;y++) {
addBlock(new Vector(x,y,16),BlockType.GLASS);
}
}
@ -169,15 +171,19 @@ public class SigRenderer implements KeyListener,MouseListener,MouseMotionListene
WritableRaster r = img.getRaster();
for (TextureType tt : TextureType.values()) {
int[] pixelData = new int[tt.texWidth*BLOCK_WIDTH*tt.texHeight*BLOCK_HEIGHT];
Texture tex = new Texture(pixelData,tt.texWidth*BLOCK_WIDTH,tt.texHeight*BLOCK_HEIGHT);
int startX=tt.texX*BLOCK_WIDTH;
int startY=tt.texY*BLOCK_HEIGHT;
for (int x=0;x<tt.texWidth*BLOCK_WIDTH;x++) {
for (int y=0;y<tt.texHeight*BLOCK_HEIGHT;y++) {
int[] pixel = r.getPixel(x+startX,y+startY,new int[4]);
pixelData[x+y*tt.texWidth*BLOCK_WIDTH]=pixel[2]+(pixel[1]<<8)+(pixel[0]<<16)+(pixel[3]<<24);
if (pixel[3]<255) {
tex.hasTransparency=true;
}
}
}
blockTextures.put(tt,new Texture(pixelData,tt.texWidth*BLOCK_WIDTH,tt.texHeight*BLOCK_HEIGHT));
blockTextures.put(tt,tex);
}
JFrame f = new JFrame("SigRenderer");

@ -13,6 +13,7 @@ public class Texture{
int[] tex;
int width;
int height;
public boolean hasTransparency=false;
public Texture(File f) {
try {
@ -33,6 +34,13 @@ public class Texture{
}
}
public static final int SOUTH = 0;
public static final int EAST = 2;
public static final int NORTH = 4;
public static final int WEST = 6;
public static final int TOP = 8;
public static final int BOTTOM = 10;
public Texture(int[] tex,int width,int height) {
this.tex=tex;
this.width=width;
@ -47,7 +55,7 @@ public class Texture{
} else {
int indice = (int)(u*width-1)+(int)(v*height-1)*width;
//return tex[indice];
return (int)((tex[indice]&0xFF)*mult) + ((int)(((tex[indice]&0xFF00)>>8)*mult)<<8) + ((int)(((tex[indice]&0xFF0000)>>16)*mult)<<16);
return (int)((tex[indice]&0xFF)*mult) + ((int)(((tex[indice]&0xFF00)>>>8)*mult)<<8) + ((int)(((tex[indice]&0xFF0000)>>>16)*mult)<<16) + ((((tex[indice]&0xFF000000)>>>24))<<24);
/*Color newCol = new Color(tex.getRGB(sx,sy));
return new Color((newCol.getRed()/255f)*mult,(newCol.getGreen()/255f)*mult,(newCol.getBlue()/255f)*mult);*/
}

@ -8,6 +8,7 @@ public class Triangle {
public Block b = null;
public Texture tex = null;
public long nextRenderTime = -1l;
public long nextRenderTime2 = -1l;
public Triangle unmodifiedTri;
public Triangle() {
this(new Vector(),new Vector(),new Vector());

@ -84,9 +84,14 @@ public class DrawUtils {
if (SigRenderer.request!=null&&j==SigRenderer.request.getX()&&i==SigRenderer.request.getY()) {
SigRenderer.tempAnswer=ref.b;
}
Draw(canvas,j,i,texture.getColor(tex_u/tex_w,tex_v/tex_w,colorMult/255f));
SigRenderer.depthBuffer[i*SigRenderer.SCREEN_WIDTH+j] = tex_w;
SigRenderer.depthBuffer_tri[i*SigRenderer.SCREEN_WIDTH+j] = ref.unmodifiedTri;
int col = texture.getColor(tex_u/tex_w,tex_v/tex_w,colorMult/255f);
if (((col&0xFF000000)>>>24)!=0) {
Draw(canvas,j,i,col);
}
if (((col&0xFF000000)>>>24)==255) {
SigRenderer.depthBuffer[i*SigRenderer.SCREEN_WIDTH+j] = tex_w;
SigRenderer.depthBuffer_tri[i*SigRenderer.SCREEN_WIDTH+j] = ref.unmodifiedTri;
}
}
t+=tstep;
}
@ -140,9 +145,14 @@ public class DrawUtils {
if (SigRenderer.request!=null&&j==SigRenderer.request.getX()&&i==SigRenderer.request.getY()) {
SigRenderer.tempAnswer=ref.b;
}
Draw(canvas,j,i,texture.getColor(tex_u/tex_w,tex_v/tex_w,colorMult/255f));
SigRenderer.depthBuffer[i*SigRenderer.SCREEN_WIDTH+j] = tex_w;
SigRenderer.depthBuffer_tri[i*SigRenderer.SCREEN_WIDTH+j] = ref.unmodifiedTri;
int col = texture.getColor(tex_u/tex_w,tex_v/tex_w,colorMult/255f);
if (((col&0xFF000000)>>>24)!=0) {
Draw(canvas,j,i,col);
}
if (((col&0xFF000000)>>>24)==255) {
SigRenderer.depthBuffer[i*SigRenderer.SCREEN_WIDTH+j] = tex_w;
SigRenderer.depthBuffer_tri[i*SigRenderer.SCREEN_WIDTH+j] = ref.unmodifiedTri;
}
}
t+=tstep;
}

Loading…
Cancel
Save