简单实现音频录制

简单采用JFrame 展示音频录取功能实现

public class MyRecorder extends JFrame implements ActionListener {


/**

*/
private static final long serialVersionUID = 1L;
// 定义录音格式
AudioFormat af = null;
// 定义目标数据行,可以从中读取音频数据,该 TargetDataLine 接口提供从目标数据行的缓冲区读取所捕获数据的方法。
TargetDataLine td = null;
// 定义源数据行,源数据行是可以写入数据的数据行。它充当其混频器的源。应用程序将音频字节写入源数据行,这样可处理字节缓冲并将它们传递给混频器。
SourceDataLine sd = null;
// 定义字节数组输入输出流
ByteArrayInputStream bais = null;
ByteArrayOutputStream baos = null;
// 定义音频输入流
AudioInputStream ais = null;
// 定义停止录音的标志,来控制录音线程的运行
Boolean stopflag = false;


// 定义所需要的组件
JPanel jp1, jp2, jp3;
JLabel jl1 = null;
JButton captureBtn, stopBtn, playBtn, saveBtn;


public static void main(String[] args) {


// 创造一个实例
 new MyRecorder();


}


// 构造函数
public MyRecorder()  
    {  
        //组件初始化  
        jp1 = new JPanel();  
        jp2 = new JPanel();  
        jp3 = new JPanel();  
          
        //定义字体  
        Font myFont = new Font("黑体",Font.BOLD,30);  
        jl1 = new JLabel("录音功能实现");  
        jl1.setFont(myFont);  
        jp1.add(jl1);  
          
        //对开始录音按钮进行注册监听  
        captureBtn = new JButton("开始录音");  
        captureBtn.addActionListener(this);  
        captureBtn.setActionCommand("captureBtn");  
        //对停止录音进行注册监听  
        stopBtn = new JButton("停止录音");  
        stopBtn.addActionListener(this);  
        stopBtn.setActionCommand("stopBtn");  
        //对播放录音进行注册监听  
        playBtn = new JButton("播放录音");  
        playBtn.addActionListener(this);  
        playBtn.setActionCommand("playBtn");  
        //对保存录音进行注册监听  
        saveBtn = new JButton("保存录音");  
        saveBtn.addActionListener(this);  
        saveBtn.setActionCommand("saveBtn");  
          
          
        this.add(jp1,BorderLayout.NORTH);  
        this.add(jp2,BorderLayout.CENTER);  
        this.add(jp3,BorderLayout.SOUTH);  
        jp3.setLayout(null);  
        jp3.setLayout(new GridLayout(1, 4,10,10));  
        jp3.add(captureBtn);  
        jp3.add(stopBtn);  
        jp3.add(playBtn);  
        jp3.add(saveBtn);  
        //设置按钮的属性  
        captureBtn.setEnabled(true);  
        stopBtn.setEnabled(false);  
        playBtn.setEnabled(false);  
        saveBtn.setEnabled(false);  
        //设置窗口的属性  
        this.setSize(400,300);  
        this.setTitle("录取音频");  
        this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);  
        this.setLocationRelativeTo(null);  
        this.setVisible(true);  
    }


public void actionPerformed(ActionEvent e) {


if (e.getActionCommand().equals("captureBtn")) {
// 点击开始录音按钮后的动作
// 停止按钮可以启动
captureBtn.setEnabled(false);
stopBtn.setEnabled(true);
playBtn.setEnabled(false);
saveBtn.setEnabled(false);
// 调用录音的方法
capture();
} else if (e.getActionCommand().equals("stopBtn")) {
// 点击停止录音按钮的动作
captureBtn.setEnabled(true);
stopBtn.setEnabled(false);
playBtn.setEnabled(true);
saveBtn.setEnabled(true);
// 调用停止录音的方法
stop();
} else if (e.getActionCommand().equals("playBtn")) {
// 调用播放录音的方法
play();
} else if (e.getActionCommand().equals("saveBtn")) {
// 调用保存录音的方法
save();
}


}


// 开始录音
public void capture() {
try {
// af为AudioFormat也就是音频格式
af = getAudioFormat();
DataLine.Info info = new DataLine.Info(TargetDataLine.class, af);
td = (TargetDataLine) (AudioSystem.getLine(info));
// 打开具有指定格式的行,这样可使行获得所有所需的系统资源并变得可操作。
td.open(af);
// 允许某一数据行执行数据 I/O
td.start();


// 创建播放录音的线程
Record record = new Record();
Thread t1 = new Thread(record);
t1.start();


} catch (LineUnavailableException ex) {
ex.printStackTrace();
return;
}
}


// 停止录音
public void stop() {
stopflag = true;
}


