/// <summary>
        /// decrements gangManager's living members count, also tells the war manager about it,
        /// clears this script's references, removes the ped's blip and marks the ped as no longer needed
        /// </summary>
        public void Die(bool fleeIfAlive = false)
        {
            if (watchedPed != null)
            {
                if (GangWarManager.instance.isOccurring)
                {
                    if (watchedPed.RelationshipGroup == GangWarManager.instance.enemyGang.relationGroupIndex)
                    {
                        //enemy down
                        GangWarManager.instance.DecrementSpawnedsNumber(false);
                    }
                    else if (watchedPed.RelationshipGroup == GangManager.instance.PlayerGang.relationGroupIndex)
                    {
                        //ally down
                        GangWarManager.instance.DecrementSpawnedsNumber(true);
                    }
                }
                if (watchedPed.CurrentBlip != null)
                {
                    watchedPed.CurrentBlip.Remove();
                }

                this.watchedPed.MarkAsNoLongerNeeded();

                if (fleeIfAlive && watchedPed.IsAlive)
                {
                    watchedPed.Task.FleeFrom(Game.Player.Character);
                }
            }

            this.myGang     = null;
            this.watchedPed = null;
            curStatus       = memberStatus.none;
            GangManager.instance.livingMembersCount--;
        }
        public void GiveTurfRewardToGang(Gang targetGang)
        {
            List <TurfZone> curGangZones = ZoneManager.instance.GetZonesControlledByGang(targetGang.name);

            if (targetGang.isPlayerOwned)
            {
                if (curGangZones.Count > 0)
                {
                    int rewardedCash = 0;

                    for (int i = 0; i < curGangZones.Count; i++)
                    {
                        int zoneReward = (int)((ModOptions.instance.baseRewardPerZoneOwned *
                                                (1 + ModOptions.instance.rewardMultiplierPerZone * curGangZones.Count)) +
                                               ((curGangZones[i].value + 1) * ModOptions.instance.baseRewardPerZoneOwned * 0.25f));

                        MindControl.instance.AddOrSubtractMoneyToProtagonist(zoneReward);

                        rewardedCash += zoneReward;
                    }
                    Function.Call(Hash.PLAY_SOUND, -1, "Virus_Eradicated", "LESTER1A_SOUNDS", 0, 0, 1);
                    UI.Notify("Money won from controlled zones: " + rewardedCash.ToString());
                }
            }
            else
            {
                for (int j = 0; j < curGangZones.Count; j++)
                {
                    targetGang.moneyAvailable += (int)((curGangZones[j].value + 1) *
                                                       ModOptions.instance.baseRewardPerZoneOwned *
                                                       (1 + ModOptions.instance.rewardMultiplierPerZone * curGangZones.Count) * ModOptions.instance.extraProfitForAIGangsFactor);
                }
            }
        }
Exemple #3
0
        /// <summary>
        /// gets all currently active spawned members of the desired gang.
        /// The onlyGetIfInsideVehicle will only add members who are inside vehicles to the returned list
        /// </summary>
        /// <param name="desiredGang"></param>
        /// <param name="onlyGetIfInsideVehicle"></param>
        /// <returns></returns>
        public List <SpawnedGangMember> GetSpawnedMembersOfGang(Gang desiredGang, bool onlyGetIfInsideVehicle = false)
        {
            List <SpawnedGangMember> returnedList = new List <SpawnedGangMember>();

            for (int i = 0; i < livingMembers.Count; i++)
            {
                if (livingMembers[i] != null)
                {
                    if (livingMembers[i].myGang == desiredGang)
                    {
                        if (onlyGetIfInsideVehicle)
                        {
                            if (Function.Call <bool>(Hash.IS_PED_IN_ANY_VEHICLE, livingMembers[i].watchedPed, false))
                            {
                                returnedList.Add(livingMembers[i]);
                            }
                        }
                        else
                        {
                            returnedList.Add(livingMembers[i]);
                        }
                    }
                }
            }

            return(returnedList);
        }
