如何用Delphi製作錄音程序
陳經韜
Delphi是InPRise(前Borland)公司的優秀的視覺化程式設計工具,它自帶的Mediaplayer控制是開發多媒體的利器。用它幾分鐘就可以做出一個像解霸一樣可以播放多媒體檔案的程式來。但可能很少人知道,用它也可以做一個錄音程式。
運行Delphi,在System頁拖曳一個Mediaplayer控製到窗體上,預設名為Mediaplayer1。由於我們的程式是採用自己的按鈕,所以將Mediaplayer1的Visible屬性設為False,其它屬性保持預設值。再放兩個按鈕Button1和Button2。 Button1的屬性Name改為BtStart,Caption改為"開始錄音", Button2的屬性Name改為BtStop,Caption改為"停止錄音",Enabled屬性改為False。然後切換窗口到程式碼窗口,開始書寫程式碼。
程式中,我們定義了一個Wav檔案的文件頭格式,錄音時先建立一個只有檔案頭的Wav文件,然後將Mediaplayer1錄製下來的聲音寫進文件。其中CreateWav過程的幾個參數意義如下:第一個channels代表聲道,取1時代表單聲,取2時代表立體聲。 resolution也只有兩個值可以選擇,取8時代表8位元聲音,取16時代表16位元聲音,rate則代表聲音頻率,如11025,22050, 44100。數值越大則聲音越清晰,當然,錄製的檔案也越大。最後一個參數則代表對應的檔案名稱了。所以CreateWav可以有以下形式:
CreateWav(1,8,11025,'C:/abc.wav');//在C盤根目錄下建立8位元單聲道頻率為11025的名為abc.wav的Wav文件
CreateWav(2,16,44100,'C:/abc.wav');//在C盤根目錄下建立16位元立體聲道頻率為44100的名為abc.wav的Wav文件
外國一個很出名的用Delphi寫的遠端控制軟體Netbus有一個聲音監聽功能,就是用本文的方法寫的。它先把對方的聲音錄下來,然後傳送回來,達到監聽對方的目的。當然,前提是對方必須安裝有麥克風,否則監聽到的是對方播放的聲音(如打開解霸或Readplay播放,運行本程序,就可以把播放的聲音錄製下來了)。
事實上,現在的網路聲音傳播技術已經發展到某個階段,語音對講和ip電話等也開始成熟。不過它們採用的是VOX格式或ACM格式,具體程式碼可以在我的首頁http://Lovejingtao.126.com下載。但如果對VOX或ACM格式不熟悉的朋友,也可以用本文的方法來製作自己的「錄音機」。至於如何呼叫系統自備的avifil32.dll來進行網路影片播放,有機會時再跟大家交流吧。
本程式在Pwin98+Delphi5下通過。
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
StdCtrls, MPlayer;
type
TWavHeader = record //定義一個Wav檔頭格式
rId : longint;
rLen : longint;
wId : longint;
fId : longint;
fLen : longint;
wFormatTag : Word;
nChannels : word;
nSamplesPerSec : longint;
nAvgBytesPerSec : longint;
nBlockAlign : word;
wBitsPerSample : word;
dId : longint;
wSampleLength : longint;
end;
TForm1 = class(TForm)
MediaPlayer1: TMediaPlayer;
BtStart: TButton;
BtStop: TButton;
procedure CreateWav(channels : word; resolution : word; rate : longint; fn : string);//自訂寫一個Wav檔案頭過程
procedure BtStartClick(Sender: TObject);
procedure BtStopClick(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;
var
Form1: TForm1;
implementation
{$R *.DFM}
procedure TForm1.CreateWav( channels : word; { 1(單聲)或2(立體聲) }
resolution : word; { 8或16,代表8位元或16位元聲音}
rate : longint; { 聲音頻率,如11025,22050, 44100}
fn : string { 對應的檔案名稱} );
var
wf : file of TWavHeader;
wh : TWavHeader;
begin
wh.rId := $46464952;
wh.rLen := 36;
wh.wId := $45564157;
wh.fId := $20746d66;
wh.fLen := 16;
wh.wFormatTag := 1;
wh.nChannels := channels;
wh.nSamplesPerSec := rate;
wh.nAvgBytesPerSec := channels*rate*(resolution div 8);
wh.nBlockAlign := channels*(resolution div 8);
wh.wBitsPerSample := resolution;
wh.dId := $61746164;
wh.wSampleLength := 0;
assignfile(wf,fn); {開啟對應檔案}
rewrite(wf); {移動指標到檔案頭}
write(wf,wh); {寫進文件頭}
closefile(wf); {關閉檔案}
end;
procedure TForm1.BtStartClick(Sender: TObject);
begin
try
//在程式目前目錄下建立一個Wav檔Temp.wav
CreateWav(1, 8, 11025, (ExtractFilePath(application.ExeName)+ 'Temp.wav'));
MediaPlayer1.DeviceType := dtAutoSelect;
MediaPlayer1.FileName := (ExtractFilePath(Application.ExeName)+ 'Temp.wav');
MediaPlayer1.Open;
MediaPlayer1.StartRecording;
BtStart.Enabled:=false;
BtStop.Enabled:=true;
except
BtStart.Enabled:=True;
BtStop.Enabled:=false;
Application.MessageBox('媒體裝置初始化失敗!','錯誤',MB_ICONERROR+MB_OK);
end;
end;
procedure TForm1.BtStopClick(Sender: TObject);
begin
try
MediaPlayer1.Stop;
MediaPlayer1.Save;
MediaPlayer1.Close;
Application.MessageBox('聲音錄製完畢!','訊息',MB_ICONINFORMATION+MB_OK);
BtStart.Enabled:=True;
BtStop.Enabled:=false;
except
Application.MessageBox('儲存聲音檔案出錯!','錯誤',MB_ICONERROR+MB_OK);
BtStart.Enabled:=True;
BtStop.Enabled:=false;
end;
end;
end.
補充:1.錄製的檔案播放時可能要把音訊屬性的Wav調大。
2.如果系統安裝了其它一些音頻驅動程序,則可能錄製的Wav文件大小為零,但會同時生成一個TMP結尾的文件,將其擴展名改為Wav就是錄製的聲音文件。但這種情況很少發生。 (機會幾乎為零^-^)
3.本程式在運行解霸和Replayer下錄製聲音通過。