将配置文件的格式改为TOML

This commit is contained in:
Tian jianyong 2025-05-11 14:39:49 +08:00
parent e630dc3a4c
commit c2d4cb1520
49 changed files with 1087 additions and 207 deletions

View File

@ -15,7 +15,13 @@
- 毫米波跟踪和锁定阶段采用脉冲多普勒制导、目标 RCS 特征矩阵
- 多种发射弹道模式:低平弹道、高抛弹道、俯冲弹道
- 双模、多模制导
- Orientation 坐标系的调整(前向方向从 X 轴改为 Z 轴)
## [0.2.17] - 2025-05-11
- Orientation 坐标系的调整前向方向从X轴改为Z轴
- 将运动学状态KinematicState放到SimulationElement类中替代原来的三个参数
- 修改了输出格式,增加对小值的输出格式
- 将配置文件的格式改为TOML
## [0.2.16] - 2025-05-09
- 支持每个组件同时处理多种干扰

View File

@ -5,8 +5,6 @@ using ThreatSource.Utils;
using ThreatSource.Simulation;
using ThreatSource.Tests.Simulation;
using ThreatSource.Data;
using AirTransmission;
using System.IO;
using Xunit.Abstractions;
namespace ThreatSource.Tests.Jamming

View File

@ -19,4 +19,8 @@
</Reference>
</ItemGroup>
<ItemGroup>
<PackageReference Include="Tomlyn" Version="0.19.0" />
</ItemGroup>
</Project>

View File

@ -0,0 +1,13 @@
# 红外测角仪-001 配置
Type = "InfraredTracker" # 指示器类型
[Name]
Zh = "红外测角仪-001"
En = "IR Tracker-001"
[InfraredTrackerConfig]
MaxTrackingRange = 10000.0 # 最大跟踪距离 (米)
FieldOfView = 0.2 # 视场角 (弧度)
AngleMeasurementAccuracy = 0.001 # 角度测量精度 (弧度)
UpdateFrequency = 10.0 # 更新频率 (赫兹)
JammingResistanceThreshold = 1.0e-5 # 干扰抗性阈值 (瓦特)

View File

@ -0,0 +1,18 @@
# 激光驾束仪-001 配置
Type = "LaserBeamRider" # 指示器类型
[Name]
Zh = "激光驾束仪-001"
En = "Laser Beam Rider-001"
[BeamRiderConfig] # 激光驾束仪配置
Power = 1000.0 # 功率 (瓦特, JSON中为1000)
Wavelength = 1.06 # 波长 (微米)
JammingResistanceThreshold = 1.0e-5 # 干扰抗性阈值 (瓦特)
ControlFieldDiameter = 6.0 # 控制视场直径 (米)
[BeamRiderConfig.LaserCodeConfig] # 激光编码配置
[BeamRiderConfig.LaserCodeConfig.Code]
CodeType = "PRF" # 编码类型
CodeValue = 1010 # 编码值
# IsCodeEnabled and IsCodeMatchRequired are not present in the JSON.

View File

@ -0,0 +1,18 @@
# 前视激光指示器-001 配置
Type = "LaserDesignator" # 指示器类型
[Name]
Zh = "前视激光指示器-001"
En = "Forward Looking Laser Designator-001"
[DesignatorConfig] # 激光指示器配置
Power = 5000.0 # 功率 (瓦特, JSON中为5000)
Wavelength = 1.06 # 波长 (微米)
DivergenceAngle = 0.0003 # 发散角 (弧度)
JammingResistanceThreshold = 1.0e-5 # 干扰抗性阈值 (瓦特)
[DesignatorConfig.LaserCodeConfig] # 激光编码配置
[DesignatorConfig.LaserCodeConfig.Code]
CodeType = "PRF" # 编码类型
CodeValue = 1010 # 编码值
# IsCodeEnabled and IsCodeMatchRequired are not present in the JSON.

View File

@ -0,0 +1,13 @@
# 红外阻塞干扰器配置
Type = "Infrared"
[Name]
Zh = "红外阻塞干扰器"
En = "Infrared Blocking Jammer"
[InfraredJammerConfig]
Power = 2000.0 # 功率 (瓦特)
Wavelength = 5.0 # 波长 (微米)
AngleRange = 10.0 # 角度范围 (度)
Mode = "Blocking" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,13 @@
# 红外欺骗干扰器配置
Type = "Infrared"
[Name]
Zh = "红外欺骗干扰器"
En = "Infrared Deception Jammer"
[InfraredJammerConfig]
Power = 800.0 # 功率 (瓦特)
Wavelength = 5.0 # 波长 (微米)
AngleRange = 15.0 # 角度范围 (度)
Mode = "Deception" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,13 @@
# 标准红外干扰器配置 (内容为阻塞型)
Type = "Infrared"
[Name]
Zh = "红外标准阻塞干扰器" # 根据JSON内容和文件名调整
En = "Infrared Standard Blocking Jammer"
[InfraredJammerConfig]
Power = 1000.0 # 功率 (瓦特)
Wavelength = 5.0 # 波长 (微米)
AngleRange = 10.0 # 角度范围 (度)
Mode = "Blocking" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,13 @@
# 红外顶部阻塞干扰器配置
Type = "Infrared"
[Name]
Zh = "顶部红外阻塞干扰器" #
En = "Top Infrared Blocking Jammer"
[InfraredJammerConfig]
Power = 2000.0 # 功率 (瓦特)
Wavelength = 5.0 # 波长 (微米)
AngleRange = 90.0 # 角度范围 (度)
Mode = "Blocking" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,13 @@
# 激光阻塞干扰器配置
Type = "Laser"
[Name]
Zh = "激光阻塞干扰器"
En = "Laser Blocking Jammer"
[LaserJammerConfig]
Power = 2000.0 # 功率 (瓦特)
Wavelength = 1.06 # 波长 (微米)
AngleRange = 10.0 # 角度范围 (度)
Mode = "Blocking" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,13 @@
# 激光欺骗干扰器配置
Type = "Laser"
[Name]
Zh = "激光欺骗干扰器"
En = "Laser Deception Jammer"
[LaserJammerConfig]
Power = 800.0 # 功率 (瓦特)
Wavelength = 1.06 # 波长 (微米)
AngleRange = 15.0 # 角度范围 (度)
Mode = "Deception" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,15 @@
# 激光诱偏目标配置
Type = "LaserDecoy"
[Name]
Zh = "激光诱偏目标"
En = "Laser Decoy"
[LaserDecoyConfig]
Mode = "Deception" # 模式
Power = 200.0 # 功率 (瓦特)
Wavelength = 1.06 # 波长 (微米)
DivergenceAngle = 0.001 # 发散角 (弧度)
ReflectiveArea = 1.2 # 反射面积 (平方米)
ReflectionCoefficient = 0.8 # 反射系数
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,13 @@
# 激光顶部阻塞干扰器配置
Type = "Laser"
[Name]
Zh = "顶部激光阻塞干扰器" #
En = "Top Laser Blocking Jammer"
[LaserJammerConfig]
Power = 2000.0 # 功率 (瓦特)
Wavelength = 1.06 # 波长 (微米)
AngleRange = 90.0 # 角度范围 (度)
Mode = "Blocking" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,13 @@
# 毫米波阻塞干扰器配置
Type = "MillimeterWave"
[Name]
Zh = "毫米波阻塞干扰器"
En = "Millimeter Wave Blocking Jammer"
[MillimeterWaveJammerConfig]
Power = 2000.0 # 功率 (瓦特)
Wavelength = 3.19 # 波长 (微米)
AngleRange = 15.0 # 角度范围 (度)
Mode = "Blocking" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,14 @@
# 毫米波补偿干扰器 配置
Type = "MillimeterWaveCompensation" # 干扰器类型
[Name]
Zh = "毫米波补偿干扰器"
En = "Millimeter Wave Compensation Jammer"
[MillimeterWaveCompensationJammerConfig]
CompensationTemperature = 293.15 # 补偿温度 (开尔文)
Power = 1000 # 功率 (瓦特)
Wavelength = 8 # 波长 (毫米)
AngleRange = 90 # 角度范围 (度)
Mode = "Deception" # 工作模式 (例如: "Barrage", "Deception")
Duration = 60 # 持续时间 (秒)

View File

@ -0,0 +1,13 @@
# 毫米波顶部阻塞干扰器配置
Type = "MillimeterWave"
[Name]
Zh = "毫米波顶部阻塞干扰器"
En = "Millimeter Wave Top Blocking Jammer"
[MillimeterWaveJammerConfig]
Power = 2000.0 # 功率 (瓦特)
Wavelength = 3.19 # 波长 (微米)
AngleRange = 90.0 # 角度范围 (度)
Mode = "Blocking" # 模式
Duration = 60.0 # 持续时间 (秒)

View File

@ -0,0 +1,19 @@
# 红外频段烟幕弹配置 (示例文件名,内容似乎是周边烟幕)
Type = "SmokeGrenade"
[Name]
Zh = "周边烟幕弹" # 根据JSON内容这似乎是周边烟幕弹的配置
En = "Surround Smoke Grenade"
[SmokeGrenadeConfig]
SmokeType = "Wall"
IsObscuring = true
RadiationTemperature = 395.0
Concentration = 0.2
Duration = 60.0
WallWidth = 50.0
WallHeight = 10.0
CloudDiameter = 0.0
Thickness = 5.0
FormationDelay = 2.0
ExpansionRate = 5.0

View File

@ -0,0 +1,19 @@
# 毫米波频段烟幕弹配置 (示例文件名,内容似乎是周边烟幕)
Type = "SmokeGrenade"
[Name]
Zh = "周边烟幕弹" # 根据JSON内容这似乎是周边烟幕弹的配置
En = "Surround Smoke Grenade"
[SmokeGrenadeConfig]
SmokeType = "Wall"
IsObscuring = true
RadiationTemperature = 173.15
Concentration = 0.2
Duration = 60.0
WallWidth = 50.0
WallHeight = 10.0
CloudDiameter = 0.0
Thickness = 5.0
FormationDelay = 2.0
ExpansionRate = 5.0

View File

@ -0,0 +1,19 @@
# 周边烟幕弹 配置
Type = "SmokeGrenade" # 干扰器类型
[Name]
Zh = "周边烟幕弹"
En = "Surround Smoke Grenade"
[SmokeGrenadeConfig]
SmokeType = "Wall" # 烟幕类型 (例如: "Cloud", "Wall")
IsObscuring = false # 是否遮蔽型 (可见光)
RadiationTemperature = 293.15 # 辐射温度 (开尔文)
Concentration = 0.2 # 浓度 (克/立方米)
Duration = 60.0 # 持续时间 (秒)
WallWidth = 50.0 # 烟幕墙宽度 (米, 当SmokeType为Wall时有效)
WallHeight = 10.0 # 烟幕墙高度 (米, 当SmokeType为Wall时有效)
CloudDiameter = 0.0 # 烟幕云直径 (米, 当SmokeType为Cloud时有效)
Thickness = 5.0 # 烟幕厚度 (米)
FormationDelay = 2.0 #形成延迟时间 (秒)
ExpansionRate = 5.0 # 扩展速率 (米/秒)

View File

@ -0,0 +1,19 @@
# 顶部烟幕弹配置
Type = "SmokeGrenade"
[Name]
Zh = "顶部烟幕弹"
En = "Top Smoke Grenade"
[SmokeGrenadeConfig]
SmokeType = "Cloud"
IsObscuring = true
RadiationTemperature = 395.0
Concentration = 0.2
Duration = 60.0
WallWidth = 0.0
WallHeight = 0.0
CloudDiameter = 20.0
Thickness = 5.0
FormationDelay = 1.5
ExpansionRate = 5.0

View File

@ -0,0 +1,25 @@
# 红外指令导引导弹-001 配置
Type = "InfraredCommandGuidance" # 导弹类型
[Name]
Zh = "红外指令导引导弹-001"
En = "IR Command Guided Missile-001"
[Properties]
Type = "InfraredCommandGuidance" # 属性中的类型与顶层Type一致
MaxSpeed = 300.0 # 最大速度 (米/秒)
MaxFlightTime = 60.0 # 最大飞行时间 (秒)
MaxFlightDistance = 5000.0 # 最大飞行距离 (米)
MaxAcceleration = 100.0 # 最大加速度 (米/秒^2)
ProportionalNavigationCoefficient = 3.0 # 比例导引系数
LaunchAcceleration = 100.0 # 发射加速度 (米/秒^2)
MaxEngineBurnTime = 0.1 # 最大发动机燃烧时间 (秒)
CruiseTime = 5.0 # 巡航时间 (秒)
Mass = 23.5 # 质量 (千克)
ExplosionRadius = 5.0 # 爆炸半径 (米)
HitProbability = 0.9 # 命中概率
SelfDestructHeight = 0.0 # 自毁高度 (米)
# TrackerSensitivity, CommandLatency, IrSignature 在JSON中为null此处省略
[InfraredCommandGuidanceConfig]
JammingResistanceThreshold = 1.0e-5 # 干扰抗性阈值 (瓦特)

View File

@ -0,0 +1,35 @@
# 红外成像末制导导弹-001 配置
Type = "InfraredImagingTerminalGuidance"
[Name]
Zh = "红外成像末制导导弹-001"
En = "IR Imaging Terminal Guided Missile-001"
[Properties]
Type = "InfraredImagingTerminalGuidance"
MaxSpeed = 250.0
MaxFlightTime = 60.0
MaxFlightDistance = 5000.0
MaxAcceleration = 100.0
ProportionalNavigationCoefficient = 3.0
LaunchAcceleration = 100.0
MaxEngineBurnTime = 0.1
CruiseTime = 5.0
Mass = 25.0
ExplosionRadius = 5.5
HitProbability = 0.9
SelfDestructHeight = 0.0
[InfraredImagingGuidanceConfig]
MaxDetectionRange = 1000.0 # 最大探测距离 (米), JSON中为1000对应C#默认为1000.0
SearchFieldOfView = 0.209 # 搜索视场角 (弧度), JSON中为0.209, C#默认为 PI/15 ≈ 0.2094
TrackFieldOfView = 0.052 # 跟踪视场角 (弧度), JSON中为0.052, C#默认为 PI/60 ≈ 0.0523
ImageWidth = 640 # 图像宽度 (像素)
ImageHeight = 512 # 图像高度 (像素)
BackgroundIntensity = 1.0e-4 # 背景辐射强度 (瓦特/球面度), JSON中为1e-4, C#默认为0.01
SearchRecognitionProbability = 0.6 # 搜索模式目标识别概率阈值
TrackRecognitionProbability = 0.8 # 跟踪模式目标识别概率阈值
TargetLostTolerance = 0.2 # 目标丢失容忍时间 (秒)
LockConfirmationTime = 0.3 # 锁定确认时间 (秒)
JammingResistanceThreshold = 1.0e-5 # 干扰抗性阈值 (瓦特)
Wavelength = 3.0 # 波长 (微米), C#中属性名为Wavelength, JSON中为waveLength

View File

