Home | All Classes | Main Classes | Annotated | Grouped Classes | Functions

An FTP client

This example implements a FTP client. It uses QUrlOperator (which in turn uses QFtp) to perform its FTP commands.


The API of the FtpMainWindow class (ftpmainwindow.h):

/****************************************************************************
** $Id:  qt/ftpmainwindow.h   3.0.5   edited Oct 12 2001 $
**
** Copyright (C) 1992-2000 Trolltech AS.  All rights reserved.
**
** This file is part of an example program for Qt.  This example
** program may be used, distributed and modified without limitation.
**
*****************************************************************************/

#ifndef FTPMAINWINDOW_H
#define FTPMAINWINDOW_H

#include <qmainwindow.h>
#include <qurloperator.h>

class FtpView;
class QSplitter;
class QVBox;
class QSpinBox;
class QComboBox;
class QLineEdit;
class QNetworkOperation;
class QLabel;
class QProgressBar;

class FtpMainWindow : public QMainWindow
{
    Q_OBJECT

public:
    FtpMainWindow();

    QSplitter *mainSplitter() const {
        return splitter;
    }

private:
    void setupLeftSide();
    void setupRightSide();
    void setupCenterCommandBar();
    void setup();

private slots:
    void slotLocalDirChanged( const QString &path );
    void slotLocalDirChanged( const QUrlInfo &info );
    void slotRemoteDirChanged( const QString &path );
    void slotRemoteDirChanged( const QUrlInfo &info );
    void slotConnect();
    void slotUpload();
    void slotDownload();
    void slotLocalStart( QNetworkOperation * );
    void slotLocalFinished( QNetworkOperation * );
    void slotRemoteStart( QNetworkOperation * );
    void slotRemoteFinished( QNetworkOperation * );
    void slotLocalDataTransferProgress( int, int, QNetworkOperation * );
    void slotRemoteDataTransferProgress( int, int, QNetworkOperation * );
    void slotLocalMkDir();
    void slotLocalRemove();
    void slotRemoteMkDir();
    void slotRemoteRemove();
    void slotConnectionStateChanged( int, const QString &msg );

private:
    QSplitter *splitter;
    QVBox *mainWidget;
    FtpView *leftView, *rightView;
    QComboBox *localCombo, *remoteHostCombo, *remotePathCombo, *userCombo;
    QLineEdit *passLined;
    QSpinBox *portSpin;
    QUrlOperator localOperator, remoteOperator, oldLocal, oldRemote;
    QLabel *progressLabel1, *progressLabel2;
    QProgressBar *progressBar1, *progressBar2;

};

#endif


The Implementation of the FtpMainWindow class (ftpmainwindow.cpp):

/****************************************************************************
** $Id:  qt/ftpmainwindow.cpp   3.0.5   edited Oct 12 2001 $
**
** Copyright (C) 1992-2000 Trolltech AS.  All rights reserved.
**
** This file is part of an example program for Qt.  This example
** program may be used, distributed and modified without limitation.
**
*****************************************************************************/

#include "ftpmainwindow.h"
#include "ftpview.h"

#include <qvbox.h>
#include <qhbox.h>
#include <qsplitter.h>
#include <qcombobox.h>
#include <qlabel.h>
#include <qspinbox.h>
#include <qlineedit.h>
#include <qpushbutton.h>
#include <qmessagebox.h>
#include <qprogressbar.h>
#include <qdir.h>
#include <qinputdialog.h>
#include <qapplication.h>
#include <qstatusbar.h>

FtpMainWindow::FtpMainWindow()
    : QMainWindow(),
      localOperator( "/" )
{
    setup();

    // connect to the signals of the local QUrlOperator - this will be used to
    // work on the local file system (listing dirs, etc.) and to copy files
    // TO the local filesystem (downloading)
    connect( &localOperator, SIGNAL( newChildren( const QValueList<QUrlInfo> &, QNetworkOperation * ) ),
             leftView, SLOT( slotInsertEntries( const QValueList<QUrlInfo> & ) ) );
    connect( &localOperator, SIGNAL( start( QNetworkOperation * ) ),
             this, SLOT( slotLocalStart( QNetworkOperation *) ) );
    connect( &localOperator, SIGNAL( finished( QNetworkOperation * ) ),
             this, SLOT( slotLocalFinished( QNetworkOperation *) ) );
    connect( leftView, SIGNAL( itemSelected( const QUrlInfo & ) ),
             this, SLOT( slotLocalDirChanged( const QUrlInfo & ) ) );
    connect( &localOperator, SIGNAL( dataTransferProgress( int, int, QNetworkOperation * ) ),
             this, SLOT( slotLocalDataTransferProgress( int, int, QNetworkOperation * ) ) );

    // connect to the signals of the remote QUrlOperator - this will be used to
    // work on the remote file system (on the FTP Server) and to copy files
    // TO the ftp server (uploading)
    connect( &remoteOperator, SIGNAL( newChildren( const QValueList<QUrlInfo> &, QNetworkOperation * ) ),
             rightView, SLOT( slotInsertEntries( const QValueList<QUrlInfo> & ) ) );
    connect( &remoteOperator, SIGNAL( start( QNetworkOperation * ) ),
             this, SLOT( slotRemoteStart( QNetworkOperation *) ) );
    connect( &remoteOperator, SIGNAL( finished( QNetworkOperation * ) ),
             this, SLOT( slotRemoteFinished( QNetworkOperation *) ) );
    connect( rightView, SIGNAL( itemSelected( const QUrlInfo & ) ),
             this, SLOT( slotRemoteDirChanged( const QUrlInfo & ) ) );
    connect( &remoteOperator, SIGNAL( dataTransferProgress( int, int, QNetworkOperation * ) ),
             this, SLOT( slotRemoteDataTransferProgress( int, int, QNetworkOperation * ) ) );
    connect( &remoteOperator, SIGNAL( connectionStateChanged( int, const QString & ) ),
             this, SLOT( slotConnectionStateChanged( int, const QString & ) ) );

    // read the local filesystem at the beginning once
    localOperator.listChildren();

    // create status bar
    (void)statusBar();
}

void FtpMainWindow::setupLeftSide()
{
    // Setup the left side of the GUI, this is the listview
    // of the local filesystem

    QVBox *layout = new QVBox( splitter );
    layout->setSpacing( 5 );
    layout->setMargin( 5 );

    QHBox *h = new QHBox( layout );
    h->setSpacing( 5 );
    QLabel *l = new QLabel( tr( "Local Path:" ), h );
    l->setFixedWidth( l->sizeHint().width() );
    localCombo = new QComboBox( TRUE, h );
    localCombo->insertItem( "/" );

    connect( localCombo, SIGNAL( activated( const QString & ) ),
             this, SLOT( slotLocalDirChanged( const QString & ) ) );

    leftView = new FtpView( layout );

    QHBox *bottom = new QHBox( layout );
    bottom->setSpacing( 5 );
    QPushButton *bMkDir = new QPushButton( tr( "New Directory" ), bottom );
    QPushButton *bRemove = new QPushButton( tr( "Remove" ), bottom );
    connect( bMkDir, SIGNAL( clicked() ),
             this, SLOT( slotLocalMkDir() ) );
    connect( bRemove, SIGNAL( clicked() ),
             this, SLOT( slotLocalRemove() ) );

    splitter->setResizeMode( layout, QSplitter::Stretch );
}

