/*********************************************************************************
* C++ Implementation: transferitem.cpp
* Description:
*
* Begin : tis jun 3 2003
* Author : Björn Sahlström <kbjorn@users.sourceforge.net> (C) 2003
* Copyright : See COPYING file that comes with this distribution
**********************************************************************************/

//////////////////////////////////////////////////////////////////////
// Qt specific include files
#include <qpixmap.h>
#include <qdatetime.h>
//////////////////////////////////////////////////////////////////////
// KDE specific include files
#include <kmimetype.h>
#include <kicontheme.h>
#include <kio/global.h>
#include <kio/job.h>
#include <kglobal.h>
#include <klocale.h>
#include <klistview.h>
//////////////////////////////////////////////////////////////////////
// System specific include files
//////////////////////////////////////////////////////////////////////
// Application specific include files
#include "transferitem.h"
#include "transfergroupitem.h"
#include "transfer.h"
#include "transfermanager.h"
#include "misc.h"

using namespace KBear;

#include "transferitem.moc"
//-----------------------------------------------
const QPixmap TransferItem::s_uninitializedPixmap( uninitialized_xpm );
const QPixmap TransferItem::s_pausedPixmap( paused_xpm );
const QPixmap TransferItem::s_startedPixmap( started_xpm );
const QPixmap TransferItem::s_queuedPixmap( queued_xpm );
//-----------------------------------------------
TransferItem::TransferItem( TransferGroupItem* groupItem, QListViewItem* after, Transfer* transfer )
	:	QListViewItem( groupItem, after ),
		m_transfer( transfer ), m_totalSize( 0 ),
		m_processedSize( 0 ), m_hidden( false )
{
	setExpandable( true );
}

