all repos — openbox @ 89e6d5c0e64513d06ac4368981239de969a6fc9d

openbox fork - make it a bit more like ryudo

add/lower work
Dana Jansens danakj@orodu.net
commit

89e6d5c0e64513d06ac4368981239de969a6fc9d

parent

37c2e0f3296b4c1334ee92001c446d1bcc7665ee

M otk/otk_wrap.ccotk/otk_wrap.cc

@@ -13599,6 +13599,7 @@ { SWIG_PY_INT, (char *)"OBProperty_net_wm_action_maximize_vert", (long) otk::OBProperty::net_wm_action_maximize_vert, 0, 0, 0},

{ SWIG_PY_INT, (char *)"OBProperty_net_wm_action_change_desktop", (long) otk::OBProperty::net_wm_action_change_desktop, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_net_wm_action_close", (long) otk::OBProperty::net_wm_action_close, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_net_wm_state_modal", (long) otk::OBProperty::net_wm_state_modal, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBProperty_net_wm_state_sticky", (long) otk::OBProperty::net_wm_state_sticky, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_net_wm_state_maximized_vert", (long) otk::OBProperty::net_wm_state_maximized_vert, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_net_wm_state_maximized_horz", (long) otk::OBProperty::net_wm_state_maximized_horz, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_net_wm_state_shaded", (long) otk::OBProperty::net_wm_state_shaded, 0, 0, 0},

@@ -13606,7 +13607,8 @@ { SWIG_PY_INT, (char *)"OBProperty_net_wm_state_skip_taskbar", (long) otk::OBProperty::net_wm_state_skip_taskbar, 0, 0, 0},

{ SWIG_PY_INT, (char *)"OBProperty_net_wm_state_skip_pager", (long) otk::OBProperty::net_wm_state_skip_pager, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_net_wm_state_hidden", (long) otk::OBProperty::net_wm_state_hidden, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_net_wm_state_fullscreen", (long) otk::OBProperty::net_wm_state_fullscreen, 0, 0, 0}, -{ SWIG_PY_INT, (char *)"OBProperty_net_wm_state_floating", (long) otk::OBProperty::net_wm_state_floating, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBProperty_net_wm_state_above", (long) otk::OBProperty::net_wm_state_above, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBProperty_net_wm_state_below", (long) otk::OBProperty::net_wm_state_below, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_kde_net_system_tray_windows", (long) otk::OBProperty::kde_net_system_tray_windows, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_kde_net_wm_system_tray_window_for", (long) otk::OBProperty::kde_net_wm_system_tray_window_for, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBProperty_kde_net_wm_window_type_override", (long) otk::OBProperty::kde_net_wm_window_type_override, 0, 0, 0},
M otk/property.ccotk/property.cc

@@ -130,6 +130,7 @@ create("_NET_WM_ACTION_CHANGE_DESKTOP");

_atoms[net_wm_action_close] = create("_NET_WM_ACTION_CLOSE"); _atoms[net_wm_state_modal] = create("_NET_WM_STATE_MODAL"); + _atoms[net_wm_state_sticky] = create("_NET_WM_STATE_STICKY"); _atoms[net_wm_state_maximized_vert] = create("_NET_WM_STATE_MAXIMIZED_VERT"); _atoms[net_wm_state_maximized_horz] = create("_NET_WM_STATE_MAXIMIZED_HORZ"); _atoms[net_wm_state_shaded] = create("_NET_WM_STATE_SHADED");

@@ -137,7 +138,8 @@ _atoms[net_wm_state_skip_taskbar] = create("_NET_WM_STATE_SKIP_TASKBAR");

_atoms[net_wm_state_skip_pager] = create("_NET_WM_STATE_SKIP_PAGER"); _atoms[net_wm_state_hidden] = create("_NET_WM_STATE_HIDDEN"); _atoms[net_wm_state_fullscreen] = create("_NET_WM_STATE_FULLSCREEN"); - _atoms[net_wm_state_floating] = create("_NET_WM_STATE_FLOATING"); + _atoms[net_wm_state_above] = create("_NET_WM_STATE_ABOVE"); + _atoms[net_wm_state_below] = create("_NET_WM_STATE_BELOW"); _atoms[kde_net_system_tray_windows] = create("_KDE_NET_SYSTEM_TRAY_WINDOWS"); _atoms[kde_net_wm_system_tray_window_for] =
M otk/property.hhotk/property.hh

@@ -127,6 +127,7 @@ net_wm_action_change_desktop,

net_wm_action_close, net_wm_state_modal, + net_wm_state_sticky, net_wm_state_maximized_vert, net_wm_state_maximized_horz, net_wm_state_shaded,

@@ -134,7 +135,8 @@ net_wm_state_skip_taskbar,

net_wm_state_skip_pager, net_wm_state_hidden, net_wm_state_fullscreen, - net_wm_state_floating, + net_wm_state_above, + net_wm_state_below, kde_net_system_tray_windows, kde_net_wm_system_tray_window_for,
M scripts/builtins.pyscripts/builtins.py

@@ -60,3 +60,18 @@ data.press_clientheight() + dy);

