1 /*
2 Copyright (C) 1996-1997 Id Software, Inc.
3
4 This program is free software; you can redistribute it and/or
5 modify it under the terms of the GNU General Public License
6 as published by the Free Software Foundation; either version 2
7 of the License, or (at your option) any later version.
8
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
12
13 See the GNU General Public License for more details.
14
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
18
19
20 */
21
22 #ifndef CLIENTONLY
23 #include "qwsvdef.h"
24
25
26 //=============================================================================
27
28 // because there can be a lot of nails, there is a special
29 // network protocol for them
30 #define MAX_NAILS 32
31 static edict_t *nails[MAX_NAILS];
32 static int numnails;
33 static int nailcount = 0;
34
35 extern int sv_nailmodel, sv_supernailmodel, sv_playermodel;
36
37 cvar_t sv_nailhack = {"sv_nailhack", "1"};
38
39 // Maximum packet we will send - currently 256 if extension supported
40 #define MAX_PACKETENTITIES_POSSIBLE 256
41
SV_AddNailUpdate(edict_t * ent)42 static qbool SV_AddNailUpdate (edict_t *ent)
43 {
44 if ((int)sv_nailhack.value)
45 return false;
46
47 if (ent->v.modelindex != sv_nailmodel && ent->v.modelindex != sv_supernailmodel)
48 return false;
49
50 if (msg_coordsize != 2)
51 return false; // Do not allow nailhack in case of sv_bigcoords.
52
53 if (numnails == MAX_NAILS)
54 return true;
55
56 nails[numnails] = ent;
57 numnails++;
58 return true;
59 }
60
SV_EmitNailUpdate(sizebuf_t * msg,qbool recorder)61 static void SV_EmitNailUpdate (sizebuf_t *msg, qbool recorder)
62 {
63 int x, y, z, p, yaw, n, i;
64 byte bits[6]; // [48 bits] xyzpy 12 12 12 4 8
65 edict_t *ent;
66
67
68 if (!numnails)
69 return;
70
71 if (recorder)
72 MSG_WriteByte (msg, svc_nails2);
73 else
74 MSG_WriteByte (msg, svc_nails);
75
76 MSG_WriteByte (msg, numnails);
77
78 for (n=0 ; n<numnails ; n++)
79 {
80 ent = nails[n];
81 if (recorder)
82 {
83 if (!ent->v.colormap)
84 {
85 if (!((++nailcount)&255)) nailcount++;
86 ent->v.colormap = nailcount&255;
87 }
88
89 MSG_WriteByte (msg, (byte)ent->v.colormap);
90 }
91
92 x = ((int)(ent->v.origin[0] + 4096 + 1) >> 1) & 4095;
93 y = ((int)(ent->v.origin[1] + 4096 + 1) >> 1) & 4095;
94 z = ((int)(ent->v.origin[2] + 4096 + 1) >> 1) & 4095;
95 p = Q_rint(ent->v.angles[0]*(16.0/360.0)) & 15;
96 yaw = Q_rint(ent->v.angles[1]*(256.0/360.0)) & 255;
97
98 bits[0] = x;
99 bits[1] = (x>>8) | (y<<4);
100 bits[2] = (y>>4);
101 bits[3] = z;
102 bits[4] = (z>>8) | (p<<4);
103 bits[5] = yaw;
104
105 for (i=0 ; i<6 ; i++)
106 MSG_WriteByte (msg, bits[i]);
107 }
108 }
109
110 //=============================================================================
111
112
113 /*
114 ==================
115 SV_WriteDelta
116
117 Writes part of a packetentities message.
118 Can delta from either a baseline or a previous packet_entity
119 ==================
120 */
SV_WriteDelta(client_t * client,entity_state_t * from,entity_state_t * to,sizebuf_t * msg,qbool force)121 void SV_WriteDelta(client_t* client, entity_state_t *from, entity_state_t *to, sizebuf_t *msg, qbool force)
122 {
123 int bits, i;
124 #ifdef PROTOCOL_VERSION_FTE
125 int evenmorebits = 0;
126 unsigned int required_extensions = 0;
127 unsigned int fte_extensions = client->fteprotocolextensions;
128 #endif
129
130 // send an update
131 bits = 0;
132
133 for (i = 0; i < 3; i++)
134 if (to->origin[i] != from->origin[i])
135 bits |= U_ORIGIN1 << i;
136
137 if (to->angles[0] != from->angles[0])
138 bits |= U_ANGLE1;
139
140 if (to->angles[1] != from->angles[1])
141 bits |= U_ANGLE2;
142
143 if (to->angles[2] != from->angles[2])
144 bits |= U_ANGLE3;
145
146 if (to->colormap != from->colormap)
147 bits |= U_COLORMAP;
148
149 if (to->skinnum != from->skinnum)
150 bits |= U_SKIN;
151
152 if (to->frame != from->frame)
153 bits |= U_FRAME;
154
155 if (to->effects != from->effects)
156 bits |= U_EFFECTS;
157
158 if (to->modelindex != from->modelindex) {
159 bits |= U_MODEL;
160 #ifdef FTE_PEXT_ENTITYDBL
161 if (to->modelindex > 255) {
162 evenmorebits |= U_FTE_MODELDBL;
163 required_extensions |= FTE_PEXT_MODELDBL;
164 }
165 #endif
166 }
167
168 if (bits & U_CHECKMOREBITS)
169 bits |= U_MOREBITS;
170
171 if (to->flags & U_SOLID)
172 bits |= U_SOLID;
173
174 // Taken from FTE
175 if (msg->cursize + 40 > msg->maxsize && !MSG_HasOverflowHandler(msg))
176 {
177 // not enough space in the buffer, don't send the entity this frame. (not sending means nothing changes, and it takes no bytes!!)
178 int oldnum = to->number;
179 *to = *from;
180 if (oldnum && !from->number) {
181 to->number = oldnum;
182 }
183 return;
184 }
185
186 //
187 // write the message
188 //
189 if (!to->number)
190 SV_Error("Unset entity number");
191
192 #ifdef PROTOCOL_VERSION_FTE
193 if (to->number >= 512)
194 {
195 if (to->number >= 1024)
196 {
197 if (to->number >= 1024 + 512) {
198 evenmorebits |= U_FTE_ENTITYDBL;
199 required_extensions |= FTE_PEXT_ENTITYDBL;
200 }
201
202 evenmorebits |= U_FTE_ENTITYDBL2;
203 required_extensions |= FTE_PEXT_ENTITYDBL2;
204 if (to->number >= 2048)
205 SV_Error ("Entity number >= 2048");
206 }
207 else {
208 evenmorebits |= U_FTE_ENTITYDBL;
209 required_extensions |= FTE_PEXT_ENTITYDBL;
210 }
211 }
212
213 if (evenmorebits&0xff00)
214 evenmorebits |= U_FTE_YETMORE;
215 if (evenmorebits&0x00ff)
216 bits |= U_FTE_EVENMORE;
217 if (bits & 511)
218 bits |= U_MOREBITS;
219 #endif
220
221 if (to->number >= sv.max_edicts) {
222 /*SV_Error*/
223 Con_Printf("Entity number >= MAX_EDICTS (%d), set to MAX_EDICTS - 1\n", sv.max_edicts);
224 to->number = sv.max_edicts - 1;
225 }
226
227 #ifdef PROTOCOL_VERSION_FTE
228 if (evenmorebits && (fte_extensions & required_extensions) != required_extensions) {
229 return;
230 }
231 #endif
232 if (!bits && !force) {
233 return; // nothing to send!
234 }
235 i = (to->number & U_CHECKMOREBITS) | (bits&~U_CHECKMOREBITS);
236 if (i & U_REMOVE)
237 Sys_Error("U_REMOVE");
238 MSG_WriteShort(msg, i);
239
240 if (bits & U_MOREBITS)
241 MSG_WriteByte(msg, bits & 255);
242 #ifdef PROTOCOL_VERSION_FTE
243 if (bits & U_FTE_EVENMORE)
244 MSG_WriteByte (msg, evenmorebits&255);
245 if (evenmorebits & U_FTE_YETMORE)
246 MSG_WriteByte (msg, (evenmorebits>>8)&255);
247 #endif
248
249 if (bits & U_MODEL)
250 MSG_WriteByte(msg, to->modelindex & 255);
251 if (bits & U_FRAME)
252 MSG_WriteByte(msg, to->frame);
253 if (bits & U_COLORMAP)
254 MSG_WriteByte(msg, to->colormap);
255 if (bits & U_SKIN)
256 MSG_WriteByte(msg, to->skinnum);
257 if (bits & U_EFFECTS)
258 MSG_WriteByte(msg, to->effects);
259 if (bits & U_ORIGIN1) {
260 if (client->mvdprotocolextensions1 & MVD_PEXT1_FLOATCOORDS) {
261 MSG_WriteLongCoord(msg, to->origin[0]);
262 }
263 else {
264 MSG_WriteCoord(msg, to->origin[0]);
265 }
266 }
267 if (bits & U_ANGLE1) {
268 MSG_WriteAngle(msg, to->angles[0]);
269 }
270 if (bits & U_ORIGIN2) {
271 if (client->mvdprotocolextensions1 & MVD_PEXT1_FLOATCOORDS) {
272 MSG_WriteLongCoord(msg, to->origin[1]);
273 }
274 else {
275 MSG_WriteCoord(msg, to->origin[1]);
276 }
277 }
278 if (bits & U_ANGLE2) {
279 MSG_WriteAngle(msg, to->angles[1]);
280 }
281 if (bits & U_ORIGIN3) {
282 if (client->mvdprotocolextensions1 & MVD_PEXT1_FLOATCOORDS) {
283 MSG_WriteLongCoord(msg, to->origin[2]);
284 }
285 else {
286 MSG_WriteCoord(msg, to->origin[2]);
287 }
288 }
289 if (bits & U_ANGLE3) {
290 MSG_WriteAngle(msg, to->angles[2]);
291 }
292 }
293
294 /*
295 =============
296 SV_EmitPacketEntities
297
298 Writes a delta update of a packet_entities_t to the message.
299
300 =============
301 */
SV_EmitPacketEntities(client_t * client,packet_entities_t * to,sizebuf_t * msg)302 static void SV_EmitPacketEntities (client_t *client, packet_entities_t *to, sizebuf_t *msg)
303 {
304 int oldindex, newindex, oldnum, newnum, oldmax;
305 client_frame_t *fromframe;
306 packet_entities_t *from1;
307 edict_t *ent;
308
309 // this is the frame that we are going to delta update from
310 if (client->delta_sequence != -1)
311 {
312 fromframe = &client->frames[client->delta_sequence & UPDATE_MASK];
313 from1 = &fromframe->entities;
314 oldmax = from1->num_entities;
315
316 MSG_WriteByte (msg, svc_deltapacketentities);
317 MSG_WriteByte (msg, client->delta_sequence);
318 }
319 else
320 {
321 oldmax = 0; // no delta update
322 from1 = NULL;
323
324 MSG_WriteByte (msg, svc_packetentities);
325 }
326
327 newindex = 0;
328 oldindex = 0;
329 //Con_Printf ("---%i to %i ----\n", client->delta_sequence & UPDATE_MASK
330 // , client->netchan.outgoing_sequence & UPDATE_MASK);
331 while (newindex < to->num_entities || oldindex < oldmax)
332 {
333 newnum = newindex >= to->num_entities ? 9999 : to->entities[newindex].number;
334 oldnum = oldindex >= oldmax ? 9999 : from1->entities[oldindex].number;
335
336 if (newnum == oldnum)
337 { // delta update from old position
338 //Con_Printf ("delta %i\n", newnum);
339 SV_WriteDelta (client, &from1->entities[oldindex], &to->entities[newindex], msg, false);
340 oldindex++;
341 newindex++;
342 continue;
343 }
344
345 if (newnum < oldnum)
346 { // this is a new entity, send it from the baseline
347 if (newnum == 9999)
348 {
349 Sys_Printf("LOL, %d, %d, %d, %d %d %d\n", // nice message
350 newnum, oldnum, to->num_entities, oldmax,
351 client->netchan.incoming_sequence & UPDATE_MASK,
352 client->delta_sequence & UPDATE_MASK);
353 if (client->edict == NULL)
354 Sys_Printf("demo\n");
355 }
356 ent = EDICT_NUM(newnum);
357 //Con_Printf ("baseline %i\n", newnum);
358 SV_WriteDelta (client, &ent->e->baseline, &to->entities[newindex], msg, true);
359 newindex++;
360 continue;
361 }
362
363 if (newnum > oldnum)
364 {
365 // the old entity isn't present in the new message
366 if (oldnum >= 512) {
367 //yup, this is expensive.
368 MSG_WriteShort (msg, oldnum | U_REMOVE | U_MOREBITS);
369 MSG_WriteByte (msg, U_FTE_EVENMORE);
370 if (oldnum >= 1024) {
371 if (oldnum >= 1024 + 512) {
372 MSG_WriteByte(msg, U_FTE_ENTITYDBL | U_FTE_ENTITYDBL2);
373 }
374 else {
375 MSG_WriteByte(msg, U_FTE_ENTITYDBL2);
376 }
377 }
378 else {
379 MSG_WriteByte(msg, U_FTE_ENTITYDBL);
380 }
381 }
382 else {
383 MSG_WriteShort(msg, oldnum | U_REMOVE);
384 }
385
386 oldindex++;
387 continue;
388 }
389 }
390
391 MSG_WriteShort (msg, 0); // end of packetentities
392 }
393
TranslateEffects(edict_t * ent)394 static int TranslateEffects (edict_t *ent)
395 {
396 int fx = (int)ent->v.effects;
397 if (pr_nqprogs)
398 fx &= ~EF_MUZZLEFLASH;
399 if (pr_nqprogs && (fx & EF_DIMLIGHT)) {
400 if ((int)ent->v.items & IT_QUAD)
401 fx |= EF_BLUE;
402 if ((int)ent->v.items & IT_INVULNERABILITY)
403 fx |= EF_RED;
404 }
405 return fx;
406 }
407
408 /*
409 =============
410 SV_MVD_WritePlayersToClient
411 =============
412 */
SV_MVD_WritePlayersToClient(void)413 static void SV_MVD_WritePlayersToClient ( void )
414 {
415 int j;
416 demo_frame_t *demo_frame;
417 demo_client_t *dcl;
418 client_t *cl;
419 edict_t *ent;
420
421 if ( !sv.mvdrecording )
422 return;
423
424 demo_frame = &demo.frames[demo.parsecount&UPDATE_MASK];
425
426 for (j = 0, cl = svs.clients, dcl = demo_frame->clients; j < MAX_CLIENTS; j++, cl++, dcl++)
427 {
428 if ( cl->state != cs_spawned || cl->spectator )
429 continue;
430
431 ent = cl->edict;
432
433 dcl->parsecount = demo.parsecount;
434
435 VectorCopy(ent->v.origin, dcl->origin);
436 VectorCopy(ent->v.angles, dcl->angles);
437 dcl->angles[0] *= -3;
438 #ifdef USE_PR2
439 if( cl->isBot )
440 VectorCopy(ent->v.v_angle, dcl->angles);
441 #endif
442 dcl->angles[2] = 0; // no roll angle
443
444 if (ent->v.health <= 0)
445 { // don't show the corpse looking around...
446 dcl->angles[0] = 0;
447 dcl->angles[1] = ent->v.angles[1];
448 dcl->angles[2] = 0;
449 }
450
451 dcl->weaponframe = ent->v.weaponframe;
452 dcl->frame = ent->v.frame;
453 dcl->skinnum = ent->v.skin;
454 dcl->model = ent->v.modelindex;
455 dcl->effects = TranslateEffects(ent);
456 dcl->flags = 0;
457
458 dcl->fixangle = demo.fixangle[j];
459 demo.fixangle[j] = 0;
460
461 dcl->sec = sv.time - cl->localtime;
462
463 if (ent->v.health <= 0)
464 dcl->flags |= DF_DEAD;
465 if (ent->v.mins[2] != -24)
466 dcl->flags |= DF_GIB;
467
468 continue;
469 }
470 }
471
472 /*
473 =============
474 SV_PlayerVisibleToClient
475 =============
476 */
SV_PlayerVisibleToClient(client_t * client,int j,byte * pvs,edict_t * self_ent,edict_t * ent)477 qbool SV_PlayerVisibleToClient (client_t* client, int j, byte* pvs, edict_t* self_ent, edict_t* ent)
478 {
479 client_t* cl = &svs.clients[j];
480
481 // ZOID visibility tracking
482 if (ent != self_ent && !(client->spec_track && client->spec_track - 1 == j))
483 {
484 int i;
485
486 if (cl->spectator)
487 return false;
488
489 if (pvs && ent->e->num_leafs >= 0) {
490 // ignore if not touching a PV leaf
491 for (i = 0; i < ent->e->num_leafs; i++) {
492 if (pvs[ent->e->leafnums[i] >> 3] & (1 << (ent->e->leafnums[i] & 7))) {
493 break;
494 }
495 }
496 if (i == ent->e->num_leafs) {
497 return false; // not visible
498 }
499 }
500 }
501
502 return true;
503 }
504
505 /*
506 =============
507 SV_WritePlayersToClient
508 =============
509 */
510
511 int SV_PMTypeForClient (client_t *cl);
SV_WritePlayersToClient(client_t * client,client_frame_t * frame,byte * pvs,qbool disable_updates,sizebuf_t * msg)512 static void SV_WritePlayersToClient (client_t *client, client_frame_t *frame, byte *pvs, qbool disable_updates, sizebuf_t *msg)
513 {
514 int msec, pflags, pm_type = 0, pm_code = 0, i, j;
515 usercmd_t cmd;
516 int hideent = 0;
517 int trackent = 0;
518 qbool hide_players = fofs_hide_players && ((eval_t *)((byte *)&(client->edict)->v + fofs_hide_players))->_int;
519
520 if (fofs_hideentity)
521 hideent = ((eval_t *)((byte *)&(client->edict)->v + fofs_hideentity))->_int / pr_edict_size;
522
523 if (fofs_trackent)
524 {
525 trackent = ((eval_t *)((byte *)&(client->edict)->v + fofs_trackent))->_int;
526 if (trackent < 1 || trackent > MAX_CLIENTS || svs.clients[trackent - 1].state != cs_spawned)
527 trackent = 0;
528 }
529
530 frame->sv_time = sv.time;
531
532 for (j = 0; j < MAX_CLIENTS; j++)
533 {
534 client_t* cl = &svs.clients[j];
535 edict_t* ent = NULL;
536 edict_t* self_ent = NULL;
537 edict_t* track_ent = NULL;
538
539 if (fofs_visibility) {
540 // Presume not visible
541 ((eval_t *)((byte *)&(cl->edict)->v + fofs_visibility))->_int &= ~(1 << (client - svs.clients));
542 }
543
544 if (cl->state != cs_spawned)
545 continue;
546
547 if (client != cl && hide_players)
548 continue;
549
550 if (trackent && cl == client)
551 {
552 cl = &svs.clients[trackent - 1]; // fakenicking.
553
554 track_ent = svs.clients[trackent - 1].edict;
555
556 self_ent = track_ent;
557 ent = track_ent;
558 }
559 else
560 {
561 self_ent = client->edict;
562 ent = cl->edict;
563 }
564
565 // set up edicts.
566 if (!SV_PlayerVisibleToClient (client, j, pvs, self_ent, ent))
567 continue;
568
569 if (fofs_visibility) {
570 // Update flags so mods can tell what was visible
571 ((eval_t *)((byte *)&(ent)->v + fofs_visibility))->_int |= (1 << (client - svs.clients));
572 }
573
574 if (j == hideent - 1)
575 continue;
576
577 if (j == trackent - 1)
578 continue;
579
580 if (disable_updates && ent != self_ent)
581 { // Vladis
582 continue;
583 }
584
585 //====================================================
586 // OK, seems we must send info about this player below
587
588 pflags = PF_MSEC | PF_COMMAND;
589
590 if (ent->v.modelindex != sv_playermodel)
591 pflags |= PF_MODEL;
592 for (i=0 ; i<3 ; i++)
593 if (ent->v.velocity[i])
594 pflags |= PF_VELOCITY1<<i;
595 if (ent->v.effects)
596 pflags |= PF_EFFECTS;
597 if (ent->v.skin || ent->v.modelindex >= 256)
598 pflags |= PF_SKINNUM;
599 if (ent->v.health <= 0)
600 pflags |= PF_DEAD;
601 if (ent->v.mins[2] != -24)
602 pflags |= PF_GIB;
603
604 if (cl->spectator)
605 { // only sent origin and velocity to spectators
606 pflags &= PF_VELOCITY1 | PF_VELOCITY2 | PF_VELOCITY3;
607 }
608 else if (ent == self_ent)
609 { // don't send a lot of data on personal entity
610 pflags &= ~(PF_MSEC|PF_COMMAND);
611 if (ent->v.weaponframe)
612 pflags |= PF_WEAPONFRAME;
613 }
614
615 // Z_EXT_PM_TYPE protocol extension
616 // encode pm_type and jump_held into pm_code
617 pm_type = track_ent ? PM_LOCK : SV_PMTypeForClient (cl);
618 switch (pm_type)
619 {
620 case PM_DEAD:
621 pm_code = PMC_NORMAL; // plus PF_DEAD
622 break;
623 case PM_NORMAL:
624 pm_code = PMC_NORMAL;
625 if (cl->jump_held)
626 pm_code = PMC_NORMAL_JUMP_HELD;
627 break;
628 case PM_OLD_SPECTATOR:
629 pm_code = PMC_OLD_SPECTATOR;
630 break;
631 case PM_SPECTATOR:
632 pm_code = PMC_SPECTATOR;
633 break;
634 case PM_FLY:
635 pm_code = PMC_FLY;
636 break;
637 case PM_NONE:
638 pm_code = PMC_NONE;
639 break;
640 case PM_LOCK:
641 pm_code = PMC_LOCK;
642 break;
643 default:
644 assert (false);
645 }
646
647 pflags |= pm_code << PF_PMC_SHIFT;
648
649 // Z_EXT_PF_ONGROUND protocol extension
650 if ((int)ent->v.flags & FL_ONGROUND)
651 pflags |= PF_ONGROUND;
652
653 // Z_EXT_PF_SOLID protocol extension
654 if (ent->v.solid == SOLID_BBOX || ent->v.solid == SOLID_SLIDEBOX)
655 pflags |= PF_SOLID;
656
657 if (pm_type == PM_LOCK && ent == self_ent)
658 pflags |= PF_COMMAND; // send forced view angles
659
660 if (client->spec_track && client->spec_track - 1 == j && ent->v.weaponframe)
661 pflags |= PF_WEAPONFRAME;
662
663 MSG_WriteByte (msg, svc_playerinfo);
664 MSG_WriteByte (msg, j);
665 MSG_WriteShort (msg, pflags);
666
667 if (client->mvdprotocolextensions1 & MVD_PEXT1_FLOATCOORDS) {
668 MSG_WriteLongCoord(msg, ent->v.origin[0]);
669 MSG_WriteLongCoord(msg, ent->v.origin[1]);
670 MSG_WriteLongCoord(msg, ent->v.origin[2]);
671 }
672 else {
673 MSG_WriteCoord(msg, ent->v.origin[0]);
674 MSG_WriteCoord(msg, ent->v.origin[1]);
675 MSG_WriteCoord(msg, ent->v.origin[2]);
676 }
677
678 MSG_WriteByte (msg, ent->v.frame);
679
680 if (pflags & PF_MSEC)
681 {
682 msec = 1000*(sv.time - cl->localtime);
683 if (msec > 255)
684 msec = 255;
685 MSG_WriteByte (msg, msec);
686 }
687
688 if (pflags & PF_COMMAND)
689 {
690 cmd = cl->lastcmd;
691
692 if (ent->v.health <= 0)
693 { // don't show the corpse looking around...
694 cmd.angles[0] = 0;
695 cmd.angles[1] = ent->v.angles[1];
696 cmd.angles[0] = 0;
697 }
698
699 cmd.buttons = 0; // never send buttons
700 cmd.impulse = 0; // never send impulses
701
702 if (ent == self_ent)
703 {
704 // this is PM_LOCK, we only want to send view angles
705 VectorCopy(ent->v.v_angle, cmd.angles);
706 cmd.forwardmove = 0;
707 cmd.sidemove = 0;
708 cmd.upmove = 0;
709 }
710
711 if ((client->extensions & Z_EXT_VWEP) && sv.vw_model_name[0] && fofs_vw_index) {
712 cmd.impulse = EdictFieldFloat (ent, fofs_vw_index);
713 }
714
715 MSG_WriteDeltaUsercmd (msg, &nullcmd, &cmd, 0);
716 }
717
718 for (i=0 ; i<3 ; i++)
719 if (pflags & (PF_VELOCITY1<<i) )
720 MSG_WriteShort (msg, ent->v.velocity[i]);
721
722 if (pflags & PF_MODEL)
723 MSG_WriteByte (msg, ent->v.modelindex);
724
725 if (pflags & PF_SKINNUM)
726 MSG_WriteByte (msg, (int)ent->v.skin | (((pflags & PF_MODEL)&&(ent->v.modelindex >= 256))<<7));
727
728 if (pflags & PF_EFFECTS)
729 MSG_WriteByte (msg, TranslateEffects(ent));
730
731 if (pflags & PF_WEAPONFRAME)
732 MSG_WriteByte (msg, ent->v.weaponframe);
733 }
734 }
735
736 /*
737 =============
738 SV_EntityVisibleToClient
739 =============
740 */
SV_EntityVisibleToClient(client_t * client,int e,byte * pvs)741 qbool SV_EntityVisibleToClient (client_t* client, int e, byte* pvs)
742 {
743 edict_t* ent = EDICT_NUM (e);
744
745 if (pr_nqprogs)
746 {
747 // don't send the player's model to himself
748 if (e < MAX_CLIENTS + 1 && svs.clients[e-1].state != cs_free)
749 return false;
750 }
751
752 // ignore ents without visible models
753 if (!ent->v.modelindex || !*PR_GetEntityString(ent->v.model))
754 return false;
755
756 if ( pvs && ent->e->num_leafs >= 0 )
757 {
758 int i;
759
760 // ignore if not touching a PV leaf
761 for (i=0 ; i < ent->e->num_leafs ; i++)
762 if (pvs[ent->e->leafnums[i] >> 3] & (1 << (ent->e->leafnums[i]&7) ))
763 break;
764
765 if (i == ent->e->num_leafs)
766 return false; // not visible
767 }
768
769 return true;
770 }
771
772 /*
773 =============
774 SV_WriteEntitiesToClient
775
776 Encodes the current state of the world as
777 a svc_packetentities messages and possibly
778 a svc_nails message and
779 svc_playerinfo messages
780 =============
781 */
782
SV_WriteEntitiesToClient(client_t * client,sizebuf_t * msg,qbool recorder)783 void SV_WriteEntitiesToClient (client_t *client, sizebuf_t *msg, qbool recorder)
784 {
785 qbool disable_updates; // disables sending entities to the client
786 int e, i, max_packet_entities;
787 packet_entities_t *pack;
788 client_frame_t *frame;
789 entity_state_t *state;
790 edict_t *ent;
791 byte *pvs;
792 int hideent;
793 unsigned int client_flag = (1 << (client - svs.clients));
794 edict_t *clent = client->edict;
795
796 float distances[MAX_PACKETENTITIES_POSSIBLE] = { 0 };
797 float distance;
798 int position;
799 vec3_t org;
800
801 if ( recorder )
802 {
803 if ( !sv.mvdrecording )
804 return;
805 }
806
807 // this is the frame we are creating
808 frame = &client->frames[client->netchan.incoming_sequence & UPDATE_MASK];
809
810 // find the client's PVS
811 if ( recorder )
812 {// demo
813 hideent = 0;
814 pvs = NULL; // ignore PVS for demos
815 max_packet_entities = MAX_MVD_PACKET_ENTITIES;
816 disable_updates = false; // updates always allowed in demos
817 }
818 else
819 {// normal client
820 vec3_t org;
821 int trackent = 0;
822
823 if (fofs_hideentity)
824 hideent = ((eval_t *)((byte *)&(client->edict)->v + fofs_hideentity))->_int / pr_edict_size;
825 else
826 hideent = 0;
827
828 if (fofs_trackent)
829 {
830 trackent = ((eval_t *)((byte *)&(client->edict)->v + fofs_trackent))->_int;
831 if (trackent < 1 || trackent > MAX_CLIENTS || svs.clients[trackent - 1].state != cs_spawned)
832 trackent = 0;
833 }
834
835 // we should use org of tracked player in case or trackent.
836 if (trackent)
837 {
838 VectorAdd (svs.clients[trackent - 1].edict->v.origin, svs.clients[trackent - 1].edict->v.view_ofs, org);
839 }
840 else
841 {
842 VectorAdd (client->edict->v.origin, client->edict->v.view_ofs, org);
843 }
844
845 pvs = CM_FatPVS (org); // search some PVS
846 max_packet_entities = (client->fteprotocolextensions & FTE_PEXT_256PACKETENTITIES) ? MAX_PEXT256_PACKET_ENTITIES : MAX_PACKET_ENTITIES;
847
848 if (client->disable_updates_stop > realtime)
849 {
850 #define ISUNDERWATER(x) ((x) == CONTENTS_WATER || (x) == CONTENTS_SLIME || (x) == CONTENTS_LAVA)
851
852 // server flash should not work underwater
853 int content = CM_HullPointContents(&sv.worldmodel->hulls[0], 0, client->edict->v.origin);
854 disable_updates = !ISUNDERWATER(content);
855
856 #undef ISUNDERWATER
857 }
858 else
859 {
860 disable_updates = false;
861 }
862 }
863
864 // send over the players in the PVS
865 if ( recorder )
866 SV_MVD_WritePlayersToClient (); // nice, no params at all!
867 else
868 SV_WritePlayersToClient (client, frame, pvs, disable_updates, msg);
869
870 // put other visible entities into either a packet_entities or a nails message
871 pack = &frame->entities;
872 pack->num_entities = 0;
873
874 numnails = 0;
875
876 if (!disable_updates)
877 {// Vladis, server flash
878
879 // QW protocol can only handle 512 entities. Any entity with number >= 512 will be invisible
880 // from ZQuake unless using protocol extensions.
881 // max_edicts = min(sv.num_edicts, MAX_EDICTS);
882
883 for (e = pr_nqprogs ? 1 : MAX_CLIENTS + 1, ent = EDICT_NUM(e); e < sv.num_edicts; e++, ent = NEXT_EDICT(ent))
884 {
885 if (!SV_EntityVisibleToClient(client, e, pvs)) {
886 if (fofs_visibility) {
887 ((eval_t *)((byte *)&(ent)->v + fofs_visibility))->_int &= ~client_flag;
888 }
889 continue;
890 }
891
892 if (fofs_visibility) {
893 // Don't include other filters in logic for setting this field
894 ((eval_t *)((byte *)&(ent)->v + fofs_visibility))->_int |= (1 << (client - svs.clients));
895 }
896
897 if (e == hideent) {
898 continue;
899 }
900
901 if (SV_AddNailUpdate (ent))
902 continue; // added to the special update list
903
904 if (clent) {
905 VectorAdd(ent->v.absmin, ent->v.absmax, org);
906 VectorMA(clent->v.origin, -0.5, org, org);
907 distance = DotProduct(org, org); //Length
908
909 // add to the packetentities
910 if (pack->num_entities == max_packet_entities) {
911 // replace the furthest entity
912 float furthestdist = -1;
913 int best = -1;
914 for (i = 0; i < max_packet_entities; i++) {
915 if (furthestdist < distances[i]) {
916 furthestdist = distances[i];
917 best = i;
918 }
919 }
920
921 if (furthestdist <= distance || best == -1) {
922 continue;
923 }
924
925 // shuffle other entities down, add to end
926 if (best < pack->num_entities - 1) {
927 memmove(&pack->entities[best], &pack->entities[best + 1], sizeof(pack->entities[0]) * (pack->num_entities - 1 - best));
928 memmove(&distances[best], &distances[best + 1], sizeof(distances[0]) * (pack->num_entities - 1 - best));
929 }
930 position = pack->num_entities - 1;
931 }
932 else {
933 position = pack->num_entities++;
934 }
935
936 distances[position] = distance;
937 }
938 else {
939 if (pack->num_entities == max_packet_entities) {
940 continue;
941 }
942
943 position = pack->num_entities++;
944 }
945
946 state = &pack->entities[position];
947 memset(state, 0, sizeof(*state));
948
949 state->number = e;
950 state->flags = 0;
951 VectorCopy (ent->v.origin, state->origin);
952 VectorCopy (ent->v.angles, state->angles);
953 state->modelindex = ent->v.modelindex;
954 state->frame = ent->v.frame;
955 state->colormap = ent->v.colormap;
956 state->skinnum = ent->v.skin;
957 state->effects = TranslateEffects(ent);
958 }
959 } // server flash
960
961 // encode the packet entities as a delta from the
962 // last packetentities acknowledged by the client
963
964 SV_EmitPacketEntities (client, pack, msg);
965
966 // now add the specialized nail update
967 SV_EmitNailUpdate (msg, recorder);
968
969 // Translate NQ progs' EF_MUZZLEFLASH to svc_muzzleflash
970 if (pr_nqprogs)
971 {
972 for (e=1, ent=EDICT_NUM(e) ; e < sv.num_edicts ; e++, ent = NEXT_EDICT(ent))
973 {
974 // ignore ents without visible models
975 if (!ent->v.modelindex || !*PR_GetEntityString(ent->v.model))
976 continue;
977
978 // ignore if not touching a PV leaf (meag: this does nothing... complete or remove?)
979 if (pvs && ent->e->num_leafs >= 0) {
980 for (i = 0; i < ent->e->num_leafs; i++)
981 if (pvs[ent->e->leafnums[i] >> 3] & (1 << (ent->e->leafnums[i] & 7)))
982 break;
983 }
984
985 if ((int)ent->v.effects & EF_MUZZLEFLASH) {
986 ent->v.effects = (int)ent->v.effects & ~EF_MUZZLEFLASH;
987 MSG_WriteByte (msg, svc_muzzleflash);
988 MSG_WriteShort (msg, e);
989 }
990 }
991 }
992 }
993
994 /*
995 ============
996 SV_SetVisibleEntitiesForBot
997 ============
998 */
SV_SetVisibleEntitiesForBot(client_t * client)999 void SV_SetVisibleEntitiesForBot (client_t* client)
1000 {
1001 int j = 0;
1002 int e = 0;
1003 unsigned int client_flag = 1 << (client - svs.clients);
1004 vec3_t org;
1005 byte* pvs = NULL;
1006
1007 if (!fofs_visibility)
1008 return;
1009
1010 VectorAdd (client->edict->v.origin, client->edict->v.view_ofs, org);
1011 pvs = CM_FatPVS (org); // search some PVS
1012
1013 // players first
1014 for (j = 0; j < MAX_CLIENTS; j++)
1015 {
1016 if (SV_PlayerVisibleToClient(client, j, pvs, client->edict, svs.clients[j].edict)) {
1017 ((eval_t *)((byte *)&(svs.clients[j].edict)->v + fofs_visibility))->_int |= client_flag;
1018 }
1019 else {
1020 ((eval_t *)((byte *)&(svs.clients[j].edict)->v + fofs_visibility))->_int &= ~client_flag;
1021 }
1022 }
1023
1024 // Other entities
1025 for (e = pr_nqprogs ? 1 : MAX_CLIENTS + 1; e < sv.num_edicts; e++)
1026 {
1027 edict_t* ent = EDICT_NUM (e);
1028
1029 if (SV_EntityVisibleToClient(client, e, pvs)) {
1030 ((eval_t *)((byte *)&(ent)->v + fofs_visibility))->_int |= client_flag;
1031 }
1032 else {
1033 ((eval_t *)((byte *)&(ent)->v + fofs_visibility))->_int &= ~client_flag;
1034 }
1035 }
1036 }
1037
SV_SkipCommsBotMessage(client_t * client)1038 qbool SV_SkipCommsBotMessage(client_t* client)
1039 {
1040 extern cvar_t sv_serveme_fix;
1041
1042 return sv_serveme_fix.value && client->spectator && !strcmp(client->name, "[ServeMe]");
1043 }
1044
1045 #endif // !CLIENTONLY
1046