ক্রিয়াকলাপের প্রেক্ষাপটের বাইরে থেকে কল করা স্টার্টএটিভিটি ()


367

আমি ListViewআমার অ্যান্ড্রয়েড অ্যাপ্লিকেশনটিতে একটি প্রয়োগ করেছি। আমি ক্লাসের 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?

(বর্তমান ) অধীনে যে কাজ চলছে Contextতা আমি কীভাবে পেতে পারি ?ListViewActivity


1
আমি মনে করি অ্যালেক্সের উত্তরটি আপনার সমস্যার 'গৃহীত' সমাধান হওয়া উচিত, যেহেতু এটি আপনি আরও সাধারণ পদ্ধতিতে উল্লিখিত ত্রুটিটি সংশোধন করে
devanshu_kaushik

10
আমি ভালবাসি যে "আপনি কি চান এটি কি সত্যই?" ... আমি এর আগে একটি বার্তা পেয়েছিলাম "" আপনি কি নিশ্চিত যে কোনও জায়গায় কোনও সম্প্রচার গ্রহণকারীকে নিবন্ধভুক্ত করতে ভোলেননি? " অসাধারণ! আমাদের স্কোয়াবগুলিকে সহায়তা করতে এই ছোট্ট সমস্ত বার্তা যিনি রেখেছেন তাদের প্রতি হ্যাটস।
Nerdy Bunz

1
আমি এই ইস্যু পূরণ। আমি যখন টার্গেটএসডিপি ভার্সনটি 28-এ আপডেট করেছি
বিভ্রম

উত্তর:


574

উভয় ক্ষেত্রেই

  • আপনার অ্যাডাপ্টারে কনস্ট্রাক্টরের মাধ্যমে প্রসঙ্গ বস্তুটি ক্যাশে করুন বা
  • আপনার দর্শন থেকে এটি পেতে।

বা একটি শেষ উপায় হিসাবে,

  • যুক্ত করুন - আপনার অভিপ্রায় FLAG_ACTIVITY_NEW_TASK পতাকা:

: _

myIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

সম্পাদনা করুন - আমি পতাকা স্থাপন এড়াব কারণ এটি ইভেন্ট এবং ইতিহাসের স্ট্যাকের স্বাভাবিক প্রবাহে হস্তক্ষেপ করবে।


6
আমি সিস্টেম দ্বারা নির্মিত ইনটেন্ট (এবং এভাবে পতাকাগুলি) নিয়ন্ত্রণ করতে পারি না এমন টেক্সটভিউয়ের অটোলিঙ্ক বৈশিষ্ট্য সম্পর্কে কী ?
অ্যালেক্স Semeniuk

75
যখন আমি ভালো কিছু করছেন আমি এই ব্যতিক্রম পেয়ে ছিল context.startActivity(intent);আমি শুধু পরিবর্তন contextথেকে ApplicationContextথেকে Activityপ্রকার। এটি সমস্যার সমাধান করেছে।
সুফিয়ান

@ অ্যালেক্সসেমিনুক কখনও সমাধান খুঁজে পাবে?

@ অ্যালেক্সসেমিনিউক - অডিওলিংক যতক্ষণ আপনি অ্যাডাপ্টারের প্রসঙ্গ হিসাবে কার্যকলাপটি পাস করবেন ততক্ষণ কাজ করবে
জর্জেস

আমি কনটেক্সট অবজেক্টটি কনস্ট্রাক্টরের মাধ্যমে পাস করেছি তবে এটি কাজ করে না। তবে FLAG_ACTIVITY_NEW_TASK আমার জন্য খুব ভাল কাজ করছে ধন্যবাদ।
হিরেন

100

আপনি এটির পরিবর্তে অ্যাডফ্ল্যাগগুলি দিয়ে এটি অর্জন করতে পারেনsetFlags

myIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

ডকুমেন্টেশন অনুসারে এটি করে:

