- 空基 GenerateFireEventsAt 投放点后移 driftX = cruiseSpeed * fallTime - MunitionEntity 记录 launchTime + flightDuration → ArrivalTime 精确计算 - 云团 Initialization 用 munition.ArrivalTime 非 SimulationTime - CloudGenerated 事件 OccurredAt 用精确到达时刻 - PlatformEntity 存储 ExactReleaseTime - 修复缺失 else 导致的空基走地基分支
126 lines
4.8 KiB
C#
126 lines
4.8 KiB
C#
using System;
|
||
using CounterDrone.Core.Algorithms;
|
||
using CounterDrone.Core.Models;
|
||
|
||
namespace CounterDrone.Core.Simulation
|
||
{
|
||
public enum PlatformState { Idle, FlyingToTarget, ReadyToRelease }
|
||
|
||
public class PlatformEntity
|
||
{
|
||
public string Id { get; }
|
||
public EquipmentRole Role { get; }
|
||
public PlatformType? PlatformType { get; }
|
||
public float PosX { get; private set; }
|
||
public float PosY { get; private set; }
|
||
public float PosZ { get; private set; }
|
||
public AerosolType? AerosolType { get; }
|
||
public int MunitionCount { get; private set; }
|
||
public float Cooldown { get; }
|
||
public float CooldownRemaining { get; private set; }
|
||
public PlatformState State { get; private set; } = PlatformState.Idle;
|
||
|
||
// 空基平台
|
||
public float CruiseSpeed { get; }
|
||
public float PatrolX { get; }
|
||
public float PatrolY { get; }
|
||
public float PatrolZ { get; }
|
||
public float ReleaseAltitude { get; }
|
||
private float _targetX, _targetY, _targetZ;
|
||
private float _flightDistance;
|
||
private float _flownDistance;
|
||
/// <summary>空基平台精确投放时刻(计算值)</summary>
|
||
public float ExactReleaseTime => _exactReleaseTime;
|
||
private float _exactReleaseTime;
|
||
|
||
// 地基平台
|
||
public float MuzzleVelocity { get; }
|
||
|
||
/// <summary>Ready 包含:冷却就绪 + 有弹药 + 非飞行中</summary>
|
||
public bool Ready => CooldownRemaining <= 0 && MunitionCount > 0 && State != PlatformState.FlyingToTarget;
|
||
|
||
public PlatformEntity(string id, EquipmentDeployment config)
|
||
{
|
||
Id = id;
|
||
Role = (EquipmentRole)config.EquipmentRole;
|
||
PlatformType = config.PlatformType.HasValue ? (PlatformType?)config.PlatformType.Value : null;
|
||
PosX = (float)config.PositionX;
|
||
PosY = (float)config.PositionY;
|
||
PosZ = (float)config.PositionZ;
|
||
AerosolType = config.AerosolType.HasValue ? (AerosolType?)config.AerosolType.Value : null;
|
||
MunitionCount = config.MunitionCount ?? 1;
|
||
Cooldown = (float)config.Cooldown;
|
||
MuzzleVelocity = (float)(config.MuzzleVelocity ?? 0f);
|
||
CruiseSpeed = (float)(config.CruiseSpeed ?? 0f);
|
||
ReleaseAltitude = (float)(config.ReleaseAltitude ?? 0f);
|
||
|
||
PatrolX = PosX;
|
||
PatrolY = PosY;
|
||
PatrolZ = PosZ;
|
||
}
|
||
|
||
public void Update(float deltaTime)
|
||
{
|
||
if (CooldownRemaining > 0)
|
||
CooldownRemaining -= deltaTime;
|
||
|
||
if (State != PlatformState.FlyingToTarget) return;
|
||
|
||
float step = CruiseSpeed * deltaTime;
|
||
_flownDistance += step;
|
||
|
||
if (_flownDistance >= _flightDistance || _flightDistance < 0.01f)
|
||
{
|
||
PosX = _targetX;
|
||
PosY = _targetY;
|
||
PosZ = _targetZ;
|
||
State = PlatformState.ReadyToRelease;
|
||
return;
|
||
}
|
||
|
||
float t = _flownDistance / _flightDistance;
|
||
PosX = PatrolX + (_targetX - PatrolX) * t;
|
||
PosY = PatrolY + (_targetY - PatrolY) * t;
|
||
PosZ = PatrolZ + (_targetZ - PatrolZ) * t;
|
||
}
|
||
|
||
/// <summary>下令空基平台飞往投放点</summary>
|
||
public void CommandFlyTo(float targetX, float targetY, float targetZ, float fireTime)
|
||
{
|
||
if (PlatformType != Models.PlatformType.AirBased) return;
|
||
_targetX = targetX;
|
||
_targetY = targetY;
|
||
_targetZ = targetZ;
|
||
float dx = targetX - PosX;
|
||
float dy = targetY - PosY;
|
||
float dz = targetZ - PosZ;
|
||
_flightDistance = (float)Math.Sqrt(dx * dx + dy * dy + dz * dz);
|
||
_flownDistance = 0;
|
||
float flightTime = CruiseSpeed > 0 ? _flightDistance / CruiseSpeed : 0f;
|
||
_exactReleaseTime = fireTime + flightTime;
|
||
State = PlatformState.FlyingToTarget;
|
||
}
|
||
|
||
/// <summary>地基:直接发射;空基:投弹后冷却</summary>
|
||
public void Release()
|
||
{
|
||
MunitionCount--;
|
||
CooldownRemaining = Cooldown;
|
||
State = PlatformState.Idle;
|
||
}
|
||
|
||
/// <summary>空基平台到达投放点后可投弹</summary>
|
||
public bool CanRelease => State == PlatformState.ReadyToRelease && CooldownRemaining <= 0 && MunitionCount > 0;
|
||
|
||
/// <summary>当前速度矢量(空基平台:飞行方向 × 巡航速度;地基:零矢量)</summary>
|
||
public (float Vx, float Vy, float Vz) CurrentVelocity
|
||
{
|
||
get
|
||
{
|
||
if (PlatformType != Models.PlatformType.AirBased) return (0, 0, 0);
|
||
return Kinematics.DirectionVelocity(PatrolX, PatrolY, PatrolZ, _targetX, _targetY, _targetZ, CruiseSpeed);
|
||
}
|
||
}
|
||
}
|
||
}
|