1
General / WxWidgets/SFML program crashes with an X window system error (BadAccess)
« on: October 24, 2016, 11:33:24 am »
I have adapted this class from the given tutorials for SFML 1.6 and tried my best to update it for new APIs on both sides.
However, I'm having no luck on Linux. On Windows this works fine but on Linux I get the following in stderr:
If you wish to try the class for yourself it is trivial from this point to write a wxApp that uses a frame and reproduce the crash. Normally I would do this for you guys but I'm not too well so I'm going back to bed now /;
Any help would be appreciated.
Code: [Select]
// .h FILE
#pragma once
#include <wx/wxprec.h>
#ifndef WX_PRECOMP
#include <wx/wx.h>
#endif
#include "SFML/Graphics.hpp"
class wxSFMLCanvas : public wxControl, public sf::RenderWindow
{
public:
wxSFMLCanvas(wxWindow* Parent = NULL, wxWindowID Id = -1, const wxPoint& Position = wxDefaultPosition,
const wxSize& Size = wxDefaultSize, long Style = 0);
virtual ~wxSFMLCanvas() {};
void setDrawMode(bool onOrOff);
private:
DECLARE_EVENT_TABLE()
virtual void OnUpdate() {};
void OnIdle(wxIdleEvent&);
void OnEraseBackground(wxEraseEvent&);
wxPaintDC* drawLock;
};
// .cpp FILE
#include "wxSFMLCanvas.h"
// some extras needed for gtk
#ifdef __WXGTK__
#include <gtk/gtk.h>
#include <gdk/gdkx.h>
#endif
BEGIN_EVENT_TABLE(wxSFMLCanvas, wxControl)
EVT_IDLE(wxSFMLCanvas::OnIdle)
EVT_ERASE_BACKGROUND(wxSFMLCanvas::OnEraseBackground)
END_EVENT_TABLE()
wxSFMLCanvas::wxSFMLCanvas(wxWindow* Parent, wxWindowID Id, const wxPoint& Position, const wxSize& Size, long Style) :
wxControl(Parent, Id, Position, Size, Style)
{
#ifdef __WXGTK__
GtkWidget* widget = GetHandle();
gtk_widget_realize(widget);
gtk_widget_set_double_buffered(widget, false);
GdkWindow* Win = gtk_widget_get_window( widget );
XFlush(GDK_WINDOW_XDISPLAY(Win));
sf::RenderWindow::create((sf::WindowHandle)GDK_WINDOW_XID(Win));
#else
// Tested under Windows XP only (should work with X11 and other Windows versions - no idea about MacOS)
sf::RenderWindow::create((sf::WindowHandle)GetHandle());
#endif
drawLock = nullptr;
}
void wxSFMLCanvas::OnIdle(wxIdleEvent&)
{
// Send a paint message when the control is idle, to ensure maximum framerate
Refresh();
}
void wxSFMLCanvas::OnEraseBackground(wxEraseEvent&)
{
}
void wxSFMLCanvas::setDrawMode(bool onOrOff)
{
if (onOrOff && !drawLock) {
drawLock = new wxPaintDC(this);
}
else if (!onOrOff && drawLock) {
delete drawLock;
drawLock = nullptr;
}
}
However, I'm having no luck on Linux. On Windows this works fine but on Linux I get the following in stderr:
Quote
The program 'MAGEditor' received an X Window System error.
This probably reflects a bug in the program.
The error was 'BadAccess (attempt to access private resource denied)'.
(Details: serial 54 error_code 10 request_code 2 minor_code 0)
(Note to programmers: normally, X errors are reported asynchronously;
that is, you will receive the error a while after causing it.
To debug your program, run it with the --sync command line
option to change this behavior. You can then get a meaningful
backtrace from your debugger if you break on the gdk_x_error() function.)
AL lib: ReleaseALC: 1 device not closed
If you wish to try the class for yourself it is trivial from this point to write a wxApp that uses a frame and reproduce the crash. Normally I would do this for you guys but I'm not too well so I'm going back to bed now /;
Any help would be appreciated.