// IW6 GSC SOURCE
// Generated by https://github.com/xensik/gsc-tool

main()
{
    if ( getdvar( "mapname" ) == "mp_background" )
        return;

    maps\mp\gametypes\_globallogic::init();
    maps\mp\gametypes\_callbacksetup::setupcallbacks();
    maps\mp\gametypes\_globallogic::setupcallbacks();

    if ( isusingmatchrulesdata() )
    {
        level.initializematchrules = ::initializematchrules;
        [[ level.initializematchrules ]]();
        level thread maps\mp\_utility::reinitializematchrulesonmigration();
    }
    else
    {
        maps\mp\_utility::registerroundswitchdvar( level.gametype, 3, 0, 9 );
        maps\mp\_utility::registertimelimitdvar( level.gametype, 2.5 );
        maps\mp\_utility::registerscorelimitdvar( level.gametype, 1 );
        maps\mp\_utility::registerroundlimitdvar( level.gametype, 0 );
        maps\mp\_utility::registerwinlimitdvar( level.gametype, 4 );
        maps\mp\_utility::registernumlivesdvar( level.gametype, 1 );
        maps\mp\_utility::registerhalftimedvar( level.gametype, 0 );
        level.matchrules_damagemultiplier = 0;
        level.matchrules_vampirism = 0;
    }

    level.objectivebased = 1;
    level.teambased = 1;
    level.nobuddyspawns = 1;
    level.onprecachegametype = ::onprecachegametype;
    level.onstartgametype = ::onstartgametype;
    level.getspawnpoint = ::getspawnpoint;
    level.onspawnplayer = ::onspawnplayer;
    level.onplayerkilled = ::onplayerkilled;
    level.ondeadevent = ::ondeadevent;
    level.ononeleftevent = ::ononeleftevent;
    level.ontimelimit = ::ontimelimit;
    level.onnormaldeath = ::onnormaldeath;
    level.initgametypeawards = ::initgametypeawards;
    level.gamemodemaydropweapon = maps\mp\_utility::isplayeroutsideofanybombsite;
    level.allowlatecomers = 0;

    if ( level.matchrules_damagemultiplier || level.matchrules_vampirism )
        level.modifyplayerdamage = maps\mp\gametypes\_damage::gamemodemodifyplayerdamage;

    game["dialog"]["gametype"] = "searchdestroy";

    if ( getdvarint( "g_hardcore" ) )
        game["dialog"]["gametype"] = "hc_" + game["dialog"]["gametype"];
    else if ( getdvarint( "camera_thirdPerson" ) )
        game["dialog"]["gametype"] = "thirdp_" + game["dialog"]["gametype"];
    else if ( getdvarint( "scr_diehard" ) )
        game["dialog"]["gametype"] = "dh_" + game["dialog"]["gametype"];
    else if ( getdvarint( "scr_" + level.gametype + "_promode" ) )
        game["dialog"]["gametype"] = game["dialog"]["gametype"] + "_pro";

    game["dialog"]["offense_obj"] = "obj_destroy";
    game["dialog"]["defense_obj"] = "obj_defend";
    game["dialog"]["lead_lost"] = "null";
    game["dialog"]["lead_tied"] = "null";
    game["dialog"]["lead_taken"] = "null";
    setomnvar( "ui_bomb_timer_endtime", 0 );
}

initializematchrules()
{
    maps\mp\_utility::setcommonrulesfrommatchrulesdata();
    var_0 = getmatchrulesdata( "sdData", "roundLength" );
    setdynamicdvar( "scr_sd_timelimit", var_0 );
    maps\mp\_utility::registertimelimitdvar( "sd", var_0 );
    var_1 = getmatchrulesdata( "sdData", "roundSwitch" );
    setdynamicdvar( "scr_sd_roundswitch", var_1 );
    maps\mp\_utility::registerroundswitchdvar( "sd", var_1, 0, 9 );
    var_2 = getmatchrulesdata( "commonOption", "scoreLimit" );
    setdynamicdvar( "scr_sd_winlimit", var_2 );
    maps\mp\_utility::registerwinlimitdvar( "sd", var_2 );
    setdynamicdvar( "scr_sd_bombtimer", getmatchrulesdata( "sdData", "bombTimer" ) );
    setdynamicdvar( "scr_sd_planttime", getmatchrulesdata( "sdData", "plantTime" ) );
    setdynamicdvar( "scr_sd_defusetime", getmatchrulesdata( "sdData", "defuseTime" ) );
    setdynamicdvar( "scr_sd_multibomb", getmatchrulesdata( "sdData", "multiBomb" ) );
    setdynamicdvar( "scr_sd_roundlimit", 0 );
    maps\mp\_utility::registerroundlimitdvar( "sd", 0 );
    setdynamicdvar( "scr_sd_scorelimit", 1 );
    maps\mp\_utility::registerscorelimitdvar( "sd", 1 );
    setdynamicdvar( "scr_sd_halftime", 0 );
    maps\mp\_utility::registerhalftimedvar( "sd", 0 );
    setdynamicdvar( "scr_sd_promode", 0 );
}

onprecachegametype()
{
    game["bomb_dropped_sound"] = "mp_war_objective_lost";
    game["bomb_recovered_sound"] = "mp_war_objective_taken";
}

