c#—如何借助windows media player控件编写播放器

windows media player控件的常用属性和方法

以下 music player 均为windows media player控件的名字。
1.属性
 1)musicPlayer.settings.autoStart:打开播放器时是否自动播放 。true:自动播放,false:不自动播放,默认自动播放。
 2)musicPlayer.URL:要播放歌曲的路径。
 3)musicPlayer.settings.mute:是否静音。true:静音,false:不静音。
 4)musicPlayer.settings.volume:音量值大小,范围是1~100。
 5)musicPlayer.Ctlcontrols.currentPositionString:当前播放时间。返回值是字符串类型,例如:02:23。
 6)musicPlayer.Ctlcontrols.currentPosition:也是返回当前播放的时间。返回值是 double 类型,例如:133.8。
 7)musicPlayer.currentMedia.name:返回当前播放歌曲的名字。
 8)musicPlayer.playState:播放器当前的状态。
  有一个枚举 WMPLib.WMPPlayState 说明了它的取值:
  0——wmppsUndefined:未知状态
  1——wmppsStopped:播放停止
  2——wmppsPaused:播放暂停
  3——wmppsPlaying:正在播放
  4——wmppsScanForward:向前搜索
  5——wmppsScanReverse:向后搜索
  6——wmppsBuffering :正在缓冲
  7——wmppsWaiting:正在等待流开始
  8——wmppsMediaEnded:播放流已结束
  9——wmppsTransitioning :准备新的媒体文件
  10——wmppsReady:播放准备就绪
  11——wmppsReconnecting:尝试重新连接流媒体数据
  12——wmppsLast:上一次状态,状态没有改变

2.方法
 1)musicPlayer.Ctlcontrols.play():播放
 2)musicPlayer.Ctlcontrols.pause():暂停
 3)musicPlayer.Ctlcontrols.stop():停止

编写播放器

1.第一步:先拖一个windows media player控件,再拖一个 listbox 用来存放歌曲名字。一个按钮,点击按钮的时候显示文件对话框。选择音乐文件后,将音乐的名字添加到 listbox 中。

//设置文件对话框
OpenFileDialog ofd = new OpenFileDialog();
ofd.Title = "请选择音乐";
ofd.InitialDirectory = @"E:\计算机资料\项目\03 CS学习\03 C#例子\【04】\04\4-4\歌曲";
ofd.Filter = "(*.mp3)|*.mp3";
ofd.Multiselect = true;
if (ofd.ShowDialog() == DialogResult.OK)
{
    //存放歌曲路径,需定义一个string[]数组或list泛型集合
    path = ofd.FileNames;
    for (int i = 0; i < path.Length; i++)
    {
        //截取歌曲名字
        string musicName = path[i].Substring(path[i].LastIndexOf('\\') + 1);
        //向listbox中添加歌曲名字
        listBox1.Items.Add(musicName);
    }
    //默认选择为第1项
    listBox1.SelectedIndex = 0;
    musicPlayer.URL = path[listBox1.SelectedIndex];
}

2.第二步:设置播放暂停按钮。

if (btnPlay.Text == "播放")
{
    musicPlayer.Ctlcontrols.play();
    btnPlay.Text = "暂停";
}
else
{
    musicPlayer.Ctlcontrols.pause();
    btnPlay.Text = "播放";
}

3.第三步:添加播放上一曲、下一曲按钮。

//播放下一曲
int index = listBox1.SelectedIndex;
index++;            
if (index == path.Length)
{
    index = 0;
}
listBox1.SelectedIndex = index;
musicPlayer.URL = path[index];
musicPlayer.Ctlcontrols.play();
//播放上一曲
int index = listBox1.SelectedIndex;
index--;
if (index < 0)
{
    index = path.Length-1;
}
listBox1.SelectedIndex = index;
musicPlayer.URL = path[index];
musicPlayer.Ctlcontrols.play();

4.第四步:音量加减、是否静音。拖两个按钮,来控制上一首、下一首。拖一个 picturebox 控件,点击它来控制是否静音。

//音量+
musicPlayer.settings.volume += 5;

//音量-
musicPlayer.settings.volume -= 5;

//静音
if (picVolume.Tag.ToString() == "1")
{
    musicPlayer.settings.mute = true;
    picVolume.Image = Image.FromFile("路径");
    picVolume.Tag = "2";
}
else
{
    musicPlayer.settings.mute = false;
    picVolume.Image = Image.FromFile("路径");
    picVolume.Tag = "1";
}