অভিপ্রায় অতিরিক্ত পতাকা যুক্ত করুন (বা বিদ্যমান পতাকা মান সহ)।


সম্পাদনা

অ্যালেক্স ভলভয়ের উত্তর যেমনটি আপনি বলেছেন যে আপনি হস্তগুলি ইতিহাসের স্ট্যাক পরিবর্তন করে থাকেন তবে সচেতন হন :

... পতাকা স্থাপন এড়ান কারণ এটি ইভেন্ট এবং ইতিহাস স্ট্যাকের স্বাভাবিক প্রবাহে হস্তক্ষেপ করবে।


1
আমি খুব একই সমস্যা আছে। উপরের উত্তরগুলি হিসাবে আপনি কি ইতিহাসের স্ট্যাক বা অন্য কোনও সমস্যা নিয়ে সমস্যায় পড়েছেন?
আইনার সুন্দরগ্রেন

1
আপনি যা খুঁজছেন তা সম্পর্কে আমি ঠিক নিশ্চিত নই তবে আপনি এর মতো ইতিহাস ব্যতীত কোনও ক্রিয়াকলাপ শুরু করতে পারেন: উদ্দীপনা: নতুন উদ্দেশ্য (নতুন উদ্দেশ্য) (উদ্দেশ্য: অ্যাকশন_ভিউ, "http: \\ www.google.com")); উদ্দেশ্য; addFlags (Intent.FLAG_ACTIVITY_NO_HISTORY); startActivity (অভিপ্রায়);
ব্রুনো বিয়েরি

কেন এটি এখানেFlags যোগ করার পরামর্শ দেওয়া হয় না? ইভেন্ট এবং ইতিহাসের স্ট্যাকের স্বাভাবিক প্রবাহে হস্তক্ষেপ করা কতটা সমালোচিত?
জেসন Krs

@ জেসনকর্স আপনি অ্যাডফ্লেগ ব্যবহার করতে পারেন। কেবলমাত্র সচেতন হন যে আপনি যুক্ত করা পতাকার উপর নির্ভর করে আপনি ইতিহাসের স্ট্যাকটি পরিবর্তন করতে পারেন। FLAG_ACTIVITY_NEW_TASK এই পরিস্থিতিতে ব্যবহার করা যেতে পারে। আরও বিশদে পড়ুন: developer.android.com/references/android/content/…
ব্রুনো বিরি


40

নীচের মত তৈরি চয়নকারী ব্যবহারের কারণে যদি ত্রুটি হয়ে থাকে:

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);

4
এটা খুব দরকারী ছিল। সঠিকভাবে চয়নকারী অভিপ্রায়টির এই পতাকাটি থাকা উচিত!
মাহদি

2
এটি সঠিক সমাধান এবং ঠিক কী করতে হবে, নতুন_টাস্ক ইনটেন্ট.চুজারে
রাফায়েল

15

তদতিরিক্ত: আপনি যদি খণ্ডে লিস্টভিউতে লিঙ্কগুলি দেখান , এটি এটি তৈরি করবেন না

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

পরিবর্তে কল

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

অ্যাডাপ্টার উভয় ক্ষেত্রেই সূক্ষ্মভাবে কাজ করে, তবে লিঙ্কগুলি কেবলমাত্র শেষের ক্ষেত্রে কাজ করে।


@ ব্যবহারকারী2676468: এটি আমার জন্য অটলিংক সমস্যা সমাধান করেছে।
গিক

এটি একটি গ্রহণযোগ্য উত্তর হওয়া উচিত, পতাকা ব্যবহারের পরিবর্তে এটি আরও ভাল !!
গ্যাস্টন স্যালেন

@ গ্যাস্টানসেইলেন, আমি ব্যবহার করি না getApplicationContext()(অ্যাপ্লিকেশন ইনিশিয়েশন বাদে) তবে এই ব্যতিক্রমটি ধরা পড়ে। সুতরাং, পরিস্থিতি আলাদা হতে পারে।
কুলমাইন্ড

