Move 3D raytracing engine to new project.
This commit is contained in:
commit
b7e570dd5f
2
.gitignore
vendored
Normal file
2
.gitignore
vendored
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
/bin/
|
||||||
|
/target/
|
9
.gitpod.yml
Normal file
9
.gitpod.yml
Normal file
@ -0,0 +1,9 @@
|
|||||||
|
---
|
||||||
|
# List the start up tasks. Learn more https://www.gitpod.io/docs/config-start-tasks/
|
||||||
|
tasks:
|
||||||
|
- init: sh coauthors.sh
|
||||||
|
vscode:
|
||||||
|
extensions:
|
||||||
|
- redhat.java
|
||||||
|
- mhutchie.git-graph
|
||||||
|
- vscjava.vscode-maven
|
3
.vscode/settings.json
vendored
Normal file
3
.vscode/settings.json
vendored
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
{
|
||||||
|
"java.configuration.updateBuildConfiguration": "automatic"
|
||||||
|
}
|
41
coauthors.sh
Executable file
41
coauthors.sh
Executable file
@ -0,0 +1,41 @@
|
|||||||
|
npm i -g git-mob
|
||||||
|
cat <<-EOF > ~/.git-coauthors
|
||||||
|
{
|
||||||
|
"coauthors": {
|
||||||
|
"sig": {
|
||||||
|
"name": "sigonasr2",
|
||||||
|
"email": "sigonasr2@gmail.com"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
EOF
|
||||||
|
git mob sig
|
||||||
|
cat <<-EOF > .git/hooks/prepare-commit-msg
|
||||||
|
#!/usr/bin/env node
|
||||||
|
let exec = require('child_process').exec,
|
||||||
|
fs = require('fs');
|
||||||
|
const commitMessage = process.argv[2];
|
||||||
|
// expect .git/COMMIT_EDITMSG
|
||||||
|
if(/COMMIT_EDITMSG/g.test(commitMessage)){
|
||||||
|
let contents = "";
|
||||||
|
exec("git mob-print",
|
||||||
|
function (err, stdout) {
|
||||||
|
if(err) {
|
||||||
|
process.exit(0);
|
||||||
|
}
|
||||||
|
// opens .git/COMMIT_EDITMSG
|
||||||
|
contents = fs.readFileSync(commitMessage);
|
||||||
|
if(contents.indexOf(stdout.trim()) !== -1) {
|
||||||
|
process.exit(0);
|
||||||
|
}
|
||||||
|
const commentPos = contents.indexOf('# ');
|
||||||
|
const gitMessage = contents.slice(0, commentPos);
|
||||||
|
const gitComments = contents.slice(commentPos)
|
||||||
|
fs.writeFileSync(commitMessage, gitMessage + stdout + gitComments);
|
||||||
|
process.exit(0);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
EOF
|
||||||
|
chmod +x .git/hooks/prepare-commit-msg
|
||||||
|
cd /workspace/SigRenderer
|
||||||
|
echo "Environment is setup!"
|
96
pom.xml
Normal file
96
pom.xml
Normal file
@ -0,0 +1,96 @@
|
|||||||
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
|
|
||||||
|
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
|
||||||
|
xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
|
||||||
|
<modelVersion>4.0.0</modelVersion>
|
||||||
|
|
||||||
|
<groupId>SigRenderer</groupId>
|
||||||
|
<artifactId>SigRenderer</artifactId>
|
||||||
|
<version>0</version>
|
||||||
|
|
||||||
|
<name>SigRenderer</name>
|
||||||
|
|
||||||
|
<properties>
|
||||||
|
<project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
|
||||||
|
<maven.compiler.source>1.8</maven.compiler.source>
|
||||||
|
<maven.compiler.target>1.8</maven.compiler.target>
|
||||||
|
</properties>
|
||||||
|
|
||||||
|
<dependencies>
|
||||||
|
<!-- https://mvnrepository.com/artifact/javax.vecmath/vecmath -->
|
||||||
|
<dependency>
|
||||||
|
<groupId>javax.vecmath</groupId>
|
||||||
|
<artifactId>vecmath</artifactId>
|
||||||
|
<version>1.5.2</version>
|
||||||
|
</dependency>
|
||||||
|
</dependencies>
|
||||||
|
|
||||||
|
<build>
|
||||||
|
<sourceDirectory>src</sourceDirectory>
|
||||||
|
<pluginManagement><!-- lock down plugins versions to avoid using Maven defaults (may be moved to parent pom) -->
|
||||||
|
<plugins>
|
||||||
|
<!-- clean lifecycle, see https://maven.apache.org/ref/current/maven-core/lifecycles.html#clean_Lifecycle -->
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-clean-plugin</artifactId>
|
||||||
|
<version>3.1.0</version>
|
||||||
|
</plugin>
|
||||||
|
<!-- default lifecycle, jar packaging: see https://maven.apache.org/ref/current/maven-core/default-bindings.html#Plugin_bindings_for_jar_packaging -->
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-resources-plugin</artifactId>
|
||||||
|
<version>3.0.2</version>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-compiler-plugin</artifactId>
|
||||||
|
<version>3.8.0</version>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-surefire-plugin</artifactId>
|
||||||
|
<version>2.22.1</version>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-jar-plugin</artifactId>
|
||||||
|
<version>3.0.2</version>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-install-plugin</artifactId>
|
||||||
|
<version>2.5.2</version>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-deploy-plugin</artifactId>
|
||||||
|
<version>2.8.2</version>
|
||||||
|
</plugin>
|
||||||
|
<!-- site lifecycle, see https://maven.apache.org/ref/current/maven-core/lifecycles.html#site_Lifecycle -->
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-site-plugin</artifactId>
|
||||||
|
<version>3.7.1</version>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-project-info-reports-plugin</artifactId>
|
||||||
|
<version>3.0.0</version>
|
||||||
|
</plugin>
|
||||||
|
<plugin>
|
||||||
|
<artifactId>maven-assembly-plugin</artifactId>
|
||||||
|
<configuration>
|
||||||
|
<archive>
|
||||||
|
<manifest>
|
||||||
|
<mainClass>sig.SigRenderer</mainClass>
|
||||||
|
</manifest>
|
||||||
|
</archive>
|
||||||
|
<descriptorRefs>
|
||||||
|
<descriptorRef>jar-with-dependencies</descriptorRef>
|
||||||
|
</descriptorRefs>
|
||||||
|
</configuration>
|
||||||
|
<executions>
|
||||||
|
<execution>
|
||||||
|
<id>make-assembly</id> <!-- this is used for inheritance merges -->
|
||||||
|
<phase>package</phase> <!-- bind to the packaging phase -->
|
||||||
|
<goals>
|
||||||
|
<goal>single</goal>
|
||||||
|
</goals>
|
||||||
|
</execution>
|
||||||
|
</executions>
|
||||||
|
</plugin>
|
||||||
|
</plugins>
|
||||||
|
</pluginManagement>
|
||||||
|
</build>
|
||||||
|
</project>
|
2
run
Executable file
2
run
Executable file
@ -0,0 +1,2 @@
|
|||||||
|
mvn compile assembly:single
|
||||||
|
java -jar target/SigRenderer-0-jar-with-dependencies.jar
|
126
src/sig/Panel.java
Normal file
126
src/sig/Panel.java
Normal file
@ -0,0 +1,126 @@
|
|||||||
|
package sig;
|
||||||
|
import javax.swing.JPanel;
|
||||||
|
import javax.vecmath.Vector3f;
|
||||||
|
|
||||||
|
import java.awt.Graphics;
|
||||||
|
import java.awt.Color;
|
||||||
|
|
||||||
|
import java.awt.Image;
|
||||||
|
import java.awt.image.MemoryImageSource;
|
||||||
|
import java.awt.image.ColorModel;
|
||||||
|
import java.awt.GraphicsEnvironment;
|
||||||
|
import java.awt.GraphicsConfiguration;
|
||||||
|
import java.awt.Toolkit;
|
||||||
|
|
||||||
|
public class Panel extends JPanel implements Runnable {
|
||||||
|
long startTime = System.nanoTime();
|
||||||
|
long endTime = System.nanoTime();
|
||||||
|
public int pixel[];
|
||||||
|
public int width=SigRenderer.SCREEN_WIDTH;
|
||||||
|
public int height=SigRenderer.SCREEN_HEIGHT;
|
||||||
|
private Image imageBuffer;
|
||||||
|
private MemoryImageSource mImageProducer;
|
||||||
|
private ColorModel cm;
|
||||||
|
private Thread thread;
|
||||||
|
|
||||||
|
public Panel() {
|
||||||
|
super(true);
|
||||||
|
thread = new Thread(this, "MyPanel Thread");
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get Best Color model available for current screen.
|
||||||
|
* @return color model
|
||||||
|
*/
|
||||||
|
protected static ColorModel getCompatibleColorModel(){
|
||||||
|
GraphicsConfiguration gfx_config = GraphicsEnvironment.
|
||||||
|
getLocalGraphicsEnvironment().getDefaultScreenDevice().
|
||||||
|
getDefaultConfiguration();
|
||||||
|
return gfx_config.getColorModel();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Call it after been visible and after resizes.
|
||||||
|
*/
|
||||||
|
public void init(){
|
||||||
|
cm = getCompatibleColorModel();
|
||||||
|
width = getWidth();
|
||||||
|
height = getHeight();
|
||||||
|
int screenSize = width * height;
|
||||||
|
if(pixel == null || pixel.length < screenSize){
|
||||||
|
pixel = new int[screenSize];
|
||||||
|
}
|
||||||
|
mImageProducer = new MemoryImageSource(width, height, cm, pixel,0, width);
|
||||||
|
mImageProducer.setAnimated(true);
|
||||||
|
mImageProducer.setFullBufferUpdates(true);
|
||||||
|
imageBuffer = Toolkit.getDefaultToolkit().createImage(mImageProducer);
|
||||||
|
if(thread.isInterrupted() || !thread.isAlive()){
|
||||||
|
thread.start();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/**
|
||||||
|
* Do your draws in here !!
|
||||||
|
* pixel is your canvas!
|
||||||
|
*/
|
||||||
|
public /* abstract */ void render(){
|
||||||
|
int[] p = pixel; // this avoid crash when resizing
|
||||||
|
|
||||||
|
final int h=SigRenderer.SCREEN_HEIGHT;
|
||||||
|
if(p.length != width * height) return;
|
||||||
|
for (int x=0;x<SigRenderer.SCREEN_WIDTH/SigRenderer.RESOLUTION;x++) {
|
||||||
|
for (int y=0;y<SigRenderer.SCREEN_HEIGHT/SigRenderer.RESOLUTION;y++) {
|
||||||
|
Vector3f dir = new Vector3f((-SigRenderer.SCREEN_WIDTH/2f+x*SigRenderer.RESOLUTION),(-SigRenderer.SCREEN_HEIGHT/2f+y*SigRenderer.RESOLUTION),SigRenderer.SCREEN_WIDTH);
|
||||||
|
if (SigRenderer.tri.rayTriangleIntersect(SigRenderer.origin, dir)) {
|
||||||
|
p[ (int)(SigRenderer.SCREEN_WIDTH-x*SigRenderer.RESOLUTION) + (int)(SigRenderer.SCREEN_HEIGHT-y*SigRenderer.RESOLUTION) * width] = Color.WHITE.getRGB();
|
||||||
|
}
|
||||||
|
if (SigRenderer.tri2.rayTriangleIntersect(SigRenderer.origin, dir)) {
|
||||||
|
p[ (int)(SigRenderer.SCREEN_WIDTH-x*SigRenderer.RESOLUTION) + (int)(SigRenderer.SCREEN_HEIGHT-y*SigRenderer.RESOLUTION) * width] = Color.BLUE.getRGB();
|
||||||
|
}
|
||||||
|
if (SigRenderer.tri3.rayTriangleIntersect(SigRenderer.origin, dir)) {
|
||||||
|
p[ (int)(SigRenderer.SCREEN_WIDTH-x*SigRenderer.RESOLUTION) + (int)(SigRenderer.SCREEN_HEIGHT-y*SigRenderer.RESOLUTION) * width] = Color.RED.getRGB();
|
||||||
|
}
|
||||||
|
if (SigRenderer.tri4.rayTriangleIntersect(SigRenderer.origin, dir)) {
|
||||||
|
p[ (int)(SigRenderer.SCREEN_WIDTH-x*SigRenderer.RESOLUTION) + (int)(SigRenderer.SCREEN_HEIGHT-y*SigRenderer.RESOLUTION) * width] = Color.GREEN.getRGB();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
i += 1;
|
||||||
|
j += 1;
|
||||||
|
endTime=System.nanoTime();
|
||||||
|
SigRenderer.DRAWLOOPTIME=(endTime-startTime)/1000000f;
|
||||||
|
}
|
||||||
|
private int i=1,j=256;
|
||||||
|
|
||||||
|
public void repaint() {
|
||||||
|
super.repaint();
|
||||||
|
startTime = System.nanoTime();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void paintComponent(Graphics g) {
|
||||||
|
super.paintComponent(g);
|
||||||
|
// perform draws on pixels
|
||||||
|
render();
|
||||||
|
// ask ImageProducer to update image
|
||||||
|
mImageProducer.newPixels();
|
||||||
|
// draw it on panel
|
||||||
|
g.drawImage(this.imageBuffer, 0, 0, this);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Overrides ImageObserver.imageUpdate.
|
||||||
|
* Always return true, assuming that imageBuffer is ready to go when called
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public boolean imageUpdate(Image image, int a, int b, int c, int d, int e) {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public void run() {
|
||||||
|
while (true) {
|
||||||
|
// request a JPanel re-drawing
|
||||||
|
repaint();
|
||||||
|
try {Thread.sleep(5);} catch (InterruptedException e) {}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
13
src/sig/Pixel.java
Normal file
13
src/sig/Pixel.java
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
package sig;
|
||||||
|
|
||||||
|
import java.awt.Color;
|
||||||
|
|
||||||
|
public class Pixel {
|
||||||
|
int x,y;
|
||||||
|
Color col;
|
||||||
|
Pixel(int x,int y,Color col) {
|
||||||
|
this.x=x;
|
||||||
|
this.y=y;
|
||||||
|
this.col=col;
|
||||||
|
}
|
||||||
|
}
|
142
src/sig/SigRenderer.java
Normal file
142
src/sig/SigRenderer.java
Normal file
@ -0,0 +1,142 @@
|
|||||||
|
package sig;
|
||||||
|
import javax.swing.JFrame;
|
||||||
|
import javax.vecmath.Point2d;
|
||||||
|
import javax.vecmath.Tuple3d;
|
||||||
|
import javax.vecmath.Vector3f;
|
||||||
|
import java.awt.event.MouseEvent;
|
||||||
|
import java.awt.event.MouseListener;
|
||||||
|
import java.awt.event.MouseMotionListener;
|
||||||
|
import java.awt.event.KeyEvent;
|
||||||
|
import java.awt.event.KeyListener;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.List;
|
||||||
|
import java.awt.Toolkit;
|
||||||
|
import java.awt.Color;
|
||||||
|
|
||||||
|
public class SigRenderer implements KeyListener,MouseListener,MouseMotionListener{
|
||||||
|
public static Triangle tri,tri2,tri3,tri4,tri5,tri6;
|
||||||
|
public final static int SCREEN_WIDTH=1280;
|
||||||
|
public final static int SCREEN_HEIGHT=720;
|
||||||
|
public final static long TIMEPERTICK = 16666667l;
|
||||||
|
public static float DRAWTIME=0;
|
||||||
|
public static float DRAWLOOPTIME=0;
|
||||||
|
public static final float RESOLUTION=1;
|
||||||
|
|
||||||
|
public static Vector3f origin = new Vector3f(0,0,10);
|
||||||
|
public static float rot = (float)Math.PI/4; //In radians.
|
||||||
|
|
||||||
|
public static List<Pixel> pixels;
|
||||||
|
|
||||||
|
public void runGameLoop() {
|
||||||
|
rot+=Math.PI/480d;
|
||||||
|
}
|
||||||
|
|
||||||
|
SigRenderer(JFrame f) {
|
||||||
|
|
||||||
|
tri = new Triangle(new Vector3f(-1,-1,0),new Vector3f(0,-1,0),new Vector3f(-1,0,0));
|
||||||
|
tri2 = new Triangle(new Vector3f(-1,0,0),new Vector3f(0,-1,0),new Vector3f(0,0,0));
|
||||||
|
tri3 = new Triangle(new Vector3f(0,0,0),new Vector3f(0,-1,0),new Vector3f(0,-1,-1));
|
||||||
|
tri4 = new Triangle(new Vector3f(0,-1,-1),new Vector3f(0,0,-1),new Vector3f(0,-1,0));
|
||||||
|
/*tri5 = new Triangle(new Vector3f(0,-1,0),new Vector3f(0,-1,-1),new Vector3f(0,0,0));
|
||||||
|
tri6 = new Triangle(new Vector3f(0,0,0),new Vector3f(0,-1,-1),new Vector3f(0,0,-1));*/
|
||||||
|
|
||||||
|
Panel p = new Panel();
|
||||||
|
|
||||||
|
new Thread() {
|
||||||
|
public void run(){
|
||||||
|
while (true) {
|
||||||
|
long startTime = System.nanoTime();
|
||||||
|
runGameLoop();
|
||||||
|
p.repaint();
|
||||||
|
Toolkit.getDefaultToolkit().sync();
|
||||||
|
long endTime = System.nanoTime();
|
||||||
|
long diff = endTime-startTime;
|
||||||
|
try {
|
||||||
|
long sleepTime = TIMEPERTICK - diff;
|
||||||
|
long millis = (sleepTime)/1000000;
|
||||||
|
int nanos = (int)(sleepTime-(((sleepTime)/1000000)*1000000));
|
||||||
|
//System.out.println("FRAME DRAWING: Sleeping for ("+millis+"ms,"+nanos+"ns) - "+(diff)+"ns");
|
||||||
|
DRAWTIME = (float)diff/1000000;
|
||||||
|
f.setTitle("Game Loop: "+DRAWTIME+"ms, Draw Loop: "+DRAWLOOPTIME+"ms");
|
||||||
|
if (sleepTime>0) {
|
||||||
|
Thread.sleep(millis,nanos);
|
||||||
|
}
|
||||||
|
} catch (InterruptedException e) {
|
||||||
|
e.printStackTrace();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}.start();
|
||||||
|
|
||||||
|
f.getContentPane().addMouseListener(this);
|
||||||
|
f.getContentPane().addMouseMotionListener(this);
|
||||||
|
f.addKeyListener(this);
|
||||||
|
f.add(p);
|
||||||
|
f.setSize(SCREEN_WIDTH,SCREEN_HEIGHT);
|
||||||
|
f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
|
||||||
|
f.setVisible(true);
|
||||||
|
p.init();
|
||||||
|
}
|
||||||
|
public static void main(String[] args) {
|
||||||
|
JFrame f = new JFrame("SigRenderer");
|
||||||
|
new SigRenderer(f);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void mouseClicked(MouseEvent e) {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void mousePressed(MouseEvent e) {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void mouseReleased(MouseEvent e) {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void mouseEntered(MouseEvent e) {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void mouseExited(MouseEvent e) {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void mouseDragged(MouseEvent e) {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void mouseMoved(MouseEvent e) {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void keyTyped(KeyEvent e) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void keyPressed(KeyEvent e) {
|
||||||
|
switch (e.getKeyCode()) {
|
||||||
|
case KeyEvent.VK_UP:{
|
||||||
|
origin.add(new Vector3f(0,0,-1));
|
||||||
|
}break;
|
||||||
|
case KeyEvent.VK_RIGHT:{
|
||||||
|
origin.add(new Vector3f(1,0,0));
|
||||||
|
}break;
|
||||||
|
case KeyEvent.VK_LEFT:{
|
||||||
|
origin.add(new Vector3f(-1,0,0));
|
||||||
|
}break;
|
||||||
|
case KeyEvent.VK_DOWN:{
|
||||||
|
origin.add(new Vector3f(0,0,1));
|
||||||
|
}break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void keyReleased(KeyEvent e) {
|
||||||
|
// TODO Auto-generated method stub
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
70
src/sig/Triangle.java
Normal file
70
src/sig/Triangle.java
Normal file
@ -0,0 +1,70 @@
|
|||||||
|
package sig;
|
||||||
|
import javax.vecmath.Vector3f;
|
||||||
|
|
||||||
|
public class Triangle {
|
||||||
|
Vector3f A,B,C;
|
||||||
|
Triangle(Vector3f A,Vector3f B,Vector3f C) {
|
||||||
|
this.A=A;
|
||||||
|
this.B=B;
|
||||||
|
this.C=C;
|
||||||
|
}
|
||||||
|
@Override
|
||||||
|
public String toString() {
|
||||||
|
return "Triangle [A=" + A + ", B=" + B + ", C=" + C + "]";
|
||||||
|
}
|
||||||
|
|
||||||
|
public Vector3f getNormal() {
|
||||||
|
Vector3f AB = (Vector3f)A.clone();
|
||||||
|
AB.sub(B);
|
||||||
|
Vector3f BC = (Vector3f)B.clone();
|
||||||
|
BC.sub(C);
|
||||||
|
Vector3f crossP = new Vector3f();
|
||||||
|
crossP.cross(AB,BC);
|
||||||
|
//crossP.normalize();
|
||||||
|
return crossP;
|
||||||
|
}
|
||||||
|
public float distanceFromOrigin() {
|
||||||
|
return getNormal().dot(A);
|
||||||
|
}
|
||||||
|
|
||||||
|
public boolean rayTriangleIntersect(Vector3f origin,Vector3f dir) {
|
||||||
|
Vector3f N = getNormal();
|
||||||
|
|
||||||
|
float NrayDir = N.dot(dir);
|
||||||
|
if (NrayDir<=0.001) { //Very small, so it's parallel.
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
float d = distanceFromOrigin();
|
||||||
|
|
||||||
|
float T=(getNormal().dot(origin)+d)/(NrayDir);
|
||||||
|
|
||||||
|
if (T<0) {return false;} //Triangle is behind the ray.
|
||||||
|
|
||||||
|
//System.out.println("Not behind.");
|
||||||
|
|
||||||
|
Vector3f scaleMult = (Vector3f)dir.clone();
|
||||||
|
scaleMult.scale(T);
|
||||||
|
Vector3f P = (Vector3f)origin.clone();
|
||||||
|
P.add(scaleMult);
|
||||||
|
|
||||||
|
Vector3f C;
|
||||||
|
|
||||||
|
Vector3f edge0 = (Vector3f)B.clone(); edge0.sub(A);
|
||||||
|
Vector3f vp0 = (Vector3f)P.clone(); vp0.sub(A);
|
||||||
|
C = new Vector3f(); C.cross(edge0,vp0);
|
||||||
|
if (N.dot(C)<0) {return false;}
|
||||||
|
|
||||||
|
Vector3f edge1 = (Vector3f)this.C.clone(); edge1.sub(B);
|
||||||
|
Vector3f vp1 = (Vector3f)P.clone(); vp1.sub(B);
|
||||||
|
C = new Vector3f(); C.cross(edge1,vp1);
|
||||||
|
if (N.dot(C)<0) {return false;}
|
||||||
|
|
||||||
|
Vector3f edge2 = (Vector3f)A.clone(); edge2.sub(this.C);
|
||||||
|
Vector3f vp2 = (Vector3f)P.clone(); vp2.sub(this.C);
|
||||||
|
C = new Vector3f(); C.cross(edge2,vp2);
|
||||||
|
if (N.dot(C)<0) {return false;}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
Loading…
x
Reference in New Issue
Block a user