天地伟业解码器二次开发/C#调用C++DLL

一:前言

  解码器是用来解码摄像头输出视频的。SDK是异步模式,很多功能都是依靠异步消息驱动。

        使用 Marshal.AllocHGlobal、Marshal.FreeHGlobal来分配、释放非托管内存;

   使用Marshal.StructureToPtr、Marshal.PtrToStructure来实现对结构体指针的操作;

二:SDK调用顺序  

  1. 初始化开发包(该SDK版本为Version4.0)

    int __stdcall Dec_ClientStartup(unsigned int_uiMessage, HWND _hWnd);

  2. 设置开发包需要的一些参数

    int __stdcall DEC_ClientSetNotify(DecNotifyFun* _pNotify);

  3. 调用开发包所提供的其他函数(连接摄像头预览视频、调整视频等功能函数)

  4. 释放开发包

    int __stdcall DEC_ClientCleanup(); 

三:二次开发

  1.初始化开发包

C++:

 

C#:

 //结构体写在namespace里,不是类里

 //OnParamChangeNotify和OnMainNotfy由系统(ParamChangeNotify/MainNotfy函数)调用,而不是由程序员调用

       2.登录解码器

    //注册登录函数,注意操作完毕后要记得注销,不然断电后将无法控制解码器

   

 //调用函数。执行完该函数后,会触发OnMainNotify主回调信息函数,可以在OnMainNotify函数里这么写

 

  //为了拿到登录状态(状态在非托管内存中),将信息放到托管的LogonStatus结构体里,使用Marshal.PtrToStructure完成

 

  //NetSDKMsg定义回调消息类型

  3:连接摄像头,解码器进行解码

   //联合体:需要联合体的哪一个结构体只需定义哪一个结构体,无需定义ServerItem 

 

 C#:

   //strServerPtzPortocol为动态链接库,和NVDSDK.dll一起放在bin包

   //结构体嵌套结构体

   //此函数ServerItem参数是一个结构体,具体传哪一种结构体视情况(NormalServer/OnvifServer/RtspServer/EncodeChannel)而定。

   //C#定义的NormalServer结构体里放入我们需要传入的数据(摄像头账号密码等信息)使用StructureToPtr将数据放入非托管内存中

  3:拼控(2 * 2)

 

    第一步:获取大屏的数量  tDev.iSplitChanNum  ,来自方法DEC_ClientGetDevConfig

    第二步:获取拼控其实编号 tOffset.iSplitScreen  ,来自方法DEC_ClientGetDevConfig,

        获取所有拼控大屏可以遍历 拼控起始编号+n  完成。

    第三步:创建大屏 DEC_ClientSetDevConfig

  // 获取支持的大屏数量,获取拼控的起始编号、开窗起始编号:执行DEC_ClientGetDevConfig后,Marshal.StructureToPtr用来将结构体从托管内存封送到非托管内存,

   Marshal.PtrToStructure用来将非托管内存块封送到新分配的托管对象,完成从非托管取数据

  //创建大屏,完成向非托管放数据。DEC_ClientSetDevConfig函数结束以后,将 2 * 2 = 4个通道合并成一个虚拟大屏通道

  

  //最后需要执行一次DEC_ClientStartView_V1函数,且将此函数的第二个参数改为拼控起始编号,执行完发现值其实为10000(S5解码器为16),我这里写死。到这里完成拼控

原文地址:https://www.cnblogs.com/HansZimmer/p/10323300.html