我的程序应该重复一个方法,直到按下一个按钮。 我试过这个,但是不起作用:
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
tts = new TextToSpeech(this, this);
Button button1 = (Button)findViewById(R.id.button1);
Button button2 = (Button)findViewById(R.id.button2);
button1.setOnClickListener(this);
button2.setOnClickListener(this);
}
public void onClick (View v){
switch(v.getId()) {
case R.id.button1:
mainprogram();
break;
case R.id.button2:
perform = false;
break;
}
}
public void mainprogram(){
while(perform == true){
speak();
}
}
(当然我编写了“speak()”方法)
你能告诉我问题出在哪里或者有什么方法可以解决吗?
答案 0 :(得分:4)
问题是你的循环在UI线程上运行。我想当你开始循环时整个用户界面会冻结。
您应该在单独的线程上运行它。像:
case R.id.button1:
Thread th = new Thread(new Runnable(){
public void run(){
mainprogram()
}
}).start();
break;
此外,由于您修改了"执行"从单独的线程中,你还应该使perform变量volatile,以便在修改发生后立即对其他线程可见更改。
您可以在此处详细了解volatile: Do you ever use the volatile keyword in Java?
答案 1 :(得分:0)
要停止while循环,只需使用break;
所以在你的情况下:
while(perform == true){
speak();
if( ... somereason ...) break;
}
哪里......某些理由......应该是有效的代码。
如果方法speak()是决定你是否需要破解的方法,只需将speak()的代码直接放在while循环而不是方法调用中。或者从发言中返回false并检查:if(!speak()) break;
答案 2 :(得分:0)
由于mainprogram将在UI线程上运行,它将阻止所有UI,直到它从循环中断开。
单击R.id.button2将不响应(因为UI线程被阻止),因此执行不会设置为false。
关闭主线程执行主程序,点击该按钮将在以后的某个时间停止
答案 3 :(得分:0)
我认为问题在于你在侦听器和你的UI运行的同一个线程中运行while循环。因此,一旦你的程序进入mainprogram(),它就会在这个循环中挂起,因为它不能再对您的UI做出反应(因此,执行将永远是true
)!
通过在另一个主题中运行mainprogram()
的内容,可以解决您遇到的问题。
您的代码可能如下所示:
class MainActivity extends Activity
{
//...
private static boolean perform;
private static getPerform()
{
return perform;
}
public void onClick (View v){
switch(v.getId()) {
case R.id.button1:
perform = true;
Thread t = new SpeakThread();
t.start();
break;
case R.id.button2:
perform = false;
break;
}
}
}
class SpeakThread extends Thread
{
public void run()
{
while(MainActivity.getPerform())
{
speak();
}
}
}