onstartgametype()
{
    if ( !isdefined( game["switchedsides"] ) )
        game["switchedsides"] = 0;

    if ( game["switchedsides"] )
    {
        var_0 = game["attackers"];
        var_1 = game["defenders"];
        game["attackers"] = var_1;
        game["defenders"] = var_0;
    }

    setclientnamemode( "manual_change" );
    level._effect["bomb_explosion"] = loadfx( "fx/explosions/tanker_explosion" );
    level._effect["vehicle_explosion"] = loadfx( "fx/explosions/small_vehicle_explosion_new" );
    level._effect["building_explosion"] = loadfx( "fx/explosions/building_explosion_gulag" );
    maps\mp\_utility::setobjectivetext( game["attackers"], &"OBJECTIVES_SD_ATTACKER" );
    maps\mp\_utility::setobjectivetext( game["defenders"], &"OBJECTIVES_SD_DEFENDER" );

    if ( level.splitscreen )
    {
        maps\mp\_utility::setobjectivescoretext( game["attackers"], &"OBJECTIVES_SD_ATTACKER" );
        maps\mp\_utility::setobjectivescoretext( game["defenders"], &"OBJECTIVES_SD_DEFENDER" );
    }
    else
    {
        maps\mp\_utility::setobjectivescoretext( game["attackers"], &"OBJECTIVES_SD_ATTACKER_SCORE" );
        maps\mp\_utility::setobjectivescoretext( game["defenders"], &"OBJECTIVES_SD_DEFENDER_SCORE" );
    }

    maps\mp\_utility::setobjectivehinttext( game["attackers"], &"OBJECTIVES_SD_ATTACKER_HINT" );
    maps\mp\_utility::setobjectivehinttext( game["defenders"], &"OBJECTIVES_SD_DEFENDER_HINT" );
    initspawns();
    var_2[0] = "sd";
    var_2[1] = "bombzone";
    var_2[2] = "blocker";
    maps\mp\gametypes\_gameobjects::main( var_2 );
    updategametypedvars();
    setspecialloadout();
    thread bombs();
}

initspawns()
{
    level.spawnmins = ( 0, 0, 0 );
    level.spawnmaxs = ( 0, 0, 0 );
    maps\mp\gametypes\_spawnlogic::addstartspawnpoints( "mp_sd_spawn_attacker" );
    maps\mp\gametypes\_spawnlogic::addstartspawnpoints( "mp_sd_spawn_defender" );
    level.mapcenter = maps\mp\gametypes\_spawnlogic::findboxcenter( level.spawnmins, level.spawnmaxs );
    setmapcenter( level.mapcenter );
}

getspawnpoint()
{
    var_0 = "mp_sd_spawn_defender";

    if ( self.pers["team"] == game["attackers"] )
        var_0 = "mp_sd_spawn_attacker";

    var_1 = maps\mp\gametypes\_spawnlogic::getspawnpointarray( var_0 );
    var_2 = maps\mp\gametypes\_spawnlogic::getspawnpoint_startspawn( var_1 );
    return var_2;
}

onspawnplayer()
{
    if ( maps\mp\_utility::isgameparticipant( self ) )
    {
        self.isplanting = 0;
        self.isdefusing = 0;
        self.isbombcarrier = 0;
    }

    if ( level.multibomb && self.pers["team"] == game["attackers"] )
        self setclientomnvar( "ui_carrying_bomb", 1 );
    else
        self setclientomnvar( "ui_carrying_bomb", 0 );

    maps\mp\_utility::setextrascore0( 0 );

    if ( isdefined( self.pers["plants"] ) )
        maps\mp\_utility::setextrascore0( self.pers["plants"] );

    level notify( "spawned_player" );
}

onplayerkilled( var_0, var_1, var_2, var_3, var_4, var_5, var_6, var_7, var_8, var_9 )
{
    self setclientomnvar( "ui_carrying_bomb", 0 );
    thread checkallowspectating();
}

checkallowspectating()
{
    wait 0.05;
    var_0 = 0;

    if ( !level.alivecount[game["attackers"]] )
    {
        level.spectateoverride[game["attackers"]].allowenemyspectate = 1;
        var_0 = 1;
    }

    if ( !level.alivecount[game["defenders"]] )
    {
        level.spectateoverride[game["defenders"]].allowenemyspectate = 1;
        var_0 = 1;
    }

    if ( var_0 )
        maps\mp\gametypes\_spectating::updatespectatesettings();
}

sd_endgame( var_0, var_1 )
{
    foreach ( var_3 in level.players )
    {
        if ( !isai( var_3 ) )
            var_3 setclientomnvar( "ui_bomb_planting_defusing", 0 );
    }

    level.finalkillcam_winner = var_0;

    if ( var_1 == game["end_reason"]["target_destroyed"] || var_1 == game["end_reason"]["bomb_defused"] )
    {
        var_5 = 1;

        foreach ( var_7 in level.bombzones )
        {
            if ( isdefined( level.finalkillcam_killcamentityindex[var_0] ) && level.finalkillcam_killcamentityindex[var_0] == var_7.killcamentnum )
            {
                var_5 = 0;
                break;
            }
        }

        if ( var_5 )
            maps\mp\gametypes\_damage::erasefinalkillcam();
    }

    thread maps\mp\gametypes\_gamelogic::endgame( var_0, var_1 );
}