@ -0,0 +1,41 @@
# 红箭-10 (HJ-10) 导弹配置
Type = "LaserBeamRiderGuidance" # 导弹类型
[Name]
Zh = "红箭-10"
En = "HJ-10"
[Properties]
Type = "LaserBeamRiderGuidance" # 属性中的类型
MaxSpeed = 300.0 # 最大速度 (米/秒)
MaxFlightTime = 60.0 # 最大飞行时间 (秒)
MaxFlightDistance = 5000.0 # 最大飞行距离 (米)
MaxAcceleration = 100.0 # 最大加速度 (米/秒^2)
ProportionalNavigationCoefficient = 3.0 # 比例导引系数
LaunchAcceleration = 100.0 # 发射加速度 (米/秒^2)
MaxEngineBurnTime = 0.1 # 最大发动机燃烧时间 (秒)
CruiseTime = 5.0 # 巡航时间 (秒)
Mass = 24.5 # 质量 (千克)
ExplosionRadius = 5.0 # 爆炸半径 (米)
HitProbability = 0.9 # 命中概率
SelfDestructHeight = 0.0 # 自毁高度 (米)
[Properties.LaserCodeConfig] # 激光编码配置
IsCodeEnabled = true # 是否启用编码
IsCodeMatchRequired = true # 是否要求编码匹配
[Properties.LaserCodeConfig.Code]
CodeType = "PRF" # 编码类型
CodeValue = 1010 # 编码值
[LaserBeamRiderGuidanceConfig] # 激光驾束制导配置
MinDetectablePower = 1.0e-10 # 最小可探测功率 (瓦特)
DetectorDiameter = 0.03 # 探测器直径 (米)
ControlFieldDiameter = 20.0 # 控制视场直径 (米, 通常指在某一距离上的光斑直径)
ProportionalGain = 30.0 # 比例增益
IntegralGain = 0.05 # 积分增益
DerivativeGain = 5.0 # 微分增益
NonlinearGain = 0.5 # 非线性增益
MaxGuidanceAcceleration = 50.0 # 最大制导加速度 (米/秒^2)
LowPassFilterCoefficient = 0.2 # 低通滤波器系数
Wavelength = 1.06 # 工作波长 (微米)
JammingResistanceThreshold = 1.0e-5 # 干扰抗性阈值 (瓦特)

View File

@ -0,0 +1,26 @@
# 科尔内特 (Kornet) 导弹配置
Type = "LaserBeamRiderGuidance" # 导弹类型
[Name]
Zh = "科尔内特"
En = "Kornet"
[Properties]
Type = "LaserBeamRiderGuidance" # 属性中的类型
MaxSpeed = 300.0 # 最大速度 (米/秒)
MaxFlightTime = 70.0 # 最大飞行时间 (秒)
MaxFlightDistance = 5500.0 # 最大飞行距离 (米)
MaxAcceleration = 110.0 # 最大加速度 (米/秒^2)
ProportionalNavigationCoefficient = 3.0 # 比例导引系数
LaunchAcceleration = 100.0 # 发射加速度 (米/秒^2)
MaxEngineBurnTime = 12.0 # 最大发动机燃烧时间 (秒)
CruiseTime = 5.0 # 巡航时间 (秒)
Mass = 27.0 # 质量 (千克)
ExplosionRadius = 5.5 # 爆炸半径 (米)
HitProbability = 0.9 # 命中概率
SelfDestructHeight = 10.0 # 自毁高度 (米)
[Properties.LaserCodeConfig] # 激光编码配置
[Properties.LaserCodeConfig.Code]
CodeType = "PRF" # 编码类型
CodeValue = 1100 # 编码值

View File

@ -0,0 +1,28 @@
# 陶式导弹 (TOW) 配置
Type = "LaserBeamRiderGuidance" # 导弹类型
[Name]
Zh = "陶式导弹"
En = "TOW"
[Properties]
Type = "LaserBeamRiderGuidance" # 属性中的类型
MaxSpeed = 278.0 # 最大速度 (米/秒)
MaxFlightTime = 65.0 # 最大飞行时间 (秒)
MaxFlightDistance = 4500.0 # 最大飞行距离 (米)
MaxAcceleration = 100.0 # 最大加速度 (米/秒^2)
ProportionalNavigationCoefficient = 3.0 # 比例导引系数
LaunchAcceleration = 100.0 # 发射加速度 (米/秒^2)
MaxEngineBurnTime = 10.0 # 最大发动机燃烧时间 (秒)
CruiseTime = 5.0 # 巡航时间 (秒)
Mass = 22.6 # 质量 (千克)
ExplosionRadius = 5.0 # 爆炸半径 (米)
HitProbability = 0.9 # 命中概率
SelfDestructHeight = 10.0 # 自毁高度 (米)
[Properties.LaserCodeConfig] # 激光编码配置
[Properties.LaserCodeConfig.Code]
CodeType = "PRF" # 编码类型 (例如: "PRF", "Custom")
CodeValue = 1110 # 编码值
# IsCodeEnabled and IsCodeMatchRequired are not present in the JSON,
# assuming they will default or are handled by the C# model if nullable.

View File

@ -0,0 +1,49 @@
// 导弹配置: 激光半主动制导导弹-001
type = "LaserSemiActiveGuidance" // 顶层类型
name { // 不同语言的名称
zh = "激光半主动制导导弹-001"
en = "Laser Semi-Active Guidance Missile-001"
}
properties { // 通用导弹属性
type = "LaserSemiActiveGuidance" // properties内部的类型标识符
maxSpeed = 800.0 // 最大速度 (m/s)
maxFlightTime = 60.0 // 最大飞行时间 (秒)
maxFlightDistance = 4000.0 // 最大飞行距离 (米)
maxAcceleration = 50.0 // 最大横向加速度 (m/s^2)
proportionalNavigationCoefficient = 2.0 // 比例导引系数
launchAcceleration = 100.0 // 初始发射加速度 (m/s^2)
maxEngineBurnTime = 0.1 // 发动机最大燃烧时间 (秒)
cruiseTime = 5.0 //巡航阶段时长 (秒)
mass = 22.0 // 导弹质量 (kg)
explosionRadius = 5.0 // 爆炸半径 (米)
hitProbability = 0.9 // 固有命中概率 (0.0 到 1.0)
selfDestructHeight = 0.0 // 离地自毁高度 (米)
laserCodeConfig { // properties内部的激光编码配置
IsCodeEnabled = true // 激光编码系统是否启用?
IsCodeMatchRequired = true // 制导是否需要匹配激光编码?
code { // 具体的激光编码详情
codeType = "PRF" // 激光编码类型 (例如 PRF)
codeValue = 1010 // 激光编码的实际值
}
}
}
laserSemiActiveGuidanceConfig { // 激光半主动制导系统配置
fieldOfViewAngle = 30.0 // 传感器视场角 (度)
lensDiameter = 0.1 // 传感器透镜直径 (米)
sensorDiameter = 0.03 // 探测器/传感器本身直径 (米)
focusedSpotDiameter = 0.006 // 传感器上聚焦激光光斑直径 (米)
reflectionCoefficient = 0.2 // 目标激光反射系数 (0.0 到 1.0)
targetReflectiveArea = 1.0 // 目标有效反射面积 (m^2)
lockThreshold = 1.0e-7 // 锁定目标的最小接收功率 (瓦特, 例如 1e-7 W)
spotOffsetSensitivity = 0.05 // 对光斑偏移的敏感度,用于制导调整
jammingResistanceThreshold = 1.0e-5 // 克服干扰所需的接收功率阈值 (瓦特, 例如 1e-5 W)
transmitterEfficiency = 0.85 // 激光指示器发射效率 (0.0 到 1.0)
receiverEfficiency = 0.8 // 导弹激光接收器效率 (0.0 到 1.0)
wavelength = 1.06 // 激光波长 (微米, μm)
}

View File

