home *** CD-ROM | disk | FTP | other *** search
/ Tricks of the Windows Gam…ming Gurus (2nd Edition) / Disc2.iso / msdn_vcb / samples / vc98 / sdk / netds / winsock / globchat / client / select.c < prev    next >
Encoding:
C/C++ Source or Header  |  1997-10-05  |  13.1 KB  |  443 lines

  1. // THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
  2. // ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
  3. // THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
  4. // PARTICULAR PURPOSE.
  5. //
  6. // Copyright (C) 1993-1997  Microsoft Corporation.  All Rights Reserved.
  7. //
  8. //  MODULE:    select.c
  9. //
  10. //  PURPOSE:   Displays the "Select" dialog box
  11. //
  12. //  FUNCTIONS:
  13. //    CmdSelect          - Displays the "Select" dialog box
  14. //    Select             - Processes messages for "Select" dialog box.
  15. //    MsgSelectInit      - Sets up event message notification for socket
  16. //    MsgSelectDataReady - Process socket event message notifications
  17. //    MsgSelectCommand   - Process WM_COMMAND message sent to the select box.
  18. //    CmdSelectDone      - Free the select box and related data.
  19. //    CmdSelectOK        - Request Peer session
  20. //    CmdSelectList      - Enables/Disables OK button
  21. //
  22. //  COMMENTS:
  23. //
  24. //
  25.  
  26. #include <windows.h>            // required for all Windows applications
  27. #include <windowsx.h>
  28. #include <wsipx.h>              // IPX Sockets defs
  29. #include <wsnetbs.h>
  30. #include <nspapi.h>
  31. #include "globals.h"            // prototypes specific to this application
  32.  
  33. LRESULT CALLBACK Select(HWND, UINT, WPARAM, LPARAM);
  34. LRESULT MsgSelectInit(HWND, UINT, WPARAM, LPARAM);
  35. LRESULT MsgSelectCommand(HWND, UINT, WPARAM, LPARAM);
  36. LRESULT MsgSelectDataReady(HWND, UINT, WPARAM, LPARAM);
  37. LRESULT CmdSelectDone(HWND, WORD, WORD, HWND);
  38. LRESULT CmdSelectOK(HWND, WORD, WORD, HWND);
  39. LRESULT CmdSelectList(HWND, WORD, WORD, HWND);
  40.  
  41. // Select dialog message table definition.
  42. MSD rgmsdSelect[] =
  43. {
  44.     {WM_COMMAND,    MsgSelectCommand},
  45.     {WM_INITDIALOG, MsgSelectInit},
  46.     {MW_DATAREADY,  MsgSelectDataReady}
  47. };
  48.  
  49. MSDI msdiSelect =
  50. {
  51.     sizeof(rgmsdSelect) / sizeof(MSD),
  52.     rgmsdSelect,
  53.     edwpNone
  54. };
  55.  
  56. // Select dialog command table definition.
  57. CMD rgcmdSelect[] =
  58. {
  59.     {IDOK,     CmdSelectOK},
  60.     {IDCANCEL, CmdSelectDone},
  61.     {SD_LIST,  CmdSelectList}
  62. };
  63.  
  64. CMDI cmdiSelect =
  65. {
  66.     sizeof(rgcmdSelect) / sizeof(CMD),
  67.     rgcmdSelect,
  68.     edwpNone
  69. };
  70.  
  71. // Module specific "globals"  Used when a variable needs to be
  72. // accessed in more than on handler function.
  73.  
  74. HFONT hFontCopyright;
  75.  
  76. //
  77. //  FUNCTION: CmdSelect(HWND, WORD, WORD, HWND)
  78. //
  79. //  PURPOSE: Displays the "Select" dialog box
  80. //
  81. //  PARAMETERS:
  82. //    hwnd      - Window handle
  83. //    wCommand  - IDM_Select (unused)
  84. //    wNotify   - Notification number (unused)
  85. //    hwndCtrl  - NULL (unused)
  86. //
  87. //  RETURN VALUE:
  88. //
  89. //    Always returns 0 - Message handled
  90. //
  91. //  COMMENTS:
  92. //    To process the IDM_Select message, call DialogBox() to display the
  93. //    Select dialog box.
  94.  
  95. LRESULT CmdSelect(HWND hwnd, WORD wCommand, WORD wNotify, HWND hwndCtrl)
  96. {
  97.     char outtext[80];
  98.  
  99.     if (DialogBox(hInst, "SelectBox", hwnd, (DLGPROC)Select))
  100.     {
  101.         // reset socket event messaging to point at the main window
  102.         if (WSAAsyncSelect(MySock.sock, hwnd, MW_DATAREADY, FD_READ | FD_CLOSE) == SOCKET_ERROR)
  103.         {
  104.             // I hate it when this happens!
  105.             wsprintf(outtext, GetStringRes(IDS_ERR_WSAASYNCSELECT),
  106.                      WSAGetLastError());
  107.             MessageBox(hwnd, outtext, NULL, MB_OK);
  108.             return 0;
  109.         }
  110.  
  111.         // We've got a connection...set up menu and title bar
  112.         EnableMenuItem(GetMenu(hwnd), IDM_END_CHAT, MF_ENABLED);
  113.         EnableMenuItem(GetMenu(hwnd), IDM_DISCONNECT_SERVER, MF_ENABLED);
  114.         EnableMenuItem(GetMenu(hwnd), IDM_CONNECT, MF_GRAYED);
  115.  
  116.         wsprintf(outtext, GetStringRes(IDS_CHATTING_REMOTE), MySock.name, peername);
  117.         SetWindowText(hwnd, outtext);
  118.         // we're now ready to rumble
  119.     }
  120.     else
  121.     {
  122.         // clean up
  123.         closesocket(MySock.sock);
  124.         EnableMenuItem(GetMenu(hwnd), IDM_END_CHAT, MF_GRAYED);
  125.         EnableMenuItem(GetMenu(hwnd), IDM_DISCONNECT_SERVER, MF_GRAYED);
  126.         EnableMenuItem(GetMenu(hwnd), IDM_CONNECT, MF_ENABLED);
  127.         SetWindowText(hwnd, szTitle);
  128.     }
  129.     return 0;
  130. }
  131.  
  132.  
  133. //
  134. //  FUNCTION: Select(HWND, UINT, WPARAM, LPARAM)
  135. //
  136. //  PURPOSE:  Processes messages for "Select" dialog box.
  137. //
  138. //  PARAMETERS:
  139. //    hdlg - window handle of the dialog box
  140. //    wMessage - type of message
  141. //    wparam - message-specific information
  142. //    lparam - message-specific information
  143. //
  144. //  RETURN VALUE:
  145. //    TRUE - message handled
  146. //    FALSE - message not handled
  147. //
  148. //  COMMENTS:
  149. //
  150. //     Display version information from the version section of the
  151. //     application resource.
  152. //
  153. //     Wait for user to click on "Ok" button, then close the dialog box.
  154. //
  155.  
  156. LRESULT CALLBACK Select(HWND hdlg, UINT uMessage, WPARAM wparam, LPARAM lparam)
  157. {
  158.     return DispMessage(&msdiSelect, hdlg, uMessage, wparam, lparam);
  159. }
  160.  
  161.  
  162. //
  163. //  FUNCTION: MsgSelectInit(HWND, UINT, WPARAM, LPARAM)
  164. //
  165. //  PURPOSE: Sets up socket message notifications
  166. //
  167. //  PARAMETERS:
  168. //    hwnd - The window handing the message.
  169. //    uMessage - The message number. (unused).
  170. //    wparam - Message specific data (unused).
  171. //    lparam - Message specific data (unused).
  172. //
  173. //  RETURN VALUE:
  174. //    Always returns 0 - message handled.
  175. //
  176. //  COMMENTS:
  177. //    Uses WSAAsyncSelect() to have socket event notifications sent
  178. //    to the Select Dialog Window
  179. //
  180.  
  181. LRESULT MsgSelectInit(HWND hdlg, UINT uMessage, WPARAM wparam, LPARAM lparam)
  182. {
  183.  
  184.     // Center the dialog over the application window
  185.     CenterWindow(hdlg, GetWindow(hdlg, GW_OWNER));
  186.  
  187.     if(WSAAsyncSelect(MySock.sock, hdlg, MW_DATAREADY, FD_READ | FD_CLOSE) != 0)
  188.     {
  189.         // ERROR  do something
  190.     }
  191.     return TRUE;
  192. }
  193.  
  194. //
  195. //  FUNCTION: MsgSelectDataReady(HWND, UINT, WPARAM, LPARAM)
  196. //
  197. //  PURPOSE: Processes incoming messages from server
  198. //
  199. //  PARAMETERS:
  200. //    hwnd - The window handing the message.
  201. //    uMessage - The message number. (unused).
  202. //    wparam - Message specific data (unused).
  203. //    lparam - Message specific data (unused).
  204. //
  205. //  RETURN VALUE:
  206. //    Always returns 0 - message handled.
  207. //
  208. //  COMMENTS:
  209. //    Receive message and then process command in message header
  210. //
  211.  
  212. LRESULT MsgSelectDataReady(HWND hdlg, UINT uMessage, WPARAM wparam, LPARAM lparam)
  213. {
  214.  
  215.     int iIndex;
  216.     char displaytext[128];
  217.  
  218.     // First check to see if connection was closed
  219.     if(LOWORD(lparam) == FD_CLOSE)
  220.     {
  221.         // Connection closed kill our socket
  222.         closesocket(MySock.sock);
  223.  
  224.         MessageBox(hdlg, GetStringRes(IDS_ERR_CONNECTION_DROPPED), NULL, MB_OK);
  225.  
  226.         // Fix menus
  227.         EnableMenuItem(GetMenu(GetParent(hdlg)), IDM_CONNECT, MF_ENABLED);
  228.         EnableMenuItem(GetMenu(GetParent(hdlg)), IDM_DISCONNECT_SERVER, MF_GRAYED);
  229.         EnableMenuItem(GetMenu(GetParent(hdlg)), IDM_END_CHAT, MF_GRAYED);
  230.  
  231.         EndDialog(hdlg, FALSE);
  232.         return 0;
  233.     }
  234.  
  235.     // receive the message
  236.     if(!recvdatamessage(&MySock, &xferbuf))
  237.     {
  238.         return 0;
  239.     }
  240.  
  241.     // We've got our whole message!  Now switch on the command flag
  242.     switch(xferbuf.hdr.command)
  243.     {
  244.         case REGISTER_NAME:
  245.             // Add name to list box
  246.             SendMessage(GetDlgItem(hdlg, SD_LIST), LB_ADDSTRING, 0, (LPARAM)&xferbuf.data);
  247.             break;
  248.  
  249.         case DEREGISTER_NAME:
  250.             // Remove name from list box
  251.             if((iIndex = SendMessage(GetDlgItem(hdlg, SD_LIST),
  252.                                      LB_FINDSTRING,
  253.                                      (UINT)-1, (LPARAM)&xferbuf.data)) != LB_ERR)
  254.             {
  255.                 // found the index to the item...delete it!
  256.                 SendMessage(GetDlgItem(hdlg, SD_LIST), LB_DELETESTRING, iIndex, 0);
  257.             }
  258.             break;
  259.  
  260.         case REQUEST_SESSION:
  261.           // Someone is asking us for a chat session
  262.             lstrcpy(displaytext, xferbuf.data);
  263.  
  264.             lstrcat(displaytext,
  265.                     GetStringRes(IDS_REQUESTS_CHAT));
  266.  
  267.             if(MessageBox(hdlg, displaytext,
  268.                           GetStringRes(IDS_SESSION_REQUEST), MB_OKCANCEL) == IDOK)
  269.             {
  270.                 // save the name of the peer
  271.                 lstrcpy(peername, xferbuf.data);
  272.                 // We've got ourselves a session!  Send response
  273.                 xferbuf.hdr.command = SESSION_REQUEST_RESPONSE;
  274.                 *(xferbuf.data) = 1;    // Flag to say we accept this session
  275.                 senddatamessage(MySock.sock, &xferbuf);
  276.                 EndDialog(hdlg, TRUE);  // kill the dialog
  277.                 return 0;
  278.             }
  279.             else
  280.             {
  281.                 // We're obviously to stuck up to accept a session
  282.             // from this lowlife...send the denial message
  283.                 xferbuf.hdr.command = SESSION_REQUEST_RESPONSE;
  284.                 *(xferbuf.data) = 0;    // Flag to deny session
  285.                 xferbuf.hdr.length = HDRSIZE;
  286.                 senddatamessage(MySock.sock, &xferbuf);
  287.                 return 0;
  288.             }
  289.             break;  // should never get here
  290.  
  291.         case SESSION_REQUEST_RESPONSE:
  292.           // Someone responded to our session request!
  293.  
  294.             if (MySock.status != SOCKSTAT_REQSESSION)
  295.             {
  296.                 return 0;  // we didn't expect this...drop packet
  297.             }
  298.             if (*xferbuf.data == 1)
  299.             {
  300.                 // Oh JOY!  Acceptance by our peer!
  301.                 EndDialog(hdlg, TRUE);
  302.                 return 0;
  303.             }
  304.             else
  305.             {
  306.                 // Depression...nobody loves us: reenable listbox so we
  307.                 // can just get rejected again.
  308.                 EnableWindow(GetDlgItem(hdlg, SD_LIST), TRUE);
  309.                 EnableWindow(GetDlgItem(hdlg, IDOK), TRUE);
  310.                 return 0;
  311.             }
  312.  
  313.  
  314.         default:
  315.             return 0; // This is unexpected... drop packet
  316.     }
  317.  
  318.     return TRUE;
  319. }
  320.  
  321. //
  322. //  FUNCTION: MsgSelectCommand(HWND, UINT, WPARAM, LPARAM)
  323. //
  324. //  PURPOSE: Process WM_COMMAND message sent to the Select box.
  325. //
  326. //  PARAMETERS:
  327. //    hwnd - The window handing the message.
  328. //    uMessage - The message number. (unused).
  329. //    wparam - Message specific data (unused).
  330. //    lparam - Message specific data (unused).
  331. //
  332. //  RETURN VALUE:
  333. //    Always returns 0 - message handled.
  334. //
  335. //  COMMENTS:
  336. //    Uses this DipsCommand function defined in wndproc.c combined
  337. //    with the cmdiSelect structure defined in this file to handle
  338. //    the command messages for the Select dialog box.
  339. //
  340.  
  341. LRESULT MsgSelectCommand(HWND   hwnd,
  342.                          UINT   uMessage,
  343.                          WPARAM wparam,
  344.                          LPARAM lparam)
  345. {
  346.     return DispCommand(&cmdiSelect, hwnd, wparam, lparam);
  347. }
  348.  
  349. //
  350. //  FUNCTION: CmdSelectDone(HWND, WORD, HWND)
  351. //
  352. //  PURPOSE: Free the Select box and related data.
  353. //
  354. //  PARAMETERS:
  355. //    hwnd - The window handling the command.
  356. //    wCommand - The command to be handled (unused).
  357. //    wNotify   - Notification number (unused)
  358. //    hwndCtrl - NULL (unused).
  359. //
  360. //  RETURN VALUE:
  361. //    Always returns TRUE.
  362. //
  363. //  COMMENTS:
  364. //    Calls EndDialog to finish the dialog session.
  365. //
  366.  
  367. LRESULT CmdSelectDone(HWND hdlg, WORD wCommand, WORD wNotify, HWND hwndCtrl)
  368. {
  369.     if (hFontCopyright)
  370.        DeleteObject(hFontCopyright);
  371.  
  372.     EndDialog(hdlg, FALSE);          // Exit the dialog
  373.     return TRUE;
  374. }
  375.  
  376. //
  377. //  FUNCTION: CmdSelectOK(HWND, WORD, HWND)
  378. //
  379. //  PURPOSE: Requests session with peer
  380. //
  381. //  PARAMETERS:
  382. //    hwnd - The window handling the command.
  383. //    wCommand - The command to be handled (unused).
  384. //    wNotify   - Notification number (unused)
  385. //    hwndCtrl - NULL (unused).
  386. //
  387. //  RETURN VALUE:
  388. //    Always returns TRUE.
  389. //
  390. //  COMMENTS:
  391. //    Sends session request message to selected peer
  392. //
  393.  
  394. LRESULT CmdSelectOK(HWND hdlg, WORD wCommand, WORD wNotify, HWND hwndCtrl)
  395. {
  396.     int iIndex;
  397.  
  398.     // Get selected peer name
  399.     iIndex = SendMessage(GetDlgItem(hdlg, SD_LIST), LB_GETCURSEL, 0, 0);
  400.     SendMessage(GetDlgItem(hdlg, SD_LIST), LB_GETTEXT, iIndex, (LPARAM)&peername);
  401.  
  402.     // Build session request message
  403.     MySock.status = SOCKSTAT_REQSESSION;
  404.     xferbuf.hdr.signature = MYSIGNATURE;
  405.     xferbuf.hdr.length = REALLEN(peername) + HDRSIZE;
  406.     xferbuf.hdr.command = REQUEST_SESSION;
  407.     lstrcpy(xferbuf.data, peername);
  408.     senddatamessage(MySock.sock, &xferbuf);       // Send it!
  409.  
  410.     EnableWindow(GetDlgItem(hdlg, SD_LIST), FALSE);
  411.     EnableWindow(GetDlgItem(hdlg, IDOK), FALSE);
  412.  
  413.     return TRUE;
  414. }
  415.  
  416. //
  417. //  FUNCTION: CmdSelectList(HWND, WORD, HWND)
  418. //
  419. //  PURPOSE: Enables OK button
  420. //
  421. //  PARAMETERS:
  422. //    hwnd - The window handling the command.
  423. //    wCommand - The command to be handled (unused).
  424. //    wNotify   - Notification number (unused)
  425. //    hwndCtrl - NULL (unused).
  426. //
  427. //  RETURN VALUE:
  428. //    Always returns TRUE.
  429. //
  430. //  COMMENTS:
  431. //    When a peer is selected, enable OK button
  432. //
  433.  
  434. LRESULT CmdSelectList(HWND hdlg, WORD wCommand, WORD wNotify, HWND hwndCtrl)
  435. {
  436.     if (wNotify == LBN_SELCHANGE)  // A peer has been selected!
  437.     {
  438.         EnableWindow(GetDlgItem(hdlg, IDOK), TRUE);     // Enable that button!
  439.     }
  440.     return TRUE;
  441. }
  442.  
  443.