Camera Information System
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

166 lines
5.0 KiB

using Cis.Application.Core.Component.MarkSeacher;
using Cis.Application.Core.Component.PtzServer;
using EC.Helper.CameraSDK;
using FreeRedis;
using StackExchange.Profiling.Internal;
using System.Collections.Concurrent;
namespace Cis.Application.Core;
public class CameraDataCenter : ISingleton
{
2 years ago
#region Attr
private readonly RedisClient _cache;
private readonly CameraDataOptions _options;
private readonly ICameraSdkServer _cameraSdkServer;
private readonly IMarkSearcherServer _markSearcherServer;
2 years ago
/// <summary>
/// {cameraId, List(MarkLabelCalcResult)}
2 years ago
/// </summary>
private ConcurrentDictionary<long, List<MarkLabelCalcResult>> SearchResultListDict { get; set; } = new();
2 years ago
#endregion Attr
public CameraDataCenter(
RedisClient cache,
ICameraSdkServer cameraSdkServer,
IMarkSearcherServer markSearcherServer
)
2 years ago
{
_cache = cache;
_options = App.GetOptions<CameraDataOptions>();
_cameraSdkServer = cameraSdkServer;
_markSearcherServer = markSearcherServer;
InitThread();
2 years ago
}
#region Loop
private Thread RefreshCameraPtzThread { get; set; }
private Thread RefreshMarkSearcherThread { get; set; }
/// <summary>
/// 初始化线程
/// </summary>
private void InitThread()
2 years ago
{
// 初始化 CameraPtzThread
RefreshCameraPtzThread = new Thread(async () =>
2 years ago
{
while (true)
2 years ago
{
await RefreshCameraPtzInfos();
Thread.Sleep(_options.CameraPtz.LoopInterval);
2 years ago
}
})
{
IsBackground = true// 设置后台线程
};
// 启动 CameraPtzThread
RefreshCameraPtzThread.Start();
2 years ago
//// 初始化 MarkSearcherThread
//RefreshMarkSearcherThread = new Thread(async () =>
//{
// while (true)
// {
// await RefreshMarkSearchers();
// Thread.Sleep(_options.MarkSearcher.LoopInterval);
// }
//})
//{
// IsBackground = true// 设置后台线程
//};
//// 启动 MarkSearcherThread
//RefreshMarkSearcherThread.Start();
2 years ago
}
/// <summary>
/// 刷新所有相机 ptz
/// 有待改善,应设置超时计数机制
/// https://blog.csdn.net/qq_28368039/article/details/118597396
2 years ago
/// </summary>
private async Task RefreshCameraPtzInfos()
2 years ago
{
string[] cameraIpList = await _cache.HKeysAsync(CacheInfo.CameraIpCounts);
List<Task> tasks = new();
foreach (string cameraIp in cameraIpList)
2 years ago
{
tasks.Add(RefreshCameraPtzInfo(cameraIp));
2 years ago
}
await Task.WhenAny(Task.WhenAll(tasks), Task.Delay(_options.CameraPtz.Timeout));
2 years ago
}
/// <summary>
/// 刷新相机 ptz
/// </summary>
/// <param name="cameraIp"></param>
/// <returns></returns>
private async Task RefreshCameraPtzInfo(string cameraIp)
2 years ago
{
bool ret = _cameraSdkServer.TryGetPtzInfoByIp(cameraIp, out PtzInfo ptzInfo);
if (!ret) return;
await _cache.HSetAsync(CacheInfo.CameraPtzInfos, cameraIp, ptzInfo.ToJson());
2 years ago
}
/// <summary>
/// 刷新所有 markSearcher
2 years ago
/// </summary>
private async Task RefreshMarkSearchers()
2 years ago
{
string[] cameraIdList = await _cache.HKeysAsync(CacheInfo.CameraId2Ip);
List<Task> tasks = new();
foreach (string cameraId in cameraIdList)
2 years ago
{
tasks.Add(RefreshMarkSearcher(cameraId.ToLong()));
2 years ago
}
await Task.WhenAny(Task.WhenAll(tasks), Task.Delay(_options.CameraPtz.Timeout));
2 years ago
}
/// <summary>
/// 刷新 markSearcher
2 years ago
/// </summary>
/// <param name="cameraId"></param>
/// <returns></returns>
private async Task RefreshMarkSearcher(long cameraId)
2 years ago
{
MarkSearcherBase markSearcher = _markSearcherServer.GetSearcher(cameraId);
if (markSearcher == null) return;
string cameraIp = await _cache.HGetAsync(CacheInfo.CameraId2Ip, cameraId.ToString());
string ptzInfoStr = await _cache.HGetAsync(CacheInfo.CameraPtzInfos, cameraIp);
if (string.IsNullOrEmpty(ptzInfoStr)) return;
PtzInfo ptzInfo = ptzInfoStr.ToObject<PtzInfo>();
if (ptzInfo == null) return;
markSearcher.UpdateCameraCalcParams(ptzInfo);
List<MarkLabelCalcResult> resultList = await markSearcher.SearchAsync();
SearchResultListDict[cameraId] = resultList;
2 years ago
}
#endregion Loop
2 years ago
#region Base Method
2 years ago
public List<MarkLabelCalcResult> GetMarkLabelCalcResultList(long cameraId)
{
bool ret = SearchResultListDict.TryGetValue(cameraId, out List<MarkLabelCalcResult> resultList);
return ret ? resultList : new List<MarkLabelCalcResult>();
2 years ago
}
#endregion Base Method
2 years ago
#region Base Method Async
2 years ago
public async Task<List<MarkLabelCalcResult>> GetMarkLabelCalcResultListAsync(long cameraId)
{
return await Task.Run(() =>
{
return GetMarkLabelCalcResultList(cameraId);
});
}
#endregion Base Method Async
}