kdeui Library API Documentation

ksystemtray.cpp

00001 /* This file is part of the KDE libraries
00002 
00003     Copyright (C) 1999 Matthias Ettrich (ettrich@kde.org)
00004 
00005     This library is free software; you can redistribute it and/or
00006     modify it under the terms of the GNU Library General Public
00007     License as published by the Free Software Foundation; either
00008     version 2 of the License, or (at your option) any later version.
00009 
00010     This library is distributed in the hope that it will be useful,
00011     but WITHOUT ANY WARRANTY; without even the implied warranty of
00012     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00013     Library General Public License for more details.
00014 
00015     You should have received a copy of the GNU Library General Public License
00016     along with this library; see the file COPYING.LIB.  If not, write to
00017     the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00018     Boston, MA 02111-1307, USA.
00019 */
00020 
00021 #include "kaction.h"
00022 #include "kshortcut.h"
00023 #include "ksystemtray.h"
00024 #include "kpopupmenu.h"
00025 #include "kapplication.h"
00026 #include "klocale.h"
00027 #include <kwin.h>
00028 #include <kwinmodule.h>
00029 #include <kiconloader.h>
00030 
00031 #include <qapplication.h>
00032 #ifndef Q_WS_QWS
00033 #include <X11/Xlib.h>
00034 #ifndef KDE_USE_FINAL
00035 const int XFocusOut = FocusOut;
00036 const int XFocusIn = FocusIn;
00037 #endif
00038 #undef FocusOut
00039 #undef FocusIn
00040 #undef KeyPress
00041 #undef KeyRelease
00042 
00043 extern Time qt_x_time;
00044 #endif
00045 
00046 class KSystemTrayPrivate
00047 {
00048 public:
00049     KSystemTrayPrivate()
00050     {
00051         actionCollection = 0;
00052     }
00053 
00054     ~KSystemTrayPrivate()
00055     {
00056         delete actionCollection;
00057     }
00058 
00059     KActionCollection* actionCollection;
00060     bool on_all_desktops; // valid only when the parent widget was hidden
00061 };
00062 
00063 KSystemTray::KSystemTray( QWidget* parent, const char* name )
00064     : QLabel( parent, name, WType_TopLevel )
00065 {
00066     d = new KSystemTrayPrivate;
00067     d->actionCollection = new KActionCollection(this);
00068 
00069 #ifndef Q_WS_QWS
00070     // FIXME(E): Talk with QWS
00071     KWin::setSystemTrayWindowFor( winId(), parent?parent->topLevelWidget()->winId(): qt_xrootwin() );
00072     setBackgroundMode(X11ParentRelative);
00073 #endif
00074     hasQuit = 0;
00075     menu = new KPopupMenu( this );
00076     menu->insertTitle( kapp->miniIcon(), kapp->caption() );
00077     move( -1000, -1000 );
00078     KAction* quitAction = KStdAction::quit(this, SIGNAL(quitSelected()), d->actionCollection);
00079 
00080     if (parentWidget())
00081     {
00082         connect(quitAction, SIGNAL(activated()), parentWidget(), SLOT(close()));
00083         new KAction(i18n("Minimize"), KShortcut(), 
00084                     this, SLOT( minimizeRestoreAction() ),
00085                     d->actionCollection, "minimizeRestore");
00086     KWin::Info info = KWin::info( parentWidget()->winId());
00087     d->on_all_desktops = info.onAllDesktops;
00088     }
00089     else
00090     {
00091         connect(quitAction, SIGNAL(activated()), qApp, SLOT(closeAllWindows()));
00092     d->on_all_desktops = false;
00093     }
00094 }
00095 
00096 KSystemTray::~KSystemTray()
00097 {
00098     delete d;
00099 }
00100 
00101 
00102 void KSystemTray::showEvent( QShowEvent * )
00103 {
00104     if ( !hasQuit ) {
00105     menu->insertSeparator();
00106         KAction* action = d->actionCollection->action("minimizeRestore");
00107 
00108         if (action)
00109         {
00110             action->plug(menu);
00111         }
00112 
00113         action = d->actionCollection->action(KStdAction::name(KStdAction::Quit));
00114 
00115         if (action)
00116         {
00117             action->plug(menu);
00118         }
00119 
00120     hasQuit = 1;
00121     }
00122 }
00123 
00124 // KDE4 remove
00125 void KSystemTray::enterEvent( QEvent* e )
00126 {
00127 #if QT_VERSION < 0x030200
00128 #ifndef Q_WS_QWS
00129     // FIXME(E): Implement for Qt Embedded
00130     if ( !qApp->focusWidget() ) {
00131     XEvent ev;
00132     memset(&ev, 0, sizeof(ev));
00133     ev.xfocus.display = qt_xdisplay();
00134     ev.xfocus.type = XFocusIn;
00135     ev.xfocus.window = winId();
00136     ev.xfocus.mode = NotifyNormal;
00137     ev.xfocus.detail = NotifyAncestor;
00138     Time time = qt_x_time;
00139     qt_x_time = 1;
00140     qApp->x11ProcessEvent( &ev );
00141     qt_x_time = time;
00142     }
00143 #endif
00144 #endif
00145     QLabel::enterEvent( e );
00146 }
00147 
00148 KPopupMenu* KSystemTray::contextMenu() const
00149 {
00150     return menu;
00151 }
00152 
00153 
00154 void KSystemTray::mousePressEvent( QMouseEvent *e )
00155 {
00156     if ( !rect().contains( e->pos() ) )
00157     return;
00158 
00159     switch ( e->button() ) {
00160     case LeftButton:
00161         activateOrHide();
00162     break;
00163     case MidButton:
00164     // fall through
00165     case RightButton:
00166     if ( parentWidget() ) {
00167             KAction* action = d->actionCollection->action("minimizeRestore");
00168         if ( parentWidget()->isVisible() )
00169         action->setText( i18n("Minimize") );
00170         else
00171         action->setText( i18n("Restore") );
00172     }
00173     contextMenuAboutToShow( menu );
00174     menu->popup( e->globalPos() );
00175     break;
00176     default:
00177     // nothing
00178     break;
00179     }
00180 }
00181 
00182 void KSystemTray::mouseReleaseEvent( QMouseEvent * )
00183 {
00184 }
00185 
00186 
00187 void KSystemTray::contextMenuAboutToShow( KPopupMenu* )
00188 {
00189 }
00190 
00191 
00192 // called from the popup menu - always do what the menu entry says,
00193 // i.e. if the window is shown, no matter if active or not, the menu
00194 // entry is "minimize", otherwise it's "restore"
00195 void KSystemTray::minimizeRestoreAction()
00196 {
00197     if ( parentWidget() ) {
00198         bool restore = !( parentWidget()->isVisible() );
00199     minimizeRestore( restore );
00200     }
00201 }
00202 
00203 // called when left-clicking the tray icon
00204 // if the window is not the active one, show it if needed, and activate it
00205 // (just like taskbar); otherwise hide it
00206 void KSystemTray::activateOrHide()
00207 {
00208     QWidget *pw = parentWidget();
00209 
00210     if ( !pw )
00211     return;
00212 
00213     KWin::Info info = KWin::info( pw->winId() );
00214     // mapped = not hidden by calling hide()
00215     bool mapped = (info.mappingState != NET::Withdrawn);
00216 #if QT_VERSION >= 0x030200
00217     if( mapped && !pw->isActiveWindow()) // visible not active -> activate
00218 #else
00219     // SELI using !pw->isActiveWindow() should be enough here,
00220     // but it doesn't work - e.g. with kscd, the "active" window
00221     // is the widget docked in Kicker
00222     if ( mapped && ( KWinModule().activeWindow() != pw->winId() ))
00223 #endif
00224     {
00225         KWin::setActiveWindow( pw->winId() );
00226         return;
00227     }
00228     minimizeRestore( !mapped );
00229 }
00230 
00231 void KSystemTray::minimizeRestore( bool restore )
00232 {
00233     QWidget* pw = parentWidget();
00234     if( !pw )
00235     return;
00236     KWin::Info info = KWin::info( pw->winId() );
00237     if ( restore )
00238     {
00239 #ifndef Q_WS_QWS //FIXME
00240     if( d->on_all_desktops )
00241         KWin::setOnAllDesktops( pw->winId(), true );
00242     else
00243         KWin::setOnDesktop( pw->winId(), KWin::currentDesktop());
00244         pw->move( info.geometry.topLeft() ); // avoid placement policies
00245         pw->show();
00246     KWin::setActiveWindow( pw->winId() );
00247 #endif
00248     } else {
00249     d->on_all_desktops = info.onAllDesktops;
00250     pw->hide();
00251     }
00252 }
00253 
00254 KActionCollection* KSystemTray::actionCollection()
00255 {
00256     return d->actionCollection;
00257 }
00258 
00259 void KSystemTray::virtual_hook( int, void* )
00260 { /*BASE::virtual_hook( id, data );*/ }
00261 
00262 #include "ksystemtray.moc"
00263 #include "kdockwindow.moc"
KDE Logo
This file is part of the documentation for kdelibs Version 3.1.4.
Documentation copyright © 1996-2002 the KDE developers.
Generated on Sun Feb 27 22:15:05 2005 by doxygen 1.3.4 written by Dimitri van Heesch, © 1997-2001