Skip to content
This repository has been archived by the owner on Sep 24, 2020. It is now read-only.

Commit

Permalink
Refactored the CustomCarAI SimulationStep method.
Browse files Browse the repository at this point in the history
  • Loading branch information
seiggy committed Jul 16, 2015
1 parent 866b484 commit ca4b22e
Show file tree
Hide file tree
Showing 4 changed files with 120 additions and 39 deletions.
9 changes: 7 additions & 2 deletions TLM/TLM.sln
Original file line number Diff line number Diff line change
@@ -1,10 +1,15 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 2013
VisualStudioVersion = 12.0.21005.1
# Visual Studio 14
VisualStudioVersion = 14.0.22823.1
MinimumVisualStudioVersion = 10.0.40219.1
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TLM", "TLM\TLM.csproj", "{7422AE58-8B0A-401C-9404-F4A438EFFE10}"
EndProject
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{1D3D9CF0-947E-4A1A-BCFE-25F48E7908DF}"
ProjectSection(SolutionItems) = preProject
..\README.md = ..\README.md
EndProjectSection
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Expand Down
2 changes: 2 additions & 0 deletions TLM/TLM.sln.DotSettings
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
<wpf:ResourceDictionary xml:space="preserve" xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml" xmlns:s="clr-namespace:System;assembly=mscorlib" xmlns:ss="urn:shemas-jetbrains-com:settings-storage-xaml" xmlns:wpf="http://schemas.microsoft.com/winfx/2006/xaml/presentation">
<s:String x:Key="/Default/CodeStyle/Naming/CSharpNaming/Abbreviations/=AI/@EntryIndexedValue">AI</s:String></wpf:ResourceDictionary>
146 changes: 110 additions & 36 deletions TLM/TLM/CustomAI/CustomCarAI.cs
Original file line number Diff line number Diff line change
Expand Up @@ -10,65 +10,139 @@ namespace TrafficManager.CustomAI
{
class CustomCarAI : CarAI
{
public void CustomSimulationStep(ushort vehicleId, ref Vehicle data, Vector3 physicsLodRefPos)
private const int MaxTrailingVehicles = 16384;
private const float FarLod = 1210000f;
private const float CloseLod = 250000f;

public void TmSimulationStep(ushort vehicleId, ref Vehicle vehicleData, Vector3 physicsLodRefPos)
{
if ((data.m_flags & Vehicle.Flags.WaitingPath) != Vehicle.Flags.None)
try
{
if (!CanFindPath(vehicleId, ref data))
return;
FindPathIfNeeded(vehicleId, ref vehicleData);
}
else if ((data.m_flags & Vehicle.Flags.WaitingSpace) != Vehicle.Flags.None)
catch (InvalidOperationException)
{
TrySpawn(vehicleId, ref data);
return;
}

SpawnVehicleIfWaiting(vehicleId, ref vehicleData);

SimulateVehicleChain(vehicleId, ref vehicleData, physicsLodRefPos);

DespawnVehicles(vehicleId, vehicleData);
}

private void SimulateVehicleChain(ushort vehicleId, ref Vehicle vehicleData, Vector3 physicsLodRefPos)
{
var lastFramePosition = vehicleData.GetLastFramePosition();

var lodPhysics = CalculateLod(physicsLodRefPos, lastFramePosition);

SimulationStep(vehicleId, ref vehicleData, vehicleId, ref vehicleData, lodPhysics);

// if there are vehicles behind this, simulate them
if (vehicleData.m_leadingVehicle == 0 && vehicleData.m_trailingVehicle != 0)
{
SimulateTrailingVehicles(vehicleId, ref vehicleData, lodPhysics);
}
}

private void DespawnVehicles(ushort vehicleId, Vehicle vehicleData)
{
DespawnInvalidVehicles(vehicleId, vehicleData);

DespawnVehicleIfOverBlockMax(vehicleId, vehicleData);
}

private void DespawnInvalidVehicles(ushort vehicleId, Vehicle vehicleData)
{
if ((vehicleData.m_flags & (Vehicle.Flags.Spawned | Vehicle.Flags.WaitingPath | Vehicle.Flags.WaitingSpace)) ==
Vehicle.Flags.None && vehicleData.m_cargoParent == 0)
{
Singleton<VehicleManager>.instance.ReleaseVehicle(vehicleId);
}
}

private void DespawnVehicleIfOverBlockMax(ushort vehicleId, Vehicle vehicleData)
{
var maxBlockingVehicles = CalculateMaxBlockingVehicleCount();
if (vehicleData.m_blockCounter >= maxBlockingVehicles && LoadingExtension.Instance.DespawnEnabled)
{
Singleton<VehicleManager>.instance.ReleaseVehicle(vehicleId);
}
}

var lastFramePosition = data.GetLastFramePosition();
private int CalculateMaxBlockingVehicleCount()
{
return (m_info.m_class.m_service > ItemClass.Service.Office) ? 150 : 100;
}

private void SimulateTrailingVehicles(ushort vehicleId, ref Vehicle vehicleData, int lodPhysics)
{
var vehicleManager = Singleton<VehicleManager>.instance;
var trailingVehicleId = vehicleData.m_trailingVehicle;
var numberOfIterations = 0;
SimulateTrailingVehicles(vehicleId, ref vehicleData, lodPhysics, trailingVehicleId, vehicleManager, numberOfIterations);
}

private void SimulateTrailingVehicles(ushort vehicleId, ref Vehicle vehicleData, int lodPhysics,
ushort leadingVehicleId, VehicleManager vehicleManager, int numberOfIterations)
{
if (leadingVehicleId == 0)
{
return;
}

var trailingVehicleId = vehicleManager.m_vehicles.m_buffer[leadingVehicleId].m_trailingVehicle;
var trailingVehicleInfo = vehicleManager.m_vehicles.m_buffer[trailingVehicleId].Info;

trailingVehicleInfo.m_vehicleAI.SimulationStep(trailingVehicleId,
ref vehicleManager.m_vehicles.m_buffer[trailingVehicleId], vehicleId,
ref vehicleData, lodPhysics);

if (++numberOfIterations > MaxTrailingVehicles)
{
CODebugBase<LogChannel>.Error(LogChannel.Core,
"Invalid list detected!\n" + Environment.StackTrace);
return;
}
SimulateTrailingVehicles(trailingVehicleId, ref vehicleData, lodPhysics, trailingVehicleId, vehicleManager, numberOfIterations);
}

private static int CalculateLod(Vector3 physicsLodRefPos, Vector3 lastFramePosition)
{
int lodPhysics;
if (Vector3.SqrMagnitude(physicsLodRefPos - lastFramePosition) >= 1210000f)
if (Vector3.SqrMagnitude(physicsLodRefPos - lastFramePosition) >= FarLod)
{
lodPhysics = 2;
}
else if (
Vector3.SqrMagnitude(Singleton<SimulationManager>.instance.m_simulationView.m_position -
lastFramePosition) >= 250000f)
lastFramePosition) >= CloseLod)
{
lodPhysics = 1;
}
else
{
lodPhysics = 0;
}
SimulationStep(vehicleId, ref data, vehicleId, ref data, lodPhysics);
if (data.m_leadingVehicle == 0 && data.m_trailingVehicle != 0)
{
var instance2 = Singleton<VehicleManager>.instance;
var num = data.m_trailingVehicle;
var num2 = 0;
while (num != 0)
{
var trailingVehicle = instance2.m_vehicles.m_buffer[num].m_trailingVehicle;
var info = instance2.m_vehicles.m_buffer[num].Info;
info.m_vehicleAI.SimulationStep(num, ref instance2.m_vehicles.m_buffer[num], vehicleId,
ref data, lodPhysics);
num = trailingVehicle;
return lodPhysics;
}

if (++num2 > 16384)
{
CODebugBase<LogChannel>.Error(LogChannel.Core,
"Invalid list detected!\n" + Environment.StackTrace);
break;
}
}
}
var num3 = (m_info.m_class.m_service > ItemClass.Service.Office) ? 150 : 100;
if ((data.m_flags & (Vehicle.Flags.Spawned | Vehicle.Flags.WaitingPath | Vehicle.Flags.WaitingSpace)) ==
Vehicle.Flags.None && data.m_cargoParent == 0)
private void SpawnVehicleIfWaiting(ushort vehicleId, ref Vehicle vehicleData)
{
if ((vehicleData.m_flags & Vehicle.Flags.WaitingSpace) != Vehicle.Flags.None)
{
Singleton<VehicleManager>.instance.ReleaseVehicle(vehicleId);
TrySpawn(vehicleId, ref vehicleData);
}
else if (data.m_blockCounter >= num3 && LoadingExtension.Instance.DespawnEnabled)
}

private void FindPathIfNeeded(ushort vehicleId, ref Vehicle vehicleData)
{
if ((vehicleData.m_flags & Vehicle.Flags.WaitingPath) != Vehicle.Flags.None)
{
Singleton<VehicleManager>.instance.ReleaseVehicle(vehicleId);
if (!CanFindPath(vehicleId, ref vehicleData))
throw new InvalidOperationException("Path Not Available for Vehicle");
}
}

Expand Down
2 changes: 1 addition & 1 deletion TLM/TLM/ThreadingExtension.cs
Original file line number Diff line number Diff line change
Expand Up @@ -79,7 +79,7 @@ public override void OnUpdate(float realTimeDelta, float simulationTimeDelta)
typeof (Vehicle).MakeByRefType(),
typeof (Vector3)
}),
typeof (CustomCarAI).GetMethod("CustomSimulationStep"));
typeof (CustomCarAI).GetMethod("TmSimulationStep"));

Debug.Log("Redirecting PassengerCarAI Simulation Step Calls");
LoadingExtension.Instance.RevertMethods[4] =
Expand Down

0 comments on commit ca4b22e

Please sign in to comment.