// 播放录音
public void play() {
// af为AudioFormat也就是音频格式
af = getAudioFormat();
// 将baos中的数据转换为字节数据
byte audioData[] = baos.toByteArray();
// 转换为输入流
bais = new ByteArrayInputStream(audioData);
af = getAudioFormat();
ais = new AudioInputStream(bais, af, audioData.length / af.getFrameSize());
try {
DataLine.Info dataLineInfo = new DataLine.Info(SourceDataLine.class, af);
sd = (SourceDataLine) AudioSystem.getLine(dataLineInfo);
sd.open(af);
sd.start();
// 创建播放进程
Play py = new Play();
Thread t2 = new Thread(py);
t2.start();
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
// 关闭流
if (ais != null) {
ais.close();
}
if (bais != null) {
bais.close();
}
if (baos != null) {
baos.close();
}


} catch (Exception e) {
e.printStackTrace();
}
}
}


// 保存录音
public void save() {
// 取得录音输入流
af = getAudioFormat();


byte audioData[] = baos.toByteArray();
bais = new ByteArrayInputStream(audioData);
ais = new AudioInputStream(bais, af, audioData.length / af.getFrameSize());
// 定义最终保存的文件名
File file = null;
// 写入文件
try {
// 以当前的时间命名录音的名字
// 将录音的文件存放到F盘下语音文件夹下
File filePath = new File("D:/语音文件");
if (!filePath.exists()) {// 如果文件不存在,则创建该目录
filePath.mkdir();
}
SimpleDateFormat sdf = new SimpleDateFormat("ddHHmmss");
file = new File(filePath.getPath() + "/" + sdf.format(new Date(System.currentTimeMillis())) + ".mp3");
AudioSystem.write(ais, AudioFileFormat.Type.WAVE, file);
} catch (Exception e) {
e.printStackTrace();
} finally {
// 关闭流
try {
if (bais != null) {
bais.close();
}
if (ais != null) {
ais.close();
}
} catch (Exception e) {
e.printStackTrace();
}
}
}


// 设置AudioFormat的参数
public AudioFormat getAudioFormat() {
// 下面注释部分是另外一种音频格式,两者都可以
// AudioFormat.Encoding encoding = AudioFormat.Encoding.PCM_SIGNED;
// float rate = 8000f;
// int sampleSize = 16;
// int channels = 1;
// boolean bigEndian = true;
// return new AudioFormat(encoding, rate, sampleSize, channels, (sampleSize / 8) * channels, rate, bigEndian);
//采样率是每秒播放和录制的样本数
float sampleRate = 16000.0F;
// 采样率8000,11025,16000,22050,44100
//sampleSizeInBits表示每个具有此格式的声音样本中的位数
int sampleSizeInBits = 16;
// 8,16
int channels = 1;
// 单声道为1,立体声为2
boolean signed = true;
// true,false
boolean bigEndian = true;
// true,false
return new AudioFormat(sampleRate, sampleSizeInBits, channels,
signed,bigEndian);
}


// 录音类,因为要用到本类中的变量,所以将其做成内部类
class Record implements Runnable {
// 定义存放录音的字节数组,作为缓冲区
byte bts[] = new byte[10000];
// 将字节数组包装到流里,最终存入到baos中
// 重写run函数
public void run() {
baos = new ByteArrayOutputStream();
try {
stopflag = false;
while (stopflag != true) {
// 当停止录音没按下时,该线程一直执行
// 从数据行的输入缓冲区读取音频数据。
// 要读取bts.length长度的字节,cnt 是实际读取的字节数
int cnt = td.read(bts, 0, bts.length);
if (cnt > 0) {
baos.write(bts, 0, cnt);
}
}
} catch (Exception e) {
e.printStackTrace();
} finally {
try {
// 关闭打开的字节数组流
if (baos != null) {
baos.close();
}
} catch (IOException e) {
e.printStackTrace();
} finally {
td.drain();
td.close();
}
}
}


}


// 播放类,同样也做成内部类
class Play implements Runnable {
// 播放baos中的数据即可
public void run() {
byte bts[] = new byte[10000];
try {
int cnt = 0;
// 读取数据到缓存数据
while ((cnt = ais.read(bts, 0, bts.length)) > 0) {
// 写入缓存数据
// 将音频数据写入到混频器
sd.write(bts, 0, cnt);
}
} catch (Exception e) {
e.printStackTrace();
} finally {
sd.drain();
sd.close();
}
}
}



}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Html5网页纯JavaScript录制MP3音频 <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>Html5网页JavaScript录制MP3音频</title> <meta charset="utf-8" /> </head> <body> Html5网页JavaScript录制MP3音频 录制 停止 上传 调试信息: [removed][removed] [removed] var recorder = new MP3Recorder({ debug:true, funOk: function () { btnStart.disabled = false; log('初始化成功'); }, funCancel: function (msg) { log(msg); recorder = null; } }); var mp3Blob; function funStart(button) { btnStart.disabled = true; btnStop.disabled = false; btnUpload.disabled = true; log('录音开始...'); recorder.start(); } function funStop(button) { recorder.stop(); btnStart.disabled = false; btnStop.disabled = true; btnUpload.disabled = false; log('录音结束,MP3导出中...'); recorder.getMp3Blob(function (blob) { log('MP3导出成功'); mp3Blob = blob; var url = URL.createObjectURL(mp3Blob); var div = document.createElement('div'); var au = document.createElement('audio'); var hf = document.createElement('a'); au.controls = true; au.src = url; hf.href = url; hf.download = new Date().toISOString() + '.mp3'; hf[removed] = hf.download; div.appendChild(au); div.appendChild(hf); recordingslist.appendChild(div); }); } function log(str) { recordingslist[removed] += str + ''; } function funUpload() { var fd = new FormData(); var mp3Name = encodeURIComponent('audio_recording_' + new Date().getTime() + '.mp3'); fd.append('mp3Name', mp3Name); fd.append('file', mp3Blob); var xhr = new XMLHttpRequest(); xhr.onreadystatechange = function () { if (xhr.readyState == 4 && xhr.status == 200) { recordingslist[removed] += '上传成功:' + mp3Name + ''; } }; xhr.open('POST', 'upload.ashx'); xhr.send(fd); } [removed] </body> </html> [javascript] view plain copy 在CODE上查看代码片派生到我的代码片 (function (exports) { var MP3Recorder = function (config) { var recorder = this; config = config || {}; config.sampleRate = config.sampleRate || 44100; config.bitRate = config.bitRate || 128; navigator.getUserMedia = navigator.getUserMedia || navigator.webkitGetUserMedia || navigator.mozGetUserMedia || navigator.msGetUserMedia; if (navigator.getUserMedia) { navigator.getUserMedia({ audio: true }, function (stream) { var context = new AudioContext(), microphone = context.createMediaStreamSource(stream), processor = context.createScriptProcessor(16384, 1, 1),//bufferSize大小,输入channel数,输出channel数 mp3ReceiveSuccess, currentErrorCallback; config.sampleRate = context.sampleRate; processor.onaudioprocess = function (event) { //边录音边转换 var array = event.inputBuffer.getChannelData(0); realTimeWorker.postMessage({ cmd: 'encode', buf: array }); }; var realTimeWorker = new Worker('js/worker-realtime.js'); realTimeWorker.onmessage = function (e) { switch (e.data.cmd) { case 'init': log('初始化成功'); if (config.funOk) { config.funOk(); } break; case 'end': log('MP3大小:', e.data.buf.length); if (mp3ReceiveSuccess) { mp3ReceiveSuccess(new Blob(e.data.buf, { type: 'audio/mp3' })); } break; case 'error': log('错误信息:' + e.data.error); if (currentErrorCallback) { currentErrorCallback(e.data.error); } break; default: log('未知信息:', e.data); } }; recorder.getMp3Blob = function (onSuccess, onError) { currentErrorCallback = onError; mp3ReceiveSuccess = onSuccess; realTimeWorker.postMessage({ cmd: 'finish' }); }; recorder.start = function () { if (processor && microphone) { microphone.connect(processor); processor.connect(context.destination); log('开始录音'); } } recorder.stop = function () { if (processor && microphone) { microphone.disconnect(); processor.disconnect(); log('录音结束'); } } realTimeWorker.postMessage({ cmd: 'init', config: { sampleRate: config.sampleRate, bitRate: config.bitRate } }); }, function (error) { var msg; switch (error.code || error.name) { case 'PERMISSION_DENIED': case 'PermissionDeniedError': msg = '用户拒绝访问麦客风'; break; case 'NOT_SUPPORTED_ERROR': case 'NotSupportedError': msg = '浏览器不支持麦客风'; break; case 'MANDATORY_UNSATISFIED_ERROR': case 'MandatoryUnsatisfiedError': msg = '找不到麦客风设备'; break; default: msg = '无法打开麦克风,异常信息:' + (error.code || error.name); break; } if (config.funCancel) { config.funCancel(msg); } }); } else { if (config.funCancel) { config.funCancel('当前浏览器不支持录音功能'); } } function log(str) { if (config.debug) { console.log(str); } } } exports.MP3Recorder = MP3Recorder; })(window);

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值