iis服务器助手广告广告
返回顶部
首页 > 资讯 > 移动开发 >Android实现录音声波图
  • 534
分享到

Android实现录音声波图

Android录音声波图Android录音声波Android声波图 2022-11-13 14:11:11 534人浏览 独家记忆
摘要

本文实例为大家分享了Android实现录音声波图的具体代码,供大家参考,具体内容如下 图像类: package com.akm.test; import android.cont

本文实例为大家分享了Android实现录音声波图的具体代码,供大家参考,具体内容如下

图像类:

package com.akm.test;


import android.content.Context;
import android.graphics.canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.util.AttributeSet;
import android.view.SurfaceView;

import java.util.LinkedList;


public class WavefORMView extends SurfaceView {

    // The number of buffer frames to keep around (for a nice fade-out visualization).
    private static final int HISTORY_SIZE = 6;

    // To make quieter sounds still show up well on the display, we use +/- 8192 as the amplitude
    // that reaches the top/bottom of the view instead of +/- 32767. Any samples that have
    // magnitude higher than this limit will simply be clipped during drawing.
    private static final float MAX_AMPLITUDE_TO_DRAW = 8192.0f;

    // The queue that will hold historical audio data.
    private final LinkedList<short[]> mAudioData;

    private final Paint mPaint;

    public WaveformView(Context context) {
        this(context, null, 0);
    }

    public WaveformView(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }

    public WaveformView(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);

        mAudioData = new LinkedList<short[]>();

        mPaint = new Paint();
        mPaint.setStyle(Paint.Style.STROKE);
        mPaint.setColor(Color.WHITE);
        mPaint.setStrokeWidth(0);
        mPaint.setAntiAlias(true);
    }

    
    public synchronized void updateAudioData(short[] buffer) {
        short[] newBuffer;

        // We want to keep a small amount of history in the view to provide a nice fading effect.
        // We use a linked list that we treat as a queue for this.
        if (mAudioData.size() == HISTORY_SIZE) {
            newBuffer = mAudioData.removeFirst();
            System.arraycopy(buffer, 0, newBuffer, 0, buffer.length);
        } else {
            newBuffer = buffer.clone();
        }

        mAudioData.addLast(newBuffer);

        // Update the display.
        Canvas canvas = getHolder().lockCanvas();
        if (canvas != null) {
            drawWaveform(canvas);
            getHolder().unlockCanvasAndPost(canvas);
        }
    }

    
    private void drawWaveform(Canvas canvas) {
        // Clear the screen each time because SurfaceView won't do this for us.
        canvas.drawColor(Color.BLACK);

        float width = getWidth();
        float height = getHeight();
        float centerY = height / 2;

        // We draw the history from oldest to newest so that the older audio data is further back
        // and darker than the most recent data.
        int colorDelta = 255 / (HISTORY_SIZE + 1);
        int brightness = colorDelta;

        for (short[] buffer : mAudioData) {
            mPaint.setColor(Color.argb(brightness, 128, 255, 192));

            float lastX = -1;
            float lastY = -1;

            // For efficiency, we don't draw all of the samples in the buffer, but only the ones
            // that align with pixel boundaries.
            for (int x = 0; x < width; x++) {
                int index = (int) ((x / width) * buffer.length);
                short sample = buffer[index];
                float y = (sample / MAX_AMPLITUDE_TO_DRAW) * centerY + centerY;

                if (lastX != -1) {
                    canvas.drawLine(lastX, lastY, x, y, mPaint);
                }

                lastX = x;
                lastY = y;
            }

            brightness += colorDelta;
        }
    }
}

头文件:



package com.akm.test;

import java.io.FileOutputStream;
import java.io.IOException;


public class WAVHeader {
    private byte[] mHeader;          // the complete header.
    private int mSampleRate;         // sampling frequency in Hz (e.g. 44100).
    private int mChannels;           // number of channels.
    private int mNumSamples;         // total number of samples per channel.
    private int mNumBytesPerSample;  // number of bytes per sample, all channels included.

    public WAVHeader(int sampleRate, int numChannels, int numSamples) {
        mSampleRate = sampleRate;
        mChannels = numChannels;
        mNumSamples = numSamples;
        mNumBytesPerSample = 2 * mChannels;  // assuming 2 bytes per sample (for 1 channel)
        mHeader = null;
        setHeader();
    }

    public byte[] getWAVHeader() {
        return mHeader;
    }

    public static byte[] getWAVHeader(int sampleRate, int numChannels, int numSamples) {
        return new WAVHeader(sampleRate, numChannels, numSamples).mHeader;
    }