এটি আমার সমস্যা ছিল, আমি প্রসঙ্গে প্রযোজ্য কনটেক্সট () প্রয়োগ করেছি। thisপ্রসঙ্গ হিসাবে সেট করা বর্তমান কার্যকলাপের সাথে সম্পর্কিত হিসাবে কাজ করে।
Brlja

14

আমি মনে করি সম্ভবত আপনি অনিক্লিকলিস্টনারকে ভুল জায়গায় প্রয়োগ করছেন - সাধারণত আপনার অবশ্যই আপনার ক্রিয়াকলাপে একটি OnItemClickListener প্রয়োগ করা উচিত এবং পরিবর্তে এটি তালিকাভিউতে সেট করা উচিত, বা আপনার ইভেন্টগুলির সাথে সমস্যা হবে ...


2
আপনি আমাকে সমাধানের দিকে নিয়ে যান। আমাকে তালিকাভিউতে নিয়োগ করা একটি অনআইটেমিক্লিকলিস্টার ব্যবহার করা দরকার। অন্য কারও জন্য এখানে কিছু লিঙ্ক রয়েছে: বিকাশকারী.আ্যান্ড্রয়েড. com/references/android/widget/… androidpeople.com/… সহায়তার জন্য ধন্যবাদ।
সাকো 73

জেনেরিক উত্তর সরবরাহ করুন। নীচে অ্যালেক্স ভলভয়ের উত্তরটি জেনেরিক পদ্ধতিতে সমস্যার সমাধান করে।
দেবানশু_কাউশিক

উত্তরসূরীদের জন্য: আপনি যদি কোনও উপাদানটিতে সেটলাইস্টেনার (নতুন শ্রোতা) হিসাবে সরাসরি এটি সংজ্ঞায়িত করেন তবে আপনার সম্পূর্ণ কার্যকলাপের জন্য একটি অন্তর্নিহিত রেফারেন্স তৈরি করা হবে যা আপনি বিশ্বাস করবেন না এমন মেমরি ফাঁস হয়ে যাবে। এটি স্থিতিশীল অভ্যন্তর শ্রেণীর শ্রোতা তৈরি করে বা শ্রোতাদের একটি পৃথক শ্রেণিতে স্থানান্তরিত করে যদি এটির একাধিক উত্স থেকে ইনপুট পরিচালনা করতে সক্ষম হয় তবে এটি পরিলক্ষিত হতে পারে।
G_V

9
CustomAdapter mAdapter = new CustomAdapter( getApplicationContext(), yourlist);

অথবা

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

নীচে পরিবর্তন করুন

CustomAdapter mAdapter = new CustomAdapter( this, yourlist);

8

শুরুতে 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);

এটি 28 এবং ততোধিক ডিভাইসের জন্য প্রয়োজনীয়।
মোঃ মহসিন

7

দেখুন, যদি আপনি কোনও পদ্ধতিতে তালিকাগুলির মধ্যে কোনও অভিপ্রায় তৈরি করে থাকেন

override onClick (View v).

তারপরে এই ভিউটির মাধ্যমে প্রসঙ্গটিও কল করুন:

v.getContext ()

এমনকি সেটফ্লেগের প্রয়োজন হবে না ...


এবং ভুল পরিস্থিতি কি ছিল? v.getApplicationContext ()?
কুলমাইন্ড

3

কারও কাছ থেকে এটি Xamarin.Android (MonoDroid) এ পাওয়ার জন্য এমনকি যখন ক্রিয়াকলাপ থেকে স্টার্টএকটিভিটি বলা হয় - এটি আসলে নতুন এআরটি রানটাইম সহ জ্যামারিন বাগ, https://bugzilla.xamarin.com/show_bug.cgi?id=17630 দেখুন