void FtpMainWindow::setupRightSide()
{
    // Setup the right side of the GUI, this is the listview
    // of the remote filesystem (FTP), needs also lineedits/combos
    // for username, password, etc.

    QVBox *layout = new QVBox( splitter );
    layout->setSpacing( 5 );
    layout->setMargin( 5 );

    QHBox *h = new QHBox( layout );
    h->setSpacing( 5 );
    QLabel *l = new QLabel( tr( "Remote Host:" ), h );
    l->setFixedWidth( l->sizeHint().width() );
    remoteHostCombo = new QComboBox( TRUE, h );

    l = new QLabel( tr( "Port:" ), h );
    l->setFixedWidth( l->sizeHint().width() );
    portSpin = new QSpinBox( 0, 32767, 1, h );
    portSpin->setValue( 21 );
    portSpin->setFixedWidth( portSpin->sizeHint().width() );
    remoteOperator.setPort( portSpin->value() );

    h = new QHBox( layout );
    h->setSpacing( 5 );
    l = new QLabel( tr( "Remote Path:" ), h );
    l->setFixedWidth( l->sizeHint().width() );
    remotePathCombo = new QComboBox( TRUE, h );

    h = new QHBox( layout );
    h->setSpacing( 5 );
    l = new QLabel( tr( "Username:" ), h );
    l->setFixedWidth( l->sizeHint().width() );
    userCombo = new QComboBox( TRUE, h );

    l = new QLabel( tr( "Password:" ), h );
    l->setFixedWidth( l->sizeHint().width() );
    passLined = new QLineEdit( h );
    passLined->setEchoMode( QLineEdit::Password );

    rightView = new FtpView( layout );

    QHBox *bottom = new QHBox( layout );
    bottom->setSpacing( 5 );
    QPushButton *bMkDir = new QPushButton( tr( "New Directory" ), bottom );
    QPushButton *bRemove = new QPushButton( tr( "Remove" ), bottom );
    connect( bMkDir, SIGNAL( clicked() ),
             this, SLOT( slotRemoteMkDir() ) );
    connect( bRemove, SIGNAL( clicked() ),
             this, SLOT( slotRemoteRemove() ) );

    splitter->setResizeMode( layout, QSplitter::Stretch );

    connect( remotePathCombo, SIGNAL( activated( const QString & ) ),
             this, SLOT( slotRemoteDirChanged( const QString & ) ) );
}

void FtpMainWindow::setupCenterCommandBar()
{
    // Setup the command bar in the middle between the two views

    QVBox *w = new QVBox( splitter );
    splitter->setResizeMode( w, QSplitter::FollowSizeHint );
    w->setSpacing( 5 );
    w->setMargin( 5 );

    QPushButton *bConnect = new QPushButton( tr( "&Connect" ), w );
    (void)new QWidget( w );
    QPushButton *bUpload = new QPushButton( tr( "== &Upload ==>" ), w );
    QPushButton *bDownload = new QPushButton( tr( "<== &Download ==" ), w );
    (void)new QWidget( w );

    connect( bConnect, SIGNAL( clicked() ),
             this, SLOT( slotConnect() ) );
    connect( bUpload, SIGNAL( clicked() ),
             this, SLOT( slotUpload() ) );
    connect( bDownload, SIGNAL( clicked() ),
             this, SLOT( slotDownload() ) );
}

void FtpMainWindow::setup()
{
    // Setup the GUI

    mainWidget = new QVBox( this );
    splitter = new QSplitter( mainWidget );
    setupLeftSide();
    setupCenterCommandBar();
    setupRightSide();

    progressLabel1 = new QLabel( tr( "No Operation in Progress" ), mainWidget );
    progressBar1 = new QProgressBar( mainWidget );
    progressLabel2 = new QLabel( tr( "No Operation in Progress" ), mainWidget );
    progressBar2 = new QProgressBar( mainWidget );

    progressLabel1->hide();
    progressBar1->hide();
    progressLabel2->hide();
    progressBar2->hide();

    setCentralWidget( mainWidget );
}

void FtpMainWindow::slotLocalDirChanged( const QString &path )
{
    // The user changed the path on the left side

    oldLocal = localOperator;
    localOperator.setPath( path );
    localOperator.listChildren();
}

void FtpMainWindow::slotLocalDirChanged( const QUrlInfo &info )
{
    // The user changed the path on the left side

    oldLocal = localOperator;
    localOperator.addPath( info.name() );
    localOperator.listChildren();
    localCombo->insertItem( localOperator.path(), 0 );
    localCombo->setCurrentItem( 0 );
}

void FtpMainWindow::slotRemoteDirChanged( const QString &path )
{
    // The user changed the path on the right side

    if ( !remoteOperator.isValid() )
        return;
    oldRemote = remoteOperator;
    remoteOperator.setPath( path );
    remoteOperator.listChildren();
}

void FtpMainWindow::slotRemoteDirChanged( const QUrlInfo &info )
{
    // The user changed the path on the right side

    oldRemote = remoteOperator;
    remoteOperator.addPath( info.name() );
    remoteOperator.listChildren();
    remotePathCombo->insertItem( remoteOperator.path(), 0 );
    remotePathCombo->setCurrentItem( 0 );
}

void FtpMainWindow::slotConnect()
{
    // The user pressed the connect button, so let's connect to the
    // FTP server
    // First we need to set stuff (host, path, etc.) which the user
    // entered on the right side to the remote QUrlOperator

    // protocol + hostname
    QString s = "ftp://" + remoteHostCombo->currentText();
    oldRemote = remoteOperator;
    remoteOperator = s;

    // path on the server
    if ( !remotePathCombo->currentText().isEmpty() )
        remoteOperator.setPath( remotePathCombo->currentText() );
    else
        remoteOperator.setPath( "/" );

    // if nothing or "ftp" or "anonymous" has been entered into the username combo,
    // let's connect anonymous, else private with password
    if ( !userCombo->currentText().isEmpty() &&
         userCombo->currentText().lower() != "anonymous" &&
         userCombo->currentText().lower() != "ftp" ) {
        remoteOperator.setUser( userCombo->currentText() );
        remoteOperator.setPassword( passLined->text() );
    }

    // set the port
    remoteOperator.setPort( portSpin->value() );

    // finally read the directory on the ftp server
    remoteOperator.listChildren();
}

void FtpMainWindow::slotUpload()
{
    // the user pressed the upload button

    // if files have been selected on the left side (local filesystem)
    QValueList<QUrlInfo> files = leftView->selectedItems();
    if ( files.isEmpty() )
        return;

    // create a list of the URLs which should be copied
    QStringList lst;
    QValueList<QUrlInfo>::Iterator it = files.begin();
    for ( ; it != files.end(); ++it )
        lst << QUrl( localOperator, ( *it ).name() );

    // copy the list of selected files to the directory in which the
    // remoteOperator currently is (upload)
    remoteOperator.copy( lst, remoteOperator, FALSE );
}

void FtpMainWindow::slotDownload()
{
    // if the user pressed the download button

    // if files have been selected on the right side (remote filesystem)
    QValueList<QUrlInfo> files = rightView->selectedItems();
    if ( files.isEmpty() )
        return;

    // create a list of the URLs which should be downloaded
    QStringList lst;
    QValueList<QUrlInfo>::Iterator it = files.begin();
    for ( ; it != files.end(); ++it )
        lst << QUrl( remoteOperator, ( *it ).name() );

    // copy the list of selected files to the directory in which the
    // localOperator currently is (download)
    localOperator.copy( lst, localOperator, FALSE );
}

void FtpMainWindow::slotLocalStart( QNetworkOperation *op )
{
    // this slot is always called if the local QUrlOperator starts
    // listing a directory or dowloading a file

    if ( !op )
        return;

    if ( op->operation() == QNetworkProtocol::OpListChildren ) {
        // start listing a dir? clear the left view!
        leftView->clear();
    } else if ( op->operation() == QNetworkProtocol::OpGet ) {
        // start downloading a file? reset the progress bar!
        progressBar1->setTotalSteps( 0 );
        progressBar1->reset();
    }
}

void FtpMainWindow::slotLocalFinished( QNetworkOperation *op )
{
    // this slot is always called if the local QUrlOperator finished
    // an operation

    if ( !op )
        return;

    if ( op && op->state() == QNetworkProtocol::StFailed ) {
        // an error happend, let the user know that
        QMessageBox::critical( this, tr( "ERROR" ), op->protocolDetail() );

        // do something depending in the error code
        int ecode = op->errorCode();
        if ( ecode == QNetworkProtocol::ErrListChildren || ecode == QNetworkProtocol::ErrParse ||
             ecode == QNetworkProtocol::ErrUnknownProtocol || ecode == QNetworkProtocol::ErrLoginIncorrect ||
             ecode == QNetworkProtocol::ErrValid || ecode == QNetworkProtocol::ErrHostNotFound ||
             ecode == QNetworkProtocol::ErrFileNotExisting ) {
            localOperator = oldLocal;
            localCombo->setEditText( localOperator.path() );
            localOperator.listChildren();
        }
    } else if ( op->operation() == QNetworkProtocol::OpPut ) {
        // finished saving the downloaded file? reread the dir and hide the progress bar
        localOperator.listChildren();
        progressLabel1->hide();
        progressBar1->hide();
    } else if ( op->operation() == QNetworkProtocol::OpGet ) {
        // finished reading a file from the ftp server? reset the progress bar
        progressBar1->setTotalSteps( 0 );
        progressBar1->reset();
    }

}

