SHARE
TWEET

Dangerous Individuals

Eddlm Jul 15th, 2016 255 Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. using GTA;
  2. using GTA.Native;
  3. using System;
  4. using System.IO;
  5. using System.Windows.Forms;
  6. using System.Collections.Generic;
  7. using NativeUI;
  8. using GTA.Math;
  9. using System.Drawing;
  10. using System.Linq;
  11. using System.Xml;
  12.  
  13. namespace LSPDispatch
  14. {
  15.     /// <summary>
  16.     /// TO IMPROVE
  17.     /// COP ARRESTING SYSTEM
  18.     ///
  19.     /// </summary>
  20.     public class DangerousIndividuals : Script
  21.     {
  22.         bool FootReminder = false;
  23.         Vector3 ReminderReference = Vector3.Zero;
  24.         bool CopVehReminder = false;
  25.         void HandleScriptReminders()
  26.         {          
  27.             if (ReminderReference == Vector3.Zero) ReminderReference = Game.Player.Character.Position;
  28.  
  29.             if (!FootReminder && !Game.Player.Character.IsInRangeOf(ReminderReference, 5f))
  30.             {
  31.                 string name = "~b~[" + ScriptName + " " + ScriptVer + "]";
  32.                 Util.AddNotification("", "", "", name + " ~w~loaded.");
  33.  
  34.                 Util.AddNotification("", "", "", "~w~Enter a police vehicle to start getting Callouts.");
  35.                 FootReminder = true;
  36.             }
  37.  
  38.             if(!CopVehReminder && (Game.Player.Character.IsInPoliceVehicle || Util.IsCop(Game.Player.Character)))
  39.             {
  40.                 CopVehReminder = true;
  41.  
  42.                 Util.AddQueuedHelpText("You're now ~b~on duty~w~.");
  43.                 Util.AddQueuedHelpText("You'll start being notified of ongoing pursuits.");
  44.                 Util.AddQueuedHelpText("Accept them hitting [ENTER] or decline waiting for the notification to dissapear.");
  45.                 Util.AddQueuedHelpText("["+MainMenuKey.ToString()+"] Will open the Settings/Backup menu, ["+ForceCalloutKey.ToString()+"] will force a new Callout.");
  46.             }
  47.         }
  48.        
  49.         public static int NumberOfCopsNearSuspect(SuspectHandler suspect, float radius)
  50.         {
  51.             int Num = 0;
  52.             Vector3 pos = suspect.Criminal.Position;
  53.             bool AnyCopNear = false;
  54.             if (Game.Player.Character.IsInRangeOf(pos, radius)) Num++;
  55.             foreach (CopUnitHandler unit in CopsChasing)
  56.             {
  57.                 if (unit.Leader.IsInRangeOf(pos, radius))
  58.                 {
  59.                     AnyCopNear = true;
  60.                 }
  61.             }
  62.             if (AnyCopNear)
  63.             {
  64.                 foreach (CopUnitHandler unit in CopsChasing)
  65.                 {
  66.                     if (unit.Leader.IsInRangeOf(pos, radius * 2)) Num++;
  67.                     foreach (Ped partner in unit.Partners) if (partner.IsInRangeOf(pos, radius * 2)) Num++;
  68.                 }
  69.             }
  70.  
  71.             return Num;
  72.         }
  73.         public static SuspectHandler GetRandomActiveCriminal()
  74.         {
  75.             List<SuspectHandler> criminals = new List<SuspectHandler>();
  76.             foreach (SuspectHandler criminal in CriminalsFleeing)
  77.             {
  78.                 if (!criminal.Surrendered() && !criminal.ShouldRemoveCriminal) criminals.Add(criminal);
  79.             }
  80.             if (criminals.Count > 0) return criminals[Util.RandomInt(0, criminals.Count - 1)];
  81.             else return null;
  82.         }
  83.  
  84.         public static SuspectHandler GetRandomSurrenderedCriminal(bool AllowBeingArrested)
  85.         {
  86.             List<SuspectHandler> criminals = new List<SuspectHandler>();
  87.             foreach (SuspectHandler criminal in CriminalsFleeing)
  88.             {
  89.                 if (criminal.Surrendered() && !criminal.ShouldRemoveCriminal)
  90.                 {
  91.                     //if ((!AllowBeingArrested && criminal.CopArrestingMe == null) || AllowBeingArrested) criminals.Add(criminal);
  92.                     if (AllowBeingArrested)
  93.                     {
  94.                         criminals.Add(criminal);
  95.                     }
  96.                     else if (criminal.CopArrestingMe == null)
  97.                     {
  98.                         criminals.Add(criminal);
  99.                     }
  100.                 }
  101.             }
  102.             if (criminals.Count > 0) return criminals[Util.RandomInt(0, criminals.Count - 1)];
  103.             else return null;
  104.         }
  105.         public static bool IsSuspectValid(SuspectHandler suspect)
  106.         {
  107.             return (suspect != null && Util.CanWeUse(suspect.Criminal) && suspect.Criminal.IsAlive && suspect.Criminal.Handle != -1 && suspect.ShouldRemoveCriminal != true);
  108.         }
  109.         public static bool IsCopUnitValid(CopUnitHandler unit)
  110.         {
  111.             return (unit != null && Util.CanWeUse(unit.Leader) && unit.Leader.IsAlive);
  112.         }
  113.         public static CopUnitHandler GetClosestCop(SuspectHandler criminal, bool CanArrest, bool AllowArresting)
  114.         {
  115.             //UI.Notify("closest cop");
  116.             CopUnitHandler finalcop = null;
  117.  
  118.             if (CopsChasing.Count > 0)
  119.             {
  120.                 foreach (CopUnitHandler Unit in CopsChasing)
  121.                 {
  122.                     if ((Unit.CanArrest() && Unit.CanArrest()) || (!Unit.CanArrest() && !CanArrest))
  123.                     {
  124.                         if (AllowArresting)
  125.                         {
  126.                             if (finalcop == null) finalcop = Unit;
  127.                             else if (Unit.Leader.Position.DistanceTo(criminal.Criminal.Position) < finalcop.Leader.Position.DistanceTo(criminal.Criminal.Position)) finalcop = Unit;
  128.                         }
  129.                         else if (Unit.State != CopState.Arrest)
  130.                         {
  131.                             if (finalcop == null) finalcop = Unit;
  132.                             else if (Unit.Leader.Position.DistanceTo(criminal.Criminal.Position) < finalcop.Leader.Position.DistanceTo(criminal.Criminal.Position)) finalcop = Unit;
  133.                         }
  134.                     }
  135.                 }
  136.             }
  137.             return finalcop;
  138.         }
  139.  
  140.         public static bool Debug = true;
  141.         static public string ScriptName = "Dangerous Individuals";
  142.         static public string ScriptVer = "v0.4";
  143.  
  144.         //STATIC INFO
  145.         public static List<string> PettyCrimes = new List<string> { "Animal Abuse", "Domestic Violence", "License Expired", "Illegal Inmigration", "Arson", "Reckless Driving", "Impaired Driving", "Speeding", "Forgery" };
  146.         public static List<string> MediumCrimes = new List<string> { "Robbery", "Drug dealing", "", "", "", "", };
  147.         public static List<string> HighTierCrimes = new List<string> { "", "", "", "", "", "", };
  148.         public static int TickRefTime = Game.GameTime;
  149.         public static int AutoDispatchRefTime = Game.GameTime;
  150.  
  151.         public static string LayoutFile = "Scripts/DangerousIndividuals/RacerLayouts.xml";
  152.         public static string ConfigFilename = "Scripts/DangerousIndividuals/Config.xml";
  153.         public static string CriminalVehicleFile = "Scripts/DangerousIndividuals/CriminalVehicles.xml";
  154.  
  155.         //KEYS
  156.         public static Keys MainMenuKey = Keys.B;
  157.         public static Keys ForceCalloutKey = Keys.X;
  158.  
  159.  
  160.         //PURSUIT VARIABLES
  161.         static public int CriminalsRLGroup = World.AddRelationshipGroup("CriminalsRLGroup");
  162.         static public int EnemyGangRLGroup = World.AddRelationshipGroup("EnemyGangRLGroup");
  163.         static public int PublicEnemyRLGroup = World.AddRelationshipGroup("PublicEnemyRLGroup");
  164.  
  165.         static public int CopsRLGroup = World.AddRelationshipGroup("LSPDCops");
  166.         static public int SurrenderedCriminalsRLGroup = World.AddRelationshipGroup("SurrenderedCriminals");
  167.  
  168.         static public int LostLOSThreshold = 30;
  169.  
  170.         public static List<CopUnitHandler> CopsChasing = new List<CopUnitHandler>();
  171.         public static List<CopUnitHandler> CopsToRemove = new List<CopUnitHandler>();
  172.  
  173.         public static List<SuspectHandler> CriminalsFleeing = new List<SuspectHandler>();
  174.         public static List<SuspectHandler> CriminalsToRemove = new List<SuspectHandler>();
  175.         public static List<Ped> SplitCriminals = new List<Ped>();
  176.         public static CriminalType SplitCriminalKind = CriminalType.ProffessionalsHeisters;
  177.  
  178.         public static List<dynamic> CriminalSelection = new List<dynamic> { 0 };
  179.         public static List<dynamic> CopschasingThatCriminal = new List<dynamic> { 0 };
  180.  
  181.         public static List<SuspectHandler> CriminalsSurrendered = new List<SuspectHandler>();
  182.  
  183.  
  184.         //NATIVEUI
  185.  
  186.  
  187.         private MenuPool _menuPool = new MenuPool();
  188.  
  189.         //When there are suspects
  190.         private UIMenu mainMenu = new UIMenu("LSPD Dispatch", "");
  191.         private UIMenuItem UISpawnLSPDCar = new UIMenuItem("Local Unit", "Average local unit.");
  192.         private UIMenuItem UISpawnLocalSWAT = new UIMenuItem("Local SWAT", "Granger with 4 SWAT units.");
  193.         private UIMenuItem UISpawnSWAT = new UIMenuItem("SWAT", "Riot with 8 SWAT units.");
  194.         private UIMenuItem UISpawnHeli = new UIMenuItem("Air Unit", "Unarmed Maverick. It will remain close to the suspect.");
  195.         private UIMenuItem UISpawnNOoSEHeli = new UIMenuItem("NOoSE Air Unit", "Armed Annihilator with four shooting SWAT units that will shoot the suspect from it.");
  196.         private UIMenuItem UISpawnArmy = new UIMenuItem("Army Barracks", "Barracks full of soldiers.");
  197.         private UIMenuItem UISpawnArmyHeli = new UIMenuItem("Army Attack heli", "Armed Attack Helicopter that will shoot at the suspect.");
  198.  
  199.         public static UIMenuCheckboxItem CloseRoads = new UIMenuCheckboxItem("Close roads", false, "If checked, all roads around you will be closed and won't contain traffic at all.");
  200.  
  201.         private UIMenuListItem UISelectCriminal = new UIMenuListItem("Suspect", CriminalSelection, 0);
  202.         private UIMenu UICopsChasingSelectedCriminalMenu = new UIMenu("Cops Chasing", "Dismiss any Units chasing this suspect.");
  203.         //private UIMenuListItem UIListCopsChasingCriminal = new UIMenuListItem("", CriminalSelection, 0);
  204.  
  205.         private UIMenuColoredItem UISuspectStatus = new UIMenuColoredItem("Fleeing Suspect", Color.Azure, Color.Wheat);
  206.         private UIMenuColoredItem UISuspectHeading = new UIMenuColoredItem("Headed", Color.DimGray, Color.White);
  207.         private UIMenuColoredItem UIsuspectPos = new UIMenuColoredItem("Last Seen", Color.DimGray, Color.White);
  208.  
  209.  
  210.  
  211.         //When there aren't suspects
  212.         private UIMenu SettingsMenu = new UIMenu("Settings", "Finetune your experience here.");
  213.  
  214.         private UIMenu AddonSelectionMenu = new UIMenu("Vehicle Add-Ons", "Finetune your experience here.");
  215.         private UIMenuItem AddonSelectionMenuItem = new UIMenuItem("Vehicle Add-Ons", "Vehicle Add-Ons.");
  216.  
  217.         private UIMenuCheckboxItem AllowMadMaxVehicles = new UIMenuCheckboxItem("Load Mad Max Vehicles", true, "Allows some criminals to spawn in Mad Max vehicles.");
  218.         private UIMenuCheckboxItem AllowRDEVehicles = new UIMenuCheckboxItem("Load RDE Vehicles", true, "Allows the cops to spawn in the vehicles Realism Dispatch Enhanced adds to the game.");
  219.         private UIMenuCheckboxItem AllowIVPack = new UIMenuCheckboxItem("Load IVPack Vehicles", true, "Allows criminals to spawn in IVPack vehicles.");
  220.         private UIMenuCheckboxItem AllowLoadingFromFile = new UIMenuCheckboxItem("Load criminal Vehicles fom file", true, "The script will load vehicles from "+CriminalVehicleFile+", and let the criminals use them.");
  221.  
  222.  
  223.         private UIMenu CalloutSelectionMenu = new UIMenu("Callout Selection", "Select the kind of callouts that can happen.");
  224.         private UIMenuItem CalloutSelectionMenuItem = new UIMenuItem("Callout Selection", "Select the kind of callouts that can happen.");
  225.  
  226.         private UIMenuCheckboxItem AllowAverageCallouts = new UIMenuCheckboxItem("Generic Criminals", true, "Average callouts range from Jaywalking to store robberies. Expect anything from footchases to shootouts.");
  227.         private UIMenuCheckboxItem AllowRaceCallouts = new UIMenuCheckboxItem("Illegal Races", true, "High speed chases await.");
  228.         private UIMenuCheckboxItem AllowHeistCallouts = new UIMenuCheckboxItem("Heists", true, "These kind of criminals are specialized in big robberies, have a well planned escape plan and don't fear the police.");
  229.         private UIMenuCheckboxItem AllowGangRiot = new UIMenuCheckboxItem("Gang activity", true, "Gang related shootouts, mostly. Hard to arrest, these people hate the pigs with all their heart.");
  230.         private UIMenuCheckboxItem AllowMilitary = new UIMenuCheckboxItem("Military vehicles", true, "Someone stole something powerful.");
  231.         private UIMenuCheckboxItem AllowTerrorism = new UIMenuCheckboxItem("Terrorists", true, "Resolve this callout quickly, because this kind of criminal actively tries to murder people. Beware of these fellas, they prefer to die rather than be arrested.");
  232.         private UIMenuCheckboxItem AllowCargoStealers = new UIMenuCheckboxItem("Cargo Steal", true, "This criminal has stolen a commercial vehicle, most likely to resell its contents overseas or something like that.");
  233.         private UIMenuCheckboxItem AllowEscapedPrisoner = new UIMenuCheckboxItem("Escaped Prisoners", true, "These people really want to dissapear for a while.");
  234.         private UIMenuCheckboxItem AllowMainCharacters = new UIMenuCheckboxItem("Main Characters", true, "These callouts involve the Main Characters. You probably know what to expect.");
  235.  
  236.         public static UIMenuCheckboxItem AllowChaseNotifications = new UIMenuCheckboxItem("Chase status Notifications", true, "Updates you on the state of the cops/suspects involved in the current chase.");
  237.         public static UIMenuCheckboxItem DebugNotifications = new UIMenuCheckboxItem("Debug mode", true, "Shows debug notifications meant for testing. '-' will spawn a harmless suspect near you and DEL will delete all criminals/cops.");
  238.         public static UIMenuCheckboxItem AllowAutomaticDispatch = new UIMenuCheckboxItem("Automatic Dispatch", true, "When chasing suspects, cop units will be dispatched as they are needed. Else, you'll have to spawn them manually.");
  239.         public static UIMenuCheckboxItem AllowOngoingChase = new UIMenuCheckboxItem("Allow Ongoing Chases", true, "This allows suspects to have other units already chasing them by the time you join in.");
  240.         public static UIMenuCheckboxItem PlayerCareMenu = new UIMenuCheckboxItem("Player Care Module", true, "If checked, the script will take care of all these petty things you would normally need to do manually via Trainer: You'll be healed and your armor replenished while you're in your vehicle and not chasing anyone. Your vehicle will be fully repaired when accepting any callout. You won't get Stars while chasing a suspect/having a cop playermodel.");
  241.         public static UIMenuCheckboxItem HelpNotifications = new UIMenuCheckboxItem("Help text", true, "While checked, the script will guide you around by displaying context-aware help text.");
  242.  
  243.  
  244.  
  245.         private UIMenuItem UtilitiesMenuItem = new UIMenuItem("Utilities", "Some utilities to enhance your experience.");
  246.         private UIMenu UtilitiesMenu = new UIMenu("Utilities", "Some utilities to enhance your experience.");
  247.         private UIMenuItem SaveCurrentVehicleLayout = new UIMenuItem("Save current vehicle Tuning Layout", "Use this option to add your current vehicle layout (color, liveries, mods, etc) to a text file. When responding to a Racing-related Callout, these Layouts will be randomly applied to the racer's vehicles.");
  248.         private UIMenuItem LoadRandomLayout = new UIMenuItem("Load random Tuning Layout", "Load a random layout from the Tuning Layouts list.");
  249.  
  250.  
  251.         private UIMenuItem UISaveVehToFileMenuItem = new UIMenuItem("Custom Vehicles for criminals", "");
  252.         private UIMenu UISaveVehToFileMenu = new UIMenu("Criminal Vehicles", "");
  253.  
  254.         private UIMenuListItem SaveVehToFileCategory = new UIMenuListItem("Category: ", Info.VehicleCategories,0,"Select the vehicle category you want the model to save to.");
  255.         private UIMenuItem SaveVehToFile = new UIMenuItem("Save Vehicle", "This utility will save your current vehicle model to a file, in the category selected above. Once you have restarted the script the criminals will use these vehicles.");
  256.         public static UIMenuCheckboxItem ForceUse = new UIMenuCheckboxItem("Only use these vehicles", false, "If enabled, criminals will only use the vehicles from the custom vehicle list. If disabled, criminals are able to use both Custom vehicles and vanilla vehicles.");
  257.  
  258.  
  259.         private UIMenuItem UIMenuKey = new UIMenuItem("Change Menu key [B]", "Change the current key to open this menu.");
  260.         private UIMenuItem UICalloutKey = new UIMenuItem("Change Force Callout key [B]", "Change the current key to force callouts.");
  261.  
  262.         public static List<CriminalType> CalloutPool = new List<CriminalType> { };
  263.  
  264.  
  265.         void AddNewVehicles()
  266.         {
  267.  
  268.             int i = 0;
  269.  
  270.  
  271.             if (File.Exists(@"" + CriminalVehicleFile))
  272.             {
  273.                 XmlDocument originalXml = new XmlDocument();
  274.                 originalXml.Load(@"" + CriminalVehicleFile);
  275.  
  276.  
  277.                 foreach (XmlElement element in originalXml.SelectNodes("//Average/*"))
  278.                 {
  279.                     bool Cleaned = false;
  280.                     Model test = Info.TranslateToVehicleModel(element.InnerText);
  281.                     if (test.IsValid)
  282.                     {
  283.                         i++;
  284.                         if (ForceUse.Checked && !Cleaned)
  285.                         {
  286.                             Info.AverageVehs.Clear();
  287.                             Cleaned = true;
  288.                         }
  289.                         Info.AverageVehs.Add(test);
  290.                     }
  291.  
  292.                 }
  293.                 foreach (XmlElement element in originalXml.SelectNodes("//Race/*"))
  294.                 {
  295.                     bool Cleaned = false;
  296.                     Model test = Info.TranslateToVehicleModel(element.InnerText);
  297.                     if (test.IsValid)
  298.                     {
  299.                         i++;
  300.                         if (ForceUse.Checked && !Cleaned)
  301.                         {
  302.                             Info.SportVehs.Clear();
  303.                             Cleaned = true;
  304.                         }
  305.  
  306.                         Info.SportVehs.Add(test);
  307.                     }
  308.                 }
  309.  
  310.                 foreach (XmlElement element in originalXml.SelectNodes("//Robbery/*"))
  311.                 {
  312.                     bool Cleaned = false;
  313.                     Model test = Info.TranslateToVehicleModel(element.InnerText);
  314.                     if (test.IsValid)
  315.                     {
  316.                         i++;
  317.                         if (ForceUse.Checked && !Cleaned)
  318.                         {
  319.                             Info.SUVs.Clear();
  320.                             Cleaned = true;
  321.                         }
  322.                         Info.SUVs.Add(test);
  323.                     }
  324.                 }
  325.                 foreach (XmlElement element in originalXml.SelectNodes("//Heist/*"))
  326.                 {
  327.                     bool Cleaned = false;
  328.                     Model test = Info.TranslateToVehicleModel(element.InnerText);
  329.                     if (test.IsValid)
  330.                     {
  331.                         i++;
  332.                         if (ForceUse.Checked && !Cleaned)
  333.                         {
  334.                             Info.HeistVehs.Clear();
  335.                             Cleaned = true;
  336.                         }
  337.                     }
  338.                     Info.HeistVehs.Add(test);
  339.                 }
  340.                 foreach (XmlElement element in originalXml.SelectNodes("//Military/*"))
  341.                 {
  342.                     bool Cleaned = false;
  343.                     Model test = Info.TranslateToVehicleModel(element.InnerText);
  344.                     if (test.IsValid)
  345.                     {
  346.                         i++;
  347.                         if (ForceUse.Checked && !Cleaned)
  348.                         {
  349.                             Info.MilitaryGradeVehs.Clear();
  350.                             Cleaned = true;
  351.                         }
  352.                     }
  353.  
  354.                     Info.MilitaryGradeVehs.Add(test);
  355.                 }
  356.             }
  357.             else
  358.             {
  359.                 Util.WarnPlayer(ScriptName + " " + ScriptVer, "No custom vehicle file found", "No vehicle file has been found in "+ CriminalVehicleFile+".");
  360.             }
  361.  
  362.  
  363.             if (AllowMadMaxVehicles.Checked)
  364.             {
  365.                 List<Model> vehs = new List<Model> { "deathdune", "gigahorse", "gonzo", "prock", "doofwagon", "warrig", };
  366.                 foreach (Model veh in vehs)
  367.                 {
  368.                     if (veh.IsValid) { i++; Info.MilitaryGradeVehs.Add(veh); }
  369.                 }
  370.             }
  371.             if (AllowIVPack.Checked)
  372.             {
  373.                 List<Model> vehs = new List<Model> { "sabre", "hakumai", "pinnacle", "esperanto", "interceptor", "vincent", "uranus", "willard", "pmp600", "chavos", "rebla", "admiral", "marbelle", "buccaneer3", "bobcat", "df8", "huntley2", "perennial", "pres", "sabre2", "solair", "schafter", "sentinel3", "sultan2", "stanier2", "fortune" };
  374.                 foreach (Model veh in vehs)
  375.                 {
  376.                     if (veh.IsValid)
  377.                     {
  378.                         i++;
  379.                         Info.AverageVehs.Add(veh);
  380.                     }
  381.                 }
  382.                 vehs = new List<Model> { "contender", "steed", "fxt", "huntley2", };
  383.                 foreach (Model veh in vehs)
  384.                 {
  385.                     if (veh.IsValid)
  386.                     {
  387.                         i++;
  388.                         Info.HeavyVehs.Add(veh);
  389.                     }
  390.                 }
  391.  
  392.                 vehs = new List<Model> { "supergt", "cheetah2", "coquette4", "feltzer", "pres2", "turismo2", };
  393.                 foreach (Model veh in vehs)
  394.                 {
  395.                     if (veh.IsValid)
  396.                     {
  397.                         i++;
  398.                         Info.SportVehs.Add(veh);
  399.                     }
  400.                 }
  401.                 vehs = new List<Model> { "brickade", };
  402.                 foreach (Model veh in vehs)
  403.                 {
  404.                     if (veh.IsValid)
  405.                     {
  406.                         i++;
  407.                         Info.StolenCashTrucks.Add(veh);
  408.                     }
  409.                 }
  410.             }
  411.  
  412.             if (AllowRDEVehicles.Checked)
  413.             {
  414.  
  415.                 //RDE
  416.                 i++;
  417.                 Info.AddVehicleToList("police5", Info.LSPDCars);
  418.  
  419.                 i++;
  420.                 Info.AddVehicleToList("pranger2", Info.SAPRCars);
  421.  
  422.                 i++;
  423.                 Info.AddVehicleToList("sheriff3", Info.Sheriff);
  424.  
  425.                 i++;
  426.                 Info.AddVehicleToList("sheriffriot", Info.BCSOSWATCars);
  427.  
  428.                 i++;
  429.                 Info.AddVehicleToList("nooseriot", Info.LSSDSWATCars);
  430.                 Info.RemoveVehicleFromLsit("nooseriot", Info.LSSDSWATCars);
  431.  
  432.                 i++;
  433.                 Info.AddVehicleToList("nooseannihilator", Info.NOoSEHelis);
  434.                 Info.RemoveVehicleFromLsit("annihilator", Info.NOoSEHelis);
  435.  
  436.                 //RDExtended Addon
  437.  
  438.                 //Federal Law Addon
  439.  
  440.                 //The Sheriffs of Blaine Addon
  441.                 i++;
  442.                 Info.AddVehicleToList("lssheriff", Info.LSSDCars);
  443.  
  444.                 i++;
  445.                 Info.AddVehicleToList("lssheriff2", Info.LSSDCars);
  446.  
  447.                 i++;
  448.                 Info.AddVehicleToList("lssheriff3", Info.LSSDCars);
  449.  
  450.                 i++;
  451.                 Info.AddVehicleToList("lssheriff4", Info.LSSDCars);
  452.  
  453.                 i++;
  454.                 Info.AddVehicleToList("sheriff3", Info.BCSOCars);
  455.  
  456.                 i++;
  457.                 Info.AddVehicleToList("sheriff4", Info.BCSOCars);
  458.  
  459.                 i++;
  460.                 Info.AddVehicleToList("sheriffmav2", Info.LSSDHelis);
  461.                 Info.RemoveVehicleFromLsit("polmav", Info.LSSDHelis);
  462.  
  463.                 i++;
  464.                 Info.AddVehicleToList("sheriffmav", Info.BCSOHelis);
  465.                 Info.RemoveVehicleFromLsit("polmav", Info.BCSOHelis);
  466.  
  467.                 i++;
  468.                 Info.AddVehicleToList("sheriffriot2", Info.LSSDSWATCars);
  469.  
  470.  
  471.             }
  472.  
  473.  
  474.             Util.WarnPlayer(ScriptName + " " + ScriptVer, "New vehicles added", "A total of " + i + " custom vehicles have been loaded succesfully.");
  475.         }
  476.  
  477.  
  478.         void ManageCalloutPool()
  479.         {
  480.             CalloutPool.Clear();
  481.  
  482.             if (AllowAverageCallouts.Checked)
  483.             {
  484.                 CalloutPool.Add(CriminalType.SmartThug);
  485.                 CalloutPool.Add(CriminalType.AggresiveThug);
  486.                 CalloutPool.Add(CriminalType.AmateurRobbers);
  487.                 CalloutPool.Add(CriminalType.ExperiencedRobbers);
  488.                 CalloutPool.Add(CriminalType.PacificFleeingFoot);
  489.             }
  490.             if (AllowHeistCallouts.Checked)
  491.             {
  492.                 CalloutPool.Add(CriminalType.NormalHeisters);
  493.                 CalloutPool.Add(CriminalType.ProffessionalsHeisters);
  494.                 CalloutPool.Add(CriminalType.CashTruckStealers);
  495.             }
  496.             if (AllowGangRiot.Checked)
  497.             {
  498.                 CalloutPool.Add(CriminalType.ViolentGang);
  499.                 CalloutPool.Add(CriminalType.ViolentBigGang);
  500.  
  501.                 CalloutPool.Add(CriminalType.ViolentGangFamilies);
  502.             }
  503.             if (AllowRaceCallouts.Checked)
  504.             {
  505.                 CalloutPool.Add(CriminalType.AmateurRacers);
  506.                 CalloutPool.Add(CriminalType.ProRacers);
  507.             }
  508.             if (AllowMilitary.Checked)
  509.             {
  510.                 CalloutPool.Add(CriminalType.MilitaryStealers);
  511.             }
  512.             if (AllowTerrorism.Checked)
  513.             {
  514.                 CalloutPool.Add(CriminalType.Terrorists);
  515.             }
  516.             if (AllowCargoStealers.Checked)
  517.             {              
  518.                 CalloutPool.Add(CriminalType.CargoStealers);
  519.                 CalloutPool.Add(CriminalType.CommertialVanStealers);
  520.             }
  521.             if (AllowEscapedPrisoner.Checked)
  522.             {
  523.                 CalloutPool.Add(CriminalType.EscapedPrisoner);
  524.             }
  525.             if (AllowMainCharacters.Checked)
  526.             {
  527.                 CalloutPool.Add(CriminalType.MainCharacters);
  528.             }
  529.  
  530.         }
  531.  
  532.         //GeneralInfo
  533.         public string GenerateContextForSuspect(CriminalType type)
  534.         {
  535.             if (new[] { CriminalType.AggresiveThug, CriminalType.SmartThug, }.Contains(type)) return Info.GenericMediumCrime[Util.RandomInt(0, Info.GenericMediumCrime.Count - 1)];
  536.  
  537.             if (new[] { CriminalType.AmateurRobbers }.Contains(type)) return Info.GenericMediumCrime[Util.RandomInt(0, Info.GenericMediumCrime.Count - 1)];
  538.  
  539.             if (new[] { CriminalType.ExperiencedRobbers, }.Contains(type)) return Info.VehicleGenericMediumCrime[Util.RandomInt(0, Info.VehicleGenericMediumCrime.Count - 1)];
  540.  
  541.             if (new[] { CriminalType.AmateurRacers, CriminalType.ProRacers }.Contains(type)) return Info.RacerTitle[Util.RandomInt(0, Info.RacerTitle.Count - 1)];
  542.  
  543.             if (new[] { CriminalType.ProffessionalsHeisters, }.Contains(type)) return Info.BigHeistTitle[Util.RandomInt(0, Info.BigHeistTitle.Count - 1)];
  544.  
  545.             if (new[] { CriminalType.NormalHeisters }.Contains(type)) return Info.NormalHeistTitle[Util.RandomInt(0, Info.NormalHeistTitle.Count - 1)];
  546.  
  547.             if (new[] { CriminalType.CashTruckStealers }.Contains(type)) return Info.CashTruckSteal[Util.RandomInt(0, Info.CashTruckSteal.Count - 1)];
  548.  
  549.             if (new[] { CriminalType.ViolentGang, CriminalType.ViolentBigGang, CriminalType.ViolentGangFamilies }.Contains(type)) return Info.FootGangTitle[Util.RandomInt(0, Info.FootGangTitle.Count - 1)];
  550.  
  551.             if (new[] { CriminalType.MilitaryStealers }.Contains(type)) return Info.MilitaryVehicleTitle[Util.RandomInt(0, Info.MilitaryVehicleTitle.Count - 1)];
  552.  
  553.             if (new[] { CriminalType.PacificFleeingFoot }.Contains(type)) return Info.FootGenericSmallCrime[Util.RandomInt(0, Info.FootGenericSmallCrime.Count - 1)];
  554.  
  555.             if (new[] { CriminalType.Terrorists }.Contains(type)) return Info.TerroristActivityTitle[Util.RandomInt(0, Info.TerroristActivityTitle.Count - 1)];
  556.  
  557.             if (new[] { CriminalType.CargoStealers }.Contains(type)) return Info.CargoStealersTitle[Util.RandomInt(0, Info.CargoStealersTitle.Count - 1)];
  558.             if (new[] { CriminalType.CommertialVanStealers }.Contains(type)) return Info.CommercialVanStealersTitle[Util.RandomInt(0, Info.CommercialVanStealersTitle.Count - 1)];
  559.  
  560.             if (new[] { CriminalType.EscapedPrisoner }.Contains(type)) return Info.EscapedPrisonerTitle[Util.RandomInt(0, Info.EscapedPrisonerTitle.Count - 1)];
  561.  
  562.             if (new[] { CriminalType.MainCharacters }.Contains(type)) return Info.GenericWantedPersonTitle[Util.RandomInt(0, Info.GenericWantedPersonTitle.Count - 1)];
  563.  
  564.  
  565.             return "No Context found for " + type.ToString();
  566.         }
  567.         static public string GenerateContextDetailsForSuspect(SuspectHandler suspect)
  568.         {
  569.             string details = "";
  570.             string accompanied = "";
  571.             if (suspect.Partners.Count > 0) accompanied = "s";
  572.             if (Util.CanWeUse(suspect.VehicleChosen))
  573.             {
  574.                 details += "Suspect" + accompanied + " seen in a " + (SimplifyColorString(suspect.VehicleChosen.PrimaryColor.ToString())).ToLowerInvariant() + " " + GetVehicleClassName(suspect.VehicleChosen) + ", heading " + Util.GetWhereIsHeaded(suspect.Criminal, false) + ". ";
  575.                 if (suspect.Flags.Contains(CriminalFlags.CAN_DRIVEBY)) details += "~r~Shots fired reported~w~, proceed with caution.";
  576.             }
  577.             else
  578.             {
  579.                 details += "Suspect" + accompanied + " last seen in " + World.GetStreetName(suspect.Criminal.Position) + ".";
  580.                 if (suspect.Criminal.Weapons.Current.Hash != WeaponHash.Unarmed)
  581.                 {
  582.                     if (suspect.Flags.Contains(CriminalFlags.CAN_STANDOFF_CAUTIOUS) && Util.RandomInt(0, 10) < 20) details += " Suspect" + accompanied + " might be armed, proceed with caution.";
  583.                     if (suspect.Flags.Contains(CriminalFlags.CAN_STANDOFF_AGGRESIVE) && Util.RandomInt(0, 10) < 90) details += " ~r~Gunfire has been reported in the vicinity.";
  584.                 }
  585.             }
  586.             return details;
  587.         }
  588.  
  589.         static public string SimplifyColorString(string color)
  590.         {
  591.             string newcolor = color;
  592.             string[] replace = { "Seafoam", "Poly", "Anthracite", "Sunrise", "Graphite", "Pueblo", "Golden", "Metallic", "Matte", "Pure", "PoliceCar", "Util", "Worn", "Dark", "Light", "Taxi", "Desert", "Foliage", "Hot", "Hunter", "Midnight", "Marine", "Formula", "Frost", "Garnet", "Epsilon", "Moss", "Olive", "Util", "Ultra", "Salmon", "Gasoline" };
  593.             foreach (string curr in replace)
  594.             {
  595.                 newcolor = newcolor.Replace(curr, string.Empty);
  596.             }
  597.             return newcolor;
  598.         }
  599.         static public string GetVehicleClassName(Vehicle veh)
  600.         {
  601.             if (new Model[] { VehicleHash.Kuruma2, VehicleHash.Insurgent, VehicleHash.Cognoscenti2, VehicleHash.Cog552, VehicleHash.Schafter5, VehicleHash.Schafter6, VehicleHash.Baller5, VehicleHash.Baller6, VehicleHash.Limo2 }.Contains(veh.Model)) return "armored vehicle";
  602.             if (veh.Model == VehicleHash.Stockade) return "securicar";
  603.             if (veh.Model == VehicleHash.PBus) return "prison bus";
  604.             if (veh.Model.IsBike) return "bike";
  605.             if (veh.Model.IsHelicopter) return "helicopter";
  606.             if (veh.Model.IsPlane) return "plane";
  607.  
  608.             switch (veh.ClassType)
  609.             {
  610.                 case VehicleClass.SUVs:
  611.                     {
  612.                         return "SUV";
  613.                     }
  614.                 case VehicleClass.Boats:
  615.                     {
  616.                         return "boat";
  617.                     }
  618.                 case VehicleClass.Emergency:
  619.                     {
  620.                         return "emergency vehicle";
  621.                     }
  622.                 case VehicleClass.Commercial:
  623.                     {
  624.                         return "commercial vehicle";
  625.                     }
  626.                 case VehicleClass.Compacts:
  627.                     {
  628.                         return "small vehicle";
  629.                     }
  630.                 case VehicleClass.Coupes:
  631.                     {
  632.                         return "coupĂ©";
  633.                     }
  634.                 case VehicleClass.Muscle:
  635.                     {
  636.                         return "muscle";
  637.                     }
  638.                 case VehicleClass.OffRoad:
  639.                     {
  640.                         return "4X4";
  641.                     }
  642.                 case VehicleClass.Sedans:
  643.                     {
  644.                         return "sedan";
  645.                     }
  646.                 case VehicleClass.Sports:
  647.                     {
  648.                         return "sports vehicle";
  649.                     }
  650.                 case VehicleClass.Super:
  651.                     {
  652.                         return "high end vehicle";
  653.                     }
  654.                 case VehicleClass.Motorcycles:
  655.                     {
  656.                         return "motorcycle";
  657.                     }
  658.                 case VehicleClass.Vans:
  659.                     {
  660.                         return "van";
  661.                     }
  662.             }
  663.             return "unidentified vehicle";
  664.  
  665.         }
  666.  
  667.         public static int UnitsPatrolling = 3;
  668.  
  669.         public DangerousIndividuals()
  670.         {
  671.             Tick += OnTick;
  672.             KeyDown += OnKeyDown;
  673.             KeyUp += OnKeyUp;
  674.  
  675.             //UI.Notify("~b~[" + ScriptName + " " + ScriptVer + "] (Closed beta) ~w~loaded.");
  676.  
  677.             Function.Call(Hash.REQUEST_STREAMED_TEXTURE_DICT, "WEB_LOSSANTOSPOLICEDEPT", true);
  678.             Function.Call(Hash.REQUEST_ANIM_DICT, "MP_ARRESTING");
  679.             Function.Call(Hash.REQUEST_ANIM_DICT, "mp_bank_heist_1");
  680.  
  681.             //Function.Call(Hash.REQUEST_STREAMED_TEXTURE_DICT, "WEB_LOSSANTOSPOLICEDEPT", true);
  682.  
  683.  
  684.             //Cops love cops, cops love me
  685.             Util.SetRelationshipBetweenGroups(CopsRLGroup, Game.Player.Character.RelationshipGroup, Relationship.Companion, true);
  686.             Util.SetRelationshipBetweenGroups(CopsRLGroup, Game.GenerateHash("COP"), Relationship.Companion, true);
  687.  
  688.             //Cops love surrendered criminals
  689.             Util.SetRelationshipBetweenGroups(CopsRLGroup, SurrenderedCriminalsRLGroup, Relationship.Companion, true);
  690.             Util.SetRelationshipBetweenGroups(CriminalsRLGroup, SurrenderedCriminalsRLGroup, Relationship.Companion, true);
  691.             Util.SetRelationshipBetweenGroups(Game.GenerateHash("COP"), SurrenderedCriminalsRLGroup, Relationship.Companion, true);
  692.  
  693.             //Criminals hate criminals from the othergroup
  694.             Util.SetRelationshipBetweenGroups(EnemyGangRLGroup, CriminalsRLGroup, Relationship.Hate, true);
  695.  
  696.  
  697.             //Criminals hate player and cops
  698.             Util.SetRelationshipBetweenGroups(CriminalsRLGroup, CopsRLGroup, Relationship.Hate, true);
  699.             Util.SetRelationshipBetweenGroups(CriminalsRLGroup, Game.GenerateHash("PLAYER"), Relationship.Hate, true);
  700.  
  701.             Util.SetRelationshipBetweenGroups(PublicEnemyRLGroup, CopsRLGroup, Relationship.Hate, true);
  702.             Util.SetRelationshipBetweenGroups(PublicEnemyRLGroup, Game.GenerateHash("CIVMALE"), Relationship.Hate, true);
  703.             Util.SetRelationshipBetweenGroups(PublicEnemyRLGroup, Game.GenerateHash("CIVFEMALE"), Relationship.Hate, true);
  704.  
  705.             Util.SetRelationshipBetweenGroups(PublicEnemyRLGroup, Game.GenerateHash("PLAYER"), Relationship.Hate, true);
  706.  
  707.             Util.SetRelationshipBetweenGroups(EnemyGangRLGroup, CopsRLGroup, Relationship.Hate, true);
  708.             Util.SetRelationshipBetweenGroups(EnemyGangRLGroup, Game.GenerateHash("PLAYER"), Relationship.Hate, true);
  709.  
  710.  
  711.             Game.Player.Character.IsPriorityTargetForEnemies = false;
  712.  
  713.  
  714.  
  715.             _menuPool.Add(mainMenu);
  716.             _menuPool.Add(SettingsMenu);
  717.             _menuPool.Add(UICopsChasingSelectedCriminalMenu);
  718.             _menuPool.Add(UtilitiesMenu);
  719.             _menuPool.Add(CalloutSelectionMenu);
  720.             _menuPool.Add(AddonSelectionMenu);
  721.             _menuPool.Add(UISaveVehToFileMenu);
  722.  
  723.             UtilitiesMenu.AddItem(SaveCurrentVehicleLayout);
  724.             UtilitiesMenu.AddItem(LoadRandomLayout);
  725.  
  726.             SettingsMenu.AddItem(CalloutSelectionMenuItem);
  727.             SettingsMenu.BindMenuToItem(CalloutSelectionMenu, CalloutSelectionMenuItem);
  728.             CalloutSelectionMenuItem.SetLeftBadge(UIMenuItem.BadgeStyle.Michael);
  729.  
  730.             SettingsMenu.AddItem(AddonSelectionMenuItem);
  731.             SettingsMenu.BindMenuToItem(AddonSelectionMenu, AddonSelectionMenuItem);
  732.             AddonSelectionMenuItem.SetLeftBadge(UIMenuItem.BadgeStyle.Michael);
  733.  
  734.             SettingsMenu.AddItem(UtilitiesMenuItem);
  735.             SettingsMenu.BindMenuToItem(UtilitiesMenu, UtilitiesMenuItem);
  736.             UtilitiesMenuItem.SetLeftBadge(UIMenuItem.BadgeStyle.Michael);
  737.  
  738.             AddonSelectionMenu.AddItem(AllowMadMaxVehicles);
  739.             AddonSelectionMenu.AddItem(AllowRDEVehicles);
  740.             AddonSelectionMenu.AddItem(AllowIVPack);
  741.  
  742.             AddonSelectionMenu.AddItem(UISaveVehToFileMenuItem);
  743.             AddonSelectionMenu.BindMenuToItem(UISaveVehToFileMenu, UISaveVehToFileMenuItem);
  744.  
  745.             UISaveVehToFileMenu.AddItem(SaveVehToFileCategory);
  746.             UISaveVehToFileMenu.AddItem(SaveVehToFile);
  747.             UISaveVehToFileMenu.AddItem(ForceUse);
  748.             ForceUse.Checked = false;
  749.             UISaveVehToFileMenuItem.SetLeftBadge(UIMenuItem.BadgeStyle.Michael);
  750.  
  751.  
  752.             CalloutSelectionMenu.AddItem(AllowAverageCallouts);
  753.             CalloutSelectionMenu.AddItem(AllowRaceCallouts);
  754.             CalloutSelectionMenu.AddItem(AllowHeistCallouts);
  755.             CalloutSelectionMenu.AddItem(AllowGangRiot);
  756.             CalloutSelectionMenu.AddItem(AllowMilitary);
  757.             CalloutSelectionMenu.AddItem(AllowTerrorism);
  758.             CalloutSelectionMenu.AddItem(AllowCargoStealers);
  759.             CalloutSelectionMenu.AddItem(AllowEscapedPrisoner);
  760.             CalloutSelectionMenu.AddItem(AllowMainCharacters);
  761.  
  762.             SettingsMenu.AddItem(HelpNotifications);
  763.             SettingsMenu.AddItem(AllowChaseNotifications);
  764.             SettingsMenu.AddItem(PlayerCareMenu);
  765.  
  766.             // Don't add Debug Mode in the released version
  767.             //SettingsMenu.AddItem(DebugNotifications);
  768.             DebugNotifications.Checked = false;
  769.             SettingsMenu.AddItem(AllowAutomaticDispatch);
  770.             AllowAutomaticDispatch.Checked = false;
  771.             SettingsMenu.AddItem(AllowOngoingChase);
  772.  
  773.             SettingsMenu.AddItem(UIMenuKey);
  774.             SettingsMenu.AddItem(UICalloutKey);
  775.  
  776.            
  777.             mainMenu.AddItem(UISelectCriminal);
  778.             mainMenu.AddItem(UISpawnLSPDCar);
  779.             mainMenu.AddItem(UISpawnHeli);
  780.             mainMenu.AddItem(UISpawnLocalSWAT);
  781.             mainMenu.AddItem(UISpawnSWAT);
  782.             mainMenu.AddItem(UISpawnNOoSEHeli);
  783.             mainMenu.AddItem(UISpawnArmy);
  784.             mainMenu.AddItem(UISpawnArmyHeli);
  785.             mainMenu.AddItem(CloseRoads);
  786.  
  787.             mainMenu.BindMenuToItem(UICopsChasingSelectedCriminalMenu, UISelectCriminal);
  788.  
  789.  
  790.  
  791.             foreach (UIMenu menu in _menuPool.ToList())
  792.             {
  793.                 menu.RefreshIndex();
  794.                 menu.OnItemSelect += OnItemSelect;
  795.                 menu.OnIndexChange += OnIndexChange;
  796.             }
  797.  
  798.             LoadSettings(ConfigFilename);
  799.  
  800.             UIMenuKey.Text = "Change Menu key [" + (MainMenuKey).ToString() + "]";
  801.             UICalloutKey.Text = "Change Force Callout key [" + (ForceCalloutKey).ToString() + "]";
  802.  
  803.  
  804.  
  805.             AddNewVehicles();
  806.         }
  807.  
  808.  
  809.         public static int UnitsNearSuspect(SuspectHandler suspect, float radius)
  810.         {
  811.             int Number = 0;
  812.             foreach (CopUnitHandler Unit in CopsChasing)
  813.             {
  814.                 if (Unit.Leader.Position.DistanceTo(suspect.Criminal.Position) < radius) Number++;
  815.             }
  816.             return Number;
  817.         }
  818.         public string GetSuspectStatus(SuspectHandler suspect, bool State, bool Street, bool Area, bool direction)
  819.         {
  820.             string desc = "";
  821.             if (State)
  822.             {
  823.                 if (suspect.State == CriminalState.Surrendering || suspect.State == CriminalState.Arrested || suspect.State == CriminalState.DealtWith)
  824.                 {
  825.                     desc += "In custody";
  826.                 }
  827.                 else
  828.                 {
  829.                     if (suspect.Criminal.IsInCombat) desc += "shootout";
  830.                     else
  831.                     {
  832.                         if (Util.CanWeUse(suspect.Criminal.CurrentVehicle)) desc += "" + suspect.Criminal.CurrentVehicle.FriendlyName + ""; else desc += "Fleeing (foot)";
  833.                     }
  834.                     //if (suspect.Partners.Count > 0) desc += ", ~y~Accompanied";
  835.                 }
  836.             }
  837.             if (direction) desc += " - " + Util.GetWhereIsHeaded(suspect.Criminal, true);
  838.             if (Street) desc += " - " + World.GetStreetName(suspect.Criminal.Position);
  839.             if (Area) desc += " - " + World.GetZoneName(suspect.Criminal.Position);
  840.  
  841.             return desc;
  842.         }
  843.  
  844.  
  845.  
  846.         public void HandleSuspectSelectionMenu()
  847.         {
  848.             if (CriminalsFleeing.Count > 0)
  849.             {
  850.                 if (!_menuPool.IsAnyMenuOpen())
  851.                 {
  852.                     int CriminalNumber = 0;
  853.  
  854.                     CriminalSelection.Clear();
  855.                     for (int i = 0; i < CriminalsFleeing.Count; i++)
  856.                     {
  857.                         CriminalNumber++;
  858.                         CriminalSelection.Add(CriminalNumber + " " + GetSuspectStatus(CriminalsFleeing[i], true, true, false, true));
  859.                     }
  860.                     int pos = 0;
  861.                     if (mainMenu.MenuItems.Contains(UISelectCriminal))
  862.                     {
  863.                         pos = mainMenu.MenuItems.IndexOf(UISelectCriminal);
  864.                         mainMenu.RemoveItemAt(mainMenu.MenuItems.IndexOf(UISelectCriminal));
  865.                         UISelectCriminal = new UIMenuListItem("", CriminalSelection, 0);
  866.                         mainMenu.AddItem(UISelectCriminal);
  867.                         mainMenu.RemoveItemAt(mainMenu.MenuItems.IndexOf(UISelectCriminal));
  868.                         mainMenu.MenuItems.Insert(pos, UISelectCriminal);
  869.                     }
  870.                     else
  871.                     {
  872.                         UISelectCriminal = new UIMenuListItem("", CriminalSelection, 0);
  873.                         mainMenu.AddItem(UISelectCriminal);
  874.                     }
  875.  
  876.                     mainMenu.BindMenuToItem(UICopsChasingSelectedCriminalMenu, UISelectCriminal);
  877.  
  878.                 }
  879.                 //mainMenu.CounterPretext= "Headed " + Util.GetWhereIsHeaded(CriminalsFleeing[UISelectCriminal.Index].Criminal);
  880.                 //UISelectCriminal.Description= "Headed " + Util.GetWhereIsHeaded(CriminalsFleeing[UISelectCriminal.Index].Criminal);
  881.                 //UISuspectHeading.Text = "Headed " + Util.GetWhereIsHeaded(CriminalsFleeing[UISelectCriminal.Index].Criminal);
  882.                 //UIsuspectPos.Text = "Last Seen in " + World.GetStreetName(CriminalsFleeing[UISelectCriminal.Index].Criminal.Position);
  883.                 //UISuspectStatus.Text =  GetSuspectStatus(CriminalsFleeing[UISelectCriminal.Index]);
  884.             }
  885.  
  886.         }
  887.  
  888.  
  889.         public void OnIndexChange(UIMenu sender, int index)
  890.         {
  891.             /*
  892.             if(index == sender.MenuItems.IndexOf(UISelectCriminal))
  893.             {
  894.                 if (!mainMenu.MenuItems.Contains(UISuspectHeading))  mainMenu.AddItem(UISuspectHeading);
  895.             }
  896.             else
  897.             {
  898.                if(mainMenu.MenuItems.Contains(UISuspectHeading)) mainMenu.RemoveItemAt(mainMenu.MenuItems.IndexOf(UISuspectHeading));
  899.             }
  900.             */
  901.         }
  902.         public void UpdateCopsChasingCriminals()
  903.         {
  904.  
  905.         }
  906.         public void OnItemSelect(UIMenu sender, UIMenuItem selectedItem, int index)
  907.         {
  908.             if (selectedItem == SaveVehToFile)
  909.             {
  910.                 if (Util.CanWeUse(Game.Player.Character.CurrentVehicle))
  911.                 {
  912.                     string Vehicle = Game.Player.Character.CurrentVehicle.Model.Hash.ToString();
  913.                     Model Vehicle2 = int.Parse(Vehicle);
  914.                     if (Vehicle2.IsVehicle)
  915.                     {
  916.                         SaveCriminalVehicle(CriminalVehicleFile, SaveVehToFileCategory.IndexToItem(SaveVehToFileCategory.Index), Game.Player.Character.CurrentVehicle);
  917.                     }
  918.                     else
  919.                     {
  920.                         Util.WarnPlayer(ScriptName + " " + ScriptVer, "MODEL ERROR", "Cannot save this vehicle. " + Vehicle + " Doesn't seem to be a valid vehicle hash.");
  921.                         Util.WarnPlayer(ScriptName + " " + ScriptVer, "MODEL ERROR", "Please, edit " + CriminalVehicleFile + " yourself and add the vehicle name/hash manually.");
  922.                     }
  923.                 }
  924.             }
  925.             //Keys
  926.             if (selectedItem == UIMenuKey)
  927.             {
  928.                 bool CouldParse = Enum.TryParse<Keys>(Game.GetUserInput(30), out MainMenuKey);
  929.  
  930.                 if (!CouldParse)
  931.                 {
  932.                     UI.Notify("~y~That key does not exist. ~w~Make sure that capital letters match (Add instead of add).");
  933.                 }
  934.                 else
  935.                 {
  936.                     UIMenuKey.Text = "Change Main Menu key [" + (MainMenuKey).ToString() + "]";
  937.                 }
  938.             }
  939.  
  940.             if (selectedItem == UICalloutKey)
  941.             {
  942.                 bool CouldParse = Enum.TryParse<Keys>(Game.GetUserInput(30), out ForceCalloutKey);
  943.  
  944.                 if (!CouldParse)
  945.                 {
  946.                     UI.Notify("~y~That key does not exist. ~w~Make sure that capital letters match (Add instead of add).");
  947.                 }
  948.                 else
  949.                 {
  950.                     UICalloutKey.Text = "Change Force Callout key [" + (ForceCalloutKey).ToString() + "]";
  951.  
  952.                 }
  953.             }
  954.  
  955.             //Vehicle Layout utility
  956.             if (selectedItem == SaveCurrentVehicleLayout)
  957.             {
  958.                 Vehicle veh = Game.Player.Character.CurrentVehicle;
  959.                 if (Util.CanWeUse(veh))
  960.                 {
  961.                     string Error = Util.SaveVehicleLayoutToFile(veh, LayoutFile);
  962.                     if (Error != "") UI.Notify("~o~Error applying Layout: ~w~" + Error);
  963.                     else UI.Notify("Vehicle layout saved to " + LayoutFile + ".");
  964.                 }
  965.                 else UI.Notify("~o~You need to be in a vehicle to do that.");
  966.             }
  967.             if (selectedItem == LoadRandomLayout)
  968.             {
  969.                 Vehicle veh = Game.Player.Character.CurrentVehicle;
  970.                 if (Util.CanWeUse(veh))
  971.                 {
  972.                     string Error = Util.ApplyRandomVehicleLayoutFromFile(veh, LayoutFile);
  973.                     if (Error != "") UI.Notify("~o~Error applying Layout: ~w~" + Error);
  974.                 }
  975.                 else UI.Notify("~o~You need to be in a vehicle to do that.");
  976.             }
  977.             if (selectedItem == UISelectCriminal || sender == UICopsChasingSelectedCriminalMenu)
  978.             {
  979.                 for (int i = 0; i < UICopsChasingSelectedCriminalMenu.MenuItems.Count; i++)
  980.                 {
  981.                     UICopsChasingSelectedCriminalMenu.RemoveItemAt(0);
  982.                     UICopsChasingSelectedCriminalMenu.Clear();
  983.                 }
  984.  
  985.                 foreach (string text in GetCopschasingIt(CriminalsFleeing[UISelectCriminal.Index]))
  986.                 {
  987.                     UICopsChasingSelectedCriminalMenu.AddItem(new UIMenuItem(text));
  988.                 }
  989.             }
  990.             if (sender == UICopsChasingSelectedCriminalMenu && UICopsChasingSelectedCriminalMenu.MenuItems.Count > 1)
  991.             {
  992.                 if (CopsChasing[index] != null)
  993.                 {
  994.                     //Util.AddNotification("web_lossantospolicedept", "~b~" + CopsChasing[index].CopVehicle.FriendlyName + " unit", "Unit Dismissed", "I'm no longer required.");
  995.                     CopsChasing[index].ShouldRemoveCopUnit = true;
  996.                     //CopsChasing[index].FindNewTarget();
  997.                     UICopsChasingSelectedCriminalMenu.RemoveItemAt(index);
  998.                 }
  999.             }
  1000.             List<Vector3> Stations = new List<Vector3>();
  1001.             Vector3 pos = Vector3.Zero;
  1002.  
  1003.             if (sender == mainMenu)
  1004.             {
  1005.                 Stations.AddRange(Util.LSSDPoliceStations);
  1006.                 Stations.AddRange(Util.LSPDPoliceStations);
  1007.                 pos = World.GetNextPositionOnStreet(Util.GetClosestLocation(CriminalsFleeing[UISelectCriminal.Index].Criminal.Position, Stations)).Around(5f);
  1008.             }
  1009.  
  1010.             if (selectedItem == UISpawnLSPDCar)
  1011.             {
  1012.                 if (UnitsPatrolling > 0)
  1013.                 {
  1014.                     UnitsPatrolling--;
  1015.                     pos = Util.GenerateSpawnPos(CriminalsFleeing[UISelectCriminal.Index].Criminal.Position.Around(300), Util.Nodetype.Road, false);
  1016.                     while (pos.DistanceTo(Game.Player.Character.Position) < 100)
  1017.                     {
  1018.                         pos = Util.GenerateSpawnPos(CriminalsFleeing[UISelectCriminal.Index].Criminal.Position.Around(300), Util.Nodetype.Road, false);
  1019.                     }
  1020.                     if (UnitsPatrolling == 0)
  1021.                     {
  1022.                         if (AllowChaseNotifications.Checked) Util.Notify("web_lossantospolicedept", "~b~DISPATCH", "NO NEARBY UNITS", "Any new patrol units called will come from the closest Station.");
  1023.                     }
  1024.                 }
  1025.                 if (CriminalsFleeing.Count > 0) DangerousIndividuals.CopsChasing.Add(new CopUnitHandler(CopUnitType.AveragePolice, CriminalsFleeing[UISelectCriminal.Index], pos, true));
  1026.             }
  1027.             if (selectedItem == UISpawnLocalSWAT)
  1028.             {
  1029.                 if (CriminalsFleeing.Count > 0) CopsChasing.Add(new CopUnitHandler(CopUnitType.LocalNoose, CriminalsFleeing[UISelectCriminal.Index], pos,true));
  1030.             }
  1031.             if (selectedItem == UISpawnNOoSEHeli)
  1032.             {
  1033.                 if (CriminalsFleeing.Count > 0) DangerousIndividuals.CopsChasing.Add(new CopUnitHandler(CopUnitType.NOoSEAirUnit, CriminalsFleeing[UISelectCriminal.Index], pos, true));
  1034.             }
  1035.             if (selectedItem == UISpawnHeli)
  1036.             {
  1037.                 if (CriminalsFleeing.Count > 0) DangerousIndividuals.CopsChasing.Add(new CopUnitHandler(CopUnitType.AirUnit, CriminalsFleeing[UISelectCriminal.Index], pos, true));
  1038.             }
  1039.             if (selectedItem == UISpawnSWAT)
  1040.             {
  1041.                 if (CriminalsFleeing.Count > 0) DangerousIndividuals.CopsChasing.Add(new CopUnitHandler(CopUnitType.NOoSE, CriminalsFleeing[UISelectCriminal.Index], pos, true));
  1042.             }
  1043.             if (selectedItem == UISpawnArmy)
  1044.             {
  1045.                 if (CriminalsFleeing.Count > 0) DangerousIndividuals.CopsChasing.Add(new CopUnitHandler(CopUnitType.Army, CriminalsFleeing[UISelectCriminal.Index], pos, true));
  1046.             }
  1047.             if (selectedItem == UISpawnArmyHeli)
  1048.             {
  1049.                 if (CriminalsFleeing.Count > 0) DangerousIndividuals.CopsChasing.Add(new CopUnitHandler(CopUnitType.ArmyAirUnit, CriminalsFleeing[UISelectCriminal.Index], pos, true));
  1050.             }
  1051.         }
  1052.  
  1053.         List<string> GetCopschasingIt(SuspectHandler Suspect)
  1054.         {
  1055.             List<string> CopList = new List<string>();
  1056.  
  1057.             CopschasingThatCriminal.Clear();
  1058.             foreach (CopUnitHandler unit in CopsChasing)
  1059.             {
  1060.                 if (unit.Suspect == Suspect) { CopList.Add(unit.CopVehicle.FriendlyName + " Unit"); CopschasingThatCriminal.Add(unit.CopVehicle.FriendlyName + " Unit"); }
  1061.             }
  1062.             return CopList;
  1063.         }
  1064.  
  1065.         public int NumberOfUnitsDispatched(CopUnitType type)
  1066.         {
  1067.             int Number = 0;
  1068.             foreach (CopUnitHandler unit in CopsChasing)
  1069.             {
  1070.                 if (unit.UnitType == type) Number++;
  1071.             }
  1072.             return Number;
  1073.         }
  1074.  
  1075.         public int NumberOfUnitsDispatched(SuspectHandler suspect, CopUnitType type)
  1076.         {
  1077.             int Number = 0;
  1078.             foreach (CopUnitHandler unit in suspect.CopsChasingMe)
  1079.             {
  1080.                 if (unit.UnitType == type) Number++;
  1081.             }
  1082.             return Number;
  1083.         }
  1084.         public bool IsPlayerChasingSuspect(SuspectHandler suspect)
  1085.         {
  1086.             if (suspect == null) return false;
  1087.             else return Game.Player.Character.IsInRangeOf(suspect.Criminal.Position, 100f);
  1088.         }
  1089.         public void HandleAutomaticCopDispatch()
  1090.         {
  1091.             if (CriminalsFleeing.Count > 0 && CopsChasing.Count < 8)
  1092.             {
  1093.                 foreach (SuspectHandler Suspect in CriminalsFleeing)
  1094.                 {
  1095.                     bool ShouldDispatch = false;
  1096.                     CopUnitType UnitType = CopUnitType.AveragePolice;
  1097.  
  1098.                     if (Suspect.Surrendered() && (NumberOfUnitsDispatched(CopUnitType.AveragePolice) + NumberOfUnitsDispatched(CopUnitType.Patrol) + NumberOfUnitsDispatched(CopUnitType.PrisonerTransporter)) * 2 < CriminalsFleeing.Count) //&& !IsPlayerChasingSuspect(Suspect)
  1099.                     {
  1100.                         ShouldDispatch = true;
  1101.                         UnitType = CopUnitType.PrisonerTransporter;
  1102.                     }
  1103.                     if (!Suspect.Surrendered())
  1104.                     {
  1105.                         //Patrol Dispatch
  1106.                         if (Suspect.Auth_DeadlyForce)// && NumberOfUnitsDispatched(Suspect, CopUnitType.AveragePolice) < 2)|| (!IsPlayerChasingSuspect(Suspect) && NumberOfUnitsDispatched(Suspect, CopUnitType.AveragePolice) == 0)
  1107.                         {
  1108.                             if (NumberOfUnitsDispatched(Suspect, CopUnitType.AveragePolice) < 2)
  1109.                             {
  1110.                                 ShouldDispatch = true;
  1111.                                 UnitType = CopUnitType.AveragePolice;
  1112.                             }
  1113.                         }
  1114.                         else
  1115.                         {
  1116.                             if (NumberOfUnitsDispatched(Suspect, CopUnitType.AveragePolice) < 1 && !IsPlayerChasingSuspect(Suspect))
  1117.                             {
  1118.                                 ShouldDispatch = true;
  1119.                                 UnitType = CopUnitType.AveragePolice;
  1120.                             }
  1121.                         }
  1122.  
  1123.                         //Air Units dispatch
  1124.                         if (NumberOfUnitsDispatched(CopUnitType.AirUnit) < 2)
  1125.                         {
  1126.                             if (Util.CanWeUse(Suspect.VehicleChosen) && Suspect.VehicleChosen.Speed > 20f && !IsPlayerChasingSuspect(Suspect) && NumberOfUnitsDispatched(Suspect, CopUnitType.AirUnit) + NumberOfUnitsDispatched(Suspect, CopUnitType.NOoSEAirUnit) == 0)
  1127.                             {
  1128.                                 CopUnitHandler closestcop = GetClosestCop(Suspect, true, false);
  1129.                                 if (closestcop == null || !closestcop.Leader.IsInRangeOf(Suspect.Criminal.Position, 100f))
  1130.                                 {
  1131.                                     ShouldDispatch = true;
  1132.                                     UnitType = CopUnitType.AirUnit;
  1133.                                 }
  1134.                             }
  1135.                         }
  1136.  
  1137.                         //Noose Dispatch
  1138.                         if (Suspect.CopsKilled > 2 && NumberOfUnitsDispatched(CopUnitType.LocalNoose) < 3 && NumberOfUnitsDispatched(Suspect, CopUnitType.LocalNoose) < 1)
  1139.                         {
  1140.                             ShouldDispatch = true;
  1141.                             UnitType = CopUnitType.LocalNoose;
  1142.                         }
  1143.                         if (Suspect.CopsKilled > 5 && NumberOfUnitsDispatched(CopUnitType.NOoSE) < 2 && NumberOfUnitsDispatched(Suspect, CopUnitType.NOoSE) < 1)
  1144.                         {
  1145.                             ShouldDispatch = true;
  1146.                             UnitType = CopUnitType.NOoSE;
  1147.                         }
  1148.                     }
  1149.  
  1150.                     if (ShouldDispatch)
  1151.                     {
  1152.                         Vector3 pos = Info.GetSpawnpointFor(UnitType, Suspect.Criminal.Position);
  1153.                         CopsChasing.Add(new CopUnitHandler(UnitType, Suspect, pos, true));
  1154.                     }
  1155.                 }
  1156.             }
  1157.         }
  1158.  
  1159.  
  1160.         //Make sure all criminals have at least one cop chasing them
  1161.         void HandleCopDistribution()
  1162.         {
  1163.             foreach (SuspectHandler criminal in CriminalsFleeing)
  1164.             {
  1165.                 criminal.CopsChasingMe.Clear();
  1166.                 int copsChasingIt = 0;
  1167.  
  1168.                 //If player is chasing criminal
  1169.                 if (IsPlayerChasingSuspect(criminal)) copsChasingIt++;
  1170.  
  1171.                 foreach (CopUnitHandler unit in CopsChasing)
  1172.                 {
  1173.                     if (unit.Suspect.Criminal.Handle == criminal.Criminal.Handle)
  1174.                     {
  1175.                         copsChasingIt++;
  1176.                         criminal.CopsChasingMe.Add(unit);
  1177.                     }
  1178.                 }
  1179.  
  1180.                 if (copsChasingIt == 0 && !criminal.Surrendered() && CopsChasing.Count >= CriminalsFleeing.Count)
  1181.                 {
  1182.                     //UI.Notify("A cop has been relocated for that criminal");
  1183.                     CopUnitHandler relocated = GetClosestCop(criminal, true, true); // CopsChasing[Util.RandomInt(0, CopsChasing.Count - 1)];
  1184.                     if (relocated != null)
  1185.                     {
  1186.                         relocated.Suspect = criminal;
  1187.                         relocated.Leader.Task.ClearAll();
  1188.                         if (AllowChaseNotifications.Checked) Util.AddNotification("web_lossantospolicedept", "~b~" + relocated.CopVehicle.FriendlyName + " unit", "Chase Update", "I'm going after them.");
  1189.                     }
  1190.                     //if(relocated.CopVehicle.Model.IsHelicopter) Function.Call(Hash.TASK_HELI_CHASE, relocated.Leader, relocated.Suspect.Criminal, 20f, 20f, 10f);
  1191.                 }
  1192.             }
  1193.         }
  1194.         Vector2 World3DToScreen2d(Vector3 pos)
  1195.         {
  1196.             var x2dp = new OutputArgument();
  1197.             var y2dp = new OutputArgument();
  1198.  
  1199.             Function.Call<bool>(Hash._WORLD3D_TO_SCREEN2D, pos.X, pos.Y, pos.Z, x2dp, y2dp);
  1200.             return new Vector2(x2dp.GetResult<float>(), y2dp.GetResult<float>());
  1201.         }
  1202.         void HandlePlayerEquipment()
  1203.         {
  1204.             if (Game.Player.Character.IsInPoliceVehicle && CriminalsFleeing.Count==0)
  1205.             {
  1206.                 if (!Game.Player.Character.Weapons.HasWeapon(WeaponHash.StunGun)) Game.Player.Character.Weapons.Give(WeaponHash.StunGun, -1, false, true);
  1207.                 if (Game.Player.Character.Health < Game.Player.Character.MaxHealth) Game.Player.Character.Health += 5;
  1208.                 if (Game.Player.Character.Armor < 100) Game.Player.Character.Armor += 100;
  1209.  
  1210.             }
  1211.         }
  1212.  
  1213.         void OnTick(object sender, EventArgs e)
  1214.         {
  1215.             if (CloseRoads.Checked && CriminalsFleeing.Count == 0) CloseRoads.Checked = false;
  1216.  
  1217.             if (CloseRoads.Checked)
  1218.             {
  1219.                 Function.Call(Hash.SET_VEHICLE_DENSITY_MULTIPLIER_THIS_FRAME, 0f);
  1220.                 Function.Call(Hash.SET_RANDOM_VEHICLE_DENSITY_MULTIPLIER_THIS_FRAME, 0f);
  1221.                 Function.Call(Hash.SET_PARKED_VEHICLE_DENSITY_MULTIPLIER_THIS_FRAME, 0f);
  1222.             }
  1223.  
  1224.             if (mainMenu.Visible || UICopsChasingSelectedCriminalMenu.Visible)
  1225.             {
  1226.                 Function.Call(Hash._START_SCREEN_EFFECT, "SwitchHUDOut", 0, true);
  1227.                 Function.Call(Hash.SET_GAME_PAUSED, true);
  1228.             }
  1229.             else
  1230.             {
  1231.                 Function.Call(Hash.SET_GAME_PAUSED, false);
  1232.                 if (Function.Call<int>(Hash._GET_SCREEN_EFFECT_IS_ACTIVE, "SwitchHUDOut") != 0) Function.Call(Hash._STOP_ALL_SCREEN_EFFECTS);
  1233.             }
  1234.  
  1235.             if (Game.IsControlJustPressed(2, GTA.Control.Context))
  1236.             {
  1237.                 /*
  1238.  
  1239.                             Function.Call(Hash.TASK_PLAY_ANIM, Game.Player.Character, "mp_bank_heist_1", "prone_l_front_intro", 1f, 1f, -1,2,0f, false, false, false);
  1240.                 Function.Call(Hash.TASK_PLAY_ANIM, Game.Player.Character, "mp_arresting", "b_arrest_on_floor", 1f, 1f, -1, 2, 0f, false, false, false);
  1241.                 Function.Call(Hash.TASK_PLAY_ANIM, Game.Player.Character, "mp_arresting", "a_arrest_on_floor", 1f, 1f, -1, 2, 0f, false, false, false);
  1242.  
  1243.                 if(Function.Call<bool>(Hash._TRANSITION_FROM_BLURRED, 1000f)) Function.Call<bool>(Hash._TRANSITION_FROM_BLURRED, 1000f); else Function.Call<bool>(Hash._TRANSITION_TO_BLURRED, 10f);
  1244.                 Script.Wait(100);
  1245.                 if (Function.Call<bool>(Hash._TRANSITION_FROM_BLURRED, 1000f)) Function.Call<bool>(Hash._TRANSITION_FROM_BLURRED, 100f); else Function.Call<bool>(Hash._TRANSITION_TO_BLURRED, 1000f);
  1246.                 */
  1247.             }
  1248.  
  1249.             if (Game.GameTime > AutoDispatchRefTime)
  1250.             {
  1251.                 AutoDispatchRefTime = Game.GameTime + 10000;
  1252.                 if (AllowAutomaticDispatch.Checked) HandleAutomaticCopDispatch();
  1253.             }
  1254.  
  1255.             if (Game.GameTime > TickRefTime)
  1256.             {
  1257.                 TickRefTime = Game.GameTime + 1000;
  1258.  
  1259.                 if (CalloutNotification == -1 && CriminalsFleeing.Count == 0 && Info.IsPlayerOnDuty() && Game.Player.Character.IsStopped && !_menuPool.IsAnyMenuOpen() && Util.RandomInt(0, 10) < 2) GenerateCallout();
  1260.                 if (CriminalsFleeing.Count > 0 || Util.IsCop(Game.Player.Character))
  1261.                 {
  1262.                     Function.Call(Hash.SET_MAX_WANTED_LEVEL, 0);
  1263.                     if (Game.Player.WantedLevel > 0) Game.Player.WantedLevel = 0;
  1264.                 }
  1265.                 else Function.Call(Hash.SET_MAX_WANTED_LEVEL, 5);
  1266.  
  1267.                if(HelpNotifications.Checked) HandleScriptReminders();
  1268.                 HandlePlayerEquipment();
  1269.                 HandleCopDistribution();
  1270.                 if (UnitsPatrolling < 3 && Util.RandomInt(0, 10) < 3)
  1271.                 {
  1272.                     UnitsPatrolling++;
  1273.                     if (AllowChaseNotifications.Checked && UnitsPatrolling == 1) Util.AddNotification("web_lossantospolicedept", "~b~DISPATCH", "NEAR UNITS AVAILABLE", "There are units in standby near your position.");
  1274.                 }
  1275.  
  1276.  
  1277.  
  1278.                 CriminalsSurrendered.Clear();
  1279.                 foreach (SuspectHandler Suspect in CriminalsFleeing)
  1280.                 {
  1281.                     if (Suspect.Surrendered()) CriminalsSurrendered.Add(Suspect);
  1282.                 }
  1283.             }
  1284.  
  1285.  
  1286.             HandleSuspectSelectionMenu();
  1287.  
  1288.             _menuPool.ProcessMenus();
  1289.             if (Info.IsPlayerOnDuty() && Game.IsKeyPressed(MainMenuKey) && !_menuPool.IsAnyMenuOpen())
  1290.             {
  1291.  
  1292.                 if (CriminalsFleeing.Count > 0)
  1293.                 {
  1294.  
  1295.                     mainMenu.Visible = !mainMenu.Visible;
  1296.                 }
  1297.                 else
  1298.                 {
  1299.                     SettingsMenu.Visible = !SettingsMenu.Visible;
  1300.                 }
  1301.                 //mainMenu.RefreshIndex();
  1302.  
  1303.             }
  1304.  
  1305.             if (SplitCriminals.Count > 0)
  1306.             {
  1307.                 if (Util.CanWeUse(SplitCriminals[0]))
  1308.                 {
  1309.                     if (SplitCriminals[0].IsAlive)
  1310.                     {
  1311.                         CriminalsFleeing.Add(new SuspectHandler(SplitCriminalKind, Vector3.Zero, SplitCriminals[0]));
  1312.                         SplitCriminals.RemoveAt(0);
  1313.                     }
  1314.                     else
  1315.                     {
  1316.                         SplitCriminals[0].MarkAsNoLongerNeeded();
  1317.                     }
  1318.                 }
  1319.  
  1320.             }
  1321.  
  1322.             //if (Game.Player.Character.Weapons.Current.Hash == WeaponHash.StunGun) Function.Call(Hash.SET_PLAYER_WEAPON_DAMAGE_MODIFIER, Game.Player, -900f);        else Function.Call(Hash.SET_PLAYER_WEAPON_DAMAGE_MODIFIER, Game.Player, 0f);
  1323.             //Function.Call(Hash.SET_PLAYER_WEAPON_DAMAGE_MODIFIER, Game.Player, -900f);
  1324.  
  1325.             Util.HandleMessages();
  1326.             Util.HandleNotifications();
  1327.  
  1328.  
  1329.  
  1330.  
  1331.             string states = "";
  1332.  
  1333.             // for (int i = 0; i <= CopsChasing.Count-1; i++)
  1334.             //{
  1335.             //CopUnitHandler unit = CopsChasing[i];
  1336.  
  1337.             foreach (CopUnitHandler unit in CopsChasing)
  1338.             {
  1339.                 if (DebugNotifications.Checked)
  1340.                 {
  1341.                     Vector2 screeninfo = World3DToScreen2d(unit.Leader.Position + new Vector3(0, 0, 1.5f));
  1342.                     Function.Call(Hash._SET_TEXT_ENTRY, "STRING");
  1343.                     Function.Call(Hash.SET_TEXT_CENTRE, true);
  1344.                     Function.Call(Hash.SET_TEXT_COLOUR, 0, 100, 0, 255);
  1345.                     Function.Call(Hash.SET_TEXT_SCALE, 1f, 0.2f);
  1346.                     Function.Call(Hash._ADD_TEXT_COMPONENT_STRING, unit.State.ToString());
  1347.                     Function.Call(Hash._DRAW_TEXT, screeninfo.X, screeninfo.Y);
  1348.                 }
  1349.                 states += unit.State.ToString() + ",";
  1350.                 if (unit.ShouldRemoveCopUnit)
  1351.                 {
  1352.                     unit.Clear();
  1353.                     CopsToRemove.Add(unit);
  1354.                 }
  1355.                 else
  1356.                 {
  1357.                     unit.UpdateOnTick();
  1358.                     if (Game.GameTime > unit.RefTime + 500)
  1359.                     {
  1360.                         unit.RefTime = Game.GameTime;
  1361.                         unit.Update();
  1362.                     }
  1363.                 }
  1364.             }
  1365.             foreach (CopUnitHandler toremove in CopsToRemove) CopsChasing.Remove(toremove);
  1366.  
  1367.             states += "~n~";
  1368.             foreach (SuspectHandler Suspect in CriminalsFleeing)
  1369.             {
  1370.                 if (DebugNotifications.Checked)
  1371.                 {
  1372.                     string BeingArrested = "";
  1373.                     if (Suspect.CopArrestingMe != null) BeingArrested = "Being Arrested";
  1374.                     Vector2 screeninfo = World3DToScreen2d(Suspect.Criminal.Position + new Vector3(0, 0, 1.5f));
  1375.                     Function.Call(Hash._SET_TEXT_ENTRY, "STRING");
  1376.                     Function.Call(Hash.SET_TEXT_CENTRE, true);
  1377.                     Function.Call(Hash.SET_TEXT_COLOUR, 100, 100, 0, 255);
  1378.                     Function.Call(Hash.SET_TEXT_SCALE, 1f, 0.2f);
  1379.                     Function.Call(Hash._ADD_TEXT_COMPONENT_STRING, Suspect.State.ToString() + "~n~" + BeingArrested);
  1380.                     Function.Call(Hash._DRAW_TEXT, screeninfo.X, screeninfo.Y);
  1381.                 }
  1382.                 states += Suspect.State.ToString() + "-";
  1383.  
  1384.                 Suspect.UpdateFast();
  1385.                 if (Game.GameTime > Suspect.RefTime + 500)
  1386.                 {
  1387.                     if (Suspect.LOSTreshold == LostLOSThreshold)
  1388.                     {
  1389.                         if (AllowChaseNotifications.Checked)
  1390.                         {
  1391.                             if (Suspect.CopsChasingMe.Count > 0)
  1392.                             {
  1393.                                 CopUnitHandler Unit = GetClosestCop(Suspect, true, true);//Suspect.CopsChasingMe[Util.RandomInt(0, Suspect.CopsChasingMe.Count - 1)];
  1394.                                 if (Unit != null)
  1395.                                 {
  1396.                                     Util.AddNotification("web_lossantospolicedept", "~b~" + Unit.CopVehicle.FriendlyName, "SUSPECT SIGHT LOST", "We have lost sight of the suspect!");
  1397.                                 }
  1398.                             }
  1399.                         }
  1400.                     }
  1401.                     if(Suspect.LOSTreshold == LostLOSThreshold + 20)
  1402.                     {
  1403.                         if (AllowChaseNotifications.Checked)
  1404.                         {
  1405.                             if (Suspect.CopsChasingMe.Count > 0)
  1406.                             {
  1407.                                 CopUnitHandler Unit = GetClosestCop(Suspect, true, true);//Suspect.CopsChasingMe[Util.RandomInt(0, Suspect.CopsChasingMe.Count - 1)];
  1408.                                 if (Unit != null)
  1409.                                 {
  1410.                                     Util.AddNotification("web_lossantospolicedept", "~b~" + Unit.CopVehicle.FriendlyName, "SUSPECT LAST SEEN", "Last Seen: ~y~"+World.GetStreetName(Suspect.LostLOSBlip.Position)+"~w~~n~Headed: ~b~"+Util.GetWhereIsHeaded(Suspect.Criminal,false));
  1411.                                 }
  1412.                             }
  1413.                         }
  1414.                     }
  1415.  
  1416.                     if (Suspect.LOSTreshold > 100)
  1417.                     {
  1418.                         Suspect.Clear();
  1419.                         CriminalsToRemove.Add(Suspect);
  1420.                         if (CriminalsFleeing.Count > 1)
  1421.                         {
  1422.                             Util.AddNotification("web_lossantospolicedept", "~b~DISPATCH", "SUSPECT LOST", "A suspect has evaded all pursuing units. There are " + (CriminalsFleeing.Count - 1).ToString() + " more suspects on the loose.");
  1423.                         }
  1424.                         else
  1425.                         {
  1426.                             Util.AddNotification("web_lossantospolicedept", "~b~DISPATCH", "SUSPECT LOST", "Suspect has evaded all pursuing units.~n~All units, cease pursuit and return to patrol.");
  1427.                         }
  1428.                         //Function.Call(Hash.SET_MAX_WANTED_LEVEL, 5);
  1429.                     }
  1430.                     else
  1431.                     if (Suspect.ShouldRemoveCriminal)
  1432.                     {
  1433.                         if (Suspect.Criminal.IsAlive)
  1434.                         {
  1435.                             Game.Player.Money += 500;
  1436.                             if ((CriminalsFleeing.Count + Suspect.Partners.Count) < 3)
  1437.                             {
  1438.                                 if ((CriminalsFleeing.Count > 1 || Suspect.Partners.Count > 0)) Util.AddNotification("web_lossantospolicedept", "~b~DISPATCH", "SUSPECT APREHENDED", "One of the suspects has been ~g~arrested. ~w~ ~n~There are " + (CriminalsFleeing.Count - 1 + Suspect.Partners.Count).ToString() + " suspects still on the loose.");
  1439.                                 else Util.AddNotification("web_lossantospolicedept", "~b~DISPATCH", "SUSPECT APREHENDED", "~g~All suspect have been arrested~w~~n~Good job, everyone.");
  1440.                             }
  1441.                             Suspect.Clear();
  1442.                             CriminalsToRemove.Add(Suspect);
  1443.  
  1444.                             //Function.Call(Hash.SET_MAX_WANTED_LEVEL, 5);
  1445.                         }
  1446.                         if (Suspect.Criminal.IsDead)
  1447.                         {
  1448.                             Suspect.Clear();
  1449.                             CriminalsToRemove.Add(Suspect);
  1450.                             if ((CriminalsFleeing.Count + Suspect.Partners.Count) < 4)
  1451.                             {
  1452.                                 if ((CriminalsFleeing.Count > 1 || Suspect.Partners.Count > 0)) Util.AddNotification("web_lossantospolicedept", "~b~DISPATCH", "SUSPECT DEAD", "One of the suspects ~r~is down. ~w~ ~n~There are " + (CriminalsFleeing.Count - 1 + Suspect.Partners.Count).ToString() + " suspects still on the loose.");
  1453.                                 else Util.AddNotification("web_lossantospolicedept", "~b~DISPATCH", "LAST SUSPECT DEAD", "~g~All suspect have been taken care of.~w~~n~All units, return to patrol."); Function.Call(Hash.SET_MAX_WANTED_LEVEL, 5);
  1454.                             }
  1455.                         }
  1456.                     }
  1457.                     else
  1458.                     {
  1459.                         Suspect.Update();
  1460.                         Suspect.RefTime = Game.GameTime;
  1461.                     }
  1462.                 }
  1463.             }
  1464.             foreach (SuspectHandler toremove in CriminalsToRemove) CriminalsFleeing.Remove(toremove);
  1465.  
  1466.             //if (CriminalsToRemove[0] == null) CriminalsToRemove.RemoveAt(0);
  1467.  
  1468.             if (AutoChase)
  1469.             {
  1470.                 if (Game.IsControlJustPressed(2, GTA.Control.CursorScrollUp))
  1471.                 {
  1472.                     Height += 10;
  1473.                     Function.Call(Hash.TASK_HELI_MISSION, Game.Player.Character, Game.Player.Character.CurrentVehicle, 0, CriminalsFleeing[UISelectCriminal.Index].Criminal.Handle, 0, 0, 0, 6, 60f, 40f, 270f, 0f, Height, 50f, 0);
  1474.                     if (DebugNotifications.Checked) UI.Notify("Height:" + Height.ToString());
  1475.  
  1476.                 }
  1477.                 if (Game.IsControlJustPressed(2, GTA.Control.CursorScrollDown))
  1478.                 {
  1479.                     Height -= 10;
  1480.                     Function.Call(Hash.TASK_HELI_MISSION, Game.Player.Character, Game.Player.Character.CurrentVehicle, 0, CriminalsFleeing[UISelectCriminal.Index].Criminal.Handle, 0, 0, 0, 6, 60f, 40f, 270f, 0f, Height, 50f, 0);
  1481.                     if (DebugNotifications.Checked) UI.Notify("Height:" + Height.ToString());
  1482.  
  1483.                 }
  1484.             }
  1485.             if (DebugNotifications.Checked) Util.DisplayHelpTextThisFrame(states);
  1486.  
  1487.             if (Game.GameTime > CalloutNotificationTimeout && CalloutNotificationActive()) CleanCalloutNotification();
  1488.         }
  1489.         void OnKeyDown(object sender, KeyEventArgs e)
  1490.         {
  1491.  
  1492.         }
  1493.  
  1494.  
  1495.         bool AutoChase = false;
  1496.         int Height = 30;
  1497.         void OnKeyUp(object sender, KeyEventArgs e)
  1498.         {
  1499.  
  1500.             if (_menuPool.IsAnyMenuOpen())  SaveSettings(ConfigFilename);
  1501.  
  1502.             if (e.KeyCode == Keys.Delete)
  1503.             {
  1504.                 foreach (CopUnitHandler unit in CopsChasing) unit.ShouldRemoveCopUnit = true;
  1505.                 foreach (SuspectHandler unit in CriminalsFleeing) unit.ShouldRemoveCriminal = true;
  1506.             }
  1507.             if (e.KeyCode == Keys.OemMinus && DebugNotifications.Checked)
  1508.             {
  1509.                 CriminalsFleeing.Add(new SuspectHandler(CriminalType.Test, Game.Player.Character.Position.Around(10), null));
  1510.             }
  1511.  
  1512.             if (e.KeyCode == Keys.Space)
  1513.             {
  1514.                 if (AutoChase)
  1515.                 {
  1516.                     if (DebugNotifications.Checked) UI.Notify("Autochase deactivated");
  1517.                     Game.Player.Character.Task.ClearAll();
  1518.                     AutoChase = false;
  1519.                 }
  1520.                 else
  1521.                 {
  1522.                     Vehicle veh = Game.Player.Character.CurrentVehicle;
  1523.                     if (CriminalsFleeing.Count > 0)
  1524.                     {
  1525.                         if (Util.CanWeUse(veh) && veh.Model.IsHelicopter)
  1526.                         {
  1527.                             AutoChase = true;
  1528.                             if (DebugNotifications.Checked) UI.Notify("Autochase activated");
  1529.                             Game.Player.Character.ShootRate = 0;
  1530.                             Function.Call(Hash.TASK_HELI_MISSION, Game.Player.Character, veh, 0, CriminalsFleeing[UISelectCriminal.Index].Criminal.Handle, 0, 0, 0, 6, 60f, 40f, 270f, 30f, Height, 50f, 0);
  1531.                         }
  1532.                     }
  1533.                 }
  1534.             }
  1535.  
  1536.             if (CalloutNotificationActive() && e.KeyCode == Keys.Enter)
  1537.             {
  1538.                 CriminalsFleeing.Add(new SuspectHandler(CalloutCriminal, CalloutPlace, null));
  1539.                 CleanCalloutNotification();
  1540.  
  1541.                 if (CalloutCriminal == CriminalType.ViolentGangFamilies)
  1542.                 {
  1543.                     CriminalsFleeing.Add(new SuspectHandler(CriminalType.ViolentGangBallas, CalloutPlace.Around(8f), null));
  1544.                 }
  1545.  
  1546.  
  1547.                 if (CalloutCriminal == CriminalType.AmateurRacers || CalloutCriminal == CriminalType.ProRacers)
  1548.                 {
  1549.                     for (int i = 0; i <= Util.RandomInt(0, 3); i++)
  1550.                     {
  1551.                         CriminalsFleeing.Add(new SuspectHandler(CalloutCriminal, CalloutPlace.Around(8f), null));
  1552.                     }
  1553.                 }
  1554.                 if (PlayerCareMenu.Checked)
  1555.                 {
  1556.                     Vehicle veh = Util.GetLastVehicle(Game.Player.Character);
  1557.                     if (Util.CanWeUse(veh))
  1558.                     {
  1559.                         Function.Call(Hash.SET_VEHICLE_FIXED,veh);
  1560.                         Function.Call(Hash.SET_VEHICLE_DEFORMATION_FIXED, veh);
  1561.  
  1562.                     }
  1563.                 }
  1564.             };
  1565.             if (CriminalsFleeing.Count==0 && Info.IsPlayerOnDuty() && e.KeyCode == ForceCalloutKey) if (CalloutNotificationActive()) { CleanCalloutNotification(); } else GenerateCallout();
  1566.         }
  1567.  
  1568.         bool CalloutNotificationActive()
  1569.         {
  1570.             return CalloutNotification != -1;
  1571.         }
  1572.  
  1573.         CriminalType CalloutCriminal = CriminalType.PacificFleeingFoot;
  1574.         Vector3 CalloutPlace = Vector3.Zero;
  1575.         public void GenerateCallout()
  1576.         {
  1577.             Util.CleanNotifications();
  1578.             ManageCalloutPool();
  1579.             if (CalloutPool.Count > 0)
  1580.             {
  1581.                 if (CalloutNotification == -1)
  1582.                 {
  1583.                     CalloutCriminal = (CriminalType)CalloutPool[Util.RandomInt(0, CalloutPool.Count - 1)]; // (CriminalType)Util.RandomInt(0,Enum.GetValues(typeof(CriminalType)).Length-1);
  1584.                     CalloutPlace = Util.GenerateSpawnPos(World.GetNextPositionOnStreet(Game.Player.Character.Position).Around(Util.RandomInt(300, 500)), Util.Nodetype.AnyRoad, true); //Util.FindSpawnpointInDirection(Game.Player.Character.Position.Around(200f), 300f, 30);
  1585.                     while (CalloutPlace.DistanceTo(Game.Player.Character.Position) < 300 || CalloutPlace == Vector3.Zero)
  1586.                     {
  1587.                         CalloutPlace = Util.GenerateSpawnPos(World.GetNextPositionOnStreet(Game.Player.Character.Position).Around(Util.RandomInt(300, 500)), Util.Nodetype.AnyRoad, true); //Util.FindSpawnpointInDirection(Game.Player.Character.Position.Around(200f), 300f, 30);
  1588.                     }
  1589.  
  1590.                     if (CalloutPlace == Vector3.Zero)
  1591.                     {
  1592.                         if (DebugNotifications.Checked) Util.WarnPlayer(ScriptName, "~R~ERROR", "There was an GenerateSpawnpoint error.");
  1593.                         CalloutPlace = World.GetNextPositionOnStreet(Game.Player.Character.Position).Around(400f);
  1594.                     }
  1595.                     NotifyCallout("web_lossantospolicedept", "~b~DISPATCH", "SUSPECT FLEEING", "Callout: ~b~" + GenerateContextForSuspect(CalloutCriminal) + "~w~~n~Reported in: ~y~" + World.GetZoneName(CalloutPlace) + "~w~.");
  1596.                 }
  1597.                 else
  1598.                 {
  1599.                     CleanCalloutNotification();
  1600.                 }
  1601.             }
  1602.             else
  1603.             {
  1604.                 UI.Notify("There are no callouts to in the Callout pool.");
  1605.             }
  1606.         }
  1607.  
  1608.         void CleanCalloutNotification()
  1609.         {
  1610.             //UI.Notify("Callout removed");
  1611.             Function.Call(Hash._REMOVE_NOTIFICATION, CalloutNotification);
  1612.             CalloutNotification = -1;
  1613.  
  1614.         }
  1615.  
  1616.  
  1617.         public static int CalloutNotificationTimeout;
  1618.         public static int CalloutNotification = -1;
  1619.         public static void NotifyCallout(string avatar, string author, string title, string message)
  1620.         {
  1621.             Function.Call(Hash._SET_NOTIFICATION_TEXT_ENTRY, "STRING");
  1622.             Function.Call(Hash._ADD_TEXT_COMPONENT_STRING, message);
  1623.             //Function.Call(Hash._0x17430B918701C342, 200,200,255,0);
  1624.             CalloutNotification = Function.Call<int>(Hash._SET_NOTIFICATION_MESSAGE, avatar, avatar, true, 0, title, author);
  1625.             CalloutNotificationTimeout = Game.GameTime + 10000;
  1626.         }
  1627.  
  1628.  
  1629.         protected override void Dispose(bool dispose)
  1630.         {
  1631.             foreach (CopUnitHandler unit in CopsChasing)
  1632.             {
  1633.                 unit.Leader.MarkAsNoLongerNeeded();
  1634.                 foreach (Ped ped in unit.Partners) ped.MarkAsNoLongerNeeded();
  1635.  
  1636.             }
  1637.             foreach (SuspectHandler unit in CriminalsFleeing)
  1638.             {
  1639.                 unit.Criminal.MarkAsNoLongerNeeded();
  1640.                 foreach (Ped ped in unit.Partners) ped.MarkAsNoLongerNeeded();
  1641.             }
  1642.         }
  1643.         void SaveCriminalVehicle(string file, string section, Vehicle veh)
  1644.         {
  1645.             if (File.Exists(@"" + file))
  1646.             {
  1647.  
  1648.                 XmlDocument originalXml = new XmlDocument();
  1649.                 originalXml.Load(@"" + file);
  1650.  
  1651.                 XmlNode changes = originalXml.SelectSingleNode("//" + section);
  1652.  
  1653.  
  1654.                 //Prevent duplications;
  1655.                 foreach (XmlElement element in originalXml.SelectNodes("//" + section+"/*"))
  1656.                 {
  1657.                     if (element.InnerText == veh.Model.Hash.ToString())
  1658.                     {
  1659.                         Util.WarnPlayer(ScriptName + " " + ScriptVer, "MODEL ALREADY EXISTED", "This vehicle model already exists in this category.");
  1660.                         return;
  1661.                     }
  1662.                 }
  1663.  
  1664.                 XmlElement Info = originalXml.CreateElement("Model");
  1665.                 Info.InnerText = veh.Model.Hash.ToString();
  1666.                 changes.AppendChild(Info);
  1667.  
  1668.  
  1669.  
  1670.                 XmlAttribute Version = originalXml.CreateAttribute("Name");
  1671.                 if (veh.FriendlyName.Length > 0)
  1672.                 {
  1673.                     Version.Value = veh.FriendlyName;
  1674.                 }
  1675.                 else
  1676.                 {
  1677.                     Version.Value = veh.DisplayName;
  1678.                 }
  1679.                 Info.Attributes.Append(Version);
  1680.                
  1681.                 /*
  1682.                 Vector3 pos = Game.Player.Character.Position + (Game.Player.Character.ForwardVector * 10);
  1683.                 Vehicle test = World.CreateVehicle(int.Parse(Info.InnerText), pos);            
  1684.                 test.IsPersistent = false; */
  1685.  
  1686.  
  1687.                 originalXml.Save(@"" + file);
  1688.                 Util.WarnPlayer(ScriptName + " " + ScriptVer, "MODEL SAVED", "Model saved.");
  1689.  
  1690.             }
  1691.         }
  1692.         void GenerateConfigFile(string file)
  1693.         {
  1694.             File.WriteAllText(@"" + file, "<Data></Data>");
  1695.  
  1696.             XmlDocument originalXml = new XmlDocument();
  1697.             originalXml.Load(@"" + file);
  1698.  
  1699.             XmlNode changes = originalXml.SelectSingleNode("//Data");
  1700.  
  1701.            
  1702.             XmlElement Info = originalXml.CreateElement("AllowAverageCallouts");
  1703.             Info.InnerText = AllowAverageCallouts.Checked.ToString();
  1704.             changes.AppendChild(Info);
  1705.  
  1706.             Info = originalXml.CreateElement("AllowRaceCallouts");
  1707.             Info.InnerText = AllowRaceCallouts.Checked.ToString();
  1708.             changes.AppendChild(Info);
  1709.  
  1710.             Info = originalXml.CreateElement("AllowHeistCallouts");
  1711.             Info.InnerText = AllowHeistCallouts.Checked.ToString();
  1712.             changes.AppendChild(Info);
  1713.  
  1714.             Info = originalXml.CreateElement("AllowGangRiot");
  1715.             Info.InnerText = AllowGangRiot.Checked.ToString();
  1716.             changes.AppendChild(Info);
  1717.  
  1718.             Info = originalXml.CreateElement("AllowMilitary");
  1719.             Info.InnerText = AllowMilitary.Checked.ToString();
  1720.             changes.AppendChild(Info);
  1721.  
  1722.             Info = originalXml.CreateElement("AllowTerrorism");
  1723.             Info.InnerText = AllowTerrorism.Checked.ToString();
  1724.             changes.AppendChild(Info);
  1725.  
  1726.             Info = originalXml.CreateElement("AllowCargoStealers");
  1727.             Info.InnerText = AllowCargoStealers.Checked.ToString();
  1728.             changes.AppendChild(Info);
  1729.  
  1730.             Info = originalXml.CreateElement("AllowEscapedPrisoner");
  1731.             Info.InnerText = AllowEscapedPrisoner.Checked.ToString();
  1732.             changes.AppendChild(Info);
  1733.  
  1734.  
  1735.             Info = originalXml.CreateElement("AllowMainCharacters");
  1736.             Info.InnerText = AllowMainCharacters.Checked.ToString();
  1737.             changes.AppendChild(Info);
  1738.  
  1739.  
  1740.             Info = originalXml.CreateElement("DebugNotifications");
  1741.             Info.InnerText = DebugNotifications.Checked.ToString();
  1742.             changes.AppendChild(Info);
  1743.  
  1744.             Info = originalXml.CreateElement("AllowAutomaticDispatch");
  1745.             Info.InnerText = AllowAutomaticDispatch.Checked.ToString();
  1746.             changes.AppendChild(Info);
  1747.  
  1748.  
  1749.             Info = originalXml.CreateElement("AllowOngoingChase");
  1750.             Info.InnerText = AllowOngoingChase.Checked.ToString();
  1751.             changes.AppendChild(Info);
  1752.  
  1753.  
  1754.             Info = originalXml.CreateElement("AllowRDEVehicles");
  1755.             Info.InnerText = AllowRDEVehicles.Checked.ToString();
  1756.             changes.AppendChild(Info);
  1757.  
  1758.             Info = originalXml.CreateElement("AllowMadMaxVehicles");
  1759.             Info.InnerText = AllowMadMaxVehicles.Checked.ToString();
  1760.             changes.AppendChild(Info);
  1761.  
  1762.             Info = originalXml.CreateElement("AllowIVPack");
  1763.             Info.InnerText = AllowIVPack.Checked.ToString();
  1764.             changes.AppendChild(Info);
  1765.  
  1766.             Info = originalXml.CreateElement("ForceUse");
  1767.             Info.InnerText = ForceUse.Checked.ToString();
  1768.             changes.AppendChild(Info);
  1769.  
  1770.             Info = originalXml.CreateElement("MainMenuKey");
  1771.             Info.InnerText = MainMenuKey.ToString();
  1772.             changes.AppendChild(Info);
  1773.  
  1774.             Info = originalXml.CreateElement("ForceCalloutKey");
  1775.             Info.InnerText = ForceCalloutKey.ToString();
  1776.             changes.AppendChild(Info);
  1777.  
  1778.             Info = originalXml.CreateElement("PlayerCareMenu");
  1779.             Info.InnerText = PlayerCareMenu.Checked.ToString();
  1780.             changes.AppendChild(Info);
  1781.  
  1782.             Info = originalXml.CreateElement("HelpNotifications");
  1783.             Info.InnerText = HelpNotifications.Checked.ToString();
  1784.             changes.AppendChild(Info);
  1785.            
  1786.             //Version saving
  1787.             XmlAttribute Version = originalXml.CreateAttribute("version");
  1788.             Version.Value = ScriptVer;
  1789.             changes.Attributes.Append(Version);
  1790.                        
  1791.             originalXml.Save(@"" + file);
  1792.         }
  1793.         void SaveSettings(string file)
  1794.         {
  1795.             if (!File.Exists(@"" + file))
  1796.             {
  1797.                 GenerateConfigFile(ConfigFilename);
  1798.             }
  1799.  
  1800.             if (File.Exists(@"" + file))
  1801.             {
  1802.                 XmlDocument ScriptInfo = new XmlDocument();
  1803.                 ScriptInfo.Load(@"" + file);
  1804.                 XmlElement root = ScriptInfo.DocumentElement;
  1805.  
  1806.  
  1807.                 //Callout filters
  1808.                 root.SelectSingleNode("//AllowAverageCallouts").InnerText = AllowAverageCallouts.Checked.ToString();
  1809.                 root.SelectSingleNode("//AllowRaceCallouts").InnerText = AllowRaceCallouts.Checked.ToString();
  1810.  
  1811.                 root.SelectSingleNode("//AllowHeistCallouts").InnerText = AllowHeistCallouts.Checked.ToString();
  1812.                 root.SelectSingleNode("//AllowGangRiot").InnerText = AllowGangRiot.Checked.ToString();
  1813.                 root.SelectSingleNode("//AllowMilitary").InnerText = AllowMilitary.Checked.ToString();
  1814.                 root.SelectSingleNode("//AllowTerrorism").InnerText = AllowTerrorism.Checked.ToString();
  1815.                 root.SelectSingleNode("//AllowCargoStealers").InnerText = AllowCargoStealers.Checked.ToString();
  1816.                 root.SelectSingleNode("//AllowEscapedPrisoner").InnerText = AllowEscapedPrisoner.Checked.ToString();
  1817.                 root.SelectSingleNode("//AllowMainCharacters").InnerText = AllowMainCharacters.Checked.ToString();
  1818.  
  1819.  
  1820.                 //Config
  1821.                 root.SelectSingleNode("//AllowRDEVehicles").InnerText = AllowRDEVehicles.Checked.ToString();
  1822.                 root.SelectSingleNode("//AllowMadMaxVehicles").InnerText = AllowMadMaxVehicles.Checked.ToString();
  1823.                 root.SelectSingleNode("//AllowIVPack").InnerText = AllowIVPack.Checked.ToString();
  1824.  
  1825.                 root.SelectSingleNode("//DebugNotifications").InnerText = DebugNotifications.Checked.ToString();
  1826.                 root.SelectSingleNode("//AllowAutomaticDispatch").InnerText = AllowAutomaticDispatch.Checked.ToString();
  1827.                 root.SelectSingleNode("//AllowOngoingChase").InnerText = AllowOngoingChase.Checked.ToString();
  1828.                 root.SelectSingleNode("//ForceUse").InnerText = ForceUse.Checked.ToString();
  1829.                 root.SelectSingleNode("//PlayerCareMenu").InnerText = PlayerCareMenu.Checked.ToString();
  1830.                 root.SelectSingleNode("//HelpNotifications").InnerText = HelpNotifications.Checked.ToString();
  1831.  
  1832.  
  1833.                 root.SelectSingleNode("//MainMenuKey").InnerText = MainMenuKey.ToString();
  1834.                 root.SelectSingleNode("//ForceCalloutKey").InnerText = ForceCalloutKey.ToString();
  1835.  
  1836.                 ScriptInfo.Save(@"" + file);
  1837.             }
  1838.             else
  1839.             {
  1840.                 Util.WarnPlayer(ScriptName + " " + ScriptVer, "CONFIG NOT FOUND", "Config file for " + ScriptName + " not found. Cannot save config.");
  1841.             }
  1842.         }
  1843.         void LoadSettings(string file)
  1844.         {
  1845.             if (!File.Exists(@"" + file))
  1846.             {
  1847.                 GenerateConfigFile(ConfigFilename);
  1848.             }
  1849.  
  1850.             if (File.Exists(@"" + file))
  1851.             {
  1852.                 XmlDocument ScriptInfo = new XmlDocument();
  1853.                 ScriptInfo.Load(@"" + file);
  1854.                 XmlElement root = ScriptInfo.DocumentElement;
  1855.  
  1856.                 if (!root.HasAttribute("version") || root.GetAttribute("version") != ScriptVer)
  1857.                 {
  1858.                     Util.WarnPlayer(ScriptName + " " + ScriptVer, "OUTDATED CONFIG", "The configuration file is outdated and has been re-generated to avoid crashes.");
  1859.                     Util.WarnPlayer(ScriptName + " " + ScriptVer, "OUTDATED CONFIG", "You have lost your current configuration in the process.");
  1860.  
  1861.                     File.Delete(@"" + file);
  1862.                     GenerateConfigFile(ConfigFilename);
  1863.                     ScriptInfo = new XmlDocument();
  1864.  
  1865.                     ScriptInfo.Load(@"" + file);
  1866.                     root = ScriptInfo.DocumentElement;
  1867.                 }
  1868.  
  1869.                 //Callout filters
  1870.                 AllowAverageCallouts.Checked = bool.Parse(root.SelectSingleNode("//AllowAverageCallouts").InnerText);
  1871.                 AllowRaceCallouts.Checked = bool.Parse(root.SelectSingleNode("//AllowRaceCallouts").InnerText);
  1872.                 AllowHeistCallouts.Checked = bool.Parse(root.SelectSingleNode("//AllowHeistCallouts").InnerText);
  1873.                 AllowGangRiot.Checked = bool.Parse(root.SelectSingleNode("//AllowGangRiot").InnerText);
  1874.                 AllowMilitary.Checked = bool.Parse(root.SelectSingleNode("//AllowMilitary").InnerText);
  1875.                 AllowTerrorism.Checked = bool.Parse(root.SelectSingleNode("//AllowTerrorism").InnerText);
  1876.                 AllowCargoStealers.Checked = bool.Parse(root.SelectSingleNode("//AllowCargoStealers").InnerText);
  1877.                 AllowEscapedPrisoner.Checked = bool.Parse(root.SelectSingleNode("//AllowEscapedPrisoner").InnerText);
  1878.                 AllowMainCharacters.Checked = bool.Parse(root.SelectSingleNode("//AllowMainCharacters").InnerText);
  1879.                 ForceUse.Checked = bool.Parse(root.SelectSingleNode("//ForceUse").InnerText);
  1880.  
  1881.                 AllowRDEVehicles.Checked = bool.Parse(root.SelectSingleNode("//AllowRDEVehicles").InnerText);
  1882.                 AllowIVPack.Checked = bool.Parse(root.SelectSingleNode("//AllowIVPack").InnerText);
  1883.                 AllowMadMaxVehicles.Checked = bool.Parse(root.SelectSingleNode("//AllowMadMaxVehicles").InnerText);
  1884.  
  1885.  
  1886.                 //Config
  1887.                 DebugNotifications.Checked = bool.Parse(root.SelectSingleNode("//DebugNotifications").InnerText);
  1888.                 AllowAutomaticDispatch.Checked = bool.Parse(root.SelectSingleNode("//AllowAutomaticDispatch").InnerText);
  1889.                 AllowOngoingChase.Checked = bool.Parse(root.SelectSingleNode("//AllowOngoingChase").InnerText);
  1890.                 MainMenuKey = (Keys)Enum.Parse(typeof(Keys), root.SelectSingleNode("//MainMenuKey").InnerText, true);
  1891.                 ForceCalloutKey = (Keys)Enum.Parse(typeof(Keys), root.SelectSingleNode("//ForceCalloutKey").InnerText, true);
  1892.  
  1893.                 PlayerCareMenu.Checked = bool.Parse(root.SelectSingleNode("//PlayerCareMenu").InnerText);
  1894.                 HelpNotifications.Checked = bool.Parse(root.SelectSingleNode("//HelpNotifications").InnerText);
  1895.             }
  1896.             else
  1897.             {
  1898.                 Util.WarnPlayer(ScriptName + " " + ScriptVer, "CONFIG NOT FOUND", "Config file for " + ScriptName + " not found. All features enabled by default.");
  1899.             }
  1900.         }
  1901.     }
  1902. }
RAW Paste Data
We use cookies for various purposes including analytics. By continuing to use Pastebin, you agree to our use of cookies as described in the Cookies Policy. OK, I Understand
 
Top