gpt4 book ai didi

c++ - 为什么当我从初始化函数返回时我的 SDL 窗口关闭?

转载 作者:塔克拉玛干 更新时间:2023-11-03 07:16:48 26 4
gpt4 key购买 nike

我一直在研究一个简单的游戏引擎(我知道,我知道,我以前听说过“写游戏而不是引擎”,这只是为了理解概念)。我一直在使用 SDL2,因为它与 OpenGL 配合得很好。但是由于某些原因,程序会在初始化函数完成后关闭。

Screen.cpp:
Screen::Screen(int width, int height, const std::string& title)
{

//Initialize SDL
SDL_Init(SDL_INIT_EVERYTHING);
//Setting OpenGL Attributes
SDL_GL_SetAttribute(SDL_GL_RED_SIZE, 8);
SDL_GL_SetAttribute(SDL_GL_GREEN_SIZE, 8);
SDL_GL_SetAttribute(SDL_GL_BLUE_SIZE, 8);
SDL_GL_SetAttribute(SDL_GL_ALPHA_SIZE, 8);
SDL_GL_SetAttribute(SDL_GL_BUFFER_SIZE, 32);
SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER, 1);

//Create the Window
m_window = SDL_CreateWindow(title.c_str(), SDL_WINDOWPOS_CENTERED, SDL_WINDOWPOS_CENTERED, width, height, SDL_WINDOW_OPENGL);
l.writeToDebugLog("Created SDL_Window!");
//Create OpenGL context from within SDL
m_glContext = SDL_GL_CreateContext(m_window);
l.writeToDebugLog("Created SDL GL Context!");

//Initializing GLEW
GLenum status = glewInit();
l.writeToDebugLog( "Initializing GLEW");
if (status != GLEW_OK)
{
l.writeToGLEWELog(" Glew Failed to Initialize!");
}

//setting the windowSurface to the m_window's surface
windowSurface = SDL_GetWindowSurface(m_window);
m_isClosed = false;
}

这是我创建屏幕对象并初始化所有 SDL 函数和 OpenGL 函数的地方

Engine.cpp:
void Engine::initialize(){

//Console Detecting platform
c.initialize();
//Printing Operating System to screen
std::cout << "Loaded on : " << platformToString(c.os) << " OS " << std::endl;
//Constructing a new Screen to be referenced too
graphics::Screen temp(800,600,"ClimLib 0.0.05");

//setting all the variables
m_window = &temp;
m_EntityManager = nullptr;
m_isRunning = temp.isClosed();
m_renderer = SDL_GetRenderer(m_window->getWindow());


}
void Engine::update(){
do{
//Check whether entities have been created and placed in the manager
if (m_EntityManager != nullptr){
for each(core::Entity *e in *m_EntityManager){
for each(core::Component *c in e->getComponentList()){
c->Update();
}
}
}


//Update Logic Here
m_window->Update();
if (m_window->isClosed()){
m_isRunning = false;
return;
}

}while (isRunning());
}

这个初始化函数是我的窗口在删除自身之前执行的最后一个函数,也许我需要从程序的主函数调用它?

main.cpp:
int main(int argc, char *argv[]){
clim::system::Engine game;
game.initialize();
while (game.isRunning()){
game.update();
}
return 0;
}

这就是我目前的主要设置方式。

编辑:我相信原因是因为我正在创建一个变量并将其存储为引用,当函数返回时临时变量被丢弃?

最佳答案

您将屏幕创建为一个临时值,然后将该值的地址分配给一个指针,该指针的生命周期实际上超过了它所指向的值的生命周期,它很可能也是一个堆栈值。如果没有窗口死机的直接问题,这将在以后使用时导致以下一种或两种情况:

  • 崩溃(非法内存访问)
  • 未定义的行为(从读取堆栈中位于此地址的随机值稍后执行)

虽然现在可能不适用,但这是一个真正让自己在几乎所有事情上都头疼的好方法。

你应该像这样分配:

 m_window = new graphics::Screen(800,600,"ClimLib 0.0.05");

您初始化它的方式意味着它会在函数退出时自行销毁,因为它是在函数中声明和初始化的。使用 new 将保证它存在,直到您删除它,因为除非您的代码这样做,否则它将不受干扰地位于堆上的某个位置。

只需确保在包含它的类的析构函数中调用 delete m_window,以便在使用 new 创建窗口时正确清理窗口。您还可以将 m_window 声明为 graphics::Screen 而不是 graphics::Screen* 并像这样分配 m_window:

m_window = graphics::Screen(800,600,"ClimLib 0.0.05");

这样您就不必担心以后自己删除它,因为它会在删除包含类时自行删除。

关于c++ - 为什么当我从初始化函数返回时我的 SDL 窗口关闭?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32551941/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com