kwinmodule.cpp Source File (kdecore Library)

| # kdecore Library API Documentation
Overview | Class Hierarchy | Classes | Classes (annotated) | Members | Source Files

# kwinmodule.cpp

    00001 /*
    00002     $Id: kwinmodule.cpp,v 1.48.4.3 2003/07/04 20:44:08 firebaugh Exp $
    00003
    00004     This file is part of the KDE libraries
    00005     Copyright (C) 1999 Matthias Ettrich (ettrich@kde.org)
    00006
    00007
    00008     This library is free software; you can redistribute it and/or
    00009     modify it under the terms of the GNU Library General Public
    00010     License as published by the Free Software Foundation; either
    00011     version 2 of the License, or (at your option) any later version.
    00012
    00013     This library is distributed in the hope that it will be useful,
    00014     but WITHOUT ANY WARRANTY; without even the implied warranty of
    00015     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
    00016     Library General Public License for more details.
    00017
    00018     You should have received a copy of the GNU Library General Public License
    00019     along with this library; see the file COPYING.LIB.  If not, write to
    00020     the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
    00021     Boston, MA 02111-1307, USA.
    00022 */
    00023
    00024 #include <qwidget.h>
    00025 #ifdef Q_WS_X11 //FIXME
    00026 #include "kwinmodule.h"
    00027 #include "kwin.h"
    00028 #include <X11/Xatom.h>
    00029 #include "kapplication.h"
    00030 #include "kdebug.h"
    00031 #include <qtl.h>
    00032 #include <qptrlist.h>
    00033 #include <klocale.h>
    00034 #include <dcopclient.h>
    00035 #include "netwm.h"
    00036
    00037 extern Atom net_wm_context_help;
    00038 extern void kwin_net_create_atoms();
    00039
    00040 static KWinModulePrivate* static_d = 0;
    00041
    00042 class KWinModulePrivate : public QWidget, public NETRootInfo
    00043 {
    00044 public:
    00045     KWinModulePrivate()
    00046         : QWidget(0,0), NETRootInfo( qt_xdisplay(),
    00047                                      ClientList |
    00048                                      ClientListStacking |
    00049                                      NumberOfDesktops |
    00050                                      DesktopGeometry |
    00051                                      CurrentDesktop |
    00052                                      DesktopNames |
    00053                                      ActiveWindow |
    00054                                      WorkArea |
    00055                                      KDESystemTrayWindows,
    00056                                      -1, false
    00057                                      )
    00058     {
    00059         kwin_net_create_atoms();
    00060         kapp->installX11EventFilter( this );
    00061         (void ) kapp->desktop(); //trigger desktop widget creation to select root window events
    00062         activate();
    00063         updateStackingOrder();
    00064     }
    00065     ~KWinModulePrivate()
    00066     {
    00067     }
    00068
    00069     QPtrList<KWinModule> modules;
    00070
    00071     QValueList<WId> windows;
    00072     QValueList<WId> stackingOrder;
    00073     QValueList<WId> systemTrayWindows;
    00074
    00075     QValueList<WId> strutWindows;
    00076
    00077     void addClient(Window);
    00078     void removeClient(Window);
    00079     void addSystemTrayWin(Window);
    00080     void removeSystemTrayWin(Window);
    00081
    00082     bool x11Event( XEvent * ev );
    00083
    00084     void updateStackingOrder();
    00085 };
    00086
    00087
    00088 KWinModule::KWinModule( QObject* parent )
    00089     : QObject( parent, "kwin_module" )
    00090 {
    00091     if ( !static_d )
    00092         static_d = new KWinModulePrivate;
    00093     d = static_d;
    00094     d->modules.append( this );
    00095
    00096 }
    00097
    00098 KWinModule::~KWinModule()
    00099 {
    00100     d->modules.removeRef( this );
    00101     if ( d->modules.isEmpty() ) {
    00102         delete d;
    00103         static_d = 0;
    00104     }
    00105 }
    00106
    00107 const QValueList<WId>& KWinModule::windows() const
    00108 {
    00109     return d->windows;
    00110 }
    00111
    00112 const QValueList<WId>& KWinModule::stackingOrder() const
    00113 {
    00114     return d->stackingOrder;
    00115 }
    00116
    00117
    00118 bool KWinModule::hasWId(WId w) const
    00119 {
    00120     return d->windows.contains( w );
    00121 }
    00122
    00123 const QValueList<WId>& KWinModule::systemTrayWindows() const
    00124 {
    00125     return d->systemTrayWindows;
    00126 }
    00127
    00128 bool KWinModulePrivate::x11Event( XEvent * ev )
    00129 {
    00130     if ( ev->xany.window == qt_xrootwin() ) {
    00131         int m = NETRootInfo::event( ev );
    00132
    00133         if ( m & CurrentDesktop )
    00134             for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit )
    00135                 emit (*mit)->currentDesktopChanged( currentDesktop() );
    00136         if ( m & ActiveWindow )
    00137             for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit )
    00138                 emit (*mit)->activeWindowChanged( activeWindow() );
    00139         if ( m & DesktopNames )
    00140             for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit )
    00141                 emit (*mit)->desktopNamesChanged();
    00142         if ( m & NumberOfDesktops )
    00143             for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit )
    00144                 emit (*mit)->numberOfDesktopsChanged( numberOfDesktops() );
    00145         if ( m & WorkArea )
    00146             for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit )
    00147                 emit (*mit)->workAreaChanged();
    00148         if ( m & ClientListStacking ) {
    00149             updateStackingOrder();
    00150             for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit )
    00151                 emit (*mit)->stackingOrderChanged();
    00152         }
    00153     } else  if ( windows.contains( ev->xany.window ) ){
    00154         NETWinInfo ni( qt_xdisplay(), ev->xany.window, qt_xrootwin(), 0 );
    00155         unsigned int dirty = ni.event( ev );
    00156         if ( !dirty && ev->type ==PropertyNotify && ev->xproperty.atom == XA_WM_HINTS )
    00157             dirty |= NET::WMIcon; // support for old icons
    00158         if ( (dirty & NET::WMStrut) != 0 ) {
    00159             if ( !strutWindows.contains( ev->xany.window )  )
    00160                 strutWindows.append( ev->xany.window );
    00161         }
    00162         if ( dirty ) {
    00163             for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit ) {
    00164                 emit (*mit)->windowChanged( ev->xany.window );
    00165                 emit (*mit)->windowChanged( ev->xany.window, dirty );
    00166                 if ( (dirty & NET::WMStrut) != 0 )
    00167                     emit (*mit)->strutChanged();
    00168             }
    00169         }
    00170     }
    00171
    00172     return FALSE;
    00173 }
    00174
    00175
    00176 void KWinModulePrivate::updateStackingOrder()
    00177 {
    00178     stackingOrder.clear();
    00179     for ( int i = 0; i <  clientListStackingCount(); i++ )
    00180         stackingOrder.append( clientListStacking()[i] );
    00181 }
    00182
    00183 void KWinModulePrivate::addClient(Window w)
    00184 {
    00185     if ( !QWidget::find( w ) )
    00186         XSelectInput( qt_xdisplay(), w, PropertyChangeMask | StructureNotifyMask );
    00187     bool emit_strutChanged = FALSE;
    00188     for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit ) {
    00189         NETWinInfo info( qt_xdisplay(), w, qt_xrootwin(), NET::WMStrut );
    00190         NETStrut strut = info.strut();
    00191         if ( strut.left || strut.top || strut.right || strut.bottom ) {
    00192             strutWindows.append( w );
    00193             emit_strutChanged = TRUE;
    00194         }
    00195         break;
    00196     }
    00197     windows.append( w );
    00198     for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit ) {
    00199         emit (*mit)->windowAdded( w );
    00200         if ( emit_strutChanged )
    00201             emit (*mit)->strutChanged();
    00202     }
    00203 }
    00204
    00205 void KWinModulePrivate::removeClient(Window w)
    00206 {
    00207     bool emit_strutChanged = strutWindows.contains( w );
    00208     strutWindows.remove( w );
    00209     windows.remove( w );
    00210     for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit ) {
    00211         emit (*mit)->windowRemoved( w );
    00212         if ( emit_strutChanged )
    00213             emit (*mit)->strutChanged();
    00214     }
    00215 }
    00216
    00217 void KWinModulePrivate::addSystemTrayWin(Window w)
    00218 {
    00219     systemTrayWindows.append( w );
    00220     for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit )
    00221         emit (*mit)->systemTrayWindowAdded( w );
    00222 }
    00223
    00224 void KWinModulePrivate::removeSystemTrayWin(Window w)
    00225 {
    00226     systemTrayWindows.remove( w );
    00227     for ( QPtrListIterator<KWinModule> mit( modules ); mit.current(); ++mit )
    00228         emit (*mit)->systemTrayWindowRemoved( w );
    00229 }
    00230
    00231 int KWinModule::currentDesktop() const
    00232 {
    00233     return d->currentDesktop();
    00234 }
    00235
    00236 int KWinModule::numberOfDesktops() const
    00237 {
    00238     return d->numberOfDesktops();
    00239 }
    00240
    00241 WId KWinModule::activeWindow() const
    00242 {
    00243     return d->activeWindow();
    00244 }
    00245
    00246 QRect KWinModule::workArea( int desktop ) const
    00247 {
    00248     int desk  = (desktop > 0 && desktop <= (int) d->numberOfDesktops() ) ? desktop : currentDesktop();
    00249     if ( desk <= 0 )
    00250         return QApplication::desktop()->geometry();
    00251     NETRect r = d->workArea( desk );
    00252     return QRect( r.pos.x, r.pos.y, r.size.width, r.size.height );
    00253 }
    00254
    00255 QRect KWinModule::workArea( const QValueList<WId>& exclude, int desktop ) const
    00256 {
    00257     QRect all = QApplication::desktop()->geometry();
    00258     QRect a = all;
    00259
    00260     if (desktop == -1)
    00261         desktop = d->currentDesktop();
    00262
    00263     QValueList<WId>::ConstIterator it;
    00264     for( it = d->windows.begin(); it != d->windows.end(); ++it ) {
    00265
    00266         if(exclude.contains(*it) > 0) continue;
    00267
    00268         NETWinInfo info( qt_xdisplay(), (*it), qt_xrootwin(), NET::WMStrut | NET::WMDesktop);
    00269         //if(!(info.desktop() == desktop || info.desktop() == NETWinInfo::OnAllDesktops)) continue;
    00270
    00271         QRect r = all;
    00272         NETStrut strut = info.strut();
    00273         if ( strut.left > 0 )
    00274             r.setLeft( r.left() + (int) strut.left );
    00275         if ( strut.top > 0 )
    00276             r.setTop( r.top() + (int) strut.top );
    00277         if ( strut.right > 0  )
    00278             r.setRight( r.right() - (int) strut.right );
    00279         if ( strut.bottom > 0  )
    00280             r.setBottom( r.bottom() - (int) strut.bottom );
    00281
    00282         a = a.intersect(r);
    00283     }
    00284     return a;
    00285 }
    00286
    00287
    00288 QString KWinModule::desktopName( int desktop ) const
    00289 {
    00290     const char* name = d->desktopName( (desktop > 0 && desktop <= (int) d->numberOfDesktops() ) ? desktop : currentDesktop() );
    00291     if ( name && name[0] )
    00292         return QString::fromUtf8( name );
    00293     return i18n("Desktop %1").arg( desktop );
    00294 }
    00295
    00296 void KWinModule::setDesktopName( int desktop, const QString& name )
    00297 {
    00298     if (desktop <= 0 || desktop > (int) d->numberOfDesktops() )
    00299         desktop = currentDesktop();
    00300     d->setDesktopName( desktop, name.utf8().data() );
    00301 }
    00302
    00303
    00304 void KWinModule::doNotManage( const QString& title )
    00305 {
    00306     if ( !kapp->dcopClient()->isAttached() )
    00307         kapp->dcopClient()->attach();
    00308     QByteArray data, replyData;
    00309     QCString replyType;
    00310     QDataStream arg(data, IO_WriteOnly);
    00311     arg << title;
    00312     kapp->dcopClient()->call("kwin", "", "doNotManage(QString)",
    00313                              data, replyType, replyData);
    00314 }
    00315
    00316 #include "kwinmodule.moc"
    00317 #endif

This file is part of the documentation for kdelibs Version 3.1.5.
Documentation copyright © 1996-2002 the KDE developers.
Generated on Wed Jan 28 12:46:59 2004 by doxygen 1.3.4 written by Dimitri van Heesch, © 1997-2001