Visual Basic - Multimedia Programming
Multimedia Programming can be done in two ways; using Multimedia Control or by using various API’s. We shall concentrate more on using Multimedia Control in this article so that we can do justice with it. Brief information about implementing through API is given at the end of the article.
Microsoft Multimedia Control
There are various controls that help us implement Multimedia Programming in Visual Basic. Some of them which we shall cover here are
· Microsoft Multimedia Control and
· Windows Media Player
To add these controls in our application, select them from Project à Components. Let us explore the Microsoft Multimedia Control which appears as shown in Figure 1. We can change the properties of this control as per the function that we wish to do through this control.
Figure 1: Microsoft Multimedia Control
The first task with this control is to select a device on which we need to operate. This is controlled using DeviceType property of the control. This property defines the multimedia type the control will support. The DeviceType property can accept various strings in Table 1.
Table 1: Strings for DeviceType
Strings for DeviceType |
We can set this property dynamically through code by writing,
MMControl1.DeviceType=“WaveAudio”
However, we need to open the device first and then use it.
MMControl1.Command=“Open”
Sometimes, Device automatically gets initiated and hence DeviceType definition is not required. |
AVIVideo |
|
CDAudio |
|
DAT |
|
Digital Video |
|
MMMovie |
|
Scanner |
|
Sequencer |
|
VideoDisc |
|
WaveAudio |
We shall understand the concept of Multimedia Control with this application developed by us. This application supports WAV, MIDI, MP3, AVI and MPEG formats of Files.
Figure 2: Multimedia Control Software
Initially we target at opening file from a desired type of files.
Dim strmode, song As String
Private Sub mnuOpen_Click()
CommonDialog1.Filter = "WAV Files (*.wav)|*.wav|" & "MP3 Files (*.mp3)|*.mp3|" & "Video Files (*.avi)|*.avi|" & "MIDI Files (*.mid)|*.mid|" & "MPEG Files (*.mpg)|*.mpg|"
CommonDialog1.ShowOpen
song = CommonDialog1.FileName
MMControl1.TimeFormat = mciFormatMilliseconds
MMControl1.FileName = song
StatusBar1.Panels(2).Text = strmode
StatusBar1.Panels(4).Text = song
If UCase(Right$(CommonDialog1.FileName, 3)) = "AVI" or & UCase(Right$(CommonDialog1.FileName, 3)) = "MPG" Then
Me.Width = 13725
Me.Height = 8565
MMControl1.hWndDisplay = Picture1.hWnd
Else
Me.Width = 4425
Me.Height = 5895
End If
MMControl1.Command = "Open"
End Sub
In the above piece of code we set the time format in MilliSeconds by using TimeFormat property. This property accepts other formats as mentioned in Table 2.
Table 2: TimeFormat Strings
TimeFormat String |
Equivalent Code |
Interpretation |
mciFormatHms |
1 |
Hours, Min and Seconds. This data is combined to form a 4-byte integer in same order* |
mciFormatMsf |
2 |
Minutes, Seconds, Frames This data is combined to form a 4-byte integer in same order |
mciFormatFrames |
3 |
Frames are stored to form a 4-byte integer. |
mciFormatSmpte24 |
4 |
24-frame SMPTE packed data in 4 byte variable in order of Hours, Minutes, Seconds and Frames |
mciFormatSmpte25 |
5 |
25-frame SMPTE packed data in 4 byte variable in order of Hours, Minutes, Seconds and Frames |
mciFormatSmpte30 |
6 |
30-frame SMPTE packed data in 4 byte variable in order of Hours, Minutes, Seconds and Frames |
mciFormatSmpte30Drop |
7 |
30Drop-frame SMPTE packed data in 4 byte variable in order of Hours, Minutes, Seconds and Frames |
mciFormatBytes |
8 |
Bytes are stored in 4-byte integer variable |
mciFormatSamples |
9 |
Samples are stored as 4-byte integer variable |
mciFormatTmsf |
10 |
Tracks, Minutes, Seconds and Frames are combined in 4-byte variable in same order. |
*Here order means from Least Significant Byte(LSB) to Most Significant Byte(MSB)
The second part which is important is viewing of pictures in AVI or MPEG files. This is done using handles of Picture Box. We connect the Multimedia Control and Picture Box using hWnd Property of PictureBox and placing the handle in the Multimedia Control’s hWndDisplay property.
We leave an exercise to think over usage of Image Control instead of PictureBox. Can you predict why we can not use an Image Control? An Image control doesn’t have hWnd Property so that you can access the frames of the Picture being played by Multimedia Control.
Private Sub MMControl1_StatusUpdate()
Select Case MMControl1.Mode
Case mciModeReady
strmode = "Ready."
Case mciModeStop
strmode = "Stopped."
Case mciModeSeek
strmode = "Seeking."
Case mciModePlay
strmode = "Playing."
Case mciModeRecord
strmode = "Recording."
Case mciModePause
strmode = "Paused."
End Select
lblLength.Caption = Str(MMControl1.Length / 10)
lblPos.Caption = Str(MMControl1.Position / 10)
StatusBar1.Panels(2).Text = strmode
StatusBar1.Panels(4).Text = song
ProgressBar1.Max = Val(lblLength.Caption)
ProgressBar1.Value = Val(lblPos.Caption)
End Sub
When a song or movie is being played, the mode of Multimedia Control (MMControl1) keeps changing. Various modes are checked in the above function and the status is updated in the StatusBar1. The Length of the track is determined by Length property, while the current position of track is known by Position property.
After the song or movie is played, we need to check if there were any errors during execution. To check this, we initially set the Notify property to True. By this property, as soon as the song is completed the Done Function of Control is executed.
Private Form_Load()
MMControl1.Notify = True
End Sub
Private Sub MMControl1_Done(NotifyCode As Integer)
If MMControl1.Error <> 0 Then
MsgBox MMControl1.ErrorMessage
End If
End Sub
To add few more facilities, we write a code that will enhance our application by using various tools like Next, Stop, Pause and so on…
Private Sub MMControl1_StopClick(Cancel As Integer)
MMControl1.Command = "Stop"
End Sub
Private Sub MMControl1_NextClick(Cancel As Integer)
MMControl1.Command = "Next"
End Sub
Private Sub MMControl1_PauseClick(Cancel As Integer)
MMControl1.Command = "Pause"
End Sub
Private Sub MMControl1_PlayClick(Cancel As Integer)
MMControl1.Command = "Play"
End Sub
Private Sub MMControl1_PrevClick(Cancel As Integer)
MMControl1.Command = "Previous"
End Sub
Let’s take an example where we wish to start the song after 2 minutes and till 10 minutes. For that we use Form and To property. The calibration of time needs to be done according to the format of TimeFormat as shown in code below
Private Sub cmdPlay_Click()
MMControl1.TimeFormat = mciFormatMilliSeconds
MMControl1.From = 2 ‘Start Time
MMControl1.To = 10 ‘End Time
MMControl.Command = “Play”
End Sub
To move the Control Forward or Backward, we can use the Step and Back Multimedia Control Commands to step through animations frame by frame by the number of frames set in the Frames Property. To check the availability of connection with the device, we use CanStep Property as shown below:
Private Sub cmdFWD_Click()
If MMControl1.CanStep Then
MMControl1.Frames = 1 ‘One Frame Ahead
MMControl1.Command = “Step”
End If
End Sub
Private Sub cmdBACK_Click()
If MMControl1.CanStep Then
MMControl1.Frames = 1 ‘One Frame Back
MMControl1.Command = “Back”
End If
End Sub
Windows Media Player
Let’s implement Multimedia Programming using Windows Media Player Control. We first add the Control through Project Menu à Components à Windows Media Player.
We shall develop one more application program and understand the working of this control. The application after designing shall appear as shown below.
Figure 3: Windows Media Player Control
The application aims at creation of playlist and playing files in that order. The reader requires knowledge of File Management which we covered in the previous articles (December 2005 Issue). The playlist is stored in a text file c:\Playlist.txt and if the file is not empty, the list is loaded in a list box. So, when the application starts, the first target is to load Playlist. In order to have status as global through out our program, we define few variables allowplay, paused and allowpause.
Dim allowplay As String
Dim paused, allowpause As Boolean
Private Sub Form_Load()
allowpause = False
Dir1.path = Drive1.Drive
paused = False
On Error Resume Next
If FileLen("c:/PlayList.txt") = 0 Then
Open "c:/PlayList.txt" For Output As #1
Close #1
End If
Open "c:/PlayList.txt" For Input As #1
Do Until EOF(1)
Input #1, playlistitem
lstSelectedEntries.AddItem playlistitem
Loop
Close #1
allowplay = "no"
End Sub
The Control MediaPlayer1 has an in-built function Pause. When New Stream is loaded, AllowPause is made True. This condition is checked here, and if this is satisfied it further checks if previously Pause button is pressed (by condition on variable paused). If previously Pause was pressed, it means the user intends to play the Stream which is coded in second part of the function
Private Sub cmdPause_Click()
If allowpause = True Then
On Error Resume Next
‘If pause was not pressed previously, Pause the song.
If paused = False Then
MediaPlayer1.Pause
paused = True
allowplay = "no"
Exit Sub
End If
‘If pause was previously pressed, Play the Song
If paused = True Then
MediaPlayer1.Play
paused = False
allowplay = "yes"
End If
End If
End Sub
Let’s understand the fundamental of Play Button. When Play Button is pressed, it plays the songs only if either the song is in pause mode or a selected song is to be played. Suppose a song is being played or is in Pause Condition. If in such a situation, user selects another song and presses Play Button then the newly selected song should be played. This logic is implemented in the second half of the code written below:
Private Sub cmdPlay_Click()
If paused = True Then ‘If previously paused, then Play
MediaPlayer1.Play
paused = False
allowplay = "yes"
Exit Sub
End If
If paused = False Then ‘If previously Playing, then play the selected song, which may no always be the one currently played.
MediaPlayer1.Open txtSelected.Text
lblSec = "0" ‘The display timers are reset to 0:00
lblMin = "0"
lblSec2 = "0"
Exit Sub
End If
End Sub
Stop Button has a very simple logic. When Stop Button is pressed, MediaPlayer1 Control should stop the song, the displayed timers as well as the actual timer (controlled by allowplay variable) should be reset.
Private Sub cmdStop_Click()
MediaPlayer1.Stop
allowplay = "no"
lblSec = "0"
lblMin = "0"
lblSec2 = "0"
allowpause = False
End Sub
The Timer Control used here has an interval of 1 second. As time elapses, the same needs to be displayed on screen using 3 labels; one to display minute (assuming no song is greater than 9 minutes) and two for seconds.
Private Sub Timer1_Timer()
If allowplay = "yes" Then
If lblSec = "9" Then
lblSec = "0"
lblSec2 = lblSec2 + 1
If lblSec2 = "6" Then
lblSec2 = "0"
lblMin = lblMin + 1
End If
Else
lblSec = lblSec + 1
End If
End If
End Sub
What happens when a new stream is opened or a stream ends? Two functions are activated. They are NewStream and EndOfStream. These functions should first reset the timer. The functions can be coded as shown:
Private Sub MediaPlayer1_NewStream()
lblSec = "0"
lblSec2 = "0"
lblMin = "0"
allowplay = "yes"
allowpause = True
End Sub
Private Sub MediaPlayer1_EndOfStream(ByVal Result As Long)
allowplay = "no"
lblSec = "0"
lblSec2 = "0"
lblMin = "0"
allowpause = False
End Sub
The application still appears to be raw as one needs to click on Import Button to transfer the file to Playlist and again Click on Play Button to play it. We add some flexibility in our program. A double click on a song in Playlist will play the song.
Private Sub lstSelectedEntries_Click()
txtSelected.Text = lstSelectedEntries.Text
End Sub
Private Sub lstSelectedEntries_DblClick()
txtSelected.Text = lstSelectedEntries.Text
MediaPlayer1.Stop
lblSec = "0"
lblMin = "0"
lblSec2 = "0"
MediaPlayer1.Open txtSelected.Text
End Sub
Private Sub lstSelectedEntries_KeyPress(KeyAscii As Integer)
txtSelected.Text = lstSelectedEntries.Text
End Sub
And finally, our application is ready to use.
Multimedia Through API
We just covered the concepts of API in our previous article in this issue. So we would just brief you with the API function and we leave the programming part to you because it is yet another simple way to do multimedia programming.
A song or music can be played using PlaySound function from winmm.dll. The syntax of the function is
Public Declare Function PlaySound Lib "winmm.dll" Alias "PlaySoundA" (ByVal lpszName As String, ByVal hModule As Long, ByVal dwFlags As Long) As Long
There’s something to observe in the above syntax. The actual name of the function is PlaySoundA. The difference is PlaySound and PlaySoundA is that the latter uses ANSI text strings. We are here just interested in knowing the values of dwFlags.
dwFlag Value |
Interpretation |
&H0 |
Play sound synchronously |
&H1 |
Play sound asynchronously |
&H2 |
If no sound is found, silence is not default |
&H4 |
lpszName points to a memory file |
&H8 |
Loop until next PlaySound |
&H10 |
Don’t stop any currently playing sound |
An example to use this function is
Private Sub cmdPlay_Click()
PlaySound(song, 0&, &H0)
End Sub