Actually, when you call exit(), you implicitely close the connection to the X server : under Linux and Unices in general, open files and sockets are closed when the process quits (including segfault!). The X server will thus detect the connection break and clean all the ressources allocated to the client (windows, etc). From the client side, any allocated memory will be automagically freed in any case (using malloc()or new()), but third party ressources might not. This can be the case of a GL context, you can’t make any assumption on it.
That said, it is a good practice to clean ressources at exit. Your sequence is allright. If you encounter any bug (crap on the desktop, etc), this can never be a programming fault, this is the display driver’s. I encountered such bugs occasionnaly with the 2313 version, but it’s harmless (once filled up an entire virtual desktop with garbage for no reason). Use the ‘xrefresh’ command to force a desktop redraw in these cases.
also, when you click the close button in most window managers, what do they do to the window? i dont seem to be getting any unmap or destroy events when i click on the button.
This one is always disturbing . Window decorations are not handled by the X server, but by the window manager, which is no more that another X client. X has no idea of what’s happening around windows (that’s why you can see so weird window managers under Unix ) : the close, minimize, maximize, and whatever-fuzzy-option buttons are window-manager specific.
That said, there is a minimum standard across window managers. For instance, they all provide a close button, and a default behaviour of proposing to kill the client/connection associated to the window. To override this, you have to intercept a message that is not coming from the X server, but from the window manager. This is inter-client communication. More precisely, the protocol used by window managers is called ICCCM (see http://tronche.com/gui/x/ for the whole story).
Now, how it works ? You need to fetch two atoms (= server ‘globals’ shared by all its clients) :
Atom wm_protocol = XInternAtom (disp, “WM_PROTOCOLS”, False);
Atom wm_close = XInternAtom (disp, “WM_DELETE_WINDOW”, False);
Next we elect to receive the ‘close’ event from the WM:
XSetWMProtocols (disp, win, &wm_close, 1);
From this point, our window can receive special X events (client messages) from the window manager. Let’s handle it :
switch (event.any.type) {
case ClientMessage:
if ((event.xclient.message_type == wm_protocol) // OK, it’s comming from the WM
&& ((Atom)event.xclient.data.l[0] == wm_delete)) // This is a close event
{
…
}
}
When you elect to receive the close event, the window manager won’t display the default dialog (proposing to kill your client). It’s now up to your app to decide, ignoring the close button being a possible decision, but it’s driving users mad (you still have ‘xkill’ left).
Now you understand why people use toolkits under X. This hide a lot of tidbits and does the right thing without you even know how the whole thing works. I must say programming the GDI or X is almost the same experience regarding those complicated details, but X has a much cleaner and modular design (it’s running on a wealth of platform and has a bunch of implementation, all perfectly interchangeable !).
[This message has been edited by zerodeux (edited 12-10-2001).]