Skocz do zawartości

Nowy szablon forum

mygo.pl

Stworzyliśmy dla Was nowy wygląd forum. Z pewnością znajdziesz rzeczy, które wg Ciebie mogą zostać zmienione - wspomnij o tym w specjalnym wątku.

Czytaj więcej

Jak założyć własną sieć

serwerów CS

Zastanawiasz się nad prowadzeniem własnej sieci serwerów? Przeczytaj podstawowe informacje, na które należy zwrócić uwagę, przy takim projekcie.

Czytaj więcej

Tworzymy spis sieci

dodaj swoją

Dodaj sieć do której należysz, pozwoli to na promocję i budowę ogólnopolskiej bazy sieci CS.

Czytaj więcej

RSScromchat


MYGO.pl
 Udostępnij

Rekomendowane odpowiedzi

  • RSSy
Hi! I don't know how to make the messages with red color here to be with cromchat.
I did some changes, but there are some of them which are different
Code:

/*
 *        Ptahhotep's Team Balancer (PTB)
 *        Version 1.8b1
 *        AUTHOR: Ptahhotep ([email protected])
 *
 *  1.7b3  PTB converted for AMX Mod by OLO
 *  1.7b5  Modified for CS 1.6 by XAD.
 *          Thanks Redmist ("slot1" to close old-style-menus).
 *          Added fix by 'Panzermensh' for lost kill when moved
 *          (thanks r0otd0wn).
 *  1.7b6  Ported to AMX Mod X 0.16 by XAD.
 *          Changed config file path to configs/ptb.cfg
 *  1.7b7  Added admin immunity by Ingerfara. (Thanks to EpsychE and rootdown)
 *  1.7b8  JGHG: changed the path of ptb.cfg to use AMXx's default custom path.
 
 *  1.7b9.2 lantz69: 2005-10-03
                        - changed how players are transfered and cleaned up the code.
                        - Players are now transfered without being killed and they also keep their weapons
                        - lastRoundSwitched[id] is also updated at transfers. Before the amx_ptb playerfreq was broken

 *  1.7b9.3 lantz69: 2006-01-12
                - small fix for client_prints.

 *  1.8b1 lantz69: 2006-04-05
                - ptb.cfg is now back in addons/amxmodx/configs/
                - wtj.log is now in addons/amxmodx/logs/
                - using amxmodx function floatabs
                - added amxmodx 1.70 autochanneling for hud messages
                - admins with kick flag is able to join spec even if autojoin is enabled
                - new cvars ptb_switch_immunity and ptb_limitjoin_immunity. (in ptb.cfg)
                  Now it's easy to disable admins immunity.
                 
        * 1.8b2 lantz69: 2006-08-03
                - If player has defuse kit before a transfer it will be removed (thx teame06)
                - Added compile option #define SHOW_IN_HLSW To be able to remove transfers being showed in HLSW chat (Sug. Brad)
               
        * 1.8b3 lantz69: 2007-03-03
                - Fixed so you can have mp_roundtime to almost whatever you want and PTB will still work.
                Before PTB did not work if you had mp_roundtime set to 2.10 or 1.75 etc It had to be 1.5, 2.0, 2.5 etc
                - Added log_message to hlds logs when a player is transfered (player X joined team ..) for PsychoStats 3.X
                - Changed the time player is transfered from 4.0 to 4.5 seconds
                - Added cvar ptb_immunity_level so you dont need to recompile to change the admin flag for immunity
                - Added cvar ptb_access_level so you dont need to recompile to change the admin flag for access to ptb
                - Added cvar ptb_show_in_hlsw If you want to see Transfers made in the HLSW chat have this set to 1
                - Added the above cvars into ptb.cfg ptb_immunity_level, ptb_show_in_hlsw and ptb_access_level
                - Made all cvars use the new pcvars system.
                - Added protection for VIP to be transfered (Uncomment #define PTB_VIP_IMMUNITY in the source for this to work)
               
                *** TODO ******
                Make it MultiLingual
 */

#include <amxmodx>
#include <amxmisc>
#include <cstrike>
#include <cromchat>

// Uncomment for support immunity on VIP
//#define PTB_VIP_IMMUNITY

// Uncomment to activate log debug messages.
//#define PTB_DEBUG

// team ids
#define UNASSIGNED                0
#define TS                        1
#define CTS                        2
#define AUTO_TEAM                5

new const PTB_VERSION[] = "1.8b3"

// team selection control
new bool:PTB_LIMITJOIN = true // set limits on team joining
new PTB_LIMITAFTER = 0 // number of rounds after which teams limiting begins
new PTB_LIMITMIN = 0 // number of minimum players on map for team limiting
new PTB_MAXSIZE = 10 // maximum team size per team
new PTB_MAXDIFF = 2 // maximum team size difference
new PTB_AUTOROUNDS = 3 // number of first rounds into match, which allow autojoin only
new PTB_WTJAUTO = 3 // wtj tries needed to become autojoined
new PTB_WTJKICK = 5 // wtj tries needed to become kicked
new bool:PTB_KICK = true // kick for wtj counts
new bool:PTB_SAVEWTJ = false // save wtjs to wtj.log

// team balancing actions
new bool:PTB_SWITCH = true // switch/transfer players
new PTB_SWITCHAFTER = 0 // number of rounds after which switching begins
new PTB_SWITCHMIN = 3 // number of minimum players on map for switching
new PTB_SWITCHFREQ = 1 // relative next possible switch round
new PTB_PLAYERFREQ = 3 // relative next possible switch round for player
new PTB_FORCESWITCH = 3 // number of tries after which PTB switches alive, if neccessary
new bool:PTB_DEADONLY = false // switch dead only

// messages
new bool:PTB_TELLWTJ = true // tell about wtj tries
new bool:PTB_ANNOUNCE = true // announce team status at beginning of round
new bool:PTB_SAYOK = true // announce team status, if teams are alright
new bool:PTB_TYPESAY = true // use typesay

// team strength limits
new PTB_MAXSTREAK = 2 // max. allowed team win streak
new PTB_MAXSCORE = 2 // max. allowed team score difference
new Float:PTB_MINRATING = 1.5 // minimum critical team rating
new Float:PTB_MAXRATING = 2.0 // maximum critical team rating
new Float:PTB_SUPERRATING = 3.0 // super critical team rating
new PTB_MAXINCIDENTS = 50 // maximum kills + deaths before the score is divided by PTB_SCALEDOWN
new PTB_SCALEDOWN = 2 // divisor for kills and deaths, when PTB_MAXINCIDENTS is reached

// sorted player indices are 0-based
new sortedTeams[3][32]
new sortedValidTargets[3][32]
new validTargetCounts[3]

new teamKills[3]
new teamDeaths[3]
new teamScores[3]
new winStreaks[3]

new wtConditions[3]
new winnerTeam
new loserTeam

new Float:ctKD
new Float:tKD
new Float:ctStrength
new Float:tStrength
new Float:ctRating
new Float:tRating

// player arrays are 1-based, there is no player 0
new clientVGUIMenu[33][2]
new bool:isBeingTransfered[33]
new playerTeam[33]
new lastRoundSwitched[33]
new wtjCount[33]
new teamCounts[3]
new kills[33]
new deaths[33]

new roundCounter
new lastSwitchRound
new couldNotSwitchCounter

new lastTeamBalanceCheck[32]

//New auto-channeling system in amxmodx 1.70
new g_MyMsgSync

// pcvars
new saychat
new transfer_type
new switch_immunity
new limitjoin_immunity
new immunity_level
new access_level
new show_in_hlsw