//-----------------------------------------------
TransferItem::TransferItem( TransferGroupItem* groupItem, Transfer* transfer )
	:	QListViewItem( groupItem ),
		m_transfer( transfer ), m_totalSize( 0 ),
		m_processedSize( 0 ), m_hidden( false )
{
	setExpandable( true );
}
//-----------------------------------------------
void TransferItem::init() {
	static const QString& kbearFtpStr = KGlobal::staticQString("kbearftp");
	static const QString& ftpStr = KGlobal::staticQString("ftp");

	if( m_transfer && m_transfer->status() == Transfer::Canceled ) {
		setVisible( false );
		m_hidden = true;
	}

	KMimeType::Ptr ptr = KMimeType::mimeType( m_transfer->mimetype() );

	KURL url = m_transfer->sourceURLs().first();
	if( url.protocol() == kbearFtpStr )
		url.setProtocol( ftpStr );
	QString sourceString = url.prettyURL();

	url = m_transfer->destURL();
	if( url.protocol() == kbearFtpStr )
		url.setProtocol( ftpStr );
	QString destString = url.prettyURL();

	setText( 0, sourceString );
	setPixmap( 0, ptr->pixmap( KIcon::Small, 16 ) );
	setPixmap( 1, s_uninitializedPixmap );

	m_transferTypeItem = new QListViewItem( this, i18n("Transfer Type") );
	m_statusItem = new QListViewItem( this, m_transferTypeItem, i18n("Status") );
	m_progressItem = new QListViewItem( this, m_statusItem, i18n("Progress") );
	m_speedItem = new QListViewItem( this, m_progressItem, i18n("Speed") );
	m_remainingTimeItem = new QListViewItem( this, m_speedItem, i18n("Remaining Time") );
	m_processedSizeItem = new QListViewItem( this, m_remainingTimeItem, i18n("Processed Size") );
	m_totalSizeItem = new QListViewItem( this, m_processedSizeItem, i18n("Total Size") );
	m_sourceItem = new QListViewItem( this, m_totalSizeItem, i18n("Source") );
	m_destinationItem = new QListViewItem( this, m_sourceItem, i18n("Destination") );
	m_totalDirsItem = new QListViewItem( this, m_destinationItem, i18n("Total Dirs") );
	m_totalFilesItem = new QListViewItem( this, m_totalDirsItem, i18n("Total Files") );
	m_processedDirsItem = new QListViewItem( this, m_totalFilesItem, i18n("Processed Dirs") );
	m_processedFilesItem = new QListViewItem( this, m_processedDirsItem, i18n("Processed Files") );

	m_transferTypeItem->setExpandable( false );
	m_statusItem->setExpandable( false );
	m_progressItem->setExpandable( false );
	m_speedItem->setExpandable( false );
	m_remainingTimeItem->setExpandable( false );
	m_processedSizeItem->setExpandable( false );
	m_totalSizeItem->setExpandable( false );
	m_sourceItem->setExpandable( false );
	m_destinationItem->setExpandable( false );
	m_totalDirsItem->setExpandable( false );
	m_totalFilesItem->setExpandable( false );
	m_processedDirsItem->setExpandable( false );
	m_processedFilesItem->setExpandable( false );

	slotStatusChanged( m_transfer->transferID(), m_transfer->status() );

	m_transferTypeItem->setText( 1 , (m_transfer->type()==Transfer::Move?i18n("Move"):i18n("Copy")) );
	m_progressItem->setText( 1 , i18n( "0 %" ) );
	m_speedItem->setText( 1 , i18n("%1/sec").arg( KIO::convertSize( (KIO::filesize_t)0 ) ) );

	QTime t( 0, 0 );
	m_remainingTimeItem->setText( 1 , t.toString() );
	m_sourceItem->setText( 1, sourceString );
	m_destinationItem->setText( 1, destString );


	connect( m_transfer, SIGNAL( statusChanged( long, unsigned int ) ), this, SLOT( slotStatusChanged( long, unsigned int ) ) );
	connect( TransferManager::getInstance(), SIGNAL( removingTransfer( long ) ), this, SLOT( slotTransferRemoved( long ) ) );
	connect( m_transfer, SIGNAL( percent( long, unsigned long ) ), this, SLOT( slotProgress( long, unsigned long ) ) );
	connect( m_transfer, SIGNAL( totalFiles( long, unsigned long ) ), this, SLOT( slotTotalFiles( long, unsigned long ) ) );
	connect( m_transfer, SIGNAL( totalDirs( long, unsigned long ) ), this, SLOT( slotTotalDirs( long, unsigned long ) ) );
	connect( m_transfer, SIGNAL( processedFiles( long, unsigned long ) ), this, SLOT( slotProcessedFiles( long, unsigned long ) ) );
	connect( m_transfer, SIGNAL( processedDirs( long, unsigned long ) ), this, SLOT( slotProcessedDirs( long, unsigned long ) ) );
	connect( m_transfer, SIGNAL( totalSize( long, KIO::filesize_t ) ), this, SLOT( slotTotalSize( long, KIO::filesize_t ) ) );
	connect( m_transfer, SIGNAL( processedSize( long, KIO::filesize_t ) ), this, SLOT( slotProcessedSize( long, KIO::filesize_t ) ) );
	connect( m_transfer, SIGNAL( speed( long, unsigned long ) ), this, SLOT( slotSpeed( long, unsigned long ) ) );
	connect( m_transfer, SIGNAL( copying( long, const KURL&, const KURL& ) ), this, SLOT( slotCopying( long, const KURL&, const KURL& ) ) );
	connect( m_transfer, SIGNAL( moving( long, const KURL&, const KURL& ) ), this, SLOT( slotCopying( long, const KURL&, const KURL& ) ) );
}
//-----------------------------------------------
TransferItem::~TransferItem() {
}
//-----------------------------------------------
void TransferItem::slotCopying( long, const KURL& source, const KURL& dest ) {
	static const QString& kbearFtpStr = KGlobal::staticQString("kbearftp");
	static const QString& ftpStr = KGlobal::staticQString("ftp");
	KURL url = source;
	if( url.protocol() == kbearFtpStr )
		url.setProtocol( ftpStr );
	QString sourceString = url.prettyURL();

	url = dest;
	if( url.protocol() == kbearFtpStr )
		url.setProtocol( ftpStr );
	QString destString = url.prettyURL();
	m_sourceItem->setText( 1, sourceString );
	m_destinationItem->setText( 1, destString );
}
//-----------------------------------------------
void TransferItem::slotTotalFiles( long, unsigned long files ) {
	m_totalFilesItem->setText( 1 , i18n("%1").arg( files ) );
}
//-----------------------------------------------
void TransferItem::slotProcessedFiles( long, unsigned long files ) {
	m_processedFilesItem->setText( 1 , i18n("%1").arg( files ) );
}
//-----------------------------------------------
void TransferItem::slotTotalDirs( long, unsigned long dirs ){
	m_totalDirsItem->setText( 1 , i18n("%1").arg( dirs ) );
}
//-----------------------------------------------
void TransferItem::slotProcessedDirs( long, unsigned long dirs ) {
	m_processedDirsItem->setText( 1 , i18n("%1").arg( dirs ) );
}
//-----------------------------------------------
void TransferItem::slotTotalSize( long, KIO::filesize_t size ) {
	m_totalSizeItem->setText( 1 , i18n("%1").arg( KIO::convertSize( size ) ) );
	m_totalSize = size;
}
//-----------------------------------------------
void TransferItem::slotProcessedSize( long, KIO::filesize_t size ) {
	m_processedSizeItem->setText( 1 , KIO::convertSize( size ) );
	m_processedSize = size;
}
//-----------------------------------------------
void TransferItem::slotSpeed( long, unsigned long bytes_per_sec ) {
	QString tmp = KIO::convertSize( (KIO::filesize_t)bytes_per_sec );
	m_speedItem->setText( 1 , i18n("%1/sec").arg( tmp ) );
	if( bytes_per_sec > 0 ) {
		QTime t = KIO::calculateRemaining( m_totalSize, m_processedSize, (KIO::filesize_t)bytes_per_sec );
		m_remainingTimeItem->setText( 1 , t.toString() );
	}
}
//-----------------------------------------------
void TransferItem::slotProgress( long, unsigned long progress ) {
	QString p = i18n("%1 %").arg( progress );
	m_progressItem->setText( 1 , p );
	m_progressItem->setPixmap( 1 , KBear::createProgressPixmap( progress ) );
	setText( 1 , p );
}
//-----------------------------------------------
void TransferItem::slotTransferRemoved( long ID ) {
	if( m_transfer && m_transfer->transferID() == ID )
		delete this;
}
//-----------------------------------------------
void TransferItem::slotStatusChanged( long ID, unsigned int status ) {
	if( ! m_transfer ) {
		delete this;
	}
	else if( m_transfer->transferID() == ID ) {
		switch( status ) {
			case Transfer::Queued: {
				setVisible( true );
				m_hidden = false;
				QString tmp = i18n("Queued");
				setText( 1, tmp );
				setPixmap( 1, s_queuedPixmap );
				m_statusItem->setText( 1, tmp );
				m_statusItem->setPixmap( 1, s_queuedPixmap );
				emit shown();
				break;
			}
			case Transfer::Finished: {
			} // fall through
			case Transfer::Stopped: {
			} // fall through
			case Transfer::Canceled: {
				setVisible( false );
				m_hidden = true;
				emit hidden();
				break;
			}
			case Transfer::Paused: {
				setPixmap( 1, s_pausedPixmap );
				m_statusItem->setText( 1, i18n("Paused") );
				m_statusItem->setPixmap( 1, s_pausedPixmap );
				break;
			}
			case Transfer::Started: {
				setVisible( true );
				m_hidden = false;
				setText( 1, QString::null );
				setPixmap( 1, s_startedPixmap );
				m_statusItem->setText( 1, i18n("Started") );
				m_statusItem->setPixmap( 1, s_startedPixmap );
				emit shown();
				break;
			}
			default: {
				setText( 1, QString::null );
				setPixmap( 1, s_uninitializedPixmap );
				m_statusItem->setText( 1, i18n("Uninitialized") );
				m_statusItem->setPixmap( 1, s_uninitializedPixmap );
				setVisible( false );
				m_hidden = true;
				emit hidden();
				break;
			}
		}
	}
}
//-----------------------------------------------