void FtpMainWindow::slotRemoteStart( QNetworkOperation *op )
{
    // this slot is always called if the remote QUrlOperator starts
    // listing a directory or uploading a file

    if ( !op )
        return;

    if ( op->operation() == QNetworkProtocol::OpListChildren ) {
        // start listing a dir? clear the right view!
        rightView->clear();
    } else if ( op->operation() == QNetworkProtocol::OpGet ) {
        // start downloading a file? reset the progress bar!
        progressBar2->setTotalSteps( 0 );
        progressBar2->reset();
    }
}

void FtpMainWindow::slotRemoteFinished( QNetworkOperation *op )
{
    // this slot is always called if the remote QUrlOperator finished
    // an operation

    if ( !op )
        return;

    if ( op && op->state() == QNetworkProtocol::StFailed ) {
        // an error happend, let the user know that
        QMessageBox::critical( this, tr( "ERROR" ), op->protocolDetail() );

        // do something depending in the error code
        int ecode = op->errorCode();
        if ( ecode == QNetworkProtocol::ErrListChildren || ecode == QNetworkProtocol::ErrParse ||
             ecode == QNetworkProtocol::ErrUnknownProtocol || ecode == QNetworkProtocol::ErrLoginIncorrect ||
             ecode == QNetworkProtocol::ErrValid || ecode == QNetworkProtocol::ErrHostNotFound ||
             ecode == QNetworkProtocol::ErrFileNotExisting ) {
            remoteOperator = oldRemote;
            remoteHostCombo->setEditText( remoteOperator.host() );
            remotePathCombo->setEditText( remoteOperator.path() );
            passLined->setText( remoteOperator.password() );
            userCombo->setEditText( remoteOperator.user() );
            portSpin->setValue( remoteOperator.port() );
            remoteOperator.listChildren();
        }
    } else if ( op->operation() == QNetworkProtocol::OpListChildren ) {
        // finished reading a dir? set the correct path to the pth combo of the right view
        remotePathCombo->setEditText( remoteOperator.path() );
    } else if ( op->operation() == QNetworkProtocol::OpPut ) {
        // finished saving the uploaded file? reread the dir and hide the progress bar
        remoteOperator.listChildren();
        progressLabel2->hide();
        progressBar2->hide();
    } else if ( op->operation() == QNetworkProtocol::OpGet ) {
        // finished reading a file from the local filesystem? reset the progress bar
        progressBar2->setTotalSteps( 0 );
        progressBar2->reset();
    }
}

void FtpMainWindow::slotLocalDataTransferProgress( int bytesDone, int bytesTotal,
                                                   QNetworkOperation *op )
{
    // Show the progress here of the local QUrlOperator reads or writes data

    if ( !op )
        return;

    if ( !progressBar1->isVisible() ) {
        if ( bytesDone < bytesTotal) {
            progressLabel1->show();
            progressBar1->show();
            progressBar1->setTotalSteps( bytesTotal );
            progressBar1->setProgress( 0 );
            progressBar1->reset();
        } else
            return;
    }

    if ( progressBar1->totalSteps() == bytesTotal )
        progressBar1->setTotalSteps( bytesTotal );

    if ( op->operation() == QNetworkProtocol::OpGet )
        progressLabel1->setText( tr( "Read: %1" ).arg( op->arg( 0 ) ) );
    else if ( op->operation() == QNetworkProtocol::OpPut )
        progressLabel1->setText( tr( "Write: %1" ).arg( op->arg( 0 ) ) );
    else
        return;

    progressBar1->setProgress( bytesDone );
}

void FtpMainWindow::slotRemoteDataTransferProgress( int bytesDone, int bytesTotal,
                                                    QNetworkOperation *op )
{
    // Show the progress here of the remote QUrlOperator reads or writes data

    if ( !op )
        return;

    if ( !progressBar2->isVisible() ) {
        if ( bytesDone < bytesTotal) {
            progressLabel2->show();
            progressBar2->show();
            progressBar2->setTotalSteps( bytesTotal );
            progressBar2->setProgress( 0 );
            progressBar2->reset();
        } else
            return;
    }

    if ( progressBar2->totalSteps() != bytesTotal )
        progressBar2->setTotalSteps( bytesTotal );

    if ( op->operation() == QNetworkProtocol::OpGet )
        progressLabel2->setText( tr( "Read: %1" ).arg( op->arg( 0 ) ) );
    else if ( op->operation() == QNetworkProtocol::OpPut )
        progressLabel2->setText( tr( "Write: %1" ).arg( op->arg( 0 ) ) );
    else
        return;

    progressBar2->setProgress( bytesDone );
}