public plugin_init(){
        register_plugin("Team Balancer",PTB_VERSION,"Ptahhotep")
        register_cvar("amx_ptb_version",PTB_VERSION,FCVAR_SERVER|FCVAR_EXTDLL|FCVAR_UNLOGGED|FCVAR_SPONLY)
       
        saychat = register_cvar("ptb_saychat", "1")
        transfer_type = register_cvar("ptb_transfer_type", "2")
        switch_immunity = register_cvar("ptb_switch_immunity", "0")
        limitjoin_immunity = register_cvar("ptb_limitjoin_immunity", "1")
        immunity_level = register_cvar("ptb_immunity_level", "o")
        access_level = register_cvar("ptb_access_level", "l")
        show_in_hlsw = register_cvar("ptb_show_in_hlsw", "1")
       
        register_menucmd(register_menuid("Team_Select",1),(1<<0)|(1<<1)|(1<<4),"teamselect")
        register_event("ShowMenu","menuclass","b","4&CT_Select","4&Terrorist_Select")
        register_clcmd("jointeam","jointeam")
        register_clcmd("team_join","team_join")
#if defined PTB_DEBUG
        register_clcmd("say /last","check_lasttransfer")
#endif
        register_event("SendAudio","round_end","a","2=%!MRAD_terwin","2=%!MRAD_ctwin","2=%!MRAD_rounddraw") // Round End
        register_event("TeamScore","team_score","a") // Team Score
        register_event("RoundTime", "new_round", "bc") // Round Time
        register_event("DeathMsg","death_msg","a") // Kill
        register_event("TeamInfo","team_assign","a") // Team Assigment (also UNASSIGNED and SPECTATOR)
        register_event("TextMsg","team_join","a","1=1","2&Game_join_te","2&Game_join_ct") // Team Joining
        register_event("TextMsg","game_restart","a","1=4","2&#Game_C","2&#Game_w") // Game restart
        register_concmd("amx_ptb","admin_ptb",get_access_level_flag(),"- displays PTB options")
       
        new configsDir[64]
        get_configsdir(configsDir, 63)
        server_cmd("exec %s/ptb.cfg", configsDir) // Execute main configuration file

        //New auto-channeling system in amxmodx 1.70
        g_MyMsgSync = CreateHudSyncObj()

       
        // Init clients VGUI-menu setting
        // Set terminating 0 to allow use of char processing instead of string
        // to improve performance.
        for (new i=0;i<33;i++){
                clientVGUIMenu[i][0] = '0'
                clientVGUIMenu[i][1] = 0
        }

        return PLUGIN_CONTINUE
}

public get_immunity_level_flag()
{
        new flags[24]
        get_pcvar_string(immunity_level, flags, 23)
       
        return(read_flags(flags))
}

public get_access_level_flag()
{
        new flags[24]
        get_pcvar_string(access_level, flags, 23)
       
        return(read_flags(flags))
}


Float:fdivWorkaround(Float:nom, Float:denom){
        if ( denom == 0.0) return nom
        return floatabs(nom / denom)
}

doTypesay(string[], duration, r, g, b) {
        if (!PTB_TYPESAY) return
        //last parameter is not needed
        set_hudmessage(r, g, b, 0.05, 0.25, 0, 6.0, float(duration) , 0.5, 0.15, -1)
        //use this instead of show_hudmessage
        ShowSyncHudMsg(0, g_MyMsgSync, "%s", string)
}

say(string[]){
        if(get_pcvar_num(saychat) == 1 || get_pcvar_num(saychat) == 3){
                client_print(0,print_chat,string)
                server_print(string)
        }
}

bool:check_param_bool(param[])
        return (equali(param, "on") || equal(param, "1")) ? true : false

Float:check_param_float(param[],Float:n){
        new Float:a = floatstr(param)
        if (a < n) a = n
        return a
}

check_param_num(param[],n){
        new a = str_to_num(param)
        if (a < n) a = n
        return a
}

transferPlayer(id){

        if (!is_user_connected(id)) return
        if (isBeingTransfered[id]) return
        isBeingTransfered[id] = false
       
        new name[32], player_steamid[50], team_pre_transfer[12]
        get_user_name(id,name,31)
        get_user_authid(id, player_steamid, 49)
        get_user_team(id, team_pre_transfer, 11)
       
        if(cs_get_user_defuse(id))
    cs_set_user_defuse(id, 0);
       
        cs_set_user_team(id, (playerTeam[id]==TS) ? 2 : 1)
        cs_reset_user_model(id)

        // This must be done here or lastroundswithed will not be registered
        lastRoundSwitched[id] = roundCounter
       
        // This logs to hlds logs so Psychostats knows that the player has changed team (PS 3.X)
        //"LAntz69<9><STEAM_0:1:1895474><TERRORIST>" joined team "CT"  //This is how it will be outputted in hlds logs
        log_message("^"%s<%d><%s><%s>^" joined team ^"%s^"",
                name, get_user_userid(id), player_steamid, team_pre_transfer, (playerTeam[id]==TS) ? "CT" : "TERRORIST" )
               
        if(get_pcvar_num(show_in_hlsw) == 1)
        {
                // This makes you able to see transfers with HLSW in the chat
                log_message("^"<><><>^" triggered ^"amx_chat^" (text ^"[PTB] Transfered %s to %s^")",
                        name, (playerTeam[id]==TS) ? "CT" : "TERRORIST" )
        }
       
#if defined PTB_DEBUG
        log_amx("Transfer player: %s lastRoundSwitched[id]: %i roundCounter:%i", name, lastRoundSwitched[id], roundCounter)
        client_print(0,print_chat,"Transfer player: %s lastRoundSwitched[id]: %i roundCounter:%i", name, lastRoundSwitched[id], roundCounter)
#endif
}

#if defined PTB_DEBUG
public check_lasttransfer(id) {
        new lasttransfer, text[255]
        lasttransfer = lastRoundSwitched[id]
       
        format(text,255,"LastRound transfered: %i", lasttransfer)
        say(text)
}
#endif

actAtEndOfRound(){
        if (!PTB_SWITCH) return
        // skip switching for the first few rounds
        if (roundCounter <= PTB_SWITCHAFTER) return
        // honor switch frequency setting
        if (roundCounter - lastSwitchRound < PTB_SWITCHFREQ) return
        // skip switching for a small number of players
        if (get_playersnum() < PTB_SWITCHMIN) return
       
        say("^x04[Xmastime] ^x01Round ended, checking teams.")
        checkTeamBalance()
        if (winnerTeam) {
                sortTeam(CTS)
                sortTeam(TS)
                               
                // If they set the cvar(ptb_transfer_type) 1 or less than 2 or bigger than 3
                // then standard transfers will be selected
                if(get_pcvar_num(transfer_type) < 2 || get_pcvar_num(transfer_type) > 3){
                       
                // This is the standard if it should be a swith of to players or just one transfer
                if (teamCounts[winnerTeam] <= teamCounts[loserTeam]) // Original formula
                        doSwitch()
                else if (teamCounts[loserTeam] < teamCounts[winnerTeam]) // Original formula
                        doTransfer()       
                       
                }
               
                if(get_pcvar_num(transfer_type) == 2){
                       
                        // This is more agressive but not so much as the one below
                        if (teamCounts[winnerTeam] < teamCounts[loserTeam])
                                doSwitch()
                                       
                        else if (teamCounts[loserTeam] <= teamCounts[winnerTeam])
                                doTransfer()
                }
               
                if(get_pcvar_num(transfer_type) == 3){
                       
                        // This is the most agressive transfertype
                        if ((teamCounts[winnerTeam]+(PTB_MAXDIFF/2)) < teamCounts[loserTeam])
                                doSwitch()
                                       
                        else if (teamCounts[loserTeam] <= (teamCounts[winnerTeam]+(PTB_MAXDIFF/2)))
                                doTransfer()
                }

        }
}

createValidTargets(theTeam, bool:deadonly) {
        new n = 0
        for (new i = 0; i < teamCounts[theTeam]; ++i) {
               

#if defined PTB_VIP_IMMUNITY
                // If player is in the VIP team dont touch
                if (cs_get_user_vip(sortedTeams[theTeam][i])) continue
#endif
               
                // Protection for admins if ptb_switch_immunity 1
                if (get_user_flags(sortedTeams[theTeam][i])&get_immunity_level_flag() && (get_pcvar_num(switch_immunity) == 1)) continue
                // Dead only condition
                if ( deadonly && is_user_alive(sortedTeams[theTeam][i]) ) continue
                // Already switched or in PTB_PLAYERFREQ time condition
                if ((lastRoundSwitched[sortedTeams[theTeam][i]] == roundCounter) ||
                        (roundCounter - lastRoundSwitched[sortedTeams[theTeam][i]] < PTB_PLAYERFREQ))        continue
                sortedValidTargets[theTeam][n++] = sortedTeams[theTeam][i]
        }
        validTargetCounts[theTeam] = n
}

sortTeam(theTeam) {
        // create list of players
        new n = 0, a = get_maxplayers()
        for (new i = 1; i <= a; ++i) {
                // Get only members of specified team
                if (playerTeam[i] != theTeam) continue
                sortedTeams[theTeam][n++] = i
        }
        // do a selection sort
        new swap, count = n
        for (new i = count-1; i > 0; --i){
                for (new k = i-1; k >= 0; --k){
                        // compare players (kills better then other or if equal then with less deaths)
                        if ( (kills[sortedTeams[theTeam][k]]<kills[sortedTeams[theTeam][i]])
                                || ( (kills[sortedTeams[theTeam][k]]==kills[sortedTeams[theTeam][i]])        &&
                                (deaths[sortedTeams[theTeam][k]]>deaths[sortedTeams[theTeam][i]]))) {
                                // swap
                                swap = sortedTeams[theTeam][k]
                                sortedTeams[theTeam][k] = sortedTeams[theTeam][i]
                                sortedTeams[theTeam][i] = swap
                        }
                }
        }
}

Float:score(team, toBeAdded=0, toBeRemoved=0){
        new Float:sumKD = 0.0
        new a = get_maxplayers()
        for (new i = 1; i <= a; ++i) {
                if ( (playerTeam[i]!=team&&i!=toBeAdded)        || (i==toBeRemoved)        )
                        continue
                sumKD += fdivWorkaround(float(kills[i]), float(deaths[i]))
        }
        new Float:strength = float(teamCounts[team])
        if (sumKD) strength *= sumKD
        return strength
}

doSwitch() {
        new text[256]
        //displayStatistics(0,true)
        // don't switch, if at least one team is empty
        if ( teamCounts[winnerTeam] == 0 || teamCounts[loserTeam] == 0 ) {
                copy(text,255, "^x04[Xmastime] ^x01Can't switch players, need players in each team.")
                doTypesay(text, 5, 0, 255, 0)
                say(text)
                return
        }
        // don't switch, if winner is alone (RULER!!!)
        if (teamCounts[winnerTeam] == 1) {
                copy(text,255, "^x04[Xmastime] ^x01Won't switch players, best player makes the winning team.")
                doTypesay(text, 5, 0, 255, 0)
                say(text)
                return
        }
        // don't switch, if both teams are full
        if (teamCounts[winnerTeam] >= PTB_MAXSIZE && teamCounts[loserTeam] >= PTB_MAXSIZE) {
                copy(text,255, "^x04[Xmastime] ^x01Can't switch players, both teams are full.")
                doTypesay(text, 5, 0, 255, 0)
                say(text)

                return
        }
        if (!PTB_DEADONLY || couldNotSwitchCounter > PTB_FORCESWITCH) {
                // choose from random top or bottom x
                createValidTargets(winnerTeam, false)
                createValidTargets(loserTeam, false)

                if (validTargetCounts[winnerTeam] == 0 || validTargetCounts[loserTeam] == 0) {
                        ++couldNotSwitchCounter
                        copy(text,255, "^x04[Xmastime] ^x01Can't switch players, need valid target in each team.")
                        doTypesay(text, 5, 0, 255, 0)
                        say(text)

                        return
                }
        }
        else {
                //say("switch dead")
                createValidTargets(winnerTeam, true)
                createValidTargets(loserTeam, true)

                if (validTargetCounts[winnerTeam] == 0 || validTargetCounts[loserTeam] == 0) {
                        if (++couldNotSwitchCounter > PTB_FORCESWITCH) {
                                say("^x04[Xmastime] ^x01Couldn't switch dead, switching alive.")
                                doSwitch()
                                return

                        }
                        copy(text, 255,"^x04[Xmastime] ^x01Can't switch players, need valid target in each team.")

                        doTypesay(text, 5, 0, 255, 0)
                        say(text)
                        return
                }
        }
        // Now search through the possible 1 to 1 swaps to equalize the strength as much as possible
        new Float:closestScore = floatabs(score(winnerTeam) - score(loserTeam))
        new Float:myScore, toLoser, toWinner
        new winner = 0
        new loser = 0
        for (new w = 0; w < validTargetCounts[winnerTeam]; ++w) {
                toLoser = sortedValidTargets[winnerTeam][w]
                for (new l = 0; l < validTargetCounts[loserTeam]; ++l) {
                        toWinner = sortedValidTargets[loserTeam][l]
                        myScore = floatabs(score(winnerTeam, toWinner, toLoser) - score(loserTeam, toLoser, toWinner))
                        if (myScore < closestScore) {
                                closestScore = myScore
                                winner = toLoser
                                loser = toWinner
                        }
                }
        }
        if (winner == 0 && loser == 0) {
                copy(text, 255,"^x04[Xmastime] ^x01No switch would improve team balancing.")
                doTypesay(text, 5, 0, 255, 0)
                say(text)
                return
        }
        couldNotSwitchCounter = 0
        lastSwitchRound = roundCounter
        new winnerName[32], loserName[32]
        get_user_name(winner,winnerName,31)
        get_user_name(loser,loserName,31)
        // if one team is full, first move the the player from the full team ...
        if (teamCounts[winnerTeam] >= PTB_MAXSIZE){
                transferPlayer(winner)
                transferPlayer(loser)
        }
        else {
                transferPlayer(loser)
                transferPlayer(winner)
        }
        format(text,255,"^x04[Xmastime] ^x01Switching ^x03%s with ^x03%s.",winnerName,loserName)
       
        if(get_pcvar_num(saychat) == 2 || get_pcvar_num(saychat) == 3){
        //say(text)
                //set_hudmessage(0, 255, 0, 0.05, 0.25, 0, 6.0, 5.0 , 0.5, 0.15, 1)
                //show_hudmessage(0, text )
                set_hudmessage(0, 255, 0, 0.05, 0.25, 0, 6.0, 5.0 , 0.5, 0.15, -1)
                ShowSyncHudMsg(0, g_MyMsgSync, "%s", text)
                CC_SendMessage(0, "^x04[Xmastime] ^x01Switching ^x03%s with ^x03%s.",winnerName,loserName)
        }else{
                doTypesay(text, 5, 0, 255, 0)
                CC_SendMessage(0, "^x04[Xmastime] ^x01Switching ^x03%s with ^x03%s.",winnerName,loserName)
                //say(text)
        }
}

doTransfer() {
        //displayStatistics(0,true)
        new text[256]
        if (teamCounts[winnerTeam] == 0) {
                        copy(text,255, "^x04[Xmastime] ^x01Can't switch players, need players in each team.")
                        doTypesay(text, 5, 0, 255, 0)
                        say(text)
                        return
        }
        if (teamCounts[loserTeam] >= PTB_MAXSIZE) {
                copy(text,255, "^x04[Xmastime] ^x01Can't transfer player, losing team is full.")
                doTypesay(text, 5, 0, 255, 0)
                say(text)
                return
        }
        if (!PTB_DEADONLY || couldNotSwitchCounter > PTB_FORCESWITCH) {
                createValidTargets(winnerTeam, false)
                if (validTargetCounts[winnerTeam] == 0) {
                        copy(text,255, "^x04[Xmastime] ^x01Can't transfer player, no valid target in winning team.")
                        doTypesay(text, 5, 0, 255, 0)
                        say(text)
                        ++couldNotSwitchCounter
                        return
                }
        }
        else {
                //say("switch dead")
                createValidTargets(winnerTeam, true)
                if (validTargetCounts[winnerTeam] == 0) {
                        if (++couldNotSwitchCounter > PTB_FORCESWITCH) {
                                say("^x04[Xmastime] ^x01Couldn't transfer dead, transferring alive.")
                                doTransfer()
                                return

                        }
                        copy(text,255, "^x04[Xmastime] ^x01Can't transfer player, no valid target in winning team.")
                        doTypesay(text, 5, 0, 255, 0)
                        say(text)
                        return
                }
        }
        new Float:closestScore = floatabs(score(winnerTeam) - score(loserTeam))
        new Float:myScore, toLoser
        new winner = 0
        for (new w = 0; w < validTargetCounts[winnerTeam]; ++w) {
                toLoser = sortedValidTargets[winnerTeam][w]
                myScore = floatabs(score(winnerTeam, 0, toLoser) - score(loserTeam, toLoser, 0))
                if (myScore < closestScore) {
                        closestScore = myScore
                        winner = toLoser
                }
        }
        if (winner == 0) {
                copy(text, 255,"^x04[Xmastime] ^x01No transfer would improve team balancing.")
                doTypesay(text, 5, 0, 255, 0)
                say(text)
                return
        }
        couldNotSwitchCounter = 0
        new winnerName[32]
        get_user_name(winner,winnerName,31)
        transferPlayer(winner)
        format(text,255,"^x04[Xmastime] ^x01Transfering ^x04%s ^x01to the ^x03%s",winnerName, (winnerTeam == CTS) ? "Ts" : "CTs")
       
        if(get_pcvar_num(saychat) == 2 || get_pcvar_num(saychat) == 3){
        //say(text)
                //set_hudmessage(0, 255, 0, 0.05, 0.25, 0, 6.0, 5.0 , 0.5, 0.15, 1)
                //show_hudmessage(0, text )
                set_hudmessage(0, 255, 0, 0.05, 0.25, 0, 6.0, 5.0 , 0.5, 0.15, -1)
                ShowSyncHudMsg(0, g_MyMsgSync, "%s", text)
                CC_SendMessage(0, "^x04[Xmastime] ^x01Transfering ^x04%s ^x01to the ^x03%s",winnerName, (winnerTeam == CTS) ? "Ts" : "CTs")
        }else{
                doTypesay(text, 5, 0, 255, 0)
                CC_SendMessage(0, "^x04[Xmastime] ^x01Transfering ^x04%s ^x01to the ^x03%s",winnerName, (winnerTeam == CTS) ? "Ts" : "CTs")
                //say(text)
        }
}

checkTeamBalance() {

        get_time("%m/%d/%Y - %H:%M:%S",lastTeamBalanceCheck,31 )
        calcTeamScores()
        ctStrength = score(CTS)
        tStrength = score(TS)
        ctRating = fdivWorkaround(ctStrength, tStrength)
        tRating = fdivWorkaround(tStrength, ctStrength)
        wtConditions[TS] = 0
        wtConditions[CTS] = 0

        // compare scores for unequal rating scores
        if (teamScores[TS] - teamScores[CTS] > PTB_MAXSCORE && tRating >= PTB_MINRATING)
                wtConditions[TS]++

        if (teamScores[CTS] - teamScores[TS] > PTB_MAXSCORE && ctRating >= PTB_MINRATING)
                wtConditions[CTS]++

        // check streaks for unequal rating scores
        if (winStreaks[TS] > PTB_MAXSTREAK && tRating >= PTB_MINRATING)
                wtConditions[TS]++

        if (winStreaks[CTS] > PTB_MAXSTREAK && ctRating >= PTB_MINRATING)
                wtConditions[CTS]++

        // check ratings
        if (tRating >= PTB_MAXRATING)
                wtConditions[TS]++

        if (ctRating >= PTB_MAXRATING)
                wtConditions[CTS]++


        // check ratings
        if (tRating >= PTB_SUPERRATING)
                wtConditions[TS]++

        if (ctRating >= PTB_SUPERRATING)
                wtConditions[CTS]++


        // check team sizes for unequal ratings
        if (teamCounts[TS] > teamCounts[CTS] && tRating >= PTB_MINRATING)
                wtConditions[TS]++

        if (teamCounts[CTS] > teamCounts[TS] && ctRating >= PTB_MINRATING)
                wtConditions[CTS]++

        // check conditions
        if (wtConditions[TS] >= 2) {
                winnerTeam = TS
                loserTeam = CTS
        }
        else if (wtConditions[CTS] >= 2) {
                winnerTeam = CTS
                loserTeam = TS
        }
        else {
                winnerTeam = 0
                loserTeam = 0
        }
}

