2025-12-26 03:18:21 +08:00
|
|
|
|
using Microsoft.AspNetCore.Builder;
|
|
|
|
|
|
using Microsoft.Extensions.DependencyInjection;
|
2025-12-26 16:58:12 +08:00
|
|
|
|
using Microsoft.Extensions.Logging;
|
2025-12-26 03:18:21 +08:00
|
|
|
|
using Microsoft.OpenApi.Models;
|
|
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
namespace SHH.CameraSdk;
|
|
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
|
|
|
/// A 方案:标准控制台结构 (动态窗口版)
|
|
|
|
|
|
/// </summary>
|
|
|
|
|
|
public class Program
|
2025-12-26 03:18:21 +08:00
|
|
|
|
{
|
2025-12-26 17:28:07 +08:00
|
|
|
|
[STAThread]
|
|
|
|
|
|
public static async Task Main(string[] args)
|
2025-12-26 03:18:21 +08:00
|
|
|
|
{
|
2025-12-26 17:28:07 +08:00
|
|
|
|
// ==============================================================================
|
|
|
|
|
|
// 1. 基础设施初始化
|
|
|
|
|
|
// ==============================================================================
|
|
|
|
|
|
InitHardwareEnv();
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
// 核心设备管理器
|
|
|
|
|
|
using var cameraManager = new CameraManager();
|
|
|
|
|
|
|
|
|
|
|
|
// [新增] 动态窗口管理器 (不再直接 new FrameConsumer)
|
|
|
|
|
|
// 这是一个单例服务,负责在运行期间管理所有弹出的窗口
|
|
|
|
|
|
var displayManager = new DisplayWindowManager();
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 06:14:55 +08:00
|
|
|
|
// ==============================================================================
|
2025-12-26 17:28:07 +08:00
|
|
|
|
// 2. 启动 Web 监控与诊断服务 (注入两个管理器)
|
2025-12-26 06:14:55 +08:00
|
|
|
|
// ==============================================================================
|
2025-12-26 17:28:07 +08:00
|
|
|
|
var app = await StartWebMonitoring(cameraManager, displayManager);
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
// 启动网络哨兵 (后台 Ping)
|
|
|
|
|
|
var sentinel = new ConnectivitySentinel(cameraManager);
|
|
|
|
|
|
|
|
|
|
|
|
// ==============================================================================
|
|
|
|
|
|
// 3. 业务编排:仅配置设备,不配置窗口
|
|
|
|
|
|
// ==============================================================================
|
|
|
|
|
|
await ConfigureBusinessLogic(cameraManager);
|
|
|
|
|
|
|
|
|
|
|
|
// ==============================================================================
|
|
|
|
|
|
// 4. 启动引擎与交互
|
|
|
|
|
|
// ==============================================================================
|
|
|
|
|
|
Console.WriteLine("\n[系统] 正在启动全局管理引擎...");
|
|
|
|
|
|
await cameraManager.StartAsync();
|
|
|
|
|
|
|
|
|
|
|
|
Console.WriteLine(">> 系统就绪。");
|
|
|
|
|
|
Console.WriteLine(">>当前无播放窗口。请通过 Web 界面 '新增订阅' -> 模式选 'UI_Preview' 来动态打开。");
|
|
|
|
|
|
Console.WriteLine(">> 按 'S' 键退出...");
|
|
|
|
|
|
|
|
|
|
|
|
// 阻塞主线程,保持程序运行
|
|
|
|
|
|
while (Console.ReadKey(true).Key != ConsoleKey.S)
|
2025-12-26 06:14:55 +08:00
|
|
|
|
{
|
2025-12-26 17:28:07 +08:00
|
|
|
|
Thread.Sleep(100);
|
2025-12-26 06:14:55 +08:00
|
|
|
|
}
|
|
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
Console.WriteLine("[系统] 正在停机...");
|
|
|
|
|
|
await app.StopAsync();
|
|
|
|
|
|
}
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
// ==============================================================================
|
|
|
|
|
|
// Static Methods
|
|
|
|
|
|
// ==============================================================================
|
2025-12-26 16:58:12 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
static void InitHardwareEnv()
|
|
|
|
|
|
{
|
|
|
|
|
|
Console.WriteLine("=== 工业级视频 SDK 架构测试 (V3.3 动态窗口版) ===");
|
|
|
|
|
|
Console.WriteLine("[硬件] 海康驱动预热中...");
|
|
|
|
|
|
HikNativeMethods.NET_DVR_Init();
|
|
|
|
|
|
HikSdkManager.ForceWarmUp();
|
|
|
|
|
|
Console.WriteLine("[硬件] 预热完成。");
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// [修改] 签名增加 DisplayWindowManager 参数
|
|
|
|
|
|
static async Task<WebApplication> StartWebMonitoring(CameraManager manager, DisplayWindowManager displayMgr)
|
|
|
|
|
|
{
|
|
|
|
|
|
var builder = WebApplication.CreateBuilder();
|
|
|
|
|
|
|
|
|
|
|
|
builder.Services.AddCors(options =>
|
|
|
|
|
|
{
|
|
|
|
|
|
options.AddPolicy("AllowAll", policy =>
|
2025-12-26 06:14:55 +08:00
|
|
|
|
{
|
2025-12-26 17:28:07 +08:00
|
|
|
|
policy.AllowAnyOrigin()
|
|
|
|
|
|
.AllowAnyHeader()
|
|
|
|
|
|
.AllowAnyMethod();
|
2025-12-26 06:14:55 +08:00
|
|
|
|
});
|
2025-12-26 17:28:07 +08:00
|
|
|
|
});
|
|
|
|
|
|
|
|
|
|
|
|
// 日志屏蔽
|
|
|
|
|
|
builder.Logging.AddFilter("Microsoft", LogLevel.Warning);
|
|
|
|
|
|
builder.Logging.AddFilter("System", LogLevel.Warning);
|
|
|
|
|
|
builder.Logging.AddFilter("Microsoft.AspNetCore.Hosting.Diagnostics", LogLevel.Warning);
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
builder.Services.AddControllers();
|
|
|
|
|
|
builder.Services.AddEndpointsApiExplorer();
|
|
|
|
|
|
builder.Services.AddSwaggerGen(c =>
|
|
|
|
|
|
{
|
|
|
|
|
|
c.SwaggerDoc("v1", new OpenApiInfo { Title = "SHH Camera Diagnostics", Version = "v1" });
|
|
|
|
|
|
});
|
|
|
|
|
|
builder.Services.AddCors(o => o.AddPolicy("AllowAll", p => p.AllowAnyOrigin().AllowAnyMethod().AllowAnyHeader()));
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
// [关键] 注入两个单例服务,让 Controller 能调用它们
|
|
|
|
|
|
builder.Services.AddSingleton(manager);
|
|
|
|
|
|
builder.Services.AddSingleton(displayMgr);
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
var webApp = builder.Build();
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
webApp.UseSwagger();
|
|
|
|
|
|
webApp.UseSwaggerUI(c => c.SwaggerEndpoint("/swagger/v1/swagger.json", "Diagnostics V1"));
|
|
|
|
|
|
webApp.UseCors("AllowAll");
|
|
|
|
|
|
webApp.MapControllers();
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
_ = webApp.RunAsync("http://0.0.0.0:5000");
|
|
|
|
|
|
Console.WriteLine("[Web] 监控API已启动: http://localhost:5000");
|
2025-12-26 03:18:21 +08:00
|
|
|
|
|
2025-12-26 17:28:07 +08:00
|
|
|
|
return webApp;
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
// [修改] 移除 FrameConsumer 参数,不再进行硬编码订阅
|
|
|
|
|
|
static async Task ConfigureBusinessLogic(CameraManager manager)
|
|
|
|
|
|
{
|
|
|
|
|
|
// 1. 仅添加设备配置
|
|
|
|
|
|
var config = new VideoSourceConfig
|
2025-12-26 03:18:21 +08:00
|
|
|
|
{
|
2025-12-26 17:28:07 +08:00
|
|
|
|
Id = 101,
|
|
|
|
|
|
Brand = DeviceBrand.HikVision,
|
|
|
|
|
|
IpAddress = "172.16.41.206",
|
|
|
|
|
|
Port = 8000,
|
|
|
|
|
|
Username = "admin",
|
|
|
|
|
|
Password = "abcd1234",
|
|
|
|
|
|
StreamType = 0
|
|
|
|
|
|
};
|
|
|
|
|
|
manager.AddDevice(config);
|
|
|
|
|
|
|
|
|
|
|
|
var config2 = new VideoSourceConfig
|
|
|
|
|
|
{
|
|
|
|
|
|
Id = 102,
|
|
|
|
|
|
Brand = DeviceBrand.HikVision,
|
|
|
|
|
|
IpAddress = "172.16.41.20",
|
|
|
|
|
|
Port = 8000,
|
|
|
|
|
|
Username = "admin",
|
|
|
|
|
|
Password = "abcd1234",
|
|
|
|
|
|
StreamType = 0
|
|
|
|
|
|
};
|
|
|
|
|
|
manager.AddDevice(config2);
|
|
|
|
|
|
|
|
|
|
|
|
// 注意:此处不再调用 Register 或 Subscribe
|
|
|
|
|
|
// 所有的播放请求都将由 WebAPI 收到前端指令后,调用 DisplayWindowManager 来动态发起
|
2025-12-26 03:18:21 +08:00
|
|
|
|
}
|
|
|
|
|
|
}
|