Exemple #4
0
        public void GiveTurfRewardToGang(Gang targetGang)
        {
            List <TurfZone> curGangZones = ZoneManager.instance.GetZonesControlledByGang(targetGang.name);
            int             zonesCount   = curGangZones.Count;

            if (targetGang.isPlayerOwned)
            {
                if (curGangZones.Count > 0)
                {
                    int rewardedCash = 0;

                    for (int i = 0; i < zonesCount; i++)
                    {
                        int zoneReward = GangCalculations.CalculateRewardForZone(curGangZones[i], zonesCount);

                        rewardedCash += zoneReward;
                    }

                    MindControl.instance.AddOrSubtractMoneyToProtagonist(rewardedCash);
                    Function.Call(Hash.PLAY_SOUND, -1, "Virus_Eradicated", "LESTER1A_SOUNDS", 0, 0, 1);
                    UI.Notify("Money won from controlled zones: " + rewardedCash.ToString());
                }
            }
            else
            {
                for (int i = 0; i < curGangZones.Count; i++)
                {
                    targetGang.moneyAvailable += (int)
                                                 (GangCalculations.CalculateRewardForZone(curGangZones[i], zonesCount) *
                                                  ModOptions.instance.extraProfitForAIGangsFactor);
                }
            }
        }
        public static int CalculateAttackCost(Gang attackerGang, GangWarManager.AttackStrength attackType)
        {
            int attackTypeInt         = (int)attackType;
            int pow2NonZeroAttackType = (attackTypeInt * attackTypeInt + 1);

            return(ModOptions.instance.baseCostToTakeTurf + ModOptions.instance.baseCostToTakeTurf * attackTypeInt * attackTypeInt * attackTypeInt +
                   attackerGang.GetFixedStrengthValue() * pow2NonZeroAttackType);
        }
        /// <summary>
        /// uses the base reward for taking enemy turf (half if it was just a battle for defending)
        /// and the enemy strength (with variation) to define the "loot"
        /// </summary>
        /// <returns></returns>
        public static int CalculateBattleRewards(Gang ourEnemy, int battleScale, bool weWereAttacking)
        {
            int baseReward = ModOptions.instance.rewardForTakingEnemyTurf;

            if (weWereAttacking)
            {
                baseReward /= 2;
            }
            return((baseReward + ourEnemy.GetGangVariedStrengthValue()) * (battleScale + 1));
        }
Exemple #7
0
        /// <summary>
        /// adds the gang to a xml file that contains a list of gangs that have been wiped out,
        ///  so that the player can reuse their data in the future
        /// </summary>
        /// <param name="gangToAdd"></param>
        public void AddGangToWipedOutList(Gang gangToAdd)
        {
            List <Gang> WOList = PersistenceHandler.LoadFromFile <List <Gang> >("wipedOutGangsList");

            if (WOList == null)
            {
                WOList = new List <Gang>();
            }
            WOList.Add(gangToAdd);
            PersistenceHandler.SaveToFile(WOList, "wipedOutGangsList");
        }
Exemple #8
0
 public GangAI GetGangAI(Gang targetGang)
 {
     for (int i = 0; i < enemyGangs.Count; i++)
     {
         if (enemyGangs[i].watchedGang == targetGang)
         {
             return(enemyGangs[i]);
         }
     }
     return(null);
 }
Exemple #9
0
        public Gang CreateNewEnemyGang(bool notifyMsg = true)
        {
            if (PotentialGangMember.MemberPool.memberList.Count <= 0)
            {
                UI.Notify("Enemy gang creation failed: bad/empty/not found memberPool file. Try adding peds as potential members for AI gangs");
                return(null);
            }
            //set gang name from options
            string gangName = "Gang";

            do
            {
                gangName = string.Concat(RandoMath.GetRandomElementFromList(ModOptions.instance.possibleGangFirstNames), " ",
                                         RandoMath.GetRandomElementFromList(ModOptions.instance.possibleGangLastNames));
            } while (GetGangByName(gangName) != null);

            PotentialGangMember.MemberColor gangColor = (PotentialGangMember.MemberColor)RandoMath.CachedRandom.Next(9);

            //the new gang takes the wealthiest gang around as reference to define its starting money.
            //that does not mean it will be the new wealthiest one, hehe (but it may)
            Gang newGang = new Gang(gangName, RandoMath.GetRandomElementFromList(ModOptions.instance.GetGangColorTranslation(gangColor).vehicleColors),
                                    false, (int)(RandoMath.Max(Game.Player.Money, GetWealthiestGang().moneyAvailable) * (RandoMath.CachedRandom.Next(1, 11) / 6.5f)))
            {
                blipColor = RandoMath.GetRandomElementFromArray(ModOptions.instance.GetGangColorTranslation(gangColor).blipColors)
            };

            GetMembersForGang(newGang);

            //relations...
            newGang.relationGroupIndex = World.AddRelationshipGroup(gangName);

            World.SetRelationshipBetweenGroups(Relationship.Hate, newGang.relationGroupIndex, Game.Player.Character.RelationshipGroup);
            World.SetRelationshipBetweenGroups(Relationship.Hate, Game.Player.Character.RelationshipGroup, newGang.relationGroupIndex);

            for (int i = 0; i < gangData.gangs.Count; i++)
            {
                World.SetRelationshipBetweenGroups(Relationship.Hate, gangData.gangs[i].relationGroupIndex, newGang.relationGroupIndex);
                World.SetRelationshipBetweenGroups(Relationship.Hate, newGang.relationGroupIndex, gangData.gangs[i].relationGroupIndex);
            }

            gangData.gangs.Add(newGang);

            newGang.GetPistolIfOptionsRequire();

            SaveGangData();
            if (notifyMsg)
            {
                UI.Notify("The " + gangName + " have entered San Andreas!");
            }


            return(newGang);
        }