ondeadevent( var_0 )
{
    if ( level.bombexploded || level.bombdefused )
        return;

    if ( var_0 == "all" )
    {
        if ( level.bombplanted )
            sd_endgame( game["attackers"], game["end_reason"][game["defenders"] + "_eliminated"] );
        else
            sd_endgame( game["defenders"], game["end_reason"][game["attackers"] + "_eliminated"] );
    }
    else if ( var_0 == game["attackers"] )
    {
        if ( level.bombplanted )
            return;

        level thread sd_endgame( game["defenders"], game["end_reason"][game["attackers"] + "_eliminated"] );
    }
    else if ( var_0 == game["defenders"] )
        level thread sd_endgame( game["attackers"], game["end_reason"][game["defenders"] + "_eliminated"] );
}

ononeleftevent( var_0 )
{
    if ( level.bombexploded || level.bombdefused )
        return;

    var_1 = maps\mp\_utility::getlastlivingplayer( var_0 );
    var_1 thread givelastonteamwarning();
}

onnormaldeath( var_0, var_1, var_2 )
{
    var_3 = maps\mp\gametypes\_rank::getscoreinfovalue( "kill" );
    var_4 = var_0.team;

    if ( game["state"] == "postgame" && ( var_0.team == game["defenders"] || !level.bombplanted ) )
        var_1.finalkill = 1;

    if ( var_0.isplanting )
    {
        thread maps\mp\_matchdata::logkillevent( var_2, "planting" );
        var_1 maps\mp\_utility::incpersstat( "defends", 1 );
        var_1 maps\mp\gametypes\_persistence::statsetchild( "round", "defends", var_1.pers["defends"] );
    }
    else if ( var_0.isbombcarrier )
    {
        var_1 maps\mp\_utility::incplayerstat( "bombcarrierkills", 1 );
        thread maps\mp\_matchdata::logkillevent( var_2, "carrying" );
    }
    else if ( var_0.isdefusing )
    {
        thread maps\mp\_matchdata::logkillevent( var_2, "defusing" );
        var_1 maps\mp\_utility::incpersstat( "defends", 1 );
        var_1 maps\mp\gametypes\_persistence::statsetchild( "round", "defends", var_1.pers["defends"] );
    }

    if ( var_1.isbombcarrier )
        var_1 maps\mp\_utility::incplayerstat( "killsasbombcarrier", 1 );
}

givelastonteamwarning()
{
    self endon( "death" );
    self endon( "disconnect" );
    level endon( "game_ended" );
    maps\mp\_utility::waittillrecoveredhealth( 3 );
    var_0 = maps\mp\_utility::getotherteam( self.pers["team"] );
    level thread maps\mp\_utility::teamplayercardsplash( "callout_lastteammemberalive", self, self.pers["team"] );
    level thread maps\mp\_utility::teamplayercardsplash( "callout_lastenemyalive", self, var_0 );
    level notify( "last_alive", self );
    maps\mp\gametypes\_missions::lastmansd();
}

ontimelimit()
{
    sd_endgame( game["defenders"], game["end_reason"]["time_limit_reached"] );

    foreach ( var_1 in level.players )
    {
        if ( isdefined( var_1.bombplantweapon ) )
        {
            var_1 takeweapon( var_1.bombplantweapon );
            break;
        }
    }
}

updategametypedvars()
{
    level.planttime = maps\mp\_utility::dvarfloatvalue( "planttime", 5, 0, 20 );
    level.defusetime = maps\mp\_utility::dvarfloatvalue( "defusetime", 5, 0, 20 );
    level.bombtimer = maps\mp\_utility::dvarfloatvalue( "bombtimer", 45, 1, 300 );
    level.multibomb = maps\mp\_utility::dvarintvalue( "multibomb", 0, 0, 1 );
}

removebombzonec( var_0 )
{
    var_1 = [];
    var_2 = getentarray( "script_brushmodel", "classname" );

    foreach ( var_4 in var_2 )
    {
        if ( isdefined( var_4.script_gameobjectname ) && var_4.script_gameobjectname == "bombzone" )
        {
            foreach ( var_6 in var_0 )
            {
                if ( distance( var_4.origin, var_6.origin ) < 100 && issubstr( tolower( var_6.script_label ), "c" ) )
                {
                    var_6.relatedbrushmodel = var_4;
                    var_1[var_1.size] = var_6;
                    break;
                }
            }
        }
    }

    foreach ( var_10 in var_1 )
    {
        var_10.relatedbrushmodel delete();
        var_11 = getentarray( var_10.target, "targetname" );

        foreach ( var_13 in var_11 )
            var_13 delete();

        var_10 delete();
    }

    return common_scripts\utility::array_removeundefined( var_0 );
}

