• C# 视频监控系列(12):H264播放器——播放录像文件


     

    前言

         本章主要实现播放海康录像文件,更多播放器说明可以参考《Hikvision H264播放器编程指南V4.8》。

     

    注意

         本系列文章限于学习交流,注重过程,由于涉及公司,所以不提供源代码下载,非常抱歉!!但是请大家放心,核心、实现以及其他能够贴出来的代码我都会贴出来,并且争取尽所能的回答留言里的每一个问题,感谢大家关注,欢迎交流 :)

    系列

         1.     C# 视频监控系列(1):准备

         2.     C# 视频监控系列(2):客户端——封装API

         3.     C# 视频监控系列(3):客户端——连接服务器

         4.     C# 视频监控系列(4):客户端——音频接收和抓图

         5.     C# 视频监控系列(5):客户端——给服务器端发送字符串和录像(数据捕获)

         6.     C# 视频监控系列(6):服务器端——封装API(上) [HikServer.dll]

         7.     C# 视频监控系列(7):服务器端——封装API(下) [DS40xxSDK.dll]

         8.     C# 视频监控系列(8):服务器端——预览和可被客户端连接

         9.     C# 视频监控系列(9):服务器端——数据捕获(抓图 + 录像)

         10.     C# 视频监控系列(10):服务器端——验证、设置画面质量、字幕叠加、板卡序列号

         11.     C# 视频监控系列(11):H264播放器——封装API[HikPlayM4.dll]

         12.     C# 视频监控系列(12):H264播放器——播放录像文件

     

    正文

         先来一张简单的效果图

         

         以下几个VC++ 代码片段:

              CPlayerDlg::OnInitDialog()

        Hik_PlayM4_SetVolume(PORT,m_SoundSlider.GetPos());

        
    // 其他代码

        
    //set the capture picture call back function;
        Hik_PlayM4_SetDisplayCallBack(PORT,DisplayCBFun);
        
    //set the wave audio call back funtion;
        Hik_PlayM4_SetAudioCallBack(PORT,WaveCBFun, (long)this);

        
    // 其他代码

        Hik_PlayM4_SetEncTypeChangeCallBack(PORT,funEncChange,(
    long)this);
    #if (WINVER > 0x0400)
        
    //If do not support multi monitor,may not call!
        Hik_PlayM4_InitDDrawDevice();
        Hik_PlayM4_SetDDrawDevice(PORT,
    0);
    #endif
        
    //Test adapter Capability;
        TestCapability(0);
        Hik_PlayM4_SetFileEndMsg(PORT,m_hWnd,WM_FILE_END);
        Hik_PlayM4_SetEncChangeMsg(PORT,m_hWnd,WM_ENC_CHANGE);
        
    if(m_strPlayFileName.Compare(""))
        {
            
    if(m_bStreamType)
                OpenStream();
            
    else
                OpenFile();
        }
      

              CPlayerDlg::OpenFile()

        Hik_PlayM4_SetFileRefCallBack(PORT,FileRefDone,(DWORD)this);
        Hik_PlayM4_SetVerifyCallBack(PORT, 
    00xffffffff, VerifyFun, (DWORD) this);// verify the whole file;
        if(!Hik_PlayM4_OpenFile(PORT,m_strPlayFileName.GetBuffer(m_strPlayFileName.GetLength())))
        {
            m_strPlayFileName
    ="";
            CString csError;
            csError.Format(
    "Open file failed(%d)",Hik_PlayM4_GetLastError(PORT));
            MessageBox(csError);
            
    return ;
        }
        SetOpenState();
        m_nMaxFileTime
    =Hik_PlayM4_GetFileTime(PORT);
        
    if(!m_nMaxFileTime)
        {
            MessageBox(
    "File seconds is zero");
            
    return;
        }
        m_nTotalHour
    =m_nMaxFileTime/3600;
        m_nTotalMinute
    =(m_nMaxFileTime%3600)/60;
        m_nTotalSecond
    =m_nMaxFileTime%60;
        m_nTotalFrames
    =Hik_PlayM4_GetFileTotalFrames(PORT);
        numFrames
    =m_nTotalFrames;
        
    //If you want to change the display buffer. Do hear!
        
    //Hik_PlayM4_SetDisplayBuf(PORT,25);
        Play();

              CPlayerDlg::Play()

        OnThrow0();
    //#ifdef _TEST_CALLBACK
        if(m_bConvert)       
           Hik_PlayM4_SetDecCallBack(PORT,DecCBFun);
        
    else
            m_pMainMenu
    ->EnableMenuItem(ID_FILE_CLOSE, FALSE);
    //#endif
        if(m_bPlaying)
        {
            Hik_PlayM4_Play(PORT,GetDlgItem(IDC_SHOW)
    ->m_hWnd);
        }
        
    else
        {
            
    if(m_bStreamType)
            {
                ::SetFilePointer(m_hStreamFile,m_nHeadSize,
    0,FILE_BEGIN);
                Hik_PlayM4_ResetSourceBuffer(PORT);
                SetEvent(m_hEventInput);
            }
            m_bPlaying 
    = Hik_PlayM4_Play(PORT,GetDlgItem(IDC_SHOW)->m_hWnd);
            m_bSound
    =Hik_PlayM4_PlaySound(PORT);
            
    if(m_bPlaying)
                SetTimer(PLAY_TIMER,
    500,NULL);
            
        }

              CPlayerDlg::SetOpenState()

        Hik_PlayM4_GetPictureSize(PORT,&m_nWidth,&m_nHeight);

        Hik_PlayM4_SetOverlayMode(PORT,TRUE,RGB(
    255,0,255));

              代码分析:

                   1.     从OnInitDialog部分代码可以看出主要是设置声音、判断是不是双击视频文件或者直接从流中读取数据。

                   2.     OpenFile和SetOpenState是打开文件、设置画面大小、显示统计信息,如总帧数、视频总时间。

                   3.     Play播放打开的视频文件。

                   4.     注意这里不讨论直接从流中读取数据并播放。

         

         以下是非完全对应的C# Code:

            //uesed port;can be from 0 to 15;
            int PORT = 0;
            
    //视频文件路径
            private string m_strPlayFileName;

            
    private void Form3_Load(object sender, EventArgs e)
            {
                
    //设置音量
                HikPlayer.Hik_PlayM4_SetVolume(PORT, 0xFFFF);

                HikPlayer.Hik_PlayM4_SetFileEndMsg(PORT, pVideo.Handle, HikPlayer.WM_FILE_END);

                HikPlayer.Hik_PlayM4_SetEncChangeMsg(PORT, pVideo.Handle, HikPlayer.WM_ENC_CHANGE);
            }

            
    /// <summary>
            
    /// 打开文件并播放
            
    /// </summary>
            
    /// <param name="sender"></param>
            
    /// <param name="e"></param>
            private void btnPlay_Click(object sender, EventArgs e)
            {
                
    if (openFileDialog1.ShowDialog() == DialogResult.OK)
                {
                    m_strPlayFileName 
    = openFileDialog1.FileName;
                    
    if (!string.IsNullOrEmpty(m_strPlayFileName))
                    {
                        OpenFile();
                        
    //设置画面质量
                        HikPlayer.Hik_PlayM4_SetPicQuality(PORT, true);
                    }
                    
    else
                        MessageBox.Show(
    "请选择文件!!");
                }
            }

            
    private void OpenFile()
            {
                
    //打开播放文件
                HikPlayer.Hik_PlayM4_OpenFile(PORT, m_strPlayFileName);

                Play();
            }

            
    public void SetOpenState()
            {
                
    //m_bOpen=TRUE;
                int m_nWidth, m_nHeight;
                
    //获取原始图像的大小,可根据这个自动设置播放器大小
                HikPlayer.Hik_PlayM4_GetPictureSize(PORT, out m_nWidth, out m_nHeight);
                HikPlayer.Hik_PlayM4_SetOverlayMode(PORT, 
    true, Color.FromArgb(2550255).ToArgb());
            }

            
    private void Play()
            {
                
    //开始播放
                HikPlayer.Hik_PlayM4_Play(PORT, pVideo.Handle);//this.Handle);  
                
    //播放声音
                HikPlayer.Hik_PlayM4_PlaySound(PORT);
            }

              代码说明:

                   1.     相对于VC++例子,这里省略了许多代码,比如空委托、显示统计信息等。

                   2.     如果文件打开出错,有可能是前面视频录像文件有问题,你可以先用自带的播放器试一下。

                   3.     建议补充错误处理。

     

    结束

         加油~~~快接近尾声了 : )

  • 相关阅读:
    关于ORA-04091异常的出现原因,以及解决方案
    <Interview problem>二进制加法
    Hadoop日志文件分析系统
    Android studio安装
    weex环境配置
    weex构建项目
    参数保存
    下拉搜索的小白demo
    angularJs中$http获取后台数据实例(搜集到的)
    前后台对接angularjs(搜集的)
  • 原文地址:https://www.cnblogs.com/over140/p/1419643.html
Copyright © 2020-2023  润新知