    public String toString() {
        String str = "";
        if (mHeader == null) {
            return str;
        }
        int num_32bits_per_lines = 8;
        int count = 0;
        for (byte b : mHeader) {
            boolean break_line = count > 0 && count % (num_32bits_per_lines * 4) == 0;
            boolean insert_space = count > 0 && count % 4 == 0 && !break_line;
            if (break_line) {
                str += '\n';
            }
            if (insert_space) {
                str += ' ';
            }
            str += String.format("%02X", b);
            count++;
        }

        return str;
    }

    private void setHeader() {
        byte[] header = new byte[46];
        int offset = 0;
        int size;

        // set the RIFF chunk
        System.arraycopy(new byte[]{'R', 'I', 'F', 'F'}, 0, header, offset, 4);
        offset += 4;
        size = 36 + mNumSamples * mNumBytesPerSample;
        header[offset++] = (byte) (size & 0xFF);
        header[offset++] = (byte) ((size >> 8) & 0xFF);
        header[offset++] = (byte) ((size >> 16) & 0xFF);
        header[offset++] = (byte) ((size >> 24) & 0xFF);
        System.arraycopy(new byte[]{'W', 'A', 'V', 'E'}, 0, header, offset, 4);
        offset += 4;

        // set the fmt chunk
        System.arraycopy(new byte[]{'f', 'm', 't', ' '}, 0, header, offset, 4);
        offset += 4;
        System.arraycopy(new byte[]{0x10, 0, 0, 0}, 0, header, offset, 4);  // chunk size = 16
        offset += 4;
        System.arraycopy(new byte[]{1, 0}, 0, header, offset, 2);  // format = 1 for PCM
        offset += 2;
        header[offset++] = (byte) (mChannels & 0xFF);
        header[offset++] = (byte) ((mChannels >> 8) & 0xFF);
        header[offset++] = (byte) (mSampleRate & 0xFF);
        header[offset++] = (byte) ((mSampleRate >> 8) & 0xFF);
        header[offset++] = (byte) ((mSampleRate >> 16) & 0xFF);
        header[offset++] = (byte) ((mSampleRate >> 24) & 0xFF);
        int byteRate = mSampleRate * mNumBytesPerSample;
        header[offset++] = (byte) (byteRate & 0xFF);
        header[offset++] = (byte) ((byteRate >> 8) & 0xFF);
        header[offset++] = (byte) ((byteRate >> 16) & 0xFF);
        header[offset++] = (byte) ((byteRate >> 24) & 0xFF);
        header[offset++] = (byte) (mNumBytesPerSample & 0xFF);
        header[offset++] = (byte) ((mNumBytesPerSample >> 8) & 0xFF);
        System.arraycopy(new byte[]{0x10, 0}, 0, header, offset, 2);
        offset += 2;

        // set the beginning of the data chunk
        System.arraycopy(new byte[]{'d', 'a', 't', 'a'}, 0, header, offset, 4);
        offset += 4;
        size = mNumSamples * mNumBytesPerSample;
        header[offset++] = (byte) (size & 0xFF);
        header[offset++] = (byte) ((size >> 8) & 0xFF);
        header[offset++] = (byte) ((size >> 16) & 0xFF);
        header[offset++] = (byte) ((size >> 24) & 0xFF);

        mHeader = header;
    }


    public static byte[] getHeader(  long totalAudioLen,
                            long totalDataLen, long longSampleRate, int channels, long byteRate) throws IOException {


        byte[] header = new byte[44];
        header[0] = 'R'; // RIFF/WAVE header
        header[1] = 'I';
        header[2] = 'F';
        header[3] = 'F';
        header[4] = (byte) (totalDataLen & 0xff);
        header[5] = (byte) ((totalDataLen >> 8) & 0xff);
        header[6] = (byte) ((totalDataLen >> 16) & 0xff);
        header[7] = (byte) ((totalDataLen >> 24) & 0xff);
        header[8] = 'W';
        header[9] = 'A';
        header[10] = 'V';
        header[11] = 'E';
        header[12] = 'f'; // 'fmt ' chunk
        header[13] = 'm';
        header[14] = 't';
        header[15] = ' ';
        header[16] = 16; // 4 bytes: size of 'fmt ' chunk
        header[17] = 0;
        header[18] = 0;
        header[19] = 0;
        header[20] = 1; // format = 1
        header[21] = 0;
        header[22] = (byte) channels;
        header[23] = 0;
        header[24] = (byte) (longSampleRate & 0xff);
        header[25] = (byte) ((longSampleRate >> 8) & 0xff);
        header[26] = (byte) ((longSampleRate >> 16) & 0xff);
        header[27] = (byte) ((longSampleRate >> 24) & 0xff);
        header[28] = (byte) (byteRate & 0xff);
        header[29] = (byte) ((byteRate >> 8) & 0xff);
        header[30] = (byte) ((byteRate >> 16) & 0xff);
        header[31] = (byte) ((byteRate >> 24) & 0xff);
        header[32] = (byte) (2 * 16 / 8); // block align
        header[33] = 0;
        header[34] = 16; // bits per sample
        header[35] = 0;
        header[36] = 'd';
        header[37] = 'a';
        header[38] = 't';
        header[39] = 'a';
        header[40] = (byte) (totalAudioLen & 0xff);
        header[41] = (byte) ((totalAudioLen >> 8) & 0xff);
        header[42] = (byte) ((totalAudioLen >> 16) & 0xff);
        header[43] = (byte) ((totalAudioLen >> 24) & 0xff);

        return header;
    }
}