def execute(bin, screen = 0): Openbox_execute(openbox, screen, bin) + +def toggle_shade(data): + print "toggle_shade" + +def raise_win(data): + client = Openbox_findClient(openbox, data.window()) + if not client: return + screen = Openbox_screen(openbox, OBClient_screen(client)) + OBScreen_raise(screen, client) + +def lower_win(data): + client = Openbox_findClient(openbox, data.window()) + if not client: return + screen = Openbox_screen(openbox, OBClient_screen(client)) + OBScreen_lower(screen, client)
M src/client.ccsrc/client.cc

@@ -37,7 +37,7 @@

// update EVERYTHING the first time!! // the state is kinda assumed to be normal. is this right? XXX - _wmstate = NormalState; + _wmstate = NormalState; _iconic = false; // no default decors or functions, each has to be enabled _decorations = _functions = 0; // start unfocused

@@ -91,53 +91,7 @@ updateTitle();

updateIconTitle(); updateClass(); -/* -#ifdef DEBUG - printf("Mapped window: 0x%lx\n" - " title: \t%s\t icon title: \t%s\n" - " app name: \t%s\t\t class: \t%s\n" - " position: \t%d, %d\t\t size: \t%d, %d\n" - " desktop: \t%lu\t\t group: \t0x%lx\n" - " type: \t%d\t\t min size \t%d, %d\n" - " base size \t%d, %d\t\t max size \t%d, %d\n" - " size incr \t%d, %d\t\t gravity \t%d\n" - " wm state \t%ld\t\t can be focused:\t%s\n" - " notify focus: \t%s\t\t urgent: \t%s\n" - " shaped: \t%s\t\t modal: \t%s\n" - " shaded: \t%s\t\t iconic: \t%s\n" - " vert maximized:\t%s\t\t horz maximized:\t%s\n" - " fullscreen: \t%s\t\t floating: \t%s\n" - " requested pos: \t%s\n", - _window, - _title.c_str(), - _icon_title.c_str(), - _app_name.c_str(), - _app_class.c_str(), - _area.x(), _area.y(), - _area.width(), _area.height(), - _desktop, - _group, - _type, - _min_x, _min_y, - _base_x, _base_y, - _max_x, _max_y, - _inc_x, _inc_y, - _gravity, - _wmstate, - _can_focus ? "yes" : "no", - _focus_notify ? "yes" : "no", - _urgent ? "yes" : "no", - _shaped ? "yes" : "no", - _modal ? "yes" : "no", - _shaded ? "yes" : "no", - _iconic ? "yes" : "no", - _max_vert ? "yes" : "no", - _max_horz ? "yes" : "no", - _fullscreen ? "yes" : "no", - _floating ? "yes" : "no", - _positioned ? "yes" : "no"); -#endif -*/ + calcLayer(); }

@@ -295,7 +249,8 @@ void OBClient::getState()

{ const otk::OBProperty *property = Openbox::instance->property(); - _modal = _shaded = _max_horz = _max_vert = _fullscreen = _floating = false; + _modal = _shaded = _max_horz = _max_vert = _fullscreen = _above = _below = + false; unsigned long *state; unsigned long num = (unsigned) -1;

@@ -317,6 +272,12 @@ _max_vert = true;

else if (state[i] == property->atom(otk::OBProperty::net_wm_state_maximized_horz)) _max_horz = true; + else if (state[i] == + property->atom(otk::OBProperty::net_wm_state_above)) + _above = true; + else if (state[i] == + property->atom(otk::OBProperty::net_wm_state_below)) + _below = true; } delete [] state;

