Developer guide for multiplayer game pdf

  Developer’s Guide to Multiplayer Games Andrew Mulholland and Teijo Hakala Wordware Publishing, Inc.

  Library of Congress Cataloging-in-Publication Data Mulholland, Andrew.

  Developer’s guide to multiplayer games / by Andrew Mulholland and Teijo Hakala. p. cm.

  ISBN 1-55622-868-6 (pbk.) 1. Computer games--Programming.

I. Hakala, Teijo.

  II. Title. QA76.76.C672 M85 2001 795.8'15--dc21 2001046789

  CIP © 2002, Wordware Publishing, Inc.

  All Rights Reserved 2320 Los Rios Boulevard Plano, Texas 75074

  No part of this book may be reproduced in any form or by any means without permission in writing from Wordware Publishing, Inc.

  Printed in the United States of America

  ISBN 1-55622-868-6 10 9 8 7 6 5 4 3 2 1 0109 OpenGL is a registered trademark of Silicon Graphics, Inc.

  Windows is a registered trademark of Microsoft Corporation.

Other product names mentioned are used for identification purposes only and may be trademarks of their respective companies.

  All inquiries for volume purchases of this book should be addressed to Wordware Publishing, Inc., at the above address. Telephone inquiries may be made by calling: (972) 423-0090

  Contents Theory Introduction . . . . . . . . . . . . . . . . . . . . . . . . . 1

  

Chapter 1 Creating Windows Applications in Visual Studio . . . . . . . . 3 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3 Windows Messaging System . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 3 Creating a Window. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 4 Sending Information to Your Window . . . . . . . . . . . . . . . . . . . . . . . . . . 8 Introduction to Static Link Libraries . . . . . . . . . . . . . . . . . . . . . . . . . . . 9 Creating a Static Link Library . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 10 Using a Static Link Library . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 13 Final Notes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 14

Chapter 2 Internet-Based Database Systems . . . . . . . . . . . . . . . 15 Introduction. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 15 Installing MySQL. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 16 Linux Specific . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 16 Windows Specific . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 17 Overview of MySQL . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18 Creating a Database in MySQL . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 18 Adding Tables to a Database. . . . . . . . . . . . . . . . . . . . . . . . . . . . 19 Adding Data to Tables . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 22 Viewing Data in a Table . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 24 Adding Extra Fields to Tables . . . . . . . . . . . . . . . . . . . . . . . . . . . 28 Updating Data in a Field . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 30 Ordering Output . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 36 Retrieving the Last Data Entered . . . . . . . . . . . . . . . . . . . . . . . . 38 Limiting Output Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 40 Deleting Data from a Table . . . . . . . . . . . . . . . . . . . . . . . . . . . . 40 Deleting Tables and Databases . . . . . . . . . . . . . . . . . . . . . . . . . . 43 Relational Databases . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 46 Creating Our Relational Database . . . . . . . . . . . . . . . . . . . . . . . . 47 Player Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 48 Payment Info . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 50 Notes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 52 Rel Friends . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 53 Rel Enemies . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 55 Adding Relational Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 57 Manipulating the Friend and Enemy Relational Tables . . . . . . . . . . . . . 70 Contents Other Methods of Data Input . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 73 Text File Input . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 73

  Native Database Input . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 75 Backup and Restoration of Databases . . . . . . . . . . . . . . . . . . . . . . . . . . 77 Backup . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 77 Restoration . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 81

  MySQL C++ Interface . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 83 Example 1 — Connecting and Retrieving Data from MySQL. . . . . . . . . . 84 Example 2 — Updating Data in MySQL from an Application . . . . . . . . . . 87 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 90

  Chapter 3 Communicating with the Internet . . . . . . . . . . . . . . . 91 Introduction. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 91 Getting Started . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 91 Debugging Perl . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 93 More Text Output Routines . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 94 Using Files and Templates . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 96 Reading in a Text File . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 96 Writing to a Text File . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 98 Using Templates . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 99 Using Forms. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 103 Command Processing. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 110 Retrieving the Date and Time . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 118 Installing the Perl Database Interface (DBI) . . . . . . . . . . . . . . . . . . . . . 120 Connecting and Disconnecting . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 121 Retrieving and Displaying Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . 123 Adding New Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 129 Using the Unique ID Field . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 137 DisplayData Function. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 147 AddData Function. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 150 DoAddData Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 151 Modify Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 152 DoModifyData Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 156 DeleteData Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 158 Adding a Search Facility . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 163 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 180 Chapter 4 Introduction to TCP/IP . . . . . . . . . . . . . . . . . . . . . 181 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 181 What is a Protocol? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 181 OSI Model . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 182 OSI Model Layers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 183 Internet Protocol . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 184 Introduction to the Transport Layer . . . . . . . . . . . . . . . . . . . . . . . . . . 186 Transmission Control Protocol . . . . . . . . . . . . . . . . . . . . . . . . . 186 User Datagram Protocol . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 187 Ports . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 187

  Contents Introduction to Sockets . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 188 Socket Types . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 189

  Address . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 189 Platforms . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 190 History of WinSock . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 190 Choosing the Platform . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 191

  Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 191

