GLRenderer: support luminance / alpha textures in core profile

experimental
Kirill Vainer 10 years ago
parent 6f33002f9a
commit e2d8fe8293
  1. 2
      jme3-core/src/main/java/com/jme3/renderer/opengl/GL.java
  2. 13
      jme3-core/src/main/java/com/jme3/renderer/opengl/GL3.java
  3. 2
      jme3-core/src/main/java/com/jme3/renderer/opengl/GL4.java
  4. 21
      jme3-core/src/main/java/com/jme3/renderer/opengl/GLImageFormat.java
  5. 28
      jme3-core/src/main/java/com/jme3/renderer/opengl/GLImageFormats.java
  6. 2
      jme3-core/src/main/java/com/jme3/renderer/opengl/GLRenderer.java
  7. 38
      jme3-core/src/main/java/com/jme3/renderer/opengl/TextureUtil.java

@ -74,6 +74,7 @@ public interface GL {
public static final int GL_FRONT_AND_BACK = 0x408;
public static final int GL_GEQUAL = 0x206;
public static final int GL_GREATER = 0x204;
public static final int GL_GREEN = 0x1904;
public static final int GL_INCR = 0x1E02;
public static final int GL_INCR_WRAP = 0x8507;
public static final int GL_INFO_LOG_LENGTH = 0x8B84;
@ -114,6 +115,7 @@ public interface GL {
public static final int GL_OUT_OF_MEMORY = 0x505;
public static final int GL_POINTS = 0x0;
public static final int GL_POLYGON_OFFSET_FILL = 0x8037;
public static final int GL_RED = 0x1903;
public static final int GL_RENDERER = 0x1F01;
public static final int GL_REPEAT = 0x2901;
public static final int GL_REPLACE = 0x1E01;

@ -34,7 +34,7 @@ package com.jme3.renderer.opengl;
import java.nio.IntBuffer;
/**
* GL functions only available on vanilla desktop OpenGL 3.0.
* GL functions only available on vanilla desktop OpenGL 3.0+.
*
* @author Kirill Vainer
*/
@ -43,6 +43,17 @@ public interface GL3 extends GL2 {
public static final int GL_DEPTH_STENCIL_ATTACHMENT = 0x821A;
public static final int GL_GEOMETRY_SHADER = 0x8DD9;
public static final int GL_NUM_EXTENSIONS = 0x821D;
public static final int GL_R8 = 0x8229;
public static final int GL_R16F = 0x822D;
public static final int GL_R32F = 0x822E;
public static final int GL_RG16F = 0x822F;
public static final int GL_RG32F = 0x8230;
public static final int GL_RG = 0x8227;
public static final int GL_RG8 = 0x822B;
public static final int GL_TEXTURE_SWIZZLE_A = 0x8E45;
public static final int GL_TEXTURE_SWIZZLE_B = 0x8E44;
public static final int GL_TEXTURE_SWIZZLE_G = 0x8E43;
public static final int GL_TEXTURE_SWIZZLE_R = 0x8E42;
public void glBindFragDataLocation(int param1, int param2, String param3); /// GL3+
public void glBindVertexArray(int param1); /// GL3+

@ -34,7 +34,7 @@ package com.jme3.renderer.opengl;
import java.nio.IntBuffer;
/**
* GL functions only available on vanilla desktop OpenGL 3.0.
* GL functions only available on vanilla desktop OpenGL 4.0.
*
* @author Kirill Vainer
*/

@ -42,6 +42,7 @@ public final class GLImageFormat {
public final int format;
public final int dataType;
public final boolean compressed;
public final boolean swizzleRequired;
/**
* Constructor for formats.
@ -55,6 +56,7 @@ public final class GLImageFormat {
this.format = format;
this.dataType = dataType;
this.compressed = false;
this.swizzleRequired = false;
}
/**
@ -63,11 +65,30 @@ public final class GLImageFormat {
* @param internalFormat OpenGL internal format
* @param format OpenGL format
* @param dataType OpenGL datatype
* @param compressed Format is compressed
*/
public GLImageFormat(int internalFormat, int format, int dataType, boolean compressed) {
this.internalFormat = internalFormat;
this.format = format;
this.dataType = dataType;
this.compressed = compressed;
this.swizzleRequired = false;
}
/**
* Constructor for formats.
*
* @param internalFormat OpenGL internal format
* @param format OpenGL format
* @param dataType OpenGL datatype
* @param compressed Format is compressed
* @param swizzleRequired Need to use texture swizzle to upload texture
*/
public GLImageFormat(int internalFormat, int format, int dataType, boolean compressed, boolean swizzleRequired) {
this.internalFormat = internalFormat;
this.format = format;
this.dataType = dataType;
this.compressed = compressed;
this.swizzleRequired = swizzleRequired;
}
}

@ -52,6 +52,13 @@ public final class GLImageFormats {
formatToGL[0][format.ordinal()] = new GLImageFormat(glInternalFormat, glFormat, glDataType);
}
private static void formatSwiz(GLImageFormat[][] formatToGL, Image.Format format,
int glInternalFormat,
int glFormat,
int glDataType){
formatToGL[0][format.ordinal()] = new GLImageFormat(glInternalFormat, glFormat, glDataType, false, true);
}
private static void formatSrgb(GLImageFormat[][] formatToGL, Image.Format format,
int glInternalFormat,
int glFormat,
@ -60,6 +67,14 @@ public final class GLImageFormats {
formatToGL[1][format.ordinal()] = new GLImageFormat(glInternalFormat, glFormat, glDataType);
}
private static void formatSrgbSwiz(GLImageFormat[][] formatToGL, Image.Format format,
int glInternalFormat,
int glFormat,
int glDataType)
{
formatToGL[1][format.ordinal()] = new GLImageFormat(glInternalFormat, glFormat, glDataType, false, true);
}
private static void formatComp(GLImageFormat[][] formatToGL, Image.Format format,
int glCompressedFormat,
int glFormat,
@ -88,6 +103,19 @@ public final class GLImageFormats {
public static GLImageFormat[][] getFormatsForCaps(EnumSet<Caps> caps) {
GLImageFormat[][] formatToGL = new GLImageFormat[2][Image.Format.values().length];
// Core Profile Formats (supported by both OpenGL Core 3.3 and OpenGL ES 3.0+)
if (caps.contains(Caps.CoreProfile)) {
formatSwiz(formatToGL, Format.Alpha8, GL3.GL_R8, GL.GL_RED, GL.GL_UNSIGNED_BYTE);
formatSwiz(formatToGL, Format.Luminance8, GL3.GL_R8, GL.GL_RED, GL.GL_UNSIGNED_BYTE);
formatSwiz(formatToGL, Format.Luminance8Alpha8, GL3.GL_RG8, GL3.GL_RG, GL.GL_UNSIGNED_BYTE);
formatSwiz(formatToGL, Format.Luminance16F, GL3.GL_R16F, GL.GL_RED, GLExt.GL_HALF_FLOAT_ARB);
formatSwiz(formatToGL, Format.Luminance32F, GL3.GL_R32F, GL.GL_RED, GL.GL_FLOAT);
formatSwiz(formatToGL, Format.Luminance16FAlpha16F, GL3.GL_RG16F, GL3.GL_RG, GLExt.GL_HALF_FLOAT_ARB);
formatSrgbSwiz(formatToGL, Format.Luminance8, GLExt.GL_SRGB8_EXT, GL.GL_RED, GL.GL_UNSIGNED_BYTE);
formatSrgbSwiz(formatToGL, Format.Luminance8Alpha8, GLExt.GL_SRGB8_ALPHA8_EXT, GL3.GL_RG, GL.GL_UNSIGNED_BYTE);
}
if (caps.contains(Caps.OpenGL20)) {
if (!caps.contains(Caps.CoreProfile)) {
format(formatToGL, Format.Alpha8, GL2.GL_ALPHA8, GL.GL_ALPHA, GL.GL_UNSIGNED_BYTE);

@ -106,7 +106,7 @@ public class GLRenderer implements Renderer {
this.gl4 = gl instanceof GL4 ? (GL4)gl : null;
this.glfbo = glfbo;
this.glext = glext;
this.texUtil = new TextureUtil(gl, gl2, glext, context);
this.texUtil = new TextureUtil(gl, gl2, glext);
}
@Override

@ -54,14 +54,12 @@ final class TextureUtil {
private final GL gl;
private final GL2 gl2;
private final GLExt glext;
private final RenderContext context;
private GLImageFormat[][] formats;
public TextureUtil(GL gl, GL2 gl2, GLExt glext, RenderContext context) {
public TextureUtil(GL gl, GL2 gl2, GLExt glext) {
this.gl = gl;
this.gl2 = gl2;
this.glext = glext;
this.context = context;
}
public void initialize(EnumSet<Caps> caps) {
@ -103,6 +101,33 @@ final class TextureUtil {
return glFmt;
}
private void setupTextureSwizzle(int target, Format format) {
// Needed for OpenGL 3.3 to support luminance / alpha formats
switch (format) {
case Alpha8:
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_R, GL.GL_ZERO);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_G, GL.GL_ZERO);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_B, GL.GL_ZERO);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_A, GL.GL_RED);
break;
case Luminance8:
case Luminance16F:
case Luminance32F:
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_R, GL.GL_RED);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_G, GL.GL_RED);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_B, GL.GL_RED);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_A, GL.GL_ONE);
break;
case Luminance8Alpha8:
case Luminance16FAlpha16F:
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_R, GL.GL_RED);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_G, GL.GL_RED);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_B, GL.GL_RED);
gl.glTexParameteri(target, GL3.GL_TEXTURE_SWIZZLE_A, GL.GL_GREEN);
break;
}
}
private void uploadTextureLevel(GLImageFormat format, int target, int level, int slice, int sliceCount, int width, int height, int depth, int samples, ByteBuffer data) {
if (format.compressed && data != null) {
if (target == GL2.GL_TEXTURE_3D) {
@ -242,6 +267,11 @@ final class TextureUtil {
}
int samples = image.getMultiSamples();
// For OGL3 core: setup texture swizzle.
if (oglFormat.swizzleRequired) {
setupTextureSwizzle(target, jmeFormat);
}
for (int i = 0; i < mipSizes.length; i++) {
int mipWidth = Math.max(1, width >> i);

Loading…
Cancel
Save