Solved

MCI Control, WaveAudio

Posted on 1997-07-22
13
646 Views
Last Modified: 2012-05-04
I can succesfully "Record" "Afile" and subsequently "Play" this file "Afile". The MCI Command "Save" doesn't work.
I want to use the MCI opened file with the Basic command:
Open "Afile" For Binary As #1
and then be able to analyse the content of this file with the usual file I/O coding.
The MCI generated file "Afile" is not recognised by VB4 with  this simple line of code; is there some other way ?
0
Comment
Question by:dand072297
  • 7
  • 6
13 Comments
 

Author Comment

by:dand072297
ID: 1428698
Adjusted points to 300
0
 

Author Comment

by:dand072297
ID: 1428699
I would settle for a solution with mci-api calls.
0
 
LVL 5

Expert Comment

by:y96andha
ID: 1428700
I do not understand your question. What do you want to do? Do you want to load the waveform data into memory so you can process the samples?
0
Windows Server 2016: All you need to know

Learn about Hyper-V features that increase functionality and usability of Microsoft Windows Server 2016. Also, throughout this eBook, you’ll find some basic PowerShell examples that will help you leverage the scripts in your environments!

 

Author Comment

by:dand072297
ID: 1428701
y96andha,
Yes, I want to access waveform data which has just been recorded with mci-api calls (so there is a Filename for this buffer in memory ). The data would be a short burst (say 1 sec or less).
0
 
LVL 5

Expert Comment

by:y96andha
ID: 1428702
Does it have to be a file that you can read from? I am looking into the possibility of using the low-level functions to record directly into memory.
0
 
LVL 5

Accepted Solution

by:
y96andha earned 300 total points
ID: 1428703
Try this code. I currently don't have a mic connected to my computer, but it gives no errors in VB4. You will get the data into the buffer and can then process it as you like. Please comment if you have any questions.

Private Type WAVEFORMATEX
        wFormatTag As Integer
        nChannels As Integer
        nSamplesPerSec As Long
        nAvgBytesPerSec As Long
        nBlockAlign As Integer
        wBitsPerSample As Integer
        cbSize As Integer
End Type
Private Type WAVEHDR
        lpData As Long
        dwBufferLength As Long
        dwBytesRecorded As Long
        dwUser As Long
        dwFlags As Long
        dwLoops As Long
        lpNext As Long
        Reserved As Long
End Type
Private Declare Function waveInAddBuffer Lib "winmm.dll" (ByVal hWaveIn As Long, lpWaveInHdr As WAVEHDR, ByVal uSize As Long) As Long
Private Declare Function waveInClose Lib "winmm.dll" (ByVal hWaveIn As Long) As Long
Private Declare Function waveInOpen Lib "winmm.dll" (lphWaveIn As Long, ByVal uDeviceID As Long, lpFormat As WAVEFORMATEX, ByVal dwCallback As Long, ByVal dwInstance As Long, ByVal dwFlags As Long) As Long
Private Declare Function waveInPrepareHeader Lib "winmm.dll" (ByVal hWaveIn As Long, lpWaveInHdr As WAVEHDR, ByVal uSize As Long) As Long
Private Declare Function waveInStart Lib "winmm.dll" (ByVal hWaveIn As Long) As Long
Private Declare Function waveInStop Lib "winmm.dll" (ByVal hWaveIn As Long) As Long
Private Declare Function waveInUnprepareHeader Lib "winmm.dll" (ByVal hWaveIn As Long, lpWaveInHdr As WAVEHDR, ByVal uSize As Long) As Long
Private Declare Function waveInReset Lib "winmm.dll" (ByVal hWaveIn As Long) As Long
Private Declare Function VarPtr Lib "vb40032" (var As Any) As Long
Private Const WHDR_DONE = &H1         '  done bit
Private Const WAVE_FORMAT_PCM = 1  '  Needed in resource files so outside #ifndef RC_INVOKED
Private Const WAVE_MAPPER = -1&


Private Sub Command1_Click()
Dim wf As WAVEFORMATEX
Dim hWaveIn As Long
Dim error As Long
wf.wFormatTag = WAVE_FORMAT_PCM
wf.nChannels = 1
wf.nSamplesPerSec = 8000
wf.wBitsPerSample = 8
wf.nBlockAlign = wf.nChannels * wf.wBitsPerSample / 8
wf.cbSize = 0
error = waveInOpen(hWaveIn, WAVE_MAPPER, wf, 0, 0, 0)
If error <> 0 Then
    Print "Error "; error; " in waveInOpen"
    Exit Sub
End If

Dim wh As WAVEHDR
Dim data(8000) As Byte
wh.lpData = VarPtr(data(1))
wh.dwBufferLength = 8000
wh.dwUser = 0
wh.dwFlags = 0
wh.dwLoops = 0
wh.lpNext = 0
wh.Reserved = 0
error = waveInPrepareHeader(hWaveIn, wh, Len(wh))
If error <> 0 Then
    waveInClose hWaveIn
    Print "Error "; error; " in waveInPrepareHeader"
    Exit Sub
End If

error = waveInAddBuffer(hWaveIn, wh, Len(wh))
If error <> 0 Then
    waveInUnprepareHeader hWaveIn, wh, Len(wh)
    waveInClose hWaveIn
    Print "Error "; error; " in waveInAddBuffer"
    Exit Sub
End If

