Advertisement
Koenrad

PatrolHelicopterAI

Sep 22nd, 2015
363
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C# 33.03 KB | None | 0 0
  1. // Decompiled with JetBrains decompiler
  2. // Type: PatrolHelicopterAI
  3. // Assembly: Assembly-CSharp, Version=0.0.0.0, Culture=neutral, PublicKeyToken=null
  4. // MVID: BE7294DA-F897-4599-AE8B-7F016E2E3E06
  5. // Assembly location: C:\Users\rust\Desktop\SteamCMD\steamapps\common\rust_dedicated\RustDedicated_Data\Managed\Assembly-CSharp.dll
  6.  
  7. using Rust;
  8. using System.Collections.Generic;
  9. using UnityEngine;
  10.  
  11. public class PatrolHelicopterAI : MonoBehaviour
  12. {
  13.   private float destination_min_dist = 2f;
  14.   public Vector3 currentOrbitTarget = Vector3.zero;
  15.   private float maxOrbitDuration = 30f;
  16.   private float timeBetweenRockets = 0.2f;
  17.   private int numRocketsLeft = 12;
  18.   private int maxRockets = 12;
  19.   private float strafe_approach_range = 175f;
  20.   private float strafe_firing_range = 150f;
  21.   public float waitAtPoint = 10f;
  22.   public float maxSpeed = 25f;
  23.   public float windForce = 5f;
  24.   public float windFrequency = 1f;
  25.   public float maxRotationSpeed = 90f;
  26.   public float terrainPushForce = 100f;
  27.   public float obstaclePushForce = 100f;
  28.   public float courseAdjustLerpTime = 2f;
  29.   private Vector3 pushVec = Vector3.zero;
  30.   public List<PatrolHelicopterAI.targetinfo> _targetList = new List<PatrolHelicopterAI.targetinfo>();
  31.   public static PatrolHelicopterAI heliInstance;
  32.   public BaseHelicopter helicopterBase;
  33.   public Vector3 interestZoneOrigin;
  34.   public bool hasInterestZone;
  35.   public Vector3 destination;
  36.   public Quaternion targetRotation;
  37.   public int waypointIndex;
  38.   public Transform[] waypoints;
  39.   public float moveSpeed;
  40.   public Vector3 windVec;
  41.   public Vector3 targetWindVec;
  42.   public float targetThrottleSpeed;
  43.   public float throttleSpeed;
  44.   public float rotationSpeed;
  45.   private Vector3 _lastPos;
  46.   private Vector3 _lastMoveDir;
  47.   private bool movementLockingAiming;
  48.   private bool hasAimTarget;
  49.   private Vector3 _aimTarget;
  50.   private bool aimDoorSide;
  51.   public PatrolHelicopterAI.aiState _currentState;
  52.   public HelicopterTurret leftGun;
  53.   public HelicopterTurret rightGun;
  54.   private bool isDead;
  55.   private float spawnTime;
  56.   private float lastDamageTime;
  57.   private bool isRetiring;
  58.   private float deathTimeout;
  59.   private float currentOrbitDistance;
  60.   private float currentOrbitTime;
  61.   private bool hasEnteredOrbit;
  62.   private float orbitStartTime;
  63.   private bool breakingOrbit;
  64.   public List<MonumentInfo> _visitedMonuments;
  65.   public float arrivalTime;
  66.   private bool leftTubeFiredLast;
  67.   private float lastRocketTime;
  68.   private Vector3 strafe_target_position;
  69.   private bool puttingDistance;
  70.   public GameObjectRef rocketProjectile;
  71.   private float _lastThinkTime;
  72.  
  73.   public bool IsAlive()
  74.   {
  75.     return !this.isDead;
  76.   }
  77.  
  78.   public void SetAimTarget(Vector3 aimTarg, bool isDoorSide)
  79.   {
  80.     if (this.movementLockingAiming)
  81.       return;
  82.     this.hasAimTarget = true;
  83.     this._aimTarget = aimTarg;
  84.     this.aimDoorSide = isDoorSide;
  85.   }
  86.  
  87.   public void ClearAimTarget()
  88.   {
  89.     this.hasAimTarget = false;
  90.     this._aimTarget = Vector3.zero;
  91.   }
  92.  
  93.   public void SetInitialDestination(Vector3 dest, float mapScaleDistance = 0.25f)
  94.   {
  95.     this.hasInterestZone = true;
  96.     this.interestZoneOrigin = dest;
  97.     float num1 = TerrainMeta.Size.x;
  98.     float num2 = dest.y + 25f;
  99.     Vector3 vector3_1 = Vector3Ex.Range(-1f, 1f);
  100.     vector3_1.y = 0.0f;
  101.     vector3_1.Normalize();
  102.     Vector3 vector3_2 = vector3_1 * (num1 * mapScaleDistance);
  103.     vector3_2.y = num2;
  104.     if ((double) mapScaleDistance == 0.0)
  105.       vector3_2 = this.interestZoneOrigin + new Vector3(0.0f, 10f, 0.0f);
  106.     this.transform.position = vector3_2;
  107.     this.ExitCurrentState();
  108.     this.State_Move_Enter(dest);
  109.   }
  110.  
  111.   public List<BaseCombatEntity> EntitiesInRadius(Vector3 pos, float radius)
  112.   {
  113.     List<BaseCombatEntity> list = new List<BaseCombatEntity>();
  114.     foreach (Component component in Physics.OverlapSphere(pos, radius))
  115.     {
  116.       BaseCombatEntity baseCombatEntity = UnityEngine.BaseEntityEx.ToBaseEntity(component.gameObject) as BaseCombatEntity;
  117.       if ((Object) baseCombatEntity != (Object) null && !list.Contains(baseCombatEntity))
  118.         list.Add(baseCombatEntity);
  119.     }
  120.     return list;
  121.   }
  122.  
  123.   public List<BasePlayer> PlayersInRadius(Vector3 pos, float radius)
  124.   {
  125.     List<BasePlayer> list = new List<BasePlayer>();
  126.     using (List<BasePlayer>.Enumerator enumerator = BasePlayer.activePlayerList.GetEnumerator())
  127.     {
  128.       while (enumerator.MoveNext())
  129.       {
  130.         BasePlayer current = enumerator.Current;
  131.         if ((double) Vector3Ex.Distance2D(pos, current.transform.position) <= (double) radius)
  132.           list.Add(current);
  133.       }
  134.     }
  135.     return list;
  136.   }
  137.  
  138.   public void Awake()
  139.   {
  140.     this.InvokeRepeating("UpdateWind", 0.0f, 1f / this.windFrequency);
  141.     this._lastPos = this.transform.position;
  142.     this.InitializeAI();
  143.     this.spawnTime = Time.realtimeSinceStartup;
  144.     if ((double) heli.lifetimeMinutes != 0.0)
  145.       return;
  146.     this.Invoke("DestroyMe", 1f);
  147.   }
  148.  
  149.   public void Retire()
  150.   {
  151.     if (this.isRetiring)
  152.       return;
  153.     this.isRetiring = true;
  154.     this.Invoke("DestroyMe", 240f);
  155.     float num1 = TerrainMeta.Size.x;
  156.     float num2 = 200f;
  157.     Vector3 newPos = Vector3Ex.Range(-1f, 1f);
  158.     newPos.y = 0.0f;
  159.     newPos.Normalize();
  160.     newPos *= num1 * 20f;
  161.     newPos.y = num2;
  162.     this.ExitCurrentState();
  163.     this.State_Move_Enter(newPos);
  164.   }
  165.  
  166.   public void DestroyMe()
  167.   {
  168.     this.helicopterBase.Kill(BaseNetworkable.DestroyMode.None);
  169.   }
  170.  
  171.   public Vector3 GetLastMoveDir()
  172.   {
  173.     return this._lastMoveDir;
  174.   }
  175.  
  176.   public Vector3 GetMoveDirection()
  177.   {
  178.     return (this.destination - this.transform.position).normalized;
  179.   }
  180.  
  181.   public float GetMoveSpeed()
  182.   {
  183.     return this.moveSpeed;
  184.   }
  185.  
  186.   public void UpdateWind()
  187.   {
  188.     this.targetWindVec = Random.onUnitSphere;
  189.   }
  190.  
  191.   public void MoveToDestination()
  192.   {
  193.     Vector3 vector3 = Vector3.Lerp(this._lastMoveDir, (this.destination - this.transform.position).normalized, Time.deltaTime / this.courseAdjustLerpTime);
  194.     this._lastMoveDir = vector3;
  195.     this.throttleSpeed = Mathf.Lerp(this.throttleSpeed, this.targetThrottleSpeed, Time.deltaTime / 3f);
  196.     float num = this.throttleSpeed * this.maxSpeed;
  197.     this.TerrainPushback();
  198.     this.transform.position += vector3 * num * Time.deltaTime;
  199.     this.windVec = Vector3.Lerp(this.windVec, this.targetWindVec, Time.deltaTime);
  200.     this.transform.position += this.windVec * this.windForce * Time.deltaTime;
  201.     this.moveSpeed = Mathf.Lerp(this.moveSpeed, Vector3.Distance(this._lastPos, this.transform.position) / Time.deltaTime, Time.deltaTime * 2f);
  202.     this._lastPos = this.transform.position;
  203.   }
  204.  
  205.   public void DoPushback()
  206.   {
  207.     if (this._currentState == PatrolHelicopterAI.aiState.DEATH)
  208.       return;
  209.     Vector3 zero = Vector3.zero;
  210.     Vector3 rayOrigin = this.transform.position + new Vector3(0.0f, 2f, 0.0f);
  211.     int mask = LayerMask.GetMask("Terrain", "World", "Construction");
  212.     Vector3 normalized = (this.destination - rayOrigin).normalized;
  213.     float b = Vector3.Distance(this.destination, this.transform.position);
  214.     this.pushVec = Vector3.Lerp(this.pushVec, zero + this.DoPushBackDirection(rayOrigin, normalized, Mathf.Min(30f, b), 5f, mask, 1f, 0.0f), Time.deltaTime);
  215.     this.transform.position += this.pushVec * Time.deltaTime;
  216.   }
  217.  
  218.   public Vector3 DoPushBackDirection(Vector3 rayOrigin, Vector3 dir, float dist, float radius, int mask, float upScale = 1f, float reverseScale = 0.0f)
  219.   {
  220.     Ray ray = new Ray(rayOrigin, dir);
  221.     float radius1 = 5f;
  222.     Vector3 vector3 = Vector3.zero;
  223.     RaycastHit hitInfo;
  224.     if (Physics.SphereCast(ray, radius1, out hitInfo, dist - radius1 * 0.5f, mask))
  225.     {
  226.       float num = this.terrainPushForce * (float) (1.0 - (double) hitInfo.distance / (double) dist);
  227.       vector3 = vector3 + this._lastMoveDir * num * -1f * reverseScale + Vector3.up * num * upScale;
  228.     }
  229.     return vector3;
  230.   }
  231.  
  232.   public void TerrainPushback()
  233.   {
  234.     if (this._currentState == PatrolHelicopterAI.aiState.DEATH)
  235.       return;
  236.     Vector3 origin = this.transform.position + new Vector3(0.0f, 2f, 0.0f);
  237.     Vector3 normalized = (this.destination - origin).normalized;
  238.     float b1 = Vector3.Distance(this.destination, this.transform.position);
  239.     Ray ray1 = new Ray(origin, normalized);
  240.     float radius = 5f;
  241.     float num1 = Mathf.Min(100f, b1);
  242.     int mask = LayerMask.GetMask("Terrain", "World", "Construction");
  243.     Vector3 b2 = Vector3.zero;
  244.     RaycastHit hitInfo1;
  245.     if (Physics.SphereCast(ray1, radius, out hitInfo1, num1 - radius * 0.5f, mask))
  246.       b2 = Vector3.up * (this.terrainPushForce * (float) (1.0 - (double) hitInfo1.distance / (double) num1));
  247.     Ray ray2 = new Ray(origin, this._lastMoveDir);
  248.     float num2 = Mathf.Min(10f, b1);
  249.     RaycastHit hitInfo2;
  250.     if (Physics.SphereCast(ray2, radius, out hitInfo2, num2 - radius * 0.5f, mask))
  251.     {
  252.       float num3 = this.obstaclePushForce * (float) (1.0 - (double) hitInfo2.distance / (double) num2);
  253.       b2 = b2 + this._lastMoveDir * num3 * -1f + Vector3.up * num3;
  254.     }
  255.     this.pushVec = Vector3.Lerp(this.pushVec, b2, Time.deltaTime);
  256.     this.transform.position += this.pushVec * Time.deltaTime;
  257.   }
  258.  
  259.   public void ObjectPushback()
  260.   {
  261.     Ray ray = new Ray(this.transform.position, this._lastMoveDir);
  262.     float maxDistance = 5f;
  263.     int layerMask = 1;
  264.     RaycastHit hitInfo;
  265.     if (!Physics.SphereCast(ray, 4f, out hitInfo, maxDistance, layerMask))
  266.       ;
  267.     if (Physics.SphereCast(ray, 4f, out hitInfo, maxDistance, layerMask))
  268.       ;
  269.   }
  270.  
  271.   public void UpdateRotation()
  272.   {
  273.     if (this.hasAimTarget)
  274.     {
  275.       Vector3 position = this.transform.position;
  276.       position.y = 0.0f;
  277.       Vector3 vector3 = this._aimTarget;
  278.       vector3.y = 0.0f;
  279.       Vector3 normalized = (vector3 - position).normalized;
  280.       Vector3 forward = Vector3.Cross(normalized, Vector3.up);
  281.       float num1 = Vector3.Angle(normalized, this.transform.right);
  282.       float num2 = Vector3.Angle(normalized, -this.transform.right);
  283.       this.targetRotation = !this.aimDoorSide ? Quaternion.LookRotation(normalized) : ((double) num1 >= (double) num2 ? Quaternion.LookRotation(-forward) : Quaternion.LookRotation(forward));
  284.     }
  285.     this.rotationSpeed = Mathf.Lerp(this.rotationSpeed, this.maxRotationSpeed, Time.deltaTime / 2f);
  286.     this.transform.rotation = Quaternion.Lerp(this.transform.rotation, this.targetRotation, this.rotationSpeed * Time.deltaTime);
  287.   }
  288.  
  289.   public void Update()
  290.   {
  291.     if (this.helicopterBase.isClient)
  292.       return;
  293.     PatrolHelicopterAI.heliInstance = this;
  294.     this.UpdateTargetList();
  295.     this.MoveToDestination();
  296.     this.UpdateRotation();
  297.     this.UpdateSpotlight();
  298.     this.AIThink();
  299.     this.DoMachineGuns();
  300.     if (this.isRetiring || (double) Time.realtimeSinceStartup <= (double) Mathf.Max(this.spawnTime + heli.lifetimeMinutes * 60f, this.lastDamageTime + 120f))
  301.       return;
  302.     this.Retire();
  303.   }
  304.  
  305.   public void WeakspotDamaged()
  306.   {
  307.     this.lastDamageTime = Time.realtimeSinceStartup;
  308.   }
  309.  
  310.   public void UpdateSpotlight()
  311.   {
  312.     if (this.hasInterestZone)
  313.       this.helicopterBase.spotlightTarget = this.interestZoneOrigin;
  314.     else
  315.       this.helicopterBase.spotlightTarget = Vector3.zero;
  316.   }
  317.  
  318.   public bool PlayerVisible(BasePlayer ply)
  319.   {
  320.     Vector3 a = ply.eyes.position;
  321.     if (TOD_Sky.Instance.IsNight && (double) Vector3.Distance(a, this.interestZoneOrigin) > 50.0)
  322.       return false;
  323.     Vector3 b = this.transform.position - Vector3.up * 6f;
  324.     float num = Vector3.Distance(a, b);
  325.     Vector3 normalized = (a - b).normalized;
  326.     RaycastHit hitInfo;
  327.     return Physics.Raycast(b + normalized * 5f, normalized, out hitInfo, num * 1.1f, -1063040255) && (Object) UnityEngine.BaseEntityEx.ToBaseEntity(hitInfo.collider.gameObject) == (Object) ply;
  328.   }
  329.  
  330.   public void WasAttacked(HitInfo info)
  331.   {
  332.     BasePlayer initPly = info.Initiator as BasePlayer;
  333.     if (!((Object) initPly != (Object) null))
  334.       return;
  335.     this._targetList.Add(new PatrolHelicopterAI.targetinfo((BaseEntity) initPly, initPly));
  336.   }
  337.  
  338.   public void UpdateTargetList()
  339.   {
  340.     Vector3 strafePos = Vector3.zero;
  341.     bool flag1 = false;
  342.     for (int index = this._targetList.Count - 1; index >= 0; --index)
  343.     {
  344.       PatrolHelicopterAI.targetinfo targetinfo = this._targetList[index];
  345.       if (targetinfo == null)
  346.       {
  347.         this._targetList.Remove(targetinfo);
  348.       }
  349.       else
  350.       {
  351.         if ((double) Time.realtimeSinceStartup > (double) targetinfo.nextLOSCheck)
  352.         {
  353.           targetinfo.nextLOSCheck = Time.realtimeSinceStartup + 1f;
  354.           if (this.PlayerVisible(targetinfo.ply))
  355.           {
  356.             targetinfo.lastSeenTime = Time.realtimeSinceStartup;
  357.             ++targetinfo.visibleFor;
  358.           }
  359.           else
  360.             targetinfo.visibleFor = 0.0f;
  361.         }
  362.         bool flag2 = !(bool) ((Object) targetinfo.ply) ? (double) targetinfo.ent.Health() <= 0.0 : targetinfo.ply.IsDead();
  363.         if ((double) targetinfo.TimeSinceSeen() >= 6.0 || flag2)
  364.         {
  365.           bool flag3 = (double) Random.Range(0.0f, 1f) >= 0.5;
  366.           if (this.IsAlive() && !flag1 && !flag2 && (((Object) targetinfo.ply == (Object) this.leftGun._target || (Object) targetinfo.ply == (Object) this.rightGun._target) && (flag3 && targetinfo.ply.CanBuild())))
  367.           {
  368.             flag1 = true;
  369.             strafePos = targetinfo.ply.transform.position;
  370.           }
  371.           this._targetList.Remove(targetinfo);
  372.         }
  373.       }
  374.     }
  375.     using (List<BasePlayer>.Enumerator enumerator1 = this.PlayersInRadius(this.transform.position, 150f).GetEnumerator())
  376.     {
  377.       while (enumerator1.MoveNext())
  378.       {
  379.         BasePlayer current = enumerator1.Current;
  380.         bool flag2 = false;
  381.         using (List<PatrolHelicopterAI.targetinfo>.Enumerator enumerator2 = this._targetList.GetEnumerator())
  382.         {
  383.           while (enumerator2.MoveNext())
  384.           {
  385.             if ((Object) enumerator2.Current.ply == (Object) current)
  386.             {
  387.               flag2 = true;
  388.               break;
  389.             }
  390.           }
  391.         }
  392.         if (!flag2 && (double) current.GetThreatLevel() > 0.5 && this.PlayerVisible(current))
  393.           this._targetList.Add(new PatrolHelicopterAI.targetinfo((BaseEntity) current, current));
  394.       }
  395.     }
  396.     if (!flag1)
  397.       return;
  398.     this.ExitCurrentState();
  399.     this.State_Strafe_Enter(strafePos);
  400.   }
  401.  
  402.   public void UpdateInterestZone()
  403.   {
  404.   }
  405.  
  406.   public void FireGun(Vector3 targetPos, float aimCone, bool left)
  407.   {
  408.     if (heli.guns == 0)
  409.       return;
  410.     Vector3 position = (!left ? this.helicopterBase.right_gun_muzzle.transform : this.helicopterBase.left_gun_muzzle.transform).position;
  411.     Vector3 normalized = (targetPos - position).normalized;
  412.     Vector3 origin = position + normalized * 2f;
  413.     float num = aimCone;
  414.     Vector3 direction = Quaternion.Euler(Random.Range((float) (-(double) num * 0.5), num * 0.5f), Random.Range((float) (-(double) num * 0.5), num * 0.5f), Random.Range((float) (-(double) num * 0.5), num * 0.5f)) * normalized;
  415.     RaycastHit hitInfo;
  416.     if (Physics.Raycast(origin, direction, out hitInfo, 300f, -1063040255))
  417.     {
  418.       targetPos = hitInfo.point;
  419.       if ((bool) ((Object) hitInfo.collider))
  420.       {
  421.         BaseEntity baseEntity = UnityEngine.BaseEntityEx.ToBaseEntity(hitInfo.collider.gameObject);
  422.         if ((bool) ((Object) baseEntity) && (Object) baseEntity != (Object) this.helicopterBase)
  423.         {
  424.           BaseCombatEntity baseCombatEntity = baseEntity as BaseCombatEntity;
  425.           HitInfo info = new HitInfo((BaseEntity) this.helicopterBase, DamageType.Bullet, this.helicopterBase.bulletDamage * heli.bulletDamageScale, hitInfo.point);
  426.           if ((bool) ((Object) baseCombatEntity))
  427.           {
  428.             baseCombatEntity.OnAttacked(info);
  429.             if (baseCombatEntity is BasePlayer)
  430.               Effect.server.ImpactEffect(new HitInfo()
  431.               {
  432.                 HitPositionWorld = hitInfo.point - direction * 0.25f,
  433.                 HitNormalWorld = -direction,
  434.                 HitMaterial = StringPool.Get("Flesh")
  435.               });
  436.           }
  437.           else
  438.             baseEntity.SendMessage("OnAttacked", (object) info, SendMessageOptions.DontRequireReceiver);
  439.         }
  440.       }
  441.     }
  442.     else
  443.       targetPos = origin + direction * 300f;
  444.     this.helicopterBase.ClientRPC((Network.Connection) null, "FireGun", (object) (bool) (left ? 1 : 0), (object) targetPos);
  445.   }
  446.  
  447.   public void DoMachineGuns()
  448.   {
  449.     if (this._targetList.Count > 0)
  450.     {
  451.       if (this.leftGun.NeedsNewTarget())
  452.         this.leftGun.UpdateTargetFromList(this._targetList);
  453.       if (this.rightGun.NeedsNewTarget())
  454.         this.rightGun.UpdateTargetFromList(this._targetList);
  455.     }
  456.     this.leftGun.TurretThink();
  457.     this.rightGun.TurretThink();
  458.   }
  459.  
  460.   public float GetMaxRotationSpeed()
  461.   {
  462.     return this.maxRotationSpeed;
  463.   }
  464.  
  465.   public void SetIdealRotation(Quaternion newTargetRot, float rotationSpeedOverride = -1)
  466.   {
  467.     this.rotationSpeed = ((double) rotationSpeedOverride != -1.0 ? rotationSpeedOverride : Mathf.Clamp01(this.moveSpeed / (this.maxSpeed * 0.5f))) * this.maxRotationSpeed;
  468.     this.targetRotation = newTargetRot;
  469.   }
  470.  
  471.   public void CriticalDamage()
  472.   {
  473.     this.isDead = true;
  474.     this.ExitCurrentState();
  475.     this.State_Death_Enter();
  476.   }
  477.  
  478.   public bool IsTargeting()
  479.   {
  480.     return this.hasAimTarget;
  481.   }
  482.  
  483.   public Quaternion GetYawRotationTo(Vector3 targetDest)
  484.   {
  485.     Vector3 vector3 = targetDest;
  486.     vector3.y = 0.0f;
  487.     Vector3 position = this.transform.position;
  488.     position.y = 0.0f;
  489.     return Quaternion.LookRotation((vector3 - position).normalized);
  490.   }
  491.  
  492.   public void SetTargetDestination(Vector3 targetDest, float minDist = 5f, float minDistForFacingRotation = 30f)
  493.   {
  494.     this.destination = targetDest;
  495.     this.destination_min_dist = minDist;
  496.     float distToTarget = Vector3.Distance(targetDest, this.transform.position);
  497.     if ((double) distToTarget > (double) minDistForFacingRotation && !this.IsTargeting())
  498.       this.SetIdealRotation(this.GetYawRotationTo(this.destination), -1f);
  499.     this.targetThrottleSpeed = this.GetThrottleForDistance(distToTarget);
  500.   }
  501.  
  502.   public bool AtDestination()
  503.   {
  504.     return (double) Vector3.Distance(this.transform.position, this.destination) < (double) this.destination_min_dist;
  505.   }
  506.  
  507.   public void State_Death_Think(float timePassed)
  508.   {
  509.     float num = Time.realtimeSinceStartup * 0.25f;
  510.     this.SetAimTarget(this.transform.position + new Vector3(Mathf.Sin(6.283185f * num) * 10f, 0.0f, Mathf.Cos(6.283185f * num) * 10f), true);
  511.     Ray ray = new Ray(this.transform.position, this.GetLastMoveDir());
  512.     int mask = LayerMask.GetMask("Terrain", "World", "Construction", "Water");
  513.     RaycastHit hitInfo;
  514.     if (!Physics.SphereCast(ray, 3f, out hitInfo, 5f, mask) && (double) Time.realtimeSinceStartup <= (double) this.deathTimeout)
  515.       return;
  516.     this.helicopterBase.Hurt(this.helicopterBase.health * 2f, DamageType.Generic, (BaseEntity) null, false);
  517.   }
  518.  
  519.   public void State_Death_Enter()
  520.   {
  521.     this.maxRotationSpeed *= 8f;
  522.     this._currentState = PatrolHelicopterAI.aiState.DEATH;
  523.     Vector3 randomOffset = this.GetRandomOffset(this.transform.position, 20f, 60f, 20f, 30f);
  524.     int num = -1063040255;
  525.     Vector3 pos;
  526.     Vector3 normal;
  527.     TransformUtil.GetGroundInfo(randomOffset - Vector3.up * 2f, out pos, out normal, 500f, (LayerMask) num, (Transform) null);
  528.     this.SetTargetDestination(pos, 5f, 30f);
  529.     this.targetThrottleSpeed = 0.5f;
  530.     this.deathTimeout = Time.realtimeSinceStartup + 10f;
  531.   }
  532.  
  533.   public void State_Death_Leave()
  534.   {
  535.   }
  536.  
  537.   public void State_Idle_Think(float timePassed)
  538.   {
  539.     this.ExitCurrentState();
  540.     this.State_Patrol_Enter();
  541.   }
  542.  
  543.   public void State_Idle_Enter()
  544.   {
  545.     this._currentState = PatrolHelicopterAI.aiState.IDLE;
  546.   }
  547.  
  548.   public void State_Idle_Leave()
  549.   {
  550.   }
  551.  
  552.   public void State_Move_Think(float timePassed)
  553.   {
  554.     this.targetThrottleSpeed = this.GetThrottleForDistance(Vector3.Distance(this.transform.position, this.destination));
  555.     if (!this.AtDestination())
  556.       return;
  557.     this.ExitCurrentState();
  558.     this.State_Idle_Enter();
  559.   }
  560.  
  561.   public void State_Move_Enter(Vector3 newPos)
  562.   {
  563.     this._currentState = PatrolHelicopterAI.aiState.MOVE;
  564.     this.destination_min_dist = 5f;
  565.     this.SetTargetDestination(newPos, 5f, 30f);
  566.     this.targetThrottleSpeed = this.GetThrottleForDistance(Vector3.Distance(this.transform.position, this.destination));
  567.   }
  568.  
  569.   public void State_Move_Leave()
  570.   {
  571.   }
  572.  
  573.   public void State_Orbit_Think(float timePassed)
  574.   {
  575.     if (!this.breakingOrbit)
  576.     {
  577.       if ((double) Vector3Ex.Distance2D(this.transform.position, this.destination) > 15.0)
  578.         return;
  579.       if (!this.hasEnteredOrbit)
  580.       {
  581.         this.hasEnteredOrbit = true;
  582.         this.orbitStartTime = Time.realtimeSinceStartup;
  583.       }
  584.       float num = 6.283185f * this.currentOrbitDistance / (0.5f * this.maxSpeed);
  585.       this.currentOrbitTime += timePassed / (num * 1.01f);
  586.       Vector3 orbitPosition = this.GetOrbitPosition(this.currentOrbitTime);
  587.       this.ClearAimTarget();
  588.       this.SetTargetDestination(orbitPosition, 0.0f, 1f);
  589.       this.targetThrottleSpeed = 0.5f;
  590.     }
  591.     else if (this.AtDestination())
  592.     {
  593.       this.ExitCurrentState();
  594.       this.State_Idle_Enter();
  595.     }
  596.     if ((double) Time.realtimeSinceStartup - (double) this.orbitStartTime <= (double) this.maxOrbitDuration || this.breakingOrbit)
  597.       return;
  598.     this.breakingOrbit = true;
  599.     this.SetTargetDestination(this.GetAppropriatePosition(this.transform.position + this.transform.forward * 75f, 40f, 50f), 10f, 0.0f);
  600.   }
  601.  
  602.   public Vector3 GetOrbitPosition(float rate)
  603.   {
  604.     return this.interestZoneOrigin + new Vector3(Mathf.Sin(6.283185f * rate) * this.currentOrbitDistance, 20f, Mathf.Cos(6.283185f * rate) * this.currentOrbitDistance);
  605.   }
  606.  
  607.   public void State_Orbit_Enter(float orbitDistance)
  608.   {
  609.     this.breakingOrbit = false;
  610.     this.hasEnteredOrbit = false;
  611.     this.orbitStartTime = Time.realtimeSinceStartup;
  612.     Vector3 vector3 = this.transform.position - this.interestZoneOrigin;
  613.     this.currentOrbitTime = Mathf.Atan2(vector3.x, vector3.z);
  614.     this.currentOrbitDistance = orbitDistance;
  615.     this._currentState = PatrolHelicopterAI.aiState.ORBIT;
  616.     this.ClearAimTarget();
  617.     this.SetTargetDestination(this.GetOrbitPosition(this.currentOrbitTime), 20f, 0.0f);
  618.   }
  619.  
  620.   public void State_Orbit_Leave()
  621.   {
  622.     this.breakingOrbit = false;
  623.     this.hasEnteredOrbit = false;
  624.     this.currentOrbitTime = 0.0f;
  625.     this.ClearAimTarget();
  626.   }
  627.  
  628.   public Vector3 GetRandomPatrolDestination()
  629.   {
  630.     Vector3 vector3_1 = Vector3.zero;
  631.     if (TerrainMeta.Path.Monuments.Count > 0)
  632.     {
  633.       MonumentInfo monumentInfo = (MonumentInfo) null;
  634.       if (this._visitedMonuments.Count > 0)
  635.       {
  636.         using (List<MonumentInfo>.Enumerator enumerator1 = TerrainMeta.Path.Monuments.GetEnumerator())
  637.         {
  638.           while (enumerator1.MoveNext())
  639.           {
  640.             MonumentInfo current1 = enumerator1.Current;
  641.             bool flag = false;
  642.             using (List<MonumentInfo>.Enumerator enumerator2 = this._visitedMonuments.GetEnumerator())
  643.             {
  644.               while (enumerator2.MoveNext())
  645.               {
  646.                 MonumentInfo current2 = enumerator2.Current;
  647.                 if ((Object) current1 == (Object) current2)
  648.                   flag = true;
  649.               }
  650.             }
  651.             if (!flag)
  652.             {
  653.               monumentInfo = current1;
  654.               break;
  655.             }
  656.           }
  657.         }
  658.       }
  659.       if ((Object) monumentInfo == (Object) null)
  660.       {
  661.         this._visitedMonuments.Clear();
  662.         monumentInfo = TerrainMeta.Path.Monuments[Random.Range(0, TerrainMeta.Path.Monuments.Count)];
  663.       }
  664.       if ((bool) ((Object) monumentInfo))
  665.       {
  666.         vector3_1 = monumentInfo.transform.position;
  667.         this._visitedMonuments.Add(monumentInfo);
  668.         vector3_1.y = TerrainMeta.HeightMap.GetHeight(vector3_1) + 200f;
  669.         RaycastHit hitOut;
  670.         if (TransformUtil.GetGroundInfo(vector3_1, out hitOut, 300f, (LayerMask) -1063190527, (Transform) null))
  671.           vector3_1.y = hitOut.point.y;
  672.         vector3_1.y += 30f;
  673.       }
  674.     }
  675.     else
  676.     {
  677.       float num1 = TerrainMeta.Size.x;
  678.       float num2 = 30f;
  679.       Vector3 vector3_2 = Vector3Ex.Range(-1f, 1f);
  680.       vector3_2.y = 0.0f;
  681.       vector3_2.Normalize();
  682.       vector3_1 = vector3_2 * (num1 * Random.Range(0.0f, 0.75f));
  683.       vector3_1.y = num2;
  684.     }
  685.     return vector3_1;
  686.   }
  687.  
  688.   public void State_Patrol_Think(float timePassed)
  689.   {
  690.     float distToTarget = Vector3.Distance(this.transform.position, this.destination);
  691.     this.targetThrottleSpeed = (double) distToTarget > 25.0 ? 0.5f : this.GetThrottleForDistance(distToTarget);
  692.     if (this.AtDestination() && (double) this.arrivalTime == 0.0)
  693.     {
  694.       this.arrivalTime = Time.realtimeSinceStartup;
  695.       this.ExitCurrentState();
  696.       this.maxOrbitDuration = 20f;
  697.       this.State_Orbit_Enter(75f);
  698.     }
  699.     if (this._targetList.Count <= 0)
  700.       return;
  701.     this.interestZoneOrigin = this._targetList[0].ply.transform.position + new Vector3(0.0f, 20f, 0.0f);
  702.     this.ExitCurrentState();
  703.     this.maxOrbitDuration = 10f;
  704.     this.State_Orbit_Enter(75f);
  705.   }
  706.  
  707.   public void State_Patrol_Enter()
  708.   {
  709.     this._currentState = PatrolHelicopterAI.aiState.PATROL;
  710.     Vector3 patrolDestination = this.GetRandomPatrolDestination();
  711.     this.SetTargetDestination(patrolDestination, 10f, 30f);
  712.     this.interestZoneOrigin = patrolDestination;
  713.     this.arrivalTime = 0.0f;
  714.   }
  715.  
  716.   public void State_Patrol_Leave()
  717.   {
  718.   }
  719.  
  720.   public int ClipRocketsLeft()
  721.   {
  722.     return this.numRocketsLeft;
  723.   }
  724.  
  725.   public void State_Strafe_Enter(Vector3 strafePos)
  726.   {
  727.     this._currentState = PatrolHelicopterAI.aiState.STRAFE;
  728.     int mask = LayerMask.GetMask("Terrain", "World", "Construction", "Water");
  729.     Vector3 pos;
  730.     Vector3 normal;
  731.     this.strafe_target_position = !TransformUtil.GetGroundInfo(strafePos, out pos, out normal, 100f, (LayerMask) mask, this.transform) ? strafePos : pos;
  732.     this.numRocketsLeft = this.maxRockets;
  733.     this.lastRocketTime = 0.0f;
  734.     this.movementLockingAiming = true;
  735.     Vector3 randomOffset = this.GetRandomOffset(strafePos, this.strafe_approach_range, this.strafe_approach_range * 1.1f, 20f, 30f);
  736.     this.SetTargetDestination(randomOffset, 10f, 30f);
  737.     this.SetIdealRotation(this.GetYawRotationTo(randomOffset), -1f);
  738.     this.puttingDistance = true;
  739.   }
  740.  
  741.   public void State_Strafe_Think(float timePassed)
  742.   {
  743.     if (this.puttingDistance)
  744.     {
  745.       if (!this.AtDestination())
  746.         return;
  747.       this.puttingDistance = false;
  748.       this.SetTargetDestination(this.strafe_target_position + new Vector3(0.0f, 20f, 0.0f), 10f, 30f);
  749.       this.SetIdealRotation(this.GetYawRotationTo(this.strafe_target_position), -1f);
  750.     }
  751.     else
  752.     {
  753.       this.SetIdealRotation(this.GetYawRotationTo(this.strafe_target_position), -1f);
  754.       float num = Vector3Ex.Distance2D(this.strafe_target_position, this.transform.position);
  755.       if ((double) num <= (double) this.strafe_firing_range && this.ClipRocketsLeft() > 0 && (double) Time.realtimeSinceStartup - (double) this.lastRocketTime > (double) this.timeBetweenRockets)
  756.       {
  757.         float maxDistance = Vector3.Distance(this.strafe_target_position, this.transform.position) - 10f;
  758.         if ((double) maxDistance < 0.0)
  759.           maxDistance = 0.0f;
  760.         if (!Physics.Raycast(this.transform.position, (this.strafe_target_position - this.transform.position).normalized, maxDistance, LayerMask.GetMask("Terrain", "World")))
  761.           this.FireRocket();
  762.       }
  763.       if (this.ClipRocketsLeft() > 0 && (double) num > 15.0)
  764.         return;
  765.       this.ExitCurrentState();
  766.       this.State_Move_Enter(this.GetAppropriatePosition(this.strafe_target_position + this.transform.forward * 120f, 20f, 30f));
  767.     }
  768.   }
  769.  
  770.   public void State_Strafe_Leave()
  771.   {
  772.     this.movementLockingAiming = false;
  773.   }
  774.  
  775.   public void FireRocket()
  776.   {
  777.     --this.numRocketsLeft;
  778.     this.lastRocketTime = Time.realtimeSinceStartup;
  779.     float num1 = 4f;
  780.     bool flag = this.leftTubeFiredLast;
  781.     this.leftTubeFiredLast = !this.leftTubeFiredLast;
  782.     Transform transform = !flag ? this.helicopterBase.rocket_tube_right.transform : this.helicopterBase.rocket_tube_left.transform;
  783.     Vector3 vector3 = transform.position + transform.forward * 1f;
  784.     Vector3 direction = (this.strafe_target_position - vector3).normalized;
  785.     if ((double) num1 > 0.0)
  786.       direction = Quaternion.Euler(Random.Range((float) (-(double) num1 * 0.5), num1 * 0.5f), Random.Range((float) (-(double) num1 * 0.5), num1 * 0.5f), Random.Range((float) (-(double) num1 * 0.5), num1 * 0.5f)) * direction;
  787.     float maxDistance = 1f;
  788.     RaycastHit hitInfo;
  789.     if (Physics.Raycast(vector3, direction, out hitInfo, maxDistance, -1063040255))
  790.     {
  791.       float num2 = hitInfo.distance - 0.1f;
  792.     }
  793.     Effect.server.Run(this.helicopterBase.rocket_fire_effect.resourcePath, (BaseEntity) this.helicopterBase, StringPool.Get(!flag ? "rocket_tube_right" : "rocket_tube_left"), Vector3.zero, Vector3.forward, (Network.Connection) null, true);
  794.     BaseEntity entity = GameManager.server.CreateEntity(this.rocketProjectile.resourcePath, vector3, new Quaternion(), true);
  795.     if ((Object) entity == (Object) null)
  796.       return;
  797.     entity.SendMessage("InitializeVelocity", (object) (direction * 1f));
  798.     entity.Spawn(true);
  799.   }
  800.  
  801.   public void InitializeAI()
  802.   {
  803.     this._lastThinkTime = Time.realtimeSinceStartup;
  804.   }
  805.  
  806.   public void OnCurrentStateExit()
  807.   {
  808.     switch (this._currentState)
  809.     {
  810.       case PatrolHelicopterAI.aiState.MOVE:
  811.         this.State_Move_Leave();
  812.         break;
  813.       case PatrolHelicopterAI.aiState.ORBIT:
  814.         this.State_Orbit_Leave();
  815.         break;
  816.       case PatrolHelicopterAI.aiState.STRAFE:
  817.         this.State_Strafe_Leave();
  818.         break;
  819.       case PatrolHelicopterAI.aiState.PATROL:
  820.         this.State_Patrol_Leave();
  821.         break;
  822.       default:
  823.         this.State_Idle_Leave();
  824.         break;
  825.     }
  826.   }
  827.  
  828.   public void ExitCurrentState()
  829.   {
  830.     this.OnCurrentStateExit();
  831.     this._currentState = PatrolHelicopterAI.aiState.IDLE;
  832.   }
  833.  
  834.   public float GetTime()
  835.   {
  836.     return Time.realtimeSinceStartup;
  837.   }
  838.  
  839.   public void AIThink()
  840.   {
  841.     float time = this.GetTime();
  842.     float timePassed = time - this._lastThinkTime;
  843.     this._lastThinkTime = time;
  844.     switch (this._currentState)
  845.     {
  846.       case PatrolHelicopterAI.aiState.MOVE:
  847.         this.State_Move_Think(timePassed);
  848.         break;
  849.       case PatrolHelicopterAI.aiState.ORBIT:
  850.         this.State_Orbit_Think(timePassed);
  851.         break;
  852.       case PatrolHelicopterAI.aiState.STRAFE:
  853.         this.State_Strafe_Think(timePassed);
  854.         break;
  855.       case PatrolHelicopterAI.aiState.PATROL:
  856.         this.State_Patrol_Think(timePassed);
  857.         break;
  858.       case PatrolHelicopterAI.aiState.DEATH:
  859.         this.State_Death_Think(timePassed);
  860.         break;
  861.       default:
  862.         this.State_Idle_Think(timePassed);
  863.         break;
  864.     }
  865.   }
  866.  
  867.   public Vector3 GetRandomOffset(Vector3 origin, float minRange, float maxRange = 0.0f, float minHeight = 20f, float maxHeight = 30f)
  868.   {
  869.     Vector3 onUnitSphere = Random.onUnitSphere;
  870.     onUnitSphere.y = 0.0f;
  871.     onUnitSphere.Normalize();
  872.     maxRange = Mathf.Max(minRange, maxRange);
  873.     return this.GetAppropriatePosition(origin + onUnitSphere * Random.Range(minRange, maxRange), minHeight, maxHeight);
  874.   }
  875.  
  876.   public Vector3 GetAppropriatePosition(Vector3 origin, float minHeight = 20f, float maxHeight = 30f)
  877.   {
  878.     float y = 100f;
  879.     Ray ray = new Ray(origin + new Vector3(0.0f, y, 0.0f), Vector3.down);
  880.     float radius = 5f;
  881.     int mask = LayerMask.GetMask("Terrain", "World", "Construction", "Water");
  882.     RaycastHit hitInfo;
  883.     if (Physics.SphereCast(ray, radius, out hitInfo, y * 2f - radius, mask))
  884.       origin = hitInfo.point;
  885.     origin.y += Random.Range(minHeight, maxHeight);
  886.     return origin;
  887.   }
  888.  
  889.   public float GetThrottleForDistance(float distToTarget)
  890.   {
  891.     return (double) distToTarget < 75.0 ? ((double) distToTarget < 50.0 ? ((double) distToTarget < 25.0 ? ((double) distToTarget < 5.0 ? (float) (0.0500000007450581 * (1.0 - (double) distToTarget / 5.0)) : 0.05f) : 0.33f) : 0.75f) : 1f;
  892.   }
  893.  
  894.   public class targetinfo
  895.   {
  896.     public float lastSeenTime = float.PositiveInfinity;
  897.     public BasePlayer ply;
  898.     public BaseEntity ent;
  899.     public float visibleFor;
  900.     public float nextLOSCheck;
  901.  
  902.     public targetinfo(BaseEntity initEnt, BasePlayer initPly = null)
  903.     {
  904.       this.ply = initPly;
  905.       this.ent = initEnt;
  906.       this.lastSeenTime = float.PositiveInfinity;
  907.       this.nextLOSCheck = Time.realtimeSinceStartup + 1.5f;
  908.     }
  909.  
  910.     public bool IsVisible()
  911.     {
  912.       return (double) this.TimeSinceSeen() < 1.5;
  913.     }
  914.  
  915.     public float TimeSinceSeen()
  916.     {
  917.       return Time.realtimeSinceStartup - this.lastSeenTime;
  918.     }
  919.   }
  920.  
  921.   public enum aiState
  922.   {
  923.     IDLE,
  924.     MOVE,
  925.     ORBIT,
  926.     STRAFE,
  927.     PATROL,
  928.     GUARD,
  929.     DEATH,
  930.   }
  931. }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement