获取硬盘录像机参数及摄像头信息
获取硬盘录像机参数
命令参数
NET_DVR_GET_DEVICECFG_V40
结构体
NET_DVR_DEVICECFG_V40
//DVR设备参数
[StructLayoutAttribute(LayoutKind.Sequential)]
public struct NET_DVR_DEVICECFG_V40
{
public uint dwSize;
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = NAME_LEN, ArraySubType = UnmanagedType.I1)]
public byte[] sDVRName; //DVR名称
public uint dwDVRID; //DVR ID,用于遥控器 //V1.4(0-99), V1.5(0-255)
public uint dwRecycleRecord; //是否循环录像,0:不是; 1:是
//以下不可更改
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = SERIALNO_LEN, ArraySubType = UnmanagedType.I1)]
public byte[] sSerialNumber; //序列号
public uint dwSoftwareVersion; //软件版本号,高16位是主版本,低16位是次版本
public uint dwSoftwareBuildDate; //软件生成日期,0xYYYYMMDD
public uint dwDSPSoftwareVersion; //DSP软件版本,高16位是主版本,低16位是次版本
public uint dwDSPSoftwareBuildDate; // DSP软件生成日期,0xYYYYMMDD
public uint dwPanelVersion; // 前面板版本,高16位是主版本,低16位是次版本
public uint dwHardwareVersion; // 硬件版本,高16位是主版本,低16位是次版本
public byte byAlarmInPortNum; //DVR报警输入个数
public byte byAlarmOutPortNum; //DVR报警输出个数
public byte byRS232Num; //DVR 232串口个数
public byte byRS485Num; //DVR 485串口个数
public byte byNetworkPortNum; //网络口个数
public byte byDiskCtrlNum; //DVR 硬盘控制器个数
public byte byDiskNum; //DVR 硬盘个数
public byte byDVRType; //DVR类型, 1:DVR 2:ATM DVR 3:DVS ......
public byte byChanNum; //DVR 通道个数
public byte byStartChan; //起始通道号,例如DVS-1,DVR - 1
public byte byDecordChans; //DVR 解码路数
public byte byVGANum; //VGA口的个数
public byte byUSBNum; //USB口的个数
public byte byAuxoutNum; //辅口的个数
public byte byAudioNum; //语音口的个数
public byte byIPChanNum; //最大数字通道数 低8位,高8位见byHighIPChanNum
public byte byZeroChanNum; //零通道编码个数
public byte bySupport; //能力,位与结果为0表示不支持,1表示支持,
//bySupport & 0x1, 表示是否支持智能搜索
//bySupport & 0x2, 表示是否支持备份
//bySupport & 0x4, 表示是否支持压缩参数能力获取
//bySupport & 0x8, 表示是否支持多网卡
//bySupport & 0x10, 表示支持远程SADP
//bySupport & 0x20, 表示支持Raid卡功能
//bySupport & 0x40, 表示支持IPSAN搜索
//bySupport & 0x80, 表示支持rtp over rtsp
public byte byEsataUseage; //Esata的默认用途,0-默认备份,1-默认录像
public byte byIPCPlug; //0-关闭即插即用,1-打开即插即用
public byte byStorageMode; //0-盘组模式,1-磁盘配额, 2抽帧模式
public byte bySupport1; //能力,位与结果为0表示不支持,1表示支持
//bySupport1 & 0x1, 表示是否支持snmp v30
//bySupport1 & 0x2, 支持区分回放和下载
//bySupport1 & 0x4, 是否支持布防优先级
//bySupport1 & 0x8, 智能设备是否支持布防时间段扩展
//bySupport1 & 0x10, 表示是否支持多磁盘数(超过33个)
//bySupport1 & 0x20, 表示是否支持rtsp over http
public ushort wDevType;//设备型号
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = DEV_TYPE_NAME_LEN, ArraySubType = UnmanagedType.I1)]
public byte[] byDevTypeName;//设备型号名称
public byte bySupport2; //能力集扩展,位与结果为0表示不支持,1表示支持
//bySupport2 & 0x1, 表示是否支持扩展的OSD字符叠加(终端和抓拍机扩展区分)
public byte byAnalogAlarmInPortNum; //模拟报警输入个数
public byte byStartAlarmInNo; //模拟报警输入起始号
public byte byStartAlarmOutNo; //模拟报警输出起始号
public byte byStartIPAlarmInNo; //IP报警输入起始号 0-无效
public byte byStartIPAlarmOutNo; //IP报警输出起始号 0-无效
public byte byHighIPChanNum; //数字通道个数,高8位
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = 9, ArraySubType = UnmanagedType.I1)]
public byte[] byRes2; //保留
}
代码
Dictionary<String, string> pairs = new Dictionary<string, string>();
// 返回值
UInt32 dwReturn = 0;
// 获取结构体大小:public CHCNetSDK.NET_DVR_DEVICECFG_V40 StruDeviceCfg;为全局
Int32 nSize = Marshal.SizeOf(StruDeviceCfg);
// 开辟空间
IntPtr ptrDeviceCfg = Marshal.AllocHGlobal(nSize);
// 将结构体放入到内存空间中
Marshal.StructureToPtr(StruDeviceCfg, ptrDeviceCfg, false);
// 调用命令
if (!CHCNetSDK.NET_DVR_GetDVRConfig(lUserId, CHCNetSDK.NET_DVR_GET_DEVICECFG_V40, -1, ptrDeviceCfg, (UInt32)nSize, ref dwReturn))
{
// 如果获取错误,则获取错误信息
iLastErr = CHCNetSDK.NET_DVR_GetLastError();
_logerror.Error("NET_DVR_GET_DEVICECFG_V40 failed, error code= " + iLastErr);
}
else
{
// 将内存中的信息转换为NET_DVR_DEVICECFG_V40结构体
StruDeviceCfg = (CHCNetSDK.NET_DVR_DEVICECFG_V40)Marshal.PtrToStructure(ptrDeviceCfg, typeof(CHCNetSDK.NET_DVR_DEVICECFG_V40));
// 获取数值,具体参见结构体实例
pairs.Add("DevName", Encoding.GetEncoding("GBK").GetString(StruDeviceCfg.sDVRName).TrimEnd('\0'));
pairs.Add("DevType", Encoding.UTF8.GetString(StruDeviceCfg.byDevTypeName).TrimEnd('\0'));
pairs.Add("ANum", Convert.ToString(StruDeviceCfg.byChanNum));
pairs.Add("IPNum", Convert.ToString(StruDeviceCfg.byIPChanNum + 256 * StruDeviceCfg.byHighIPChanNum));
pairs.Add("ZeroNum", Convert.ToString(StruDeviceCfg.byZeroChanNum));
pairs.Add("NetNum", Convert.ToString(StruDeviceCfg.byNetworkPortNum));
pairs.Add("AlarmInNum", Convert.ToString(StruDeviceCfg.byAlarmInPortNum));
pairs.Add("AlarmOutNum", Convert.ToString(StruDeviceCfg.byAlarmOutPortNum));
pairs.Add("xDevSerial", Encoding.UTF8.GetString(StruDeviceCfg.sSerialNumber).TrimEnd('\0'));
}
// 将StruDeviceCfg设置为null
StruDeviceCfg = default;
// 清空内存
Marshal.FreeHGlobal(ptrDeviceCfg);
// 返回
return pairs;
获取硬盘录像机的摄像头信息
命令参数
CHCNetSDK.NET_DVR_GET_IPPARACFG_V40
结构体
CHCNetSDK.NET_DVR_IPPARACFG_V40
/* V40扩展IP接入配置结构 */
[StructLayoutAttribute(LayoutKind.Sequential)]
public struct NET_DVR_IPPARACFG_V40
{
public uint dwSize;/* 结构大小 */
public uint dwGroupNum;
public uint dwAChanNum;
public uint dwDChanNum;
public uint dwStartDChan;
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = MAX_CHANNUM_V30, ArraySubType = UnmanagedType.I1)]
public byte[] byAnalogChanEnable; /* 模拟通道是否启用,从低到高表示1-32通道,0表示无效 1有效 */
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = MAX_IP_DEVICE_V40, ArraySubType = UnmanagedType.Struct)]
public NET_DVR_IPDEVINFO_V31[] struIPDevInfo; /* IP设备 */
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = MAX_CHANNUM_V30, ArraySubType = UnmanagedType.Struct)]
public NET_DVR_STREAM_MODE[] struStreamMode;/* IP通道 */
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = 20, ArraySubType = UnmanagedType.I1)]
public byte[] byRes2; /* 模拟通道是否启用,从低到高表示1-32通道,0表示无效 1有效 */
}
NET_DVR_IPDEVINFO_V31
//ipc接入设备信息扩展,支持ip设备的域名添加
[StructLayoutAttribute(LayoutKind.Sequential)]
public struct NET_DVR_IPDEVINFO_V31
{
public byte byEnable;//该IP设备是否有效
public byte byProType;
public byte byEnableQuickAdd;
public byte byRes1;//保留字段,置0
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = NAME_LEN, ArraySubType = UnmanagedType.I1)]
public byte[] sUserName;//用户名
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = PASSWD_LEN, ArraySubType = UnmanagedType.I1)]
public byte[] sPassword;//密码
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = MAX_DOMAIN_NAME, ArraySubType = UnmanagedType.I1)]
public byte[] byDomain;//设备域名
public NET_DVR_IPADDR struIP;//IP地址
public ushort wDVRPort;// 端口号
[MarshalAsAttribute(UnmanagedType.ByValArray, SizeConst = 34, ArraySubType = UnmanagedType.I1)]
public byte[] byRes2;//保留字段,置0
public void Init()
{
sUserName = new byte[NAME_LEN];
sPassword = new byte[PASSWD_LEN];
byDomain = new byte[MAX_DOMAIN_NAME];
byRes2 = new byte[34];
}
}
代码
-
MonitorCamera类
public class MonitorCamera { // 摄像头名称 public string name { get; set; } // 摄像头ip地址 public string ip { get; set; } // 摄像头通道地址 public string channel { get; set; } }
-
dwAChanTotalNum变量及dwDChanTotalNum获取
摄像头数量
int lUserID = CHCNetSDK.NET_DVR_Login_V30(accessInfo.Ip地址, Int16.Parse(accessInfo.端口号), accessInfo.用户名, accessInfo.密码, ref DeviceInfo); if (lUserID >= 0) { dwAChanTotalNum = (uint)DeviceInfo.byChanNum; dwDChanTotalNum = (uint)DeviceInfo.byIPChanNum + 256 * (uint)DeviceInfo.byHighDChanNum; return ""; }
-
摄像头数组获得
List<MonitorCamera> cameras = new List<MonitorCamera>(); uint dwSize = (uint)Marshal.SizeOf(StruIpParaCfgV40); IntPtr ptrIpParaCfgV40 = Marshal.AllocHGlobal((Int32)dwSize); Marshal.StructureToPtr(StruIpParaCfgV40, ptrIpParaCfgV40, false); uint dwReturn = 0; //该Demo仅获取第一组64个通道,如果设备IP通道大于64路,需要按组号0~i多次调用NET_DVR_GET_IPPARACFG_V40获取 int iGroupNo = 0; // 调用海康命令 if (!CHCNetSDK.NET_DVR_GetDVRConfig(lUserID, CHCNetSDK.NET_DVR_GET_IPPARACFG_V40, iGroupNo, ptrIpParaCfgV40, dwSize, ref dwReturn)) { iLastErr = CHCNetSDK.NET_DVR_GetLastError(); _logerror.Error(String.Format("获得硬盘录像机通道号NET_DVR_GET_IPPARACFG_V40 failed, error code={0}", iLastErr)); } else { // 将内存信息转换为结构体 StruIpParaCfgV40 = (CHCNetSDK.NET_DVR_IPPARACFG_V40)Marshal.PtrToStructure(ptrIpParaCfgV40, typeof(CHCNetSDK.NET_DVR_IPPARACFG_V40)); int i; // 判断摄像头路数 for (i = 0; i < dwAChanTotalNum; i++) { // 获取摄像头ip地址 String strIp = System.Text.Encoding.Default.GetString(StruIpParaCfgV40.struIPDevInfo[i].struIP.sIpV4); int nIndex = strIp.IndexOf('\0'); // 判断是否存在ip地址 if (!String.IsNullOrEmpty(strIp) && strIp.IndexOf("0.0.0") == -1 && nIndex > 1) { //存在,则进行声明,存储数据 MonitorCamera monitor = GetCamera((i + (int)DeviceInfo.byStartChan).ToString(), strIp.Substring(0, nIndex)); if (GetCameraConfig(lUserID, (i + (int)DeviceInfo.byStartChan)).Length == 0 && StruPicCfgV40.sChanName != null) { // 获取摄像头名称 monitor.name = Encoding.GetEncoding("GBK").GetString(StruPicCfgV40.sChanName).TrimEnd('\0'); } cameras.Add(monitor); } } uint iDChanNum = 64; if (dwDChanTotalNum < 64) { iDChanNum = dwDChanTotalNum; //如果设备IP通道小于64路,按实际路数获取 } //和上面的循环一致,至于为什么会有两个路,感觉一个是按照路数来设定的,还有一个是按照ip来设定的,不仅仅是摄像头使用,可能还有其他设备也是用该代码 for (i = 0; i < iDChanNum; i++) { String strIp = Encoding.Default.GetString(StruIpParaCfgV40.struIPDevInfo[i].struIP.sIpV4); int nIndex = strIp.IndexOf('\0'); if (!String.IsNullOrEmpty(strIp) && strIp.IndexOf("0.0.0") == -1 && nIndex > 1) { MonitorCamera monitor = GetCamera((i + (int)StruIpParaCfgV40.dwStartDChan).ToString(), strIp.Substring(0, nIndex), ); // 获得的StruPicCfgV40为全局变量,如果成功则赋值 if (GetCameraConfig(lUserID, (i + (int)StruIpParaCfgV40.dwStartDChan)).Length == 0 && StruPicCfgV40.sChanName != null) { //获取通道名称,监控画面上现实的文字 monitor.name = Encoding.GetEncoding("GBK").GetString(StruPicCfgV40.sChanName).TrimEnd('\0'); } cameras.Add(monitor); } } StruIpParaCfgV40 = default; } Marshal.FreeHGlobal(ptrIpParaCfgV40); return cameras;
-
GetCamera代码实例
private MonitorCamera GetCamera(String channel, String ip) { MonitorCamera camera = new MonitorCamera { ip = ip, channel = channel }; return camera; }
-
GetCameraConfig代码实例
// 目的是获得StruPicCfgV40结构体 internal String GetCameraConfig(int lUserID, int lChannel) { UInt32 dwReturn = 0; Int32 nSize = Marshal.SizeOf(StruPicCfgV40); IntPtr getPtrPicCfg = Marshal.AllocHGlobal(nSize); Marshal.StructureToPtr(StruPicCfgV40, getPtrPicCfg, false); // 获得该通道的信息 if (!CHCNetSDK.NET_DVR_GetDVRConfig(lUserID, CHCNetSDK.NET_DVR_GET_PICCFG_V40, lChannel, getPtrPicCfg, (UInt32)nSize, ref dwReturn)) { _logerror.Error("NET_DVR_GET_PICCFG_V40 failed, error code= " + CHCNetSDK.NET_DVR_GetLastError()); Marshal.FreeHGlobal(getPtrPicCfg); return "获取信息失败"; } else { StruPicCfgV40 = (CHCNetSDK.NET_DVR_PICCFG_V40)Marshal.PtrToStructure(getPtrPicCfg, typeof(CHCNetSDK.NET_DVR_PICCFG_V40)); Marshal.FreeHGlobal(getPtrPicCfg); } return ""; }