VLC Qt视频播放器开发指南

Lida ·
更新时间:2024-11-15
· 677 次阅读

        VLC的音视频编解码是对ffmpeg的封装,用FFmpeg可以开发视频播放器,推拉流,同样用VLC也可以,某些时候可能比ffmpeg还要简单点。本篇博客介绍VLC Qt视频播放器开发的预备工作。

        开发环境:VS2017, Qt5.12_x64, win10

        首先需要获取VLC的SDK,  3.0版本的VLC安装后只有dll, 没有头文件,lib库,直接用源码编译还是有一定难度的。2.x版本的安装包会有sdk, 下载链接:http://download.videolan.org/pub/videolan/vlc/ 下载后,将include, lib,dll, plugins等文件放到一块儿,方便在vs中引用,如下图:

        sdk也可以直接编译 vlc 2.x 的源码得到,可以看我的这篇博客:VS2013编译vlc源码

        运行的时候,dll和plugins要放到exe所在的路径。

        VS2017项目属性包含include, lib,项目依赖项添加 libvlc.lib,libvlccore.lib

        播放器界面如下:

        视频显示用的是QWidget, 界面用qss做了美化,

        代码不太难,下面全部贴出来,有兴趣的可以参考。

        界面qss

QMainWindow { background-color: rgb(53, 53, 53); } QPushButton { background-color:rgb(128, 138, 135); color:white; font:16px; border-radius:6px; } QPushButton:hover { color:#0000ff; background-color:rgb(210, 205, 205); /*改变背景色*/ border-style:inset;/*改变边框风格*/ padding-left:1px; padding-top:1px; } QSlider::groove:horizontal { border: 1px solid #4A708B; background: #C0C0C0; height: 5px; border-radius: 1px; padding-left:-1px; padding-right:-1px; } QSlider::sub-page:horizontal { background: qlineargradient(x1:0, y1:0, x2:0, y2:1, stop:0 #B1B1B1, stop:1 #c4c4c4); background: qlineargradient(x1: 0, y1: 0.2, x2: 1, y2: 1, stop: 0 #5DCCFF, stop: 1 #1874CD); border: 1px solid #4A708B; height: 10px; border-radius: 2px; } QSlider::add-page:horizontal { background: #575757; border: 0px solid #777; height: 10px; border-radius: 2px; } QSlider::handle:horizontal { background: qradialgradient(spread:pad, cx:0.5, cy:0.5, radius:0.5, fx:0.5, fy:0.5, stop:0.6 #45ADED, stop:0.778409 rgba(255, 255, 255, 255)); width: 11px; margin-top: -5px; margin-bottom: -5px; border-radius: 5px; } QSlider::handle:horizontal:hover { background: qradialgradient(spread:pad, cx:0.5, cy:0.5, radius:0.5, fx:0.5, fy:0.5, stop:0.6 #2A8BDA, stop:0.778409 rgba(255, 255, 255, 255)); width: 11px; margin-top: -5px; margin-bottom: -5px; border-radius: 5px; }

 头文件

#pragma once #include #include "ui_MyVLCPlayer.h" #include "vlc/vlc.h" class MyVLCPlayer : public QMainWindow { Q_OBJECT public: MyVLCPlayer(QWidget *parent = Q_NULLPTR); ~MyVLCPlayer(); void stopPlay(); private slots: void on_btnLoadVideo_clicked(); void on_btnStart_clicked(); void on_btnStop_clicked(); int changeVolume(int vol); void changePosition(int pos); void updateInterface(); void on_btnMute_clicked(); private: Ui::MyVLCPlayerClass ui; libvlc_instance_t *m_vlcInstance; libvlc_media_player_t *m_vlcPlayer; };

  cpp文件

#pragma execution_character_set("utf-8") #include "MyVLCPlayer.h" #include #include #include MyVLCPlayer::MyVLCPlayer(QWidget *parent) : QMainWindow(parent) { ui.setupUi(this); #ifdef _DEBUG setWindowTitle("MyVLCPlayer_d"); #else setWindowTitle("MyVLCPlayer"); #endif m_vlcPlayer = NULL; //创建vlc实例 m_vlcInstance = libvlc_new(0, NULL); //判断vlc实例化是否ok if (m_vlcInstance == NULL) { QMessageBox::critical(this, "Qt libVLC player", "Could not init libVLC"); exit(1); } //音量进度条 connect(ui.volumeSlider, SIGNAL(sliderMoved(int)), this, SLOT(changeVolume(int))); ui.volumeSlider->setValue(50); //时间进度条 ui.timeSlider->setMaximum(1000); connect(ui.timeSlider, SIGNAL(sliderMoved(int)), this, SLOT(changePosition(int))); QTimer *timer = new QTimer(this); connect(timer, SIGNAL(timeout()), this, SLOT(updateInterface())); timer->start(100); } MyVLCPlayer::~MyVLCPlayer() { if (m_vlcInstance) { libvlc_release(m_vlcInstance); } stopPlay(); } void MyVLCPlayer::on_btnLoadVideo_clicked() { QString fileName = QFileDialog::getOpenFileName(this, tr("请选择视频文件"), tr("D:\\TestVideo"), tr("视频文件 (*.flv *.rmvb *.avi *.mp4);; 所有文件 (*.*);; ")); fileName.replace(":/", ":\\"); setWindowTitle(fileName); //如果视频正在播放,先停止播放 if (m_vlcPlayer && libvlc_media_player_is_playing(m_vlcPlayer)) { stopPlay(); } libvlc_media_t *vlcMedia = libvlc_media_new_path(m_vlcInstance, fileName.toStdString().c_str()); if (!vlcMedia) { return; } m_vlcPlayer = libvlc_media_player_new_from_media(vlcMedia); libvlc_media_release(vlcMedia); //vlcplayer和Qt控件关联 libvlc_media_player_set_hwnd(m_vlcPlayer, (void*)(ui.widget->winId())); libvlc_media_player_play(m_vlcPlayer); ui.btnStart->setText(tr("暂停")); } void MyVLCPlayer::on_btnStart_clicked() { if (!m_vlcPlayer) return; if (libvlc_media_player_is_playing(m_vlcPlayer)) { libvlc_media_player_pause(m_vlcPlayer); ui.btnStart->setText(tr("开始播放")); } else { libvlc_media_player_play(m_vlcPlayer); ui.btnStart->setText(tr("暂停")); } } void MyVLCPlayer::on_btnStop_clicked() { stopPlay(); } void MyVLCPlayer::stopPlay() { if (m_vlcPlayer) { libvlc_media_player_stop(m_vlcPlayer); libvlc_media_player_release(m_vlcPlayer); m_vlcPlayer = NULL; ui.timeSlider->setValue(0); ui.btnStart->setText(tr("开始播放")); } } int MyVLCPlayer::changeVolume(int vol) { if (m_vlcPlayer) { return libvlc_audio_set_volume(m_vlcPlayer, vol); } return 0; } void MyVLCPlayer::changePosition(int pos) { if (m_vlcPlayer) { libvlc_media_player_set_position(m_vlcPlayer, (float)pos / 1000.0); } } void MyVLCPlayer::updateInterface() { if (!m_vlcPlayer) { return; } float pos = libvlc_media_player_get_position(m_vlcPlayer); ui.timeSlider->setValue((int)(pos*1000.0)); if (libvlc_media_player_get_state(m_vlcPlayer) == libvlc_Ended) { this->stopPlay(); } } void MyVLCPlayer::on_btnMute_clicked() { if (m_vlcPlayer) { if (ui.volumeSlider->value() == 0) { this->changeVolume(80); ui.volumeSlider->setValue(80); } else { this->changeVolume(0); ui.volumeSlider->setValue(0); } } }

         音量处理这块儿有问题,声音曲线是log函数类型的,目前简单的处理了。视频其它功能基本ok.

         以后有时间再写写vlc推拉流。

令狐掌门 原创文章 251获赞 111访问量 23万+ 关注 私信 展开阅读全文
作者:令狐掌门



vlc

需要 登录 后方可回复, 如果你还没有账号请 注册新账号