2009-09-13 11:36:45 +00:00
|
|
|
/********************************************************************
|
|
|
|
KWin - the KDE window manager
|
|
|
|
This file is part of the KDE project.
|
|
|
|
|
|
|
|
Copyright (C) 2009 Martin Gräßlin <kde@martin-graesslin.com>
|
|
|
|
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
|
|
it under the terms of the GNU General Public License as published by
|
|
|
|
the Free Software Foundation; either version 2 of the License, or
|
|
|
|
(at your option) any later version.
|
|
|
|
|
|
|
|
This program is distributed in the hope that it will be useful,
|
|
|
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
GNU General Public License for more details.
|
|
|
|
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
|
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
|
|
*********************************************************************/
|
|
|
|
|
|
|
|
// own
|
|
|
|
#include "clientmodel.h"
|
|
|
|
// tabbox
|
|
|
|
#include "tabboxconfig.h"
|
|
|
|
#include "tabboxhandler.h"
|
|
|
|
// Qt
|
|
|
|
#include <QTextStream>
|
|
|
|
// KDE
|
|
|
|
#include <KLocale>
|
|
|
|
// other
|
|
|
|
#include <math.h>
|
|
|
|
|
|
|
|
namespace KWin
|
|
|
|
{
|
|
|
|
namespace TabBox
|
|
|
|
{
|
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
ClientModel::ClientModel(QObject* parent)
|
|
|
|
: QAbstractItemModel(parent)
|
|
|
|
{
|
2011-10-30 15:07:14 +00:00
|
|
|
QHash<int, QByteArray> roles;
|
|
|
|
roles[CaptionRole] = "caption";
|
|
|
|
roles[DesktopNameRole] = "desktopName";
|
|
|
|
roles[MinimizedRole] = "minimized";
|
2011-11-10 13:28:06 +00:00
|
|
|
roles[WIdRole] = "windowId";
|
2011-11-27 13:15:49 +00:00
|
|
|
roles[CloseableRole] = "closeable";
|
2011-10-30 15:07:14 +00:00
|
|
|
setRoleNames(roles);
|
2011-01-30 14:34:42 +00:00
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
|
|
|
ClientModel::~ClientModel()
|
2011-01-30 14:34:42 +00:00
|
|
|
{
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
QVariant ClientModel::data(const QModelIndex& index, int role) const
|
|
|
|
{
|
|
|
|
if (!index.isValid())
|
2009-09-13 11:36:45 +00:00
|
|
|
return QVariant();
|
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
if (m_clientList.isEmpty()) {
|
2012-03-17 09:31:15 +00:00
|
|
|
return QVariant();
|
2011-01-30 14:34:42 +00:00
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
int clientIndex = index.row() * columnCount() + index.column();
|
|
|
|
if (clientIndex >= m_clientList.count())
|
2009-09-13 11:36:45 +00:00
|
|
|
return QVariant();
|
2011-01-30 14:34:42 +00:00
|
|
|
switch(role) {
|
|
|
|
case Qt::DisplayRole:
|
|
|
|
case CaptionRole:
|
|
|
|
return m_clientList[ clientIndex ]->caption();
|
|
|
|
case ClientRole:
|
|
|
|
return qVariantFromValue((void*)m_clientList[ clientIndex ]);
|
|
|
|
case DesktopNameRole: {
|
|
|
|
return tabBox->desktopName(m_clientList[ clientIndex ]);
|
2009-09-13 11:36:45 +00:00
|
|
|
}
|
2011-01-30 14:34:42 +00:00
|
|
|
case WIdRole:
|
|
|
|
return qulonglong(m_clientList[ clientIndex ]->window());
|
|
|
|
case MinimizedRole:
|
|
|
|
return m_clientList[ clientIndex ]->isMinimized();
|
2011-11-27 13:15:49 +00:00
|
|
|
case CloseableRole:
|
2012-02-27 21:20:11 +00:00
|
|
|
//clients that claim to be first are not closeable
|
|
|
|
return m_clientList[ clientIndex ]->isCloseable() && !m_clientList[ clientIndex ]->isFirstInTabBox();
|
2011-01-30 14:34:42 +00:00
|
|
|
default:
|
|
|
|
return QVariant();
|
|
|
|
}
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-10-30 15:07:14 +00:00
|
|
|
QString ClientModel::longestCaption() const
|
|
|
|
{
|
|
|
|
QString caption;
|
|
|
|
foreach (TabBoxClient *client, m_clientList) {
|
|
|
|
if (client->caption().size() > caption.size()) {
|
|
|
|
caption = client->caption();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return caption;
|
|
|
|
}
|
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
int ClientModel::columnCount(const QModelIndex& parent) const
|
|
|
|
{
|
|
|
|
Q_UNUSED(parent)
|
2009-10-05 06:59:10 +00:00
|
|
|
int count = 1;
|
2011-01-30 14:34:42 +00:00
|
|
|
switch(tabBox->config().layout()) {
|
|
|
|
case TabBoxConfig::HorizontalLayout:
|
|
|
|
count = m_clientList.count();
|
|
|
|
break;
|
|
|
|
case TabBoxConfig::VerticalLayout:
|
|
|
|
count = 1;
|
|
|
|
break;
|
|
|
|
case TabBoxConfig::HorizontalVerticalLayout:
|
|
|
|
count = qRound(sqrt(float(m_clientList.count())));
|
|
|
|
if (count * count < m_clientList.count())
|
|
|
|
count++;
|
|
|
|
break;
|
2009-09-13 11:36:45 +00:00
|
|
|
}
|
2011-01-30 14:34:42 +00:00
|
|
|
return qMax(count, 1);
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
int ClientModel::rowCount(const QModelIndex& parent) const
|
|
|
|
{
|
|
|
|
Q_UNUSED(parent)
|
2009-10-05 06:59:10 +00:00
|
|
|
int count = 1;
|
2011-01-30 14:34:42 +00:00
|
|
|
switch(tabBox->config().layout()) {
|
|
|
|
case TabBoxConfig::HorizontalLayout:
|
|
|
|
count = 1;
|
|
|
|
break;
|
|
|
|
case TabBoxConfig::VerticalLayout:
|
|
|
|
count = m_clientList.count();
|
|
|
|
break;
|
|
|
|
case TabBoxConfig::HorizontalVerticalLayout:
|
|
|
|
count = qRound(sqrt(float(m_clientList.count())));
|
|
|
|
break;
|
2009-09-13 11:36:45 +00:00
|
|
|
}
|
2011-01-30 14:34:42 +00:00
|
|
|
return qMax(count, 1);
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
QModelIndex ClientModel::parent(const QModelIndex& child) const
|
|
|
|
{
|
|
|
|
Q_UNUSED(child)
|
2009-09-13 11:36:45 +00:00
|
|
|
return QModelIndex();
|
2011-01-30 14:34:42 +00:00
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
QModelIndex ClientModel::index(int row, int column, const QModelIndex& parent) const
|
|
|
|
{
|
|
|
|
Q_UNUSED(parent)
|
2009-09-13 11:36:45 +00:00
|
|
|
int index = row * columnCount() + column;
|
2011-01-30 14:34:42 +00:00
|
|
|
if (index >= m_clientList.count() && !m_clientList.isEmpty())
|
2009-09-13 11:36:45 +00:00
|
|
|
return QModelIndex();
|
2011-01-30 14:34:42 +00:00
|
|
|
return createIndex(row, column);
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
QModelIndex ClientModel::index(TabBoxClient* client) const
|
|
|
|
{
|
|
|
|
if (!m_clientList.contains(client))
|
2009-09-13 11:36:45 +00:00
|
|
|
return QModelIndex();
|
2011-01-30 14:34:42 +00:00
|
|
|
int index = m_clientList.indexOf(client);
|
2009-09-13 11:36:45 +00:00
|
|
|
int row = index / columnCount();
|
|
|
|
int column = index % columnCount();
|
2011-01-30 14:34:42 +00:00
|
|
|
return createIndex(row, column);
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
void ClientModel::createClientList(bool partialReset)
|
|
|
|
{
|
|
|
|
createClientList(tabBox->currentDesktop(), partialReset);
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
void ClientModel::createClientList(int desktop, bool partialReset)
|
|
|
|
{
|
2009-09-13 11:36:45 +00:00
|
|
|
TabBoxClient* start = tabBox->activeClient();
|
|
|
|
// TODO: new clients are not added at correct position
|
2011-01-30 14:34:42 +00:00
|
|
|
if (partialReset && !m_clientList.isEmpty())
|
2009-09-13 11:36:45 +00:00
|
|
|
start = m_clientList.first();
|
|
|
|
|
|
|
|
m_clientList.clear();
|
2011-12-01 12:15:11 +00:00
|
|
|
QList<TabBoxClient*> stickyClients;
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-01-30 14:34:42 +00:00
|
|
|
switch(tabBox->config().clientSwitchingMode()) {
|
|
|
|
case TabBoxConfig::FocusChainSwitching: {
|
|
|
|
TabBoxClient* c = tabBox->nextClientFocusChain(start);
|
|
|
|
TabBoxClient* stop = c;
|
|
|
|
while (c) {
|
2012-03-04 18:24:13 +00:00
|
|
|
TabBoxClient* add = tabBox->clientToAddToList(c, desktop);
|
2011-01-30 14:34:42 +00:00
|
|
|
if (add != NULL) {
|
|
|
|
if (start == add) {
|
|
|
|
m_clientList.removeAll(add);
|
|
|
|
m_clientList.prepend(add);
|
|
|
|
} else
|
|
|
|
m_clientList += add;
|
2011-12-01 12:15:11 +00:00
|
|
|
if (add->isFirstInTabBox()) {
|
|
|
|
stickyClients << add;
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
}
|
2011-01-30 14:34:42 +00:00
|
|
|
c = tabBox->nextClientFocusChain(c);
|
|
|
|
|
|
|
|
if (c == stop)
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
case TabBoxConfig::StackingOrderSwitching: {
|
|
|
|
// TODO: needs improvement
|
|
|
|
TabBoxClientList stacking = tabBox->stackingOrder();
|
|
|
|
TabBoxClient* c = stacking.first();
|
|
|
|
TabBoxClient* stop = c;
|
|
|
|
int index = 0;
|
|
|
|
while (c) {
|
2012-03-04 18:24:13 +00:00
|
|
|
TabBoxClient* add = tabBox->clientToAddToList(c, desktop);
|
2011-01-30 14:34:42 +00:00
|
|
|
if (add != NULL) {
|
|
|
|
if (start == add) {
|
|
|
|
m_clientList.removeAll(add);
|
|
|
|
m_clientList.prepend(add);
|
|
|
|
} else
|
|
|
|
m_clientList += add;
|
2011-12-01 12:15:11 +00:00
|
|
|
if (add->isFirstInTabBox()) {
|
|
|
|
stickyClients << add;
|
|
|
|
}
|
2011-01-30 14:34:42 +00:00
|
|
|
}
|
|
|
|
if (index >= stacking.size() - 1) {
|
|
|
|
c = NULL;
|
|
|
|
} else {
|
|
|
|
c = stacking[++index];
|
2009-09-13 11:36:45 +00:00
|
|
|
}
|
2011-01-30 14:34:42 +00:00
|
|
|
|
|
|
|
if (c == stop)
|
|
|
|
break;
|
2009-09-13 11:36:45 +00:00
|
|
|
}
|
2011-01-30 14:34:42 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
2011-12-01 12:15:11 +00:00
|
|
|
foreach (TabBoxClient *c, stickyClients) {
|
|
|
|
m_clientList.removeAll(c);
|
|
|
|
m_clientList.prepend(c);
|
|
|
|
}
|
2012-03-17 09:31:15 +00:00
|
|
|
if (tabBox->config().showDesktopMode() == TabBoxConfig::ShowDesktopClient || m_clientList.isEmpty()) {
|
2010-03-19 10:15:56 +00:00
|
|
|
TabBoxClient* desktopClient = tabBox->desktopClient();
|
2011-01-30 14:34:42 +00:00
|
|
|
if (desktopClient)
|
|
|
|
m_clientList.append(desktopClient);
|
2009-09-13 11:36:45 +00:00
|
|
|
}
|
2011-01-30 14:34:42 +00:00
|
|
|
reset();
|
|
|
|
}
|
2009-09-13 11:36:45 +00:00
|
|
|
|
2011-11-27 14:00:09 +00:00
|
|
|
void ClientModel::close(int i)
|
|
|
|
{
|
|
|
|
QModelIndex ind = index(i, 0);
|
|
|
|
if (!ind.isValid()) {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
m_clientList.at(i)->close();
|
|
|
|
}
|
|
|
|
|
2011-11-27 16:03:35 +00:00
|
|
|
void ClientModel::activate(int i)
|
|
|
|
{
|
|
|
|
QModelIndex ind = index(i, 0);
|
|
|
|
if (!ind.isValid()) {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
tabBox->setCurrentIndex(ind);
|
|
|
|
tabBox->activateAndClose();
|
|
|
|
}
|
|
|
|
|
2009-09-13 11:36:45 +00:00
|
|
|
} // namespace Tabbox
|
|
|
|
} // namespace KWin
|