我的主线程正在创建一个新线程的实例。这个新线程创建了一个节拍器的实例。如果我尝试通过按钮点击主线程调用节拍器play()方法,那么节拍器开始但整个应用程序冻结。
主要活动代码:
public class HomeScreen extends Activity {
MetroThread metronome;
/*** onCreate ***/
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_home_screen);
metronome = new MetroThread();
metronome.start();
}
/*** button clicks ***/
public void st44BtnClick(View v)
{
if(metronome.myMetronome==null)
{
metronome.playMetronome();
}
else if(metronome.myMetronome!=null)
{
metronome.stopMetronome();
}
}
和节拍器线程代码:
public class MetroThread extends Thread
{
//create instance of the metronome
public Metro myMetronome;
public void run()
{
System.out.println("metroThread started");
}
/*** play metronome ***/
public void playMetronome()
{
myMetronome = new Metro();
myMetronome.bpm = 200;
myMetronome.beat = 7;
myMetronome.beatSound = 2000;
myMetronome.sound = 2600;
myMetronome.play();
}
/*** stop metronome ***/
public void stopMetronome()
{
myMetronome.stop();
myMetronome = null;
}
}
如果不是使用按钮点击调用playMetronome方法,我只需从节拍器线程中的run()调用该方法,它工作正常并且不会锁定应用程序。
答案 0 :(得分:0)
那是对的。这些方法在实际调用Thread的Thread中执行。由于您是从UI线程调用它们,因此这些是在UI线程中执行的。尝试从playMetronome
方法
run()
答案 1 :(得分:0)
仅仅因为方法与线程对象相关联并不意味着它在该特定线程上运行。事实上,在这种情况下,您的Metronome
线程实际上已立即退出,一旦您从run()
方法返回,它就会结束。
当您调用playMetronome
方法时,实际上是通过按钮单击线程调用它。
你需要做的是向Metronome
线程发送一个信号,然后让它开始播放...或创建一个新的Metronome
并在按下按钮时启动线程并拥有线程总是播放声音。
答案 2 :(得分:0)
只有来自您的工作线程的run()
调用的代码才能真正在单独的线程中运行。现在你正在创建第二个线程,但是在主线程中进行所有操作(因为你从它调用play()
)
你可以:
1)在第二个线程中添加布尔标志isPlaying
并从mainThread更改它的值
2)在第二个帖子run()
中启动无限循环,有时会在这里检查此标志。