424

我已经ListView在我的 Android 应用程序中实现了一个。我ListView使用该类的自定义子类绑定到它ArrayAdapter。在被覆盖的ArrayAdapter.getView(...)方法中,我分配了一个OnClickListener. 在 的onClick方法中OnClickListener,我想发起一个新的活动。我得到了例外:

Calling startActivity() from outside of an Activity  context requires the  
FLAG_ACTIVITY_NEW_TASK flag. Is this really what you want?

我怎样才能得到ContextListView当前Activity)正在工作的?

4

27 回答 27

652

任何一个

  • 通过适配器中的构造函数缓存 Context 对象,或者
  • 从你的角度得到它。

或者作为最后的手段,

  • 在您的意图中添加 - FLAG_ACTIVITY_NEW_TASK 标志:

_

myIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

编辑 - 我会避免设置标志,因为它会干扰事件和历史堆栈的正常流动。

于 2010-10-12T20:40:14.783 回答
109

您可以使用addFlags而不是setFlags

myIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

根据它的文档

向意图添加其他标志(或使用现有标志值)。


编辑

当您使用可能会更改历史堆栈的标志时要小心,正如Alex Volovoy 的回答所说:

...避免设置标志,因为它会干扰事件和历史堆栈的正常流动。

于 2012-11-25T08:33:40.240 回答
74

而不是使用(getApplicationContext)使用YourActivity.this

于 2016-07-27T08:44:42.123 回答
59

如果您因为使用如下创建选择器而出错:

Intent sharingIntent = new Intent(Intent.ACTION_VIEW);
sharingIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
sharingIntent.setData(Uri.parse("http://google.com"));
startActivity(Intent.createChooser(sharingIntent, "Open With"));

设置标志以创建选择器,如下所示:

Intent sharingIntent = new Intent(Intent.ACTION_VIEW);
sharingIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
sharingIntent.setData(Uri.parse("http://google.com"));

Intent chooserIntent = Intent.createChooser(sharingIntent, "Open With");
chooserIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

startActivity(chooserIntent);
于 2016-09-29T01:32:27.480 回答
15

另外:如果你在片段列表视图中显示链接,不要这样创建

adapter = new ListAdapter(getActivity().getApplicationContext(),mStrings);

而是打电话

adapter = new ListAdapter(getActivity(),mStrings);

适配器在这两种情况下都可以正常工作,但链接仅在最后一种情况下有效。

于 2014-09-02T17:52:12.283 回答
14

我想也许你在错误的地方实现 OnClickListener - 通常你肯定应该在你的 Activity 中实现一个 OnItemClickListener 并将它设置在 ListView 上,否则你的事件会出现问题......

于 2010-10-12T20:14:51.590 回答
9
CustomAdapter mAdapter = new CustomAdapter( getApplicationContext(), yourlist);

或者

Context mContext = getAppliactionContext();
CustomAdapter mAdapter = new CustomAdapter( mContext, yourlist);

改为下面

CustomAdapter mAdapter = new CustomAdapter( this, yourlist);
于 2014-05-21T08:59:14.133 回答
9

在开始Android 28(Android P)活动

if ((intent.getFlags() & Intent.FLAG_ACTIVITY_NEW_TASK) == 0
        && (targetSdkVersion < Build.VERSION_CODES.N
                || targetSdkVersion >= Build.VERSION_CODES.P)
        && (options == null
                || ActivityOptions.fromBundle(options).getLaunchTaskId() == -1)) {
    throw new AndroidRuntimeException(
            "Calling startActivity() from outside of an Activity "
                    + " context requires the FLAG_ACTIVITY_NEW_TASK flag."
                    + " Is this really what you want?");
}

所以最好的方法是添加FLAG_ACTIVITY_NEW_TASK

Intent intent = new Intent(context, XXXActivity.class);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
    intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
}
context.startActivity(intent);
于 2019-08-14T08:29:00.463 回答
8

看,如果您正在以某种方法在侦听器中创建意图

override onClick (View v).

然后也通过这个视图调用上下文:

v.getContext ()

甚至不需要 SetFlags ...

于 2016-03-11T12:27:33.070 回答
4

对于任何在Xamarin.Android (MonoDroid)上获得此功能的人,即使从活动中调用 StartActivity - 这实际上是带有新 ART 运行时的 Xamarin 错误,请参阅https://bugzilla.xamarin.com/show_bug.cgi?id=17630

于 2014-02-25T15:19:42.040 回答
3

当 startactivity 不知道哪个是他的活动时,就会出现此错误。所以你必须在 startActivity() 之前添加活动

你必须设置

context.startActivity(yourIntent);
于 2014-09-05T08:19:39.493 回答
3

详细阐述 Alex Volovoy 的答案 -

如果您遇到片段问题,getActivity() 可以很好地获取上下文

在其他情况下:

如果您不想使用-

myIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);//not recommend

然后在你的 OutsideClass 中创建一个这样的函数 -

public void gettingContext(Context context){
    real_context = context;//where real_context is a global variable of type Context
}

现在,在您的主要活动中,当您定义将活动的上下文作为参数的 OutsideClass 之后,当您创建一个新的 OutsideClass 时立即调用上述方法。同样在您的主要活动中创建一个功能-

public void startNewActivity(final String activity_to_start) {
    if(activity_to_start.equals("ACTIVITY_KEY"));
    //ACTIVITY_KEY-is a custom key,just to
    //differentiate different activities
    Intent i = new Intent(MainActivity.this, ActivityToStartName.class);
    activity_context.startActivity(i);      
}//you can make a if-else ladder or use switch-case

