kdeui Library API Documentation

kcursor.cpp

00001 /* This file is part of the KDE libraries 00002 Copyright (C) 1998 Kurt Granroth (granroth@kde.org) 00003 00004 This library is free software; you can redistribute it and/or 00005 modify it under the terms of the GNU Library General Public 00006 License version 2 as published by the Free Software Foundation. 00007 00008 This library is distributed in the hope that it will be useful, 00009 but WITHOUT ANY WARRANTY; without even the implied warranty of 00010 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00011 Library General Public License for more details. 00012 00013 You should have received a copy of the GNU Library General Public License 00014 along with this library; see the file COPYING.LIB. If not, write to 00015 the Free Software Foundation, Inc., 59 Temple Place - Suite 330, 00016 Boston, MA 02111-1307, USA. 00017 */ 00018 00019 #ifdef KDE_USE_FINAL 00020 #ifdef KeyRelease 00021 #undef KeyRelease 00022 #endif 00023 #endif 00024 00025 #include <kcursor.h> 00026 00027 #include <qbitmap.h> 00028 #include <qcursor.h> 00029 #include <qevent.h> 00030 #include <qtimer.h> 00031 #include <qwidget.h> 00032 00033 #include <kglobal.h> 00034 #include <kconfig.h> 00035 #include <qscrollview.h> 00036 00037 #include "kcursor_private.h" 00038 00039 KCursor::KCursor() 00040 { 00041 } 00042 00043 QCursor KCursor::handCursor() 00044 { 00045 static QCursor *hand_cursor = 0; 00046 00047 if (!hand_cursor) 00048 { 00049 KConfig *config = KGlobal::config(); 00050 KConfigGroupSaver saver( config, "General" ); 00051 00052 #ifndef Q_WS_WIN // this mask doesn't work too well on win32 00053 if ( config->readEntry("handCursorStyle", "Windows") == "Windows" ) 00054 { 00055 static const unsigned char HAND_BITS[] = { 00056 0x80, 0x01, 0x00, 0x40, 0x02, 0x00, 0x40, 0x02, 0x00, 0x40, 0x02, 00057 0x00, 0x40, 0x02, 0x00, 0x40, 0x02, 0x00, 0x40, 0x1e, 0x00, 0x40, 00058 0xf2, 0x00, 0x40, 0x92, 0x01, 0x70, 0x92, 0x02, 0x50, 0x92, 0x04, 00059 0x48, 0x80, 0x04, 0x48, 0x00, 0x04, 0x48, 0x00, 0x04, 0x08, 0x00, 00060 0x04, 0x08, 0x00, 0x04, 0x10, 0x00, 0x04, 0x10, 0x00, 0x04, 0x20, 00061 0x00, 0x02, 0x40, 0x00, 0x02, 0x40, 0x00, 0x01, 0xc0, 0xff, 0x01}; 00062 static const unsigned char HAND_MASK_BITS[] = { 00063 0x80, 0x01, 0x00, 0xc0, 0x03, 0x00, 0xc0, 0x03, 0x00, 0xc0, 0x03, 00064 0x00, 0xc0, 0x03, 0x00, 0xc0, 0x03, 0x00, 0xc0, 0x1f, 0x00, 0xc0, 00065 0xff, 0x00, 0xc0, 0xff, 0x01, 0xf0, 0xff, 0x03, 0xf0, 0xff, 0x07, 00066 0xf8, 0xff, 0x07, 0xf8, 0xff, 0x07, 0xf8, 0xff, 0x07, 0xf8, 0xff, 00067 0x07, 0xf8, 0xff, 0x07, 0xf0, 0xff, 0x07, 0xf0, 0xff, 0x07, 0xe0, 00068 0xff, 0x03, 0xc0, 0xff, 0x03, 0xc0, 0xff, 0x01, 0xc0, 0xff, 0x01}; 00069 QBitmap hand_bitmap(22, 22, HAND_BITS, true); 00070 QBitmap hand_mask(22, 22, HAND_MASK_BITS, true); 00071 hand_cursor = new QCursor(hand_bitmap, hand_mask, 7, 0); 00072 // Hack to force QCursor to call XCreatePixmapCursor() immediately 00073 // so the bitmaps don't get pushed out of the Xcursor LRU cache. 00074 hand_cursor->handle(); 00075 } 00076 else 00077 #endif 00078 hand_cursor = new QCursor(PointingHandCursor); 00079 } 00080 00081 Q_CHECK_PTR(hand_cursor); 00082 return *hand_cursor; 00083 } 00084 00085 /* XPM */ 00086 static const char * const working_cursor_xpm[]={ 00087 "32 32 3 1", 00088 "# c None", 00089 "a c #000000", 00090 ". c #ffffff", 00091 "..##############################", 00092 ".a.##########.aaaa.#############", 00093 ".aa.#########.aaaa.#############", 00094 ".aaa.#######.aaaaaa.############", 00095 ".aaaa.#####.a...a..a..##########", 00096 ".aaaaa.####a....a...aa##########", 00097 ".aaaaaa.###a...aa...aa##########", 00098 ".aaaaaaa.##a..a.....aa##########", 00099 ".aaaaaaaa.#.aa.....a..##########", 00100 ".aaaaa....##.aaaaaa.############", 00101 ".aa.aa.######.aaaa.#############", 00102 ".a.#.aa.#####.aaaa.#############", 00103 "..##.aa.########################", 00104 "#####.aa.#######################", 00105 "#####.aa.#######################", 00106 "######..########################", 00107 "################################", 00108 "################################", 00109 "################################", 00110 "################################", 00111 "################################", 00112 "################################", 00113 "################################", 00114 "################################", 00115 "################################", 00116 "################################", 00117 "################################", 00118 "################################", 00119 "################################", 00120 "################################", 00121 "################################", 00122 "################################"}; 00123 00124 00125 QCursor KCursor::workingCursor() 00126 { 00127 static QCursor *working_cursor = 0; 00128 00129 if (!working_cursor) 00130 { 00131 QPixmap pm( const_cast< const char** >( working_cursor_xpm )); 00132 working_cursor = new QCursor( pm, 1, 1 ); 00133 // Hack to force QCursor to call XCreatePixmapCursor() immediately 00134 // so the bitmaps don't get pushed out of the Xcursor LRU cache. 00135 working_cursor->handle(); 00136 } 00137 00138 Q_CHECK_PTR(working_cursor); 00139 return *working_cursor; 00140 } 00141 00146 QCursor KCursor::arrowCursor() 00147 { 00148 return Qt::arrowCursor; 00149 } 00150 00151 00152 QCursor KCursor::upArrowCursor() 00153 { 00154 return Qt::upArrowCursor; 00155 } 00156 00157 00158 QCursor KCursor::crossCursor() 00159 { 00160 return Qt::crossCursor; 00161 } 00162 00163 00164 QCursor KCursor::waitCursor() 00165 { 00166 return Qt::waitCursor; 00167 } 00168 00169 00170 QCursor KCursor::ibeamCursor() 00171 { 00172 return Qt::ibeamCursor; 00173 } 00174 00175 00176 QCursor KCursor::sizeVerCursor() 00177 { 00178 return Qt::sizeVerCursor; 00179 } 00180 00181 00182 QCursor KCursor::sizeHorCursor() 00183 { 00184 return Qt::sizeHorCursor; 00185 } 00186 00187 00188 QCursor KCursor::sizeBDiagCursor() 00189 { 00190 return Qt::sizeBDiagCursor; 00191 } 00192 00193 00194 QCursor KCursor::sizeFDiagCursor() 00195 { 00196 return Qt::sizeFDiagCursor; 00197 } 00198 00199 00200 QCursor KCursor::sizeAllCursor() 00201 { 00202 return Qt::sizeAllCursor; 00203 } 00204 00205 00206 QCursor KCursor::blankCursor() 00207 { 00208 return Qt::blankCursor; 00209 } 00210 00211 QCursor KCursor::whatsThisCursor() 00212 { 00213 return Qt::whatsThisCursor; 00214 } 00215 00216 // auto-hide cursor stuff 00217 00218 void KCursor::setAutoHideCursor( QWidget *w, bool enable ) 00219 { 00220 setAutoHideCursor( w, enable, false ); 00221 } 00222 00223 void KCursor::setAutoHideCursor( QWidget *w, bool enable, 00224 bool customEventFilter ) 00225 { 00226 KCursorPrivate::self()->setAutoHideCursor( w, enable, customEventFilter ); 00227 } 00228 00229 void KCursor::autoHideEventFilter( QObject *o, QEvent *e ) 00230 { 00231 KCursorPrivate::self()->eventFilter( o, e ); 00232 } 00233 00234 void KCursor::setHideCursorDelay( int ms ) 00235 { 00236 KCursorPrivate::self()->hideCursorDelay = ms; 00237 } 00238 00239 int KCursor::hideCursorDelay() 00240 { 00241 return KCursorPrivate::self()->hideCursorDelay; 00242 } 00243 00244 // ************************************************************************** 00245 00246 KCursorPrivateAutoHideEventFilter::KCursorPrivateAutoHideEventFilter( QWidget* widget ) 00247 : m_widget( widget ) 00248 , m_wasMouseTracking( m_widget->hasMouseTracking() ) 00249 , m_isCursorHidden( false ) 00250 , m_isOwnCursor( false ) 00251 { 00252 m_widget->setMouseTracking( true ); 00253 connect( &m_autoHideTimer, SIGNAL( timeout() ), 00254 this, SLOT( hideCursor() ) ); 00255 } 00256 00257 KCursorPrivateAutoHideEventFilter::~KCursorPrivateAutoHideEventFilter() 00258 { 00259 if( m_widget != NULL ) 00260 m_widget->setMouseTracking( m_wasMouseTracking ); 00261 } 00262 00263 void KCursorPrivateAutoHideEventFilter::resetWidget() 00264 { 00265 m_widget = NULL; 00266 } 00267 00268 void KCursorPrivateAutoHideEventFilter::hideCursor() 00269 { 00270 m_autoHideTimer.stop(); 00271 00272 if ( m_isCursorHidden ) 00273 return; 00274 00275 m_isCursorHidden = true; 00276 00277 QWidget* w = actualWidget(); 00278 00279 m_isOwnCursor = w->ownCursor(); 00280 if ( m_isOwnCursor ) 00281 m_oldCursor = w->cursor(); 00282 00283 w->setCursor( KCursor::blankCursor() ); 00284 } 00285 00286 void KCursorPrivateAutoHideEventFilter::unhideCursor() 00287 { 00288 m_autoHideTimer.stop(); 00289 00290 if ( !m_isCursorHidden ) 00291 return; 00292 00293 m_isCursorHidden = false; 00294 00295 QWidget* w = actualWidget(); 00296 00297 if ( m_isOwnCursor ) 00298 w->setCursor( m_oldCursor ); 00299 else 00300 w->unsetCursor(); 00301 } 00302 00303 QWidget* KCursorPrivateAutoHideEventFilter::actualWidget() const 00304 { 00305 QWidget* w = m_widget; 00306 00307 // Is w a scrollview ? Call setCursor on the viewport in that case. 00308 QScrollView * sv = dynamic_cast<QScrollView *>( w ); 00309 if ( sv ) 00310 w = sv->viewport(); 00311 00312 return w; 00313 } 00314 00315 bool KCursorPrivateAutoHideEventFilter::eventFilter( QObject *o, QEvent *e ) 00316 { 00317 Q_ASSERT( o == m_widget ); 00318 00319 switch ( e->type() ) 00320 { 00321 case QEvent::Create: 00322 // Qt steals mouseTracking on create() 00323 m_widget->setMouseTracking( true ); 00324 break; 00325 case QEvent::Leave: 00326 case QEvent::FocusOut: 00327 case QEvent::WindowDeactivate: 00328 unhideCursor(); 00329 break; 00330 case QEvent::KeyPress: 00331 case QEvent::AccelOverride: 00332 hideCursor(); 00333 break; 00334 case QEvent::Enter: 00335 case QEvent::FocusIn: 00336 case QEvent::MouseButtonPress: 00337 case QEvent::MouseButtonRelease: 00338 case QEvent::MouseButtonDblClick: 00339 case QEvent::MouseMove: 00340 case QEvent::Show: 00341 case QEvent::Hide: 00342 case QEvent::Wheel: 00343 unhideCursor(); 00344 if ( m_widget->hasFocus() ) 00345 m_autoHideTimer.start( KCursorPrivate::self()->hideCursorDelay, true ); 00346 break; 00347 default: 00348 break; 00349 } 00350 00351 return false; 00352 } 00353 00354 KCursorPrivate * KCursorPrivate::s_self = 0L; 00355 00356 KCursorPrivate * KCursorPrivate::self() 00357 { 00358 if ( !s_self ) 00359 s_self = new KCursorPrivate; 00360 // WABA: We never delete KCursorPrivate. Don't change. 00361 00362 return s_self; 00363 } 00364 00365 KCursorPrivate::KCursorPrivate() 00366 { 00367 hideCursorDelay = 5000; // 5s default value 00368 00369 KConfig *kc = KGlobal::config(); 00370 KConfigGroupSaver ks( kc, QString::fromLatin1("KDE") ); 00371 enabled = kc->readBoolEntry( 00372 QString::fromLatin1("Autohiding cursor enabled"), true ); 00373 } 00374 00375 KCursorPrivate::~KCursorPrivate() 00376 { 00377 } 00378 00379 void KCursorPrivate::setAutoHideCursor( QWidget *w, bool enable, bool customEventFilter ) 00380 { 00381 if ( !w || !enabled ) 00382 return; 00383 00384 if ( enable ) 00385 { 00386 if ( m_eventFilters.find( w ) != NULL ) 00387 return; 00388 KCursorPrivateAutoHideEventFilter* filter = new KCursorPrivateAutoHideEventFilter( w ); 00389 m_eventFilters.insert( w, filter ); 00390 if ( !customEventFilter ) 00391 w->installEventFilter( filter ); 00392 connect( w, SIGNAL( destroyed(QObject*) ), 00393 this, SLOT( slotWidgetDestroyed(QObject*) ) ); 00394 } 00395 else 00396 { 00397 KCursorPrivateAutoHideEventFilter* filter = m_eventFilters.take( w ); 00398 if ( filter == NULL ) 00399 return; 00400 w->removeEventFilter( filter ); 00401 delete filter; 00402 disconnect( w, SIGNAL( destroyed(QObject*) ), 00403 this, SLOT( slotWidgetDestroyed(QObject*) ) ); 00404 } 00405 } 00406 00407 bool KCursorPrivate::eventFilter( QObject *o, QEvent *e ) 00408 { 00409 if ( !enabled ) 00410 return false; 00411 00412 KCursorPrivateAutoHideEventFilter* filter = m_eventFilters.find( o ); 00413 00414 Q_ASSERT( filter != NULL ); 00415 if ( filter == NULL ) 00416 return false; 00417 00418 return filter->eventFilter( o, e ); 00419 } 00420 00421 void KCursorPrivate::slotWidgetDestroyed( QObject* o ) 00422 { 00423 KCursorPrivateAutoHideEventFilter* filter = m_eventFilters.take( o ); 00424 00425 Q_ASSERT( filter != NULL ); 00426 00427 filter->resetWidget(); // so that dtor doesn't access it 00428 delete filter; 00429 } 00430 00431 #include "kcursor_private.moc"
KDE Logo
This file is part of the documentation for kdeui Library Version 3.4.0.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Tue Apr 12 22:56:21 2005 by doxygen 1.3.7 written by Dimitri van Heesch, © 1997-2003