测试:

package com.akm.test;

import android.app.Activity;
import android.media.AudioFormat;
import android.media.AudioManager;
import android.media.AudioRecord;
import android.media.AudioTrack;
import android.media.MediaPlayer;
import android.media.MediaRecorder;
import android.os.Bundle;
import android.os.Environment;
import android.os.Message;
import android.os.SystemClock;
import android.util.DisplayMetrics;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.Chronometer;
import android.widget.SeekBar;
import android.widget.TextView;

import com.ringdroid.R;

import java.io.File;
import java.io.IOException;
import java.io.RandoMaccessFile;
import java.NIO.ByteBuffer;
import java.nio.ByteOrder;
import java.nio.ShortBuffer;
import java.nio.channels.FileChannel;


public class Test extends Activity implements View.OnClickListener {

    WaveformView waveformView;
    private Button btnStart;
    private Button btnStop;
    private String filePath;
    private boolean mRecordingKeepGoing;
    private SoundFile soundFile;
    private RandomAccessFile randomAccessFile;
    private int totalLength;//总长
    private int duration;//时长
    private int rate;//采样率
    private int channelConfig;//声道

    private int samples;
    private int startPos;
    private int bufferSize;//缓冲区大小
    private int minBufferSize;//最小缓冲区

    private AudioRecord audioRecord;
    private AudioTrack audioTrack;
    private boolean mThreadFlag;
    private int i;
    private int j;
    private int STATUS = 1;
    private int STATUS_PAUSE = 2;
    private int STATUS_PREPARED = 1;
    private int STATUS_RECORDING = 1;
    private Thread audioTrackThread;
    private Thread thread;
    private int endPos;
    private int curFileLength;
    OnFileChangedListener onFileChangedListener;
    private boolean isRewrite;
    private boolean audioTrackFlag;
    private int frequency = 22050;//22050;
    private int recBufSize;
    private String outPath;
    private byte[] bytes;
    private int time;
    private Button btnPasue;
    private Button btnPlay;
    private Button btnPlay2;
    private long startTime;
    private long restOfTime;
    private int audioFormat;//采集
    private int bufferSizeInBytes;//缓冲区大小
    private Button btnSave;
    //    private ByteBuffer mDecodedBytes;
//    private ByteBuffer mDecodedSamples;
    private byte[] sampleBytes;
    private MediaPlayer mediaPlayer;
    private SeekBar seekBar;
    private android.os.Handler handler = new android.os.Handler();
    Runnable updateThread = new Runnable() {
        public void run() {
            // 获得歌曲现在播放位置并设置成播放进度条的值
            if (mediaPlayer != null) {
                seekBar.setProgress(mediaPlayer.getCurrentPosition());
                Log.e("Test", "run------ updateThread:getCurrentPosition " + mediaPlayer.getCurrentPosition());
                // 每次延迟100毫秒再启动线程
                handler.postDelayed(updateThread, 100);
            }
        }
    };
    private Chronometer et_time;
    private long falgTime;
    private long pauseTime;
    private long subtime;
    private long beginTime;
    private TextView currentTime;
    private int currentProgress;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.test);


        waveformView = (WaveformView) findViewById(R.id.waveform);
        btnStart = (Button) findViewById(R.id.button_start);
        btnPasue = (Button) findViewById(R.id.button_pasue);
        btnStop = (Button) findViewById(R.id.button2_stop);
        btnPlay = (Button) findViewById(R.id.button_play);
        btnPlay2 = (Button) findViewById(R.id.button_play2);
        btnSave = (Button) findViewById(R.id.button_save);
        seekBar = (SeekBar) findViewById(R.id.sb);
        et_time = (Chronometer) this.findViewById(R.id.et_time);
        currentTime = (TextView) this.findViewById(R.id.currentTime);


        btnStart.setOnClickListener(this);
        btnPasue.setOnClickListener(this);
        btnStop.setOnClickListener(this);
        btnPlay.setOnClickListener(this);
        btnPlay2.setOnClickListener(this);
        btnSave.setOnClickListener(this);


        initPar();
        initRecorder(true);
        initAudioTack();
    }


    @Override
    protected void onResume() {
        super.onResume();

        initRecorder(false);
    }

    private void initAudioTack() {
        minBufferSize = AudioTrack.getMinBufferSize(rate, 3, audioFormat);
        Log.e("Test", "initAudioTack------ minBufferSize:" + minBufferSize);
        audioTrack = new AudioTrack(AudioManager.STREAM_MUSIC, rate, 1, audioFormat, minBufferSize, AudioTrack.MODE_STREAM);
    }

    private void initPar() {
        duration = 60 * 1000;//毫秒
        rate = 44100;//声卡一般提供11.025kHz、22.05kHz和44.1kHz等不同的采样频率
        channelConfig = AudioFormat.CHANNEL_IN_DEFAULT;
        audioFormat = AudioFormat.ENcoding_PCM_16BIT;
        restOfTime = duration;
    }

    private void initRecorder(boolean isNew) {

        initAudioFile(isNew);
        bufferSize = AudioRecord.getMinBufferSize(rate, channelConfig, audioFormat);
        Log.d("Test", "initRecorder: bufferSize:" + bufferSize);//44100 1 2 = v fc
//        int k = audioFormat * rate / 25;
//        if (bufferSize % k != 0) {
//            bufferSize = (k * (channelConfig + bufferSize / k));
//        }
        audioRecord = new AudioRecord(MediaRecorder.AudiOSource.MIC, rate, channelConfig, audioFormat, bufferSize);

    }

    public boolean isRecording() {
        return audioRecord.getRecordingState() == AudioRecord.RECORDSTATE_RECORDING;
    }

    private void initAudioFile(boolean isNew) {

        filePath = Environment.getExternalStorageDirectory().getAbsolutePath() + "/akm/t.wav";

        new File(Environment.getExternalStorageDirectory().getAbsolutePath() + "/akm").mkdir();
        File f = new File(filePath);
        try {
            if (f.exists() && isNew) {
                f.delete();
            }

            randomAccessFile = new RandomAccessFile(filePath, "rw");
            //文件长度 = 比特率*时间
            //= 采样率*位数*声道 / 8

            totalLength = (rate * 1 * 16 / 8) * (duration / 1000);
//            totalLength = (int) (4l * (duration * rate / 1000l));
            createWaveFile(randomAccessFile, true, totalLength);
            totalLength = 44 + totalLength;
            randomAccessFile = new RandomAccessFile(filePath, "rw");

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

    private void createWaveFile(RandomAccessFile randomAccessFile, boolean b, int totalLength) {


        if (b) {


            try {
//                randomAccessFile.write(WAVHeader.getHeader(rate,channels,samples));
                // long totalAudioLen,long totalDataLen, long longSampleRate, int channels, long byteRate
                //数据长度 文件长度 采样率 声道 比特率

                //比特率(字节/秒)= (采样频率(Hz)× 采样位数(bit) × 声道数)/ 8
                //

                long byteRate = (channelConfig * audioFormat * rate) / 8;
                byte[] bytes = WAVHeader.getHeader(totalLength - 36l, totalLength, rate, channelConfig, byteRate);
                FileChannel localFileChannel = randomAccessFile.getChannel();
                localFileChannel.map(FileChannel.MapMode.READ_WRITE, 0l, 44l).put(bytes);
                localFileChannel.close();
                Log.e("Test", "createWaveFile------ OK ");


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


        }

    }


    @Override
    public void onClick(View view) {
        switch (view.getId()) {
            case R.id.button_start:

                try {

                    mRecordingKeepGoing = true;

                    new Thread() {
                        @Override
                        public void run() {


                            startRecording();

                        }
                    }.start();


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


                break;

            case R.id.button_pasue:
                mRecordingKeepGoing = false;

                pauseRecord();

                try {//暂停后,设置文件索引为末尾

                    startPos = (int) randomAccessFile.getFilePointer();
                } catch (IOException e) {
                    e.printStackTrace();
                }

                pausePlay();

                break;


            case R.id.button_play:
                startReview(true);

                break;
            case R.id.button2_stop:
                mRecordingKeepGoing = false;

                stopRecord();

                stopPlay();

                break;

            case R.id.button_save:

                startPos = currentProgress;
                if (randomAccessFile==null){
                    try {
                        randomAccessFile = new RandomAccessFile(filePath, "rw");
                    } catch (IOException e) {
                        e.printStackTrace();
                    }
                }
                try {
                    Log.e("Test", "onClick: pos" + randomAccessFile.getFilePointer());
                    int size = ((rate * 1 * 16 / 8) * (currentProgress / 1000));
                    Log.e("Test", "onClick------ size "+size);
                    if (size<44){
                        size = 44;
                    }
                    randomAccessFile.seek(size);
                    randomAccessFile.write(sampleBytes);
                    randomAccessFile.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
                Log.e("Test", "onClick------pos "+currentProgress);

                break;
            case R.id.button_play2:
                play();
                break;

        }
    }

    private void pausePlay() {

        if (mediaPlayer != null && mediaPlayer.isPlaying()) {
            // 暂停音乐播放器
            mediaPlayer.pause();
            btnPasue.setText("续播");
            seekBar.setEnabled(false);
            et_time.stop();

            pauseTime = SystemClock.elapsedRealtime();
            // System.out.println("1 pauseTime" + pauseTime);
        } else if (mediaPlayer != null
                && "续播".equals(btnPasue.getText().toString())) {
            subtime += SystemClock.elapsedRealtime() - pauseTime;
            // System.out.println("2 subtime:" + subtime);
            mediaPlayer.start();
            btnPasue.setText("暂停");
            seekBar.setEnabled(true);
            beginTime = falgTime + subtime;
            // System.out.println("3 beginTime" + beginTime);
            et_time.setBase(beginTime);
            et_time.start();
        }
    }

    private void stopPlay() {


        if (mediaPlayer != null && mediaPlayer.isPlaying()) {
            mediaPlayer.stop();
            mediaPlayer = null;
            et_time.setBase(SystemClock.elapsedRealtime());
            et_time.start();
            et_time.stop();
            btnPlay2.setEnabled(true);
            btnPlay2.setClickable(true);
        }
        falgTime = 0;
        subtime = 0;
        seekBar.setProgress(0);
        seekBar.setEnabled(false);

    }

    private void play() {

        mediaPlayer = new MediaPlayer();
        try {
            mediaPlayer.setDataSource(filePath);
            mediaPlayer.prepareAsync();

            // 为播放器注册
            mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {

                public void onPrepared(MediaPlayer mp) {
                    // TODO Auto-generated method stub
                    mediaPlayer.start();
                    btnPlay2.setEnabled(false);
                    btnPlay2.setClickable(false);
                    seekBar.setMax(mediaPlayer.getDuration());
                    handler.post(updateThread);
                    seekBar.setEnabled(true);
                }
            });

            // 注册播放完毕后的监听事件
            mediaPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {

                public void onCompletion(MediaPlayer mp) {
//                    mediaPlayer.release();
//                    mediaPlayer = null;
                    btnPlay2.setEnabled(true);
                    btnPlay2.setClickable(true);
                    et_time.setBase(SystemClock.elapsedRealtime());
                    et_time.start();
                    et_time.stop();
                    seekBar.setProgress(0);
                }
            });
            falgTime = SystemClock.elapsedRealtime();
            et_time.setBase(falgTime);
            et_time.start();

            et_time.setOnChronometerTickListener(new Chronometer.OnChronometerTickListener() {
                @Override
                public void onChronometerTick(Chronometer chronometer) {


                }
            });

            seekBar.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
                @Override
                public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
                    if (fromUser == true && mediaPlayer != null) {
                        Log.e("Test", "onProgressChanged------ progress "+progress);
                        mediaPlayer.seekTo(progress);
                        falgTime = SystemClock.elapsedRealtime();
                        beginTime = falgTime - seekBar.getProgress();
                        et_time.setBase(beginTime);
//                        et_time.start();


//                        final int ctime = mediaPlayer.getDuration() / progress;
                        //时间*比特率 = 大小 (rate * 1 * 16 / 8) * (duration / 1000);
                        //时间 = 大小/比特率

                        int ctime = progress/((rate * 1 * 16 / 8) * (duration / 1000));
                        currentTime.setText( ctime+ "s");

                    }
                }

                @Override
                public void onStartTrackingTouch(SeekBar seekBar) {

                }

                @Override
                public void onStopTrackingTouch(SeekBar seekBar) {
//                    startPos = seekBar.getProgress();
                    currentProgress = seekBar.getProgress();

                }
            });


        } catch (IOException e) {
            e.printStackTrace();
        }
        // mediaPlayer.prepare(); // C/C++ 播放器引擎的初始化
        // 同步方法
        // 采用异步的方式


    }

    private OnEventListener onEventListener;

    public void setOnEventListener(OnEventListener onEventListener) {
        this.onEventListener = onEventListener;
    }


    android.os.Handler errorHandler = new android.os.Handler() {
        @Override
        public void handleMessage(Message msg) {

            if (onEventListener != null) {
                onEventListener.onError("error");
            }

        }
    };

    private void startThread() {

        if (startPos == 0) {//开始位置
            try {
                randomAccessFile.seek(44);
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        mThreadFlag = true;
        i = 0;
        j = -1;
        STATUS = 1;
        thread = new Thread() {
            @Override
            public void run() {

                if (startTime == 0) {
                    startTime = System.currentTimeMillis();

                }
                byte[] arrayOfByte = new byte[bufferSize];
                short[] arrayOfShort = new short[bufferSize];
                while (mThreadFlag) {

                    try {
                        if (audioRecord == null || STATUS != 1) {
                            continue;
                        }
                        int bufferReadResult = audioRecord.read(arrayOfByte, 0, bufferSize);
                        int bufferReadResult2 = audioRecord.read(arrayOfShort, 0, bufferSize);

                        Log.e("Test", "run------ bufferReadResult "+bufferReadResult);
                        Log.e("Test", "run------ bufferReadResult2 "+bufferReadResult2);

                        if (audioRecord.getRecordingState() != AudioRecord.RECORDSTATE_RECORDING || bufferReadResult <= 0) {
                            break;
                        }

                        i = 1;

                        randomAccessFile.write(arrayOfByte);

                        waveformView.updateAudioData(arrayOfShort);

                        byte[] tmpBuf = new byte[bufferReadResult];
                        System.arraycopy(arrayOfByte, 0, tmpBuf, 0, bufferReadResult);
                        audioTrack.write(tmpBuf, 0, tmpBuf.length);

                        pjByteBuffer(tmpBuf);


                        curFileLength = (int) randomAccessFile.length() / 1024;
                        Log.e("Test", "run------ curFilelength:" + curFileLength + ",startPos:" + startPos + ",endPos:" + endPos + ",isRewrite:" + isRewrite);
                        int time = (int) (System.currentTimeMillis() - startTime);
                        Log.e("Test", "run------ time: " + time);
                        Log.e("Test", "run------ bytes:" + arrayOfByte.length);
                        Log.e("Test", "run------ getFilePointer:" + randomAccessFile.getFilePointer());

                        startPos = (int) randomAccessFile.getFilePointer();


                        if (time >= restOfTime) {
                            stopRecord();
                        }
                        onFileChangedListener.onBufferRecevied(startPos, endPos, arrayOfByte, curFileLength, isRewrite);


//                        Test t1 = Test.this;
//                        t1.i = 1+t1.i;
//
//                        long length = randomAccessFile.getFilePointer() + arrayOfByte.length;
//                        xxx(this,length);
//                        if (endPos>curFileLength){
//                            xxx(this,endPos);
//                        }
//                        randomAccessFile.write(arrayOfByte);
//                        onFileChangedListener.onBufferRecevied(startPos,endPos,arrayOfByte,curFileLength,isRewrite);
//
//                        Test t2 =Test.this;
//                        t2.j = 1+t2.j;
//                        if (i!=0||j!=0){
//                            continue;
//                        }
//                        xxx(this,false);
//                        errorHandler.sendEmptyMessage(0);


                    } catch (Exception e) {
                        e.printStackTrace();
                        errorHandler.sendEmptyMessage(0);
                    }

                }


            }
        };
        thread.start();


    }


    private byte[] pjarray(byte[] src, byte[] dest) {
        byte[] newBytes = new byte[src.length + dest.length];

        System.arraycopy(src, 0, newBytes, 0, src.length);
        System.arraycopy(dest, 0, newBytes, src.length, dest.length);

        return newBytes;
    }

    private void pjByteBuffer(byte[] tmpBuf) {

        if (sampleBytes == null) {
            sampleBytes = tmpBuf;
        } else {
            sampleBytes = pjArray(sampleBytes, tmpBuf);
        }


    }


    private void pauseReview() {
        audioTrackFlag = false;
        audioTrack.pause();
        audioTrack.flush();
        Log.e("Test", "pauseReview------ ");

    }

    private void startReview(boolean b) {
        if (audioTrack == null) {
            initAudioTack();
        }
        audioTrack.play();
        audioTrackFlag = true;
        audioTrackThread = new Thread() {
            @Override
            public void run() {
                try {
                    bytes = new byte[minBufferSize];
                    while (randomAccessFile.read(bytes) != -1 && audioTrackFlag) {

                        Log.e("Test", "run------ ");
                        Log.e("Test", "run------audiotrackflag is  " + audioTrackFlag);
                        Log.e("Test", "run------wrtie data in audiotrack ");

                    }
                    Log.e("Test", "run------ audiotrack end.");

                } catch (Exception e) {

                }
            }
        };
        audioTrackThread.start();


    }


    public void pauseRecord() {

        if (audioRecord != null) {
            audioRecord.stop();
            mThreadFlag = false;
        }
    }

    private void reset() {
        startPos = 0;
        endPos = 0;
        curFileLength = 44;
        isRewrite = false;
    }


    private void resumeRecord() {


        while (isRewrite) {//写文件


            try {
                if (randomAccessFile.getFilePointer() != endPos || !isRewrite) {//不可写 ,或者选中位置不是文件指针所在位置
                    startPos = (int) randomAccessFile.getFilePointer(); // 从文件指针位置开始
                }
                if (!isRewrite) {//不写文件

                    if (44 + startPos >= endPos) {//
                        continue;
                    }

                    isRewrite = true;

                }


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


            audioRecord.startRecording();
            if (thread == null || !mThreadFlag) {
                startThread();
            }

        }
    }

    private void startRecording() {
        try {
            audioRecord.startRecording();

//            if (thread==null||!mThreadFlag){
//                startThread();
//            }
            startThread();
            Log.e("Test", "startRecording------ ");
        } catch (Exception e) {
            initRecorder(true);
        }

    }

    public int getMinBufferSize() {
        return minBufferSize;
    }

    public void getMinBufSize() {
        recBufSize = AudioRecord.getMinBufferSize(frequency, 12, 2);
    }

    public void setOnFileChangedListener(OnFileChangedListener onFileChangedListener) {
        this.onFileChangedListener = onFileChangedListener;
    }

    public void setDuration(int duration) {
        this.duration = duration;
    }

    interface OnFileChangedListener {
        void onBufferRecevied(long startPos, long endPos, byte[] b1, long currenFileLength, boolean isRew);
    }

    interface OnEventListener {
        void onError(String s);

        void onRecordComplete();

        void onVolumnChanged(double vl);
    }

    public String creatFile() {
//        copyWaveFile(filePath,filePath,true);
        return outPath;
    }

    private void moveToPrevious(long pl) {
        try {
            long l = 44 + 4 * (pl * rate / 1000l);
            randomAccessFile.seek(l);
            Log.e("Test", "moveToPrevious------ offset:" + l + " length:" + randomAccessFile.length());

        } catch (Exception e) {

        }

    }

    @Override
    protected void onPause() {
        super.onPause();
        stopRecord();
    }

    @Override
    protected void onStop() {
        super.onStop();
        closeStream();
    }

    private void stopRecord() {

        try {
            mThreadFlag = false;
            time = 0;
            thread = null;

            if (audioRecord != null) {
                if (audioRecord.getRecordingState() == AudioRecord.RECORDSTATE_RECORDING) {
                    audioRecord.stop();
                    Log.e("Test", "stopRecord------ ");
                }
                audioRecord.release();
                audioRecord = null;

            }
            closeStream();


        } catch (Exception e) {

        }


    }

    private void closeStream() {
        try {
            if (randomAccessFile != null) {
                randomAccessFile.close();
            }
        } catch (Exception e) {

        }

    }


    float getDensity() {
        DisplayMetrics metrics = new DisplayMetrics();
        getWindowManager().getDefaultDisplay().getMetrics(metrics);
        return metrics.density;
    }


}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持编程网。

--结束END--

本文标题: Android实现录音声波图

本文链接: https://www.lsjlt.com/news/172091.html(转载时请注明来源链接)

有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

本篇文章演示代码以及资料文档资料下载

下载Word文档到电脑,方便收藏和打印~

下载Word文档
猜你喜欢
  • Android实现录音声波图
    本文实例为大家分享了Android实现录音声波图的具体代码,供大家参考,具体内容如下 图像类: package com.akm.test; import android.cont...
    99+
    2022-11-13
    Android录音声波图 Android录音声波 Android声波图
  • Android实现声音采集回声与回声消除
    本文实例为大家分享了Android实现声音采集回声与回声消除的具体代码,供大家参考,具体内容如下 一、回声产生的原因   回声(或称回音)是指障碍物对声音的反射。声波在遇到障碍物时,...
    99+
    2024-04-02
  • Android中语音声波控件以及条形波控件怎么用
    这篇文章主要为大家展示了“Android中语音声波控件以及条形波控件怎么用”,内容简而易懂,条理清晰,希望能够帮助大家解决疑惑,下面让小编带领大家一起研究并学习一下“Android中语音声波控件以及条形波控件怎么用”这篇文章吧。SoundW...
    99+
    2023-05-30
    android
  • Android实现录音静音降噪
    本文实例为大家分享了Android实现录音静音降噪的具体代码,供大家参考,具体内容如下 需求: 客户反馈产品的录音里面很多杂音(因为我们把Codec的录音增益调至最大,且电路上没有专...
    99+
    2022-11-13
    Android录音静音降噪 Android静音降噪 Android录音降噪
  • wavesurfer.js绘制音频波形图的实现
    1.查看效果图 向前选中: 向后选中: 代码如下(示例): <template> <div class="waveSurfer"> <d...
    99+
    2024-04-02
  • Android实现音频录音与播放
    目录一、PCM 、WAV、AAC 的文件头介绍二、使用 AudioRecord 实现录音生成 PCM 文件三、PCM 转化为 WAV四、PCM 转化为 AAC 文件格式五、Audio...
    99+
    2022-11-13
    Android音频录音 Android音频播放 Android录音播放
  • vue实现录音功能js-audio-recorder带波浪图效果的示例
    目录前言:因为业务需要,现在将整理的录音功能资料记录下,使用插件js-audio-recorder实现效果:可得到三种录音数据,pcm,wav,mp3 等官方api入口:点我(网不好...
    99+
    2022-11-13
    vue js-audio-recorder录音 vue  录音
  • windows7系统怎么调节声音的波形图文教程
    点击电脑的左下角扬声器 进入这个里的 扬声器图标   进入之后是这样的   进入[级别   进入第一个[平衡B]的选项 只要调节 左前和右前两个选项的变化大小取不同的值就可以了,...
    99+
    2023-05-30
    win7 声音波形 图文 声音 系统 波形 windows7
  • Android简单自定义音乐波动特效图
    本文实例为大家分享了Android简单自定义音乐波动特效图的具体代码,供大家参考,具体内容如下 最终效果: 思路:就是绘制一个不断变化高度的矩形或者是宽虚线 1.自定义属性: ...
    99+
    2024-04-02
  • Android如何实现录音功能
    这篇文章给大家分享的是有关Android如何实现录音功能的内容。小编觉得挺实用的,因此分享给大家做个参考,一起跟随小编过来看看吧。本文介绍了Android实现录音的实例代码(MediaRecorder),分享给大家,具体如下:Android...
    99+
    2023-05-30
    android
  • Java怎么实现图像与声音效果
    这篇文章主要介绍“Java怎么实现图像与声音效果”,在日常操作中,相信很多人在Java怎么实现图像与声音效果问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”Java怎么实现图像与声音效果”的疑惑有所帮助!接下来...
    99+
    2023-06-03
  • Android利用MediaRecorder实现录音功能
    本文实例为大家分享了Android利用MediaRecorder实现录音功能 的具体代码,供大家参考,具体内容如下 android用手机录音保存到sd卡中; 布局文件: &...
    99+
    2024-04-02
  • Android使用Flutter实现录音插件
    目录安卓部分手动注册Android和Dart的通讯安卓录音Dart module部分iOS部分手动注册插件iOS插件Dart调用部分原生提供功能,Dart module 通过 met...
    99+
    2022-11-13
    Android Flutter录音 Android 录音功能
  • Android使用AudioRecord实现录音功能
    前言 Android使用AudioRecord实现录音 提示:以下是本篇文章正文内容,下面案例可供参考 一、AudioRecord使用 Android平台可以使用AudioRecor...
    99+
    2022-11-13
    Android AudioRecord 录音
  • HTML5中怎么实现声音录制/播放功能
    这篇文章主要介绍HTML5中怎么实现声音录制/播放功能,文中介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们一定要看完!html代码:<!DOCTYPE html><html>  &...
    99+
    2023-06-09
  • OpenCV实现图像滤波之双边滤波
    本文实例为大家分享了opencv实现双边滤波的具体代码,供大家参考,具体内容如下 1、2D卷积 #!/usr/bin/env python3 # -*- coding: utf-...
    99+
    2024-04-02
  • Android如何实现动态滚动波形图(心电图)功能
    目录一、前言二、效果图三、功能实现四、如何使用一、前言 最近涉及的某个医疗相关的业务,传感器数据传递上来需要实现示波器的效果,心电图的效果,目前交付效果还算理想,于是封装了一下,方便...
    99+
    2024-04-02
  • Android一个类实现录音与播放实例
    目录前言实现效果代码实现XML静态权限动态权限总结前言 最近混合开发的项目 在做语音识别时 h5拿不到麦克风的权限几经周折 开发任务又落到了原生开发这里 先写一个demo实现录音和播...
    99+
    2024-04-02
  • 在Android中使用MediaRecorder实现录音功能
    在Android中使用MediaRecorder实现录音功能?针对这个问题,这篇文章详细介绍了相对应的分析和解答,希望可以帮助更多想解决这个问题的小伙伴找到更简单易行的方法。MediaRecorder已经集成了录音、编码、压缩等,支持少量的...
    99+
    2023-05-31
    android mediarecorder roi
  • 如何在Android中自定义一个音乐波动特效图
    今天就跟大家聊聊有关如何在Android中自定义一个音乐波动特效图,可能很多人都不太了解,为了让大家更加了解,小编给大家总结了以下内容,希望大家根据这篇文章可以有所收获。Android是什么Android是一种基于Linux内核的自由及开放...
    99+
    2023-06-14
软考高级职称资格查询
编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
  • 官方手机版

  • 微信公众号

  • 商务合作