@@ -340,6 +301,17 @@ &foo, &ufoo, &ufoo, &foo, &foo, &foo, &ufoo, &ufoo);

_shaped = (s != 0); } #endif // SHAPE +} + + +void OBClient::calcLayer() { + if (_iconic) _layer = OBScreen::Layer_Icon; + else if (_type == Type_Desktop) _layer = OBScreen::Layer_Desktop; + else if (_type == Type_Dock) _layer = OBScreen::Layer_Top; + else if (_fullscreen) _layer = OBScreen::Layer_Fullscreen; + else if (_above) _layer = OBScreen::Layer_Above; + else if (_below) _layer = OBScreen::Layer_Below; + else _layer = OBScreen::Layer_Normal; }

@@ -596,8 +568,10 @@ action = _shaded ? State_Remove : State_Add;

else if (state == property->atom(otk::OBProperty::net_wm_state_fullscreen)) action = _fullscreen ? State_Remove : State_Add; - else if (state == property->atom(otk::OBProperty::net_wm_state_floating)) - action = _floating ? State_Remove : State_Add; + else if (state == property->atom(otk::OBProperty::net_wm_state_above)) + action = _above ? State_Remove : State_Add; + else if (state == property->atom(otk::OBProperty::net_wm_state_below)) + action = _below ? State_Remove : State_Add; } if (action == State_Add) {

@@ -626,10 +600,15 @@ if (_fullscreen) continue;

_fullscreen = true; // XXX: raise the window n shit } else if (state == - property->atom(otk::OBProperty::net_wm_state_floating)) { - if (_floating) continue; - _floating = true; + property->atom(otk::OBProperty::net_wm_state_above)) { + if (_above) continue; + _above = true; // XXX: raise the window n shit + } else if (state == + property->atom(otk::OBProperty::net_wm_state_below)) { + if (_below) continue; + _below = true; + // XXX: lower the window n shit } } else { // action == State_Remove

@@ -657,13 +636,20 @@ if (!_fullscreen) continue;

_fullscreen = false; // XXX: lower the window to its proper layer } else if (state == - property->atom(otk::OBProperty::net_wm_state_floating)) { - if (!_floating) continue; - _floating = false; + property->atom(otk::OBProperty::net_wm_state_above)) { + if (!_above) continue; + _above = false; // XXX: lower the window to its proper layer + } else if (state == + property->atom(otk::OBProperty::net_wm_state_below)) { + if (!_below) continue; + _below = false; + // XXX: raise the window to its proper layer } } } + calcLayer(); + Openbox::instance->screen(_screen)->raise(this); }

@@ -928,7 +914,7 @@

if (e.value_mask & CWBorderWidth) _border_width = e.border_width; - // resize, then move, as specified in the EWMH section 7.7 + // resize, then move, as specified in the EWMH section 7.7 if (e.value_mask & (CWWidth | CWHeight)) { int w = (e.value_mask & CWWidth) ? e.width : _area.width(); int h = (e.value_mask & CWHeight) ? e.height : _area.height();
M src/client.hhsrc/client.hh

@@ -17,11 +17,12 @@ }

#include <string> +#include "screen.hh" +#include "widget.hh" #include "otk/point.hh" #include "otk/strut.hh" #include "otk/rect.hh" #include "otk/eventhandler.hh" -#include "widget.hh" namespace ob {

@@ -254,7 +255,11 @@ bool _max_horz;

//! The window is a 'fullscreen' window, and should be on top of all others bool _fullscreen; //! The window should be on top of other windows of the same type - bool _floating; + bool _above; + //! The window should be underneath other windows of the same type + bool _below; + + OBScreen::StackLayer _layer; //! A bitmask of values in the OBClient::Decoration enum /*!

@@ -292,6 +297,9 @@ //! Sends the window to the specified desktop

void setDesktop(long desktop); //! Adjusts the window's net_state void setState(StateAction action, long data1, long data2); + + //! Calculates the stacking layer for the client window + void calcLayer(); //! Update the protocols that the window supports and adjusts things if they //! change