হ্যাঁ উপরের বর্ণিত যা যা করা হয়েছে ঠিক তেমনভাবে আপনাকে করতে হবে, তবে শব্দটির পরিবর্তন হয়েছে ... অভিপ্রায়.সেটফ্ল্যাগস (অ্যাক্টিভিটিফ্ল্যাজস.ইউ নিউটাস্ক);
লুক অলডারটন

3

অ্যালেক্স ভলভয়ের উত্তরটি আরও কিছু বিশদভাবে বর্ণনা করা -

আপনি যদি টুকরো টুকরো করে এই সমস্যাটি পেয়ে থাকেন তবে getActivity () প্রসঙ্গটি পেতে সঠিক কাজ করে

অন্যান্য ক্ষেত্রে:

আপনি যদি ব্যবহার করতে না চান-

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

তারপরে আপনার আউটসাইডক্লাসে এর মতো একটি ফাংশন তৈরি করুন -

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

এখন, আপনার মূল ক্রিয়াকলাপে আপনি যখনই কোনও নতুন আউটসাইডক্লাস করেন তখনই আপনি আউটসাইডক্লাসটিকে সংজ্ঞা হিসাবে কার্যকলাপের প্রসঙ্গটি প্রদান করার পরে উপরের পদ্ধতিটিকে কল করুন। এছাড়াও আপনার মূল ক্রিয়াকলাপে একটি ফাংশন করুন-

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

এখন আপনার আউটসাইডক্লাসে ফিরে আসুন এবং নতুন ক্রিয়াকলাপ শুরু করার জন্য এই জাতীয় কিছু করুন-

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

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

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

এইভাবে আপনি পতাকাগুলির সাথে গোলযোগ না করে বিভিন্ন আউটসাইডক্লাস থেকে কল করা বিভিন্ন ক্রিয়াকলাপ শুরু করতে সক্ষম হবেন।

দ্রষ্টব্য - প্রবন্ধের জন্য কনস্ট্রাক্টরের মাধ্যমে প্রাসঙ্গিক বস্তুটি ক্যাশে না করার চেষ্টা করুন (অ্যাডাপ্টারের সাথে, এটির সূক্ষ্ম) A একটি খণ্ডে একটি খালি কনস্ট্রাক্টর থাকা উচিত অন্যথায় কিছু পরিস্থিতিতে অ্যাপ্লিকেশন ক্রাশ হয়।

কল করতে মনে আছে

OutsideClass.gettingContext(Context context);

onResume () ফাংশনেও।


3

এই ত্রুটিটি তখন ঘটে যখন স্টার্টাক্টিভিটি না জানে যে তার কার্যকলাপটি। সুতরাং অবশ্যই আপনাকে অবশ্যই স্টার্টঅ্যাক্টিভিটি () এর আগে ক্রিয়াকলাপ যুক্ত করতে হবে

আপনি সেট করতে হবে

context.startActivity(yourIntent);

যদি আপনি কল startActivityকরেন Fragment, একজন কলকারী প্রায়শই খণ্ড হতে পারে, কোনও ক্রিয়াকলাপ নয়।
কুলমাইন্ড

2

আমার মতে, startActivity()আপনার কোডের কোডটিতে কেবল পদ্ধতিটি ব্যবহার করা ভাল Activity.class। যদি আপনি Adapterএটি অন্য বা অন্য শ্রেণিতে ব্যবহার করেন তবে এর ফলস্বরূপ।


2

আমারও একই সমস্যা ছিল। আপনি যে সমস্ত প্রসঙ্গটি পেরিয়ে গেছেন তা পরীক্ষা করে দেখুন। 'এর জন্য লিঙ্ক ' দরকার ভ্রমণ প্রসঙ্গ না অ্যাপ্লিকেশান প্রসঙ্গে

এটি সেই জায়গা যেখানে আপনার চেক করা উচিত:

