qt6.5.0屏幕录制
记录一下本次开发踩到的坑,qt开发屏幕录制最坑的点是m_screen_caputure->setActive(true);
录制前需要先激活屏幕捕获。不然会直接报找不到编码器的错误。其他废话不多说,直接上代码
widget.h
#ifndef WIDGET_H
#define WIDGET_H
#include <QWidget>
#include <QMediaRecorder>
#include <QMediaCaptureSession>
#include <QScreenCapture>
#include <QAudioInput>
#include <QMediaFormat>
#include <QMediaDevices>
#include <QAudioDevice>
#include <QTimer>
#include <QTime>
QT_BEGIN_NAMESPACE
namespace Ui {
class Widget;
}
QT_END_NAMESPACE
class Widget : public QWidget
{
Q_OBJECT
public:
Widget(QWidget *parent = nullptr);
~Widget();
private:
void initSrceen();//初始化屏幕
void initAudioDev();//初始化音频设备
void initVideoCodec();//初始化视频编码格式
void initAudioCodec();//初始化音频编码格式
void initFileFormat();//初始化文件格式
void initQuality();//初始化音视频质量
void updateStateEnable(bool bl);//更新控件使能
void showRecordDuration();//显示录制时长
void showError(QMediaRecorder::Error error, const QString &errorString);//显示错误信息
private slots:
void on_btn_start_record_clicked();
void on_btn_stop_record_clicked();
void on_btn_pause_record_clicked();
void on_comboBox_video_encode_format_currentIndexChanged(int index);
void on_comboBox_audio_encode_format_currentIndexChanged(int index);
void on_comboBox_file_format_currentIndexChanged(int index);
void on_comboBox_video_quality_currentIndexChanged(int index);
void on_comboBox_audio_currentIndexChanged(int index);
void on_comboBox_screen_currentIndexChanged(int index);
void on_tbtn_set_dir_clicked();
private:
Ui::Widget *ui;
QMediaCaptureSession m_captureSession;
QMediaRecorder m_recorder;
QScreenCapture *m_screen_caputure = nullptr;
QScreen *m_srceen = nullptr;
QAudioDevice m_dev;
QAudioInput m_audio;
QMediaFormat format;
//屏幕设备列表
QList<QScreen *> m_screenList;
//音频设备列表
QList<QAudioDevice> m_audioInputList;
QTimer *m_timer;
};
#endif // WIDGET_H
widget.cpp
#include "widget.h"
#include "ui_widget.h"
#include <QUrl>
#include <QMessageBox>
#include <QDir>
#include <QFileDialog>
Widget::Widget(QWidget *parent)
: QWidget(parent)
, ui(new Ui::Widget)
{
ui->setupUi(this);
initSrceen();
initAudioDev();
initVideoCodec();
initAudioCodec();
initFileFormat();
initQuality();
//绑定主屏幕
m_srceen = qApp->primaryScreen();
m_screen_caputure = new QScreenCapture(this);
m_screen_caputure->setScreen(m_srceen);
//绑定默认音频设备
m_dev= QMediaDevices::defaultAudioInput();
m_audio.setDevice(m_dev);
connect(&m_recorder,&QMediaRecorder::errorOccurred,this,&Widget::showError);
ui->btn_start_record->setEnabled(true);
ui->btn_pause_record->setEnabled(false);
ui->btn_stop_record->setEnabled(false);
m_timer = new QTimer(this);
connect(m_timer,&QTimer::timeout,this,&Widget::showRecordDuration);
//设置桌面为初始文件保存目录,保存文件名字为test
QString filePath = QDir::homePath() + "/Desktop/test";
ui->lineEdit_file_save_path->setText(filePath);
}
Widget::~Widget()
{
delete ui;
}
//初始化屏幕
void Widget::initSrceen()
{
m_screenList = qApp->screens();
foreach (auto dev,m_screenList) {
ui->comboBox_screen->addItem(dev->name());
}
ui->comboBox_screen->setCurrentIndex(0);
}
//初始化音频设备
void Widget::initAudioDev()
{
m_audioInputList = QMediaDevices::audioInputs();
foreach (auto dev,m_audioInputList) {
ui->comboBox_audio->addItem(dev.description());
}
ui->comboBox_audio->setCurrentIndex(0);
}
//初始化视频编码格式
void Widget::initVideoCodec()
{
QStringList video_encode_list;
video_encode_list << "MPEG1"<<"MPEG2"<<"MPEG4"<<"H264"<<"H265"<<"VP8"<<"VP9"<<"AV1"<<"Theora"<<"WMV"<<"MotionJPEG";
ui->comboBox_video_encode_format->addItems(video_encode_list);
ui->comboBox_video_encode_format->setCurrentIndex(3);
}
//初始化音频编码格式
void Widget::initAudioCodec()
{
QStringList audio_encode_list;
audio_encode_list << "MP3"<<"AAC"<<"AC3"<<"EAC3"<<"FLAC"<<"DolbyTrueHD"<<"Opus"<<"Vorbis"<<"Wave"<<"WMA"<<"ALAC";
ui->comboBox_audio_encode_format->addItems(audio_encode_list);
ui->comboBox_audio_encode_format->setCurrentIndex(1);
}
//初始化文件格式
void Widget::initFileFormat()
{
QStringList file_format_list;
file_format_list << "WMV"<<"AVI"<<"Matroska"<<"MPEG4"<<"Ogg"<<"QuickTime"<<"WebM"<<"Mpeg4Audio"<<"AAC"<<"WMA"<<"MP3"<<"FLAC"<<"Wave";
ui->comboBox_file_format->addItems(file_format_list);
ui->comboBox_file_format->setCurrentIndex(3);
}
//初始化音视频质量
void Widget::initQuality()
{
QStringList video_quality_list;
video_quality_list << "VeryLowQuality"<<"LowQuality"<<"NormalQuality"<<"HighQuality"<<"VeryHighQuality";
ui->comboBox_video_quality->addItems(video_quality_list);
ui->comboBox_video_quality->setCurrentIndex(2);
}
//屏幕设备改变槽函数
void Widget::on_comboBox_screen_currentIndexChanged(int index)
{
if(!m_screenList.isEmpty() && m_screen_caputure != nullptr)
m_screen_caputure->setScreen(m_screenList.at(index));
}
//音频设备改变槽函数
void Widget::on_comboBox_audio_currentIndexChanged(int index)
{
if(!m_audioInputList.isEmpty())
m_audio.setDevice(m_audioInputList.at(index));
}
//视频编码格式改变槽函数
void Widget::on_comboBox_video_encode_format_currentIndexChanged(int index)
{
format.setVideoCodec((QMediaFormat::VideoCodec)index);
}
//音频编码格式改变槽函数
void Widget::on_comboBox_audio_encode_format_currentIndexChanged(int index)
{
format.setAudioCodec((QMediaFormat::AudioCodec)index);
}
//文件格式改变槽函数
void Widget::on_comboBox_file_format_currentIndexChanged(int index)
{
format.setFileFormat((QMediaFormat::FileFormat)index);
}
//音视频质量改变槽函数
void Widget::on_comboBox_video_quality_currentIndexChanged(int index)
{
m_recorder.setQuality((QMediaRecorder::Quality)index);
}
//显示错误信息
void Widget::showError(QMediaRecorder::Error error, const QString &errorString)
{
Q_UNUSED(error);
QMessageBox::critical(this,"Error",errorString);
}
//显示录制时长
void Widget::showRecordDuration()
{
int show_time = m_recorder.duration();//获取视频总时长
//总时长转成hh:mm:ss.zzz格式
QTime start = QTime(0,0,0);
QTime qtime = start.addMSecs(show_time);
ui->label_duration->setText("录制时长:" + qtime.toString("hh:mm:ss.zzz"));
}
//手动设置目录
void Widget::on_tbtn_set_dir_clicked()
{
QString dir = QFileDialog::getExistingDirectory(this, tr("Open Directory"),
"/home",
QFileDialog::ShowDirsOnly
| QFileDialog::DontResolveSymlinks);
if(!dir.isEmpty())
ui->lineEdit_file_save_path->setText(dir);
}
//开始录制
void Widget::on_btn_start_record_clicked()
{
//激活屏幕捕获
m_screen_caputure->setActive(true);
//设置音频参数,视频参数
m_captureSession.setScreenCapture(m_screen_caputure);
m_captureSession.setAudioInput(&m_audio);
m_captureSession.setRecorder(&m_recorder);
m_recorder.setMediaFormat(format);
m_recorder.setVideoBitRate(ui->lineEdit_video_bit_rate->text().toInt());
m_recorder.setVideoFrameRate(ui->lineEdit_frame_rate->text().toInt());
m_recorder.setVideoResolution(ui->lineEdit_resolution_ratio_w->text().toInt(),ui->lineEdit_resolution_ratio_h->text().toInt());
m_recorder.setAudioBitRate(ui->lineEdit_audio_bit_rate->text().toInt());
m_recorder.setAudioChannelCount(ui->lineEdit_channels->text().toInt());
m_recorder.setAudioSampleRate(ui->lineEdit_sampling_rate->text().toInt());
QString str = ui->lineEdit_file_save_path->text();
//m_recorder.setOutputLocation(QUrl::fromLocalFile("/C:/Users/10986/Desktop/test"));
m_recorder.setOutputLocation(QUrl::fromLocalFile(str));
m_recorder.record();
ui->btn_start_record->setEnabled(false);
ui->btn_pause_record->setEnabled(true);
ui->btn_stop_record->setEnabled(true);
updateStateEnable(false);
m_timer->start(1000);
}
//停止录制
void Widget::on_btn_stop_record_clicked()
{
m_recorder.stop();
ui->btn_start_record->setEnabled(true);
ui->btn_pause_record->setEnabled(false);
ui->btn_stop_record->setEnabled(false);
updateStateEnable(true);
}
//暂停录制
void Widget::on_btn_pause_record_clicked()
{
m_recorder.pause();
ui->btn_start_record->setEnabled(true);
ui->btn_pause_record->setEnabled(false);
ui->btn_stop_record->setEnabled(true);
updateStateEnable(true);
m_timer->stop();
}
//更新控件使能
void Widget::updateStateEnable(bool bl)
{
ui->groupBox_video->setEnabled(bl);
ui->groupBox_audio->setEnabled(bl);
ui->groupBox_file->setEnabled(bl);
ui->groupBox_other->setEnabled(bl);
m_timer->stop();
}
软件运行截图: