diff options
Diffstat (limited to 'src/jogl/classes')
6 files changed, 104 insertions, 36 deletions
diff --git a/src/jogl/classes/com/jogamp/opengl/math/FloatUtil.java b/src/jogl/classes/com/jogamp/opengl/math/FloatUtil.java index a04055430..7f630f9d5 100644 --- a/src/jogl/classes/com/jogamp/opengl/math/FloatUtil.java +++ b/src/jogl/classes/com/jogamp/opengl/math/FloatUtil.java @@ -35,6 +35,7 @@ import jogamp.opengl.Debug; import com.jogamp.common.os.Platform; import com.jogamp.opengl.math.geom.AABBox; +import com.jogamp.opengl.math.geom.Frustum; /** * Basic Float math utility functions. @@ -491,18 +492,18 @@ public final class FloatUtil { * @param zNear * @param zFar * @return given matrix for chaining - * @throws GLException with GL_INVALID_VALUE if zNear is <= 0, or zFar < 0, - * or if left == right, or bottom == top, or zNear == zFar. + * @throws GLException if {@code zNear <= 0} or {@code zFar <= zNear} + * or {@code left == right}, or {@code bottom == top}. */ public static float[] makeFrustum(final float[] m, final int m_offset, final boolean initM, final float left, final float right, final float bottom, final float top, final float zNear, final float zFar) throws GLException { - if( zNear <= 0.0f || zFar < 0.0f ) { - throw new GLException("GL_INVALID_VALUE: zNear and zFar must be positive, and zNear>0"); + if( zNear <= 0.0f || zFar <= zNear ) { + throw new GLException("Requirements zNear > 0 and zFar > zNear, but zNear "+zNear+", zFar "+zFar); } - if( left == right || top == bottom || zNear == zFar ) { - throw new GLException("GL_INVALID_VALUE: top,bottom and left,right and zNear,zFar must not be equal"); + if( left == right || top == bottom) { + throw new GLException("GL_INVALID_VALUE: top,bottom and left,right must not be equal"); } if( initM ) { // m[m_offset+0+4*0] = 1f; @@ -565,14 +566,15 @@ public final class FloatUtil { * @param zNear * @param zFar * @return given matrix for chaining - * @throws GLException with GL_INVALID_VALUE if zNear is <= 0, or zFar < 0, or if zNear == zFar. + * @throws GLException if {@code zNear <= 0} or {@code zFar <= zNear} + * @see #makeFrustum(float[], int, boolean, float, float, float, float, float, float) */ public static float[] makePerspective(final float[] m, final int m_off, final boolean initM, final float fovy_rad, final float aspect, final float zNear, final float zFar) throws GLException { final float top = tan(fovy_rad/2f) * zNear; // use tangent of half-fov ! - final float bottom = -1.0f * top; - final float left = aspect * bottom; - final float right = aspect * top; + final float bottom = -1.0f * top; // -1f * fovhvTan.top * zNear + final float left = aspect * bottom; // aspect * -1f * fovhvTan.top * zNear + final float right = aspect * top; // aspect * fovhvTan.top * zNear return makeFrustum(m, m_off, initM, left, right, bottom, top, zNear, zFar); } @@ -591,7 +593,9 @@ public final class FloatUtil { * @param zNear * @param zFar * @return given matrix for chaining - * @throws GLException with GL_INVALID_VALUE if zNear is <= 0, or zFar < 0, or if zNear == zFar. + * @throws GLException if {@code zNear <= 0} or {@code zFar <= zNear} + * @see #makeFrustum(float[], int, boolean, float, float, float, float, float, float) + * @see Frustum#updateByFovDesc(float[], int, boolean, Frustum.FovDesc) */ public static float[] makePerspective(final float[] m, final int m_offset, final boolean initM, final FovHVHalves fovhv, final float zNear, final float zFar) throws GLException { diff --git a/src/jogl/classes/com/jogamp/opengl/math/FovHVHalves.java b/src/jogl/classes/com/jogamp/opengl/math/FovHVHalves.java index 26ed57009..5d7907f2f 100644 --- a/src/jogl/classes/com/jogamp/opengl/math/FovHVHalves.java +++ b/src/jogl/classes/com/jogamp/opengl/math/FovHVHalves.java @@ -35,13 +35,13 @@ package com.jogamp.opengl.math; * </p> */ public final class FovHVHalves { - /** Half horizontal FOV from center to left. */ + /** Half horizontal FOV from center to left, either in {@link #inTangents} or radians. */ public final float left; - /** Half horizontal FOV from center to right. */ + /** Half horizontal FOV from center to right, either in {@link #inTangents} or radians. */ public final float right; - /** Half vertical FOV from center to top. */ + /** Half vertical FOV from center to top, either in {@link #inTangents} or radians. */ public final float top; - /** Half vertical FOV from center to bottom. */ + /** Half vertical FOV from center to bottom, either in {@link #inTangents} or radians. */ public final float bottom; /** If true, values are in tangent, otherwise radians.*/ public final boolean inTangents; @@ -67,7 +67,7 @@ public final class FovHVHalves { } /** - * Returns a symmetrical centered {@link FovHVHalves} instance in tangents, using: + * Returns a symmetrical centered {@link FovHVHalves} instance in {@link #inTangents}, using: * <pre> halfHorizFovTan = tan( horizontalFov / 2f ); halfVertFovTan = tan( verticalFov / 2f ); @@ -82,7 +82,7 @@ public final class FovHVHalves { } /** - * Returns a symmetrical centered {@link FovHVHalves} instance in tangents, using: + * Returns a symmetrical centered {@link FovHVHalves} instance in {@link #inTangents}, using: * <pre> top = bottom = tan( verticalFov / 2f ); left = right = aspect * top; @@ -99,7 +99,7 @@ public final class FovHVHalves { } /** - * Returns a custom symmetry {@link FovHVHalves} instance in tangents, using: + * Returns a custom symmetry {@link FovHVHalves} instance {@link #inTangents}, using: * <pre> left = tan( horizontalFov * horizCenterFromLeft ) right = tan( horizontalFov * ( 1f - horizCenterFromLeft ) ) @@ -121,7 +121,7 @@ public final class FovHVHalves { } /** - * Returns a custom symmetry {@link FovHVHalves} instance in tangents, + * Returns a custom symmetry {@link FovHVHalves} instance {@link #inTangents}, * via computing the <code>horizontalFov</code> using: * <pre> halfVertFovTan = tan( verticalFov / 2f ); @@ -157,10 +157,10 @@ public final class FovHVHalves { } } - /** Returns the full horizontal FOV, i.e. {@link #left} + {@link #right}. */ + /** Returns the full horizontal FOV, i.e. {@link #left} + {@link #right}, either in {@link #inTangents} or radians. */ public final float horzFov() { return left+right; } - /** Returns the full vertical FOV, i.e. {@link #top} + {@link #bottom}. */ + /** Returns the full vertical FOV, i.e. {@link #top} + {@link #bottom}, either in {@link #inTangents} or radians. */ public final float vertFov() { return top+bottom; } public final String toString() { diff --git a/src/jogl/classes/com/jogamp/opengl/math/Matrix4.java b/src/jogl/classes/com/jogamp/opengl/math/Matrix4.java index 421bb909f..a080d4442 100644 --- a/src/jogl/classes/com/jogamp/opengl/math/Matrix4.java +++ b/src/jogl/classes/com/jogamp/opengl/math/Matrix4.java @@ -147,8 +147,9 @@ public class Matrix4 { * @param top * @param zNear * @param zFar - * @throws GLException with GL_INVALID_VALUE if zNear is <= 0, or zFar < 0, - * or if left == right, or bottom == top, or zNear == zFar. + * @throws GLException if {@code zNear <= 0} or {@code zFar <= zNear} + * or {@code left == right}, or {@code bottom == top}. + * @see FloatUtil#makeFrustum(float[], int, boolean, float, float, float, float, float, float) */ public final void makeFrustum(final float left, final float right, final float bottom, final float top, final float zNear, final float zFar) throws GLException { multMatrix( FloatUtil.makeFrustum(mat4Tmp1, 0, true, left, right, bottom, top, zNear, zFar) ); @@ -159,7 +160,8 @@ public class Matrix4 { * @param aspect * @param zNear * @param zFar - * @throws GLException with GL_INVALID_VALUE if zNear is <= 0, or zFar < 0, or if zNear == zFar. + * @throws GLException if {@code zNear <= 0} or {@code zFar <= zNear} + * @see FloatUtil#makePerspective(float[], int, boolean, float, float, float, float) */ public final void makePerspective(final float fovy_rad, final float aspect, final float zNear, final float zFar) throws GLException { multMatrix( FloatUtil.makePerspective(mat4Tmp1, 0, true, fovy_rad, aspect, zNear, zFar) ); diff --git a/src/jogl/classes/com/jogamp/opengl/math/geom/Frustum.java b/src/jogl/classes/com/jogamp/opengl/math/geom/Frustum.java index b73bad613..8b0fa559e 100644 --- a/src/jogl/classes/com/jogamp/opengl/math/geom/Frustum.java +++ b/src/jogl/classes/com/jogamp/opengl/math/geom/Frustum.java @@ -30,6 +30,8 @@ package com.jogamp.opengl.math.geom; import jogamp.common.os.PlatformPropsImpl; import com.jogamp.common.os.Platform; +import com.jogamp.opengl.math.FloatUtil; +import com.jogamp.opengl.math.FovHVHalves; /** * Providing frustum {@link #getPlanes() planes} derived by different inputs @@ -77,6 +79,35 @@ import com.jogamp.common.os.Platform; * </p> */ public class Frustum { + /** + * {@link Frustum} description by {@link #fovhv} and {@link #zNear}, {@link #zFar}. + */ + public static class FovDesc { + /** Field of view in both directions, may not be centered, either {@link FovHVHalves#inTangents} or radians. */ + public final FovHVHalves fovhv; + /** Near Z */ + public final float zNear; + /** Far Z */ + public final float zFar; + /** + * @param fovhv field of view in both directions, may not be centered, either {@link FovHVHalves#inTangents} or radians + * @param zNear + * @param zFar + * @throws IllegalArgumentException if {@code zNear <= 0} or {@code zFar <= zNear}. + */ + public FovDesc(final FovHVHalves fovhv, final float zNear, final float zFar) throws IllegalArgumentException { + if( zNear <= 0.0f || zFar <= zNear ) { + throw new IllegalArgumentException("Requirements zNear > 0 and zFar > zNear, but zNear "+zNear+", zFar "+zFar); + } + this.fovhv = fovhv; + this.zNear = zNear; + this.zFar = zFar; + } + public final String toString() { + return "FrustumFovDesc["+fovhv.toStringInDegrees()+", Z["+zNear+" - "+zFar+"]]"; + } + } + /** Normalized planes[l, r, b, t, n, f] */ protected final Plane[] planes = new Plane[6]; @@ -176,19 +207,47 @@ public class Frustum { */ public final void updateByPlanes(final Plane[] src) { for (int i = 0; i < 6; ++i) { - final Plane p0 = planes[i]; - final float[] p0_n = p0.n; - final Plane p1 = src[i]; - final float[] p1_n = p1.n; - p0_n[0] = p1_n[0]; - p0_n[1] = p1_n[1]; - p0_n[2] = p1_n[2]; - p0.d = p1.d; + final Plane pD = planes[i]; + final Plane pS = src[i]; + pD.d = pS.d; + System.arraycopy(pS.n, 0, pD.n, 0, 3); } } /** * Calculate the frustum planes in world coordinates + * using the passed {@link FovDesc}. + * <p> + * Operation Details: + * <ul> + * <li>The given {@link FovDesc} will be transformed + * into the given float[16] as a perspective matrix (column major order) first, + * see {@link FloatUtil#makePerspective(float[], int, boolean, FovHVHalves, float, float)}.</li> + * <li>Then the float[16] perspective matrix is used to {@link #updateByPMV(float[], int)} this instance.</li> + * </ul> + * </p> + * <p> + * Frustum plane's normals will point to the inside of the viewing frustum, + * as required by this class. + * </p> + * + * @param m 4x4 matrix in column-major order (also result) + * @param m_offset offset in given array <i>m</i>, i.e. start of the 4x4 matrix + * @param initM if true, given matrix will be initialized w/ identity matrix, + * otherwise only the frustum fields are set. + * @param fovDesc {@link Frustum} {@link FovDesc} + * @return given matrix for chaining + * @see FloatUtil#makePerspective(float[], int, boolean, FovHVHalves, float, float) + */ + public float[] updateByFovDesc(final float[] m, final int m_offset, final boolean initM, + final FovDesc fovDesc) { + FloatUtil.makePerspective(m, m_offset, initM, fovDesc.fovhv, fovDesc.zNear, fovDesc.zFar); + updateByPMV(m, 0); + return m; + } + + /** + * Calculate the frustum planes in world coordinates * using the passed float[16] as premultiplied P*MV (column major order). * <p> * Frustum plane's normals will point to the inside of the viewing frustum, diff --git a/src/jogl/classes/com/jogamp/opengl/util/PMVMatrix.java b/src/jogl/classes/com/jogamp/opengl/util/PMVMatrix.java index 57f9301b8..196acf9ab 100644 --- a/src/jogl/classes/com/jogamp/opengl/util/PMVMatrix.java +++ b/src/jogl/classes/com/jogamp/opengl/util/PMVMatrix.java @@ -663,8 +663,9 @@ public final class PMVMatrix implements GLMatrixFunc { /** * {@inheritDoc} * - * @throws GLException with GL_INVALID_VALUE if zNear is <= 0, or zFar < 0, - * or if left == right, or bottom == top, or zNear == zFar. + * @throws GLException if {@code zNear <= 0} or {@code zFar <= zNear} + * or {@code left == right}, or {@code bottom == top}. + * @see FloatUtil#makeFrustum(float[], int, boolean, float, float, float, float, float, float) */ @Override public final void glFrustumf(final float left, final float right, final float bottom, final float top, final float zNear, final float zFar) throws GLException { @@ -682,7 +683,8 @@ public final class PMVMatrix implements GLMatrixFunc { * @param aspect aspect ratio width / height * @param zNear * @param zFar - * @throws GLException with GL_INVALID_VALUE if zNear is <= 0, or zFar < 0, or if zNear == zFar. + * @throws GLException if {@code zNear <= 0} or {@code zFar <= zNear} + * @see FloatUtil#makePerspective(float[], int, boolean, float, float, float, float) */ public final void gluPerspective(final float fovy_deg, final float aspect, final float zNear, final float zFar) throws GLException { glMultMatrixf( FloatUtil.makePerspective(mat4Tmp1, 0, true, fovy_deg * FloatUtil.PI / 180.0f, aspect, zNear, zFar), 0 ); diff --git a/src/jogl/classes/jogamp/opengl/ProjectFloat.java b/src/jogl/classes/jogamp/opengl/ProjectFloat.java index ee9560214..5ec5a8e3f 100644 --- a/src/jogl/classes/jogamp/opengl/ProjectFloat.java +++ b/src/jogl/classes/jogamp/opengl/ProjectFloat.java @@ -170,7 +170,8 @@ public class ProjectFloat { * @param aspect * @param zNear * @param zFar - * @throws GLException with GL_INVALID_VALUE if zNear is <= 0, or zFar < 0, or if zNear == zFar. + * @throws GLException if {@code zNear <= 0} or {@code zFar <= zNear} + * @see FloatUtil#makePerspective(float[], int, boolean, float, float, float, float) */ public void gluPerspective(final GLMatrixFunc gl, final float fovy_deg, final float aspect, final float zNear, final float zFar) throws GLException { gl.glMultMatrixf(FloatUtil.makePerspective(mat4Tmp1, 0, true, fovy_deg * FloatUtil.PI / 180.0f, aspect, zNear, zFar), 0); |