১) আপনি যদি লেআউটইনফ্লেটার ব্যবহার করেন তবে আপনি কোন প্রসঙ্গে পাস করেছেন তা পরীক্ষা করে দেখুন check

২) আপনি যদি কোনও অ্যাডাপ্টার ব্যবহার করেন তবে আপনি কোন প্রসঙ্গটি পেরিয়ে গেছেন তা পরীক্ষা করে দেখুন।


2

আমারও একই সমস্যা ছিল। সমস্যাটি প্রসঙ্গে। আপনি যদি কোনও লিঙ্ক খুলতে চান (উদাহরণস্বরূপ চয়নকারীর মাধ্যমে কোনও লিঙ্ক ভাগ করুন) কার্যকলাপ প্রসঙ্গটি পাস করুন, অ্যাপ্লিকেশন প্রসঙ্গে নয়।

myIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)আপনি যদি আপনার কার্যকলাপে না থাকেন তবে যুক্ত করতে ভুলবেন না।


2

আপনার অ্যাডাপ্টার_অ্যাক্টিভিটিতে এই কোডটি ব্যবহার করুন এবং ব্যবহার করুন 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);

এটি কাজ করে ....


1
Intent viewIntent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);    
viewIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);    
startActivity(viewIntent);   

আমি আশা করি এটি কার্যকর হবে।


1

এরপরে বাস্তবায়িত একই সমস্যার মুখোমুখি

intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);

এবং সমস্যার সমাধান পেয়েছি।

আরও একটি কারণ থাকতে পারে যা তালিকার ভিউ অ্যাডাপ্টারের সাথে সম্পর্কিত।
আপনি এই ব্লগটি দেখতে পারেন , এটি খুব ভাল বর্ণনা করেছেন।


সহায়ক ব্লগ, আপনাকে ধন্যবাদ। :)
রুচা ভট্ট জোশী

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);

ফ্ল্যাগগুলি বিশৃঙ্খলা করে স্ট্যাকট্রেস ইতিহাস স্থাপন করুন
ইজিও

1

পতাকা যুক্ত করার ফলে প্রভাবিত হয় event_flowএবংstack_history 'অ্যাপ্লিকেশন প্রসঙ্গটি' অ-ক্রিয়াকলাপে পাস করা ভাল যেখানে থেকে আপনাকে নিম্নলিখিত উপায়ে একটি ক্রিয়াকলাপ শ্রেণি কল করতে হবে:

"ActivityClassName.this" (আপনি এই পদ্ধতিতে প্রসঙ্গটি পাস করার সময় এটিতে অ-ক্রিয়াকলাপের পরিস্থিতি থেকে কোনও ক্রিয়াকলাপ কল করতে হবে এমন সমস্ত বিবরণ এবং তথ্য থাকবে)

সুতরাং পতাকা স্থাপন বা যুক্ত করার দরকার নেই, এটি প্রতিটি ক্ষেত্রেই সূক্ষ্মভাবে কাজ করবে।



0

আপনি যদি কর্ডোভা প্লাগইনে ইনটেন্ট ভাগ করে নেওয়ার আবেদন করছেন তবে পতাকাটি সেট করা কোনও লাভ করবে না। পরিবর্তে এটি ব্যবহার করুন -

cordova.getActivity().startActivity(Intent.createChooser(shareIntent, "title"));

0

আমার পরিস্থিতি কিছুটা আলাদা ছিল, আমি আমার অ্যাপ্লিকেশনটি ব্যবহার করে পরীক্ষা করছি Espressoএবং আমাকে আমার ক্রিয়াকলাপটি ActivityTestRuleইনস্ট্রুমেন্টেশন দিয়ে চালু করতে হয়েছিল Context( এটি কোনওটিই আসছে না Activity)।

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

আমাকে পতাকাগুলি পরিবর্তন করতে হয়েছিল এবং এর সাথে কিছুটা দিক or( |জাভাতে) যোগ করতে হয়েছিল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)

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.