void FtpMainWindow::slotLocalMkDir()
{
    // create a dir on the local filesystem

    bool ok = FALSE;
    QString name = QInputDialog::getText( tr( "Directory Name:" ), QString::null, QLineEdit::Normal, QString::null, &ok, this );

    if ( !name.isEmpty() && ok )
        localOperator.mkdir( name );
}

void FtpMainWindow::slotLocalRemove()
{
}

void FtpMainWindow::slotRemoteMkDir()
{
    // create a dir on the remote filesystem (FTP server)

    bool ok = FALSE;
    QString name = QInputDialog::getText( tr( "Directory Name:" ), QString::null, QLineEdit::Normal, QString::null, &ok, this );

    if ( !name.isEmpty() && ok )
        remoteOperator.mkdir( name );
}

void FtpMainWindow::slotRemoteRemove()
{
}

void FtpMainWindow::slotConnectionStateChanged( int, const QString &msg )
{
    statusBar()->message( msg );
}


The API of the FtpViewItem and FtpView classes (ftpview.h):

/****************************************************************************
** $Id:  qt/ftpview.h   3.0.5   edited Oct 12 2001 $
**
** Copyright (C) 1992-2000 Trolltech AS.  All rights reserved.
**
** This file is part of an example program for Qt.  This example
** program may be used, distributed and modified without limitation.
**
*****************************************************************************/

#ifndef FTPVIEW_H
#define FTPVIEW_H

#include <qlistview.h>
#include <qvaluelist.h>
#include <qurlinfo.h>

class FtpViewItem : public QListViewItem
{
public:
    FtpViewItem( QListView *parent, const QUrlInfo &i );

    int compare( QListViewItem * i, int col, bool ascending ) const;
    QString text( int c ) const;
    const QPixmap* pixmap( int c ) const;

    QUrlInfo entryInfo() {
        return info;
    }

private:
    QUrlInfo info;

};

class FtpView : public QListView
{
    Q_OBJECT

public:
    FtpView( QWidget *parent );
    QValueList<QUrlInfo> selectedItems() const;

public slots:
    void slotInsertEntries( const QValueList<QUrlInfo> &info );

signals:
    void itemSelected( const QUrlInfo &info );

private slots:
    void slotSelected( QListViewItem *item );

};

#endif


Their Implementation (ftpview.cpp):

/****************************************************************************
** $Id:  qt/ftpview.cpp   3.0.5   edited Oct 12 2001 $
**
** Copyright (C) 1992-2000 Trolltech AS.  All rights reserved.
**
** This file is part of an example program for Qt.  This example
** program may be used, distributed and modified without limitation.
**
*****************************************************************************/

#include "ftpview.h"

#include <qpixmap.h>
#include <qvaluelist.h>

/* XPM */
static const char* closed_xpm[]={
    "15 15 6 1",
    ". c None",
    "b c #ffff00",
    "d c #000000",
    "* c #999999",
    "a c #cccccc",
    "c c #ffffff",
    "...............",
    "..*****........",
    ".*ababa*.......",
    "*abababa******.",
    "*cccccccccccc*d",
    "*cbababababab*d",
    "*cabababababa*d",
    "*cbababababab*d",
    "*cabababababa*d",
    "*cbababababab*d",
    "*cabababababa*d",
    "*cbababababab*d",
    "**************d",
    ".dddddddddddddd",
    "..............."};

/* XPM */
static const char* file_xpm[]={
    "13 15 5 1",
    ". c #7f7f7f",
    "# c None",
    "c c #000000",
    "b c #bfbfbf",
    "a c #ffffff",
    "..........###",
    ".aaaaaaaab.##",
    ".aaaaaaaaba.#",
    ".aaaaaaaacccc",
    ".aaaaaaaaaabc",
    ".aaaaaaaaaabc",
    ".aaaaaaaaaabc",
    ".aaaaaaaaaabc",
    ".aaaaaaaaaabc",
    ".aaaaaaaaaabc",
    ".aaaaaaaaaabc",
    ".aaaaaaaaaabc",
    ".aaaaaaaaaabc",
    ".bbbbbbbbbbbc",
    "ccccccccccccc"};