error = waveInStart(hWaveIn)
If error <> 0 Then
    waveInReset hWaveIn
    waveInUnprepareHeader hWaveIn, wh, Len(wh)
    waveInClose hWaveIn
    Print "Error "; error; " in waveInStart"
    Exit Sub
End If

Print "Recording"
While (wh.dwFlags And WHDR_DONE) <> WHDR_DONE
    DoEvents
Wend
Print "Finished"

error = waveInUnprepareHeader(hWaveIn, wh, Len(wh))
If error <> 0 Then
    waveInClose hWaveIn
    Print "Error "; error; "in waveInUnprepareHeader"
    Exit Sub
End If

waveInClose hWaveIn
Print "Recorded data successfully"

End Sub


0
 

Author Comment

by:dand072297
ID: 1428704
y96andha,
Thank you for your effort. There is a problem running your code.
Present spec. as follows:
Win 95 upgrade
VB4 32_bit
c:\windows\system\WINMM.DLL
Form created. It has 1 PushButton, Command1
Your code entered as Form code
Added "Debug" as object to your Print statements

Run,  Click on Command1:
error 32 waveInOpen

I note the code line wf.nSamplesPerSec=8000; this is not
the expected 11025, 22050 or 44100.

Regards, dand
0
 
LVL 5

Expert Comment

by:y96andha
ID: 1428705
You are probably right about that. The error code 32 means format not supported. It does work on my computer in that it generates no error messages, but it might be because of some special driver I have installed. You can try and change this to some value supported with your sound card.

You can use this piece of code to get the error text for a certain error code:
    Dim s As String
    dim errorcode as integer
    errorcode = 32 ' for example
    s = String(512, 0)
    waveInGetErrorText errorcode, s, 512
    s = Left(s, InStr(s, Chr(0)) - 1)
    Print s

0
 

Author Comment

by:dand072297
ID: 1428706
y96andha,
Added Decl.Function waveInGetErrorText and your code snippet within If Statement: If error<> 0 Then
            Debug.Print "error".............
>>>
             errorcode = 32 ' for example
             s = String(512, 0)
 XXX         waveInGetErrorText errorcode, s, 512
             s = Left(s, InStr(s, Chr(0)) - 1)
             Debug.Print s
>>>
 Exit Sub
      ......................
Result:            error 32 in waveInOpen

      MsgBox:Error in loading DLL  (highlighting line XXX as above)

I have tried conventional Sample rates,11025, 22050 but error 32 persists. My Sound is audio tone in Aux Input and I have matched the Sound Blaster settings of Chan/sampleRate/BitsperSample with the coded values but the error 32 remains.
I am interested in your solution to my question but if this "error" problem persists perhaps you may give some consideration to my original requirement. I shall re-state my objective:
      By utilizing the existing ocx, MMControl I can record my Sound to a Buffer (MMControl1.Filename) and I can play this sound with MMControl1.Command="Play". I want to process the contents of MMControl1.FileName (Which I call say,"Mysound") in some other way, eg a Waveform Display.
      How do I find the Address of the Buffer "Mysound" ?
Thank you for your interest,                  dand

0
 
LVL 5

Expert Comment

by:y96andha
ID: 1428707
There seems to be an other problem with the waveInGetErrorText function. Did you use this declaration?:

Private Declare Function waveInGetErrorText Lib "winmm.dll" Alias "waveInGetErrorTextA" (ByVal err As Long, ByVal lpText As String, ByVal uSize As Long) As Long

Could you send me your source file to andreas.hansson@mbox303.swipnet.se? I would like to try and load it in my VB4, to see if exactly the same code works on my machine.

About the MMControl way: You need to save it to a file on your hard disk, and then you would have the trouble of parsing the file format in order to load the sample data.
0
 

Author Comment

by:dand072297
ID: 1428708
Your latest .exe program works on 1 out of 3 systems that I have tried it on. I'm trying to find out what the difference is and am concentrating on Sound cards. I would like to know what Sound Card you and your friends have or any other info that might help identify the cause of the error message.
Thanks for your help so far. Cheers, Dan
0
 
LVL 5

Expert Comment

by:y96andha
ID: 1428709
Both I and my friends have SB32's. Maybe not such a good test after all :-)

I'll see if I can try it on some other sound cards. What cards have you tested, and with what results?


0
 

Author Comment

by:dand072297
ID: 1428710
My sound card and friend #1 card are sb16 generic and show the error message :-(  Friend #2 card is a SB Pro/16 Emulator (AD1812), this card (or some other factor) handles the WaveIn program OK.    

0

Featured Post

Netscaler Common Configuration How To guides

If you use NetScaler you will want to see these guides. The NetScaler How To Guides show administrators how to get NetScaler up and configured by providing instructions for common scenarios and some not so common ones.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

The debugging module of the VB 6 IDE can be accessed by way of the Debug menu item. That menu item can normally be found in the IDE's main menu line as shown in this picture.   There is also a companion Debug Toolbar that looks like the followin…
Have you ever wanted to restrict the users input in a textbox to numbers, and while doing that make sure that they can't 'cheat' by pasting in non-numeric text? Of course you can do that with code you write yourself but it's tedious and error-prone …
As developers, we are not limited to the functions provided by the VBA language. In addition, we can call the functions that are part of the Windows operating system. These functions are part of the Windows API (Application Programming Interface). U…
Get people started with the process of using Access VBA to control Outlook using automation, Microsoft Access can control other applications. An example is the ability to programmatically talk to Microsoft Outlook. Using automation, an Access applic…

803 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question