Chapter 5 Basic Sockets Programming. . . . . . . . . . . . . . . . . . 193 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 193 WinSock Initialization. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 193 WSAStartup Function (Win32). . . . . . . . . . . . . . . . . . . . . . . . . . 193 WSACleanup Function (Win32) . . . . . . . . . . . . . . . . . . . . . . . . . 194 WSAEnumProtocols Function (Win32) . . . . . . . . . . . . . . . . . . . . . 195 WinSock Initialization Function . . . . . . . . . . . . . . . . . . . . . . . . . 195 Error Handling . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 198 WSAGetLastError Function (Win32) . . . . . . . . . . . . . . . . . . . . . . 198 Sockets Data Types . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 199 Platform Specific Data Types . . . . . . . . . . . . . . . . . . . . . . . . . . 199 Address Structures . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 199 IPv4 Address Structure . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 199 IPv6 Address Structure . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 200 Generic Address Structure. . . . . . . . . . . . . . . . . . . . . . . . . . . . 201 Basic Sockets Functions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 202 Socket Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . 202 Bind Function (Unix, Win32). . . . . . . . . . . . . . . . . . . . . . . . . . . 203 Connect Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . 204 Listen Function (Unix, Win32). . . . . . . . . . . . . . . . . . . . . . . . . . 205 Accept Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . 206 Close Function (Unix)/Closesocket Function (Win32) . . . . . . . . . . . . . 207 Input/Output Functions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 207 Send Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . . 207 Recv Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . . 209 Sendto Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . 210 Recvfrom Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . 211 Address Data Conversion Functions. . . . . . . . . . . . . . . . . . . . . . . . . . 212 Inet_aton Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . 212 Client/Server Programming . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 212 Server Methods. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 212 Clients . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 214 Byte Ordering . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 214 Creating a Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 215 TCP . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 216 UDP . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 217 Simple Echo TCP Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . 218 Main Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 221 InitSockets Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . 222

  Contents ServerProcess Function . . . . . . . . . . . . . . . . . . . . . . . . . . 224 Simple Echo UDP Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . 225 InitSockets Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . 228 ServerProcess Function . . . . . . . . . . . . . . . . . . . . . . . . . . 228

  Creating a Client . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 230 TCP . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 230 UDP . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 230 Simple Echo TCP Client . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 231

  Main Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 233 InitSockets Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . 234 ClientProcess Function . . . . . . . . . . . . . . . . . . . . . . . . . . 235 Simple Echo UDP Client . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 237 InitSockets Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . 239 ClientProcess Function . . . . . . . . . . . . . . . . . . . . . . . . . . 239

  Running the Simple Echo Application . . . . . . . . . . . . . . . . . . . . . . . . . 240 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 241

Chapter 6 I/O Operations . . . . . . . . . . . . . . . . . . . . . . . . 243 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 243 Detecting Network Events . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 243 Select Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . . 243 Macros . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 244 WSAAsyncSelect Function (Win32) . . . . . . . . . . . . . . . . . . . . . . . 245 WSAEventSelect Function (Win32) . . . . . . . . . . . . . . . . . . . . . . . 245 WSAWaitForMultipleEvents Function (Win32). . . . . . . . . . . . . . . . . 246 Event Object . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 247 Multithreading . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 247 What is Multithreading? . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 248 CreateThread Function (Win32) . . . . . . . . . . . . . . . . . . . . . . . . . 248 Pthread_Create Function (Unix). . . . . . . . . . . . . . . . . . . . . . . . . 249 I/O Strategy . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 250 Blocking I/O. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 250 Non-blocking I/O . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 250 Signal-Driven I/O . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 251 Multiplexing I/O . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 252 I/O Control . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 252 Ioctl (Unix)/IoctlSocket Function (Win32) . . . . . . . . . . . . . . . . . . . 252 SetSockOpt/GetSockOpt Function (Unix, Win32) . . . . . . . . . . . . . . . 253 Shutdown Function (Unix, Win32). . . . . . . . . . . . . . . . . . . . . . . . 255 Broadcasting. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 256 Searching for Servers . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 256 Broadcast Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 256 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 258

  Contents Tutorial Introduction . . . . . . . . . . . . . . . . . . . . . . . 259

  

Tutorial 1 Using Our 2D Library . . . . . . . . . . . . . . . . . . . . . 261

Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 261 Configuring Visual Studio . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 261 Creating a Skeleton Project . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 262

  Creating the Workspace . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 262 Adding the Static Libraries. . . . . . . . . . . . . . . . . . . . . . . . . 263 Adding the Source File . . . . . . . . . . . . . . . . . . . . . . . . . . . 263 Creating a Basic Windowed Application with 2DLib . . . . . . . . . . . . . . 264 The WinMain Function . . . . . . . . . . . . . . . . . . . . . . . . . . . 264 The Windows Procedure . . . . . . . . . . . . . . . . . . . . . . . . . . 266 The Complete Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . 268 Using the 2DLib Graphics Routines . . . . . . . . . . . . . . . . . . . . . . . . . . 270

  Graphical Functions . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 270

  2D Positions on the Screen . . . . . . . . . . . . . . . . . . . . . . . . 270 Use of Colors . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 271 Plotting a Single Pixel . . . . . . . . . . . . . . . . . . . . . . . . . . . 271 Drawing a Line . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 271 Drawing a Rectangle/Filled Rectangle . . . . . . . . . . . . . . . . . . 271 Drawing a Triangle/Filled Triangle . . . . . . . . . . . . . . . . . . . . 272 Graphic Loading Functions . . . . . . . . . . . . . . . . . . . . . . . . 272 Graphics Display (Blitting) Function . . . . . . . . . . . . . . . . . . . 273 Keyboard Input Method . . . . . . . . . . . . . . . . . . . . . . . . . . 273

  2DLib Example 1 — Moving Primitives with the Cursor Keys . . . . . . . . 275 Complete Code Listing for Example 1 . . . . . . . . . . . . . . . . . . 277

  2DLib Example 2 — Loading and Rotating Graphics . . . . . . . . . . . . . 280 Complete Code Listing for Example 2 . . . . . . . . . . . . . . . . . . 281 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 283

Tutorial 2 Creating Your Network Library . . . . . . . . . . . . . . . . 285

Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 285 Why Create a Network Library of Our Own? . . . . . . . . . . . . . . . . . . . . . 285 Planning the Structure . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 286 Planning the Functionality . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 287

  Identifying Hosts . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 287 Sending Data to Hosts . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 287 Building the Library . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 288 Windows. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 288

  Unix/Linux . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 289 Creating Independent Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 290 Creating Definitions for Data Types . . . . . . . . . . . . . . . . . . . . . . . 290 Protocol Independence . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 291

  Transport Protocol Independence . . . . . . . . . . . . . . . . . . . . . 291 Internet Protocol Independence . . . . . . . . . . . . . . . . . . . . . . 292 Log System . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 292 Getting Started . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 294 Contents Setting Up Source and Header Files . . . . . . . . . . . . . . . . . . . . . . 294 NET_Socket Class . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 295 Individual Setup Functions. . . . . . . . . . . . . . . . . . . . . . . . . . . . 298 Dependence . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 301 NET_Socket Class Initialization Functions . . . . . . . . . . . . . . . . . . . 301 Constructor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 301

  Destructor . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 301 Shutdown . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 302 Closing Connections . . . . . . . . . . . . . . . . . . . . . . . . . . . . 302 Closing Input Event Handle . . . . . . . . . . . . . . . . . . . . . . . . 303 Setting the Local Host Offline . . . . . . . . . . . . . . . . . . . . . . . 303 Setting Blocking/Non-Blocking . . . . . . . . . . . . . . . . . . . . . . . . . 303

  Message System . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 304 Sending/Receiving Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 306 Read Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 306 ReadFrom Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . 309 Write Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 311 WriteTo Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 313 WriteAll Function. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 315 Host ID System. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 318 Finding Next Free Host Index . . . . . . . . . . . . . . . . . . . . . . . 318 Giving Local ID . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 319

  Creating the Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 320 CreateServer Function . . . . . . . . . . . . . . . . . . . . . . . . . . . 320 CreateWinServer Function . . . . . . . . . . . . . . . . . . . . . . . . 321 CreateTCPServer Function . . . . . . . . . . . . . . . . . . . . . . . . 324 CreateWinTCPServer Function . . . . . . . . . . . . . . . . . . . . . . 324 Accepting a Connection . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 325

  Connecting to the Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . 329 ConnectToServer Function . . . . . . . . . . . . . . . . . . . . . . . . 329 CloseConnection Function . . . . . . . . . . . . . . . . . . . . . . . . . 336 Multithreading . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 340

  Handling Network Events . . . . . . . . . . . . . . . . . . . . . . . . . . . . 344 WinHandleEvents Function . . . . . . . . . . . . . . . . . . . . . . . . 345 ProcessMessages Function . . . . . . . . . . . . . . . . . . . . . . . . 347 Message Recording. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 351

  Complete Independent Version . . . . . . . . . . . . . . . . . . . . . . . . . . . . 351 NET_Socket Class . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 352 Constructor/Destructor . . . . . . . . . . . . . . . . . . . . . . . . . . 353 RemoteHost Class . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 354

  Initializing/Uninitializing . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 355 Blocking/Non-blocking I/O . . . . . . . . . . . . . . . . . . . . . . . . . . . . 355 Sending/Receiving Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 356 Read Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 356

  ReadFrom Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . 358 Write Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 359 WriteTo Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 361

  Contents WriteAll Function. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 362 Message Buffer System . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 364 Message Buffer Class . . . . . . . . . . . . . . . . . . . . . . . . . . . 365 ReadToBuffer Function. . . . . . . . . . . . . . . . . . . . . . . . . . . 365 ProcessMessageBuffer Function . . . . . . . . . . . . . . . . . . . . . 366 ProcessMessages Function . . . . . . . . . . . . . . . . . . . . . . . . 370

  Buffered Function Calls . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 372 WinHandleEvents Function (Win32) . . . . . . . . . . . . . . . . . . . 372 Platform-Dependent Functions . . . . . . . . . . . . . . . . . . . . . . . . . 373 NET_WinIOThreadFunc (Win32) . . . . . . . . . . . . . . . . . . . . . 373

  NET_WinUDPServerIOThreadFunc (Win32) . . . . . . . . . . . . . . 375 NET_UnixIOThreadFunc (Unix) . . . . . . . . . . . . . . . . . . . . . 383 NET_UnixUDPServerIOThreadFunc (Unix) . . . . . . . . . . . . . . . 386 Give Local ID Number . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 390 GiveLocalIdTCP Function . . . . . . . . . . . . . . . . . . . . . . . . . 390 GiveLocalIdUDP Function . . . . . . . . . . . . . . . . . . . . . . . . . 391

  Creating a Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 394 CreateServer Function . . . . . . . . . . . . . . . . . . . . . . . . . . . 394 CreateWinServer Function . . . . . . . . . . . . . . . . . . . . . . . . 395 CreateUnixServer Function . . . . . . . . . . . . . . . . . . . . . . . . 398 CreateTCPServer and CreateUDPServer Functions. . . . . . . . . . . 399 CreateWinTCPServer Function . . . . . . . . . . . . . . . . . . . . . . 400 CreateUnixTCPServer Function . . . . . . . . . . . . . . . . . . . . . 400 NET_UnixPollAcceptFunc Function . . . . . . . . . . . . . . . . . . . 401 CreateWinUDPServer Function . . . . . . . . . . . . . . . . . . . . . . 402 CreateUnixUDPServer Function . . . . . . . . . . . . . . . . . . . . . 403 AcceptConnection Function . . . . . . . . . . . . . . . . . . . . . . . . 404 Connecting to a Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 406 ConnectToServer Function . . . . . . . . . . . . . . . . . . . . . . . . 406 CloseConnection Function . . . . . . . . . . . . . . . . . . . . . . . . . 413 Shutdown Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 416 Final Thoughts . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 416

  Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 417

