2011-03-18 104 views
7

如何在Android中輕鬆生成合成和絃聲音? 我想使用8bit動態生成遊戲音樂。 試用AudioTrack,但沒有得到很好的聲音效果呢。如何在Android中輕鬆生成合成和絃聲音?

那裏有任何例子嗎?

我曾嘗試下面的代碼沒有成功:

public class BitLoose { 
    private final int duration = 1; // seconds 
    private final int sampleRate = 4200; 
    private final int numSamples = duration * sampleRate; 
    private final double sample[] = new double[numSamples]; 

    final AudioTrack audioTrack; 

    public BitLoose() { 
     audioTrack = new AudioTrack(AudioManager.STREAM_MUSIC, 
       sampleRate, AudioFormat.CHANNEL_CONFIGURATION_MONO, 
       AudioFormat.ENCODING_PCM_8BIT, numSamples, 
       AudioTrack.MODE_STREAM); 
     audioTrack.play(); 
    } 

    public void addTone(final int freqOfTone) { 
     // fill out the array 
     for (int i = 0; i < numSamples; ++i) { 
      sample[i] = Math.sin(2 * Math.PI * i/(sampleRate/freqOfTone)); 
     } 

     // convert to 16 bit pcm sound array 
     // assumes the sample buffer is normalised. 
     final byte generatedSnd[] = new byte[numSamples]; 

     int idx = 0; 
     for (final double dVal : sample) { 
      // scale to maximum amplitude 
      final short val = (short) ((((dVal * 255))) % 255); 
      // in 16 bit wav PCM, first byte is the low order byte 
      generatedSnd[idx++] = (byte) (val); 
     } 
     audioTrack.write(generatedSnd, 0, sampleRate); 
    } 

    public void stop() { 
     audioTrack.stop(); 
    } 

回答

2

我認爲不好的聲音是由於音頻格式:AudioFormat.ENCODING_PCM_8BIT使用簽名樣本,因此1,必須-1轉換之間的正弦0-255字節值,試試這個:

for (final double dVal : sample) { 
    final short val = (short) ((dVal + 1)/2 * 255) ; 
    generatedSnd[idx++] = (byte) val; 
} 

嘗試也改變採樣率11025,因爲4200可能不支持某些設備上:

private final int sampleRate = 11025; 
0

除了答案1,您應該使用:
sample [i] = Math.sin(2 * Math.PI * i /((double) sampleRate/freqOfTone));
而不是
sample [i] = Math.sin(2 * Math.PI * i /(sampleRate/freqOfTone));