Exemple #10
0
        public Ped SpawnParachutingMember(Gang ownerGang, Vector3 spawnPos, Vector3 destPos)
        {
            SpawnedGangMember spawnedPara = SpawnGangMember(ownerGang, spawnPos);

            if (spawnedPara != null)
            {
                spawnedPara.watchedPed.BlockPermanentEvents = true;
                spawnedPara.watchedPed.Task.ParachuteTo(destPos);
                return(spawnedPara.watchedPed);
            }

            return(null);
        }
        public void SpawnAmbientVehicle(Gang curGang)
        {
            Vector3 vehSpawnPoint = SpawnManager.instance.FindGoodSpawnPointForCar();
            SpawnedDrivingGangMember spawnedVehicleAI = SpawnManager.instance.SpawnGangVehicle(curGang,
                                                                                               vehSpawnPoint, Vector3.Zero, true);

            if (spawnedVehicleAI != null)
            {
                SpawnManager.instance.TryPlaceVehicleOnStreet(spawnedVehicleAI.vehicleIAmDriving, vehSpawnPoint);
                Ped driver = spawnedVehicleAI.watchedPed;
                if (driver != null) //if, for some reason, we don't have a driver, do nothing
                {
                    driver.Task.CruiseWithVehicle(spawnedVehicleAI.vehicleIAmDriving, 20, ModOptions.instance.wanderingDriverDrivingStyle);
                }
            }
        }
Exemple #12
0
 public void GetMembersForGang(Gang targetGang)
 {
     PotentialGangMember.MemberColor gangColor = ModOptions.instance.TranslateVehicleToMemberColor(targetGang.vehicleColor);
     PotentialGangMember.DressStyle  gangStyle = (PotentialGangMember.DressStyle)RandoMath.CachedRandom.Next(3);
     for (int i = 0; i < RandoMath.CachedRandom.Next(2, 6); i++)
     {
         PotentialGangMember newMember = PotentialGangMember.GetMemberFromPool(gangStyle, gangColor);
         if (newMember != null)
         {
             targetGang.AddMemberVariation(newMember);
         }
         else
         {
             break;
         }
     }
 }
Exemple #13
0
        public List <Ped> GetSpawnedPedsOfGang(Gang desiredGang)
        {
            List <Ped> returnedList = new List <Ped>();

            for (int i = 0; i < livingMembers.Count; i++)
            {
                if (livingMembers[i].watchedPed != null)
                {
                    if (livingMembers[i].watchedPed.RelationshipGroup == desiredGang.relationGroupIndex)
                    {
                        returnedList.Add(livingMembers[i].watchedPed);
                    }
                }
            }

            return(returnedList);
        }
 public void KillGang(GangAI aiWatchingTheGang)
 {
     UI.Notify("The " + aiWatchingTheGang.watchedGang.name + " have been wiped out!");
     enemyGangs.Remove(aiWatchingTheGang);
     //save the fallen gang in a file
     PersistenceHandler.SaveAppendToFile(aiWatchingTheGang.watchedGang, "wipedOutGangs");
     gangData.gangs.Remove(aiWatchingTheGang.watchedGang);
     if (enemyGangs.Count == 0 && ModOptions.instance.maxCoexistingGangs > 1)
     {
         //create a new gang right away... but do it silently to not demotivate the player too much
         Gang createdGang = CreateNewEnemyGang(false);
         if (createdGang != null)
         {
             enemyGangs.Add(new GangAI(createdGang));
         }
     }
     SaveGangData(false);
 }
        public static GangWarManager.AttackStrength CalculateRequiredAttackStrength(Gang attackerGang, int defenderStrength)
        {
            GangWarManager.AttackStrength requiredAtk = GangWarManager.AttackStrength.light;

            for (int i = 0; i < 3; i++)
            {
                if (CalculateAttackerStrength(attackerGang, requiredAtk) >= defenderStrength)
                {
                    break;
                }
                else
                {
                    requiredAtk++;
                }
            }

            return(requiredAtk);
        }