@@ -396,17 +404,8 @@ //! Returns if the window is maximized vertically

inline bool maxVert() const { return _max_vert; } //! Returns if the window is maximized horizontally inline bool maxHorz() const { return _max_horz; } - //! Returns if the window is fullscreen - /*! - When the window is fullscreen, it is kept above all others - */ - inline bool fullscreen() const { return _fullscreen; } - //! Returns if the window is floating - /*! - When the window is floating, it is kept above all others in the same - stacking layer as it - */ - inline bool floating() const { return _floating; } + //! Returns the window's stacking layer + inline OBScreen::StackLayer layer() const { return _layer; } //! Removes or reapplies the client's border to its window /*!
M src/openbox_wrap.ccsrc/openbox_wrap.cc

@@ -1560,6 +1560,44 @@ return NULL;

} +static PyObject *_wrap_OBScreen_raise(PyObject *self, PyObject *args) { + PyObject *resultobj; + ob::OBScreen *arg1 = (ob::OBScreen *) 0 ; + ob::OBClient *arg2 = (ob::OBClient *) 0 ; + PyObject * obj0 = 0 ; + PyObject * obj1 = 0 ; + + if(!PyArg_ParseTuple(args,(char *)"OO:OBScreen_raise",&obj0,&obj1)) goto fail; + if ((SWIG_ConvertPtr(obj0,(void **) &arg1, SWIGTYPE_p_ob__OBScreen,SWIG_POINTER_EXCEPTION | 0 )) == -1) SWIG_fail; + if ((SWIG_ConvertPtr(obj1,(void **) &arg2, SWIGTYPE_p_ob__OBClient,SWIG_POINTER_EXCEPTION | 0 )) == -1) SWIG_fail; + (arg1)->raise(arg2); + + Py_INCREF(Py_None); resultobj = Py_None; + return resultobj; + fail: + return NULL; +} + + +static PyObject *_wrap_OBScreen_lower(PyObject *self, PyObject *args) { + PyObject *resultobj; + ob::OBScreen *arg1 = (ob::OBScreen *) 0 ; + ob::OBClient *arg2 = (ob::OBClient *) 0 ; + PyObject * obj0 = 0 ; + PyObject * obj1 = 0 ; + + if(!PyArg_ParseTuple(args,(char *)"OO:OBScreen_lower",&obj0,&obj1)) goto fail; + if ((SWIG_ConvertPtr(obj0,(void **) &arg1, SWIGTYPE_p_ob__OBScreen,SWIG_POINTER_EXCEPTION | 0 )) == -1) SWIG_fail; + if ((SWIG_ConvertPtr(obj1,(void **) &arg2, SWIGTYPE_p_ob__OBClient,SWIG_POINTER_EXCEPTION | 0 )) == -1) SWIG_fail; + (arg1)->lower(arg2); + + Py_INCREF(Py_None); resultobj = Py_None; + return resultobj; + fail: + return NULL; +} + + static PyObject * OBScreen_swigregister(PyObject *self, PyObject *args) { PyObject *obj; if (!PyArg_ParseTuple(args,(char*)"O", &obj)) return NULL;

@@ -2132,32 +2170,15 @@ return NULL;

} -static PyObject *_wrap_OBClient_fullscreen(PyObject *self, PyObject *args) { +static PyObject *_wrap_OBClient_layer(PyObject *self, PyObject *args) { PyObject *resultobj; ob::OBClient *arg1 = (ob::OBClient *) 0 ; - bool result; - PyObject * obj0 = 0 ; - - if(!PyArg_ParseTuple(args,(char *)"O:OBClient_fullscreen",&obj0)) goto fail; - if ((SWIG_ConvertPtr(obj0,(void **) &arg1, SWIGTYPE_p_ob__OBClient,SWIG_POINTER_EXCEPTION | 0 )) == -1) SWIG_fail; - result = (bool)((ob::OBClient const *)arg1)->fullscreen(); - - resultobj = PyInt_FromLong((long)result); - return resultobj; - fail: - return NULL; -} - - -static PyObject *_wrap_OBClient_floating(PyObject *self, PyObject *args) { - PyObject *resultobj; - ob::OBClient *arg1 = (ob::OBClient *) 0 ; - bool result; + int result; PyObject * obj0 = 0 ; - if(!PyArg_ParseTuple(args,(char *)"O:OBClient_floating",&obj0)) goto fail; + if(!PyArg_ParseTuple(args,(char *)"O:OBClient_layer",&obj0)) goto fail; if ((SWIG_ConvertPtr(obj0,(void **) &arg1, SWIGTYPE_p_ob__OBClient,SWIG_POINTER_EXCEPTION | 0 )) == -1) SWIG_fail; - result = (bool)((ob::OBClient const *)arg1)->floating(); + result = (int)((ob::OBClient const *)arg1)->layer(); resultobj = PyInt_FromLong((long)result); return resultobj;

@@ -2646,6 +2667,8 @@ { (char *)"OBScreen_removeStrut", _wrap_OBScreen_removeStrut, METH_VARARGS },

{ (char *)"OBScreen_manageExisting", _wrap_OBScreen_manageExisting, METH_VARARGS }, { (char *)"OBScreen_manageWindow", _wrap_OBScreen_manageWindow, METH_VARARGS }, { (char *)"OBScreen_unmanageWindow", _wrap_OBScreen_unmanageWindow, METH_VARARGS }, + { (char *)"OBScreen_raise", _wrap_OBScreen_raise, METH_VARARGS }, + { (char *)"OBScreen_lower", _wrap_OBScreen_lower, METH_VARARGS }, { (char *)"OBScreen_swigregister", OBScreen_swigregister, METH_VARARGS }, { (char *)"MwmHints_flags_set", _wrap_MwmHints_flags_set, METH_VARARGS }, { (char *)"MwmHints_flags_get", _wrap_MwmHints_flags_get, METH_VARARGS },

@@ -2679,8 +2702,7 @@ { (char *)"OBClient_shaded", _wrap_OBClient_shaded, METH_VARARGS },

{ (char *)"OBClient_iconic", _wrap_OBClient_iconic, METH_VARARGS }, { (char *)"OBClient_maxVert", _wrap_OBClient_maxVert, METH_VARARGS }, { (char *)"OBClient_maxHorz", _wrap_OBClient_maxHorz, METH_VARARGS }, - { (char *)"OBClient_fullscreen", _wrap_OBClient_fullscreen, METH_VARARGS }, - { (char *)"OBClient_floating", _wrap_OBClient_floating, METH_VARARGS }, + { (char *)"OBClient_layer", _wrap_OBClient_layer, METH_VARARGS }, { (char *)"OBClient_toggleClientBorder", _wrap_OBClient_toggleClientBorder, METH_VARARGS }, { (char *)"OBClient_area", _wrap_OBClient_area, METH_VARARGS }, { (char *)"OBClient_move", _wrap_OBClient_move, METH_VARARGS },

@@ -2789,6 +2811,15 @@ { SWIG_PY_INT, (char *)"Openbox_State_Starting", (long) ob::Openbox::State_Starting, 0, 0, 0},

{ SWIG_PY_INT, (char *)"Openbox_State_Normal", (long) ob::Openbox::State_Normal, 0, 0, 0}, { SWIG_PY_INT, (char *)"Openbox_State_Exiting", (long) ob::Openbox::State_Exiting, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBScreen_event_mask", (long) ob::OBScreen::event_mask, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_Layer_Icon", (long) ob::OBScreen::Layer_Icon, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_Layer_Desktop", (long) ob::OBScreen::Layer_Desktop, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_Layer_Below", (long) ob::OBScreen::Layer_Below, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_Layer_Normal", (long) ob::OBScreen::Layer_Normal, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_Layer_Above", (long) ob::OBScreen::Layer_Above, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_Layer_Top", (long) ob::OBScreen::Layer_Top, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_Layer_Fullscreen", (long) ob::OBScreen::Layer_Fullscreen, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_Layer_Internal", (long) ob::OBScreen::Layer_Internal, 0, 0, 0}, +{ SWIG_PY_INT, (char *)"OBScreen_NUM_LAYERS", (long) ob::OBScreen::NUM_LAYERS, 0, 0, 0}, { SWIG_PY_INT, (char *)"MwmHints_elements", (long) ob::MwmHints::elements, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBClient_TopLeft", (long) ob::OBClient::TopLeft, 0, 0, 0}, { SWIG_PY_INT, (char *)"OBClient_TopRight", (long) ob::OBClient::TopRight, 0, 0, 0},
M src/screen.ccsrc/screen.cc

@@ -26,6 +26,8 @@ #include "bindings.hh"

#include "python.hh" #include "otk/display.hh" +#include <vector> + static bool running; static int anotherWMRunning(Display *display, XErrorEvent *) { printf(_("Another window manager already running on display %s.\n"),

@@ -87,7 +89,7 @@ ::exit(1);

} } _style.load(sconfig); - + // Set the netwm atoms for geomtery and viewport unsigned long geometry[] = { _info->width(), _info->height() };

