1/********************************************************************
2 KWin - the KDE window manager
3 This file is part of the KDE project.
4
5Copyright (C) 2006 Lubos Lunak <l.lunak@kde.org>
6
7This program is free software; you can redistribute it and/or modify
8it under the terms of the GNU General Public License as published by
9the Free Software Foundation; either version 2 of the License, or
10(at your option) any later version.
11
12This program is distributed in the hope that it will be useful,
13but WITHOUT ANY WARRANTY; without even the implied warranty of
14MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15GNU General Public License for more details.
16
17You should have received a copy of the GNU General Public License
18along with this program. If not, see <http://www.gnu.org/licenses/>.
19*********************************************************************/
20
21#include "unmanaged.h"
22
23#include "workspace.h"
24#include "effects.h"
25#include "deleted.h"
26#include "xcbutils.h"
27
28#include <QTimer>
29#include <QDebug>
30
31#include <X11/extensions/shape.h>
32
33namespace KWin
34{
35
36Unmanaged::Unmanaged()
37 : Toplevel()
38{
39 ready_for_painting = false;
40 connect(this, SIGNAL(geometryShapeChanged(KWin::Toplevel*,QRect)), SIGNAL(geometryChanged()));
41 QTimer::singleShot(50, this, SLOT(setReadyForPainting()));
42}
43
44Unmanaged::~Unmanaged()
45{
46}
47
48bool Unmanaged::track(Window w)
49{
50 XWindowAttributes attr;
51 grabXServer();
52 if (!XGetWindowAttributes(display(), w, &attr) || attr.map_state != IsViewable) {
53 ungrabXServer();
54 return false;
55 }
56 if (attr.c_class == InputOnly) {
57 ungrabXServer();
58 return false;
59 }
60 setWindowHandles(w, w); // the window is also the frame
61 XSelectInput(display(), w, attr.your_event_mask | StructureNotifyMask | PropertyChangeMask);
62 geom = QRect(attr.x, attr.y, attr.width, attr.height);
63 checkScreen();
64 vis = attr.visual;
65 bit_depth = attr.depth;
66 unsigned long properties[ 2 ];
67 properties[ NETWinInfo::PROTOCOLS ] =
68 NET::WMWindowType |
69 NET::WMPid |
70 0;
71 properties[ NETWinInfo::PROTOCOLS2 ] =
72 NET::WM2Opacity |
73 0;
74 info = new NETWinInfo2(display(), w, rootWindow(), properties, 2);
75 getResourceClass();
76 getWindowRole();
77 getWmClientLeader();
78 getWmClientMachine();
79 if (Xcb::Extensions::self()->isShapeAvailable())
80 XShapeSelectInput(display(), w, ShapeNotifyMask);
81 detectShape(w);
82 getWmOpaqueRegion();
83 getSkipCloseAnimation();
84 setupCompositing();
85 ungrabXServer();
86 if (effects)
87 static_cast<EffectsHandlerImpl*>(effects)->checkInputWindowStacking();
88 return true;
89}
90
91void Unmanaged::release(bool on_shutdown)
92{
93 Deleted* del = NULL;
94 if (!on_shutdown) {
95 del = Deleted::create(this);
96 }
97 emit windowClosed(this, del);
98 finishCompositing();
99 if (!QWidget::find(window())) { // don't affect our own windows
100 if (Xcb::Extensions::self()->isShapeAvailable())
101 XShapeSelectInput(display(), window(), NoEventMask);
102 XSelectInput(display(), window(), NoEventMask);
103 }
104 if (!on_shutdown) {
105 workspace()->removeUnmanaged(this);
106 addWorkspaceRepaint(del->visibleRect());
107 disownDataPassedToDeleted();
108 del->unrefWindow();
109 }
110 deleteUnmanaged(this);
111}
112
113void Unmanaged::deleteUnmanaged(Unmanaged* c)
114{
115 delete c;
116}
117
118int Unmanaged::desktop() const
119{
120 return NET::OnAllDesktops; // TODO for some window types should be the current desktop?
121}
122
123QStringList Unmanaged::activities() const
124{
125 return QStringList();
126}
127
128QPoint Unmanaged::clientPos() const
129{
130 return QPoint(0, 0); // unmanaged windows don't have decorations
131}
132
133QSize Unmanaged::clientSize() const
134{
135 return size();
136}
137
138QRect Unmanaged::transparentRect() const
139{
140 return QRect(clientPos(), clientSize());
141}
142
143void Unmanaged::debug(QDebug& stream) const
144{
145 stream << "\'ID:" << window() << "\'";
146}
147
148NET::WindowType Unmanaged::windowType(bool direct, int supportedTypes) const
149{
150 // for unmanaged windows the direct does not make any difference
151 // as there are no rules to check and no hacks to apply
152 Q_UNUSED(direct)
153 if (supportedTypes == 0) {
154 supportedTypes = SUPPORTED_UNMANAGED_WINDOW_TYPES_MASK;
155 }
156 return info->windowType(supportedTypes);
157}
158
159} // namespace
160
161#include "unmanaged.moc"
162