现在回到你的OutsideClass,开始新的活动,做这样的事情-

@Override
public void onClick(View v) {
........
case R.id.any_button:

            MainActivity mainAct = (MainActivity) real_context;             
            mainAct.startNewActivity("ACTIVITY_KEY");                   

        break;
    }
........
}

这样,您将能够启动从不同 OutsideClass 调用的不同活动,而不会弄乱标志。

注意 - 尽量不要通过片段的构造函数缓存上下文对象(使用适配器,它很好)。片段应该有一个空的构造函数,否则应用程序在某些情况下会崩溃。

记得打电话

OutsideClass.gettingContext(Context context);

在 onResume() 函数中也是如此。

于 2014-10-21T17:21:18.593 回答
2

在我看来,最好startActivity()在你的代码中使用 just的方法Activity.class。如果您在Adapter该类或其他类中使用它,它将导致该结果。

于 2014-08-28T03:42:26.683 回答
2

我也有同样的问题。检查您通过的所有上下文。对于“链接”,它需要活动上下文而不是应用程序上下文

这是您应该检查的地方:

1.) 如果你使用了 LayoutInflater然后检查你通过了什么上下文。

2.) 如果您使用任何适配器,请检查您通过了什么上下文。

于 2015-06-12T07:06:40.880 回答
2

我有同样的问题。问题在于上下文。如果您想打开任何链接(例如通过选择器共享任何链接)传递活动上下文,而不是应用程序上下文。

myIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)如果您不在活动中,请不要忘记添加。

于 2015-12-21T12:40:13.887 回答
2

在您的 Adapter_Activity 中使用此代码并使用context.startActivity(intent_Object)intent_Object.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

像这样:

Intent n_act = new Intent(context, N_Activity.class);
n_act.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(n_act);

有用....

于 2019-02-01T11:56:20.373 回答
1

面临同样的问题然后实施

intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

并解决了问题。

可能还有另一个与列表视图适配器有关的原因。
你可以看到这个博客,描述得很好。

于 2017-06-24T18:24:23.717 回答
1
Intent viewIntent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);    
viewIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);    
startActivity(viewIntent);   

我希望这会奏效。

于 2015-09-11T06:26:36.290 回答
1

由于添加标志会影响event_flow并且stack_history最好将“应用程序上下文”传递给您需要通过以下方式调用活动类的非活动:

“ActivityClassName.this”(当您以这种方式传递上下文时,它将包含您从非活动场景中调用活动所需的所有详细信息和信息)

所以不需要设置或添加标志,这在任何情况下都可以正常工作。

于 2018-05-24T12:49:34.460 回答
1

使用此代码。对我来说很好。从活动之外分享一些东西:

Intent intent = new Intent(Intent.ACTION_SEND);
intent.setType("text/plain");

// Append Text
String Text = "Your Text Here"

intent.putExtra(Intent.EXTRA_TEXT, Text);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

Intent shareIntent = Intent.createChooser(intent,"Share . . . ");
shareIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
G.context.getApplicationContext().startActivity(shareIntent);
于 2017-09-05T05:34:15.287 回答
1

在您的活动中(您在其中调用适配器)只需getActivityContext()更改YourActivity.this. 这是一个例子:

yourAdapter = new YourAdapter(yourList, YourActivity.this); // Here YourActivity.this is the Context instead of getActivityContext()
recyclerView.setAdapter(yourAdapter);
于 2020-09-29T12:23:24.030 回答
0

如果您使用数据绑定,只需获取您的上下文

binding.root.context

这解决了我的问题。

于 2022-01-31T10:54:58.813 回答
0

如果您在 Cordova 插件中调用共享 Intent,则设置标志将无济于事。而是使用这个 -

cordova.getActivity().startActivity(Intent.createChooser(shareIntent, "title"));
于 2017-11-27T17:41:12.177 回答
0
Intent i= new Intent(context, NextActivity.class);
i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_SINGLE_TOP);
于 2016-09-08T10:20:45.870 回答
0

我的情况有点不同,我正在使用测试我的应用程序Espresso,我不得不ActivityTestRule从仪器启动我的活动Context(这不是来自一个Activity)。

fun intent(context: Context) = 
    Intent(context, HomeActivity::class.java)
        .addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)

我不得不更改标志并添加一个or按位(|在Java中)Intent.FLAG_ACTIVITY_NEW_TASK

所以它导致:

fun intent(context: Context) = 
    Intent(context, HomeActivity::class.java)
        .addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP or Intent.FLAG_ACTIVITY_NEW_TASK)
于 2018-01-25T15:00:23.830 回答
0

从 Activity 上下文外部调用 startActivity() 从您的视图中获取

val context = activity.applicationContext
openBrowser(context, MenuUrl.TERM_CONDITION)

   1. val context = binding.root.context // If you are using view binding
   2. val context = yourView.context // If you are not use view binding
    openBrowser(context, MenuUrl.TERM_CONDITION)

谢谢你。

于 2022-02-26T05:35:51.930 回答
0

Kotlin 版本

val intent = Intent(Intent.ACTION_EDIT, ContactsContract.Profile.CONTENT_URI)
intent.flags = Intent.FLAG_ACTIVITY_NEW_TASK
this.startActivity(intent)
于 2019-07-04T10:41:08.797 回答