• 753阅读
  • 0回复

Qt音视频开发36-超时检测和自动重连的设计 [复制链接]

上一主题 下一主题
离线liudianwu
 

只看楼主 倒序阅读 楼主  发表于: 2023-04-10


## 一、前言
如果网络环境正常设备正常,视频监控系统一般都是按照正常运行下去,不会出现什么问题,但是实际情况会很不同,奇奇怪怪七七八八的问题都会出现,就比如网络出了问题都有很多情况(交换机故障、网线故障、带宽故障等),所以监控系统在运行过程中,还得做超时检测,超过规定的时间没有收到数据则认为掉线了,需要重连,超时检测有两个地方需要,一个是打开的时候,因为受限于网络等,默认超时时间是30s太久,在打开之前,可以做个简单的连接探测是否地址通,不通就不用继续;另一个地方就是实时采集过程中,也要能够及时识别到,防止一直在那边死循环的读取。

在上面超过检测后,一般都是更新最后的收到数据的时间,然后自动重连的机制就是在线程中判断这个最后接收数据的时间和当前时间比较,超过了设定的超时时间,则认为掉线,关闭视频,如果还设置了自动重连属性,则先关闭再去重新打开,务必记得关闭的时候及时释放所有的资源,不然内存会一直增长。封装后的视频流控件自带了自动重连的机制,这样用户再使用的时候不用管如何重连,只需要开启自动重连属性即可,默认开,还有一种情况可能要关闭自动重连属性,比如播放本地视频文件,有时候只需要播放一次就行,不需要播放完成以后又重新播放,如果确实需要,则关联播放完毕信号自行重新open即可。

## 二、效果图



## 三、体验地址
1. 国内站点:[https://gitee.com/feiyangqingyun](https://gitee.com/feiyangqingyun)
2. 国际站点:[https://github.com/feiyangqingyun](https://github.com/feiyangqingyun)
3. 个人作品:[https://blog.csdn.net/feiyangqingyun/article/details/97565652](https://blog.csdn.net/feiyangqingyun/article/details/97565652)
4. 体验地址:[https://pan.baidu.com/s/1d7TH_GEYl5nOecuNlWJJ7g](https://pan.baidu.com/s/1d7TH_GEYl5nOecuNlWJJ7g) 提取码:01jf 文件名:bin_video_demo/bin_linux_video。

## 四、相关代码
```cpp
void VideoThread::checkOpen()
{
    //特意每次做个小延时每次都去判断标志位等可以大大加快关闭速度
    int count = 0;
    int maxCount = openSleepTime / 100;
    while (!stopped) {
        msleep(100);
        count++;
        //测试下来正常情况下基本上等待一次后 isOk=true
        if (count == maxCount || isOk) {
            break;
        }
    }
}

void VideoThread::run()
{
    while (!stopped) {
        if (!isOk) {
            this->closeVideo();
            if (videoMode == VideoMode_Hwnd) {
                QMetaObject::invokeMethod(this, "openVideo");
            } else {
                this->openVideo();
            }

            this->checkOpen();
            continue;
        }

        if (videoCore == VideoCore_Vlc) {
            if (videoWidth <= 0 && !getOnlyAudio()) {
                //视频文件需要尝试读取媒体信息多次保证能够读取到(一般视频流需要多次才能读取到)
                this->readMediaInfo();
            }
        } else if (videoCore == VideoCore_HaiKang) {
            if (videoType == VideoType_FileLocal) {
                //本地文件需要这里实时读取播放进度
                this->getPosition();
            } else if (isOk && videoMode == VideoMode_Hwnd) {
                //句柄模式下视频流如果打开正常了则sdk内部处理重连
                lastTime = QDateTime::currentDateTime();
            }
        } else if (videoCore == VideoCore_EasyPlayer) {
            if (videoWidth <= 0) {
                this->readMediaInfo();
            }

            this->getPosition();
        }

        //启用了自动重连则通过判断最后的消息时间(超时则重新打开)
        if (readTimeout > 0) {
            qint64 offset = lastTime.msecsTo(QDateTime::currentDateTime());
            if (offset >= readTimeout) {
                isOk = false;
                debug("超时重连", "");
                continue;
            }
        }

        msleep(100);
    }

    //关闭视频
    this->closeVideo();

    //文件名为空才说明真正处理完可以彻底结束线程(否则一直等因为有可能文件还没保存完成)
    while (!fileName.isEmpty()) {
        debug("等待完成", "");
        msleep(5);
    }

    debug("线程结束", "");
}
```

4条评分好评度+1贡献值+1金钱+10威望+1
20091001753 好评度 +1 - 2023-04-10
20091001753 贡献值 +1 - 2023-04-10
20091001753 威望 +1 - 2023-04-10
20091001753 金钱 +10 - 2023-04-10
欢迎关注微信公众号:Qt实战/Qt入门和进阶(各种开源作品、经验整理、项目实战技巧,专注Qt/C++软件开发,视频监控、物联网、工业控制、嵌入式软件、国产化系统应用软件开发) QQ:517216493  WX:feiyangqingyun  QQ群:751439350
快速回复
限100 字节
 
上一个 下一个