ThreatSourceLibaray/docs/examples/Integration/SimulinkExample.cs

599 lines
18 KiB
C#
Raw Permalink Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

#if NEVER // 使用编译指令确保此文件永远不会被编译
// Matlab/Simulink集成示例代码 - .NET Assembly直接调用方式
//
// 【适用场景】
// - Matlab R2019b或更高版本
// - 需要在Simulink模型中集成威胁源仿真
// - 实时仿真数据交换和时间同步
//
// 【前置条件】
// 1. 将 ThreatSource.dll 放入 Matlab 路径或指定目录
// 2. 将 data/ 目录复制到 Matlab 工作目录下
// 3. Matlab版本支持 .NET 8.0
//
// 展示如何将Matlab/Simulink与ThreatSource仿真系统集成
// 需要实现的核心功能: .NET Assembly加载、数据交换、时间同步
using ThreatSource.Simulation;
using ThreatSource.Data;
using ThreatSource.Missile;
using ThreatSource.Equipment;
using ThreatSource.Utils;
using System;
using System.Collections.Generic;
/// <summary>
/// Matlab/Simulink适配器类演示如何将威胁源库集成到Matlab/Simulink中
/// </summary>
/// <remarks>
/// 该类提供以下功能:
/// - .NET Assembly方式的Matlab集成
/// - 简化的API接口便于Matlab调用
/// - 实时数据交换和状态同步
/// - 事件处理和回调机制
/// - 与Simulink时间步长的协调
/// 本示例代码作为集成参考,可根据具体需求进行修改
/// </remarks>
public class MatlabSimulinkAdapter
{
#region
/// <summary>
/// 仿真管理器实例
/// </summary>
private ISimulationManager _simulationManager;
/// <summary>
/// 数据管理器实例
/// </summary>
private ThreatSourceDataManager _dataManager;
/// <summary>
/// Matlab创建的实体映射
/// </summary>
private Dictionary<string, object> _matlabEntities = new Dictionary<string, object>();
/// <summary>
/// 当前仿真时间
/// </summary>
private double _currentTime = 0.0;
/// <summary>
/// 仿真时间步长
/// </summary>
private double _timeStep = 0.01;
/// <summary>
/// 是否已初始化
/// </summary>
private bool _isInitialized = false;
#endregion
#region
/// <summary>
/// 初始化Matlab/Simulink适配器的新实例
/// </summary>
public MatlabSimulinkAdapter()
{
InitializeSimulation();
}
/// <summary>
/// 初始化仿真系统
/// </summary>
private void InitializeSimulation()
{
try
{
// 创建仿真管理器
_simulationManager = new SimulationManager();
// 创建数据管理器
_dataManager = new ThreatSourceDataManager();
Console.WriteLine("[MatlabAdapter] 威胁源仿真系统初始化完成");
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 初始化失败: {ex.Message}");
throw;
}
}
#endregion
#region Matlab公共接口
/// <summary>
/// 启动仿真系统
/// </summary>
/// <param name="timeStep">仿真时间步长(秒)</param>
/// <returns>启动是否成功</returns>
public bool StartSimulation(double timeStep = 0.01)
{
try
{
if (!_isInitialized)
{
_timeStep = timeStep;
_simulationManager.StartSimulation(timeStep);
_isInitialized = true;
Console.WriteLine($"[MatlabAdapter] 仿真已启动,时间步长: {timeStep}s");
}
return true;
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 启动仿真失败: {ex.Message}");
return false;
}
}
/// <summary>
/// 更新仿真状态在Simulink中每个时间步调用
/// </summary>
/// <param name="deltaTime">时间步长</param>
/// <returns>更新是否成功</returns>
public bool UpdateSimulation(double deltaTime)
{
try
{
if (!_isInitialized) return false;
_simulationManager.Update(deltaTime);
_currentTime += deltaTime;
return true;
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 仿真更新失败: {ex.Message}");
return false;
}
}
/// <summary>
/// 创建目标实体供Matlab调用
/// </summary>
/// <param name="entityId">实体ID</param>
/// <param name="posX">X坐标</param>
/// <param name="posY">Y坐标</param>
/// <param name="posZ">Z坐标</param>
/// <param name="velX">X方向速度</param>
/// <param name="velY">Y方向速度</param>
/// <param name="velZ">Z方向速度</param>
/// <returns>创建是否成功</returns>
public bool CreateTarget(string entityId, double posX, double posY, double posZ,
double velX, double velY, double velZ)
{
try
{
var targetPos = new Vector3D(posX, posY, posZ);
var targetVel = new Vector3D(velX, velY, velZ);
var tankInitialMotion = new KinematicState
{
Position = targetPos,
Orientation = new Orientation(0, 0, Math.Atan2(velY, velX)),
Speed = targetVel.Magnitude()
};
var tankProperties = new EquipmentProperties
{
InfraredRadiationIntensity = 10.0,
UltravioletRadiationIntensity = 10.0,
MillimeterWaveRadiationIntensity = 10.0
};
var tank = new Tank(entityId, tankProperties, tankInitialMotion, _simulationManager);
_simulationManager.RegisterEntity(entityId, tank);
_matlabEntities[entityId] = tank;
Console.WriteLine($"[MatlabAdapter] 成功创建目标: {entityId}");
return true;
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 创建目标失败: {ex.Message}");
return false;
}
}
/// <summary>
/// 创建红外成像制导导弹
/// </summary>
/// <param name="entityId">导弹ID</param>
/// <param name="posX">发射位置X</param>
/// <param name="posY">发射位置Y</param>
/// <param name="posZ">发射位置Z</param>
/// <param name="targetId">目标ID</param>
/// <returns>创建是否成功</returns>
public bool CreateIRMissile(string entityId, double posX, double posY, double posZ, string targetId)
{
try
{
var launchPos = new Vector3D(posX, posY, posZ);
var missileInitialMotion = new KinematicState
{
Position = launchPos,
Orientation = new Orientation(0, 0, 0),
Speed = 100
};
var properties = new MissileProperties
{
MaxSpeed = 1000,
MaxFlightTime = 100,
MaxFlightDistance = 10000,
MaxAcceleration = 50,
ProportionalNavigationCoefficient = 3,
Mass = 100,
ExplosionRadius = 10,
HitProbability = 0.9,
Type = MissileType.InfraredImagingTerminalGuidance
};
var guidanceConfig = new InfraredImagingGuidanceConfig
{
JammingResistanceThreshold = 1e-3
};
var missile = new InfraredImagingTerminalGuidanceMissile(
entityId, properties, missileInitialMotion, guidanceConfig, _simulationManager);
if (!string.IsNullOrEmpty(targetId))
{
missile.SetTarget(targetId);
}
_simulationManager.RegisterEntity(entityId, missile);
_matlabEntities[entityId] = missile;
Console.WriteLine($"[MatlabAdapter] 成功创建红外导弹: {entityId}");
return true;
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 创建红外导弹失败: {ex.Message}");
return false;
}
}
/// <summary>
/// 创建毫米波制导导弹
/// </summary>
/// <param name="entityId">导弹ID</param>
/// <param name="posX">发射位置X</param>
/// <param name="posY">发射位置Y</param>
/// <param name="posZ">发射位置Z</param>
/// <param name="targetId">目标ID</param>
/// <returns>创建是否成功</returns>
public bool CreateMMWMissile(string entityId, double posX, double posY, double posZ, string targetId)
{
try
{
var launchPos = new Vector3D(posX, posY, posZ);
var missileInitialMotion = new KinematicState
{
Position = launchPos,
Orientation = new Orientation(0, 0, 0),
Speed = 100
};
var properties = new MissileProperties
{
MaxSpeed = 1000,
MaxFlightTime = 100,
MaxFlightDistance = 10000,
MaxAcceleration = 50,
ProportionalNavigationCoefficient = 3,
Mass = 100,
ExplosionRadius = 10,
HitProbability = 0.9,
Type = MissileType.MillimeterWaveTerminalGuidance
};
var guidanceConfig = new MillimeterWaveGuidanceConfig
{
FieldOfViewAngle = 30,
TransmitPower = 0.5,
AntennaGainDB = 25,
WaveFrequency = 94e9
};
var missile = new MillimeterWaveTerminalGuidedMissile(
entityId, properties, missileInitialMotion, guidanceConfig, _simulationManager);
if (!string.IsNullOrEmpty(targetId))
{
missile.SetTarget(targetId);
}
_simulationManager.RegisterEntity(entityId, missile);
_matlabEntities[entityId] = missile;
Console.WriteLine($"[MatlabAdapter] 成功创建毫米波导弹: {entityId}");
return true;
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 创建毫米波导弹失败: {ex.Message}");
return false;
}
}
/// <summary>
/// 获取实体状态供Matlab调用
/// </summary>
/// <param name="entityId">实体ID</param>
/// <returns>状态数组 [x, y, z, vx, vy, vz, roll, pitch, yaw, isActive]</returns>
public double[] GetEntityState(string entityId)
{
try
{
var entity = _simulationManager.GetEntityById(entityId);
if (entity is ISimulationElement simElement)
{
return ConvertToMatlabStateArray(simElement);
}
return new double[10]; // 返回零数组
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 获取实体状态失败: {ex.Message}");
return new double[10];
}
}
/// <summary>
/// 设置实体位置供Matlab调用
/// </summary>
/// <param name="entityId">实体ID</param>
/// <param name="posX">X坐标</param>
/// <param name="posY">Y坐标</param>
/// <param name="posZ">Z坐标</param>
/// <returns>设置是否成功</returns>
public bool SetEntityPosition(string entityId, double posX, double posY, double posZ)
{
try
{
var entity = _simulationManager.GetEntityById(entityId);
if (entity is ISimulationElement simElement)
{
simElement.KState.Position = new Vector3D(posX, posY, posZ);
return true;
}
return false;
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 设置实体位置失败: {ex.Message}");
return false;
}
}
/// <summary>
/// 获取所有实体ID列表供Matlab调用
/// </summary>
/// <returns>实体ID字符串数组</returns>
public string[] GetAllEntityIds()
{
try
{
var allEntities = _simulationManager.GetAllEntities();
var entityIds = new List<string>();
foreach (var entity in allEntities)
{
if (entity is ISimulationElement simElement)
{
entityIds.Add(simElement.Id);
}
}
return entityIds.ToArray();
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 获取实体列表失败: {ex.Message}");
return new string[0];
}
}
/// <summary>
/// 停止仿真
/// </summary>
public void StopSimulation()
{
try
{
_simulationManager.StopSimulation();
_isInitialized = false;
_matlabEntities.Clear();
_currentTime = 0.0;
Console.WriteLine("[MatlabAdapter] 仿真已停止");
}
catch (Exception ex)
{
Console.WriteLine($"[MatlabAdapter] 停止仿真失败: {ex.Message}");
}
}
/// <summary>
/// 获取当前仿真时间
/// </summary>
/// <returns>当前仿真时间(秒)</returns>
public double GetCurrentTime()
{
return _currentTime;
}
/// <summary>
/// 检查实体是否存在
/// </summary>
/// <param name="entityId">实体ID</param>
/// <returns>实体是否存在</returns>
public bool EntityExists(string entityId)
{
var entity = _simulationManager.GetEntityById(entityId);
return entity != null;
}
#endregion
#region
/// <summary>
/// 将仿真元素转换为Matlab状态数组
/// </summary>
/// <param name="element">仿真元素</param>
/// <returns>状态数组 [x, y, z, vx, vy, vz, roll, pitch, yaw, isActive]</returns>
private double[] ConvertToMatlabStateArray(ISimulationElement element)
{
var pos = element.KState.Position;
var ori = element.KState.Orientation;
var speed = element.KState.Speed;
// 计算速度分量
var vx = speed * Math.Cos(ori.Yaw) * Math.Cos(ori.Pitch);
var vy = speed * Math.Sin(ori.Yaw) * Math.Cos(ori.Pitch);
var vz = speed * Math.Sin(ori.Pitch);
return new double[]
{
pos.X, pos.Y, pos.Z, // 位置 [0-2]
vx, vy, vz, // 速度 [3-5]
ori.Roll, ori.Pitch, ori.Yaw, // 姿态 [6-8]
element.IsActive ? 1.0 : 0.0 // 活动状态 [9]
};
}
#endregion
}
/// <summary>
/// Matlab/Simulink仿真示例类
/// </summary>
/// <remarks>
/// 该类演示了:
/// - Matlab/Simulink仿真系统的初始化
/// - 适配器的配置和使用
/// - 典型的导弹-目标仿真场景
/// 用于指导实际项目中的集成实现
/// </remarks>
public class MatlabSimulinkExample
{
private MatlabSimulinkAdapter _adapter;
/// <summary>
/// 初始化示例
/// </summary>
public void Initialize()
{
_adapter = new MatlabSimulinkAdapter();
Console.WriteLine("Matlab/Simulink ThreatSource集成示例初始化完成");
}
/// <summary>
/// 运行基本仿真示例
/// </summary>
public void RunBasicSimulationExample()
{
try
{
// 启动仿真系统
if (!_adapter.StartSimulation(0.01))
{
Console.WriteLine("仿真启动失败");
return;
}
// 创建目标
bool targetCreated = _adapter.CreateTarget(
"target_001",
5000, 0, 1000, // 位置: 5km距离1km高度
-50, 0, 0 // 速度: 50m/s向西移动
);
if (!targetCreated)
{
Console.WriteLine("目标创建失败");
return;
}
// 创建红外制导导弹
bool missileCreated = _adapter.CreateIRMissile(
"missile_001",
0, 0, 100, // 发射位置: 起始位置100m高度
"target_001" // 目标ID
);
if (missileCreated)
{
Console.WriteLine("基本仿真示例场景创建成功");
// 运行仿真步骤示例
for (int i = 0; i < 10; i++)
{
_adapter.UpdateSimulation(0.01);
// 获取导弹状态
var missileState = _adapter.GetEntityState("missile_001");
Console.WriteLine($"时间: {_adapter.GetCurrentTime():F2}s, 导弹位置: [{missileState[0]:F1}, {missileState[1]:F1}, {missileState[2]:F1}]");
// 在实际Simulink中这里会是Simulink的时间步进
System.Threading.Thread.Sleep(10);
}
}
else
{
Console.WriteLine("导弹创建失败");
}
}
catch (Exception ex)
{
Console.WriteLine($"运行仿真示例失败: {ex.Message}");
}
}
/// <summary>
/// 运行多导弹仿真示例
/// </summary>
public void RunMultiMissileExample()
{
try
{
// 启动仿真
_adapter.StartSimulation(0.01);
// 创建多个目标
_adapter.CreateTarget("target_001", 3000, 1000, 800, -30, -10, 0);
_adapter.CreateTarget("target_002", 4000, -500, 1200, -40, 20, 0);
// 创建不同类型的导弹
_adapter.CreateIRMissile("ir_missile_001", 0, 0, 100, "target_001");
_adapter.CreateMMWMissile("mmw_missile_001", 100, 0, 100, "target_002");
Console.WriteLine("多导弹仿真示例场景创建成功");
// 显示所有实体
var entityIds = _adapter.GetAllEntityIds();
Console.WriteLine($"仿真中共有 {entityIds.Length} 个实体:");
foreach (var id in entityIds)
{
Console.WriteLine($" - {id}");
}
}
catch (Exception ex)
{
Console.WriteLine($"运行多导弹示例失败: {ex.Message}");
}
}
/// <summary>
/// 清理资源
/// </summary>
public void Cleanup()
{
_adapter?.StopSimulation();
Console.WriteLine("Matlab/Simulink ThreatSource集成示例已清理");
}
}
#endif // 结束编译指令块