/** * @brief Sets the entity fields so that the beacon is visible only by its team and spectators. */ void Propagate( gentity_t *ent ) { ent->r.svFlags = SVF_BROADCAST | SVF_CLIENTMASK; G_TeamToClientmask( (team_t)ent->s.bc_team, &ent->r.loMask, &ent->r.hiMask ); // Don't send enemy bases or tagged enemy entities to spectators. if ( ent->s.eFlags & EF_BC_ENEMY ) {} // Don't send tagged structures to spectators. else if ( ent->s.modelindex == BCT_TAG && !(ent->s.eFlags & EF_BC_TAG_PLAYER) ) {} else { int loMask, hiMask; G_TeamToClientmask( TEAM_NONE, &loMask, &hiMask ); ent->r.loMask |= loMask; ent->r.hiMask |= hiMask; } // Don't send a player tag to the tagged client itself. if ( ent->s.bc_type == BCT_TAG && (ent->s.eFlags & EF_BC_TAG_PLAYER) ) { int loMask, hiMask; G_ClientnumToMask( ent->s.bc_target, &loMask, &hiMask ); ent->r.loMask &= ~loMask; ent->r.hiMask &= ~hiMask; } trap_LinkEntity( ent ); }
/* =============== G_BroadcastEvent Sends an event to every client =============== */ void G_BroadcastEvent( int event, int eventParm, team_t team ) { gentity_t *ent; ent = G_NewTempEntity( vec3_origin, event ); ent->s.eventParm = eventParm; if ( team ) { G_TeamToClientmask( team, &ent->r.loMask, &ent->r.hiMask ); ent->r.svFlags = SVF_BROADCAST | SVF_CLIENTMASK; } else { ent->r.svFlags = SVF_BROADCAST; } }
/** * Awards momentum to a team. * * Will notify the client hwo earned it if given, otherwise the whole team, with *an event. */ static float AddMomentum(momentum_t type, team_t team, float amount, gentity_t* source, bool skipChangeHook) { gentity_t* event = nullptr; gclient_t* client; char* clientName; if (team <= TEAM_NONE || team >= NUM_TEAMS) { return 0.0f; } // apply modifier amount *= MomentumMod(type); // limit a team's total if (level.team[team].momentum + amount > MOMENTUM_MAX) { amount = MOMENTUM_MAX - level.team[team].momentum; } if (amount != 0.0f) { // add momentum to team level.team[team].momentum += amount; // run change hook if requested if (!skipChangeHook) { MomentumChanged(); } // notify source if (source) { client = source->client; if (client && client->pers.team == team) { event = G_NewTempEntity(client->ps.origin, EV_MOMENTUM); event->r.svFlags = SVF_SINGLECLIENT; event->r.singleClient = client->ps.clientNum; } } else { event = G_NewTempEntity(vec3_origin, EV_MOMENTUM); event->r.svFlags = (SVF_BROADCAST | SVF_CLIENTMASK); G_TeamToClientmask(team, &(event->r.loMask), &(event->r.hiMask)); } if (event) { // TODO: Use more bits for momentum value event->s.eventParm = 0; event->s.otherEntityNum = 0; event->s.otherEntityNum2 = (int) (fabs(amount) * 10.0f + 0.5f); event->s.groundEntityNum = amount < 0.0f ? true : false; } // notify legacy stage sensors NotifyLegacyStageSensors(team, amount); } if (g_debugMomentum.integer > 0) { if (source && source->client) { clientName = source->client->pers.netname; } else { clientName = "no source"; } Com_Printf("Momentum: %.2f to %s (%s by %s for %s)\n", amount, BG_TeamNamePlural(team), amount < 0.0f ? "lost" : "earned", clientName, MomentumTypeToReason(type)); } return amount; }