Hi there! First post here :-)
I've found this curious situation in which you get an exception on program exit when your main RenderWindow is a static object (in my case is a singleton). The exception is thrown when I close the window and the corresponding stack trace goes like:
nvoglv64.dll!000000005e1f9b74() Unknown
opengl32.dll!000007f967b49ac1() Unknown
sfml-window-d-2.dll!sf::priv::WglContext::~WglContext() Line 114 C++
sfml-window-d-2.dll!sf::priv::WglContext::`scalar deleting destructor'(unsigned int) C++
sfml-window-d-2.dll!sf::priv::GlContext::globalCleanup() Line 119 C++
sfml-window-d-2.dll!sf::GlResource::~GlResource() Line 75 C++
sfml-window-d-2.dll!sf::Window::~Window() Line 77 C++
sfml-graphics-d-2.dll!sf::RenderWindow::~RenderWindow() Line 61 C++
grape++-d.dll!Grape::Application::~Application() Line 49 C++
I'm using SFML 2.0, not from the RC but from the revision a40ef79a18b16fe47ce7eecb7a8d8f6b42b9e5d0 of Feb 21 20:25:11 2013 +0100 compiled with Visual C++ 2012 Express for Desktop to x64 architecture. SFML is linked into a dynamic library, which is also linked (dynamically) to the Application code. The Application is a Windows application (using /SUBSYSTEM:WINDOWS) so its entry point is WinMain, but WinMain just calls a generic int main(int, char**).
I'm not sure, but possibly this exception is related to this other forum thread I didn't want to revive:
Possible Bug in RenderWindow Destructor (SFML 2.0)I haven't found recent information about this "bug" (inconvenient situation?) so I wanted to ask you how do you avoid it. Also whether it's related to the other forum thread or not. Maybe it's just I'm doing something wrong...
Well, I found an ugly and partial solution. Looks like this happens because SFML deallocates some global resources (OpenGL context?) that can't be postponed to the destructor of a static instance of a class. So I created a destroyInstance() method in my Application singleton that simply deletes the single instance. This prevents the exception on exit.
Relevant code looks like:
// in main.cpp
int main(int argc, char *argv[])
{
// Application initialization and main loop.
Grape::Application::instance()->init();
Grape::Application::instance()->loop();
// Application destruction before end of main.
Grape::Application::destroyInstance();
}
// in Application.h
class Application: public sf::RenderWindow
{
public:
GRAPE_API static boost::shared_ptr<Application> instance(void);
GRAPE_API static void destroyInstance(void);
private:
static boost::shared_ptr<Application> sInstance;
};
// in Application.cpp
boost::shared_ptr<Application> Application::sInstance;
boost::shared_ptr<Application> Application::instance(void)
{
if(!sInstance)
{
sInstance = boost::shared_ptr<Application>(new Application());
}
return sInstance;
}
void Application::destroyInstance(void)
{
if(sInstance)
{
sInstance.reset();
}
}
What do you think about it? How do you prevent this situation (apart from avoiding singletons and static instances of classes)? Is it really that ugly what I'm doing?
Thanks for your insights! :-D
Álex