00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023 #include "config.h"
00024
00025 #undef QT_NO_TRANSLATION
00026 #include <qtranslator.h>
00027 #define QT_NO_TRANSLATION
00028 #undef Unsorted
00029 #include <qdir.h>
00030 #include <qptrcollection.h>
00031 #include <qwidgetlist.h>
00032 #include <qstrlist.h>
00033 #include <qfile.h>
00034 #include <qmessagebox.h>
00035 #include <qtextstream.h>
00036 #include <qregexp.h>
00037 #include <qlineedit.h>
00038 #include <qtextedit.h>
00039 #include <qsessionmanager.h>
00040 #include <qptrlist.h>
00041 #include <qtimer.h>
00042 #include <qstylesheet.h>
00043 #include <qpixmapcache.h>
00044 #include <qtooltip.h>
00045 #include <qstylefactory.h>
00046 #ifndef QT_NO_SQL
00047 #include <qsqlpropertymap.h>
00048 #endif
00049
00050 #undef QT_NO_TRANSLATION
00051 #include "kapplication.h"
00052 #define QT_NO_TRANSLATION
00053 #include <kglobal.h>
00054 #include <kstandarddirs.h>
00055 #include <kdebug.h>
00056 #include <klocale.h>
00057 #include <kstyle.h>
00058 #include <kiconloader.h>
00059 #include <kclipboard.h>
00060 #include <kconfig.h>
00061 #include <ksimpleconfig.h>
00062 #include <kcmdlineargs.h>
00063 #include <kaboutdata.h>
00064 #include <kglobalsettings.h>
00065 #include <kcrash.h>
00066 #include <kdatastream.h>
00067 #include <klibloader.h>
00068 #include <kmimesourcefactory.h>
00069 #include <kstdaccel.h>
00070 #include <kaccel.h>
00071 #include <kcheckaccelerators.h>
00072 #include <qptrdict.h>
00073
00074 #include <kstartupinfo.h>
00075
00076 #include <dcopclient.h>
00077
00078 #include <sys/types.h>
00079 #ifdef HAVE_SYS_STAT_H
00080 #include <sys/stat.h>
00081 #endif
00082 #include <sys/wait.h>
00083
00084 #include "kwin.h"
00085
00086 #include <fcntl.h>
00087 #include <stdlib.h>
00088 #include <signal.h>
00089 #include <unistd.h>
00090 #include <time.h>
00091 #include <sys/time.h>
00092 #include <errno.h>
00093 #include <string.h>
00094 #include <netdb.h>
00095 #ifndef Q_WS_QWS //FIXME(E): NetWM should talk to QWS...
00096 #include <netwm.h>
00097 #endif
00098
00099 #include "kprocctrl.h"
00100
00101 #ifdef HAVE_PATHS_H
00102 #include <paths.h>
00103 #endif
00104
00105 #ifdef Q_WS_X11
00106 #include <X11/Xlib.h>
00107 #include <X11/Xutil.h>
00108 #include <X11/Xatom.h>
00109 #include <X11/SM/SMlib.h>
00110 #endif
00111 #include <KDE-ICE/ICElib.h>
00112
00113 #if defined(Q_WS_X11)
00114
00115 const int XKeyPress = KeyPress;
00116 const int XKeyRelease = KeyRelease;
00117 #undef KeyPress
00118 #endif
00119
00120 #ifdef Q_WS_X11
00121 #define DISPLAY "DISPLAY"
00122 #elif defined(Q_WS_QWS)
00123 #define DISPLAY "QWS_DISPLAY"
00124 #endif
00125
00126 #include <kipc.h>
00127
00128 #include "kappdcopiface.h"
00129
00130 bool kde_have_kipc = true;
00131
00132 KApplication* KApplication::KApp = 0L;
00133 bool KApplication::loadedByKdeinit = false;
00134 DCOPClient *KApplication::s_DCOPClient = 0L;
00135 bool KApplication::s_dcopClientNeedsPostInit = false;
00136
00137 static Atom atom_DesktopWindow;
00138 static Atom atom_NetSupported;
00139 static Atom atom_KdeNetUserTime;
00140
00141 template class QPtrList<KSessionManaged>;
00142
00143 #ifdef Q_WS_X11
00144 extern "C" {
00145 static int kde_xio_errhandler( Display * )
00146 {
00147 return kapp->xioErrhandler();
00148 }
00149
00150 static int kde_x_errhandler( Display *dpy, XErrorEvent *err )
00151 {
00152 char errstr[256];
00153 XGetErrorText( dpy, err->error_code, errstr, 256 );
00154 if ( err->error_code != BadWindow )
00155 kdWarning() << "KDE detected X Error: " << errstr << " " << err->error_code
00156 << "\n Major opcode: " << err->request_code << endl;
00157 return 0;
00158 }
00159 }
00160 #endif
00161
00162 extern "C" {
00163 static void kde_ice_ioerrorhandler( IceConn conn )
00164 {
00165 if(kapp)
00166 kapp->iceIOErrorHandler( conn );
00167
00168 }
00169 }
00170
00171
00172
00173
00174 class KApplicationPrivate
00175 {
00176 public:
00177 KApplicationPrivate()
00178 {
00179 actionRestrictions = false;
00180 refCount = 1;
00181 oldIceIOErrorHandler = 0;
00182 checkAccelerators = 0;
00183 overrideStyle=QString::null;
00184 startup_id = "0";
00185 m_KAppDCOPInterface = 0L;
00186 }
00187
00188 ~KApplicationPrivate()
00189 {}
00190
00191
00192 bool actionRestrictions : 1;
00199 int refCount;
00200 IceIOErrorHandler oldIceIOErrorHandler;
00201 KCheckAccelerators* checkAccelerators;
00202 QString overrideStyle;
00203 QString geometry_arg;
00204 QCString startup_id;
00205 KAppDCOPInterface *m_KAppDCOPInterface;
00206
00207 class URLActionRule
00208 {
00209 public:
00210 #define checkExactMatch(s, b) \
00211 if (s.isEmpty()) b = true; \
00212 else if (s[s.length()-1] == '!') \
00213 { b = false; s.truncate(s.length()-1); } \
00214 else b = true;
00215 #define checkStartWildCard(s, b) \
00216 if (s.isEmpty()) b = true; \
00217 else if (s[0] == '*') \
00218 { b = true; s = s.mid(1); } \
00219 else b = false;
00220 #define checkEqual(s, b) \
00221 b = (s == "=");
00222
00223 URLActionRule(const QString &act,
00224 const QString &bProt, const QString &bHost, const QString &bPath,
00225 const QString &dProt, const QString &dHost, const QString &dPath,
00226 bool perm)
00227 : action(act),
00228 baseProt(bProt), baseHost(bHost), basePath(bPath),
00229 destProt(dProt), destHost(dHost), destPath(dPath),
00230 permission(perm)
00231 {
00232 checkExactMatch(baseProt, baseProtWildCard);
00233 checkStartWildCard(baseHost, baseHostWildCard);
00234 checkExactMatch(basePath, basePathWildCard);
00235 checkExactMatch(destProt, destProtWildCard);
00236 checkStartWildCard(destHost, destHostWildCard);
00237 checkExactMatch(destPath, destPathWildCard);
00238 checkEqual(destProt, destProtEqual);
00239 checkEqual(destHost, destHostEqual);
00240 }
00241
00242 bool baseMatch(const KURL &url)
00243 {
00244 if (baseProtWildCard)
00245 {
00246 if (!baseProt.isEmpty() && !url.protocol().startsWith(baseProt))
00247 return false;
00248 }
00249 else
00250 {
00251 if (url.protocol() != baseProt)
00252 return false;
00253 }
00254 if (baseHostWildCard)
00255 {
00256 if (!baseHost.isEmpty() && !url.host().endsWith(baseHost))
00257 return false;
00258 }
00259 else
00260 {
00261 if (url.host() != baseHost)
00262 return false;
00263 }
00264 if (basePathWildCard)
00265 {
00266 if (!basePath.isEmpty() && !url.path().startsWith(basePath))
00267 return false;
00268 }
00269 else
00270 {
00271 if (url.path() != basePath)
00272 return false;
00273 }
00274 return true;
00275 }
00276
00277 bool destMatch(const KURL &url, const KURL &base)
00278 {
00279 if (destProtEqual)
00280 {
00281 if (url.protocol() != base.protocol())
00282 return false;
00283 }
00284 else if (destProtWildCard)
00285 {
00286 if (!destProt.isEmpty() && !url.protocol().startsWith(destProt))
00287 return false;
00288 }
00289 else
00290 {
00291 if (url.protocol() != destProt)
00292 return false;
00293 }
00294 if (destHostWildCard)
00295 {
00296 if (!destHost.isEmpty() && !url.host().endsWith(destHost))
00297 return false;
00298 }
00299 else if (destHostEqual)
00300 {
00301 if (url.host() != base.host())
00302 return false;
00303 }
00304 else
00305 {
00306 if (url.host() != destHost)
00307 return false;
00308 }
00309 if (destPathWildCard)
00310 {
00311 if (!destPath.isEmpty() && !url.path().startsWith(destPath))
00312 return false;
00313 }
00314 else
00315 {
00316 if (url.path() != destPath)
00317 return false;
00318 }
00319 return true;
00320 }
00321
00322 QString action;
00323 QString baseProt;
00324 QString baseHost;
00325 QString basePath;
00326 QString destProt;
00327 QString destHost;
00328 QString destPath;
00329 bool baseProtWildCard : 1;
00330 bool baseHostWildCard : 1;
00331 bool basePathWildCard : 1;
00332 bool destProtWildCard : 1;
00333 bool destHostWildCard : 1;
00334 bool destPathWildCard : 1;
00335 bool destProtEqual : 1;
00336 bool destHostEqual : 1;
00337 bool permission;
00338 };
00339 QPtrList<URLActionRule> urlActionRestrictions;
00340
00341 QString sessionKey;
00342 QString pSessionConfigFile;
00343 };
00344
00345
00346 static QPtrList<QWidget>*x11Filter = 0;
00347 static bool autoDcopRegistration = true;
00348
00349 void KApplication::installX11EventFilter( QWidget* filter )
00350 {
00351 if ( !filter )
00352 return;
00353 if (!x11Filter)
00354 x11Filter = new QPtrList<QWidget>;
00355 connect ( filter, SIGNAL( destroyed() ), this, SLOT( x11FilterDestroyed() ) );
00356 x11Filter->append( filter );
00357 }
00358
00359 void KApplication::x11FilterDestroyed()
00360 {
00361 if ( !x11Filter || !sender() )
00362 return;
00363 QWidget *w = static_cast<QWidget *>(const_cast<QObject *>(sender()));
00364 x11Filter->removeRef( w );
00365 if ( x11Filter->isEmpty() ) {
00366 delete x11Filter;
00367 x11Filter = 0;
00368 }
00369 }
00370
00371
00372
00373
00374
00375 extern bool g_bKillAccelOverride;
00376
00377 bool KApplication::notify(QObject *receiver, QEvent *event)
00378 {
00379 QEvent::Type t = event->type();
00380 if (g_bKillAccelOverride)
00381 {
00382 g_bKillAccelOverride = false;
00383
00384 if (t == QEvent::AccelOverride)
00385 {
00386 static_cast<QKeyEvent *>(event)->accept();
00387 return true;
00388 }
00389 else
00390 kdWarning(125) << "g_bKillAccelOverride set, but received an event other than AccelOverride." << endl;
00391 }
00392
00393 if ((t == QEvent::AccelOverride) || (t == QEvent::KeyPress))
00394 {
00395 static const KShortcut& _selectAll = KStdAccel::selectAll();
00396 if (receiver && receiver->inherits("QLineEdit"))
00397 {
00398 QLineEdit *edit = static_cast<QLineEdit *>(receiver);
00399
00400 QKeyEvent *kevent = static_cast<QKeyEvent *>(event);
00401 KKey key(kevent);
00402 if (_selectAll.contains(key))
00403 {
00404 if (t == QEvent::KeyPress)
00405 {
00406 edit->selectAll();
00407 return true;
00408 }
00409 else
00410 {
00411 kevent->accept();
00412 }
00413 }
00414
00415 if (key == KKey(Qt::CTRL + Qt::Key_U))
00416 {
00417 if (t == QEvent::KeyPress)
00418 {
00419 if (!edit->isReadOnly())
00420 {
00421 QString t(edit->text());
00422 t = t.mid(edit->cursorPosition());
00423 edit->validateAndSet(t, 0, 0, 0);
00424 }
00425 return true;
00426 }
00427 else
00428 {
00429 kevent->accept();
00430 }
00431
00432 }
00433 }
00434 if (receiver && receiver->inherits("QTextEdit"))
00435 {
00436 QTextEdit *medit = static_cast<QTextEdit *>(receiver);
00437
00438 QKeyEvent *kevent = static_cast<QKeyEvent *>(event);
00439 if (_selectAll.contains(KKey(kevent)))
00440 {
00441 if (t == QEvent::KeyPress)
00442 {
00443 medit->selectAll();
00444 return true;
00445 }
00446 else
00447 {
00448 kevent->accept();
00449 }
00450 }
00451 }
00452 }
00453 return QApplication::notify(receiver, event);
00454 }
00455
00456
00457
00458 static QPtrList<KSessionManaged>* sessionClients()
00459 {
00460 static QPtrList<KSessionManaged>* session_clients = 0L;
00461 if ( !session_clients )
00462 session_clients = new QPtrList<KSessionManaged>;
00463 return session_clients;
00464 }
00465
00466
00467
00468
00469
00470
00471 QString KApplication::sessionConfigName() const
00472 {
00473 #if QT_VERSION < 0x030100
00474 return QString("session/%1_%2_%3").arg(name()).arg(sessionId()).arg(d->sessionKey);
00475 #else
00476 QString sessKey = sessionKey();
00477 if ( sessKey.isEmpty() && !d->sessionKey.isEmpty() )
00478 sessKey = d->sessionKey;
00479 return QString("session/%1_%2_%3").arg(name()).arg(sessionId()).arg(sessKey);
00480 #endif
00481 }
00482
00483 #ifndef Q_WS_QWS
00484 static SmcConn mySmcConnection = 0;
00485 static SmcConn tmpSmcConnection = 0;
00486 #else
00487
00488
00489 #endif
00490 static QTime* smModificationTime = 0;
00491
00492 KApplication::KApplication( int& argc, char** argv, const QCString& rAppName,
00493 bool allowStyles, bool GUIenabled ) :
00494 QApplication( argc, argv, GUIenabled ), KInstance(rAppName),
00495 #ifdef Q_WS_X11
00496 display(0L),
00497 #endif
00498 d (new KApplicationPrivate())
00499 {
00500 read_app_startup_id();
00501 if (!GUIenabled)
00502 allowStyles = false;
00503 useStyles = allowStyles;
00504 Q_ASSERT (!rAppName.isEmpty());
00505 setName(rAppName);
00506
00507 KCmdLineArgs::initIgnore(argc, argv, rAppName.data());
00508 parseCommandLine( );
00509 init(GUIenabled);
00510 d->m_KAppDCOPInterface = new KAppDCOPInterface(this);
00511 }
00512
00513 KApplication::KApplication( bool allowStyles, bool GUIenabled ) :
00514 QApplication( *KCmdLineArgs::qt_argc(), *KCmdLineArgs::qt_argv(),
00515 GUIenabled ),
00516 KInstance( KCmdLineArgs::about),
00517 #ifdef Q_WS_X11
00518 display(0L),
00519 #endif
00520 d (new KApplicationPrivate)
00521 {
00522 read_app_startup_id();
00523 if (!GUIenabled)
00524 allowStyles = false;
00525 useStyles = allowStyles;
00526 setName( instanceName() );
00527
00528 parseCommandLine( );
00529 init(GUIenabled);
00530 d->m_KAppDCOPInterface = new KAppDCOPInterface(this);
00531 }
00532
00533 KApplication::KApplication( bool allowStyles, bool GUIenabled, KInstance* _instance ) :
00534 QApplication( *KCmdLineArgs::qt_argc(), *KCmdLineArgs::qt_argv(),
00535 GUIenabled ),
00536 KInstance( _instance ),
00537 #ifdef Q_WS_X11
00538 display(0L),
00539 #endif
00540 d (new KApplicationPrivate)
00541 {
00542 read_app_startup_id();
00543 if (!GUIenabled)
00544 allowStyles = false;
00545 useStyles = allowStyles;
00546 setName( instanceName() );
00547
00548 parseCommandLine( );
00549 init(GUIenabled);
00550 }
00551
00552 #ifdef Q_WS_X11
00553 KApplication::KApplication(Display *display, int& argc, char** argv, const QCString& rAppName,
00554 bool allowStyles, bool GUIenabled ) :
00555 QApplication( display ), KInstance(rAppName),
00556 display(0L),
00557 d (new KApplicationPrivate())
00558 {
00559 read_app_startup_id();
00560 if (!GUIenabled)
00561 allowStyles = false;
00562 useStyles = allowStyles;
00563
00564 Q_ASSERT (!rAppName.isEmpty());
00565 setName(rAppName);
00566
00567 KCmdLineArgs::initIgnore(argc, argv, rAppName.data());
00568 parseCommandLine( );
00569 init(GUIenabled);
00570 d->m_KAppDCOPInterface = new KAppDCOPInterface(this);
00571 }
00572 #endif
00573
00574 int KApplication::xioErrhandler()
00575 {
00576 if(kapp)
00577 {
00578 emit shutDown();
00579 exit( 1 );
00580 }
00581 return 0;
00582 }
00583
00584 void KApplication::iceIOErrorHandler( _IceConn *conn )
00585 {
00586 emit shutDown();
00587
00588 if ( d->oldIceIOErrorHandler != NULL )
00589 (*d->oldIceIOErrorHandler)( conn );
00590
00591 exit( 1 );
00592 }
00593
00594 class KDETranslator : public QTranslator
00595 {
00596 public:
00597 KDETranslator(QObject *parent) : QTranslator(parent, "kdetranslator") {}
00598 virtual QTranslatorMessage findMessage(const char* context,
00599 const char *sourceText,
00600 const char* message) const
00601 {
00602 QTranslatorMessage res;
00603 res.setTranslation(KGlobal::locale()->translateQt(context, sourceText, message));
00604 return res;
00605 }
00606 };
00607
00608 void KApplication::init(bool GUIenabled)
00609 {
00610 if ((getuid() != geteuid()) ||
00611 (getgid() != getegid()))
00612 {
00613 fprintf(stderr, "The KDE libraries are not designed to run with suid privileges.\n");
00614 ::exit(127);
00615 }
00616
00617 if( KProcessController::theKProcessController == 0 )
00618 (void) new KProcessController();
00619
00620 (void) KClipboardSynchronizer::self();
00621
00622 QApplication::setDesktopSettingsAware( false );
00623
00624 KApp = this;
00625
00626
00627 #ifdef Q_WS_X11 //FIXME(E)
00628
00629 if ( GUIenabled ) {
00630 const int max = 20;
00631 Atom* atoms[max];
00632 char* names[max];
00633 Atom atoms_return[max];
00634 int n = 0;
00635
00636 atoms[n] = &kipcCommAtom;
00637 names[n++] = (char *) "KIPC_COMM_ATOM";
00638
00639 atoms[n] = &atom_DesktopWindow;
00640 names[n++] = (char *) "KDE_DESKTOP_WINDOW";
00641
00642 atoms[n] = &atom_NetSupported;
00643 names[n++] = (char *) "_NET_SUPPORTED";
00644
00645 atoms[n] = &atom_KdeNetUserTime;
00646 names[n++] = (char *) "_KDE_NET_USER_TIME";
00647
00648 XInternAtoms( qt_xdisplay(), names, n, FALSE, atoms_return );
00649 for (int i = 0; i < n; i++ )
00650 *atoms[i] = atoms_return[i];
00651 }
00652 #endif
00653
00654 dcopAutoRegistration();
00655 dcopClientPostInit();
00656
00657 smw = 0;
00658
00659
00660 kipcEventMask = (1 << KIPC::StyleChanged) | (1 << KIPC::PaletteChanged) |
00661 (1 << KIPC::FontChanged) | (1 << KIPC::BackgroundChanged) |
00662 (1 << KIPC::ToolbarStyleChanged) | (1 << KIPC::SettingsChanged) |
00663 (1 << KIPC::ClipboardConfigChanged);
00664
00665
00666 (void) KGlobal::locale();
00667
00668 KConfig* config = KGlobal::config();
00669 d->actionRestrictions = config->hasGroup("KDE Action Restrictions" );
00670
00671 if (GUIenabled)
00672 {
00673 #ifdef Q_WS_X11
00674
00675 fcntl(ConnectionNumber(qt_xdisplay()), F_SETFD, FD_CLOEXEC);
00676
00677 XSetErrorHandler( kde_x_errhandler );
00678 XSetIOErrorHandler( kde_xio_errhandler );
00679 #endif
00680
00681 connect( this, SIGNAL( aboutToQuit() ), this, SIGNAL( shutDown() ) );
00682
00683 #ifdef Q_WS_X11 //FIXME(E)
00684 display = desktop()->x11Display();
00685 #endif
00686
00687 {
00688 QStringList plugins = KGlobal::dirs()->resourceDirs( "qtplugins" );
00689 QStringList::Iterator it = plugins.begin();
00690 while (it != plugins.end()) {
00691 addLibraryPath( *it );
00692 ++it;
00693 }
00694
00695 }
00696 kdisplaySetStyle();
00697 kdisplaySetFont();
00698
00699 propagateSettings(SETTINGS_QT);
00700
00701
00702 QMimeSourceFactory::setDefaultFactory (mimeSourceFactory());
00703
00704 KConfigGroupSaver saver( config, "Development" );
00705 if( config->hasKey( "CheckAccelerators" ) || config->hasKey( "AutoCheckAccelerators" ))
00706 d->checkAccelerators = new KCheckAccelerators( this );
00707 }
00708
00709
00710
00711 bool rtl = reverseLayout();
00712 installTranslator(new KDETranslator(this));
00713 setReverseLayout( rtl );
00714 if (i18n( "_: Dear Translator! Translate this string to the string 'LTR' in "
00715 "left-to-right languages (as english) or to 'RTL' in right-to-left "
00716 "languages (such as Hebrew and Arabic) to get proper widget layout." ) == "RTL")
00717
00718 setReverseLayout( !rtl );
00719
00720
00721 KGlobal::dirs()->addResourceType("appdata", KStandardDirs::kde_default("data")
00722 + QString::fromLatin1(name()) + '/');
00723 pSessionConfig = 0L;
00724 bSessionManagement = true;
00725
00726 #ifdef Q_WS_X11
00727
00728 if (GUIenabled && kde_have_kipc )
00729 {
00730 smw = new QWidget(0,0);
00731 long data = 1;
00732 XChangeProperty(qt_xdisplay(), smw->winId(),
00733 atom_DesktopWindow, atom_DesktopWindow,
00734 32, PropModeReplace, (unsigned char *)&data, 1);
00735 }
00736 #else
00737
00738 #endif
00739
00740 d->oldIceIOErrorHandler = IceSetIOErrorHandler( kde_ice_ioerrorhandler );
00741 }
00742
00743 static int my_system (const char *command) {
00744 int pid, status;
00745
00746 QApplication::flushX();
00747 pid = fork();
00748 if (pid == -1)
00749 return -1;
00750 if (pid == 0) {
00751 const char* shell = "/bin/sh";
00752 execl(shell, shell, "-c", command, 0L);
00753 ::exit(127);
00754 }
00755 do {
00756 if (waitpid(pid, &status, 0) == -1) {
00757 if (errno != EINTR)
00758 return -1;
00759 } else
00760 return status;
00761 } while(1);
00762 }
00763
00764
00765 DCOPClient *KApplication::dcopClient()
00766 {
00767 if (s_DCOPClient)
00768 return s_DCOPClient;
00769
00770 s_DCOPClient = new DCOPClient();
00771 KCmdLineArgs *args = KCmdLineArgs::parsedArgs("kde");
00772 if (args->isSet("dcopserver"))
00773 {
00774 s_DCOPClient->setServerAddress( args->getOption("dcopserver"));
00775 }
00776 if( kapp ) {
00777 connect(s_DCOPClient, SIGNAL(attachFailed(const QString &)),
00778 kapp, SLOT(dcopFailure(const QString &)));
00779 connect(s_DCOPClient, SIGNAL(blockUserInput(bool) ),
00780 kapp, SLOT(dcopBlockUserInput(bool)) );
00781 }
00782 else
00783 s_dcopClientNeedsPostInit = true;
00784
00785 DCOPClient::setMainClient( s_DCOPClient );
00786 return s_DCOPClient;
00787 }
00788
00789 void KApplication::dcopClientPostInit()
00790 {
00791 if( s_dcopClientNeedsPostInit )
00792 {
00793 s_dcopClientNeedsPostInit = false;
00794 connect(s_DCOPClient, SIGNAL(blockUserInput(bool) ),
00795 SLOT(dcopBlockUserInput(bool)) );
00796 s_DCOPClient->bindToApp();
00797 }
00798 }
00799
00800 void KApplication::dcopAutoRegistration()
00801 {
00802 if (autoDcopRegistration)
00803 {
00804 ( void ) dcopClient();
00805 if( dcopClient()->appId().isEmpty())
00806 dcopClient()->registerAs(name());
00807 }
00808 }
00809
00810 void KApplication::disableAutoDcopRegistration()
00811 {
00812 autoDcopRegistration = false;
00813 }
00814
00815 KConfig* KApplication::sessionConfig()
00816 {
00817 if (pSessionConfig)
00818 return pSessionConfig;
00819
00820
00821 pSessionConfig = new KConfig( sessionConfigName(), false, false);
00822 return pSessionConfig;
00823 }
00824
00825 void KApplication::ref()
00826 {
00827 d->refCount++;
00828
00829 }
00830
00831 void KApplication::deref()
00832 {
00833 d->refCount--;
00834
00835 if ( d->refCount <= 0 )
00836 quit();
00837 }
00838
00839 KSessionManaged::KSessionManaged()
00840 {
00841 sessionClients()->remove( this );
00842 sessionClients()->append( this );
00843 }
00844
00845 KSessionManaged::~KSessionManaged()
00846 {
00847 sessionClients()->remove( this );
00848 }
00849
00850 bool KSessionManaged::saveState(QSessionManager&)
00851 {
00852 return true;
00853 }
00854
00855 bool KSessionManaged::commitData(QSessionManager&)
00856 {
00857 return true;
00858 }
00859
00860
00861 void KApplication::disableSessionManagement() {
00862 bSessionManagement = false;
00863 }
00864
00865
00866 bool KApplication::requestShutDown(
00867 ShutdownConfirm confirm, ShutdownType sdtype, ShutdownMode sdmode )
00868 {
00869 #ifdef Q_WS_X11
00870 QApplication::syncX();
00871
00872 if ( confirm == ShutdownConfirmYes ||
00873 sdtype != ShutdownTypeDefault ||
00874 sdmode != ShutdownModeDefault )
00875 {
00876 QByteArray data;
00877 QDataStream arg(data, IO_WriteOnly);
00878 arg << (int)confirm << (int)sdtype << (int)sdmode;
00879 return dcopClient()->send( "ksmserver", "ksmserver",
00880 "logout(int,int,int)", data );
00881 }
00882
00883 if ( mySmcConnection ) {
00884
00885 SmcRequestSaveYourself( mySmcConnection, SmSaveBoth, True,
00886 SmInteractStyleAny,
00887 confirm == ShutdownConfirmNo, True );
00888
00889
00890 IceFlush(SmcGetIceConnection(mySmcConnection));
00891 return TRUE;
00892 }
00893
00894
00895
00896 propagateSessionManager();
00897 QCString smEnv = ::getenv("SESSION_MANAGER");
00898 if (smEnv.isEmpty())
00899 return FALSE;
00900
00901 if (! tmpSmcConnection) {
00902 char cerror[256];
00903 char* myId = 0;
00904 char* prevId = 0;
00905 SmcCallbacks cb;
00906 tmpSmcConnection = SmcOpenConnection( 0, 0, 1, 0,
00907 0, &cb,
00908 prevId,
00909 &myId,
00910 255,
00911 cerror );
00912 ::free( myId );
00913 if (!tmpSmcConnection )
00914 return FALSE;
00915 }
00916
00917 SmcRequestSaveYourself( tmpSmcConnection, SmSaveBoth, True,
00918 SmInteractStyleAny, False, True );
00919
00920
00921 IceFlush(SmcGetIceConnection(tmpSmcConnection));
00922 return TRUE;
00923 #else
00924
00925 return false;
00926 #endif
00927 }
00928
00929 void KApplication::propagateSessionManager()
00930 {
00931 QCString fName = QFile::encodeName(locateLocal("socket", "KSMserver"));
00932 QCString display = ::getenv(DISPLAY);
00933
00934 display.replace(QRegExp("\\.[0-9]+$"), "");
00935 int i;
00936 while( (i = display.find(':')) >= 0)
00937 display[i] = '_';
00938
00939 fName += "_"+display;
00940 QCString smEnv = ::getenv("SESSION_MANAGER");
00941 bool check = smEnv.isEmpty();
00942 if ( !check && smModificationTime ) {
00943 QFileInfo info( fName );
00944 QTime current = info.lastModified().time();
00945 check = current > *smModificationTime;
00946 }
00947 if ( check ) {
00948 delete smModificationTime;
00949 QFile f( fName );
00950 if ( !f.open( IO_ReadOnly ) )
00951 return;
00952 QFileInfo info ( f );
00953 smModificationTime = new QTime( info.lastModified().time() );
00954 QTextStream t(&f);
00955 t.setEncoding( QTextStream::Latin1 );
00956 QString s = t.readLine();
00957 f.close();
00958 ::setenv( "SESSION_MANAGER", s.latin1(), TRUE );
00959 }
00960 }
00961
00962 void KApplication::commitData( QSessionManager& sm )
00963 {
00964 bool cancelled = false;
00965 for (KSessionManaged* it = sessionClients()->first();
00966 it && !cancelled;
00967 it = sessionClients()->next() ) {
00968 cancelled = !it->commitData( sm );
00969 }
00970 if ( cancelled )
00971 sm.cancel();
00972
00973 if ( sm.allowsInteraction() ) {
00974 QWidgetList done;
00975 QWidgetList *list = QApplication::topLevelWidgets();
00976 bool cancelled = FALSE;
00977 QWidget* w = list->first();
00978 while ( !cancelled && w ) {
00979 if ( !w->testWState( WState_ForceHide ) && !w->inherits("KMainWindow") ) {
00980 QCloseEvent e;
00981 sendEvent( w, &e );
00982 cancelled = !e.isAccepted();
00983 if ( !cancelled )
00984 done.append( w );
00985 delete list;
00986 list = QApplication::topLevelWidgets();
00987 w = list->first();
00988 } else {
00989 w = list->next();
00990 }
00991 while ( w && done.containsRef( w ) )
00992 w = list->next();
00993 }
00994 delete list;
00995 }
00996
00997
00998 if ( !bSessionManagement ) {
00999 sm.setRestartHint( QSessionManager::RestartNever );
01000 return;
01001 }
01002 }
01003
01004 void KApplication::saveState( QSessionManager& sm )
01005 {
01006 #ifndef Q_WS_QWS
01007 static bool firstTime = true;
01008 mySmcConnection = (SmcConn) sm.handle();
01009
01010 if ( !bSessionManagement ) {
01011 sm.setRestartHint( QSessionManager::RestartNever );
01012 return;
01013 }
01014
01015 #if QT_VERSION < 0x030100
01016 {
01017
01018 timeval tv;
01019 gettimeofday( &tv, 0 );
01020 d->sessionKey = QString::number( tv.tv_sec ) + "_" + QString::number(tv.tv_usec);
01021 }
01022 #endif
01023
01024 if ( firstTime ) {
01025 firstTime = false;
01026 return;
01027 }
01028
01029
01030
01031
01032
01033
01034
01035 if ( pSessionConfig ) {
01036 delete pSessionConfig;
01037 pSessionConfig = 0;
01038 }
01039
01040
01041 QStringList restartCommand = sm.restartCommand();
01042 #if QT_VERSION < 0x030100
01043 restartCommand.clear();
01044 restartCommand << argv()[0] << "-session" << sm.sessionId() << "-smkey" << d->sessionKey;
01045 sm.setRestartCommand( restartCommand );
01046 #endif
01047
01048
01049 QCString multiHead = getenv("KDE_MULTIHEAD");
01050 if (multiHead.lower() == "true") {
01051
01052
01053
01054
01055
01056
01057 QCString displayname = getenv(DISPLAY);
01058 if (! displayname.isNull()) {
01059
01060
01061 restartCommand.append("-display");
01062 restartCommand.append(displayname);
01063 }
01064 sm.setRestartCommand( restartCommand );
01065 }
01066
01067
01068
01069 emit saveYourself();
01070 bool cancelled = false;
01071 for (KSessionManaged* it = sessionClients()->first();
01072 it && !cancelled;
01073 it = sessionClients()->next() ) {
01074 cancelled = !it->saveState( sm );
01075 }
01076
01077
01078 if ( pSessionConfig ) {
01079 pSessionConfig->sync();
01080 QStringList discard;
01081 discard << "rm" << locateLocal("config", sessionConfigName());
01082 sm.setDiscardCommand( discard );
01083 }
01084
01085 if ( cancelled )
01086 sm.cancel();
01087 #else
01088
01089 #endif
01090 }
01091
01092 void KApplication::startKdeinit()
01093 {
01094
01095 QString srv = KStandardDirs::findExe(QString::fromLatin1("kdeinit"));
01096 if (srv.isEmpty())
01097 srv = KStandardDirs::findExe(QString::fromLatin1("kdeinit"), KDEDIR+QString::fromLatin1("/bin"));
01098 if (srv.isEmpty())
01099 return;
01100 if (kapp && (Tty != kapp->type()))
01101 setOverrideCursor( Qt::waitCursor );
01102 my_system(QFile::encodeName(srv)+" --suicide");
01103 if (kapp && (Tty != kapp->type()))
01104 restoreOverrideCursor();
01105 }
01106
01107 void KApplication::dcopFailure(const QString &msg)
01108 {
01109 static int failureCount = 0;
01110 failureCount++;
01111 if (failureCount == 1)
01112 {
01113 startKdeinit();
01114 return;
01115 }
01116 if (failureCount == 2)
01117 {
01118 QString msgStr(i18n("There was an error setting up inter-process\n"
01119 "communications for KDE. The message returned\n"
01120 "by the system was:\n\n"));
01121 msgStr += msg;
01122 msgStr += i18n("\n\nPlease check that the \"dcopserver\" program is running!");
01123
01124 if (Tty != kapp->type())
01125 {
01126 QMessageBox::critical
01127 (
01128 kapp->mainWidget(),
01129 i18n("DCOP communications error (%1)").arg(kapp->caption()),
01130 msgStr,
01131 i18n("OK")
01132 );
01133 }
01134 else
01135 {
01136 fprintf(stderr, "%s\n", msgStr.local8Bit().data());
01137 }
01138
01139 return;
01140 }
01141 }
01142
01143 static const KCmdLineOptions qt_options[] =
01144 {
01145
01146 #ifdef Q_WS_X11
01147 { "display <displayname>", I18N_NOOP("Use the X-server display 'displayname'."), 0},
01148 #else
01149 { "display <displayname>", I18N_NOOP("Use the QWS display 'displayname'."), 0},
01150 #endif
01151 { "session <sessionId>", I18N_NOOP("Restore the application for the given 'sessionId'."), 0},
01152 { "cmap", I18N_NOOP("Causes the application to install a private color\nmap on an 8-bit display."), 0},
01153 { "ncols <count>", I18N_NOOP("Limits the number of colors allocated in the color\ncube on an 8-bit display, if the application is\nusing the QApplication::ManyColor color\nspecification."), 0},
01154 { "nograb", I18N_NOOP("tells Qt to never grab the mouse or the keyboard."), 0},
01155 { "dograb", I18N_NOOP("running under a debugger can cause an implicit\n-nograb, use -dograb to override."), 0},
01156 { "sync", I18N_NOOP("switches to synchronous mode for debugging."), 0},
01157 { "fn", 0, 0},
01158 { "font <fontname>", I18N_NOOP("defines the application font."), 0},
01159 { "bg", 0, 0},
01160 { "background <color>", I18N_NOOP("sets the default background color and an\napplication palette (light and dark shades are\ncalculated)."), 0},
01161 { "fg", 0, 0},
01162 { "foreground <color>", I18N_NOOP("sets the default foreground color."), 0},
01163 { "btn", 0, 0},
01164 { "button <color>", I18N_NOOP("sets the default button color."), 0},
01165 { "name <name>", I18N_NOOP("sets the application name."), 0},
01166 { "title <title>", I18N_NOOP("sets the application title (caption)."), 0},
01167 #ifdef Q_WS_X11
01168 { "visual TrueColor", I18N_NOOP("forces the application to use a TrueColor visual on\nan 8-bit display."), 0},
01169 { "inputstyle <inputstyle>", I18N_NOOP("sets XIM (X Input Method) input style. Possible\nvalues are onthespot, overthespot, offthespot and\nroot."), 0 },
01170 { "im <XIM server>", I18N_NOOP("set XIM server."),0},
01171 { "noxim", I18N_NOOP("disable XIM."), 0 },
01172 #endif
01173 #ifdef Q_WS_QWS
01174 { "qws", I18N_NOOP("forces the application to run as QWS Server."), 0},
01175 #endif
01176 { "reverse", I18N_NOOP("mirrors the whole layout of widgets."), 0},
01177 { 0, 0, 0 }
01178 };
01179
01180 static const KCmdLineOptions kde_options[] =
01181 {
01182 { "caption <caption>", I18N_NOOP("Use 'caption' as name in the titlebar."), 0},
01183 { "icon <icon>", I18N_NOOP("Use 'icon' as the application icon."), 0},
01184 { "miniicon <icon>", I18N_NOOP("Use 'icon' as the icon in the titlebar."), 0},
01185 { "config <filename>", I18N_NOOP("Use alternative configuration file."), 0},
01186 { "dcopserver <server>", I18N_NOOP("Use the DCOP Server specified by 'server'."), 0},
01187 { "nocrashhandler", I18N_NOOP("Disable crash handler, to get core dumps."), 0},
01188 { "waitforwm", I18N_NOOP("Waits for a WM_NET compatible windowmanager."), 0},
01189 { "style <style>", I18N_NOOP("sets the application GUI style."), 0},
01190 { "geometry <geometry>", I18N_NOOP("sets the client geometry of the main widget."), 0},
01191 #if QT_VERSION < 0x030100
01192 { "smkey <sessionKey>", I18N_NOOP("Define a 'sessionKey' for the session id. Only valid with -session"), 0},
01193 #else
01194 { "smkey <sessionKey>", 0, 0},
01195
01196
01197 #endif
01198 { 0, 0, 0 }
01199 };
01200
01201 void
01202 KApplication::addCmdLineOptions()
01203 {
01204 KCmdLineArgs::addCmdLineOptions(qt_options, "Qt", "qt");
01205 KCmdLineArgs::addCmdLineOptions(kde_options, "KDE", "kde");
01206 }
01207
01208 void KApplication::parseCommandLine( )
01209 {
01210 KCmdLineArgs *args = KCmdLineArgs::parsedArgs("kde");
01211
01212 if (args->isSet("config"))
01213 {
01214 QString config = QString::fromLocal8Bit(args->getOption("config"));
01215 setConfigName(config);
01216 }
01217
01218 if (args->isSet("style"))
01219 {
01220
01221 QStringList styles = QStyleFactory::keys();
01222 QString reqStyle(args->getOption("style").lower());
01223
01224 for (QStringList::ConstIterator it = styles.begin(); it != styles.end(); ++it)
01225 if ((*it).lower() == reqStyle)
01226 {
01227 d->overrideStyle = *it;
01228 break;
01229 }
01230
01231 if (d->overrideStyle.isEmpty())
01232 fprintf(stderr, "%s", i18n("The style %1 was not found\n").arg(reqStyle).local8Bit().data());
01233 }
01234
01235 if (args->isSet("caption"))
01236 {
01237 aCaption = QString::fromLocal8Bit(args->getOption("caption"));
01238 }
01239
01240 if (args->isSet("miniicon"))
01241 {
01242 const char *tmp = args->getOption("miniicon");
01243 aMiniIconPixmap = SmallIcon(tmp);
01244 aMiniIconName = tmp;
01245 }
01246
01247 if (args->isSet("icon"))
01248 {
01249 const char *tmp = args->getOption("icon");
01250 aIconPixmap = DesktopIcon( tmp );
01251 aIconName = tmp;
01252 if (aMiniIconPixmap.isNull())
01253 {
01254 aMiniIconPixmap = SmallIcon( tmp );
01255 aMiniIconName = tmp;
01256 }
01257 }
01258
01259 bool nocrashhandler = (getenv("KDE_DEBUG") != NULL);
01260 if (!nocrashhandler && args->isSet("crashhandler"))
01261 {
01262
01263 KCrash::setCrashHandler(KCrash::defaultCrashHandler);
01264 KCrash::setEmergencySaveFunction(NULL);
01265
01266 KCrash::setApplicationName(QString(args->appName()));
01267 }
01268
01269 #ifdef Q_WS_X11
01270 if ( args->isSet( "waitforwm" ) ) {
01271 Atom type;
01272 (void) desktop();
01273 int format;
01274 unsigned long length, after;
01275 unsigned char *data;
01276 while ( XGetWindowProperty( qt_xdisplay(), qt_xrootwin(), atom_NetSupported,
01277 0, 1, FALSE, AnyPropertyType, &type, &format,
01278 &length, &after, &data ) != Success || !length ) {
01279 if ( data )
01280 XFree( data );
01281 XEvent event;
01282 XWindowEvent( qt_xdisplay(), qt_xrootwin(), PropertyChangeMask, &event );
01283 }
01284 if ( data )
01285 XFree( data );
01286 }
01287 #else
01288
01289 #endif
01290
01291 if (args->isSet("geometry"))
01292 {
01293 d->geometry_arg = args->getOption("geometry");
01294 }
01295
01296 if (args->isSet("smkey"))
01297 {
01298 d->sessionKey = args->getOption("smkey");
01299 }
01300
01301 }
01302
01303 QString KApplication::geometryArgument() const
01304 {
01305 return d->geometry_arg;
01306 }
01307
01308 QPixmap KApplication::icon() const
01309 {
01310 if( aIconPixmap.isNull()) {
01311 KApplication *that = const_cast<KApplication *>(this);
01312 that->aIconPixmap = DesktopIcon( instanceName() );
01313 }
01314 return aIconPixmap;
01315 }
01316
01317 QString KApplication::iconName() const
01318 {
01319 return aIconName.isNull() ? (QString)instanceName() : aIconName;
01320 }
01321
01322 QPixmap KApplication::miniIcon() const
01323 {
01324 if (aMiniIconPixmap.isNull()) {
01325 KApplication *that = const_cast<KApplication *>(this);
01326 that->aMiniIconPixmap = SmallIcon( instanceName() );
01327 }
01328 return aMiniIconPixmap;
01329 }
01330
01331 QString KApplication::miniIconName() const
01332 {
01333 return aMiniIconName.isNull() ? (QString)instanceName() : aMiniIconName;
01334 }
01335
01336 extern void kDebugCleanup();
01337
01338 KApplication::~KApplication()
01339 {
01340 delete d->m_KAppDCOPInterface;
01341
01342
01343
01344
01345 KGlobal::deleteStaticDeleters();
01346 KLibLoader::cleanUp();
01347
01348 delete smw;
01349
01350
01351 delete s_DCOPClient;
01352 s_DCOPClient = 0L;
01353
01354 delete KProcessController::theKProcessController;
01355
01356 if ( d->oldIceIOErrorHandler != NULL )
01357 IceSetIOErrorHandler( d->oldIceIOErrorHandler );
01358
01359 delete d;
01360 KApp = 0;
01361
01362 #ifndef Q_WS_QWS
01363 mySmcConnection = 0;
01364 delete smModificationTime;
01365 smModificationTime = 0;
01366
01367
01368 if (tmpSmcConnection) {
01369 SmcCloseConnection( tmpSmcConnection, 0, 0 );
01370 tmpSmcConnection = 0;
01371 }
01372 #else
01373
01374 #endif
01375 }
01376
01377
01378 #ifdef Q_WS_X11
01379 class KAppX11HackWidget: public QWidget
01380 {
01381 public:
01382 bool publicx11Event( XEvent * e) { return x11Event( e ); }
01383 };
01384 #endif
01385
01386
01387
01388 static bool kapp_block_user_input = false;
01389
01390 void KApplication::dcopBlockUserInput( bool b )
01391 {
01392 kapp_block_user_input = b;
01393 }
01394
01395 #ifdef Q_WS_X11
01396 bool KApplication::x11EventFilter( XEvent *_event )
01397 {
01398 if ( activeWindow() ) {
01399 switch ( _event->type ) {
01400 case ButtonPress:
01401 case ButtonRelease:
01402 case XKeyPress:
01403 {
01404 timeval tv;
01405 gettimeofday( &tv, NULL );
01406 unsigned long now = tv.tv_sec * 10 + tv.tv_usec / 100000;
01407 XChangeProperty(qt_xdisplay(), activeWindow()->winId(),
01408 atom_KdeNetUserTime, XA_CARDINAL,
01409 32, PropModeReplace, (unsigned char *)&now, 1);
01410 }
01411 break;
01412 default: break;
01413 }
01414 }
01415
01416
01417 if ( kapp_block_user_input ) {
01418 switch ( _event->type ) {
01419 case ButtonPress:
01420 case ButtonRelease:
01421 case XKeyPress:
01422 case XKeyRelease:
01423 case MotionNotify:
01424 return TRUE;
01425 default:
01426 break;
01427 }
01428 }
01429
01430 if (x11Filter) {
01431 for (QWidget *w=x11Filter->first(); w; w=x11Filter->next()) {
01432 if (((KAppX11HackWidget*) w)->publicx11Event(_event))
01433 return true;
01434 }
01435 }
01436
01437 if ((_event->type == ClientMessage) &&
01438 (_event->xclient.message_type == kipcCommAtom))
01439 {
01440 XClientMessageEvent *cme = (XClientMessageEvent *) _event;
01441
01442 int id = cme->data.l[0];
01443 int arg = cme->data.l[1];
01444 if ((id < 32) && (kipcEventMask & (1 << id)))
01445 {
01446 switch (id)
01447 {
01448 case KIPC::StyleChanged:
01449 KGlobal::config()->reparseConfiguration();
01450 kdisplaySetStyle();
01451 break;
01452
01453 case KIPC::ToolbarStyleChanged:
01454 KGlobal::config()->reparseConfiguration();
01455 if (useStyles)
01456 emit toolbarAppearanceChanged(arg);
01457 break;
01458
01459 case KIPC::PaletteChanged:
01460 KGlobal::config()->reparseConfiguration();
01461 kdisplaySetPalette();
01462 break;
01463
01464 case KIPC::FontChanged:
01465 KGlobal::config()->reparseConfiguration();
01466 KGlobalSettings::rereadFontSettings();
01467 kdisplaySetFont();
01468 break;
01469
01470 case KIPC::BackgroundChanged:
01471 emit backgroundChanged(arg);
01472 break;
01473
01474 case KIPC::SettingsChanged:
01475 KGlobal::config()->reparseConfiguration();
01476 if (arg == SETTINGS_PATHS)
01477 KGlobalSettings::rereadPathSettings();
01478 else if (arg == SETTINGS_MOUSE)
01479 KGlobalSettings::rereadMouseSettings();
01480 propagateSettings((SettingsCategory)arg);
01481 break;
01482
01483 case KIPC::IconChanged:
01484 QPixmapCache::clear();
01485 KGlobal::config()->reparseConfiguration();
01486 KGlobal::instance()->newIconLoader();
01487 emit iconChanged(arg);
01488 break;
01489
01490 case KIPC::ClipboardConfigChanged:
01491 KClipboardSynchronizer::newConfiguration(arg);
01492 break;
01493 }
01494 }
01495 else if (id >= 32)
01496 {
01497 emit kipcMessage(id, arg);
01498 }
01499 return true;
01500 }
01501
01502 return false;
01503 }
01504 #endif
01505
01506 void KApplication::addKipcEventMask(int id)
01507 {
01508 if (id >= 32)
01509 {
01510 kdDebug(101) << "Cannot use KIPC event mask for message IDs >= 32\n";
01511 return;
01512 }
01513 kipcEventMask |= (1 << id);
01514 }
01515
01516 void KApplication::removeKipcEventMask(int id)
01517 {
01518 if (id >= 32)
01519 {
01520 kdDebug(101) << "Cannot use KIPC event mask for message IDs >= 32\n";
01521 return;
01522 }
01523 kipcEventMask &= ~(1 << id);
01524 }
01525
01526 void KApplication::enableStyles()
01527 {
01528 if (!useStyles)
01529 {
01530 useStyles = true;
01531 applyGUIStyle();
01532 }
01533 }
01534
01535 void KApplication::disableStyles()
01536 {
01537 useStyles = false;
01538 }
01539
01540 void KApplication::applyGUIStyle()
01541 {
01542 if ( !useStyles ) return;
01543
01544 KConfigGroup pConfig (KGlobal::config(), "General");
01545 QString defaultStyle = KStyle::defaultStyle();
01546 QString styleStr = pConfig.readEntry("widgetStyle", defaultStyle);
01547
01548 if (d->overrideStyle.isEmpty()) {
01549
01550
01551
01552 QStyle* sp = QStyleFactory::create( styleStr );
01553
01554
01555 if ( !sp && styleStr != defaultStyle)
01556 sp = QStyleFactory::create( defaultStyle );
01557 if ( !sp )
01558 sp = QStyleFactory::create( *(QStyleFactory::keys().begin()) );
01559 setStyle(sp);
01560 }
01561 else
01562 setStyle(d->overrideStyle);
01563
01564 kdisplaySetPalette();
01565 }
01566
01567 QString KApplication::caption() const
01568 {
01569
01570 if( !aCaption.isNull() )
01571 return aCaption;
01572 else
01573
01574 if ( KGlobal::instance()->aboutData() )
01575 return KGlobal::instance()->aboutData()->programName();
01576 else
01577
01578 return name();
01579 }
01580
01581
01582
01583
01584
01585
01586 QString KApplication::makeStdCaption( const QString &userCaption,
01587 bool withAppName, bool modified ) const
01588 {
01589 QString s = userCaption.isEmpty() ? caption() : userCaption;
01590
01591
01592 if (modified)
01593 s += QString::fromUtf8(" [") + i18n("modified") + QString::fromUtf8("]");
01594
01595 if ( !userCaption.isEmpty() ) {
01596
01597
01598 if ( withAppName && !caption().isNull() && !userCaption.endsWith(caption()) )
01599 s += QString::fromUtf8(" - ") + caption();
01600 }
01601
01602 return s;
01603 }
01604
01605 QPalette KApplication::createApplicationPalette()
01606 {
01607 KConfig *config = KGlobal::config();
01608 KConfigGroupSaver saver( config, "General" );
01609 return createApplicationPalette( config, KGlobalSettings::contrast() );
01610 }
01611
01612 QPalette KApplication::createApplicationPalette( KConfig *config, int contrast_ )
01613 {
01614 QColor kde31Background( 238, 238, 230 );
01615 QColor kde31Beige( 255,221,118 );
01616
01617 QColor kde31Button;
01618 if ( QPixmap::defaultDepth() > 8 )
01619 kde31Button.setRgb( 238, 234, 222 );
01620 else
01621 kde31Button.setRgb( 220, 220, 220 );
01622
01623 QColor kde31Link( 0, 0, 192 );
01624 QColor kde31VisitedLink( 128, 0,128 );
01625
01626 QColor background = config->readColorEntry( "background", &kde31Background );
01627 QColor foreground = config->readColorEntry( "foreground", &black );
01628 QColor button = config->readColorEntry( "buttonBackground", &kde31Button );
01629 QColor buttonText = config->readColorEntry( "buttonForeground", &foreground );
01630 QColor highlight = config->readColorEntry( "selectBackground", &kde31Beige );
01631 QColor highlightedText = config->readColorEntry( "selectForeground", &black );
01632 QColor base = config->readColorEntry( "windowBackground", &white );
01633 QColor baseText = config->readColorEntry( "windowForeground", &black );
01634 QColor link = config->readColorEntry( "linkColor", &kde31Link );
01635 QColor visitedLink = config->readColorEntry( "visitedLinkColor", &kde31VisitedLink );
01636
01637 int highlightVal, lowlightVal;
01638 highlightVal = 100 + (2*contrast_+4)*16/10;
01639 lowlightVal = 100 + (2*contrast_+4)*10;
01640
01641 QColor disfg = foreground;
01642
01643 int h, s, v;
01644 disfg.hsv( &h, &s, &v );
01645 if (v > 128)
01646
01647 disfg = disfg.dark(lowlightVal);
01648 else if (disfg != black)
01649
01650 disfg = disfg.light(highlightVal);
01651 else
01652
01653 disfg = Qt::darkGray;
01654
01655
01656 QColorGroup disabledgrp(disfg, background,
01657 background.light(highlightVal),
01658 background.dark(lowlightVal),
01659 background.dark(120),
01660 background.dark(120), base);
01661
01662 QColorGroup colgrp(foreground, background, background.light(highlightVal),
01663 background.dark(lowlightVal),
01664 background.dark(120),
01665 baseText, base);
01666
01667 int inlowlightVal = lowlightVal-25;
01668 if(inlowlightVal < 120)
01669 inlowlightVal = 120;
01670
01671 colgrp.setColor(QColorGroup::Highlight, highlight);
01672 colgrp.setColor(QColorGroup::HighlightedText, highlightedText);
01673 colgrp.setColor(QColorGroup::Button, button);
01674 colgrp.setColor(QColorGroup::ButtonText, buttonText);
01675 colgrp.setColor(QColorGroup::Midlight, background.light(110));
01676 colgrp.setColor(QColorGroup::Link, link);
01677 colgrp.setColor(QColorGroup::LinkVisited, visitedLink);
01678
01679 disabledgrp.setColor(QColorGroup::Button, button);
01680
01681 QColor disbtntext = buttonText;
01682 disbtntext.hsv( &h, &s, &v );
01683 if (v > 128)
01684
01685 disbtntext = disbtntext.dark(lowlightVal);
01686 else if (disbtntext != black)
01687
01688 disbtntext = disbtntext.light(highlightVal);
01689 else
01690
01691 disbtntext = Qt::darkGray;
01692
01693 disabledgrp.setColor(QColorGroup::ButtonText, disbtntext);
01694 disabledgrp.setColor(QColorGroup::Midlight, background.light(110));
01695 disabledgrp.setColor(QColorGroup::Link, link);
01696 disabledgrp.setColor(QColorGroup::LinkVisited, visitedLink);
01697
01698 return QPalette(colgrp, disabledgrp, colgrp);
01699 }
01700
01701
01702 void KApplication::kdisplaySetPalette()
01703 {
01704 QApplication::setPalette( createApplicationPalette(), true);
01705 emit kdisplayPaletteChanged();
01706 emit appearanceChanged();
01707 }
01708
01709
01710 void KApplication::kdisplaySetFont()
01711 {
01712 QApplication::setFont(KGlobalSettings::generalFont(), true);
01713 QApplication::setFont(KGlobalSettings::menuFont(), true, "QMenuBar");
01714 QApplication::setFont(KGlobalSettings::menuFont(), true, "QPopupMenu");
01715 QApplication::setFont(KGlobalSettings::menuFont(), true, "KPopupTitle");
01716
01717
01718 QStyleSheet* sheet = QStyleSheet::defaultSheet();
01719 sheet->item ("pre")->setFontFamily (KGlobalSettings::fixedFont().family());
01720 sheet->item ("code")->setFontFamily (KGlobalSettings::fixedFont().family());
01721 sheet->item ("tt")->setFontFamily (KGlobalSettings::fixedFont().family());
01722
01723 emit kdisplayFontChanged();
01724 emit appearanceChanged();
01725 }
01726
01727
01728 void KApplication::kdisplaySetStyle()
01729 {
01730 if (useStyles)
01731 {
01732 applyGUIStyle();
01733 emit kdisplayStyleChanged();
01734 emit appearanceChanged();
01735 }
01736 }
01737
01738
01739 void KApplication::propagateSettings(SettingsCategory arg)
01740 {
01741 KConfigBase* config = KGlobal::config();
01742 KConfigGroupSaver saver( config, "KDE" );
01743
01744 int num = config->readNumEntry("CursorBlinkRate", QApplication::cursorFlashTime());
01745 if (num < 200)
01746 num = 200;
01747 if (num > 2000)
01748 num = 2000;
01749 QApplication::setCursorFlashTime(num);
01750 num = config->readNumEntry("DoubleClickInterval", QApplication::doubleClickInterval());
01751 QApplication::setDoubleClickInterval(num);
01752 num = config->readNumEntry("StartDragTime", QApplication::startDragTime());
01753 QApplication::setStartDragTime(num);
01754 num = config->readNumEntry("StartDragDist", QApplication::startDragDistance());
01755 QApplication::setStartDragDistance(num);
01756 num = config->readNumEntry("WheelScrollLines", QApplication::wheelScrollLines());
01757 QApplication::setWheelScrollLines(num);
01758
01759 bool b = config->readBoolEntry("EffectAnimateMenu", false);
01760 QApplication::setEffectEnabled( Qt::UI_AnimateMenu, b);
01761 b = config->readBoolEntry("EffectFadeMenu", false);
01762 QApplication::setEffectEnabled( Qt::UI_FadeMenu, b);
01763 b = config->readBoolEntry("EffectAnimateCombo", false);
01764 QApplication::setEffectEnabled( Qt::UI_AnimateCombo, b);
01765 b = config->readBoolEntry("EffectAnimateTooltip", false);
01766 QApplication::setEffectEnabled( Qt::UI_AnimateTooltip, b);
01767 b = config->readBoolEntry("EffectFadeTooltip", false);
01768 QApplication::setEffectEnabled( Qt::UI_FadeTooltip, b);
01769 b = !config->readBoolEntry("EffectNoTooltip", false);
01770 QToolTip::setGloballyEnabled( b );
01771
01772 emit settingsChanged(arg);
01773 }
01774
01775 void KApplication::installKDEPropertyMap()
01776 {
01777 #ifndef QT_NO_SQL
01778
01779 QSqlPropertyMap *kdeMap = new QSqlPropertyMap;
01780 kdeMap->insert( "KComboBox", "currentItem" );
01781 kdeMap->insert( "KDatePicker", "getDate" );
01782 kdeMap->insert( "KEditListBox", "currentItem" );
01783 kdeMap->insert( "KFontCombo", "currentFont" );
01784 kdeMap->insert( "KHistoryCombo", "currentItem" );
01785 kdeMap->insert( "KListBox", "currentItem" );
01786 kdeMap->insert( "KLineEdit", "text" );
01787 kdeMap->insert( "KPasswordEdit", "text" );
01788 kdeMap->insert( "KRestrictedLine", "text" );
01789 kdeMap->insert( "KSqueezedTextLabel", "text" );
01790 kdeMap->insert( "KTextBrowser", "source" );
01791 kdeMap->insert( "KURLRequester", "url" );
01792 QSqlPropertyMap::installDefaultMap( kdeMap );
01793 #endif
01794 }
01795
01796 void KApplication::invokeHelp( const QString& anchor,
01797 const QString& _appname) const
01798 {
01799 QString url;
01800 QString appname;
01801 if (_appname.isEmpty())
01802 appname = name();
01803 else
01804 appname = _appname;
01805
01806 if (!anchor.isEmpty())
01807 url = QString("help:/%1?anchor=%2").arg(appname).arg(anchor);
01808 else
01809 url = QString("help:/%1/index.html").arg(appname);
01810
01811 QString error;
01812
01813 if (startServiceByDesktopName("khelpcenter", url, &error, 0, 0, "", true))
01814 {
01815 kdWarning() << "Could not launch help:\n" << error << endl;
01816 return;
01817 }
01818 }
01819
01820 void KApplication::invokeHTMLHelp( const QString& _filename, const QString& topic ) const
01821 {
01822 kdWarning() << "invoking HTML help is deprecated! use docbook and invokeHelp!\n";
01823
01824 QString filename;
01825
01826 if( _filename.isEmpty() )
01827 filename = QString(name()) + "/index.html";
01828 else
01829 filename = _filename;
01830
01831 QString url;
01832 if (!topic.isEmpty())
01833 url = QString("help:/%1#%2").arg(filename).arg(topic);
01834 else
01835 url = QString("help:/%1").arg(filename);
01836
01837 QString error;
01838
01839 if (startServiceByDesktopName("khelpcenter", url, &error, 0, 0, "", true))
01840 {
01841 kdWarning() << "Could not launch help:\n" << error << endl;
01842 return;
01843 }
01844 }
01845
01846
01847 void KApplication::invokeMailer(const QString &address, const QString &subject)
01848 {
01849 invokeMailer(address, QString::null, QString::null, subject, QString::null, QString::null, QStringList());
01850 }
01851
01852 void KApplication::invokeMailer(const KURL &mailtoURL)
01853 {
01854 QString address = KURL::decode_string(mailtoURL.path()), subject, cc, bcc, body, attach;
01855 QStringList queries = QStringList::split('&', mailtoURL.query().mid(1));
01856 for (QStringList::Iterator it = queries.begin(); it != queries.end(); ++it)
01857 {
01858 QString q = (*it).lower();
01859 if (q.startsWith("subject="))
01860 subject = KURL::decode_string((*it).mid(8));
01861 else
01862 if (q.startsWith("cc="))
01863 cc = KURL::decode_string((*it).mid(3));
01864 else
01865 if (q.startsWith("bcc="))
01866 bcc = KURL::decode_string((*it).mid(4));
01867 else
01868 if (q.startsWith("body="))
01869 body = KURL::decode_string((*it).mid(5));
01870
01871
01872
01873 }
01874
01875 invokeMailer( address, cc, bcc, subject, body, QString::null, QStringList() );
01876 }
01877
01878 void KApplication::invokeMailer(const QString &to, const QString &cc, const QString &bcc,
01879 const QString &subject, const QString &body,
01880 const QString & , const QStringList &attachURLs)
01881 {
01882 KConfig config("emaildefaults");
01883 config.setGroup( QString::fromLatin1("PROFILE_Default") );
01884 QString command = config.readEntry("EmailClient");
01885
01886 if (command.isEmpty() || command == QString::fromLatin1("kmail")
01887 || command.right(6) == "/kmail")
01888 command = QString::fromLatin1("kmail --composer -s %s -c %c -b %b --body %B --attach %A %t");
01889
01890
01891
01892
01893
01894
01895 if (config.readBoolEntry("TerminalClient", false))
01896 command = "konsole -e " + command;
01897
01898
01899
01900
01901
01902 QStringList cmdTokens = QStringList::split(' ', command.simplifyWhiteSpace());
01903 QString cmd = cmdTokens[0];
01904 cmdTokens.remove(cmdTokens.begin());
01905 QString lastToken;
01906 QStringList newTokens;
01907
01908 for (QStringList::Iterator it = cmdTokens.begin(); it != cmdTokens.end(); ++it)
01909 {
01910 if ((*it).find("%t") >= 0)
01911 (*it).replace(QRegExp("%t"), to);
01912 else
01913 if ((*it).find("%s") >= 0)
01914 (*it).replace(QRegExp("%s"), subject);
01915 else
01916 if ((*it).find("%c") >= 0)
01917 (*it).replace(QRegExp("%c"), cc);
01918 else
01919 if ((*it).find("%b") >= 0)
01920 (*it).replace(QRegExp("%b"), bcc);
01921 else
01922 if ((*it).find("%B") >= 0)
01923 (*it).replace(QRegExp("%B"), body);
01924 else
01925 if ((*it).find("%A") >= 0)
01926 {
01927 QStringList::ConstIterator urlit = attachURLs.begin();
01928 QStringList::ConstIterator urlend = attachURLs.end();
01929 if ( urlit != urlend )
01930 {
01931 (*it).replace(QRegExp("%A"), (*urlit));
01932 ++urlit;
01933 QStringList::Iterator nextit = it; nextit++;
01934 for ( ; urlit != urlend ; ++urlit )
01935 {
01936 it = cmdTokens.insert( nextit, lastToken );
01937 it = cmdTokens.insert( nextit, (*urlit) );
01938 }
01939 } else
01940 (*it).replace(QRegExp("%A"), QString::null);
01941 }
01942 lastToken = (*it);
01943 }
01944 QString error;
01945
01946 if (kdeinitExec(cmd, cmdTokens, &error))
01947 {
01948 kdWarning() << "Could not launch mail client:\n" << error << endl;
01949 }
01950 }
01951
01952
01953 void KApplication::invokeBrowser( const QString &url )
01954 {
01955 QString error;
01956
01957 if (startServiceByDesktopName("kfmclient", url, &error, 0, 0, "", true))
01958 {
01959 kdWarning() << "Could not launch browser:\n" << error << endl;
01960 return;
01961 }
01962 }
01963
01964 QCString
01965 KApplication::launcher()
01966 {
01967 return "klauncher";
01968 }
01969
01970 static int
01971 startServiceInternal( const QCString &function,
01972 const QString& _name, const QStringList &URLs,
01973 QString *error, QCString *dcopService, int *pid, const QCString& startup_id, bool noWait )
01974 {
01975 struct serviceResult
01976 {
01977 int result;
01978 QCString dcopName;
01979 QString error;
01980 pid_t pid;
01981 };
01982
01983
01984 DCOPClient *dcopClient;
01985 if (kapp)
01986 dcopClient = kapp->dcopClient();
01987 else
01988 dcopClient = new DCOPClient;
01989
01990 if (!dcopClient->isAttached())
01991 {
01992 if (!dcopClient->attach())
01993 {
01994 if (error)
01995 *error = i18n("Could not register with DCOP.\n");
01996 return -1;
01997 }
01998 }
01999 QByteArray params;
02000 QDataStream stream(params, IO_WriteOnly);
02001 stream << _name << URLs;
02002 QCString replyType;
02003 QByteArray replyData;
02004 QCString _launcher = KApplication::launcher();
02005 QValueList<QCString> envs;
02006 #ifdef Q_WS_X11
02007 if (qt_xdisplay()) {
02008 QCString dpystring(XDisplayString(qt_xdisplay()));
02009 envs.append( QCString("DISPLAY=") + dpystring );
02010 }
02011 #endif
02012 stream << envs;
02013 if( !startup_id.isNull())
02014 stream << startup_id << noWait;
02015
02016 if (!dcopClient->call(_launcher, _launcher,
02017 function, params, replyType, replyData))
02018 {
02019 if (error)
02020 *error = i18n("KLauncher could not be reached via DCOP.\n");
02021 if (!kapp)
02022 delete dcopClient;
02023 return -1;
02024 }
02025 if (!kapp)
02026 delete dcopClient;
02027
02028 if (noWait)
02029 return 0;
02030
02031 QDataStream stream2(replyData, IO_ReadOnly);
02032 serviceResult result;
02033 stream2 >> result.result >> result.dcopName >> result.error >> result.pid;
02034 if (dcopService)
02035 *dcopService = result.dcopName;
02036 if (error)
02037 *error = result.error;
02038 if (pid)
02039 *pid = result.pid;
02040 return result.result;
02041 }
02042
02043 int
02044 KApplication::startServiceByName( const QString& _name, const QString &URL,
02045 QString *error, QCString *dcopService, int *pid, const QCString& startup_id, bool noWait )
02046 {
02047 QStringList URLs;
02048 if (!URL.isEmpty())
02049 URLs.append(URL);
02050 return startServiceInternal(
02051 "start_service_by_name(QString,QStringList,QValueList<QCString>,QCString,bool)",
02052 _name, URLs, error, dcopService, pid, startup_id, noWait);
02053 }
02054
02055 int
02056 KApplication::startServiceByName( const QString& _name, const QStringList &URLs,
02057 QString *error, QCString *dcopService, int *pid, const QCString& startup_id, bool noWait )
02058 {
02059 return startServiceInternal(
02060 "start_service_by_name(QString,QStringList,QValueList<QCString>,QCString,bool)",
02061 _name, URLs, error, dcopService, pid, startup_id, noWait);
02062 }
02063
02064 int
02065 KApplication::startServiceByDesktopPath( const QString& _name, const QString &URL,
02066 QString *error, QCString *dcopService, int *pid, const QCString& startup_id, bool noWait )
02067 {
02068 QStringList URLs;
02069 if (!URL.isEmpty())
02070 URLs.append(URL);
02071 return startServiceInternal(
02072 "start_service_by_desktop_path(QString,QStringList,QValueList<QCString>,QCString,bool)",
02073 _name, URLs, error, dcopService, pid, startup_id, noWait);
02074 }
02075
02076 int
02077 KApplication::startServiceByDesktopPath( const QString& _name, const QStringList &URLs,
02078 QString *error, QCString *dcopService, int *pid, const QCString& startup_id, bool noWait )
02079 {
02080 return startServiceInternal(
02081 "start_service_by_desktop_path(QString,QStringList,QValueList<QCString>,QCString,bool)",
02082 _name, URLs, error, dcopService, pid, startup_id, noWait);
02083 }
02084
02085 int
02086 KApplication::startServiceByDesktopName( const QString& _name, const QString &URL,
02087 QString *error, QCString *dcopService, int *pid, const QCString& startup_id, bool noWait )
02088 {
02089 QStringList URLs;
02090 if (!URL.isEmpty())
02091 URLs.append(URL);
02092 return startServiceInternal(
02093 "start_service_by_desktop_name(QString,QStringList,QValueList<QCString>,QCString,bool)",
02094 _name, URLs, error, dcopService, pid, startup_id, noWait);
02095 }
02096
02097 int
02098 KApplication::startServiceByDesktopName( const QString& _name, const QStringList &URLs,
02099 QString *error, QCString *dcopService, int *pid, const QCString& startup_id, bool noWait )
02100 {
02101 return startServiceInternal(
02102 "start_service_by_desktop_name(QString,QStringList,QValueList<QCString>,QCString,bool)",
02103 _name, URLs, error, dcopService, pid, startup_id, noWait);
02104 }
02105
02106 int
02107 KApplication::kdeinitExec( const QString& name, const QStringList &args,
02108 QString *error, int *pid )
02109 {
02110 return startServiceInternal("kdeinit_exec(QString,QStringList,QValueList<QCString>)",
02111 name, args, error, 0, pid, QCString(), false);
02112 }
02113
02114 int
02115 KApplication::kdeinitExecWait( const QString& name, const QStringList &args,
02116 QString *error, int *pid )
02117 {
02118 return startServiceInternal("kdeinit_exec_wait(QString,QStringList,QValueList<QCString>)",
02119 name, args, error, 0, pid, QCString(), false);
02120 }
02121
02122 QString KApplication::tempSaveName( const QString& pFilename ) const
02123 {
02124 QString aFilename;
02125
02126 if( pFilename[0] != '/' )
02127 {
02128 kdWarning(101) << "Relative filename passed to KApplication::tempSaveName" << endl;
02129 aFilename = QFileInfo( QDir( "." ), pFilename ).absFilePath();
02130 }
02131 else
02132 aFilename = pFilename;
02133
02134 QDir aAutosaveDir( QDir::homeDirPath() + "/autosave/" );
02135 if( !aAutosaveDir.exists() )
02136 {
02137 if( !aAutosaveDir.mkdir( aAutosaveDir.absPath() ) )
02138 {
02139
02140 aAutosaveDir.setPath( KGlobal::dirs()->saveLocation("tmp") );
02141 }
02142 }
02143
02144 aFilename.replace( QRegExp( "/" ),"\\!" ).prepend( "#" ).append( "#" ).prepend( "/" ).prepend( aAutosaveDir.absPath() );
02145
02146 return aFilename;
02147 }
02148
02149
02150 QString KApplication::checkRecoverFile( const QString& pFilename,
02151 bool& bRecover ) const
02152 {
02153 QString aFilename;
02154
02155 if( pFilename[0] != '/' )
02156 {
02157 kdWarning(101) << "Relative filename passed to KApplication::tempSaveName" << endl;
02158 aFilename = QFileInfo( QDir( "." ), pFilename ).absFilePath();
02159 }
02160 else
02161 aFilename = pFilename;
02162
02163 QDir aAutosaveDir( QDir::homeDirPath() + "/autosave/" );
02164 if( !aAutosaveDir.exists() )
02165 {
02166 if( !aAutosaveDir.mkdir( aAutosaveDir.absPath() ) )
02167 {
02168
02169 aAutosaveDir.setPath( KGlobal::dirs()->saveLocation("tmp") );
02170 }
02171 }
02172
02173 aFilename.replace( QRegExp( "/" ), "\\!" ).prepend( "#" ).append( "#" ).prepend( "/" ).prepend( aAutosaveDir.absPath() );
02174
02175 if( QFile( aFilename ).exists() )
02176 {
02177 bRecover = true;
02178 return aFilename;
02179 }
02180 else
02181 {
02182 bRecover = false;
02183 return pFilename;
02184 }
02185 }
02186
02187
02188 bool checkAccess(const QString& pathname, int mode)
02189 {
02190 int accessOK = access( QFile::encodeName(pathname), mode );
02191 if ( accessOK == 0 )
02192 return true;
02193
02194
02195
02196
02197 if ( (mode & W_OK) == 0 )
02198 return false;
02199
02200
02201 if (!access( QFile::encodeName(pathname), F_OK))
02202 return false;
02203
02204
02205 QString dirName(pathname);
02206 int pos = dirName.findRev('/');
02207 if ( pos == -1 )
02208 return false;
02209 else if ( pos == 0 )
02210 pos = 1;
02211
02212 dirName.truncate(pos);
02213
02214 accessOK = access( QFile::encodeName(dirName), W_OK );
02215
02216 if ( accessOK == 0 )
02217 return true;
02218 else
02219 return false;
02220 }
02221
02222 void KApplication::setTopWidget( QWidget *topWidget )
02223 {
02224 if( topWidget != 0 )
02225 {
02226 #ifdef Q_WS_X11 // FIXME(E): Implement for Qt/Embedded
02227 Window leader = topWidget->winId();
02228 char* argv = const_cast< char* >( KCmdLineArgs::appName());
02229 XSetCommand(display, leader, &argv, 1);
02230
02231 XWMHints *hints = XGetWMHints(display, topWidget->winId());
02232 if (hints)
02233 {
02234 if (!(hints->flags & WindowGroupHint))
02235 {
02236 hints->window_group = leader;
02237 hints->flags |= WindowGroupHint;
02238 }
02239 if (!(hints->flags & InputHint))
02240 {
02241 hints->input = True;
02242 hints->flags |= InputHint;
02243 }
02244 XSetWMHints(display, topWidget->winId(), hints);
02245 XFree(reinterpret_cast<char *>(hints));
02246 }
02247
02248 #endif
02249
02250 if ( !topWidget->inherits("KMainWindow") ) {
02251 topWidget->setCaption( caption() );
02252 #ifndef Q_WS_QWS // FIXME(E): Implement for Qt/Embedded
02253 NETWinInfo info(qt_xdisplay(), topWidget->winId(), qt_xrootwin(), NET::WMName );
02254 info.setName( caption().utf8().data() );
02255 #endif
02256 }
02257
02258
02259 topWidget->setIcon( icon() );
02260 #ifdef Q_WS_X11 // FIXME(E): Implement for Qt/Embedded
02261 KWin::setIcons(topWidget->winId(), icon(), miniIcon() );
02262
02263
02264 XSetIconName( qt_xdisplay(), topWidget->winId(), caption().utf8() );
02265
02266
02267 KStartupInfo::setWindowStartupId( topWidget->winId(), startupId());
02268 #endif
02269 }
02270 }
02271
02272 QCString KApplication::startupId() const
02273 {
02274 return d->startup_id;
02275 }
02276
02277 void KApplication::setStartupId( const QCString& startup_id )
02278 {
02279 if( startup_id.isEmpty())
02280 d->startup_id = "0";
02281 else
02282 d->startup_id = startup_id;
02283 }
02284
02285
02286
02287 void KApplication::read_app_startup_id()
02288 {
02289 #ifdef Q_WS_X11
02290 KStartupInfoId id = KStartupInfo::currentStartupIdEnv();
02291 KStartupInfo::resetStartupEnv();
02292 d->startup_id = id.id();
02293 #endif
02294 }
02295
02296 int KApplication::random()
02297 {
02298 static int init = false;
02299 if (!init)
02300 {
02301 unsigned int seed;
02302 init = true;
02303 int fd = open("/dev/urandom", O_RDONLY);
02304 if (fd <= 0 || ::read(fd, &seed, sizeof(seed)) != sizeof(seed))
02305 {
02306
02307 srand(getpid());
02308 seed = rand()+time(0);
02309 }
02310 if (fd >= 0) close(fd);
02311 srand(seed);
02312 }
02313 return rand();
02314 }
02315
02316 QString KApplication::randomString(int length)
02317 {
02318 if (length <=0 ) return QString::null;
02319
02320 QString str;
02321 while (--length)
02322 {
02323 int r=random() % 62;
02324 r+=48;
02325 if (r>57) r+=7;
02326 if (r>90) r+=6;
02327 str += char(r);
02328
02329 }
02330 return str;
02331 }
02332
02333 bool KApplication::authorize(const QString &genericAction)
02334 {
02335 if (!d->actionRestrictions)
02336 return true;
02337
02338 KConfig *config = KGlobal::config();
02339 KConfigGroupSaver saver( config, "KDE Action Restrictions" );
02340 return config->readBoolEntry(genericAction, true);
02341 }
02342
02343 bool KApplication::authorizeKAction(const char *action)
02344 {
02345 if (!d->actionRestrictions || !action)
02346 return true;
02347
02348 static const QString &action_prefix = KGlobal::staticQString( "action/" );
02349
02350 return authorize(action_prefix + action);
02351 }
02352
02353 void KApplication::initUrlActionRestrictions()
02354 {
02355 d->urlActionRestrictions.setAutoDelete(true);
02356 d->urlActionRestrictions.clear();
02357 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02358 ("open", QString::null, QString::null, QString::null, QString::null, QString::null, QString::null, true));
02359 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02360 ("list", QString::null, QString::null, QString::null, QString::null, QString::null, QString::null, true));
02361
02362
02363
02364
02365
02366 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02367 ("link", QString::null, QString::null, QString::null, "http", QString::null, QString::null, true));
02368 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02369 ("link", QString::null, QString::null, QString::null, "ftp", QString::null, QString::null, true));
02370 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02371 ("link", QString::null, QString::null, QString::null, "news", QString::null, QString::null, true));
02372 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02373 ("link", QString::null, QString::null, QString::null, "mailto", QString::null, QString::null, true));
02374 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02375 ("redirect", QString::null, QString::null, QString::null, "http", QString::null, QString::null, true));
02376 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02377 ("redirect", QString::null, QString::null, QString::null, "ftp", QString::null, QString::null, true));
02378 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02379 ("redirect", QString::null, QString::null, QString::null, "mailto", QString::null, QString::null, true));
02380
02381
02382
02383 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02384 ("redirect", QString::null, QString::null, QString::null, "file", QString::null, QString::null, true));
02385 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02386 ("redirect", "http", QString::null, QString::null, "file", QString::null, QString::null, false));
02387 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02388 ("redirect", "ftp", QString::null, QString::null, "file", QString::null, QString::null, false));
02389 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02390 ("redirect", "webdav", QString::null, QString::null, "file", QString::null, QString::null, false));
02391
02392 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02393 ("redirect", QString::null, QString::null, QString::null, "about", QString::null, QString::null, true));
02394 d->urlActionRestrictions.append( new KApplicationPrivate::URLActionRule
02395 ("redirect", QString::null, QString::null, QString::null, "=", QString::null, QString::null, true));
02396
02397 KConfig *config = KGlobal::config();
02398 KConfigGroupSaver saver( config, "KDE URL Restrictions" );
02399 int count = config->readNumEntry("rule_count");
02400 QString keyFormat = QString("rule_%1");
02401 for(int i = 1; i <= count; i++)
02402 {
02403 QString key = keyFormat.arg(i);
02404 QStringList rule = config->readListEntry(key);
02405 if (rule.count() != 8)
02406 continue;
02407 QString action = rule[0];
02408 QString refProt = rule[1];
02409 QString refHost = rule[2];
02410 QString refPath = rule[3];
02411 QString urlProt = rule[4];
02412 QString urlHost = rule[5];
02413 QString urlPath = rule[6];
02414 QString strEnabled = rule[7].lower();
02415
02416 bool bEnabled = (strEnabled == "true");
02417
02418 if (refPath.startsWith("$HOME"))
02419 refPath.replace(0, 5, QDir::homeDirPath());
02420 else if (refPath.startsWith("~"))
02421 refPath.replace(0, 1, QDir::homeDirPath());
02422 if (urlPath.startsWith("$HOME"))
02423 urlPath.replace(0, 5, QDir::homeDirPath());
02424 else if (urlPath.startsWith("~"))
02425 urlPath.replace(0, 1, QDir::homeDirPath());
02426
02427 d->urlActionRestrictions.append(new KApplicationPrivate::URLActionRule
02428 ( action, refProt, refHost, refPath, urlProt, urlHost, urlPath, bEnabled));
02429 }
02430 }
02431
02432 bool KApplication::authorizeURLAction(const QString &action, const KURL &baseURL, const KURL &destURL)
02433 {
02434 bool result = false;
02435 if (d->urlActionRestrictions.isEmpty())
02436 initUrlActionRestrictions();
02437 for(KApplicationPrivate::URLActionRule *rule = d->urlActionRestrictions.first();
02438 rule; rule = d->urlActionRestrictions.next())
02439 {
02440 if ((result != rule->permission) &&
02441 (action == rule->action) &&
02442 rule->baseMatch(baseURL) &&
02443 rule->destMatch(destURL, baseURL))
02444 {
02445 result = rule->permission;
02446 }
02447 }
02448 return result;
02449 }
02450
02451
02452 uint KApplication::keyboardModifiers()
02453 {
02454 Window root;
02455 Window child;
02456 int root_x, root_y, win_x, win_y;
02457 uint keybstate;
02458 XQueryPointer( qt_xdisplay(), qt_xrootwin(), &root, &child,
02459 &root_x, &root_y, &win_x, &win_y, &keybstate );
02460 return keybstate & 0x00ff;
02461 }
02462
02463 uint KApplication::mouseState()
02464 {
02465 Window root;
02466 Window child;
02467 int root_x, root_y, win_x, win_y;
02468 uint keybstate;
02469 XQueryPointer( qt_xdisplay(), qt_xrootwin(), &root, &child,
02470 &root_x, &root_y, &win_x, &win_y, &keybstate );
02471 return keybstate & 0xff00;
02472 }
02473
02474 void KApplication::virtual_hook( int id, void* data )
02475 { KInstance::virtual_hook( id, data ); }
02476
02477 void KSessionManaged::virtual_hook( int, void* )
02478 { }
02479
02480 #include "kapplication.moc"
02481 #define KeyPress XKeyPress