Exemple #16
0
        /// <summary>
        /// this controls the gang AI decisions and rewards for the player and AI gangs
        /// </summary>
        void TickGangs()
        {
            gangAIUpdateRanThisFrame = false;
            for (int i = 0; i < enemyGangs.Count; i++)
            {
                enemyGangs[i].ticksSinceLastUpdate++;
                if (!gangAIUpdateRanThisFrame)
                {
                    if (enemyGangs[i].ticksSinceLastUpdate >= enemyGangs[i].ticksBetweenUpdates)
                    {
                        enemyGangs[i].ticksSinceLastUpdate = 0 - RandoMath.CachedRandom.Next(enemyGangs[i].ticksBetweenUpdates / 3);
                        enemyGangs[i].Update();
                        //lets also check if there aren't too many gangs around
                        //if there aren't, we might create a new one...
                        if (enemyGangs.Count < ModOptions.instance.maxCoexistingGangs - 1)
                        {
                            if (RandoMath.CachedRandom.Next(enemyGangs.Count) == 0)
                            {
                                Gang createdGang = CreateNewEnemyGang();
                                if (createdGang != null)
                                {
                                    enemyGangs.Add(new GangAI(createdGang));
                                }
                            }
                        }

                        gangAIUpdateRanThisFrame = true;                         //max is one update per tick
                    }
                }
            }

            if (ModCore.curGameTime - timeLastReward > ModOptions.instance.msTimeBetweenTurfRewards)
            {
                timeLastReward = ModCore.curGameTime;
                for (int i = 0; i < enemyGangs.Count; i++)
                {
                    GiveTurfRewardToGang(enemyGangs[i].watchedGang);
                }

                //this also counts for the player's gang
                GiveTurfRewardToGang(PlayerGang);
            }
        }
Exemple #17
0
        /// <summary>
        /// sets relations between gangs to a certain level according to the aggressiveness
        /// </summary>
        /// <param name="aggrLevel"></param>
        public void SetGangRelationsAccordingToAggrLevel(ModOptions.GangMemberAggressivenessMode aggrLevel)
        {
            Relationship targetRelationLevel = Relationship.Hate;
            Gang         excludedGang        = null;

            if (GangWarManager.instance.isOccurring)
            {
                excludedGang = GangWarManager.instance.enemyGang;
            }
            switch (aggrLevel)
            {
            case ModOptions.GangMemberAggressivenessMode.veryAgressive:
                targetRelationLevel = Relationship.Hate;
                break;

            case ModOptions.GangMemberAggressivenessMode.agressive:
                targetRelationLevel = Relationship.Dislike;
                break;

            case ModOptions.GangMemberAggressivenessMode.defensive:
                targetRelationLevel = Relationship.Neutral;
                break;
            }
            for (int i = gangData.gangs.Count - 1; i > -1; i--)
            {
                for (int j = 0; j < i; j++)
                {
                    if ((gangData.gangs[i] != excludedGang || gangData.gangs[j] != PlayerGang) &&
                        (gangData.gangs[j] != excludedGang || gangData.gangs[i] != PlayerGang))
                    {
                        World.SetRelationshipBetweenGroups(targetRelationLevel, gangData.gangs[i].relationGroupIndex, gangData.gangs[j].relationGroupIndex);
                        World.SetRelationshipBetweenGroups(targetRelationLevel, gangData.gangs[j].relationGroupIndex, gangData.gangs[i].relationGroupIndex);
                    }
                }
                if (!gangData.gangs[i].isPlayerOwned && gangData.gangs[i] != excludedGang)
                {
                    World.SetRelationshipBetweenGroups(targetRelationLevel, gangData.gangs[i].relationGroupIndex, Game.Player.Character.RelationshipGroup);
                    World.SetRelationshipBetweenGroups(targetRelationLevel, Game.Player.Character.RelationshipGroup, gangData.gangs[i].relationGroupIndex);
                }
            }
        }
Exemple #18
0
        /// <summary>
        /// creates a new "player's gang" (there should be only one!)
        /// and adds it to the gangdata gangs list
        /// </summary>
        /// <param name="notifyMsg"></param>
        /// <returns></returns>
        public Gang CreateNewPlayerGang(bool notifyMsg = true)
        {
            Gang playerGang = new Gang("Player's Gang", VehicleColor.BrushedGold, true);

            //setup gangs
            gangData.gangs.Add(playerGang);

            playerGang.blipColor = (int)BlipColor.Yellow;

            if (ModOptions.instance.gangsStartWithPistols)
            {
                playerGang.gangWeaponHashes.Add(WeaponHash.Pistol);
            }

            if (notifyMsg)
            {
                UI.Notify("Created new gang for the player!");
            }

            return(playerGang);
        }
Exemple #19
0
        /// <summary>
        /// returns the gang with the most stocked money
        /// </summary>
        /// <returns></returns>
        public Gang GetWealthiestGang()
        {
            Gang pickedGang = null;

            for (int i = 0; i < gangData.gangs.Count; i++)
            {
                if (pickedGang != null)
                {
                    if (gangData.gangs[i].moneyAvailable > pickedGang.moneyAvailable)
                    {
                        pickedGang = gangData.gangs[i];
                    }
                }
                else
                {
                    pickedGang = gangData.gangs[i];
                }
            }

            return(pickedGang);
        }
        public void UpdateZoneBlip(TurfZone targetZone)
        {
            if (targetZone.AttachedBlip != null)
            {
                Gang ownerGang = GangManager.instance.GetGangByName(targetZone.ownerGangName);
                if (ownerGang == null)
                {
                    targetZone.AttachedBlip.Sprite = BlipSprite.GTAOPlayerSafehouseDead;
                    targetZone.AttachedBlip.Color  = BlipColor.White;
                }
                else
                {
                    targetZone.AttachedBlip.Sprite = BlipSprite.GTAOPlayerSafehouse;
                    Function.Call(Hash.SET_BLIP_COLOUR, targetZone.AttachedBlip, ownerGang.blipColor);

                    if (ownerGang.isPlayerOwned)
                    {
                        Function.Call(Hash.SET_BLIP_SECONDARY_COLOUR, targetZone.AttachedBlip, 0f, 255, 0f);
                    }
                    else
                    {
                        Function.Call(Hash.SET_BLIP_SECONDARY_COLOUR, targetZone.AttachedBlip, 255, 0f, 0f);
                    }

                    targetZone.AttachedBlip.Scale = 1.0f + 0.65f / ((ModOptions.instance.maxTurfValue + 1) / (targetZone.value + 1));
                }

                Function.Call(Hash.BEGIN_TEXT_COMMAND_SET_BLIP_NAME, "STRING");
                if (ownerGang != null)
                {
                    Function.Call(Hash._ADD_TEXT_COMPONENT_STRING, string.Concat(targetZone.zoneName, " (", targetZone.ownerGangName, " turf, level ", targetZone.value.ToString(), ")"));
                }
                else
                {
                    Function.Call(Hash._ADD_TEXT_COMPONENT_STRING, string.Concat(targetZone.zoneName, " (neutral territory)"));
                }

                Function.Call(Hash.END_TEXT_COMMAND_SET_BLIP_NAME, targetZone.AttachedBlip);
            }
        }
Exemple #21
0
        public GangAI(Gang watchedGang)
        {
            this.watchedGang = watchedGang;
            ResetUpdateInterval();

            //have some turf for free! but only if you're new around here
            DoInitialTakeover();

            //do we have vehicles?
            if (this.watchedGang.carVariations.Count == 0)
            {
                //get some vehicles!
                for (int i = 0; i < RandoMath.CachedRandom.Next(1, 4); i++)
                {
                    PotentialGangVehicle newVeh = PotentialGangVehicle.GetCarFromPool();
                    if (newVeh != null)
                    {
                        this.watchedGang.AddGangCar(newVeh);
                    }
                }
            }
        }
Exemple #22
0
        /// <summary>
        /// returns gang members who are not from the gang provided
        /// </summary>
        /// <param name="myGang"></param>
        /// <returns></returns>
        public List <Ped> GetMembersNotFromMyGang(Gang myGang, bool includePlayer = true)
        {
            List <Ped> returnedList = new List <Ped>();

            for (int i = 0; i < livingMembers.Count; i++)
            {
                if (livingMembers[i].watchedPed != null)
                {
                    if (livingMembers[i] != MindControl.instance.currentlyControlledMember &&
                        livingMembers[i].watchedPed.RelationshipGroup != myGang.relationGroupIndex)
                    {
                        returnedList.Add(livingMembers[i].watchedPed);
                    }
                }
            }

            if (includePlayer && myGang != GangManager.instance.PlayerGang)
            {
                returnedList.Add(MindControl.CurrentPlayerCharacter);
            }

            return(returnedList);
        }