Tutorial 3 Creating the Login System . . . . . . . . . . . . . . . . . . 419

Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 419 Creating the Database . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 419 Creating Our Basic Client Application. . . . . . . . . . . . . . . . . . . . . . . . . 421 Integrating the Login System (Part 1). . . . . . . . . . . . . . . . . . . . . . . . . 429

  Creating Our Dialogs . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 429 Coding the Login System . . . . . . . . . . . . . . . . . . . . . . . . . . . . 433 Creating the Login Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 438 Messages . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 439

  LobbyLogin Message. . . . . . . . . . . . . . . . . . . . . . . . . . . . 439 LobbyLoginFeedback Message . . . . . . . . . . . . . . . . . . . . . . 440 LobbyCreateAccount Message . . . . . . . . . . . . . . . . . . . . . . 440 LobbyCreateAccountFeedback Message . . . . . . . . . . . . . . . . . 441 Contents The Header File . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 441 The Main Server File. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 442 Server Application — Complete Code Listing . . . . . . . . . . . . . . . . . 453 Integrating the Login System (Part 2). . . . . . . . . . . . . . . . . . . . . . . . . 462 Client Application — Complete Code Listing . . . . . . . . . . . . . . . . . 472 Executing the Login System . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 483

  Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 486 Tutorial 4 Creating the Game Lobby . . . . . . . . . . . . . . . . . . . 487 Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 487 Creating the Lobby Client Application . . . . . . . . . . . . . . . . . . . . . . . . 487

  Creating the Dialogs . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 488 Lobby Dialog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 488 Create Game Dialog . . . . . . . . . . . . . . . . . . . . . . . . . . . . 491 Create View Players Dialog . . . . . . . . . . . . . . . . . . . . . . . . 492 Join Game Dialog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 492 Game Code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 493 Main.cpp/Main.h . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 493 Netcommon.h . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 494 Init.cpp . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 494 Chat System . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 495 TutChatClass . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 495 SendMessage Function. . . . . . . . . . . . . . . . . . . . . . . . . . . 495

  Handling Chat Messages . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 497 HandleChatMessages Function . . . . . . . . . . . . . . . . . . . . . . 497 Player Identification . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 497 Logging In. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 498

  LoginToServer Function . . . . . . . . . . . . . . . . . . . . . . . . . . 498 Game Lobby. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 498 Lobby Dialog . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 498 LogoutFromServer Function . . . . . . . . . . . . . . . . . . . . . . . 503

  Handling Remove Player Message . . . . . . . . . . . . . . . . . . . . . . . 505 RemovePlayer Function . . . . . . . . . . . . . . . . . . . . . . . . . . 506 LobbyRefreshPlayerList Function. . . . . . . . . . . . . . . . . . . . . 506 Creating a New Game . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 507 CreateGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . . 507 CreateGameDialogProc Function . . . . . . . . . . . . . . . . . . . . . 507 DoCreateGame Function. . . . . . . . . . . . . . . . . . . . . . . . . . 510 CreateViewPlayers Function . . . . . . . . . . . . . . . . . . . . . . . 510 CreateViewPlayersDialogProc Function . . . . . . . . . . . . . . . . . 511 DoDestroyGame Function . . . . . . . . . . . . . . . . . . . . . . . . . 511

  Joining a Game . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 512 JoinGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 512 DoJoinGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . . 513 JoinGameDialogProc Function. . . . . . . . . . . . . . . . . . . . . . . 513 DoLogoff Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 514 Updating the Lobby Lists . . . . . . . . . . . . . . . . . . . . . . . . . . . . 514

  LobbyRefreshJoinedPlayerList Function . . . . . . . . . . . . . . . . . 514 LobbyRefreshGameList Function . . . . . . . . . . . . . . . . . . . . . 515 Creating the Lobby Server Application . . . . . . . . . . . . . . . . . . . . . . . . 516 PlayerServed_t Structure . . . . . . . . . . . . . . . . . . . . . . . . . . . . 516

  ArmyServerClass Init Function . . . . . . . . . . . . . . . . . . . . . . . . . 516 ArmyServerClass Shutdown Function . . . . . . . . . . . . . . . . . . . . . 517 Handling Login Messages . . . . . . . . . . . . . . . . . . . . . . . . . . . . 518 Handling Logout Messages . . . . . . . . . . . . . . . . . . . . . . . . . . . 519

  LogoutPlayer Function . . . . . . . . . . . . . . . . . . . . . . . . . . . 520 HandlePlayerSync Function . . . . . . . . . . . . . . . . . . . . . . . . 523 HandleGameSync Function . . . . . . . . . . . . . . . . . . . . . . . . 525 Creating a Game . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 527 AddGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 528 DestroyGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . 528 RemoveGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . 529 Joining a Game . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 530 JoinGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 530 LogOff Game . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 530 LogOffGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . . 531 Handling Game Messages on the Server . . . . . . . . . . . . . . . . . . . . 531

  Handling Game Messages on the Client . . . . . . . . . . . . . . . . . . . . 532 Handling the Game Host . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 535 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 536

