Click here to Skip to main content
Click here to Skip to main content

MP3 Player for Windows 7

, 1 Feb 2010 CPOL
Rate this:
Please Sign up or sign in to vote.
MP3 player which has Windows 7 features like Progressbar and Thumbnail toolbar
Player.png

Introduction

In this article, we will see how we can develop an MP3 player, using C#.NET, which will use some of the new features of Windows 7.

We will show the progress of the song being played using the "Progress bar" in Taskbar. We will also show the Album art of the song as the "Thumbnail" and we will also have a Thumbnail Toolbar which has the Play/Pause, Next and Previous buttons.

Prerequisites

  1. To play MP3 songs, we will be using the BASS Audio Library.
  2. We will also need Bass.net which is the .NET API for BASS.
  3. TagLib Sharp: We will use this library to read tagging information about the song being played.
  4. Windows® API Code Pack for Microsoft® .NET Framework

Developing the Application

The Player

  1. Create a new project in Visual Studio
  2. Add the existing projects Shell and Core which can be found under the WindowsAPICodePack\shell and WindowsAPICodePack\core folders
  3. Add a reference to the above projects and import the following namespaces:
    • Microsoft.WindowsAPICodePack.Dialogs
    • Microsoft.WindowsAPICodePack.Taskbar
    • Microsoft.WindowsAPICodePack.Shell

The first part of the development is developing the player which will have the basic functionality like Play/Pause, Stop, next Previous/Next and Add/Remove songs Buttons.  The main form in our application has 7 Buttons, A listbox, Label and a Picture Box.

We will use the Picture Box to display the Album Art and we will use the Label to display the seconds remaining while a song is being played.

Note: Make sure you have added references for Core, Shell, Bass.net and taglib-sharp. Also add bass.dll to your project (Make sure you have set "Copy to Output Directory" as "Copy Always".)

Player Class: This class has all the methods which we will be using to play MP3 files. The first step is to initialize an output device. We use Bass.BASS_Init() for this. Following are the parameters:

  1. -1 denotes default device.
  2. 44100 is the frequency.
  3. BASSInit.BASS_DEVICE_DEFAULT denotes th default device to use
  4. System.IntPtr.Zero denotes the application's main window which is the current foreground window.

Before playing a song, we must first create a stream. We use BASS_StreamCreateFile() to create a stream from a file. We then use BASS_ChanelPlay() to play the stream which we created in the LoadSong() function.

class player
    {
        int stream;
        public player()
        {
            Bass.BASS_Init(-1, 44100, BASSInit.BASS_DEVICE_DEFAULT, System.IntPtr.Zero);  
        }
        public void LoadSong(string location)
        {
            stream = Bass.BASS_StreamCreateFile
			(location, 0, 0, BASSFlag.BASS_SAMPLE_FLOAT);
        }

        public void PlaySong()
        {
            Bass.BASS_ChannelPlay(stream,false);
        }

        public void StopSong()
        {
            Bass.BASS_ChannelStop(stream);
        }

        public void PauseSong()
        {
            Bass.BASS_ChannelPause(stream);
        }

        ~player()
        {
            Bass.BASS_Free();
        }
    }		

Song Length and Album Art

Once the player is ready, we will use Taglib sharp to get the length of the song and album art. We will use the picture box to display the album art. We will also use this picture box's location and size to create the Thumbnail. 

Once we create the TagLib file from a file (in this case, the selected item in the playlist listbox), we will use Properties.Duration.TotalSeconds to get the length of the song in seconds. We will be using this value to populate the Label and the set the progressbar value.

private void GetSongLength()
        {
            if (playlist.SelectedItem != null)
            {
                TagLib.File f = TagLib.File.Create(playlist.SelectedItem.ToString());   
                songLength = (int)f.Properties.Duration.TotalSeconds;
            }           
        } 

We will also be using taglib sharp to get the album art of the song which is being currently played. Some songs may not have an Album art so we will use TagLibfile.Tag.Pictures.Length to get the numbers of pictures associated with the song. If it is more than zero, then we load the picture box with the album art.

private void SetAlbumArt()
        {

            if (playlist.SelectedItem != null)
            {
                TagLib.File file = TagLib.File.Create(playlist.SelectedItem.ToString());
                if (file.Tag.Pictures.Length > 0)
                {
                    var bin = (byte[])(file.Tag.Pictures[0].Data.Data);
                    albumart.Image = 
			Image.FromStream(new MemoryStream(bin)).GetThumbnailImage
					(100, 100, null, IntPtr.Zero);

                }
                else
                {
                    albumart.Image = Properties.Resources.gramophone;
                }
            }            
        }

Progressbar, Thumbnail Toolbar and Player Buttons

Create Taskbar buttons and instance of TaskbarManager.

player player;
int playState, songLength, timerCount;
private ThumbnailToolbarButton buttonPlayPause;
private ThumbnailToolbarButton buttonNext;
private ThumbnailToolbarButton buttonPrevious;
TaskbarManager tbManager = TaskbarManager.Instance;
public Form1()
        {
            InitializeComponent();
            player = new player();
            playState = 1;
            songLength = 0;
            timerCount = 1;
        }

This is the main function which will play the song. First we call the SetAlbumArt() function which will set the album art. We use SetTaskBarthumbnail() function to the set the thumbnail. Explanation for this function comes later in this article. We will use GetSongLength() and SetTimerforPlay() to get the song length and activate the timer respectively.

private void PlaySelectedSong()
        {
            SetAlbumArt();
            SetTaskbarthumbnail();
            GetSongLength();
            timerCount = 1;
            SetTimerforPlay();

            if (playlist.SelectedItem != null)
            {
                buttonPlayPause.Icon = Properties.Resources.Pause;
                player.StopSong();
                player.LoadSong(playlist.SelectedItem.ToString());
                player.PlaySong();
                this.Text = playlist.SelectedItem.ToString().Substring
			(playlist.SelectedItem.ToString().LastIndexOf("\\") + 1,
			(playlist.SelectedItem.ToString().Length - 
			(playlist.SelectedItem.ToString().LastIndexOf("\\") + 1)));
            }   
        }
//Play song when the song is double clicked in the Listbox
private void playlist_DoubleClick(object sender, EventArgs e)
        {
            PlaySelectedSong();
        }
private void btnPrevious_Click(object sender, EventArgs e)
        {
            PlayPreviousSong(); 
        }
private void PlayPreviousSong()
        {
            if ((playlist.SelectedIndex - 1) >= 0)
            {
                playlist.SelectedItem = playlist.Items[playlist.SelectedIndex - 1];
                PlaySelectedSong();
            }
        }
private void btnNext_Click(object sender, EventArgs e)
        {
            PlayNextSong();            
        }
private void PlayNextSong()
        {
            if ((playlist.SelectedIndex + 1) < playlist.Items.Count)
            {
                playlist.SelectedItem = 
			playlist.Items[playlist.SelectedIndex + 1];
                PlaySelectedSong();
            }
        }
private void btnAddSong_Click(object sender, EventArgs e)
        {
            if (openFileDialog.ShowDialog() == DialogResult.OK)
            {
                playlist.Items.Add(openFileDialog.FileName);
            }
        }
private void btnRemoveSong_Click(object sender, EventArgs e)
        {
            playlist.Items.Remove(playlist.SelectedItem);
        }

In the below function, we first check whether the song is paused. We use the value of playState for this. Value zero means the song is paused and we use the PlaySong() function to continue playing the song. If the value is not zero, then it denotes that the song should be played from the beginning. In this case, we load the song and then play it.

private void btnPlay_Click(object sender, EventArgs e)
        {
            if (playState == 0)
            {
                //Paused state so start playing
                player.PlaySong();
                playState = 1;
                SetTimerforPlay();
            }
            else
            {
                //Play from Beginning
                PlaySelectedSong();
            }
            buttonPlayPause.Icon = Properties.Resources.Pause;
        }
