本篇博客介绍如何基于qt5制作简单音乐播放器
开发工具:devc++
实现语言:c++
需导入qt5这个库
**
以下是本篇文章正文内容
从以下链接下载QT类库的在线安装程序: 链接:https://pan.baidu.com/s/1mZK_3-9f23455gyxljmrkQ
提取码:2019或者从以下网站下载在线安装文件4.1.1版本,点击执行进行安装。 Download Qt: Get Qt Online Installer
安装过程中需要注册,请按照要求注册。然后输入Email和密码进入下一步
这里是引用
在DEV C++菜单中选择Tools,Compiler Options,在弹出的窗口中,点击右上方带加号的按钮(Add a blank compiler set),然后输入新编译器名字,比如MinGW810_64 Compiler,点击OK退出。在General中勾选Add the following commands when calling the compile,然后复制以下内容在方框中:-O2 -lqt5core -lqt5widgets -lqt5gui -lQt5Multimedia -lQt5MultimediaWidgets -lQt5Network -lQt5TextToSpeech -lQt5Charts -lQt5DataVisualization
#ifndef LESPLAYER_H
#define LESPLAYER_H
#include //包含QtWidgets头文件
#include //包含播放器头文件
#include //包含视频项头文件
class MyGraphicsView:public QGraphicsView
{
public:
MyGraphicsView(QWidget *parent = 0); //构造函数,参数是父窗体指针,默认是0,即没有父窗口
QGraphicsScene *scene=new QGraphicsScene; //定义场景,用于放置视频项
QGraphicsVideoItem *videoItem=new QGraphicsVideoItem; //定义一个视频窗口
private:
void resizeEvent(QResizeEvent *event);//视图窗口尺寸改变时自动执行的函数
};
class MyMainWindow:public QMainWindow //定义一个MyMainWindow类,继承自QMainWindow窗口类
{
public:
MyMainWindow(QWidget *parent = 0); //构造函数,参数是父窗体指针
QMenuBar *menuBar=new QMenuBar;//定义菜单栏对象指针menuBar
QMediaPlayer *player=new QMediaPlayer(this); //定义一个播放器对象指针
MyGraphicsView *view=new MyGraphicsView; //定义视图窗口,用于观看视频
//Layout
QHBoxLayout *hLayout = new QHBoxLayout;//存放进度条的
QHBoxLayout *ListLayout = new QHBoxLayout;//歌曲列表list
QHBoxLayout *buttonLayout = new QHBoxLayout;//开始、暂停、上下一首
QHBoxLayout *name_list = new QHBoxLayout;//歌曲名-播放进度条-列表
QVBoxLayout *verticalLayout = new QVBoxLayout;//整个的垂直结构
QVBoxLayout *play_slider = new QVBoxLayout;
//Slider
QSlider *slider=new QSlider; //创建QSlider对象指针
//ListWidget
QWidget *centralWidget=new QWidget;//定义一个QWidget对象指针centralWidget
QListWidget *listWidget = new QListWidget;//列表窗
//Label
QLabel *timeLabel = new QLabel;//显示实时的时间
QLabel *durationLabel = new QLabel;//显示总时间
QLabel *songName = new QLabel;//歌名标签
//Button
QPushButton *startButton = new QPushButton;//播放按钮
QPushButton *nextLButton = new QPushButton;//左按钮
QPushButton *nextRButton = new QPushButton;//右按钮
QPushButton *importMusic = new QPushButton;//右按钮
QPushButton *playMode = new QPushButton;//模式切换按钮
//标志
int flag = 1;//播放暂停按钮播放控制
int playNow = 0;//正在播放曲目控制
int Mode = 1;//播放模式控制标志
void listWidgetItemActivated(QListWidgetItem *activatedItem); //item列表项被激发以后的处理函数
void openFile(); //点击open菜单项时的处理函数
void openMusic();//打开音乐
void videoPositionChanged(double position);//进度变化
void durationChanged(double duration);//获取总时间
void mediaStatusChanged(QMediaPlayer::MediaStatus statu); //让歌曲进度随进度条变化而改变
void sliderMovedEvent();//
void sliderReleasedEvent();
void sliderPressedEvent();
void startButtonEvent();//播放
void pauseButtonEvent();//暂停
void stopButtonEvent();//停止
void importLocalSongs();//导入本地音乐
void lastMusic();//上一曲
void nextMusic();//下一曲
void changeList();//列表变化
void changeMode();//播放模式改变
void inputInformation();//错误提示
int generateRandomNumber();
};
#endif // LESPLAYER_H
.cpp文件
#include "LesPlayer.h"
#define cn QString::fromLocal8Bit //中文字符显示
MyGraphicsView::MyGraphicsView(QWidget *parent):QGraphicsView(parent)
{
this->setStyleSheet("background-color:rgb(232,255,255);");//通过样式表设置背景色
this->setContentsMargins(0,0,0,0); //设定边界宽度是0
this->setFocusPolicy(Qt::NoFocus); //设置本控件不接收焦点
this->setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); //禁止水平滚动条显示
this->setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff); //禁止垂直滚动条显示
this->setMinimumSize(QSize(520,280));//设置窗口最小尺寸
this->setScene(scene); //设置视图窗口要观看的场景为scene
scene->addItem(videoItem); //添加视频项videoItem到场景scene
}
void MyGraphicsView::resizeEvent(QResizeEvent *event)
{
scene->setSceneRect(0, 0, this->width(), this->height()); //设置场景scene的显示坐标范围和视图窗口相同
videoItem->setSize(QSize(this->width(), this->height())); //设置视频项的大小和场景一致。
}
//定义构造函数,参数是父窗体指针,先调用基类构造函数QMainWindow(parent)
MyMainWindow::MyMainWindow(QWidget *parent):QMainWindow(parent)
{
this->setWindowTitle("Libin Music"); //设置窗体的标题
this->resize(960,600); //变更窗体尺寸
this->setMenuBar(menuBar); //menuBar设置为本窗口的菜单栏
this->setCentralWidget(centralWidget);//设置一个widget
this->setWindowIcon(QPixmap("logoIcon.png"));//窗口图标
//定义菜单对象指针fileMenu,显示“File”
QMenu *fileMenu=new QMenu("File");
//为fileMen添加一个菜单项,有图标和点击时的处理函数openFile();
fileMenu->addAction(QPixmap("open.png"), "OpenVideo", this, &openFile);
fileMenu->addAction(QPixmap("open.png"), "OpenMusic", this, &openMusic);
menuBar->addMenu(fileMenu); //将fileMenu菜单添加到菜单栏
//进度条管理
slider->setRange(1,100); //设定数据范围
slider->setSingleStep(5); //设定单次步长
slider->setPageStep(5); //设定PageUp和PageDown步长
slider->setFixedWidth(600); //设定控件固定宽度
slider->setOrientation(Qt::Horizontal); //设定控件显示方位
//下一曲按钮
QPixmap nextRicon(tr("next.png"));
nextRButton->setIcon(nextRicon);
nextRButton->setFixedSize(nextRicon.size());
nextRButton->setStyleSheet("background-color:rgb(20,145,168);""color:rgb(248,244,237);");
nextRButton->setCursor(Qt::PointingHandCursor);
//开始按钮设置
QPixmap pauseIcon(tr("play4.png"));
startButton->setIcon(pauseIcon);
startButton->setFixedSize(nextRicon.size());
startButton->setStyleSheet("background-color:rgb(20,145,168);""color:rgb(248,244,237);");
startButton->setCursor(Qt::PointingHandCursor);
//上一曲按钮
QPixmap nextLicon(tr("last.png"));
nextLButton->setIcon(nextLicon);
nextLButton->setFixedSize(nextLicon.size());
nextLButton->setStyleSheet("background-color:rgb(20,145,168);""color:rgb(248,244,237);");
nextLButton->setCursor(Qt::PointingHandCursor);
//导入音乐列表
QPixmap ListIcon(tr("menu.png"));
importMusic->setIcon(ListIcon);
importMusic->setFixedSize(80,80);
importMusic->setStyleSheet("background-color:rgb(20,145,168);""color:rgb(20,145,168);");
importMusic->setCursor(Qt::PointingHandCursor);
QString str=QString(cn("导入本地音乐\n"));
importMusic->setToolTip(str);
//模式切换按钮
playMode->setIcon(QPixmap("Sequential.png"));
playMode->setFixedSize(nextLicon.size());
playMode->setStyleSheet("background-color:rgb(20,145,168);""color:rgb(20,145,168);");
playMode->setCursor(Qt::PointingHandCursor);
//歌曲名label
songName->setMinimumSize(120,80);
songName->setMaximumSize(120,80);//固定大小,防止乱跑
songName->setText(cn("音乐的力量"));
songName->setAlignment(Qt::AlignCenter | Qt::AlignHCenter);
songName->setStyleSheet("background-color:rgb(20,145,168);""color:rgb(248,244,237);");
songName->setWordWrap(true);//Label内容换行
//进度时间层
hLayout->addWidget(timeLabel);
hLayout->addWidget(slider);
hLayout->addWidget(durationLabel);
//按钮层添加按钮
buttonLayout->addWidget(playMode);//播放模式
buttonLayout->addWidget(nextLButton);
buttonLayout->addWidget(startButton);
buttonLayout->addWidget(nextRButton);
//play_slider 上播放按钮,下进度条
play_slider->addLayout(buttonLayout);
play_slider->addLayout(hLayout);
//name_list歌曲名-播放进度条-列表
name_list->addWidget(songName);
name_list->addLayout(play_slider);
name_list->addWidget(importMusic);
//列表窗
ListLayout->addWidget(listWidget);
//垂直结构添加
verticalLayout->addLayout(ListLayout);
verticalLayout->addLayout(name_list);
//添加垂直结构
centralWidget->setLayout(verticalLayout);
//播放器进度改变信号以及该信号的处理函数
connect(player, &QMediaPlayer::positionChanged, this, &videoPositionChanged);
//打开媒体文件时,player播放器会发出媒体总长度改变信号,用此信号设置滑动条最大值
connect(player, &QMediaPlayer::durationChanged, this, &durationChanged);
//播放器的媒体状态改变信号以及该信号处理函数
connect(player, &QMediaPlayer::mediaStatusChanged, this, &mediaStatusChanged);
//进度条和媒体播放链接起来
connect(slider, &QSlider::sliderMoved, this, &sliderMovedEvent);
//检测释放进度条
connect(slider, &QSlider::sliderReleased, this, &sliderReleasedEvent);
//检测按压进度条
connect(slider, &QSlider::sliderPressed, this, &sliderPressedEvent);
//播放、暂停按钮
connect(startButton,&QPushButton::clicked, this, &startButtonEvent);
//下一曲
connect(nextRButton,&QPushButton::clicked, this, &nextMusic);
//上一曲
connect(nextLButton,&QPushButton::clicked, this, &lastMusic);
//建立itemActivated列表项激发信号和信号处理函数之间的连接
connect(listWidget, &QListWidget::itemActivated, this, &listWidgetItemActivated);
//导入音乐
connect(importMusic,&QPushButton::clicked, this, &importLocalSongs);
//播放模式
connect(playMode,&QPushButton::clicked, this, &changeMode);
}
//列表同步变化
void MyMainWindow::changeList(){
for (int i=0; i<listWidget->count(); i++)//遍历列表框的所有项,设置背景色和前景色,更改图标
{
listWidget->item(i)->setForeground(QColor(0, 0, 0));
listWidget->item(i)->setBackground(QColor(255, 255, 255));
listWidget->item(i)->setIcon(QPixmap("MultiMedia 32p-3.ico"));
}
listWidget->item(playNow)->setForeground(QColor(255, 0, 0));
listWidget->item(playNow)->setBackground(QColor(0, 255, 0));
listWidget->item(playNow)->setIcon(QPixmap("play2.png"));
//下面是列表显示的同步设置
QString musicFullName = listWidget->item(playNow)->data(Qt::UserRole).toString();
QFileInfo fileInfo(musicFullName); //创建文件信息类对象fileInfo
QString fileName=fileInfo.fileName(); //从fileInfo中获得文件名(无路径)
songName->setText(fileName);
//开始按钮同步
startButton->setIcon(QPixmap("play2.png"));
flag = 1;
}
//滑动条最大值
void MyMainWindow::durationChanged(double duration)
{
slider->setMaximum(duration); //设置滑动条最大值
int min = duration/1000/60;//分钟
int s = (duration/1000/60 - min)*60;//秒数
QString durationText = QString::number(min)+":"+QString::number(s);//durationlabel显示内容
durationLabel->setMinimumSize(80,60);
durationLabel->setMaximumSize(80,60);//固定大小,防止乱跑
durationLabel->setText(durationText); //媒体总长度(分钟)
durationLabel->setAlignment(Qt::AlignCenter | Qt::AlignHCenter);
durationLabel->setStyleSheet("background-color:rgb(248,244,237);""color:rgb(20,145,168);");
durationLabel->setWordWrap(true);//Label内容换行
}
//进度条实时变化
void MyMainWindow::videoPositionChanged(double position) //播放器进度信号的处理函数
{
slider->setValue(position); //播放器进度改变时,更改滑动条上滑块的位置显示进度。
int min = position/1000/60;//分钟
int s = (position/1000/60 - min)*60;//秒数
QString positionText = QString::number(min)+":"+QString::number(s);//进度label显示内容
if(min == 0){
positionText = QString::number(s);
}
timeLabel->setMinimumSize(80,60);
timeLabel->setMaximumSize(80,60);//固定大小,防止乱跑
timeLabel->setText(positionText); //当前播放进度
timeLabel->setAlignment(Qt::AlignCenter | Qt::AlignHCenter);
timeLabel->setStyleSheet("background-color:rgb(248,244,237);""color:rgb(20,145,168);");
timeLabel->setWordWrap(true);//Label内容换行
}
//导入本地音乐
void MyMainWindow:: importLocalSongs(){
QStringList filenames=QFileDialog::getOpenFileNames(this, "Open File", "","Music(*.mp3 *.flac *.ape);;All files (*.*)");
for (int i=0; i<filenames.count(); i++){
QFileInfo fileInfo(filenames.at(i));
QString fileName = fileInfo.fileName();
QListWidgetItem *item=new QListWidgetItem; //定义列表项
item->setIcon(QPixmap("MultiMedia 32p-3.ico")); //设置列表项图标
item->setText(fileName);//设置显示文本,比如显示歌名
item->setData(Qt::UserRole, filenames.at(i));
listWidget->addItem(item);//添加列表项到列表框
}
hLayout->addWidget(slider);
}
//歌曲列表双击操作
void MyMainWindow::listWidgetItemActivated(QListWidgetItem *activatedItem)
{
for (int i=0; i<listWidget->count(); i++)//遍历列表框的所有项,设置背景色和前景色,更改图标
{
listWidget->item(i)->setForeground(QColor(0, 0, 0));
listWidget->item(i)->setBackground(QColor(255, 255, 255));
listWidget->item(i)->setIcon(QPixmap("MultiMedia 32p-3.ico"));
}
playNow = listWidget->currentRow();
activatedItem->setForeground(QColor(255, 0, 0));
activatedItem->setBackground(QColor(0, 255, 0));
activatedItem->setIcon(QPixmap("play2.png"));
QString musicFullName = activatedItem->data(Qt::UserRole).toString(); //获得用户数据,也就是因为文件全名,可以送到播放器播放
player->setMedia(QUrl::fromLocalFile(musicFullName));//设置播放器的媒体文件
player->play();//开始播放
QFileInfo fileInfo(musicFullName); //创建文件信息类对象fileInfo
QString fileName=fileInfo.fileName(); //从fileInfo中获得文件名(无路径)
songName->setText(fileName);
QPixmap startIcon(tr("play2.png"));
startButton->setIcon(startIcon);
flag = 1;
hLayout->addWidget(timeLabel);
hLayout->addWidget(slider);
hLayout->addWidget(durationLabel);
}
//打开音乐
void MyMainWindow:: openMusic()
{
//打开文件选择对话框,过滤器选择mp3,flac,ape音乐文件,或者所有文件。
QString fileFullName = QFileDialog::getOpenFileName(this, "Open Music", "","Music(*.mp3 *.flac *.ape);;All files (*.*)");
if (fileFullName=="") return;//如果没有选择,返回。
player->setMedia(QUrl::fromLocalFile(fileFullName));//设置播放器的媒体文件
QPixmap startIcon(tr("play2.png"));
startButton->setIcon(startIcon);//按钮设置成开始的样子
player->play();//开始播放
QFileInfo fileInfo(fileFullName); //创建文件信息类对象fileInfo
QString fileName=fileInfo.fileName(); //从fileInfo中获得文件名(无路径)
for (int i=0; i<listWidget->count(); i++)//遍历列表框的所有项,设置背景色和前景色,更改图标
{
listWidget->item(i)->setForeground(QColor(0, 0, 0));
listWidget->item(i)->setBackground(QColor(255, 255, 255));
listWidget->item(i)->setIcon(QPixmap("MultiMedia 32p-3.ico"));
}
QListWidgetItem *item=new QListWidgetItem; //定义列表项
item->setForeground(QColor(255, 0, 0));
item->setBackground(QColor(0, 255, 0));
item->setIcon(QPixmap("play2.png"));
item->setText(fileName);//设置显示文本,比如显示歌名
item->setData(Qt::UserRole, fileFullName);
listWidget->addItem(item);//添加列表项到列表框
songName->setText(fileName);
playNow = listWidget->count() - 1;
}
//上一曲
void MyMainWindow:: lastMusic(){
//上一曲,首位置,转回最后,其他的减减
if(playNow == 0){
playNow =listWidget->count()-1;
}
else{
playNow--;
}
QString musicFullName = listWidget->item(playNow)->data(Qt::UserRole).toString(); //获得用户数据,也就是因为文件全名,可以送到播放器播放
player->setMedia(QUrl::fromLocalFile(musicFullName));//设置播放器的媒体文件
player->play();//开始播放
//列表显示同步
changeList();//调用changeList函数
}
//下一曲
void MyMainWindow:: nextMusic(){
//下一曲1.末尾,转回第一曲2.不是末尾,加加
if(playNow == listWidget->count()-1){
playNow = 0;
}
else{
playNow++;
}
QString musicFullName = listWidget->item(playNow)->data(Qt::UserRole).toString(); //获得用户数据,也就是因为文件全名,可以送到播放器播放
player->setMedia(QUrl::fromLocalFile(musicFullName));//设置播放器的媒体文件
player->play();//开始播放
//列表显示同步
changeList();//调用changeList函数
}
//播放模式改变,仅改变值,播放让状态函数变化
void MyMainWindow::changeMode(){
if (Mode == 1)
{
Mode++;
playMode->setIcon(QPixmap("Loop.png"));
}
else if(Mode == 2)
{
Mode++;
playMode->setIcon(QPixmap("Random.png"));
}
else{
Mode = 1;
playMode->setIcon(QPixmap("Sequential.png"));
}
}
//提示信息
void MyMainWindow::inputInformation()
{
}
//利用自带的函数来做1.顺序直接用nextMusic,2.循环不改变playNow3.随机,palyNow取1-list.count的随机数
void MyMainWindow:: mediaStatusChanged(QMediaPlayer::MediaStatus status)
{
if (status == QMediaPlayer::InvalidMedia) //无法播放媒体文件,输出错误信息
{
inputInformation();
}
else if (status == QMediaPlayer::EndOfMedia) //当前文件播放结束,播放下一首?
{
if (Mode == 1){
nextMusic();
}
else if(Mode == 2){
QString musicFullName = listWidget->item(playNow)->data(Qt::UserRole).toString(); //获得用户数据,也就是因为文件全名,可以送到播放器播放
player->setMedia(QUrl::fromLocalFile(musicFullName));//设置播放器的媒体文件
player->play();//开始播放
//列表显示同步
changeList();//调用changeList函数
}
else{
playNow = generateRandomNumber();
QString musicFullName = listWidget->item(playNow)->data(Qt::UserRole).toString(); //获得用户数据,也就是因为文件全名,可以送到播放器播放
player->setMedia(QUrl::fromLocalFile(musicFullName));//设置播放器的媒体文件
player->play();//开始播放
//列表显示同步
changeList();//调用changeList函数
}
}
}
//随机数产生
int MyMainWindow:: generateRandomNumber()
{
int playRandom;
QRandomGenerator(QTime(0,0,0).secsTo(QTime::currentTime()));
do{
playRandom =qrand()%listWidget->count();
}
while(playNow == playRandom);
return playRandom;
}
void MyMainWindow::sliderPressedEvent()
{
disconnect(player, &QMediaPlayer::positionChanged, this, &videoPositionChanged);
}
void MyMainWindow::startButtonEvent()
{
if(flag == 0){
player->play();//开始播放
QPixmap startIcon(tr("play2.png"));
startButton->setIcon(startIcon);
flag = 1;
}
else if(flag == 1){
player->pause();//暂停播放
QPixmap pauseIcon(tr("play4.png"));
startButton->setIcon(pauseIcon);
flag = 0;
}
}
void MyMainWindow::sliderReleasedEvent()
{
player->setPosition(slider->value());
connect(player, &QMediaPlayer::positionChanged, this, &videoPositionChanged);
}
void MyMainWindow::sliderMovedEvent()
{
timeLabel->setText(QString::number(slider->value()/1000/60)); //显示调整进度(分钟)
}
void MyMainWindow:: openFile()
{
//打开文件选择对话框,过滤器选择mp4,mkv,avi等视频文件
QString fileFullName = QFileDialog::getOpenFileName(this, "Open File", "","Videos(*.mp4 *.mkv *.avi *.wmv *.mov *.mpg *.rm *.rmvb);;All files (*.*)");
if (fileFullName=="") return;//如果没有选择文件,返回。
player->setMedia(QUrl::fromLocalFile(fileFullName));//设置播放器的媒体文件
player->play();//开始播放
view->fitInView(view->videoItem, Qt::KeepAspectRatio); //将视频项保持纵横比缩放到和视图窗口一样大小。
}
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
MyMainWindow mainWindow;
mainWindow.show();
mainWindow.setGeometry(40,40,1800,1000);//位置
//程序启动时接收的参数字符串列表,中文也自动转换为Unicode格式
QStringList args = QApplication::arguments();
int argsSize = args.size();//获得列表中的字符串个数
if (argsSize>1) //args[0]是程序名,如果字符串个数超过1,表示main函数有参数输入
{
mainWindow.player->setMedia(QUrl::fromLocalFile(args[1]));//将args[1]参数设置为媒体源
mainWindow.player->play();//调用mainWindow窗口中的公用成员player播放媒体文件
mainWindow.songName->setText(args[1]);//将args[1]设置为主窗口公用成员label的显示文本
}
return app.exec();
}
QMenu *fileMenu=new QMenu("File");
//为fileMen添加一个菜单项,有图标和点击时的处理函数openFile();
fileMenu->addAction(QPixmap("open.png"), "OpenVideo", this, &openFile);
fileMenu->addAction(QPixmap("open.png"), "OpenMusic", this, &openMusic);
menuBar->addMenu(fileMenu); //将fileMenu菜单添加到菜单栏
将按钮与函数做一个connect,实际上这里打开文件管理器是通过QFileDialog::getOpenFileName实现的,而不是直接与menu联系起来的。
void MyMainWindow:: openMusic()
{
//打开文件选择对话框,过滤器选择mp3,flac,ape音乐文件,或者所有文件。
QString fileFullName = QFileDialog::getOpenFileName(this, "Open Music", "","Music(*.mp3 *.flac *.ape);;All files (*.*)");
listWidget是一个列表窗口,实例化后是一个自成体系的组件,主要由list->item构成内部,各种操作也是通过对item的操作来进行的。
在播放器中主要
1.list图标和背景改变以达到歌曲切换的效果
for (int i=0; i<listWidget->count(); i++)//遍历列表框的所有项,设置背景色和前景色,更改图标
{
listWidget->item(i)->setForeground(QColor(0, 0, 0));
listWidget->item(i)->setBackground(QColor(255, 255, 255));
listWidget->item(i)->setIcon(QPixmap("MultiMedia 32p-3.ico"));
}
先把所有的列表都都变统一
QListWidgetItem *item=new QListWidgetItem; //定义列表项
item->setForeground(QColor(255, 0, 0));
item->setBackground(QColor(0, 255, 0));
item->setIcon(QPixmap("play2.png"));
item->setText(fileName);//设置显示文本,比如显示歌名
item->setData(Qt::UserRole, fileFullName);
再把正在播放的那个变成独特的
2.list双击,这个在下面详细说
这个很简单,slider组件是自动检测正在播放的音频文件的,都不用你多做,系统自动带着的功能
//滑动条最大值
void MyMainWindow::durationChanged(double duration)
{
slider->setMaximum(duration); //设置滑动条最大值
}
//进度条实时变化
void MyMainWindow::videoPositionChanged(double position) //播放器进度信号的处理函数
{
slider->setValue(position); //播放器进度改变时,更改滑动条上滑块的位置显示进度。
}
这个也很简单,QStringList filenames=QFileDialog::getOpenFileNames(this, “Open File”, “”,"Music(.mp3 .flac .ape);;All files (.)");*
打开文件时,按ctrl键来多选文件
QStringList filenames=QFileDialog::getOpenFileNames(this, "Open File", "","Music(*.mp3 *.flac *.ape);;All files (*.*)");
for (int i=0; i<filenames.count(); i++){
QFileInfo fileInfo(filenames.at(i));
QString fileName = fileInfo.fileName();
QListWidgetItem *item=new QListWidgetItem; //定义列表项
item->setIcon(QPixmap("MultiMedia 32p-3.ico")); //设置列表项图标
item->setText(fileName);//设置显示文本,比如显示歌名
item->setData(Qt::UserRole, filenames.at(i));
listWidget->addItem(item);//添加列表项到列表框
}
非常巧妙,一个键控制播放暂停,一看就懂
就是设置一个标志变量:flag,按下暂停按钮置为0,按下开始按钮置为1,其实这里只有一个按钮,两个不同是icon设置不同而已。
//播放暂停
void MyMainWindow::startButtonEvent()
{
if(flag == 0){
player->play();//开始播放
QPixmap startIcon(tr("play2.png"));
startButton->setIcon(startIcon);
flag = 1;
}
else if(flag == 1){
player->pause();//暂停播放
QPixmap pauseIcon(tr("play4.png"));
startButton->setIcon(pauseIcon);
flag = 0;
}
}
也很简单,slider默认的是内存字节大小,先除以1000,换成60进制的。
QString::number(),数字转字符串
//滑动条最大值
void MyMainWindow::durationChanged(double duration)
{
slider->setMaximum(duration); //设置滑动条最大值
int min = duration/1000/60;//分钟
int s = (duration/1000/60 - min)*60;//秒数
QString durationText = QString::number(min)+":"+QString::number(s);//durationlabel显示内容
durationLabel->setText(durationText); //媒体总长度(分钟)
durationLabel->setAlignment(Qt::AlignCenter | Qt::AlignHCenter);
durationLabel->setStyleSheet("background-color:rgb(248,244,237);""color:rgb(20,145,168);");
durationLabel->setWordWrap(true);//Label内容换行
}
//进度条实时变化
void MyMainWindow::videoPositionChanged(double position) //播放器进度信号的处理函数
{
slider->setValue(position); //播放器进度改变时,更改滑动条上滑块的位置显示进度。
int min = position/1000/60;//分钟
int s = (position/1000/60 - min)*60;//秒数
QString positionText = QString::number(min)+":"+QString::number(s);//进度label显示内容
if(min == 0){
positionText = QString::number(s);
}
timeLabel->setText(positionText); //当前播放进度
timeLabel->setAlignment(Qt::AlignCenter | Qt::AlignHCenter);
timeLabel->setStyleSheet("background-color:rgb(248,244,237);""color:rgb(20,145,168);");
timeLabel->setWordWrap(true);//Label内容换行
}
这个利用的是listWidget的自动传参功能,双击传给函数一个参数:被双击的这个item,然后进行操作,怎么实现播放呢。
1.要保证几种途径添加到列表的歌曲setData要有,也就是要知道文件的地址。
2.双击后,传递item的同时,传递了item的data
3.将item的data设置成播放的源。
void MyMainWindow::listWidgetItemActivated(QListWidgetItem *activatedItem)
{
QString musicFullName = activatedItem->data(Qt::UserRole).toString(); //获得用户数据,也就是因为文件全名,可以送到播放器播放
player->setMedia(QUrl::fromLocalFile(musicFullName));//设置播放器的媒体文件
player->play();//开始播放
QFileInfo fileInfo(musicFullName); //创建文件信息类对象fileInfo
QString fileName=fileInfo.fileName(); //从fileInfo中获得文件名(无路径)
}
上一曲和下一曲功能的实现核心是知道现在播放的位置
因为我们这个软件播放的实现有两种情况
1.通过file这个menu打开文件播放,这种情况是添加在list末尾,所以palyNow的值是list.count().
2.双击播放,这时候playNow的值是 activateItem.At(n).
这样就好办了,上一曲和下一曲不过是将播放器的播放源设置成list(playNow+/-1).data即可
其中注意的是,首尾;两个位置需要置首或回到末尾。
这个类比播放暂停,也是一个按钮三个功能,1、2、3数字的变化对应三种下一曲的playNow的取值
其中比较麻烦的是随机模式,随机数的取法在qt下比较麻烦
QRandomGenerator(QTime(0,0,0).secsTo(QTime::currentTime()));
实现的种子的改变,随着时间变化而变化,否则这个种子不变会产生相同的随机数
do while的好处是可以先得到一个判断值,如果先判断的话就得先确定一个值。
在这里do while,先do出来一个随机数,这样while就好添加判断条件了。
如果用while的话,不知道怎么写。
//随机数产生
int MyMainWindow:: generateRandomNumber()
{
int playRandom;
QRandomGenerator(QTime(0,0,0).secsTo(QTime::currentTime()));
do{
playRandom =qrand()%listWidget->count();
}
while(playNow == playRandom);
return playRandom;
}
得到随机数随机模式也好办了
//播放模式改变,仅改变值,播放让状态函数变化
void MyMainWindow::changeMode(){
if (Mode == 1)
{
Mode++;
playMode->setIcon(QPixmap("Loop.png"));
}
else if(Mode == 2)
{
Mode++;
playMode->setIcon(QPixmap("Random.png"));
}
else{
Mode = 1;
playMode->setIcon(QPixmap("Sequential.png"));
}
}
前面这个函数只负责控制按钮的样子,以及给出mode编号1,2,3,他们在按钮按下时的改变关系。
//利用自带的函数来做1.顺序直接用nextMusic,2.循环不改变playNow3.随机,palyNow取1-list.count的随机数
void MyMainWindow:: mediaStatusChanged(QMediaPlayer::MediaStatus status)
{
if (status == QMediaPlayer::InvalidMedia) //无法播放媒体文件,输出错误信息
{
inputInformation();
}
else if (status == QMediaPlayer::EndOfMedia) //当前文件播放结束,播放下一首?
{
if (Mode == 1){
nextMusic();
}
else if(Mode == 2){
QString musicFullName = listWidget->item(playNow)->data(Qt::UserRole).toString(); //获得用户数据,也就是因为文件全名,可以送到播放器播放
player->setMedia(QUrl::fromLocalFile(musicFullName));//设置播放器的媒体文件
player->play();//开始播放
//列表显示同步
changeList();//调用changeList函数
}
else{
playNow = generateRandomNumber();
QString musicFullName = listWidget->item(playNow)->data(Qt::UserRole).toString(); //获得用户数据,也就是因为文件全名,可以送到播放器播放
player->setMedia(QUrl::fromLocalFile(musicFullName));//设置播放器的媒体文件
player->play();//开始播放
//列表显示同步
changeList();//调用changeList函数
}
}
}
这里很关键的一个:
void MyMainWindow:: mediaStatusChanged(QMediaPlayer::MediaStatus status)
{
if (status == QMediaPlayer::InvalidMedia) //无法播放媒体文件,输出错误信息
{
inputInformation();
}
else if (status == QMediaPlayer::EndOfMedia) //当前文件播放结束,播放下一首?
{
}
}
这个和slider一样,自动检测你的文件播放状态,我们的播放模式是在下一曲切换歌曲的时候起作用的,这里也是,结合这个做到播放模式变换的功能。
顺序播放:直接nextMusic函数
随机播放:把随机数传递过去,作为playNow。
循环,每次都playNow
int main(int argc, char *argv[])
{
QApplication app(argc, argv);
MyMainWindow mainWindow;
mainWindow.show();
mainWindow.setGeometry(40,40,1800,1000);//位置
//程序启动时接收的参数字符串列表,中文也自动转换为Unicode格式
QStringList args = QApplication::arguments();
int argsSize = args.size();//获得列表中的字符串个数
if (argsSize>1) //args[0]是程序名,如果字符串个数超过1,表示main函数有参数输入
{
mainWindow.show();
mainWindow.setGeometry(40,40,1800,1000);//位置
mainWindow.player->setMedia(QUrl::fromLocalFile(args[1]));//将args[1]参数设置为媒体源
mainWindow.songName->setText(args[1]);//将args[1]设置为主窗口公用成员label的显示文本
//打开文件选择对话框,过滤器选择mp3,flac,ape音乐文件,或者所有文件。
mainWindow.startButton->setIcon(QPixmap ("play2.png"));//按钮设置成开始的样子
mainWindow.player->play();//开始播放
QFileInfo fileInfo(args[1]); //创建文件信息类对象fileInfo
QString fileName=fileInfo.fileName(); //从fileInfo中获得文件名(无路径)
for (int i=0; i<mainWindow.listWidget->count(); i++)//遍历列表框的所有项,设置背景色和前景色,更改图标
{
mainWindow.listWidget->item(i)->setForeground(QColor(0, 0, 0));
mainWindow.listWidget->item(i)->setBackground(QColor(255, 255, 255));
mainWindow.listWidget->item(i)->setIcon(QPixmap("MultiMedia 32p-3.ico"));
}
QListWidgetItem *item=new QListWidgetItem; //定义列表项
item->setForeground(QColor(255, 0, 0));
item->setBackground(QColor(0, 255, 0));
item->setIcon(QPixmap("play2.png"));
item->setText(fileName);//设置显示文本,比如显示歌名
item->setData(Qt::UserRole, QUrl::fromLocalFile(args[1]));
mainWindow.listWidget->addItem(item);//添加列表项到列表框
mainWindow.songName->setText(fileName);
mainWindow.playNow = mainWindow.listWidget->count() - 1;
}
return app.exec();
}
就是打开方式应该是操作系统传一个参数args【1】过来,这个参数里是文件地址,然后在main函数里对这个文件全名处理就可以了。
编译器选项添加指令-mwindow
qt发布exe多简单啊
CPP和EXE文件单独放一个目录下,然后打开CPP文件,在dev c++界面上点击Tools菜单,然后选择prompt command,打开一个黑方框窗口,在此窗口下输入Windeployqt LiBinMusic.exe就可以产生安装所需文件包。
不然播放不了flac等文件,只能播放mp3
http://codecguide.com/download_kl.htm
大家到以上网站下载音视频解码器,安装过程中针对各种选项全部回车即可。