问题
Is there a way in which we can implement onBackPressed()
in Android Fragment similar to the way in which we implement in Android Activity?
As the Fragment lifecycle do not have onBackPressed()
. Is there any other alternative method to over ride onBackPressed()
in Android 3.0 fragments?
回答1:
I solved in this way override onBackPressed
in the Activity. All the FragmentTransaction
are addToBackStack
before commit:
@Override
public void onBackPressed() {
int count = getSupportFragmentManager().getBackStackEntryCount();
if (count == 0) {
super.onBackPressed();
//additional code
} else {
getSupportFragmentManager().popBackStack();
}
}
回答2:
I thing the best solution is
JAVA SOLUTION
Create simple interface :
public interface IOnBackPressed {
/**
* If you return true the back press will not be taken into account, otherwise the activity will act naturally
* @return true if your processing has priority if not false
*/
boolean onBackPressed();
}
And in your Activity
public class MyActivity extends Activity {
@Override public void onBackPressed() {
Fragment fragment = getSupportFragmentManager().findFragmentById(R.id.main_container);
if (!(fragment instanceof IOnBackPressed) || !((IOnBackPressed) fragment).onBackPressed()) {
super.onBackPressed();
}
} ...
}
Finally in your Fragment:
public class MyFragment extends Fragment implements IOnBackPressed{
@Override
public boolean onBackPressed() {
if (myCondition) {
//action not popBackStack
return true;
} else {
return false;
}
}
}
KOTLIN SOLUTION
1 - Create Interface
interface IOnBackPressed {
fun onBackPressed(): Boolean
}
2 - Prepare your Activity
class MyActivity : AppCompatActivity() {
override fun onBackPressed() {
val fragment =
this.supportFragmentManager.findFragmentById(R.id.main_container)
(fragment as? IOnBackPressed)?.onBackPressed()?.not()?.let {
super.onBackPressed()
}
}
}
3 - Implement in your target Fragment
class MyFragment : Fragment(), IOnBackPressed {
override fun onBackPressed(): Boolean {
return if (myCondition) {
//action not popBackStack
true
} else {
false
}
}
}
回答3:
According to @HaMMeRed answer here is pseudocode how should it works.
Lets say that your main activity is called BaseActivity
which has child fragments (like in SlidingMenu lib example).
Here are the steps:
First we need create interface and class which implements its interface to have generic method
Create class interface
OnBackPressedListener
public interface OnBackPressedListener { public void doBack(); }
Create class which implements skills of
OnBackPressedListener
public class BaseBackPressedListener implements OnBackPressedListener { private final FragmentActivity activity; public BaseBackPressedListener(FragmentActivity activity) { this.activity = activity; } @Override public void doBack() { activity.getSupportFragmentManager().popBackStack(null, FragmentManager.POP_BACK_STACK_INCLUSIVE); } }
Since now, we will work on our code
BaseActivity
and its fragmentsCreate private listener on top of your class
BaseActivity
protected OnBackPressedListener onBackPressedListener;
create method to set listener in
BaseActivity
public void setOnBackPressedListener(OnBackPressedListener onBackPressedListener) { this.onBackPressedListener = onBackPressedListener; }
in override
onBackPressed
implement something like that@Override public void onBackPressed() { if (onBackPressedListener != null) onBackPressedListener.doBack(); else super.onBackPressed();
in your fragment in
onCreateView
you should add our listener@Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { activity = getActivity(); ((BaseActivity)activity).setOnBackPressedListener(new BaseBackPressedListener(activity)); View view = ... ; //stuff with view return view; }
Voila, now when you click back in fragment you should catch your custom on back method.
回答4:
This worked for me: https://stackoverflow.com/a/27145007/3934111
@Override
public void onResume() {
super.onResume();
if(getView() == null){
return;
}
getView().setFocusableInTouchMode(true);
getView().requestFocus();
getView().setOnKeyListener(new View.OnKeyListener() {
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
if (event.getAction() == KeyEvent.ACTION_UP && keyCode == KeyEvent.KEYCODE_BACK){
// handle back button's click listener
return true;
}
return false;
}
});
}
回答5:
If you wanted that sort of functionality you would need to override it in your activity, and then add a YourBackPressed
interface to all your fragments, which you call on the relevant fragment whenever the back button is pressed.
Edit: I'd like to append my previous answer.
If I were to do this today, I'd use a broadcast, or possibly a ordered broadcast if I expected other panels to update in unison to the master/main content panel.
LocalBroadcastManager in the Support Library can help with this, and you just send the broadcast in onBackPressed
and subscribe in your fragments that care. I think that Messaging is a more decoupled implementation and would scale better, so it would be my official implementation recommendation now. Just use the Intent
's action as a filter for your message. send your newly created ACTION_BACK_PRESSED
, send it from your activity and listen for it in the relevant fragments.
回答6:
None of that is easy to implement nor will it function in an optimal way.
Fragments have a method call onDetach that will do the job.
@Override
public void onDetach() {
super.onDetach();
PUT YOUR CODE HERE
}
THIS WILL DO THE JOB.
回答7:
Just add addToBackStack
while you are transitioning between your fragments like below:
fragmentManager.beginTransaction().replace(R.id.content_frame,fragment).addToBackStack("tag").commit();
if you write addToBackStack(null)
, it will handle it by itself but if you give a tag , you should handle it manually.
回答8:
since this question and some of the answers are over five years old, let me share my solution. This is a follow-up and modernization to the answer from @oyenigun
UPDATE: At the bottom of this article, I added an alternative implementation using an abstract Fragment extension that won't involve the Activity at all, which would be useful for anyone with a more complex fragment hierarchy involving nested fragments that require different back behavior.
I needed to implement this because some of the fragments I use have smaller views that I would like to dismiss with the back button, such as small information views that pop up, etc, but this is good for anyone who needs to override the behavior of the back button inside fragments.
First, define an Interface
public interface Backable {
boolean onBackPressed();
}
This interface, which I call Backable
(I'm a stickler for naming conventions), has a single method onBackPressed()
that must return a boolean
value. We need to enforce a boolean value because we will need to know if the back button press has "absorbed" the back event. Returning true
means that it has, and no further action is needed, otherwise, false
says that the default back action still must take place. This interface should be it's own file (preferably in a separate package named interfaces
). Remember, separating your classes into packages is good practice.
Second, find the top fragment
I created a method that returns the last Fragment
object in the back stack. I use tags... if you use ID's, make the necessary changes. I have this static method in a utility class that deals with navigation states, etc... but of course, put it where it best suits you. For edification, I've put mine in a class called NavUtils
.
public static Fragment getCurrentFragment(Activity activity) {
FragmentManager fragmentManager = activity.getFragmentManager();
if (fragmentManager.getBackStackEntryCount() > 0) {
String lastFragmentName = fragmentManager.getBackStackEntryAt(
fragmentManager.getBackStackEntryCount() - 1).getName();
return fragmentManager.findFragmentByTag(lastFragmentName);
}
return null;
}
Make sure the back stack count is greater than 0, otherwise an ArrayOutOfBoundsException
could be thrown at runtime. If it isn't greater than 0, return null. We'll check for a null value later...
Third, Implement in a Fragment
Implement the Backable
interface in whichever fragment where you need to override the back button behavior. Add the implementation method.
public class SomeFragment extends Fragment implements
FragmentManager.OnBackStackChangedListener, Backable {
...
@Override
public boolean onBackPressed() {
// Logic here...
if (backButtonShouldNotGoBack) {
whateverMethodYouNeed();
return true;
}
return false;
}
}
In the onBackPressed()
override, put whatever logic you need. If you want the back button to not pop the back stack (the default behavior), return true, that your back event has been absorbed. Otherwise, return false.
Lastly, in your Activity...
Override the onBackPressed()
method and add this logic to it:
@Override
public void onBackPressed() {
// Get the current fragment using the method from the second step above...
Fragment currentFragment = NavUtils.getCurrentFragment(this);
// Determine whether or not this fragment implements Backable
// Do a null check just to be safe
if (currentFragment != null && currentFragment instanceof Backable) {
if (((Backable) currentFragment).onBackPressed()) {
// If the onBackPressed override in your fragment
// did absorb the back event (returned true), return
return;
} else {
// Otherwise, call the super method for the default behavior
super.onBackPressed();
}
}
// Any other logic needed...
// call super method to be sure the back button does its thing...
super.onBackPressed();
}
We get the current fragment in the back stack, then we do a null check and determine if it implements our Backable
interface. If it does, determine if the event was absorbed. If so, we're done with onBackPressed()
and can return. Otherwise, treat it as a normal back press and call the super method.
Second Option to not involve the Activity
At times, you don't want the Activity to handle this at all, and you need to handle it directly within the fragment. But who says you can't have Fragments with a back press API? Just extend your fragment to a new class.
Create an abstract class that extends Fragment and implements the View.OnKeyListner
interface...
import android.app.Fragment;
import android.os.Bundle;
import android.view.KeyEvent;
import android.view.View;
public abstract class BackableFragment extends Fragment implements View.OnKeyListener {
@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
view.setFocusableInTouchMode(true);
view.requestFocus();
view.setOnKeyListener(this);
}
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
if (event.getAction() == KeyEvent.ACTION_UP) {
if (keyCode == KeyEvent.KEYCODE_BACK) {
onBackButtonPressed();
return true;
}
}
return false;
}
public abstract void onBackButtonPressed();
}
As you can see, any fragment that extends BackableFragment
will automatically capture back clicks using the View.OnKeyListener
interface. Just call the abstract onBackButtonPressed()
method from within the implemented onKey()
method using the standard logic to discern a back button press. If you need to register key clicks other than the back button, just be sure to call the super
method when overriding onKey()
in your fragment, otherwise you'll override the behavior in the abstraction.
Simple to use, just extend and implement:
public class FragmentChannels extends BackableFragment {
...
@Override
public void onBackButtonPressed() {
if (doTheThingRequiringBackButtonOverride) {
// do the thing
} else {
getActivity().onBackPressed();
}
}
...
}
Since the onBackButtonPressed()
method in the super class is abstract, once you extend you must implement onBackButtonPressed()
. It returns void
because it just needs to perform an action within the fragment class, and does not need to relay the absorption of the press back to the Activity. Make sure you do call the Activity onBackPressed()
method if whatever you're doing with the back button doesn't require handling, otherwise, the back button will be disabled... and you don't want that!
Caveats As you can see, this sets the key listener to the root view of the fragment, and we'll need to focus it. If there are edit texts involved (or any other focus-stealing views) in your fragment that extends this class, (or other inner fragments or views that have the same), you'll need to handle that separately. There's a good article on extending an EditText to lose focus on a back press.
I hope someone finds this useful. Happy coding.
回答9:
The solution is simple:
1) If you have a base fragment class that all fragments extend, then add this code to it's class, otherwise create such a base fragment class
/*
* called when on back pressed to the current fragment that is returned
*/
public void onBackPressed()
{
// add code in super class when override
}
2) In your Activity class, override onBackPressed as follows:
private BaseFragment _currentFragment;
@Override
public void onBackPressed()
{
super.onBackPressed();
_currentFragment.onBackPressed();
}
3) In Your Fragment class, add your desired code:
@Override
public void onBackPressed()
{
setUpTitle();
}
回答10:
onBackPressed()
cause Fragment to be detach from Activity.
According to @Sterling Diaz answer I think he is right. BUT some situation will be wrong. (ex. Rotate Screen)
So, I think we could detect whether isRemoving()
to achieve goals.
You can write it at onDetach()
or onDestroyView()
. It is work.
@Override
public void onDetach() {
super.onDetach();
if(isRemoving()){
// onBackPressed()
}
}
@Override
public void onDestroyView() {
super.onDestroyView();
if(isRemoving()){
// onBackPressed()
}
}
回答11:
Well I done it like this, and it work for me
Simple interface
FragmentOnBackClickInterface.java
public interface FragmentOnBackClickInterface {
void onClick();
}
Example implementation
MyFragment.java
public class MyFragment extends Fragment implements FragmentOnBackClickInterface {
// other stuff
public void onClick() {
// what you want to call onBackPressed?
}
then just override onBackPressed in activity
@Override
public void onBackPressed() {
int count = getSupportFragmentManager().getBackStackEntryCount();
List<Fragment> frags = getSupportFragmentManager().getFragments();
Fragment lastFrag = getLastNotNull(frags);
//nothing else in back stack || nothing in back stack is instance of our interface
if (count == 0 || !(lastFrag instanceof FragmentOnBackClickInterface)) {
super.onBackPressed();
} else {
((FragmentOnBackClickInterface) lastFrag).onClick();
}
}
private Fragment getLastNotNull(List<Fragment> list){
for (int i= list.size()-1;i>=0;i--){
Fragment frag = list.get(i);
if (frag != null){
return frag;
}
}
return null;
}
回答12:
You should add interface to your project like below;
public interface OnBackPressed {
void onBackPressed();
}
And then, you should implement this interface on your fragment;
public class SampleFragment extends Fragment implements OnBackPressed {
@Override
public void onBackPressed() {
//on Back Pressed
}
}
And you can trigger this onBackPressed event under your activities onBackPressed event like below;
public class MainActivity extends AppCompatActivity {
@Override
public void onBackPressed() {
Fragment currentFragment = getSupportFragmentManager().getFragments().get(getSupportFragmentManager().getBackStackEntryCount() - 1);
if (currentFragment instanceof OnBackPressed) {
((OnBackPressed) currentFragment).onBackPressed();
}
super.onBackPressed();
}
}
回答13:
If you use EventBus, it is probably a far more simpler solution :
In your Fragment :
@Override
public void onAttach(Activity activity) {
super.onAttach(activity);
EventBus.getDefault().register(this);
}
@Override
public void onDetach() {
super.onDetach();
EventBus.getDefault().unregister(this);
}
// This method will be called when a MessageEvent is posted
public void onEvent(BackPressedMessage type){
getSupportFragmentManager().popBackStack();
}
and in your Activity class you can define :
@Override
public void onStart() {
super.onStart();
EventBus.getDefault().register(this);
}
@Override
public void onStop() {
EventBus.getDefault().unregister(this);
super.onStop();
}
// This method will be called when a MessageEvent is posted
public void onEvent(BackPressedMessage type){
super.onBackPressed();
}
@Override
public void onBackPressed() {
EventBus.getDefault().post(new BackPressedMessage(true));
}
BackPressedMessage.java is just a POJO object
This is super clean and there is no interface/implementation hassle.
回答14:
This is just a small code that will do the trick:
getActivity().onBackPressed();
Hope it helps someone :)
回答15:
this is my solution:
in MyActivity.java:
public interface OnBackClickListener {
boolean onBackClick();
}
private OnBackClickListener onBackClickListener;
public void setOnBackClickListener(OnBackClickListener onBackClickListener) {
this.onBackClickListener = onBackClickListener;
}
@Override
public void onBackPressed() {
if (onBackClickListener != null && onBackClickListener.onBackClick()) {
return;
}
super.onBackPressed();
}
and in Fragment:
((MyActivity) getActivity()).setOnBackClickListener(new MyActivity.OnBackClickListener() {
@Override
public boolean onBackClick() {
if (condition) {
return false;
}
// some codes
return true;
}
});
回答16:
If you're using androidx.appcompat:appcompat:1.1.0
or above then you can add an OnBackPressedCallback
to your fragment as follows
requireActivity()
.onBackPressedDispatcher
.addCallback(this, object : OnBackPressedCallback(true) {
override fun handleOnBackPressed() {
Log.d(TAG, "Fragment back pressed invoked")
// Do custom work here
// if you want onBackPressed() to be called as normal afterwards
if (isEnabled) {
isEnabled = false
requireActivity().onBackPressed()
}
}
}
)
See https://developer.android.com/guide/navigation/navigation-custom-back
回答17:
How about using onDestroyView()?
@Override
public void onDestroyView() {
super.onDestroyView();
}
回答18:
@Override
public void onResume() {
super.onResume();
getView().setFocusableInTouchMode(true);
getView().requestFocus();
getView().setOnKeyListener(new View.OnKeyListener() {
@Override
public boolean onKey(View v, int keyCode, KeyEvent event) {
if (event.getAction() == KeyEvent.ACTION_UP && keyCode == KeyEvent.KEYCODE_BACK) {
// handle back button
replaceFragmentToBackStack(getActivity(), WelcomeFragment.newInstance(bundle), tags);
return true;
}
return false;
}
});
}
回答19:
public class MyActivity extends Activity {
protected OnBackPressedListener onBackPressedListener;
public interface OnBackPressedListener {
void doBack();
}
public void setOnBackPressedListener(OnBackPressedListener onBackPressedListener) {
this.onBackPressedListener = onBackPressedListener;
}
@Override
public void onBackPressed() {
if (onBackPressedListener != null)
onBackPressedListener.doBack();
else
super.onBackPressed();
}
@Override
protected void onDestroy() {
onBackPressedListener = null;
super.onDestroy();
}
}
in your fragment add the following, dont forget to implement mainactivity's interface.
public class MyFragment extends Framgent implements MyActivity.OnBackPressedListener {
@Override
public void onViewCreated(View view, Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
((MyActivity) getActivity()).setOnBackPressedListener(this);
}
@Override
public void doBack() {
//BackPressed in activity will call this;
}
}
回答20:
Do not implement ft.addToBackStack() method so that when you pressed back button your activity will be finished.
proAddAccount = new ProfileAddAccount();
FragmentManager fragmentManager = getSupportFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
fragmentTransaction.replace(R.id.fragment_container, proAddAccount);
//fragmentTransaction.addToBackStack(null);
fragmentTransaction.commit();
回答21:
Just follow these steps:
Always while adding a fragment,
fragmentTransaction.add(R.id.fragment_container, detail_fragment, "Fragment_tag").addToBackStack(null).commit();
Then in the main activity, override onBackPressed()
if (getSupportFragmentManager().getBackStackEntryCount() > 0) {
getSupportFragmentManager().popBackStack();
} else {
finish();
}
To handle the back button in your app,
Fragment f = getActivity().getSupportFragmentManager().findFragmentByTag("Fragment_tag");
if (f instanceof FragmentName) {
if (f != null)
getActivity().getSupportFragmentManager().beginTransaction().remove(f).commit()
}
That's it!
回答22:
Very short and sweet answer:
getActivity().onBackPressed();
Explanation of whole scenario of my case:
I have FragmentA in MainActivity, I am opening FragmentB from FragmentA (FragmentB is child or nested fragment of FragmentA)
Fragment duedateFrag = new FragmentB();
FragmentTransaction ft = getFragmentManager().beginTransaction();
ft.replace(R.id.container_body, duedateFrag);
ft.addToBackStack(null);
ft.commit();
Now if you want to go to FragmentA from FragmentB you can simply put getActivity().onBackPressed();
in FragmentB.
回答23:
In activity life cycle, always android back button deals with FragmentManager transactions when we used FragmentActivity or AppCompatActivity.
To handle the backstack we don't need to handle its backstack count or tag anything but we should keep focus while adding or replacing a fragment. Please find the following snippets to handle the back button cases,
public void replaceFragment(Fragment fragment) {
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
if (!(fragment instanceof HomeFragment)) {
transaction.addToBackStack(null);
}
transaction.replace(R.id.activity_menu_fragment_container, fragment).commit();
}
Here, I won't add back stack for my home fragment because it's home page of my application. If add addToBackStack to HomeFragment then app will wait to remove all the frament in acitivity then we'll get blank screen so I'm keeping the following condition,
if (!(fragment instanceof HomeFragment)) {
transaction.addToBackStack(null);
}
Now, you can see the previously added fragment on acitvity and app will exit when reaching HomeFragment. you can also look on the following snippets.
@Override
public void onBackPressed() {
if (mDrawerLayout.isDrawerOpen(Gravity.LEFT)) {
closeDrawer();
} else {
super.onBackPressed();
}
}
回答24:
Fragment: Make a BaseFragment placing a method:
public boolean onBackPressed();
Activity:
@Override
public void onBackPressed() {
List<Fragment> fragments = getSupportFragmentManager().getFragments();
if (fragments != null) {
for (Fragment fragment : fragments) {
if (!fragment.isVisible()) continue;
if (fragment instanceof BaseFragment && ((BaseFragment) fragment).onBackPressed()) {
return;
}
}
}
super.onBackPressed();
}
Your activity will run over the attached and visible fragments and call onBackPressed() on each one of them and abort if one of them returns 'true' (meaning that it has been handled, so no further actions).
回答25:
According to the AndroidX release notes, androidx.activity 1.0.0-alpha01
is released and introduces ComponentActivity
, a new base class of the existing FragmentActivity
and AppCompatActivity
. And this release brings us a new feature:
You can now register an OnBackPressedCallback
via addOnBackPressedCallback
to receive onBackPressed()
callbacks without needing to override the method in your activity.
回答26:
You can register fragment in activity to handle back press:
interface BackPressRegistrar {
fun registerHandler(handler: BackPressHandler)
fun unregisterHandler(handler: BackPressHandler)
}
interface BackPressHandler {
fun onBackPressed(): Boolean
}
usage:
In Fragment:
private val backPressHandler = object : BackPressHandler {
override fun onBackPressed(): Boolean {
showClosingWarning()
return false
}
}
override fun onResume() {
super.onResume()
(activity as? BackPressRegistrar)?.registerHandler(backPressHandler)
}
override fun onStop() {
(activity as? BackPressRegistrar)?.unregisterHandler(backPressHandler)
super.onStop()
}
In Activity:
class MainActivity : AppCompatActivity(), BackPressRegistrar {
private var registeredHandler: BackPressHandler? = null
override fun registerHandler(handler: BackPressHandler) { registeredHandler = handler }
override fun unregisterHandler(handler: BackPressHandler) { registeredHandler = null }
override fun onBackPressed() {
if (registeredHandler?.onBackPressed() != false) super.onBackPressed()
}
}
回答27:
Best solution,
import android.support.v4.app.Fragment;
import android.support.v4.app.FragmentManager;
import android.support.v7.app.AppCompatActivity;
public class BaseActivity extends AppCompatActivity {
@Override
public void onBackPressed() {
FragmentManager fm = getSupportFragmentManager();
for (Fragment frag : fm.getFragments()) {
if (frag == null) {
super.onBackPressed();
finish();
return;
}
if (frag.isVisible()) {
FragmentManager childFm = frag.getChildFragmentManager();
if (childFm.getFragments() == null) {
super.onBackPressed();
finish();
return;
}
if (childFm.getBackStackEntryCount() > 0) {
childFm.popBackStack();
return;
}
else {
fm.popBackStack();
if (fm.getFragments().size() <= 1) {
finish();
}
return;
}
}
}
}
}
回答28:
Its just simple if you have An Activity A and you make 3 fragments like B ,C and D.Now if you are in fragment B or C and onBackPressed
you want to move on Fragment D every time .Then you have to just Override the onBackPressed()
method in main Activity A and also when you jump to any fragment then pass a TAG or name of that fragment by which you recognized that fragment in main Activity A.
I am giving the example of that one by which you can easily understand that....
if (savedInstanceState == null) {
getSupportFragmentManager().beginTransaction().add(R.id.container, new C_fragment(),"xyz").commit();
}
or if you are moving from fragment B to fragment C..and on back press you want to come on Fragment D...like below
btn.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
getActivity().getSupportFragmentManager().beginTransaction().add(R.id.container, new C_frament(), "xyz").commit();
((ActionBarActivity) getActivity()).getSupportActionBar().setTitle("Fragment C");
}
});
Now you have to just override the onBackPressed() method in main activity....like below..
@Override
public void onBackPressed() {
FragmentManager fragmentManager =getSupportFragmentManager();
if (((C_fragment) getSupportFragmentManager().findFragmentByTag("xyz")) != null && ((C_fragment) getSupportFragmentManager().findFragmentByTag("xyz")).isVisible()) {
Fragment fragment = new D_Fragment();
fragmentManager.beginTransaction().replace(R.id.container, fragment).commit();
getSupportActionBar().setTitle("D fragment ");
} else {
super.onBackPressed();
}
}
回答29:
I have used another approach as follows:
- An Otto event bus to communicate between the Activity and its Fragments
- A Stack in the Activity containing custom back actions wrapped in a
Runnable
that the calling fragment defines - When
onBackPressed
is called in the controlling Activity, it pops the most recent custom back action and executes itsRunnable
. If there's nothing on the Stack, the defaultsuper.onBackPressed()
is called
The full approach with sample code is included here as an answer to this other SO question.
回答30:
I know it's too late but I had the same problem last week. None of the answers helped me. I then was playing around with the code and this worked, since I already added the fragments.
In your Activity, set an OnPageChangeListener
for the ViewPager
so that you will know when the user is in the second activity. If he is in the second activity, make a boolean true
as follows:
mSectionsPagerAdapter = new SectionsPagerAdapter(getSupportFragmentManager());
// Set up the ViewPager with the sections adapter.
mViewPager = (ViewPager) findViewById(R.id.pager);
mViewPager.setAdapter(mSectionsPagerAdapter);
mViewPager.setCurrentItem(0);
mViewPager.addOnPageChangeListener(new OnPageChangeListener() {
@Override
public void onPageSelected(int position) {
// TODO Auto-generated method stub
mSectionsPagerAdapter.instantiateItem(mViewPager, position);
if(position == 1)
inAnalytics = true;
else if(position == 0)
inAnalytics = false;
}
@Override
public void onPageScrolled(int position, float arg1, int arg2) {
// TODO Auto-generated method stub
}
@Override
public void onPageScrollStateChanged(int arg0) {
// TODO Auto-generated method stub
}
});
Now check for the boolean whenever back button is pressed and set the current item to your first Fragment:
@Override
public void onBackPressed() {
if(inAnalytics)
mViewPager.setCurrentItem(0, true);
else
super.onBackPressed();
}
来源:https://stackoverflow.com/questions/5448653/how-to-implement-onbackpressed-in-fragments