巴拉同学 2019-08-01 13:53 采纳率: 0%
浏览 1560

海康sdk 回调函数取帧,是否存在丢包

现象描述:
海康sdk 回调函数取帧,作检测人脸,是不是会出现一张断层的人脸照。
如下图:

图片说明

可能原因是什么?

调用函数为:NET_DVR_SetRealDataCallBack()

BOOL NET_DVR_SetRealDataCallBack(
LONG lRealHandle,
fRealDataCallBack cbRealDataCallBack,
DWORD dwUser
);

官方文档中提到这样几句话:

1、cbRealDataCallBack回调函数中不能执行可能会占用时间较长的接口或操作,不建议调用该SDK(HCNetSDK.dll)本身的接口。

2、此函数包括开始和停止用户处理SDK捕获的数据,当回调函数cbRealDataCallBack设为非NULL值时,表示回调和处理数据;当设为NULL时表示停止回调和处理数据。回调的第一个包是40个字节的文件头,供后续解码使用,之后回调的是压缩的码流。回调数据最大为256K字节。

官方也给出是实例代码:

#include <stdio.h>
#include <iostream>
#include <time.h>
#include "plaympeg4.h"
using namespace std;

LONG lPort; //全局的播放库port号

void CALLBACK g_RealDataCallBack_V30(LONG lRealHandle, DWORD dwDataType, BYTE *pBuffer,DWORD dwBufSize,DWORD dwUser)
{
    HWND hWnd = GetConsoleWindow();

    switch (dwDataType)
    {
    case NET_DVR_SYSHEAD: //系统头

        if (!PlayM4_GetPort(&lPort))  //获取播放库未使用的通道号
        {
            break;
        }
        //m_iPort = lPort; //第一次回调的是系统头,将获取的播放库port号赋值给全局port,下次回调数据时即使用此port号播放
        if (dwBufSize > 0)
        {
            if (!PlayM4_SetStreamOpenMode(lPort, STREAME_REALTIME))  //设置实时流播放模式
            {
                break;
            }

            if (!PlayM4_OpenStream(lPort, pBuffer, dwBufSize, 1024*1024)) //打开流接口
            {
                break;
            }

            if (!PlayM4_Play(lPort, hWnd)) //播放开始
            {
                break;
            }
        }
    case NET_DVR_STREAMDATA:   //码流数据
        if (dwBufSize > 0 && lPort != -1)
        {
            if (!PlayM4_InputData(lPort, pBuffer, dwBufSize))
            {
                break;
            } 
        }
    }
}

void CALLBACK g_ExceptionCallBack(DWORD dwType, LONG lUserID, LONG lHandle, void *pUser)
{
    char tempbuf[256] = {0};
    switch(dwType) 
    {
    case EXCEPTION_RECONNECT:    //预览时重连
    printf("----------reconnect--------%d\n", time(NULL));
    break;
    default:
    break;
    }
}

void main() {

  //---------------------------------------
  // 初始化
  NET_DVR_Init();

  //---------------------------------------
  // 注册设备
  LONG lUserID;
  NET_DVR_DEVICEINFO_V30 struDeviceInfo;
  lUserID = NET_DVR_Login_V30("172.0.0.100", 8000, "admin", "12345", &struDeviceInfo);
  if (lUserID < 0)
  {
       printf("Login error, %d\n", NET_DVR_GetLastError());
       NET_DVR_Cleanup();
       return;
  }

  //---------------------------------------
  //设置异常消息回调函数
  NET_DVR_SetExceptionCallBack_V30(0, NULL,g_ExceptionCallBack, NULL);

  //---------------------------------------
  //启动预览并设置回调数据流
  LONG lRealPlayHandle;
  NET_DVR_CLIENTINFO ClientInfo = {0};
  ClientInfo.hPlayWnd = NULL;         //需要SDK解码时句柄设为有效值,仅取流不解码时可设为空
  ClientInfo.lChannel     = 1;       //预览通道号
  ClientInfo.lLinkMode    = 0;       //最高位(31)为0表示主码流,为1表示子码流0~30位表示连接方式:0-TCP方式;1-UDP方式;2-多播方式;3-RTP方式;
  ClientInfo.sMultiCastIP = NULL;   //多播地址,需要多播预览时配置

  BOOL bPreviewBlock = false;       //请求码流过程是否阻塞,0:否,1:是
  lRealPlayHandle = NET_DVR_RealPlay_V30(lUserID, &ClientInfo, NULL, NULL, 0);

  if (lRealPlayHandle < 0)
  {
      printf("NET_DVR_RealPlay_V30 error\n");
      NET_DVR_Logout(lUserID);
      NET_DVR_Cleanup();
      return;
  }

  if (!NET_DVR_SetRealDataCallBack(lRealPlayHandle, g_RealDataCallBack_V30, 0))
  {
      printf("NET_DVR_SetRealDataCallBack error\n");
  }

  //---------------------------------------
  //关闭预览
  NET_DVR_StopRealPlay(lRealPlayHandle);
  //注销用户
  NET_DVR_Logout_V30(lUserID);
  NET_DVR_Cleanup();

  return;
}

  • 写回答

1条回答 默认 最新

  • CSDN-Ada助手 CSDN-AI 官方账号 2022-09-20 21:15
    关注
    不知道你这个问题是否已经解决, 如果还没有解决的话:

    如果你已经解决了该问题, 非常希望你能够分享一下解决方案, 写成博客, 将相关链接放在评论区, 以帮助更多的人 ^-^
    评论

报告相同问题?

悬赏问题

  • ¥50 有数据,怎么建立模型求影响全要素生产率的因素
  • ¥50 有数据,怎么用matlab求全要素生产率
  • ¥15 TI的insta-spin例程
  • ¥15 完成下列问题完成下列问题
  • ¥15 C#算法问题, 不知道怎么处理这个数据的转换
  • ¥15 YoloV5 第三方库的版本对照问题
  • ¥15 请完成下列相关问题!
  • ¥15 drone 推送镜像时候 purge: true 推送完毕后没有删除对应的镜像,手动拷贝到服务器执行结果正确在样才能让指令自动执行成功删除对应镜像,如何解决?
  • ¥15 求daily translation(DT)偏差订正方法的代码
  • ¥15 js调用html页面需要隐藏某个按钮