~ubuntu-branches/ubuntu/utopic/kde-workspace/utopic-proposed

« back to all changes in this revision

Viewing changes to kwin/effects/thumbnailaside/thumbnailaside.cpp

  • Committer: Bazaar Package Importer
  • Author(s): Michał Zając
  • Date: 2011-07-09 08:31:15 UTC
  • Revision ID: james.westby@ubuntu.com-20110709083115-ohyxn6z93mily9fc
Tags: upstream-4.6.90
Import upstream version 4.6.90

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/********************************************************************
 
2
 KWin - the KDE window manager
 
3
 This file is part of the KDE project.
 
4
 
 
5
Copyright (C) 2007 Lubos Lunak <l.lunak@kde.org>
 
6
Copyright (C) 2007 Christian Nitschkowski <christian.nitschkowski@kdemail.net>
 
7
 
 
8
This program is free software; you can redistribute it and/or modify
 
9
it under the terms of the GNU General Public License as published by
 
10
the Free Software Foundation; either version 2 of the License, or
 
11
(at your option) any later version.
 
12
 
 
13
This program is distributed in the hope that it will be useful,
 
14
but WITHOUT ANY WARRANTY; without even the implied warranty of
 
15
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
16
GNU General Public License for more details.
 
17
 
 
18
You should have received a copy of the GNU General Public License
 
19
along with this program.  If not, see <http://www.gnu.org/licenses/>.
 
20
*********************************************************************/
 
21
 
 
22
#include "thumbnailaside.h"
 
23
 
 
24
#include <kactioncollection.h>
 
25
#include <kaction.h>
 
26
#include <kconfiggroup.h>
 
27
#include <klocale.h>
 
28
 
 
29
namespace KWin
 
30
{
 
31
 
 
32
KWIN_EFFECT(thumbnailaside, ThumbnailAsideEffect)
 
33
 
 
34
ThumbnailAsideEffect::ThumbnailAsideEffect()
 
35
{
 
36
    KActionCollection* actionCollection = new KActionCollection(this);
 
37
    KAction* a = (KAction*)actionCollection->addAction("ToggleCurrentThumbnail");
 
38
    a->setText(i18n("Toggle Thumbnail for Current Window"));
 
39
    a->setGlobalShortcut(KShortcut(Qt::CTRL + Qt::META + Qt::Key_T));
 
40
    connect(a, SIGNAL(triggered(bool)), this, SLOT(toggleCurrentThumbnail()));
 
41
    connect(effects, SIGNAL(windowClosed(EffectWindow*)), this, SLOT(slotWindowClosed(EffectWindow*)));
 
42
    connect(effects, SIGNAL(windowGeometryShapeChanged(EffectWindow*,QRect)), this, SLOT(slotWindowGeometryShapeChanged(EffectWindow*,QRect)));
 
43
    connect(effects, SIGNAL(windowDamaged(EffectWindow*,QRect)), this, SLOT(slotWindowDamaged(EffectWindow*,QRect)));
 
44
    reconfigure(ReconfigureAll);
 
45
}
 
46
 
 
47
void ThumbnailAsideEffect::reconfigure(ReconfigureFlags)
 
48
{
 
49
    KConfigGroup conf = EffectsHandler::effectConfig("ThumbnailAside");
 
50
    maxwidth = conf.readEntry("MaxWidth", 200);
 
51
    spacing = conf.readEntry("Spacing", 10);
 
52
    opacity = conf.readEntry("Opacity", 50) / 100.0;
 
53
    screen = conf.readEntry("Screen", -1); // Xinerama screen TODO add gui option
 
54
    arrange();
 
55
}
 
56
 
 
57
void ThumbnailAsideEffect::paintScreen(int mask, QRegion region, ScreenPaintData& data)
 
58
{
 
59
    effects->paintScreen(mask, region, data);
 
60
    foreach (const Data & d, windows) {
 
61
        if (region.contains(d.rect)) {
 
62
            WindowPaintData data(d.window);
 
63
            data.opacity = opacity;
 
64
            QRect region;
 
65
            setPositionTransformations(data, region, d.window, d.rect, Qt::KeepAspectRatio);
 
66
            effects->drawWindow(d.window, PAINT_WINDOW_OPAQUE | PAINT_WINDOW_TRANSLUCENT | PAINT_WINDOW_TRANSFORMED | PAINT_WINDOW_LANCZOS,
 
67
                                region, data);
 
68
        }
 
69
    }
 
70
}
 
71
 
 
72
void ThumbnailAsideEffect::slotWindowDamaged(EffectWindow* w, const QRect&)
 
73
{
 
74
    foreach (const Data & d, windows) {
 
75
        if (d.window == w)
 
76
            effects->addRepaint(d.rect);
 
77
    }
 
78
}
 
79
 
 
80
void ThumbnailAsideEffect::slotWindowGeometryShapeChanged(EffectWindow* w, const QRect& old)
 
81
{
 
82
    foreach (const Data & d, windows) {
 
83
        if (d.window == w) {
 
84
            if (w->size() == old.size())
 
85
                effects->addRepaint(d.rect);
 
86
            else
 
87
                arrange();
 
88
            return;
 
89
        }
 
90
    }
 
91
}
 
92
 
 
93
void ThumbnailAsideEffect::slotWindowClosed(EffectWindow* w)
 
94
{
 
95
    removeThumbnail(w);
 
96
}
 
97
 
 
98
void ThumbnailAsideEffect::toggleCurrentThumbnail()
 
99
{
 
100
    EffectWindow* active = effects->activeWindow();
 
101
    if (active == NULL)
 
102
        return;
 
103
    if (windows.contains(active))
 
104
        removeThumbnail(active);
 
105
    else
 
106
        addThumbnail(active);
 
107
}
 
108
 
 
109
void ThumbnailAsideEffect::addThumbnail(EffectWindow* w)
 
110
{
 
111
    repaintAll(); // repaint old areas
 
112
    Data d;
 
113
    d.window = w;
 
114
    d.index = windows.count();
 
115
    windows[ w ] = d;
 
116
    arrange();
 
117
}
 
118
 
 
119
void ThumbnailAsideEffect::removeThumbnail(EffectWindow* w)
 
120
{
 
121
    if (!windows.contains(w))
 
122
        return;
 
123
    repaintAll(); // repaint old areas
 
124
    int index = windows[ w ].index;
 
125
    windows.remove(w);
 
126
    for (QHash< EffectWindow*, Data >::Iterator it = windows.begin();
 
127
            it != windows.end();
 
128
            ++it) {
 
129
        Data& d = *it;
 
130
        if (d.index > index)
 
131
            --d.index;
 
132
    }
 
133
    arrange();
 
134
}
 
135
 
 
136
void ThumbnailAsideEffect::arrange()
 
137
{
 
138
    if (windows.size() == 0)
 
139
        return;
 
140
    int height = 0;
 
141
    QVector< int > pos(windows.size());
 
142
    int mwidth = 0;
 
143
    foreach (const Data & d, windows) {
 
144
        height += d.window->height();
 
145
        mwidth = qMax(mwidth, d.window->width());
 
146
        pos[ d.index ] = d.window->height();
 
147
    }
 
148
    QRect area = effects->clientArea(MaximizeArea, screen, effects->currentDesktop());
 
149
    double scale = area.height() / double(height);
 
150
    scale = qMin(scale, maxwidth / double(mwidth));    // don't be wider than maxwidth pixels
 
151
    int add = 0;
 
152
    for (int i = 0;
 
153
            i < windows.size();
 
154
            ++i) {
 
155
        pos[ i ] = int(pos[ i ] * scale);
 
156
        pos[ i ] += spacing + add; // compute offset of each item
 
157
        add = pos[ i ];
 
158
    }
 
159
    for (QHash< EffectWindow*, Data >::Iterator it = windows.begin();
 
160
            it != windows.end();
 
161
            ++it) {
 
162
        Data& d = *it;
 
163
        int width = int(d.window->width() * scale);
 
164
        d.rect = QRect(area.right() - width, area.bottom() - pos[ d.index ], width, int(d.window->height() * scale));
 
165
    }
 
166
    repaintAll();
 
167
}
 
168
 
 
169
void ThumbnailAsideEffect::repaintAll()
 
170
{
 
171
    foreach (const Data & d, windows)
 
172
    effects->addRepaint(d.rect);
 
173
}
 
174
 
 
175
} // namespace
 
176
 
 
177
#include "thumbnailaside.moc"