bombs()
{
    level.bombplanted = 0;
    level.bombdefused = 0;
    level.bombexploded = 0;
    var_0 = getent( "sd_bomb_pickup_trig", "targetname" );

    if ( !isdefined( var_0 ) )
    {
        common_scripts\utility::error( "No sd_bomb_pickup_trig trigger found in map." );
        return;
    }

    var_1[0] = getent( "sd_bomb", "targetname" );

    if ( !isdefined( var_1[0] ) )
    {
        common_scripts\utility::error( "No sd_bomb script_model found in map." );
        return;
    }

    var_1[0] setmodel( "weapon_briefcase_bomb_iw6" );

    if ( !level.multibomb )
    {
        level.sdbomb = maps\mp\gametypes\_gameobjects::createcarryobject( game["attackers"], var_0, var_1, ( 0, 0, 32 ) );
        level.sdbomb maps\mp\gametypes\_gameobjects::allowcarry( "friendly" );
        level.sdbomb maps\mp\gametypes\_gameobjects::set2dicon( "friendly", "waypoint_bomb" );
        level.sdbomb maps\mp\gametypes\_gameobjects::set3dicon( "friendly", "waypoint_bomb" );
        level.sdbomb maps\mp\gametypes\_gameobjects::setvisibleteam( "friendly" );
        level.sdbomb.allowweapons = 1;
        level.sdbomb.onpickup = ::onpickup;
        level.sdbomb.ondrop = ::ondrop;
    }
    else
    {
        var_0 delete();
        var_1[0] delete();
    }

    level.bombzones = [];
    var_2 = getentarray( "bombzone", "targetname" );
    var_2 = removebombzonec( var_2 );

    for ( var_3 = 0; var_3 < var_2.size; var_3++ )
    {
        var_0 = var_2[var_3];
        var_1 = getentarray( var_2[var_3].target, "targetname" );
        var_4 = maps\mp\gametypes\_gameobjects::createuseobject( game["defenders"], var_0, var_1, ( 0, 0, 64 ) );
        var_4.id = "bomb_zone";
        var_4 maps\mp\gametypes\_gameobjects::allowuse( "enemy" );
        var_4 maps\mp\gametypes\_gameobjects::setusetime( level.planttime );
        var_4 maps\mp\gametypes\_gameobjects::setwaitweaponchangeonuse( 0 );
        var_4 maps\mp\gametypes\_gameobjects::setusetext( &"MP_PLANTING_EXPLOSIVE" );
        var_4 maps\mp\gametypes\_gameobjects::setusehinttext( &"PLATFORM_HOLD_TO_PLANT_EXPLOSIVES" );

        if ( !level.multibomb )
            var_4 maps\mp\gametypes\_gameobjects::setkeyobject( level.sdbomb );

        var_5 = var_4 maps\mp\gametypes\_gameobjects::getlabel();
        var_4.label = var_5;
        var_4 maps\mp\gametypes\_gameobjects::set2dicon( "friendly", "waypoint_defend" + var_5 );
        var_4 maps\mp\gametypes\_gameobjects::set3dicon( "friendly", "waypoint_defend" + var_5 );
        var_4 maps\mp\gametypes\_gameobjects::set2dicon( "enemy", "waypoint_target" + var_5 );
        var_4 maps\mp\gametypes\_gameobjects::set3dicon( "enemy", "waypoint_target" + var_5 );
        var_4 maps\mp\gametypes\_gameobjects::setvisibleteam( "any" );
        var_4.onbeginuse = ::onbeginuse;
        var_4.onenduse = ::onenduse;
        var_4.onuse = ::onuseplantobject;
        var_4.oncantuse = ::oncantuse;
        var_4.useweapon = "briefcase_bomb_mp";

        for ( var_6 = 0; var_6 < var_1.size; var_6++ )
        {
            if ( isdefined( var_1[var_6].script_exploder ) )
            {
                var_4.exploderindex = var_1[var_6].script_exploder;
                var_1[var_6] thread setupkillcament( var_4 );
                break;
            }
        }

        level.bombzones[level.bombzones.size] = var_4;
        var_4.bombdefusetrig = getent( var_1[0].target, "targetname" );
        var_4.bombdefusetrig.origin = var_4.bombdefusetrig.origin + ( 0, 0, -10000 );
        var_4.bombdefusetrig.label = var_5;
    }

    for ( var_3 = 0; var_3 < level.bombzones.size; var_3++ )
    {
        var_7 = [];

        for ( var_8 = 0; var_8 < level.bombzones.size; var_8++ )
        {
            if ( var_8 != var_3 )
                var_7[var_7.size] = level.bombzones[var_8];
        }

        level.bombzones[var_3].otherbombzones = var_7;
    }
}

setupkillcament( var_0 )
{
    var_1 = spawn( "script_origin", self.origin );
    var_1.angles = self.angles;
    var_1 rotateyaw( -45, 0.05 );
    wait 0.05;
    var_2 = undefined;

    if ( isdefined( level.srkillcamoverrideposition ) && isdefined( level.srkillcamoverrideposition[var_0.label] ) )
        var_2 = level.srkillcamoverrideposition[var_0.label];
    else
    {
        var_3 = self.origin + ( 0, 0, 5 );
        var_4 = self.origin + anglestoforward( var_1.angles ) * 100 + ( 0, 0, 128 );
        var_5 = bullettrace( var_3, var_4, 0, self );
        var_2 = var_5["position"];
    }

    self.killcament = spawn( "script_model", var_2 );
    self.killcament setscriptmoverkillcam( "explosive" );
    var_0.killcamentnum = self.killcament getentitynumber();
    var_1 delete();
}

onbeginuse( var_0 )
{
    if ( maps\mp\gametypes\_gameobjects::isfriendlyteam( var_0.pers["team"] ) )
    {
        var_0 maps\mp\_utility::notify_enemy_bots_bomb_used( "defuse" );
        var_0.isdefusing = 1;

        if ( isdefined( level.sdbombmodel ) )
            level.sdbombmodel hide();

        var_0 thread startnpcbombusesound( "briefcase_bomb_defuse_mp", "weap_suitcase_defuse_button" );
    }
    else
    {
        var_0 maps\mp\_utility::notify_enemy_bots_bomb_used( "plant" );
        var_0.isplanting = 1;
        var_0.bombplantweapon = self.useweapon;
        var_0 thread startnpcbombusesound( "briefcase_bomb_mp", "weap_suitcase_raise_button" );

        if ( level.multibomb )
        {
            for ( var_1 = 0; var_1 < self.otherbombzones.size; var_1++ )
            {
                self.otherbombzones[var_1] maps\mp\gametypes\_gameobjects::allowuse( "none" );
                self.otherbombzones[var_1] maps\mp\gametypes\_gameobjects::setvisibleteam( "friendly" );
            }
        }
    }
}

onenduse( var_0, var_1, var_2 )
{
    if ( !isdefined( var_1 ) )
        return;

    var_1.bombplantweapon = undefined;

    if ( isalive( var_1 ) )
    {
        var_1.isdefusing = 0;
        var_1.isplanting = 0;
    }

    if ( isplayer( var_1 ) )
    {
        var_1 setclientomnvar( "ui_bomb_planting_defusing", 0 );
        var_1.ui_bomb_planting_defusing = undefined;
    }

    if ( maps\mp\gametypes\_gameobjects::isfriendlyteam( var_1.pers["team"] ) )
    {
        if ( isdefined( level.sdbombmodel ) && !var_2 )
            level.sdbombmodel show();
    }
    else if ( level.multibomb && !var_2 )
    {
        for ( var_3 = 0; var_3 < self.otherbombzones.size; var_3++ )
        {
            self.otherbombzones[var_3] maps\mp\gametypes\_gameobjects::allowuse( "enemy" );
            self.otherbombzones[var_3] maps\mp\gametypes\_gameobjects::setvisibleteam( "any" );
        }
    }
}

startnpcbombusesound( var_0, var_1 )
{
    self endon( "death" );
    self endon( "stopNpcBombSound" );

    if ( maps\mp\_utility::isanymlgmatch() )
        return;

    var_2 = "";

    while ( var_2 != var_0 )
        self waittill( "weapon_change", var_2 );

    self playsoundtoteam( var_1, self.team, self );
    var_3 = maps\mp\_utility::getotherteam( self.team );
    self playsoundtoteam( var_1, var_3 );
    self waittill( "weapon_change" );
    self notify( "stopNpcBombSound" );
}

oncantuse( var_0 )
{
    var_0 iprintlnbold( &"MP_CANT_PLANT_WITHOUT_BOMB" );
}

onuseplantobject( var_0 )
{
    if ( !maps\mp\gametypes\_gameobjects::isfriendlyteam( var_0.pers["team"] ) )
    {
        level thread bombplanted( self, var_0 );

        for ( var_1 = 0; var_1 < level.bombzones.size; var_1++ )
        {
            if ( level.bombzones[var_1] == self )
                continue;

            level.bombzones[var_1] maps\mp\gametypes\_gameobjects::disableobject();
        }

        var_0 playsound( "mp_bomb_plant" );
        var_0 notify( "bomb_planted" );
        var_0 notify( "objective", "plant" );
        var_0 maps\mp\_utility::incpersstat( "plants", 1 );
        var_0 maps\mp\gametypes\_persistence::statsetchild( "round", "plants", var_0.pers["plants"] );
        var_0 maps\mp\_utility::setextrascore0( var_0.pers["plants"] );

        if ( isdefined( level.sd_loadout ) && isdefined( level.sd_loadout[var_0.team] ) )
            var_0 thread removebombcarrierclass();

        maps\mp\_utility::leaderdialog( "bomb_planted" );
        level thread maps\mp\_utility::teamplayercardsplash( "callout_bombplanted", var_0 );
        level.bombowner = var_0;
        var_0 thread maps\mp\gametypes\_hud_message::splashnotify( "plant", maps\mp\gametypes\_rank::getscoreinfovalue( "plant" ) );
        var_0 thread maps\mp\gametypes\_rank::xpeventpopup( "plant" );
        var_0 thread maps\mp\gametypes\_rank::giverankxp( "plant" );
        var_0.bombplantedtime = gettime();
        maps\mp\gametypes\_gamescore::giveplayerscore( "plant", var_0 );

        if ( isplayer( var_0 ) )
            var_0 thread maps\mp\_matchdata::loggameevent( "plant", var_0.origin );
    }
}

applybombcarrierclass()
{
    self endon( "death" );
    self endon( "disconnect" );
    level endon( "game_ended" );

    if ( isdefined( self.iscarrying ) && self.iscarrying == 1 )
    {
        self notify( "force_cancel_placement" );
        wait 0.05;
    }

    while ( self ismantling() )
        wait 0.05;

    while ( !self isonground() )
        wait 0.05;

    if ( maps\mp\_utility::isjuggernaut() )
    {
        self notify( "lost_juggernaut" );
        wait 0.05;
    }

    self.pers["gamemodeLoadout"] = level.sd_loadout[self.team];

    if ( isdefined( self.setspawnpoint ) )
        maps\mp\perks\_perkfunctions::deleteti( self.setspawnpoint );

    var_0 = spawn( "script_model", self.origin );
    var_0.angles = self.angles;
    var_0.playerspawnpos = self.origin;
    var_0.notti = 1;
    self.setspawnpoint = var_0;
    self.gamemode_chosenclass = self.class;
    self.pers["class"] = "gamemode";
    self.pers["lastClass"] = "gamemode";
    self.class = "gamemode";
    self.lastclass = "gamemode";
    self notify( "faux_spawn" );
    self.gameobject_fauxspawn = 1;
    self.faux_spawn_stance = self getstance();
    thread maps\mp\gametypes\_playerlogic::spawnplayer( 1 );
}

removebombcarrierclass()
{
    self endon( "death" );
    self endon( "disconnect" );
    level endon( "game_ended" );

    if ( isdefined( self.iscarrying ) && self.iscarrying == 1 )
    {
        self notify( "force_cancel_placement" );
        wait 0.05;
    }

    while ( self ismantling() )
        wait 0.05;

    while ( !self isonground() )
        wait 0.05;

    if ( maps\mp\_utility::isjuggernaut() )
    {
        self notify( "lost_juggernaut" );
        wait 0.05;
    }

    self.pers["gamemodeLoadout"] = undefined;

    if ( isdefined( self.setspawnpoint ) )
        maps\mp\perks\_perkfunctions::deleteti( self.setspawnpoint );

    var_0 = spawn( "script_model", self.origin );
    var_0.angles = self.angles;
    var_0.playerspawnpos = self.origin;
    var_0.notti = 1;
    self.setspawnpoint = var_0;
    self notify( "faux_spawn" );
    self.faux_spawn_stance = self getstance();
    thread maps\mp\gametypes\_playerlogic::spawnplayer( 1 );
}

onusedefuseobject( var_0 )
{
    var_0 notify( "bomb_defused" );
    var_0 notify( "objective", "defuse" );
    level thread bombdefused();
    maps\mp\gametypes\_gameobjects::disableobject();
    maps\mp\_utility::leaderdialog( "bomb_defused_" + var_0.team );
    level thread maps\mp\_utility::teamplayercardsplash( "callout_bombdefused", var_0 );

    if ( isdefined( level.bombowner ) && level.bombowner.bombplantedtime + 3000 + level.defusetime * 1000 > gettime() && maps\mp\_utility::isreallyalive( level.bombowner ) )
        var_0 thread maps\mp\gametypes\_hud_message::splashnotify( "ninja_defuse", maps\mp\gametypes\_rank::getscoreinfovalue( "defuse" ) );
    else
        var_0 thread maps\mp\gametypes\_hud_message::splashnotify( "defuse", maps\mp\gametypes\_rank::getscoreinfovalue( "defuse" ) );

    var_0 thread maps\mp\gametypes\_rank::xpeventpopup( "defuse" );
    var_0 thread maps\mp\gametypes\_rank::giverankxp( "defuse" );
    maps\mp\gametypes\_gamescore::giveplayerscore( "defuse", var_0 );
    var_0 maps\mp\_utility::incpersstat( "defuses", 1 );
    var_0 maps\mp\gametypes\_persistence::statsetchild( "round", "defuses", var_0.pers["defuses"] );

    if ( isplayer( var_0 ) )
        var_0 thread maps\mp\_matchdata::loggameevent( "defuse", var_0.origin );
}

ondrop( var_0 )
{
    level notify( "bomb_dropped" );
    setomnvar( "ui_bomb_carrier", -1 );
    maps\mp\gametypes\_gameobjects::set2dicon( "friendly", "waypoint_bomb" );
    maps\mp\gametypes\_gameobjects::set3dicon( "friendly", "waypoint_bomb" );
    maps\mp\_utility::playsoundonplayers( game["bomb_dropped_sound"], game["attackers"] );
}

onpickup( var_0 )
{
    var_0.isbombcarrier = 1;
    var_0 maps\mp\_utility::incplayerstat( "bombscarried", 1 );

    if ( isplayer( var_0 ) )
        var_0 thread maps\mp\_matchdata::loggameevent( "pickup", var_0.origin );

    var_0 setclientomnvar( "ui_carrying_bomb", 1 );
    setomnvar( "ui_bomb_carrier", var_0 getentitynumber() );
    maps\mp\gametypes\_gameobjects::set2dicon( "friendly", "waypoint_escort" );
    maps\mp\gametypes\_gameobjects::set3dicon( "friendly", "waypoint_escort" );

    if ( isdefined( level.sd_loadout ) && isdefined( level.sd_loadout[var_0.team] ) )
        var_0 thread applybombcarrierclass();

    if ( !level.bombdefused )
    {
        maps\mp\_utility::teamplayercardsplash( "callout_bombtaken", var_0, var_0.team );
        maps\mp\_utility::leaderdialog( "bomb_taken", var_0.pers["team"] );
    }

    maps\mp\_utility::playsoundonplayers( game["bomb_recovered_sound"], game["attackers"] );
}

onreset()
{

}

