c++ - 代码错误:线程 1:EXC_BAD_ACCESS(代码=1,地址=0x0)
问题描述
我正在尝试使用 OpenGL 用 C++ 编写代码(我使用 GLFW 和 GLEW 库)。这是代码:
#include <GL/glew.h>
#include <GLFW/glfw3.h>
#define numVAOs 1
GLuint renderingProgram;
GLuint vao[numVAOs];
GLuint createShaderProgram(){
const char*vshaderSource =
"#version 430 \n"
"void main(void) \n"
"{gl_Position = vec4(0.0,0.0,0.0,1.0)};";
const char*fshaderSource =
"#version 430 \n"
"out vec4 color; \n"
"void main(void) \n"
"{gl_Position = vec4(0.0,0.0,1.0,1.0)};";
GLuint vShader = glCreateShader(GL_VERTEX_SHADER);
GLuint fShader = glCreateShader(GL_FRAGMENT_SHADER);
glShaderSource(vShader,1,&vshaderSource,NULL);
glShaderSource(fShader,1,&fshaderSource,NULL);
glCompileShader(vShader);
glCompileShader(fShader);
GLuint vfProgram = glCreateProgram();
glAttachShader(vfProgram,vShader);
glAttachShader(vfProgram,fShader);
glLinkProgram(vfProgram);
return vfProgram;
}
int main()
{
glfwInit();
// Define version and compatibility settings
glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 2);
glfwWindowHint(GLFW_OPENGL_PROFILE,GLFW_OPENGL_CORE_PROFILE);
glfwWindowHint(GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE);
glfwWindowHint(GLFW_RESIZABLE, GL_FALSE);
glGenVertexArrays(numVAOs,vao);
glBindVertexArray(vao[0]);
glUseProgram(renderingProgram);
glDrawArrays(GL_POINT,0,1);
// Create OpenGL window and context
GLFWwindow* window = glfwCreateWindow(1430, 800, "Davide", NULL, NULL);
glfwMakeContextCurrent(window);
// Check for window creation failure
if (!window)
{
// Terminate GLFW
glfwTerminate();
return 0;
}
glewExperimental = GL_TRUE; glewInit();
// Event loop
while(!glfwWindowShouldClose(window))
{
// Clear the screen to black
glClearColor(0.0f, 0.0f, 0.0f, 1.0f); glClear(GL_COLOR_BUFFER_BIT);
glfwSwapBuffers(window);
glfwPollEvents();
}
// Terminate GLFW
glfwTerminate(); return 0;
}
不幸的是,当我运行代码时,我得到一个错误代码:
Thread 1: EXC_BAD_ACCESS (code = 1, address = 0x0).
它应该出现一个黑屏,中间有一个点。
解决方案
多个问题:
您在拥有当前 GL 上下文之前调用 GL 函数:
glGenVertexArrays(numVAOs,vao); // nope glBindVertexArray(vao[0]); // nope glUseProgram(renderingProgram); // nope glDrawArrays(GL_POINT,0,1); // nope // Create OpenGL window and context GLFWwindow* window = glfwCreateWindow(1430, 800, "Davide", NULL, NULL); glfwMakeContextCurrent(window);
将这些调用移至after
glfwMakeContextCurrent()
(以及您的 GL 加载程序 init),以便它们具有可操作的 GL 上下文(并在使用它之前window
检查是否为 NULL ):glfwMakeContextCurrent()
// Create OpenGL window and context GLFWwindow* window = glfwCreateWindow(1430, 800, "Davide", NULL, NULL); // Check for window creation failure if (!window) { // Terminate GLFW glfwTerminate(); return 0; } glfwMakeContextCurrent(window); glewExperimental = GL_TRUE; glewInit(); glGenVertexArrays(numVAOs,vao); glBindVertexArray(vao[0]); glUseProgram(renderingProgram); glDrawArrays(GL_POINT,0,1);
您还应该在 ing 它
renderingProgram
之前进行初始化glUseProgram()
,也许使用createShaderProgram()
?gl_Position
在片段着色器中无效。您正在考虑gl_Color
或用户定义的输出,例如您的color
输出。如果您请求的是 GL 3.2 上下文,那么
#version 430
也无效。升级到 GL 4.3 或将着色器降级到#version 150
.GL_POINT
不是 的有效输入glDrawArrays()
。你在想GL_POINTS
。在你的绘制循环开始时调用
glDrawArrays()
每一帧而不是一次,这样你就有机会真正看到你的观点。GLSL 语句后面需要一个分号。
无效的:
void main(void) { gl_Position = vec4(0.0,0.0,0.0,1.0) };
有效的:
void main(void) { gl_Position = vec4(0.0,0.0,0.0,1.0); // note the semicolon } // note the lack of semicolon
全部一起:
#include <GL/glew.h>
#include <GLFW/glfw3.h>
#include <iostream>
void CheckStatus( GLuint obj, bool isShader )
{
GLint status = GL_FALSE, log[ 1 << 11 ] = { 0 };
( isShader ? glGetShaderiv : glGetProgramiv )( obj, isShader ? GL_COMPILE_STATUS : GL_LINK_STATUS, &status );
if( status == GL_TRUE ) return;
( isShader ? glGetShaderInfoLog : glGetProgramInfoLog )( obj, sizeof( log ), NULL, (GLchar*)log );
std::cerr << (GLchar*)log << "\n";
std::exit( EXIT_FAILURE );
}
void AttachShader( GLuint program, GLenum type, const char* src )
{
GLuint shader = glCreateShader( type );
glShaderSource( shader, 1, &src, NULL );
glCompileShader( shader );
CheckStatus( shader, true );
glAttachShader( program, shader );
glDeleteShader( shader );
}
const char* const vert = 1 + R"GLSL(
#version 150
void main()
{
gl_Position = vec4(0.0,0.0,0.0,1.0);
}
)GLSL";
const char* const frag = 1 + R"GLSL(
#version 150
out vec4 color;
void main()
{
color = vec4(0.0,0.0,1.0,1.0);
}
)GLSL";
#define numVAOs 1
GLuint renderingProgram;
GLuint vao[ numVAOs ];
int main()
{
glfwInit();
// Define version and compatibility settings
glfwWindowHint( GLFW_CONTEXT_VERSION_MAJOR, 3 );
glfwWindowHint( GLFW_CONTEXT_VERSION_MINOR, 2 );
glfwWindowHint( GLFW_OPENGL_PROFILE, GLFW_OPENGL_CORE_PROFILE );
glfwWindowHint( GLFW_OPENGL_FORWARD_COMPAT, GL_TRUE );
glfwWindowHint( GLFW_RESIZABLE, GL_FALSE );
// Create OpenGL window and context
GLFWwindow* window = glfwCreateWindow( 320, 240, "Davide", NULL, NULL );
// Check for window creation failure
if( !window )
{
// Terminate GLFW
glfwTerminate();
return 0;
}
glfwMakeContextCurrent( window );
glewExperimental = GL_TRUE;
glewInit();
glGenVertexArrays( numVAOs, vao );
glBindVertexArray( vao[ 0 ] );
GLuint renderingProgram = glCreateProgram();
AttachShader( renderingProgram, GL_VERTEX_SHADER, vert );
AttachShader( renderingProgram, GL_FRAGMENT_SHADER, frag );
glLinkProgram( renderingProgram );
CheckStatus( renderingProgram, false );
glUseProgram( renderingProgram );
// Event loop
while( !glfwWindowShouldClose( window ) )
{
// Clear the screen to black
glClearColor( 0.0f, 0.0f, 0.0f, 1.0f );
glClear( GL_COLOR_BUFFER_BIT );
glDrawArrays( GL_POINTS, 0, 1 );
glfwSwapBuffers( window );
glfwPollEvents();
}
// Terminate GLFW
glfwTerminate();
return 0;
}
推荐阅读
- python - 在 Django 中为每个用户设置一个 IP 白名单
- node.js - Laravel view 和 node.js api 结合项目配置
- python - 最佳实践:在 django 框架中放置抓取文件的位置
- python - 如何使用 re.search 从字符串中提取所有日期?
- javascript - React Stripe 拆分卡元素出错:超出最大更新深度
- react-native - 如何修复意外的令牌,预期的“;” 反应中的错误
- informatica - Informatica 审计框架
- r - removeUI 不会完全删除 UI
- reactjs - Recharts XAxis 未显示来自 tickFormatter 的日期值
- xamarin - 在 XF 中加载 svg 图像的 luberda-molinet/FFImageLoading 代码是否有任何替代方案