一、环境介绍
操作系统: win10 64位
QT版本: QT5.12.6
编译器: MinGW 32
VLC版本: 3.0.12
功能说明: 下面的播放器例子支持基本播放器的功能。
1. 支持鼠标点击进度条跳转到指定帧
2. 支持音量设置、静音设置
3. 支持加载视频、暂停、停止、重播
4. 播放速率设置
5. 播放总时间与当前时间显示
完整项目代码下载地址: https://download.csdn.net/download/xiaolong1126626497/16579867
二、下载VLC的SDK文件
VLC官网地址: https://www.videolan.org/
所有的VLC版本下载地址: http://ftp.heanet.ie/pub/videolan/vlc
3.0.12的SDK下载地址: http://ftp.heanet.ie/pub/videolan/vlc/last/win32/
三、创建QT工程,编写简单的播放器
将下载目录下的sdk文件夹拷贝到QT的工程目录下,方便引用库和头文件。
3.2 pro工程文件里加路径
3.3 ui文件
3.4 widget.cpp代码
#include "widget.h" #include "ui_widget.h" Widget* Widget::pThis = nullptr; Widget::Widget(QWidget *parent) : QWidget(parent) , ui(new Ui::Widget) { pThis=this; ui->setupUi(this); this->setWindowTitle("视频播放器"); //VLC相关的初始化 vlc_base=libvlc_new(0, nullptr); //创建并初始化libvlc实例 if(!vlc_base) { qDebug()<<"libvlc_new 执行错误."; } //播放速度设置 ui->MediaSpeedBtn->setCheckable(true); m_TimeSpeedGrp = new QActionGroup(this); QStringList strSpeedItems; strSpeedItems << tr("0.03X") << tr("0.06X") << tr("0.1X") << tr("0.15X") << tr("0.2X") << tr("0.3X") << tr("0.4X") << tr("0.5X") << tr("0.6X") << tr("0.8X") << tr("1.0X") << tr("1.25X") << tr("1.5X") << tr("2.0X") << tr("4.0X") << tr("8.0X"); float speeds[] = { 0.03, 0.06, 0.1, 0.15, 0.2, 0.3, 0.4, 0.5,0.6,0.8,1.0,1.25,1.5,2.0,4.0,8.0}; for (int i = 0; i < strSpeedItems.size(); i++) { QAction *pSpeedItem = m_SpeedMenu.addAction(strSpeedItems.at(i)); pSpeedItem->setData(QVariant::fromValue(speeds[i])); pSpeedItem->setCheckable(true); m_TimeSpeedGrp->addAction(pSpeedItem); if (i == 10) { pSpeedItem->setChecked(true); } } connect(m_TimeSpeedGrp, SIGNAL(triggered(QAction *)), this, SLOT(slot_onSetTimeSpeed(QAction *))); //事件监听 ui->horizontalSlider_pos->installEventFilter(this); ui->horizontalSlider_volume->installEventFilter(this); } Widget::~Widget() { delete ui; libvlc_release(vlc_base); //减少libvlc实例的引用计数,并销毁它 } bool Widget::eventFilter(QObject *obj, QEvent *event) { if(obj==ui->horizontalSlider_pos) { if (event->type()==QEvent::MouseButtonPress) //判断类型 { QMouseEvent *mouseEvent = static_cast<QMouseEvent *>(event); if (mouseEvent->button() == Qt::LeftButton) //判断左键 { int value = QStyle::sliderValueFromPosition(ui->horizontalSlider_pos->minimum(), ui->horizontalSlider_pos->maximum(), mouseEvent->pos().x(), ui->horizontalSlider_pos->width()); ui->horizontalSlider_pos->setValue(value); //跳转播放器 float f_value=(float)value/(float)ui->horizontalSlider_pos->maximum(); libvlc_media_player_set_position(vlc_mediaPlayer,f_value); } } } if(obj==ui->horizontalSlider_volume) { if (event->type()==QEvent::MouseButtonPress) //判断类型 { QMouseEvent *mouseEvent = static_cast<QMouseEvent *>(event); if (mouseEvent->button() == Qt::LeftButton) //判断左键 { int value = QStyle::sliderValueFromPosition(ui->horizontalSlider_volume->minimum(), ui->horizontalSlider_volume->maximum(), mouseEvent->pos().x(), ui->horizontalSlider_volume->width()); ui->horizontalSlider_volume->setValue(value); //设置音量 if(vlc_mediaPlayer)libvlc_audio_set_volume(vlc_mediaPlayer,value); } } } return QWidget::eventFilter(obj, event); } /* 工程: QtVLC_Player 日期: 2021-03-24 作者: DS小龙哥 环境: win10 QT5.12.6 MinGW32 功能: 打开本地文件 */ void Widget::on_pushButton_open_clicked() { /*选择文件*/ QString filename=QFileDialog::getOpenFileName(this,"选择打开的文件","D:/",tr("*.*")); /* 将 / 转为windows下的右斜杆 */ std::replace(filename.begin(), filename.end(), QChar('/'), QChar('\\')); qDebug()<<"播放的媒体:"<<filename; /*为特定文件路径创建媒体*/ if(vlc_media)libvlc_media_release(vlc_media); vlc_media=libvlc_media_new_path(vlc_base,filename.toUtf8().data()); if(vlc_media==nullptr) { qDebug()<<"libvlc_media_new_path 执行错误."; return; } /*根据给定的媒体对象创建一个播放器对象*/ if(vlc_mediaPlayer)libvlc_media_player_release(vlc_mediaPlayer); vlc_mediaPlayer=libvlc_media_player_new_from_media(vlc_media); /*解析媒体实例*/ // libvlc_media_parse(vlc_media); /*获取媒体播放器事件管理器*/ libvlc_event_manager_t *em = libvlc_media_player_event_manager(vlc_mediaPlayer); libvlc_event_attach(em, libvlc_MediaPlayerTimeChanged, vlcEvents, this); libvlc_event_attach(em, libvlc_MediaPlayerEndReached, vlcEvents, this); libvlc_event_attach(em, libvlc_MediaPlayerStopped, vlcEvents, this); libvlc_event_attach(em, libvlc_MediaPlayerPlaying, vlcEvents, this); libvlc_event_attach(em, libvlc_MediaPlayerPaused, vlcEvents, this); /*设置给予媒体播放器媒体输出的win32/win64窗口句柄*/ libvlc_media_player_set_hwnd(vlc_mediaPlayer, (void *)ui->widget_VideoPlay->winId()); //如果不使用句柄方式,VLC也支持回调方式处理图像,这种方式可以自己提取图像数据,自己渲染显示处理. libvlc_video_set_callbacks /*播放媒体文件*/ if(vlc_mediaPlayer)libvlc_media_player_play(vlc_mediaPlayer); //等待VLC解析文件.否则下面的时间获取不成功 QThread::msleep(100); //获取媒体文件总长度 ms libvlc_time_t length = libvlc_media_player_get_length(vlc_mediaPlayer); qDebug()<<"媒体文件总长度:"<<length; ui->label_t2->setText(QString("%1").arg(length)); ui->horizontalSlider_pos->setMaximum(length); ui->horizontalSlider_pos->setMinimum(0); //获取当前媒体播放的位置 libvlc_time_t current_movie_time=libvlc_media_player_get_time(vlc_mediaPlayer); qDebug()<<"获取当前媒体播放的位置:"<<current_movie_time; unsigned int width=0,height=0; libvlc_video_get_size(vlc_mediaPlayer,0,&width,&height); qDebug()<<"视频尺寸:"<<"width:"<<width<<"height:"<<height; /*获取媒体播放器使用的媒体。*/ ui->label_video_name->setText(QString("%1:%2x%3").arg(filename).arg(width).arg(height)); //暂停: 停留在第一帧画面 if(vlc_mediaPlayer)libvlc_media_player_pause(vlc_mediaPlayer); } /* 工程: QtVLC_Player 日期: 2021-03-24 作者: DS小龙哥 环境: win10 QT5.12.6 MinGW32 功能: VLC的事件回调 */ void Widget::vlcEvents(const libvlc_event_t *ev, void *param) { qint64 pos; switch (ev->type){ case libvlc_MediaPlayerTimeChanged: qDebug() << "VLC媒体播放器时间已更改"; //获取当前媒体播放的位置 pos=libvlc_media_player_get_time(pThis->vlc_mediaPlayer); pThis->ui->label_t1->setText(QString("%1").arg(pos)); pThis->ui->horizontalSlider_pos->setValue(pos); break; case libvlc_MediaPlayerEndReached: qDebug() << "VLC播放完毕."; break; case libvlc_MediaPlayerStopped: qDebug() << "VLC停止播放"; break; case libvlc_MediaPlayerPlaying: qDebug() << "VLC开始播放"; break; case libvlc_MediaPlayerPaused: qDebug() << "VLC暂停播放"; break; } } /* 工程: QtVLC_Player 日期: 2021-03-24 作者: DS小龙哥 环境: win10 QT5.12.6 MinGW32 功能: 暂停 */ void Widget::on_pushButton_pause_clicked() { if(vlc_mediaPlayer)libvlc_media_player_pause(vlc_mediaPlayer); } /* 工程: QtVLC_Player 日期: 2021-03-24 作者: DS小龙哥 环境: win10 QT5.12.6 MinGW32 功能: 停止 */ void Widget::on_pushButton_stop_clicked() { if(vlc_mediaPlayer)libvlc_media_player_stop(vlc_mediaPlayer); } /* 工程: QtVLC_Player 日期: 2021-03-24 作者: DS小龙哥 环境: win10 QT5.12.6 MinGW32 功能: 速率 */ void Widget::slot_onSetTimeSpeed(QAction *action) { action->setChecked(true); ui->MediaSpeedBtn->setToolTip(action->text()); ui->MediaSpeedBtn->setText(action->text()); /*设置播放速率*/ if(vlc_mediaPlayer)libvlc_media_player_set_rate(vlc_mediaPlayer,float(action->data().toFloat())); } void Widget::on_MediaSpeedBtn_clicked() { QPoint ptWgt = ui->MediaSpeedBtn->mapToGlobal(QPoint(0, 0)); ptWgt -= QPoint(10, 180); QAction *pSelect = m_SpeedMenu.exec(ptWgt); if (pSelect == nullptr) return; } void Widget::on_pushButton_get_state_clicked() { if(vlc_mediaPlayer) { //4表示暂停 3表示继续 5表示停止 qDebug()<<"播放状态:"<<libvlc_media_player_get_state(vlc_mediaPlayer); } } void Widget::on_pushButton_reset_clicked() { /*需要先停止才可以继续重头播放*/ if(vlc_mediaPlayer)libvlc_media_player_stop(vlc_mediaPlayer); /*播放媒体文件*/ if(vlc_mediaPlayer)libvlc_media_player_play(vlc_mediaPlayer); } //静音切换 void Widget::on_pushButton_volume_clicked() { static bool state=false; state=!state; if(state) { //静音 if(vlc_mediaPlayer)libvlc_audio_set_volume(vlc_mediaPlayer,0); } else { int val=ui->horizontalSlider_volume->value(); qDebug()<<"设置音量:"<<val; if(vlc_mediaPlayer)libvlc_audio_set_volume(vlc_mediaPlayer,val); } } //音量滑块 void Widget::on_horizontalSlider_volume_valueChanged(int value) { //设置音量 if(vlc_mediaPlayer)libvlc_audio_set_volume(vlc_mediaPlayer,value); }
3.5 widget.h代码
#ifndef WIDGET_H #define WIDGET_H #include <QWidget> #include <vlc/vlc.h> #include <QFileDialog> #include <QDebug> #include <QThread> #include <QActionGroup> #include <QMenu> #include <QMouseEvent> #include <QStyle> #include <QTimer> QT_BEGIN_NAMESPACE namespace Ui { class Widget; } QT_END_NAMESPACE class Widget : public QWidget { Q_OBJECT public: Widget(QWidget *parent = nullptr); ~Widget(); private slots: void on_pushButton_open_clicked(); void on_pushButton_pause_clicked(); void on_pushButton_stop_clicked(); void slot_onSetTimeSpeed(QAction *action); void on_MediaSpeedBtn_clicked(); void on_pushButton_get_state_clicked(); void on_pushButton_reset_clicked(); void on_pushButton_volume_clicked(); void on_horizontalSlider_volume_valueChanged(int value); protected: bool eventFilter(QObject *obj, QEvent *event); static void vlcEvents(const libvlc_event_t *ev, void *param); private: Ui::Widget *ui; libvlc_instance_t *vlc_base=nullptr; libvlc_media_t *vlc_media=nullptr; libvlc_media_player_t *vlc_mediaPlayer=nullptr; QActionGroup *m_TimeSpeedGrp; QMenu m_SpeedMenu; static Widget *pThis; }; #endif // WIDGET_H
3.6 编译之后, 拷贝运行需要的文件
编译完成之后,将plugins目录、libvlc.dll、libvlccore.dll文件拷贝到exe同级目录下,再去QtCreate里运行测试。