bombplanted( var_0, var_1 )
{
    level notify( "bomb_planted", var_0 );
    maps\mp\gametypes\_gamelogic::pausetimer();
    level.bombplanted = 1;
    var_1 setclientomnvar( "ui_carrying_bomb", 0 );
    setomnvar( "ui_bomb_carrier", -1 );
    var_0.visuals[0] thread maps\mp\gametypes\_gamelogic::playtickingsound();
    level.tickingobject = var_0.visuals[0];
    level.timelimitoverride = 1;
    level.defuseendtime = int( gettime() + level.bombtimer * 1000 );
    setgameendtime( level.defuseendtime );
    setomnvar( "ui_bomb_timer", 1 );

    if ( !level.multibomb )
    {
        level.sdbomb maps\mp\gametypes\_gameobjects::allowcarry( "none" );
        level.sdbomb maps\mp\gametypes\_gameobjects::setvisibleteam( "none" );
        level.sdbomb maps\mp\gametypes\_gameobjects::setdropped();
        level.sdbombmodel = level.sdbomb.visuals[0];
    }
    else
    {
        level.sdbombmodel = spawn( "script_model", var_1.origin );
        level.sdbombmodel.angles = var_1.angles;
        level.sdbombmodel setmodel( "weapon_briefcase_bomb_iw6" );
    }

    var_0 maps\mp\gametypes\_gameobjects::allowuse( "none" );
    var_0 maps\mp\gametypes\_gameobjects::setvisibleteam( "none" );
    var_2 = var_0 maps\mp\gametypes\_gameobjects::getlabel();
    var_3 = var_0.bombdefusetrig;
    var_3.origin = level.sdbombmodel.origin;
    var_4 = [];
    var_5 = maps\mp\gametypes\_gameobjects::createuseobject( game["defenders"], var_3, var_4, ( 0, 0, 32 ) );
    var_5.id = "defuse_object";
    var_5 maps\mp\gametypes\_gameobjects::allowuse( "friendly" );
    var_5 maps\mp\gametypes\_gameobjects::setusetime( level.defusetime );
    var_5 maps\mp\gametypes\_gameobjects::setwaitweaponchangeonuse( 0 );
    var_5 maps\mp\gametypes\_gameobjects::setusetext( &"MP_DEFUSING_EXPLOSIVE" );
    var_5 maps\mp\gametypes\_gameobjects::setusehinttext( &"PLATFORM_HOLD_TO_DEFUSE_EXPLOSIVES" );
    var_5 maps\mp\gametypes\_gameobjects::setvisibleteam( "any" );
    var_5 maps\mp\gametypes\_gameobjects::set2dicon( "friendly", "waypoint_defuse" + var_2 );
    var_5 maps\mp\gametypes\_gameobjects::set2dicon( "enemy", "waypoint_defend" + var_2 );
    var_5 maps\mp\gametypes\_gameobjects::set3dicon( "friendly", "waypoint_defuse" + var_2 );
    var_5 maps\mp\gametypes\_gameobjects::set3dicon( "enemy", "waypoint_defend" + var_2 );
    var_5.label = var_2;
    var_5.onbeginuse = ::onbeginuse;
    var_5.onenduse = ::onenduse;
    var_5.onuse = ::onusedefuseobject;
    var_5.useweapon = "briefcase_bomb_defuse_mp";
    bombtimerwait();
    setomnvar( "ui_bomb_timer", 0 );
    var_0.visuals[0] maps\mp\gametypes\_gamelogic::stoptickingsound();

    if ( level.gameended || level.bombdefused )
        return;

    level.bombexploded = 1;
    level notify( "bomb_exploded" );

    if ( isdefined( level.sd_onbombtimerend ) )
        level thread [[ level.sd_onbombtimerend ]]();

    var_6 = level.sdbombmodel.origin;
    level.sdbombmodel hide();

    if ( isdefined( var_1 ) )
    {
        var_0.visuals[0] radiusdamage( var_6, 512, 200, 20, var_1, "MOD_EXPLOSIVE", "bomb_site_mp" );
        var_1 maps\mp\_utility::incpersstat( "destructions", 1 );
        var_1 maps\mp\gametypes\_persistence::statsetchild( "round", "destructions", var_1.pers["destructions"] );
    }
    else
        var_0.visuals[0] radiusdamage( var_6, 512, 200, 20, undefined, "MOD_EXPLOSIVE", "bomb_site_mp" );

    var_7 = randomfloat( 360 );

    if ( isdefined( var_0.trigger.effect ) )
        var_8 = var_0.trigger.effect;
    else
        var_8 = "bomb_explosion";

    var_9 = var_6 + ( 0, 0, 50 );
    var_10 = spawnfx( level._effect[var_8], var_9, ( 0, 0, 1 ), ( cos( var_7 ), sin( var_7 ), 0 ) );
    triggerfx( var_10 );
    physicsexplosionsphere( var_9, 200, 100, 3 );
    playrumbleonposition( "grenade_rumble", var_6 );
    earthquake( 0.75, 2.0, var_6, 2000 );
    thread maps\mp\_utility::playsoundinspace( "exp_suitcase_bomb_main", var_6 );

    if ( isdefined( var_0.exploderindex ) )
        common_scripts\utility::exploder( var_0.exploderindex );

    for ( var_11 = 0; var_11 < level.bombzones.size; var_11++ )
        level.bombzones[var_11] maps\mp\gametypes\_gameobjects::disableobject();

    var_5 maps\mp\gametypes\_gameobjects::disableobject();
    setgameendtime( 0 );
    wait 3;
    sd_endgame( game["attackers"], game["end_reason"]["target_destroyed"] );
}

