Removed crappy FileListView::updateItem() method and replace it with addOrUpdateItem()

Enhanced in several ways parsing of rar-5+ output (fixes a crash and several potential issues)
Spacing fixes

Minor modification: replace assert with if()
Signed-off-by: Michele Calgaro <michele.calgaro@yahoo.it>
pull/1/head
Alexander Golubev 8 years ago committed by Michele Calgaro
parent 058176316e
commit 8cf274c35a

@ -170,6 +170,17 @@ void FileLVI::setText( int column, const TQString &text )
TQListViewItem::setText(column, text); TQListViewItem::setText(column, text);
} }
void FileLVI::setItemData( const TQStringList &entryData )
{
int i = 0;
for (TQStringList::ConstIterator it = entryData.begin(); it != entryData.end(); ++it)
{
this->setText(i, *it);
++i;
}
}
static FileLVI* folderLVI( TDEListViewItem *parent, const TQString& name ) static FileLVI* folderLVI( TDEListViewItem *parent, const TQString& name )
{ {
FileLVI *folder = new FileLVI( parent ); FileLVI *folder = new FileLVI( parent );
@ -383,7 +394,7 @@ FileListView::item(const TQString& filename) const
return 0; return 0;
} }
void FileListView::addItem( const TQStringList & entries ) FileLVI *FileListView::addItem( const TQStringList & entries )
{ {
FileLVI *flvi, *parent = findParent( entries[0] ); FileLVI *flvi, *parent = findParent( entries[0] );
if ( parent ) if ( parent )
@ -391,72 +402,23 @@ void FileListView::addItem( const TQStringList & entries )
else else
flvi = new FileLVI( this ); flvi = new FileLVI( this );
flvi->setItemData (entries);
int i = 0;
for (TQStringList::ConstIterator it = entries.begin(); it != entries.end(); ++it)
{
flvi->setText(i, *it);
++i;
}
KMimeType::Ptr mimeType = KMimeType::findByPath( entries.first(), 0, true ); KMimeType::Ptr mimeType = KMimeType::findByPath( entries.first(), 0, true );
flvi->setPixmap( 0, mimeType->pixmap( TDEIcon::Small ) ); flvi->setPixmap( 0, mimeType->pixmap( TDEIcon::Small ) );
}
void FileListView::updateItem( const TQStringList &entries )
{
TQStringList ancestorList = TQStringList::split( '/', entries[0] );
// Checks if the listview contains the first item in the list of ancestors
TQListViewItem *item = firstChild();
while ( item )
{
if ( item->text( 0 ) == ancestorList[0] || item->text( 0 ) == ancestorList[0].stripWhiteSpace())
break;
item = item->nextSibling();
}
// If the list view does not contain the item ...
if ( !item )
{
kdError( 1601 ) << ancestorList[0] << " not found" << endl;
return;
}
// We've already dealt with the first item, remove it
ancestorList.pop_front();
while ( ancestorList.count() > 0 )
{
TQString name = ancestorList[0];
FileLVI *parent = static_cast< FileLVI*>( item ); return flvi;
item = parent->firstChild();
while ( item )
{
if ( item->text(0) == name )
break;
item = item->nextSibling();
}
if ( !item )
{
kdError( 1601 ) << name << " not found" << endl;
return;
}
ancestorList.pop_front();
} }
int i = 0; FileLVI *FileListView::addOrUpdateItem( const TQStringList &entries )
for (TQStringList::ConstIterator it = entries.begin(); it != entries.end(); ++it)
{ {
item->setText(i, *it); FileLVI *flvi = item ( entries[0] );
++i; if (flvi) {
flvi->setItemData (entries);
return flvi;
} else {
return addItem (entries);
} }
item->setOpen( true );
} }
void FileListView::selectAll() void FileListView::selectAll()

@ -60,6 +60,8 @@ class FileLVI : public TDEListViewItem
int compare ( TQListViewItem * i, int col, bool ascending ) const; int compare ( TQListViewItem * i, int col, bool ascending ) const;
virtual TQString key( int column, bool ) const; virtual TQString key( int column, bool ) const;
virtual void setText( int column, const TQString &text ); virtual void setText( int column, const TQString &text );
/// Set the data for model entry all at once
void setItemData( const TQStringList &entryData );
private: private:
TDEIO::filesize_t m_fileSize; TDEIO::filesize_t m_fileSize;
@ -109,14 +111,16 @@ class FileListView: public TDEListView
/** /**
* Adds a file and stats to the file listing * Adds a file and stats to the file listing
* @param entries A stringlist of the entries for each column of the list. * @param entries A stringlist of the entries for each column of the list.
* @return The newly added FileLVI
*/ */
void addItem( const TQStringList& entries ); FileLVI* addItem( const TQStringList& entries );
/** /**
* Updates a file or folder item already included in the listview * Adds a file and stats if it doesn't exists or updates the existing one
* @param entries A stringlist of the updated entries for each column of the list. * @param entries A stringlist of the updated entries for each column of the list.
* @return The newly added or the updated FileLVI
*/ */
void updateItem( const TQStringList& entries ); FileLVI* addOrUpdateItem( const TQStringList& entries );
/** /**
* Returns the number of files in the archive. * Returns the number of files in the archive.

@ -30,6 +30,8 @@
#include <string> #include <string>
// QT includes // QT includes
#include <tqstring.h>
#include <tqregexp.h>
#include <tqfile.h> #include <tqfile.h>
#include <tqdir.h> #include <tqdir.h>
#include <tqtextcodec.h> #include <tqtextcodec.h>
@ -39,6 +41,7 @@
#include <tdeglobal.h> #include <tdeglobal.h>
#include <tdelocale.h> #include <tdelocale.h>
#include <tdemessagebox.h> #include <tdemessagebox.h>
#include <kmimetype.h>
#include <kpassdlg.h> #include <kpassdlg.h>
#include <kprocess.h> #include <kprocess.h>
#include <kstandarddirs.h> #include <kstandarddirs.h>
@ -83,94 +86,96 @@ RarArch::RarArch( ArkWidget *_gui, const TQString & _fileName )
verifyUncompressUtilityIsAvailable( m_unarchiver_program ); verifyUncompressUtilityIsAvailable( m_unarchiver_program );
setReadOnly( true ); setReadOnly( true );
} }
m_headerString = "";
} }
bool RarArch::processLine( const TQCString &line ) bool RarArch::processLine( const TQCString &line )
{ {
TQString unicode_line; TQString uline = TQTextCodec::codecForLocale()->toUnicode(line);
TQTextCodec *codec = TQTextCodec::codecForLocale();
unicode_line = codec->toUnicode( line );
// Look for rar/unrar version first // Look for rar/unrar version first
if (!m_version) if (!m_version)
{ {
if (line.left(3) == "RAR") TQRegExp versionRegExp (TQString::fromLatin1 ("RAR\\s(\\d+)\\.(\\S+)\\s.*"));
{
bool ok_flag = false; if (versionRegExp.exactMatch (uline))
short version = line.mid(4, 1).toShort(&ok_flag);
if (ok_flag)
{
m_version = version;
if (m_version < VERSION_5)
{ {
m_version = versionRegExp.capturedTexts()[1].toShort ();
if (m_version < VERSION_5) {
m_headerString = "-------------------------------------------------------------------------------"; m_headerString = "-------------------------------------------------------------------------------";
m_isFirstLine = true; m_isFirstLine = true;
} } else {
else
{
m_headerString = "----------- --------- -------- ----- ---------- ----- -------- ----"; m_headerString = "----------- --------- -------- ----- ---------- ----- -------- ----";
} }
setHeaders(); setHeaders(); //< Note: header order for version 5 is different, but keep the old one for consistency
return true; return true;
} }
}
return false; return false;
} }
if (m_version < VERSION_5 && m_isFirstLine) TQStringList entry;
TQStringList parsedData = TQStringList::split(QChar(' '), uline);
if (m_version < VERSION_5) {
if (m_isFirstLine)
{ {
m_entryFilename = TQString::fromLocal8Bit( line ); m_entryFilename = uline.remove( 0, 1 );
m_entryFilename.remove( 0, 1 );
m_isFirstLine = false; m_isFirstLine = false;
return true; return true;
} }
TQStringList list; if (parsedData.size() < 9) {
TQStringList l2 = TQStringList::split( ' ', line ); kdError ( 1601 ) << "Failed to parse rar<5 output string: \"" << uline << "\"" << endl;
}
if (m_version < VERSION_5) entry << m_entryFilename; // filename
{ entry << parsedData[ 0 ]; // size
list << m_entryFilename; // filename entry << parsedData[ 1 ]; // packed
list << l2[ 0 ]; // size entry << parsedData[ 2 ]; // ratio
list << l2[ 1 ]; // packed
list << l2[ 2 ]; // ratio
TQStringList date = TQStringList::split( '-', l2[ 3 ] ); TQStringList date = TQStringList::split( '-', parsedData[ 3 ] );
list << ArkUtils::fixYear( date[ 2 ].latin1() ) + '-' + date[ 1 ] + '-' + date [ 0 ] + ' ' + l2[4]; // date entry << ArkUtils::fixYear( date[ 2 ].latin1() ) + '-' + date[ 1 ] + '-' + date [ 0 ] + ' ' + parsedData[4]; // date
list << l2[ 5 ]; // attributes entry << parsedData[ 5 ]; // attributes
list << l2[ 6 ]; // crc entry << parsedData[ 6 ]; // crc
list << l2[ 7 ]; // method entry << parsedData[ 7 ]; // method
list << l2[ 8 ]; // Version entry << parsedData[ 8 ]; // Version
m_isFirstLine = true; m_isFirstLine = true;
} }
else else
{ {
m_entryFilename = line.mid(line.find(l2[7])); // Note: don't use parsedData for names due to they may contain trailing spaces
list << m_entryFilename; // filename TQRegExp nameRegExp (TQString::fromLatin1 ("\\s*(\\S+\\s+){6}\\S+ (.*)"));
list << l2[ 1 ]; // size
list << l2[ 2 ]; // packed
list << l2[ 3 ]; // ratio
TQStringList date = TQStringList::split('-', l2[4]); if (parsedData.size() >= 8 && nameRegExp.exactMatch (uline)) {
list << l2[ 4 ] + " " + l2[ 5 ]; // date and time m_entryFilename = nameRegExp.capturedTexts()[2];
list << l2[ 0 ]; // attributes
list << l2[ 6 ]; // crc entry << m_entryFilename; // filename
entry << parsedData[ 1 ]; // size
entry << parsedData[ 2 ]; // packed
entry << parsedData[ 3 ]; // ratio
entry << parsedData[ 4 ] + " " + parsedData[ 5 ]; // date and time
entry << parsedData[ 0 ]; // attributes
entry << parsedData[ 6 ]; // crc
} else {
kdError ( 1601 ) << "Failed to parse rar-5+ output string: \"" << uline << "\"" << endl;
return false;
} }
}
// send to GUI // send to GUI
if ( l2[6] == "00000000" ) // Use addOrUpdateItem() rather than addItem() due to recent RAR version
{ // place directories in archive after their content.
// folders have CRC equal to 00000000 FileLVI *item = m_gui->fileList()->addOrUpdateItem( entry );
// RAR utilities show the folders at the end of the listing so the folders
// have been already added to the listview at this point without specifying // But archives packaged with older versions of ark may have directories
// all the columns but the name. Update the item with the missing info // entries first, so make sure they will get an appropriate icon
m_gui->fileList()->updateItem( list ); if (item && entry[5].find('d', 0, false) != -1) {
// check attr's for d (case insensitive to handle windows archives)
item->setPixmap( 0, KMimeType::mimeType( "inode/directory" )->pixmap( TDEIcon::Small ) );
} }
else
m_gui->fileList()->addItem( list );
return true; return true;
} }

Loading…
Cancel
Save