2013-07-08 2 views
1

나는 짹짹 신호를 통해 텍스트를 보내기 위해 응용 프로그램을 개발 중입니다. 기본적으로 나는 사용자에게 텍스트를 쓸 기회를 주며 시작 빈도, 최종 빈도 및 전송할 비트의 시간 간격과 지속 시간에 대한 다른 옵션을 선택합니다.안드로이드 응용 프로그램이 오디오 신호를 몇 번 생성 한 후 충돌합니다.

나는 텍스트를 문자로 분할하고, ASCII 정수로 변환하고,이 정수를 바이너리로 변환 한 다음, 초기 주파수에서 최종 주파수로가는 5ms 삑 소리와 함께 챠프 신호 (Big Endian)로 전송합니다 (아래에서 위로) 1을 보내고, 마지막에서 초기 주파수로 보냅니다.

07-08 15:09:58.036: E/AudioTrack(8747): AudioFlinger could not create track, status: -12 
07-08 15:09:58.036: E/AudioTrack-JNI(8747): Error initializing AudioTrack 
07-08 15:09:58.036: E/AudioTrack-Java(8747): [ android.media.AudioTrack ] Error code -20 when initializing AudioTrack. 
07-08 15:09:58.044: W/dalvikvm(8747): threadid=13: thread exiting with uncaught exception (group=0x40f77930) 
07-08 15:09:58.051: E/AndroidRuntime(8747): FATAL EXCEPTION: Thread-445 
07-08 15:09:58.051: E/AndroidRuntime(8747): java.lang.IllegalStateException:play() called on uninitialized AudioTrack. 
07-08 15:09:58.051: E/AndroidRuntime(8747):  at android.media.AudioTrack.play(AudioTrack.java:883) 
07-08 15:09:58.051: E/AndroidRuntime(8747):  at android.nacho.UltraSoundSender.AudioDevice.<init>(AudioDevice.java:19) 
07-08 15:09:58.051: E/AndroidRuntime(8747):  at android.nacho.UltraSoundSender.ChirpGenerator.playDOWN(ChirpGenerator.java:104) 
07-08 15:09:58.051: E/AndroidRuntime(8747):  at android.nacho.UltraSoundSender.UltraSoundSender$1$1.run(UltraSoundSender.java:61) 
07-08 15:09:58.051: E/AndroidRuntime(8747):  at java.lang.Thread.run(Thread.java:856) 
: (아래까지) 그것은 매우 간단하고 작동하고 있지만, 송신 버튼을 몇 번을 누른 후,이 충돌, 그리고 내가 로그 캣에서 다음과 같은 오류 메시지를 얻을 수 0

을 보내

public class UltraSoundSender extends Activity { 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.activity_ultra_sound_sender); 


     Button btnCode = (Button) findViewById(R.id.btnCode); 
     btnCode.setOnClickListener(new OnClickListener() { 

      //@Override 
      public void onClick(View arg0) {    


       new Thread(new Runnable() 
       { 
        public void run() 
        { 


         String word= ((EditText)findViewById(R.id.Line)).getText().toString(); 
         int IniFreq=Integer.parseInt(((EditText)findViewById(R.id.IniFreq)).getText().toString()); 
         int FinFreq=Integer.parseInt(((EditText)findViewById(R.id.FinFreq)).getText().toString()); 
         int bitLength=Integer.parseInt(((EditText)findViewById(R.id.bitLength)).getText().toString()); 
         int bitGap=Integer.parseInt(((EditText)findViewById(R.id.bitGap)).getText().toString()); 

         Integer digits[]= new Integer[64]; 
         int NumChar= word.length(); 

         //This split the string in chars 
         for(int i = 0; i < NumChar ; i++){ 

          digits[i]=(int)word.charAt(i); 

          } 


         double impulseDuration = 250; //not negotiable 
         int Delay=(int) (bitGap-((int)impulseDuration*0.8)); 
         for(int IndexChar= 0; IndexChar< NumChar ; IndexChar++) 
         { 

          new ChirpGenerator().playDOWN(IniFreq*1000, FinFreq*1000, impulseDuration, digits[IndexChar], bitLength); 
          try { 
           Thread.sleep(Delay); //Time diference since whe generate one bit and the next one 
          } catch (InterruptedException e) { 
           // TODO Auto-generated catch block 
           e.printStackTrace(); 
          } 
         } 
         Thread.currentThread().interrupt(); 

         // enableButton(true); 
        } 

       }).start(); 

      } 
     }); 


} 

    //Enable/disable button 
    private void enableButton(boolean isEnable) 
    { 
     ((Button)findViewById(R.id.btnCode)).setEnabled(isEnable); 

} 



    @Override 
    public boolean onCreateOptionsMenu(Menu menu) { 
     getMenuInflater().inflate(R.menu.activity_ultra_sound_sender, menu); 
     return true; 


    } 
} 

2 º

:

내가 사용 세 코드는 다음입니다 앱 충돌 할 때 내가 몇 번을 실행하는 이유 4,218,216,891,858,139,367,642,583,210

3 °

package android.nacho.UltraSoundSender; 

import android.media.AudioFormat; 
import android.media.AudioManager; 
import android.media.AudioTrack; 

public class AudioDevice 
{ 
    public static final int SAMPLING_RATE = 44100; //44100; 
    AudioTrack track; 
    short[] buffer = new short[1024]; 

    public AudioDevice() 
    { 
     int minSize =AudioTrack.getMinBufferSize(SAMPLING_RATE, AudioFormat.CHANNEL_CONFIGURATION_MONO, AudioFormat.ENCODING_PCM_16BIT);   
     track = new AudioTrack(AudioManager.STREAM_MUSIC, SAMPLING_RATE, 
             AudioFormat.CHANNEL_CONFIGURATION_MONO, AudioFormat.ENCODING_PCM_16BIT, 
             minSize, AudioTrack.MODE_STREAM); 
     track.play(); 
     int nativeSampleRate = AudioTrack.getNativeOutputSampleRate(AudioManager.STREAM_MUSIC); 

     int sampleRate = track.getSampleRate(); 

    }  

    public void writeSamples(float[] samples) 
    {  
     fillBuffer(samples); 
     track.write(buffer, 0, samples.length); 
    } 

    private void fillBuffer(float[] samples) 
    { 
     if(buffer.length < samples.length) 
     buffer = new short[samples.length]; 

     for(int i = 0; i < samples.length; i++) 
     buffer[i] = (short)Math.round(samples[i] * (float)Short.MAX_VALUE); 
    } 
} 

사람은 말해 줄 수? 감사합니다.

답변

2

AudioTrack 인스턴스를 사용하고 나면 AudioTrack 인스턴스를 닫지 않는 것처럼 보입니다. 끝내 버리면 오디오 트랙의 인스턴스를 닫고 무효화해야합니다.

+0

감사합니다. 실제로 언젠가 전에 실수를 발견했지만, 피드백을받지 못했기 때문에 나는 그 질문을 잊어 버렸습니다. 전체 코드를 읽는 데 시간을내어 주셔서 대단히 감사합니다.) –