java - 构建为 jar 时读取 .shader 文件

标签 java opengl jar shader lwjgl

我正在尝试为学校项目制作游戏,一切正常,除了当我构建为 jar 时,它不会渲染任何内容,并且我确定这是因为它找不到着色器文件。这是读取文件的代码。

public static int loadShader(String filepath, int type){
    StringBuilder result = new StringBuilder();

    try{
        BufferedReader bufferedReader = new BufferedReader(new FileReader(filepath));
        String buffer = "";
        while((buffer = bufferedReader.readLine()) != null)
            result.append(buffer + "\n");
        bufferedReader.close();
    }catch (IOException e1){
        e1.printStackTrace();
    }

    int shaderID = glCreateShader(type);
    glShaderSource(shaderID, result.toString());
    glCompileShader(shaderID);
    if(glGetShaderi(shaderID, GL_COMPILE_STATUS) == GL_FALSE){
        System.err.println(glGetShaderInfoLog(shaderID, 500));
        System.err.println("Could not compile shader.");
        System.err.println(-1);
    }
    return shaderID;

}

这是我需要放置文件路径的地方

public static void loadAll(){
    shader1 = new Shader("src/com/myGame/shaders/vertex.shader", "src/com/myGame/shaders/fragment.shader");
    shader3 = new Shader("src/com/myGame/shaders/vertex3.shader", "src/com/myGame/shaders/fragment3.shader");
}

这是 Shader 类

public class Shader {
    private int programID;
    private int vertexShaderID;
    private int fragmentShaderID;

public Shader(String vertexFile, String fragmentFile){
    vertexShaderID = loadShader(vertexFile, GL_VERTEX_SHADER);
    fragmentShaderID = loadShader(fragmentFile, GL_FRAGMENT_SHADER);
    programID = glCreateProgram();
    glAttachShader(programID, vertexShaderID);
    glAttachShader(programID, fragmentShaderID);
    glLinkProgram(programID);
    glValidateProgram(programID);
}

public void start(){
    glUseProgram(programID);
}

public void stop(){
    glUseProgram(0);
}

public int getID(){
    return this.programID;
}

public int getUniform(String name){
    int result = glGetUniformLocation(programID, name);
    if(result == -1)
        System.err.println("Could not find uniform variable'" + name + "'!");
    return glGetUniformLocation(programID, name);
}

public void setUniform3f(String name, Vector3f vector) {
    glUniform3f(getUniform(name), vector.x, vector.y, vector.z);
}

}

当我在 IntelliJ 中编译时,这一切都有效,但当我编译、构建并作为 jar 运行它时,这一切都不起作用。当我尝试从命令提示符将其作为 jar 运行时,它表示无法找出放入着色器类中的 setUniform3f 方法中的变量 pos 。

编辑:我正在尝试使用InputStream,这就是我所拥有的,但它遇到了空指针异常。

    Exception in thread "Bot Fighting" java.lang.NullPointerException
at java.io.Reader.<init>(Reader.java:78)
at java.io.InputStreamReader.<init>(InputStreamReader.java:72)
at com.myGame.utils.Utilities.loadShader(Utilities.java:22)
at com.myGame.graphicsEngine.Shader.<init>(Shader.java:20)
at com.myGame.graphicsEngine.ShaderManager.loadAll(ShaderManager.java:20)
at com.myGame.gameEngine.Level.<init>(Level.java:21)
at com.myGame.main.BotMain.init(BotMain.java:50)
at com.myGame.main.BotMain.run(BotMain.java:58)
at java.lang.Thread.run(Thread.java:745)

这是我的带有 InputStream 的代码

     public static int loadShader(String filepath, int type){
    StringBuilder result = new StringBuilder();
    InputStream in = ClassLoader.getSystemResourceAsStream(filepath);
    try{
        BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(in));
        String buffer = "";
        while((buffer = bufferedReader.readLine()) != null)
            result.append(buffer + "\n");
        bufferedReader.close();
    }catch (IOException e1){
        e1.printStackTrace();
    }
    try {
        in.close();
    } catch (IOException e) {
        e.printStackTrace();
    }

    int shaderID = glCreateShader(type);
    glShaderSource(shaderID, result.toString());
    glCompileShader(shaderID);
    if(glGetShaderi(shaderID, GL_COMPILE_STATUS) == GL_FALSE){
        System.err.println(glGetShaderInfoLog(shaderID, 500));
        System.err.println("Could not compile shader.");
        System.err.println(-1);
    }
    return shaderID;

我显然没有使用这个权利,那么我该如何使用这个呢?

最佳答案

试试这个:

public static void loadAll(){
    shader1 = new Shader("com/myGame/shaders/vertex.shader", "com/myGame/shaders/fragment.shader");
    shader3 = new Shader("com/myGame/shaders/vertex3.shader", "com/myGame/shaders/fragment3.shader");
}

没有“src/”

如果它不起作用,请使用这个:

InputStreamReader(cls.getResourceAsStream(name))

哪里Class<?> cls是与着色器位于同一包中的某个类,并且 String name是文件名,类似于:

public static int loadShader(Class<?> cls, String name, int type){
    StringBuilder result = new StringBuilder();
    InputStream in = ClassLoader.getSystemResourceAsStream(cls, name);
    try{
        BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(in));
        String buffer = "";
        while((buffer = bufferedReader.readLine()) != null)
            result.append(buffer + "\n");
        bufferedReader.close();
    }catch (IOException e1){
        e1.printStackTrace();
    }

你打电话loadShader(com.myGame.shaders.Shader.class, "vertex.shader", GL_VERTEX_SHADER) 。 问题是,您需要使用与文件位于同一包中的类。

希望对你有帮助

关于java - 构建为 jar 时读取 .shader 文件,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/37353499/

相关文章:

java - 从流中获取副本而不消耗原始流

c++ - 按需渲染帧

在 OpenGL 中创建带动画点的正弦波?

c++ - FPS 相机实现错误(OpenGL/GLUT/C++)

java - 如何添加新的 jar 文件作为 Java Maven Web 项目的 POM.xml 的依赖项?

java - 如何使java应用程序作为在特定时间自动打开的服务运行

java - 让 Actionbar 标签贴在 Fragment 上

java - 为什么无法从 JAR 文件加载主类 list 属性?

推送到github后Android项目jar文件丢失

java - getValidationMode() 的 AbstractMethodErrorLjavax/persistence/ValidationMode