manages windows that exist before running.
This commit is contained in:
parent
24dd636f73
commit
c4a1fac49d
9 changed files with 57 additions and 33 deletions
|
@ -51,6 +51,7 @@ int OBDisplay::_xinerama_event_basep = 0;
|
|||
unsigned int OBDisplay::_mask_list[8];
|
||||
OBDisplay::ScreenInfoList OBDisplay::_screenInfoList;
|
||||
BGCCache *OBDisplay::_gccache = (BGCCache*) 0;
|
||||
int OBDisplay::_grab_count = 0;
|
||||
|
||||
|
||||
int OBDisplay::xerrorHandler(Display *d, XErrorEvent *e)
|
||||
|
@ -172,6 +173,21 @@ const ScreenInfo* OBDisplay::screenInfo(int snum) {
|
|||
}
|
||||
|
||||
|
||||
void OBDisplay::grab()
|
||||
{
|
||||
if (_grab_count == 0)
|
||||
XGrabServer(display);
|
||||
_grab_count++;
|
||||
}
|
||||
|
||||
|
||||
void OBDisplay::ungrab()
|
||||
{
|
||||
if (_grab_count == 0) return;
|
||||
_grab_count--;
|
||||
if (_grab_count == 0)
|
||||
XUngrabServer(display);
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -42,6 +42,9 @@ private:
|
|||
//! A list of all possible combinations of keyboard lock masks
|
||||
static unsigned int _mask_list[8];
|
||||
|
||||
//! The number of requested grabs on the display
|
||||
static int _grab_count;
|
||||
|
||||
//! A list of information for all screens on the display
|
||||
static ScreenInfoList _screenInfoList;
|
||||
|
||||
|
@ -94,7 +97,11 @@ public:
|
|||
//! Returns if the display has the xinerama extention available
|
||||
inline static bool xinerama() { return _xinerama; }
|
||||
|
||||
//! Grabs the display
|
||||
static void grab();
|
||||
|
||||
//! Ungrabs the display
|
||||
static void ungrab();
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -27,6 +27,8 @@ OBClient::OBClient(int screen, Window window)
|
|||
{
|
||||
assert(window);
|
||||
|
||||
ignore_unmaps = 0;
|
||||
|
||||
// update EVERYTHING the first time!!
|
||||
|
||||
// the state is kinda assumed to be normal. is this right? XXX
|
||||
|
|
|
@ -119,8 +119,10 @@ public:
|
|||
};
|
||||
|
||||
//! The event mask to grab on client windows
|
||||
static const long event_mask = PropertyChangeMask | FocusChangeMask |
|
||||
StructureNotifyMask;
|
||||
static const long event_mask = PropertyChangeMask | FocusChangeMask;
|
||||
|
||||
//! The number of unmap events to ignore on the window
|
||||
int ignore_unmaps;
|
||||
|
||||
private:
|
||||
//! The screen number on which the client resides
|
||||
|
|
15
src/frame.cc
15
src/frame.cc
|
@ -18,7 +18,7 @@ extern "C" {
|
|||
|
||||
namespace ob {
|
||||
|
||||
OBFrame::OBFrame(const OBClient *client, const otk::Style *style)
|
||||
OBFrame::OBFrame(OBClient *client, const otk::Style *style)
|
||||
: _client(client),
|
||||
_screen(otk::OBDisplay::screenInfo(client->screen()))
|
||||
{
|
||||
|
@ -392,28 +392,19 @@ void OBFrame::updateShape()
|
|||
void OBFrame::grabClient()
|
||||
{
|
||||
|
||||
XGrabServer(otk::OBDisplay::display);
|
||||
|
||||
// select the event mask on the frame
|
||||
XSelectInput(otk::OBDisplay::display, _window, SubstructureRedirectMask);
|
||||
//XSelectInput(otk::OBDisplay::display, _window, SubstructureRedirectMask);
|
||||
|
||||
// reparent the client to the frame
|
||||
XSelectInput(otk::OBDisplay::display, _client->window(),
|
||||
OBClient::event_mask & ~StructureNotifyMask);
|
||||
XReparentWindow(otk::OBDisplay::display, _client->window(), _window, 0, 0);
|
||||
XSelectInput(otk::OBDisplay::display, _client->window(),
|
||||
OBClient::event_mask);
|
||||
_client->ignore_unmaps++;
|
||||
|
||||
// raise the client above the frame
|
||||
//XRaiseWindow(otk::OBDisplay::display, _client->window());
|
||||
// map the client so it maps when the frame does
|
||||
XMapWindow(otk::OBDisplay::display, _client->window());
|
||||
|
||||
XUngrabServer(otk::OBDisplay::display);
|
||||
|
||||
update();
|
||||
|
||||
XMapWindow(otk::OBDisplay::display, _window);
|
||||
}
|
||||
|
||||
|
||||
|
|
|
@ -24,7 +24,7 @@ namespace ob {
|
|||
*/
|
||||
class OBFrame {
|
||||
private:
|
||||
const OBClient *_client;
|
||||
OBClient *_client;
|
||||
const otk::ScreenInfo *_screen;
|
||||
|
||||
//! The style to use for size and display the decorations
|
||||
|
@ -89,7 +89,7 @@ public:
|
|||
@param client The client window which will be decorated by the new OBFrame
|
||||
@param style The style to use to decorate the frame
|
||||
*/
|
||||
OBFrame(const OBClient *client, const otk::Style *style);
|
||||
OBFrame(OBClient *client, const otk::Style *style);
|
||||
//! Destroys the OBFrame object
|
||||
virtual ~OBFrame();
|
||||
|
||||
|
|
|
@ -101,7 +101,7 @@ OBScreen::~OBScreen()
|
|||
|
||||
// unmanage all windows
|
||||
while (!_clients.empty())
|
||||
unmanageWindow(_clients[0]);
|
||||
unmanageWindow(_clients.front());
|
||||
|
||||
delete _image_control;
|
||||
}
|
||||
|
@ -338,6 +338,8 @@ void OBScreen::manageWindow(Window window)
|
|||
XFree(wmhint);
|
||||
}
|
||||
|
||||
otk::OBDisplay::grab();
|
||||
|
||||
// choose the events we want to receive on the CLIENT window
|
||||
attrib_set.event_mask = OBClient::event_mask;
|
||||
attrib_set.do_not_propagate_mask = ButtonPressMask | ButtonReleaseMask |
|
||||
|
@ -362,7 +364,15 @@ void OBScreen::manageWindow(Window window)
|
|||
// create the decoration frame for the client window
|
||||
client->frame = new OBFrame(client, &_style);
|
||||
|
||||
// add all the client's decoration windows as event handlers for the client
|
||||
// XXX: if on the current desktop..
|
||||
XMapWindow(otk::OBDisplay::display, client->frame->window());
|
||||
|
||||
// XXX: handle any requested states such as shaded/maximized
|
||||
|
||||
otk::OBDisplay::ungrab();
|
||||
|
||||
// add all the client's windows as event handlers for the client
|
||||
Openbox::instance->addClient(window, client);
|
||||
Openbox::instance->addClient(client->frame->window(), client);
|
||||
Openbox::instance->addClient(client->frame->titlebar(), client);
|
||||
Openbox::instance->addClient(client->frame->buttonIconify(), client);
|
||||
|
@ -374,13 +384,9 @@ void OBScreen::manageWindow(Window window)
|
|||
Openbox::instance->addClient(client->frame->gripLeft(), client);
|
||||
Openbox::instance->addClient(client->frame->gripRight(), client);
|
||||
|
||||
// XXX: if on the current desktop..
|
||||
XMapWindow(otk::OBDisplay::display, client->frame->window());
|
||||
|
||||
// XXX: handle any requested states such as shaded/maximized
|
||||
|
||||
|
||||
// add to the screen's list
|
||||
_clients.push_back(client);
|
||||
// update the root properties
|
||||
setClientList();
|
||||
}
|
||||
|
||||
|
@ -420,14 +426,11 @@ void OBScreen::unmanageWindow(OBClient *client)
|
|||
delete client->frame;
|
||||
client->frame = 0;
|
||||
|
||||
ClientList::iterator it = _clients.begin(), end = _clients.end();
|
||||
for (; it != end; ++it)
|
||||
if (*it == client) {
|
||||
_clients.erase(it);
|
||||
break;
|
||||
}
|
||||
// remove from the screen's list
|
||||
_clients.remove(client);
|
||||
delete client;
|
||||
|
||||
// update the root properties
|
||||
setClientList();
|
||||
}
|
||||
|
||||
|
|
|
@ -29,7 +29,7 @@ class OBClient;
|
|||
class OBScreen {
|
||||
public:
|
||||
//! Holds a list of OBClient objects
|
||||
typedef std::vector<OBClient*> ClientList;
|
||||
typedef std::list<OBClient*> ClientList;
|
||||
//! Holds a list of otk::Strut objects
|
||||
typedef std::list<otk::Strut*> StrutList;
|
||||
|
||||
|
|
|
@ -232,7 +232,10 @@ void OBXEventHandler::unmapNotify(const XUnmapEvent &e)
|
|||
OBClient *client = Openbox::instance->findClient(e.window);
|
||||
if (!client) return;
|
||||
|
||||
Openbox::instance->screen(client->screen())->unmanageWindow(client);
|
||||
if (client->ignore_unmaps == 0)
|
||||
Openbox::instance->screen(client->screen())->unmanageWindow(client);
|
||||
else
|
||||
client->ignore_unmaps--;
|
||||
}
|
||||
|
||||
|
||||
|
|
Loading…
Reference in a new issue