5.显示当前播放时间和歌词。拖一个 timer 控件,在 timer 控件里让当前播放时间和歌词显示在 label 控件上。
显示当前播放时间很容易,用 musicPlayer.Ctlcontrols.currentPositionString 属性就可以了,但是歌词略微有点儿麻烦。首先得有歌词,其次将歌词文件中的内容读取出来后,还要将歌词分割,将歌词补充完整,最后再进行排序。
c#—如何借助windows media player控件编写播放器_第1张图片
什么意思呢?比如上图中的歌词有一些重复的歌词内容,需要按时间分割整行歌词,然后再在每个时间后面都加上个歌词内容,保存到一个list泛型集合中,最后再对他们排序,这才是完整的歌词。

//切割歌词的方法
private List<string> FormatLrc()
{
    List<string> list = new List<string>();
    //遍历歌词
    for (int i = 0; i < listSongLrc.Count; i++)
    {
        //切割歌词
        string[] strSongLrc = listSongLrc[i].Split(new char[] { '[', ']' }, StringSplitOptions.RemoveEmptyEntries);
        //如果数组长度大于1,则表明时间后有歌词
        if (strSongLrc.Length>1)
        {
            for (int j = 0; j < strSongLrc.Length-1; j++)
            {
                list.Add(strSongLrc[j] + "|" + strSongLrc[strSongLrc.Length - 1]);
            }
        }
    }
    //歌词排序,冒泡排序法
    for (int i = 0; i < list.Count-1; i++)
    {
        for (int j = 0; j < list.Count-1-i; j++)
        {
            if (string.Compare(list[j],list[j+1])>0)
            {
                string temp = list[j];
                list[j] = list[j + 1];
                list[j + 1] = temp;
            }
        }
    }
    return list;
}
//timer事件,显示当前播放时间和歌词
private void timer1_Tick(object sender, EventArgs e)
{
    //显示播放时间和歌曲名字
    if (musicPlayer.currentMedia != null)
    {
        labTime.Text = musicPlayer.Ctlcontrols.currentPositionString;
        labMusicName.Text = musicPlayer.currentMedia.name;
    }
    //显示歌词
    if (listLrcPath.Count > 0 && musicPlayer.currentMedia != null)
    {
        for (int i = 0; i < listSongLrc.Count; i++)
        {
            //如果当前播放时间超过了歌词中的某个时间,就显示该时间后的歌词
            if (string.Compare(musicPlayer.Ctlcontrols.currentPositionString, listSongLrc[i]) > 0)
            {
                lblLrc.Text = listSongLrc[i].Split('|')[1];
            }
        }
    }
}        

6.自动播放下一曲
实现自动播放下一曲的原理:当播放完一首歌的时候,播放器的播放状态变为 Ended,按照正常的状态变换,是这样的的:Ended –> Transtioning –> stopped。而在变成 Ended 状态之后,将下一曲的歌曲路径传给播放器,状态就变为了:Transtioning –> Ready,然后调用 play 方法,就实现了自动播放下一曲。

//状态改变事件
private void musicPlayer_PlayStateChange(object sender, AxWMPLib._WMPOCXEvents_PlayStateChangeEvent e)
{
    //歌曲播放完,变换索引
    if (musicPlayer.playState == WMPLib.WMPPlayState.wmppsMediaEnded)
    {
        int index = listBox1.SelectedIndex;
        if (index == path.Length - 1)
        {
            index = 0;
        }
        else
        {
            index++;
        }
        listBox1.SelectedIndex = index;
    }
    if (musicPlayer.playState == WMPLib.WMPPlayState.wmppsReady)
    {
        try
        {
            musicPlayer.Ctlcontrols.play();
            btnPlay.Text = "暂停";
        }
        catch
        {

        }
    }
}

★解释一下为什么是在 ready 状态之后,调用播放方法?
 因为在播放之前必须得给 musicplayer 一个歌曲路径,否则无法播放,而当路径改变的时候会经历两个状态:Transitioning –> Ready,也就是说只有在 Ready 状态时,才会把路径传给 musicplayer ,所以播放方法得在 Ready 状态中。

★以下是windows media player控件播放状态的状态图:
c#—如何借助windows media player控件编写播放器_第2张图片

你可能感兴趣的:(C#)