Exemple #23
0
        /// <summary>
        /// decrements gangManager's living members count, also tells the war manager about it,
        /// clears this script's references, removes the ped's blip and marks the ped as no longer needed
        /// </summary>
        public void Die(bool alsoDelete = false)
        {
            if (watchedPed != null)
            {
                if (GangWarManager.instance.isOccurring)
                {
                    if (watchedPed.RelationshipGroup == GangWarManager.instance.enemyGang.relationGroupIndex)
                    {
                        //enemy down
                        GangWarManager.instance.DecrementSpawnedsNumber(false);
                    }
                    else if (watchedPed.RelationshipGroup == GangManager.instance.PlayerGang.relationGroupIndex)
                    {
                        //ally down
                        GangWarManager.instance.DecrementSpawnedsNumber(true);
                    }
                }
                if (watchedPed.CurrentBlip != null)
                {
                    watchedPed.CurrentBlip.Remove();
                }

                if (alsoDelete)
                {
                    watchedPed.Delete();
                }
                else
                {
                    watchedPed.MarkAsNoLongerNeeded();
                }
            }

            this.myGang     = null;
            this.watchedPed = null;
            curStatus       = MemberStatus.none;
            SpawnManager.instance.livingMembersCount--;
        }
 public static int CalculateAttackerReinforcements(Gang attackerGang, GangWarManager.AttackStrength attackType)
 {
     return(ModOptions.instance.extraKillsPerTurfValue * ((int)(attackType + 1) * (int)(attackType + 1)) + ModOptions.instance.baseNumKillsBeforeWarVictory / 2 +
            attackerGang.GetReinforcementsValue() / 100);
 }
