QT基于Gstreamer采集的简单示例

我们在终端敲指令可以使用gstreamer方式去采集,如下所示,按1920*1080分辨率,60帧方式采集video0的视频。

复制代码
gst-launch-1.0 v4l2src device=/dev/video0 ! video/x-raw, width=1920, height=1080, framerate=60/1 ! videoconvert ! autovideosink

敲完指令后会自动弹出一个显示窗口,那么如何让gstreamer与QT结合,使得视频显示在指定的QT窗体里呢。

首先我们把gst采集部分封装一下,可传入参数视频设备,分辨率,帧率等,同时包含一个用于显示的QWidget。

下边是头文件

复制代码
class gstWidget : public QWidget
{
    Q_OBJECT

public:
    gstWidget(std::string device,int width,int height,int framerate,QWidget *parent = nullptr);
    ~gstWidget();

private:
    GstElement *pipeline;
    void startGStreamer(std::string device,int width,int height,int framerate);
};

下边是源文件

复制代码
gstWidget::gstWidget(std::string device,int width,int height,int framerate,QWidget *parent)
    : QWidget(parent)
{
    gst_init(nullptr, nullptr);
    startGStreamer(device,width,height,framerate);
}

gstWidget::~gstWidget()
{
    if (pipeline) {
        gst_element_set_state(pipeline, GST_STATE_NULL);
        gst_object_unref(pipeline);
    }
}

void gstWidget::startGStreamer(std::string device,int width,int height,int framerate)
{
     std::string pipeline_str = "v4l2src device=" + device + " ! "
     "video/x-raw,width="+std::to_string(width)+",height="+ std::to_string(height)+",framerate="+std::to_string(framerate)+"/1 ! "
     "xvimagesink name=xvimagesink ";

    pipeline = gst_parse_launch(pipeline_str.c_str(), nullptr);

    WId winId = this->winId();
    GstElement* xv_sink = gst_bin_get_by_name(GST_BIN(pipeline), "xvimagesink");
    g_object_set(xv_sink, "force-aspect-ratio", true, NULL);
    if (xv_sink) {
        gst_video_overlay_set_window_handle(GST_VIDEO_OVERLAY(xv_sink), (guintptr)winId);
    } else {
        qDebug() << "Failed to get xvimagesink element.";
    }

    gst_element_set_state(pipeline, GST_STATE_PLAYING);
}

后续如果要使用只需要调用gstWidget创建窗口即可,下边是一个使用示意,构造了一个带标题的cam显示窗口。

首先是头文件

复制代码
class camWidget : public QWidget
{
    Q_OBJECT

public:
    camWidget(std::string device,QString title,int width,int height,int framerate,QWidget *parent = nullptr);
    ~camWidget();

public:
    gstWidget *camDisp;

private:
    QLabel *title_label;
};

然后是源文件

复制代码
camWidget::camWidget(std::string device,QString title,int width,int height,int framerate,QWidget *parent)
    : QWidget(parent)
{
    QVBoxLayout *mainLayout = new QVBoxLayout(this);
    camDisp=new gstWidget(device,width,height,framerate,this);

    mainLayout->addWidget(camDisp);
    setLayout(mainLayout);

    title_label=new QLabel(this);

    title_label->setAlignment(Qt::AlignCenter);
    title_label->setStyleSheet("background: transparent; color: #FFFFFF");
    title_label->setText(title);
}
camWidget::~camWidget()
{
}

接下来是真正的应用,在这里创建一个video0的显示窗口,标题为"cam",按1920*1080分辨率60帧去采集,显示窗口的大小为640*480。

复制代码
camWidget cam=new camWidget("/dev/video0","cam",1920,1080,60,this);
cam->setGeometry(0,0,640,480);
相关推荐
牵牛老人2 分钟前
【Qt 开发后台服务避坑指南:从库存管理系统开发出现的问题来看后台开发常见问题与解决方案】
开发语言·qt·系统架构
froginwe1111 分钟前
Python3与MySQL的连接:使用mysql-connector
开发语言
灵感菇_29 分钟前
Java HashMap全面解析
java·开发语言
杜子不疼.30 分钟前
PyPTO:面向NPU的高效并行张量编程范式
开发语言
lly20240631 分钟前
C# 结构体(Struct)
开发语言
YMWM_42 分钟前
python3继承使用
开发语言·python
Once_day1 小时前
C++之《程序员自我修养》读书总结(1)
c语言·开发语言·c++·程序员自我修养
xmRao1 小时前
Qt+FFmpeg 实现 PCM 音频转 AAC 编码
qt·ffmpeg·pcm
xmRao1 小时前
Qt+FFmpeg 实现录音程序(pcm转wav)
qt·ffmpeg