Main Page | Namespace List | Class Hierarchy | Alphabetical List | Class List | Directories | File List | Namespace Members | Class Members | File Members | Related Pages

lnkproperties.cpp

Go to the documentation of this file.
00001 /**********************************************************************
00002 ** Copyright (C) 2000-2002 Trolltech AS.  All rights reserved.
00003 **
00004 ** This file is part of the Qtopia Environment.
00005 **
00006 ** This file may be distributed and/or modified under the terms of the
00007 ** GNU General Public License version 2 as published by the Free Software
00008 ** Foundation and appearing in the file LICENSE.GPL included in the
00009 ** packaging of this file.
00010 **
00011 ** This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE
00012 ** WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
00013 **
00014 ** See http://www.trolltech.com/gpl/ for GPL licensing information.
00015 **
00016 ** Contact info@trolltech.com if any conditions of this licensing are
00017 ** not clear to you.
00018 **
00019 **********************************************************************/
00020 
00021 // WARNING: Do *NOT* define this yourself. The SL5xxx from SHARP does NOT
00022 //      have this class.
00023 #define QTOPIA_INTERNAL_FSLP
00024 #include "lnkpropertiesbase_p.h"
00025 #include "lnkproperties.h"
00026 #include "ir.h"
00027 
00028 #include <qpe/qpeapplication.h>
00029 #include <qpe/applnk.h>
00030 #include <qpe/global.h>
00031 #include <qpe/categorywidget.h>
00032 #include <qpe/qcopenvelope_qws.h>
00033 #include <qpe/filemanager.h>
00034 #include <qpe/config.h>
00035 #include <qpe/storage.h>
00036 #include <qpe/qpemessagebox.h>
00037 #include <qpe/mimetype.h>
00038 
00039 #include <qlineedit.h>
00040 #include <qtoolbutton.h>
00041 #include <qpushbutton.h>
00042 #include <qgroupbox.h>
00043 #include <qcheckbox.h>
00044 #include <qlabel.h>
00045 #include <qlayout.h>
00046 #include <qfile.h>
00047 #include <qdir.h>
00048 #include <qfileinfo.h>
00049 #include <qmessagebox.h>
00050 #include <qsize.h>
00051 #include <qcombobox.h>
00052 #include <qregexp.h>
00053 #include <qbuttongroup.h>
00054 
00055 #include <stdlib.h>
00056 
00057 LnkProperties::LnkProperties( AppLnk* l, QWidget* parent )
00058     : QDialog( parent, 0, TRUE ), lnk(l), fileSize( 0 )
00059 {
00060     setCaption( tr("Properties") );
00061 
00062     QVBoxLayout *vbox = new QVBoxLayout( this );
00063     d = new LnkPropertiesBase( this );
00064     vbox->add( d );
00065 
00066     // hide custom rotation feature for now, need a new implementation to fit quicklauch,
00067     // is confusing for the user and doubtable useful since life rotation
00068     d->rotate->hide();
00069     d->rotateButtons->hide();
00070 
00071     d->docname->setText(l->name());
00072     QString inf;
00073     if ( l->type().isEmpty() ) {
00074         d->type->hide();
00075         d->typeLabel->hide();
00076     } else {
00077         d->type->setText( l->type() );
00078     }
00079 
00080     if ( l->comment().isEmpty() ) {
00081         d->comment->hide();
00082         d->commentLabel->hide();
00083     } else {
00084         d->comment->setText( l->comment() );
00085     }
00086 
00087     connect(d->beam,SIGNAL(clicked()),this,SLOT(beamLnk()));
00088     if ( lnk->type().contains('/') ) { // A document? (#### better predicate needed)
00089         connect(d->unlink,SIGNAL(clicked()),this,SLOT(unlinkLnk()));
00090         connect(d->duplicate,SIGNAL(clicked()),this,SLOT(duplicateLnk()));
00091 
00092         d->docname->setReadOnly( FALSE );
00093         d->preload->hide();
00094         d->rotate->hide();
00095         d->rotateButtons->hide();
00096         d->labelspacer->hide();
00097 
00098         // ### THIS MUST GO, FIX WIERD BUG in QLAYOUT
00099         d->categoryEdit->kludge();
00100 
00101         d->categoryEdit->setCategories( lnk->categories(),
00102                                         "Document View",
00103                                         tr("Document View") );
00104         setupLocations();
00105     } else {
00106         d->unlink->hide();
00107         d->duplicate->hide();
00108         d->beam->hide();
00109         d->hline->hide();
00110         d->locationLabel->hide();
00111         d->locationCombo->hide();
00112 
00113         // Can't edit categories, since the app .desktop files are global,
00114         // possibly read-only.
00115         d->categoryEdit->hide();
00116 
00117         d->docname->setReadOnly( TRUE );
00118 
00119         if ( l->property("CanFastload") == "0" )
00120             d->preload->hide();
00121         if ( !l->property("Rotation"). isEmpty ()) {
00122             d->rotate->setChecked ( true );
00123             //don't use rotate buttons for now (see comment above)
00124             //d->rotateButtons->setButton((l->rotation().toInt()%360)/90);
00125         }
00126         else {
00127             d->rotateButtons->setEnabled(false);
00128         }
00129 
00130         if ( !l->property( "Arguments" ).isEmpty() )
00131             d->arguments->setText( l->property( "Arguments" ) );
00132 
00133         Config cfg("Launcher");
00134         cfg.setGroup("Preload");
00135         QStringList apps = cfg.readListEntry("Apps",',');
00136         d->preload->setChecked( apps.contains(l->exec()) );
00137         if ( Global::isBuiltinCommand(lnk->exec()) )
00138             d->preload->hide(); // builtins are always fast
00139 
00140         currentLocation = 0; // apps not movable (yet)
00141     }
00142 }
00143 
00144 LnkProperties::~LnkProperties()
00145 {
00146 }
00147 
00148 void LnkProperties::unlinkLnk()
00149 {
00150     if ( QPEMessageBox::confirmDelete( this, tr("Delete"), lnk->name() ) ) {
00151         lnk->removeFiles();
00152         if ( QFile::exists(lnk->file()) ) {
00153             QMessageBox::warning( this, tr("Delete"), tr("File deletion failed.") );
00154         } else {
00155             reject();
00156         }
00157     }
00158 }
00159 
00160 void LnkProperties::setupLocations()
00161 {
00162     QFileInfo fi( lnk->file() );
00163     fileSize = fi.size();
00164     StorageInfo storage;
00165     const QList<FileSystem> &fs = storage.fileSystems();
00166     QListIterator<FileSystem> it ( fs );
00167     QString s;
00168     QString homeDir = getenv("HOME");
00169     QString hardDiskHome;
00170     QString hardDiskPath;
00171     int index = 0;
00172     currentLocation = -1;
00173     for ( ; it.current(); ++it ) {
00174         // we add 10k to the file size so we are sure we can also save the desktop file
00175         if ( (ulong)(*it)->availBlocks() * (ulong)(*it)->blockSize() > (ulong)fileSize + 10000 ) {
00176             if ( (*it)->isRemovable() ||
00177                  (*it)->disk() == "/dev/mtdblock1" ||
00178                  (*it)->disk() == "/dev/mtdblock/1" ||
00179                  (*it)->disk().left(13) == "/dev/mtdblock" ||
00180                  (*it)->disk() == "/dev/mtdblock6" ||
00181                  (*it )->disk() == "/dev/root" ||
00182                  (*it)->disk() == "tmpfs" ) {
00183                 d->locationCombo->insertItem( (*it)->name(), index );
00184                 locations.append( ( ((*it)->isRemovable() ||
00185                                     (*it)->disk() == "/dev/mtdblock6" ||
00186                                     (*it)->disk() == "tmpfs" )
00187                                     ? (*it)->path() : homeDir) );
00188                 if ( lnk->file().contains( (*it)->path() ) ) {
00189                      d->locationCombo->setCurrentItem( index );
00190                      currentLocation = index;
00191                 }
00192                 index++;
00193             } else if ( (*it)->name().contains( tr("Hard Disk") ) &&
00194                         homeDir.contains( (*it)->path() ) &&
00195                         (*it)->path().length() > hardDiskHome.length() ) {
00196                 hardDiskHome = (*it)->name();
00197                 hardDiskPath = (*it)->path();
00198             }
00199         }
00200     }
00201     if ( !hardDiskHome.isEmpty() ) {
00202         d->locationCombo->insertItem( hardDiskHome );
00203         locations.append( hardDiskPath );
00204         if ( currentLocation == -1 ) { // assume it's the hard disk
00205             d->locationCombo->setCurrentItem( index );
00206             currentLocation = index;
00207         }
00208     }
00209 }
00210 
00211 void LnkProperties::duplicateLnk()
00212 {
00213     // The duplicate takes the new properties.
00214     DocLnk newdoc( *((DocLnk *)lnk) );
00215     if ( d->docname->text() == lnk->name() )
00216         newdoc.setName(tr("Copy of ")+d->docname->text());
00217     else
00218         newdoc.setName(d->docname->text());
00219 
00220     if ( !copyFile( newdoc ) ) {
00221         QMessageBox::warning( this, tr("Duplicate"), tr("File copy failed.") );
00222         return;
00223     }
00224     reject();
00225 }
00226 
00227 bool LnkProperties::moveLnk()
00228 {
00229     DocLnk newdoc( *((DocLnk *)lnk) );
00230     newdoc.setName(d->docname->text());
00231 
00232     if ( !copyFile( newdoc ) ) {
00233         QMessageBox::warning( this, tr("Details"), tr("Moving Document failed.") );
00234         return FALSE;
00235     }
00236     // remove old lnk
00237     lnk->removeFiles();
00238 
00239     return TRUE;
00240 }
00241 
00242 void LnkProperties::beamLnk()
00243 {
00244     Ir ir;
00245     DocLnk doc( *((DocLnk *)lnk) );
00246     doc.setName(d->docname->text());
00247     reject();
00248     ir.send( doc, doc.comment() );
00249 }
00250 
00251 static bool createMimedir(const QString&base,const QString&mimetype)
00252 {
00253     int pos = 0;
00254     int stage = 0;
00255         if (base.length()==0) return FALSE;
00256     QString _tname = base+"/Documents";
00257     QDir _dir(_tname+"/"+mimetype);
00258     if (_dir.exists()) return TRUE;
00259     pos = mimetype.find("/");
00260     _dir.setPath(_tname);
00261     while (stage<2) {
00262         if (!_dir.exists()) {
00263             if (!_dir.mkdir(_tname)) {
00264                 qDebug( QString("Creation of dir %1 failed\n").arg(_tname));
00265                 return FALSE;
00266                 }
00267         }
00268         switch(stage) {
00269         case 0:
00270             _tname+="/"+mimetype.left(pos);
00271             break;
00272         case 1:
00273             _tname+="/"+mimetype.right(pos-1);
00274             break;
00275         default:
00276             break;
00277         }
00278         _dir.setPath(_tname);
00279         ++stage;
00280     }
00281     return TRUE;
00282 }
00283 
00284 bool LnkProperties::copyFile( DocLnk &newdoc )
00285 {
00286     const char *linkExtn = ".desktop";
00287     QString fileExtn;
00288     int extnPos = lnk->file().findRev( '.' );
00289     if ( extnPos > 0 )
00290         fileExtn = lnk->file().mid( extnPos );
00291 
00292     QString safename = newdoc.name();
00293     safename.replace(QRegExp("/"),"_");
00294 
00295     QString fn = locations[ d->locationCombo->currentItem() ]
00296                   + "/Documents/" + newdoc.type();
00297     if (!createMimedir(locations[ d->locationCombo->currentItem() ],newdoc.type())) {
00298         return FALSE;
00299     }
00300     fn+="/"+safename;
00301     if ( QFile::exists(fn + fileExtn) || QFile::exists(fn + linkExtn) ) {
00302         int n=1;
00303         QString nn = fn + "_" + QString::number(n);
00304         while ( QFile::exists(nn+fileExtn) || QFile::exists(nn+linkExtn) ) {
00305             n++;
00306             nn = fn + "_" + QString::number(n);
00307         }
00308         fn = nn;
00309     }
00310     newdoc.setFile( fn + fileExtn );
00311     newdoc.setLinkFile( fn + linkExtn );
00312 
00313     // Copy file
00314     FileManager fm;
00315     if ( !fm.copyFile( *lnk, newdoc ) )
00316         return FALSE;
00317     return TRUE;
00318 }
00319 
00320 void LnkProperties::done(int ok)
00321 {
00322     if ( ok ) {
00323         bool changed=FALSE;
00324         bool reloadMime=FALSE;
00325 
00326         if ( lnk->name() != d->docname->text() ) {
00327             lnk->setName(d->docname->text());
00328             changed=TRUE;
00329         }
00330         if ( d->categoryEdit->isVisible() ) {
00331             QArray<int> tmp = d->categoryEdit->newCategories();
00332             if ( lnk->categories() != tmp ) {
00333                 lnk->setCategories( tmp );
00334                 changed = TRUE;
00335             }
00336         }
00337         if ( !d->rotate->isHidden()) {
00338             QString newrot;
00339 
00340             if ( d->rotate->isChecked() ) {
00341                 int rot=0;
00342                 for(; rot<4; rot++) {
00343                     if (d->rotateButtons->find(rot)->isOn())
00344                         break;
00345                 }
00346                 newrot = QString::number((rot*90)%360);
00347             }
00348             if ( newrot != lnk->rotation() ) {
00349                 lnk-> setRotation(newrot);
00350                 changed = TRUE;
00351                 reloadMime = TRUE;
00352             }
00353         }
00354     if ( d->arguments->text() != lnk->property( "Arguments" ) ) {
00355         lnk->setProperty( "Arguments", d->arguments->text() );
00356         changed = TRUE;
00357     }
00358         if ( d->preload->isHidden() && d->locationCombo->currentItem() != currentLocation ) {
00359             moveLnk();
00360         } else if ( changed ) {
00361             lnk->writeLink();
00362         }
00363 
00364         if ( !d->preload->isHidden() ) {
00365             Config cfg("Launcher");
00366             cfg.setGroup("Preload");
00367             QStringList apps = cfg.readListEntry("Apps",',');
00368             QString exe = lnk->exec();
00369             if ( apps.contains(exe) != d->preload->isChecked() ) {
00370                 if ( d->preload->isChecked() ) {
00371                     apps.append(exe);
00372 #ifndef QT_NO_COP
00373                     QCopEnvelope e("QPE/Application/"+exe.local8Bit(),
00374                                    "enablePreload()");
00375 #endif
00376                 } else {
00377                     apps.remove(exe);
00378 #ifndef QT_NO_COP
00379                     QCopEnvelope e("QPE/Application/"+exe.local8Bit(),
00380                                    "quitIfInvisible()");
00381 #endif
00382                 }
00383                 cfg.writeEntry("Apps",apps,',');
00384             }
00385         }
00386         if ( reloadMime )
00387             MimeType::updateApplications ( );
00388     }
00389     QDialog::done( ok );
00390 }
00391 

Generated on Sat Nov 5 16:16:37 2005 for OPIE by  doxygen 1.4.2