initobjectivecam( var_0 )
{
    var_1 = undefined;
    var_2 = getentarray( "sd_bombcam_start", "targetname" );

    foreach ( var_4 in var_2 )
    {
        if ( var_4.script_label == var_0.label )
        {
            var_1 = var_4;
            break;
        }
    }

    var_6 = [];

    if ( isdefined( var_1 ) && isdefined( var_1.target ) )
    {
        var_7 = getent( var_1.target, "targetname" );

        while ( isdefined( var_7 ) )
        {
            var_6[var_6.size] = var_7;

            if ( isdefined( var_7.target ) )
            {
                var_7 = getent( var_7.target, "targetname" );
                continue;
            }

            break;
        }
    }

    if ( isdefined( var_1 ) && var_6.size )
    {
        var_8 = spawn( "script_model", var_1.origin );
        var_8.origin = var_1.origin;
        var_8.angles = var_1.angles;
        var_8.path = var_6;
        var_8 setmodel( "tag_origin" );
        var_8 hide();
        return var_8;
    }
    else
        return undefined;
}

runobjectivecam()
{
    level notify( "objective_cam" );

    foreach ( var_1 in level.players )
    {
        if ( !isai( var_1 ) )
        {
            var_1 maps\mp\_utility::freezecontrolswrapper( 1 );
            var_1 visionsetnakedforplayer( "black_bw", 0.5 );
        }
    }

    wait 0.5;

    foreach ( var_1 in level.players )
    {
        if ( !isai( var_1 ) )
        {
            if ( isdefined( var_1.disabledoffhandweapons ) )
            {
                var_1 maps\mp\_utility::setusingremote( "objective_cam" );
                var_1 common_scripts\utility::_disableweapon();
            }

            var_1 playerlinkweaponviewtodelta( self, "tag_player", 1, 180, 180, 180, 180, 1 );
            var_1 maps\mp\_utility::freezecontrolswrapper( 1 );
            var_1 setplayerangles( self.angles );
            var_1 visionsetnakedforplayer( "", 0.5 );
        }
    }

    var_5 = 0;

    if ( !getdvarint( "g_hardcore" ) )
    {
        setdynamicdvar( "g_hardcore", 1 );
        var_5 = 1;
    }

    for ( var_6 = 0; var_6 < self.path.size; var_6++ )
    {
        var_7 = 0;

        if ( var_6 == 0 )
            var_7 = 5 / self.path.size / 2;

        var_8 = 0;

        if ( var_6 == self.path.size - 1 )
            var_8 = 5 / self.path.size / 2;

        self moveto( self.path[var_6].origin, 5 / self.path.size, var_7, var_8 );
        self rotateto( self.path[var_6].angles, 5 / self.path.size, var_7, var_8 );
        wait( 5 / self.path.size );
    }

    if ( var_5 )
    {
        wait 0.5;
        setdynamicdvar( "g_hardcore", 0 );
    }
}

bombtimerwait()
{
    level endon( "game_ended" );
    level endon( "bomb_defused" );
    var_0 = int( level.bombtimer * 1000 + gettime() );
    setomnvar( "ui_bomb_timer_endtime", var_0 );
    level thread handlehostmigration( var_0 );
    maps\mp\gametypes\_hostmigration::waitlongdurationwithgameendtimeupdate( level.bombtimer );
}

handlehostmigration( var_0 )
{
    level endon( "game_ended" );
    level endon( "bomb_defused" );
    level endon( "game_ended" );
    level endon( "disconnect" );
    level waittill( "host_migration_begin" );
    setomnvar( "ui_bomb_timer_endtime", 0 );
    var_1 = maps\mp\gametypes\_hostmigration::waittillhostmigrationdone();

    if ( var_1 > 0 )
        setomnvar( "ui_bomb_timer_endtime", var_0 + var_1 );
}

bombdefused()
{
    level.tickingobject maps\mp\gametypes\_gamelogic::stoptickingsound();
    level.bombdefused = 1;
    setomnvar( "ui_bomb_timer", 0 );
    level notify( "bomb_defused" );
    wait 1.5;
    setgameendtime( 0 );
    sd_endgame( game["defenders"], game["end_reason"]["bomb_defused"] );
}

initgametypeawards()
{
    maps\mp\_awards::initstataward( "targetsdestroyed", 0, maps\mp\_awards::highestwins );
    maps\mp\_awards::initstataward( "bombsplanted", 0, maps\mp\_awards::highestwins );
    maps\mp\_awards::initstataward( "bombsdefused", 0, maps\mp\_awards::highestwins );
    maps\mp\_awards::initstataward( "bombcarrierkills", 0, maps\mp\_awards::highestwins );
    maps\mp\_awards::initstataward( "bombscarried", 0, maps\mp\_awards::highestwins );
    maps\mp\_awards::initstataward( "killsasbombcarrier", 0, maps\mp\_awards::highestwins );
}

setspecialloadout()
{
    if ( isusingmatchrulesdata() && getmatchrulesdata( "defaultClasses", game["attackers"], 5, "class", "inUse" ) )
        level.sd_loadout[game["attackers"]] = maps\mp\_utility::getmatchrulesspecialclass( game["attackers"], 5 );
}
