33 #include <config-kleopatra.h>
58 #include "progresswidget/statusbarprogresswidget.h"
59 #include "progresswidget/progressdialog.h"
61 #include <KApplication>
62 #include <KActionCollection>
66 #include <KStandardAction>
69 #include <KMessageBox>
70 #include <KStandardGuiItem>
71 #include <KStandardDirs>
72 #include <KShortcutsDialog>
73 #include <KXMLGUIFactory>
74 #include <KEditToolBar>
75 #include <KAboutApplicationDialog>
78 #include <QAbstractItemView>
81 #include <QApplication>
82 #include <QCloseEvent>
88 #include <kleo/cryptobackendfactory.h>
89 #include <ui/cryptoconfigdialog.h>
90 #include <kleo/cryptoconfig.h>
91 #include <kleo/stl_util.h>
93 #include <boost/bind.hpp>
94 #include <boost/shared_ptr.hpp>
99 static const bool OS_WIN =
true;
104 using namespace Kleo;
105 using namespace Kleo::Commands;
106 using namespace boost;
107 using namespace GpgME;
111 static const KAboutData * aboutGpg4WinData() {
119 static const QString app = KGlobal::mainComponent().aboutData()->programName();
120 KGuiItem item = KStandardGuiItem::quit();
121 item.setText( i18nc(
"Quit [ApplicationName]",
"&Quit %1", app ) );
126 KGuiItem item = KStandardGuiItem::close();
127 item.setText( i18n(
"Only &Close Window" ) );
133 class MainWindow::Private {
134 friend class ::MainWindow;
141 template <
typename T>
142 void createAndStart() {
143 (
new T( this->currentView(), &this->controller ) )->start();
145 template <
typename T>
146 void createAndStart( QAbstractItemView * view ) {
147 (
new T( view, &this->controller ) )->start();
149 template <
typename T>
150 void createAndStart(
const QStringList & a ) {
151 (
new T( a, this->currentView(), &this->controller ) )->start();
153 template <
typename T>
154 void createAndStart(
const QStringList & a, QAbstractItemView * view ) {
155 (
new T( a, view, &this->controller ) )->start();
158 void closeAndQuit() {
159 const QString app = KGlobal::mainComponent().aboutData()->programName();
160 const int rc = KMessageBox::questionYesNoCancel(
q,
161 i18n(
"%1 may be used by other applications as a service.\n"
162 "You may instead want to close this window without exiting %1.", app ),
164 QLatin1String(
"really-quit-") + app.toLower() );
165 if ( rc == KMessageBox::Cancel )
171 if ( rc == KMessageBox::No )
174 void configureToolbars() {
175 KEditToolBar dlg(
q->factory() );
178 void editKeybindings() {
179 KShortcutsDialog::configure(
q->actionCollection(), KShortcutsEditor::LetterShortcutsAllowed );
183 createAndStart<SelfTestCommand>();
185 void configureBackend();
189 void gnupgLogViewer() {
190 if( !QProcess::startDetached(QLatin1String(
"kwatchgnupg") ) )
191 KMessageBox::error(
q, i18n(
"Could not start the GnuPG Log Viewer (kwatchgnupg). "
192 "Please check your installation." ),
193 i18n(
"Error Starting KWatchGnuPG" ) );
196 void gnupgAdministrativeConsole() {
197 if( !QProcess::startDetached(QLatin1String(
"kgpgconf") ) )
198 KMessageBox::error(
q, i18n(
"Could not start the GnuPG Administrative Console (kgpgconf). "
199 "Please check your installation." ),
200 i18n(
"Error Starting KGpgConf" ) );
203 void slotConfigCommitted();
204 void slotContextMenuRequested( QAbstractItemView *,
const QPoint & p ) {
205 if ( QMenu *
const menu = qobject_cast<QMenu*>(
q->factory()->container( QLatin1String(
"listview_popup"),
q ) ) )
208 kDebug() <<
"no \"listview_popup\" <Menu> in kleopatra's ui.rc file";
211 void aboutGpg4Win() {
212 (
new KAboutApplicationDialog( aboutGpg4WinData(), KAboutApplicationDialog::HideKdeVersion|KAboutApplicationDialog::HideTranslators,
q ) )->show();
218 QAbstractItemView * currentView()
const {
219 return ui.tabWidget.currentView();
235 q->setCentralWidget(&tabWidget);
236 KPIM::ProgressDialog * progressDialog =
new KPIM::ProgressDialog( q->statusBar(),
q );
238 progressDialog->hide();
239 KPIM::StatusbarProgressWidget * statusBarProgressWidget
240 =
new KPIM::StatusbarProgressWidget( progressDialog, q->statusBar() );
242 q->statusBar()->addPermanentWidget( statusBarProgressWidget, 0 );
243 statusBarProgressWidget->show();
248 MainWindow::Private::Private(
MainWindow * qq )
257 AbstractKeyListModel * hierarchicalModel = AbstractKeyListModel::createHierarchicalKeyListModel(
q );
263 controller.setFlatModel( flatModel );
264 controller.setHierarchicalModel( hierarchicalModel );
265 controller.setTabWidget( &ui.tabWidget );
267 ui.tabWidget.setFlatModel( flatModel );
268 ui.tabWidget.setHierarchicalModel( hierarchicalModel );
272 connect( &controller, SIGNAL(message(QString,
int)),
q->statusBar(), SLOT(showMessage(QString,
int)) );
273 connect( &controller, SIGNAL(contextMenuRequested(QAbstractItemView*,QPoint)),
274 q, SLOT(slotContextMenuRequested(QAbstractItemView*,QPoint)) );
276 q->createGUI( QLatin1String(
"kleopatra.rc") );
278 q->setAcceptDrops(
true );
280 q->setAutoSaveSettings();
283 MainWindow::Private::~Private() {}
293 void MainWindow::Private::setupActions() {
295 KActionCollection *
const coll =
q->actionCollection();
297 KAction *
const searchBarAction =
new KAction(
q );
300 ui.tabWidget.connectSearchBar( searchBar );
302 searchBarAction->setDefaultWidget( searchBar );
303 coll->addAction( QLatin1String(
"key_search_bar"), searchBarAction );
309 {
"tools_start_kwatchgnupg", i18n(
"GnuPG Log Viewer"), QString(),
310 "kwatchgnupg",
q, SLOT(gnupgLogViewer()), QString(),
false,
true },
313 {
"tools_start_kgpgconf", i18n(
"GnuPG Administrative Console"), QString(),
314 "kgpgconf",
q, SLOT(gnupgLogViewer()), QString(),
false,
true },
318 {
"configure_backend", i18n(
"Configure GnuPG Backend..."), QString(),
319 0,
q, SLOT(configureBackend()), QString(),
false,
true },
322 {
"settings_self_test", i18n(
"Perform Self-Test"), QString(),
323 0,
q, SLOT(selfTest()), QString(),
false,
true },
326 {
"help_about_gpg4win", i18n(
"About Gpg4win"), QString(),
327 "gpg4win-compact",
q, SLOT(aboutGpg4Win()), QString(),
false,
true },
334 if ( QAction * action = coll->action( QLatin1String(
"configure_backend") ) )
335 action->setMenuRole( QAction::NoRole );
337 KStandardAction::close(
q, SLOT(close()), coll );
338 KStandardAction::quit(
q, SLOT(closeAndQuit()), coll );
339 KStandardAction::configureToolbars(
q, SLOT(configureToolbars()), coll );
340 KStandardAction::keyBindings(
q, SLOT(editKeybindings()), coll );
341 KStandardAction::preferences( qApp, SLOT(openOrRaiseConfigDialog()), coll );
343 q->createStandardStatusBarAction();
344 q->setStandardToolBarMenuEnabled(
true );
346 controller.createActions( coll );
348 ui.tabWidget.createActions( coll );
351 void MainWindow::Private::configureBackend() {
352 Kleo::CryptoConfig *
const config = Kleo::CryptoBackendFactory::instance()->config();
354 KMessageBox::error(
q, i18n(
"Could not configure the cryptography backend (gpgconf tool not found)" ), i18n(
"Configuration Error" ) );
358 Kleo::CryptoConfigDialog dlg( config );
360 const int result = dlg.exec();
366 if ( result == QDialog::Accepted ) {
369 QDBusMessage message =
370 QDBusMessage::createSignal(QString(),
"org.kde.kleo.CryptoConfig",
"changed");
371 QDBusConnection::sessionBus().send(message);
376 void MainWindow::Private::slotConfigCommitted() {
377 controller.updateConfig();
384 if ( d->controller.hasRunningCommands() ) {
385 if ( d->controller.shutdownWarningRequired() ) {
386 const int ret = KMessageBox::warningContinueCancel(
this, i18n(
"There are still some background operations ongoing. "
387 "These will be terminated when closing the window. "
389 i18n(
"Ongoing Background Tasks") );
390 if ( ret != KMessageBox::Continue ) {
395 d->controller.cancelCommands();
396 if ( d->controller.hasRunningCommands() ) {
400 QTimer::singleShot( 100, &ev, SLOT(quit()) );
401 connect( &d->controller, SIGNAL(commandsExecuting(
bool)), &ev, SLOT(quit()) );
403 kWarning( d->controller.hasRunningCommands() )
404 <<
"controller still has commands running, this may crash now...";
409 d->ui.tabWidget.saveViews( KGlobal::config().data() );
410 saveMainWindowSettings( KConfigGroup( KGlobal::config(), autoSaveGroup() ) );
419 KXmlGuiWindow::showEvent( e );
420 if ( d->firstShow ) {
421 d->ui.tabWidget.loadViews( KGlobal::config().data() );
422 d->firstShow =
false;
434 KXmlGuiWindow::hideEvent( e );
439 if ( !files.empty() )
448 if ( urls.size() > 1 && !urls.back().isValid() )
452 std::transform( urls.begin(), end,
453 std::back_inserter( result ),
454 boost::bind( &QUrl::toLocalFile, _1 ) );
455 result.erase( std::remove_if( result.begin(), result.end(),
456 boost::bind( &QString::isEmpty, _1 ) ), result.end() );
470 e->acceptProposedAction();
479 e->setDropAction( Qt::CopyAction );
483 const unsigned int classification =
classify( files );
487 QAction *
const signEncrypt = menu.addAction( i18n(
"Sign/Encrypt...") );
488 QAction *
const decryptVerify = mayBeAnyMessageType( classification ) ? menu.addAction( i18n(
"Decrypt/Verify...") ) : 0 ;
489 if ( signEncrypt || decryptVerify )
492 QAction *
const importCerts = mayBeAnyCertStoreType( classification ) ? menu.addAction( i18n(
"Import Certificates") ) : 0 ;
493 QAction *
const importCRLs = mayBeCertificateRevocationList( classification ) ? menu.addAction( i18n(
"Import CRLs") ) : 0 ;
494 if ( importCerts || importCRLs )
497 if ( !signEncrypt && !decryptVerify && !importCerts && !importCRLs )
500 menu.addAction( i18n(
"Cancel") );
502 const QAction *
const chosen = menu.exec( mapToGlobal( e->pos() ) );
507 if ( chosen == signEncrypt )
509 else if ( chosen == decryptVerify )
511 else if ( chosen == importCerts )
513 else if ( chosen == importCRLs )
522 KXmlGuiWindow::readProperties(cg);
523 savedGeometry = cg.readEntry(
"savedGeometry", QByteArray() );
528 if (! cg.readEntry<
bool>(
"hidden",
false))
535 KXmlGuiWindow::saveProperties( cg );
536 cg.writeEntry(
"hidden", isHidden() );
540 cg.writeEntry(
"savedGeometry", saveGeometry() );
544 #include "moc_mainwindow_desktop.cpp"
static const char * flags[]
void showEvent(QShowEvent *e)
void dropEvent(QDropEvent *)
static KGuiItem KStandardGuiItem_quit()
static QStringList extract_local_files(const QMimeData *data)
void hideEvent(QHideEvent *e)
void dragEnterEvent(QDragEnterEvent *)
void importCertificatesFromFile(const QStringList &files)
void readProperties(const KConfigGroup &cg)
void closeEvent(QCloseEvent *e)
void saveProperties(KConfigGroup &cg)
unsigned int classify(const QString &filename)
static bool can_decode_local_files(const QMimeData *data)
static KGuiItem KStandardGuiItem_close()
void make_actions_from_data(const action_data *data, unsigned int numData, KActionCollection *collection)
MainWindow(QWidget *parent=0, Qt::WindowFlags flags=0)