@@ -402,6 +404,9 @@ otk::OBDisplay::ungrab();

// add to the screen's list clients.push_back(client); + // this puts into the stacking order, then raises it + _stacking.push_back(client); + raise(client); // update the root properties setClientList();

@@ -447,12 +452,65 @@

delete client->frame; client->frame = 0; - // remove from the screen's list + // remove from the screen's lists + _stacking.remove(client); clients.remove(client); delete client; // update the root properties setClientList(); +} + +void OBScreen::raise(OBClient *client) +{ + const int layer = client->layer(); + std::vector<Window> wins; + + _stacking.remove(client); + + // the stacking list is from highest to lowest + + ClientList::iterator it = _stacking.begin(), end = _stacking.end(); + // insert the windows above this window + for (; it != end; ++it) { + if ((*it)->layer() <= layer) + break; + wins.push_back((*it)->frame->window()); + } + // insert our client + wins.push_back(client->frame->window()); + _stacking.insert(it, client); + // insert the remaining below this window + for (; it != end; ++it) + wins.push_back((*it)->frame->window()); + + XRestackWindows(otk::OBDisplay::display, &wins[0], wins.size()); +} + +void OBScreen::lower(OBClient *client) +{ + const int layer = client->layer(); + std::vector<Window> wins; + + _stacking.remove(client); + + // the stacking list is from highest to lowest + + ClientList::iterator it = _stacking.begin(), end = _stacking.end(); + // insert the windows above this window + for (; it != end; ++it) { + if ((*it)->layer() < layer) + break; + wins.push_back((*it)->frame->window()); + } + // insert our client + wins.push_back(client->frame->window()); + _stacking.insert(it, client); + // insert the remaining below this window + for (; it != end; ++it) + wins.push_back((*it)->frame->window()); + + XRestackWindows(otk::OBDisplay::display, &wins[0], wins.size()); } }
M src/screen.hhsrc/screen.hh

