diff options
author | Sven Gothel <[email protected]> | 2008-08-11 14:26:52 +0000 |
---|---|---|
committer | Sven Gothel <[email protected]> | 2008-08-11 14:26:52 +0000 |
commit | 28d62d086afefaf752b38ce5c2c67bc826b5a286 (patch) | |
tree | ac7b720db745c2ab872da484c28e197065866fc3 /src/classes/javax/media | |
parent | 1ef16ee89df4d0dd4df0c1356e5b52eba20f3850 (diff) |
FixedFunction shader as files, prepared for binary shader files
git-svn-id: file:///usr/local/projects/SUN/JOGL/git-svn/svn-server-sync/jogl/branches/JOGL_2_SANDBOX@1748 232f8b59-042b-4e1e-8c03-345bb8c30851
Diffstat (limited to 'src/classes/javax/media')
-rw-r--r-- | src/classes/javax/media/opengl/util/glsl/ShaderCode.java | 153 |
1 files changed, 152 insertions, 1 deletions
diff --git a/src/classes/javax/media/opengl/util/glsl/ShaderCode.java b/src/classes/javax/media/opengl/util/glsl/ShaderCode.java index 46ead1b30..b512f5912 100644 --- a/src/classes/javax/media/opengl/util/glsl/ShaderCode.java +++ b/src/classes/javax/media/opengl/util/glsl/ShaderCode.java @@ -5,7 +5,8 @@ import javax.media.opengl.util.*; import javax.media.opengl.*; import java.nio.*; -import java.io.PrintStream; +import java.io.*; +import java.net.*; public class ShaderCode { public ShaderCode(int type, int number, @@ -25,6 +26,29 @@ public class ShaderCode { id = getNextID(); } + public static ShaderCode create(int type, int number, + Class context, int binFormat, String binaryFile, String[] sourceFiles) { + String[][] shaderSources = null; + ByteBuffer shaderBinary = null; + if(null!=sourceFiles) { + shaderSources = new String[sourceFiles.length][1]; + for(int i=0; i<sourceFiles.length; i++) { + shaderSources[i][0] = readShaderSource(context, sourceFiles[i]); + if(null == shaderSources[i][0]) { + throw new RuntimeException("Can't find shader source " + sourceFiles[i]); + } + } + } + if(null!=binaryFile && 0<=binFormat) { + shaderBinary = readShaderBinary(context, binaryFile); + if(null == shaderBinary) { + System.err.println("Can't find shader binary " + binaryFile + " - ignored"); + binFormat = -1; + } + } + return new ShaderCode(type, number, binFormat, shaderBinary, shaderSources); + } + /** * returns the uniq shader id as an integer * @see #key() @@ -105,6 +129,133 @@ public class ShaderCode { return buf.toString(); } + public static void readShaderSource(ClassLoader context, String path, URL url, StringBuffer result) { + try { + BufferedReader reader = new BufferedReader(new InputStreamReader(url.openStream())); + String line = null; + while ((line = reader.readLine()) != null) { + if (line.startsWith("#include ")) { + String includeFile = line.substring(9).trim(); + // Try relative path first + String next = makeRelative(path, includeFile); + URL nextURL = getResource(context, next); + if (nextURL == null) { + // Try absolute path + next = includeFile; + nextURL = getResource(context, next); + } + if (nextURL == null) { + // Fail + throw new FileNotFoundException("Can't find include file " + includeFile); + } + readShaderSource(context, next, nextURL, result); + } else { + result.append(line + "\n"); + } + } + } catch (IOException e) { + throw new RuntimeException(e); + } + } + + public static String readShaderSource(Class context, String path) { + URL url = getResource(context.getClassLoader(), path); + if (url == null) { + // Try again by scoping the path within the class's package + String className = context.getName().replace('.', '/'); + int lastSlash = className.lastIndexOf('/'); + if (lastSlash >= 0) { + String tmpPath = className.substring(0, lastSlash + 1) + path; + url = getResource(context.getClassLoader(), tmpPath); + if (url != null) { + path = tmpPath; + } + } + } + if (url == null) { + return null; + } + StringBuffer result = new StringBuffer(); + readShaderSource(context.getClassLoader(), path, url, result); + return result.toString(); + } + + public static ByteBuffer readShaderBinary(Class context, String path) { + try { + URL url = getResource(context.getClassLoader(), path); + if (url == null) { + // Try again by scoping the path within the class's package + String className = context.getName().replace('.', '/'); + int lastSlash = className.lastIndexOf('/'); + if (lastSlash >= 0) { + String tmpPath = className.substring(0, lastSlash + 1) + path; + url = getResource(context.getClassLoader(), tmpPath); + if (url != null) { + path = tmpPath; + } + } + } + if (url == null) { + return null; + } + return readAll(new BufferedInputStream(url.openStream())); + } catch (IOException e) { + throw new RuntimeException(e); + } + } + + //---------------------------------------------------------------------- + // Internals only below this point + // + + protected static URL getResource(ClassLoader context, String path) { + if (context != null) { + return context.getResource(path); + } else { + return ClassLoader.getSystemResource(path); + } + } + + protected static String makeRelative(String context, String includeFile) { + File file = new File(context); + file = file.getParentFile(); + while (file != null && includeFile.startsWith("../")) { + file = file.getParentFile(); + includeFile = includeFile.substring(3); + } + if (file != null) { + String res = new File(file, includeFile).getPath(); + // Handle things on Windows + return res.replace('\\', '/'); + } else { + return includeFile; + } + } + + private static ByteBuffer readAll(InputStream stream) throws IOException { + byte[] data = new byte[1024]; + int numRead = 0; + int pos = 0; + do { + int avail = data.length - pos; + if (avail == 0) { + int newSize = 2 * data.length; + byte[] newData = new byte[newSize]; + System.arraycopy(data, 0, newData, 0, data.length); + data = newData; + avail = data.length - pos; + } + numRead = stream.read(data, pos, avail); + if (numRead > 0) { + pos += numRead; + } + } while (numRead >= 0); + ByteBuffer res = ByteBuffer.wrap(data); + if (data.length != pos) { + res.limit(pos); + } + return res; + } protected String[][] shaderSource = null; protected Buffer shaderBinary = null; protected int shaderBinaryFormat = -1; |