@ -0,0 +1,44 @@
# 导弹配置: 激光半主动制导导弹-001
Type = "LaserSemiActiveGuidance" # 顶层类型
[Name] # 不同语言的名称
Zh = "激光半主动制导导弹-001"
En = "Laser Semi-Active Guidance Missile-001"
[Properties] # 通用导弹属性
Type = "LaserSemiActiveGuidance" # properties内部的类型标识符
MaxSpeed = 800.0 # 最大速度 (m/s)
MaxFlightTime = 60.0 # 最大飞行时间 (秒)
MaxFlightDistance = 4000.0 # 最大飞行距离 (米)
MaxAcceleration = 50.0 # 最大横向加速度 (m/s^2)
ProportionalNavigationCoefficient = 2.0 # 比例导引系数
LaunchAcceleration = 100.0 # 初始发射加速度 (m/s^2)
MaxEngineBurnTime = 0.1 # 发动机最大燃烧时间 (秒)
CruiseTime = 5.0 #巡航阶段时长 (秒)
Mass = 22.0 # 导弹质量 (kg)
ExplosionRadius = 5.0 # 爆炸半径 (米)
HitProbability = 0.9 # 固有命中概率 (0.0 到 1.0)
SelfDestructHeight = 0.0 # 离地自毁高度 (米)
[Properties.LaserCodeConfig] # properties内部的激光编码配置
IsCodeEnabled = true # 激光编码系统是否启用?
IsCodeMatchRequired = true # 制导是否需要匹配激光编码?
[Properties.LaserCodeConfig.Code] # 具体的激光编码详情
CodeType = "PRF" # 激光编码类型 (例如 PRF)
CodeValue = 1010 # 激光编码的实际值
[LaserSemiActiveGuidanceConfig] # 激光半主动制导系统配置
FieldOfViewAngle = 30.0 # 传感器视场角 (度)
LensDiameter = 0.1 # 传感器透镜直径 (米)
SensorDiameter = 0.03 # 探测器/传感器本身直径 (米)
FocusedSpotDiameter = 0.006 # 传感器上聚焦激光光斑直径 (米)
ReflectionCoefficient = 0.2 # 目标激光反射系数 (0.0 到 1.0)
TargetReflectiveArea = 1.0 # 目标有效反射面积 (m^2)
LockThreshold = 1.0e-7 # 锁定目标的最小接收功率 (瓦特, 例如 1e-7 W)
SpotOffsetSensitivity = 0.05 # 对光斑偏移的敏感度,用于制导调整
JammingResistanceThreshold = 1.0e-5 # 克服干扰所需的接收功率阈值 (瓦特, 例如 1e-5 W)
TransmitterEfficiency = 0.85 # 激光指示器发射效率 (0.0 到 1.0)
ReceiverEfficiency = 0.8 # 导弹激光接收器效率 (0.0 到 1.0)
Wavelength = 1.06 # 激光波长 (微米, μm)

View File

@ -0,0 +1,56 @@
# 毫米波末制导导弹-001 配置
Type = "MillimeterWaveTerminalGuidance" # 导弹类型
[Name]
Zh = "毫米波末制导导弹-001"
En = "Millimeter Wave Terminal Guided Missile-001"
[Properties]
Type = "MillimeterWaveTerminalGuidance" # 属性中的类型与顶层Type一致
MaxSpeed = 250.0 # 最大速度 (米/秒)
MaxFlightTime = 60.0 # 最大飞行时间 (秒)
MaxFlightDistance = 8000.0 # 最大飞行距离 (米)
MaxAcceleration = 100.0 # 最大加速度 (米/秒^2)
ProportionalNavigationCoefficient = 3.0 # 比例导引系数
LaunchAcceleration = 100.0 # 发射加速度 (米/秒^2)
MaxEngineBurnTime = 0.1 # 最大发动机燃烧时间 (秒)
CruiseTime = 4.0 # 巡航时间 (秒)
Mass = 28.0 # 质量 (千克)
ExplosionRadius = 5.0 # 爆炸半径 (米)
HitProbability = 0.9 # 命中概率
SelfDestructHeight = 0.0 # 自毁高度 (米)
[MillimeterWaveGuidanceConfig]
MaxDetectionRange = 5000.0 # 最大探测距离 (米)
FieldOfViewAngle = 45.0 # 视场角 (度)
TargetRecognitionProbability = 0.95 # 目标识别概率
WaveFrequency = 9.4e10 # 波频率 (赫兹, JSON中为94e9)
PulseDuration = 1.0e-6 # 脉冲持续时间 (秒)
SearchBeamWidth = 4.0 # 搜索波束宽度 (度)
TrackBeamWidth = 2.0 # 跟踪波束宽度 (度)
LockBeamWidth = 1.0 # 锁定波束宽度 (度)
ScanAngularSpeedDeg = 360.0 # 扫描角速度 (度/秒)
ScanRadiusGrowthRateDeg = 22.5 # 扫描半径增长率 (度)
RecognitionSNRThreshold = -25.0 # 识别信噪比阈值 (分贝)
LockSNRThreshold = -10.0 # 锁定信噪比阈值 (分贝)
TargetLostTolerance = 0.2 # 目标丢失容忍时间 (秒)
LockConfirmationTime = 0.3 # 锁定确认时间 (秒)
PulseRepetitionFrequency = 1.0e-4 # 脉冲重复频率 (秒, JSON中为1e-4通常PRT单位是秒PRF是Hz。这里JSON的注释可能不准确按数值和C#模型属性名推断这里应为PulseRepetitionTime即脉冲重复间隔)
TransmitPower = 0.3 # 发射功率 (瓦特)
DopplerVelocityResolution = 1.0 # 多普勒速度分辨率 (米/秒)
MaxMeasurableVelocity = 1000.0 # 最大可测量速度 (米/秒)
AntennaGainDB = 23.0 # 天线增益 (分贝)
NoiseFigureDB = 7.0 # 噪声系数 (分贝)
SystemLossDB = 6.0 # 系统损耗 (分贝)
MonopulseSensitivity = 1.0 # 单脉冲灵敏度 (单位取决于具体实现JSON中为1)
YawControlEffectiveness = 120.0 # 偏航控制有效性 (度/秒^2 或类似单位)
PitchControlEffectiveness = 150.0 # 俯仰控制有效性 (度/秒^2 或类似单位)
JammingResistanceThreshold = 1.0e-5 # 干扰抗性阈值 (瓦特)

View File

@ -0,0 +1,78 @@
# 末敏导弹-001 配置
Type = "TerminalSensitiveMissile" # 导弹类型
SubmunitionCount = 1 # 子弹药数量
[Name]
Zh = "末敏导弹-001"
En = "Terminal Sensitive Missile-001"
[Properties] # 母弹属性
Type = "TerminalSensitiveMissile" # 属性中的类型
MaxSpeed = 1000.0 # 最大速度 (米/秒)
MaxFlightTime = 100.0 # 最大飞行时间 (秒)
MaxFlightDistance = 5000.0 # 最大飞行距离 (米)
MaxAcceleration = 200.0 # 最大加速度 (米/秒^2)
ProportionalNavigationCoefficient = 3.0 # 比例导引系数
LaunchAcceleration = 100.0 # 发射加速度 (米/秒^2)
MaxEngineBurnTime = 0.1 # 最大发动机燃烧时间 (秒)
CruiseTime = 5.0 # 巡航时间 (秒)
Mass = 50.0 # 质量 (千克)
ExplosionRadius = 5.0 # 爆炸半径 (米)
SelfDestructHeight = 0.0 # 自毁高度 (米)
[SubmunitionProperties] # 子弹药属性
MaxSpeed = 2000.0 # 最大速度 (米/秒)
MaxFlightTime = 60.0 # 最大飞行时间 (秒)
MaxFlightDistance = 2000.0 # 最大飞行距离 (米)
MaxAcceleration = 300.0 # 最大加速度 (米/秒^2)
ProportionalNavigationCoefficient = 4.0 # 比例导引系数
LaunchAcceleration = 10.0 # 发射加速度 (米/秒^2)
MaxEngineBurnTime = 0.1 # 最大发动机燃烧时间 (秒)
Mass = 10.0 # 质量 (千克)
ExplosionRadius = 5.0 # 爆炸半径 (米)
HitProbability = 0.9 # 命中概率
SelfDestructHeight = 20.0 # 自毁高度 (米)
[SubmunitionConfig] # 子弹药配置
SeparationHeight = 1000.0 # 分离高度 (米)
SeparationDistance = 1000.0 # 分离距离 (米)
SubmunitionSeparationAngle = 45.0 # 子弹药分离角度 (度)
SeparationRange = 50.0 # 分离散布范围 (米)
DecelerationAcceleration = 250.0 # 减速加速度 (米/秒^2)
DecelerationEndSpeed = 50.0 # 减速结束速度 (米/秒)
ParachuteDeploymentHeight = 400.0 # 开伞高度 (米)
ParachuteDeceleration = 90.0 # 降落伞减速度 (米/秒^2)
StableScanHeight = 200.0 # 稳定扫描高度 (米)
VerticalDeclineSpeed = 10.0 # 垂直下降速度 (米/秒)
SpiralRotationSpeed = 25.13 # 螺旋旋转速度 (弧度/秒)
ScanAngle = 30.0 # 扫描角度 (度)
TargetDetectionDistance = 150.0 # 目标探测距离 (米)
SelfDestructHeight = 20.0 # (子弹药)自毁高度 (米)
AttackSpeed = 200.0 # 攻击速度 (米/秒)
[SubmunitionConfig.InfraredDetectorConfig] # 子弹药红外探测器配置
MaxDetectionRange = 1000.0 # 最大探测距离 (米)
Band = "Medium" # 工作波段 (例如: "Short", "Medium", "Long")
FieldOfView = 1.0 # 视场角 (弧度)
DetectionRadiationIntensityThreshold = 50.0 # 探测辐射强度阈值 (瓦特/球面度)
JammingResistanceThreshold = 1.0e-4 # 干扰抗性阈值 (瓦特)
[SubmunitionConfig.RadiometerConfig] # 子弹药辐射计配置
MaxDetectionRange = 1000.0 # 最大探测距离 (米)
Band = "Band8" # 工作波段 (例如: "Band3", "Band8", "Band35", "Band94")
ScanFieldOfView = 1.0 # 扫描视场角 (弧度)
JammingResistanceThreshold = 1.0e-4 # 干扰抗性阈值 (瓦特)
[SubmunitionConfig.AltimeterConfig] # 子弹药高度计配置
MaxAltitude = 1000.0 # 最大高度 (米)
Band = "Band3" # 工作波段
MeasurementAccuracy = 0.5 # 测量精度 (米)
ScanFieldOfView = 25.0 # 扫描视场角 (度)
JammingResistanceThreshold = 1.0e-4 # 干扰抗性阈值 (瓦特)
[SubmunitionConfig.RangefinderConfig] # 子弹药激光测距仪配置
MaxDetectionRange = 1000.0 # 最大探测距离 (米)
Wavelength = 1.06 # 波长 (微米)
PulseRate = 100.0 # 脉冲频率 (赫兹)
Accuracy = 0.5 # 精度 (米)
JammingResistanceThreshold = 1.0e-4 # 干扰抗性阈值 (瓦特)