@@ -43,7 +43,19 @@ SubstructureRedirectMask |

ButtonPressMask | ButtonReleaseMask; - //! All managed clients on the screen + enum StackLayer { + Layer_Icon, // 0 - iconified windows, in any order at all + Layer_Desktop, // 1 - desktop windows + Layer_Below, // 2 - normal windows w/ below + Layer_Normal, // 3 - normal windows + Layer_Above, // 4 - normal windows w/ above + Layer_Top, // 5 - always-on-top-windows (docks?) + Layer_Fullscreen, // 6 - fullscreeen windows + Layer_Internal, // 7 - openbox windows/menus + NUM_LAYERS + }; + + //! All managed clients on the screen (in order of being mapped) ClientList clients; private:

@@ -76,7 +88,9 @@ StrutList _struts;

//! An offscreen window which gets focus when nothing else has it Window _focuswindow; - + + //! A list of all managed clients on the screen, in their stacking order + ClientList _stacking; //! Calculate the OBScreen::_area member void calcArea();

@@ -96,7 +110,7 @@ /*!

Set the _NET_WORKAREA root window property. */ void setWorkArea(); - + public: #ifndef SWIG //! Constructs a new OBScreen object

@@ -138,6 +152,12 @@ This removes the window's frame, reparents it to root, unselects events on

it, etc. */ void unmanageWindow(OBClient *client); + + //! Raises a client window above all others in its stacking layer + void raise(OBClient *client); + + //! Lowers a client window below all others in its stacking layer + void lower(OBClient *client); }; }