QPixmap *folderIcon = 0;
QPixmap *fileIcon = 0;

FtpViewItem::FtpViewItem( QListView *parent, const QUrlInfo &i )
    : QListViewItem( parent, i.name() ), info( i )
{
}

int FtpViewItem::compare( QListViewItem * i, int col, bool ascending ) const
{
    FtpViewItem *other = (FtpViewItem*)i;
    switch ( col ) {
    case 1:
        if ( info.size() == other->info.size() )
            return 0;
        else
            return info.size() < other->info.size() ? -1 : 1;
    case 2:
        if ( info.lastModified() == other->info.lastModified() )
            return 0;
        else
            return info.lastModified() < other->info.lastModified() ? -1 : 1;
    default:
        // use default method for colum 0 and others added in the future
        return QListViewItem::compare( i, col, ascending );
    };
}

QString FtpViewItem::text( int c ) const
{
    switch ( c ) {
    case 0:
        return info.name();
    case 1:
        return QString::number( info.size() );
    case 2:
        return info.lastModified().toString();
    }

    return "????";
}

const QPixmap *FtpViewItem::pixmap( int c ) const
{
    if ( !folderIcon )
        folderIcon = new QPixmap( closed_xpm );
    if ( !fileIcon )
        fileIcon = new QPixmap( file_xpm );
    if ( info.isDir() && c == 0 )
        return folderIcon;
    else if ( info.isFile() && c == 0 )
        return fileIcon;
    return 0;
}


FtpView::FtpView( QWidget *parent )
    : QListView( parent )
{
    addColumn( tr( "Name" ) );
    addColumn( tr( "Size" ) );
    addColumn( tr( "Last Modified" ) );
    setColumnAlignment( 1, Qt::AlignRight );
    setShowSortIndicator( TRUE );
    setAllColumnsShowFocus( TRUE );
    setSelectionMode( Extended );

    connect( this, SIGNAL( doubleClicked( QListViewItem * ) ),
             this, SLOT( slotSelected( QListViewItem * ) ) );
    connect( this, SIGNAL( returnPressed( QListViewItem * ) ),
             this, SLOT( slotSelected( QListViewItem * ) ) );
}

void FtpView::slotInsertEntries( const QValueList<QUrlInfo> &info )
{
    QValueList<QUrlInfo>::ConstIterator it;
    for( it = info.begin(); it != info.end(); ++it ) {
        if ( (*it).name() != ".." && (*it).name() != "." && (*it).name()[ 0 ] == '.' )
            continue;
        FtpViewItem *item = new FtpViewItem( this, (*it) );
        if ( (*it).isDir() )
            item->setSelectable( FALSE );
    }
}

void FtpView::slotSelected( QListViewItem *item )
{
    if ( !item )
        return;

    FtpViewItem *i = (FtpViewItem*)item;
    if ( i->entryInfo().isDir() )
        emit itemSelected( i->entryInfo() );
}

QValueList<QUrlInfo> FtpView::selectedItems() const
{
    QValueList<QUrlInfo> lst;
    QListViewItemIterator it( (QListView*)this );
    for ( ; it.current(); ++it ) {
        if ( it.current()->isSelected() ) {
            lst << ( (FtpViewItem*)it.current() )->entryInfo();
        }
    }

    return lst;
}


Main (main.cpp):

/****************************************************************************
** $Id:  qt/main.cpp   3.0.5   edited Nov 6 2001 $
**
** Copyright (C) 1992-2000 Trolltech AS.  All rights reserved.
**
** This file is part of an example program for Qt.  This example
** program may be used, distributed and modified without limitation.
**
*****************************************************************************/

#include <qapplication.h>
#include <qnetwork.h>
#include <qsplitter.h>

#include "ftpmainwindow.h"

int main( int argc, char **argv )
{
    QApplication a( argc, argv );

    // call this to register the built-in network protocols, e.g. FTP
    // and HTTP.
    qInitNetworkProtocols();

    FtpMainWindow m;
    a.setMainWidget( &m );
    QValueList<int> sizes;
    sizes << 300 << 70 << 300;
    m.mainSplitter()->setSizes( sizes );
    m.resize( 800, 600 );
    m.show();
    return a.exec();
}

See also Network Examples.


Copyright © 2002 TrolltechTrademarks
Qt version 3.0.5