Tutorial 5 Creating Your Online Game. . . . . . . . . . . . . . . . . . 537

Introduction . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 537 Creating a Game . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 538

  Starting a Game. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 538 StartGame Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . 538 Receiving the Start Game Message . . . . . . . . . . . . . . . . . . . . . . . 538 Handling Main Application Window Messages . . . . . . . . . . . . . . . . . 540

  ApplicationProc Function . . . . . . . . . . . . . . . . . . . . . . . . . 540 Updating the Game Screen . . . . . . . . . . . . . . . . . . . . . . . . . . . 542 DoStartGame Function. . . . . . . . . . . . . . . . . . . . . . . . . . . 542 Game Engine . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 543

  Player Synchronization . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 543 Local Player Movement Variables . . . . . . . . . . . . . . . . . . . . . 544 Data Structures . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 544 Player Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 544

  Bullet Data . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 545 Creating the Game World . . . . . . . . . . . . . . . . . . . . . . . . . . . . 545 ENGINE_Init Function. . . . . . . . . . . . . . . . . . . . . . . . . . . 545 ENGINE_GenerateRandomMap Function . . . . . . . . . . . . . . . . 550 ENGINE_AddPlayer Function . . . . . . . . . . . . . . . . . . . . . . . 551 ENGINE_Shutdown Function . . . . . . . . . . . . . . . . . . . . . . . 551

  Updating the Game World . . . . . . . . . . . . . . . . . . . . . . . . . . . . 552 ENGINE_Render Function . . . . . . . . . . . . . . . . . . . . . . . . 552 Contents Contents ENGINE_DrawMap Function . . . . . . . . . . . . . . . . . . . . . . . 553 ENGINE_ProcessInput Function . . . . . . . . . . . . . . . . . . . . . 555 ENGINE_UpdatePlayers Function . . . . . . . . . . . . . . . . . . . . 561 ENGINE_UpdateBullets Function . . . . . . . . . . . . . . . . . . . . 565 ENGINE_CheckBulletCollisions Function . . . . . . . . . . . . . . . . 566 ENGINE_CheckFlagCollisions Function . . . . . . . . . . . . . . . . . 567

  Handling Player Messages . . . . . . . . . . . . . . . . . . . . . . . . . . . . 569 ENGINE_AddBullet Function . . . . . . . . . . . . . . . . . . . . . . . 571 Game Server . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 572 Running the Server on Unix . . . . . . . . . . . . . . . . . . . . . . . . . . . 573

  Main Function . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 573 Daemon_init Function . . . . . . . . . . . . . . . . . . . . . . . . . . . 573 Summary . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 574 Appendix A Byte Ordering Functions . . . . . . . . . . . . . . . . . . . 575 htons Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . . 575 htonl Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . . 575 ntohs Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . . 575 ntohl Function (Unix, Win32) . . . . . . . . . . . . . . . . . . . . . . . . . . 576

  Appendix B NetLib.h . . . . . . . . . . . . . . . . . . . . . . . . . . . . 577 Index . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 585

  Introduction

With Internet technology developing rapidly, Internet gaming has become ever

more popular, while documentation on how to actually make Internet games

remains inadequate. Developer’s Guide to Multiplayer Games provides in-depth

coverage of all the major topics associated with online game programming, as

well as giving you easy-to-follow, step-by-step tutorials on how to create your

own fully functional network library, back-end MySQL database, and complete,

working online game!

The book contains two main areas. The first is dedicated to explaining practical

theory on how to utilize MySQL, Perl, sockets, and basic Windows dialog pro-

gramming. The second section consists of five extensive tutorials, leading you

through the stages of creating a working online game that you can both learn from and expand upon. After reading this book, you will have a solid knowledge of online game pro- gramming and you will also be able to start making your own online games. Also note that the companion CD-ROM contains all the source code from the book and a ready-to-use version of the network library you will create in the tutorial section. We hope you enjoy reading and learning from this book as much as we have enjoyed writing it!

  About the Authors Andrew Mulholland is currently working as lead programmer at a software development company in Scotland. He is also an undergraduate at the University of Abertay in Dundee studying com- puter games technology. His e-mail address is andrew@dreamcircle.co.uk.

  Teijo Hakala is currently studying software engi- neering at Jyväskylä Polytechnic in Finland and specializes in network design, programming, and optimization. He also has a wide variety of work experience with computer technology. His e-mail address is teijo@dreamcircle.co.uk.

  Andrew Mulholland Teijo Hakala Theory Introduction The theory section of this book is full of practical information that will help you understand how to make functional online games. We recommend that you read

this section thoroughly before attempting the tutorial section, as there is a lot of

knowledge that will benefit you here.

  

This section first covers the basics of dialog-based Windows programming,

which we will utilize in the tutorial section to create our login and lobby system

for the sample online game. Then we cover how to use MySQL and Perl to create

a back-end database for your game, allowing you to interact with game data

directly from a web browser. Then we give an introduction to TCP/IP and sockets,

followed by how to get started with sockets programming. Finally, we learn about

different ways to send data, and how to modify the behavior of our sockets.

  First, let’s look at how to create dialog-based Windows applications…

Chapter 1 Creating Windows Applications in Visual Studio Introduction The most essential knowledge anyone can have is the basics. If you already know

  how to create dialog-based Windows applications, skip past this chapter. If not, this chapter will give you a quick and easy introduction to it so that you will find the rest of this book more accessible.

  The reason for learning this is to be able to create our server applications for the Microsoft Windows operating system.

  Windows Messaging System Windows controls everything by the use of its messaging system. This is a funda- mental idea to grasp if you wish to create any Windows-based applications. Within this messaging system, tasks to be processed by the operating system are stored in a queue. For example, when a user clicks a button in a window, a message is

  4 Chapter 1 / Creating Windows Applications in Visual Studio added to the queue and is then sent to the appropriate window to inform it that the button has been pressed.

  When the operating system creates a window, the window continually checks for messages being sent to it. If it receives a relevant message, it will react accordingly; otherwise, it will send it back to the operating system to be reprocessed.

  Each window created is assigned a unique handle that is used to control and determine which messages are relevant to that window. In code, this is defined as the HWND, or window handle. The main reason behind this system is to allow for multi-tasking and multithreading. This means that the operating system can run more than one application in one instance, even though a processor can only han- dle one task at a time.

  There is a lot more to windows than this, but this should give you a reasonable overview of how the system works.

  Creating a Window Load Microsoft Visual Studio and select File, New… The following dialog box should now be visible in the center of the screen.

  Figure 1-1 Select the Projects tab at the top of the dialog and then choose the Win32 Applica- tion option on the main display. Select the location for your project, enter your project’s name, and click OK.

Chapter 1 / Creating Windows Applications in Visual Studio

  5 Next, select the type of project you wish to create. Leave it on the default option (An empty project) and click the Finish button. A project information box appears; simply click OK in this box.

  Now we are working with the Visual Studio main interface. Currently,

ClassView is active, but we are interested in FileView so select this tab.

  Figure 1-2 FileView lists all of the C and C++ source and header files that are active in your project. Currently we do not have any files in our project so we need to add our main C++ source file.

  Select File, New… as you did before, but this time select the Files tab instead of Projects. The following dialog will be visible.

  Figure 1-3 Select C++ Source File as shown in Figure 1-3 and type in the filename as main.cpp. Click the OK button to add this empty file to your project.

  You now have your main source file in your project, and it is visible in the Visual Studio editor. There are two main items required in a standard Windows program: the entry point to your program, which is named WinMain, and the Windows callback proce-

dure (commonly named WndProc), which is used to keep your Windows

application up to date.

  For what we require though, it is best to take the dialog approach, making it even simpler to design and code. First, we need to add our dialog. Click File,

  6 Chapter 1 / Creating Windows Applications in Visual Studio New… again, but this time select Resource Script. Type in the filename as resource and click OK.

  Once this is done, you will notice another tab has appeared between the ClassView and FileView tabs. This tab is called ResourceView and allows you to visually create and edit dialogs for use within your program.

  Figure 1-4 Once you select the ResourceView tab, you will be presented with the resource editor. Right-click on resource.rc in the main view and then left-click on the Insert

option. You will then be presented with the Insert Resource dialog box.

  Figure 1-5 Select Dialog and click New. Now you will see a sample dialog box in front of you.

  For now, we will not do much to it except change the name of the title bar and its identifier that I will explain after the code below.

  Double-click on the sample dialog box that Visual Studio created. Now a dialog properties box can be seen. All we are interested in here is the ID, which will probably be set to Idd_Dialog1, and the Caption, which should be Dialog. Let’s change the ID to Idd_Client and the Caption to Window Example.

  OK, now it’s time to go back and do some code. We have our dialog template that we can call from our code so let’s use it. Here is the code required to make your dialog appear on the screen:

  // Simple Windows Code #include <windows.h> #include "resource.h" LRESULT CALLBACK ClientDlgProc(HWND DialogWindow, UINT Message, WPARAM wParam, LPARAM lParam) {

Chapter 1 / Creating Windows Applications in Visual Studio

  7

  switch(Message) { case WM_INITDIALOG: return FALSE; case WM_COMMAND: switch(wParam) { case IDCANCEL:

  EndDialog(DialogWindow, FALSE); return FALSE; default: break; } break; default: break; } return FALSE;

  } int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpCmdLine, int nCmdShow) {

  DialogBox((HINSTANCE) hInstance, MAKEINTRESOURCE(IDD_CLIENT), NULL, (DLGPROC) ClientDlgProc); return 0;

  }

  The OK button on the dialog can be pressed but will have no action, whereas the Cancel button will close the dialog.

  NOTE If you get an error and it tells you it can’t find afxres.h, you need to install MFC support for Visual Studio, which comes with the Visual Studio package.

  

If you have never seen Windows code before, the code above may look complex

and a little confusing. Welcome to the world of Windows! It’s not that bad, honest.

  Let’s start with the WinMain function. This is simply the point at which Win- dows starts executing your code. Do not worry about the variables that are passed in; they are controlled by Windows and are beyond the scope of this book.

  

The main issue here is the DialogBox function and callback procedure

(ClientDlgProc) that creates our dialog window on the screen. The first parameter is the instance of the application that you simply take from the first parameter of

  8 Chapter 1 / Creating Windows Applications in Visual Studio template for our dialog. The third parameter is of no interest to us so we set it to NULL, but the final one is. This is a pointer to the update function for the dialog. Each dialog you create requires this update function (basically the same idea as a Windows procedure). In this update function is where you set the actions for but- tons and other useful tools. So we set this update function to our callback function for the dialog (ClientDlgProc). For example, the identifier for the Cancel button is Idcancel. As you can see in the code, there is a Case statement for the Cancel but- ton so when it is clicked, it will close the dialog window. Other buttons can be easily added to the template using the toolbox on the template editor. Just remem- ber that each button must contain a unique ID so you can reference it from within your code.