private void btnPause_Click(object sender, EventArgs e)
        {
            buttonPlayPause.Icon = Properties.Resources.play;
            player.PauseSong();
            playState = 0;
            SetTimerforPause();
        }

This function is called just before playing the song to enable the timer and set the progress bar style. TaskbarProgressBarState.Normal denotes that the progress will be normal. Timer's interval is set as 1000 ms.

//Set progressbar Style and Enable Timer 
private void SetTimerforPlay()
        {
            tbManager.SetProgressState(TaskbarProgressBarState.Normal);
            progressbarTimer.Enabled = true;
        }

This is similar to SetTimerforPlay() but we will disable the timer to stop the progress in the progress bar. At the same time, we will also set its style to TaskbarProgressBarState.Error so that the color is set as Red. This function is called when the song is paused.

private void SetTimerforPause()
        {
            tbManager.SetProgressState(TaskbarProgressBarState.Error);
            progressbarTimer.Enabled = false;
        }
private void btnStop_Click(object sender, EventArgs e)
        {
            player.StopSong();
        }

We will be using TabbedThumbnail.SetThumbnailClip to set the thumbnail for our MP3 player. For this, we create a new Rectangle selection inside the main form and then set it as the thumbnail clip. Our motive is to use the Album art which we have already loaded in the Picture Box. Note: I had to make some adjustments in the Height and Width of the rectangle selection to get a proper thumbnail.

private void SetTaskbarthumbnail()
        {
            TaskbarManager.Instance.TabbedThumbnail.SetThumbnailClip
		(this.Handle,new Rectangle(albumart.Location.X+4,
		albumart.Location.Y,albumart.Size.Width-1,albumart.Size.Height-4));
        }

Thumbnail Toolbar should be created during the Form's Shown event. ThumbnailToolbarButton accepts two parameters:

  1. Icon: The Icon to be used for the button.
  2. Tooltip: The tool tip for the button.

We also add an Event Handler for each of the Button's Click events.

private void Form1_Shown(object sender, EventArgs e)
        {
            buttonPlayPause = new ThumbnailToolbarButton
			(Properties.Resources.play, "Play");
            buttonPlayPause.Enabled = true;
            buttonPlayPause.Click += 
	     new EventHandler<thumbnailbuttonclickedeventargs>(buttonPlay_Click);

            buttonNext = new ThumbnailToolbarButton
			(Properties.Resources.nextArrow, "Next");
            buttonNext.Enabled = true;
            buttonNext.Click += 
	     new EventHandler<thumbnailbuttonclickedeventargs>(buttonNext_Click);

            buttonPrevious = new ThumbnailToolbarButton
			(Properties.Resources.prevArrow, "Previous");
            buttonPrevious.Click += 
	     new EventHandler<thumbnailbuttonclickedeventargs>(buttonPrevious_Click);
            TaskbarManager.Instance.ThumbnailToolbars.AddButtons
		(this.Handle, buttonPrevious, buttonPlayPause, buttonNext);
            TaskbarManager.Instance.TabbedThumbnail.SetThumbnailClip
		(this.Handle, new Rectangle(albumart.Location, albumart.Size));
        }

Thumbnail Toolbars : Play/Pause, Next and Previous Buttons

void buttonPlay_Click(object sender, EventArgs e)
        {
            if (playState == 0)
            {
                player.PlaySong();
                playState = 1;
                buttonPlayPause.Icon = Properties.Resources.Pause;
                buttonPlayPause.Tooltip = "Pause";
                SetTimerforPlay();
            }
            else
            {
                player.PauseSong();
                playState = 0;
                buttonPlayPause.Icon = Properties.Resources.play;
                buttonPlayPause.Tooltip = "Play";
                SetTimerforPause();
            }
        }
void buttonNext_Click(object sender, EventArgs e)
        {
            PlayNextSong();
        }
void buttonPrevious_Click(object sender, EventArgs e)
        {
            PlayPreviousSong();
        }

Progressbar

Timer's interval is set to 1000ms and it will be enabled as soon as the play button is pressed. We use the SongLength to set the maximum value of the progressbar. and increment the progress value every second. Timer will be disabled as soon as the pause button is pressed.

private void progressbarTimer_Tick(object sender, EventArgs e)
        {
            if (timerCount <= songLength)
            {
                tbManager.SetProgressValue(timerCount, songLength);
            }
            lblSeconds.Text = (songLength - timerCount).ToString() + " seconds";
            timerCount += 1;
        }

Player in Action

Play

playing.png

Thumbnail

thumbnail.png

Thumbnail while Paused

ThumbnailPaused.png

Thumbnail while Playing

ThumbnailPlay.png

Progressbar while Paused

paused.png

Conclusion

This is a basic MP3 player which was developed in few hours. The idea was to use progress bar differently. Comments and suggestions are always welcome.

References and Useful Links

History

  • Initial release: 31st January, 2010

License

This article, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)

Share

About the Author

Shoban Kumar
Software Developer (Senior) Allianz Cornhill
India India
Shoban Kumar currently works with Allianz Cornhill India in Trivandrum as a Senior Software Engineer. He is one of the core member of Kerala Microsoft User's Group http://www.k-mug.org.
 
SharePoint Blog : http://allaboutmoss.com
 
He has also written many open source applications which can be found in Codeplex : http://www.codeplex.com/site/users/view/shobankr

Comments and Discussions

 
QuestionErrror PinmemberDamian Darul1-Sep-13 2:51 
GeneralMy vote of 5 PinmemberSad Pencil25-Jul-13 17:16 
QuestionGraphic Equalizers Pinmembergaurav123pareek1-Feb-13 1:40 
Generalhi., thank you Pinmemberullas kishan30-Jan-13 6:21 
GeneralMy vote of 5 PinmemberMario Majčica29-Jan-13 0:04 
QuestionJump list? PinmemberIandavid12326-Jun-12 16:23 
GeneralMy vote of 5 Pinmembervshal5261-Jun-12 2:57 
GeneralMy Vote of 5 PinmemberRaviRanjankr28-Nov-11 9:31 
QuestionYou can ditch that Bass library requirement for my MP3 library PinmemberWong Shao Voon14-Aug-11 16:19 
Questionwhich version of vs? PinmemberMember 778883726-Mar-11 22:04 
GeneralProblem with error 0x8007000B (Solution) PinmemberRiskboy31-Aug-10 10:19 
GeneralRe: Problem with error 0x8007000B (Solution) PinmemberAlonso Calle10-Mar-11 8:54 
GeneralRe: Problem with error 0x8007000B (Solution) PinmemberRiskboy10-Mar-11 10:44 
GeneralRe: Problem with error 0x8007000B (Solution) PinmemberAlonso Calle10-Mar-11 11:58 
GeneralRe: Problem with error 0x8007000B (Solution) PinmemberRiskboy13-Mar-11 1:35 
GeneralRe: Problem with error 0x8007000B (Solution) PinmemberAlonso Calle13-Mar-11 20:23 
GeneralMy vote of 3 Pinmemberkimehi23-Aug-10 6:32 
GeneralProblem with error 0x8007000B PinmemberAnkioSei2-Jul-10 0:49 
GeneralLeft-Right channel changing PinmemberPowR_TocH20-Apr-10 8:56 
GeneralGood work... PinmemberSandeep Mewara13-Mar-10 0:55 
GeneralLooks well but not work in my computer Pinmembernicholas_pei9-Mar-10 17:22 
GeneralRe: Looks well but not work in my computer PinmemberMember 418768911-Mar-10 4:54 
GeneralRe: Looks well but not work in my computer Pinmemberfaraza13-Mar-10 3:50 
GeneralRe: Looks well but not work in my computer Pinmemberach2r15-Mar-10 21:24 
Generalgood player Pinmemberajaykumarpathak25-Feb-10 17:45 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.

| Advertise | Privacy | Terms of Use | Mobile
Web01 | 2.8.141223.1 | Last Updated 2 Feb 2010
Article Copyright 2010 by Shoban Kumar
Everything else Copyright © CodeProject, 1999-2014
Layout: fixed | fluid