00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015 #include <Windows.h>
00016 #include <Assert.h>
00017 #include <Math.h>
00018
00019 #include "Client.h"
00020
00021 #include "Buffer.h"
00022 #include "Gmenu.h"
00023 #include "cd.h"
00024
00025 LARGE_INTEGER g_Freq, g_OldTick, g_CurTick;
00026
00027 #define NUM_AVG 10
00028 static float AvgTime[NUM_AVG];
00029 static int32 CurAvg;
00030
00031 static void SubLarge(LARGE_INTEGER *start, LARGE_INTEGER *end, LARGE_INTEGER *delta)
00032 {
00033 _asm {
00034 mov ebx,dword ptr [start]
00035 mov esi,dword ptr [end]
00036
00037 mov eax,dword ptr [esi+0]
00038 sub eax,dword ptr [ebx+0]
00039
00040 mov edx,dword ptr [esi+4]
00041 sbb edx,dword ptr [ebx+4]
00042
00043 mov ebx,dword ptr [delta]
00044 mov dword ptr [ebx+0],eax
00045 mov dword ptr [ebx+4],edx
00046 }
00047 }
00048
00049 #define BEGIN_TIMER() QueryPerformanceCounter(&g_OldTick)
00050
00051 #define END_TIMER(g) \
00052 { \
00053 LARGE_INTEGER DeltaTick; \
00054 float ElapsedTime, Total; \
00055 int32 i; \
00056 \
00057 QueryPerformanceCounter(&g_CurTick); \
00058 SubLarge(&g_OldTick, &g_CurTick, &DeltaTick); \
00059 \
00060 if (DeltaTick.LowPart > 0) \
00061 ElapsedTime = 1.0f / (((float)g_Freq.LowPart / (float)DeltaTick.LowPart)); \
00062 else \
00063 ElapsedTime = 0.001f; \
00064 \
00065 AvgTime[CurAvg] = ElapsedTime; \
00066 CurAvg++; \
00067 CurAvg %= NUM_AVG; \
00068 \
00069 for (Total = 0.0f, i=0; i< NUM_AVG; i++) \
00070 Total += AvgTime[i]; \
00071 \
00072 Total *= (1.0f/ NUM_AVG); \
00073 \
00074 geEngine_Printf(GameMgr_GetEngine(g), 1, 50, "Timer ms: %2.3f/%2.3f", ElapsedTime, Total); \
00075 }
00076 extern geVFile *MainFS;
00077 extern geFloat EffectScale;
00078
00079 static int32 NumUpdates = 0;
00080
00081 #ifdef _DEBUG
00082 Fx_Player *PLAYER_TO_FXPLAYER(Client_Client *Client, GPlayer *Player)
00083 {
00084 uint32 Index;
00085
00086 assert(Client_IsValid(Client) == GE_TRUE);
00087 assert(Player);
00088
00089 assert(Player >= Client->Players);
00090
00091 Index = Player - Client->Players;
00092
00093 assert(Index < NETMGR_MAX_PLAYERS);
00094
00095 return &Client->FxPlayers[Index];
00096 }
00097
00098 Fx_Player *TEMP_PLAYER_TO_FXPLAYER(Client_Client *Client, GPlayer *Player)
00099 {
00100 uint32 Index;
00101
00102 assert(Client_IsValid(Client) == GE_TRUE);
00103 assert(Player);
00104
00105 assert(Player >= Client->TempPlayers);
00106
00107 Index = Player - Client->TempPlayers;
00108
00109 assert(Index < CLIENT_MAX_TEMP_PLAYERS);
00110
00111 return &Client->FxPlayers[Index];
00112 }
00113
00114 uint32 CLIENT_GPLAYER_TO_INDEX(Client_Client *Client, GPlayer *Player)
00115 {
00116 uint32 Index;
00117
00118 assert(Client_IsValid(Client) == GE_TRUE);
00119 assert(Player);
00120
00121 assert(Player >= Client->Players);
00122
00123 Index = (Player - Client->Players);
00124
00125 assert(Index < NETMGR_MAX_PLAYERS);
00126
00127 return Index;
00128 }
00129
00130 uint32 CLIENT_TEMP_GPLAYER_TO_INDEX(Client_Client *Client, GPlayer *Player)
00131 {
00132 uint32 Index;
00133
00134 assert(Client_IsValid(Client) == GE_TRUE);
00135 assert(Player);
00136
00137 assert(Player >= Client->TempPlayers);
00138
00139 Index = (Player - Client->TempPlayers);
00140
00141 assert(Index < CLIENT_MAX_TEMP_PLAYERS);
00142
00143 return Index;
00144 }
00145 #else
00146 #define PLAYER_TO_FXPLAYER(c, p) (&(c)->FxPlayers[(p) - (c)->Players])
00147 #define TEMP_PLAYER_TO_FXPLAYER(c, p) (&(c)->TempFxPlayers[(p) - (c)->TempPlayers])
00148 #define CLIENT_GPLAYER_TO_INDEX(c, p) ((p) - (c)->Players)
00149 #define CLIENT_TEMP_GPLAYER_TO_INDEX(c, p) ((p) - (c)->TempPlayers)
00150 #endif
00151
00152 #define REFRESH_TIMES (4)
00153
00154
00155 #define PREDICT_CLIENT
00156
00157 void GenVS_Error(const char *Msg, ...);
00158
00159
00160
00161
00162 static BOOL IsKeyDown(int KeyCode, HWND hWnd);
00163 BOOL NewKeyDown(int KeyCode, HWND hWnd);
00164 geBoolean ReadServerMessages(Client_Client *Client, GameMgr *GMgr, float Time);
00165 static void UpdatePlayers(Client_Client *Client, float Time);
00166 static geBoolean RenderWorld(Client_Client *Client, GameMgr *GMgr, float Time);
00167 static void SetupCamera(geCamera *Camera, GE_Rect *Rect, geXForm3d *XForm);
00168 static void ParsePlayerDataLocally(Client_Client *Client, Buffer_Data *Buffer, geBoolean Fake);
00169 static void Client_SetupGenVSI(Client_Client *Client);
00170 static geBoolean Client_MovePlayerModel(Client_Client *Client, GPlayer *Player, const geXForm3d *DestXForm);
00171 static geBoolean CheckClientPlayerChanges(Client_Client *Client, GPlayer *Player, geBoolean TempPlayer);
00172 void Client_DestroyPlayer(Client_Client *Client, GPlayer *Player);
00173
00174 #define M_PI (3.14159f)
00175 #define PI_2 (M_PI*2.0f)
00176 #define M_PI2 (PI_2)
00177
00178 uint8 SData[5000];
00179 Buffer_Data SendBuffer;
00180
00181
00182
00183
00184 Client_Client *Client_Create( geEngine *Engine,
00185 Client_Mode Mode,
00186 GameMgr *GMgr,
00187 NetMgr *NMgr,
00188 VidMode VidMode,
00189 int32 DemoMode,
00190 const char *DemoName,
00191 geBoolean MultiPlayer)
00192 {
00193 geRect Rect = {0, 0, 0, 0};
00194
00195 Client_Client *NewClient;
00196
00197 NewClient = GE_RAM_ALLOCATE_STRUCT(Client_Client);
00198
00199 assert(NewClient != NULL);
00200
00201 if (!NewClient)
00202 return NULL;
00203
00204
00205
00206
00207 memset(NewClient, 0, sizeof(Client_Client));
00208
00209
00210 NewClient->Self1 = NewClient;
00211 NewClient->Self2 = NewClient;
00212
00213 NewClient->MultiPlayer = MultiPlayer;
00214
00215
00216 NewClient->NetState = NetState_Disconnected;
00217
00218
00219 NewClient->GMgr = GMgr;
00220 NewClient->NMgr = NMgr;
00221
00222
00223 NewClient->Mode = Mode;
00224
00225
00226 NewClient->VidMode = VidMode;
00227
00228
00229 Client_NewWorldDefaults(NewClient);
00230
00231
00232 geXForm3d_SetIdentity(&NewClient->ViewXForm);
00233 NewClient->ViewPlayer = -1;
00234 NewClient->ClientPlayer = -1;
00235
00236 NewClient->Engine = Engine;
00237
00238 NewClient->Time = 0.0f;
00239
00240 NewClient->CurrentWeapon = 0;
00241
00242 Buffer_Set(&SendBuffer, SData, 5000);
00243
00244
00245 if (!Client_CreateStatusBar(NewClient, VidMode))
00246 {
00247 geErrorLog_AddString(-1, "Client_Create: Client_CreateStatusBar failed.", NULL);
00248 goto ExitWithError;
00249 }
00250
00251
00252 Client_SetupGenVSI(NewClient);
00253
00254
00255 if (!Client_SetupDemos(NewClient, DemoMode, DemoName))
00256 NewClient->Demo.Mode = CLIENT_DEMO_NONE;
00257
00258
00259 Client_Main(&NewClient->GenVSI);
00260 Console_Printf(GameMgr_GetConsole(GMgr), "Client_Create: Client_Main initialized...\n");
00261
00262 QueryPerformanceFrequency(&g_Freq);
00263
00264 return NewClient;
00265
00266 ExitWithError:
00267 {
00268 if (NewClient)
00269 {
00270 Client_FreeALLResources(NewClient);
00271 Client_Destroy(NewClient);
00272 }
00273
00274 return NULL;
00275 }
00276 }
00277
00278
00279
00280
00281 void Client_Destroy(Client_Client *Client)
00282 {
00283 assert(Client_IsValid(Client) == GE_TRUE);
00284
00285 Client_FreeALLResources(Client);
00286
00287 if (Client->Demo.File != NULL)
00288 fclose (Client->Demo.File);
00289
00290 geRam_Free(Client);
00291 }
00292
00293
00294
00295
00296
00297 geBoolean Client_IsValid(const Client_Client *Client)
00298 {
00299 if (!Client)
00300 return GE_FALSE;
00301
00302 if (Client->Self1 != Client)
00303 return GE_FALSE;
00304
00305 if (Client->Self2 != Client)
00306 return GE_FALSE;
00307
00308 return GE_TRUE;
00309 }
00310
00311 #define CONSOLE_HEIGHT_320 (30)
00312 #define CONSOLE_HEIGHT_640 (60)
00313
00314
00315
00316
00317 geBoolean Client_CreateStatusBar(Client_Client *Client, VidMode VidMode)
00318 {
00319 int32 i, k;
00320 int Width,Height;
00321 int LeftElementWidth,ElementHeight,RightElementWidth,PrintOffsX,PrintOffsY,Left;
00322 char BmpPath[MAX_PATH];
00323
00324 assert(Client_IsValid(Client) == GE_TRUE);
00325 assert(Client->Engine);
00326
00327 VidMode_GetResolution(VidMode,&Width,&Height);
00328
00329 if (Width < SMALL_CONSOLE_CUTOFF_WIDTH)
00330 {
00331 strcpy(BmpPath,"320x240");
00332 LeftElementWidth = 56;
00333 RightElementWidth = 52;
00334 ElementHeight = CONSOLE_HEIGHT_320;
00335 PrintOffsX = 18;
00336 PrintOffsY = 10;
00337 Left = (Width-320)/2;
00338 }
00339 else
00340 {
00341 strcpy(BmpPath,"640x480");
00342 LeftElementWidth = 112;
00343 RightElementWidth = 104;
00344 ElementHeight = CONSOLE_HEIGHT_640;
00345 PrintOffsX = 36;
00346 PrintOffsY = 22;
00347 Left = (Width-640)/2;
00348 }
00349
00350 for (i=0; i<6; i++)
00351 {
00352 if (i<2)
00353 {
00354 Client->StatusBar.Elements[i].XPos = Left + LeftElementWidth*i;
00355 }
00356 else
00357 {
00358 Client->StatusBar.Elements[i].XPos = Left + LeftElementWidth*2 + RightElementWidth*(i-2);
00359 }
00360
00361 Client->StatusBar.Elements[i].YPos = Height - 1 - ElementHeight;
00362 Client->StatusBar.Elements[i].Print1XPos = Client->StatusBar.Elements[i].XPos + PrintOffsX;
00363 Client->StatusBar.Elements[i].Print1YPos = Height - 1 - PrintOffsY;
00364 }
00365
00366
00367 for (i=0; i<6; i++)
00368 {
00369 for (k=0; k<3; k++)
00370 {
00371 char Name[64];
00372
00373 sprintf(Name, "Bmp\\SBar\\%s\\SBar%i-%i.Bmp", BmpPath, i, k);
00374
00375 assert(Client->StatusBar.Elements[i].Bitmaps[k] == NULL);
00376
00377 Client->StatusBar.Elements[i].Bitmaps[k] = geBitmap_CreateFromFileName(MainFS, Name);
00378
00379 if (!Client->StatusBar.Elements[i].Bitmaps[k])
00380 {
00381 geErrorLog_AddString(-1, "Client_CreateStatusBar: Could not load status bar element:", Name);
00382 goto ExitWithError;
00383 }
00384
00385 if (!geEngine_AddBitmap(Client->Engine, Client->StatusBar.Elements[i].Bitmaps[k]))
00386 {
00387 geErrorLog_AddString(-1, "Client_CreateStatusBar: geEngine_AddBitmap failed.", NULL);
00388 goto ExitWithError;
00389 }
00390
00391 }
00392 }
00393
00394 return GE_TRUE;
00395
00396 ExitWithError:
00397 {
00398 Client_FreeALLResources(Client);
00399 return GE_FALSE;
00400 }
00401 }
00402
00403
00404
00405
00406 void Client_DestroyStatusBar(Client_Client *Client)
00407 {
00408 int32 i, k;
00409
00410 assert(Client_IsValid(Client) == GE_TRUE);
00411
00412
00413 for (i=0; i<6; i++)
00414 {
00415 for (k=0; k<3; k++)
00416 {
00417 if (!Client->StatusBar.Elements[i].Bitmaps[k])
00418 continue;
00419
00420 if (!geEngine_RemoveBitmap(Client->Engine, Client->StatusBar.Elements[i].Bitmaps[k]))
00421 {
00422 geErrorLog_AddString(-1, "Client_DestroyConsole: geEngine_RemoveBitmap failed.", NULL);
00423 assert(0);
00424 }
00425
00426 geBitmap_Destroy(&Client->StatusBar.Elements[i].Bitmaps[k]);
00427 Client->StatusBar.Elements[i].Bitmaps[k] = NULL;
00428 }
00429 }
00430 }
00431
00432
00433
00434
00435 static void SetPlayerDefaults(GPlayer *Player)
00436 {
00437
00438
00439 Player->OldScale =
00440 Player->Scale = 1.0f;
00441
00442 Player->OldViewFlags = VIEW_TYPE_NONE;
00443 Player->OldViewFlags2 = VIEW_TYPE_NONE;
00444 Player->ViewFlags = VIEW_TYPE_NONE;
00445
00446 Player->OldViewIndex = 0xffff;
00447 Player->OldViewIndex2 = 0xffff;
00448 Player->ViewIndex = 0xffff;
00449
00450 Player->OldControlIndex = 0xffff;
00451 Player->OldTriggerIndex = 0xffff;
00452 Player->ControlIndex = 0xffff;
00453 Player->TriggerIndex = 0xffff;
00454
00455 Player->UpdateTime = -1.0f;
00456
00457 Player->Mesh = NULL;
00458 Player->Actor = NULL;
00459 Player->Light = NULL;
00460 Player->Poly = NULL;
00461
00462 Player->OldMotionIndex =
00463 Player->MotionIndex = GAMEMGR_MOTION_INDEX_NONE;
00464
00465 Player->ActorDef = NULL;
00466 }
00467
00468
00469
00470
00471 void Client_DestroyALLPlayers(Client_Client *Client)
00472 {
00473 int32 i;
00474 GPlayer *Player;
00475
00476 assert(Client_IsValid(Client) == GE_TRUE);
00477
00478
00479 Player = Client->Players;
00480
00481 for (i=0; i< NETMGR_MAX_PLAYERS; i++, Player++)
00482 {
00483 if (!Player->Active)
00484 continue;
00485
00486 Client_DestroyPlayer(Client, Player);
00487 }
00488
00489
00490 Player = Client->TempPlayers;
00491
00492 for (i=0; i< CLIENT_MAX_TEMP_PLAYERS; i++, Player++)
00493 {
00494 if (!Player->Active)
00495 continue;
00496
00497 Client_DestroyTempPlayer(Client, Player);
00498 }
00499 }
00500
00501
00502
00503
00504 void Client_FreeALLResources(Client_Client *Client)
00505 {
00506 geBoolean Ret;
00507
00508 assert(Client_IsValid(Client) == GE_TRUE);
00509
00510 Ret = GE_TRUE;
00511
00512
00513 Client_DestroyStatusBar(Client);
00514
00515
00516 Client_DestroyALLPlayers(Client);
00517
00518
00519 while (Client_PeekMove(Client))
00520 Client_RemoveFirstMove(Client);
00521
00522 assert(Ret == GE_TRUE);
00523 }
00524
00525
00526
00527
00528 void Client_FreeResourcesForNewWorld(Client_Client *Client)
00529 {
00530
00531 Client_DestroyALLPlayers(Client);
00532
00533
00534 while (Client_PeekMove(Client))
00535 Client_RemoveFirstMove(Client);
00536 }
00537
00538 static int32 LastPlayer = -1;
00539
00540
00541
00542
00543 void Client_NewWorldDefaults(Client_Client *Client)
00544 {
00545 int32 i;
00546
00547 assert(Client_IsValid(Client) == GE_TRUE);
00548
00549
00550 for (i=0; i< NETMGR_MAX_PLAYERS; i++)
00551 SetPlayerDefaults(&Client->Players[i]);
00552
00553 Client->Time = 0.0f;
00554 Client->NetTime = 0.0f;
00555 Client->OldNetTime = 0.0f;
00556
00557 LastPlayer = -1;
00558
00559
00560 NumUpdates = REFRESH_TIMES;
00561 }
00562
00563
00564
00565
00566 static geBoolean PrintClientScores(Client_Client *Client)
00567 {
00568 int32 i, k, j, Total;
00569 int32 Sorted[NETMGR_MAX_CLIENTS];
00570 int32 SortedScores[NETMGR_MAX_CLIENTS];
00571 Client_ClientInfo *ClientInfo;
00572 char *Name;
00573 int32 Score;
00574 int Width,Height;
00575
00576 assert(Client_IsValid(Client) == GE_TRUE);
00577
00578
00579 Total = 0;
00580 ClientInfo = Client->ClientInfo;
00581
00582 for (i=0 ; i<NETMGR_MAX_CLIENTS; i++, ClientInfo++)
00583 {
00584 if (!ClientInfo->Active)
00585 continue;
00586
00587 Score = ClientInfo->Score;
00588
00589 for (j=0 ; j<Total ; j++)
00590 {
00591 if (Score > SortedScores[j])
00592 break;
00593 }
00594
00595 for (k=Total ; k>j ; k--)
00596 {
00597 Sorted[k] = Sorted[k-1];
00598 SortedScores[k] = SortedScores[k-1];
00599 }
00600 Sorted[j] = i;
00601 SortedScores[j] = Score;
00602 Total++;
00603 }
00604
00605 VidMode_GetResolution(Client->VidMode,&Width,&Height);
00606
00607 for (i=0; i< Total; i++)
00608 {
00609 int Line;
00610 ClientInfo = &Client->ClientInfo[Sorted[i]];
00611
00612 Name = ClientInfo->Name;
00613 Score = ClientInfo->Score;
00614
00615 if (Width < SMALL_CONSOLE_CUTOFF_WIDTH)
00616 Line = i+((Height-30)/6)-9;
00617 else
00618 Line = i+((Height-60)/15)-9;
00619
00620 if (!Console_XYPrintf(GameMgr_GetConsole(Client->GMgr), 0, Line, 0, "%12s: %4i", Name, Score))
00621 return GE_FALSE;
00622 }
00623
00624
00625 if (Width < SMALL_CONSOLE_CUTOFF_WIDTH)
00626 {
00627 if (Client->MultiPlayer)
00628 {
00629 if (!Console_XYPrintf(GameMgr_GetConsole(Client->GMgr), (Width/6)-13, ((Height-30)/6)-2, 0, "Ping: %2.2f", Client->Ping*1000.0f))
00630 return GE_FALSE;
00631 }
00632 }
00633 else
00634 {
00635 if (Client->MultiPlayer)
00636 {
00637 if (!Console_XYPrintf(GameMgr_GetConsole(Client->GMgr), (Width/9)-13, ((Height-60)/16)-1, 0, "Ping: %2.2f", Client->Ping*1000.0f))
00638 return GE_FALSE;
00639 }
00640 }
00641
00642 return GE_TRUE;
00643 }
00644
00645
00646
00647
00648 static void PrintCrossHair(Client_Client *Client)
00649 {
00650 int Width,Height;
00651
00652 VidMode_GetResolution(Client->VidMode,&Width,&Height);
00653
00654 if (Width < SMALL_CONSOLE_CUTOFF_WIDTH)
00655 {
00656 if (!Console_XYPrintf(GameMgr_GetConsole(Client->GMgr), ((Width/6)/2), (((Height-30)/6)/2), 0, "*"))
00657 GenVS_Error("PrintCrossHair: Console_XYPrintf failed.\n");
00658 }
00659 else
00660 {
00661 if (!Console_XYPrintf(GameMgr_GetConsole(Client->GMgr), ((Width/9)/2), (((Height-60)/15)/2)-1, 0, "+"))
00662 GenVS_Error("PrintCrossHair: Console_XYPrintf failed.\n");
00663 }
00664 }
00665
00666
00667
00668
00669 static geBoolean DrawStatusBar(Client_Client *Client)
00670 {
00671 Client_ClientInfo *ClientInfo;
00672 uint32 Ammo;
00673 geBoolean HasItem;
00674 int32 i;
00675 int32 Val[6];
00676
00677 assert(Client_IsValid(Client) == GE_TRUE);
00678
00679 ClientInfo = &Client->ClientInfo[Client->ClientIndex];
00680
00681 Val[0] = ClientInfo->Health;
00682 Val[1] = Client->Inventory[16] & ((1<<15)-1);
00683
00684
00685 for (i=0; i< 2; i++)
00686 {
00687 geBitmap *Bitmap;
00688 Client_StatusElement *Element;
00689
00690 Element = &Client->StatusBar.Elements[i];
00691
00692
00693
00694
00695 Bitmap = Element->Bitmaps[STATE_Normal];
00696
00697 geEngine_DrawBitmap(Client->Engine, Bitmap, NULL, Element->XPos, Element->YPos);
00698 }
00699
00700 for (i=0; i< 4; i++)
00701 {
00702 geBitmap *Bitmap;
00703 Client_StatusState State;
00704 Client_StatusElement *Element;
00705
00706 Element = &Client->StatusBar.Elements[i+2];
00707
00708 Ammo = Client->Inventory[i];
00709
00710 HasItem = (Ammo & (1<<15));
00711
00712 Ammo &= 0xff;
00713
00714 if (i == 0)
00715 {
00716 HasItem = GE_TRUE;
00717 Ammo = 99;
00718 }
00719
00720 if (!HasItem)
00721 {
00722 State = STATE_Disable;
00723 }
00724 else if (i == Client->CurrentWeapon)
00725 {
00726
00727
00728
00729 State = STATE_Selected;
00730 }
00731 else
00732 {
00733
00734
00735
00736 State = STATE_Normal;
00737 }
00738
00739 Element->State = State;
00740
00741 Bitmap = Element->Bitmaps[State];
00742
00743 geEngine_DrawBitmap(Client->Engine, Bitmap, NULL, Element->XPos, Element->YPos);
00744
00745 Val[i+2] = Ammo;
00746 }
00747
00748 for (i=0; i<6; i++)
00749 {
00750 char Temp[32];
00751 int32 XPos, YPos;
00752
00753 if (i==2)
00754 strcpy(Temp, "Inf");
00755 else
00756 sprintf(Temp, "%i", Val[i]);
00757
00758 XPos = Client->StatusBar.Elements[i].Print1XPos;
00759 YPos = Client->StatusBar.Elements[i].Print1YPos;
00760
00761 Console_XYPrintf(GameMgr_GetConsole(Client->GMgr), XPos, YPos, 1, "%s", Temp);
00762 }
00763
00764 return GE_TRUE;
00765
00766 }
00767
00768
00769
00770
00771 void Client_RefreshStatusBar(int32 NumPages)
00772 {
00773 NumPages;
00774 NumUpdates = REFRESH_TIMES;
00775 }
00776
00777
00778
00779 static void UpdateStatusBar(Client_Client *Client)
00780 {
00781 Client_ClientInfo *ClientInfo;
00782 int32 i;
00783
00784 assert(Client_IsValid(Client) == GE_TRUE);
00785 assert(Client->ClientIndex >= 0 && Client->ClientIndex < NETMGR_MAX_CLIENTS);
00786
00787 ClientInfo = &Client->ClientInfo[Client->ClientIndex];
00788
00789 for (i=0; i<4; i++)
00790 {
00791 if (Client->Inventory[i] != Client->OldInventory[i])
00792 {
00793 Client->OldInventory[i] = Client->Inventory[i];
00794 NumUpdates = REFRESH_TIMES;
00795 break;
00796 }
00797 }
00798
00799 for (i=16; i<17; i++)
00800 {
00801 if (Client->Inventory[i] != Client->OldInventory[i])
00802 {
00803 NumUpdates = REFRESH_TIMES;
00804 break;
00805 }
00806 }
00807
00808 for (i=0; i<4; i++)
00809 {
00810 if (Client->Inventory[i] != Client->OldInventory[i])
00811 {
00812 Client->OldInventory[i] = Client->Inventory[i];
00813 NumUpdates = REFRESH_TIMES;
00814 break;
00815 }
00816 }
00817
00818 if (Client->CurrentWeapon != Client->OldWeapon)
00819 {
00820 Client->OldWeapon = Client->CurrentWeapon;
00821 NumUpdates = REFRESH_TIMES;
00822 }
00823
00824 if (ClientInfo->OldHealth != ClientInfo->Health)
00825 {
00826 ClientInfo->OldHealth = ClientInfo->Health;
00827 NumUpdates = REFRESH_TIMES;
00828 }
00829
00830 if (NumUpdates <= 0)
00831 return;
00832
00833 if (!DrawStatusBar(Client))
00834 GenVS_Error("UpdateStatusBar: Could not draw the status bar.");
00835
00836 NumUpdates--;
00837 }
00838
00839
00840
00841
00842 static void ControlTempPlayers(Client_Client *Client, float Time)
00843 {
00844 int32 i;
00845 GPlayer *Player;
00846
00847 assert(Client_IsValid(Client) == GE_TRUE);
00848
00849 Player = Client->TempPlayers;
00850
00851 for (i=0; i<CLIENT_MAX_TEMP_PLAYERS; i++, Player++)
00852 {
00853 if (!Player->Active)
00854 continue;
00855
00856 if (!Player->Control)
00857 continue;
00858
00859 Player->Control(&Client->GenVSI, Player, Time);
00860
00861 if (!Fx_PlayerSetFxFlags(GameMgr_GetFxSystem(Client->GMgr), TEMP_PLAYER_TO_FXPLAYER(Client, Player), Player->FxFlags))
00862 GenVS_Error("Client_ControlTempPlayers: Could not set fx flags.\n");
00863
00864 Player->Pos = Player->XForm.Translation;
00865 geXForm3d_GetEulerAngles(&Player->XForm, &Player->Angles);
00866
00867 Client_UpdateSinglePlayer(Client, Player, 1.0f, Time, GE_TRUE);
00868 }
00869 }
00870
00871
00872
00873
00874
00875
00876 geBoolean Client_Frame(Client_Client *Client, float Time)
00877 {
00878 assert(Client_IsValid(Client) == GE_TRUE);
00879
00880 Client->Time += Time;
00881
00882
00883 if (!ReadServerMessages(Client, Client->GMgr, Time))
00884 GenVS_Error("Client_Frame: ReadServerMessages failed.\n");
00885
00886 if (Client->Demo.Mode != CLIENT_DEMO_PLAY)
00887 {
00888
00889 if (Client->NetState == NetState_WorldActive)
00890 {
00891 if (!Client_SendMove(Client, Time))
00892 GenVS_Error("Client_Frame: Client_SendMove failed.\n");
00893 }
00894
00895 ControlTempPlayers(Client, Time);
00896 }
00897
00898 return GE_TRUE;
00899 }
00900
00901
00902
00903
00904 geBoolean Client_RenderFrame(Client_Client *Client, float Time)
00905 {
00906 assert(Client_IsValid(Client) == GE_TRUE);
00907
00908 if (Client->NetState != NetState_WorldActive)
00909 return GE_TRUE;
00910
00911 if (!RenderWorld(Client, Client->GMgr, Time))
00912 GenVS_Error("Client_RenderFrame: RenderWorld failed.\n");
00913
00914
00915 {
00916 if (!PrintClientScores(Client))
00917 GenVS_Error("Client_RenderFrame: PrintClientScores failed.\n");
00918 }
00919
00920 PrintCrossHair(Client);
00921
00922 UpdateStatusBar(Client);
00923
00924 return GE_TRUE;
00925 }
00926
00927 extern float GlobalMouseSpeedX;
00928 extern float GlobalMouseSpeedY;
00929
00930 extern int32 KeyLut[256];
00931 extern geBoolean MouseInvert;
00932
00933
00934
00935
00936
00937 static void Client_MoveClientLocally(Client_Client *Client, Client_Move *Move)
00938 {
00939 GPlayer *Player;
00940
00941 assert(Client_IsValid(Client) == GE_TRUE);
00942 assert(Client->ClientPlayer != -1);
00943
00944 if (!GameMgr_GetWorld(Client->GMgr))
00945 return;
00946
00947
00948
00949 Client->Move.MoveTime = Move->Time;
00950 Client->Move.ForwardSpeed = Move->ForwardSpeed;
00951 Client->Move.Angles.X = Move->Pitch;
00952 Client->Move.Angles.Y = Move->Yaw;
00953 Client->Move.Angles.Z = 0.0f;
00954 Client->Move.ButtonBits = Move->ButtonBits;
00955 Client->Move.Weapon = Move->CurrentWeapon;
00956 Client->Move.PingTime = Move->Delta;
00957
00958 Player = &Client->Players[Client->ClientPlayer];
00959
00960 if (Player->Control)
00961 Player->Control(&Client->GenVSI, Player, Move->Delta);
00962
00963 Player->Pos = Player->XForm.Translation;
00964 }
00965
00966 int32 NumMoves = 0;
00967
00968
00969
00970
00971 void Client_AddMove(Client_Client *Client, Client_Move *Move)
00972 {
00973 Client_Move *NewMove, *Last;
00974
00975 NewMove = GE_RAM_ALLOCATE_STRUCT(Client_Move);
00976
00977 if (!NewMove)
00978 GenVS_Error("Client_AddMove: Out of memory.\n");
00979
00980 *NewMove = *Move;
00981
00982 NewMove->Next = NULL;
00983
00984 Last = Client->LastMove;
00985
00986 if (!Last)
00987 Client->MoveStack = NewMove;
00988 else
00989 Last->Next = NewMove;
00990
00991 Client->LastMove = NewMove;
00992
00993 NumMoves++;
00994
00995 if (NumMoves >= 1000)
00996 GenVS_Error("NumMoves > 1000.\n");
00997 }
00998
00999
01000
01001
01002 Client_Move *Client_PeekMove(Client_Client *Client)
01003 {
01004 assert(Client_IsValid(Client) == GE_TRUE);
01005
01006 return Client->MoveStack;
01007 }
01008
01009
01010
01011
01012 void Client_RemoveFirstMove(Client_Client *Client)
01013 {
01014 Client_Move *Next;
01015
01016 assert(Client_IsValid(Client) == GE_TRUE);
01017
01018 NumMoves--;
01019
01020 if (NumMoves < 0)
01021 GenVS_Error("NumMove < 0.\n");
01022
01023 if (!Client->MoveStack)
01024 GenVS_Error("Client_RemoveFirstMove: No more moves left...");
01025
01026 Next = Client->MoveStack->Next;
01027
01028 geRam_Free(Client->MoveStack);
01029
01030 if (Next)
01031 Client->MoveStack = Next;
01032 else
01033 {
01034 Client->MoveStack = NULL;
01035 Client->LastMove = NULL;
01036 }
01037 }
01038
01039
01040
01041
01042 void Client_ValidateWeapon(Client_Client *Client)
01043 {
01044 int32 i;
01045
01046 assert(Client_IsValid(Client) == GE_TRUE);
01047
01048 for (i=0; i<5; i++)
01049 {
01050 geBoolean HasItem;
01051
01052 HasItem = (Client->Inventory[Client->CurrentWeapon] & (1<<15));
01053
01054 if (!HasItem && Client->CurrentWeapon != 0)
01055 {
01056 Client->CurrentWeapon++;
01057 Client->CurrentWeapon %= 4;
01058 continue;
01059 }
01060
01061 assert(Client->CurrentWeapon >= 0 && Client->CurrentWeapon <= 3);
01062
01063 return;
01064 }
01065
01066
01067 assert(!"No best weapon!!!");
01068 }
01069
01070
01071
01072
01073
01074 geBoolean Client_SendMove(Client_Client *Client, float Time)
01075 {
01076 Buffer_Data Buffer;
01077 uint8 Data[512];
01078 uint16 ButtonBits;
01079 HWND hWnd;
01080
01081 assert(Client_IsValid(Client) == GE_TRUE);
01082
01083 if (GMenu_IsAMenuActive() == GE_TRUE)
01084 return GE_TRUE;
01085
01086 hWnd = GameMgr_GethWnd(Client->GMgr);
01087
01088
01089
01090
01091 Buffer_Set(&Buffer, Data, 512);
01092
01093 ButtonBits = 0;
01094
01095
01096 if (IsKeyDown(KeyLut[VK_UP], hWnd))
01097 Client->ForwardSpeed = 4000.0f;
01098 else if (IsKeyDown(KeyLut[VK_DOWN], hWnd))
01099 Client->ForwardSpeed = -4000.0f;
01100 else
01101 Client->ForwardSpeed = 0.0f;
01102
01103 if (MouseInvert)
01104 Client->Angles.X -= GlobalMouseSpeedY;
01105 else
01106 Client->Angles.X += GlobalMouseSpeedY;
01107
01108 Client->Angles.Y += GlobalMouseSpeedX;
01109
01110 if (Client->Angles.X > 1.3f)
01111 Client->Angles.X = 1.3f;
01112 else if (Client->Angles.X < -1.3f)
01113 Client->Angles.X = -1.3f;
01114
01115 GlobalMouseSpeedX = 0.0f;
01116 GlobalMouseSpeedY = 0.0f;
01117
01118 if (IsKeyDown(KeyLut[VK_LEFT], hWnd))
01119 ButtonBits |= HOST_BUTTON_LEFT;
01120
01121 if (IsKeyDown(KeyLut[VK_RIGHT], hWnd))
01122 ButtonBits |= HOST_BUTTON_RIGHT;
01123
01124
01125 if (NewKeyDown(KeyLut[VK_RBUTTON], hWnd))
01126 ButtonBits |= HOST_BUTTON_JUMP;
01127
01128 if (IsKeyDown(KeyLut[VK_LBUTTON], hWnd))
01129 {
01130 ButtonBits |= HOST_BUTTON_FIRE;
01131 }
01132
01133 if (IsKeyDown('1', hWnd))
01134 {
01135 Client->CurrentWeapon = 0;
01136 }
01137 else if (IsKeyDown('2', hWnd))
01138 {
01139 Client->CurrentWeapon = 1;
01140 }
01141 else if (IsKeyDown('3', hWnd))
01142 {
01143 Client->CurrentWeapon = 2;
01144 }
01145 else if (IsKeyDown('4', hWnd))
01146 {
01147 Client->CurrentWeapon = 3;
01148 }
01149 else if (NewKeyDown(KeyLut[VK_CONTROL], hWnd))
01150 {
01151 Client->CurrentWeapon ++;
01152 Client->CurrentWeapon %= 4;
01153
01154 Client_ValidateWeapon(Client);
01155 }
01156
01157 Client->ButtonBits = ButtonBits;
01158
01159 Buffer_FillByte(&Buffer, NETMGR_MSG_CLIENT_MOVE);
01160 Buffer_FillFloat(&Buffer, Client->Time);
01161 Buffer_FillFloat(&Buffer, Client->ServerPingBack);
01162 Buffer_FillFloat(&Buffer, Client->ForwardSpeed);
01163 Buffer_FillFloat(&Buffer, Client->Angles.X);
01164 Buffer_FillFloat(&Buffer, Client->Angles.Y);
01165 Buffer_FillShort(&Buffer, ButtonBits);
01166
01167 if (ButtonBits & HOST_BUTTON_FIRE)
01168 {
01169 assert(Client->CurrentWeapon >= 0 && Client->CurrentWeapon <= 65535);
01170 Buffer_FillShort(&Buffer, (uint16)Client->CurrentWeapon);
01171 }
01172
01173 #ifdef CALC_ERROR
01174 if (Client->ClientPlayer >= 0)
01175 {
01176 GPlayer *Player;
01177
01178 Player = &Client->Players[Client->ClientPlayer];
01179 Buffer_FillAngle(&Buffer, Player->Pos);
01180 }
01181 else
01182 {
01183 geVec3d FakePos = {0.0f, 0.0f, 0.0f};
01184
01185 Buffer_FillAngle(&Buffer, FakePos);
01186 }
01187 #endif
01188
01189
01190 #if 1
01191 if (!NetMgr_SendServerMessage(Client->NMgr, &Buffer, GE_FALSE))
01192 GenVS_Error("Client_SendMove: NetMgr_SendServerMessage failed.\n");
01193 #else
01194 if (Client->Mode == ClientMode_Dumb)
01195 {
01196
01197 if (!NetMgr_SendServerMessage(Client->NMgr, &Buffer, GE_FALSE))
01198 GenVS_Error("Client_SendMove: NetMgr_SendServerMessage failed.\n");
01199 }
01200 else if (Client->Time >= Client->NextSend)
01201 {
01202 Buffer_FillBuffer(&SendBuffer, &Buffer);
01203
01204
01205 if (!NetMgr_SendServerMessage(Client->NMgr, &SendBuffer, GE_FALSE))
01206 GenVS_Error("Client_SendMove: NetMgr_SendServerMessage failed.\n");
01207
01208 Buffer_Set(&SendBuffer, SData, 5000);
01209
01210
01211
01212 Client->NextSend = Client->Time;
01213 }
01214 #endif
01215
01216
01217
01218 if (Client->Mode == ClientMode_Proxy && Client->ClientPlayer != -1)
01219 {
01220 Client_Move Move;
01221 GPlayer *Player;
01222
01223 Player = &Client->Players[Client->ClientPlayer];
01224
01225 Move.Time = Client->Time;
01226 Move.Delta = Time;
01227 Move.ForwardSpeed = Client->ForwardSpeed;
01228 Move.Pitch = Client->Angles.X;
01229 Move.Yaw = Client->Angles.Y;
01230 Move.Pos = Player->Pos;
01231 Move.ButtonBits = ButtonBits;
01232 Move.CurrentWeapon = Client->CurrentWeapon;
01233
01234 #ifdef PREDICT_CLIENT
01235
01236 Client_MoveClientLocally(Client, &Move);
01237
01238
01239
01240
01241
01242
01243 Client_AddMove(Client, &Move);
01244 #endif
01245 }
01246
01247 return GE_TRUE;
01248 }
01249
01250
01251
01252
01253 static geBoolean IsKeyDown(int KeyCode, HWND hWnd)
01254 {
01255
01256 if (GetAsyncKeyState(KeyCode) & 0x8000)
01257 return GE_TRUE;
01258
01259 return GE_FALSE;
01260 }
01261
01262
01263
01264
01265 geBoolean NewKeyDown(int KeyCode, HWND hWnd)
01266 {
01267
01268 if (GetAsyncKeyState(KeyCode) & 1)
01269 return GE_TRUE;
01270
01271 return GE_FALSE;
01272 }
01273
01274
01275
01276
01277 static void SetClientProxyPlayer(Client_Client *Client, int32 Player)
01278 {
01279 GPlayer *PPlayer;
01280
01281 assert(Client_IsValid(Client) == GE_TRUE);
01282
01283 if (Client->Mode != ClientMode_Proxy)
01284 return;
01285
01286 Client->ClientPlayer = Player;
01287
01288
01289 if (Client->Players[Player].Actor)
01290 {
01291 geWorld *World;
01292
01293 World = GameMgr_GetWorld(Client->GMgr);
01294
01295 assert(World);
01296
01297 geWorld_SetActorFlags(World, Client->Players[Player].Actor, GE_ACTOR_RENDER_MIRRORS|GE_ACTOR_COLLIDE);
01298 }
01299
01300 PPlayer = &Client->Players[Player];
01301
01302 PPlayer->Active = GE_TRUE;
01303
01304 PPlayer->Owner = NULL;
01305
01306 PPlayer->ClientHandle = Client->ClientIndex;
01307
01308
01309 PPlayer->GunOffset.X = 0.0f;
01310 PPlayer->GunOffset.Y = 130.0f;
01311 PPlayer->GunOffset.Z = 0.0f;
01312 }
01313
01314 geBoolean MHack = GE_TRUE;
01315
01316 int32 TotalMsgBytes;
01317 geBoolean NetPlayGetNumMessages(int32 *NumMsgSend, int32 *NumBytesSend, int32 *NumMsgRec, int32 *NumBytesRec);
01318
01319
01320
01321
01322
01323 static geBoolean ReadServerMessages(Client_Client *Client, GameMgr *GMgr, float Time)
01324 {
01325 uint8 Type;
01326 Buffer_Data Buffer;
01327
01328 assert(Client_IsValid(Client) == GE_TRUE);
01329
01330 MHack = GE_FALSE;
01331
01332 Client->ServerPingBack = -1.0f;
01333
01334
01335
01336 while (Client_ReadServerMessages(Client, &Buffer))
01337 {
01338 assert(Buffer.Size < NETMGR_LOCAL_MSG_BUFFER_SIZE);
01339 assert(Buffer.Size >= 0);
01340
01341 TotalMsgBytes += Buffer.Size;
01342
01343
01344 while (Buffer.Pos < Buffer.Size)
01345 {
01346
01347 Buffer_GetByte(&Buffer, &Type);
01348
01349
01350
01351 switch(Type)
01352 {
01353 case NETMGR_MSG_VERSION:
01354 {
01355 uint32 VersionMajor, VersionMinor;
01356
01357 Buffer_GetLong(&Buffer, &VersionMajor);
01358 Buffer_GetLong(&Buffer, &VersionMinor);
01359
01360 if (VersionMajor != NETMGR_VERSION_MAJOR || VersionMinor != NETMGR_VERSION_MINOR)
01361 GenVS_Error("Wrong Server Version: %i.%i", VersionMajor, VersionMinor);
01362
01363 break;
01364 }
01365
01366 case NETMGR_MSG_TIME:
01367 {
01368 Client->TempTime = 0.0f;
01369 Client->OldNetTime = Client->NetTime;
01370 Buffer_GetFloat(&Buffer, &Client->NetTime);
01371
01372 if (Client->NetTime >= Client->OldNetTime)
01373 Client->NetTimeGood = GE_TRUE;
01374 else
01375 Client->NetTimeGood = GE_FALSE;
01376
01377 Client->ServerPingBack = Client->NetTime;
01378
01379 Buffer_GetFloat(&Buffer, &Client->Ping);
01380
01381 break;
01382 }
01383
01384 case NETMGR_MSG_PLAYER_DATA:
01385 {
01386 if (Client->NetState != NetState_WorldActive)
01387 GenVS_Error("ReadServerMessages: Client->NetState != NetState_WorldActive\n");
01388
01389
01390 if (!Client->NetTimeGood || Client->NetState != NetState_WorldActive)
01391 ParsePlayerDataLocally(Client, &Buffer, GE_TRUE);
01392 else
01393 ParsePlayerDataLocally(Client, &Buffer, GE_FALSE);
01394
01395 break;
01396 }
01397
01398 case NETMGR_MSG_NEW_WORLD_PLAYER_DATA:
01399 {
01400 if (Client->NetState != NetState_WorldChange)
01401 GenVS_Error("ReadServerMessages: Client->NetState != NetState_WorldChange\n");
01402
01403 ParsePlayerDataLocally(Client, &Buffer, GE_FALSE);
01404 break;
01405 }
01406
01407 case NETMGR_MSG_VIEW_PLAYER:
01408 {
01409 uint16 Player;
01410 GPlayer *pPlayer;
01411 int32 OldViewPlayer;
01412
01413 Buffer_GetShort(&Buffer, &Player);
01414
01415 assert(Player != 0);
01416
01417
01418 OldViewPlayer = Client->ViewPlayer;
01419
01420 Client->ViewPlayer = (int32)Player;
01421
01422 if (OldViewPlayer != -1)
01423 {
01424 pPlayer = &Client->Players[OldViewPlayer];
01425
01426 if (pPlayer->Actor)
01427 {
01428 pPlayer->OldViewIndex2 = 0xffff;
01429 CheckClientPlayerChanges(Client, pPlayer, GE_FALSE);
01430 }
01431 }
01432
01433
01434 pPlayer = &Client->Players[Player];
01435
01436 if (pPlayer->Actor)
01437 {
01438 pPlayer->OldViewIndex2 = 0xffff;
01439 CheckClientPlayerChanges(Client, pPlayer, GE_FALSE);
01440 }
01441
01442
01443 break;
01444 }
01445
01446 case NETMGR_MSG_SET_WORLD:
01447 {
01448 char Name[256];
01449
01450 assert( Client->NetState == NetState_WorldChange);
01451
01452 Buffer_GetString(&Buffer, Name);
01453
01454 assert(Name[0]);
01455
01456 if (!Name[0])
01457 GenVS_Error("ReadServerMessages: No World Name!\n");
01458
01459 if (Client->Mode == ClientMode_Dumb)
01460 break;
01461
01462 Client_FreeResourcesForNewWorld(Client);
01463 Client_NewWorldDefaults(Client);
01464
01465 if (!GameMgr_SetWorld(GMgr, Name))
01466 GenVS_Error("ReadServerMessages: GameMgr_SetWorld failed.\n");
01467 break;
01468 }
01469
01470 case NETMGR_MSG_ACTOR_INDEX:
01471 {
01472 int32 ActorIndex;
01473 char ActorName[GAMEMGR_MAX_ACTOR_NAME];
01474
01475 Buffer_GetSLong(&Buffer, &ActorIndex);
01476 Buffer_GetString(&Buffer, ActorName);
01477
01478 if (Client->Mode == ClientMode_Dumb)
01479 break;
01480
01481 if (!GameMgr_SetActorIndex(GMgr, ActorIndex, ActorName))
01482 GenVS_Error("ReadServerMessages: GameMgr_SetActorIndex failed.\n");
01483
01484 break;
01485 }
01486
01487 case NETMGR_MSG_MOTION_INDEX:
01488 {
01489 GameMgr_MotionIndex MotionIndex;
01490 char MotionName[GAMEMGR_MAX_MOTION_NAME];
01491
01492 Buffer_GetSLong(&Buffer, &MotionIndex);
01493 Buffer_GetString(&Buffer, MotionName);
01494
01495 if (Client->Mode == ClientMode_Dumb)
01496 break;
01497
01498 if (!GameMgr_SetMotionIndexDef(Client->GMgr, MotionIndex, MotionName))
01499 GenVS_Error("ReadServerMessages: GameMgr_SetMotionIndexDef failed.\n");
01500
01501 break;
01502 }
01503
01504 case NETMGR_MSG_BONE_INDEX:
01505 {
01506 int32 BoneIndex;
01507 char BoneName[GAMEMGR_MAX_BONE_NAME];
01508
01509 Buffer_GetSLong(&Buffer, &BoneIndex);
01510 Buffer_GetString(&Buffer, BoneName);
01511
01512 if (Client->Mode == ClientMode_Dumb)
01513 break;
01514
01515 if (!GameMgr_SetBoneIndex(Client->GMgr, BoneIndex, BoneName))
01516 GenVS_Error("ReadServerMessages: GameMgr_SetBoneIndex failed.\n");
01517
01518 break;
01519 }
01520
01521 case NETMGR_MSG_TEXTURE_INDEX:
01522 {
01523 int32 Index;
01524 char FileName[256];
01525 char AFileName[256];
01526
01527 assert(Client->NetState == NetState_WorldChange);
01528
01529 Buffer_GetSLong(&Buffer, &Index);
01530 Buffer_GetString(&Buffer, FileName);
01531 Buffer_GetString(&Buffer, AFileName);
01532
01533 if (Client->Mode == ClientMode_Dumb)
01534 break;
01535
01536 if (!GameMgr_SetTextureIndex(Client->GMgr, Index, FileName, AFileName))
01537 GenVS_Error("ReadServerMessages: GameMgr_SetTextureIndex failed.\n");
01538
01539 break;
01540 }
01541
01542 case NETMGR_MSG_SOUND_INDEX:
01543 {
01544 int32 Index;
01545 char FileName[GAMEMGR_MAX_FILENAME];
01546
01547 Buffer_GetSLong(&Buffer, &Index);
01548 Buffer_GetString(&Buffer, FileName);
01549
01550 if (Client->Mode == ClientMode_Dumb)
01551 break;
01552
01553 if (!GameMgr_SetSoundIndex(Client->GMgr, Index, FileName))
01554 GenVS_Error("ReadServerMessages: GameMgr_SetSoundIndex failed.\n");
01555
01556 break;
01557 }
01558
01559 case NETMGR_MSG_CD_TRACK:
01560 {
01561 uint8 Track, Smin, Ssec, Emin, Esec;
01562
01563 Buffer_GetByte(&Buffer, &Track);
01564 Buffer_GetByte(&Buffer, &Smin);
01565 Buffer_GetByte(&Buffer, &Ssec);
01566 Buffer_GetByte(&Buffer, &Emin);
01567 Buffer_GetByte(&Buffer, &Esec);
01568
01569 Track = 1;
01570 Smin = 0;
01571 Ssec = 0;
01572 Emin = 2;
01573 Esec = 42;
01574
01575
01576 break;
01577 }
01578
01579 case NETMGR_MSG_PLAY_SOUND_INDEX:
01580 {
01581 uint16 SoundIndex;
01582 geVec3d Pos;
01583 geWorld *World;
01584 GameMgr_SoundIndex *pSoundIndex;
01585 geSound_System *SoundSys;
01586
01587 Buffer_GetShort(&Buffer, &SoundIndex);
01588 Buffer_GetPos(&Buffer, &Pos);
01589
01590 World = GameMgr_GetWorld(Client->GMgr);
01591
01592 if (!World)
01593 break;
01594
01595 SoundSys = GameMgr_GetSoundSystem(Client->GMgr);
01596
01597
01598 if (SoundSys)
01599 {
01600 pSoundIndex = GameMgr_GetSoundIndex(Client->GMgr, SoundIndex);
01601
01602 if (pSoundIndex->SoundDef)
01603 {
01604 float Vol, Pan, Freq;
01605
01606 geSound3D_GetConfig(World, &Client->ViewXForm, &Pos, 500.0f, 2.0f, &Vol, &Pan, &Freq);
01607 geSound_PlaySoundDef(SoundSys, pSoundIndex->SoundDef, Vol, Pan, Freq, GE_FALSE);
01608 }
01609 }
01610
01611 break;
01612 }
01613
01614 case NETMGR_MSG_CLIENT_INDEX:
01615 {
01616 uint8 ClientIndex;
01617 Buffer_GetByte(&Buffer, &ClientIndex);
01618
01619 if (ClientIndex >= NETMGR_MAX_CLIENTS)
01620 GenVS_Error("ReadServerMessages: Bad client index number.\n");
01621
01622 Client->ClientIndex = (int32)ClientIndex;
01623
01624 break;
01625 }
01626
01627 case NETMGR_MSG_CLIENT_ACTIVE:
01628 {
01629 uint8 ClientIndex, Active;
01630 Buffer_GetByte(&Buffer, &ClientIndex);
01631
01632 if (ClientIndex >= NETMGR_MAX_CLIENTS)
01633 GenVS_Error("ReadServerMessages: Bad client index number.\n");
01634
01635 Buffer_GetByte(&Buffer, &Active);
01636
01637 Client->ClientInfo[ClientIndex].Active = (geBoolean)Active;
01638 break;
01639 }
01640
01641 case NETMGR_MSG_CLIENT_NAME:
01642 {
01643 uint8 ClientIndex;
01644 Buffer_GetByte(&Buffer, &ClientIndex);
01645
01646 if (ClientIndex >= NETMGR_MAX_CLIENTS)
01647 GenVS_Error("ReadServerMessages: Bad client index number.\n");
01648
01649 Buffer_GetString(&Buffer, Client->ClientInfo[ClientIndex].Name);
01650 break;
01651 }
01652
01653 case NETMGR_MSG_CLIENT_SCORE:
01654 {
01655 uint8 ClientIndex;
01656 Buffer_GetByte(&Buffer, &ClientIndex);
01657
01658 if (ClientIndex >= NETMGR_MAX_CLIENTS)
01659 GenVS_Error("ReadServerMessages: Bad client index number.\n");
01660
01661 Buffer_GetSLong(&Buffer, &Client->ClientInfo[ClientIndex].Score);
01662 break;
01663 }
01664
01665 case NETMGR_MSG_CLIENT_HEALTH:
01666 {
01667 uint8 ClientIndex;
01668 Buffer_GetByte(&Buffer, &ClientIndex);
01669
01670 if (ClientIndex >= NETMGR_MAX_CLIENTS)
01671 GenVS_Error("ReadServerMessages: Bad client index number.\n");
01672
01673 Buffer_GetSLong(&Buffer, &Client->ClientInfo[ClientIndex].Health);
01674 break;
01675 }
01676
01677 case NETMGR_MSG_CLIENT_INVENTORY:
01678 {
01679 uint8 ClientIndex, Slot;
01680 uint16 Val;
01681 Buffer_GetByte(&Buffer, &ClientIndex);
01682
01683 if (ClientIndex >= NETMGR_MAX_CLIENTS)
01684 GenVS_Error("ReadServerMessages: Bad client index number.\n");
01685
01686 Buffer_GetByte(&Buffer, &Slot);
01687 Buffer_GetShort(&Buffer, &Val);
01688 Client->Inventory[Slot] = Val;
01689
01690 if (Client->ClientPlayer != -1)
01691 {
01692 GPlayer *Player;
01693 int32 Ammo;
01694 geBoolean HasItem;
01695
01696 Player = &Client->Players[Client->ClientPlayer];
01697
01698 Ammo = Client->Inventory[Slot];
01699
01700 HasItem = (Val & (1<<15))>>15;
01701 Val &= 0xff;
01702
01703 Player->Inventory[Slot] = Val;
01704 Player->InventoryHas[Slot] = HasItem;
01705 }
01706
01707 break;
01708 }
01709
01710 case NETMGR_MSG_CLIENT_WEAPON:
01711 {
01712 uint8 ClientIndex;
01713
01714 Buffer_GetByte(&Buffer, &ClientIndex);
01715
01716 if (ClientIndex >= NETMGR_MAX_CLIENTS)
01717 GenVS_Error("ReadServerMessages: Bad client index number.\n");
01718
01719 Buffer_GetShort(&Buffer, &Client->CurrentWeapon);
01720 break;
01721 }
01722
01723 case NETMGR_MSG_SPAWN_FX:
01724 {
01725 uint8 Type, Sound;
01726 geVec3d Pos;
01727 geWorld *World;
01728 geSound_System *SoundSys;
01729 GameMgr_SoundIndex *pSoundIndex;
01730
01731 Buffer_GetPos(&Buffer, &Pos);
01732 Buffer_GetByte(&Buffer, &Type);
01733 Buffer_GetByte(&Buffer, &Sound);
01734
01735 World = GameMgr_GetWorld(Client->GMgr);
01736 if (!World)
01737 break;
01738
01739 if (!Fx_SpawnFx(GameMgr_GetFxSystem(Client->GMgr), &Pos, Type))
01740 GenVS_Error("[CLIENT] ReadServerMessages: Could not spawn fx: %i.\n", Type);
01741
01742 if (Sound == 255)
01743 break;
01744
01745 SoundSys = GameMgr_GetSoundSystem(Client->GMgr);
01746
01747 if (SoundSys)
01748 {
01749 pSoundIndex = GameMgr_GetSoundIndex(Client->GMgr, Sound);
01750
01751 if (pSoundIndex->SoundDef)
01752 {
01753 float Vol, Pan, Freq;
01754
01755 assert(pSoundIndex->Active == GE_TRUE);
01756
01757 geSound3D_GetConfig(World, &Client->ViewXForm, &Pos, 500.0f, 2.0f, &Vol, &Pan, &Freq);
01758 geSound_PlaySoundDef(SoundSys, pSoundIndex->SoundDef, Vol, Pan, Freq, GE_FALSE);
01759 }
01760 }
01761
01762 break;
01763 }
01764
01765
01766 case NETMGR_MSG_HEADER_PRINTF:
01767 {
01768 char Str[256];
01769
01770 Buffer_GetString(&Buffer, Str);
01771
01772 Console_HeaderPrintf(GameMgr_GetConsole(Client->GMgr), Str);
01773
01774 break;
01775 }
01776
01777 case NETMGR_MSG_CLIENT_PLAYER_INDEX:
01778 {
01779 int32 PlayerIndex;
01780
01781 Buffer_GetSLong(&Buffer, &PlayerIndex);
01782
01783 SetClientProxyPlayer(Client, PlayerIndex);
01784 break;
01785 }
01786
01787 case NETMGR_MSG_NET_STATE_CHANGE:
01788 {
01789 NetMgr_NetState NetState;
01790
01791 Buffer_GetSLong(&Buffer, &NetState);
01792
01793 if (!Client_ChangeNetState(Client, NetState))
01794 GenVS_Error("ReadServerMessages: Client_ChangeNetState failed.\n");
01795
01796 break;
01797 }
01798
01799 case NETMGR_MSG_SHUTDOWN:
01800 {
01801 GenVS_Error("Lost connection with server!!!");
01802 }
01803
01804 default:
01805 {
01806 GenVS_Error("Unknown message from server: %i\n", Type);
01807 }
01808 }
01809 }
01810
01811
01812 if (Client->Demo.Mode == CLIENT_DEMO_PLAY && !Client->Demo.OriginalSpeed)
01813 break;
01814 }
01815
01816
01817 UpdatePlayers(Client, Time);
01818
01819 #if 0
01820 {
01821
01822
01823
01824
01825
01826
01827
01828 geEngine_Printf(GameMgr_GetEngine(Client->GMgr), 2, 400, "Bytes Received: %i", TotalMsgBytes);
01829 }
01830 #endif
01831
01832 return GE_TRUE;
01833 }
01834
01835
01836
01837
01838
01839
01840 static void UpdateProxyPlayer(Client_Client *Client, GPlayer *Player)
01841 {
01842 int32 PlayerIndex;
01843 geXForm3d XForm;
01844 GPlayer *Player2;
01845 int32 i;
01846
01847 assert(Client_IsValid(Client) == GE_TRUE);
01848
01849 PlayerIndex = (int32)(Player - Client->Players);
01850
01851
01852 Client_UpdateSinglePlayer(Client, Player, 1.0f, 1.0f, GE_FALSE);
01853
01854
01855 if (PlayerIndex == Client->ClientPlayer)
01856 {
01857 Client_Move *Move, *CMove;
01858 int32 NumMoves2;
01859
01860 MHack = GE_TRUE;
01861
01862 geXForm3d_SetEulerAngles(&XForm, &Player->Angles);
01863 XForm.Translation = Player->Pos;
01864 Player->LastGoodPos = Player->Pos;
01865
01866 Player->XForm = XForm;
01867
01868
01869
01870
01871 LastPlayer = PlayerIndex;
01872
01873 Move = Client_PeekMove(Client);
01874
01875
01876
01877
01878 for (Move = Client_PeekMove(Client); Move; Move = Client_PeekMove(Client))
01879 {
01880 if (Move->Time > Player->SpawnTime)
01881 break;
01882
01883 Client_RemoveFirstMove(Client);
01884 }
01885
01886 NumMoves2 = 0;
01887
01888
01889 for (CMove = Move; CMove; CMove = CMove->Next)
01890 {
01891 NumMoves2++;
01892
01893 Client_MoveClientLocally(Client, CMove);
01894 }
01895
01896
01897 Player2 = Client->TempPlayers;
01898
01899 for (i=0; i< CLIENT_MAX_TEMP_PLAYERS; i++, Player2++)
01900 {
01901 if (!Player2->Active)
01902 continue;
01903
01904 if (Player->SpawnTime < Player2->SpawnTime)
01905 continue;
01906
01907 Client_DestroyTempPlayer(Client, Player2);
01908 }
01909
01910 }
01911 }
01912
01913 #define CLIENT_POLY_FLAGS (GE_RENDER_DEPTH_SORT_BF)
01914
01915
01916
01917
01918
01919
01920
01921 static geBoolean CheckClientPlayerChanges(Client_Client *Client, GPlayer *Player, geBoolean TempPlayer)
01922 {
01923 int32 ViewFlags;
01924 int32 ViewIndex;
01925 int32 PlayerIndex;
01926 geVec3d PlayerPos;
01927 geWorld *World;
01928
01929 assert(Client_IsValid(Client) == GE_TRUE);
01930
01931 World = GameMgr_GetWorld(Client->GMgr);
01932 assert(World);
01933
01934 if (TempPlayer)
01935 PlayerIndex = CLIENT_TEMP_GPLAYER_TO_INDEX(Client, Player);
01936 else
01937 PlayerIndex = CLIENT_GPLAYER_TO_INDEX(Client, Player);
01938
01939 ViewFlags = Player->ViewFlags;
01940 ViewIndex = Player->ViewIndex;
01941
01942 PlayerPos = Player->Pos;
01943
01944 if (ViewFlags & VIEW_TYPE_ACTOR)
01945 {
01946 if (ViewIndex == 0xffff)
01947 {
01948 if (Player->Actor)
01949 {
01950 geWorld_RemoveActor(World, Player->Actor);
01951 geActor_Destroy(&Player->Actor);
01952 Player->Actor = NULL;
01953 }
01954 }
01955 else if (Player->OldViewIndex2 != ViewIndex)
01956 {
01957 geActor_Def *ActorDef;
01958 GameMgr_ActorIndex *ActorIndex;
01959 geVec3d Normal = {0.0f, 1.0f, 0.0f};
01960 geVec3d Mins;
01961 geVec3d Maxs;
01962 geExtBox ExtBox;
01963 geVec3d NullVec = {0.0f, 0.0f, 0.0f};
01964
01965 ActorIndex = GameMgr_GetActorIndex(Client->GMgr, ViewIndex);
01966
01967 assert(ActorIndex->Active == GE_TRUE);
01968
01969 ActorDef = ActorIndex->ActorDef;
01970
01971 assert(ActorDef);
01972
01973 if (Player->Actor)
01974 {
01975 geWorld_RemoveActor(World, Player->Actor);
01976 geActor_Destroy(&Player->Actor);
01977 Player->Actor = NULL;
01978 }
01979
01980 Mins = Player->Mins;
01981 Maxs = Player->Maxs;
01982
01983 assert(geVec3d_Compare(&Mins, &NullVec, 0.01f) == GE_FALSE);
01984 assert(geVec3d_Compare(&Maxs, &NullVec, 0.01f) == GE_FALSE);
01985
01986 Player->Actor = geActor_Create(ActorDef);
01987
01988 if (!Player->Actor)
01989 GenVS_Error("[CLIENT] CheckClientPlayerChanges: Could not create actor. ActorDef Name: %s.\n", ActorIndex->FileName);
01990
01991 if (Client->ViewPlayer == PlayerIndex && !TempPlayer)
01992 {
01993 if (geWorld_AddActor(World, Player->Actor, GE_ACTOR_RENDER_MIRRORS|GE_ACTOR_COLLIDE, 0xffffffff) == GE_FALSE)
01994 GenVS_Error("[CLIENT] CheckClientPlayerChanges: Could not add actor to world. ActorDef Name: %s.\n", ActorIndex->FileName);
01995 }
01996 else
01997 {
01998 if (geWorld_AddActor(World, Player->Actor, GE_ACTOR_RENDER_NORMAL|GE_ACTOR_COLLIDE, 0xffffffff) == GE_FALSE)
01999 GenVS_Error("[CLIENT] CheckClientPlayerChanges: Could not add actor to world. ActorDef Name: %s.\n", ActorIndex->FileName);
02000 }
02001
02002 geActor_SetScale(Player->Actor, Player->Scale, Player->Scale, Player->Scale);
02003
02004 ExtBox.Min = Mins;
02005 ExtBox.Max = Maxs;
02006
02007 if (!geActor_SetRenderHintExtBox(Player->Actor, &ExtBox, NULL))
02008 GenVS_Error("[CLIENT] CheckClientPlayerChanges: Set actor HintBox failed.\n");
02009
02010 if (!geActor_SetExtBox(Player->Actor, &ExtBox, NULL))
02011 GenVS_Error("[CLIENT] CheckClientPlayerChanges: Set actor AABox failed.\n");
02012
02013 if (Client->ViewPlayer == PlayerIndex && !TempPlayer)
02014 {
02015 if (!geActor_SetShadow(Player->Actor, GE_TRUE, 100.0f, GameMgr_GetShadowMap(Client->GMgr), NULL))
02016 GenVS_Error("[CLIENT] CheckClientPlayerChanges: Could not set actor shadow. ActorDef Name: %s.\n", ActorIndex->FileName);
02017 }
02018
02019 if (!geActor_SetLightingOptions(Player->Actor, GE_TRUE, &Normal, 155.0f, 155.0f, 155.0f, 1.0f, 1.0f, 1.0f, GE_TRUE, 3, NULL, GE_FALSE))
02020 GenVS_Error("[CLIENT] CheckClientPlayerChanges: Could not set actor lighting options. ActorDef Name: %s.\n", ActorIndex->FileName);
02021
02022 geActor_SetUserData(Player->Actor, Player);
02023
02024 Player->ActorDef = ActorDef;
02025
02026
02027 }
02028 }
02029 else if (ViewFlags & VIEW_TYPE_MODEL)
02030 {
02031 if (ViewIndex == 0xffff)
02032 Player->Model = NULL;
02033 else
02034 Player->Model = GameMgr_GetModel(Client->GMgr, ViewIndex);
02035
02036 if (Player->Model)
02037 {
02038 if (Player->ViewFlags & VIEW_TYPE_MODEL_OPEN)
02039 geWorld_OpenModel(World, Player->Model, GE_TRUE);
02040 else
02041 geWorld_OpenModel(World, Player->Model, GE_FALSE);
02042
02043 if (Client->Mode == ClientMode_Proxy)
02044 {
02045 geWorld_ModelSetUserData(Player->Model, Player);
02046 }
02047 }
02048 }
02049 else if (ViewFlags & VIEW_TYPE_SPRITE)
02050 {
02051 if (ViewIndex == 0xffff)
02052 {
02053 if (Player->Poly)
02054 {
02055 geWorld_RemovePoly(World, Player->Poly);
02056 Player->Poly = NULL;
02057 }
02058 }
02059
02060 else if (Player->OldViewIndex2 != ViewIndex || Player->OldScale2 != Player->Scale)
02061 {
02062 geBitmap *Bitmap;
02063 GE_LVertex Vert;
02064 GameMgr_TextureIndex *TextureIndex;
02065
02066 TextureIndex = GameMgr_GetTextureIndex(Client->GMgr, ViewIndex);
02067
02068 Bitmap = TextureIndex->TextureDef;
02069
02070 assert(Bitmap);
02071
02072 if (Bitmap)
02073 {
02074 geVec3d Pos = Player->Pos;
02075
02076 if (Player->Poly)
02077 geWorld_RemovePoly(World, Player->Poly);
02078
02079 Vert.X = Pos.X;
02080 Vert.Y = Pos.Y;
02081 Vert.Z = Pos.Z;
02082 Vert.u = 0.0f;
02083 Vert.v = 0.0f;
02084 Vert.r = Vert.g = Vert.b = Vert.a = 255.0f;
02085
02086 Player->Poly =
02087 geWorld_AddPoly(World, &Vert, 1, Bitmap, GE_TEXTURED_POINT,
02088 CLIENT_POLY_FLAGS, Player->Scale * EffectScale);
02089
02090 assert(Player->Poly);
02091 }
02092 }
02093 }
02094
02095
02096 if (ViewFlags & VIEW_TYPE_LIGHT)
02097 {
02098 if (!Player->Light)
02099 {
02100
02101 Player->Light = geWorld_AddLight(World);
02102
02103
02104
02105 }
02106 }
02107 else if (Player->Light)
02108 {
02109 geWorld_RemoveLight(World, Player->Light);
02110 Player->Light = NULL;
02111 }
02112
02113
02114 Player->OldViewFlags2 = Player->ViewFlags;
02115 Player->OldViewIndex2 = Player->ViewIndex;
02116 Player->OldScale2 = Player->Scale;
02117
02118 return GE_TRUE;
02119 }
02120
02121
02122
02123
02124 void BuildXForm(geXForm3d *XForm, const geVec3d *Angles)
02125 {
02126 geVec3d Pos;
02127
02128 Pos = XForm->Translation;
02129
02130
02131 geXForm3d_SetIdentity(XForm);
02132
02133
02134 geXForm3d_RotateZ(XForm, Angles->Z);
02135
02136 geXForm3d_RotateX(XForm, Angles->X);
02137 geXForm3d_RotateY(XForm, Angles->Y);
02138
02139 geXForm3d_Translate(XForm, Pos.X, Pos.Y, Pos.Z);
02140
02141 }
02142
02143
02144
02145
02146
02147
02148
02149 static void BuildClientViewXForm(Client_Client *Client)
02150 {
02151 geVec3d Pos;
02152 GPlayer *Player;
02153
02154 assert(Client_IsValid(Client) == GE_TRUE);
02155
02156 assert(Client->ViewPlayer >= 0 && Client->ViewPlayer < NETMGR_MAX_PLAYERS);
02157
02158 Player = &Client->Players[Client->ViewPlayer];
02159
02160 Client->ViewXForm = Player->XForm;
02161
02162 if (Client->Demo.Mode != CLIENT_DEMO_PLAY && !(Player->ViewFlags & VIEW_TYPE_FORCE_XFORM))
02163 {
02164 Pos = Client->ViewXForm.Translation;
02165
02166
02167 geXForm3d_SetIdentity(&Client->ViewXForm);
02168
02169
02170 geXForm3d_RotateZ(&Client->ViewXForm, Client->Angles.Z);
02171
02172 geXForm3d_RotateX(&Client->ViewXForm, Client->Angles.X);
02173 geXForm3d_RotateY(&Client->ViewXForm, Client->Angles.Y);
02174
02175 geXForm3d_Translate(&Client->ViewXForm, Pos.X, Pos.Y, Pos.Z);
02176 }
02177
02178
02179
02180 Client->ViewXForm.Translation.Y += 140.0f;
02181 }
02182
02183
02184
02185
02186 geBoolean Client_UpdateSinglePlayer(Client_Client *Client, GPlayer *Player, float Ratio, float Time, geBoolean TempPlayer)
02187 {
02188 geXForm3d XForm;
02189 geWorld *World;
02190
02191 assert(Client_IsValid(Client) == GE_TRUE);
02192
02193 World = GameMgr_GetWorld(Client->GMgr);
02194
02195
02196
02197 if (!World)
02198 return GE_TRUE;
02199
02200
02201
02202
02203
02204 geXForm3d_SetEulerAngles(&XForm, &Player->Angles);
02205 XForm.Translation = Player->Pos;
02206
02207
02208 Player->XForm = XForm;
02209
02210
02211 CheckClientPlayerChanges(Client, Player, TempPlayer);
02212
02213
02214 if (Player->Light)
02215 {
02216 GE_RGBA RGBA = {255.0f, 55.0f, 15.0f, 255.0f};
02217 geWorld_SetLightAttributes(World, Player->Light,
02218 &Player->Pos, &RGBA, 320.0f, GE_FALSE);
02219 }
02220
02221 if (Player->Mesh)
02222 {
02223 geXForm3d TXForm;
02224 geVec3d In, Up, Lf, Pos;
02225
02226 Pos = Player->XForm.Translation;
02227
02228 if (Player->ViewFlags & VIEW_TYPE_YAW_ONLY)
02229 {
02230 geVec3d_Set(&Up, 0.0f, 1.0f, 0.0f);
02231
02232 geXForm3d_GetIn(&Player->XForm, &In);
02233 geXForm3d_GetLeft(&Player->XForm, &Lf);
02234
02235 geVec3d_CrossProduct(&In, &Up, &Lf);
02236 geVec3d_CrossProduct(&Lf, &Up, &In);
02237
02238 geVec3d_Normalize(&Lf);
02239 geVec3d_Normalize(&In);
02240
02241 geXForm3d_SetFromLeftUpIn(&TXForm, &Lf, &Up, &In);
02242 }
02243 else
02244 {
02245 TXForm = Player->XForm;
02246 }
02247
02248 TXForm.Translation = Pos;
02249
02250 #if 0
02251 geWorld_SetMeshXForm(World, Player->Mesh, &TXForm);
02252 geWorld_SetMeshFrame(World, Player->Mesh, (int32)Player->FrameTime);
02253 #endif
02254 }
02255
02256 if (Player->Actor)
02257 {
02258 geXForm3d XForm;
02259 geVec3d In, Up, Lf, Pos;
02260 geMotion *Motion;
02261 char *MotionName;
02262 GameMgr_MotionIndexDef *MotionIndex;
02263
02264 assert((Player->ViewFlags & VIEW_TYPE_ACTOR));
02265
02266 Pos = Player->XForm.Translation;
02267
02268 if (Player->ViewFlags & VIEW_TYPE_YAW_ONLY)
02269 {
02270 geVec3d_Set(&Up, 0.0f, 1.0f, 0.0f);
02271
02272 geXForm3d_GetIn(&Player->XForm, &In);
02273 geXForm3d_GetLeft(&Player->XForm, &Lf);
02274
02275 geVec3d_CrossProduct(&In, &Up, &Lf);
02276 geVec3d_CrossProduct(&Lf, &Up, &In);
02277
02278 geVec3d_Normalize(&Lf);
02279 geVec3d_Normalize(&In);
02280
02281 geXForm3d_SetFromLeftUpIn(&XForm, &Lf, &Up, &In);
02282 }
02283 else
02284 {
02285 XForm = Player->XForm;
02286 }
02287
02288 if (Player->ViewFlags & VIEW_TYPE_ACTOR)
02289 {
02290
02291 geXForm3d RXForm;
02292 geXForm3d_SetXRotation(&RXForm, -(3.14159f/2.0f));
02293 geXForm3d_Multiply(&XForm, &RXForm, &XForm);
02294 }
02295
02296 XForm.Translation = Pos;
02297
02298 if (Player->MotionIndex == GAMEMGR_MOTION_INDEX_NONE)
02299 {
02300 if (!geActor_SetBoneAttachment(Player->Actor, NULL, &XForm))
02301 {
02302 GenVS_Error("Client_UpdateSinglePlayer: geActor_SetBoneAttachment failed...");
02303 }
02304 }
02305 else
02306 {
02307 MotionIndex = GameMgr_GetMotionIndexDef(Client->GMgr, Player->MotionIndex);
02308
02309 assert(MotionIndex);
02310 assert(MotionIndex->Active == GE_TRUE);
02311
02312
02313 if (MotionIndex->Active)
02314 {
02315 float FrameTime;
02316
02317 if (Player->FrameTime > Player->OldFrameTime)
02318 FrameTime = Player->OldFrameTime + (Player->FrameTime - Player->OldFrameTime) * Ratio;
02319 else
02320 FrameTime = Player->FrameTime;
02321
02322 MotionName = MotionIndex->MotionName;
02323
02324 Motion = geActor_GetMotionByName(Player->ActorDef, MotionName);
02325
02326 if (!Motion)
02327 GenVS_Error("Client_UpdateSinglePlayer: geActor_GetMotionByName1 failed...");
02328
02329 geActor_SetPose(Player->Actor, Motion, FrameTime, &XForm);
02330 }
02331 }
02332
02333
02334 {
02335 int32 i;
02336 GPlayer_MotionData *pMotionData;
02337
02338 pMotionData = Player->MotionData;
02339
02340 for (i=0; i< Player->NumMotionData; i++, pMotionData++)
02341 {
02342 MotionIndex = GameMgr_GetMotionIndexDef(Client->GMgr, pMotionData->MotionIndex);
02343
02344 assert(MotionIndex->Active == GE_TRUE);
02345
02346 if (!MotionIndex->Active)
02347 continue;
02348
02349 Motion = geActor_GetMotionByName(Player->ActorDef, MotionIndex->MotionName);
02350
02351 if (!Motion)
02352 GenVS_Error("Client_UpdateSinglePlayer: geActor_GetMotionByName2 failed...");
02353
02354 geActor_BlendPose(Player->Actor, Motion, pMotionData->MotionTime, &XForm, 1.0f);
02355 }
02356 }
02357
02358
02359 {
02360 int32 i;
02361 GPlayer_XFormData *pXFormData;
02362 GameMgr_BoneIndex *pBoneIndex;
02363 geXForm3d BoneXForm;
02364
02365 pXFormData = Player->XFormData;
02366
02367 for (i=0; i< Player->NumXFormData; i++, pXFormData++)
02368 {
02369 pBoneIndex = GameMgr_GetBoneIndex(Client->GMgr, pXFormData->BoneIndex);
02370
02371 assert(pBoneIndex->Active == GE_TRUE);
02372
02373 if (!pBoneIndex->Active)
02374 continue;
02375
02376 geActor_GetBoneAttachment(Player->Actor, pBoneIndex->BoneName, &BoneXForm);
02377
02378 pXFormData->XForm.Translation = BoneXForm.Translation;
02379
02380 geActor_SetBoneAttachment(Player->Actor, pBoneIndex->BoneName, &pXFormData->XForm);
02381 }
02382 }
02383
02384 }
02385
02386 if (Player->Model)
02387 {
02388 geWorld_SetModelXForm(World, Player->Model, &XForm);
02389 }
02390
02391 if (Player->Poly && Player->ViewFlags & VIEW_TYPE_SPRITE)
02392 {
02393 GE_LVertex Vert;
02394
02395 Vert.X = Player->Pos.X;
02396 Vert.Y = Player->Pos.Y;
02397 Vert.Z = Player->Pos.Z;
02398 Vert.u = 0.0f;
02399 Vert.v = 0.0f;
02400 Vert.r = Vert.a = 255.0f;
02401 Vert.g = Vert.b = 255.0f;
02402
02403 gePoly_SetLVertex(Player->Poly, 0, &Vert);
02404 }
02405
02406
02407 if (TempPlayer)
02408 {
02409 if (!Fx_PlayerFrame(GameMgr_GetFxSystem(Client->GMgr), TEMP_PLAYER_TO_FXPLAYER(Client, Player), &Player->XForm, Time))
02410 GenVS_Error("[CLIENT] UpdateSinglePlayer: Could not run Fx_Player frame.\n");
02411 }
02412 else
02413 {
02414 if (!Fx_PlayerFrame(GameMgr_GetFxSystem(Client->GMgr), PLAYER_TO_FXPLAYER(Client, Player), &Player->XForm, Time))
02415 GenVS_Error("[CLIENT] UpdateSinglePlayer: Could not run Fx_Player frame.\n");
02416 }
02417
02418 return GE_TRUE;
02419 }
02420
02421 static void *g_ProcIndex[CLIENT_MAX_PROC_INDEX];
02422
02423
02424
02425
02426 void *Client_GetProcIndex(Client_Client *Client, uint16 Index)
02427 {
02428 assert(Client_IsValid(Client) == GE_TRUE);
02429
02430 if (Index == CONTROL_INDEX_NONE)
02431 return NULL;
02432
02433 assert( Index >= 0 );
02434 assert( Index < CLIENT_MAX_PROC_INDEX );
02435
02436 return Client->ProcIndex[Index];
02437 }
02438
02439
02440
02441
02442 static void UpdatePlayers(Client_Client *Client, float Time)
02443 {
02444 int32 i;
02445 GPlayer *Player;
02446 float Ratio, Delta;
02447 geWorld *World;
02448
02449 assert(Client_IsValid(Client) == GE_TRUE);
02450
02451 World = GameMgr_GetWorld(Client->GMgr);
02452
02453 if (!World)
02454 return;
02455
02456 if (Client->ViewPlayer == -1)
02457 return;
02458
02459
02460 Delta = Client->NetTime - Client->OldNetTime;
02461
02462
02463 if (Delta <= 0.0f)
02464 Ratio = 1.0f;
02465 else
02466 Ratio = Client->TempTime / Delta;
02467
02468 if (Ratio < 0.0f)
02469 Ratio = 0.0f;
02470 else if (Ratio > 1.0f)
02471 Ratio = 1.0f;
02472
02473
02474 Client->TempTime += Time;
02475
02476 for (i=0; i< NETMGR_MAX_PLAYERS; i++)
02477 {
02478 Player = &Client->Players[i];
02479
02480
02481
02482 if (Player->UpdateTime != Client->NetTime)
02483 {
02484
02485 if (!Fx_PlayerSetFxFlags(GameMgr_GetFxSystem(Client->GMgr), PLAYER_TO_FXPLAYER(Client, Player), 0))
02486 GenVS_Error("[CLIENT] UpdatePlayers: Could not set Fx_Player flags.\n");
02487
02488 if (Player->Actor)
02489 {
02490 geWorld_RemoveActor(World, Player->Actor);
02491 geActor_Destroy(&Player->Actor);
02492 }
02493
02494 if (Player->Light)
02495 geWorld_RemoveLight(World, Player->Light);
02496
02497 if (Player->Poly)
02498 geWorld_RemovePoly(World, Player->Poly);
02499
02500
02501 memset(Player, 0, sizeof(GPlayer));
02502
02503
02504 SetPlayerDefaults(Player);
02505 continue;
02506 }
02507
02508 Client_UpdateSinglePlayer(Client, Player, 1.0f, Time, GE_FALSE);
02509
02510 #if 1
02511 Player->Control = Client_GetProcIndex(Client, Player->ControlIndex);
02512
02513
02514 if ( (Client->Demo.Mode != CLIENT_DEMO_PLAY)
02515 && (Client->Mode == ClientMode_Proxy)
02516 && (i != Client->ClientPlayer)
02517 && (Player->Control) )
02518 {
02519 Player->Control(&Client->GenVSI, Player, Time);
02520 Player->Pos = Player->XForm.Translation;
02521 }
02522 #endif
02523
02524
02525 }
02526
02527
02528 BuildClientViewXForm(Client);
02529 }
02530
02531
02532
02533
02534
02535 GPlayer *Client_ParsePlayerData(Client_Client *Client, Buffer_Data *Buffer, GPlayer *AuxPlayer)
02536 {
02537 uint16 PlayerIndex;
02538 uint16 SendFlags, PlayerIndexFlags;
02539 GPlayer *pPlayer;
02540
02541 assert(Client_IsValid(Client) == GE_TRUE);
02542
02543 Buffer_GetShort(Buffer, &PlayerIndex);
02544
02545 PlayerIndexFlags = (uint16)(PlayerIndex & (1<<15));
02546 PlayerIndex &= (uint16)0x7FFF;
02547
02548 if (AuxPlayer)
02549 pPlayer = AuxPlayer;
02550 else
02551 pPlayer = &Client->Players[PlayerIndex];
02552
02553 pPlayer->Active = GE_TRUE;
02554
02555 pPlayer->UpdateTime = Client->NetTime;
02556
02557 if (!(PlayerIndexFlags & (1<<15)) )
02558 {
02559
02560 pPlayer->SpawnTime = pPlayer->OldSpawnTime;
02561 pPlayer->ViewFlags = pPlayer->OldViewFlags;
02562 pPlayer->ViewIndex = pPlayer->OldViewIndex;
02563 pPlayer->MotionIndex = pPlayer->OldMotionIndex;
02564 pPlayer->FxFlags = pPlayer->OldFxFlags;
02565
02566 if (!AuxPlayer)
02567 {
02568 if (!Fx_PlayerSetFxFlags(GameMgr_GetFxSystem(Client->GMgr), PLAYER_TO_FXPLAYER(Client, pPlayer), pPlayer->FxFlags))
02569 GenVS_Error("Client_ParsePlayerData: Fx_PlayerSetFxFlags failed.\n");
02570 }
02571
02572 pPlayer->Pos = pPlayer->OldPos;
02573 pPlayer->Angles = pPlayer->OldAngles;
02574 pPlayer->FrameTime = pPlayer->OldFrameTime;
02575 pPlayer->Scale = pPlayer->OldScale;
02576 pPlayer->Velocity = pPlayer->OldVelocity;
02577 pPlayer->State = pPlayer->OldState;
02578 pPlayer->ControlIndex = pPlayer->OldControlIndex;
02579 pPlayer->TriggerIndex = pPlayer->OldTriggerIndex;
02580 pPlayer->Mins = pPlayer->OldMins;
02581 pPlayer->Maxs = pPlayer->OldMaxs;
02582
02583 if (Client->Mode == ClientMode_Proxy)
02584 {
02585
02586 if (pPlayer->ControlIndex == 0xffff)
02587 pPlayer->Control = NULL;
02588 else
02589 pPlayer->Control = Client->ProcIndex[pPlayer->ControlIndex];
02590
02591
02592 if (pPlayer->TriggerIndex == 0xffff)
02593 pPlayer->Trigger = NULL;
02594 else
02595 {
02596 pPlayer->Trigger = Client->ProcIndex[pPlayer->TriggerIndex];
02597 }
02598 }
02599
02600 return pPlayer;
02601 }
02602
02603
02604
02605
02606 Buffer_GetShort(Buffer, &SendFlags);
02607
02608
02609 if (SendFlags & NETMGR_SEND_SPAWN_TIME)
02610 {
02611 Buffer_GetFloat(Buffer, &pPlayer->SpawnTime);
02612 pPlayer->OldSpawnTime = pPlayer->SpawnTime;
02613 }
02614 else
02615 pPlayer->SpawnTime = pPlayer->OldSpawnTime;
02616
02617 if (SendFlags & NETMGR_SEND_VIEW_FLAGS)
02618 {
02619 Buffer_GetShort(Buffer, &pPlayer->ViewFlags);
02620 pPlayer->OldViewFlags = pPlayer->ViewFlags;
02621 }
02622 else
02623 pPlayer->ViewFlags = pPlayer->OldViewFlags;
02624
02625 if (SendFlags & NETMGR_SEND_VIEW_INDEX)
02626 {
02627 Buffer_GetShort(Buffer, &pPlayer->ViewIndex);
02628 pPlayer->OldViewIndex = pPlayer->ViewIndex;
02629 }
02630 else
02631 pPlayer->ViewIndex = pPlayer->OldViewIndex;
02632
02633 if (SendFlags & NETMGR_SEND_MOTION_INDEX)
02634 {
02635 Buffer_GetByte(Buffer, &pPlayer->MotionIndex);
02636 pPlayer->OldMotionIndex = pPlayer->MotionIndex;
02637 }
02638 else
02639 pPlayer->MotionIndex = pPlayer->OldMotionIndex;
02640
02641 if (SendFlags & NETMGR_SEND_FX_FLAGS)
02642 {
02643 Buffer_GetShort(Buffer, &pPlayer->FxFlags);
02644 pPlayer->OldFxFlags = pPlayer->FxFlags;
02645 }
02646 else
02647 pPlayer->FxFlags = pPlayer->OldFxFlags;
02648
02649 if (SendFlags & NETMGR_SEND_POS)
02650 {
02651 Buffer_GetPos(Buffer, &pPlayer->Pos);
02652 pPlayer->OldPos = pPlayer->Pos;
02653 }
02654 else
02655 pPlayer->Pos = pPlayer->OldPos;
02656
02657 if (SendFlags & NETMGR_SEND_ANGLES)
02658 {
02659 Buffer_GetAngle(Buffer, &pPlayer->Angles);
02660 pPlayer->OldAngles = pPlayer->Angles;
02661 }
02662 else
02663 pPlayer->Angles = pPlayer->OldAngles;
02664
02665 if (SendFlags & NETMGR_SEND_FRAME_TIME)
02666 {
02667 Buffer_GetFloat2(Buffer, &pPlayer->FrameTime, 60.0f);
02668 pPlayer->OldFrameTime = pPlayer->FrameTime;
02669 }
02670 else
02671 pPlayer->FrameTime = pPlayer->OldFrameTime;
02672
02673 if (SendFlags & NETMGR_SEND_SCALE)
02674 {
02675 Buffer_GetFloat2(Buffer, &pPlayer->Scale, 100.0f);
02676 pPlayer->OldScale = pPlayer->Scale;
02677 }
02678 else
02679 pPlayer->Scale = pPlayer->OldScale;
02680
02681 if (SendFlags & NETMGR_SEND_VELOCITY)
02682 {
02683 Buffer_GetAngle(Buffer, &pPlayer->Velocity);
02684 pPlayer->OldVelocity = pPlayer->Velocity;
02685 }
02686 else
02687 pPlayer->Velocity = pPlayer->OldVelocity;
02688
02689 if (SendFlags & NETMGR_SEND_STATE)
02690 {
02691 uint8 State;
02692
02693 Buffer_GetByte(Buffer, &State);
02694 pPlayer->State = (GPlayer_PState)State;
02695 pPlayer->OldState = pPlayer->State;
02696 }
02697 else
02698 pPlayer->State = pPlayer->OldState;
02699
02700 if (SendFlags & NETMGR_SEND_CONTROL_INDEX)
02701 {
02702 pPlayer->OldControlIndex = pPlayer->ControlIndex;
02703 Buffer_GetShort(Buffer, &pPlayer->ControlIndex);
02704
02705 pPlayer->OldControlIndex = pPlayer->ControlIndex;
02706 }
02707 else
02708 pPlayer->ControlIndex = pPlayer->OldControlIndex;
02709
02710 if (SendFlags & NETMGR_SEND_TRIGGER_INDEX)
02711 {
02712 pPlayer->OldTriggerIndex = pPlayer->TriggerIndex;
02713 Buffer_GetShort(Buffer, &pPlayer->TriggerIndex);
02714
02715 pPlayer->OldTriggerIndex = pPlayer->TriggerIndex;
02716 }
02717 else
02718 pPlayer->TriggerIndex = pPlayer->OldTriggerIndex;
02719
02720
02721 if (Client->Mode == ClientMode_Proxy)
02722 {
02723
02724 if (pPlayer->ControlIndex == 0xffff)
02725 pPlayer->Control = NULL;
02726 else
02727 pPlayer->Control = Client->ProcIndex[pPlayer->ControlIndex];
02728
02729
02730 if (pPlayer->TriggerIndex == 0xffff)
02731 pPlayer->Trigger = NULL;
02732 else
02733 {
02734 pPlayer->Trigger = Client->ProcIndex[pPlayer->TriggerIndex];
02735 }
02736 }
02737
02738
02739 if (!AuxPlayer)
02740 {
02741 if (!Fx_PlayerSetFxFlags(GameMgr_GetFxSystem(Client->GMgr), PLAYER_TO_FXPLAYER(Client, pPlayer), pPlayer->FxFlags))
02742 GenVS_Error("Client_ParsePlayerData: Fx_PlayerSetFxFlags failed.\n");
02743 }
02744
02745 if (SendFlags & NETMGR_SEND_MINS_MAXS)
02746 {
02747 Buffer_GetPos(Buffer, &pPlayer->Mins);
02748 Buffer_GetPos(Buffer, &pPlayer->Maxs);
02749
02750
02751 pPlayer->OldMins = pPlayer->Mins;
02752 pPlayer->OldMaxs = pPlayer->Maxs;
02753 }
02754 else
02755 {
02756 pPlayer->Mins = pPlayer->OldMins;
02757 pPlayer->Maxs = pPlayer->OldMaxs;
02758 }
02759
02760 #if 0
02761
02762 if (pPlayer->ViewFlags & VIEW_TYPE_HACK)
02763 {
02764 GPlayer_XFormData *pXFormData;
02765 int32 i;
02766 uint8 NumXFormData;
02767
02768 Buffer_GetByte(Buffer, &NumXFormData);
02769
02770 pPlayer->NumXFormData = (uint8)NumXFormData;
02771
02772 pXFormData = pPlayer->XFormData;
02773
02774 for (i=0; i<pPlayer->NumXFormData; i++, pXFormData++)
02775 {
02776 geVec3d EulerAngles;
02777
02778 Buffer_GetAngle(Buffer, &EulerAngles);
02779 geXForm3d_SetEulerAngles(&pXFormData->XForm, &EulerAngles);
02780 Buffer_GetPos(Buffer, &pXFormData->XForm.Translation);
02781 Buffer_GetByte(Buffer, &pXFormData->BoneIndex);
02782 }
02783 }
02784
02785
02786 if (pPlayer->ViewFlags & VIEW_TYPE_HACK)
02787 {
02788 GPlayer_MotionData *pMotionData;
02789 int32 i;
02790 uint8 NumMotionData;
02791
02792 Buffer_GetByte(Buffer, &NumMotionData);
02793
02794 pPlayer->NumMotionData = NumMotionData;
02795
02796 pMotionData = pPlayer->MotionData;
02797
02798 for (i=0; i<pPlayer->NumMotionData; i++, pMotionData++)
02799 {
02800 Buffer_GetFloat(Buffer, &pMotionData->MotionTime);
02801 Buffer_GetByte(Buffer, &pMotionData->MotionIndex);
02802 }
02803 }
02804
02805 #endif
02806
02807 return pPlayer;
02808 }
02809
02810
02811
02812
02813 static void ParsePlayerDataLocally(Client_Client *Client, Buffer_Data *Buffer, geBoolean Fake)
02814 {
02815 GPlayer *Player;
02816
02817 assert(Client_IsValid(Client) == GE_TRUE);
02818
02819 if (Fake)
02820 {
02821 GPlayer FakePlayer;
02822
02823 memset(&FakePlayer, 0, sizeof(GPlayer));
02824
02825 Player = Client_ParsePlayerData(Client, Buffer, &FakePlayer);
02826
02827 return;
02828 }
02829
02830 Player = Client_ParsePlayerData(Client, Buffer, NULL);
02831
02832 if (!Player)
02833 GenVS_Error("[CLIENT] ParsePlayerDataLocally: Could not parse data.\n");
02834
02835 #ifdef PREDICT_CLIENT
02836
02837 if (Client->Mode == ClientMode_Proxy)
02838 UpdateProxyPlayer(Client, Player);
02839 #endif
02840 }
02841
02842
02843
02844
02845 static geBoolean RenderWorld(Client_Client *Client, GameMgr *GMgr, float Time)
02846 {
02847 GE_Rect Rect;
02848 geCamera *Camera;
02849 geEngine *Engine;
02850 geWorld *World;
02851 int Width,Height;
02852
02853 assert(Client_IsValid(Client) == GE_TRUE);
02854
02855 World = GameMgr_GetWorld(GMgr);
02856
02857 if (!World)
02858 return GE_TRUE;
02859
02860 VidMode_GetResolution(Client->VidMode,&Width,&Height);
02861
02862 Rect.Left = 0;
02863 Rect.Right = Width-1;
02864 Rect.Top = 0;
02865
02866 if (Width<SMALL_CONSOLE_CUTOFF_WIDTH)
02867 Rect.Bottom = Height - 1 - CONSOLE_HEIGHT_320;
02868 else
02869 Rect.Bottom = Height - 1 - CONSOLE_HEIGHT_640;
02870
02871 Engine = GameMgr_GetEngine(GMgr);
02872 assert(Engine);
02873
02874 Camera = GameMgr_GetCamera(GMgr);
02875 assert(Camera);
02876
02877 SetupCamera(Camera, &Rect, &Client->ViewXForm);
02878
02879
02880 if (!Corona_Frame(World, &Client->ViewXForm, Time))
02881 GenVS_Error("Client_RenderWorld: Corona_Frame failed.\n");
02882
02883
02884 if (!Electric_Frame(World, &Client->ViewXForm, Time))
02885 GenVS_Error("Client_RenderWorld: Electric_Frame failed.\n");
02886
02887
02888 if (!DynLight_Frame(World, &Client->ViewXForm, Time))
02889 GenVS_Error("Client_RenderWorld: DynLight_Frame failed.\n");
02890
02891
02892 if (!ModelCtl_Frame(World, &Client->ViewXForm, Time))
02893 GenVS_Error("Client_RenderWorld: ModelCtl_Frame failed.\n");
02894
02895
02896 if (!geEngine_RenderWorld(Engine, World, Camera, Time))
02897 GenVS_Error("Client_RenderWorld: geEngine_RenderWorld failed.\n");
02898
02899 return GE_TRUE;
02900 }
02901
02902
02903
02904
02905 static void SetupCamera(geCamera *Camera, geRect *Rect, geXForm3d *XForm)
02906 {
02907 geCamera_SetWorldSpaceXForm(Camera, XForm);
02908 geCamera_SetAttributes(Camera, 2.0f, Rect);
02909 }
02910
02911
02912
02913
02914 geBoolean Client_ChangeNetState(Client_Client *Client, NetMgr_NetState NewNetState)
02915 {
02916 char Data[128];
02917 Buffer_Data Buffer;
02918
02919 assert(Client_IsValid(Client) == GE_TRUE);
02920
02921 Client->NetState = NewNetState;
02922
02923
02924 Buffer_Set(&Buffer, Data, 128);
02925 Buffer_FillByte(&Buffer, NETMGR_MSG_CLIENT_CONFIRM);
02926 Buffer_FillSLong(&Buffer, NewNetState);
02927
02928 if (!NetMgr_SendServerMessage(Client->NMgr, &Buffer, GE_TRUE))
02929 GenVS_Error("Client_ChangeNetState: NetMgr_SendServerMessage failed.\n");
02930
02931 return GE_TRUE;
02932 }
02933
02934
02935
02936
02937 geBoolean Client_SetDemo(Client_Client *Client, int32 DemoNum)
02938 {
02939 assert(Client_IsValid(Client) == GE_TRUE);
02940 assert(DemoNum < Client->Demo.NumDemos);
02941 assert(Client->Demo.Mode == CLIENT_DEMO_PLAY);
02942
02943
02944 if (Client->Demo.File)
02945 fclose(Client->Demo.File);
02946
02947
02948 Client->Demo.CurrentDemo = DemoNum;
02949
02950 Client->Demo.File = fopen(Client->Demo.DemoNames[Client->Demo.CurrentDemo], "rb");
02951
02952 if (!Client->Demo.File)
02953 GenVS_Error("Client_SetDemo: Failed to open demo file: %s.\n", Client->Demo.DemoNames[Client->Demo.CurrentDemo]);
02954
02955 return GE_TRUE;
02956 }
02957
02958 char DemoBuffer[NETMGR_LOCAL_MSG_BUFFER_SIZE];
02959
02960
02961
02962
02963
02964 geBoolean Client_ReadServerMessages(Client_Client *Client, Buffer_Data *Buffer)
02965 {
02966 geCSNetMgr_NetMsgType MsgType;
02967
02968 assert(Client_IsValid(Client) == GE_TRUE);
02969
02970
02971 Buffer->Pos = 0;
02972
02973 if (Client->Demo.Mode == CLIENT_DEMO_PLAY)
02974 {
02975 geBoolean Good = GE_FALSE;
02976
02977 Buffer->Data = DemoBuffer;
02978
02979 assert(Client->Demo.File);
02980
02981
02982 if (Client->Demo.OriginalSpeed)
02983 if (Client->Time <= Client->NetTime)
02984 return GE_FALSE;
02985
02986 if (fread(&Buffer->Size, sizeof(int32), 1, Client->Demo.File) == 1)
02987 {
02988 if (Buffer->Size >= NETMGR_LOCAL_MSG_BUFFER_SIZE)
02989 GenVS_Error("Client_ReadServerMessages: Demo Buffer size can't hold data.\n");
02990
02991 if (fread(Buffer->Data, sizeof(char), Buffer->Size, Client->Demo.File) == (uint32)Buffer->Size)
02992 Good = GE_TRUE;
02993 }
02994
02995 if (!Good)
02996 {
02997 Client->Time = 0.0f;
02998 Client->NetTime = 0.0f;
02999
03000
03001 memset(Client->ClientInfo, 0, sizeof(Client_ClientInfo)*NETMGR_MAX_CLIENTS);
03002
03003 if (!Client_SetDemo(Client, (Client->Demo.CurrentDemo+1)%Client->Demo.NumDemos))
03004 {
03005 Client->Demo.Mode = CLIENT_DEMO_NONE;
03006 return GE_TRUE;
03007 }
03008
03009
03010 fseek(Client->Demo.File, 0, SEEK_SET);
03011
03012 if (fread(&Buffer->Size, sizeof(int32), 1, Client->Demo.File) != 1)
03013 GenVS_Error("Error reading the demo file.\n");
03014
03015 if (fread(Buffer->Data, sizeof(char), Buffer->Size, Client->Demo.File) != (uint32)Buffer->Size)
03016 GenVS_Error("Error reading the demo file.\n");
03017 }
03018
03019 return GE_TRUE;
03020 }
03021
03022 while (1)
03023 {
03024 if (!NetMgr_ReceiveServerMessage(Client->NMgr, &MsgType, Buffer))
03025 GenVS_Error("Client_ReadServerMessages: NetMgr_ReceiveServerMessage failed.\n");
03026
03027 if (MsgType == NET_MSG_SESSIONLOST)
03028 GenVS_Error("Client_ReadServerMessages: Session was lost.\n");
03029
03030 if (MsgType == NET_MSG_NONE)
03031 return GE_FALSE;
03032
03033 if (MsgType == NET_MSG_USER)
03034 break;
03035 }
03036
03037
03038 if (!Buffer->Size)
03039 return GE_FALSE;
03040
03041
03042 if (Client->Demo.Mode == CLIENT_DEMO_RECORD)
03043 {
03044 assert(Client->Demo.File);
03045 fwrite(&Buffer->Size, 1, sizeof(int32), Client->Demo.File);
03046 fwrite(Buffer->Data, Buffer->Size, 1, Client->Demo.File);
03047 }
03048
03049 return GE_TRUE;
03050 }
03051
03052 char TempDemoName[CLIENT_MAX_DEMO_NAME_SIZE];
03053
03054
03055
03056
03057 static const char *ParseDemoName(FILE *f)
03058 {
03059 char *pName;
03060 char c;
03061
03062
03063 while (1)
03064 {
03065 if (fread(&c, 1, sizeof(char), f) != 1)
03066 return NULL;
03067
03068 if (c != ' ' && c != 0x0d)
03069 break;
03070 }
03071
03072 if (c == '\n')
03073 return NULL;
03074
03075 pName = TempDemoName;
03076
03077 *pName++ = c;
03078
03079 while (1)
03080 {
03081 if (fread(&c, 1, sizeof(char), f) != 1)
03082 return NULL;
03083
03084 if (c == 0x0d)
03085 continue;
03086
03087
03088
03089
03090 *pName = c;
03091
03092 if ((int32)(pName - TempDemoName) >= CLIENT_MAX_DEMO_NAME_SIZE)
03093 return NULL;
03094
03095 if (c == '\n')
03096 {
03097 *pName = 0;
03098 break;
03099 }
03100
03101 pName++;
03102
03103 }
03104
03105 return TempDemoName;
03106 }
03107
03108
03109
03110
03111 static geBoolean ReadDemoIni(Client_Client *Client)
03112 {
03113 FILE *f;
03114
03115 assert(Client_IsValid(Client) == GE_TRUE);
03116
03117
03118 f = fopen("Demo.Ini", "r");
03119
03120 if (!f)
03121 return GE_FALSE;
03122
03123 while (1)
03124 {
03125 const char *Name;
03126
03127 Name = ParseDemoName(f);
03128
03129 if (!Name)
03130 break;
03131
03132 strcpy(Client->Demo.DemoNames[Client->Demo.NumDemos], Name);
03133 Client->Demo.NumDemos++;
03134
03135 if (Client->Demo.NumDemos >= CLIENT_MAX_DEMOS)
03136 break;
03137 }
03138
03139
03140 fclose(f);
03141
03142
03143 if (Client->Demo.NumDemos <= 0)
03144 {
03145 Client->Demo.Mode = CLIENT_DEMO_NONE;
03146 return GE_FALSE;
03147 }
03148
03149 return GE_TRUE;
03150 }
03151
03152
03153
03154
03155 geBoolean Client_SetupDemos(Client_Client *Client, int32 Mode, const char *DemoFile)
03156 {
03157 assert(Client);
03158
03159 assert(Client_IsValid(Client) == GE_TRUE);
03160
03161 Client->Demo.Mode = Mode;
03162 Client->Demo.OriginalSpeed = GE_TRUE;
03163
03164 Client->Demo.NumDemos = 0;
03165 Client->Demo.CurrentDemo = 0;
03166
03167 Client->Demo.File = NULL;
03168
03169 if (Client->Demo.Mode == CLIENT_DEMO_RECORD)
03170 {
03171 assert(DemoFile && DemoFile[0]);
03172
03173 Client->Demo.File = fopen(DemoFile, "wb");
03174
03175 if (!Client->Demo.File)
03176 return GE_FALSE;
03177
03178 return GE_TRUE;
03179 }
03180 else if (Client->Demo.Mode == CLIENT_DEMO_PLAY && DemoFile[0])
03181 {
03182 Client->Demo.NumDemos = 1;
03183 Client->Demo.CurrentDemo = 0;
03184 strcpy(Client->Demo.DemoNames[0], DemoFile);
03185 }
03186 else if (Client->Demo.Mode == CLIENT_DEMO_PLAY && !DemoFile[0])
03187 {
03188 if (!ReadDemoIni(Client))
03189 return GE_FALSE;
03190 }
03191
03192 if (Client->Demo.Mode == CLIENT_DEMO_PLAY)
03193 {
03194 if (!Client_SetDemo(Client, Client->Demo.CurrentDemo))
03195 return GE_FALSE;
03196 }
03197
03198 return GE_TRUE;
03199 }
03200
03201
03202
03203
03204
03205
03206
03207
03208
03209 static float Client_GetTime(Client_Client *Client)
03210 {
03211 assert(Client_IsValid(Client) == GE_TRUE);
03212
03213 return GameMgr_GetTime(Client->GMgr);
03214 }
03215
03216
03217
03218
03219 geWorld *Client_GetWorld(Client_Client *Client)
03220 {
03221 assert(Client_IsValid(Client) == GE_TRUE);
03222
03223 return GameMgr_GetWorld(Client->GMgr);
03224 }
03225
03226
03227
03228
03229 static GenVSI_CMove *Client_GetClientMove(Client_Client *Client, GenVSI_CHandle ClientHandle)
03230 {
03231 assert(Client_IsValid(Client) == GE_TRUE);
03232
03233
03234
03235 if (ClientHandle == Client->ClientIndex)
03236 return &Client->Move;
03237 else
03238 return NULL;
03239 }
03240
03241
03242
03243
03244 static void Client_ProcIndex(Client_Client *Client, uint16 Index, void *Proc)
03245 {
03246 assert(Client_IsValid(Client) == GE_TRUE);
03247 assert(Index >= 0 && Index < 65535);
03248 assert(Index >= 0 && Index < CLIENT_MAX_PROC_INDEX);
03249
03250 Client->ProcIndex[Index] = Proc;
03251
03252 g_ProcIndex[Index] = Proc;
03253 }
03254
03255
03256
03257
03258 static geBoolean Client_MovePlayerModel(Client_Client *Client, GPlayer *Player, const geXForm3d *DestXForm)
03259 {
03260 geBoolean CanMove;
03261 int32 i;
03262 geWorld *World;
03263
03264 assert(Client_IsValid(Client) == GE_TRUE);
03265
03266 World = GameMgr_GetWorld(Client->GMgr);
03267 assert(World);
03268
03269 CanMove = GE_TRUE;
03270
03271 for (i=0; i< NETMGR_MAX_PLAYERS; i++)
03272 {
03273 geVec3d Mins, Maxs, Pos, Out;
03274 GPlayer *Target;
03275
03276 Target = &Client->Players[i];
03277
03278 if (!Target->Active)
03279 continue;
03280
03281 if (Target->ViewFlags & VIEW_TYPE_MODEL)
03282 continue;
03283
03284 if (i != Client->ClientPlayer)
03285 continue;
03286
03287 Mins = Target->Mins;
03288 Maxs = Target->Maxs;
03289
03290 Pos = Target->XForm.Translation;
03291
03292
03293 if (!geWorld_TestModelMove(World, Player->Model, DestXForm, &Mins, &Maxs, &Pos, &Out))
03294 {
03295 CanMove = GE_FALSE;
03296
03297
03298 if (Player->Blocked)
03299 {
03300 Player->Blocked(&Client->GenVSI, Player, Target);
03301 }
03302
03303 }
03304 else
03305 {
03306 Target->XForm.Translation = Out;
03307 Target->Pos = Out;
03308 Target->LastGoodPos = Out;
03309 }
03310 }
03311
03312 if (CanMove)
03313 {
03314 if (World)
03315 geWorld_SetModelXForm(World, Player->Model, DestXForm);
03316 else
03317 Console_Printf(GameMgr_GetConsole(Client->GMgr), "Client_MovePlayerModel: No world!\n");
03318
03319 Player->Pos = DestXForm->Translation;
03320 Player->XForm.Translation = DestXForm->Translation;
03321 }
03322
03323 return CanMove;
03324 }
03325
03326
03327
03328
03329
03330 static GPlayer *Client_SpawnTempPlayer(Client_Client *Client, const char *ClassName)
03331 {
03332 int32 i;
03333
03334 assert(Client_IsValid(Client) == GE_TRUE);
03335 assert(strlen(ClassName) < MAX_CLASS_NAME_SIZE);
03336
03337 for (i=0; i< CLIENT_MAX_TEMP_PLAYERS; i++)
03338 {
03339 if (!Client->TempPlayers[i].Active)
03340 break;
03341 }
03342
03343 if (i >= CLIENT_MAX_TEMP_PLAYERS)
03344 {
03345 GenVS_Error("Client_SpawnTempPlayer: Failed to add player!!!\n");
03346 return NULL;
03347 }
03348
03349 memset(&Client->TempPlayers[i], 0, sizeof(GPlayer));
03350
03351 SetPlayerDefaults(&Client->TempPlayers[i]);
03352
03353 Client->TempPlayers[i].Active = GE_TRUE;
03354 Client->TempPlayers[i].SpawnTime = Client->Move.MoveTime;
03355
03356 return &Client->TempPlayers[i];
03357 }
03358
03359
03360
03361
03362 void Client_DestroyPlayerWorldObjects(Client_Client *Client, GPlayer *Player)
03363 {
03364 geBoolean Ret;
03365 geWorld *World;
03366
03367 World = GameMgr_GetWorld(Client->GMgr);
03368
03369 if (Player->Actor)
03370 {
03371 assert(World);
03372 Ret = geWorld_RemoveActor(World, Player->Actor);
03373 assert(Ret == GE_TRUE);
03374 geActor_Destroy(&Player->Actor);
03375 }
03376
03377 if (Player->Light)
03378 {
03379 assert(World);
03380 geWorld_RemoveLight(World, Player->Light);
03381 }
03382
03383 if (Player->Poly)
03384 {
03385 assert(World);
03386 geWorld_RemovePoly(World, Player->Poly);
03387 }
03388 }
03389
03390
03391
03392
03393 void Client_DestroyTempPlayer(Client_Client *Client, GPlayer *Player)
03394 {
03395 assert(Client_IsValid(Client) == GE_TRUE);
03396 assert(Player);
03397
03398 assert(Player->Active);
03399
03400
03401
03402
03403 Client_DestroyPlayerWorldObjects(Client, Player);
03404
03405 memset(Player, 0, sizeof(GPlayer));
03406 }
03407
03408
03409
03410
03411 GPlayer *Client_GetPlayer(Client_Client *Client, int32 Index)
03412 {
03413 assert(Client_IsValid(Client) == GE_TRUE);
03414 assert(Index >= 0);
03415 assert(Index < NETMGR_MAX_PLAYERS);
03416
03417 return &Client->Players[Index];
03418 }
03419
03420
03421
03422
03423 void Client_DestroyPlayer(Client_Client *Client, GPlayer *Player)
03424 {
03425 assert(Client_IsValid(Client) == GE_TRUE);
03426 assert(Player);
03427
03428 assert(Player->Active);
03429
03430 if (!Fx_PlayerSetFxFlags(GameMgr_GetFxSystem(Client->GMgr), PLAYER_TO_FXPLAYER(Client, Player), 0))
03431 GenVS_Error("[CLIENT] UpdatePlayers: Could not set Fx_Player flags.\n");
03432
03433 Client_DestroyPlayerWorldObjects(Client, Player);
03434
03435 memset(Player, 0, sizeof(GPlayer));
03436 }
03437
03438
03439
03440
03441
03442 static void Client_SetupGenVSI(Client_Client *Client)
03443 {
03444 GenVSI *VSI;
03445
03446 assert(Client_IsValid(Client) == GE_TRUE);
03447
03448 VSI = &Client->GenVSI;
03449
03450 memset(VSI, 0, sizeof(GenVSI));
03451
03452 VSI->Mode = MODE_SmartClient;
03453
03454 VSI->UData = Client;
03455
03456 VSI->GetTime = Client_GetTime;
03457
03458 VSI->MovePlayerModel = Client_MovePlayerModel;
03459
03460 VSI->GetWorld = Client_GetWorld;
03461 VSI->GetClientMove = Client_GetClientMove;
03462
03463 VSI->ProcIndex = Client_ProcIndex;
03464
03465 VSI->SpawnPlayer = Client_SpawnTempPlayer;
03466 VSI->DestroyPlayer = Client_DestroyTempPlayer;
03467 }