KDEUI
ktoolbarhandler.cpp
Go to the documentation of this file.
00001 /* This file is part of the KDE libraries 00002 Copyright (C) 2002 Simon Hausmann <hausmann@kde.org> 00003 00004 This library is free software; you can redistribute it and/or 00005 modify it under the terms of the GNU Library General Public 00006 License version 2 as published by the Free Software Foundation. 00007 00008 This library is distributed in the hope that it will be useful, 00009 but WITHOUT ANY WARRANTY; without even the implied warranty of 00010 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00011 Library General Public License for more details. 00012 00013 You should have received a copy of the GNU Library General Public License 00014 along with this library; see the file COPYING.LIB. If not, write to 00015 the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 00016 Boston, MA 02110-1301, USA. 00017 */ 00018 00019 #include "ktoolbarhandler_p.h" 00020 00021 #include <QtXml/QDomDocument> 00022 00023 #include <kaction.h> 00024 #include <kactioncollection.h> 00025 #include <kactionmenu.h> 00026 #include <kauthorized.h> 00027 #include <kguiitem.h> 00028 #include <klocale.h> 00029 #include <kxmlguiwindow.h> 00030 #include <kmenu.h> 00031 #include <ktoggletoolbaraction.h> 00032 #include <ktoolbar.h> 00033 #include <kxmlguifactory.h> 00034 #include <kdebug.h> 00035 #include <kstandardaction_p.h> 00036 00037 namespace 00038 { 00039 const char *actionListName = "show_menu_and_toolbar_actionlist"; 00040 00041 const char *guiDescription = "" 00042 "<!DOCTYPE kpartgui><kpartgui name=\"StandardToolBarMenuHandler\">" 00043 "<MenuBar>" 00044 " <Menu name=\"settings\">" 00045 " <ActionList name=\"%1\" />" 00046 " </Menu>" 00047 "</MenuBar>" 00048 "</kpartgui>"; 00049 00050 class BarActionBuilder 00051 { 00052 public: 00053 BarActionBuilder( KActionCollection *actionCollection, KXmlGuiWindow *mainWindow, 00054 QLinkedList<KToolBar*> &oldToolBarList ) 00055 : m_actionCollection( actionCollection ), m_mainWindow( mainWindow ), m_needsRebuild( false ) 00056 { 00057 QList<KToolBar*> toolBars = qFindChildren<KToolBar*>( m_mainWindow ); 00058 00059 foreach( KToolBar * toolBar, toolBars) { 00060 if ( toolBar->mainWindow() != m_mainWindow ) 00061 continue; 00062 00063 if ( !oldToolBarList.contains( toolBar ) ) 00064 m_needsRebuild = true; 00065 00066 m_toolBars.append( toolBar ); 00067 } 00068 00069 if ( !m_needsRebuild ) 00070 m_needsRebuild = ( oldToolBarList.count() != m_toolBars.count() ); 00071 } 00072 00073 bool needsRebuild() const 00074 { 00075 return m_needsRebuild; 00076 } 00077 00078 QList<QAction*> create() 00079 { 00080 QList<QAction*> actions; 00081 00082 if ( !m_needsRebuild ) 00083 return actions; 00084 00085 foreach ( KToolBar* bar, m_toolBars ) 00086 handleToolBar( bar ); 00087 00088 if ( m_toolBarActions.count() == 0 ) 00089 return actions; 00090 00091 if ( m_toolBarActions.count() == 1 ) { 00092 const KStandardAction::KStandardActionInfo* pInfo = KStandardAction::infoPtr(KStandardAction::ShowToolbar); 00093 KToggleToolBarAction* action = static_cast<KToggleToolBarAction *>( m_toolBarActions.first() ); 00094 action->setText( i18n( pInfo->psLabel ) ); 00095 return m_toolBarActions; 00096 } 00097 00098 KActionMenu *menuAction = new KActionMenu(i18n( "Toolbars Shown" ), m_actionCollection); 00099 m_actionCollection->addAction("toolbars_submenu_action", menuAction); 00100 00101 foreach ( QAction* action, m_toolBarActions ) 00102 menuAction->menu()->addAction( action ); 00103 00104 actions.append( menuAction ); 00105 00106 return actions; 00107 } 00108 00109 const QLinkedList<KToolBar*> &toolBars() const 00110 { 00111 return m_toolBars; 00112 } 00113 00114 private: 00115 void handleToolBar( KToolBar *toolBar ) 00116 { 00117 KToggleToolBarAction *action = new KToggleToolBarAction( 00118 toolBar, 00119 toolBar->windowTitle(), 00120 m_actionCollection); 00121 m_actionCollection->addAction(toolBar->objectName(), action); 00122 00123 // ## tooltips, whatsthis? 00124 m_toolBarActions.append( action ); 00125 } 00126 00127 KActionCollection *m_actionCollection; 00128 KXmlGuiWindow *m_mainWindow; 00129 00130 QLinkedList<KToolBar*> m_toolBars; 00131 QList<QAction*> m_toolBarActions; 00132 00133 bool m_needsRebuild : 1; 00134 }; 00135 } 00136 00137 using namespace KDEPrivate; 00138 00139 class ToolBarHandler::Private 00140 { 00141 public: 00142 Private( ToolBarHandler *_parent ) 00143 : parent( _parent ) 00144 { 00145 } 00146 00147 void clientAdded( KXMLGUIClient *client ) 00148 { 00149 Q_UNUSED(client) 00150 parent->setupActions(); 00151 } 00152 00153 void init( KXmlGuiWindow *mainWindow ); 00154 void connectToActionContainers(); 00155 void connectToActionContainer( QAction *action ); 00156 void connectToActionContainer( QWidget *container ); 00157 00158 ToolBarHandler *parent; 00159 QPointer<KXmlGuiWindow> mainWindow; 00160 QList<QAction*> actions; 00161 QLinkedList<KToolBar*> toolBars; 00162 }; 00163 00164 void ToolBarHandler::Private::init( KXmlGuiWindow *mw ) 00165 { 00166 mainWindow = mw; 00167 00168 QObject::connect( mainWindow->guiFactory(), SIGNAL( clientAdded( KXMLGUIClient * ) ), 00169 parent, SLOT( clientAdded( KXMLGUIClient * ) ) ); 00170 00171 if ( parent->domDocument().documentElement().isNull() ) { 00172 00173 QString completeDescription = QString::fromLatin1( guiDescription ) 00174 .arg( actionListName ); 00175 00176 parent->setXML( completeDescription, false /*merge*/ ); 00177 } 00178 } 00179 00180 void ToolBarHandler::Private::connectToActionContainers() 00181 { 00182 foreach ( QAction* action, actions ) 00183 connectToActionContainer( action ); 00184 } 00185 00186 void ToolBarHandler::Private::connectToActionContainer( QAction *action ) 00187 { 00188 uint containerCount = action->associatedWidgets().count(); 00189 00190 for ( uint i = 0; i < containerCount; ++i ) 00191 connectToActionContainer( action->associatedWidgets().value( i ) ); 00192 } 00193 00194 void ToolBarHandler::Private::connectToActionContainer( QWidget *container ) 00195 { 00196 QMenu *popupMenu = qobject_cast<QMenu *>( container ); 00197 if ( !popupMenu ) 00198 return; 00199 00200 connect( popupMenu, SIGNAL( aboutToShow() ), 00201 parent, SLOT( setupActions() ) ); 00202 } 00203 00204 ToolBarHandler::ToolBarHandler( KXmlGuiWindow *mainWindow ) 00205 : QObject( mainWindow ), KXMLGUIClient( mainWindow ), 00206 d( new Private( this ) ) 00207 { 00208 d->init( mainWindow ); 00209 } 00210 00211 ToolBarHandler::ToolBarHandler( KXmlGuiWindow *mainWindow, QObject *parent ) 00212 : QObject( parent ), KXMLGUIClient( mainWindow ), 00213 d( new Private( this ) ) 00214 { 00215 d->init( mainWindow ); 00216 } 00217 00218 ToolBarHandler::~ToolBarHandler() 00219 { 00220 qDeleteAll( d->actions ); 00221 d->actions.clear(); 00222 00223 delete d; 00224 } 00225 00226 QAction *ToolBarHandler::toolBarMenuAction() 00227 { 00228 Q_ASSERT( d->actions.count() == 1 ); 00229 return d->actions.first(); 00230 } 00231 00232 void ToolBarHandler::setupActions() 00233 { 00234 if ( !factory() || !d->mainWindow ) 00235 return; 00236 00237 BarActionBuilder builder( actionCollection(), d->mainWindow, d->toolBars ); 00238 00239 if ( !builder.needsRebuild() ) 00240 return; 00241 00242 unplugActionList( actionListName ); 00243 00244 qDeleteAll( d->actions ); 00245 d->actions.clear(); 00246 00247 d->actions = builder.create(); 00248 00249 d->toolBars = builder.toolBars(); 00250 00251 // We have no XML file associated with our action collection, so load settings from KConfig 00252 actionCollection()->readSettings(); // #233712 00253 00254 if ( KAuthorized::authorizeKAction( "options_show_toolbar" ) ) 00255 plugActionList( actionListName, d->actions ); 00256 00257 d->connectToActionContainers(); 00258 } 00259 00260 #include "ktoolbarhandler_p.moc"
KDE 4.6 API Reference