using System; using System.Collections.Generic; using UnityEngine; namespace SUISSEngine { public class VehicleManager : MonoBehaviour { protected virtual void Awake() { } protected virtual void Start() { } protected virtual void LateUpdate() { this.RefreshVehiclesIfNeeded(); } public virtual void WillBeginBuildingRoads(int type) { } public virtual void DidBuildRoadAt(GridIndex index, Road road) { VehicleManager.RoadStats statsForRoadType = this.GetStatsForRoadType(road.type); statsForRoadType.Area++; } public virtual void WillDestroyRoadAt(GridIndex index, Road road) { VehicleManager.RoadStats statsForRoadType = this.GetStatsForRoadType(road.type); statsForRoadType.Area--; } public virtual void DidFinishBuildingRoads(int type) { this.SetNeedsRefresh(); } public virtual void DidBuildTileAt(GridIndex index, GridTile tile) { } public virtual void WillDestroyTileAt(GridIndex index, GridTile tile) { } public virtual void VehicleStuck(Vehicle vehicle) { if (vehicle == null || !vehicle.IsStuck) { return; } VehicleManager.RoadStats statsForRoadType = this.GetStatsForRoadType(vehicle.RoadType); foreach (VehicleManager.VehicleRegistration vehicleRegistration in statsForRoadType.Registrations) { int num = vehicleRegistration.Instances.IndexOf(vehicle); if (num >= 0) { vehicleRegistration.Instances.RemoveAt(num); break; } } UnityEngine.Object.Destroy(vehicle.gameObject); this.SetNeedsRefresh(); } public VehicleManager.RoadStats GetStatsForRoadType(int type) { VehicleManager.RoadStats roadStats; if (!this.statsDictionary.TryGetValue(type, out roadStats)) { roadStats = this.CreateStatsForRoadType(type); this.statsDictionary.Add(type, roadStats); } return roadStats; } protected virtual VehicleManager.RoadStats CreateStatsForRoadType(int type) { return new VehicleManager.RoadStats(this, type); } protected void SetNeedsRefresh() { this.needsRefresh = true; } protected void RefreshVehiclesIfNeeded() { if (this.needsRefresh) { this.needsRefresh = false; this.RefreshVehicles(); } } protected void RefreshVehicles() { if (this.grid == null) { return; } foreach (VehicleManager.RoadStats roadStats in this.statsDictionary.Values) { foreach (VehicleManager.VehicleRegistration vehicleRegistration in roadStats.Registrations) { while (vehicleRegistration.Instances.Count > vehicleRegistration.PreferredCount) { int index = vehicleRegistration.Instances.Count - 1; Vehicle vehicle = vehicleRegistration.Instances[index]; vehicleRegistration.Instances.RemoveAt(index); UnityEngine.Object.Destroy(vehicle.gameObject); } } } foreach (VehicleManager.RoadStats roadStats2 in this.statsDictionary.Values) { List list = null; bool flag = true; foreach (VehicleManager.VehicleRegistration vehicleRegistration2 in roadStats2.Registrations) { while (vehicleRegistration2.Instances.Count < vehicleRegistration2.PreferredCount) { if (list == null) { list = this.FindRoadsOfType(roadStats2.Type); } Road road = this.FindRandomAvailableRoad(list); if (road == null) { flag = false; break; } GridTile component = road.GetComponent(); if (vehicleRegistration2.Prefabs == null || vehicleRegistration2.Prefabs.Length == 0) { UnityEngine.Debug.LogError("Failed to instantiate a vehicle for " + vehicleRegistration2 + " because it has no prefabs."); break; } GameObject gameObject = vehicleRegistration2.Prefabs[UnityEngine.Random.Range(0, vehicleRegistration2.Prefabs.Length)]; GameObject gameObject2 = UnityEngine.Object.Instantiate(gameObject); Vehicle component2 = gameObject2.GetComponent(); if (component2 == null) { UnityEngine.Debug.LogError(string.Concat(new object[] { "Failed to instantiate a vehicle for ", vehicleRegistration2, " because prefab ", gameObject, " is not a Vehicle." })); UnityEngine.Object.Destroy(gameObject2); } else { component2.transform.parent = this.grid.transform; GridIndex index2 = component.element.Index; index2.u -= UnityEngine.Random.Range(0, component.size.u); index2.v -= UnityEngine.Random.Range(0, component.size.v); vehicleRegistration2.Instances.Add(component2); component2.SpawnAt(index2, roadStats2.Type); } } if (!flag) { break; } } } } protected List FindRoadsOfType(int type) { List list = new List(); if (this.grid == null) { return list; } GridSize size = this.grid.Size; for (int i = 0; i < size.v; i++) { for (int j = 0; j < size.u; j++) { GridTile tile = this.grid[j, i].Tile; if (tile != null) { Road component = tile.GetComponent(); if (component != null && component.type == type) { list.Add(component); } } } } return list; } protected Road FindRandomAvailableRoad(List roads) { Road road = null; while (roads.Count > 0 && road == null) { int index = UnityEngine.Random.Range(0, roads.Count); road = roads[index]; GridIndex index2 = road.GetComponent().index; int num = 0; index2.v--; if (Road.RoadExists(this.grid, index2, road.type)) { num++; } index2.v++; index2.u++; if (Road.RoadExists(this.grid, index2, road.type)) { num++; } index2.u--; index2.v++; if (Road.RoadExists(this.grid, index2, road.type)) { num++; } index2.v--; index2.u--; if (Road.RoadExists(this.grid, index2, road.type)) { num++; } index2.u++; if (num < 2) { roads.RemoveAt(index); road = null; } } return road; } [ChildReference] public IsometricGrid grid; protected Dictionary statsDictionary = new Dictionary(); protected bool needsRefresh; public class RoadStats { public RoadStats(VehicleManager owner, int type) { this._owner = owner; this._type = type; this._area = 0; this._registrations = new List(); this._readOnlyRegistrations = this._registrations.AsReadOnly(); } public VehicleManager Owner { get { return this._owner; } } public int Type { get { return this._type; } } public int Area { get { return this._area; } set { this._area = value; } } public IList Registrations { get { return this._readOnlyRegistrations; } } public VehicleManager.VehicleRegistration RegisterVehicle(Vehicle.VehicleType vehicleType, params GameObject[] prefabs) { VehicleManager.VehicleRegistration vehicleRegistration = this.CreateRegistrationForPrefabs(vehicleType, prefabs); this._registrations.Add(vehicleRegistration); return vehicleRegistration; } public void UnregisterVehicle(VehicleManager.VehicleRegistration registration) { this._registrations.Remove(registration); } protected virtual VehicleManager.VehicleRegistration CreateRegistrationForPrefabs(Vehicle.VehicleType vehicleType, params GameObject[] prefabs) { return new VehicleManager.VehicleRegistration(this, vehicleType, prefabs); } protected VehicleManager _owner; protected int _type; protected int _area; protected List _registrations; protected IList _readOnlyRegistrations; } public class VehicleRegistration { public VehicleRegistration(VehicleManager.RoadStats stats, Vehicle.VehicleType vehicleType, GameObject[] prefabs) { this._stats = stats; this._prefabs = new List(prefabs); this._instances = new List(); this._preferredCount = 0; this._vehicleType = vehicleType; } public int RoadType { get { return this._stats.Type; } } public VehicleManager.RoadStats Stats { get { return this._stats; } } public GameObject[] Prefabs { get { return this._prefabs.ToArray(); } } public List Instances { get { return this._instances; } } public int PreferredCount { get { return this._preferredCount; } set { if (value != this._preferredCount) { this._preferredCount = Math.Max(0, value); this._stats.Owner.SetNeedsRefresh(); } } } public Vehicle.VehicleType VehicleType { get { return this._vehicleType; } } public void AddPrefab(GameObject prefab) { this._prefabs.Add(prefab); } protected VehicleManager.RoadStats _stats; protected List _prefabs; protected List _instances; protected int _preferredCount; protected Vehicle.VehicleType _vehicleType; } } }