Android: Sinuswellengenerierung

Ich versuche, mit AudioTrack Sinus-, Rechteck- und Sägezahnwellen zu erzeugen. Das erzeugte Audio klingt jedoch nicht wie eine reine Sinuswelle, sondern wie eine andere Welle, die überlagert ist. Wie würde ich vorgehen, um die reine Sinuswelle wie im zweiten Codebeispiel zu erhalten, während ich die Methode in meinem ersten Beispiel verwende? Da sich das oberste Beispiel nur um einen Teil der in der zweiten verwendeten Arithmetik bewegt, sollten sie dann nicht eine identische Welle erzeugen?

@Override
        protected Void doInBackground(Void... foo) {
            short[] buffer = new short[1024];
            this.track = new AudioTrack(AudioManager.STREAM_MUSIC, 44100, AudioFormat.CHANNEL_CONFIGURATION_MONO, AudioFormat.ENCODING_PCM_16BIT, minBufferSize, AudioTrack.MODE_STREAM);
            float samples[] = new float[1024];

            this.track.play();

            while (true) {
                for (int i = 0; i < samples.length; i++) {
                    samples[i] = (float) Math.sin( (float)i * ((float)(2*Math.PI) * frequency / 44100));    //the part that makes this a sine wave....
                    buffer[i] = (short) (samples[i] * Short.MAX_VALUE);
                }
                this.track.write( buffer, 0, samples.length );  //write to the audio buffer.... and start all over again!

            }           
        }

Hinweis: Dies gibt mir eine reine Sinuswelle:

@Override
        protected Void doInBackground(Void... foo) {
            short[] buffer = new short[1024];
            this.track = new AudioTrack(AudioManager.STREAM_MUSIC, 44100, AudioFormat.CHANNEL_CONFIGURATION_MONO, AudioFormat.ENCODING_PCM_16BIT, minBufferSize, AudioTrack.MODE_STREAM);
            float increment = (float)(2*Math.PI) * frequency / 44100; // angular increment for each sample
            float angle = 0;
            float samples[] = new float[1024];

            this.track.play();

            while (true) {
                for (int i = 0; i < samples.length; i++) {
                    samples[i] = (float) Math.sin(angle);   //the part that makes this a sine wave....
                    buffer[i] = (short) (samples[i] * Short.MAX_VALUE);
                    angle += increment;
                }
                this.track.write( buffer, 0, samples.length );  //write to the audio buffer.... and start all over again!

            }           
        }

Dank an Martijn: Das Problem ist, dass die Welle zwischen den Wellenlängen im Puffer abgeschnitten wird. Das Erhöhen der Puffergröße löst das Problem im zweiten Beispiel. Es scheint, dass die Math.PI * 2-Arithmetik die intensivste der Schleife war. Verschieben Sie diesen Wert in eine externe Variable, die nur einmal berechnet wird, um alles zu lösen.

Antworten auf die Frage(3)

Ihre Antwort auf die Frage