/* This file is part of KDE Kontact. Copyright (c) 2001 Matthias Hoelzer-Kluepfel Copyright (c) 2002-2005 Daniel Molkentin Copyright (c) 2003-2005 Cornelius Schumacher This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include #include "aboutdialog.h" #include "iconsidepane.h" #include "mainwindow.h" #include "plugin.h" #include "prefs.h" #include "profiledialog.h" #include "profilemanager.h" #include "progressdialog.h" #include "statusbarprogresswidget.h" #include "broadcaststatus.h" using namespace Kontact; class SettingsDialogWrapper : public KSettings::Dialog { public: SettingsDialogWrapper( ContentInListView content, TQWidget * parent = 0 ) : KSettings::Dialog( content, parent, 0 ) { } void fixButtonLabel( TQWidget *widget ) { TQObject *object = widget->child( "KJanusWidget::buttonBelowList" ); TQPushButton *button = static_cast( TQT_TQWIDGET(object) ); if ( button ) button->setText( i18n( "Select Components ..." ) ); } }; MainWindow::MainWindow() : Kontact::Core(), mTopWidget( 0 ), mSplitter( 0 ), mCurrentPlugin( 0 ), mAboutDialog( 0 ), mReallyClose( false ), mSyncActionsEnabled( true ) { // Set this to be the group leader for all subdialogs - this means // modal subdialogs will only affect this dialog, not the other windows setWFlags( getWFlags() | WGroupLeader ); initGUI(); initObject(); } void MainWindow::initGUI() { initWidgets(); setupActions(); setHelpMenuEnabled( false ); KHelpMenu *helpMenu = new KHelpMenu( this, 0, true, actionCollection() ); connect( helpMenu, TQT_SIGNAL( showAboutApplication() ), TQT_SLOT( showAboutDialog() ) ); KTrader::OfferList offers = KTrader::self()->query( TQString::tqfromLatin1( "Kontact/Plugin" ), TQString( "[X-KDE-KontactPluginVersion] == %1" ).tqarg( KONTACT_PLUGIN_VERSION ) ); mPluginInfos = KPluginInfo::fromServices( offers, Prefs::self()->config(), "Plugins" ); KPluginInfo::List::Iterator it; for ( it = mPluginInfos.begin(); it != mPluginInfos.end(); ++it ) { (*it)->load(); KAction *action = new KAction( (*it)->name(), (*it)->icon(), KShortcut(), TQT_TQOBJECT(this), TQT_SLOT(slotActionTriggered()), actionCollection(), (*it)->pluginName().latin1() ); action->setName( (*it)->pluginName().latin1() ); action->setWhatsThis( i18n( "Switch to plugin %1" ).tqarg( (*it)->name() ) ); TQVariant hasPartProp = (*it)->property( "X-KDE-KontactPluginHasPart" ); if ( !hasPartProp.isValid() || hasPartProp.toBool() ) { mActionPlugins.append( action ); } } KStdAction::keyBindings( TQT_TQOBJECT(this), TQT_SLOT( configureShortcuts() ), actionCollection() ); KStdAction::configureToolbars( TQT_TQOBJECT(this), TQT_SLOT( configureToolbars() ), actionCollection() ); setXMLFile( "kontactui.rc" ); setStandardToolBarMenuEnabled( true ); createGUI( 0 ); loadPlugins(); resize( 700, 520 ); // initial size to prevent a scrollbar in sidepane setAutoSaveSettings(); connect( Kontact::ProfileManager::self(), TQT_SIGNAL( profileLoaded( const TQString& ) ), this, TQT_SLOT( slotLoadProfile( const TQString& ) ) ); connect( Kontact::ProfileManager::self(), TQT_SIGNAL( saveToProfileRequested( const TQString& ) ), this, TQT_SLOT( slotSaveToProfile( const TQString& ) ) ); } void MainWindow::initObject() { // prepare the part manager mPartManager = new KParts::PartManager( this ); connect( mPartManager, TQT_SIGNAL( activePartChanged( KParts::Part* ) ), this, TQT_SLOT( slotActivePartChanged( KParts::Part* ) ) ); if ( mSidePane ) { mSidePane->updatePlugins(); } KSettings::Dispatcher::self()->registerInstance( instance(), TQT_TQOBJECT(this), TQT_SLOT( updateConfig() ) ); loadSettings(); statusBar()->show(); showTip( false ); // done initializing slotShowStatusMsg( TQString() ); connect( KPIM::BroadcastStatus::instance(), TQT_SIGNAL( statusMsg( const TQString& ) ), this, TQT_SLOT( slotShowStatusMsg( const TQString& ) ) ); // launch commandline specified module if any activatePluginModule(); if ( Prefs::lastVersionSeen() == kapp->aboutData()->version() ) { selectPlugin( mCurrentPlugin ); } paintAboutScreen( introductionString() ); Prefs::setLastVersionSeen( kapp->aboutData()->version() ); } MainWindow::~MainWindow() { saveSettings(); TQPtrList parts = *mPartManager->parts(); for ( KParts::Part *p = parts.last(); p; p = parts.prev() ) { delete p; p = 0; } Prefs::self()->writeConfig(); } void MainWindow::setActivePluginModule( const TQString &module ) { mActiveModule = module; activatePluginModule(); } void MainWindow::activatePluginModule() { if ( !mActiveModule.isEmpty() ) { PluginList::ConstIterator end = mPlugins.end(); for ( PluginList::ConstIterator it = mPlugins.begin(); it != end; ++it ) if ( ( *it )->identifier().contains( mActiveModule ) ) { selectPlugin( *it ); return; } } } void MainWindow::initWidgets() { // includes sidebar and part stack mTopWidget = new TQHBox( this ); mTopWidget->setFrameStyle( TQFrame::Panel | TQFrame::Sunken ); setCentralWidget( mTopWidget ); TQHBox *mBox = 0; mSplitter = new TQSplitter( mTopWidget ); mBox = new TQHBox( mTopWidget ); mSidePane = new IconSidePane( this, mSplitter ); mSidePane->tqsetSizePolicy( TQSizePolicy( TQSizePolicy::Maximum, TQSizePolicy::Preferred ) ); // donÄt occupy screen estate on load TQValueList sizes; sizes << 0; mSplitter->setSizes(sizes); connect( mSidePane, TQT_SIGNAL( pluginSelected( Kontact::Plugin * ) ), TQT_SLOT( selectPlugin( Kontact::Plugin * ) ) ); TQVBox *vBox; if ( mSplitter ) { vBox = new TQVBox( mSplitter ); } else { vBox = new TQVBox( mBox ); } vBox->setSpacing( 0 ); mPartsStack = new TQWidgetStack( vBox ); initAboutScreen(); TQString loading = i18n( "

%1

" ) .tqarg( i18n("Loading Kontact...") ); paintAboutScreen( loading ); /* Create a progress dialog and hide it. */ KPIM::ProgressDialog *progressDialog = new KPIM::ProgressDialog( statusBar(), this ); progressDialog->hide(); mLittleProgress = new KPIM::StatusbarProgressWidget( progressDialog, statusBar() ); mStatusMsgLabel = new KRSqueezedTextLabel( i18n( " Initializing..." ), statusBar() ); mStatusMsgLabel->tqsetAlignment( AlignLeft | AlignVCenter ); statusBar()->addWidget( mStatusMsgLabel, 10 , false ); statusBar()->addWidget( mLittleProgress, 0 , true ); mLittleProgress->show(); } void MainWindow::paintAboutScreen( const TQString& msg ) { TQString location = locate( "data", "kontact/about/main.html" ); TQString content = KPIM::kFileToString( location ); content = content.tqarg( locate( "data", "libkdepim/about/kde_infopage.css" ) ); if ( kapp->reverseLayout() ) content = content.tqarg( "@import \"%1\";" ).tqarg( locate( "data", "libkdepim/about/kde_infopage_rtl.css" ) ); else content = content.tqarg( "" ); mIntroPart->begin( KURL( location ) ); TQString appName( i18n( "KDE Kontact" ) ); TQString catchPhrase( i18n( "Get Organized!" ) ); TQString quickDescription( i18n( "The KDE Personal Information Management Suite" ) ); mIntroPart->write( content.tqarg( TQFont().pointSize() + 2 ).tqarg( appName ) .tqarg( catchPhrase ).tqarg( quickDescription ).tqarg( msg ) ); mIntroPart->end(); } void MainWindow::initAboutScreen() { TQHBox *introbox = new TQHBox( mPartsStack ); mPartsStack->addWidget( introbox ); mPartsStack->raiseWidget( introbox ); mIntroPart = new KHTMLPart( introbox ); mIntroPart->widget()->setFocusPolicy( TQ_WheelFocus ); // Let's better be paranoid and disable plugins (it defaults to enabled): mIntroPart->setPluginsEnabled( false ); mIntroPart->setJScriptEnabled( false ); // just make this explicit mIntroPart->setJavaEnabled( false ); // just make this explicit mIntroPart->setMetaRefreshEnabled( false ); mIntroPart->setURLCursor( KCursor::handCursor() ); mIntroPart->view()->setLineWidth( 0 ); connect( mIntroPart->browserExtension(), TQT_SIGNAL( openURLRequest( const KURL&, const KParts::URLArgs& ) ), TQT_SLOT( slotOpenUrl( const KURL& ) ) ); connect( mIntroPart->browserExtension(), TQT_SIGNAL( createNewWindow( const KURL&, const KParts::URLArgs& ) ), TQT_SLOT( slotOpenUrl( const KURL& ) ) ); } void MainWindow::setupActions() { KStdAction::quit( TQT_TQOBJECT(this), TQT_SLOT( slotQuit() ), actionCollection() ); mNewActions = new KToolBarPopupAction( KGuiItem( i18n( "New" ), "" ), KStdAccel::shortcut(KStdAccel::New), TQT_TQOBJECT(this), TQT_SLOT( slotNewClicked() ), actionCollection(), "action_new" ); KConfig* const cfg = Prefs::self()->config(); cfg->setGroup( "Kontact Groupware Settings" ); mSyncActionsEnabled = cfg->readBoolEntry( "GroupwareMailFoldersEnabled", true ); if ( mSyncActionsEnabled ) { mSyncActions = new KToolBarPopupAction( KGuiItem( i18n( "Synchronize" ), "kitchensync" ), KStdAccel::shortcut(KStdAccel::Reload), TQT_TQOBJECT(this), TQT_SLOT( slotSyncClicked() ), actionCollection(), "action_sync" ); } new KAction( i18n( "Configure Kontact..." ), "configure", 0, TQT_TQOBJECT(this), TQT_SLOT( slotPreferences() ), actionCollection(), "settings_configure_kontact" ); new KAction( i18n( "Configure &Profiles..." ), 0, TQT_TQOBJECT(this), TQT_SLOT( slotConfigureProfiles() ), actionCollection(), "settings_configure_kontact_profiles" ); new KAction( i18n( "&Kontact Introduction" ), 0, TQT_TQOBJECT(this), TQT_SLOT( slotShowIntroduction() ), actionCollection(), "help_introduction" ); new KAction( i18n( "&Tip of the Day" ), 0, TQT_TQOBJECT(this), TQT_SLOT( slotShowTip() ), actionCollection(), "help_tipofday" ); KWidgetAction* spacerAction = new KWidgetAction( new TQWidget( this ), "SpacerAction", "", 0, 0, actionCollection(), "navigator_spacer_item" ); spacerAction->setAutoSized( true ); } void MainWindow::slotConfigureProfiles() { TQGuardedPtr dlg = new Kontact::ProfileDialog( this ); dlg->setModal( true ); dlg->exec(); delete dlg; } namespace { void copyConfigEntry( KConfig* source, KConfig* dest, const TQString& group, const TQString& key, const TQString& defaultValue=TQString() ) { source->setGroup( group ); dest->setGroup( group ); dest->writeEntry( key, source->readEntry( key, defaultValue ) ); } } void MainWindow::slotSaveToProfile( const TQString& id ) { const TQString path = Kontact::ProfileManager::self()->profileById( id ).saveLocation(); if ( path.isNull() ) return; KConfig* const cfg = Prefs::self()->config(); Prefs::self()->writeConfig(); saveMainWindowSettings( cfg ); saveSettings(); KConfig profile( path+"/kontactrc", /*read-only=*/false, /*useglobals=*/false ); ::copyConfigEntry( cfg, &profile, "MainWindow Toolbar navigatorToolBar", "Hidden", "true" ); ::copyConfigEntry( cfg, &profile, "View", "SidePaneSplitter" ); ::copyConfigEntry( cfg, &profile, "Icons", "Theme" ); for ( PluginList::Iterator it = mPlugins.begin(); it != mPlugins.end(); ++it ) { if ( !(*it)->isRunningStandalone() ) { (*it)->part(); } (*it)->saveToProfile( path ); } } void MainWindow::slotLoadProfile( const TQString& id ) { const TQString path = Kontact::ProfileManager::self()->profileById( id ).saveLocation(); if ( path.isNull() ) return; KConfig* const cfg = Prefs::self()->config(); Prefs::self()->writeConfig(); saveMainWindowSettings( cfg ); saveSettings(); const KConfig profile( path+"/kontactrc", /*read-only=*/false, /*useglobals=*/false ); const TQStringList groups = profile.groupList(); for ( TQStringList::ConstIterator it = groups.begin(), end = groups.end(); it != end; ++it ) { cfg->setGroup( *it ); typedef TQMap StringMap; const StringMap entries = profile.entryMap( *it ); for ( StringMap::ConstIterator it2 = entries.begin(), end = entries.end(); it2 != end; ++it2 ) { if ( it2.data() == "KONTACT_PROFILE_DELETE_KEY" ) cfg->deleteEntry( it2.key() ); else cfg->writeEntry( it2.key(), it2.data() ); } } cfg->sync(); Prefs::self()->readConfig(); applyMainWindowSettings( cfg ); KIconTheme::reconfigure(); const WId wid = winId(); KIPC::sendMessage( KIPC::PaletteChanged, wid ); KIPC::sendMessage( KIPC::FontChanged, wid ); KIPC::sendMessage( KIPC::StyleChanged, wid ); KIPC::sendMessage( KIPC::SettingsChanged, wid ); for ( int i = 0; i < KIcon::LastGroup; ++i ) KIPC::sendMessage( KIPC::IconChanged, wid, i ); loadSettings(); for ( PluginList::Iterator it = mPlugins.begin(); it != mPlugins.end(); ++it ) { if ( !(*it)->isRunningStandalone() ) { kdDebug() << "Ensure loaded: " << (*it)->identifier() << endl; (*it)->part(); } (*it)->loadProfile( path ); } } bool MainWindow::isPluginLoaded( const KPluginInfo *info ) { return (pluginFromInfo( info ) != 0); } Plugin *MainWindow::pluginFromInfo( const KPluginInfo *info ) { PluginList::ConstIterator end = mPlugins.end(); for ( PluginList::ConstIterator it = mPlugins.begin(); it != end; ++it ) if ( (*it)->identifier() == info->pluginName() ) return *it; return 0; } Plugin *MainWindow::pluginFromAction( const KAction *action ) { PluginList::ConstIterator end = mPlugins.end(); for ( PluginList::ConstIterator it = mPlugins.begin(); it != end; ++it ) { if ( (*it)->identifier() == action->name() ) { return *it; } } return 0; } bool MainWindow::isPluginLoadedByAction( const KAction *action ) { KPluginInfo::List::ConstIterator it; for ( it = mPluginInfos.begin(); it != mPluginInfos.end(); ++it ) { if ( !(*it)->isPluginEnabled() ) continue; if ( isPluginLoaded( *it ) ) { Plugin *plugin = pluginFromInfo( *it ); if ( plugin ) { if ( plugin->identifier() == action->name() ) { return true; } } } } return false; } void MainWindow::sortActionsByWeight() { TQPtrList sorted; TQPtrListIterator eit( mActionPlugins ); KAction *action; while ( ( action = eit.current() ) != 0 ) { ++eit; TQPtrListIterator sortIt( sorted ); uint at = 0; KAction *saction; Plugin *p1 = pluginFromAction( action ); while ( ( saction = sortIt.current() ) != 0 ) { Plugin *p2 = pluginFromAction( saction ); if ( p1 && p2 && p1->weight() >= p2->weight() ) { ++sortIt; ++at; } else { break; } } sorted.insert( at, action ); } mActionPlugins = sorted; } void MainWindow::loadPlugins() { TQPtrList plugins; TQPtrList loadDelayed; uint i; KPluginInfo::List::ConstIterator it; for ( it = mPluginInfos.begin(); it != mPluginInfos.end(); ++it ) { if ( !(*it)->isPluginEnabled() ) continue; if ( isPluginLoaded( *it ) ) { Plugin *plugin = pluginFromInfo( *it ); if ( plugin ) plugin->configUpdated(); continue; } kdDebug(5600) << "Loading Plugin: " << (*it)->name() << endl; Kontact::Plugin *plugin = KParts::ComponentFactory::createInstanceFromService( (*it)->service(), TQT_TQOBJECT(this) ); if ( !plugin ) continue; plugin->setIdentifier( (*it)->pluginName() ); plugin->setTitle( (*it)->name() ); plugin->setIcon( (*it)->icon() ); TQVariant libNameProp = (*it)->property( "X-KDE-KontactPartLibraryName" ); TQVariant exeNameProp = (*it)->property( "X-KDE-KontactPartExecutableName" ); TQVariant loadOnStart = (*it)->property( "X-KDE-KontactPartLoadOnStart" ); TQVariant hasPartProp = (*it)->property( "X-KDE-KontactPluginHasPart" ); if ( !loadOnStart.isNull() && loadOnStart.toBool() ) mDelayedPreload.append( plugin ); kdDebug(5600) << "LIBNAMEPART: " << libNameProp.toString() << endl; plugin->setPartLibraryName( libNameProp.toString().utf8() ); plugin->setExecutableName( exeNameProp.toString() ); if ( hasPartProp.isValid() ) plugin->setShowInSideBar( hasPartProp.toBool() ); for ( i = 0; i < plugins.count(); ++i ) { Plugin *p = plugins.at( i ); if ( plugin->weight() < p->weight() ) break; } plugins.insert( i, plugin ); } for ( i = 0; i < plugins.count(); ++ i ) { Plugin *plugin = plugins.at( i ); KAction *action; TQPtrList *actionList = plugin->newActions(); for ( action = actionList->first(); action; action = actionList->next() ) { kdDebug(5600) << "Plugging " << action->name() << endl; action->plug( mNewActions->popupMenu() ); if ( action->name() == plugin->identifier() ) { mPluginAction.insert( plugin, action ); } } if ( mSyncActionsEnabled ) { actionList = plugin->syncActions(); for ( action = actionList->first(); action; action = actionList->next() ) { kdDebug(5600) << "Plugging " << action->name() << endl; action->plug( mSyncActions->popupMenu() ); } } addPlugin( plugin ); } updateShortcuts(); mNewActions->setEnabled( mPlugins.size() != 0 ); if ( mSyncActionsEnabled ) mSyncActions->setEnabled( mPlugins.size() != 0 ); } void MainWindow::unloadPlugins() { KPluginInfo::List::ConstIterator end = mPluginInfos.constEnd(); KPluginInfo::List::ConstIterator it; for ( it = mPluginInfos.constBegin(); it != end; ++it ) { if ( !(*it)->isPluginEnabled() ) removePlugin( *it ); } } void MainWindow::updateShortcuts() { TQPtrList loadedActions; sortActionsByWeight(); TQPtrListIterator it( mActionPlugins ); int i = 1; KAction *action; while ( ( action = it.current() ) != 0 ) { ++it; if ( isPluginLoadedByAction( action ) ) { loadedActions.append( action ); TQString shortcut = TQString( "CTRL+%1" ).tqarg( i ); action->setShortcut( KShortcut( shortcut ) ); i++; } else { action->setShortcut( KShortcut() ); } } unplugActionList( "navigator_actionlist" ); factory()->plugActionList( this, TQString( "navigator_actionlist" ), loadedActions ); } bool MainWindow::removePlugin( const KPluginInfo *info ) { PluginList::Iterator end = mPlugins.end(); for ( PluginList::Iterator it = mPlugins.begin(); it != end; ++it ) { if ( ( *it )->identifier() == info->pluginName() ) { Plugin *plugin = *it; KAction *action; TQPtrList *actionList = plugin->newActions(); for ( action = actionList->first(); action; action = actionList->next() ) { kdDebug(5600) << "Unplugging " << action->name() << endl; action->unplug( mNewActions->popupMenu() ); } if ( mSyncActionsEnabled ) { actionList = plugin->syncActions(); for ( action = actionList->first(); action; action = actionList->next() ) { kdDebug(5600) << "Unplugging " << action->name() << endl; action->unplug( mSyncActions->popupMenu() ); } } removeChildClient( plugin ); if ( mCurrentPlugin == plugin ) mCurrentPlugin = 0; plugin->deleteLater(); // removes the part automatically mPlugins.remove( it ); if ( plugin->showInSideBar() ) { mPluginAction.remove( plugin ); } if ( mCurrentPlugin == 0 ) { PluginList::Iterator it; for ( it = mPlugins.begin(); it != mPlugins.end(); ++it ) { if ( (*it)->showInSideBar() ) { selectPlugin( *it ); return true; } } } return true; } } return false; } void MainWindow::addPlugin( Kontact::Plugin *plugin ) { kdDebug(5600) << "Added plugin" << endl; mPlugins.append( plugin ); // merge the plugins GUI into the main window insertChildClient( plugin ); } void MainWindow::partLoaded( Kontact::Plugin*, KParts::ReadOnlyPart *part ) { // See if we have this part already (e.g. due to two plugins sharing it) if ( mPartsStack->id( part->widget() ) != -1 ) return; mPartsStack->addWidget( part->widget() ); mPartManager->addPart( part, false ); // Workaround for KParts misbehavior: addPart calls show! part->widget()->hide(); } void MainWindow::slotActivePartChanged( KParts::Part *part ) { if ( !part ) { createGUI( 0 ); return; } kdDebug(5600) << "Part activated: " << part << " with stack id. " << mPartsStack->id( part->widget() )<< endl; //createGUI( part ); // moved to selectPlugin() statusBar()->clear(); } void MainWindow::slotNewClicked() { KAction *action = mCurrentPlugin->newActions()->first(); if ( action ) { action->activate(); } else { PluginList::Iterator it; for ( it = mPlugins.begin(); it != mPlugins.end(); ++it ) { action = (*it)->newActions()->first(); if ( action ) { action->activate(); return; } } } } void MainWindow::slotSyncClicked() { KAction *action = mCurrentPlugin->syncActions()->first(); if ( action ) { action->activate(); } else { PluginList::Iterator it; for ( it = mPlugins.begin(); it != mPlugins.end(); ++it ) { action = (*it)->syncActions()->first(); if ( action ) { action->activate(); return; } } } } KToolBar* Kontact::MainWindow::findToolBar(const char* name) { // like KMainWindow::toolBar, but which doesn't create the toolbar if not found return static_cast(TQT_TQWIDGET(child(name, "KToolBar"))); } void MainWindow::slotActionTriggered() { const KAction *actionSender = static_cast( sender() ); TQString identifier = actionSender->name(); if ( !identifier.isEmpty() ) { selectPlugin( identifier ); } } void MainWindow::selectPlugin( Kontact::Plugin *plugin ) { if ( !plugin ) return; if ( plugin->isRunningStandalone() ) { statusBar()->message( i18n( "Application is running standalone. Foregrounding..." ), 1000 ); mSidePane->indicateForegrunding( plugin ); plugin->bringToForeground(); return; } KApplication::setOverrideCursor( TQCursor( TQt::WaitCursor ) ); KParts::Part *part = plugin->part(); if ( !part ) { KApplication::restoreOverrideCursor(); KMessageBox::error( this, i18n( "Cannot load part for %1." ) .tqarg( plugin->title() ) + "\n" + lastErrorMessage() ); plugin->setDisabled( true ); mSidePane->updatePlugins(); return; } // store old focus widget TQWidget *tqfocusWidget = kapp->tqfocusWidget(); if ( mCurrentPlugin && tqfocusWidget ) { // save the focus widget only when it belongs to the activated part TQWidget *parent = tqfocusWidget->parentWidget(); while ( parent ) { if ( parent == mCurrentPlugin->part()->widget() ) mFocusWidgets.insert( mCurrentPlugin->identifier(), TQGuardedPtr( tqfocusWidget ) ); parent = parent->parentWidget(); } } if ( mSidePane ) { mSidePane->selectPlugin( plugin->identifier() ); } plugin->select(); mPartManager->setActivePart( part ); TQWidget *view = part->widget(); Q_ASSERT( view ); if ( view ) { mPartsStack->raiseWidget( view ); view->show(); if ( mFocusWidgets.contains( plugin->identifier() ) ) { tqfocusWidget = mFocusWidgets[ plugin->identifier() ]; if ( tqfocusWidget ) tqfocusWidget->setFocus(); } else view->setFocus(); mCurrentPlugin = plugin; KAction *newAction = plugin->newActions()->first(); KAction *syncAction = plugin->syncActions()->first(); createGUI( plugin->part() ); KToolBar* navigatorToolBar = findToolBar( "navigatorToolBar" ); // Let the navigator toolbar be always the last one, if it's in the top dockwindow if ( navigatorToolBar && !navigatorToolBar->isHidden() && navigatorToolBar->barPos() == KToolBar::Top ) { topDock()->moveDockWindow( navigatorToolBar, -1 ); } setCaption( i18n( "Plugin dependent window title" ,"%1 - Kontact" ).tqarg( plugin->title() ) ); if ( newAction ) { mNewActions->setIcon( newAction->icon() ); mNewActions->setText( newAction->text() ); } else { // we'll use the action of the first plugin which offers one PluginList::Iterator it; for ( it = mPlugins.begin(); it != mPlugins.end(); ++it ) { newAction = (*it)->newActions()->first(); if ( newAction ) { mNewActions->setIcon( newAction->icon() ); mNewActions->setText( newAction->text() ); break; } } } if ( mSyncActionsEnabled ) { if ( syncAction ) { mSyncActions->setIcon( syncAction->icon() ); mSyncActions->setText( syncAction->text() ); } else { // we'll use the action of the first plugin which offers one PluginList::Iterator it; for ( it = mPlugins.begin(); it != mPlugins.end(); ++it ) { syncAction = (*it)->syncActions()->first(); if ( syncAction ) { mSyncActions->setIcon( syncAction->icon() ); mSyncActions->setText( syncAction->text() ); break; } } } } } TQStringList invisibleActions = plugin->invisibleToolbarActions(); TQStringList::ConstIterator it; for ( it = invisibleActions.begin(); it != invisibleActions.end(); ++it ) { KAction *action = part->actionCollection()->action( (*it).latin1() ); if ( action ) { TQPtrListIterator it( toolBarIterator() ); for ( ; it.current() ; ++it ) { action->unplug( it.current() ); } } } KApplication::restoreOverrideCursor(); } void MainWindow::selectPlugin( const TQString &pluginName ) { PluginList::ConstIterator end = mPlugins.end(); for ( PluginList::ConstIterator it = mPlugins.begin(); it != end; ++it ) if ( ( *it )->identifier() == pluginName ) { selectPlugin( *it ); return; } } void MainWindow::loadSettings() { if ( mSplitter ) mSplitter->setSizes( Prefs::self()->mSidePaneSplitter ); // Preload Plugins. This _must_ happen before the default part is loaded PluginList::ConstIterator it; for ( it = mDelayedPreload.begin(); it != mDelayedPreload.end(); ++it ) selectPlugin( *it ); selectPlugin( Prefs::self()->mActivePlugin ); } void MainWindow::saveSettings() { if ( mSplitter ) Prefs::self()->mSidePaneSplitter = mSplitter->sizes(); if ( mCurrentPlugin ) Prefs::self()->mActivePlugin = mCurrentPlugin->identifier(); } void MainWindow::slotShowTip() { showTip( true ); } void MainWindow::slotShowIntroduction() { mPartsStack->raiseWidget( 0 ); // ### } void MainWindow::showTip( bool force ) { TQStringList tips; PluginList::ConstIterator end = mPlugins.end(); for ( PluginList::ConstIterator it = mPlugins.begin(); it != end; ++it ) { TQString file = (*it)->tipFile(); if ( !file.isEmpty() ) tips.append( file ); } KTipDialog::showMultiTip( this, tips, force ); } void MainWindow::slotQuit() { mReallyClose = true; close(); } void MainWindow::slotPreferences() { static SettingsDialogWrapper *dlg = 0; if ( !dlg ) { // do not show settings of components running standalone TQValueList filteredPlugins = mPluginInfos; PluginList::ConstIterator it; for ( it = mPlugins.begin(); it != mPlugins.end(); ++it ) if ( (*it)->isRunningStandalone() ) { TQValueList::ConstIterator infoIt; for ( infoIt = filteredPlugins.begin(); infoIt != filteredPlugins.end(); ++infoIt ) { if ( (*infoIt)->pluginName() == (*it)->identifier() ) { filteredPlugins.remove( *infoIt ); break; } } } dlg = new SettingsDialogWrapper( KSettings::Dialog::Configurable, this ); dlg->addPluginInfos( filteredPlugins ); connect( dlg, TQT_SIGNAL( pluginSelectionChanged() ), TQT_SLOT( pluginsChanged() ) ); } dlg->show(); dlg->fixButtonLabel( this ); } int MainWindow::startServiceFor( const TQString& serviceType, const TQString& constraint, const TQString& preferences, TQString *error, TQCString* dcopService, int flags ) { PluginList::ConstIterator end = mPlugins.end(); for ( PluginList::ConstIterator it = mPlugins.begin(); it != end; ++it ) { if ( (*it)->createDCOPInterface( serviceType ) ) { kdDebug(5600) << "found interface for " << serviceType << endl; if ( dcopService ) *dcopService = (*it)->dcopClient()->appId(); kdDebug(5600) << "appId=" << (*it)->dcopClient()->appId() << endl; return 0; // success } } kdDebug(5600) << "Didn't find dcop interface, falling back to external process" << endl; return KDCOPServiceStarter::startServiceFor( serviceType, constraint, preferences, error, dcopService, flags ); } void MainWindow::pluginsChanged() { unloadPlugins(); loadPlugins(); mSidePane->updatePlugins(); updateShortcuts(); } void MainWindow::updateConfig() { kdDebug( 5600 ) << k_funcinfo << endl; saveSettings(); loadSettings(); } void MainWindow::showAboutDialog() { KApplication::setOverrideCursor( TQCursor( TQt::WaitCursor ) ); if ( !mAboutDialog ) mAboutDialog = new AboutDialog( this ); mAboutDialog->show(); mAboutDialog->raise(); KApplication::restoreOverrideCursor(); } void MainWindow::configureShortcuts() { KKeyDialog dialog( true, this ); dialog.insert( actionCollection() ); if ( mCurrentPlugin && mCurrentPlugin->part() ) dialog.insert( mCurrentPlugin->part()->actionCollection() ); dialog.configure(); } void MainWindow::configureToolbars() { saveMainWindowSettings( KGlobal::config(), "MainWindow" ); KEditToolbar edit( factory() ); connect( &edit, TQT_SIGNAL( newToolbarConfig() ), this, TQT_SLOT( slotNewToolbarConfig() ) ); edit.exec(); } void MainWindow::slotNewToolbarConfig() { if ( mCurrentPlugin && mCurrentPlugin->part() ) { createGUI( mCurrentPlugin->part() ); } if ( mCurrentPlugin ) { applyMainWindowSettings( KGlobal::config(), "MainWindow" ); } updateShortcuts(); // for the plugActionList call } void MainWindow::slotOpenUrl( const KURL &url ) { if ( url.protocol() == "exec" ) { if ( url.path() == "/switch" ) { selectPlugin( mCurrentPlugin ); } if ( url.path() == "/gwwizard" ) { KRun::runCommand( "groupwarewizard" ); slotQuit(); } if ( url.path().startsWith( "/help" ) ) { TQString app( "kontact" ); if ( !url.query().isEmpty() ) { app = url.query().mid( 1 ); } kapp->invokeHelp( TQString(), app ); } } else { new KRun( url, this ); } } void MainWindow::readProperties( KConfig *config ) { Core::readProperties( config ); TQStringList activePlugins = config->readListEntry( "ActivePlugins" ); TQValueList::ConstIterator it = mPlugins.begin(); TQValueList::ConstIterator end = mPlugins.end(); for ( ; it != end; ++it ) { Plugin *plugin = *it; if ( !plugin->isRunningStandalone() ) { TQStringList::ConstIterator activePlugin = activePlugins.find( plugin->identifier() ); if ( activePlugin != activePlugins.end() ) { plugin->readProperties( config ); } } } } void MainWindow::saveProperties( KConfig *config ) { Core::saveProperties( config ); TQStringList activePlugins; KPluginInfo::List::Iterator it = mPluginInfos.begin(); KPluginInfo::List::Iterator end = mPluginInfos.end(); for ( ; it != end; ++it ) { KPluginInfo *info = *it; if ( info->isPluginEnabled() ) { Plugin *plugin = pluginFromInfo( info ); if ( plugin ) { activePlugins.append( plugin->identifier() ); plugin->saveProperties( config ); } } } config->writeEntry( "ActivePlugins", activePlugins ); } bool MainWindow::queryClose() { //if ( kapp->sessionSaving() || mReallyClose ) if ( kapp->sessionSaving() ) return true; bool localClose = true; TQValueList::ConstIterator end = mPlugins.end(); TQValueList::ConstIterator it = mPlugins.begin(); for ( ; it != end; ++it ) { Plugin *plugin = *it; if ( !plugin->isRunningStandalone() ) if ( !plugin->queryClose() ) localClose = false; } return localClose; } void MainWindow::slotShowStatusMsg( const TQString &msg ) { if ( !statusBar() || !mStatusMsgLabel ) return; mStatusMsgLabel->setText( msg ); } TQString MainWindow::introductionString() { KIconLoader *iconloader = KGlobal::iconLoader(); int iconSize = iconloader->currentSize( KIcon::Desktop ); TQString handbook_icon_path = iconloader->iconPath( "contents2", KIcon::Desktop ); TQString html_icon_path = iconloader->iconPath( "html", KIcon::Desktop ); TQString wizard_icon_path = iconloader->iconPath( "wizard", KIcon::Desktop ); TQString info = i18n( "

Welcome to Kontact %1

" "

%1

" "" "" "" "" "" "" "" "
%1
%1
%1
%1
%1
%1
" "

Skip this introduction

" ) .tqarg( kapp->aboutData()->version() ) .tqarg( i18n( "Kontact handles your e-mail, addressbook, calendar, to-do list and more." ) ) .tqarg( "exec:/help?kontact" ) .tqarg( iconSize ) .tqarg( iconSize ) .tqarg( handbook_icon_path ) .tqarg( "exec:/help?kontact" ) .tqarg( i18n( "Read Manual" ) ) .tqarg( i18n( "Learn more about Kontact and its components" ) ) .tqarg( "http://kontact.org" ) .tqarg( iconSize ) .tqarg( iconSize ) .tqarg( html_icon_path ) .tqarg( "http://kontact.org" ) .tqarg( i18n( "Visit Kontact Website" ) ) .tqarg( i18n( "Access online resources and tutorials" ) ) .tqarg( "exec:/gwwizard" ) .tqarg( iconSize ) .tqarg( iconSize ) .tqarg( wizard_icon_path ) .tqarg( "exec:/gwwizard" ) .tqarg( i18n( "Configure Kontact as Groupware Client" ) ) .tqarg( i18n( "Prepare Kontact for use in corporate networks" ) ) .tqarg( "exec:/switch" ); return info; } #include "mainwindow.moc"