2017-04-01 53 views
0

我有以下代碼:如何增加放大AudioTrack?

public class MainActivity extends Activity { 
    private int freq = 8000; 
    private AudioRecord audioRecord = null; 
    private Thread Rthread = null; 

    int PERMISSION_ALL = 1; 
    String[] PERMISSIONS = {Manifest.permission.RECORD_AUDIO}; 

    private AudioTrack audioTrack = null; 
    byte[] buffer = new byte[freq]; 
    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 

     if(!hasPermissions(this, PERMISSIONS)){ 
      ActivityCompat.requestPermissions(this, PERMISSIONS, PERMISSION_ALL); 
     } 

     android.os.Process.setThreadPriority(android.os.Process.THREAD_PRIORITY_URGENT_AUDIO); 
     final int bufferSize = AudioRecord.getMinBufferSize(freq, 
       AudioFormat.CHANNEL_CONFIGURATION_MONO, 
       AudioFormat.ENCODING_PCM_16BIT); 


     audioRecord = new AudioRecord(MediaRecorder.AudioSource.MIC, freq, 
       AudioFormat.CHANNEL_CONFIGURATION_MONO, 
       MediaRecorder.AudioEncoder.AMR_NB, bufferSize); 

     audioTrack = new AudioTrack(AudioManager.ROUTE_HEADSET, freq, 
       AudioFormat.CHANNEL_CONFIGURATION_MONO, 
       MediaRecorder.AudioEncoder.AMR_NB, bufferSize, 
       AudioTrack.MODE_STREAM); 

     LoudnessEnhancer enhancer = new LoudnessEnhancer(audioTrack.getAudioSessionId()); 

     enhancer.setTargetGain(100); 
     enhancer.setEnabled(true); 


     audioTrack.setPlaybackRate(freq); 
     buffer = new byte[bufferSize]; 
     audioRecord.startRecording(); 
     Log.i("info", "Audio Recording started"); 
     audioTrack.play(); 
     Log.i("info", "Audio Playing started"); 
     Rthread = new Thread(new Runnable() { 
      public void run() { 
       while (true) { 
        try { 
         audioRecord.read(buffer, 0, bufferSize); 
         audioTrack.write(buffer, 0, buffer.length); 

        } catch (Throwable t) { 
         Log.e("Error", "Read write failed"); 
         t.printStackTrace(); 
        } 
       } 
      } 
     }); 
     Rthread.start(); 
    } 

    public static boolean hasPermissions(Context context, String... permissions) { 
     if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && context != null && permissions != null) { 
      for (String permission : permissions) { 
       if (ActivityCompat.checkSelfPermission(context, permission) != PackageManager.PERMISSION_GRANTED) { 
        return false; 
       } 
      } 
     } 
     return true; 
    } 
} 

這個代碼能夠從麥克風輸入讀取並播放上一個揚聲器/耳機連接。到現在爲止還挺好。現在,我需要放大輸入的音量。我試過了解決方案here,但我最終得到了非常失真的音頻。我也試過了LoudnessEnhancer,但它似乎沒有任何效果。

+0

音頻只是一個曲線......爲了增加音量,您只需將曲線上的每個點乘以某個因子......說出1.2 ...如果不夠,請嘗試1.6等......在示例代碼中,您指的是他使用的因子爲2,可能對您的音頻來說太多了......請注意,必須檢查此延伸,並將其剪裁爲位深度所定義的最大和最小允許值......在您的代碼中,您不是顯示你在做這個點乘法的位置...對於16位的深度,保證你拔出兩個字節的數據來切割一個新點,避免單獨地乘以每個字節..也要注意字節順序 –

+0

感謝您的快速響應!也許失真是在這裏使用的錯誤術語。我的意思是音頻在播放時不斷分解。它不會像連續流一樣發揮作用。另外,我確實需要在音頻上放大很多。現在,我不是一名音響工程師,而且我在低級別的東西上很糟糕,所以我們非常感謝代碼示例。 –

回答

0

好吧,我設法讓LoudnessEnhancer工作。我知道這是一個巨大的收益價值,但是我需要在這方面獲得很多收益。以下是可能有類似問題的其他人的更新代碼。

public class MainActivity extends Activity { 
    private int freq = 8000; 
    private AudioRecord audioRecord = null; 
    private Thread Rthread = null; 

    int PERMISSION_ALL = 1; 
    String[] PERMISSIONS = {Manifest.permission.RECORD_AUDIO}; 

    private AudioTrack audioTrack = null; 
    byte[] buffer = new byte[freq]; 
    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_main); 

     if(!hasPermissions(this, PERMISSIONS)){ 
      ActivityCompat.requestPermissions(this, PERMISSIONS, PERMISSION_ALL); 
     } 

     android.os.Process.setThreadPriority(android.os.Process.THREAD_PRIORITY_URGENT_AUDIO); 
     final int bufferSize = AudioRecord.getMinBufferSize(freq, 
       AudioFormat.CHANNEL_CONFIGURATION_MONO, 
       AudioFormat.ENCODING_PCM_16BIT); 


     audioRecord = new AudioRecord(MediaRecorder.AudioSource.MIC, freq, 
       AudioFormat.CHANNEL_CONFIGURATION_MONO, 
       MediaRecorder.AudioEncoder.AMR_NB, bufferSize); 

     audioTrack = new AudioTrack(AudioManager.ROUTE_HEADSET, freq, 
       AudioFormat.CHANNEL_CONFIGURATION_MONO, 
       MediaRecorder.AudioEncoder.AMR_NB, bufferSize, 
       AudioTrack.MODE_STREAM); 

     LoudnessEnhancer enhancer = new LoudnessEnhancer(audioTrack.getAudioSessionId()); 
     NoiseSuppressor.create(audioTrack.getAudioSessionId()); 
     AcousticEchoCanceler.create(audioTrack.getAudioSessionId()); 

     enhancer.setTargetGain(10000); 
     enhancer.setEnabled(true); 


     audioTrack.setPlaybackRate(freq); 
     buffer = new byte[bufferSize]; 
     audioRecord.startRecording(); 
     Log.i("info", "Audio Recording started"); 
     audioTrack.play(); 
     Log.i("info", "Audio Playing started"); 
     Rthread = new Thread(new Runnable() { 
      public void run() { 
       while (true) { 
        try { 
         audioRecord.read(buffer, 0, bufferSize); 
         audioTrack.write(buffer, 0, buffer.length); 

        } catch (Throwable t) { 
         Log.e("Error", "Read write failed"); 
         t.printStackTrace(); 
        } 
       } 
      } 
     }); 
     Rthread.start(); 
    } 

    public static boolean hasPermissions(Context context, String... permissions) { 
     if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && context != null && permissions != null) { 
      for (String permission : permissions) { 
       if (ActivityCompat.checkSelfPermission(context, permission) != PackageManager.PERMISSION_GRANTED) { 
        return false; 
       } 
      } 
     } 
     return true; 
    } 
}