manageWtjFile(id) {
                if (!PTB_SAVEWTJ) return   
                //say("Trying to write wtj.log ....")
                //if (wtjCount[id] < 4) return
                //say("wtj.log should be written to now ....")
                new text[256], mapname[32], name[32], authid[32]
                get_mapname(mapname,31)
                get_user_name(id,name,31)
                get_user_authid(id,authid,31)
                format(text, 255, "%s <%s> %s", name, authid, mapname)
                log_to_file("wtj.log", text)



public menuclass(id) {
        if (!isBeingTransfered[id]) return PLUGIN_CONTINUE
        client_cmd(id,"slot1")
        isBeingTransfered[id] = false
        return PLUGIN_CONTINUE
}

public jointeam(id) {
        new arg[2]
        read_argv(1,arg,1)
        if (isBeingTransfered[id]) return PLUGIN_HANDLED
        return checkTeamSwitch(id,str_to_num(arg)) // team is key pressed + 1
}

public teamselect(id,key) {
       
        return checkTeamSwitch(id,key+1) // team is key pressed + 1
}

checkTeamSwitch(id,iNewTeam) {
       
        // don't care where player joins
        if (!PTB_LIMITJOIN) return PLUGIN_CONTINUE
        // Protection for admins if ptb_limitjoin_immunity 1
        if (get_user_flags(id)&get_immunity_level_flag() && (get_pcvar_num(limitjoin_immunity) == 1)) return PLUGIN_CONTINUE
        // players is transfered so don't care with rest
        if (isBeingTransfered[id]) {
                //say("TRANSFER")
                isBeingTransfered[id] = false
                return PLUGIN_CONTINUE
        }
        //say("NO TRANSFER")
        // skip limiting for a few rounds into the map
        if (PTB_LIMITAFTER && roundCounter <= PTB_LIMITAFTER) return PLUGIN_CONTINUE
        // skip limiting for a small number of players
        if (get_playersnum() < PTB_LIMITMIN) return PLUGIN_CONTINUE

        new iOldTeam = playerTeam[id]
       
        // disallow free team choices in the first rounds of a map
        if (PTB_AUTOROUNDS && (iOldTeam==UNASSIGNED) && roundCounter<=PTB_AUTOROUNDS && !(get_user_flags(id) & ADMIN_KICK))
                iNewTeam = AUTO_TEAM
               
        // prevent unwanted rejoining of the same team ...
        if (iNewTeam == iOldTeam) {
                //say("Preventing rejoining of the same team.")
                CC_SendMessage(id, "^x04[Xmastime] ^x01Joining to the same team is not allowed...")
#if !defined MANUAL_SWITCH
                engclient_cmd(id,"chooseteam") // display menu again
#endif
                return PLUGIN_HANDLED
        }
       
        checkTeamBalance()
        //displayStatistics(0,true)

        // Player for sure was in CT or T team and now is joining to the opposite team
        if ((iNewTeam==CTS&&iOldTeam==TS)||(iNewTeam==TS&&iOldTeam==CTS)){
                // If someone is in new team and old team weren't full
                // and the winning team is a destination team or in
                // new team is more players than in old then treat it as wtj
                if ( teamCounts[iNewTeam]&&(teamCounts[iOldTeam]<PTB_MAXSIZE)&&
                        ((iNewTeam==winnerTeam)||(teamCounts[iNewTeam]>=teamCounts[iOldTeam])) ) {
                        // player is wtjing
                        new text[256],name[32]
                        get_user_name(id,name,31)
                        // Kick wtj player if reached set limit
                        if (++wtjCount[id] >= PTB_WTJKICK && PTB_KICK) {
                                format(text, 255, "^x04[Xmastime] ^x01Kicking %s for a WTJ count %d of %d.", name, wtjCount[id],PTB_WTJKICK )
                                doTypesay(text, 5, 0, 255, 0)
                                say(text)
                                server_cmd("kick #%d",get_user_userid(id))
                                return PLUGIN_HANDLED
                        }
                        // Announce about WTJ
                        if (PTB_TELLWTJ) {
                                if (iNewTeam == CTS) {
                                        format(text, 255, "^x04[Xmastime] ^x01The CTs are strong enough, ^x04%s (WTJ: %d/%d).", name, wtjCount[id],PTB_WTJKICK)
                                        doTypesay(text, 5, 0, 50, 255)
                                }
                                else {
                                        format(text, 255, "^x04[Xmastime] ^x01The Ts are strong enough, ^x04%s (WTJ: %d/%d).", name, wtjCount[id],PTB_WTJKICK)
                                        doTypesay(text, 5, 255, 50, 0)
                                }
                                say(text)
                        }
#if !defined MANUAL_SWITCH
                        engclient_cmd(id,"chooseteam") // display menu again
#endif
                        return PLUGIN_HANDLED
                }
                // check for maximum team size
                if (teamCounts[iNewTeam] >= PTB_MAXSIZE) {
                        CC_SendMessage(id, "^x04[Xmastime] ^x01Maximum team size prohibits team change.")
#if !defined MANUAL_SWITCH
                        engclient_cmd(id,"chooseteam") // display menu again
#endif
                        return PLUGIN_HANDLED
                }
                // check team size difference limits
                if ( teamCounts[iNewTeam]+1-teamCounts[iOldTeam] >= PTB_MAXDIFF ) {
                        CC_SendMessage(id, "^x04[Xmastime] ^x01Maximum team size difference prohibits team change.")
#if !defined MANUAL_SWITCH
                        engclient_cmd(id,"chooseteam") // display menu again
#endif
                        return PLUGIN_HANDLED
                }
                return PLUGIN_CONTINUE // OK! He can join to the oppsoite team!!!
        }
       
        // Player is choosing his team for the first time!
        if (iNewTeam==CTS||iNewTeam==TS){
                // Get opposite team
                new opposingTeam = (iNewTeam==CTS)? TS : CTS
                // Players is joining to one team but the opposite is not full
                // and his team is bettter then opposite or has more players
                if (teamCounts[iNewTeam] && teamCounts[opposingTeam]<PTB_MAXSIZE &&
                                (iNewTeam==winnerTeam||(!winnerTeam&&teamCounts[iNewTeam]>teamCounts[opposingTeam]))) {
                        new text[256],name[32]
                        get_user_name(id,name,31)
                        if (++wtjCount[id] >= PTB_WTJKICK && PTB_KICK) {
                                format(text, 255, "^x04[Xmastime] Kicking %s for a WTJ count %d of %d.", name, wtjCount[id],PTB_WTJKICK)
                                doTypesay(text, 5, 0, 255, 0)
                                say(text)
                                server_cmd("kick #%d", get_user_userid(id))
                                return PLUGIN_HANDLED
                        }
                        if (iNewTeam==CTS) {
                                if (wtjCount[id]>=PTB_WTJAUTO && is_user_connected(id)) {
                                        manageWtjFile(id)
                                        format(text, 255, "^x04[Xmastime] ^x01Forcing ^x03%s ^x04to the Ts (WTJ: %d/%d).", name, wtjCount[id],PTB_WTJKICK)

                                        engclient_cmd(id,"jointeam","1")

                                        doTypesay(text, 5, 255, 50, 0)
                                        say(text)
                                }
                                else if (PTB_TELLWTJ) {
                                        format(text, 255, "^x04[Xmastime] ^x01The CTs are strong enough, ^x04%s (WTJ: %d/%d).", name, wtjCount[id],PTB_WTJKICK)
                                        doTypesay(text, 5, 0, 50, 255)
                                        say(text)
#if !defined MANUAL_SWITCH
                                        engclient_cmd(id,"chooseteam") // display menu again
#endif
                                }
                        }
                        else {
                                if (wtjCount[id]>=PTB_WTJAUTO) {
                                        manageWtjFile(id)
                                        format(text, 255, "^x04[Xmastime] ^x01Forcing ^x03%s ^x01to the CTs (WTJ: %d/%d).", name, wtjCount[id],PTB_WTJKICK)

                                        engclient_cmd(id,"jointeam","2")

                                        doTypesay(text, 5, 0, 50, 255)
                                        say(text)
                                }
                                else if (PTB_TELLWTJ) {
                                        format(text, 255, "^x04[Xmastime] ^x01The Ts are strong enough, ^x04%s (WTJ: %d/%d).", name, wtjCount[id],PTB_WTJKICK)
                                        doTypesay(text, 5, 255, 50, 0)
                                        say(text)
#if !defined MANUAL_SWITCH
                                        engclient_cmd(id,"chooseteam") // display menu again
#endif
                                }
                        }
                        return PLUGIN_HANDLED
                }
                // check for maximum team size
                if (teamCounts[iNewTeam] >= PTB_MAXSIZE) {
                        CC_SendMessage(id, "^x04[Xmastime] ^x01Maximum team size prohibits team join.")
#if !defined MANUAL_SWITCH
                        engclient_cmd(id,"chooseteam") // display menu again
#endif
                        return PLUGIN_HANDLED
                }
                // check team size difference limits
                if ( teamCounts[iNewTeam]-teamCounts[opposingTeam] >= PTB_MAXDIFF) {
                        CC_SendMessage(id, "^x04[Xmastime] ^x01Maximum team size difference prohibits team join.")
#if !defined MANUAL_SWITCH
                        engclient_cmd(id,"chooseteam") // display menu again
#endif
                        return PLUGIN_HANDLED
                }
                return PLUGIN_CONTINUE // OK! He can join to the oppsoite team!!!
        }

        // He is choosing the AUTO-SELECT but he was already in game (He wants to play fair!)
        if (iNewTeam==AUTO_TEAM&&(iOldTeam==CTS||iOldTeam==TS)) {
                //say("Changing team automatically.")
                new opposingTeam = (iOldTeam==CTS) ? TS : CTS
                if (teamCounts[opposingTeam] && ( (teamCounts[opposingTeam]>=PTB_MAXSIZE)
                                || (iOldTeam==loserTeam) || (!loserTeam&&teamCounts[iOldTeam]<=teamCounts[opposingTeam])
                                || (teamCounts[opposingTeam]+1-teamCounts[iOldTeam]>=PTB_MAXDIFF)) ) {
                        CC_SendMessage(id, "^x04[Xmastime] ^x01You have better stay in your current team...")
                        return PLUGIN_HANDLED
                }
                CC_SendMessage(id, "^x04[Xmastime] ^x01You have been auto-assigned...")

                engclient_cmd(id,"jointeam",(opposingTeam==CTS)?"2":"1")

                return PLUGIN_HANDLED
        }
        // He is choosing the team for the first time with AUTO-SELECT (What a nice kid!)
        if (iNewTeam==AUTO_TEAM) {
                /* this is the "always smaller team" version
                if (teamCounts[CTS] < teamCounts[TS] || teamCounts[TS] >= PTB_MAXSIZE) iNewTeam = CTS
                else if (teamCounts[TS] < teamCounts[CTS] || teamCounts[CTS] >= PTB_MAXSIZE) iNewTeam = TS
                // both teams have same size ...
                else if (winnerTeam && teamCounts[loserTeam]<PTB_MAXSIZE) iNewTeam = loserTeam
                else if (teamCounts[TS] >= PTB_MAXSIZE) iNewTeam = CTS
                else if (teamCounts[CTS] >= PTB_MAXSIZE) iNewTeam = TS
                else iNewTeam = (random_num(0,100) < 50) ? CTS : TS
                */
                // this version prefers the losing team (but still honors PTB_MAXDIFF)
                if (teamCounts[CTS] >= PTB_MAXSIZE) iNewTeam = TS
                else if (teamCounts[TS] >= PTB_MAXSIZE) iNewTeam = CTS
                else if (teamCounts[CTS]-teamCounts[TS] >= PTB_MAXDIFF) iNewTeam = TS
                else if (teamCounts[TS]-teamCounts[CTS] >= PTB_MAXDIFF) iNewTeam = CTS
                else if (winnerTeam) iNewTeam = loserTeam
                else if (teamCounts[CTS]<teamCounts[TS]) iNewTeam = CTS
                else if (teamCounts[TS]<teamCounts[CTS]) iNewTeam = TS
                // both teams have same size ...
                else iNewTeam = (random_num(0,100) < 50) ? CTS : TS
                // check for maximum team size
                if (teamCounts[iNewTeam]>=PTB_MAXSIZE) {
                        client_print(id,print_chat,"^x04[Xmastime] Maximum team size prohibits team join.") // ??? - only a spectator???
#if !defined MANUAL_SWITCH
                        engclient_cmd(id,"chooseteam") // display menu again
#endif
                        return PLUGIN_HANDLED
                }
                client_print(id,print_chat,"^x04[Xmastime] You have been auto-assigned...")

                engclient_cmd(id,"jointeam",(iNewTeam==CTS)?"2":"1")

                return PLUGIN_HANDLED
        }
        return PLUGIN_CONTINUE
}

public team_score(){
        new arg[2]
        read_data(1,arg,1)
        teamScores[ ( arg[0] == 'T' ) ? TS : CTS ] = read_data(2)
}

public win_streaks(param[]){
        new winner = param[0]
        new looser = param[1]
        if (winStreaks[winner] < 0) {
                winStreaks[winner] = 1
                winStreaks[looser] = -1
        }
        else {
                winStreaks[winner]++
                winStreaks[looser]--
        }
        actAtEndOfRound()
}

public round_end(){
        new param[12]
        read_data(2,param,8)
        if (param[7]=='c') {//%!MRAD_ctwin
                param[0] = CTS
                param[1] = TS
        }
        else if (param[7]=='t') {//%!MRAD_terwin
                param[0] = TS
                param[1] = CTS
        }
        else
                return // %!MRAD_rounddraw (both teams have left the game)
        set_task(4.5,"win_streaks",0,param,2)
}

public new_round() {
        //if ( floatround(get_cvar_float("mp_roundtime") * 60.0) != read_data(1) ) return
        if ( floatround(get_cvar_float("mp_roundtime") * 60.0,floatround_floor) != read_data(1) ) return
        ++roundCounter
        announceStatus()
}

// Happen only at team select (also auto-join)
public team_join() {
        new arg[32]
        read_data(3,arg,31)
        lastRoundSwitched[ get_user_index(arg) ] = roundCounter
}

// Can happen at begin of round or team select
public team_assign() {
        new arg[2], team
        new i = read_data(1)
        read_data(2,arg,1)
        if ( arg[0] == 'C'  )
                team = CTS
        else if ( arg[0] == 'T' )
                team = TS
        else
                team = UNASSIGNED
        teamCounts[playerTeam[i]]-- // Unregister from old team
        teamCounts[team]++ // Increase ammount in new team
        playerTeam[i] = team // Assign to new
}

public game_restart(){
        roundCounter = 0
        lastSwitchRound = 0
        couldNotSwitchCounter = 0
        teamKills[0] = teamKills[1] = teamKills[2] = 0
        teamDeaths[0] = teamDeaths[1] = teamDeaths[2] = 0
        teamScores[0] = teamScores[1] = teamScores[2] = 0
        winStreaks[0]        = winStreaks[1] = winStreaks[2] = 0
        wtConditions[0] = wtConditions[1] = wtConditions[2] = 0
        validTargetCounts[0] = validTargetCounts[1] = validTargetCounts[2] = 0
        new a = get_maxplayers()
        for (new i = 1; i <= a; ++i){
                kills[i] = 0
                deaths[i] = 0
                wtjCount[i] = 0
                lastRoundSwitched[i] = -999
        }
}

public death_msg(){
        new iWinner = read_data(1)
        new iLoser = read_data(2)
        if ( iWinner < 1 || iWinner > 32 || iLoser < 1 || iLoser > 32 )
                return
        if ( playerTeam[iWinner] == playerTeam[iLoser] )
                return // no TKS!!!
        kills[iWinner]++
        deaths[iLoser]++
        if (PTB_SCALEDOWN <= 1) return
        if (kills[iWinner] + deaths[iWinner] >= PTB_MAXINCIDENTS) {
                kills[iWinner] /= PTB_SCALEDOWN
                deaths[iWinner] /= PTB_SCALEDOWN
        }
        if (kills[iLoser] + deaths[iLoser] >= PTB_MAXINCIDENTS) {
                kills[iLoser] /= PTB_SCALEDOWN
                deaths[iLoser] /= PTB_SCALEDOWN
        }
}

calcTeamScores() {
        teamDeaths[UNASSIGNED] = 0
        teamDeaths[CTS] = 0
        teamDeaths[TS] = 0
        teamKills[UNASSIGNED] = 0
        teamKills[CTS] = 0
        teamKills[TS] = 0

        new team, a = get_maxplayers()
        for (new i = 1; i <= a; ++i) {
                team = playerTeam[i]
                teamKills[team] += kills[i]
                teamDeaths[team] += deaths[i]
        }

        ctKD = fdivWorkaround(float(teamKills[CTS]), float(teamDeaths[CTS]))
        tKD = fdivWorkaround(float(teamKills[TS]), float(teamDeaths[TS]))
}

announceStatus() {
        if (!PTB_ANNOUNCE) return
        checkTeamBalance()
        new text[256]
        if (winnerTeam == TS) {
                format(text, 255, "PTB: The COUNTER-TERRORIST team could use some support.")
                doTypesay(text, 5, 0, 50, 255)
                say("PTB: The COUNTER-TERRORIST team could use some support.")
        }
        else if (winnerTeam == CTS) {
                format(text, 255, "PTB: The TERRORIST team could use some support.")
                doTypesay(text, 5, 255, 50, 0)
                say("PTB: The TERRORIST team could use some support.")
        }
        else if (wtConditions[TS] > wtConditions[CTS]) {
                format(text, 255, "PTB: Observing TERRORIST team advantage.")
                doTypesay(text, 5, 255, 50, 0)
                say("PTB: Observing TERRORIST team advantage.")
        }
        else if (wtConditions[CTS] > wtConditions[TS]) {
                format(text, 255, "PTB: Observing COUNTER-TERRORIST team advantage.")
                doTypesay(text, 5, 0, 50, 255)
                say("PTB: Observing COUNTER-TERRORIST team advantage.")
        }
        else if (PTB_SAYOK) {
                format(text, 255, "PTB: Teams look fine, no action required.")
                doTypesay(text, 5, 200, 100, 0)
                say("PTB: Teams look fine, no action required.")
        }
}

public admin_ptb(id,level,cid) {
        if (!cmd_access(id,level,cid,1))
                return PLUGIN_HANDLED
        new cmd[32], arg[32], lastcmd

        if ( read_argv(1,cmd,31) == 0 ) { // no command - plain amx_ptb
                //console_print(id,"PTB: Ptahhotep's Team Balancer %s", PTB_VERSION)
                //console_print(id,"PTB: ([email protected])")
                checkTeamBalance()
                displayStatistics(id)
                return PLUGIN_HANDLED
        }
        if (equali(cmd, "on") || equal(cmd, "1")) {
                PTB_LIMITJOIN = true
                PTB_SWITCH = true
                PTB_ANNOUNCE = true
                console_print(id,"PTB: Enabled all PTB actions.")
                return PLUGIN_HANDLED
        }
        if (equali(cmd, "off") || equal(cmd, "0")) {
                PTB_SWITCH = false
                PTB_ANNOUNCE = false
                PTB_LIMITJOIN = false
                console_print(id,"PTB: Disabled all PTB actions.")
                return PLUGIN_HANDLED
        }
        if (equal(cmd, "list") || equal(cmd, "help")) {
                console_print(id,"PTB: Available Commands:")
                console_print(id,"PTB: Team Join Control: ^"limitjoin^", ^"limitafter^", ^"limitmin^", ^"maxsize^", ^"autorounds^",")
                console_print(id,"PTB: ^"maxdiff^", ^"wtjauto^", ^"wtjkick^", ^"kick^", ^"savewtj^"")
                console_print(id,"PTB: Team Balancing Actions: ^"switch^", ^"switchafter^", ^"switchmin^", ^"switchfreq^", ^"playerfreq^",")
                console_print(id,"PTB: ^"forceswitch^", ^"deadonly^"")
                console_print(id,"PTB: Team Strength Limits: ^"maxstreak^", ^"maxscore^", ^"minrating^", ^"maxrating^", ^"superrating^"")
                console_print(id,"PTB: Messages: ^"tellwtj^", ^"announce^", ^"sayok^", ^"typesay^"")
                console_print(id,"PTB: Misc: ^"^", ^"status^", ^"list^", ^"help^", ^"on^", ^"off^", ^"save^", ^"load^"")
                console_print(id,"PTB: To view all PTB settings, type ^"amx_ptb status^".")
                console_print(id,"PTB: To view or change a single PTB setting, type ^"amx_ptb <setting> <on|off|value>^".")
                console_print(id,"PTB: For PTB statistics, simply type ^"amx_ptb^".")
                return PLUGIN_HANDLED
        }
        new arglen = read_argv(2,arg,31)
        new status = equal(cmd, "status")

        // team selection control
        if ( status ) console_print(id,"PTB: ---------- Team Selection Control ----------")
       
        // PTB_LIMITJOIN
        if ( (lastcmd = equal(cmd, "limitjoin")) && arglen ) PTB_LIMITJOIN = check_param_bool(arg)
        if ( status ||  lastcmd )        console_print(id,"PTB: (limitjoin) WTJ prevention is %s.", PTB_LIMITJOIN ? "ON" : "OFF")

        // PTB_LIMITAFTER
        if ( (lastcmd = equal(cmd, "limitafter")) && arglen )        PTB_LIMITAFTER = check_param_num(arg,0)
        if ( status || lastcmd )        console_print(id,"PTB: (limitafter) Team limiting starts after %d round(s).", PTB_LIMITAFTER)

        // PTB_LIMITMIN
        if ( (lastcmd = equal(cmd, "limitmin")) && arglen ) PTB_LIMITMIN = check_param_num(arg,0)
        if ( status || lastcmd )        console_print(id,"PTB: (limitmin) Team limiting needs at least %d player(s).", PTB_LIMITMIN)

        // PTB_MAXSIZE
        if ( (lastcmd = equal(cmd, "maxsize")) && arglen )        PTB_MAXSIZE = check_param_num(arg,0)
        if ( status || lastcmd )        console_print(id,"PTB: (maxsize) Maximum team size is %d player(s).", PTB_MAXSIZE)

        // PTB_MAXDIFF
        if ( (lastcmd = equal(cmd, "maxdiff")) && arglen ) PTB_MAXDIFF = check_param_num(arg,1)
        if ( status || lastcmd )        console_print(id,"PTB: (maxdiff) Maximum team size difference is %d.", PTB_MAXDIFF)

        // PTB_AUTOROUNDS
        if ( (lastcmd = equal(cmd, "autorounds")) && arglen )        PTB_AUTOROUNDS = check_param_num(arg,0)
        if ( status || lastcmd )        console_print(id, "PTB: (autorounds) First %d rounds no free team choice.", PTB_AUTOROUNDS)

        // PTB_WTJAUTO
        if ( (lastcmd = equal(cmd, "wtjauto")) && arglen )        PTB_WTJAUTO = check_param_num(arg,0)
        if ( status || lastcmd )        console_print(id,"PTB: (wtjauto) Auto-joining WTJ after %d tr(y/ies).", PTB_WTJAUTO)

        // PTB_WTJKICK
        if ( (lastcmd = equal(cmd, "wtjkick")) && arglen ) PTB_WTJKICK = check_param_num(arg,1)
        if ( status || lastcmd )        console_print(id,"PTB: (wtjauto) Auto-kicking WTJ after %d tr(y/ies).", PTB_WTJKICK)

        // PTB_KICK
        if ( (lastcmd = equal(cmd, "kick")) && arglen ) PTB_KICK = check_param_bool(arg)
        if ( status || lastcmd ) console_print(id,"PTB: (kick) WTJ kicking is %s.", PTB_KICK ? "ON" : "OFF" )

        // PTB_SAVEWTJ
        if (  (lastcmd = equal(cmd, "savewtj")) && arglen ) PTB_SAVEWTJ = check_param_bool(arg)
        if ( status || lastcmd )        console_print(id,"PTB: (savewtj) Saving to wtj.log is %s.", PTB_SAVEWTJ ? "ON" : "OFF");

        // team balancing actions
        if ( status ) console_print(id,"PTB: ---------- Team Balancing Actions ----------")

        // PTB_SWITCH
        if ( (lastcmd = equal(cmd, "switch")) && arglen ) PTB_SWITCH = check_param_bool(arg)
        if ( status || lastcmd ) console_print(id,"PTB: (switch) Team switching is %s.", PTB_SWITCH ? "ON" : "OFF")

        // PTB_SWITCHAFTER
        if ( (lastcmd = equal(cmd, "switchafter")) && arglen ) PTB_SWITCHAFTER = check_param_num(arg,0)
        if ( status || lastcmd ) console_print(id,"PTB: (switchafter) Switching starts after %d round(s).", PTB_SWITCHAFTER)

        // PTB_SWITCHMIN
        if ( (lastcmd = equal(cmd, "switchmin")) && arglen ) PTB_SWITCHMIN = check_param_num(arg,0)
        if ( status || lastcmd ) console_print(id,"PTB: (switchmin) Switching needs at least %d player(s).", PTB_SWITCHMIN)

        // PTB_PLAYERFREQ
        if ( (lastcmd = equal(cmd, "playerfreq")) && arglen )        PTB_PLAYERFREQ = check_param_num(arg,0)
        if ( status || lastcmd )        console_print(id,"PTB: (playerfreq) Individual players are switched every %d round(s) at maximum.", PTB_PLAYERFREQ)

        // PTB_SWITCHFREQ
        if (  (lastcmd = equal(cmd, "switchfreq")) && arglen )        PTB_SWITCHFREQ = check_param_num(arg,1)
        if ( status || lastcmd )        console_print(id,"PTB: (switchfreq) Switch occurs every %d round(s) at maximum.", PTB_SWITCHFREQ)

        // PTB_FORCESWITCH
        if ( (lastcmd = equal(cmd, "forceswitch")) && arglen )        PTB_FORCESWITCH = check_param_num(arg,0)
        if ( status || lastcmd ) console_print(id,"PTB: (forceswitch) Forcing switch after %d unsuccessful switch(es).", PTB_FORCESWITCH)

        // PTB_DEADONLY
        if ( (lastcmd =  equal(cmd, "deadonly")) && arglen )        PTB_DEADONLY = check_param_bool(arg)
        if ( status || lastcmd ) console_print(id,"PTB: (deadonly) Switching dead only is %s.",PTB_DEADONLY ? "ON" : "OFF" )

        // messages
        if ( status ) console_print(id,"PTB: ---------- Messages ----------")

        // PTB_TELLWTJ
        if ( (lastcmd =  equal(cmd, "tellwtj")) && arglen ) PTB_TELLWTJ = check_param_bool(arg)
        if ( status || lastcmd ) console_print(id,"PTB: (tellwtj) Telling about WTJ tries is %s.",PTB_TELLWTJ ? "ON" : "OFF")

        // PTB_ANNOUNCE
        if ( (lastcmd = equal(cmd, "announce")) && arglen ) PTB_ANNOUNCE = check_param_bool(arg)
        if ( status || lastcmd )  console_print(id,"PTB: (announce) Announcements are %s.",PTB_ANNOUNCE ? "ON" : "OFF")

        // PTB_SAYOK
        if ( (lastcmd = equal(cmd, "sayok")) && arglen ) PTB_SAYOK = check_param_bool(arg)
        if ( status || lastcmd ) console_print(id,"PTB: (sayok) ^"OK^" announcements are %s.",PTB_SAYOK ? "ON" : "OFF")

        // PTB_TYPESAY
        if ( (lastcmd = equal(cmd, "typesay")) && arglen ) PTB_TYPESAY = check_param_bool(arg)
        if ( status || lastcmd ) console_print(id,"PTB: (typesay) typesay usage is %s.",PTB_TYPESAY ? "ON" : "OFF")

        // team strength limits
        if ( status ) console_print(id,"PTB: ---------- Team Strength Limits ----------")

        // PTB_MAXSTREAK
        if ( (lastcmd = equal(cmd, "maxstreak")) && arglen ) PTB_MAXSTREAK = check_param_num(arg,1)
        if ( status || lastcmd )        console_print(id,"PTB: (maxstreak) Maximum accepted win streak is %d.", PTB_MAXSTREAK)

        // PTB_MAXSCORE
        if ( (lastcmd = equal(cmd, "maxscore")) && arglen )        PTB_MAXSCORE = check_param_num(arg,1)
        if ( status || lastcmd ) console_print(id,"PTB: (maxscore) Maximum accepted team score difference is %d.", PTB_MAXSCORE)

        // PTB_MINRATING
        if ( (lastcmd = equal(cmd, "minrating")) && arglen ) PTB_MINRATING = check_param_float(arg,1.0)
        if ( status || lastcmd )        console_print(id,"PTB: (minrating) Minimum critical strength rating is %.2f.",PTB_MINRATING)

        // PTB_MAXRATING
        if ( (lastcmd = equal(cmd, "maxrating")) && arglen ) PTB_MAXRATING = check_param_float(arg,1.0)
        if ( status || lastcmd )        console_print(id,"PTB: (maxrating) Maximum critical strength rating is %.2f.",PTB_MAXRATING)

        // PTB_SUPERRATING
        if ( (lastcmd = equal(cmd, "superrating")) && arglen ) PTB_SUPERRATING = check_param_float(arg,1.0)
        if ( status || lastcmd )        console_print(id,"PTB: (superrating) Super critical strength rating is %.2f.",PTB_SUPERRATING)

        // PTB_MAXINCIDENTS
        if ( (lastcmd = equal(cmd, "maxincidents")) && arglen )        PTB_MAXINCIDENTS = check_param_num(arg,1)
        if ( status || lastcmd )        console_print(id,"PTB: (maxincidents) Maximum incidents before internal player score scale down is %d.", PTB_MAXINCIDENTS)

        // PTB_SCALEDOWN
        if ( (lastcmd =  equal(cmd, "scaledown")) && arglen )        PTB_SCALEDOWN = check_param_num(arg,1)
        if ( status || lastcmd )        console_print(id,"PTB: (scaledown) Integer scale down factor for player scores is %d.", PTB_SCALEDOWN)

        // misc
        if ( status ) {
                console_print(id,"PTB: ---------- Misc ----------")
                console_print(id,"PTB: To enable or disable PTB, type ^"admin_ptb <on|1|off|0>^".")
                console_print(id,"PTB: To view or change a single PTB setting, type ^"amx_ptb <setting> <on|off|value>^".")
                console_print(id,"PTB: To view a brief overview of PTB commands, type ^"amx_ptb help^" or ^"amx_ptb list^".")
                console_print(id,"PTB: For PTB statistics, simply type ^"amx_ptb^".")
        }

        return PLUGIN_HANDLED
}

stock displayStatistics(id,bool:toLog = false) {
        //say("displayStatistics")
        new text[256]
        // time
        /*format(text, 255, "PTB: Statistics generated at: %s", lastTeamBalanceCheck)
        if (toLog) log_amx(text)
        console_print(id,text)*/
        // connected players
        format(text, 255, "PTB: Connected players: %d", get_playersnum())
        if (toLog) log_amx(text)
        console_print(id,text)
        // team sizes
        format(text, 255, "PTB: Team sizes: CTs %d, Ts %d", teamCounts[CTS], teamCounts[TS])
        if (toLog) log_amx(text)
        console_print(id,text)
        // team scores
        format(text, 255, "PTB: Team scores: CTs %d, Ts %d", teamScores[CTS], teamScores[TS])
        if (toLog) log_amx(text)
        console_print(id,text)
        // Kills:Deaths
        format(text, 255, "PTB: Team kills:deaths: CTs %d:%d, Ts %d:%d", teamKills[CTS], teamDeaths[CTS], teamKills[TS], teamDeaths[TS])
        if (toLog) log_amx(text)
        console_print(id,text)
        // Kills/Deaths
        format(text, 255, "PTB: Team kills/deaths: CTs %.2f, Ts %.2f", ctKD , tKD        )
        if (toLog) log_amx(text)
        console_print(id,text)
        // strength
        format(text, 255, "PTB: Team strengths: CTs %.2f, Ts %.2f",ctStrength , tStrength        )
        if (toLog) log_amx(text)
        console_print(id,text)
        // rating
        format(text, 255, "PTB: Team ratings: CTs %.2f, Ts %.2f",ctRating,tRating        )
        if (toLog) log_amx(text)
        console_print(id,text)
        // won rounds
        if (winStreaks[CTS] > 0) {
                format(text, 255, "PTB: Last %d round(s) won by CTs.", winStreaks[CTS])
                if (toLog) log_amx(text)
                console_print(id,text)
        }
        else if (winStreaks[TS] > 0) {
                format(text, 255, "PTB: Last %d round(s) won by Ts.", winStreaks[TS])
                if (toLog) log_amx(text)
                console_print(id,text)
        }

        // winning team
        switch(winnerTeam){
                case CTS: format(text, 255, "PTB: The CTs are the winning team.")
                case TS: format(text, 255, "PTB: The Ts are the winning team.")
                default: format(text, 255, "PTB: Teams are balanced.")
        }
        if (toLog) log_amx(text)
        console_print(id,text)

        /*format(text, 255, "PTB: These statistics might be already outdated.")
        if (toLog) log_amx(text)
        console_print(id,text)

        format(text, 255, "PTB: To view a brief overview of PTB commands, type ^"amx_ptb help^" or ^"amx_ptb list^".")
        if (toLog) log_amx(text)
        console_print(id,text)

        format(text, 255, "PTB: To view all PTB settings, type ^"amx_ptb status^".")
        if (toLog) log_amx(text)
        console_print(id,text)*/
}

public client_connect(id){
        kills[id] = 0
        deaths[id] = 0
        isBeingTransfered[id] = false
        playerTeam[id] = UNASSIGNED
        lastRoundSwitched[id] = -999
        wtjCount[id] = 0
        get_user_info(id,"_vgui_menus",clientVGUIMenu[id],1)
        clientVGUIMenu[id][0] = '0'

        return PLUGIN_CONTINUE
}

public client_disconnect(id) {
        kills[id] = 0
        deaths[id] = 0
        isBeingTransfered[id] = false
        playerTeam[id] = UNASSIGNED
        lastRoundSwitched[id] = -999
        wtjCount[id] = 0
        // redundant team size check
        teamCounts[UNASSIGNED] = 0
        teamCounts[CTS] = 0
        teamCounts[TS] = 0

        new a = get_maxplayers()
        for (new i = 1; i <= a; ++i)
                ++teamCounts[playerTeam[i]]


        if (clientVGUIMenu[id][0] != '0') {
                set_user_info( id, "_vgui_menus", clientVGUIMenu[id] )
                clientVGUIMenu[id][0] = '0'
        }

        return PLUGIN_CONTINUE
}

Przeczytaj cały wpis

Odnośnik do komentarza
Udostępnij na innych stronach

Gość
Ten temat został zamknięty. Brak możliwości dodania odpowiedzi.
 Udostępnij

  • Ostatnio przeglądający   0 użytkowników

    • Brak zarejestrowanych użytkowników przeglądających tę stronę.
×
×
  • Dodaj nową pozycję...