client.cpp 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689
  1. /////////////////////////////////////////////////////////////////////////////
  2. // Name: client.cpp
  3. // Purpose: Client for wxSocket demo
  4. // Author: Guillermo Rodriguez Garcia <guille@iies.es>
  5. // Modified by:
  6. // Created: 1999/09/19
  7. // Copyright: (c) 1999 Guillermo Rodriguez Garcia
  8. // Licence: wxWindows licence
  9. /////////////////////////////////////////////////////////////////////////////
  10. // ==========================================================================
  11. // declarations
  12. // ==========================================================================
  13. // --------------------------------------------------------------------------
  14. // headers
  15. // --------------------------------------------------------------------------
  16. // For compilers that support precompilation, includes "wx/wx.h".
  17. #include "wx/wxprec.h"
  18. #ifdef __BORLANDC__
  19. # pragma hdrstop
  20. #endif
  21. // for all others, include the necessary headers
  22. #ifndef WX_PRECOMP
  23. # include "wx/wx.h"
  24. #endif
  25. #include "wx/socket.h"
  26. #include "wx/url.h"
  27. #include "wx/sstream.h"
  28. #include <memory>
  29. // --------------------------------------------------------------------------
  30. // resources
  31. // --------------------------------------------------------------------------
  32. // the application icon
  33. #ifndef wxHAS_IMAGES_IN_RESOURCES
  34. #include "../sample.xpm"
  35. #endif
  36. // --------------------------------------------------------------------------
  37. // classes
  38. // --------------------------------------------------------------------------
  39. // Define a new application type
  40. class MyApp : public wxApp
  41. {
  42. public:
  43. virtual bool OnInit();
  44. };
  45. // Define a new frame type: this is going to be our main frame
  46. class MyFrame : public wxFrame
  47. {
  48. public:
  49. MyFrame();
  50. ~MyFrame();
  51. // event handlers for File menu
  52. void OnQuit(wxCommandEvent& event);
  53. void OnAbout(wxCommandEvent& event);
  54. // event handlers for Socket menu
  55. void OnOpenConnection(wxCommandEvent& event);
  56. void OnTest1(wxCommandEvent& event);
  57. void OnTest2(wxCommandEvent& event);
  58. void OnTest3(wxCommandEvent& event);
  59. void OnCloseConnection(wxCommandEvent& event);
  60. #if wxUSE_URL
  61. // event handlers for Protocols menu
  62. void OnTestURL(wxCommandEvent& event);
  63. #endif
  64. #if wxUSE_IPV6
  65. void OnOpenConnectionIPv6(wxCommandEvent& event);
  66. #endif
  67. void OpenConnection(wxSockAddress::Family family);
  68. // event handlers for DatagramSocket menu (stub)
  69. void OnDatagram(wxCommandEvent& event);
  70. // socket event handler
  71. void OnSocketEvent(wxSocketEvent& event);
  72. // convenience functions
  73. void UpdateStatusBar();
  74. private:
  75. wxSocketClient *m_sock;
  76. wxTextCtrl *m_text;
  77. wxMenu *m_menuFile;
  78. wxMenu *m_menuSocket;
  79. wxMenu *m_menuDatagramSocket;
  80. wxMenu *m_menuProtocols;
  81. wxMenuBar *m_menuBar;
  82. bool m_busy;
  83. // any class wishing to process wxWidgets events must use this macro
  84. wxDECLARE_EVENT_TABLE();
  85. };
  86. // simple helper class to log start and end of each test
  87. class TestLogger
  88. {
  89. public:
  90. TestLogger(const wxString& name) : m_name(name)
  91. {
  92. wxLogMessage("=== %s test begins ===", m_name);
  93. }
  94. ~TestLogger()
  95. {
  96. wxLogMessage("=== %s test ends ===", m_name);
  97. }
  98. private:
  99. const wxString m_name;
  100. };
  101. // --------------------------------------------------------------------------
  102. // constants
  103. // --------------------------------------------------------------------------
  104. // IDs for the controls and the menu commands
  105. enum
  106. {
  107. // menu items
  108. CLIENT_QUIT = wxID_EXIT,
  109. CLIENT_ABOUT = wxID_ABOUT,
  110. CLIENT_OPEN = 100,
  111. #if wxUSE_IPV6
  112. CLIENT_OPENIPV6,
  113. #endif
  114. CLIENT_TEST1,
  115. CLIENT_TEST2,
  116. CLIENT_TEST3,
  117. CLIENT_CLOSE,
  118. #if wxUSE_URL
  119. CLIENT_TESTURL,
  120. #endif
  121. CLIENT_DGRAM,
  122. // id for socket
  123. SOCKET_ID
  124. };
  125. // --------------------------------------------------------------------------
  126. // event tables and other macros for wxWidgets
  127. // --------------------------------------------------------------------------
  128. wxBEGIN_EVENT_TABLE(MyFrame, wxFrame)
  129. EVT_MENU(CLIENT_QUIT, MyFrame::OnQuit)
  130. EVT_MENU(CLIENT_ABOUT, MyFrame::OnAbout)
  131. EVT_MENU(CLIENT_OPEN, MyFrame::OnOpenConnection)
  132. #if wxUSE_IPV6
  133. EVT_MENU(CLIENT_OPENIPV6, MyFrame::OnOpenConnectionIPv6)
  134. #endif
  135. EVT_MENU(CLIENT_TEST1, MyFrame::OnTest1)
  136. EVT_MENU(CLIENT_TEST2, MyFrame::OnTest2)
  137. EVT_MENU(CLIENT_TEST3, MyFrame::OnTest3)
  138. EVT_MENU(CLIENT_CLOSE, MyFrame::OnCloseConnection)
  139. EVT_MENU(CLIENT_DGRAM, MyFrame::OnDatagram)
  140. #if wxUSE_URL
  141. EVT_MENU(CLIENT_TESTURL, MyFrame::OnTestURL)
  142. #endif
  143. EVT_SOCKET(SOCKET_ID, MyFrame::OnSocketEvent)
  144. wxEND_EVENT_TABLE()
  145. IMPLEMENT_APP(MyApp)
  146. // ==========================================================================
  147. // implementation
  148. // ==========================================================================
  149. // --------------------------------------------------------------------------
  150. // the application class
  151. // --------------------------------------------------------------------------
  152. bool MyApp::OnInit()
  153. {
  154. if ( !wxApp::OnInit() )
  155. return false;
  156. // Create the main application window
  157. MyFrame *frame = new MyFrame();
  158. // Show it
  159. frame->Show(true);
  160. // success
  161. return true;
  162. }
  163. // --------------------------------------------------------------------------
  164. // main frame
  165. // --------------------------------------------------------------------------
  166. // frame constructor
  167. MyFrame::MyFrame() : wxFrame((wxFrame *)NULL, wxID_ANY,
  168. _("wxSocket demo: Client"),
  169. wxDefaultPosition, wxSize(300, 200))
  170. {
  171. // Give the frame an icon
  172. SetIcon(wxICON(sample));
  173. // Make menus
  174. m_menuFile = new wxMenu();
  175. m_menuFile->Append(CLIENT_ABOUT, _("&About\tCtrl-A"), _("Show about dialog"));
  176. m_menuFile->AppendSeparator();
  177. m_menuFile->Append(CLIENT_QUIT, _("E&xit\tAlt-X"), _("Quit client"));
  178. m_menuSocket = new wxMenu();
  179. m_menuSocket->Append(CLIENT_OPEN, _("&Open session\tCtrl-O"), _("Connect to server"));
  180. #if wxUSE_IPV6
  181. m_menuSocket->Append(CLIENT_OPENIPV6, _("&Open session(IPv6)\tShift-Ctrl-O"), _("Connect to server(IPv6)"));
  182. #endif
  183. m_menuSocket->AppendSeparator();
  184. m_menuSocket->Append(CLIENT_TEST1, _("Test &1\tCtrl-F1"), _("Test basic functionality"));
  185. m_menuSocket->Append(CLIENT_TEST2, _("Test &2\tCtrl-F2"), _("Test ReadMsg and WriteMsg"));
  186. m_menuSocket->Append(CLIENT_TEST3, _("Test &3\tCtrl-F3"), _("Test large data transfer"));
  187. m_menuSocket->AppendSeparator();
  188. m_menuSocket->Append(CLIENT_CLOSE, _("&Close session\tCtrl-Q"), _("Close connection"));
  189. m_menuDatagramSocket = new wxMenu();
  190. m_menuDatagramSocket->Append(CLIENT_DGRAM, _("&Datagram test\tCtrl-D"), _("Test UDP sockets"));
  191. #if wxUSE_URL
  192. m_menuProtocols = new wxMenu();
  193. m_menuProtocols->Append(CLIENT_TESTURL, _("Test URL\tCtrl-U"),
  194. _("Get data from the specified URL"));
  195. #endif
  196. // Append menus to the menubar
  197. m_menuBar = new wxMenuBar();
  198. m_menuBar->Append(m_menuFile, _("&File"));
  199. m_menuBar->Append(m_menuSocket, _("&TCP"));
  200. m_menuBar->Append(m_menuDatagramSocket, _("&UDP"));
  201. #if wxUSE_URL
  202. m_menuBar->Append(m_menuProtocols, _("&Protocols"));
  203. #endif
  204. SetMenuBar(m_menuBar);
  205. #if wxUSE_STATUSBAR
  206. // Status bar
  207. CreateStatusBar(2);
  208. #endif // wxUSE_STATUSBAR
  209. // Make a textctrl for logging
  210. m_text = new wxTextCtrl(this, wxID_ANY,
  211. _("Welcome to wxSocket demo: Client\nClient ready\n"),
  212. wxDefaultPosition, wxDefaultSize,
  213. wxTE_MULTILINE | wxTE_READONLY);
  214. delete wxLog::SetActiveTarget(new wxLogTextCtrl(m_text));
  215. // Create the socket
  216. m_sock = new wxSocketClient();
  217. // Setup the event handler and subscribe to most events
  218. m_sock->SetEventHandler(*this, SOCKET_ID);
  219. m_sock->SetNotify(wxSOCKET_CONNECTION_FLAG |
  220. wxSOCKET_INPUT_FLAG |
  221. wxSOCKET_LOST_FLAG);
  222. m_sock->Notify(true);
  223. m_busy = false;
  224. UpdateStatusBar();
  225. }
  226. MyFrame::~MyFrame()
  227. {
  228. // No delayed deletion here, as the frame is dying anyway
  229. delete m_sock;
  230. }
  231. // event handlers
  232. void MyFrame::OnQuit(wxCommandEvent& WXUNUSED(event))
  233. {
  234. // true is to force the frame to close
  235. Close(true);
  236. }
  237. void MyFrame::OnAbout(wxCommandEvent& WXUNUSED(event))
  238. {
  239. wxMessageBox(_("wxSocket demo: Client\n(c) 1999 Guillermo Rodriguez Garcia\n"),
  240. _("About Client"),
  241. wxOK | wxICON_INFORMATION, this);
  242. }
  243. void MyFrame::OnOpenConnection(wxCommandEvent& WXUNUSED(event))
  244. {
  245. OpenConnection(wxSockAddress::IPV4);
  246. }
  247. #if wxUSE_IPV6
  248. void MyFrame::OnOpenConnectionIPv6(wxCommandEvent& WXUNUSED(event))
  249. {
  250. OpenConnection(wxSockAddress::IPV6);
  251. }
  252. #endif // wxUSE_IPV6
  253. void MyFrame::OpenConnection(wxSockAddress::Family family)
  254. {
  255. wxUnusedVar(family); // unused in !wxUSE_IPV6 case
  256. wxIPaddress * addr;
  257. wxIPV4address addr4;
  258. #if wxUSE_IPV6
  259. wxIPV6address addr6;
  260. if ( family == wxSockAddress::IPV6 )
  261. addr = &addr6;
  262. else
  263. #endif
  264. addr = &addr4;
  265. m_menuSocket->Enable(CLIENT_OPEN, false);
  266. #if wxUSE_IPV6
  267. m_menuSocket->Enable(CLIENT_OPENIPV6, false);
  268. #endif
  269. m_menuSocket->Enable(CLIENT_CLOSE, false);
  270. // Ask user for server address
  271. wxString hostname = wxGetTextFromUser(
  272. _("Enter the address of the wxSocket demo server:"),
  273. _("Connect ..."),
  274. _("localhost"));
  275. if ( hostname.empty() )
  276. return;
  277. addr->Hostname(hostname);
  278. addr->Service(3000);
  279. // we connect asynchronously and will get a wxSOCKET_CONNECTION event when
  280. // the connection is really established
  281. //
  282. // if you want to make sure that connection is established right here you
  283. // could call WaitOnConnect(timeout) instead
  284. wxLogMessage("Trying to connect to %s:%d", hostname, addr->Service());
  285. m_sock->Connect(*addr, false);
  286. }
  287. void MyFrame::OnTest1(wxCommandEvent& WXUNUSED(event))
  288. {
  289. // Disable socket menu entries (exception: Close Session)
  290. m_busy = true;
  291. UpdateStatusBar();
  292. m_text->AppendText(_("\n=== Test 1 begins ===\n"));
  293. // Tell the server which test we are running
  294. unsigned char c = 0xBE;
  295. m_sock->Write(&c, 1);
  296. // Send some data and read it back. We know the size of the
  297. // buffer, so we can specify the exact number of bytes to be
  298. // sent or received and use the wxSOCKET_WAITALL flag. Also,
  299. // we have disabled menu entries which could interfere with
  300. // the test, so we can safely avoid the wxSOCKET_BLOCK flag.
  301. //
  302. // First we send a byte with the length of the string, then
  303. // we send the string itself (do NOT try to send any integral
  304. // value larger than a byte "as is" across the network, or
  305. // you might be in trouble! Ever heard about big and little
  306. // endian computers?)
  307. m_sock->SetFlags(wxSOCKET_WAITALL);
  308. const char *buf1 = "Test string (less than 256 chars!)";
  309. unsigned char len = (unsigned char)(wxStrlen(buf1) + 1);
  310. wxCharBuffer buf2(wxStrlen(buf1));
  311. m_text->AppendText(_("Sending a test buffer to the server ..."));
  312. m_sock->Write(&len, 1);
  313. m_sock->Write(buf1, len);
  314. m_text->AppendText(m_sock->Error() ? _("failed !\n") : _("done\n"));
  315. m_text->AppendText(_("Receiving the buffer back from server ..."));
  316. m_sock->Read(buf2.data(), len);
  317. m_text->AppendText(m_sock->Error() ? _("failed !\n") : _("done\n"));
  318. m_text->AppendText(_("Comparing the two buffers ..."));
  319. if (memcmp(buf1, buf2, len) != 0)
  320. {
  321. m_text->AppendText(_("failed!\n"));
  322. m_text->AppendText(_("Test 1 failed !\n"));
  323. }
  324. else
  325. {
  326. m_text->AppendText(_("done\n"));
  327. m_text->AppendText(_("Test 1 passed !\n"));
  328. }
  329. m_text->AppendText(_("=== Test 1 ends ===\n"));
  330. m_busy = false;
  331. UpdateStatusBar();
  332. }
  333. void MyFrame::OnTest2(wxCommandEvent& WXUNUSED(event))
  334. {
  335. // Disable socket menu entries (exception: Close Session)
  336. m_busy = true;
  337. UpdateStatusBar();
  338. m_text->AppendText(_("\n=== Test 2 begins ===\n"));
  339. // Tell the server which test we are running
  340. unsigned char c = 0xCE;
  341. m_sock->Write(&c, 1);
  342. // Here we use ReadMsg and WriteMsg to send messages with
  343. // a header with size information. Also, the reception is
  344. // event triggered, so we test input events as well.
  345. //
  346. // We need to set no flags here (ReadMsg and WriteMsg are
  347. // not affected by flags)
  348. m_sock->SetFlags(wxSOCKET_WAITALL);
  349. wxString s = wxGetTextFromUser(
  350. _("Enter an arbitrary string to send to the server:"),
  351. _("Test 2 ..."),
  352. _("Yes I like wxWidgets!"));
  353. const wxScopedCharBuffer msg1(s.utf8_str());
  354. size_t len = wxStrlen(msg1) + 1;
  355. wxCharBuffer msg2(wxStrlen(msg1));
  356. m_text->AppendText(_("Sending the string with WriteMsg ..."));
  357. m_sock->WriteMsg(msg1, len);
  358. m_text->AppendText(m_sock->Error() ? _("failed !\n") : _("done\n"));
  359. m_text->AppendText(_("Waiting for an event (timeout = 2 sec)\n"));
  360. // Wait until data available (will also return if the connection is lost)
  361. m_sock->WaitForRead(2);
  362. if (m_sock->IsData())
  363. {
  364. m_text->AppendText(_("Reading the string back with ReadMsg ..."));
  365. m_sock->ReadMsg(msg2.data(), len);
  366. m_text->AppendText(m_sock->Error() ? _("failed !\n") : _("done\n"));
  367. m_text->AppendText(_("Comparing the two buffers ..."));
  368. if (memcmp(msg1, msg2, len) != 0)
  369. {
  370. m_text->AppendText(_("failed!\n"));
  371. m_text->AppendText(_("Test 2 failed !\n"));
  372. }
  373. else
  374. {
  375. m_text->AppendText(_("done\n"));
  376. m_text->AppendText(_("Test 2 passed !\n"));
  377. }
  378. }
  379. else
  380. m_text->AppendText(_("Timeout ! Test 2 failed.\n"));
  381. m_text->AppendText(_("=== Test 2 ends ===\n"));
  382. m_busy = false;
  383. UpdateStatusBar();
  384. }
  385. void MyFrame::OnTest3(wxCommandEvent& WXUNUSED(event))
  386. {
  387. // Disable socket menu entries (exception: Close Session)
  388. m_busy = true;
  389. UpdateStatusBar();
  390. m_text->AppendText(_("\n=== Test 3 begins ===\n"));
  391. // Tell the server which test we are running
  392. unsigned char c = 0xDE;
  393. m_sock->Write(&c, 1);
  394. // This test also is similar to the first one but it sends a
  395. // large buffer so that wxSocket is actually forced to split
  396. // it into pieces and take care of sending everything before
  397. // returning.
  398. m_sock->SetFlags(wxSOCKET_WAITALL);
  399. // Note that len is in kbytes here!
  400. const unsigned char len = 32;
  401. wxCharBuffer buf1(len * 1024),
  402. buf2(len * 1024);
  403. for (size_t i = 0; i < len * 1024; i ++)
  404. buf1.data()[i] = (char)(i % 256);
  405. m_text->AppendText(_("Sending a large buffer (32K) to the server ..."));
  406. m_sock->Write(&len, 1);
  407. m_sock->Write(buf1, len * 1024);
  408. m_text->AppendText(m_sock->Error() ? _("failed !\n") : _("done\n"));
  409. m_text->AppendText(_("Receiving the buffer back from server ..."));
  410. m_sock->Read(buf2.data(), len * 1024);
  411. m_text->AppendText(m_sock->Error() ? _("failed !\n") : _("done\n"));
  412. m_text->AppendText(_("Comparing the two buffers ..."));
  413. if (memcmp(buf1, buf2, len) != 0)
  414. {
  415. m_text->AppendText(_("failed!\n"));
  416. m_text->AppendText(_("Test 3 failed !\n"));
  417. }
  418. else
  419. {
  420. m_text->AppendText(_("done\n"));
  421. m_text->AppendText(_("Test 3 passed !\n"));
  422. }
  423. m_text->AppendText(_("=== Test 3 ends ===\n"));
  424. m_busy = false;
  425. UpdateStatusBar();
  426. }
  427. void MyFrame::OnCloseConnection(wxCommandEvent& WXUNUSED(event))
  428. {
  429. m_sock->Close();
  430. UpdateStatusBar();
  431. }
  432. void MyFrame::OnDatagram(wxCommandEvent& WXUNUSED(event))
  433. {
  434. wxString hostname = wxGetTextFromUser
  435. (
  436. "Enter the address of the wxSocket demo server:",
  437. "UDP peer",
  438. "localhost"
  439. );
  440. if ( hostname.empty() )
  441. return;
  442. TestLogger logtest("UDP");
  443. wxIPV4address addrLocal;
  444. addrLocal.Hostname();
  445. wxDatagramSocket sock(addrLocal);
  446. if ( !sock.IsOk() )
  447. {
  448. wxLogMessage("ERROR: failed to create UDP socket");
  449. return;
  450. }
  451. wxLogMessage("Created UDP socket at %s:%u",
  452. addrLocal.IPAddress(), addrLocal.Service());
  453. wxIPV4address addrPeer;
  454. addrPeer.Hostname(hostname);
  455. addrPeer.Service(3000);
  456. wxLogMessage("Testing UDP with peer at %s:%u",
  457. addrPeer.IPAddress(), addrPeer.Service());
  458. char buf[] = "Uryyb sebz pyvrag!";
  459. if ( sock.SendTo(addrPeer, buf, sizeof(buf)).LastCount() != sizeof(buf) )
  460. {
  461. wxLogMessage("ERROR: failed to send data");
  462. return;
  463. }
  464. if ( sock.RecvFrom(addrPeer, buf, sizeof(buf)).LastCount() != sizeof(buf) )
  465. {
  466. wxLogMessage("ERROR: failed to receive data");
  467. return;
  468. }
  469. wxLogMessage("Received \"%s\" from %s:%u.",
  470. wxString::From8BitData(buf, sock.LastCount()),
  471. addrPeer.IPAddress(), addrPeer.Service());
  472. }
  473. #if wxUSE_URL
  474. void MyFrame::OnTestURL(wxCommandEvent& WXUNUSED(event))
  475. {
  476. // Ask for the URL
  477. static wxString s_urlname("http://www.google.com/");
  478. wxString urlname = wxGetTextFromUser
  479. (
  480. _("Enter an URL to get"),
  481. _("URL:"),
  482. s_urlname
  483. );
  484. if ( urlname.empty() )
  485. return; // cancelled by user
  486. s_urlname = urlname;
  487. TestLogger logtest("URL");
  488. // Parse the URL
  489. wxURL url(urlname);
  490. if ( url.GetError() != wxURL_NOERR )
  491. {
  492. wxLogError("Failed to parse URL \"%s\"", urlname);
  493. return;
  494. }
  495. // Try to get the input stream (connects to the given URL)
  496. wxLogMessage("Establishing connection to \"%s\"...", urlname);
  497. const std::auto_ptr<wxInputStream> data(url.GetInputStream());
  498. if ( !data.get() )
  499. {
  500. wxLogError("Failed to retrieve URL \"%s\"", urlname);
  501. return;
  502. }
  503. // Print the contents type and file size
  504. wxLogMessage("Contents type: %s\nFile size: %lu\nStarting to download...",
  505. url.GetProtocol().GetContentType(),
  506. static_cast<unsigned long>( data->GetSize() ));
  507. // Get the data
  508. wxStringOutputStream sout;
  509. if ( data->Read(sout).GetLastError() != wxSTREAM_EOF )
  510. {
  511. wxLogError("Error reading the input stream.");
  512. }
  513. wxLogMessage("Text retrieved from URL \"%s\" follows:\n%s",
  514. urlname, sout.GetString());
  515. }
  516. #endif // wxUSE_URL
  517. void MyFrame::OnSocketEvent(wxSocketEvent& event)
  518. {
  519. switch ( event.GetSocketEvent() )
  520. {
  521. case wxSOCKET_INPUT:
  522. wxLogMessage("Input available on the socket");
  523. break;
  524. case wxSOCKET_LOST:
  525. wxLogMessage("Socket connection was unexpectedly lost.");
  526. UpdateStatusBar();
  527. break;
  528. case wxSOCKET_CONNECTION:
  529. wxLogMessage("... socket is now connected.");
  530. UpdateStatusBar();
  531. break;
  532. default:
  533. wxLogMessage("Unknown socket event!!!");
  534. break;
  535. }
  536. }
  537. // convenience functions
  538. void MyFrame::UpdateStatusBar()
  539. {
  540. #if wxUSE_STATUSBAR
  541. wxString s;
  542. if (!m_sock->IsConnected())
  543. {
  544. s = "Not connected";
  545. }
  546. else
  547. {
  548. #if wxUSE_IPV6
  549. wxIPV6address addr;
  550. #else
  551. wxIPV4address addr;
  552. #endif
  553. m_sock->GetPeer(addr);
  554. s.Printf("%s : %d", addr.Hostname(), addr.Service());
  555. }
  556. SetStatusText(s, 1);
  557. #endif // wxUSE_STATUSBAR
  558. m_menuSocket->Enable(CLIENT_OPEN, !m_sock->IsConnected() && !m_busy);
  559. #if wxUSE_IPV6
  560. m_menuSocket->Enable(CLIENT_OPENIPV6, !m_sock->IsConnected() && !m_busy);
  561. #endif
  562. m_menuSocket->Enable(CLIENT_TEST1, m_sock->IsConnected() && !m_busy);
  563. m_menuSocket->Enable(CLIENT_TEST2, m_sock->IsConnected() && !m_busy);
  564. m_menuSocket->Enable(CLIENT_TEST3, m_sock->IsConnected() && !m_busy);
  565. m_menuSocket->Enable(CLIENT_CLOSE, m_sock->IsConnected());
  566. }