Exemple #25
0
        /// <summary>
        /// if fighting is enabled and the targetzone is controlled by an enemy, attack it! ... But only if it's affordable.
        /// if we're desperate we do it anyway
        /// </summary>
        /// <param name="targetZone"></param>
        void TryStartFightForZone(TurfZone targetZone)
        {
            Gang ownerGang = GangManager.instance.GetGangByName(targetZone.ownerGangName);

            if (ownerGang == null)
            {
                Logger.Log("Gang with name " + targetZone.ownerGangName + " no longer exists; assigning all owned turf to 'none'", 1);
                ZoneManager.instance.GiveGangZonesToAnother(targetZone.ownerGangName, "none");

                //this zone was controlled by a gang that no longer exists. it is neutral now
                if (watchedGang.moneyAvailable >= ModOptions.instance.baseCostToTakeTurf)
                {
                    watchedGang.moneyAvailable -= ModOptions.instance.baseCostToTakeTurf;
                    watchedGang.TakeZone(targetZone);
                }
            }
            else
            {
                if (GangWarManager.instance.isOccurring && GangWarManager.instance.warZone == targetZone)
                {
                    //don't mess with this zone then, it's a warzone
                    return;
                }
                //we check how well defended this zone is,
                //then figure out how large our attack should be.
                //if we can afford that attack, we do it
                int defenderStrength = GangCalculations.CalculateDefenderStrength(ownerGang, targetZone);
                GangWarManager.AttackStrength requiredStrength =
                    GangCalculations.CalculateRequiredAttackStrength(watchedGang, defenderStrength);
                int atkCost = GangCalculations.CalculateAttackCost(watchedGang, requiredStrength);

                if (watchedGang.moneyAvailable < atkCost)
                {
                    if (myZones.Count == 0)
                    {
                        //if we're out of turf and cant afford a decent attack, lets just attack anyway
                        //we use a light attack and do it even if that means our money gets negative.
                        //this should make gangs get back in the game or be wiped out instead of just staying away
                        requiredStrength = GangWarManager.AttackStrength.light;
                        atkCost          = GangCalculations.CalculateAttackCost(watchedGang, requiredStrength);
                    }
                    else
                    {
                        return;                         //hopefully we can just find a cheaper fight
                    }
                }

                if (targetZone.ownerGangName == GangManager.instance.PlayerGang.name)
                {
                    if (ModOptions.instance.warAgainstPlayerEnabled &&
                        GangWarManager.instance.CanStartWarAgainstPlayer)
                    {
                        //the player may be in big trouble now
                        watchedGang.moneyAvailable -= atkCost;
                        GangWarManager.instance.StartWar(watchedGang, targetZone, GangWarManager.WarType.defendingFromEnemy, requiredStrength);
                    }
                }
                else
                {
                    watchedGang.moneyAvailable -= atkCost;
                    int attackStrength = GangCalculations.CalculateAttackerStrength(watchedGang, requiredStrength);
                    //roll dices... favor the defenders a little here
                    if (attackStrength / RandoMath.CachedRandom.Next(1, 22) >
                        defenderStrength / RandoMath.CachedRandom.Next(1, 15))
                    {
                        watchedGang.TakeZone(targetZone);
                        watchedGang.moneyAvailable += (int)(GangCalculations.CalculateBattleRewards(ownerGang, targetZone.value, true) *
                                                            ModOptions.instance.extraProfitForAIGangsFactor);
                    }
                    else
                    {
                        ownerGang.moneyAvailable += (int)(GangCalculations.CalculateBattleRewards(watchedGang, (int)requiredStrength, false) *
                                                          ModOptions.instance.extraProfitForAIGangsFactor);
                    }
                }
            }
        }
 public void SpawnAmbientMember(Gang curGang)
 {
     Vector3 spawnPos = SpawnManager.instance.FindGoodSpawnPointForMember
                            (MindControl.CurrentPlayerCharacter.Position);
     SpawnedGangMember newMember = SpawnManager.instance.SpawnGangMember(curGang, spawnPos);
 }
        void OnTick(object sender, EventArgs e)
        {
            Wait(3000 + RandoMath.CachedRandom.Next(1000));
            Logger.Log("ambient spawner tick: begin", 5);

            TurfZone curTurfZone = ZoneManager.instance.GetCurrentTurfZone();

            if (curTurfZone != null)
            {
                // also reduce police influence
                if (enabled)
                {
                    Game.WantedMultiplier = (1.0f / (curTurfZone.value + 1)) + ModOptions.instance.minWantedFactorWhenInGangTurf;
                    Game.MaxWantedLevel   = RandoMath.Max(CalculateMaxWantedLevelInTurf(curTurfZone.value), ModOptions.instance.maxWantedLevelInMaxedGangTurf);
                }

                if (Game.Player.WantedLevel > Game.MaxWantedLevel)
                {
                    Game.Player.WantedLevel--;
                }

                if (postWarBackupsRemaining > 0 && GangWarManager.instance.playerNearWarzone)
                {
                    Vector3 playerPos     = MindControl.CurrentPlayerCharacter.Position,
                            safePlayerPos = MindControl.SafePositionNearPlayer;
                    if (SpawnManager.instance.SpawnParachutingMember(GangManager.instance.PlayerGang,
                                                                     playerPos + Vector3.WorldUp * 50, safePlayerPos) == null)
                    {
                        SpawnManager.instance.SpawnGangVehicle(GangManager.instance.PlayerGang,
                                                               SpawnManager.instance.FindGoodSpawnPointForCar(safePlayerPos), safePlayerPos);
                    }
                    postWarBackupsRemaining--;
                }

                //if spawning is enabled, lets try to spawn the current zone's corresponding gang members!
                if (ModOptions.instance.ambientSpawningEnabled && enabled)
                {
                    Gang curGang = GangManager.instance.GetGangByName(curTurfZone.ownerGangName);
                    if (GangWarManager.instance.isOccurring && GangWarManager.instance.enemyGang == curGang)
                    {
                        return;                                                                     //we want enemies of this gang to spawn only when close to the war
                    }
                    if (curTurfZone.ownerGangName != "none" && curGang != null)                     //only spawn if there really is a gang in control here
                    {
                        if (SpawnManager.instance.livingMembersCount < ModOptions.instance.spawnedMembersBeforeAmbientGenStops)
                        {
                            Vehicle playerVehicle = MindControl.CurrentPlayerCharacter.CurrentVehicle;
                            if ((playerVehicle != null && playerVehicle.Speed < 30) || playerVehicle == null)
                            {
                                SpawnAmbientMember(curGang);
                            }
                            if (RandoMath.CachedRandom.Next(0, 5) < 3)
                            {
                                Wait(100 + RandoMath.CachedRandom.Next(300));
                                SpawnAmbientVehicle(curGang);
                            }

                            Wait(1 + RandoMath.CachedRandom.Next(RandoMath.Max(1, ModOptions.instance.msBaseIntervalBetweenAmbientSpawns / 2), ModOptions.instance.msBaseIntervalBetweenAmbientSpawns) / (curTurfZone.value + 1));
                        }
                    }
                    else
                    {
                        Game.WantedMultiplier = 1;
                        Game.MaxWantedLevel   = 6;
                    }
                }
            }

            Logger.Log("ambient spawner tick: end", 5);
        }
 public static int CalculateDefenderReinforcements(Gang defenderGang, TurfZone targetZone)
 {
     return(ModOptions.instance.extraKillsPerTurfValue * targetZone.value + ModOptions.instance.baseNumKillsBeforeWarVictory +
            defenderGang.GetReinforcementsValue() / 100);
 }
        public bool StartWar(Gang enemyGang, TurfZone warZone, WarType theWarType, AttackStrength attackStrength)
        {
            if (!isOccurring || enemyGang == GangManager.instance.PlayerGang)
            {
                this.enemyGang    = enemyGang;
                this.warZone      = warZone;
                this.curWarType   = theWarType;
                curWarAtkStrength = attackStrength;
                playerNearWarzone = false;
                spawnPointsSet    = false;

                warBlip            = World.CreateBlip(warZone.zoneBlipPosition);
                warBlip.IsFlashing = true;
                warBlip.Sprite     = BlipSprite.Deathmatch;
                warBlip.Color      = BlipColor.Red;

                warAreaBlip = World.CreateBlip(warZone.zoneBlipPosition,
                                               ModOptions.instance.maxDistToWarBlipBeforePlayerLeavesWar);
                warAreaBlip.Sprite = BlipSprite.BigCircle;
                warAreaBlip.Color  = BlipColor.Red;
                warAreaBlip.Alpha  = 175;


                Function.Call(Hash.BEGIN_TEXT_COMMAND_SET_BLIP_NAME, "STRING");
                Function.Call(Hash._ADD_TEXT_COMPONENT_STRING, "Gang War (versus " + enemyGang.name + ")");
                Function.Call(Hash.END_TEXT_COMMAND_SET_BLIP_NAME, warBlip);

                curTicksAwayFromBattle = 0;
                enemiesInsideCars      = SpawnManager.instance.GetSpawnedMembersOfGang(enemyGang, true);

                if (theWarType == WarType.attackingEnemy)
                {
                    alliedReinforcements = GangCalculations.CalculateAttackerReinforcements(GangManager.instance.PlayerGang, attackStrength);
                    enemyReinforcements  = GangCalculations.CalculateDefenderReinforcements(enemyGang, warZone);
                }
                else
                {
                    alliedReinforcements = GangCalculations.CalculateDefenderReinforcements(GangManager.instance.PlayerGang, warZone);
                    enemyReinforcements  = GangCalculations.CalculateAttackerReinforcements(enemyGang, attackStrength);
                }

                float screenRatio = (float)Game.ScreenResolution.Width / Game.ScreenResolution.Height;

                int proportionalScreenWidth = (int)(1080 * screenRatio); //nativeUI UIResText works with 1080p height

                alliedNumText.Position = new Point((proportionalScreenWidth / 2) - 120, 10);
                enemyNumText.Position  = new Point((proportionalScreenWidth / 2) + 120, 10);

                alliedNumText.Caption = alliedReinforcements.ToString();
                enemyNumText.Caption  = enemyReinforcements.ToString();

                initialEnemyReinforcements = enemyReinforcements;

                reinforcementsAdvantage = alliedReinforcements / (float)enemyReinforcements;

                spawnedAllies  = SpawnManager.instance.GetSpawnedMembersOfGang(GangManager.instance.PlayerGang).Count;
                spawnedEnemies = SpawnManager.instance.GetSpawnedMembersOfGang(enemyGang).Count;

                maxSpawnedAllies  = (int)(RandoMath.Max((ModOptions.instance.spawnedMemberLimit / 2) * reinforcementsAdvantage, 5));
                maxSpawnedEnemies = RandoMath.Max(ModOptions.instance.spawnedMemberLimit - maxSpawnedAllies, 5);

                isOccurring = true;

                //BANG-like sound
                Function.Call(Hash.PLAY_SOUND_FRONTEND, -1, "PROPERTY_PURCHASE", "HUD_AWARDS");

                if (theWarType == WarType.attackingEnemy)
                {
                    UI.ShowSubtitle("The " + enemyGang.name + " are coming!");

                    //if we are attacking, set spawns around the player!
                    SetSpawnPoints(MindControl.CurrentPlayerCharacter.Position);
                }
                else
                {
                    UI.Notify(string.Concat("The ", enemyGang.name, " are attacking ", warZone.zoneName, "! They are ",
                                            GangCalculations.CalculateAttackerReinforcements(enemyGang, attackStrength).ToString(),
                                            " against our ",
                                            GangCalculations.CalculateDefenderReinforcements(GangManager.instance.PlayerGang, warZone).ToString()));
                    //spawns are set around the zone blip if we are defending
                    if (World.GetDistance(MindControl.CurrentPlayerCharacter.Position, warZone.zoneBlipPosition) < 100)
                    {
                        SetSpawnPoints(warZone.zoneBlipPosition);
                    }
                }

                SetHateRelationsBetweenGangs();

                return(true);
            }
            else
            {
                return(false);
            }
        }
 /// <summary>
 /// gets the reinforcement count for the defenders and estimates a total power based on that number and
 /// the gang's fixed strength value
 /// </summary>
 /// <param name="defenderGang"></param>
 /// <param name="contestedZone"></param>
 /// <returns></returns>
 public static int CalculateDefenderStrength(Gang defenderGang, TurfZone contestedZone)
 {
     return(defenderGang.GetFixedStrengthValue() *
            CalculateDefenderReinforcements(defenderGang, contestedZone));
 }