ksystemtray.cpp
00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021 #include "config.h"
00022 #include "kaction.h"
00023 #include "kshortcut.h"
00024 #include "ksystemtray.h"
00025 #include "kpopupmenu.h"
00026 #include "kapplication.h"
00027 #include "klocale.h"
00028
00029 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00030 #include <kwin.h>
00031 #include <kwinmodule.h>
00032 #endif
00033
00034 #include <kiconloader.h>
00035 #include <kconfig.h>
00036
00037 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00038 #include <qxembed.h>
00039 #endif
00040
00041 #include <qapplication.h>
00042
00043 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00044 #include <X11/Xlib.h>
00045 #ifndef KDE_USE_FINAL
00046 const int XFocusOut = FocusOut;
00047 const int XFocusIn = FocusIn;
00048 #endif
00049 #undef FocusOut
00050 #undef FocusIn
00051 #undef KeyPress
00052 #undef KeyRelease
00053
00054 extern Time qt_x_time;
00055 #endif // Q_WS_X11 && ! K_WS_QTONLY
00056
00057 class KSystemTrayPrivate
00058 {
00059 public:
00060 KSystemTrayPrivate()
00061 {
00062 actionCollection = 0;
00063 }
00064
00065 ~KSystemTrayPrivate()
00066 {
00067 delete actionCollection;
00068 }
00069
00070 KActionCollection* actionCollection;
00071 bool on_all_desktops;
00072 };
00073
00074 KSystemTray::KSystemTray( QWidget* parent, const char* name )
00075 : QLabel( parent, name, WType_TopLevel )
00076 {
00077 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00078 QXEmbed::initialize();
00079 #endif
00080
00081 d = new KSystemTrayPrivate;
00082 d->actionCollection = new KActionCollection(this);
00083
00084 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00085
00086
00087 KWin::setSystemTrayWindowFor( winId(), parent?parent->topLevelWidget()->winId(): qt_xrootwin() );
00088 setBackgroundMode(X11ParentRelative);
00089 setBackgroundOrigin(WindowOrigin);
00090 #endif
00091 hasQuit = 0;
00092 menu = new KPopupMenu( this );
00093 menu->insertTitle( kapp->miniIcon(), kapp->caption() );
00094 move( -1000, -1000 );
00095 KAction* quitAction = KStdAction::quit(this, SIGNAL(quitSelected()), d->actionCollection);
00096
00097 if (parentWidget())
00098 {
00099 connect(quitAction, SIGNAL(activated()), parentWidget(), SLOT(close()));
00100 new KAction(i18n("Minimize"), KShortcut(),
00101 this, SLOT( minimizeRestoreAction() ),
00102 d->actionCollection, "minimizeRestore");
00103 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00104 KWin::WindowInfo info = KWin::windowInfo( parentWidget()->winId());
00105 d->on_all_desktops = info.onAllDesktops();
00106 #endif
00107 }
00108 else
00109 {
00110 connect(quitAction, SIGNAL(activated()), qApp, SLOT(closeAllWindows()));
00111 d->on_all_desktops = false;
00112 }
00113 }
00114
00115 KSystemTray::~KSystemTray()
00116 {
00117 delete d;
00118 }
00119
00120
00121 void KSystemTray::showEvent( QShowEvent * )
00122 {
00123 if ( !hasQuit ) {
00124 menu->insertSeparator();
00125 KAction* action = d->actionCollection->action("minimizeRestore");
00126
00127 if (action)
00128 {
00129 action->plug(menu);
00130 }
00131
00132 action = d->actionCollection->action(KStdAction::name(KStdAction::Quit));
00133
00134 if (action)
00135 {
00136 action->plug(menu);
00137 }
00138
00139 hasQuit = 1;
00140 }
00141 }
00142
00143
00144 void KSystemTray::enterEvent( QEvent* e )
00145 {
00146 #if QT_VERSION < 0x030200
00147 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00148
00149
00150 if ( !qApp->focusWidget() ) {
00151 XEvent ev;
00152 memset(&ev, 0, sizeof(ev));
00153 ev.xfocus.display = qt_xdisplay();
00154 ev.xfocus.type = XFocusIn;
00155 ev.xfocus.window = winId();
00156 ev.xfocus.mode = NotifyNormal;
00157 ev.xfocus.detail = NotifyAncestor;
00158 Time time = qt_x_time;
00159 qt_x_time = 1;
00160 qApp->x11ProcessEvent( &ev );
00161 qt_x_time = time;
00162 }
00163 #endif
00164 #endif
00165 QLabel::enterEvent( e );
00166 }
00167
00168 KPopupMenu* KSystemTray::contextMenu() const
00169 {
00170 return menu;
00171 }
00172
00173
00174 void KSystemTray::mousePressEvent( QMouseEvent *e )
00175 {
00176 if ( !rect().contains( e->pos() ) )
00177 return;
00178
00179 switch ( e->button() ) {
00180 case LeftButton:
00181 activateOrHide();
00182 break;
00183 case MidButton:
00184
00185 case RightButton:
00186 if ( parentWidget() ) {
00187 KAction* action = d->actionCollection->action("minimizeRestore");
00188 if ( parentWidget()->isVisible() )
00189 action->setText( i18n("&Minimize") );
00190 else
00191 action->setText( i18n("&Restore") );
00192 }
00193 contextMenuAboutToShow( menu );
00194 menu->popup( e->globalPos() );
00195 break;
00196 default:
00197
00198 break;
00199 }
00200 }
00201
00202 void KSystemTray::mouseReleaseEvent( QMouseEvent * )
00203 {
00204 }
00205
00206
00207 void KSystemTray::contextMenuAboutToShow( KPopupMenu* )
00208 {
00209 }
00210
00211
00212
00213
00214 void KSystemTray::minimizeRestoreAction()
00215 {
00216 if ( parentWidget() ) {
00217 bool restore = !( parentWidget()->isVisible() );
00218 minimizeRestore( restore );
00219 }
00220 }
00221
00222
00223
00224
00225 void KSystemTray::activateOrHide()
00226 {
00227 QWidget *pw = parentWidget();
00228
00229 if ( !pw )
00230 return;
00231
00232 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00233 KWin::WindowInfo info1 = KWin::windowInfo( pw->winId(), NET::XAWMState | NET::WMState );
00234
00235 bool mapped = (info1.mappingState() == NET::Visible) && !info1.isMinimized();
00236
00237
00238
00239
00240 if( !mapped )
00241 minimizeRestore( true );
00242 else
00243 {
00244 KWinModule module;
00245 for( QValueList< WId >::ConstIterator it = module.stackingOrder().fromLast();
00246 it != module.stackingOrder().end() && (*it) != pw->winId();
00247 --it )
00248 {
00249 KWin::WindowInfo info2 = KWin::windowInfo( *it,
00250 NET::WMGeometry | NET::XAWMState | NET::WMState | NET::WMWindowType );
00251 if( info2.mappingState() != NET::Visible )
00252 continue;
00253 if( !info2.geometry().intersects( pw->geometry()))
00254 continue;
00255 if( !info1.hasState( NET::KeepAbove ) && info2.hasState( NET::KeepAbove ))
00256 continue;
00257 NET::WindowType type = info2.windowType( NET::NormalMask | NET::DesktopMask
00258 | NET::DockMask | NET::ToolbarMask | NET::MenuMask | NET::DialogMask
00259 | NET::OverrideMask | NET::TopMenuMask | NET::UtilityMask | NET::SplashMask );
00260 if( type == NET::Dock || type == NET::TopMenu )
00261 continue;
00262 pw->raise();
00263 KWin::activateWindow( pw->winId());
00264 return;
00265 }
00266 minimizeRestore( false );
00267 }
00268 #endif
00269 }
00270
00271 void KSystemTray::minimizeRestore( bool restore )
00272 {
00273 QWidget* pw = parentWidget();
00274 if( !pw )
00275 return;
00276 #if defined Q_WS_X11 && ! defined K_WS_QTONLY
00277 KWin::WindowInfo info = KWin::windowInfo( pw->winId(), NET::WMGeometry | NET::WMDesktop );
00278 if ( restore )
00279 {
00280
00281
00282 if( d->on_all_desktops )
00283 KWin::setOnAllDesktops( pw->winId(), true );
00284 else
00285 KWin::setOnDesktop( pw->winId(), KWin::currentDesktop());
00286 pw->move( info.geometry().topLeft() );
00287 pw->show();
00288 pw->raise();
00289 KWin::activateWindow( pw->winId() );
00290 } else {
00291 d->on_all_desktops = info.onAllDesktops();
00292 pw->hide();
00293 }
00294 #endif
00295 }
00296
00297 KActionCollection* KSystemTray::actionCollection()
00298 {
00299 return d->actionCollection;
00300 }
00301
00302 QPixmap KSystemTray::loadIcon( const QString &icon, KInstance *instance )
00303 {
00304 KConfig *appCfg = kapp->config();
00305 KConfigGroupSaver configSaver(appCfg, "System Tray");
00306 int iconWidth = appCfg->readNumEntry("systrayIconWidth", 22);
00307 return instance->iconLoader()->loadIcon( icon, KIcon::Panel, iconWidth );
00308 }
00309
00310 void KSystemTray::virtual_hook( int, void* )
00311 { }
00312
00313 #include "ksystemtray.moc"
00314 #include "kdockwindow.moc"
This file is part of the documentation for kdeui Library Version 3.2.2.