I am new to Android programming though I am coding in another languages. I am not able to navigate to home fragment in a particular scenario.
I have three fragments among few more viz., Settings, Capacity and About. All these can be reached via Overflow Toolbar menu items. Settings can be reached thru another button on home fragment.
Use case 1: Click Settings button on home fragment. Settings open. In Settings use either Up/Home or Back Button. On clicking any one of them, home fragment is reached.
Use case 2: Click Toolbar overflow menu(three dots). Three menu item appears. Select Settings menu item. Settings Open. In Settings, use either Up/Home or Back Button. On clicking any one of them, home fragment is reached.
Use Case 1 is working fine. I think nav_graph defined is used here where navigation between fragments is defined.
Use Case 2 fails. Upon pressing Up/Home button or Back button, I get white screen rather landing on home fragment.
I studied code in several websites including SO and official Android site. But could not make out what kind of code to be used when navigating back to home fragment from another fragment(which was particularly reached via Toolbar menu and outside of nav_graph).
I studied methods in stack in debug window. But did not help me either.
Please enlighten me the approach to be used.
First set Home Fragment in content view(frame view).
on top you can your next fragment kinda stack of fragments 1 above another.
create method in activity this method will popout all fragments except Home Fragment.
Add Fragment use below code
Fragment fragment = new FragmentHome();
FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction().replace(R.id.content_frame,fragment).addToBackStack(fragment.getClass().getSimpleName()).commit();
To go Home clearing all
public void goToHome()
{
FragmentManager fragmentManager = getSupportFragmentManager();
for(int i = 0; i < fragmentManager.getBackStackEntryCount()-1; ++i)
{
fragmentManager.popBackStack();
}
}
I continued searching for solution to my problem. I came across a solution in https://medium.com/mobile-app-development-publication/learn-android-navigation-component-through-coding-79dc47b240b3 It worked perfectly well and solved white screen issue and also not using explicit method using fragment manager for traversing to another fragment. It was about linking menu items to navigation graph.
Related
My problem is illustrated by this screen record.
When I click the FAB on FinanceFragment, it will open AddTransactionFragment. But when I navigate to ReminderFragment and go back to FinanceFragment, the AddTransactionFragment is destroyed.
How could I -- similar to the YouTube app when one switches between fragments -- keep AddTransactionFragment visible while I navigate to another fragment?
I tried to add addToBackStack() but this turned out not to be what I was looking for.
I'm trying to make an app which has the DrawerActivity as the main activity. I have implemented 8 fragments within it, which correspond to each item in the drawer. Now, the problem I have is, whenever I try to press the back button to go back to the DrawerActivity from the fragment, I end up exiting the app instead. I've been searching on forums for three days now, and have not found any solution to this. Quite frustrated, I stupidly deleted my code, so I can't really show it right now. Can anyone simply explain to me how I should exit a fragment using the back button, and return to my main activity?
Current scenario:
DrawerActivity contains eight fragments, all independent of each other. Let's call them fragments A through H. When I go to fragment A, I should be able to open the navigationDrawer and head to any other fragments from B to H. However, on pressing the back button, I should also be able to go back to the drawer activity's main page.
Things I have tried which didn't work are
1. Using onBackPressed and popBackStack.
2. Creating custom listener.
3. Using fragmentTransaction.
I can't believe how stupid I am. I was using my Gmail app on my phone when I suddenly realized that the first fragment in the drawer activity is always the default fragment, and the app should always revert to it on the back button press. What I was thinking was that the drawer activity would go back to the original state when back is pressed, but I didn't account for the fact that fragments are part of the activity itself.
Thank you all for trying to understand my problem, which wasn't really a problem at all... It seems I learned something in spite of myself.
Have you tried overriding onBackPressed() without calling the superclass method? (So that you prevent finish() from being called.)
#Override
public void onBackPressed() {
//show Fragment A
}
Call it without the "super.onBackPressed()" and it should work.
You must add your fragment to the android back Stack like this:
getSupportFragmentManager()
.beginTransaction()
.replace(R.id.your_container,fragment,fragment.TAG)
.addToBackStack(null)
.commit();
On my app I am using a Main Activity, which has a Navigation Drawer, and as the user go to an options from the drawer, it will change the fragment beging displayed accordingly to the option selected.
If the user hit's "Back button" several times, it will go back to a point in which it will reach my Main Activity, which is a blank and empty layout.
When I reach this point (my main activit, empty), I would like to exit the app, or, open the Navigation Drawer.
The problem is, I don't know any event that shows me that I am back to the Main Activity. I checked the onResume, but it's never called, which makes sense, since the main activity has never been stopped.
I thought perhaps there would be an event from the fragment manager that would be called on the Main Activity when a fragment was detached, and from there I could check if there was no fragment at all attached?
When you push your first fragment, add a tag to it. Something like
transaction.replace( R.id.rootContainer, firstFragment, "rootFragment");
Whenever user presses back button, you can get your rootFragment from FragmentManager
FirstFragment myFragment = (FirstFragment) getSupportFragmentManager().findFragmentByTag("rootFragment");
And check if this fragment is visible or not, by myFragment.isVisible(), if not, then keep popping the stack, if it is visible, it means user is on the first fragment. Now you can either quit the app, or show your menu drawer.
Good night good sir. Thank you for your tip.
I used a different approach, based on your repply, that gave me quite a few insights.
On main activity, I Overrided the onKeyDown and check if it was pressed the Back Button. If yes, then I check the size of my Back Stack.
Uppon that, I decide if I want to finish my application.
Also, thanks for the tip of "labeling" the fragments on the back stack, didn't know I could do that.
I have 3 actionbar tabs at the top of my main activity, and a fragments for each tab. I have a few questions regarding such a design and how to open new activities from it.
I have a button in my first tab fragment that I need to open a new activity, but I want the tabs to remain. Here is an image to demonstrate:
If you are on fragment 1 and you press the button to open the new activity, the back button should simply return you to fragment 1. However, if you are on fragment 1, you press the button to go to the new activity and then navigate to a different tab, pressing the back button should do nothing. I hope this makes sense. What is the best way to achieve this?
You shouldn't do this - it is a common Navigation Anti-Pattern. Instead, you should consider taking the user to a new screen (whether that is a new activity or a fragment that replaces everything visible including the tabs).
In my main activity, I have an actionbar with NAVIGATION_MODE_TABS. The contents of each tab is a listfragment.
I'd like to make it so that that when a listitem is clicked, a new fragment is brought into view, and the actionbar mode is changed to NAVIGATION_MODE_STANDARD (so that the tabs are now hidden).
I've managed to get this to work with the following code:
In the listitemclick method:
ActionBar actionBar = getActivity().getActionBar();
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
Fragment albumListFragment = new AlbumListFragment();
albumListFragment.setArguments(bundle);
FragmentTransaction ft = getFragmentManager().beginTransaction();
ft.replace(android.R.id.content, albumListFragment);
ft.addToBackStack(null);
// Commit the transaction
ft.commit();
Log.i("FragmentList", "Item clicked: " + id);
The problem is when I press the back button, the tabs are still gone, and the previous fragment doesn't come back into view.
Am I doing something wrong.. Is it something to do with the fragment backstack? Should I go about it another way, or even override the backpress?
--Edit--
For clarity - I am calling addToBackStack when I call fragmenttransaction.replace, but when I press the back button, the previous fragment is not restored.
Maybe this is a little late, I tried to re-construct your problem for hours but didnot succeed. I tried to switch from a listview in a fragment hosted by a ActionBar Tab to another view by the way described in your question(i.e. ft.replace(android.R.id.content, albumListFragment);) but with no effect. After some google and stackoverflow, I use this way to successfully switch the fragment within the tab, yet with no problem as you have.
As the "action bar is not showing correctly" problem, its probably caused by the backstack revert and UI change as describe in android developer guide. you might try to override the onBackStackChanged() callback and re-construct the UI.
As the "backstack does not bring the previous fragment back" problem, you may want to post a little more code to help others re-construct the problem to find the answer.
Wish helpful.
I experienced exactly the same issue and figured it out that the problem only occurs when you set the ActionBar back to NAVIGATION_MODE_STANDARD.
The only solution for me was to place the new fragment with no tabs in a helper activity which has NAVIGATION_MODE_STANDARD. Then you can easily use the back button functionality provided by Android to go back to the activity with NAVIGATION_MODE_TABS and retain its state.
FragmentTransaction.replace() actually removes the previous fragment in the layout and add new instance of the fragment.
Try using FragmentTransaction#show() and FragmentTransaction#hide() methods instead of replace.
The backstack ends the current activity and goes to the previous activity, not the previous fragment. (See the backstack guide: http://developer.android.com/guide/components/tasks-and-back-stack.html).
You could force, as you suggested, the behavior by overriding onBackPressed, however, I don't know that I would change the natural Android behavior in such a way. If you look at other apps, particularly core apps, that do similar things the back button does not go to a previous fragment, but a previous activity.
Also you do have total control on the behavior of the "up" button (that is your app icon on the action bar with a left arrow). You have to programatically set it up to be used as a button as described in the ActionBar guide (let me know if you need to know how to do this) and with that you could have it set up a previous fragment on a stack that you maintain somewhere.