• Skip to content
  • Skip to link menu
KDE API Reference
  • KDE API Reference
  • kdesdk API Reference
  • KDE Home
  • Contact Us
 

kompare

  • sources
  • kde-4.14
  • kdesdk
  • kompare
  • komparepart
kompare_part.cpp
Go to the documentation of this file.
1 /***************************************************************************
2  kompare_part.cpp
3  ----------------
4  begin : Sun Mar 4 2001
5  Copyright 2001-2005,2009 Otto Bruggeman <bruggie@gmail.com>
6  Copyright 2001-2003 John Firebaugh <jfirebaugh@kde.org>
7  Copyright 2004 Jeff Snyder <jeff@caffeinated.me.uk>
8  Copyright 2007-2011 Kevin Kofler <kevin.kofler@chello.at>
9  Copyright 2012 Jean-Nicolas Artaud <jeannicolasartaud@gmail.com>
10 ****************************************************************************/
11 
12 /***************************************************************************
13 **
14 ** This program is free software; you can redistribute it and/or modify
15 ** it under the terms of the GNU General Public License as published by
16 ** the Free Software Foundation; either version 2 of the License, or
17 ** (at your option) any later version.
18 **
19 ***************************************************************************/
20 
21 #include "kompare_part.h"
22 
23 #include <QtGui/QLayout>
24 #include <QtGui/QWidget>
25 #include <QPainter>
26 #include <QPrinter>
27 #include <QPrintDialog>
28 #include <QPrintPreviewDialog>
29 
30 #include <kaboutdata.h>
31 #include <kaction.h>
32 #include <kactioncollection.h>
33 #include <kapplication.h>
34 #include <kcomponentdata.h>
35 #include <kdebug.h>
36 #include <kdeprintdialog.h>
37 #include <kfiledialog.h>
38 #include <klocale.h>
39 #include <kmessagebox.h>
40 #include <kstandardaction.h>
41 #include <kstandarddirs.h>
42 #include <kstandardshortcut.h>
43 #include <ktemporaryfile.h>
44 #include <ktempdir.h>
45 
46 #include <kio/netaccess.h>
47 #include <kglobal.h>
48 
49 #include "diffmodel.h"
50 #include "komparelistview.h"
51 #include "kompareconnectwidget.h"
52 #include "diffsettings.h"
53 #include "viewsettings.h"
54 #include "kompareprefdlg.h"
55 #include "komparesaveoptionswidget.h"
56 #include "komparesplitter.h"
57 #include "kompareview.h"
58 
59 K_PLUGIN_FACTORY( KomparePartFactory, registerPlugin<KomparePart>(); )
60 K_EXPORT_PLUGIN( KomparePartFactory )
61 
62 ViewSettings* KomparePart::m_viewSettings = 0L;
63 DiffSettings* KomparePart::m_diffSettings = 0L;
64 
65 KomparePart::KomparePart( QWidget *parentWidget, QObject *parent, const QVariantList & /*args*/ ) :
66  KParts::ReadWritePart(parent),
67  m_tempDiff( 0 ),
68  m_info()
69 {
70  if( !m_viewSettings ) {
71  m_viewSettings = new ViewSettings( 0 );
72  }
73  if( !m_diffSettings ) {
74  m_diffSettings = new DiffSettings( 0 );
75  }
76 
77  readProperties( KGlobal::config().data() );
78 
79  m_view = new KompareView ( m_viewSettings, parentWidget );
80  setWidget( m_view );
81  m_splitter = m_view->splitter();
82 
83  // This creates the "Model creator" and connects the signals and slots
84  m_modelList = new Diff2::KompareModelList( m_diffSettings, m_splitter, this, "komparemodellist" , KParts::ReadWritePart::isReadWrite());
85 
86  Q_FOREACH(QAction* action, m_modelList->actionCollection()->actions())
87  {
88  actionCollection()->addAction(action->objectName(), action);
89  }
90  connect( m_modelList, SIGNAL(status( Kompare::Status )),
91  this, SLOT(slotSetStatus( Kompare::Status )) );
92  connect( m_modelList, SIGNAL(setStatusBarModelInfo( int, int, int, int, int )),
93  this, SIGNAL(setStatusBarModelInfo( int, int, int, int, int )) );
94  connect( m_modelList, SIGNAL(error( QString )),
95  this, SLOT(slotShowError( QString )) );
96  connect( m_modelList, SIGNAL(applyAllDifferences( bool )),
97  this, SLOT(updateActions()) );
98  connect( m_modelList, SIGNAL(applyDifference( bool )),
99  this, SLOT(updateActions()) );
100  connect( m_modelList, SIGNAL(applyAllDifferences( bool )),
101  this, SIGNAL(appliedChanged()) );
102  connect( m_modelList, SIGNAL(applyDifference( bool )),
103  this, SIGNAL(appliedChanged()) );
104  connect( m_modelList, SIGNAL(updateActions()), this, SLOT(updateActions()) );
105 
106  // This is the stuff to connect the "interface" of the kompare part to the model inside
107  connect( m_modelList, SIGNAL(modelsChanged(const Diff2::DiffModelList*)),
108  this, SIGNAL(modelsChanged(const Diff2::DiffModelList*)) );
109 
110  connect( m_modelList, SIGNAL(setSelection(const Diff2::DiffModel*, const Diff2::Difference*)),
111  this, SIGNAL(setSelection(const Diff2::DiffModel*, const Diff2::Difference*)) );
112  connect( this, SIGNAL(selectionChanged(const Diff2::DiffModel*, const Diff2::Difference*)),
113  m_modelList, SLOT(slotSelectionChanged(const Diff2::DiffModel*, const Diff2::Difference*)) );
114 
115  connect( m_modelList, SIGNAL(setSelection(const Diff2::Difference*)),
116  this, SIGNAL(setSelection(const Diff2::Difference*)) );
117  connect( this, SIGNAL(selectionChanged(const Diff2::Difference*)),
118  m_modelList, SLOT(slotSelectionChanged(const Diff2::Difference*)) );
119 
120  connect( m_modelList, SIGNAL(applyDifference(bool)),
121  this, SIGNAL(applyDifference(bool)) );
122  connect( m_modelList, SIGNAL(applyAllDifferences(bool)),
123  this, SIGNAL(applyAllDifferences(bool)) );
124  connect( m_modelList, SIGNAL(applyDifference(const Diff2::Difference*, bool)),
125  this, SIGNAL(applyDifference(const Diff2::Difference*, bool)) );
126  connect( m_modelList, SIGNAL(diffString(const QString&)),
127  this, SIGNAL(diffString(const QString&)) );
128 
129  connect( this, SIGNAL(kompareInfo(Kompare::Info*)), m_modelList, SLOT(slotKompareInfo(Kompare::Info*)) );
130 
131  // Here we connect the splitter to the modellist
132  connect( m_modelList, SIGNAL(setSelection(const Diff2::DiffModel*, const Diff2::Difference*)),
133  m_splitter, SLOT(slotSetSelection(const Diff2::DiffModel*, const Diff2::Difference*)) );
134 // connect( m_splitter, SIGNAL(selectionChanged(const Diff2::Difference*, const Diff2::Difference*)),
135 // m_modelList, SLOT(slotSelectionChanged(const Diff2::Difference*, const Diff2::Difference*)) );
136  connect( m_modelList, SIGNAL(setSelection(const Diff2::Difference*)),
137  m_splitter, SLOT(slotSetSelection(const Diff2::Difference*)) );
138  connect( m_splitter, SIGNAL(selectionChanged(const Diff2::Difference*)),
139  m_modelList, SLOT(slotSelectionChanged(const Diff2::Difference*)) );
140 
141  connect( m_modelList, SIGNAL(applyDifference(bool)),
142  m_splitter, SLOT(slotApplyDifference(bool)) );
143  connect( m_modelList, SIGNAL(applyAllDifferences(bool)),
144  m_splitter, SLOT(slotApplyAllDifferences(bool)) );
145  connect( m_modelList, SIGNAL(applyDifference(const Diff2::Difference*, bool)),
146  m_splitter, SLOT(slotApplyDifference(const Diff2::Difference*, bool)) );
147  connect( this, SIGNAL(configChanged()), m_splitter, SIGNAL(configChanged()) );
148 
149  setupActions();
150 
151  // set our XML-UI resource file
152  setXMLFile( "komparepartui.rc" );
153 
154  // we are read-write by default -> uhm what if we are opened by lets say konq in RO mode ?
155  // Then we should not be doing this...
156  setReadWrite( true );
157 
158  // we are not modified since we haven't done anything yet
159  setModified( false );
160 }
161 
162 KomparePart::~KomparePart()
163 {
164  // This is the only place allowed to call cleanUpTemporaryFiles
165  // because before there might still be a use for them (when swapping)
166  cleanUpTemporaryFiles();
167 }
168 
169 void KomparePart::setupActions()
170 {
171  // create our actions
172 
173  m_saveAll = actionCollection()->addAction("file_save_all", this, SLOT(saveAll()));
174  m_saveAll->setIcon(KIcon("document-save-all"));
175  m_saveAll->setText(i18n("Save &All"));
176  m_saveDiff = actionCollection()->addAction("file_save_diff", this, SLOT(saveDiff()));
177  m_saveDiff->setText(i18n("Save &Diff..."));
178  m_swap = actionCollection()->addAction("file_swap", this, SLOT(slotSwap()));
179  m_swap->setText(i18n("Swap Source with Destination"));
180  m_diffStats = actionCollection()->addAction("file_diffstats", this, SLOT(slotShowDiffstats()));
181  m_diffStats->setText(i18n("Show Statistics"));
182  m_diffRefresh = actionCollection()->addAction("file_refreshdiff", this, SLOT(slotRefreshDiff()));
183  m_diffRefresh->setIcon(KIcon("view-refresh"));
184  m_diffRefresh->setText(i18n("Refresh Diff"));
185  m_diffRefresh->setShortcut(KStandardShortcut::reload());
186 
187  m_print = actionCollection()->addAction(KStandardAction::Print, this, SLOT( slotFilePrint() ));
188  m_printPreview = actionCollection()->addAction(KStandardAction::PrintPreview, this, SLOT( slotFilePrintPreview() ));
189  KStandardAction::preferences(this, SLOT(optionsPreferences()), actionCollection());
190 }
191 
192 void KomparePart::updateActions()
193 {
194  m_saveAll->setEnabled ( m_modelList->hasUnsavedChanges() );
195  m_saveDiff->setEnabled ( m_modelList->mode() == Kompare::ComparingFiles || m_modelList->mode() == Kompare::ComparingDirs );
196  m_swap->setEnabled ( m_modelList->mode() == Kompare::ComparingFiles || m_modelList->mode() == Kompare::ComparingDirs );
197  m_diffRefresh->setEnabled ( m_modelList->mode() == Kompare::ComparingFiles || m_modelList->mode() == Kompare::ComparingDirs );
198  m_diffStats->setEnabled ( m_modelList->modelCount() > 0 );
199  m_print->setEnabled ( m_modelList->modelCount() > 0 ); // If modellist has models then we have something to print, it's that simple.
200  m_printPreview->setEnabled( m_modelList );
201 }
202 
203 void KomparePart::setEncoding( const QString& encoding )
204 {
205  kDebug(8103) << "Encoding: " << encoding << endl;
206  m_modelList->setEncoding( encoding );
207 }
208 
209 bool KomparePart::openDiff( const KUrl& url )
210 {
211  kDebug(8103) << "Url = " << url.url() << endl;
212 
213  m_info.mode = Kompare::ShowingDiff;
214  m_info.source = url;
215  bool result = false;
216  fetchURL( url, true );
217 
218  emit kompareInfo( &m_info );
219 
220  if ( !m_info.localSource.isEmpty() )
221  {
222  kDebug(8103) << "Download succeeded " << endl;
223  result = m_modelList->openDiff( m_info.localSource );
224  updateActions();
225  updateCaption();
226  updateStatus();
227  }
228  else
229  {
230  kDebug(8103) << "Download failed !" << endl;
231  }
232 
233  return result;
234 }
235 
236 bool KomparePart::openDiff( const QString& diffOutput )
237 {
238  bool value = false;
239 
240  m_info.mode = Kompare::ShowingDiff;
241 
242  emit kompareInfo( &m_info );
243 
244  if ( m_modelList->parseAndOpenDiff( diffOutput ) == 0 )
245  {
246  value = true;
247  updateActions();
248  updateCaption();
249  updateStatus();
250  }
251 
252  return value;
253 }
254 
255 bool KomparePart::openDiff3( const KUrl& diff3Url )
256 {
257  // FIXME: Implement this !!!
258  kDebug(8103) << "Not implemented yet. Filename is: " << diff3Url.prettyUrl() << endl;
259  return false;
260 }
261 
262 bool KomparePart::openDiff3( const QString& diff3Output )
263 {
264  // FIXME: Implement this !!!
265  kDebug(8103) << "Not implemented yet. diff3 output is: " << endl;
266  kDebug(8103) << diff3Output << endl;
267  return false;
268 }
269 
270 bool KomparePart::exists( const QString& url )
271 {
272  QFileInfo fi( url );
273  return fi.exists();
274 }
275 
276 bool KomparePart::fetchURL( const KUrl& url, bool addToSource )
277 {
278  // Default value if there is an error is "", we rely on it!
279  QString tempFileName( "" );
280  // Only in case of error do we set result to false, don't forget!!
281  bool result = true;
282  KTempDir* tmpDir = 0;
283 
284  if ( !url.isLocalFile() )
285  {
286  KIO::UDSEntry node;
287  KIO::NetAccess::stat( url, node, widget() );
288  if ( !node.isDir() )
289  {
290  if ( ! KIO::NetAccess::download( url, tempFileName, widget() ) )
291  {
292  slotShowError( i18n( "<qt>The URL <b>%1</b> cannot be downloaded.</qt>", url.prettyUrl() ) );
293  tempFileName = ""; // Not sure if download has already touched this tempFileName when there is an error
294  result = false;
295  }
296  }
297  else
298  {
299  tmpDir = new KTempDir(KStandardDirs::locateLocal("tmp", "kompare"));
300  tmpDir->setAutoRemove( true ); // Yes this is the default but just to make sure
301  if ( ! KIO::NetAccess::dircopy( url, KUrl( tmpDir->name() ), widget() ) )
302  {
303  slotShowError( i18n( "<qt>The URL <b>%1</b> cannot be downloaded.</qt>", url.prettyUrl() ) );
304  delete tmpDir;
305  tmpDir = 0;
306  result = false;
307  }
308  else
309  {
310  tempFileName = tmpDir->name();
311  kDebug(8101) << "tempFileName = " << tempFileName << endl;
312  // If a directory is copied into KTempDir then the directory in
313  // here is what I need to add to tempFileName
314  QDir dir( tempFileName );
315  QStringList entries = dir.entryList( QDir::Dirs | QDir::NoDotAndDotDot );
316  if ( entries.size() == 1 ) // More than 1 entry in here means big problems!!!
317  {
318  if ( !tempFileName.endsWith( '/' ) )
319  tempFileName += '/';
320  tempFileName += entries.at( 0 );
321  tempFileName += '/';
322  }
323  else
324  {
325  kDebug(8101) << "Yikes, nothing downloaded?" << endl;
326  delete tmpDir;
327  tmpDir = 0;
328  tempFileName = "";
329  result = false;
330  }
331  }
332  }
333  }
334  else
335  {
336  // is Local already, check if exists
337  if ( exists( url.toLocalFile() ) )
338  tempFileName = url.toLocalFile();
339  else
340  {
341  slotShowError( i18n( "<qt>The URL <b>%1</b> does not exist on your system.</qt>", url.prettyUrl() ) );
342  result = false;
343  }
344  }
345 
346  if ( addToSource )
347  {
348  m_info.localSource = tempFileName;
349  m_info.sourceKTempDir = tmpDir;
350  }
351  else
352  {
353  m_info.localDestination = tempFileName;
354  m_info.destinationKTempDir = tmpDir;
355  }
356 
357  return result;
358 }
359 
360 void KomparePart::cleanUpTemporaryFiles()
361 {
362  kDebug(8101) << "Cleaning temporary files." << endl;
363  if ( !m_info.localSource.isEmpty() )
364  {
365  if ( m_info.sourceKTempDir == 0 )
366  KIO::NetAccess::removeTempFile( m_info.localSource );
367  else
368  {
369  delete m_info.sourceKTempDir;
370  m_info.sourceKTempDir = 0;
371  }
372  m_info.localSource = "";
373  }
374  if ( !m_info.localDestination.isEmpty() )
375  {
376  if ( m_info.destinationKTempDir == 0 )
377  KIO::NetAccess::removeTempFile( m_info.localDestination );
378  else
379  {
380  delete m_info.destinationKTempDir;
381  m_info.destinationKTempDir = 0;
382  }
383  m_info.localDestination = "";
384  }
385 }
386 
387 void KomparePart::compare( const KUrl& source, const KUrl& destination )
388 {
389  // FIXME: This is silly, i can use NetAccess::stat to figure out what it is and not
390  // wait until i am in the modellist to determine the mode we're supposed to be in.
391  // That should make the code more readable
392  // I should store the KTempDir(s)/File(s) in the Info struct as well and delete it at the right time
393  m_info.source = source;
394  m_info.destination = destination;
395 
396  // FIXME: (Not urgent) But turn this into an enum, for now i cant find a nice name for the enum that has Source and Destination as values
397  // For now we do not do error checking, user has already been notified and if the localString is empty then we dont diff
398  fetchURL( source, true );
399  fetchURL( destination, false );
400 
401  emit kompareInfo( &m_info );
402 
403  compareAndUpdateAll();
404 }
405 
406 void KomparePart::compareFileString( const KUrl & sourceFile, const QString & destination)
407 {
408  //Set the modeto specify that the source is a file, and the destination is a string
409  m_info.mode = Kompare::ComparingFileString;
410 
411  m_info.source = sourceFile;
412  m_info.localDestination = destination;
413 
414  fetchURL(sourceFile, true);
415 
416  emit kompareInfo( &m_info );
417 
418  compareAndUpdateAll();
419 }
420 
421 void KomparePart::compareStringFile( const QString & source, const KUrl & destinationFile)
422 {
423  //Set the modeto specify that the source is a file, and the destination is a string
424  m_info.mode = Kompare::ComparingStringFile;
425 
426  m_info.localSource = source;
427  m_info.destination = destinationFile;
428 
429  fetchURL(destinationFile, false);
430 
431  emit kompareInfo( &m_info );
432 
433  compareAndUpdateAll();
434 }
435 
436 void KomparePart::compareFiles( const KUrl& sourceFile, const KUrl& destinationFile )
437 {
438  m_info.mode = Kompare::ComparingFiles;
439 
440  m_info.source = sourceFile;
441  m_info.destination = destinationFile;
442 
443  // FIXME: (Not urgent) But turn this into an enum, for now i cant find a nice name for the enum that has Source and Destination as values
444  // For now we do not do error checking, user has already been notified and if the localString is empty then we dont diff
445  fetchURL( sourceFile, true );
446  fetchURL( destinationFile, false );
447 
448  emit kompareInfo( &m_info );
449 
450  compareAndUpdateAll();
451 }
452 
453 void KomparePart::compareDirs( const KUrl& sourceDirectory, const KUrl& destinationDirectory )
454 {
455  m_info.mode = Kompare::ComparingDirs;
456 
457  m_info.source = sourceDirectory;
458  m_info.destination = destinationDirectory;
459 
460  fetchURL( sourceDirectory, true );
461  fetchURL( destinationDirectory, false );
462 
463  emit kompareInfo( &m_info );
464 
465  compareAndUpdateAll();
466 }
467 
468 void KomparePart::compare3Files( const KUrl& /*originalFile*/, const KUrl& /*changedFile1*/, const KUrl& /*changedFile2*/ )
469 {
470  // FIXME: actually implement this some day :)
471  updateActions();
472  updateCaption();
473  updateStatus();
474 }
475 
476 void KomparePart::openFileAndDiff( const KUrl& file, const KUrl& diffFile )
477 {
478  m_info.source = file;
479  m_info.destination = diffFile;
480 
481  fetchURL( file, true );
482  fetchURL( diffFile, false );
483  m_info.mode = Kompare::BlendingFile;
484 
485  emit kompareInfo( &m_info );
486 
487  compareAndUpdateAll();
488 }
489 
490 void KomparePart::openDirAndDiff ( const KUrl& dir, const KUrl& diffFile )
491 {
492  m_info.source = dir;
493  m_info.destination = diffFile;
494 
495  fetchURL( dir, true );
496  fetchURL( diffFile, false );
497  m_info.mode = Kompare::BlendingDir;
498 
499  emit kompareInfo( &m_info );
500 
501  if ( !m_info.localSource.isEmpty() && !m_info.localDestination.isEmpty() )
502  {
503  m_modelList->openDirAndDiff();
504  //Must this be in here? couldn't we use compareAndUpdateAll as well?
505  updateActions();
506  updateCaption();
507  updateStatus();
508  }
509 }
510 
511 bool KomparePart::openFile()
512 {
513  // This is called from openURL
514  // This is a little inefficient but i will do it anyway
515  openDiff( url() );
516  return true;
517 }
518 
519 bool KomparePart::saveAll()
520 {
521  bool result = m_modelList->saveAll();
522  updateActions();
523  updateCaption();
524  updateStatus();
525  return result;
526 }
527 
528 void KomparePart::saveDiff()
529 {
530  KDialog dlg( widget() );
531  dlg.setObjectName( "save_options" );
532  dlg.setModal( true );
533  dlg.setWindowTitle( i18n("Diff Options") );
534  dlg.setButtons( KDialog::Ok|KDialog::Cancel );
535  KompareSaveOptionsWidget* w = new KompareSaveOptionsWidget(
536  m_info.localSource,
537  m_info.localDestination,
538  m_diffSettings, &dlg );
539  dlg.setMainWidget( w );
540  dlg.setButtonGuiItem( KDialog::Ok, KStandardGuiItem::save() );
541 
542  if( dlg.exec() ) {
543  w->saveOptions();
544  KSharedConfig::Ptr config = componentData().config();
545  saveProperties( config.data() );
546  config->sync();
547 
548  while ( 1 )
549  {
550  KUrl url = KFileDialog::getSaveUrl( m_info.destination.url(),
551  i18n("*.diff *.dif *.patch|Patch Files"), widget(), i18n( "Save .diff" ) );
552  if ( KIO::NetAccess::exists( url, KIO::NetAccess::DestinationSide, widget() ) )
553  {
554  int result = KMessageBox::warningYesNoCancel( widget(), i18n("The file exists or is write-protected; do you want to overwrite it?"), i18n("File Exists"), KGuiItem(i18n("Overwrite")), KGuiItem(i18n("Do Not Overwrite")) );
555  if ( result == KMessageBox::Cancel )
556  {
557  break;
558  }
559  else if ( result == KMessageBox::No )
560  {
561  continue;
562  }
563  else
564  {
565  kDebug(8103) << "URL = " << url.prettyUrl() << endl;
566  kDebug(8103) << "Directory = " << w->directory() << endl;
567  kDebug(8103) << "DiffSettings = " << m_diffSettings << endl;
568 
569  m_modelList->saveDiff( url.url(), w->directory(), m_diffSettings );
570  break;
571  }
572  }
573  else
574  {
575  kDebug(8103) << "URL = " << url.prettyUrl() << endl;
576  kDebug(8103) << "Directory = " << w->directory() << endl;
577  kDebug(8103) << "DiffSettings = " << m_diffSettings << endl;
578 
579  m_modelList->saveDiff( url.url(), w->directory(), m_diffSettings );
580  break;
581  }
582  }
583  }
584 }
585 
586 void KomparePart::slotFilePrint()
587 {
588  QPrinter printer;
589  printer.setOrientation( QPrinter::Landscape );
590  QPrintDialog* dlg = KdePrint::createPrintDialog( &printer, m_splitter );
591 
592  if ( dlg->exec() == QDialog::Accepted )
593  {
594  // do some printing in qprinter
595  slotPaintRequested( &printer );
596  }
597 
598  delete dlg;
599 }
600 
601 void KomparePart::slotFilePrintPreview()
602 {
603  QPrinter printer;
604  printer.setOrientation( QPrinter::Landscape );
605  QPrintPreviewDialog dlg( &printer );
606 
607  connect( &dlg, SIGNAL(paintRequested(QPrinter*)), this, SLOT(slotPaintRequested(QPrinter*)) );
608 
609  dlg.exec();
610 }
611 
612 void KomparePart::slotPaintRequested( QPrinter* printer )
613 {
614  kDebug(8103) << "Now paint something..." << endl;
615  QPainter p;
616  p.begin( printer );
617 
618  QSize widgetWidth = m_view->size();
619  kDebug(8103) << "printer.width() = " << printer->width() << endl;
620  kDebug(8103) << "widgetWidth.width() = " << widgetWidth.width() << endl;
621  qreal factor = ((qreal)printer->width())/((qreal)widgetWidth.width());
622 
623  kDebug(8103) << "factor = " << factor << endl;
624 
625  p.scale( factor, factor );
626  m_view->render( &p );
627 
628  p.end();
629  kDebug(8103) << "Done painting something..." << endl;
630 }
631 
632 KAboutData* KomparePart::createAboutData()
633 {
634  KAboutData *about = new KAboutData("kompare", 0, ki18n("KomparePart"), "4.0");
635  about->addAuthor(ki18n("John Firebaugh"), ki18n("Author"), "jfirebaugh@kde.org");
636  about->addAuthor(ki18n("Otto Bruggeman"), ki18n("Author"), "bruggie@gmail.com" );
637  about->addAuthor(ki18n("Kevin Kofler"), ki18n("Author"), "kevin.kofler@chello.at" );
638  return about;
639 }
640 
641 void KomparePart::slotSetStatus( enum Kompare::Status status )
642 {
643  updateActions();
644 
645  switch( status ) {
646  case Kompare::RunningDiff:
647  emit setStatusBarText( i18n( "Running diff..." ) );
648  break;
649  case Kompare::Parsing:
650  emit setStatusBarText( i18n( "Parsing diff output..." ) );
651  break;
652  case Kompare::FinishedParsing:
653  updateStatus();
654  break;
655  case Kompare::FinishedWritingDiff:
656  updateStatus();
657  emit diffURLChanged();
658  break;
659  default:
660  break;
661  }
662 }
663 
664 void KomparePart::updateCaption()
665 {
666  QString source = m_info.source.prettyUrl();
667  QString destination = m_info.destination.prettyUrl();
668 
669  QString text;
670 
671  switch ( m_info.mode )
672  {
673  case Kompare::ComparingFiles :
674  case Kompare::ComparingDirs :
675  case Kompare::BlendingFile :
676  case Kompare::BlendingDir :
677  text = source + " -- " + destination; // no need to translate this " -- "
678  break;
679  case Kompare::ShowingDiff :
680  text = source;
681  break;
682  default:
683  break;
684  }
685 
686  emit setWindowCaption( text );
687 }
688 
689 void KomparePart::updateStatus()
690 {
691  QString source = m_info.source.prettyUrl();
692  QString destination = m_info.destination.prettyUrl();
693 
694  QString text;
695 
696  switch ( m_info.mode )
697  {
698  case Kompare::ComparingFiles :
699  text = i18n( "Comparing file %1 with file %2" ,
700  source ,
701  destination );
702  break;
703  case Kompare::ComparingDirs :
704  text = i18n( "Comparing files in %1 with files in %2" ,
705  source ,
706  destination );
707  break;
708  case Kompare::ShowingDiff :
709  text = i18n( "Viewing diff output from %1", source );
710  break;
711  case Kompare::BlendingFile :
712  text = i18n( "Blending diff output from %1 into file %2" ,
713  source ,
714  destination );
715  break;
716  case Kompare::BlendingDir :
717  text = i18n( "Blending diff output from %1 into folder %2" ,
718  m_info.source.prettyUrl() ,
719  m_info.destination.prettyUrl() );
720  break;
721  default:
722  break;
723  }
724 
725  emit setStatusBarText( text );
726 }
727 
728 void KomparePart::compareAndUpdateAll()
729 {
730  if ( !m_info.localSource.isEmpty() && !m_info.localDestination.isEmpty() )
731  {
732  switch(m_info.mode)
733  {
734  default:
735  case Kompare::UnknownMode:
736  m_modelList->compare();
737  break;
738 
739  case Kompare::ComparingStringFile:
740  case Kompare::ComparingFileString:
741  case Kompare::ComparingFiles:
742  case Kompare::ComparingDirs:
743  m_modelList->compare(m_info.mode);
744  break;
745 
746  case Kompare::BlendingFile:
747  m_modelList->openFileAndDiff();
748  break;
749  }
750  updateCaption();
751  updateStatus();
752  }
753  updateActions();
754 }
755 
756 void KomparePart::slotShowError( QString error )
757 {
758  KMessageBox::error( widget(), error );
759 }
760 
761 void KomparePart::slotSwap()
762 {
763  if ( m_modelList->hasUnsavedChanges() )
764  {
765  int query = KMessageBox::warningYesNoCancel
766  (
767  widget(),
768  i18n( "You have made changes to the destination file(s).\n"
769  "Would you like to save them?" ),
770  i18n( "Save Changes?" ),
771  KStandardGuiItem::save(),
772  KStandardGuiItem::discard()
773  );
774 
775  if ( query == KMessageBox::Yes )
776  m_modelList->saveAll();
777 
778  if ( query == KMessageBox::Cancel )
779  return; // Abort prematurely so no swapping
780  }
781 
782  // Swap the info in the Kompare::Info struct
783  m_info.swapSourceWithDestination();
784 
785  // Update window caption and statusbar text
786  updateCaption();
787  updateStatus();
788 
789  m_modelList->swap();
790 }
791 
792 void KomparePart::slotRefreshDiff()
793 {
794  if ( m_modelList->hasUnsavedChanges() )
795  {
796  int query = KMessageBox::warningYesNoCancel
797  (
798  widget(),
799  i18n( "You have made changes to the destination file(s).\n"
800  "Would you like to save them?" ),
801  i18n( "Save Changes?" ),
802  KStandardGuiItem::save(),
803  KStandardGuiItem::discard()
804  );
805 
806  if ( query == KMessageBox::Cancel )
807  return; // Abort prematurely so no refreshing
808 
809  if ( query == KMessageBox::Yes )
810  m_modelList->saveAll();
811  }
812 
813  // For this to work properly you have to refetch the files from their (remote) locations
814  cleanUpTemporaryFiles();
815  fetchURL( m_info.source, true );
816  fetchURL( m_info.destination, false );
817  m_modelList->refresh();
818 }
819 
820 void KomparePart::slotShowDiffstats( void )
821 {
822  // Fetch all the args needed for komparestatsmessagebox
823  // oldfile, newfile, diffformat, noofhunks, noofdiffs
824 
825  QString oldFile;
826  QString newFile;
827  QString diffFormat;
828  int filesInDiff;
829  int noOfHunks;
830  int noOfDiffs;
831 
832  oldFile = m_modelList->selectedModel() ? m_modelList->selectedModel()->sourceFile() : QString( "" );
833  newFile = m_modelList->selectedModel() ? m_modelList->selectedModel()->destinationFile() : QString( "" );
834 
835  if ( m_modelList->selectedModel() )
836  {
837  switch( m_info.format ) {
838  case Kompare::Unified :
839  diffFormat = i18n( "Unified" );
840  break;
841  case Kompare::Context :
842  diffFormat = i18n( "Context" );
843  break;
844  case Kompare::RCS :
845  diffFormat = i18n( "RCS" );
846  break;
847  case Kompare::Ed :
848  diffFormat = i18n( "Ed" );
849  break;
850  case Kompare::Normal :
851  diffFormat = i18n( "Normal" );
852  break;
853  case Kompare::UnknownFormat :
854  default:
855  diffFormat = i18n( "Unknown" );
856  break;
857  }
858  }
859  else
860  {
861  diffFormat = "";
862  }
863 
864  filesInDiff = m_modelList->modelCount();
865 
866  noOfHunks = m_modelList->selectedModel() ? m_modelList->selectedModel()->hunkCount() : 0;
867  noOfDiffs = m_modelList->selectedModel() ? m_modelList->selectedModel()->differenceCount() : 0;
868 
869  if ( m_modelList->modelCount() == 0 ) { // no diff loaded yet
870  KMessageBox::information( 0L, i18n(
871  "No diff file, or no 2 files have been diffed. "
872  "Therefore no stats are available."),
873  i18n("Diff Statistics"), QString(), 0 );
874  }
875  else if ( m_modelList->modelCount() == 1 ) { // 1 file in diff, or 2 files compared
876  KMessageBox::information( 0L, i18n(
877  "Statistics:\n"
878  "\n"
879  "Old file: %1\n"
880  "New file: %2\n"
881  "\n"
882  "Format: %3\n"
883  "Number of hunks: %4\n"
884  "Number of differences: %5",
885  oldFile, newFile, diffFormat,
886  noOfHunks, noOfDiffs),
887  i18n("Diff Statistics"), QString(), 0 );
888  } else { // more than 1 file in diff, or 2 directories compared
889  KMessageBox::information( 0L, ki18n(
890  "Statistics:\n"
891  "\n"
892  "Number of files in diff file: %1\n"
893  "Format: %2\n"
894  "\n"
895  "Current old file: %3\n"
896  "Current new file: %4\n"
897  "\n"
898  "Number of hunks: %5\n"
899  "Number of differences: %6")
900  .subs(filesInDiff).subs(diffFormat).subs(oldFile)
901  .subs(newFile).subs(noOfHunks).subs(noOfDiffs)
902  .toString(),
903  i18n("Diff Statistics"), QString(), 0 );
904  }
905 }
906 
907 bool KomparePart::queryClose()
908 {
909  if ( !m_modelList->hasUnsavedChanges() ) return true;
910 
911  int query = KMessageBox::warningYesNoCancel
912  (
913  widget(),
914  i18n("You have made changes to the destination file(s).\n"
915  "Would you like to save them?" ),
916  i18n( "Save Changes?" ),
917  KStandardGuiItem::save(),
918  KStandardGuiItem::discard()
919  );
920 
921  if( query == KMessageBox::Cancel )
922  return false;
923 
924  if( query == KMessageBox::Yes )
925  return m_modelList->saveAll();
926 
927  return true;
928 }
929 
930 int KomparePart::readProperties( KConfig *config )
931 {
932  m_viewSettings->loadSettings( config );
933  m_diffSettings->loadSettings( config );
934  emit configChanged();
935  return 0;
936 }
937 
938 int KomparePart::saveProperties( KConfig *config )
939 {
940  m_viewSettings->saveSettings( config );
941  m_diffSettings->saveSettings( config );
942  return 0;
943 }
944 
945 void KomparePart::optionsPreferences()
946 {
947  // show preferences
948  KomparePrefDlg pref( m_viewSettings, m_diffSettings );
949 
950  connect( &pref, SIGNAL(configChanged()), this, SIGNAL(configChanged()) );
951 
952  if ( pref.exec() )
953  emit configChanged();
954 }
955 
956 #include "kompare_part.moc"
KompareSaveOptionsWidget::directory
QString directory() const
Definition: komparesaveoptionswidget.cpp:97
KomparePart::createAboutData
static KAboutData * createAboutData()
Definition: kompare_part.cpp:632
QWidget
QSize::width
int width() const
QPainter::end
bool end()
KomparePart::setEncoding
virtual void setEncoding(const QString &encoding)
Reimplementing this because this one knows more about the real part then the interface.
Definition: kompare_part.cpp:203
QPrinter
KomparePart::updateCaption
void updateCaption()
Definition: kompare_part.cpp:664
QPainter::scale
void scale(qreal sx, qreal sy)
KomparePrefDlg
Definition: kompareprefdlg.h:29
KomparePart::compareAndUpdateAll
void compareAndUpdateAll()
Definition: kompare_part.cpp:728
QList::at
const T & at(int i) const
KomparePart::openDiff
virtual bool openDiff(const KUrl &diffUrl)
Open and parse the diff file at diffUrl.
Definition: kompare_part.cpp:209
QDialog::exec
int exec()
komparesplitter.h
KomparePart::slotRefreshDiff
void slotRefreshDiff()
Definition: kompare_part.cpp:792
KomparePart
This is a "Part".
Definition: kompare_part.h:58
KomparePart::openFile
virtual bool openFile()
This is the method that gets called when the file is opened, when using openURL( const KUrl& ) or in ...
Definition: kompare_part.cpp:511
kompare_part.h
KomparePart::slotFilePrintPreview
void slotFilePrintPreview()
Definition: kompare_part.cpp:601
QList::size
int size() const
KompareSaveOptionsWidget::saveOptions
void saveOptions()
Definition: komparesaveoptionswidget.cpp:206
QPaintDevice::width
int width() const
KomparePart::openFileAndDiff
virtual void openFileAndDiff(const KUrl &file, const KUrl &diffFile)
This will show the file and the file with the diff applied.
Definition: kompare_part.cpp:476
QWidget::size
size
KomparePart::~KomparePart
virtual ~KomparePart()
Destructor.
Definition: kompare_part.cpp:162
KomparePart::readProperties
virtual int readProperties(KConfig *config)
Warning this should be in class Part in KDE 4.0, not here ! Around that time the methods will disappe...
Definition: kompare_part.cpp:930
KomparePart::compareFiles
virtual void compareFiles(const KUrl &sourceFile, const KUrl &destinationFile)
Compare, with diff, source with destination.
Definition: kompare_part.cpp:436
KomparePart::slotSetStatus
void slotSetStatus(Kompare::Status status)
Definition: kompare_part.cpp:641
ViewSettings::loadSettings
virtual void loadSettings(KConfig *config)
Definition: viewsettings.cpp:49
QPrintDialog
kompareview.h
QObject
KomparePart::optionsPreferences
void optionsPreferences()
Definition: kompare_part.cpp:945
komparelistview.h
QPainter
QObject::objectName
objectName
KomparePart::compareFileString
virtual void compareFileString(const KUrl &sourceFile, const QString &destination)
Compare a Source file to a custom Destination string.
Definition: kompare_part.cpp:406
kompareprefdlg.h
KomparePart::diffURLChanged
void diffURLChanged()
QString
QStringList
KomparePart::configChanged
void configChanged()
QFileInfo
kompareconnectwidget.h
QSize
KomparePart::compare
virtual void compare(const KUrl &sourceFile, const KUrl &destinationFile)
Compare, with diff, source with destination.
Definition: kompare_part.cpp:387
KomparePart::compareStringFile
virtual void compareStringFile(const QString &source, const KUrl &destinationFile)
Compare a custom Source string to a Destination file.
Definition: kompare_part.cpp:421
KomparePart::slotPaintRequested
void slotPaintRequested(QPrinter *)
Definition: kompare_part.cpp:612
QPrinter::setOrientation
void setOrientation(Orientation orientation)
KomparePart::compare3Files
virtual void compare3Files(const KUrl &originalFile, const KUrl &changedFile1, const KUrl &changedFile2)
Compare, with diff3, originalFile with changedFile1 and changedFile2.
Definition: kompare_part.cpp:468
QDir
KomparePart::queryClose
virtual bool queryClose()
Warning this should be in class ReadWritePart in KDE 4.0, not here ! Around that time the method will...
Definition: kompare_part.cpp:907
KompareView
Definition: kompareview.h:27
QPrintDialog::exec
virtual int exec()
KomparePart::slotShowError
void slotShowError(QString error)
Definition: kompare_part.cpp:756
KomparePart::slotFilePrint
void slotFilePrint()
To enable printing, the part has the only interesting printable content so putting it here...
Definition: kompare_part.cpp:586
QPrintPreviewDialog
ViewSettings
Definition: viewsettings.h:29
QAction
KomparePart::slotShowDiffstats
void slotShowDiffstats()
Definition: kompare_part.cpp:820
viewsettings.h
KomparePart::updateActions
void updateActions()
Definition: kompare_part.cpp:192
KomparePart::compareDirs
virtual void compareDirs(const KUrl &sourceDir, const KUrl &destinationDir)
Compare, with diff, source with destination.
Definition: kompare_part.cpp:453
KomparePart::updateStatus
void updateStatus()
Definition: kompare_part.cpp:689
komparesaveoptionswidget.h
ViewSettings::saveSettings
virtual void saveSettings(KConfig *config)
Definition: viewsettings.cpp:64
KomparePart::saveDiff
void saveDiff()
Save the results of a comparison as a diff file.
Definition: kompare_part.cpp:528
KomparePart::saveProperties
virtual int saveProperties(KConfig *config)
Definition: kompare_part.cpp:938
KomparePart::openDirAndDiff
virtual void openDirAndDiff(const KUrl &dir, const KUrl &diffFile)
This will show the directory and the directory with the diff applied.
Definition: kompare_part.cpp:490
QPainter::begin
bool begin(QPaintDevice *device)
KompareSaveOptionsWidget
Definition: komparesaveoptionswidget.h:29
QWidget::render
void render(QPaintDevice *target, const QPoint &targetOffset, const QRegion &sourceRegion, QFlags< QWidget::RenderFlag > renderFlags)
KomparePart::saveAll
bool saveAll()
Save all destinations.
Definition: kompare_part.cpp:519
KomparePart::slotSwap
void slotSwap()
Definition: kompare_part.cpp:761
KomparePart::kompareInfo
void kompareInfo(Kompare::Info *info)
KomparePart::openDiff3
virtual bool openDiff3(const KUrl &diff3URL)
Open and parse the diff3 file at diff3Url.
Definition: kompare_part.cpp:255
This file is part of the KDE documentation.
Documentation copyright © 1996-2020 The KDE developers.
Generated on Mon Jun 22 2020 13:40:01 by doxygen 1.8.7 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.

kompare

Skip menu "kompare"
  • Main Page
  • Namespace List
  • Alphabetical List
  • Class List
  • Class Hierarchy
  • Class Members
  • File List
  • File Members

kdesdk API Reference

Skip menu "kdesdk API Reference"
  • kapptemplate
  • kcachegrind
  • kompare
  • lokalize
  • umbrello
  •   umbrello

Search



Report problems with this website to our bug tracking system.
Contact the specific authors with questions and comments about the page contents.

KDE® and the K Desktop Environment® logo are registered trademarks of KDE e.V. | Legal