View File

@ -0,0 +1,33 @@
# 装甲运兵车-001 配置
Type = "APC" # 目标类型
[Name]
Zh = "装甲运兵车-001"
En = "Armored Personnel Carrier-001"
[Properties]
Type = "APC" # 属性中的类型
Mass = 25000.0 # 质量 (千克)
Length = 7.0 # 长度 (米)
Width = 3.2 # 宽度 (米)
Height = 2.8 # 高度 (米)
MaxSpeed = 80.0 # 最大速度 (千米/小时)
ArmorThickness = 400.0 # 装甲厚度 (毫米)
RadarCrossSection = 12.0 # 雷达散射截面积 (平方米)
InfraredRadiationIntensity = 2000.0 # 红外辐射强度 (瓦特/球面度)
UltravioletRadiationIntensity = 12.0 # 紫外辐射强度 (瓦特/球面度)
MillimeterWaveRadiationIntensity = 8.0 # 毫米波辐射强度 (瓦特/球面度)
MillimeterWaveRadiationTemperature = 350.0 # 毫米波辐射温度 (开尔文)
LaserReflectivity = 0.25 # 激光反射率
[Properties.ThermalPattern] # 热辐射特征模型
StaticPatternSource = [ # 静态时温度分布
[35, 40, 65],
[30, 35, 70],
[40, 40, 45]
]
MovingPatternSource = [ # 移动时温度分布
[40, 45, 70],
[35, 40, 75],
[50, 50, 55]
]

View File

@ -0,0 +1,33 @@
# 武装直升机-001 配置
Type = "Helicopter" # 目标类型
[Name]
Zh = "武装直升机-001"
En = "Attack Helicopter-001"
[Properties]
Type = "Helicopter" # 属性中的类型
Mass = 10000.0 # 质量 (千克)
Length = 17.0 # 长度 (米)
Width = 3.0 # 宽度 (米)
Height = 4.5 # 高度 (米)
MaxSpeed = 280.0 # 最大速度 (千米/小时, JSON中为280C#中可能是米/秒,需确认)
ArmorThickness = 150.0 # 装甲厚度 (毫米)
RadarCrossSection = 8.0 # 雷达散射截面积 (平方米)
InfraredRadiationIntensity = 3000.0 # 红外辐射强度 (瓦特/球面度)
UltravioletRadiationIntensity = 20.0 # 紫外辐射强度 (瓦特/球面度)
MillimeterWaveRadiationIntensity = 6.0 # 毫米波辐射强度 (瓦特/球面度)
MillimeterWaveRadiationTemperature = 450.0 # 毫米波辐射温度 (开尔文)
LaserReflectivity = 0.2 # 激光反射率
[Properties.ThermalPattern] # 热辐射特征模型
StaticPatternSource = [ # 静态时温度分布
[85, 110, 80],
[35, 45, 40],
[30, 35, 30]
]
MovingPatternSource = [ # 移动时温度分布
[90, 115, 85],
[40, 50, 45],
[35, 40, 35]
]

View File

@ -0,0 +1,33 @@
# 主战坦克-001 配置
Type = "Tank" # 目标类型
[Name]
Zh = "主战坦克-001"
En = "Main Battle Tank-001"
[Properties]
Type = "Tank" # 属性中的类型
Mass = 50000.0 # 质量 (千克)
Length = 10.0 # 长度 (米)
Width = 3.5 # 宽度 (米)
Height = 2.4 # 高度 (米)
MaxSpeed = 70.0 # 最大速度 (千米/小时)
ArmorThickness = 800.0 # 装甲厚度 (毫米)
RadarCrossSection = 15.0 # 雷达散射截面积 (平方米)
InfraredRadiationIntensity = 250.0 # 红外辐射强度 (瓦特/球面度)
UltravioletRadiationIntensity = 15.0 # 紫外辐射强度 (瓦特/球面度)
MillimeterWaveRadiationIntensity = 10.0 # 毫米波辐射强度 (瓦特/球面度)
MillimeterWaveRadiationTemperature = 150.0 # 毫米波辐射温度 (开尔文)
LaserReflectivity = 0.3 # 激光反射率
[Properties.ThermalPattern] # 热辐射特征模型
StaticPatternSource = [ # 静态时温度分布
[40, 45, 80],
[35, 40, 90],
[50, 50, 60]
]
MovingPatternSource = [ # 移动时温度分布
[45, 50, 85],
[40, 45, 95],
[65, 65, 75]
]

View File

@ -0,0 +1,16 @@
# 浓雾 天气配置
[Name]
Zh = "浓雾"
En = "Heavy Fog"
[WeatherConfig]
Type = "Fog" # 天气类型
Temperature = 8.0 # 温度 (摄氏度)
RelativeHumidity = 99.0 # 相对湿度 (%)
Visibility = 0.1 # 能见度 (公里)
Precipitation = 0.0 # 降水量 (毫米/小时)
CO2Concentration = 415.0 # 二氧化碳浓度 (ppm)
Pressure = 998.0 # 大气压力 (hPa)
WindSpeed = 0.0 # 风速 (米/秒)
WindDirection = 0.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 大雨 天气配置
[Name]
Zh = "大雨"
En = "Heavy Rain"
[WeatherConfig]
Type = "Rain" # 天气类型
Temperature = 16.0 # 温度 (摄氏度)
RelativeHumidity = 95.0 # 相对湿度 (%)
Visibility = 2.0 # 能见度 (公里)
Precipitation = 25.0 # 降水量 (毫米/小时)
CO2Concentration = 415.0 # 二氧化碳浓度 (ppm)
Pressure = 985.0 # 大气压力 (hPa)
WindSpeed = 8.0 # 风速 (米/秒)
WindDirection = 180.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 大雪 天气配置
[Name]
Zh = "大雪"
En = "Heavy Snow"
[WeatherConfig]
Type = "Snow" # 天气类型
Temperature = -7.0 # 温度 (摄氏度)
RelativeHumidity = 85.0 # 相对湿度 (%)
Visibility = 1.0 # 能见度 (公里)
Precipitation = 8.0 # 降水量 (毫米/小时)
CO2Concentration = 410.0 # 二氧化碳浓度 (ppm)
Pressure = 990.0 # 大气压力 (hPa)
WindSpeed = 6.0 # 风速 (米/秒)
WindDirection = 270.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 轻雾 天气配置
[Name]
Zh = "轻雾"
En = "Light Fog"
[WeatherConfig]
Type = "Fog" # 天气类型
Temperature = 12.0 # 温度 (摄氏度)
RelativeHumidity = 95.0 # 相对湿度 (%)
Visibility = 0.8 # 能见度 (公里)
Precipitation = 0.0 # 降水量 (毫米/小时)
CO2Concentration = 415.0 # 二氧化碳浓度 (ppm)
Pressure = 1000.0 # 大气压力 (hPa)
WindSpeed = 0.5 # 风速 (米/秒)
WindDirection = 20.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 小雨 天气配置
[Name]
Zh = "小雨"
En = "Light Rain"
[WeatherConfig]
Type = "Rain" # 天气类型
Temperature = 20.0 # 温度 (摄氏度)
RelativeHumidity = 80.0 # 相对湿度 (%)
Visibility = 6.0 # 能见度 (公里)
Precipitation = 5.0 # 降水量 (毫米/小时)
CO2Concentration = 415.0 # 二氧化碳浓度 (ppm)
Pressure = 1005.0 # 大气压力 (hPa)
WindSpeed = 3.0 # 风速 (米/秒)
WindDirection = 180.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 小雪 天气配置
[Name]
Zh = "小雪"
En = "Light Snow"
[WeatherConfig]
Type = "Snow" # 天气类型
Temperature = -3.0 # 温度 (摄氏度)
RelativeHumidity = 75.0 # 相对湿度 (%)
Visibility = 4.0 # 能见度 (公里)
Precipitation = 2.0 # 降水量 (毫米/小时)
CO2Concentration = 410.0 # 二氧化碳浓度 (ppm)
Pressure = 1002.0 # 大气压力 (hPa)
WindSpeed = 3.0 # 风速 (米/秒)
WindDirection = 270.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 中雾 天气配置
[Name]
Zh = "中雾"
En = "Medium Fog"
[WeatherConfig]
Type = "Fog" # 天气类型
Temperature = 10.0 # 温度 (摄氏度)
RelativeHumidity = 98.0 # 相对湿度 (%)
Visibility = 0.4 # 能见度 (公里)
Precipitation = 0.0 # 降水量 (毫米/小时)
CO2Concentration = 415.0 # 二氧化碳浓度 (ppm)
Pressure = 1000.0 # 大气压力 (hPa)
WindSpeed = 0.2 # 风速 (米/秒)
WindDirection = 10.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 中雨 天气配置
[Name]
Zh = "中雨"
En = "Medium Rain"
[WeatherConfig]
Type = "Rain" # 天气类型
Temperature = 18.0 # 温度 (摄氏度)
RelativeHumidity = 90.0 # 相对湿度 (%)
Visibility = 4.0 # 能见度 (公里)
Precipitation = 15.0 # 降水量 (毫米/小时)
CO2Concentration = 415.0 # 二氧化碳浓度 (ppm)
Pressure = 995.0 # 大气压力 (hPa)
WindSpeed = 6.0 # 风速 (米/秒)
WindDirection = 180.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 中雪 天气配置
[Name]
Zh = "中雪"
En = "Medium Snow"
[WeatherConfig]
Type = "Snow" # 天气类型
Temperature = -5.0 # 温度 (摄氏度)
RelativeHumidity = 80.0 # 相对湿度 (%)
Visibility = 2.0 # 能见度 (公里)
Precipitation = 4.0 # 降水量 (毫米/小时)
CO2Concentration = 410.0 # 二氧化碳浓度 (ppm)
Pressure = 1000.0 # 大气压力 (hPa)
WindSpeed = 4.0 # 风速 (米/秒)
WindDirection = 270.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 沙尘 天气配置
[Name]
Zh = "沙尘"
En = "Sandstorm"
[WeatherConfig]
Type = "Dust" # 天气类型
Temperature = 30.0 # 温度 (摄氏度)
RelativeHumidity = 25.0 # 相对湿度 (%)
Visibility = 1.5 # 能见度 (公里)
Precipitation = 0.0 # 降水量 (毫米/小时)
CO2Concentration = 430.0 # 二氧化碳浓度 (ppm)
Pressure = 1005.0 # 大气压力 (hPa)
WindSpeed = 12.0 # 风速 (米/秒)
WindDirection = 315.0 # 风向 (度0为北顺时针增加)

View File

@ -0,0 +1,16 @@
# 晴天 天气配置
[Name]
Zh = "晴天"
En = "Sunny"
[WeatherConfig]
Type = "Clear" # 天气类型
Temperature = 25.0 # 温度 (摄氏度)
RelativeHumidity = 45.0 # 相对湿度 (%)
Visibility = 15.0 # 能见度 (公里)
Precipitation = 0.0 # 降水量 (毫米/小时)
CO2Concentration = 415.0 # 二氧化碳浓度 (ppm)
Pressure = 1018.0 # 大气压力 (hPa)
WindSpeed = 1.2 # 风速 (米/秒)
WindDirection = 90.0 # 风向 (度0为北顺时针增加)

View File

