我称之为主要活动的子活动。这个子活动应该从用户那里拿几个数字(我使用编辑文本控件来实现这一点),将它们保存到另一个类中的静态变量并终止。我希望主要活动等待子活动,但两者都只是同时运行。即使这样做也没有用:
Thread t = new Thread(new Runnable(){
public void run(){
Log.v("==================", "run "+new Date());
startActivityForResult(new Intent(ctx,myCustomSubactivity.class),1);
} });
Log.v("==================", "calling run "+new Date());
t.start();
try {
t.join();
} catch (InterruptedException e) {Log.v("==================", "can't join");}
Log.v("==================", "back from activity "+new Date());
你知道如何强迫主要活动等待吗? Android中不支持Thread.wait()方法(程序抛出错误)。
答案 0 :(得分:7)
可能是我遗漏了一些东西,但为什么不只是使用startActivityForResult
和onActivityResult
机制?你可以从你的意图得到你的意图的结果。
编辑:顺便说一下,据我所知,如果你从Object.wait()
代码运行Activity
,如果保持用户界面,则会导致Application not responding
错误。
答案 1 :(得分:3)
我同意Nikolay这绝对是安卓的方法。
在子活动使用startActivityForResult中使用setResult启动子活动,以在数据包中添加您需要的所有数字的结果代码和意图。
在您的第一个活动中覆盖onActivityResult并从意图中检索数字。
如果你使用静态变量,这在第一时间似乎更容易,但是它非常不安全,并且在某些情况下这可能不起作用。如果您的程序被发送到后台,您的活动将被保存,但如果手机内存不足,系统将关闭您的程序,用户恢复后,一切看起来就像用户离开它的那一刻,但静态变量将被重新创建为他们的初始化值。
尝试习惯android activity lifecycle的工作方式。使用此方法将减少已用内存和更好的用户体验。
答案 2 :(得分:3)
查看Notepad example,它涵盖了这种情况。正如其他人所说,Android的方式是让你的第一个活动启动你的第二个活动(不是子活动!)并异步监听响应(不是暂停或等待,不需要加入等)。
答案 3 :(得分:2)
嗯......你可以这样做(顺便说一下,没有直接的方式):
有一个单独的类,我们称之为Monitor:
public class Singleton
{
private Singleton() { }
private static Singleton instance = new Singleton();
public static Singleton getInstance() {
return instance;
}
}
public class ParentActivity extends Activity
{
private void startAndWait()
{
Intent i = new Intent();
// initialize i
startActivityForResult(i);
Singleton si = Singleton.getInstance();
synchronized(si)
{
si.wait();
}
//do remaining work
}
}
public class ChildActivity extends Activity
{
protected void onCreate(Bundle savedInstance)
{
//do all the work
Singleton si = Singleton.getInstance();
synchronized(si)
{
si.notify();
}
}
}
答案 4 :(得分:2)
我不是来判断这是不是一个好的模式,但如果你真的需要一个等待子活动的活动,你可以尝试这种方法:
我在我的应用程序中做了类似的事情并且恕我直言有充分的理由(在应用程序启动或恢复时不打扰用户登录屏幕,应用程序尝试重新使用存储在安全位置的凭据,仅在如果它失败了,它会显示这个登录屏幕。所以是的,基本上我的应用程序中的任何活动都可以“暂停”并等待用户在登录活动中提供正确的凭据,登录屏幕完成后应用程序继续正确暂停(在父活动中)。
在代码中它将是这样的:
ParentActivity:
public class ParentActivity extends Activity {
private static final String TAG = ParentActivity.class.getSimpleName();
public static class Lock {
private boolean condition;
public boolean conditionMet() {
return condition;
}
public void setCondition(boolean condition) {
this.condition = condition;
}
}
public static final Lock LOCK = new Lock();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.parent_layout);
// do whatever logic you need and anytime you need to stat sub-activity
new ParentAsyncTask().execute(false);
}
private class ParentAsyncTask extends AsyncTask<Boolean, Void, Boolean> {
@Override
protected Boolean doInBackground(Boolean... params) {
// do what you need and if you decide to stop this activity and wait for the sub-activity, do this
Intent i = new Intent(ParentActivity.this, ChildActivity.class);
startActivity(i);
synchronized (LOCK) {
while (!LOCK.conditionMet()) {
try {
LOCK.wait();
} catch (InterruptedException e) {
Log.e(TAG, "Exception when waiting for condition", e);
return false;
}
}
}
return true;
}
}
}
ChildActivity:
public class ChildActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.child_layout);
// do whatever you need in child activity, but once you want to finish, do this and continue in parent activity
synchronized (ParentActivity.LOCK) {
ParentActivity.LOCK.setCondition(true);
ParentActivity.LOCK.notifyAll();
}
finish();
// if you need the stuff to run in background, use AsyncTask again, just please note that you need to
// start the async task using executeOnExecutor method as you need more executors (one is already occupied), like this:
// new ChildAsyncTask().executeOnExecutor(ChildAsyncTask.THREAD_POOL_EXECUTOR, false);
}
}