Newer
Older
import com.jogamp.opengl.GL;
import com.jogamp.opengl.GL2;
import com.jogamp.opengl.glu.GLU;
import cz.fidentis.analyst.mesh.core.MeshFacet;
import java.util.Collections;
import java.util.List;
import javax.vecmath.Point3d;
import javax.vecmath.Vector3d;
/**
* Handles {@link DrawableMesh}s - objects to be drawn, and (re-)renders them on demand.
*
* @author Natalia Bebjakova
* @author Radek Oslejsek
public static final Color BRIGHT_BACKGROUND = new Color(0.9f, 0.9f, 0.9f);
public static final Color DARK_BACKGROUND = new Color(0.25f, 0.25f, 0.25f);
private final GLU glu = new GLU();
private GL2 gl;
private boolean brightBackground = false;
/**
* Constructor.
*
* @param gl OpenGL context of drawable objects
* @throws IllegalArgumentException if the {@code gl} is null
*/
if (gl == null) {
throw new IllegalArgumentException("gl is null");
}
this.gl = gl;
gl.setSwapInterval(1);
gl.glEnable(GL2.GL_LIGHTING);
gl.glEnable(GL2.GL_LIGHT0);
gl.glEnable(GL2.GL_DEPTH_TEST);
gl.glClearColor(0,0,0,0); // background for GLCanvas
gl.glClear(GL2.GL_COLOR_BUFFER_BIT);
gl.glShadeModel(GL2.GL_SMOOTH); // use smooth shading
gl.glDepthFunc(GL2.GL_LESS);
gl.glDepthRange(0.0, 1.0);
gl.glEnable(GL.GL_DEPTH_TEST);
gl.glEnable(GL2.GL_NORMALIZE);
gl.glDisable(GL2.GL_CULL_FACE);
gl.glEnable(GL2.GL_BLEND); // enable transparency
gl.glBlendFunc(GL2.GL_SRC_ALPHA, GL2.GL_ONE_MINUS_SRC_ALPHA);
}
/**
* Sets the scene background to bright.
*/
public void setBrightBackground() {
this.brightBackground = true;
}
/**
* Sets the scene background to dark.
*/
public void setDarkBackground() {
this.brightBackground = false;
}
/**
* Sets the view-port.
*
* @param x X corner
* @param y Y corner
* @param width Width
* @param height Height
*/
public void setViewport(int x, int y, int width, int height) {
//OutputWindow out = OutputWindow.measureTime();
if (height == 0) {
height = 1; // to avoid division by 0 in aspect ratio below
}
gl.glViewport(x, y, width, height); // size of drawing area
float h = (float) height / (float) width;
gl.glMatrixMode(GL2.GL_PROJECTION);
gl.glLoadIdentity();
glu.gluPerspective(50, width / (float) height, 5.0f, 1500.0f);
gl.glMatrixMode(GL2.GL_MODELVIEW);
gl.glLoadIdentity();
gl.glTranslatef(0.0f, 0.0f, -40.0f);
//out.printDuration("GL viewport set to " + width + "x" + height);
}
/**
* Renders drawable objects.
*/
public void renderScene(Camera camera, Collection<Drawable> drawables) {
//OutputWindow out = OutputWindow.measureTime();
// light backface
gl.glLightfv(GL2.GL_LIGHT1, GL2.GL_POSITION, new float[] {0f, 0f, -1f, 0f}, 0);
gl.glLightfv(GL2.GL_LIGHT1, GL2.GL_DIFFUSE, Color.white.getComponents(null), 0);
List<Drawable> objects = new ArrayList<>(drawables);
objects.sort(new Drawable.TransparencyComparator());
for (Drawable obj : objects) {
if (obj.isShown()) {
obj.render(gl);
}
}
//out.printDuration("Scene rendering");
/**
* Sets model to proper position
*
* @param camera Camera
*/
private void setPosition(Camera camera) {
Vector3d currentPosition = camera.getPosition();
Vector3d center = camera.getCenter();
Vector3d upDirection = camera.getUpDirection();
glu.gluLookAt(currentPosition.x, currentPosition.y, currentPosition.z,
center.x, center.y, center.z,
upDirection.x, upDirection.y, upDirection.z);
}
/**
* Sets up transparent objects to render later in order to render properly
* Now works only for two meshes
*
* @param drawables List of meshes
*/
private List<DrawableFace> getOrderedFaces(Collection<Drawable> drawables) {
List<DrawableFace> faces = new ArrayList<>();
for (Drawable obj: drawables) {
if (obj instanceof DrawableFace) {
faces.add((DrawableFace) obj);
}
}
if (faces.get(0).getTransparency() != 1) {
Collections.reverse(faces);
/**
* Clears the scene and prepares it for the re-drawing.
*/
protected void clearScene() { // join with the renderScene() ???
if (brightBackground) {
gl.glClearColor(
BRIGHT_BACKGROUND.getRed() / 255f,
BRIGHT_BACKGROUND.getGreen() / 255f,
BRIGHT_BACKGROUND.getBlue() / 255f,
0.0f);
gl.glClearColor(
DARK_BACKGROUND.getRed() / 255f,
DARK_BACKGROUND.getGreen() / 255f,
DARK_BACKGROUND.getBlue() / 255f,
0.0f);
}
gl.glClear(GL.GL_COLOR_BUFFER_BIT | GL.GL_DEPTH_BUFFER_BIT);
gl.glLoadIdentity();
}
/**
* Loops through the facet and render all the vertices as they are stored in corner table
*
* @param facet facet of model
*/
protected void renderFacet(MeshFacet facet) {
gl.glBegin(GL2.GL_TRIANGLES); //vertices are rendered as triangles
// get the normal and tex coords indicies for face i
for (int v = 0; v < facet.getCornerTable().getSize(); v++) {
// render the normals
Vector3d norm = facet.getVertices().get(facet.getCornerTable().getRow(v).getVertexIndex()).getNormal();
if(norm != null) {
gl.glNormal3d(norm.x, norm.y, norm.z);
}
// render the vertices
Point3d vert = facet.getVertices().get(facet.getCornerTable().getRow(v).getVertexIndex()).getPosition();
gl.glVertex3d(vert.x, vert.y, vert.z);
}
gl.glEnd();
}
}