kio Library API Documentation

renamedlg.cpp

00001 /* This file is part of the KDE libraries
00002     Copyright (C) 2000 Stephan Kulow <coolo@kde.org>
00003                        David Faure <faure@kde.org>
00004                   2001 Holger Freyther <freyther@kde.org>
00005 
00006     This library is free software; you can redistribute it and/or
00007     modify it under the terms of the GNU Library General Public
00008     License as published by the Free Software Foundation; either
00009     version 2 of the License, or (at your option) any later version.
00010 
00011     This library is distributed in the hope that it will be useful,
00012     but WITHOUT ANY WARRANTY; without even the implied warranty of
00013     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00014     Library General Public License for more details.
00015 
00016     You should have received a copy of the GNU Library General Public License
00017     along with this library; see the file COPYING.LIB.  If not, write to
00018     the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
00019     Boston, MA 02111-1307, USA.
00020 */
00021 
00022 #include "kio/renamedlg.h"
00023 #include "kio/renamedlgplugin.h"
00024 #include <stdio.h>
00025 #include <assert.h>
00026 
00027 #include <qfileinfo.h>
00028 #include <qlabel.h>
00029 #include <qlayout.h>
00030 #include <qlineedit.h>
00031 
00032 #include <kmessagebox.h>
00033 #include <kpushbutton.h>
00034 #include <kapplication.h>
00035 #include <kio/global.h>
00036 #include <ktrader.h>
00037 #include <klibloader.h>
00038 #include <kdialog.h>
00039 #include <klocale.h>
00040 #include <kglobal.h>
00041 #include <kdebug.h>
00042 #include <kurl.h>
00043 #include <kmimetype.h>
00044 #include <kwin.h>
00045 #include <kseparator.h>
00046 #include <kstringhandler.h>
00047 #include <kstdguiitem.h>
00048 #include <kguiitem.h>
00049 #include <ksqueezedtextlabel.h>
00050 
00051 using namespace KIO;
00052 
00053 class RenameDlg::RenameDlgPrivate
00054 {
00055  public:
00056   RenameDlgPrivate(){
00057     b0 = 0L;
00058     b1 = b2 = b3 = b4 = b5 = b6 = b7 = b8 = 0L;
00059     m_pLineEdit=0L;
00060     m_pLayout=0L;
00061   }
00062   KPushButton *b0;
00063   QPushButton *b1;
00064   QPushButton *b2;
00065   QPushButton *b3;
00066   QPushButton *b4;
00067   QPushButton *b5;
00068   QPushButton *b6;
00069   QPushButton *b7;
00070   QPushButton *b8; //why isn't it an array
00071   QLineEdit* m_pLineEdit;
00072   QVBoxLayout* m_pLayout; // ### doesn't need to be here
00073   QString src;
00074   QString dest;
00075   QString mimeSrc;
00076   QString mimeDest;
00077   bool modal;
00078   bool plugin;
00079 };
00080 
00081 RenameDlg::RenameDlg(QWidget *parent, const QString & _caption,
00082                      const QString &_src, const QString &_dest,
00083                      RenameDlg_Mode _mode,
00084                      KIO::filesize_t sizeSrc,
00085                      KIO::filesize_t sizeDest,
00086                      time_t ctimeSrc,
00087                      time_t ctimeDest,
00088                      time_t mtimeSrc,
00089                      time_t mtimeDest,
00090                      bool _modal)
00091   : QDialog ( parent, "KIO::RenameDialog" , _modal )
00092 {
00093     d = new RenameDlgPrivate( );
00094     d->modal = _modal;
00095     // Set "StaysOnTop", because this dialog is typically used in kio_uiserver,
00096     // i.e. in a separate process.
00097     // ####### This isn't the case anymore - remove?
00098 #ifndef Q_WS_QWS //FIXME(E): Implement for QT Embedded
00099     if (d->modal)
00100         KWin::setState( winId(), NET::StaysOnTop );
00101 #endif
00102 
00103     d->src = _src;
00104     d->dest = _dest;
00105     d->plugin = false;
00106 
00107 
00108     setCaption( _caption );
00109 
00110     d->b0 = new KPushButton( KStdGuiItem::cancel(), this );
00111     connect(d->b0, SIGNAL(clicked()), this, SLOT(b0Pressed()));
00112 
00113     if ( ! (_mode & M_NORENAME ) ) {
00114         d->b1 = new QPushButton( i18n( "&Rename" ), this );
00115         d->b1->setEnabled(false);
00116         d->b8 = new QPushButton( i18n( "Suggest New &Name" ), this );
00117         connect(d->b8, SIGNAL(clicked()), this, SLOT(b8Pressed()));
00118         connect(d->b1, SIGNAL(clicked()), this, SLOT(b1Pressed()));
00119     }
00120 
00121     if ( ( _mode & M_MULTI ) && ( _mode & M_SKIP ) ) {
00122         d->b2 = new QPushButton( i18n( "&Skip" ), this );
00123         connect(d->b2, SIGNAL(clicked()), this, SLOT(b2Pressed()));
00124 
00125         d->b3 = new QPushButton( i18n( "&Auto Skip" ), this );
00126         connect(d->b3, SIGNAL(clicked()), this, SLOT(b3Pressed()));
00127     }
00128 
00129     if ( _mode & M_OVERWRITE ) {
00130         d->b4 = new QPushButton( i18n( "&Overwrite" ), this );
00131         connect(d->b4, SIGNAL(clicked()), this, SLOT(b4Pressed()));
00132 
00133         if ( _mode & M_MULTI ) {
00134             d->b5 = new QPushButton( i18n( "O&verwrite All" ), this );
00135             connect(d->b5, SIGNAL(clicked()), this, SLOT(b5Pressed()));
00136         }
00137     }
00138 
00139     if ( _mode & M_RESUME ) {
00140         d->b6 = new QPushButton( i18n( "&Resume" ), this );
00141         connect(d->b6, SIGNAL(clicked()), this, SLOT(b6Pressed()));
00142 
00143         if ( _mode & M_MULTI )
00144         {
00145             d->b7 = new QPushButton( i18n( "R&esume All" ), this );
00146             connect(d->b7, SIGNAL(clicked()), this, SLOT(b7Pressed()));
00147         }
00148     }
00149 
00150     d->m_pLayout = new QVBoxLayout( this, KDialog::marginHint(),
00151                                     KDialog::spacingHint() );
00152     d->m_pLayout->addStrut( 360 );  // makes dlg at least that wide
00153 
00154     // User tries to overwrite a file with itself ?
00155     if ( _mode & M_OVERWRITE_ITSELF ) {
00156         QLabel *lb = new QLabel( i18n( "This action would overwrite '%1' with itself.\n"
00157                                        "Please enter a new file name:" ).arg( KStringHandler::csqueeze( d->src,100 ) ), this );
00158         d->b1->setText(i18n("C&ontinue"));
00159         d->m_pLayout->addWidget( lb );
00160     }
00161     else if ( _mode & M_OVERWRITE ) {
00162 
00163         // Figure out the mimetype and load one plugin
00164         // (This is the only mode that is handled by plugins)
00165         pluginHandling();
00166         KTrader::OfferList plugin_offers;
00167         if( d->mimeSrc != KMimeType::defaultMimeType()   ){
00168             plugin_offers = KTrader::self()->query(d->mimeSrc, "'RenameDlg/Plugin' in ServiceTypes");
00169 
00170         }else if(d->mimeDest != KMimeType::defaultMimeType() ) {
00171             plugin_offers = KTrader::self()->query(d->mimeDest, "'RenameDlg/Plugin' in ServiceTypes");
00172         }
00173         if(!plugin_offers.isEmpty() ){
00174             kdDebug(7024) << "Offers" << endl;
00175             KTrader::OfferList::ConstIterator it = plugin_offers.begin();
00176             KTrader::OfferList::ConstIterator end = plugin_offers.end();
00177             for( ; it != end; ++it ){
00178                 QString libName = (*it)->library();
00179                 if( libName.isEmpty() ){
00180                     kdDebug(7024) << "lib is empty" << endl;
00181                     continue;
00182                 }
00183                 KLibrary *lib = KLibLoader::self()->library(libName.local8Bit() );
00184                 if(!lib) {
00185                     continue;
00186                 }
00187                 KLibFactory *factory = lib->factory();
00188                 if(!factory){
00189                     lib->unload();
00190                     continue;
00191                 }
00192                 QObject *obj = factory->create( this, (*it)->name().latin1() );
00193                 if(!obj) {
00194                     lib->unload();
00195                     continue;
00196                 }
00197                 RenameDlgPlugin *plugin = static_cast<RenameDlgPlugin *>(obj);
00198                 if(!plugin ){
00199                     delete obj;
00200                     continue;
00201                 }
00202                 if( plugin->initialize( _mode, _src, _dest, d->mimeSrc,
00203                                         d->mimeDest, sizeSrc, sizeDest,
00204                                         ctimeSrc, ctimeDest,
00205                                         mtimeSrc, mtimeDest ) ) {
00206                     d->plugin = true;
00207                     d->m_pLayout->addWidget(plugin );
00208                     kdDebug(7024) << "RenameDlgPlugin" << endl;
00209                     break;
00210                 } else {
00211                     delete obj;
00212                 }
00213             }
00214 
00215         }
00216 
00217         if( !d->plugin ){
00218             // No plugin found, build default dialog
00219             QGridLayout * gridLayout = new QGridLayout( 0L, 9, 2, KDialog::marginHint(),
00220                                                         KDialog::spacingHint() );
00221             d->m_pLayout->addLayout(gridLayout);
00222             gridLayout->setColStretch(0,0);
00223             gridLayout->setColStretch(1,10);
00224 
00225             QString sentence1;
00226             if (mtimeDest < mtimeSrc)
00227                 sentence1 = i18n("An older item named '%1' already exists.");
00228             else if (mtimeDest == mtimeSrc)
00229                 sentence1 = i18n("A similar file named '%1' already exists.");
00230             else
00231                 sentence1 = i18n("A newer item named '%1' already exists.");
00232 
00233             QLabel * lb1 = new KSqueezedTextLabel( sentence1.arg(d->dest), this );
00234             gridLayout->addMultiCellWidget( lb1, 0, 0, 0, 1 ); // takes the complete first line
00235 
00236             lb1 = new QLabel( this );
00237             lb1->setPixmap( KMimeType::pixmapForURL( d->dest ) );
00238             gridLayout->addMultiCellWidget( lb1, 1, 3, 0, 0 ); // takes the first column on rows 1-3
00239 
00240             int row = 1;
00241             if ( sizeDest != (KIO::filesize_t)-1 )
00242             {
00243                 QLabel * lb = new QLabel( i18n("size %1").arg( KIO::convertSize(sizeDest) ), this );
00244                 gridLayout->addWidget( lb, row, 1 );
00245                 row++;
00246 
00247             }
00248             if ( ctimeDest != (time_t)-1 )
00249             {
00250                 QDateTime dctime; dctime.setTime_t( ctimeDest );
00251                 QLabel * lb = new QLabel( i18n("created on %1").arg( KGlobal::locale()->formatDateTime(dctime) ), this );
00252                 gridLayout->addWidget( lb, row, 1 );
00253                 row++;
00254             }
00255             if ( mtimeDest != (time_t)-1 )
00256             {
00257                 QDateTime dmtime; dmtime.setTime_t( mtimeDest );
00258                 QLabel * lb = new QLabel( i18n("modified on %1").arg( KGlobal::locale()->formatDateTime(dmtime) ), this );
00259                 gridLayout->addWidget( lb, row, 1 );
00260                 row++;
00261             }
00262 
00263             if ( !d->src.isEmpty() )
00264             {
00265                 // rows 1 to 3 are the details (size/ctime/mtime), row 4 is empty
00266                 gridLayout->addRowSpacing( 4, 20 );
00267 
00268                 QLabel * lb2 = new KSqueezedTextLabel( i18n("The source file is '%1'").arg(d->src), this );
00269                 gridLayout->addMultiCellWidget( lb2, 5, 5, 0, 1 ); // takes the complete first line
00270 
00271                 lb2 = new QLabel( this );
00272                 lb2->setPixmap( KMimeType::pixmapForURL( d->src ) );
00273                 gridLayout->addMultiCellWidget( lb2, 6, 8, 0, 0 ); // takes the first column on rows 6-8
00274 
00275                 row = 6;
00276 
00277                 if ( sizeSrc != (KIO::filesize_t)-1 )
00278                 {
00279                     QLabel * lb = new QLabel( i18n("size %1").arg( KIO::convertSize(sizeSrc) ), this );
00280                     gridLayout->addWidget( lb, row, 1 );
00281                     row++;
00282                 }
00283                 if ( ctimeSrc != (time_t)-1 )
00284                 {
00285                     QDateTime dctime; dctime.setTime_t( ctimeSrc );
00286                     QLabel * lb = new QLabel( i18n("created on %1").arg( KGlobal::locale()->formatDateTime(dctime) ), this );
00287                     gridLayout->addWidget( lb, row, 1 );
00288                     row++;
00289                 }
00290                 if ( mtimeSrc != (time_t)-1 )
00291                 {
00292                     QDateTime dmtime; dmtime.setTime_t( mtimeSrc );
00293                     QLabel * lb = new QLabel( i18n("modified on %1").arg( KGlobal::locale()->formatDateTime(dmtime) ), this );
00294                     gridLayout->addWidget( lb, row, 1 );
00295                     row++;
00296                 }
00297             }
00298         }
00299     }
00300     else
00301     {
00302         // This is the case where we don't want to allow overwriting, the existing
00303         // file must be preserved (e.g. when renaming).
00304         QString sentence1;
00305         if (mtimeDest < mtimeSrc)
00306             sentence1 = i18n("An older item named '%1' already exists.");
00307         else if (mtimeDest == mtimeSrc)
00308             sentence1 = i18n("A similar file named '%1' already exists.");
00309         else
00310             sentence1 = i18n("A newer item named '%1' already exists.");
00311 
00312         QLabel *lb = new KSqueezedTextLabel ( sentence1.arg(d->dest), this );
00313         d->m_pLayout->addWidget(lb);
00314     }
00315     QHBoxLayout* layout2 = new QHBoxLayout();
00316     d->m_pLayout->addLayout( layout2 );
00317 
00318     d->m_pLineEdit = new QLineEdit( this );
00319     layout2->addWidget( d->m_pLineEdit );
00320     QString fileName = KURL(d->dest).fileName();
00321     d->m_pLineEdit->setText( KIO::decodeFileName( fileName ) );
00322     if (d->b1)
00323         connect(d->m_pLineEdit, SIGNAL(textChanged(const QString &)),
00324                 SLOT(enableRenameButton(const QString &)));
00325     if ( d->b8 )
00326     {
00327         layout2->addWidget( d->b8 );
00328         setTabOrder( d->m_pLineEdit, d->b8 );
00329     }
00330 
00331     KSeparator* separator = new KSeparator( this );
00332     d->m_pLayout->addWidget( separator );
00333 
00334     QHBoxLayout* layout = new QHBoxLayout();
00335     d->m_pLayout->addLayout( layout );
00336 
00337     layout->addStretch(1);
00338 
00339     if ( d->b1 )
00340     {
00341         layout->addWidget( d->b1 );
00342         setTabOrder( d->b1, d->b0 );
00343     }
00344     if ( d->b2 )
00345     {
00346         layout->addWidget( d->b2 );
00347         setTabOrder( d->b2, d->b0 );
00348     }
00349     if ( d->b3 )
00350     {
00351         layout->addWidget( d->b3 );
00352         setTabOrder( d->b3, d->b0 );
00353     }
00354     if ( d->b4 )
00355     {
00356         layout->addWidget( d->b4 );
00357         setTabOrder( d->b4, d->b0 );
00358     }
00359     if ( d->b5 )
00360     {
00361         layout->addWidget( d->b5 );
00362         setTabOrder( d->b5, d->b0 );
00363     }
00364     if ( d->b6 )
00365     {
00366         layout->addWidget( d->b6 );
00367         setTabOrder( d->b6, d->b0 );
00368     }
00369     if ( d->b7 )
00370     {
00371         layout->addWidget( d->b7 );
00372         setTabOrder( d->b7, d->b0 );
00373     }
00374 
00375     d->b0->setDefault( true );
00376     layout->addWidget( d->b0 );
00377 
00378     resize( sizeHint() );
00379 }
00380 
00381 RenameDlg::~RenameDlg()
00382 {
00383   delete d;
00384   // no need to delete Pushbuttons,... qt will do this
00385 }
00386 
00387 void RenameDlg::enableRenameButton(const QString &newDest)
00388 {
00389   if (newDest != d->dest)
00390   {
00391     d->b1->setEnabled(true);
00392     d->b1->setDefault(true);
00393   }
00394   else
00395     d->b1->setEnabled(false);
00396 }
00397 
00398 KURL RenameDlg::newDestURL()
00399 {
00400   KURL newDest( d->dest );
00401   QString fileName = d->m_pLineEdit->text();
00402   newDest.setFileName( KIO::encodeFileName( fileName ) );
00403   return newDest;
00404 }
00405 
00406 void RenameDlg::b0Pressed()
00407 {
00408   done( 0 );
00409 }
00410 
00411 // Rename
00412 void RenameDlg::b1Pressed()
00413 {
00414   if ( d->m_pLineEdit->text().isEmpty() )
00415     return;
00416 
00417   KURL u = newDestURL();
00418   if ( !u.isValid() )
00419   {
00420     KMessageBox::error( this, i18n( "Malformed URL\n%1" ).arg( u.prettyURL() ) );
00421     return;
00422   }
00423 
00424   done( 1 );
00425 }
00426 // Propose button clicked
00427 void RenameDlg::b8Pressed()
00428 {
00429   int pos;
00430 
00431   /* no name to play with */
00432   if ( d->m_pLineEdit->text().isEmpty() )
00433     return;
00434 
00435   QString basename, dotSuffix, tmp;
00436   QFileInfo info ( d->m_pLineEdit->text() );
00437   basename = info.baseName();
00438   dotSuffix = info.extension();
00439 
00440   if ( !dotSuffix.isEmpty() )
00441     dotSuffix = '.' + dotSuffix;
00442 
00443   pos = basename.findRev('_' );
00444   if(pos != -1 ){
00445     bool ok;
00446     tmp = basename.right( basename.length() - (pos + 1) );
00447     int number = tmp.toInt( &ok, 10 );
00448     if ( !ok ) {// ok there is no number
00449       basename.append("_1" );
00450       d->m_pLineEdit->setText(basename + dotSuffix );
00451       return;
00452     }
00453     else {
00454      // yes there's already a number behind the _ so increment it by one
00455       QString tmp2 = QString::number ( number + 1 );
00456       basename.replace( pos+1, tmp.length() ,tmp2);
00457       d->m_pLineEdit->setText( basename + dotSuffix );
00458       return;
00459     }
00460   }
00461   else // no underscore yet
00462   {
00463     d->m_pLineEdit->setText( basename + "_1" + dotSuffix );
00464     return;
00465 
00466   }
00467   return; // we should never return from here jic
00468 }
00469 
00470 void RenameDlg::b2Pressed()
00471 {
00472   done( 2 );
00473 }
00474 
00475 void RenameDlg::b3Pressed()
00476 {
00477   done( 3 );
00478 }
00479 
00480 void RenameDlg::b4Pressed()
00481 {
00482   done( 4 );
00483 }
00484 
00485 void RenameDlg::b5Pressed()
00486 {
00487   done( 5 );
00488 }
00489 
00490 void RenameDlg::b6Pressed()
00491 {
00492   done( 6 );
00493 }
00494 
00495 void RenameDlg::b7Pressed()
00496 {
00497   done( 7 );
00498 }
00505 void RenameDlg::pluginHandling()
00506 {
00507   d->mimeSrc = mime( d->src );
00508   d->mimeDest = mime(d->dest );
00509 
00510   kdDebug(7024) << "Source Mimetype: "<< d->mimeSrc << endl;
00511   kdDebug(7024) << "Dest Mimetype: "<< d->mimeDest << endl;
00512 }
00513 QString RenameDlg::mime( const QString &src )
00514 {
00515   KMimeType::Ptr type = KMimeType::findByURL(src );
00516   //if( type->name() == KMimeType::defaultMimeType() ){ // ok no mimetype
00517     //    QString ty = KIO::NetAccess::mimetype(d->src );
00518     // return ty;
00519     return type->name();
00520 }
00521 
00522 
00523 RenameDlg_Result KIO::open_RenameDlg( const QString & _caption,
00524                                       const QString & _src, const QString & _dest,
00525                                       RenameDlg_Mode _mode,
00526                                       QString& _new,
00527                                       KIO::filesize_t sizeSrc,
00528                                       KIO::filesize_t sizeDest,
00529                                       time_t ctimeSrc,
00530                                       time_t ctimeDest,
00531                                       time_t mtimeSrc,
00532                                       time_t mtimeDest)
00533 {
00534   Q_ASSERT(kapp);
00535 
00536   RenameDlg dlg( 0L, _caption, _src, _dest, _mode,
00537                  sizeSrc, sizeDest, ctimeSrc, ctimeDest, mtimeSrc, mtimeDest,
00538                  true /*modal*/ );
00539   int i = dlg.exec();
00540   _new = dlg.newDestURL().path();
00541 
00542   return (RenameDlg_Result)i;
00543 }
00544 
00545 #include "renamedlg.moc"
00546 
00547 
00548 
00549 
00550 
KDE Logo
This file is part of the documentation for kio Library Version 3.2.0.
Documentation copyright © 1996-2004 the KDE developers.
Generated on Wed Feb 4 12:35:09 2004 by doxygen 1.2.18 written by Dimitri van Heesch, © 1997-2003