Note that there are some explanatory texts on larger screens.

plurals
  1. POwhat is a good way to stop a thread in android
    primarykey
    data
    text
    <p>I am trying to passthrough the input obtained from the microphone to the speaker (the goal is to be able to perform audio processing in real time in the future). This is the code: </p> <pre><code>public class MainActivity extends Activity { AudioManager am = null; AudioRecord record =null; AudioTrack track =null; final int SAMPLE_FREQUENCY = 44100; final int SIZE_OF_RECORD_ARRAY = 1024; // 1024 ORIGINAL final int WAV_SAMPLE_MULTIPLICATION_FACTOR = 1; int i= 0; boolean isPlaying = true; class MyThread extends Thread{ @Override public void run(){ recordAndPlay(); } } MyThread newThread; private void init() { int min = AudioRecord.getMinBufferSize(SAMPLE_FREQUENCY, AudioFormat.CHANNEL_IN_MONO, AudioFormat.ENCODING_PCM_16BIT); record = new AudioRecord(MediaRecorder.AudioSource.VOICE_COMMUNICATION, SAMPLE_FREQUENCY, AudioFormat.CHANNEL_IN_MONO, AudioFormat.ENCODING_PCM_16BIT, min); int maxJitter = AudioTrack.getMinBufferSize(SAMPLE_FREQUENCY, AudioFormat.CHANNEL_OUT_MONO, AudioFormat.ENCODING_PCM_16BIT); track = new AudioTrack(AudioManager.MODE_IN_COMMUNICATION, SAMPLE_FREQUENCY, AudioFormat.CHANNEL_OUT_MONO, AudioFormat.ENCODING_PCM_16BIT, maxJitter, AudioTrack.MODE_STREAM); } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); setVolumeControlStream(AudioManager.MODE_IN_COMMUNICATION); init(); newThread = new MyThread(); newThread.start(); } @Override public boolean onCreateOptionsMenu(Menu menu) { // Inflate the menu; this adds items to the action bar if it is present. getMenuInflater().inflate(R.menu.main, menu); return true; } private void recordAndPlay() { short[] lin = new short[SIZE_OF_RECORD_ARRAY]; int num = 0; am = (AudioManager) this.getSystemService(Context.AUDIO_SERVICE); am.setMode(AudioManager.MODE_IN_COMMUNICATION); record.startRecording(); track.play(); while (true) { num = record.read(lin, 0, SIZE_OF_RECORD_ARRAY); for(i=0;i&lt;lin.length;i++) lin[i] *= WAV_SAMPLE_MULTIPLICATION_FACTOR; track.write(lin, 0, num); } } public void passStop(View view){ Button playBtn = (Button) findViewById(R.id.playBtn); // /* if(!isPlaying){ record.startRecording(); track.play(); isPlaying = true; playBtn.setText("Pause"); } else{ record.stop(); track.pause(); isPlaying=false; playBtn.setText("Pass through"); } // */ } /* @SuppressWarnings("deprecation") @Override public void onDestroy(){ newThread.stop(); } */ @Override protected void onDestroy() { android.os.Process.killProcess(android.os.Process.myPid()); // killProcess(android.os.Process.myPid()); } } </code></pre> <p>Brief overview:<br> The <code>while(true) {}</code> infinite loop in <code>recordAndPlay()</code> function continuously reads raw audio samples from the microphone and outputs the raw samples to the speaker. <code>recordAndPlay()</code> is called from a Thread started in the <code>onCreate()</code> function. So it starts sending the input on the microphone to the speaker as soon as the program starts (well actually after a few seconds lag but I think this latency in unavoidable). I also have a button that can pause and resume this pass through. Now if the Thread is not stopped, the pass through continues even when I exit the application or the application looses focus (so even when the phone is on the desktop it keeps doing the passthrough). </p> <pre><code>@SuppressWarnings("deprecation") @Override public void onDestroy(){ newThread.stop(); } </code></pre> <p>This code causes the app to crash on exit (<strong>Why?</strong>) so I used </p> <pre><code>@Override protected void onDestroy() { android.os.Process.killProcess(android.os.Process.myPid()); // killProcess(android.os.Process.myPid()); } </code></pre> <p>that I found somewhere in stackoverflow (I forgot where). It seems to do what I want for now, but I want know if this is the proper way to stop the Thread or not. It does what I need, that is, it stops the passthrough when I exit the application, but I am not sure what exactly the killProcess() function does to my application overall, and if it is the best way to stop a Thread that I started myself. </p> <p>Also, I can get the same effect if I exit my application (or loose focus to it) while the passthrough is being paused. But I assume this means the Thread is still running which means the infinite loop is also continuously running as well. Is it a good idea to do this, that is, just leave the Thread running, as long as my overall program is behaving as I want it to? What if I have lots of Threads or other background processes running? Can this practice cause memory problems in the future if the app grows too big?</p>
    singulars
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    plurals
    1. This table or related slice is empty.
    1. This table or related slice is empty.
    1. This table or related slice is empty.
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload