00001
00002 #include <config.h>
00003
00004 #include "kmmimeparttree.h"
00005
00006 #include "kmreaderwin.h"
00007 #include "partNode.h"
00008 #include "kmmsgpart.h"
00009 #include "kmkernel.h"
00010 #include "kmcommands.h"
00011
00012 #include <kdebug.h>
00013 #include <klocale.h>
00014 #include <kfiledialog.h>
00015 #include <kmessagebox.h>
00016 #include <kiconloader.h>
00017
00018 #include <qheader.h>
00019 #include <qpopupmenu.h>
00020 #include <qstyle.h>
00021
00022 KMMimePartTree::KMMimePartTree( KMReaderWin* readerWin,
00023 QWidget* parent,
00024 const char* name )
00025 : KListView( parent, name ),
00026 mReaderWin( readerWin ), mSizeColumn(0)
00027 {
00028 setStyleDependantFrameWidth();
00029 addColumn( i18n("Description") );
00030 addColumn( i18n("Type") );
00031 addColumn( i18n("Encoding") );
00032 mSizeColumn = addColumn( i18n("Size") );
00033 setColumnAlignment( 3, Qt::AlignRight );
00034
00035 restoreLayoutIfPresent();
00036 connect( this, SIGNAL( clicked( QListViewItem* ) ),
00037 this, SLOT( itemClicked( QListViewItem* ) ) );
00038 connect( this, SIGNAL( contextMenuRequested( QListViewItem*,
00039 const QPoint&, int ) ),
00040 this, SLOT( itemRightClicked( QListViewItem*, const QPoint& ) ) );
00041 setSelectionMode( QListView::Extended );
00042 setRootIsDecorated( false );
00043 setAllColumnsShowFocus( true );
00044 setShowToolTips( true );
00045 setSorting(-1);
00046 }
00047
00048
00049 static const char configGroup[] = "MimePartTree";
00050
00051 KMMimePartTree::~KMMimePartTree() {
00052 saveLayout( KMKernel::config(), configGroup );
00053 }
00054
00055
00056 void KMMimePartTree::restoreLayoutIfPresent() {
00057
00058 setColumnWidthMode( 0, Manual );
00059 header()->setStretchEnabled( true, 0 );
00060
00061 if ( KMKernel::config()->hasGroup( configGroup ) ) {
00062
00063 restoreLayout( KMKernel::config(), configGroup );
00064
00065 for ( int i = 1 ; i < 4 ; ++i )
00066 setColumnWidthMode( i, Manual );
00067 } else {
00068
00069 for ( int i = 1 ; i < 4 ; ++i )
00070 setColumnWidthMode( i, Maximum );
00071 }
00072 }
00073
00074
00075 void KMMimePartTree::itemClicked( QListViewItem* item )
00076 {
00077 if ( const KMMimePartTreeItem * i = dynamic_cast<KMMimePartTreeItem*>( item ) ) {
00078 if( mReaderWin->mRootNode == i->node() )
00079 mReaderWin->update( true );
00080 else
00081 mReaderWin->setMsgPart( i->node() );
00082 } else
00083 kdWarning(5006) << "Item was not a KMMimePartTreeItem!" << endl;
00084 }
00085
00086
00087 void KMMimePartTree::itemRightClicked( QListViewItem* item,
00088 const QPoint& point )
00089 {
00090
00091 mCurrentContextMenuItem = dynamic_cast<KMMimePartTreeItem*>( item );
00092 if ( 0 == mCurrentContextMenuItem ) {
00093 kdDebug(5006) << "Item was not a KMMimePartTreeItem!" << endl;
00094 }
00095 else {
00096 kdDebug(5006) << "\n**\n** KMMimePartTree::itemRightClicked() **\n**" << endl;
00097
00098 QPopupMenu* popup = new QPopupMenu;
00099 popup->insertItem( i18n( "Save &As..." ), this, SLOT( slotSaveAs() ) );
00100 popup->insertItem( i18n( "Save as &Encoded..." ), this,
00101 SLOT( slotSaveAsEncoded() ) );
00102 popup->insertItem( i18n( "Save All Attachments..." ), this,
00103 SLOT( slotSaveAll() ) );
00104 popup->exec( point );
00105 delete popup;
00106 mCurrentContextMenuItem = 0;
00107 }
00108 }
00109
00110 void KMMimePartTree::slotSaveAs()
00111 {
00112 QPtrList<QListViewItem> selected = selectedItems();
00113
00114 Q_ASSERT( !selected.isEmpty() );
00115 if ( selected.isEmpty() )
00116 return;
00117 if ( selected.count() == 1 )
00118 saveOneFile( selected.first(), false );
00119 else
00120 saveMultipleFiles( selected, false );
00121 }
00122
00123 void KMMimePartTree::slotSaveAsEncoded()
00124 {
00125 QPtrList<QListViewItem> selected = selectedItems();
00126
00127 Q_ASSERT( !selected.isEmpty() );
00128 if ( selected.isEmpty() )
00129 return;
00130 if ( selected.count() == 1 )
00131 saveOneFile( selected.first(), true );
00132 else
00133 saveMultipleFiles( selected, true );
00134 }
00135
00136 void KMMimePartTree::slotSaveAll()
00137 {
00138 if( childCount() == 0)
00139 return;
00140
00141 QPtrList<QListViewItem> items;
00142 for ( QListViewItemIterator lit( firstChild() ); lit.current(); ++lit ) {
00143 KMMimePartTreeItem *item = static_cast<KMMimePartTreeItem*>( lit.current() );
00144 items.append( item );
00145 }
00146
00147 saveMultipleFiles( items, false );
00148 }
00149
00150 void KMMimePartTree::saveOneFile( QListViewItem* item, bool encoded )
00151 {
00152 QPtrList<partNode> parts;
00153 parts.append( static_cast<KMMimePartTreeItem *>(item)->node() );
00154 mReaderWin->setUpdateAttachment();
00155 KMSaveAttachmentsCommand *command = new KMSaveAttachmentsCommand( this, parts,
00156 mReaderWin->message(), encoded );
00157 command->start();
00158 }
00159
00160 void KMMimePartTree::saveMultipleFiles( const QPtrList<QListViewItem>& selected, bool encoded )
00161 {
00162 QPtrListIterator<QListViewItem> it( selected );
00163 QPtrList<partNode> parts;
00164 while ( it.current() )
00165 {
00166 parts.append( static_cast<KMMimePartTreeItem *>(it.current())->node() );
00167 ++it;
00168 }
00169 mReaderWin->setUpdateAttachment();
00170 KMSaveAttachmentsCommand *command = new KMSaveAttachmentsCommand( this, parts,
00171 mReaderWin->message(), encoded );
00172 command->start();
00173 }
00174
00175
00176
00177 void KMMimePartTree::setStyleDependantFrameWidth()
00178 {
00179
00180 int frameWidth;
00181 if( style().isA("KeramikStyle") )
00182 frameWidth = style().pixelMetric( QStyle::PM_DefaultFrameWidth ) - 1;
00183 else
00184 frameWidth = style().pixelMetric( QStyle::PM_DefaultFrameWidth );
00185 if ( frameWidth < 0 )
00186 frameWidth = 0;
00187 if ( frameWidth != lineWidth() )
00188 setLineWidth( frameWidth );
00189 }
00190
00191
00192
00193 void KMMimePartTree::styleChange( QStyle& oldStyle )
00194 {
00195 setStyleDependantFrameWidth();
00196 KListView::styleChange( oldStyle );
00197 }
00198
00199
00200 void KMMimePartTree::correctSize( QListViewItem * item )
00201 {
00202 if (!item) return;
00203
00204 KIO::filesize_t totalSize = 0;
00205 QListViewItem * myChild = item->firstChild();
00206 while ( myChild )
00207 {
00208 totalSize += static_cast<KMMimePartTreeItem*>(myChild)->origSize();
00209 myChild = myChild->nextSibling();
00210 }
00211 if ( totalSize > static_cast<KMMimePartTreeItem*>(item)->origSize() )
00212 item->setText( mSizeColumn, KIO::convertSize(totalSize) );
00213 if ( item->parent() )
00214 correctSize( item->parent() );
00215 }
00216
00217
00218 KMMimePartTreeItem::KMMimePartTreeItem( KMMimePartTree * parent,
00219 partNode* node,
00220 const QString & description,
00221 const QString & mimetype,
00222 const QString & encoding,
00223 KIO::filesize_t size )
00224 : QListViewItem( parent, description,
00225 QString::null,
00226 encoding,
00227 KIO::convertSize( size ) ),
00228 mPartNode( node ), mOrigSize(size)
00229 {
00230 if( node )
00231 node->setMimePartTreeItem( this );
00232 setIconAndTextForType( mimetype );
00233 if ( parent )
00234 parent->correctSize(this);
00235 }
00236
00237 KMMimePartTreeItem::KMMimePartTreeItem( KMMimePartTreeItem * parent,
00238 partNode* node,
00239 const QString & description,
00240 const QString & mimetype,
00241 const QString & encoding,
00242 KIO::filesize_t size,
00243 bool revertOrder )
00244 : QListViewItem( parent, description,
00245 QString::null,
00246 encoding,
00247 KIO::convertSize( size ) ),
00248 mPartNode( node ), mOrigSize(size)
00249 {
00250 if( revertOrder && nextSibling() ){
00251 QListViewItem* sib = nextSibling();
00252 while( sib->nextSibling() )
00253 sib = sib->nextSibling();
00254 moveItem( sib );
00255 }
00256 if( node )
00257 node->setMimePartTreeItem( this );
00258 setIconAndTextForType( mimetype );
00259 if ( listView() )
00260 static_cast<KMMimePartTree*>(listView())->correctSize(this);
00261 }
00262
00263 void KMMimePartTreeItem::setIconAndTextForType( const QString & mime )
00264 {
00265 QString mimetype = mime.lower();
00266 if ( mimetype.startsWith( "multipart/" ) ) {
00267 setText( 1, mimetype );
00268 setPixmap( 0, SmallIcon("folder") );
00269 } else if ( mimetype == "application/octet-stream" ) {
00270 setText( 1, i18n("Unspecified Binary Data") );
00271 setPixmap( 0, SmallIcon("unknown") );
00272 } else {
00273 KMimeType::Ptr mtp = KMimeType::mimeType( mimetype );
00274 setText( 1, mtp ? mtp->comment() : mimetype );
00275 setPixmap( 0, mtp ? mtp->pixmap( KIcon::Small) : SmallIcon("unknown") );
00276 }
00277 }
00278
00279
00280 #include "kmmimeparttree.moc"