2003-06-30 14:38:42 +00:00
|
|
|
// WorkspaceCmd.cc for Fluxbox - an X11 Window manager
|
2006-02-16 06:53:05 +00:00
|
|
|
// Copyright (c) 2003 - 2006 Henrik Kinnunen (fluxgen at fluxbox dot org)
|
2003-06-30 14:38:42 +00:00
|
|
|
// and Simon Bowden (rathnor at users.sourceforge.net)
|
|
|
|
//
|
|
|
|
// Permission is hereby granted, free of charge, to any person obtaining a
|
|
|
|
// copy of this software and associated documentation files (the "Software"),
|
|
|
|
// to deal in the Software without restriction, including without limitation
|
|
|
|
// the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
|
|
|
// and/or sell copies of the Software, and to permit persons to whom the
|
|
|
|
// Software is furnished to do so, subject to the following conditions:
|
|
|
|
//
|
|
|
|
// The above copyright notice and this permission notice shall be included in
|
|
|
|
// all copies or substantial portions of the Software.
|
|
|
|
//
|
|
|
|
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
|
|
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
|
|
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
|
|
|
// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
|
|
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
|
|
|
// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
|
|
|
|
// DEALINGS IN THE SOFTWARE.
|
|
|
|
|
|
|
|
#include "WorkspaceCmd.hh"
|
2003-09-06 14:05:32 +00:00
|
|
|
|
2003-06-30 14:38:42 +00:00
|
|
|
#include "Workspace.hh"
|
|
|
|
#include "Window.hh"
|
|
|
|
#include "Screen.hh"
|
|
|
|
#include "fluxbox.hh"
|
2004-04-28 14:59:12 +00:00
|
|
|
#include "WinClient.hh"
|
2006-02-18 20:19:22 +00:00
|
|
|
#include "FocusControl.hh"
|
2007-11-22 04:07:57 +00:00
|
|
|
#include "WindowCmd.hh"
|
2003-09-06 14:05:32 +00:00
|
|
|
|
|
|
|
#include "FbTk/KeyUtil.hh"
|
2008-01-11 07:41:22 +00:00
|
|
|
#include "FbTk/CommandParser.hh"
|
2007-12-13 05:48:00 +00:00
|
|
|
#include "FbTk/stringstream.hh"
|
2007-12-20 20:23:56 +00:00
|
|
|
#include "FbTk/StringUtil.hh"
|
2003-09-06 14:05:32 +00:00
|
|
|
|
2004-08-31 15:26:40 +00:00
|
|
|
#ifdef HAVE_CMATH
|
|
|
|
#include <cmath>
|
|
|
|
#else
|
|
|
|
#include <math.h>
|
|
|
|
#endif
|
2003-06-30 14:38:42 +00:00
|
|
|
#include <algorithm>
|
|
|
|
#include <functional>
|
2007-12-20 20:23:56 +00:00
|
|
|
#include <vector>
|
2003-06-30 14:38:42 +00:00
|
|
|
|
2007-12-13 05:48:00 +00:00
|
|
|
using std::string;
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND_PARSER(map, WindowListCmd::parse, void);
|
|
|
|
REGISTER_COMMAND_PARSER(foreach, WindowListCmd::parse, void);
|
2007-12-20 20:23:56 +00:00
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
FbTk::Command<void> *WindowListCmd::parse(const string &command, const string &args,
|
2007-12-20 20:23:56 +00:00
|
|
|
bool trusted) {
|
2008-01-11 07:41:22 +00:00
|
|
|
FbTk::Command<void> *cmd = 0;
|
|
|
|
FbTk::Command<bool> *filter = 0;
|
2007-12-20 20:23:56 +00:00
|
|
|
std::vector<string> tokens;
|
|
|
|
int opts;
|
|
|
|
string pat;
|
|
|
|
|
|
|
|
FbTk::StringUtil::stringTokensBetween(tokens, args, pat, '{', '}');
|
|
|
|
if (tokens.empty())
|
|
|
|
return 0;
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
cmd = FbTk::CommandParser<void>::instance().parse(tokens[0], trusted);
|
2007-12-20 20:23:56 +00:00
|
|
|
if (!cmd)
|
|
|
|
return 0;
|
|
|
|
|
|
|
|
if (tokens.size() > 1) {
|
|
|
|
FocusableList::parseArgs(tokens[1], opts, pat);
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
filter = FbTk::CommandParser<bool>::instance().parse(pat,
|
2007-12-20 20:23:56 +00:00
|
|
|
trusted);
|
2007-10-13 21:51:37 +00:00
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
return new WindowListCmd(FbTk::RefCount<FbTk::Command<void> >(cmd), opts,
|
|
|
|
FbTk::RefCount<FbTk::Command<bool> >(filter));
|
2007-12-20 20:23:56 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void WindowListCmd::execute() {
|
2007-10-13 21:51:37 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->keyScreen();
|
|
|
|
if (screen != 0) {
|
2007-12-20 20:23:56 +00:00
|
|
|
FocusableList::Focusables win_list(FocusableList::getListFromOptions(*screen, m_opts)->clientList());
|
2007-10-13 21:51:37 +00:00
|
|
|
|
2007-12-20 20:23:56 +00:00
|
|
|
FocusableList::Focusables::iterator it = win_list.begin(),
|
|
|
|
it_end = win_list.end();
|
2007-11-23 18:41:23 +00:00
|
|
|
// save old value, so we can restore it later
|
|
|
|
WinClient *old = WindowCmd<void>::client();
|
2007-10-13 21:51:37 +00:00
|
|
|
for (; it != it_end; ++it) {
|
2007-12-20 20:23:56 +00:00
|
|
|
if (typeid(**it) == typeid(FluxboxWindow))
|
2007-11-22 04:07:57 +00:00
|
|
|
WindowCmd<void>::setWindow((*it)->fbwindow());
|
2007-12-20 20:23:56 +00:00
|
|
|
else if (typeid(**it) == typeid(WinClient))
|
|
|
|
WindowCmd<void>::setClient(dynamic_cast<WinClient *>(*it));
|
2008-01-11 07:41:22 +00:00
|
|
|
if (!*m_filter || m_filter->execute())
|
2007-11-22 04:07:57 +00:00
|
|
|
m_cmd->execute();
|
2007-10-13 21:51:37 +00:00
|
|
|
}
|
2007-11-23 18:41:23 +00:00
|
|
|
WindowCmd<void>::setClient(old);
|
2007-10-13 21:51:37 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
FbTk::Command<bool> *SomeCmd::parse(const string &command, const string &args,
|
2007-12-13 05:48:00 +00:00
|
|
|
bool trusted) {
|
2008-01-11 07:41:22 +00:00
|
|
|
FbTk::Command<bool> *boolcmd =
|
|
|
|
FbTk::CommandParser<bool>::instance().parse(args,
|
2007-12-16 03:36:01 +00:00
|
|
|
trusted);
|
2007-12-13 05:48:00 +00:00
|
|
|
if (!boolcmd)
|
|
|
|
return 0;
|
|
|
|
if (command == "some")
|
2008-01-11 07:41:22 +00:00
|
|
|
return new SomeCmd(FbTk::RefCount<FbTk::Command<bool> >(boolcmd));
|
|
|
|
return new EveryCmd(FbTk::RefCount<FbTk::Command<bool> >(boolcmd));
|
2007-12-13 05:48:00 +00:00
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND_PARSER(some, SomeCmd::parse, bool);
|
|
|
|
REGISTER_COMMAND_PARSER(every, SomeCmd::parse, bool);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
bool SomeCmd::execute() {
|
2007-11-22 04:07:57 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->keyScreen();
|
|
|
|
if (screen != 0) {
|
|
|
|
FocusControl::Focusables win_list(screen->focusControl().creationOrderList().clientList());
|
|
|
|
|
|
|
|
FocusControl::Focusables::iterator it = win_list.begin(),
|
|
|
|
it_end = win_list.end();
|
2007-11-23 18:41:23 +00:00
|
|
|
// save old value, so we can restore it later
|
|
|
|
WinClient *old = WindowCmd<void>::client();
|
2007-11-22 04:07:57 +00:00
|
|
|
for (; it != it_end; ++it) {
|
|
|
|
WinClient *client = dynamic_cast<WinClient *>(*it);
|
|
|
|
if (!client) continue;
|
|
|
|
WindowCmd<void>::setClient(client);
|
2008-01-11 07:41:22 +00:00
|
|
|
if (m_cmd->execute())
|
2007-11-22 04:07:57 +00:00
|
|
|
return true;
|
|
|
|
}
|
2007-11-23 18:41:23 +00:00
|
|
|
WindowCmd<void>::setClient(old);
|
2007-11-22 04:07:57 +00:00
|
|
|
}
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
bool EveryCmd::execute() {
|
2007-11-22 04:07:57 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->keyScreen();
|
|
|
|
if (screen != 0) {
|
|
|
|
FocusControl::Focusables win_list(screen->focusControl().creationOrderList().clientList());
|
|
|
|
|
|
|
|
FocusControl::Focusables::iterator it = win_list.begin(),
|
|
|
|
it_end = win_list.end();
|
2007-11-23 18:41:23 +00:00
|
|
|
// save old value, so we can restore it later
|
|
|
|
WinClient *old = WindowCmd<void>::client();
|
2007-11-22 04:07:57 +00:00
|
|
|
for (; it != it_end; ++it) {
|
|
|
|
WinClient *client = dynamic_cast<WinClient *>(*it);
|
|
|
|
if (!client) continue;
|
|
|
|
WindowCmd<void>::setClient(client);
|
2008-01-11 07:41:22 +00:00
|
|
|
if (!m_cmd->execute())
|
2007-11-22 04:07:57 +00:00
|
|
|
return false;
|
|
|
|
}
|
2007-11-23 18:41:23 +00:00
|
|
|
WindowCmd<void>::setClient(old);
|
2007-11-22 04:07:57 +00:00
|
|
|
}
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
2007-12-13 05:48:00 +00:00
|
|
|
namespace {
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
FbTk::Command<void> *parseWindowList(const string &command,
|
2007-12-13 05:48:00 +00:00
|
|
|
const string &args, bool trusted) {
|
|
|
|
int opts;
|
|
|
|
string pat;
|
|
|
|
FocusableList::parseArgs(args, opts, pat);
|
|
|
|
if (command == "attach")
|
|
|
|
return new AttachCmd(pat);
|
|
|
|
else if (command == "nextwindow")
|
|
|
|
return new NextWindowCmd(opts, pat);
|
|
|
|
else if (command == "nextgroup") {
|
|
|
|
opts |= FocusableList::LIST_GROUPS;
|
|
|
|
return new NextWindowCmd(opts, pat);
|
|
|
|
} else if (command == "prevwindow")
|
|
|
|
return new PrevWindowCmd(opts, pat);
|
|
|
|
else if (command == "prevgroup") {
|
|
|
|
opts |= FocusableList::LIST_GROUPS;
|
|
|
|
return new PrevWindowCmd(opts, pat);
|
2008-08-04 01:18:04 +00:00
|
|
|
} else if (command == "arrangewindows")
|
|
|
|
return new ArrangeWindowsCmd(pat);
|
2007-12-13 05:48:00 +00:00
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND_PARSER(attach, parseWindowList, void);
|
|
|
|
REGISTER_COMMAND_PARSER(nextwindow, parseWindowList, void);
|
|
|
|
REGISTER_COMMAND_PARSER(nextgroup, parseWindowList, void);
|
|
|
|
REGISTER_COMMAND_PARSER(prevwindow, parseWindowList, void);
|
|
|
|
REGISTER_COMMAND_PARSER(prevgroup, parseWindowList, void);
|
2008-08-04 01:18:04 +00:00
|
|
|
REGISTER_COMMAND_PARSER(arrangewindows, parseWindowList, void);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
|
|
|
}; // end anonymous namespace
|
|
|
|
|
2007-10-13 21:51:37 +00:00
|
|
|
void AttachCmd::execute() {
|
|
|
|
BScreen *screen = Fluxbox::instance()->keyScreen();
|
|
|
|
if (screen != 0) {
|
2007-11-12 21:59:43 +00:00
|
|
|
FocusControl::Focusables win_list(screen->focusControl().focusedOrderWinList().clientList());
|
2007-10-13 21:51:37 +00:00
|
|
|
|
|
|
|
FocusControl::Focusables::iterator it = win_list.begin(),
|
|
|
|
it_end = win_list.end();
|
|
|
|
FluxboxWindow *first = 0;
|
|
|
|
for (; it != it_end; ++it) {
|
|
|
|
if (m_pat.match(**it) && (*it)->fbwindow()) {
|
|
|
|
if (first == 0)
|
|
|
|
first = (*it)->fbwindow();
|
|
|
|
else
|
|
|
|
first->attachClient((*it)->fbwindow()->winClient());
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2003-06-30 14:38:42 +00:00
|
|
|
void NextWindowCmd::execute() {
|
2007-03-04 17:47:37 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->keyScreen();
|
|
|
|
if (screen != 0)
|
2007-10-13 21:51:37 +00:00
|
|
|
screen->cycleFocus(m_option, &m_pat, false);
|
2003-06-30 14:38:42 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void PrevWindowCmd::execute() {
|
2007-03-04 17:47:37 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->keyScreen();
|
|
|
|
if (screen != 0)
|
2007-10-13 21:51:37 +00:00
|
|
|
screen->cycleFocus(m_option, &m_pat, true);
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
FbTk::Command<void> *GoToWindowCmd::parse(const string &command,
|
2007-12-13 05:48:00 +00:00
|
|
|
const string &arguments, bool trusted) {
|
|
|
|
int num, opts;
|
|
|
|
string args, pat;
|
|
|
|
FbTk_istringstream iss(arguments.c_str());
|
|
|
|
iss >> num;
|
|
|
|
string::size_type pos = arguments.find_first_of("({");
|
|
|
|
if (pos != string::npos && pos != arguments.size())
|
|
|
|
args = arguments.c_str() + pos;
|
|
|
|
FocusableList::parseArgs(args, opts, pat);
|
|
|
|
return new GoToWindowCmd(num, opts, pat);
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND_PARSER(gotowindow, GoToWindowCmd::parse, void);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
2007-10-13 21:51:37 +00:00
|
|
|
void GoToWindowCmd::execute() {
|
|
|
|
BScreen *screen = Fluxbox::instance()->keyScreen();
|
|
|
|
if (screen != 0) {
|
2007-11-12 21:59:43 +00:00
|
|
|
const FocusableList *win_list =
|
|
|
|
FocusableList::getListFromOptions(*screen, m_option);
|
2007-10-13 21:51:37 +00:00
|
|
|
screen->focusControl().goToWindowNumber(*win_list, m_num, &m_pat);
|
|
|
|
}
|
2003-06-30 14:38:42 +00:00
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
FbTk::Command<void> *DirFocusCmd::parse(const string &command,
|
2007-12-13 05:48:00 +00:00
|
|
|
const string &args, bool trusted) {
|
|
|
|
if (command == "focusup")
|
|
|
|
return new DirFocusCmd(FocusControl::FOCUSUP);
|
|
|
|
else if (command == "focusdown")
|
|
|
|
return new DirFocusCmd(FocusControl::FOCUSDOWN);
|
|
|
|
else if (command == "focusleft")
|
|
|
|
return new DirFocusCmd(FocusControl::FOCUSLEFT);
|
|
|
|
else if (command == "focusright")
|
|
|
|
return new DirFocusCmd(FocusControl::FOCUSRIGHT);
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND_PARSER(focusup, DirFocusCmd::parse, void);
|
|
|
|
REGISTER_COMMAND_PARSER(focusdown, DirFocusCmd::parse, void);
|
|
|
|
REGISTER_COMMAND_PARSER(focusleft, DirFocusCmd::parse, void);
|
|
|
|
REGISTER_COMMAND_PARSER(focusright, DirFocusCmd::parse, void);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
2004-04-28 14:59:12 +00:00
|
|
|
void DirFocusCmd::execute() {
|
|
|
|
BScreen *screen = Fluxbox::instance()->keyScreen();
|
|
|
|
if (screen == 0)
|
|
|
|
return;
|
|
|
|
|
2006-07-12 00:08:57 +00:00
|
|
|
FluxboxWindow *win = FocusControl::focusedFbWindow();
|
|
|
|
if (win)
|
|
|
|
screen->focusControl().dirFocus(*win, m_dir);
|
2004-04-28 14:59:12 +00:00
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND(addworkspace, AddWorkspaceCmd, void);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
2007-07-01 21:01:31 +00:00
|
|
|
void AddWorkspaceCmd::execute() {
|
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
|
|
|
if (screen != 0)
|
|
|
|
screen->addWorkspace();
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND(removelastworkspace, RemoveLastWorkspaceCmd, void);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
2007-07-01 21:01:31 +00:00
|
|
|
void RemoveLastWorkspaceCmd::execute() {
|
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
|
|
|
if (screen != 0)
|
|
|
|
screen->removeLastWorkspace();
|
|
|
|
}
|
|
|
|
|
2007-12-13 05:48:00 +00:00
|
|
|
namespace {
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
FbTk::Command<void> *parseIntCmd(const string &command, const string &args,
|
2007-12-13 05:48:00 +00:00
|
|
|
bool trusted) {
|
|
|
|
int num = 1;
|
|
|
|
FbTk_istringstream iss(args.c_str());
|
|
|
|
iss >> num;
|
|
|
|
if (command == "nextworkspace")
|
|
|
|
return new NextWorkspaceCmd(num);
|
|
|
|
else if (command == "prevworkspace")
|
|
|
|
return new PrevWorkspaceCmd(num);
|
|
|
|
else if (command == "rightworkspace")
|
|
|
|
return new RightWorkspaceCmd(num);
|
|
|
|
else if (command == "leftworkspace")
|
|
|
|
return new LeftWorkspaceCmd(num);
|
|
|
|
else if (command == "workspace")
|
|
|
|
// workspaces appear 1-indexed to the user, hence the minus 1
|
|
|
|
return new JumpToWorkspaceCmd(num - 1);
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND_PARSER(nextworkspace, parseIntCmd, void);
|
|
|
|
REGISTER_COMMAND_PARSER(prevworkspace, parseIntCmd, void);
|
|
|
|
REGISTER_COMMAND_PARSER(rightworkspace, parseIntCmd, void);
|
|
|
|
REGISTER_COMMAND_PARSER(leftworkspace, parseIntCmd, void);
|
|
|
|
REGISTER_COMMAND_PARSER(workspace, parseIntCmd, void);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
|
|
|
}; // end anonymous namespace
|
|
|
|
|
2003-06-30 14:38:42 +00:00
|
|
|
void NextWorkspaceCmd::execute() {
|
2003-07-19 13:51:24 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
2003-06-30 14:38:42 +00:00
|
|
|
if (screen != 0)
|
2006-03-09 19:38:18 +00:00
|
|
|
screen->nextWorkspace(m_option == 0 ? 1 : m_option);
|
2003-06-30 14:38:42 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void PrevWorkspaceCmd::execute() {
|
2003-07-19 13:51:24 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
2003-06-30 14:38:42 +00:00
|
|
|
if (screen != 0)
|
2006-03-09 19:38:18 +00:00
|
|
|
screen->prevWorkspace(m_option == 0 ? 1 : m_option);
|
2003-06-30 14:38:42 +00:00
|
|
|
}
|
|
|
|
|
2003-07-01 09:47:41 +00:00
|
|
|
void LeftWorkspaceCmd::execute() {
|
2003-07-19 13:51:24 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
2003-07-01 09:47:41 +00:00
|
|
|
if (screen != 0)
|
|
|
|
screen->leftWorkspace(m_param);
|
|
|
|
}
|
|
|
|
|
|
|
|
void RightWorkspaceCmd::execute() {
|
2003-07-19 13:51:24 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
2003-07-01 09:47:41 +00:00
|
|
|
if (screen != 0)
|
|
|
|
screen->rightWorkspace(m_param);
|
|
|
|
}
|
|
|
|
|
2003-06-30 14:38:42 +00:00
|
|
|
JumpToWorkspaceCmd::JumpToWorkspaceCmd(int workspace_num):m_workspace_num(workspace_num) { }
|
|
|
|
|
|
|
|
void JumpToWorkspaceCmd::execute() {
|
2003-07-19 13:51:24 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
2007-07-07 04:54:34 +00:00
|
|
|
if (screen != 0) {
|
|
|
|
int num = screen->numberOfWorkspaces();
|
|
|
|
int actual = m_workspace_num;
|
|
|
|
// we need an extra +1, since it's subtracted in FbCommandFactory
|
|
|
|
if (actual < 0) actual += num+1;
|
|
|
|
if (actual < 0) actual = 0;
|
|
|
|
if (actual >= num) actual = num - 1;
|
|
|
|
screen->changeWorkspaceID(actual);
|
|
|
|
}
|
2003-06-30 14:38:42 +00:00
|
|
|
}
|
|
|
|
|
2005-04-30 13:10:15 +00:00
|
|
|
/**
|
|
|
|
try to arrange the windows on the current workspace in a 'clever' way.
|
|
|
|
we take the shaded-windows and put them ontop of the workspace and put the
|
|
|
|
normal windows underneath it.
|
|
|
|
*/
|
2003-06-30 14:38:42 +00:00
|
|
|
void ArrangeWindowsCmd::execute() {
|
2003-07-19 13:51:24 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
2003-06-30 14:38:42 +00:00
|
|
|
if (screen == 0)
|
|
|
|
return;
|
|
|
|
|
|
|
|
Workspace *space = screen->currentWorkspace();
|
2006-04-19 05:18:10 +00:00
|
|
|
|
2008-08-04 01:18:04 +00:00
|
|
|
if (space->windowList().empty())
|
2003-06-30 14:38:42 +00:00
|
|
|
return;
|
|
|
|
|
2006-04-19 05:18:10 +00:00
|
|
|
// TODO: choice between
|
2005-04-30 13:10:15 +00:00
|
|
|
// - arrange using all windows on all heads
|
|
|
|
// - arrange for each head
|
|
|
|
// - only on current head
|
2004-01-16 09:21:31 +00:00
|
|
|
const int head = screen->getCurrHead();
|
2005-04-30 13:10:15 +00:00
|
|
|
Workspace::Windows::iterator win;
|
2006-04-19 05:18:10 +00:00
|
|
|
|
2005-04-30 13:10:15 +00:00
|
|
|
Workspace::Windows normal_windows;
|
|
|
|
Workspace::Windows shaded_windows;
|
|
|
|
for(win = space->windowList().begin(); win != space->windowList().end(); win++) {
|
|
|
|
int winhead = screen->getHead((*win)->fbWindow());
|
2008-08-04 01:18:04 +00:00
|
|
|
if ((winhead == head || winhead == 0) && m_pat.match(**win)) {
|
|
|
|
if ((*win)->isShaded())
|
2005-04-30 13:10:15 +00:00
|
|
|
shaded_windows.push_back(*win);
|
2008-08-04 01:18:04 +00:00
|
|
|
else
|
|
|
|
normal_windows.push_back(*win);
|
2005-04-30 13:10:15 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// to arrange only shaded windows is a bit pointless imho (mathias)
|
2008-08-04 01:18:04 +00:00
|
|
|
size_t win_count = normal_windows.size();
|
|
|
|
if (win_count == 0)
|
2005-04-30 13:10:15 +00:00
|
|
|
return;
|
|
|
|
|
2004-01-16 09:21:31 +00:00
|
|
|
const unsigned int max_width = screen->maxRight(head) - screen->maxLeft(head);
|
2005-04-30 13:10:15 +00:00
|
|
|
unsigned int max_height = screen->maxBottom(head) - screen->maxTop(head);
|
2003-06-30 14:38:42 +00:00
|
|
|
|
2006-04-19 05:18:10 +00:00
|
|
|
// try to get the same number of rows as columns.
|
|
|
|
unsigned int cols = int(sqrt((float)win_count)); // truncate to lower
|
|
|
|
unsigned int rows = int(0.99 + float(win_count) / float(cols));
|
|
|
|
if (max_width<max_height) { // rotate
|
2005-04-30 13:10:15 +00:00
|
|
|
std::swap(cols, rows);
|
2006-04-19 05:18:10 +00:00
|
|
|
}
|
2003-06-30 14:38:42 +00:00
|
|
|
|
2005-04-21 09:05:02 +00:00
|
|
|
unsigned int x_offs = screen->maxLeft(head); // window position offset in x
|
|
|
|
unsigned int y_offs = screen->maxTop(head); // window position offset in y
|
2006-04-19 05:18:10 +00:00
|
|
|
// unsigned int window = 0; // current window
|
2005-04-30 13:10:15 +00:00
|
|
|
const unsigned int cal_width = max_width/cols; // calculated width ratio (width of every window)
|
|
|
|
unsigned int i;
|
|
|
|
unsigned int j;
|
|
|
|
|
|
|
|
// place the shaded windows
|
|
|
|
// TODO: until i resolve the shadedwindow->moveResize() issue to place
|
|
|
|
// them in the same columns as the normal windows i just place the shaded
|
|
|
|
// windows unchanged ontop of the current head
|
|
|
|
for (i = 0, win = shaded_windows.begin(); win != shaded_windows.end(); win++, i++) {
|
|
|
|
if (i & 1)
|
|
|
|
(*win)->move(x_offs, y_offs);
|
|
|
|
else
|
|
|
|
(*win)->move(screen->maxRight(head) - (*win)->frame().width(), y_offs);
|
2006-04-19 05:18:10 +00:00
|
|
|
|
2005-04-30 13:10:15 +00:00
|
|
|
y_offs += (*win)->frame().height();
|
|
|
|
}
|
|
|
|
|
|
|
|
// TODO: what if the number of shaded windows is really big and we end up
|
|
|
|
// with really little space left for the normal windows? how to handle
|
|
|
|
// this?
|
|
|
|
if (!shaded_windows.empty())
|
2006-04-19 05:18:10 +00:00
|
|
|
max_height -= i * (*shaded_windows.begin())->frame().height();
|
2005-04-30 13:10:15 +00:00
|
|
|
|
|
|
|
const unsigned int cal_height = max_height/rows; // height ratio (height of every window)
|
|
|
|
// Resizes and sets windows positions in columns and rows.
|
|
|
|
for (i = 0; i < rows; ++i) {
|
2005-04-21 09:05:02 +00:00
|
|
|
x_offs = screen->maxLeft(head);
|
2006-04-19 05:18:10 +00:00
|
|
|
for (j = 0; j < cols && normal_windows.size() > 0; ++j) {
|
|
|
|
|
|
|
|
|
|
|
|
int cell_center_x = x_offs + (x_offs + cal_width) / 2;
|
|
|
|
int cell_center_y = y_offs + (y_offs + cal_height) / 2;
|
|
|
|
unsigned int closest_dist = ~0;
|
|
|
|
|
|
|
|
Workspace::Windows::iterator closest = normal_windows.end();
|
|
|
|
for (win = normal_windows.begin(); win != normal_windows.end(); win++) {
|
|
|
|
|
|
|
|
int win_center_x = (*win)->frame().x() + ((*win)->frame().x() + (*win)->frame().width() / 2);
|
|
|
|
int win_center_y = (*win)->frame().y() + ((*win)->frame().y() + (*win)->frame().height() / 2);
|
|
|
|
unsigned int dist = (win_center_x - cell_center_x) * (win_center_x - cell_center_x) +
|
|
|
|
(win_center_y - cell_center_y) * (win_center_y - cell_center_y);
|
|
|
|
|
|
|
|
if (dist < closest_dist) {
|
|
|
|
closest = win;
|
|
|
|
closest_dist = dist;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
if (normal_windows.size() > 1) {
|
2007-02-27 18:07:36 +00:00
|
|
|
(*closest)->moveResize(x_offs + (*closest)->xOffset(),
|
|
|
|
y_offs + (*closest)->yOffset(),
|
|
|
|
cal_width - (*closest)->widthOffset(),
|
|
|
|
cal_height - (*closest)->heightOffset());
|
2006-04-19 05:18:10 +00:00
|
|
|
} else { // the last window gets everything that is left.
|
2007-02-27 18:07:36 +00:00
|
|
|
(*closest)->moveResize(x_offs + (*closest)->xOffset(),
|
|
|
|
y_offs + (*closest)->yOffset(),
|
|
|
|
screen->maxRight(head) - x_offs - (*closest)->widthOffset(),
|
|
|
|
cal_height - (*closest)->heightOffset());
|
2006-04-19 05:18:10 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
normal_windows.erase(closest);
|
|
|
|
|
2003-06-30 14:38:42 +00:00
|
|
|
// next x offset
|
|
|
|
x_offs += cal_width;
|
|
|
|
}
|
|
|
|
// next y offset
|
2005-04-30 13:10:15 +00:00
|
|
|
y_offs += cal_height;
|
2003-06-30 14:38:42 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND(showdesktop, ShowDesktopCmd, void);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
2003-06-30 14:38:42 +00:00
|
|
|
void ShowDesktopCmd::execute() {
|
2003-07-19 13:51:24 +00:00
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
2003-06-30 14:38:42 +00:00
|
|
|
if (screen == 0)
|
|
|
|
return;
|
|
|
|
|
2005-04-23 08:11:42 +00:00
|
|
|
Workspace::Windows windows(screen->currentWorkspace()->windowList());
|
2007-11-05 17:05:58 +00:00
|
|
|
Workspace::Windows::iterator it = windows.begin(),
|
|
|
|
it_end = windows.end();
|
|
|
|
for (; it != it_end; ++it) {
|
|
|
|
if ((*it)->getWindowType() != Focusable::TYPE_DESKTOP)
|
|
|
|
(*it)->iconify();
|
|
|
|
}
|
2003-06-30 14:38:42 +00:00
|
|
|
}
|
2006-04-16 11:29:38 +00:00
|
|
|
|
2008-01-11 07:41:22 +00:00
|
|
|
REGISTER_COMMAND(closeallwindows, CloseAllWindowsCmd, void);
|
2007-12-13 05:48:00 +00:00
|
|
|
|
2006-04-16 11:29:38 +00:00
|
|
|
void CloseAllWindowsCmd::execute() {
|
|
|
|
BScreen *screen = Fluxbox::instance()->mouseScreen();
|
|
|
|
if (screen == 0)
|
|
|
|
return;
|
|
|
|
|
|
|
|
BScreen::Workspaces::iterator workspace_it = screen->getWorkspacesList().begin();
|
|
|
|
BScreen::Workspaces::iterator workspace_it_end = screen->getWorkspacesList().end();
|
|
|
|
for (; workspace_it != workspace_it_end; ++workspace_it) {
|
|
|
|
Workspace::Windows windows((*workspace_it)->windowList());
|
|
|
|
std::for_each(windows.begin(),
|
|
|
|
windows.end(),
|
|
|
|
std::mem_fun(&FluxboxWindow::close));
|
|
|
|
}
|
|
|
|
BScreen::Icons::iterator icon_it = screen->iconList().begin();
|
|
|
|
BScreen::Icons::iterator icon_it_end = screen->iconList().end();
|
|
|
|
for (; icon_it != icon_it_end; ++icon_it ) {
|
|
|
|
(*icon_it)->close();
|
|
|
|
}
|
|
|
|
|
|
|
|
}
|