diff options
Diffstat (limited to 'examples/network/clientserver')
-rw-r--r-- | examples/network/clientserver/client/client.cpp | 125 | ||||
-rw-r--r-- | examples/network/clientserver/client/client.pro | 9 | ||||
-rw-r--r-- | examples/network/clientserver/clientserver.doc | 35 | ||||
-rw-r--r-- | examples/network/clientserver/server/server.cpp | 162 | ||||
-rw-r--r-- | examples/network/clientserver/server/server.pro | 9 |
5 files changed, 340 insertions, 0 deletions
diff --git a/examples/network/clientserver/client/client.cpp b/examples/network/clientserver/client/client.cpp new file mode 100644 index 0000000..35cfb98 --- /dev/null +++ b/examples/network/clientserver/client/client.cpp @@ -0,0 +1,125 @@ +/**************************************************************************** +** +** Copyright (C) 1992-2008 Trolltech ASA. 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 <qsocket.h> +#include <qapplication.h> +#include <qvbox.h> +#include <qhbox.h> +#include <qtextview.h> +#include <qlineedit.h> +#include <qlabel.h> +#include <qpushbutton.h> +#include <qtextstream.h> + + +class Client : public QVBox +{ + Q_OBJECT +public: + Client( const QString &host, Q_UINT16 port ) + { + // GUI layout + infoText = new QTextView( this ); + QHBox *hb = new QHBox( this ); + inputText = new QLineEdit( hb ); + QPushButton *send = new QPushButton( tr("Send") , hb ); + QPushButton *close = new QPushButton( tr("Close connection") , this ); + QPushButton *quit = new QPushButton( tr("Quit") , this ); + + connect( send, SIGNAL(clicked()), SLOT(sendToServer()) ); + connect( close, SIGNAL(clicked()), SLOT(closeConnection()) ); + connect( quit, SIGNAL(clicked()), qApp, SLOT(quit()) ); + + // create the socket and connect various of its signals + socket = new QSocket( this ); + connect( socket, SIGNAL(connected()), + SLOT(socketConnected()) ); + connect( socket, SIGNAL(connectionClosed()), + SLOT(socketConnectionClosed()) ); + connect( socket, SIGNAL(readyRead()), + SLOT(socketReadyRead()) ); + connect( socket, SIGNAL(error(int)), + SLOT(socketError(int)) ); + + // connect to the server + infoText->append( tr("Trying to connect to the server\n") ); + socket->connectToHost( host, port ); + } + + ~Client() + { + } + +private slots: + void closeConnection() + { + socket->close(); + if ( socket->state() == QSocket::Closing ) { + // We have a delayed close. + connect( socket, SIGNAL(delayedCloseFinished()), + SLOT(socketClosed()) ); + } else { + // The socket is closed. + socketClosed(); + } + } + + void sendToServer() + { + // write to the server + QTextStream os(socket); + os << inputText->text() << "\n"; + inputText->setText( "" ); + } + + void socketReadyRead() + { + // read from the server + while ( socket->canReadLine() ) { + infoText->append( socket->readLine() ); + } + } + + void socketConnected() + { + infoText->append( tr("Connected to server\n") ); + } + + void socketConnectionClosed() + { + infoText->append( tr("Connection closed by the server\n") ); + } + + void socketClosed() + { + infoText->append( tr("Connection closed\n") ); + } + + void socketError( int e ) + { + infoText->append( tr("Error number %1 occurred\n").arg(e) ); + } + +private: + QSocket *socket; + QTextView *infoText; + QLineEdit *inputText; +}; + + +int main( int argc, char** argv ) +{ + QApplication app( argc, argv ); + Client client( argc<2 ? "localhost" : argv[1], 4242 ); + app.setMainWidget( &client ); + client.show(); + return app.exec(); +} + +#include "client.moc" diff --git a/examples/network/clientserver/client/client.pro b/examples/network/clientserver/client/client.pro new file mode 100644 index 0000000..bc3b9e9 --- /dev/null +++ b/examples/network/clientserver/client/client.pro @@ -0,0 +1,9 @@ +TEMPLATE = app +TARGET = client + +CONFIG += qt warn_on release + +REQUIRES = network full-config + +HEADERS = +SOURCES = client.cpp diff --git a/examples/network/clientserver/clientserver.doc b/examples/network/clientserver/clientserver.doc new file mode 100644 index 0000000..67b72a5 --- /dev/null +++ b/examples/network/clientserver/clientserver.doc @@ -0,0 +1,35 @@ +/* +*/ + +/*! \page clientserver-example.html + + \ingroup network-examples + + \title A small client-server example + + This example shows how two programs can communicate using sockets. + + Two simple example programs are provided, a client program and a + server program. Both use the QSocket class, and the server also uses + QServerSocket class. + + The server listens on port number 4242 and accepts incoming connections. + It sends back every line it receives from the client, prepended with + the line number. + + The client tries to connect to the server on the host specified on the + command line or to localhost if no command line arguments are + specified. You can send single lines to the server. + + <hr> + + Implementation server (server.cpp): + + \include network/clientserver/server/server.cpp + + <hr> + + Implementation client (client.cpp): + + \include network/clientserver/client/client.cpp +*/ diff --git a/examples/network/clientserver/server/server.cpp b/examples/network/clientserver/server/server.cpp new file mode 100644 index 0000000..440647c --- /dev/null +++ b/examples/network/clientserver/server/server.cpp @@ -0,0 +1,162 @@ +/**************************************************************************** +** +** Copyright (C) 1992-2008 Trolltech ASA. 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 <qsocket.h> +#include <qserversocket.h> +#include <qapplication.h> +#include <qvbox.h> +#include <qtextview.h> +#include <qlabel.h> +#include <qpushbutton.h> +#include <qtextstream.h> + +#include <stdlib.h> + + +/* + The ClientSocket class provides a socket that is connected with a client. + For every client that connects to the server, the server creates a new + instance of this class. +*/ +class ClientSocket : public QSocket +{ + Q_OBJECT +public: + ClientSocket( int sock, QObject *parent=0, const char *name=0 ) : + QSocket( parent, name ) + { + line = 0; + connect( this, SIGNAL(readyRead()), + SLOT(readClient()) ); + connect( this, SIGNAL(connectionClosed()), + SLOT(deleteLater()) ); + setSocket( sock ); + } + + ~ClientSocket() + { + } + +signals: + void logText( const QString& ); + +private slots: + void readClient() + { + QTextStream ts( this ); + while ( canReadLine() ) { + QString str = ts.readLine(); + emit logText( tr("Read: '%1'\n").arg(str) ); + + ts << line << ": " << str << endl; + emit logText( tr("Wrote: '%1: %2'\n").arg(line).arg(str) ); + + line++; + } + } + +private: + int line; +}; + + +/* + The SimpleServer class handles new connections to the server. For every + client that connects, it creates a new ClientSocket -- that instance is now + responsible for the communication with that client. +*/ +class SimpleServer : public QServerSocket +{ + Q_OBJECT +public: + SimpleServer( QObject* parent=0 ) : + QServerSocket( 4242, 1, parent ) + { + if ( !ok() ) { + qWarning("Failed to bind to port 4242"); + exit(1); + } + } + + ~SimpleServer() + { + } + + void newConnection( int socket ) + { + ClientSocket *s = new ClientSocket( socket, this ); + emit newConnect( s ); + } + +signals: + void newConnect( ClientSocket* ); +}; + + +/* + The ServerInfo class provides a small GUI for the server. It also creates the + SimpleServer and as a result the server. +*/ +class ServerInfo : public QVBox +{ + Q_OBJECT +public: + ServerInfo() + { + SimpleServer *server = new SimpleServer( this ); + + QString itext = tr( + "This is a small server example.\n" + "Connect with the client now." + ); + QLabel *lb = new QLabel( itext, this ); + lb->setAlignment( AlignHCenter ); + infoText = new QTextView( this ); + QPushButton *quit = new QPushButton( tr("Quit") , this ); + + connect( server, SIGNAL(newConnect(ClientSocket*)), + SLOT(newConnect(ClientSocket*)) ); + connect( quit, SIGNAL(clicked()), qApp, + SLOT(quit()) ); + } + + ~ServerInfo() + { + } + +private slots: + void newConnect( ClientSocket *s ) + { + infoText->append( tr("New connection\n") ); + connect( s, SIGNAL(logText(const QString&)), + infoText, SLOT(append(const QString&)) ); + connect( s, SIGNAL(connectionClosed()), + SLOT(connectionClosed()) ); + } + + void connectionClosed() + { + infoText->append( tr("Client closed connection\n") ); + } + +private: + QTextView *infoText; +}; + + +int main( int argc, char** argv ) +{ + QApplication app( argc, argv ); + ServerInfo info; + app.setMainWidget( &info ); + info.show(); + return app.exec(); +} + +#include "server.moc" diff --git a/examples/network/clientserver/server/server.pro b/examples/network/clientserver/server/server.pro new file mode 100644 index 0000000..0a845b5 --- /dev/null +++ b/examples/network/clientserver/server/server.pro @@ -0,0 +1,9 @@ +TEMPLATE = app +TARGET = server + +CONFIG += qt warn_on release + +REQUIRES = network full-config + +HEADERS = +SOURCES = server.cpp |