00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
#include <stdlib.h>
00023
#include <unistd.h>
00024
00025
#ifdef HAVE_SYSENT_H
00026
#include <sysent.h>
00027
#endif
00028
00029
#include <qapplication.h>
00030
#include <qbitmap.h>
00031
#include <qimage.h>
00032
#include <qwhatsthis.h>
00033
#include <qcstring.h>
00034
00035
#include "config.h"
00036
00037
#include "kwin.h"
00038
#include "kapplication.h"
00039
00040
#include <kglobal.h>
00041
#include <kiconloader.h>
00042
#include <kdebug.h>
00043
00044
#include <kdatastream.h>
00045
#include <klocale.h>
00046
#include <dcopclient.h>
00047
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00048
#include <kstartupinfo.h>
00049
#include <kxerrorhandler.h>
00050
00051
#include <X11/Xlib.h>
00052
#include <X11/Xatom.h>
00053
#include <X11/Xutil.h>
00054
00055
#include "netwm.h"
00056
00057
static bool atoms_created =
false;
00058
extern Atom qt_wm_protocols;
00059
extern Time qt_x_time;
00060
extern Time qt_x_user_time;
00061
00062
static Atom net_wm_context_help;
00063
static Atom kde_wm_change_state;
00064
static void kwin_net_create_atoms() {
00065
if (!atoms_created){
00066
const int max = 20;
00067 Atom* atoms[max];
00068
const char* names[max];
00069 Atom atoms_return[max];
00070
int n = 0;
00071
00072 atoms[n] = &net_wm_context_help;
00073 names[n++] =
"_NET_WM_CONTEXT_HELP";
00074
00075 atoms[n] = &kde_wm_change_state;
00076 names[n++] =
"_KDE_WM_CHANGE_STATE";
00077
00078
00079 XInternAtoms( qt_xdisplay(), const_cast<char**>(names), n,
false, atoms_return );
00080
for (
int i = 0; i < n; i++ )
00081 *atoms[i] = atoms_return[i];
00082
00083 atoms_created = True;
00084 }
00085 }
00086
#endif
00087
00088
00089
00090
00091
static void sendClientMessageToRoot(Window w, Atom a,
long x,
long y = 0,
long z = 0 ){
00092
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00093
XEvent ev;
00094
long mask;
00095
00096 memset(&ev, 0,
sizeof(ev));
00097 ev.xclient.type = ClientMessage;
00098 ev.xclient.window = w;
00099 ev.xclient.message_type = a;
00100 ev.xclient.format = 32;
00101 ev.xclient.data.l[0] = x;
00102 ev.xclient.data.l[1] = y;
00103 ev.xclient.data.l[2] = z;
00104 mask = SubstructureRedirectMask;
00105 XSendEvent(qt_xdisplay(), qt_xrootwin(), False, mask, &ev);
00106
#endif
00107
}
00108
00109
00110
00111
00112
static void sendClientMessage(Window w, Atom a,
long x){
00113
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00114
XEvent ev;
00115
long mask;
00116
00117 memset(&ev, 0,
sizeof(ev));
00118 ev.xclient.type = ClientMessage;
00119 ev.xclient.window = w;
00120 ev.xclient.message_type = a;
00121 ev.xclient.format = 32;
00122 ev.xclient.data.l[0] = x;
00123 ev.xclient.data.l[1] = CurrentTime;
00124 mask = 0L;
00125
if (w == qt_xrootwin())
00126 mask = SubstructureRedirectMask;
00127 XSendEvent(qt_xdisplay(), w, False, mask, &ev);
00128
#endif
00129
}
00130
00131
namespace
00132
{
00133
class ContextWidget :
public QWidget
00134 {
00135
public:
00136 ContextWidget();
00137
virtual bool x11Event( XEvent * ev);
00138 };
00139
00140 ContextWidget::ContextWidget()
00141 :
QWidget(0,0)
00142 {
00143
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00144
kwin_net_create_atoms();
00145 kapp->installX11EventFilter(
this );
00146
QWhatsThis::enterWhatsThisMode();
00147
QCursor c = *
QApplication::overrideCursor();
00148
QWhatsThis::leaveWhatsThisMode();
00149 XGrabPointer( qt_xdisplay(), qt_xrootwin(),
true,
00150 (uint)( ButtonPressMask | ButtonReleaseMask |
00151 PointerMotionMask | EnterWindowMask |
00152 LeaveWindowMask ),
00153 GrabModeAsync, GrabModeAsync,
00154 None, c.
handle(), CurrentTime );
00155 qApp->enter_loop();
00156
#endif
00157
}
00158
00159
00160
bool ContextWidget::x11Event( XEvent * ev)
00161 {
00162
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00163
if ( ev->type == ButtonPress && ev->xbutton.button == Button1 ) {
00164 XUngrabPointer( qt_xdisplay(), ev->xbutton.time );
00165 Window root;
00166 Window child = qt_xrootwin();
00167
int root_x, root_y, lx, ly;
00168 uint state;
00169 Window w;
00170
do {
00171 w = child;
00172 XQueryPointer( qt_xdisplay(), w, &root, &child,
00173 &root_x, &root_y, &lx, &ly, &state );
00174 }
while ( child != None && child != w );
00175
00176 ::sendClientMessage(w, qt_wm_protocols, net_wm_context_help);
00177 XEvent e = *ev;
00178 e.xbutton.window = w;
00179 e.xbutton.subwindow = w;
00180 e.xbutton.x = lx;
00181 e.xbutton.y = ly;
00182 XSendEvent( qt_xdisplay(), w,
true, ButtonPressMask, &e );
00183 qApp->exit_loop();
00184
return true;
00185 }
00186
return false;
00187
#endif
00188
}
00189 }
00190
00191 void KWin::invokeContextHelp()
00192 {
00193 ContextWidget w;
00194 }
00195
00196 void KWin::setSystemTrayWindowFor( WId trayWin, WId forWin )
00197 {
00198
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00199
NETWinInfo
info( qt_xdisplay(), trayWin, qt_xrootwin(), 0 );
00200
if ( !forWin )
00201 forWin = qt_xrootwin();
00202 info.setKDESystemTrayWinFor( forWin );
00203
#endif
00204
}
00205
00206 void KWin::activateWindow( WId win,
long time )
00207 {
00208
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00209
NETRootInfo
info( qt_xdisplay(), 0 );
00210
if( time == 0 )
00211 time = qt_x_user_time;
00212 info.setActiveWindow( win, NET::FromApplication, time,
00213 kapp->activeWindow() ? kapp->activeWindow()->winId() : 0 );
00214
#endif // Q_WS_X11 ...
00215
}
00216
00217 void KWin::forceActiveWindow( WId win,
long time )
00218 {
00219
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00220
NETRootInfo
info( qt_xdisplay(), 0 );
00221
if( time == 0 )
00222 time = qt_x_time;
00223 info.setActiveWindow( win, NET::FromTool, time, 0 );
00224
#endif // Q_WS_X11 ...
00225
}
00226
00227 void KWin::setActiveWindow( WId win )
00228 {
00229
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00230
NETRootInfo
info( qt_xdisplay(), 0 );
00231 info.setActiveWindow( win, NET::FromUnknown, 0, 0 );
00232
#endif
00233
}
00234
00235 void KWin::demandAttention( WId win,
bool set )
00236 {
00237
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00238
NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), 0 );
00239 info.setState( set ? NET::DemandsAttention : 0, NET::DemandsAttention );
00240
#endif
00241
}
00242
00243 void KWin::setUserTime( WId win,
long time )
00244 {
00245
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00246
NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), 0 );
00247 info.setUserTime( time );
00248
#endif
00249
}
00250
00251 KWin::WindowInfo KWin::windowInfo( WId win,
unsigned long properties,
unsigned long properties2 )
00252 {
00253
return WindowInfo( win, properties, properties2 );
00254 }
00255
00256
00257 WId
KWin::transientFor( WId win )
00258 {
00259
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00260
KXErrorHandler handler;
00261 Window transient_for = None;
00262
if( XGetTransientForHint( qt_xdisplay(), win, &transient_for ))
00263
return transient_for;
00264
00265
return None;
00266
#else
00267
return 0L;
00268
#endif
00269
}
00270
00271 WId
KWin::groupLeader( WId win )
00272 {
00273
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00274
KXErrorHandler handler;
00275 XWMHints *hints = XGetWMHints( qt_xdisplay(), win );
00276 Window window_group = None;
00277
if ( hints )
00278 {
00279
if( hints->flags & WindowGroupHint )
00280 window_group = hints->window_group;
00281 XFree( reinterpret_cast< char* >( hints ));
00282 }
00283
00284
return window_group;
00285
#else
00286
return 0L;
00287
#endif
00288
}
00289
00290
00291 KWin::Info KWin::info( WId win )
00292 {
00293
Info w;
00294
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00295
NETWinInfo inf( qt_xdisplay(), win, qt_xrootwin(),
00296 NET::WMState |
00297 NET::WMStrut |
00298 NET::WMWindowType |
00299 NET::WMName |
00300 NET::WMVisibleName |
00301 NET::WMDesktop |
00302 NET::WMPid |
00303 NET::WMKDEFrameStrut |
00304 NET::XAWMState
00305 );
00306
00307 w.
win = win;
00308 w.
state = inf.state();
00309 w.
mappingState = inf.mappingState();
00310 w.
strut = inf.strut();
00311 w.
windowType = inf.windowType();
00312
if ( inf.name() ) {
00313 w.
name =
QString::fromUtf8( inf.name() );
00314 }
else {
00315
char* c = 0;
00316
if ( XFetchName( qt_xdisplay(), win, &c ) != 0 ) {
00317 w.
name =
QString::fromLocal8Bit( c );
00318 XFree( c );
00319 }
00320 }
00321
if ( inf.visibleName() )
00322 w.
visibleName =
QString::fromUtf8( inf.visibleName() );
00323
else
00324 w.
visibleName = w.
name;
00325
00326 w.
desktop = inf.desktop();
00327 w.
onAllDesktops = inf.desktop() == NETWinInfo::OnAllDesktops;
00328 w.
pid = inf.pid();
00329
NETRect frame, geom;
00330 inf.kdeGeometry( frame, geom );
00331 w.
geometry.
setRect( geom.
pos.
x, geom.
pos.
y, geom.
size.
width, geom.
size.
height );
00332 w.
frameGeometry.
setRect( frame.
pos.
x, frame.
pos.
y, frame.
size.
width, frame.
size.
height );
00333
#endif
00334
return w;
00335 }
00336
00337 QPixmap KWin::icon( WId win,
int width,
int height,
bool scale )
00338 {
00339
return icon( win, width, height, scale,
NETWM |
WMHints |
ClassHint |
XApp );
00340 }
00341
00342
00343 QPixmap KWin::icon( WId win,
int width,
int height,
bool scale,
int flags )
00344 {
00345
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00346
KXErrorHandler handler;
00347
#endif
00348
QPixmap result;
00349
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00350
if( flags &
NETWM ) {
00351 NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), NET::WMIcon );
00352
NETIcon ni = info.icon( width, height );
00353
if ( ni.
data && ni.
size.
width > 0 && ni.
size.
height > 0 ) {
00354
QImage img( (uchar*) ni.
data, (
int) ni.
size.
width, (
int) ni.
size.
height, 32, 0, 0, QImage::IgnoreEndian );
00355 img.setAlphaBuffer(
true );
00356
if ( scale && width > 0 && height > 0 &&img.size() !=
QSize( width, height ) && !img.isNull() )
00357 img = img.smoothScale( width, height );
00358
if ( !img.isNull() )
00359 result.
convertFromImage( img );
00360
return result;
00361 }
00362 }
00363
00364
if( flags &
WMHints ) {
00365 Pixmap p = None;
00366 Pixmap p_mask = None;
00367
00368 XWMHints *hints = XGetWMHints(qt_xdisplay(), win );
00369
if (hints && (hints->flags & IconPixmapHint)){
00370 p = hints->icon_pixmap;
00371 }
00372
if (hints && (hints->flags & IconMaskHint)){
00373 p_mask = hints->icon_mask;
00374 }
00375
if (hints)
00376 XFree((
char*)hints);
00377
00378
if (p != None){
00379 Window root;
00380
int x, y;
00381
unsigned int w = 0;
00382
unsigned int h = 0;
00383
unsigned int border_w, depth;
00384 XGetGeometry(qt_xdisplay(), p, &root,
00385 &x, &y, &w, &h, &border_w, &depth);
00386
if (w > 0 && h > 0){
00387
QPixmap pm(w, h, depth);
00388
00389 pm.
detach();
00390 XCopyArea(qt_xdisplay(), p, pm.handle(),
00391 qt_xget_temp_gc(qt_xscreen(), depth==1),
00392 0, 0, w, h, 0, 0);
00393
if (p_mask != None){
00394
QBitmap bm(w, h);
00395 XCopyArea(qt_xdisplay(), p_mask, bm.handle(),
00396 qt_xget_temp_gc(qt_xscreen(),
true),
00397 0, 0, w, h, 0, 0);
00398 pm.
setMask(bm);
00399 }
00400
if ( scale && width > 0 && height > 0 && !pm.
isNull() &&
00401 ( (
int) w != width || (
int) h != height) ){
00402 result.
convertFromImage( pm.
convertToImage().smoothScale( width, height ) );
00403 }
else {
00404 result = pm;
00405 }
00406 }
00407 }
00408 }
00409
00410
00411
00412
00413
int iconWidth;
00414
if( width < 24 )
00415 iconWidth = 16;
00416
else if( width < 40 )
00417 iconWidth = 32;
00418
else
00419 iconWidth = 48;
00420
00421
if( flags &
ClassHint ) {
00422
00423
00424
if( result.
isNull() ) {
00425
00426 XClassHint hint;
00427
if( XGetClassHint( qt_xdisplay(), win, &hint ) ) {
00428
QString className = hint.res_class;
00429
00430
QPixmap pm =
KGlobal::instance()->
iconLoader()->
loadIcon( className.
lower(), KIcon::Small, iconWidth,
00431 KIcon::DefaultState, 0,
true );
00432
if( scale && !pm.
isNull() )
00433 result.
convertFromImage( pm.
convertToImage().smoothScale( width, height ) );
00434
else
00435 result = pm;
00436
00437 XFree( hint.res_name );
00438 XFree( hint.res_class );
00439 }
00440 }
00441 }
00442
00443
if( flags &
XApp ) {
00444
00445
00446
if ( result.
isNull() ) {
00447
QPixmap pm =
KGlobal::instance()->
iconLoader()->
loadIcon(
"xapp", KIcon::Small, iconWidth,
00448 KIcon::DefaultState, 0,
true );
00449
if( scale && !pm.
isNull() )
00450 result.
convertFromImage( pm.
convertToImage().smoothScale( width, height ) );
00451
else
00452 result = pm;
00453 }
00454 }
00455
#endif
00456
return result;
00457 }
00458
00459 void KWin::setIcons( WId win,
const QPixmap& icon,
const QPixmap& miniIcon )
00460 {
00461
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00462
if ( icon.
isNull() )
00463
return;
00464 NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), 0 );
00465
QImage img = icon.
convertToImage().convertDepth( 32 );
00466
NETIcon ni;
00467 ni.
size.
width = img.
size().width();
00468 ni.
size.
height = img.
size().height();
00469 ni.
data = (
unsigned char *) img.
bits();
00470 info.setIcon( ni,
true );
00471
if ( miniIcon.
isNull() )
00472
return;
00473 img = miniIcon.
convertToImage().convertDepth( 32 );
00474 ni.
size.
width = img.
size().width();
00475 ni.
size.
height = img.
size().height();
00476 ni.
data = (
unsigned char *) img.
bits();
00477 info.setIcon( ni,
false );
00478
#endif
00479
}
00480
00481 void KWin::setType( WId win, NET::WindowType windowType )
00482 {
00483
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00484
NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), 0 );
00485 info.setWindowType( windowType );
00486
#endif
00487
}
00488
00489 void KWin::setState( WId win,
unsigned long state )
00490 {
00491
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00492
NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), NET::WMState );
00493 info.setState( state, state );
00494
#endif
00495
}
00496
00497 void KWin::clearState( WId win,
unsigned long state )
00498 {
00499
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00500
NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), NET::WMState );
00501 info.setState( 0, state );
00502
#endif
00503
}
00504
00505 void KWin::setOnAllDesktops( WId win,
bool b )
00506 {
00507
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00508
NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), NET::WMDesktop );
00509
if ( b )
00510 info.setDesktop( NETWinInfo::OnAllDesktops );
00511
else if ( info.desktop() == NETWinInfo::OnAllDesktops ) {
00512 NETRootInfo rinfo( qt_xdisplay(), NET::CurrentDesktop );
00513 info.setDesktop( rinfo.currentDesktop() );
00514 }
00515
#endif
00516
}
00517
00518 void KWin::setOnDesktop( WId win,
int desktop )
00519 {
00520
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00521
NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), NET::WMDesktop );
00522 info.setDesktop( desktop );
00523
#endif
00524
}
00525
00526 void KWin::setStrut( WId win,
int left,
int right,
int top,
int bottom )
00527 {
00528
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00529
NETWinInfo
info( qt_xdisplay(), win, qt_xrootwin(), 0 );
00530
NETStrut strut;
00531 strut.
left = left;
00532 strut.
right = right;
00533 strut.
top = top;
00534 strut.
bottom = bottom;
00535 info.setStrut( strut );
00536
#endif
00537
}
00538
00539 int KWin::currentDesktop()
00540 {
00541
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00542
if (!qt_xdisplay())
00543
#endif
00544
return 1;
00545
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00546
NETRootInfo
info( qt_xdisplay(), NET::CurrentDesktop );
00547
return info.currentDesktop();
00548
#endif
00549
}
00550
00551 int KWin::numberOfDesktops()
00552 {
00553
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00554
if (!qt_xdisplay())
00555
#endif
00556
return 0;
00557
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00558
NETRootInfo
info( qt_xdisplay(), NET::NumberOfDesktops );
00559
return info.numberOfDesktops();
00560
#endif
00561
}
00562
00563 void KWin::setCurrentDesktop(
int desktop )
00564 {
00565
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00566
NETRootInfo
info( qt_xdisplay(), NET::CurrentDesktop );
00567 info.setCurrentDesktop( desktop );
00568
#endif
00569
}
00570
00571
00572 void KWin::iconifyWindow( WId win,
bool animation)
00573 {
00574
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00575
if ( !animation )
00576 {
00577 kwin_net_create_atoms();
00578 sendClientMessageToRoot( win, kde_wm_change_state, IconicState, 1 );
00579 }
00580 XIconifyWindow( qt_xdisplay(), win, qt_xscreen() );
00581
#endif
00582
}
00583
00584
00585 void KWin::deIconifyWindow( WId win,
bool animation )
00586 {
00587
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00588
if ( !animation )
00589 {
00590 kwin_net_create_atoms();
00591 sendClientMessageToRoot( win, kde_wm_change_state, NormalState, 1 );
00592 }
00593 XMapWindow( qt_xdisplay(), win );
00594
#endif
00595
}
00596
00597 void KWin::raiseWindow( WId win )
00598 {
00599
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00600
NETRootInfo
info( qt_xdisplay(), NET::Supported );
00601
if( info.isSupported( NET::WM2RestackWindow ))
00602 info.restackRequest( win, None, Above );
00603
else
00604 XRaiseWindow( qt_xdisplay(), win );
00605
#endif
00606
}
00607
00608 void KWin::lowerWindow( WId win )
00609 {
00610
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00611
NETRootInfo
info( qt_xdisplay(), NET::Supported );
00612
if( info.isSupported( NET::WM2RestackWindow ))
00613 info.restackRequest( win, None, Below );
00614
else
00615 XLowerWindow( qt_xdisplay(), win );
00616
#endif
00617
}
00618
00619 void KWin::appStarted()
00620 {
00621
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00622
KStartupInfo::appStarted();
00623
#endif
00624
}
00625
00626
class KWin::WindowInfoPrivate
00627 {
00628
public:
00629 WindowInfoPrivate()
00630 #
if defined Q_WS_X11 && ! defined K_WS_QTONLY
00631 :
info( NULL )
00632 #endif
00633 {}
00634
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00635
~WindowInfoPrivate() {
delete info; }
00636 NETWinInfo* info;
00637
#endif
00638
WId win_;
00639
QString name_;
00640
QString iconic_name_;
00641
QRect geometry_;
00642
QRect frame_geometry_;
00643
int ref;
00644
bool valid;
00645
private:
00646 WindowInfoPrivate(
const WindowInfoPrivate& );
00647
void operator=(
const WindowInfoPrivate& );
00648 };
00649
00650
00651 KWin::WindowInfo::WindowInfo( WId win,
unsigned long properties,
unsigned long properties2 )
00652 {
00653
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00654
KXErrorHandler handler;
00655 d =
new WindowInfoPrivate;
00656 d->ref = 1;
00657
if( properties == 0 )
00658 properties = NET::WMState |
00659 NET::WMStrut |
00660 NET::WMWindowType |
00661 NET::WMName |
00662 NET::WMVisibleName |
00663 NET::WMIconName |
00664 NET::WMVisibleIconName |
00665 NET::WMDesktop |
00666 NET::WMPid |
00667 NET::WMKDEFrameStrut |
00668 NET::XAWMState |
00669 NET::WMGeometry;
00670
if( properties & NET::WMVisibleIconName )
00671 properties |= NET::WMIconName | NET::WMVisibleName;
00672
if( properties & NET::WMVisibleName )
00673 properties |= NET::WMName;
00674 properties |= NET::XAWMState;
00675
unsigned long props[ 2 ] = { properties, properties2 };
00676 d->info =
new NETWinInfo( qt_xdisplay(), win, qt_xrootwin(), props, 2 );
00677 d->win_ = win;
00678
if( properties & NET::WMName ) {
00679
if( d->info->name() && d->info->name()[ 0 ] !=
'\0' )
00680 d->name_ =
QString::fromUtf8( d->info->name() );
00681
else
00682 d->name_ =
readNameProperty( win, XA_WM_NAME );
00683 }
00684
if( properties & NET::WMIconName ) {
00685
if( d->info->iconName() && d->info->iconName()[ 0 ] !=
'\0' )
00686 d->iconic_name_ =
QString::fromUtf8( d->info->iconName());
00687
else
00688 d->iconic_name_ =
readNameProperty( win, XA_WM_ICON_NAME );
00689 }
00690
if( properties & ( NET::WMGeometry | NET::WMKDEFrameStrut )) {
00691
NETRect frame, geom;
00692 d->info->kdeGeometry( frame, geom );
00693 d->geometry_.setRect( geom.
pos.
x, geom.
pos.
y, geom.
size.
width, geom.
size.
height );
00694 d->frame_geometry_.setRect( frame.
pos.
x, frame.
pos.
y, frame.
size.
width, frame.
size.
height );
00695 }
00696 d->valid = !handler.
error(
false );
00697
#endif
00698
}
00699
00700
00701
KWin::WindowInfo::WindowInfo()
00702 : d( NULL )
00703 {
00704 }
00705
00706 KWin::WindowInfo::~WindowInfo()
00707 {
00708
if( d != NULL ) {
00709
if( --d->ref == 0 ) {
00710
delete d;
00711 }
00712 }
00713 }
00714
00715
KWin::WindowInfo::WindowInfo(
const WindowInfo& wininfo )
00716 : d( wininfo.d )
00717 {
00718
if( d != NULL )
00719 ++d->ref;
00720 }
00721
00722
KWin::WindowInfo& KWin::WindowInfo::operator=(
const WindowInfo& wininfo )
00723 {
00724
if( d != wininfo.d ) {
00725
if( d != NULL )
00726
if( --d->ref == 0 )
00727
delete d;
00728 d = wininfo.d;
00729
if( d != NULL )
00730 ++d->ref;
00731 }
00732
return *
this;
00733 }
00734
00735 bool KWin::WindowInfo::valid(
bool withdrawn_is_valid )
const
00736
{
00737
if( !d->valid )
00738
return false;
00739
if( !withdrawn_is_valid &&
mappingState() == NET::Withdrawn )
00740
return false;
00741
return true;
00742 }
00743
00744 WId
KWin::WindowInfo::win()
const
00745
{
00746
return d->win_;
00747 }
00748
00749 unsigned long KWin::WindowInfo::state()
const
00750
{
00751
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00752
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMState ) == 0, 176 )
00753 <<
"Pass NET::WMState to KWin::windowInfo()" <<
endl;
00754
return d->info->state();
00755
#else
00756
return 0;
00757
#endif
00758
}
00759
00760 NET::MappingState
KWin::WindowInfo::mappingState()
const
00761
{
00762
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00763
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::XAWMState ) == 0, 176 )
00764 <<
"Pass NET::XAWMState to KWin::windowInfo()" <<
endl;
00765
return d->info->mappingState();
00766
#else
00767
return 0;
00768
#endif
00769
}
00770
00771 NETStrut KWin::WindowInfo::strut()
const
00772
{
00773
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00774
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMStrut ) == 0, 176 )
00775 <<
"Pass NET::WMStrut to KWin::windowInfo()" <<
endl;
00776
return d->info->strut();
00777
#else
00778
NETStrut n;
00779
return n;
00780
#endif
00781
}
00782
00783 NET::WindowType
KWin::WindowInfo::windowType(
int supported_types )
const
00784
{
00785
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00786
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMWindowType ) == 0, 176 )
00787 <<
"Pass NET::WMWindowType to KWin::windowInfo()" <<
endl;
00788
return d->info->windowType( supported_types );
00789
#else
00790
return 0;
00791
#endif
00792
}
00793
00794 QString KWin::WindowInfo::visibleNameWithState()
const
00795
{
00796
QString s =
visibleName();
00797
if (
isMinimized() ) {
00798 s.
prepend(
'(');
00799 s.
append(
')');
00800 }
00801
return s;
00802 }
00803
00804
QString KWin::Info::visibleNameWithState()
const
00805
{
00806
QString s = visibleName;
00807
if (
isMinimized() ) {
00808 s.
prepend(
'(');
00809 s.
append(
')');
00810 }
00811
return s;
00812 }
00813
00814 QString KWin::WindowInfo::visibleName()
const
00815
{
00816
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00817
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMVisibleName ) == 0, 176 )
00818 <<
"Pass NET::WMVisibleName to KWin::windowInfo()" <<
endl;
00819
return d->info->visibleName() && d->info->visibleName()[ 0 ] !=
'\0'
00820 ?
QString::fromUtf8(d->info->visibleName()) :
name();
00821
#else
00822
return QString(
"name");
00823
#endif
00824
}
00825
00826 QString KWin::WindowInfo::name()
const
00827
{
00828
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00829
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMName ) == 0, 176 )
00830 <<
"Pass NET::WMName to KWin::windowInfo()" <<
endl;
00831
return d->name_;
00832
#else
00833
return QString();
00834
#endif
00835
}
00836
00837 QString KWin::WindowInfo::visibleIconNameWithState()
const
00838
{
00839
QString s =
visibleIconName();
00840
if (
isMinimized() ) {
00841 s.
prepend(
'(');
00842 s.
append(
')');
00843 }
00844
return s;
00845 }
00846
00847 QString KWin::WindowInfo::visibleIconName()
const
00848
{
00849
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00850
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMVisibleIconName ) == 0, 176 )
00851 <<
"Pass NET::WMVisibleIconName to KWin::windowInfo()" <<
endl;
00852
if( d->info->visibleIconName() && d->info->visibleIconName()[ 0 ] !=
'\0' )
00853
return QString::fromUtf8( d->info->visibleIconName());
00854
if( d->info->iconName() && d->info->iconName()[ 0 ] !=
'\0' )
00855
return QString::fromUtf8( d->info->iconName());
00856
if( !d->iconic_name_.isEmpty())
00857
return d->iconic_name_;
00858
#endif
00859
return visibleName();
00860 }
00861
00862 QString KWin::WindowInfo::iconName()
const
00863
{
00864
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00865
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMIconName ) == 0, 176 )
00866 <<
"Pass NET::WMIconName to KWin::windowInfo()" <<
endl;
00867
if( d->info->iconName() && d->info->iconName()[ 0 ] !=
'\0' )
00868
return QString::fromUtf8( d->info->iconName());
00869
if( !d->iconic_name_.isEmpty())
00870
return d->iconic_name_;
00871
#endif
00872
return name();
00873 }
00874
00875 bool KWin::WindowInfo::isOnCurrentDesktop()
const
00876
{
00877
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00878
return isOnDesktop(
KWin::currentDesktop());
00879
#else
00880
return false;
00881
#endif
00882
}
00883
00884 bool KWin::WindowInfo::isOnDesktop(
int desktop )
const
00885
{
00886
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00887
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMDesktop ) == 0, 176 )
00888 <<
"Pass NET::WMDesktop to KWin::windowInfo()" <<
endl;
00889
return d->info->desktop() == desktop || d->info->desktop() == NET::OnAllDesktops;
00890
#else
00891
return false;
00892
#endif
00893
}
00894
00895 bool KWin::WindowInfo::onAllDesktops()
const
00896
{
00897
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00898
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMDesktop ) == 0, 176 )
00899 <<
"Pass NET::WMDesktop to KWin::windowInfo()" <<
endl;
00900
return d->info->desktop() == NET::OnAllDesktops;
00901
#else
00902
return false;
00903
#endif
00904
}
00905
00906 int KWin::WindowInfo::desktop()
const
00907
{
00908
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00909
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMDesktop ) == 0, 176 )
00910 <<
"Pass NET::WMDesktop to KWin::windowInfo()" <<
endl;
00911
return d->info->desktop();
00912
#else
00913
return 1;
00914
#endif
00915
}
00916
00917 QRect KWin::WindowInfo::geometry()
const
00918
{
00919
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00920
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMGeometry ) == 0, 176 )
00921 <<
"Pass NET::WMGeometry to KWin::windowInfo()" <<
endl;
00922
return d->geometry_;
00923
#else
00924
return QRect( 100, 100, 200, 200 );;
00925
#endif
00926
}
00927
00928 QRect KWin::WindowInfo::frameGeometry()
const
00929
{
00930 kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS ] & NET::WMKDEFrameStrut ) == 0, 176 )
00931 <<
"Pass NET::WMKDEFrameStrut to KWin::windowInfo()" <<
endl;
00932
return d->frame_geometry_;
00933 }
00934
00935 WId
KWin::WindowInfo::transientFor()
const
00936
{
00937
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00938
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS2 ] & NET::WM2TransientFor ) == 0, 176 )
00939 <<
"Pass NET::WM2TransientFor to KWin::windowInfo()" <<
endl;
00940
return d->info->transientFor();
00941
#else
00942
return 0;
00943
#endif
00944
}
00945
00946 WId
KWin::WindowInfo::groupLeader()
const
00947
{
00948
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00949
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS2 ] & NET::WM2GroupLeader ) == 0, 176 )
00950 <<
"Pass NET::WM2GroupLeader to KWin::windowInfo()" <<
endl;
00951
return d->info->groupLeader();
00952
#else
00953
return 0;
00954
#endif
00955
}
00956
00957 bool KWin::WindowInfo::actionSupported( NET::Action action )
const
00958
{
00959
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00960
kdWarning(( d->info->passedProperties()[ NETWinInfo::PROTOCOLS2 ] & NET::WM2AllowedActions ) == 0, 176 )
00961 <<
"Pass NET::WM2AllowedActions to KWin::windowInfo()" <<
endl;
00962
if(
allowedActionsSupported())
00963
return d->info->allowedActions() & action;
00964
else
00965
#endif
00966
return true;
00967 }
00968
00969
00970 bool KWin::WindowInfo::isMinimized()
const
00971
{
00972
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00973
if(
mappingState() != NET::Iconic )
00974
return false;
00975
00976
if((
state() & NET::Hidden ) != 0
00977 && (
state() & NET::Shaded ) == 0 )
00978
return true;
00979
00980
00981
return icccmCompliantMappingState() ?
false :
true;
00982
#else
00983
return false;
00984
#endif
00985
}
00986
00987 bool KWin::Info::isMinimized()
const
00988
{
00989
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
00990
if( mappingState != NET::Iconic )
00991
return false;
00992
00993
if((
state & NET::Hidden ) != 0
00994 && (
state & NET::Shaded ) == 0 )
00995
return true;
00996
00997
00998
return icccmCompliantMappingState() ?
false :
true;
00999
#else
01000
return false;
01001
#endif
01002
}
01003
01004
bool KWin::Info::isIconified()
const
01005
{
01006
return isMinimized();
01007 }
01008
01009
bool KWin::icccmCompliantMappingState()
01010 {
01011
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
01012
static enum { noidea, yes, no } wm_is_1_2_compliant = noidea;
01013
if( wm_is_1_2_compliant == noidea ) {
01014 NETRootInfo
info( qt_xdisplay(), NET::Supported );
01015 wm_is_1_2_compliant =
info.isSupported( NET::Hidden ) ? yes : no;
01016 }
01017
return wm_is_1_2_compliant == yes;
01018
#else
01019
return false;
01020
#endif
01021
}
01022
01023 bool KWin::allowedActionsSupported()
01024 {
01025
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
01026
static enum { noidea, yes, no } wm_supports_allowed_actions = noidea;
01027
if( wm_supports_allowed_actions == noidea ) {
01028 NETRootInfo
info( qt_xdisplay(), NET::Supported );
01029 wm_supports_allowed_actions = info.isSupported( NET::WM2AllowedActions ) ? yes : no;
01030 }
01031
return wm_supports_allowed_actions == yes;
01032
#else
01033
return false;
01034
#endif
01035
}
01036
01037 QString KWin::readNameProperty( WId win,
unsigned long atom )
01038 {
01039
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
01040
XTextProperty tp;
01041
char **text = NULL;
01042
int count;
01043
#endif
01044
QString result;
01045
#if defined Q_WS_X11 && ! defined K_WS_QTONLY
01046
if ( XGetTextProperty( qt_xdisplay(), win, &tp, atom ) != 0 && tp.value != NULL ) {
01047
if ( XmbTextPropertyToTextList( qt_xdisplay(), &tp, &text, &count) == Success &&
01048 text != NULL && count > 0 ) {
01049 result =
QString::fromLocal8Bit( text[0] );
01050 }
else if ( tp.encoding == XA_STRING )
01051 result =
QString::fromLocal8Bit( (
const char*) tp.value );
01052
if( text != NULL )
01053 XFreeStringList( text );
01054 XFree( tp.value );
01055 }
01056
#endif
01057
return result;
01058 }
01059
01060