@ -1,5 +1,8 @@
using System.Text.Json;
using System.Text.Json.Serialization;
using System.IO;
using Tomlyn;
using Tomlyn.Model; // Required for TomlModelOptions
using System;
// No longer need Tomlyn.Syntax for exceptions if ConvertTo is removed
namespace ThreatSource.Data
{
@ -19,15 +22,11 @@ namespace ThreatSource.Data
/// 默认数据目录路径
/// </summary>
private static readonly string DATA_PATH = "../data";
private static readonly JsonSerializerOptions _jsonOptions = new()
private static readonly TomlModelOptions _tomlOptions = new()
{
PropertyNameCaseInsensitive = true,
WriteIndented = true,
Converters =
{
new JsonStringEnumConverter(JsonNamingPolicy.CamelCase)
}
ConvertPropertyName = name => name
};
private readonly Dictionary<string, MissileData> _missiles = [];
private readonly Dictionary<string, IndicatorData> _indicators = [];
private readonly Dictionary<string, SensorData> _sensors = [];
@ -71,13 +70,12 @@ namespace ThreatSource.Data
return;
}
foreach (var file in Directory.GetFiles(path, "*.json", SearchOption.AllDirectories))
foreach (var file in Directory.GetFiles(path, "*.toml", SearchOption.AllDirectories))
{
try
{
var jsonContent = File.ReadAllText(file);
var data = JsonSerializer.Deserialize<MissileData>(jsonContent, _jsonOptions);
var tomlContent = File.ReadAllText(file);
var data = Toml.ToModel<MissileData>(tomlContent, options: _tomlOptions); // Pass options
if (data != null)
{
string model = Path.GetFileNameWithoutExtension(file);
@ -107,13 +105,12 @@ namespace ThreatSource.Data
return;
}
foreach (var file in Directory.GetFiles(path, "*.json", SearchOption.AllDirectories))
foreach (var file in Directory.GetFiles(path, "*.toml", SearchOption.AllDirectories))
{
try
{
var jsonContent = File.ReadAllText(file);
var data = JsonSerializer.Deserialize<IndicatorData>(jsonContent, _jsonOptions);
var tomlContent = File.ReadAllText(file);
var data = Toml.ToModel<IndicatorData>(tomlContent, options: _tomlOptions); // Pass options
if (data != null)
{
string model = Path.GetFileNameWithoutExtension(file);
@ -139,13 +136,12 @@ namespace ThreatSource.Data
return;
}
foreach (var file in Directory.GetFiles(path, "*.json", SearchOption.AllDirectories))
foreach (var file in Directory.GetFiles(path, "*.toml", SearchOption.AllDirectories))
{
try
{
var jsonContent = File.ReadAllText(file);
var data = JsonSerializer.Deserialize<SensorData>(jsonContent, _jsonOptions);
var tomlContent = File.ReadAllText(file);
var data = Toml.ToModel<SensorData>(tomlContent, options: _tomlOptions); // Pass options
if (data != null)
{
string model = Path.GetFileNameWithoutExtension(file);
@ -171,13 +167,12 @@ namespace ThreatSource.Data
return;
}
foreach (var file in Directory.GetFiles(path, "*.json", SearchOption.AllDirectories))
foreach (var file in Directory.GetFiles(path, "*.toml", SearchOption.AllDirectories))
{
try
{
var jsonContent = File.ReadAllText(file);
var data = JsonSerializer.Deserialize<EquipmentData>(jsonContent, _jsonOptions);
var tomlContent = File.ReadAllText(file);
var data = Toml.ToModel<EquipmentData>(tomlContent, options: _tomlOptions); // Pass options
if (data != null)
{
string model = Path.GetFileNameWithoutExtension(file);
@ -204,12 +199,12 @@ namespace ThreatSource.Data
return;
}
foreach (var file in Directory.GetFiles(path, "*.json", SearchOption.AllDirectories))
foreach (var file in Directory.GetFiles(path, "*.toml", SearchOption.AllDirectories))
{
try
{
var jsonContent = File.ReadAllText(file);
var data = JsonSerializer.Deserialize<WeatherData>(jsonContent, _jsonOptions);
var tomlContent = File.ReadAllText(file);
var data = Toml.ToModel<WeatherData>(tomlContent, options: _tomlOptions); // Pass options
if (data != null)
{
string model = Path.GetFileNameWithoutExtension(file);
@ -235,12 +230,12 @@ namespace ThreatSource.Data
return;
}
foreach (var file in Directory.GetFiles(path, "*.json", SearchOption.AllDirectories))
foreach (var file in Directory.GetFiles(path, "*.toml", SearchOption.AllDirectories))
{
try
{
var jsonContent = File.ReadAllText(file);
var data = JsonSerializer.Deserialize<JammerData>(jsonContent, _jsonOptions);
var tomlContent = File.ReadAllText(file);
var data = Toml.ToModel<JammerData>(tomlContent, options: _tomlOptions); // Pass options
if (data != null)
{
string model = Path.GetFileNameWithoutExtension(file);

View File

@ -1,13 +1,12 @@
using System.Text.Json.Serialization;
using System.Collections.Generic;
using System;
using System.Text.Json;
using System.Text.Json.Serialization;
namespace ThreatSource.Equipment
{
/// <summary>
/// 目标的温度分布模式
/// </summary>
[JsonConverter(typeof(ThermalPatternConverter))]
public class ThermalPattern
{
/// <summary>
@ -15,28 +14,51 @@ namespace ThreatSource.Equipment
/// </summary>
public const int GRID_SIZE = 3;
// TOML 键名将直接是 StaticPatternSource 和 MovingPatternSource
/// <summary>
/// 静止状态下的温度分布源数据 (供Tomlyn使用)
/// </summary>
public List<List<double>> StaticPatternSource { get; set; }
/// <summary>
/// 运动状态下的温度分布源数据 (供Tomlyn使用)
/// </summary>
public List<List<double>> MovingPatternSource { get; set; }
/// <summary>
/// 静止状态下的温度分布(摄氏度)
/// </summary>
public double[,] StaticPattern { get; }
public double[,] StaticPattern
{
get { return ConvertSourceToGrid(StaticPatternSource, nameof(StaticPatternSource)); }
}
/// <summary>
/// 运动状态下的温度分布(摄氏度)
/// </summary>
public double[,] MovingPattern { get; }
public double[,] MovingPattern
{
get { return ConvertSourceToGrid(MovingPatternSource, nameof(MovingPatternSource)); }
}
/// <summary>
/// 无参数构造函数 (供Tomlyn使用)
/// </summary>
public ThermalPattern()
{
// 初始化为空列表以便即使TOML中缺少这些字段属性也不会是null从而简化访问逻辑
StaticPatternSource = new List<List<double>>();
MovingPatternSource = new List<List<double>>();
}
/// <summary>
/// 初始化温度分布模式
/// 初始化温度分布模式 (通过 double[,] 数组)
/// </summary>
public ThermalPattern(double[,] staticPattern, double[,] movingPattern)
{
if (staticPattern.GetLength(0) != GRID_SIZE || staticPattern.GetLength(1) != GRID_SIZE)
throw new ArgumentException("Static pattern must be 3x3");
if (movingPattern.GetLength(0) != GRID_SIZE || movingPattern.GetLength(1) != GRID_SIZE)
throw new ArgumentException("Moving pattern must be 3x3");
StaticPattern = staticPattern;
MovingPattern = movingPattern;
// 将输入的 double[,] 转换为 List<List<double>> 并存储
StaticPatternSource = ConvertGridToSource(staticPattern, nameof(staticPattern));
MovingPatternSource = ConvertGridToSource(movingPattern, nameof(movingPattern));
}
/// <summary>
@ -105,146 +127,58 @@ namespace ThreatSource.Equipment
verticalGradient * verticalWeight +
concentrationGradient * concentrationWeight;
}
}
/// <summary>
/// ThermalPattern的JSON转换器
/// </summary>
public class ThermalPatternConverter : JsonConverter<ThermalPattern>
{
/// <summary>
/// 读取ThermalPattern的JSON数据
/// </summary>
/// <param name="reader">JSON读取器</param>
/// <param name="typeToConvert">目标类型</param>
/// <param name="options">JSON序列化选项</param>
/// <returns>解析后的ThermalPattern对象</returns>
public override ThermalPattern Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
// 辅助方法:将 List<List<double>> 转换为 double[,]
private double[,] ConvertSourceToGrid(List<List<double>> source, string sourceNameForErrorMessage)
{
if (reader.TokenType != JsonTokenType.StartObject)
if (source == null)
{
throw new JsonException("Expected StartObject token");
throw new InvalidOperationException($"ThermalPattern source data ('{sourceNameForErrorMessage}') is null. TOML data might be missing or invalid.");
}
double[,] staticPattern = new double[ThermalPattern.GRID_SIZE, ThermalPattern.GRID_SIZE];
double[,] movingPattern = new double[ThermalPattern.GRID_SIZE, ThermalPattern.GRID_SIZE];
bool hasStatic = false;
bool hasMoving = false;
while (reader.Read())
if (source.Count != GRID_SIZE)
{
if (reader.TokenType == JsonTokenType.EndObject)
{
break;
}
if (reader.TokenType != JsonTokenType.PropertyName)
{
throw new JsonException("Expected PropertyName token");
}
string propertyName = reader.GetString()!;
reader.Read(); // Move to the value
switch (propertyName.ToLower())
{
case "static":
ReadMatrix(ref reader, staticPattern);
hasStatic = true;
break;
case "moving":
ReadMatrix(ref reader, movingPattern);
hasMoving = true;
break;
default:
reader.Skip(); // Skip description or other properties
break;
}
throw new InvalidOperationException($"ThermalPattern source data ('{sourceNameForErrorMessage}') must have {GRID_SIZE} rows, but found {source.Count}.");
}
if (!hasStatic || !hasMoving)
var grid = new double[GRID_SIZE, GRID_SIZE];
for (int i = 0; i < GRID_SIZE; i++)
{
throw new JsonException("Missing required static or moving pattern");
if (source[i] == null || source[i].Count != GRID_SIZE)
{
throw new InvalidOperationException($"ThermalPattern source data ('{sourceNameForErrorMessage}') row {i} must have {GRID_SIZE} columns, but found {(source[i] == null ? "null" : source[i].Count.ToString())}.");
}
for (int j = 0; j < GRID_SIZE; j++)
{
grid[i, j] = source[i][j];
}
}
return new ThermalPattern(staticPattern, movingPattern);
return grid;
}
private static void ReadMatrix(ref Utf8JsonReader reader, double[,] matrix)
// 辅助方法:将 double[,] 转换为 List<List<double>>
private List<List<double>> ConvertGridToSource(double[,] grid, string gridNameForErrorMessage)
{
if (reader.TokenType != JsonTokenType.StartArray)
if (grid == null)
{
throw new JsonException("Expected StartArray token for matrix");
throw new ArgumentNullException(gridNameForErrorMessage);
}
if (grid.GetLength(0) != GRID_SIZE || grid.GetLength(1) != GRID_SIZE)
{
throw new ArgumentException($"Input grid ('{gridNameForErrorMessage}') for ThermalPattern must be {GRID_SIZE}x{GRID_SIZE}.", gridNameForErrorMessage);
}
for (int i = 0; i < ThermalPattern.GRID_SIZE; i++)
var source = new List<List<double>>(GRID_SIZE);
for(int i=0; i < GRID_SIZE; i++)
{
reader.Read(); // Move to start of row array
if (reader.TokenType != JsonTokenType.StartArray)
var row = new List<double>(GRID_SIZE);
for(int j=0; j < GRID_SIZE; j++)
{
throw new JsonException($"Expected StartArray token for row {i}");
}
for (int j = 0; j < ThermalPattern.GRID_SIZE; j++)
{
reader.Read(); // Move to number
if (reader.TokenType != JsonTokenType.Number)
{
throw new JsonException($"Expected Number token at position [{i},{j}]");
}
matrix[i, j] = reader.GetDouble();
}
reader.Read(); // Move to end of row array
if (reader.TokenType != JsonTokenType.EndArray)
{
throw new JsonException($"Expected EndArray token for row {i}");
row.Add(grid[i,j]);
}
source.Add(row);
}
reader.Read(); // Move to end of matrix array
if (reader.TokenType != JsonTokenType.EndArray)
{
throw new JsonException("Expected EndArray token for matrix");
}
}
/// <summary>
/// 将ThermalPattern对象序列化为JSON字符串
/// </summary>
/// <param name="writer">JSON写入器</param>
/// <param name="value">要序列化的ThermalPattern对象</param>
/// <param name="options">JSON序列化选项</param>
public override void Write(Utf8JsonWriter writer, ThermalPattern value, JsonSerializerOptions options)
{
writer.WriteStartObject();
writer.WritePropertyName("description");
writer.WriteStringValue("3x3 matrix representing side view temperature distribution (°C)");
writer.WritePropertyName("static");
WriteMatrix(writer, value.StaticPattern);
writer.WritePropertyName("moving");
WriteMatrix(writer, value.MovingPattern);
writer.WriteEndObject();
}
private static void WriteMatrix(Utf8JsonWriter writer, double[,] matrix)
{
writer.WriteStartArray();
for (int i = 0; i < ThermalPattern.GRID_SIZE; i++)
{
writer.WriteStartArray();
for (int j = 0; j < ThermalPattern.GRID_SIZE; j++)
{
writer.WriteNumberValue(matrix[i, j]);
}
writer.WriteEndArray();
}
writer.WriteEndArray();
return source;
}
}
}

View File

@ -75,13 +75,30 @@ namespace ThreatSource.Jammer
/// </summary>
protected override void UpdateJamming(double deltaTime)
{
var weather = SimulationManager?.CurrentWeather;
if (weather != null && IsActive && CurrentParameters != null)
// 首先检查 IsActive 和 CurrentParameters确保后续操作的有效性
// IsActive 会在 Deactivate() 中被设为 false。如果已非激活则不应再更新。
if (!IsActive || CurrentParameters == null)
{
return;
}
_elapsedTime += deltaTime;
var weather = SimulationManager?.CurrentWeather; // 获取天气可能为null
// 检查是否达到或超过总有效时间
if (_elapsedTime >= config.Duration)
{
CurrentParameters.SmokeConcentration = 0.0; // 明确设置浓度为0
// Deactivate 会处理 IsActive = false, IsJamming = false, 和发布 JammingStoppedEvent
Deactivate();
return; // 已停用,不再进行后续处理
}
// --- 如果烟幕仍在有效期内 ---
// 1. 处理风力导致的烟幕位置移动
if (weather != null)
{
// 更新累计时间
_elapsedTime += deltaTime;
// 风力移动部分
double windSpeed = weather.WindSpeed;
double windDirectionDeg = weather.WindDirection;
double windDirectionRad = windDirectionDeg * Math.PI / 180.0;
@ -91,40 +108,38 @@ namespace ThreatSource.Jammer
0,
Math.Cos(windDirectionRad)
);
// 烟雾位置随风移动
KState.Position += windVector * windSpeed * deltaTime;
// 计算浓度衰减
double decayRate = Math.Log(2) / config.Duration;
CurrentParameters.SmokeConcentration *= Math.Exp(-decayRate * deltaTime);
// 计算扩散
double expansionAmount = config.ExpansionRate * deltaTime;
CurrentParameters.SmokeThickness = config.Thickness + expansionAmount;
if (config.SmokeType == SmokeScreenType.Cloud)
{
CurrentParameters.SmokeDiameter = config.CloudDiameter + expansionAmount;
CurrentParameters.SmokeWallWidth = null;
CurrentParameters.SmokeWallHeight = null;
}
else // Wall
{
CurrentParameters.SmokeWallWidth = config.WallWidth + expansionAmount;
CurrentParameters.SmokeWallHeight = config.WallHeight + expansionAmount;
CurrentParameters.SmokeDiameter = null;
}
// 发布烟幕状态更新事件
PublishJammingEvent(CurrentParameters);
// 检查是否需要停止烟幕效果
if (_elapsedTime >= config.Duration ||
CurrentParameters.SmokeConcentration < config.Concentration * 0.1)
{
Deactivate();
}
CurrentParameters.SourcePosition = KState.Position; // 更新参数中的源位置
}
// 2. 线性衰减浓度
// config.Concentration 被视作初始浓度。
double initialConcentration = config.Concentration;
// 计算当前时间占总持续时间的比例
double timeRatio = _elapsedTime / config.Duration;
// 浓度从 initialConcentration 线性衰减到 0
CurrentParameters.SmokeConcentration = initialConcentration * Math.Max(0.0, 1.0 - timeRatio);
// 3. 更新烟幕尺寸(扩散)
// 扩散应该是从初始尺寸开始,基于已消耗时间的总扩散量
double totalExpansionSinceFormation = config.ExpansionRate * _elapsedTime;
// (假设FormationDelay不影响此处的_elapsedTime计算或者_elapsedTime是从形成后开始计时的)
// 如果config.ExpansionRate本身是0则尺寸不变。
CurrentParameters.SmokeThickness = config.Thickness + totalExpansionSinceFormation;
if (config.SmokeType == SmokeScreenType.Cloud)
{
CurrentParameters.SmokeDiameter = config.CloudDiameter + totalExpansionSinceFormation;
}
else // Wall
{
CurrentParameters.SmokeWallWidth = config.WallWidth + totalExpansionSinceFormation;
CurrentParameters.SmokeWallHeight = config.WallHeight + totalExpansionSinceFormation;
}
// 4. 发布当前的干扰事件 (包含更新后的位置、浓度、尺寸)
PublishJammingEvent(CurrentParameters);
}
/// <summary>

View File

@ -1 +1 @@
0.2.16
0.2.17

View File

@ -193,7 +193,7 @@ namespace ThreatSource.Tools.MissileSimulation
{
Position = new Vector3D(0, 1.2, 0),
Orientation = new Orientation(0.0, 0.0, 0.0),
Speed = 0.0
Speed = 1.0
};
string targetId = "Tank_1";
var target = _threatSourceFactory.CreateTarget(targetId, "mbt_001", motionParameters);