diff options
Diffstat (limited to 'src/classes/com/sun/opengl/util/texture')
-rwxr-xr-x | src/classes/com/sun/opengl/util/texture/TextureIO.java | 192 | ||||
-rwxr-xr-x | src/classes/com/sun/opengl/util/texture/spi/DDSImage.java | 42 |
2 files changed, 155 insertions, 79 deletions
diff --git a/src/classes/com/sun/opengl/util/texture/TextureIO.java b/src/classes/com/sun/opengl/util/texture/TextureIO.java index c1e5bcf8b..ca57e9886 100755 --- a/src/classes/com/sun/opengl/util/texture/TextureIO.java +++ b/src/classes/com/sun/opengl/util/texture/TextureIO.java @@ -168,6 +168,9 @@ public class TextureIO { public static TextureData newTextureData(File file, boolean mipmap, String fileSuffix) throws IOException { + if (fileSuffix == null) { + fileSuffix = FileUtil.getFileSuffix(file); + } return newTextureDataImpl(file, 0, 0, mipmap, fileSuffix); } @@ -218,6 +221,9 @@ public class TextureIO { public static TextureData newTextureData(URL url, boolean mipmap, String fileSuffix) throws IOException { + if (fileSuffix == null) { + fileSuffix = FileUtil.getFileSuffix(url.getPath()); + } return newTextureDataImpl(url, 0, 0, mipmap, fileSuffix); } @@ -281,6 +287,10 @@ public class TextureIO { throw new IllegalArgumentException("internalFormat and pixelFormat must be non-zero"); } + if (fileSuffix == null) { + fileSuffix = FileUtil.getFileSuffix(file); + } + return newTextureDataImpl(file, internalFormat, pixelFormat, mipmap, fileSuffix); } @@ -365,6 +375,10 @@ public class TextureIO { throw new IllegalArgumentException("internalFormat and pixelFormat must be non-zero"); } + if (fileSuffix == null) { + fileSuffix = FileUtil.getFileSuffix(url.getPath()); + } + return newTextureDataImpl(url, internalFormat, pixelFormat, mipmap, fileSuffix); } @@ -496,6 +510,9 @@ public class TextureIO { * OpenGL error occurred */ public static Texture newTexture(URL url, boolean mipmap, String fileSuffix) throws IOException, GLException { + if (fileSuffix == null) { + fileSuffix = FileUtil.getFileSuffix(url.getPath()); + } TextureData data = newTextureData(url, mipmap, fileSuffix); Texture texture = newTexture(data); data.flush(); @@ -835,82 +852,8 @@ public class TextureIO { String fileSuffix) throws IOException { if (DDS.equals(fileSuffix) || DDS.equals(FileUtil.getFileSuffix(file))) { - final DDSImage image = DDSImage.read(file); - DDSImage.ImageInfo info = image.getMipMap(0); - if (pixelFormat == 0) { - switch (image.getPixelFormat()) { - case DDSImage.D3DFMT_R8G8B8: - pixelFormat = GL.GL_RGB; - break; - default: - pixelFormat = GL.GL_RGBA; - break; - } - } - if (info.isCompressed()) { - switch (info.getCompressionFormat()) { - case DDSImage.D3DFMT_DXT1: - internalFormat = GL.GL_COMPRESSED_RGB_S3TC_DXT1_EXT; - break; - case DDSImage.D3DFMT_DXT3: - internalFormat = GL.GL_COMPRESSED_RGBA_S3TC_DXT3_EXT; - break; - case DDSImage.D3DFMT_DXT5: - internalFormat = GL.GL_COMPRESSED_RGBA_S3TC_DXT5_EXT; - break; - default: - throw new RuntimeException("Unsupported DDS compression format \"" + - DDSImage.getCompressionFormatName(info.getCompressionFormat()) + "\""); - } - } - if (internalFormat == 0) { - switch (image.getPixelFormat()) { - case DDSImage.D3DFMT_R8G8B8: - pixelFormat = GL.GL_RGB; - break; - default: - pixelFormat = GL.GL_RGBA; - break; - } - } - TextureData.Flusher flusher = new TextureData.Flusher() { - public void flush() { - image.close(); - } - }; - TextureData data; - if (mipmap && image.getNumMipMaps() > 0) { - Buffer[] mipmapData = new Buffer[image.getNumMipMaps()]; - for (int i = 0; i < image.getNumMipMaps(); i++) { - mipmapData[i] = image.getMipMap(i).getData(); - } - data = new TextureData(internalFormat, - info.getWidth(), - info.getHeight(), - 0, - pixelFormat, - GL.GL_UNSIGNED_BYTE, - info.isCompressed(), - true, - mipmapData, - flusher); - } else { - // Fix this up for the end user because we can't generate - // mipmaps for compressed textures - mipmap = false; - data = new TextureData(internalFormat, - info.getWidth(), - info.getHeight(), - 0, - pixelFormat, - GL.GL_UNSIGNED_BYTE, - mipmap, - info.isCompressed(), - true, - info.getData(), - flusher); - } - return data; + DDSImage image = DDSImage.read(file); + return newTextureData(image, internalFormat, pixelFormat, mipmap); } return null; @@ -921,6 +864,14 @@ public class TextureIO { int pixelFormat, boolean mipmap, String fileSuffix) throws IOException { + if (DDS.equals(fileSuffix) || + DDSImage.isDDSImage(stream)) { + byte[] data = StreamUtil.readAll(stream); + ByteBuffer buf = ByteBuffer.wrap(data); + DDSImage image = DDSImage.read(buf); + return newTextureData(image, internalFormat, pixelFormat, mipmap); + } + return null; } @@ -929,7 +880,94 @@ public class TextureIO { int pixelFormat, boolean mipmap, String fileSuffix) throws IOException { - return null; + InputStream stream = new BufferedInputStream(url.openStream()); + try { + return newTextureData(stream, internalFormat, pixelFormat, mipmap, fileSuffix); + } finally { + stream.close(); + } + } + + private TextureData newTextureData(final DDSImage image, + int internalFormat, + int pixelFormat, + boolean mipmap) { + DDSImage.ImageInfo info = image.getMipMap(0); + if (pixelFormat == 0) { + switch (image.getPixelFormat()) { + case DDSImage.D3DFMT_R8G8B8: + pixelFormat = GL.GL_RGB; + break; + default: + pixelFormat = GL.GL_RGBA; + break; + } + } + if (info.isCompressed()) { + switch (info.getCompressionFormat()) { + case DDSImage.D3DFMT_DXT1: + internalFormat = GL.GL_COMPRESSED_RGB_S3TC_DXT1_EXT; + break; + case DDSImage.D3DFMT_DXT3: + internalFormat = GL.GL_COMPRESSED_RGBA_S3TC_DXT3_EXT; + break; + case DDSImage.D3DFMT_DXT5: + internalFormat = GL.GL_COMPRESSED_RGBA_S3TC_DXT5_EXT; + break; + default: + throw new RuntimeException("Unsupported DDS compression format \"" + + DDSImage.getCompressionFormatName(info.getCompressionFormat()) + "\""); + } + } + if (internalFormat == 0) { + switch (image.getPixelFormat()) { + case DDSImage.D3DFMT_R8G8B8: + pixelFormat = GL.GL_RGB; + break; + default: + pixelFormat = GL.GL_RGBA; + break; + } + } + TextureData.Flusher flusher = new TextureData.Flusher() { + public void flush() { + image.close(); + } + }; + TextureData data; + if (mipmap && image.getNumMipMaps() > 0) { + Buffer[] mipmapData = new Buffer[image.getNumMipMaps()]; + for (int i = 0; i < image.getNumMipMaps(); i++) { + mipmapData[i] = image.getMipMap(i).getData(); + } + System.err.println("Creating from mipmapped data"); + data = new TextureData(internalFormat, + info.getWidth(), + info.getHeight(), + 0, + pixelFormat, + GL.GL_UNSIGNED_BYTE, + info.isCompressed(), + true, + mipmapData, + flusher); + } else { + // Fix this up for the end user because we can't generate + // mipmaps for compressed textures + mipmap = false; + data = new TextureData(internalFormat, + info.getWidth(), + info.getHeight(), + 0, + pixelFormat, + GL.GL_UNSIGNED_BYTE, + mipmap, + info.isCompressed(), + true, + info.getData(), + flusher); + } + return data; } } diff --git a/src/classes/com/sun/opengl/util/texture/spi/DDSImage.java b/src/classes/com/sun/opengl/util/texture/spi/DDSImage.java index 486515628..068e3baa6 100755 --- a/src/classes/com/sun/opengl/util/texture/spi/DDSImage.java +++ b/src/classes/com/sun/opengl/util/texture/spi/DDSImage.java @@ -148,6 +148,14 @@ public class DDSImage { return image; } + /** Reads a DirectDraw surface from the specified ByteBuffer, returning + the resulting DDSImage. */ + public static DDSImage read(ByteBuffer buf) throws IOException { + DDSImage image = new DDSImage(); + image.readFromBuffer(buf); + return image; + } + /** Closes open files and resources associated with the open DDSImage. No other methods may be called on this object once this is called. */ @@ -191,6 +199,31 @@ public class DDSImage { return image; } + /** Determines from the magic number whether the given InputStream + points to a DDS image. The given InputStream must return true + from markSupported() and support a minimum of four bytes of + read-ahead. */ + public static boolean isDDSImage(InputStream in) throws IOException { + if (!(in instanceof BufferedInputStream)) { + in = new BufferedInputStream(in); + } + if (!in.markSupported()) { + throw new IOException("Can not test non-destructively whether given InputStream is a DDS image"); + } + in.mark(4); + int magic = 0; + for (int i = 0; i < 4; i++) { + int tmp = in.read(); + if (tmp < 0) { + in.reset(); + return false; + } + magic = ((magic >>> 8) | (tmp << 24)); + } + in.reset(); + return (magic == MAGIC); + } + /** * Writes this DDSImage to the specified file name. */ @@ -555,8 +588,13 @@ public class DDSImage { private void readFromFile(File file) throws IOException { fis = new FileInputStream(file); chan = fis.getChannel(); - buf = chan.map(FileChannel.MapMode.READ_ONLY, - 0, (int) file.length()); + ByteBuffer buf = chan.map(FileChannel.MapMode.READ_ONLY, + 0, (int) file.length()); + readFromBuffer(buf); + } + + private void readFromBuffer(ByteBuffer buf) throws IOException { + this.buf = buf; buf.order(ByteOrder.LITTLE_ENDIAN); header = new Header(); header.read(buf); |