C++ 调用OpenGL函数时程序崩溃
我正在尝试设置一个游戏引擎项目。我的VisualStudio项目已经设置好,这样我就有了一个独立于“游戏”项目的“引擎”项目。然后引擎项目被编译成一个dll供游戏项目使用。我已经下载并设置了glfw和glew以开始使用openGL。我的问题是,当我第一次使用openGL函数时,程序就会崩溃。我知道这与glewinit有关,即使glew正在成功初始化(没有控制台错误)。在我的引擎项目中,我有一个窗口类,在窗口构建时,应设置glew: 窗户C++ 调用OpenGL函数时程序崩溃,c++,opengl,game-engine,glew,C++,Opengl,Game Engine,Glew,我正在尝试设置一个游戏引擎项目。我的VisualStudio项目已经设置好,这样我就有了一个独立于“游戏”项目的“引擎”项目。然后引擎项目被编译成一个dll供游戏项目使用。我已经下载并设置了glfw和glew以开始使用openGL。我的问题是,当我第一次使用openGL函数时,程序就会崩溃。我知道这与glewinit有关,即使glew正在成功初始化(没有控制台错误)。在我的引擎项目中,我有一个窗口类,在窗口构建时,应设置glew: 窗户 #pragma once #include "GL\gle
#pragma once
#include "GL\glew.h"
#include "GLFW\glfw3.h"
#if (_DEBUG)
#define LOG(x) printf(x)
#else
#define LOG(x)
#endif
namespace BlazeGraphics
{
class __declspec(dllexport) Window
{
public:
Window(short width, short height, const char* title);
~Window();
void Update();
void Clear() const;
bool Closed() const;
private:
int m_height;
int m_width;
const char* m_title;
GLFWwindow* m_window;
private:
Window(const Window& copy) {}
void operator=(const Window& copy) {}
};
}
Window.cpp(调用glewinit()的位置)
然后我的程序编译得很好。为什么试图在engine.dll内初始化glew会导致程序崩溃?感谢您的帮助。GLEW的工作原理是为每个OpenGL函数定义一个函数指针作为全局变量。让我们以
glBindBuffer
为例:
#define GLEW_FUN_EXPORT GLEWAPI
typedef void (GLAPIENTRY * PFNGLBINDBUFFERPROC) (GLenum target, GLuint buffer);
GLEW_FUN_EXPORT PFNGLBINDBUFFERPROC __glewBindBuffer;
因此,我们只有一个\uu glewBindBuffer
函数指针,它将通过glewInit
从OpenGL实现中设置为正确的地址
为了能够实际编写glBindBuffer
,GLEW只需定义将GL函数映射到这些函数指针变量的预处理器宏:
#define glBindBuffer GLEW_GET_FUN(__glewBindBuffer);
为什么试图在engine.dll中初始化glew会导致程序崩溃
因为engine.dll
和主应用程序都有一组单独的全局变量。您必须从引擎DLL中导出所有\uu glew*
变量,才能访问glewInit
调用engine.DLL的结果glew通过为每个OpenGL函数定义一个函数指针作为全局变量来工作。让我们以glBindBuffer
为例:
#define GLEW_FUN_EXPORT GLEWAPI
typedef void (GLAPIENTRY * PFNGLBINDBUFFERPROC) (GLenum target, GLuint buffer);
GLEW_FUN_EXPORT PFNGLBINDBUFFERPROC __glewBindBuffer;
因此,我们只有一个\uu glewBindBuffer
函数指针,它将通过glewInit
从OpenGL实现中设置为正确的地址
为了能够实际编写glBindBuffer
,GLEW只需定义将GL函数映射到这些函数指针变量的预处理器宏:
#define glBindBuffer GLEW_GET_FUN(__glewBindBuffer);
为什么试图在engine.dll中初始化glew会导致程序崩溃
因为engine.dll
和主应用程序都有一组单独的全局变量。您必须从引擎DLL导出所有\uuu glew*
变量,才能访问glewInit
调用engine.DLL
桌面的结果。我无意中添加了opengl es标记,现在删除了它只有在已经创建了opengl上下文的情况下才能调用glewInit
,否则会撞到墙。。。我没有看到任何OpenGL初始化。。。可能是隐藏在BlazeGraphics::Window(1280720,“MyGame”)中代码>。另外,应该从同一个线程调用glewInit
和所有OpenGL东西…桌面。我无意中添加了opengl es标记,现在删除了它只有在已经创建了opengl上下文的情况下才能调用glewInit
,否则会撞到墙。。。我没有看到任何OpenGL初始化。。。可能是隐藏在BlazeGraphics::Window(1280720,“MyGame”)中代码>。另外,应该从同一个线程调用glewInit
和所有OpenGL内容……感谢您的澄清。确保导出游戏项目中使用的所有glew变量的最佳方法是什么?动态链接glew而不是在引擎中静态链接它会起作用吗?@Jason:老实说,你可能不应该这么做,因为函数指针可能在不同的上下文中有所不同。从技术上讲,每次切换上下文时都必须调用glewInit
。正确的解决方案是让一个结构或类保存所有函数指针,并通过它进行调用。然后,您可以在DLL之间传递指向该结构的指针当然,大多数OpenGL加载程序的设计不允许它轻松完成这项工作。我建议你在每个需要它的模块中调用glewInit
。哇,真的吗?那很有趣。我从没想过会是这样。谢谢你的提醒。谢谢你的澄清。确保导出游戏项目中使用的所有glew变量的最佳方法是什么?动态链接glew而不是在引擎中静态链接它会起作用吗?@Jason:老实说,你可能不应该这么做,因为函数指针可能在不同的上下文中有所不同。从技术上讲,每次切换上下文时都必须调用glewInit
。正确的解决方案是让一个结构或类保存所有函数指针,并通过它进行调用。然后,您可以在DLL之间传递指向该结构的指针当然,大多数OpenGL加载程序的设计不允许它轻松完成这项工作。我建议你在每个需要它的模块中调用glewInit
。哇,真的吗?那很有趣。我从没想过会是这样。谢谢你的提醒
#define glBindBuffer GLEW_GET_FUN(__glewBindBuffer);