From 97f7c3e1b59b9a94e36a78d97c141f6a05f43e20 Mon Sep 17 00:00:00 2001 From: markt Date: Mon, 5 Nov 2007 17:05:58 +0000 Subject: various refactoring and minor changes --- src/Ewmh.cc | 126 ++++++++++++++++------------------------------------ src/FocusControl.cc | 35 +++++---------- src/Focusable.hh | 14 ++++++ src/Keys.cc | 5 +++ src/WinClient.cc | 100 ++++++++--------------------------------- src/WinClient.hh | 18 +++----- src/Window.cc | 116 +++++++++++++++++++++++++++++++++-------------- src/Window.hh | 2 + src/WorkspaceCmd.cc | 9 ++-- 9 files changed, 182 insertions(+), 243 deletions(-) diff --git a/src/Ewmh.cc b/src/Ewmh.cc index 5483b8e..3e01e36 100644 --- a/src/Ewmh.cc +++ b/src/Ewmh.cc @@ -214,19 +214,9 @@ void Ewmh::setupClient(WinClient &winclient) { updateStrut(winclient); FbTk::FbString newtitle = winclient.textProperty(m_net_wm_name); - if (!newtitle.empty()) { + if (!newtitle.empty()) winclient.setTitle(newtitle); - } - newtitle = winclient.textProperty(m_net_wm_icon_name); - if (!newtitle.empty()) { - winclient.setIconTitle(newtitle); - } - - if ( winclient.fbwindow() ) - winclient.fbwindow()->titleSig().notify(); -} -void Ewmh::setupFrame(FluxboxWindow &win) { Atom ret_type; int fmt; unsigned long nitems, bytes_after; @@ -248,95 +238,59 @@ void Ewmh::setupFrame(FluxboxWindow &win) { * */ - win.winClient().property(m_net_wm_window_type, 0, 0x7fffffff, False, XA_ATOM, - &ret_type, &fmt, &nitems, &bytes_after, - &data); + winclient.property(m_net_wm_window_type, 0, 0x7fffffff, False, XA_ATOM, + &ret_type, &fmt, &nitems, &bytes_after, + &data); + Focusable::WindowType type = Focusable::TYPE_NORMAL; if (data) { Atom *atoms = (unsigned long *)data; for (unsigned long l = 0; l < nitems; ++l) { - /* From Extended Window Manager Hints, draft 1.3: - * - * _NET_WM_WINDOW_TYPE_DOCK indicates a dock or panel feature. - * Typically a Window Manager would keep such windows on top - * of all other windows. - * + if (atoms[l] == m_net_wm_window_type_dock) + type = Focusable::TYPE_DOCK; + else if (atoms[l] == m_net_wm_window_type_desktop) + type = Focusable::TYPE_DESKTOP; + else if (atoms[l] == m_net_wm_window_type_splash) + type = Focusable::TYPE_SPLASH; + else if (atoms[l] == m_net_wm_window_type_dialog) + type = Focusable::TYPE_DIALOG; + else if (atoms[l] == m_net_wm_window_type_menu) + type = Focusable::TYPE_MENU; + else if (atoms[l] == m_net_wm_window_type_toolbar) + type = Focusable::TYPE_TOOLBAR; + else if (atoms[l] != m_net_wm_window_type_normal) + continue; + /* + * NOT YET IMPLEMENTED: + * _NET_WM_WINDOW_TYPE_UTILITY */ - if (atoms[l] == m_net_wm_window_type_dock) { - // we also assume it shouldn't be visible in any toolbar - win.setFocusHidden(true); - win.setIconHidden(true); - win.setDecorationMask(FluxboxWindow::DECOR_NONE); - win.moveToLayer(Layer::DOCK); - } else if (atoms[l] == m_net_wm_window_type_desktop) { - /* - * _NET_WM_WINDOW_TYPE_DESKTOP indicates a "false desktop" window - * We let it be the size it wants, but it gets no decoration, - * is hidden in the toolbar and window cycling list, plus - * windows don't tab with it and is right on the bottom. - */ - - win.setFocusHidden(true); - win.setIconHidden(true); - win.moveToLayer(Layer::DESKTOP); - win.setDecorationMask(FluxboxWindow::DECOR_NONE); - win.setTabable(false); - win.setMovable(false); - win.setResizable(false); - win.stick(); - - } else if (atoms[l] == m_net_wm_window_type_splash) { - /* - * _NET_WM_WINDOW_TYPE_SPLASH indicates that the - * window is a splash screen displayed as an application - * is starting up. - */ - win.setDecorationMask(FluxboxWindow::DECOR_NONE); - win.setFocusHidden(true); - win.setIconHidden(true); - win.setMovable(false); - } else if (atoms[l] == m_net_wm_window_type_normal) { - // do nothing, this is ..normal.. - } else if (atoms[l] == m_net_wm_window_type_dialog) { - // dialog windows should not be tabable - win.setTabable(false); - } else if (atoms[l] == m_net_wm_window_type_menu) { - /* - * _NET_WM_WINDOW_TYPE_TOOLBAR and _NET_WM_WINDOW_TYPE_MENU - * indicate toolbar and pinnable menu windows, respectively - * (i.e. toolbars and menus "torn off" from the main - * application). Windows of this type may set the - * WM_TRANSIENT_FOR hint indicating the main application window. - */ - win.setDecorationMask(FluxboxWindow::DECOR_TOOL); - win.setIconHidden(true); - win.moveToLayer(Layer::ABOVE_DOCK); - } else if (atoms[l] == m_net_wm_window_type_toolbar) { - win.setDecorationMask(FluxboxWindow::DECOR_NONE); - win.setIconHidden(true); - win.moveToLayer(Layer::ABOVE_DOCK); - } + break; } XFree(data); - } else { + } else if (winclient.isTransient()) { // if _NET_WM_WINDOW_TYPE not set and this window // has transient_for the type must be set to _NET_WM_WINDOW_TYPE_DIALOG - if ( win.winClient().isTransient() ) { - win.winClient(). + if (winclient.isTransient()) { + type = Focusable::TYPE_DIALOG; + winclient. changeProperty(m_net_wm_window_type, XA_ATOM, 32, PropModeReplace, (unsigned char*)&m_net_wm_window_type_dialog, 1); - // and then we should treat it like a dialog - win.setTabable(false); + } } + winclient.setWindowType(type); - /* - * NOT YET IMPLEMENTED: - * _NET_WM_WINDOW_TYPE_UTILITY - */ +} + +void Ewmh::setupFrame(FluxboxWindow &win) { setupState(win); + Atom ret_type; + int fmt; + unsigned long nitems, bytes_after; + unsigned char *data = 0; + if (win.winClient().property(m_net_wm_desktop, 0, 1, False, XA_CARDINAL, &ret_type, &fmt, &nitems, &bytes_after, (unsigned char **) &data) && data) { @@ -929,11 +883,7 @@ bool Ewmh::propertyNotify(WinClient &winclient, Atom the_property) { winclient.fbwindow()->titleSig().notify(); return true; } else if (the_property == m_net_wm_icon_name) { - FbTk::FbString newtitle = winclient.textProperty(the_property); - if (!newtitle.empty()) - winclient.setIconTitle(newtitle); - if (winclient.fbwindow()) - winclient.fbwindow()->titleSig().notify(); + // we don't use icon title, since we don't show icons return true; } diff --git a/src/FocusControl.cc b/src/FocusControl.cc index 0893d68..4aa896b 100644 --- a/src/FocusControl.cc +++ b/src/FocusControl.cc @@ -167,32 +167,17 @@ void FocusControl::cycleFocus(const Focusables &window_list, void FocusControl::goToWindowNumber(const Focusables &winlist, int num, const ClientPattern *pat) { - Focusable *last_matched = 0; - if (num > 0) { - Focusables::const_iterator it = winlist.begin(); - Focusables::const_iterator it_end = winlist.end(); - for (; it != it_end; ++it) { - if (!doSkipWindow(**it, pat) && (*it)->acceptsFocus()) { - --num; - last_matched = *it; - if (!num) break; + Focusables::const_iterator it = winlist.begin(); + Focusables::const_iterator it_end = winlist.end(); + for (; it != it_end && num; ++it) { + if (!doSkipWindow(**it, pat) && (*it)->acceptsFocus()) { + num > 0 ? --num : ++num; + if (!num) { + (*it)->focus(); + if ((*it)->fbwindow()) + (*it)->fbwindow()->raise(); } } - } else if (num < 0) { - Focusables::const_reverse_iterator it = winlist.rbegin(); - Focusables::const_reverse_iterator it_end = winlist.rend(); - for (; it != it_end; ++it) { - if (!doSkipWindow(**it, pat) && (*it)->acceptsFocus()) { - ++num; - last_matched = *it; - if (!num) break; - } - } - } - if (last_matched) { - last_matched->focus(); - if (last_matched->fbwindow()) - last_matched->fbwindow()->raise(); } } @@ -371,7 +356,7 @@ void FocusControl::dirFocus(FluxboxWindow &win, FocusDir dir) { if ((*it) == &win || (*it)->isIconic() || (*it)->isFocusHidden() - || !(*it)->winClient().acceptsFocus()) + || !(*it)->acceptsFocus()) continue; // skip self // we check things against an edge, and within the bounds (draw a picture) diff --git a/src/Focusable.hh b/src/Focusable.hh index cd2ad49..3903e25 100644 --- a/src/Focusable.hh +++ b/src/Focusable.hh @@ -46,6 +46,17 @@ public: m_titlesig(*this), m_focussig(*this), m_diesig(*this), m_attentionsig(*this) { } virtual ~Focusable() { } + + enum WindowType { + TYPE_NORMAL, + TYPE_DOCK, + TYPE_DESKTOP, + TYPE_SPLASH, + TYPE_DIALOG, + TYPE_MENU, + TYPE_TOOLBAR + }; + /** * Take focus. * @return true if the focuable took focus @@ -87,6 +98,9 @@ public: /// @return wm role string (for pattern matching) virtual std::string getWMRole() const { return "Focusable"; } + /// @return window type + virtual WindowType getWindowType() const { return TYPE_NORMAL; } + /// @return whether this window is a transient (for pattern matching) virtual bool isTransient() const { return false; } diff --git a/src/Keys.cc b/src/Keys.cc index 34d5cc0..6a4406a 100644 --- a/src/Keys.cc +++ b/src/Keys.cc @@ -390,6 +390,11 @@ bool Keys::doAction(int type, unsigned int mods, unsigned int key, // grab "None Escape" to exit keychain in the middle unsigned int esc = FbTk::KeyUtil::getKey("Escape"); + // if focus changes, windows will get NotifyWhileGrabbed, + // which they tend to ignore + if (temp_key && type == KeyPress) + XUngrabKeyboard(Fluxbox::instance()->display(), CurrentTime); + if (temp_key && !temp_key->keylist.empty()) { // emacs-style if (!saved_keymode) saved_keymode = m_keylist; diff --git a/src/WinClient.cc b/src/WinClient.cc index 99264d2..83637e2 100644 --- a/src/WinClient.cc +++ b/src/WinClient.cc @@ -79,13 +79,13 @@ WinClient::WinClient(Window win, BScreen &screen, FluxboxWindow *fbwin): wm_hint_flags(0), m_modal_count(0), m_modal(false), + accepts_input(false), send_focus_message(false), send_close_message(false), m_win_gravity(0), m_title_override(false), - m_icon_title_override(false), + m_window_type(Focusable::TYPE_NORMAL), m_mwm_hint(0), - m_focus_mode(F_PASSIVE), m_strut(0) { updateWMProtocols(); updateMWMHints(); @@ -93,7 +93,6 @@ WinClient::WinClient(Window win, BScreen &screen, FluxboxWindow *fbwin): updateWMNormalHints(); updateWMClassHint(); updateTitle(); - updateIconTitle(); Fluxbox::instance()->saveWindowSearch(win, this); if (window_group != None) Fluxbox::instance()->saveGroupSearch(window_group, this); @@ -167,11 +166,17 @@ WinClient::~WinClient() { } bool WinClient::acceptsFocus() const { - return (m_focus_mode == F_LOCALLYACTIVE || - m_focus_mode == F_PASSIVE); + return ((accepts_input || send_focus_message) && + // focusing fbpanel messes up quite a few things + m_window_type != Focusable::TYPE_DOCK && + m_window_type != Focusable::TYPE_SPLASH); } bool WinClient::sendFocus() { + if (accepts_input) { + setInputFocus(RevertToParent, CurrentTime); + return true; + } if (!send_focus_message) return false; #ifdef DEBUG @@ -236,12 +241,6 @@ string WinClient::getWMRole() const { return textProperty(wm_role); } -const string &WinClient::title() const { - if (!fbwindow() || !fbwindow()->isIconic() || m_icon_title.empty()) - return m_title; - return m_icon_title; -} - void WinClient::updateWMClassHint() { XClassHint ch; if (XGetClassHint(display(), window(), &ch) == 0) { @@ -369,48 +368,6 @@ void WinClient::setTitle(FbTk::FbString &title) { fbwindow()->updateTitleFromClient(*this); } -void WinClient::setIconTitle(FbTk::FbString &icon_title) { - m_icon_title = icon_title; - m_icon_title_override = true; - if (fbwindow() && fbwindow()->isIconic()) - fbwindow()->updateTitleFromClient(*this); -} - -void WinClient::updateIconTitle() { - if (m_icon_title_override) - return; - - XTextProperty text_prop; - char **list = 0; - int num = 0; - - if (getWMIconName(text_prop)) { - if (text_prop.value && text_prop.nitems > 0) { - if (text_prop.encoding != XA_STRING) { - text_prop.nitems = strlen((char *) text_prop.value); - XmbTextPropertyToTextList(display(), &text_prop, &list, &num); - - if (num > 0 && list) - m_icon_title = (char *)*list; - else - m_icon_title = text_prop.value ? (char *)text_prop.value : ""; - if (list) - XFreeStringList(list); - - } else - m_icon_title = text_prop.value ? (char *)text_prop.value : ""; - - if (text_prop.value) - XFree((char *) text_prop.value); - } else - m_icon_title = ""; - } else - m_icon_title = ""; - - if (fbwindow() && fbwindow()->isIconic()) - fbwindow()->updateTitleFromClient(*this); -} - void WinClient::saveBlackboxAttribs(FluxboxWindow::BlackboxAttributes &blackbox_attribs) { changeProperty(FbAtoms::instance()->getFluxboxAttributesAtom(), XA_CARDINAL, 32, PropModeReplace, @@ -450,11 +407,10 @@ void WinClient::updateMWMHints() { void WinClient::updateWMHints() { XWMHints *wmhint = XGetWMHints(display(), window()); - if (! wmhint) { - m_focus_mode = F_PASSIVE; - window_group = None; - initial_state = NormalState; - } else { + accepts_input = true; + window_group = None; + initial_state = NormalState; + if (wmhint) { wm_hint_flags = wmhint->flags; /* * ICCCM 4.1.7 @@ -467,34 +423,16 @@ void WinClient::updateWMHints() { * Globally Active False Present *--------------------------------------------- * Here: WM_TAKE_FOCUS = send_focus_message - * Input Field = wmhint->input - * Input Model = m_focus_mode + * Input Field = accepts_input */ - if (wmhint->flags & InputHint) { - if (wmhint->input) { - if (send_focus_message) - m_focus_mode = F_LOCALLYACTIVE; - else - m_focus_mode = F_PASSIVE; - } else { - if (send_focus_message) - m_focus_mode = F_GLOBALLYACTIVE; - else - m_focus_mode = F_NOINPUT; - } - } else // InputHint not present: ignoring send_focus_message and assuming F_PASSIVE - m_focus_mode = F_PASSIVE; + if (wmhint->flags & InputHint) + accepts_input = (bool)wmhint->input; if (wmhint->flags & StateHint) initial_state = wmhint->initial_state; - else - initial_state = NormalState; - if (wmhint->flags & WindowGroupHint) { - if (! window_group) - window_group = wmhint->window_group; - } else - window_group = None; + if (wmhint->flags & WindowGroupHint && !window_group) + window_group = wmhint->window_group; if ((bool)(wmhint->flags & IconPixmapHint) && wmhint->icon_pixmap != 0) m_icon.pixmap().copy(wmhint->icon_pixmap, 0, 0); diff --git a/src/WinClient.hh b/src/WinClient.hh index 4a5cf27..035ece5 100644 --- a/src/WinClient.hh +++ b/src/WinClient.hh @@ -64,9 +64,7 @@ public: // override the title with this void setTitle(FbTk::FbString &title); - void setIconTitle(FbTk::FbString &icon_title); void updateTitle(); - void updateIconTitle(); /// updates transient window information void updateTransientInfo(); @@ -80,7 +78,7 @@ public: bool focus(); // calls Window->setCurrentClient to give focus to this client bool isFocused() const; void setAttentionState(bool value); - const std::string &title() const; + const std::string &title() const { return m_title; } /** * Changes width and height to the nearest (lower) value @@ -110,6 +108,8 @@ public: bool getWMName(XTextProperty &textprop) const; bool getWMIconName(XTextProperty &textprop) const; std::string getWMRole() const; + Focusable::WindowType getWindowType() const { return m_window_type; } + void setWindowType(Focusable::WindowType type) { m_window_type = type; } inline WinClient *transientFor() { return transient_for; } inline const WinClient *transientFor() const { return transient_for; } @@ -127,7 +127,6 @@ public: // grouping is tracked by remembering the window to the left in the group Window getGroupLeftWindow() const; - inline int getFocusMode() const { return m_focus_mode; } inline const MwmHints *getMwmHint() const { return m_mwm_hint; } inline unsigned int maxWidth() const { return max_width; } @@ -152,9 +151,6 @@ public: base_width, base_height; unsigned long initial_state, normal_hint_flags, wm_hint_flags; - - enum FocusMode { F_NOINPUT = 0, F_PASSIVE, F_LOCALLYACTIVE, F_GLOBALLYACTIVE }; - private: /// removes client from any waiting list and clears empty waiting lists void removeTransientFromWaitingList(); @@ -167,17 +163,15 @@ private: // number of transients which we are modal for int m_modal_count; bool m_modal; - bool send_focus_message, send_close_message; + bool accepts_input, send_focus_message, send_close_message; int m_win_gravity; - std::string m_icon_title; - bool m_title_override, m_icon_title_override; + bool m_title_override; + Focusable::WindowType m_window_type; MwmHints *m_mwm_hint; - int m_focus_mode; - Strut *m_strut; // map transient_for X window to winclient transient // (used if transient_for FbWindow was created after transient) diff --git a/src/Window.cc b/src/Window.cc index 5d9404d..898111d 100644 --- a/src/Window.cc +++ b/src/Window.cc @@ -453,6 +453,8 @@ void FluxboxWindow::init() { wattrib.width, wattrib.height, m_client->gravity(), m_client->old_bw); + setWindowType(m_client->getWindowType()); + if (fluxbox.isStartup()) m_placed = true; else if (m_client->isTransient() || @@ -1021,7 +1023,6 @@ void FluxboxWindow::associateClientWindow(bool use_attrs, unsigned int width, unsigned int height, int gravity, unsigned int client_bw) { m_client->updateTitle(); - m_client->updateIconTitle(); frame().setShapingClient(m_client, false); @@ -1353,26 +1354,7 @@ bool FluxboxWindow::focus() { if (m_client->isModal()) return false; - bool ret = false; - - if (m_client->acceptsFocus()) { - - m_client->setInputFocus(RevertToParent, CurrentTime); - - FbTk::App *app = FbTk::App::instance(); - - XFlush(app->display()); - - m_client->sendFocus(); - - app->sync(false); - - ret = true; - } else { - ret = m_client->sendFocus(); - } - - return ret; + return m_client->sendFocus(); } // don't hide the frame directly, use this function @@ -2129,14 +2111,6 @@ void FluxboxWindow::restoreAttributes() { m_layernum = m_blackbox_attrib.stack; } - if ((m_blackbox_attrib.flags & ATTRIB_MAXHORIZ) || - (m_blackbox_attrib.flags & ATTRIB_MAXVERT)) { - m_blackbox_attrib.premax_x = m_blackbox_attrib.premax_x; - m_blackbox_attrib.premax_y = m_blackbox_attrib.premax_y; - m_blackbox_attrib.premax_w = m_blackbox_attrib.premax_w; - m_blackbox_attrib.premax_h = m_blackbox_attrib.premax_h; - } - } /** @@ -2369,8 +2343,9 @@ void FluxboxWindow::propertyNotifyEvent(WinClient &client, Atom atom) { break; case XA_WM_ICON_NAME: - // update icon title and then do normal XA_WM_NAME stuff - client.updateIconTitle(); + // we don't use icon title, since many apps don't update it, + // and we don't show icons anyway + break; case XA_WM_NAME: client.updateTitle(); break; @@ -2610,7 +2585,7 @@ void FluxboxWindow::buttonPressEvent(XButtonEvent &be) { frame().buttonPressEvent(be); if (be.button == 1) { - if (!m_focused) //check focus + if (!m_focused && acceptsFocus()) //check focus focus(); if (frame().window().window() == be.window || frame().tabcontainer().window() == be.window) { @@ -2968,7 +2943,8 @@ void FluxboxWindow::enterNotifyEvent(XCrossingEvent &ev) { ev.window == m_client->window() || client) { - if (screen().focusControl().isMouseFocus() && !isFocused()) { + if (screen().focusControl().isMouseFocus() && !isFocused() && + acceptsFocus() && getWindowType() != Focusable::TYPE_DESKTOP) { // check that there aren't any subsequent leave notify events in the // X event queue @@ -3138,7 +3114,6 @@ void FluxboxWindow::startMoving(int x, int y) { m_button_grab_y = y - frame().y() - frame().window().borderWidth(); moving = true; - maximized = MAX_NONE; Fluxbox *fluxbox = Fluxbox::instance(); // grabbing (and masking) on the root window allows us to @@ -3674,6 +3649,10 @@ std::string FluxboxWindow::getWMRole() const { return (m_client ? m_client->getWMRole() : "FluxboxWindow"); } +Focusable::WindowType FluxboxWindow::getWindowType() const { + return (m_client ? m_client->getWindowType() : Focusable::TYPE_NORMAL); +} + bool FluxboxWindow::isTransient() const { return (m_client && m_client->isTransient()); } @@ -4139,3 +4118,72 @@ void FluxboxWindow::placeWindow(int head) { screen().placementStrategy().placeWindow(*this, head, place_x, place_y); move(place_x, place_y); } + +void FluxboxWindow::setWindowType(Focusable::WindowType type) { + switch (type) { + case Focusable::TYPE_DOCK: + /* From Extended Window Manager Hints, draft 1.3: + * + * _NET_WM_WINDOW_TYPE_DOCK indicates a dock or panel feature. + * Typically a Window Manager would keep such windows on top + * of all other windows. + * + */ + setFocusHidden(true); + setIconHidden(true); + setDecorationMask(DECOR_NONE); + moveToLayer(::Layer::DOCK); + break; + case Focusable::TYPE_DESKTOP: + /* + * _NET_WM_WINDOW_TYPE_DESKTOP indicates a "false desktop" window + * We let it be the size it wants, but it gets no decoration, + * is hidden in the toolbar and window cycling list, plus + * windows don't tab with it and is right on the bottom. + */ + setFocusHidden(true); + setIconHidden(true); + moveToLayer(::Layer::DESKTOP); + setDecorationMask(DECOR_NONE); + setTabable(false); + setMovable(false); + setResizable(false); + stick(); + break; + case Focusable::TYPE_SPLASH: + /* + * _NET_WM_WINDOW_TYPE_SPLASH indicates that the + * window is a splash screen displayed as an application + * is starting up. + */ + setDecorationMask(DECOR_NONE); + setFocusHidden(true); + setIconHidden(true); + setMovable(false); + break; + case Focusable::TYPE_DIALOG: + setTabable(false); + break; + case Focusable::TYPE_MENU: + case Focusable::TYPE_TOOLBAR: + /* + * _NET_WM_WINDOW_TYPE_TOOLBAR and _NET_WM_WINDOW_TYPE_MENU + * indicate toolbar and pinnable menu windows, respectively + * (i.e. toolbars and menus "torn off" from the main + * application). Windows of this type may set the + * WM_TRANSIENT_FOR hint indicating the main application window. + */ + setDecorationMask(DECOR_TOOL); + setIconHidden(true); + moveToLayer(::Layer::ABOVE_DOCK); + break; + case Focusable::TYPE_NORMAL: + default: + break; + } + + /* + * NOT YET IMPLEMENTED: + * _NET_WM_WINDOW_TYPE_UTILITY + */ +} diff --git a/src/Window.hh b/src/Window.hh index 4304037..d2529bc 100644 --- a/src/Window.hh +++ b/src/Window.hh @@ -459,6 +459,8 @@ public: const std::string &getWMClassName() const; const std::string &getWMClassClass() const; std::string getWMRole() const; + Focusable::WindowType getWindowType() const; + void setWindowType(Focusable::WindowType type); bool isTransient() const; inline int x() const { return frame().x(); } diff --git a/src/WorkspaceCmd.cc b/src/WorkspaceCmd.cc index 567d86e..a525078 100644 --- a/src/WorkspaceCmd.cc +++ b/src/WorkspaceCmd.cc @@ -301,9 +301,12 @@ void ShowDesktopCmd::execute() { return; Workspace::Windows windows(screen->currentWorkspace()->windowList()); - std::for_each(windows.begin(), - windows.end(), - std::mem_fun(&FluxboxWindow::iconify)); + Workspace::Windows::iterator it = windows.begin(), + it_end = windows.end(); + for (; it != it_end; ++it) { + if ((*it)->getWindowType() != Focusable::TYPE_DESKTOP) + (*it)->iconify(); + } } void CloseAllWindowsCmd::execute() { -- cgit v0.11.2