home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 10 Tools / 10-Tools.zip / qt3_emx.zip / examples / network / ftpclient / ftpmainwindow.cpp < prev    next >
Encoding:
C/C++ Source or Header  |  2001-10-11  |  17.5 KB  |  534 lines

  1. /****************************************************************************
  2. ** $Id:  qt/ftpmainwindow.cpp   3.0.0   edited Jun 1 18:44 $
  3. **
  4. ** Copyright (C) 1992-2000 Trolltech AS.  All rights reserved.
  5. **
  6. ** This file is part of an example program for Qt.  This example
  7. ** program may be used, distributed and modified without limitation.
  8. **
  9. *****************************************************************************/
  10.  
  11. #include "ftpmainwindow.h"
  12. #include "ftpview.h"
  13.  
  14. #include <qvbox.h>
  15. #include <qhbox.h>
  16. #include <qsplitter.h>
  17. #include <qcombobox.h>
  18. #include <qlabel.h>
  19. #include <qspinbox.h>
  20. #include <qlineedit.h>
  21. #include <qpushbutton.h>
  22. #include <qmessagebox.h>
  23. #include <qprogressbar.h>
  24. #include <qdir.h>
  25. #include <qinputdialog.h>
  26. #include <qapplication.h>
  27. #include <qstatusbar.h>
  28.  
  29. FtpMainWindow::FtpMainWindow()
  30.     : QMainWindow(),
  31.       localOperator( "/" )
  32. {
  33.     setup();
  34.  
  35.     // connect to the signals of the local QUrlOperator - this will be used to
  36.     // work on the local file system (listing dirs, etc.) and to copy files
  37.     // TO the local filesystem (downloading)
  38.     connect( &localOperator, SIGNAL( newChildren( const QValueList<QUrlInfo> &, QNetworkOperation * ) ),
  39.          leftView, SLOT( slotInsertEntries( const QValueList<QUrlInfo> & ) ) );
  40.     connect( &localOperator, SIGNAL( start( QNetworkOperation * ) ),
  41.          this, SLOT( slotLocalStart( QNetworkOperation *) ) );
  42.     connect( &localOperator, SIGNAL( finished( QNetworkOperation * ) ),
  43.          this, SLOT( slotLocalFinished( QNetworkOperation *) ) );
  44.     connect( leftView, SIGNAL( itemSelected( const QUrlInfo & ) ),
  45.          this, SLOT( slotLocalDirChanged( const QUrlInfo & ) ) );
  46.     connect( &localOperator, SIGNAL( dataTransferProgress( int, int, QNetworkOperation * ) ),
  47.              this, SLOT( slotLocalDataTransferProgress( int, int, QNetworkOperation * ) ) );
  48.  
  49.     // connect to the signals of the remote QUrlOperator - this will be used to
  50.     // work on the remote file system (on the FTP Server) and to copy files
  51.     // TO the ftp server (uploading)
  52.     connect( &remoteOperator, SIGNAL( newChildren( const QValueList<QUrlInfo> &, QNetworkOperation * ) ),
  53.          rightView, SLOT( slotInsertEntries( const QValueList<QUrlInfo> & ) ) );
  54.     connect( &remoteOperator, SIGNAL( start( QNetworkOperation * ) ),
  55.          this, SLOT( slotRemoteStart( QNetworkOperation *) ) );
  56.     connect( &remoteOperator, SIGNAL( finished( QNetworkOperation * ) ),
  57.          this, SLOT( slotRemoteFinished( QNetworkOperation *) ) );
  58.     connect( rightView, SIGNAL( itemSelected( const QUrlInfo & ) ),
  59.          this, SLOT( slotRemoteDirChanged( const QUrlInfo & ) ) );
  60.     connect( &remoteOperator, SIGNAL( dataTransferProgress( int, int, QNetworkOperation * ) ),
  61.              this, SLOT( slotRemoteDataTransferProgress( int, int, QNetworkOperation * ) ) );
  62.     connect( &remoteOperator, SIGNAL( connectionStateChanged( int, const QString & ) ),
  63.              this, SLOT( slotConnectionStateChanged( int, const QString & ) ) );
  64.  
  65.     // read the local filesystem at the beginning once
  66.     localOperator.listChildren();
  67.  
  68.     // create status bar
  69.     (void)statusBar();
  70. }
  71.  
  72. void FtpMainWindow::setupLeftSide()
  73. {
  74.     // Setup the left side of the GUI, this is the listview
  75.     // of the local filesystem
  76.  
  77.     QVBox *layout = new QVBox( splitter );
  78.     layout->setSpacing( 5 );
  79.     layout->setMargin( 5 );
  80.  
  81.     QHBox *h = new QHBox( layout );
  82.     h->setSpacing( 5 );
  83.     QLabel *l = new QLabel( tr( "Local Path:" ), h );
  84.     l->setFixedWidth( l->sizeHint().width() );
  85.     localCombo = new QComboBox( TRUE, h );
  86.     localCombo->insertItem( "/" );
  87.  
  88.     connect( localCombo, SIGNAL( activated( const QString & ) ),
  89.          this, SLOT( slotLocalDirChanged( const QString & ) ) );
  90.  
  91.     leftView = new FtpView( layout );
  92.  
  93.     QHBox *bottom = new QHBox( layout );
  94.     bottom->setSpacing( 5 );
  95.     QPushButton *bMkDir = new QPushButton( tr( "New Directory" ), bottom );
  96.     QPushButton *bRemove = new QPushButton( tr( "Remove" ), bottom );
  97.     connect( bMkDir, SIGNAL( clicked() ),
  98.          this, SLOT( slotLocalMkDir() ) );
  99.     connect( bRemove, SIGNAL( clicked() ),
  100.          this, SLOT( slotLocalRemove() ) );
  101.  
  102.     splitter->setResizeMode( layout, QSplitter::Stretch );
  103. }
  104.  
  105. void FtpMainWindow::setupRightSide()
  106. {
  107.     // Setup the right side of the GUI, this is the listview
  108.     // of the remote filesystem (FTP), needs also lineedits/combos
  109.     // for username, password, etc.
  110.  
  111.     QVBox *layout = new QVBox( splitter );
  112.     layout->setSpacing( 5 );
  113.     layout->setMargin( 5 );
  114.  
  115.     QHBox *h = new QHBox( layout );
  116.     h->setSpacing( 5 );
  117.     QLabel *l = new QLabel( tr( "Remote Host:" ), h );
  118.     l->setFixedWidth( l->sizeHint().width() );
  119.     remoteHostCombo = new QComboBox( TRUE, h );
  120.  
  121.     l = new QLabel( tr( "Port:" ), h );
  122.     l->setFixedWidth( l->sizeHint().width() );
  123.     portSpin = new QSpinBox( 0, 32767, 1, h );
  124.     portSpin->setValue( 21 );
  125.     portSpin->setFixedWidth( portSpin->sizeHint().width() );
  126.     remoteOperator.setPort( portSpin->value() );
  127.  
  128.     h = new QHBox( layout );
  129.     h->setSpacing( 5 );
  130.     l = new QLabel( tr( "Remote Path:" ), h );
  131.     l->setFixedWidth( l->sizeHint().width() );
  132.     remotePathCombo = new QComboBox( TRUE, h );
  133.  
  134.     h = new QHBox( layout );
  135.     h->setSpacing( 5 );
  136.     l = new QLabel( tr( "Username:" ), h );
  137.     l->setFixedWidth( l->sizeHint().width() );
  138.     userCombo = new QComboBox( TRUE, h );
  139.  
  140.     l = new QLabel( tr( "Password:" ), h );
  141.     l->setFixedWidth( l->sizeHint().width() );
  142.     passLined = new QLineEdit( h );
  143.     passLined->setEchoMode( QLineEdit::Password );
  144.  
  145.     rightView = new FtpView( layout );
  146.  
  147.     QHBox *bottom = new QHBox( layout );
  148.     bottom->setSpacing( 5 );
  149.     QPushButton *bMkDir = new QPushButton( tr( "New Directory" ), bottom );
  150.     QPushButton *bRemove = new QPushButton( tr( "Remove" ), bottom );
  151.     connect( bMkDir, SIGNAL( clicked() ),
  152.          this, SLOT( slotRemoteMkDir() ) );
  153.     connect( bRemove, SIGNAL( clicked() ),
  154.          this, SLOT( slotRemoteRemove() ) );
  155.  
  156.     splitter->setResizeMode( layout, QSplitter::Stretch );
  157.  
  158.     connect( remotePathCombo, SIGNAL( activated( const QString & ) ),
  159.          this, SLOT( slotRemoteDirChanged( const QString & ) ) );
  160. }
  161.  
  162. void FtpMainWindow::setupCenterCommandBar()
  163. {
  164.     // Setup the command bar in the middle between the two views
  165.  
  166.     QVBox *w = new QVBox( splitter );
  167.     splitter->setResizeMode( w, QSplitter::FollowSizeHint );
  168.     w->setSpacing( 5 );
  169.     w->setMargin( 5 );
  170.  
  171.     QPushButton *bConnect = new QPushButton( tr( "&Connect" ), w );
  172.     (void)new QWidget( w );
  173.     QPushButton *bUpload = new QPushButton( tr( "== &Upload ==>" ), w );
  174.     QPushButton *bDownload = new QPushButton( tr( "<== &Download ==" ), w );
  175.     (void)new QWidget( w );
  176.  
  177.     connect( bConnect, SIGNAL( clicked() ),
  178.          this, SLOT( slotConnect() ) );
  179.     connect( bUpload, SIGNAL( clicked() ),
  180.          this, SLOT( slotUpload() ) );
  181.     connect( bDownload, SIGNAL( clicked() ),
  182.          this, SLOT( slotDownload() ) );
  183. }
  184.  
  185. void FtpMainWindow::setup()
  186. {
  187.     // Setup the GUI
  188.  
  189.     mainWidget = new QVBox( this );
  190.     splitter = new QSplitter( mainWidget );
  191.     setupLeftSide();
  192.     setupCenterCommandBar();
  193.     setupRightSide();
  194.  
  195.     progressLabel1 = new QLabel( tr( "No Operation in Progress" ), mainWidget );
  196.     progressBar1 = new QProgressBar( mainWidget );
  197.     progressLabel2 = new QLabel( tr( "No Operation in Progress" ), mainWidget );
  198.     progressBar2 = new QProgressBar( mainWidget );
  199.  
  200.     progressLabel1->hide();
  201.     progressBar1->hide();
  202.     progressLabel2->hide();
  203.     progressBar2->hide();
  204.  
  205.     setCentralWidget( mainWidget );
  206. }
  207.  
  208. void FtpMainWindow::slotLocalDirChanged( const QString &path )
  209. {
  210.     // The user changed the path on the left side
  211.  
  212.     oldLocal = localOperator;
  213.     localOperator.setPath( path );
  214.     localOperator.listChildren();
  215. }
  216.  
  217. void FtpMainWindow::slotLocalDirChanged( const QUrlInfo &info )
  218. {
  219.     // The user changed the path on the left side
  220.  
  221.     oldLocal = localOperator;
  222.     localOperator.addPath( info.name() );
  223.     localOperator.listChildren();
  224.     localCombo->insertItem( localOperator.path(), 0 );
  225.     localCombo->setCurrentItem( 0 );
  226. }
  227.  
  228. void FtpMainWindow::slotRemoteDirChanged( const QString &path )
  229. {
  230.     // The user changed the path on the right side
  231.  
  232.     if ( !remoteOperator.isValid() )
  233.     return;
  234.     oldRemote = remoteOperator;
  235.     remoteOperator.setPath( path );
  236.     remoteOperator.listChildren();
  237. }
  238.  
  239. void FtpMainWindow::slotRemoteDirChanged( const QUrlInfo &info )
  240. {
  241.     // The user changed the path on the right side
  242.  
  243.     oldRemote = remoteOperator;
  244.     remoteOperator.addPath( info.name() );
  245.     remoteOperator.listChildren();
  246.     remotePathCombo->insertItem( remoteOperator.path(), 0 );
  247.     remotePathCombo->setCurrentItem( 0 );
  248. }
  249.  
  250. void FtpMainWindow::slotConnect()
  251. {
  252.     // The user pressed the connect button, so let's connect to the
  253.     // FTP server
  254.     // First we need to set stuff (host, path, etc.) which the user
  255.     // entered on the right side to the remote QUrlOperator
  256.  
  257.     // protocol + hostname
  258.     QString s = "ftp://" + remoteHostCombo->currentText();
  259.     oldRemote = remoteOperator;
  260.     remoteOperator = s;
  261.  
  262.     // path on the server
  263.     if ( !remotePathCombo->currentText().isEmpty() )
  264.     remoteOperator.setPath( remotePathCombo->currentText() );
  265.     else
  266.     remoteOperator.setPath( "/" );
  267.  
  268.     // if nothing or "ftp" or "anonymous" has been entered into the username combo,
  269.     // let's connect anonymous, else private with password
  270.     if ( !userCombo->currentText().isEmpty() &&
  271.      userCombo->currentText().lower() != "anonymous" &&
  272.      userCombo->currentText().lower() != "ftp" ) {
  273.     remoteOperator.setUser( userCombo->currentText() );
  274.     remoteOperator.setPassword( passLined->text() );
  275.     }
  276.  
  277.     // set the port
  278.     remoteOperator.setPort( portSpin->value() );
  279.  
  280.     // finally read the directory on the ftp server
  281.     remoteOperator.listChildren();
  282. }
  283.  
  284. void FtpMainWindow::slotUpload()
  285. {
  286.     // the user pressed the upload button
  287.  
  288.     // if files have been selected on the left side (local filesystem)
  289.     QValueList<QUrlInfo> files = leftView->selectedItems();
  290.     if ( files.isEmpty() )
  291.     return;
  292.  
  293.     // create a list of the URLs which should be copied
  294.     QStringList lst;
  295.     QValueList<QUrlInfo>::Iterator it = files.begin();
  296.     for ( ; it != files.end(); ++it )
  297.     lst << QUrl( localOperator, ( *it ).name() );
  298.  
  299.     // copy the list of selected files to the directory in which the
  300.     // remoteOperator currently is (upload)
  301.     remoteOperator.copy( lst, remoteOperator, FALSE );
  302. }
  303.  
  304. void FtpMainWindow::slotDownload()
  305. {
  306.     // if the user pressed the download button
  307.  
  308.     // if files have been selected on the right side (remote filesystem)
  309.     QValueList<QUrlInfo> files = rightView->selectedItems();
  310.     if ( files.isEmpty() )
  311.     return;
  312.  
  313.     // create a list of the URLs which should be downloaded
  314.     QStringList lst;
  315.     QValueList<QUrlInfo>::Iterator it = files.begin();
  316.     for ( ; it != files.end(); ++it )
  317.     lst << QUrl( remoteOperator, ( *it ).name() );
  318.  
  319.     // copy the list of selected files to the directory in which the
  320.     // localOperator currently is (download)
  321.     localOperator.copy( lst, localOperator, FALSE );
  322. }
  323.  
  324. void FtpMainWindow::slotLocalStart( QNetworkOperation *op )
  325. {
  326.     // this slot is always called if the local QUrlOperator starts
  327.     // listing a directory or dowloading a file
  328.  
  329.     if ( !op )
  330.     return;
  331.  
  332.     if ( op->operation() == QNetworkProtocol::OpListChildren ) {
  333.     // start listing a dir? clear the left view!
  334.     leftView->clear();
  335.     } else if ( op->operation() == QNetworkProtocol::OpGet ) {
  336.     // start downloading a file? reset the progress bar!
  337.     progressBar1->setTotalSteps( 0 );
  338.     progressBar1->reset();
  339.     }
  340. }
  341.  
  342. void FtpMainWindow::slotLocalFinished( QNetworkOperation *op )
  343. {
  344.     // this slot is always called if the local QUrlOperator finished
  345.     // an operation
  346.  
  347.     if ( !op )
  348.     return;
  349.  
  350.     if ( op && op->state() == QNetworkProtocol::StFailed ) {
  351.     // an error happend, let the user know that
  352.     QMessageBox::critical( this, tr( "ERROR" ), op->protocolDetail() );
  353.  
  354.     // do something depending in the error code
  355.     int ecode = op->errorCode();
  356.     if ( ecode == QNetworkProtocol::ErrListChildren || ecode == QNetworkProtocol::ErrParse ||
  357.          ecode == QNetworkProtocol::ErrUnknownProtocol || ecode == QNetworkProtocol::ErrLoginIncorrect ||
  358.          ecode == QNetworkProtocol::ErrValid || ecode == QNetworkProtocol::ErrHostNotFound ||
  359.          ecode == QNetworkProtocol::ErrFileNotExisting ) {
  360.         localOperator = oldLocal;
  361.         localCombo->setEditText( localOperator.path() );
  362.         localOperator.listChildren();
  363.     }
  364.     } else if ( op->operation() == QNetworkProtocol::OpPut ) {
  365.     // finished saving the downloaded file? reread the dir and hide the progress bar
  366.     localOperator.listChildren();
  367.     progressLabel1->hide();
  368.     progressBar1->hide();
  369.     } else if ( op->operation() == QNetworkProtocol::OpGet ) {
  370.     // finished reading a file from the ftp server? reset the progress bar
  371.     progressBar1->setTotalSteps( 0 );
  372.     progressBar1->reset();
  373.     }
  374.  
  375. }
  376.  
  377. void FtpMainWindow::slotRemoteStart( QNetworkOperation *op )
  378. {
  379.     // this slot is always called if the remote QUrlOperator starts
  380.     // listing a directory or uploading a file
  381.  
  382.     if ( !op )
  383.     return;
  384.  
  385.     if ( op->operation() == QNetworkProtocol::OpListChildren ) {
  386.     // start listing a dir? clear the right view!
  387.     rightView->clear();
  388.     } else if ( op->operation() == QNetworkProtocol::OpGet ) {
  389.     // start downloading a file? reset the progress bar!
  390.     progressBar2->setTotalSteps( 0 );
  391.     progressBar2->reset();
  392.     }
  393. }
  394.  
  395. void FtpMainWindow::slotRemoteFinished( QNetworkOperation *op )
  396. {
  397.     // this slot is always called if the remote QUrlOperator finished
  398.     // an operation
  399.  
  400.     if ( !op )
  401.     return;
  402.  
  403.     if ( op && op->state() == QNetworkProtocol::StFailed ) {
  404.     // an error happend, let the user know that
  405.     QMessageBox::critical( this, tr( "ERROR" ), op->protocolDetail() );
  406.  
  407.     // do something depending in the error code
  408.     int ecode = op->errorCode();
  409.     if ( ecode == QNetworkProtocol::ErrListChildren || ecode == QNetworkProtocol::ErrParse ||
  410.          ecode == QNetworkProtocol::ErrUnknownProtocol || ecode == QNetworkProtocol::ErrLoginIncorrect ||
  411.          ecode == QNetworkProtocol::ErrValid || ecode == QNetworkProtocol::ErrHostNotFound ||
  412.          ecode == QNetworkProtocol::ErrFileNotExisting ) {
  413.         remoteOperator = oldRemote;
  414.         remoteHostCombo->setEditText( remoteOperator.host() );
  415.         remotePathCombo->setEditText( remoteOperator.path() );
  416.         passLined->setText( remoteOperator.password() );
  417.         userCombo->setEditText( remoteOperator.user() );
  418.         portSpin->setValue( remoteOperator.port() );
  419.         remoteOperator.listChildren();
  420.     }
  421.     } else if ( op->operation() == QNetworkProtocol::OpListChildren ) {
  422.     // finished reading a dir? set the correct path to the pth combo of the right view
  423.     remotePathCombo->setEditText( remoteOperator.path() );
  424.     } else if ( op->operation() == QNetworkProtocol::OpPut ) {
  425.     // finished saving the uploaded file? reread the dir and hide the progress bar
  426.     remoteOperator.listChildren();
  427.     progressLabel2->hide();
  428.     progressBar2->hide();
  429.     } else if ( op->operation() == QNetworkProtocol::OpGet ) {
  430.     // finished reading a file from the local filesystem? reset the progress bar
  431.     progressBar2->setTotalSteps( 0 );
  432.     progressBar2->reset();
  433.     }
  434. }
  435.  
  436. void FtpMainWindow::slotLocalDataTransferProgress( int bytesDone, int bytesTotal,
  437.                            QNetworkOperation *op )
  438. {
  439.     // Show the progress here of the local QUrlOperator reads or writes data
  440.  
  441.     if ( !op )
  442.     return;
  443.  
  444.     if ( !progressBar1->isVisible() ) {
  445.     if ( bytesDone < bytesTotal) {
  446.         progressLabel1->show();
  447.         progressBar1->show();
  448.         progressBar1->setTotalSteps( bytesTotal );
  449.         progressBar1->setProgress( 0 );
  450.         progressBar1->reset();
  451.     } else
  452.         return;
  453.     }
  454.  
  455.     if ( progressBar1->totalSteps() == bytesTotal )
  456.     progressBar1->setTotalSteps( bytesTotal );
  457.  
  458.     if ( op->operation() == QNetworkProtocol::OpGet )
  459.     progressLabel1->setText( tr( "Read: %1" ).arg( op->arg( 0 ) ) );
  460.     else if ( op->operation() == QNetworkProtocol::OpPut )
  461.     progressLabel1->setText( tr( "Write: %1" ).arg( op->arg( 0 ) ) );
  462.     else
  463.     return;
  464.  
  465.     progressBar1->setProgress( bytesDone );
  466. }
  467.  
  468. void FtpMainWindow::slotRemoteDataTransferProgress( int bytesDone, int bytesTotal,
  469.                             QNetworkOperation *op )
  470. {
  471.     // Show the progress here of the remote QUrlOperator reads or writes data
  472.  
  473.     if ( !op )
  474.     return;
  475.  
  476.     if ( !progressBar2->isVisible() ) {
  477.     if ( bytesDone < bytesTotal) {
  478.         progressLabel2->show();
  479.         progressBar2->show();
  480.         progressBar2->setTotalSteps( bytesTotal );
  481.         progressBar2->setProgress( 0 );
  482.         progressBar2->reset();
  483.     } else
  484.         return;
  485.     }
  486.  
  487.     if ( progressBar2->totalSteps() != bytesTotal )
  488.     progressBar2->setTotalSteps( bytesTotal );
  489.  
  490.     if ( op->operation() == QNetworkProtocol::OpGet )
  491.     progressLabel2->setText( tr( "Read: %1" ).arg( op->arg( 0 ) ) );
  492.     else if ( op->operation() == QNetworkProtocol::OpPut )
  493.     progressLabel2->setText( tr( "Write: %1" ).arg( op->arg( 0 ) ) );
  494.     else
  495.     return;
  496.  
  497.     progressBar2->setProgress( bytesDone );
  498. }
  499.  
  500. void FtpMainWindow::slotLocalMkDir()
  501. {
  502.     // create a dir on the local filesystem
  503.  
  504.     bool ok = FALSE;
  505.     QString name = QInputDialog::getText( tr( "Directory Name:" ), QString::null, QLineEdit::Normal, QString::null, &ok, this );
  506.  
  507.     if ( !name.isEmpty() && ok )
  508.     localOperator.mkdir( name );
  509. }
  510.  
  511. void FtpMainWindow::slotLocalRemove()
  512. {
  513. }
  514.  
  515. void FtpMainWindow::slotRemoteMkDir()
  516. {
  517.     // create a dir on the remote filesystem (FTP server)
  518.  
  519.     bool ok = FALSE;
  520.     QString name = QInputDialog::getText( tr( "Directory Name:" ), QString::null, QLineEdit::Normal, QString::null, &ok, this );
  521.  
  522.     if ( !name.isEmpty() && ok )
  523.     remoteOperator.mkdir( name );
  524. }
  525.  
  526. void FtpMainWindow::slotRemoteRemove()
  527. {
  528. }
  529.  
  530. void FtpMainWindow::slotConnectionStateChanged( int, const QString &msg )
  531. {
  532.     statusBar()->message( msg );
  533. }
  534.